2011-04-13 9 views
5

मैं एक Makefile है कि या तो gnumake या makepp कि दिए गए directiories के तहत सभी फाइलों को पैक के साथ चलता है क्या करना चाहते हैं:Makefile: एक निर्देशिका के हर फ़ाइल पर निर्भर

DIRS:=$(shell find . -mindepth 2 -maxdepth 2 -not -name mp3 -not -name ".*" -type d) 
PACKAGES = $(DIRS:%=%.npk) 

all: packages 

packages: $(PACKAGES) 

%.npk: %/* 
    npack c [email protected] @^ 

.PHONY: all packages 

समस्या यह है कि ऐसी कोई है निर्भरता में%/* के रूप में बात। मुझे निर्देशिका एक्स में प्रत्येक फ़ाइल पर निर्भर करने के लिए लक्ष्य (X.npk) की आवश्यकता है, लेकिन मुझे नहीं पता कि जब मैं मेकफ़ाइल लिखता हूं तो फाइलें क्या होती हैं, 'क्योंकि वे बाद में उत्पन्न होते हैं।

एक उदाहरण:

./dirA/x 
./dirA/y 
./dirB/e 
./dirB/f 

मैं ./dirA.npk (एक्स के आधार पर, वाई) बनाना चाहते हैं, ./dirB.npk (ई, एफ) कुछ भी मैं के बारे में पता है डीआईआर या अग्रिम फाइलें सिवाय इसके कि पहली पंक्ति में इस्तेमाल किए गए खोज में सभी डीआईआर मिलते हैं।

+0

मैंने कोशिश की:% .npk: $ (वाइल्डकार्ड%/*) लेकिन यह काम नहीं करता है। मैंने एक सेफफ़ोर के बारे में भी सोचा लेकिन एक ही समस्या के लिए, मुझे target_dir/* पर निर्भर रहने की आवश्यकता होगी। – Gavriel

उत्तर

1

यह समाधान मैंने पाया: यह कुछ "मेटा" स्क्रिप्टिंग के साथ makedepend विचार पर आधारित है। बहुत अच्छा नहीं है, लेकिन काम करता है।

PACKAGES := 

all: packages 

-include Makefile.depend 

packages: Makefile.depend $(PACKAGES) 

depend: clean Makefile.depend 

Makefile.depend: 
    @(PACKAGES= ; \ 
    for DIR in `find . -mindepth 2 -maxdepth 2 -not -name mp3 -not -name ".*" -type d` ; \ 
    do \ 
     PACKAGE=`basename $${DIR}.npk` ; \ 
     PACKAGES="$${PACKAGES} $${PACKAGE}" ; \ 
     DEPS=`find $${DIR} -not -type d | sed -e 's#\([: ]\)#\\\\\1#' -e 's#^\./\(.*\)# \1#' | tr -d "\n"` ; \ 
     SUBDIR=`echo $${DIR} | sed -e 's#^\./\([^/]\+\)/.*#\1#'` ; \ 
     FILES=`echo \ $${DEPS} | sed -e "s# $${SUBDIR}/# #g"` ; \ 
     echo "$${PACKAGE}:$${DEPS}" ; \ 
     echo " @cd $${SUBDIR} ; \\" ; \ 
     echo " npack c ../\[email protected] $${FILES} ; \\" ; \ 
     echo ; \ 
    done ; \ 
    echo "PACKAGES = $${PACKAGES}" \ 
    )>> Makefile.depend ; \ 

cleanall: clean 
    rm -f *.npk 

clean: 
    @rm -f Makefile.depend 

.PHONY: all packages depend clean 
2

wildcard निर्देश उपयोग करके देखें:

DEPS := $(foreach dir, $(DIRS), $(wildcard $(dir)/*)) 

%.npk: $(DEPS) 
    npack c [email protected] $^ 

संपादित करें: ऊपर सिर्फ wildcard का उपयोग करने का एक उदाहरण है और प्रत्येक .npk फ़ाइल अन्य फ़ोल्डर के सभी में फ़ाइलों पर निर्भर करता है। आपका उपयोग थोड़ा अलग होगा।

मुझे लगता है कि इसके बारे में जाने का एक आसान तरीका हो सकता है। आप फ़ोल्डर में सभी फाइलों पर निर्भरता क्यों चाहते हैं? क्या यह सिर्फ $^ ऑपरेटर का उपयोग करना है? या अगर किसी भी फाइल को बदल दिया गया है तो आपको .npk को पुनर्निर्माण करने की आवश्यकता है?

एक वैकल्पिक (और संभवतः क्लीनर) समाधान $^ के बजाय अपने नुस्खा में find उपयोगिता का उपयोग करें और .FORCE निर्देश का उपयोग हमेशा पुनर्निर्माण की .npk फ़ाइल के लिए मजबूर करने के लिए किया जाएगा। नकारात्मकता यह है कि .npk फ़ाइलों को अनावश्यक रूप से पुनर्निर्मित किया जा सकता है।

संपादित करें 2: अगर वहाँ make आदेशों के साथ सफाई से यह करने के लिए एक तरह से नहीं है, आप .FORCE का उपयोग कर कि नुस्खा हमेशा चलाया जाता है सुनिश्चित करने और ले जाने के "मैं इस फाइल के पुनर्निर्माण चाहिए" चेक करने से यह काम कर सकते हैं

#!/bin/bash 
# Returns non-zero if the archive needs to be rebuilt 
if [ -e $1 ]; then 
    folder_name=$(basename $1 .npk) 
    [ -z "$(find $folder_name -newer $1 -not -type d)" ] && return 0 
fi 
return 1 

मैं डॉन:

%.npk: .FORCE 
    check_for_rebuild.sh [email protected] && npack c [email protected] $^ 

जहां check_for_rebuild.sh एक खोल स्क्रिप्ट है कि कुछ इस तरह करता है: नुस्खा के शरीर में वास्तव में उस समाधान की तरह नहीं है क्योंकि यह सीधे इसे हल करने की बजाय समस्या के आसपास काम करता है, लेकिन यह आपको इस दौरान जाने में सक्षम हो सकता है। यदि आप उस मार्ग पर जा रहे हैं, तो शायद शेल स्क्रिप्ट में सब कुछ करने के लिए यह क्लीनर और आसान है और या तो मेकफ़ाइल केवल स्क्रिप्ट का आह्वान करता है या मेकफ़ाइल से पूरी तरह से छुटकारा पाता है।

+0

बिल्कुल, मुझे फ़ाइलों में से कोई भी बदल दिया गया है या एक नई फ़ाइल जोड़ा गया था, तो मुझे npk फ़ाइल को पुनर्निर्माण करने की आवश्यकता है। .FORCE एक विकल्प नहीं है, मैं विरोध करने की कोशिश कर रहा हूं (वर्तमान में मेरे पास एक शेल स्क्रिप्ट है जो सब कुछ X.npk.tmp में बदल देती है, फिर यदि 'cmp X.npk X.npk.tmp' दिखाता है तो मैं बदलता हूं tmp फ़ाइल अन्यथा मैं इसे हटा देता हूं। लेकिन यह धीमा हो रहा है क्योंकि मेरे पास अधिक dirs और फ़ाइलें हैं। – Gavriel

0

makepp के साथ आप 2 चरणों में यह कर सकते हैं, के माध्यम से: foreach नियम संशोधक:

$(foreach).txt: $(foreach)/*: foreach */ 
    &echo $(inputs) -o $(output) 

यह हर उपनिर्देशिका, जो reexecutes जब भी फ़ाइलों की सूची में एक परिवर्तन है उसमें के लिए एक नियम प्रदान करता है।

संबंधित मुद्दे