MinGW下Makefile的shell命令路径异常:为何调用Windows的find而非GNU find?
MinGW bash中GNUWin32 Make路径查找异常问题解析
问题场景
给定Makefile内容:
.PHONY: all all: $(shell find example/data) @echo $(shell which find)
在MinGW bash shell中使用GNUWin32 Make运行该Makefile,输出如下:
$ make FIND: Parameter format not correct /usr/bin/find
出现明显异常:
- 错误提示
FIND: Parameter format not correct来自Windows系统自带的C:\Windows\system32\find.exe $(shell find example/data)调用的是Windows系统的find工具,但$(shell which find)却返回MinGW的GNU find路径/usr/bin/find
原因解析
核心问题在于Make的$(shell)命令和MinGW bash的环境变量PATH不一致:
- GNUWin32 Make并不是通过MinGW bash来执行
$(shell)里的命令,而是直接调用Windows系统的进程创建接口(CreateProcess)启动程序。 - MinGW bash启动时会自行修改自身的PATH环境变量,把MinGW工具所在的
/usr/bin目录放到系统默认PATH(比如C:\Windows\system32)的前面,但GNUWin32 Make继承的是Windows系统原始的PATH设置,而非bash修改后的PATH。 - Windows默认PATH中
C:\Windows\system32的优先级高于MinGW的/usr/bin,所以Make执行$(shell find)时会先找到Windows自带的find.exe;而which find是在MinGW bash环境下执行的,bash会用自己修改后的PATH查找,因此返回GNU find的路径。
解决方法(让$(shell find)与bash直接执行find行为一致)
这里提供几种无需硬编码路径的方案:
- 方案一:在bash中先导出修改后的PATH,再启动Make
在MinGW bash中执行以下命令:
这样Make会继承bash修改后的PATH,优先查找MinGW的工具。export PATH="$PATH" make - 方案二:在Makefile中显式调整PATH顺序
修改Makefile,把MinGW工具目录放到PATH最前面:PATH := /usr/bin:$(PATH) .PHONY: all all: $(shell find example/data) @echo $(shell which find) - 方案三:指定Make使用MinGW bash执行shell命令
在Makefile中设置SHELL变量,让Make通过bash来执行所有shell相关操作:SHELL := /bin/bash .PHONY: all all: $(shell find example/data) @echo $(shell which find)
内容的提问来源于stack exchange,提问作者Jason C
相关产品推荐
相关产品推荐

