Ejemplo n.º 1
0
DWORD Sm_Shiloh::WriteSync(__in SNI_Packet * pPacket, SNI_ProvInfo * pInfo)
{
	BidxScopeAutoSNI3( SNIAPI_TAG _T("%u#, ")
							  _T("pPacket: %p{SNI_Packet*}, ")
							  _T("pInfo: %p{SNI_ProvInfo*}\n"), 
							  GetBidId(),
							  pPacket, 
							  pInfo );

	DWORD 	dwRet = ERROR_SUCCESS;

	// Check that the packetsize does not exceed the max packet size
	if( MAX_BUFFER_SIZE < SNIPacketGetBufferSize(pPacket) )
	{
		dwRet = ERROR_NOT_SUPPORTED;
		SNI_SET_LAST_ERROR( SM_PROV, SNIE_SYSTEM, dwRet );
		goto Exit;
	}
	
	// Post the transport write
	LONG Error;
	if( SNIPacketGetBufferSize(pPacket) != g_rgFuncs.Write( m_pConnObj,
							      SNIPacketGetBufPtr(pPacket),
							      (int)SNIPacketGetBufferSize(pPacket),
							      &Error ) )
	{
		dwRet = Error;
		SNI_SET_LAST_ERROR( SM_PROV, SNIE_1, dwRet );
	}

Exit:
	BidTraceU1( SNI_BID_TRACE_ON, RETURN_TAG _T("%d{WINERR}\n"), dwRet);
	
	return dwRet;
}                    
Ejemplo n.º 2
0
	friend void SNIPacketRelease(SNI_Packet * pPacket)
	{	
		BidTraceU2( SNI_BID_TRACE_ON, SNIAPI_TAG _T("%u#{SNI_Packet}, ")
												 _T("pPacket: %p{SNI_Packet*}\n"), 
												 SNIPacketGetBidId(pPacket), 
												 pPacket);
		
		Assert (pPacket);
		Assert (pPacket->m_pConn);
		Assert (pPacket->m_cRef > 0);
		Assert (pPacket->m_IOType < SNI_Packet_InvalidType);
		Assert ((pPacket->m_IOType != SNI_Packet_KeyHolderNoBuf) || 
				(	(NULL == pPacket->m_pBuffer) &&
					(0 == pPacket->m_cbBuffer) &&
					(0 == pPacket->m_cBufferSize))	);
		Assert (pPacket->m_ConsBuf < SNI_Consumer_Invalid);

		int iBidId = SNIPacketGetBidId(pPacket); 
		
		// Only release the packet if it's ref count drops to zero.
		if ( 0 != InterlockedDecrement( &pPacket->m_cRef ) ) 
		{
			BidTraceU2( SNI_BID_TRACE_ON, RETURN_TAG 
				_T("%u#!{SNI_Packet}: ")
				_T("Not final release.  ")
				_T("pPacket: %p{SNI_Packet*}\n"), 
				iBidId, 
				pPacket);
			return;
		}

#ifndef SNI_BASED_CLIENT
		if ((SNI_Packet_Read == pPacket->m_IOType) ||
			(SNI_Packet_Write == pPacket->m_IOType))
		{
			Assert(pPacket->m_pBuffer != NULL);
			BOOL fGlobalZeroingRequired = SOS_OS::GetCommonCriteriaModeEnabled ();
			if (pPacket->m_fZeroPayloadOnRelease || fGlobalZeroingRequired)
			{
				BYTE * pbBuf;
				DWORD cbBuf;
				if (fGlobalZeroingRequired)
				{
					//	If global zeroing is required always zero out the whole buffer
					//
					pbBuf = pPacket->m_pBuffer;
					cbBuf = pPacket->m_cBufferSize;
				}
				else
				{
					pbBuf = SNIPacketGetBufPtr(pPacket);
					cbBuf = SNIPacketGetBufferSize(pPacket);
					//	The bytes of memory to zero should never exceed the size
					//	of the packet
					//	If the m_cbBytesToZero is on-zero, we will zero out that
					//	amount, if not, zero out all the bytes
					//
					Assert (pPacket->m_cbBytesToZero <= cbBuf);
					if (pPacket->m_cbBytesToZero != 0)
						cbBuf = pPacket->m_cbBytesToZero;
				}
				SecureZeroMemory(pbBuf, cbBuf);
				pPacket->m_fZeroPayloadOnRelease = FALSE;
				pPacket->m_cbBytesToZero= 0;
			}
		}
		else	// "Buffer-less" packet like SNI_Packet_KeyHolderNoBuf or SNI_Packet_VaryingBuffer*
		{
			pPacket->m_fZeroPayloadOnRelease = FALSE;
			pPacket->m_cbBytesToZero= 0;
		}
#endif // ifndef SNI_BASED_CLIENT


		// While SNI_Packet_KeyHolderNoBuf type of packet never gets a buffer assigned to it
		// the SNI_Packet_VaryingBuffer* packets get their buffers assigned by the Consumer
		// However, Consumer is fully responsible for releasing the buffers, SNI treats
		// these types of packets as "buffer-less" and simply removes any reference to
		// the potential buffers used by the Consumer
		if ((SNI_Packet_VaryingBufferRead == pPacket->m_IOType) ||
			(SNI_Packet_VaryingBufferWrite == pPacket->m_IOType))
		{
			pPacket->m_pBuffer = NULL;
			pPacket->m_pNext = NULL;
			pPacket->m_cBufferSize = 0;
			pPacket->m_cbBuffer = 0;
		}

		pPacket->m_ConsBuf = SNI_Consumer_PacketIsReleased;

		BidTraceU1( SNI_BID_TRACE_ON, SNI_TAG 
			_T("%u#{SNI_Packet} to pool\n"), 
			SNIPacketGetBidId(pPacket) );

		SNI_Conn* pConn = pPacket->m_pConn;

		if ((SNI_Packet_Read == pPacket->m_IOType) || 
			(SNI_Packet_Write == pPacket->m_IOType))
		{
			pConn->Release( REF_Packet );
		}
		else
		{
			pConn->Release( REF_PacketNotOwningBuf );
		}

#ifdef SNI_BASED_CLIENT
		// No need to check for [....] or async conn, we just set the Overlapped hEvent to NULL
		pPacket->RemoveOvlEvent();
#endif
		
		pPacket->m_pMemRegion->Push(pPacket);
	}
Ejemplo n.º 3
0
DWORD Sm_Shiloh::ReadSync(__out SNI_Packet ** ppNewPacket, int timeout)
{
	BidxScopeAutoSNI3( SNIAPI_TAG _T("%u#, ")
							  _T("ppNewPacket: %p{SNI_Packet**}, ")
							  _T("timeout: %d\n"), 
							  GetBidId(),
							  ppNewPacket, 
							  timeout );

	DWORD dwRet = ERROR_SUCCESS;

	*ppNewPacket = 0;
	
	// Check for 0 timeout - proceed only if there is data
	if( 0 == timeout)
	{
		LONG Error, cBytes;

		if( FALSE == g_rgFuncs.CheckData( m_pConnObj,
								              &cBytes,
								              &Error) )
		{
			if( Error )
			{
				SNI_SET_LAST_ERROR( SM_PROV, SNIE_1, static_cast<DWORD>(Error) );

				BidTraceU1( SNI_BID_TRACE_ON, RETURN_TAG _T("%d{WINERR}\n"), Error);
				return Error;
			}
			else
			{
				SNI_SET_LAST_ERROR( SM_PROV, SNIE_SYSTEM, WAIT_TIMEOUT );

				BidTraceU1( SNI_BID_TRACE_ON, RETURN_TAG _T("%d{WINERR}\n"), WAIT_TIMEOUT);
				return WAIT_TIMEOUT;
			}
		}

		// Since we already have data, call Read iwth infinite timeout
		timeout = -1;
	}
	
	// Allocate a new packet
	SNI_Packet  * pPacket = SNIPacketAllocate(m_pConn, SNI_Packet_Read);
	if( !pPacket )
	{
		dwRet = ERROR_OUTOFMEMORY;
		SNI_SET_LAST_ERROR( SM_PROV, SNIE_SYSTEM, dwRet );
		goto ErrorExit;
	}
	
	// Post the transport read
	DWORD 	dwBytesRead = 0;
	{
		LONG Error;
		#define NETE_TIMEOUT -2
		#define NET_IMMEDIATE	0xFFFF

		// Convert from Shiloh timeout format to Yukon
		// For Yukon, 
		//	-1 = INFINITE
		//	0 = ZERO
		// 	Others - MilliSecs
		// For Shiloh,
		//	NET_IMMEDIATE = ZERO
		//	0 = INFINITE
		// 	Others - Secs
		if( -1 == timeout )
			timeout = 0;
		else if( 0 == timeout )
			timeout = NET_IMMEDIATE;
		else
			timeout /= 1000;
		
		dwBytesRead = g_rgFuncs.Read( m_pConnObj,
				                   SNIPacketGetBufPtr(pPacket),
				                   (int)SNIPacketGetBufActualSize(pPacket),
				                   (int)SNIPacketGetBufActualSize(pPacket),
				                   (USHORT)timeout,
				                   &Error );
		if( Error == NETE_TIMEOUT )
		{
			dwRet = WAIT_TIMEOUT;
			SNI_SET_LAST_ERROR( SM_PROV, SNIE_SYSTEM, dwRet );
			goto ErrorExit;
		}
		
		if( 0 == dwBytesRead )
		{
			dwRet = Error;
			SNI_SET_LAST_ERROR( SM_PROV, SNIE_1, dwRet );
			goto ErrorExit;
		}
	}

	SNIPacketSetBufferSize( pPacket, dwBytesRead );

	*ppNewPacket = pPacket;

	BidTraceU1( SNI_BID_TRACE_ON, RETURN_TAG _T("%d{WINERR}\n"), dwRet);

	return dwRet;

ErrorExit:

	if( pPacket )
		SNIPacketRelease( pPacket );

	*ppNewPacket = NULL;

	BidTraceU1( SNI_BID_TRACE_ON, RETURN_TAG _T("%d{WINERR}\n"), dwRet);
	
	return dwRet;

}