PyWin SendMessage

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • g.franzkowiak

    PyWin SendMessage

    Hello everybody,

    I've tryed to use an interprocess communication via
    SendMessage on Windows.
    Unfortunately, nothing goes on

    ############### ############### ############### ############### #############
    #! /usr/bin/env python

    import win32api, win32ui, win32con
    import struct, array

    """
    typedef struct tagCOPYDATASTRU CT { // cds
    DWORD dwData;
    DWORD cbData;
    PVOID lpData;
    } COPYDATASTRUCT;
    """

    def packCopyData(nN um, sString):
    int_buffer = array.array("L" ,[nNum])
    char_buffer = array.array('c' , sString)
    int_buffer_addr ess = int_buffer.buff er_info()[0]
    char_buffer_add ress = char_buffer.buf fer_info()[0]
    char_buffer_siz e = char_buffer.buf fer_info()[1]
    copy_struct = struct.pack("pL p", # dword*, dword, char*
    int_buffer_addr ess,
    char_buffer_siz e,
    char_buffer)
    return copy_struct


    # get the window handle
    hwnd = win32ui.FindWin dow(None, "special window")

    # print just for fun
    print hwnd

    cds = packCopyData(1, '1')
    print cds

    # try to send it a message
    win32api.SendMe ssage(hwnd,
    win32con.WM_COP YDATA,
    0,
    cds)

    ############### ############### ############### ############### #############

    The last parameter shut be an integer, but I think it must be a pointer ?

    Any experience or a tip for me ?


    gf
  • Thomas Heller

    #2
    Re: PyWin SendMessage

    "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
    [color=blue]
    > Hello everybody,
    >
    > I've tryed to use an interprocess communication via
    > SendMessage on Windows.
    > Unfortunately, nothing goes on
    >
    > ############### ############### ############### ############### #############
    > #! /usr/bin/env python
    >
    > import win32api, win32ui, win32con
    > import struct, array
    >
    > """
    > typedef struct tagCOPYDATASTRU CT { // cds
    > DWORD dwData;
    > DWORD cbData;
    > PVOID lpData;
    > } COPYDATASTRUCT;
    > """
    >
    > def packCopyData(nN um, sString):
    > int_buffer = array.array("L" ,[nNum])
    > char_buffer = array.array('c' , sString)
    > int_buffer_addr ess = int_buffer.buff er_info()[0]
    > char_buffer_add ress = char_buffer.buf fer_info()[0]
    > char_buffer_siz e = char_buffer.buf fer_info()[1]
    > copy_struct = struct.pack("pL p", # dword*, dword, char*
    > int_buffer_addr ess,
    > char_buffer_siz e,
    > char_buffer)
    > return copy_struct[/color]

    After packCopyData(.. .) returns, the arrays are destroyed, which will
    probably void their contents. You must keep them alive until you don't
    need the COPYDATASTRUCT instance any longer. For this kind of stuff,
    ctypes may be easier to use than pywin32.

    Thomas

    Comment

    • g.franzkowiak

      #3
      Re: PyWin SendMessage

      Thomas Heller schrieb:[color=blue]
      > "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
      >
      >[color=green]
      >>Hello everybody,
      >>
      >>I've tryed to use an interprocess communication via
      >>SendMessage on Windows.
      >>Unfortunately , nothing goes on
      >>
      >>############# ############### ############### ############### ###############
      >>#! /usr/bin/env python
      >>
      >>import win32api, win32ui, win32con
      >>import struct, array
      >>
      >>"""
      >>typedef struct tagCOPYDATASTRU CT { // cds
      >> DWORD dwData;
      >> DWORD cbData;
      >> PVOID lpData;
      >>} COPYDATASTRUCT;
      >>"""
      >>
      >>def packCopyData(nN um, sString):
      >> int_buffer = array.array("L" ,[nNum])
      >> char_buffer = array.array('c' , sString)
      >> int_buffer_addr ess = int_buffer.buff er_info()[0]
      >> char_buffer_add ress = char_buffer.buf fer_info()[0]
      >> char_buffer_siz e = char_buffer.buf fer_info()[1]
      >> copy_struct = struct.pack("pL p", # dword*, dword, char*
      >> int_buffer_addr ess,
      >> char_buffer_siz e,
      >> char_buffer)
      >> return copy_struct[/color]
      >
      >
      > After packCopyData(.. .) returns, the arrays are destroyed, which will
      > probably void their contents. You must keep them alive until you don't
      > need the COPYDATASTRUCT instance any longer. For this kind of stuff,
      > ctypes may be easier to use than pywin32.
      >
      > Thomas[/color]

      Hmm, have read something in <<http://aspn.activestat e.com>>
      and the script changed to this:

      #---------------------------------------------------------
      #! /usr/bin/env python

      import win32api, win32ui, win32con, win32gui
      import struct, array
      from ctypes import *

      """
      typedef struct tagCOPYDATASTRU CT { // cds
      DWORD dwData;
      DWORD cbData;
      PVOID lpData;
      } COPYDATASTRUCT;
      """

      class COPYDATATYPE(St ructure):
      _fields_ = [("nNum", c_ulong),
      ("szData", c_char_p)]

      class COPYDATASTRUCT( Structure):
      _fields_ = [("dwData", c_ulong),
      ("cbData", c_ulong),
      ("lpData", POINTER(COPYDAT ATYPE))]

      # get the window handle
      hwnd = win32ui.FindWin dow(None, "target window")

      # print just for fun
      # ##print hwnd

      # prepare copydata structure for sending data
      cpyData = COPYDATATYPE(1, '1')
      cds = COPYDATASTRUCT( c_ulong(1),
      c_ulong(sizeof( cpyData)),
      pointer(cpyData ))

      # try to send a message
      win32api.SendMe ssage(hwnd,
      win32con.WM_COP YDATA,
      0,
      pointer(cds))

      #---------------------------------------------------------
      and the message for the last line is:
      ==> TypeError: an integer is required"

      This message comes with "pointer(cd s)" and with "addressof(cds) "


      gerd

      Comment

      • Thomas Heller

        #4
        Re: PyWin SendMessage

        "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
        [color=blue]
        > Thomas Heller schrieb:[color=green]
        >> "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
        >>
        >>[color=darkred]
        >>>Hello everybody,
        >>>
        >>>I've tryed to use an interprocess communication via
        >>>SendMessag e on Windows.
        >>>Unfortunatel y, nothing goes on
        >>>
        >>>############ ############### ############### ############### ############### #
        >>>#! /usr/bin/env python
        >>>
        >>>import win32api, win32ui, win32con
        >>>import struct, array
        >>>
        >>>"""
        >>>typedef struct tagCOPYDATASTRU CT { // cds
        >>> DWORD dwData;
        >>> DWORD cbData;
        >>> PVOID lpData;
        >>>} COPYDATASTRUCT;
        >>>"""
        >>>
        >>>def packCopyData(nN um, sString):
        >>> int_buffer = array.array("L" ,[nNum])
        >>> char_buffer = array.array('c' , sString)
        >>> int_buffer_addr ess = int_buffer.buff er_info()[0]
        >>> char_buffer_add ress = char_buffer.buf fer_info()[0]
        >>> char_buffer_siz e = char_buffer.buf fer_info()[1]
        >>> copy_struct = struct.pack("pL p", # dword*, dword, char*
        >>> int_buffer_addr ess,
        >>> char_buffer_siz e,
        >>> char_buffer)
        >>> return copy_struct[/color]
        >>
        >>
        >> After packCopyData(.. .) returns, the arrays are destroyed, which will
        >> probably void their contents. You must keep them alive until you don't
        >> need the COPYDATASTRUCT instance any longer. For this kind of stuff,
        >> ctypes may be easier to use than pywin32.
        >>
        >> Thomas[/color]
        >
        > Hmm, have read something in <<http://aspn.activestat e.com>>
        > and the script changed to this:
        >
        > #---------------------------------------------------------
        > #! /usr/bin/env python
        >
        > import win32api, win32ui, win32con, win32gui
        > import struct, array
        > from ctypes import *
        >
        > """
        > typedef struct tagCOPYDATASTRU CT { // cds
        > DWORD dwData;
        > DWORD cbData;
        > PVOID lpData;
        > } COPYDATASTRUCT;
        > """
        >
        > class COPYDATATYPE(St ructure):
        > _fields_ = [("nNum", c_ulong),
        > ("szData", c_char_p)]
        >
        > class COPYDATASTRUCT( Structure):
        > _fields_ = [("dwData", c_ulong),
        > ("cbData", c_ulong),
        > ("lpData", POINTER(COPYDAT ATYPE))]
        >
        > # get the window handle
        > hwnd = win32ui.FindWin dow(None, "target window")
        >
        > # print just for fun
        > # ##print hwnd
        >
        > # prepare copydata structure for sending data
        > cpyData = COPYDATATYPE(1, '1')
        > cds = COPYDATASTRUCT( c_ulong(1),
        > c_ulong(sizeof( cpyData)),
        > pointer(cpyData ))
        >
        > # try to send a message
        > win32api.SendMe ssage(hwnd,
        > win32con.WM_COP YDATA,
        > 0,
        > pointer(cds))
        >
        > #---------------------------------------------------------
        > and the message for the last line is:
        > ==> TypeError: an integer is required"
        >
        > This message comes with "pointer(cd s)" and with "addressof(cds) "[/color]

        That error refers to the first argument - win32ui.FindWin dow returns a
        PyCWnd object, which is not accepted by win32api.SendMe ssage.
        Changing this brings you one step further. win32api.SendMe ssage accepts
        an integer for the last element, so addressof(cds) should work now.

        win32gui.SendMe ssage is more tolerant in what it accepts as 4th
        argument, according to the error message you get when you try it it
        expects a string, a buffer, or an integer. So you could use addressof()
        or pointer(), what you like best.

        Thomas

        Comment

        • g.franzkowiak

          #5
          Re: PyWin SendMessage

          Thomas Heller schrieb:[color=blue]
          > "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
          >
          >[color=green]
          >>Thomas Heller schrieb:
          >>[color=darkred]
          >>>"g.franzkowi ak" <g.franzkowiak@ onlinehome.de> writes:
          >>>
          >>>
          >>>
          >>>>Hello everybody,
          >>>>
          >>>>I've tryed to use an interprocess communication via
          >>>>SendMessa ge on Windows.
          >>>>Unfortunate ly, nothing goes on
          >>>>
          >>>>########### ############### ############### ############### ############### ##
          >>>>#! /usr/bin/env python
          >>>>
          >>>>import win32api, win32ui, win32con
          >>>>import struct, array
          >>>>
          >>>>"""
          >>>>typedef struct tagCOPYDATASTRU CT { // cds
          >>>> DWORD dwData;
          >>>> DWORD cbData;
          >>>> PVOID lpData;
          >>>>} COPYDATASTRUCT;
          >>>>"""
          >>>>
          >>>>def packCopyData(nN um, sString):
          >>>> int_buffer = array.array("L" ,[nNum])
          >>>> char_buffer = array.array('c' , sString)
          >>>> int_buffer_addr ess = int_buffer.buff er_info()[0]
          >>>> char_buffer_add ress = char_buffer.buf fer_info()[0]
          >>>> char_buffer_siz e = char_buffer.buf fer_info()[1]
          >>>> copy_struct = struct.pack("pL p", # dword*, dword, char*
          >>>> int_buffer_addr ess,
          >>>> char_buffer_siz e,
          >>>> char_buffer)
          >>>> return copy_struct
          >>>
          >>>
          >>>After packCopyData(.. .) returns, the arrays are destroyed, which will
          >>>probably void their contents. You must keep them alive until you don't
          >>>need the COPYDATASTRUCT instance any longer. For this kind of stuff,
          >>>ctypes may be easier to use than pywin32.
          >>>
          >>>Thomas[/color]
          >>
          >>Hmm, have read something in <<http://aspn.activestat e.com>>
          >>and the script changed to this:
          >>
          >>#---------------------------------------------------------
          >>#! /usr/bin/env python
          >>
          >>import win32api, win32ui, win32con, win32gui
          >>import struct, array
          >>from ctypes import *
          >>
          >>"""
          >>typedef struct tagCOPYDATASTRU CT { // cds
          >> DWORD dwData;
          >> DWORD cbData;
          >> PVOID lpData;
          >>} COPYDATASTRUCT;
          >>"""
          >>
          >>class COPYDATATYPE(St ructure):
          >> _fields_ = [("nNum", c_ulong),
          >> ("szData", c_char_p)]
          >>
          >>class COPYDATASTRUCT( Structure):
          >> _fields_ = [("dwData", c_ulong),
          >> ("cbData", c_ulong),
          >> ("lpData", POINTER(COPYDAT ATYPE))]
          >>
          >># get the window handle
          >>hwnd = win32ui.FindWin dow(None, "target window")
          >>
          >># print just for fun
          >># ##print hwnd
          >>
          >># prepare copydata structure for sending data
          >>cpyData = COPYDATATYPE(1, '1')
          >>cds = COPYDATASTRUCT( c_ulong(1),
          >> c_ulong(sizeof( cpyData)),
          >> pointer(cpyData ))
          >>
          >># try to send a message
          >>win32api.Send Message(hwnd,
          >> win32con.WM_COP YDATA,
          >> 0,
          >> pointer(cds))
          >>
          >>#---------------------------------------------------------
          >>and the message for the last line is:
          >>==> TypeError: an integer is required"
          >>
          >>This message comes with "pointer(cd s)" and with "addressof(cds) "[/color]
          >
          >
          > That error refers to the first argument - win32ui.FindWin dow returns a
          > PyCWnd object, which is not accepted by win32api.SendMe ssage.
          > Changing this brings you one step further. win32api.SendMe ssage accepts
          > an integer for the last element, so addressof(cds) should work now.
          >
          > win32gui.SendMe ssage is more tolerant in what it accepts as 4th
          > argument, according to the error message you get when you try it it
          > expects a string, a buffer, or an integer. So you could use addressof()
          > or pointer(), what you like best.
          >
          > Thomas[/color]

          Hi Thomas,

          crazy, operates :-))
          Only 'addressof' is possible and
          merely the data types on the receiver side are not correct.
          I want use an int and char[256], must play...

          Thanks
          gerd

          Comment

          • g.franzkowiak

            #6
            Re: PyWin SendMessage

            Thomas Heller schrieb:[color=blue]
            > "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
            >
            >[color=green]
            >>Thomas Heller schrieb:
            >>[color=darkred]
            >>>"g.franzkowi ak" <g.franzkowiak@ onlinehome.de> writes:
            >>>
            >>>
            >>>
            >>>>Hello everybody,
            >>>>
            >>>>I've tryed to use an interprocess communication via
            >>>>SendMessa ge on Windows.
            >>>>Unfortunate ly, nothing goes on
            >>>>
            >>>>########### ############### ############### ############### ############### ##
            >>>>#! /usr/bin/env python
            >>>>
            >>>>import win32api, win32ui, win32con
            >>>>import struct, array
            >>>>
            >>>>"""
            >>>>typedef struct tagCOPYDATASTRU CT { // cds
            >>>> DWORD dwData;
            >>>> DWORD cbData;
            >>>> PVOID lpData;
            >>>>} COPYDATASTRUCT;
            >>>>"""
            >>>>
            >>>>def packCopyData(nN um, sString):
            >>>> int_buffer = array.array("L" ,[nNum])
            >>>> char_buffer = array.array('c' , sString)
            >>>> int_buffer_addr ess = int_buffer.buff er_info()[0]
            >>>> char_buffer_add ress = char_buffer.buf fer_info()[0]
            >>>> char_buffer_siz e = char_buffer.buf fer_info()[1]
            >>>> copy_struct = struct.pack("pL p", # dword*, dword, char*
            >>>> int_buffer_addr ess,
            >>>> char_buffer_siz e,
            >>>> char_buffer)
            >>>> return copy_struct
            >>>
            >>>
            >>>After packCopyData(.. .) returns, the arrays are destroyed, which will
            >>>probably void their contents. You must keep them alive until you don't
            >>>need the COPYDATASTRUCT instance any longer. For this kind of stuff,
            >>>ctypes may be easier to use than pywin32.
            >>>
            >>>Thomas[/color]
            >>
            >>Hmm, have read something in <<http://aspn.activestat e.com>>
            >>and the script changed to this:
            >>
            >>#---------------------------------------------------------
            >>#! /usr/bin/env python
            >>
            >>import win32api, win32ui, win32con, win32gui
            >>import struct, array
            >>from ctypes import *
            >>
            >>"""
            >>typedef struct tagCOPYDATASTRU CT { // cds
            >> DWORD dwData;
            >> DWORD cbData;
            >> PVOID lpData;
            >>} COPYDATASTRUCT;
            >>"""
            >>
            >>class COPYDATATYPE(St ructure):
            >> _fields_ = [("nNum", c_ulong),
            >> ("szData", c_char_p)]
            >>
            >>class COPYDATASTRUCT( Structure):
            >> _fields_ = [("dwData", c_ulong),
            >> ("cbData", c_ulong),
            >> ("lpData", POINTER(COPYDAT ATYPE))]
            >>
            >># get the window handle
            >>hwnd = win32ui.FindWin dow(None, "target window")
            >>
            >># print just for fun
            >># ##print hwnd
            >>
            >># prepare copydata structure for sending data
            >>cpyData = COPYDATATYPE(1, '1')
            >>cds = COPYDATASTRUCT( c_ulong(1),
            >> c_ulong(sizeof( cpyData)),
            >> pointer(cpyData ))
            >>
            >># try to send a message
            >>win32api.Send Message(hwnd,
            >> win32con.WM_COP YDATA,
            >> 0,
            >> pointer(cds))
            >>
            >>#---------------------------------------------------------
            >>and the message for the last line is:
            >>==> TypeError: an integer is required"
            >>
            >>This message comes with "pointer(cd s)" and with "addressof(cds) "[/color]
            >
            >
            > That error refers to the first argument - win32ui.FindWin dow returns a
            > PyCWnd object, which is not accepted by win32api.SendMe ssage.
            > Changing this brings you one step further. win32api.SendMe ssage accepts
            > an integer for the last element, so addressof(cds) should work now.
            >
            > win32gui.SendMe ssage is more tolerant in what it accepts as 4th
            > argument, according to the error message you get when you try it it
            > expects a string, a buffer, or an integer. So you could use addressof()
            > or pointer(), what you like best.
            >
            > Thomas[/color]

            Super, operates :-))

            My last answer must be in the Nirvana, strange ?

            Ok, only the version with 'addressof' generates a message and I must
            play with the data types. The receiver becomes a wrong data formate.
            Expect (int=1, char[256]='1\00'), but the int is 0x31 and the string
            somewhat. Must play with my data.

            Thanks
            gerd

            Comment

            • Gonzalo Monzón

              #7
              Re: PyWin SendMessage

              g.franzkowiak escribió:
              [color=blue]
              >Thomas Heller schrieb:
              >
              >[color=green]
              >>"g.franzkowia k" <g.franzkowiak@ onlinehome.de> writes:
              >>
              >>
              >>
              >>[color=darkred]
              >>>Thomas Heller schrieb:
              >>>
              >>>
              >>>
              >>>>"g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
              >>>>
              >>>>
              >>>>
              >>>>
              >>>>
              >>>>>Hello everybody,
              >>>>>
              >>>>>I've tryed to use an interprocess communication via
              >>>>>SendMessag e on Windows.
              >>>>>Unfortunat ely, nothing goes on
              >>>>>
              >>>>>########## ############### ############### ############### ############### ###
              >>>>>#! /usr/bin/env python
              >>>>>
              >>>>>import win32api, win32ui, win32con
              >>>>>import struct, array
              >>>>>
              >>>>>"""
              >>>>>typedef struct tagCOPYDATASTRU CT { // cds
              >>>>> DWORD dwData;
              >>>>> DWORD cbData;
              >>>>> PVOID lpData;
              >>>>>} COPYDATASTRUCT;
              >>>>>"""
              >>>>>
              >>>>>def packCopyData(nN um, sString):
              >>>>> int_buffer = array.array("L" ,[nNum])
              >>>>> char_buffer = array.array('c' , sString)
              >>>>> int_buffer_addr ess = int_buffer.buff er_info()[0]
              >>>>> char_buffer_add ress = char_buffer.buf fer_info()[0]
              >>>>> char_buffer_siz e = char_buffer.buf fer_info()[1]
              >>>>> copy_struct = struct.pack("pL p", # dword*, dword, char*
              >>>>> int_buffer_addr ess,
              >>>>> char_buffer_siz e,
              >>>>> char_buffer)
              >>>>> return copy_struct
              >>>>>
              >>>>>
              >>>>After packCopyData(.. .) returns, the arrays are destroyed, which will
              >>>>probably void their contents. You must keep them alive until you don't
              >>>>need the COPYDATASTRUCT instance any longer. For this kind of stuff,
              >>>>ctypes may be easier to use than pywin32.
              >>>>
              >>>>Thomas
              >>>>
              >>>>
              >>>Hmm, have read something in <<http://aspn.activestat e.com>>
              >>>and the script changed to this:
              >>>
              >>>#---------------------------------------------------------
              >>>#! /usr/bin/env python
              >>>
              >>>import win32api, win32ui, win32con, win32gui
              >>>import struct, array
              >>>
              >>>
              >>>from ctypes import *[/color]
              >>
              >>[color=darkred]
              >>>"""
              >>>typedef struct tagCOPYDATASTRU CT { // cds
              >>> DWORD dwData;
              >>> DWORD cbData;
              >>> PVOID lpData;
              >>>} COPYDATASTRUCT;
              >>>"""
              >>>
              >>>class COPYDATATYPE(St ructure):
              >>> _fields_ = [("nNum", c_ulong),
              >>> ("szData", c_char_p)]
              >>>
              >>>class COPYDATASTRUCT( Structure):
              >>> _fields_ = [("dwData", c_ulong),
              >>> ("cbData", c_ulong),
              >>> ("lpData", POINTER(COPYDAT ATYPE))]
              >>>
              >>># get the window handle
              >>>hwnd = win32ui.FindWin dow(None, "target window")
              >>>
              >>># print just for fun
              >>># ##print hwnd
              >>>
              >>># prepare copydata structure for sending data
              >>>cpyData = COPYDATATYPE(1, '1')
              >>>cds = COPYDATASTRUCT( c_ulong(1),
              >>> c_ulong(sizeof( cpyData)),
              >>> pointer(cpyData ))
              >>>
              >>># try to send a message
              >>>win32api.Sen dMessage(hwnd,
              >>> win32con.WM_COP YDATA,
              >>> 0,
              >>> pointer(cds))
              >>>
              >>>#---------------------------------------------------------
              >>>and the message for the last line is:
              >>>==> TypeError: an integer is required"
              >>>
              >>>This message comes with "pointer(cd s)" and with "addressof(cds) "
              >>>
              >>>[/color]
              >>That error refers to the first argument - win32ui.FindWin dow returns a
              >>PyCWnd object, which is not accepted by win32api.SendMe ssage.
              >>Changing this brings you one step further. win32api.SendMe ssage accepts
              >>an integer for the last element, so addressof(cds) should work now.
              >>
              >>win32gui.Send Message is more tolerant in what it accepts as 4th
              >>argument, according to the error message you get when you try it it
              >>expects a string, a buffer, or an integer. So you could use addressof()
              >>or pointer(), what you like best.
              >>
              >>Thomas
              >>
              >>[/color]
              >
              >Super, operates :-))
              >
              >My last answer must be in the Nirvana, strange ?
              >
              >Ok, only the version with 'addressof' generates a message and I must
              >play with the data types. The receiver becomes a wrong data formate.
              >Expect (int=1, char[256]='1\00'), but the int is 0x31 and the string
              >somewhat. Must play with my data.
              >
              >Thanks
              >gerd
              >
              >[/color]

              Hi Gerd,

              I'm not really sure of, but I think you must use a message value in
              range of WM_USER or WM_APP so this fact maybe let the receiver window
              getting bad data... have a look to this:



              0 through WM_USER
              <http://msdn.microsoft. com/library/en-us/winui/winui/windowsuserinte rface/windowing/messagesandmess agequeues/messagesandmess agequeuesrefere nce/messagesandmess agequeuesmessag es/wm_user.asp>
              0x0400
              Messages reserved for use by the system.
              *WM_USER* through 0x7FFF Integer messages for use by private window
              classes.
              *WM_APP* through 0xBFFF Messages available for use by applications.
              0xC000 through 0xFFFF String messages for use by applications.
              Greater than 0xFFFF Reserved by the system.



              I've done the same with PHP GTK and achieved random results sending low
              Msg values... until used WM_USER and above. Also, in my case only
              PostMessage work fine... try using both... but expect this doesn't
              happen with python,

              Hope it helps.

              Gonzalo

              Comment

              • g.franzkowiak

                #8
                Re: PyWin SendMessage

                Gonzalo Monzón schrieb:[color=blue]
                > g.franzkowiak escribió:
                >[color=green]
                >> Thomas Heller schrieb:
                >>
                >>[color=darkred]
                >>> "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
                >>>
                >>>
                >>>
                >>>
                >>>> Thomas Heller schrieb:
                >>>>
                >>>>
                >>>>
                >>>>> "g.franzkow iak" <g.franzkowiak@ onlinehome.de> writes:
                >>>>>
                >>>>>
                >>>>>
                >>>>>
                >>>>>
                >>>>>> Hello everybody,
                >>>>>>
                >>>>>> I've tryed to use an interprocess communication via
                >>>>>> SendMessage on Windows.
                >>>>>> Unfortunately, nothing goes on
                >>>>>>
                >>>>>> ############### ############### ############### ############### #############
                >>>>>>
                >>>>>> #! /usr/bin/env python
                >>>>>>
                >>>>>> import win32api, win32ui, win32con
                >>>>>> import struct, array
                >>>>>>
                >>>>>> """
                >>>>>> typedef struct tagCOPYDATASTRU CT { // cds
                >>>>>> DWORD dwData;
                >>>>>> DWORD cbData;
                >>>>>> PVOID lpData;
                >>>>>> } COPYDATASTRUCT;
                >>>>>> """
                >>>>>>
                >>>>>> def packCopyData(nN um, sString):
                >>>>>> int_buffer = array.array("L" ,[nNum])
                >>>>>> char_buffer = array.array('c' , sString)
                >>>>>> int_buffer_addr ess = int_buffer.buff er_info()[0]
                >>>>>> char_buffer_add ress = char_buffer.buf fer_info()[0]
                >>>>>> char_buffer_siz e = char_buffer.buf fer_info()[1]
                >>>>>> copy_struct = struct.pack("pL p", # dword*, dword, char*
                >>>>>> int_buffer_addr ess,
                >>>>>> char_buffer_siz e,
                >>>>>> char_buffer)
                >>>>>> return copy_struct
                >>>>>>
                >>>>>
                >>>>> After packCopyData(.. .) returns, the arrays are destroyed, which will
                >>>>> probably void their contents. You must keep them alive until you
                >>>>> don't
                >>>>> need the COPYDATASTRUCT instance any longer. For this kind of stuff,
                >>>>> ctypes may be easier to use than pywin32.
                >>>>>
                >>>>> Thomas
                >>>>>
                >>>>
                >>>> Hmm, have read something in <<http://aspn.activestat e.com>>
                >>>> and the script changed to this:
                >>>>
                >>>> #---------------------------------------------------------
                >>>> #! /usr/bin/env python
                >>>>
                >>>> import win32api, win32ui, win32con, win32gui
                >>>> import struct, array
                >>>>
                >>>> from ctypes import *
                >>>
                >>>
                >>>
                >>>> """
                >>>> typedef struct tagCOPYDATASTRU CT { // cds
                >>>> DWORD dwData;
                >>>> DWORD cbData;
                >>>> PVOID lpData;
                >>>> } COPYDATASTRUCT;
                >>>> """
                >>>>
                >>>> class COPYDATATYPE(St ructure):
                >>>> _fields_ = [("nNum", c_ulong),
                >>>> ("szData", c_char_p)]
                >>>>
                >>>> class COPYDATASTRUCT( Structure):
                >>>> _fields_ = [("dwData", c_ulong),
                >>>> ("cbData", c_ulong),
                >>>> ("lpData", POINTER(COPYDAT ATYPE))]
                >>>>
                >>>> # get the window handle
                >>>> hwnd = win32ui.FindWin dow(None, "target window")
                >>>>
                >>>> # print just for fun
                >>>> # ##print hwnd
                >>>>
                >>>> # prepare copydata structure for sending data
                >>>> cpyData = COPYDATATYPE(1, '1')
                >>>> cds = COPYDATASTRUCT( c_ulong(1),
                >>>> c_ulong(sizeof( cpyData)),
                >>>> pointer(cpyData ))
                >>>>
                >>>> # try to send a message
                >>>> win32api.SendMe ssage(hwnd,
                >>>> win32con.WM_COP YDATA,
                >>>> 0,
                >>>> pointer(cds))
                >>>>
                >>>> #---------------------------------------------------------
                >>>> and the message for the last line is:
                >>>> ==> TypeError: an integer is required"
                >>>>
                >>>> This message comes with "pointer(cd s)" and with "addressof(cds) "
                >>>>
                >>>
                >>> That error refers to the first argument - win32ui.FindWin dow returns a
                >>> PyCWnd object, which is not accepted by win32api.SendMe ssage.
                >>> Changing this brings you one step further. win32api.SendMe ssage accepts
                >>> an integer for the last element, so addressof(cds) should work now.
                >>>
                >>> win32gui.SendMe ssage is more tolerant in what it accepts as 4th
                >>> argument, according to the error message you get when you try it it
                >>> expects a string, a buffer, or an integer. So you could use addressof()
                >>> or pointer(), what you like best.
                >>>
                >>> Thomas
                >>>[/color]
                >>
                >>
                >> Super, operates :-))
                >>
                >> My last answer must be in the Nirvana, strange ?
                >>
                >> Ok, only the version with 'addressof' generates a message and I must
                >> play with the data types. The receiver becomes a wrong data formate.
                >> Expect (int=1, char[256]='1\00'), but the int is 0x31 and the string
                >> somewhat. Must play with my data.
                >>
                >> Thanks
                >> gerd
                >>
                >>[/color]
                >
                > Hi Gerd,
                >
                > I'm not really sure of, but I think you must use a message value in
                > range of WM_USER or WM_APP so this fact maybe let the receiver window
                > getting bad data... have a look to this:
                >
                > http://msdn.microsoft.com/library/de...es/wm_user.asp
                >
                >
                > 0 through WM_USER
                > <http://msdn.microsoft. com/library/en-us/winui/winui/windowsuserinte rface/windowing/messagesandmess agequeues/messagesandmess agequeuesrefere nce/messagesandmess agequeuesmessag es/wm_user.asp>
                > 0x0400
                > Messages reserved for use by the system.
                > *WM_USER* through 0x7FFF Integer messages for use by private window
                > classes.
                > *WM_APP* through 0xBFFF Messages available for use by applications.
                > 0xC000 through 0xFFFF String messages for use by applications.
                > Greater than 0xFFFF Reserved by the system.
                >
                >
                >
                > I've done the same with PHP GTK and achieved random results sending low
                > Msg values... until used WM_USER and above. Also, in my case only
                > PostMessage work fine... try using both... but expect this doesn't
                > happen with python,
                >
                > Hope it helps.
                >
                > Gonzalo[/color]


                Hi Gonzalo,

                thank you for your interest and for your tips.
                With your links was it possible to learn something over messages in user
                applications. I'm not the windows guru, like the open source scene.

                My problem was not the message type and I think the WM_COPYDATA is the
                right thing for interprocess communication between python and C++.
                I've changed in my script the COPYDATATYPE field szData from c_char_p to
                c_char * 256 and the memory is correct initialized. The first situation
                was according to **data and in consequence the wrong content on the
                receiver side.
                Now is it a good thing :-)

                gerd

                Comment

                • Tim Roberts

                  #9
                  Re: PyWin SendMessage

                  Gonzalo Monzón <gmc@serveisw3. net> wrote:[color=blue]
                  >
                  >Hi Gerd,
                  >
                  >I'm not really sure of, but I think you must use a message value in
                  >range of WM_USER or WM_APP so this fact maybe let the receiver window
                  >getting bad data...[/color]

                  No. WM_COPYDATA is designed specifically for his use case -- interprocess
                  communication. The WM_USER range is only if you are inventing a custom
                  message for some new purpose.
                  --
                  - Tim Roberts, timr@probo.com
                  Providenza & Boekelheide, Inc.

                  Comment

                  Working...