Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Properly detect failing fallocate #79

Closed
vadimcomanescu opened this issue Jun 2, 2014 · 4 comments
Closed

Properly detect failing fallocate #79

vadimcomanescu opened this issue Jun 2, 2014 · 4 comments

Comments

@vadimcomanescu
Copy link

The check for CAN_FALLOCATE in whisper.py assumes that if it can import ctypes.util it can fallocate. This assumption is not all the time valid, since on most solaris based operating systems running ZFS will fail. I believe the assumption is not correct.

@pcn
Copy link

pcn commented Jun 2, 2014

Can you provide a stand-alone test case that someone could run on an opensolaris vm or something?

@reynir
Copy link

reynir commented Nov 20, 2015

I can confirm that fallocate will fail on ZFS on Solaris 11.1. It seems to work fine in Solaris 11.3 with ZFS, though.

try:
  import ctypes
  import ctypes.util
  CAN_FALLOCATE = True
except ImportError:
  CAN_FALLOCATE = False

fallocate = None

if CAN_FALLOCATE:
  libc_name = ctypes.util.find_library('c')
  libc = ctypes.CDLL(libc_name)
  c_off64_t = ctypes.c_int64
  c_off_t = ctypes.c_int

  try:
    _fallocate = libc.posix_fallocate64
    _fallocate.restype = ctypes.c_int
    _fallocate.argtypes = [ctypes.c_int, c_off64_t, c_off64_t]
  except AttributeError:
    try:
      _fallocate = libc.posix_fallocate
      _fallocate.restype = ctypes.c_int
      _fallocate.argtypes = [ctypes.c_int, c_off_t, c_off_t]
    except AttributeError:
      CAN_FALLOCATE = False

  if CAN_FALLOCATE:
    def _py_fallocate(fd, offset, len_):
      res = _fallocate(fd.fileno(), offset, len_)
      if res != 0:
        raise IOError(res, 'fallocate')
    fallocate = _py_fallocate
  del libc
  del libc_name

# The actual test
fd = open("test", "w")
fallocate(fd, 0, 4096)

From the posix_fallocate man page on Solaris 11.1:

NOTES
     The posix_fallocate() function is supported only for regular
     files  residing  on UFS filesystems. Attempts to use it with
     files on any other filesystem  type  results  in  an  EINVAL
     error.

The same comment is in the Solaris 11.2 man page.

@reynir
Copy link

reynir commented Nov 23, 2015

As the fallocate support is per filesystem I don't see how you could detect if fallocate is supported in advance. One solution could be to try to use fallocate, and if EINVAL is returned (thrown) then resort to using non-fallocate methods. It's perhaps not the most elegant solution.

@stale
Copy link

stale bot commented Apr 13, 2020

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

@stale stale bot added the stale label Apr 13, 2020
@stale stale bot closed this as completed Apr 20, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants