Spaces:
Running
Running
Commit
·
21c5b64
1
Parent(s):
9ac3c7e
GGUF: C++ refactor, backend support, misc fixes (llama/11030)
Browse files* GGUF: C++ refactor, backend support, misc fixes
remove ggml_tensor.backend
update CODEOWNERS [no ci]
remove gguf_get_data from API
revise GGUF API data types
- ggml/CMakeLists.txt +2 -1
- ggml/include/ggml-cpp.h +1 -0
- ggml/include/ggml.h +0 -140
- ggml/src/CMakeLists.txt +3 -1
- ggml/src/ggml-impl.h +11 -16
- ggml/src/ggml.c +0 -1276
ggml/CMakeLists.txt
CHANGED
|
@@ -243,7 +243,8 @@ set(GGML_PUBLIC_HEADERS
|
|
| 243 |
include/ggml-metal.h
|
| 244 |
include/ggml-rpc.h
|
| 245 |
include/ggml-sycl.h
|
| 246 |
-
include/ggml-vulkan.h
|
|
|
|
| 247 |
|
| 248 |
set_target_properties(ggml PROPERTIES PUBLIC_HEADER "${GGML_PUBLIC_HEADERS}")
|
| 249 |
#if (GGML_METAL)
|
|
|
|
| 243 |
include/ggml-metal.h
|
| 244 |
include/ggml-rpc.h
|
| 245 |
include/ggml-sycl.h
|
| 246 |
+
include/ggml-vulkan.h
|
| 247 |
+
include/gguf.h)
|
| 248 |
|
| 249 |
set_target_properties(ggml PROPERTIES PUBLIC_HEADER "${GGML_PUBLIC_HEADERS}")
|
| 250 |
#if (GGML_METAL)
|
ggml/include/ggml-cpp.h
CHANGED
|
@@ -7,6 +7,7 @@
|
|
| 7 |
#include "ggml.h"
|
| 8 |
#include "ggml-alloc.h"
|
| 9 |
#include "ggml-backend.h"
|
|
|
|
| 10 |
#include <memory>
|
| 11 |
|
| 12 |
// Smart pointers for ggml types
|
|
|
|
| 7 |
#include "ggml.h"
|
| 8 |
#include "ggml-alloc.h"
|
| 9 |
#include "ggml-backend.h"
|
| 10 |
+
#include "gguf.h"
|
| 11 |
#include <memory>
|
| 12 |
|
| 13 |
// Smart pointers for ggml types
|
ggml/include/ggml.h
CHANGED
|
@@ -241,12 +241,6 @@
|
|
| 241 |
#define GGML_ROPE_TYPE_MROPE 8
|
| 242 |
#define GGML_ROPE_TYPE_VISION 24
|
| 243 |
|
| 244 |
-
#define GGUF_MAGIC "GGUF"
|
| 245 |
-
|
| 246 |
-
#define GGUF_VERSION 3
|
| 247 |
-
|
| 248 |
-
#define GGUF_DEFAULT_ALIGNMENT 32
|
| 249 |
-
|
| 250 |
#define GGML_UNUSED(x) (void)(x)
|
| 251 |
|
| 252 |
#define GGML_PAD(x, n) (((x) + (n) - 1) & ~((n) - 1))
|
|
@@ -403,12 +397,6 @@ extern "C" {
|
|
| 403 |
GGML_PREC_F32,
|
| 404 |
};
|
| 405 |
|
| 406 |
-
enum ggml_backend_type {
|
| 407 |
-
GGML_BACKEND_TYPE_CPU = 0,
|
| 408 |
-
GGML_BACKEND_TYPE_GPU = 10,
|
| 409 |
-
GGML_BACKEND_TYPE_GPU_SPLIT = 20,
|
| 410 |
-
};
|
| 411 |
-
|
| 412 |
// model file types
|
| 413 |
enum ggml_ftype {
|
| 414 |
GGML_FTYPE_UNKNOWN = -1,
|
|
@@ -587,8 +575,6 @@ extern "C" {
|
|
| 587 |
struct ggml_tensor {
|
| 588 |
enum ggml_type type;
|
| 589 |
|
| 590 |
-
GGML_DEPRECATED(enum ggml_backend_type backend, "use the buffer type to find the storage location of the tensor");
|
| 591 |
-
|
| 592 |
struct ggml_backend_buffer * buffer;
|
| 593 |
|
| 594 |
int64_t ne[GGML_MAX_DIMS]; // number of elements
|
|
@@ -2111,132 +2097,6 @@ extern "C" {
|
|
| 2111 |
int64_t n_per_row,
|
| 2112 |
const float * imatrix);
|
| 2113 |
|
| 2114 |
-
//
|
| 2115 |
-
// gguf
|
| 2116 |
-
//
|
| 2117 |
-
|
| 2118 |
-
enum gguf_type {
|
| 2119 |
-
GGUF_TYPE_UINT8 = 0,
|
| 2120 |
-
GGUF_TYPE_INT8 = 1,
|
| 2121 |
-
GGUF_TYPE_UINT16 = 2,
|
| 2122 |
-
GGUF_TYPE_INT16 = 3,
|
| 2123 |
-
GGUF_TYPE_UINT32 = 4,
|
| 2124 |
-
GGUF_TYPE_INT32 = 5,
|
| 2125 |
-
GGUF_TYPE_FLOAT32 = 6,
|
| 2126 |
-
GGUF_TYPE_BOOL = 7,
|
| 2127 |
-
GGUF_TYPE_STRING = 8,
|
| 2128 |
-
GGUF_TYPE_ARRAY = 9,
|
| 2129 |
-
GGUF_TYPE_UINT64 = 10,
|
| 2130 |
-
GGUF_TYPE_INT64 = 11,
|
| 2131 |
-
GGUF_TYPE_FLOAT64 = 12,
|
| 2132 |
-
GGUF_TYPE_COUNT, // marks the end of the enum
|
| 2133 |
-
};
|
| 2134 |
-
|
| 2135 |
-
struct gguf_context;
|
| 2136 |
-
|
| 2137 |
-
struct gguf_init_params {
|
| 2138 |
-
bool no_alloc;
|
| 2139 |
-
|
| 2140 |
-
// if not NULL, create a ggml_context and allocate the tensor data in it
|
| 2141 |
-
struct ggml_context ** ctx;
|
| 2142 |
-
};
|
| 2143 |
-
|
| 2144 |
-
GGML_API struct gguf_context * gguf_init_empty(void);
|
| 2145 |
-
GGML_API struct gguf_context * gguf_init_from_file(const char * fname, struct gguf_init_params params);
|
| 2146 |
-
//GGML_API struct gguf_context * gguf_init_from_buffer(..);
|
| 2147 |
-
|
| 2148 |
-
GGML_API void gguf_free(struct gguf_context * ctx);
|
| 2149 |
-
|
| 2150 |
-
GGML_API const char * gguf_type_name(enum gguf_type type);
|
| 2151 |
-
|
| 2152 |
-
GGML_API int gguf_get_version (const struct gguf_context * ctx);
|
| 2153 |
-
GGML_API size_t gguf_get_alignment (const struct gguf_context * ctx);
|
| 2154 |
-
GGML_API size_t gguf_get_data_offset(const struct gguf_context * ctx);
|
| 2155 |
-
GGML_API void * gguf_get_data (const struct gguf_context * ctx);
|
| 2156 |
-
|
| 2157 |
-
GGML_API int gguf_get_n_kv(const struct gguf_context * ctx);
|
| 2158 |
-
GGML_API int gguf_find_key(const struct gguf_context * ctx, const char * key);
|
| 2159 |
-
GGML_API const char * gguf_get_key (const struct gguf_context * ctx, int key_id);
|
| 2160 |
-
|
| 2161 |
-
GGML_API enum gguf_type gguf_get_kv_type (const struct gguf_context * ctx, int key_id);
|
| 2162 |
-
GGML_API enum gguf_type gguf_get_arr_type(const struct gguf_context * ctx, int key_id);
|
| 2163 |
-
|
| 2164 |
-
// will abort if the wrong type is used for the key
|
| 2165 |
-
GGML_API uint8_t gguf_get_val_u8 (const struct gguf_context * ctx, int key_id);
|
| 2166 |
-
GGML_API int8_t gguf_get_val_i8 (const struct gguf_context * ctx, int key_id);
|
| 2167 |
-
GGML_API uint16_t gguf_get_val_u16 (const struct gguf_context * ctx, int key_id);
|
| 2168 |
-
GGML_API int16_t gguf_get_val_i16 (const struct gguf_context * ctx, int key_id);
|
| 2169 |
-
GGML_API uint32_t gguf_get_val_u32 (const struct gguf_context * ctx, int key_id);
|
| 2170 |
-
GGML_API int32_t gguf_get_val_i32 (const struct gguf_context * ctx, int key_id);
|
| 2171 |
-
GGML_API float gguf_get_val_f32 (const struct gguf_context * ctx, int key_id);
|
| 2172 |
-
GGML_API uint64_t gguf_get_val_u64 (const struct gguf_context * ctx, int key_id);
|
| 2173 |
-
GGML_API int64_t gguf_get_val_i64 (const struct gguf_context * ctx, int key_id);
|
| 2174 |
-
GGML_API double gguf_get_val_f64 (const struct gguf_context * ctx, int key_id);
|
| 2175 |
-
GGML_API bool gguf_get_val_bool(const struct gguf_context * ctx, int key_id);
|
| 2176 |
-
GGML_API const char * gguf_get_val_str (const struct gguf_context * ctx, int key_id);
|
| 2177 |
-
GGML_API const void * gguf_get_val_data(const struct gguf_context * ctx, int key_id);
|
| 2178 |
-
GGML_API int gguf_get_arr_n (const struct gguf_context * ctx, int key_id);
|
| 2179 |
-
GGML_API const void * gguf_get_arr_data(const struct gguf_context * ctx, int key_id);
|
| 2180 |
-
GGML_API const char * gguf_get_arr_str (const struct gguf_context * ctx, int key_id, int i);
|
| 2181 |
-
|
| 2182 |
-
GGML_API int gguf_get_n_tensors (const struct gguf_context * ctx);
|
| 2183 |
-
GGML_API int gguf_find_tensor (const struct gguf_context * ctx, const char * name);
|
| 2184 |
-
GGML_API size_t gguf_get_tensor_offset(const struct gguf_context * ctx, int i);
|
| 2185 |
-
GGML_API char * gguf_get_tensor_name (const struct gguf_context * ctx, int i);
|
| 2186 |
-
GGML_API enum ggml_type gguf_get_tensor_type (const struct gguf_context * ctx, int i);
|
| 2187 |
-
|
| 2188 |
-
// removes key if it exists
|
| 2189 |
-
GGML_API void gguf_remove_key(struct gguf_context * ctx, const char * key);
|
| 2190 |
-
|
| 2191 |
-
// overrides existing values or adds a new one
|
| 2192 |
-
GGML_API void gguf_set_val_u8 (struct gguf_context * ctx, const char * key, uint8_t val);
|
| 2193 |
-
GGML_API void gguf_set_val_i8 (struct gguf_context * ctx, const char * key, int8_t val);
|
| 2194 |
-
GGML_API void gguf_set_val_u16 (struct gguf_context * ctx, const char * key, uint16_t val);
|
| 2195 |
-
GGML_API void gguf_set_val_i16 (struct gguf_context * ctx, const char * key, int16_t val);
|
| 2196 |
-
GGML_API void gguf_set_val_u32 (struct gguf_context * ctx, const char * key, uint32_t val);
|
| 2197 |
-
GGML_API void gguf_set_val_i32 (struct gguf_context * ctx, const char * key, int32_t val);
|
| 2198 |
-
GGML_API void gguf_set_val_f32 (struct gguf_context * ctx, const char * key, float val);
|
| 2199 |
-
GGML_API void gguf_set_val_u64 (struct gguf_context * ctx, const char * key, uint64_t val);
|
| 2200 |
-
GGML_API void gguf_set_val_i64 (struct gguf_context * ctx, const char * key, int64_t val);
|
| 2201 |
-
GGML_API void gguf_set_val_f64 (struct gguf_context * ctx, const char * key, double val);
|
| 2202 |
-
GGML_API void gguf_set_val_bool(struct gguf_context * ctx, const char * key, bool val);
|
| 2203 |
-
GGML_API void gguf_set_val_str (struct gguf_context * ctx, const char * key, const char * val);
|
| 2204 |
-
GGML_API void gguf_set_arr_data(struct gguf_context * ctx, const char * key, enum gguf_type type, const void * data, int n);
|
| 2205 |
-
GGML_API void gguf_set_arr_str (struct gguf_context * ctx, const char * key, const char ** data, int n);
|
| 2206 |
-
|
| 2207 |
-
// set or add KV pairs from another context
|
| 2208 |
-
GGML_API void gguf_set_kv(struct gguf_context * ctx, struct gguf_context * src);
|
| 2209 |
-
|
| 2210 |
-
// manage tensor info
|
| 2211 |
-
GGML_API void gguf_add_tensor(struct gguf_context * ctx, const struct ggml_tensor * tensor);
|
| 2212 |
-
GGML_API void gguf_set_tensor_type(struct gguf_context * ctx, const char * name, enum ggml_type type);
|
| 2213 |
-
GGML_API void gguf_set_tensor_data(struct gguf_context * ctx, const char * name, const void * data, size_t size);
|
| 2214 |
-
|
| 2215 |
-
// writing gguf files can be done in 2 ways:
|
| 2216 |
-
//
|
| 2217 |
-
// - write the entire gguf_context to a binary file in a single pass:
|
| 2218 |
-
//
|
| 2219 |
-
// gguf_write_to_file(ctx, fname);
|
| 2220 |
-
//
|
| 2221 |
-
// - first prepare a file with a placeholder for the meta data, write the tensor data, then write the meta data:
|
| 2222 |
-
//
|
| 2223 |
-
// FILE * f = fopen(fname, "wb");
|
| 2224 |
-
// fseek(f, gguf_get_meta_size(ctx), SEEK_SET);
|
| 2225 |
-
// fwrite(f, ...);
|
| 2226 |
-
// void * data = gguf_meta_get_meta_data(ctx);
|
| 2227 |
-
// fseek(f, 0, SEEK_SET);
|
| 2228 |
-
// fwrite(f, data, gguf_get_meta_size(ctx));
|
| 2229 |
-
// free(data);
|
| 2230 |
-
// fclose(f);
|
| 2231 |
-
//
|
| 2232 |
-
|
| 2233 |
-
// write the entire context to a binary file
|
| 2234 |
-
GGML_API void gguf_write_to_file(const struct gguf_context * ctx, const char * fname, bool only_meta);
|
| 2235 |
-
|
| 2236 |
-
// get the size in bytes of the meta data (header, kv pairs, tensor info) including padding
|
| 2237 |
-
GGML_API size_t gguf_get_meta_size(const struct gguf_context * ctx);
|
| 2238 |
-
GGML_API void gguf_get_meta_data(const struct gguf_context * ctx, void * data);
|
| 2239 |
-
|
| 2240 |
#ifdef __cplusplus
|
| 2241 |
// restrict not standard in C++
|
| 2242 |
# if defined(__GNUC__)
|
|
|
|
| 241 |
#define GGML_ROPE_TYPE_MROPE 8
|
| 242 |
#define GGML_ROPE_TYPE_VISION 24
|
| 243 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 244 |
#define GGML_UNUSED(x) (void)(x)
|
| 245 |
|
| 246 |
#define GGML_PAD(x, n) (((x) + (n) - 1) & ~((n) - 1))
|
|
|
|
| 397 |
GGML_PREC_F32,
|
| 398 |
};
|
| 399 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 400 |
// model file types
|
| 401 |
enum ggml_ftype {
|
| 402 |
GGML_FTYPE_UNKNOWN = -1,
|
|
|
|
| 575 |
struct ggml_tensor {
|
| 576 |
enum ggml_type type;
|
| 577 |
|
|
|
|
|
|
|
| 578 |
struct ggml_backend_buffer * buffer;
|
| 579 |
|
| 580 |
int64_t ne[GGML_MAX_DIMS]; // number of elements
|
|
|
|
| 2097 |
int64_t n_per_row,
|
| 2098 |
const float * imatrix);
|
| 2099 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 2100 |
#ifdef __cplusplus
|
| 2101 |
// restrict not standard in C++
|
| 2102 |
# if defined(__GNUC__)
|
ggml/src/CMakeLists.txt
CHANGED
|
@@ -208,6 +208,7 @@ add_library(ggml-base
|
|
| 208 |
../include/ggml-backend.h
|
| 209 |
../include/ggml-cpp.h
|
| 210 |
../include/ggml-opt.h
|
|
|
|
| 211 |
ggml.c
|
| 212 |
ggml-alloc.c
|
| 213 |
ggml-backend.cpp
|
|
@@ -215,7 +216,8 @@ add_library(ggml-base
|
|
| 215 |
ggml-threading.cpp
|
| 216 |
ggml-threading.h
|
| 217 |
ggml-quants.c
|
| 218 |
-
ggml-quants.h
|
|
|
|
| 219 |
|
| 220 |
target_include_directories(ggml-base PRIVATE .)
|
| 221 |
|
|
|
|
| 208 |
../include/ggml-backend.h
|
| 209 |
../include/ggml-cpp.h
|
| 210 |
../include/ggml-opt.h
|
| 211 |
+
../include/gguf.h
|
| 212 |
ggml.c
|
| 213 |
ggml-alloc.c
|
| 214 |
ggml-backend.cpp
|
|
|
|
| 216 |
ggml-threading.cpp
|
| 217 |
ggml-threading.h
|
| 218 |
ggml-quants.c
|
| 219 |
+
ggml-quants.h
|
| 220 |
+
gguf.cpp)
|
| 221 |
|
| 222 |
target_include_directories(ggml-base PRIVATE .)
|
| 223 |
|
ggml/src/ggml-impl.h
CHANGED
|
@@ -3,6 +3,8 @@
|
|
| 3 |
// GGML internal header
|
| 4 |
|
| 5 |
#include "ggml.h"
|
|
|
|
|
|
|
| 6 |
#include <assert.h>
|
| 7 |
#include <math.h>
|
| 8 |
#include <stdlib.h> // load `stdlib.h` before other headers to work around MinGW bug: https://sourceforge.net/p/mingw-w64/bugs/192/
|
|
@@ -551,22 +553,15 @@ static inline ggml_bf16_t ggml_compute_fp32_to_bf16(float s) {
|
|
| 551 |
#define GGML_FP32_TO_BF16(x) ggml_compute_fp32_to_bf16(x)
|
| 552 |
#define GGML_BF16_TO_FP32(x) ggml_compute_bf16_to_fp32(x)
|
| 553 |
|
| 554 |
-
// expose GGUF internals for test code
|
| 555 |
-
|
| 556 |
-
GGML_API size_t gguf_type_size(enum gguf_type type);
|
| 557 |
-
|
| 558 |
-
GGML_API struct gguf_context * gguf_init_from_file_impl(FILE * file, struct gguf_init_params params);
|
| 559 |
-
|
| 560 |
-
struct gguf_buf {
|
| 561 |
-
void * data;
|
| 562 |
-
size_t size;
|
| 563 |
-
size_t offset;
|
| 564 |
-
};
|
| 565 |
-
GGML_API struct gguf_buf gguf_buf_init(size_t size);
|
| 566 |
-
GGML_API void gguf_buf_free(struct gguf_buf buf);
|
| 567 |
-
|
| 568 |
-
GGML_API void gguf_write_to_buf(const struct gguf_context * ctx, struct gguf_buf * buf, bool only_meta);
|
| 569 |
-
|
| 570 |
#ifdef __cplusplus
|
| 571 |
}
|
| 572 |
#endif
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 3 |
// GGML internal header
|
| 4 |
|
| 5 |
#include "ggml.h"
|
| 6 |
+
#include "gguf.h"
|
| 7 |
+
|
| 8 |
#include <assert.h>
|
| 9 |
#include <math.h>
|
| 10 |
#include <stdlib.h> // load `stdlib.h` before other headers to work around MinGW bug: https://sourceforge.net/p/mingw-w64/bugs/192/
|
|
|
|
| 553 |
#define GGML_FP32_TO_BF16(x) ggml_compute_fp32_to_bf16(x)
|
| 554 |
#define GGML_BF16_TO_FP32(x) ggml_compute_bf16_to_fp32(x)
|
| 555 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 556 |
#ifdef __cplusplus
|
| 557 |
}
|
| 558 |
#endif
|
| 559 |
+
|
| 560 |
+
#ifdef __cplusplus
|
| 561 |
+
#include <vector>
|
| 562 |
+
|
| 563 |
+
// expose GGUF internals for test code
|
| 564 |
+
GGML_API size_t gguf_type_size(enum gguf_type type);
|
| 565 |
+
GGML_API struct gguf_context * gguf_init_from_file_impl(FILE * file, struct gguf_init_params params);
|
| 566 |
+
GGML_API void gguf_write_to_buf(const struct gguf_context * ctx, std::vector<int8_t> & buf, bool only_meta);
|
| 567 |
+
#endif // __cplusplus
|
ggml/src/ggml.c
CHANGED
|
@@ -1588,15 +1588,8 @@ static struct ggml_tensor * ggml_new_tensor_impl(
|
|
| 1588 |
|
| 1589 |
struct ggml_tensor * const result = (struct ggml_tensor *)((char *)ctx->mem_buffer + obj_new->offs);
|
| 1590 |
|
| 1591 |
-
#ifdef __clang__
|
| 1592 |
-
// temporary until ggml_tensor::backend is removed
|
| 1593 |
-
#pragma clang diagnostic push
|
| 1594 |
-
#pragma clang diagnostic ignored "-Wdeprecated-declarations"
|
| 1595 |
-
#endif
|
| 1596 |
-
|
| 1597 |
*result = (struct ggml_tensor) {
|
| 1598 |
/*.type =*/ type,
|
| 1599 |
-
/*.backend =*/ GGML_BACKEND_TYPE_CPU,
|
| 1600 |
/*.buffer =*/ NULL,
|
| 1601 |
/*.ne =*/ { 1, 1, 1, 1 },
|
| 1602 |
/*.nb =*/ { 0, 0, 0, 0 },
|
|
@@ -1612,10 +1605,6 @@ static struct ggml_tensor * ggml_new_tensor_impl(
|
|
| 1612 |
/*.padding =*/ { 0 },
|
| 1613 |
};
|
| 1614 |
|
| 1615 |
-
#ifdef __clang__
|
| 1616 |
-
#pragma clang diagnostic pop
|
| 1617 |
-
#endif
|
| 1618 |
-
|
| 1619 |
// TODO: this should not be needed as long as we don't rely on aligned SIMD loads
|
| 1620 |
//GGML_ASSERT_ALIGNED(result->data);
|
| 1621 |
|
|
@@ -6417,1271 +6406,6 @@ size_t ggml_quantize_chunk(
|
|
| 6417 |
|
| 6418 |
////////////////////////////////////////////////////////////////////////////////
|
| 6419 |
|
| 6420 |
-
struct gguf_str {
|
| 6421 |
-
uint64_t n; // GGUFv2
|
| 6422 |
-
char * data;
|
| 6423 |
-
};
|
| 6424 |
-
|
| 6425 |
-
static const size_t GGUF_TYPE_SIZE[GGUF_TYPE_COUNT] = {
|
| 6426 |
-
[GGUF_TYPE_UINT8] = sizeof(uint8_t),
|
| 6427 |
-
[GGUF_TYPE_INT8] = sizeof(int8_t),
|
| 6428 |
-
[GGUF_TYPE_UINT16] = sizeof(uint16_t),
|
| 6429 |
-
[GGUF_TYPE_INT16] = sizeof(int16_t),
|
| 6430 |
-
[GGUF_TYPE_UINT32] = sizeof(uint32_t),
|
| 6431 |
-
[GGUF_TYPE_INT32] = sizeof(int32_t),
|
| 6432 |
-
[GGUF_TYPE_FLOAT32] = sizeof(float),
|
| 6433 |
-
[GGUF_TYPE_BOOL] = sizeof(bool),
|
| 6434 |
-
[GGUF_TYPE_STRING] = sizeof(struct gguf_str),
|
| 6435 |
-
[GGUF_TYPE_UINT64] = sizeof(uint64_t),
|
| 6436 |
-
[GGUF_TYPE_INT64] = sizeof(int64_t),
|
| 6437 |
-
[GGUF_TYPE_FLOAT64] = sizeof(double),
|
| 6438 |
-
[GGUF_TYPE_ARRAY] = 0, // undefined
|
| 6439 |
-
};
|
| 6440 |
-
static_assert(GGUF_TYPE_COUNT == 13, "GGUF_TYPE_COUNT != 13");
|
| 6441 |
-
|
| 6442 |
-
static const char * GGUF_TYPE_NAME[GGUF_TYPE_COUNT] = {
|
| 6443 |
-
[GGUF_TYPE_UINT8] = "u8",
|
| 6444 |
-
[GGUF_TYPE_INT8] = "i8",
|
| 6445 |
-
[GGUF_TYPE_UINT16] = "u16",
|
| 6446 |
-
[GGUF_TYPE_INT16] = "i16",
|
| 6447 |
-
[GGUF_TYPE_UINT32] = "u32",
|
| 6448 |
-
[GGUF_TYPE_INT32] = "i32",
|
| 6449 |
-
[GGUF_TYPE_FLOAT32] = "f32",
|
| 6450 |
-
[GGUF_TYPE_BOOL] = "bool",
|
| 6451 |
-
[GGUF_TYPE_STRING] = "str",
|
| 6452 |
-
[GGUF_TYPE_ARRAY] = "arr",
|
| 6453 |
-
[GGUF_TYPE_UINT64] = "u64",
|
| 6454 |
-
[GGUF_TYPE_INT64] = "i64",
|
| 6455 |
-
[GGUF_TYPE_FLOAT64] = "f64",
|
| 6456 |
-
};
|
| 6457 |
-
static_assert(GGUF_TYPE_COUNT == 13, "GGUF_TYPE_COUNT != 13");
|
| 6458 |
-
|
| 6459 |
-
union gguf_value {
|
| 6460 |
-
uint8_t uint8;
|
| 6461 |
-
int8_t int8;
|
| 6462 |
-
uint16_t uint16;
|
| 6463 |
-
int16_t int16;
|
| 6464 |
-
uint32_t uint32;
|
| 6465 |
-
int32_t int32;
|
| 6466 |
-
float float32;
|
| 6467 |
-
uint64_t uint64;
|
| 6468 |
-
int64_t int64;
|
| 6469 |
-
double float64;
|
| 6470 |
-
bool bool_;
|
| 6471 |
-
|
| 6472 |
-
struct gguf_str str;
|
| 6473 |
-
|
| 6474 |
-
struct {
|
| 6475 |
-
enum gguf_type type;
|
| 6476 |
-
|
| 6477 |
-
uint64_t n; // GGUFv2
|
| 6478 |
-
void * data;
|
| 6479 |
-
} arr;
|
| 6480 |
-
};
|
| 6481 |
-
|
| 6482 |
-
struct gguf_kv {
|
| 6483 |
-
struct gguf_str key;
|
| 6484 |
-
|
| 6485 |
-
enum gguf_type type;
|
| 6486 |
-
union gguf_value value;
|
| 6487 |
-
};
|
| 6488 |
-
|
| 6489 |
-
struct gguf_header {
|
| 6490 |
-
char magic[4];
|
| 6491 |
-
|
| 6492 |
-
uint32_t version;
|
| 6493 |
-
uint64_t n_tensors; // GGUFv2
|
| 6494 |
-
uint64_t n_kv; // GGUFv2
|
| 6495 |
-
};
|
| 6496 |
-
|
| 6497 |
-
struct gguf_tensor_info {
|
| 6498 |
-
struct gguf_str name;
|
| 6499 |
-
|
| 6500 |
-
uint32_t n_dims;
|
| 6501 |
-
uint64_t ne[GGML_MAX_DIMS];
|
| 6502 |
-
|
| 6503 |
-
enum ggml_type type;
|
| 6504 |
-
|
| 6505 |
-
uint64_t offset; // offset from start of `data`, must be a multiple of `ALIGNMENT`
|
| 6506 |
-
|
| 6507 |
-
// for writing API
|
| 6508 |
-
const void * data;
|
| 6509 |
-
size_t size;
|
| 6510 |
-
};
|
| 6511 |
-
|
| 6512 |
-
struct gguf_context {
|
| 6513 |
-
struct gguf_header header;
|
| 6514 |
-
|
| 6515 |
-
struct gguf_kv * kv;
|
| 6516 |
-
struct gguf_tensor_info * infos;
|
| 6517 |
-
|
| 6518 |
-
size_t alignment;
|
| 6519 |
-
size_t offset; // offset of `data` from beginning of file
|
| 6520 |
-
size_t size; // size of `data` in bytes
|
| 6521 |
-
|
| 6522 |
-
//uint8_t * padding;
|
| 6523 |
-
void * data;
|
| 6524 |
-
};
|
| 6525 |
-
|
| 6526 |
-
size_t gguf_type_size(enum gguf_type type) {
|
| 6527 |
-
GGML_ASSERT(0 <= type && type < GGUF_TYPE_COUNT);
|
| 6528 |
-
return GGUF_TYPE_SIZE[type];
|
| 6529 |
-
}
|
| 6530 |
-
|
| 6531 |
-
static bool gguf_tensor_info_sanitize(struct gguf_tensor_info * info) {
|
| 6532 |
-
if (info->n_dims > GGML_MAX_DIMS) {
|
| 6533 |
-
fprintf(stderr, "%s: invalid number of dimensions (%" PRIu32 ")\n", __func__, info->n_dims);
|
| 6534 |
-
return false;
|
| 6535 |
-
}
|
| 6536 |
-
|
| 6537 |
-
if (info->type < 0 || info->type >= GGML_TYPE_COUNT) {
|
| 6538 |
-
fprintf(stderr, "%s: invalid type (%d)\n", __func__, info->type);
|
| 6539 |
-
return false;
|
| 6540 |
-
}
|
| 6541 |
-
|
| 6542 |
-
if (strlen(info->name.data) >= GGML_MAX_NAME) {
|
| 6543 |
-
fprintf(stderr, "%s: tensor '%s' name is too long\n", __func__, info->name.data);
|
| 6544 |
-
return false;
|
| 6545 |
-
}
|
| 6546 |
-
|
| 6547 |
-
for (uint32_t i = 0; i < info->n_dims; ++i) {
|
| 6548 |
-
if (info->ne[i] <= 0) {
|
| 6549 |
-
fprintf(stderr, "%s: invalid number of elements (%" PRIu64 ")\n", __func__, info->ne[i]);
|
| 6550 |
-
return false;
|
| 6551 |
-
}
|
| 6552 |
-
}
|
| 6553 |
-
|
| 6554 |
-
// prevent overflow for total number of elements
|
| 6555 |
-
if (INT64_MAX/info->ne[1] <= info->ne[0]) {
|
| 6556 |
-
fprintf(stderr, "%s: invalid number of elements (%" PRIu64 ")\n", __func__, info->ne[1]);
|
| 6557 |
-
return false;
|
| 6558 |
-
}
|
| 6559 |
-
|
| 6560 |
-
if (INT64_MAX/info->ne[2] <= info->ne[0]*info->ne[1]) {
|
| 6561 |
-
fprintf(stderr, "%s: invalid number of elements (%" PRIu64 ")\n", __func__, info->ne[2]);
|
| 6562 |
-
return false;
|
| 6563 |
-
}
|
| 6564 |
-
|
| 6565 |
-
if (INT64_MAX/info->ne[3] <= info->ne[0]*info->ne[1]*info->ne[2]) {
|
| 6566 |
-
fprintf(stderr, "%s: invalid number of elements (%" PRIu64 ")\n", __func__, info->ne[3]);
|
| 6567 |
-
return false;
|
| 6568 |
-
}
|
| 6569 |
-
|
| 6570 |
-
return true;
|
| 6571 |
-
}
|
| 6572 |
-
|
| 6573 |
-
static bool gguf_fread_el(FILE * file, void * dst, size_t size, size_t * offset) {
|
| 6574 |
-
const size_t n = fread(dst, 1, size, file);
|
| 6575 |
-
*offset += n;
|
| 6576 |
-
return n == size;
|
| 6577 |
-
}
|
| 6578 |
-
|
| 6579 |
-
static bool gguf_fread_str(FILE * file, struct gguf_str * p, size_t * offset) {
|
| 6580 |
-
p->n = 0;
|
| 6581 |
-
p->data = NULL;
|
| 6582 |
-
|
| 6583 |
-
bool ok = true;
|
| 6584 |
-
|
| 6585 |
-
ok = ok && gguf_fread_el(file, &p->n, sizeof(p->n), offset);
|
| 6586 |
-
|
| 6587 |
-
// early exit if string length is invalid, prevents from integer overflow
|
| 6588 |
-
if (p->n == SIZE_MAX) {
|
| 6589 |
-
fprintf(stderr, "%s: invalid string length (%" PRIu64 ")\n", __func__, p->n);
|
| 6590 |
-
return false;
|
| 6591 |
-
}
|
| 6592 |
-
|
| 6593 |
-
p->data = calloc(p->n + 1, 1);
|
| 6594 |
-
if (!p->data) {
|
| 6595 |
-
fprintf(stderr, "%s: failed to allocate memory for string of length %" PRIu64 "\n", __func__, p->n);
|
| 6596 |
-
return false;
|
| 6597 |
-
}
|
| 6598 |
-
|
| 6599 |
-
ok = ok && gguf_fread_el(file, p->data, p->n, offset);
|
| 6600 |
-
|
| 6601 |
-
return ok;
|
| 6602 |
-
}
|
| 6603 |
-
|
| 6604 |
-
static void gguf_free_kv(struct gguf_kv * kv) {
|
| 6605 |
-
if (kv->key.data) {
|
| 6606 |
-
GGML_FREE(kv->key.data);
|
| 6607 |
-
}
|
| 6608 |
-
|
| 6609 |
-
if (kv->type == GGUF_TYPE_STRING) {
|
| 6610 |
-
if (kv->value.str.data) {
|
| 6611 |
-
GGML_FREE(kv->value.str.data);
|
| 6612 |
-
}
|
| 6613 |
-
}
|
| 6614 |
-
|
| 6615 |
-
if (kv->type == GGUF_TYPE_ARRAY) {
|
| 6616 |
-
if (kv->value.arr.data) {
|
| 6617 |
-
if (kv->value.arr.type == GGUF_TYPE_STRING) {
|
| 6618 |
-
for (uint64_t j = 0; j < kv->value.arr.n; ++j) {
|
| 6619 |
-
struct gguf_str * str = &((struct gguf_str *) kv->value.arr.data)[j];
|
| 6620 |
-
if (str->data) {
|
| 6621 |
-
GGML_FREE(str->data);
|
| 6622 |
-
}
|
| 6623 |
-
}
|
| 6624 |
-
}
|
| 6625 |
-
GGML_FREE(kv->value.arr.data);
|
| 6626 |
-
}
|
| 6627 |
-
}
|
| 6628 |
-
}
|
| 6629 |
-
|
| 6630 |
-
struct gguf_context * gguf_init_empty(void) {
|
| 6631 |
-
struct gguf_context * ctx = calloc(1, sizeof(struct gguf_context));
|
| 6632 |
-
if (!ctx) {
|
| 6633 |
-
fprintf(stderr, "%s: failed to allocate memory for context\n", __func__);
|
| 6634 |
-
return NULL;
|
| 6635 |
-
}
|
| 6636 |
-
|
| 6637 |
-
memcpy(ctx->header.magic, GGUF_MAGIC, sizeof(ctx->header.magic));
|
| 6638 |
-
ctx->header.version = GGUF_VERSION;
|
| 6639 |
-
ctx->header.n_tensors = 0;
|
| 6640 |
-
ctx->header.n_kv = 0;
|
| 6641 |
-
|
| 6642 |
-
ctx->kv = NULL;
|
| 6643 |
-
ctx->infos = NULL;
|
| 6644 |
-
|
| 6645 |
-
ctx->alignment = GGUF_DEFAULT_ALIGNMENT;
|
| 6646 |
-
ctx->offset = 0;
|
| 6647 |
-
ctx->size = 0;
|
| 6648 |
-
|
| 6649 |
-
ctx->data = NULL;
|
| 6650 |
-
|
| 6651 |
-
return ctx;
|
| 6652 |
-
}
|
| 6653 |
-
|
| 6654 |
-
struct gguf_context * gguf_init_from_file_impl(FILE * file, struct gguf_init_params params) {
|
| 6655 |
-
// offset from start of file
|
| 6656 |
-
size_t offset = 0;
|
| 6657 |
-
|
| 6658 |
-
char magic[4];
|
| 6659 |
-
|
| 6660 |
-
// check the magic before making allocations
|
| 6661 |
-
{
|
| 6662 |
-
gguf_fread_el(file, &magic, sizeof(magic), &offset);
|
| 6663 |
-
|
| 6664 |
-
for (uint32_t i = 0; i < sizeof(magic); i++) {
|
| 6665 |
-
if (magic[i] != GGUF_MAGIC[i]) {
|
| 6666 |
-
fprintf(stderr, "%s: invalid magic characters '%c%c%c%c'\n", __func__, magic[0], magic[1], magic[2], magic[3]);
|
| 6667 |
-
return NULL;
|
| 6668 |
-
}
|
| 6669 |
-
}
|
| 6670 |
-
}
|
| 6671 |
-
|
| 6672 |
-
bool ok = true;
|
| 6673 |
-
|
| 6674 |
-
struct gguf_context * ctx = calloc(1, sizeof(struct gguf_context));
|
| 6675 |
-
if (!ctx) {
|
| 6676 |
-
fprintf(stderr, "%s: failed to allocate memory for context\n", __func__);
|
| 6677 |
-
return NULL;
|
| 6678 |
-
}
|
| 6679 |
-
|
| 6680 |
-
// read the header
|
| 6681 |
-
{
|
| 6682 |
-
strncpy(ctx->header.magic, magic, 4);
|
| 6683 |
-
|
| 6684 |
-
ctx->kv = NULL;
|
| 6685 |
-
ctx->infos = NULL;
|
| 6686 |
-
ctx->data = NULL;
|
| 6687 |
-
|
| 6688 |
-
ok = ok && gguf_fread_el(file, &ctx->header.version, sizeof(ctx->header.version), &offset);
|
| 6689 |
-
ok = ok && gguf_fread_el(file, &ctx->header.n_tensors, sizeof(ctx->header.n_tensors), &offset);
|
| 6690 |
-
ok = ok && gguf_fread_el(file, &ctx->header.n_kv, sizeof(ctx->header.n_kv), &offset);
|
| 6691 |
-
|
| 6692 |
-
if (ctx->header.version == 1) {
|
| 6693 |
-
fprintf(stderr, "%s: GGUFv1 is no longer supported. please use a more up-to-date version\n", __func__);
|
| 6694 |
-
gguf_free(ctx);
|
| 6695 |
-
return NULL;
|
| 6696 |
-
}
|
| 6697 |
-
|
| 6698 |
-
// sanity-checks to prevent from integer/buffer overflows
|
| 6699 |
-
|
| 6700 |
-
ok = ok && (ctx->header.n_tensors < (SIZE_MAX/2)/sizeof(struct gguf_tensor_info));
|
| 6701 |
-
ok = ok && (ctx->header.n_tensors < (SIZE_MAX/2)/ggml_tensor_overhead());
|
| 6702 |
-
ok = ok && (ctx->header.n_kv < (SIZE_MAX/2)/sizeof(struct gguf_kv));
|
| 6703 |
-
|
| 6704 |
-
if (!ok) {
|
| 6705 |
-
fprintf(stderr, "%s: failed to read header\n", __func__);
|
| 6706 |
-
gguf_free(ctx);
|
| 6707 |
-
return NULL;
|
| 6708 |
-
}
|
| 6709 |
-
}
|
| 6710 |
-
|
| 6711 |
-
// read the kv pairs
|
| 6712 |
-
{
|
| 6713 |
-
const uint64_t n_kv = ctx->header.n_kv;
|
| 6714 |
-
|
| 6715 |
-
if (n_kv > 0) {
|
| 6716 |
-
ctx->kv = calloc(n_kv, sizeof(struct gguf_kv));
|
| 6717 |
-
if (!ctx->kv) {
|
| 6718 |
-
fprintf(stderr, "%s: failed to allocate memory for kv pairs\n", __func__);
|
| 6719 |
-
gguf_free(ctx);
|
| 6720 |
-
return NULL;
|
| 6721 |
-
}
|
| 6722 |
-
}
|
| 6723 |
-
|
| 6724 |
-
for (uint64_t i = 0; i < n_kv; ++i) {
|
| 6725 |
-
struct gguf_kv * kv = &ctx->kv[i];
|
| 6726 |
-
|
| 6727 |
-
//fprintf(stderr, "%s: reading kv %d\n", __func__, i);
|
| 6728 |
-
|
| 6729 |
-
ok = ok && gguf_fread_str(file, &kv->key, &offset);
|
| 6730 |
-
ok = ok && gguf_fread_el (file, &kv->type, sizeof(kv->type), &offset);
|
| 6731 |
-
|
| 6732 |
-
//fprintf(stderr, "%s: reading kv with key %s\n", __func__, kv->key.data);
|
| 6733 |
-
|
| 6734 |
-
switch (kv->type) {
|
| 6735 |
-
case GGUF_TYPE_UINT8: ok = ok && gguf_fread_el (file, &kv->value.uint8, sizeof(kv->value.uint8), &offset); break;
|
| 6736 |
-
case GGUF_TYPE_INT8: ok = ok && gguf_fread_el (file, &kv->value.int8, sizeof(kv->value.int8), &offset); break;
|
| 6737 |
-
case GGUF_TYPE_UINT16: ok = ok && gguf_fread_el (file, &kv->value.uint16, sizeof(kv->value.uint16), &offset); break;
|
| 6738 |
-
case GGUF_TYPE_INT16: ok = ok && gguf_fread_el (file, &kv->value.int16, sizeof(kv->value.int16), &offset); break;
|
| 6739 |
-
case GGUF_TYPE_UINT32: ok = ok && gguf_fread_el (file, &kv->value.uint32, sizeof(kv->value.uint32), &offset); break;
|
| 6740 |
-
case GGUF_TYPE_INT32: ok = ok && gguf_fread_el (file, &kv->value.int32, sizeof(kv->value.int32), &offset); break;
|
| 6741 |
-
case GGUF_TYPE_FLOAT32: ok = ok && gguf_fread_el (file, &kv->value.float32, sizeof(kv->value.float32), &offset); break;
|
| 6742 |
-
case GGUF_TYPE_UINT64: ok = ok && gguf_fread_el (file, &kv->value.uint64, sizeof(kv->value.uint64), &offset); break;
|
| 6743 |
-
case GGUF_TYPE_INT64: ok = ok && gguf_fread_el (file, &kv->value.int64, sizeof(kv->value.int64), &offset); break;
|
| 6744 |
-
case GGUF_TYPE_FLOAT64: ok = ok && gguf_fread_el (file, &kv->value.float64, sizeof(kv->value.float64), &offset); break;
|
| 6745 |
-
case GGUF_TYPE_BOOL: ok = ok && gguf_fread_el (file, &kv->value.bool_, sizeof(kv->value.bool_), &offset); break;
|
| 6746 |
-
case GGUF_TYPE_STRING: ok = ok && gguf_fread_str(file, &kv->value.str, &offset); break;
|
| 6747 |
-
case GGUF_TYPE_ARRAY:
|
| 6748 |
-
{
|
| 6749 |
-
ok = ok && gguf_fread_el(file, &kv->value.arr.type, sizeof(kv->value.arr.type), &offset);
|
| 6750 |
-
ok = ok && gguf_fread_el(file, &kv->value.arr.n, sizeof(kv->value.arr.n), &offset);
|
| 6751 |
-
|
| 6752 |
-
switch (kv->value.arr.type) {
|
| 6753 |
-
case GGUF_TYPE_UINT8:
|
| 6754 |
-
case GGUF_TYPE_INT8:
|
| 6755 |
-
case GGUF_TYPE_UINT16:
|
| 6756 |
-
case GGUF_TYPE_INT16:
|
| 6757 |
-
case GGUF_TYPE_UINT32:
|
| 6758 |
-
case GGUF_TYPE_INT32:
|
| 6759 |
-
case GGUF_TYPE_FLOAT32:
|
| 6760 |
-
case GGUF_TYPE_UINT64:
|
| 6761 |
-
case GGUF_TYPE_INT64:
|
| 6762 |
-
case GGUF_TYPE_FLOAT64:
|
| 6763 |
-
case GGUF_TYPE_BOOL:
|
| 6764 |
-
{
|
| 6765 |
-
// prevent from integer overflow in the malloc below
|
| 6766 |
-
if (kv->value.arr.n >= SIZE_MAX/gguf_type_size(kv->value.arr.type)) {
|
| 6767 |
-
fprintf(stderr, "%s: array size is too large (%" PRIu64 ")\n", __func__, kv->value.arr.n);
|
| 6768 |
-
gguf_free(ctx);
|
| 6769 |
-
return NULL;
|
| 6770 |
-
}
|
| 6771 |
-
|
| 6772 |
-
kv->value.arr.data = calloc(kv->value.arr.n, gguf_type_size(kv->value.arr.type));
|
| 6773 |
-
if (!kv->value.arr.data) {
|
| 6774 |
-
fprintf(stderr, "%s: failed to allocate memory for array\n", __func__);
|
| 6775 |
-
gguf_free(ctx);
|
| 6776 |
-
return NULL;
|
| 6777 |
-
}
|
| 6778 |
-
|
| 6779 |
-
ok = ok && gguf_fread_el(file, kv->value.arr.data, kv->value.arr.n * gguf_type_size(kv->value.arr.type), &offset);
|
| 6780 |
-
} break;
|
| 6781 |
-
case GGUF_TYPE_STRING:
|
| 6782 |
-
{
|
| 6783 |
-
// prevent from integer overflow in the malloc below
|
| 6784 |
-
if (kv->value.arr.n >= SIZE_MAX/sizeof(struct gguf_str)) {
|
| 6785 |
-
fprintf(stderr, "%s: array size is too large (%" PRIu64 ")\n", __func__, kv->value.arr.n);
|
| 6786 |
-
gguf_free(ctx);
|
| 6787 |
-
return NULL;
|
| 6788 |
-
}
|
| 6789 |
-
|
| 6790 |
-
kv->value.arr.data = calloc(kv->value.arr.n, sizeof(struct gguf_str));
|
| 6791 |
-
if (!kv->value.arr.data) {
|
| 6792 |
-
fprintf(stderr, "%s: failed to allocate memory for array\n", __func__);
|
| 6793 |
-
gguf_free(ctx);
|
| 6794 |
-
return NULL;
|
| 6795 |
-
}
|
| 6796 |
-
|
| 6797 |
-
for (uint64_t j = 0; j < kv->value.arr.n; ++j) {
|
| 6798 |
-
ok = ok && gguf_fread_str(file, &((struct gguf_str *) kv->value.arr.data)[j], &offset);
|
| 6799 |
-
}
|
| 6800 |
-
} break;
|
| 6801 |
-
case GGUF_TYPE_ARRAY:
|
| 6802 |
-
default:
|
| 6803 |
-
{
|
| 6804 |
-
fprintf(stderr, "%s: invalid array type %d\n", __func__, kv->value.arr.type);
|
| 6805 |
-
ok = false;
|
| 6806 |
-
} break;
|
| 6807 |
-
}
|
| 6808 |
-
} break;
|
| 6809 |
-
default:
|
| 6810 |
-
{
|
| 6811 |
-
fprintf(stderr, "%s: invalid type %d\n", __func__, kv->type);
|
| 6812 |
-
ok = false;
|
| 6813 |
-
} break;
|
| 6814 |
-
}
|
| 6815 |
-
|
| 6816 |
-
if (!ok) {
|
| 6817 |
-
break;
|
| 6818 |
-
}
|
| 6819 |
-
}
|
| 6820 |
-
|
| 6821 |
-
if (!ok) {
|
| 6822 |
-
fprintf(stderr, "%s: failed to read key-value pairs\n", __func__);
|
| 6823 |
-
gguf_free(ctx);
|
| 6824 |
-
return NULL;
|
| 6825 |
-
}
|
| 6826 |
-
}
|
| 6827 |
-
|
| 6828 |
-
// read the tensor infos
|
| 6829 |
-
if (ctx->header.n_tensors > 0) {
|
| 6830 |
-
ctx->infos = calloc(ctx->header.n_tensors, sizeof(struct gguf_tensor_info));
|
| 6831 |
-
if (!ctx->infos) {
|
| 6832 |
-
fprintf(stderr, "%s: failed to allocate memory for tensor infos\n", __func__);
|
| 6833 |
-
gguf_free(ctx);
|
| 6834 |
-
return NULL;
|
| 6835 |
-
}
|
| 6836 |
-
|
| 6837 |
-
for (uint64_t i = 0; i < ctx->header.n_tensors; ++i) {
|
| 6838 |
-
struct gguf_tensor_info * info = &ctx->infos[i];
|
| 6839 |
-
|
| 6840 |
-
for (int j = 0; j < GGML_MAX_DIMS; ++j) {
|
| 6841 |
-
info->ne[j] = 1;
|
| 6842 |
-
}
|
| 6843 |
-
|
| 6844 |
-
ok = ok && gguf_fread_str(file, &info->name, &offset);
|
| 6845 |
-
ok = ok && gguf_fread_el (file, &info->n_dims, sizeof(info->n_dims), &offset);
|
| 6846 |
-
|
| 6847 |
-
ok = ok && (info->n_dims <= GGML_MAX_DIMS);
|
| 6848 |
-
|
| 6849 |
-
for (uint32_t j = 0; j < info->n_dims; ++j) {
|
| 6850 |
-
ok = ok && gguf_fread_el(file, &info->ne[j], sizeof(info->ne[j]), &offset);
|
| 6851 |
-
}
|
| 6852 |
-
|
| 6853 |
-
ok = ok && gguf_fread_el (file, &info->type, sizeof(info->type), &offset);
|
| 6854 |
-
ok = ok && gguf_fread_el (file, &info->offset, sizeof(info->offset), &offset);
|
| 6855 |
-
|
| 6856 |
-
ok = ok && gguf_tensor_info_sanitize(info);
|
| 6857 |
-
|
| 6858 |
-
// make sure there is no duplicated tensor names
|
| 6859 |
-
for (uint64_t j = 0; j < i && ok; ++j) {
|
| 6860 |
-
if (strcmp(info->name.data, ctx->infos[j].name.data) == 0) {
|
| 6861 |
-
fprintf(stderr, "%s: duplicated tensor name %s\n", __func__, info->name.data);
|
| 6862 |
-
ok = false;
|
| 6863 |
-
}
|
| 6864 |
-
}
|
| 6865 |
-
|
| 6866 |
-
if (!ok) {
|
| 6867 |
-
fprintf(stderr, "%s: failed to read tensor info\n", __func__);
|
| 6868 |
-
gguf_free(ctx);
|
| 6869 |
-
return NULL;
|
| 6870 |
-
}
|
| 6871 |
-
}
|
| 6872 |
-
}
|
| 6873 |
-
|
| 6874 |
-
ctx->alignment = GGUF_DEFAULT_ALIGNMENT;
|
| 6875 |
-
|
| 6876 |
-
int alignment_idx = gguf_find_key(ctx, "general.alignment");
|
| 6877 |
-
if (alignment_idx != -1) {
|
| 6878 |
-
ctx->alignment = gguf_get_val_u32(ctx, alignment_idx);
|
| 6879 |
-
}
|
| 6880 |
-
|
| 6881 |
-
// we require the data section to be aligned, so take into account any padding
|
| 6882 |
-
{
|
| 6883 |
-
const size_t offset_pad = offset % ctx->alignment;
|
| 6884 |
-
|
| 6885 |
-
if (offset_pad != 0) {
|
| 6886 |
-
offset += ctx->alignment - offset_pad;
|
| 6887 |
-
fseek(file, offset, SEEK_SET);
|
| 6888 |
-
}
|
| 6889 |
-
}
|
| 6890 |
-
|
| 6891 |
-
// store the current file offset - this is where the data section starts
|
| 6892 |
-
ctx->offset = offset;
|
| 6893 |
-
|
| 6894 |
-
// compute the total size of the data section, taking into account the alignment
|
| 6895 |
-
{
|
| 6896 |
-
ctx->size = 0;
|
| 6897 |
-
for (uint64_t i = 0; i < ctx->header.n_tensors; ++i) {
|
| 6898 |
-
struct gguf_tensor_info * info = &ctx->infos[i];
|
| 6899 |
-
|
| 6900 |
-
const int64_t ne =
|
| 6901 |
-
(int64_t) info->ne[0] *
|
| 6902 |
-
(int64_t) info->ne[1] *
|
| 6903 |
-
(int64_t) info->ne[2] *
|
| 6904 |
-
(int64_t) info->ne[3];
|
| 6905 |
-
|
| 6906 |
-
if (ggml_blck_size(info->type) == 0 ) {
|
| 6907 |
-
// this tensor type support have been removed:
|
| 6908 |
-
fprintf(stderr, "%s: tensor '%s' of type %d: %s\n",
|
| 6909 |
-
__func__, info->name.data, (int) info->type, ggml_type_name(info->type));
|
| 6910 |
-
gguf_free(ctx);
|
| 6911 |
-
return NULL;
|
| 6912 |
-
}
|
| 6913 |
-
|
| 6914 |
-
if (ne % ggml_blck_size(info->type) != 0) {
|
| 6915 |
-
fprintf(stderr, "%s: tensor '%s' of type %d (%s) number of elements (%" PRId64 ") is not a multiple of block size (%" PRId64 ")\n",
|
| 6916 |
-
__func__, info->name.data, (int) info->type, ggml_type_name(info->type), ne, ggml_blck_size(info->type));
|
| 6917 |
-
gguf_free(ctx);
|
| 6918 |
-
return NULL;
|
| 6919 |
-
}
|
| 6920 |
-
|
| 6921 |
-
const size_t size_cur = ggml_row_size(info->type, ne);
|
| 6922 |
-
|
| 6923 |
-
ctx->size += GGML_PAD(size_cur, ctx->alignment);
|
| 6924 |
-
}
|
| 6925 |
-
}
|
| 6926 |
-
|
| 6927 |
-
// load the tensor data only if requested
|
| 6928 |
-
if (params.ctx != NULL) {
|
| 6929 |
-
// if the provided gguf_context is no_alloc, then we create "empty" tensors and do not read the binary blob
|
| 6930 |
-
// otherwise, we load the binary blob into the created ggml_context as well, and point the "data" members of
|
| 6931 |
-
// the ggml_tensor structs to the appropriate locations in the binary blob
|
| 6932 |
-
|
| 6933 |
-
// compute the exact size needed for the new ggml_context
|
| 6934 |
-
const size_t mem_size =
|
| 6935 |
-
params.no_alloc ?
|
| 6936 |
-
(ctx->header.n_tensors )*ggml_tensor_overhead() :
|
| 6937 |
-
(ctx->header.n_tensors + 1)*ggml_tensor_overhead() + ctx->size;
|
| 6938 |
-
|
| 6939 |
-
struct ggml_init_params pdata = {
|
| 6940 |
-
.mem_size = mem_size,
|
| 6941 |
-
.mem_buffer = NULL,
|
| 6942 |
-
.no_alloc = params.no_alloc,
|
| 6943 |
-
};
|
| 6944 |
-
|
| 6945 |
-
*params.ctx = ggml_init(pdata);
|
| 6946 |
-
if (*params.ctx == NULL) {
|
| 6947 |
-
fprintf(stderr, "%s: failed to initialize context\n", __func__);
|
| 6948 |
-
gguf_free(ctx);
|
| 6949 |
-
return NULL;
|
| 6950 |
-
}
|
| 6951 |
-
|
| 6952 |
-
struct ggml_context * ctx_data = *params.ctx;
|
| 6953 |
-
|
| 6954 |
-
struct ggml_tensor * data = NULL;
|
| 6955 |
-
|
| 6956 |
-
if (!params.no_alloc) {
|
| 6957 |
-
data = ggml_new_tensor_1d(ctx_data, GGML_TYPE_I8, ctx->size);
|
| 6958 |
-
|
| 6959 |
-
ok = ok && data != NULL;
|
| 6960 |
-
|
| 6961 |
-
// read the binary blob with the tensor data
|
| 6962 |
-
ok = ok && gguf_fread_el(file, data->data, ctx->size, &offset);
|
| 6963 |
-
|
| 6964 |
-
if (!ok) {
|
| 6965 |
-
fprintf(stderr, "%s: failed to read tensor data\n", __func__);
|
| 6966 |
-
ggml_free(ctx_data);
|
| 6967 |
-
gguf_free(ctx);
|
| 6968 |
-
return NULL;
|
| 6969 |
-
}
|
| 6970 |
-
|
| 6971 |
-
ctx->data = data->data;
|
| 6972 |
-
}
|
| 6973 |
-
|
| 6974 |
-
ggml_set_no_alloc(ctx_data, true);
|
| 6975 |
-
|
| 6976 |
-
// create the tensors
|
| 6977 |
-
for (uint64_t i = 0; i < ctx->header.n_tensors; ++i) {
|
| 6978 |
-
const int64_t ne[GGML_MAX_DIMS] = {
|
| 6979 |
-
ctx->infos[i].ne[0],
|
| 6980 |
-
ctx->infos[i].ne[1],
|
| 6981 |
-
ctx->infos[i].ne[2],
|
| 6982 |
-
ctx->infos[i].ne[3],
|
| 6983 |
-
};
|
| 6984 |
-
|
| 6985 |
-
struct ggml_tensor * cur = ggml_new_tensor(ctx_data, ctx->infos[i].type, ctx->infos[i].n_dims, ne);
|
| 6986 |
-
|
| 6987 |
-
ok = ok && cur != NULL;
|
| 6988 |
-
|
| 6989 |
-
if (!ok) {
|
| 6990 |
-
break;
|
| 6991 |
-
}
|
| 6992 |
-
|
| 6993 |
-
ggml_set_name(cur, ctx->infos[i].name.data);
|
| 6994 |
-
|
| 6995 |
-
// point the data member to the appropriate location in the binary blob using the tensor infos
|
| 6996 |
-
if (!params.no_alloc) {
|
| 6997 |
-
//cur->data = (char *) data->data + ctx->infos[i].offset - ctx->offset; // offset from start of file
|
| 6998 |
-
cur->data = (char *) data->data + ctx->infos[i].offset; // offset from data
|
| 6999 |
-
}
|
| 7000 |
-
}
|
| 7001 |
-
|
| 7002 |
-
if (!ok) {
|
| 7003 |
-
fprintf(stderr, "%s: failed to read the tensor data\n", __func__);
|
| 7004 |
-
ggml_free(ctx_data);
|
| 7005 |
-
gguf_free(ctx);
|
| 7006 |
-
return NULL;
|
| 7007 |
-
}
|
| 7008 |
-
|
| 7009 |
-
ggml_set_no_alloc(ctx_data, params.no_alloc);
|
| 7010 |
-
}
|
| 7011 |
-
|
| 7012 |
-
return ctx;
|
| 7013 |
-
}
|
| 7014 |
-
|
| 7015 |
-
struct gguf_context * gguf_init_from_file(const char * fname, struct gguf_init_params params) {
|
| 7016 |
-
FILE * file = ggml_fopen(fname, "rb");
|
| 7017 |
-
if (!file) {
|
| 7018 |
-
fprintf(stderr, "%s: failed to open '%s': '%s'\n", __func__, fname, strerror(errno));
|
| 7019 |
-
return NULL;
|
| 7020 |
-
}
|
| 7021 |
-
|
| 7022 |
-
struct gguf_context * result = gguf_init_from_file_impl(file, params);
|
| 7023 |
-
fclose(file);
|
| 7024 |
-
return result;
|
| 7025 |
-
}
|
| 7026 |
-
|
| 7027 |
-
void gguf_free(struct gguf_context * ctx) {
|
| 7028 |
-
if (ctx == NULL) {
|
| 7029 |
-
return;
|
| 7030 |
-
}
|
| 7031 |
-
|
| 7032 |
-
if (ctx->kv) {
|
| 7033 |
-
// free string memory - not great..
|
| 7034 |
-
for (uint64_t i = 0; i < ctx->header.n_kv; ++i) {
|
| 7035 |
-
gguf_free_kv(&ctx->kv[i]);
|
| 7036 |
-
}
|
| 7037 |
-
|
| 7038 |
-
GGML_FREE(ctx->kv);
|
| 7039 |
-
}
|
| 7040 |
-
|
| 7041 |
-
if (ctx->infos) {
|
| 7042 |
-
for (uint64_t i = 0; i < ctx->header.n_tensors; ++i) {
|
| 7043 |
-
struct gguf_tensor_info * info = &ctx->infos[i];
|
| 7044 |
-
|
| 7045 |
-
if (info->name.data) {
|
| 7046 |
-
GGML_FREE(info->name.data);
|
| 7047 |
-
}
|
| 7048 |
-
}
|
| 7049 |
-
|
| 7050 |
-
GGML_FREE(ctx->infos);
|
| 7051 |
-
}
|
| 7052 |
-
|
| 7053 |
-
GGML_FREE(ctx);
|
| 7054 |
-
}
|
| 7055 |
-
|
| 7056 |
-
const char * gguf_type_name(enum gguf_type type) {
|
| 7057 |
-
return GGUF_TYPE_NAME[type];
|
| 7058 |
-
}
|
| 7059 |
-
|
| 7060 |
-
int gguf_get_version(const struct gguf_context * ctx) {
|
| 7061 |
-
return ctx->header.version;
|
| 7062 |
-
}
|
| 7063 |
-
|
| 7064 |
-
size_t gguf_get_alignment(const struct gguf_context * ctx) {
|
| 7065 |
-
return ctx->alignment;
|
| 7066 |
-
}
|
| 7067 |
-
|
| 7068 |
-
size_t gguf_get_data_offset(const struct gguf_context * ctx) {
|
| 7069 |
-
return ctx->offset;
|
| 7070 |
-
}
|
| 7071 |
-
|
| 7072 |
-
void * gguf_get_data(const struct gguf_context * ctx) {
|
| 7073 |
-
return ctx->data;
|
| 7074 |
-
}
|
| 7075 |
-
|
| 7076 |
-
int gguf_get_n_kv(const struct gguf_context * ctx) {
|
| 7077 |
-
return ctx->header.n_kv;
|
| 7078 |
-
}
|
| 7079 |
-
|
| 7080 |
-
int gguf_find_key(const struct gguf_context * ctx, const char * key) {
|
| 7081 |
-
// return -1 if key not found
|
| 7082 |
-
int keyfound = -1;
|
| 7083 |
-
|
| 7084 |
-
const int n_kv = gguf_get_n_kv(ctx);
|
| 7085 |
-
|
| 7086 |
-
for (int i = 0; i < n_kv; ++i) {
|
| 7087 |
-
if (strcmp(key, gguf_get_key(ctx, i)) == 0) {
|
| 7088 |
-
keyfound = i;
|
| 7089 |
-
break;
|
| 7090 |
-
}
|
| 7091 |
-
}
|
| 7092 |
-
|
| 7093 |
-
return keyfound;
|
| 7094 |
-
}
|
| 7095 |
-
|
| 7096 |
-
const char * gguf_get_key(const struct gguf_context * ctx, int key_id) {
|
| 7097 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7098 |
-
return ctx->kv[key_id].key.data;
|
| 7099 |
-
}
|
| 7100 |
-
|
| 7101 |
-
enum gguf_type gguf_get_kv_type(const struct gguf_context * ctx, int key_id) {
|
| 7102 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7103 |
-
return ctx->kv[key_id].type;
|
| 7104 |
-
}
|
| 7105 |
-
|
| 7106 |
-
enum gguf_type gguf_get_arr_type(const struct gguf_context * ctx, int key_id) {
|
| 7107 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7108 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_ARRAY);
|
| 7109 |
-
return ctx->kv[key_id].value.arr.type;
|
| 7110 |
-
}
|
| 7111 |
-
|
| 7112 |
-
const void * gguf_get_arr_data(const struct gguf_context * ctx, int key_id) {
|
| 7113 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7114 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_ARRAY);
|
| 7115 |
-
return ctx->kv[key_id].value.arr.data;
|
| 7116 |
-
}
|
| 7117 |
-
|
| 7118 |
-
const char * gguf_get_arr_str(const struct gguf_context * ctx, int key_id, int i) {
|
| 7119 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7120 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_ARRAY);
|
| 7121 |
-
struct gguf_kv * kv = &ctx->kv[key_id];
|
| 7122 |
-
struct gguf_str * str = &((struct gguf_str *) kv->value.arr.data)[i];
|
| 7123 |
-
return str->data;
|
| 7124 |
-
}
|
| 7125 |
-
|
| 7126 |
-
int gguf_get_arr_n(const struct gguf_context * ctx, int key_id) {
|
| 7127 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7128 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_ARRAY);
|
| 7129 |
-
return ctx->kv[key_id].value.arr.n;
|
| 7130 |
-
}
|
| 7131 |
-
|
| 7132 |
-
uint8_t gguf_get_val_u8(const struct gguf_context * ctx, int key_id) {
|
| 7133 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7134 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_UINT8);
|
| 7135 |
-
return ctx->kv[key_id].value.uint8;
|
| 7136 |
-
}
|
| 7137 |
-
|
| 7138 |
-
int8_t gguf_get_val_i8(const struct gguf_context * ctx, int key_id) {
|
| 7139 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7140 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_INT8);
|
| 7141 |
-
return ctx->kv[key_id].value.int8;
|
| 7142 |
-
}
|
| 7143 |
-
|
| 7144 |
-
uint16_t gguf_get_val_u16(const struct gguf_context * ctx, int key_id) {
|
| 7145 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7146 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_UINT16);
|
| 7147 |
-
return ctx->kv[key_id].value.uint16;
|
| 7148 |
-
}
|
| 7149 |
-
|
| 7150 |
-
int16_t gguf_get_val_i16(const struct gguf_context * ctx, int key_id) {
|
| 7151 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7152 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_INT16);
|
| 7153 |
-
return ctx->kv[key_id].value.int16;
|
| 7154 |
-
}
|
| 7155 |
-
|
| 7156 |
-
uint32_t gguf_get_val_u32(const struct gguf_context * ctx, int key_id) {
|
| 7157 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7158 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_UINT32);
|
| 7159 |
-
return ctx->kv[key_id].value.uint32;
|
| 7160 |
-
}
|
| 7161 |
-
|
| 7162 |
-
int32_t gguf_get_val_i32(const struct gguf_context * ctx, int key_id) {
|
| 7163 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7164 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_INT32);
|
| 7165 |
-
return ctx->kv[key_id].value.int32;
|
| 7166 |
-
}
|
| 7167 |
-
|
| 7168 |
-
float gguf_get_val_f32(const struct gguf_context * ctx, int key_id) {
|
| 7169 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7170 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_FLOAT32);
|
| 7171 |
-
return ctx->kv[key_id].value.float32;
|
| 7172 |
-
}
|
| 7173 |
-
|
| 7174 |
-
uint64_t gguf_get_val_u64(const struct gguf_context * ctx, int key_id) {
|
| 7175 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7176 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_UINT64);
|
| 7177 |
-
return ctx->kv[key_id].value.uint64;
|
| 7178 |
-
}
|
| 7179 |
-
|
| 7180 |
-
int64_t gguf_get_val_i64(const struct gguf_context * ctx, int key_id) {
|
| 7181 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7182 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_INT64);
|
| 7183 |
-
return ctx->kv[key_id].value.int64;
|
| 7184 |
-
}
|
| 7185 |
-
|
| 7186 |
-
double gguf_get_val_f64(const struct gguf_context * ctx, int key_id) {
|
| 7187 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7188 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_FLOAT64);
|
| 7189 |
-
return ctx->kv[key_id].value.float64;
|
| 7190 |
-
}
|
| 7191 |
-
|
| 7192 |
-
bool gguf_get_val_bool(const struct gguf_context * ctx, int key_id) {
|
| 7193 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7194 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_BOOL);
|
| 7195 |
-
return ctx->kv[key_id].value.bool_;
|
| 7196 |
-
}
|
| 7197 |
-
|
| 7198 |
-
const char * gguf_get_val_str(const struct gguf_context * ctx, int key_id) {
|
| 7199 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7200 |
-
GGML_ASSERT(ctx->kv[key_id].type == GGUF_TYPE_STRING);
|
| 7201 |
-
return ctx->kv[key_id].value.str.data;
|
| 7202 |
-
}
|
| 7203 |
-
|
| 7204 |
-
const void * gguf_get_val_data(const struct gguf_context * ctx, int key_id) {
|
| 7205 |
-
GGML_ASSERT(key_id >= 0 && key_id < gguf_get_n_kv(ctx));
|
| 7206 |
-
GGML_ASSERT(ctx->kv[key_id].type != GGUF_TYPE_ARRAY);
|
| 7207 |
-
GGML_ASSERT(ctx->kv[key_id].type != GGUF_TYPE_STRING);
|
| 7208 |
-
return &ctx->kv[key_id].value;
|
| 7209 |
-
}
|
| 7210 |
-
|
| 7211 |
-
int gguf_get_n_tensors(const struct gguf_context * ctx) {
|
| 7212 |
-
return ctx->header.n_tensors;
|
| 7213 |
-
}
|
| 7214 |
-
|
| 7215 |
-
int gguf_find_tensor(const struct gguf_context * ctx, const char * name) {
|
| 7216 |
-
// return -1 if tensor not found
|
| 7217 |
-
int tensorfound = -1;
|
| 7218 |
-
|
| 7219 |
-
const int n_tensors = gguf_get_n_tensors(ctx);
|
| 7220 |
-
|
| 7221 |
-
for (int i = 0; i < n_tensors; ++i) {
|
| 7222 |
-
if (strcmp(name, gguf_get_tensor_name(ctx, i)) == 0) {
|
| 7223 |
-
tensorfound = i;
|
| 7224 |
-
break;
|
| 7225 |
-
}
|
| 7226 |
-
}
|
| 7227 |
-
|
| 7228 |
-
return tensorfound;
|
| 7229 |
-
}
|
| 7230 |
-
|
| 7231 |
-
size_t gguf_get_tensor_offset(const struct gguf_context * ctx, int i) {
|
| 7232 |
-
return ctx->infos[i].offset;
|
| 7233 |
-
}
|
| 7234 |
-
|
| 7235 |
-
char * gguf_get_tensor_name(const struct gguf_context * ctx, int i) {
|
| 7236 |
-
return ctx->infos[i].name.data;
|
| 7237 |
-
}
|
| 7238 |
-
|
| 7239 |
-
enum ggml_type gguf_get_tensor_type(const struct gguf_context * ctx, int i) {
|
| 7240 |
-
return ctx->infos[i].type;
|
| 7241 |
-
}
|
| 7242 |
-
|
| 7243 |
-
// returns the index
|
| 7244 |
-
static int gguf_get_or_add_key(struct gguf_context * ctx, const char * key) {
|
| 7245 |
-
const int idx = gguf_find_key(ctx, key);
|
| 7246 |
-
if (idx >= 0) {
|
| 7247 |
-
return idx;
|
| 7248 |
-
}
|
| 7249 |
-
|
| 7250 |
-
const int n_kv = gguf_get_n_kv(ctx);
|
| 7251 |
-
|
| 7252 |
-
ctx->kv = realloc(ctx->kv, (n_kv + 1) * sizeof(struct gguf_kv));
|
| 7253 |
-
ctx->kv[n_kv].key.n = strlen(key);
|
| 7254 |
-
ctx->kv[n_kv].key.data = strdup(key);
|
| 7255 |
-
ctx->header.n_kv++;
|
| 7256 |
-
|
| 7257 |
-
return n_kv;
|
| 7258 |
-
}
|
| 7259 |
-
|
| 7260 |
-
void gguf_remove_key(struct gguf_context * ctx, const char * key) {
|
| 7261 |
-
const int idx = gguf_find_key(ctx, key);
|
| 7262 |
-
if (idx >= 0) {
|
| 7263 |
-
const int n_kv = gguf_get_n_kv(ctx);
|
| 7264 |
-
gguf_free_kv(&ctx->kv[idx]);
|
| 7265 |
-
for (int i = idx; i < n_kv-1; ++i) {
|
| 7266 |
-
ctx->kv[i] = ctx->kv[i+1];
|
| 7267 |
-
}
|
| 7268 |
-
ctx->kv = realloc(ctx->kv, (n_kv - 1) * sizeof(struct gguf_kv));
|
| 7269 |
-
ctx->header.n_kv--;
|
| 7270 |
-
}
|
| 7271 |
-
}
|
| 7272 |
-
|
| 7273 |
-
void gguf_set_val_u8(struct gguf_context * ctx, const char * key, uint8_t val) {
|
| 7274 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7275 |
-
|
| 7276 |
-
ctx->kv[idx].type = GGUF_TYPE_UINT8;
|
| 7277 |
-
ctx->kv[idx].value.uint8 = val;
|
| 7278 |
-
}
|
| 7279 |
-
|
| 7280 |
-
void gguf_set_val_i8(struct gguf_context * ctx, const char * key, int8_t val) {
|
| 7281 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7282 |
-
|
| 7283 |
-
ctx->kv[idx].type = GGUF_TYPE_INT8;
|
| 7284 |
-
ctx->kv[idx].value.int8 = val;
|
| 7285 |
-
}
|
| 7286 |
-
|
| 7287 |
-
void gguf_set_val_u16(struct gguf_context * ctx, const char * key, uint16_t val) {
|
| 7288 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7289 |
-
|
| 7290 |
-
ctx->kv[idx].type = GGUF_TYPE_UINT16;
|
| 7291 |
-
ctx->kv[idx].value.uint16 = val;
|
| 7292 |
-
}
|
| 7293 |
-
|
| 7294 |
-
void gguf_set_val_i16(struct gguf_context * ctx, const char * key, int16_t val) {
|
| 7295 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7296 |
-
|
| 7297 |
-
ctx->kv[idx].type = GGUF_TYPE_INT16;
|
| 7298 |
-
ctx->kv[idx].value.int16 = val;
|
| 7299 |
-
}
|
| 7300 |
-
|
| 7301 |
-
void gguf_set_val_u32(struct gguf_context * ctx, const char * key, uint32_t val) {
|
| 7302 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7303 |
-
|
| 7304 |
-
ctx->kv[idx].type = GGUF_TYPE_UINT32;
|
| 7305 |
-
ctx->kv[idx].value.uint32 = val;
|
| 7306 |
-
}
|
| 7307 |
-
|
| 7308 |
-
void gguf_set_val_i32(struct gguf_context * ctx, const char * key, int32_t val) {
|
| 7309 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7310 |
-
|
| 7311 |
-
ctx->kv[idx].type = GGUF_TYPE_INT32;
|
| 7312 |
-
ctx->kv[idx].value.int32 = val;
|
| 7313 |
-
}
|
| 7314 |
-
|
| 7315 |
-
void gguf_set_val_f32(struct gguf_context * ctx, const char * key, float val) {
|
| 7316 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7317 |
-
|
| 7318 |
-
ctx->kv[idx].type = GGUF_TYPE_FLOAT32;
|
| 7319 |
-
ctx->kv[idx].value.float32 = val;
|
| 7320 |
-
}
|
| 7321 |
-
|
| 7322 |
-
void gguf_set_val_u64(struct gguf_context * ctx, const char * key, uint64_t val) {
|
| 7323 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7324 |
-
|
| 7325 |
-
ctx->kv[idx].type = GGUF_TYPE_UINT64;
|
| 7326 |
-
ctx->kv[idx].value.uint64 = val;
|
| 7327 |
-
}
|
| 7328 |
-
|
| 7329 |
-
void gguf_set_val_i64(struct gguf_context * ctx, const char * key, int64_t val) {
|
| 7330 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7331 |
-
|
| 7332 |
-
ctx->kv[idx].type = GGUF_TYPE_INT64;
|
| 7333 |
-
ctx->kv[idx].value.int64 = val;
|
| 7334 |
-
}
|
| 7335 |
-
|
| 7336 |
-
void gguf_set_val_f64(struct gguf_context * ctx, const char * key, double val) {
|
| 7337 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7338 |
-
|
| 7339 |
-
ctx->kv[idx].type = GGUF_TYPE_FLOAT64;
|
| 7340 |
-
ctx->kv[idx].value.float64 = val;
|
| 7341 |
-
}
|
| 7342 |
-
|
| 7343 |
-
void gguf_set_val_bool(struct gguf_context * ctx, const char * key, bool val) {
|
| 7344 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7345 |
-
|
| 7346 |
-
ctx->kv[idx].type = GGUF_TYPE_BOOL;
|
| 7347 |
-
ctx->kv[idx].value.bool_ = val;
|
| 7348 |
-
}
|
| 7349 |
-
|
| 7350 |
-
void gguf_set_val_str(struct gguf_context * ctx, const char * key, const char * val) {
|
| 7351 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7352 |
-
|
| 7353 |
-
ctx->kv[idx].type = GGUF_TYPE_STRING;
|
| 7354 |
-
ctx->kv[idx].value.str.n = strlen(val);
|
| 7355 |
-
ctx->kv[idx].value.str.data = strdup(val);
|
| 7356 |
-
}
|
| 7357 |
-
|
| 7358 |
-
void gguf_set_arr_data(struct gguf_context * ctx, const char * key, enum gguf_type type, const void * data, int n) {
|
| 7359 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7360 |
-
|
| 7361 |
-
ctx->kv[idx].type = GGUF_TYPE_ARRAY;
|
| 7362 |
-
ctx->kv[idx].value.arr.type = type;
|
| 7363 |
-
ctx->kv[idx].value.arr.n = n;
|
| 7364 |
-
ctx->kv[idx].value.arr.data = GGML_CALLOC(n, gguf_type_size(type));
|
| 7365 |
-
memcpy(ctx->kv[idx].value.arr.data, data, n*gguf_type_size(type));
|
| 7366 |
-
}
|
| 7367 |
-
|
| 7368 |
-
void gguf_set_arr_str(struct gguf_context * ctx, const char * key, const char ** data, int n) {
|
| 7369 |
-
const int idx = gguf_get_or_add_key(ctx, key);
|
| 7370 |
-
|
| 7371 |
-
ctx->kv[idx].type = GGUF_TYPE_ARRAY;
|
| 7372 |
-
ctx->kv[idx].value.arr.type = GGUF_TYPE_STRING;
|
| 7373 |
-
ctx->kv[idx].value.arr.n = n;
|
| 7374 |
-
ctx->kv[idx].value.arr.data = GGML_CALLOC(n, sizeof(struct gguf_str));
|
| 7375 |
-
for (int i = 0; i < n; i++) {
|
| 7376 |
-
struct gguf_str * str = &((struct gguf_str *)ctx->kv[idx].value.arr.data)[i];
|
| 7377 |
-
str->n = strlen(data[i]);
|
| 7378 |
-
str->data = strdup(data[i]);
|
| 7379 |
-
}
|
| 7380 |
-
}
|
| 7381 |
-
|
| 7382 |
-
// set or add KV pairs from another context
|
| 7383 |
-
void gguf_set_kv(struct gguf_context * ctx, struct gguf_context * src) {
|
| 7384 |
-
for (uint32_t i = 0; i < src->header.n_kv; i++) {
|
| 7385 |
-
switch (src->kv[i].type) {
|
| 7386 |
-
case GGUF_TYPE_UINT8: gguf_set_val_u8 (ctx, src->kv[i].key.data, src->kv[i].value.uint8); break;
|
| 7387 |
-
case GGUF_TYPE_INT8: gguf_set_val_i8 (ctx, src->kv[i].key.data, src->kv[i].value.int8); break;
|
| 7388 |
-
case GGUF_TYPE_UINT16: gguf_set_val_u16 (ctx, src->kv[i].key.data, src->kv[i].value.uint16); break;
|
| 7389 |
-
case GGUF_TYPE_INT16: gguf_set_val_i16 (ctx, src->kv[i].key.data, src->kv[i].value.int16); break;
|
| 7390 |
-
case GGUF_TYPE_UINT32: gguf_set_val_u32 (ctx, src->kv[i].key.data, src->kv[i].value.uint32); break;
|
| 7391 |
-
case GGUF_TYPE_INT32: gguf_set_val_i32 (ctx, src->kv[i].key.data, src->kv[i].value.int32); break;
|
| 7392 |
-
case GGUF_TYPE_FLOAT32: gguf_set_val_f32 (ctx, src->kv[i].key.data, src->kv[i].value.float32); break;
|
| 7393 |
-
case GGUF_TYPE_UINT64: gguf_set_val_u64 (ctx, src->kv[i].key.data, src->kv[i].value.uint64); break;
|
| 7394 |
-
case GGUF_TYPE_INT64: gguf_set_val_i64 (ctx, src->kv[i].key.data, src->kv[i].value.int64); break;
|
| 7395 |
-
case GGUF_TYPE_FLOAT64: gguf_set_val_f64 (ctx, src->kv[i].key.data, src->kv[i].value.float64); break;
|
| 7396 |
-
case GGUF_TYPE_BOOL: gguf_set_val_bool(ctx, src->kv[i].key.data, src->kv[i].value.bool_); break;
|
| 7397 |
-
case GGUF_TYPE_STRING: gguf_set_val_str (ctx, src->kv[i].key.data, src->kv[i].value.str.data); break;
|
| 7398 |
-
case GGUF_TYPE_ARRAY:
|
| 7399 |
-
{
|
| 7400 |
-
if (src->kv[i].value.arr.type == GGUF_TYPE_STRING) {
|
| 7401 |
-
const char ** data = GGML_CALLOC(src->kv[i].value.arr.n, sizeof(char *));
|
| 7402 |
-
for (uint32_t j = 0; j < src->kv[i].value.arr.n; j++) {
|
| 7403 |
-
data[j] = ((struct gguf_str *)src->kv[i].value.arr.data)[j].data;
|
| 7404 |
-
}
|
| 7405 |
-
gguf_set_arr_str(ctx, src->kv[i].key.data, data, src->kv[i].value.arr.n);
|
| 7406 |
-
GGML_FREE((void *)data);
|
| 7407 |
-
} else if (src->kv[i].value.arr.type == GGUF_TYPE_ARRAY) {
|
| 7408 |
-
GGML_ABORT("nested arrays not supported");
|
| 7409 |
-
} else {
|
| 7410 |
-
gguf_set_arr_data(ctx, src->kv[i].key.data, src->kv[i].value.arr.type, src->kv[i].value.arr.data, src->kv[i].value.arr.n);
|
| 7411 |
-
}
|
| 7412 |
-
} break;
|
| 7413 |
-
default: GGML_ABORT("invalid type");
|
| 7414 |
-
}
|
| 7415 |
-
}
|
| 7416 |
-
}
|
| 7417 |
-
|
| 7418 |
-
void gguf_add_tensor(
|
| 7419 |
-
struct gguf_context * ctx,
|
| 7420 |
-
const struct ggml_tensor * tensor) {
|
| 7421 |
-
GGML_ASSERT(tensor);
|
| 7422 |
-
if (gguf_find_tensor(ctx, tensor->name) != -1) {
|
| 7423 |
-
GGML_ABORT("duplicated tensor name");
|
| 7424 |
-
}
|
| 7425 |
-
|
| 7426 |
-
const int idx = ctx->header.n_tensors;
|
| 7427 |
-
ctx->infos = realloc(ctx->infos, (idx + 1)*sizeof(struct gguf_tensor_info));
|
| 7428 |
-
|
| 7429 |
-
ctx->infos[idx].name.n = strlen(tensor->name);
|
| 7430 |
-
ctx->infos[idx].name.data = strdup(tensor->name);
|
| 7431 |
-
|
| 7432 |
-
for (int i = 0; i < GGML_MAX_DIMS; ++i) {
|
| 7433 |
-
ctx->infos[idx].ne[i] = 1;
|
| 7434 |
-
}
|
| 7435 |
-
|
| 7436 |
-
ctx->infos[idx].n_dims = ggml_n_dims(tensor);
|
| 7437 |
-
for (uint32_t i = 0; i < ctx->infos[idx].n_dims; i++) {
|
| 7438 |
-
ctx->infos[idx].ne[i] = tensor->ne[i];
|
| 7439 |
-
}
|
| 7440 |
-
|
| 7441 |
-
ctx->infos[idx].type = tensor->type;
|
| 7442 |
-
ctx->infos[idx].offset = 0;
|
| 7443 |
-
ctx->infos[idx].data = tensor->data;
|
| 7444 |
-
ctx->infos[idx].size = ggml_nbytes(tensor);
|
| 7445 |
-
|
| 7446 |
-
if (ctx->header.n_tensors > 0) {
|
| 7447 |
-
ctx->infos[idx].offset = ctx->infos[idx - 1].offset + GGML_PAD(ctx->infos[idx - 1].size, ctx->alignment);
|
| 7448 |
-
}
|
| 7449 |
-
|
| 7450 |
-
ctx->header.n_tensors++;
|
| 7451 |
-
}
|
| 7452 |
-
|
| 7453 |
-
void gguf_set_tensor_type(struct gguf_context * ctx, const char * name, enum ggml_type type) {
|
| 7454 |
-
const int idx = gguf_find_tensor(ctx, name);
|
| 7455 |
-
if (idx < 0) {
|
| 7456 |
-
GGML_ABORT("tensor not found");
|
| 7457 |
-
}
|
| 7458 |
-
|
| 7459 |
-
ctx->infos[idx].type = type;
|
| 7460 |
-
}
|
| 7461 |
-
|
| 7462 |
-
void gguf_set_tensor_data(struct gguf_context * ctx, const char * name, const void * data, size_t size) {
|
| 7463 |
-
const int idx = gguf_find_tensor(ctx, name);
|
| 7464 |
-
if (idx < 0) {
|
| 7465 |
-
GGML_ABORT("tensor not found");
|
| 7466 |
-
}
|
| 7467 |
-
|
| 7468 |
-
ctx->infos[idx].data = data;
|
| 7469 |
-
ctx->infos[idx].size = size;
|
| 7470 |
-
|
| 7471 |
-
// update offsets
|
| 7472 |
-
for (uint32_t i = idx + 1; i < ctx->header.n_tensors; ++i) {
|
| 7473 |
-
ctx->infos[i].offset = ctx->infos[i - 1].offset + GGML_PAD(ctx->infos[i - 1].size, ctx->alignment);
|
| 7474 |
-
}
|
| 7475 |
-
}
|
| 7476 |
-
|
| 7477 |
-
//static void gguf_fwrite_str(FILE * file, const struct gguf_str * val) {
|
| 7478 |
-
// fwrite(&val->n, sizeof(val->n), 1, file);
|
| 7479 |
-
// fwrite(val->data, sizeof(char), val->n, file);
|
| 7480 |
-
//}
|
| 7481 |
-
//
|
| 7482 |
-
//static void gguf_fwrite_el(FILE * file, const void * val, size_t size) {
|
| 7483 |
-
// fwrite(val, sizeof(char), size, file);
|
| 7484 |
-
//}
|
| 7485 |
-
|
| 7486 |
-
struct gguf_buf gguf_buf_init(size_t size) {
|
| 7487 |
-
struct gguf_buf buf = {
|
| 7488 |
-
/*buf.data =*/ size == 0 ? NULL : GGML_CALLOC(1, size),
|
| 7489 |
-
/*buf.size =*/ size,
|
| 7490 |
-
/*buf.offset =*/ 0,
|
| 7491 |
-
};
|
| 7492 |
-
|
| 7493 |
-
return buf;
|
| 7494 |
-
}
|
| 7495 |
-
|
| 7496 |
-
void gguf_buf_free(struct gguf_buf buf) {
|
| 7497 |
-
if (buf.data) {
|
| 7498 |
-
GGML_FREE(buf.data);
|
| 7499 |
-
}
|
| 7500 |
-
}
|
| 7501 |
-
|
| 7502 |
-
static void gguf_buf_grow(struct gguf_buf * buf, size_t size) {
|
| 7503 |
-
if (buf->offset + size > buf->size) {
|
| 7504 |
-
buf->size = 1.5*(buf->offset + size);
|
| 7505 |
-
if (buf->data) {
|
| 7506 |
-
buf->data = realloc(buf->data, buf->size);
|
| 7507 |
-
}
|
| 7508 |
-
}
|
| 7509 |
-
}
|
| 7510 |
-
|
| 7511 |
-
static void gguf_bwrite_str(struct gguf_buf * buf, const struct gguf_str * val) {
|
| 7512 |
-
gguf_buf_grow(buf, sizeof(val->n) + val->n);
|
| 7513 |
-
|
| 7514 |
-
if (buf->data) {
|
| 7515 |
-
memcpy((char *) buf->data + buf->offset, &val->n, sizeof(val->n));
|
| 7516 |
-
}
|
| 7517 |
-
buf->offset += sizeof(val->n);
|
| 7518 |
-
|
| 7519 |
-
if (buf->data) {
|
| 7520 |
-
memcpy((char *) buf->data + buf->offset, val->data, val->n);
|
| 7521 |
-
}
|
| 7522 |
-
buf->offset += val->n;
|
| 7523 |
-
}
|
| 7524 |
-
|
| 7525 |
-
static void gguf_bwrite_el(struct gguf_buf * buf, const void * val, size_t el_size) {
|
| 7526 |
-
gguf_buf_grow(buf, el_size);
|
| 7527 |
-
|
| 7528 |
-
if (buf->data) {
|
| 7529 |
-
memcpy((char *) buf->data + buf->offset, val, el_size);
|
| 7530 |
-
}
|
| 7531 |
-
buf->offset += el_size;
|
| 7532 |
-
}
|
| 7533 |
-
|
| 7534 |
-
void gguf_write_to_buf(const struct gguf_context * ctx, struct gguf_buf * buf, bool only_meta) {
|
| 7535 |
-
// write header
|
| 7536 |
-
gguf_bwrite_el(buf, &ctx->header.magic, sizeof(ctx->header.magic));
|
| 7537 |
-
gguf_bwrite_el(buf, &ctx->header.version, sizeof(ctx->header.version));
|
| 7538 |
-
gguf_bwrite_el(buf, &ctx->header.n_tensors, sizeof(ctx->header.n_tensors));
|
| 7539 |
-
gguf_bwrite_el(buf, &ctx->header.n_kv, sizeof(ctx->header.n_kv));
|
| 7540 |
-
|
| 7541 |
-
// write key-value pairs
|
| 7542 |
-
for (uint32_t i = 0; i < ctx->header.n_kv; ++i) {
|
| 7543 |
-
struct gguf_kv * kv = &ctx->kv[i];
|
| 7544 |
-
|
| 7545 |
-
gguf_bwrite_str(buf, &kv->key);
|
| 7546 |
-
gguf_bwrite_el (buf, &kv->type, sizeof(kv->type));
|
| 7547 |
-
|
| 7548 |
-
switch (kv->type) {
|
| 7549 |
-
case GGUF_TYPE_UINT8: gguf_bwrite_el( buf, &kv->value.uint8, sizeof(kv->value.uint8) ); break;
|
| 7550 |
-
case GGUF_TYPE_INT8: gguf_bwrite_el (buf, &kv->value.int8, sizeof(kv->value.int8) ); break;
|
| 7551 |
-
case GGUF_TYPE_UINT16: gguf_bwrite_el (buf, &kv->value.uint16, sizeof(kv->value.uint16) ); break;
|
| 7552 |
-
case GGUF_TYPE_INT16: gguf_bwrite_el (buf, &kv->value.int16, sizeof(kv->value.int16) ); break;
|
| 7553 |
-
case GGUF_TYPE_UINT32: gguf_bwrite_el (buf, &kv->value.uint32, sizeof(kv->value.uint32) ); break;
|
| 7554 |
-
case GGUF_TYPE_INT32: gguf_bwrite_el (buf, &kv->value.int32, sizeof(kv->value.int32) ); break;
|
| 7555 |
-
case GGUF_TYPE_FLOAT32: gguf_bwrite_el (buf, &kv->value.float32, sizeof(kv->value.float32)); break;
|
| 7556 |
-
case GGUF_TYPE_UINT64: gguf_bwrite_el (buf, &kv->value.uint64, sizeof(kv->value.uint64) ); break;
|
| 7557 |
-
case GGUF_TYPE_INT64: gguf_bwrite_el (buf, &kv->value.int64, sizeof(kv->value.int64) ); break;
|
| 7558 |
-
case GGUF_TYPE_FLOAT64: gguf_bwrite_el (buf, &kv->value.float64, sizeof(kv->value.float64)); break;
|
| 7559 |
-
case GGUF_TYPE_BOOL: gguf_bwrite_el (buf, &kv->value.bool_, sizeof(kv->value.bool_) ); break;
|
| 7560 |
-
case GGUF_TYPE_STRING: gguf_bwrite_str(buf, &kv->value.str ); break;
|
| 7561 |
-
case GGUF_TYPE_ARRAY:
|
| 7562 |
-
{
|
| 7563 |
-
gguf_bwrite_el(buf, &kv->value.arr.type, sizeof(kv->value.arr.type));
|
| 7564 |
-
gguf_bwrite_el(buf, &kv->value.arr.n, sizeof(kv->value.arr.n) );
|
| 7565 |
-
|
| 7566 |
-
switch (kv->value.arr.type) {
|
| 7567 |
-
case GGUF_TYPE_UINT8:
|
| 7568 |
-
case GGUF_TYPE_INT8:
|
| 7569 |
-
case GGUF_TYPE_UINT16:
|
| 7570 |
-
case GGUF_TYPE_INT16:
|
| 7571 |
-
case GGUF_TYPE_UINT32:
|
| 7572 |
-
case GGUF_TYPE_INT32:
|
| 7573 |
-
case GGUF_TYPE_FLOAT32:
|
| 7574 |
-
case GGUF_TYPE_UINT64:
|
| 7575 |
-
case GGUF_TYPE_INT64:
|
| 7576 |
-
case GGUF_TYPE_FLOAT64:
|
| 7577 |
-
case GGUF_TYPE_BOOL:
|
| 7578 |
-
{
|
| 7579 |
-
gguf_bwrite_el(buf, kv->value.arr.data, kv->value.arr.n * gguf_type_size(kv->value.arr.type));
|
| 7580 |
-
} break;
|
| 7581 |
-
case GGUF_TYPE_STRING:
|
| 7582 |
-
{
|
| 7583 |
-
for (uint32_t j = 0; j < kv->value.arr.n; ++j) {
|
| 7584 |
-
gguf_bwrite_str(buf, &((struct gguf_str *) kv->value.arr.data)[j]);
|
| 7585 |
-
}
|
| 7586 |
-
} break;
|
| 7587 |
-
case GGUF_TYPE_ARRAY:
|
| 7588 |
-
default: GGML_ABORT("invalid type");
|
| 7589 |
-
}
|
| 7590 |
-
} break;
|
| 7591 |
-
default: GGML_ABORT("invalid type");
|
| 7592 |
-
}
|
| 7593 |
-
}
|
| 7594 |
-
|
| 7595 |
-
// write tensor infos
|
| 7596 |
-
for (uint32_t i = 0; i < ctx->header.n_tensors; ++i) {
|
| 7597 |
-
struct gguf_tensor_info * info = &ctx->infos[i];
|
| 7598 |
-
|
| 7599 |
-
gguf_bwrite_str(buf, &info->name);
|
| 7600 |
-
gguf_bwrite_el (buf, &info->n_dims, sizeof(info->n_dims));
|
| 7601 |
-
for (uint32_t j = 0; j < info->n_dims; ++j) {
|
| 7602 |
-
gguf_bwrite_el(buf, &info->ne[j], sizeof(info->ne[j]));
|
| 7603 |
-
}
|
| 7604 |
-
gguf_bwrite_el(buf, &info->type, sizeof(info->type));
|
| 7605 |
-
gguf_bwrite_el(buf, &info->offset, sizeof(info->offset));
|
| 7606 |
-
}
|
| 7607 |
-
|
| 7608 |
-
// we require the data section to be aligned, so take into account any padding
|
| 7609 |
-
{
|
| 7610 |
-
const size_t offset = buf->offset;
|
| 7611 |
-
const size_t offset_pad = GGML_PAD(offset, ctx->alignment);
|
| 7612 |
-
|
| 7613 |
-
if (offset_pad != offset) {
|
| 7614 |
-
uint8_t pad = 0;
|
| 7615 |
-
for (size_t i = 0; i < offset_pad - offset; ++i) {
|
| 7616 |
-
gguf_bwrite_el(buf, &pad, sizeof(pad));
|
| 7617 |
-
}
|
| 7618 |
-
}
|
| 7619 |
-
}
|
| 7620 |
-
|
| 7621 |
-
if (only_meta) {
|
| 7622 |
-
return;
|
| 7623 |
-
}
|
| 7624 |
-
|
| 7625 |
-
size_t offset = 0;
|
| 7626 |
-
|
| 7627 |
-
// write tensor data
|
| 7628 |
-
for (uint32_t i = 0; i < ctx->header.n_tensors; ++i) {
|
| 7629 |
-
struct gguf_tensor_info * info = &ctx->infos[i];
|
| 7630 |
-
|
| 7631 |
-
const size_t size = info->size;
|
| 7632 |
-
const size_t size_pad = GGML_PAD(size, ctx->alignment);
|
| 7633 |
-
|
| 7634 |
-
gguf_bwrite_el(buf, info->data, size);
|
| 7635 |
-
|
| 7636 |
-
if (size_pad != size) {
|
| 7637 |
-
uint8_t pad = 0;
|
| 7638 |
-
for (size_t j = 0; j < size_pad - size; ++j) {
|
| 7639 |
-
gguf_bwrite_el(buf, &pad, sizeof(pad));
|
| 7640 |
-
}
|
| 7641 |
-
}
|
| 7642 |
-
|
| 7643 |
-
GGML_ASSERT(offset == info->offset);
|
| 7644 |
-
|
| 7645 |
-
offset += size_pad;
|
| 7646 |
-
}
|
| 7647 |
-
}
|
| 7648 |
-
|
| 7649 |
-
void gguf_write_to_file(const struct gguf_context * ctx, const char * fname, bool only_meta) {
|
| 7650 |
-
FILE * file = ggml_fopen(fname, "wb");
|
| 7651 |
-
if (!file) {
|
| 7652 |
-
GGML_ABORT("failed to open file for writing");
|
| 7653 |
-
}
|
| 7654 |
-
|
| 7655 |
-
struct gguf_buf buf = gguf_buf_init(16*1024);
|
| 7656 |
-
|
| 7657 |
-
gguf_write_to_buf(ctx, &buf, only_meta);
|
| 7658 |
-
|
| 7659 |
-
fwrite(buf.data, 1, buf.offset, file);
|
| 7660 |
-
|
| 7661 |
-
gguf_buf_free(buf);
|
| 7662 |
-
|
| 7663 |
-
fclose(file);
|
| 7664 |
-
}
|
| 7665 |
-
|
| 7666 |
-
size_t gguf_get_meta_size(const struct gguf_context * ctx) {
|
| 7667 |
-
// no allocs - only compute size
|
| 7668 |
-
struct gguf_buf buf = gguf_buf_init(0);
|
| 7669 |
-
|
| 7670 |
-
gguf_write_to_buf(ctx, &buf, true);
|
| 7671 |
-
|
| 7672 |
-
return buf.offset;
|
| 7673 |
-
}
|
| 7674 |
-
|
| 7675 |
-
void gguf_get_meta_data(const struct gguf_context * ctx, void * data) {
|
| 7676 |
-
struct gguf_buf buf = gguf_buf_init(16*1024);
|
| 7677 |
-
|
| 7678 |
-
gguf_write_to_buf(ctx, &buf, true);
|
| 7679 |
-
|
| 7680 |
-
memcpy(data, buf.data, buf.offset);
|
| 7681 |
-
|
| 7682 |
-
gguf_buf_free(buf);
|
| 7683 |
-
}
|
| 7684 |
-
|
| 7685 |
void ggml_log_set(ggml_log_callback log_callback, void * user_data) {
|
| 7686 |
g_logger_state.log_callback = log_callback ? log_callback : ggml_log_callback_default;
|
| 7687 |
g_logger_state.log_callback_user_data = user_data;
|
|
|
|
| 1588 |
|
| 1589 |
struct ggml_tensor * const result = (struct ggml_tensor *)((char *)ctx->mem_buffer + obj_new->offs);
|
| 1590 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1591 |
*result = (struct ggml_tensor) {
|
| 1592 |
/*.type =*/ type,
|
|
|
|
| 1593 |
/*.buffer =*/ NULL,
|
| 1594 |
/*.ne =*/ { 1, 1, 1, 1 },
|
| 1595 |
/*.nb =*/ { 0, 0, 0, 0 },
|
|
|
|
| 1605 |
/*.padding =*/ { 0 },
|
| 1606 |
};
|
| 1607 |
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1608 |
// TODO: this should not be needed as long as we don't rely on aligned SIMD loads
|
| 1609 |
//GGML_ASSERT_ALIGNED(result->data);
|
| 1610 |
|
|
|
|
| 6406 |
|
| 6407 |
////////////////////////////////////////////////////////////////////////////////
|
| 6408 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 6409 |
void ggml_log_set(ggml_log_callback log_callback, void * user_data) {
|
| 6410 |
g_logger_state.log_callback = log_callback ? log_callback : ggml_log_callback_default;
|
| 6411 |
g_logger_state.log_callback_user_data = user_data;
|