summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGuillaume Cottenceau <gc@mandriva.com>2003-12-18 16:00:51 +0000
committerGuillaume Cottenceau <gc@mandriva.com>2003-12-18 16:00:51 +0000
commitf4d0cbba874d45d1e31ebca5ef63df9fc4b6a4ec (patch)
treed268120d9d2c10e7c987c15c3568aa56fffca7d0
parentef7b88972b9c49fd04119efab49908b819560e6a (diff)
downloaddrakx-f4d0cbba874d45d1e31ebca5ef63df9fc4b6a4ec.tar
drakx-f4d0cbba874d45d1e31ebca5ef63df9fc4b6a4ec.tar.gz
drakx-f4d0cbba874d45d1e31ebca5ef63df9fc4b6a4ec.tar.bz2
drakx-f4d0cbba874d45d1e31ebca5ef63df9fc4b6a4ec.tar.xz
drakx-f4d0cbba874d45d1e31ebca5ef63df9fc4b6a4ec.zip
2.6 kernel support
-rwxr-xr-xkernel/check_mar.pl3
-rw-r--r--kernel/dependencies.pl3
-rwxr-xr-xkernel/update_kernel42
-rw-r--r--mdk-stage1/modules.c74
-rw-r--r--mdk-stage1/stage1.c11
-rw-r--r--mdk-stage1/tools.c11
-rw-r--r--mdk-stage1/tools.h1
7 files changed, 118 insertions, 27 deletions
diff --git a/kernel/check_mar.pl b/kernel/check_mar.pl
index aedbfdfe7..80c0cc86c 100755
--- a/kernel/check_mar.pl
+++ b/kernel/check_mar.pl
@@ -8,7 +8,6 @@ my $mar = '../mdk-stage1/mar/mar';
my %sanity_check = (
hd => [
qw(sym53c8xx),
- if_(arch() !~ /x86_64/, 'initio'),
if_(arch() !~ /ppc|x86_64/, 'advansys'),
],
network => [
@@ -24,7 +23,7 @@ foreach (keys %sanity_check) {
my $marfile = "all.modules/$main_version/${_}_modules.mar";
-e $marfile or die "ERROR: missing $marfile\n";
- my @l = map { /(\S+)\.o/ } `$mar -l $marfile`;
+ my @l = map { /(\S+)\.k?o/ } `$mar -l $marfile`;
my @pbs = difference2($sanity_check{$_}, \@l);
@pbs and die "ERROR: sanity check should prove that " . join(" ", @pbs) . " be part of $marfile\n";
diff --git a/kernel/dependencies.pl b/kernel/dependencies.pl
index 10663b56b..e3be14212 100644
--- a/kernel/dependencies.pl
+++ b/kernel/dependencies.pl
@@ -3,10 +3,11 @@ use strict;
use MDK::Common;
use list_modules;
+my $version = shift @ARGV;
my $depfile = shift @ARGV;
load_dependencies($depfile);
print STDERR "Loaded dependencies from $depfile\n";
my @modules = uniq(map { dependencies_closure($_) } @ARGV);
-print join " ", map { "$_.o" } @modules;
+print join " ", map { $_ . ($version == 24 ? '.o' : '.ko') } @modules;
print "\n";
diff --git a/kernel/update_kernel b/kernel/update_kernel
index 5fad04dd6..6a5da3db4 100755
--- a/kernel/update_kernel
+++ b/kernel/update_kernel
@@ -23,32 +23,54 @@ function create_marfile() {
$GIBASEDIR/mdk-stage1/mar/mar -c $marfile $*
}
+function kern_version() {
+ if echo $1 | grep -q ^2.4; then
+ version=24
+ objects="*.o"
+ else
+ version=25
+ objects="*.ko"
+ fi
+}
+
function create_modules() {
kernel_path=$1
kern=$2
echo "Updating modules in '`pwd`' for kernel '$kern'"
- find $kernel_path/lib/modules/ -name "*.o" -exec cp -f {} . \;
- /sbin/depmod -F $kernel_path/boot/System.map* -e *.o | perl -pe 's/\\\n//' \
- | perl -ne 's/\.o//g; s/[ \t]+/ /g; print if /: /' > modules.dep
+ kern_version $kern
+ find $kernel_path/lib/modules/ -name "$objects" -exec cp -f {} . \;
+ if [ $version -eq 24 ]; then
+ /sbin/depmod-24 -F $kernel_path/boot/System.map* -e *.o | perl -pe 's/\\\n//' \
+ | perl -ne 's/\.o//g; s/[ \t]+/ /g; print if /: /' > modules.dep
+ else
+ cp $kernel_path/lib/modules/*/modules.dep .
+ perl -ni -e 's|/\S+/([^/]+)\.k?o|$1|g; print if /: /' modules.dep
+ fi
perl -pi -e 's/((plip|ppa|imm): parport)/$1 parport_pc/' modules.dep
- /sbin/modinfo -f '%{filename} %{description}\n' *.o | perl -lne 'print "$1\t$2" if /(.*?)\.o "(.*)"/' > modules.description
+ /sbin/modinfo-$version -f '%{filename} %{description}\n' $objects | perl -lne 'print "$1\t$2" if /(.*?)\.k?o "(.*)"/' > modules.description
}
function create_modules_mar() {
- echo -n "stripping $kern: "
- $GIBASEDIR/kernel/strip_modules *.o 2>/dev/null
- echo "done"
+ kern_version $kern
+
+ if [ $version -eq 24 ]; then
+ echo -n "stripping $kern: "
+ $GIBASEDIR/kernel/strip_modules *.o 2>/dev/null
+ echo "done"
+ else
+ echo "don't strip on 2.6 since it breaks modules"
+ fi
if [ -z "$MOVE" ]; then
echo -n "packdrake $kern: "
- ls *.o | packdrake -b9s "modules.cz" 400000
+ ls $objects | packdrake -b9s "modules.cz" 400000
echo "done"
mv modules.cz ../modules.cz-$kern
fi
for i in network network_gigabit_usb network_gigabit network_usb cdrom hd hdcdrom_usb pcmcia all; do
eval "modules=\$${i}_modules_raw"
- modules_with_deps=`perl -I $GIBASEDIR/kernel $GIBASEDIR/kernel/dependencies.pl modules.dep $modules`
+ modules_with_deps=`perl -I $GIBASEDIR/kernel $GIBASEDIR/kernel/dependencies.pl $version modules.dep $modules`
if [ -n "$MOVE" ]; then modules_with_deps="change_loop.o gzloop.o isofs.o zlib_inflate.o supermount.o $modules_with_deps"; fi
eval "create_marfile ${i}_modules.mar $modules_with_deps"
done
@@ -80,7 +102,7 @@ if [ -n "$rpm" -a ! -e $ALL_KERNELS/$rpm ]; then
else
rpm2cpio $file | cpio -id
fi
- find -type f -name "*.o.gz" | xargs gunzip
+ find -type f -name "*.o.gz" -o -name "*.ko.gz" | xargs gunzip
cd ../..
for dir in /tftpboot /var/lib/tftpboot; do
diff --git a/mdk-stage1/modules.c b/mdk-stage1/modules.c
index b3090fa18..6620c771d 100644
--- a/mdk-stage1/modules.c
+++ b/mdk-stage1/modules.c
@@ -26,6 +26,7 @@
#include <unistd.h>
#include <string.h>
#include <stdio.h>
+#include <errno.h>
#include "insmod.h"
#include "stage1.h"
#include "log.h"
@@ -41,6 +42,48 @@ static struct module_deps_elem * modules_deps = NULL;
static char * archive_name = "/modules/modules.mar";
int disable_modules = 0;
+extern long init_module(void *, unsigned long, const char *);
+
+
+static const char *moderror(int err)
+{
+ switch (err) {
+ case ENOEXEC:
+ return "Invalid module format";
+ case ENOENT:
+ return "Unknown symbol in module";
+ case ESRCH:
+ return "Module has wrong symbol version";
+ case EINVAL:
+ return "Invalid parameters";
+ default:
+ return strerror(err);
+ }
+}
+
+static void *grab_file(const char *filename, unsigned long *size)
+{
+ unsigned int max = 16384;
+ int ret, fd;
+ void *buffer = malloc(max);
+
+ fd = open(filename, O_RDONLY, 0);
+ if (fd < 0)
+ return NULL;
+
+ *size = 0;
+ while ((ret = read(fd, buffer + *size, max - *size)) > 0) {
+ *size += ret;
+ if (*size == max)
+ buffer = realloc(buffer, max *= 2);
+ }
+ if (ret < 0) {
+ free(buffer);
+ buffer = NULL;
+ }
+ close(fd);
+ return buffer;
+}
/* unarchive and insmod given module
* WARNING: module must not contain the trailing ".o"
@@ -52,7 +95,10 @@ static enum insmod_return insmod_archived_file(const char * mod_name, char * opt
int i, rc;
strncpy(module_name, mod_name, sizeof(module_name));
- strcat(module_name, ".o");
+ if (kernel_version() <= 4)
+ strcat(module_name, ".o");
+ else
+ strcat(module_name, ".ko");
i = mar_extract_file(archive_name, module_name, "/tmp/");
if (i == 1) {
log_message("file-not-found-in-archive %s (maybe you can try another boot floppy such as 'hdcdrom_usb.img' or 'network_gigabit_usb.img')", module_name);
@@ -62,9 +108,26 @@ static enum insmod_return insmod_archived_file(const char * mod_name, char * opt
return INSMOD_FAILED;
strcat(final_name, mod_name);
- strcat(final_name, ".o");
+ if (kernel_version() <= 4) {
+ strcat(final_name, ".o");
+ rc = insmod_call(final_name, options);
+ } else {
+ void *file;
+ unsigned long len;
+
+ strcat(final_name, ".ko");
+ file = grab_file(final_name, &len);
+
+ if (!file) {
+ log_perror("\terror reading %s");
+ return INSMOD_FAILED;
+ }
+
+ rc = init_module(file, len, options ? options : "");
+ if (rc)
+ log_message("\terror %s", moderror(errno));
+ }
- rc = insmod_call(final_name, options);
unlink(final_name); /* sucking no space left on device */
if (rc) {
log_message("\tfailed");
@@ -366,7 +429,10 @@ enum return_type ask_insmod(enum driver_type type)
}
if (results == RETURN_OK) {
- choice[strlen(choice)-2] = '\0'; /* remove trailing .o */
+ if (kernel_version() <= 4)
+ choice[strlen(choice)-2] = '\0'; /* remove trailing .o */
+ else
+ choice[strlen(choice)-3] = '\0'; /* remove trailing .ko */
return insmod_with_options(choice, type);
} else
return results;
diff --git a/mdk-stage1/stage1.c b/mdk-stage1/stage1.c
index 526560122..4ade8eb64 100644
--- a/mdk-stage1/stage1.c
+++ b/mdk-stage1/stage1.c
@@ -274,16 +274,7 @@ static void expert_third_party_modules(void)
#ifdef ENABLE_PCMCIA
static void handle_pcmcia(char ** pcmcia_adapter)
{
- char buf[50];
- int fd = open("/proc/version", O_RDONLY);
- int size;
- if (fd == -1)
- fatal_error("could not open /proc/version");
- size = read(fd, buf, sizeof(buf));
- buf[size-1] = '\0'; // -1 to eat the \n
- close(fd);
- buf[17] = '\0'; // enough to extract `2.2'
- if (ptr_begins_static_str(buf+14, "2.2")) {
+ if (kernel_version() == 2) {
stg1_error_message("We now use kernel pcmcia support and this won't work with a 2.2 kernel.");
return;
}
diff --git a/mdk-stage1/tools.c b/mdk-stage1/tools.c
index ea8450cef..5b2128fe9 100644
--- a/mdk-stage1/tools.c
+++ b/mdk-stage1/tools.c
@@ -34,6 +34,7 @@
#include <sys/mount.h>
#include <sys/poll.h>
#include <errno.h>
+#include <sys/utsname.h>
#include "stage1.h"
#include "log.h"
#include "mount.h"
@@ -465,6 +466,16 @@ int string_array_length(char ** a)
return i;
}
+int kernel_version(void)
+{
+ struct utsname val;
+ if (uname(&val)) {
+ log_perror("uname failed");
+ return -1;
+ }
+ return charstar_to_int(val.release + 2);
+}
+
int scall_(int retval, char * msg, char * file, int line)
{
char tmp[5000];
diff --git a/mdk-stage1/tools.h b/mdk-stage1/tools.h
index 851480d2d..d8892a1ed 100644
--- a/mdk-stage1/tools.h
+++ b/mdk-stage1/tools.h
@@ -42,6 +42,7 @@ void handle_env(char ** env);
char ** grab_env(void);
char ** list_directory(char * direct);
int string_array_length(char ** a);
+int kernel_version(void);
int scall_(int retval, char * msg, char * file, int line);
#define scall(retval, msg) scall_(retval, msg, __FILE__, __LINE__)