#!/usr/bin/perl -w
#
# Xdebconfigurator is a Debian xserver-xfree86 package configuration script.
# Copyright 2002 - 2003 Kristoffer Tjrns.
#
# Licensed under the GNU General Public License, version 2.  See the file
# /usr/share/common-licenses/GPL or <http://www.gnu.org/copyleft/gpl.txt>.
#
# This script is designed to work noninteractively, and uses the following
# packages for hardware detection:
#  - hwinfo, kudzu (+ddcprobe), discover, detect, hwdata
#  - Xdriver.pl
#
# Todo:
#  - use the vesa-driver if noone else is found (?)
#

sub usage()
{
                                print STDERR << "EOF";
The Xdebconfigurator Help Screen
usage: $0 [-cdiklmprsxh]
  -c            : ddcprobe (can detect monitor and video-card memory)
  -d            : discover (can detect video card, driver and xserver)
  -i            : hwinfo (can detect video card, xserver, keyboard, mouse, monitor)
  -k            : kudzu (can detect video card driver and mouse device)
  -l            : libdetect (can detect video card, mouse device and protocol)
  -m            : mdetect (can detect mouse device, but not fully functional yet)
  -r            : read-edid (monitor detection.)
  -x            : dry-run, report only - do not actually update debconf
  -v            : verbose, print debug output during run
  -h            : this (help) message
No argument     : try all if necessary

example: $0 -cdix
EOF
}

use Getopt::Std; # command line options processing
my $opt_string = 'cdhiklmrxv';
getopts( "$opt_string", \my %opt );
if (not scalar %opt or (scalar keys %opt == 1 and $opt{"x"})) {
    # no options selected so do some of them
    %opt = (
            "c" =>"true",
            "d" =>"true",
            "i" =>"true",
            "k" =>"true",
            "l" =>"true",
# It might be better to use ddcprobe (-c)
#            "r" =>"true",
            "s" =>"true"
            );
}
usage() and exit if $opt{h};

use Debconf::Db;
use Debconf::Template;

# Establish paths
my $pkgdir   = "/usr/share/xdebconfigurator";
my $xdriver  = "$pkgdir/Xdriver.pl";

my $hwinfo = "/usr/sbin/hwinfo";
my $ddcprobe = "/usr/sbin/ddcprobe";
my $mdetect = "/usr/bin/mdetect"; # path to mdetect
my $detect = "/usr/sbin/detect"; # path to detect (libdetect)
my $kudzu = "/usr/sbin/kudzu"; # path to kudzu
my $discover = "/sbin/discover"; # path to discover
chomp($getedid = `which get-edid`); # read-edid exists?
# Monitor table (part of package hwdata)
my $MONITORDB = "/usr/share/hwdata/MonitorsDB";

# Establish some variables - which don't exist in debconf
my $mdriv = ""; #mouse driver?
my $mname = ""; #mouse name/model??
my $mwheel = 0; # mouse wheel 0/1

my $card_dID = ''; # device ID
my $card_vID = ''; # vendor ID
# Don't know how to change server yet.. script only works with version
# 4 server for now!
my $xserver = "";
my $xserver3 = '';
my $xserver4 = ''; # xserver4 can be either empty or xfree86
my $xdebpkg = '';

my $monitorID = '';
my $screenX = ''; # screen width
my $screenY = ''; # screen height
# unless we can calc this from cms I don't think we can find this:
#$screensize = "unknown";

## max color depth for driver
# is used to check that we don't specify a depth higher than the
# driver supports
my @driverdepth;

# hash to store debconf Q and A's
%xdebc_map = ();

# if this is set to 1, then we won't run xdebset()
$dry_run = 0;
$debug = 0;

# Establish the preliminaries.
my $THIS_PACKAGE;
my $THIS_SERVER;
my $DEBCONF_OWNER;
if ( -d "/usr/share/doc/xserver-xorg/" ) {
    warn "Detected Xorg server\n";
    $THIS_PACKAGE = "xserver-xorg";
    $THIS_SERVER  = "/usr/bin/X11/Xorg";
    $DEBCONF_OWNER = "xserver-xorg";
    $xserver = "xorg";
} elsif ( -d "/usr/share/doc/xserver-xfree86/" ) {
    warn "Detected XFree86 server\n";
    $THIS_PACKAGE = "xserver-xfree86";
    $THIS_SERVER  = "/usr/bin/X11/XFree86";
    $DEBCONF_OWNER = "xserver-xfree86";
    $xserver = "xfree86";
} else {
    warn "No known X server system detected!\n";
    exit 1;
}

sub xdebc_init()
{
    # build the map of debconf Questions

    # not used:
    #note (multiple vid-cards found):
    #xserver-xfree86/multiple_possible_x-drivers
    #xserver-xfree86/aware_XF86Config-4 # note
    #shared/no_known_x-server #note No support for your video card
    #shared/multiple_possible_x-servers #note

    # These shared choices will be handled in xdebset()
    #select x-server, xserver-xfree86 for version 4
    #set('shared/default-x-server', "$THIS_PACKAGE");
    #boolean xserver-link already exists..; let's re-link it
    #xdebc_map{'shared/clobber_x-server_symlink'} = 'true';
    #xdebc_type{'shared/clobber_x-server_symlink'} = 'boolean';

    $xdebc_map{'aware_XF86Config-4'} = 'true';
    $xdebc_type{'aware_XF86Config-4'} = 'boolean';
    # whack the config file?
    $xdebc_map{'clobber_XF86Config-4'} = 'true';
    $xdebc_type{'clobber_XF86Config-4'} = 'boolean';
    # VIDEO CARD
    $xdebc_map{'config/device/driver'} = '';
    $xdebc_type{'config/device/driver'} = 'select';
    $driversource = "none";
    $xdebc_map{'config/device/identifier'} = ''; #string video-card identifier
    $xdebc_map{'config/device/use_fbdev'} = ''; #boolean
    $xdebc_type{'config/device/use_fbdev'} = 'boolean';
    $xdebc_map{'config/device/video_ram'} = ''; #string
    # KEYBOARD AND MOUSE
    # deprecated (shall be set by another package):
    # "$locale"); #ex: no for norwegian
    #$xdebc_map{'config/inputdevice/keyboard/layout'} = '';
    #$xdebc_map{'config/inputdevice/keyboard/model'} = '';
    #$xdebc_type{'config/inputdevice/keyboard/model'} = 'select';

    #found these in debconf db /var/cache/debconf/
    $xdebc_map{'config/inputdevice/keyboard/rules'} = ''; # 'xfree86');
    # Leave this alone, and set them using localization-config or similar
    #$xdebc_map{'config/inputdevice/keyboard/options'} = '';
    #$xdebc_map{'config/inputdevice/keyboard/variant'} = '';

    $mousesource = "none";
    $xdebc_map{'config/inputdevice/mouse/port'} = '';
    $xdebc_type{'config/inputdevice/mouse/port'} = 'select';
    $xdebc_map{'config/inputdevice/mouse/protocol'} = '';
    $xdebc_type{'config/inputdevice/mouse/protocol'} = 'select';
    $xdebc_map{'config/inputdevice/mouse/emulate3buttons'} = '';
    $xdebc_type{'config/inputdevice/mouse/emulate3buttons'} = 'boolean';
    $xdebc_map{'config/inputdevice/mouse/zaxismapping'} = ''; #boolean
    $xdebc_type{'config/inputdevice/mouse/zaxismapping'} = 'boolean';
    # best turn this off:
    $xdebc_map{'config/inputdevice/mouse/retry_detection'} = 'false';
    $xdebc_type{'config/inputdevice/mouse/retry_detection'} = 'boolean';

    # MONITOR
    $xdebc_map{'config/monitor/identifier'} = ''; #string monitor identifier
    $xdebc_map{'config/monitor/lcd'} = 'false'; # laptop or not?
    $xdebc_type{'config/monitor/lcd'} = 'boolean';

    #select simple,medium,advanced:
    $xdebc_map{'config/monitor/selection-method'} = '';
    $xdebc_map{'config/monitor/screen-size'} = ''; #select simple
    $xdebc_type{'config/monitor/screen-size'} = 'select';

    #multi-select defulats ok - '1024x768, 800x600, 640x480');
    #multiselect, use defaults:
    $xdebc_map{'config/display/modes'} = '';
    $xdebc_type{'config/display/modes'} = 'multiselect';

    # '1024x768 @ 70Hz'); #this default should be ok on 15 inch+
    $xdebc_map{'config/monitor/mode-list'} = '';
    $xdebc_map{'config/display/default_depth'} = ''; #select default 24 ok
    $xdebc_type{'config/display/default_depth'} = 'select';
    $modesource = "none";

    # '28-50'; #this is the default for 15 inches
    $xdebc_map{'config/monitor/horiz-sync'} = '';

    # '43-75'; #this is the default for 15 inches
    $xdebc_map{'config/monitor/vert-refresh'} = '';

    #note wrong format for range-string:
    #xserver-xfree86/config/monitor/range_input_error
}


sub kudzu_video_driver()
{
    #/etc/sysconfig/hwconf
    #vendorId: 1002
    #deviceId: 4755
    #subVendorId: 1002
    #subDeviceId: 4755

    #desc: "Mach64 3D RAGE II 3D Rage II+ 215GTB [Mach64 GTB]"
    $vid_flag = 0; #flag to make sure we're getting VIDEO-driver
    $vid_name = '';
    %vid_hash = ();

    # output from kudzu piped to KUDZU
    open (KUDZU, "$kudzu -p|");

  VLINE: while ($line = <KUDZU>) {
      if ($line =~ /class: VIDEO/i) {
          $vid_flag = 1;
      }

      if ($vid_flag && $line =~ /driver:/) {
          if ($line =~ /Server:(\w+)\((\w+)\)/i) {
              # driver: Server:XFree86(ati)
              #chomp($vid_driver = $2); # chomping is unnecessary
              #chomp($xserver = $1);
              $xdebc_map{'config/device/driver'} = "\L$2";
              $driversource = "kudzu";
              $xserver = $1;
          }
      }

      if ($vid_flag && $line =~ /vendorId: (\S{4})/) {
          $card_vID = $1;
      }

      if ($vid_flag && $line =~ /deviceId: (\S{4})/) {
          $card_dID = $1;
          # last VLINE;
      }

      if ($vid_flag && $line =~ /desc: \"(.+)\"/) {
          $vid_name = $1;

          # create a name without duplicate words
          $vid_name =~ s/\[.+\]//i;

          # all lowercase gets rid of some multis
          %vid_hash = map { $_, 1 } split(/ /,"\L$vid_name");
          $vid_name = join(" ",keys %vid_hash);
      }

      if ($vid_flag && $line =~ /-/) {
          last VLINE;
      }
  }
    close(KUDZU);

    $xdebc_map{'config/device/identifier'} = $vid_name;
}

sub kudzu_mouse_device()
{
    #/etc/sysconfig/hwconf
    #device: psaux
    #driver: genericps/2
    #desc: "Generic Mouse (PS/2)"

    $m_flag = 0; #flag to make sure we're getting MOUSE-device
    $m_driver = "unknown";

    # output from kudzu piped to KUDZU
    open (KUDZU, "$kudzu -p|");

  MLINE: while ($line = <KUDZU>) {

      if ($line =~ /class: MOUSE/i) {
          $m_flag = 1;
      }

      if ($m_flag && $line =~ /device: (\S+)/) {
          $xdebc_map{'config/inputdevice/mouse/port'} = $1;
          # kudzu doesn't attach the /dev/ to device.
          # Resulted in /dev/unknown in some cases.

          if ($xdebc_map{'config/inputdevice/mouse/port'} ) {
              $xdebc_map{'config/inputdevice/mouse/port'} =~ s/(.+)/\/dev\/$1/;
          }
          $mousesource = "kudzu";
      }

      if ($m_flag && $line =~ /driver: ([\w|\/]+)/) {
          $m_driver = $1; # Is there any use for this?
      }

      if ($m_flag && $line =~ /desc: .+\((.+)\)/) {
          # not sure if this is the right place to get protocol
          $xdebc_map{'config/inputdevice/mouse/protocol'} = $1;
          # last MLINE;
      }

      if ($m_flag && $line =~ /-/) {
          last MLINE;
      }
  }
    close(KUDZU);

    #return "".$m_device.":$m_driver:$m_protocol";
}

sub libdetect()
{
    # Detect, "frontend" for libdetect - harddrake - can detect mouse
    # and video some biased things here too.. report.txt doesn't seem
    # to be stored in a static place
    # report.txt get's stored in ./ which sometimes seem to be
    # /usr/sbin/ and some times the directory from where you run this
    # script :/
    system("/usr/sbin/detect"); # generates a file report.txt
    if(-e "./report.txt") { $rapport = "./report.txt"; }
    elsif(-e "/usr/sbin/report.txt") { $rapport = "/usr/sbin/report.txt"; }
    open (FIL,$rapport) or die "Failed to open $rapport !\n";
    $line = <FIL>;          # <FIL> return a line from the file
    while ($line = <FIL>)   # <FIL> returning an empty string at file-end
    {
        if($line =~ /MOUSE:([\w|\/|\d]+):(.+):(.+):(\/dev\/[\w|\d|\/]+)/i)
        {
            $xdebc_map{'config/inputdevice/mouse/port'} = $4;
            $xdebc_map{'config/inputdevice/mouse/protocol'} = $1;
            $mousesource = "libdetect";
        } elsif($line =~ /VIDEO:/i ) {
            if($line =~ /VIDEO:\w+:[\w| ]+:([\w+| |\+|\-|\/]+)/i) {
                # no .= cause we don't want "unknown" in there
                $xdebc_map{'config/device/identifier'} = $1;
            }
            if($line =~ /\[Card:([\w| ]+)\]/i) {
                $xdebc_map{'config/device/identifier'} .= " $1";
            }

            #get rid of multi instances, they're just slowing us down
            %namehash = map { $_, 1 } split(/ /,$xdebc_map{'config/device/identifier'});
            $xdebc_map{'config/device/identifier'} = join(" ",keys %namehash);
        }
    }
    close(FIL);
    #return "$cname:$mp:$md"; # ATI Rage Pro II:PS/2:/dev/psaux
}

sub hwinfo_keyboard()
{
    $kName = '';
    open (HW, "$hwinfo --keyboard |");   # output from hwinfo piped to HW
    while ($line = <HW>)    # <HW> give line-by-line of hwinfo-output
    {
        if($line =~ /\s+Model: (\d+) \"(.+)\"/i) {
            $kName = $2;
        } elsif($line =~ /XkbRules: (\w+)/i) {
            $xdebc_map{'config/inputdevice/keyboard/rules'} = $1; # xfree86
        }
    }
    close(HW);
}

sub hwinfo_monitor()
{
    # hwinfo can get monitor ID. If hwinfo doesn't give refresh rates we
    # can look that up in /usr/share/hwdata/MonitorsDB
    # Ex:
    # Vendor: CPQ "COMPAQ"
    # Device: 0027 "151FS"
    # ID in MonitorsDB is cpq0027 :
    # Compaq; Compaq 151FS; cpq0027; 31.5-57.0; 50.0-90.0; 1
    # or hwinfo already knows (cpw1322):
    # Vert. Sync Range: 50-125 Hz
    # Hor. Sync Range: 30-60 kHz
    open (HW, "$hwinfo --monitor |");   # output from hwinfo piped to HW
    while ($line = <HW>)    # <HW> give line-by-line of hwinfo-output
    {
        if($line =~ /Vendor: (.+) \".+\"/i)
        {
            $monitorID = "\L$1"; # vendor shortname in lowercase
        } elsif($line =~ /Device: (\S{4}) \"(.+)\"/i) {
            $monitorID .= $1; # + device ID
        } elsif($line =~ /Vert\. Sync Range: (\d+)\-(\d+) \w+/i) {
            $xdebc_map{'config/monitor/vert-refresh'} = $1.'-'.$2;
        } elsif($line =~ /Hor\. Sync Range: (\d+)\-(\d+) \w+/i) {
            $xdebc_map{'config/monitor/horiz-sync'} = $1.'-'.$2;
        }
    }
    close(HW);
}

sub hwinfo_frame()
{
    # TODO! - we should be carefull using this cause it only gets the
    # modes supported by the video card, not the monitor
    %temp_modes = ();

    # framebuffer can get memory size and possible modelines!
    open (HW, "$hwinfo --framebuffer |");
    while ($line = <HW>)
    {
        if($line =~ /Memory Size: (\d+) MB/)
        {
            # we need kB representation
            $xdebc_map{'config/device/video_ram'} = $1*1024;
        }
        elsif($line =~ /Mode 0x\S{4}: (\d+)x(\d+) \([+|-]\d+\), (\d+) bits/)
        {
            # Lots of matches, each one will give something like
            # ($1,$2,$3)=(800,600,16) as in 800x600 16 bits
            # maybe we can use it to get highest combo of res and depth?

            # 800x600:16 => 16, 1024x768:16 => 16, 800x600:24 => 24
            $temp_modes{$1.'x'.$2.':'.$3} = $3;
            # find best combo 800x600 or 1024x768
        }
    }
    close(HW);
    # now sort the hash by value and pick a depth that works with both
    # 1024 and 800
    # TODO: this works well for making a mode list like 1024, 800, 640 but
    # what if we have higher modes?
    ($temp_mode, $rest) = ('','');
    %temp_depths = ();
    sub sortHashDesc {
        $temp_modes{$b} <=> $temp_modes{$a};
    }

    foreach $key (sort  sortHashDesc (keys(%temp_modes))) {
        #print "$key\n";
        if($temp_depths{$temp_modes{$key}}) {
            ($temp_mode, $rest) = split(/:/, $key);
            $temp_depths{$temp_modes{$key}} .= ", ".$temp_mode;
        } else {
            ($temp_mode, $rest) = split(/:/, $key);

            # first instance of this depth
            $temp_depths{$temp_modes{$key}} = $temp_mode;
        }
    }

    foreach $key (sort keys %temp_depths) {
        if(!$xdebc_map{'config/display/default_depth'} ||
           $key > $xdebc_map{'config/display/default_depth'}) {
            if($temp_modes{'1024x768:'.$key} && $temp_modes{'800x600:'.$key}) {
                # highest depth that works with both 1024 and 800
                $xdebc_map{'config/display/default_depth'} = $key;
            }
        }
    }

    $xdebc_map{'config/display/modes'} =
        $temp_depths{ $xdebc_map{'config/display/default_depth'} };
}

sub hwinfo_display()
{
    open (HW,"$hwinfo --display |");   # output from hwinfo piped to HW
    while ($line = <HW>)    # <HW> give line-by-line of hwinfo-output
    {
        if($line =~ /Model: \"(.+)\"/i) {
            $xdebc_map{'config/device/identifier'} = $1; # just a name
        } elsif($line =~ /\WDevice: (\S{4}) \"(.+)\"/i) {
            # new and improved - works with hwinfo 4.27 - use \W to avoid
            # matching subDevice/subVendor
            $card_dID = $1; #video card ID
        } elsif($line =~ /\WVendor: (\S{4}) \"(.+)\"/i) {
            $card_vID = $1; #video card vendor ID
        } elsif($line =~ /v4 Server Module: (\w+)/i) {
            # this should be something like "trident"
            chomp($xdebc_map{'config/device/driver'} = $1);
            $driversource = "hwinfo";
            $xserver4 = 'xfree86'; # there can be only one...
            last;
        } elsif($line =~ /Color Depths: (.+)$/i) {
            # only check the first as this is probably the one for
            # XFree86 v4
            if ( ! $driverdepth[0] ) {
                push(@driverdepth, split(/[, ]+/, $1));
            }
        }
    }
    close(HW);
}

sub hwinfo_mouse()
{
    #16: PS/2 00.0: 10500 PS/2 Mouse
    #[Created at mouse.275]
    #Unique ID: gG82.g++hATXqKsF
    #Vendor: s0200 "Unknown"
    #Model: 0002 "Generic PS/2 Mouse"
    #Device File: /dev/psaux
    #Driver Info #0:
    #   Wheels: 0
    #   XFree86 Protocol: ps/2
    #   GPM Protocol: ps2
    #Attached to: #9 (PS/2 Controller)
    open (HW, "$hwinfo --mouse |");   # output from hwinfo piped to HW
    while ($line = <HW>)    # <HW> give line-by-line of hwinfo-output
    {
        if($line =~ /Model: (\d+) \"(.+)\"/i)
        {
            $mname = $2; # Just a mouse name
        } elsif($line =~ /Device File: ([\/a-z0-9]+)/i) {
            # this should be something like /dev/psaux
            $xdebc_map{'config/inputdevice/mouse/port'} = $1;
            $mousesource = "hwinfo";
        } elsif($line =~ /XFree86 Protocol: (.+)/i) {
            # this should be something like ps/2 (capitalize later)
            $xdebc_map{'config/inputdevice/mouse/protocol'} = $1;
        } elsif($line =~ /Wheels: (\d)/i) {
            $mwheel = $1; # 0/1
        }
    }
    close(HW);

    if($xdebc_map{'config/inputdevice/mouse/port'} eq "/dev/psaux")
    {
        # ImPS/2 is normal for wheel-mice
        if($mwheel) {
            $xdebc_map{'config/inputdevice/mouse/protocol'} = "ImPS/2";
        } else {
            #most likely
            $xdebc_map{'config/inputdevice/mouse/protocol'} = "PS/2";
        }
    }

    if($xdebc_map{'config/inputdevice/mouse/port'} eq "/dev/input/mice")
    {
        # The /dev/input/mice device s a mouse multiplexer using the
        # "ExplorerPS/2" protocol.  Using "ImPS/2" which seem to be
        # compatible to avoid having to change large parts of the
        # script.
        $xdebc_map{'config/inputdevice/mouse/protocol'} = "ImPS/2";
    }

    #boolean; best turn this off:
    $xdebc_map{'config/inputdevice/mouse/retry_detection'} = 'false';
}

sub mdetect()
{
    # TODO! NOT IN USE FOR NOW
    # mdetect -x on my test-box don't really work. Using verbose will
    # produce something though:
    #Found the following devices:
    #/dev/psaux
    #/dev/ttyS1
    #/dev/ttyS0

    $md_flag = 0;
    $mdet_dev = "";
    open (MD,"mdetect -x -v |");   # output from mdetect piped to MD
    while ($line = <MD>)    # <MD> give line-by-line of mdetect-output
    {
        if($line =~ /Found/i)
        {
            $md_flag = 1;
        }
        elsif($line =~ /[ ]+(.+)/i && $md_flag)
        {
            if($mdet_dev eq "unknown") {
                # need a hash or something as there can be several hits here
                $mdet_dev = $1;
            } else {
                $mdet_dev .= ":$1";
            }
        }
    }
    close(MD);
    # if it detected a psaux, then chances are that's what we got
    #this is a hack since mdetect no worky on my box
    $mdet_dev =~ s/.*\/dev\/psaux.*/\/dev\/psaux/i;
    $xdebc_map{'config/inputdevice/mouse/port'} = $mdet_dev; #select
    #return "$mdet_dev"; #/dev/psaux:/dev/ttyS1:/dev/ttyS0
    $mousesource = "mdetect";
}

sub edid()
{
    # command to issue: get-edid 2>&1 | parse-edid
    # can reveal timings. Not using the optimized modes section.
    if($getedid)
    {
        open (ED,"get-edid 2>&1 | parse-edid |"); # output from edid piped to ED
        LINE: while ($line = <ED>)    # <ED> give line-by-line of edid-output
        {
            # bail out if EDID checksum fails
            last LINE if($line =~ /EDID checksum failed - data is corrupt/);

            # HorizSync 30-95
            # VertRefresh 47-160
            if ($line =~ /HorizSync (\d+)\-(\d+)/i) {
                $xdebc_map{'config/monitor/horiz-sync'} = $1 . "-" . $2;
            } elsif ($line =~ /VertRefresh (\d+)\-(\d+)/i) {
                $xdebc_map{'config/monitor/vert-refresh'} = $1 . "-" . $2;
            }

            # Bomb out if edid if this happens, or it might loop!
            last LINE if($line =~ /Something special has happened/i);
        }
        close(ED);

        if ($xdebc_map{'config/monitor/horiz-sync'} &&
            $xdebc_map{'config/monitor/vert-refresh'} ) {
            #we got refresh rates so we can use "Advanced mode"
            $xdebc_map{'config/monitor/selection-method'} = "Advanced";
        } else {
            # no refresh rates - use simple configuration?
            $xdebc_map{'config/monitor/selection-method'} = "Simple";
        }
    }
}

sub ddcprobe()
{
    # using ddcprobe to look for monitor!
    # what do we need to know about monitor:
    # horizSync, VertRefresh, a def Mode list (pick highest?!), screen
    # size, modes, def depth

    my $temp_mode = "1024x768 @ 70Hz";
    open (HW,"$ddcprobe |");   # output from ddcprobe piped to HW
    while ($line = <HW>)    # <HW> give line-by-line of ddcprobe-output
    {
        #ID: 4538
        #EISA ID: API4538
        #Screen size max 27 cm horizontal, 20 cm vertical.
        # 640x480 @ 75 Hz (VESA)

        if($line =~ /(\d+x\d+ @ \d+ Hz) \(VESA\)/i)
        {
            # we'll use the greatest one as def
            # TODO: change selection of default mode
            # It's better to have a smaller resolution with high refresh
            # rate, than vice versa
            # Maybe test 1024x768 against these modes and pick it with a
            # high refresh if it exists
            # Then next try 800x600 with a high refresh.
            # 14 inches aparently wanna have max 800x600 @ 60Hz
            $temp_mode = $1;

            # let's first get the best refresh rate at 800x600, then
            # 1024x768 if possible
            if($temp_mode =~ /800x600/) {
                # this will eventually store 800x600 with best refresh rate
                $xdebc_map{'config/monitor/mode-list'} = $temp_mode;
                $modesource = "ddcprobe";
            } elsif($temp_mode =~ /1024x768/) {
                # this will eventually store 1024x768 with best refresh rate
                $xdebc_map{'config/monitor/mode-list'} = $temp_mode;
                $modesource = "ddcprobe";
            }
        } elsif($line =~ /EISA ID: (\S+)/i) {
            $monitorID = $1;
        } elsif($line =~ /Memory installed .+ (\d+)kb/i) {
            # Memory installed = 32 * 64k blocks = 2048kb
            $xdebc_map{'config/device/video_ram'} = $1;
        } elsif($line =~ /Screen size max (\d+) cm horizontal, (\d+) cm vertical/i) {
            $screenX = $1;
            $screenY = $2;
        }

        # On some monitors the timings range is reported as: Timing ranges:
        # horizontal = 30 - 130, vertical = 50 - 160
        if($line =~ /Timing ranges\: horizontal \= (\d+) \- (\d+)\, vertical \= (\d+) \- (\d+)/i)
        {
            $xdebc_map{'config/monitor/horiz-sync'} = $1 . "-" . $2;
            $xdebc_map{'config/monitor/vert-refresh'} = $3 . "-" . $4;
            #we got refresh rates so we can use "Advanced mode"
            $xdebc_map{'config/monitor/selection-method'} = "Advanced";
        }
    }
    close (HW);

    # fix: slightly different format than what config wants
    $xdebc_map{'config/monitor/mode-list'} =~ s/(\d+) Hz/$1Hz/i;
    #$xdebc_map{'config/display/default_depth'} = ''; #select default 24 ok
}


# deprecated (not used anymore, but not removing the function yet)
sub proc_pci()
{
    # good chance /proc/pci got video-card info (but most likely only the name)
    #  VGA compatible controller: ATI Mach64 GT (Rage II) (rev 154).
    chomp($cname = `cat /proc/pci | grep VGA | cut -f2 -d:`);
    $cname =~ s/\(rev \d+\)//i;
    $cname =~ s/\(//i;
    $cname =~ s/\)//i;

    #string video-card identifier
    $xdebc_map{'config/device/identifier'} = $cname;
    return $cname;
}

sub discover()
{
    # this is what the original debconf script is using, so might not be
    # necessary but VERY easy to use! discover is excellent

    # check which version of discover
    my $discover_version;
    chomp($discover_version = `$discover --version`);

    my $discover_data;
    if ($discover_version =~ /discover 2/) {
        chomp($discover_data =
              `$discover --data-path=xfree86/server/device/driver display | grep -v '^\$' | head -n1`);
    } else {
        #FIXME - change --format to same as discover2, driver only
        chomp($discover_data =
              `$discover --format="%D\n" video | head -n1`);
    }
    return "$discover_data";
}

sub monitor_size()
{
    # calculate the monitor size based on width and height using
    # pythagorean theorem

    # in cm
    $monitorSize = int(sqrt( ($screenX*$screenX) + ($screenY*$screenY) ));

    # in inches 28 x 21 cm = 13.78 inches
    $monitorSize = $monitorSize / 2.54;

    if($monitorSize > 0 && $monitorSize < 14.8 ) {
        $xdebc_map{'config/monitor/screen-size'} = '15 inches (380 mm)';
    }
}

sub lookup_card($)
{
    # Using my Xdriver.pl script to determine a suitable XFree86-4 card driver
    # the script is sort of hack-n-slash, determining driver based on name!!
    $cname = $_[0];
    $cd = '';
    open (XD,"$xdriver \"$cname\" |");   # output from Xdriver.pl piped to XD
    while ($line = <XD>)    # <XD> give line-by-line of Xdriver.pl-output
    {
        if($line =~ /DRIVER: (\w+)/)
        {
            $cd = $1;
        }
    }
    close(XD);
    if($cd eq "unknown") { $cd = ''; }
    return $cd;
}

sub lookup_monitor()
{
    $mu = ''; # init monitor-unused dump variable
    # get sync and refresh from MonitorDB - greping on $monitorID
    if(-f $MONITORDB && $monitorID)
    {
        open (FIL,$MONITORDB) or die "Failed to open $MONITORDB !\n";
        $line = <FIL>;          # <FIL> return a line from the file
        READDB: {
            while ($line = <FIL>) # <FIL> returning an empty string at file-end
            {
                # Acer; Acer 56e; API4538; 30.0-69.0; 50.0-110.0
                if($line =~ /$monitorID/i)
                {
                    chomp($dbstring = $line);
                    last READDB;
                }
            }
        }
        if ( ! defined $dbstring ) {
            warn("Unable to find Monitor '$monitorID' in " . "$MONITORDB\n");
            return 0;
        } else {
            ($mu,$xdebc_map{'config/monitor/identifier'},$mu,$xdebc_map{'config/monitor/horiz-sync'},$xdebc_map{'config/monitor/vert-refresh'},$mu) = split(/\;/, $dbstring);
            return 1;
        }
    }
}

sub test_existion($)
{
    if(-e $_[0])
    {
        return 1;
    } else {
        warn "$_[0] NOT found!\n";
        return 0;
    }
}

# Function copied from debconf-set-selection/debconf-load-defaults, to
# make sure a dummy template is created if it is missing
sub load_answer {
    my ($owner, $label, $type, $content) = @_;

    print STDERR "Loading '$label' with answer '$content'\n" if $debug;

    # don't set debconf-templates if user doesn't want :)
    return if $dry_run;

    my $template=Debconf::Template->get($label);
    if (! $template) {
        $template=Debconf::Template->new($label, $owner, $type);
        $template->description("Dummy template");
        $template->extended_description("This is a fake template used to pre-seed the debconf database. If you are seeing this, something is probably wrong.");
      }
    else {
        $template->default($content);
    }
    $template->type($type);

    my $question=Debconf::Question->get($label);
    if (! $question) {
        error("Cannot find a question for $label");
        return;
      }
    $question->addowner($owner, $type);
    $question->value($content);
    $question->flag("seen", "true");
}

# function that provides the debconf functionality for xdebconfigurator
# (was Xdebset.pl)

sub xdebset()
{
    # get machine architecture
    #$ARCH= 'dpkg --print-installation-architecture'; # ex: i386
    # uncomment for debconf

    my $deftype = "string";

    $debconfprefix = 'xserver-' . $xserver; # xfree86, svga, ...

    # populate debconf
    #select x-server, xserver-xfree86 for version 4

    Debconf::Db->load unless $dry_run;

    load_answer($DEBCONF_OWNER, 'shared/default-x-server', "select",
                $debconfprefix);
    #boolean xserver-link already exists..; let's re-link it
    load_answer($DEBCONF_OWNER, 'shared/clobber_x-server_symlink', "boolean", 'true');

    if($debconfprefix !~ /xserver-xfree86/ &&
       $debconfprefix !~ /xserver-xorg/ ) {
        # does all v3 servers use this? or just svga?
        $debconfprefix = 'shared/xfree86v3';
    }
    # do the loop
    # we can probably make this work for version 3 servers by substing
    # xserver-xfree86 with xserver shared/xfree86v3/
    foreach $key (sort keys %xdebc_map) {
        my $type = $xdebc_type{$key} || $deftype;
        load_answer($DEBCONF_OWNER, $debconfprefix.'/'.$key, $type, $xdebc_map{$key});
    }
    Debconf::Db->save unless $dry_run;
}

# Run
# Initialize hash
xdebc_init();


# Run through opts
# we're testing the availability of each prog here, so no need do it in
# the subs
if($opt{c}){
    if(test_existion("$ddcprobe") &&
       $xdebc_map{'config/monitor/selection-method'} ne "Advanced" ) {
        ddcprobe();
    }
}
if($opt{d}){
    if(test_existion("$discover")) {
        if ( !$xdebc_map{'config/device/driver'} ) {
            $xdebc_map{'config/device/driver'} = discover();

            # the "defaulting to vesa" section at the bottom will handle it
            if ($xdebc_map{'config/device/driver'} eq 'unknown' ) {
                $xdebc_map{'config/device/driver'} = '';
            }

            $driversource = "discover";
        }
    }
}
if($opt{i}) {
    if(test_existion("$hwinfo")) {
        if( !$xdebc_map{'config/device/driver'} ) {
            hwinfo_display();
        }
        if( !$xdebc_map{'config/inputdevice/mouse/port'} ) {
            hwinfo_mouse();
        }
        # we will stop use hwinfo for Monitor information because when the
        # computer is already using the framebuffer device, hwinfo fetches
        # the running settings, not the capabilities of the hardware
        #
        #if( $xdebc_map{'config/monitor/selection-method'} ne "Advanced" ) {
        #    # we're only using Simple and Advanced modes - Simple if we
        #    # can't get refresh rates
        #    hwinfo_monitor();
        #}
        if( !$xdebc_map{'config/display/modes'} ) {
            hwinfo_frame(); # generates a modes list and gets video card memory
        }
    }
}
if($opt{k}) {
    if(test_existion("$kudzu")) {
        if( !$xdebc_map{'config/device/driver'} ) {
            kudzu_video_driver(); # good one for driver
        }
        if( !$xdebc_map{'config/inputdevice/mouse/port'} ) {
            kudzu_mouse_device(); #diff between driver and prot?
        }
    }
}
if($opt{l}) {
    if(test_existion("$detect")) {
        if( !$xdebc_map{'config/device/driver'} || !$xdebc_map{'config/inputdevice/mouse/port'} ) {
            libdetect(); # libdetect only gets a name for the video card
        }
    }
}
if($opt{m}) {
    if(test_existion("$mdetect")) {
        #TODO mdetect
        if( !$xdebc_map{'config/inputdevice/mouse/port'} ) {
            mdetect();
        }
    }
}

if($opt{r}) {
    #TODO read-edid
    if( $xdebc_map{'config/monitor/selection-method'} ne "Advanced" ) {
        edid(); # read-edid can get refresh rates etc, but is buggy
    }
}

$debug = 1 if ($opt{v});
$dry_run = 1 if ($opt{x});

### Mouse detection
# is mouse protocol case sensitive in debconf? I tested and aparently it was!
if ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
    /imps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "ImPS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /ps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "PS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /glidepointps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "GlidePointPS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /netmouseps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "NetMousePS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /netscrollps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "NetScrollPS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /thinkingmouseps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "ThinkingMousePS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /mousemanplusps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "MouseManPlusPS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /explorerps\/2/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "ExplorerPS/2";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /microsoft/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "Microsoft";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /mousesystems/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "MouseSystems";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /glidepoint/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "GlidePoint";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /thinkingmouse/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "ThinkingMouse";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /mouseman/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "MouseMan";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /Logitech/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "Logitech";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /intellimouse/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "IntelliMouse";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /mmseries/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "MMSeries";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /mmhittab/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "MMHitTab";
} elsif ($xdebc_map{'config/inputdevice/mouse/protocol'} =~
         /busmouse/i ) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "BusMouse";
}

# mouse device but no protocol?
if ($xdebc_map{'config/inputdevice/mouse/port'} &&
    !$xdebc_map{'config/inputdevice/mouse/protocol'} ) {
    # psaux is one of: PS/2, ImPS/2, GlidePointPS/2, NetMousePS/2,
    # NetScrollPS/2, ThinkingMousePS/2, MouseManPlusPS/2, ExplorerPS/2
    if ($xdebc_map{'config/inputdevice/mouse/port'} eq "/dev/psaux")  {
        if ($mwheel) {
            # ImPS/2 is normal for wheel-mice
            $xdebc_map{'config/inputdevice/mouse/protocol'} = "ImPS/2";
        } else {
            #most likely
            $xdebc_map{'config/inputdevice/mouse/protocol'} = "PS/2";
        }

    # tt is one of: Auto, Microsoft, MouseSystems, GlidePoint, ThinkingMouse,
    # MouseMan, Logitech, IntelliMouse, MMSeries, MMHitTab
    } elsif ($xdebc_map{'config/inputdevice/mouse/port'} =~ /tty/) {
        #real ugly default
        $xdebc_map{'config/inputdevice/mouse/protocol'} = "Microsoft";
    } elsif ($xdebc_map{'config/inputdevice/mouse/port'} =~ /tts/) {
        #real ugly default
        $xdebc_map{'config/inputdevice/mouse/protocol'} = "Microsoft";
    } elsif ($xdebc_map{'config/inputdevice/mouse/port'} =~ /mice/) {
        $xdebc_map{'config/inputdevice/mouse/protocol'} = "ImPS/2";
    } elsif( $xdebc_map{'config/inputdevice/mouse/port'} =~ /ati/) {
        $xdebc_map{'config/inputdevice/mouse/protocol'} = "BusMouse";
    } elsif ($xdebc_map{'config/inputdevice/mouse/port'} =~ /sunmouse/) {
        $xdebc_map{'config/inputdevice/mouse/protocol'} = "BusMouse";
    } elsif ($xdebc_map{'config/inputdevice/mouse/port'} =~ /gpm/) {
        $xdebc_map{'config/inputdevice/mouse/protocol'} = "IntelliMouse";
    }
}

# mouse wheel detected, but protocol is set to PS/2
if ($xdebc_map{'config/inputdevice/mouse/protocol'} eq "PS/2" && $mwheel) {
    $xdebc_map{'config/inputdevice/mouse/protocol'} = "ImPS/2";
}

### Xserver detection

#$xserver = "XF86_S3"; #for testing purposes
#$card_driver = "unknown"; #for testing purposes

# match up xserver, xserver3/4 and $xdebc_map{'config/device/driver'}
if ($xdebc_map{'config/device/driver'} ) {
    $xserver4 = 'xfree86'; # there can be only one..
    # $xserver is already set to xfree86 or xorg
} elsif ($xserver3 && !$xserver) {
    $xserver = $xserver3;
}

$xserver = "\L$xserver"; # lowercase or dexconf will choke

if (!$xdebc_map{'config/device/driver'} &&
    $xdebc_map{'config/device/identifier'} ) {
    # getting driver based on name
    $xdebc_map{'config/device/driver'} =
        lookup_card ($xdebc_map{'config/device/identifier'});
    $driversource = "identifier";
}

# defaulting to vesa if we're unable to detect it with some of the
# great tools :)
if ( !$xdebc_map{'config/device/driver'} ) {
    $xdebc_map{'config/device/driver'} = "vesa";
    $driversource = "defaulting to vesa";
}

### Monitor detection

if ((!$xdebc_map{'config/monitor/horiz-sync'} ||
     !$xdebc_map{'config/monitor/vert-refresh'} ) && $monitorID ) {
    if (lookup_monitor()) {
        #we got refresh rates so we can use "Advanced mode"
        $xdebc_map{'config/monitor/selection-method'} = "Advanced";
    }
}

if ($xdebc_map{'config/monitor/horiz-sync'} &&
    $xdebc_map{'config/monitor/vert-refresh'}) {
    # we got refresh rates so we can use "Advanced mode"
    $xdebc_map{'config/monitor/selection-method'} = "Advanced";
}


if ($xserver) {
    $xdebpkg = "xserver-\L$xserver";
    $xdebpkg =~ s/-xf86_/-/;

}


### Do some checks, defaulting and cleanups

# lower-case driver name - beeing nice to dexconf
$xdebc_map{'config/device/driver'} = "\L$xdebc_map{'config/device/driver'}";

# method might be empty so check !=Advanced rather than ==Simple
if( $xdebc_map{'config/monitor/selection-method'} ne "Advanced" ) {
    $xdebc_map{'config/monitor/selection-method'} = "Simple";

    # try calculating the size based on width and height (if present)
    if( $screenX && $screenY ) {
        monitor_size();
    }

    # couldn't determine monitor refresh rates or size - default to 15 incher
    if( !$xdebc_map{'config/monitor/screen-size'} ) {
        $xdebc_map{'config/monitor/screen-size'} = '15 inches (380 mm)';
    }

    if (!$xdebc_map{'config/monitor/horiz-sync'} ||
        !$xdebc_map{'config/monitor/vert-refresh'} ) {
        # default value for 15 inches
        $xdebc_map{'config/monitor/horiz-sync'} = '28-50';

        # default value for 15 inches
        $xdebc_map{'config/monitor/vert-refresh'} = '43-75';
    }
}

# couldn't determine modes - use defaults for 15 incher
if (!$xdebc_map{'config/display/modes'} ) {
    $xdebc_map{'config/display/modes'} =
        '1024x768, 800x600, 640x480';
}

# couldn't determine mode - use default for 15 incher
if( !$xdebc_map{'config/monitor/mode-list'} ) {
    $xdebc_map{'config/monitor/mode-list'} = '1024x768 @ 70Hz';
    $modesource = "default";
}

# couldn't determine depth - default to 16
if( !$xdebc_map{'config/display/default_depth'} ) {
    $xdebc_map{'config/display/default_depth'} = '16';
}

# set maximum 16bit depth... we don't have any way to find out when
# the monitors doesn't support 32bit color depth. and if the machine
# is short of video memory, we will have a terrible resolution..
if ( $xdebc_map{'config/display/default_depth'} gt 16 ) {
    $xdebc_map{'config/display/default_depth'} = '16';
}

# check if driver's maximum color depth is exceeded
if ( $driverdepth[0] ) {
    my $driverdepthok = 0;
    foreach my $tmpdepth (@driverdepth) {
        if ( $tmpdepth eq $xdebc_map{'config/display/default_depth'} ) {
            $driverdepthok = 1;
        }
    }

    if ( !$driverdepthok ) {
        foreach my $tmpdepth (@driverdepth) {
            if ( $tmpdepth le 16 &&
                 $tmpdepth gt $xdebc_map{'config/display/default_depth'} ) {
                $xdebc_map{'config/display/default_depth'} = $tmpdepth;
            }
        }
    }
}

# hwinfo can do it
if( !$xdebc_map{'config/inputdevice/keyboard/rules'} ) {
    $xdebc_map{'config/inputdevice/keyboard/rules'} = $xserver;
}

# we don't have a good way to determine this - this will default
if( !$xdebc_map{'config/inputdevice/mouse/emulate3buttons'} ) {
    $xdebc_map{'config/inputdevice/mouse/emulate3buttons'} = 'true';
}

# we need some default string - monitor
if( !$xdebc_map{'config/monitor/identifier'} ) {
    $xdebc_map{'config/monitor/identifier'} = 'Xdebconfigurator Monitor';
}

# we need some default string - graphics card
if( !$xdebc_map{'config/device/identifier'} ) {
    $xdebc_map{'config/device/identifier'} = 'Xdebconfigurator Card';
}

# default mouse port
if( !$xdebc_map{'config/inputdevice/mouse/port'} ) {
        $xdebc_map{'config/inputdevice/mouse/port'} = '/dev/input/mice';
        $mousesource = "default";
}

# default mouse type
if( !$xdebc_map{'config/inputdevice/mouse/protocol'} ) {
        $xdebc_map{'config/inputdevice/mouse/protocol'} = 'ExplorerPS/2';
}


# Sort the modes list, highest resolution first
# mode-list value is only used in Simple mode I think?
%sorted_modes = ();
sub sortDesc {
    $sorted_modes{$b} <=> $sorted_modes{$a}; # sorting numericly by value
}

%sorted_modes = map { s/(\d+)(x\d+)/$1/; $1.$2, $1 }
                split(/, /, $xdebc_map{'config/display/modes'});
$xdebc_map{'config/display/modes'} =
    join(', ', sort  sortDesc (keys(%sorted_modes)));

# Set config/device/video_ram to "", from 'man XF86Config-4':
#   In most cases this is not required because the X server probes the
#   graphics  board to determine this quantity. The driver-specific
#   documentation should indicate when it might be needed.
# So we'll have to find out which graphic boards that need this and
# eventually make exceptions (that why the whole thing is not removed).
if ($xdebc_map{'config/device/video_ram'} ne "") {
    $xdebc_map{'config/device/video_ram'} = "";
}

# Hardcoded settings:
$xdebc_map{'config/monitor/lcd'} = 'false';
$xdebc_map{'config/inputdevice/mouse/retry_detection'} = 'false';
$xdebc_map{'aware_XF86Config-4'} = 'true';

# boolean - whack the config file?
if (-e "/etc/X11/XF86Config-4") {
    $xdebc_map{'clobber_XF86Config-4'} = 'true';
}

# zaxismapping needed for wheel mice
if (($xdebc_map{'config/inputdevice/mouse/protocol'} eq "ImPS/2") || $mwheel) {
    # Needed for wheel-mice scrolling
    $xdebc_map{'config/inputdevice/mouse/zaxismapping'} = 'true';
} else {
    $xdebc_map{'config/inputdevice/mouse/zaxismapping'} = 'false';
}

# PRINTOUT for debugging
warn "VIDEO CARD: $xdebc_map{'config/device/identifier'}\n";
#warn "VIDEO CARD ID: $card_number\n";
warn "VIDEO CARD DEVICE: $card_dID\n";
warn "VIDEO CARD VENDOR: $card_vID\n";
warn "VIDEO DRIVER: $xdebc_map{'config/device/driver'}\n";
warn "VIDEO DRIVER SRC: $driversource\n";
warn "VIDEO MEMORY: $xdebc_map{'config/device/video_ram'}\n";
warn "POSSIBLE XSERVER: $xserver\n";
warn "XSERVER 3: $xserver3\n";
warn "XSERVER 4: $xserver4\n";
warn "DEBIAN PACKAGE: $xdebpkg\n";
warn "MOUSE DEVICE SRC: $mousesource\n";
warn "MOUSE DEVICE: $xdebc_map{'config/inputdevice/mouse/port'}\n";
warn "MOUSE PROTOCOL: $xdebc_map{'config/inputdevice/mouse/protocol'}\n";
#warn "MOUSE DRIVER: $mdriv\n";
warn "MOUSE WHEEL: $mwheel\n";
#warn "KEYBOARD NAME: $keyName\n";
#Deprecated:
#warn "KEYBOARD MODEL: $xdebc_map{'config/inputdevice/keyboard/model'}\n";
#warn "KEYBOARD LAYOUT: $xdebc_map{'config/inputdevice/keyboard/layout'}\n";
warn "KEYBOARD RULES: $xdebc_map{'config/inputdevice/keyboard/rules'}\n";
warn "MONITOR: $xdebc_map{'config/monitor/identifier'}\n";
warn "MONITOR ID: $monitorID\n";
warn "SUGGESTED METHOD: $xdebc_map{'config/monitor/selection-method'}\n";
warn "MONITOR SIZE: $xdebc_map{'config/monitor/screen-size'}\n";
warn "MONITOR HOR SYNC: $xdebc_map{'config/monitor/horiz-sync'}\n";
warn "MONITOR VER REFR: $xdebc_map{'config/monitor/vert-refresh'}\n";
warn "MONITOR MODES: $xdebc_map{'config/display/modes'}\n";
warn "MONITOR MODE: $xdebc_map{'config/monitor/mode-list'}\n";
warn "MONITOR MODE SRC: $modesource\n";
warn "MONITOR DEFAULT DEPTH: $xdebc_map{'config/display/default_depth'}\n";

# die if the driver/xserver to use was not found
die "Failed to determine video card driver or xserver" if not $xserver;

# strip leading xf86_ for server3, allthough 3 is not supported
$xserver =~ s/xf86_//;

xdebset();

# If we want we can run dexconf from here to create a new XF86Config-4 file
#system(dexconf);

exit(0);

