Home | Contact Us | FAQ | Search & Site Map | Link to Us
Sign In | Join | Other 45 Sites in Network
Home
Discussion GroupsVB SyntaxEnterprise DevelopmentDatabase AccessControlsCOMWin APICrystal ReportDeploymentGeneralGeneral 2
Related Topics
VB.NET / ASP.NETMS SQL ServerMS AccessOther Database ProductsMore Topics ...

VB Forum / General 2 / June 2004



Tip: Looking for answers? Try searching our database.

CopyMemory confusion...

Thread view: 
Enable EMail Alerts  Start New Thread
Thread rating: 
Don@home.com - 29 Jun 2004 13:11 GMT
I'll try to keep this as short and to the point as I can...
I'm doing a rewrite of some classes I downloaded from VBAdvance, image
processing...
I'm not all that familure using the CopyMemory API (RtlMoveMemory) and have
gotten confused as to just what in the hex is happening here...

First: Here is one (shortest) of the subs/functions that use CopyMemory...
After the code I have layed out the question(s)...

***Start Code***
Public Sub PerformCompositeClear()
' Both the color and the alpha of the destination are cleared.
' Neither the source nor the destination are used as input.
'  Dc' = 0
'  Da ' = 0
 
Dim srcX As Long
Dim srcY As Long
Dim srcWidth As Long
Dim srcHeight As Long
Dim bDibSrc() As Byte
Dim bDibDst() As Byte
Dim tSASrc As SAFEARRAY2D
Dim tSADst As SAFEARRAY2D
Dim x As Long
Dim y As Long
Dim xEnd As Long
Dim yEnd As Long
 
  If getSourceDimensions(srcX, srcY, srcWidth, srcHeight) Then
 
     ' Get the bits in the from DIB section:
     With tSASrc
         .cbElements = 1
         .cDims = 2
         .Bounds(0).lBound = 0
         .Bounds(0).cElements = m_cDibSrc.height
         .Bounds(1).lBound = 0
         .Bounds(1).cElements = m_cDibSrc.BytesPerScanLine
         .pvData = m_cDibSrc.DIBSectionBitsPtr
     End With
     CopyMemory ByVal VarPtrArray(bDibSrc()), VarPtr(tSASrc), 4
 
     ' Get the bits in the from DIB section:
     With tSADst
         .cbElements = 1
         .cDims = 2
         .Bounds(0).lBound = 0
         .Bounds(0).cElements = m_cDibDst.height
         .Bounds(1).lBound = 0
         .Bounds(1).cElements = m_cDibDst.BytesPerScanLine()
         .pvData = m_cDibDst.DIBSectionBitsPtr
     End With
     CopyMemory ByVal VarPtrArray(bDibDst()), VarPtr(tSADst), 4
 
     xEnd = srcX + srcWidth - 1
     yEnd = srcY + srcHeight - 1
     
     For x = srcX To xEnd Step 4
        For y = srcY To yEnd
           bDibDst(x, y) = 0
           bDibDst(x + 1, y) = 0
           bDibDst(x + 2, y) = 0
           bDibDst(x + 3, y) = 0
        Next y
     Next x
     
     CopyMemory ByVal VarPtrArray(bDibDst), 0&, 4
     CopyMemory ByVal VarPtrArray(bDibSrc), 0&, 4
 
  End If
 
End Sub
***End Code***

1) m_cDibSrc is another Class that holds the DIBSection... Not a problem...
2) Doesn't 'CopyMemory ByVal VarPtrArray(bDibDst()), VarPtr(tSADst), 4' just
copy the contents of the DIBSection into bDibDst()??? ie: Different memory
location...
3) The For...Next... loops modifies this new area of the memory, correct???
4) Doesn't 'CopyMemory ByVal VarPtrArray(bDibDst), 0&, 4' just clear this newly
created memory area???

Ok so what am I missing here??? How does the modified data get back to the
original memory location???

Have a good day...

Don
Peter Young - 29 Jun 2004 23:34 GMT
> I'll try to keep this as short and to the point as I can...
> I'm doing a rewrite of some classes I downloaded from VBAdvance, image
> processing...

I'm guessing you mean vbAccelerator, not vbAdvance.

> I'm not all that familure using the CopyMemory API (RtlMoveMemory) and have
> gotten confused as to just what in the hex is happening here...
>
> First: Here is one (shortest) of the subs/functions that use CopyMemory...
> After the code I have layed out the question(s)...

<snip>

> 1) m_cDibSrc is another Class that holds the DIBSection... Not a problem...
> 2) Doesn't 'CopyMemory ByVal VarPtrArray(bDibDst()), VarPtr(tSADst), 4' just
> copy the contents of the DIBSection into bDibDst()??? ie: Different memory
> location...

No. It copies the safearray pointer to the Byte array pointer, effectively 'casting' the Byte array variable to the DIB
data pointer, so that the data can be accessed as an array of Bytes. Necessary because VB doesn't provide a built-in way
to dereference a pointer. VB arrays are Win32 safearrays, and using this knowledge, you can use a safearray structure to
assign an arbitrary data pointer to a Byte array. It's a clever hack. I fairly certain this originated with Matt
Curland. He details it in his book:
http://www.powervb.com

> 3) The For...Next... loops modifies this new area of the memory, correct???

Yes. It's clearing portions of the data.

> 4) Doesn't 'CopyMemory ByVal VarPtrArray(bDibDst), 0&, 4' just clear this newly
> created memory area???

No. It frees the Byte array variables - just doing cleanup that the VB compiler wouldn't understand to do, since the
arrays weren't allocated normally.

> Ok so what am I missing here??? How does the modified data get back to the
> original memory location???

The pointer to the DIB was passed in, a Byte array variable was temporarily assigned to the same memory address,
allowing it to access the data in-place, and then the Byte array variable was freed. It's essentially doing the same
thing you'd do in C by using the dereference operator against a pointer variable.

HTH,
Pete
Don@home.com - 30 Jun 2004 12:53 GMT
>> I'll try to keep this as short and to the point as I can...
>> I'm doing a rewrite of some classes I downloaded from VBAdvance, image
>> processing...
>
>I'm guessing you mean vbAccelerator, not vbAdvance.

True!!! I don't know where I came up with VBAdvance... Frustration got the
better of me and my thinking I guess... ;-<

>> I'm not all that familure using the CopyMemory API (RtlMoveMemory) and have
>> gotten confused as to just what in the hex is happening here...
[quoted text clipped - 35 lines]
>HTH,
>Pete

Thanks Pete for your vary understandable explanation...
After reading it a couple of times and looking at the API docs again I can see
where I was getting confused and missed some clues as to what was going on
here... (also getting away from it for a bit and coming back to it helps me)
CopyMemory ByVal VarPtrArray(bDibDst()), VarPtr(tSADst), 4
The above should have told me up front it does the following:
Copy the 4 byte pointer of tSADst (m_cDibDst the original) to the temporary
bDibDst(). IOW, map bDibDst() over the memory locations for tSADst...
I'm not sure who wrote this class but the reason(s) I'm rewritting it is because
it is only partially done correctly, IMOHO...
Doing Byte calculations *Rules of Engagement* , so to speak, have been
implemented only partially and *Overflows* are here, there and everywhere due to
the mixed mode calculations...

Thanks again Pete... I appreciate it greatly...

(the older one gets the blacker the gray matter becomes... LOL)

Have a good day...

Don
 
Sign In
Join
My Latest Posts
My Monitored Threads
My Blog
My Photo Gallery
My Profile
My Homepage

Start New Thread
Enable EMail Alerts
Rate this Thread



©2009 Advenet LLC   Privacy Policy - Terms of Use
This website includes both content owned or controlled by Advenet as well as content owned or controlled by third parties.