Ускорьте Матричные операции в сгенерированном автономном коде при помощи вызовов BLAS

Чтобы улучшить скорость выполнения кода, сгенерированного для определенного низкоуровневого вектора и операций над матрицей (таких как умножение матриц) в автономном коде, укажите, что вы хотите, чтобы MATLAB® Coder™ сгенерировал вызовы BLAS. BLAS является библиотекой программного обеспечения для низкоуровневых векторных и матричных вычислений, которая имеет несколько высоко оптимизированных специфичных для машины реализаций. Генератор кода использует интерфейс CBLAS C для BLAS. Если вы указываете, что хотите сгенерировать вызовы BLAS, и входные массивы для матричных функций соответствуют определенным критериям, генератор кода производит вызовы BLAS. В противном случае генератор кода производит код для матричных функций.

Для вызовов BLAS в автономном коде MATLAB CODER пользуется библиотекой BLAS, которую вы задаете. Задайте библиотеку BLAS, которая оптимизирована для вашей среды выполнения.

Задайте библиотеку BLAS

Чтобы сгенерировать вызовы BLAS в автономном коде, у вас должен быть доступ к классу обратного вызова BLAS. Класс обратного вызова BLAS задает библиотеку BLAS, заголовочный файл CBLAS, определенные типы данных C, которые конкретный интерфейс CBLAS использует, и компилятор и опции компоновщика для процесса сборки. Выполнить одно из следующих действий:

  • В командной строке, набор свойство объекта настройки кода CustomBLASCallback к имени класса обратного вызова.

  • В приложении MATLAB CODER, обратном вызове библиотеки Custom BLAS набора к имени класса обратного вызова.

Запишите класс обратного вызова BLAS

Чтобы сгенерировать вызовы определенной библиотеки BLAS в сгенерированном коде, запишите класс обратного вызова BLAS. Совместно используйте класс обратного вызова с другими, которые хотят пользоваться этой библиотекой BLAS для вызовов BLAS в автономном коде.

Класс обратного вызова должен вывести из абстрактного класса coder.BLASCallback. Этим примером является реализация класса обратного вызова mklcallback для интегрирования с библиотекой Intel MKL BLAS по платформе Windows®.

classdef mklcallback < coder.BLASCallback
    methods (Static)
        function updateBuildInfo(buildInfo, ~)
            libPath = fullfile(pwd,'mkl','WIN','lib','intel64');
            libPriority = '';
            libPreCompiled = true;
            libLinkOnly = true;
            libs = {'mkl_intel_ilp64.lib' 'mkl_intel_thread.lib' 'mkl_core.lib'};
            buildInfo.addLinkObjects(libs, libPath, libPriority, libPreCompiled, libLinkOnly);
            buildInfo.addLinkObjects('libiomp5md.lib',fullfile(matlabroot,'bin','win64'), ...
                libPriority, libPreCompiled, libLinkOnly);
            buildInfo.addIncludePaths(fullfile(pwd,'mkl','WIN','include'));
            buildInfo.addDefines('-DMKL_ILP64');
        end
        function headerName = getHeaderFilename()
            headerName = 'mkl_cblas.h';
        end
        function intTypeName = getBLASIntTypeName()
            intTypeName = 'MKL_INT';
        end
    end
end

Необходимо обеспечить getHeaderFilename, getBLASIntTypeName и методы updateBuildInfo. Метод getHeaderFilename возвращает имя заголовочного файла CBLAS. Если вы пользуетесь различной библиотекой BLAS, заменяете mkl_cblas.h на имя вашего заголовочного файла CBLAS. Метод getBLASIntTypeName возвращает имя целочисленного типа данных, который использует ваш интерфейс CBLAS. Если вы пользуетесь различной библиотекой BLAS, заменяете MKL_INT на имя целочисленного типа данных, характерного для вашего интерфейса CBLAS. Метод updateBuildInfo предоставляет информацию, запрошенную для процесса сборки, чтобы соединиться с библиотекой BLAS. Используйте код, который похож на код в классе обратного вызова в качестве примера, чтобы задать местоположение заголовочного файла, имя полного пути библиотеки BLAS, и опции компоновщика и компилятор. Если вы пользуетесь библиотекой Intel MKL BLAS, используйте советника по вопросам строки ссылки, чтобы видеть, каким библиотекам и параметрам компилятора рекомендуют для вашего варианта использования.

Существует три других метода, которые уже реализованы в coder.BLASCallback. Этими методами является getBLASDoubleComplexTypeName, getBLASSingleComplexTypeName и useEnumNameRatherThanTypedef. По умолчанию ваш класс обратного вызова наследовал эти реализации от coder.BLASCallback. В определенных ситуациях необходимо заменить эти методы с собственными определениями, когда вы задаете свой класс обратного вызова.

Метод getBLASDoubleComplexTypeName возвращает тип, используемый для с двойной точностью комплексных переменных в сгенерированном коде. Если ваша библиотека BLAS берет тип кроме double* и void* для с двойной точностью аргументов комплексного массива, включайте этот метод в свое определение класса обратного вызова.

function doubleComplexTypeName = getBLASDoubleComplexTypeName()
doubleComplexTypeName = 'my_double_complex_type';
end

Замените my_double_complex_type на тип, который ваша библиотека BLAS берет для с двойной точностью аргументов комплексного массива.

Метод getBLASSingleComplexTypeName возвращает тип, используемый для комплексных переменных с одинарной точностью в сгенерированном коде. Если ваша библиотека BLAS берет тип кроме float* и void* для аргументов комплексного массива с одинарной точностью, включайте этот метод в свое определение класса обратного вызова.

function singleComplexTypeName = getBLASSingleComplexTypeName()
doubleComplexTypeName = 'my_single_complex_type';
end

Замените my_single_complex_type на тип, который ваша библиотека BLAS берет для аргументов комплексного массива с одинарной точностью.

Метод useEnumNameRatherThanTypedef возвращает false по умолчанию. Если типы для перечислений в вашей библиотеке BLAS включают ключевое слово enum, переопределяют этот метод, чтобы возвратить true в вашем определении класса обратного вызова.

function p = useEnumNameRatherThanTypedef()
p = true;
end

Выборка из сгенерированного исходного кода C, который включает ключевое слово enum:

enum CBLAS_SIDE t;
enum CBLAS_UPLO b_t;
double temp;
enum CBLAS_TRANSPOSE c_t;
enum CBLAS_DIAG d_t;

Сгенерируйте вызовы BLAS путем определения класса обратного вызова BLAS

Этот пример показывает, как сгенерировать код, который вызывает функции BLAS в определенной библиотеке BLAS. useMyBLAS класса обратного вызова BLAS задает библиотеку BLAS, которой вы хотите пользоваться в этом примере.

  1. Запишите функцию MATLAB, которая вызывает функцию для основной операции над матрицей. Например, запишите функциональный myMultiply, который умножает две матрицы A и B.

    function C = myMultiply(A,B) %#codegen
    C = A*B;
    end

  2. Задайте объект настройки кода для статической библиотеки, динамически подключаемой библиотеки или исполняемой программы. Например, задайте объект настройки для динамически подключаемой библиотеки на платформе Windows.

    cfg = coder.config('dll');
  3. Задайте класс обратного вызова BLAS useMyBLAS.

    cfg.CustomBLASCallback = 'useMyBLAS';

    Класс обратного вызова должен быть на пути MATLAB.

  4. Сгенерируйте код. Укажите, что входные параметры, из которых A и B являются массивами 1000 на 1000, удваиваются.

    codegen myMultiply -args {zeros(1000),zeros(1000)} -config cfg -report

    Если A и B являются достаточно большими, генератор кода производит BLAS, призывают к функции умножения матриц.

Найдите библиотеку BLAS в среде выполнения

Библиотека BLAS должна быть доступной в вашей среде выполнения. Если ваша библиотека BLAS совместно используется, используйте переменные окружения или опции компоновщика, чтобы задать местоположение библиотеки BLAS.

  • На платформе Windows измените переменную окружения PATH.

  • На платформе Linux® измените переменную окружения LD_LIBRARY_PATH или используйте опцию компоновщика rpath.

  • На macOS платформе измените переменную окружения DYLD_LIBRARY_PATH или используйте опцию компоновщика rpath.

Чтобы задать опцию компоновщика rpath, используйте информацию о сборке метод addLinkFlags в методе updateBuildInfo вашего класса обратного вызова BLAS. Например, для компилятора GCC:

buildInfo.addLinkFlags(sprintf('-Wl,-rpath,"%s"',libPath));

Указания и ограничения по применению для библиотеки OpenBLAS

Если вы генерируете код, который включает вызовы библиотечных функций OpenBLAS, следуйте этим инструкциям и ограничениям:

  • Если вы генерируете Код С++, который включает вызовы библиотечных функций OpenBLAS, компилирование его с опцией -pedantic производит предупреждения. Чтобы отключить параметр компилятора -pedantic, включайте эти строки в метод updateBuildInfo:

    if ctx.getTargetLang() == 'C++'
        buildInfo.addCompileFlags('-Wno-pedantic');
    end
  • OpenBLAS не поддерживает стандарт C89/C90.

Смотрите также

Похожие темы

Внешние веб-сайты

Была ли эта тема полезной?