2009-08-18 12 views
4

Ein Teil des Programms unserer Forschungsgruppe verfügt über zusätzliche Funktionen, die von der Bibliothek ctemplate zur Verfügung gestellt werden. Auf unserem datierten Cluster können wir die Software aufgrund der Kompilierung nicht erstellen, daher möchte ich diese Funktionalität trennen und steuern, ob sie über ein configure Flag wie --disable-ctemplate enthalten ist oder nicht.Wie fügt man Konfigurationsflags in Autotools hinzu und implementiert sie?

Die in C++ geschriebene Software verwendet das Autotools-Build-System —, von dem ich nicht viel Erfahrung habe. Mein Verständnis ist, dass diese Aufgabe zu erfüllen, muß ich folgendes tun:

  1. ein neues Flag in dem Configure-Skript hinzu, indem Sie einen neuen Eintrag in AC_ARG_ENABLEconfigure.ac zu schaffen.

  2. Fügen Sie einige #ifdef (oder möglicherweise #ifndef) Aussagen um den Code, der die ctemplate Bibliothek verwendet, und um einen beliebigen Code, der diesen Code aufruft.

Ich denke, der erste Schritt in etwa so aussehen würde:

AC_ARG_ENABLE(ctemplate, 
[ --disable-ctemplate Disable HTML output], 
[case "${enableval}" in 
    yes) ctemplate=false ;; 
    no) ctemplate=true ;; 
    *) AC_MSG_ERROR(bad value ${enableval} for --disable-ctemplate) ;; 
esac],[ctemplate=true]) 
AM_CONDITIONAL(NOCTEMPLATE, test x$ctemplate = xfalse) 

obwohl ich weiß nicht, ob die Logik korrekt ist, da ich dieses Beispiel aus den Beispielen angepasst haben, die --enable-FLAG stattdessen verwendet von --disable-FLAG.

Für den zweiten Schritt, ich werde wickeln Abschnitte in Präprozessor Flags wie

#ifndef NOCTEMPLATE 
void Class::MethodUsingCtemplate(...) 
{ 
    ... 
} 
#endif 

Wäre dies richtig „verdrahten“ alles, wenn ich configure --disable-ctemplate tat?

Wird auch sichergestellt, dass das Programm nicht in die ctemplate Bibliothek für die Kompilierung gehen? Wenn nicht, dann ist das alles umsonst; Es ist zwingend notwendig, dass ich die Kompilierung der ctemplate Bibliothek und abhängigen Komponenten verhindern kann.

Ich wiederhole, dass ich sowohl mit C++ als auch mit Autotools nicht vertraut bin; Ich habe einen sehr naiven ersten Ansatz zur Lösung dieses Problems gemacht. Wenn Sie Erfahrung in diesem Bereich haben, würde ich Ihre Korrekturen und Erklärungen sehr schätzen.

Antwort

5

Dies ist die Lösung, die ich zusammen nach Ich las Dokumentation, Tutorials, Hilfestellungen, Mailinglisten usw. durch und probierte einfach Dinge aus, bis sie funktionierten. Ich konnte erklären, warum sie arbeiteten.

In configure.ac stellte ich die folgenden Codezeilen

# This adds the option of compiling without using the ctemplate library, 
# which has proved troublesome for compilation on some platforms 
AC_ARG_ENABLE(ctemplate, 
    [ --disable-ctemplate Disable compilation with ctemplate and HTML output], 
    [case "${enableval}" in 
    yes | no) WITH_CTEMPLATE="${enableval}" ;; 
    *) AC_MSG_ERROR(bad value ${enableval} for --disable-ctemplate) ;; 
    esac], 
    [WITH_CTEMPLATE="yes"] 
) 

dnl Make sure we register this option with Automake, so we know whether to 
dnl descend into ctemplate for more configuration or not 
AM_CONDITIONAL([WITH_CTEMPLATE], [test "x$WITH_CTEMPLATE" = "xyes"]) 

# Define CTEMPLATE in config.h if we're going to compile against it 
if test "x$WITH_CTEMPLATE" = "xyes"; then 
    AC_DEFINE([CTEMPLATE], [], ["build using ctemplate library"]) 
    AC_MSG_NOTICE([ctemplate will be used, HTML output enabled]) 
else 
    AC_MSG_NOTICE([ctemplate will not be used, HTML output disabled]) 
fi 

Im nächsten Schritt, I die Makefile.am auf der obersten Ebene in den folgenden geändert:

if WITH_CTEMPLATE 
    MAYBE_CTEMPLATE = ctemplate 
endif 

SUBDIRS = boost libgsl $(MAYBE_CTEMPLATE) libutil ... 

in der unteren Ebene Makefile.am s , Fügte ich hinzu

if WITH_CTEMPLATE 
    # some change to the configuration 
else 
    # some other change to the configuration 
endif 

Schließlich habe ich ha d, um sicherzustellen, dass eine der wichtigsten C++ Header-Dateien (durch andere Teile des Codes enthalten) hatte die folgende:

#ifdef HAVE_CONFIG_H 
# include "config.h" 
#endif 

config.h enthält keine neuen Definitionen schafft man mit AC_DEFINE, so muss diese Datei in Teilen enthalten sein die prüfen, ob eine von dieser Route erstellte Makrodefinition definiert (undefiniert) ist.

Das hat viel Zeit gekostet und frustrierte meinerseits; Ich kann nur hoffen, diese Erklärung hier zu dokumentieren, rettet jemand anderen vor dem gleichen Schicksal.

1

Sie sind definitiv auf dem richtigen Weg. Autotools können auf den ersten Blick sehr kompliziert erscheinen, aber einer der Vorteile ist, dass es Tausende von Projekten gibt, die bereits getan haben, was Sie tun wollen. Alles, was Sie tun müssen, ist sie zu finden.

Here is a link to a Google code search for AC_ARG_DISABLE. Verrückt werden.

+0

Ist AC_ARG_DISABLE in Standard-Autotools? Ich habe die Dokumentation dafür von Google nicht gefunden. Im Vergleich zu AC_ARG_ENABLE in der Google-Codesuche gibt es nur sehr wenige Treffer. (Vergleichen Sie http://www.google.com/codesearch?hl=de&q=AC_ARG_ENABLE+disable). – gotgenes

+0

+1 für "Autotools kann auf den ersten Blick sehr kompliziert erscheinen" –

+0

Einige dieser Projekte haben ein Makro, das 'AC_ARG_DISABLE' definiert. Warum sollten sie das nicht in das Standardpaket aufnehmen? – nlucaroni

1

den Build, um zu verhindern versuchen, im ctemplate Unterverzeichnis zu kompilieren, werden Sie wie etwas zu tun:

 
if CTEMPLATE 
SUBDIRS += ctemplate 
endif 

in Makefile.am

Verwandte Themen