【问题标题】:`nix-build` fails because Python wants something that's unavailable, without saying what it wants`nix-build` 失败是因为 Python 想要一些不可用的东西,但没有说它想要什么
【发布时间】:2020-01-28 07:10:13
【问题描述】:

(至少我认为这是问题所在。)

错误

当我从 nixpkgs 的根目录运行 nix-build -A serialosc 时,nix 会打印以下内容:

[jeff@jbb-dell:~/nix/nixpkgs-fork]$ nix-build -A serialosc
these derivations will be built:
  /nix/store/p40wvn28grb8nrcd6scbxhhjqw4495kk-serialosc.drv
building '/nix/store/p40wvn28grb8nrcd6scbxhhjqw4495kk-serialosc.drv'...
unpacking sources
unpacking source archive /nix/store/5zj802wfjd0ima92lpzzsqdjqvrnrwf9-serialosc
source root is serialosc
patching sources
configuring
configure flags: --prefix=/nix/store/b6qzvzmwjdi29nnzc769904wc0mj1cds-serialosc configure
Setting top to                           : /build/serialosc 
Setting out to                           : /build/serialosc/build 

Checking for 'gcc' (C compiler)          : gcc 

Checking for working poll()              : yes 
Checking for libudev                     : yes 
Checking for libmonome                   : yes 
Checking for liblo                       : yes 
Checking for function strdup             : yes 
Checking for function _strdup            : not found 
Checking for function strndup            : yes 
Checking for function strcasecmp         : yes 
Checking for header unistd.h             : yes 
Checking for header dns_sd.h             : yes 
Checking for library dl                  : yes 

Traceback (most recent call last):
  File "/build/serialosc/.waf-1.8.5-3fc7b0f5070c04bfd3f2489448471a84/waflib/Scripting.py", line 103, in waf_entry_point
    run_commands()
  File "/build/serialosc/.waf-1.8.5-3fc7b0f5070c04bfd3f2489448471a84/waflib/Scripting.py", line 164, in run_commands
    ctx=run_command(cmd_name)
  File "/build/serialosc/.waf-1.8.5-3fc7b0f5070c04bfd3f2489448471a84/waflib/Scripting.py", line 155, in run_command
    ctx.execute()
  File "/build/serialosc/.waf-1.8.5-3fc7b0f5070c04bfd3f2489448471a84/waflib/Configure.py", line 92, in execute
    super(ConfigurationContext,self).execute()
  File "/build/serialosc/.waf-1.8.5-3fc7b0f5070c04bfd3f2489448471a84/waflib/Context.py", line 92, in execute
    self.recurse([os.path.dirname(g_module.root_path)])
  File "/build/serialosc/.waf-1.8.5-3fc7b0f5070c04bfd3f2489448471a84/waflib/Context.py", line 133, in recurse
    user_function(self)
  File "/build/serialosc/wscript", line 259, in configure
    stderr=devnull).decode().strip()
  File "/nix/store/lbrpma3528hq7gwn8ffbnwaxvsqah0bb-python-2.7.17/lib/python2.7/subprocess.py", line 216, in check_output
    process = Popen(stdout=PIPE, *popenargs, **kwargs)
  File "/nix/store/lbrpma3528hq7gwn8ffbnwaxvsqah0bb-python-2.7.17/lib/python2.7/subprocess.py", line 394, in __init__
    errread, errwrite)
  File "/nix/store/lbrpma3528hq7gwn8ffbnwaxvsqah0bb-python-2.7.17/lib/python2.7/subprocess.py", line 1047, in _execute_child
    raise child_exception
OSError: [Errno 2] No such file or directory
builder for '/nix/store/p40wvn28grb8nrcd6scbxhhjqw4495kk-serialosc.drv' failed with exit code 2
error: build of '/nix/store/p40wvn28grb8nrcd6scbxhhjqw4495kk-serialosc.drv' failed

[jeff@jbb-dell:~/nix/nixpkgs-fork]$ 

我的怀疑

问题似乎出现在lib/python2.7/subprocess.py。我在网上找到了a version of that file,而definition of _execute_child 似乎引用了一些绝对路径——例如,在这段话中:

    if shell:
        args = ["/bin/sh", "-c"] + args
        if executable:
            args[0] = executable

因此,我的猜测是 Nix 是在一个沙盒中构建的,它不提供 Python 所期望的任何东西。但错误并没有告诉我 Python 希望找到什么。

上下文

(您可能不需要此信息。)

我正在尝试在 NixOS 19.09 上build serialosc。这是我的fork of nixpkgs,包括我的broken recipe for serialosc。这个分支还包括我的libmonome 包,它可以工作,serialosc 依赖于它,它还不是官方nixpkgs 存储库的一部分。我已经给出了具体提交的硬链接;当我更新分叉时,它们不应该改变。

【问题讨论】:

  • 就个人而言,我会通过使用 sysdig 来跟踪失败的execve() 调用试图调用什么来调试它。 (在 NixOS 上,您可能需要小心使用哪个内核包——至少有一段时间,sysdig 无法使用 nixpkgs 中的默认内核构建;但希望现在已经修复,如果上游没有修复,它在任何情况下都是可修复的)。

标签: python-2.7 sandbox nix nixos


【解决方案1】:

交叉发布自 https://discourse.nixos.org/t/nix-build-fails-because-python-wants-something-thats-unavailable-without-saying-what-it-wants/5675/2 所以它可以帮助那些只找到这个的人,答案可能会在 NixOS 的话语中继续。我试图让它对一般的 NixOS 编写派生调试有所帮助,并带有一些 Python 位

fetchgit

首先,让我们帮助您解决食谱中的 fetchgit 部分

  src = fetchgit {
    # Once, it seemed to finish, and I don't know how! Then it crashed with:
    # Switched to a new branch 'fetchgit'
    # removing `.git'...
    # hash mismatch in fixed-output derivation '/nix/store/5zj802wfjd0ima92lpzzsqdjqvrnrwf9-serialosc':
    # wanted: sha256:1vqcxi32wc4pklbddllflkaigkfvd4ykwrjqccayvrk10dx1sna3
    # got:    sha256:1zmzjasv21ix7i7s58a31k0025ji32hv2jm2ww6s0xhjmr5ax34j

    # This way it [[gets pretty far]].
    # The fetchSubmodules value I set again seems to have no effect.
    url = https://github.com/monome/serialosc.git;
    rev = "v1.4.1";
    sha256 = "1zmzjasv21ix7i7s58a31k0025ji32hv2jm2ww6s0xhjmr5ax34j";

也许有强制推动?不知道为什么它会停止使用哈希

我发现 fetchSubmodules 没有任何效果,如果你有没有子模块的哈希,请使用 nix-prefetch-git --fetch-submodules https://github.com/monome/serialosc 给出

{
  "url": "https://github.com/monome/serialosc",
  "rev": "cec0ea76b2d5f69afa74d3ffc14a0950e32a7914",
  "date": "2019-06-09T21:46:13+02:00",
  "sha256": "03qkzslhih72idwafgfxmkwp5v3x048njh0c682phw2ks11plmbp",
  "fetchSubmodules": true
}

所以用

fetchgit {
  url = https://github.com/monome/serialosc;
  rev = "cec0ea76b2d5f69afa74d3ffc14a0950e32a7914";
  # or rev = version; but that might break with force pushes
  sha256 = "03qkzslhih72idwafgfxmkwp5v3x048njh0c682phw2ks11plmbp";
  fetchSubmodules = true;
}

wafHook

https://nixos.org/nixpkgs/manual/ 中有一个(少量)wafHook 文档

调试错误

它似乎想做git的东西,这是我调试它的方式:

$ nix-shell https://github.com/JeffreyBenjaminBrown/nixpkgs/archive/2bbd131811991bec9ae6b296b5cd1441640c306c.tar.gz -A serialosc --pure
nix-shell $ mkdir /tmp/delme-serialosc
nix-shell $ cd !$
# To find out what a build would do
nix-shell $ type genericBuild
...
# Doing the `if [ -z "${phases:-}" ]; then ...` bit gives us `echo $phases`
# unpackPhase patchPhase configurePhase buildPhase checkPhase installPhase fixupPhase installCheckPhase distPhase
nix-shell $ ${unpackPhase:-unpackPhase}
nix-shell $ cd $sourceRoot
nix-shell $ ${patchPhase:-patchPhase}
nix-shell $ ${configurePhase:-configurePhase}
# Error happens here
nix-shell $ type ${configurePhase:-configurePhase}
# Do the steps until you find it stops in `python ...`
# Python debug info: https://docs.python.org/3/library/pdb.html
nix-shell $ python -m pdb "$wafPath" "${flagsArray[@]}";
(Pdb) continue # or cont, or just c
...
(Pdb)  break /nix/store/lbrpma3528hq7gwn8ffbnwaxvsqah0bb-python-2.7.17/lib/python2.7/subprocess.py:1047
(Pdb) continue
> /nix/store/lbrpma3528hq7gwn8ffbnwaxvsqah0bb-python-2.7.17/lib/python2.7/subprocess.py(1047)_execute_child()
-> raise child_exception
(Pdb) up 
> /nix/store/lbrpma3528hq7gwn8ffbnwaxvsqah0bb-python-2.7.17/lib/python2.7/subprocess.py(394)__init__()
-> errread, errwrite)
(Pdb) # empty is equivalent to do last command, i.e. up in this case
> /nix/store/lbrpma3528hq7gwn8ffbnwaxvsqah0bb-python-2.7.17/lib/python2.7/subprocess.py(216)check_output()
-> process = Popen(stdout=PIPE, *popenargs, **kwargs)
(Pdb) print(popenargs)
(['git', 'rev-parse', '--verify', '--short', 'HEAD'],)

但是您会发现您可能需要想办法避免使用waf 使用git,因为它无法访问网络,除非它是一个固定输出派生(例如那些获取源)。希望关于fetchSubmodules 的内容能够解决它!

编辑:我没有读过它试图使用 git,它试图找出它是什么版本,你应该以某种方式让它避免使用 git 来做到这一点,例如grep -r 'rev-parse' 建议编辑 wscript 文件

编辑 2:例如像

--- wscript-old 2020-01-29 15:55:54.100976818 +0000
+++ wscript     2020-01-29 15:55:58.128977024 +0000
@@ -257,7 +257,7 @@
                conf.env.GIT_COMMIT = subprocess.check_output(
                        ["git", "rev-parse", "--verify", "--short", "HEAD"],
                        stderr=devnull).decode().strip()
-       except subprocess.CalledProcessError:
+       except (subprocess.CalledProcessError, OSError):
                conf.env.GIT_COMMIT = ''

        conf.define("VERSION", VERSION)

也许它也可以被上游化(在这种情况下,这会使 git commit ID 为空)?或者只是使用substituteInPlace 或其他东西来输入实际的提交ID

--- wscript-old 2020-01-29 15:55:54.100976818 +0000
+++ wscript     2020-01-29 15:57:56.177983054 +0000
@@ -249,16 +249,7 @@

        conf.env.VERSION = VERSION

-       try:
-               import os
-
-               devnull = open(os.devnull, 'w')
-
-               conf.env.GIT_COMMIT = subprocess.check_output(
-                       ["git", "rev-parse", "--verify", "--short", "HEAD"],
-                       stderr=devnull).decode().strip()
-       except subprocess.CalledProcessError:
-               conf.env.GIT_COMMIT = ''
+        conf.env.GIT_COMMIT = 'cec0ea76b2d5f69afa74d3ffc14a0950e32a7914'

        conf.define("VERSION", VERSION)
        conf.define("_GNU_SOURCE", 1)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-06-22
    • 1970-01-01
    • 2014-02-17
    • 2021-04-07
    • 2021-10-15
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多