首页 > 解决方案 > 为什么在后续调用中不能使用 IntPtr

问题描述

我的程序:

class Program {
    [DllImport("libiconvD.dll", CallingConvention = CallingConvention.Cdecl)]
    public static extern IntPtr libiconv_open([MarshalAs(UnmanagedType.LPStr)]
                                          string tocode, 
                                          [MarshalAs(UnmanagedType.LPStr)] 
                                          string fromcode);

    [DllImport("libiconvD.dll", CallingConvention = CallingConvention.Cdecl)]
    static extern ulong libiconv(IntPtr icd,
                             ref StringBuilder inbuf, ref ulong inbytesleft,
                             out StringBuilder outbuf, out ulong outbytesleft);

    [DllImport("libiconvD.dll", CallingConvention = CallingConvention.Cdecl)]
    static extern int libiconv_close(IntPtr icd);

    static void Main(string[] args) {
        var inbuf = new StringBuilder("Rule(s): Global Tag – Refer to Print Rules – General Requirements");
        ulong inbytes = (ulong)inbuf.Length;
        ulong outbytes = inbytes;
        StringBuilder outbuf = new StringBuilder((int)outbytes);

        IntPtr icd = libiconv_open("utf8", "windows-1252");
        var rcode1 = libiconv(icd, ref inbuf, ref inbytes, out outbuf, out outbytes);
        Debug.WriteLine(rcode1);
        var rcode2 = libiconv_close(icd);
        Debug.WriteLine(rcode2);
    }//Main()
}//Program CLASS

libiconv_open() 的第一次调用有效并返回一个指向 icd 的指针。当 libiconv() 的第二次调用运行时,它会在 icd 指针上发生访问冲突。

这是被调用的 C 代码:

size_t iconv (iconv_t icd,
              ICONV_CONST char* * inbuf, size_t *inbytesleft,
              char* * outbuf, size_t *outbytesleft)
{
  conv_t cd = (conv_t) icd;
  if (inbuf == NULL || *inbuf == NULL)
    return cd->lfuncs.loop_reset(icd,outbuf,outbytesleft);
  else
    return cd->lfuncs.loop_convert(icd,
                                   (const char* *)inbuf,inbytesleft,
                                   outbuf,outbytesleft);
}

在此处输入图像描述 它似乎无法访问指针指向的结构中定义的函数。是否必须对返回的指针执行一些特殊操作才能在后续调用中使用。

谢谢

标签: c#cpinvoke

解决方案


事实证明,C# 不需要使用 libiconv 库。只需使用 Encoding 类。

        static void Main(string[] args) {
            UTF8Encoding utf8 = new UTF8Encoding();
            Encoding w1252 = Encoding.GetEncoding(1252);

            string inbuf = "Rule(s): Global Tag – Refer to Print Rules – General Requirements";
            byte[] bytearray = utf8.GetBytes(inbuf);
            byte[] outbytes = Encoding.Convert(utf8, w1252, bytearray);

            Debug.WriteLine("*************************");
            Debug.WriteLine(String.Format("  Input: {0}", inbuf));
            Debug.WriteLine(String.Format(" Output: {0}", utf8.GetString(outbytes)));
            Debug.WriteLine("*************************");

        }//Main()

*************************
  Input: Rule(s): Global Tag – Refer to Print Rules – General Requirements
 Output: Rule(s): Global Tag – Refer to Print Rules – General Requirements
*************************

推荐阅读