require 'build-tool/errors' module BuildTool; module BuildSystem class UnknownOptionError < BuildTool::Error; end # # Base class for all build system implementations # class Base def initialize ( parent = nil ) @module = nil @default = nil @options = Hash.new @out_of_source = true @supported_options = Array.new @feature = nil if parent and parent.name == name @parent = parent else @parent = nil end end # ### ATTRIBUTES # attr_accessor :module attr_accessor :feature attr_accessor :out_of_source attr_accessor :defaults def build_directory @module.build_directory end def dup self.class.new( self ) end def env @module.environment.values end def parent if @parent par = @parent elsif @module && @module.parent && @module.parent.build_system && ( @module.parent.build_system.name == name ) par = @module.parent.build_system elsif @module par = defaults else par = nil end return par end def option_hash # Check the parents names (if any) par = parent if par parent_option_hash = par.option_hash else parent_option_hash = {} end # If this build-system declaration is not active we are done if active? return parent_option_hash.merge( @options ) else return parent_option_hash end end def option_names # Check the parents names (if any) par = parent if par parent_option_names = par.option_names else parent_option_names = [] end # If this build-system declaration is not active we are done if active? return ( @options.keys + parent_option_names ).uniq else return parent_option_names end end def to_s return "#{self.module.name} #{self.name} #{@options.keys.join( ', ')}" end def active? if @feature.nil? true else @feature.active? end end def []( var ) # Get the parents value (if any) par = parent if par and par.option_set?( var ) parentval = par[var] else parentval = nil end # If this build-system declaration is not active we are done if !active? return parentval if !parentval.nil? raise UnknownOptionError, "#{self} Option #{var} is unknown for build-system #{name}" end # Now check our value and merge with parents if @options.has_key?( var ) return @options[ var ]. sub( '{{{}}} ', parentval.nil? ? "" : "#{parentval} " ). sub( ' {{{}}}', parentval.nil? ? "" : " #{parentval}" ) end return parentval if !parentval.nil? return "" if @supported_options.include?( var ) raise UnknownOptionError, "[#{self.module.name}] Option #{var} is unknown for build-system #{name}" end def []=( var, value ) @options[ var ] = value end def option_set?( var ) return true if active? && @options.has_key?( var ) return true if parent && parent.option_set?( var ) return false end def set( var, value ) self[var]= value end def append( var, value ) if option_set?( var ) self[var]= self[var] + " " + value else self[var]= "{{{}}} " + value end end def prepend( var, value ) if option_set?( var ) self[var]= value + " " + self[var] else self[var]= value + " {{{}}}" end end def install_prefix return @module.install_prefix_required if @module raise ConfigurationError, "No module set for build-system" end def source_directory return @module.source_directory_required if @module raise ConfigurationError, "No module set for build-system" end def after_rebase end # ### METHODS # # ### VIRTUAL FUNCTIONS # for method in [ :clone, :configure, :configured?, :make, :name, :reconfigure, :install, :install_fast, :install_fast_supported? ] do class_eval <<-EOS def #{method} raise NotImplementedError, "Method #{method} is not implemented for class #{self}" end EOS end def check_build_directory( create = false ) if !out_of_source if File.exist? build_directory if !File.symlink?( build_directory ) raise ConfigurationError, "Build directory #{build_directory} exists and is not a symlink!" end return true elsif create && !$noop FileUtils.mkdir_p( Pathname.new( build_directory ).parent ) File.symlink( source_directory, build_directory ) return true end return false else if File.exist? build_directory if !File.directory? build_directory raise ConfigurationError, "Build directory #{build_directory} exists and is not a directory!" end return true elsif create && !$noop FileUtils.mkdir_p( build_directory ) return true end return false end end def recipe Application::instance.recipe end def remove_build_directory self.class.execute "rm -rf #{build_directory}" end end # class Base end; end # module BuildTool::BuildSystem