Re: [Fwd: Re: [patch] Real-Time Preemption, -RT-2.6.9-mm1-V0.4]

Ingo Molnar
2004-10-29T16:42:53Z

* Ingo Molnar <mingo@elte.hu> wrote:

> > correct, and with the changeall-tree hack in addition. And keep your
> > finger near the reset button, just in case ...
>
> it wont even boot ...
>
> let me try some more hacks to make this a little bit safer.

ok, next attempt. Please apply this patch and do the changeall-tree
thing in the sound/ directory. This should in theory switch the ALSA
ioctls (and only them) to a BKL-less variant.

Ingo

--- linux/sound/core/pcm_native.c.orig
+++ linux/sound/core/pcm_native.c
@@ -3317,7 +3317,7 @@ static struct file_operations snd_pcm_f_
.open = snd_pcm_open,
.release = snd_pcm_release,
.poll = snd_pcm_playback_poll,
- .ioctl = snd_pcm_playback_ioctl,
+ .ioctl2 = snd_pcm_playback_ioctl,
.mmap = snd_pcm_mmap,
.fasync = snd_pcm_fasync,
};
@@ -3329,7 +3329,7 @@ static struct file_operations snd_pcm_f_
.open = snd_pcm_open,
.release = snd_pcm_release,
.poll = snd_pcm_capture_poll,
- .ioctl = snd_pcm_capture_ioctl,
+ .ioctl2 = snd_pcm_capture_ioctl,
.mmap = snd_pcm_mmap,
.fasync = snd_pcm_fasync,
};
--- linux/fs/ioctl.c.orig
+++ linux/fs/ioctl.c
@@ -68,19 +68,26 @@ asmlinkage long sys_ioctl(unsigned int f
goto out;
}

- lock_kernel();
switch (cmd) {
case FIOCLEX:
+ lock_kernel();
set_close_on_exec(fd, 1);
+ unlock_kernel();
break;

case FIONCLEX:
+ lock_kernel();
set_close_on_exec(fd, 0);
+ unlock_kernel();
break;

case FIONBIO:
- if ((error = get_user(on, (int __user *)arg)) != 0)
+ lock_kernel();
+ unlock_kernel();
+ if ((error = get_user(on, (int __user *)arg)) != 0) {
+ unlock_kernel();
break;
+ }
flag = O_NONBLOCK;
#ifdef __sparc__
/* SunOS compatibility item. */
@@ -91,11 +98,15 @@ asmlinkage long sys_ioctl(unsigned int f
filp->f_flags |= flag;
else
filp->f_flags &= ~flag;
+ unlock_kernel();
break;

case FIOASYNC:
- if ((error = get_user(on, (int __user *)arg)) != 0)
+ lock_kernel();
+ if ((error = get_user(on, (int __user *)arg)) != 0) {
+ unlock_kernel();
break;
+ }
flag = on ? FASYNC : 0;

/* Did FASYNC state change ? */
@@ -104,16 +115,20 @@ asmlinkage long sys_ioctl(unsigned int f
error = filp->f_op->fasync(fd, filp, on);
else error = -ENOTTY;
}
- if (error != 0)
+ if (error != 0) {
+ unlock_kernel();
break;
+ }

if (on)
filp->f_flags |= FASYNC;
else
filp->f_flags &= ~FASYNC;
+ unlock_kernel();
break;

case FIOQSIZE:
+ lock_kernel();
if (S_ISDIR(filp->f_dentry->d_inode->i_mode) ||
S_ISREG(filp->f_dentry->d_inode->i_mode) ||
S_ISLNK(filp->f_dentry->d_inode->i_mode)) {
@@ -122,15 +137,21 @@ asmlinkage long sys_ioctl(unsigned int f
}
else
error = -ENOTTY;
+ unlock_kernel();
break;
default:
error = -ENOTTY;
- if (S_ISREG(filp->f_dentry->d_inode->i_mode))
+ if (S_ISREG(filp->f_dentry->d_inode->i_mode)) {
+ lock_kernel();
error = file_ioctl(filp, cmd, arg);
- else if (filp->f_op && filp->f_op->ioctl)
+ unlock_kernel();
+ } else if (filp->f_op && filp->f_op->ioctl) {
+ lock_kernel();
error = filp->f_op->ioctl(filp->f_dentry->d_inode, filp, cmd, arg);
+ unlock_kernel();
+ } else if (filp->f_op && filp->f_op->ioctl2)
+ error = filp->f_op->ioctl2(filp->f_dentry->d_inode, filp, cmd, arg);
}
- unlock_kernel();
fput(filp);

out:
--- linux/include/linux/fs.h.orig
+++ linux/include/linux/fs.h
@@ -993,6 +993,7 @@ struct file_operations {
int (*check_flags)(int);
int (*dir_notify)(struct file *filp, unsigned long arg);
int (*flock) (struct file *, int, struct file_lock *);
+ int (*ioctl2) (struct inode *, struct file *, unsigned int, unsigned long);
};

struct inode_operations {