Skip to content

Commit

Permalink
fixed transitive config spec and ruby 1.8.7 compatibility #80
Browse files Browse the repository at this point in the history
  • Loading branch information
marcmo committed Jul 7, 2011
1 parent 19921dd commit 1fffd90
Show file tree
Hide file tree
Showing 6 changed files with 106 additions and 93 deletions.
2 changes: 1 addition & 1 deletion cxx.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ require 'rake'

include FileUtils

PKG_VERSION = '0.5.0'
PKG_VERSION = '0.5.1'
PKG_FILES = FileList[
'lib/**/*.rb',
'Rakefile.rb',
Expand Down
59 changes: 27 additions & 32 deletions lib/cxxproject/buildingblocks/executable.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
require 'cxxproject/buildingblocks/has_libraries_mixin'
require 'cxxproject/buildingblocks/has_sources_mixin'
require 'cxxproject/buildingblocks/has_includes_mixin'
require 'cxxproject/utils/process'

require 'tmpdir'
require 'set'
Expand Down Expand Up @@ -46,31 +45,31 @@ def linker_libs_string

def get_executable_name() # relative path
return @exe_name if @exe_name

parts = [@output_dir]

if @output_dir_abs
parts = [@output_dir_relPath] if @output_dir_relPath
parts << 'exes'
end

parts << "#{@name}#{@tcs[:LINKER][:OUTPUT_ENDING]}"

@exe_name = File.join(parts)
@exe_name
end

def get_task_name() # full path
return @task_name if @task_name

return @task_name if @task_name
parts = [@output_dir]
parts << 'exes' if @output_dir_abs
parts << "#{@name}#{@tcs[:LINKER][:OUTPUT_ENDING]}"
@task_name = File.join(parts)

@task_name = @project_dir + "/" + @task_name unless @output_dir_abs
@task_name
end
end

def collect_unique(array, set)
ret = []
Expand Down Expand Up @@ -125,37 +124,29 @@ def convert_to_rake()

res = typed_file_task Rake::Task::EXECUTABLE, get_task_name => object_multitask do
Dir.chdir(@project_dir) do
cmd = remove_empty_strings_and_join([
linker[:COMMAND], # g++
linker[:MUST_FLAGS],
linker[:FLAGS], # --all_load
linker[:EXE_FLAG],
get_executable_name, # -o debug/x.exe
get_object_filenames, # debug/src/abc.o debug/src/xy.o
@linker_script ? "#{@tcs[:LINKER][:SCRIPT]} #{@linker_script}" : "", # -T xy/xy.dld
@mapfile ? "#{linker[:MAP_FILE_FLAG]} >#{@output_dir + "/" + @mapfile}" : "", # -Wl,-m6 > xy.map
linker[:LIB_PREFIX_FLAGS], # "-Wl,--whole-archive "
remove_empty_strings_and_join(calc_linker_lib_string),
linker[:LIB_POSTFIX_FLAGS] # "-Wl,--no-whole-archive "
])

cmd = [linker[:COMMAND]] # g++
cmd += linker[:MUST_FLAGS].split(" ")
cmd += linker[:FLAGS].split(" ") # --all_load
cmd << linker[:EXE_FLAG]
cmd << get_executable_name # -o debug/x.exe
cmd += @objects # debug/src/abc.o debug/src/xy.o
cmd << linker[:SCRIPT] if @linker_script # -T
cmd << @linker_script if @linker_script # xy/xy.dld
cmd << linker[:MAP_FILE_FLAG] if @mapfile # -Wl,-m6
cmd += linker[:LIB_PREFIX_FLAGS].split(" ") # "-Wl,--whole-archive "
cmd += calc_linker_lib_string
cmd += linker[:LIB_POSTFIX_FLAGS].split(" ") # "-Wl,--no-whole-archive "

rd, wr = IO.pipe
sp = spawn(*cmd,
{
:out=> @mapfile ? "#{@output_dir}/#{@mapfile}" : :err, # > xy.map
:err=>wr
})

# for console print
cmd << " >#{@output_dir}/#{@mapfile}" if @mapfile

consoleOutput = ProcessHelper.readOutput(sp, rd, wr)
show_command(cmd, "Linking #{get_executable_name}")
# TempFile used, because some compilers, e.g. diab, uses ">" for piping to map files:
consoleOutput = `#{cmd + " 2>" + get_temp_filename}`
consoleOutput.concat(read_file_or_empty_string(get_temp_filename))
process_console_output(consoleOutput, @tcs[:LINKER][:ERROR_PARSER])
check_system_command(cmd)
end
end
res.enhance(transitive_config_files)
res.enhance(@config_files)
res.enhance([@project_dir + "/" + @linker_script]) if @linker_script
add_output_dir_dependency(get_task_name, res, true)

Expand Down Expand Up @@ -187,5 +178,9 @@ def run_command(task, command)
sh "#{command}"
end

def get_temp_filename
Dir.tmpdir + "/lake.tmp"
end

end
end
57 changes: 20 additions & 37 deletions lib/cxxproject/buildingblocks/has_sources_mixin.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
require 'yaml'
require 'cxxproject/utils/process'

module Cxxproject
module HasSources
Expand All @@ -21,14 +20,14 @@ def set_sources(x)
@sources = x
self
end

def source_patterns
@source_patterns ||= []
end
def set_source_patterns(x)
@source_patterns = x
self
end
end

def exclude_sources
@exclude_sources ||= []
Expand Down Expand Up @@ -68,27 +67,27 @@ def calc_compiler_strings()

@incArray = local_includes.dup
@incArray.concat(includes)

all_dependencies.each_with_index do |d,i|
next if not HasIncludes === d
next if i == 0
prefix = File.rel_from_to_project(@project_dir,d.project_dir)
next if not prefix
@incArray.concat(d.includes.map {|inc| File.add_prefix(prefix,inc)})
end

[:CPP, :C, :ASM].each do |type|
@include_string[type] = get_include_string(@tcs, type)
@define_string[type] = get_define_string(@tcs, type)
end
end

def get_include_string(tcs, type)
@incArray.uniq.map!{|k| "#{tcs[:COMPILER][type][:INCLUDE_PATH_FLAG]}#{k}"}
@incArray.uniq.map!{|k| "#{tcs[:COMPILER][type][:INCLUDE_PATH_FLAG]}#{k}"}.join(" ")
end

def get_define_string(tcs, type)
tcs[:COMPILER][type][:DEFINES].map {|k| "#{tcs[:COMPILER][type][:DEFINE_FLAG]}#{k}"}
tcs[:COMPILER][type][:DEFINES].map {|k| "#{tcs[:COMPILER][type][:DEFINE_FLAG]}#{k}"}.join(" ")
end

def get_object_file(sourceRel)
Expand Down Expand Up @@ -160,7 +159,7 @@ def outfileTask.needed?
def create_object_file_tasks()

sources_to_build = {} # todo: pair!

exclude_files = Set.new
exclude_sources.each do |p|
Dir.glob(p).each {|f| exclude_files << f}
Expand All @@ -182,13 +181,13 @@ def create_object_file_tasks()
sources_to_build[f] = tcs4source(p)
end
end

obj_tasks = []
sources_to_build.each do |s, the_tcs|
obj_task = create_object_file_task(s, the_tcs)
obj_tasks << obj_task unless obj_task.nil?
end

obj_tasks
end

Expand All @@ -203,40 +202,24 @@ def create_object_file_task(sourceRel, the_tcs)
@objects << objectRel
object = File.expand_path(objectRel)
source = File.expand_path(sourceRel)

depStr = ""
if type != :ASM
if type != :ASM
dep_file = get_dep_file(objectRel)
depStr = the_tcs[:COMPILER][type][:DEP_FLAGS] + dep_file # -MMD -MF debug/src/abc.o.d
end

compiler = the_tcs[:COMPILER][type]
cmd = remove_empty_strings_and_join([compiler[:COMMAND], compiler[:COMPILE_FLAGS], depStr, compiler[:FLAGS], # g++ -c -depstr -g3
the_tcs == @tcs ? @include_string[type] : get_include_string(the_tcs, type), # -I include
the_tcs == @tcs ? @define_string[type] : get_define_string(the_tcs, type), # -DDEBUG
compiler[:OBJECT_FILE_FLAG], objectRel, sourceRel # -o abc.o src/abc.cpp
])
res = typed_file_task Rake::Task::OBJECT, object => source do

i_array = the_tcs == @tcs ? @include_string[type] : get_include_string(the_tcs, type)
d_array = the_tcs == @tcs ? @define_string[type] : get_define_string(the_tcs, type)

compiler = the_tcs[:COMPILER][type]
cmd = [compiler[:COMMAND]]
cmd += compiler[:COMPILE_FLAGS].split(" ")
cmd += depStr.split(" ")
cmd += compiler[:FLAGS].split(" ")
cmd += i_array
cmd += d_array
cmd << compiler[:OBJECT_FILE_FLAG]
cmd << objectRel
cmd << sourceRel

rd, wr = IO.pipe
sp = spawn(*cmd, {
:err=>:out,
:out=>wr
})
consoleOutput = ProcessHelper.readOutput(sp, rd, wr)

show_command(cmd, "Compiling #{sourceRel}")
process_console_output(consoleOutput, compiler[:ERROR_PARSER])
process_console_output(catch_output(cmd), compiler[:ERROR_PARSER])
check_system_command(cmd)
convert_depfile(dep_file) if type != :ASM
convert_depfile(dep_file) if type != :ASM
end
enhance_with_additional_files(res)
add_output_dir_dependency(object, res, false)
Expand All @@ -245,8 +228,8 @@ def create_object_file_task(sourceRel, the_tcs)
end

def enhance_with_additional_files(task)
task.enhance(@config_files)
task.enhance(file_dependencies)
task.enhance(transitive_config_files)
end

def process_console_output(console_output, ep)
Expand Down
54 changes: 34 additions & 20 deletions lib/cxxproject/buildingblocks/source_library.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
require 'cxxproject/buildingblocks/has_libraries_mixin'
require 'cxxproject/buildingblocks/has_sources_mixin'
require 'cxxproject/buildingblocks/has_includes_mixin'
require 'cxxproject/utils/process'
require 'cxxproject/utils/string'

module Cxxproject
class SourceLibrary < BuildingBlock
Expand Down Expand Up @@ -54,39 +54,53 @@ def get_task_name() # full path
#
def convert_to_rake()
object_multitask = prepare_tasks_for_objects()

archiver = @tcs[:ARCHIVER]

res = typed_file_task Rake::Task::LIBRARY, get_task_name => object_multitask do
Dir.chdir(@project_dir) do

FileUtils.rm(get_archive_name) if File.exists?(get_archive_name)
cmd = [archiver[:COMMAND]] # ar
cmd += archiver[:ARCHIVE_FLAGS].split(" ")
cmd += archiver[:FLAGS].split(" ") # --all_load
cmd << get_archive_name # -o debug/x.exe
cmd += @objects

rd, wr = IO.pipe
sp = spawn(*cmd,
{
:err=>:out,
:out=>wr
})

consoleOutput = ProcessHelper.readOutput(sp, rd, wr)

objString = get_object_filenames
if objString.length > 8000
ar_arrays = StringUtils.splitString(objString,8000,".o ", 1)
archs = []
for i in 1..ar_arrays.length
cmd = remove_empty_strings_and_join([
archiver[:COMMAND], # ar
archiver[:ARCHIVE_FLAGS], # -rc
archiver[:FLAGS],
get_archive_name+"_"+i.to_s, # debug/x.a
ar_arrays[i-1] # debug/src/abc.o debug/src/xy.o
])
show_command(cmd, "Creating #{get_archive_name}, part #{i} of #{ar_arrays.length}")
process_console_output(catch_output(cmd), @tcs[:ARCHIVER][:ERROR_PARSER])
check_system_command(cmd)
archs << get_archive_name+"_"+i.to_s
end
objString = archs.join(" ")
end

cmd = remove_empty_strings_and_join([
archiver[:COMMAND], # ar
archiver[:ARCHIVE_FLAGS], # -rc
archiver[:FLAGS],
get_archive_name, # debug/x.a
objString # debug/src/abc.o debug/src/xy.o
])
show_command(cmd, "Creating #{get_archive_name}")
process_console_output(consoleOutput, @tcs[:ARCHIVER][:ERROR_PARSER])
process_console_output(catch_output(cmd), @tcs[:ARCHIVER][:ERROR_PARSER])
check_system_command(cmd)
end
end

enhance_with_additional_files(res)
add_output_dir_dependency(get_task_name, res, true)

add_grouping_tasks(get_task_name)

setup_rake_dependencies(res)


return res
end

Expand Down
16 changes: 16 additions & 0 deletions lib/cxxproject/utils/string.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
module Cxxproject
class StringUtils
def self.splitString(str, chunkSize, delim, delimShift = -1)
res = []
s = str
oldPos = 0
while s.length > chunkSize + oldPos
pos = s.rindex(delim,oldPos+chunkSize)
res << s[oldPos..pos+delimShift]
oldPos = pos+delim.length
end
res << s[oldPos..-1]
res
end
end
end
11 changes: 8 additions & 3 deletions spec/building_block_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -45,8 +45,13 @@
end

it 'should calc correct transitive_config_files' do
lib1 = Cxxproject::SourceLibrary.new('1').set_config_files(['config1']).set_project_dir('.')
lib2 = Cxxproject::SourceLibrary.new('2').set_dependencies(['1']).set_config_files(['config2']).set_project_dir('.')
lib2.transitive_config_files.should eq(['config2', 'config1'])
lib1 = Cxxproject::SourceLibrary.new('1').
set_config_files(['config1']).
set_project_dir('.')
lib2 = Cxxproject::SourceLibrary.new('2').
set_dependencies(['1']).
set_config_files(['config2']).
set_project_dir('.')
Set.new(lib2.transitive_config_files).should eq(Set.new(['config2', 'config1']))
end
end

0 comments on commit 1fffd90

Please sign in to comment.