Использование блока или лямбда С++ для API указателя функции C

Работаю с C API JavaScriptCore, и у меня есть эта подпись указателя функции C:

typedef void
(*JSObjectInitializeCallback) (JSContextRef ctx, JSObjectRef object);

А вот проблемное использование:

JSClassDefinition def = kJSClassDefinitionEmpty;
// This is that previously typed out signature being used
def.initialize = [](JSContextRef ctx, JSObjectRef obj){
  CAMLlocal2(init_context, init_obj);

  init_context = caml_alloc(sizeof(JSContextRef), Abstract_tag);
  init_obj = caml_alloc(sizeof(JSObjectRef), Abstract_tag);
  Store_field(init_context, 0, (value)ctx);
  Store_field(init_obj, 0, (value)obj);
  // Need to call this but can't because class_def is 
  // from the outside and can't be put in the capture list
  //caml_callback2(Field(class_def, 5), init_context, init_obj);
};

Поэтому я не уверен, что это правильный способ обойти это. Я не хочу начинать определять функции C повсюду, потому что мне нужно динамически создавать эти обратные вызовы, и я не уверен, как правильно решить глобальное состояние, потому что это вызовет больше проблем с правильной блокировкой и т. д. Я' m также открыт для использования блоков Objective-C, только блоков, без Objective-C. Видел некоторые упоминания о std::function, но я недостаточно хорошо понимаю C++, чтобы использовать этот API.

Просматривая слой Apple Objective-C поверх JSC, чтобы увидеть, как они это сделали...

EDIT1: нашел эту ссылку как возможное решение, http://p-nand-q.com/programming/cplusplus/using_member_functions_with_c_function_pointers .html, но это довольно глубокое знание C++, в котором мои знания ограничены.

EDIT2: Думаю, мне нужно что-то, чтобы шаблонная магия сгенерировала для меня код?


person Edgar Aroutiounian    schedule 27.06.2016    source источник
comment
Если ваш вопрос связан с использованием Obj-C, добавьте и этот тег.   -  person CinchBlue    schedule 27.06.2016
comment
Если вы можете что-то сделать с помощью обычной функции, вы можете сделать это и с лямбдой без захвата, и наоборот. Захватывающие лямбда-выражения OTOH несовместимы с обычными функциями, поэтому вы не можете взять один и отправить его в место, которое ожидает обычную функцию. Я понятия не имею, что такое блок ObjC, но я подозреваю, что они точно эквивалентны любому типу лямбда-выражений. Кажется, вопрос выиграл бы от перефразирования с точки зрения обычных функций, поскольку лямбды (и блоки ObjC?) Только путают воду, не внося ничего, кроме синтаксического сахара.   -  person n. 1.8e9-where's-my-share m.    schedule 27.06.2016
comment
@VermillionAzure нет, блоки отделены от Objective-C. n.m Я смотрю, сталкивался ли кто-нибудь еще с этим блокпостом и какие решения они придумали.   -  person Edgar Aroutiounian    schedule 27.06.2016
comment
Это довольно распространенная проблема при привязке C++ к таким языкам, как python или lua. В случае lua люди используют библиотеки шаблонов, такие как luabind или luabridge, которые оборачивают более сложные вызовы функций C++ и преобразовывают их в делегаты, соответствующие требуемому typedef. Существует множество способов реализовать эту упаковку. Один хакерский способ состоит в том, чтобы создать своего рода глобальный менеджер ресурсов и оценивать делегаты простого типа указателя функции, обращаясь к глобальному синглтону и вызывая более сложную функцию. Я не знаю деталей привязки JS, YMMV   -  person Chris Beck    schedule 28.06.2016