mirror of
https://github.com/UpsilonNumworks/Upsilon.git
synced 2026-01-18 16:27:34 +01:00
[Fix] Fix conflicts ._.
This commit is contained in:
59
build/all.mak
Normal file
59
build/all.mak
Normal file
@@ -0,0 +1,59 @@
|
||||
# This is a standalone Makefile
|
||||
# Invoke using "make -f build/all.mak"
|
||||
|
||||
ANDROID_GRADLE_KEYSTORE ?= ~/.gradle/google-play-upload.keystore
|
||||
ANDROID_GRADLE_PROPERTIES ?= ~/.gradle/gradle.properties
|
||||
IOS_MOBILE_PROVISION ?= build/artifacts/NumWorks_Graphing_Calculator_Distribution.mobileprovision
|
||||
EMCC ?= emcc
|
||||
|
||||
define file_check
|
||||
@ if test ! -f $(1); \
|
||||
then \
|
||||
echo "Missing file: $(1)"; \
|
||||
exit 1; \
|
||||
fi
|
||||
endef
|
||||
|
||||
define command_check
|
||||
@ if ! command -v $(1) > /dev/null; \
|
||||
then \
|
||||
echo "Missing command: $(1), did you forget to source?"; \
|
||||
exit 1; \
|
||||
fi
|
||||
endef
|
||||
|
||||
.PHONY: all
|
||||
all:
|
||||
$(call file_check,$(ANDROID_GRADLE_KEYSTORE))
|
||||
$(call file_check,$(ANDROID_GRADLE_PROPERTIES))
|
||||
$(call file_check,$(IOS_MOBILE_PROVISION))
|
||||
$(call command_check,$(EMCC))
|
||||
@ rm -rf output/all_official
|
||||
@ mkdir -p output/all_official
|
||||
@ echo "BUILD_FIRMWARE DEVICE N0110"
|
||||
@ $(MAKE) clean
|
||||
@ $(MAKE) epsilon.official.onboarding.dfu
|
||||
@ cp output/release/device/n0110/epsilon.official.onboarding.dfu output/all_official/epsilon.device.n0110.dfu
|
||||
@ echo "BUILD_FIRMWARE DEVICE N0100"
|
||||
@ $(MAKE) MODEL=n0100 clean
|
||||
@ $(MAKE) MODEL=n0100 epsilon.official.onboarding.dfu
|
||||
@ cp output/release/device/n0100/epsilon.official.onboarding.dfu output/all_official/epsilon.device.n0100.dfu
|
||||
@ echo "BUILD_FIRMWARE SIMULATOR WEB ZIP"
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=web clean
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=web epsilon.official.zip
|
||||
@ cp output/release/simulator/web/epsilon.official.zip output/all_official/simulator.web.zip
|
||||
@ echo "BUILD_FIRMWARE SIMULATOR WEB JS"
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=web epsilon.official.js
|
||||
@ cp output/release/simulator/web/epsilon.official.js output/all_official/epsilon.js
|
||||
@ echo "BUILD_FIRMWARE SIMULATOR WEB PYTHON JS"
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=web clean
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=web EPSILON_GETOPT=1 EPSILON_APPS=code epsilon.official.js
|
||||
@ cp output/release/simulator/web/epsilon.official.js output/all_official/epsilon.python.js
|
||||
@ echo "BUILD_FIRMWARE SIMULATOR ANDROID"
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=android clean
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=android epsilon.official.apk
|
||||
@ cp output/release/simulator/android/epsilon.official.apk output/all_official/epsilon.official.apk
|
||||
@ echo "BUILD_FIRMWARE SIMULATOR IOS"
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=ios clean
|
||||
@ $(MAKE) PLATFORM=simulator TARGET=ios IOS_PROVISIONNING_PROFILE=$(IOS_MOBILE_PROVISION) epsilon.official.ipa
|
||||
@ cp output/release/simulator/ios/epsilon.official.ipa output/all_official/epsilon.ipa
|
||||
@@ -2,10 +2,6 @@
|
||||
|
||||
PLATFORM ?= device
|
||||
DEBUG ?= 0
|
||||
LEDS_CHOICE ?= 0
|
||||
|
||||
include build/defaults.mak
|
||||
include build/platform.$(PLATFORM).mak
|
||||
|
||||
EPSILON_VERSION ?= 13.1.0
|
||||
EPSILON_CUSTOM_VERSION ?= 1.19.0-0
|
||||
@@ -17,17 +13,4 @@ EPSILON_GETOPT ?= 0
|
||||
EPSILON_TELEMETRY ?= 0
|
||||
ESCHER_LOG_EVENTS_BINARY ?= 0
|
||||
OMEGA_THEME ?= omega_light
|
||||
|
||||
ifndef USE_LIBA
|
||||
$(error platform.mak should define USE_LIBA)
|
||||
endif
|
||||
include build/toolchain.$(TOOLCHAIN).mak
|
||||
|
||||
SFLAGS += -DDEBUG=$(DEBUG)
|
||||
SFLAGS += -DLEDS_CHOICE=$(LEDS_CHOICE)
|
||||
ifdef USERNAME
|
||||
SFLAGS += -DUSERNAME="$(USERNAME)"
|
||||
endif
|
||||
SFLAGS += -DEPSILON_GETOPT=$(EPSILON_GETOPT)
|
||||
SFLAGS += -DEPSILON_TELEMETRY=$(EPSILON_TELEMETRY)
|
||||
SFLAGS += -DESCHER_LOG_EVENTS_BINARY=$(ESCHER_LOG_EVENTS_BINARY)
|
||||
LEDS_CHOICE ?= 0
|
||||
|
||||
@@ -2,6 +2,15 @@ HOSTCC = gcc
|
||||
HOSTCXX = g++
|
||||
PYTHON = python3
|
||||
|
||||
SFLAGS += -DDEBUG=$(DEBUG)
|
||||
SFLAGS += -DLEDS_CHOICE=$(LEDS_CHOICE)
|
||||
ifdef USERNAME
|
||||
SFLAGS += -DUSERNAME="$(USERNAME)"
|
||||
endif
|
||||
SFLAGS += -DEPSILON_GETOPT=$(EPSILON_GETOPT)
|
||||
SFLAGS += -DEPSILON_TELEMETRY=$(EPSILON_TELEMETRY)
|
||||
SFLAGS += -DESCHER_LOG_EVENTS_BINARY=$(ESCHER_LOG_EVENTS_BINARY)
|
||||
|
||||
# Language-specific flags
|
||||
CFLAGS = -std=c99
|
||||
CXXFLAGS = -std=c++11 -fno-exceptions -fno-rtti -fno-threadsafe-statics
|
||||
|
||||
60
build/helpers.mk
Normal file
60
build/helpers.mk
Normal file
@@ -0,0 +1,60 @@
|
||||
# Define a standard rule helper
|
||||
# If passed a last parameter value of with_local_version, we also define an
|
||||
# extra rule that can build source files within the $(BUILD_DIR). This is useful
|
||||
# for rules that can be applied for intermediate objects (for example, when
|
||||
# going .png -> .cpp -> .o).
|
||||
|
||||
define rule_label
|
||||
@ echo "$(shell printf "%-8s" $(strip $(1)))$(@:$(BUILD_DIR)/%=%)"
|
||||
endef
|
||||
|
||||
# rule_for can define both global and local rules
|
||||
# - use local if the source can be an intermediate file
|
||||
# - use global if the source can be in the main tree
|
||||
define rule_for
|
||||
ifneq ($(filter global,$(5)),)
|
||||
$(addprefix $$(BUILD_DIR)/,$(strip $(2))): $(strip $(3)) | $$$$(@D)/.
|
||||
@ echo "$(shell printf "%-8s" $(strip $(1)))$$(@:$$(BUILD_DIR)/%=%)"
|
||||
$(Q) $(4)
|
||||
endif
|
||||
ifneq ($(filter local,$(5)),)
|
||||
$(addprefix $$(BUILD_DIR)/,$(strip $(2))): $(addprefix $$(BUILD_DIR)/,$(strip $(3)))
|
||||
@ echo "$(shell printf "%-8s" $(strip $(1)))$$(@:$$(BUILD_DIR)/%=%)"
|
||||
$(Q) $(4)
|
||||
endif
|
||||
endef
|
||||
|
||||
# Helper functions to work with variants
|
||||
|
||||
define direct_object_for
|
||||
$(addprefix $(BUILD_DIR)/,$(addsuffix .o,$(basename $(1))))
|
||||
endef
|
||||
|
||||
# Objects for source files in $(1) matching flavor $(2). A flavor is a dot
|
||||
# separated list of variants (e.g. large.speed).
|
||||
define flavored_object_for
|
||||
$(call direct_object_for,$(call filter_variants,$(1),$(sort $(subst ., ,$(2)))))
|
||||
endef
|
||||
|
||||
define object_for
|
||||
$(call direct_object_for,$(call any_variant,$(1)))
|
||||
endef
|
||||
|
||||
# Multi-arch helpers
|
||||
ifdef ARCHS
|
||||
ifndef ARCH
|
||||
|
||||
# This rule allow us to build any executable (%) for a specified ARCH ($1)
|
||||
# We depend on a phony target to make sure this rule is always executed
|
||||
.PHONY: force_remake
|
||||
define rule_for_arch_executable
|
||||
.PRECIOUS: $$(BUILD_DIR)/$(1)/%.$$(EXE)
|
||||
$$(BUILD_DIR)/$(1)/%.$$(EXE): force_remake
|
||||
$(Q) echo "MAKE ARCH=$(1)"
|
||||
$(Q) $$(MAKE) ARCH=$(1) --silent $$*.$$(EXE)
|
||||
endef
|
||||
|
||||
$(foreach ARCH,$(ARCHS),$(eval $(call rule_for_arch_executable,$(ARCH))))
|
||||
|
||||
endif
|
||||
endif
|
||||
140
build/metrics/binary_size.py
Normal file
140
build/metrics/binary_size.py
Normal file
@@ -0,0 +1,140 @@
|
||||
#!/usr/bin/env python3
|
||||
|
||||
import argparse
|
||||
import os
|
||||
import re
|
||||
import subprocess
|
||||
import urllib.parse
|
||||
|
||||
# ELF analysis
|
||||
|
||||
def loadable_sections(elf_file, address_prefix = ""):
|
||||
objdump_section_headers_pattern = re.compile("^\s+\d+\s+(\.[\w\.]+)\s+([0-9a-f]+)\s+([0-9a-f]+)\s+("+address_prefix+"[0-9a-f]+)\s+([0-9a-f]+).*LOAD", flags=re.MULTILINE)
|
||||
objdump_output = subprocess.check_output(["arm-none-eabi-objdump", "-h", "-w", elf_file]).decode('utf-8')
|
||||
sections = []
|
||||
for (name, size, vma, lma, offset) in re.findall(objdump_section_headers_pattern, objdump_output):
|
||||
int_size = int(size,16)
|
||||
if (int_size > 0):
|
||||
sections.append({'name': name, 'size': int_size, 'vma': int(vma,16), 'lma': int(lma,16), 'offset':int(offset,16)})
|
||||
return sections
|
||||
|
||||
|
||||
# Data filtering
|
||||
|
||||
def biggest_sections(sections, n):
|
||||
sorted_sections = sorted(sections, key=lambda s: s['size'], reverse=True)
|
||||
return sorted_sections[:n]
|
||||
|
||||
def total_size(sections):
|
||||
return sum(map(lambda s: s['size'], sections))
|
||||
|
||||
def row_for_elf(elf, columns):
|
||||
sections = loadable_sections(elf)
|
||||
result = {}
|
||||
for s in biggest_sections(sections, columns):
|
||||
result[s['name']] = s['size']
|
||||
result['Total'] = total_size(sections)
|
||||
return result
|
||||
|
||||
|
||||
# String formatting
|
||||
|
||||
def iso_separate(string):
|
||||
space = ' ' # We may want to use a thin non-breaking space as thousands separator
|
||||
return string.replace('_',space).replace('+','+'+space).replace('-','-'+space)
|
||||
|
||||
def format_bytes(value, force_sign=False):
|
||||
if value is None:
|
||||
return ''
|
||||
number_format = '{:'
|
||||
if force_sign:
|
||||
number_format += '+'
|
||||
number_format += '_} bytes'
|
||||
return iso_separate(number_format.format(value))
|
||||
|
||||
def format_percentage(value):
|
||||
if value is None:
|
||||
return ''
|
||||
return iso_separate("{:+.1f} %".format(100*value))
|
||||
|
||||
|
||||
# Markdown
|
||||
|
||||
def emphasize(string):
|
||||
if string:
|
||||
return '_' + string + '_'
|
||||
else:
|
||||
return ''
|
||||
|
||||
def strong(string):
|
||||
if string:
|
||||
return '**' + string + '**'
|
||||
else:
|
||||
return ''
|
||||
|
||||
|
||||
# Deltas
|
||||
|
||||
def absolute_delta(x,y):
|
||||
if x is None or y is None:
|
||||
return None
|
||||
return x-y
|
||||
|
||||
def ratio_delta(x,y):
|
||||
if x is None or y is None:
|
||||
return None
|
||||
return (x-y)/y
|
||||
|
||||
|
||||
# Table formatting
|
||||
|
||||
def format_row(row, header=False):
|
||||
result = '|'
|
||||
if header:
|
||||
result += strong(header)
|
||||
result += '|'
|
||||
for v in row:
|
||||
result += v
|
||||
result += '|'
|
||||
result += '\n'
|
||||
return result
|
||||
|
||||
def format_table(table):
|
||||
base = table[0]['values']
|
||||
listed_sections = base.keys()
|
||||
result = ''
|
||||
result += format_row(listed_sections)
|
||||
result += '|-|' + '-:|'*len(listed_sections) + '\n'
|
||||
for i,row in enumerate(table):
|
||||
v = row['values']
|
||||
result += format_row((format_bytes(v.get(s)) for s in listed_sections), header=row['label'])
|
||||
if i != 0:
|
||||
result += format_row(emphasize(format_bytes(absolute_delta(v.get(s), base.get(s)), force_sign=True)) for s in listed_sections)
|
||||
result += format_row(emphasize(format_percentage(ratio_delta(v.get(s), base.get(s)))) for s in listed_sections)
|
||||
return result
|
||||
|
||||
|
||||
# Argument parsing
|
||||
|
||||
parser = argparse.ArgumentParser(description='Compute binary size metrics')
|
||||
parser.add_argument('files', type=str, nargs='+', help='an ELF file')
|
||||
parser.add_argument('--labels', type=str, nargs='+', help='label for ELF file')
|
||||
parser.add_argument('--number-of-sections', type=int, default=2, help='Number of detailed sections')
|
||||
parser.add_argument('--escape', action='store_true', help='Escape the output')
|
||||
args = parser.parse_args()
|
||||
|
||||
|
||||
# Execution
|
||||
|
||||
table = []
|
||||
for i,filename in enumerate(args.files):
|
||||
label = os.path.basename(filename)
|
||||
if args.labels and i < len(args.labels):
|
||||
label = args.labels[i]
|
||||
table.append({'label': label, 'values': row_for_elf(filename, args.number_of_sections)})
|
||||
formatted_table = format_table(table)
|
||||
|
||||
if args.escape:
|
||||
print(urllib.parse.quote(formatted_table, safe='| :*+'))
|
||||
else:
|
||||
print(formatted_table)
|
||||
@@ -1,10 +1,12 @@
|
||||
TOOLCHAIN = android
|
||||
EXE = so
|
||||
|
||||
EPSILON_TELEMETRY ?= 1
|
||||
|
||||
ARCHS = armeabi-v7a arm64-v8a x86 x86_64
|
||||
|
||||
ifdef ARCH
|
||||
EXE = so
|
||||
BUILD_DIR := $(BUILD_DIR)/$(ARCH)
|
||||
else
|
||||
HANDY_TARGETS_EXTENSIONS = apk
|
||||
endif
|
||||
|
||||
@@ -6,7 +6,7 @@ APPLE_PLATFORM_MIN_VERSION = 8.0
|
||||
EPSILON_TELEMETRY ?= 1
|
||||
|
||||
ifeq ($(APPLE_PLATFORM),ios)
|
||||
ARCHS ?= arm64 armv7
|
||||
ARCHS = arm64 armv7
|
||||
UI_REQUIRED_CAPABILITIES += armv7
|
||||
else ifeq ($(APPLE_PLATFORM),ios-simulator)
|
||||
ARCHS = x86_64
|
||||
@@ -16,4 +16,6 @@ BUILD_DIR := $(subst $(TARGET),$(APPLE_PLATFORM),$(BUILD_DIR))
|
||||
|
||||
ifdef ARCH
|
||||
BUILD_DIR := $(BUILD_DIR)/$(ARCH)
|
||||
else
|
||||
HANDY_TARGETS_EXTENSIONS = ipa app
|
||||
endif
|
||||
|
||||
@@ -10,4 +10,6 @@ EPSILON_SIMULATOR_HAS_LIBPNG = 1
|
||||
|
||||
ifdef ARCH
|
||||
BUILD_DIR := $(BUILD_DIR)/$(ARCH)
|
||||
else
|
||||
HANDY_TARGETS_EXTENSIONS = app
|
||||
endif
|
||||
|
||||
@@ -1,2 +1,4 @@
|
||||
TOOLCHAIN = emscripten
|
||||
EXE = js
|
||||
|
||||
HANDY_TARGETS_EXTENSIONS += zip
|
||||
|
||||
@@ -1,46 +1,63 @@
|
||||
# Define standard compilation rules
|
||||
|
||||
.PHONY: official_authorization
|
||||
ifeq ($(ACCEPT_OFFICIAL_TOS),1)
|
||||
official_authorization:
|
||||
else
|
||||
official_authorization:
|
||||
@echo "CAUTION: You are trying to build an official NumWorks firmware."
|
||||
@echo "Distribution of such firmware by a third party is prohibited."
|
||||
@echo "Please set the ACCEPT_OFFICIAL_TOS environment variable to proceed."
|
||||
@exit -1
|
||||
endif
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
AS, %.o, %.s, \
|
||||
$$(CC) $$(SFLAGS) -c $$< -o $$@ \
|
||||
$$(CC) $$(SFLAGS) -c $$< -o $$@, \
|
||||
global \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
CC, %.o, %.c, \
|
||||
$$(CC) $$(CFLAGS) $$(SFLAGS) -c $$< -o $$@, \
|
||||
with_local_version \
|
||||
global local \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
CPP, %, %.inc, \
|
||||
$$(CPP) -P $$< $$@, \
|
||||
global \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
CXX, %.o, %.cpp, \
|
||||
$$(CXX) $$(CXXFLAGS) $$(SFLAGS) -c $$< -o $$@, \
|
||||
with_local_version \
|
||||
global local \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
DFUSE, %.dfu, %.elf, \
|
||||
$$(PYTHON) build/device/elf2dfu.py $$< $$@, \
|
||||
local \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
OBJCOPY, %.hex, %.elf, \
|
||||
$$(OBJCOPY) -O ihex $$< $$@, \
|
||||
local \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
OBJCOPY, %.bin, %.elf, \
|
||||
$$(OBJCOPY) -O binary $$< $$@, \
|
||||
local \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
OCC, %.o, %.m, \
|
||||
$$(CC) $$(CFLAGS) $$(SFLAGS) -c $$< -o $$@ \
|
||||
$$(CC) $$(CFLAGS) $$(SFLAGS) -c $$< -o $$@, \
|
||||
global \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
OCC, %.o, %.mm, \
|
||||
$$(CXX) $$(CXXFLAGS) $$(SFLAGS) -c $$< -o $$@ \
|
||||
$$(CXX) $$(CXXFLAGS) $$(SFLAGS) -c $$< -o $$@, \
|
||||
global \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
CPP, %, %.inc, \
|
||||
$$(CPP) -P $$< $$@ \
|
||||
WINDRES, %.o, %.rc, \
|
||||
$$(WINDRES) $$< -O coff -o $$@, \
|
||||
global \
|
||||
))
|
||||
|
||||
ifdef EXE
|
||||
@@ -52,17 +69,14 @@ ifeq ($(OS),Windows_NT)
|
||||
# the linker to read its arguments from this file.
|
||||
$(eval $(call rule_for, \
|
||||
LD, %.$$(EXE), , \
|
||||
echo $$^ > $$@.objs && $$(LD) @$$@.objs $$(LDFLAGS) -o $$@ && rm $$@.objs \
|
||||
echo $$^ > $$@.objs && $$(LD) @$$@.objs $$(LDFLAGS) -o $$@ && rm $$@.objs, \
|
||||
global \
|
||||
))
|
||||
else
|
||||
$(eval $(call rule_for, \
|
||||
LD, %.$$(EXE), , \
|
||||
$$(LD) $$^ $$(LDFLAGS) -o $$@ \
|
||||
$$(LD) $$^ $$(LDFLAGS) -o $$@, \
|
||||
global \
|
||||
))
|
||||
endif
|
||||
endif
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
WINDRES, %.o, %.rc, \
|
||||
$$(WINDRES) $$< -O coff -o $$@ \
|
||||
))
|
||||
|
||||
@@ -1,60 +0,0 @@
|
||||
ANDROID_GRADLE_KEYSTORE ?= ~/.gradle/google-play-upload.keystore
|
||||
ANDROID_GRADLE_PROPERTIES ?= ~/.gradle/gradle.properties
|
||||
IOS_MOBILE_PROVISION ?= build/artifacts/NumWorks_Graphing_Calculator_Distribution.mobileprovision
|
||||
EMCC ?= emcc
|
||||
|
||||
define source_emsdk
|
||||
source ~/emsdk/emsdk_env.sh > /dev/null
|
||||
endef
|
||||
|
||||
define file_check
|
||||
@ if test ! -f $(1); \
|
||||
then \
|
||||
echo "Missing file: $(1)"; \
|
||||
exit 1; \
|
||||
fi
|
||||
endef
|
||||
|
||||
define command_check
|
||||
@ if ! command -v $(1) > /dev/null; \
|
||||
then \
|
||||
echo "Missing command: $(1), did you forget to source?"; \
|
||||
exit 1; \
|
||||
fi
|
||||
endef
|
||||
|
||||
.PHONY: all_official
|
||||
all_official:
|
||||
$(call file_check,$(ANDROID_GRADLE_KEYSTORE))
|
||||
$(call file_check,$(ANDROID_GRADLE_PROPERTIES))
|
||||
$(call file_check,$(IOS_MOBILE_PROVISION))
|
||||
$(call command_check,$(EMCC))
|
||||
$(Q) rm -rf output/all_official
|
||||
$(Q) mkdir -p output/all_official
|
||||
$(Q) echo "BUILD_FIRMWARE DEVICE N0110"
|
||||
$(Q) $(MAKE) clean
|
||||
$(Q) $(MAKE) epsilon.official.onboarding.dfu
|
||||
$(Q) cp output/release/device/n0110/epsilon.official.onboarding.dfu output/all_official/epsilon.device.n0110.dfu
|
||||
$(Q) echo "BUILD_FIRMWARE DEVICE N0100"
|
||||
$(Q) $(MAKE) MODEL=n0100 clean
|
||||
$(Q) $(MAKE) MODEL=n0100 epsilon.official.onboarding.dfu
|
||||
$(Q) cp output/release/device/n0100/epsilon.official.onboarding.dfu output/all_official/epsilon.device.n0100.dfu
|
||||
$(Q) echo "BUILD_FIRMWARE SIMULATOR WEB ZIP"
|
||||
$(Q) $(MAKE) PLATFORM=simulator TARGET=web clean
|
||||
$(Q) $(call source_emsdk); $(MAKE) PLATFORM=simulator TARGET=web epsilon.official.zip
|
||||
$(Q) cp output/release/simulator/web/epsilon.official.zip output/all_official/simulator.web.zip
|
||||
$(Q) echo "BUILD_FIRMWARE SIMULATOR WEB JS"
|
||||
$(Q) $(call source_emsdk); $(MAKE) PLATFORM=simulator TARGET=web epsilon.official.js
|
||||
$(Q) cp output/release/simulator/web/epsilon.official.js output/all_official/epsilon.js
|
||||
$(Q) echo "BUILD_FIRMWARE SIMULATOR WEB PYTHON JS"
|
||||
$(Q) $(MAKE) PLATFORM=simulator TARGET=web clean
|
||||
$(Q) $(call source_emsdk); $(MAKE) PLATFORM=simulator TARGET=web EPSILON_GETOPT=1 EPSILON_APPS=code epsilon.official.js
|
||||
$(Q) cp output/release/simulator/web/epsilon.official.js output/all_official/epsilon.python.js
|
||||
$(Q) echo "BUILD_FIRMWARE SIMULATOR ANDROID"
|
||||
$(Q) $(MAKE) PLATFORM=simulator TARGET=android clean
|
||||
$(Q) $(MAKE) PLATFORM=simulator TARGET=android epsilon.official.signed.apk
|
||||
$(Q) cp output/release/simulator/android/app/outputs/apk/codesigned/android-codesigned.apk output/all_official/epsilon.official.apk
|
||||
$(Q) echo "BUILD_FIRMWARE SIMULATOR IOS"
|
||||
$(Q) $(MAKE) PLATFORM=simulator TARGET=ios clean
|
||||
$(Q) $(MAKE) PLATFORM=simulator TARGET=ios IOS_PROVISIONNING_PROFILE=$(IOS_MOBILE_PROVISION) output/release/simulator/ios/app/epsilon.official.ipa
|
||||
$(Q) cp output/release/simulator/ios/app/epsilon.official.ipa output/all_official/epsilon.ipa
|
||||
@@ -3,23 +3,6 @@ include build/targets.device.$(MODEL).mak
|
||||
HANDY_TARGETS += flasher.light flasher.verbose bench.ram bench.flash
|
||||
HANDY_TARGETS_EXTENSIONS += dfu hex bin
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
DFUSE, %.dfu, %.$$(EXE), \
|
||||
$$(PYTHON) build/device/elf2dfu.py $$< $$@, \
|
||||
with_local_version \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
OBJCOPY, %.hex, %.$$(EXE), \
|
||||
$$(OBJCOPY) -O ihex $$< $$@ \
|
||||
))
|
||||
|
||||
$(eval $(call rule_for, \
|
||||
OBJCOPY, %.bin, %.$$(EXE), \
|
||||
$$(OBJCOPY) -O binary $$< $$@, \
|
||||
with_local_version \
|
||||
))
|
||||
|
||||
%_ram_map: %.$(EXE)
|
||||
$(PYTHON) build/device/ram_map.py $(BUILD_DIR)/$<
|
||||
|
||||
@@ -50,19 +33,19 @@ openocd:
|
||||
|
||||
# The flasher target is defined here because otherwise $(%_src) has not been
|
||||
# fully filled
|
||||
flasher_src = $(ion_src) $(ion_device_flasher_src) $(liba_src) $(kandinsky_src)
|
||||
$(BUILD_DIR)/flasher.light.$(EXE): $(call flavored_object_for,$(flasher_src),light usbxip)
|
||||
$(BUILD_DIR)/flasher.verbose.$(EXE): $(call flavored_object_for,$(flasher_src),usbxip)
|
||||
$(BUILD_DIR)/flasher.%.$(EXE): LDFLAGS += -Lion/src/$(PLATFORM)/flasher
|
||||
$(BUILD_DIR)/flasher.%.$(EXE): LDSCRIPT = ion/src/$(PLATFORM)/shared/ram.ld
|
||||
flasher_base_src = $(ion_xip_src) $(liba_src) $(kandinsky_src)
|
||||
$(BUILD_DIR)/flasher.light.$(EXE): $(call object_for,$(flasher_base_src) $(ion_target_device_flasher_light_src))
|
||||
$(BUILD_DIR)/flasher.verbose.$(EXE): $(call object_for,$(flasher_base_src) $(ion_target_device_flasher_verbose_src))
|
||||
|
||||
#TODO Do not build all apps... Put elsewhere?
|
||||
bench_src = $(ion_src) $(liba_src) $(kandinsky_src) $(poincare_src) $(libaxx_src) $(app_shared_src) $(ion_device_bench_src)
|
||||
$(BUILD_DIR)/bench.ram.$(EXE): $(call flavored_object_for,$(bench_src),consoleuart usbxip)
|
||||
$(BUILD_DIR)/bench.ram.$(EXE): LDFLAGS += -Lion/src/$(PLATFORM)/bench
|
||||
$(BUILD_DIR)/bench.ram.$(EXE): LDSCRIPT = ion/src/$(PLATFORM)/shared/ram.ld
|
||||
$(BUILD_DIR)/bench.flash.$(EXE): $(call flavored_object_for,$(bench_src),consoleuart usbxip)
|
||||
$(BUILD_DIR)/bench.flash.$(EXE): LDSCRIPT = ion/src/$(PLATFORM)/$(MODEL)/internal_flash.ld
|
||||
bench_src = $(ion_xip_src) $(liba_src) $(kandinsky_src) $(poincare_src) $(libaxx_src) $(app_shared_src) $(ion_target_device_bench_src)
|
||||
$(BUILD_DIR)/bench.ram.$(EXE): $(call object_for,$(bench_src))
|
||||
$(BUILD_DIR)/bench.flash.$(EXE): $(call object_for,$(bench_src))
|
||||
|
||||
.PHONY: %.two_binaries
|
||||
%.two_binaries: %.elf
|
||||
|
||||
@@ -1,28 +1,78 @@
|
||||
# Define standard Epsilon targets
|
||||
base_src = $(liba_src) $(kandinsky_src) $(escher_src) $(libaxx_src) $(poincare_src) $(python_src)
|
||||
|
||||
epsilon_src = $(base_src) $(ion_default_src) $(apps_default_src)
|
||||
epsilon_official_src = $(base_src) $(ion_default_src) $(apps_official_default_src)
|
||||
|
||||
$(BUILD_DIR)/epsilon.$(EXE): $(call object_for,$(epsilon_src))
|
||||
$(BUILD_DIR)/epsilon.official.$(EXE): $(call object_for,$(epsilon_official_src))
|
||||
$(BUILD_DIR)/epsilon.onboarding.$(EXE): $(call object_for, $(base_src) $(ion_default_src) $(apps_onboarding_src))
|
||||
$(BUILD_DIR)/epsilon.official.onboarding.$(EXE): $(call object_for,$(base_src) $(ion_default_src) $(apps_official_onboarding_src))
|
||||
$(BUILD_DIR)/epsilon.onboarding.update.$(EXE): $(call object_for, $(base_src) $(ion_default_src) $(apps_onboarding_update_src))
|
||||
$(BUILD_DIR)/epsilon.official.onboarding.update.$(EXE): $(call object_for,$(base_src) $(ion_default_src) $(apps_official_onboarding_update_src))
|
||||
$(BUILD_DIR)/epsilon.onboarding.beta.$(EXE): $(call object_for, $(base_src) $(ion_default_src) $(apps_onboarding_beta_src))
|
||||
$(BUILD_DIR)/epsilon.official.onboarding.beta.$(EXE): $(call object_for,$(base_src) $(ion_default_src) $(apps_official_onboarding_beta_src))
|
||||
|
||||
test_base_src = $(base_src) $(apps_tests_src) $(runner_src) $(tests_src)
|
||||
|
||||
test_runner_src = $(test_base_src) $(ion_console_on_screen_src)
|
||||
$(BUILD_DIR)/test.$(EXE): $(call object_for,$(test_runner_src))
|
||||
|
||||
# Define handy targets
|
||||
# Those can be built easily by simply invoking "make target.ext". The named file
|
||||
# will be built in $(BUILD_DIR).
|
||||
|
||||
HANDY_TARGETS += epsilon epsilon.official epsilon.onboarding epsilon.official.onboarding epsilon.onboarding.update epsilon.official.onboarding.update epsilon.onboarding.beta epsilon.official.onboarding.beta test
|
||||
HANDY_TARGETS ?=
|
||||
HANDY_TARGETS_EXTENSIONS ?=
|
||||
|
||||
# Epsilon base target
|
||||
|
||||
base_src = $(ion_src) $(liba_src) $(kandinsky_src) $(escher_src) $(libaxx_src) $(poincare_src) $(python_src)
|
||||
|
||||
epsilon_src = $(base_src) $(apps_src)
|
||||
|
||||
$(BUILD_DIR)/epsilon.$(EXE): $(call flavored_object_for,$(epsilon_src))
|
||||
|
||||
HANDY_TARGETS += epsilon
|
||||
|
||||
# Epsilon flavored targets
|
||||
|
||||
epsilon_flavors = \
|
||||
onboarding \
|
||||
onboarding.update \
|
||||
onboarding.beta
|
||||
|
||||
define rule_for_epsilon_flavor
|
||||
$$(BUILD_DIR)/epsilon.$(1).$$(EXE): $$(call flavored_object_for,$$(epsilon_src),$(1))
|
||||
endef
|
||||
|
||||
$(foreach flavor,$(epsilon_flavors),$(eval $(call rule_for_epsilon_flavor,$(flavor))))
|
||||
|
||||
HANDY_TARGETS += $(foreach flavor,$(epsilon_flavors),epsilon.$(flavor))
|
||||
|
||||
# Epsilon official targets
|
||||
|
||||
epsilon_official_flavors = \
|
||||
official \
|
||||
official.onboarding \
|
||||
official.onboarding.update \
|
||||
official.onboarding.beta
|
||||
|
||||
define rule_for_unconfirmed_official_flavor
|
||||
$$(BUILD_DIR)/epsilon.$(1).$$(EXE):
|
||||
@echo "CAUTION: You are trying to build an official NumWorks firmware."
|
||||
@echo "Distribution of such firmware by a third party is prohibited."
|
||||
@echo "Please set the ACCEPT_OFFICIAL_TOS environment variable to proceed."
|
||||
@exit -1
|
||||
endef
|
||||
|
||||
ifeq ($(ACCEPT_OFFICIAL_TOS),1)
|
||||
rule_for_official_epsilon_flavor = rule_for_epsilon_flavor
|
||||
else
|
||||
rule_for_official_epsilon_flavor = rule_for_unconfirmed_official_flavor
|
||||
endif
|
||||
|
||||
$(foreach flavor,$(epsilon_official_flavors),$(eval $(call $(rule_for_official_epsilon_flavor),$(flavor))))
|
||||
|
||||
HANDY_TARGETS += $(foreach flavor,$(epsilon_official_flavors),epsilon.$(flavor))
|
||||
|
||||
# Test
|
||||
|
||||
test_runner_src = $(base_src) $(apps_tests_src) $(runner_src) $(tests_src)
|
||||
|
||||
$(BUILD_DIR)/test.$(EXE): $(call flavored_object_for,$(test_runner_src),consoledisplay)
|
||||
|
||||
HANDY_TARGETS += test
|
||||
|
||||
# Load platform-specific targets
|
||||
# We include them before the standard ones to give them precedence.
|
||||
-include build/targets.$(PLATFORM).mak
|
||||
|
||||
# Generate handy targets rules
|
||||
# Define handy targets
|
||||
# Those can be built easily by simply invoking "make target.ext". The named file
|
||||
# will be built in $(BUILD_DIR).
|
||||
|
||||
HANDY_TARGETS_EXTENSIONS += $(EXE)
|
||||
|
||||
define handy_target_rule
|
||||
@@ -30,10 +80,4 @@ define handy_target_rule
|
||||
$(1).$(2): $$(BUILD_DIR)/$(1).$(2)
|
||||
endef
|
||||
|
||||
# Load platform-specific targets
|
||||
# We include them before the standard ones to give them precedence.
|
||||
-include build/targets.$(PLATFORM).mak
|
||||
|
||||
$(foreach extension,$(HANDY_TARGETS_EXTENSIONS),$(foreach executable,$(HANDY_TARGETS),$(eval $(call handy_target_rule,$(executable),$(extension)))))
|
||||
|
||||
include build/targets.all.mak
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
ifndef ARCH
|
||||
HANDY_TARGETS_EXTENSIONS += apk
|
||||
endif
|
||||
.PHONY: %_run
|
||||
%_run: $(BUILD_DIR)/%.apk
|
||||
$(call rule_label,ADB)
|
||||
$(Q) adb install $<
|
||||
|
||||
6
build/targets.simulator.ios.mak
Normal file
6
build/targets.simulator.ios.mak
Normal file
@@ -0,0 +1,6 @@
|
||||
ifeq ($(APPLE_PLATFORM),ios-simulator)
|
||||
.PHONY: %_run
|
||||
%_run: $(BUILD_DIR)/%.app
|
||||
$(call rule_label,XCRUN)
|
||||
$(Q) xcrun simctl install booted $^
|
||||
endif
|
||||
@@ -1,10 +1,8 @@
|
||||
# Headless targets
|
||||
epsilon_headless_src = $(base_src) $(ion_headless_src) $(apps_default_src)
|
||||
$(BUILD_DIR)/epsilon.headless.$(EXE): $(call object_for,$(epsilon_headless_src))
|
||||
$(eval $(call rule_for_epsilon_flavor,headless))
|
||||
HANDY_TARGETS += epsilon.headless
|
||||
|
||||
test_runner_headless_src = $(test_base_src) $(ion_headless_src)
|
||||
$(BUILD_DIR)/test.headless.$(EXE): $(call object_for,$(test_runner_headless_src))
|
||||
|
||||
HANDY_TARGETS += epsilon.headless test.headless
|
||||
$(BUILD_DIR)/test.headless.$(EXE): $(call flavored_object_for,$(test_runner_src),headless)
|
||||
HANDY_TARGETS += test.headless
|
||||
|
||||
-include build/targets.simulator.$(TARGET).mak
|
||||
|
||||
@@ -1,3 +1 @@
|
||||
HANDY_TARGETS_EXTENSIONS += zip
|
||||
|
||||
$(BUILD_DIR)/test.headless.js: EMSCRIPTEN_MODULARIZE = 0
|
||||
|
||||
63
build/variants.mak
Normal file
63
build/variants.mak
Normal file
@@ -0,0 +1,63 @@
|
||||
# Helper functions to work with variants
|
||||
# Make variants_test for an example
|
||||
|
||||
define available_variants_in
|
||||
$(sort $(patsubst +%,%,$(filter +%,$(subst :, ,$(1)))))
|
||||
endef
|
||||
|
||||
define without_any_variant_specifier
|
||||
$(filter-out $(foreach variant,$(call available_variants_in,$(1)),%:-$(variant) %:+$(variant)),$(1))
|
||||
endef
|
||||
|
||||
define with_variant_specifier_matching
|
||||
$(foreach variant,$(3),$(patsubst %:$(1)$(variant),%,$(filter %:$(1)$(variant),$(2))))
|
||||
endef
|
||||
|
||||
define without_any_variant_specifier_matching
|
||||
$(filter-out \
|
||||
$(call with_variant_specifier_matching,$(1),$(2),$(3)), \
|
||||
$(foreach variant,$(call available_variants_in,$(2)),$(call with_variant_specifier_matching,$(1),$(2),$(variant))) \
|
||||
)
|
||||
endef
|
||||
|
||||
# Return files in $(1) that match the variant $(2)
|
||||
define filter_variants
|
||||
$(sort \
|
||||
$(call without_any_variant_specifier,$(1)) \
|
||||
$(call with_variant_specifier_matching,+,$(1),$(2)) \
|
||||
$(call without_any_variant_specifier_matching,-,$(1),$(2)) \
|
||||
)
|
||||
endef
|
||||
|
||||
# Return all files in $(1) no matter their variant
|
||||
define any_variant
|
||||
$(sort $(filter-out -%,$(filter-out +%,$(subst :, ,$(1)))))
|
||||
endef
|
||||
|
||||
# Examples
|
||||
|
||||
variants_test_src = base.cpp
|
||||
variants_test_src += color/green.cpp:+green
|
||||
variants_test_src += color/red.cpp:+red
|
||||
variants_test_src += color/blue.cpp:-red
|
||||
variants_test_src += color/blue.cpp:-green
|
||||
variants_test_src += engine/fast.cpp:+nitro
|
||||
variants_test_src += engine/slow.cpp:-nitro
|
||||
|
||||
.PHONY: variants_test
|
||||
variants_test:
|
||||
$(info AVAILABLE_VARIANTS_IN)
|
||||
$(info --result: $(call available_variants_in,$(variants_test_src),))
|
||||
$(info --expected: green nitro red)
|
||||
$(info FILTER_VARIANTS)
|
||||
$(info --result: $(call filter_variants,$(variants_test_src),))
|
||||
$(info --expected: base.cpp color/blue.cpp engine/slow.cpp)
|
||||
$(info FILTER_VARIANTS red)
|
||||
$(info --result: $(call filter_variants,$(variants_test_src),red))
|
||||
$(info --expected: base.cpp color/red.cpp engine/slow.cpp)
|
||||
$(info FILTER_VARIANTS green speed)
|
||||
$(info --result: $(call filter_variants,$(variants_test_src),green nitro))
|
||||
$(info --expected: base.cpp color/green.cpp engine/fast.cpp)
|
||||
$(info ANY_VARIANT)
|
||||
$(info --result: $(call any_variant,$(variants_test_src)))
|
||||
$(info --expected: base.cpp color/blue.cpp color/green.cpp color/red.cpp engine/fast.cpp engine/slow.cpp)
|
||||
Reference in New Issue
Block a user