Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* This Source Code Form is subject to the terms of the Mozilla Public
3 : * License, v. 2.0. If a copy of the MPL was not distributed with this
4 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 :
6 : /*
7 : ** uxshm.c -- Unix Implementations NSPR Named Shared Memory
8 : **
9 : **
10 : ** lth. Jul-1999.
11 : **
12 : */
13 : #include <string.h>
14 : #include <prshm.h>
15 : #include <prerr.h>
16 : #include <prmem.h>
17 : #include "primpl.h"
18 : #include <fcntl.h>
19 :
20 : extern PRLogModuleInfo *_pr_shm_lm;
21 :
22 :
23 : #define NSPR_IPC_SHM_KEY 'b'
24 : /*
25 : ** Implementation for System V
26 : */
27 : #if defined PR_HAVE_SYSV_NAMED_SHARED_MEMORY
28 : #include <sys/ipc.h>
29 : #include <sys/shm.h>
30 : #include <sys/types.h>
31 : #include <sys/stat.h>
32 :
33 : #define _MD_OPEN_SHARED_MEMORY _MD_OpenSharedMemory
34 : #define _MD_ATTACH_SHARED_MEMORY _MD_AttachSharedMemory
35 : #define _MD_DETACH_SHARED_MEMORY _MD_DetachSharedMemory
36 : #define _MD_CLOSE_SHARED_MEMORY _MD_CloseSharedMemory
37 : #define _MD_DELETE_SHARED_MEMORY _MD_DeleteSharedMemory
38 :
39 0 : extern PRSharedMemory * _MD_OpenSharedMemory(
40 : const char *name,
41 : PRSize size,
42 : PRIntn flags,
43 : PRIntn mode
44 : )
45 : {
46 0 : PRStatus rc = PR_SUCCESS;
47 : key_t key;
48 : PRSharedMemory *shm;
49 : char ipcname[PR_IPC_NAME_SIZE];
50 :
51 0 : rc = _PR_MakeNativeIPCName( name, ipcname, PR_IPC_NAME_SIZE, _PRIPCShm );
52 0 : if ( PR_FAILURE == rc )
53 : {
54 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
55 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
56 : ("_MD_OpenSharedMemory(): _PR_MakeNativeIPCName() failed: %s", name ));
57 0 : return( NULL );
58 : }
59 :
60 0 : shm = PR_NEWZAP( PRSharedMemory );
61 0 : if ( NULL == shm )
62 : {
63 0 : PR_SetError(PR_OUT_OF_MEMORY_ERROR, 0 );
64 0 : PR_LOG(_pr_shm_lm, PR_LOG_DEBUG, ( "PR_OpenSharedMemory: New PRSharedMemory out of memory"));
65 0 : return( NULL );
66 : }
67 :
68 0 : shm->ipcname = (char*)PR_MALLOC( strlen( ipcname ) + 1 );
69 0 : if ( NULL == shm->ipcname )
70 : {
71 0 : PR_SetError(PR_OUT_OF_MEMORY_ERROR, 0 );
72 0 : PR_LOG(_pr_shm_lm, PR_LOG_DEBUG, ( "PR_OpenSharedMemory: New shm->ipcname out of memory"));
73 0 : PR_DELETE( shm );
74 0 : return( NULL );
75 : }
76 :
77 : /* copy args to struct */
78 0 : strcpy( shm->ipcname, ipcname );
79 0 : shm->size = size;
80 0 : shm->mode = mode;
81 0 : shm->flags = flags;
82 0 : shm->ident = _PR_SHM_IDENT;
83 :
84 : /* create the file first */
85 0 : if ( flags & PR_SHM_CREATE ) {
86 0 : int osfd = open( shm->ipcname, (O_RDWR | O_CREAT), shm->mode );
87 0 : if ( -1 == osfd ) {
88 0 : _PR_MD_MAP_OPEN_ERROR( errno );
89 0 : PR_FREEIF( shm->ipcname );
90 0 : PR_DELETE( shm );
91 0 : return( NULL );
92 : }
93 0 : if ( close(osfd) == -1 ) {
94 0 : _PR_MD_MAP_CLOSE_ERROR( errno );
95 0 : PR_FREEIF( shm->ipcname );
96 0 : PR_DELETE( shm );
97 0 : return( NULL );
98 : }
99 : }
100 :
101 : /* hash the shm.name to an ID */
102 0 : key = ftok( shm->ipcname, NSPR_IPC_SHM_KEY );
103 0 : if ( -1 == key )
104 : {
105 0 : rc = PR_FAILURE;
106 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
107 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
108 : ("_MD_OpenSharedMemory(): ftok() failed on name: %s", shm->ipcname));
109 0 : PR_FREEIF( shm->ipcname );
110 0 : PR_DELETE( shm );
111 0 : return( NULL );
112 : }
113 :
114 : /* get the shared memory */
115 0 : if ( flags & PR_SHM_CREATE ) {
116 0 : shm->id = shmget( key, shm->size, ( shm->mode | IPC_CREAT|IPC_EXCL));
117 0 : if ( shm->id >= 0 ) {
118 0 : return( shm );
119 : }
120 0 : if ((errno == EEXIST) && (flags & PR_SHM_EXCL)) {
121 0 : PR_SetError( PR_FILE_EXISTS_ERROR, errno );
122 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
123 : ("_MD_OpenSharedMemory(): shmget() exclusive failed, errno: %d", errno));
124 0 : PR_FREEIF(shm->ipcname);
125 0 : PR_DELETE(shm);
126 0 : return(NULL);
127 : }
128 : }
129 :
130 0 : shm->id = shmget( key, shm->size, shm->mode );
131 0 : if ( -1 == shm->id ) {
132 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
133 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
134 : ("_MD_OpenSharedMemory(): shmget() failed, errno: %d", errno));
135 0 : PR_FREEIF(shm->ipcname);
136 0 : PR_DELETE(shm);
137 0 : return(NULL);
138 : }
139 :
140 0 : return( shm );
141 : } /* end _MD_OpenSharedMemory() */
142 :
143 0 : extern void * _MD_AttachSharedMemory( PRSharedMemory *shm, PRIntn flags )
144 : {
145 : void *addr;
146 0 : PRUint32 aFlags = shm->mode;
147 :
148 0 : PR_ASSERT( shm->ident == _PR_SHM_IDENT );
149 :
150 0 : aFlags |= (flags & PR_SHM_READONLY )? SHM_RDONLY : 0;
151 :
152 0 : addr = shmat( shm->id, NULL, aFlags );
153 0 : if ( (void*)-1 == addr )
154 : {
155 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
156 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
157 : ("_MD_AttachSharedMemory(): shmat() failed on name: %s, OsError: %d",
158 : shm->ipcname, PR_GetOSError() ));
159 0 : addr = NULL;
160 : }
161 :
162 0 : return addr;
163 : }
164 :
165 0 : extern PRStatus _MD_DetachSharedMemory( PRSharedMemory *shm, void *addr )
166 : {
167 0 : PRStatus rc = PR_SUCCESS;
168 : PRIntn urc;
169 :
170 0 : PR_ASSERT( shm->ident == _PR_SHM_IDENT );
171 :
172 0 : urc = shmdt( addr );
173 0 : if ( -1 == urc )
174 : {
175 0 : rc = PR_FAILURE;
176 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
177 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
178 : ("_MD_DetachSharedMemory(): shmdt() failed on name: %s", shm->ipcname ));
179 : }
180 :
181 0 : return rc;
182 : }
183 :
184 0 : extern PRStatus _MD_CloseSharedMemory( PRSharedMemory *shm )
185 : {
186 0 : PR_ASSERT( shm->ident == _PR_SHM_IDENT );
187 :
188 0 : PR_FREEIF(shm->ipcname);
189 0 : PR_DELETE(shm);
190 :
191 0 : return PR_SUCCESS;
192 : }
193 :
194 0 : extern PRStatus _MD_DeleteSharedMemory( const char *name )
195 : {
196 0 : PRStatus rc = PR_SUCCESS;
197 : key_t key;
198 : int id;
199 : PRIntn urc;
200 : char ipcname[PR_IPC_NAME_SIZE];
201 :
202 0 : rc = _PR_MakeNativeIPCName( name, ipcname, PR_IPC_NAME_SIZE, _PRIPCShm );
203 0 : if ( PR_FAILURE == rc )
204 : {
205 0 : PR_SetError( PR_UNKNOWN_ERROR , errno );
206 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
207 : ("_MD_DeleteSharedMemory(): _PR_MakeNativeIPCName() failed: %s", name ));
208 0 : return(PR_FAILURE);
209 : }
210 :
211 : /* create the file first */
212 : {
213 0 : int osfd = open( ipcname, (O_RDWR | O_CREAT), 0666 );
214 0 : if ( -1 == osfd ) {
215 0 : _PR_MD_MAP_OPEN_ERROR( errno );
216 0 : return( PR_FAILURE );
217 : }
218 0 : if ( close(osfd) == -1 ) {
219 0 : _PR_MD_MAP_CLOSE_ERROR( errno );
220 0 : return( PR_FAILURE );
221 : }
222 : }
223 :
224 : /* hash the shm.name to an ID */
225 0 : key = ftok( ipcname, NSPR_IPC_SHM_KEY );
226 0 : if ( -1 == key )
227 : {
228 0 : rc = PR_FAILURE;
229 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
230 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
231 : ("_MD_DeleteSharedMemory(): ftok() failed on name: %s", ipcname));
232 : }
233 :
234 : #ifdef SYMBIAN
235 : /* In Symbian OS the system imposed minimum is 1 byte, instead of ZERO */
236 : id = shmget( key, 1, 0 );
237 : #else
238 0 : id = shmget( key, 0, 0 );
239 : #endif
240 0 : if ( -1 == id ) {
241 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
242 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
243 : ("_MD_DeleteSharedMemory(): shmget() failed, errno: %d", errno));
244 0 : return(PR_FAILURE);
245 : }
246 :
247 0 : urc = shmctl( id, IPC_RMID, NULL );
248 0 : if ( -1 == urc )
249 : {
250 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
251 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
252 : ("_MD_DeleteSharedMemory(): shmctl() failed on name: %s", ipcname ));
253 0 : return(PR_FAILURE);
254 : }
255 :
256 0 : urc = unlink( ipcname );
257 0 : if ( -1 == urc ) {
258 0 : _PR_MD_MAP_UNLINK_ERROR( errno );
259 0 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
260 : ("_MD_DeleteSharedMemory(): unlink() failed: %s", ipcname ));
261 0 : return(PR_FAILURE);
262 : }
263 :
264 0 : return rc;
265 : } /* end _MD_DeleteSharedMemory() */
266 :
267 : /*
268 : ** Implementation for Posix
269 : */
270 : #elif defined PR_HAVE_POSIX_NAMED_SHARED_MEMORY
271 : #include <sys/mman.h>
272 :
273 : #define _MD_OPEN_SHARED_MEMORY _MD_OpenSharedMemory
274 : #define _MD_ATTACH_SHARED_MEMORY _MD_AttachSharedMemory
275 : #define _MD_DETACH_SHARED_MEMORY _MD_DetachSharedMemory
276 : #define _MD_CLOSE_SHARED_MEMORY _MD_CloseSharedMemory
277 : #define _MD_DELETE_SHARED_MEMORY _MD_DeleteSharedMemory
278 :
279 : struct _MDSharedMemory {
280 : int handle;
281 : };
282 :
283 : extern PRSharedMemory * _MD_OpenSharedMemory(
284 : const char *name,
285 : PRSize size,
286 : PRIntn flags,
287 : PRIntn mode
288 : )
289 : {
290 : PRStatus rc = PR_SUCCESS;
291 : PRInt32 end;
292 : PRSharedMemory *shm;
293 : char ipcname[PR_IPC_NAME_SIZE];
294 :
295 : rc = _PR_MakeNativeIPCName( name, ipcname, PR_IPC_NAME_SIZE, _PRIPCShm );
296 : if ( PR_FAILURE == rc )
297 : {
298 : PR_SetError( PR_UNKNOWN_ERROR , errno );
299 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
300 : ("_MD_OpenSharedMemory(): _PR_MakeNativeIPCName() failed: %s", name ));
301 : return( NULL );
302 : }
303 :
304 : shm = PR_NEWZAP( PRSharedMemory );
305 : if ( NULL == shm )
306 : {
307 : PR_SetError(PR_OUT_OF_MEMORY_ERROR, 0 );
308 : PR_LOG(_pr_shm_lm, PR_LOG_DEBUG, ( "PR_OpenSharedMemory: New PRSharedMemory out of memory"));
309 : return( NULL );
310 : }
311 :
312 : shm->ipcname = PR_MALLOC( strlen( ipcname ) + 1 );
313 : if ( NULL == shm->ipcname )
314 : {
315 : PR_SetError(PR_OUT_OF_MEMORY_ERROR, 0 );
316 : PR_LOG(_pr_shm_lm, PR_LOG_DEBUG, ( "PR_OpenSharedMemory: New shm->ipcname out of memory"));
317 : return( NULL );
318 : }
319 :
320 : /* copy args to struct */
321 : strcpy( shm->ipcname, ipcname );
322 : shm->size = size;
323 : shm->mode = mode;
324 : shm->flags = flags;
325 : shm->ident = _PR_SHM_IDENT;
326 :
327 : /*
328 : ** Create the shared memory
329 : */
330 : if ( flags & PR_SHM_CREATE ) {
331 : int oflag = (O_CREAT | O_RDWR);
332 :
333 : if ( flags & PR_SHM_EXCL )
334 : oflag |= O_EXCL;
335 : shm->id = shm_open( shm->ipcname, oflag, shm->mode );
336 : } else {
337 : shm->id = shm_open( shm->ipcname, O_RDWR, shm->mode );
338 : }
339 :
340 : if ( -1 == shm->id ) {
341 : _PR_MD_MAP_DEFAULT_ERROR( errno );
342 : PR_LOG(_pr_shm_lm, PR_LOG_DEBUG,
343 : ("_MD_OpenSharedMemory(): shm_open failed: %s, OSError: %d",
344 : shm->ipcname, PR_GetOSError()));
345 : PR_DELETE( shm->ipcname );
346 : PR_DELETE( shm );
347 : return(NULL);
348 : }
349 :
350 : end = ftruncate( shm->id, shm->size );
351 : if ( -1 == end ) {
352 : _PR_MD_MAP_DEFAULT_ERROR( errno );
353 : PR_LOG(_pr_shm_lm, PR_LOG_DEBUG,
354 : ("_MD_OpenSharedMemory(): ftruncate failed, OSError: %d",
355 : PR_GetOSError()));
356 : PR_DELETE( shm->ipcname );
357 : PR_DELETE( shm );
358 : return(NULL);
359 : }
360 :
361 : return(shm);
362 : } /* end _MD_OpenSharedMemory() */
363 :
364 : extern void * _MD_AttachSharedMemory( PRSharedMemory *shm, PRIntn flags )
365 : {
366 : void *addr;
367 : PRIntn prot = (PROT_READ | PROT_WRITE);
368 :
369 : PR_ASSERT( shm->ident == _PR_SHM_IDENT );
370 :
371 : if ( PR_SHM_READONLY == flags)
372 : prot ^= PROT_WRITE;
373 :
374 : addr = mmap( (void*)0, shm->size, prot, MAP_SHARED, shm->id, 0 );
375 : if ((void*)-1 == addr )
376 : {
377 : _PR_MD_MAP_DEFAULT_ERROR( errno );
378 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
379 : ("_MD_AttachSharedMemory(): mmap failed: %s, errno: %d",
380 : shm->ipcname, PR_GetOSError()));
381 : addr = NULL;
382 : } else {
383 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
384 : ("_MD_AttachSharedMemory(): name: %s, attached at: %p", shm->ipcname, addr));
385 : }
386 :
387 : return addr;
388 : }
389 :
390 : extern PRStatus _MD_DetachSharedMemory( PRSharedMemory *shm, void *addr )
391 : {
392 : PRStatus rc = PR_SUCCESS;
393 : PRIntn urc;
394 :
395 : PR_ASSERT( shm->ident == _PR_SHM_IDENT );
396 :
397 : urc = munmap( addr, shm->size );
398 : if ( -1 == urc )
399 : {
400 : rc = PR_FAILURE;
401 : _PR_MD_MAP_DEFAULT_ERROR( errno );
402 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
403 : ("_MD_DetachSharedMemory(): munmap failed: %s, errno: %d",
404 : shm->ipcname, PR_GetOSError()));
405 : }
406 : return rc;
407 : }
408 :
409 : extern PRStatus _MD_CloseSharedMemory( PRSharedMemory *shm )
410 : {
411 : int urc;
412 :
413 : PR_ASSERT( shm->ident == _PR_SHM_IDENT );
414 :
415 : urc = close( shm->id );
416 : if ( -1 == urc ) {
417 : _PR_MD_MAP_CLOSE_ERROR( errno );
418 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
419 : ("_MD_CloseSharedMemory(): close() failed, error: %d", PR_GetOSError()));
420 : return(PR_FAILURE);
421 : }
422 : PR_DELETE( shm->ipcname );
423 : PR_DELETE( shm );
424 : return PR_SUCCESS;
425 : }
426 :
427 : extern PRStatus _MD_DeleteSharedMemory( const char *name )
428 : {
429 : PRStatus rc = PR_SUCCESS;
430 : PRUintn urc;
431 : char ipcname[PR_IPC_NAME_SIZE];
432 :
433 : rc = _PR_MakeNativeIPCName( name, ipcname, PR_IPC_NAME_SIZE, _PRIPCShm );
434 : if ( PR_FAILURE == rc )
435 : {
436 : PR_SetError( PR_UNKNOWN_ERROR , errno );
437 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
438 : ("_MD_OpenSharedMemory(): _PR_MakeNativeIPCName() failed: %s", name ));
439 : return rc;
440 : }
441 :
442 : urc = shm_unlink( ipcname );
443 : if ( -1 == urc ) {
444 : rc = PR_FAILURE;
445 : _PR_MD_MAP_DEFAULT_ERROR( errno );
446 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
447 : ("_MD_DeleteSharedMemory(): shm_unlink failed: %s, errno: %d",
448 : ipcname, PR_GetOSError()));
449 : } else {
450 : PR_LOG( _pr_shm_lm, PR_LOG_DEBUG,
451 : ("_MD_DeleteSharedMemory(): %s, success", ipcname));
452 : }
453 :
454 : return rc;
455 : } /* end _MD_DeleteSharedMemory() */
456 : #endif
457 :
458 :
459 :
460 : /*
461 : ** Unix implementation for anonymous memory (file) mapping
462 : */
463 : extern PRLogModuleInfo *_pr_shma_lm;
464 :
465 : #include <unistd.h>
466 :
467 0 : extern PRFileMap* _md_OpenAnonFileMap(
468 : const char *dirName,
469 : PRSize size,
470 : PRFileMapProtect prot
471 : )
472 : {
473 0 : PRFileMap *fm = NULL;
474 : PRFileDesc *fd;
475 : int osfd;
476 : PRIntn urc;
477 0 : PRIntn mode = 0600;
478 : char *genName;
479 0 : pid_t pid = getpid(); /* for generating filename */
480 0 : PRThread *tid = PR_GetCurrentThread(); /* for generating filename */
481 : int incr; /* for generating filename */
482 0 : const int maxTries = 20; /* maximum # attempts at a unique filename */
483 : PRInt64 size64; /* 64-bit version of 'size' */
484 :
485 : /*
486 : ** generate a filename from input and runtime environment
487 : ** open the file, unlink the file.
488 : ** make maxTries number of attempts at uniqueness in the filename
489 : */
490 0 : for ( incr = 0; incr < maxTries ; incr++ ) {
491 : #if defined(SYMBIAN)
492 : #define NSPR_AFM_FILENAME "%s\\NSPR-AFM-%d-%p.%d"
493 : #else
494 : #define NSPR_AFM_FILENAME "%s/.NSPR-AFM-%d-%p.%d"
495 : #endif
496 0 : genName = PR_smprintf( NSPR_AFM_FILENAME,
497 : dirName, (int) pid, tid, incr );
498 0 : if ( NULL == genName ) {
499 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
500 : ("_md_OpenAnonFileMap(): PR_snprintf(): failed, generating filename"));
501 0 : goto Finished;
502 : }
503 :
504 : /* create the file */
505 0 : osfd = open(genName, (O_CREAT | O_EXCL | O_RDWR), mode);
506 0 : if (-1 == osfd) {
507 0 : if (EEXIST == errno) {
508 0 : PR_smprintf_free(genName);
509 0 : continue; /* name exists, try again */
510 : }
511 0 : _PR_MD_MAP_OPEN_ERROR(errno);
512 0 : PR_LOG(
513 : _pr_shma_lm,
514 : PR_LOG_DEBUG,
515 : ("_md_OpenAnonFileMap(): open(): failed, filename: %s, errno: %d",
516 : genName,
517 : PR_GetOSError()));
518 0 : PR_smprintf_free(genName);
519 0 : goto Finished;
520 : }
521 0 : break; /* name generation and open successful, break; */
522 : } /* end for() */
523 :
524 0 : if (incr == maxTries) {
525 0 : PR_ASSERT(-1 == osfd);
526 0 : PR_ASSERT(EEXIST == errno);
527 0 : _PR_MD_MAP_OPEN_ERROR(errno);
528 0 : goto Finished;
529 : }
530 :
531 0 : urc = unlink( genName );
532 : #if defined(SYMBIAN) && defined(__WINS__)
533 : /* If it is being used by the system or another process, Symbian OS
534 : * Emulator(WINS) considers this an error. */
535 : if ( -1 == urc && EACCES != errno ) {
536 : #else
537 0 : if ( -1 == urc ) {
538 : #endif
539 0 : _PR_MD_MAP_UNLINK_ERROR( errno );
540 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
541 : ("_md_OpenAnonFileMap(): failed on unlink(), errno: %d", errno));
542 0 : PR_smprintf_free( genName );
543 0 : close( osfd );
544 0 : goto Finished;
545 : }
546 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
547 : ("_md_OpenAnonFileMap(): unlink(): %s", genName ));
548 :
549 0 : PR_smprintf_free( genName );
550 :
551 0 : fd = PR_ImportFile( osfd );
552 0 : if ( NULL == fd ) {
553 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
554 : ("_md_OpenAnonFileMap(): PR_ImportFile(): failed"));
555 0 : goto Finished;
556 : }
557 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
558 : ("_md_OpenAnonFileMap(): fd: %p", fd ));
559 :
560 0 : urc = ftruncate( fd->secret->md.osfd, size );
561 0 : if ( -1 == urc ) {
562 0 : _PR_MD_MAP_DEFAULT_ERROR( errno );
563 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
564 : ("_md_OpenAnonFileMap(): failed on ftruncate(), errno: %d", errno));
565 0 : PR_Close( fd );
566 0 : goto Finished;
567 : }
568 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
569 : ("_md_OpenAnonFileMap(): ftruncate(): size: %d", size ));
570 :
571 0 : LL_UI2L(size64, size); /* PRSize (size_t) is unsigned */
572 0 : fm = PR_CreateFileMap( fd, size64, prot );
573 0 : if ( NULL == fm ) {
574 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
575 : ("PR_OpenAnonFileMap(): failed"));
576 0 : PR_Close( fd );
577 0 : goto Finished;
578 : }
579 0 : fm->md.isAnonFM = PR_TRUE; /* set fd close */
580 :
581 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
582 : ("_md_OpenAnonFileMap(): PR_CreateFileMap(): fm: %p", fm ));
583 :
584 : Finished:
585 0 : return(fm);
586 : } /* end md_OpenAnonFileMap() */
587 :
588 : /*
589 : ** _md_ExportFileMapAsString()
590 : **
591 : **
592 : */
593 0 : extern PRStatus _md_ExportFileMapAsString(
594 : PRFileMap *fm,
595 : PRSize bufSize,
596 : char *buf
597 : )
598 : {
599 : PRIntn written;
600 0 : PRIntn prot = (PRIntn)fm->prot;
601 :
602 0 : written = PR_snprintf( buf, bufSize, "%ld:%d",
603 0 : fm->fd->secret->md.osfd, prot );
604 :
605 0 : return((written == -1)? PR_FAILURE : PR_SUCCESS);
606 : } /* end _md_ExportFileMapAsString() */
607 :
608 :
609 0 : extern PRFileMap * _md_ImportFileMapFromString(
610 : const char *fmstring
611 : )
612 : {
613 : PRStatus rc;
614 : PRInt32 osfd;
615 : PRIntn prot; /* really: a PRFileMapProtect */
616 : PRFileDesc *fd;
617 0 : PRFileMap *fm = NULL; /* default return value */
618 : PRFileInfo64 info;
619 :
620 0 : PR_sscanf( fmstring, "%ld:%d", &osfd, &prot );
621 :
622 : /* import the os file descriptor */
623 0 : fd = PR_ImportFile( osfd );
624 0 : if ( NULL == fd ) {
625 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
626 : ("_md_ImportFileMapFromString(): PR_ImportFile() failed"));
627 0 : goto Finished;
628 : }
629 :
630 0 : rc = PR_GetOpenFileInfo64( fd, &info );
631 0 : if ( PR_FAILURE == rc ) {
632 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
633 : ("_md_ImportFileMapFromString(): PR_GetOpenFileInfo64() failed"));
634 0 : goto Finished;
635 : }
636 :
637 0 : fm = PR_CreateFileMap( fd, info.size, (PRFileMapProtect)prot );
638 0 : if ( NULL == fm ) {
639 0 : PR_LOG( _pr_shma_lm, PR_LOG_DEBUG,
640 : ("_md_ImportFileMapFromString(): PR_CreateFileMap() failed"));
641 : }
642 :
643 : Finished:
644 0 : return(fm);
645 : } /* end _md_ImportFileMapFromString() */
|