Skip to content

Commit

Permalink
search: fix use of cps_path
Browse files Browse the repository at this point in the history
This must be @Prefix@ prefaced, and is used to describe how the prefix
is calculated when the cps file is passed by path, not to calculate a
prefix which is different than where the cps file is located.
  • Loading branch information
dcbaker committed Sep 11, 2024
1 parent 32c7865 commit 579313a
Show file tree
Hide file tree
Showing 6 changed files with 40 additions and 18 deletions.
6 changes: 3 additions & 3 deletions src/cps/loader.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
// Copyright © 2023-2024 Dylan Baker
// Copyright © 2024 Bret Brown
// Copyright © 2024 Dylan Baker
// SPDX-License-Identifier: MIT

#include "cps/loader.hpp"
Expand Down Expand Up @@ -293,8 +293,7 @@ namespace cps::loader {
auto const name = CPS_TRY(get_required<std::string>(root, "package", "name"));
auto const cps_version = CPS_TRY(get_required<std::string>(root, "package", "cps_version"));
auto const components = CPS_TRY(get_required<Components>(root, "package", "components"));
auto const cps_path =
CPS_TRY(get_optional<std::string>(root, "package", "cps_path")).value_or(filename.parent_path());
auto const cps_path = CPS_TRY(get_optional<std::string>(root, "package", "cps_path"));
auto const default_components =
CPS_TRY(get_optional<std::vector<std::string>>(root, "package", "default_components"));
auto const platform = std::nullopt; // TODO: parse platform
Expand All @@ -315,6 +314,7 @@ namespace cps::loader {
.cps_version = std::move(cps_version),
.components = std::move(components),
.cps_path = std::move(cps_path),
.filename = filename,
.default_components = std::move(default_components),
.platform = std::move(platform),
.require = std::move(require), // requires is a keyword
Expand Down
3 changes: 2 additions & 1 deletion src/cps/loader.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -135,7 +135,8 @@ namespace cps::loader {
// TODO: compat-version
// TODO: configuration
// TODO: configurations
std::string cps_path;
std::optional<std::string> cps_path;
std::string filename;
std::optional<std::vector<std::string>> default_components;
std::optional<Platform> platform;
Requires require; // Requires is a keyword
Expand Down
36 changes: 25 additions & 11 deletions src/cps/search.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -309,13 +309,27 @@ namespace cps::search {
}
}

fs::path calculate_prefix(const fs::path & path) {
fs::path calculate_prefix(const std::optional<std::string> & path, const fs::path & filename) {
// TODO: Windows
// TODO: /cps/<name-like>
std::vector<std::string> split = utils::split(std::string{path}, "/");
if (split.back() == "") {
split.pop_back();
if (path) {
fs::path p{path.value()};
if (p.stem() == "") {
p = p.parent_path();
}
fs::path f = filename.parent_path();
while (p != "@prefix@") {
utils::assert_fn(
p.stem() == f.stem(),
fmt::format("filepath and cps_path have non overlapping stems, prefix: {}, filename {}",
std::string{p}, std::string{f}));
p = p.parent_path();
f = f.parent_path();
}
return f;
}

std::vector<std::string> split = utils::split(std::string{filename.parent_path()}, "/");
if (split.back() == "cps") {
split.pop_back();
}
Expand All @@ -326,6 +340,7 @@ namespace cps::search {
if (split.back() == "lib") {
split.pop_back();
}

fs::path p{"/"};
for (auto && s : split) {
p /= s;
Expand Down Expand Up @@ -398,20 +413,19 @@ namespace cps::search {

result.version = root->data.package.version.value_or("unknown");

const auto prefix_path = [&]() -> std::optional<fs::path> {
if (prefix_variable) {
return fs::path{prefix_variable.value()};
}
return std::nullopt;
}();
const auto prefix_path =
prefix_variable.has_value() ? std::optional{fs::path{prefix_variable.value()}} : std::nullopt;

for (auto && node : flat) {

const auto prefix =
prefix_path.value_or(calculate_prefix(node->data.package.cps_path, node->data.package.filename));

const auto && prefix_replacer = [&](const std::string & s) -> std::string {
// TODO: Windows…
auto && split = utils::split(s, "/");
if (split[0] == "@prefix@") {
auto p = prefix_path.value_or(calculate_prefix(node->data.package.cps_path));
fs::path p = prefix;
for (auto it = split.begin() + 1; it != split.end(); ++it) {
p /= *it;
}
Expand Down
8 changes: 7 additions & 1 deletion tests/cases/cps-config.toml
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,13 @@ expected = "-I/err"
name = "prefix set"
cps = "cps-path-set"
args = ["flags", "--cflags-only-I", "--libs-only-l"]
expected = "-I/sentinel/err -l/sentinel/lib/libfoo.a"
expected = "-I{prefix}/err -l{prefix}/lib/libfoo.a"

[[case]]
name = "prefix set (called by path)"
cps = "{prefix}/cps-path-set.cps"
args = ["flags", "--cflags-only-I", "--libs-only-l"]
expected = "-I{prefix}/err -l{prefix}/lib/libfoo.a"

[[case]]
name = "prefix calculated"
Expand Down
2 changes: 1 addition & 1 deletion tests/cps-files/lib/cps/cps-path-set.cps
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"name": "cps-path-set",
"cps_version": "0.10.0",
"cps_path": "/sentinel/lib/cps/",
"cps_path": "@prefix@/lib/cps/",
"version": "1.0.0",
"components": {
"default": {
Expand Down
3 changes: 2 additions & 1 deletion tests/runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,8 @@ def unordered_compare(out, expected):
return sorted(out_parts) == sorted(expected_parts)

async def test(runner: str, case_: TestCase) -> Result:
cmd = [runner] + case_['args'] + [case_['cps']]
cmd = [runner] + case_['args']
cmd.append(case_['cps'].replace('{prefix}', os.path.join(PREFIX, 'lib/cps')))
if 'mode' in case_:
cmd.extend([f"--format={case_['mode']}"])

Expand Down

0 comments on commit 579313a

Please sign in to comment.