kerneltest/e32test/usbho/t_otgdi/src/otgroot.cpp
changeset 9 96e5fb8b040d
child 43 c1f20ce4abcf
equal deleted inserted replaced
-1:000000000000 9:96e5fb8b040d
       
     1 // Copyright (c) 2007-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 // @internalComponent
       
    15 // 
       
    16 //
       
    17 
       
    18 #include <e32std.h>
       
    19 #include <e32std_private.h>
       
    20 #include <u32std.h> 	// unicode builds
       
    21 #include <e32base.h>
       
    22 #include <e32base_private.h>
       
    23 #include <e32cons.h>
       
    24 #include <e32Test.h>	// RTest header
       
    25 #include <e32def.h>
       
    26 #include <e32def_private.h>
       
    27 #include <d32otgdi.h>		// OTGDI header
       
    28 #include <d32usbc.h>		// USBCC header
       
    29 #include "otgroot.h"
       
    30 #include "testcaseroot.h"
       
    31 
       
    32 RUsbOtgDriver  oUsbOtgDriver;
       
    33 RDevUsbcClient oUsbcClient;
       
    34 
       
    35 
       
    36 //=====================================================================================
       
    37 	
       
    38 /*	this class wraps all OTGDI calls as well to simplify 
       
    39 	 calling and normalising object access. - it has no base-class hence we can use multiple-inheritance
       
    40 	 */	
       
    41 	COtgRoot::COtgRoot()
       
    42 	{
       
    43 	iOptActive = EFalse;
       
    44 	SetLoaded(EFalse);	
       
    45 	}
       
    46 	
       
    47 	
       
    48 /** otgLoadLdd
       
    49 */
       
    50 TInt COtgRoot::otgLoadLdd()
       
    51 	{
       
    52 	
       
    53 	LOG_FUNC
       
    54 	LOG_VERBOSE2(_L("Load driver: %S\n"), &KOTGDeviceInterfaceDriverName);
       
    55 
       
    56 	if (!LddLoaded())
       
    57 		{
       
    58 
       
    59 	 	// load ldd device drivers (load otg only, it will load the needed stuff for us)
       
    60 		TInt err(User::LoadLogicalDevice(KOTGDeviceInterfaceDriverName));
       
    61 		if ( (err != KErrNone) && (err != KErrAlreadyExists) )
       
    62 			{
       
    63 			test.Printf(_L("<Error %d> Unable to load driver: %S\n"), err, &KOTGDeviceInterfaceDriverName);
       
    64 			SetLoaded(EFalse);
       
    65 			return(err);
       
    66 			}
       
    67 		else
       
    68 			{
       
    69 			LOG_VERBOSE2(_L("Loaded driver: '%S' OK\n"), &KOTGDeviceInterfaceDriverName);
       
    70 			SetLoaded(ETrue);
       
    71 			}
       
    72 		
       
    73 		}
       
    74 		return(KErrNone);
       
    75 	}
       
    76 
       
    77 
       
    78 /** otgOpen
       
    79 */
       
    80 TInt COtgRoot::otgOpen()
       
    81 	{
       
    82 	LOG_FUNC
       
    83 	
       
    84 	LOG_VERBOSE2(_L("Opening session... loaded = %d\n"), LddLoaded());
       
    85 
       
    86 	TInt err(oUsbOtgDriver.Open());
       
    87 	if (err != KErrNone)
       
    88 		{
       
    89 		test.Printf(_L("<Error %d> Unable to open a channel to USB OTG driver\n"),err);
       
    90 		return(err);
       
    91 		}
       
    92 	else
       
    93 		{
       
    94 		LOG_VERBOSE1(_L("Open channel OK\n"));
       
    95 		}
       
    96 		
       
    97 	return(KErrNone);	
       
    98 	}
       
    99 
       
   100 
       
   101 /** otgClose
       
   102 */
       
   103 void COtgRoot::otgClose()
       
   104 	{
       
   105 	LOG_FUNC
       
   106 	
       
   107 	test.Printf(_L("Closing session... loaded = %d\n"), LddLoaded());
       
   108 	oUsbOtgDriver.Close();
       
   109 	}
       
   110 
       
   111 
       
   112 /* otgActivateOptTestMode
       
   113  */ 
       
   114 TInt COtgRoot::otgActivateOptTestMode()
       
   115 	{
       
   116 	LOG_FUNC
       
   117 
       
   118 	TInt err = oUsbOtgDriver.ActivateOptTestMode();
       
   119 
       
   120 	return(err);
       
   121 	}
       
   122 
       
   123 
       
   124 /** otgStartStacks
       
   125 */
       
   126 TInt COtgRoot::otgStartStacks()
       
   127 	{
       
   128 	LOG_FUNC
       
   129 
       
   130 	TInt err(oUsbOtgDriver.StartStacks());
       
   131 	if (err != KErrNone)
       
   132 		{
       
   133 
       
   134 		LOG_FUNCERROR(err)
       
   135 
       
   136 		}
       
   137 	return(err);
       
   138 	
       
   139 	}
       
   140 
       
   141 
       
   142 /** otgStopStacks
       
   143 */ 
       
   144 void COtgRoot::otgStopStacks()
       
   145 	{
       
   146 	LOG_FUNC
       
   147 	
       
   148 	oUsbOtgDriver.StopStacks();
       
   149 	}
       
   150 
       
   151 
       
   152 /** otgUnloadLdd
       
   153 */
       
   154 void COtgRoot::otgUnloadLdd()
       
   155 	{
       
   156 
       
   157 	// code to unload the OTG ldd driver
       
   158 	TInt err (User::FreeLogicalDevice(KOTGDeviceInterfaceDriverName));
       
   159 	if (err != KErrNone)
       
   160 		{
       
   161 		LOG_FUNCERROR(err)
       
   162 		}
       
   163 
       
   164 	SetLoaded(EFalse);
       
   165 	}
       
   166 
       
   167 
       
   168 /** otgQueueOtgEventRequest
       
   169 */
       
   170 void COtgRoot::otgQueueOtgEventRequest(RUsbOtgDriver::TOtgEvent& aEvent, TRequestStatus &aStatus)
       
   171 	{
       
   172 	//LOG_FUNC	
       
   173 	LOG_VERBOSE2(_L("Queue an Event Request %08X.\n"), (TInt)(&aStatus));
       
   174 
       
   175 	oUsbOtgDriver.QueueOtgEventRequest(aEvent, aStatus);
       
   176 	
       
   177 	}
       
   178 	
       
   179 
       
   180 /** otgCancelOtgEventRequest
       
   181 */	
       
   182 void COtgRoot::otgCancelOtgEventRequest()
       
   183 	{
       
   184 	LOG_VERBOSE1(_L("Cancel Event Request.\n"));
       
   185 	oUsbOtgDriver.CancelOtgEventRequest();
       
   186 	}
       
   187     
       
   188     
       
   189 /** otgQueueOtgMessageRequest
       
   190 */
       
   191 void COtgRoot::otgQueueOtgMessageRequest(RUsbOtgDriver::TOtgMessage& aMessage, TRequestStatus &aStatus)
       
   192 	{
       
   193 	//LOG_FUNC	
       
   194 	LOG_VERBOSE2(_L("Queue a Message Request %08X.\n"), (TInt)(&aStatus));
       
   195 
       
   196 	//LOG_VERBOSE1(_L("Queue a Message Request.\n"));
       
   197 	oUsbOtgDriver.QueueOtgMessageRequest(aMessage, aStatus);
       
   198 		
       
   199 	}
       
   200 	
       
   201 
       
   202 /** otgCancelOtgMessageRequest
       
   203 */	
       
   204 void COtgRoot::otgCancelOtgMessageRequest()
       
   205 	{
       
   206 	LOG_VERBOSE1(_L("Cancel Message Request.\n"));
       
   207 	oUsbOtgDriver.CancelOtgMessageRequest();
       
   208 	}    
       
   209     
       
   210 void COtgRoot::otgQueuePeripheralStateRequest(TUint& aPeripheralState, TRequestStatus& aStatus)
       
   211 	{
       
   212 	LOG_VERBOSE1(_L("Queue Peripheral State Request.\n"));
       
   213 	oUsbcClient.AlternateDeviceStatusNotify(aStatus, aPeripheralState);
       
   214 	}
       
   215 
       
   216 void COtgRoot::otgCancelPeripheralStateRequest()
       
   217 	{
       
   218 	LOG_VERBOSE1(_L("Cancel Peripheral State Request.\n"));
       
   219 	oUsbcClient.AlternateDeviceStatusNotifyCancel();	
       
   220 	}
       
   221 
       
   222 void COtgRoot::otgQueueAConnectionIdleRequest(RUsbOtgDriver::TOtgConnection& aAConnectionIdle, TRequestStatus& aStatus)
       
   223 	{
       
   224 	LOG_VERBOSE1(_L("Queue A Connection Idle Request.\n"));
       
   225 	oUsbOtgDriver.QueueOtgConnectionNotification(aAConnectionIdle, aStatus);
       
   226 	}
       
   227 
       
   228 void COtgRoot::otgCancelAConnectionIdleRequest()
       
   229 	{
       
   230 	LOG_VERBOSE1(_L("Cancel A Connection Idle Request.\n"));
       
   231 	oUsbOtgDriver.CancelOtgConnectionNotification();
       
   232 	}
       
   233 
       
   234 
       
   235 /** otgQueueOtgStateRequest
       
   236 */
       
   237 void COtgRoot::otgQueueOtgStateRequest(RUsbOtgDriver::TOtgState& aState, TRequestStatus &aStatus)
       
   238 	{
       
   239 	//LOG_FUNC	
       
   240 	LOG_VERBOSE2(_L("Queue a State Request %08X.\n"), (TInt)(&aStatus));
       
   241 
       
   242 	oUsbOtgDriver.QueueOtgStateRequest(aState, aStatus);
       
   243 	
       
   244 	}
       
   245 	
       
   246 
       
   247 /** otgCancelOtgStateRequest
       
   248 */	
       
   249 void COtgRoot::otgCancelOtgStateRequest()
       
   250 	{
       
   251 	LOG_VERBOSE1(_L("Cancel State Request.\n"));
       
   252 	oUsbOtgDriver.CancelOtgStateRequest();
       
   253 	}
       
   254 
       
   255     
       
   256 /** otgBusRequest
       
   257 raise VBus (in reality this must only happen when a 'A' is present... and when not present it starts HNP)
       
   258 */
       
   259 TInt COtgRoot::otgBusRequest()
       
   260 	{
       
   261 	LOG_FUNC
       
   262 	
       
   263 	TInt err(0);
       
   264 	err = oUsbOtgDriver.BusRequest();
       
   265 	if (err != KErrNone)
       
   266 		{
       
   267 		LOG_FUNCERROR(err)
       
   268 		}
       
   269 	return(err);
       
   270 	}
       
   271 	
       
   272 
       
   273 /* call when SRP has been recieved, based on our HNP Enable setting, this will allow HNP. The 
       
   274  * A-device may choose to call BusRequest directly, which will result in a 'short-circuit' role-swap.
       
   275  */
       
   276 TInt COtgRoot::otgBusRespondSRP()
       
   277 	{
       
   278 	LOG_FUNC
       
   279 	TInt err(0);
       
   280 		err = oUsbOtgDriver.BusRespondSrp();
       
   281 		if (err != KErrNone)
       
   282 			{
       
   283 			LOG_FUNCERROR(err)
       
   284 			}
       
   285 		return(err);
       
   286 	}
       
   287 
       
   288 	
       
   289 /** Drop VBus (A-host)
       
   290 */	
       
   291 TInt COtgRoot::otgBusDrop()
       
   292 	{
       
   293 	LOG_FUNC
       
   294 	TInt err(0);
       
   295 	err = oUsbOtgDriver.BusDrop();
       
   296 	if (err != KErrNone)
       
   297 		{
       
   298 		LOG_FUNCERROR(err)
       
   299 		}
       
   300 	return(err);
       
   301 	}
       
   302 
       
   303 /** otgBusClearError
       
   304 */
       
   305 TInt COtgRoot::otgBusClearError()
       
   306 	{
       
   307 	LOG_FUNC
       
   308 	
       
   309 	TInt err(0);
       
   310 	err = oUsbOtgDriver.BusClearError();
       
   311 	if (err != KErrNone)
       
   312 		{
       
   313 		LOG_FUNCERROR(err)
       
   314 		}
       
   315 	return(err);
       
   316 	}
       
   317 	
       
   318 
       
   319 	
       
   320 void COtgRoot::otgQueueOtgIdPinNotification(RUsbOtgDriver::TOtgIdPin& aPin, TRequestStatus& aStatus)
       
   321 	{
       
   322 	LOG_FUNC
       
   323 	oUsbOtgDriver.QueueOtgIdPinNotification(aPin, aStatus);	// the kernel driver populates aPin...
       
   324 	}
       
   325 
       
   326 	
       
   327 void COtgRoot::otgCancelOtgIdPinNotification()
       
   328 	{
       
   329 	LOG_FUNC
       
   330 	oUsbOtgDriver.CancelOtgIdPinNotification();
       
   331 	}
       
   332 
       
   333 
       
   334 void COtgRoot::otgQueueOtgVbusNotification(RUsbOtgDriver::TOtgVbus& aVbus, 
       
   335                                                 TRequestStatus& aStatus
       
   336                                                )
       
   337 	{
       
   338 	LOG_FUNC
       
   339 	oUsbOtgDriver.QueueOtgVbusNotification(aVbus, aStatus);
       
   340 	}
       
   341 	
       
   342 	
       
   343 void COtgRoot::otgCancelOtgVbusNotification()
       
   344 	{
       
   345 	LOG_FUNC
       
   346 	oUsbOtgDriver.CancelOtgVbusNotification();
       
   347 	}
       
   348 
       
   349 
       
   350 TBool COtgRoot::otgIdPinPresent()
       
   351 	{
       
   352 	LOG_FUNC
       
   353 	TRequestStatus aStatus;
       
   354 	RUsbOtgDriver::TOtgIdPin aPin;
       
   355 	oUsbOtgDriver.QueueOtgIdPinNotification(aPin, aStatus);	// the kernel driver populates aPin...
       
   356 	LOG_VERBOSE2(_L("(sync) ID_PIN=%d\n"), iOTGIdPin);
       
   357 	
       
   358 	oUsbOtgDriver.CancelOtgIdPinNotification();
       
   359 	// swallow the event
       
   360 	User::WaitForRequest(aStatus);
       
   361 	
       
   362 	if (RUsbOtgDriver::EIdPinAPlug == aPin)			// at this stage, the aPin value is known
       
   363 		{
       
   364 		return(ETrue);
       
   365 		}
       
   366 	return(EFalse);
       
   367 	}
       
   368 	
       
   369 	
       
   370 TBool COtgRoot::otgVbusPresent()
       
   371 	{
       
   372 	LOG_FUNC
       
   373 	TRequestStatus aStatus;
       
   374  	RUsbOtgDriver::TOtgVbus aVBus;
       
   375 	oUsbOtgDriver.QueueOtgVbusNotification(aVBus, aStatus);	// the kernel driver populates aPin in a kernel thread...
       
   376 	oUsbOtgDriver.CancelOtgVbusNotification();
       
   377 	// swallow the event
       
   378 	User::WaitForRequest(aStatus);
       
   379 
       
   380 	if (RUsbOtgDriver::EVbusHigh == aVBus)			// by this stage, the aVBus value is known
       
   381 		{
       
   382 		return(ETrue);
       
   383 		}
       
   384 	return(EFalse);
       
   385 	}
       
   386 
       
   387 
       
   388 TBool COtgRoot::iLoadedLdd = EFalse;
       
   389 TBool COtgRoot::iFdfActorActive = EFalse;
       
   390 RProcess COtgRoot::iFdfActorProcess;
       
   391 
       
   392 /** static */
       
   393 TBool& COtgRoot::LddLoaded()
       
   394 	{ 
       
   395 	return(iLoadedLdd);
       
   396 	}
       
   397 
       
   398 
       
   399 /** static */
       
   400 TBool COtgRoot::SetLoaded(TBool aState) 
       
   401 	{ 
       
   402 	iLoadedLdd = aState; 
       
   403 	return(LddLoaded());
       
   404 	}
       
   405 
       
   406 /** static */
       
   407 void COtgRoot::OtgEventString( RUsbOtgDriver::TOtgEvent aEvent, TBuf<MAX_DSTRLEN> &aDescription)
       
   408 	{
       
   409 
       
   410 	switch( aEvent )
       
   411 		{
       
   412 		case RUsbOtgDriver::EEventAPlugInserted:		aDescription= _L("A Plug Inserted");break;
       
   413 		case RUsbOtgDriver::EEventAPlugRemoved:			aDescription= _L("A Plug Removed");	break;
       
   414 		case RUsbOtgDriver::EEventVbusRaised:			aDescription= _L("VBUS Raised");	break;
       
   415 		case RUsbOtgDriver::EEventVbusDropped:			aDescription= _L("VBUS Dropped");	break;
       
   416 		case RUsbOtgDriver::EEventSrpReceived:			aDescription= _L("SRP Received");	break;
       
   417 		case RUsbOtgDriver::EEventSrpInitiated:			aDescription= _L("SRP Initiated");	break;
       
   418 		case RUsbOtgDriver::EEventHnpEnabled:			aDescription= _L("HNP Enabled");	break;
       
   419 		case RUsbOtgDriver::EEventHnpDisabled:			aDescription= _L("HNP Disabled");	break;
       
   420 		case RUsbOtgDriver::EEventRoleChangedToHost:	aDescription= _L("Role->Host");		break;
       
   421 		case RUsbOtgDriver::EEventRoleChangedToDevice:	aDescription= _L("Role->Device");	break;
       
   422 		case RUsbOtgDriver::EEventRoleChangedToIdle:	aDescription= _L("Role->Idle");		break;
       
   423 		
       
   424 		case RUsbOtgDriver::EEventHnpSupported : 		aDescription= _L("HNP Supported");		break;
       
   425 		case RUsbOtgDriver::EEventHnpAltSupported:		aDescription= _L("Alt-HNP Supp.");		break;
       
   426 		case RUsbOtgDriver::EEventBusConnectionBusy:	aDescription= _L("Connection Busy");	break;
       
   427 		case RUsbOtgDriver::EEventBusConnectionIdle:	aDescription= _L("Connection Idle");	break;
       
   428 		default:										aDescription= _L("Unknown");		break;
       
   429 		}
       
   430 	}
       
   431 
       
   432 /** static */
       
   433 void COtgRoot::OtgStateString( RUsbOtgDriver::TOtgState aState, TBuf<MAX_DSTRLEN> &aDescription)
       
   434 	{
       
   435 
       
   436 	switch( aState )
       
   437 		{
       
   438 		case RUsbOtgDriver::EStateReset:		aDescription= _L("Reset");			break;
       
   439 		case RUsbOtgDriver::EStateAIdle:		aDescription= _L("A-Idle");			break;
       
   440 		case RUsbOtgDriver::EStateAHost:		aDescription= _L("A-Host");			break;
       
   441 		case RUsbOtgDriver::EStateAPeripheral:	aDescription= _L("A-Peripheral");	break;
       
   442 		case RUsbOtgDriver::EStateAVbusError:   aDescription= _L("A-VBus Error");	break;
       
   443 		case RUsbOtgDriver::EStateBIdle:		aDescription= _L("B-Idle");			break;
       
   444 		case RUsbOtgDriver::EStateBPeripheral:	aDescription= _L("B-Peripheral");	break;
       
   445 		case RUsbOtgDriver::EStateBHost:		aDescription= _L("B-Host");			break;
       
   446 		default:								aDescription= _L("Unknown");		break;
       
   447 		}
       
   448 	}
       
   449 
       
   450 /** static */
       
   451 void COtgRoot::OtgMessageString( RUsbOtgDriver::TOtgMessage aMessage, TBuf<MAX_DSTRLEN> &aDescription)
       
   452 	{
       
   453 
       
   454 	switch( aMessage )
       
   455 		{
       
   456 		case RUsbOtgDriver::EEventQueueOverflow:			aDescription = _L("Event Queue Overflow");		break;
       
   457 		case RUsbOtgDriver::EStateQueueOverflow:			aDescription = _L("State Queue Overflow");		break;
       
   458 		case RUsbOtgDriver::EMessageQueueOverflow:			aDescription = _L("Message Queue Overflow");	break;
       
   459 		case RUsbOtgDriver::EMessageBadState:				aDescription = _L("Bad State");					break;
       
   460 		case RUsbOtgDriver::EMessageStackNotStarted:		aDescription = _L("Stack Not Started");			break;
       
   461 		case RUsbOtgDriver::EMessageVbusAlreadyRaised:		aDescription = _L("Vbus Already Raised");		break;
       
   462 		case RUsbOtgDriver::EMessageSrpForbidden:			aDescription = _L("SRP Forbidden");				break;
       
   463 		case RUsbOtgDriver::EMessageBusControlProblem:		aDescription = _L("Bus Control Problem");		break;
       
   464 		case RUsbOtgDriver::EMessageVbusError:				aDescription = _L("Vbus Error");				break;
       
   465 		case RUsbOtgDriver::EMessageSrpTimeout:				aDescription = _L("SRP Timeout");				break;
       
   466 		case RUsbOtgDriver::EMessageSrpActive:				aDescription = _L("SRP In Use");				break;
       
   467 		// PREQ 1305 messages
       
   468 		case RUsbOtgDriver::EMessageSrpNotPermitted:		aDescription = _L("Srp Not Permitted"); break;
       
   469 		case RUsbOtgDriver::EMessageHnpNotPermitted:		aDescription = _L("Hnp Not Permitted"); break;
       
   470 		case RUsbOtgDriver::EMessageHnpNotEnabled:			aDescription = _L("Hnp Not Enabled"); break;
       
   471 		case RUsbOtgDriver::EMessageHnpNotSuspended: 			aDescription = _L("HNP not possible, not suspended"); break;
       
   472 		case RUsbOtgDriver::EMessageVbusPowerUpNotPermitted:	aDescription = _L("Vbus PowerUp Not Permitted"); break;
       
   473 		case RUsbOtgDriver::EMessageVbusPowerUpError:			aDescription = _L("Vbus PowerUp Error"); break;
       
   474 		case RUsbOtgDriver::EMessageVbusPowerDownNotPermitted:	aDescription = _L("Vbus PowerDown Not Permitted"); break;
       
   475 		case RUsbOtgDriver::EMessageVbusClearErrorNotPermitted:	aDescription = _L("Vbus ClearError Not Permitted"); break;
       
   476 		case RUsbOtgDriver::EMessageHnpNotResponding:		aDescription = _L("Not reposnding to HNP");
       
   477 		case RUsbOtgDriver::EMessageHnpBusDrop:				aDescription = _L("VBUS drop during HNP");
       
   478 		default:												aDescription = _L("Unknown");					break;
       
   479 		}
       
   480 	}
       
   481 
       
   482 void COtgRoot::PeripheralStateString( TUint aPeripheralState, TBuf<MAX_DSTRLEN> &aDescription)
       
   483 	{
       
   484 	if(aPeripheralState & KUsbAlternateSetting)
       
   485 		{
       
   486 		aDescription = _L("Interface Alternate Setting Change");
       
   487 		}
       
   488 	else
       
   489 		{
       
   490 		switch( aPeripheralState )
       
   491 			{
       
   492 			case EUsbcDeviceStateUndefined:		aDescription = _L("Undefined");			break;
       
   493 			case EUsbcDeviceStateAttached:		aDescription = _L("Attached");			break;
       
   494 			case EUsbcDeviceStatePowered:		aDescription = _L("Powered");			break;
       
   495 			case EUsbcDeviceStateDefault:		aDescription = _L("Default");			break;
       
   496 			case EUsbcDeviceStateAddress:		aDescription = _L("Addressed");			break;
       
   497 			case EUsbcDeviceStateConfigured:	aDescription = _L("Configured");		break;
       
   498 			case EUsbcDeviceStateSuspended:		aDescription = _L("Suspended");			break;
       
   499 			case EUsbcNoState:					aDescription = _L("NoState!");			break;
       
   500 			default:							aDescription = _L("Unknown");			break;
       
   501 			}
       
   502 		}
       
   503 	}
       
   504 	
       
   505 void COtgRoot::AConnectionIdleString(RUsbOtgDriver::TOtgConnection aAConnectionIdle, TBuf<MAX_DSTRLEN> &aDescription)
       
   506 	{
       
   507 	switch( aAConnectionIdle )
       
   508 		{
       
   509 		case RUsbOtgDriver::EConnectionBusy:		aDescription = _L("Busy");			break;
       
   510 		case RUsbOtgDriver::EConnectionIdle:		aDescription = _L("Idle");			break;
       
   511 		case RUsbOtgDriver::EConnectionUnknown:		aDescription = _L("Unknown");		break;
       
   512 		default:									aDescription = _L("Not recognised");break;
       
   513 		}
       
   514 	}
       
   515 
       
   516 TInt COtgRoot::otgActivateFdfActor()
       
   517 	{
       
   518 	if(iFdfActorActive)
       
   519 		{
       
   520 		RDebug::Print(_L("FdfActor already exists!"));
       
   521 		return KErrAlreadyExists;
       
   522 		}
       
   523 		
       
   524 	const TUid KFdfSvrUid={0x10282B48};
       
   525 	const TUidType fdfActorUid(KNullUid, KNullUid, KFdfSvrUid);
       
   526 
       
   527 	RDebug::Print(_L("About to activate FDF Actor"));
       
   528 
       
   529 //	RProcess fdfActorProcess;
       
   530 	TInt err = iFdfActorProcess.Create(_L("t_otgdi_fdfactor.exe"), KNullDesC, fdfActorUid);
       
   531 	
       
   532 	if (err != KErrNone)
       
   533 		{
       
   534 		RDebug::Print(_L("Failed to create FDF Actor, err=%d"),err);
       
   535 		iFdfActorProcess.Close();
       
   536 		return err;
       
   537 		}
       
   538 
       
   539 	TRequestStatus stat;
       
   540 	iFdfActorProcess.Rendezvous(stat);
       
   541 	
       
   542 	if (stat!=KRequestPending)
       
   543 		{
       
   544 		RDebug::Print(_L("Failed to commence rendezvous, err=%d"),stat.Int());
       
   545 		iFdfActorProcess.Kill(0);		// abort startup
       
   546 		iFdfActorProcess.Close();
       
   547 		return stat.Int();
       
   548 		}
       
   549 	else
       
   550 		{
       
   551 		iFdfActorProcess.Resume();	// logon OK - start the server
       
   552 		}
       
   553 
       
   554 	User::WaitForRequest(stat);		// wait for start or death
       
   555 	if(stat.Int()!=KErrNone)
       
   556 		{
       
   557 		//	Wasn't KErrNone, which means that the FDFActor didn't successfully
       
   558 		//	start up. We shouldn't proceed with the test we're in.
       
   559 		RDebug::Print(_L("Failed to activate FDF Actor, err=%d"),stat.Int());
       
   560 		iFdfActorProcess.Close();
       
   561 		return stat.Int();
       
   562 		}
       
   563 	
       
   564 	//	We rendezvoused(?) with the FDFActor OK, so it is going to suspend
       
   565 	//	any devices it sees being attached, and will shut itself down
       
   566 	//	when this process signals its Rendezvous (at the end of the test)...
       
   567 	RDebug::Print(_L("Activated FDF Actor"));
       
   568 	iFdfActorActive = ETrue;
       
   569 
       
   570 	return KErrNone;
       
   571 	}
       
   572 
       
   573 void COtgRoot::otgDeactivateFdfActor()
       
   574 	{
       
   575 	if(!iFdfActorActive)
       
   576 		{
       
   577 		RDebug::Print(_L("FdfActor is not running!"));
       
   578 		return;
       
   579 		}
       
   580 
       
   581 	//	If iFdfActorActive is set, the FDF Actor should be waiting to
       
   582 	//	rendezvous with us before it shuts down...
       
   583 	//	First of all, logon to wait for it to close down properly
       
   584 	TRequestStatus waitForCloseStat;
       
   585 	iFdfActorProcess.Logon(waitForCloseStat);
       
   586 	
       
   587 	//	Now, trigger the FDF Actor to close down
       
   588 
       
   589 	RProcess::Rendezvous(KErrNone);
       
   590 	
       
   591 	//	...and wait for it to go away.
       
   592 	User::WaitForRequest(waitForCloseStat);
       
   593 	test.Printf(_L("T_OTGDI confirms FDF Actor has gone away %d\n"), waitForCloseStat.Int());
       
   594 	
       
   595 	//	Now close our handle, and record that the process is no more...
       
   596 	iFdfActorProcess.Close();
       
   597 	iFdfActorActive = EFalse;
       
   598 	}
       
   599 	
       
   600 /** Commonly used step to unload the USB Client Driver
       
   601 * @return ETrue if the ldd unloaded sucessfully
       
   602 */
       
   603 TBool COtgRoot::StepUnloadClient()
       
   604 	{
       
   605 	test.Printf(_L("Unload USBCC Client\n"));
       
   606 
       
   607 	TInt err;
       
   608 
       
   609 	// Close the Client
       
   610 
       
   611 	test.Printf(_L("..Close\n"));
       
   612 	oUsbcClient.Close();
       
   613 
       
   614 	// Unload the LDD - note the name is *not* the same as for loading
       
   615 
       
   616 	test.Printf(_L("..Unload\n"));
       
   617 	err = User::FreeLogicalDevice( KUsbDeviceName );
       
   618 	if (err != KErrNone)
       
   619 		{
       
   620 		AssertionFailed2(KErrAbort, _L("Client Unload Fail "), err);
       
   621 		return (EFalse);
       
   622 		}
       
   623 
       
   624 
       
   625 	return(ETrue);
       
   626 	}
       
   627 
       
   628 
       
   629 /** Commonly used step to load the USB Client Driver and set up
       
   630  *	a 'useful' default device descriptor set
       
   631  * @return ETrue if the ldd loaded sucessfully
       
   632  */
       
   633 TBool COtgRoot::StepLoadClient(TUint16 aPID, 
       
   634 								TBool aEnableHNP/*=ETrue*/, 
       
   635 								TBool aEnableSRP/*=ETrue*/)
       
   636 	{
       
   637 	test.Printf(_L("Load USBCC Client 0x%04x\n"),aPID);
       
   638 
       
   639 	TInt err;
       
   640 
       
   641 	// The incoming PID is expected to have a form of 0x0TTT or 0xFTTT
       
   642 	// where 'TTT' is the test number: if the lead is 0xF000 we now 
       
   643 	// overlay an 'A' or a 'B' depending on the default role
       
   644 	
       
   645 	if (   ( ( aPID & 0xF000 ) != 0xF000 )
       
   646 		&& ( ( aPID & 0xF000 ) != 0x0000 )
       
   647 	   )
       
   648 		{
       
   649 		AssertionFailed(KErrAbort, _L("Bad default PID"));
       
   650 		}
       
   651 		
       
   652 	if ( aPID & 0xF000 )
       
   653 		{
       
   654 		aPID &= 0x0FFF;
       
   655 		
       
   656 		if ( gTestRoleMaster )
       
   657 			{
       
   658 			// this is the 'B' device
       
   659 			aPID |= 0xB000;
       
   660 			}
       
   661 		else
       
   662 			{
       
   663 			// this is the 'A' device
       
   664 			aPID |= 0xA000;
       
   665 			}
       
   666 		}
       
   667 	
       
   668 	// Load the LDD - note the name is *not* the same as for unload
       
   669 
       
   670 	test.Printf(_L("..Load LDD\n"));
       
   671 	err = User::LoadLogicalDevice( KUsbcLddFileName );
       
   672 	if ((err != KErrNone) && (err !=KErrAlreadyExists))
       
   673 		{
       
   674 		AssertionFailed2(KErrAbort, _L("Client Load Fail "), err);
       
   675 		return (EFalse);
       
   676 		}
       
   677 
       
   678 	// Open the Client
       
   679 
       
   680 	test.Printf(_L("..Open LDD\n"));
       
   681 	err = oUsbcClient.Open(0);
       
   682 	if (err != KErrNone)
       
   683 		{
       
   684 		AssertionFailed2(KErrAbort, _L("Client Open Fail "), err);
       
   685 		return (EFalse);
       
   686 		}
       
   687 
       
   688 	// Set up descriptors
       
   689 	
       
   690 	test.Printf(_L("..Setup Descriptors\n"));
       
   691 
       
   692 	// the OTG descriptor
       
   693 	TBuf8<KUsbDescSize_Otg> theOtgDescriptor;
       
   694 	err = oUsbcClient.GetOtgDescriptor(theOtgDescriptor);
       
   695 	if (err != KErrNone)
       
   696 		{
       
   697 		AssertionFailed2(KErrAbort, _L("OTG GetDes Fail "), err);
       
   698 		return (EFalse);
       
   699 		}
       
   700 	// modify OTG descriptor based on parameters passed
       
   701 	if (aEnableHNP)
       
   702 		aEnableSRP=ETrue;	// Keep the device Legal according to OTG spec 6.4.2
       
   703 	/*Attribute Fields
       
   704 	  D7…2: Reserved (reset to zero)
       
   705 	  D1: HNP support
       
   706 	  D0: SRP support*/
       
   707 	TUint8 aByte = theOtgDescriptor[2];
       
   708 		aByte &= (~0x03);
       
   709 		aByte |= (aEnableSRP? 1 : 0); 
       
   710 		aByte |= (aEnableHNP? 2 : 0); 
       
   711 	test.Printf(_L("..Change OTG 0x%02X->0x%02X\n"), theOtgDescriptor[2], aByte);
       
   712 	theOtgDescriptor[2] = aByte;
       
   713 	
       
   714 	err = oUsbcClient.SetOtgDescriptor(theOtgDescriptor);
       
   715 	if (err != KErrNone)
       
   716 		{
       
   717 		AssertionFailed2(KErrAbort, _L("OTG SetDes Fail "), err);
       
   718 		return (EFalse);
       
   719 		}
       
   720 	
       
   721 	//
       
   722 
       
   723 	TUsbDeviceCaps d_caps;
       
   724 	err = oUsbcClient.DeviceCaps(d_caps);
       
   725 	TBool softwareConnect;
       
   726 
       
   727 	if (err != KErrNone)
       
   728 		{
       
   729 		AssertionFailed2(KErrAbort, _L("Client DevCaps Fail "), err);
       
   730 		return (EFalse);
       
   731 		}
       
   732 
       
   733 	const TInt n = d_caps().iTotalEndpoints;
       
   734 
       
   735 	softwareConnect = d_caps().iConnect;
       
   736 	test.Printf(_L("..SoftwareConnect = %d\n"),softwareConnect);
       
   737 
       
   738 	if (n < 2)
       
   739 		{
       
   740 		AssertionFailed2(KErrAbort, _L("Client Endpoints Fail "), err);
       
   741 		return (EFalse);
       
   742 		}
       
   743 
       
   744 	// Endpoints
       
   745 	TUsbcEndpointData data[KUsbcMaxEndpoints];
       
   746 	TPtr8 dataptr(reinterpret_cast<TUint8*>(data), sizeof(data), sizeof(data));
       
   747 	err = oUsbcClient.EndpointCaps(dataptr);
       
   748 	if (err != KErrNone)
       
   749 		{
       
   750 		AssertionFailed2(KErrAbort, _L("Client EpCaps Fail "), err);
       
   751 		return (EFalse);
       
   752 		}
       
   753 
       
   754 	// Set up the active interface
       
   755 	TUsbcInterfaceInfoBuf ifc;
       
   756 	TInt ep_found = 0;
       
   757 	TBool foundBulkIN = EFalse;
       
   758 	TBool foundBulkOUT = EFalse;
       
   759 	for (TInt i = 0; i < n; i++)
       
   760 		{
       
   761 		const TUsbcEndpointCaps* const caps = &data[i].iCaps;
       
   762 		const TInt mps = caps->MaxPacketSize();
       
   763 		if (!foundBulkIN &&
       
   764 			(caps->iTypesAndDir & (KUsbEpTypeBulk | KUsbEpDirIn)) ==
       
   765 			(KUsbEpTypeBulk | KUsbEpDirIn))
       
   766 			{
       
   767 			if (!(mps == 64 || mps == 512))
       
   768 				{
       
   769 				}
       
   770 			// EEndpoint1 is going to be our Tx (IN) endpoint
       
   771 			ifc().iEndpointData[0].iType = KUsbEpTypeBulk;
       
   772 			ifc().iEndpointData[0].iDir	 = KUsbEpDirIn;
       
   773 			ifc().iEndpointData[0].iSize = mps;
       
   774 			foundBulkIN = ETrue;
       
   775 			if (++ep_found == 2)
       
   776 				break;
       
   777 			}
       
   778 		else if (!foundBulkOUT &&
       
   779 			(caps->iTypesAndDir & (KUsbEpTypeBulk | KUsbEpDirOut)) ==
       
   780 			(KUsbEpTypeBulk | KUsbEpDirOut))
       
   781 			{
       
   782 			if (!(mps == 64 || mps == 512))
       
   783 				{
       
   784 				}
       
   785 			// EEndpoint2 is going to be our Rx (OUT) endpoint
       
   786 			ifc().iEndpointData[1].iType = KUsbEpTypeBulk;
       
   787 			ifc().iEndpointData[1].iDir	 = KUsbEpDirOut;
       
   788 			ifc().iEndpointData[1].iSize = mps;
       
   789 			foundBulkOUT = ETrue;
       
   790 			if (++ep_found == 2)
       
   791 				break;
       
   792 			}
       
   793 		}
       
   794 	if (ep_found != 2)
       
   795 		{
       
   796 		AssertionFailed2(KErrAbort, _L("Client EpFound Fail "), err);
       
   797 		return (EFalse);
       
   798 		}
       
   799 
       
   800 	_LIT16(ifcname, "T_OTGDI Test Interface (Default Setting 0)");
       
   801 	ifc().iString = const_cast<TDesC16*>(&ifcname);
       
   802 	ifc().iTotalEndpointsUsed = 2;
       
   803 	ifc().iClass.iClassNum	  = 0xff;						// vendor-specific
       
   804 	ifc().iClass.iSubClassNum = 0xff;						// vendor-specific
       
   805 	ifc().iClass.iProtocolNum = 0xff;						// vendor-specific
       
   806 
       
   807 	err = oUsbcClient.SetInterface(0, ifc, (EUsbcBandwidthOUTDefault | EUsbcBandwidthINDefault));
       
   808 
       
   809 	if( err != KErrNone )
       
   810 		{
       
   811 		AssertionFailed2(KErrAbort, _L("Client SetInt Fail "), err);
       
   812 		return (EFalse);
       
   813 		}
       
   814 	
       
   815 	// Set the revised PID
       
   816 	
       
   817 	TBuf8<KUsbDescSize_Device> theDeviceDescriptor;
       
   818 	err = oUsbcClient.GetDeviceDescriptor(theDeviceDescriptor);
       
   819 	if (err != KErrNone)
       
   820 		{
       
   821 		AssertionFailed2(KErrAbort, _L("Client GetDes Fail "), err);
       
   822 		return (EFalse);
       
   823 		}
       
   824 
       
   825 	TUint16 oldPID = ( theDeviceDescriptor[10] )
       
   826 		           + ( theDeviceDescriptor[11] << 8 );
       
   827 
       
   828 	theDeviceDescriptor[10] = ( aPID & 0x00FF );
       
   829 	theDeviceDescriptor[11] = ( aPID & 0xFF00 ) >> 8;
       
   830 
       
   831 	test.Printf(_L("..Change PID 0x%04X->0x%04X\n"), oldPID, aPID);
       
   832 
       
   833 	err = oUsbcClient.SetDeviceDescriptor(theDeviceDescriptor);
       
   834 	if (err != KErrNone)
       
   835 		{
       
   836 		AssertionFailed2(KErrAbort, _L("Client SetDes Fail "), err);
       
   837 		return (EFalse);
       
   838 		}
       
   839 
       
   840 
       
   841 	// Power Up UDC - KErrNotReady is expected
       
   842 
       
   843 	test.Printf(_L("..Power Up UDC\n"));
       
   844 
       
   845 	err = oUsbcClient.PowerUpUdc();
       
   846 	if( err != KErrNotReady )
       
   847 		{
       
   848 		AssertionFailed2(KErrAbort, _L("PowerUp UDC Fail "), err);
       
   849 		return (EFalse);
       
   850 		}
       
   851 
       
   852 	// Connect to Host
       
   853 
       
   854 	test.Printf(_L("..Connect to Host\n"));
       
   855 
       
   856 	err = oUsbcClient.DeviceConnectToHost();
       
   857 	if( err != KErrNone )
       
   858 		{
       
   859 		AssertionFailed2(KErrAbort, _L("Host Connect Fail "), err);
       
   860 		return (EFalse);
       
   861 		}
       
   862 
       
   863 	// Default no-problem return
       
   864 
       
   865 	return(ETrue);
       
   866 	}
       
   867 
       
   868 
       
   869 /** Commonly used steps to control D+ connect/disconnect
       
   870  *  the device to/from the host
       
   871  */
       
   872 TBool COtgRoot::StepDisconnect()
       
   873 	{
       
   874 	test.Printf(_L("Disconnect from Host\n"));
       
   875 
       
   876 	TInt err;
       
   877 	
       
   878 	err = oUsbcClient.DeviceDisconnectFromHost();
       
   879 	if( err != KErrNone )
       
   880 		{
       
   881 		AssertionFailed2(KErrAbort, _L("Host Disconnect Fail "), err);
       
   882 		return (EFalse);
       
   883 		}
       
   884 
       
   885 	// Default no-problem return
       
   886 
       
   887 	return(ETrue);
       
   888 	}
       
   889 
       
   890 TBool COtgRoot::StepConnect()
       
   891 	{
       
   892 	test.Printf(_L("Connect to Host\n"));
       
   893 
       
   894 	TInt err;
       
   895 	
       
   896 	err = oUsbcClient.DeviceConnectToHost();
       
   897 	if( err != KErrNone )
       
   898 		{
       
   899 		AssertionFailed2(KErrAbort, _L("Host Connect Fail "), err);
       
   900 		return (EFalse);
       
   901 		}
       
   902 
       
   903 	// Default no-problem return
       
   904 
       
   905 	return(ETrue);
       
   906 	}
       
   907 
       
   908 
       
   909 /** Commonly used step to load the USB Client Driver and set up
       
   910  *	a High-Speed electrical test VID/PID pair
       
   911  * @return ETrue if the ldd loaded sucessfully
       
   912  */
       
   913 TBool COtgRoot::StepChangeVidPid(TUint16 aVID, TUint16 aPID)
       
   914 
       
   915 	{
       
   916 	test.Printf(_L("Load USBCC HS Test Client 0x%04x/0x%04x\n"),aVID,aPID);
       
   917 
       
   918 	TInt err;
       
   919 
       
   920 	// Set the revised VID/PID pair
       
   921 	
       
   922 	TBuf8<KUsbDescSize_Device> theDeviceDescriptor;
       
   923 	err = oUsbcClient.GetDeviceDescriptor(theDeviceDescriptor);
       
   924 	if (err != KErrNone)
       
   925 		{
       
   926 		AssertionFailed2(KErrAbort, _L("Client GetDes Fail "), err);
       
   927 		return (EFalse);
       
   928 		}
       
   929 
       
   930 	TUint16 oldVID = ( theDeviceDescriptor[8] )
       
   931 		           + ( theDeviceDescriptor[9] << 8 );
       
   932 
       
   933 	theDeviceDescriptor[8] = ( aVID & 0x00FF );
       
   934 	theDeviceDescriptor[9] = ( aVID & 0xFF00 ) >> 8;
       
   935 
       
   936 	test.Printf(_L("..Change VID 0x%04X->0x%04X\n"), oldVID, aVID);
       
   937 
       
   938 	TUint16 oldPID = ( theDeviceDescriptor[10] )
       
   939 		           + ( theDeviceDescriptor[11] << 8 );
       
   940 
       
   941 	theDeviceDescriptor[10] = ( aPID & 0x00FF );
       
   942 	theDeviceDescriptor[11] = ( aPID & 0xFF00 ) >> 8;
       
   943 
       
   944 	test.Printf(_L("..Change PID 0x%04X->0x%04X\n"), oldPID, aPID);
       
   945 
       
   946 	err = oUsbcClient.SetDeviceDescriptor(theDeviceDescriptor);
       
   947 	if (err != KErrNone)
       
   948 		{
       
   949 		AssertionFailed2(KErrAbort, _L("Client SetDes Fail "), err);
       
   950 		return (EFalse);
       
   951 		}
       
   952 
       
   953 	// Default no-problem return
       
   954 
       
   955 	return(ETrue);
       
   956 	}
       
   957 
       
   958 
       
   959 /** Commonly used step to set a flag that will cause the
       
   960     OPT test mode to be activated when the stacks are
       
   961 	started 
       
   962 */
       
   963 void COtgRoot::StepSetOptActive() 
       
   964 	{ 
       
   965 	iOptActive = ETrue;
       
   966 	}
       
   967 
       
   968 
       
   969 /** Commonly used step to unload the ldd and shut it down
       
   970 *@return ETrue if the ldd unloaded sucessfully
       
   971 */
       
   972 TBool COtgRoot::StepUnloadLDD()
       
   973 	{ 
       
   974 	test.Printf(_L("Unload otg LDD (implicit Stop() + Close()) \n"));
       
   975 	
       
   976 	LOG_VERBOSE1(_L("  Stop OTG+Host Stack\n"));
       
   977 	otgStopStacks();
       
   978 	otgClose();
       
   979 	
       
   980 	LOG_VERBOSE1(_L("  Unload\n"));
       
   981 	otgUnloadLdd();
       
   982 	
       
   983 	iOptActive = EFalse; // retain the OTGDI behavour to clears this flag when client shuts 
       
   984 	if (LddLoaded())
       
   985 		return(EFalse);
       
   986 	return(ETrue);
       
   987 	}
       
   988 	
       
   989 
       
   990 /** StepLoadLDD - utility method : load the LDD, open it and init the stacks
       
   991  a commonly used test step */
       
   992 TBool COtgRoot::StepLoadLDD()
       
   993 	{
       
   994 	TInt err;	
       
   995 
       
   996 	LOG_VERBOSE1(_L("Load otg LDD\n"));
       
   997 	err = otgLoadLdd();
       
   998 	if (err != KErrNone)
       
   999 		{
       
  1000 		AssertionFailed2(KErrAbort, _L("Loading LDD failed "), err);
       
  1001 		return (EFalse);
       
  1002 		}
       
  1003 		
       
  1004 	LOG_VERBOSE1(_L("Open the LDD session\n"));
       
  1005 	err = otgOpen();
       
  1006 	if (err != KErrNone)
       
  1007 		{
       
  1008 		AssertionFailed2(KErrAbort, _L("Open LDD session failed "), err);
       
  1009 		return (EFalse);
       
  1010 		}
       
  1011 
       
  1012 	if ( iOptActive )
       
  1013 		{
       
  1014 		test.Printf(_L("Activate OPT Test Mode\n"));
       
  1015 		err = otgActivateOptTestMode();
       
  1016 		if (err != KErrNone)
       
  1017 			{
       
  1018 			AssertionFailed2(KErrAbort, _L("OPT Activate failed "), err);
       
  1019 			return (EFalse);
       
  1020 			}	
       
  1021 		}
       
  1022 
       
  1023 	test.Printf(_L("Start OTG+Host Stack\n"));
       
  1024 	err = otgStartStacks();
       
  1025 	if (err != KErrNone)
       
  1026 		{
       
  1027 		AssertionFailed2(KErrAbort, _L("Start stack failed "), err);
       
  1028 		return (EFalse);
       
  1029 		}	
       
  1030 		
       
  1031 	//	DS - Temporarily adding .1 second delay in here to beat the race
       
  1032 	//	condition to be fixed as part of third part USB HOST/OTG stack issue 60761
       
  1033 	User::After(100000);
       
  1034 		
       
  1035 	return(ETrue);
       
  1036 	}
       
  1037 
       
  1038 void COtgRoot::SetMaxPowerToL(TUint16 aVal)
       
  1039 	{
       
  1040 
       
  1041 	TBuf8<KUsbDescSize_Config> buf;
       
  1042 	
       
  1043 	oUsbcClient.GetConfigurationDescriptor(buf);
       
  1044 	
       
  1045 	aVal %= 500;
       
  1046 	
       
  1047 	buf[8] = (TUint8)(aVal / 2);
       
  1048 	
       
  1049 	oUsbcClient.SetConfigurationDescriptor(buf);
       
  1050 	
       
  1051 	}
       
  1052 
       
  1053 void COtgRoot::GetMaxPower(TUint16& aVal)
       
  1054 	{
       
  1055 	TBuf8<KUsbDescSize_Config> buf;
       
  1056 	
       
  1057 	oUsbcClient.GetConfigurationDescriptor(buf);
       
  1058 	
       
  1059 	aVal = buf[8] * 2;
       
  1060 	}
       
  1061 
       
  1062