Как легко передать очень длинную строку рабочему процессу в соответствии с Windows?

Мой собственный C++ программа Win32 порождает рабочий процесс и потребности передать огромную строку конфигурации ему. В настоящее время это просто передает строку как командную строку к CreateProcess(). Проблемой является строка, становится длиннее, и теперь она не вписывается в 32K ограничение символов, наложенное Windows.

Конечно, я мог сделать что-то как усложнение рабочего процесса, запускаются - я использую сервер RPC в нем так или иначе, и я мог представить запрос RPC на передачу строки конфигурации, но это потребует большого количества изменений и сделает решение не настолько надежным. Сохранение данных в файл для передачи также не очень изящно - файл можно было оставить в файловой системе и становиться мусором.

Что другие простые пути там для передачи длинных строк к рабочему процессу, запущенному моей программой в Windows?

5
задан sharptooth 5 April 2010 в 07:14
поделиться

7 ответов

Одна из возможных стратегий - создать канал с именем и передать дескриптор (или имя канала) другому процессу. Затем используйте обычные операции чтения \ записи в Pipe для извлечения данных.

6
ответ дан 18 December 2019 в 09:06
поделиться

Вы можете использовать наследуемый хэндл к объекту секции. В родительском процессе создайте объект секции (CreateFileMapping) и укажите, что его handle должен быть унаследован дочерним процессом; затем передайте значение handle дочернему процессу в командной строке. Затем дочерний процесс может открыть объект секции (OpenFileMapping). Хотя я бы предпочел именованный объект секции, поскольку семантику его использования легче понять.

0
ответ дан 18 December 2019 в 09:06
поделиться

Есть ли возможность настроить именованный сегмент общей памяти?

http://msdn.microsoft.com/en-us/library/ aa366551 (VS.85) .aspx

0
ответ дан 18 December 2019 в 09:06
поделиться

Уже есть несколько хороших ответов, но самый простой способ - сохранить его в файл и передать имя файла в команде линия.

Помимо простоты, преимуществом этого подхода является то, что приложения будут очень слабо связаны (вы потенциально сможете использовать дочернее приложение автономно другими способами, вместо того, чтобы всегда запускать его из программа, которая знает, как передавать данные в него через специализированный интерфейс)

Если вы хотите быть уверены, что файл будет очищен после обработки, отметьте его для удаления при следующей перезагрузке. ТО, если кто-то забудет очистить его, ОС сделает это за вас при следующей перезагрузке.

6
ответ дан 18 December 2019 в 09:06
поделиться

Использовать общую память. Передайте рабочему процессу имя объекта общей памяти. Другое решение - использовать сообщение WM_COPYDATA .

1
ответ дан 18 December 2019 в 09:06
поделиться

Я бы предпочел очередь сообщений Boost. Это очень просто, но изощренно. Вот пример:


#include <boost/interprocess/ipc/message_queue.hpp>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/shared_ptr.hpp>

using namespace boost::interprocess;

// ------------------------------------------------------------------------------
// Your worker:
// ------------------------------------------------------------------------------

try {
        message_queue::remove("NAME_OF_YOUR_QUEUE");

        boost::shared_ptr<message_queue> mq(new message_queue(create_only, "NAME_OF_YOUR_QUEUE", 65535, 32));

        char message[1024];
        std::size_t size_received;
        unsigned int priority;

        if (mq->timed_receive(&message, sizeof(message), size_received, priority, boost::posix_time::ptime(boost::posix_time::second_clock::universal_time()) + boost::posix_time::seconds(1))) {
                std::string s(message); // s now contains the message.
        }
} catch (std::exception &) {
        // ...
}

// ------------------------------------------------------------------------------
// And the sender:
// ------------------------------------------------------------------------------

try {
        boost::shared_ptr<message_queue> mq(new message_queue(create_only, "NAME_OF_YOUR_QUEUE", 1024, 1024));
        std::stringstream message;

        message << "the very very very long message you wish to send over";

        while (!mq.try_send(message.str().c_str(), message.str().length(), 0))
                ::Sleep(33);
} catch (std::exception &) {
        // ...
}
4
ответ дан 18 December 2019 в 09:06
поделиться

Как насчет того, чтобы прочитать это из stdin :) Кажется, это работает для пользователей Unix.

Это намного проще, чем передавать имена / ручки каналов!

Вот некоторый официальный код от MSDN для создания дочерних процессов с каналами ввода-вывода.

1
ответ дан 18 December 2019 в 09:06
поделиться
Другие вопросы по тегам:

Похожие вопросы: