Index: SOURCES/drakxtools-kmsstuff.patch
===================================================================
--- SOURCES/drakxtools-kmsstuff.patch	(revision 0)
+++ SOURCES/drakxtools-kmsstuff.patch	(revision 0)
@@ -0,0 +1,209 @@
+Index: drakxtools-13.42/perl-install/standalone/service_harddrake
+===================================================================
+--- drakxtools-13.42/perl-install/standalone/service_harddrake
++++ drakxtools-13.42/perl-install/standalone/service_harddrake	2011-03-06 09:19:50.597214025 +0200
+@@ -24,11 +24,18 @@
+ use harddrake::autoconf;
+ use harddrake::sound;
+ use Xconfig::card;
++use Xconfig::initrd;
+ use modules;
+ use Storable qw(store retrieve);
+ 
+ 
+ my $force = member('--force', @ARGV);
++my $in;
++# ask for initrd regeneration due to display driver change
++my $initrd_needed;
++# ask for reboot due to display driver change
++my $reboot_needed;
++my $plymouth = -x '/bin/plymouth';
+ 
+ my $invert_do_it = $ARGV[0] eq 'X11' ? 1 : 0;
+ my ($hw_sysconfdir, $timeout) = ("/etc/sysconfig/harddrake2", $invert_do_it ? 600 : 25);
+@@ -59,6 +66,7 @@
+ 
+ # default to 'yes' on upgrade:
+ $cfg{AUTORECONFIGURE_RIGHT_XORG_DRIVER} = 'yes' if !exists $cfg{AUTORECONFIGURE_RIGHT_XORG_DRIVER};
++$cfg{CHECK_INITRD} = 'yes' if !exists $cfg{CHECK_INITRD};
+ 
+ # autoreconfigure laptop-dependent services when switching from laptop to desktop, and vice versa
+ if (!exists $previous_kernel_config{IS_LAPTOP} || $force || $isLaptop != text2bool($previous_kernel_config{IS_LAPTOP})) {
+@@ -72,6 +80,22 @@
+     append_to_file($known_kernels, "$curr_kernel\n");
+ }
+ 
++sub ask_with_timeout {
++    my ($title, $msg, $timeout, $plymouth) = @_;
++    my ($pid, $res, $timed_out);
++
++    $SIG{ALRM} = sub { $no = 1; kill 15, $pid };
++    unless ($pid = fork()) {
++	$plymouth and system('plymouth', 'hide-splash');
++	exec("/usr/share/harddrake/confirm", $title, $msg);
++    }
++    alarm($timeout);
++    wait();
++    $res = $?;
++    alarm(0);
++    return $res, $timed_out;
++}
++
+ sub get_xorg_driver() {
+     my $x = Xconfig::xfree->read;
+     if ($x) {
+@@ -95,15 +119,29 @@
+ }
+ 
+ sub switch_x_driver {
+-    my ($old_driver, $new_driver, $reason) = @_;
++    my ($old_driver, $new_driver, $reason, $plymouth, $o_in) = @_;
++    $plymouth and system('plymouth', 'message', '--text=' . N("Configuring display driver - this may take several minutes..."));
+     if (!find_xorg_driver($new_driver)) {
+         log::explanations("would switch X.org driver from '$old_driver' to '$new_driver' ($reason); but new driver is not installed");
+         return;
+     }
++    # This should use calls to Xconfig instead of substitution. However, currently
++    # Xconfig probably makes too intrusive changes to xorg.conf when switching the driver.
+     cp_af('/etc/X11/xorg.conf', "/etc/X11/xorg.conf.mdv$^T");
+     substInFile { s!Driver "($old_driver)"!Driver "$new_driver"!g } '/etc/X11/xorg.conf';
+     log::explanations("switch X.org driver from '$old_driver' to '$new_driver' ($reason)");
+     Xconfig::card::libgl_config_and_more({ Driver => $new_driver });
++    Xconfig::initrd::rebuild_initrds_if_needed($o_in);
++
++    # If a wrong driver is loaded, ask for a reboot.
++    my $reboot_needed = -x "/sbin/display_driver_helper" && system("/sbin/display_driver_helper", "--check-loaded") != 0;
++    if (!$reboot_needed) {
++        # Load any new drivers.
++        system("udevadm", "trigger",  "--subsystem-match=pci", "--attr-match=class=0x03*");
++        system("udevadm", "settle", "--timeout=15");
++        $plymouth and system("plymouth", "message", "--text=" . N("Display driver configuration done, continuing..."));
++    }
++    $reboot_needed;
+ }
+ 
+ sub should_reconfigure_x_driver {
+@@ -168,10 +206,20 @@
+     # auto reconfigure x11 only on first time default driver have changed:
+     my ($should_reconfigure, $reason) = should_reconfigure_x_driver($card_data, $device, $current_driver);
+     if ($should_reconfigure) {
+-	    switch_x_driver($current_driver, $card_data->{Driver}, $reason);
++	if (-e "/tmp/.X11-unix/X0") {
++	    # We are too late, X server is already running.
++	    # Disable speedboot for next boot.
++	    my $kernel_version = c::kernel_version();
++	    substInFile { s!^$kernel_version .*\n!! } "/var/lib/speedboot/status" if -e "/var/lib/speedboot/status";
++	    # Restore state as we were not able to switch the driver yet.
++	    setVarsInSh("$hw_sysconfdir/xorg", { XORG_DRV => $previous_xorg_config{XORG_DRV} });
++	} else {
++	    $in ||= interactive->vnew;
++	    $reboot_needed ||= switch_x_driver($current_driver, $card_data->{Driver}, $reason, $plymouth, $in);
+ 	    schedule_warn_about_switch($reason) if any { $current_driver =~ $_->{xorg_driver_regexp} } @cards;
+ 	    # Update $current_driver with the new one
+ 	    $current_driver = $card_data->{Driver};
++	}
+     }
+ 
+     # nv->nouveau or non_kms_nouveau->kms_nouveau can't have "Disable dri"!
+@@ -209,18 +257,33 @@
+         if ($old_driver) {
+             my $reason = N("The proprietary kernel driver was not found for '%s' X.org driver",
+                            $old_driver);
+-            switch_x_driver($card->{xorg_driver_regexp}, $driver, $reason);
++            $in ||= interactive->vnew;
++            $reboot_needed ||= switch_x_driver($card->{xorg_driver_regexp}, $driver, $reason, $plymouth, $in);
+             schedule_warn_about_switch($reason);
+         }
+     }
+ }
+ 
++if (!$reboot_needed && text2bool($cfg{CHECK_INITRD})) {
++    if (-x "/sbin/display_driver_helper" && system("display_driver_helper", "--check-loaded") != 0) {
++	# incorrect driver is loaded, X.org can't start (e.g. proprietary driver loaded while free driver in use,
++	# or free driver loaded while vesa is configured).
++	if (Xconfig::initrd::is_rebuild_needed()) {
++	    $initrd_needed = 1;
++	    # no auto-reboot if user is somehow in X (speedboot bug etc.)
++	    $reboot_needed = 1 unless -e "/tmp/.X11-unix/X0";
++	}
++    } elsif (!$reboot_needed && -e "/dev/.harddrake-unoptimal-initrd") {
++	# initrd didn't have the KMS driver, it was loaded by udev later in the boot process.
++	unlink("/dev/.harddrake-unoptimal-initrd");
++	$initrd_needed ||= Xconfig::initrd::is_rebuild_needed();
++    }
++}
++
+ my $is_globetrotter = -f '/usr/sbin/mdkmove';
+ 
+ my (%config, $wait);
+ my $in;
+-my $splash = -f '/proc/splash';
+-my $splash_was_silent = cat_('/proc/splash') =~ /, silent : on/;
+ 
+ # For each hw, class, detect device, compare and offer to reconfigure if needed
+ foreach my $hw_class (@harddrake::data::tree) {
+@@ -333,19 +396,12 @@
+         log::explanations(qw(skip $Ident configuration since "$configurator" is not executable));
+         next;
+     }
+-    my ($pid, $no, $res);
++    my ($no, $res);
+     $hw_class->{automatic} ||= ref($configurator) eq 'CODE';
+ 
+     if (!$hw_class->{automatic}) {
+-        $SIG{ALRM} = sub { $no = 1; kill 15, $pid };
+-        unless ($pid = fork()) {
+-            $splash and eval { output('/proc/splash', 'verbose') } and $splash = 0;
+-            exec("/usr/share/harddrake/confirm", $Ident, $timeout, $msg);
+-        }
+-        alarm($timeout);
+-        wait();
+-        $res = $?;
+-        alarm(0);
++	($res, $no) = ask_with_timeout(N("Hardware changes in \"%s\" class (%s seconds to answer)", $Ident, $timeout),
++	    			       $msg . N("Do you want to run the appropriate config tool?"), $timeout, $plymouth);
+     } else {
+         $res = 1;
+     }
+@@ -379,8 +435,28 @@
+ log::explanations("created file $last_boot_config");
+ Storable::store(\%config, $last_boot_config);
+ 
++# Handle $need_initrd and $need_reboot from earlier:
++my ($do_initrd, $do_reboot);
++my ($reply, $timedout);
++if ($initrd_needed && $reboot_needed) {
++    ($reply, $timedout) = ask_with_timeout(N("Display driver setup"), N("Due to a previous display driver change the initrd images will have to be regenerated and the system rebooted to prevent the X server startup from failing.") . "\n\n" .  N("Press Cancel within 15 seconds to abort."), 15, $plymouth);
++} elsif ($reboot_needed) {
++    ($reply, $timedout) = ask_with_timeout(N("Display driver setup"), N("The system has to be rebooted due to a display driver change.") . "\n\n" .  N("Press Cancel within 15 seconds to abort."), 15, $plymouth);
++} elsif ($initrd_needed) {
++    ($reply, $timedout) = ask_with_timeout(N("Display driver setup"), N("The initrd images will be regenerated to optimize the boot process for the current display driver.") . "\n\n" .  N("Press Cancel within 15 seconds to abort."), 15, $plymouth);
++}
++if ($reply || $timedout) {
++    $do_initrd = $initrd_needed;
++    $do_reboot = $reboot_needed;
++}
++if ($do_initrd) {
++    $in ||= interactive->vnew;
++    Xconfig::initrd::rebuild_initrds(0, $in);
++}
++exec("/sbin/reboot") if $do_reboot;
++
+ # restore bootsplash mode
+-$splash_was_silent and eval { output('/proc/splash', 'silent') };
++$plymouth and system('plymouth', 'show-splash');
+ 
+ 
+ $in->exit(0) if $in;
+Index: drakxtools-13.42/perl-install/standalone/service_harddrake_confirm
+===================================================================
+--- drakxtools-13.42/perl-install/standalone/service_harddrake_confirm
++++ drakxtools-13.42/perl-install/standalone/service_harddrake_confirm	2011-03-06 05:06:23.564798660 +0200
+@@ -4,6 +4,5 @@
+ use interactive;
+ 
+ my $in = interactive->vnew;
+-my $res = $in->ask_okcancel(N("Hardware changes in \"%s\" class (%s seconds to answer)", $ARGV[0], $ARGV[1]),
+-                            $ARGV[2] . N("Do you want to run the appropriate config tool?"), 1);
++my $res = $in->ask_okcancel($ARGV[0], $ARGV[1], 1);
+ $in->exit($res);
Index: SPECS/drakxtools.spec
===================================================================
--- SPECS/drakxtools.spec	(revision 642211)
+++ SPECS/drakxtools.spec	(working copy)
@@ -1,9 +1,10 @@
 Summary: The drakxtools (diskdrake, ...)
 Name:    drakxtools
 Version: 13.42
-Release: %mkrel 1
+Release: %mkrel 1.test.2
 Url:     http://wiki.mandriva.com/en/Development/Docs/drakxtools_dev
 Source0: %name-%version.tar.lzma
+Patch0: drakxtools-kmsstuff.patch
 License: GPLv2+
 Group: System/Configuration/Other
 # usermode 1.92-4mdv2008.0 has the /etc/pam.d/mandriva-{simple,console}-auth
