A weird problem with POSIX function

Hi all,

Sorry for the title because I didn't find a proper name for it. My question is about POSIX functions, such as timer_create(), mq_open() and pthread_create().

void test_queue()
{
struct mq_attr attr;

attr.mq_maxmsg = 10;
attr.mq_msgsize = 64;

mq_unlink("/my_test_queue");
if(mq_open("/my_test_queue", (O_RDWR + O_CREATE + O_EXCL), 0777, &attr) == -1)
{
  printf("\n__%s__errno(%d: %s)", __FUNCTION__, errno, strerror(errno));
  return FAIL;
}
}

If I put the above function in main.c, there will have no problem. The queue is successfully created. But if I put in a file, let say foo.c. This file is compiled into libFOO.a and linked with main.c. Then I got the following error: errno(2: No such file or directory)

The other POSIX functions are also same if put in libFOO.a, for example, timer_create() failed with "Invalid argument" errro, pthread_create() succeeds but it is never run.

Is there any difference between running in main.c and foo.c? If you ever experienced such problem then please give me some hints

Thank you very much

Your code looks okay.

How are you making (compiling) the final complete file? What OS are you on?

I am working on embedded linux.
It turns out that the problem is not come from the source code itself but from the compile option. If I add -D_GNU_SOURCE when compiling libFOO then problem will be solved.

(O_RDWR + O_CREATE + O_EXCL)

This is wrong. Sometimes you can get away with adding bitfields, but not always. Imagine these binary numbers:

  00000001
+ 00000010
=========
  00000011

No overlap, so they act like you expect. If they overlap:

  00000011
+ 00000010
=========
  00000101

1+1=10, so it carries, enabling a brand-new bit which had nothing to do with anything you meant to enable.

If you want to set bits and nothing but set bits, | is what you want.

O_RDWR | O_CREATE | O_EXCL

Hi!

Strange. Can you check if the following works on your platform:

/* foo.c */
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>

#include "foo.h" 

static pthread_t tid;

void* my_thread(void* ignore)
{
   int i;
   printf("Hello from thread\n");
   for (i=0; i<10; i++) {
      printf ("%d ", i); 
      fflush(stdout);
      sleep(1);
   }
}

void init(void)
{
   int rc;
   
   rc = pthread_create(&tid, NULL, my_thread, NULL);
   if (rc!=0) {
      fprintf(stderr,"pthread_create failed: %s (%d)\n", strerror(rc), rc);
      exit(1);
   }
}
/* foo.h */
#ifndef __FOO_H_
#define __FOO_H_
void init(void);
#endif
//myprog.c
#include <unistd.h>
#include "foo.h"

int
main()
{
   int val; 
   init();
   sleep(6);
}

Compile as follows:

cc -c foo.c
ar rcs libfoo.a foo.o
cc -pthread -static myprog.c -o myprog -L. -lfoo

If everything works as expected, you should see the following output:

Hello from thread
0 1 2 3 4 5

/Lew

Hi NH2,

My problem comes from invalid compile option that I mentioned from my previous post. By the way, I tested with your code and get error code 11 returned from pthread_create() function. The meaning is "Resource temporarily unavailable". Do you have any idea?

I used MSVC2010 for testing your code (pthreadVC2.lib)

That's probably your problem. Try a UNIX system.