AccessViolationException when using Arg.IsAny in property setter arrangement (WPF)

1 Answer 22 Views
API General Discussions
James
Top achievements
Rank 1
James asked on 16 May 2025, 07:03 PM | edited on 16 May 2025, 07:07 PM

I am using WPF JustMock to create unit tests and am trying to create an argument matcher for a property setter in a mock arrangement as below.

            Mock.ArrangeSet(() => mockSelectionRuleRow.SelectedRuleAttribute = Arg.IsAny<RuleAttribute>())
                .DoNothing();

RuleAttribute is a simple data class. Originally I wanted to have a matcher like "Arg.Matches<RuleAttribute>(x => x.Name == name)" but I was getting the AccessViolationException so I tried checking just any RuleAttribute and I am still getting the exception.

Note that I have other property setter arangements for mockSelectionRuleRow that are working just fine however they are checking specific values I have stored in local variables. In this case I cannot guarantee it is the same object, as internally the logic being tested may copy it.

The JustMock documentation shows using Arg.IsAny in an ArrangeSet, though it only shows using it with a primitive type (int). Is this sort of usage not supported?

This is the runtime exception (inner) I get when the above ArrangeSet executes. {"Attempted to read or write protected memory. This is often an indication that other memory is corrupt."}

Can anyone provide any guidance?

1 Answer, 1 is accepted

Sort by
0
Ivo
Telerik team
answered on 20 May 2025, 08:16 AM

Hello James,

Thank you for highlighting this issue. We kindly request that you create and share a minimal working sample that reproduces the problem. This will allow us to investigate the issue thoroughly and find a solution more quickly.

Regards,
Ivo
Progress Telerik

Love the Telerik and Kendo UI products and believe more people should try them? Invite a fellow developer to become a Progress customer and each of you can get a $50 Amazon gift voucher.

James
Top achievements
Rank 1
commented on 20 May 2025, 06:24 PM | edited

I have been able to reproduce with an isolated example. It looks like this issue is somehow caused by assignment to an ICommand variable in the constructor (or even a mocked method) of the ViewModel class ExampleViewModelMock. If you move the assignment to ExampleCommand to the declaration of the property as an expression bodied property or inside a getter the AccessViolationException no longer occurs.

This is the same as my actual ViewModel class SelectionRuleRow. However, somehow I am not able to prevent the exception in my own class yet.

The below code results in the exception. If you comment/uncomment the indicated code the test will run properly.


        #region Telerik Exception Example

        public class ExampleDataClass
        {
            public string Name { get; set; }
            public string Value { get; set; }
        }

        public class ExampleViewModel : ViewModelBase
        {
            public ExampleViewModelMock ExampleViewModelMock { get; private set; }

            public ObservableCollection<ExampleDataClass> ExampleData { get; set; }
            public ExampleViewModel()
            {
                ExampleDataClass exampleDataClass = new ExampleDataClass() { Name = "Example1", Value = "ExampleValue" };
                ExampleData = new ObservableCollection<ExampleDataClass>(new List<ExampleDataClass>() { exampleDataClass });
            }

            public void CreateExampleViewModelMock()
            {
                ExampleViewModelMock = new ExampleViewModelMock();
                ExampleViewModelMock.DataClass = ExampleData[0];
            }
        }

        public class ExampleViewModelMock : ViewModelBase
        {

            public ExampleViewModelMock()
            {
                ExampleCommand = new DelegateCommand(ExampleCommandMethod); // => Comment this to make it work properly.
            }

            ICommand ExampleCommand; // => Uncomment the below and remove the semicolon to make it work properly.
            //{
            //    get
            //    {
            //        return new DelegateCommand(ExampleCommandMethod);
            //    }
            //}

            public void ExampleMethod()
            {
                ExampleCommand.Execute(null);
            }

            private ExampleDataClass _dataClass;
            public ExampleDataClass DataClass
            {
                get => _dataClass;
                set
                {
                    _dataClass = value;
                    OnPropertyChanged(nameof(DataClass));
                }
            }

            private void ExampleCommandMethod(object obj)
            {

            }
        }

        [TestMethod]
        public void AccessViolationExample()
        {
            // Arrange

            ExampleDataClass exampleDataClass = new ExampleDataClass() { Name = "Example1", Value = "ExampleValue" };

            ExampleViewModelMock exampleViewModelMock = Mock.Create<ExampleViewModelMock>(Constructor.Mocked, Behavior.Strict);
            Mock.Arrange(() => new ExampleViewModelMock())
                .Returns(exampleViewModelMock);
            Mock.Arrange(() => exampleViewModelMock.ExampleMethod())
                .DoNothing();
            Mock.Arrange(() => exampleViewModelMock.DataClass)
                .Returns(exampleDataClass);
            Mock.ArrangeSet(() => exampleViewModelMock.DataClass = Arg.Matches<ExampleDataClass>(x => x.Name == "Example1"))
                .DoNothing();

            // Act

            ExampleViewModel exampleViewModel = new ExampleViewModel();
            exampleViewModel.CreateExampleViewModelMock();

            // Assert

            Assert.AreEqual(expected: exampleViewModelMock, actual: exampleViewModel.ExampleViewModelMock);
            Assert.IsTrue(exampleViewModel.ExampleData.Count > 0);
            Assert.AreEqual(expected: exampleDataClass.Name, actual: exampleViewModel.ExampleData[0].Name);
            Assert.AreEqual(expected: exampleDataClass, actual: exampleViewModel.ExampleViewModelMock.DataClass);
        }

        #endregion




James
Top achievements
Rank 1
commented on 20 May 2025, 06:58 PM

Interestingly, even after removing the commands entirely from my view model class I am still getting the issue... there must be something else which is also causing this exception. In the test example I gave above I can definitely reproduce it with just manipulation of the command property.
Ivo
Telerik team
commented on 23 May 2025, 09:27 AM

Hello James, thank you for the code you provided. I used it with a few adjustments, but still cannot observe any issues. Please find the attached project and modify it so that the problem occurs.
James
Top achievements
Rank 1
commented on 27 May 2025, 01:25 PM

Hi, I downloaded your solution and uncomented "ExampleCommand = new DelegateCommand(ExampleCommandMethod);" and commented the getter for ExampleCommand and still get the AccessViolationException as described above...

Ivo
Telerik team
commented on 28 May 2025, 06:41 PM

Hello James,

Thank you for the update. It seems that the problem can be consistently reproduced on your end, while I am not experiencing the same issue on mine. A deep analysis is required, and I would appreciate it if you could provide a memory dump.

The property set arrangement has historically been problematic because it uses a completely different approach compared to other arrangements based on expressions. Specifically, the assignment operator cannot be used directly in expression trees. However, there is a way to achieve the property set arrangement using a special syntax sugar that composes the desired expression (see here).

The bad news is that this solution is not mature enough to handle cases involving matchers. To address this, I have fixed the code and added it as a workaround to the project. I hope this temporary solution will work for you until we can find a better fix for the problem.
James
Top achievements
Rank 1
commented on 02 Jun 2025, 04:35 PM

Hi, I haven't had a chance to test this yet. I will get back to you when I can. Thank you for looking for alternatives.

For the memory dump, I'm not entirely sure what you are looking for.
Ivo
Telerik team
commented on 03 Jun 2025, 07:21 AM | edited

Hello James,

Here is how you can capture a memory dump when an exception occurs:

Option 1: Use Windows Error Reporting (WER)

1. WER can automatically generate a dump when your application crashes. Enable WER dumps via the registry:

  • Open regedit and navigate to:
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\Windows ErrorReporting\LocalDumps
  • If the key doesn't exist, create it.
  • Add the following values:
    • DumpFolder (REG_EXPAND_SZ): e.g., C:\Dumps
    • DumpCount (DWORD): e.g., 10
    • DumpType (DWORD): 2 for full dump, 1 for mini dump

2. Reproduce the crash and a dump will be created in the specified folder.

Option 2: Use ProcDump

ProcDump is a tool that can capture dumps on exceptions.

  • Download and extract ProcDump.
  • Run it with the following command:
procdump -e 1 -f "" -ma testhost.exe

-e 1: triggers on first chance exceptions
-f "": captures all exceptions
-ma: full memory dump

You can also target AccessViolationException specifically:

procdump -e 1 -f AccessViolationException -ma testhost.exe

Option 3: Use Visual Studio

If you can reproduce the issue in a dev environment:

  • Run the app in Debug mode.
  • When the exception occurs, Visual Studio will break.
  • Go to Debug > Save Dump As... and choose Minidump with Heap or Full Dump.

Option 4: Use Task Manager

  • When the app is running (or frozen), open Task Manager.
  • Right-click the process testhost.exe > Create dump file.
  • The dump will be saved in your %TEMP% folder.
Tags
API General Discussions
Asked by
James
Top achievements
Rank 1
Answers by
Ivo
Telerik team
Share this question
or