Hello,
the next example look curious for me.
plz, tell me : where i wrong:
in this example
server allocates memory with mmap() call with flags
MAP_ANON|MAP_PHYS|MAP_NOX64K
(see: w/o MAP_SHARED!!!)
but in any case (also if MAP_PRIVATE is set)
client (separate process) could read/write this memory!!!
Q: WHY???
// EXAMPLE --------------------------------
#include <stdio.h>
#include <errno.h>
#include <stdlib.h>
#include <sys/dispatch.h>
#include <sys/mman.h>
#define ATTACH_POINT “myname”
#define ALLOCMEM(len) mmap(NULL, len, PROT_READ | PROT_WRITE |
PROT_NOCACHE, MAP_ANON|MAP_PHYS|MAP_NOX64K, NOFD, 0)
#define MMAPMEM(len,phys) mmap_device_memory( 0, len, PROT_READ | PROT_WRITE
| PROT_NOCACHE, 0, phys);
paddr_t mphys(void *addr) {
off64_t offset;
if(mem_offset64(addr, NOFD, 1, &offset, 0) == -1) {
return -1;
}
return offset;
}
/* We specify the header as being at least a pulse */
typedef struct _pulse msg_header_t;
/* Our real data comes after the header /
typedef struct _my_data {
msg_header_t hdr;
int data;
void shared_buf;
unsigned buflen;
uint64_t physical;
} my_data_t;
static uint64_t physical = (uint64_t)-1;
static char * shared_buf;
#define BUF_LEN 0x1000000
/*** Server Side of the code ***/
int server() {
name_attach_t *attach;
my_data_t msg;
int rcvid;
/* Create a local name (/dev/name/local/…) */
if ((attach = name_attach(NULL, ATTACH_POINT, 0)) == NULL) {
perror(“name_attach”);
return EXIT_FAILURE;
}
shared_buf = ALLOCMEM(BUF_LEN);
if (shared_buf == MAP_FAILED){
perror(“mmap”);
return EXIT_FAILURE;
}
physical = mphys (shared_buf);
printf (“Server: physical:%llX shared_buf:%p\n”, physical, shared_buf);
if (physical == (paddr_t)-1){
perror(“mphys”);
return EXIT_FAILURE;
}
memset (shared_buf, 0, BUF_LEN);
memset (&msg, 0, sizeof msg);
/* Do your MsgReceive’s here now with the chid */
while (1) {
strcpy (shared_buf, “server”);
rcvid = MsgReceive(attach->chid, &msg, sizeof(msg), NULL);
if (rcvid == -1) {/* Error condition, exit */
break;
}
if (rcvid == 0) {/* Pulse received /
switch (msg.hdr.code) {
case _PULSE_CODE_DISCONNECT:
/
- A client disconnected all its connections (called
- name_close() for each name_open() of our name) or
- terminated
/
ConnectDetach(msg.hdr.scoid);
break;
case _PULSE_CODE_UNBLOCK:
/ - REPLY blocked client wants to unblock (was hit by
- a signal or timed out). It’s up to you if you
- reply now or later.
/
break;
default:
/ - A pulse sent by one of your processes or a
- _PULSE_CODE_COIDDEATH or _PULSE_CODE_THREADDEATH
- from the kernel?
*/
}
continue;
}
/* A QNX IO message received, reject */
if (msg.hdr.type >= _IO_BASE && msg.hdr.type <= _IO_MAX) {
MsgError(rcvid, ENOSYS);
continue;
}
/* A message (presumable ours) received, handle */
printf(“Server receive %d \n”, msg.data);
msg.physical = physical;
msg.buflen = BUF_LEN;
msg.shared_buf = shared_buf;
printf (“physical:%llX shared_buf:%p\n”, msg.physical, msg.shared_buf);
MsgReply(rcvid, EOK, &msg, sizeof msg);
printf (“shared_buf:[%s]\n”,shared_buf);
}
/* Remove the name from the space */
name_detach(attach, 0);
return EXIT_SUCCESS;
}
/*** Client Side of the code ***/
int client() {
my_data_t msg;
my_data_t omsg;
int fd;
if ((fd = name_open(ATTACH_POINT, 0)) == -1) {
return EXIT_FAILURE;
}
memset (&msg, 0, sizeof msg);
memset (&omsg, 0, sizeof omsg);
/* We would have pre-defined data to stuff here */
msg.hdr.type = 0x00;
msg.hdr.subtype = 0x00;
/* Do whatever work you wanted with server connection */
for (msg.data=0; msg.data < 5; msg.data++) {
printf(“Client sending %d \n”, msg.data);
if (MsgSend(fd, &msg, sizeof(msg), &omsg, sizeof omsg) == -1) {
break;
}
if (shared_buf)
break;
printf (“physical:%llX shared_buf:%p buflen:%u\n”,
omsg.physical, omsg.shared_buf, omsg.buflen);
if (omsg.physical != (paddr_t)-1){
// shared_buf = mmap_device_memory( 0, BUF_LEN, PROT_READ | PROT_WRITE |
PROT_NOCACHE, 0, omsg.physical);
shared_buf = MMAPMEM (omsg.buflen, omsg.physical);
if (shared_buf == MAP_FAILED){
perror(“mmap_device_memory”);
}else{
printf (“shared_buf:[%s]\n”,shared_buf);
strcpy (shared_buf, “client”);
}
}
}
/* Close the connection */
name_close(fd);
return 0;//EXIT_SUCCESS;
}
int main(int argc, char **argv) {
int ret;
if (argc < 2) {
// printf(“Running Server … \n”);
// ret = server(); /* see name_attach() for this code /
printf(“Usage %s -s | -c \n”, argv[0]);
ret = EXIT_FAILURE;
}else if (strcmp(argv[1], “-c”) == 0) {
printf(“Running Client … \n”);
ret = client(); / see name_open() for this code /
}else if (strcmp(argv[1], “-s”) == 0) {
printf(“Running Server … \n”);
ret = server(); / see name_attach() for this code */
}else{
printf(“Usage %s -s | -c \n”, argv[0]);
ret = EXIT_FAILURE;
}
return ret;
}