LINUX.ORG.RU

C++ — приведение типов


0

1

Есть некий объект Capture, один из методов которого передаётся как callback (использую libpcap, а коллбэк передаётся в pcap_dispatch()). У pcap_dispatch() первый аргумент — пользовательский указатель. Чтобы применить эту хрень к объекту, я объявляю класс с методом packetHandler() без этого первого аргумента; вместо него как раз передаётся this.

потом запускаю:

pcap_dispatch(iface,
    65536,
    (void (*)(uchar *, const pcap_pkthdr *, const uchar *))&Capture::packetHandler,
    (uchar *)this);

вот заголовок pcap_dispatch():

typedef void (*pcap_handler)(u_char *user, const struct pcap_pkthdr *h, const u_char *bytes);

int pcap_dispatch(pcap_t *p, int cnt, pcap_handler callback, u_char *user);

g++ 4.4.3 воспринимает это нормально, но когда я решил скомпилить на 3.3.6, возникла ошибка. попробовал немного запариться, но без особых успехов.


Неправильно, может падать в зависимости от платформы (версии ABI).

Сделай статический метод, либо лучше extern «C» status функцию с сигнатурой для pcap. В ней сделай typecast для получения this и вызова метода.

ly
()
Ответ на: комментарий от ly

Про status-функцию не понял, что ты имеешь в виду. Пробую для начала

void *ptr = reinterpret_cast<void *>(&Capture::packetHandler);
Это одна из тех вещей, которую хавает только новый G++.

unnamed
() автор топика
Ответ на: комментарий от ly

Понимаю, что Страуструп убил бы за такое, но платформа будет сугубо определённая. А делать статический метод — лень всё переписывать. Можно, конечно, синглтон попробовать сделать... Вся фишка в том, что объектность исполнения позволяет использовать сигналы и слоты в Qt без извращений :)

unnamed
() автор топика
Ответ на: комментарий от unnamed

Синглтон — то же самое извращение, кстати: придётся для instance event-ы слать или invokeMethod() использовать.

unnamed
() автор топика
Ответ на: комментарий от unnamed

>делать статический метод — лень всё переписывать

Ничего не придется переписывать, тем более у тебя уже есть packetHandler().

(void (*)(uchar *, const pcap_pkthdr *, const uchar *))&Capture::packetHandler

Это вообще пять.

yoghurt ★★★★★
()
Ответ на: комментарий от unnamed

>Про status-функцию не понял...

очепятался s/status/static/

ly
()
Ответ на: комментарий от unnamed
class Brainfuck {
protected:
    void handler(const struct pcap_pkthdr *h, const u_char *bytes);
public:
    static void pcap_handler(u_char *user, const struct pcap_pkthdr *h, const u_char *bytes)
    {
        Brainfuck *my = (Brainfuck*) user;
        my->handler(h, bytes);
    }
}

pcap_dispatch(..., pcap_handler, (u_char*) this);
ly
()
Ответ на: комментарий от ly

Да, я уже понял, спасибо. Это самый сильный тупизм в моей карьере. Просто в то время, когда писал, не вспомнил про все эти invokeMethod()

unnamed
() автор топика
Ответ на: комментарий от unnamed

То есть, фактически, в моём классе можно даже без обёртки обойтись и сделать всё из static. Пока не вижу этому препятствий.

unnamed
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.