Skip to content

Commit 1c34002

Browse files
mutinifniweberlo
authored andcommitted
current status, semi implemented micro session
1 parent 6d67f2a commit 1c34002

File tree

11 files changed

+416
-55
lines changed

11 files changed

+416
-55
lines changed

python/tvm/contrib/binutil.py

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -81,13 +81,13 @@ def tvm_relocate_binary(binary_name, text, data, bss):
8181

8282

8383
@register_func("tvm_read_binary_section")
84-
def tvm_read_binary_section(binary_name, section):
84+
def tvm_read_binary_section(binary, section):
8585
"""Returns the contents of the specified section in the binary file
8686
8787
Parameters
8888
----------
89-
binary_name : string
90-
name of the binary file
89+
binary : bytearray
90+
contents of the binary
9191
9292
section : string
9393
type of section
@@ -98,10 +98,13 @@ def tvm_read_binary_section(binary_name, section):
9898
contents of the read section
9999
"""
100100
tmp_dir = util.tempdir()
101+
tmp_bin = tmp_dir.relpath("temp.bin")
101102
tmp_section = tmp_dir.relpath("tmp_section.bin")
103+
with open(tmp_bin, "wb") as out_file:
104+
out_file.write(bytes(binary))
102105
p1 = subprocess.Popen(["objcopy", "--dump-section",
103106
"." + section + "=" + tmp_section,
104-
binary_name],
107+
tmp_bin],
105108
stdout=subprocess.PIPE,
106109
stderr=subprocess.STDOUT)
107110
(out, _) = p1.communicate()

src/runtime/micro/device/utvm_runtime.cc

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,7 @@ UTVMTask task;
1212
void UTVMDone() {}
1313

1414
// init stub
15-
int UTVMMain()
16-
{
15+
int UTVMMain() {
1716
task.func(task.args, task.arg_type_ids, *task.num_args);
1817
UTVMDone();
1918
return 0;

src/runtime/micro/low_level_device.h

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@
33
* \file low_level_device.h
44
* \brief Abstract low-level micro device management
55
*/
6-
#ifndef TVM_RUNTIME_LOW_LEVEL_DEVICE_H_
7-
#define TVM_RUNTIME_LOW_LEVEL_DEVICE_H_
6+
#ifndef TVM_RUNTIME_MICRO_LOW_LEVEL_DEVICE_H_
7+
#define TVM_RUNTIME_MICRO_LOW_LEVEL_DEVICE_H_
88

99
#include <cstddef>
1010
#include <memory>
@@ -64,6 +64,6 @@ const std::shared_ptr<LowLevelDevice> HostLowLevelDeviceCreate(size_t num_bytes)
6464
* \param port port of the OpenOCD server to connect to
6565
*/
6666
const std::shared_ptr<LowLevelDevice> OpenOCDLowLevelDeviceCreate(int port);
67-
} // namespace runtime
68-
} // namespace tvm
69-
#endif // TVM_RUNTIME_LOW_LEVEL_DEVICE_H_
67+
} // namespace runtime
68+
} // namespace tvm
69+
#endif // TVM_RUNTIME_MICRO_LOW_LEVEL_DEVICE_H_

src/runtime/micro/micro_common.cc

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ const char* SectionToString(SectionKind section) {
3131

3232
void* GetSymbol(std::unordered_map<std::string, void*> symbol_map,
3333
std::string name,
34-
void* base_addr) {
34+
const void* base_addr) {
3535
void* symbol_addr = symbol_map[name];
3636
return (void*)((uint8_t*) symbol_addr - (uint8_t*) base_addr);
3737
}
@@ -59,12 +59,12 @@ std::string RelocateBinarySections(std::string binary_name,
5959
return relocated_bin;
6060
}
6161

62-
std::string ReadSection(std::string binary_name, SectionKind section) {
62+
std::string ReadSection(std::string binary, SectionKind section) {
6363
CHECK(section == kText || section == kData || section == kBss)
6464
<< "ReadSection requires section to be one of text, data or bss.";
6565
const auto* f = Registry::Get("tvm_read_binary_section");
6666
CHECK(f != nullptr) << "Require tvm_read_binary_section to exist in registry";
67-
std::string section_contents = (*f)(binary_name, SectionToString(section));
67+
std::string section_contents = (*f)(binary, SectionToString(section));
6868
return section_contents;
6969
}
7070

src/runtime/micro/micro_common.h

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -88,7 +88,7 @@ const char* SectionToString(SectionKind section);
8888
*/
8989
void* GetSymbol(std::unordered_map<std::string, void*> symbol_map,
9090
std::string name,
91-
void* base_addr);
91+
const void* base_addr);
9292

9393
/*!
9494
* \brief links binary by repositioning section addresses
@@ -104,12 +104,12 @@ std::string RelocateBinarySections(std::string binary_name,
104104
void* bss);
105105

106106
/*!
107-
* \brief reads section from binary file
108-
* \param binary_name input binary filename
107+
* \brief reads section from binary
108+
* \param binary input binary contents
109109
* \param section section type to be read
110110
* \return contents of the section
111111
*/
112-
std::string ReadSection(std::string binary_name, SectionKind section);
112+
std::string ReadSection(std::string binary, SectionKind section);
113113

114114
/*!
115115
* \brief finds size of the section in the binary

src/runtime/micro/micro_device_api.cc

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -29,13 +29,13 @@ class MicroDeviceAPI final : public DeviceAPI {
2929
size_t alignment,
3030
TVMType type_hint) final {
3131
// TODO: can make this a private member, but where to best init it?
32-
MicroSession* session = MicroSession::Global();
32+
std::shared_ptr<MicroSession> session = MicroSession::Global();
3333
void* alloc_ptr = session->AllocateInSection(kHeap, nbytes);
3434
return alloc_ptr;
3535
}
3636

3737
void FreeDataSpace(TVMContext ctx, void* ptr) final {
38-
MicroSession* session = MicroSession::Global();
38+
std::shared_ptr<MicroSession> session = MicroSession::Global();
3939
session->FreeInSection(kHeap, ptr);
4040
}
4141

@@ -48,7 +48,7 @@ class MicroDeviceAPI final : public DeviceAPI {
4848
TVMContext ctx_to,
4949
TVMType type_hint,
5050
TVMStreamHandle stream) final {
51-
MicroSession* session = MicroSession::Global();
51+
std::shared_ptr<MicroSession> session = MicroSession::Global();
5252
uint8_t buffer[size];
5353
constexpr int micro_devtype = kDLMicroDev;
5454
std::tuple<int, int> type_from_to(ctx_from.device_type, ctx_to.device_type);
@@ -75,20 +75,20 @@ class MicroDeviceAPI final : public DeviceAPI {
7575
}
7676
}
7777

78-
// TODO: ignore this?
78+
// TODO(): ignore this?
7979
void StreamSync(TVMContext ctx, TVMStreamHandle stream) final {
8080
}
8181

8282
// TODO: what about ctx?
8383
void* AllocWorkspace(TVMContext ctx, size_t size, TVMType type_hint) final {
84-
MicroSession* session = MicroSession::Global();
84+
std::shared_ptr<MicroSession> session = MicroSession::Global();
8585
void* alloc_ptr = session->AllocateInSection(kWorkspace, size);
8686
return alloc_ptr;
8787
}
8888

8989
// TODO: what about ctx?
9090
void FreeWorkspace(TVMContext ctx, void* data) final {
91-
MicroSession* session = MicroSession::Global();
91+
std::shared_ptr<MicroSession> session = MicroSession::Global();
9292
session->FreeInSection(kWorkspace, data);
9393
}
9494

@@ -109,5 +109,5 @@ TVM_REGISTER_GLOBAL("device_api.micro_dev")
109109
DeviceAPI* ptr = MicroDeviceAPI::Global().get();
110110
*rv = static_cast<void*>(ptr);
111111
});
112-
} // namespace runtime
113-
} // namespace tvm
112+
} // namespace runtime
113+
} // namespace tvm

src/runtime/micro/micro_module.cc

Lines changed: 49 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
#include "micro_session.h"
1212
#include "low_level_device.h"
1313
#include "micro_common.h"
14+
#include "../pack_args.h"
1415

1516
namespace tvm {
1617
namespace runtime {
@@ -32,14 +33,24 @@ class MicroModuleNode final : public ModuleNode {
3233
* \brief initializes module by establishing device connection and loads binary
3334
* \param binary name of the binary to be loaded
3435
*/
35-
void InitMicroModule(const std::string binary);
36+
void InitMicroModule(const std::string binary) {
37+
// TODO: if first MicroModule, then load init section in MicroSession
38+
session_ = MicroSession::Global();
39+
// TODO: ensure low_level_device_ is initialized in MicroSession
40+
lldevice_ = session_->low_level_device();
41+
binary_ = binary;
42+
LoadBinary();
43+
}
3644

3745
/*!
3846
* \brief runs selected function on the micro device
3947
* \param func name of the function to be run
48+
* \param func_addr address of the function to be run
4049
* \param args type-erased arguments passed to the function
4150
*/
42-
void RunFunction(std::string func, TVMArgs args);
51+
void RunFunction(std::string func, void* func_addr, TVMArgs args) {
52+
session_->PushToExecQueue(func_addr, args);
53+
}
4354

4455
private:
4556
/*! \brief loaded module text start address */
@@ -49,7 +60,7 @@ class MicroModuleNode final : public ModuleNode {
4960
/*! \brief loaded module bss start address */
5061
void* bss_start_;
5162
/*! \brief size of module text section */
52-
size_t code_size_;
63+
size_t text_size_;
5364
/*! \brief size of module data section */
5465
size_t data_size_;
5566
/*! \brief size of module bss section */
@@ -61,7 +72,27 @@ class MicroModuleNode final : public ModuleNode {
6172
/*! \brief low-level device pointer */
6273
std::shared_ptr<LowLevelDevice> lldevice_;
6374
/*! \brief symbol map to addresses */
64-
std::unordered_map<std::string, void*> symbol_map;
75+
std::unordered_map<std::string, void*> symbol_map_;
76+
77+
void LoadBinary() {
78+
text_size_ = GetSectionSize(binary_, kText);
79+
data_size_ = GetSectionSize(binary_, kData);
80+
bss_size_ = GetSectionSize(binary_, kBss);
81+
text_start_ = session_->AllocateInSection(kText, text_size_);
82+
data_start_ = session_->AllocateInSection(kData, data_size_);
83+
bss_start_ = session_->AllocateInSection(kBss, bss_size_);
84+
CHECK(text_start_ != nullptr && data_start_ != nullptr && bss_start_ != nullptr)
85+
<< "Not enough space to load module on device";
86+
std::string relocated_bin = RelocateBinarySections(binary_, text_start_,
87+
data_start_, bss_start_);
88+
std::string text_contents = ReadSection(relocated_bin, kText);
89+
std::string data_contents = ReadSection(relocated_bin, kData);
90+
std::string bss_contents = ReadSection(relocated_bin, kBss);
91+
lldevice_->Write(text_start_, &text_contents[0], text_size_);
92+
lldevice_->Write(data_start_, &data_contents[0], data_size_);
93+
lldevice_->Write(bss_start_, &bss_contents[0], bss_size_);
94+
symbol_map_ = GetSymbolMap(relocated_bin);
95+
}
6596
};
6697

6798
class MicroWrappedFunc {
@@ -74,7 +105,9 @@ class MicroWrappedFunc {
74105
func_addr_ = func_addr;
75106
}
76107

77-
void operator()(TVMArgs args, TVMRetValue* rv) const {
108+
void operator()(TVMArgs args, TVMRetValue* rv, void** void_args) const {
109+
// no return value yet, but may implement in the future
110+
m_->RunFunction(func_name_, func_addr_, args);
78111
}
79112

80113
private:
@@ -86,10 +119,20 @@ class MicroWrappedFunc {
86119
void* func_addr_;
87120
};
88121

89-
// TODO: register module load function
122+
PackedFunc MicroModuleNode::GetFunction(
123+
const std::string& name,
124+
const std::shared_ptr<ModuleNode>& sptr_to_self) {
125+
void* func_addr = GetSymbol(symbol_map_, name, lldevice_->base_addr());
126+
MicroWrappedFunc f(this, name, func_addr);
127+
return PackFuncVoidAddr(f, std::vector<TVMType>());
128+
}
129+
90130
// register loadfile function to load module from Python frontend
91131
TVM_REGISTER_GLOBAL("module.loadfile_micro_dev")
92132
.set_body([](TVMArgs args, TVMRetValue* rv) {
133+
std::shared_ptr<MicroModuleNode> n = std::make_shared<MicroModuleNode>();
134+
n->InitMicroModule(args[0]);
135+
*rv = runtime::Module(n);
93136
});
94137
} // namespace runtime
95138
} // namespace tvm

0 commit comments

Comments
 (0)