0

My Python project works correctly on Windows but it encounters bugs on WSL2. I have done some debugging and finally localized the error to a compatibility problem. That is, in WSL2, Python's native functions os.rename() and os.replace() cannot deal with files on a mounted ReFS drive well, and PermissionError occurs.

For example, we have a ReFS drive F and a file F:\text.txt on Windows. Then, F: will be mounted to WSL2 as /mnt/f and the file path is /mnt/f/text.txt. The test with PermissionError is:

import os
with open('/mnt/f/text.txt','w'):
    pass

assert os.path.exists('/mnt/f/text.txt')

try:
    os.rename('/mnt/f/text.txt','/mnt/f/text2.txt')
except PermissionError as e:
    print(e)
# [Errno 1] Operation not permitted: '/mnt/f/text.txt' -> '/mnt/f/text2.txt'

try:
    os.replace('/mnt/f/text.txt','/mnt/f/text2.txt')
except PermissionError as e:
    print(e)
# [Errno 1] Operation not permitted: '/mnt/f/text.txt' -> '/mnt/f/text2.txt'

os.remove('/mnt/f/text.txt') # passed
assert not os.path.exists('/mnt/f/text.txt')

But, if we turn to a normal NTFS drive, such as X:, and the test with no bug is:

import os
with open('/mnt/x/text.txt','w'):
    pass

assert os.path.exists('/mnt/x/text.txt')

try:
    os.rename('/mnt/x/text.txt','/mnt/x/text2.txt')
except PermissionError as e:
    print(e)

with open('/mnt/x/text.txt','w'):
    pass

assert os.path.exists('/mnt/x/text.txt')

try:
    os.replace('/mnt/x/text.txt','/mnt/x/text3.txt')
except PermissionError as e:
    print(e)

assert not os.path.exists('/mnt/x/text.txt')
os.remove('/mnt/x/text2.txt') 
assert not os.path.exists('/mnt/x/text2.txt')
os.remove('/mnt/x/text3.txt') 
assert not os.path.exists('/mnt/x/text3.txt')

So, the conclusions from the above tests are:

  1. WSL2 and its Python do not completely support ReFS
  2. In the Python run on WSL2, os.rename() and os.replace() do not support files in a ReFS drive that mounted to WSL2
  3. os.remove() is supported.
  4. When it comes to NTFS drive, all the above operations are supported.

To solve the problem, I have tried the following 2 methods but they both do not work respectively:

  1. modify /etc/wsl.conf by adding:
    [automount]
    options = "metadata,umask=22,fmask=11"
    
    and then restart WSL2.
  2. re-mount target drive by arg noperm
    sudo umount /mnt/f
    sudo mount -t drvfs F: /mnt/f -o noperm
    

So, how to fix it? How can I rename files in a Windows ReFS dive that is mounted to WSL2?

Thanks in advance.

Little Train
  • 707
  • 2
  • 11

0 Answers0