require 'fileutils' require "open3" require "set" describe Rscons do def rm_rf(dir) FileUtils.rm_rf(dir) if File.exists?(dir) sleep 0.2 FileUtils.rm_rf(dir) if File.exists?(dir) sleep 0.5 FileUtils.rm_rf(dir) if File.exists?(dir) sleep 1.0 FileUtils.rm_rf(dir) if File.exists?(dir) raise "Could not remove #{dir}" end end end end end before(:all) do @statics = {} @build_test_run_base_dir = File.expand_path("build_test_run") @run_results = Struct.new(:stdout, :stderr, :status) @owd = Dir.pwd rm_rf(@build_test_run_base_dir) FileUtils.mkdir_p(@build_test_run_base_dir) end before(:each) do @statics[:example_id] ||= 0 @statics[:example_id] += 1 @build_test_run_dir = "#{@build_test_run_base_dir}/test#{@statics[:example_id]}" end after(:each) do |example| Dir.chdir(@owd) if example.exception @statics[:keep_test_run_dir] = true puts "Leaving #{@build_test_run_dir} for inspection due to test failure" else rm_rf(@build_test_run_dir) end end after(:all) do unless @statics[:keep_test_run_dir] rm_rf(@build_test_run_base_dir) end end def test_dir(build_test_directory) Dir.chdir(@owd) rm_rf(@build_test_run_dir) FileUtils.cp_r("build_tests/#{build_test_directory}", @build_test_run_dir) FileUtils.mkdir("#{@build_test_run_dir}/_bin") Dir.chdir(@build_test_run_dir) end def create_exe(exe_name, contents) exe_file = "#{@build_test_run_dir}/_bin/#{exe_name}" File.open(exe_file, "wb") do |fh| fh.puts("#!/bin/sh") fh.puts(contents) end FileUtils.chmod(0755, exe_file) end def file_sub(fname) contents = File.read(fname) replaced = '' contents.each_line do |line| replaced += yield(line) end File.open(fname, 'wb') do |fh| fh.write(replaced) end end def run_rscons(options = {}) operation = options[:op] || "build" if operation.is_a?(Symbol) operation = operation.to_s end unless operation.is_a?(Array) operation = [operation] end rsconscript_args = if options[:rsconscript] %W[-f #{options[:rsconscript]}] else [] end rscons_args = options[:rscons_args] || [] if ENV["dist_specs"] exe = "#{@owd}/test/rscons.rb" else exe = "#{@owd}/bin/rscons" end command = %W[ruby -I. -r _simplecov_setup #{exe}] + rsconscript_args + rscons_args + operation @statics[:build_test_id] ||= 0 @statics[:build_test_id] += 1 command_prefix = if ENV["partial_specs"] "p" else "b" end command_name = "#{command_prefix}#{@statics[:build_test_id]}" File.open("_simplecov_setup.rb", "w") do |fh| fh.puts < :bar})).to be_truthy expect(slines.include?(%{CFLAGS => ["-O2", "-fomit-frame-pointer"]})).to be_truthy expect(slines.include?(%{CPPPATH => []})).to be_truthy end it "considers deep dependencies when deciding whether to rerun Preprocess builder" do test_dir("preprocess") result = run_rscons expect(result.stderr).to eq "" expect(lines(result.stdout)).to include "Preprocess pp" expect(File.read("pp")).to match(%r{xyz42abc}m) result = run_rscons expect(result.stderr).to eq "" expect(result.stdout).to eq "" File.open("bar.h", "w") do |fh| fh.puts "#define BAR abc88xyz" end result = run_rscons expect(result.stderr).to eq "" expect(lines(result.stdout)).to include "Preprocess pp" expect(File.read("pp")).to match(%r{abc88xyz}m) end it "allows construction variable references which expand to arrays in sources of a build target" do test_dir("simple") result = run_rscons(rsconscript: "cvar_array.rb") expect(result.stderr).to eq "" expect(File.exists?("build/e.1/simple.o")).to be_truthy expect(`./simple.exe`).to eq "This is a simple C program\n" end it "supports registering multiple build targets with the same target path" do test_dir("typical") result = run_rscons(rsconscript: "multiple_targets_same_name.rb") expect(result.stderr).to eq "" expect(File.exists?("one.o")).to be_truthy expect(lines(result.stdout)).to include *[ "CC one.o", "CC one.o", ] end it "expands target and source paths when builders are registered in build hooks" do test_dir("typical") result = run_rscons(rsconscript: "post_build_hook_expansion.rb") expect(result.stderr).to eq "" expect(File.exists?("one.o")).to be_truthy expect(File.exists?("two.o")).to be_truthy expect(lines(result.stdout)).to include *[ "CC one.o", "CC two.o", ] end it "does not re-run previously successful builders if one fails" do test_dir('simple') File.open("two.c", "w") do |fh| fh.puts("FOO") end result = run_rscons(rsconscript: "cache_successful_builds_when_one_fails.rb", rscons_args: %w[-j1]) expect(result.stderr).to match /FOO/ expect(File.exists?("simple.o")).to be_truthy expect(File.exists?("two.o")).to be_falsey File.open("two.c", "w") {|fh|} result = run_rscons(rsconscript: "cache_successful_builds_when_one_fails.rb", rscons_args: %w[-j1]) expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *[ "CC two.o", ] end it "allows overriding PROGSUFFIX" do test_dir("simple") result = run_rscons(rsconscript: "progsuffix.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *[ "CC build/e.1/simple.o", "LD simple.out", ] end it "does not use PROGSUFFIX when the Program target name expands to a value already containing an extension" do test_dir("simple") result = run_rscons(rsconscript: "progsuffix2.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *[ "CC build/e.1/simple.o", "LD simple.out", ] end it "allows overriding PROGSUFFIX from extra vars passed in to the builder" do test_dir("simple") result = run_rscons(rsconscript: "progsuffix3.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *[ "CC build/e.1/simple.o", "LD simple.xyz", ] end it "creates object files under the build root for absolute source paths" do test_dir("simple") result = run_rscons(rsconscript: "absolute_source_path.rb") expect(result.stderr).to eq "" slines = lines(result.stdout) expect(slines).to include a_string_matching %r{^CC build/e.1/.*/abs\.o$} expect(slines).to include "LD abs.exe" end it "creates shared libraries" do test_dir("shared_library") result = run_rscons expect(result.stderr).to eq "" slines = lines(result.stdout) if RUBY_PLATFORM =~ /mingw/ expect(slines).to include("SHLD mine.dll") expect(File.exists?("mine.dll")).to be_truthy else expect(slines).to include("SHLD libmine.so") expect(File.exists?("libmine.so")).to be_truthy end result = run_rscons expect(result.stderr).to eq "" expect(result.stdout).to eq "" ld_library_path_prefix = (RUBY_PLATFORM =~ /mingw/ ? "" : "LD_LIBRARY_PATH=. ") expect(`#{ld_library_path_prefix}./test-shared.exe`).to match /Hi from one/ expect(`./test-static.exe`).to match /Hi from one/ end it "creates shared libraries using C++" do test_dir("shared_library") result = run_rscons(rsconscript: "shared_library_cxx.rb") expect(result.stderr).to eq "" slines = lines(result.stdout) if RUBY_PLATFORM =~ /mingw/ expect(slines).to include("SHLD mine.dll") else expect(slines).to include("SHLD libmine.so") end result = run_rscons(rsconscript: "shared_library_cxx.rb") expect(result.stderr).to eq "" expect(result.stdout).to eq "" ld_library_path_prefix = (RUBY_PLATFORM =~ /mingw/ ? "" : "LD_LIBRARY_PATH=. ") expect(`#{ld_library_path_prefix}./test-shared.exe`).to match /Hi from one/ expect(`./test-static.exe`).to match /Hi from one/ end it "raises an error for a circular dependency" do test_dir("simple") result = run_rscons(rsconscript: "error_circular_dependency.rb") expect(result.stderr).to match /Possible circular dependency for (foo|bar|baz)/ expect(result.status).to_not eq 0 end it "raises an error for a circular dependency where a build target contains itself in its source list" do test_dir("simple") result = run_rscons(rsconscript: "error_circular_dependency2.rb") expect(result.stderr).to match /Possible circular dependency for foo/ expect(result.status).to_not eq 0 end it "orders builds to respect user dependencies" do test_dir("simple") result = run_rscons(rsconscript: "user_dep_build_order.rb", rscons_args: %w[-j4]) expect(result.stderr).to eq "" end it "waits for all parallelized builds to complete if one fails" do test_dir("simple") result = run_rscons(rsconscript: "wait_for_builds_on_failure.rb", rscons_args: %w[-j4]) expect(result.status).to_not eq 0 expect(result.stderr).to match /Failed to build foo_1/ expect(result.stderr).to match /Failed to build foo_2/ expect(result.stderr).to match /Failed to build foo_3/ expect(result.stderr).to match /Failed to build foo_4/ end it "clones n_threads attribute when cloning an Environment" do test_dir("simple") result = run_rscons(rsconscript: "clone_n_threads.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *["165"] end it "prints a builder's short description with 'command' echo mode if there is no command" do test_dir("typical") result = run_rscons(rsconscript: "echo_command_ruby_builder.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *["Install inst.exe"] end it "supports a string for a builder's echoed 'command' with Environment#print_builder_run_message" do test_dir("typical") result = run_rscons(rsconscript: "echo_command_string.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *["MyBuilder foo command"] end context "colored output" do it "does not output in color with --color=off" do test_dir("simple") result = run_rscons(rscons_args: %w[--color=off]) expect(result.stderr).to eq "" expect(result.stdout).to_not match(/\e\[/) end it "displays output in color with --color=force" do test_dir("simple") result = run_rscons(rscons_args: %w[--color=force]) expect(result.stderr).to eq "" expect(result.stdout).to match(/\e\[/) File.open("simple.c", "wb") do |fh| fh.write("foobar") end result = run_rscons(rscons_args: %w[--color=force]) expect(result.stderr).to match(/\e\[/) end end context "backward compatibility" do it "allows a builder to call Environment#run_builder in a non-threaded manner" do test_dir("simple") result = run_rscons(rsconscript: "run_builder.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *[ "CC simple.o", "LD simple.exe", ] end it "allows a builder to call Environment#build_sources in a non-threaded manner" do test_dir("simple") result = run_rscons(rsconscript: "build_sources.rb") expect(result.stderr).to eq "" expect(lines(result.stdout)).to include *[ "CC simple.o", "CC build/e.1/two.o", "MyProgram simple.exe", ] end it "prints the failed build command for a non-threaded builder" do test_dir("simple") File.open("simple.c", "wb") do |fh| fh.write(< "when no arguments are given", "check_c_compiler_find_first.rb" => "when arguments are given"}.each_pair do |rsconscript, desc| context desc do it "finds the first listed C compiler" do test_dir "configure" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C compiler\.\.\. gcc/ end it "finds the second listed C compiler" do test_dir "configure" create_exe "gcc", "exit 1" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C compiler\.\.\. clang/ end it "fails to configure when it cannot find a C compiler" do test_dir "configure" create_exe "gcc", "exit 1" create_exe "clang", "exit 1" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for C compiler\.\.\. not found/ end end end it "successfully tests a compiler with an unknown name" do test_dir "configure" create_exe "mycompiler", %[exec gcc "$@"] result = run_rscons(rsconscript: "check_c_compiler_custom.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C compiler\.\.\. mycompiler/ end end context "check_cxx_compiler" do {"check_cxx_compiler.rb" => "when no arguments are given", "check_cxx_compiler_find_first.rb" => "when arguments are given"}.each_pair do |rsconscript, desc| context desc do it "finds the first listed C++ compiler" do test_dir "configure" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C\+\+ compiler\.\.\. g\+\+/ end it "finds the second listed C++ compiler" do test_dir "configure" create_exe "g++", "exit 1" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C\+\+ compiler\.\.\. clang\+\+/ end it "fails to configure when it cannot find a C++ compiler" do test_dir "configure" create_exe "g++", "exit 1" create_exe "clang++", "exit 1" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for C\+\+ compiler\.\.\. not found/ end end end it "successfully tests a compiler with an unknown name" do test_dir "configure" create_exe "mycompiler", %[exec clang++ "$@"] result = run_rscons(rsconscript: "check_cxx_compiler_custom.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C\+\+ compiler\.\.\. mycompiler/ end end context "check_d_compiler" do {"check_d_compiler.rb" => "when no arguments are given", "check_d_compiler_find_first.rb" => "when arguments are given"}.each_pair do |rsconscript, desc| context desc do it "finds the first listed D compiler" do test_dir "configure" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for D compiler\.\.\. gdc/ end it "finds the second listed D compiler" do test_dir "configure" create_exe "gdc", "exit 1" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for D compiler\.\.\. ldc2/ end it "fails to configure when it cannot find a D compiler" do test_dir "configure" create_exe "gdc", "exit 1" create_exe "ldc2", "exit 1" result = run_rscons(rsconscript: rsconscript, op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for D compiler\.\.\. not found/ end end end it "successfully tests a compiler with an unknown name that uses gdc-compatible options" do test_dir "configure" create_exe "mycompiler", %[exec gdc "$@"] result = run_rscons(rsconscript: "check_d_compiler_custom.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for D compiler\.\.\. mycompiler/ end it "successfully tests a compiler with an unknown name that uses ldc2-compatible options" do test_dir "configure" create_exe "mycompiler", %[exec ldc2 "$@"] result = run_rscons(rsconscript: "check_d_compiler_custom.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for D compiler\.\.\. mycompiler/ end end context "check_c_header" do it "succeeds when the requested header is found" do test_dir "configure" result = run_rscons(rsconscript: "check_c_header_success.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C header 'string\.h'... found/ end it "fails when the requested header is not found" do test_dir "configure" result = run_rscons(rsconscript: "check_c_header_failure.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for C header 'not___found\.h'... not found/ end it "succeeds when the requested header is not found but :fail is set to false" do test_dir "configure" result = run_rscons(rsconscript: "check_c_header_no_fail.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C header 'not___found\.h'... not found/ end it "sets the specified define when the header is found" do test_dir "configure" result = run_rscons(rsconscript: "check_c_header_success_set_define.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C header 'string\.h'... found/ result = run_rscons(rsconscript: "check_c_header_success_set_define.rb", op: "build") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /-DHAVE_STRING_H/ end it "does not set the specified define when the header is not found" do test_dir "configure" result = run_rscons(rsconscript: "check_c_header_no_fail_set_define.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C header 'not___found\.h'... not found/ result = run_rscons(rsconscript: "check_c_header_no_fail_set_define.rb", op: "build") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to_not match /-DHAVE_/ end end context "check_cxx_header" do it "succeeds when the requested header is found" do test_dir "configure" result = run_rscons(rsconscript: "check_cxx_header_success.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C\+\+ header 'string\.h'... found/ end it "fails when the requested header is not found" do test_dir "configure" result = run_rscons(rsconscript: "check_cxx_header_failure.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for C\+\+ header 'not___found\.h'... not found/ end it "succeeds when the requested header is not found but :fail is set to false" do test_dir "configure" result = run_rscons(rsconscript: "check_cxx_header_no_fail.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for C\+\+ header 'not___found\.h'... not found/ end end context "check_d_import" do it "succeeds when the requested import is found" do test_dir "configure" result = run_rscons(rsconscript: "check_d_import_success.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for D import 'std\.stdio'... found/ end it "fails when the requested import is not found" do test_dir "configure" result = run_rscons(rsconscript: "check_d_import_failure.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for D import 'not\.found'... not found/ end it "succeeds when the requested import is not found but :fail is set to false" do test_dir "configure" result = run_rscons(rsconscript: "check_d_import_no_fail.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for D import 'not\.found'... not found/ end end context "check_lib" do it "succeeds when the requested library is found" do test_dir "configure" result = run_rscons(rsconscript: "check_lib_success.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for library 'm'... found/ end it "fails when the requested library is not found" do test_dir "configure" result = run_rscons(rsconscript: "check_lib_failure.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for library 'mfoofoo'... not found/ end it "succeeds when the requested library is not found but :fail is set to false" do test_dir "configure" result = run_rscons(rsconscript: "check_lib_no_fail.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for library 'mfoofoo'... not found/ end it "links against the checked library by default" do test_dir "configure" result = run_rscons(rsconscript: "check_lib_success.rb", op: "build") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for library 'm'... found/ expect(result.stdout).to match /gcc.*-lm/ end end context "check_program" do it "succeeds when the requested program is found" do test_dir "configure" result = run_rscons(rsconscript: "check_program_success.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for program 'find'... .*find/ end it "fails when the requested program is not found" do test_dir "configure" result = run_rscons(rsconscript: "check_program_failure.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking for program 'program-that-is-not-found'... not found/ end it "succeeds when the requested program is not found but :fail is set to false" do test_dir "configure" result = run_rscons(rsconscript: "check_program_no_fail.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for program 'program-that-is-not-found'... not found/ end end context "check_cfg" do context "when passed a package" do it "stores flags and uses them during a build operation" do test_dir "configure" create_exe "pkg-config", "echo '-DMYPACKAGE'" result = run_rscons(rsconscript: "check_cfg_package.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking for package 'mypackage'\.\.\. found/ result = run_rscons(rsconscript: "check_cfg_package.rb", op: "build") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /gcc.*-o.*\.o.*-DMYPACKAGE/ end it "fails when the configure program given does not exist" do test_dir "configure" result = run_rscons(rsconscript: "check_cfg.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to_not eq 0 expect(result.stdout).to match /Checking 'my-config'\.\.\. not found/ end end context "when passed a program" do it "stores flags and uses them during a build operation" do test_dir "configure" create_exe "my-config", "echo '-DMYCONFIG -lm'" result = run_rscons(rsconscript: "check_cfg.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Checking 'my-config'\.\.\. found/ result = run_rscons(rsconscript: "check_cfg.rb", op: "build") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /gcc.*-o.*\.o.*-DMYCONFIG/ expect(result.stdout).to match /gcc.*-o myconfigtest.*-lm/ end end end it "does everything" do test_dir "configure" create_exe "pkg-config", "echo '-DMYPACKAGE'" result = run_rscons(rsconscript: "everything.rb", op: %w[configure --build=bb --prefix=/my/prefix]) expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /Configuring configure test\.\.\./ expect(result.stdout).to match /Setting build directory\.\.\. bb/ expect(result.stdout).to match %r{Setting prefix\.\.\. /my/prefix} expect(result.stdout).to match /Checking for C compiler\.\.\. gcc/ expect(result.stdout).to match /Checking for C\+\+ compiler\.\.\. g++/ expect(result.stdout).to match /Checking for D compiler\.\.\. gdc/ expect(result.stdout).to match /Checking for package 'mypackage'\.\.\. found/ expect(result.stdout).to match /Checking for C header 'stdio.h'\.\.\. found/ expect(result.stdout).to match /Checking for C\+\+ header 'iostream'\.\.\. found/ expect(result.stdout).to match /Checking for D import 'std.stdio'\.\.\. found/ expect(result.stdout).to match /Checking for library 'm'\.\.\. found/ expect(result.stdout).to match /Checking for program 'ls'\.\.\. .*ls/ end it "aggregates multiple set_define's" do test_dir "configure" result = run_rscons(rsconscript: "multiple_set_define.rb", op: "configure") expect(result.stderr).to eq "" expect(result.status).to eq 0 result = run_rscons(rsconscript: "multiple_set_define.rb", op: "build") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to match /gcc.*-o.*\.o.*-DHAVE_MATH_H\s.*-DHAVE_STDIO_H/ end it "exits with an error if the project is not configured and a build is requested and autoconf is false" do test_dir "configure" result = run_rscons(rsconscript: "autoconf_false.rb") expect(result.stderr).to match /Project must be configured first, and autoconf is disabled/ expect(result.status).to_not eq 0 end it "exits with an error if configuration fails during autoconf" do test_dir "configure" result = run_rscons(rsconscript: "autoconf_fail.rb") expect(result.stdout).to match /Checking for C compiler\.\.\. not found/ expect(result.status).to_not eq 0 end it "exits with an error if configuration has not been performed before attempting to process an environment" do test_dir "configure" result = run_rscons(rsconscript: "error_env_process_before_configure.rb") expect(result.stderr).to match /Project must be configured before processing an Environment/ expect(result.status).to_not eq 0 end it "does not rebuild after building with auto-configuration" do test_dir "configure" result = run_rscons(rsconscript: "autoconf_rebuild.rb") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(File.exists?("simple.exe")).to be_truthy result = run_rscons(rsconscript: "autoconf_rebuild.rb") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(result.stdout).to eq "" end end context "distclean" do it "removes built files and the build directory" do test_dir "simple" result = run_rscons(rsconscript: "distclean.rb") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(File.exists?("simple.o")).to be_truthy expect(File.exists?("build")).to be_truthy result = run_rscons(rsconscript: "distclean.rb", op: "distclean") expect(result.stderr).to eq "" expect(result.status).to eq 0 expect(File.exists?("simple.o")).to be_falsey expect(File.exists?("build")).to be_falsey expect(File.exists?(Rscons::Cache::CACHE_FILE)).to be_falsey end end end