From d9af24d372eb49bcfcf0325946692c7b1125ef39 Mon Sep 17 00:00:00 2001
From: Klaus Fischer <klaus.fischer@eloware.com>
Date: Tue, 1 Nov 2022 11:29:13 +0100
Subject: [PATCH] Implemented 4.2

---
 FitConnect/SecurityEventException.cs          | 27 +++++++++
 FitConnect/Services/Models/v1/Api/Problems.cs |  5 +-
 FitConnect/Subscriber.cs                      | 56 +++++++++----------
 3 files changed, 56 insertions(+), 32 deletions(-)
 create mode 100644 FitConnect/SecurityEventException.cs

diff --git a/FitConnect/SecurityEventException.cs b/FitConnect/SecurityEventException.cs
new file mode 100644
index 00000000..dc97bd24
--- /dev/null
+++ b/FitConnect/SecurityEventException.cs
@@ -0,0 +1,27 @@
+using FitConnect.Models.v1.Api;
+
+namespace FitConnect;
+
+public class SecurityEventException : Exception {
+    public string Title { get; }
+    public string Detail { get; }
+
+    public SecurityEventException(Problems problem, Exception? innerException = null) : base(
+        $"{problem.title}: {problem.detail}", innerException) {
+        Title = problem.title;
+        Detail = problem.detail;
+    }
+
+    public SecurityEventException(Problems[] problem, Exception? innerException = null) : base(
+        $"{problem[0].title}: {problem[0].detail}", innerException) {
+        Title = problem.Select(p => p.title).Aggregate((a, b) => a + "\r\n" + b);
+        Detail = problem.Select(p => p.detail).Aggregate((a, b) => a + "\r\n" + b);
+    }
+
+    public SecurityEventException(string title, string detail, Exception? innerException = null) :
+        base(
+            $"{title}: {detail}", innerException) {
+        Title = title;
+        Detail = detail;
+    }
+}
diff --git a/FitConnect/Services/Models/v1/Api/Problems.cs b/FitConnect/Services/Models/v1/Api/Problems.cs
index 52cd3f36..68ecf380 100644
--- a/FitConnect/Services/Models/v1/Api/Problems.cs
+++ b/FitConnect/Services/Models/v1/Api/Problems.cs
@@ -12,11 +12,13 @@ public class Problems {
     public const string TitleAuthenticationTagMissing = "Fehlende Authentication-Tags";
     public const string TitleAuthenticationTagInvalid = "Authentication-Tag ungültig";
     public const string DetailAuthenticationTagMissing = "Das Event 'submit-submission' enthält keine Authentication-Tags.";
+    public const string DetailAuthenticationTagDataInvalid = "Das Authentication-Tag des Fachdatensatzes ist ungültig.";
     public const string DetailAuthenticationMetadataInvalid = "Das Authentication-Tag des Metadatensatzes ist ungültig.";
     public const string DetailAuthenticationAttachmentInvalid = "Das Authentication-Tag der Anlage {attachmentId} ist ungültig.";
     
     public const string TitleEncryptionIssue = "Entschlüsselungs-Fehler";
-    public const string DetailEncryptionIssue = "Die Entschlüsselung des Metadatensatzes ist fehlgeschlagen.";
+    public const string DetailEncryptionIssueMetadata = "Die Entschlüsselung des Metadatensatzes ist fehlgeschlagen.";
+    public const string DetailEncryptionIssueData = "Der Fachdatensatz konnte nicht entschlüsselt werden.";
     
     public const string TitleMissingData = "Fachdatensatz fehlt";
     public const string DetailMissingData = "Der Fachdatensatz fehlt.";
@@ -170,6 +172,7 @@ public class Problems {
         this.instance = problemInstance switch {
             ProblemInstanceEnum.Metadata => "metadata",
             ProblemInstanceEnum.Submission => "submission",
+            ProblemInstanceEnum.Data => "data",
             _ => throw new ArgumentOutOfRangeException(nameof(problemInstance), problemType, null)
         };
     }
diff --git a/FitConnect/Subscriber.cs b/FitConnect/Subscriber.cs
index 998e56a8..6cd6563a 100644
--- a/FitConnect/Subscriber.cs
+++ b/FitConnect/Subscriber.cs
@@ -101,7 +101,7 @@ public class Subscriber : FitConnectClient,
         catch (Exception e) {
             // SuccessCriteria:3.2
             var problem = new Problems(Problems.ProblemTypeEnum.EncryptionIssue,
-                Problems.DetailEncryptionIssue);
+                Problems.DetailEncryptionIssueMetadata);
             RejectSubmission(submission, problem);
             throw new SecurityEventException(problem, e);
         }
@@ -164,9 +164,19 @@ public class Subscriber : FitConnectClient,
 
 
         if (submission.EncryptedData != null) {
-            var (dataString, _, dataHash) = Encryption.Decrypt(submission.EncryptedData);
-            submission.Data = dataString;
-            VerifyDataHash(submission, dataString);
+            try {
+                var (dataString, _, dataHash) = Encryption.Decrypt(submission.EncryptedData);
+                submission.Data = dataString;
+                VerifyDataHash(submission, dataString);
+            }
+            catch (Exception e) {
+                // SuccessCriteria: 4.2
+                var problem = new Problems(Problems.ProblemTypeEnum.EncryptionIssue,
+                    Problems.DetailEncryptionIssueMetadata, Problems.DetailEncryptionIssueData,
+                    Problems.ProblemInstanceEnum.Data);
+                RejectSubmission(problem);
+                throw new SecurityEventException(problem, e);
+            }
         }
 
         // SuccessCriteria:3.10
@@ -240,9 +250,12 @@ public class Subscriber : FitConnectClient,
             submission.Metadata?.ContentStructure.Data.Hash.Content,
             FitEncryption.CalculateHash(dataString));
 
-        // TODO: Check if problem is correct
+        // SuccessCriteria: 4.1
+        var problem = new Problems(Problems.ProblemTypeEnum.IncorrectAuthenticationTag,
+            Problems.TitleAuthenticationTagInvalid,
+            detail: Problems.DetailAuthenticationTagDataInvalid, Problems.ProblemInstanceEnum.Data);
         RejectSubmission(submission, Problems.EncryptionIssue);
-        throw new Exception("Data hash mismatch");
+        throw new SecurityEventException(problem);
     }
 
 
@@ -308,8 +321,13 @@ public class Subscriber : FitConnectClient,
         return submitEvent;
     }
 
+    /// <summary>
+    /// Checking Attachments
+    /// Criteria 3.12, 5.2
+    /// </summary>
+    /// <exception cref="SecurityEventException"></exception>
     private void CheckAttachments(Submission submission,
-        Dictionary<string, string> attachmentSignatures) {
+        IReadOnlyDictionary<string, string> attachmentSignatures) {
         if (submission?.Attachments != null) {
             // SuccessCriteria:3.12
             if (submission.Attachments.Count != attachmentSignatures.Count ||
@@ -465,27 +483,3 @@ public enum FinishSubmissionStatus {
     Rejected
     // Forwarded
 }
-
-public class SecurityEventException : Exception {
-    public string Title { get; }
-    public string Detail { get; }
-
-    public SecurityEventException(Problems problem, Exception? innerException = null) : base(
-        $"{problem.title}: {problem.detail}", innerException) {
-        Title = problem.title;
-        Detail = problem.detail;
-    }
-
-    public SecurityEventException(Problems[] problem, Exception? innerException = null) : base(
-        $"{problem[0].title}: {problem[0].detail}", innerException) {
-        Title = problem.Select(p => p.title).Aggregate((a, b) => a + "\r\n" + b);
-        Detail = problem.Select(p => p.detail).Aggregate((a, b) => a + "\r\n" + b);
-    }
-
-    public SecurityEventException(string title, string detail, Exception? innerException = null) :
-        base(
-            $"{title}: {detail}", innerException) {
-        Title = title;
-        Detail = detail;
-    }
-}
-- 
GitLab