Newsgroup: it.comp.lang.visual-basic
Titolo: Bit_fields e VB

Hola gente,
vediamo se riesco a trovare qui un po' di conforto...
ho una funzione scritta in una dll C++, questa funzione dovrebbe
restituire due cose, un parametro che gli dico io (e' una callback) ed un
bit-field (ma che roba e'??) che dovrebbe indicarmi l'evento che ha
scatenato la callback.
Che cosa c'e' da sapere su questi bit-field per manovrarli con vb?
lo chiedo perche'ho un grosso problema e non so se possa dipendere da
questo tipo di dati... io ve lo spiego, se poi avete anche voglia di
leggere :-)
Dichiaro una Funzione in un modulo .bas (ad esempio MiaFunzione
(PrimoArgomento as Long, SecondoArgomento as Long) as Long
Alla funzione della dll RegistraFunzione (e' una funzione che permette di
dire alla DLL quale funzione della applicazione chiamare in caso di
eventi), dico RegistraFunzione (AddressOf MiaFunzione, PrimoArgomento)
Quando avviene un evento intercettabile, MiaFunzione dovrebbe essere
chiamata dalla DLL e ricevere come argomenti PrimoArgomento (quello che
avevo passato io) e questo cavolo di bit-field.
Se faccio girare il tutto, la chiamata alla mia funzione viene
effettivamente fatta (ho messo un msgbox all'interno della funzione), ma
appena clicco sull'ok del msgbox, esce fuori il bellissimo messaggio di
errore di Windows:
"Si e' verificato un erroe in Visual Basic. L'applicazione verra' chiusa
ecc.
Segnalazione del problema a microsoft"
Ma che te voi segnala'!?!?
Che pesci prendo?
Ciao e buon fine settimana... Maurizio
-- 
questo articolo e` stato inviato via web dal servizio gratuito 
http://www.newsland.it/news
 segnala gli abusi ad 
ab...@newsland.it

 Ciao e buon fine settimana... Maurizio
Ho in mente 2 "aree" su cui intervenire
1) La "signature" (argomenti e valori di ritorno) della tua funzione callback:
deve corrispondere pari pari al prototipo C (quindi occhio ai tipi di dato e ai
byval/byref).
2) Meglio evitare MsgBox in una callback, per debuggare puoi utilizzare
Debug.Print
Se puoi, posta sia il prototipo C che la definizione VB della funzione callback.
Bye
Raf
-----------------------------------------------------
Funk: cooler than the other side of the pillow.

 Se puoi, posta sia il prototipo C che la definizione VB della funzione
callback.
...
Pronti!!
Allora, dal supporto tecnico di chi produce questa scheda, mi e' arrivato
questo:
StradisDecoder_Decoder_RegisterEventCallBack64(hDecoder, EventFunction,
hDecoder);
che divrebbe corrispondere piu' o meno a questo prototipo:
int Decoder_RegisterEventCallBack(StradisDecoderEventFunction function,
 CALLBACKPARAM param);
Come si puo' notare, la funzione e' leggermente differente, infatti quella
chiamata finisce con 64 (dovrebbe restituire un numero a 64 bit), ed ha un
argomento in piu', il primo, che contiene l'handle della scheda (o meglio
della funzione che ha aperto il drivre della scheda.
Ho provato anche a chiamare la funzione senza il 64; senza mettere come
primo argomento l'handle alla scheda, non va per niente; mettendolo,
funziona ma poi viene fuori il solito errore.
per quel che mi riguarda, dichiaro questa funzione nel modo seguente:
 Private Declare Function StradisDecoder_Decoder_RegisterEventCallBack64
Lib "StradisDEcoder.dll" (ByVal hsettings As Long, ByVal Funzione As Long,
ByVal Indirizzo As Long) As Long
e la chiamo in questo modo:
Indirizzo = StradisDecoder_Decoder_RegisterEventCallBack64(HandleDecoder,
AddressOf Funzione, HandleDecoder)
chiaramente HandleDecoder e' un long.
Ancora, il supporto mi porta un esempio della funzione che la dll
chiamera' in caso di un evento registrato:
void STRADISCALLMETHOD EventFunction(CALLBACKPARAM param, __int64
qwEvents)
che io invece dichiaro cosi':
Public Function Funzione(ByVal Indirizzo As Long, ByVal Evento As Currency)
Evento e' dichiarato Currency se chiamo la versione a 64 bit, mentre Long
se uso la versione a 32
Nella funzione scrivo questo:
MsgBox "Funzione: Indirizzo: " & Indirizzo & "   Evento: " & Evento
Ed effettivamente nella msgbox appaiono i valori di ritorno, ma appena
faccio click su ok, esce fuori l'errore incirminato.
Per cio' che dici riguardo l'utilizzo del debug.print, ho anche questo,
subito dopo il msgbox
Debug.Print "Indirizzo: " & Indirizzo & "   Evento : " & Evento
Ma qui non ci arriva, l'errore avviene tra il msgbox e l'istruzione
debug.print.
Avevo infatti aggiunto il msgbox proprio perche' non riuscivo ad
utilizzare il metodo debug.print
Scusate se mi sono dilungato, ma non sarei riuscito a spiegarmi senza
dovre scrivere tutto.
Grazie ancora.. Maurizio


 Se puoi, posta sia il prototipo C che la definizione VB della funzione
callback.
...
Ricominciamo, ho trovato qualche cosa in piu', le definizioni in C
Per registrare la funzione che la dll chiamera':
void StradisDecoder_Decoder_RegisterEventCallBack(STRADISDECODER hDecoder,
StradisDecoderEventFunction function, CALLBACKPARAM param);
Ed io rispondo cosi':
Private Declare Function StradisDecoder_Decoder_RegisterEventCallBack Lib
"StradisDEcoder.dll" (ByVal hSettings As Long, ByVal Funzione As Long,
ByVal Indirizzo As Long) As Long
Visto che nel prototipo in C, il tutto inizia con Void, ho porvato a
togliere as Long nella dichiarazione della funzione, ma va subito in errore
e poi:
The CallBack function should be specified as follows:
int STRADISCALLMETHOD function(CALLBACKPARAM param, unsigned long
dwEvents);
ed io dichiaro una funzione in questo modo :
Public Function Funzione(ByVal Indirizzo As Long, ByVal Evento As Long) As
Long
e questa e' la modalita' in cui il tutto va piu' avanti.
Cosi' strutturata, la mia funzione viene chiamata, il debug.print viene
chiamato (questa e' una novita'), ma appena interrompo l'esecuzione (sia
con il comando End dell'ide, sia scaricando il form pricipale con unload)
del programma, esce fuori l'errore maledetto.
Bohh


 debug.print.
E infatti il problema è proprio MsgBox. Non devi mai usarla in una callback (né
mostrare altre finestre).


 Bohh
Mmmm... non č che prima di terminare il programma sia necessario chiamare una
funzione di "unregister" del callback?


 E infatti il problema è proprio MsgBox. Non devi mai usarla in una callback 
...
Provato anche a toglierla, non e' quello il problema ( o almeno non solo).
Se vedi, ho messo un altro post su questo 3ad dove indico meglio la
documentazione che ho.
Grazie ancora


 funzione di "unregister" del callback?
...
Si, fatto anche quello, nell'evento Class_Terminate della classe che
gestisce la dll ho inserito anche la funzione di unregister, ma
l'applicazione si ferma prima, l'errore e' precedente.


 l'applicazione si ferma prima, l'errore e' precedente.
In che senso "l'applicazione si ferma prima"?
Chiaramente se premi il pulsante di stop dell'IDE di VB ti scavi la fossa da
solo perché il Class_Terminate verosimilmente non verrà chiamato.
Idem se non rilasci esplicitamente tutte le istanze della classe e ti affidi
all'istruzione End per terminare il programma.
Insomma, devi essere certo al 100% che prima della terminazione del programma
venga chiamata la unregister (e che venga chiamata con i parametri giusti,
naturalmente).


 In che senso "l'applicazione si ferma prima"?
...
Nel senso che ho messo un Button sul form principale, il classico Exit, e
la prima cosa che gli faccio fare e':
Set MioOggetto = Nothing
dove chiaramente MioOggetto fa riferimento alla classe che gestisce la
scheda.
Ho messo un breakpoint su questa istruzione, ma anche premendo il pulsante
di uscita, l'applicazione qui non ci arriva, ma va in errore prima.
Dove? Boh!


 Dove? Boh!
Ti farò qualche altra domanda per cercare di diagnosticare meglio il problema:
- cosa fai nella routine callback? eventualmente posta il codice completo. Tieni
presente che qui dentro, oltre a non poter mostrare msgbox, probabilmente non
puoi nemmeno aprire dei form.
- vuoi dire che nella sub (ad es.) cmdExit_Click la prima istruzione in assoluto
è Set ... = Nothing ma premendo il bottone il programma schianta prima ancora di
arrivarci?


 arrivarci?
...
Gia' :-(


 Gia' :-(
Mmmmm... prova a mettere debug.print prima di ogni istruzione, anziché un
breakpoint, per capire dove capita l'errore.
Altra cosa: riesci ad avere informazioni piů approfondite sull'"access
violation"? Es: codice, DLL o modulo in cui si verifica...
In ultimo, prova ad isolare il problema creando un progetto VB in cui esegui
solo le chiamate alla DLL.
Mi immagino un form con 2 pulsanti "Registra" e "Deregistra" e un listbox, piů
un modulo VB con la funzione callback che ogni volta che viene chiamata accoda
un nuovo elemento al listbox.
-- 


 un nuovo elemento al listbox.
...
Beh, intanto dovrei dirgli anche di fare qualche cosa, altrimenti gli
eventi non li scatena mai.


 eventi non li scatena mai.
Sě scusami, pensavo si capisse che negli eventi click dei pulsanti Registra e
Deregistra volevo metterci le chiamate alle funzioni della DLL che registrano e
deregistrano il callback.
Ciao

 Ciao


 deregistrano il callback.
...
Si si, era chiaro cosa volessi dire, ma effettivamente non mi sono
spiegato bene io.
registra e deregistra, non mandano nulla indietro, niente callback.
Per "ricevere" qualche cosa, dovrei dire alla scheda di far qualche cosa,
come ad esempio mandare in play il flusso video, ed e' proprio cio' che
faccio nel progettino di prova.


 cio' che faccio nel progettino di prova.
Ok, ora ho capito: devi in qualche modo "triggerare".
Comunque mi sa che ho finito le "frecce".
Se hai controllato e sei sicuro che la "signature" della funzione callback VB
corrisponde esattamente a quella del prototipo C, l'ultima possibilitą č
compilare il programma di test semplificato al massimo con l'opzione "generate
debug symbols" e poi debuggarlo nell'IDE di Visual C++, sperando che l'access
violation sia replicabile.
Altro non saprei...
Ciao
Raf

 violation sia replicabile.
...
Naaa, non e' roba per me!
Mai visto ne il C, ne tantomeno il C++
Grazie comunque, sei stato gentilissimo!
