Как я могу объявить функцию без ptrsafe в 64-битной среде?

Моя программа vb6 работала на 32-битной версии. Теперь мне нужно переместить его на 64-битную версию.

Библиотека, которую я объявляю ниже, система, похоже, не может ее получить. Объявляем:

Public Declare Function LogonUser Lib "advapi32.dll" _
Alias "LogonUserA" (ByVal lpszUsername As String, _
ByVal lpszDomain As String, ByVal lpszPassword As String, _
ByVal dwLogonType As Long, ByVal dwLogonProvider As Long, _
phToken As Long) As Long

Public Declare Function ImpersonateLoggedOnUser Lib "advapi32.dll" (ByVal hToken As Long) As Long
Public Declare Function RevertToSelf Lib "advapi32.dll" () As Long
Public Declare Function CloseHandle Lib "kernel32" (ByVal hObject As Long) As Long

Выполнить код:

Public Sub Logon(ByVal strAdminUser As String, ByVal _
    strAdminPassword As String, ByVal strAdminDomain As String)
    Dim lngTokenHandle As Long
    Dim lngLogonType As Long
    Dim lngLogonProvider As Long
    Dim blnResult As Boolean

    lngLogonType = 2
    lngLogonProvider = 0

    blnResult = RevertToSelf()

    blnResult = LogonUser(strAdminUser, strAdminDomain, strAdminPassword, _
    lngLogonType, lngLogonProvider, _
    lngTokenHandle)

    blnResult = ImpersonateLoggedOnUser(lngTokenHandle)
    CloseHandle (lngTokenHandle)

End Sub

Я получил сообщение об ошибке

Error 91:Object variable or With block variable not set

Почти люди говорят, что нужно добавить "ptrsafe" после Declare, но в vb6 нет ptrsafe.

Как я могу объявить функцию lib без ptrsafe в 64-битной и vb6?


person 鄭有維    schedule 15.08.2017    source источник
comment
Это VB6 или VBA? (У вас есть теги на обоих языках, но, похоже, вы обсуждаете VB6. Возможно, люди предложили вам решение VBA, потому что думали, что вы говорите о VBA.)   -  person YowE3K    schedule 15.08.2017
comment
Некоторые комментарии с страницы VB в Википедии могут быть уместными - разработка Visual Basic завершилась с выпуском 6.0, но в 2010 г. Microsoft представила VBA 7 для предоставления расширенных функций и добавления поддержки 64-разрядных версий. И хотя вендор поддерживает Visual Basic 6, и продукт никогда не поддерживался в последних версиях Windows, ключевые части среды все еще работают на новых платформах. Можно получить подмножество среды разработки, работающее с 32-разрядными и 64-разрядными версиями Windows Vista, Windows 7, Windows 8 и Windows 10.   -  person YowE3K    schedule 15.08.2017
comment
Вы не можете скомпилировать VB6 до 64-разрядной версии. VB6 ничего не знает о PtrSafe, LongPtr, LongLong, CLngLng.   -  person ThunderFrame    schedule 15.08.2017
comment
Покажите полный код, который вы используете, иначе вам ничего не поможет.   -  person Giorgio Brausi    schedule 15.08.2017
comment
кто проголосует против моего вопроса? Подскажите где моя ошибка?   -  person 鄭有維    schedule 15.08.2017
comment
@GiorgioBrausi Покажи, спасибо!   -  person 鄭有維    schedule 15.08.2017


Ответы (3)


Почти люди говорят, что нужно добавить "ptrsafe" после Declare, но в vb6 нет ptrsafe. Как я могу объявить функцию lib без ptrsafe в 64-битной и vb6?

VBA должен иметь возможность работать с 64-битной Windows при ее запуске в 64-битном приложении, таком как одна из программ из 64-битного пакета Office.

VB6 работает сам по себе вечно и всегда как 32-битный процесс, ему не нужно знать 64-битную версию, поскольку 64-битная Windows успешно эмулирует 32-битный код без каких-либо дополнительных действий.

Поскольку эти типы, безопасные для указателей, не нужны, используйте 32-битное соглашение (Long) в VB6.

person Alex K.    schedule 15.08.2017
comment
Это ответ, приложение на основе VB6 будет работать как 32-разрядный процесс. - person tcarvin; 15.08.2017
comment
Спасибо за ваш ответ! Но код, работающий под 64-битной версией, кажется, не может понять эту dll? - person 鄭有維; 16.08.2017
comment
вам нужно посмотреть документацию по этим функциям, выяснить, как они возвращают код ошибки, и узнать, что это такое. - person Alex K.; 16.08.2017
comment
Ошибка 91: переменная объекта или не заданная переменная блока кажется проблемой dll? - person 鄭有維; 18.08.2017
comment
Правильный ответ! Просто нужно повторно regrsvr32 все dll, которые мне нужны! - person 鄭有維; 31.08.2017

Ваши объявления функций неверны. Вам не нужно добавлять полный путь к Lib, нужно только имя библиотеки. При добавлении пути ваш код не работает в 32-битной среде ОС, потому что папка "C:\Windows\SysWOW64 не существует в 32-битных системах.

Public Declare Function LogonUser Lib "advapi32.dll" _
Alias "LogonUserA" (ByVal lpszUsername As String, _
ByVal lpszDomain As String, ByVal lpszPassword As String, _
ByVal dwLogonType As Long, ByVal dwLogonProvider As Long, _
phToken As Long) As Long

   Public Declare Function ImpersonateLoggedOnUser Lib "advapi32.dll" (ByVal hToken As Long) As Long

   Public Declare Function RevertToSelf Lib "advapi32.dll" () As Long

   Public Declare Function CloseHandle Lib "kernel32" (ByVal hObject As Long) As Long

См .: https://support.microsoft.com/en-us/help/248187/how-to-impersonate-a-user-from-active-server-pages

person Giorgio Brausi    schedule 15.08.2017
comment
Создайте образец проекта (с исходным кодом DLL), который воспроизводит ошибку, заархивируйте его, затем сделайте общедоступным и поделитесь ссылкой для загрузки zip-архива. - person Giorgio Brausi; 16.08.2017

Поскольку вы говорите о декларациях API, вам может быть полезно следующее. VB6 не распознает тип данных LongLong (64-битное целое число), но его можно подделать с помощью типа данных VB6 Currency. Числа валют фактически хранятся как 64-битные целые числа. Четыре десятичных разряда отображаются на дисплее только после деления фактического числа на 10 000. В зависимости от конкретных вызовов API, которые вы используете, вам может потребоваться иметь двойные объявления API и выбрать правильный во время выполнения. Таким образом, вам также необходимо уметь определять «разрядность» работающей системы.

См. Следующие ссылки:

Определить разрядность

Подделка 64-битных целых чисел

person thx1138v2    schedule 16.08.2017