Quindi, su quale base dovrei decidere se usare pthread_self orgettid per determinare quale thread sta eseguendo la funzione?
Dovresti sempre usare pthread_self()
ogni volta che vuoi identificare un thread all'interno della tua applicazione. gettid()
può essere utilizzati per determinati scopi e se sai che è Linux. Ad esempio, gettid()
può essere usato per ottenere il seme per un seme specifico del thread (usato in srand()
).
Entrambi non sono portatili.
Questo non è del tutto vero. gettid()
non è portatile in quanto è una funzione specifica di Linux. Ma pthread_self()
è portatile fintanto che non si fanno supposizioni sulla sua rappresentazione.
Ad esempio, quanto segue è not portatile.
printf("Thread ID is: %ld", (long) pthread_self());
poiché non c'è alcuna garanzia che qualunque pthread_self()
sarà un numero intero di qualche tipo. Ma
pthread_t my_tid; //filled elsewhere
pthread_t tid = pthread_self();
if( pthread_equal(my_tid, tid) ) {
/* do stuff */
}
è completamente portatile.
Il primo non è portabile perché presuppone quell'id del thread è un numero intero mentre quest'ultimo no.
Perché ci sono due diverse funzioni per ottenere l'ID del thread?
Non sono due modi diversi per ottenere lo stesso valore. Uno (pthread_self()
è fornito dalla libreria dei thread (pthreads) mentre l'altro (gettid()
è una funzione specifica del sistema operativo. Un sistema operativo diverso può fornire un'interfaccia/chiamata di sistema differente per ottenere un ID thread simile a gettid()
. Quindi non puoi fare affidamento su gettid()
in un'applicazione portatile.
pthread_self() returns the process-wide unique pthread-id.
gettid() restituisce il thread-id univoco (specifico dell'implementazione pthread) a livello di sistema (su Linux).
the TID(thread id) returned by gettid() is unique inside a process
Sì.
(or inside a program with multiple processes,
Sì.
inside a process, different thread has different thread id.
Sì.
the TID returned by pthread_self() is unique across processes,
No.
different thread has different TID on the same machine at the same time.
Sì nello stesso processo, No su tutta la macchina.
Poiché gettid() è specifico di Linux e quindi non portabile, l'unico modo per identificare ampiamente un pthread dal sistema è utilizzare il suo id di processo genitore (univoco a livello di sistema) come restituito da getpid() insieme al suo pthread- (univoco a livello di processo) id restituito da pthread_self().
Questo è uno studio interessante sulla differenza tra concettuale terminologia e entità software reali (che appartengono a specifiche astrazioni software).
Prima di tutto, fai attenzione ai tipi di queste due chiamate.
pid_t gettid(void);
pthread_t pthread_self(void);
Uno è pid_t
e l'altro è pthread_t
. Entrambi si riferiscono a un'entità concettuale comune chiamata thread
, ma i diversi tipi implicano che si tratta di due diversi software entities
. Sono diverse rappresentazioni di un thread id
, e ha senso all'interno dell'astrazione software che lo incorpora. Quindi, pthread_t
ha solo senso all'interno dell'astrazione supportata dal pthread
pacchetto e pid_t
ha senso all'interno dell'astrazione che incorpora questo tipo (ovvero chiamate di sistema Linux che trattano pid_t
).
Dovresti utilizzare il tipo corretto in base al contesto. Usa pthread_t
nel contesto che richiede il tipo pthread_t
e pid_t
nel contesto che richiede pid_t
- indipendentemente dal fatto che possano fare riferimento allo stesso thread.
Ciascuno di questi contesti ha prescritto la sintassi per il confronto e l'uguaglianza. pid_t
può essere confrontato direttamente con ==
operatore, mentre pthread_t
deve essere confrontato invocando pthread_equal
.
La ragione di questa doppia rappresentazione/astrazioni software è che il pthread
library è una libreria di thread portatile che può essere implementata su diversi sistemi operativi. Diverse implementazioni del pthread
library garantisce che il thread id
il tipo sarà sempre pthread_t
. Questi thread possono essere associati a un thread entity
specifico del sistema operativo il cui identificatore del sistema operativo dipende dal sistema operativo (ad esempio per Linux è pid_t
; per Windows è DWORD
).
Quindi, sebbene l'implementazione sottostante possa differire da sistema operativo a sistema operativo, il codice scritto rispetto a pthread
l'astrazione rimane portabile su tutti i sistemi operativi (a patto che ti limiti al pthread
astrazione).