From 64d15602cca61c4915d5ec4a94ed1cbf0b0ac10d Mon Sep 17 00:00:00 2001 From: Josh Holtrop Date: Thu, 12 Sep 2013 23:35:34 -0400 Subject: [PATCH] add Library default builder --- build_tests/library/build.rb | 4 ++++ build_tests/library/one.c | 8 ++++++++ build_tests/library/three.c | 0 build_tests/library/two.c | 0 lib/rscons.rb | 2 ++ lib/rscons/builders/library.rb | 33 +++++++++++++++++++++++++++++++++ lib/rscons/environment.rb | 3 +++ spec/build_tests_spec.rb | 13 +++++++++++++ 8 files changed, 63 insertions(+) create mode 100644 build_tests/library/build.rb create mode 100644 build_tests/library/one.c create mode 100644 build_tests/library/three.c create mode 100644 build_tests/library/two.c create mode 100644 lib/rscons/builders/library.rb diff --git a/build_tests/library/build.rb b/build_tests/library/build.rb new file mode 100644 index 0000000..3671c62 --- /dev/null +++ b/build_tests/library/build.rb @@ -0,0 +1,4 @@ +Rscons::Environment.new(echo: :command) do |env| + env.Program('library', ['lib.a', 'three.c']) + env.Library("lib.a", ['one.c', 'two.c'], 'CPPFLAGS' => ['-Dmake_lib']) +end diff --git a/build_tests/library/one.c b/build_tests/library/one.c new file mode 100644 index 0000000..7b74439 --- /dev/null +++ b/build_tests/library/one.c @@ -0,0 +1,8 @@ +#include + +#ifdef make_lib +int main(int argc, char *argv[]) +{ + printf("Library\n"); +} +#endif diff --git a/build_tests/library/three.c b/build_tests/library/three.c new file mode 100644 index 0000000..e69de29 diff --git a/build_tests/library/two.c b/build_tests/library/two.c new file mode 100644 index 0000000..e69de29 diff --git a/lib/rscons.rb b/lib/rscons.rb index 744a71c..042cfa9 100644 --- a/lib/rscons.rb +++ b/lib/rscons.rb @@ -8,12 +8,14 @@ require "rscons/monkey/module" require "rscons/monkey/string" # default builders +require "rscons/builders/library" require "rscons/builders/object" require "rscons/builders/program" # Namespace module for rscons classes module Rscons DEFAULT_BUILDERS = [ + Library, Object, Program, ] diff --git a/lib/rscons/builders/library.rb b/lib/rscons/builders/library.rb new file mode 100644 index 0000000..cfaa76a --- /dev/null +++ b/lib/rscons/builders/library.rb @@ -0,0 +1,33 @@ +require 'fileutils' + +module Rscons + # A default RScons builder that produces a static library archive. + class Library < Builder + def default_variables(env) + { + 'AR' => 'ar', + 'LIBSUFFIX' => '.a', + 'ARFLAGS' => [], + 'ARCOM' => ['$AR', 'rcs', '$ARFLAGS', '$TARGET', '$SOURCES'] + } + end + + def run(target, sources, cache, env, vars = {}) + # build sources to linkable objects + objects = env.build_sources(sources, [env['OBJSUFFIX'], env['LIBSUFFIX']].flatten, cache, vars) + if objects + vars = vars.merge({ + 'TARGET' => target, + 'SOURCES' => objects, + }) + command = env.build_command(env['ARCOM'], vars) + unless cache.up_to_date?(target, command, objects) + FileUtils.rm_f(target) + return false unless env.execute("AR #{target}", command) + cache.register_build(target, command, objects) + end + target + end + end + end +end diff --git a/lib/rscons/environment.rb b/lib/rscons/environment.rb index 782909b..376ce68 100644 --- a/lib/rscons/environment.rb +++ b/lib/rscons/environment.rb @@ -194,6 +194,9 @@ module Rscons def method_missing(method, *args) if @builders.has_key?(method.to_s) target, source, vars, *rest = args + unless vars.nil? or vars.is_a?(Hash) or vars.is_a?(VarSet) + raise "Unexpected construction variable set: #{vars.inspect}" + end source = [source] unless source.is_a?(Array) @targets[target] = { builder: @builders[method.to_s], diff --git a/spec/build_tests_spec.rb b/spec/build_tests_spec.rb index bf447f7..82c5179 100644 --- a/spec/build_tests_spec.rb +++ b/spec/build_tests_spec.rb @@ -153,4 +153,17 @@ describe Rscons do File.exists?('two_sources').should be_true `./two_sources`.should == "This is a C program with two sources.\n" end + + it 'builds a static library archive' do + lines = test_dir('library') + lines.should == [ + 'gcc -c -o one.o -MMD -MF one.mf -Dmake_lib one.c', + 'gcc -c -o two.o -MMD -MF two.mf -Dmake_lib two.c', + 'ar rcs lib.a one.o two.o', + 'gcc -c -o three.o -MMD -MF three.mf three.c', + 'gcc -o library lib.a three.o', + ] + File.exists?('library').should be_true + `ar t lib.a`.should == "one.o\ntwo.o\n" + end end