LLVM: lib/Support/Path.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

17#include "llvm/Config/config.h"

18#include "llvm/Config/llvm-config.h"

24#include

25

26#if !defined(_MSC_VER) && !defined(__MINGW32__)

27#include <unistd.h>

28#else

29#include <io.h>

30#endif

31

32using namespace llvm;

34

35namespace {

39

40 inline Style real_style(Style style) {

41 if (style != Style::native)

42 return style;

44 return Style::posix;

45 return LLVM_WINDOWS_PREFER_FORWARD_SLASH ? Style::windows_slash

46 : Style::windows_backslash;

47 }

48

49 inline const char *separators(Style style) {

51 return "\\/";

52 return "/";

53 }

54

55 inline char preferred_separator(Style style) {

56 if (real_style(style) == Style::windows)

57 return '\\';

58 return '/';

59 }

60

62

63

64

65

66

67

69 return path;

70

72

73 if (path.size() >= 2 &&

74 std::isalpha(static_cast<unsigned char>(path[0])) && path[1] == ':')

75 return path.substr(0, 2);

76 }

77

78

80 path[0] == path[1] && is\_separator(path[2], style)) {

81

83 return path.substr(0, end);

84 }

85

86

88 return path.substr(0, 1);

89

90

92 return path.substr(0, end);

93 }

94

95

96

97 size_t filename_pos(StringRef str, Style style) {

99 return str.size() - 1;

100

101 size_t pos = str.find_last_of(separators(style), str.size() - 1);

102

106 }

107

109 return 0;

110

111 return pos + 1;

112 }

113

114

115

116 size_t root_dir_start(StringRef str, Style style) {

117

119 if (str.size() > 2 && str[1] == ':' && is_separator(str[2], style))

120 return 2;

121 }

122

123

124 if (str.size() > 3 && is_separator(str[0], style) && str[0] == str[1] &&

127 }

128

129

131 return 0;

132

134 }

135

136

137

138

139 size_t parent_path_end(StringRef path, Style style) {

140 size_t end_pos = filename_pos(path, style);

141

142 bool filename_was_sep =

144

145

146 size_t root_dir_pos = root_dir_start(path, style);

147 while (end_pos > 0 &&

148 (root_dir_pos == StringRef::npos || end_pos > root_dir_pos) &&

150 --end_pos;

151

152 if (end_pos == root_dir_pos && !filename_was_sep) {

153

154

155 return root_dir_pos + 1;

156 }

157

158

159 return end_pos;

160 }

161}

162

168

169static std::error_code

173 unsigned Mode = 0) {

174

175

176

177

178

179 std::error_code EC;

180 for (int Retries = 128; Retries > 0; --Retries) {

182

183 switch (Type) {

187 if (EC) {

188

189

190 if (EC == errc::file_exists || EC == errc::permission_denied)

191 continue;

192 return EC;

193 }

194

195 return std::error_code();

196 }

197

200 if (EC == errc::no_such_file_or_directory)

201 return std::error_code();

202 if (EC)

203 return EC;

204 continue;

205 }

206

209 if (EC) {

210 if (EC == errc::file_exists)

211 continue;

212 return EC;

213 }

214 return std::error_code();

215 }

216 }

218 }

219 return EC;

220}

221

222namespace llvm {

223namespace sys {

224namespace path {

225

228 i.Path = path;

229 i.Component = find_first_component(path, style);

230 i.Position = 0;

231 i.S = style;

232 return i;

233}

234

237 i.Path = path;

238 i.Position = path.size();

239 return i;

240}

241

243 assert(Position < Path.size() && "Tried to increment past end!");

244

245

246 Position += Component.size();

247

248

249 if (Position == Path.size()) {

251 return *this;

252 }

253

254

255

256 bool was_net = Component.size() > 2 && is_separator(Component[0], S) &&

257 Component[1] == Component[0] && is\_separator(Component[2], S);

258

259

261

262 if (was_net ||

263

265 Component = Path.substr(Position, 1);

266 return *this;

267 }

268

269

270 while (Position != Path.size() && is_separator(Path[Position], S)) {

271 ++Position;

272 }

273

274

275 if (Position == Path.size() && Component != "/") {

276 --Position;

277 Component = ".";

278 return *this;

279 }

280 }

281

282

283 size_t end_pos = Path.find_first_of(separators(S), Position);

284 Component = Path.slice(Position, end_pos);

285

286 return *this;

287}

288

290 return Path.begin() == RHS.Path.begin() && Position == RHS.Position;

291}

292

294 return Position - RHS.Position;

295}

296

299 I.Path = Path;

300 I.Position = Path.size();

301 I.S = style;

302 ++I;

303 return I;

304}

305

308 I.Path = Path;

309 I.Component = Path.substr(0, 0);

310 I.Position = 0;

311 return I;

312}

313

315 size_t root_dir_pos = root_dir_start(Path, S);

316

317

318 size_t end_pos = Position;

319 while (end_pos > 0 && (end_pos - 1) != root_dir_pos &&

321 --end_pos;

322

323

324 if (Position == Path.size() && !Path.empty() &&

326 (root_dir_pos == StringRef::npos || end_pos - 1 > root_dir_pos)) {

327 --Position;

328 Component = ".";

329 return *this;

330 }

331

332

333 size_t start_pos = filename_pos(Path.substr(0, end_pos), S);

334 Component = Path.slice(start_pos, end_pos);

335 Position = start_pos;

336 return *this;

337}

338

340 return Path.begin() == RHS.Path.begin() && Component == RHS.Component &&

341 Position == RHS.Position;

342}

343

345 return Position - RHS.Position;

346}

347

350 if (b != e) {

351 bool has_net =

352 b->size() > 2 && is_separator((*b)[0], style) && (*b)[1] == (*b)[0];

353 bool has_drive = is_style_windows(style) && b->ends_with(":");

354

355 if (has_net || has_drive) {

356 if ((++pos != e) && is_separator((*pos)[0], style)) {

357

358 return path.substr(0, b->size() + pos->size());

359 }

360

361 return *b;

362 }

363

364

366 return *b;

367 }

368 }

369

371}

372

375 if (b != e) {

376 bool has_net =

377 b->size() > 2 && is_separator((*b)[0], style) && (*b)[1] == (*b)[0];

378 bool has_drive = is_style_windows(style) && b->ends_with(":");

379

380 if (has_net || has_drive) {

381

382 return *b;

383 }

384 }

385

386

388}

389

392 if (b != e) {

393 bool has_net =

394 b->size() > 2 && is_separator((*b)[0], style) && (*b)[1] == (*b)[0];

395 bool has_drive = is_style_windows(style) && b->ends_with(":");

396

397 if ((has_net || has_drive) &&

398

399 (++pos != e) && is_separator((*pos)[0], style)) {

400 return *pos;

401 }

402

403

404 if (!has_net && is_separator((*b)[0], style)) {

405 return *b;

406 }

407 }

408

409

411}

412

416}

417

424

427 if (!b.isTriviallyEmpty()) components.push_back(b.toStringRef(b_storage));

430

431 for (auto &component : components) {

432 bool path_has_sep =

434 if (path_has_sep) {

435

436 size_t loc = component.find_first_not_of(separators(style));

437 StringRef c = component.substr(loc);

438

439

441 continue;

442 }

443

444 bool component_has_sep =

445 !component.empty() && is_separator(component[0], style);

446 if (!component_has_sep &&

448

449 path.push_back(preferred_separator(style));

450 }

451

452 path.append(component.begin(), component.end());

453 }

454}

455

459}

460

465}

466

468 size_t end_pos = parent_path_end(path, style);

471 return path.substr(0, end_pos);

472}

473

475 size_t end_pos = parent_path_end(StringRef(path.begin(), path.size()), style);

478}

479

485

486

487 size_t pos = p.find_last_of('.');

488 if (pos != StringRef::npos && pos >= filename_pos(p, style))

490

491

492 if (ext.size() > 0 && ext[0] != '.')

494

495

497}

498

501

503 if (Path.size() < Prefix.size())

504 return false;

505 for (size_t I = 0, E = Prefix.size(); I != E; ++I) {

508 if (SepPath != SepPrefix)

509 return false;

510 if (!SepPath && toLower(Path[I]) != toLower(Prefix[I]))

511 return false;

512 }

513 return true;

514 }

515 return Path.starts_with(Prefix);

516}

517

520 if (OldPrefix.empty() && NewPrefix.empty())

521 return false;

522

523 StringRef OrigPath(Path.begin(), Path.size());

524 if (starts\_with(OrigPath, OldPrefix, style))

525 return false;

526

527

528 if (OldPrefix.size() == NewPrefix.size()) {

530 return true;

531 }

532

535 (Twine(NewPrefix) + RelPath).toVector(NewPath);

536 Path.swap(NewPath);

537 return true;

538}

539

543 "path and result are not allowed to overlap!");

544

547 native(result, style);

548}

549

551 if (Path.empty())

552 return;

554 for (char &Ch : Path)

556 Ch = preferred_separator(style);

557 if (Path[0] == '~' && (Path.size() == 1 || is_separator(Path[1], style))) {

560 PathHome.append(Path.begin() + 1, Path.end());

561 Path = PathHome;

562 }

563 } else {

564 std::replace(Path.begin(), Path.end(), '\\', '/');

565 }

566}

567

570 return std::string(path);

571

572 std::string s = path.str();

573 std::replace(s.begin(), s.end(), '\\', '/');

574 return s;

575}

576

578

583 return fname;

584 if ((fname.size() == 1 && fname == ".") ||

585 (fname.size() == 2 && fname == ".."))

586 return fname;

587 return fname.substr(0, pos);

588}

589

595 if ((fname.size() == 1 && fname == ".") ||

596 (fname.size() == 2 && fname == ".."))

598 return fname.substr(pos);

599}

600

602 if (value == '/')

603 return true;

605 return value == '\\';

606 return false;

607}

608

611 return "\\";

612 return "/";

613}

614

618

620}

621

625

627}

628

632

634}

635

639

641}

642

646

648}

649

653

655}

656

660

662}

663

667

669}

670

674

677

678 return rootDir && rootName;

679}

680

684

685

686

687 if (!p.empty() && is_separator(p.front(), style))

688 return true;

689

691

692 if (p.size() >= 2 && (p[0] && p[1] == ':'))

693 return true;

694 }

695

696 return false;

697}

698

701}

702

704

705 while (Path.size() > 2 && Path[0] == '.' && is_separator(Path[1], style)) {

706 Path = Path.substr(2);

707 while (Path.size() > 0 && is_separator(Path[0], style))

708 Path = Path.substr(1);

709 }

710 return Path;

711}

712

713

714

717 style = real_style(style);

719 bool needs_change = false;

721

722

724 bool absolute = !root.empty();

725 if (absolute)

727

728

729

730 while (!remaining.empty()) {

731 size_t next_slash = remaining.find_first_of(separators(style));

733 next_slash = remaining.size();

735 remaining = remaining.drop_front(next_slash);

736

737

738 if (!remaining.empty()) {

739 needs_change |= remaining.front() != preferred_separator(style);

741

742

743 needs_change |= remaining.empty();

744 }

745

746

747 if (component.empty() || component == ".") {

748 needs_change = true;

749 } else if (remove_dot_dot && component == "..") {

750 needs_change = true;

751

752

753 if (!components.empty() && components.back() != "..") {

755 } else if (!absolute) {

757 }

758 } else {

760 }

761 }

762

764

766 needs_change |= root != buffer;

767

768

769 if (!needs_change)

770 return false;

771

772 if (!components.empty()) {

773 buffer += components[0];

775 buffer += preferred_separator(style);

776 buffer += C;

777 }

778 }

779 the_path.swap(buffer);

780 return true;

781}

782

783}

784

785namespace fs {

786

790 if (EC)

791 return EC;

792 Result = Status.getUniqueID();

793 return std::error_code();

794}

795

797 bool MakeAbsolute) {

799 Model.toVector(ModelStorage);

800

801 if (MakeAbsolute) {

802

807 ModelStorage.swap(TDir);

808 }

809 }

810

811 ResultPath = ModelStorage;

814

815

816 for (unsigned i = 0, e = ModelStorage.size(); i != e; ++i) {

817 if (ModelStorage[i] == '%')

819 }

820}

821

824 OpenFlags Flags, unsigned Mode) {

826 Mode);

827}

828

831 unsigned Mode) {

832 int FD;

834 if (EC)

835 return EC;

836

837 close(FD);

838 return EC;

839}

840

841static std::error_code

846 StringRef P = Model.toNullTerminatedStringRef(Storage);

848 "Model must be a simple filename.");

849

852}

853

854static std::error_code

858 const char *Middle = Suffix.empty() ? "-%%%%%%" : "-%%%%%%.";

859 return createTemporaryFile(Prefix + Middle + Suffix, ResultFD, ResultPath,

860 Type, Flags);

861}

862

864 int &ResultFD,

868 Flags);

869}

870

874 int FD;

876 if (EC)

877 return EC;

878

879 close(FD);

880 return EC;

881}

882

883

884

887 int Dummy;

888 return createUniqueEntity(Prefix + "-%%%%%%", Dummy, ResultPath, true,

890}

891

892std::error_code

895 int Dummy;

897}

898

899std::error_code

902 int Dummy;

904}

905

909

912

913

914 if ((rootName || is_style_posix(Style::native)) && rootDirectory)

915 return;

916

917

919 current_directory.toVector(current_dir);

920

921

922 if (!rootName && !rootDirectory) {

923

925

926 path.swap(current_dir);

927 return;

928 }

929

930 if (!rootName && rootDirectory) {

934

935 path.swap(curDirRootName);

936 return;

937 }

938

939 if (rootName && !rootDirectory) {

944

946 path::append(res, pRootName, bRootDirectory, bRelativePath, pRelativePath);

947 path.swap(res);

948 return;

949 }

950

951 llvm_unreachable("All rootName and rootDirectory combinations should have "

952 "occurred above!");

953}

954

957 return {};

958

960 if (std::error_code ec = current_path(current_dir))

961 return ec;

962

964 return {};

965}

966

970 StringRef P = Path.toStringRef(PathStorage);

971

972

974

975

977 return EC;

978

979

980

982 if (Parent.empty())

983 return EC;

984

986 return EC;

987

989}

990

992 const size_t BufSize = 4096;

993 char *Buf = new char[BufSize];

994 int BytesRead = 0, BytesWritten = 0;

995 for (;;) {

996 BytesRead = read(ReadFD, Buf, BufSize);

997 if (BytesRead <= 0)

998 break;

999 while (BytesRead) {

1000 BytesWritten = write(WriteFD, Buf, BytesRead);

1001 if (BytesWritten < 0)

1002 break;

1003 BytesRead -= BytesWritten;

1004 }

1005 if (BytesWritten < 0)

1006 break;

1007 }

1008 delete[] Buf;

1009

1010 if (BytesRead < 0 || BytesWritten < 0)

1012 return std::error_code();

1013}

1014

1015#ifndef __APPLE__

1017 int ReadFD, WriteFD;

1019 return EC;

1020 if (std::error_code EC =

1022 close(ReadFD);

1023 return EC;

1024 }

1025

1027

1028 close(ReadFD);

1029 close(WriteFD);

1030

1031 return EC;

1032}

1033#endif

1034

1036 int ReadFD;

1038 return EC;

1039

1041

1042 close(ReadFD);

1043

1044 return EC;

1045}

1046

1048 MD5 Hash;

1049

1050 constexpr size_t BufSize = 4096;

1051 std::vector<uint8_t> Buf(BufSize);

1052 int BytesRead = 0;

1053 for (;;) {

1054 BytesRead = read(FD, Buf.data(), BufSize);

1055 if (BytesRead <= 0)

1056 break;

1058 }

1059

1060 if (BytesRead < 0)

1063 Hash.final(Result);

1064 return Result;

1065}

1066

1068 int FD;

1070 return EC;

1071

1073 close(FD);

1074 return Result;

1075}

1076

1079}

1080

1083}

1084

1087 if (status(Path, st, Follow))

1089 return st.type();

1090}

1091

1094}

1095

1098 if (std::error_code ec = status(path, st))

1099 return ec;

1101 return std::error_code();

1102}

1103

1106}

1107

1110 if (std::error_code ec = status(path, st))

1111 return ec;

1113 return std::error_code();

1114}

1115

1118}

1119

1122 if (std::error_code ec = status(path, st, false))

1123 return ec;

1125 return std::error_code();

1126}

1127

1132}

1133

1136 if (std::error_code EC = status(Path, FileStatus))

1137 return EC;

1138 Result = is_other(FileStatus);

1139 return std::error_code();

1140}

1141

1146 this->Path = std::string(PathStr);

1147 this->Type = Type;

1148 this->Status = Status;

1149}

1150

1153 if (std::error_code EC = status(Path, Status))

1154 return EC;

1155

1156 return Status.permissions();

1157}

1158

1160 assert(Mapping && "Mapping failed but used anyway!");

1161 return Size;

1162}

1163

1165 assert(Mapping && "Mapping failed but used anyway!");

1166 return reinterpret_cast<char *>(Mapping);

1167}

1168

1170 assert(Mapping && "Mapping failed but used anyway!");

1171 return reinterpret_cast<const char *>(Mapping);

1172}

1173

1175 ssize_t ChunkSize) {

1176

1177 size_t Size = Buffer.size();

1179

1180

1181 for (;;) {

1185 if (!ReadBytes)

1187 if (*ReadBytes == 0)

1189 Size += *ReadBytes;

1190 }

1191}

1192

1193}

1194}

1195}

1196

1197

1198#if defined(LLVM_ON_UNIX)

1200#endif

1201#if defined(_WIN32)

1203#endif

1204

1205namespace llvm {

1206namespace sys {

1207namespace fs {

1208

1213 TmpName = std::move(Other.TmpName);

1215 Other.Done = true;

1217#ifdef _WIN32

1218 RemoveOnClose = Other.RemoveOnClose;

1219 Other.RemoveOnClose = false;

1220#endif

1221 return *this;

1222}

1223

1225

1227 Done = true;

1228 if (FD != -1 && close(FD) == -1) {

1231 }

1232 FD = -1;

1233

1234#ifdef _WIN32

1235

1236

1237 bool Remove = RemoveOnClose;

1238#else

1239

1240 bool Remove = true;

1241#endif

1242 std::error_code RemoveEC;

1243 if (Remove && !TmpName.empty()) {

1246 if (!RemoveEC)

1247 TmpName = "";

1248 } else {

1249 TmpName = "";

1250 }

1252}

1253

1256 Done = true;

1257

1258#ifdef _WIN32

1259

1260 auto H = reinterpret_cast<HANDLE>(_get_osfhandle(FD));

1261 std::error_code RenameEC =

1262 RemoveOnClose ? std::error_code() : setDeleteDisposition(H, false);

1263 bool ShouldDelete = false;

1264 if (!RenameEC) {

1265 RenameEC = rename_handle(H, Name);

1266

1267 if (RenameEC ==

1268 std::error_code(ERROR_NOT_SAME_DEVICE, std::system_category())) {

1270 ShouldDelete = true;

1271 }

1272 }

1273

1274

1275 if (RenameEC)

1276 ShouldDelete = true;

1277 if (ShouldDelete) {

1278 if (!RemoveOnClose)

1279 setDeleteDisposition(H, true);

1280 else

1282 }

1283#else

1284 std::error_code RenameEC = fs::rename(TmpName, Name);

1285 if (RenameEC) {

1286

1288

1289 if (RenameEC)

1291 }

1292#endif

1294

1295 if (!RenameEC)

1296 TmpName = "";

1297

1298 if (close(FD) == -1)

1300 FD = -1;

1301

1303}

1304

1307 Done = true;

1308

1309#ifdef _WIN32

1310 auto H = reinterpret_cast<HANDLE>(_get_osfhandle(FD));

1311 if (std::error_code EC = setDeleteDisposition(H, false))

1313#endif

1315

1316 TmpName = "";

1317

1318 if (close(FD) == -1)

1320 FD = -1;

1321

1323}

1324

1327 int FD;

1329 if (std::error_code EC =

1332

1333 TempFile Ret(ResultPath, FD);

1334#ifdef _WIN32

1335 auto H = reinterpret_cast<HANDLE>(_get_osfhandle(FD));

1336 bool SetSignalHandler = false;

1337 if (std::error_code EC = setDeleteDisposition(H, true)) {

1338 Ret.RemoveOnClose = true;

1339 SetSignalHandler = true;

1340 }

1341#else

1342 bool SetSignalHandler = true;

1343#endif

1345

1349 }

1350 return std::move(Ret);

1351}

1352}

1353

1354}

1355}

BlockVerifier::State From

Given that RA is a live value

static std::error_code createUniqueEntity(const Twine &Model, int &ResultFD, SmallVectorImpl< char > &ResultPath, bool MakeAbsolute, FSEntity Type, sys::fs::OpenFlags Flags=sys::fs::OF_None, unsigned Mode=0)

Provides a library for accessing information about this process and other processes on the operating ...

assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())

This file defines the make_scope_exit function, which executes user-defined cleanup logic at scope ex...

ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...

Represents either an error or a value T.

Lightweight error class with error context and mandatory checking.

static ErrorSuccess success()

Create a success value.

Tagged union holding either a T or a Error.

Error takeError()

Take ownership of the stored error.

void update(ArrayRef< uint8_t > Data)

Updates the hash for the byte stream provided.

void final(MD5Result &Result)

Finishes off the hash and puts the result in result.

MutableArrayRef - Represent a mutable reference to an array (0 or more elements consecutively in memo...

SmallString - A SmallString is just a SmallVector with methods and accessors that make it work better...

void append(StringRef RHS)

Append from a StringRef.

This class consists of common code factored out of the SmallVector class to reduce code duplication b...

void resize_for_overwrite(size_type N)

Like resize, but T is POD, the new values won't be initialized.

void append(ItTy in_start, ItTy in_end)

Add the specified range to the end of the SmallVector.

void truncate(size_type N)

Like resize, but requires that N is less than size().

void swap(SmallVectorImpl &RHS)

void push_back(const T &Elt)

pointer data()

Return a pointer to the vector's buffer, even if empty().

This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.

StringRef - Represent a constant reference to a string, i.e.

std::string str() const

str - Get the contents as an std::string.

constexpr StringRef substr(size_t Start, size_t N=npos) const

Return a reference to the substring from [Start, Start + N).

constexpr bool empty() const

empty - Check if the string is empty.

StringRef drop_front(size_t N=1) const

Return a StringRef equal to 'this' but with the first N elements dropped.

char back() const

back - Get the last character in the string.

StringRef slice(size_t Start, size_t End) const

Return a reference to the substring from [Start, End).

constexpr size_t size() const

size - Get the string size.

char front() const

front - Get the first character in the string.

size_t find_last_of(char C, size_t From=npos) const

Find the last character in the string that is C, or npos if not found.

constexpr const char * data() const

data - Get a pointer to the start of the string (which may not be null terminated).

size_t find_first_of(char C, size_t From=0) const

Find the first character in the string that is C, or npos if not found.

StringRef take_front(size_t N=1) const

Return a StringRef equal to 'this' but with only the first N elements remaining.

bool ends_with(StringRef Suffix) const

Check if this string ends with the given Suffix.

static constexpr size_t npos

Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...

bool isSingleStringRef() const

Return true if this twine can be dynamically accessed as a single StringRef value with getSingleStrin...

bool isTriviallyEmpty() const

Check if this twine is trivially empty; a false return value does not necessarily mean the twine is e...

StringRef toStringRef(SmallVectorImpl< char > &Out) const

This returns the twine as a single StringRef if it can be represented as such.

StringRef getSingleStringRef() const

This returns the twine as a single StringRef.

void toVector(SmallVectorImpl< char > &Out) const

Append the concatenated string into the given SmallString or SmallVector.

The instances of the Type class are immutable: once they are created, they are never changed.

static unsigned GetRandomNumber()

Get the result of a process wide random number generator.

Represents a temporary file.

Represents the result of a call to directory_iterator::status().

void replace_filename(const Twine &Filename, file_type Type, basic_file_status Status=basic_file_status())

Represents the result of a call to sys::fs::status().

const char * const_data() const

Get a const view of the data.

const_iterator & operator++()

bool operator==(const const_iterator &RHS) const

ptrdiff_t operator-(const const_iterator &RHS) const

Difference in bytes between this and RHS.

bool operator==(const reverse_iterator &RHS) const

ptrdiff_t operator-(const reverse_iterator &RHS) const

Difference in bytes between this and RHS.

reverse_iterator & operator++()

#define llvm_unreachable(msg)

Marks that the current location is not supposed to be reachable.

@ C

The default llvm calling convention, compatible with C.

value_type read(const void *memory, endianness endian)

Read a value of a particular endianness from memory.

bool is_regular_file(const basic_file_status &status)

Does status represent a regular file?

bool is_symlink_file(const basic_file_status &status)

Does status represent a symlink file?

void make_absolute(const Twine &current_directory, SmallVectorImpl< char > &path)

Make path an absolute path.

std::error_code openFileForReadWrite(const Twine &Name, int &ResultFD, CreationDisposition Disp, OpenFlags Flags, unsigned Mode=0666)

Opens the file with the given name in a write-only or read-write mode, returning its open file descri...

Error readNativeFileToEOF(file_t FileHandle, SmallVectorImpl< char > &Buffer, ssize_t ChunkSize=DefaultReadChunkSize)

Reads from FileHandle until EOF, appending to Buffer in chunks of size ChunkSize.

Expected< size_t > readNativeFile(file_t FileHandle, MutableArrayRef< char > Buf)

Reads Buf.size() bytes from FileHandle into Buf.

ErrorOr< perms > getPermissions(const Twine &Path)

Get file permissions.

std::error_code getPotentiallyUniqueFileName(const Twine &Model, SmallVectorImpl< char > &ResultPath)

Get a unique name, not currently exisiting in the filesystem.

std::error_code rename(const Twine &from, const Twine &to)

Rename from to to.

std::error_code openFileForRead(const Twine &Name, int &ResultFD, OpenFlags Flags=OF_None, SmallVectorImpl< char > *RealPath=nullptr)

Opens the file with the given name in a read-only mode, returning its open file descriptor.

bool is_other(const basic_file_status &status)

Does this status represent something that exists but is not a directory or regular file?

std::error_code access(const Twine &Path, AccessMode Mode)

Can the file be accessed?

std::error_code getPotentiallyUniqueTempFileName(const Twine &Prefix, StringRef Suffix, SmallVectorImpl< char > &ResultPath)

Get a unique temporary file name, not currently exisiting in the filesystem.

std::error_code status(const Twine &path, file_status &result, bool follow=true)

Get file status as if by POSIX stat().

bool exists(const basic_file_status &status)

Does file exist?

@ OF_Delete

The returned handle can be used for deleting the file.

file_type

An enumeration for the file system's view of the type.

std::error_code getUniqueID(const Twine Path, UniqueID &Result)

std::error_code createUniqueFile(const Twine &Model, int &ResultFD, SmallVectorImpl< char > &ResultPath, OpenFlags Flags=OF_None, unsigned Mode=all_read|all_write)

Create a uniquely named file.

std::error_code create_directory(const Twine &path, bool IgnoreExisting=true, perms Perms=owner_all|group_all)

Create the directory in path.

std::error_code remove(const Twine &path, bool IgnoreNonExisting=true)

Remove path.

@ CD_CreateAlways

CD_CreateAlways - When opening a file:

@ CD_CreateNew

CD_CreateNew - When opening a file:

void createUniquePath(const Twine &Model, SmallVectorImpl< char > &ResultPath, bool MakeAbsolute)

Create a potentially unique file name but does not create it.

std::error_code openFileForWrite(const Twine &Name, int &ResultFD, CreationDisposition Disp=CD_CreateAlways, OpenFlags Flags=OF_None, unsigned Mode=0666)

Opens the file with the given name in a write-only or read-write mode, returning its open file descri...

std::error_code create_directories(const Twine &path, bool IgnoreExisting=true, perms Perms=owner_all|group_all)

Create all the non-existent directories in path.

bool status_known(const basic_file_status &s)

Is status available?

std::error_code createTemporaryFile(const Twine &Prefix, StringRef Suffix, int &ResultFD, SmallVectorImpl< char > &ResultPath, OpenFlags Flags=OF_None)

Create a file in the system temporary directory.

file_type get_file_type(const Twine &Path, bool Follow=true)

Does status represent a directory?

std::error_code copy_file(const Twine &From, const Twine &To)

Copy the contents of From to To.

std::error_code createUniqueDirectory(const Twine &Prefix, SmallVectorImpl< char > &ResultPath)

ErrorOr< MD5::MD5Result > md5_contents(int FD)

Compute an MD5 hash of a file's contents.

std::error_code current_path(SmallVectorImpl< char > &result)

Get the current path.

static std::error_code copy_file_internal(int ReadFD, int WriteFD)

bool is_directory(const basic_file_status &status)

Does status represent a directory?

StringRef get_separator(Style style=Style::native)

Return the preferred separator for this platform.

StringRef root_path(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get root path.

void remove_filename(SmallVectorImpl< char > &path, Style style=Style::native)

Remove the last component from path unless it is the root dir.

bool has_relative_path(const Twine &path, Style style=Style::native)

Has relative path?

bool home_directory(SmallVectorImpl< char > &result)

Get the user's home directory.

StringRef stem(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get stem.

bool has_root_name(const Twine &path, Style style=Style::native)

Has root name?

void replace_extension(SmallVectorImpl< char > &path, const Twine &extension, Style style=Style::native)

Replace the file extension of path with extension.

const_iterator begin(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get begin iterator over path.

reverse_iterator rend(StringRef path LLVM_LIFETIME_BOUND)

Get reverse end iterator over path.

bool remove_dots(SmallVectorImpl< char > &path, bool remove_dot_dot=false, Style style=Style::native)

In-place remove any '.

bool has_root_path(const Twine &path, Style style=Style::native)

Has root path?

constexpr bool is_style_posix(Style S)

Check if S uses POSIX path rules.

StringRef parent_path(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get parent path.

bool has_parent_path(const Twine &path, Style style=Style::native)

Has parent path?

void make_preferred(SmallVectorImpl< char > &path, Style style=Style::native)

For Windows path styles, convert path to use the preferred path separators.

bool is_relative(const Twine &path, Style style=Style::native)

Is path relative?

StringRef remove_leading_dotslash(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Remove redundant leading "./" pieces and consecutive separators.

bool has_extension(const Twine &path, Style style=Style::native)

Has extension?

bool is_absolute_gnu(const Twine &path, Style style=Style::native)

Is path absolute using GNU rules?

StringRef filename(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get filename.

void system_temp_directory(bool erasedOnReboot, SmallVectorImpl< char > &result)

Get the typical temporary directory for the system, e.g., "/var/tmp" or "C:/TEMP".

std::string convert_to_slash(StringRef path, Style style=Style::native)

Replaces backslashes with slashes if Windows.

bool is_absolute(const Twine &path, Style style=Style::native)

Is path absolute?

bool has_stem(const Twine &path, Style style=Style::native)

Has stem?

constexpr bool is_style_windows(Style S)

Check if S uses Windows path rules.

StringRef root_name(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get root name.

StringRef root_directory(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get root directory.

bool replace_path_prefix(SmallVectorImpl< char > &Path, StringRef OldPrefix, StringRef NewPrefix, Style style=Style::native)

Replace matching path prefix with another path.

void append(SmallVectorImpl< char > &path, const Twine &a, const Twine &b="", const Twine &c="", const Twine &d="")

Append to path.

StringRef extension(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get extension.

bool has_filename(const Twine &path, Style style=Style::native)

Has filename?

reverse_iterator rbegin(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get reverse begin iterator over path.

const_iterator end(StringRef path LLVM_LIFETIME_BOUND)

Get end iterator over path.

bool is_separator(char value, Style style=Style::native)

Check whether the given char is a path separator on the host OS.

StringRef relative_path(StringRef path LLVM_LIFETIME_BOUND, Style style=Style::native)

Get relative path.

bool has_root_directory(const Twine &path, Style style=Style::native)

Has root directory?

void DontRemoveFileOnSignal(StringRef Filename)

This function removes a file from the list of files to be removed on signal delivery.

bool RemoveFileOnSignal(StringRef Filename, std::string *ErrMsg=nullptr)

This function registers signal handlers to ensure that if a signal gets delivered that the named file...

This is an optimization pass for GlobalISel generic memory operations.

detail::scope_exit< std::decay_t< Callable > > make_scope_exit(Callable &&F)

@ no_such_file_or_directory

@ operation_not_permitted

Error write(MCStreamer &Out, ArrayRef< std::string > Inputs, OnCuIndexOverflow OverflowOptValue)

OutputIt copy(R &&Range, OutputIt Out)

Error errorCodeToError(std::error_code EC)

Helper for converting an std::error_code to a Error.

std::error_code errnoAsErrorCode()

Helper to get errno as an std::error_code.

void consumeError(Error Err)

Consume a Error without doing anything.

Implement std::hash so that hash_code can be used in STL containers.