Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / C++ [игнор отключен] [закрыт для гостей] / _bstr_t преобразовать в строку / 25 сообщений из 40, страница 1 из 2
12.04.2004, 14:11
    #32477521
panza
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Имею переменную _bstr_t bstrStr. В неё залито какое то значение,типа"Hello,word!".

Как перелить это в С-строку (массив символов,заканчивающийся нулем)?
...
Рейтинг: 0 / 0
12.04.2004, 14:26
    #32477555
ZrenBy
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Код: sql
1.
2.
3.
4.
5.
_bstr_t Tmp = "Hello"; 
char* szTmp = new char[Tmp.length()+1];
strcpy(szTmp,(LPCSTR)Tmp);
fprintf(stderr,"%s\n",szTmp);
delete [] szTmp;
...
Рейтинг: 0 / 0
12.04.2004, 14:31
    #32477569
panza
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Спасибо.

P.S.
(Тьфу,как все просто.)
...
Рейтинг: 0 / 0
12.04.2004, 14:54
    #32477629
funikovyuri
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
(Тьфу,как все просто.)
_bstr_t это врапер для
BSTR т.е. это Unicode-строка - вы уверены что хотите ее в char* переделать? Можно ведь и в wchar_t*

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
//http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vclang98/HTML/_pluslang__bstr_t.asp

operator const wchar_t*( ) const throw( );

operator wchar_t*( ) const throw( );

operator const char*( ) const throw( _com_error );

operator char*( ) const throw( _com_error );

Remarks

These operators can be used to extract raw pointers to the encapsulated Unicode or multibyte BSTR object.
The operators return the pointer to the actual internal buffer, so the resulting string cannot be modified.


...
Рейтинг: 0 / 0
12.04.2004, 15:06
    #32477649
panza
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
стоп,стоп,на самом деле мне нужно в unsigned char передавать
а там приведение типа
strcpy(szTmp,(LPCSTR)Tmp);//ругается на второй параметр

на самом деле у меня под new-массивы из unsigned char заделан довольно боьшой кусок проги и ковырять его очень не хотелось бы
??
...
Рейтинг: 0 / 0
12.04.2004, 15:22
    #32477696
ZrenBy
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Код: plaintext
1.
2.
3.
4.
_bstr_t Tmp =  "Hello" ; 
unsigned char* szTmp = new unsigned char[Tmp.length()+ 1 ];
strcpy((char*)szTmp,(LPCSTR)Tmp);
fprintf(stderr, "\n%s\n" ,szTmp);
delete [] szTmp;
...
Рейтинг: 0 / 0
12.04.2004, 15:35
    #32477733
panza
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Действительно,работает.
Спасибо,ZrenBy .
...
Рейтинг: 0 / 0
14.04.2004, 19:14
    #32481750
panza
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Н-н-нда-а, работает оно ,как же.
Компилится,то оно компилится,в вот при освобождении
памяти прога сваливается.

//////////////////
_bstr_t bstrStr;
unsigned char* p_ucValue;
int length;


bstrStr = "Hello";
length = bstrStr.length()+1;
p_ucFieldValue = new unsigned char(length);
strcpy((char*)p_ucValue,(LPCSTR)bstrStr);

delete []p_ucValue;//вылет
//////////////////////////////////

мне кажется что всё таки нельзя для strcpy втупую
приводить указатель на char к указателю на unsigned char
...
Рейтинг: 0 / 0
14.04.2004, 19:30
    #32481771
panza
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Извиняюсь,ошибся сам.

p_ucFieldValue = new unsigned char [ length ] ;
а не
p_ucFieldValue = new unsigned char ( length ) ;
...
Рейтинг: 0 / 0
14.04.2004, 19:49
    #32481785
ZrenBy
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Вот еще вариант

Код: plaintext
memcpy((LPVOID)szTmp,(LPVOID)(LPCSTR)Tmp,Tmp.length()+ 1 );
...
Рейтинг: 0 / 0
15.04.2004, 17:38
    #32483275
Alexandr Davydenko
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Можно и так:

Код: plaintext
1.
2.
3.
_bstr_t BodyData
DWORD nBodyDataSize = BodyData.length();
BYTE * pBody = new BYTE[nBodyDataSize];
wcstombs((char *)pBody, BodyData, nBodyDataSize);
...
Рейтинг: 0 / 0
Период между сообщениями больше года.
14.10.2016, 16:33
    #39327257
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
ZrenBy
Код: sql
1.
2.
3.
4.
5.
_bstr_t Tmp = "Hello"; 
char* szTmp = new char[Tmp.length()+1];
strcpy(szTmp,(LPCSTR)Tmp);
fprintf(stderr,"%s\n",szTmp);
delete [] szTmp;



А у меня на строке:
strcpy(szTmp,(LPCSTR)Tmp);

VS2013 Выдает ошибку:
error C4996: 'strcpy': This function or variable may be unsafe. Consider using strcpy_s instead. To disable deprecation, use _CRT_SECURE_NO_WARNINGS. See online help for details.

подскажите плиз...
...
Рейтинг: 0 / 0
14.10.2016, 19:53
    #39327363
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Разобрался сам.
...
Рейтинг: 0 / 0
16.10.2016, 21:36
    #39327856
MasterZiv
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Arbit,

Вот этот макрос _CRT_SECURE_NO_WARNINGS определи в проекте (лучше всего), или если не знаешь, как,
напиши в первой строке исходного кода (каждого модуля, если их несколько).

Код: plaintext
1.
#define_CRT_SECURE_NO_WARNINGS



Когда вырастишь, и поймёшь, зачем это, макрос можно будет удалить.
...
Рейтинг: 0 / 0
17.10.2016, 20:41
    #39328529
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
MasterZiv , спасибо за макрос!

Есть вопрос по обмену данными между С++ и С#
В разных способах результат один и тот же получаю
Наступил на грабли в приведении типов в соответствие
Чтобы не засорять тему можно в личку?

Спасибо

Модератор: чтобы не засорять тему, можно в новой теме. А "лички" на sql.ru никогда не было.
...
Рейтинг: 0 / 0
17.10.2016, 21:28
    #39328538
Изопропил
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Arbit,

с unicode сначала чуток разберись
...
Рейтинг: 0 / 0
19.10.2016, 21:23
    #39330179
MasterZiv
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
ZrenBy
Код: sql
1.
2.
3.
4.
5.
_bstr_t Tmp = "Hello"; 
char* szTmp = new char[Tmp.length()+1];
strcpy(szTmp,(LPCSTR)Tmp);
fprintf(stderr,"%s\n",szTmp);
delete [] szTmp;




тогда уж лучше так

Код: sql
1.
2.
3.
4.
_bstr_t Tmp = "Hello"; 
std::vector<char> szTmp( Tmp.length()+1 );
strcpy(&szTmp[0],(LPCSTR)Tmp);
fprintf(stderr,"%s\n",&szTmp[]);
...
Рейтинг: 0 / 0
24.10.2016, 21:58
    #39333146
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Уважаемые ГУРУ!
Помогите пожалуйста разобраться.

При использовании COM объекта (работа с WMI )
В качестве примера взял на сайте MSDN
https://msdn.microsoft.com/en-us/library/aa390423(v=vs.85).aspx
получаю результат - свойство объекта (строку с типом BSTR ). Строка содержит ожидаемое значение.
Сохраняю его в _bstr_t resValue.

Все это происходит в функции DLL (c++), которая получает параметром указатель на выделенный блок памяти
необходимого размера из С# wchar_t* pResult

Преобразовываю _bstr_t strBstr в wchar_t и записываю в выделенный блок памяти по переданному указателю.

В вызывающем коде на C# получаю исключение, из DLL передается NULL

А если я создам _bstr_t в ручную , (bstr_t strBstr = L"Test")
то на стороне С# получаю нужную строку


Подскажите пожалуйста на какие грабли я наступил.
И как правильно преобразовать _bstr_t в данном случае

Бьюсь уже неделю.
Передавал строку и используя строковый буфер StringBuilder

Пробовал передавать и непосредственно тип _bstr_t и в шарпе соответствующий код писал
Результат один и тот же:
"ручная" bstr_t строка передается, а bstr_t из COM объекта - нет, хотя при отладке pResult содержит данные

Заранее всем благодарен

С#
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
[DllImport(@"D:\\ProjectsC++\\DLL\\DLLPodolog\\Debug\\DLLPodolog.dll",
            EntryPoint = "GetSomeText",
            ExactSpelling = true,
            CharSet = CharSet.Unicode,
            CallingConvention = CallingConvention.Cdecl)]

public static extern int GetSomeText(IntPtr pComputerName);

var pComputerName = Marshal.AllocHGlobal(4096);
            GetSomeText(pComputerName);
            var str = Marshal.PtrToStringUni(pComputerName);
            Marshal.FreeHGlobal(pComputerName);



Вот такой вариант работает нормально
C++
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
extern "C" __declspec(dllexport)  int GetSomeText(wchar_t* pResult)
{
	_bstr_t resValue = L"TestString";

	const size_t widesize = resValue.length() + 1;
	wcscpy_s(pResult, widesize, (wchar_t *)resValue);
	wcscat_s(pResult, widesize, L"\0");
};



А такой вариант дает исключение - NULL при передаче строки wchar_t* pResult
C++
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
extern "C" __declspec(dllexport)  int GetSomeText(wchar_t* pResult)
{
	_bstr_t resValue;

// в resValue  функция GetStringID(resValue) возвращает нужную _bstr_t  строку (функция большая потому не привожу.
// но возвращает нужный результат - _bstr_t  строку из COM объекта 

	int result = GetStringID(resValue); 
	const size_t widesize = resValue.length() + 1;
	wcscpy_s(pResult, widesize, (wchar_t *)resValue);
	wcscat_s(pResult, widesize, L"\0");
};
...
Рейтинг: 0 / 0
24.10.2016, 22:28
    #39333157
Изопропил
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Arbit
Код: plaintext
1.
int result = GetStringID(resValue); 


подозреваю что resValue передаётся по значению, а не по ссылке
...
Рейтинг: 0 / 0
24.10.2016, 22:39
    #39333165
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Изопропил,

Вот функция
int GetStringID(bstr_t & ID)
{
......
}
...
Рейтинг: 0 / 0
24.10.2016, 22:52
    #39333171
Изопропил
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Arbit,

ещё раз и целиком как в соседнем топике (в спойлер заверни, чтоб глаз не мозолила)
дьявол - в деталях
...
Рейтинг: 0 / 0
25.10.2016, 12:05
    #39333441
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Изопропил,
Я все оформил в класс, и как консольное приложение все работает, все строки присутствуют
Но как DLL, строки _bstr_t из COM не передаются

С#
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
[DllImport(@"D:\\ProjectsC++\\DLL\\DLLPodolog\\Debug\\DLLPodolog.dll",
            EntryPoint = "GetSomeText",
            ExactSpelling = true,
            CharSet = CharSet.Unicode,
            CallingConvention = CallingConvention.Cdecl)]

public static extern int GetSomeText(IntPtr pComputerName);

var pComputerName = Marshal.AllocHGlobal(4096);
            GetSomeText(pComputerName);
            var str = Marshal.PtrToStringUni(pComputerName);
            Marshal.FreeHGlobal(pComputerName);



C++
Сама функция в DLL
"C" __declspec(dllexport) int GetSomeText(wchar_t* pResult)
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
#pragma once
#include "HardWareData.h"



extern "C" __declspec(dllexport)  int GetSomeText(wchar_t* pResult)
{

	HardWareData objHW;
	_bstr_t resValue;
	int result = objHW.GetStringID(resValue);

	const size_t widesize = resValue.length() + 1;
	wcscpy_s(pResult, widesize, (wchar_t *)resValue);
	wcscat_s(pResult, widesize, L"\0");

	return 0;
};



HardWareData.h
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
#pragma once
#pragma comment(lib, "wbemuuid.lib")  //Библиотека для работы с WMI 
#define _WIN32_DCOM
#include <comdef.h>  //Для работы с COM  (типы параметров в методах класса)
#include <Wbemidl.h> // Для работы с WMI 
using namespace std;

class HardWareData
{
private:
	int GetWmiInfo(char[], wchar_t[], bstr_t &);

public:
	HardWareData();
	~HardWareData();
	int GetStringID(_bstr_t &);
};



HardWareData.cpp
Функция GetWmiInfo(char strSQL[], wchar_t NamePrt[], bstr_t & resValue)
Код: 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.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
84.
85.
86.
87.
88.
89.
90.
91.
92.
93.
94.
95.
96.
97.
98.
99.
100.
101.
102.
103.
104.
105.
106.
107.
108.
109.
110.
111.
112.
113.
114.
115.
116.
117.
118.
119.
120.
121.
122.
123.
124.
125.
126.
127.
128.
129.
130.
131.
132.
133.
134.
135.
136.
137.
138.
139.
140.
141.
142.
143.
144.
145.
146.
147.
148.
149.
150.
151.
152.
153.
#pragma once
#include "HardWareData.h"

HardWareData::HardWareData()
{
}

HardWareData::~HardWareData()
{
}
int HardWareData::GetWmiInfo(char strSQL[], wchar_t NamePrt[], bstr_t & resValue)
{
	HRESULT hres;
	// Step 1: Initialize COM ------------------------------------------
	hres = CoInitializeEx(0, COINIT_MULTITHREADED);
	if (FAILED(hres))
	{
		resValue = "Failed to initialize COM library. Error code = 0x";
		return 1;                  // Program has failed.
	}

	// Step 2: Set general COM security levels --------------------------
	hres = CoInitializeSecurity(
		NULL,
		-1,                          // COM authentication
		NULL,                        // Authentication services
		NULL,                        // Reserved
		RPC_C_AUTHN_LEVEL_DEFAULT,   // Default authentication 
		RPC_C_IMP_LEVEL_IMPERSONATE, // Default Impersonation  
		NULL,                        // Authentication info
		EOAC_NONE,                   // Additional capabilities 
		NULL                         // Reserved
		);

	if (FAILED(hres))
	{
		resValue = "Failed to initialize security. Error code = 0x";
		CoUninitialize();
		return 1;                    // Program has failed.
	}

	// Step 3: Obtain the initial locator to WMI -------------------------
	IWbemLocator *pLoc = NULL;
	hres = CoCreateInstance(
		CLSID_WbemLocator,
		0,
		CLSCTX_INPROC_SERVER,
		IID_IWbemLocator, (LPVOID *)&pLoc);

	if (FAILED(hres))
	{
		resValue = "Failed to create IWbemLocator object. Err code = 0x";
		CoUninitialize();
		return 1;                 // Program has failed.
	}

	// Step 4: Connect to WMI through the IWbemLocator::ConnectServer method
	IWbemServices *pSvc = NULL;
	// Connect to the root\cimv2 namespace with the current user and obtain pointer pSvc to make IWbemServices calls.
	hres = pLoc->ConnectServer(
		_bstr_t(L"ROOT\\CIMV2"), // Object path of WMI namespace
		NULL,                    // User name. NULL = current user
		NULL,                    // User password. NULL = current
		0,                       // Locale. NULL indicates current
		NULL,                    // Security flags.
		0,                       // Authority (for example, Kerberos)
		0,                       // Context object 
		&pSvc                    // pointer to IWbemServices proxy
		);

	if (FAILED(hres))
	{
		resValue = "Could not connect. Error code = 0x";
		pLoc->Release();
		CoUninitialize();
		return 1;                // Program has failed.
	}
	resValue = "Connected to ROOT\\CIMV2 WMI namespace";

	// Step 5: Set security levels on the proxy -------------------------
	hres = CoSetProxyBlanket(
		pSvc,                        // Indicates the proxy to set
		RPC_C_AUTHN_WINNT,           // RPC_C_AUTHN_xxx
		RPC_C_AUTHZ_NONE,            // RPC_C_AUTHZ_xxx
		NULL,                        // Server principal name 
		RPC_C_AUTHN_LEVEL_CALL,      // RPC_C_AUTHN_LEVEL_xxx 
		RPC_C_IMP_LEVEL_IMPERSONATE, // RPC_C_IMP_LEVEL_xxx
		NULL,                        // client identity
		EOAC_NONE                    // proxy capabilities 
		);

	if (FAILED(hres))
	{
		resValue = "Could not set proxy blanket. Error code = 0x";
		pSvc->Release();
		pLoc->Release();
		CoUninitialize();
		return 1;               // Program has failed.
	}

	// Step 6: Use the IWbemServices pointer to make requests of WMI ----
	IEnumWbemClassObject* pEnumerator = NULL;
	hres = pSvc->ExecQuery(
		bstr_t("WQL"),
		//bstr_t("SELECT * FROM Win32_BaseBoard"),    //Серийный номер BaseBoard
		bstr_t(strSQL),
		WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY,
		NULL,
		&pEnumerator);

	if (FAILED(hres))
	{
		resValue = "Query for operating system name failed. Error code = 0x";
		pSvc->Release();
		pLoc->Release();
		CoUninitialize();
		return 1;               // Program has failed.
	}

	// Step 7: -------------------------------------------------
	// Get the data from the query in step 6 -------------------
	IWbemClassObject *pclsObj = NULL;
	ULONG uReturn = 0;

	while (pEnumerator)
	{
		HRESULT hr = pEnumerator->Next(WBEM_INFINITE, 1,
			&pclsObj, &uReturn);

		if (0 == uReturn)
		{
			break;
		}

		VARIANT vtProp;
		// Get the value of the Name property
		//hr = pclsObj->Get(NamePrt, 0, &vtProp, 0, 0)
		hr = pclsObj->Get(NamePrt, 0, &vtProp, 0, 0);  		//+vtProp	BSTR = 0x005205b4 L"PF05TBD8"	tagVARIANT
		resValue = vtProp.bstrVal;
		VariantClear(&vtProp);
		pclsObj->Release();
	}

	// Cleanup
	// ========
	pSvc->Release();
	pLoc->Release();
	pEnumerator->Release();

	CoUninitialize();

	return 0;   // Program successfully completed.
}


Функция GetStringID(bstr_t & ID)
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
int HardWareData::GetStringID(bstr_t & ID)
{	
	bstr_t resValue;
	//BaseBoard
	char strSQL1[] = "SELECT * FROM Win32_BaseBoard";
	wchar_t NamePrt1[] = L"SerialNumber";
	int result = GetWmiInfo(strSQL1, NamePrt1, resValue);
	bstr_t BaseBoard(resValue);



	ID = L"BaseBoard=" + BaseBoard;

	return 0;
}

...
Рейтинг: 0 / 0
25.10.2016, 21:55
    #39333962
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Потролить конечно проще, чем подсказать правильное решение :)
Но и на том спасибо :)
...
Рейтинг: 0 / 0
25.10.2016, 22:33
    #39333975
Изопропил
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Arbit,

видишь ли, у всех нас есть работа.
только сейчас появилась возможность внимательно прочитать твой код да и решение предложить почище.
...
Рейтинг: 0 / 0
26.10.2016, 01:03
    #39334007
Arbit
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
_bstr_t преобразовать в строку
Изопропил ,

Я благодарен за то что при всей занятости выделили на меня немного времени.
Меня сбила с толку фраза: "в спойлер заверни, чтоб глаз не мозолила", подумал что надоедаю. :)

Я благодарен за любую помощь и ценный совет:)
...
Рейтинг: 0 / 0
Форумы / C++ [игнор отключен] [закрыт для гостей] / _bstr_t преобразовать в строку / 25 сообщений из 40, страница 1 из 2
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


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