pyADS icon indicating copy to clipboard operation
pyADS copied to clipboard

The most up to date version of this did not work.... I have uploaded the reworked version.

Open enisbukalo opened this issue 5 years ago • 2 comments

'''python

from ctypes import windll, Structure, Union, byref
from ctypes import c_wchar_p, c_ulong, c_wchar, c_longlong

import os

# from os.path import join, expanduser, isfile
# file = join(expanduser("~"), "Desktop", "Test.txt")

kernel32 = windll.kernel32

LPSTR = c_wchar_p
DWORD = c_ulong
LONG = c_ulong
WCHAR = c_wchar * 296
LONGLONG = c_longlong


class LARGE_INTEGER_UNION(Structure):
    _fields_ = [
        ("LowPart", DWORD),
        ("HighPart", LONG),
        ]


class LARGE_INTEGER(Union):
    _fields_ = [
        ("large1", LARGE_INTEGER_UNION),
        ("large2", LARGE_INTEGER_UNION),
        ("QuadPart",    LONGLONG),
    ]


class WIN32_FIND_STREAM_DATA(Structure):
    _fields_ = [
        ("StreamSize", LARGE_INTEGER),
        ("cStreamName", WCHAR),
    ]
    """
    typedef struct _WIN32_FIND_STREAM_DATA {
      LARGE_INTEGER StreamSize;
      WCHAR         cStreamName[MAX_PATH + 36];
    } WIN32_FIND_STREAM_DATA, *PWIN32_FIND_STREAM_DATA;
    """


class ADS():
    def __init__(self, filename):
        self.filename = filename
        self.streams = self.init_streams()

    def init_streams(self):
        file_infos = WIN32_FIND_STREAM_DATA()
        streamlist = list()
        myhandler = kernel32.FindFirstStreamW(
                LPSTR(self.filename), 0, byref(file_infos), 0)
        """
        HANDLE WINAPI FindFirstStreamW(
          __in        LPCWSTR lpFileName,
          __in        STREAM_INFO_LEVELS InfoLevel, (0 standard, 1 max infos)
          __out       LPVOID lpFindStreamData, (return information about file in a 
WIN32_FIND_STREAM_DATA if 0 is given in infos_level
          __reserved  DWORD dwFlags (Reserved for future use. This parameter must be zero.) cf: doc
        );
        https://msdn.microsoft.com/en-us/library/aa364424(v=vs.85).aspx
        """

        if file_infos.cStreamName:
            streamname = file_infos.cStreamName.split(":")[1]
            if streamname:
                streamlist.append(streamname)

            while kernel32.FindNextStreamW(myhandler, byref(file_infos)):
                streamlist.append(file_infos.cStreamName.split(":")[1])

        kernel32.FindClose(myhandler)  # Close the handle

        return streamlist

    def __iter__(self):
        return iter(self.streams)

    def has_streams(self):
        return len(self.streams) > 0

    def full_filename(self, stream):
        return "%s:%s" % (self.filename, stream)

    def add_stream_from_file(self, filename):
        if os.path.exists(filename):
            with open(filename, "rb") as f:
                content = f.read()
            return self.add_stream_from_string(filename, content)
        else:
            print("Could not find file: {0}".format(filename))
            return False

    def add_stream_from_string(self, stream_name, string):
        fullname = self.full_filename(os.path.basename(stream_name))
        if os.path.exists(fullname):
            print("Stream name already exists")
            return False
        else:
            fd = open(fullname, "wb")
            fd.write(string)
            fd.close()
            self.streams.append(stream_name)
            return True

    def delete_stream(self, stream):
        try:
            os.remove(self.full_filename(stream))
            self.streams.remove(stream)
            return True
        except:
            return False

    def get_stream_content(self, stream):
        fd = open(self.full_filename(stream), "rb")
        content = fd.read()
        fd.close()
        return content

# handler = ADS(file)
# if handler.has_streams():
#     for stream in handler:
#         print(stream)

'''

enisbukalo avatar Nov 06 '18 14:11 enisbukalo

Why not just making a pull request ?

RobinDavid avatar Nov 07 '18 20:11 RobinDavid

There is a pull request pending.

petersilva avatar Mar 29 '19 02:03 petersilva