laze icon indicating copy to clipboard operation
laze copied to clipboard

Windows platform, path separator in rspfile contain backslash

Open Merisy-Thing opened this issue 8 months ago • 3 comments

Windows platform(Win10) with arm-none-eabi-gcc, path separator in rspfile(.rsp) contain backslash, this will cause the gcc can't find the obj file when linking.

rule:

      - name: LINK
        description: LINK ${out}
        in: "obj"
        out: "elf"
        rspfile: $out.rsp
        rspfile_content: ${in}
        cmd: ${CC} ${LDFLAGS} @${out}.rsp ${LIBS} -o ${out}

rspfile(.rsp)

project/build_laze/objects\builder-mcu\src/input/net.obj
--------------------------^-----------^

gcc error:

arm-none-eabi-gcc: error: project/build_laze/objectsbuilder-mcusrc/input/net.obj: No such file or directory
---------------------------------------------------^-----------^

These backslash was from Utf8PathBuf.push() method( srcpath.push(source) ), In src\generate.rs

            // now for each source file,
            for source in module.sources.iter().chain(optional_sources.iter()) {
                // 1. determine full file path (relative to project root)
                let mut srcpath = srcdir.clone();
                srcpath.push(source);

This is the test I have try:

------------------------------- src/generate.rs -------------------------------
index 12bab25..0bae908 100644
@@ -885,6 +885,16 @@ fn configure_build(
                 }
                 object.push(out);
 
+                if let Some(options) = rule.options.as_ref() {
+                    if let Some(value) = options.get("path-slash") {
+                        if value == "unix" {
+                            object = object.as_str().replace("\\", "/").into();
+                        } else if value == "win" {
+                            object = object.as_str().replace("/", "\\").into();
+                        }
+                    }
+                }

                 // 4. render ninja "build:" snippet and add to this build's
                 // ninja statement set
                 let build = NinjaBuildBuilder::from_rule(ninja_rule)
    rules:
      - name: CC
        description: CC ${out}
        in: "c"
        out: "obj"
        sharable: false
        options:
          path-slash: unix
        cmd: ${CC} -c ${CFLAGS} ${C_DEFS} ${COMMON_INC} ${includes} ${in} -o ${out}

Merisy-Thing avatar Apr 16 '25 01:04 Merisy-Thing

Thanks for the report! Yeah there's probably more spots where unix slashes are used. I'm on leave this week, will try to come up with a fix next week.

kaspar030 avatar Apr 16 '25 08:04 kaspar030

Ok, I actually see two issues here:

  1. laze itself sometimes uses / separators, understands both, but then mixes them by using push() on unix paths on windows. This leads to mixes paths (like in your case), which just don't work. I think paths can be "normalized" to one form by splitting into components and re-assembling. I'm experimenting with that in #708. It does require creating a new (Utf8)PathBuf for every path, so there might be a slight performance hit. I think I'll do that only on windows.

  2. gcc on windows does accept \ (windows style paths) when used directly on the command line, but not in an rspfile. Even a fully windows path in there is not accepted. So we need a way to pass in a unix path, probably conditionally. For 2., I'm not familiar enough with Windows tooling. Would it be an option to just always use unix style paths? I guess not... :/

kaspar030 avatar Apr 23 '25 09:04 kaspar030

For me, using GCC for cross-compile ARM targets on the windows platform, I always use the unix style path and never encountered any problems.

Merisy-Thing avatar Apr 27 '25 07:04 Merisy-Thing