В программе linux c, как распечатать идентификатор потока потока, созданного библиотекой pthread?
например: мы можем получить представление о процессе с помощьюgetpid()
В программе linux c, как распечатать идентификатор потока потока, созданного библиотекой pthread?
например: мы можем получить представление о процессе с помощьюgetpid()
Ответы:
pthread_self()
функция даст идентификатор потока текущего потока.
pthread_t pthread_self(void);
pthread_self()
Функция возвращает PTHREAD дескриптор вызывающего потока. Функция pthread_self () НЕ возвращает интегральный поток вызывающего потока. Вы должны использовать pthread_getthreadid_np()
для возврата интегрального идентификатора потока.
НОТА:
pthread_id_np_t tid;
tid = pthread_getthreadid_np();
значительно быстрее, чем эти вызовы, но обеспечивает такое же поведение.
pthread_id_np_t tid;
pthread_t self;
self = pthread_self();
pthread_getunique_np(&self, &tid);
pthread_threadid_np
. Мне нужно использовать его для проекта, поэтому мне нужно проверить надежность этого API на платформах iOS и OSX. Ссылался на ссылку на opensource.apple.com/source/Libc/Libc-583/pthreads/pthread.h, но не уверен, что они правильные.
_np
означает непереносимый . У Linux есть свои собственные _np
вещи, но они не включают Apple pthread_getthreadid_np
.
Какие? Человек попросил специфику Linux и эквивалент getpid (). Ни BSD, ни Apple. Ответ gettid () возвращает целочисленный тип. Вам нужно будет вызвать его с помощью syscall (), например:
#include <sys/types.h>
#include <unistd.h>
#include <sys/syscall.h>
....
pid_t x = syscall(__NR_gettid);
Хотя это может быть непереносимым для систем, отличных от Linux, threadid напрямую сопоставим и очень быстро получить. Его можно напечатать (например, для журналов регистрации) как обычное целое число.
getpid()
приведен в качестве примера. Он не сказал, что семантика была жесткой спецификацией. Информировать людей о том, что они делают что-то совместимым с POSIX способом, чтобы другие сообщества, помимо Linux (например, FreeBSD, Illumos, OS X и т. Д.), Могли получить от них пользу, не является «хвастовством». Как я уже сказал, я полагаю, что Linux действительно стала следующей Windows.
Как отмечалось в других ответах, pthreads не определяет независимый от платформы способ получения интегрального идентификатора потока.
В системах Linux вы можете получить идентификатор потока следующим образом:
#include <sys/types.h>
pid_t tid = gettid();
На многих платформах на основе BSD этот ответ https://stackoverflow.com/a/21206357/316487 дает непереносимый способ.
Однако, если причина, по которой вы считаете, что вам нужен идентификатор потока, заключается в том, чтобы знать, работаете ли вы в одном или другом потоке с другим потоком, который вы контролируете, вы можете найти некоторую полезность в этом подходе.
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");
Если вам просто нужно знать, находитесь ли вы в основном потоке, существуют дополнительные способы, задокументированные в ответах на этот вопрос, как я могу определить, является ли pthread_self основным (первым) потоком в процессе? .
pthread_getthreadid_np
не было на моем Mac os x. pthread_t
непрозрачный тип. Не бей головой над этим. Просто назначьте его void*
и назовите хорошим. Если вам нужно printf
использовать %p
.
Я думаю, что не только вопрос не ясен, но и большинство людей не осознают разницу. Изучите следующее высказывание:
Идентификаторы потоков POSIX не совпадают с идентификаторами потоков, возвращаемыми
gettid()
системным вызовом Linux . Идентификаторы потоков POSIX назначаются и поддерживаются реализацией потоковой передачи. Идентификатор потока, возвращаемый функцией,gettid()
представляет собой номер (аналогичный идентификатору процесса), присвоенный ядром. Хотя каждый поток POSIX имеет уникальный идентификатор потока ядра в реализации потоков Linux NPTL, приложению обычно не требуется знать идентификаторы ядра (и оно не будет переносимым, если это зависит от их знания).
IMHO, есть только один переносимый способ передать структуру, в которой определяют номера хранения переменных по возрастанию, например, 1,2,3...
для каждого потока. Таким образом можно отслеживать идентификатор потока. Тем не менее, int pthread_equal(tid1, tid2)
функцию следует использовать.
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()
самом деле это хорошее предложение, спасибо! Однако мне нужно было следить за ответом Сергея Л. здесь: stackoverflow.com/a/21280941/2430526
Есть еще один способ получить идентификатор потока. При создании потоков с
int pthread_create(pthread_t * thread, const pthread_attr_t * attr, void * (*start_routine)(void *), void *arg);
вызов функции; первый параметр pthread_t * thread
на самом деле является идентификатором потока (это длинное целое число без знака, определенное в файле bits / pthreadtypes.h). Кроме того, последний аргумент void *arg
- это аргумент, который передается void * (*start_routine)
функции для потоковой передачи .
Вы можете создать структуру для передачи нескольких аргументов и отправки указателя на структуру.
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
}
Вы также можете писать таким же образом, и он делает то же самое. Например:
for(int i=0;i < total; i++)
{
pthread_join(pth[i],NULL);
cout << "SUM of thread id " << pth[i] << " is " << args[i].sum << endl;
}
Эта программа создает массив pthread_t и вычисляет сумму для каждого. Таким образом, он печатает сумму каждого потока с идентификатором потока.
Независимый от платформы способ (начиная с c ++ 11):
#include <thread>
std::this_thread::get_id();
pthread_t
. На Mac это будет указатель, а на Linux - целое число. Он также не отражает «родной» идентификатор, который вы можете увидеть, top
например. Кое-что нужно знать, но, возможно, для некоторых целей это нормально.