os/security/cryptoplugins/cryptospiplugins/test/h4drv/crypto_h4/cryptoh4.cpp
author sl@SLION-WIN7.fritz.box
Fri, 15 Jun 2012 03:10:57 +0200
changeset 0 bde4ae8d615e
permissions -rw-r--r--
First public contribution.
sl@0
     1
/*
sl@0
     2
* Copyright (c) 2007-2009 Nokia Corporation and/or its subsidiary(-ies).
sl@0
     3
* All rights reserved.
sl@0
     4
* This component and the accompanying materials are made available
sl@0
     5
* under the terms of the License "Eclipse Public License v1.0"
sl@0
     6
* which accompanies this distribution, and is available
sl@0
     7
* at the URL "http://www.eclipse.org/legal/epl-v10.html".
sl@0
     8
*
sl@0
     9
* Initial Contributors:
sl@0
    10
* Nokia Corporation - initial contribution.
sl@0
    11
*
sl@0
    12
* Contributors:
sl@0
    13
*
sl@0
    14
* Description: 
sl@0
    15
*
sl@0
    16
*/
sl@0
    17
sl@0
    18
sl@0
    19
/**
sl@0
    20
 @file
sl@0
    21
 @internalComponent
sl@0
    22
 @released
sl@0
    23
*/
sl@0
    24
#include <kernel/kern_priv.h>
sl@0
    25
#include "cryptodriver.h"
sl@0
    26
#ifdef __MARM__
sl@0
    27
#include <omap_hrp/assp/shared/omap_reg.h>
sl@0
    28
#include <omap_hrp/assp/shared/omap_interrupt.h>
sl@0
    29
#endif
sl@0
    30
#include "cryptoh4.h"
sl@0
    31
#include "cryptoh4rng.h"
sl@0
    32
#include "cryptoh4aes.h"
sl@0
    33
sl@0
    34
DECLARE_STANDARD_PDD()
sl@0
    35
    {
sl@0
    36
    return new DCryptoPddFactory;
sl@0
    37
    }
sl@0
    38
sl@0
    39
// Name for PDD, must match LDD name with a '.' and distinguishing name appended
sl@0
    40
_LIT(KCryptoH4PddName,"crypto.h4");
sl@0
    41
sl@0
    42
DCryptoPddFactory::DCryptoPddFactory()
sl@0
    43
	// : iDfcQueInitialised(EFalse)
sl@0
    44
    {
sl@0
    45
	TRACE_FUNCTION("DCryptoPddFactory");
sl@0
    46
	// Set version number for this device
sl@0
    47
	//
sl@0
    48
	// We re-use the version number of the LDD which effectively
sl@0
    49
	// specifies the version of both the external RCryptoDriver
sl@0
    50
	// interface to the LDD and the internal LDD to PDD interface.
sl@0
    51
    iVersion=RCryptoDriver::VersionRequired();
sl@0
    52
    }
sl@0
    53
sl@0
    54
void DCryptoPddFactory::DeleteDfcQFunc(TAny *p)
sl@0
    55
	{
sl@0
    56
	TRACE_FUNCTION("DeleteDfcQFunc");
sl@0
    57
	// We do not need to delete the TDfc because it is a static
sl@0
    58
	// Delete the DFC queue.
sl@0
    59
	TDfcQue *q = reinterpret_cast<TDfcQue *>(p);
sl@0
    60
	delete q;
sl@0
    61
	// Delete our thread
sl@0
    62
	Kern::Exit(KErrNone);
sl@0
    63
	}
sl@0
    64
sl@0
    65
TDfc deleteDfcQDfc(0, 0, 0); // Dummy create, will be overwritten later
sl@0
    66
sl@0
    67
DCryptoPddFactory::~DCryptoPddFactory()
sl@0
    68
	{
sl@0
    69
	TRACE_FUNCTION("~DCryptoPddFactory");
sl@0
    70
	if(iDfcQueInitialised)
sl@0
    71
		{
sl@0
    72
		// Need to shutdown our DFC queue.
sl@0
    73
		// 
sl@0
    74
		// In theory the DFC could run after we have returned and the
sl@0
    75
		// framework has deleting everything...
sl@0
    76
		// 
sl@0
    77
		// But the DLL will NOT be unloaded until the next time the
sl@0
    78
		// IDLE task runs, so we know the DFC will reach completion
sl@0
    79
		// before then (but it most not use any of our members....
sl@0
    80
		//
sl@0
    81
		// For the same reason we should use a TDfc which is not
sl@0
    82
		// inside this object.
sl@0
    83
		deleteDfcQDfc = TDfc(DeleteDfcQFunc, iDfcQue, iDfcQue, 0);
sl@0
    84
		deleteDfcQDfc.Enque();
sl@0
    85
		iDfcQueInitialised = EFalse;
sl@0
    86
		}
sl@0
    87
	}
sl@0
    88
sl@0
    89
sl@0
    90
sl@0
    91
sl@0
    92
// Missing h/w registers & masks
sl@0
    93
const TUint KHtRngSysResetStatus = KBit0;
sl@0
    94
sl@0
    95
/**
sl@0
    96
  Second stage constructor for DPhysicalDevice derived objects.
sl@0
    97
  This must at least set a name for the driver object.
sl@0
    98
sl@0
    99
  @return KErrNone or standard error code.
sl@0
   100
*/
sl@0
   101
_LIT(KCryptoHwQueueName, "CryptoHwDfcQue");
sl@0
   102
TInt DCryptoPddFactory::Install()
sl@0
   103
    {
sl@0
   104
	TRACE_FUNCTION("Install");
sl@0
   105
	// 28 is the recommended setting for a low priority kernel driver
sl@0
   106
	// (I can't find an enum for this).
sl@0
   107
	TInt r = Kern::DfcQCreate(iDfcQue, 28, &KCryptoHwQueueName);
sl@0
   108
	if(r != KErrNone)
sl@0
   109
		{
sl@0
   110
		return r;
sl@0
   111
		}
sl@0
   112
	iDfcQueInitialised = ETrue;
sl@0
   113
sl@0
   114
	// Reset h/w
sl@0
   115
	Kern::Printf("DCryptoPddFactory::Install - Reseting h/w");
sl@0
   116
#ifdef __MARM__
sl@0
   117
	// RNG
sl@0
   118
	// The RNG has no state worth reseting - a reset would delay the
sl@0
   119
	// availabilty of a new random number (and maybe reduce its
sl@0
   120
	// quality).
sl@0
   121
	//	TOmap::SetRegister32(KHwBaseRngReg + KHoRng_Mask, KHtRngMaskSoftReset);
sl@0
   122
sl@0
   123
	// DES/3DES
sl@0
   124
	TOmap::SetRegister32(KHwBaseDes3DesReg + KHoDES_MASK, KHtDesMaskSoftReset);
sl@0
   125
sl@0
   126
	// SHA1/MD5
sl@0
   127
	TOmap::SetRegister32(KHwBaseSha1Md5Reg + KHoSHA_MASK, KHtShaMaskSoftReset);
sl@0
   128
sl@0
   129
	// AES
sl@0
   130
	TOmap::SetRegister32(KHwBaseAesReg + KHoAES_MASK, KHtAesMaskSoftReset);
sl@0
   131
sl@0
   132
	// PKA
sl@0
   133
	TOmap::SetRegister32(KHwBasePkaReg + KHoPKA_MASK, KHtPkaMaskSoftReset);
sl@0
   134
	
sl@0
   135
	// Make sure all cypto h/w (rng/des/sha1/aes/pka) is out of reset
sl@0
   136
	while(((TOmap::Register32(KHwBaseRngReg + KHoRng_SysStatus) & KHtRngSysResetStatus) == 0) ||
sl@0
   137
		  ((TOmap::Register32(KHwBaseDes3DesReg + KHoDES_SYSSTATUS) & KHtDesSysResetStatus) == 0) ||
sl@0
   138
		  ((TOmap::Register32(KHwBaseSha1Md5Reg + KHoSHA_SYSSTATUS) & KHtShaSysResetStatus) == 0) ||
sl@0
   139
		  ((TOmap::Register32(KHwBaseAesReg + KHoAES_SYSSTATUS) & KHtAesSysResetStatus) == 0) ||
sl@0
   140
		  ((TOmap::Register32(KHwBasePkaReg + KHoPKA_SYSSTATUS) & KHtPkaSysResetStatus) == 0))
sl@0
   141
		{
sl@0
   142
		Kern::Printf("DCryptoPddFactory::Install - waiting for h/w");
sl@0
   143
		}
sl@0
   144
sl@0
   145
#endif
sl@0
   146
	//	Kern::Printf("DCryptoPddFactory::Install - h/w reset complete");
sl@0
   147
sl@0
   148
    return SetName(&KCryptoH4PddName);
sl@0
   149
    }
sl@0
   150
sl@0
   151
sl@0
   152
sl@0
   153
sl@0
   154
/**
sl@0
   155
   Returns the drivers capabilities.
sl@0
   156
sl@0
   157
   This is required by the Symbian OS device driver framework.
sl@0
   158
   
sl@0
   159
   It can NOT be used by the LDD factory GetCaps function because that
sl@0
   160
   class does not contain a link tous (and we might not be loaded)....
sl@0
   161
sl@0
   162
   NOT USED IN THIS DRIVER.
sl@0
   163
   
sl@0
   164
   @param aDes Descriptor to write capabilities information into
sl@0
   165
*/
sl@0
   166
void DCryptoPddFactory::GetCaps(TDes8& /* aDes */) const
sl@0
   167
	{
sl@0
   168
	TRACE_FUNCTION("GetCaps");
sl@0
   169
	}
sl@0
   170
sl@0
   171
sl@0
   172
/**
sl@0
   173
  Called by the kernel's device driver framework to create a Physical Channel.
sl@0
   174
  This is called in the context of the user thread (client) which requested the creation of a Logical Channel
sl@0
   175
  (E.g. through a call to RBusLogicalChannel::DoCreate)
sl@0
   176
  The thread is in a critical section.
sl@0
   177
sl@0
   178
  @param aChannel Set to point to the created Physical Channel
sl@0
   179
  @param aUnit The unit argument supplied by the client to RBusLogicalChannel::DoCreate
sl@0
   180
  @param aInfo The info argument supplied by the client to RBusLogicalChannel::DoCreate
sl@0
   181
  @param aVer The version number of the Logical Channel which will use this Physical Channel 
sl@0
   182
sl@0
   183
  @return KErrNone or standard error code.
sl@0
   184
*/
sl@0
   185
TInt DCryptoPddFactory::Create(DBase*& aChannel, TInt aUnit, const TDesC8* aInfo, const TVersion& aVer)
sl@0
   186
    {
sl@0
   187
	TRACE_FUNCTION("Create");
sl@0
   188
    // Ignore the parameters we aren't interested in...
sl@0
   189
    (void)aUnit;
sl@0
   190
    (void)aInfo;
sl@0
   191
    (void)aVer;
sl@0
   192
sl@0
   193
    // Create a new physical channel
sl@0
   194
DCryptoH4Chan* device=new DCryptoH4Chan(*this);
sl@0
   195
    aChannel=device;
sl@0
   196
    if (!device)
sl@0
   197
        return KErrNoMemory;
sl@0
   198
    return device->DoCreate();
sl@0
   199
    }
sl@0
   200
sl@0
   201
/**
sl@0
   202
  Called by the kernel's device driver framework to check if this PDD is suitable for use with a Logical Channel.
sl@0
   203
  This is called in the context of the user thread (client) which requested the creation of a Logical Channel
sl@0
   204
  (E.g. through a call to RBusLogicalChannel::DoCreate)
sl@0
   205
  The thread is in a critical section.
sl@0
   206
sl@0
   207
  @param aUnit The unit argument supplied by the client to RBusLogicalChannel::DoCreate
sl@0
   208
  @param aInfo The info argument supplied by the client to RBusLogicalChannel::DoCreate
sl@0
   209
  @param aVer The version number of the Logical Channel which will use this Physical Channel 
sl@0
   210
sl@0
   211
  @return KErrNone or standard error code.
sl@0
   212
*/
sl@0
   213
TInt DCryptoPddFactory::Validate(TInt aUnit, const TDesC8* aInfo, const TVersion& aVer)
sl@0
   214
    {
sl@0
   215
	TRACE_FUNCTION("Validate");
sl@0
   216
    // Check version numbers
sl@0
   217
    if ((!Kern::QueryVersionSupported(iVersion,aVer)) || (!Kern::QueryVersionSupported(aVer,TVersion(EMinimumLddMajorVersion,EMinimumLddMinorVersion,EMinimumLddBuild))))
sl@0
   218
        return KErrNotSupported;
sl@0
   219
sl@0
   220
    // We don't support units
sl@0
   221
    if (aUnit != -1)
sl@0
   222
        return KErrNotSupported;
sl@0
   223
sl@0
   224
    // Ignore extra info, (this could be used for validation purposes)
sl@0
   225
    // Note, aInfo is a pointer to a descriptor in user memory, therefore safe methods should
sl@0
   226
    // be used for reading its contents. E.g. using Kern::KUDesGet()
sl@0
   227
    (void)aInfo;
sl@0
   228
sl@0
   229
    // OK
sl@0
   230
    return KErrNone;
sl@0
   231
    }
sl@0
   232
sl@0
   233
sl@0
   234
TDfcQue *DCryptoPddFactory::DfcQue()
sl@0
   235
	{
sl@0
   236
	TRACE_FUNCTION("DfcQue");
sl@0
   237
	return iDfcQue;
sl@0
   238
	}
sl@0
   239
sl@0
   240
sl@0
   241
sl@0
   242
//
sl@0
   243
// DCryptoH4Chan
sl@0
   244
//
sl@0
   245
sl@0
   246
DCryptoH4Chan::DCryptoH4Chan(DCryptoPddFactory &iCryptoPddFactory)
sl@0
   247
    : iCryptoPddFactory(iCryptoPddFactory),
sl@0
   248
	  iFakeDriverSetting(100000)
sl@0
   249
    {
sl@0
   250
	TRACE_FUNCTION("DCryptoH4Chan");
sl@0
   251
    }
sl@0
   252
sl@0
   253
DCryptoH4Chan::~DCryptoH4Chan()
sl@0
   254
    {
sl@0
   255
	TRACE_FUNCTION("~DCryptoH4Chan");
sl@0
   256
	if(iCryptoJobRandom)
sl@0
   257
		{
sl@0
   258
		// Make sure we are not queued on a job scheduler.
sl@0
   259
		iCryptoJobRandom->DeScheduleJob();
sl@0
   260
		delete iCryptoJobRandom;
sl@0
   261
		}
sl@0
   262
	if(iCryptoJobAes)
sl@0
   263
		{
sl@0
   264
		// Make sure we are not queued on a job scheduler.
sl@0
   265
		iCryptoJobAes->DeScheduleJob();
sl@0
   266
		delete iCryptoJobAes;
sl@0
   267
		}
sl@0
   268
    }
sl@0
   269
sl@0
   270
sl@0
   271
TInt DCryptoH4Chan::DoCreate()
sl@0
   272
    {
sl@0
   273
	TRACE_FUNCTION("DoCreate");
sl@0
   274
sl@0
   275
sl@0
   276
    return KErrNone;
sl@0
   277
    }
sl@0
   278
sl@0
   279
TDfcQue* DCryptoH4Chan::DfcQue()
sl@0
   280
    {
sl@0
   281
	TRACE_FUNCTION("DfcQue");
sl@0
   282
    return iCryptoPddFactory.DfcQue();
sl@0
   283
    }
sl@0
   284
sl@0
   285
void DCryptoH4Chan::GetHwVersions(RCryptoDriver::THwVersions &aHwVersions) const
sl@0
   286
	{
sl@0
   287
	TRACE_FUNCTION("THwVersions");
sl@0
   288
#ifdef __MARM__
sl@0
   289
	aHwVersions.iRngHwVersion = TOmap::Register32(KHwBaseRngReg + KHoRng_Rev);
sl@0
   290
	aHwVersions.iDes3DesHwVersion = TOmap::Register32(KHwBaseDes3DesReg + KHoDES_REV);
sl@0
   291
	aHwVersions.iSha1Md5HwVersion = TOmap::Register32(KHwBaseSha1Md5Reg + KHoSHA_REV);
sl@0
   292
	aHwVersions.iAesHwVersion = TOmap::Register32(KHwBaseAesReg + KHoAES_REV);
sl@0
   293
	aHwVersions.iPkaHwVersion = TOmap::Register32(KHwBasePkaReg + KHoPKA_REV);
sl@0
   294
	TOmap::SetRegister32(KHwBasePkaReg + KHoPKA_REV,42);
sl@0
   295
	aHwVersions.iPkaHwVersion = TOmap::Register32(KHwBasePkaReg + KHoPKA_REV);
sl@0
   296
#else
sl@0
   297
	// Return fake hardware versions for testing
sl@0
   298
	aHwVersions.iRngHwVersion = 42;
sl@0
   299
	aHwVersions.iDes3DesHwVersion = 43;
sl@0
   300
	aHwVersions.iSha1Md5HwVersion = 44;
sl@0
   301
	aHwVersions.iAesHwVersion = 45;
sl@0
   302
	aHwVersions.iPkaHwVersion = 46;
sl@0
   303
#endif
sl@0
   304
    }
sl@0
   305
sl@0
   306
TInt DCryptoH4Chan::FakeDriverSetting() const
sl@0
   307
    {
sl@0
   308
	TRACE_FUNCTION("FakeDriverSetting");
sl@0
   309
    return iFakeDriverSetting;
sl@0
   310
    }
sl@0
   311
sl@0
   312
TInt DCryptoH4Chan::SetFakeDriverSetting(TInt aFakeDriverSetting)
sl@0
   313
    {
sl@0
   314
	TRACE_FUNCTION("SetFakeDriverSetting");
sl@0
   315
    if(aFakeDriverSetting<=0)
sl@0
   316
        return KErrArgument;
sl@0
   317
    iFakeDriverSetting = aFakeDriverSetting;
sl@0
   318
    return KErrNone;
sl@0
   319
    }
sl@0
   320
sl@0
   321
CryptoJobRandom *DCryptoH4Chan::GetJobRandom(TBool aAutoCreate)
sl@0
   322
	{
sl@0
   323
	TRACE_FUNCTION("GetJobRandom");
sl@0
   324
	if(aAutoCreate && iCryptoJobRandom == 0)
sl@0
   325
		{
sl@0
   326
		iCryptoJobRandom = new CryptoH4JobRandom(iCryptoLddChannel->iLddChanRandom);
sl@0
   327
		iCryptoJobRandom->SetDfcQ(DfcQue());
sl@0
   328
		}
sl@0
   329
	return iCryptoJobRandom;
sl@0
   330
	}
sl@0
   331
sl@0
   332
CryptoJobAes *DCryptoH4Chan::GetJobAes(TBool aAutoCreate)
sl@0
   333
	{
sl@0
   334
	TRACE_FUNCTION("GetJobAes");
sl@0
   335
	if(aAutoCreate && iCryptoJobAes == 0)
sl@0
   336
		{
sl@0
   337
		iCryptoJobAes = new CryptoH4JobAes(iCryptoLddChannel->iLddChanAes);
sl@0
   338
		iCryptoJobAes->SetDfcQ(DfcQue());
sl@0
   339
		}
sl@0
   340
	return iCryptoJobAes;
sl@0
   341
	}
sl@0
   342
sl@0
   343
sl@0
   344
// End of file