在FreeBSD下的错误目录下启动 [英] Make starts in wrong directory under FreeBSD

查看:65
本文介绍了在FreeBSD下的错误目录下启动的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个非常简单的Makefile,可以将它打包为另一个Makefile:

I have a very simple Makefile that just shells out to another Makefile:

all:
    cd src && make all

我的目录结构(Makefile在顶级目录中):

My directory structure (the Makefile is in the top-level directory):

[I] mqudsi@php ~/bbcp> tree -d
.
├── bin
│   └── FreeBSD
├── obj
│   └── FreeBSD
├── src
└── utils

这在Linux上可以正常工作,但是在FreeBSD下,它会给出有关找不到src的错误.

This works just fine under Linux, but under FreeBSD, it gives an error about src not being found.

要进行调试,我将Makefile命令更新为pwd; cd src && make all,当我在顶级目录中运行make时,我发现以某种方式,它正在./obj下执行,表示它正在寻找./obj/src/cd进入.

To debug, I updated the Makefile command to pwd; cd src && make all and I discovered that somehow when I run make in the top-level directory, it is being executed under ./obj instead, meaning it's looking for ./obj/src/ to cd into.

除了我不知道为什么要这么做的事实外,我想肯定可以在FreeBSD下调用gmake而不是make来解决这个问题,但是事实并非如此(我我松了口气,因为我不敢相信BSD品牌和GNU品牌之间在核心操作方面会有巨大的差异.

Aside from the fact that I have no clue why it's doing that, I presumed for sure that calling gmake instead of make under FreeBSD would take care of it, but that wasn't the case (and I'm relieved, because I can't believe there is that huge of a difference between BSD make and GNU make in terms of core operation).

奇怪的是,删除obj可使一切正常运行.因此,在存在obj目录的情况下,make cds首先进入./obj.否则它将按照您的期望执行.

The odd thing is, deleting obj makes everything work perfectly. So in the presence of an obj directory, make cds into ./obj first; otherwise it executes as you'd expect it to.

推荐答案

在这里回答我自己的问题.

Answering my own question here.

从FreeBSD make手册页:

From the FreeBSD make man page:

.OBJDIR      A path to the directory where the targets are built.  Its
             value is determined by trying to chdir(2) to the follow-
             ing directories in order and using the first match:

             1.   ${MAKEOBJDIRPREFIX}${.CURDIR}

              (Only if `MAKEOBJDIRPREFIX' is set in the environ-
              ment or on the command line.)

             2.   ${MAKEOBJDIR}

              (Only if `MAKEOBJDIR' is set in the environment or
              on the command line.)

             3.   ${.CURDIR}/obj.${MACHINE}

             4.   ${.CURDIR}/obj

             5.   /usr/obj/${.CURDIR}

             6.   ${.CURDIR}

             Variable expansion is performed on the value before it's
             used, so expressions such as
               ${.CURDIR:S,^/usr/src,/var/obj,}
             may be used.  This is especially useful with
             `MAKEOBJDIR'.

             `.OBJDIR' may be modified in the makefile via the special
             target `.OBJDIR'.  In all cases, make will chdir(2) to
             the specified directory if it exists, and set `.OBJDIR'
             and `PWD' to that directory before executing any targets.

关键部分是

在所有情况下,make都会将chdir(2)到指定目录(如果存在),并在执行任何目标之前将.OBJDIR' PWD'设置为该目录.

In all cases, make will chdir(2) to specified directory if it exists, and set .OBJDIR'PWD' to that directory before executing any targets.

相比之下, GNU make手册页没有这样的内容引用OBJDIR的任何种类的自动确定,只有在设置了它后才使用.

By contrast, the GNU make manual page makes no such reference to any sort of automatic determination of OBJDIR, only that it will be used if it is set.

解决方案是通过伪目标.OBJDIR覆盖OBJDIR变量:

The solution was to override the OBJDIR variable via the pseudotarget .OBJDIR:

.OBJDIR: ./

all:
    cd src && make
clean:
    cd src && make clean

另一种解决方案是在cd目标前面加上${CURDIR},在chdirOBJDIR之后不会对其进行修改.

An alternative solution is to prefix the cd targets with ${CURDIR}, which isn't modified after the chdir into OBJDIR.

我不明白为什么gmake表现出相同的方式.对我来说,这简直像是个虫子.

I don't get why gmake behaved the same way, however. That feels almost like a bug to me.

这篇关于在FreeBSD下的错误目录下启动的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆