Nano Hash - криптовалюты, майнинг, программирование

Вызов nvcc.exe с помощью CreateProcess

В настоящее время мы используем фиктивный JIT-компилятор для CUDA, где nvcc.exe вызывается для некоторых файлов и генерируются результирующие файлы .ptx.

bool executeWindowsProcess(ofstream &logFF) {

    STARTUPINFO si;
    PROCESS_INFORMATION pi;
    ZeroMemory( &si, sizeof(si) );
    si.cb = sizeof(si);
    ZeroMemory( &pi, sizeof(pi) );

    char cmd[] = "\"C:\\Program Files\\NVIDIA GPU Computing Toolkit\\CUDA\\v5.0\\bin\\nvcc.exe\"";
    char args[] = "\"C:\\Program Files\\NVIDIA GPU Computing Toolkit\\CUDA\\v5.0\\bin\\nvcc.exe\" --ptx --machine 32 -arch=sm_30 -o C:\\Users\\Yutong\\GOODKERNELCOMPILED.ptx --use_fast_math C:\\Users\\Yutong\\tempkernel.cu";

    logFF << cmd << endl;
    logFF << args << endl;

    CreateProcess(cmd, args, NULL, NULL, false, CREATE_DEFAULT_ERROR_MODE, NULL, NULL, &si, &pi); 

    logFF << GetLastError() << endl;

    WaitForSingleObject(pi.hProcess, INFINITE);

    logFF << GetLastError() << endl;

    CloseHandle( pi.hProcess );
    CloseHandle( pi.hThread );

    return true;
}

Первый GetLastError() возвращает 123, что, по-видимому, указывает на то, что nvcc.exe вообще не вызывается. Настройка cmd[] на что-то вроде notepad.exe (который находится в C:/Windows/System32/notepad.exe) работает нормально. Я спросил некоторых людей, и кажется, что:

  1. Мое приложение развернуто для 32-разрядной версии Windows
  2. nvcc.exe находится в C:/Program Files/..../, который является 64-битным каталогом, и CreateProcess, похоже, не может вызывать исполняемые файлы в каталогах, для которых у него нет разрешения.

PS, раньше мы использовали system() для вызова JIT-компилятора, но system() запускает внешнее окно терминала (мы пишем графический интерфейс) и, как правило, не рекомендуется.


  • Вы хотели задать вопрос здесь? 18.03.2013

Ответы:


1

GetLastError() имеет значение только тогда, когда возникает реальная ошибка. Вы не проверяете возвращаемое значение CreateProcess(), чтобы убедиться, что ошибка действительно произошла, прежде чем вызывать GetLastError() для ее извлечения. Вам нужно сделать это, например:

bool executeWindowsProcess(ofstream &logFF)
{
    STARTUPINFO si;
    PROCESS_INFORMATION pi;
    ZeroMemory( &si, sizeof(si) );
    si.cb = sizeof(si);
    ZeroMemory( &pi, sizeof(pi) );

    char cmd[] = "\"C:\\Program Files\\NVIDIA GPU Computing Toolkit\\CUDA\\v5.0\\bin\\nvcc.exe\"";
    char args[] = "\"C:\\Program Files\\NVIDIA GPU Computing Toolkit\\CUDA\\v5.0\\bin\\nvcc.exe\" --ptx --machine 32 -arch=sm_30 -o C:\\Users\\Yutong\\GOODKERNELCOMPILED.ptx --use_fast_math C:\\Users\\Yutong\\tempkernel.cu";

    logFF << cmd << endl;
    logFF << args << endl;

    if (!CreateProcess(cmd, args, NULL, NULL, FALSE, CREATE_DEFAULT_ERROR_MODE, NULL, NULL, &si, &pi))
    {
        logFF << GetLastError() << endl;
        return false;
    }

    logFF << "Running" << endl;

    WaitForSingleObject(pi.hProcess, INFINITE);

    logFF << "Terminated" << endl;

    CloseHandle( pi.hThread );
    CloseHandle( pi.hProcess );

    return true;
}

При этом ошибка 123 — это ERROR_INVALID_NAME ("Неверный синтаксис имени файла, имени каталога или метки тома"). Поскольку вы пытаетесь вызвать командную строку, я предлагаю вам установить для параметра lpApplicationName CreateProcess() значение NULL и просто использовать параметр lpCommandLine сам по себе, например:

bool executeWindowsProcess(ofstream &logFF)
{
    STARTUPINFO si;
    PROCESS_INFORMATION pi;
    ZeroMemory( &si, sizeof(si) );
    si.cb = sizeof(si);
    ZeroMemory( &pi, sizeof(pi) );

    char args[] = "\"C:\\Program Files\\NVIDIA GPU Computing Toolkit\\CUDA\\v5.0\\bin\\nvcc.exe\" --ptx --machine 32 -arch=sm_30 -o C:\\Users\\Yutong\\GOODKERNELCOMPILED.ptx --use_fast_math C:\\Users\\Yutong\\tempkernel.cu";

    logFF << args << endl;

    if (!CreateProcessA(NULL, args, NULL, NULL, FALSE, CREATE_DEFAULT_ERROR_MODE, NULL, NULL, &si, &pi))
    {
        logFF << GetLastError() << endl;
        return false;
    }

    logFF << "Running" << endl;

    WaitForSingleObject(pi.hProcess, INFINITE);

    logFF << "Terminated" << endl;

    CloseHandle( pi.hThread );
    CloseHandle( pi.hProcess );

    return true;
}
18.03.2013
  • Привет, это отличный ответ! Кажется, действительно перенос всего в командную строку работает. Часть нашего рабочего процесса также передает все в файл журнала через 2›, что нарушает работу — не знаю, как с этим справиться. \C:\\Program Files\\NVIDIA GPU Computing Toolkit\\CUDA\\v5.0\\bin\\nvcc.exe\ --ptx --machine 32 -arch=sm_30 -o C:\\Users\\ Yutong\\GOODKERNELCOMPILED.ptx --use_fast_math C:\\Users\\Yutong\\tempkernel.cu 2› log.txt 18.03.2013
  • Вы не можете использовать конвейер командной строки с CreateProcess() таким образом. Вам нужно будет либо 1) создать свой собственный дескриптор STDOUT через CreatePipe() и передать его CreateProcess(), затем вручную прочитать вывод nvcc и записать его в файл самостоятельно, либо 2) не иметь CreateProcess() прямого вызова nvcc.exe, пусть он вызывает cmd .exe, передав ему параметр /C, чтобы указать полную командную строку для его выполнения, включая конвейер. Используйте переменную среды %COMSPEC%, чтобы найти полный путь к cmd.exe. 18.03.2013
  • к сожалению, опция CMD / C не работает, я не думаю, что символ «›» даже разрешен. Я ищу, как сделать трубы прямо сейчас (но это выглядит довольно уродливо). 18.03.2013
  • @proteneer: да, вы можете использовать символ > с cmd.exe. Я только что проверил его, он работал нормально. Я смог перенаправить вывод в файл .txt, используя "<full path to>\cmd.exe" /C <command line> > log.txt. На самом деле именно потому, что он проходит через cmd.exe, перенаправление командной строки вообще можно использовать, потому что > является частью командного процессора. 19.03.2013
  • Благодарность! У меня все заработало =) Я был ленив и просто передал %COMPSPEC% вместо полного уточнения (расширения) пути к cmd 19.03.2013
  • @proteneer: да, сначала нужно расширить %COMSPEC%. 19.03.2013
  • Я компилировал навсегда с набором lpApplicationName, и все работало нормально. Он перестал работать с VS19. Установите его на NULL и все хорошо! Спасибо. 09.07.2021
  • Новые материалы

    Кластеризация: более глубокий взгляд
    Кластеризация — это метод обучения без учителя, в котором мы пытаемся найти группы в наборе данных на основе некоторых известных или неизвестных свойств, которые могут существовать. Независимо от..

    Как написать эффективное резюме
    Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

    Частный метод Python: улучшение инкапсуляции и безопасности
    Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

    Как я автоматизирую тестирование с помощью Jest
    Шутка для победы, когда дело касается автоматизации тестирования Одной очень важной частью разработки программного обеспечения является автоматизация тестирования, поскольку она создает..

    Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
    Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

    Понимание расстояния Вассерштейна: мощная метрика в машинном обучении
    В обширной области машинного обучения часто возникает необходимость сравнивать и измерять различия между распределениями вероятностей. Традиционные метрики расстояния, такие как евклидово..

    Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
    В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..