Skip to content
This repository was archived by the owner on Apr 25, 2021. It is now read-only.

Commit 122e50f

Browse files
committed
빌드 스크립트 추가/고침
1 parent bc6de26 commit 122e50f

2 files changed

Lines changed: 158 additions & 0 deletions

File tree

src/Makefile

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ FIRMWARE = $(BUILD)/firmware
1212
# include py core make definitions
1313
include $(TOP)/py/py.mk
1414

15+
# TODO: common CROSS_COMPILE required
1516
CROSS_COMPILE = /opt/gcc-arm-none-eabi-7-2018-q2-update/bin/arm-none-eabi-
1617
# CROSS_COMPILE = arm-none-eabi-
1718

src/build.py

Lines changed: 157 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,157 @@
1+
import os
2+
import sys
3+
import time
4+
import traceback
5+
from collections import Container
6+
from pathlib import Path
7+
from subprocess import check_call, DEVNULL, CalledProcessError
8+
from typing import TypeVar, Generic
9+
10+
from dataclasses import dataclass
11+
from elftools.elf.elffile import ELFFile
12+
from elftools.elf.sections import SymbolTableSection, Section, Symbol
13+
import shutil
14+
15+
FOLDER = Path(__file__).parent
16+
OPMOD_PATH = FOLDER.parent / "opmod"
17+
TARGET_FOLDER = OPMOD_PATH / "src/main/resources/assets/openpie/firmwares/debug" # TODO: place version
18+
19+
20+
@dataclass
21+
class SymbolInfo:
22+
bind: str
23+
type: str
24+
25+
26+
@dataclass
27+
class SimpleSymbol:
28+
name: str
29+
st_name: int
30+
st_value: int
31+
st_size: int
32+
st_info: SymbolInfo
33+
st_other: Container
34+
st_shndx: int
35+
36+
@classmethod
37+
def from_symbol(cls, symbol_obj: Symbol):
38+
return SimpleSymbol(
39+
symbol_obj.name,
40+
st_info=SymbolInfo(**symbol_obj.entry.pop("st_info")),
41+
**symbol_obj.entry,
42+
)
43+
44+
45+
@dataclass
46+
class SimpleSection:
47+
name: str
48+
sh_name: int
49+
sh_type: str
50+
sh_flags: int
51+
sh_addr: int
52+
sh_offset: int
53+
sh_size: int
54+
sh_link: int
55+
sh_info: int
56+
sh_addralign: int
57+
sh_entsize: int
58+
59+
60+
@dataclass
61+
class SimpleSegment:
62+
p_type: str
63+
p_offset: int
64+
p_vaddr: int
65+
p_paddr: int
66+
p_filesz: int
67+
p_memsz: int
68+
p_flags: int
69+
p_align: int
70+
71+
72+
T = TypeVar("T")
73+
74+
75+
def find_section(elf: ELFFile, cls: Generic[T]) -> T:
76+
return list(s for s in elf.iter_sections() if type(s) == cls)
77+
78+
79+
def pretty_addr(addr: int, size=8) -> str:
80+
return "0x" + hex(addr)[2:].zfill(size)
81+
82+
83+
def process_elf(elf: ELFFile, map_file: Path):
84+
assert elf.get_machine_arch() == "ARM"
85+
86+
if False:
87+
print(">", "section")
88+
for section_obj in find_section(elf, Section): # type: Section
89+
section = SimpleSection(section_obj.name, **section_obj.header)
90+
if not section.sh_addr:
91+
continue
92+
93+
print(
94+
pretty_addr(section.sh_addr),
95+
pretty_addr(section.sh_size, size=6),
96+
section.sh_flags,
97+
section.sh_type,
98+
section.name,
99+
sep="\t"
100+
)
101+
102+
with map_file.open('w') as fp:
103+
type2typ = {
104+
"STT_OBJECT": "OBJECT",
105+
"STT_FUNC": "FUNC",
106+
}
107+
for symbol_table in find_section(elf, SymbolTableSection):
108+
symbols = [SimpleSymbol.from_symbol(obj) for obj in symbol_table.iter_symbols()
109+
if (obj['st_info']['type'] == "STT_FUNC" or
110+
obj['st_info']['type'] == "STT_OBJECT") and
111+
obj['st_info']['bind'] == "STB_GLOBAL"]
112+
113+
for symbol in sorted(symbols, key=lambda x: x.st_value):
114+
print(
115+
pretty_addr(symbol.st_value),
116+
pretty_addr(symbol.st_size, size=4),
117+
# symbol.st_info.bind,
118+
type2typ[symbol.st_info.type],
119+
symbol.name,
120+
sep="\t",
121+
file=fp,
122+
)
123+
124+
125+
def build(folder: Path = FOLDER, target_folder: Path = TARGET_FOLDER):
126+
build_path: Path = folder / "build"
127+
128+
check_call(
129+
["wsl", "make", "-j8"],
130+
cwd=str(folder),
131+
shell=True,
132+
stdin=DEVNULL
133+
)
134+
135+
target_folder.mkdir(parents=True, exist_ok=True)
136+
137+
with (build_path / "firmware.elf").open('rb') as fp:
138+
elf = ELFFile(fp)
139+
process_elf(elf, target_folder / "firmware.map")
140+
141+
shutil.copyfile(str(build_path / "firmware.bin"), str(target_folder / "firmware.bin"))
142+
shutil.copyfile(str(build_path / "firmware.elf"), str(target_folder / "firmware.elf"))
143+
shutil.copyfile(str(build_path / "firmware.elf.map"), str(target_folder / "firmware.elf.map"))
144+
print(target_folder / "firmware.bin")
145+
146+
147+
def main():
148+
try:
149+
build()
150+
return 0
151+
except CalledProcessError as e:
152+
traceback.print_exc()
153+
raise SystemExit(e.returncode)
154+
155+
156+
if __name__ == '__main__':
157+
main()

0 commit comments

Comments
 (0)