CC := gcc
TASIGN_TOOL ?= $(shell which tasign-tool 2>/dev/null || echo "~/.cargo/bin/tasign-tool")
SIGN_ALGORITHM ?= sm2-sm3
LEAF_CERT ?= TEST
INTERMEDIATE_CERT ?= TEST
INTERMEDIATE_COUNT ?= 1
LEAF_KEY ?= TEST
LEAF_KEY_PASS ?= TEST
SIGN_OUTPUT_DIR ?= signed
DEBUG ?= 0
ANDROID_CC := $(ANDROID_NDK_HOME)/toolchains/llvm/prebuilt/linux-x86_64/bin/$(ANDROID_TARGET)$(ANDROID_API_LEVEL)-clang
ANDROID_OBJCOPY := $(ANDROID_NDK_HOME)/toolchains/llvm/prebuilt/linux-x86_64/bin/llvm-objcopy
ANDROID_LIB_DIR := $(CURDIR)/../target/$(ANDROID_TARGET)/release
ANDROID_SIGN_OUTPUT_DIR := signed-android
CC_TEEC_TARGET := cc-teec
KYBOX_TEST_TARGET := kybox-test
KYDE_TEST_TARGET := kyde-test
TARGETS := $(CC_TEEC_TARGET) $(KYBOX_TEST_TARGET) $(KYDE_TEST_TARGET)
TEE_CLIENT_SRC := tee_client.c
CC_TEEC_SRCS := cc-teec.c $(TEE_CLIENT_SRC)
KYBOX_TEST_SRCS := kybox-test.c $(TEE_CLIENT_SRC)
KYDE_TEST_SRCS := kyde-test.c $(TEE_CLIENT_SRC)
ALL_SRCS := $(CC_TEEC_SRCS) $(KYBOX_TEST_SRCS) $(KYDE_TEST_SRCS)
INC_DIR := include
BASE_CFLAGS := \
-I$(INC_DIR) \
-D_GNU_SOURCE \
-DBINARY_PREFIX=\"TEEC\" \
-std=gnu11
SECURITY_CFLAGS := \
-Wall \
-Werror \
-Wextra \
-Wformat-security \
-Wstrict-prototypes \
-Wshadow \
-Wunused \
-Wcast-align \
-Wpointer-arith
SECURITY_LDFLAGS := \
-Wl,--as-needed \
-Wl,-z,relro \
-Wl,-z,now \
-Wl,-z,noexecstack \
-Wl,--no-undefined \
-Wl,--fatal-warnings
PIE_CFLAGS := -fPIE -fpie
PIE_LDFLAGS := -pie
STACK_PROTECTOR := -fstack-protector-strong
ifeq ($(BUILD_MODE), release)
OPTIMIZE_CFLAGS := -O2
OPTIMIZE_LDFLAGS := -s
else
OPTIMIZE_CFLAGS := -O0 -ggdb3
OPTIMIZE_LDFLAGS := -g
endif
ifeq ($(DEBUG), 1)
DEBUG_CFLAGS := -g3
DEBUG_LDFLAGS := -g
else
DEBUG_CFLAGS :=
DEBUG_LDFLAGS :=
endif
CFLAGS := \
$(BASE_CFLAGS) \
$(SECURITY_CFLAGS) \
$(PIE_CFLAGS) \
$(STACK_PROTECTOR) \
$(OPTIMIZE_CFLAGS) \
$(DEBUG_CFLAGS)
LDFLAGS := \
$(PIE_LDFLAGS) \
$(SECURITY_LDFLAGS) \
$(OPTIMIZE_LDFLAGS) \
$(DEBUG_LDFLAGS)
LIBS := -l$(RUST_LIB_NAME)
.PHONY: all
all: check-tasign $(TARGETS) sign-all
.PHONY: check-tasign
check-tasign:
@if [ ! -x "$(TASIGN_TOOL)" ]; then \
echo "Error: tasign-tool not found at $(TASIGN_TOOL)"; \
echo "Please install tasign-tool:"; \
echo " cargo install tasign --force"; \
echo "Or set TASIGN_TOOL environment variable to the correct path"; \
exit 1; \
fi
@echo "Using tasign-tool: $(TASIGN_TOOL)"
define BUILD_TARGET
$(1): $(2) $$(RUST_TARGET_BUILD_DIR)/$$(RUST_LIB_FILE)
@if [ ! -f "$$(RUST_TARGET_BUILD_DIR)/$$(RUST_LIB_FILE)" ]; then \
echo "Error: Rust library $$(RUST_LIB_FILE) not found in $$(RUST_TARGET_BUILD_DIR)"; \
echo "Please build the Rust library first: cd .. && cargo build --release"; \
exit 1; \
fi; \
echo "Using Rust library: $$(RUST_TARGET_BUILD_DIR)/$$(RUST_LIB_FILE)"; \
$$(CC) $$(CFLAGS) $$(LDFLAGS) -o $$@ $$^ -L$$(RUST_TARGET_BUILD_DIR) $$(LIBS)
endef
$(eval $(call BUILD_TARGET,$(CC_TEEC_TARGET),$(CC_TEEC_SRCS)))
$(eval $(call BUILD_TARGET,$(KYBOX_TEST_TARGET),$(KYBOX_TEST_SRCS)))
$(eval $(call BUILD_TARGET,$(KYDE_TEST_TARGET),$(KYDE_TEST_SRCS)))
.PHONY: sign-all
sign-all: $(addprefix sign-,$(TARGETS))
.PHONY: sign-%
sign-%: %
@echo "Signing $<..."
@ @if objdump -h $< | grep -q ".ta_signature"; then \
echo "Removing existing .ta_signature section..."; \
objcopy --remove-section .ta_signature $< $<.tmp && mv $<.tmp $<; \
fi
@mkdir -p $(SIGN_OUTPUT_DIR)/$<
@$(TASIGN_TOOL) sign \
--elf $< \
--out-dir $(SIGN_OUTPUT_DIR)/$< \
--leaf-cert $(LEAF_CERT) \
--intermediate-cert $(INTERMEDIATE_CERT) \
--intermediate-count $(INTERMEDIATE_COUNT) \
--algorithm $(SIGN_ALGORITHM) \
--leaf-key $(LEAF_KEY) \
--leaf-key-pass $(LEAF_KEY_PASS)
@$(TASIGN_TOOL) write-elf \
--input-elf $< \
--signature-bin $(SIGN_OUTPUT_DIR)/$</signature.bin \
--output-elf $< \
--objcopy objcopy
@$(TASIGN_TOOL) verify-elf --elf $< --ca-cert $(LEAF_CERT) && \
echo "✓ Successfully signed and verified: $<" || \
(echo "✗ Signature verification failed for $<"; exit 1)
.PHONY: clean
clean:
rm -rf $(TARGETS) $(SIGN_OUTPUT_DIR) $(ANDROID_SIGN_OUTPUT_DIR)
android-ndk-check:
@if [ -z "$(ANDROID_NDK_HOME)" ]; then \
echo "Error: ANDROID_NDK_HOME is not set. Please export ANDROID_NDK_HOME=/path/to/android-ndk-r29"; \
exit 1; \
fi
define ANDROID_BUILD_TARGET
android-$(1): android-ndk-check
@if [ ! -f "$$(ANDROID_CC)" ]; then \
echo "Error: NDK compiler not found at $$(ANDROID_CC)"; \
echo "Set ANDROID_NDK_HOME to your NDK installation path"; \
exit 1; \
fi
@if [ ! -f "$$(ANDROID_LIB_DIR)/$$(RUST_LIB_FILE)" ]; then \
echo "Error: $$(RUST_LIB_FILE) not found at $$(ANDROID_LIB_DIR)"; \
echo "Build it first: cd .. && make android"; \
exit 1; \
fi
@echo "Building $(1) for Android $$(ANDROID_TARGET)..."
$$(ANDROID_CC) $$(BASE_CFLAGS) $$(SECURITY_CFLAGS) -fstack-protector-strong -fPIE -O2 \
-I$$(INC_DIR) -o $(1) $(2) \
-L$$(ANDROID_LIB_DIR) -Wl,-rpath,/vendor/lib64 -l$$(RUST_LIB_NAME) -ldl
@echo "Android build completed: $(1)"
endef
$(eval $(call ANDROID_BUILD_TARGET,$(CC_TEEC_TARGET),$(CC_TEEC_SRCS)))
$(eval $(call ANDROID_BUILD_TARGET,$(KYBOX_TEST_TARGET),$(KYBOX_TEST_SRCS)))
$(eval $(call ANDROID_BUILD_TARGET,$(KYDE_TEST_TARGET),$(KYDE_TEST_SRCS)))
android: android-$(CC_TEEC_TARGET) android-$(KYBOX_TEST_TARGET) android-$(KYDE_TEST_TARGET)
define ANDROID_SIGN_TARGET
android-sign-$(1): android-$(1)
@echo "Signing $(1) (Android)..."
@if $$(ANDROID_OBJCOPY) --dump-section .ta_signature=/dev/null $(1) 2>/dev/null; then \
echo "Removing existing .ta_signature section..."; \
$$(ANDROID_OBJCOPY) --remove-section .ta_signature $(1) $(1).tmp && mv $(1).tmp $(1); \
fi
@mkdir -p $$(ANDROID_SIGN_OUTPUT_DIR)/$(1)
@$$(TASIGN_TOOL) sign \
--elf $(1) \
--out-dir $$(ANDROID_SIGN_OUTPUT_DIR)/$(1) \
--leaf-cert $$(LEAF_CERT) \
--intermediate-cert $$(INTERMEDIATE_CERT) \
--intermediate-count $$(INTERMEDIATE_COUNT) \
--algorithm $$(SIGN_ALGORITHM) \
--leaf-key $$(LEAF_KEY) \
--leaf-key-pass $$(LEAF_KEY_PASS)
@$$(TASIGN_TOOL) write-elf \
--input-elf $(1) \
--signature-bin $$(ANDROID_SIGN_OUTPUT_DIR)/$(1)/signature.bin \
--output-elf $(1) \
--objcopy $$(ANDROID_OBJCOPY)
@$$(TASIGN_TOOL) verify-elf --elf $(1) --ca-cert $$(LEAF_CERT) && \
echo "✓ Successfully signed and verified: $(1) (Android)" || \
(echo "✗ Signature verification failed for $(1) (Android)"; exit 1)
endef
$(eval $(call ANDROID_SIGN_TARGET,$(CC_TEEC_TARGET)))
$(eval $(call ANDROID_SIGN_TARGET,$(KYBOX_TEST_TARGET)))
$(eval $(call ANDROID_SIGN_TARGET,$(KYDE_TEST_TARGET)))
android-sign: android-sign-$(CC_TEEC_TARGET) android-sign-$(KYBOX_TEST_TARGET) android-sign-$(KYDE_TEST_TARGET)
.PHONY: all check-tasign sign-all sign-% clean \
android-ndk-check android android-sign \
android-$(CC_TEEC_TARGET) android-$(KYBOX_TEST_TARGET) android-$(KYDE_TEST_TARGET) \
android-sign-$(CC_TEEC_TARGET) android-sign-$(KYBOX_TEST_TARGET) android-sign-$(KYDE_TEST_TARGET)