"vshost32.exe has stopped working" 或 "fatal execution engine error" 在 Visual Studio

"vshost32.exe has stopped working" OR "fatal execution engine error" in Visual Studio

我在 Visual Studio 中遇到了一些奇怪的错误,找不到头或尾。我正在用 C# 编写一些后端代码,它联系第三方 API 来检索数据。有问题的代码,单个 class,是更大解决方案的一部分,但一定是问题所在,因为在不使用此 class.

时不会发生遇到的错误

计算机设置:

遇到错误

昨天,应用程序在调试时开始表现异常。 第一个错误我记不太清楚了,但大致是“坏”或“损坏的内存”。

在不改变程序的情况下,我也可能遇到 FatalExecutionEngineError 异常,在尝试 运行 程序后会立即抛出(它没有到达第一个断点,它在第一个程序主入口中的行。奇怪!

编辑:看起来像这样:

Managed Debugging Assistant 'FatalExecutionEngineError' has detected a problem in 'PathRedacted\whatsfordinner\whatsfordinner\bin\Debug\whatsfordinner.vshost.exe'.

Additional information: The runtime has encountered a fatal error. The address of the error was at 0x613e4379, on thread 0x11ac. 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.

最后我重新启动了我的电脑,因为这一切都很奇怪。问题直到今天才解决。

现在我似乎根本无法 运行 该程序; 运行 启动程序后,vshost32.exe 就崩溃了。我没有收到任何错误消息或任何提示问题所在的信息。

故障排除步骤

  1. 重新启动我的电脑 - 没有变化,vshost32.exe 执行时崩溃
  2. 注释了使用问题 class 的两行 - 程序 运行 没问题。
  3. 尝试以“Release”而不是“Debug”启动程序。 - 程序似乎 运行 很好,虽然我无法测试到最后。 (class 还没有完全完成,我不想向有问题的 API 发送垃圾邮件)
  4. 尝试在另一台计算机上 运行ning 程序 运行ning Windows 7 和 Visual Studio 2012。- 程序似乎 运行 正常。

此时我很迷茫。我不知道问题出在哪里。不幸的是,源代码包含将近200行,但由于我不知道,所以我将其全部发布。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Collections.Specialized;
using System.Net;
using System.IO;
using System.Text.RegularExpressions;
using System.Security.Cryptography;

using Newtonsoft.Json.Linq;
using Newtonsoft.Json;

namespace whatsfordinner {

public class eTilbudRetriever {
    
    //Web method names
    readonly String Get = "GET";
    readonly String Post = "POST";
    readonly String Update = "UPDATE";
    readonly String Delete = "DELETE";

    //Parameter identifiers
    readonly String ParamApiKey = "api_key";
    readonly String ParamLatitude = "r_lat";
    readonly String ParamLongitude = "r_lng";
    readonly String ParamRadius = "r_radius";
    readonly String ParamLimit = "limit";
    readonly String ParamOffset = "offset";

    //Parameter values
    String Latitude = "57.051188"; //Aalborg coordinates
    String Longitude = "9.922371";
    String Radius = "800000"; //Radius in meters (800km)
    String Limit = "48"; // Results per query

    //Custom header identifiers
    readonly String HeaderXToken = "X-Token";
    readonly String HeaderXSignature = "X-Signature";

    //Custom header values
    readonly String ContentType = "application/json";

    //Web Addresses
    readonly String HostAddress = "https://api.etilbudsavis.dk/v2/";
    readonly String Sessions = "sessions";
    readonly String Stores = "stores";
    readonly String Offers = "offers";
    readonly String Dealers = "dealers";

    //Keys
    readonly String ApiKey = "<Redacted>";
    readonly String ApiSecret = "<Redacted>";
    String XToken; //Same as a Session Token in documentation
    String XSignature; //Same as a Session Signature in documentation

    public eTilbudRetriever() {

        //Create a body consisting of the API key
        List<KeyValuePair<String, String>> body = new List<KeyValuePair<String, String>>();
        body.Add(new KeyValuePair<String, String>(ParamApiKey, ApiKey));

        //Send request to create a new session
        String response = SendWebRequest(Post, Sessions, body);

        //Get the Session Token from the response
        dynamic json = JObject.Parse(response);
        XToken = json.token;

        //Save the Session Signature as well (SHA256 version of API Secret combined with Session Token)
        XSignature = ConvertToSha256(ApiSecret + XToken);
    }

    public void GetDealersList() {
        GetList(Dealers);
    }

    public void GetStoresList() {
        GetList(Stores);
    }

    public void GetOffersList() {
        GetList(Offers);
    }

    private void GetList(string target) {

        List<String> resultSet = new List<String>();
        String result;
        int offset = 0;

        //Add desired parameters as headers for the eTilbudsavisen API
        List<KeyValuePair<String, String>> query = new List<KeyValuePair<String, String>>();
        query.Add(new KeyValuePair<String, String>(ParamLatitude, Latitude));
        query.Add(new KeyValuePair<String, String>(ParamLongitude, Longitude));
        query.Add(new KeyValuePair<String, String>(ParamRadius, Radius));
        query.Add(new KeyValuePair<String, String>(ParamLimit, Limit));
        query.Add(new KeyValuePair<String, String>(ParamOffset, offset.ToString()));

        //Retrieve a result through the request
        result = SendWebRequest(Get, target, query);

        /*
         * If result is valid, add it to the set of valid results.
         * Keep sending requests and increase the offset to avoid duplicated results
         * Stop when returned results are no longer valid
         */
        while (!String.IsNullOrEmpty(result)) {
            resultSet.Add(result);
            offset += Int32.Parse(Limit);
            query[query.Count-1] = new KeyValuePair<String, String>(ParamOffset, offset.ToString());
            result = SendWebRequest(Get, target, query);
        }
    }

    private String SendWebRequest(String method, String extension, List<KeyValuePair<String, String>> arguments) {

        try {
            String finalAddress = HostAddress + extension;

            //Add query to Address (if applicable)
            if (method.Equals(Get)) {
                finalAddress += '?';
                finalAddress += arguments[0].Key + '=' + arguments[0].Value;
                for (int i = 1; i < arguments.Count; i++) {
                    finalAddress += '&' + arguments[i].Key + '=' + arguments[i].Value;
                }
            }

            //Create request and set mandatory header properties
            var request = (HttpWebRequest)WebRequest.Create(finalAddress);
            request.Method = method;
            request.ContentType = ContentType;
            request.Accept = ContentType;

            //If a Session Token and Signature are available (= After session create), add as headers
            if (!String.IsNullOrEmpty(XToken)) {
                request.Headers.Add(HeaderXToken, XToken);
                request.Headers.Add(HeaderXSignature, XSignature);
            }

            //Create JSON string containing the desired body arguments (if applicable)
            if (method.Equals(Post)) {

                //Write body to API
                using (var writer = new StreamWriter(request.GetRequestStream())) {
                    writer.Write(MakeJsonBody(arguments));
                }
            }

            //get response as a JSON object in string format
            var response = (HttpWebResponse)request.GetResponse();
            return new StreamReader(response.GetResponseStream()).ReadToEnd();

        } catch (UriFormatException e) {
            Console.WriteLine(e.ToString());
            return null;
        } catch (WebException e) {
            Console.WriteLine(e.ToString());
            return null;
        }
    }

    private String ConvertToSha256(String text) {

        byte[] bytes = Encoding.UTF8.GetBytes(text);
        SHA256Managed hashstring = new SHA256Managed();
        byte[] hash = hashstring.ComputeHash(bytes);
        string hashString = string.Empty;

        foreach (byte x in hash) {
            hashString += String.Format("{0:x2}", x);
        }

        return hashString;
    }

    private String MakeJsonBody(List<KeyValuePair<String, String>> arguments) {

        String json = "{";

        foreach (KeyValuePair<String, String> kv in arguments) {
            json += "\"" + kv.Key + "\": \"" + kv.Value + "\"";

            if (arguments.IndexOf(kv) != arguments.Count() - 1) {
                json += ", ";
            }
        }

        json += "}";
        return json;
    }
}

}

Main中,这是相对于class执行的。从解决方案中删除这些行时,程序 运行 正常。

eTilbudRetriever retriever = new eTilbudRetriever();
retriever.GetDealersList();

Windows 10, Preview Build 10041

这是您的程序崩溃的唯一可能原因。没有其他人,您的代码没有做任何危险的事情,并且 Newtonsoft.Json 已经被数百万个程序以各种可能的方式抨击。您使用的是 .NET Framework (v4.6) 和操作系统的测试版。代表所有 Microsoft 客户感谢帮助调试此新软件,您的问题不是我们必须解决的问题。希望 FEEE 崩溃非常严重且难以调试。

应该做的是向 Microsoft 提交崩溃进程的小型转储,以便他们修复潜在的错误。不管它是什么,你的问题都没有任何线索。 可能是对x64抖动(项目代号RyuJit)的彻底重写。它现在没有错误的可能性很小,这样的错误肯定会使您的程序像这样崩溃。不过这只是一个大胆的猜测。

Microsoft 免费提供这些预览版。他们的基本意图是在产品发布之前解决错误。应该发生在夏天前后的某个地方。只有真正的方法,他们才能 一些 相信他们的支持 phone 线路在他们运送产品后不会超载。 Beta 更新来得又快又猛,.NET 4.6 已经有 6 个 CTP 版本。相当史无前例,通常不超过 3 个。至少其中一部分是 VS2015 的测试版,该版本中有很多很多新东西。你不用的,那也没用。

您在其中的角色是一名无偿 Beta 测试员。这往往与您的其他角色不相容,即以编写和调试代码为生的程序员。您的代码,而不是其他人的。如果您不能像这样陷入困境,那么唯一明智的做法就是取消订阅该测试版程序。将您的计算机恢复到框架和操作系统的已知良好版本。现在是 .NET 4.5.2 和 Windows 8.1