int SYS$EXPREG(int pagcnt, long ret[2], int a, int b) { if (vms_mm) return sys$expreg(pagcnt,ret,a,b); int size=pagcnt*4096; // check ret[0]=malloc(size); ret[1]=ret[0]+size; return SS$_NORMAL; }
rlSharedMemory::rlSharedMemory(const char *shmname, unsigned long Size, int rwmode) { #ifdef RLUNIX struct shmid_ds buf; status = OK; name = new char[strlen(shmname)+1]; strcpy(name,shmname); _size = Size + sizeof(*mutex); // create file fdlock = open(name, O_RDWR | O_CREAT, rwmode ); if(fdlock < 0) { int ret; char buf[1024]; sprintf(buf,"could not write shm=%s\n",shmname); ret = ::write(1,buf,strlen(buf)); if(ret < 0) exit(-1); sprintf(buf,"you have to run this program as root !!!\n"); ret = ::write(1,buf,strlen(buf)); if(ret < 0) exit(-1); status=ERROR_FILE; exit(-1); } // old stuff, without suggestions from Stefan Lievens //shmkey = ftok(name,0); // //id = shmget(shmkey, _size, IPC_CREAT); //shmkey = ftok(name, 'R'); shmkey = ftok(name, 'b'); //id = shmget(shmkey, _size, 0600 | IPC_CREAT); id = shmget(shmkey, _size, rwmode | IPC_CREAT); if(id < 0) { status=ERROR_SHMGET; return; } base_adr = (char *) shmat(id,NULL,0); if(base_adr == NULL) { status=ERROR_SHMAT; return; } if(shmctl(id, IPC_STAT, &buf) != 0) { status=ERROR_SHMCTL; return; }; mutex = (pthread_mutex_t *) base_adr; user_adr = base_adr + sizeof(*mutex); flock(fdlock,LOCK_UN); #endif #ifdef __VMS int file_existed = 0; long ret,fd,page_size,pagelets,pagelet_size,file_block_size,flags,item,ident[2]; FILE *fp; ADD add_in,add_ret; struct dsc$descriptor_s section_name; struct FAB fab; status = OK; name = new char[strlen(shmname)+1]; strcpy(name,shmname); _size = Size + sizeof(*mutex); // The file block size is fixed file_block_size = 512; // Bytes // Get the page size item = SYI$_PAGE_SIZE; ret = lib$getsyi( &item , &page_size , 0 , 0 , 0 , 0 ); if(ret != SS$_NORMAL) { status=ERROR_FILE; return; } // Fill descriptor for section name section_name.dsc$w_length = strlen(name); section_name.dsc$a_pointer = name; section_name.dsc$b_dtype = DSC$K_DTYPE_T; section_name.dsc$b_class = DSC$K_CLASS_S; // The pagelet size is fixed pagelet_size = 512; // Bytes // Get memory if(_size % page_size == 0) pagelets = _size / pagelet_size; else pagelets = (_size / page_size + 1) * (page_size / pagelet_size); ret = sys$expreg(pagelets,&add_ret,0,0); if(ret != SS$_NORMAL) { status=ERROR_FILE; return; } // Set the addresses base_adr = (char *) add_ret.start; user_adr = base_adr + sizeof(*mutex); mutex = (pthread_mutex_t *) base_adr; if(base_adr == NULL) { status=ERROR_SHMAT; return; } // Fill the fab fab = cc$rms_fab; // Initialize fab fab.fab$b_fac = fab.fab$b_fac | FAB$M_PUT | FAB$M_DEL | FAB$M_GET | FAB$M_UPD; fab.fab$l_fna = name; fab.fab$b_fns = strlen(name); fab.fab$l_fop = fab.fab$l_fop | FAB$M_CIF // create file if not existent | FAB$M_CTG // contiguous | FAB$M_UFO; // user open fab.fab$b_shr = fab.fab$b_shr // shareble access | FAB$M_SHRPUT | FAB$M_UPI; fab.fab$l_alq = pagelets * pagelet_size / file_block_size; // Open the section file ret = sys$create (&fab); if(ret != RMS$_NORMAL && ret != RMS$_CREATED) { sys$close (&fab); status=ERROR_FILE; return; } // Set the channel fd = fab.fab$l_stv; // Fill the input address add_in.start = add_ret.start; add_in.end = add_ret.end; // Clear ident ident[0] = 0; ident[1] = 0; // Set flags flags = 0; flags = SEC$M_GBL | SEC$M_WRT | SEC$M_PERM; // Create and map the section ret = sys$crmpsc(&add_in ,&add_ret, (long)0 , // acmode flags , // flags §ion_name , // gsdnam &ident , // ident (long)0 , // relpag (short)fd , // chan pagelets , // pagcnt (long)0 , // vbn (long)0 , // prot (long)0 // pfc ); if(ret != SS$_NORMAL && ret != SS$_CREATED) { sys$close(&fab); status=ERROR_FILE; return; } // Test the section addresses if(add_in.start != add_ret.start || add_in.end != add_ret.end) { sys$close(&fab); status=ERROR_FILE; return; } // Close the section file ret = sys$close(&fab); // rlwthread_mutex_init(mutex,NULL); if(file_existed == 0) myinit(mutex); #endif #ifdef RLWIN32 HANDLE hShmem; //int file_existed; status = OK; name = new char[strlen(shmname)+1]; strcpy(name,shmname); _size = Size + sizeof(HANDLE); // sizeof(*mutex); //file_existed = 1; hSharedFile = CreateFile(name, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL ); if(hSharedFile == INVALID_HANDLE_VALUE) { //file_existed = 0; hSharedFile = CreateFile(name, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL ); } if(hSharedFile == INVALID_HANDLE_VALUE) { status=ERROR_FILE; return; } //char *global_name = new char[strlen(name)+40]; //strcpy(global_name,"Global\\"); strcat(global_name, name); //for(int i=7; i<strlen(global_name); i++) //{ // if (global_name[i] == ':') global_name[i] = '_'; // else if(global_name[i] == '\\') global_name[i] = '_'; // else if(global_name[i] == '.') global_name[i] = '_'; // else if(global_name[i] == ' ') global_name[i] = '_'; //} hShmem = CreateFileMapping( hSharedFile, NULL, // no security attributes PAGE_READWRITE, // read/write access 0, // size: high 32-bits _size, // size: low 32-bits 0); // name of map object // changed by FMakkinga 25-03-2013 global_name); // global_name); // name of map object //delete [] global_name; if(hShmem == NULL) { status=ERROR_FILE; return; } base_adr = (char *) MapViewOfFile( hShmem, // object to map view of FILE_MAP_WRITE, // read/write access 0, // high offset: map from 0, // low offset: beginning 0); // default: map entire file if(base_adr == NULL) { status=ERROR_FILE; return; } id = (int) hShmem; shmkey = (int) hSharedFile; mutex = (pthread_mutex_t *) base_adr; user_adr = base_adr + sizeof(*mutex); memset(&overlapped, 0, sizeof(overlapped)); // Changed by FMakkinga 22-03-2013 UnlockFileEx(hSharedFile,0,_size,0,&overlapped); #endif if(rwmode == 0) return; // no warning of unused parameter }