Domanda

Ho un'applicazione che consiste di diversi moduli scritti in C ++.
Uno dei moduli si intende per la gestione di attività distribuite su Sungrid Engine. Esso utilizza l'API per DRMAA Sottoporre e la griglia di monitoraggio jobs.If il cliente non supporta griglia, macchina locale dovrebbero essere usati
L'oggetto condiviso della libdrmaa.so API è legata in fase di compilazione e caricato durante l'esecuzione.
Se il client utilizza la mia domanda è questa ".so" tutto va bene, ma nel caso in cui il cliente non ha che, la chiusura dell'applicazione non riuscire a caricare le librerie condivise.
Per evitare questo, ho sostituito le chiamate API con puntatori funzione ottenuta utilizzando dlsym () e dlopen (). Ora posso usare la macchina locale anzichè griglia se la chiamata a dlopen non lo fa riesce e il mio obiettivo è raggiunto.
Il problema ora è che l'applicazione ora gira con successo per i piccoli casi di test, ma con casi di test più grandi getta errore di segmentazione mentre lo stesso codice utilizzando il caricamento dinamico funziona correttamente.

Mi sto perdendo qualcosa durante l'utilizzo dlsym () e dlopen ()?
C'è un altro modo per raggiungere lo stesso obiettivo?

Qualsiasi aiuto sarebbe apprezzato.

Grazie,

È stato utile?

Soluzione

E 'molto improbabile che sia un problema diretto con il codice caricato tramite dlsym() -. Nel senso che il carico dinamico rende seg-guasto

Che cosa si può fare è di esporre un problema a parte, probabilmente spostando i dati. Questo probabilmente significa un puntatore randagio (non inizializzato) che punta da qualche parte 'legittima', nel caso di collegamento statico, ma da qualche altra parte, nel caso di collegamento dinamico - e da qualche altra parte fa scattare il seg-colpa. In effetti, questo è un vantaggio per voi nel lungo periodo -. Dimostra che v'è un problema che altrimenti potrebbe rimanere silente per un lungo periodo di tempo

Lo considero particolarmente probabile dal momento che si parla che si verifica con il test più grandi e non con quelli di piccole dimensioni.

Altri suggerimenti

Come dice Jonathan Leffler, il problema molto probabilmente esiste nel caso in cui si utilizza direttamente l'API; semplicemente non ha ancora causato un crash.

Il primo passo quando si ottiene un SIGSEGV dovrebbe essere analizzando il core dump risultante (o semplicemente eseguire l'applicazione direttamente sotto debugger), e guardando , dove si è schiantato. Scommetto $ 0.02 che è schiantarsi da qualche parte dentro malloc o free, nel qual caso il problema è semplice danneggiamento vecchio mucchio, e ci sono molti strumenti di heap-checker disponibili per aiutarti a prenderlo. Solaris fornisce watchmalloc , che è un buon inizio.

Se si sta gettando un'eccezione attraverso una funzione extern "C", allora l'applicazione deve smettere. Questo perché il C ABI non ha le strutture per propagare eccezioni.

Per contrastare questo fenomeno quando si utilizza DLL (o librerie condivise) si ha normalmente una funzione di una C che restituisce oggetto di un C ++. Poi l'interazione rimanente è con l'oggetto C ++ che è stato restituito dalla DLL.

Questo modello suggerisce (e sottolineo suggerisce) una fabbrica come oggetto, quindi la DLL dovrebbe avere una singola funzione extern "C" che restituisce un void *, che si può reinterpret_cast <> di nuovo in un C ++ oggetto factory.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top