- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我即将为用 VBScript 编写的遗留系统启动一个正在工作的迁移项目。它有一个有趣的结构,其中大部分是通过将各种组件编写为“WSC”文件来隔离的,这实际上是一种以类似 COM 的方式公开 VBScript 代码的方式。从“核心”到这些组件的边界接口(interface)相当紧密且众所周知,所以我希望我能够编写新的核心并重用 WSC,推迟重写。
可以通过添加对“Microsoft.VisualBasic”的引用并调用来加载 WSC
var component = (dynamic)Microsoft.VisualBasic.Interaction.GetObject("script:" + controlFilename, null);
using System;
using System.IO;
using System.Reflection;
using System.Runtime.InteropServices;
using Microsoft.VisualBasic;
namespace WSCErrorExample
{
public partial class Default : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
var currentFolder = GetCurrentDirectory();
var logFile = new FileInfo(Path.Combine(currentFolder, "Log.txt"));
Action<string> logger = message =>
{
// The try..catch is to avoid IO exceptions when reproducing by requesting the page many times
try { File.AppendAllText(logFile.FullName, message + Environment.NewLine); }
catch { }
};
var controlFilename = Path.Combine(currentFolder, "TestComponent.wsc");
var control = (dynamic)Interaction.GetObject("script:" + controlFilename, null);
logger("About to call Go");
control.Go(new DataProvider(logger));
logger("Completed");
}
private static string GetCurrentDirectory()
{
// This is a way to get the working path that works within ASP.Net web projects as well as Console apps
var path = Path.GetDirectoryName(Assembly.GetExecutingAssembly().GetName().CodeBase);
if (path.StartsWith(@"file:\", StringComparison.InvariantCultureIgnoreCase))
path = path.Substring(6);
return path;
}
[ComVisible(true)]
public class DataProvider
{
private readonly Action<string> _logger;
public DataProvider(Action<string> logger)
{
_logger = logger;
}
public DataContainer GetDataContainer()
{
return new DataContainer();
}
public void Log(string content)
{
_logger(content);
}
}
[ComVisible(true)]
public class DataContainer
{
public object this[string fieldName]
{
get { return "Item:" + fieldName; }
}
}
}
}
<?xml version="1.0" ?>
<?component error="false" debug="false" ?>
<package>
<component id="TestComponent">
<registration progid="TestComponent" description="TestComponent" version="1" />
<public>
<method name="Go" />
</public>
<script language="VBScript">
<![CDATA[
Function Go(objDataProvider)
Dim objDataContainer: Set objDataContainer = objDataProvider.GetDataContainer()
If IsEmpty(objDataContainer) Then
mDataProvider.Log "No data provided"
End If
End Function
]]>
</script>
</component>
</package>
Managed Debugging Assistant 'FatalExecutionEngineError' has detected a problem in 'C:\Program Files (x86)\IIS Express\iisexpress.exe'.
Additional information: The runtime has encountered a fatal error. The address of the error was at 0x733c3512, on thread 0x1e10. The error code is 0xc0000005. This error may be a bug in the CLR or in the unsafe or non-verifiable portions of user code. Common sources of this bug include user marshaling errors for COM-> interop or PInvoke, which may corrupt the stack.
This thread is stopped with only external code frames on the call stack. External code frames are typically from framework code but can also include other optimized modules which are loaded in the target process.
Call stack with external code
mscorlib.dll!System.Variant.Variant(object obj) mscorlib.dll!System.OleAutBinder.ChangeType(object value, System.Type type, System.Globalization.CultureInfo cultureInfo) mscorlib.dll!System.RuntimeType.TryChangeType(object value, System.Reflection.Binder binder, System.Globalization.CultureInfo culture, bool needsSpecialCast) mscorlib.dll!System.RuntimeType.CheckValue(object value, System.Reflection.Binder binder, System.Globalization.CultureInfo culture, System.Reflection.BindingFlags invokeAttr) mscorlib.dll!System.Reflection.MethodBase.CheckArguments(object[] parameters, System.Reflection.Binder binder, System.Reflection.BindingFlags invokeAttr, System.Globalization.CultureInfo culture, System.Signature sig) [Native to Managed Transition]
最佳答案
我的猜测是,您看到的错误是由 WSC 脚本组件本质上是 COM STA 对象这一事实引起的。它们由底层的 VBScript 事件脚本引擎实现,它本身是一个 STA COM 对象。因此,它们需要创建和访问 STA 线程,并且此类线程应在任何特定 WSC 对象的生命周期内保持不变(该对象需要线程关联)。
ASP.NET 线程不是 STA。他们是 ThreadPool
线程,并且当您开始在它们上使用 COM 对象时,它们会隐式地成为 COM MTA 线程(有关 STA 和 MTA 之间的差异,请参阅 INFO: Descriptions and Workings of OLE Threading Models )。 COM 然后为您的 WSC 对象创建一个单独的隐式 STA 单元,并从您的 ASP.NET 请求线程对那里进行编码调用。整个事情在 ASP.NET 环境中可能会也可能不会顺利。
理想情况下,您应该摆脱 WSC 脚本组件并用 .NET 程序集替换它们。如果这在短期内不可行,我建议您运行自己的明确控制的 STA 线程来托管 WSC 组件。以下可能有帮助:
// create a global instance of ThreadAffinityTaskScheduler - per web app
public static class GlobalState
{
public static ThreadAffinityTaskScheduler TaScheduler { get; private set; }
public static GlobalState()
{
GlobalState.TaScheduler = new ThreadAffinityTaskScheduler(
numberOfThreads: 10,
staThreads: true,
waitHelper: WaitHelpers.WaitWithMessageLoop);
}
}
// ... inside Page_Load
GlobalState.TaScheduler.Run(() =>
{
var control = (dynamic)Interaction.GetObject("script:" + controlFilename, null);
logger("About to call Go");
control.Go(new DataProvider(logger));
logger("Completed");
}, CancellationToken.None).Wait();
PageAsyncTask
稍微提高 Web 应用程序的可扩展性。和
async/await
而不是阻塞
Wait()
.
关于c# - C#/WSC (COM) 互操作中的 FatalExecutionEngineError,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24759189/
WSC 的安全性如何? 它是否始终假定它在受信任的环境中运行? 该技术会持续存在还是 MS 有可能很快将其淘汰? 最佳答案 WSC 在调用它们的代码的帐户下运行。我在 IIS 中大量使用它们,在我的案
我即将为用 VBScript 编写的遗留系统启动一个正在工作的迁移项目。它有一个有趣的结构,其中大部分是通过将各种组件编写为“WSC”文件来隔离的,这实际上是一种以类似 COM 的方式公开 VBScr
我无法让此示例 WSC Salesforce 代码正常工作。我缺少什么?我正在尝试为特定帐户创建新事件。我不介意先查询帐户。这看起来很简单,但行不通。 QueryResult queryRes
我正在尝试将一个扩展从 Firefox 移植到 IE。所有扩展的代码都在 JS 中(没有 C++ 组件),所以我想我会重用代码并且只麻烦自己处理它的 mozilla 特定部分(这无疑也是一种折磨,但我
我想在当前可用的服务中使用这个 npm 包。当我运行“npm run start”时,它失败了并且我得到了错误: TypeError: wsc.require is not a function at
我在标签(NFC 切换 wifi)记录类型上写了一条“application/vnd.wfa.wsc”记录。现在我想用扫描标签的给定 Activity 启动我的应用程序。 我做了以下事情: 我通过写标
我正在尝试在 Swift 中创建一个 application/vnd.wfa.wsc 负载。我在这里找到了这篇适用于 Android 的帖子: Creating an NDEF WiFi record
从 Android 5.0.0 开始,您可以长按 WiFi 连接并将该连接写入标签(“写入 NFC 标签”)。您可以在此处找到该操作的来源:WriteWifiConfigToNfcDialog.jav
单元测试项目 Up.UnitTests 在构建期间失败,并出现此构建错误 错误 CS0430:未在/reference 选项中指定外部别名“snh”错误 CS0234:命名空间“snh”中不存在类型或
我是一名优秀的程序员,十分优秀!