VirtualBox

Changeset 44184 in vbox for trunk/src/VBox/HostDrivers


Ignore:
Timestamp:
Dec 19, 2012 7:48:22 PM (12 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
82894
Message:

SUPDrv-linux.c: /dev/vboxdrvu (untested).

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/HostDrivers/Support/linux/SUPDrv-linux.c

    r44173 r44184  
    9696static int  VBoxDrvLinuxInit(void);
    9797static void VBoxDrvLinuxUnload(void);
    98 static int  VBoxDrvLinuxCreate(struct inode *pInode, struct file *pFilp);
     98static int  VBoxDrvLinuxCreateSys(struct inode *pInode, struct file *pFilp);
     99static int  VBoxDrvLinuxCreateUsr(struct inode *pInode, struct file *pFilp);
    99100static int  VBoxDrvLinuxClose(struct inode *pInode, struct file *pFilp);
    100101#ifdef HAVE_UNLOCKED_IOCTL
     
    103104static int  VBoxDrvLinuxIOCtl(struct inode *pInode, struct file *pFilp, unsigned int uCmd, unsigned long ulArg);
    104105#endif
    105 static int  VBoxDrvLinuxIOCtlSlow(struct file *pFilp, unsigned int uCmd, unsigned long ulArg);
     106static int  VBoxDrvLinuxIOCtlSlow(struct file *pFilp, unsigned int uCmd, unsigned long ulArg, PSUPDRVSESSION pSession);
    106107static int  VBoxDrvLinuxErr2LinuxErr(int);
    107108#ifdef VBOX_WITH_SUSPEND_NOTIFICATION
     
    127128
    128129#ifndef CONFIG_VBOXDRV_AS_MISC
    129 /** Module major number */
    130 #define DEVICE_MAJOR        234
    131 /** Saved major device number */
    132 static int                  g_iModuleMajor;
     130/** Module major number for vboxdrv. */
     131#define DEVICE_MAJOR_SYS    234
     132/** Saved major device number for vboxdrv. */
     133static int                  g_iModuleMajorSys;
     134/** Module major number for vboxdrvu. */
     135#define DEVICE_MAJOR_USR    235
     136/** Saved major device number for vboxdrvu. */
     137static int                  g_iModuleMajorUsr;
    133138#endif /* !CONFIG_VBOXDRV_AS_MISC */
    134139
     
    137142static int force_async_tsc = 0;
    138143
    139 /** The module name. */
    140 #define DEVICE_NAME         "vboxdrv"
     144/** The system device name. */
     145#define DEVICE_NAME_SYS     "vboxdrvu"
     146/** The user device name. */
     147#define DEVICE_NAME_USR     "vboxdrv"
    141148
    142149#if defined(RT_ARCH_AMD64) && !defined(CONFIG_DEBUG_SET_MODULE_RONX)
     
    156163
    157164/** The file_operations structure. */
    158 static struct file_operations gFileOpsVBoxDrv =
     165static struct file_operations gFileOpsVBoxDrvSys =
    159166{
    160167    owner:      THIS_MODULE,
    161     open:       VBoxDrvLinuxCreate,
     168    open:       VBoxDrvLinuxCreateSys,
    162169    release:    VBoxDrvLinuxClose,
    163170#ifdef HAVE_UNLOCKED_IOCTL
     
    168175};
    169176
     177/** The file_operations structure. */
     178static struct file_operations gFileOpsVBoxDrvUsr =
     179{
     180    owner:      THIS_MODULE,
     181    open:       VBoxDrvLinuxCreateUsr,
     182    release:    VBoxDrvLinuxClose,
     183#ifdef HAVE_UNLOCKED_IOCTL
     184    unlocked_ioctl: VBoxDrvLinuxIOCtl,
     185#else
     186    ioctl:      VBoxDrvLinuxIOCtl,
     187#endif
     188};
     189
    170190#ifdef CONFIG_VBOXDRV_AS_MISC
    171 /** The miscdevice structure. */
    172 static struct miscdevice gMiscDevice =
     191/** The miscdevice structure for vboxdrv. */
     192static struct miscdevice gMiscDeviceSys =
    173193{
    174194    minor:      MISC_DYNAMIC_MINOR,
    175     name:       DEVICE_NAME,
    176     fops:       &gFileOpsVBoxDrv,
     195    name:       DEVICE_NAME_SYS,
     196    fops:       &gFileOpsVBoxDrvSys,
    177197# if LINUX_VERSION_CODE <= KERNEL_VERSION(2, 6, 17)
    178     devfs_name: DEVICE_NAME,
     198    devfs_name: DEVICE_NAME_SYS,
     199# endif
     200};
     201/** The miscdevice structure for vboxdrvu. */
     202static struct miscdevice gMiscDeviceUsr =
     203{
     204    minor:      MISC_DYNAMIC_MINOR,
     205    name:       DEVICE_NAME_USR,
     206    fops:       &gFileOpsVBoxDrvUsr,
     207# if LINUX_VERSION_CODE <= KERNEL_VERSION(2, 6, 17)
     208    devfs_name: DEVICE_NAME_USR,
    179209# endif
    180210};
     
    260290     * Check for synchronous/asynchronous TSC mode.
    261291     */
    262     printk(KERN_DEBUG DEVICE_NAME ": Found %u processor cores.\n", (unsigned)RTMpGetOnlineCount());
     292    printk(KERN_DEBUG "vboxdrv: Found %u processor cores.\n", (unsigned)RTMpGetOnlineCount());
    263293#ifdef CONFIG_VBOXDRV_AS_MISC
    264     rc = misc_register(&gMiscDevice);
     294    rc = misc_register(&gMiscDeviceSys);
    265295    if (rc)
    266296    {
    267         printk(KERN_ERR DEVICE_NAME ": Can't register misc device! rc=%d\n", rc);
     297        printk(KERN_ERR "vboxdrv: Can't register system misc device! rc=%d\n", rc);
    268298        return rc;
    269299    }
     300    rc = misc_register(&gMiscDeviceUsr);
     301    if (rc)
     302    {
     303        printk(KERN_ERR "vboxdrv: Can't register user misc device! rc=%d\n", rc);
     304        misc_deregister(&gMiscDeviceSys);
     305        return rc;
     306    }
    270307#else  /* !CONFIG_VBOXDRV_AS_MISC */
    271308    /*
    272      * Register character device.
    273      */
    274     g_iModuleMajor = DEVICE_MAJOR;
    275     rc = register_chrdev((dev_t)g_iModuleMajor, DEVICE_NAME, &gFileOpsVBoxDrv);
     309     * Register character devices and save the returned major numbers.
     310     */
     311    /* /dev/vboxdrv */
     312    g_iModuleMajorSys = DEVICE_MAJOR_SYS;
     313    rc = register_chrdev((dev_t)g_iModuleMajorSys, DEVICE_NAME_SYS, &gFileOpsVBoxDrvSys);
    276314    if (rc < 0)
    277315    {
    278         Log(("register_chrdev() failed with rc=%#x!\n", rc));
     316        Log(("register_chrdev() failed with rc=%#x for vboxdrv!\n", rc));
    279317        return rc;
    280318    }
    281 
    282     /*
    283      * Save returned module major number
    284      */
    285     if (DEVICE_MAJOR != 0)
    286         g_iModuleMajor = DEVICE_MAJOR;
     319    if (DEVICE_MAJOR_SYS != 0)
     320        g_iModuleMajorSys = DEVICE_MAJOR_SYS;
    287321    else
    288         g_iModuleMajor = rc;
     322        g_iModuleMajorSys = rc;
     323
     324    /* /dev/vboxdrvu */
     325    /** @todo Use a minor number of this bugger (not sure if this code is used
     326     *        though, so not bothering right now.) */
     327    g_iModuleMajorUsr = DEVICE_MAJOR_USR;
     328    rc = register_chrdev((dev_t)g_iModuleMajorUsr, DEVICE_NAME_USR, &gFileOpsVBoxDrvUsr);
     329    if (rc < 0)
     330    {
     331        Log(("register_chrdev() failed with rc=%#x for vboxdrv!\n", rc));
     332        return rc;
     333    }
     334    if (DEVICE_MAJOR_USR != 0)
     335        g_iModuleMajorUsr = DEVICE_MAJOR_USR;
     336    else
     337        g_iModuleMajorUsr = rc;
    289338    rc = 0;
    290339
     
    293342     * Register a device entry
    294343     */
    295     if (devfs_mk_cdev(MKDEV(DEVICE_MAJOR, 0), S_IFCHR | VBOX_DEV_FMASK, DEVICE_NAME) != 0)
     344    if (   devfs_mk_cdev(MKDEV(DEVICE_MAJOR_SYS, 0), S_IFCHR | VBOX_DEV_FMASK, DEVICE_NAME_SYS) != 0
     345        || devfs_mk_cdev(MKDEV(DEVICE_MAJOR_USR, 0), S_IFCHR | VBOX_DEV_FMASK, DEVICE_NAME_USR) != 0)
    296346    {
    297347        Log(("devfs_register failed!\n"));
     
    330380#endif
    331381                    {
    332                         printk(KERN_INFO DEVICE_NAME ": TSC mode is %s, kernel timer mode is 'normal'.\n",
     382                        printk(KERN_INFO "vboxdrv: TSC mode is %s, kernel timer mode is 'normal'.\n",
    333383                               g_DevExt.pGip->u32Mode == SUPGIPMODE_SYNC_TSC ? "'synchronous'" : "'asynchronous'");
    334384                        LogFlow(("VBoxDrv::ModuleInit returning %#x\n", rc));
    335                         printk(KERN_DEBUG DEVICE_NAME ": Successfully loaded version "
     385                        printk(KERN_DEBUG "vboxdrv: Successfully loaded version "
    336386                                VBOX_VERSION_STRING " (interface " RT_XSTR(SUPDRV_IOC_VERSION) ").\n");
    337387                        return rc;
     
    354404         */
    355405#if defined(CONFIG_DEVFS_FS) && !defined(CONFIG_VBOXDRV_AS_MISC)
    356         devfs_remove(DEVICE_NAME);
     406        devfs_remove(DEVICE_NAME_SYS);
     407        devfs_remove(DEVICE_NAME_USR);
    357408#endif
    358409    }
    359410#ifdef CONFIG_VBOXDRV_AS_MISC
    360     misc_deregister(&gMiscDevice);
    361     Log(("VBoxDrv::ModuleInit returning %#x (minor:%d)\n", rc, gMiscDevice.minor));
     411    misc_deregister(&gMiscDeviceSys);
     412    misc_deregister(&gMiscDeviceUsr);
     413    Log(("VBoxDrv::ModuleInit returning %#x (minor:%d & %d)\n", rc, gMiscDeviceSys.minor, gMiscDeviceUsr.minor));
    362414#else
    363     unregister_chrdev(g_iModuleMajor, DEVICE_NAME);
    364     Log(("VBoxDrv::ModuleInit returning %#x (major:%d)\n", rc, g_iModuleMajor));
     415    unregister_chrdev(g_iModuleMajorUsr, DEVICE_NAME_USR);
     416    unregister_chrdev(g_iModuleMajorSys, DEVICE_NAME_SYS);
     417    Log(("VBoxDrv::ModuleInit returning %#x (major:%d & %d)\n", rc, g_iModuleMajorSys, g_iModuleMajorUsr));
    365418#endif
    366419    return rc;
     
    387440     */
    388441#ifdef CONFIG_VBOXDRV_AS_MISC
    389     rc = misc_deregister(&gMiscDevice);
     442    rc = misc_deregister(&gMiscDeviceUsr);
    390443    if (rc < 0)
    391444    {
    392         Log(("misc_deregister failed with rc=%#x\n", rc));
     445        Log(("misc_deregister failed with rc=%#x on vboxdrvu\n", rc));
     446    }
     447    rc = misc_deregister(&gMiscDeviceSys);
     448    if (rc < 0)
     449    {
     450        Log(("misc_deregister failed with rc=%#x on vboxdrv\n", rc));
    393451    }
    394452#else  /* !CONFIG_VBOXDRV_AS_MISC */
     
    397455     * Unregister a device entry
    398456     */
    399     devfs_remove(DEVICE_NAME);
     457    devfs_remove(DEVICE_NAME_USR);
     458    devfs_remove(DEVICE_NAME_SYS);
    400459# endif /* devfs */
    401     unregister_chrdev(g_iModuleMajor, DEVICE_NAME);
     460    unregister_chrdev(g_iModuleMajorUsr, DEVICE_NAME_USR);
     461    unregister_chrdev(g_iModuleMajorSys, DEVICE_NAME_SYS);
    402462#endif /* !CONFIG_VBOXDRV_AS_MISC */
    403463
     
    411471
    412472/**
    413  * Device open. Called on open /dev/vboxdrv
    414  *
    415  * @param   pInode      Pointer to inode info structure.
    416  * @param   pFilp       Associated file pointer.
    417  */
    418 static int VBoxDrvLinuxCreate(struct inode *pInode, struct file *pFilp)
     473 * Common open code.
     474 *
     475 * @param   pInode          Pointer to inode info structure.
     476 * @param   pFilp           Associated file pointer.
     477 * @param   fUnrestricted   Indicates which device node which was opened.
     478 */
     479static int VBoxDrvLinuxCreateCommon(struct inode *pInode, struct file *pFilp, bool fUnrestricted)
    419480{
    420481    int                 rc;
     
    436497     * Call common code for the rest.
    437498     */
    438     rc = supdrvCreateSession(&g_DevExt, true /* fUser */, true /*fUnrestricted*/, &pSession);
     499    rc = supdrvCreateSession(&g_DevExt, true /* fUser */, fUnrestricted, &pSession);
    439500    if (!rc)
    440501    {
     
    449510         RTProcSelf(), current->pid, current->comm));
    450511    return VBoxDrvLinuxErr2LinuxErr(rc);
     512}
     513
     514
     515/** /dev/vboxdrv.  */
     516static int VBoxDrvLinuxCreateSys(struct inode *pInode, struct file *pFilp)
     517{
     518    return vboxdrvLinuxCreateCommon(pInode, pFilp, true);
     519}
     520
     521
     522/** /dev/vboxdrvu.  */
     523static int VBoxDrvLinuxCreateUsr(struct inode *pInode, struct file *pFilp)
     524{
     525    return vboxdrvLinuxCreateCommon(pInode, pFilp, false);
    451526}
    452527
     
    534609#endif
    535610{
     611    PSUPDRVSESSION pSession = (PSUPDRVSESSION)pFilp->private_data;
     612
    536613    /*
    537614     * Deal with the two high-speed IOCtl that takes it's arguments from
     
    539616     */
    540617#ifdef HAVE_UNLOCKED_IOCTL
    541     if (RT_LIKELY(   uCmd == SUP_IOCTL_FAST_DO_RAW_RUN
    542                   || uCmd == SUP_IOCTL_FAST_DO_HM_RUN
    543                   || uCmd == SUP_IOCTL_FAST_DO_NOP))
    544         return supdrvIOCtlFast(uCmd, ulArg, &g_DevExt, (PSUPDRVSESSION)pFilp->private_data);
    545     return VBoxDrvLinuxIOCtlSlow(pFilp, uCmd, ulArg);
     618    if (RT_LIKELY(   (   uCmd == SUP_IOCTL_FAST_DO_RAW_RUN
     619                      || uCmd == SUP_IOCTL_FAST_DO_HM_RUN
     620                      || uCmd == SUP_IOCTL_FAST_DO_NOP)
     621                  && pSession->fUnrestricted == true))
     622        return supdrvIOCtlFast(uCmd, ulArg, &g_DevExt, pSession);
     623    return VBoxDrvLinuxIOCtlSlow(pFilp, uCmd, ulArg, pSession);
    546624
    547625#else   /* !HAVE_UNLOCKED_IOCTL */
     
    549627    int rc;
    550628    unlock_kernel();
    551     if (RT_LIKELY(   uCmd == SUP_IOCTL_FAST_DO_RAW_RUN
    552                   || uCmd == SUP_IOCTL_FAST_DO_HM_RUN
    553                   || uCmd == SUP_IOCTL_FAST_DO_NOP))
    554         rc = supdrvIOCtlFast(uCmd, ulArg, &g_DevExt, (PSUPDRVSESSION)pFilp->private_data);
     629    if (RT_LIKELY(   (   uCmd == SUP_IOCTL_FAST_DO_RAW_RUN
     630                      || uCmd == SUP_IOCTL_FAST_DO_HM_RUN
     631                      || uCmd == SUP_IOCTL_FAST_DO_NOP)
     632                  && pSession->fUnrestricted == true))
     633        rc = supdrvIOCtlFast(uCmd, ulArg, &g_DevExt, pSession);
    555634    else
    556         rc = VBoxDrvLinuxIOCtlSlow(pFilp, uCmd, ulArg);
     635        rc = VBoxDrvLinuxIOCtlSlow(pFilp, uCmd, ulArg, pSession);
    557636    lock_kernel();
    558637    return rc;
     
    567646 * @param   uCmd        The function specified to ioctl().
    568647 * @param   ulArg       The argument specified to ioctl().
    569  */
    570 static int VBoxDrvLinuxIOCtlSlow(struct file *pFilp, unsigned int uCmd, unsigned long ulArg)
     648 * @param   pSession    The session instance.
     649 */
     650static int VBoxDrvLinuxIOCtlSlow(struct file *pFilp, unsigned int uCmd, unsigned long ulArg, PSUPDRVSESSION pSession)
    571651{
    572652    int                 rc;
     
    621701     * Process the IOCtl.
    622702     */
    623     rc = supdrvIOCtl(uCmd, &g_DevExt, (PSUPDRVSESSION)pFilp->private_data, pHdr);
     703    rc = supdrvIOCtl(uCmd, &g_DevExt, pSession, pHdr);
    624704
    625705    /*
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette