blob: ffe3e0301fa17e361f920b0365df119b595555df (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
|
// file : libbuild2/cc/utility.cxx -*- C++ -*-
// license : MIT; see accompanying LICENSE file
#include <libbuild2/cc/utility.hxx>
#include <libbuild2/file.hxx>
using namespace std;
namespace build2
{
namespace cc
{
using namespace bin;
const dir_path module_dir ("cc");
const dir_path module_build_dir (dir_path (module_dir) /= "build");
const dir_path module_build_modules_dir (
dir_path (module_build_dir) /= "modules");
void
normalize_header (path& f)
{
// Interestingly, on most paltforms and with most compilers (Clang on
// Linux being a notable exception) most system/compiler headers are
// already normalized.
//
path_abnormality a (f.abnormalities ());
if (a != path_abnormality::none)
{
// While we can reasonably expect this path to exit, things do go
// south from time to time (like compiling under wine with file
// wlantypes.h included as WlanTypes.h).
//
try
{
// If we have any parent components, then we have to verify the
// normalized path matches realized.
//
path r;
if ((a & path_abnormality::parent) == path_abnormality::parent)
{
r = f;
r.realize ();
}
try
{
f.normalize ();
// Note that we might still need to resolve symlinks in the
// normalized path.
//
if (!r.empty () && f != r && path (f).realize () != r)
f = move (r);
}
catch (const invalid_path&)
{
assert (!r.empty ()); // Shouldn't have failed if no `..`.
f = move (r); // Fallback to realize.
}
}
catch (const invalid_path&)
{
fail << "invalid header path '" << f.string () << "'";
}
catch (const system_error& e)
{
fail << "invalid header path '" << f.string () << "': " << e;
}
}
}
}
}
|