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

📄 pgpnetpolicymanager.c

📁 vc环境下的pgp源码
💻 C
📖 第 1 页 / 共 2 页
字号:

		pSA->reKeyInProgress = TRUE;
	}
}

PGPnetPMStatus
sDoTransformOutgoing(PGPnetPMContext *pContext, 
					 PGPNDIS_PACKET *packet, 
					 PVPN_ADAPTER adapter)
{
	PGPUInt32		ipAddress		= htonl(packet->ipAddress);
	PGPUInt32		i				= 0;
	PGPNetHostEntry *host 			= PMFindHost(pContext, ipAddress);
	PGPnetKernelSA 	*transportSA	= 0, *tunnelSA = 0;
	PGPError		err				= kPGPError_NoErr;
	PGPBoolean		bRet			= FALSE;
	PGPnetPMStatus	ret;

    DBG_FUNC("sDoTransformOutgoing")

    DBG_ENTER();

retry:
	ret = sLookHardForSA(pContext, 
		adapter, 
		host, 
		ipAddress, 
		packet->port,
		packet,
		0,
		&transportSA, 
		&tunnelSA, 
		FALSE);

	if (ret != kPGPNetPMPacketEncrypt && ret != kPGPNetPMPacketClear) {
		DBG_PRINT(("Could not find SA\n"););
		DBG_PRINT(("Happens w/ fragmented packets and other cases\n"););
		goto end;
	}
	
	bRet = sCheckExpiration(adapter, transportSA);
	if (bRet) {
		/* now set activeOut to false  */
		transportSA->ikeSA.activeOut = FALSE;
		goto retry;
	}

	bRet = sCheckExpiration(adapter, tunnelSA);
	if (bRet) {
		/* now set activeOut to false */
		transportSA->ikeSA.activeOut = FALSE;
		goto retry;
	}

	sCheckRekey(adapter, transportSA);
	sCheckRekey(adapter, tunnelSA);

	if (transportSA && packet->port != UDP_PORT_IKE_NET) {
		err = PGPnetIPsecApplySA(adapter, pContext, packet, transportSA, FALSE, FALSE);
		if (IsntPGPError(err)) {
			transportSA->packetsSent++;
			DBG_PRINT(("Packets sent: %d\n", transportSA->packetsSent););		
			/* XXX Is BlockLen the right thing to add? */
			transportSA->bytesSent += packet->srcBlockLen /* - header size */;
		} else {
			goto fail;
		}

#if/*def*/ 0 /*DBG*/
	/* write out SA info */
	DBG_PRINT(("inESPKey\n"););
	for (i = 0; i< kPGPike_ESPMaximumKeySize; i++) {
		DbgPrint("%X ", transportSA->ikeSA.transform[0].u.ipsec.u.esp.inESPKey[i]);
	}
	DBG_PRINT(("\noutESPKey\n"););
	for (i = 0; i< kPGPike_ESPMaximumKeySize; i++) {
		DbgPrint("%X ", transportSA->ikeSA.transform[0].u.ipsec.u.esp.outESPKey[i]);
	}
	DBG_PRINT(("\ninAuthKey\n"););
	for (i = 0; i< kPGPike_AuthMaximumKeySize; i++) {
		DbgPrint("%X ", transportSA->ikeSA.transform[0].u.ipsec.u.esp.inAuthKey[i]);
	}
	DBG_PRINT(("\noutAuthKey\n"););
	for (i = 0; i< kPGPike_AuthMaximumKeySize; i++) {
		DbgPrint("%X ", transportSA->ikeSA.transform[0].u.ipsec.u.esp.outAuthKey[i]);
	}
	DBG_PRINT(("\nESP Cipher: %d\n", transportSA->ikeSA.transform[0].u.ipsec.u.esp.t.cipher););
	DBG_PRINT(("ESP Auth Attr: %d\n", transportSA->ikeSA.transform[0].u.ipsec.u.esp.t.authAttr););
#endif

	} else if (packet->port == UDP_PORT_IKE_NET && !tunnelSA) {
		// copy the chained buffer
		sCopySrcToxForm(packet);
	}

	if (tunnelSA) {
		err = PGPnetIPsecApplySA(adapter, pContext, packet, tunnelSA, FALSE, TRUE);		
	
		if (IsntPGPError(err)) {
			/* XXX this doesn't seem right */
			tunnelSA->packetsSent++;
			DBG_PRINT(("Packets sent: %d\n", tunnelSA->packetsSent););		
			tunnelSA->bytesSent += packet->srcBlockLen /* - something */;
		} else {
			goto fail;
		}
	}

	if (!tunnelSA && !transportSA && packet->port != UDP_PORT_IKE_NET) {
		err = kPGPIPsecError_NoSAFound;
		goto fail;
	}

	DBG_LEAVE(kPGPNetPMPacketSent);
	return kPGPNetPMPacketSent;

fail:
	PMfireErrorEvent(adapter, ipAddress, err);
	DBG_LEAVE(kPGPNetPMPacketDrop);
	return kPGPNetPMPacketDrop;

end:
	DBG_LEAVE(ret);
	return ret;
}

PGPnetPMStatus
sDoTransformIncoming(PGPnetPMContext *pContext, PGPNDIS_PACKET *packet, PVPN_ADAPTER adapter)
{
	PGPUInt32		ipAddress		= htonl(packet->ipAddress);
	PGPUInt32		i				= 0;
	PGPUInt32		spi				= 0;
	PGPUInt32		tunnelIPsrc		= 0;
	PGPNetHostEntry *host 			= PMFindHost(pContext, ipAddress);
	PGPnetKernelSA	*pSA			= 0;
	PGPnetKernelSA	*unused			= 0;
	PGPError		err				= kPGPError_NoErr;
	PGPBoolean		tunnelMode		= FALSE;
	PGPNDIS_PACKET	*pgpPacket		= 0;
	NDIS_STATUS		status;

    DBG_FUNC("sDoTransformIncoming")

    DBG_ENTER();

	/* retrieve the outermost spi (tunnelIPsrc ignored) */
	err = PGPnetIPsecGetAddrAndSPI(pContext, packet, &tunnelIPsrc, &spi);
	if (IsPGPError(err))
		goto fail;

	if (spi) {
		/* try to find SA */
		if (!(pSA = PMFindSAspi(pContext, ipAddress, spi))) {
			/* No SA found with this SPI
			 * Try to find another SA, and possibly
			 * acquire a new SA. Must drop this packet, 
			 * since there isn't anyway I can decrypt it.
			 */
			sLookHardForSA(pContext, 
				adapter, 
				host, 
				ipAddress, 
				packet->port,
				packet,
				0,
				&pSA,
				&unused,
				TRUE);
			/* silent drop */
			DBG_LEAVE(kPGPNetPMPacketDrop);
			return kPGPNetPMPacketDrop;
		}
		if (host && host->hostType == kPGPnetSecureGateway) {
			/* tunnels require phaseII */
			tunnelMode = TRUE;
		} else {
			tunnelMode = FALSE;
		}

		/* Ok, time to apply SA */
		err = PGPnetIPsecApplySA(adapter, pContext, packet, pSA, TRUE, tunnelMode);
		if (IsPGPError(err)) {
			DBG_PRINT(("Returning Drop: PGPnetIPsecApplySA error: %d\n", err););
			goto fail;
		}
	} else {
		if (packet->port == UDP_PORT_IKE_NET) {
			sCopySrcToxForm(packet);
		} else {
			/* Ok the packet did not have an SPI. But it should, since we can't get here unless we
			* have an SA for the machine. Although it may have been deleted in the meantime
			so check again. Should it? only if it came from a configured host. If it did, then we start an SA acquisition.
			if we already have an SA, which is the most likely case, then what?
			*/
			if (!(pSA = PMFindSAspi(pContext, ipAddress, spi))) {
				/* No SA found with this SPI
				* Try to find another SA, and possibly
				* acquire a new SA. Must drop this packet, 
				* since there isn't anyway I can decrypt it.
				*/
				sLookHardForSA(pContext,
					adapter,
					host,
					ipAddress,
					packet->port,
					packet,
					0,
					&pSA,
					&unused,
					TRUE);
				/* silent drop */
				DBG_LEAVE(kPGPNetPMPacketDrop);
				return kPGPNetPMPacketDrop;
			} else {
				err = kPGPIPsecError_NoSPIFound;
				goto fail;
			}
		}
	}
	
	/* phase II */
	if (tunnelMode) {
		DBG_PRINT(("Entering Phase II\n"););

#define ETHERNET_HDRLENGTH	14

		if (pgpIsFragmented(packet->xformBlock + ETHERNET_HDRLENGTH)) {

			// Allocate the pgpPacket
			pgpPacket = PGPNdisPacketAllocWithSrcPacket(&status, adapter);

			if (status != NDIS_STATUS_SUCCESS)
			{
				DBG_LEAVE(kPGPNetPMPacketDrop);
				return kPGPNetPMPacketDrop;
			}

			sCopyPacketXformToSrc(packet /*src*/, pgpPacket, adapter);

			status = TransformAndIndicate(adapter, pgpPacket);
			if (status == NDIS_STATUS_SUCCESS)
			{
				PGPNdisPacketFreeSrcPacket(adapter, pgpPacket);
			}

			return kPGPNetPMPacketDrop;
		}

		err = PGPnetIPsecGetAddrAndSPI(pContext, packet, &tunnelIPsrc, &spi); 
		if (IsPGPError(err)) {
			goto fail;
		}

		/* 
		 * If we don't find an SPI, that's fine. It just means that
		 * was a normal IP packet within the tunnel, rather than
		 * an IPSEC packet
		 */
		if (spi) {
			if (!(pSA = PMFindSAspi(pContext, tunnelIPsrc, spi))) {			
				err = kPGPIPsecError_NoSAFound;
				goto fail;
			}
			tunnelMode = FALSE;
			err = PGPnetIPsecApplySA(adapter, pContext, packet, pSA, TRUE, tunnelMode);
			if (IsPGPError(err)) {
				DBG_PRINT(("Returning Drop: PGPnetIPsecApplySA error: %d\n", err););
				goto fail;
			}
		}
	}

#if/*def*/ 0 /*DBG*/
	/* write out SA info */
	DBG_PRINT(("inESPKey\n"););
	for (i = 0; i< kPGPike_ESPMaximumKeySize; i++) {
		DbgPrint("%X ", pSA->ikeSA.transform[0].u.ipsec.u.esp.inESPKey[i]);
	}
	DBG_PRINT(("\noutESPKey\n"););
	for (i = 0; i< kPGPike_ESPMaximumKeySize; i++) {
		DbgPrint("%X ", pSA->ikeSA.transform[0].u.ipsec.u.esp.outESPKey[i]);
	}
	DBG_PRINT(("\ninAuthKey\n"););
	for (i = 0; i< kPGPike_AuthMaximumKeySize; i++) {
		DbgPrint("%X ", pSA->ikeSA.transform[0].u.ipsec.u.esp.inAuthKey[i]);
	}
	DBG_PRINT(("\noutAuthKey\n"););
	for (i = 0; i< kPGPike_AuthMaximumKeySize; i++) {
		DbgPrint("%X ", pSA->ikeSA.transform[0].u.ipsec.u.esp.outAuthKey[i]);
	}
	DBG_PRINT(("\nESP Cipher: %d\n", pSA->ikeSA.transform[0].u.ipsec.u.esp.t.cipher););
	DBG_PRINT(("ESP Auth Attr: %d\n", pSA->ikeSA.transform[0].u.ipsec.u.esp.t.authAttr););
#endif

	DBG_LEAVE(kPGPNetPMPacketSent);
	return kPGPNetPMPacketSent;

fail:
	PMfireErrorEvent(adapter, ipAddress, err);
	DBG_LEAVE(kPGPNetPMPacketDrop);
	return kPGPNetPMPacketDrop;
}

void
sCopySrcToxForm(PGPNDIS_PACKET *start)
{
	PGPNDIS_PACKET *current = start;
	PGPBoolean moreLinks = TRUE;

	DBG_FUNC("sCopySrcToxForm")

	DBG_ENTER();

	if (!current->firstSrcBlock)
		return;

	do {
		DBG_PRINT(("current->srcBlockLen: %d\n", current->srcBlockLen););
		
		pgpCopyMemory(current->srcBlock /*src*/, current->xformBlock, current->srcBlockLen);
		current->xformBlockLen = current->srcBlockLen;
		current->firstXformBlock = current->firstSrcBlock;
		current->lastXformBlock = current->lastSrcBlock;

		if (current->lastSrcBlock)
			moreLinks = FALSE;

		current = current->link;
	} while (moreLinks);

	DBG_LEAVE(0);
}

void
sCopyPacketXformToSrc(const PGPNDIS_PACKET *source, PGPNDIS_PACKET *dest, PVPN_ADAPTER adapter)
{
	DBG_FUNC("sCopyPacketXformToSrc")

	DBG_ENTER();

	if (!source->firstXformBlock)
		return;

	if (!source->lastXformBlock) {
		DBG_BREAK();
	}

	DBG_PRINT(("source->xformBlockLen: %d\n", source->xformBlockLen););
		
	pgpCopyMemory(source->xformBlock /*src*/, dest->srcBlock, source->xformBlockLen);
	dest->srcBlockLen = source->xformBlockLen;
	dest->firstSrcBlock = TRUE;
	dest->lastSrcBlock = FALSE;

	DBG_LEAVE(0);
}

PGPnetPMStatus
sLookHardForSA(PGPnetPMContext *pContext, 
			   PVPN_ADAPTER adapter,
			   PGPNetHostEntry *host,
			   PGPUInt32 ipAddress,
			   PGPUInt16 port,
			   void * ipBuffer,
			   PGPUInt32 ipBufferSize,
			   PGPnetKernelSA **ppTransport,
			   PGPnetKernelSA **ppTunnel,
			   PGPBoolean incoming)
{
	PGPnetPMStatus ret = kPGPNetPMPacketDrop;
	PGPnetPMStatus tunnelRet, transportRet;
	PGPNetHostEntry *secureGW = 0;

	if (host) {
		if (host->hostType == kPGPnetSecureGateway && 
			port != UDP_PORT_IKE_NET &&
			!incoming) {
			/* we always talk to Gateways in Tunnel mode */
			/* this should be right, but doesn't work with GVPN NT */
			ret = sAcquireSA(pContext, 
				host->ipAddress, 
				host->ipAddress,
				host->ipMask,
				incoming,
				ipBuffer,
				ipBufferSize,
				adapter,
				ppTunnel);

			return ret;
		}

		if (host->hostType == kPGPnetSecureHost && 
			host->childOf == -1 && 
			port != UDP_PORT_IKE_NET) {
			/* we need only the transport SA */
			ret = sAcquireSA(pContext,
				ipAddress,
				0,
				0,
				incoming,
				ipBuffer,
				ipBufferSize,
				adapter,
				ppTransport);
			return ret;
		}

		if (host->hostType == kPGPnetInsecureHost && host->childOf != -1) {
			/* we need only the tunnel SA */
			secureGW = &(pContext->pKernelHostList[host->childOf]);
			ret = sAcquireSA(pContext, 
				secureGW->ipAddress,
				host->ipAddress,
				host->ipMask,
				incoming,
				ipBuffer,
				ipBufferSize,
				adapter,
				ppTunnel);
			return ret;
		}

		if (host->hostType == kPGPnetSecureHost && host->childOf != -1) {
			/* we need transport SA and tunnel SA */

			/* first get tunnel SA */
			secureGW = &(pContext->pKernelHostList[host->childOf]);

			tunnelRet = sAcquireSA(pContext, 
				secureGW->ipAddress,
				host->ipAddress,
				host->ipMask,
				incoming,
				ipBuffer,
				ipBufferSize,
				adapter,
				ppTunnel);

			if (port == UDP_PORT_IKE_NET) {
				return tunnelRet;
			}

			/* next get the transport SA */
			transportRet = sAcquireSA(pContext, 
				ipAddress,
				0,
				0,
				incoming,
				ipBuffer,
				ipBufferSize,
				adapter,
				ppTransport);

			if (tunnelRet == kPGPNetPMPacketEncrypt && 
				transportRet == kPGPNetPMPacketEncrypt) {
				/* both SAs are ready to go */
				ret = kPGPNetPMPacketEncrypt;
			} else {
				/* something isn't ready yet */
				ret = kPGPNetPMPacketWaiting;
			}
			return ret;
		}
	}

	if (pContext->pConfig->bAllowUnconfigHost && 
		!pContext->pConfig->bAttemptUnconfigHost) {
		/* 
		 * There may be an SA for this host that was initiated by the peer.
		 * So we need to look for an SA, before sending it in the clear
		 */
		if ((*ppTransport = PMFindSA(pContext, ipAddress, 0, incoming))) {
			return kPGPNetPMPacketEncrypt;
		} else {
			return kPGPNetPMPacketClear;
		}
	}

	if (pContext->pConfig->bAllowUnconfigHost && 
		pContext->pConfig->bAttemptUnconfigHost && 
		port != UDP_PORT_IKE_NET) {

		ret = sAcquireSA(pContext, 
			ipAddress,
			0,
			0,
			incoming,
			ipBuffer,
			ipBufferSize,
			adapter,
			ppTransport);

		return ret;
	}

	if (ret != kPGPNetPMPacketEncrypt && port == UDP_PORT_IKE_NET)
		ret = kPGPNetPMPacketClear;

	return ret;
}
	

⌨️ 快捷键说明

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