Merged PR 785475: Resolve ptrace sandbox reports dfa in Ubuntu 22.04 on readlink

Untrack /user/local/include and /usr/x86_64-linux-gnu by default
Report Checker::Lookup for absent path in readlink
Fix a small bug when pathname is empty, we added extra slash at the end of the path

Related work items: #2137346
This commit is contained in:
Qi Wang 2024-05-21 18:01:24 +00:00
Родитель 05828f78c4
Коммит 0c6c081ef9
7 изменённых файлов: 76 добавлений и 3 удалений

Просмотреть файл

@ -100,6 +100,26 @@ namespace Test.BuildXL.Processes
XAssert.AreEqual(1, accesses.Where(a => a.Path == realPath3).Count()); XAssert.AreEqual(1, accesses.Where(a => a.Path == realPath3).Count());
} }
[Fact]
public void CallBoostReadlinkAbsentPathTests()
{
var fileStorage = new TempFileStorage(canGetFileNames: true);
var absentFilePath = Path.Combine(fileStorage.RootDirectory, "absentFile.o");
// This test calls readlink(absentFilePath)
var result = RunTest("readlink_absent_path", fileStorage);
XAssert.IsNotNull(result.FileAccesses);
// There should be only one absent file access
var absentPathAccesses = result.FileAccesses!.Where(a => a.IsNonexistent);
XAssert.AreEqual(1, absentPathAccesses.Count());
// readlink on absent path is reported backed as probe
var absentFileAccess = absentPathAccesses.Single();
XAssert.AreEqual(absentFilePath, absentFileAccess.GetPath(Context.PathTable));
XAssert.AreEqual(RequestedAccess.Probe, absentFileAccess.RequestedAccess);
}
[Fact] [Fact]
public void CallBoostObserverUtilitiesTests() public void CallBoostObserverUtilitiesTests()
{ {

Просмотреть файл

@ -121,6 +121,8 @@ namespace BuildXL.Pips.Graph
UnixPaths.LibLinuxGnu, UnixPaths.LibLinuxGnu,
UnixPaths.Lib64, UnixPaths.Lib64,
UnixPaths.Run, UnixPaths.Run,
UnixPaths.UsrLocalInclude,
UnixPaths.UsrLinuxGnu,
} }
.Concat(IfMacOs( .Concat(IfMacOs(
MacPaths.AppleInternal, MacPaths.AppleInternal,

Просмотреть файл

@ -32,6 +32,10 @@ namespace UnitTests
exeName: a`observer_utilities_test`, exeName: a`observer_utilities_test`,
sourceFiles: [ f`observer_utilities_test.cpp`, f`${sandboxSrcDirectory.path}/observer_utilities.cpp` ], sourceFiles: [ f`observer_utilities_test.cpp`, f`${sandboxSrcDirectory.path}/observer_utilities.cpp` ],
includeDirectories: [ sandboxSrcDirectory ] includeDirectories: [ sandboxSrcDirectory ]
},
{
exeName: a`readlink_absent_path`,
sourceFiles:[f`readlink_absent_path.cpp`]
} }
]; ];

Просмотреть файл

@ -0,0 +1,34 @@
// Copyright (c) Microsoft. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
#define BOOST_TEST_MODULE LinuxSandboxTest
#define _DO_NOT_EXPORT
#include <boost/test/included/unit_test.hpp>
#include <limits.h>
#include <string.h>
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
using namespace std;
BOOST_AUTO_TEST_SUITE(ReadlinkAbsentPath)
BOOST_AUTO_TEST_CASE(TestReadlinkAbsentPath)
{
// Create a absent file path under current working directory
char cwd[PATH_MAX] = { 0 };
char *res = getcwd(cwd, PATH_MAX);
string newPath(res);
newPath.append("/absentFile.o");
// Call readlink on this absent file path
char buf[PATH_MAX] = { 0 };
auto read = readlink(newPath.c_str(), buf, PATH_MAX);
// readlink return -1 on absent path and error number is ENOENT
BOOST_CHECK(read == -1);
BOOST_CHECK_EQUAL(errno, ENOENT);
}
BOOST_AUTO_TEST_SUITE_END()

Просмотреть файл

@ -1129,8 +1129,11 @@ void BxlObserver::relative_to_absolute(const char *pathname, int dirfd, int asso
_fatal("['%s'] Could not get path for fd %d with path '%s'; errno: %d", systemcall, dirfd, pathname, errno); _fatal("['%s'] Could not get path for fd %d with path '%s'; errno: %d", systemcall, dirfd, pathname, errno);
} }
fullpath[len] = '/'; if (pathname[0] != '\0')
strcpy(fullpath + len + 1, pathname); {
fullpath[len] = '/';
strcpy(fullpath + len + 1, pathname);
}
} }
else else
{ {

Просмотреть файл

@ -127,7 +127,15 @@ AccessCheckResult IOHandler::HandleUnlink(const IOEvent &event, AccessReport &ac
AccessCheckResult IOHandler::HandleReadlink(const IOEvent &event, AccessReport &accessToReport) AccessCheckResult IOHandler::HandleReadlink(const IOEvent &event, AccessReport &accessToReport)
{ {
return CheckAndCreateReport(kOpMacReadlink, event.GetEventPath(SRC_PATH), Checkers::CheckRead, event.GetPid(), false, event.GetError(), accessToReport); bool isDir = S_ISDIR(event.GetMode());
if (!event.EventPathExists())
{
return CheckAndCreateReport(kOpMacLookup, event.GetEventPath(SRC_PATH), Checkers::CheckLookup, event.GetPid(), isDir, event.GetError(), accessToReport);
}
else
{
return CheckAndCreateReport(kOpMacReadlink, event.GetEventPath(SRC_PATH), Checkers::CheckRead, event.GetPid(), isDir, event.GetError(), accessToReport);
}
} }
AccessCheckResult IOHandler::HandleRename(const IOEvent &event, AccessReport &sourceAccessToReport, AccessReport &destinationAccessToReport) AccessCheckResult IOHandler::HandleRename(const IOEvent &event, AccessReport &sourceAccessToReport, AccessReport &destinationAccessToReport)

Просмотреть файл

@ -492,6 +492,8 @@ namespace BuildXL.Interop.Unix
public const string UsrStandalone = "/usr/standalone"; public const string UsrStandalone = "/usr/standalone";
public const string UsrSbin = "/usr/sbin"; public const string UsrSbin = "/usr/sbin";
public const string Var = "/var"; public const string Var = "/var";
public const string UsrLocalInclude = "/usr/local/include";
public const string UsrLinuxGnu = "/usr/x86_64-linux-gnu";
} }
public static class MacPaths public static class MacPaths