⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 crtsis.cpp

📁 Symbian操作系统手机上可执行程序的安装打包程序的源码
💻 CPP
📖 第 1 页 / 共 4 页
字号:
			//append hash cipher text to end of the file						//if RSA, we need to add the RSA'd SHA-1 signature			if (pKey->KeyType() == ERSAPrivateKey)				{				memcpy(&pFileBuf[TargetLen], ciphertext, KeyLen);				}						//If DSA, we need to add the DSA'd SHA-1 signature			if (pKey->KeyType() == EDSAPrivateKey)				{				memcpy(&pFileBuf[TargetLen], hash, KeyLen);												delete pHash;				}						//write new SIS file to disk (hash is now appended)			HANDLE hOutFile = ::MakeSISOpenFile(pszTargetFile, GENERIC_WRITE, OPEN_EXISTING);			if(hOutFile == INVALID_HANDLE_VALUE) throw ErrCannotOpenFile;									if(!::WriteFile(hOutFile, (LPVOID)pFileBuf, TargetLen + KeyLen, &dwNumBytes, NULL))				throw ErrCannotWriteFile;						::CloseHandle(hOutFile);						delete [] pFileBuf;			delete pKey;					}#endif		}// Load the private key from the fileCPrivateKey* CSISFileGeneratorBase::LoadPrivateKey()	{	CPrivateKey* result = NULL;#ifdef DIGITAL_SIGNATURES		const SIGNATURENODE* pSignature = m_pSISWriter->GetSignatureBase();	if (pSignature)		{		// convert private key file name into MBCS for Encrypt() method		DWORD length=wcslen(pSignature->pszPrivateKey);		LPSTR fName=MakeMBCSString(pSignature->pszPrivateKey, CP_ACP, length);				// convert password into MBCS for Encrypt() method		WCHAR pszCmdPassword[MAX_PATH];	 // Command Line Decryption Password		LPSTR pszPassword = "";				//test for command line Decryption Password		if (m_pSISWriter->GetCmdPassword(pszCmdPassword))			{			length=wcslen(pszCmdPassword);			pszPassword=MakeMBCSString(pszCmdPassword, CP_ACP, length);						/*			#ifdef _DEBUG			printf("***DEBUG CODE*** Password is %s\n", pszPassword);			#endif			*/			}				else			{			length=wcslen(pSignature->pszPassword);			pszPassword=MakeMBCSString(pSignature->pszPassword, CP_ACP, length);			}						CPrivateKey* pKey = new CPrivateKey;		if (!pKey) throw ErrNotEnoughMemory;				pKey->LoadKey(fName, pszPassword);				delete [] pszPassword;		delete [] fName;				if (pKey->Loaded() == FALSE)			{				throw ErrCannotOpenFile;			}		else			{			result = pKey;			}		}#endif			return result;	}void CSISFileGeneratorBase::Crc(const void *pPtr, DWORD dwLength)// Purpose  : Creates the CRC checksum                              // Inputs   : pPtr    - Pointer to a block of memory                 //            wLength - The length of the memory block            	{	const unsigned char *pB = (const unsigned char *)pPtr;	const unsigned char *pE = pB + dwLength;	WORD crc = m_wCheck;    while (pB < pE)		crc = (WORD)((crc << 8) ^ crcTab[((crc >> 8) ^ *pB++) & 0xff]);	m_wCheck = crc;	}void CSISFileGeneratorBase::UIDCheck(const void *pPtr)// Purpose  : To create a UID checksum                           // Inputs   : pPtr    - Pointer to a block of memory                 	{	const unsigned char *pB = (const unsigned char *)pPtr;	const unsigned char *pE = pB + (KUidInstallNumUid * sizeof(DWORD));	unsigned char buf[(KUidInstallNumUid * sizeof(DWORD))>>1];	unsigned char *pT = (&buf[0]);	while (pB < pE)		{		*pT++ = (*pB);		pB += 2;		} 	m_wCheck = 0;	Crc(&buf[0], (KUidInstallNumUid * sizeof(DWORD))>>1);	}void CSISFileGeneratorBase::EstimateInstallationSizeL()	{	int nodes, i;	const PKGLINENODE *pNode = m_pSISWriter->GetPkgLineBase();		// This method makes an estimate of the amount of space required by an installation.	// It sums the uncompressed size of all files that are to be installed on an epoc device.	// If statements are a special case.  Only the largest file installed by any given branch of	// an if statement will be added to the total install size.  Consequently the space required will	// overestimated for package files with if statements. 		// Since nodes are added to the front of the list, the last package line appears at the 	// front of the list.  Its easier to compute the maximum amount of space required by an	// if statement if we can access the nodes in the order in which they appear in the 	// .pkg file.  Hence, an array is created with pointers to these nodes. 		for (nodes = 0; pNode != NULL; pNode = pNode->pNext) 		nodes++;		const PKGLINENODE **pNodePointers = new const PKGLINENODE*[nodes];		pNode = m_pSISWriter->GetPkgLineBase();	for (i = nodes-1; i >= 0; i--)		{		pNodePointers[i] = pNode;		pNode = pNode->pNext;		}		try		{		m_dwMaximumSpaceNeeded = 0;		i = 0;		while (i < nodes)			{			if (pNodePointers[i]->iPackageLineType == EInstPkgLineCondIf)				m_dwMaximumSpaceNeeded += CalculateInstallSizeOfIfBlockL(pNodePointers, i);			else				{				m_dwMaximumSpaceNeeded += CalculateInstallSizeOfFileL(pNodePointers[i]);				i++;				}			}		}	catch (...)		{		delete[] pNodePointers;		throw;		}		delete[] pNodePointers;	}int CSISFileGeneratorBase::CalculateInstallSizeOfIfBlockL(const PKGLINENODE **pNode, int &index) const	{	int spaceNeeded = 0;	int needsOfBlock;	bool processingIf = true;	index++;		while (processingIf)		{		needsOfBlock = 0;		while (pNode[index]->iPackageLineType != EInstPkgLineCondElseIf &&			pNode[index]->iPackageLineType != EInstPkgLineCondElse &&			pNode[index]->iPackageLineType != EInstPkgLineCondEndIf)			{			if (pNode[index]->iPackageLineType == EInstPkgLineCondIf)				needsOfBlock += CalculateInstallSizeOfIfBlockL(pNode,index);			else				{				needsOfBlock += CalculateInstallSizeOfFileL(pNode[index]);				index++;				}			}				if (needsOfBlock > spaceNeeded)			spaceNeeded = needsOfBlock;				processingIf = (pNode[index]->iPackageLineType != EInstPkgLineCondEndIf);		index++;		}		return spaceNeeded;	}int CSISFileGeneratorBase::CalculateInstallSizeOfFileL(const PKGLINENODE *pNode) const	{	int spaceNeeded = 0;		if ((pNode->iPackageLineType == EInstPkgLineFile || pNode->iPackageLineType == EInstPkgLineLanguageFile) &&		(pNode->file->type != EInstFileTypeText && pNode->file->type != EInstFileTypeNull && 		pNode->file->type != EInstFileTypeMime))		{		if (pNode->file->type == EInstFileTypeComponent)			{			HANDLE hFile = ::MakeSISOpenFile(pNode->file->pszSource,GENERIC_READ, OPEN_EXISTING);			if (hFile==INVALID_HANDLE_VALUE) throw ErrCannotOpenFile;			TInstInstallation header;			DWORD dwBytesRead;			if (!::ReadFile(hFile,(LPVOID) &header,sizeof(TInstInstallation),&dwBytesRead,NULL))				throw ErrCannotReadFile;			::CloseHandle(hFile);			spaceNeeded = header.iMaximumSpaceNeeded;			}		else			if (pNode->file->type != EInstFileTypeText)				spaceNeeded = pNode->file->dwSize;		}		return spaceNeeded;	}void CSISFileGeneratorBase::CompressFiles()// Purpose : To compress files embedded within the sis file.	{	int compressedSize = 0;			Verbage(_T("Compressing files"));	const PKGLINENODE *pNode = m_pSISWriter->GetPkgLineBase();		while(pNode)		{		if ((pNode->iPackageLineType == EInstPkgLineFile || pNode->iPackageLineType == EInstPkgLineLanguageFile) && pNode->file->type != EInstFileTypeNull)			{			pNode->file->dwUncompressedSize = pNode->file->dwSize;						if (((m_pSISWriter->GetFlags() & EInstNoCompress) == 0))				{				LPWSTR pszCompressedFileName = TempFileName(pNode->file->pszSource);								CompressFile(pNode,pszCompressedFileName,compressedSize);								// update the source filename and the file size in the PKGLINEFILE node.								wcscpy(pNode->file->pszSource, pszCompressedFileName);				pNode->file->dwSize = compressedSize;				}			}		pNode = pNode->pNext;		}	}void CSISFileGeneratorBase::CompressFile(const PKGLINENODE *pNode, LPWSTR pszOutputFname, int &compressedSize)// Purpose: Compresses the file pointed into a temporary file.// Inputs:  pNode: a pointer to a PKGLINENODE which contains information about the source file//			pszOutputFname: the name of the compressed file to be created.// Outputs:	compressedSize: The size of the compressed File.	{	HANDLE hUncompressedFile, hCompressedFile;	DWORD dwUncompressedFileSize;	const int bufferSize = 0xffff;	int zlibErr;	BOOL zlibInit = FALSE;		hUncompressedFile = ::MakeSISOpenFile(pNode->file->pszSource, GENERIC_READ, OPEN_EXISTING);	if(hUncompressedFile == INVALID_HANDLE_VALUE) throw ErrCannotOpenFile;	dwUncompressedFileSize = ::GetFileSize(hUncompressedFile, NULL);		hCompressedFile = ::MakeSISOpenFile(pszOutputFname, GENERIC_WRITE|GENERIC_READ, CREATE_NEW);	if (hCompressedFile==INVALID_HANDLE_VALUE) throw ErrCannotOpenFile;		BYTE *pbInputBuffer = new BYTE [bufferSize];	BYTE *pbOutputBuffer = new BYTE [bufferSize];	z_stream compressionState;		try		{		if (!pbOutputBuffer || !pbInputBuffer) throw ErrNotEnoughMemory;				compressionState.zalloc = NULL;		compressionState.zfree = NULL;		compressionState.opaque = NULL;		compressionState.next_out = pbOutputBuffer;		compressionState.avail_out = bufferSize;		ReadFromUncompressedFile(hUncompressedFile,pbInputBuffer,compressionState,bufferSize);				zlibInit = TRUE;		zlibErr = deflateInit(&compressionState,Z_DEFAULT_COMPRESSION);		if (zlibErr != Z_OK) throw ErrFailedCompression;				while ((zlibErr = deflate(&compressionState,Z_NO_FLUSH)) == Z_OK)			{			if (compressionState.avail_in == 0)				ReadFromUncompressedFile(hUncompressedFile,pbInputBuffer,compressionState,bufferSize);						if (compressionState.avail_out == 0)				WriteToCompressedFile(hCompressedFile, pbOutputBuffer,compressionState, bufferSize);			}				while ((zlibErr = deflate(&compressionState,Z_FINISH)) == Z_OK)			{			if (compressionState.avail_in == 0)				ReadFromUncompressedFile(hUncompressedFile,pbInputBuffer,compressionState,bufferSize);						if (compressionState.avail_out == 0)				WriteToCompressedFile(hCompressedFile, pbOutputBuffer,compressionState, bufferSize);			}		if (zlibErr != Z_STREAM_END) throw ErrFailedCompression;		WriteToCompressedFile(hCompressedFile, pbOutputBuffer,compressionState, bufferSize);		} 	catch(...)		{		delete[] pbInputBuffer;		delete[] pbOutputBuffer;		::CloseHandle(hUncompressedFile);		::CloseHandle(hCompressedFile);		_wunlink(pszOutputFname); // delete compressed file		if (zlibInit)			deflateEnd(&compressionState);		throw;		}		delete[] pbInputBuffer;	delete[] pbOutputBuffer;	::CloseHandle(hUncompressedFile);	::CloseHandle(hCompressedFile);		compressedSize = compressionState.total_out;	deflateEnd(&compressionState);		}void CSISFileGeneratorBase::ReadFromUncompressedFile(HANDLE hFile,BYTE *pbBuffer,z_stream &compressionState, int bufferSize)	{	DWORD dwNumBytes;	if (::ReadFile(hFile, (LPVOID)pbBuffer, bufferSize, &dwNumBytes, NULL))		{		compressionState.next_in = pbBuffer;		compressionState.avail_in = dwNumBytes;			}	else		throw ErrCannotReadFile;	}void CSISFileGeneratorBase::WriteToCompressedFile(HANDLE hFile,BYTE *pbBuffer,z_stream &compressionState, int bufferSize)	{	DWORD dwNumBytes;	if (::WriteFile(hFile, (LPVOID)pbBuffer, bufferSize - compressionState.avail_out, &dwNumBytes, NULL))		{		compressionState.next_out = pbBuffer;		compressionState.avail_out = dwNumBytes;		}	else		throw ErrCannotWriteFile; 	}// ===========================================================================// CSISFileGeneratorT<>// Template class, handles the character size specific SIS file generation// ===========================================================================template<class T>void CSISFileGeneratorT<T>::WriteString(LPCWSTR pStr, HANDLE hFile)// Purpose  : Write a string to the file// Inputs   : pStr	-	The string to write (comes from CSISWritre so is always UNICODE!)//			  hFile -	The target file		{	// Copy the string into the output format...	long len = wcslen(pStr);		T* buf = new T[len + 1];	if (!buf) throw ErrNotEnoughMemory;		for(int i = 0; i < len; ++i)		buf[i] = (T)pStr[i];		// And write it to the file	DWORD dwNumBytes;	if(!::WriteFile(hFile, (LPVOID)buf, len * sizeof(T), &dwNumBytes, NULL))		throw ErrFailedToWriteStringsBlock;		// CRC	Crc((void *)buf, len * sizeof(T));		delete [] buf;	}template<class T>void CSISFileGeneratorT<T>::WriteString8(LPCWSTR pStr, HANDLE hFile)// Purpose  : Write an 8bit string to the file// Inputs   : pStr	-	The string to write//			  hFile -	The target file		{	// Copy the string into the output format...	long len = wcslen(pStr);		char* buf = new char[len + 1];	if (!buf) throw ErrNotEnoughMemory;		for(int i = 0; i < len; ++i)		buf[i] = (char)pStr[i];		// And write it to the file	DWORD dwNumBytes;	if(!::WriteFile(hFile, (LPVOID)buf, len, &dwNumBytes, NULL))		throw ErrFailedToWriteStringsBlock;		// CRC	Crc((void *)buf, len);		delete [] buf;	}void CSISFileGeneratorBase::ParseCertificates()	{	// Test for PKCS7 chain and re-write as concatenated certificates#ifdef DIGITAL_SIGNATURES	//get digital sig info	const SIGNATURENODE* pSignature = m_pSISWriter->GetSignatureBase();		if (pSignature)		{				int status;				m_bWriteChain = FALSE;				//get a temporary filename for re-writing a PCKS chain		LPWSTR pszTempCert;		pszTempCert = TempFileName(pSignature->pszPublicKey);				// convert tempfile name for Convert Signed method		DWORD lent=wcslen(pszTempCert);		LPSTR fNameTmp=MakeMBCSString(pszTempCert, CP_ACP, lent);						// convert temporary Certificate file name for Convert Signed method		DWORD lench=wcslen(pSignature->pszChainFile);		LPSTR fNameChain=MakeMBCSString(pSignature->pszChainFile, CP_ACP, lench);						// convert certificate name for Convert Signed method		DWORD lenc=wcslen(pSignature->pszPublicKey);		LPSTR fNameCrt=MakeMBCSString(pSignature->pszPublicKey, CP_ACP, lenc);						// convert b64 name		DWORD lencb64=wcslen(pSignature->pszB64File);		LPSTR fNameB64=MakeMBCSString(pSignature->pszB64File, CP_ACP, lencb64);								//create our PKCS7 aware object		CPKCS7* pPKCS7 = new CPKCS7;		if (!pPKCS7) throw ErrNotEnoughMemory;				status = pPKCS7->ConvertSigned(fNameCrt, fNameTmp);		//status = pPKCS7->ConvertBase64(fNameCrt, fNameTmp);						// If not a single cert, specify that the end entity cert comes first.		// Identify ee cert by private key		CPrivateKey* pKey = LoadPrivateKey();		pPKCS7->SetEndEntityKey(pKey);				int keyMatchesCert = 1;		if (status == PKCS7FileReWritten)			{			int extractStatus = pPKCS7->ExtractChain(fNameTmp, fNameChain, &(unsigned short)pSignature->iNumCerts);			m_bWriteChain = TRUE;			if (extractStatus == ErrEndEntityNotFound)				keyMatchesCert = 0;						}		else if (status != PKCS7FileIsCertificate)			{			int extractStatus = pPKCS7->ExtractChain(fNameCrt, fNameChain, &(unsigned short)pSignature->iNumCerts);			m_bWriteChain = TRUE;			if (extractStatus == ErrEndEntityNotFound)				keyMatchesCert = 0;			}		else			{			// File is a single cert - check it matches the key			keyMatchesCert = pKey->MatchesCert(fNameCrt);			}		if (!keyMatchesCert)			throw ErrCertFileKeyFileMismatch;				delete pKey;		delete pPKCS7;				//create a Base64 convertor object		CB64Decrypt* pB64 = new CB64Decrypt;				if (!pB64) throw ErrNotEnoughMemory;				if (m_bWriteChain)			{			pB64->Do(fNameChain, fNameB64, NULL);			}		else			{			pB64->Do(fNameCrt, fNameB64, NULL);			}				delete pB64;				delete [] fNameTmp;		delete [] fNameChain;		delete [] fNameCrt;						}#endif	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -