Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

forced slash replacement #41

Open
tbasnoopy opened this issue Apr 14, 2015 · 7 comments
Open

forced slash replacement #41

tbasnoopy opened this issue Apr 14, 2015 · 7 comments

Comments

@tbasnoopy
Copy link
Contributor

prerequisites

premake5.lua

local qt_bin_path = "C:/dev/mx/v1/dep/qt/qt_33_x64_bin"

solution "myTestSln"
  location "testfiles/sln"

  platforms "x64"
  configurations "release"
  project "myTestPrj1"
    kind "Utility"
    files (qt_bin_path.."/bin/QtDeclarative_sofistik33_x64_4.dll")

    filter "files:**/*.dll"
      buildmessage ([[%{file.name} (copy)]])
      buildcommands [[xcopy /y "%{file.path:gsub("/","\\")}" "bla"]]
      buildoutputs ("bla")
    filter "*"

Problem
The resulting path can be an absolute and all "" in the path are replaced by "/". There is - afaik - no possibility to change the slashes and not all Windows tools - like xcopy - can handle paths with "/".

Cause
If premake is detecting absolute paths in non path variables, they are replaced by relative paths. This is not possible all the time (not sure but here can be a bug, too). It's never possible on Windows system where files are placed over different Partitions (C:; D:).

detoken.lua:66

local isAbs = path.isabsolute(result)
if isAbs and not field.paths and basedir then
  result = path.getrelative(basedir, result)
end

The path.getrelative function calls path.normalize which replaces all the "" to "/". This is not the system specification but required for further processing in premake.

path_normalize.c:30

if (ch == '\\') {
  ch = '/';
}

possible Solution
Allow avoiding path fixing.

detoken.lua:66

local isAbs = path.isabsolute(result)
if type(result) == "string" and result:find("!$") then
  result = result:match("(.-)!$"):gsub("/","\\")
elseif isAbs and not field.paths and basedir then
  result = path.getrelative(basedir, result)
end

premake5.lua (part replacement)

buildcommands [[xcopy /y "%{file.path.."!"}" "bla"]]

Or is there a way I didn't see?

@starkos
Copy link
Member

starkos commented Apr 14, 2015

A couple of things mixed up here; let's use this ticket to address the path separators and open another for the relative path logic if needed.

Premake specifies that all paths should use forward slashes, so let's take that as a given, and that path.normalize() is doing the right thing.

Translating separators in commands can sometimes be an issue even when you are not using tokens, e.g. trying to launch an executable on a relative path across different platforms. So ideally a more general solution would be best.

One solution similar to yours is to wrap it with a path.translate(), like your gsub(). We could make a shortcut for it and place it in the token environment, so maybe do something like:

buildcommands [[xcopy /y "%{T(file.path)}" "bla"]]

That helper could even have a bit of additional logic to try to determine which separator is appropriate for the target.

Makefiles are tricky because they can technically target multiple platforms now. But we can punt and just use the target OS until someone wants to tackle that fully.

@starkos
Copy link
Member

starkos commented Apr 14, 2015

Oh, and an example of the relative executable would be

buildcommands [[%{T("../bin/cg")} "bla"]]

@tbasnoopy
Copy link
Contributor Author

No need for another ticket for relative path logic from my side.

How can we detect which separator is appropriate for the target platform?

I've written a short test:

function T(p)
  return p:gsub("/","\\")
end

buildcommands [[xcopy /y "%{T(file.path)}" "bla"]],

But this doesn't work. I didn't take an exact look on that but i think the same logic (detoken.lua:66) which breaks my gsub is breaking this, too.

If we want to avoid this issue we have to change this function (detoken.lua:66) in some way. But I think i do not understand how you think this should happen.

@starkos
Copy link
Member

starkos commented Apr 15, 2015

How can we detect which separator is appropriate for the target platform?

os.is("windows") should do it.

I'm a little concerned about building this into the token expander since we don't necessarily know the context in which the path is being used? I don't have a great solution off the top of my head.

@TurkeyMan
Copy link
Contributor

xbox, xbox360, xbone all use windows slash too...

@tbasnoopy
Copy link
Contributor Author

I meant something like an cool api call: system_get_path_seperator. But I think there is no system comprehensive call.

@starkos : Which case could be a problem? In the most cases the path is good... or not. But I have not clue which cases can occur.

@Jarod42
Copy link
Contributor

Jarod42 commented Sep 4, 2024

https://premake.github.io/docs/Tokens/#path-in-commands
%[..] handles path in commands string.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants