Write variable from background worker
Dear Forum users!<br><br>I am looking for help with the following problem. I have an application in which I have a background worker in the C# VSTA environment. In this background worker, I repeatedly report progress, which calls the ProgressChanged function of the background worker. In this ProgressChanged function I modify zenon internal variables and write CEL lines with the <br><pre class="brush: csharp">private static zenOn.IProject myZenonProject;<br><br><br>
myZenonProject.Variables().Item("Variable_name").s et_Value(); //and<br><br><br>
myZenonProject.Cel().WriteCelStringEx();</pre><br>functions respectively. <br>The problem is, that sometimes these function calls fails and not even an exception is thrown, but the whole Zenon application crashes and stops. The exception that is thrown is either<br><strong>"Object reference not set to an instance of an object"</strong>,<br><strong>"Collection was modified, enumeration operation may not execute"</strong> or<br><strong>"Item with same key has already been added".</strong><br>In the Zenon error dump, the exception is "<strong>An exception came from the CLR</strong>", exception code is <strong>0xE0434F4D</strong>.<br><br>I suspected that this error may be a cause of the background worker and running zenon functions in it, so I created a test project, in which I only added a background worker and a zenon variable assignment function call, thus eliminating every other factor. Interestingly the error still occurs, so it is not related to the rest of the application.<br><br>As far as I know, the background worker's ProgressChanged function executes on the main thread. So, I can do whatever, in the backgroundworker, on a different thread, but when I call the ProgressChanged function (through ReportProgress()) it always runs on the main thread, so it shouldn't have thread accessing problems.<br>My question is: is this a valid assumption? Is it truly safe to call zenon function in the ProgressChanged function? How could I narrow down the problem, and try to avoid calling functions that cause a crash? What should I check, before running the above mentioned zenon functions, to make sure, that it wont cause problems? If this is not a good practice or valid approach, then what is a good way to handle such tasks? Background worker was the only option I found to handle multiple threads. <br><br>My environment: Zenon 7.6 SP0 Build56718 Energy Edition<br>VSTA 2008 v9.0.30729, .NET 3.5 SP1<br>Windows 10 64bit<br><br>Thanks in advance, Peter
Re: Write variable from background worker
Hello,
Have you tried to use AddIn Framework?
I am aware of an error similar to this: The analysis showed that it originates in VSTA - not zenon.
What could mitigate the problem is to put the COM access behind a semaphore. To ensure that only one thread accesses the COM at any time.
What you should do is use try catch blocks to catch any exceptions (and log them).
And use Null-Conditional operators for chaining:
<code class="csharp plain" style="white-space: pre; margin: 0px !important; padding: 0px !important; font-family: Consolas, " bitstream="" vera="" sans="" mono",="" "courier="" new",="" courier,="" monospace="" !important;="" line-height:="" 1.1em="" border-radius:="" 0px="" background:="" none="" border:="" inset:="" auto="" float:="" height:="" outline:="" overflow:="" visible="" position:="" static="" vertical-align:="" baseline="" width:="" box-sizing:="" content-box="" min-height:="" color:="" black="" !important;"="">myZenonProject?.Variables().Item(</code><code class="csharp string" style="white-space: pre; margin: 0px !important; padding: 0px !important; font-family: Consolas, " bitstream="" vera="" sans="" mono",="" "courier="" new",="" courier,="" monospace="" !important;="" line-height:="" 1.1em="" border-radius:="" 0px="" background:="" none="" border:="" inset:="" auto="" float:="" height:="" outline:="" overflow:="" visible="" position:="" static="" vertical-align:="" baseline="" width:="" box-sizing:="" content-box="" min-height:="" color:="" blue="" !important;"="">"Variable_name"</code><code class="csharp plain" style="white-space: pre; margin: 0px !important; padding: 0px !important; font-family: Consolas, " bitstream="" vera="" sans="" mono",="" "courier="" new",="" courier,="" monospace="" !important;="" line-height:="" 1.1em="" border-radius:="" 0px="" background:="" none="" border:="" inset:="" auto="" float:="" height:="" outline:="" overflow:="" visible="" position:="" static="" vertical-align:="" baseline="" width:="" box-sizing:="" content-box="" min-height:="" color:="" black="" !important;"="">)?.set_Value()</code><code class="csharp plain" style="white-space: pre; margin: 0px !important; padding: 0px !important; font-family: Consolas, " bitstream="" vera="" sans="" mono",="" "courier="" new",="" courier,="" monospace="" !important;="" line-height:="" 1.1em="" border-radius:="" 0px="" background:="" none="" border:="" inset:="" auto="" float:="" height:="" outline:="" overflow:="" visible="" position:="" static="" vertical-align:="" baseline="" width:="" box-sizing:="" content-box="" min-height:="" color:="" black="" !important;"="">
</code>
Re: Write variable from background worker
Thank you for your reply! <br><br>No, I haven't tried AddIn Framework yet. Do you have any information/documentation about that?<br><br>I have placed the zenon function calls inside a lock statement, and it looks like it has solved the issue, since I can no longer reproduce the error.<br><br>I will implement the Null-Conditional operator as well for additional safety.<br><br>Thanks, for the suggestions!