# -*- makefile -*- ifndef CONTIKI ${error CONTIKI not defined! You must specify where Contiki resides} endif ifeq ($(TARGET),) -include Makefile.target ifeq ($(TARGET),) ${info TARGET not defined, using target 'native'} TARGET=native else ${info using saved target '$(TARGET)'} endif endif ifeq ($(DEFINES),) -include Makefile.$(TARGET).defines ifneq ($(DEFINES),) ${info using saved defines '$(DEFINES)'} endif endif ifndef HOST_OS ifeq ($(OS),Windows_NT) ## TODO: detect more specific Windows set-ups, ## e.g. CygWin, MingW, VisualC, Watcom, Interix HOST_OS := Windows else HOST_OS := $(shell uname) endif endif #More debug information when running in CI ifdef CI ifeq ($(CI),true) V = 1 endif endif usage: @echo "make MAKETARGETS... [TARGET=(TARGET)] [savetarget] [targets]" targets: @ls -1 $(CONTIKI)/platform $(TARGETDIRS) | grep -v CVS savetarget: -@rm -f Makefile.target @echo "saving Makefile.target" @echo >Makefile.target "TARGET = $(TARGET)" savedefines: -@rm -f Makefile.$(TARGET).defines @echo "saving Makefile.$(TARGET).defines" @echo >Makefile.$(TARGET).defines "DEFINES = $(DEFINES)" OBJECTDIR = obj_$(TARGET) LOWERCASE = -abcdefghijklmnopqrstuvwxyz UPPERCASE = _ABCDEFGHIJKLMNOPQRSTUVWXYZ TARGET_UPPERCASE := ${strip ${shell echo $(TARGET) | sed y!$(LOWERCASE)!$(UPPERCASE)!}} CFLAGS += -DCONTIKI=1 -DCONTIKI_TARGET_$(TARGET_UPPERCASE)=1 MODULES += core/sys core/dev core/lib # Include IPv6, IPv4, and/or Rime HAS_STACK = 0 ifeq ($(CONTIKI_WITH_IPV4),1) HAS_STACK = 1 CFLAGS += -DNETSTACK_CONF_WITH_IPV4=1 MODULES += core/net/ipv4 core/net/ip endif ifeq ($(CONTIKI_WITH_RIME),1) HAS_STACK = 1 CFLAGS += -DNETSTACK_CONF_WITH_RIME=1 MODULES += core/net/rime endif # Make IPv6 the default stack ifeq ($(HAS_STACK),0) ifneq ($(CONTIKI_WITH_IPV6),0) CONTIKI_WITH_IPV6 = 1 endif endif ifeq ($(CONTIKI_WITH_IPV6),1) CFLAGS += -DNETSTACK_CONF_WITH_IPV6=1 ifneq ($(CONTIKI_WITH_RPL),0) CONTIKI_WITH_RPL = 1 endif MODULES += core/net/ipv6 core/net/ip endif ifeq ($(CONTIKI_WITH_RPL),1) CFLAGS += -DUIP_CONF_IPV6_RPL=1 MODULES += core/net/rpl else CFLAGS += -DUIP_CONF_IPV6_RPL=0 endif CONTIKI_SOURCEFILES += $(CONTIKIFILES) CONTIKIDIRS += ${addprefix $(CONTIKI)/core/,dev lib net net/llsec net/mac net/rime \ net/rpl sys cfs ctk lib/ctk loader . } oname = ${patsubst %.cpp,%.o,${patsubst %.c,%.o,${patsubst %.S,%.o,$(1)}}} CONTIKI_OBJECTFILES = ${addprefix $(OBJECTDIR)/,${call oname, $(CONTIKI_SOURCEFILES)}} PROJECT_OBJECTFILES = ${addprefix $(OBJECTDIR)/,${call oname, $(PROJECT_SOURCEFILES)}} # Provide way to create $(OBJECTDIR) if it has been removed by make clean $(OBJECTDIR): mkdir $@ uniq = $(if $1,$(firstword $1) $(call uniq,$(filter-out $(firstword $1),$1))) ### Include application makefiles ifdef APPS APPDS = ${wildcard ${foreach DIR, $(APPDIRS), ${addprefix $(DIR)/, $(APPS)}}} \ ${wildcard ${addprefix $(CONTIKI)/apps/, $(APPS)} \ ${addprefix $(CONTIKI)/platform/$(TARGET)/apps/, $(APPS)} \ $(APPS)} APPINCLUDES = ${foreach APP, $(APPS), ${wildcard ${foreach DIR, $(APPDS), $(DIR)/Makefile.$(APP)}}} -include $(APPINCLUDES) APP_SOURCES = ${foreach APP, $(APPS), $($(APP)_src)} DSC_SOURCES = ${foreach APP, $(APPS), $($(APP)_dsc)} CONTIKI_SOURCEFILES += $(APP_SOURCES) $(DSC_SOURCES) endif ### Include target makefile (TODO Unsafe?) target_makefile := $(wildcard $(CONTIKI)/platform/$(TARGET)/Makefile.$(TARGET) ${foreach TDIR, $(TARGETDIRS), $(TDIR)/$(TARGET)/Makefile.$(TARGET)}) # Check if the target makefile exists, and create the object directory if necessary. ifeq ($(strip $(target_makefile)),) ${error The target platform "$(TARGET)" does not exist (maybe it was misspelled?)} else ifneq (1, ${words $(target_makefile)}) ${error More than one TARGET Makefile found: $(target_makefile)} endif include $(target_makefile) endif ifdef MODULES UNIQUEMODULES = $(call uniq,$(MODULES)) MODULEDIRS = ${wildcard ${addprefix $(CONTIKI)/, $(UNIQUEMODULES)}} MODULES_SOURCES = ${foreach d, $(MODULEDIRS), ${subst ${d}/,,${wildcard $(d)/*.c}}} CONTIKI_SOURCEFILES += $(MODULES_SOURCES) APPDS += $(MODULEDIRS) endif ### Verbosity control. Use make V=1 to get verbose builds. ifeq ($(V),1) TRACE_CC = TRACE_CXX = TRACE_LD = TRACE_AR = TRACE_AS = Q= else TRACE_CC = @echo " CC " $< TRACE_CXX = @echo " CXX " $< TRACE_LD = @echo " LD " $@ TRACE_AR = @echo " AR " $@ TRACE_AS = @echo " AS " $< Q=@ endif ### Forward comma-separated list of arbitrary defines to the compiler COMMA := , CFLAGS += ${addprefix -D,${subst $(COMMA), ,$(DEFINES)}} ### Setup directory search path for source and header files CONTIKI_TARGET_DIRS_CONCAT = ${addprefix ${dir $(target_makefile)}, \ $(CONTIKI_TARGET_DIRS)} CONTIKI_CPU_DIRS_CONCAT = ${addprefix $(CONTIKI_CPU)/, \ $(CONTIKI_CPU_DIRS)} SOURCEDIRS = . $(PROJECTDIRS) $(CONTIKI_TARGET_DIRS_CONCAT) \ $(CONTIKI_CPU_DIRS_CONCAT) $(CONTIKIDIRS) $(APPDS) $(EXTERNALDIRS) ${dir $(target_makefile)} vpath %.c $(SOURCEDIRS) vpath %.cpp $(SOURCEDIRS) vpath %.S $(SOURCEDIRS) CFLAGS += ${addprefix -I,$(SOURCEDIRS) $(CONTIKI)} ### Check for a git repo and pass version if found ### git.exe in Windows cmd shells may require no stderr redirection ifndef RELSTR RELSTR:=${shell git --git-dir ${CONTIKI}/.git describe --tags --always} endif ifneq ($(RELSTR),) CFLAGS += -DCONTIKI_VERSION_STRING=\"Contiki-$(RELSTR)\" endif ### Automatic dependency generation ifneq ($(MAKECMDGOALS),clean) -include ${addprefix $(OBJECTDIR)/,$(CONTIKI_SOURCEFILES:.c=.d) \ $(PROJECT_OBJECTFILES:.o=.d)} endif ### See http://make.paulandlesley.org/autodep.html#advanced define FINALIZE_DEPENDENCY cp $(@:.o=.d) $(@:.o=.$$$$); \ sed -e 's/#.*//' -e 's/^[^:]*: *//' -e 's/ *\\$$//' \ -e '/^$$/ d' -e 's/$$/ :/' < $(@:.o=.$$$$) >> $(@:.o=.d); \ rm -f $(@:.o=.$$$$) endef clean: -rm -f *~ *core core *.srec \ *.lst *.map \ *.cprg *.bin *.data contiki*.a *.firmware core-labels.S *.ihex *.ini \ *.ce *.co rm -rf $(CLEAN) -rm -rf $(OBJECTDIR) distclean: clean -rm -f ${addsuffix .$(TARGET),$(CONTIKI_PROJECT)} -include $(CONTIKI)/platform/$(TARGET)/Makefile.customrules-$(TARGET) ifndef CUSTOM_RULE_C_TO_CE %.ce: %.c $(TRACE_CC) $(Q)$(CC) $(CFLAGS) -DAUTOSTART_ENABLE -c $< -o $@ $(STRIP) --strip-unneeded -g -x $@ endif ifndef CUSTOM_RULE_C_TO_OBJECTDIR_O $(OBJECTDIR)/%.o: %.c | $(OBJECTDIR) $(TRACE_CC) $(Q)$(CC) $(CFLAGS) -MMD -c $< -o $@ @$(FINALIZE_DEPENDENCY) endif ifndef CUSTOM_RULE_CPP_TO_OBJECTDIR_O $(OBJECTDIR)/%.o: %.cpp | $(OBJECTDIR) $(TRACE_CXX) $(Q)$(CXX) $(CFLAGS) -MMD -c $< -o $@ @$(FINALIZE_DEPENDENCY) endif ifndef CUSTOM_RULE_S_TO_OBJECTDIR_O $(OBJECTDIR)/%.o: %.S | $(OBJECTDIR) $(TRACE_AS) $(Q)$(AS) $(ASFLAGS) -o $@ $< endif ifndef CUSTOM_RULE_C_TO_O %.o: %.c $(TRACE_CC) $(Q)$(CC) $(CFLAGS) -c $< -o $@ endif ifndef CUSTOM_RULE_CPP_TO_O %.o: %.cpp $(TRACE_CXX) $(Q)$(CXX) $(CFLAGS) -c $< -o $@ endif ifndef CUSTOM_RULE_C_TO_CO %.co: %.c $(TRACE_CC) $(Q)$(CC) $(CFLAGS) -DAUTOSTART_ENABLE -c $< -o $@ endif ifndef AROPTS AROPTS = rcf endif ifndef CUSTOM_RULE_ALLOBJS_TO_TARGETLIB contiki-$(TARGET).a: $(CONTIKI_OBJECTFILES) $(TRACE_AR) $(Q)$(AR) $(AROPTS) $@ $^ endif ifndef LD LD = $(CC) endif ifndef CUSTOM_RULE_LINK %.$(TARGET): %.co $(PROJECT_OBJECTFILES) $(PROJECT_LIBRARIES) contiki-$(TARGET).a $(TRACE_LD) $(Q)$(LD) $(LDFLAGS) $(TARGET_STARTFILES) ${filter-out %.a,$^} \ ${filter %.a,$^} $(TARGET_LIBFILES) -o $@ endif %.ramprof: %.$(TARGET) $(NM) -S -td --size-sort $< | grep -i " [abdrw] " | cut -d' ' -f2,4 %.flashprof: %.$(TARGET) $(NM) -S -td --size-sort $< | grep -i " [t] " | cut -d' ' -f2,4 viewconf: @echo "----------------- Make variables: --------------" @echo "##### \"TARGET\": ________________________________ $(TARGET)" @echo "##### \"BOARD\": _________________________________ $(BOARD)" @echo "##### \"MAKE_MAC\": ______________________________ $(MAKE_MAC)" @echo "##### \"MAKE_NET\": ______________________________ $(MAKE_NET)" @echo "##### \"MAKE_ROUTING\": __________________________ $(MAKE_ROUTING)" ifdef MAKE_COAP_DTLS_KEYSTORE @echo "##### \"MAKE_COAP_DTLS_KEYSTORE\": _______________ $(MAKE_COAP_DTLS_KEYSTORE)" endif @echo "----------------- C variables: -----------------" $(Q)$(CC) $(CFLAGS) -E $(CONTIKI)/tools/viewconf.c | grep \#\#\#\#\# @echo "------------------------------------------------" @echo "'==' Means the flag is set to a given a value" @echo "'->' Means the flag is unset, but will default to a given value" @echo "'><' Means the flag is unset and has no default value" @echo "To view more Make variables, edit $(CONTIKI)/Makefile.include, rule 'viewconf'" @echo "To view more C variables, edit $(CONTIKI)/tools/viewconf.c" # Don't treat %.$(TARGET) as an intermediate file because it is # in fact the primary target. .PRECIOUS: %.$(TARGET) # Cancel the predefined implict rule for compiling and linking # a single C source into a binary to force GNU make to consider # the match-anything rule below instead. %: %.c %: %.cpp # Match-anything pattern rule to allow the project makefiles to # abstract from the actual binary name. It needs to contain some # command in order to be a rule, not just a prerequisite. %: %.$(TARGET) @