/*
 * FreeBSD example kernel module
 * Matteo Cicuttin 2007
 * Se vi tuona la macchina c***i vostri
 */
 
#include <sys/types.h>
#include <sys/module.h>
#include <sys/systm.h>
#include <sys/errno.h>
#include <sys/param.h>
#include <sys/kernel.h>
#include <sys/conf.h>
#include <sys/uio.h>
#include <sys/ioccom.h>

#define TEST	_IO('x', 1)

static int pippo_open(struct cdev *, int, int, struct thread *);
static int pippo_close(struct cdev *, int, int, struct thread *);
static int pippo_ioctl(struct cdev *, u_long, caddr_t, int, struct thread *);

static struct cdev* pippo_dev;

static struct cdevsw pippo_cdevsw = {
    .d_version  = D_VERSION,
    .d_open     = pippo_open,
    .d_close    = pippo_close,
    .d_ioctl    = pippo_ioctl,
    .d_name     = "pippo",
};

static int
pippo_open(struct cdev *dev, int oflags, int devtype, struct thread *p)
{
    printf("pippo: open\n");
    return 0;
}

static int
pippo_close(struct cdev *dev, int fflag, int devtype, struct thread *p)
{
    printf("pippo: close\n");
    return 0;
}

static int
pippo_ioctl(struct cdev *dev, u_long cmd, 
            caddr_t data, int flags, struct thread *p)
{
    int error = 0;
    switch (cmd)
    {
        case TEST:
    	    printf("pippo: ioctl TEST\n");
            break;
        default:
            error = EPERM; //ritorniamo un errore x
            break;
    }

    return 0;
}

static int
pippo_loader(struct module *m, int cmd, void *arg)
{
    int err = 0;
    
    switch(cmd)
    {
        case MOD_LOAD:
            pippo_dev = make_dev(&pippo_cdevsw, 0, UID_ROOT,
                                 GID_WHEEL, 0600, "pippo");
            printf("pippo: device loaded\n");  
            break;
        
        case MOD_UNLOAD:
            destroy_dev(pippo_dev);
            printf("pippo: device unloaded\n");
            break;
        
        default:
            err = EINVAL;
            break;
    }
    return err;
}

DEV_MODULE(pippo, pippo_loader, NULL);



