SQLite UDF - обратный вызов VBA

Кто-нибудь пытался передать функцию VBA (или VB6) (через AddressOf?) В SQLite, чтобы создать функцию UDF (http://www.sqlite.org/c3ref/create_function.html).

Как VBA будет обрабатывать результирующие аргументы обратного вызова?

Вызываемая функция будет иметь следующую сигнатуру ...

void (xFunc) (sqlite3_context, int, sqlite3_value **)

Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
4
0
1 851
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

К сожалению, вы не можете использовать функцию VB6 / VBA в качестве обратного вызова напрямую, поскольку VB6 генерирует только функции stdcall, а не функции cdecl, которые ожидает SQLite.

Вам нужно будет написать C dll для проксирования вызовов туда и обратно или перекомпилировать SQLite для поддержки вашего собственного расширения.

После перекомпиляции вашей dll для экспорта функций как stdcall вы можете зарегистрировать функцию с помощью следующего кода:

'Create Function
Public Declare Function sqlite3_create_function Lib "SQLiteVB.dll" (ByVal db As Long, ByVal zFunctionName As String, ByVal nArg As Long, ByVal eTextRep As Long, ByVal pApp As Long, ByVal xFunc As Long, ByVal xStep As Long, ByVal xFinal As Long) As Long

'Gets a value
Public Declare Function sqlite3_value_type Lib "SQLiteVB.dll" (ByVal arg As Long) As SQLiteDataTypes    'Gets the type
Public Declare Function sqlite3_value_text_bstr Lib "SQLiteVB.dll" (ByVal arg As Long) As String        'Gets as String
Public Declare Function sqlite3_value_int Lib "SQLiteVB.dll" (ByVal arg As Long) As Long                'Gets as Long

'Sets the Function Result
Public Declare Sub sqlite3_result_int Lib "SQLiteVB.dll" (ByVal context As Long, ByVal value As Long)
Public Declare Sub sqlite3_result_error_code Lib "SQLiteVB.dll" (ByVal context As Long, ByVal value As Long)

Public Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (dest As Any, source As Any, ByVal bytes As Long)

Public Property Get ArgValue(ByVal argv As Long, ByVal index As Long) As Long
    CopyMemory ArgValue, ByVal (argv + index * 4), 4
End Property

Public Sub FirstCharCallback(ByVal context As Long, ByVal argc As Long, ByVal argv As Long)
    Dim arg1 As String
    If argc >= 1 Then
        arg1 = sqlite3_value_text_bstr(ArgValue(argv, 0))
        sqlite3_result_int context, AscW(arg1)
    Else
        sqlite3_result_error_code context, 666
    End If
End Sub

Public Sub RegisterFirstChar(ByVal db As Long)
    sqlite3_create_function db, "FirstChar", 1, 0, 0, AddressOf FirstCharCallback, 0, 0
    'Example query: SELECT FirstChar(field) FROM Table
End Sub

Мне удалось найти удобную оболочку stdcall, которая также преобразует c arraya в безопасные массивы и т. д., Поэтому вызов функций без обратного вызова работает нормально, это как обрабатывать c-подобные структуры, возвращаемые обратным вызовом, это моя следующая проблема. Как вы сказали, VBA вполне может задохнуться до того, как будет достигнута эта точка.

gobansaor 16.09.2008 13:36

Мне удалось изменить оболочку SQLite3VB для поддержки stdcall из определенных функций. Поскольку мои изменения были довольно сложными, я опубликовал только код VB. Если вам нужны изменения, которые я внес в исходный код SQLite, отправьте электронное письмо, чтобы я мог его отправить. Может быть, после того, как вы сможете разместить в своем блоге?

rpetrich 18.09.2008 12:05

Отлично, именно то, что я искал! Было бы здорово, если бы вы могли отправить изменения исходного кода SQLite на «tom at gobansaor.com». Я собираю вместе различные фрагменты кода SQLite / ExcelVBA, которые затем опубликую в своем блоге, и обязательно упомяну вас, когда это сделаю.

gobansaor 22.09.2008 16:26

Другие вопросы по теме