Оглавление
- Сколько ядер CUDA вам действительно нужно?
- Tools
- Как запустить все ядра процессора?
- Terminology
- На что влияет количество ядер процессора?
- Понимаем работу GPU:
- Функции ядер
- Сторонние программы для просмотра характеристик компьютера
- Cross-compiling cuDNN Samples
- Coverage of the Runtime API
- Роль количества ядер, их влияние на производительность
- Техпроцесс
- Где найти Кристальные ядра
- Видеокарта и типы памяти
- Key features
Сколько ядер CUDA вам действительно нужно?
Чем больше у вас ядер CUDA, тем лучше будет ваш игровой опыт. Однако, если вы ищете доступную видеокарту
6 лучших бюджетных видеокарт для дешевых игр
6 лучших бюджетных видеокарт для дешевых игрБюджетные видеокарты очень способны в наши дни. Вот лучшие бюджетные видеокарты, которые позволят вам играть по дешевке.
Прочитайте больше
Возможно, вы не захотите получить одно с большим количеством ядер CUDA (они могут быть довольно дорогими).
Ядра CUDA не просто популярны среди геймеров. Они имеют несколько различных применений в областях, которые имеют дело с огромным количеством данных, таких как инжиниринг и майнинг биткойнов. Вам понадобится большое количество ядер CUDA в этих областях, но сколько вам нужно, чтобы просто играть в компьютерную игру?
Ответ на самом деле зависит от того, сколько денег в вашем кошельке и насколько хорошо вы хотите свою видеокарту. При этом видеокарта с большим количеством ядер CUDA не обязательно означает, что она лучше, чем карта с меньшим числом. Качество видеокарты действительно зависит от того, как другие ее функции взаимодействуют с ядрами CUDA.
Чтобы получить точное сравнение между двумя картами, вы должны взглянуть на тесты производительности
10 лучших бесплатных тестовых программ для Windows
10 лучших бесплатных тестовых программ для WindowsИспользуйте это фантастическое и бесплатное тестовое программное обеспечение для Windows, чтобы устранить неполадки в вашей системе и поддерживать ее в актуальном состоянии.
Прочитайте больше
,
Tools
- NVCC
-
This is a reference document for nvcc,
the CUDA compiler driver.
nvcc accepts a range of conventional compiler options,
such as for defining macros and include/library paths, and for steering
the compilation process. - CUDA-GDB
- The NVIDIA tool for debugging CUDA applications running on Linux and QNX, providing developers with a mechanism for debugging
CUDA applications running on actual hardware. CUDA-GDB is an extension to the x86-64 port of GDB, the GNU Project debugger. - CUDA-MEMCHECK
- CUDA-MEMCHECK is a suite of run time tools capable of precisely detecting
out of bounds and misaligned memory access errors, checking device
allocation leaks, reporting hardware errors and identifying shared memory data
access hazards. - Compute Sanitizer
- The user guide for Compute Sanitizer.
- Nsight Eclipse Plugins Installation Guide
- Nsight Eclipse Plugins Installation Guide
- Nsight Eclipse Plugins Edition
- Nsight Eclipse Plugins Edition getting started guide
- Nsight Systems
- The documentation for Nsight Systems.
- Nsight Compute
- The NVIDIA Nsight Compute is the next-generation interactive kernel profiler for CUDA applications. It provides detailed performance
metrics and API debugging via a user interface and command line tool. - Profiler
- This is the guide to the Profiler.
- CUDA Binary Utilities
- The application notes for cuobjdump, nvdisasm, and nvprune.
Как запустить все ядра процессора?
Итак, способов будет несколько. По этому показываю первый.
Заходим в пуск — выполнить или клавиши win+r
Пишем msconfig
Далее в открывшемся окне переходим в загрузки — дополнительные параметры.
Выбираем ваше максимальное число процессоров.
Так кстати можно узнать количество ядер процессора. Но это виртуальные ядра, а не физически. Физических может быть меньше.
Нажимаем ОК, перезагружаемся.
Далее способ 2.
- Заходим в диспетчер задач — ctrl+shift+esc.
- Или ctrl+alt+del и диспетчер задач.
- Или нажимаем правой кнопкой по панели управления и выбираем диспетчер задач.
Переходим во вкладку процессы. Находим игру и нажимаем правой кнопкой мыши по процессу. Да кстати, игра должна быть запущена. Свернуть её можно или Win+D или alt+tab.
Выбираем задать соответствие.
Выбираем все и нажимаем ок.
Чтобы посмотреть, работают все ядра или нет, то в диспетчере задач заходим во вкладку быстродействие.
Во всех вкладках будет идти диаграмма.
Если нет, то нажимаем опять задать соответствие, оставляем только ЦП 0, нажимаем ок. Закрываем диспетчер задач, открываем опять повторяем все, то же самое, выбираем все процессоры и нажимаем ок.
Ещё!
В ноутбуках, бывает настроено энергосбережение таким образом, что настройки не дают использовать все ядра.
- Win7 — Заходим в панель управления, идем в электропитание — Изменить параметры плана — изменить дополнительные параметры питания — управление питанием процессора — минимальное состояние процессора.
- Win8, 10 — Или: параметры — система — питание и спящий режим — дополнительные параметры питания — настройка схемы электропитания — изменить дополнительные параметры питания — управление питанием процессора — минимальное состояние процессора
Для полного использования, должно стоять 100%.
Terminology
-
Heterogeneous Computing
- Host The CPU and its memory (host memory)
- Device The GPU and its memory (device memory)
-
The compute capability of a device describes its architecture, e.g.
- Number of registers
- Sizes of memories
- Features & capabilities
-
Programming in Parallel
GPU computing is about massive parallelism. We will use ‘blocks’ and ‘threads’ to implement parallelism.
-
Blocks
…
-
Threads
- A block can be split into parallel threads. Unlike parallel blocks, threads have mechanisms to efficiently:
- Communicate
- Synchronize
-
What is a thread block?
- One thread block consists of set of threads. Those threads may be in 1D, 2D or 3D. When we consider a thread block, threadIdx and blockDim standard variables in CUDA can be considered very important.
-
threadIdx // = Used to access the index of a thread inside a thread block threadIdx.x // = Index of a thread inside a block in X direction threadIdx.y // = Index of a thread inside a block in Y direction threadIdx.z // = Index of a thread inside a block in Z direction
-
blockDim // = Number of threads in the block for a specific direction blockDim.x // = Number of threads in the block for X direction blockDim.y // = Number of threads in the block for Y direction blockDim.z // = Number of threads in the block for Z direction
-
What is a thread grid?
- Thread grid is a set of thread blocks. Blocks also can be in 1D, 2D or 3D (Imagine replacing threads by thread blocks in the previous clarification for thread blocks). When it comes to thread grid, following variables are important.
-
blockIdx = Used to access an index of a thread block inside a thread grid blockIdx.x = Index of a tread block in X direction blockIdx.y = Index of a tread block in Y direction blockIdx.z = Index of a tread block in Z direction
-
gridDim = Number of thread blocks in a specific direction. gridDim.x = Number of thread blocks in X direction gridDim.y = Number of thread blocks in Y direction gridDim.z = Number of thread blocks in Z direction
-
Launching parallel threads:
- Launch N blocks with M threads per block with
- Use to access block index within grid
- Use to access thread index within block
-
Allocate elements to threads:
int index = threadIdx.x + blockIdx.x * blockDim.x;
-
Use to declare a variable/array in shared memory
- Data is shared between threads in a block
- Not visible to threads in other blocks
-
Use as a barrier
Use to prevent data hazards
-
Sharing Data Between Threads
- Within a block, threads share data via shared memory.
- Extremely fast on-chip memory,
- Declare using , allocated per block.
- Data is not visible to threads in other blocks.
- Implementing With Shared Memory
На что влияет количество ядер процессора?
Многие путают понятие количества ядер и частоту процессора. Если это сравнивать с человеком, то мозг это процессор, нейроны — это ядра. Ядра работают не во всех играх и приложениях. Если в игре например выполняется 2 процесса, один вырисовывает лес, а другой город и в игре заложено многоядерность, то понадобиться всего 2 ядра, чтобы загрузить эту картинку. А если в игре заложено больше процессов, то задействуют все ядра.
И может быть наоборот, игра или приложение может быть написана так, одно действие может выполнять только одно ядро и в этой ситуации выиграет процессор, у которого выше частота и наиболее хорошо сложена архитектура (по этому обычно процессоры Интел чуть выигрывают Амд).
По этому грубо говоря, количество ядер процессора, влияет на производительность и быстродействие.
Понимаем работу GPU:
Задача.
- Получить данные для расчетов.
- Скопировать эти данные в GPU память.
- Произвести вычисление в GPU через функцию ядра.
- Скопировать вычисленные данные из GPU памяти в ОЗУ.
- Посмотреть результаты.
- Высвободить используемые ресурсы.
cudaMalloc
- devPtr – указатель, в который записывается адрес выделенной памяти,
- count – размер выделяемой памяти в байтах.
- cudaSuccess – при удачном выделении памяти
- cudaErrorMemoryAllocation – при ошибке выделения памяти
- dst – указатель, содержащий адрес места-назначения копирования,
- src – указатель, содержащий адрес источника копирования,
- count – размер копируемого ресурса в байтах,
- cudaMemcpyKind – перечисление, указывающее направление копирования (может быть cudaMemcpyHostToDevice, cudaMemcpyDeviceToHost, cudaMemcpyHostToHost, cudaMemcpyDeviceToDevice).
- cudaSuccess – при удачном копировании
- cudaErrorInvalidValue – неверные параметры аргумента (например, размер копирования отрицателен)
- cudaErrorInvalidDevicePointer – неверный указатель памяти в видеокарте
- cudaErrorInvalidMemcpyDirection – неверное направление (например, перепутан источник и место-назначение копирования)
cudaEventCreate
- *event – указатель для записи хендла event’а.
- cudaSuccess – в случае успеха
- cudaErrorInitializationError – ошибка инициализации
- cudaErrorPriorLaunchFailure – ошибка при предыдущем асинхронном запуске функции
- cudaErrorInvalidValue – неверное значение
- cudaErrorMemoryAllocation – ошибка выделения памяти
cudaEventRecord
- event – хендл хаписываемого event’а,
- stream – номер потока, в котором записываем (в нашем случае это основной нулевой по-ток).
- cudaSuccess – в случае успеха
- cudaErrorInvalidValue – неверное значение
- cudaErrorInitializationError – ошибка инициализации
- cudaErrorPriorLaunchFailure – ошибка при предыдущем асинхронном запуске функции
- cudaErrorInvalidResourceHandle – неверный хендл event’а
- event – хендл event’а, прохождение которого ожидается.
- cudaSuccess – в случае успеха
- cudaErrorInitializationError – ошибка инициализации
- cudaErrorPriorLaunchFailure – ошибка при предыдущем асинхронном запуске функции
- cudaErrorInvalidValue – неверное значение
- cudaErrorInvalidResourceHandle – неверный хендл event’а
Функции ядер
Центральное ядро процессора выполняет 2 основных типа задач:
- внутрисистемные;
- пользовательские.
В первую категорию стоит отнести задачи по организации вычислений, загрузке интернет-страниц и обработке прерываний.
Во вторую же попадают функции поддержки приложений путем использования программной среды. Собственно, прикладное программирование как раз и построено на том, чтобы нагрузить ЦП задачами, которые он будет выполнять. Цель разработчика – настроить приоритеты выполнения той или иной процедуры.
Современные ОС позволяют грамотно задействовать все ядра процессора, что дает максимальную продуктивность системы. Из этого стоит отметить банальный, но логичный факт: чем больше физических ядер на процессоре, тем быстрее и стабильней будет работать ваш ПК.
Сторонние программы для просмотра характеристик компьютера
В Сети существуют десятки специализированных утилит, позволяющих получить полные данные о процессоре. Они разделяются на платные и бесплатные, отличаются объемом предоставляемой информации. В список наиболее востребованных входят следующие.
CPU-Z
Как узнать имя пользователя компьютера с Windows 10
Свободно распространяемая программа, которая дает исчерпывающие сведения о ПК, включая данные о процессоре, памяти, материнской плате и отдельных ключевых компонентов. Все нужные сведения в утилите располагаются во вкладке «CPU». Там пользователь узнает:
- о названии производителя устройства;
- марке, типе сокета;
- частоте;
- количестве ядерных и поточных единиц.
К сведению! Приложение указывает данные о напряжении, кэше, множителе и внешней частоте.
Приложение CPU-Z
Speccy
Бесплатная программа от разработчиков утилиты для чистки компьютера от ненужной сохраненной информации CCleaner. Позволяет узнать о конфигурации, названии и кодовом имени процессора. Список сведений о ПК представлен:
- частотой шины;
- моделью, конструктивом;
- количеством ядер и потоков;
- температурой;
- множителями;
- процессорным кэшем;
- скоростью работы кулеров.
Обратите внимание! Утилита предоставляет дополнительные инструкции для пользователя. Просмотреть актуальные сведения можно в подразделе «Центральный процессор»
AIDA64
Относится к мощным программным продуктам, предоставляющим данные о конфигурации персонального компьютера. Кроме основного функционала, поддерживает дополнительные возможности, помогающие протестировать диск, монитор, графическую карту и оперативную память.
Для просмотра сведений о процессоре необходимо переместиться в левую часть меню и открыть блок «Системная плата — ЦП». Там будет указано о наименовании и псевдониме процессора, тактовой частоте, количестве ядер, данных кэша (информация не доступна в триал-версии) степпинге и проч.
Важно! Дополнительные данные расположены в подразделе «CPUID». Программа AIDA64
Программа AIDA64
HWiNFO
Утилита необходима для получения информации об аппаратном разделе ПК. Она не пользуется популярностью, как предыдущая программа, хотя обладает внушительным набором средств для анализа. Кроме основной информации, приложение укажет характеристику памяти, данные о материнской плате, сетевых адаптерах, видеокарте и иных не менее важных компонентах.
В основном окне пользователь может проверить численность ядер, спецификацию ЦП и другие интересующие вопросы. Список дополнительных данных представлен кодовым именем, сокетом, количеством логических или физических ядер, вольтажом и тактовой частотой.
Существует множество причин, по которым пользователям может понадобиться информация о ядрах центрального процессора. От их показателей зависит уровень общей производительности устройства. Определять данные можно как при помощи встроенных программ, так и через сторонние специализированные приложения.
Cross-compiling cuDNN Samples
This section describes how to cross-compile cuDNN
samples.
Follow the below steps to cross-compile cuDNN samples on NVIDIA DRIVE OS
Linux.
Procedure
- Download the Ubuntu package: cuda*ubuntu*_amd64.deb
- Download the cross compile package:
cuda*-cross-aarch64*_all.deb -
Execute the following commands:
sudo dpkg -i cuda*ubuntu*_amd64.deb
sudo apt-get update
sudo apt-get install cuda-toolkit-x-x -y
sudo apt-get install cuda-cross-aarch64* -y
Procedure
- Download cuDNN Ubuntu package for your preferred CUDA Toolkit version:
*libcudnn7-cross-aarch64_*.deb - Download the cross compile package:
libcudnn7-dev-cross-aarch64_*.deb -
Execute the following commands:
sudo dpkg -i *libcudnn7-cross-aarch64_*.deb
sudo dpkg -i libcudnn7-dev-cross-aarch64_*.deb
Procedure
-
Copy the cudnn_samples_v7 directory to your home
directory:$ cp -r /usr/src/cudnn_samples_v7 $HOME
-
For each sample, execute the following commands:
$ cd $HOME/cudnn_samples_v7/(each sample) $ make TARGET_ARCH=aarch64
Follow the below steps to cross-compile cuDNN samples on NVIDIA DRIVE OS for
QNX.
Procedure
- Download the Ubuntu package: cuda*ubuntu*_amd64.deb
- Download the Cross compile package:
cuda*-cross-aarch64*_all.deb -
Execute the following commands:
sudo dpkg -i cuda*ubuntu*_amd64.deb
sudo dpkg -i cuda*-cross-aarch64*_all.deb
sudo apt-get update
sudo apt-get install cuda-toolkit-x-x -y
sudo apt-get install cuda-cross-qnx -y
Procedure
- Download the cuDNN Ubuntu package for your preferred CUDA Toolkit version:
*libcudnn7-cross-aarch64_*.deb - Download the cross compile package:
libcudnn7-dev-cross-aarch64_*.deb -
Execute the following commands:
sudo dpkg -i *libcudnn7-cross-aarch64_*.deb
sudo dpkg -i libcudnn7-dev-cross-aarch64_*.deb
Procedure
To set the environment variables, issue the following commands:
export CUDA_PATH={PATH}/install/cuda/
export QNX_HOST={PATH}/host/linux/x86_64
export QNX_TARGET={PATH}/target/qnx7
Procedure
-
Copy the cudnn_samples_v7 directory to your home
directory:$ cp -r /usr/src/cudnn_samples_v7 $HOME
-
For each sample, execute the following commands:
Note: Before issuing the following commands, you’ll need to replace
7.x.x with your specific cuDNN version.$ cd $HOME/cudnn_samples_v7/(each sample) $ make TARGET_OS=QNX TARGET_ARCH=aarch64 HOST_COMPILER={SET FULL PATH to YOUR CROSS COMPILER} (for example: make TARGET_OS=QNX TARGET_ARCH=aarch64 HOST_COMPILER=$QNX_HOST/usr/bin/aarch64-unknown-nto-qnx7.x.x-g++)
Coverage of the Runtime API
Coverage level | Modules |
---|---|
full | Error Handling, Stream Management, Event Management, Version Management, Peer Device Memory Access, Occupancy, Unified Addressing |
almost full | Device Management (no chooseDevice, cudaSetValidDevices), Memory Management, Execution Control (no support for working with parameter buffers) |
partial | 2D & 3D Arrays, Texture Object Management, Texture Reference Management |
(deprecated) | Thread management |
no coverage | Graph Management, OpenGL Interoperability, Direct3D Interoperability, VDPAU Interoperability, EGL Interoperability, Graphics Interoperability, Surface Reference Management, Surface Object Management |
The Milestones indicates some features which aren’t covered and are slated for future work.
Since I am not currently working on anything graphics-related, there are no short-term plans to extend coverage to any of the graphics related modules.
Роль количества ядер, их влияние на производительность
Первоначально ЦП имели только одно ядро. Однако на рубеже XX и XXI веков инженеры пришли к выводу, что стоит увеличить их количество. Это должно было позволить получить более высокую вычислительную мощность, а также позволить обрабатывать несколько задач одновременно.
Но для начала стоит разобраться с главным мифом. Принято считать, что чем больше ядер у процессора, тем больше мощности он будет предлагать. Но на практике все не так просто. Реальное влияние на производительность оказывают и другие факторы – например, тактовая частота, объем кэша, архитектура, количество потоков.
Дополнительные ядра означают, что процессор способен одновременно справляться с большим количеством задач. Однако здесь нельзя забывать об одном: несмотря на популяризацию четырех-, шести- или восьмиядерных процессоров, приложения используют один или два потока
Поэтому количество потоков ядра также важно учитывать
Например, если первый ЦП имеет 2 ядра 4 потока, а второй 4 ядра 4 потока, то разница в производительности будет небольшая. Однако если сравнить первый чип с 4-ядерным 8-поточным, то в данном случае производительность возрастет на 50 %.
Техпроцесс
Техпроцесс — это размер, используемый при производстве процессоров. Он определяет величину транзистора, единицей измерения которого является нм (нанометр). Транзисторы, в свою очередь, составляют внутреннюю основу ЦП. Суть заключается в том, что постоянное совершенствование методики изготовления позволяет уменьшать размер этих компонентов. В результате на кристалле процессора их размещается гораздо больше. Это способствует улучшению характеристик CPU, поэтому в его параметрах всегда указывают используемый техпроцесс. Например, Intel Core i5-760 выполнен по техпроцессу 45 нм, а Intel Core i5-2500K по 32 нм, исходя из этой информации, можно судить о том, насколько процессор современен и превосходит по производительности своего предшественника, но при выборе необходимо учитывать и ряд других параметров.
Где найти Кристальные ядра
Кристальные ядра можно найти по всему Тейвату, но лучшие места для фарма находятся в регионе Ли Юэ, в нескольких конкретных областях: Каменный лес Гуюнь, у подножья Горы Аоцзан, западная часть Долины Бишуй, Гора Тяньхэн. Карту каждого региона, а также рекомендованный маршрут для фарма кристальных ядер вы можете найти ниже.
Каменный лес Гуюнь
Проще всего найти кристальные ядра в Каменном лесу Гуюнь. Телепортируйтесь к подземелью Владения Гуюнь, и вы увидите около шести кристальных бабочек поблизости. Собрать всех сразу будет сложно, так как они очень пугливы и улетают при первой опасности. Пробегитесь, соберите несколько, потом пройдитесь в сторону, слева от вас будет арка, за ней есть ещё 2 кристальные бабочки на тропинке, после вернитесь в первоначальную локацию, не собранные вами бабочки вернутся на место.
Всего в этой локации находится 10 кристальных бабочек, но не теряйте времени в попытках собрать все до одной, проще переместиться в другую локацию.
Кликните для увеличения
Гора Аоцзан и Долина Бишуй
Еще одно отличное место для фарма Кристальных ядер — подножие Горы Аоцзан. Начните с подземелья «Чистая вода и горная пещера» и двигайтесь к полуострову. Здесь вы можете найти до 9 кристальных бабочек и кристальных ядер. Как только вы закончите у горы, телепортируйтесь к точке указанной на карте, это долина Бишуй. В этой области есть ещё 4 кристальных ядра.
Кликните для увеличения
Гора Тяньхэн
Затем вы можете отправиться к западу от гавани Ли Юэ к горе Тяньхэн. Телепортируйтесь на гору и планируйте вниз к северо-западу от неё. Вы можете найти там от 5 до 6 кристальных бабочек. Затем телепортируйтесь в точку указанную на карте, это Предместье Лиша. У входа в пещеру с водопадом есть еще 4-5 кристальных ядер.
Кликните для увеличения
Видеокарта и типы памяти
- Регистровая память (register) является самой быстрой из всех видов. Определить количество регистров доступных GPU можно с помощью уже хорошо известной функции cudaGetDeviceProperties. Рассчитать количество регистров, доступных одной нити GPU, так же не составляет труда, для этого необходимо разделить общее число регистров на произведение количества нитей в блоке и количества блоков в гриде. Все регистры GPU 32 разрядные. В CUDA нет явных способов использования регистровой памяти, всю работу по размещению данных в регистрах берет на себя компилятор.
- Локальная память (local memory) может быть использована компилятором при большом количестве локальных переменных в какой-либо функции. По скоростным характеристикам локальная память значительно медленнее, чем регистровая. В документации от nVidia рекомендуется использовать локальную память только в самых необходимых случаях. Явных средств, позволяющих блокировать использование локальной памяти, не предусмотрено, поэтому при падении производительности стоит тщательно проанализировать код и исключить лишние локальные переменные.
- Глобальная память (global memory) – самый медленный тип памяти, из доступных GPU. Глобальные переменные можно выделить с помощью спецификатора __global__, а так же динамически, с помощью функций из семейства cudMallocXXX. Глобальная память в основном служит для хранения больших объемов данных, поступивших на device с host’а, данное перемещение осуществляется с использованием функций cudaMemcpyXXX. В алгоритмах, требующих высокой производительности, количество операций с глобальной памятью необходимо свести к минимуму.
- Разделяемая память (shared memory) относиться к быстрому типу памяти. Разделяемую память рекомендуется использовать для минимизации обращение к глобальной памяти, а так же для хранения локальных переменных функций. Адресация разделяемой памяти между нитями потока одинакова в пределах одного блока, что может быть использовано для обмена данными между потоками в пределах одного блока. Для размещения данных в разделяемой памяти используется спецификатор __shared__.
- Константная память (constant memory) является достаточно быстрой из доступных GPU. Отличительной особенностью константной памяти является возможность записи данных с хоста, но при этом в пределах GPU возможно лишь чтение из этой памяти, что и обуславливает её название. Для размещения данных в константной памяти предусмотрен спецификатор __constant__. Если необходимо использовать массив в константной памяти, то его размер необходимо указать заранее, так как динамическое выделение в отличие от глобальной памяти в константной не поддерживается. Для записи с хоста в константную память используется функция cudaMemcpyToSymbol, и для копирования с device’а на хост cudaMemcpyFromSymbol, как видно этот подход несколько отличается от подхода при работе с глобальной памятью.
- Текстурная память (texture memory), как и следует из названия, предназначена главным образом для работы с текстурами. Текстурная память имеет специфические особенности в адресации, чтении и записи данных. Более подробно о текстурной памяти я расскажу при рассмотрении вопросов обработки изображений на GPU.
Key features
- All functions and methods throw exceptions on failure — no need to check return values (the exceptions carry the status information).
- Judicious namespacing (and some internal namespace-like classes) for better clarity and for semantically grouping related functionality together.
- You can mostly forget about numeric IDs and handles; the proxy classes will fit everywhere.
- Aims for clarity and straightforwardness in naming and semantics, so that you don’t need to look concepts up in the official documentation to understand what each class and function do.
- Thin and lightweight:
- No work done behind your back, no caches or indices or any such thing.
- No costly inheritance structure, vtables, virtual methods and so on — vanishes almost entirely on compilation.
- Doesn’t really «hide» any of CUDA’s complexity or functionality; it only simplifies use of the Runtime API.