Я пытаюсь устранить неполадку, почему элемент приложения, написанный и скомпилированный в VB6 на машине Vista SP2, отлично работает на этой машине, но не на 64-битной машине Windows 10. Чтобы улучшить возможности отладки, я воспроизвел проблему с кодировкой в Excel VBA. Работает на машине Vista, но не на машине Windows 10.VB-код с использованием advapi32.dll cryptverifysignature работает на Vista SP2 не на Windows 10 64-разрядный
В CryptoAPI вызовы объявлены таким образом:
Private Declare Function CryptVerifySignature _
Lib "advapi32.dll" _
Alias "CryptVerifySignatureA" (_
ByVal hHash As Long, _
pbSignature As Byte, _
ByVal dwSigLen As Long, _
ByVal hPubKey As Long, _
ByVal sDescription As String, _
ByVal dwFlags As Long _
) As Long
Та часть, которая терпит неудачу на машине Windows 10 подсвечивается железнодорожных путей выше и ниже в следующем:
Private Function SignValidate(ByRef abData() As Byte, _
ByRef abSigned() As Byte, _
Optional bSigned As Boolean = True) As Long
Dim hHash As Long
Dim lngReturnValue As Long
Dim lngSigLen As Long
Dim abText() As Byte
Dim strTxt As String
Dim lngW As Long
Dim lngX As Long
Dim lngY As Long
Dim abHashVal() As Byte
SignValidate = -1
ReDim abText(UBound(abData))
abText = abData
'Create a hash object to sign/validate
lngReturnValue = CryptCreateHash(hCryptProv, CALG_SHA, 0, 0, hHash)
If lngReturnValue = 0 Then
'Set_locale regionalSymbol
Err.Raise Err.LastDllError, , "DLL error code shown above. Could not create a Hash Object (CryptCreateHash API)"
End If
'Hash the data
lngW = UBound(abText) + 1
lngReturnValue = CryptHashData(hHash, abText(0), lngW, 0)
If lngReturnValue = 0 Then
'Set_locale regionalSymbol
Err.Raise Err.LastDllError, , "DLL error code shown above. Could not calculate a Hash Value (CryptHashData API)"
End If
If bSigned Then
'release old key pair handle
If hKeyPair <> 0 Then CryptDestroyKey hKeyPair
'get a handle to the signature key pair
lngReturnValue = CryptGetUserKey(hCryptProv, AT_SIGNATURE, hKeyPair)
If lngReturnValue = 0 Then
'Set_locale regionalSymbol
Err.Raise Err.LastDllError, , "DLL error code shown above. Could not obtain key pair"
End If
'Determine the size of the signature
lngReturnValue = CryptSignHash(hHash, AT_SIGNATURE, 0, 0, vbNull, lngSigLength)
If lngSigLength > 0 Then ReDim abSig(lngSigLength - 1)
'Sign the hash object
lngReturnValue = CryptSignHash(hHash, AT_SIGNATURE, 0, 0, abSig(0), lngSigLength)
If lngReturnValue = 0 Then
'Set_locale regionalSymbol
Err.Raise Err.LastDllError, , "DLL error code shown above. Could not sign the hash"
End If
' the signature is now available
' size returned array to signature length
ReDim abSigned(UBound(abSig))
' return the signature to the calling procedure
abSigned = abSig
SignValidate = 0
Else
lngSigLength = UBound(abSigned) + 1
ReDim abSig(UBound(abSigned))
abSig = abSigned ' load the Signature array
'========================================================
'this is the line where the actual validation is done
lngReturnValue = CryptVerifySignature(hHash, abSig(0), lngSigLength, hKeyPair, 0, 0)
'========================================================
If lngReturnValue = 0 Then 'some error occurred
SignValidate = Err.LastDllError
Else
SignValidate = 0
End If
End If
End Function
окон 10 завершает вызов выделенного вызова CryptVerifySignature и возвращает Err.LastDllError, равный NTE_BAD_SIGNATURE. Машина Vista проверяет подлинность подписи.
Я провел дни, исследуя, что может происходить здесь. Все безрезультатно. Любые указатели с благодарностью получил
Является ли Vista машиной 64-бит? – dbugger
Возможно, вам придется использовать атрибуты условной компиляции. Если у вас 64-разрядная версия офиса, версия VBA больше не VBA6, это VBA7. Вызов API/функций несколько отличается. См. Эту статью от MS. https://msdn.microsoft.com/en-us/library/office/ee691831(v=office.14).aspx –
Спасибо за ваши ответы. Машина Vista - 32 бит. Excel 2003 на машине Vista, 32-разрядный Excel 2016 на компьютере с Windows 10. Я считаю, что строка, которая не работает в VBA, является той же строкой, которая не работает в скомпилированной программе VB6, где вызов CryptVerifySignature находится в пользовательской DLL. –