Как я могу регулировать пропускную способность на уровне домена приложения в Windows (в пользовательском режиме)?

Я хотел бы сделать следующее:

  • Мое приложение работает на компьютере с Windows (назовите его приложением A).
  • Я могу изменить исходный код приложения A, чтобы ввести регулирование пропускной способности.
  • Я хотел бы иметь возможность повторно использовать мой код регулирования пропускной способности и перенести его в любые другие приложения, которые у меня есть (другими словами, я хотел бы попытаться регулировать пропускную способность на уровне домена приложения, чтобы не пришлось повторно учитывать фактор существующие приложения для регулирования пропускной способности).
  • Я хочу регулировать суммарную скорость загрузки и загрузки А отдельно. Например, если для загрузки A выделено максимум 5 Кбит / с, то все потоки загрузки A будут ограничены совокупной суммой 5 Кбит / с.

Мои требования:

  • Я не могу использовать драйвер режима ядра.
  • Мне нужно добавить регулирование на уровне домена приложения.

Я пытался исследовать это, особенно в отношении переполнения стека, но не смог найти ничего полезного для моего случая:

  • Я видел этот пример использования оболочки класса ThrottledStream вокруг объекта Stream, который будет вводить регулирование при использовании, но мне нужно, чтобы это было на уровне домена; Подобный подход проблематичен, потому что он потребует от меня рефакторинга большого количества существующего кода в других приложениях.
  • Я видел этот вопрос, чей ответ говорит об использовании Windows Filtering Platform API. К сожалению, у меня есть требование, что я абсолютно не могу использовать драйвер режима ядра для этого, и я понимаю, что WFP API требует его.

Кто-нибудь знает способ реализации моих конкретных требований регулирования пропускной способности для регулирования приложений на уровне домена приложения?

1 ответ

Я думаю, что нашел решение. С помощью API QOS вам нужно получить дескриптор к целевому интерфейсу, используя TcOpenInterface (вы можете выяснить, какой интерфейс вы хотите настроить, используя вызов TcEnumerateInterfaces). С вашим дескриптором интерфейса вам нужно вызвать TcAddFlow вместе с указателем на структуру TC_GEN_FLOW, которая позволяет вам указывать как SendingFlowspec (Структура FLOWSPEC) и ReceivingFlowspec (Структура FLOWSPEC), которая содержит PeakBandwidth член. Затем, чтобы ваш интерфейс использовал этот поток, который вы только что добавили в него, вам нужно добавить фильтр в ваш интерфейс, используя вызов TcAddFilter, поскольку MSDN говорит, что функция TcAddFilter связывает новый фильтр с существующим потоком, который позволяет пакетам соответствие фильтра, который будет направлен на связанный поток. Я думаю, что для того, чтобы сделать его специфичным для приложения, вызов TcRegisterClient может сделать то, что вам нужно будет в любом случае вызвать, чтобы получить дескриптор клиента для использования с TcEnumerateInterfaces и TcAddFlow по его внешнему виду (но это еще предстоит проверить). Я нашел этот полезный пример (не проверял).

Взято из MSDN, PeakBandwidth member - это верхний предел разрешения передачи на основе времени для данного потока в байтах в секунду. Элемент PeakBandwidth ограничивает потоки, которые могли накопить значительное количество кредитов передачи или маркеров из-за перегрузки ресурсов сети одноразовыми или циклическими пакетами данных, путем применения предельного уровня передачи данных в секунду. Некоторые промежуточные системы могут использовать эту информацию, что приводит к более эффективному распределению ресурсов.

Другие вопросы по тегам