国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 學(xué)院 > 開發(fā)設(shè)計(jì) > 正文

如何調(diào)用com組件中包含IntPtr類型參數(shù)的函數(shù)

2019-11-17 02:41:01
字體:
供稿:網(wǎng)友

如何調(diào)用com組件中包含IntPtr類型參數(shù)的函數(shù)

背景

  公司的支付平臺最近對接了西安移動的支付接口,接口中簽名的方法是對方提供了一個com組件,組件中包含了一個簽名的方法和一個驗(yàn)簽的方法,注冊了簽名之后,在vs中進(jìn)行了引用,引用之后,查看組件的定義如下:

using System;using System.Runtime.InteropServices;namespace UMPAYLib{    [ClassInterface(0)]    [Guid("E92EB0AA-00CC-4F93-A76D-632BEA94E980")]    [TypeLibType(2)]    [ComConversionLoss]    public class SignClass : ISign, Sign    {        public SignClass();        [DispId(1)]        public virtual string Sign(string str, string certfile, string keyfile);        [DispId(2)]        public virtual int Verify(string str, string sig, IntPtr certfile);    }}

  首先先看一下簽名的方法:Sign(string str,string certfile,string keyfile);

  三個參數(shù)分別是用于簽名的串、公鑰證書的路徑和私鑰證書的路徑。

  再看驗(yàn)簽的方法:Verify(string str,string sig,IntPtr certfile);

  三個參數(shù)分別是用于簽名的串,要驗(yàn)證的簽名值和公鑰證書的路徑。

  那么問題來了,驗(yàn)簽方法的第三個參數(shù),證書的路徑怎么是IntPtr類型呢?IntPtr到底是個什么類型呢?我該怎么調(diào)用這個方法呢?

解決過程

  首先我問題了接口方,接口放的對接人員倒是挺負(fù)責(zé)任,幫我看文檔,問同事,可接口方看過他們自己的文檔之后,也郁悶了,他們也不清楚文檔咋和組件里的方法定義不一樣,他們說要請示總部,而請示總部要用郵件,而且半天也不見回復(fù),可接口后天就要上線測試了,等回復(fù)看來不靠譜,還得靠自己,于是就開始了求助度娘。

  首先我們來看看IntPtr到底是個什么類型?

  MSDN的解釋:

用于表示指針或句柄的平臺特定類型。備注:IntPtr 類型被設(shè)計(jì)成整數(shù),其大小適用于特定平臺。 即是說,此類型的實(shí)例在 32 位硬件和操作系統(tǒng)中將是 32 位,在 64 位硬件和操作系統(tǒng)上將是 64 位。IntPtr 類型可以由支持指針的語言使用,并可作為在支持與不支持指針的語言間引用數(shù)據(jù)的一種通用方式。IntPtr 對象也可用于保持句柄。 例如,IntPtr 的實(shí)例廣泛地用在 System.IO.FileStream 類中來保持文件句柄。IntPtr 類型符合 CLS,而 UIntPtr 類型卻不符合。 只有 IntPtr 類型可用在公共語言運(yùn)行時中。 UIntPtr 類型大多數(shù)是提供來維護(hù)與 IntPtr 類型之間的體系結(jié)構(gòu)上的對稱性。此類型實(shí)現(xiàn) ISerializable 接口。

  其中一行是這樣說的:

  IntPtr類型可以由支持指針的語言使用,并可作為在支持與不支持指針的語言間引用數(shù)據(jù)的一種通用方式。

引用數(shù)據(jù)的通用方式?指針?看到這個之后,我就在度娘里輸入了“IntPtr傳字符串“幾個字,搜索結(jié)果中看到了一篇園子里一個仁兄寫的博客,http://m.survivalescaperooms.com/jxsoft/archive/2011/07/06/2099061.html,正式這篇博客,讓我豁然開朗,找到了問題最終的解決辦法,雖然解決的方法不是用的這位仁兄的方法,但思路是從這兒而來,所以還是要謝謝”許明吉博客“了。

  我先是用了這篇博客中的如下這個方法進(jìn)行測試:

/// <summary>           /// 根據(jù)數(shù)據(jù)的長度申請非托管空間           /// </summary>           /// <param name="strData">要申請非托管空間的數(shù)據(jù)</param>           /// <returns>指向非拖管空間的指針</returns>           PRivate static IntPtr mallocIntptr( string strData )          {              //先將字符串轉(zhuǎn)化成字節(jié)方式               Byte[] btData = System.Text.Encoding.Default.GetBytes(strData);                //申請非拖管空間               IntPtr m_ptr = Marshal.AllocHGlobal(btData.Length);                //給非拖管空間清0                Byte[] btZero = new Byte[btData .Length+ 1]; //一定要加1,否則后面是亂碼,原因未找到               Marshal.Copy(btZero, 0, m_ptr, btZero.Length);                //給指針指向的空間賦值               Marshal.Copy(btData, 0, m_ptr, btData.Length);                return m_ptr;          }  

  測試的代碼如下:

UMPAYLib.SignClass signClass = new UMPAYLib.SignClass();IntPtr ptrCertFile = mallocIntptr(certFile);int b = signClass.Verify(prestr, SIGN, ptrCertFile);

運(yùn)行測試的頁面,當(dāng)執(zhí)行到signClass.Verify這個com組件驗(yàn)簽的方法的時候,報(bào)了一個”沒有足夠的內(nèi)存來繼續(xù)運(yùn)行程序“的異常,組件內(nèi)部的代碼也看不到,所以也不知道里面怎么處理導(dǎo)致了這個內(nèi)存溢出的異常,好不容易找到了思路,卻有出現(xiàn)了這個問題,該怎么辦呢?于是我又看了看ptrCertFile的屬性和方法,我輸出了ptrCertFile的.ToString(),發(fā)現(xiàn)得到了一個很大的數(shù)字,可還是不知道為什么會內(nèi)存溢出,我又仔細(xì)看了看,mallocIntptr這個方法,方法里有一個分配內(nèi)存的類引起了我的興趣,它就是Marshal,我們再來看看Mashal這個類具體是干啥的?有啥方法?

MSDN的解釋:

提供了一個方法集,這些方法用于分配非托管內(nèi)存、復(fù)制非托管內(nèi)存塊、將托管類型轉(zhuǎn)換為非托管類型,此外還提供了在與非托管代碼交互時使用的其他雜項(xiàng)方法。

從解釋中可以看出,該類主要是用于分配非托管內(nèi)存和在托管類型和非托管類型之間進(jìn)行轉(zhuǎn)換。

于是我就瀏覽了一下Mashal類的成員,發(fā)現(xiàn)了一個方法:

而這個方法也本身就能實(shí)現(xiàn)上面mallocIntptr這個方法的功能,于是我就把代碼修改為如下:

UMPAYLib.SignClass signClass = new SignClass();string certPath = MobileWapPayConfig.CertFile;IntPtr ptrCertFile = Marshal.StringToBSTR(certPath);int result = signClass.Verify(prestr, sign, ptrCertFile);Marshal.FreeBSTR(ptrCertFile);return result == 0;

重新運(yùn)行測試頁面,一切正常。

至此,最初遇到的IntPtr不知如何調(diào)用的問題已經(jīng)解決了,但遺留了一個小問題,那就是為什么mallocIntptr這個方法會導(dǎo)致內(nèi)存溢出,望了解的朋友不吝賜教!

總結(jié)

對于一些com組件的方法參數(shù)IntPtr類型的,可以使用Marshal類的相關(guān)方法來處理。


發(fā)表評論 共有條評論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
主站蜘蛛池模板: 佛冈县| 右玉县| 清新县| 逊克县| 辽宁省| 扎兰屯市| 明光市| 拜泉县| 渭南市| 富源县| 蒙山县| 金昌市| 肇庆市| 马公市| 札达县| 郑州市| 沾益县| 张家界市| 吴桥县| 五常市| 恩平市| 丹凤县| 丰都县| 始兴县| 灌南县| 玛曲县| 淄博市| 开化县| 基隆市| 宁都县| 汽车| 米林县| 吉林省| 沅江市| 泸水县| 车致| 英吉沙县| 高要市| 柏乡县| 都匀市| 陇南市|