2010-08-31 23 views
13

Tenemos una base de código bastante grande. La gran mayoría del código se compila utilizando qmake para producir los archivos make. Sin embargo, hay algunos subproyectos que se obtienen ejecutando archivos por lotes o ejecutando otros programas.Ejecutando un programa/script de QMake

Me gustaría poder tener todo compilado usando qmake, pero no puedo entender cómo hacer que qmake simplemente ejecute un script.

Una cosa que he intentado es usar QMAKE_EXTRA_TARGETS en mi pro archivo, así:

TEMPLATE = lib 
SOURCES = placeholder.cpp 
CONFIG += no_link staticlib 
batch_runner.target = placeholder.cpp 
batch_runner.commands = my_batch_file.bat 
QMAKE_EXTRA_TARGETS = batch_runner 

entonces tengo que tener el archivo por lotes de productos placeholder.cpp así:

# do the real work here 
# ... 
# create placeholder.cpp so qmake and nmake are happy 
echo // dummy >> placeholder.cpp 

Esto parece funcionar bien. El problema es que es algo cursi. Si no especifico batch_runner.target (es decir, lo dejo en blanco) o no coloque placeholder.cpp en SOURCES, el archivo por lotes nunca se ejecutará. Esto es porque qmake no está haciendo que batch_runner.com solicite la acción para cualquier otra dependencia en el archivo Makefile.

¿Hay alguna forma mejor de hacer que QMake construya un archivo Makefile de modo que se ejecute un script cuando se ejecuta el archivo Makefile?

Respuesta

14

Parece que QMAKE_POST_LINK funciona bien para este tipo de cosas.

Esto parece hacer el trabajo. my_batch_file.bat se ejecuta cuando se ejecuta nmake (en lugar de cuando qmake se ejecuta) y no necesito hacer nada gracioso con los marcadores de posición o los archivos.

Es bastante probable que no necesite todos los elementos enumerados en 'CONFIG'.

TEMPLATE = lib 
TARGET = 
CONFIG += no_link target_predeps staticlib 

QMAKE_POST_LINK = my_batch_file.bat 
QMAKE_CLEAN  += batch_output.obj 
6

Pruebe el system() command. Por ejemplo:

system(pwd) 
+1

Interesante. Eso funciona, pero el comando se ejecuta cuando se ejecuta 'qmake' en lugar de cuando se ejecuta 'nmake'. También sucede que se ejecuta tres veces en lugar de una vez realmente debería ejecutarse. –

+1

Es posible que tenga que agregar un alcance para asegurarse de que solo se ejecute una vez. –

+0

Acabo de agregar el alcance al ejemplo, por lo que el comando se ejecuta solo una vez cuando se ejecuta qmake. – pixelgrease

1

Puede utilizar la configuración SUBDIRS para ejecutar múltiples objetivos diferentes, incluso desde el mismo archivo MAKE. Esto podría funcionar especialmente bien con sus objetivos adicionales, ya que una configuración de subdirectorio puede especificar un objetivo específico en el archivo MAKE para ejecutar (consulte undocumented qmake para obtener más información). En este caso, colocaría todos los comandos de compilación "normales" en un archivo .pro, los comandos de compilación externa en otro y un archivo .pro de subdirectorios para compilar todos ellos. No he probado nada como esto, pero debería funcionar.

regular.pro:

SOURCES += main.cpp 
TARGET = regular.exe 

external.pro:

batch_runner.commands = my_batch_file.bat 
QMAKE_EXTRA_TARGETS += batch_runner 

other_runner.commands = other_batch_file.bat 
QMAKE_EXTRA_TARGETS += other_runner 

do_it_all.pro:

TEMPLATE = subdirs 
CONFIG += ordered 

regular.file = regular.pro 
SUBDIRS += regular 

batch.file = external.pro 
batch.target = batch_runner 
SUBDIRS += batch 

other.file = external.pro 
other.target = other_runner 
SUBDIRS += other 
+0

Esto tiene el mismo problema que expliqué en mi pregunta original. El objetivo extra no se ejecutará a menos que se especifique .target (parece que no puede especificar los comandos) y el .target necesita ser realmente requerido por alguna otra parte del Makefile, de lo contrario no se ejecutará. –

5

Aquí hay otra solución:

TEMPLATE = aux 
OBJECTS_DIR = ./ 
DESTDIR = ./ 

first.commands = my_batch_file.bat 
QMAKE_EXTRA_TARGETS += first 
QMAKE_CLEAN += batch_output.obj 

La plantilla aux básicamente produce un makefile que no hace nada cuando se ejecuta sin especificar un objetivo.Las variables OBJECTS_DIR y DESTDIR se configuran en el directorio actual para evitar que qmake cree los directorios debug y release (es importante configurarlos en ./ y no solo en ., al menos en Windows). Luego, usando QMAKE_EXTRA_TARGETS, redefinimos el objetivo first para ejecutar el comando personalizado cuando el archivo MAKE se invoca sin objetivo.

Es un poco raro pero hace el trabajo bien.

Adición: Si desea evitar la generación de tres archivos make (Makefile, Makefile.Debug, Makefile.Release), puede agregar

CONFIG -= debug_and_release 

Sin embargo, si se utiliza este y dependiendo de cómo el makefile es invocado (siempre invocado manualmente, invocado por el archivo "subdirs" * .pro del directorio principal, ...), podría ser necesario crear objetivos falsos debug y release para evitar errores "sin regla para hacer objetivo ...". Por ejemplo:

release.target = release 
release-clean.target = release-clean 
release-install.target = release-install 
[...] 
debug.target = debug 
debug-clean.target = debug-clean 
debug-install.target = debug-install 
[...] 
QMAKE_EXTRA_TARGETS += release release-clean release-install [...] 
QMAKE_EXTRA_TARGETS += debug debug-clean debug-install [...] 
Cuestiones relacionadas