Files
revng-revng/include/revng/Storage/Path.h
Giacomo Vercesi 5070fe6aef revng::Path: add newline to dump
The `revng::Path.dump` method was missing a newline, which caused the
output to be harder to read.
2024-01-26 17:46:21 +01:00

136 lines
4.1 KiB
C++

#pragma once
//
// This file is distributed under the MIT License. See LICENSE.md for details.
//
#include "llvm/ADT/SmallString.h"
#include "llvm/Support/Path.h"
#include "revng/Storage/StorageClient.h"
#include "revng/Support/Debug.h"
#include "revng/Support/PathList.h"
namespace revng {
class PathBase {
protected:
revng::StorageClient *Client = nullptr;
std::string SubPath;
public:
explicit PathBase(StorageClient *Client, llvm::StringRef SubPath) :
Client(Client), SubPath(SubPath.str()){};
public:
void dump() const debug_function { dump(dbg); }
template<typename T>
void dump(T &OS) const debug_function {
OS << "Client: ";
Client->dump(OS);
OS << " Path: " << SubPath << "\n";
}
bool isValid() const { return Client != nullptr; }
};
class FilePath : public PathBase {
public:
using PathBase::PathBase;
/// Utility function to get a FilePath that can read stdin
static FilePath stdin();
/// Utility function to get a FilePath that can write stdout
static FilePath stdout();
/// Utility function to get a FilePath on the local filesystem
static FilePath fromLocalStorage(llvm::StringRef Path);
/// This function will return another FilePath with the extension added
FilePath addExtension(llvm::StringRef Extension) const {
using llvm::sys::path::get_separator;
llvm::StringRef Separator = get_separator(Client->getStyle());
revng_assert(Extension.find('.') == llvm::StringRef::npos);
revng_assert(Extension.find(Separator) == llvm::StringRef::npos);
return FilePath(Client, SubPath + '.' + Extension.str());
}
llvm::Expected<bool> exists() const {
auto MaybeResult = Client->type(SubPath);
if (!MaybeResult)
return MaybeResult.takeError();
revng_assert(MaybeResult.get() != PathType::Directory);
return MaybeResult.get() == PathType::File;
}
llvm::Error remove() const { return Client->remove(SubPath); }
/// This function will allow the user of a FilePath to obtain a wrapped
/// llvm::MemoryBuffer that can be used for reading
llvm::Expected<std::unique_ptr<ReadableFile>> getReadableFile() const {
return Client->getReadableFile(SubPath);
};
/// This function will allow the user of a FilePath to obtain a wrapped
/// llvm::raw_ostream that can be used to write to the file (reminder to then
/// call WritableFile::commit). The Encoding parameter is useful only on some
/// backend (currently, S3) which tell the storage provider the encoding of
/// the file.
llvm::Expected<std::unique_ptr<WritableFile>>
getWritableFile(ContentEncoding Encoding = ContentEncoding::None) const {
return Client->getWritableFile(SubPath, Encoding);
}
llvm::Error copyTo(const FilePath &Destination) const {
if (Client == Destination.Client)
return Client->copy(SubPath, Destination.SubPath);
auto MaybeReadableFile = getReadableFile();
if (not MaybeReadableFile)
return MaybeReadableFile.takeError();
auto MaybeWritableFile = Destination.getWritableFile();
if (not MaybeWritableFile)
return MaybeWritableFile.takeError();
auto &ReadableFile = MaybeReadableFile.get();
auto &WritableFile = MaybeWritableFile.get();
WritableFile->os() << ReadableFile->buffer().getBuffer();
return WritableFile->commit();
}
};
class DirectoryPath : public PathBase {
public:
using PathBase::PathBase;
static DirectoryPath fromLocalStorage(llvm::StringRef Path);
public:
DirectoryPath getDirectory(llvm::StringRef DirectoryName) const {
std::string Path = joinPath(Client->getStyle(), SubPath, DirectoryName);
return DirectoryPath(Client, Path);
}
FilePath getFile(llvm::StringRef Filename) const {
return FilePath(Client, joinPath(Client->getStyle(), SubPath, Filename));
}
llvm::Expected<bool> exists() const {
auto MaybeResult = Client->type(SubPath);
if (!MaybeResult)
return MaybeResult.takeError();
revng_assert(MaybeResult.get() != PathType::File);
return MaybeResult.get() == PathType::Directory;
}
llvm::Error create() const { return Client->createDirectory(SubPath); }
};
} // namespace revng