Negative Array.Length при использовании Visual Studio 2019 - PullRequest
0 голосов
/ 15 апреля 2020

В моем приложении я создаю массив с предопределенным размером, который затем фиксируется и заполняется неуправляемой библиотекой. Это прекрасно работает, если приложение собирается с использованием Visual Studio 2017, но если приложение создается с использованием Visual Studio 2019 , размер массива перестает иметь смысл. Как длина массива может быть отрицательной?

// edit

Длинная длина та же: .

Буфер является полностью нормальным байтовым массивом

_buffer = new byte[BufferSize];

Метод просто простая обертка вокруг официального zlib dll. Как ошибка в этом методе может сбить с толку. net о размере массива?

fixed (byte* inputPtr = input)
fixed (byte* bufPtr = _buffer)
{
    _zStreamHandle.ZStream.nextIn = (IntPtr)inputPtr;
    _zStreamHandle.ZStream.availIn = length;
    _zStreamHandle.ZStream.nextOut = (IntPtr)bufPtr;
    _zStreamHandle.ZStream.availOut = BufferSize;
    var dataLeft = false;

    while (_zStreamHandle.ZStream.availIn != 0 || dataLeft)
    {
        var state = _zStreamHandle.Deflate(_flushMode);

        if (state != ErrorCode.Ok)
            throw new VncException("ZStream error: " + state);

        var outCount = BufferSize - (int) _zStreamHandle.ZStream.availOut;
        dataLeft = _zStreamHandle.ZStream.availOut == 0;

        try
        {
            _baseStream.Write(_buffer, 0, outCount);
        }
        catch (Exception e)
        {
            var bufferLength = _buffer.Length;
            var bufferLongLength = _buffer.LongLength;
            Debugger.Break();
        }

        _zStreamHandle.ZStream.nextOut = (IntPtr)bufPtr;
        _zStreamHandle.ZStream.availOut = BufferSize;
    }
}

1 Ответ

4 голосов
/ 15 апреля 2020

Я полагаю, что неуправляемый код топает память непосредственно перед началом самого массива данных. Вы можете смоделировать это с помощью управляемого небезопасного кода. Точные результаты могут зависеть от CLR, но на моем компьютере этот код составляет. NET думаю, что длина массива равна -1:

using System;

class Test
{
    unsafe static void Main()
    {
        byte[] array = new byte[20];
        Console.WriteLine(array.Length);
        fixed (byte* b = array)
        {
            // On my machine, the length of the array starts
            // 8 bytes before the array data itself
            byte* lengthPtr = b - 8;

            // So let's stop on those four bytes...
            *lengthPtr++ = 255;
            *lengthPtr++ = 255;
            *lengthPtr++ = 255;
            *lengthPtr++ = 255;
        }

        // Prints -1
        Console.WriteLine(array.Length);
    }
}

Так что в основном вам нужно исправить неуправляемую библиотеку в твой случай. Может быть, где-то есть проблема 32-бит / 64-бит - я бы посоветовал вам проверить, что все ожидает ту же архитектуру.

...