Перемещение объекта STL между процессами - PullRequest
4 голосов
/ 12 февраля 2012

Я знаю, что это странно, но мне просто весело.

Я пытаюсь передать std::map (создается с использованием размещения new в фиксированной области памяти) между двумя процессами через сокет между двумя машинами: Master и Slave. На карте, которую я использую, есть typedef:

   // A vector of Page objects
   typedef
      std::vector<Page*,
           PageTableAllocator<Page*> >
      PageVectorType;

   // A mapping of binary 'ip address' to a PageVector
   typedef
      std::map<uint32_t,
           PageVectorType*,
           std::less<uint32_t>,
           PageTableAllocator<std::pair<uint32_t, PageVectorType*> > >
      PageTableType;

Класс PageTableAllocator<T> отвечает за выделение любой памяти, которую STL-контейнеры могут пожелать / нужно, в фиксированное место в памяти. Например, все Page объекты и внутренние структуры STL создаются в этой фиксированной области памяти. Это гарантирует, что и объект std::map, и распределитель оба размещены в фиксированной области памяти. Я использовал GDB, чтобы убедиться, что карта и распределитель работают правильно (вся используемая память находится в фиксированной области, в обычную кучу приложения ничего не попадает).

Предполагая, что Master запускается, инициализирует все его структуры STL и специальную область памяти, происходит следующее. Slave запускается, распечатывает свою версию таблицы страниц, затем ищет Master. Slave находит мастер, удаляет его версию таблицы страниц, копирует версию таблицы страниц Master (и специальную область памяти), а успешно печатает его Master ' версия таблицы страниц. Из того, что я сделал в GDB, я могу выполнять много операций только для чтения.

При попытке добавить к недавно скопированному объекту PageTableType ошибка Slave в методе void construct (pointer p, const T& value) распределителя. Значение, переданное как p, указывает на уже выделенную область памяти (согласно версии std::map *1032*).

Я ничего не знаю о структуре объектов C ++, но я предполагаю, что состояние объекта из Slave версии PageTableType должно зависать даже после замены всей памяти, которую PageTableType и его распределитель используется. Мой вопрос, является ли это действительным беспокойством. Поддерживает ли C ++ какое-либо состояние объекта вне области памяти, в которой был создан экземпляр объекта din?

Все объекты, используемые на карте, не являются POD. То же самое верно для распределителя.

1 Ответ

3 голосов
/ 12 февраля 2012

Чтобы ответить на ваш конкретный вопрос:

Поддерживает ли C ++ какое-либо состояние объекта вне области памяти, в которой был создан объект?

Ответ нет . Нет никаких других структур данных, настроенных для «отслеживания» объектов или чего-либо подобного. C ++ использует явную модель выделения памяти, поэтому, если вы решите нести ответственность за выделение и освобождение, то у вас будет полный контроль.

Я подозреваю, что где-то что-то не так в вашем коде, но, поскольку вы считаете, что код корректен, вы придумываете другую причину, по которой ваш код может давать сбой, и вместо этого следует по этому пути. Я хотел бы отступить и внимательно изучить все, как работает ваш код прямо сейчас, и посмотреть, сможете ли вы определить проблему. Хотя классы STL являются сложными (особенно std::map), они, в конечном счете, просто код, и в них нет скрытой магии.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...