1*13ebd6f5SMangoPeachGrape #undef NDEBUG
2*13ebd6f5SMangoPeachGrape
3*13ebd6f5SMangoPeachGrape #include <fstream>
4*13ebd6f5SMangoPeachGrape #include <iostream>
5*13ebd6f5SMangoPeachGrape #include <sstream>
6*13ebd6f5SMangoPeachGrape #include <wasmtime.hh>
7*13ebd6f5SMangoPeachGrape
8*13ebd6f5SMangoPeachGrape using namespace wasmtime;
9*13ebd6f5SMangoPeachGrape
readFile(const char * name)10*13ebd6f5SMangoPeachGrape std::string readFile(const char *name) {
11*13ebd6f5SMangoPeachGrape std::ifstream watFile;
12*13ebd6f5SMangoPeachGrape watFile.open(name);
13*13ebd6f5SMangoPeachGrape std::stringstream strStream;
14*13ebd6f5SMangoPeachGrape strStream << watFile.rdbuf();
15*13ebd6f5SMangoPeachGrape return strStream.str();
16*13ebd6f5SMangoPeachGrape }
17*13ebd6f5SMangoPeachGrape
main()18*13ebd6f5SMangoPeachGrape int main() {
19*13ebd6f5SMangoPeachGrape // Create our `store` context and then compile a module and create an
20*13ebd6f5SMangoPeachGrape // instance from the compiled module all in one go.
21*13ebd6f5SMangoPeachGrape Engine engine;
22*13ebd6f5SMangoPeachGrape Module module =
23*13ebd6f5SMangoPeachGrape Module::compile(engine, readFile("examples/memory.wat")).unwrap();
24*13ebd6f5SMangoPeachGrape Store store(engine);
25*13ebd6f5SMangoPeachGrape Instance instance = Instance::create(store, module, {}).unwrap();
26*13ebd6f5SMangoPeachGrape
27*13ebd6f5SMangoPeachGrape // load_fn up our exports from the instance
28*13ebd6f5SMangoPeachGrape auto memory = std::get<Memory>(*instance.get(store, "memory"));
29*13ebd6f5SMangoPeachGrape auto size = std::get<Func>(*instance.get(store, "size"));
30*13ebd6f5SMangoPeachGrape auto load_fn = std::get<Func>(*instance.get(store, "load"));
31*13ebd6f5SMangoPeachGrape auto store_fn = std::get<Func>(*instance.get(store, "store"));
32*13ebd6f5SMangoPeachGrape
33*13ebd6f5SMangoPeachGrape std::cout << "Checking memory...\n";
34*13ebd6f5SMangoPeachGrape assert(memory.size(store) == 2);
35*13ebd6f5SMangoPeachGrape auto data = memory.data(store);
36*13ebd6f5SMangoPeachGrape assert(data.size() == 0x20000);
37*13ebd6f5SMangoPeachGrape assert(data[0] == 0);
38*13ebd6f5SMangoPeachGrape assert(data[0x1000] == 1);
39*13ebd6f5SMangoPeachGrape assert(data[0x1003] == 4);
40*13ebd6f5SMangoPeachGrape
41*13ebd6f5SMangoPeachGrape assert(size.call(store, {}).unwrap()[0].i32() == 2);
42*13ebd6f5SMangoPeachGrape assert(load_fn.call(store, {0}).unwrap()[0].i32() == 0);
43*13ebd6f5SMangoPeachGrape assert(load_fn.call(store, {0x1000}).unwrap()[0].i32() == 1);
44*13ebd6f5SMangoPeachGrape assert(load_fn.call(store, {0x1003}).unwrap()[0].i32() == 4);
45*13ebd6f5SMangoPeachGrape assert(load_fn.call(store, {0x1ffff}).unwrap()[0].i32() == 0);
46*13ebd6f5SMangoPeachGrape load_fn.call(store, {0x20000}).err(); // out of bounds trap
47*13ebd6f5SMangoPeachGrape
48*13ebd6f5SMangoPeachGrape std::cout << "Mutating memory...\n";
49*13ebd6f5SMangoPeachGrape memory.data(store)[0x1003] = 5;
50*13ebd6f5SMangoPeachGrape
51*13ebd6f5SMangoPeachGrape store_fn.call(store, {0x1002, 6}).unwrap();
52*13ebd6f5SMangoPeachGrape store_fn.call(store, {0x20000, 0}).err(); // out of bounds trap
53*13ebd6f5SMangoPeachGrape
54*13ebd6f5SMangoPeachGrape assert(memory.data(store)[0x1002] == 6);
55*13ebd6f5SMangoPeachGrape assert(memory.data(store)[0x1003] == 5);
56*13ebd6f5SMangoPeachGrape assert(load_fn.call(store, {0x1002}).unwrap()[0].i32() == 6);
57*13ebd6f5SMangoPeachGrape assert(load_fn.call(store, {0x1003}).unwrap()[0].i32() == 5);
58*13ebd6f5SMangoPeachGrape
59*13ebd6f5SMangoPeachGrape // Grow memory.
60*13ebd6f5SMangoPeachGrape std::cout << "Growing memory...\n";
61*13ebd6f5SMangoPeachGrape memory.grow(store, 1).unwrap();
62*13ebd6f5SMangoPeachGrape assert(memory.size(store) == 3);
63*13ebd6f5SMangoPeachGrape assert(memory.data(store).size() == 0x30000);
64*13ebd6f5SMangoPeachGrape
65*13ebd6f5SMangoPeachGrape assert(load_fn.call(store, {0x20000}).unwrap()[0].i32() == 0);
66*13ebd6f5SMangoPeachGrape store_fn.call(store, {0x20000, 0}).unwrap();
67*13ebd6f5SMangoPeachGrape load_fn.call(store, {0x30000}).err();
68*13ebd6f5SMangoPeachGrape store_fn.call(store, {0x30000, 0}).err();
69*13ebd6f5SMangoPeachGrape
70*13ebd6f5SMangoPeachGrape memory.grow(store, 1).err();
71*13ebd6f5SMangoPeachGrape memory.grow(store, 0).ok();
72*13ebd6f5SMangoPeachGrape
73*13ebd6f5SMangoPeachGrape std::cout << "Creating stand-alone memory...\n";
74*13ebd6f5SMangoPeachGrape MemoryType ty(5, 5);
75*13ebd6f5SMangoPeachGrape Memory memory2 = Memory::create(store, ty).unwrap();
76*13ebd6f5SMangoPeachGrape assert(memory2.size(store) == 5);
77*13ebd6f5SMangoPeachGrape memory2.grow(store, 1).err();
78*13ebd6f5SMangoPeachGrape memory2.grow(store, 0).ok();
79*13ebd6f5SMangoPeachGrape }
80