Skip to contentSkip to conversation

Two IA-64 Linux bugs

Linux-ia64 Wan-Teh Chang 4 participants 6 messages Jun 5, 2000 – Jun 7, 2000

lore
Share & tools
lore
#0 lore raw

System info:
[nspr@tl2 unix]$ uname -a
Linux tl2.compile.sourceforge.net 2.3.99-pre6-000501-18smp #1 SMP Sat May 6 21:30:48 PDT 2000 ia64 unknown

Bug #1: pthread_cond_wait sometimes returns EINVAL (22). Run the first attachment (pingpong.c) repeatedly. Note that this test doesn't call pthread_cond_destroy so it is impossible that we are waiting on a destroyed condition variable. This failure is intermittent so you may need to try many times to reproduce it.

Bug #2: sysconf(_SC_NPROCESSORS_ONLN) returns 0. It should return the number of processors online. Run the second attachment (ncpus.c) to reproduce it.

Wan-Teh

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

#define LOOP 20000

int toggle = 0;          /* either 0 or 1 */
pthread_mutex_t mutex;   /* protects 'toggle' */
pthread_cond_t cond;     /* for the threads to wait on */

void *ping(void *arg)

{
    int i;
    int rv;

    rv = pthread_mutex_lock(&mutex);
    if (rv) {
        fprintf(stderr, "pthread_mutex_lock failed: %d\n", rv);
        exit(1);
    }
    for (i = 0; i < LOOP; i++) {
        while (toggle == 0) {
            rv = pthread_cond_wait(&cond, &mutex);
            if (rv) {
                fprintf(stderr, "pthread_cond_wait failed: %d\n", rv);
                exit(1);
            }
        }
        toggle--;
        rv = pthread_cond_signal(&cond);
        if (rv) {
            fprintf(stderr, "pthread_cond_signal failed: %d\n", rv);
            exit(1);
        }
    }
    rv = pthread_mutex_unlock(&mutex);
    if (rv) {
        fprintf(stderr, "pthread_mutex_unlock failed: %d\n", rv);
        exit(1);
    }
    return NULL;
}

void *pong(void *arg)

{
    int i;
    int rv;

    rv = pthread_mutex_lock(&mutex);
    if (rv) {
        fprintf(stderr, "pthread_mutex_lock failed: %d\n", rv);
        exit(1);
    }
    for (i = 0; i < LOOP; i++) {
        while (toggle == 1) {
            rv = pthread_cond_wait(&cond, &mutex);
            if (rv) {
                fprintf(stderr, "pthread_cond_wait failed: %d\n", rv);
                exit(1);
            }
        }
        toggle++;
        rv = pthread_cond_signal(&cond);
        if (rv) {
            fprintf(stderr, "pthread_cond_signal failed: %d\n", rv);
            exit(1);
        }
    }
    rv = pthread_mutex_unlock(&mutex);
    if (rv) {
        fprintf(stderr, "pthread_mutex_unlock failed: %d\n", rv);
        exit(1);
    }
    return NULL;
}

int main()

{
    pthread_attr_t attr;
    pthread_t t1, t2;
    int rv;

    rv = pthread_mutex_init(&mutex, NULL);
    if (rv) {
        fprintf(stderr, "pthread_mutex_init failed: %d\n", rv);
        exit(1);
    }
    rv = pthread_cond_init(&cond, NULL);
    if (rv) {
        fprintf(stderr, "pthread_cond_init failed: %d\n", rv);
        exit(1);
    }

    rv = pthread_attr_init(&attr);
    if (rv) {
        fprintf(stderr, "pthread_attr_init failed: %d\n", rv);
        exit(1);
    }
    rv = pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
    if (rv) {
        fprintf(stderr, "pthread_attr_setdetachstate failed: %d\n", rv);
        exit(1);
    }
    rv = pthread_create(&t1, &attr, ping, NULL);
    if (rv) {
        fprintf(stderr, "pthread_create failed: %d\n", rv);
        exit(1);
    }
    rv = pthread_create(&t2, &attr, pong, NULL);
    if (rv) {
        fprintf(stderr, "pthread_create failed: %d\n", rv);
        exit(1);
    }

    rv = pthread_join(t1, NULL);
    if (rv) {
        fprintf(stderr, "pthread_join failed: %d\n", rv);
        exit(1);
    }
    rv = pthread_join(t2, NULL);
    if (rv) {
        fprintf(stderr, "pthread_join failed: %d\n", rv);
        exit(1);
    }
    
    return 0;
}

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

int main()

{
    printf("# processors online = %d\n", sysconf(_SC_NPROCESSORS_ONLN));
    return 0;
}
#1 lore raw
Quoted 7 lines · Wan-Teh Chang

System info:
[nspr@tl2 unix]$ uname -a
Linux tl2.compile.sourceforge.net 2.3.99-pre6-000501-18smp #1 SMP Sat May 6 21:30:48 PDT 2000 ia64 unknown

Bug #2: sysconf(_SC_NPROCESSORS_ONLN) returns 0.
It should return the number of processors online.

I've fixed that in the "official" glibc tree one week ago. It's been fixed in HJ's tree a few weeks ago (but I don't know how he did it).

This is implemented by counting the lines starting with "CPU#" in /proc/cpuinfo. If the kernel guys change the format of that file, it might break again.

Dan

#2 lore raw
In reply to Wan-Teh Chang
Quoted 6 lines · Dan Pop

I've fixed that in the "official" glibc tree one week ago. It's been fixed in HJ's tree a few weeks ago (but I don't know how he did it).

This is implemented by counting the lines starting with "CPU#" in /proc/cpuinfo. If the kernel guys change the format of that file, it might break again.

Is there any reason why this reads /proc/cpuinfo and not /proc/stat? /proc/stat is at least consistent across architectures...

Bill

#3 lore raw
In reply to Wan-Teh Chang
Quoted 8 lines · Bill Nottingham
Quoted 4 lines · Dan Pop

This is implemented by counting the lines starting with "CPU#" in /proc/cpuinfo. If the kernel guys change the format of that file, it might break again.

Is there any reason why this reads /proc/cpuinfo and not /proc/stat? /proc/stat is at least consistent across architectures...

The right person to answer this question is the glibc maintainer, who happens to be a colleague of yours :-)

Dan

#4 lore raw
In reply to Wan-Teh Chang

We also had problems around here with pthread_cond_wait. The glibc version we were using was used a linuxthreads snapshot taken at a bad time. Pthread_cond_wait checked that the current thread owned the mutex. Unfortunately, it did so even for "fast" mutexes, for which the owner field wasn't set.

If this is the problem, I would guess that you should be able to avoid it by using recursive or checking mutexes. The problem is hopefully very temporary, since the glibc on sourceware exhibited this problem for only a day.

Hans

Quoted 7 lines

Bug #1: pthread_cond_wait sometimes returns EINVAL (22). Run the first attachment (pingpong.c) repeatedly. Note that this test doesn't call pthread_cond_destroy so it is impossible that we are waiting on a destroyed condition variable. This failure is intermittent so you may need to try many times to reproduce it.

#5 lore raw
In reply to Wan-Teh Chang
Quoted 11 lines · Hans

We also had problems around here with pthread_cond_wait. The glibc version we were using was used a linuxthreads snapshot taken at a bad time. Pthread_cond_wait checked that the current thread owned the mutex. Unfortunately, it did so even for "fast" mutexes, for which the owner field wasn't set.

If this is the problem, I would guess that you should be able to avoid it by using recursive or checking mutexes. The problem is hopefully very temporary, since the glibc on sourceware exhibited this problem for only a day.

Indeed, if I use a recursive or error-checking mutex, I cannot make my test case (pingpong.c) fail.

Wan-Teh