paramiko._winapi

Package paramiko :: Module _winapi |
[frames] | no frames]

# Source Code for Module paramiko._winapi

      1  """
      2  Windows API functions implemented as ctypes functions and classes as found
      3  in jaraco.windows (2.10).
      4
      5  If you encounter issues with this module, please consider reporting the issues
      6  in jaraco.windows and asking the author to port the fixes back here.
      7  """
      8
      9  import ctypes
     10  import ctypes.wintypes
     11  import __builtin__
     12
     13  ######################
     14  # jaraco.windows.error
     15
     16 -def format_system_message(errno):
     17          """
     18          Call FormatMessage with a system error number to retrieve
     19          the descriptive error message.
     20          """
     21          # first some flags used by FormatMessageW
     22          ALLOCATE_BUFFER = 0x100
     23          ARGUMENT_ARRAY = 0x2000
     24          FROM_HMODULE = 0x800
     25          FROM_STRING = 0x400
     26          FROM_SYSTEM = 0x1000
     27          IGNORE_INSERTS = 0x200
     28
     29          # Let FormatMessageW allocate the buffer (we'll free it below)
     30          # Also, let it know we want a system error message.
     31          flags = ALLOCATE_BUFFER | FROM_SYSTEM
     32          source = None
     33          message_id = errno
     34          language_id = 0
     35          result_buffer = ctypes.wintypes.LPWSTR()
     36          buffer_size = 0
     37          arguments = None
     38          bytes = ctypes.windll.kernel32.FormatMessageW(
     39                  flags,
     40                  source,
     41                  message_id,
     42                  language_id,
     43                  ctypes.byref(result_buffer),
     44                  buffer_size,
     45                  arguments,
     46                  )
     47          # note the following will cause an infinite loop if GetLastError
     48          #  repeatedly returns an error that cannot be formatted, although
     49          #  this should not happen.
     50          handle_nonzero_success(bytes)
     51          message = result_buffer.value
     52          ctypes.windll.kernel32.LocalFree(result_buffer)
     53          return message
     54
     55
     56 -class WindowsError(__builtin__.WindowsError):
     57          "more info about errors at http://msdn.microsoft.com/en-us/library/ms681381(VS.85).aspx"
     58
     59 -        def __init__(self, value=None):
     60                  if value is None:
     61                          value = ctypes.windll.kernel32.GetLastError()
     62                  strerror = format_system_message(value)
     63                  super(WindowsError, self).__init__(value, strerror)
     64
     65          @property
     66 -        def message(self):
     67                  return self.strerror
     68
     69          @property
     70 -        def code(self):
     71                  return self.winerror
     72
     73 -        def __str__(self):
     74                  return self.message
     75
     76 -        def __repr__(self):
     77                  return '{self.__class__.__name__}({self.winerror})'.format(**vars())
     78
     79 -def handle_nonzero_success(result):
     80          if result == 0:
     81                  raise WindowsError()
     82
     83
     84  #####################
     85  # jaraco.windows.mmap
     86
     87  CreateFileMapping = ctypes.windll.kernel32.CreateFileMappingW
     88  CreateFileMapping.argtypes = [
     89          ctypes.wintypes.HANDLE,
     90          ctypes.c_void_p,
     91          ctypes.wintypes.DWORD,
     92          ctypes.wintypes.DWORD,
     93          ctypes.wintypes.DWORD,
     94          ctypes.wintypes.LPWSTR,
     95  ]
     96  CreateFileMapping.restype = ctypes.wintypes.HANDLE
     97
     98  MapViewOfFile = ctypes.windll.kernel32.MapViewOfFile
     99  MapViewOfFile.restype = ctypes.wintypes.HANDLE
    100
    101 -class MemoryMap(object):
    102          """
    103          A memory map object which can have security attributes overrideden.
    104          """
    105 -        def __init__(self, name, length, security_attributes=None):
    106                  self.name = name
    107                  self.length = length
    108                  self.security_attributes = security_attributes
    109                  self.pos = 0
    110
    111 -        def __enter__(self):
    112                  p_SA = (
    113                          ctypes.byref(self.security_attributes)
    114                          if self.security_attributes else None
    115                  )
    116                  INVALID_HANDLE_VALUE = -1
    117                  PAGE_READWRITE = 0x4
    118                  FILE_MAP_WRITE = 0x2
    119                  filemap = ctypes.windll.kernel32.CreateFileMappingW(
    120                          INVALID_HANDLE_VALUE, p_SA, PAGE_READWRITE, 0, self.length,
    121                          unicode(self.name))
    122                  handle_nonzero_success(filemap)
    123                  if filemap == INVALID_HANDLE_VALUE:
    124                          raise Exception("Failed to create file mapping")
    125                  self.filemap = filemap
    126                  self.view = MapViewOfFile(filemap, FILE_MAP_WRITE, 0, 0, 0)
    127                  return self
    128
    129 -        def seek(self, pos):
    130                  self.pos = pos
    131
    132 -        def write(self, msg):
    133                  ctypes.windll.msvcrt.memcpy(self.view + self.pos, msg, len(msg))
    134                  self.pos += len(msg)
    135
    136 -        def read(self, n):
    137                  """
    138                  Read n bytes from mapped view.
    139                  """
    140                  out = ctypes.create_string_buffer(n)
    141                  ctypes.windll.msvcrt.memcpy(out, self.view + self.pos, n)
    142                  self.pos += n
    143                  return out.raw
    144
    145 -        def __exit__(self, exc_type, exc_val, tb):
    146                  ctypes.windll.kernel32.UnmapViewOfFile(self.view)
    147                  ctypes.windll.kernel32.CloseHandle(self.filemap)
    148
    149  #########################
    150  # jaraco.windows.security
    151
    152 -class TokenInformationClass:
    153          TokenUser = 1
    154
    155 -class TOKEN_USER(ctypes.Structure):
    156          num = 1
    157          _fields_ = [
    158                  ('SID', ctypes.c_void_p),
    159                  ('ATTRIBUTES', ctypes.wintypes.DWORD),
    160          ]
    161
    162
    163 -class SECURITY_DESCRIPTOR(ctypes.Structure):
    164          """
    165          typedef struct _SECURITY_DESCRIPTOR
    166                  {
    167                  UCHAR Revision;
    168                  UCHAR Sbz1;
    169                  SECURITY_DESCRIPTOR_CONTROL Control;
    170                  PSID Owner;
    171                  PSID Group;
    172                  PACL Sacl;
    173                  PACL Dacl;
    174                  }   SECURITY_DESCRIPTOR;
    175          """
    176          SECURITY_DESCRIPTOR_CONTROL = ctypes.wintypes.USHORT
    177          REVISION = 1
    178
    179          _fields_ = [
    180                  ('Revision', ctypes.c_ubyte),
    181                  ('Sbz1', ctypes.c_ubyte),
    182                  ('Control', SECURITY_DESCRIPTOR_CONTROL),
    183                  ('Owner', ctypes.c_void_p),
    184                  ('Group', ctypes.c_void_p),
    185                  ('Sacl', ctypes.c_void_p),
    186                  ('Dacl', ctypes.c_void_p),
    187          ]
    188
    189 -class SECURITY_ATTRIBUTES(ctypes.Structure):
    190          """
    191          typedef struct _SECURITY_ATTRIBUTES {
    192                  DWORD  nLength;
    193                  LPVOID lpSecurityDescriptor;
    194                  BOOL   bInheritHandle;
    195          } SECURITY_ATTRIBUTES;
    196          """
    197          _fields_ = [
    198                  ('nLength', ctypes.wintypes.DWORD),
    199                  ('lpSecurityDescriptor', ctypes.c_void_p),
    200                  ('bInheritHandle', ctypes.wintypes.BOOL),
    201          ]
    202
    203 -        def __init__(self, *args, **kwargs):
    204                  super(SECURITY_ATTRIBUTES, self).__init__(*args, **kwargs)
    205                  self.nLength = ctypes.sizeof(SECURITY_ATTRIBUTES)
    206
    207 -        def _get_descriptor(self):
    208                  return self._descriptor
    209 -        def _set_descriptor(self, descriptor):
    210                  self._descriptor = descriptor
    211                  self.lpSecurityDescriptor = ctypes.addressof(descriptor)
    212          descriptor = property(_get_descriptor, _set_descriptor)
    213
    214 -def GetTokenInformation(token, information_class):
    215          """
    216          Given a token, get the token information for it.
    217          """
    218          data_size = ctypes.wintypes.DWORD()
    219          ctypes.windll.advapi32.GetTokenInformation(token, information_class.num,
    220                  0, 0, ctypes.byref(data_size))
    221          data = ctypes.create_string_buffer(data_size.value)
    222          handle_nonzero_success(ctypes.windll.advapi32.GetTokenInformation(token,
    223                  information_class.num,
    224                  ctypes.byref(data), ctypes.sizeof(data),
    225                  ctypes.byref(data_size)))
    226          return ctypes.cast(data, ctypes.POINTER(TOKEN_USER)).contents
    227
    228 -class TokenAccess:
    229          TOKEN_QUERY = 0x8
    230
    231 -def OpenProcessToken(proc_handle, access):
    232          result = ctypes.wintypes.HANDLE()
    233          proc_handle = ctypes.wintypes.HANDLE(proc_handle)
    234          handle_nonzero_success(ctypes.windll.advapi32.OpenProcessToken(
    235                  proc_handle, access, ctypes.byref(result)))
    236          return result
    237
    238 -def get_current_user():
    239          """
    240          Return a TOKEN_USER for the owner of this process.
    241          """
    242          process = OpenProcessToken(
    243                  ctypes.windll.kernel32.GetCurrentProcess(),
    244                  TokenAccess.TOKEN_QUERY,
    245          )
    246          return GetTokenInformation(process, TOKEN_USER)
    247
    248 -def get_security_attributes_for_user(user=None):
    249          """
    250          Return a SECURITY_ATTRIBUTES structure with the SID set to the
    251          specified user (uses current user if none is specified).
    252          """
    253          if user is None:
    254                  user = get_current_user()
    255
    256          assert isinstance(user, TOKEN_USER), "user must be TOKEN_USER instance"
    257
    258          SD = SECURITY_DESCRIPTOR()
    259          SA = SECURITY_ATTRIBUTES()
    260          # by attaching the actual security descriptor, it will be garbage-
    261          # collected with the security attributes
    262          SA.descriptor = SD
    263          SA.bInheritHandle = 1
    264
    265          ctypes.windll.advapi32.InitializeSecurityDescriptor(ctypes.byref(SD),
    266                  SECURITY_DESCRIPTOR.REVISION)
    267          ctypes.windll.advapi32.SetSecurityDescriptorOwner(ctypes.byref(SD),
    268                  user.SID, 0)
    269          return SA
    270