0.4.27-38-g36ecbf9.update-magic-compat-py.patch 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198
  1. Subject: Update magic/compat.py
  2. Origin: upstream, commit 0.4.27-38-g36ecbf9 <https://github.com/ahupp/python-magic/commit/0.4.27-38-g36ecbf9>
  3. Author: Adam Hupp <adam@hupp.org>
  4. Date: Mon Aug 5 09:24:16 2024 -0700
  5. Forwarded: not-needed
  6. This pulls changes from https://github.com/file/file, commit
  7. 512840337ead1076519332d24fefcaa8fac36e06
  8. --- a/.gitignore
  9. +++ b/.gitignore
  10. @@ -11,3 +11,4 @@
  11. *.pyc
  12. *~
  13. dist/
  14. +.vscode/
  15. --- a/magic/compat.py
  16. +++ b/magic/compat.py
  17. @@ -4,14 +4,12 @@
  18. Python bindings for libmagic
  19. '''
  20. -import ctypes
  21. -
  22. +import threading
  23. from collections import namedtuple
  24. from ctypes import *
  25. from ctypes.util import find_library
  26. -
  27. from . import loader
  28. _libraries = {}
  29. @@ -45,13 +43,19 @@
  30. MAGIC_NO_CHECK_BUILTIN = NO_CHECK_BUILTIN = 4173824
  31. +MAGIC_PARAM_INDIR_MAX = PARAM_INDIR_MAX = 0
  32. +MAGIC_PARAM_NAME_MAX = PARAM_NAME_MAX = 1
  33. +MAGIC_PARAM_ELF_PHNUM_MAX = PARAM_ELF_PHNUM_MAX = 2
  34. +MAGIC_PARAM_ELF_SHNUM_MAX = PARAM_ELF_SHNUM_MAX = 3
  35. +MAGIC_PARAM_ELF_NOTES_MAX = PARAM_ELF_NOTES_MAX = 4
  36. +MAGIC_PARAM_REGEX_MAX = PARAM_REGEX_MAX = 5
  37. +MAGIC_PARAM_BYTES_MAX = PARAM_BYTES_MAX = 6
  38. +
  39. FileMagic = namedtuple('FileMagic', ('mime_type', 'encoding', 'name'))
  40. class magic_set(Structure):
  41. pass
  42. -
  43. -
  44. magic_set._fields_ = []
  45. magic_t = POINTER(magic_set)
  46. @@ -103,6 +107,14 @@
  47. _errno.restype = c_int
  48. _errno.argtypes = [magic_t]
  49. +_getparam = _libraries['magic'].magic_getparam
  50. +_getparam.restype = c_int
  51. +_getparam.argtypes = [magic_t, c_int, c_void_p]
  52. +
  53. +_setparam = _libraries['magic'].magic_setparam
  54. +_setparam.restype = c_int
  55. +_setparam.argtypes = [magic_t, c_int, c_void_p]
  56. +
  57. class Magic(object):
  58. def __init__(self, ms):
  59. @@ -228,29 +240,81 @@
  60. """
  61. return _errno(self._magic_t)
  62. + def getparam(self, param):
  63. + """
  64. + Returns the param value if successful and -1 if the parameter
  65. + was unknown.
  66. + """
  67. + v = c_int()
  68. + i = _getparam(self._magic_t, param, byref(v))
  69. + if i == -1:
  70. + return -1
  71. + return v.value
  72. +
  73. + def setparam(self, param, value):
  74. + """
  75. + Returns 0 if successful and -1 if the parameter was unknown.
  76. + """
  77. + v = c_int(value)
  78. + return _setparam(self._magic_t, param, byref(v))
  79. +
  80. def open(flags):
  81. """
  82. Returns a magic object on success and None on failure.
  83. Flags argument as for setflags.
  84. """
  85. - return Magic(_open(flags))
  86. + magic_t = _open(flags)
  87. + if magic_t is None:
  88. + return None
  89. + return Magic(magic_t)
  90. # Objects used by `detect_from_` functions
  91. -mime_magic = Magic(_open(MAGIC_MIME))
  92. -mime_magic.load()
  93. -none_magic = Magic(_open(MAGIC_NONE))
  94. -none_magic.load()
  95. +class error(Exception):
  96. + pass
  97. +class MagicDetect(object):
  98. + def __init__(self):
  99. + self.mime_magic = open(MAGIC_MIME)
  100. + if self.mime_magic is None:
  101. + raise error
  102. + if self.mime_magic.load() == -1:
  103. + self.mime_magic.close()
  104. + self.mime_magic = None
  105. + raise error
  106. + self.none_magic = open(MAGIC_NONE)
  107. + if self.none_magic is None:
  108. + self.mime_magic.close()
  109. + self.mime_magic = None
  110. + raise error
  111. + if self.none_magic.load() == -1:
  112. + self.none_magic.close()
  113. + self.none_magic = None
  114. + self.mime_magic.close()
  115. + self.mime_magic = None
  116. + raise error
  117. +
  118. + def __del__(self):
  119. + if self.mime_magic is not None:
  120. + self.mime_magic.close()
  121. + if self.none_magic is not None:
  122. + self.none_magic.close()
  123. +
  124. +threadlocal = threading.local()
  125. +
  126. +def _detect_make():
  127. + v = getattr(threadlocal, "magic_instance", None)
  128. + if v is None:
  129. + v = MagicDetect()
  130. + setattr(threadlocal, "magic_instance", v)
  131. + return v
  132. def _create_filemagic(mime_detected, type_detected):
  133. - splat = mime_detected.split('; ')
  134. - mime_type = splat[0]
  135. - if len(splat) == 2:
  136. - mime_encoding = splat[1]
  137. - else:
  138. - mime_encoding = ''
  139. + try:
  140. + mime_type, mime_encoding = mime_detected.split('; ')
  141. + except ValueError:
  142. + raise ValueError(mime_detected)
  143. return FileMagic(name=type_detected, mime_type=mime_type,
  144. encoding=mime_encoding.replace('charset=', ''))
  145. @@ -261,9 +325,9 @@
  146. Returns a `FileMagic` namedtuple.
  147. '''
  148. -
  149. - return _create_filemagic(mime_magic.file(filename),
  150. - none_magic.file(filename))
  151. + x = _detect_make()
  152. + return _create_filemagic(x.mime_magic.file(filename),
  153. + x.none_magic.file(filename))
  154. def detect_from_fobj(fobj):
  155. @@ -273,8 +337,9 @@
  156. '''
  157. file_descriptor = fobj.fileno()
  158. - return _create_filemagic(mime_magic.descriptor(file_descriptor),
  159. - none_magic.descriptor(file_descriptor))
  160. + x = _detect_make()
  161. + return _create_filemagic(x.mime_magic.descriptor(file_descriptor),
  162. + x.none_magic.descriptor(file_descriptor))
  163. def detect_from_content(byte_content):
  164. @@ -283,5 +348,6 @@
  165. Returns a `FileMagic` namedtuple.
  166. '''
  167. - return _create_filemagic(mime_magic.buffer(byte_content),
  168. - none_magic.buffer(byte_content))
  169. + x = _detect_make()
  170. + return _create_filemagic(x.mime_magic.buffer(byte_content),
  171. + x.none_magic.buffer(byte_content))