#include <errno.h>
#include <pthread.h>
#include <stdio.h>
#include <unistd.h> 

/*
  Inicializacao estatica.

  NP significa Non-portable
  Para usar este inicializador, devemos compilar o programa
  informando a flag -D_GNU_SOURCE

*/
pthread_mutex_t lock = PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP;
                       
void* f_thread(void *v) {


  pthread_mutex_lock(&lock);

  /*
    Mutexes do tipo ERRORCHECK verificam se a thread tentou
    lockar o mutex mais de uma vez.

    Caso isto aconteça, a função pthread_mutex_lock retorna
    imediatamente EDEADLK, sinalizando o erro para quem a chamou.
    É importante notar que a função não tenta lockar o mutex de
    novo, evitando o deadlock da thread.

   */
  if (pthread_mutex_lock(&lock) == EDEADLK) {
    printf("Deadlock detected!\n");
  }

  sleep(1);
  printf("Lock obtido\n");
  pthread_mutex_unlock(&lock);

  return NULL;
}

int main() {
  pthread_t thr;
  pthread_create(&thr, NULL, f_thread, NULL);
  pthread_join(thr, NULL);

  printf("Finalizando programa\n");

  return 0;
}