From tomo.bbe at gmail.com Tue Sep 6 15:43:47 2016 From: tomo.bbe at gmail.com (James) Date: Tue, 6 Sep 2016 20:43:47 +0100 Subject: [python-win32] Array of VT_RECORD Message-ID: I am trying to use a 3rd party COM application. Several arguments to the main methods are defined as (24612, 3) in my makepy.py output. I have seen from previous mailing list discussion in 2007 that this should mean I pass an array of "pythoncom.VT_RECORD | pythoncom.VT_ARRAY | pythoncom.VT_BYREF". However when create such an array like so, state_array = VARIANT(pythoncom.VT_RECORD | pythoncom.VT_ARRAY | pythoncom.VT_BYREF, [states,]) And pass this to the function it complains: TypeError: Objects for SAFEARRAYS must be sequences (of sequences), or a buffer object. I have looked at the source code, but I do not understand why this code is incorrect. It seems to be related to a check re the number of dimensions in the array. Any advice welcome. Thanks, James From david.hautbois at free.fr Thu Sep 15 04:08:20 2016 From: david.hautbois at free.fr (David Hautbois) Date: Thu, 15 Sep 2016 10:08:20 +0200 Subject: [python-win32] Windows service - sderr - stdout - win32trace Message-ID: <06373e10-10b1-7d84-3320-0e7c16c4e47b@free.fr> Hi I'm currently working on a Windows service with python3/pywin32. I understood that stdout and stderr output are redirected to the win32trace remote collector. Is there a way to disable this ? Thanks. David. From david.hautbois at free.fr Thu Sep 15 09:50:32 2016 From: david.hautbois at free.fr (David Hautbois) Date: Thu, 15 Sep 2016 15:50:32 +0200 Subject: [python-win32] Windows service - sderr - stdout - win32trace In-Reply-To: <06373e10-10b1-7d84-3320-0e7c16c4e47b@free.fr> References: <06373e10-10b1-7d84-3320-0e7c16c4e47b@free.fr> Message-ID: <52665fd3-7962-5fb4-84bf-6527104a1af8@free.fr> Ok I found the trick. I removed : import win32traceutil David. Le 15/09/2016 ? 10:08, David Hautbois a ?crit : > Hi > > I'm currently working on a Windows service with python3/pywin32. > > I understood that stdout and stderr output are redirected to the > win32trace remote collector. > > Is there a way to disable this ? > > Thanks. > > David. > _______________________________________________ > python-win32 mailing list > python-win32 at python.org > https://mail.python.org/mailman/listinfo/python-win32 From tfa.signup.test1 at gmail.com Mon Sep 19 10:16:22 2016 From: tfa.signup.test1 at gmail.com (Goku Balu) Date: Mon, 19 Sep 2016 19:46:22 +0530 Subject: [python-win32] File access entries are incorrectly set Message-ID: If I deny GENERIC_WRITE it denies Rc as well (Rc - Read Control). I can't even open the folder in explorer. Here is the sample code. Is this a bug? import win32security,win32api,win32con import ntsecuritycon as con import os def show_cacls (filename): for line in os.popen ("Icacls %s" % filename).read ().splitlines (): print(line) def denyWrite(): everyone, everyone_domain, everyone_type = win32security.LookupAccountName ("", "Everyone") print(everyone, everyone_domain, everyone_type) sd = win32security.GetFileSecurity(FILENAME, win32security.DACL_SECURITY_INFORMATION) dacl = sd.GetSecurityDescriptorDacl() masks=con.GENERIC_WRITE dacl.AddAccessDeniedAce(win32security.ACL_REVISION_DS,masks,everyone) sd.SetSecurityDescriptorDacl(1, dacl, 0) # may not be necessary win32security.SetFileSecurity(FILENAME, win32security.DACL_SECURITY_INFORMATION, sd) show_cacls (FILENAME) try: FILENAME = "D:\\test" denyWrite() Any help regarding this would be welcomed. Thanks -------------- next part -------------- An HTML attachment was scrubbed... URL: From chris at slort.org Mon Sep 19 18:21:04 2016 From: chris at slort.org (Christopher Nilsson) Date: Mon, 19 Sep 2016 22:21:04 +0000 Subject: [python-win32] File access entries are incorrectly set In-Reply-To: References: Message-ID: Hi Goku, That doesn't seem like a bug to me. GENERIC_WRITE represents several permissions mashed together, including FILE_WRITE and read control. Perhaps try with just FILE_WRITE on its own? On Tue, 20 Sep 2016, 8:03 AM Goku Balu wrote: > If I deny GENERIC_WRITE it denies Rc as well (Rc - Read Control). I can't > even open the folder in explorer. Here is the sample code. Is this a bug? > > import win32security,win32api,win32con > import ntsecuritycon as con > import os > > def show_cacls (filename): > for line in os.popen ("Icacls %s" % filename).read ().splitlines (): > print(line) > > def denyWrite(): > everyone, everyone_domain, everyone_type = > win32security.LookupAccountName ("", "Everyone") > print(everyone, everyone_domain, everyone_type) > > sd = win32security.GetFileSecurity(FILENAME, > win32security.DACL_SECURITY_INFORMATION) > dacl = sd.GetSecurityDescriptorDacl() > > masks=con.GENERIC_WRITE > dacl.AddAccessDeniedAce(win32security.ACL_REVISION_DS,masks,everyone) > sd.SetSecurityDescriptorDacl(1, dacl, 0) # may not be necessary > win32security.SetFileSecurity(FILENAME, > win32security.DACL_SECURITY_INFORMATION, sd) > show_cacls (FILENAME) > > > try: > > FILENAME = "D:\\test" > denyWrite() > > Any help regarding this would be welcomed. Thanks > _______________________________________________ > python-win32 mailing list > python-win32 at python.org > https://mail.python.org/mailman/listinfo/python-win32 > -------------- next part -------------- An HTML attachment was scrubbed... URL: From chris at slort.org Tue Sep 20 03:53:40 2016 From: chris at slort.org (Christopher Nilsson) Date: Tue, 20 Sep 2016 07:53:40 +0000 Subject: [python-win32] File access entries are incorrectly set In-Reply-To: References: Message-ID: I think file_generic_write will have the same problem. You may want to check out: https://msdn.microsoft.com/en-us/library/windows/desktop/aa364399(v=vs.85).aspx Note they explicitly say you can't deny generic_write without causing problems. Blocking access like this can get pretty fiddly. I can only suggest starting by blocking the bare minimum that you can. Check those consts on msdn & avoid the generic ones. On Tue, 20 Sep 2016, 4:42 PM Goku Balu wrote: > Hi Christopher, > > Thanks for responding. Forgot to mention that I did test this with > FILE_GENERIC_WRITE also but the result is the same. If this > is applied on a folder it leaves the folder unopenable. If it's applied on > a file(say a.txt file), Notepad shows warning informing "Access Denied" but > can be edited and can be saved in a different location. > > FYI I'm using Python 3.2 with Pywin32 ver 219. > > Thanks, > Jeba > > On Tue, Sep 20, 2016 at 3:51 AM, Christopher Nilsson > wrote: > >> Hi Goku, >> >> That doesn't seem like a bug to me. GENERIC_WRITE represents several >> permissions mashed together, including FILE_WRITE and read control. >> >> Perhaps try with just FILE_WRITE on its own? >> >> On Tue, 20 Sep 2016, 8:03 AM Goku Balu >> wrote: >> >>> If I deny GENERIC_WRITE it denies Rc as well (Rc - Read Control). I >>> can't even open the folder in explorer. Here is the sample code. Is this a >>> bug? >>> >>> import win32security,win32api,win32con >>> import ntsecuritycon as con >>> import os >>> >>> def show_cacls (filename): >>> for line in os.popen ("Icacls %s" % filename).read ().splitlines (): >>> print(line) >>> >>> def denyWrite(): >>> everyone, everyone_domain, everyone_type = >>> win32security.LookupAccountName ("", "Everyone") >>> print(everyone, everyone_domain, everyone_type) >>> >>> sd = win32security.GetFileSecurity(FILENAME, >>> win32security.DACL_SECURITY_INFORMATION) >>> dacl = sd.GetSecurityDescriptorDacl() >>> >>> masks=con.GENERIC_WRITE >>> dacl.AddAccessDeniedAce(win32security.ACL_REVISION_DS,masks,everyone) >>> sd.SetSecurityDescriptorDacl(1, dacl, 0) # may not be necessary >>> win32security.SetFileSecurity(FILENAME, >>> win32security.DACL_SECURITY_INFORMATION, sd) >>> show_cacls (FILENAME) >>> >>> >>> try: >>> >>> FILENAME = "D:\\test" >>> denyWrite() >>> >>> Any help regarding this would be welcomed. Thanks >>> _______________________________________________ >>> python-win32 mailing list >>> python-win32 at python.org >>> https://mail.python.org/mailman/listinfo/python-win32 >>> >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From tfa.signup.test1 at gmail.com Tue Sep 20 02:42:23 2016 From: tfa.signup.test1 at gmail.com (Goku Balu) Date: Tue, 20 Sep 2016 12:12:23 +0530 Subject: [python-win32] File access entries are incorrectly set In-Reply-To: References: Message-ID: Hi Christopher, Thanks for responding. Forgot to mention that I did test this with FILE_GENERIC_WRITE also but the result is the same. If this is applied on a folder it leaves the folder unopenable. If it's applied on a file(say a.txt file), Notepad shows warning informing "Access Denied" but can be edited and can be saved in a different location. FYI I'm using Python 3.2 with Pywin32 ver 219. Thanks, Jeba On Tue, Sep 20, 2016 at 3:51 AM, Christopher Nilsson wrote: > Hi Goku, > > That doesn't seem like a bug to me. GENERIC_WRITE represents several > permissions mashed together, including FILE_WRITE and read control. > > Perhaps try with just FILE_WRITE on its own? > > On Tue, 20 Sep 2016, 8:03 AM Goku Balu wrote: > >> If I deny GENERIC_WRITE it denies Rc as well (Rc - Read Control). I can't >> even open the folder in explorer. Here is the sample code. Is this a bug? >> >> import win32security,win32api,win32con >> import ntsecuritycon as con >> import os >> >> def show_cacls (filename): >> for line in os.popen ("Icacls %s" % filename).read ().splitlines (): >> print(line) >> >> def denyWrite(): >> everyone, everyone_domain, everyone_type = win32security.LookupAccountName >> ("", "Everyone") >> print(everyone, everyone_domain, everyone_type) >> >> sd = win32security.GetFileSecurity(FILENAME, >> win32security.DACL_SECURITY_INFORMATION) >> dacl = sd.GetSecurityDescriptorDacl() >> >> masks=con.GENERIC_WRITE >> dacl.AddAccessDeniedAce(win32security.ACL_REVISION_DS,masks,everyone) >> sd.SetSecurityDescriptorDacl(1, dacl, 0) # may not be necessary >> win32security.SetFileSecurity(FILENAME, win32security.DACL_SECURITY_INFORMATION, >> sd) >> show_cacls (FILENAME) >> >> >> try: >> >> FILENAME = "D:\\test" >> denyWrite() >> >> Any help regarding this would be welcomed. Thanks >> _______________________________________________ >> python-win32 mailing list >> python-win32 at python.org >> https://mail.python.org/mailman/listinfo/python-win32 >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From eryksun at gmail.com Tue Sep 20 04:11:37 2016 From: eryksun at gmail.com (eryk sun) Date: Tue, 20 Sep 2016 08:11:37 +0000 Subject: [python-win32] File access entries are incorrectly set In-Reply-To: References: Message-ID: On Mon, Sep 19, 2016 at 10:21 PM, Christopher Nilsson wrote: > > That doesn't seem like a bug to me. GENERIC_WRITE represents several > permissions mashed together, including FILE_WRITE and read control. > > Perhaps try with just FILE_WRITE on its own? For a file or directory, GENERIC_WRITE (0x80000000) gets mapped to FILE_GENERIC_WRITE, which includes the following standard rights (upper 16 bits): SYNCHRONIZE = 0x00100000 READ_CONTROL = 0x00020000 and File-object specific rights (lower 16 bits): FILE_WRITE_ATTRIBUTES = 0x00000100 FILE_WRITE_EA = 0x00000010 FILE_APPEND_DATA = 0x00000004 FILE_WRITE_DATA = 0x00000002 The relevant access right that's being denied in this case is SYNCHRONIZE. For example, SetCurrentDirectory uses a synchronous directory handle, i.e. it calls NtOpenfile with desired access SYNCHRONIZE | FILE_TRAVERSE and open option FILE_SYNCHRONOUS_IO_NONALERT. Similarly, for listing a directory, FindFirstFile uses a synchronous handle with SYNCHRONIZE | FILE_LIST_DIRECTORY access. The open option FILE_SYNCHRONOUS_IO_NONALERT is defined as follows: All operations on the file are performed synchronously. Waits in the system that synchronize I/O queuing and completion are not subject to alerts. This flag also causes the I/O system to maintain the file-position context. If this flag is set, the SYNCHRONIZE flag must be set in the DesiredAccess parameter. For example, when FindFirstFile calls NtQueryDirectoryFile (FileBothDirectoryInformation) to list the directory, the system call sees the handle is opened for synchronous access, so it waits to acquire the File object's Lock before calling the filesystem driver (e.g. NTFS). Then it waits again to complete the request. From chris at slort.org Tue Sep 20 07:24:08 2016 From: chris at slort.org (Christopher Nilsson) Date: Tue, 20 Sep 2016 11:24:08 +0000 Subject: [python-win32] File access entries are incorrectly set In-Reply-To: References: Message-ID: Awesome detail. Thanks eryk. On Tue, 20 Sep 2016, 6:13 PM eryk sun wrote: > On Mon, Sep 19, 2016 at 10:21 PM, Christopher Nilsson > wrote: > > > > That doesn't seem like a bug to me. GENERIC_WRITE represents several > > permissions mashed together, including FILE_WRITE and read control. > > > > Perhaps try with just FILE_WRITE on its own? > > For a file or directory, GENERIC_WRITE (0x80000000) gets mapped to > FILE_GENERIC_WRITE, which includes the following standard rights > (upper 16 bits): > > SYNCHRONIZE = 0x00100000 > READ_CONTROL = 0x00020000 > > and File-object specific rights (lower 16 bits): > > FILE_WRITE_ATTRIBUTES = 0x00000100 > FILE_WRITE_EA = 0x00000010 > FILE_APPEND_DATA = 0x00000004 > FILE_WRITE_DATA = 0x00000002 > > The relevant access right that's being denied in this case is SYNCHRONIZE. > > For example, SetCurrentDirectory uses a synchronous directory handle, > i.e. it calls NtOpenfile with desired access SYNCHRONIZE | > FILE_TRAVERSE and open option FILE_SYNCHRONOUS_IO_NONALERT. Similarly, > for listing a directory, FindFirstFile uses a synchronous handle with > SYNCHRONIZE | FILE_LIST_DIRECTORY access. > > The open option FILE_SYNCHRONOUS_IO_NONALERT is defined as follows: > > All operations on the file are performed synchronously. > Waits in the system that synchronize I/O queuing and > completion are not subject to alerts. This flag also > causes the I/O system to maintain the file-position > context. If this flag is set, the SYNCHRONIZE flag must > be set in the DesiredAccess parameter. > > For example, when FindFirstFile calls NtQueryDirectoryFile > (FileBothDirectoryInformation) to list the directory, the system call > sees the handle is opened for synchronous access, so it waits to > acquire the File object's Lock before calling the filesystem driver > (e.g. NTFS). Then it waits again to complete the request. > _______________________________________________ > python-win32 mailing list > python-win32 at python.org > https://mail.python.org/mailman/listinfo/python-win32 > -------------- next part -------------- An HTML attachment was scrubbed... URL: From tfa.signup.test1 at gmail.com Fri Sep 23 06:39:20 2016 From: tfa.signup.test1 at gmail.com (Goku Balu) Date: Fri, 23 Sep 2016 16:09:20 +0530 Subject: [python-win32] python-win32 Digest, Vol 162, Issue 4 In-Reply-To: References: Message-ID: So if we deny WRITE then SYNCHRONIZE will be denied which will in-turn affect READ. Is there a way to deny WRITE alone without affecting file/folder read? Thanks, Goku On Tue, Sep 20, 2016 at 9:30 PM, wrote: > > > > > That doesn't seem like a bug to me. GENERIC_WRITE represents several > > permissions mashed together, including FILE_WRITE and read control. > > > > Perhaps try with just FILE_WRITE on its own? > > For a file or directory, GENERIC_WRITE (0x80000000) gets mapped to > FILE_GENERIC_WRITE, which includes the following standard rights > (upper 16 bits): > > SYNCHRONIZE = 0x00100000 > READ_CONTROL = 0x00020000 > > and File-object specific rights (lower 16 bits): > > FILE_WRITE_ATTRIBUTES = 0x00000100 > FILE_WRITE_EA = 0x00000010 > FILE_APPEND_DATA = 0x00000004 > FILE_WRITE_DATA = 0x00000002 > > The relevant access right that's being denied in this case is SYNCHRONIZE. > > For example, SetCurrentDirectory uses a synchronous directory handle, > i.e. it calls NtOpenfile with desired access SYNCHRONIZE | > FILE_TRAVERSE and open option FILE_SYNCHRONOUS_IO_NONALERT. Similarly, > for listing a directory, FindFirstFile uses a synchronous handle with > SYNCHRONIZE | FILE_LIST_DIRECTORY access. > > The open option FILE_SYNCHRONOUS_IO_NONALERT is defined as follows: > > All operations on the file are performed synchronously. > Waits in the system that synchronize I/O queuing and > completion are not subject to alerts. This flag also > causes the I/O system to maintain the file-position > context. If this flag is set, the SYNCHRONIZE flag must > be set in the DesiredAccess parameter. > > For example, when FindFirstFile calls NtQueryDirectoryFile > (FileBothDirectoryInformation) to list the directory, the system call > sees the handle is opened for synchronous access, so it waits to > acquire the File object's Lock before calling the filesystem driver > (e.g. NTFS). Then it waits again to complete the request. > -------------- next part -------------- An HTML attachment was scrubbed... URL: From eryksun at gmail.com Fri Sep 23 10:12:03 2016 From: eryksun at gmail.com (eryk sun) Date: Fri, 23 Sep 2016 14:12:03 +0000 Subject: [python-win32] python-win32 Digest, Vol 162, Issue 4 In-Reply-To: References: Message-ID: On Fri, Sep 23, 2016 at 10:39 AM, Goku Balu wrote: > On Tue, Sep 20, 2016 at 9:30 PM, wrote: >> > >> > That doesn't seem like a bug to me. GENERIC_WRITE represents several >> > permissions mashed together, including FILE_WRITE and read control. >> > >> > Perhaps try with just FILE_WRITE on its own? >> >> For a file or directory, GENERIC_WRITE (0x80000000) gets mapped to >> FILE_GENERIC_WRITE, which includes the following standard rights >> (upper 16 bits): >> >> SYNCHRONIZE = 0x00100000 >> READ_CONTROL = 0x00020000 >> >> and File-object specific rights (lower 16 bits): >> >> FILE_WRITE_ATTRIBUTES = 0x00000100 >> FILE_WRITE_EA = 0x00000010 >> FILE_APPEND_DATA = 0x00000004 >> FILE_WRITE_DATA = 0x00000002 >> >> The relevant access right that's being denied in this case is SYNCHRONIZE. > > So if we deny WRITE then SYNCHRONIZE will be denied which will in-turn > affect READ. Is there a way to deny WRITE alone without affecting > file/folder read? Each kernel object type has a GENERIC_MAPPING that maps generic rights to sets of standard and object-specific rights. Before doing an AccessCheck, generic rights have to be mapped to specific rights via MapGenericMask. For the File type this generic mapping consists of the following values: FILE_GENERIC_READ FILE_GENERIC_WRITE FILE_GENERIC_EXECUTE FILE_ALL_ACCESS If you deny GENERIC_WRITE for a File, that's the same as denying the 6 rights in FILE_GENERIC_WRITE, which includes the standard SYNCHRONIZE and READ_CONTROL rights. You need to mask the value to filter out rights that shouldn't be denied. Use the constant SPECIFIC_RIGHTS_ALL, which is defined as 0xFFFF (i.e. the lower 16 bits of an access mask are reserved for object-specific rights). For example: import win32security import ntsecuritycon WORLD = win32security.CreateWellKnownSid(win32security.WinWorldSid) FILE_WRITE = (ntsecuritycon.FILE_GENERIC_WRITE & ntsecuritycon.SPECIFIC_RIGHTS_ALL) def deny_write(filename, account=None, ace_flags=0): sd = win32security.GetFileSecurity( filename, win32security.DACL_SECURITY_INFORMATION) sid = WORLD if account is None else ( win32security.LookupAccountName(None, account)[0]) dacl = sd.GetSecurityDescriptorDacl() dacl.AddAccessDeniedAceEx( win32security.ACL_REVISION_DS, ace_flags, FILE_WRITE, sid) sd.SetSecurityDescriptorDacl(1, dacl, 0) win32security.SetFileSecurity( filename, win32security.DACL_SECURITY_INFORMATION, sd) For a directory, generic write access entails the ability to write attributes and add files and subdirectories. Note that file delete rights are separately controlled by standard DELETE access and the specific directory right FILE_DELETE_CHILD, which is the right to delete files or subdirectories of a directory, even if the user is otherwise denied or not granted DELETE access. The ace_flags parameter allows controlling whether the ACE is inherited by subdirectories and files (CONTAINER_INHERIT_ACE, OBJECT_INHERIT_ACE) , whether the inheritance flags get propagated (NO_PROPAGATE_INHERIT_ACE), and whether the ACE applies only for inheritance (INHERIT_ONLY_ACE). From eryksun at gmail.com Fri Sep 23 10:54:19 2016 From: eryksun at gmail.com (eryk sun) Date: Fri, 23 Sep 2016 14:54:19 +0000 Subject: [python-win32] python-win32 Digest, Vol 162, Issue 4 In-Reply-To: References: Message-ID: On Fri, Sep 23, 2016 at 2:12 PM, eryk sun wrote: > Each kernel object type has a GENERIC_MAPPING that maps generic rights > to sets of standard and object-specific rights. Before doing an > AccessCheck, generic rights have to be mapped to specific rights via > MapGenericMask. > > For the File type this generic mapping consists of the following values: > > FILE_GENERIC_READ > FILE_GENERIC_WRITE > FILE_GENERIC_EXECUTE > FILE_ALL_ACCESS > > If you deny GENERIC_WRITE for a File, that's the same as denying the 6 > rights in FILE_GENERIC_WRITE, which includes the standard SYNCHRONIZE > and READ_CONTROL rights. You need to mask the value to filter out > rights that shouldn't be denied. Use the constant SPECIFIC_RIGHTS_ALL, > which is defined as 0xFFFF (i.e. the lower 16 bits of an access mask > are reserved for object-specific rights). For example: For reference, here's an access mask diagram: 3 3 2 2 2 2 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 +---------------+---------------+-------------------------------+ |G|G|G|G|Resvd|A| StandardRights| SpecificRights | |R|W|E|A| |S| | | +-+-------------+---------------+-------------------------------+ Generic Read Generic Write Generic Execute Generic All Reserved: 3 Access SACL Standard Rights: 8 Specific Rights: 16 The four most significant bits are the generic rights. Before evaluating an AccessCheck, the system maps generic rights in access masks to the corresponding standard and specific rights. Only 5 of the 8 possible standard rights have been assigned: SYNCHRONIZE (bit 20), WRITE_OWNER, WRITE_DAC, READ_CONTROL, and DELETE (bit 16). The File type assigns 9 out of 16 possible specific rights, from FILE_WRITE_ATTRIBUTES (bit 8) down to FILE_READ_DATA (bit 0). Some bits have multiple meanings depending on whether the object is a directory, data file, or named pipe. For example, bit 2 can mean FILE_ADD_SUBDIRECTORY, FILE_APPEND_DATA, or FILE_CREATE_PIPE_INSTANCE. From bhood2 at comcast.net Fri Sep 23 15:18:40 2016 From: bhood2 at comcast.net (Bob Hood) Date: Fri, 23 Sep 2016 13:18:40 -0600 Subject: [python-win32] Is SHChangeNotifyRegister implemented? Message-ID: I'm using Python 2.x with pywin32 2.18. I noticed the SHChangeNotifyRegister flags in win32comext\shell\shellcon.py, but I don't find any references in any of the remaining Python files or demos that reference this function. Has it been implemented? If so, can anybody point me at an example? From tfa.signup.test1 at gmail.com Tue Sep 27 05:14:37 2016 From: tfa.signup.test1 at gmail.com (Goku Balu) Date: Tue, 27 Sep 2016 14:44:37 +0530 Subject: [python-win32] File access entries are incorrectly set Message-ID: Thanks Eryk for being so thorough and for a great explanation. If this can be solved differently, I tried with removing the rights such as READ_CONTROL and SYNCHRONIZE from the FILE_GENERIC_WRITE mask and it worked as well. masks= ntsecuritycon.FILE_GENERIC_WRITE masks=masks&~ntsecuritycon.READ_CONTROL masks=masks&~ntsecuritycon.SYNCHRONIZE Really appreciate the great community help. Thanks, Goku On Fri, Sep 23, 2016 at 9:30 PM, wrote: > >> > That doesn't seem like a bug to me. GENERIC_WRITE represents several > >> > permissions mashed together, including FILE_WRITE and read control. > >> > > >> > Perhaps try with just FILE_WRITE on its own? > >> > >> For a file or directory, GENERIC_WRITE (0x80000000) gets mapped to > >> FILE_GENERIC_WRITE, which includes the following standard rights > >> (upper 16 bits): > >> > >> SYNCHRONIZE = 0x00100000 > >> READ_CONTROL = 0x00020000 > >> > >> and File-object specific rights (lower 16 bits): > >> > >> FILE_WRITE_ATTRIBUTES = 0x00000100 > >> FILE_WRITE_EA = 0x00000010 > >> FILE_APPEND_DATA = 0x00000004 > >> FILE_WRITE_DATA = 0x00000002 > >> > >> The relevant access right that's being denied in this case is > SYNCHRONIZE. > > > > So if we deny WRITE then SYNCHRONIZE will be denied which will in-turn > > affect READ. Is there a way to deny WRITE alone without affecting > > file/folder read? > > Each kernel object type has a GENERIC_MAPPING that maps generic rights > to sets of standard and object-specific rights. Before doing an > AccessCheck, generic rights have to be mapped to specific rights via > MapGenericMask. > > For the File type this generic mapping consists of the following values: > > FILE_GENERIC_READ > FILE_GENERIC_WRITE > FILE_GENERIC_EXECUTE > FILE_ALL_ACCESS > > If you deny GENERIC_WRITE for a File, that's the same as denying the 6 > rights in FILE_GENERIC_WRITE, which includes the standard SYNCHRONIZE > and READ_CONTROL rights. You need to mask the value to filter out > rights that shouldn't be denied. Use the constant SPECIFIC_RIGHTS_ALL, > which is defined as 0xFFFF (i.e. the lower 16 bits of an access mask > are reserved for object-specific rights). For example: > > import win32security > import ntsecuritycon > > WORLD = win32security.CreateWellKnownSid(win32security.WinWorldSid) > > FILE_WRITE = (ntsecuritycon.FILE_GENERIC_WRITE & > ntsecuritycon.SPECIFIC_RIGHTS_ALL) > > def deny_write(filename, account=None, ace_flags=0): > sd = win32security.GetFileSecurity( > filename, win32security.DACL_SECURITY_INFORMATION) > sid = WORLD if account is None else ( > win32security.LookupAccountName(None, account)[0]) > dacl = sd.GetSecurityDescriptorDacl() > dacl.AddAccessDeniedAceEx( > win32security.ACL_REVISION_DS, ace_flags, FILE_WRITE, sid) > sd.SetSecurityDescriptorDacl(1, dacl, 0) > win32security.SetFileSecurity( > filename, win32security.DACL_SECURITY_INFORMATION, sd) > > For a directory, generic write access entails the ability to write > attributes and add files and subdirectories. Note that file delete > rights are separately controlled by standard DELETE access and the > specific directory right FILE_DELETE_CHILD, which is the right to > delete files or subdirectories of a directory, even if the user is > otherwise denied or not granted DELETE access. > > The ace_flags parameter allows controlling whether the ACE is > inherited by subdirectories and files (CONTAINER_INHERIT_ACE, > OBJECT_INHERIT_ACE) , whether the inheritance flags get propagated > (NO_PROPAGATE_INHERIT_ACE), and whether the ACE applies only for > inheritance (INHERIT_ONLY_ACE). > > For reference, here's an access mask diagram: > > 3 3 2 2 2 2 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 > 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 > +---------------+---------------+-------------------------------+ > |G|G|G|G|Resvd|A| StandardRights| SpecificRights | > |R|W|E|A| |S| | | > +-+-------------+---------------+-------------------------------+ > > Generic Read > Generic Write > Generic Execute > Generic All > Reserved: 3 > Access SACL > Standard Rights: 8 > Specific Rights: 16 > > The four most significant bits are the generic rights. Before > evaluating an AccessCheck, the system maps generic rights in access > masks to the corresponding standard and specific rights. > > Only 5 of the 8 possible standard rights have been assigned: > SYNCHRONIZE (bit 20), WRITE_OWNER, WRITE_DAC, READ_CONTROL, and DELETE > (bit 16). > > The File type assigns 9 out of 16 possible specific rights, from > FILE_WRITE_ATTRIBUTES (bit 8) down to FILE_READ_DATA (bit 0). Some > bits have multiple meanings depending on whether the object is a > directory, data file, or named pipe. For example, bit 2 can mean > FILE_ADD_SUBDIRECTORY, FILE_APPEND_DATA, or FILE_CREATE_PIPE_INSTANCE. > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From dominik.heller1 at gmail.com Tue Sep 27 12:33:18 2016 From: dominik.heller1 at gmail.com (Dominik .) Date: Tue, 27 Sep 2016 18:33:18 +0200 Subject: [python-win32] win32com.client: Struggling with dynamic dispatch, behavior differs when debugging Message-ID: Hi, I?m trying to control an existing COM server (C++ code) with a python COM client. Unfortunately, no type library exists for most of the COM objects. Thus I?m restricted to the dynamic dispatch implementation. This is my sample code. Its equivalent works flawlessly when called via VBA, moreover I'm sure that the requested COM methods exist in the server. import win32com.client obj_1 = win32com.client.DispatchEx(?MyCOMServerApplication?) obj_2 = obj_1.NewDocument() # works, returns a new dynamic dispatch () obj_2.SubObject.DoSomething(?MyArgument?) # works, but only if I don?t step into it (i.e. into CDispatch.__getattr__) #obj_2.GetSomeNumber() # TypeError: 'int' object is not callable obj_2.GetSomeNumber # works correctly, but only if I don?t step into it (i.e. into CDispatch.__getattr__) obj_2.DoSomething(?MyArgument?) # doesn?t work I also tried passing any arguments (e.g. ?MyArgument?) as VARIANTs, but to no avail. Evidently I?m very confused, especially since the behavior differs when stepping into the relevant python code. I have also read that the dynamic dispatch implementation doesn't support by-ref parameters, is this information still up to date? Looking forward to any help. If needed, I'll gladly provide more information. Thanks, Dominik -------------- next part -------------- An HTML attachment was scrubbed... URL: From timr at probo.com Wed Sep 28 14:45:24 2016 From: timr at probo.com (Tim Roberts) Date: Wed, 28 Sep 2016 11:45:24 -0700 Subject: [python-win32] win32com.client: Struggling with dynamic dispatch, behavior differs when debugging In-Reply-To: References: Message-ID: Dominik . wrote: > > I?m trying to control an existing COM server (C++ code) with a python > COM client. > > Unfortunately, no type library exists for most of the COM objects. > Thus I?m restricted to the dynamic dispatch implementation. > Do you have an IDL file or a C++ header file? It might be possible for you to build a type library. Dynamic dispatch has rather strict rules on the data types and parameter usages. Many C++ programmers totally disregard those rules, and treat a COM interface as if it were a simple pure virtual base class. It's not hard to build C++ interfaces that cannot be called dynamically. > > This is my sample code. Its equivalent works flawlessly when called > via VBA, moreover I'm sure that the requested COM methods exist in the > server. > > import win32com.client > > obj_1 = win32com.client.DispatchEx(?MyCOMServerApplication?) > > obj_2 = obj_1.NewDocument() # works, returns a new dynamic dispatch > () > > obj_2.SubObject.DoSomething(?MyArgument?) # works, but only if I don?t > step into it (i.e. into CDispatch.__getattr__) > > #obj_2.GetSomeNumber() # TypeError: 'int' object is not callable > > obj_2.GetSomeNumber # works correctly, but only if I don?t step into > it (i.e. into CDispatch.__getattr__) > This suggests that GetSomeNumber is being interpreted as a property. > obj_2.DoSomething(?MyArgument?) # doesn?t work > What is the C++ signature of this method? > Evidently I?m very confused, especially since the behavior differs > when stepping into the relevant python code. > Yeah, don't do that. There's a fair amount of magic going on in the COM glue. > I have also read that the dynamic dispatch implementation doesn't > support by-ref parameters, is this information still up to date? > Pretty much. The C++ implementation is expected to identify one or more [output] parameters. The Python wrapper will return those values. You don't pass a location for them. So, if you have a method to compute the product and average of two numbers: HRESULT TimesAndAverage( long one, long two, long * prod, long * avg ); If it is declared correctly in the server, you would call it from Python as: (res, prod, avg) = iface.TimesAndAverage( 3, 4 ) -- Tim Roberts, timr at probo.com Providenza & Boekelheide, Inc. From dominik.heller1 at gmail.com Thu Sep 29 03:29:45 2016 From: dominik.heller1 at gmail.com (Dominik Heller) Date: Thu, 29 Sep 2016 09:29:45 +0200 Subject: [python-win32] win32com.client: Struggling with dynamic dispatch, behavior differs when debugging Message-ID: Hi Tim, thanks for your reply, much appreciated. > Do you have an IDL file or a C++ header file? It might be possible for > you to build a type library. I do even have the complete C++ source. However I currently have no possibility to generate the IDL-files in an automated way and it's too much to do by hand, let alone maintaining these files. It might be possible to have another look into this in the future, maybe even generating these files with a script or something. > >> obj_2.DoSomething(?MyArgument?) # doesn?t work >> > >What is the C++ signature of this method? > This would be the declaration in the C++ class header: class CMyCommand : public CCmdTarget { // ... afx_msg void DoSomething(LPCTSTR message); // ... }; with this being the dispatch macro in the corresponding cpp: DISP_FUNCTION(CMyCommand, "DoSomething", DoSomething, VT_EMPTY, VTS_BSTR) Basically, it seems that on the obj_2 "main" dispatch, I can't use any methods which do require parameters (such as the BSTR here). Having GetSomeNumber as a property sounds false to me as well, it shouldn't be possible to set the value this COM method returns. It is declared/dispatched with: afx_msg long GetSomeNumber(); DISP_FUNCTION(CMyCommand, "GetSomeNumber", GetSomeNumber, VT_I4, VTS_NONE) > Dynamic dispatch has rather strict rules on the data types and parameter > usages. Many C++ programmers totally disregard those rules, and treat a > COM interface as if it were a simple pure virtual base class. It's not > hard to build C++ interfaces that cannot be called dynamically. So if I understand you correctly, it should be possible to use all these methods even with a dynamic python dispatch object, as long as they're implemented correctly on C++ side? What could be the thing going wrong in the C++ code? > Pretty much. The C++ implementation is expected to identify one or more > [output] parameters. The Python wrapper will return those values. You > don't pass a location for them. So if I'm aware that a python tuple is returned and the parameter list for the call is thus shorter, I can still call it on a dynamic dispatch? Basically I'm trying to find out how much my life would get easier if I somehow generated those IDL-files, or if rather the existing C++ COM interface needs to be fixed. From timr at probo.com Thu Sep 29 13:08:00 2016 From: timr at probo.com (Tim Roberts) Date: Thu, 29 Sep 2016 10:08:00 -0700 Subject: [python-win32] win32com.client: Struggling with dynamic dispatch, behavior differs when debugging In-Reply-To: References: Message-ID: <2f3452ed-317d-b268-4e70-0ed2dc50ee3b@probo.com> Dominik Heller wrote: > >> >>> obj_2.DoSomething(?MyArgument?) # doesn?t work >> What is the C++ signature of this method? > This would be the declaration in the C++ class header: > > class CMyCommand : public CCmdTarget { > // ... > afx_msg void DoSomething(LPCTSTR message); > // ... > }; > > with this being the dispatch macro in the corresponding cpp: > > DISP_FUNCTION(CMyCommand, "DoSomething", DoSomething, VT_EMPTY, VTS_BSTR) That's odd. Is your application compiled with -DUNICODE? BSTR is always Unicode, but LPCTSTR depends on the compiled character set. I would expect it to be LPCWSTR. However, if it works for "obj_2.SubObject.DoSomething", then that's not a problem. What do you mean by "doesn't work"? Is the method missing, or do you get trash results? > Having GetSomeNumber as a property sounds false to me as well, it shouldn't > be possible to set the value this COM method returns. > It is declared/dispatched with: > > afx_msg long GetSomeNumber(); > DISP_FUNCTION(CMyCommand, "GetSomeNumber", GetSomeNumber, VT_I4, VTS_NONE) Well, it's all about interpretation. A method that returns one thing and accepts no parameters is (apparently) exposed by the Python COM wrapper as a read-only property, and that's a reasonable interpretation. > So if I understand you correctly, it should be possible to use all these > methods even with a dynamic python dispatch object, as long as they're > implemented correctly on C++ side? What could be the thing going wrong in > the C++ code? By "implemented correctly", I really meant "declared correctly". The IDispatch handler in your code doesn't have a clue what the C++ function signatures actually are. It has to trust your dispatch map. If there is disagreement, garbage results. > So if I'm aware that a python tuple is returned and the parameter list for > the call is thus shorter, I can still call it on a dynamic dispatch? That's the theory. ;) Most true COM-compliant functions return an HRESULT, with a by-reference parameter as the output value. In that case, the Python COM wrapper returns a tuple with those two values. > Basically I'm trying to find out how much my life would get easier if I > somehow generated those IDL-files, or if rather the existing C++ COM > interface needs to be fixed. That's a very good question. You will probably end up having to print out what type mapping the Python COM wrappers have done. That's easier if you have a makepy result from a type library, but I believe it's still possible with an IDispatch. I just haven't done it in a while to remember the recipe. -- Tim Roberts, timr at probo.com Providenza & Boekelheide, Inc. From dominik.heller1 at gmail.com Fri Sep 30 04:01:10 2016 From: dominik.heller1 at gmail.com (Dominik Heller) Date: Fri, 30 Sep 2016 10:01:10 +0200 Subject: [python-win32] win32com.client: Struggling with dynamic dispatch, behavior differs when debugging Message-ID: > That's odd. Is your application compiled with -DUNICODE? BSTR is > always Unicode, but LPCTSTR depends on the compiled character set. I > would expect it to be LPCWSTR. However, if it works for > "obj_2.SubObject.DoSomething", then that's not a problem. It's compiled with /D "_MBCS" so it should indeed be a wide string. But I don't think it's related to the character set as it also fails e.g. with integer arguments. Consider the following snippet: # subobject nnames = obj_1.SubObj.GetNumberOfNames # nnames: 4 -> ok! names = [obj_1.SubObj.GetName(i) for i in xrange(nnames)] # names: [u'a', u'PP', u'N', u'L'] -> ok! # parent object nnames_2 = obj_1.GetNumberOfNames # nnames_2: 4 -> ok! names_2 = [obj_1.GetName(i) for i in xrange(nnames_2)] # pnames: [None, None, None, None] -> wrong! So again it works on the sub object but not on the parent (if anything, I'd have expected it the other way around if maybe the subobject could not be determined properly). The methods share the same interface and implementation in both objects, they even use the same C++ command base class. They should return the same results not only for number of names but also the names. DISP_FUNCTION(CMyCommand, "GetName", GetName, VT_BSTR, VTS_I4) BSTR CMyCommand::GetName(long index) But even completely without strings, simple methods won't work on obj_1, e.g. something like double CosD(double degrees), but will work on SubObj, e.g. double GetValue(long index). Long story short, it seems the only thing I can get to work on obj_1 are methods without any arguments. On SubObj, most things seem to work except for call-by-ref parameters. > What do you mean by "doesn't work"? Is the method missing, or do you > get trash results? I don't get a Python exception (or any result or output). I can also see that in the C++ code the method is not called. I even tried to set earlier breakpoints in OLE message handlers but wasn't able to find any trace of evidence that some COM call was triggered at all. > By "implemented correctly", I really meant "declared correctly". The > IDispatch handler in your code doesn't have a clue what the C++ function > signatures actually are. It has to trust your dispatch map. If there > is disagreement, garbage results. Ok, I get that. However since the same interface is working without problems with VBA I'm doubtful if it is really related to a wrong interface declaration. Is there any way to explicitly tell the Python wrapper about the interface to use without using makepy?