initial revision
[ucgine.git] / mk / ucgine-obj-vars.mk
1 #
2 # Copyright 2015, Olivier MATZ <zer0@droids-corp.org>
3 #
4 # Redistribution and use in source and binary forms, with or without
5 # modification, are permitted provided that the following conditions are met:
6 #
7 #     * Redistributions of source code must retain the above copyright
8 #       notice, this list of conditions and the following disclaimer.
9 #     * Redistributions in binary form must reproduce the above copyright
10 #       notice, this list of conditions and the following disclaimer in the
11 #       documentation and/or other materials provided with the distribution.
12 #     * Neither the name of the University of California, Berkeley nor the
13 #       names of its contributors may be used to endorse or promote products
14 #       derived from this software without specific prior written permission.
15 #
16 # THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND ANY
17 # EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 # DISCLAIMED. IN NO EVENT SHALL THE REGENTS AND CONTRIBUTORS BE LIABLE FOR ANY
20 # DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 # SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 #
27
28 # obj-y-$(obj) is provided by the user
29 #  $(obj) is the path of the object, and the variable contains
30 #  the list of sources. Several obj-y-$(obj) can be present.
31
32 # list all object builds requested by user
33 all-obj := $(patsubst obj-y-%,%,$(filter obj-y-%,$(.VARIABLES)))
34
35 # add them to the list of targets
36 all-targets += $(all-obj)
37
38 # convert source path to intermediate object path, and filter
39 # objects from sources
40 #  $1: list of source paths
41 #  $2: output directory (including trailing slash)
42 #  return: list of intermediate object paths
43 src2iobj = $(addprefix $(filter-out ./,$(2)),$(notdir $(strip \
44         $(patsubst %.c,%.o,\
45         $(patsubst %.s,%.o,\
46         $(filter-out %.o,$(1)))))))
47
48 # return the file if it matches a extension that is built with cc
49 #   $1: source file
50 is_cc_source = $(filter %.c %.s %S,$(1))
51
52 # return the file if it's already an object file: in this case no
53 # intermediate object is needed
54 #   $1: source file
55 is_obj_source = $(filter %.o,$(1))
56
57 # return the file if it's a static library
58 #   $1: source file
59 is_alib_source = $(filter %.a,$(1))
60
61 # for each obj, create the following variables:
62 #   out-$(obj) = output path of the object
63 #   pre-$(obj) = list of prerequisites for this object
64 # Some source files need intermediate objects, we define these variables
65 # for them too, and add them in a list: $(all-iobj).
66 # Last, we add the generated files in $(all-clean-file).
67 $(foreach obj,$(all-obj),\
68         $(eval out-$(obj) := $(dir $(obj))) \
69         $(eval pre-$(obj) := ) \
70         $(foreach src,$(obj-y-$(obj)), \
71                 $(if $(call is_cc_source,$(src)), \
72                         $(eval iobj := $(call src2iobj,$(src),$(out-$(obj)))) \
73                         $(eval pre-$(iobj) := $(src)) \
74                         $(eval all-iobj += $(iobj)) \
75                         $(eval all-clean-file += $(iobj)) \
76                         $(eval pre-$(obj) += $(iobj)) \
77                 , \
78                 $(if $(call is_obj_source,$(src)),\
79                         $(eval pre-$(obj) += $(src)) \
80                 , \
81                 $(error "unsupported source format: $(src)"))) \
82         )\
83         $(eval all-clean-file += $(obj)) \
84 )
85
86 # fix the format of .o.d.tmp (generated by gcc) to a .o.d that defines
87 # dependencies as makefile variables
88 #  $1: object file (.o)
89 obj-fixdep = if [ -f $(call file2tmpdep,$(1)) ]; then\
90                 echo -n "dep-$(1) = " > $(call depfile,$(1)) && \
91                 sed 's,^[^ ][^:]*: ,,' $(call file2tmpdep,$(1)) >> $(call depfile,$(1)) && \
92                 rm -f $(call file2tmpdep,$(1)); \
93         else \
94                 $(call create_empty_depfile,$(1)); \
95         fi
96
97 # compile a file
98 #  $1: sources
99 #  $2: dst
100 compile_cmd = $(CC) -Wp,-MD,$(call file2tmpdep,$(2)) \
101         $(CPPFLAGS) $(cppflags-$(2)) \
102         $(CFLAGS) $(cflags-$(2)) \
103         -c -o $2 $1
104
105 # print line used to compile a file
106 ifeq ($(V),1)
107 compile_print_cmd = echo $(call protect_quote,$(call compile_cmd,$1,$2))
108 else
109 compile_print_cmd = echo "  CC $(2)"
110 endif
111
112 # combine several *.o files into one
113 #   $1: sources (*.o)
114 #   $2: dst (xyz.o too)
115 combine_cmd = $(LD) -r $(1) -o $(2)
116
117 # print line used to combine object files
118 ifeq ($(V),1)
119 combine_print_cmd = echo $(call protect_quote,$(call combine_cmd,$1,$2))
120 else
121 combine_print_cmd = echo "  LD $(2)"
122 endif
123
124 all-clean-file += $(all-obj)