目录
一.前言
二.netcore调用
1.windows库引用dll文件
2.linux库引用so文件
3.C++接口所需结构体
4.实现帮助类/返回结果类
一.前言
C++提供了windows和linux的两种库,netcore调用并实现.
二.netcore调用 1.windows库引用dll文件public static class VVSecurity_win32 { private const string dllName = "Lib/vvsec_win32/VVSecurity.dll"; [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_Initlize(IntPtr pDevice, string pUserPin); [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_SM4EncryptData(DEVICE_HANDLE pDevice, PKI_DATA plaintext, ref PKI_DATA ciphertext); [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_SM4DecryptData(DEVICE_HANDLE pDevice, PKI_DATA ciphertext, ref PKI_DATA plaintext); [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_Finalize(DEVICE_HANDLE pDevice); }2.linux库引用so文件
public static class VVSecurity_centos64 { private const string dllName = "Lib/vvsec_centosx64/VVSecurity.so"; [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_Initlize(IntPtr pDevice, string pUserPin); [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_SM4EncryptData(DEVICE_HANDLE pDevice, PKI_DATA plaintext, ref PKI_DATA ciphertext); [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_SM4DecryptData(DEVICE_HANDLE pDevice, PKI_DATA ciphertext, ref PKI_DATA plaintext); [Dllimport(dllName, CharSet = CharSet.Ansi, CallingConvention = CallingConvention.Cdecl)] public static extern int VVSec_Finalize(DEVICE_HANDLE pDevice); }3.C++接口所需结构体
public struct DEVICE_HANDLE { public uint hdev { get; set; } public uint hcont { get; set; } public uint happ { get; set; } } ///4.实现帮助类/返回结果类/// 加解密结构体:用句柄接收byte[]返回值 /// public struct PKI_DATA { ////// value的长度,以16位单位增长.加密后的密文存储空间需要计算. /// public int size { get; set; } ////// 值:byte[]句柄 /// public IntPtr value { get; set; } }
public static class VVSecurityHelper { public static bool IsSuccessVVSecInit { get { return _issSuccessVVSecInit; } } private static bool _issSuccessVVSecInit = false; private static object _lockEncrypt = new object();//加密锁 private static object _lockDecrypt = new object();//解密锁 #region 处理后的加解密 private static DEVICE_HANDLE _deviceHandle = new DEVICE_HANDLE(); public static VVSecResult Init(string pUserPin = null) { try { DEVICE_HANDLE dh = new DEVICE_HANDLE(); GCHandle initlizeHandle = GCHandle.Alloc(dh, GCHandleType.Pinned); var pdevice = Marshal.AllocHGlobal(12); Marshal.StructureToPtr(dh, pdevice, false); int code = 0; if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { #region 设置动态库路径 StreamWriter sw = new StreamWriter("aavs.sh", false, Encoding.ASCII); string dirPath = Path.Combine(Directory.GetCurrentDirectory(), "Lib/vvsec_centosx64").Trim('/').Replace("/", "\/"); sw.WriteLine($"sed -i '/{dirPath}/d' /etc/ld.so.conf");//删除配置项 sw.WriteLine($"echo '{Directory.GetCurrentDirectory()}/Lib/vvsec_centosx64'>>/etc/ld.so.conf");//增加配置项 sw.WriteLine("ldconfig"); sw.Close(); Process process = new Process(); process.StartInfo.FileName = "sh"; process.StartInfo.Arguments = "aavs.sh"; process.Start(); process.WaitForExit(); process.Close(); #endregion code = VVSecurity_centos64.VVSec_Initlize(pdevice, pUserPin); } else { code = VVSecurity_win32.VVSec_Initlize(pdevice, pUserPin); } Console.WriteLine($"安全加密.初始化:状态码{code}"); _issSuccessVVSecInit = code == 0; _deviceHandle = Marshal.PtrToStructure(pdevice); initlizeHandle.Free(); return new VVSecResult { code = code }; } catch (Exception ex) { Console.WriteLine("安全加密初始化异常:" + ex.ToString()); return new VVSecResult { code = -2, msessage = ex.ToString() }; } } public static VVSecResult Encrypt(string plaintextStr) { //初始化未成功,原文返回 if (!_issSuccessVVSecInit) return new VVSecResult { code = -1, text = plaintextStr }; //空内容 if (string.IsNullOrEmpty(plaintextStr)) return new VVSecResult { code = 0, text = "" }; lock (_lockEncrypt) { //明文 byte[] plaintextBt = Encoding.UTF8.GetBytes(plaintextStr); var plaintextGCH = GCHandle.Alloc(plaintextBt, GCHandleType.Pinned); PKI_DATA plaintextData = new PKI_DATA() { size = plaintextBt.Length, value = plaintextGCH.AddrOfPinnedObject() }; plaintextGCH.Free(); //密文 var ciphertextLen = (plaintextBt.Length / 16 + 1) * 16;//以16为单位增长 byte[] ciphertextBt = new byte[ciphertextLen]; var ciphertextGCH = GCHandle.Alloc(ciphertextBt, GCHandleType.Pinned); PKI_DATA ciphertextData = new PKI_DATA() { size = ciphertextLen, value = ciphertextGCH.AddrOfPinnedObject() }; int code = 0; if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { code = VVSecurity_centos64.VVSec_SM4EncryptData(_deviceHandle, plaintextData, ref ciphertextData); } else { code = VVSecurity_win32.VVSec_SM4EncryptData(_deviceHandle, plaintextData, ref ciphertextData); } var byteArr = (byte[])ciphertextGCH.Target;//密文返回值 var plaintextResult = code == 0 ? Convert.Tobase64String(byteArr) : ""; ciphertextGCH.Free(); var result = new VVSecResult() { code = code, text = plaintextResult }; return result; } } public static VVSecResult Decrypt(string ciphertextbase64) { //初始化未成功,原文返回 if (!_issSuccessVVSecInit) return new VVSecResult { code = -1, text = ciphertextbase64 }; //空内容 if (string.IsNullOrEmpty(ciphertextbase64)) return new VVSecResult { code = 0, text = "" }; lock (_lockDecrypt) { byte[] ciphertextBt = null; try { ciphertextBt = Convert.Frombase64String(ciphertextbase64); } catch (Exception) { return new VVSecResult { code = -3, text = "" };//要解密的字符串不是base64内容 } //空密文直接返回 if (ciphertextBt == null || ciphertextBt.Length == 0) return new VVSecResult { code = 0, text = "" }; //密文 var ciphertextGCH = GCHandle.Alloc(ciphertextBt, GCHandleType.Pinned); PKI_DATA ciphertextData = new PKI_DATA() { size = ciphertextBt.Length, value = ciphertextGCH.AddrOfPinnedObject() }; ciphertextGCH.Free(); //明文 byte[] plaintextBt = new byte[ciphertextBt.Length]; var plaintextGCH = GCHandle.Alloc(plaintextBt, GCHandleType.Pinned); PKI_DATA plaintextData = new PKI_DATA() { size = plaintextBt.Length, value = plaintextGCH.AddrOfPinnedObject() }; int code = 0; if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) { code = VVSecurity_centos64.VVSec_SM4DecryptData(_deviceHandle, ciphertextData, ref plaintextData); } else { code = VVSecurity_win32.VVSec_SM4DecryptData(_deviceHandle, ciphertextData, ref plaintextData); } var byteArr = (byte[])plaintextGCH.Target;//明文byte数组 plaintextGCH.Free(); var text = Encoding.UTF8.GetString(byteArr).Replace("", "");//去掉明文中的空位 var result = new VVSecResult() { code = code, text = text }; return result; } } #endregion } public class VVSecResult { /// /// 状态码:0成功,其他失败 /// public int code { get; set; } ////// 加密后的base64密文 / 解密后的明文 /// public string text { get; set; } public string msessage { get; set; } }
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)