преобразование пути msys (или cygpath для msys?)

мне нужно передать /защ:с:путь_к_файлубиблиотеки MyLib.параметр командной деф" строки из bash-скрипт для MS компилятора/линкера. Путь генерируется как часть процесса сборки сценарием bash. В принципе, аргумент, который передает мой скрипт:

-DEF:/c/filepath/myLib.def

преобразование пути MSYS Не могу справиться с этим должным образом, потому что он не понимает /DEF: часть. Это работает, если я делаю

-DEF=/c/filepath/myLib.def

но тогда ms tools не понимает этот параметр. Короче говоря, каков правильный способ напишите этот параметр в MSYS bash, чтобы он преобразовал его в правильный аргумент?

на cygwin я мог бы использовать cygpath, но нет эквивалента, потому что кто-то из msys думает, что это не нужно (даже если есть скрипты для cygwin, который использует cygpath).

7 ответов


Обновление (Август-2016):

этот вопрос уже не актуален, так как msys2 С cygpath в его установке.

...

я подытожу свои исследования здесь.

на cygpath эквивалент в MSYS-использовать эту команду:

{ cd /c/some/path && pwd -W; } | sed 's|/|\|g'

проблема с этим подходом заключается в том, что он требует существующего пути, например c:\some\path должен быть существующий каталог; однако, настоящий cygpath поддерживает пути, которые не существуют.

Итак, если вам нужно получить путь к каталогу, который не существует, то вы можете вернуться к преобразованию sed пути:

{ cd 2>/dev/null /c/some/path && pwd -W ||
  echo /c/some/path | sed 's|^/\([a-z,A-Z]\)/|:/|'; } | sed 's|/|\|g'

полный рот слэшей есть, чтобы удовлетворить правила цитирования sed. Итак, если c:\some\path не существует на вашем ПК, он попытается преобразовать вперед В назад косые черты и заменить /c/ С c:\ (или любая другая буква диска). Единственным недостатком этого является то, что он не корректно работают несуществующие пути, содержащие смонтированный компонент, например /bin/does-not-exist или /usr/bin/does-not-exist.

еще один подход-использовать cygpath от cygwin в MSYS. Похоже, что cygwin устанавливает глобальную переменную среды CYGPATH, то есть вы можете использовать ее из обычного cmd.exe:

%CYGPATH% -w /c/some/path
C:\some\path

или от MSYS:

$CYGPATH -w /c/some/path
C:\some\path

до тех пор, пока вы установите точку /c to /cygdrive/c в cygwin. Но этот подход напечатает вас /usr находится в cygwin установка, а не в MSYS.

короче говоря, я думаю, что msys действительно должен включать реальный cygpath в набор инструментов по умолчанию только для некоторых случаев, которые не обрабатываются автоматически логикой преобразования аргументов командной строки msys


Я использую это с msysgit:

winpath() {
    if [ -z "" ]; then
        echo "$@"
    else
        if [ -f "" ]; then
            local dir=$(dirname "")
            local fn=$(basename "")
            echo "$(cd "$dir"; echo "$(pwd -W)/$fn")" | sed 's|/|\|g';
        else
            if [ -d "" ]; then
                echo "$(cd ""; pwd -W)" | sed 's|/|\|g';
            else
                echo "" | sed 's|^/\(.\)/|:\|g; s|/|\|g';
            fi
        fi
    fi
}

подобно Дмитрию-Рубинштейну@ выше, я немного очистил код и добавил обратное преобразование.

winpath() {
    if [ ${#} -eq 0 ]; then
        : skip
    elif [ -f "" ]; then
        local dirname=$(dirname "")
        local basename=$(basename "")
        echo "$(cd "$dirname" && pwd -W)/$basename" \
        | sed \
          -e 's|/|\|g';
    elif [ -d "" ]; then
        echo "$(cd "" && pwd -W)" \
        | sed \
          -e 's|/|\|g';
    else
        echo "" \
        | sed \
          -e 's|^/\(.\)/|:\|g' \
          -e 's|/|\|g'
    fi
}

unixpath() {
    echo "" \
    | sed -r \
      -e 's/\/\//g' \
      -e 's/^([^:]+):/\//'
}

использовать pwd -W

или скачать cygpath для msys отсюда http://mingw.5.n7.nabble.com/enhanced-version-of-cygpath-td28556.html

и использовать cygpath -wa


мой bash foo слаб, и я не мог заставить regexes работать в bash 3.1, поэтому я взломал скрипт perl для него:

#!/bin/env perl
use strict;

my @r;
foreach my $e (@ARGV) {
 $e=~s/\//\/g;
 $e=~s/^\([A-Za-z])\/:\/;
 push @r, $e;
}

print join(" ", @r);

префикса msys cygpath

программа

эта программа преобразует путь DOS в путь UNIX и наоборот

#!/bin/env perl
# DOS to UNIX path conversion
# © John S. Peterson. License GNU GPL 3.
use strict;
use Getopt::Std;

# usage
if ($#ARGV == -1) {
    print 'Usage: cygpath (-w) NAME...

Convert Unix and Windows format paths

Output type options:

  -w, --windows         print Windows form of NAMEs (C:\WINNT)
';
    exit 0;
}

# option
my %opt;
getopts('w', \%opt);

# convert path
my @r;
foreach my $e (@ARGV) {
    if ($opt{w}) {
        # add drive letter suffix
        $e =~ s,^\/([A-Za-z])\/,:\/,;
        $e =~ s,\/,\,g;

    } else {
        $e =~ s,\,\/,g;
        # add leading slash
        $e = "/$e";
        # remove drive letter suffix
        $e =~ s,:,,;
    }

    push @r, $e;
}

print join("\n", @r);

по сравнению с Cygwin cygpath

выход из этой программы лучше, чем выход из Cygwin cygpath В MSYS потому что

  • Cygwin cygpath удалите Cygwin home из преобразованного пути, f.e.
cygpath "$CYGWIN/usr/local/bin"
/usr/local/bin

что является проблемой, потому что

  • это иногда полезно преобразовать путь DOS Cygwin в путь UNIX с целью копирования файлов из Cygwin в MSYS

эта программа не удаляет Cygwin home

cygpath "$CYGWIN/usr/local/bin"
/c/file/program/cygwin/usr/local/bin

по сравнению с автоматическим преобразованием пути MSYS

преобразование ручного пути используется в MSYS, потому что

  • автоматическое преобразование пути является недостаточным

для F.е.


Как насчет этого ? cmd //c echo <your path>

это может не работать всегда, но это самый короткий, который я нашел