AccessViolationException и MSSQL 2005
От: sivachenko  
Дата: 02.02.07 13:55
Оценка:
Привет, не могли бы вы помочь разобраться с проблемой, все пересмотрел, не как не могу понять причину.

Пишу хранимую процедуру на C#, она должна вызывать неуправляемый код из .dll.
При работе процедуры вылетает исключение AccessViolationException.
Похоже что вылетает при передаче параметров.

Такой же точно код, как и в хранимой процедуре, нормально работает в отдельном приложении.
Никаких исключений не вылетает (трассировал в VC со всеми включенными исключениями).
Исходные данные одни и те же, библиотека .dll отлажена абсолютно.

Нужно передать массивы в библиотеку и в них же получить результат.
Библиотека указатели не меняет, только изменят данные в памяти.

ref или out вроде как не нужны т.к. идея такая: выделяем в .NET область памяти, передаем укзатель на неё,
под данному адресу меняем данные, возвращаемся назад в .NET и всё должно быть ОК.

Код хранимой процедуры:
[DllImport("TSA.dll", CallingConvention = CallingConvention.Cdecl)]
    public static extern void iInitNOS(
        float[] Other,
        float[] Realiz,
        float[] Rest,
        float[] Supply,
        ushort[] NosStats,
        ushort ToDay,
        float NosConfidence,
        byte[] Nos,
        byte[] Presence);

    
    [Microsoft.SqlServer.Server.SqlProcedure]
    public static void CalcNos(int id_dep, int id_item)
    {
        _сurItemMove.Realiz = new float[length];
        _сurItemMove.Supply = new float[length];
        _сurItemMove.Rest = new float[length];
        _сurItemMove.Other = new float[length];

        <В описанные выше массивы читаются данные из БД длины length>

        //массивы для результатов
        _сurItemMove.Nos = new byte[length];
        _сurItemMove.Presence = new byte[length];

        // параметры
        ushort[] _NosStats = new ushort[3];
        _NosStats[0] = 0;
        _NosStats[1] = 0;
        _NosStats[2] = 0;
        
        float _NosConfidence = (float)0.01;

        ushort _ToDay = (ushort)(length - 1);
        
        iInitNOS(_сurItemMove.Other,
                 _сurItemMove.Realiz,
                 _сurItemMove.Rest,
                 _сurItemMove.Supply,
                 _NosStats,
                 _ToDay,
                 _NosConfidence,
                 _сurItemMove.Nos,
                 _сurItemMove.Presence);
    }



Заголовок в библиотеке на с++:
__declspec(dllexport) void __cdecl iInitNOS(
        float *Other, float *Realiz, float *Rest, float *Supply,
        unsigned short *NosStats,
        unsigned short ToDay, float NosConfidence, 
        char *Nos, char *Presence) 
{
       //меням данные в памяти по адресам Nos, Presence
}


пробовал ещё так:


        [DllImport("TSA.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern unsafe void iInitNOS(
            float* Other,
            float* Realiz,
            float* Rest,
            float* Supply,
            ushort* NosStats,
            ushort ToDay,
            float NosConfidence,
            byte* Nos,
            byte* Presence);

                unsafe
                {
                    fixed (
                        float* Other = _сurItemMove.Other,
                        Realiz = _сurItemMove.Realiz,
                        Rest = _сurItemMove.Rest,
                        Supply = _сurItemMove.Supply)
                    fixed (ushort* pNosStats = _NosStats)
                    fixed (byte* Nos = _сurItemMove.Nos, Presence = _сurItemMove.Presence)
                    {
                        

                        iInitNOS(Other,
                                 Realiz,
                                 Rest,
                                 Supply,
                                 pNosStats,
                                 (ushort)_ToDay,
                                 _NosConfidence,
                                 Nos,
                                 Presence); 
                    }
Re: AccessViolationException и MSSQL 2005
От: shelkovnikov Россия  
Дата: 05.02.07 06:59
Оценка:
а как подключается сборка к sql?

в create assembly есть параметр PERMISSION_SET, может в этом дело?
[msdn]
PERMISSION_SET { SAFE | EXTERNAL_ACCESS | UNSAFE }
Specifies a set of code access permissions that are granted to the assembly when it is accessed by SQL Server. If not specified, SAFE is applied as the default.

We recommend using SAFE. SAFE is the most restrictive permission set. Code executed by an assembly with SAFE permissions cannot access external system resources such as files, the network, environment variables, or the registry.

EXTERNAL_ACCESS enables assemblies to access certain external system resources such as files, networks, environmental variables, and the registry.

UNSAFE enables assemblies unrestricted access to resources, both within and outside an instance of SQL Server. Code running from within an UNSAFE assembly can call unmanaged code.

Security Note:
SAFE is the recommended permission setting for assemblies that perform computation and data management tasks without accessing resources outside an instance of SQL Server.

We recommend using EXTERNAL_ACCESS for assemblies that access resources outside of an instance of SQL Server. EXTERNAL_ACCESS assemblies include the reliability and scalability protections of SAFE assemblies, but from a security perspective are similar to UNSAFE assemblies. This is because code in EXTERNAL_ACCESS assemblies runs by default under the SQL Server service account and accesses external resources under that account, unless the code explicitly impersonates the caller. Therefore, permission to create EXTERNAL_ACCESS assemblies should be granted only to logins that are trusted to run code under the SQL Server service account. For more information about impersonation, see CLR Integration Security.

Specifying UNSAFE enables the code in the assembly complete freedom to perform operations in the SQL Server process space that can potentially compromise the robustness of SQL Server. UNSAFE assemblies can also potentially subvert the security system of either SQL Server or the common language runtime. UNSAFE permissions should be granted only to highly trusted assemblies. Only members of the sysadmin fixed server role can create and alter UNSAFE assemblies.



For more information about assembly permission sets, see Designing Assemblies.
[/msdn]
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.