func()

in pkg/encrypt/encrypt_windows.go [31:102]


func (cHandler *certHandler) Encrypt(bytesToEncrypt []byte) (encryptedBytes []byte, err error) {
	alg := szOID_RSA_RC4
	buffer := []byte(alg)
	procCryptEncryptMessage := crypto.Modcrypt32.NewProc("CryptEncryptMessage")
	cai := crypto.CryptAlgorithmIdentifier{
		PszObjID: uintptr(unsafe.Pointer(&buffer[0])),
		Parameters: crypto.CryptObjectIDBlob{
			CbData: uint32(0),
			PbData: uintptr(0),
		},
	}

	cemp := cryptEncryptMessagePara{
		cbSize:                     uint32(0),
		dwMsgEncodingType:          uint32(windows.X509_ASN_ENCODING | windows.PKCS_7_ASN_ENCODING),
		hCryptProv:                 uint32(0),
		ContentEncryptionAlgorithm: cai,
		pvEncryptionAuxInfo:        uintptr(0),
		dwFlags:                    uint32(0),
		dwInnerContentType:         uint32(0),
	}
	cemp.cbSize = uint32(unsafe.Sizeof(cemp))

	// Call the first time to get the size
	var pbToBeEncrypted *byte
	var cbEncryptedBlob uint32
	pbToBeEncrypted = &bytesToEncrypt[0]
	ret, _, err := syscall.Syscall9(
		procCryptEncryptMessage.Addr(),
		7,
		uintptr(unsafe.Pointer(&cemp)), //pEncryptPara,
		uintptr(1),                     // cRecipientCert,
		uintptr(unsafe.Pointer(&cHandler.certContext)), // rgpRecipientCert,
		uintptr(unsafe.Pointer(pbToBeEncrypted)),       // *pbToBeEncrypted,
		uintptr(len(bytesToEncrypt)),                   // cbToBeEncrypted,
		uintptr(0),                                     // *pbEncryptedBlob,
		uintptr(unsafe.Pointer(&cbEncryptedBlob)),      // *pcbEncryptedBlob,
		0,
		0)

	if ret == 0 {
		return nil, fmt.Errorf("CryptEncryptMessage failed due to '%v'", err)
	}

	// Build the buffer
	if cbEncryptedBlob <= 0 {
		return nil, fmt.Errorf("the count of encrypted bytes was 0")
	}
	encryptedBytes = make([]byte, cbEncryptedBlob)
	var pencryptedBytes *byte
	pencryptedBytes = &encryptedBytes[0]

	// Perform the encryption
	ret, _, err = syscall.Syscall9(
		procCryptEncryptMessage.Addr(),
		7,
		uintptr(unsafe.Pointer(&cemp)), // pEncryptPara,
		uintptr(1),                     // cRecipientCert,
		uintptr(unsafe.Pointer(&cHandler.certContext)), // rgpRecipientCert,
		uintptr(unsafe.Pointer(pbToBeEncrypted)),       // *pbToBeEncrypted,
		uintptr(len(bytesToEncrypt)),                   // cbToBeEncrypted,
		uintptr(unsafe.Pointer(pencryptedBytes)),       // *pbEncryptedBlob,
		uintptr(unsafe.Pointer(&cbEncryptedBlob)),      // *pcbEncryptedBlob,
		0,
		0)

	if ret == 0 {
		return nil, fmt.Errorf("CryptEncryptMessage failed due to '%v'", err)
	}

	return encryptedBytes, nil
}