Solved

WM_COPYDATA need  to correct errors.any one help me

Posted on 2003-11-10
13
515 Views
Last Modified: 2013-11-20
I have used a structure and the following code . i am getting error access violation when message is sent to destination window. i am not able find were the error lies. plz any one help  me .
typedef struct tagSII{
      long lsessionID;
      long lqueue;
                CString  sCommand;
}SII ;
//Sending window
CWnd *pPdmm;

LRESULT lresult;
COPYDATASTRUCT copy;
HANDLE hWnd(this);

SII sii;       
      
  pPdmm = CWnd::FindWindow(NULL,"di");
 if(pPdmm == NULL){
  MessageBox("Would not find",NULL,MB_OK);
 }
else{
      sii.lsessionID = 4;
      sii.lqueue     = 5;
      sii.sCommand ="ab";
            
      copy.dwData =500;
      copy.cbData = sizeof(sii);
      copy.lpData = &sii;
lresult =pPdmm->SendMessage(WM_COPYDATA,(WPARAM)(HWND)m_hWnd,(LPARAM)(LPVOID)   &copy);
            
      }

      if ( lresult== TRUE)
            MessageBox("posted",NULL,MB_OK);
      else
            MessageBox("Failed",NULL,MB_OK);

//Receiving window

BOOL CDiDlg::OnCopyData(CWnd* pWnd, COPYDATASTRUCT* pCopyDataStruct)
{
      if( pCopyDataStruct->cbData == sizeof(SII ) )
            {
                  SII sii1;
                  SII sii2;
            memcpy( &sii1, pCopyDataStruct->lpData, sizeof( SII ) );
           sii2.lsessionID=sii1.lsessionID;
             sii2.lqueue    =sii1.lqueue;
              sii2.sCommand      =sii2.sCommand;
         
             MessageBox(sii1.sCommand);
             return TRUE;
            }
 return FALSE;

}

0
Comment
Question by:sarath83
  • 7
  • 6
13 Comments
 
LVL 8

Expert Comment

by:martynjpearson
ID: 9720735
I'm not sure about the validity of doing the line

memcpy( &sii1, pCopyDataStruct->lpData, sizeof( SII ) );

This is all very well when copying basic data, but I'm fairly certain that this will not set up the CString correctly. You would be better off to do a cast instead, like this :

SII * pSII = (SII *)pCopyDataStruct->lpData
sii1.sCommand = pSII->sCommand; etc

Hope this helps
Martyn
0
 

Author Comment

by:sarath83
ID: 9720889
i am getting the error"memory cannot b read" when i send the message
0
 
LVL 8

Expert Comment

by:martynjpearson
ID: 9720969
I've had a look at the documentation for WM_COPYDATA, and came across the line :

"The data being passed must not contain pointers or other references to objects not accessible to the application receiving the data. "

What this means is that your SII struct can't contain pointers to local memory, and I would imagine that it is the CString that is causing the problem. Instead, you could have a character buffer in SII instead of a CString, or you'd have to dynamically allocate a chunk of memory to hold your SII members and the string, and then copy the data into it for sending.

So, something like this :

long lBufferLength = sizeof(long) + sizeof(long) + sCommand.GetLength() + 1
BYTE * pBuffer = new BYTE(lBufferLength);

memcpy(pBuffer, &sii.lsessionID, sizeof(long));
memcpy(pBuffer, &sii.lqueue, sizeof(long));
strcpy((char *)&pBuffer[sizeof(long) + sizeof(long)], sCommand);

Then send pBuffer as the data.

All the best
Martyn


0
 

Author Comment

by:sarath83
ID: 9720996
is there any onther technique  available to do this
0
 
LVL 8

Expert Comment

by:martynjpearson
ID: 9721022
When you set up the COPYDATASTRUCT structure, you pass it a pointer to some data. It doesn't matter what the data is, but it cannot include pointers to other data. So, in other words, all the data you want to be copied has to be within that structure - with no pointers to any other data.

So, one approach is the one that I have suggested above, where you allocate a buffer, place your data into it and send it. Another approach could be to replace your CString with a fixed length character array in SII. However, this is less flexible as the number of charcters you send is fixed, and of course there will always be an upper limit. If you are always sending the same number of characters, this is fine, but what if you could send anywhere between 1 and 64,000 characters - you wouldn't want to have an array of 64,000 chars as that would mean that you are copying 64k EVERY time - even if you are really only sending one character.

Martyn
0
 

Author Comment

by:sarath83
ID: 9721056
Then hw to  retrieve the data in destination window. I wish to send using CString .
0
How to run any project with ease

Manage projects of all sizes how you want. Great for personal to-do lists, project milestones, team priorities and launch plans.
- Combine task lists, docs, spreadsheets, and chat in one
- View and edit from mobile/offline
- Cut down on emails

 
LVL 8

Expert Comment

by:martynjpearson
ID: 9721075
Assuming when sending the data, you have built up a buffer containing the longs, and the characters of the string, you can do the following to put your data back together :

BOOL CDiDlg::OnCopyData(CWnd* pWnd, COPYDATASTRUCT* pCopyDataStruct)
{
    SII sii;
    memcpy( &sii1.lsessionID, pCopyDataStruct->lpData, sizeof(long) );
    memcpy( &sii1.lsessionID, pCopyDataStruct->lpData, sizeof(long) );
    sii1.sCommand = CString((const char *)&pCopyDataStruct->lpData[sizeof(long) + sizeof(long)]);

    return TRUE;
}


Martyn
0
 

Author Comment

by:sarath83
ID: 9721097
Can I use this lines to send data

                                copy.dwData =500;
            copy.cbData = sizeof(pBuffer);
            copy.lpData = &pBuffer;
            lresult =pPdmm->SendMessage(WM_COPYDATA,(WPARAM)(HWND)m_hWnd,(LPARAM) &pBuffer);
0
 

Author Comment

by:sarath83
ID: 9721166
please help me out hw to do this .i am trying this for a very long time.
0
 

Author Comment

by:sarath83
ID: 9721267
sii1.sCommand = CString((const char *)&pCopyDataStruct->lpData[sizeof(long) + sizeof(long)]);
for the above line i am getting error :

 C2036: 'void *' : unknown size
0
 
LVL 8

Accepted Solution

by:
martynjpearson earned 55 total points
ID: 9721439
Firstly, on the receive side, my code needs a couple of changes :

   BYTE * pData = (BYTE *)pCopyDataStruct->lpData;
 SII sii;
    memcpy( &sii1.lsessionID, pData, sizeof(long) );
    memcpy( &sii1.lqueue, &pData[sizeof(long)], sizeof(long) );
    sii1.sCommand = CString((const char *)&pData[sizeof(long) + sizeof(long)]);

    return TRUE;

That should solve your C2036 error.

For sending the data, your code needs to be like this :

copy.dwData =500;
copy.cbData = lBufferLength;
copy.lpData = pBuffer;
lresult =pPdmm->SendMessage(WM_COPYDATA,(WPARAM)(HWND)m_hWnd,(LPARAM)(LPVOID)   &copy);


Martyn
0
 

Author Comment

by:sarath83
ID: 9721523
Mr.Martyn Thanku very much . its working . Can u plz suggets me which books to follow to learn VC++ . I am a beginner.
0
 
LVL 8

Expert Comment

by:martynjpearson
ID: 9721557
No problems - glad it's working now!

With regards to books, that's a tricky one, as the ones that I learnt from are probably no longer in print!! I learnt C and C++ at university, and then when I started programming for Windows (using Visual C++ 4.0 on Windows 95!!!) I had a book published by Sams, called Essential Visual C++ 4.0. This was quite good in that it covered all the basics, like dialogs, documents etc, and then went on to cover the basics of graphics using brushes, pens etc.

In the past, I have found the Wrox books to be of consistently high quality - check out www.wrox.com - and they generally do books that are aimed at a particular level, such as beginner, intermediate, expert etc.

All the best!
Martyn
0

Featured Post

How your wiki can always stay up-to-date

Quip doubles as a “living” wiki and a project management tool that evolves with your organization. As you finish projects in Quip, the work remains, easily accessible to all team members, new and old.
- Increase transparency
- Onboard new hires faster
- Access from mobile/offline

Join & Write a Comment

Suggested Solutions

Title # Comments Views Activity
Strange date stored 22 100
Pressing cancel button with C# UI Automation 3 40
sum28 challenge 31 96
sumHeights2  challenge 7 78
In this article, I'll describe -- and show pictures of -- some of the significant additions that have been made available to programmers in the MFC Feature Pack for Visual C++ 2008.  These same feature are in the MFC libraries that come with Visual …
Introduction: Hints for the grid button.  Nested classes, templated collections.  Squash that darned bug! Continuing from the sixth article about sudoku.   Open the project in visual studio. First we will finish with the SUD_SETVALUE messa…
This video will show you how to get GIT to work in Eclipse.   It will walk you through how to install the EGit plugin in eclipse and how to checkout an existing repository.
In this seventh video of the Xpdf series, we discuss and demonstrate the PDFfonts utility, which lists all the fonts used in a PDF file. It does this via a command line interface, making it suitable for use in programs, scripts, batch files — any pl…

759 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

20 Experts available now in Live!

Get 1:1 Help Now