-
Notifications
You must be signed in to change notification settings - Fork 2.6k
Add basic SafeArray marshalling tests #20866
Conversation
|
@dotnet-bot test this please. |
|
@dotnet-bot test OSX10.12 x64 Checked Innerloop Build and Test |
| // Start of SafeArray calls | ||
| //-------------------------------- | ||
|
|
||
| extern "C" DLL_EXPORT BOOL STDMETHODCALLTYPE SafeArray_In(SAFEARRAY* psa) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
These tests are a bit much. Instead, I would look at the COM tests for arrays and see the basic validation that is needed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd actually prefer to keep the validation of all of the different components of the safe array since they're not something we have tests for anywhere else and they add a lot of complexity on top of traditional arrays.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am fine with the validation - although in this case, you are testing windows not the CLR, but the validation is fine. My criticism is that it is in every case. That is definitely not needed and should be limited to a single case.
tests/src/Interop/ArrayMarshalling/SafeArray/SafeArrayNative.cpp
Outdated
Show resolved
Hide resolved
| int* pInt; | ||
| HRESULT hr; | ||
| StructWithSA* ps = (StructWithSA*)CoreClrAlloc(sizeof(StructWithSA)); | ||
| (*ps).i32 = 77; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where is this value being validated?
| printf("\t\tSafeArrayCreateVector call failed!\n"); | ||
| exit(1); | ||
| } | ||
| else |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This else isn't needed.
| } | ||
|
|
||
| //check element size | ||
| if(SafeArrayGetElemsize(psa) != 4) //size of each element should be 4 bytes |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why? This is a perfect example of why I dislike how these tests are written. The base invariant here is that the passed in SafeArray is of INT4, but that isn't defined anywhere in this code nor validated. Additionally this could be for a float for that matter. Basically I am fine with this kind of validation, but my question to you and something we should always consider when writing tests is the following list:
What are we validating?
Why are we validating it?
If this test fails what does it indicate?
If this test fails is it obvious what other scenarios are impacted?
Is this test validating undocumented or unsupported scenarios?
Can a new person look at this test and easily determine the test purpose and value?
| { | ||
| SAFEARRAY * psa; | ||
|
|
||
| const int rank = 2; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Again, what rank is wrong? This is setting the rank to 2? Is that wrong? A nice indication of this is defining the variable as const int InvalidRank = 2; that would make it clear 2 isn't the valid value.
AaronRobinsonMSFT
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's chat in person when I get back.
…#33413) dotnet/coreclr#20866 extends the jit to incorporate the type of readonly ref class typed static fields into jitted code when jitting happens after class initialization. For instance, the jit may optimize type tests or devirtualize calls. With the advent of type based jit optimizations we are also blocking reflection based updates to all readonly static fields after class initialization.
| return --refCount; | ||
| } | ||
|
|
||
| HRESULT QueryInterface(const IID& riid, void** ppvObject) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Boo. Technically this doesn't matter, but these kind of things tend to get copy/pasted. QueryInterface() always calls AddRef() on success. Just make the call prior to returning S_OK.
Same for the one below.
| #include <xplatform.h> | ||
| #include <oleauto.h> | ||
| #include <algorithm> | ||
| #include "platformdefines.h" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is platformdefines.h in this directory? I think this should be <...>? Please fix this where ever you see it.
| #include "platformdefines.h" | ||
| #include "Helpers.h" | ||
|
|
||
| extern "C" DLL_EXPORT BOOL STDMETHODCALLTYPE XorBoolArray(SAFEARRAY* d, BOOL* result) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We are getting to the point where this model of testing is more burden than benefit.
Instead of returning a BOOL, just return the HRESULT. Tests should almost always just throw an exception or return an error code. The BOOL concept is a relic that should be purged from the codebase. HRESULTs will be properly converted to an Exception and in most cases translated. This will also allow you to follow the standard pattern of RETURN_IF_FAILED().
| } | ||
|
|
||
| [DllImport(nameof(SafeArrayNative))] | ||
| public static extern bool XorBoolArray( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All of the associated out params can now just be natural return values.
…dotnet#33413) dotnet/coreclr#20866 extends the jit to incorporate the type of readonly ref class typed static fields into jitted code when jitting happens after class initialization. For instance, the jit may optimize type tests or devirtualize calls. With the advent of type based jit optimizations we are also blocking reflection based updates to all readonly static fields after class initialization.
Port over basic tests from .NET Framework for marshalling an array as a
SAFEARRAY*.