2013-08-13 4 views
7

Le funzioni OpenGL sono definite come se funzionassero in modo sincrono. Ma le funzioni di rendering (e altre) saranno spesso eseguite in modo asincrono dalla GPU. OpenGL nasconderà efficacemente questo: se fai qualcosa che richiede i risultati di un'operazione (come la lettura da un framebuffer a cui è stato eseguito il rendering), OpenGL interromperà le operazioni della CPU finché la GPU non avrà raggiunto quel punto.C'è un modo per dire se un'operazione OpenGL è finita?

Questo è funzionale, ma difficilmente ideale per le prestazioni, poiché la CPU praticamente blocca fino a quando la GPU non viene completata. C'è un modo per determinare se una particolare operazione è stata completata, in modo che tu sappia che un'operazione dipendente verrà eseguita senza così tanto blocco della CPU?

risposta

6

Sì, c'è. Supponendo che tu abbia accesso a OpenGL 3.2+ o all'estensione ARB_sync.

Se si desidera sapere quando un particolare comando è terminato, è possibile inserire una "fence" sync object nello stream di comandi immediatamente dopo l'emissione di tale comando. Questo viene fatto con lo glFenceSync function.

È necessario memorizzare il puntatore restituito da questa funzione. Con quel puntatore in mano, puoi chiedere se il recinto è completato controllando se il recinto è segnalato con lo glGetSync function. Come questo:

GLint isSignaled = 0; 
glGetSync(syncObj, GL_SYNC_STATUS, 1, NULL, &isSignaled); 

if(isSignaled == GL_SIGNALED) 
{ 
    //Prior commands have completed. 
} 
else 
{ 
    //Not done yet. 
} 

Se sei a corto di altre cose da fare, non è necessario attendere che l'oggetto di sincronizzazione per finire; puoi semplicemente fare qualunque processo OpenGL tu voglia fare. Ciò indurrà il blocco della CPU per te.

Una volta terminato con l'oggetto di sincronizzazione, è necessario cancellarlo . Utilizzare lo glDeleteSync function per farlo.

+0

Ottima domanda. Ma va bene sia chiedere e rispondere allo stesso tempo? ;) Inoltre, un controllo di sincronizzazione non può aggiungere ulteriori overhead inutili alla pipeline? –

+1

@MichaelIV: "* Ma va bene sia chiedere e rispondere allo stesso tempo? *" Sì. Questo è il motivo per cui, quando fai una domanda, c'è una casella in fondo che ti permette di rispondere proprio lì prima di chiederla. Per quanto riguarda l'aggiunta di "overhead inutile", le recinzioni dovrebbero essere abbastanza leggere. I processi interni del driver usano sempre le fence, in modo che * loro * possano dire quando hai finito con un oggetto buffer e così via. –