/*********************************************************************** * * Copyright (C) 2005-2006 Novell, Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; version 2.1 * of the License. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Library General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * * To contact Novell about this file by physical or electronic mail, * you may find current contact information at www.novell.com. * ***********************************************************************/ using System; using System.Runtime.InteropServices; using System.Text; using System.Collections.Specialized; using System.Collections; using Novell.CASA.MiCasa.Communication; using Novell.CASA.MiCasa.Common; namespace Novell.CASA { /// /// Summary description for NativeCalls. /// public class NativeCalls { private static SSCS_KEYCHAIN_ID_T DefaultKeychainID = null; private static int SSCS_CRED_TYPE_BASIC_F = 1; private static int USERNAME_LEN = 256; private static int PASSWORD_LEN = 128; public NativeCalls() { // // TODO: Add constructor logic here // if (DefaultKeychainID == null) { DefaultKeychainID = new SSCS_KEYCHAIN_ID_T(); } } [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_PASSWORD_T { public uint pwordType; public uint pwordLen; // * enhanced protection len & pword to set // [MarshalAs(UnmanagedType.LPStr, SizeConst = 128)] [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 128)] public string pword; // * should be passed in # of chars } ; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_PASSCODE_T { public uint passcodeType; public IntPtr passcodeHandle; } [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_KEYCHAIN_ID_T { public int len; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 512)] public string keychainID; }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SH_SECRET_ID_T { public int type; // The shared secret type i.e. SS_App or SS_CredSet public int len; // except that it excludes the header and is not escaped. [MarshalAs(UnmanagedType.ByValTStr , SizeConst = 512)] public string name; // The shared secret name. This is the same as the identifier }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SECRET_STORE_ID_T { public int version; // * max id len in bytes [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 512)] public string id; // * should be passed in # of chars }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SECRET_ID_T { public int len; // * max id len in bytes [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 512)] public string id; // * should be passed in # of chars }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)] public class SSCS_HINT_T { ulong hintLen; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 128)] string hint; //* should be passed in # of chars }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_EXT_T { public int extID; // defined to identify the extension public int version; // defined as the version of the specified extension public IntPtr ext; // points to the actual extension } ; /* [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SECRETSTORE_INF_T { uint numKeyChains; uint enumBufsize; }; */ [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SRCH_KEY_T { public uint srchKeyLen; [MarshalAs(UnmanagedType.LPStr, SizeConst = 128)] public string srchKey; //[NSSCS_MAX_SRCH_KEY_LEN]; //* should be passed in # of chars } ; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SECRET_ID_LIST_T { public uint enumHandle; public uint returnedIDs; public IntPtr secretIDList; //* an array of secretID structures }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SH_SECRET_ID_LIST_T { public uint enumHandle; public uint returnedIDs; public IntPtr secretIDList; //* an array of secretID structures }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_CONTEXT_T { public int version; public int flags; public SSCS_SECRET_ID_T ssid; public UInt64 ssHandle; }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_READEXT_T { public uint statFlags; //* OUT - return flags on the secret public uint crtStamp; //* OUT - secret creation time stamp public uint latStamp; //* OUT - last accessed time stamp (optional) public uint lmtStamp; //* OUT - last modified time stamp }; [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_SECRETSTORE_INFO_T { public UInt32 statFlags; public UInt32 secretCount; public UInt32 lockCount; public UInt32 enumBufLen; public UInt32 hidSecCount; public UInt32 clientVersion; public UInt32 serverVersion; public UInt32 serverCryptoStrength; public UInt32 clientCryptoStrength; public UInt32 unlockTStamp; public UInt32 admnDNLen; [MarshalAs(UnmanagedType.ByValArray, SizeConst = 516)] public string admnDN; //[NSSS_MAX_DN_LEN]; public UInt32 hintLen; [MarshalAs(UnmanagedType.ByValArray, SizeConst = 128)] public string hint; //[NSSS_MAX_MP_PWORD_HINT_LEN]]; }; /* [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_BASIC_CREDENTIAL { public uint unFlags; public uint unLen; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)] public string username; public uint pwordLen; [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 128)] public string password; } */ [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] public class SSCS_BASIC_CREDENTIAL_UTF8 { public uint unFlags; public uint unLen; [MarshalAs(UnmanagedType.ByValArray, SizeConst = 256)] public byte[] username; public uint pwordLen; [MarshalAs(UnmanagedType.ByValArray, SizeConst = 128)] public byte[] password; } // * The following functions will be exposed as exported API: // ************************************************************** // * These function calls will utilize the Support Functions for // * populating or extracting data from a Shared Secret. // ************************************************************** private const string NDK_LIBRARY = "micasa"; [DllImport(NDK_LIBRARY)] public static extern int miCASARemoveCredential ( [In] uint ssFlags, // IN [In] SSCS_SECRET_ID_T appSecretID, [In] SSCS_SECRET_ID_T sharedSecretID, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAGetCredential ( [In] uint ssFlags, // IN [In] SSCS_SECRET_ID_T appSecretID, [In] SSCS_SECRET_ID_T sharedSecretID, [In, Out] ref uint credentialType, // IN [In, Out] IntPtr pCredential, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASASetCredential ( [In] uint ssFlags, // IN [In] SSCS_SECRET_ID_T appSecretID, [In] SSCS_SECRET_ID_T sharedSecretID, int credentialType, // IN [In] IntPtr credential, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASASetMasterPasscode ( [In] uint ssFlags, [In] SSCS_PASSCODE_T passcode, [In] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAIsSecretPersistent ( [In] uint ssFlags, [In] SSCS_SECRET_ID_T secretID, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern IntPtr miCASAOpenSecretStoreCache ( [In, Out] SSCS_SECRET_STORE_ID_T ssid, ulong ssFlags, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASACloseSecretStoreCache ( [In] IntPtr context, [In] uint ssFlags, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY) ] public static extern int miCASAReadSecret ( [In] IntPtr context, [In] SSCS_KEYCHAIN_ID_T keyChainID, [In] uint ssFlags, [In] IntPtr secretHandle, [In] SSCS_SH_SECRET_ID_T sharedSecretID, [In] SSCS_PASSWORD_T epPassword, [In, Out] SSCS_READEXT_T readData, [In, Out] SSCS_EXT_T ext ); // TODO: check the order of these paramters [DllImport(NDK_LIBRARY)] public static extern int miCASARemoveSecret ( [In] IntPtr context, [In] SSCS_KEYCHAIN_ID_T keyChainID, [In] uint ssFlags, [In] SSCS_SH_SECRET_ID_T sharedSecretID, [In] SSCS_PASSWORD_T epPassword, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAWriteSecret ( [In] IntPtr context, [In] SSCS_KEYCHAIN_ID_T keyChainID, [In] uint ssFlags, [In] IntPtr secretHandle, [In] SSCS_SH_SECRET_ID_T sharedSecretID, [In] SSCS_PASSWORD_T epPassword, [In] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAGetStoreInformation ( [In] IntPtr context, [In] uint ssFlags, [In, Out] SSCS_SECRETSTORE_INFO_T ssInfo, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAEnumerateSecretIDs ( [In] IntPtr context, [In] SSCS_KEYCHAIN_ID_T keyChainID, [In] uint ssFlags, [In] SSCS_SRCH_KEY_T searchKey, [In, Out] SSCS_SH_SECRET_ID_LIST_T secretIDList, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAEnumerateKeyChainIDs ( [In] IntPtr context, [In] uint ssFlags, [In] SSCS_SRCH_KEY_T searchKey, [In, Out] SSCS_SECRET_ID_LIST_T kcIDList, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASARemoveSecretStore ( [In] IntPtr context, [In] uint ssFlags, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASASetMasterPassword ( [In] uint ssFlags, [In] SSCS_PASSWORD_T password, [In] SSCS_HINT_T hint, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAUnlockSecrets ( [In] IntPtr context, [In] uint ssFlags, [In] SSCS_PASSWORD_T password, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASALockStore ( [In] IntPtr context, [In] uint ssFlags, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAUnlockStore ( [In] IntPtr context, [In] uint ssFlags, [In] SSCS_PASSWORD_T password, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASARemoveKeyChain ( [In] IntPtr context, [In] uint ssFlags, [In] SSCS_KEYCHAIN_ID_T keyChainID, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASAAddKeyChain ( [In] IntPtr context, [In] uint ssFlags, [In] SSCS_KEYCHAIN_ID_T keyChainID, [In, Out] SSCS_EXT_T ext ); //************************************************************** //* Support Functions for processing (populating or extracting) //* data components from a Shared Secret //************************************************************** [DllImport(NDK_LIBRARY)] public static extern IntPtr miCASA_CreateSHSHandle(); [DllImport(NDK_LIBRARY)] public static extern int miCASA_DestroySHSHandle( [In] IntPtr secretHandle); [DllImport(NDK_LIBRARY, CharSet=CharSet.None) ] public static extern int miCASA_GetNextSHSEntry ( [In] int restart, //* in (set to 1 to begin from head of list) [In] IntPtr secretHandle, //* in [In, Out] ref uint keyLen, //* out IntPtr theKey, [In, Out] ref uint valLen, //* out IntPtr theValue ); [DllImport(NDK_LIBRARY, CharSet=CharSet.None)] public static extern int miCASA_AddSHSEntry ( [In] IntPtr secretHandle, //* in] [MarshalAs(UnmanagedType.LPStr)] string key, //* in /wchar [In] uint valueLenBytes, // in bytes [MarshalAs(UnmanagedType.LPStr)] string val //* in /uchar ); [DllImport(NDK_LIBRARY, CharSet=CharSet.None)] public static extern int miCASAWriteKey ( [In] IntPtr context, [In] uint ssFlags, [In] SSCS_KEYCHAIN_ID_T keyChainID, [In] SSCS_SH_SECRET_ID_T sharedSecretID, [MarshalAs(UnmanagedType.LPStr)] string key, //* in /wchar [In] uint keyLenBytes, // in bytes [MarshalAs(UnmanagedType.LPStr)] string val, //* in /uchar [In] uint valueLenBytes, // in bytes [In] SSCS_PASSWORD_T password, [In, Out] SSCS_EXT_T ext ); [DllImport(NDK_LIBRARY)] public static extern int miCASA_RemoveSHSEntry ( [In] IntPtr secretHandle, //* in [MarshalAs(UnmanagedType.LPStr)] string key, //* out /uchar uint valueLenBytes, // in bytes [MarshalAs(UnmanagedType.LPStr)] string val //* out /uchar ); // Methods start here internal IntPtr openSecretStore(string sSecretStoreName) { //check params if (sSecretStoreName == null || sSecretStoreName.Length==0) throw new miCasaException(miCasaException.NSSCS_E_INVALID_PARAM); SSCS_SECRET_STORE_ID_T SSid = new SSCS_SECRET_STORE_ID_T(); SSid.id = sSecretStoreName; SSid.version = 0; SSCS_EXT_T ext = new SSCS_EXT_T(); try { IntPtr hSC = miCASAOpenSecretStoreCache( SSid, 0, ext); return hSC; } catch (Exception) { return IntPtr.Zero; } } internal void closeSecretStore(IntPtr hSC) { SSCS_EXT_T ext = new SSCS_EXT_T(); miCASACloseSecretStoreCache(hSC, 0, ext); } internal Secret getSecret( IntPtr pHsc, string sKeyChainID, uint iFlags, string sSharedSecretID, int iSecretType, string sEPPassword) { if (pHsc == IntPtr.Zero || sKeyChainID == null || sSharedSecretID == null || sKeyChainID.Length == 0 || sSharedSecretID.Length == 0) throw new miCasaException(miCasaException.NSSCS_E_INVALID_PARAM); // setup structures SSCS_KEYCHAIN_ID_T keyChainID = new SSCS_KEYCHAIN_ID_T(); keyChainID.keychainID = sKeyChainID; SSCS_SH_SECRET_ID_T sharedSecretID = new SSCS_SH_SECRET_ID_T(); sharedSecretID.name = sSharedSecretID; SSCS_PASSWORD_T epPassword = new SSCS_PASSWORD_T(); SSCS_READEXT_T readData = new SSCS_READEXT_T(); SSCS_EXT_T ext =new SSCS_EXT_T(); // get SecretHandle IntPtr pSecretHandle = miCASA_CreateSHSHandle(); // setup keychainid keyChainID.len = sKeyChainID.Length + 1; // setup sharedSecretID sharedSecretID.len = sSharedSecretID.Length + 1; sharedSecretID.type = iSecretType; // TODO: type APP(1), CRED(2), or Binary(4) epPassword.pwordType = 1; // TODO: ep or master password based on flags if (sEPPassword != null) { epPassword.pword = sEPPassword; epPassword.pwordLen = (uint)sEPPassword.Length; } else epPassword.pwordLen = 0; int rcode = miCASAReadSecret( pHsc, keyChainID, iFlags, pSecretHandle, sharedSecretID, epPassword, readData, ext); // create new secret Secret temp = new Secret(pHsc, sKeyChainID, iFlags, pSecretHandle, sSharedSecretID, sharedSecretID.type, sEPPassword); temp.setTimeStamps(readData.crtStamp, readData.lmtStamp, readData.latStamp); // if read was sucessful, read key value pairs if (rcode == 0) loadKeyValuePairs(temp); // else // throw new Exception(); return temp; } internal void loadKeyValuePairs(Secret secret) { int rcode=0; int iStart = 1; IntPtr theKey = Marshal.AllocHGlobal(60416); IntPtr theValue = Marshal.AllocHGlobal(60416); String sKey; String sValue; while (true) { uint iKeyLen = 60416; uint iValueLen = 60416; sKey = ""; sValue = ""; rcode = miCASA_GetNextSHSEntry( iStart, secret.m_secretHandle, ref iKeyLen, theKey, //sKey, ref iValueLen, theValue // sValue ); if (rcode != 0) break; else { if (iKeyLen > 1) { //sKey = Marshal.PtrToStringAnsi(theKey, (int)iKeyLen - 1); // convert from UTF8 byte[] baKey = new byte[iKeyLen-1]; Marshal.Copy(theKey, baKey, 0, (int)iKeyLen-1); sKey = System.Text.Encoding.UTF8.GetString(baKey, 0, baKey.Length); } if (iValueLen > 1) { //sValue = Marshal.PtrToStringAnsi(theValue, (int)iValueLen -1); // convert from UTF8 byte[] baValue = new byte[iValueLen-1]; Marshal.Copy(theValue, baValue, 0, (int)iValueLen-1); sValue = System.Text.Encoding.UTF8.GetString(baValue, 0, baValue.Length); } if (sKey != null && sValue != null) secret.setKeyValuePair(sKey, sValue); iStart = 0; } } Marshal.FreeHGlobal(theKey); Marshal.FreeHGlobal(theValue); } internal static int removeKeyValue( IntPtr pSecretHandle, string sKey, string sValue, uint ctxFlags) { if ((sKey == null) || (sValue == null)) return 0; int rcode = miCASA_RemoveSHSEntry( pSecretHandle, sKey, (uint)(sValue.Length + 1) * 2, sValue); return rcode; } /* internal int setSecret( IntPtr pHsc, string sKeyChainID, uint iFlags, Secret secret, int iSecretType) { int rcode; if (iSecretType == Secret.SS_BINARY) { rcode = miCASA_AddSHSEntry( secret.m_secretHandle, "SS_Binary", (uint)secret.getBinaryValue().Length, secret.getBinaryValue().ToString()); } else { NameValueCollection nvc = secret.getKeyValueCollection(); if (nvc != null) { for (int i=0; i 0) { // first write out all key/value pairs rcode = miCASA_AddSHSEntry( secret.m_secretHandle, sKey, //sKey, (uint)(sValue.Length+1) * 2, sValue); //sValue); } } } } // now call miCASAWriteSecret SSCS_KEYCHAIN_ID_T keyChainID = new SSCS_KEYCHAIN_ID_T(); keyChainID.keychainID = sKeyChainID; SSCS_SH_SECRET_ID_T sharedSecretID = new SSCS_SH_SECRET_ID_T(); SSCS_PASSWORD_T epPassword = new SSCS_PASSWORD_T(); SSCS_EXT_T ext =new SSCS_EXT_T(); ext.extID = 0; ext.version = 0; // setup keychainid keyChainID.len = sKeyChainID.Length + 1; String tempStr = secret.getID(); sharedSecretID.name = tempStr; sharedSecretID.len = tempStr.Length + 1; sharedSecretID.type = iSecretType; // TODO: type APP(1), CRED(2), or Binary(4) if (secret.getEnhancedProtectionPassword() != null) { epPassword.pword = secret.getEnhancedProtectionPassword(); epPassword.pwordLen = (uint)secret.getEnhancedProtectionPassword().Length + 1; epPassword.pwordType = 0; } else { epPassword = null; } ext.ext = Marshal.AllocHGlobal(10); try { rcode = miCASAWriteSecret( pHsc, keyChainID, iFlags, secret.m_secretHandle, sharedSecretID, epPassword, ext); } catch (Exception) { //Console.WriteLine(e.ToString()); rcode = -803; } Marshal.FreeHGlobal(ext.ext); return rcode; } */ internal bool KeyInNewList(NameValueCollection nvc, string key) { //Console.WriteLine("Checking for " + key ); if (nvc != null) { for (int i = 0; i < nvc.Count; i++) { string sKey = nvc.GetKey(i); if( key == sKey ) return true; } } //Console.WriteLine("key = " + key + " is not present in nvc"); return false; } internal int setSecret( IntPtr pHsc, string sKeyChainID, uint iFlags, Secret secret, int iSecretType) { int rcode = 0; if (sKeyChainID == null || sKeyChainID.Length == 0) throw new miCasaException(miCasaException.NSSCS_E_INVALID_PARAM); // now call miCASAWriteSecret SSCS_KEYCHAIN_ID_T keyChainID = new SSCS_KEYCHAIN_ID_T(); keyChainID.keychainID = sKeyChainID; SSCS_SH_SECRET_ID_T sharedSecretID = new SSCS_SH_SECRET_ID_T(); SSCS_PASSWORD_T epPassword = new SSCS_PASSWORD_T(); SSCS_EXT_T ext =new SSCS_EXT_T(); ext.extID = 0; ext.version = 0; // setup keychainid keyChainID.len = sKeyChainID.Length + 1; String tempStr = secret.getID(); sharedSecretID.name = tempStr; sharedSecretID.len = (tempStr.Length + 1) * 2; sharedSecretID.type = iSecretType; // TODO: type APP(1), CRED(2), or Binary(4) if (secret.getEnhancedProtectionPassword() != null) { epPassword.pword = secret.getEnhancedProtectionPassword(); epPassword.pwordLen = (uint)secret.getEnhancedProtectionPassword().Length + 1; epPassword.pwordType = 0; } else { epPassword = null; } ext.ext = Marshal.AllocHGlobal(10); if (iSecretType == Secret.SS_BINARY) { rcode = miCASA_AddSHSEntry( secret.m_secretHandle, "SS_Binary", (uint)secret.getBinaryValue().Length, secret.getBinaryValue().ToString()); } else { NameValueCollection nvc = secret.getKeyValueCollection(); if (nvc != null) { for (int i=0; i 0) { try { object o = MiCasaRequestReply.Send(MiCasaRequestReply.VERB_WRITE_KEY, sKeyChainID, secret.getID(), sKey, EscapeReservedChars(sValue)); /* rcode = miCASAWriteKey( pHsc, iFlags, keyChainID, sharedSecretID, sKey, (uint) (sKey.Length+1) * 2, sValue, (uint) (sValue.Length+1) * 2, epPassword, ext); */ } catch (Exception e) { rcode = -803; } } } if( 0 == rcode ) { try { ArrayList keyList = (ArrayList)MiCasaRequestReply.Send(MiCasaRequestReply.VERB_GET_KEY_LIST,sKeyChainID,secret.getID(),null,null); if( null != keyList ) { IEnumerator etor = keyList.GetEnumerator(); while( etor.MoveNext() ) { string key = (string)etor.Current; if(KeyInNewList(nvc,key) == false) { MiCasaRequestReply.Send(MiCasaRequestReply.VERB_REMOVE_KEY,sKeyChainID,secret.getID(),key, null ); } } } } catch(Exception e) { rcode = -803; Console.WriteLine(e.ToString()); } } } } Marshal.FreeHGlobal(ext.ext); return rcode; } internal int RemoveSecret( IntPtr context, uint ssFlags, string sKeyChainID, string sEPPassword, string sSecretID, int iSecretType) { if (context == IntPtr.Zero || sKeyChainID == null || sSecretID == null || sKeyChainID.Length==0 || sSecretID.Length==0) return miCasaException.NSSCS_E_INVALID_PARAM; int rcode = 0; SSCS_KEYCHAIN_ID_T keyChainID = new SSCS_KEYCHAIN_ID_T(); keyChainID.keychainID = sKeyChainID; keyChainID.len = sKeyChainID.Length + 1; SSCS_PASSWORD_T epPassword = new SSCS_PASSWORD_T(); epPassword.pword = sEPPassword; epPassword.pwordLen = (uint)sEPPassword.Length + 1; epPassword.pwordType = 0; // todo set type SSCS_SH_SECRET_ID_T secretID = new SSCS_SH_SECRET_ID_T(); secretID.name = sSecretID; secretID.len = sSecretID.Length + 1; secretID.type = iSecretType; SSCS_EXT_T ext = new SSCS_EXT_T(); // make the call rcode = miCASARemoveSecret( context, keyChainID, ssFlags, secretID, epPassword, ext); return rcode; } internal StringCollection EnumerateSecretIDs( IntPtr context, uint ssFlags, string sKeyChainID, string sSearchKey) { if (context == IntPtr.Zero || sKeyChainID==null || sSearchKey==null || sKeyChainID.Length==0) throw new miCasaException(miCasaException.NSSCS_E_INVALID_PARAM); // setup structures SSCS_KEYCHAIN_ID_T keyChainID = new SSCS_KEYCHAIN_ID_T(); keyChainID.keychainID = sKeyChainID; SSCS_SRCH_KEY_T searchKey = new SSCS_SRCH_KEY_T(); SSCS_SH_SECRET_ID_LIST_T idList = new SSCS_SH_SECRET_ID_LIST_T(); SSCS_EXT_T ext = new SSCS_EXT_T(); int numIDS = 100; StringCollection sc = null; // setup keychainid keyChainID.len = sKeyChainID.Length + 1; searchKey.srchKey = sSearchKey; searchKey.srchKeyLen = (uint)sSearchKey.Length; idList.returnedIDs = (uint)numIDS; SSCS_SH_SECRET_ID_T secretId = new SSCS_SH_SECRET_ID_T(); // secretId.name = new char[512]; StringBuilder buffer3 = new StringBuilder( "content", 512 ); buffer3.Append( (char)0 ); buffer3.Append( '*', buffer3.Capacity - 8 ); String tempStr = buffer3.ToString(); idList.secretIDList = Marshal.AllocHGlobal(numIDS * Marshal.SizeOf(secretId)); // make the call int rcode = miCASAEnumerateSecretIDs( context, keyChainID, ssFlags, searchKey, idList, ext); if (idList.returnedIDs > 0) { sc = new StringCollection(); if (idList.returnedIDs != 100) { // enumerate returned list for (int i=0; i 0) { Decoder utfDec = System.Text.Encoding.UTF8.GetDecoder(); int charCount = utfDec.GetCharCount(utf8Bytes, 0, numBytes); char[] chars = new char[charCount]; int len = utfDec.GetChars(utf8Bytes, 0, numBytes, chars, 0); string text = new string(chars); text = text.Trim(); return text; } else return ""; } private static uint GetUTF8ByteCount(string str) { uint byteCount = (uint)System.Text.Encoding.UTF8.GetEncoder().GetByteCount(str.ToCharArray(), 0, str.Length, true); return byteCount; } private static byte[] GetUTF8FromString(string str, int arrayLength) { // NOTE: Must return a padded array of arrayLength Encoder utfEnc = System.Text.Encoding.UTF8.GetEncoder(); byte[] utf8Bytes = new byte[arrayLength]; int len = utfEnc.GetBytes(str.ToCharArray(), 0, str.Length, utf8Bytes, 0, true); return utf8Bytes; } internal int RemoveKey( string sKeyChainID, string secretID, string keyID) { if (sKeyChainID==null || secretID==null || keyID==null || sKeyChainID.Length==0 || secretID.Length==0 || keyID.Length==0) throw new miCasaException(miCasaException.NSSCS_E_INVALID_PARAM); int rcode = 0; if (keyID.Length > 0) { try { object o = MiCasaRequestReply.Send( MiCasaRequestReply.VERB_REMOVE_KEY, sKeyChainID, secretID, keyID, null); } catch (Exception e) { rcode = -803; } } return rcode; } internal ArrayList GetKeyList( string sKeyChainID, string secretID) { if (sKeyChainID==null || secretID==null || sKeyChainID.Length==0 || secretID.Length==0) throw new miCasaException(miCasaException.NSSCS_E_INVALID_PARAM); ArrayList keyList = null; try { keyList = (ArrayList) MiCasaRequestReply.Send( MiCasaRequestReply.VERB_GET_KEY_LIST, sKeyChainID, secretID,null,null); return keyList; #if false if( null != keyList ) { IEnumerator etor = keyList.GetEnumerator(); while( etor.MoveNext() ) { Console.WriteLine("Key = " + etor.Current); } } #endif } catch(Exception e) { Console.WriteLine(e.ToString()); keyList = null; } return keyList; } internal string ReadKey( string sKeyChainID, string secretID, string keyID) { if (sKeyChainID==null || secretID==null || keyID==null || sKeyChainID.Length==0 || secretID.Length==0 || keyID.Length==0) throw new miCasaException(miCasaException.NSSCS_E_INVALID_PARAM); int rcode = 0; string value = null; if (keyID.Length > 0) { try { value = (String)MiCasaRequestReply.Send( MiCasaRequestReply.VERB_REMOVE_KEY, sKeyChainID, secretID, keyID, null); } catch (Exception e) { // rcode = -803; Console.WriteLine(e.ToString()); } } return value; } private string EscapeReservedChars(string origString) { if (origString==null) return origString; StringBuilder sb = new StringBuilder(); for (int i=0; i