public inbox for glibc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug nptl/27458] New: pthread_mutex_trylock ENOTRECOVERABLE
@ 2021-02-22 21:20 andy.map88 at yahoo dot it
  0 siblings, 0 replies; only message in thread
From: andy.map88 at yahoo dot it @ 2021-02-22 21:20 UTC (permalink / raw)
  To: glibc-bugs

https://sourceware.org/bugzilla/show_bug.cgi?id=27458

            Bug ID: 27458
           Summary: pthread_mutex_trylock ENOTRECOVERABLE
           Product: glibc
           Version: 2.31
            Status: UNCONFIRMED
          Severity: normal
          Priority: P2
         Component: nptl
          Assignee: unassigned at sourceware dot org
          Reporter: andy.map88 at yahoo dot it
                CC: drepper.fsp at gmail dot com
  Target Milestone: ---

Created attachment 13251
  --> https://sourceware.org/bugzilla/attachment.cgi?id=13251&action=edit
Source Code

I found unexpected behavior when i tried to lock mutex with 'trylock' when the
previous owner is dead without unlock it.
The first process that uses 'pthread_mutex_trylock' gets EOWNERDEAD error as
expected, so uses the 'unlock' function to relase the mutex.
The second calls the same function obtaining the ENOTRECOVERABLE error, as
expected.
But when the third calls 'pthread_mutex_trylock' gets the EBUSY error and this
is unexpected.
This behavior doesn't occur using 'pthread_mutex_lock' that always gets
EOWNERDEAD  or ENOTRECOVERABLE error.

CODE:
///TEST MUTEX
#include <stdio.h>
#include <unistd.h>
#include <sys/wait.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <pthread.h>

main(void)
{
int32_t lock_status, mutex_fdesc;
pid_t process_id;
pthread_mutex_t* mutex;
pthread_mutexattr_t m_att;

//Process 1 die with locked mutex
process_id = fork();
if (process_id < 0) {exit(0);}
if (process_id == 0)
{
        usleep(100000);
        mutex_fdesc = shm_open("/mutex", O_RDWR, S_IRWXU | S_IRWXG);
        mutex = (pthread_mutex_t*)mmap(NULL, sizeof(pthread_mutex_t), 
                                PROT_READ | PROT_WRITE, MAP_SHARED, 
                                mutex_fdesc, 0);
        close(mutex_fdesc);
        pthread_mutex_lock(mutex);
        exit(0);
}
///Process 2 try to lock mutex and gets EOWNERDEAD then make an unlock
process_id = fork();
if (process_id < 0) {exit(0);}
if (process_id == 0)
{
        usleep(200000);
        mutex_fdesc = shm_open("/mutex", O_RDWR, S_IRWXU | S_IRWXG);
        mutex = (pthread_mutex_t*)mmap(NULL, sizeof(pthread_mutex_t), 
                                PROT_READ | PROT_WRITE, MAP_SHARED, 
                                mutex_fdesc, 0);
        close(mutex_fdesc);
        lock_status = pthread_mutex_trylock(mutex);
        if (lock_status == EOWNERDEAD)
                {
                pthread_mutex_unlock(mutex);
                printf("P2 mutex status: EOWNERDEAD\n");}
        else if (lock_status == ENOTRECOVERABLE)
                {printf("P2 mutex status: ENOTRECOVERABLE\n");}
        else if (lock_status == EBUSY)
                {printf("P2 mutex status: EBUSY\n");}
        else {printf("P2 mutex status: %d\n", lock_status);}
        exit(0);
}
///Process 2 try to lock mutex and gets ENOTRECOVERABLE then do nothing
process_id = fork();
if (process_id < 0) {exit(0);}
if (process_id == 0)
{
        usleep(400000);
        mutex_fdesc = shm_open("/mutex", O_RDWR, S_IRWXU | S_IRWXG);
        mutex = (pthread_mutex_t*)mmap(NULL, sizeof(pthread_mutex_t), 
                                PROT_READ | PROT_WRITE, MAP_SHARED, 
                                 mutex_fdesc, 0);
        close(mutex_fdesc);
        lock_status = pthread_mutex_trylock(mutex);
        if (lock_status == EOWNERDEAD)
                {
                pthread_mutex_unlock(mutex);
                printf("P3 mutex status: EOWNERDEAD\n");}
        else if (lock_status == ENOTRECOVERABLE)
                {printf("P3 mutex status: ENOTRECOVERABLE\n");}
        else if (lock_status == EBUSY)
                {printf("P3 mutex status: EBUSY\n");}
        else {printf("P3 mutex status: %d\n", lock_status);}
        //delay_MilliSec(2000);
        exit(0);
}

mutex_fdesc = shm_open("/mutex", O_RDWR | O_CREAT | O_EXCL, S_IRWXU | S_IRWXG);
ftruncate(mutex_fdesc, sizeof(pthread_mutex_t));
mutex = (pthread_mutex_t*)mmap(NULL, sizeof(pthread_mutex_t), 
                        PROT_READ | PROT_WRITE, MAP_SHARED, mutex_fdesc, 0);
close(mutex_fdesc);
pthread_mutexattr_init(&m_att);
pthread_mutexattr_setpshared(&m_att, PTHREAD_PROCESS_SHARED);
pthread_mutexattr_setrobust(&m_att, PTHREAD_MUTEX_ROBUST);
pthread_mutex_init(mutex, &m_att);
pthread_mutexattr_destroy(&m_att);

///Parent process try to lock the mutex and gets EBUSY
usleep(800000);
lock_status = pthread_mutex_trylock(mutex);
if (lock_status == EOWNERDEAD)
                {printf("Pparent mutex status: EOWNERDEAD\n");}
        else if (lock_status == ENOTRECOVERABLE)
                {printf("Pparent mutex status: ENOTRECOVERABLE\n");}
        else if (lock_status == EBUSY)
                {printf("Pparent mutex status: EBUSY\n");}
        else {printf("Pparent mutex status: %d\n", lock_status);}

pthread_mutex_destroy(mutex);
munmap((void*)mutex, sizeof(pthread_mutex_t));
shm_unlink("/mutex");
wait(NULL);
wait(NULL);
wait(NULL);
exit(0);
}

-- 
You are receiving this mail because:
You are on the CC list for the bug.

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2021-02-22 21:20 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-02-22 21:20 [Bug nptl/27458] New: pthread_mutex_trylock ENOTRECOVERABLE andy.map88 at yahoo dot it

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).