Commit 9add6ead authored by Linus Torvalds's avatar Linus Torvalds

Merge bk://bk.linux1394.org/ieee1394-2.6

into ppc970.osdl.org:/home/torvalds/v2.6/linux
parents b0e15db0 3caef8d2
...@@ -458,6 +458,13 @@ void nmi_watchdog_tick (struct pt_regs * regs) ...@@ -458,6 +458,13 @@ void nmi_watchdog_tick (struct pt_regs * regs)
wrmsr(MSR_P4_IQ_CCCR0, P4_NMI_IQ_CCCR0, 0); wrmsr(MSR_P4_IQ_CCCR0, P4_NMI_IQ_CCCR0, 0);
apic_write(APIC_LVTPC, APIC_DM_NMI); apic_write(APIC_LVTPC, APIC_DM_NMI);
} }
else if (nmi_perfctr_msr == MSR_P6_PERFCTR0) {
/* Only P6 based Pentium M need to re-unmask
* the apic vector but it doesn't hurt
* other P6 variant */
apic_write(APIC_LVTPC,
apic_read(APIC_LVTPC) & ~APIC_LVT_MASKED);
}
wrmsr(nmi_perfctr_msr, -(cpu_khz/nmi_hz*1000), -1); wrmsr(nmi_perfctr_msr, -(cpu_khz/nmi_hz*1000), -1);
} }
} }
......
...@@ -487,7 +487,7 @@ _GLOBAL(enter_rtas) ...@@ -487,7 +487,7 @@ _GLOBAL(enter_rtas)
mflr r0 mflr r0
std r0,16(r1) std r0,16(r1)
stdu r1,-RTAS_FRAME_SIZE(r1) /* Save SP and create stack space. */ stdu r1,-RTAS_FRAME_SIZE(r1) /* Save SP and create stack space. */
/* Because RTAS is running in 32b mode, it clobbers the high order half /* Because RTAS is running in 32b mode, it clobbers the high order half
* of all registers that it saves. We therefore save those registers * of all registers that it saves. We therefore save those registers
* RTAS might touch to the stack. (r0, r3-r13 are caller saved) * RTAS might touch to the stack. (r0, r3-r13 are caller saved)
...@@ -512,12 +512,25 @@ _GLOBAL(enter_rtas) ...@@ -512,12 +512,25 @@ _GLOBAL(enter_rtas)
mfsrr1 r10 mfsrr1 r10
std r10,_SRR1(r1) std r10,_SRR1(r1)
/* There is no way it is acceptable to get here with interrupts enabled,
* check it with the asm equivalent of WARN_ON
*/
mfmsr r6
andi. r0,r6,MSR_EE
1: tdnei r0,0
.section __bug_table,"a"
.llong 1b,__LINE__ + 0x1000000, 1f, 2f
.previous
.section .rodata,"a"
1: .asciz __FILE__
2: .asciz "enter_rtas"
.previous
/* Unfortunately, the stack pointer and the MSR are also clobbered, /* Unfortunately, the stack pointer and the MSR are also clobbered,
* so they are saved in the PACA which allows us to restore * so they are saved in the PACA which allows us to restore
* our original state after RTAS returns. * our original state after RTAS returns.
*/ */
std r1,PACAR1(r13) std r1,PACAR1(r13)
mfmsr r6
std r6,PACASAVEDMSR(r13) std r6,PACASAVEDMSR(r13)
/* Setup our real return addr */ /* Setup our real return addr */
......
...@@ -93,8 +93,13 @@ ...@@ -93,8 +93,13 @@
_stext: _stext:
#ifdef CONFIG_PPC_PSERIES #ifdef CONFIG_PPC_PSERIES
_STATIC(__start) _STATIC(__start)
/* NOP this out unconditionally */
BEGIN_FTR_SECTION
b .__start_initialization_pSeries b .__start_initialization_pSeries
END_FTR_SECTION(0, 1)
#endif #endif
/* Catch branch to 0 in real mode */
trap
#ifdef CONFIG_PPC_ISERIES #ifdef CONFIG_PPC_ISERIES
/* /*
* At offset 0x20, there is a pointer to iSeries LPAR data. * At offset 0x20, there is a pointer to iSeries LPAR data.
......
...@@ -1926,6 +1926,11 @@ finish_node(struct device_node *np, unsigned long mem_start, ...@@ -1926,6 +1926,11 @@ finish_node(struct device_node *np, unsigned long mem_start,
np->name = get_property(np, "name", 0); np->name = get_property(np, "name", 0);
np->type = get_property(np, "device_type", 0); np->type = get_property(np, "device_type", 0);
if (!np->name)
np->name = "<NULL>";
if (!np->type)
np->type = "<NULL>";
/* get the device addresses and interrupts */ /* get the device addresses and interrupts */
if (ifunc != NULL) if (ifunc != NULL)
mem_start = ifunc(np, mem_start, naddrc, nsizec); mem_start = ifunc(np, mem_start, naddrc, nsizec);
......
...@@ -68,15 +68,20 @@ char rtas_data_buf[RTAS_DATA_BUF_SIZE]__page_aligned; ...@@ -68,15 +68,20 @@ char rtas_data_buf[RTAS_DATA_BUF_SIZE]__page_aligned;
void void
call_rtas_display_status(char c) call_rtas_display_status(char c)
{ {
struct rtas_args *rtas = &(get_paca()->xRtas); struct rtas_args *args = &(get_paca()->xRtas);
unsigned long s;
spin_lock_irqsave(&rtas.lock, s);
rtas->token = 10; args->token = 10;
rtas->nargs = 1; args->nargs = 1;
rtas->nret = 1; args->nret = 1;
rtas->rets = (rtas_arg_t *)&(rtas->args[1]); args->rets = (rtas_arg_t *)&(args->args[1]);
rtas->args[0] = (int)c; args->args[0] = (int)c;
enter_rtas((void *)__pa((unsigned long)rtas)); enter_rtas((void *)__pa((unsigned long)args));
spin_unlock_irqrestore(&rtas.lock, s);
} }
int int
...@@ -91,8 +96,9 @@ rtas_token(const char *service) ...@@ -91,8 +96,9 @@ rtas_token(const char *service)
return tokp ? *tokp : RTAS_UNKNOWN_SERVICE; return tokp ? *tokp : RTAS_UNKNOWN_SERVICE;
} }
void
log_rtas_error(struct rtas_args *rtas_args) static int
__log_rtas_error(struct rtas_args *rtas_args)
{ {
struct rtas_args err_args, temp_args; struct rtas_args err_args, temp_args;
...@@ -111,13 +117,24 @@ log_rtas_error(struct rtas_args *rtas_args) ...@@ -111,13 +117,24 @@ log_rtas_error(struct rtas_args *rtas_args)
PPCDBG(PPCDBG_RTAS, "\tentering rtas with 0x%lx\n", PPCDBG(PPCDBG_RTAS, "\tentering rtas with 0x%lx\n",
(void *)__pa((unsigned long)&err_args)); (void *)__pa((unsigned long)&err_args));
enter_rtas((void *)__pa((unsigned long)&get_paca()->xRtas)); enter_rtas((void *)__pa((unsigned long)&get_paca()->xRtas));
PPCDBG(PPCDBG_RTAS, "\treturned from rtas ...\n"); PPCDBG(PPCDBG_RTAS, "\treturned from rtas ...\n");
err_args = get_paca()->xRtas; err_args = get_paca()->xRtas;
get_paca()->xRtas = temp_args; get_paca()->xRtas = temp_args;
if (err_args.rets[0] == 0) return err_args.rets[0];
}
void
log_rtas_error(struct rtas_args *rtas_args)
{
unsigned long s;
int rc;
spin_lock_irqsave(&rtas.lock, s);
rc = __log_rtas_error(rtas_args);
spin_unlock_irqrestore(&rtas.lock, s);
if (rc == 0)
log_error(rtas_err_buf, ERR_TYPE_RTAS_LOG, 0); log_error(rtas_err_buf, ERR_TYPE_RTAS_LOG, 0);
} }
...@@ -126,9 +143,10 @@ rtas_call(int token, int nargs, int nret, ...@@ -126,9 +143,10 @@ rtas_call(int token, int nargs, int nret,
unsigned long *outputs, ...) unsigned long *outputs, ...)
{ {
va_list list; va_list list;
int i; int i, logit = 0;
unsigned long s; unsigned long s;
struct rtas_args *rtas_args = &(get_paca()->xRtas); struct rtas_args *rtas_args = &(get_paca()->xRtas);
long ret;
PPCDBG(PPCDBG_RTAS, "Entering rtas_call\n"); PPCDBG(PPCDBG_RTAS, "Entering rtas_call\n");
PPCDBG(PPCDBG_RTAS, "\ttoken = 0x%x\n", token); PPCDBG(PPCDBG_RTAS, "\ttoken = 0x%x\n", token);
...@@ -138,6 +156,9 @@ rtas_call(int token, int nargs, int nret, ...@@ -138,6 +156,9 @@ rtas_call(int token, int nargs, int nret,
if (token == RTAS_UNKNOWN_SERVICE) if (token == RTAS_UNKNOWN_SERVICE)
return -1; return -1;
/* Gotta do something different here, use global lock for now... */
spin_lock_irqsave(&rtas.lock, s);
rtas_args->token = token; rtas_args->token = token;
rtas_args->nargs = nargs; rtas_args->nargs = nargs;
rtas_args->nret = nret; rtas_args->nret = nret;
...@@ -150,26 +171,16 @@ rtas_call(int token, int nargs, int nret, ...@@ -150,26 +171,16 @@ rtas_call(int token, int nargs, int nret,
va_end(list); va_end(list);
for (i = 0; i < nret; ++i) for (i = 0; i < nret; ++i)
rtas_args->rets[i] = 0; rtas_args->rets[i] = 0;
#if 0 /* Gotta do something different here, use global lock for now... */
spin_lock_irqsave(&rtas_args->lock, s);
#else
spin_lock_irqsave(&rtas.lock, s);
#endif
PPCDBG(PPCDBG_RTAS, "\tentering rtas with 0x%lx\n", PPCDBG(PPCDBG_RTAS, "\tentering rtas with 0x%lx\n",
(void *)__pa((unsigned long)rtas_args)); (void *)__pa((unsigned long)rtas_args));
enter_rtas((void *)__pa((unsigned long)rtas_args)); enter_rtas((void *)__pa((unsigned long)rtas_args));
PPCDBG(PPCDBG_RTAS, "\treturned from rtas ...\n"); PPCDBG(PPCDBG_RTAS, "\treturned from rtas ...\n");
if (rtas_args->rets[0] == -1) if (rtas_args->rets[0] == -1)
log_rtas_error(rtas_args); logit = (__log_rtas_error(rtas_args) == 0);
#if 0 /* Gotta do something different here, use global lock for now... */
spin_unlock_irqrestore(&rtas_args->lock, s);
#else
spin_unlock_irqrestore(&rtas.lock, s);
#endif
ifppcdebug(PPCDBG_RTAS) { ifppcdebug(PPCDBG_RTAS) {
for(i=0; i < nret ;i++) for(i=0; i < nret ;i++)
udbg_printf("\tnret[%d] = 0x%lx\n", i, (ulong)rtas_args->rets[i]); udbg_printf("\tnret[%d] = 0x%lx\n", i, (ulong)rtas_args->rets[i]);
...@@ -178,7 +189,15 @@ rtas_call(int token, int nargs, int nret, ...@@ -178,7 +189,15 @@ rtas_call(int token, int nargs, int nret,
if (nret > 1 && outputs != NULL) if (nret > 1 && outputs != NULL)
for (i = 0; i < nret-1; ++i) for (i = 0; i < nret-1; ++i)
outputs[i] = rtas_args->rets[i+1]; outputs[i] = rtas_args->rets[i+1];
return (ulong)((nret > 0) ? rtas_args->rets[0] : 0); ret = (ulong)((nret > 0) ? rtas_args->rets[0] : 0);
/* Gotta do something different here, use global lock for now... */
spin_unlock_irqrestore(&rtas.lock, s);
if (logit)
log_error(rtas_err_buf, ERR_TYPE_RTAS_LOG, 0);
return ret;
} }
/* Given an RTAS status code of 990n compute the hinted delay of 10^n /* Given an RTAS status code of 990n compute the hinted delay of 10^n
...@@ -464,12 +483,12 @@ asmlinkage int ppc_rtas(struct rtas_args __user *uargs) ...@@ -464,12 +483,12 @@ asmlinkage int ppc_rtas(struct rtas_args __user *uargs)
enter_rtas((void *)__pa((unsigned long)&get_paca()->xRtas)); enter_rtas((void *)__pa((unsigned long)&get_paca()->xRtas));
args = get_paca()->xRtas; args = get_paca()->xRtas;
spin_unlock_irqrestore(&rtas.lock, flags);
args.rets = (rtas_arg_t *)&(args.args[nargs]); args.rets = (rtas_arg_t *)&(args.args[nargs]);
if (args.rets[0] == -1) if (args.rets[0] == -1)
log_rtas_error(&args); log_rtas_error(&args);
spin_unlock_irqrestore(&rtas.lock, flags);
/* Copy out args. */ /* Copy out args. */
if (copy_to_user(uargs->args + nargs, if (copy_to_user(uargs->args + nargs,
args.args + nargs, args.args + nargs,
...@@ -485,7 +504,9 @@ asmlinkage int ppc_rtas(struct rtas_args __user *uargs) ...@@ -485,7 +504,9 @@ asmlinkage int ppc_rtas(struct rtas_args __user *uargs)
void rtas_stop_self(void) void rtas_stop_self(void)
{ {
struct rtas_args *rtas_args = &(get_paca()->xRtas); struct rtas_args *rtas_args = &(get_paca()->xRtas);
unsigned long s;
spin_lock_irqsave(&rtas.lock, s);
rtas_args->token = rtas_token("stop-self"); rtas_args->token = rtas_token("stop-self");
BUG_ON(rtas_args->token == RTAS_UNKNOWN_SERVICE); BUG_ON(rtas_args->token == RTAS_UNKNOWN_SERVICE);
rtas_args->nargs = 0; rtas_args->nargs = 0;
...@@ -495,6 +516,8 @@ void rtas_stop_self(void) ...@@ -495,6 +516,8 @@ void rtas_stop_self(void)
printk("%u %u Ready to die...\n", printk("%u %u Ready to die...\n",
smp_processor_id(), hard_smp_processor_id()); smp_processor_id(), hard_smp_processor_id());
enter_rtas((void *)__pa(rtas_args)); enter_rtas((void *)__pa(rtas_args));
spin_unlock_irqrestore(&rtas.lock, s);
panic("Alas, I survived.\n"); panic("Alas, I survived.\n");
} }
#endif /* CONFIG_HOTPLUG_CPU */ #endif /* CONFIG_HOTPLUG_CPU */
......
...@@ -9,14 +9,14 @@ config FW_LOADER ...@@ -9,14 +9,14 @@ config FW_LOADER
the kernel tree does. the kernel tree does.
config DEBUG_DRIVER config DEBUG_DRIVER
bool "Driver Core verbose debug messages" bool "Driver Core verbose debug messages"
depends on DEBUG_KERNEL depends on DEBUG_KERNEL
help help
Say Y here if you want the Driver core to produce a bunch of Say Y here if you want the Driver core to produce a bunch of
debug messages to the system log. Select this if you are having a debug messages to the system log. Select this if you are having a
problem with the driver core and want to see more of what is problem with the driver core and want to see more of what is
going on. going on.
If you are unsure about this, say N here. If you are unsure about this, say N here.
endmenu endmenu
...@@ -155,8 +155,7 @@ static int class_device_dev_link(struct class_device * class_dev) ...@@ -155,8 +155,7 @@ static int class_device_dev_link(struct class_device * class_dev)
static void class_device_dev_unlink(struct class_device * class_dev) static void class_device_dev_unlink(struct class_device * class_dev)
{ {
if (class_dev->dev) sysfs_remove_link(&class_dev->kobj, "device");
sysfs_remove_link(&class_dev->kobj, "device");
} }
static int class_device_driver_link(struct class_device * class_dev) static int class_device_driver_link(struct class_device * class_dev)
...@@ -169,8 +168,7 @@ static int class_device_driver_link(struct class_device * class_dev) ...@@ -169,8 +168,7 @@ static int class_device_driver_link(struct class_device * class_dev)
static void class_device_driver_unlink(struct class_device * class_dev) static void class_device_driver_unlink(struct class_device * class_dev)
{ {
if ((class_dev->dev) && (class_dev->dev->driver)) sysfs_remove_link(&class_dev->kobj, "driver");
sysfs_remove_link(&class_dev->kobj, "driver");
} }
......
...@@ -35,6 +35,7 @@ ...@@ -35,6 +35,7 @@
#include <linux/init.h> #include <linux/init.h>
#include <linux/devfs_fs_kernel.h> #include <linux/devfs_fs_kernel.h>
#include <linux/smp_lock.h> #include <linux/smp_lock.h>
#include <linux/device.h>
#include <asm/atarihw.h> #include <asm/atarihw.h>
#include <asm/traps.h> #include <asm/traps.h>
...@@ -149,6 +150,8 @@ static struct dsp56k_device { ...@@ -149,6 +150,8 @@ static struct dsp56k_device {
int tx_wsize, rx_wsize; int tx_wsize, rx_wsize;
} dsp56k; } dsp56k;
static struct class_simple *dsp56k_class;
static int dsp56k_reset(void) static int dsp56k_reset(void)
{ {
u_char status; u_char status;
...@@ -502,6 +505,8 @@ static char banner[] __initdata = KERN_INFO "DSP56k driver installed\n"; ...@@ -502,6 +505,8 @@ static char banner[] __initdata = KERN_INFO "DSP56k driver installed\n";
static int __init dsp56k_init_driver(void) static int __init dsp56k_init_driver(void)
{ {
int err = 0;
if(!MACH_IS_ATARI || !ATARIHW_PRESENT(DSP56K)) { if(!MACH_IS_ATARI || !ATARIHW_PRESENT(DSP56K)) {
printk("DSP56k driver: Hardware not present\n"); printk("DSP56k driver: Hardware not present\n");
return -ENODEV; return -ENODEV;
...@@ -511,17 +516,35 @@ static int __init dsp56k_init_driver(void) ...@@ -511,17 +516,35 @@ static int __init dsp56k_init_driver(void)
printk("DSP56k driver: Unable to register driver\n"); printk("DSP56k driver: Unable to register driver\n");
return -ENODEV; return -ENODEV;
} }
dsp56k_class = class_simple_create(THIS_MODULE, "dsp56k");
if (IS_ERR(dsp56k_class)) {
err = PTR_ERR(dsp56k_class);
goto out_chrdev;
}
class_simple_device_add(dsp56k_class, MKDEV(DSP56K_MAJOR, 0), NULL, "dsp56k");
devfs_mk_cdev(MKDEV(DSP56K_MAJOR, 0), err = devfs_mk_cdev(MKDEV(DSP56K_MAJOR, 0),
S_IFCHR | S_IRUSR | S_IWUSR, "dsp56k"); S_IFCHR | S_IRUSR | S_IWUSR, "dsp56k");
if(err)
goto out_class;
printk(banner); printk(banner);
return 0; goto out;
out_class:
class_simple_device_remove(MKDEV(DSP56K_MAJOR, 0));
class_simple_destroy(dsp56k_class);
out_chrdev:
unregister_chrdev(DSP56K_MAJOR, "dsp56k");
out:
return err;
} }
module_init(dsp56k_init_driver); module_init(dsp56k_init_driver);
static void __exit dsp56k_cleanup_driver(void) static void __exit dsp56k_cleanup_driver(void)
{ {
class_simple_device_remove(MKDEV(DSP56K_MAJOR, 0));
class_simple_destroy(dsp56k_class);
unregister_chrdev(DSP56K_MAJOR, "dsp56k"); unregister_chrdev(DSP56K_MAJOR, "dsp56k");
devfs_remove("dsp56k"); devfs_remove("dsp56k");
} }
......
...@@ -38,6 +38,7 @@ ...@@ -38,6 +38,7 @@
#include <linux/zftape.h> #include <linux/zftape.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/device.h>
#include "../zftape/zftape-init.h" #include "../zftape/zftape-init.h"
#include "../zftape/zftape-read.h" #include "../zftape/zftape-read.h"
...@@ -103,6 +104,8 @@ static struct file_operations zft_cdev = ...@@ -103,6 +104,8 @@ static struct file_operations zft_cdev =
.release = zft_close, .release = zft_close,
}; };
static struct class_simple *zft_class;
/* Open floppy tape device /* Open floppy tape device
*/ */
static int zft_open(struct inode *ino, struct file *filep) static int zft_open(struct inode *ino, struct file *filep)
...@@ -341,22 +344,29 @@ KERN_INFO ...@@ -341,22 +344,29 @@ KERN_INFO
"installing zftape VFS interface for ftape driver ..."); "installing zftape VFS interface for ftape driver ...");
TRACE_CATCH(register_chrdev(QIC117_TAPE_MAJOR, "zft", &zft_cdev),); TRACE_CATCH(register_chrdev(QIC117_TAPE_MAJOR, "zft", &zft_cdev),);
zft_class = class_simple_create(THIS_MODULE, "zft");
for (i = 0; i < 4; i++) { for (i = 0; i < 4; i++) {
class_simple_device_add(zft_class, MKDEV(QIC117_TAPE_MAJOR, i), NULL, "qft%i", i);
devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i), devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i),
S_IFCHR | S_IRUSR | S_IWUSR, S_IFCHR | S_IRUSR | S_IWUSR,
"qft%i", i); "qft%i", i);
class_simple_device_add(zft_class, MKDEV(QIC117_TAPE_MAJOR, i + 4), NULL, "nqft%i", i);
devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 4), devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 4),
S_IFCHR | S_IRUSR | S_IWUSR, S_IFCHR | S_IRUSR | S_IWUSR,
"nqft%i", i); "nqft%i", i);
class_simple_device_add(zft_class, MKDEV(QIC117_TAPE_MAJOR, i + 16), NULL, "zqft%i", i);
devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 16), devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 16),
S_IFCHR | S_IRUSR | S_IWUSR, S_IFCHR | S_IRUSR | S_IWUSR,
"zqft%i", i); "zqft%i", i);
class_simple_device_add(zft_class, MKDEV(QIC117_TAPE_MAJOR, i + 20), NULL, "nzqft%i", i);
devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 20), devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 20),
S_IFCHR | S_IRUSR | S_IWUSR, S_IFCHR | S_IRUSR | S_IWUSR,
"nzqft%i", i); "nzqft%i", i);
class_simple_device_add(zft_class, MKDEV(QIC117_TAPE_MAJOR, i + 32), NULL, "rawqft%i", i);
devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 32), devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 32),
S_IFCHR | S_IRUSR | S_IWUSR, S_IFCHR | S_IRUSR | S_IWUSR,
"rawqft%i", i); "rawqft%i", i);
class_simple_device_add(zft_class, MKDEV(QIC117_TAPE_MAJOR, i + 36), NULL, "nrawrawqft%i", i);
devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 36), devfs_mk_cdev(MKDEV(QIC117_TAPE_MAJOR, i + 36),
S_IFCHR | S_IRUSR | S_IWUSR, S_IFCHR | S_IRUSR | S_IWUSR,
"nrawqft%i", i); "nrawqft%i", i);
...@@ -386,12 +396,19 @@ static void zft_exit(void) ...@@ -386,12 +396,19 @@ static void zft_exit(void)
} }
for (i = 0; i < 4; i++) { for (i = 0; i < 4; i++) {
devfs_remove("qft%i", i); devfs_remove("qft%i", i);
class_simple_device_remove(MKDEV(QIC117_TAPE_MAJOR, i));
devfs_remove("nqft%i", i); devfs_remove("nqft%i", i);
class_simple_device_remove(MKDEV(QIC117_TAPE_MAJOR, i + 4));
devfs_remove("zqft%i", i); devfs_remove("zqft%i", i);
class_simple_device_remove(MKDEV(QIC117_TAPE_MAJOR, i + 16));
devfs_remove("nzqft%i", i); devfs_remove("nzqft%i", i);
class_simple_device_remove(MKDEV(QIC117_TAPE_MAJOR, i + 20));
devfs_remove("rawqft%i", i); devfs_remove("rawqft%i", i);
class_simple_device_remove(MKDEV(QIC117_TAPE_MAJOR, i + 32));
devfs_remove("nrawqft%i", i); devfs_remove("nrawqft%i", i);
class_simple_device_remove(MKDEV(QIC117_TAPE_MAJOR, i + 36));
} }
class_simple_destroy(zft_class);
zft_uninit_mem(); /* release remaining memory, if any */ zft_uninit_mem(); /* release remaining memory, if any */
printk(KERN_INFO "zftape successfully unloaded.\n"); printk(KERN_INFO "zftape successfully unloaded.\n");
TRACE_EXIT; TRACE_EXIT;
......
...@@ -40,6 +40,7 @@ ...@@ -40,6 +40,7 @@
#include <linux/delay.h> #include <linux/delay.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/devfs_fs_kernel.h> #include <linux/devfs_fs_kernel.h>
#include <linux/device.h>
#include <asm/io.h> #include <asm/io.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
...@@ -795,6 +796,8 @@ static int stli_timeron; ...@@ -795,6 +796,8 @@ static int stli_timeron;
/*****************************************************************************/ /*****************************************************************************/
static struct class_simple *istallion_class;
#ifdef MODULE #ifdef MODULE
/* /*
...@@ -853,9 +856,12 @@ static void __exit istallion_module_exit(void) ...@@ -853,9 +856,12 @@ static void __exit istallion_module_exit(void)
return; return;
} }
put_tty_driver(stli_serial); put_tty_driver(stli_serial);
for (i = 0; i < 4; i++) for (i = 0; i < 4; i++) {
devfs_remove("staliomem/%d", i); devfs_remove("staliomem/%d", i);
class_simple_device_remove(MKDEV(STL_SIOMEMMAJOR, i));
}
devfs_remove("staliomem"); devfs_remove("staliomem");
class_simple_destroy(istallion_class);
if ((i = unregister_chrdev(STL_SIOMEMMAJOR, "staliomem"))) if ((i = unregister_chrdev(STL_SIOMEMMAJOR, "staliomem")))
printk("STALLION: failed to un-register serial memory device, " printk("STALLION: failed to un-register serial memory device, "
"errno=%d\n", -i); "errno=%d\n", -i);
...@@ -5310,10 +5316,13 @@ int __init stli_init(void) ...@@ -5310,10 +5316,13 @@ int __init stli_init(void)
"device\n"); "device\n");
devfs_mk_dir("staliomem"); devfs_mk_dir("staliomem");
istallion_class = class_simple_create(THIS_MODULE, "staliomem");
for (i = 0; i < 4; i++) { for (i = 0; i < 4; i++) {
devfs_mk_cdev(MKDEV(STL_SIOMEMMAJOR, i), devfs_mk_cdev(MKDEV(STL_SIOMEMMAJOR, i),
S_IFCHR | S_IRUSR | S_IWUSR, S_IFCHR | S_IRUSR | S_IWUSR,
"staliomem/%d", i); "staliomem/%d", i);
class_simple_device_add(istallion_class, MKDEV(STL_SIOMEMMAJOR, i),
NULL, "staliomem%d", i);
} }
/* /*
......
...@@ -41,6 +41,7 @@ ...@@ -41,6 +41,7 @@
#include <linux/init.h> #include <linux/init.h>
#include <linux/smp_lock.h> #include <linux/smp_lock.h>
#include <linux/devfs_fs_kernel.h> #include <linux/devfs_fs_kernel.h>
#include <linux/device.h>
#include <asm/io.h> #include <asm/io.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
...@@ -732,6 +733,8 @@ static struct file_operations stl_fsiomem = { ...@@ -732,6 +733,8 @@ static struct file_operations stl_fsiomem = {
/*****************************************************************************/ /*****************************************************************************/
static struct class_simple *stallion_class;
#ifdef MODULE #ifdef MODULE
/* /*
...@@ -788,12 +791,15 @@ static void __exit stallion_module_exit(void) ...@@ -788,12 +791,15 @@ static void __exit stallion_module_exit(void)
restore_flags(flags); restore_flags(flags);
return; return;
} }
for (i = 0; i < 4; i++) for (i = 0; i < 4; i++) {
devfs_remove("staliomem/%d", i); devfs_remove("staliomem/%d", i);
class_simple_device_remove(MKDEV(STL_SIOMEMMAJOR, i));
}
devfs_remove("staliomem"); devfs_remove("staliomem");
if ((i = unregister_chrdev(STL_SIOMEMMAJOR, "staliomem"))) if ((i = unregister_chrdev(STL_SIOMEMMAJOR, "staliomem")))
printk("STALLION: failed to un-register serial memory device, " printk("STALLION: failed to un-register serial memory device, "
"errno=%d\n", -i); "errno=%d\n", -i);
class_simple_destroy(stallion_class);
if (stl_tmpwritebuf != (char *) NULL) if (stl_tmpwritebuf != (char *) NULL)
kfree(stl_tmpwritebuf); kfree(stl_tmpwritebuf);
...@@ -3181,10 +3187,12 @@ int __init stl_init(void) ...@@ -3181,10 +3187,12 @@ int __init stl_init(void)
printk("STALLION: failed to register serial board device\n"); printk("STALLION: failed to register serial board device\n");
devfs_mk_dir("staliomem"); devfs_mk_dir("staliomem");
stallion_class = class_simple_create(THIS_MODULE, "staliomem");
for (i = 0; i < 4; i++) { for (i = 0; i < 4; i++) {
devfs_mk_cdev(MKDEV(STL_SIOMEMMAJOR, i), devfs_mk_cdev(MKDEV(STL_SIOMEMMAJOR, i),
S_IFCHR|S_IRUSR|S_IWUSR, S_IFCHR|S_IRUSR|S_IWUSR,
"staliomem/%d", i); "staliomem/%d", i);
class_simple_device_add(stallion_class, MKDEV(STL_SIOMEMMAJOR, i), NULL, "staliomem%d", i);
} }
stl_serial->owner = THIS_MODULE; stl_serial->owner = THIS_MODULE;
......
...@@ -67,7 +67,7 @@ ...@@ -67,7 +67,7 @@
/* /*
* Version Information * Version Information
*/ */
#define DRIVER_VERSION "1.17" #define DRIVER_VERSION "1.19"
#define DRIVER_AUTHOR "Romain Lievin <roms@lpg.ticalc.org>" #define DRIVER_AUTHOR "Romain Lievin <roms@lpg.ticalc.org>"
#define DRIVER_DESC "Device driver for TI/PC parallel link cables" #define DRIVER_DESC "Device driver for TI/PC parallel link cables"
#define DRIVER_LICENSE "GPL" #define DRIVER_LICENSE "GPL"
...@@ -361,10 +361,13 @@ tipar_ioctl(struct inode *inode, struct file *file, ...@@ -361,10 +361,13 @@ tipar_ioctl(struct inode *inode, struct file *file,
switch (cmd) { switch (cmd) {
case IOCTL_TIPAR_DELAY: case IOCTL_TIPAR_DELAY:
delay = (int)arg; //get_user(delay, &arg); delay = (int)arg; //get_user(delay, &arg);
break; break;
case IOCTL_TIPAR_TIMEOUT: case IOCTL_TIPAR_TIMEOUT:
timeout = (int)arg; //get_user(timeout, &arg); if (arg != 0)
timeout = (int)arg;
else
retval = -EINVAL;
break; break;
default: default:
retval = -ENOTTY; retval = -ENOTTY;
...@@ -399,7 +402,10 @@ tipar_setup(char *str) ...@@ -399,7 +402,10 @@ tipar_setup(char *str)
str = get_options(str, ARRAY_SIZE(ints), ints); str = get_options(str, ARRAY_SIZE(ints), ints);
if (ints[0] > 0) { if (ints[0] > 0) {
timeout = ints[1]; if (ints[1] != 0)
timeout = ints[1];
else
printk("tipar: wrong timeout value (0), using default value instead.");
if (ints[0] > 1) { if (ints[0] > 1) {
delay = ints[2]; delay = ints[2];
} }
......
...@@ -94,6 +94,7 @@ ...@@ -94,6 +94,7 @@
#include <linux/init.h> #include <linux/init.h>
#include <linux/smp_lock.h> #include <linux/smp_lock.h>
#include <linux/devfs_fs_kernel.h> #include <linux/devfs_fs_kernel.h>
#include <linux/device.h>
#include <asm/dma.h> #include <asm/dma.h>
#include <asm/system.h> #include <asm/system.h>
...@@ -229,6 +230,8 @@ static const char *format_names[] = { ...@@ -229,6 +230,8 @@ static const char *format_names[] = {
"600" /* untested. */ "600" /* untested. */
}; };
static struct class_simple *tpqic02_class;
/* `exception_list' is needed for exception status reporting. /* `exception_list' is needed for exception status reporting.
* Exceptions 1..14 are defined by QIC-02 rev F. * Exceptions 1..14 are defined by QIC-02 rev F.
...@@ -2696,23 +2699,32 @@ int __init qic02_tape_init(void) ...@@ -2696,23 +2699,32 @@ int __init qic02_tape_init(void)
return -ENODEV; return -ENODEV;
} }
tpqic02_class = class_simple_create(THIS_MODULE, TPQIC02_NAME);
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 2), NULL, "ntpqic11");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 2), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 2),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic11"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic11");
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 3), NULL, "tpqic11");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 3), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 3),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic11"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic11");
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 4), NULL, "ntpqic24");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 4), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 4),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic24"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic24");
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 5), NULL, "tpqic24");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 5), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 5),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic24"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic24");
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 6), NULL, "ntpqic20");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 6), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 6),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic120"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic120");
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 7), NULL, "tpqic20");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 7), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 7),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic120"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic120");
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 8), NULL, "ntpqic50");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 8), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 8),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic150"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "ntpqic150");
class_simple_device_add(tpqic02_class, MKDEV(QIC02_TAPE_MAJOR, 9), NULL, "tpqic50");
devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 9), devfs_mk_cdev(MKDEV(QIC02_TAPE_MAJOR, 9),
S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic150"); S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP, "tpqic150");
...@@ -2757,13 +2769,23 @@ static void qic02_module_exit(void) ...@@ -2757,13 +2769,23 @@ static void qic02_module_exit(void)
qic02_release_resources(); qic02_release_resources();
devfs_remove("ntpqic11"); devfs_remove("ntpqic11");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 2));
devfs_remove("tpqic11"); devfs_remove("tpqic11");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 3));
devfs_remove("ntpqic24"); devfs_remove("ntpqic24");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 4));
devfs_remove("tpqic24"); devfs_remove("tpqic24");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 5));
devfs_remove("ntpqic120"); devfs_remove("ntpqic120");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 6));
devfs_remove("tpqic120"); devfs_remove("tpqic120");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 7));
devfs_remove("ntpqic150"); devfs_remove("ntpqic150");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 8));
devfs_remove("tpqic150"); devfs_remove("tpqic150");
class_simple_device_remove(MKDEV(QIC02_TAPE_MAJOR, 9));
class_simple_destroy(tpqic02_class);
} }
static int qic02_module_init(void) static int qic02_module_init(void)
......
...@@ -36,6 +36,7 @@ ...@@ -36,6 +36,7 @@
#include <linux/kbd_kern.h> #include <linux/kbd_kern.h>
#include <linux/console.h> #include <linux/console.h>
#include <linux/smp_lock.h> #include <linux/smp_lock.h>
#include <linux/device.h>
#include <asm/uaccess.h> #include <asm/uaccess.h>
#include <asm/byteorder.h> #include <asm/byteorder.h>
#include <asm/unaligned.h> #include <asm/unaligned.h>
...@@ -469,6 +470,8 @@ static struct file_operations vcs_fops = { ...@@ -469,6 +470,8 @@ static struct file_operations vcs_fops = {
.open = vcs_open, .open = vcs_open,
}; };
static struct class_simple *vc_class;
void vcs_make_devfs(struct tty_struct *tty) void vcs_make_devfs(struct tty_struct *tty)
{ {
devfs_mk_cdev(MKDEV(VCS_MAJOR, tty->index + 1), devfs_mk_cdev(MKDEV(VCS_MAJOR, tty->index + 1),
...@@ -477,19 +480,26 @@ void vcs_make_devfs(struct tty_struct *tty) ...@@ -477,19 +480,26 @@ void vcs_make_devfs(struct tty_struct *tty)
devfs_mk_cdev(MKDEV(VCS_MAJOR, tty->index + 129), devfs_mk_cdev(MKDEV(VCS_MAJOR, tty->index + 129),
S_IFCHR|S_IRUSR|S_IWUSR, S_IFCHR|S_IRUSR|S_IWUSR,
"vcc/a%u", tty->index + 1); "vcc/a%u", tty->index + 1);
class_simple_device_add(vc_class, MKDEV(VCS_MAJOR, tty->index + 1), NULL, "vcs%u", tty->index + 1);
class_simple_device_add(vc_class, MKDEV(VCS_MAJOR, tty->index + 129), NULL, "vcsa%u", tty->index + 1);
} }
void vcs_remove_devfs(struct tty_struct *tty) void vcs_remove_devfs(struct tty_struct *tty)
{ {
devfs_remove("vcc/%u", tty->index + 1); devfs_remove("vcc/%u", tty->index + 1);
devfs_remove("vcc/a%u", tty->index + 1); devfs_remove("vcc/a%u", tty->index + 1);
class_simple_device_remove(MKDEV(VCS_MAJOR, tty->index + 1));
class_simple_device_remove(MKDEV(VCS_MAJOR, tty->index + 129));
} }
int __init vcs_init(void) int __init vcs_init(void)
{ {
if (register_chrdev(VCS_MAJOR, "vcs", &vcs_fops)) if (register_chrdev(VCS_MAJOR, "vcs", &vcs_fops))
panic("unable to get major %d for vcs device", VCS_MAJOR); panic("unable to get major %d for vcs device", VCS_MAJOR);
vc_class = class_simple_create(THIS_MODULE, "vc");
devfs_mk_cdev(MKDEV(VCS_MAJOR, 0), S_IFCHR|S_IRUSR|S_IWUSR, "vcc/0"); devfs_mk_cdev(MKDEV(VCS_MAJOR, 0), S_IFCHR|S_IRUSR|S_IWUSR, "vcc/0");
devfs_mk_cdev(MKDEV(VCS_MAJOR, 128), S_IFCHR|S_IRUSR|S_IWUSR, "vcc/a0"); devfs_mk_cdev(MKDEV(VCS_MAJOR, 128), S_IFCHR|S_IRUSR|S_IWUSR, "vcc/a0");
class_simple_device_add(vc_class, MKDEV(VCS_MAJOR, 0), NULL, "vcs");
class_simple_device_add(vc_class, MKDEV(VCS_MAJOR, 128), NULL, "vcsa");
return 0; return 0;
} }
...@@ -2617,6 +2617,8 @@ static struct tty_operations con_ops = { ...@@ -2617,6 +2617,8 @@ static struct tty_operations con_ops = {
int __init vty_init(void) int __init vty_init(void)
{ {
vcs_init();
console_driver = alloc_tty_driver(MAX_NR_CONSOLES); console_driver = alloc_tty_driver(MAX_NR_CONSOLES);
if (!console_driver) if (!console_driver)
panic("Couldn't allocate console driver\n"); panic("Couldn't allocate console driver\n");
...@@ -2644,7 +2646,6 @@ int __init vty_init(void) ...@@ -2644,7 +2646,6 @@ int __init vty_init(void)
#ifdef CONFIG_FRAMEBUFFER_CONSOLE #ifdef CONFIG_FRAMEBUFFER_CONSOLE
fb_console_init(); fb_console_init();
#endif #endif
vcs_init();
return 0; return 0;
} }
......
...@@ -37,6 +37,7 @@ ...@@ -37,6 +37,7 @@
#include <linux/capi.h> #include <linux/capi.h>
#include <linux/kernelcapi.h> #include <linux/kernelcapi.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/device.h>
#include <linux/devfs_fs_kernel.h> #include <linux/devfs_fs_kernel.h>
#include <linux/isdn/capiutil.h> #include <linux/isdn/capiutil.h>
#include <linux/isdn/capicmd.h> #include <linux/isdn/capicmd.h>
...@@ -56,6 +57,8 @@ MODULE_LICENSE("GPL"); ...@@ -56,6 +57,8 @@ MODULE_LICENSE("GPL");
/* -------- driver information -------------------------------------- */ /* -------- driver information -------------------------------------- */
static struct class_simple *capi_class;
int capi_major = 68; /* allocated */ int capi_major = 68; /* allocated */
#ifdef CONFIG_ISDN_CAPI_MIDDLEWARE #ifdef CONFIG_ISDN_CAPI_MIDDLEWARE
#define CAPINC_NR_PORTS 32 #define CAPINC_NR_PORTS 32
...@@ -1313,7 +1316,8 @@ static int capinc_tty_init(void) ...@@ -1313,7 +1316,8 @@ static int capinc_tty_init(void)
drv->owner = THIS_MODULE; drv->owner = THIS_MODULE;
drv->driver_name = "capi_nc"; drv->driver_name = "capi_nc";
drv->name = "capi/"; drv->devfs_name = "capi/";
drv->name = "capi";
drv->major = capi_ttymajor; drv->major = capi_ttymajor;
drv->minor_start = 0; drv->minor_start = 0;
drv->type = TTY_DRIVER_TYPE_SERIAL; drv->type = TTY_DRIVER_TYPE_SERIAL;
...@@ -1483,11 +1487,20 @@ static int __init capi_init(void) ...@@ -1483,11 +1487,20 @@ static int __init capi_init(void)
return -EIO; return -EIO;
} }
capi_class = class_simple_create(THIS_MODULE, "capi");
if (IS_ERR(capi_class)) {
unregister_chrdev(capi_major, "capi20");
return PTR_ERR(capi_class);
}
class_simple_device_add(capi_class, MKDEV(capi_major, 0), NULL, "capi");
devfs_mk_cdev(MKDEV(capi_major, 0), S_IFCHR | S_IRUSR | S_IWUSR, devfs_mk_cdev(MKDEV(capi_major, 0), S_IFCHR | S_IRUSR | S_IWUSR,
"isdn/capi20"); "isdn/capi20");
#ifdef CONFIG_ISDN_CAPI_MIDDLEWARE #ifdef CONFIG_ISDN_CAPI_MIDDLEWARE
if (capinc_tty_init() < 0) { if (capinc_tty_init() < 0) {
class_simple_device_remove(MKDEV(capi_major, 0));
class_simple_destroy(capi_class);
unregister_chrdev(capi_major, "capi20"); unregister_chrdev(capi_major, "capi20");
return -ENOMEM; return -ENOMEM;
} }
...@@ -1514,6 +1527,8 @@ static void __exit capi_exit(void) ...@@ -1514,6 +1527,8 @@ static void __exit capi_exit(void)
{ {
proc_exit(); proc_exit();
class_simple_device_remove(MKDEV(capi_major, 0));
class_simple_destroy(capi_class);
unregister_chrdev(capi_major, "capi20"); unregister_chrdev(capi_major, "capi20");
devfs_remove("isdn/capi20"); devfs_remove("isdn/capi20");
......
...@@ -32,6 +32,9 @@ ...@@ -32,6 +32,9 @@
#include <linux/kmod.h> #include <linux/kmod.h>
#endif #endif
#include <linux/devfs_fs_kernel.h> #include <linux/devfs_fs_kernel.h>
#include <linux/err.h>
#include <linux/kernel.h>
#include <linux/device.h>
#if defined(__mc68000__) || defined(CONFIG_APUS) #if defined(__mc68000__) || defined(CONFIG_APUS)
#include <asm/setup.h> #include <asm/setup.h>
...@@ -1245,6 +1248,8 @@ static struct file_operations fb_fops = { ...@@ -1245,6 +1248,8 @@ static struct file_operations fb_fops = {
#endif #endif
}; };
static struct class_simple *fb_class;
/** /**
* register_framebuffer - registers a frame buffer device * register_framebuffer - registers a frame buffer device
* @fb_info: frame buffer info structure * @fb_info: frame buffer info structure
...@@ -1259,6 +1264,7 @@ int ...@@ -1259,6 +1264,7 @@ int
register_framebuffer(struct fb_info *fb_info) register_framebuffer(struct fb_info *fb_info)
{ {
int i; int i;
struct class_device *c;
if (num_registered_fb == FB_MAX) if (num_registered_fb == FB_MAX)
return -ENXIO; return -ENXIO;
...@@ -1267,6 +1273,12 @@ register_framebuffer(struct fb_info *fb_info) ...@@ -1267,6 +1273,12 @@ register_framebuffer(struct fb_info *fb_info)
if (!registered_fb[i]) if (!registered_fb[i])
break; break;
fb_info->node = i; fb_info->node = i;
c = class_simple_device_add(fb_class, MKDEV(FB_MAJOR, i), NULL, "fb%d", i);
if (IS_ERR(c)) {
/* Not fatal */
printk(KERN_WARNING "Unable to create class_device for framebuffer %d; errno = %ld\n", i, PTR_ERR(c));
}
if (fb_info->pixmap.addr == NULL) { if (fb_info->pixmap.addr == NULL) {
fb_info->pixmap.addr = kmalloc(FBPIXMAPSIZE, GFP_KERNEL); fb_info->pixmap.addr = kmalloc(FBPIXMAPSIZE, GFP_KERNEL);
...@@ -1332,6 +1344,7 @@ unregister_framebuffer(struct fb_info *fb_info) ...@@ -1332,6 +1344,7 @@ unregister_framebuffer(struct fb_info *fb_info)
kfree(fb_info->sprite.addr); kfree(fb_info->sprite.addr);
registered_fb[i]=NULL; registered_fb[i]=NULL;
num_registered_fb--; num_registered_fb--;
class_simple_device_remove(MKDEV(FB_MAJOR, i));
return 0; return 0;
} }
...@@ -1393,6 +1406,12 @@ fbmem_init(void) ...@@ -1393,6 +1406,12 @@ fbmem_init(void)
if (register_chrdev(FB_MAJOR,"fb",&fb_fops)) if (register_chrdev(FB_MAJOR,"fb",&fb_fops))
printk("unable to get major %d for fb devs\n", FB_MAJOR); printk("unable to get major %d for fb devs\n", FB_MAJOR);
fb_class = class_simple_create(THIS_MODULE, "graphics");
if (IS_ERR(fb_class)) {
printk(KERN_WARNING "Unable to create fb class; errno = %ld\n", PTR_ERR(fb_class));
fb_class = NULL;
}
#ifdef CONFIG_FB_OF #ifdef CONFIG_FB_OF
if (ofonly) { if (ofonly) {
offb_init(); offb_init();
......
...@@ -37,6 +37,7 @@ ...@@ -37,6 +37,7 @@
#include <linux/init.h> #include <linux/init.h>
#include <linux/list.h> #include <linux/list.h>
#include <linux/smp_lock.h> #include <linux/smp_lock.h>
#include <linux/device.h>
#include <asm/io.h> #include <asm/io.h>
#include <asm/system.h> #include <asm/system.h>
#include <asm/poll.h> #include <asm/poll.h>
...@@ -61,6 +62,7 @@ unsigned long coda_timeout = 30; /* .. secs, then signals will dequeue */ ...@@ -61,6 +62,7 @@ unsigned long coda_timeout = 30; /* .. secs, then signals will dequeue */
struct venus_comm coda_comms[MAX_CODADEVS]; struct venus_comm coda_comms[MAX_CODADEVS];
static struct class_simple *coda_psdev_class;
/* /*
* Device operations * Device operations
...@@ -358,20 +360,38 @@ static struct file_operations coda_psdev_fops = { ...@@ -358,20 +360,38 @@ static struct file_operations coda_psdev_fops = {
static int init_coda_psdev(void) static int init_coda_psdev(void)
{ {
int i; int i, err = 0;
if (register_chrdev(CODA_PSDEV_MAJOR,"coda_psdev", if (register_chrdev(CODA_PSDEV_MAJOR,"coda_psdev",
&coda_psdev_fops)) { &coda_psdev_fops)) {
printk(KERN_ERR "coda_psdev: unable to get major %d\n", printk(KERN_ERR "coda_psdev: unable to get major %d\n",
CODA_PSDEV_MAJOR); CODA_PSDEV_MAJOR);
return -EIO; return -EIO;
} }
coda_psdev_class = class_simple_create(THIS_MODULE, "coda_psdev");
if (IS_ERR(coda_psdev_class)) {
err = PTR_ERR(coda_psdev_class);
goto out_chrdev;
}
devfs_mk_dir ("coda"); devfs_mk_dir ("coda");
for (i = 0; i < MAX_CODADEVS; i++) { for (i = 0; i < MAX_CODADEVS; i++) {
devfs_mk_cdev(MKDEV(CODA_PSDEV_MAJOR, i), class_simple_device_add(coda_psdev_class, MKDEV(CODA_PSDEV_MAJOR,i),
NULL, "cfs%d", i);
err = devfs_mk_cdev(MKDEV(CODA_PSDEV_MAJOR, i),
S_IFCHR|S_IRUSR|S_IWUSR, "coda/%d", i); S_IFCHR|S_IRUSR|S_IWUSR, "coda/%d", i);
if (err)
goto out_class;
} }
coda_sysctl_init(); coda_sysctl_init();
return 0; goto out;
out_class:
for (i = 0; i < MAX_CODADEVS; i++)
class_simple_device_remove(MKDEV(CODA_PSDEV_MAJOR, i));
class_simple_destroy(coda_psdev_class);
out_chrdev:
unregister_chrdev(CODA_PSDEV_MAJOR, "coda_psdev");
out:
return err;
} }
...@@ -408,8 +428,11 @@ static int __init init_coda(void) ...@@ -408,8 +428,11 @@ static int __init init_coda(void)
} }
return 0; return 0;
out: out:
for (i = 0; i < MAX_CODADEVS; i++) for (i = 0; i < MAX_CODADEVS; i++) {
class_simple_device_remove(MKDEV(CODA_PSDEV_MAJOR, i));
devfs_remove("coda/%d", i); devfs_remove("coda/%d", i);
}
class_simple_destroy(coda_psdev_class);
devfs_remove("coda"); devfs_remove("coda");
unregister_chrdev(CODA_PSDEV_MAJOR,"coda_psdev"); unregister_chrdev(CODA_PSDEV_MAJOR,"coda_psdev");
coda_sysctl_clean(); coda_sysctl_clean();
...@@ -427,8 +450,11 @@ static void __exit exit_coda(void) ...@@ -427,8 +450,11 @@ static void __exit exit_coda(void)
if ( err != 0 ) { if ( err != 0 ) {
printk("coda: failed to unregister filesystem\n"); printk("coda: failed to unregister filesystem\n");
} }
for (i = 0; i < MAX_CODADEVS; i++) for (i = 0; i < MAX_CODADEVS; i++) {
class_simple_device_remove(MKDEV(CODA_PSDEV_MAJOR, i));
devfs_remove("coda/%d", i); devfs_remove("coda/%d", i);
}
class_simple_destroy(coda_psdev_class);
devfs_remove("coda"); devfs_remove("coda");
unregister_chrdev(CODA_PSDEV_MAJOR, "coda_psdev"); unregister_chrdev(CODA_PSDEV_MAJOR, "coda_psdev");
coda_sysctl_clean(); coda_sysctl_clean();
......
...@@ -349,16 +349,16 @@ int kobject_set_name(struct kobject * kobj, const char * fmt, ...) ...@@ -349,16 +349,16 @@ int kobject_set_name(struct kobject * kobj, const char * fmt, ...)
/* /*
* Need more space? Allocate it and try again * Need more space? Allocate it and try again
*/ */
name = kmalloc(need,GFP_KERNEL); limit = need + 1;
name = kmalloc(limit,GFP_KERNEL);
if (!name) { if (!name) {
error = -ENOMEM; error = -ENOMEM;
goto Done; goto Done;
} }
limit = need;
need = vsnprintf(name,limit,fmt,args); need = vsnprintf(name,limit,fmt,args);
/* Still? Give up. */ /* Still? Give up. */
if (need > limit) { if (need >= limit) {
kfree(name); kfree(name);
error = -EFAULT; error = -EFAULT;
goto Done; goto Done;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment