char-fork/llama.cpp
git clone https://git.t4t.associates/char-fork/llama.cpp
dd1ea5243
char/aliceai-t5-moe
1#include "arg.h" 2#include "ggml.h" 3#include "common.h" 4#include "ngram-cache.h" 5#include "sampling.h" 6#include "speculative.h" 7#include "log.h" 8#include "llama.h" 9 10#include <algorithm> 11#include <clocale> 12#include <cstdint> 13#include <cstdio> 14#include <fstream> 15#include <string> 16#include <vector> 17 18int main (int argc ,char ** argv ){ 19 std::setlocale (LC_NUMERIC ,"C" ); 20 21common_params params ; 22 23common_init (); 24 25if (!common_params_parse (argc ,argv ,params ,LLAMA_EXAMPLE_LOOKUP )) { 26return 1 ; 27 } 28 29// max. number of additional tokens to draft if match is found 30const int n_draft = params .speculative .draft .n_max ; 31 32const auto output_limits = common_speculative_get_output_limits (params .n_batch ,params .n_parallel ,n_draft ); 33params .n_outputs_max = output_limits .total ; 34params .n_outputs_max_per_seq = output_limits .per_seq ; 35 36// init llama.cpp 37llama_backend_init (); 38llama_numa_init (params .numa ); 39 40// load the model 41auto llama_init = common_init_from_params (params ); 42 43auto * model = llama_init -> model (); 44auto * ctx = llama_init -> context (); 45 46const llama_vocab * vocab = llama_model_get_vocab (model ); 47 48// tokenize the prompt 49 std::vector < llama_token > inp ; 50inp = common_tokenize (ctx ,params .prompt , true, true); 51 52common_ngram_cache ngram_cache_context ; 53common_ngram_cache ngram_cache_dynamic ; 54common_ngram_cache ngram_cache_static ; 55int64_t t_draft_flat_us = 0 ; 56int64_t t_draft_us = 0 ; 57 58 { 59// Fill up context ngram cache with tokens from user input: 60const int64_t t_start_draft_us = ggml_time_us (); 61common_ngram_cache_update (ngram_cache_context ,LLAMA_NGRAM_MIN ,LLAMA_NGRAM_MAX ,inp ,inp .size (), false); 62 63if (!params .speculative .ngram_cache .lookup_cache_static .empty ()) { 64try { 65ngram_cache_static = common_ngram_cache_load (params .speculative .ngram_cache .lookup_cache_static ); 66 }catch (std::ifstream::failure const & ) { 67LOG_ERR ("failed to open static lookup cache: %s" ,params .speculative .ngram_cache .lookup_cache_static .c_str ()); 68exit (1 ); 69 } 70 } 71 72if (!params .speculative .ngram_cache .lookup_cache_dynamic .empty ()) { 73try { 74ngram_cache_dynamic = common_ngram_cache_load (params .speculative .ngram_cache .lookup_cache_dynamic ); 75 }catch (std::ifstream::failure const & ) {}// if the file does not exist it will simply be created at the end of the program 76 } 77 78t_draft_flat_us += ggml_time_us ()- t_start_draft_us ; 79 } 80 81const int max_context_size = llama_n_ctx (ctx ); 82const int max_tokens_list_size = max_context_size - 4 ; 83 84if ((int )inp .size ()> max_tokens_list_size ) { 85LOG_ERR ("%s: prompt too long (%d tokens, max %d)\n" ,__func__ , (int )inp .size (),max_tokens_list_size ); 86return 1 ; 87 } 88 89LOG ("\n\n" ); 90 91for (auto id :inp ) { 92LOG ("%s" ,common_token_to_piece (ctx ,id ).c_str ()); 93 } 94 95fflush (stderr ); 96 97const int n_input = inp .size (); 98 99const auto t_enc_start = ggml_time_us (); 100 101llama_decode (ctx ,llama_batch_get_one (inp .data (),n_input - 1 )); 102llama_decode (ctx ,llama_batch_get_one (& inp .back (),1 )); 103 104const auto t_enc_end = ggml_time_us (); 105 106int n_predict = 0 ; 107int n_drafted = 0 ; 108int n_accept = 0 ; 109 110int n_past = inp .size (); 111 112bool has_eos = false; 113 114struct common_sampler * smpl = common_sampler_init (model ,params .sampling ); 115 116 std::vector < llama_token > draft ; 117 118llama_batch batch_tgt = llama_batch_init (llama_n_ctx (ctx ),0 ,1 ); 119 120const auto t_dec_start = ggml_time_us (); 121 122while (true) { 123// print current draft sequence 124LOG_DBG ("drafted %s\n" ,string_from (ctx ,draft ).c_str ()); 125 126int i_dft = 0 ; 127while (true) { 128// sample from the target model 129llama_token id = common_sampler_sample (smpl ,ctx ,i_dft ); 130 131common_sampler_accept (smpl ,id , true); 132 133const std::string token_str = common_token_to_piece (ctx ,id ); 134 135if (!params .use_color ) { 136LOG ("%s" ,token_str .c_str ()); 137 } 138 139if (llama_vocab_is_eog (vocab ,id )) { 140has_eos = true; 141 } 142 143++ n_predict ; 144 145// check if the target token matches the draft 146if (i_dft < (int )draft .size ()&& id == draft [i_dft ]) { 147LOG_DBG ("the sampled target token matches the %dth drafted token (%d, '%s') - accepted\n" ,i_dft ,id ,token_str .c_str ()); 148++ n_accept ; 149++ n_past ; 150++ i_dft ; 151inp .push_back (id ); 152 { 153// Update context ngram cache with the newly accepted token: 154const int64_t t_start_draft_us = ggml_time_us (); 155common_ngram_cache_update (ngram_cache_context ,LLAMA_NGRAM_MIN ,LLAMA_NGRAM_MAX ,inp ,1 , false); 156t_draft_us += ggml_time_us ()- t_start_draft_us ; 157 } 158 159if (params .use_color ) { 160// color accepted draft token 161LOG ("\033[34m%s\033[0m" ,token_str .c_str ()); 162fflush (stdout ); 163 } 164continue ; 165 } 166 167if (params .use_color ) { 168LOG ("%s" ,token_str .c_str ()); 169 } 170fflush (stdout ); 171 172 173LOG_DBG ("the sampled target token (%d, '%s') did not match, or we ran out of drafted tokens\n" ,id ,token_str .c_str ()); 174 175draft .clear (); 176draft .push_back (id ); 177inp .push_back (id ); 178 { 179// Update context ngram cache with the newly accepted token: 180const int64_t t_start_draft_us = ggml_time_us (); 181common_ngram_cache_update (ngram_cache_context ,LLAMA_NGRAM_MIN ,LLAMA_NGRAM_MAX ,inp ,1 , false); 182t_draft_us += ggml_time_us ()- t_start_draft_us ; 183 } 184break ; 185 } 186 187if ((params .n_predict > 0 && n_predict > params .n_predict )|| has_eos ) { 188break ; 189 } 190 191// KV cache management 192// clean the cache of draft tokens that weren't accepted 193llama_memory_seq_rm (llama_get_memory (ctx ),0 ,n_past ,-1 ); 194 195common_batch_clear (batch_tgt ); 196common_batch_add (batch_tgt ,draft [0 ],n_past , {0 }, true); 197 198// Draft already contains a single token sampled from the model: 199GGML_ASSERT (draft .size ()== 1 ); 200GGML_ASSERT (draft [0 ]== inp .back ()); 201const int64_t t_start_draft_us = ggml_time_us (); 202 203common_ngram_cache_draft (inp ,draft ,n_draft ,LLAMA_NGRAM_MIN ,LLAMA_NGRAM_MAX ,ngram_cache_context ,ngram_cache_dynamic ,ngram_cache_static ); 204 205for (size_t i = 1 ;i < draft .size ();++ i ) { 206common_batch_add (batch_tgt ,draft [i ],n_past + i , {0 }, true); 207 } 208 209t_draft_us += ggml_time_us ()- t_start_draft_us ; 210n_drafted += draft .size ()- 1 ; 211 212llama_decode (ctx ,batch_tgt ); 213++ n_past ; 214 215draft .erase (draft .begin ()); 216 } 217 218auto t_dec_end = ggml_time_us (); 219 220// Update dynamic ngram cache with context ngram cache and save it to disk: 221common_ngram_cache_merge (ngram_cache_dynamic ,ngram_cache_context ); 222common_ngram_cache_save (ngram_cache_dynamic ,params .speculative .ngram_cache .lookup_cache_dynamic ); 223 224LOG ("\n\n" ); 225 226LOG_INF ("encoded %4d tokens in %8.3f seconds, speed: %8.3f t/s\n" ,n_input , (t_enc_end - t_enc_start ) /1e6f ,inp .size () / ((t_enc_end - t_enc_start ) /1e6f )); 227LOG_INF ("decoded %4d tokens in %8.3f seconds, speed: %8.3f t/s\n" ,n_predict , (t_dec_end - t_dec_start ) /1e6f ,n_predict / ((t_dec_end - t_dec_start ) /1e6f )); 228 229LOG_INF ("\n" ); 230LOG_INF ("n_draft = %d\n" ,n_draft ); 231LOG_INF ("n_predict = %d\n" ,n_predict ); 232LOG_INF ("n_drafted = %d\n" ,n_drafted ); 233LOG_INF ("t_draft_flat = %.2f ms\n" ,t_draft_flat_us * 1e-3 ); 234LOG_INF ("t_draft = %.2f ms, %.2f us per token, %.2f tokens per second\n" , 235t_draft_us * 1e-3 ,1.0f * t_draft_us /n_drafted ,n_drafted /(1e-6 * t_draft_us )); 236LOG_INF ("n_accept = %d\n" ,n_accept ); 237LOG_INF ("accept = %.3f%%\n" ,100.0f * n_accept /n_drafted ); 238 239LOG_INF ("\ntarget:\n\n" ); 240common_perf_print (ctx ,smpl ); 241 242common_sampler_free (smpl ); 243 244llama_batch_free (batch_tgt ); 245 246llama_backend_free (); 247 248LOG ("\n\n" ); 249 250return 0 ; 251}