| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154 | 
							- // Copyright (c) Meta Platforms, Inc. and affiliates.
 
- // All rights reserved.
 
- //
 
- // This source code is licensed under the license found in the
 
- // LICENSE file in the root directory of this source tree.
 
- #include "ggml/ggml.h"
 
- #include "ggml/ggml-alloc.h"
 
- #include "common.h"
 
- #include "common-ggml.h"
 
- #include <iostream>
 
- #include <stdexcept>
 
- #include "model_loader.h"
 
- template<typename T>
 
- void
 
- model_loader<T>::load_ggml_file(const std::string &fname, fairseq2_model<T> &model)
 
- {
 
-     printf("%s: loading model from '%s'\n", __func__, fname.c_str());
 
-     auto fin = std::ifstream(fname, std::ios::binary);
 
-     if (!fin) {
 
-         fprintf(stderr, "%s: failed to open '%s'\n", __func__, fname.c_str());
 
-         throw std::invalid_argument("failed to open file."); // TODO Merge error message.
 
-     }
 
-     if (!verify_magic(fin)) {
 
-         fprintf(stderr, "%s: invalid model file '%s' (bad magic)\n", __func__, fname.c_str());
 
-         throw std::invalid_argument("failed to open file."); // TODO Merge error message.
 
-     }
 
-     load_hparams(fin, model.hparams);
 
-     init_model(model);
 
-     load_model_weights(fin, model);
 
- };
 
- template<typename T>
 
- bool 
 
- model_loader<T>::verify_magic(std::ifstream &fin)
 
- {
 
-     uint32_t magic;
 
-     fin.read((char *) &magic, sizeof(magic));
 
-     return magic == GGML_FILE_MAGIC;
 
- };
 
- template<typename T>
 
- void
 
- model_loader<T>::init_model(fairseq2_model<T> &model)
 
- {
 
-     struct ggml_init_params params = {
 
-         /*.mem_size   =*/ compute_context_size(model.hparams),
 
-         /*.mem_buffer =*/ NULL,
 
-         /*.no_alloc   =*/ false,
 
-     };
 
-     model.ctx = ggml_init(params);
 
-     if (!model.ctx)
 
-         throw std::runtime_error("ggml_init() failed.");
 
-     init_model_tensors(model);
 
- };
 
- template<typename T>
 
- void
 
- model_loader<T>::load_model_weights(std::ifstream &fin, fairseq2_model<T> &model)
 
- {
 
-     size_t total_size = 0;
 
-     while (!fin.eof()) {
 
-         auto tensor = next_tensor(fin, model);
 
-         load_tensor_value(fin, tensor);
 
-         total_size += ggml_nbytes(tensor);
 
-     }
 
-     printf("%s: model size  = %8.2f MB\n", __func__, total_size/1024.0/1024.0);
 
- };
 
- template<typename T>
 
- ggml_tensor *
 
- model_loader<T>::next_tensor(std::ifstream &fin, fairseq2_model<T> &model)
 
- {
 
-     auto name = get_name(fin);
 
-     std::cout << "loading tensor: " << name << std::endl;
 
-    
 
-     if (model.tensors.find(name) == model.tensors.end()) {
 
-         fprintf(stderr, "%s: unknown tensor '%s' in model file\n", __func__, name.c_str());
 
-         throw std::invalid_argument("failed to open file."); // TODO Merge error message.
 
-     }
 
-     return model.tensors[name];
 
- };
 
- template<typename T>
 
- void
 
- model_loader<T>::load_tensor_value(std::ifstream &fin, ggml_tensor *tensor)
 
- {
 
-     int32_t n_dims;
 
-     int32_t ttype;
 
-     fin.read(reinterpret_cast<char *>(&n_dims), sizeof(n_dims));
 
-     fin.read(reinterpret_cast<char *>(&ttype),  sizeof(ttype));
 
-     int32_t nelements = 1;
 
-     int32_t ne[3] = {1, 1, 1};
 
-     for (int i = 0; i < n_dims; ++i) {
 
-         fin.read(reinterpret_cast<char *>(&ne[i]), sizeof(ne[i]));
 
-         nelements *= ne[i];
 
-     }
 
-     if (ggml_nelements(tensor) != nelements) {
 
-         std::cout << ggml_nelements(tensor) << std::endl;
 
-         std::cout << nelements << std::endl;
 
-         throw std::runtime_error("tensor has wrong size in model file.");
 
-     }
 
-     if (tensor->ne[0] != ne[0] || tensor->ne[1] != ne[1]) {
 
-         fprintf(stderr, "%s: tensor '%s' has wrong shape in model file: got [%d, %d], expected [%d, %d]\n",
 
-                 __func__, (int) tensor->ne[0], (int) tensor->ne[1], ne[0], ne[1]);
 
-         throw std::runtime_error("tensor has wrong shape in file."); // TODO Merge error message.
 
-     }
 
-     // for debugging
 
-     if (0) {
 
-         printf("%[%5d, %5d], type = %6s, %6.2f MB, %9zu bytes\n", ne[0], ne[1], ggml_type_name(ggml_type(ttype)), ggml_nbytes(tensor)/1024.0/1024.0, ggml_nbytes(tensor));
 
-     }
 
-     const size_t bpe = ggml_type_size(ggml_type(ttype));
 
-     if ((nelements * bpe)/ggml_blck_size(tensor->type) != ggml_nbytes(tensor)) {
 
-         fprintf(stderr, "%s: tensor has wrong size in model file: got %zu, expected %zu\n",
 
-                 __func__, ggml_nbytes(tensor), nelements * bpe);
 
-         throw std::runtime_error("tensor has wrong size in file."); // TODO Merge error message.
 
-     }
 
-     fin.read(reinterpret_cast<char *>(tensor->data), ggml_nbytes(tensor));
 
- };
 
- template<typename T>
 
- std::string
 
- model_loader<T>::get_name(std::ifstream& fin)
 
- {
 
-     int32_t length;
 
-     fin.read(reinterpret_cast<char *>(&length), sizeof(length));
 
-     std::string name(length, 0);
 
-     fin.read(&name[0], length);
 
-  
 
-     return name;
 
- };
 
 
  |