#include "risc0/zkvm/prove/method_id.h"
#include <fstream>
#include <map>
#include "risc0/core/elf.h"
#include "risc0/zkp/prove/poly_group.h"
#include "risc0/zkvm/prove/step.h"
namespace risc0 {
MethodID makeMethodID(const std::string& elfFile) {
std::map<uint32_t, uint32_t> image;
uint32_t startAddr = loadElf(elfFile, kMemSize, image);
MethodID ret;
for (size_t i = 0; i < kCodeDigestCount; i++) {
size_t cycles = kMinCycles * (1 << i);
if (cycles < image.size() + 3 + kZkCycles) {
ret[i] = ShaDigest::zero();
continue;
}
std::vector<Fp> code(cycles * kCodeSize);
setupCode(code.data(), cycles, startAddr, image);
auto coeffs = AccelSlice<Fp>::copy(code);
batchInterpolateNTT(coeffs, kCodeSize);
zkShiftAccel(coeffs, kCodeSize);
PolyGroup codeGroup(coeffs, kCodeSize, cycles);
ret[i] = codeGroup.getMerkle().getRoot();
}
return ret;
}
void writeMethodID(const std::string& filename, const MethodID& id) {
std::ofstream file(filename, std::ios::out | std::ios::binary);
if (!file) {
throw std::runtime_error("Unable to open file: " + filename);
}
file.write(reinterpret_cast<const char*>(&id), sizeof(MethodID));
file.close();
if (!file.good()) {
throw std::runtime_error("Error writing code id file: " + filename);
}
}
namespace rust {
MethodID::MethodID(const std::string& elf_path) : id(makeMethodID(elf_path)) {}
std::unique_ptr<MethodID> new_method_id(const std::string& elf_path) {
return std::make_unique<MethodID>(elf_path);
}
void MethodID::write(const std::string& filename) const {
writeMethodID(filename, id);
}
}
}