File avr_common.mk of Package avr-libc

# avr_common.mk -- common Makefile macros for avr projects
#
# (C) Copyright 2008, Juergen Weigert, jw@suse.de
# Distribute under GPLv2, use with care.
#
# 2007-07-23, jw, 	features: VPATH support
# 2008-01-27, jw	added make depend, make help. 
#                       make NNmhz did not generates cpu_mhz.h - fixed.
#
#
# Makefile example:
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
# # Makefile for project $(NAME)
# # Distribute under GPLv2, use with care.
# #
# # 2007-06-08, jw
# 
# NAME		= tinyPWMout
# OFILES	= $(NAME).o eeprom.o i2c_slave_cb.o
# CPU		= tiny2313
# TOP_DIR	= ..
# 
# include $(TOP_DIR)/avr_common.mk
# 
# distclean:: 
# 	rm -f download* ee_data.* 
# 
# ## header file dependencies
# #############################
# $(NAME).o: cpu_mhz.h config.h eeprom.h i2c_slave_cb.h
# eeprom.o: eeprom.h cpu_mhz.h config.h 
# i2c_slave_cb.o: i2c_slave_cb.h cpu_mhz.h config.h 
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #

ifeq ($(TOP_DIR),)
  TOP_DIR	= .
endif

ifeq ($(PROJ),)
  PROJ		:= $(NAME)
endif

CFILES		:= $(OFILES:%.o=%.c)

## uisp-2050207 does not know tiny24
#ISP		= $(TOP_DIR)/avr_isp.pl -s uisp -p $(CPU)
ISP		= $(TOP_DIR)/avr_isp.pl -s avrdude -p $(CPU)

CC		= avr-gcc -mmcu=at$(CPU)
O2HEX		= avr-objcopy -O ihex
O2HEX_T		= $(O2HEX) -j .text -j .data
O2HEX_EE	= $(O2HEX) -j .eeprom --change-section-lma .eeprom=0
OBJDUMP		= avr-objdump
OBJCOPY		= avr-objcopy -v
AVRSIZE		= avr-size

# don't use -mint8, or preprocesor will issue silly warnings.
# have -I. here, so that .c files from VPATH find .h files in the target dir, not source dir.
CFLAGS		= -I.  -Wall -g -O2 # -mint8 
#CFLAGS		= -I. -Wall -g -Os -mint8 

# .c files found via VPATH say
# include <config.h> to prefer the config.h from the target directory via -I
# include "config.h" to prefer the config.h next to themselves.

ifeq ($(TOP_DIR),)
else
  VPATH		= $(TOP_DIR)
  CFLAGS	+= -I$(VPATH)
endif

DIST_EXCLUDE	= --exclude \*.tgz --exclude core --exclude \*.orig --exclude \*.swp --exclude
MAKE_SUBDIRS	= for d in $(SUBDIRS); do $(MAKE) $(MFLAGS) -C $$d $@; done
MAKE_SUBDIRS_NP	= for d in $(SUBDIRS); do $(MAKE) $(MFLAGS) --no-print-directory -C $$d $@; done

SHELL		= /bin/sh

# .PHONY: $(NAME).hex $(NAME)-src.hex version.h flashcount

# always rebuild version.h  and flashcount
.PHONY: version.h flashcount help

ifeq ($(NAME),)
all:
else
all: $(NAME).hex 
endif

%.hex: %.out; $(O2HEX_T) $^ $@

flashcount:
	@read n < flashcount; echo > flashcount "$$(($$n + 1))"
	@echo -n flashcount=
	@cat flashcount

help: 
	@echo 
	@echo avr_common.mk uses the following variables:
	@echo
	@echo 'NAME        name of the binary. Specify in Makefile, no default.'
	@echo 'PROJ        name of the project. Specify in Makefile, defaults to "$$(NAME)".'
	@echo 'OFILE       list of object files. Should include at least "$$(NAME).o".'
	@echo '            Specify in Makefile, no default.'
	@echo 'TOP_DIR     directory where avr_common.mk is found. Default "."'
	@echo 'SUBDIRS     directories with own Makefiles. Specify in Makefile, optional.'
	@echo 'CC          compiler name. Default: "$(value CC)"'
	@echo 'CFLAGS      compiler options. Default: "$(value CFLAGS)"'
	@echo 'LDFLAGS     compiler options. Default: "$(value LDFLAGS)"'
	@echo 'ISP         upload helper. Default: "$(value ISP)"'
	@echo 'CPU         name of the ATMEL processor chip. Specify in Makefile,'
	@echo '            no default. Valid names with $(value CC) are:'
	@cpu=`$(CC) -mmcu=not_a_valid_mcu -x c /dev/null 2>&1 | grep ' at'`; echo $$cpu | fold -s
	@echo 
	@echo avr_common.mk offers the following additional make targets: 
	@echo
	@echo "help        - print this online help."
	@echo 'depend      - create depend.mk using $$(OFILES).'
	@echo 'all         - compile and link $$(NAME) using $$(OFILES).'
	@echo 'reset       - reset the device. Also a useful connectivity test.'
	@echo 'upload      - create and load $$(NAME) into the device.'
	@echo 'flashcount  - file with an upload counter.'
	@echo 'erase       - erase flash (and eeprom) of device.'
	@echo '1mhz 2.5mhz 4mhz 8mhz 16mhz 20mhz'
	@echo '            - program the device clock speed.'
	@echo 'download    - retrieve binary from device flash.'
	@echo 'download_ee - retrieve eeprom contents from device.'
	@echo 'clean       - remove all generated (and temporary) files.'
	@echo 'dist        - pack everything into a compressed tar archive.'
	@echo 'version     - increment the minor version number in file "version.h"'
	@echo '              and rename the current directory accordingly.'
	@echo 
	@echo 'For further details, see $(TOP_DIR)/avr_common.mk'


depend depend.mk: $(CFILES)
	$(CC) -MM $(CFILES) > depend.mk || rm -f depend.mk

install: all upload

# erase zaps the eeprom. be careful with that...
erase: download_ee flashcount
	$(ISP) erase

upload_dist: upload_all
upload_src: upload_all
install_all: upload_all
install_src: upload_all
install_dist: upload_all

ifeq ($(NAME),)
else
## use egrep to make dude half quiet.
up upload: $(NAME).hex flashcount
	$(ISP) up $(NAME).hex 2>&1 | egrep '(signature|bytes)'
	@# test "`wc -c < $(NAME)-ee.hex`" -gt 13 && $(ISP) up_ee $(NAME)-ee.hex

ee_up ee_upload upload_ee up_ee: $(NAME)-ee.hex
	$(ISP) up_ee $(NAME)-ee.hex


# if __bss_start > 60, we probably have strings in RAM, check __data
# if __bss_end gets close to __stack, think of subroutine calls.
#
# In order to know how much flash the final program will consume, one needs to
# add the values for both, .text and .data (but not .bss), while the amount of
# pre-allocated SRAM is the sum of .data and .bss.

$(NAME).out: $(OFILES)
	$(CC) $(CFLAGS) -Wl,-Map,$(NAME).map,--cref -o $(NAME).out $(OFILES)
	@$(AVRSIZE) $(NAME).out
#	@$(OBJDUMP) -t $(NAME).out | egrep '(__stack|__bss|_etext)'
#	@$(OBJDUMP) -h $(NAME).out | \
#	perl -ane '{printf "$$1 %d bytes.\n", hex($$2) if $$_ =~ m{\.(text)\s+(\S+)}}'

# identical implicit rule using $(CC) and $(CFLAGS) exists.
# $(NAME).o: $(NAME).c
# 	$(CC) $(CFLAGS) -c $<

$(NAME).s: $(NAME).c
	$(CC) $(CFLAGS) -S -o $(NAME).s -c $<
endif


ee_down ee_download download_ee down_ee: 
	$(ISP) down_ee ee_data.hex
	@mkdir -p down
	d=`date '+%Y%m%d%H%M%S'`; \
	$(OBJCOPY) -I ihex -O binary ee_data.hex down/ee_data.bin.$$d; \
	set -x; ln -sf down/ee_data.bin.$$d ee_data.bin

1mhz 2.5mhz 4mhz 8mhz 16mhz 20mhz:; $(ISP) -q clock $@ cpu_mhz.h

download down reset:; $(ISP) $@

install.sh: Makefile
	echo  > $@ '#! /bin/sh'
	echo >> $@ '# $@ -- install binaries, how the Makefile does it.'
	echo >> $@ '# (C) 2005 jw@suse.de, distribute under GPL, use with care.'
	echo >> $@ 
	echo >> $@ 'ISP="$(ISP)"'
	echo >> $@ 'set -x'
	make -n upload | sed -n -e 's@$(ISP)@$$ISP@p' >> $@
	clock=`grep 'CPU_MHZ\b' cpu_mhz.h|sed -e 's@.*CPU_MHZ@@'`; \
	echo \$$ISP clock $${clock}mhz >> $@
	chmod a+x $@

clean::
	rm -f *.o *.s *.out *.hex

distclean:: clean
	rm -f *.orig *.map *~

ifeq ($(TOP_DIR),.)

# := evaluates immediatly, but = propagates.
VERSION		= $(shell read a b < version; printf "%d.%02d" $$a $$b)
VERSION_MAJ	= $(shell read a b < version; echo $$a)
VERSION_MIN	= $(shell read a b < version; echo $$b)
OLD_VERSION	:= VERSION

version:: incr_vmin rename

version.h:
	@echo \#define VERSION   \"$(VERSION)\"    > version.h; \
	echo \#define VERSION_MAJ $(VERSION_MAJ) >> version.h; \
	echo \#define VERSION_MIN $(VERSION_MIN) >> version.h

incr: incr_vmin

incr_vmin:
	read a b < version; echo > version "$${a:-0} $$(($$b + 1))"
	@cat version

incr_vmaj:
	read a b < version; echo > version "$$(($$a + 1)) $${b:-0}"
	@cat version


rename: 
	n="$(PROJ)-$(VERSION)"; rm -f ../$(PROJ); \
	mv `/bin/pwd` "../$$n" 2> /dev/null; ln -s $$n ../$(PROJ);


bin dist-bin:: $(NAME).hex $(NAME)-ee.hex version.h install.sh
	n="$(PROJ)-$(VERSION)"; ln -s . $$n; \
	tar zcvf ../$$n-bin.tgz $$n/$(NAME).hex $$n/$(NAME)-ee.hex $$n/install.sh $$n/doc/matrix.txt; \
	rm $$n; mv `/bin/pwd` "../$$n" 2> /dev/null; true

dist:: distclean version.h
	n="$(PROJ)-$(VERSION)"; \
	test -f ../$$n.tgz && (echo "WARNING: ../$$n.tgz exists, press ENTER to overwrite"; read a); \
	ln -s . $$n; tar zcvf "../$$n.tgz" $(DIST_EXCLUDE) "$$n/$$n" $$n/*; \
	rm $$n; mv `/bin/pwd` "../$$n" 2> /dev/null; true

else
version dist bin dist-bin::; $(MAKE) -C $(TOP_DIR) $@
endif
openSUSE Build Service is sponsored by