Pagina 1 di 2 1 2 ultimoultimo
Visualizzazione dei risultati da 1 a 10 su 11

Discussione: [c++]callback

  1. #1
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826

    [c++]callback

    ciao.
    Ho una libreria(opencl)con varie funzioni che accettano come parametro una callback.
    Questa callback viene richiamata a seconda di alcuni eventi , ad es finish quando si è finito di calcolare sulla gpu.
    Sto creando un piccolo application framework per opencl e vorrei sapere se nel parametro che accetta la callback posso in qualche modo usare una std::function.
    Posso ad es avvolgere la callback in una std::function e poi in qualche modo passare l'indirizzo della function?
    Vorrei utilizzare la std::function per svariati motivi, volevo pero' assicurarmi che essa accetti, o possa puntare a una function to member di una determinata classe.
    Shodan mi aveva suggerito per questo di utilizzare mem_fun.
    grazie.

  2. #2
    "callback" è termine generico per indicare una funzione che viene richiamata... di che tipo sono i callback della libreria in questione? Puntatori a funzione? Parametro template? std::function? Altro ancora?
    Amaro C++, il gusto pieno dell'undefined behavior.

  3. #3
    Utente di HTML.it
    Registrato dal
    Sep 2012
    Messaggi
    707
    Mai usato opencl, std::function o mem_fn, non capisco però quando dici: "vorrei sapere se nel parametro che accetta la callback posso in qualche modo usare una std::function"

    Intendi il parametro della funzione dove tu passi la callback a opencl? Qui dovrai passare una funzione con la firma decisa dall'api opencl, non puoi passargli qualcos'altro.

    Oppure intendi il classico "void *userdata" che di solito è un ulteriore parametro (oltre al parametro callback) che la libreria richiede, per essere poi passato indietro alla callback in fase di chiamata per creare una sorta di contesto utente?

  4. #4
    Utente di HTML.it L'avatar di shodan
    Registrato dal
    Jun 2001
    Messaggi
    2,381

    Re: [c++]callback

    Originariamente inviato da giuseppe500
    Sto creando un piccolo application framework per opencl e vorrei sapere se nel parametro che accetta la callback posso in qualche modo usare una std::function.
    Posso ad es avvolgere la callback in una std::function e poi in qualche modo passare l'indirizzo della function?
    Assolutamente no. Se il parametro callback è un puntatore a funzione, quello gli devi dare.

    Vorrei utilizzare la std::function per svariati motivi, volevo pero' assicurarmi che essa accetti, o possa puntare a una function to member di una determinata classe.
    Shodan mi aveva suggerito per questo di utilizzare mem_fun.
    grazie.
    Non ricordo il contesto esatto, ma se ti serviva per questo sei completamente fuori strada.
    Mostra la parte di codice a cui ti riferisci, così ci capiamo meglio.
    This code and information is provided "as is" without warranty of any kind, either expressed
    or implied, including but not limited to the implied warranties of merchantability and/or
    fitness for a particular purpose.

  5. #5
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826
    ciao.
    questo è il codice che mi interessa:
    codice:
    void CL_CALLBACK checkData(cl_event event, cl_int status, void* data) {
    
       int i;
       cl_bool check;
       int *buffer_data;
    
       buffer_data = (int*)data;
       check = CL_TRUE;
       for(i=0; i<100; i++) {
          if(buffer_data[i] != 2*i) {
             check = CL_FALSE;
             break;
          }  
       }
    }
    void fx()
    {
    .
    .
    .
    cl::Event callbackEvent;
    queue.enqueueReadBuffer(buffer, CL_FALSE, 0, sizeof(data), 
        data, NULL, &callbackEvent);
    
    // Setta la callback &checkData che viene richiamata quando è finito il processo di             //caricamento di sopra
      callbackEvent.setCallback(CL_COMPLETE, &checkData, (void*)data);
    volevo fare puntare la callback a una funzione di una classe membro, è possibile?
    e se è possibile, è possibile utilizzare un std::functional o std::mem_fn che puntano alla callback?
    per potere inserire in un vector le varie function e usare il bind, in modo da poterle gestire all evenienza come si vuole.

    grazie.
    ciao.

  6. #6
    Così ad occhio ti direi che quei callback sono dei puntatori a funzione, per cui non puoi passarci né std::function né puntatori a metodi. Quello che però puoi fare è usare una funzione "fissa" come callback e passare tramite il parametro user_data di setCallback un puntatore all'std::function che questa dovrà chiamare.
    Amaro C++, il gusto pieno dell'undefined behavior.

  7. #7
    Utente di HTML.it
    Registrato dal
    Sep 2012
    Messaggi
    707
    Aggiungo una cosa. Ma questi std::function ti incapsulano anche l'oggetto su cui chiamare il metodo? Perché nel caso non lo facessero (a meno che tu non abbia altri modi tipo "l'oggetto è globale") non ti conviene passare in "void *user_data" direttamente l'oggetto (invece che la funzione) e poi nella callback checkData chiami il metodo della classe? E anche se std::function incapsulasse l'oggetto su cui chiamare il metodo, sinceramente non vedo la ragione di passare la funzione invece dell'oggetto.

    Cioè:
    codice:
    void CL_CALLBACK checkData(cl_event event, cl_int status, void* data) {
        MyObject *obj = (MyObject *)data;
        obj->myfunction(....);
    }
    
    callbackEvent.setCallback(CL_COMPLETE, &checkData, (void*)obj);
    P.S. Se ti serve ancora quell' "int *buffer_data" ovviamente puoi agganciarlo a un nuovo campo di MyObject oppure fai una struttura con 2 campi (uno per per l'int *buffer_data e l'altro per l'oggetto). Tuttavia la struttura la dovresti allocare/disallocare, ti conviene appoggiarti a un campo dell'oggetto che invece esiste già.

  8. #8
    Utente di HTML.it L'avatar di shodan
    Registrato dal
    Jun 2001
    Messaggi
    2,381
    Originariamente inviato da c0der
    Aggiungo una cosa. Ma questi std::function ti incapsulano anche l'oggetto su cui chiamare il metodo?
    Si. std::function nasce per dare un'interfaccia comune a funzioni normali, indipendentemente dalla convenzione di chiamata (__stdcall, cdecl etc), a funzioni membro (tramite mem_fun), lamdba function e function objects in genere. Ma non è che questo significhi poterle passare come puntatore a funzione come (da quanto ho capito) era nelle intenzioni dell'OP.

    non ti conviene passare in "void *user_data" direttamente l'oggetto (invece che la funzione) e poi nella callback checkData chiami il metodo della classe?
    In effetti è quello che si fa di solito (quando almeno c'è un campo void* da qualche parte).
    Tra l'altro fare il cast a void* di una qualsiasi funzione è illegale per lo standard e il fatto che VC++ non se ne curi e lo consenta comunque, non è proprio il massimo.
    This code and information is provided "as is" without warranty of any kind, either expressed
    or implied, including but not limited to the implied warranties of merchantability and/or
    fitness for a particular purpose.

  9. #9
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826
    La mia idea di passare le function come puntatore a funzione era completamente sbagliata, adesso ho capito.
    Ma con quello che mi avete spiegato posso fare cio che volevo fare.
    grazie.

  10. #10
    Utente di HTML.it L'avatar di shodan
    Registrato dal
    Jun 2001
    Messaggi
    2,381
    Giusto per aggiungere un po' di carne al fuoco: se hai anche la necessità di dover installare più callback per differenziare in modo da differenziare il comportamento per esigenze specifiche, ricorda che puoi passare anche un oggetto polimorfico come parametro.
    In questo modo non hai mille mila callback da scrivere, ma solo una per tutti.

    Altra cosa: le eccezioni (se sollevate) non devono uscire dalla callback.
    Ti consiglio di modificare la callback così:

    codice:
    void CL_CALLBACK checkData(cl_event event, cl_int status, void* data) {
        try {
            MyObject *obj = (MyObject *)data;
            obj->myfunction(....);
        } catch (const std::exception& e) {
            // eventuale informazione da portare all'esterno tramite myObject
        }
    }
    This code and information is provided "as is" without warranty of any kind, either expressed
    or implied, including but not limited to the implied warranties of merchantability and/or
    fitness for a particular purpose.

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2025 vBulletin Solutions, Inc. All rights reserved.