Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(369)

Side by Side Diff: base/shared_memory_posix.cc

Issue 21063: Transition POSIX shmem to use lockf(), not semaphores. (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: '' Created 11 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « base/shared_memory.h ('k') | base/shared_memory_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "base/shared_memory.h" 5 #include "base/shared_memory.h"
6 6
7 #include <errno.h> 7 #include <errno.h>
8 #include <fcntl.h> 8 #include <fcntl.h>
9 #include <sys/mman.h> 9 #include <sys/mman.h>
10 10
11 #include "base/file_util.h" 11 #include "base/file_util.h"
12 #include "base/logging.h" 12 #include "base/logging.h"
13 #include "base/platform_thread.h"
13 #include "base/string_util.h" 14 #include "base/string_util.h"
14 15
15 namespace base { 16 namespace base {
16 17
17 namespace { 18 namespace {
18 // Paranoia. Semaphores and shared memory segments should live in different 19 // Paranoia. Semaphores and shared memory segments should live in different
19 // namespaces, but who knows what's out there. 20 // namespaces, but who knows what's out there.
20 const char kSemaphoreSuffix[] = "-sem"; 21 const char kSemaphoreSuffix[] = "-sem";
21 } 22 }
22 23
23 SharedMemory::SharedMemory() 24 SharedMemory::SharedMemory()
24 : mapped_file_(-1), 25 : mapped_file_(-1),
25 memory_(NULL), 26 memory_(NULL),
26 read_only_(false), 27 read_only_(false),
27 max_size_(0), 28 max_size_(0) {
28 lock_(NULL) {
29 } 29 }
30 30
31 SharedMemory::SharedMemory(SharedMemoryHandle handle, bool read_only) 31 SharedMemory::SharedMemory(SharedMemoryHandle handle, bool read_only)
32 : mapped_file_(handle), 32 : mapped_file_(handle),
33 memory_(NULL), 33 memory_(NULL),
34 read_only_(read_only), 34 read_only_(read_only),
35 max_size_(0), 35 max_size_(0) {
36 lock_(NULL) {
37 } 36 }
38 37
39 SharedMemory::SharedMemory(SharedMemoryHandle handle, bool read_only, 38 SharedMemory::SharedMemory(SharedMemoryHandle handle, bool read_only,
40 ProcessHandle process) 39 ProcessHandle process)
41 : mapped_file_(handle), 40 : mapped_file_(handle),
42 memory_(NULL), 41 memory_(NULL),
43 read_only_(read_only), 42 read_only_(read_only),
44 max_size_(0), 43 max_size_(0) {
45 lock_(NULL) {
46 // We don't handle this case yet (note the ignored parameter); let's die if 44 // We don't handle this case yet (note the ignored parameter); let's die if
47 // someone comes calling. 45 // someone comes calling.
48 NOTREACHED(); 46 NOTREACHED();
49 } 47 }
50 48
51 SharedMemory::~SharedMemory() { 49 SharedMemory::~SharedMemory() {
52 Close(); 50 Close();
53 if (lock_ != NULL)
54 sem_close(lock_);
55 } 51 }
56 52
57 bool SharedMemory::Create(const std::wstring &name, bool read_only, 53 bool SharedMemory::Create(const std::wstring &name, bool read_only,
58 bool open_existing, size_t size) { 54 bool open_existing, size_t size) {
59 read_only_ = read_only; 55 read_only_ = read_only;
60 56
61 int posix_flags = 0; 57 int posix_flags = 0;
62 posix_flags |= read_only ? O_RDONLY : O_RDWR; 58 posix_flags |= read_only ? O_RDONLY : O_RDWR;
63 if (!open_existing || mapped_file_ <= 0) 59 if (!open_existing || mapped_file_ <= 0)
64 posix_flags |= O_CREAT; 60 posix_flags |= O_CREAT;
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after
198 // possibly shrink. 194 // possibly shrink.
199 if ((ftruncate(fileno(fp), size) != 0) || 195 if ((ftruncate(fileno(fp), size) != 0) ||
200 (fflush(fp) != 0)) { 196 (fflush(fp) != 0)) {
201 return false; 197 return false;
202 } 198 }
203 } 199 }
204 } 200 }
205 201
206 mapped_file_ = dup(fileno(fp)); 202 mapped_file_ = dup(fileno(fp));
207 DCHECK(mapped_file_ >= 0); 203 DCHECK(mapped_file_ >= 0);
208
209 mode_t posix_mode = S_IRUSR | S_IWUSR; // owner read/write
210 // name_ that includes a tmpdir easily exceeds SEM_NAME_LEN,
211 // so we cannot use it directly as the basis for a sem_name_.
212 sem_name_ = WideToUTF8(name) + kSemaphoreSuffix;
213 lock_ = sem_open(sem_name_.c_str(), O_CREAT, posix_mode, 1);
214 if (lock_ == SEM_FAILED) {
215 close(mapped_file_);
216 mapped_file_ = -1;
217 lock_ = NULL;
218 return false;
219 }
220
221 return true; 204 return true;
222 } 205 }
223 206
224 bool SharedMemory::Map(size_t bytes) { 207 bool SharedMemory::Map(size_t bytes) {
225 if (mapped_file_ == -1) 208 if (mapped_file_ == -1)
226 return false; 209 return false;
227 210
228 memory_ = mmap(NULL, bytes, PROT_READ | (read_only_ ? 0 : PROT_WRITE), 211 memory_ = mmap(NULL, bytes, PROT_READ | (read_only_ ? 0 : PROT_WRITE),
229 MAP_SHARED, mapped_file_, 0); 212 MAP_SHARED, mapped_file_, 0);
230 213
(...skipping 25 matching lines...) Expand all
256 239
257 void SharedMemory::Close() { 240 void SharedMemory::Close() {
258 241
259 Unmap(); 242 Unmap();
260 243
261 std::string posix_name(WideToUTF8(name_)); 244 std::string posix_name(WideToUTF8(name_));
262 if (mapped_file_ > 0) { 245 if (mapped_file_ > 0) {
263 close(mapped_file_); 246 close(mapped_file_);
264 mapped_file_ = -1; 247 mapped_file_ = -1;
265 } 248 }
249 }
266 250
267 if (lock_) { 251 void SharedMemory::LockOrUnlockCommon(int function) {
268 sem_unlink(sem_name_.c_str()); 252 DCHECK(mapped_file_ >= 0);
269 lock_ = NULL; 253 while (lockf(mapped_file_, function, 0) < 0) {
254 if (errno == EINTR) {
255 continue;
256 } else if (errno == ENOLCK) {
257 // temporary kernel resource exaustion
258 PlatformThread::Sleep(500);
259 continue;
260 } else {
261 NOTREACHED() << "lockf() failed."
262 << " function:" << function
263 << " fd:" << mapped_file_
264 << " errno:" << errno
265 << " msg:" << strerror(errno);
266 }
270 } 267 }
271 } 268 }
272 269
273 void SharedMemory::Lock() { 270 void SharedMemory::Lock() {
274 DCHECK(lock_ != NULL); 271 LockOrUnlockCommon(F_LOCK);
275 while(sem_wait(lock_) < 0) {
276 DCHECK(errno == EAGAIN || errno == EINTR);
277 }
278 } 272 }
279 273
280 void SharedMemory::Unlock() { 274 void SharedMemory::Unlock() {
281 DCHECK(lock_ != NULL); 275 LockOrUnlockCommon(F_ULOCK);
282 int result = sem_post(lock_);
283 DCHECK(result == 0);
284 } 276 }
285 277
286 } // namespace base 278 } // namespace base
OLDNEW
« no previous file with comments | « base/shared_memory.h ('k') | base/shared_memory_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698