Commit 5aaaf9f0 authored by Heiko Carstens's avatar Heiko Carstens Committed by Martin Schwidefsky

[S390] Fix sclp_vt220 error handling.

Also convert to slab_is_available() as an indicator if
get_zeroed_page() will work or not.
Signed-off-by: default avatarHeiko Carstens <heiko.carstens@de.ibm.com>
Signed-off-by: default avatarMartin Schwidefsky <schwidefsky@de.ibm.com>
parent 4434a38c
...@@ -621,10 +621,24 @@ sclp_vt220_flush_buffer(struct tty_struct *tty) ...@@ -621,10 +621,24 @@ sclp_vt220_flush_buffer(struct tty_struct *tty)
/* /*
* Initialize all relevant components and register driver with system. * Initialize all relevant components and register driver with system.
*/ */
static int __init_refok __sclp_vt220_init(int early) static void __init __sclp_vt220_cleanup(void)
{
struct list_head *page, *p;
list_for_each_safe(page, p, &sclp_vt220_empty) {
list_del(page);
if (slab_is_available())
free_page((unsigned long) page);
else
free_bootmem((unsigned long) page, PAGE_SIZE);
}
}
static int __init __sclp_vt220_init(void)
{ {
void *page; void *page;
int i; int i;
int num_pages;
if (sclp_vt220_initialized) if (sclp_vt220_initialized)
return 0; return 0;
...@@ -641,13 +655,16 @@ static int __init_refok __sclp_vt220_init(int early) ...@@ -641,13 +655,16 @@ static int __init_refok __sclp_vt220_init(int early)
sclp_vt220_flush_later = 0; sclp_vt220_flush_later = 0;
/* Allocate pages for output buffering */ /* Allocate pages for output buffering */
for (i = 0; i < (early ? MAX_CONSOLE_PAGES : MAX_KMEM_PAGES); i++) { num_pages = slab_is_available() ? MAX_KMEM_PAGES : MAX_CONSOLE_PAGES;
if (early) for (i = 0; i < num_pages; i++) {
page = alloc_bootmem_low_pages(PAGE_SIZE); if (slab_is_available())
else
page = (void *) get_zeroed_page(GFP_KERNEL | GFP_DMA); page = (void *) get_zeroed_page(GFP_KERNEL | GFP_DMA);
if (!page) else
page = alloc_bootmem_low_pages(PAGE_SIZE);
if (!page) {
__sclp_vt220_cleanup();
return -ENOMEM; return -ENOMEM;
}
list_add_tail((struct list_head *) page, &sclp_vt220_empty); list_add_tail((struct list_head *) page, &sclp_vt220_empty);
} }
return 0; return 0;
...@@ -661,14 +678,13 @@ static const struct tty_operations sclp_vt220_ops = { ...@@ -661,14 +678,13 @@ static const struct tty_operations sclp_vt220_ops = {
.flush_chars = sclp_vt220_flush_chars, .flush_chars = sclp_vt220_flush_chars,
.write_room = sclp_vt220_write_room, .write_room = sclp_vt220_write_room,
.chars_in_buffer = sclp_vt220_chars_in_buffer, .chars_in_buffer = sclp_vt220_chars_in_buffer,
.flush_buffer = sclp_vt220_flush_buffer .flush_buffer = sclp_vt220_flush_buffer,
}; };
/* /*
* Register driver with SCLP and Linux and initialize internal tty structures. * Register driver with SCLP and Linux and initialize internal tty structures.
*/ */
static int __init static int __init sclp_vt220_tty_init(void)
sclp_vt220_tty_init(void)
{ {
struct tty_driver *driver; struct tty_driver *driver;
int rc; int rc;
...@@ -678,18 +694,15 @@ sclp_vt220_tty_init(void) ...@@ -678,18 +694,15 @@ sclp_vt220_tty_init(void)
driver = alloc_tty_driver(1); driver = alloc_tty_driver(1);
if (!driver) if (!driver)
return -ENOMEM; return -ENOMEM;
rc = __sclp_vt220_init(0); rc = __sclp_vt220_init();
if (rc) { if (rc)
put_tty_driver(driver); goto out_driver;
return rc;
}
rc = sclp_register(&sclp_vt220_register); rc = sclp_register(&sclp_vt220_register);
if (rc) { if (rc) {
printk(KERN_ERR SCLP_VT220_PRINT_HEADER printk(KERN_ERR SCLP_VT220_PRINT_HEADER
"could not register tty - " "could not register tty - "
"sclp_register returned %d\n", rc); "sclp_register returned %d\n", rc);
put_tty_driver(driver); goto out_init;
return rc;
} }
driver->owner = THIS_MODULE; driver->owner = THIS_MODULE;
...@@ -708,14 +721,20 @@ sclp_vt220_tty_init(void) ...@@ -708,14 +721,20 @@ sclp_vt220_tty_init(void)
printk(KERN_ERR SCLP_VT220_PRINT_HEADER printk(KERN_ERR SCLP_VT220_PRINT_HEADER
"could not register tty - " "could not register tty - "
"tty_register_driver returned %d\n", rc); "tty_register_driver returned %d\n", rc);
put_tty_driver(driver); goto out_sclp;
return rc;
} }
sclp_vt220_driver = driver; sclp_vt220_driver = driver;
return 0; return 0;
}
module_init(sclp_vt220_tty_init); out_sclp:
sclp_unregister(&sclp_vt220_register);
out_init:
__sclp_vt220_cleanup();
out_driver:
put_tty_driver(driver);
return rc;
}
__initcall(sclp_vt220_tty_init);
#ifdef CONFIG_SCLP_VT220_CONSOLE #ifdef CONFIG_SCLP_VT220_CONSOLE
...@@ -761,7 +780,7 @@ sclp_vt220_con_init(void) ...@@ -761,7 +780,7 @@ sclp_vt220_con_init(void)
if (!CONSOLE_IS_SCLP) if (!CONSOLE_IS_SCLP)
return 0; return 0;
rc = __sclp_vt220_init(1); rc = __sclp_vt220_init();
if (rc) if (rc)
return rc; return rc;
/* Attach linux console */ /* Attach linux console */
......
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