diff --git a/cbits/wrapper.c b/cbits/wrapper.c index 5b1bb98..55f6cdd 100644 --- a/cbits/wrapper.c +++ b/cbits/wrapper.c @@ -3,14 +3,25 @@ #include "wrapper.h" struct llama_model * wrapper_load_model_from_file -( const char * path_model, struct llama_context_params * params) { +( const char * path_model, struct llama_model_params * params) { return llama_load_model_from_file(path_model, *params); } +struct llama_context * wrapper_new_context_with_model( + struct llama_model * model, + struct llama_context_params * params + ) { + return llama_new_context_with_model(model, *params); +} + void wrapper_context_default_params(struct llama_context_params * default_params) { *default_params = llama_context_default_params(); } +void wrapper_model_default_params(struct llama_model_params * default_params) { + *default_params = llama_model_default_params(); +} + void wrapper_model_quantize_default_params(struct llama_model_quantize_params * default_params) { *default_params = llama_model_quantize_default_params(); } diff --git a/cbits/wrapper.h b/cbits/wrapper.h index b94ebfc..9482ecb 100644 --- a/cbits/wrapper.h +++ b/cbits/wrapper.h @@ -3,11 +3,19 @@ struct llama_model * wrapper_load_model_from_file( const char * path_model, - struct llama_context_params * params + struct llama_model_params * params ); + +struct llama_context * wrapper_new_context_with_model( + struct llama_model * model, + struct llama_context_params * params + ); + void wrapper_context_default_params(struct llama_context_params *); +void wrapper_model_default_params(struct llama_model_params *); + void wrapper_model_quantize_default_params(struct llama_model_quantize_params *); void wrapper_get_timings(struct llama_context * ctx, struct llama_timings * timings); diff --git a/examples/Main.hs b/examples/Main.hs index a498d62..aa7e4c5 100644 --- a/examples/Main.hs +++ b/examples/Main.hs @@ -1,14 +1,15 @@ module Main where import Prelude hiding (takeWhile) - import Control.Applicative ((<**>)) import Control.Exception (bracket) import Control.Monad.IO.Class (MonadIO, liftIO) import Control.Monad.Reader (MonadReader, ReaderT, runReaderT, asks) +import Data.Either (fromRight) import Data.Functor ((<&>), void) import qualified Data.Vector.Storable as V -import Foreign.C.String (peekCString, withCString) +import Foreign (allocaBytes) +import Foreign.C.String (peekCString, peekCStringLen, withCString, withCStringLen) import Foreign.C.Types (CFloat, CInt) import Foreign.ForeignPtr (newForeignPtr_) import Foreign.Marshal.Alloc (alloca, free, malloc) @@ -39,10 +40,11 @@ import Options.Applicative ) import Pipes (Producer, (>->), for, lift, runEffect, yield) import Pipes.Prelude (takeWhile) +import System.IO (hFlush, stdout) data Params = Params { _nCtx :: Int - , _nThreads :: CInt + , _nThreads :: Int , _nPredict :: Int , _nGpuLayers :: Int , _enableNumaOpts :: Bool @@ -118,6 +120,24 @@ runContextM :: Context -> ContextM () -> IO () runContextM ctx (ContextM ctxM) = runReaderT ctxM ctx +tokenToString :: L.Model -> L.Token -> IO String +tokenToString m t = + let + -- Returns (Right tokenString) if successful, otherwise + -- (Left len), where len is correct token size to allocate + tokenBufToStr size = allocaBytes size $ \buf -> do + nTokens <- fromIntegral <$> L.tokenToPiece m t buf (fromIntegral size) + if nTokens >= 0 + then Right <$> peekCStringLen (buf, nTokens) + -- tokenToPiece will return the token size, negated, + -- iff the size we allocate is too small. + else pure $ Left (negate nTokens) + in do + r <- tokenBufToStr 8 + either (\nTokens -> do + r' <- tokenBufToStr nTokens + pure $ fromRight (error "token allocation failed") r' + ) (pure . id) r -- -- mimicking call here, somewhat: https://huggingface.co/TheBloke/open-llama-7B-v2-open-instruct-GGML#how-to-run-in-llamacpp @@ -147,24 +167,25 @@ main = do params' <- asks _params ctx <- asks _llamaCtx + model <- asks _model -- tokenizing & eval -- "do one empty run to warm up the model" liftIO . allocaArray 1 $ \(tmp :: Ptr L.Token) -> do - bos <- L.tokenBos + bos <- L.tokenBos model pokeArray tmp [bos] - _evalRes <- L.eval ctx tmp 1 0 (_nThreads $ params') + _evalRes <- L.eval ctx tmp 1 0 L.resetTimings ctx let -- todo why is this constant here maxTokens = 1024 - tokenize s tks addBos = - L.tokenize ctx s tks (fromIntegral maxTokens) (fromBool addBos) + tokenize s l tks addBos = + L.tokenize model s (fromIntegral l) tks (fromIntegral maxTokens) (fromBool addBos) (fromBool False) (tokenized, tokenizedCount) <- liftIO . allocaArray maxTokens $ \tokensPtr -> do - tokenizedCount' <- withCString (_prompt params') $ \ts -> tokenize ts tokensPtr True + tokenizedCount' <- withCStringLen (_prompt params') $ \(ts, l) -> tokenize ts l tokensPtr True putStrLn "\nPrompt" putStrLn $ _prompt params' <> "\n\n" @@ -172,7 +193,7 @@ main = do putStrLn $ "\nTokenized " <> show tokenizedCount' putStrLn "\nRunning first eval of entire prompt" - _evalRes <- L.eval ctx tokensPtr tokenizedCount' 0 (_nThreads params') + _evalRes <- L.eval ctx tokensPtr tokenizedCount' 0 (, tokenizedCount') <$> peekArray (fromIntegral tokenizedCount') tokensPtr @@ -190,29 +211,32 @@ main = do liftIO . putStrLn $ "\nsampling" - eos <- liftIO L.tokenEos + eos <- liftIO $ L.tokenEos model -- I feel like this is not the right way to do this? runEffect $ for (sample >-> takeWhile (/= eos)) $ \id' -> - lift . liftIO $ putStr =<< peekCString =<< L.tokenToStr ctx id' + lift . liftIO $ do + putStr =<< tokenToString model id' + hFlush stdout sample :: Producer L.Token ContextM () sample = do params' <- asks _params ctx <- asks _llamaCtx + model <- asks _model nPastTV <- asks _nPast nPast' <- liftIO . readTVarIO $ nPastTV lastNTokensTV <- asks _lastNTokens lastNTokens' <- liftIO . readTVarIO $ lastNTokensTV - nVocab <- fromIntegral <$> (liftIO . L.nVocab $ ctx) + nVocab <- fromIntegral <$> (liftIO . L.nVocab $ model) - id' <- liftIO $ sample' params' ctx nVocab lastNTokensTV + id' <- liftIO $ sample' model params' ctx nVocab lastNTokensTV void . liftIO . withArray [id'] $ \newTokenArrPtr -> - L.eval ctx newTokenArrPtr 1 (fromIntegral nPast') (_nThreads $ params') + L.eval ctx newTokenArrPtr 1 (fromIntegral nPast') liftIO . atomically $ do writeTVar nPastTV $ @@ -221,13 +245,11 @@ main = do else nPast' + 1 writeTVar lastNTokensTV $ drop 1 lastNTokens' <> [id'] - -- liftIO $ putStr =<< peekCString =<< L.tokenToStr ctx id' - yield id' *> sample - sample' :: Params -> L.Context -> Int -> TVar [L.Token] -> IO L.Token - sample' params' ctx nVocab lastNTokensTV = do + sample' :: L.Model -> Params -> L.Context -> Int -> TVar [L.Token] -> IO L.Token + sample' model params' ctx nVocab lastNTokensTV = do alloca $ \candidatesPPtr -> allocaArray nVocab $ \logitsCopyPtr -> do @@ -262,23 +284,15 @@ main = do lastNTokensLen = fromIntegral . length $ lastNTokens' -- float nl_logit = logits[llama_token_nl()]; - _nlLogit <- V.unsafeIndex logitsCopy . fromIntegral <$> L.tokenNl + _nlLogit <- V.unsafeIndex logitsCopy . fromIntegral <$> (L.tokenNl model) -- -- lastNTokensPtr should be a pointer just to the last -- set of tokens at the end of lastNTokens matching the -- count of lastNRepeat, right now it's the entire thing -- - L.sampleRepetitionPenalty - ctx candidatesPPtr lastNTokensPtr lastNTokensLen (_repeatPenalty params') - - L.sampleFrequencyAndPresencePenalties - ctx - candidatesPPtr - lastNTokensPtr - lastNTokensLen - (_alphaFrequency params') - (_alphaPresence params') + L.sampleRepetitionPenalties + ctx candidatesPPtr lastNTokensPtr lastNTokensLen (_repeatPenalty params') (1.0) (1.0) -- todo -- if (!penalize_nl) { @@ -315,22 +329,30 @@ main = do -- todo -- putStrLn "\ndefault model quantize params" + putStrLn "\ninit model & context params" + mpp <- malloc + L.modelDefaultParams mpp + modelParams' <- peek mpp + cpp <- malloc - putStrLn "\ninit context params" L.contextDefaultParams cpp ctxParams' <- peek cpp let + modelParams = modelParams' + { L._nGpuLayers = _nGpuLayers params' + } ctxParams = ctxParams' { L._nCtx = _nCtx params' - , L._nGpuLayers = _nGpuLayers params' + , L._nThreads = _nThreads params' } + poke mpp modelParams poke cpp ctxParams putStrLn "\nloading model" - model' <- withCString (_modelPath params') $ flip L.loadModelFromFile cpp + model' <- withCString (_modelPath params') $ flip L.loadModelFromFile mpp putStrLn "\nloading context" diff --git a/src/LLaMACPP.chs b/src/LLaMACPP.chs index d6d07f4..d440750 100644 --- a/src/LLaMACPP.chs +++ b/src/LLaMACPP.chs @@ -1,7 +1,8 @@ module LLaMACPP where -import Data.Word (Word32) +import Control.Exception (assert) +import Data.Word (Word8, Word32) import Foreign.C.Types (CChar, CDouble, CFloat, CInt, CLong, CSize, CUChar, CULong) import Foreign.Marshal.Utils (fromBool, toBool) import Foreign.Ptr (FunPtr, Ptr, castPtr) @@ -103,7 +104,6 @@ instance Storable TokenDataArray where {# set token_data_array->size #} p $ fromIntegral _size {# set token_data_array->sorted #} p _sorted - -- -- typedef void (*llama_progress_callback)(float progress, void *ctx); -- @@ -111,47 +111,107 @@ type ProgressCallback = CFloat -> Ptr () -> IO () {# pointer progress_callback as ProgressCallbackPtr -> ProgressCallback #} +-- struct llama_model_params { +-- int32_t n_gpu_layers; // number of layers to store in VRAM +-- int32_t main_gpu; // the GPU that is used for scratch and small tensors +-- const float * tensor_split; // how to split layers across multiple GPUs (size: LLAMA_MAX_DEVICES) +-- +-- // called with a progress value between 0 and 1, pass NULL to disable +-- llama_progress_callback progress_callback; +-- +-- // context pointer passed to the progress callback +-- void * progress_callback_user_data; +-- +-- // override key-value pairs of the model meta data +-- const struct llama_model_kv_override * kv_overrides; +-- +-- // Keep the booleans together to avoid misalignment during copy-by-value. +-- bool vocab_only; // only load the vocabulary, no weights +-- bool use_mmap; // use mmap if possible +-- bool use_mlock; // force system to keep model in RAM +-- }; +data ModelParams = ModelParams + { _nGpuLayers :: Int + , _mainGpu :: Word32 + , _tensorSplit :: Ptr CFloat + , _progressCallback :: FunPtr ProgressCallback + , _progressCallbackUserData :: Ptr () + , _kvOverrides :: Ptr () + , _vocabOnly :: Bool + , _useMmap :: Bool + , _useMlock :: Bool + } + deriving (Show, Eq) + +{# pointer *model_params as ModelParamsPtr -> ModelParams #} + +instance Storable ModelParams where + sizeOf _ = {# sizeof model_params #} + alignment _ = {# alignof model_params #} + peek p = ModelParams + <$> (fromIntegral <$> {# get model_params->n_gpu_layers #} p) + <*> (fromIntegral <$> {# get model_params->main_gpu #} p) + <*> ({# get model_params->tensor_split #} p) + <*> ({# get model_params->progress_callback #} p) + <*> ({# get model_params->progress_callback_user_data #} p) + <*> ({# get model_params->kv_overrides #} p) + <*> ({# get model_params->vocab_only #} p) + <*> ({# get model_params->use_mmap #} p) + <*> ({# get model_params->use_mlock #} p) + poke p mps = do + {# set model_params->n_gpu_layers #} p $ fromIntegral $ _nGpuLayers mps + {# set model_params->main_gpu #} p $ fromIntegral $ _mainGpu mps + -- --struct llama_context_params { --- uint32_t seed; // RNG seed, -1 for random --- int32_t n_ctx; // text context --- int32_t n_batch; // prompt processing batch size --- int32_t n_gpu_layers; // number of layers to store in VRAM --- int32_t main_gpu; // the GPU that is used for scratch and small tensors --- float tensor_split[LLAMA_MAX_DEVICES]; // how to split layers across multiple GPUs --- // called with a progress value between 0 and 1, pass NULL to disable --- llama_progress_callback progress_callback; --- // context pointer passed to the progress callback --- void * progress_callback_user_data; --- --- // Keep the booleans together to avoid misalignment during copy-by-value. --- bool low_vram; // if true, reduce VRAM usage at the cost of performance --- bool f16_kv; // use fp16 for KV cache --- bool logits_all; // the llama_eval() call computes all logits, not just the last one --- bool vocab_only; // only load the vocabulary, no weights --- bool use_mmap; // use mmap if possible --- bool use_mlock; // force system to keep model in RAM --- bool embedding; // embedding mode only --- }; +-- uint32_t seed; // RNG seed, -1 for random +-- uint32_t n_ctx; // text context, 0 = from model +-- uint32_t n_batch; // prompt processing maximum batch size +-- uint32_t n_threads; // number of threads to use for generation +-- uint32_t n_threads_batch; // number of threads to use for batch processing +-- int8_t rope_scaling_type; // RoPE scaling type, from `enum llama_rope_scaling_type` +-- +-- // ref: https://github.com/ggerganov/llama.cpp/pull/2054 +-- float rope_freq_base; // RoPE base frequency, 0 = from model +-- float rope_freq_scale; // RoPE frequency scaling factor, 0 = from model +-- float yarn_ext_factor; // YaRN extrapolation mix factor, negative = from model +-- float yarn_attn_factor; // YaRN magnitude scaling factor +-- float yarn_beta_fast; // YaRN low correction dim +-- float yarn_beta_slow; // YaRN high correction dim +-- uint32_t yarn_orig_ctx; // YaRN original context size +-- +-- enum ggml_type type_k; // data type for K cache +-- enum ggml_type type_v; // data type for V cache +-- +-- // Keep the booleans together to avoid misalignment during copy-by-value. +-- bool mul_mat_q; // if true, use experimental mul_mat_q kernels (DEPRECATED - always true) +-- bool logits_all; // the llama_eval() call computes all logits, not just the last one (DEPRECATED - set llama_batch.logits instead) +-- bool embedding; // embedding mode only +-- bool offload_kqv; // whether to offload the KQV ops (including the KV cache) to GPU +-- }; -- data ContextParams = ContextParams { _seed :: Word32 , _nCtx :: Int , _nBatch :: Int - , _nGpuLayers :: Int - , _mainGpu :: Int - , _tensorSplit :: Ptr CFloat - , _progressCallback :: FunPtr ProgressCallback - , _progressCallbackUserData :: Ptr () - , _lowVRAM :: Bool - , _f16KV :: Bool + , _nThreads :: Int + , _nThreadsBatch :: Word32 + , _ropeScalingType :: Word8 + , _ropeFreqBase :: CFloat + , _ropeFreqScale :: CFloat + , _yarnExtFactor :: CFloat + , _yarnAttnFactor :: CFloat + , _yarnBetaFast :: CFloat + , _yarnBetaSlow :: CFloat + , _yarnOrigCtx :: Word32 + , _typeK :: CInt + , _typeV :: CInt + , _mulMatQ :: Bool , _logitsAll :: Bool - , _vocabOnly :: Bool - , _useMmap :: Bool - , _useMlock :: Bool , _embedding :: Bool + , _offloadKqv :: Bool } - -- deriving (Eq, Show) -- needs ProgressCallback instance + deriving (Eq, Show) {# pointer *context_params as ContextParamsPtr -> ContextParams #} @@ -162,34 +222,66 @@ instance Storable ContextParams where <$> (fromIntegral <$> {# get context_params->seed #} p) <*> (fromIntegral <$> {# get context_params->n_ctx #} p) <*> (fromIntegral <$> {# get context_params->n_batch #} p) - <*> (fromIntegral <$> {# get context_params->n_gpu_layers #} p) - <*> (fromIntegral <$> {# get context_params->main_gpu #} p) - <*> {# get context_params->tensor_split #} p - <*> {# get context_params->progress_callback #} p - <*> {# get context_params->progress_callback_user_data #} p - <*> {# get context_params->low_vram #} p - <*> {# get context_params->f16_kv #} p - <*> {# get context_params->logits_all #} p - <*> {# get context_params->vocab_only #} p - <*> {# get context_params->use_mmap #} p - <*> {# get context_params->use_mlock #} p - <*> {# get context_params->embedding #} p + <*> (fromIntegral <$> {# get context_params->n_threads #} p) + <*> (fromIntegral <$> {# get context_params->n_threads_batch #} p) + <*> (fromIntegral <$> {# get context_params->rope_scaling_type #} p) + <*> {# get context_params->rope_freq_base #} p + <*> {# get context_params->rope_freq_scale #} p + <*> {# get context_params->yarn_ext_factor #} p + <*> {# get context_params->yarn_attn_factor #} p + <*> {# get context_params->yarn_beta_fast #} p + <*> {# get context_params->yarn_beta_slow #} p + <*> (fromIntegral <$> {# get context_params->yarn_orig_ctx #} p) + <*> {# get context_params->type_k #} p + <*> {# get context_params->type_k #} p + <*> {# get context_params->mul_mat_q #} p + <*> {# get context_params->logits_all #} p + <*> {# get context_params->embedding #} p + <*> {# get context_params->offload_kqv #} p + -- <*> (fromIntegral <$> {# get context_params->n_gpu_layers #} p) + -- <*> (fromIntegral <$> {# get context_params->main_gpu #} p) + -- <*> {# get context_params->tensor_split #} p + -- <*> {# get context_params->progress_callback #} p + -- <*> {# get context_params->progress_callback_user_data #} p + -- <*> {# get context_params->low_vram #} p + -- <*> {# get context_params->f16_kv #} p + -- <*> {# get context_params->logits_all #} p + -- <*> {# get context_params->vocab_only #} p + -- <*> {# get context_params->use_mmap #} p + -- <*> {# get context_params->use_mlock #} p + -- <*> {# get context_params->embedding #} p poke p cps = do {# set context_params->seed #} p $ fromIntegral $ _seed cps {# set context_params->n_ctx #} p $ fromIntegral $ _nCtx cps {# set context_params->n_batch #} p $ fromIntegral $ _nBatch cps - {# set context_params->n_gpu_layers #} p $ fromIntegral $ _nGpuLayers cps - {# set context_params->main_gpu #} p $ fromIntegral $ _mainGpu cps - {# set context_params->tensor_split #} p $ _tensorSplit cps - {# set context_params->progress_callback #} p $ _progressCallback cps - {# set context_params->progress_callback_user_data #} p $ _progressCallbackUserData cps - {# set context_params->low_vram #} p $ _lowVRAM cps - {# set context_params->f16_kv #} p $ _f16KV cps - {# set context_params->logits_all #} p $ _logitsAll cps - {# set context_params->vocab_only #} p $ _vocabOnly cps - {# set context_params->use_mmap #} p $ _useMmap cps - {# set context_params->use_mlock #} p $ _useMlock cps - {# set context_params->embedding #} p $ _embedding cps + {# set context_params-> n_threads #} p $ fromIntegral $ _nThreads cps + {# set context_params-> n_threads_batch #} p $ fromIntegral $ _nThreadsBatch cps + {# set context_params-> rope_scaling_type #} p $ fromIntegral $ _ropeScalingType cps + {# set context_params-> rope_freq_base #} p $ _ropeFreqBase cps + {# set context_params-> rope_freq_scale #} p $ _ropeFreqScale cps + {# set context_params-> yarn_ext_factor #} p $ _yarnExtFactor cps + {# set context_params-> yarn_attn_factor #} p $ _yarnAttnFactor cps + {# set context_params-> yarn_beta_fast #} p $ _yarnBetaFast cps + {# set context_params-> yarn_beta_slow #} p $ _yarnBetaSlow cps + {# set context_params-> yarn_orig_ctx #} p $ fromIntegral $ _yarnOrigCtx cps + {# set context_params-> type_k #} p $ _typeK cps + {# set context_params-> type_v #} p $ _typeV cps + {# set context_params-> mul_mat_q #} p $ _mulMatQ cps + {# set context_params-> logits_all #} p $ _logitsAll cps + {# set context_params-> embedding #} p $ _embedding cps + {# set context_params-> offload_kqv #} p $ _offloadKqv cps + -- {# set context_params->n_gpu_layers #} p $ fromIntegral $ _nGpuLayers cps + -- {# set context_params->main_gpu #} p $ fromIntegral $ _mainGpu cps + -- {# set context_params->tensor_split #} p $ _tensorSplit cps + -- {# set context_params->progress_callback #} p $ _progressCallback cps + -- {# set context_params->progress_callback_user_data #} p $ _progressCallbackUserData cps + -- {# set context_params->low_vram #} p $ _lowVRAM cps + -- {# set context_params->f16_kv #} p $ _f16KV cps + -- {# set context_params->logits_all #} p $ _logitsAll cps + -- {# set context_params->vocab_only #} p $ _vocabOnly cps + -- {# set context_params->use_mmap #} p $ _useMmap cps + -- {# set context_params->use_mlock #} p $ _useMlock cps + -- {# set context_params->embedding #} p $ _embedding cps -- @@ -266,6 +358,9 @@ maxDevices = {# call max_devices #} contextDefaultParams :: ContextParamsPtr -> IO () contextDefaultParams = {# call wrapper_context_default_params #} +modelDefaultParams :: ModelParamsPtr -> IO () +modelDefaultParams = {# call wrapper_model_default_params #} + -- -- LLAMA_API struct llama_model_quantize_params llama_model_quantize_default_params(); @@ -319,9 +414,9 @@ timeUs = {# call time_us #} -- -- Can't pass structs by value via FFI, so wrote a wrapper: -- -loadModelFromFile :: Ptr CChar -> ContextParamsPtr -> IO Model -loadModelFromFile modelPath ctxParamsPtr = - {# call wrapper_load_model_from_file #} modelPath (castPtr ctxParamsPtr) +loadModelFromFile :: Ptr CChar -> ModelParamsPtr -> IO Model +loadModelFromFile modelPath modelParamsPtr = + {# call wrapper_load_model_from_file #} modelPath (castPtr modelParamsPtr) -- @@ -339,7 +434,7 @@ freeModel = {# call free_model #} newContextWithModel :: Model -> ContextParamsPtr -> IO (Context) newContextWithModel model ctxParamsPtr = - {# call new_context_with_model #} model (castPtr ctxParamsPtr) + {# call wrapper_new_context_with_model #} model (castPtr ctxParamsPtr) -- @@ -369,7 +464,7 @@ modelQuantize = {# call model_quantize #} -- const char * path_base_model, -- int n_threads); -- -modelApplyLoraFromFile :: Model -> Ptr CChar -> Ptr CChar -> CInt -> IO CInt +modelApplyLoraFromFile :: Model -> Ptr CChar -> CFloat -> Ptr CChar -> CInt -> IO CInt modelApplyLoraFromFile = {# call model_apply_lora_from_file #} @@ -444,7 +539,7 @@ saveSessionFile = {# call save_session_file #} -- int n_past, -- int n_threads); -- -eval :: Context -> Ptr Token -> CInt -> CInt -> CInt -> IO CInt +eval :: Context -> Ptr CInt -> CInt -> CInt -> IO CInt eval = {# call eval #} @@ -457,21 +552,9 @@ eval = {# call eval #} -- int n_past, -- int n_threads); -- -evalEmbd :: Context -> Ptr CFloat -> CInt -> CInt -> CInt -> IO CInt +evalEmbd :: Context -> Ptr CFloat -> CInt -> CInt -> IO CInt evalEmbd = {# call eval_embd #} - --- --- // Export a static computation graph for context of 511 and batch size of 1 --- // NOTE: since this functionality is mostly for debugging and demonstration purposes, we hardcode these --- // parameters here to keep things simple --- // IMPORTANT: do not use for anything else other than debugging and testing! --- LLAMA_API int llama_eval_export(struct llama_context * ctx, const char * fname); --- -evalExport :: Context -> Ptr CChar -> IO CInt -evalExport = {# call eval_export #} - - -- -- // Convert the provided text into tokens. -- // The tokens pointer must be large enough to hold the resulting tokens. @@ -485,23 +568,20 @@ evalExport = {# call eval_export #} -- int n_max_tokens, -- bool add_bos); -- -tokenize :: Context -> Ptr CChar -> Ptr Token -> CInt -> CUChar -> IO CInt +tokenize :: Model + -> Ptr CChar + -> CInt + -> Ptr CInt + -> CInt + -> CUChar + -> CUChar + -> IO CInt tokenize = {# call tokenize #} --- LLAMA_API int llama_tokenize_with_model( --- const struct llama_model * model, --- const char * text, --- llama_token * tokens, --- int n_max_tokens, --- bool add_bos); -tokenizeWithModel :: Model -> Ptr CChar -> Ptr Token -> CInt -> CUChar -> IO CInt -tokenizeWithModel = {# call tokenize_with_model #} - - -- -- LLAMA_API int llama_n_vocab(const struct llama_context * ctx); -- -nVocab :: Context -> IO CInt +nVocab :: Model -> IO CInt nVocab = {# call n_vocab #} -- @@ -513,43 +593,9 @@ nCtx = {# call n_ctx #} -- -- LLAMA_API int llama_n_embd (const struct llama_context * ctx); -- -nEmbd :: Context -> IO CInt +nEmbd :: Model -> IO CInt nEmbd = {# call n_embd #} - --- --- LLAMA_API int llama_n_vocab_from_model(const struct llama_model * model); --- -nVocabFromModel :: Model -> IO CInt -nVocabFromModel = {# call n_vocab_from_model #} - --- --- LLAMA_API int llama_n_ctx_from_model (const struct llama_model * model); --- -nCtxFromModel :: Model -> IO CInt -nCtxFromModel = {# call n_ctx_from_model #} - - --- --- LLAMA_API int llama_n_embd_from_model (const struct llama_model * model); --- -nEmbdFromModel :: Model -> IO CInt -nEmbdFromModel = {# call n_embd_from_model #} - - --- --- // Get the vocabulary as output parameters. --- // Returns number of results. --- LLAMA_API int llama_get_vocab( --- const struct llama_context * ctx, --- const char * * strings, --- float * scores, --- int capacity); --- -getVocab :: Context -> Ptr (Ptr CChar) -> Ptr CFloat -> CInt -> IO CInt -getVocab = {# call get_vocab #} - - -- -- // Token logits obtained from the last call to llama_eval() -- // The logits for the last token are stored in the last row @@ -561,7 +607,6 @@ getVocab = {# call get_vocab #} getLogits :: Context -> IO (Ptr CFloat) getLogits = {# call llama_get_logits #} - -- -- // Get the embeddings for the input -- // shape: [n_embd] (1-dimensional) @@ -575,37 +620,30 @@ getEmbeddings = {# call llama_get_embeddings #} -- // Token Id -> String. Uses the vocabulary in the provided context -- LLAMA_API const char * llama_token_to_str(const struct llama_context * ctx, llama_token token); -- -tokenToStr :: Context -> Token -> IO (Ptr CChar) -tokenToStr = {# call token_to_str #} - - --- LLAMA_API const char * llama_token_to_str_with_model( --- const struct llama_model * model, --- llama_token token); -tokenToStrWithModel :: Model -> Token -> IO (Ptr CChar) -tokenToStrWithModel = {# call token_to_str_with_model #} +tokenToPiece :: Model -> Token -> Ptr CChar -> CInt -> IO CInt +tokenToPiece = {# call token_to_piece #} -- // Special tokens -- --- LLAMA_API llama_token llama_token_bos(); // beginning-of-sentence +-- LLAMA_API llama_token llama_token_bos(const struct llama_model * model); // beginning-of-sentence -- -tokenBos :: IO Token +tokenBos :: Model -> IO Token tokenBos = {# call token_bos #} -- --- LLAMA_API llama_token llama_token_eos(); // end-of-sentence +-- LLAMA_API llama_token llama_token_eos(const struct llama_model * model); // end-of-sentence -- -tokenEos :: IO Token +tokenEos :: Model -> IO Token tokenEos = {# call token_eos #} -- --- LLAMA_API llama_token llama_token_nl(); // next-line +-- LLAMA_API llama_token llama_token_nl(const struct llama_model * model); // next-line -- -tokenNl :: IO Token +tokenNl :: Model -> IO Token tokenNl = {# call token_nl #} @@ -613,19 +651,10 @@ tokenNl = {# call token_nl #} -- -- /// @details Repetition penalty described in CTRL academic paper https://arxiv.org/abs/1909.05858, with negative logit fix. --- LLAMA_API void llama_sample_repetition_penalty(struct llama_context * ctx, llama_token_data_array * candidates, const llama_token * last_tokens, size_t last_tokens_size, float penalty); --- -sampleRepetitionPenalty :: Context -> Ptr TokenDataArray -> Ptr Token -> CULong -> CFloat -> IO () -sampleRepetitionPenalty = {# call sample_repetition_penalty #} - - --- --- /// @details Frequency and presence penalties described in OpenAI API https://platform.openai.com/docs/api-reference/parameter-details. --- LLAMA_API void llama_sample_frequency_and_presence_penalties(struct llama_context * ctx, llama_token_data_array * candidates, const llama_token * last_tokens, size_t last_tokens_size, float alpha_frequency, float alpha_presence); +-- LLAMA_API void llama_sample_repetition_penalty(struct llama_context * ctx, llama_token_data_array * candidates, const llama_token * last_tokens, size_t last_tokens_size, float penalty, float penalty_freq); -- -sampleFrequencyAndPresencePenalties - :: Context -> Ptr TokenDataArray -> Ptr Token -> CULong -> CFloat -> CFloat -> IO () -sampleFrequencyAndPresencePenalties = {# call sample_frequency_and_presence_penalties #} +sampleRepetitionPenalties :: Context -> Ptr TokenDataArray -> Ptr Token -> CULong -> CFloat -> CFloat -> CFloat -> IO () +sampleRepetitionPenalties = {# call sample_repetition_penalties #} -- /// @details Apply classifier-free guidance to the logits as described in academic paper "Stay on topic with Classifier-Free Guidance" https://arxiv.org/abs/2306.17806