# File lib/asciidoctor/reader.rb, line 319
  def preprocess_conditional_inclusion(directive, target, delimiter, text)
    # must have a target before brackets if ifdef or ifndef
    # must not have text between brackets if endif
    # don't honor match if it doesn't meet this criteria
    if ((directive == 'ifdef' || directive == 'ifndef') && target.empty?) ||
        (directive == 'endif' && !text.nil?)
      @next_line_preprocessed = true
      return false
    end

    if directive == 'endif'
      stack_size = @conditionals_stack.size
      if stack_size > 0
        pair = @conditionals_stack.last
        if target.empty? || target == pair[:target]
          @conditionals_stack.pop
          @skipping = @conditionals_stack.empty? ? false : @conditionals_stack.last[:skipping]
        else
          puts "asciidoctor: ERROR: line #{@lineno + 1}: mismatched macro: endif::#{target}[], expected endif::#{pair[:target]}[]"
        end
      else
        puts "asciidoctor: ERROR: line #{@lineno + 1}: unmatched macro: endif::#{target}[]"
      end
      advance
      return preprocess_next_line.nil? ? nil : true
    end

    skip = false
    if !@skipping
      case directive
      when 'ifdef'
        case delimiter
        when nil
          # if the attribute is undefined, then skip
          skip = !@document.attributes.has_key?(target)
        when ','
          # if any attribute is defined, then don't skip
          skip = !target.split(',').detect {|name| @document.attributes.has_key? name }
        when '+'
          # if any attribute is undefined, then skip
          skip = target.split('+').detect {|name| !@document.attributes.has_key? name }
        end
      when 'ifndef'
        case delimiter
        when nil
          # if the attribute is defined, then skip
          skip = @document.attributes.has_key?(target)
        when ','
          # if any attribute is undefined, then don't skip
          skip = !target.split(',').detect {|name| !@document.attributes.has_key? name }
        when '+'
          # if any attribute is defined, then skip
          skip = target.split('+').detect {|name| @document.attributes.has_key? name }
        end
      when 'ifeval'
        # the text in brackets must match an expression
        # don't honor match if it doesn't meet this criteria
        if !target.empty? || !(expr_match = text.strip.match(REGEXP[:eval_expr]))
          @next_line_preprocessed = true
          return false
        end

        lhs = resolve_expr_val(expr_match[1])
        op = expr_match[2]
        rhs = resolve_expr_val(expr_match[3])

        skip = !lhs.send(op.to_sym, rhs)
      end
    end
    advance
    # single line conditional inclusion
    if directive != 'ifeval' && !text.nil?
      if !@skipping && !skip
        unshift_line "#{text.rstrip}\n"
        return true
      end
    # conditional inclusion block
    else
      if !@skipping && skip
        @skipping = true
      end
      @conditionals_stack << {:target => target, :skip => skip, :skipping => @skipping}
    end
    return preprocess_next_line.nil? ? nil : true
  end