Dalam program linux c, bagaimana cara mencetak id thread dari sebuah thread yang dibuat oleh pthread library?
sebagai contoh: kita bisa mendapatkan pid dari sebuah proses dengangetpid()
Dalam program linux c, bagaimana cara mencetak id thread dari sebuah thread yang dibuat oleh pthread library?
sebagai contoh: kita bisa mendapatkan pid dari sebuah proses dengangetpid()
Jawaban:
pthread_self()
fungsi akan memberikan id utas utas saat ini.
pthread_t pthread_self(void);
The pthread_self()
mengembalikan fungsi pthread pegangan thread menelepon. Fungsi pthread_self () TIDAK mengembalikan utas integral utas pemanggil. Anda harus menggunakan pthread_getthreadid_np()
untuk mengembalikan pengenal integral untuk utas.
CATATAN:
pthread_id_np_t tid;
tid = pthread_getthreadid_np();
jauh lebih cepat daripada panggilan ini, tetapi memberikan perilaku yang sama.
pthread_id_np_t tid;
pthread_t self;
self = pthread_self();
pthread_getunique_np(&self, &tid);
pthread_threadid_np
. Saya perlu menggunakan untuk sebuah proyek, jadi perlu memeriksa keandalan API itu di platform iOS dan OSX. Merujuk tautan di opensource.apple.com/source/Libc/Libc-583/pthreads/pthread.h tetapi tidak yakin apakah itu yang benar.
_np
berarti non-portabel. Linux memiliki _np
barang - barangnya sendiri , tetapi tidak termasuk milik Apple pthread_getthreadid_np
.
Apa? Orang tersebut meminta untuk spesifik Linux, dan yang setara dengan getpid (). Bukan BSD atau Apple. Jawabannya adalah gettid () dan mengembalikan tipe integral. Anda harus memanggilnya menggunakan syscall (), seperti ini:
#include <sys/types.h>
#include <unistd.h>
#include <sys/syscall.h>
....
pid_t x = syscall(__NR_gettid);
Meskipun ini mungkin tidak portabel untuk sistem non-linux, threadid ini secara langsung dapat dibandingkan dan sangat cepat untuk diperoleh. Dapat dicetak (seperti untuk LOG) seperti bilangan bulat biasa.
getpid()
diberikan sebagai contoh. Itu tidak mengatakan bahwa semantik adalah spesifikasi yang sulit. Membuat orang sadar melakukan sesuatu dengan cara yang kompatibel dengan POSIX sehingga komunitas lain selain Linux (seperti FreeBSD, Illumos, OS X, dll.) Dapat mengambil keuntungan darinya bukanlah "pamer". Seperti yang saya katakan, saya kira Linux benar-benar telah menjadi Windows berikutnya.
Seperti dicatat dalam jawaban lain, pthreads tidak menentukan cara yang tidak bergantung platform untuk mengambil ID utas integral.
Pada sistem Linux, Anda bisa mendapatkan ID utas sebagai berikut:
#include <sys/types.h>
pid_t tid = gettid();
Pada banyak platform berbasis BSD, jawaban https://stackoverflow.com/a/21206357/316487 ini memberikan cara non-portabel.
Namun, jika alasan Anda merasa memerlukan ID utas adalah untuk mengetahui apakah Anda menjalankan utas yang sama atau berbeda ke utas lain yang Anda kontrol, Anda mungkin menemukan beberapa utilitas dalam pendekatan ini.
static pthread_t threadA;
// On thread A...
threadA = pthread_self();
// On thread B...
pthread_t threadB = pthread_self();
if (pthread_equal(threadA, threadB)) printf("Thread B is same as thread A.\n");
else printf("Thread B is NOT same as thread A.\n");
Jika Anda hanya perlu tahu apakah Anda berada di utas utama, ada cara tambahan, yang didokumentasikan dalam jawaban atas pertanyaan ini, bagaimana saya bisa tahu jika pthread_self adalah utas utama (pertama) dalam proses? .
pid_t tid = syscall(SYS_gettid);
Linux menyediakan panggilan sistem seperti itu untuk memungkinkan Anda mendapatkan id dari sebuah utas.
pthread_getthreadid_np
tidak ada di Mac os x saya. pthread_t
adalah tipe buram. Jangan menyalahkan kepala Anda karenanya. Tetapkan saja void*
dan sebut baik. Jika Anda perlu printf
menggunakan %p
.
Saya pikir pertanyaannya tidak hanya tidak jelas tetapi kebanyakan orang juga tidak menyadari perbedaannya. Perhatikan pepatah berikut,
ID utas POSIX tidak sama dengan ID utas yang dikembalikan oleh
gettid()
panggilan sistem khusus Linux . ID utas POSIX ditetapkan dan dikelola oleh implementasi threading. ID utas yang dikembalikan olehgettid()
adalah angka (mirip dengan ID proses) yang ditetapkan oleh kernel. Meskipun setiap utas POSIX memiliki ID utas kernel unik dalam implementasi penguliran NPTL Linux, aplikasi umumnya tidak perlu mengetahui tentang ID kernel (dan tidak akan portabel jika tergantung pada mengetahuinya).Dikutip dari: The Linux Programming Interface: A Linux and UNIX System Programming Handbook, Michael Kerrisk
IMHO, hanya ada satu cara portabel yang melewati struktur di mana mendefinisikan variabel memegang nomor secara menaik misalnya 1,2,3...
ke per utas. Dengan melakukan ini, id utas dapat dilacak. Meskipun demikian, int pthread_equal(tid1, tid2)
fungsi harus digunakan.
if (pthread_equal(tid1, tid2)) printf("Thread 2 is same as thread 1.\n");
else printf("Thread 2 is NOT same as thread 1.\n");
gettid()
sebenarnya saran yang bagus, terima kasih! Namun, saya perlu mengikuti jawaban dari Sergey L. di sini: stackoverflow.com/a/21280941/2430526
Ada juga cara lain untuk mendapatkan id utas. Saat membuat utas dengan
int pthread_create(pthread_t * thread, const pthread_attr_t * attr, void * (*start_routine)(void *), void *arg);
panggilan fungsi; parameter pertama pthread_t * thread
sebenarnya adalah thread id (yaitu int panjang unsigned yang didefinisikan dalam bits / pthreadtypes.h). Juga, argumen terakhir void *arg
adalah argumen yang diteruskan ke void * (*start_routine)
fungsi yang akan di-thread.
Anda dapat membuat struktur untuk meneruskan beberapa argumen dan mengirim pointer ke struktur.
typedef struct thread_info {
pthread_t thread;
//...
} thread_info;
//...
tinfo = malloc(sizeof(thread_info) * NUMBER_OF_THREADS);
//...
pthread_create (&tinfo[i].thread, NULL, handler, (void*)&tinfo[i]);
//...
void *handler(void *targs) {
thread_info *tinfo = targs;
// here you get the thread id with tinfo->thread
}
Anda juga dapat menulis dengan cara ini dan melakukan hal yang sama. Misalnya:
for(int i=0;i < total; i++)
{
pthread_join(pth[i],NULL);
cout << "SUM of thread id " << pth[i] << " is " << args[i].sum << endl;
}
Program ini menyiapkan array pthread_t dan menghitung jumlah masing-masing. Jadi mencetak jumlah setiap utas dengan id utas.
Cara yang tidak bergantung platform (mulai dari c ++ 11) adalah:
#include <thread>
std::this_thread::get_id();
pthread_t
. Di mac itu akan menjadi penunjuk dan di Linux itu bilangan bulat. Ini juga tidak mencerminkan id "asli" yang mungkin Anda lihat top
misalnya. Sesuatu yang harus diperhatikan, tetapi mungkin baik-baik saja untuk beberapa kegunaan.