DEVICE := NRF51 DEVICESERIES := nrf51 SDK_INCLUDE_PATH = $(SDK_PATH)/Include/ SDK_SOURCE_PATH = $(SDK_PATH)/Source/ # TEMPLATE_PATH += $(SDK_SOURCE_PATH)/templates/gcc/ OUTPUT_BINARY_DIRECTORY := _build ifeq ($(OS),Windows_NT) include $(TEMPLATE_PATH)Makefile.windows else include $(TEMPLATE_PATH)Makefile.posix endif ifeq ($(LINKER_SCRIPT),) ifeq ($(USE_SOFTDEVICE), S110) LINKER_SCRIPT = gcc_$(DEVICESERIES)_s110_$(DEVICE_VARIANT).ld OUTPUT_FILENAME := $(OUTPUT_FILENAME)_s110_$(DEVICE_VARIANT) STARTADDRESS = 0x16000 else ifeq ($(USE_SOFTDEVICE), S210) LINKER_SCRIPT = gcc_$(DEVICESERIES)_s210_$(DEVICE_VARIANT).ld OUTPUT_FILENAME := $(OUTPUT_FILENAME)_s210_$(DEVICE_VARIANT) STARTADDRESS = 0x16000 else LINKER_SCRIPT = gcc_$(DEVICESERIES)_blank_$(DEVICE_VARIANT).ld OUTPUT_FILENAME := $(OUTPUT_FILENAME)_$(DEVICE_VARIANT) STARTADDRESS = 0x0 endif endif else # Use externally defined settings endif CPU := cortex-m0 # Toolchain commands JLINK := JLinkExe -Device nrf51822 -speed 100 -if swd CC := "$(GNU_INSTALL_ROOT)/bin/$(GNU_PREFIX)-gcc" AS := "$(GNU_INSTALL_ROOT)/bin/$(GNU_PREFIX)-as" AR := "$(GNU_INSTALL_ROOT)/bin/$(GNU_PREFIX)-ar" -r LD := "$(GNU_INSTALL_ROOT)/bin/$(GNU_PREFIX)-ld" NM := "$(GNU_INSTALL_ROOT)/bin/$(GNU_PREFIX)-nm" OBJDUMP := "$(GNU_INSTALL_ROOT)/bin/$(GNU_PREFIX)-objdump" OBJCOPY := "$(GNU_INSTALL_ROOT)/bin/$(GNU_PREFIX)-objcopy" MK := mkdir RM := rm -rf OBJECT_DIRECTORY := _build LISTING_DIRECTORY := _build C_SOURCE_FILES += system_$(DEVICESERIES).c ASSEMBLER_SOURCE_FILES += gcc_startup_$(DEVICESERIES).s # Linker flags #LDFLAGS += -L"$(GNU_INSTALL_ROOT)/arm-none-eabi/lib/armv6-m" #LDFLAGS += -L"$(GNU_INSTALL_ROOT)/lib/gcc/arm-none-eabi/$(GNU_VERSION)/armv6-m" LDFLAGS += -Xlinker -Map=$(LISTING_DIRECTORY)/$(OUTPUT_FILENAME).map LDFLAGS += -mcpu=$(CPU) -mthumb -mabi=aapcs -L $(TEMPLATE_PATH) -T$(LINKER_SCRIPT) # Compiler flags CFLAGS += -mcpu=$(CPU) -mthumb -mabi=aapcs -D$(DEVICE) -D$(BOARD) -D$(TARGET_CHIP) --std=gnu99 CFLAGS += -Wall -Werror CFLAGS += -mfloat-abi=soft # Assembler flags ASMFLAGS += -x assembler-with-cpp INCLUDEPATHS += -I"$(SDK_PATH)Include" INCLUDEPATHS += -I"$(SDK_PATH)Include/gcc" INCLUDEPATHS += -I"$(SDK_PATH)Include/console" INCLUDEPATHS += -I"$(SDK_PATH)Include/nrf_assert" INCLUDEPATHS += -I"$(SDK_PATH)Include/sdk" INCLUDEPATHS += -I"$(SDK_PATH)Include/app_common" INCLUDEPATHS += -I"$(SDK_PATH)Include/sd_common" INCLUDEPATHS += -I"$(SDK_PATH)Include/ble" INCLUDEPATHS += -I"$(SDK_PATH)Include/ble/ble_services" INCLUDEPATHS += -I"$(SDK_PATH)Include/ble/device_manager" INCLUDEPATHS += -I"$(SDK_PATH)Include/ble/device_manager/experimental" INCLUDEPATHS += -I"$(SDK_PATH)Include/ext_sensors" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/common" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/common/transport" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/common/struct_ser" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/connectivity" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/connectivity/codecs" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/application/transport" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/application/codecs/common" INCLUDEPATHS += -I"$(SDK_PATH)Include/serialization/application/codecs/s110/serializers" ifeq ($(USE_SOFTDEVICE), S110) INCLUDEPATHS += -I"$(SDK_PATH)Include/s110" else ifeq ($(USE_SOFTDEVICE), S210) INCLUDEPATHS += -I"$(SDK_PATH)Include/s120" else INCLUDEPATHS += -I"$(SDK_PATH)Include/sdk_soc" endif endif # Sorting removes duplicates BUILD_DIRECTORIES := $(sort $(OBJECT_DIRECTORY) $(OUTPUT_BINARY_DIRECTORY) $(LISTING_DIRECTORY) ) #################################################################### # Rules # #################################################################### C_SOURCE_FILENAMES = $(notdir $(C_SOURCE_FILES) ) ASSEMBLER_SOURCE_FILENAMES = $(notdir $(ASSEMBLER_SOURCE_FILES) ) # Make a list of source paths C_SOURCE_PATHS += $(SDK_SOURCE_PATH) $(TEMPLATE_PATH) $(wildcard $(SDK_SOURCE_PATH)*/) $(wildcard $(SDK_SOURCE_PATH)ext_sensors/*/) $(wildcard $(SDK_SOURCE_PATH)ble/*/) $(BUILD_SCRIPTS_PATH) ASSEMBLER_SOURCE_PATHS = $(SDK_SOURCE_PATH) $(TEMPLATE_PATH) $(wildcard $(SDK_SOURCE_PATH)*/) $(BUILD_SCRIPTS_PATH) C_OBJECTS = $(addprefix $(OBJECT_DIRECTORY)/, $(C_SOURCE_FILENAMES:.c=.o) ) ASSEMBLER_OBJECTS = $(addprefix $(OBJECT_DIRECTORY)/, $(ASSEMBLER_SOURCE_FILENAMES:.s=.o) ) # Set source lookup paths vpath %.c $(C_SOURCE_PATHS) vpath %.s $(ASSEMBLER_SOURCE_PATHS) # Include automatically previously generated dependencies -include $(addprefix $(OBJECT_DIRECTORY)/, $(COBJS:.o=.d)) ### Targets # debug: OUTPUT_FILENAME:=$(OUTPUT_FILENAME)-debug debug: CFLAGS += -DDEBUG -g3 -O0 debug: ASMFLAGS += -DDEBUG -g3 -O0 debug: $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).hex .PHONY: release # release: OUTPUT_FILENAME:=$(OUTPUT_FILENAME)-release release: CFLAGS += -DNDEBUG -O3 release: ASMFLAGS += -DNDEBUG -O3 release: $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).hex echostuff: @echo C_OBJECTS: [$(C_OBJECTS)] @echo C_SOURCE_FILES: [$(C_SOURCE_FILES)] @echo C_SOURCE_PATHS: [$(C_SOURCE_PATHS)] ## Create build directories $(BUILD_DIRECTORIES): $(MK) $@ ## Create objects from C source files $(OBJECT_DIRECTORY)/%.o: %.c # Build header dependencies $(CC) $(CFLAGS) $(INCLUDEPATHS) -M $< -MF "$(@:.o=.d)" -MT $@ # Do the actual compilation $(CC) $(CFLAGS) $(INCLUDEPATHS) -g -c -o $@ $< ## Assemble .s files $(OBJECT_DIRECTORY)/%.o: %.s $(CC) $(ASMFLAGS) $(INCLUDEPATHS) -c -o $@ $< ## Link C and assembler objects to an .out file $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).out: $(BUILD_DIRECTORIES) $(C_OBJECTS) $(ASSEMBLER_OBJECTS) $(LIBRARIES) $(CC) $(LDFLAGS) $(C_OBJECTS) $(ASSEMBLER_OBJECTS) $(LIBRARIES) -o $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).out ## Create binary .bin file from the .out file $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin: $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).out $(OBJCOPY) -O binary $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).out $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin ## Create binary .hex file from the .out file $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).hex: $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).out $(OBJCOPY) -O ihex $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).out $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).hex ## Default build target .PHONY: all all: clean debug clean: $(RM) $(OUTPUT_BINARY_DIRECTORY) $(OUTPUT_BINARY_DIRECTORY)/erase_all.jlink : $(BUILD_DIRECTORIES) echo " \ r \n\ h \n\ w4 0x4001e504,2 # enable erase all \n\ w4 0x4001e50c,1 # start erasing \n\ sleep 1000 \n\ w4 0x4001e514,1 # start erasing UICR \n\ sleep 500 \n\ r \n\ q \n\ " \ > $(OUTPUT_BINARY_DIRECTORY)/erase_all.jlink erase_all: $(OUTPUT_BINARY_DIRECTORY)/erase_all.jlink $(JLINK) -CommanderScript $(OUTPUT_BINARY_DIRECTORY)/erase_all.jlink; [ "$$?" -eq 1 ] $(OUTPUT_BINARY_DIRECTORY)/softdevice.bin: $(BUILD_DIRECTORIES) $(OBJCOPY) -I ihex -O binary $(SOFTDEVICE_HEX_PATH) $(OUTPUT_BINARY_DIRECTORY)/softdevice.bin $(OUTPUT_BINARY_DIRECTORY)/flash_softdevice.jlink: $(BUILD_DIRECTORIES) echo " \n\ r \n\ h \n\ w4 0x4001e504,2 # enable erase \n\ w4 0x4001e50c,1 # start erasing all \n\ sleep 1000 \n\ w4 0x4001e514,1 # start erasing UICR \n\ sleep 500 \n\ w4 0x10001000, $(STARTADDRESS) # write code region size \n\ sleep 1000 \n\ w4 0x4001e504,1 \n\ sleep 1000 \n\ loadbin \"$(OUTPUT_BINARY_DIRECTORY)/softdevice.bin\", 0x0 \n\ verifybin \"$(OUTPUT_BINARY_DIRECTORY)/softdevice.bin\", 0x0 \n\ r \n\ qc \n\ " > $(OUTPUT_BINARY_DIRECTORY)/flash_softdevice.jlink flash_softdevice: $(OUTPUT_BINARY_DIRECTORY)/flash_softdevice.jlink $(OUTPUT_BINARY_DIRECTORY)/softdevice.bin $(JLINK) -CommanderScript $(OUTPUT_BINARY_DIRECTORY)/flash_softdevice.jlink; [ "$$?" -eq 1 ] $(OUTPUT_BINARY_DIRECTORY)/flash.jlink: $(BUILD_DIRECTORIES) $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin echo " \n\ r \n\ h \n\ w4 0x4001e504,2 # enable erase \n\ " > $(OUTPUT_BINARY_DIRECTORY)/flash.jlink binsize=`stat -f %z $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin`; \ starthexaddr=$(STARTADDRESS); \ startaddr=`printf "%d" $$starthexaddr`; \ page=0; \ while [ $$binsize -gt 0 ]; \ do \ echo "w4 0x4001e508, $$starthexaddr # start erasing code region 1 page $$page\n" >> $(OUTPUT_BINARY_DIRECTORY)/flash.jlink ; \ binsize=`expr $$binsize - 1024`; \ page=`expr $$page + 1`; \ startaddr=`expr $$startaddr + 1024`; \ starthexaddr=`printf "0x%x" $$startaddr`; \ done echo "sleep 1000 \n\ r \n\ w4 0x4001e504,1 # enable write \n\ loadbin \"$(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin\", $(STARTADDRESS)\n\ verifybin \"$(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).bin\", $(STARTADDRESS)\n\ r \n\ g \n\ qc \n\ " >> $(OUTPUT_BINARY_DIRECTORY)/flash.jlink flash: $(OUTPUT_BINARY_DIRECTORY)/flash.jlink $(JLINK) -CommanderScript $(OUTPUT_BINARY_DIRECTORY)/flash.jlink; [ "$$?" -eq 1 ] $(OUTPUT_BINARY_DIRECTORY)/pinreset.jlink: $(BUILD_DIRECTORIES) echo "\n\ r \n\ h \n\ w4 4001e504 2 \n\ w4 40000544 1 \n\ r \n\ qc \n\ " > $(OUTPUT_BINARY_DIRECTORY)/pinreset.jlink pin-reset: $(OUTPUT_BINARY_DIRECTORY)/pinreset.jlink $(JLINK) -CommanderScript $(OUTPUT_BINARY_DIRECTORY)/pinreset.jlink; [ "$$?" -eq 1 ] START_GDB_SERVER_SCRIPT=$(OUTPUT_BINARY_DIRECTORY)/start_gdbserver.sh $(START_GDB_SERVER_SCRIPT): $(BUILD_DIRECTORIES) echo "JLinkGDBServer -if swd -device nrf51822 -LocalHostOnly" > $(START_GDB_SERVER_SCRIPT) gdbserver: $(START_GDB_SERVER_SCRIPT) /bin/sh $(START_GDB_SERVER_SCRIPT) GDB_COMMAND_SCRIPT=$(OUTPUT_BINARY_DIRECTORY)/gdbinit $(GDB_COMMAND_SCRIPT): debug echo " \n\ target remote localhost:2331 \n\ mon flash breakpoints = 1 \n\ monitor reset \n\ file $(OUTPUT_BINARY_DIRECTORY)/$(OUTPUT_FILENAME).out \n\ load \n\ b main \n\ b app_error_handler \n\ monitor reset \n\ continue" >> $(GDB_COMMAND_SCRIPT) gdb: $(GDB_COMMAND_SCRIPT) debug arm-none-eabi-gdb -x $(GDB_COMMAND_SCRIPT) serial: screen /dev/cu.usbmodem1411 38400