HRESULT Guest::directoryQueryInfoInternal(IN_BSTR aDirectory, IN_BSTR aUsername, IN_BSTR aPassword, PRTFSOBJINFO aObjInfo, RTFSOBJATTRADD enmAddAttribs, int *pRC) { using namespace guestControl; /** @todo Search directory cache first? */ CheckComArgStrNotEmptyOrNull(aDirectory); /* aUsername is optional. */ /* aPassword is optional. */ /* aObjInfo is optional. */ AutoCaller autoCaller(this); if (FAILED(autoCaller.rc())) return autoCaller.rc(); HRESULT hr = S_OK; try { Utf8Str Utf8Dir(aDirectory); Utf8Str Utf8Username(aUsername); Utf8Str Utf8Password(aPassword); com::SafeArray<IN_BSTR> args; com::SafeArray<IN_BSTR> env; /* * Prepare tool command line. */ /* We need to get output which is machine-readable in form * of "key=value\0..key=value\0\0". */ args.push_back(Bstr("--machinereadable").raw()); /* Only the actual file name to chekc is needed for now. */ args.push_back(Bstr(Utf8Dir).raw()); /* * Execute guest process. */ ULONG uPID; ComPtr<IProgress> pProgress; GuestCtrlStreamObjects stdOut; hr = executeAndWaitForTool(Bstr(VBOXSERVICE_TOOL_STAT).raw(), Bstr("Querying directory information").raw(), ComSafeArrayAsInParam(args), ComSafeArrayAsInParam(env), aUsername, aPassword, ExecuteProcessFlag_WaitForStdOut, &stdOut, NULL /* stdErr */, pProgress.asOutParam(), &uPID); if (SUCCEEDED(hr)) { hr = setErrorFromProgress(pProgress); if (SUCCEEDED(hr)) { int rc = VINF_SUCCESS; if (stdOut.size()) { const char *pszFsType = stdOut[0].GetString("ftype"); if (!pszFsType) /* Attribute missing? */ rc = VERR_PATH_NOT_FOUND; if ( RT_SUCCESS(rc) && strcmp(pszFsType, "d")) /* Directory? */ { rc = VERR_PATH_NOT_FOUND; /* This is not critical for Main, so don't set hr -- * we will take care of rc then. */ } if ( RT_SUCCESS(rc) && aObjInfo) /* Do we want object details? */ { rc = executeStreamQueryFsObjInfo(aDirectory, stdOut[0], aObjInfo, enmAddAttribs); } } else rc = VERR_NO_DATA; if (pRC) *pRC = rc; } pProgress.setNull(); } } catch (std::bad_alloc &) { hr = E_OUTOFMEMORY; } return hr; }
HRESULT Guest::fileQueryInfoInternal(IN_BSTR aFile, IN_BSTR aUsername, IN_BSTR aPassword, PRTFSOBJINFO aObjInfo, RTFSOBJATTRADD enmAddAttribs, int *pRC) { using namespace guestControl; /* aUsername is optional. */ /* aPassword is optional. */ /* aObjInfo is optional. */ HRESULT hr; try { Utf8Str Utf8File(aFile); Utf8Str Utf8Username(aUsername); Utf8Str Utf8Password(aPassword); com::SafeArray<IN_BSTR> args; com::SafeArray<IN_BSTR> env; /* * Prepare tool command line. */ /* We need to get output which is machine-readable in form * of "key=value\0..key=value\0\0". */ args.push_back(Bstr("--machinereadable").raw()); /* Only the actual file name to chekc is needed for now. */ args.push_back(Bstr(Utf8File).raw()); /* * Execute guest process. */ ULONG uPID; GuestCtrlStreamObjects stdOut; ComPtr<IProgress> pProgress; hr = executeAndWaitForTool(Bstr(VBOXSERVICE_TOOL_STAT).raw(), Bstr("Querying file information").raw(), ComSafeArrayAsInParam(args), ComSafeArrayAsInParam(env), aUsername, aPassword, ExecuteProcessFlag_WaitForStdOut, &stdOut, NULL, pProgress.asOutParam(), &uPID); if (SUCCEEDED(hr)) { hr = setErrorFromProgress(pProgress); if (SUCCEEDED(hr)) { int rc = VINF_SUCCESS; if (stdOut.size()) { #if 0 /* Dump the parsed stream contents to Log(). */ stdOut[0].Dump(); #endif const char *pszFsType = stdOut[0].GetString("ftype"); if (!pszFsType) /* Was an object found at all? */ rc = VERR_FILE_NOT_FOUND; if ( RT_SUCCESS(rc) && strcmp(pszFsType, "-")) /* Regular file? */ { rc = VERR_FILE_NOT_FOUND; /* This is not critical for Main, so don't set hr -- * we will take care of rc then. */ } if ( RT_SUCCESS(rc) && aObjInfo) /* Do we want object details? */ { rc = executeStreamQueryFsObjInfo(aFile, stdOut[0], aObjInfo, enmAddAttribs); } } else rc = VERR_NO_DATA; if (pRC) *pRC = rc; } pProgress.setNull(); } } catch (std::bad_alloc &) { hr = E_OUTOFMEMORY; } return hr; }