* not known ahead of time.
         */
        accessibility_kobj = kobject_create_and_add("accessibility", NULL);
-       if (!accessibility_kobj)
-               return -ENOMEM;
+       if (!accessibility_kobj) {
+               retval = -ENOMEM;
+               goto out;
+       }
 
        speakup_kobj = kobject_create_and_add("speakup", accessibility_kobj);
        if (!speakup_kobj) {
        if (retval)
                goto err_group;
 
-       return 0;
+       goto out;
 
 err_group:
        sysfs_remove_group(speakup_kobj, &main_attr_group);
        kobject_put(speakup_kobj);
 err_acc:
        kobject_put(accessibility_kobj);
+out:
        return retval;
 }
 
 
 
        err = speakup_add_virtual_keyboard();
        if (err)
-               return err;
+               goto out;
 
        initialize_msgs();      /* Initialize arrays for i18n. */
        first_console = kzalloc(sizeof(*first_console), GFP_KERNEL);
-       if (!first_console)
-               return -ENOMEM;
-       err = speakup_kobj_init();
-       if (err) {
-               kfree(first_console);
-               return err;
+       if (!first_console) {
+               err = -ENOMEM;
+               goto err_cons;
        }
+       err = speakup_kobj_init();
+       if (err)
+               goto err_kobject;
 
        reset_default_chars();
        reset_default_chartab();
 
        speakup_task = kthread_create(speakup_thread, NULL, "speakup");
        set_user_nice(speakup_task, 10);
-       if (!IS_ERR(speakup_task))
-               wake_up_process(speakup_task);
-       else
-               return -ENOMEM;
-       return 0;
+       if (IS_ERR(speakup_task)) {
+               err = -ENOMEM;
+               goto err_kobject;
+       }
+       wake_up_process(speakup_task);
+       goto out;
+
+err_kobject:
+speakup_kobj_exit();
+       kfree(first_console);
+err_cons:
+       speakup_remove_virtual_keyboard();
+out:
+       return err;
 }
 
 module_init(speakup_init);