Порт llama.cpp в Паскаль АБС

llama.cpp - это движок, позволяющий общаться на компьютере с большими языковыми моделями в формате gguf. Программист Альфредо Ортега портировал этот движок в объектный паскаль, поддерживаемый средой разработки Lazarus: ortegaalfredo/fpc-llama: Freepascal bindings for Llama.cpp (github.com) Было бы здорово, если бы нашёлся альтруист, который бы портировал движок из объектного паскаля в Паскаль АБС. Самому мне это, увы, не под силу. Собственно кода немного: 252 строки (без учёта пустых строк: fpc-llama/llama.pas at main · ortegaalfredo/fpc-llama (github.com)), которые в основном являются описаниями вызова функций движка из llama.dll.

Тут маркдаун более чистый чем на гитхабе, поэтому тупо скопировать то что вы туда засунули нельзя - соседние строки сливает в одну.
Чтобы не сливало - ставьте \ или два пробела в конце строки.

Ну и думайте когда лучше поставить 2 переноса строки, чтобы начать новый абзац, чтобы читабельнее текст был.


Если я правильно понял масштаб - могу и я сделать, но что то мне подсказывает что та обёртка для лазариуса это огрызок от оригинального функционала. В первой паскальной обёртке (в README) вообще почему-то написано что это для CPU, хотя по-нормальному ИИ на GPU выполняют. И вроде оригинальная Llama.cpp GPU поддерживает.

Я ещё посмотрю как будет больше времени, тема ИИ мне в целом интересна.
Но пока что - можете подсказать, откуда брать инфу о точках входа в .dll-ке?
То есть я понимаю есть .h, но ещё должна быть документация, а для генерации обёрток - какой-нибуть машино-читаемый файл вроде этого: OpenCL-Docs/xml/cl.xml at main · KhronosGroup/OpenCL-Docs · GitHub
Быстрым поиском почему-то такого не нашёл…

Спасибо за ответ. Не у всех есть большая, полноценная гпу.

У меня, например, встроенная графическая карта, поэтому локальные нейросети запускаю на процессоре.

У движка Ортеги есть расширенная версия, которая поддерживает ГПУ.

Расширенная версия встроена в программу Нейрочат, вот её инсталлятор:

https://github.com/ortegaalfredo/neurochat/releases/download/0.6-dev/neurochat-0.6-setup-win64.exe

Когда установите программу, в её папке можно найти ту самую llama.dll.

Я не хакер, но точки входа вызова функций в llama.dll вроде бы можно определить с помощью программ вроде Dll Export Viewer от nirsoft.

Собственно говоря, я скачал эту программу, загрузил туда llama.dll, и все адреса вызова функций успешно отобразились.

И ещё два возможных варианта нахождения точек входа:

  1. посмотреть исходники оригинальной ggerganov/llama.cpp, а именно файлы llama.h и llama.cpp

  2. посмотреть код Нейрочата:

ortegaalfredo/neurochat: Native gui to serveral AI services plus llama.cpp local AIs. (github.com)

Файлы main.pas, chat.pas и другие.

Нет, реверс-инженерией заниматься тут не серьёзно.
Я сказал про .h файлы, можно их парсить - это по крайней мере лучше чем пытаться из .dll такую инфу доставать.
Но должны быть официальные ресурсы для этого дела.

Ну, это не мешает вам запускать нейронки используя свою встройку через тот же OpenCL. Так они могут быть даже быстрее чем если напрямую на CPU их выполнять - обычно драйвер OpenCL очень умно работу распараллеливает, в частности используя векторные инструкции CPU (обрабатывающие сразу по 4, 8 и т.п. значений 1 операцией).

Самый официальный .h файл от создателя ламы с++:

ggerganov/llama.cpp/blob/master/llama.h

Если там нет точек входа ( я не искал, не разбираюсь в этом деле ), то можно обратиться к Ортеге, спросить у него, где он нашёл их.

Контактные данные Ортеги есть в программе Нейрочат, в меню Help → About.

Нашёл упрощённую llama.dll, написанную на Дельфи.

Репозиторий на гитхабе - tinyBigGAMES/Dllama.

Проще готовое использовать

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

там есть issue на эту тему. возможно советы из них как-то помогут

Видел, не помогло.

В оригинальном llama.cpp тоже есть issue об этом, хотя это немного не по адресу им.
Я кажись в одну из них свой случай тоже случайно написал…

Ну, стоило больше моделей попробовать, это да, но не с моим интернетом…

В библиотеку Dllama, про которую я написал в своем предыдущем посте, добавили функцию для новичков, которая позволяет даже самому начинающему программисту общаться с ИИ моделями, задействовав всего одну функцию.

Вот так она выглядит на BCX, современном диалекте Бейсика:

DECLARE FUNCTION LLM$ LIB “Dllama.dll” ALIAS “Dllama_Simple_Inference” (A AS STRING, B AS STRING, C AS STRING, D AS BOOLEAN, E AS UINT, X AS UCHAR, F AS STRING )

Первый параметр - путь к папке, где хранятся модели ИИ. По умолчанию это - C:\LLM\gguf.

Второй параметр - название файла в формате .json, в котором хранятся настройки ИИ для моделей разной архитектуры.

Третий параметр - аббревиатура, обозначающая ту модель, которая будет использована во время текущего сеанса общения с ИИ. Например, “phi3:4B:Q4”. Новейшая модель Microsoft Phi 3, с количеством нейронов равным 4В и в четвертой степени квантования.

Четвертый параметр определяет железо, которое будет использовано для работы ИИ. FALSE - будет использован процессор, TRUE - будет задействована видеокарта.

Пятый параметр определяет размерность минимального понятийно-ситуативного контекста, используемого моделью. По умолчанию равен 1024.

Шестой параметр задаёт аппаратный код клавиши на клавиатуре, который может быть использован для прерывания работы программы в случае её реализации в виде консольного приложения. Если это клавиша escape, то надо установить этот параметр равным числу 27.

Седьмой параметр определяет тот вопрос, на который мы хотим получить ответ от искусственного интеллекта.

Пример запуска функции из кода BCX:

answer$ = LLM("C:\LLM\gguf", “models.json”, “phi3:4B:Q4”, FALSE, 1024, 27, “Why the grass is green?”)

ИИ поместит свой ответ на вопрос “Почему трава зеленая?” в строковую переменную answer$, которую можно отобразить в окне консоли с помощью команды print: print answer$.

И никаких проблем с AccessViolationException.

Выделяйте код по принципам Markdown-а…

Скачал отсюда: Phi-3-mini-4k-instruct-q4.gguf · microsoft/Phi-3-mini-4k-instruct-gguf at main

ggml_opencl: selecting platform: 'NVIDIA CUDA'
ggml_opencl: selecting device: 'NVIDIA GeForce GTX 750 Ti'
llama_model_loader: loaded meta data with 24 key-value pairs and 195 tensors from models\Phi-3-mini-4k-instruct-q4.gguf (version GGUF V3 (latest))
llama_model_loader: Dumping metadata keys/values. Note: KV overrides do not apply in this output.
llama_model_loader: - kv   0:                       general.architecture str              = phi3
llama_model_loader: - kv   1:                               general.name str              = Phi3
llama_model_loader: - kv   2:                        phi3.context_length u32              = 4096
llama_model_loader: - kv   3:                      phi3.embedding_length u32              = 3072
llama_model_loader: - kv   4:                   phi3.feed_forward_length u32              = 8192
llama_model_loader: - kv   5:                           phi3.block_count u32              = 32
llama_model_loader: - kv   6:                  phi3.attention.head_count u32              = 32
llama_model_loader: - kv   7:               phi3.attention.head_count_kv u32              = 32

llama_model_loader: - kv   8:      phi3.attention.layer_norm_rms_epsilon f32              = 0.000010
llama_model_loader: - kv   9:                  phi3.rope.dimension_count u32              = 96
llama_model_loader: - kv  10:                          general.file_type u32              = 15
llama_model_loader: - kv  11:                       tokenizer.ggml.model str              = llama
llama_model_loader: - kv  12:                         tokenizer.ggml.pre str              = default
llama_model_loader: - kv  13:                      tokenizer.ggml.tokens arr[str,32064]   = ["<unk>", "<s>", "</s>", "<0x00>", "<...
llama_model_loader: - kv  14:                      tokenizer.ggml.scores arr[f32,32064]   = [0.000000, 0.000000, 0.000000, 0.0000...
llama_model_loader: - kv  15:                  tokenizer.ggml.token_type arr[i32,32064]   = [2, 3, 3, 6, 6, 6, 6, 6, 6, 6, 6, 6, ...
llama_model_loader: - kv  16:                tokenizer.ggml.bos_token_id u32              = 1
llama_model_loader: - kv  17:                tokenizer.ggml.eos_token_id u32              = 32000
llama_model_loader: - kv  18:            tokenizer.ggml.unknown_token_id u32              = 0
llama_model_loader: - kv  19:            tokenizer.ggml.padding_token_id u32              = 32000
llama_model_loader: - kv  20:               tokenizer.ggml.add_bos_token bool             = true
llama_model_loader: - kv  21:               tokenizer.ggml.add_eos_token bool             = false
llama_model_loader: - kv  22:                    tokenizer.chat_template str              = {{ bos_token }}{% for message in mess...
llama_model_loader: - kv  23:               general.quantization_version u32              = 2
llama_model_loader: - type  f32:   65 tensors
llama_model_loader: - type q4_K:   81 tensors
llama_model_loader: - type q5_K:   32 tensors
llama_model_loader: - type q6_K:   17 tensors
llama_model_load: error loading model: error loading model architecture: unknown model architecture: 'phi3'

Не знаю, почему у Вас не запустилась модель. Библиотека Dllama загружает Phi 3 без проблем. Сегодня опробовал её в ещё одном простом языке программирования - AutoIt. Написал простое оконное приложение, задал вопрос: Are cats bigger than dogs? Ответ: No, on average, dogs are bigger than cats. However, there are many dog breeds that are smaller than some cat breeds. For example, the Chihuahua is significantly smaller than many cat breeds. It’s important to note that size can vary widely within each species due to different breeds and individual genetics.

Код простейшего чата с ИИ на AutoIt: Dllama.au3

Вы бы лучше скинули ссылку на конкретную модель на HuggingFace - туда постят все оригинальные версии моделей. Можно и на другом сайте, но в модель легко подсунуть вирус, потому что она исполняет произвольный код, кроме собственно умножения матриц. В чистоту с гугл диска не поверю.

Ну и по хорошему мне надо больше времени в это вложить, больше вещей протестить. mistral хотелось бы заставить работать - эта модель умеет делать и менее тривиальные вещи чем ваш пример - на который и GPT2 ответил бы правильно.