Repository: conda/conda-build

Issue:
Invalid cross-device-link
Example output:
```bash
INFO:conda_build.build:Packaging <...>
number of files: 63
Fixing permissions
Traceback (most recent call last):
  File "./build.py", line 599, in build_single
    built = cb.api.build(RECIPE, **bargs)
  File "$CONDA_ROOT/lib/python3.6/site-packages/conda_build/api.py", line 185, in build
    need_source_download=need_source_download, config=config, variants=variants)
  File "$CONDA_ROOT/lib/python3.6/site-packages/conda_build/build.py", line 1782, in build_tree
    notest=notest,
  File "$CONDA_ROOT/lib/python3.6/site-packages/conda_build/build.py", line 1241, in build
    built_package = bundlers[output_d.get('type', 'conda')](output_d, m, env)
  File "$CONDA_ROOT/lib/python3.6/site-packages/conda_build/build.py", line 719, in bundle_conda
    files = post_process_files(metadata, initial_files)
  File "$CONDA_ROOT/lib/python3.6/site-packages/conda_build/build.py", line 656, in post_process_files
    croot=m.config.croot)
  File "$CONDA_ROOT/lib/python3.6/site-packages/conda_build/post.py", line 444, in post_build
    make_hardlink_copy(f, prefix)
  File "$CONDA_ROOT/lib/python3.6/site-packages/conda_build/post.py", line 517, in make_hardlink_copy
    os.rename(os.path.join(dest, fn), path)
OSError: [Errno 18] Invalid cross-device link: '/tmp/tmpg6gbg6di/libgcc_s.so' -> '$PREFIX/lib/libgcc_s.so'
```
I bisected the issue to 9914f397053312172feb4bc9f312adbe98b0ae3c

The issue seems to appear when packing runtime libraries with always_include_files e.g. libgcc, libllvm, libmpich, ...

**meta.yaml**
```yaml
<...>
build:
  always_include_files:
     - lib/libgcc_s.so
     - <...>
```

No issue with 3.0.25, but issues since 3.0.26.
Maybe related: https://github.com/conda/conda-build/issues/1659
Thanks.


Discussion:
Sorry, I think I introduced this at https://github.com/conda/conda-build/pull/2437/commits/9914f397053312172feb4bc9f312adbe98b0ae3c#diff-60400bbbdb51124a0a8a06ca17ecec5cR517

I think the change from ``utils.copy_into`` to ``os.rename`` is responsible.

Since this is hard to test (creating volumes), do you mind making that small change and letting me know if that's the appropriate fix?  The diff is:

```
diff --git a/conda_build/post.py b/conda_build/post.py
index d22eafd5..4912c5f8 100644
--- a/conda_build/post.py
+++ b/conda_build/post.py
@@ -514,7 +514,7 @@ def make_hardlink_copy(path, prefix):
             # remove old file
             utils.rm_rf(path)
             # rename copy to original filename
-            os.rename(os.path.join(dest, fn), path)
+            utils.copy_into(os.path.join(dest, fn), path)


 def get_build_metadata(m):
```
@msarahan 

Yep tested on a few recipes, and the patch fixes the issue. I leave it up to you for PRing the patch.

Thanks !!



Resolving patch:
diff --git a/conda_build/post.py b/conda_build/post.py
--- a/conda_build/post.py
+++ b/conda_build/post.py
@@ -514,7 +514,9 @@ def make_hardlink_copy(path, prefix):
             # remove old file
             utils.rm_rf(path)
             # rename copy to original filename
-            os.rename(os.path.join(dest, fn), path)
+            #   It is essential here to use copying (as opposed to os.rename), so that
+            #        crossing volume boundaries works
+            utils.copy_into(os.path.join(dest, fn), path)
 
 
 def get_build_metadata(m):


Test patch: