/** * Checks whether a shared folder share exists or not. * * @returns True if shared folder exists, false if not. * @param u32ClientId The client id returned by VbglR3InfoSvcConnect(). * @param pszShareName Shared folder name to check. */ VBGLR3DECL(bool) VbglR3SharedFolderExists(uint32_t u32ClientId, const char *pszShareName) { AssertPtr(pszShareName); uint32_t cMappings; VBGLR3SHAREDFOLDERMAPPING *paMappings; /** @todo Use some caching here? */ bool fFound = false; int rc = VbglR3SharedFolderGetMappings(u32ClientId, true /* Only process auto-mounted folders */, &paMappings, &cMappings); if (RT_SUCCESS(rc)) { for (uint32_t i = 0; i < cMappings && !fFound; i++) { char *pszName = NULL; rc = VbglR3SharedFolderGetName(u32ClientId, paMappings[i].u32Root, &pszName); if ( RT_SUCCESS(rc) && *pszName) { if (RTStrICmp(pszName, pszShareName) == 0) fFound = true; RTStrFree(pszName); } } VbglR3SharedFolderFreeMappings(paMappings); } return fFound; }
int VBoxSharedFoldersAutoMount(void) { uint32_t u32ClientId; int rc = VbglR3SharedFolderConnect(&u32ClientId); if (RT_FAILURE(rc)) Log(("VBoxTray: Failed to connect to the shared folder service, error %Rrc\n", rc)); else { uint32_t cMappings; VBGLR3SHAREDFOLDERMAPPING *paMappings; rc = VbglR3SharedFolderGetMappings(u32ClientId, true /* Only process auto-mounted folders */, &paMappings, &cMappings); if (RT_SUCCESS(rc)) { #if 0 /* Check for a fixed/virtual auto-mount share. */ if (VbglR3SharedFolderExists(u32ClientId, "vbsfAutoMount")) { Log(("VBoxTray: Hosts supports auto-mount root\n")); } else { #endif Log(("VBoxTray: Got %u shared folder mappings\n", cMappings)); for (uint32_t i = 0; i < cMappings && RT_SUCCESS(rc); i++) { char *pszName = NULL; rc = VbglR3SharedFolderGetName(u32ClientId, paMappings[i].u32Root, &pszName); if ( RT_SUCCESS(rc) && *pszName) { Log(("VBoxTray: Connecting share %u (%s) ...\n", i+1, pszName)); char *pszShareName; if (RTStrAPrintf(&pszShareName, "\\\\vboxsrv\\%s", pszName) >= 0) { char chDrive = 'D'; /* Start probing whether drive D: is free to use. */ do { char szCurDrive[3]; RTStrPrintf(szCurDrive, sizeof(szCurDrive), "%c:", chDrive++); NETRESOURCE resource; RT_ZERO(resource); resource.dwType = RESOURCETYPE_ANY; resource.lpLocalName = TEXT(szCurDrive); resource.lpRemoteName = TEXT(pszShareName); /* Go straight to our network provider in order to get maximum lookup speed. */ resource.lpProvider = TEXT("VirtualBox Shared Folders"); /** @todo Figure out how to map the drives in a block (F,G,H, ...). Save the mapping for later use. */ DWORD dwErr = WNetAddConnection2A(&resource, NULL, NULL, 0); if (dwErr == NO_ERROR) { LogRel(("VBoxTray: Shared folder \"%s\" was mounted to drive \"%s\"\n", pszName, szCurDrive)); break; } else { LogRel(("VBoxTray: Mounting \"%s\" to \"%s\" resulted in dwErr = %ld\n", pszName, szCurDrive, dwErr)); switch (dwErr) { /* * The local device specified by the lpLocalName member is already * connected to a network resource. Try next drive ... */ case ERROR_ALREADY_ASSIGNED: break; default: LogRel(("VBoxTray: Error while mounting shared folder \"%s\" to \"%s\", error = %ld\n", pszName, szCurDrive, dwErr)); break; } } } while (chDrive <= 'Z'); if (chDrive > 'Z') { LogRel(("VBoxTray: No free driver letter found to assign shared folder \"%s\", aborting\n", pszName)); break; } RTStrFree(pszShareName); } else rc = VERR_NO_STR_MEMORY; RTStrFree(pszName); } else Log(("VBoxTray: Error while getting the shared folder name for root node = %u, rc = %Rrc\n", paMappings[i].u32Root, rc)); } #if 0 } #endif RTMemFree(paMappings); } else Log(("VBoxTray: Error while getting the shared folder mappings, rc = %Rrc\n", rc)); VbglR3SharedFolderDisconnect(u32ClientId); } return rc; }
int VBoxSharedFoldersAutoUnmount(void) { uint32_t u32ClientId; int rc = VbglR3SharedFolderConnect(&u32ClientId); if (!RT_SUCCESS(rc)) Log(("VBoxTray: Failed to connect to the shared folder service, error %Rrc\n", rc)); else { uint32_t cMappings; VBGLR3SHAREDFOLDERMAPPING *paMappings; rc = VbglR3SharedFolderGetMappings(u32ClientId, true /* Only process auto-mounted folders */, &paMappings, &cMappings); if (RT_SUCCESS(rc)) { for (uint32_t i = 0; i < cMappings && RT_SUCCESS(rc); i++) { char *pszName = NULL; rc = VbglR3SharedFolderGetName(u32ClientId, paMappings[i].u32Root, &pszName); if ( RT_SUCCESS(rc) && *pszName) { Log(("VBoxTray: Disconnecting share %u (%s) ...\n", i+1, pszName)); char *pszShareName; if (RTStrAPrintf(&pszShareName, "\\\\vboxsrv\\%s", pszName) >= 0) { DWORD dwErr = WNetCancelConnection2(pszShareName, 0, FALSE /* Force disconnect */); if (dwErr == NO_ERROR) { LogRel(("VBoxTray: Share \"%s\" was disconnected\n", pszShareName)); RTStrFree(pszShareName); RTStrFree(pszName); break; } LogRel(("VBoxTray: Disconnecting \"%s\" failed, dwErr = %ld\n", pszShareName, dwErr)); switch (dwErr) { case ERROR_NOT_CONNECTED: break; default: LogRel(("VBoxTray: Error while disconnecting shared folder \"%s\", error = %ld\n", pszShareName, dwErr)); break; } RTStrFree(pszShareName); } else rc = VERR_NO_MEMORY; RTStrFree(pszName); } else Log(("VBoxTray: Error while getting the shared folder name for root node = %u, rc = %Rrc\n", paMappings[i].u32Root, rc)); } RTMemFree(paMappings); } else Log(("VBoxTray: Error while getting the shared folder mappings, rc = %Rrc\n", rc)); VbglR3SharedFolderDisconnect(u32ClientId); } return rc; }
static int VBoxServiceAutoMountProcessMappings(PVBGLR3SHAREDFOLDERMAPPING paMappings, uint32_t cMappings, const char *pszMountDir, const char *pszSharePrefix, uint32_t uClientID) { if (cMappings == 0) return VINF_SUCCESS; AssertPtrReturn(paMappings, VERR_INVALID_PARAMETER); AssertPtrReturn(pszMountDir, VERR_INVALID_PARAMETER); AssertPtrReturn(pszSharePrefix, VERR_INVALID_PARAMETER); AssertReturn(uClientID > 0, VERR_INVALID_PARAMETER); int rc = VINF_SUCCESS; for (uint32_t i = 0; i < cMappings && RT_SUCCESS(rc); i++) { char *pszShareName = NULL; rc = VbglR3SharedFolderGetName(uClientID, paMappings[i].u32Root, &pszShareName); if ( RT_SUCCESS(rc) && *pszShareName) { VBoxServiceVerbose(3, "VBoxServiceAutoMountWorker: Connecting share %u (%s) ...\n", i+1, pszShareName); char *pszShareNameFull = NULL; if (RTStrAPrintf(&pszShareNameFull, "%s%s", pszSharePrefix, pszShareName) > 0) { char szMountPoint[RTPATH_MAX]; rc = RTPathJoin(szMountPoint, sizeof(szMountPoint), pszMountDir, pszShareNameFull); if (RT_SUCCESS(rc)) { VBoxServiceVerbose(4, "VBoxServiceAutoMountWorker: Processing mount point \"%s\"\n", szMountPoint); struct group *grp_vboxsf = getgrnam("vboxsf"); if (grp_vboxsf) { struct vbsf_mount_opts mount_opts = { 0, /* uid */ (int)grp_vboxsf->gr_gid, /* gid */ 0, /* ttl */ 0770, /* dmode, owner and group "vboxsf" have full access */ 0770, /* fmode, owner and group "vboxsf" have full access */ 0, /* dmask */ 0, /* fmask */ 0, /* ronly */ 0, /* noexec */ 0, /* nodev */ 0, /* nosuid */ 0, /* remount */ "\0", /* nls_name */ NULL, /* convertcp */ }; rc = VBoxServiceAutoMountSharedFolder(pszShareName, szMountPoint, &mount_opts); } else VBoxServiceError("VBoxServiceAutoMountWorker: Group \"vboxsf\" does not exist\n"); } else VBoxServiceError("VBoxServiceAutoMountWorker: Unable to join mount point/prefix/shrae, rc = %Rrc\n", rc); RTStrFree(pszShareNameFull); } else VBoxServiceError("VBoxServiceAutoMountWorker: Unable to allocate full share name\n"); RTStrFree(pszShareName); } else VBoxServiceError("VBoxServiceAutoMountWorker: Error while getting the shared folder name for root node = %u, rc = %Rrc\n", paMappings[i].u32Root, rc); } /* for cMappings. */ return rc; }