static const char * DnDCreateRootStagingDirectory(void) { const char *root; /* * DnD_GetFileRoot() gives us a pointer to a static string, so there's no * need to free anything. */ root = DnD_GetFileRoot(); if (!root) { return NULL; } if (File_Exists(root)) { if (!DnDRootDirUsable(root) && !DnDSetPermissionsOnRootDir(root)) { /* * The directory already exists and its permissions are wrong and * cannot be set, so there's not much we can do. */ return NULL; } } else { if (!File_CreateDirectory(root) || !DnDSetPermissionsOnRootDir(root)) { /* We couldn't create the directory or set the permissions. */ return NULL; } } return root; }
static const char * CreateApparentRootDirectory(void) { const char *root; /* * DnD_GetFileRoot() gives us a pointer to a static string, so there's no * need to free anything. * * XXX On XDG platforms this path ("/tmp/VMwareDnD") is created by an * init script, so we could remove some of the code below and just bail * if the user deletes it. */ root = DnD_GetFileRoot(); if (!root) { return NULL; } if (File_Exists(root)) { if ( !DnDRootDirUsable(root) && !DnDSetPermissionsOnRootDir(root)) { /* * The directory already exists and its permissions are wrong and * cannot be set, so there's not much we can do. */ return NULL; } } else { if ( !File_CreateDirectory(root) || !DnDSetPermissionsOnRootDir(root)) { /* We couldn't create the directory or set the permissions. */ return NULL; } } return root; }
char * DnD_CreateStagingDirectory(void) { const char *root; char **stagingDirList; int numStagingDirs; int i; char *ret = NULL; Bool found = FALSE; /* * Make sure the root staging directory is created with the correct * permissions. */ root = DnDCreateRootStagingDirectory(); if (!root) { return NULL; } /* Look for an existing, empty staging directory */ numStagingDirs = File_ListDirectory(root, &stagingDirList); if (numStagingDirs < 0) { goto exit; } for (i = 0; i < numStagingDirs; i++) { if (!found) { char *stagingDir; stagingDir = Unicode_Append(root, stagingDirList[i]); if (File_IsEmptyDirectory(stagingDir) && DnDStagingDirectoryUsable(stagingDir)) { ret = Unicode_Append(stagingDir, DIRSEPS); /* * We can use this directory. Make sure to continue to loop * so we don't leak the remaining stagindDirList[i]s. */ found = TRUE; } free(stagingDir); } } Util_FreeStringList(stagingDirList, numStagingDirs); /* Only create a directory if we didn't find one above. */ if (!found) { rqContext *context; context = Random_QuickSeed((unsigned)time(NULL)); for (i = 0; i < 10; i++) { char *temp; /* Each staging directory is given a random name. */ free(ret); temp = Unicode_Format("%08x%c", Random_Quick(context), DIRSEPC); VERIFY(temp); ret = Unicode_Append(root, temp); free(temp); if (File_CreateDirectory(ret) && DnDSetPermissionsOnStagingDir(ret)) { found = TRUE; break; } } free(context); } exit: if (!found && ret != NULL) { free(ret); ret = NULL; } return ret; }