/*
- * $Id$
- *
- * DEBUG: section 54 Interprocess Communication
+ * Copyright (C) 1996-2018 The Squid Software Foundation and contributors
*
+ * Squid software is distributed under GPLv2+ license and includes
+ * contributions from numerous individuals and organizations.
+ * Please see the COPYING and CONTRIBUTORS files for details.
*/
-#include "config.h"
+/* DEBUG: section 54 Interprocess Communication */
+
+#include "squid.h"
#include "base/TextException.h"
#include "ipc/mem/Page.h"
#include "ipc/mem/PagePool.h"
-
-static String
-PageIndexId(String id)
-{
- id.append("-index");
- return id;
-}
-
-
// Ipc::Mem::PagePool
-Ipc::Mem::PagePool::PagePool(const String &id, const unsigned int capacity, const size_t pageSize):
- pageIndex(PageIndexId(id), capacity),
- shm(id.termedBuf())
+Ipc::Mem::PagePool::Owner *
+Ipc::Mem::PagePool::Init(const char *const id, const unsigned int capacity, const size_t pageSize)
{
- shm.create(Shared::MemSize(capacity, pageSize));
- assert(shm.mem());
- shared = new (shm.mem()) Shared(capacity, pageSize);
+ static uint32_t LastPagePoolId = 0;
+ if (++LastPagePoolId == 0)
+ ++LastPagePoolId; // skip zero pool id
+ return shm_new(PageStack)(id, LastPagePoolId, capacity, pageSize);
}
-Ipc::Mem::PagePool::PagePool(const String &id):
- pageIndex(PageIndexId(id)), shm(id.termedBuf())
+Ipc::Mem::PagePool::PagePool(const char *const id):
+ pageIndex(shm_old(PageStack)(id)),
+ theLevels(reinterpret_cast<Levels_t *>(
+ reinterpret_cast<char *>(pageIndex.getRaw()) +
+ pageIndex->stackSize())),
+ theBuf(reinterpret_cast<char *>(theLevels + PageId::maxPurpose))
{
- shm.open();
- shared = reinterpret_cast<Shared *>(shm.mem());
- assert(shared);
}
-void
-Ipc::Mem::PagePool::Unlink(const String &id)
+size_t
+Ipc::Mem::PagePool::level(const int purpose) const
{
- PageStack::Unlink(PageIndexId(id));
- Segment::Unlink(id.termedBuf());
+ Must(0 <= purpose && purpose < PageId::maxPurpose);
+ return theLevels[purpose];
}
bool
-Ipc::Mem::PagePool::get(PageId &page)
+Ipc::Mem::PagePool::get(const PageId::Purpose purpose, PageId &page)
{
- if (pageIndex.pop(page.number)) {
- page.pool = shared->theId;
+ Must(0 <= purpose && purpose < PageId::maxPurpose);
+ if (pageIndex->pop(page)) {
+ page.purpose = purpose;
+ ++theLevels[purpose];
return true;
}
return false;
void
Ipc::Mem::PagePool::put(PageId &page)
{
- Must(pageIdIsValid(page));
- pageIndex.push(page.number);
- page = PageId();
-}
+ if (!page)
+ return;
-void *
-Ipc::Mem::PagePool::pagePointer(const PageId &page)
-{
- Must(pageIdIsValid(page));
- return shared->theBuf + shared->thePageSize * (page.number - 1);
+ Must(0 <= page.purpose && page.purpose < PageId::maxPurpose);
+ --theLevels[page.purpose];
+ page.purpose = PageId::maxPurpose;
+ return pageIndex->push(page);
}
-bool
-Ipc::Mem::PagePool::pageIdIsValid(const PageId &page) const
-{
- return page.pool == shared->theId &&
- 0 < page.number && page.number <= shared->theCapacity;
-}
-
-
-// Ipc::Mem::PagePool::Shared
-
-static unsigned int LastPagePoolId = 0;
-
-Ipc::Mem::PagePool::Shared::Shared(const unsigned int aCapacity, size_t aPageSize):
- theId(++LastPagePoolId), theCapacity(aCapacity), thePageSize(aPageSize)
+char *
+Ipc::Mem::PagePool::pagePointer(const PageId &page)
{
- if (LastPagePoolId + 1 == 0)
- ++LastPagePoolId; // skip zero pool id
+ Must(pageIndex->pageIdIsValid(page));
+ return theBuf + pageSize() * (page.number - 1);
}
-off_t
-Ipc::Mem::PagePool::Shared::MemSize(const unsigned int capacity, const size_t pageSize)
-{
- return static_cast<off_t>(sizeof(Shared)) +
- static_cast<off_t>(pageSize) * capacity;
-}