-3

funcion on C

TCHAR* __stdcall W1251ToUtf8(CHAR* str)//функция пребразования строки из Windows-1251 в Unicode
{
    int wsize = MultiByteToWideChar(CP_UTF8, 0, str, -1, NULL, 0);
    TCHAR* result = new TCHAR[wsize*sizeof(TCHAR)]; 
    MultiByteToWideChar(CP_UTF8, 0, str, -1, result, wsize);
    return result;
}

function declaration in c# project

[DllImport("D://EncodingStringData.dll", EntryPoint = "W1251ToUtf8")]
        static extern string W1251ToUtf8(string str);

function call

string TextForEncoding = ReadFromFile();
string OutText = W1251ToUtf8(TextForEncoding);

first time app crash without any reason, then im add try catch

try
            { 
                string TextForEncoding = ReadFromFile();
                string OutText = W1251ToUtf8(TextForEncoding);
            }
            catch (Win32Exception ex)
            {
                System.Windows.Forms.MessageBox.Show(ex.ToString());
            }  

and i catch accessviolationexception, now crashing againg without reason.

So anyone know what i need to do?

dennismeister
  • 61
  • 1
  • 11
  • Did you compile with `/unsafe`? – Ian H. Nov 13 '16 at 23:00
  • What is the error message? – Abion47 Nov 13 '16 at 23:00
  • 3
    This function is bananas. The name and comment imply it converts Windows-1251 characters into UTF-8, which is not at all what it does -- it converts UTF-8 to UTF-16. Regardless of what it does or is supposed to do, there's a perfectly safe managed equivalent that does not require calling it at all. Use `System.Text.Encoding` to convert between encodings and don't bother with this. – Jeroen Mostert Nov 13 '16 at 23:06
  • Jeroen is right. See [this question](http://stackoverflow.com/questions/14057434/how-can-i-transform-string-to-utf-8-in-c) for some sample code – NineBerry Nov 13 '16 at 23:09
  • i should do it through unsafe code and dont ask me why – dennismeister Nov 13 '16 at 23:14
  • 2
    @dennismeister I'll give a -1 and don't ask me why – L.B Nov 13 '16 at 23:19
  • @IanH. He's just using p-invoke. –  Nov 13 '16 at 23:27
  • @Abion47 program has exited with code -1073740940 (0xc0000374). – dennismeister Nov 13 '16 at 23:49
  • 1
    That exit code doesn't tell me much of anything at all. Rather than Google it, though, I will reiterate what others have said. There is a much simpler and safer method of doing exactly this without having to bother with C code or P/Invokes, and insisting on this method after knowing that is clinically insane. – Abion47 Nov 13 '16 at 23:56

1 Answers1

1

A few problems:

  • You pass 1251 text but ask it to be treated as UTF8. So the API function call likely fails. You don't check return value for failure.
  • Your input is 8 bit text, your output if 16 bit text, but your pinvoke assumes 8 bit for both.
  • A return value type of string leads to the returned pointer being passed CoTaskMemFree for deallocation.

The exit code is STATUS_HEAP_CORRUPTION which suggests the final bullet is the immediate problem. Fix that by returning IntPtr and convert to text with Marshal.PtrToStringUni. And also export a deallocator. Or allocate off a shared heap. Or return a COM BStr. Indeed use any of the correct ways to return a string.

Having fixed that problem you'll need to fix the others too.

Quite why you won't use System.Text.Encoding is beyond me.

David Heffernan
  • 601,492
  • 42
  • 1,072
  • 1,490
  • i dont use c# tool coz my project name is "using win32/64 api dll in c# project" – dennismeister Nov 14 '16 at 08:54
  • what i need to do with another construction Declaration on C CHAR* __stdcall Utf8ToW1251(TCHAR* str); Wich types i need to use in C# code? private static extern string Utf8ToW1251(IntPtr str); IntPtr TextForEncodingInInt = Marshal.StringToHGlobalUni (TextForEncoding); string OutText = Utf8ToW1251(TextForEncodingInInt); its didnt work – dennismeister Nov 20 '16 at 20:38
  • Well no. You'll need to encode the UTF8 manually. And your function will need to deallocation the returned value too. – David Heffernan Nov 20 '16 at 20:41
  • so i need to put into function string and take IntPtr? – dennismeister Nov 21 '16 at 00:53
  • This is a different question. – David Heffernan Nov 21 '16 at 05:02