ImageRules revision 8ca0de0c89534d817754c42d616508e64772f1a4
1rule FSameTargetWithPrependedGrist
2{
3	# SameTargetWithPrependedGrist <target> : <grist to prepend> ;
4	#
5	local target = $(1) ;
6	local gristToPrepend = $(2) ;
7	local grist = $(target:G) ;
8
9	if $(grist) {
10		grist = $(gristToPrepend)!$(grist) ;
11	} else {
12		grist = $(gristToPrepend) ;
13	}
14	
15	return $(target:G=$(grist)) ;
16}
17
18rule InitScript
19{
20	# Note: The script must have been LOCATEd before.
21	local script = $(1) ;
22	local initScript
23		= [ FSameTargetWithPrependedGrist $(script) : init-script ] ;
24
25	if ! [ on $(script) return $(__is_initialized) ] {
26		__is_initialized on $(script) = true ;
27
28		MakeLocate $(initScript) : [ on $(script) return $(LOCATE) ] ;
29		Always $(initScript) ;
30		Depends $(script) : $(initScript) ;
31
32		InitScript1 $(initScript) ;
33	}
34
35	return $(initScript) ;
36}
37
38actions InitScript1
39{
40	rm -f $(1)
41	echo -n > $(1)
42}
43
44rule AddVariableToScript
45{
46	# AddVariableToScript <script> : <variable> : <value> ;
47	#
48	local script = $(1) ;
49	local variable = $(2) ;
50	local value = $(3) ;
51
52	InitScript $(script) ;
53
54	VARIABLE_DEFS on $(script) += "echo $(variable)=\\\"$(value)\\\" >> " ;
55
56	AddVariableToScript1 $(script) ;
57}
58
59actions together AddVariableToScript1
60{
61	$(VARIABLE_DEFS)$(1);
62}
63
64rule AddTargetVariableToScript
65{
66	# AddTargetVariableToScript <script> : <target> [ : <variable> ] ;
67	#
68	local script = $(1) ;
69	local target = $(2) ;
70	local variable = $(3:E=$(target:BS)) ;
71
72	InitScript $(script) ;
73
74	# That's not completely save, if one has more than on target with the
75	# same base name. A unique pseudo target would have to be introduced
76	# to do it more correctly.
77	VARIABLE_NAME($(target:BS)) on $(script) = $(variable) ;
78
79	Depends $(script) : $(target) ;
80	AddTargetVariableToScript1 $(script) : $(target) ;
81}
82
83actions AddTargetVariableToScript1
84{
85	echo "$(VARIABLE_NAME($(2:BS)))=\"$(2)\"" >> $(1)
86}
87
88
89rule AddDirectoryToHaikuImage
90{
91	# AddDirectoryToHaikuImage <directory>
92	local directoryTokens = $(1) ;
93	local directory = [ FDirName $(directoryTokens) ] ;
94	directory = $(directory:G=HaikuImage) ;
95
96	if ! [ on $(directory) return $(__is_on_image) ] {
97		INSTALL_DIRECTORIES on haiku-image-contents += $(directory) ;
98		__is_on_image on $(directory) = true ;
99		NotFile $(directory) ;
100	
101		# mark the parent dir as not to be created
102		local parent = [ FReverse $(directoryTokens) ] ;
103		parent = [ FReverse $(parent[2-]) ] ;
104		if $(parent) {
105			parent = [ FDirName $(parent) ] ;
106			parent = $(parent:G=HaikuImage) ;
107			DONT_CREATE on $(parent) = true ;
108		}
109	}
110
111	return $(directory) ;
112}
113
114rule AddFilesToHaikuImage
115{
116	# AddFilesToHaikuImage <directory> : <targets> [ : dest name ]
117	#
118	local directory = [ AddDirectoryToHaikuImage $(1) ] ;
119	local targets = $(2) ;
120	local destName = $(3) ;
121
122	# We create a unique dummy target per target to install.
123	local target ;
124	for target in $(targets) {
125		local name ;
126		if $(destName) {
127			name = $(destName) ;
128		} else {
129			name = $(target:G=:D=) ;
130		}
131
132		local destTarget = $(name:G=HaikuImage__$(directory:G=)) ;
133		TARGET on $(destTarget) = $(target) ;
134		INSTALL_DIR on $(destTarget) = $(directory) ;
135		INSTALL_TARGETS on $(target) += $(destTarget) ;
136		TARGETS_TO_INSTALL on $(directory) += $(destTarget) ;
137	}
138}
139
140rule AddSymlinkToHaikuImage
141{
142	# AddSymlinkToHaikuImage <directory> : <link target> [ : <link name> ] ;
143	#
144	local directory = [ AddDirectoryToHaikuImage $(1) ] ;
145	local linkTarget = $(2) ;
146	local linkName = $(3) ;
147
148	if ! $(linkName) {
149		local path = [ FReverse [ FSplitPath $(linkTarget) ] ] ;
150		linkName = $(path[1]) ;
151	}
152
153	local link = $(directory)/$(linkName) ;
154	SYMLINK_TARGET on $(link) = $(linkTarget) ;
155	SYMLINKS_TO_INSTALL on $(directory) += $(link) ;
156}
157
158rule AddDriversToHaikuImage
159{
160	# AddDriversToHaikuImage <relative directory> : <targets> ;
161	#
162	local relativeDirectoryTokens = $(1) ;
163	local targets = $(2) ;
164	local directoryTokens = beos system add-ons kernel drivers dev
165		$(relativeDirectoryTokens) ;
166
167	AddFilesToHaikuImage beos system add-ons kernel drivers bin : $(targets) ;
168
169	# get the relative symlink path prefix
170	local linkPrefix = ;
171	for i in $(relativeDirectoryTokens) {
172		linkPrefix += .. ;
173	}
174	linkPrefix += .. bin ;
175
176	# add the symlinks
177	local name ;
178	for name in $(targets:BS) {
179		AddSymlinkToHaikuImage $(directoryTokens)
180			: [ FDirName $(linkPrefix) $(name) ] : $(name) ;
181	}
182}
183
184rule AddDriverRegistrationToHaikuImage
185{
186	# AddDriverRegistrationToHaikuImage <directory> : <link target> : <link names> ] ;
187	#
188	local relativeDirectoryTokens = $(1) ;
189	local target = $(2) ;
190	local links = $(3) ;
191	local directoryTokens = beos system add-ons kernel registration $(relativeDirectoryTokens) ;
192
193	# get the relative symlink path prefix
194	local linkPrefix = ;
195	for i in $(relativeDirectoryTokens) {
196		linkPrefix += .. ;
197	}
198	linkPrefix += .. drivers bin ;
199
200	# add the symlink
201	AddSymlinkToHaikuImage $(directoryTokens) : [ FDirName $(linkPrefix) $(target:BS) ] : $(links) ;
202}
203
204rule AddBootModuleSymlinks
205{
206	# AddBootModuleSymlinks <targets> ;
207	#
208	local targets = $(1) ;
209
210	# add the symlinks
211	local target ;
212	for target in $(targets) {
213		# Symlink to the first place where the target has been installed.
214		local destTarget = [ on $(target) return $(INSTALL_TARGETS[1]) ] ;
215		local installDir = [ on $(destTarget) return $(INSTALL_DIR) ] ;
216
217		if ! $(installDir) {
218			Echo "ERROR: AddBootModuleSymlinks: Can't create a symlink to"
219				"target" \"$(target)"\"." ;
220			Exit "ERROR: Add*ToHaikuImage has not been invoked for it yet." ;
221		}
222
223		local name = $(target:BS) ;
224		local linkTarget = [ FDirName /boot $(installDir:G=) $(name) ] ; 
225
226		AddSymlinkToHaikuImage beos system add-ons kernel boot
227			: $(linkTarget) : $(name) ;
228	}
229}
230
231rule CreateHaikuImageMakeDirectoriesScript
232{
233	local script = $(1) ;
234	MakeLocate $(script) : $(HAIKU_OUTPUT_DIR) ;
235	Always $(script) ;
236
237	local initScript = [ InitScript $(script) ] ;
238
239	local scriptBody
240		= [ FSameTargetWithPrependedGrist $(script) : script-body ] ;
241	LOCATE on $(scriptBody) = [ on $(script) return $(LOCATE) ] ;
242	Depends $(scriptBody) : $(initScript) ;
243	Depends $(script) : $(scriptBody) ;
244	
245	local dirsToCreate ;
246	local dir ;
247	for dir in [ on haiku-image-contents return $(INSTALL_DIRECTORIES) ] {
248		if ! [ on $(dir) return $(DONT_CREATE) ] {
249			dirsToCreate += $(dir) ;
250		}
251	}
252
253	Depends $(scriptBody) : $(dirsToCreate) ;
254	CreateHaikuImageMakeDirectoriesScript1 $(scriptBody) : $(dirsToCreate) ;
255}
256
257actions piecemeal CreateHaikuImageMakeDirectoriesScript1
258{
259	echo \$mkdir -p "\"\${tPrefix}$(2:G=)\"" >> $(1)
260}
261
262rule CreateHaikuImageCopyFilesScript
263{
264	local script = $(1) ;
265	MakeLocate $(script) : $(HAIKU_OUTPUT_DIR) ;
266	Always $(script) ;
267
268	local initScript = [ InitScript $(script) ] ;
269
270	local scriptBody
271		= [ FSameTargetWithPrependedGrist $(script) : script-body ] ;
272	LOCATE on $(scriptBody) = [ on $(script) return $(LOCATE) ] ;
273	Depends $(scriptBody) : $(initScript) ;
274	Depends $(script) : $(scriptBody) ;
275
276	local dir ;
277	for dir in [ on haiku-image-contents return $(INSTALL_DIRECTORIES) ] {
278		# filter the targets that shall be renamed; they have to be copied
279		# individually
280		local destTargets = [ on $(dir) return $(TARGETS_TO_INSTALL) ] ;
281		local remainingTargets ;
282		local destTarget ;
283		for destTarget in $(destTargets) {
284			local target = [ on $(destTarget) return $(TARGET) ] ;
285			local name = $(destTarget:BS) ;
286			if $(name) != $(target:BS) {
287				# use a unique dummy target for this file, on which we
288				# can define the TARGET_DIR variable
289				local dummyTarget = $(script)-dummy-$(dir:G=)-$(target) ;
290				NotFile $(dummyTarget) ;
291				TARGET_DIR on $(dummyTarget) = $(dir:G=) ;
292				INSTALL_TARGET_NAME on $(dummyTarget) = $(name) ;
293	
294				Depends $(dummyTarget) : $(initScript) $(target) ;
295				Depends $(script) : $(dummyTarget) ;
296
297				AppendToHaikuImageCopyFilesScriptSingleFile $(dummyTarget)
298					: $(initScript) $(target) ;
299			} else {
300				remainingTargets += $(target) ;
301			}
302		}
303		targets = $(remainingTargets) ;
304
305		if $(targets) {
306			# use a unique dummy target for this directory, on which we
307			# can define the TARGET_DIR variable
308			local dummyTarget = $(script)-dummy-$(dir:G=) ;
309			NotFile $(dummyTarget) ;
310			TARGET_DIR on $(dummyTarget) = $(dir:G=) ;
311
312			Depends $(dummyTarget) : $(initScript) $(targets) ;
313			Depends $(script) : $(dummyTarget) ;
314
315			OUTPUT_SCRIPT on $(dummyTarget) = $(initScript) ;
316			AppendToHaikuImageCopyFilesScript $(dummyTarget) : $(targets) ;
317		}
318	
319		local symlinks = [ on $(dir) return $(SYMLINKS_TO_INSTALL) ] ;
320		local symlink ;
321		for symlink in $(symlinks) {
322			NotFile $(symlink) ;
323
324			Depends $(script) : $(symlink) ;
325			Depends $(symlink) : $(initScript) ;
326
327			AddSymlinkToHaikuImageCopyFilesScript $(symlink) : $(initScript) ;
328		}
329	}
330}
331
332actions piecemeal AppendToHaikuImageCopyFilesScript bind OUTPUT_SCRIPT
333{
334	echo \$cp "\"\${sPrefix}$(2)\"" "\"\${tPrefix}$(TARGET_DIR)\"" >> $(OUTPUT_SCRIPT)
335}
336
337actions AppendToHaikuImageCopyFilesScriptSingleFile
338{
339	echo \$cp "\"\${sPrefix}$(2[2])\"" \
340		"\"\${tPrefix}$(TARGET_DIR)/$(INSTALL_TARGET_NAME)\"" >> $(2[1])
341}
342
343actions AddSymlinkToHaikuImageCopyFilesScript
344{
345	echo \$ln -sfn "\"$(SYMLINK_TARGET)\"" "\"\${tPrefix}$(1:G=)\"" >> $(2[1])
346}
347
348rule BuildHaikuImage
349{
350	# BuildHaikuImage <haiku image> : <scripts> : <is image> ;
351	#
352	local haikuImage = $(1) ;
353	local scripts = $(2) ;
354	local isImage = $(3) ;
355
356	if $(isImage) = 1 || $(isImage) = true {
357		IS_IMAGE on $(haikuImage) = 1 ;
358	} else {
359		IS_IMAGE on $(haikuImage) = "" ;
360	}
361
362	local mainScript = build_haiku_image ;
363	SEARCH on $(mainScript) = [ FDirName $(HAIKU_TOP) build scripts ] ;
364
365	Depends $(haikuImage) : $(mainScript) $(scripts) ;
366	BuildHaikuImage1 $(haikuImage) : $(mainScript) $(scripts) ;
367}
368
369actions BuildHaikuImage1
370{
371	export isImage="$(IS_IMAGE)"
372	$(2[1]) $(2[2-])
373}
374