private IChapServer CreateTestServer() { var responseService = Substitute.For <ISignatureService>(); var signatureResult = new SignatureResult { SignatureHash = "RESPONSE" }; responseService.CreateSignature(Arg.Any <string>(), Arg.Any <string>(), Arg.Any <IEnumerable <SignatureFactor> >()).Returns(signatureResult); return(new ChapServer(responseService, new InMemoryChallengeStore(null))); }
public void WhenExecuteSyncRequestReturnsFalseAndThereAreLoggedErrors_ReturnsFalse() { // Arrange var urlProvider = Substitute.For <IUrlProvider>(); var syncUrl = "http://test.sc?Sync"; var challengeUrl = "http://test.sc?Challenge"; urlProvider.GetUrl(Verb.Sync).Returns(syncUrl); urlProvider.GetUrl(Verb.Challenge).Returns(challengeUrl); var challengeRequest = Substitute.For <IRequest>(); var challenge = "challenge"; challengeRequest.Execute().Returns(challenge); var streamProcessor = Substitute.For <IResponseStreamProcessor <bool> >(); var syncRequest = Substitute.For <IRequest>(); syncRequest.Execute(streamProcessor).Returns(false); var signatureService = Substitute.For <ISignatureService>(); var signatureResult = new SignatureResult() { SignatureHash = "signature hash" }; signatureService.CreateSignature(challenge, syncUrl, null).Returns(signatureResult); var requestFactory = Substitute.For <IRequestFactory>(); requestFactory.Create(challengeUrl, 360000, null).Returns(challengeRequest); requestFactory.Create(syncUrl, 10800000, Arg.Is <Dictionary <string, string> >(x => x.Keys.Count == 2 && x.ContainsKey("X-MC-MAC") && x.ContainsKey("X-MC-Nonce") && x["X-MC-MAC"] == signatureResult.SignatureHash && x["X-MC-Nonce"] == challenge)) .Returns(syncRequest); var log = Substitute.For <TaskLoggingHelper>(Substitute.For <ITask>()); log.LogError("error"); var sut = new UnicornManager("http://test.sc", "secret", log, urlProvider, requestFactory, signatureService, streamProcessor); // Act var result = sut.Sync(); // Assert result.Should().Be(false); }
public void WhenExecuteSync_RequestToSyncUrlIsCreatedWithCorrectHeaders() { // Arrange var urlProvider = Substitute.For <IUrlProvider>(); var syncUrl = "http://test.sc?Sync"; var challengeUrl = "http://test.sc?Challenge"; urlProvider.GetUrl(Verb.Sync).Returns(syncUrl); urlProvider.GetUrl(Verb.Challenge).Returns(challengeUrl); var challengeRequest = Substitute.For <IRequest>(); var challenge = "challenge"; challengeRequest.Execute().Returns(challenge); var streamProcessor = Substitute.For <IResponseStreamProcessor <bool> >(); var syncRequest = Substitute.For <IRequest>(); syncRequest.Execute(streamProcessor).Returns(true); var signatureService = Substitute.For <ISignatureService>(); var signatureResult = new SignatureResult() { SignatureHash = "signature hash" }; signatureService.CreateSignature(challenge, syncUrl, null).Returns(signatureResult); var requestFactory = Substitute.For <IRequestFactory>(); requestFactory.Create(challengeUrl, 360000, null).Returns(challengeRequest); requestFactory.Create(syncUrl, 10800000, Arg.Is <Dictionary <string, string> >(x => x.Keys.Count == 2 && x.ContainsKey("X-MC-MAC") && x.ContainsKey("X-MC-Nonce") && x["X-MC-MAC"] == signatureResult.SignatureHash && x["X-MC-Nonce"] == challenge)) .Returns(syncRequest); var sut = new UnicornManager("http://test.sc", "secret", Substitute.For <TaskLoggingHelper>(Substitute.For <ITask>()), urlProvider, requestFactory, signatureService, streamProcessor); // Act sut.Sync(); // Assert requestFactory.Received(1).Create(syncUrl, 10800000, Arg.Is <Dictionary <string, string> >(x => x.Keys.Count == 2 && x.ContainsKey("X-MC-MAC") && x.ContainsKey("X-MC-Nonce") && x["X-MC-MAC"] == signatureResult.SignatureHash && x["X-MC-Nonce"] == challenge)); syncRequest.Received(1).Execute(streamProcessor); }
protected override bool IsAuthorized(HttpActionContext actionContext) { NameValueCollection _collection; string _query; string _body; _query = actionContext.Request.RequestUri.Query; _collection = SignatureHelper.ParseQueryString(_query); _body = actionContext.Request.Content.ReadAsStringAsync().Result; this._signatureResult = _signatureService.Validation(_collection["a"] , _collection["s"] , _collection["t"] , _body); return(this._signatureResult.IsValid); }
protected override bool IsAuthorized(HttpActionContext actionContext) { NameValueCollection _collection; string _query; string _body; _query = actionContext.Request.RequestUri.Query; _collection = SignatureHelper.ParseQueryString(_query); _body = actionContext.Request.Content.ReadAsStringAsync().Result; this._signatureResult = _signatureService.Validation(_collection["a"] , _collection["s"] , _collection["t"] , _body); return (this._signatureResult.IsValid); }
public void WhenExecuteSync_DoRequestForChallengeWithChallengeUrl() { // Arrange var urlProvider = Substitute.For <IUrlProvider>(); var syncUrl = "http://test.sc?Sync"; var challengeUrl = "http://test.sc?Challenge"; urlProvider.GetUrl(Verb.Sync).Returns(syncUrl); urlProvider.GetUrl(Verb.Challenge).Returns(challengeUrl); var challengeRequest = Substitute.For <IRequest>(); var challenge = "challenge"; challengeRequest.Execute().Returns(challenge); var streamProcessor = Substitute.For <IResponseStreamProcessor <bool> >(); var syncRequest = Substitute.For <IRequest>(); syncRequest.Execute(streamProcessor).Returns(true); var requestFactory = Substitute.For <IRequestFactory>(); requestFactory.Create(challengeUrl, Arg.Any <int>(), null).Returns(challengeRequest); requestFactory.Create(syncUrl, Arg.Any <int>(), null).Returns(syncRequest); var signatureService = Substitute.For <ISignatureService>(); var signatureResult = new SignatureResult(); signatureService.CreateSignature(challenge, syncUrl, null).Returns(signatureResult); var sut = new UnicornManager("http://test.sc", "secret", null, urlProvider, requestFactory, signatureService, streamProcessor); // Act sut.Sync(); // Assert urlProvider.Received(1).GetUrl(Verb.Sync); urlProvider.Received(1).GetUrl(Verb.Challenge); requestFactory.Received(1).Create(challengeUrl, 360000, null); challengeRequest.Received(1).Execute(); }
public void WhenExecuteSync_SetRequiredSecurityProtocolType() { // Arrange var urlProvider = Substitute.For <IUrlProvider>(); var syncUrl = "http://test.sc?Sync"; var challengeUrl = "http://test.sc?Challenge"; urlProvider.GetUrl(Verb.Sync).Returns(syncUrl); urlProvider.GetUrl(Verb.Challenge).Returns(challengeUrl); var challengeRequest = Substitute.For <IRequest>(); var challenge = "challenge"; challengeRequest.Execute().Returns(challenge); var streamProcessor = Substitute.For <IResponseStreamProcessor <bool> >(); var syncRequest = Substitute.For <IRequest>(); syncRequest.Execute(streamProcessor).Returns(true); var requestFactory = Substitute.For <IRequestFactory>(); requestFactory.Create(challengeUrl, Arg.Any <int>(), null).Returns(challengeRequest); requestFactory.Create(syncUrl, Arg.Any <int>(), null).Returns(syncRequest); var signatureService = Substitute.For <ISignatureService>(); var signatureResult = new SignatureResult(); signatureService.CreateSignature(challenge, syncUrl, null).Returns(signatureResult); var sut = new UnicornManager("http://test.sc", "secret", null, urlProvider, requestFactory, signatureService, streamProcessor); ServicePointManager.SecurityProtocol = SecurityProtocolType.SystemDefault; // Act sut.Sync(); // Assert ServicePointManager.SecurityProtocol.Should().Be(SecurityProtocolType.Tls12); }
/// <summary> /// Scans for the specified signature in the specified memory range. /// </summary> /// <param name="SignatureName">The signature name.</param> /// <param name="From">The address used to start the scan.</param> /// <param name="To">The address used to end the scan.</param> /// <param name="Result">The scan result.</param> /// <param name="UICallback">The UI callback.</param> public bool TrySearchFor(string SignatureName, ulong From, ulong To, out SignatureResult Result, Action <ScanInfoEvent> UICallback = null) { if (this.IsDisposed) { throw new ObjectDisposedException(nameof(BekoEngine), "The engine is disposed"); } if (string.IsNullOrEmpty(SignatureName)) { throw new ArgumentNullException(nameof(SignatureName)); } var Signature = this.Signatures.Get(SignatureName); if (Signature == null) { throw new ArgumentException("SignatureName is not in the signatures dictionnary"); } return(TrySearchFor(Signature, From, To, out Result, UICallback)); }
/// <summary> /// Scans for the specified signature in the specified memory range. /// </summary> /// <param name="Signature">The signature.</param> /// <param name="From">The address used to start the scan.</param> /// <param name="To">The address used to end the scan.</param> /// <param name="Result">The scan result address.</param> /// <param name="UICallback">The UI callback.</param> public bool TrySearchFor(Signature Signature, ulong From, ulong To, out SignatureResult Result, Action <ScanInfoEvent> UICallback = null) { if (this.IsDisposed) { throw new ObjectDisposedException(nameof(BekoEngine), "The engine is disposed"); } if (Signature == null) { throw new ArgumentException("SignatureName is not in the signatures dictionnary"); } Result = this.SearchFor(Signature, From, To, UICallback); if (Result != null) { return(Result.IsFound); } return(false); }
public void RejectedDueToInvalidSignature(string challenge, string signatureProvided, SignatureResult signatureExpected) { Log.Warn($"[{_logPrefix}] CHAP authentication attempt rejected due to mismatching HMAC code.", this); Log.Warn($"[{_logPrefix}] MAC (should match client): {signatureExpected.SignatureSource}", this); Log.Warn($"[{_logPrefix}] HMAC expected: {signatureExpected.SignatureHash}", this); Log.Warn($"[{_logPrefix}] HMAC provided by client: {signatureProvided}", this); }
internal void Complete(SignatureResult result) { this.tcs.TrySetResult(result); }
/// <summary> /// 驗證簽章結果 /// </summary> /// <param name="apikey">金鑰</param> /// <param name="signature">簽章</param> /// <param name="timestamp">時間戳記</param> /// <param name="requestBody">請求內容</param> /// <param name="errorSecond">時間戳記的誤差允許秒數</param> /// <returns>驗證結果</returns> public SignatureResult Validation(string apikey , string signature , string timestamp , string requestBody , int errorSecond = 300) { string _serverSaltKey = string.Empty; string _serverSignature = string.Empty; string _serverRequestBody = string.Empty; string _serverHash = string.Empty; string _serverHashBody = string.Empty; long _serverTimestamp = 0; long _clientTimestamp = 0; SignatureResult _message; _message = new SignatureResult(); _message.IsValid = (false); //如果 apikey , signature , timestamp 不存在回傳錯誤訊息 if (string.IsNullOrWhiteSpace(apikey) == true && string.IsNullOrWhiteSpace(signature) == true && string.IsNullOrWhiteSpace(timestamp) == true) { _message.Message = "apikey , signature , timestamp is required"; return _message; } if (string.IsNullOrWhiteSpace(apikey) == true) { _message.Message = "apikey is required"; return _message; } if (string.IsNullOrWhiteSpace(signature) == true) { _message.Message = "signature is required"; return _message; } if (string.IsNullOrWhiteSpace(timestamp) == true) { _message.Message = "timestamp is required"; return _message; } if (long.TryParse(timestamp, out _clientTimestamp) == false) { _message.Message = "timestamp is not valid integer"; return _message; } _serverTimestamp = SignatureHelper.GetUnixTimeSeconds(); //驗證時間戳記是否在誤差數值範圍 if ((_serverTimestamp - errorSecond) <= _clientTimestamp && _clientTimestamp <= (_serverTimestamp + errorSecond)) { } else { _message.Message = "timestamp not valid"; _message.t = _serverTimestamp; return _message; } //取得簽章加鹽字串 _serverSaltKey = this.GetSaltKey(apikey); if (string.IsNullOrWhiteSpace(_serverSaltKey) == true) { _message.Message = "apikey not valid"; return _message; } //取得簽章 _serverRequestBody = requestBody; _serverHashBody = string.Format("{0}{1}{2}" , _serverRequestBody , _clientTimestamp , _serverSaltKey); _serverHash = SignatureHelper.MD5ToHex(_serverHashBody); //比對簽章結果 if (_serverHash == signature) { //結果正確 } else { //結果不正確,並提供伺服器端用來驗證的內容 _message.Message = "signature not valid"; _message.RequestBody = requestBody; _message.s = _serverHash; _message.t = _clientTimestamp; _message.a = apikey; return _message; } _message.IsValid = (true); return _message; }
/// <summary> /// Scans for the specified signature in the specified memory range. /// </summary> /// <param name="Signature">The signature.</param> /// <param name="From">The address used to start the scan.</param> /// <param name="To">The address used to end the scan.</param> /// <param name="UICallback">The UI callback.</param> public SignatureResult SearchFor(Signature Signature, ulong From, ulong To, Action <ScanInfoEvent> UICallback = null) { if (this.IsDisposed) { throw new ObjectDisposedException(nameof(BekoEngine), "The engine is disposed"); } if (Signature == null) { throw new ArgumentNullException(nameof(Signature)); } if (To < From) { throw new ArgumentException("The address to start from is superior to the end address"); } var Size = (long)To - (long)From; if (Size <= 0) { throw new ArgumentException("The address range is inferior or equal to zero", nameof(Size)); } if (Size < Signature.Length) { throw new ArgumentException("The memory range to search in is inferior than the size of the signature"); } const uint BufferSize = 0x1000; var Result = new SignatureResult(Signature); for (ulong I = 0; I < (ulong)Size;) { var Address = From + I; var EndAddr = From + I + BufferSize; var Buffer = (byte[])null; try { if (Size < BufferSize) { Buffer = this.BekoEngine.MemoryHandler.Read(Address, (uint)Size); } else { if (EndAddr > To) { Buffer = this.BekoEngine.MemoryHandler.Read(Address, (uint)(BufferSize - (EndAddr - To))); } else { Buffer = this.BekoEngine.MemoryHandler.Read(Address, BufferSize); } } } catch (Exception Exception) { // .. } finally { if (Size < BufferSize) { I += (ulong)Size; } else { if (EndAddr > To) { I += (BufferSize - (EndAddr - To)); } else { I += (BufferSize); } } } if (Buffer != null) { if (TrySearchInBuffer(Signature, Buffer, out ulong Offset)) { Result.SetAddress(Address + Offset); Result.IsFound = true; Log.Warning(typeof(ScannerEngine), " - Found the searched signature at 0x" + Result.Address.ToString("X").PadLeft(16, '0') + "."); break; } } else { Result.IsErrored = true; } if (UICallback != null) { try { UICallback.Invoke(new ScanInfoEvent((int)I / (int)BufferSize, (int)Size / (int)BufferSize)); } catch (Exception) { // .. } } } return(Result); }
static void Main() { Context ctx = new Context(); if (ctx.Protocol != Protocol.OpenPGP) { ctx.SetEngineInfo(Protocol.OpenPGP, null, null); } Console.WriteLine("Search Alice's PGP key in the default keyring.."); const string SEARCHSTR = "*****@*****.**"; IKeyStore keyring = ctx.KeyStore; // retrieve all keys that have Alice's email address Key[] keys = keyring.GetKeyList(SEARCHSTR, false); if (keys == null || keys.Length == 0) { Console.WriteLine("Cannot find Alice's PGP key {0} in your keyring.", SEARCHSTR); Console.WriteLine("You may want to create the PGP key by using the appropriate\n" + "sample in the Samples/ directory."); return; } // print a list of all returned keys foreach (Key key in keys) { if (key.Uid != null && key.Fingerprint != null) { Console.WriteLine("Found key {0} with fingerprint {1}", key.Uid.Name, key.Fingerprint); } } // we are going to use the first key in the list PgpKey alice = (PgpKey)keys[0]; if (alice.Uid == null || alice.Fingerprint == null) { throw new InvalidKeyException(); } // Create a sample string StringBuilder randomtext = new StringBuilder(); for (int i = 0; i < 80 * 6; i++) { randomtext.Append((char)(34 + i % 221)); } string origintxt = new string('+', 508) + " Die Gedanken sind frei " + new string('+', 508) + randomtext; Console.WriteLine("Text to be signed:\n\n{0}", origintxt); // we want our string UTF8 encoded. UTF8Encoding utf8 = new UTF8Encoding(); // Prepare a file for later usage File.WriteAllText("original.txt", origintxt, utf8); /////// SIGN DATA (detached signature) /////// Console.Write("Write a detached signature to file: original.txt.sig.. "); GpgmeData origin = new GpgmeFileData("original.txt", FileMode.Open, FileAccess.Read); GpgmeData detachsig = new GpgmeFileData("original.txt.sig", FileMode.Create, FileAccess.Write); // Set Alice as signer ctx.Signers.Clear(); ctx.Signers.Add(alice); // we want or PGP encrypted/signed data RADIX/BASE64 encoded. ctx.Armor = true; /* Set the password callback - needed if the user doesn't run * gpg-agent or any other password / pin-entry software. */ ctx.SetPassphraseFunction(MyPassphraseCallback); // create a detached signature SignatureResult sigrst = ctx.Sign( origin, // plain text (source buffer) detachsig, // signature (destination buffer) SignatureMode.Detach); Console.WriteLine("done."); // print out invalid signature keys if (sigrst.InvalidSigners != null) { foreach (InvalidKey key in sigrst.InvalidSigners) { Console.WriteLine("Invalid key: {0} ({1})", key.Fingerprint, key.Reason); } } // print out signature information if (sigrst.Signatures != null) { foreach (NewSignature newsig in sigrst.Signatures) { Console.WriteLine("New signature: " + "\n\tFingerprint: {0}" + "\n\tHash algorithm: {1}" + "\n\tKey algorithm: {2}" + "\n\tTimestamp: {3}" + "\n\tType: {4}", newsig.Fingerprint, Gpgme.GetHashAlgoName(newsig.HashAlgorithm), Gpgme.GetPubkeyAlgoName(newsig.PubkeyAlgorithm), newsig.Timestamp, newsig.Type); } } origin.Close(); detachsig.Close(); /////// VERIFY DATA (detached signature) /////// Console.Write("Verify a detached signature from file: original.txt.sig.. "); origin = new GpgmeFileData("original.txt", FileMode.Open, FileAccess.Read); detachsig = new GpgmeFileData("original.txt.sig", FileMode.Open, FileAccess.Read); VerificationResult verrst = ctx.Verify( detachsig, // detached signature origin, // original data null); // should be NULL if a detached signature has been provided Console.WriteLine("done."); Console.WriteLine("Filename: {0}", verrst.FileName); // print out signature information if (verrst.Signature != null) { foreach (Signature sig in verrst.Signature) { Console.WriteLine("Verification result (signature): " + "\n\tFingerprint: {0}" + "\n\tHash algorithm: {1}" + "\n\tKey algorithm: {2}" + "\n\tTimestamp: {3}" + "\n\tSummary: {4}" + "\n\tValidity: {5}", sig.Fingerprint, Gpgme.GetHashAlgoName(sig.HashAlgorithm), Gpgme.GetPubkeyAlgoName(sig.PubkeyAlgorithm), sig.Timestamp, sig.Summary, sig.Validity); } } }
/// <summary> /// 驗證簽章結果 /// </summary> /// <param name="apikey">金鑰</param> /// <param name="signature">簽章</param> /// <param name="timestamp">時間戳記</param> /// <param name="requestBody">請求內容</param> /// <param name="errorSecond">時間戳記的誤差允許秒數</param> /// <returns>驗證結果</returns> public SignatureResult Validation(string apikey , string signature , string timestamp , string requestBody , int errorSecond = 300) { string _serverSaltKey = string.Empty; string _serverSignature = string.Empty; string _serverRequestBody = string.Empty; string _serverHash = string.Empty; string _serverHashBody = string.Empty; long _serverTimestamp = 0; long _clientTimestamp = 0; SignatureResult _message; _message = new SignatureResult(); _message.IsValid = (false); //如果 apikey , signature , timestamp 不存在回傳錯誤訊息 if (string.IsNullOrWhiteSpace(apikey) == true && string.IsNullOrWhiteSpace(signature) == true && string.IsNullOrWhiteSpace(timestamp) == true) { _message.Message = "apikey , signature , timestamp is required"; return(_message); } if (string.IsNullOrWhiteSpace(apikey) == true) { _message.Message = "apikey is required"; return(_message); } if (string.IsNullOrWhiteSpace(signature) == true) { _message.Message = "signature is required"; return(_message); } if (string.IsNullOrWhiteSpace(timestamp) == true) { _message.Message = "timestamp is required"; return(_message); } if (long.TryParse(timestamp, out _clientTimestamp) == false) { _message.Message = "timestamp is not valid integer"; return(_message); } _serverTimestamp = SignatureHelper.GetUnixTimeSeconds(); //驗證時間戳記是否在誤差數值範圍 if ((_serverTimestamp - errorSecond) <= _clientTimestamp && _clientTimestamp <= (_serverTimestamp + errorSecond)) { } else { _message.Message = "timestamp not valid"; _message.t = _serverTimestamp; return(_message); } //取得簽章加鹽字串 _serverSaltKey = this.GetSaltKey(apikey); if (string.IsNullOrWhiteSpace(_serverSaltKey) == true) { _message.Message = "apikey not valid"; return(_message); } //取得簽章 _serverRequestBody = requestBody; _serverHashBody = string.Format("{0}{1}{2}" , _serverRequestBody , _clientTimestamp , _serverSaltKey); _serverHash = SignatureHelper.MD5ToHex(_serverHashBody); //比對簽章結果 if (_serverHash == signature) { //結果正確 } else { //結果不正確,並提供伺服器端用來驗證的內容 _message.Message = "signature not valid"; _message.RequestBody = requestBody; _message.s = _serverHash; _message.t = _clientTimestamp; _message.a = apikey; return(_message); } _message.IsValid = (true); return(_message); }
private IChapServer CreateTestServer() { var responseService = Substitute.For<ISignatureService>(); var signatureResult = new SignatureResult { SignatureHash = "RESPONSE" }; responseService.CreateSignature(Arg.Any<string>(), Arg.Any<string>(), Arg.Any<IEnumerable<SignatureFactor>>()).Returns(signatureResult); return new ChapServer(responseService, new InMemoryChallengeStore(null)); }