#[=======================================================================[.rst:
E x t e r n a l P r o j e c t
- - - - - - - - - - - - - - -
C r e a t e c u s t o m t a r g e t s t o b u i l d p r o j e c t s i n e x t e r n a l t r e e s
. . c o m m a n d : : E x t e r n a l P r o j e c t _ A d d
T h e ` ` E x t e r n a l P r o j e c t _ A d d ` ` f u n c t i o n c r e a t e s a c u s t o m t a r g e t t o d r i v e
d o w n l o a d , u p d a t e / p a t c h , c o n f i g u r e , b u i l d , i n s t a l l a n d t e s t s t e p s o f a n
e x t e r n a l p r o j e c t : :
ExternalProject_Add ( <name> [<option>...] )
G e n e r a l o p t i o n s a r e :
` ` D E P E N D S < p r o j e c t s > . . . ` `
T a r g e t s o n w h i c h t h e p r o j e c t d e p e n d s
` ` P R E F I X < d i r > ` `
R o o t d i r f o r e n t i r e p r o j e c t
` ` L I S T _ S E P A R A T O R < s e p > ` `
S e p t o b e r e p l a c e d b y ; i n c m d l i n e s
` ` T M P _ D I R < d i r > ` `
D i r e c t o r y t o s t o r e t e m p o r a r y f i l e s
` ` S T A M P _ D I R < d i r > ` `
D i r e c t o r y t o s t o r e s t e p t i m e s t a m p s
` ` E X C L U D E _ F R O M _ A L L 1 ` `
T h e " a l l " t a r g e t d o e s n o t d e p e n d o n t h i s
D o w n l o a d s t e p o p t i o n s a r e :
` ` D O W N L O A D _ N A M E < f n a m e > ` `
F i l e n a m e t o store ( if not end of URL )
` ` D O W N L O A D _ D I R < d i r > ` `
D i r e c t o r y t o s t o r e d o w n l o a d e d f i l e s
` ` D O W N L O A D _ C O M M A N D < c m d > . . . ` `
C o m m a n d t o d o w n l o a d s o u r c e t r e e
` ` D O W N L O A D _ N O _ P R O G R E S S 1 ` `
D i s a b l e d o w n l o a d p r o g r e s s r e p o r t s
` ` C V S _ R E P O S I T O R Y < c v s r o o t > ` `
C V S R O O T o f C V S r e p o s i t o r y
` ` C V S _ M O D U L E < m o d > ` `
M o d u l e t o c h e c k o u t f r o m C V S r e p o
` ` C V S _ T A G < t a g > ` `
T a g t o c h e c k o u t f r o m C V S r e p o
` ` S V N _ R E P O S I T O R Y < u r l > ` `
U R L o f S u b v e r s i o n r e p o
` ` S V N _ R E V I S I O N - r < r e v > ` `
R e v i s i o n t o c h e c k o u t f r o m S u b v e r s i o n r e p o
` ` S V N _ U S E R N A M E < u s e r n a m e > ` `
U s e r n a m e f o r S u b v e r s i o n c h e c k o u t a n d u p d a t e
` ` S V N _ P A S S W O R D < p a s s w o r d > ` `
P a s s w o r d f o r S u b v e r s i o n c h e c k o u t a n d u p d a t e
` ` S V N _ T R U S T _ C E R T 1 ` `
T r u s t t h e S u b v e r s i o n s e r v e r s i t e c e r t i f i c a t e
` ` G I T _ R E P O S I T O R Y < u r l > ` `
U R L o f g i t r e p o
` ` G I T _ T A G < t a g > ` `
G i t b r a n c h n a m e , c o m m i t i d o r t a g
` ` G I T _ S U B M O D U L E S < m o d u l e > . . . ` `
G i t s u b m o d u l e s t h a t s h a l l b e u p d a t e d , a l l i f e m p t y
` ` H G _ R E P O S I T O R Y < u r l > ` `
U R L o f m e r c u r i a l r e p o
` ` H G _ T A G < t a g > ` `
M e r c u r i a l b r a n c h n a m e , c o m m i t i d o r t a g
` ` U R L / . . . / s r c . t g z ` `
F u l l p a t h o r U R L o f s o u r c e
` ` U R L _ H A S H A L G O = v a l u e ` `
H a s h o f f i l e a t U R L
` ` U R L _ M D 5 m d 5 ` `
E q u i v a l e n t t o U R L _ H A S H M D 5 = m d 5
` ` T L S _ V E R I F Y < b o o l > ` `
S h o u l d c e r t i f i c a t e f o r h t t p s b e c h e c k e d
` ` T L S _ C A I N F O < f i l e > ` `
P a t h t o a c e r t i f i c a t e a u t h o r i t y f i l e
` ` T I M E O U T < s e c o n d s > ` `
T i m e a l l o w e d f o r f i l e d o w n l o a d o p e r a t i o n s
U p d a t e / P a t c h s t e p o p t i o n s a r e :
` ` U P D A T E _ C O M M A N D < c m d > . . . ` `
S o u r c e w o r k - t r e e u p d a t e c o m m a n d
` ` U P D A T E _ D I S C O N N E C T E D 1 ` `
N e v e r u p d a t e a u t o m a t i c a l l y f r o m t h e r e m o t e r e p o s i t o r y
` ` P A T C H _ C O M M A N D < c m d > . . . ` `
C o m m a n d t o p a t c h d o w n l o a d e d s o u r c e
C o n f i g u r e s t e p o p t i o n s a r e :
` ` S O U R C E _ D I R < d i r > ` `
S o u r c e d i r t o b e u s e d f o r b u i l d
` ` C O N F I G U R E _ C O M M A N D < c m d > . . . ` `
B u i l d t r e e c o n f i g u r a t i o n c o m m a n d
` ` C M A K E _ C O M M A N D / . . . / c m a k e ` `
S p e c i f y a l t e r n a t i v e c m a k e e x e c u t a b l e
` ` C M A K E _ G E N E R A T O R < g e n > ` `
S p e c i f y g e n e r a t o r f o r n a t i v e b u i l d
` ` C M A K E _ G E N E R A T O R _ P L A T F O R M < p l a t f o r m > ` `
G e n e r a t o r - s p e c i f i c p l a t f o r m n a m e
` ` C M A K E _ G E N E R A T O R _ T O O L S E T < t o o l s e t > ` `
G e n e r a t o r - s p e c i f i c t o o l s e t n a m e
` ` C M A K E _ A R G S < a r g > . . . ` `
A r g u m e n t s t o C M a k e c o m m a n d l i n e .
T h e s e a r g u m e n t s a r e p a s s e d t o C M a k e c o m m a n d l i n e , a n d c a n c o n t a i n
a r g u m e n t s o t h e r t h a n c a c h e v a l u e s , s e e a l s o
: m a n u a l : ` C M a k e O p t i o n s < cmake ( 1 ) > ` . A r g u m e n t s i n t h e f o r m
` ` - D v a r : s t r i n g = o n ` ` a r e a l w a y s p a s s e d t o t h e c o m m a n d l i n e , a n d
t h e r e f o r e c a n n o t b e c h a n g e d b y t h e u s e r .
A r g u m e n t s m a y u s e
: m a n u a l : ` g e n e r a t o r e x p r e s s i o n s < c m a k e - g e n e r a t o r - expressions ( 7 ) > ` .
` ` C M A K E _ C A C H E _ A R G S < a r g > . . . ` `
I n i t i a l c a c h e a r g u m e n t s , o f t h e f o r m ` ` - D v a r : s t r i n g = o n ` ` .
T h e s e a r g u m e n t s a r e w r i t t e n i n a p r e - l o a d a s c r i p t t h a t p o p u l a t e s
C M a k e c a c h e , s e e a l s o : m a n u a l : ` c m a k e - C < cmake ( 1 ) > ` . T h i s a l l o w s t o
o v e r c o m e c o m m a n d l i n e l e n g t h l i m i t s .
T h e s e a r g u m e n t s a r e : c o m m a n d : ` s e t ` u s i n g t h e ` ` F O R C E ` ` a r g u m e n t ,
a n d t h e r e f o r e c a n n o t b e c h a n g e d b y t h e u s e r .
A r g u m e n t s m a y u s e
: m a n u a l : ` g e n e r a t o r e x p r e s s i o n s < c m a k e - g e n e r a t o r - expressions ( 7 ) > ` .
` ` C M A K E _ C A C H E _ D E F A U L T _ A R G S < a r g > . . . ` `
I n i t i a l d e f a u l t c a c h e a r g u m e n t s , o f t h e f o r m ` ` - D v a r : s t r i n g = o n ` ` .
T h e s e a r g u m e n t s a r e w r i t t e n i n a p r e - l o a d a s c r i p t t h a t p o p u l a t e s
C M a k e c a c h e , s e e a l s o : m a n u a l : ` c m a k e - C < cmake ( 1 ) > ` . T h i s a l l o w s t o
o v e r c o m e c o m m a n d l i n e l e n g t h l i m i t s .
T h e s e a r g u m e n t s c a n b e u s e d a s d e f a u l t v a l u e t h a t w i l l b e s e t i f n o
p r e v i o u s v a l u e i s f o u n d i n t h e c a c h e , a n d t h a t t h e u s e r c a n c h a n g e
l a t e r .
A r g u m e n t s m a y u s e
: m a n u a l : ` g e n e r a t o r e x p r e s s i o n s < c m a k e - g e n e r a t o r - expressions ( 7 ) > ` .
B u i l d s t e p o p t i o n s a r e :
` ` B I N A R Y _ D I R < d i r > ` `
S p e c i f y b u i l d d i r l o c a t i o n
` ` B U I L D _ C O M M A N D < c m d > . . . ` `
C o m m a n d t o d r i v e t h e n a t i v e b u i l d
` ` B U I L D _ I N _ S O U R C E 1 ` `
U s e s o u r c e d i r f o r b u i l d d i r
` ` B U I L D _ A L W A Y S 1 ` `
N o s t a m p f i l e , b u i l d s t e p a l w a y s r u n s
` ` B U I L D _ B Y P R O D U C T S < f i l e > . . . ` `
F i l e s t h a t w i l l b e g e n e r a t e d b y t h e b u i l d c o m m a n d b u t m a y o r m a y
n o t h a v e t h e i r m o d i f i c a t i o n t i m e u p d a t e d b y s u b s e q u e n t b u i l d s .
I n s t a l l s t e p o p t i o n s a r e :
` ` I N S T A L L _ D I R < d i r > ` `
I n s t a l l a t i o n p r e f i x
` ` I N S T A L L _ C O M M A N D < c m d > . . . ` `
C o m m a n d t o d r i v e i n s t a l l a f t e r b u i l d
T e s t s t e p o p t i o n s a r e :
` ` T E S T _ B E F O R E _ I N S T A L L 1 ` `
A d d t e s t s t e p e x e c u t e d b e f o r e i n s t a l l s t e p
` ` T E S T _ A F T E R _ I N S T A L L 1 ` `
A d d t e s t s t e p e x e c u t e d a f t e r i n s t a l l s t e p
` ` T E S T _ E X C L U D E _ F R O M _ M A I N 1 ` `
M a i n t a r g e t d o e s n o t d e p e n d o n t h e t e s t s t e p
` ` T E S T _ C O M M A N D < c m d > . . . ` `
C o m m a n d t o d r i v e t e s t
O u t p u t l o g g i n g o p t i o n s a r e :
` ` L O G _ D O W N L O A D 1 ` `
W r a p d o w n l o a d i n s c r i p t t o l o g o u t p u t
` ` L O G _ U P D A T E 1 ` `
W r a p u p d a t e i n s c r i p t t o l o g o u t p u t
` ` L O G _ C O N F I G U R E 1 ` `
W r a p c o n f i g u r e i n s c r i p t t o l o g o u t p u t
` ` L O G _ B U I L D 1 ` `
W r a p b u i l d i n s c r i p t t o l o g o u t p u t
` ` L O G _ T E S T 1 ` `
W r a p t e s t i n s c r i p t t o l o g o u t p u t
` ` L O G _ I N S T A L L 1 ` `
W r a p i n s t a l l i n s c r i p t t o l o g o u t p u t
S t e p s c a n b e g i v e n d i r e c t a c c e s s t o t h e t e r m i n a l i f p o s s i b l e . W i t h
t h e : g e n e r a t o r : ` N i n j a ` g e n e r a t o r , t h i s p l a c e s t h e s t e p s i n t h e
` ` c o n s o l e ` ` : p r o p _ g b l : ` p o o l < J O B _ P O O L S > ` . O p t i o n s a r e :
` ` U S E S _ T E R M I N A L _ D O W N L O A D 1 ` `
G i v e d o w n l o a d t e r m i n a l a c c e s s .
` ` U S E S _ T E R M I N A L _ U P D A T E 1 ` `
G i v e u p d a t e t e r m i n a l a c c e s s .
` ` U S E S _ T E R M I N A L _ C O N F I G U R E 1 ` `
G i v e c o n f i g u r e t e r m i n a l a c c e s s .
` ` U S E S _ T E R M I N A L _ B U I L D 1 ` `
G i v e b u i l d t e r m i n a l a c c e s s .
` ` U S E S _ T E R M I N A L _ T E S T 1 ` `
G i v e t e s t t e r m i n a l a c c e s s .
` ` U S E S _ T E R M I N A L _ I N S T A L L 1 ` `
G i v e i n s t a l l t e r m i n a l a c c e s s .
O t h e r o p t i o n s a r e :
` ` S T E P _ T A R G E T S < s t e p - t a r g e t > . . . ` `
G e n e r a t e c u s t o m t a r g e t s f o r t h e s e s t e p s
` ` I N D E P E N D E N T _ S T E P _ T A R G E T S < s t e p - t a r g e t > . . . ` `
G e n e r a t e c u s t o m t a r g e t s f o r t h e s e s t e p s t h a t d o n o t d e p e n d o n o t h e r
e x t e r n a l p r o j e c t s e v e n i f a d e p e n d e n c y i s s e t
T h e ` ` * _ D I R ` ` o p t i o n s s p e c i f y d i r e c t o r i e s f o r t h e p r o j e c t , w i t h d e f a u l t
d i r e c t o r i e s c o m p u t e d a s f o l l o w s . I f t h e ` ` P R E F I X ` ` o p t i o n i s g i v e n t o
` ` ExternalProject_Add ( ) ` ` o r t h e ` ` E P _ P R E F I X ` ` d i r e c t o r y p r o p e r t y i s s e t ,
t h e n a n e x t e r n a l p r o j e c t i s b u i l t a n d i n s t a l l e d u n d e r t h e s p e c i f i e d p r e f i x : :
T M P _ D I R = < p r e f i x > / t m p
S T A M P _ D I R = < p r e f i x > / s r c / < n a m e > - s t a m p
D O W N L O A D _ D I R = < p r e f i x > / s r c
S O U R C E _ D I R = < p r e f i x > / s r c / < n a m e >
B I N A R Y _ D I R = < p r e f i x > / s r c / < n a m e > - b u i l d
I N S T A L L _ D I R = < p r e f i x >
O t h e r w i s e , i f t h e ` ` E P _ B A S E ` ` d i r e c t o r y p r o p e r t y i s s e t t h e n c o m p o n e n t s
o f a n e x t e r n a l p r o j e c t a r e s t o r e d u n d e r t h e s p e c i f i e d b a s e : :
T M P _ D I R = < b a s e > / t m p / < n a m e >
S T A M P _ D I R = < b a s e > / S t a m p / < n a m e >
D O W N L O A D _ D I R = < b a s e > / D o w n l o a d / < n a m e >
S O U R C E _ D I R = < b a s e > / S o u r c e / < n a m e >
B I N A R Y _ D I R = < b a s e > / B u i l d / < n a m e >
I N S T A L L _ D I R = < b a s e > / I n s t a l l / < n a m e >
I f n o ` ` P R E F I X ` ` , ` ` E P _ P R E F I X ` ` , o r ` ` E P _ B A S E ` ` i s s p e c i f i e d t h e n t h e
d e f a u l t i s t o s e t ` ` P R E F I X ` ` t o ` ` < n a m e > - p r e f i x ` ` . R e l a t i v e p a t h s a r e
i n t e r p r e t e d w i t h r e s p e c t t o t h e b u i l d d i r e c t o r y c o r r e s p o n d i n g t o t h e
s o u r c e d i r e c t o r y i n w h i c h ` ` E x t e r n a l P r o j e c t _ A d d ` ` i s i n v o k e d .
I f ` ` S O U R C E _ D I R ` ` i s e x p l i c i t l y s e t t o a n e x i s t i n g d i r e c t o r y t h e p r o j e c t
w i l l b e b u i l t f r o m i t . O t h e r w i s e a d o w n l o a d s t e p m u s t b e s p e c i f i e d
u s i n g o n e o f t h e ` ` D O W N L O A D _ C O M M A N D ` ` , ` ` C V S _ * ` ` , ` ` S V N _ * ` ` , o r ` ` U R L ` `
o p t i o n s . T h e ` ` U R L ` ` o p t i o n m a y r e f e r l o c a l l y t o a d i r e c t o r y o r s o u r c e
t a r b a l l , o r r e f e r t o a r e m o t e tarball ( e.g. ``http://.../src.tgz`` ) .
I f ` ` U P D A T E _ D I S C O N N E C T E D ` ` i s s e t , t h e u p d a t e s t e p i s n o t e x e c u t e d
a u t o m a t i c a l l y w h e n b u i l d i n g t h e m a i n t a r g e t . T h e u p d a t e s t e p c a n s t i l l
b e a d d e d a s a s t e p t a r g e t a n d c a l l e d m a n u a l l y . T h i s i s u s e f u l i f y o u
w a n t t o a l l o w t o b u i l d t h e p r o j e c t w h e n y o u a r e d i s c o n n e c t e d f r o m t h e
network ( you might still need the network for the download step ) .
T h i s i s d i s a b l e d b y d e f a u l t .
T h e d i r e c t o r y p r o p e r t y ` ` E P _ U P D A T E _ D I S C O N N E C T E D ` ` c a n b e u s e d t o c h a n g e
t h e d e f a u l t v a l u e f o r a l l t h e e x t e r n a l p r o j e c t s i n t h e c u r r e n t
d i r e c t o r y a n d i t s s u b d i r e c t o r i e s .
. . c o m m a n d : : E x t e r n a l P r o j e c t _ A d d _ S t e p
T h e ` ` E x t e r n a l P r o j e c t _ A d d _ S t e p ` ` f u n c t i o n a d d s a c u s t o m s t e p t o a n
e x t e r n a l p r o j e c t : :
ExternalProject_Add_Step ( <name> <step> [<option>...] )
O p t i o n s a r e :
` ` C O M M A N D < c m d > . . . ` `
C o m m a n d l i n e i n v o k e d b y t h i s s t e p
` ` C O M M E N T " < t e x t > . . . " ` `
T e x t p r i n t e d w h e n s t e p e x e c u t e s
` ` D E P E N D E E S < s t e p > . . . ` `
S t e p s o n w h i c h t h i s s t e p d e p e n d s
` ` D E P E N D E R S < s t e p > . . . ` `
S t e p s t h a t d e p e n d o n t h i s s t e p
` ` D E P E N D S < f i l e > . . . ` `
F i l e s o n w h i c h t h i s s t e p d e p e n d s
` ` B Y P R O D U C T S < f i l e > . . . ` `
F i l e s t h a t w i l l b e g e n e r a t e d b y t h i s s t e p b u t m a y o r m a y n o t
h a v e t h e i r m o d i f i c a t i o n t i m e u p d a t e d b y s u b s e q u e n t b u i l d s .
` ` A L W A Y S 1 ` `
N o s t a m p f i l e , s t e p a l w a y s r u n s
` ` E X C L U D E _ F R O M _ M A I N 1 ` `
M a i n t a r g e t d o e s n o t d e p e n d o n t h i s s t e p
` ` W O R K I N G _ D I R E C T O R Y < d i r > ` `
W o r k i n g d i r e c t o r y f o r c o m m a n d
` ` L O G 1 ` `
W r a p s t e p i n s c r i p t t o l o g o u t p u t
` ` U S E S _ T E R M I N A L 1 ` `
G i v e t h e s t e p d i r e c t a c c e s s t o t h e t e r m i n a l i f p o s s i b l e .
T h e c o m m a n d l i n e , c o m m e n t , w o r k i n g d i r e c t o r y , a n d b y p r o d u c t s o f e v e r y
s t a n d a r d a n d c u s t o m s t e p a r e p r o c e s s e d t o r e p l a c e t o k e n s ` ` < S O U R C E _ D I R > ` ` ,
` ` < B I N A R Y _ D I R > ` ` , ` ` < I N S T A L L _ D I R > ` ` , a n d ` ` < T M P _ D I R > ` ` w i t h
c o r r e s p o n d i n g p r o p e r t y v a l u e s .
A n y b u i l t i n s t e p t h a t s p e c i f i e s a ` ` < s t e p > _ C O M M A N D c m d . . . ` ` o r c u s t o m
s t e p t h a t s p e c i f i e s a ` ` C O M M A N D c m d . . . ` ` m a y s p e c i f y a d d i t i o n a l c o m m a n d
l i n e s u s i n g t h e f o r m ` ` C O M M A N D c m d . . . ` ` . A t b u i l d t i m e t h e c o m m a n d s
w i l l b e e x e c u t e d i n o r d e r a n d a b o r t e d i f a n y o n e f a i l s . F o r e x a m p l e : :
. . . B U I L D _ C O M M A N D m a k e C O M M A N D e c h o d o n e . . .
s p e c i f i e s t o r u n ` ` m a k e ` ` a n d t h e n ` ` e c h o d o n e ` ` d u r i n g t h e b u i l d s t e p .
W h e t h e r t h e c u r r e n t w o r k i n g d i r e c t o r y i s p r e s e r v e d b e t w e e n c o m m a n d s i s
n o t d e f i n e d . B e h a v i o r o f s h e l l o p e r a t o r s l i k e ` ` & & ` ` i s n o t d e f i n e d .
A r g u m e n t s t o ` ` < s t e p > _ C O M M A N D ` ` o r ` ` C O M M A N D ` ` o p t i o n s m a y u s e
: m a n u a l : ` g e n e r a t o r e x p r e s s i o n s < c m a k e - g e n e r a t o r - expressions ( 7 ) > ` .
. . c o m m a n d : : E x t e r n a l P r o j e c t _ G e t _ P r o p e r t y
T h e ` ` E x t e r n a l P r o j e c t _ G e t _ P r o p e r t y ` ` f u n c t i o n r e t r i e v e s e x t e r n a l p r o j e c t
t a r g e t p r o p e r t i e s : :
ExternalProject_Get_Property ( <name> [prop1 [prop2 [...]]] )
I t s t o r e s p r o p e r t y v a l u e s i n v a r i a b l e s o f t h e s a m e n a m e . P r o p e r t y
n a m e s c o r r e s p o n d t o t h e k e y w o r d a r g u m e n t n a m e s o f
` ` E x t e r n a l P r o j e c t _ A d d ` ` .
. . c o m m a n d : : E x t e r n a l P r o j e c t _ A d d _ S t e p T a r g e t s
T h e ` ` E x t e r n a l P r o j e c t _ A d d _ S t e p T a r g e t s ` ` f u n c t i o n g e n e r a t e s c u s t o m
t a r g e t s f o r t h e s t e p s l i s t e d : :
ExternalProject_Add_StepTargets ( <name> [NO_DEPENDS] [step1 [step2 [...]]] )
I f ` ` N O _ D E P E N D S ` ` i s s e t , t h e t a r g e t w i l l n o t d e p e n d o n t h e
d e p e n d e n c i e s o f t h e c o m p l e t e p r o j e c t . T h i s i s u s u a l l y s a f e t o u s e f o r
t h e d o w n l o a d , u p d a t e , a n d p a t c h s t e p s t h a t d o n o t r e q u i r e t h a t a l l t h e
d e p e n d e n c i e s a r e u p d a t e d a n d b u i l t . U s i n g ` ` N O _ D E P E N D S ` ` f o r o t h e r
o f t h e d e f a u l t s t e p s m i g h t b r e a k p a r a l l e l b u i l d s , s o y o u s h o u l d a v o i d ,
i t . F o r c u s t o m s t e p s , y o u s h o u l d c o n s i d e r w h e t h e r o r n o t t h e c u s t o m
c o m m a n d s r e q u i r e s t h a t t h e d e p e n d e n c i e s a r e c o n f i g u r e d , b u i l t a n d
i n s t a l l e d .
I f ` ` S T E P _ T A R G E T S ` ` o r ` ` I N D E P E N D E N T _ S T E P _ T A R G E T S ` ` i s s e t t h e n
` ` E x t e r n a l P r o j e c t _ A d d _ S t e p T a r g e t s ` ` i s a u t o m a t i c a l l y c a l l e d a t t h e e n d
o f m a t c h i n g c a l l s t o ` ` E x t e r n a l P r o j e c t _ A d d _ S t e p ` ` . P a s s
` ` S T E P _ T A R G E T S ` ` o r ` ` I N D E P E N D E N T _ S T E P _ T A R G E T S ` ` e x p l i c i t l y t o
i n d i v i d u a l ` ` E x t e r n a l P r o j e c t _ A d d ` ` c a l l s , o r i m p l i c i t l y t o a l l
` ` E x t e r n a l P r o j e c t _ A d d ` ` c a l l s b y s e t t i n g t h e d i r e c t o r y p r o p e r t i e s
` ` E P _ S T E P _ T A R G E T S ` ` a n d ` ` E P _ I N D E P E N D E N T _ S T E P _ T A R G E T S ` ` . T h e
` ` I N D E P E N D E N T ` ` v e r s i o n o f t h e a r g u m e n t a n d o f t h e p r o p e r t y w i l l c a l l
` ` E x t e r n a l P r o j e c t _ A d d _ S t e p T a r g e t s ` ` w i t h t h e ` ` N O _ D E P E N D S ` ` a r g u m e n t .
I f ` ` S T E P _ T A R G E T S ` ` a n d ` ` I N D E P E N D E N T _ S T E P _ T A R G E T S ` ` a r e n o t s e t ,
c l i e n t s m a y s t i l l m a n u a l l y c a l l ` ` E x t e r n a l P r o j e c t _ A d d _ S t e p T a r g e t s ` `
a f t e r c a l l i n g ` ` E x t e r n a l P r o j e c t _ A d d ` ` o r ` ` E x t e r n a l P r o j e c t _ A d d _ S t e p ` ` .
T h i s f u n c t i o n a l i t y i s p r o v i d e d t o m a k e i t e a s y t o d r i v e t h e s t e p s
i n d e p e n d e n t l y o f e a c h o t h e r b y s p e c i f y i n g t a r g e t s o n b u i l d c o m m a n d
l i n e s . F o r e x a m p l e , y o u m a y b e s u b m i t t i n g t o a s u b - p r o j e c t b a s e d
d a s h b o a r d , w h e r e y o u w a n t t o d r i v e t h e c o n f i g u r e p o r t i o n o f t h e b u i l d ,
t h e n s u b m i t t o t h e d a s h b o a r d , f o l l o w e d b y t h e b u i l d p o r t i o n , f o l l o w e d
b y t e s t s . I f y o u i n v o k e a c u s t o m t a r g e t t h a t d e p e n d s o n a s t e p
h a l f w a y t h r o u g h t h e s t e p d e p e n d e n c y c h a i n , t h e n a l l t h e p r e v i o u s s t e p s
w i l l a l s o r u n t o e n s u r e e v e r y t h i n g i s u p t o d a t e .
F o r e x a m p l e , t o d r i v e c o n f i g u r e , b u i l d a n d t e s t s t e p s i n d e p e n d e n t l y
f o r e a c h ` ` E x t e r n a l P r o j e c t _ A d d ` ` c a l l i n y o u r p r o j e c t , w r i t e t h e f o l l o w i n g
l i n e p r i o r t o a n y ` ` E x t e r n a l P r o j e c t _ A d d ` ` c a l l s i n y o u r ` ` C M a k e L i s t s . t x t ` `
f i l e : :
set_property ( DIRECTORY PROPERTY EP_STEP_TARGETS configure build test )
. . c o m m a n d : : E x t e r n a l P r o j e c t _ A d d _ S t e p D e p e n d e n c i e s
T h e ` ` E x t e r n a l P r o j e c t _ A d d _ S t e p D e p e n d e n c i e s ` ` f u n c t i o n a d d s o m e
d e p e n d e n c i e s f o r s o m e e x t e r n a l p r o j e c t s t e p : :
ExternalProject_Add_StepDependencies ( <name> <step> [target1 [target2 [...]]] )
T h i s f u n c t i o n t a k e s c a r e t o s e t b o t h t a r g e t a n d f i l e l e v e l
d e p e n d e n c i e s , a n d w i l l e n s u r e t h a t p a r a l l e l b u i l d s w i l l n o t b r e a k .
I t s h o u l d b e u s e d i n s t e a d o f : c o m m a n d : ` add_dependencies ( ) ` w h e n a d d i n g
a d e p e n d e n c y f o r s o m e o f t h e s t e p t a r g e t s g e n e r a t e d b y
` ` E x t e r n a l P r o j e c t ` ` .
#]=======================================================================]
#=============================================================================
# Copyright 2008-2013 Kitware, Inc.
#
# Distributed under the OSI-approved BSD License (the "License");
# see accompanying file Copyright.txt for details.
#
# This software is distributed WITHOUT ANY WARRANTY; without even the
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
# See the License for more information.
#=============================================================================
# (To distribute this file outside of CMake, substitute the full
# License text for the above reference.)
# Pre-compute a regex to match documented keywords for each command.
math ( EXPR _ep_documentation_line_count "${CMAKE_CURRENT_LIST_LINE} - 16" )
file ( STRINGS "${CMAKE_CURRENT_LIST_FILE}" lines
L I M I T _ C O U N T $ { _ e p _ d o c u m e n t a t i o n _ l i n e _ c o u n t }
R E G E X " ^ \ \ . \ \ . c o m m a n d : : [ A - Z a - z 0 - 9 _ ] + | ^ ` ` [ A - Z 0 - 9 _ ] + . * ` ` $ " )
foreach ( line IN LISTS lines )
if ( "${line}" MATCHES "^\\.\\. command:: ([A-Za-z0-9_]+)" )
if ( _ep_func )
set ( _ep_keywords_ ${ _ep_func } "${_ep_keywords_${_ep_func}})$" )
endif ( )
set ( _ep_func "${CMAKE_MATCH_1}" )
#message("function [${_ep_func}]")
set ( _ep_keywords_ ${ _ep_func } "^(" )
set ( _ep_keyword_sep )
elseif ( "${line}" MATCHES "^ ``([A-Z0-9_]+) .*``$" )
set ( _ep_key "${CMAKE_MATCH_1}" )
#message(" keyword [${_ep_key}]")
set ( _ep_keywords_ ${ _ep_func }
" $ { _ e p _ k e y w o r d s _ $ { _ e p _ f u n c } } $ { _ e p _ k e y w o r d _ s e p } $ { _ e p _ k e y } " )
set ( _ep_keyword_sep "|" )
endif ( )
endforeach ( )
if ( _ep_func )
set ( _ep_keywords_ ${ _ep_func } "${_ep_keywords_${_ep_func}})$" )
endif ( )
# Save regex matching supported hash algorithm names.
set ( _ep_hash_algos "MD5|SHA1|SHA224|SHA256|SHA384|SHA512" )
set ( _ep_hash_regex "^(${_ep_hash_algos})=([0-9A-Fa-f]+)$" )
function ( _ep_parse_arguments f name ns args )
# Transfer the arguments to this function into target properties for the
# new custom target we just added so that we can set up all the build steps
# correctly based on target properties.
#
# We loop through ARGN and consider the namespace starting with an
# upper-case letter followed by at least two more upper-case letters,
# numbers or underscores to be keywords.
set ( key )
foreach ( arg IN LISTS args )
set ( is_value 1 )
if ( arg MATCHES "^[A-Z][A-Z0-9_][A-Z0-9_]+$" AND
NOT ( ( "x${arg}x" STREQUAL "x${key}x" ) AND ( "x${key}x" STREQUAL "xCOMMANDx" ) ) A N D
N O T a r g M A T C H E S " ^ ( T R U E | F A L S E ) $ " )
if ( _ep_keywords_ ${ f } AND arg MATCHES "${_ep_keywords_${f}}" )
set ( is_value 0 )
endif ( )
endif ( )
if ( is_value )
if ( key )
# Value
if ( NOT arg STREQUAL "" )
set_property ( TARGET ${ name } APPEND PROPERTY ${ ns } ${ key } "${arg}" )
else ( )
get_property ( have_key TARGET ${ name } PROPERTY ${ ns } ${ key } SET )
if ( have_key )
get_property ( value TARGET ${ name } PROPERTY ${ ns } ${ key } )
set_property ( TARGET ${ name } PROPERTY ${ ns } ${ key } "${value};${arg}" )
else ( )
set_property ( TARGET ${ name } PROPERTY ${ ns } ${ key } "${arg}" )
endif ( )
endif ( )
else ( )
# Missing Keyword
message ( AUTHOR_WARNING "value '${arg}' with no previous keyword in ${f}" )
endif ( )
else ( )
set ( key "${arg}" )
endif ( )
endforeach ( )
endfunction ( )
define_property ( DIRECTORY PROPERTY "EP_BASE" INHERITED
B R I E F _ D O C S " B a s e d i r e c t o r y f o r E x t e r n a l P r o j e c t s t o r a g e . "
F U L L _ D O C S
" S e e d o c u m e n t a t i o n o f t h e ExternalProject_Add ( ) f u n c t i o n i n t h e "
" E x t e r n a l P r o j e c t m o d u l e . "
)
define_property ( DIRECTORY PROPERTY "EP_PREFIX" INHERITED
B R I E F _ D O C S " T o p p r e f i x f o r E x t e r n a l P r o j e c t s t o r a g e . "
F U L L _ D O C S
" S e e d o c u m e n t a t i o n o f t h e ExternalProject_Add ( ) f u n c t i o n i n t h e "
" E x t e r n a l P r o j e c t m o d u l e . "
)
define_property ( DIRECTORY PROPERTY "EP_STEP_TARGETS" INHERITED
B R I E F _ D O C S
" L i s t o f E x t e r n a l P r o j e c t s t e p s t h a t a u t o m a t i c a l l y g e t c o r r e s p o n d i n g t a r g e t s "
F U L L _ D O C S
" T h e s e t a r g e t s w i l l b e d e p e n d e n t o n t h e m a i n t a r g e t d e p e n d e n c i e s "
" S e e d o c u m e n t a t i o n o f t h e ExternalProject_Add_StepTargets ( ) f u n c t i o n i n t h e "
" E x t e r n a l P r o j e c t m o d u l e . "
)
define_property ( DIRECTORY PROPERTY "EP_INDEPENDENT_STEP_TARGETS" INHERITED
B R I E F _ D O C S
" L i s t o f E x t e r n a l P r o j e c t s t e p s t h a t a u t o m a t i c a l l y g e t c o r r e s p o n d i n g t a r g e t s "
F U L L _ D O C S
" T h e s e t a r g e t s w i l l n o t b e d e p e n d e n t o n t h e m a i n t a r g e t d e p e n d e n c i e s "
" S e e d o c u m e n t a t i o n o f t h e ExternalProject_Add_StepTargets ( ) f u n c t i o n i n t h e "
" E x t e r n a l P r o j e c t m o d u l e . "
)
define_property ( DIRECTORY PROPERTY "EP_UPDATE_DISCONNECTED" INHERITED
B R I E F _ D O C S " N e v e r u p d a t e a u t o m a t i c a l l y f r o m t h e r e m o t e r e p o . "
F U L L _ D O C S
" S e e d o c u m e n t a t i o n o f t h e ExternalProject_Add ( ) f u n c t i o n i n t h e "
" E x t e r n a l P r o j e c t m o d u l e . "
)
function ( _ep_write_gitclone_script script_filename source_dir git_EXECUTABLE git_repository git_tag git_submodules src_name work_dir gitclone_infofile gitclone_stampfile )
file ( WRITE ${ script_filename }
" if ( \"${git_tag}\" STREQUAL \"\")
message ( FATAL_ERROR \"Tag for git checkout should not be empty.\ " )
endif ( )
set ( run 0 )
if ( \"${gitclone_infofile}\" IS_NEWER_THAN \"${gitclone_stampfile}\")
set ( run 1 )
endif ( )
if ( NOT run )
message ( STATUS \"Avoiding repeated git clone, stamp file is up to date: ' ${ gitclone_stampfile } '\ " )
return ( )
endif ( )
execute_process (
C O M M A N D \ $ { C M A K E _ C O M M A N D } - E r e m o v e _ d i r e c t o r y \ " $ { s o u r c e _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to remove directory: ' ${ source_dir } '\ " )
endif ( )
# try the clone 3 times incase there is an odd git clone issue
set ( error_code 1 )
set ( number_of_tries 0 )
while ( error_code AND number_of_tries LESS 3 )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " c l o n e \ " $ { g i t _ r e p o s i t o r y } \ " \ " $ { s r c _ n a m e } \ "
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
math ( EXPR number_of_tries \"\${number_of_tries} + 1\ " )
endwhile ( )
if ( number_of_tries GREATER 1 )
message ( STATUS \"Had to git clone more than once:
\ $ { n u m b e r _ o f _ t r i e s } t i m e s . \ " )
endif ( )
if ( error_code )
message ( FATAL_ERROR \"Failed to clone repository: ' ${ git_repository } '\ " )
endif ( )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " c h e c k o u t $ { g i t _ t a g }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } / $ { s r c _ n a m e } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to checkout tag: ' ${ git_tag } '\ " )
endif ( )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s u b m o d u l e i n i t $ { g i t _ s u b m o d u l e s }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } / $ { s r c _ n a m e } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to init submodules in: ' ${ work_dir } / ${ src_name } '\ " )
endif ( )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s u b m o d u l e u p d a t e - - r e c u r s i v e $ { g i t _ s u b m o d u l e s }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } / $ { s r c _ n a m e } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to update submodules in: ' ${ work_dir } / ${ src_name } '\ " )
endif ( )
# Complete success, update the script-last-run stamp file:
#
execute_process (
C O M M A N D \ $ { C M A K E _ C O M M A N D } - E c o p y
\ " $ { g i t c l o n e _ i n f o f i l e } \ "
\ " $ { g i t c l o n e _ s t a m p f i l e } \ "
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } / $ { s r c _ n a m e } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to copy script-last-run stamp file: ' ${ gitclone_stampfile } '\ " )
endif ( )
"
)
endfunction ( )
function ( _ep_write_hgclone_script script_filename source_dir hg_EXECUTABLE hg_repository hg_tag src_name work_dir hgclone_infofile hgclone_stampfile )
file ( WRITE ${ script_filename }
" if ( \"${hg_tag}\" STREQUAL \"\")
message ( FATAL_ERROR \"Tag for hg checkout should not be empty.\ " )
endif ( )
set ( run 0 )
if ( \"${hgclone_infofile}\" IS_NEWER_THAN \"${hgclone_stampfile}\")
set ( run 1 )
endif ( )
if ( NOT run )
message ( STATUS \"Avoiding repeated hg clone, stamp file is up to date: ' ${ hgclone_stampfile } '\ " )
return ( )
endif ( )
execute_process (
C O M M A N D \ $ { C M A K E _ C O M M A N D } - E r e m o v e _ d i r e c t o r y \ " $ { s o u r c e _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to remove directory: ' ${ source_dir } '\ " )
endif ( )
execute_process (
C O M M A N D \ " $ { h g _ E X E C U T A B L E } \ " c l o n e - U \ " $ { h g _ r e p o s i t o r y } \ " \ " $ { s r c _ n a m e } \ "
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to clone repository: ' ${ hg_repository } '\ " )
endif ( )
execute_process (
C O M M A N D \ " $ { h g _ E X E C U T A B L E } \ " u p d a t e $ { h g _ t a g }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } / $ { s r c _ n a m e } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to checkout tag: ' ${ hg_tag } '\ " )
endif ( )
# Complete success, update the script-last-run stamp file:
#
execute_process (
C O M M A N D \ $ { C M A K E _ C O M M A N D } - E c o p y
\ " $ { h g c l o n e _ i n f o f i l e } \ "
\ " $ { h g c l o n e _ s t a m p f i l e } \ "
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } / $ { s r c _ n a m e } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to copy script-last-run stamp file: ' ${ hgclone_stampfile } '\ " )
endif ( )
"
)
endfunction ( )
function ( _ep_write_gitupdate_script script_filename git_EXECUTABLE git_tag git_submodules git_repository work_dir )
if ( NOT GIT_VERSION_STRING VERSION_LESS 1.7.6 )
set ( git_stash_save_options --all --quiet )
else ( )
set ( git_stash_save_options --quiet )
endif ( )
file ( WRITE ${ script_filename }
" if ( \"${git_tag}\" STREQUAL \"\")
message ( FATAL_ERROR \"Tag for git checkout should not be empty.\ " )
endif ( )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " r e v - l i s t - - m a x - c o u n t = 1 H E A D
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
O U T P U T _ V A R I A B L E h e a d _ s h a
O U T P U T _ S T R I P _ T R A I L I N G _ W H I T E S P A C E
)
if ( error_code )
message ( FATAL_ERROR \"Failed to get the hash for HEAD\ " )
endif ( )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s h o w - r e f $ { g i t _ t a g }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
O U T P U T _ V A R I A B L E s h o w _ r e f _ o u t p u t
)
# If a remote ref is asked for, which can possibly move around,
# we must always do a fetch and checkout.
if ( \"\${show_ref_output}\" MATCHES \"remotes\")
set ( is_remote_ref 1 )
else ( )
set ( is_remote_ref 0 )
endif ( )
# Tag is in the form <remote>/<tag> (i.e. origin/master) we must strip
# the remote from the tag.
if ( \"\${show_ref_output}\" MATCHES \"refs/remotes/${git_tag}\")
string ( REGEX MATCH \"^([^/]+)/(.+)$\" _unused \"${git_tag}\")
set ( git_remote \"\${CMAKE_MATCH_1}\")
set ( git_tag \"\${CMAKE_MATCH_2}\")
else ( )
set ( git_remote \"origin\")
set ( git_tag \"${git_tag}\")
endif ( )
# This will fail if the tag does not exist (it probably has not been fetched
# yet).
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " r e v - l i s t - - m a x - c o u n t = 1 $ { g i t _ t a g }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
O U T P U T _ V A R I A B L E t a g _ s h a
O U T P U T _ S T R I P _ T R A I L I N G _ W H I T E S P A C E
)
# Is the hash checkout out that we want?
if ( error_code OR is_remote_ref OR NOT ( \"\${tag_sha}\" STREQUAL \"\${head_sha}\"))
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " f e t c h
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to fetch repository ' ${ git_repository } '\ " )
endif ( )
if ( is_remote_ref )
# Check if stash is needed
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s t a t u s - - p o r c e l a i n
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
O U T P U T _ V A R I A B L E r e p o _ s t a t u s
)
if ( error_code )
message ( FATAL_ERROR \"Failed to get the status\ " )
endif ( )
string ( LENGTH \"\${repo_status}\" need_stash )
# If not in clean state, stash changes in order to be able to be able to
# perform git pull --rebase
if ( need_stash )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s t a s h s a v e $ { g i t _ s t a s h _ s a v e _ o p t i o n s }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to stash changes\ " )
endif ( )
endif ( )
# Pull changes from the remote branch
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " r e b a s e \ $ { g i t _ r e m o t e } / \ $ { g i t _ t a g }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
# Rebase failed: Restore previous state.
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " r e b a s e - - a b o r t
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
)
if ( need_stash )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s t a s h p o p - - i n d e x - - q u i e t
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
)
endif ( )
message ( FATAL_ERROR \"\\nFailed to rebase in: ' ${ work_dir } / ${ src_name } '.\\nYou will have to resolve the conflicts manually\ " )
endif ( )
if ( need_stash )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s t a s h p o p - - i n d e x - - q u i e t
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
# Stash pop --index failed: Try again dropping the index
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " r e s e t - - h a r d - - q u i e t
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s t a s h p o p - - q u i e t
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
# Stash pop failed: Restore previous state.
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " r e s e t - - h a r d - - q u i e t \ $ { h e a d _ s h a }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
)
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s t a s h p o p - - i n d e x - - q u i e t
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
)
message ( FATAL_ERROR \"\\nFailed to unstash changes in: ' ${ work_dir } / ${ src_name } '.\\nYou will have to resolve the conflicts manually\ " )
endif ( )
endif ( )
endif ( )
else ( )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " c h e c k o u t $ { g i t _ t a g }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to checkout tag: ' ${ git_tag } '\ " )
endif ( )
endif ( )
execute_process (
C O M M A N D \ " $ { g i t _ E X E C U T A B L E } \ " s u b m o d u l e u p d a t e - - r e c u r s i v e $ { g i t _ s u b m o d u l e s }
W O R K I N G _ D I R E C T O R Y \ " $ { w o r k _ d i r } / $ { s r c _ n a m e } \ "
R E S U L T _ V A R I A B L E e r r o r _ c o d e
)
if ( error_code )
message ( FATAL_ERROR \"Failed to update submodules in: ' ${ work_dir } / ${ src_name } '\ " )
endif ( )
endif ( )
"
)
endfunction ( _ep_write_gitupdate_script )
function ( _ep_write_downloadfile_script script_filename remote local timeout no_progress hash tls_verify tls_cainfo )
if ( timeout )
set ( timeout_args TIMEOUT ${ timeout } )
set ( timeout_msg "${timeout} seconds" )
else ( )
set ( timeout_args "# no TIMEOUT" )
set ( timeout_msg "none" )
endif ( )
if ( no_progress )
set ( show_progress "" )
else ( )
set ( show_progress "SHOW_PROGRESS" )
endif ( )
if ( "${hash}" MATCHES "${_ep_hash_regex}" )
string ( CONCAT hash_check
" if ( EXISTS \"${local}\")\n"
" file ( \"${CMAKE_MATCH_1}\" \"${local}\" hash_value ) \ n "
" if ( \"x\${hash_value}\" STREQUAL \"x${CMAKE_MATCH_2}\")\n"
" return ( ) \ n "
" endif ( ) \ n "
" endif ( ) \ n "
)
else ( )
set ( hash_check "" )
endif ( )
# check for curl globals in the project
if ( DEFINED CMAKE_TLS_VERIFY )
set ( tls_verify "set(CMAKE_TLS_VERIFY ${CMAKE_TLS_VERIFY})" )
endif ( )
if ( DEFINED CMAKE_TLS_CAINFO )
set ( tls_cainfo "set(CMAKE_TLS_CAINFO \" ${ CMAKE_TLS_CAINFO } \")")
endif ( )
# now check for curl locals so that the local values
# will override the globals
# check for tls_verify argument
string ( LENGTH "${tls_verify}" tls_verify_len )
if ( tls_verify_len GREATER 0 )
set ( tls_verify "set(CMAKE_TLS_VERIFY ${tls_verify})" )
endif ( )
# check for tls_cainfo argument
string ( LENGTH "${tls_cainfo}" tls_cainfo_len )
if ( tls_cainfo_len GREATER 0 )
set ( tls_cainfo "set(CMAKE_TLS_CAINFO \" ${ tls_cainfo } \")")
endif ( )
file ( WRITE ${ script_filename }
" $ { h a s h _ c h e c k } message ( STATUS \"downloading...
s r c = ' $ { r e m o t e } '
d s t = ' $ { l o c a l } '
t i m e o u t = ' $ { t i m e o u t _ m s g } ' \ " )
$ { t l s _ v e r i f y }
$ { t l s _ c a i n f o }
file ( DOWNLOAD
\ " $ { r e m o t e } \ "
\ " $ { l o c a l } \ "
$ { s h o w _ p r o g r e s s }
$ { t i m e o u t _ a r g s }
S T A T U S s t a t u s
L O G l o g )
list ( GET status 0 status_code )
list ( GET status 1 status_string )
if ( NOT status_code EQUAL 0 )
message ( FATAL_ERROR \"error: downloading ' ${ remote } ' failed
s t a t u s _ c o d e : \ $ { s t a t u s _ c o d e }
s t a t u s _ s t r i n g : \ $ { s t a t u s _ s t r i n g }
l o g : \ $ { l o g }
\ " )
endif ( )
message ( STATUS \"downloading... done\ " )
"
)
endfunction ( )
function ( _ep_write_verifyfile_script script_filename local hash retries download_script )
if ( "${hash}" MATCHES "${_ep_hash_regex}" )
set ( algo "${CMAKE_MATCH_1}" )
string ( TOLOWER "${CMAKE_MATCH_2}" expect_value )
set ( script_content "set(expect_value \" ${ expect_value } \")
set ( attempt 0 )
set ( succeeded 0 )
while ( \${attempt} LESS ${ retries } OR \${attempt} EQUAL ${ retries } AND NOT \${succeeded})
file ( ${ algo } \"\${file}\" actual_value )
if ( \"\${actual_value}\" STREQUAL \"\${expect_value}\")
set ( succeeded 1 )
elseif ( \${attempt} LESS ${ retries } )
message ( STATUS \"${algo} hash of \${file}
d o e s n o t m a t c h e x p e c t e d v a l u e
e x p e c t e d : \ $ { e x p e c t _ v a l u e }
a c t u a l : \ $ { a c t u a l _ v a l u e }
R e t r y i n g d o w n l o a d .
\ " )
file ( REMOVE \"\${file}\")
execute_process ( COMMAND \${CMAKE_COMMAND} -P \"${download_script}\")
endif ( )
math ( EXPR attempt \"\${attempt} + 1\ " )
endwhile ( )
if ( \${succeeded})
message ( STATUS \"verifying file... done\ " )
else ( )
message ( FATAL_ERROR \"error: ${ algo } hash of
\ $ { f i l e }
d o e s n o t m a t c h e x p e c t e d v a l u e
e x p e c t e d : \ $ { e x p e c t _ v a l u e }
a c t u a l : \ $ { a c t u a l _ v a l u e }
\ " )
endif ( ) " )
else ( )
set ( script_content "message(STATUS \" verifying file... warning: did not verify file - no URL_HASH specified?\ ")" )
endif ( )
file ( WRITE ${ script_filename } "set(file \" ${ local } \")
message ( STATUS \"verifying file...
f i l e = ' \ $ { f i l e } ' \ " )
$ { s c r i p t _ c o n t e n t }
" )
endfunction ( )
function ( _ep_write_extractfile_script script_filename name filename directory )
set ( args "" )
if ( filename MATCHES "(\\.|=)(7z|tar\\.bz2|tar\\.gz|tar\\.xz|tbz2|tgz|txz|zip)$" )
set ( args xfz )
endif ( )
if ( filename MATCHES "(\\.|=)tar$" )
set ( args xf )
endif ( )
if ( args STREQUAL "" )
message ( SEND_ERROR "error: do not know how to extract '${filename}' -- known types are .7z, .tar, .tar.bz2, .tar.gz, .tar.xz, .tbz2, .tgz, .txz and .zip" )
return ( )
endif ( )
file ( WRITE ${ script_filename }
" # Make file names absolute:
#
get_filename_component ( filename \"${filename}\" ABSOLUTE )
get_filename_component ( directory \"${directory}\" ABSOLUTE )
message ( STATUS \"extracting...
s r c = ' \ $ { f i l e n a m e } '
d s t = ' \ $ { d i r e c t o r y } ' \ " )
if ( NOT EXISTS \"\${filename}\")
message ( FATAL_ERROR \"error: file to extract does not exist: '\ ${ filename } '\ " )
endif ( )
# Prepare a space for extracting:
#
set ( i 1234 )
while ( EXISTS \"\${directory}/../ex-${name}\${i}\")
math ( EXPR i \"\${i} + 1\ " )
endwhile ( )
set ( ut_dir \"\${directory}/../ex-${name}\${i}\")
file ( MAKE_DIRECTORY \"\${ut_dir}\")
# Extract it:
#
message ( STATUS \"extracting... [tar ${ args } ]\ " )
execute_process ( COMMAND \${CMAKE_COMMAND} -E tar ${ args } \${filename}
W O R K I N G _ D I R E C T O R Y \ $ { u t _ d i r }
R E S U L T _ V A R I A B L E r v )
if ( NOT rv EQUAL 0 )
message ( STATUS \"extracting... [error clean up]\ " )
file ( REMOVE_RECURSE \"\${ut_dir}\")
message ( FATAL_ERROR \"error: extract of '\ ${ filename } ' failed\ " )
endif ( )
# Analyze what came out of the tar file:
#
message ( STATUS \"extracting... [analysis]\ " )
file ( GLOB contents \"\${ut_dir}/*\")
list ( LENGTH contents n )
if ( NOT n EQUAL 1 OR NOT IS_DIRECTORY \"\${contents}\")
set ( contents \"\${ut_dir}\")
endif ( )
# Move \"the one\" directory to the final directory:
#
message ( STATUS \"extracting... [rename]\ " )
file ( REMOVE_RECURSE \${directory})
get_filename_component ( contents \${contents} ABSOLUTE )
file ( RENAME \${contents} \${directory})
# Clean up:
#
message ( STATUS \"extracting... [clean up]\ " )
file ( REMOVE_RECURSE \"\${ut_dir}\")
message ( STATUS \"extracting... done\ " )
"
)
endfunction ( )
function ( _ep_set_directories name )
get_property ( prefix TARGET ${ name } PROPERTY _EP_PREFIX )
if ( NOT prefix )
get_property ( prefix DIRECTORY PROPERTY EP_PREFIX )
if ( NOT prefix )
get_property ( base DIRECTORY PROPERTY EP_BASE )
if ( NOT base )
set ( prefix "${name}-prefix" )
endif ( )
endif ( )
endif ( )
if ( prefix )
set ( tmp_default "${prefix}/tmp" )
set ( download_default "${prefix}/src" )
set ( source_default "${prefix}/src/${name}" )
set ( binary_default "${prefix}/src/${name}-build" )
set ( stamp_default "${prefix}/src/${name}-stamp" )
set ( install_default "${prefix}" )
else ( )
set ( tmp_default "${base}/tmp/${name}" )
set ( download_default "${base}/Download/${name}" )
set ( source_default "${base}/Source/${name}" )
set ( binary_default "${base}/Build/${name}" )
set ( stamp_default "${base}/Stamp/${name}" )
set ( install_default "${base}/Install/${name}" )
endif ( )
get_property ( build_in_source TARGET ${ name } PROPERTY _EP_BUILD_IN_SOURCE )
if ( build_in_source )
get_property ( have_binary_dir TARGET ${ name } PROPERTY _EP_BINARY_DIR SET )
if ( have_binary_dir )
message ( FATAL_ERROR
" E x t e r n a l p r o j e c t $ { n a m e } h a s b o t h B I N A R Y _ D I R a n d B U I L D _ I N _ S O U R C E ! " )
endif ( )
endif ( )
set ( top "${CMAKE_CURRENT_BINARY_DIR}" )
set ( places stamp download source binary install tmp )
foreach ( var ${ places } )
string ( TOUPPER "${var}" VAR )
get_property ( ${ var } _dir TARGET ${ name } PROPERTY _EP_ ${ VAR } _DIR )
if ( NOT ${ var } _dir )
set ( ${ var } _dir "${${var}_default}" )
endif ( )
if ( NOT IS_ABSOLUTE "${${var}_dir}" )
get_filename_component ( ${ var } _dir "${top}/${${var}_dir}" ABSOLUTE )
endif ( )
set_property ( TARGET ${ name } PROPERTY _EP_ ${ VAR } _DIR "${${var}_dir}" )
endforeach ( )
if ( build_in_source )
get_property ( source_dir TARGET ${ name } PROPERTY _EP_SOURCE_DIR )
set_property ( TARGET ${ name } PROPERTY _EP_BINARY_DIR "${source_dir}" )
endif ( )
# Make the directories at CMake configure time *and* add a custom command
# to make them at build time. They need to exist at makefile generation
# time for Borland make and wmake so that CMake may generate makefiles
# with "cd C:\short\paths\with\no\spaces" commands in them.
#
# Additionally, the add_custom_command is still used in case somebody
# removes one of the necessary directories and tries to rebuild without
# re-running cmake.
foreach ( var ${ places } )
string ( TOUPPER "${var}" VAR )
get_property ( dir TARGET ${ name } PROPERTY _EP_ ${ VAR } _DIR )
file ( MAKE_DIRECTORY "${dir}" )
if ( NOT EXISTS "${dir}" )
message ( FATAL_ERROR "dir '${dir}' does not exist after file(MAKE_DIRECTORY)" )
endif ( )
endforeach ( )
endfunction ( )
# IMPORTANT: this MUST be a macro and not a function because of the
# in-place replacements that occur in each ${var}
#
macro ( _ep_replace_location_tags target_name )
set ( vars ${ ARGN } )
foreach ( var ${ vars } )
if ( ${ var } )
foreach ( dir SOURCE_DIR BINARY_DIR INSTALL_DIR TMP_DIR )
get_property ( val TARGET ${ target_name } PROPERTY _EP_ ${ dir } )
string ( REPLACE "<${dir}>" "${val}" ${ var } "${${var}}" )
endforeach ( )
endif ( )
endforeach ( )
endmacro ( )
function ( _ep_command_line_to_initial_cache var args force )
set ( script_initial_cache "" )
set ( regex "^([^:]+):([^=]+)=(.*)$" )
set ( setArg "" )
set ( forceArg "" )
if ( force )
set ( forceArg "FORCE" )
endif ( )
foreach ( line ${ args } )
if ( "${line}" MATCHES "^-D(.*)" )
set ( line "${CMAKE_MATCH_1}" )
if ( setArg )
# This is required to build up lists in variables, or complete an entry
set ( setArg "${setArg}${accumulator}\" CACHE ${ type } \"Initial cache\ " ${forceArg})" )
set ( script_initial_cache "${script_initial_cache}\n${setArg}" )
set ( accumulator "" )
set ( setArg "" )
endif ( )
if ( "${line}" MATCHES "${regex}" )
set ( name "${CMAKE_MATCH_1}" )
set ( type "${CMAKE_MATCH_2}" )
set ( value "${CMAKE_MATCH_3}" )
set ( setArg "set(${name} \" ${ value } " )
else ( )
message ( WARNING "Line '${line}' does not match regex. Ignoring." )
endif ( )
else ( )
# Assume this is a list to append to the last var
set ( accumulator "${accumulator};${line}" )
endif ( )
endforeach ( )
# Catch the final line of the args
if ( setArg )
set ( setArg "${setArg}${accumulator}\" CACHE ${ type } \"Initial cache\ " ${forceArg})" )
set ( script_initial_cache "${script_initial_cache}\n${setArg}" )
endif ( )
set ( ${ var } ${ script_initial_cache } PARENT_SCOPE )
endfunction ( )
function ( _ep_write_initial_cache target_name script_filename script_initial_cache )
# Write out values into an initial cache, that will be passed to CMake with -C
# Replace location tags.
_ep_replace_location_tags ( ${ target_name } script_initial_cache )
# Write out the initial cache file to the location specified.
file ( GENERATE OUTPUT "${script_filename}" CONTENT "${script_initial_cache}" )
endfunction ( )
function ( ExternalProject_Get_Property name )
foreach ( var ${ ARGN } )
string ( TOUPPER "${var}" VAR )
get_property ( ${ var } TARGET ${ name } PROPERTY _EP_ ${ VAR } )
if ( NOT ${ var } )
message ( FATAL_ERROR "External project \" ${ name } \" has no ${ var } " )
endif ( )
set ( ${ var } "${${var}}" PARENT_SCOPE )
endforeach ( )
endfunction ( )
function ( _ep_get_configure_command_id name cfg_cmd_id_var )
get_target_property ( cmd ${ name } _EP_CONFIGURE_COMMAND )
if ( cmd STREQUAL "" )
# Explicit empty string means no configure step for this project
set ( ${ cfg_cmd_id_var } "none" PARENT_SCOPE )
else ( )
if ( NOT cmd )
# Default is "use cmake":
set ( ${ cfg_cmd_id_var } "cmake" PARENT_SCOPE )
else ( )
# Otherwise we have to analyze the value:
if ( cmd MATCHES "^[^;]*/configure" )
set ( ${ cfg_cmd_id_var } "configure" PARENT_SCOPE )
elseif ( cmd MATCHES "^[^;]*/cmake" AND NOT cmd MATCHES ";-[PE];" )
set ( ${ cfg_cmd_id_var } "cmake" PARENT_SCOPE )
elseif ( cmd MATCHES "config" )
set ( ${ cfg_cmd_id_var } "configure" PARENT_SCOPE )
else ( )
set ( ${ cfg_cmd_id_var } "unknown:${cmd}" PARENT_SCOPE )
endif ( )
endif ( )
endif ( )
endfunction ( )
function ( _ep_get_build_command name step cmd_var )
set ( cmd "${${cmd_var}}" )
if ( NOT cmd )
set ( args )
_ep_get_configure_command_id ( ${ name } cfg_cmd_id )
if ( cfg_cmd_id STREQUAL "cmake" )
# CMake project. Select build command based on generator.
get_target_property ( cmake_generator ${ name } _EP_CMAKE_GENERATOR )
if ( "${CMAKE_GENERATOR}" MATCHES "Make" AND
( " $ { c m a k e _ g e n e r a t o r } " M A T C H E S " M a k e " O R N O T c m a k e _ g e n e r a t o r ) )
# The project uses the same Makefile generator. Use recursive make.
set ( cmd "$(MAKE)" )
if ( step STREQUAL "INSTALL" )
set ( args install )
endif ( )
if ( "x${step}x" STREQUAL "xTESTx" )
set ( args test )
endif ( )
else ( )
# Drive the project with "cmake --build".
get_target_property ( cmake_command ${ name } _EP_CMAKE_COMMAND )
if ( cmake_command )
set ( cmd "${cmake_command}" )
else ( )
set ( cmd "${CMAKE_COMMAND}" )
endif ( )
set ( args --build "." )
if ( CMAKE_CFG_INTDIR AND NOT CMAKE_CFG_INTDIR STREQUAL "." )
list ( APPEND args --config "${CMAKE_CFG_INTDIR}" )
endif ( )
if ( step STREQUAL "INSTALL" )
list ( APPEND args --target install )
endif ( )
# But for "TEST" drive the project with corresponding "ctest".
if ( "x${step}x" STREQUAL "xTESTx" )
string ( REGEX REPLACE "^(.*/)cmake([^/]*)$" "\\1ctest\\2" cmd "${cmd}" )
set ( args "" )
endif ( )
endif ( )
else ( )
# Non-CMake project. Guess "make" and "make install" and "make test".
if ( "${CMAKE_GENERATOR}" MATCHES "Makefiles" )
# Try to get the parallel arguments
set ( cmd "$(MAKE)" )
else ( )
set ( cmd "make" )
endif ( )
if ( step STREQUAL "INSTALL" )
set ( args install )
endif ( )
if ( "x${step}x" STREQUAL "xTESTx" )
set ( args test )
endif ( )
endif ( )
# Use user-specified arguments instead of default arguments, if any.
get_property ( have_args TARGET ${ name } PROPERTY _EP_ ${ step } _ARGS SET )
if ( have_args )
get_target_property ( args ${ name } _EP_ ${ step } _ARGS )
endif ( )
list ( APPEND cmd ${ args } )
endif ( )
set ( ${ cmd_var } "${cmd}" PARENT_SCOPE )
endfunction ( )
function ( _ep_write_log_script name step cmd_var )
ExternalProject_Get_Property ( ${ name } stamp_dir )
set ( command "${${cmd_var}}" )
set ( make "" )
set ( code_cygpath_make "" )
if ( command MATCHES "^\\$\\(MAKE\\)" )
# GNU make recognizes the string "$(MAKE)" as recursive make, so
# ensure that it appears directly in the makefile.
string ( REGEX REPLACE "^\\$\\(MAKE\\)" "\${make}" command "${command}" )
set ( make "-Dmake=$(MAKE)" )
if ( WIN32 AND NOT CYGWIN )
set ( code_cygpath_make "
if ( \${make} MATCHES \"^/\")
execute_process (
C O M M A N D c y g p a t h - w \ $ { m a k e }
O U T P U T _ V A R I A B L E c y g p a t h _ m a k e
E R R O R _ V A R I A B L E c y g p a t h _ m a k e
R E S U L T _ V A R I A B L E c y g p a t h _ e r r o r
O U T P U T _ S T R I P _ T R A I L I N G _ W H I T E S P A C E
)
if ( NOT cygpath_error )
set ( make \${cygpath_make})
endif ( )
endif ( )
" )
endif ( )
endif ( )
set ( config "" )
if ( "${CMAKE_CFG_INTDIR}" MATCHES "^\\$" )
string ( REPLACE "${CMAKE_CFG_INTDIR}" "\${config}" command "${command}" )
set ( config "-Dconfig=${CMAKE_CFG_INTDIR}" )
endif ( )
# Wrap multiple 'COMMAND' lines up into a second-level wrapper
# script so all output can be sent to one log file.
if ( command MATCHES "(^|;)COMMAND;" )
set ( code_execute_process "
$ { c o d e _ c y g p a t h _ m a k e }
execute_process ( COMMAND \${command} RESULT_VARIABLE result )
if ( result )
set ( msg \"Command failed ( \${result}):\\n\")
foreach ( arg IN LISTS command )
set ( msg \"\${msg} '\ ${ arg } '\ " )
endforeach ( )
message ( FATAL_ERROR \"\${msg}\")
endif ( )
" )
set ( code "" )
set ( cmd "" )
set ( sep "" )
foreach ( arg IN LISTS command )
if ( "x${arg}" STREQUAL "xCOMMAND" )
if ( NOT "x${cmd}" STREQUAL "x" )
set ( code "${code}set(command \" ${ cmd } \")${code_execute_process}")
endif ( )
set ( cmd "" )
set ( sep "" )
else ( )
set ( cmd "${cmd}${sep}${arg}" )
set ( sep ";" )
endif ( )
endforeach ( )
set ( code "${code}set(command \" ${ cmd } \")${code_execute_process}")
file ( GENERATE OUTPUT "${stamp_dir}/${name}-${step}-$<CONFIG>-impl.cmake" CONTENT "${code}" )
set ( command ${ CMAKE_COMMAND } "-Dmake=\${make}" "-Dconfig=\${config}" -P ${ stamp_dir } / ${ name } - ${ step } - $< CONFIG > -impl.cmake )
endif ( )
# Wrap the command in a script to log output to files.
set ( script ${ stamp_dir } / ${ name } - ${ step } - $< CONFIG > .cmake )
set ( logbase ${ stamp_dir } / ${ name } - ${ step } )
set ( code "
$ { c o d e _ c y g p a t h _ m a k e }
set ( command \"${command}\")
execute_process (
C O M M A N D \ $ { c o m m a n d }
R E S U L T _ V A R I A B L E r e s u l t
O U T P U T _ F I L E \ " $ { l o g b a s e } - o u t . l o g \ "
E R R O R _ F I L E \ " $ { l o g b a s e } - e r r . l o g \ "
)
if ( result )
set ( msg \"Command failed: \${result}\\n\")
foreach ( arg IN LISTS command )
set ( msg \"\${msg} '\ ${ arg } '\ " )
endforeach ( )
set ( msg \"\${msg}\\nSee also\\n ${ logbase } -*.log\ " )
message ( FATAL_ERROR \"\${msg}\")
else ( )
set ( msg \"${name} ${ step } command succeeded. See also ${ logbase } -*.log\ " )
message ( STATUS \"\${msg}\")
endif ( )
" )
file ( GENERATE OUTPUT "${script}" CONTENT "${code}" )
set ( command ${ CMAKE_COMMAND } ${ make } ${ config } -P ${ script } )
set ( ${ cmd_var } "${command}" PARENT_SCOPE )
endfunction ( )
# This module used to use "/${CMAKE_CFG_INTDIR}" directly and produced
# makefiles with "/./" in paths for custom command dependencies. Which
# resulted in problems with parallel make -j invocations.
#
# This function was added so that the suffix (search below for ${cfgdir}) is
# only set to "/${CMAKE_CFG_INTDIR}" when ${CMAKE_CFG_INTDIR} is not going to
# be "." (multi-configuration build systems like Visual Studio and Xcode...)
#
function ( _ep_get_configuration_subdir_suffix suffix_var )
set ( suffix "" )
if ( CMAKE_CONFIGURATION_TYPES )
set ( suffix "/${CMAKE_CFG_INTDIR}" )
endif ( )
set ( ${ suffix_var } "${suffix}" PARENT_SCOPE )
endfunction ( )
function ( _ep_get_step_stampfile name step stampfile_var )
ExternalProject_Get_Property ( ${ name } stamp_dir )
_ep_get_configuration_subdir_suffix ( cfgdir )
set ( stampfile "${stamp_dir}${cfgdir}/${name}-${step}" )
set ( ${ stampfile_var } "${stampfile}" PARENT_SCOPE )
endfunction ( )
function ( ExternalProject_Add_StepTargets name )
set ( steps ${ ARGN } )
if ( ARGC GREATER 1 AND "${ARGV1}" STREQUAL "NO_DEPENDS" )
set ( no_deps 1 )
list ( REMOVE_AT steps 0 )
endif ( )
foreach ( step ${ steps } )
if ( no_deps AND "${step}" MATCHES "^(configure|build|install|test)$" )
message ( AUTHOR_WARNING "Using NO_DEPENDS for \" ${ step } \" step might break parallel builds " )
endif ( )
_ep_get_step_stampfile ( ${ name } ${ step } stamp_file )
add_custom_target ( ${ name } - ${ step }
D E P E N D S $ { s t a m p _ f i l e } )
set_property ( TARGET ${ name } - ${ step } PROPERTY _EP_IS_EXTERNAL_PROJECT_STEP 1 )
set_property ( TARGET ${ name } - ${ step } PROPERTY LABELS ${ name } )
set_property ( TARGET ${ name } - ${ step } PROPERTY FOLDER "ExternalProjectTargets/${name}" )
# Depend on other external projects (target-level).
if ( NOT no_deps )
get_property ( deps TARGET ${ name } PROPERTY _EP_DEPENDS )
foreach ( arg IN LISTS deps )
add_dependencies ( ${ name } - ${ step } ${ arg } )
endforeach ( )
endif ( )
endforeach ( )
endfunction ( )
function ( ExternalProject_Add_Step name step )
set ( cmf_dir ${ CMAKE_CURRENT_BINARY_DIR } /CMakeFiles )
_ep_get_configuration_subdir_suffix ( cfgdir )
set ( complete_stamp_file "${cmf_dir}${cfgdir}/${name}-complete" )
_ep_get_step_stampfile ( ${ name } ${ step } stamp_file )
_ep_parse_arguments ( ExternalProject_Add_Step
$ { n a m e } _ E P _ $ { s t e p } _ " $ { A R G N } " )
get_property ( exclude_from_main TARGET ${ name } PROPERTY _EP_ ${ step } _EXCLUDE_FROM_MAIN )
if ( NOT exclude_from_main )
add_custom_command ( APPEND
O U T P U T $ { c o m p l e t e _ s t a m p _ f i l e }
D E P E N D S $ { s t a m p _ f i l e }
)
endif ( )
# Steps depending on this step.
get_property ( dependers TARGET ${ name } PROPERTY _EP_ ${ step } _DEPENDERS )
foreach ( depender IN LISTS dependers )
_ep_get_step_stampfile ( ${ name } ${ depender } depender_stamp_file )
add_custom_command ( APPEND
O U T P U T $ { d e p e n d e r _ s t a m p _ f i l e }
D E P E N D S $ { s t a m p _ f i l e }
)
endforeach ( )
# Dependencies on files.
get_property ( depends TARGET ${ name } PROPERTY _EP_ ${ step } _DEPENDS )
# Byproducts of the step.
get_property ( byproducts TARGET ${ name } PROPERTY _EP_ ${ step } _BYPRODUCTS )
# Dependencies on steps.
get_property ( dependees TARGET ${ name } PROPERTY _EP_ ${ step } _DEPENDEES )
foreach ( dependee IN LISTS dependees )
_ep_get_step_stampfile ( ${ name } ${ dependee } dependee_stamp_file )
list ( APPEND depends ${ dependee_stamp_file } )
endforeach ( )
# The command to run.
get_property ( command TARGET ${ name } PROPERTY _EP_ ${ step } _COMMAND )
if ( command )
set ( comment "Performing ${step} step for '${name}'" )
else ( )
set ( comment "No ${step} step for '${name}'" )
endif ( )
get_property ( work_dir TARGET ${ name } PROPERTY _EP_ ${ step } _WORKING_DIRECTORY )
# Replace list separators.
get_property ( sep TARGET ${ name } PROPERTY _EP_LIST_SEPARATOR )
if ( sep AND command )
string ( REPLACE "${sep}" "\\;" command "${command}" )
endif ( )
# Replace location tags.
_ep_replace_location_tags ( ${ name } comment command work_dir byproducts )
# Custom comment?
get_property ( comment_set TARGET ${ name } PROPERTY _EP_ ${ step } _COMMENT SET )
if ( comment_set )
get_property ( comment TARGET ${ name } PROPERTY _EP_ ${ step } _COMMENT )
endif ( )
# Uses terminal?
get_property ( uses_terminal TARGET ${ name } PROPERTY _EP_ ${ step } _USES_TERMINAL )
if ( uses_terminal )
set ( uses_terminal USES_TERMINAL )
else ( )
set ( uses_terminal "" )
endif ( )
# Run every time?
get_property ( always TARGET ${ name } PROPERTY _EP_ ${ step } _ALWAYS )
if ( always )
set_property ( SOURCE ${ stamp_file } PROPERTY SYMBOLIC 1 )
set ( touch )
# Remove any existing stamp in case the option changed in an existing tree.
if ( CMAKE_CONFIGURATION_TYPES )
foreach ( cfg ${ CMAKE_CONFIGURATION_TYPES } )
string ( REPLACE "/${CMAKE_CFG_INTDIR}" "/${cfg}" stamp_file_config "${stamp_file}" )
file ( REMOVE ${ stamp_file_config } )
endforeach ( )
else ( )
file ( REMOVE ${ stamp_file } )
endif ( )
else ( )
set ( touch ${ CMAKE_COMMAND } -E touch ${ stamp_file } )
endif ( )
# Wrap with log script?
get_property ( log TARGET ${ name } PROPERTY _EP_ ${ step } _LOG )
if ( command AND log )
_ep_write_log_script ( ${ name } ${ step } command )
endif ( )
if ( "${command}" STREQUAL "" )
# Some generators (i.e. Xcode) will not generate a file level target
# if no command is set, and therefore the dependencies on this
# target will be broken.
# The empty command is replaced by an echo command here in order to
# avoid this issue.
set ( command ${ CMAKE_COMMAND } -E echo_append )
endif ( )
add_custom_command (
O U T P U T $ { s t a m p _ f i l e }
B Y P R O D U C T S $ { b y p r o d u c t s }
C O M M E N T $ { c o m m e n t }
C O M M A N D $ { c o m m a n d }
C O M M A N D $ { t o u c h }
D E P E N D S $ { d e p e n d s }
W O R K I N G _ D I R E C T O R Y $ { w o r k _ d i r }
V E R B A T I M
$ { u s e s _ t e r m i n a l }
)
set_property ( TARGET ${ name } APPEND PROPERTY _EP_STEPS ${ step } )
# Add custom "step target"?
get_property ( step_targets TARGET ${ name } PROPERTY _EP_STEP_TARGETS )
if ( NOT step_targets )
get_property ( step_targets DIRECTORY PROPERTY EP_STEP_TARGETS )
endif ( )
foreach ( st ${ step_targets } )
if ( "${st}" STREQUAL "${step}" )
ExternalProject_Add_StepTargets ( ${ name } ${ step } )
break ( )
endif ( )
endforeach ( )
get_property ( independent_step_targets TARGET ${ name } PROPERTY _EP_INDEPENDENT_STEP_TARGETS )
if ( NOT independent_step_targets )
get_property ( independent_step_targets DIRECTORY PROPERTY EP_INDEPENDENT_STEP_TARGETS )
endif ( )
foreach ( st ${ independent_step_targets } )
if ( "${st}" STREQUAL "${step}" )
ExternalProject_Add_StepTargets ( ${ name } NO_DEPENDS ${ step } )
break ( )
endif ( )
endforeach ( )
endfunction ( )
function ( ExternalProject_Add_StepDependencies name step )
set ( dependencies ${ ARGN } )
# Sanity checks on "name" and "step".
if ( NOT TARGET ${ name } )
message ( FATAL_ERROR "Cannot find target \" ${ name } \". Perhaps it has not yet been created using ExternalProject_Add. " )
endif ( )
get_property ( type TARGET ${ name } PROPERTY TYPE )
if ( NOT type STREQUAL "UTILITY" )
message ( FATAL_ERROR "Target \" ${ name } \" was not generated by ExternalProject_Add. " )
endif ( )
get_property ( is_ep TARGET ${ name } PROPERTY _EP_IS_EXTERNAL_PROJECT )
if ( NOT is_ep )
message ( FATAL_ERROR "Target \" ${ name } \" was not generated by ExternalProject_Add. " )
endif ( )
get_property ( steps TARGET ${ name } PROPERTY _EP_STEPS )
list ( FIND steps ${ step } is_step )
if ( NOT is_step )
message ( FATAL_ERROR "External project \" ${ name } \" does not have a step \"${step}\".")
endif ( )
if ( TARGET ${ name } - ${ step } )
get_property ( type TARGET ${ name } - ${ step } PROPERTY TYPE )
if ( NOT type STREQUAL "UTILITY" )
message ( FATAL_ERROR "Target \" ${ name } - ${ step } \" was not generated by ExternalProject_Add_StepTargets. " )
endif ( )
get_property ( is_ep_step TARGET ${ name } - ${ step } PROPERTY _EP_IS_EXTERNAL_PROJECT_STEP )
if ( NOT is_ep_step )
message ( FATAL_ERROR "Target \" ${ name } - ${ step } \" was not generated by ExternalProject_Add_StepTargets. " )
endif ( )
endif ( )
# Always add file-level dependency, but add target-level dependency
# only if the target exists for that step.
_ep_get_step_stampfile ( ${ name } ${ step } stamp_file )
foreach ( dep ${ dependencies } )
add_custom_command ( APPEND
O U T P U T $ { s t a m p _ f i l e }
D E P E N D S $ { d e p } )
if ( TARGET ${ name } - ${ step } )
foreach ( dep ${ dependencies } )
add_dependencies ( ${ name } - ${ step } ${ dep } )
endforeach ( )
endif ( )
endforeach ( )
endfunction ( )
function ( _ep_add_mkdir_command name )
ExternalProject_Get_Property ( ${ name }
s o u r c e _ d i r b i n a r y _ d i r i n s t a l l _ d i r s t a m p _ d i r d o w n l o a d _ d i r t m p _ d i r )
_ep_get_configuration_subdir_suffix ( cfgdir )
ExternalProject_Add_Step ( ${ name } mkdir
C O M M E N T " C r e a t i n g d i r e c t o r i e s f o r ' $ { n a m e } ' "
C O M M A N D $ { C M A K E _ C O M M A N D } - E m a k e _ d i r e c t o r y $ { s o u r c e _ d i r }
C O M M A N D $ { C M A K E _ C O M M A N D } - E m a k e _ d i r e c t o r y $ { b i n a r y _ d i r }
C O M M A N D $ { C M A K E _ C O M M A N D } - E m a k e _ d i r e c t o r y $ { i n s t a l l _ d i r }
C O M M A N D $ { C M A K E _ C O M M A N D } - E m a k e _ d i r e c t o r y $ { t m p _ d i r }
C O M M A N D $ { C M A K E _ C O M M A N D } - E m a k e _ d i r e c t o r y $ { s t a m p _ d i r } $ { c f g d i r }
C O M M A N D $ { C M A K E _ C O M M A N D } - E m a k e _ d i r e c t o r y $ { d o w n l o a d _ d i r }
)
endfunction ( )
function ( _ep_is_dir_empty dir empty_var )
file ( GLOB gr "${dir}/*" )
if ( "${gr}" STREQUAL "" )
set ( ${ empty_var } 1 PARENT_SCOPE )
else ( )
set ( ${ empty_var } 0 PARENT_SCOPE )
endif ( )
endfunction ( )
function ( _ep_add_download_command name )
ExternalProject_Get_Property ( ${ name } source_dir stamp_dir download_dir tmp_dir )
get_property ( cmd_set TARGET ${ name } PROPERTY _EP_DOWNLOAD_COMMAND SET )
get_property ( cmd TARGET ${ name } PROPERTY _EP_DOWNLOAD_COMMAND )
get_property ( cvs_repository TARGET ${ name } PROPERTY _EP_CVS_REPOSITORY )
get_property ( svn_repository TARGET ${ name } PROPERTY _EP_SVN_REPOSITORY )
get_property ( git_repository TARGET ${ name } PROPERTY _EP_GIT_REPOSITORY )
get_property ( hg_repository TARGET ${ name } PROPERTY _EP_HG_REPOSITORY )
get_property ( url TARGET ${ name } PROPERTY _EP_URL )
get_property ( fname TARGET ${ name } PROPERTY _EP_DOWNLOAD_NAME )
# TODO: Perhaps file:// should be copied to download dir before extraction.
string ( REGEX REPLACE "^file://" "" url "${url}" )
set ( depends )
set ( comment )
set ( work_dir )
if ( cmd_set )
set ( work_dir ${ download_dir } )
elseif ( cvs_repository )
find_package ( CVS QUIET )
if ( NOT CVS_EXECUTABLE )
message ( FATAL_ERROR "error: could not find cvs for checkout of ${name}" )
endif ( )
get_target_property ( cvs_module ${ name } _EP_CVS_MODULE )
if ( NOT cvs_module )
message ( FATAL_ERROR "error: no CVS_MODULE" )
endif ( )
get_property ( cvs_tag TARGET ${ name } PROPERTY _EP_CVS_TAG )
set ( repository ${ cvs_repository } )
set ( module ${ cvs_module } )
set ( tag ${ cvs_tag } )
configure_file (
" $ { C M A K E _ R O O T } / M o d u l e s / R e p o s i t o r y I n f o . t x t . i n "
" $ { s t a m p _ d i r } / $ { n a m e } - c v s i n f o . t x t "
@ O N L Y
)
get_filename_component ( src_name "${source_dir}" NAME )
get_filename_component ( work_dir "${source_dir}" PATH )
set ( comment "Performing download step (CVS checkout) for '${name}'" )
set ( cmd ${ CVS_EXECUTABLE } -d ${ cvs_repository } -q co ${ cvs_tag } -d ${ src_name } ${ cvs_module } )
list ( APPEND depends ${ stamp_dir } / ${ name } -cvsinfo.txt )
elseif ( svn_repository )
find_package ( Subversion QUIET )
if ( NOT Subversion_SVN_EXECUTABLE )
message ( FATAL_ERROR "error: could not find svn for checkout of ${name}" )
endif ( )
get_property ( svn_revision TARGET ${ name } PROPERTY _EP_SVN_REVISION )
get_property ( svn_username TARGET ${ name } PROPERTY _EP_SVN_USERNAME )
get_property ( svn_password TARGET ${ name } PROPERTY _EP_SVN_PASSWORD )
get_property ( svn_trust_cert TARGET ${ name } PROPERTY _EP_SVN_TRUST_CERT )
set ( repository "${svn_repository} user=${svn_username} password=${svn_password}" )
set ( module )
set ( tag ${ svn_revision } )
configure_file (
" $ { C M A K E _ R O O T } / M o d u l e s / R e p o s i t o r y I n f o . t x t . i n "
" $ { s t a m p _ d i r } / $ { n a m e } - s v n i n f o . t x t "
@ O N L Y
)
get_filename_component ( src_name "${source_dir}" NAME )
get_filename_component ( work_dir "${source_dir}" PATH )
set ( comment "Performing download step (SVN checkout) for '${name}'" )
set ( svn_user_pw_args "" )
if ( DEFINED svn_username )
set ( svn_user_pw_args ${ svn_user_pw_args } "--username=${svn_username}" )
endif ( )
if ( DEFINED svn_password )
set ( svn_user_pw_args ${ svn_user_pw_args } "--password=${svn_password}" )
endif ( )
if ( svn_trust_cert )
set ( svn_trust_cert_args --trust-server-cert )
endif ( )
set ( cmd ${ Subversion_SVN_EXECUTABLE } co ${ svn_repository } ${ svn_revision }
- - n o n - i n t e r a c t i v e $ { s v n _ t r u s t _ c e r t _ a r g s } $ { s v n _ u s e r _ p w _ a r g s } $ { s r c _ n a m e } )
list ( APPEND depends ${ stamp_dir } / ${ name } -svninfo.txt )
elseif ( git_repository )
unset ( CMAKE_MODULE_PATH ) # Use CMake builtin find module
find_package ( Git QUIET )
if ( NOT GIT_EXECUTABLE )
message ( FATAL_ERROR "error: could not find git for clone of ${name}" )
endif ( )
# The git submodule update '--recursive' flag requires git >= v1.6.5
#
if ( GIT_VERSION_STRING VERSION_LESS 1.6.5 )
message ( FATAL_ERROR "error: git version 1.6.5 or later required for 'git submodule update --recursive': GIT_VERSION_STRING='${GIT_VERSION_STRING}'" )
endif ( )
get_property ( git_tag TARGET ${ name } PROPERTY _EP_GIT_TAG )
if ( NOT git_tag )
set ( git_tag "master" )
endif ( )
get_property ( git_submodules TARGET ${ name } PROPERTY _EP_GIT_SUBMODULES )
# For the download step, and the git clone operation, only the repository
# should be recorded in a configured RepositoryInfo file. If the repo
# changes, the clone script should be run again. But if only the tag
# changes, avoid running the clone script again. Let the 'always' running
# update step checkout the new tag.
#
set ( repository ${ git_repository } )
set ( module )
set ( tag )
configure_file (
" $ { C M A K E _ R O O T } / M o d u l e s / R e p o s i t o r y I n f o . t x t . i n "
" $ { s t a m p _ d i r } / $ { n a m e } - g i t i n f o . t x t "
@ O N L Y
)
get_filename_component ( src_name "${source_dir}" NAME )
get_filename_component ( work_dir "${source_dir}" PATH )
# Since git clone doesn't succeed if the non-empty source_dir exists,
# create a cmake script to invoke as download command.
# The script will delete the source directory and then call git clone.
#
_ep_write_gitclone_script ( ${ tmp_dir } / ${ name } -gitclone.cmake ${ source_dir }
$ { G I T _ E X E C U T A B L E } $ { g i t _ r e p o s i t o r y } $ { g i t _ t a g } " $ { g i t _ s u b m o d u l e s } " $ { s r c _ n a m e } $ { w o r k _ d i r }
$ { s t a m p _ d i r } / $ { n a m e } - g i t i n f o . t x t $ { s t a m p _ d i r } / $ { n a m e } - g i t c l o n e - l a s t r u n . t x t
)
set ( comment "Performing download step (git clone) for '${name}'" )
set ( cmd ${ CMAKE_COMMAND } -P ${ tmp_dir } / ${ name } -gitclone.cmake )
list ( APPEND depends ${ stamp_dir } / ${ name } -gitinfo.txt )
elseif ( hg_repository )
find_package ( Hg QUIET )
if ( NOT HG_EXECUTABLE )
message ( FATAL_ERROR "error: could not find hg for clone of ${name}" )
endif ( )
get_property ( hg_tag TARGET ${ name } PROPERTY _EP_HG_TAG )
if ( NOT hg_tag )
set ( hg_tag "tip" )
endif ( )
# For the download step, and the hg clone operation, only the repository
# should be recorded in a configured RepositoryInfo file. If the repo
# changes, the clone script should be run again. But if only the tag
# changes, avoid running the clone script again. Let the 'always' running
# update step checkout the new tag.
#
set ( repository ${ hg_repository } )
set ( module )
set ( tag )
configure_file (
" $ { C M A K E _ R O O T } / M o d u l e s / R e p o s i t o r y I n f o . t x t . i n "
" $ { s t a m p _ d i r } / $ { n a m e } - h g i n f o . t x t "
@ O N L Y
)
get_filename_component ( src_name "${source_dir}" NAME )
get_filename_component ( work_dir "${source_dir}" PATH )
# Since hg clone doesn't succeed if the non-empty source_dir exists,
# create a cmake script to invoke as download command.
# The script will delete the source directory and then call hg clone.
#
_ep_write_hgclone_script ( ${ tmp_dir } / ${ name } -hgclone.cmake ${ source_dir }
$ { H G _ E X E C U T A B L E } $ { h g _ r e p o s i t o r y } $ { h g _ t a g } $ { s r c _ n a m e } $ { w o r k _ d i r }
$ { s t a m p _ d i r } / $ { n a m e } - h g i n f o . t x t $ { s t a m p _ d i r } / $ { n a m e } - h g c l o n e - l a s t r u n . t x t
)
set ( comment "Performing download step (hg clone) for '${name}'" )
set ( cmd ${ CMAKE_COMMAND } -P ${ tmp_dir } / ${ name } -hgclone.cmake )
list ( APPEND depends ${ stamp_dir } / ${ name } -hginfo.txt )
elseif ( url )
get_filename_component ( work_dir "${source_dir}" PATH )
get_property ( hash TARGET ${ name } PROPERTY _EP_URL_HASH )
if ( hash AND NOT "${hash}" MATCHES "${_ep_hash_regex}" )
message ( FATAL_ERROR "URL_HASH is set to\n ${hash}\n"
" b u t m u s t b e A L G O = v a l u e w h e r e A L G O i s \ n $ { _ e p _ h a s h _ a l g o s } \ n "
" a n d v a l u e i s a h e x s t r i n g . " )
endif ( )
get_property ( md5 TARGET ${ name } PROPERTY _EP_URL_MD5 )
if ( md5 AND NOT "MD5=${md5}" MATCHES "${_ep_hash_regex}" )
message ( FATAL_ERROR "URL_MD5 is set to\n ${md5}\nbut must be a hex string." )
endif ( )
if ( md5 AND NOT hash )
set ( hash "MD5=${md5}" )
endif ( )
set ( repository "external project URL" )
set ( module "${url}" )
set ( tag "${hash}" )
set ( retries 0 )
set ( download_script "" )
configure_file (
" $ { C M A K E _ R O O T } / M o d u l e s / R e p o s i t o r y I n f o . t x t . i n "
" $ { s t a m p _ d i r } / $ { n a m e } - u r l i n f o . t x t "
@ O N L Y
)
list ( APPEND depends ${ stamp_dir } / ${ name } -urlinfo.txt )
if ( IS_DIRECTORY "${url}" )
get_filename_component ( abs_dir "${url}" ABSOLUTE )
set ( comment "Performing download step (DIR copy) for '${name}'" )
set ( cmd ${ CMAKE_COMMAND } -E remove_directory ${ source_dir }
C O M M A N D $ { C M A K E _ C O M M A N D } - E c o p y _ d i r e c t o r y $ { a b s _ d i r } $ { s o u r c e _ d i r } )
else ( )
if ( "${url}" MATCHES "^[a-z]+://" )
# TODO: Should download and extraction be different steps?
if ( "x${fname}" STREQUAL "x" )
string ( REGEX MATCH "[^/\\?]*$" fname "${url}" )
endif ( )
if ( NOT "${fname}" MATCHES "(\\.|=)(7z|tar|tar\\.bz2|tar\\.gz|tar\\.xz|tbz2|tgz|txz|zip)$" )
string ( REGEX MATCH "([^/\\?]+(\\.|=)(7z|tar|tar\\.bz2|tar\\.gz|tar\\.xz|tbz2|tgz|txz|zip))/.*$" match_result "${url}" )
set ( fname "${CMAKE_MATCH_1}" )
endif ( )
if ( NOT "${fname}" MATCHES "(\\.|=)(7z|tar|tar\\.bz2|tar\\.gz|tar\\.xz|tbz2|tgz|txz|zip)$" )
message ( FATAL_ERROR "Could not extract tarball filename from url:\n ${url}" )
endif ( )
string ( REPLACE ";" "-" fname "${fname}" )
set ( file ${ download_dir } / ${ fname } )
get_property ( timeout TARGET ${ name } PROPERTY _EP_TIMEOUT )
get_property ( no_progress TARGET ${ name } PROPERTY _EP_DOWNLOAD_NO_PROGRESS )
get_property ( tls_verify TARGET ${ name } PROPERTY _EP_TLS_VERIFY )
get_property ( tls_cainfo TARGET ${ name } PROPERTY _EP_TLS_CAINFO )
set ( download_script "${stamp_dir}/download-${name}.cmake" )
_ep_write_downloadfile_script ( "${download_script}" "${url}" "${file}" "${timeout}" "${no_progress}" "${hash}" "${tls_verify}" "${tls_cainfo}" )
set ( cmd ${ CMAKE_COMMAND } -P "${download_script}"
C O M M A N D )
set ( retries 3 )
set ( comment "Performing download step (download, verify and extract) for '${name}'" )
else ( )
set ( file "${url}" )
set ( comment "Performing download step (verify and extract) for '${name}'" )
endif ( )
_ep_write_verifyfile_script ( "${stamp_dir}/verify-${name}.cmake" "${file}" "${hash}" "${retries}" "${download_script}" )
list ( APPEND cmd ${ CMAKE_COMMAND } -P ${ stamp_dir } /verify- ${ name } .cmake
C O M M A N D )
_ep_write_extractfile_script ( "${stamp_dir}/extract-${name}.cmake" "${name}" "${file}" "${source_dir}" )
list ( APPEND cmd ${ CMAKE_COMMAND } -P ${ stamp_dir } /extract- ${ name } .cmake )
endif ( )
else ( )
_ep_is_dir_empty ( "${source_dir}" empty )
if ( ${ empty } )
message ( SEND_ERROR
" N o d o w n l o a d i n f o g i v e n f o r ' $ { n a m e } ' a n d i t s s o u r c e d i r e c t o r y : \ n "
" $ { s o u r c e _ d i r } \ n "
" i s n o t a n e x i s t i n g n o n - e m p t y d i r e c t o r y . P l e a s e s p e c i f y o n e o f : \ n "
" * S O U R C E _ D I R w i t h a n e x i s t i n g n o n - e m p t y d i r e c t o r y \ n "
" * U R L \ n "
" * G I T _ R E P O S I T O R Y \ n "
" * H G _ R E P O S I T O R Y \ n "
" * C V S _ R E P O S I T O R Y a n d C V S _ M O D U L E \ n "
" * S V N _ R E V I S I O N \ n "
" * D O W N L O A D _ C O M M A N D "
)
endif ( )
endif ( )
get_property ( log TARGET ${ name } PROPERTY _EP_LOG_DOWNLOAD )
if ( log )
set ( log LOG 1 )
else ( )
set ( log "" )
endif ( )
get_property ( uses_terminal TARGET ${ name } PROPERTY
_ E P _ U S E S _ T E R M I N A L _ D O W N L O A D )
if ( uses_terminal )
set ( uses_terminal USES_TERMINAL 1 )
else ( )
set ( uses_terminal "" )
endif ( )
ExternalProject_Add_Step ( ${ name } download
C O M M E N T $ { c o m m e n t }
C O M M A N D $ { c m d }
W O R K I N G _ D I R E C T O R Y $ { w o r k _ d i r }
D E P E N D S $ { d e p e n d s }
D E P E N D E E S m k d i r
$ { l o g }
$ { u s e s _ t e r m i n a l }
)
endfunction ( )
function ( _ep_add_update_command name )
ExternalProject_Get_Property ( ${ name } source_dir tmp_dir )
get_property ( cmd_set TARGET ${ name } PROPERTY _EP_UPDATE_COMMAND SET )
get_property ( cmd TARGET ${ name } PROPERTY _EP_UPDATE_COMMAND )
get_property ( cvs_repository TARGET ${ name } PROPERTY _EP_CVS_REPOSITORY )
get_property ( svn_repository TARGET ${ name } PROPERTY _EP_SVN_REPOSITORY )
get_property ( git_repository TARGET ${ name } PROPERTY _EP_GIT_REPOSITORY )
get_property ( hg_repository TARGET ${ name } PROPERTY _EP_HG_REPOSITORY )
get_property ( update_disconnected_set TARGET ${ name } PROPERTY _EP_UPDATE_DISCONNECTED SET )
if ( update_disconnected_set )
get_property ( update_disconnected TARGET ${ name } PROPERTY _EP_UPDATE_DISCONNECTED )
else ( )
get_property ( update_disconnected DIRECTORY PROPERTY EP_UPDATE_DISCONNECTED )
endif ( )
set ( work_dir )
set ( comment )
set ( always )
if ( cmd_set )
set ( work_dir ${ source_dir } )
elseif ( cvs_repository )
if ( NOT CVS_EXECUTABLE )
message ( FATAL_ERROR "error: could not find cvs for update of ${name}" )
endif ( )
set ( work_dir ${ source_dir } )
set ( comment "Performing update step (CVS update) for '${name}'" )
get_property ( cvs_tag TARGET ${ name } PROPERTY _EP_CVS_TAG )
set ( cmd ${ CVS_EXECUTABLE } -d ${ cvs_repository } -q up -dP ${ cvs_tag } )
set ( always 1 )
elseif ( svn_repository )
if ( NOT Subversion_SVN_EXECUTABLE )
message ( FATAL_ERROR "error: could not find svn for update of ${name}" )
endif ( )
set ( work_dir ${ source_dir } )
set ( comment "Performing update step (SVN update) for '${name}'" )
get_property ( svn_revision TARGET ${ name } PROPERTY _EP_SVN_REVISION )
get_property ( svn_username TARGET ${ name } PROPERTY _EP_SVN_USERNAME )
get_property ( svn_password TARGET ${ name } PROPERTY _EP_SVN_PASSWORD )
get_property ( svn_trust_cert TARGET ${ name } PROPERTY _EP_SVN_TRUST_CERT )
set ( svn_user_pw_args "" )
if ( DEFINED svn_username )
set ( svn_user_pw_args ${ svn_user_pw_args } "--username=${svn_username}" )
endif ( )
if ( DEFINED svn_password )
set ( svn_user_pw_args ${ svn_user_pw_args } "--password=${svn_password}" )
endif ( )
if ( svn_trust_cert )
set ( svn_trust_cert_args --trust-server-cert )
endif ( )
set ( cmd ${ Subversion_SVN_EXECUTABLE } up ${ svn_revision }
- - n o n - i n t e r a c t i v e $ { s v n _ t r u s t _ c e r t _ a r g s } $ { s v n _ u s e r _ p w _ a r g s } )
set ( always 1 )
elseif ( git_repository )
if ( NOT GIT_EXECUTABLE )
message ( FATAL_ERROR "error: could not find git for fetch of ${name}" )
endif ( )
set ( work_dir ${ source_dir } )
set ( comment "Performing update step for '${name}'" )
get_property ( git_tag TARGET ${ name } PROPERTY _EP_GIT_TAG )
if ( NOT git_tag )
set ( git_tag "master" )
endif ( )
get_property ( git_submodules TARGET ${ name } PROPERTY _EP_GIT_SUBMODULES )
_ep_write_gitupdate_script ( ${ tmp_dir } / ${ name } -gitupdate.cmake
$ { G I T _ E X E C U T A B L E } $ { g i t _ t a g } " $ { g i t _ s u b m o d u l e s } " $ { g i t _ r e p o s i t o r y } $ { w o r k _ d i r }
)
set ( cmd ${ CMAKE_COMMAND } -P ${ tmp_dir } / ${ name } -gitupdate.cmake )
set ( always 1 )
elseif ( hg_repository )
if ( NOT HG_EXECUTABLE )
message ( FATAL_ERROR "error: could not find hg for pull of ${name}" )
endif ( )
set ( work_dir ${ source_dir } )
set ( comment "Performing update step (hg pull) for '${name}'" )
get_property ( hg_tag TARGET ${ name } PROPERTY _EP_HG_TAG )
if ( NOT hg_tag )
set ( hg_tag "tip" )
endif ( )
if ( "${HG_VERSION_STRING}" STREQUAL "2.1" )
message ( WARNING " Mercurial 2.1 does not distinguish an empty pull from a failed pull:
h t t p : / / m e r c u r i a l . s e l e n i c . c o m / w i k i / U p g r a d e N o t e s #A2.1.1:_revert_pull_return_code_change.2C_compile_issue_on_OS_X
h t t p : / / t h r e a d . g m a n e . o r g / g m a n e . c o m p . v e r s i o n - c o n t r o l . m e r c u r i a l . d e v e l / 4 7 6 5 6
U p d a t e t o M e r c u r i a l > = 2 . 1 . 1 .
" )
endif ( )
set ( cmd ${ HG_EXECUTABLE } pull
C O M M A N D $ { H G _ E X E C U T A B L E } u p d a t e $ { h g _ t a g }
)
set ( always 1 )
endif ( )
get_property ( log TARGET ${ name } PROPERTY _EP_LOG_UPDATE )
if ( log )
set ( log LOG 1 )
else ( )
set ( log "" )
endif ( )
get_property ( uses_terminal TARGET ${ name } PROPERTY
_ E P _ U S E S _ T E R M I N A L _ U P D A T E )
if ( uses_terminal )
set ( uses_terminal USES_TERMINAL 1 )
else ( )
set ( uses_terminal "" )
endif ( )
ExternalProject_Add_Step ( ${ name } update
C O M M E N T $ { c o m m e n t }
C O M M A N D $ { c m d }
A L W A Y S $ { a l w a y s }
E X C L U D E _ F R O M _ M A I N $ { u p d a t e _ d i s c o n n e c t e d }
W O R K I N G _ D I R E C T O R Y $ { w o r k _ d i r }
D E P E N D E E S d o w n l o a d
$ { l o g }
$ { u s e s _ t e r m i n a l }
)
if ( always AND update_disconnected )
_ep_get_step_stampfile ( ${ name } skip-update skip-update_stamp_file )
string ( REPLACE "Performing" "Skipping" comment "${comment}" )
ExternalProject_Add_Step ( ${ name } skip-update
C O M M E N T $ { c o m m e n t }
A L W A Y S 1
E X C L U D E _ F R O M _ M A I N 1
W O R K I N G _ D I R E C T O R Y $ { w o r k _ d i r }
D E P E N D E E S d o w n l o a d
$ { l o g }
$ { u s e s _ t e r m i n a l }
)
set_property ( SOURCE ${ skip-update_stamp_file } PROPERTY SYMBOLIC 1 )
endif ( )
endfunction ( )
function ( _ep_add_patch_command name )
ExternalProject_Get_Property ( ${ name } source_dir )
get_property ( cmd_set TARGET ${ name } PROPERTY _EP_PATCH_COMMAND SET )
get_property ( cmd TARGET ${ name } PROPERTY _EP_PATCH_COMMAND )
set ( work_dir )
if ( cmd_set )
set ( work_dir ${ source_dir } )
endif ( )
ExternalProject_Add_Step ( ${ name } patch
C O M M A N D $ { c m d }
W O R K I N G _ D I R E C T O R Y $ { w o r k _ d i r }
D E P E N D E E S d o w n l o a d
)
endfunction ( )
# TODO: Make sure external projects use the proper compiler
function ( _ep_add_configure_command name )
ExternalProject_Get_Property ( ${ name } source_dir binary_dir tmp_dir )
# Depend on other external projects (file-level).
set ( file_deps )
get_property ( deps TARGET ${ name } PROPERTY _EP_DEPENDS )
foreach ( dep IN LISTS deps )
get_property ( dep_type TARGET ${ dep } PROPERTY TYPE )
if ( dep_type STREQUAL "UTILITY" )
get_property ( is_ep TARGET ${ dep } PROPERTY _EP_IS_EXTERNAL_PROJECT )
if ( is_ep )
_ep_get_step_stampfile ( ${ dep } "done" done_stamp_file )
list ( APPEND file_deps ${ done_stamp_file } )
endif ( )
endif ( )
endforeach ( )
get_property ( cmd_set TARGET ${ name } PROPERTY _EP_CONFIGURE_COMMAND SET )
if ( cmd_set )
get_property ( cmd TARGET ${ name } PROPERTY _EP_CONFIGURE_COMMAND )
else ( )
get_target_property ( cmake_command ${ name } _EP_CMAKE_COMMAND )
if ( cmake_command )
set ( cmd "${cmake_command}" )
else ( )
set ( cmd "${CMAKE_COMMAND}" )
endif ( )
get_property ( cmake_args TARGET ${ name } PROPERTY _EP_CMAKE_ARGS )
list ( APPEND cmd ${ cmake_args } )
# If there are any CMAKE_CACHE_ARGS or CMAKE_CACHE_DEFAULT_ARGS,
# write an initial cache and use it
get_property ( cmake_cache_args TARGET ${ name } PROPERTY _EP_CMAKE_CACHE_ARGS )
get_property ( cmake_cache_default_args TARGET ${ name } PROPERTY _EP_CMAKE_CACHE_DEFAULT_ARGS )
if ( cmake_cache_args OR cmake_cache_default_args )
set ( _ep_cache_args_script "${tmp_dir}/${name}-cache-$<CONFIG>.cmake" )
if ( cmake_cache_args )
_ep_command_line_to_initial_cache ( script_initial_cache_force "${cmake_cache_args}" 1 )
endif ( )
if ( cmake_cache_default_args )
_ep_command_line_to_initial_cache ( script_initial_cache_default "${cmake_cache_default_args}" 0 )
endif ( )
_ep_write_initial_cache ( ${ name } "${_ep_cache_args_script}" "${script_initial_cache_force}${script_initial_cache_default}" )
list ( APPEND cmd "-C${_ep_cache_args_script}" )
endif ( )
get_target_property ( cmake_generator ${ name } _EP_CMAKE_GENERATOR )
get_target_property ( cmake_generator_platform ${ name } _EP_CMAKE_GENERATOR_PLATFORM )
get_target_property ( cmake_generator_toolset ${ name } _EP_CMAKE_GENERATOR_TOOLSET )
if ( cmake_generator )
list ( APPEND cmd "-G${cmake_generator}" )
if ( cmake_generator_platform )
list ( APPEND cmd "-A${cmake_generator_platform}" )
endif ( )
if ( cmake_generator_toolset )
list ( APPEND cmd "-T${cmake_generator_toolset}" )
endif ( )
else ( )
if ( CMAKE_EXTRA_GENERATOR )
list ( APPEND cmd "-G${CMAKE_EXTRA_GENERATOR} - ${CMAKE_GENERATOR}" )
else ( )
list ( APPEND cmd "-G${CMAKE_GENERATOR}" )
endif ( )
if ( cmake_generator_platform )
message ( FATAL_ERROR "Option CMAKE_GENERATOR_PLATFORM not allowed without CMAKE_GENERATOR." )
endif ( )
if ( CMAKE_GENERATOR_PLATFORM )
list ( APPEND cmd "-A${CMAKE_GENERATOR_PLATFORM}" )
endif ( )
if ( cmake_generator_toolset )
message ( FATAL_ERROR "Option CMAKE_GENERATOR_TOOLSET not allowed without CMAKE_GENERATOR." )
endif ( )
if ( CMAKE_GENERATOR_TOOLSET )
list ( APPEND cmd "-T${CMAKE_GENERATOR_TOOLSET}" )
endif ( )
endif ( )
list ( APPEND cmd "${source_dir}" )
endif ( )
# If anything about the configure command changes, (command itself, cmake
# used, cmake args or cmake generator) then re-run the configure step.
# Fixes issue http://public.kitware.com/Bug/view.php?id=10258
#
if ( NOT EXISTS ${ tmp_dir } / ${ name } -cfgcmd.txt.in )
file ( WRITE ${ tmp_dir } / ${ name } -cfgcmd.txt.in "cmd='\@cmd\@'\n" )
endif ( )
configure_file ( ${ tmp_dir } / ${ name } -cfgcmd.txt.in ${ tmp_dir } / ${ name } -cfgcmd.txt )
list ( APPEND file_deps ${ tmp_dir } / ${ name } -cfgcmd.txt )
list ( APPEND file_deps ${ _ep_cache_args_script } )
get_property ( log TARGET ${ name } PROPERTY _EP_LOG_CONFIGURE )
if ( log )
set ( log LOG 1 )
else ( )
set ( log "" )
endif ( )
get_property ( uses_terminal TARGET ${ name } PROPERTY
_ E P _ U S E S _ T E R M I N A L _ C O N F I G U R E )
if ( uses_terminal )
set ( uses_terminal USES_TERMINAL 1 )
else ( )
set ( uses_terminal "" )
endif ( )
get_property ( update_disconnected_set TARGET ${ name } PROPERTY _EP_UPDATE_DISCONNECTED SET )
if ( update_disconnected_set )
get_property ( update_disconnected TARGET ${ name } PROPERTY _EP_UPDATE_DISCONNECTED )
else ( )
get_property ( update_disconnected DIRECTORY PROPERTY EP_UPDATE_DISCONNECTED )
endif ( )
if ( update_disconnected )
set ( update_dep skip-update )
else ( )
set ( update_dep update )
endif ( )
ExternalProject_Add_Step ( ${ name } configure
C O M M A N D $ { c m d }
W O R K I N G _ D I R E C T O R Y $ { b i n a r y _ d i r }
D E P E N D E E S $ { u p d a t e _ d e p } p a t c h
D E P E N D S $ { f i l e _ d e p s }
$ { l o g }
$ { u s e s _ t e r m i n a l }
)
endfunction ( )
function ( _ep_add_build_command name )
ExternalProject_Get_Property ( ${ name } binary_dir )
get_property ( cmd_set TARGET ${ name } PROPERTY _EP_BUILD_COMMAND SET )
if ( cmd_set )
get_property ( cmd TARGET ${ name } PROPERTY _EP_BUILD_COMMAND )
else ( )
_ep_get_build_command ( ${ name } BUILD cmd )
endif ( )
get_property ( log TARGET ${ name } PROPERTY _EP_LOG_BUILD )
if ( log )
set ( log LOG 1 )
else ( )
set ( log "" )
endif ( )
get_property ( uses_terminal TARGET ${ name } PROPERTY
_ E P _ U S E S _ T E R M I N A L _ B U I L D )
if ( uses_terminal )
set ( uses_terminal USES_TERMINAL 1 )
else ( )
set ( uses_terminal "" )
endif ( )
get_property ( build_always TARGET ${ name } PROPERTY _EP_BUILD_ALWAYS )
if ( build_always )
set ( always 1 )
else ( )
set ( always 0 )
endif ( )
get_property ( build_byproducts TARGET ${ name } PROPERTY _EP_BUILD_BYPRODUCTS )
ExternalProject_Add_Step ( ${ name } build
C O M M A N D $ { c m d }
B Y P R O D U C T S $ { b u i l d _ b y p r o d u c t s }
W O R K I N G _ D I R E C T O R Y $ { b i n a r y _ d i r }
D E P E N D E E S c o n f i g u r e
A L W A Y S $ { a l w a y s }
$ { l o g }
$ { u s e s _ t e r m i n a l }
)
endfunction ( )
function ( _ep_add_install_command name )
ExternalProject_Get_Property ( ${ name } binary_dir )
get_property ( cmd_set TARGET ${ name } PROPERTY _EP_INSTALL_COMMAND SET )
if ( cmd_set )
get_property ( cmd TARGET ${ name } PROPERTY _EP_INSTALL_COMMAND )
else ( )
_ep_get_build_command ( ${ name } INSTALL cmd )
endif ( )
get_property ( log TARGET ${ name } PROPERTY _EP_LOG_INSTALL )
if ( log )
set ( log LOG 1 )
else ( )
set ( log "" )
endif ( )
get_property ( uses_terminal TARGET ${ name } PROPERTY
_ E P _ U S E S _ T E R M I N A L _ I N S T A L L )
if ( uses_terminal )
set ( uses_terminal USES_TERMINAL 1 )
else ( )
set ( uses_terminal "" )
endif ( )
ExternalProject_Add_Step ( ${ name } install
C O M M A N D $ { c m d }
W O R K I N G _ D I R E C T O R Y $ { b i n a r y _ d i r }
D E P E N D E E S b u i l d
$ { l o g }
$ { u s e s _ t e r m i n a l }
)
endfunction ( )
function ( _ep_add_test_command name )
ExternalProject_Get_Property ( ${ name } binary_dir )
get_property ( before TARGET ${ name } PROPERTY _EP_TEST_BEFORE_INSTALL )
get_property ( after TARGET ${ name } PROPERTY _EP_TEST_AFTER_INSTALL )
get_property ( exclude TARGET ${ name } PROPERTY _EP_TEST_EXCLUDE_FROM_MAIN )
get_property ( cmd_set TARGET ${ name } PROPERTY _EP_TEST_COMMAND SET )
# Only actually add the test step if one of the test related properties is
# explicitly set. (i.e. the test step is omitted unless requested...)
#
if ( cmd_set OR before OR after OR exclude )
if ( cmd_set )
get_property ( cmd TARGET ${ name } PROPERTY _EP_TEST_COMMAND )
else ( )
_ep_get_build_command ( ${ name } TEST cmd )
endif ( )
if ( before )
set ( dependees_args DEPENDEES build )
else ( )
set ( dependees_args DEPENDEES install )
endif ( )
if ( exclude )
set ( dependers_args "" )
set ( exclude_args EXCLUDE_FROM_MAIN 1 )
else ( )
if ( before )
set ( dependers_args DEPENDERS install )
else ( )
set ( dependers_args "" )
endif ( )
set ( exclude_args "" )
endif ( )
get_property ( log TARGET ${ name } PROPERTY _EP_LOG_TEST )
if ( log )
set ( log LOG 1 )
else ( )
set ( log "" )
endif ( )
get_property ( uses_terminal TARGET ${ name } PROPERTY
_ E P _ U S E S _ T E R M I N A L _ T E S T )
if ( uses_terminal )
set ( uses_terminal USES_TERMINAL 1 )
else ( )
set ( uses_terminal "" )
endif ( )
ExternalProject_Add_Step ( ${ name } test
C O M M A N D $ { c m d }
W O R K I N G _ D I R E C T O R Y $ { b i n a r y _ d i r }
$ { d e p e n d e e s _ a r g s }
$ { d e p e n d e r s _ a r g s }
$ { e x c l u d e _ a r g s }
$ { l o g }
$ { u s e s _ t e r m i n a l }
)
endif ( )
endfunction ( )
function ( ExternalProject_Add name )
_ep_get_configuration_subdir_suffix ( cfgdir )
# Add a custom target for the external project.
set ( cmf_dir ${ CMAKE_CURRENT_BINARY_DIR } /CMakeFiles )
set ( complete_stamp_file "${cmf_dir}${cfgdir}/${name}-complete" )
# The "ALL" option to add_custom_target just tells it to not set the
# EXCLUDE_FROM_ALL target property. Later, if the EXCLUDE_FROM_ALL
# argument was passed, we explicitly set it for the target.
add_custom_target ( ${ name } ALL DEPENDS ${ complete_stamp_file } )
set_property ( TARGET ${ name } PROPERTY _EP_IS_EXTERNAL_PROJECT 1 )
set_property ( TARGET ${ name } PROPERTY LABELS ${ name } )
set_property ( TARGET ${ name } PROPERTY FOLDER "ExternalProjectTargets/${name}" )
_ep_parse_arguments ( ExternalProject_Add ${ name } _EP_ "${ARGN}" )
_ep_set_directories ( ${ name } )
_ep_get_step_stampfile ( ${ name } "done" done_stamp_file )
_ep_get_step_stampfile ( ${ name } "install" install_stamp_file )
# Set the EXCLUDE_FROM_ALL target property if required.
get_property ( exclude_from_all TARGET ${ name } PROPERTY _EP_EXCLUDE_FROM_ALL )
if ( exclude_from_all )
set_property ( TARGET ${ name } PROPERTY EXCLUDE_FROM_ALL TRUE )
endif ( )
# The 'complete' step depends on all other steps and creates a
# 'done' mark. A dependent external project's 'configure' step
# depends on the 'done' mark so that it rebuilds when this project
# rebuilds. It is important that 'done' is not the output of any
# custom command so that CMake does not propagate build rules to
# other external project targets, which may cause problems during
# parallel builds. However, the Ninja generator needs to see the entire
# dependency graph, and can cope with custom commands belonging to
# multiple targets, so we add the 'done' mark as an output for Ninja only.
set ( complete_outputs ${ complete_stamp_file } )
if ( ${ CMAKE_GENERATOR } MATCHES "Ninja" )
set ( complete_outputs ${ complete_outputs } ${ done_stamp_file } )
endif ( )
add_custom_command (
O U T P U T $ { c o m p l e t e _ o u t p u t s }
C O M M E N T " C o m p l e t e d ' $ { n a m e } ' "
C O M M A N D $ { C M A K E _ C O M M A N D } - E m a k e _ d i r e c t o r y $ { c m f _ d i r } $ { c f g d i r }
C O M M A N D $ { C M A K E _ C O M M A N D } - E t o u c h $ { c o m p l e t e _ s t a m p _ f i l e }
C O M M A N D $ { C M A K E _ C O M M A N D } - E t o u c h $ { d o n e _ s t a m p _ f i l e }
D E P E N D S $ { i n s t a l l _ s t a m p _ f i l e }
V E R B A T I M
)
# Depend on other external projects (target-level).
get_property ( deps TARGET ${ name } PROPERTY _EP_DEPENDS )
foreach ( arg IN LISTS deps )
add_dependencies ( ${ name } ${ arg } )
endforeach ( )
# Set up custom build steps based on the target properties.
# Each step depends on the previous one.
#
# The target depends on the output of the final step.
# (Already set up above in the DEPENDS of the add_custom_target command.)
#
_ep_add_mkdir_command ( ${ name } )
_ep_add_download_command ( ${ name } )
_ep_add_update_command ( ${ name } )
_ep_add_patch_command ( ${ name } )
_ep_add_configure_command ( ${ name } )
_ep_add_build_command ( ${ name } )
_ep_add_install_command ( ${ name } )
# Test is special in that it might depend on build, or it might depend
# on install.
#
_ep_add_test_command ( ${ name } )
endfunction ( )