cemulate
cemulate

Reputation: 2333

scons behavior after running twice in a row

I'm trying to get scons configured as conveniently as possible. My build script works fine, but I'm still having trouble with one thing.

With make, if I run just 'make' twice in a row, the second time will do nothing because it will detect that the target is up to date (because I just built it).

How can I make sure that scons behaves the same? Right now, if I run scons a second time, it thinks the target needs to be built again, and furthermore, it fails to build because of conflicting dependencies of all the leftover .o files (because clean was not called first).

How can I get scons to handle this by itself, i.e. detect if the target is out of date and if so rebuild accordingly?

Also, I've noticed that if I call

scons
scons -q

a build and then DIRECTLY question, the exit status is still always 1. If I understand correctly, it should be 0 because the target is up to date.

Any help appreciated!

EDIT:

Here is my SConstruct file. If I am doing anything wrong, please bring it to my attention:

import os

env = Environment(CXX = "C:/MinGW/bin/g++", CCFLAGS = "-g")
env.Tool("mingw")

sourceList = list('./src/' + x for x in os.listdir("./src"))

pathList = ['./include',
            'C:/boost',
            'C:/frameworks/SFML/include',
            'C:/Python27/include']

libPathList = ['C:/boost/stage/lib', 'C:/frameworks/SFML/lib', 'C:/Python27/libs']
libList = ['boost_thread-mgw45-mt-1_46_1',
           'boost_python-mgw45-mt-1_46_1', 
           'sfml-system',
           'sfml-window',
           'sfml-graphics',
           'python27']

env.Append(CPPPATH=pathList)
env.Append(LIBPATH=libPathList)
env.Append(LIBS=libList)

t = env.Program(target='./bin/build_result.exe', source=sourceList)
Default(t)

Yes, I know I should add the proper debug options at all, but I can refine the file later. However, I don't know if there are any issues relating to what I'm experiencing. Furthermore, this file works exactly right for a smaller test project:

import os

env = Environment(CXX = "C:/MinGW/bin/g++", CCFLAGS = "-g")
env.Tool("mingw")

sourceList = os.listdir('.')
sourceList = list(x for x in sourceList if x[-3:] == 'cpp')

t = env.Program(target='./result.exe', source=sourceList)
Default(t)

"scons -q" works as expected too. Any idea what's going on?

Upvotes: 3

Views: 399

Answers (2)

Brady
Brady

Reputation: 10357

A more common way to specify the source files to be compiled in SCons is as follows:

sourceList = Glob('#/src/*.cpp')
t = env.Program(target='#/bin/build_result.exe', source=sourceList)

Notice the '#' character in the path. In SCons that means relative to the directory where the SConstruct file is located. Glob() documentation. SConstruct relative path documentation.

Additionally, you could configure everything in the SConstruct file and then use the SConscript() function to load a SConscript file in the src dir, which would import the env created in the SConstruct and simply specify what files to compile and the necessary target. This would be more future proof, making it easier to add more source directories, each with their own SConscript file. This is called SCons Hierarchical Builds.

Upvotes: 2

cemulate
cemulate

Reputation: 2333

Aha, found the problem. Below this line:

sourceList = list('./src/' + x for x in os.listdir("./src"))

I should have added

sourceList = list(x for x in sourceList if x[-3:] == 'cpp')

The first build, .o file were generated IN the ./src directory, so the second time it was picking up object files as sources. Problem solved.

Upvotes: 1

Related Questions