Условный сигнал Pthread - не работающий как ожидалось

В вашем файле yaml отсутствует строка, указывающая, какой хост вы защищаете. Поскольку вы не используете external-dns, вам придется создавать записи на стороне вашего поставщика домена вручную, чтобы подключить IP-адрес к вашему домену (кажется, вы уже сделали это). Похоже, что и ваш вход, и ваш секрет tls находятся в пространстве имен default, поэтому вы можете использовать следующее ingress.yaml:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: myapp-ingress
  annotations:
    kubernetes.io/tls-acme: "true"
    kubernetes.io/ingress.global-static-ip-name: myapp-ip
spec:
  tls:
  - hosts:
    - "myapp.co.uk"
    secretName: myapp-tls-secret-1
  rules:
  - host: "myapp.co.uk"
    http:
      paths:
      - path: /
        backend:
          serviceName: myapp-service
          servicePort: 80
5
задан poundifdef 22 March 2009 в 15:55
поделиться

4 ответа

pthread_cond_signal функция не заставляет текущий поток уступать и не выпускает взаимное исключение. Все, что это делает, перезапустить один поток, который приостановил себя на условии через pthread_cond_wait. Это просто означает, что пробужденный поток доступен для планирования, он не заставляет это сразу выполниться. Планировщик потока запланирует его когда-то в будущем.

Кроме того, просто потому что s-поток был пробужден и борется за взаимное исключение, которое не означает, что собирается получить взаимное исключение затем. Взаимные исключения не обязательно справедливы ко всем потокам, которые запросили это. Согласно pthread_mutex страница справочника:"pthread_mutex_lock блокирует данное взаимное исключение. Если взаимное исключение в настоящее время разблокировано, это становится заблокированным и находящимся в собственности вызывающего потока, и pthread_mutex_lock возвраты сразу". Таким образом, r-поток может несколько раз вращаться в его цикле, счастливо разблокировав и повторно блокируя взаимное исключение несколько раз прежде чем быть выгруженным планировщиком. Это означает, что s-поток только получит шанс во взаимном исключении, если планировщик, окажется, будет прерывать r-поток в течение краткого времени, в которое это выпустило взаимное исключение.

Для достижения вывода, Вы хотите, оба потока должны будут управлять своим выполнением с условием и сигнализировать друг о друге прежде, чем временно отстранить себя. Однако это может или не может быть тем, что Вы на самом деле хотите сделать со своим реальным проектом.

Другое примечание: действительно не имеет значения, что приказывает, чтобы Вы создали потоки в. Создание потока не приводит к потоку создания. Таким образом, основной поток, вероятно, создаст оба потока, прежде чем любой будет запланирован, и планировщик потока свободен запланировать любого из них для выполнения затем. Если s-поток действительно работает сначала на Вашей платформе, которая просто, оказывается, поведение реализации на Вашей платформе и не является чем-то, на что нужно полагаться.

8
ответ дан 18 December 2019 в 08:31
поделиться

Я, кажется, не забываю читать где-нибудь это pthread_cond_signal() на самом деле не заставляет поток сразу уступить. С тех пор pthread_cond_signal() не выпускает блокировку, поток, который звонит, это должно продолжить выполняться, пока это действительно не выпускает блокировку и только затем делает это приводит и позволяет сообщенному потоку возвращаться из pthread_cond_wait().

Если это так, затем я думаю, что Ваш вывод был бы похож

s1
s2
r1
r2
s3
s4
s5

и т.д....., если дело не в этом, Вы, возможно, должны были бы отредактировать эффективную выходную мощность в свой вопрос получить точный ответ.

6
ответ дан 18 December 2019 в 08:31
поделиться

Вы делаете неправильное использование условий. Я не сделал понятый точно, что Вы хотите, но что Вы пытаетесь сделать, много походит на типичную проблему синхронизации, названную проблемой производителя/потребителя, которая может быть реализована с условиями как, я сделал после.

Необходимо взглянуть на это, чтобы понять, как используются условия. Проблема следующая: у Меня есть два потока, данные записи в буфер фиксированного размера и другие данные чтения с буфера. Первый поток не может записать больше данных, если буфер полон, второе не может читать, если буфер пуст.

#include <stdlib.h>
#include <stdio.h>

#include <pthread.h>

#define BUFFER_SIZE 4 

int buffer_nb_entries = 0; 

pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER; 
pthread_cond_t cond = PTHREAD_COND_INITIALIZER; 

void send(){
for(;;){
  pthread_mutex_lock(&mutex);
  while( buffer_nb_entries == BUFFER_SIZE) /* If buffer is full, then wait */
    pthread_cond_wait(&cond, &mutex); 

  /* Here I am sure that buffer is not full */
  printf("sending\n"); 
  buffer_nb_entries++;

  pthread_cond_signal(&cond); // signal that the condition has changed. 
  pthread_mutex_unlock(&mutex); 
 }
}

void receive(){
  for(;;){
    pthread_mutex_lock(&mutex); 
    while(buffer_nb_entries == 0)
      pthread_cond_wait(&cond, &mutex);
    /* Here I am sure that buffer is not empty */
    printf("receiving\n");
    buffer_nb_entries--; 
    pthread_cond_signal(&cond); 
    pthread_mutex_unlock(&mutex); 
  }

}

int main(){
  pthread_t s, r; 

  pthread_create(&s, NULL, (void *(*)(void*))send, NULL); 
  pthread_create(&r, NULL, (void *(*)(void*))receive, NULL); 

  pthread_join(s, NULL); 

}

Обратите внимание, что необходимо протестировать на что-то прежде, чем назвать pthread_cond_wait (), если Вы не делаете и если Вы предупреждаете, что функция была вызвана прежде, затем можно спать навсегда.

4
ответ дан 18 December 2019 в 08:31
поделиться

Я думаю, что Ваша проблема прибывает из попытки использовать одну блокировку для слишком многих вещей. Необходимо только использовать блокировку для 1 вещи, тот путь, там не беспорядок о том, чего Вы ожидаете. Я предлагаю добавить вторую блокировку для сигнала записи. Кроме того, необходимо добавить второй cond_wait для второй группировки сообщений. Если Вы не делаете, порядок, что вещи, выполненные в, будут случайны. Вот моя отредактированная версия Вашей программы:

#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>

#define NUM_MESSAGES 3
int messages = 0;
void * send_segments(void *);
void * recv_acks(void *v);
pthread_mutex_t lock_it = PTHREAD_MUTEX_INITIALIZER;
pthread_mutex_t write_mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t write_cond = PTHREAD_COND_INITIALIZER;

   int main(int argc, char**argv)
  {

     pthread_t t_send_segments, t_recv_acks;

     pthread_create(&t_send_segments, NULL, send_segments, (void*)NULL);
     pthread_create(&t_recv_acks,     NULL, recv_acks,     (void*)NULL);

     pthread_join(t_recv_acks, (void**)NULL);
     pthread_join(t_send_segments, (void**)NULL);

     //pthread_mutex_destroy(&lock_it);
     //pthread_cond_destroy(&write_it);
}

 void* send_segments(void *v) {
    for(;;) {
       pthread_mutex_lock(&lock_it);
       printf("s1\n");
       printf("s2\n");
       pthread_mutex_unlock(&lock_it);

       // wait for other thread
       pthread_mutex_lock(&write_mutex);
       pthread_cond_wait(&write_cond, &write_mutex);
       pthread_mutex_unlock(&write_mutex);

       pthread_mutex_lock(&lock_it);
       printf("s3\n");
       printf("s4\n");
       printf("s5\n"); 
       pthread_mutex_unlock(&lock_it);

       // wait for other thread
       pthread_mutex_lock(&write_mutex);
       pthread_cond_wait(&write_cond, &write_mutex);
       pthread_mutex_unlock(&write_mutex);

       if (messages > NUM_MESSAGES) return( NULL );
    }
    return 0;
 }


 void* recv_acks(void *v) {
    for(;;) {
       // write first response
       pthread_mutex_lock(&lock_it);
       printf("r1\n");
       pthread_mutex_unlock(&lock_it);

       // signal other thread
       pthread_mutex_lock(&write_mutex);
       pthread_cond_signal(&write_cond);
       pthread_mutex_unlock(&write_mutex);

       // write second response
       pthread_mutex_lock(&lock_it);
       printf("r2\n\n");
       // increment count before releasing lock, otherwise the other thread
       // will be stuck waiting for a write_cond signal
       messages++;
       pthread_mutex_unlock(&lock_it);

       // signal other thread
       pthread_mutex_lock(&write_mutex);
       pthread_cond_signal(&write_cond);
       pthread_mutex_unlock(&write_mutex);

       if (messages > NUM_MESSAGES) return(NULL);
    } 
    return 0;
 }

Если я запускаю эту программу, я добираюсь, следующий вывод (обратите внимание, что я добавил вторую новую строку после r2 для ясности):

leif@indurain:~/tmp$ ./test
s1
s2
r1
s3
s4
s5
r2

s1
s2
r1
s3
s4
s5
r2

s1
s2
r1
s3
s4
s5
r2

s1
s2
r1
s3
s4
s5
r2

leif@indurain:~/tmp$ 
1
ответ дан 18 December 2019 в 08:31
поделиться
Другие вопросы по тегам:

Похожие вопросы: