-
Notifications
You must be signed in to change notification settings - Fork 20.4k
Add self‑speculative decoding (no draft model required) #18471
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from 15 commits
1fb2658
1faeb62
e3e809c
38f7c28
917f4bb
f1f6584
907d094
456268f
b38eb59
eb43748
1e29af4
a1584ac
cb3a402
af382c3
924517d
9ac8817
8ea068e
288ab50
fd4d803
f895bca
a330093
1f8d366
72f416e
dd23149
351e798
bc33838
9f8401a
003c903
7164b4f
c1ff133
606ff8f
aba472e
6fc7dfc
45da93e
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -164,6 +164,17 @@ enum common_params_sampling_config : uint64_t { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_PARAMS_SAMPLING_CONFIG_MIROSTAT_ETA = 1 << 11, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| enum common_speculative_type { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_NONE, // no speculative decoding | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_DRAFT, // draft model | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_EAGLE3, // eagle draft model | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_NGRAM_SIMPLE, // simple self-speculative decoding | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_NGRAM_MAP_K, // self-speculative decoding with n-gram keys only | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_NGRAM_MAP_K4V, // self-speculative decoding with n-gram keys and 4 m-gram values | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_NGRAM_CACHE, // self-speculative decoding with 3-level n-gram cache | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| COMMON_SPECULATIVE_TYPE_COUNT // number of types, unknown type | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // sampling parameters | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| struct common_params_sampling { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -242,6 +253,14 @@ struct common_params_model { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string name = ""; // in format <user>/<model>[:<tag>] (tag is optional) // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| struct common_speculative_config { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| common_speculative_type type; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::map<std::string, std::string> config; // map of incubative options (not yet in common_params) | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. IMO this mapping will be a headache for long-term maintenance. Either add more comments to explain what can be the key/value, or just refactor it into a simple struct
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. AFAICT, this config is a generic/oblique way to adjust ngram parameters at runtime. They are consumed here: llama.cpp/common/speculative.cpp Lines 211 to 246 in 924517d
I think @srogmann is likely using it to evaluate different configurations more efficiently (i.e. without having to restart the server), which he alluded to in #18471 (comment). If this is the case, I would recommend to extract this functionality in a separate PR that would remain as draft and be used for such experimentation/research. This way we simplify the logic and don't have to maintain this logic before it matures to a good level where it can be documented and used by everyone. |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| common_speculative_config(common_speculative_type t, | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| const std::map<std::string, std::string>& c = {}) : type(t), config(c) {} | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| struct common_params_speculative { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::vector<ggml_backend_dev_t> devices; // devices to use for offloading | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -261,6 +280,21 @@ struct common_params_speculative { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| struct cpu_params cpuparams_batch; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| struct common_params_model model; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // draftless: | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| common_speculative_type draftless_type = COMMON_SPECULATIVE_TYPE_NONE; // type of speculative decoding without a draft model | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| uint16_t spec_ngram_size_n = 12; // ngram size for lookup | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| uint16_t spec_ngram_size_m = 48; // mgram size for speculative tokens | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::vector<common_speculative_config> configs = {}; // list of speculative configs to try | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string lookup_cache_static = ""; // path of static ngram cache file for lookup decoding // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string lookup_cache_dynamic = ""; // path of dynamic ngram cache file for lookup decoding // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| bool has_dft() const { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return !model.path.empty() || !model.hf_repo.empty(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| struct common_params_vocoder { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -378,8 +412,6 @@ struct common_params { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string path_prompt_cache = ""; // path to file for saving/loading prompt eval state // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string input_prefix = ""; // string to prefix user inputs with // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string input_suffix = ""; // string to suffix user inputs with // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string lookup_cache_static = ""; // path of static ngram cache file for lookup decoding // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string lookup_cache_dynamic = ""; // path of dynamic ngram cache file for lookup decoding // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::string logits_file = ""; // file for saving *all* logits // NOLINT | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // llama-debug specific options | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -575,10 +607,6 @@ struct common_params { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // return false from callback to abort model loading or true to continue | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| llama_progress_callback load_progress_callback = NULL; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| void * load_progress_callback_user_data = NULL; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| bool has_speculative() const { | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| return !speculative.model.path.empty() || !speculative.model.hf_repo.empty(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| // call once at the start of a program if it uses libcommon | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -714,8 +742,6 @@ struct common_init_result { | |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::vector<llama_adapter_lora_ptr> & lora(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| void free_context(); | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| private: | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| struct impl; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
| std::unique_ptr<impl> pimpl; | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think we should allow combined values here, for ex:
eagle3;draftis an invalid combination. Probably just support single value first for simplification.Also, we are mixing between no-draft and draft model config here (as
eagle3can be specified here). I think the system should be divided into 2 categories:-mdoptionAnd this option can be renamed to
--spec-draftlessor something like this, the rule is that-mdand--spec-draftlesscannot be specified at the same timeThere was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
IMO each ngram config should be a dedicated arg, prefixed by
--spec-ngram, example:--spec-ngram-size-n, --spec-ngram-size-mEach arg must have a short help message to explain what it does