Re: [Xenomai-help] shm_open, ftruncate
Gilles Chanteperdrix a écrit : Lionel Perrin wrote: > ///* the following lines shouldn't be commented but xenomai... */ > //else > //{ > ///* a new shm_file has been created, we need to truncate it */ > //if (ftruncate(h_shm, nbvalues * sizeof(double))==-1) > //{ > //printf("truncate failed\n"); > //goto close_and_unlink; > //} > //} Do you still have an issue with ftruncate ? Note that it is better to always call ftruncate even in a process that is not creating the shared memory, this avoid the race condition where the process that created the shared memory is about to truncate it and is interrupted by the second process which did not create it but want to mmap it. > mem->h_mut = (pthread_mutex_t *)malloc(sizeof(pthread_mutex_t)); > pthread_mutex_init(mem->h_mut, NULL); Note that if you want to share the mem structure between several processes, you should put the mutex on the shared memory, doing for example: typedef struct { pthread_mutex_t mutex; int nbaccess; double values[0] } myshm_t; myshm_t *myshm; myshm = (myshm_t *) mmap(...); mem->h_mut = &myshm->mutex; mem->ptr = &myshm->values; pthread_mutex_init(mem->h_mut, NULL); Xenomai should detect that you are initializing a mutex that was already initialized and return EBUSY that you can safely ignore. Thanks for your help, all work as i wish now... You're right, i've done a terrible mistake with the mutex... I'm a bit ashamed ;) ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > // /* the following lines shouldn't be commented but xenomai... */ > // else > // { > // /* a new shm_file has been created, we need to truncate it */ > // if (ftruncate(h_shm, nbvalues * sizeof(double))==-1) > // { > // printf("truncate failed\n"); > // goto close_and_unlink; > // } > // } Do you still have an issue with ftruncate ? Note that it is better to always call ftruncate even in a process that is not creating the shared memory, this avoid the race condition where the process that created the shared memory is about to truncate it and is interrupted by the second process which did not create it but want to mmap it. > mem->h_mut = (pthread_mutex_t *)malloc(sizeof(pthread_mutex_t)); > pthread_mutex_init(mem->h_mut, NULL); Note that if you want to share the mem structure between several processes, you should put the mutex on the shared memory, doing for example: typedef struct { pthread_mutex_t mutex; int nbaccess; double values[0] } myshm_t; myshm_t *myshm; myshm = (myshm_t *) mmap(...); mem->h_mut = &myshm->mutex; mem->ptr = &myshm->values; pthread_mutex_init(mem->h_mut, NULL); Xenomai should detect that you are initializing a mutex that was already initialized and return EBUSY that you can safely ignore. -- Gilles Chanteperdrix. ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > > > > > I can confirm that a few fixes in v2.1 were missing, so trunk works > > > > correctly, didn't you forget to rebuild the kernel when building > > trunk ? > > > > Attached is a patch to v2.1 that contain the fixes backported from > > > > trunk. Please try this patch and tell me if this works for you. > > > > > > > In fact, I've downloaded the last version of trunk before your mail and > > > the patch. You're right that works pretty good with this version... :) > > > > > > Unfortunately, it seem's that we can't share between a real time > > process > > > and a non real one ? > > > > Sharing memory should work, could you explain what happens ? Note that > > you may use Linux regular shared memory services in the real-time > > process by calling __real_shm_open instead of shm_open. > > > Ok, > But I'd like a real time behaviour of shared memory for my real time > task... so I can't use __real_shm_open, etc... > > Here is the little code I've developped to access shared memory. May be > there some mistakes... > I compile it with or without xeno-config --posix-cflags, xeno-config > --posix-ldflags to get two executables. > I launch these two executables and the shared_memory seem's to be > different in these two cases. > All Xenomai processes are accessing the same shared_memory while all > non-xenomai processes are accessing another one shared memory. That is the expected behaviour: xenomai posix skin shared memory is different from Linux regular shared memory. In the same vein, xenomai posix skin semaphores are different from Linux regular semaphores. But there is no problem using Linux regular shared memory in a real-time thread, providing that you call mlockall. Using a Linux regular semaphore in a real-time thread is also possible by using __real_sem_post or __real_sem_wait, but the real-time thread will migrate to secondary mode. The alternative is to compile the two processes with the flags given by xeno-config, and to create non real-time threads in one process using __real_pthread_create. -- Gilles Chanteperdrix. ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
> > I can confirm that a few fixes in v2.1 were missing, so trunk works > > correctly, didn't you forget to rebuild the kernel when building trunk ? > > Attached is a patch to v2.1 that contain the fixes backported from > > trunk. Please try this patch and tell me if this works for you. > > > In fact, I've downloaded the last version of trunk before your mail and > the patch. You're right that works pretty good with this version... :) > > Unfortunately, it seem's that we can't share between a real time process > and a non real one ? Sharing memory should work, could you explain what happens ? Note that you may use Linux regular shared memory services in the real-time process by calling __real_shm_open instead of shm_open. Ok, But I'd like a real time behaviour of shared memory for my real time task... so I can't use __real_shm_open, etc... Here is the little code I've developped to access shared memory. May be there some mistakes... I compile it with or without xeno-config --posix-cflags, xeno-config --posix-ldflags to get two executables. I launch these two executables and the shared_memory seem's to be different in these two cases. All Xenomai processes are accessing the same shared_memory while all non-xenomai processes are accessing another one shared memory. #include #include #include #include #include #include #include #include #include #include #include "rtsharedmem.h" /* ** * Creates a shared memory object protected by a mutex * * This object is referenced throw its name. If there's no * * shared memory object with the given name, a new one is created, * * otherwise, we get an access to the existing shared memory object. * / MemMap* RtOpenSharedMem(unsigned int nbvalues, const char * name) { int shm_exists; int h_shm; MemMap* mem; void * ptr; int * nbaccess; char *name_shm; name_shm = (char *)malloc((strlen(name)+6)*sizeof(char)); mem = (MemMap *)malloc(sizeof(MemMap)); shm_exists = 0; strcpy(name_shm, name); sprintf(name_shm, "/%s_shm", name); /* Here is the clean version to open shm, but for the moment, this doesn't work with xenomai.*/ h_shm = shm_open( name_shm, O_RDWR | O_CREAT | O_EXCL, S_IRUSR | S_IWUSR | S_IROTH | S_IWOTH); if (h_shm < 0) { if (errno == EEXIST) { /* shm_open has just warned that shm already exists */ /* we shouldn't need O_CREAT here but xenomain failed without */ h_shm = shm_open( name_shm, O_RDWR| O_CREAT, S_IRUSR | S_IWUSR | S_IROTH | S_IWOTH); if (h_shm<0) { printf("shm_open failed to open existing shared mem : %s\n", name_shm); return NULL; } shm_exists = 1; } else { /* shm_open really failed */ printf("shm_open failed to open %s\n", name_shm); return NULL; } } // /* the following lines shouldn't be commented but xenomai... */ // else // { // /* a new shm_file has been created, we need to truncate it */ // if (ftruncate(h_shm, nbvalues * sizeof(double))==-1) // { // printf("truncate failed\n"); // goto close_and_unlink; // } // } if (ftruncate(h_shm, nbvalues * sizeof(double))==-1) { printf("truncate failed\n"); goto close_and_unlink; } ptr = mmap(NULL, sizeof(int) + nbvalues * sizeof(double), PROT_READ | PROT_WRITE, MAP_SHARED, h_shm, 0); if( ptr == MAP_FAILED) { printf("mmap failed\n"); goto close_and_unlink; } mem->h_mut = (pthread_mutex_t *)malloc(sizeof(pthread_mutex_t)); pthread_mutex_init(mem->h_mut, NULL); /* the first sizeof(int) bytes at ptr are reserved to count the number of access to shared mem in order to be able to unlink cleanly */ nbaccess = (int *)ptr; if (shm_exists) *nbaccess = (*nbaccess)+1; else *nbaccess = 1; /* the real data starts at ptr + sizeof(int) */ mem->ptr = (double *)(ptr + sizeof(int)); mem->h_shm = h_shm; mem->nbvalues = nbvalues; mem->name_shm = name_shm; return mem; close_and_unlink: close(h_shm); if (shm_exists==0) shm_un
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > > > I can confirm that a few fixes in v2.1 were missing, so trunk works > > correctly, didn't you forget to rebuild the kernel when building trunk ? > > Attached is a patch to v2.1 that contain the fixes backported from > > trunk. Please try this patch and tell me if this works for you. > > > In fact, I've downloaded the last version of trunk before your mail and > the patch. You're right that works pretty good with this version... :) > > Unfortunately, it seem's that we can't share between a real time process > and a non real one ? Sharing memory should work, could you explain what happens ? Note that you may use Linux regular shared memory services in the real-time process by calling __real_shm_open instead of shm_open. > I got one task which need to be real time in order to acquire datas, and > another one that plot this datas on screen. > I'd like to give user the choice to launch (or not) the second process, > if he wish (or not) to watch the acquired datas. I'm figure out that > making this second process a xenomai thread with a low priority would > solve my problem but i'd rather prefered a standard linux process... Using Xenomai thread with a low priority would allow you to share synchronization objects between the real-time and non real-time activites. You may also create non real-time threads in a real-time process by calling __real_pthread_create instead of pthread_create. -- Gilles Chanteperdrix. ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
I can confirm that a few fixes in v2.1 were missing, so trunk works correctly, didn't you forget to rebuild the kernel when building trunk ? Attached is a patch to v2.1 that contain the fixes backported from trunk. Please try this patch and tell me if this works for you. In fact, I've downloaded the last version of trunk before your mail and the patch. You're right that works pretty good with this version... :) Unfortunately, it seem's that we can't share between a real time process and a non real one ? I got one task which need to be real time in order to acquire datas, and another one that plot this datas on screen. I'd like to give user the choice to launch (or not) the second process, if he wish (or not) to watch the acquired datas. I'm figure out that making this second process a xenomai thread with a low priority would solve my problem but i'd rather prefered a standard linux process... ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > > > > - Will this shared memory be accessible to non rt-task ? > > > - What's the simplest way to share information with a non rt-task ? > > > > Shared memory are also accessible to non-rt tasks. Since user-space > > realtime and non-realtime threads from the same process reside in the > > same address space, the simplest way to share information from rt to > > non-rt tasks is to create them as threads of the same process. > > > Ok, but I figure out that it's possible to share memory between > processes ? (rt and non rt?) > For the moment, i focus on sharing between two rt tasks, but in vain :( > I still have a ftruncate error (EBADF) when i launch two rt processes... > I explain : > I've tried the attached program. I've added a sleep(1) between mmap and > munmap. I launch this appli twice with > >> shm_test & > >> shm_test & > For the second one, I got "ftruncate: Invalid argument". Am I the only > one to have this problem ? No, these errors were due to a few fixes in trunk that had not been backported to the 2.1 branch. It should now be fixed in the repository. -- Gilles Chanteperdrix. ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > > > > - Will this shared memory be accessible to non rt-task ? > > > - What's the simplest way to share information with a non rt-task ? > > > > Shared memory are also accessible to non-rt tasks. Since user-space > > realtime and non-realtime threads from the same process reside in the > > same address space, the simplest way to share information from rt to > > non-rt tasks is to create them as threads of the same process. > > > Ok, but I figure out that it's possible to share memory between > processes ? (rt and non rt?) > For the moment, i focus on sharing between two rt tasks, but in vain :( > I still have a ftruncate error (EBADF) when i launch two rt processes... > I explain : > I've tried the attached program. I've added a sleep(1) between mmap and > munmap. I launch this appli twice with > >> shm_test & > >> shm_test & > For the second one, I got "ftruncate: Invalid argument". Am I the only > one to have this problem ? Using trunk, your example run fine. Which version of Xenomai are you using ? If not trunk, did you apply the patch I sent ? -- Gilles Chanteperdrix. ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
> - Will this shared memory be accessible to non rt-task ? > - What's the simplest way to share information with a non rt-task ? Shared memory are also accessible to non-rt tasks. Since user-space realtime and non-realtime threads from the same process reside in the same address space, the simplest way to share information from rt to non-rt tasks is to create them as threads of the same process. Ok, but I figure out that it's possible to share memory between processes ? (rt and non rt?) For the moment, i focus on sharing between two rt tasks, but in vain :( I still have a ftruncate error (EBADF) when i launch two rt processes... I explain : I've tried the attached program. I've added a sleep(1) between mmap and munmap. I launch this appli twice with >> shm_test & >> shm_test & For the second one, I got "ftruncate: Invalid argument". Am I the only one to have this problem ? #include #include #include #include #include #include #include #define MAX_LEN 1 struct region {/* Defines "structure" of shared memory */ int len; char buf[MAX_LEN]; }; struct region *rptr; int fd; int main(int argc, const char *argv[]) { int fd, status; mlockall(MCL_CURRENT|MCL_FUTURE); /* Create shared memory object and set its size */ fd = shm_open("/myregion", O_CREAT | O_RDWR, S_IRUSR | S_IWUSR); if (fd == -1) { perror("shm_open"); exit(EXIT_FAILURE); } if ((status = ftruncate(fd, sizeof(struct region))) == -1) { /* Handle error */; perror("ftruncate"); close(fd); status = EXIT_FAILURE; goto close_and_unlink; } /* Map shared memory object */ rptr = (struct region *) mmap(NULL, sizeof(struct region), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (rptr == MAP_FAILED) { /* Handle error */; perror("mmap"); status = EXIT_FAILURE; goto close_and_unlink; } /* Now we can refer to mapped region using fields of rptr; for example, rptr->len */ sleep(1); munmap(rptr, sizeof(struct region)); close_and_unlink: close(fd); shm_unlink("/myregion"); return status; } ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > Ok, thanks, i'll try. My old pc will have some job... :) > > I still have a few questions : > - How can we load/unload posix skin ? When configuring your kernel, configure the posix skin as a module. A module xeno_posix.ko will then be compiled that you may load with modprobe and unload with modprobe -r. > - Will this shared memory be accessible to non rt-task ? > - What's the simplest way to share information with a non rt-task ? Shared memory are also accessible to non-rt tasks. Since user-space realtime and non-realtime threads from the same process reside in the same address space, the simplest way to share information from rt to non-rt tasks is to create them as threads of the same process. -- Gilles Chanteperdrix. ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Ok, thanks, i'll try. My old pc will have some job... :) I still have a few questions : - How can we load/unload posix skin ? - Will this shared memory be accessible to non rt-task ? - What's the simplest way to share information with a non rt-task ? ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > Hi, > > I got some problems with shared memory. > I started from the shm_open example from opengroup.org. > When I compile it as non real time tasks, it works properly. But since I > tried to compile it with > gcc $(xeno-config --posix-cflags) shm_open.c $(xeno-config > --posix-ldflags) -o xeno_shm_open, > i get an EINVAL error from ftruncate that i can fix. > > Does shm under xenomai require particular things ? When applying the attached patch to xenomai (do not forget to rebuild the kernel), the attached program compiled with the attached Makefile works here. -- Gilles Chanteperdrix. Index: ksrc/skins/posix/shm.c === --- ksrc/skins/posix/shm.c (revision 1143) +++ ksrc/skins/posix/shm.c (working copy) @@ -516,10 +516,8 @@ is aligned). */ if (len) { -len += PAGE_SIZE + xnheap_overhead(len, PAGE_SIZE); +len += PAGE_SIZE + PAGE_ALIGN(xnheap_overhead(len, PAGE_SIZE)); len = PAGE_ALIGN(len); -if (len == 2 * PAGE_SIZE) -len = 3 * PAGE_SIZE; } err = 0; #include #include #include #include #include #include #define MAX_LEN 1 struct region {/* Defines "structure" of shared memory */ int len; char buf[MAX_LEN]; }; struct region *rptr; int fd; int main(int argc, const char *argv[]) { int fd, status; mlockall(MCL_CURRENT|MCL_FUTURE); /* Create shared memory object and set its size */ fd = shm_open("/myregion", O_CREAT | O_RDWR, S_IRUSR | S_IWUSR); if (fd == -1) { perror("shm_open"); exit(EXIT_FAILURE); } if ((status = ftruncate(fd, sizeof(struct region))) == -1) { /* Handle error */; perror("ftruncate"); close(fd); status = EXIT_FAILURE; goto close_and_unlink; } /* Map shared memory object */ rptr = (struct region *) mmap(NULL, sizeof(struct region), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (rptr == MAP_FAILED) { /* Handle error */; perror("mmap"); status = EXIT_FAILURE; goto close_and_unlink; } /* Now we can refer to mapped region using fields of rptr; for example, rptr->len */ munmap(rptr, sizeof(struct region)); close_and_unlink: close(fd); shm_unlink("/myregion"); return status; } DESTDIR=/home/gilles/files/perso/dev/build/nestor/inst XENO_CONFIG=$(DESTDIR)/usr/xenomai/bin/xeno-config CFLAGS:=$(shell DESTDIR=$(DESTDIR) $(XENO_CONFIG) --posix-cflags) -g -O2 -Wall -W -Werror-implicit-function-declaration LDFLAGS:=$(shell DESTDIR=$(DESTDIR) $(XENO_CONFIG) --posix-ldflags) LOADLIBES=-lpthread_rt all: test_shm test_shm: test_shm.o clean: $(RM) foo foo.o test_shm.o test_shm ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
Re: [Xenomai-help] shm_open, ftruncate
Lionel Perrin wrote: > Hi, > > I got some problems with shared memory. > I started from the shm_open example from opengroup.org. > When I compile it as non real time tasks, it works properly. But since I > tried to compile it with > gcc $(xeno-config --posix-cflags) shm_open.c $(xeno-config > --posix-ldflags) -o xeno_shm_open, > i get an EINVAL error from ftruncate that i can fix. > > Does shm under xenomai require particular things ? The posix skin does not use the new per-process cleanup callback yet, so you have to clean yourself the mappings, i.e. do not forget to call munmap before exiting your processes, or unload and reload the POSIX skin module before running your program. I tried your program and it did not fail here as it fails for you: mmap is returning an error of ENXIO, because of some bug that I am currently fixing. -- Gilles Chanteperdrix. ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help
[Xenomai-help] shm_open, ftruncate
Hi, I got some problems with shared memory. I started from the shm_open example from opengroup.org. When I compile it as non real time tasks, it works properly. But since I tried to compile it with gcc $(xeno-config --posix-cflags) shm_open.c $(xeno-config --posix-ldflags) -o xeno_shm_open, i get an EINVAL error from ftruncate that i can fix. Does shm under xenomai require particular things ? Thanks for your help... Lionel #include #include ... #define MAX_LEN 1 struct region {/* Defines "structure" of shared memory */ int len; char buf[MAX_LEN]; }; struct region *rptr; int fd; /* Create shared memory object and set its size */ fd = shm_open("/myregion", O_CREAT | O_RDWR, S_IRUSR | S_IWUSR); if (fd == -1) /* Handle error */; if (ftruncate(fd, sizeof(struct region)) == -1) /* Handle error */; /* Map shared memory object */ rptr = mmap(NULL, sizeof(struct region), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (rptr == MAP_FAILED) /* Handle error */; /* Now we can refer to mapped region using fields of rptr; for example, rptr->len */ ___ Xenomai-help mailing list Xenomai-help@gna.org https://mail.gna.org/listinfo/xenomai-help