powered by simpleCommunicator - 2.0.59     © 2025 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / C++ [игнор отключен] [закрыт для гостей] / P/invoke помогите
11 сообщений из 11, страница 1 из 1
P/invoke помогите
    #39439754
vadipok
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Добрый день!
Коллеги, на выходе получаю 1-3 строки, хотя error равен 66.
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
struct PLAST_PAR_ARRAY
{
	int id; 
	long plast; 
	long skvag; 
	int year; 
	int month; 
	int day; 
	short oil;
	short water;
	short pzab;
};

// Многомерные характеристики
extern "C" __declspec(dllexport) void  WINAPI getPLAST_PAR_ARRAY(PLAST_PAR_ARRAY ** p, int * plast, int * skvag, char * modelPath, int * errorCode)
{
	if (*p) {
		::CoTaskMemFree(*p);
		  *p = nullptr;
	}

        ............................
        ............................

	//--------------------------
	// Вывод данных 
	//--------------------------
	// выделение памяти
	int sz = ig;
	PLAST_PAR_ARRAY *pt = (PLAST_PAR_ARRAY*)CoTaskMemAlloc(sz * sizeof PLAST_PAR_ARRAY);
	memset(pt, 0, sz * sizeof PLAST_PAR_ARRAY);

	int id = 0;
	for (i = 0; i<ig; i++)
	{ // цикл по годам 
		pt[i].id = id;
		pt[i].pzab = 100;
		pt[i].plast = ip - 1;
		pt[i].skvag = -1;
		pt[i].year = god + i;
		pt[i].month = 1;
		pt[i].day = 1;
		pt[i].oil = C09O(i, ip - 1, 0);
		pt[i].water = C09O(i, ip - 1, 1) - pt[i].oil;
		id++;
		error++;
	}

	*p = pt;

	// освобождение памяти 
	free(c09o);

	*errorCode = error;
}



Ошибку найти не могу, помогите плиз.
Что не так?
...
Рейтинг: 0 / 0
P/invoke помогите
    #39439762
vadipok
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
На стороне C#
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
    public class PlastParArraySearch
    {
        [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
        struct PLAST_PAR_ARRAY
        {
            public int id; // id
            public int plast; // 
            public int skvag; // 
            public int year; // Дата год
            public int month; // Дата месяц
            public int day; // Дата день
            public float oil; // 
            public float water; // 
            public float pzab; // 
        }

        [DllImport(@"Z:\*****.dll", CallingConvention = CallingConvention.StdCall)]
        private static extern int getPLAST_PAR_ARRAY([MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 1)] ref PLAST_PAR_ARRAY[] p,
                                   int plast,
                                   int skvag,
                                   [MarshalAs(UnmanagedType.LPStr)] string modelPath,
                                   ref int errorCode);

        public List<PlastParArray> getData(string modelPath, int plast, int skvag = -1)
        {
            // Извлечение данных
            PLAST_PAR_ARRAY[] LTplast_par_array = new PLAST_PAR_ARRAY[5];
            int errorCode = 0;
            getPLAST_PAR_ARRAY(ref LTplast_par_array, plast, skvag, modelPath, ref errorCode);
            
            // Присвоение данных 
            List<PlastParArray> plastParArray = new List<PlastParArray>();
            foreach (PLAST_PAR_ARRAY p in LTplast_par_array)
            {
                plastParArray.Add(new PlastParArray
                {
                    Id = p.id,
                    Plast = p.plast,
                    Skvag = p.skvag,
                    Oil = p.oil,
                    Water = p.water,
                    Pzab = p.pzab/*,
                    Date = new DateTime(p.year, p.month, p.day)*/
                });
            }

            return plastParArray;
        }
    }
...
Рейтинг: 0 / 0
P/invoke помогите
    #39439774
egorych
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
vadipok
Код: plaintext
1.
2.
3.
4.
5.
6.
	// выделение памяти
	int sz = ig;
	PLAST_PAR_ARRAY *pt = (PLAST_PAR_ARRAY*)CoTaskMemAlloc(sz * sizeof PLAST_PAR_ARRAY);
...
	// освобождение памяти 
	free(c09o);

это чё?
...
Рейтинг: 0 / 0
P/invoke помогите
    #39439828
vadipok
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
egorychvadipok
Код: plaintext
1.
2.
3.
4.
5.
6.
	// выделение памяти
	int sz = ig;
	PLAST_PAR_ARRAY *pt = (PLAST_PAR_ARRAY*)CoTaskMemAlloc(sz * sizeof PLAST_PAR_ARRAY);
...
	// освобождение памяти 
	free(c09o);

это чё?

Если честно, то я не смогу ответить на ваш вопрос грамотно.
Подозреваю, что первое - это выделение памяти размером sz, там в начале есть код, который извлекает sz, и он работает правильно, я проверял.
Точно такой же работает без проблем, с другим struct.

На Второе замечание можно забить, т.к. я пытался до этого убрать, но он так же не работал.
...
Рейтинг: 0 / 0
P/invoke помогите
    #39439935
vadipok
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Вот такой код отработал без проблем в командную строку.

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
	//--------------------------
	// Вывод данных 
	//--------------------------
	// выделение памяти
	int sz = ig;
	PLAST_PAR_ARRAY *pt = (PLAST_PAR_ARRAY*)CoTaskMemAlloc(sz * sizeof PLAST_PAR_ARRAY);
	memset(pt, 0, sz * sizeof PLAST_PAR_ARRAY);

	int id = 0;
	for (i = 0; i<ig; i++)
	{ // цикл по годам 
		pt[i].id = id;
		pt[i].plast = ip - 1;
		pt[i].skvag = -1;
		pt[i].year = god + i;
		pt[i].month = 1;
		pt[i].day = 1;
		pt[i].oil = C09O(i, ip - 1, 0);
		pt[i].water = C09O(i, ip - 1, 1) - C09O(i, ip - 1, 0);
		std::cout << pt[i].oil << "	" << pt[i].water << std::endl;
		id++;
	}

	system("pause");
	 // освобождение памяти 
	free(m00c);
	free(m01c);
	free(c09o);
...
Рейтинг: 0 / 0
P/invoke помогите
    #39440026
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
vadipok....

Ошибку найти не могу, помогите плиз.
Что не так?
Путаница в типах и параметрах.

Легким движением руки int превращается в long, а short во float.
Полная дичь с передачей массива.
Утечка памяти.

Надо курить мануалы.
...
Рейтинг: 0 / 0
P/invoke помогите
    #39440123
vadipok
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Не знаю почему, но с этим параметром c программа работает.
Сея объяснить я не могу.
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
// Многомерные характеристики
extern "C" __declspec(dllexport) void  WINAPI getARRAY_PAR(ARRAY_PAR ** p, int * c, int * plast, int * skvag, char * modelPath, int * errorCode)
{
        ..........................................
        ..........................................
        ..........................................	
	//--------------------------
	// Вывод данных 
	//--------------------------
	// выделение памяти
	int sz = ig;
	ARRAY_PAR *pt = (ARRAY_PAR*)CoTaskMemAlloc(sz * sizeof ARRAY_PAR);
	memset(pt, 0, sz * sizeof ARRAY_PAR);

	// Присвоение данных
	for (i = 0; i < ig; i++)
	{
		pt[i].id = i;
		pt[i].year = god + i;
		pt[i].month = 1;
		pt[i].day = 1;
		pt[i].oil = C09O(i, ip - 1, 0);
		pt[i].water = C09O(i, ip - 1, 1) - pt[i].oil;
		pt[i].pzab = 0;
	}

	*p = pt;
	*c = sz;
	*errorCode = error;

	// освобождение памяти 
	free(m00c);
	free(m01c);
	free(c09o);
}



Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
        [DllImport(@"Z:\*****************.dll", CallingConvention = CallingConvention.StdCall)]
        private static extern int getARRAY_PAR([MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 1)] ref ARRAY_PAR[] p,
                                   ref int c,
                                   int plast,
                                   int skvag,
                                   [MarshalAs(UnmanagedType.LPStr)] string modelPath,
                                   ref int errorCode);

        public List<PlastParArray> getData(string modelPath, int plast, int skvag = -1)
        {
            // Извлечение скважин
            ARRAY_PAR[] LTArrayPar = new ARRAY_PAR[5];
            int c = 0;
            int errorCode = 0;
            getARRAY_PAR(ref LTArrayPar, ref c, plast, skvag, modelPath, ref errorCode);
 
            ..........................................
            ..........................................
            ..........................................

}



Этот параметр нигде не используется, но без него все глючит.
Спасибо, разобрался.
Догадки только есть, возможно после передачи массива структуры необходимо передать его размер.
С этим параметром все пашет.
...
Рейтинг: 0 / 0
P/invoke помогите
    #39440145
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
vadipok,

Неверно. См документацию по маршаллингу
...
Рейтинг: 0 / 0
P/invoke помогите
    #39440150
Фотография Изопропил
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
CoTaskMemFree не вижу для ref параметра

ARRAY_PAR[] LTArrayPar = new ARRAY_PAR[5]; - утечёт
...
Рейтинг: 0 / 0
P/invoke помогите
    #39440591
vadipok
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ИзопропилCoTaskMemFree не вижу для ref параметра

ARRAY_PAR[] LTArrayPar = new ARRAY_PAR[5]; - утечёт

В первом примере посмотрите и в остальных есть, просто в многоточиях затерялся.
...
Рейтинг: 0 / 0
P/invoke помогите
    #39440726
Фотография Изопропил
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
vadipok,

c++: int * plast, int * skvag, char * modelPath, int * errorCode
значит и в c# ref должен присутсвовать

главное - количество возвращаемых структур SizeParamIndex = 1
а я вижу в коде, что размер результирующего массива в четвёртом (с нуля считая) параметре передаётся
...
Рейтинг: 0 / 0
11 сообщений из 11, страница 1 из 1
Форумы / C++ [игнор отключен] [закрыт для гостей] / P/invoke помогите
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]