BSL v0.0.0
AMMOS Bundle Protocol Security Library (BSL)
Loading...
Searching...
No Matches
SecOutcome.c
1/*
2 * Copyright (c) 2025 The Johns Hopkins University Applied Physics
3 * Laboratory LLC.
4 *
5 * This file is part of the Bundle Protocol Security Library (BSL).
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 * This work was performed for the Jet Propulsion Laboratory, California
18 * Institute of Technology, sponsored by the United States Government under
19 * the prime contract 80NM0018D0004 between the Caltech and NASA under
20 * subcontract 1700763.
21 */
27#include <BPSecLib_Private.h>
28
29#include "AbsSecBlock.h"
30#include "SecOutcome.h"
31
32size_t BSL_SecOutcome_Sizeof(void)
33{
34 return sizeof(BSL_SecOutcome_t);
35}
36
37void BSL_SecOutcome_Init(BSL_SecOutcome_t *self, const BSL_SecOper_t *sec_oper, size_t allocation_size)
38{
39 ASSERT_ARG_NONNULL(self);
40 ASSERT_ARG_NONNULL(sec_oper);
41 ASSERT_ARG_EXPR(allocation_size > 0);
42
43 ASSERT_PRECONDITION(BSL_SecOper_IsConsistent(sec_oper));
44
45 memset(self, 0, sizeof(*self));
46 self->is_success = 0;
47 BSLB_SecParamList_init(self->param_list);
48 BSLB_SecResultList_init(self->result_list);
49 self->sec_oper = sec_oper;
50 BSL_Data_InitBuffer(&self->allocation, allocation_size);
51
52 ASSERT_POSTCONDITION(BSL_SecOutcome_IsConsistent(self));
53}
54
55void BSL_SecOutcome_Deinit(BSL_SecOutcome_t *self)
56{
57 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
58
59 BSLB_SecParamList_clear(self->param_list);
60 BSLB_SecResultList_clear(self->result_list);
62 memset(self, 0, sizeof(*self));
63}
64
65bool BSL_SecOutcome_IsConsistent(const BSL_SecOutcome_t *self)
66{
67 CHK_AS_BOOL(self != NULL);
68 CHK_AS_BOOL(self->sec_oper != NULL);
69 CHK_AS_BOOL(self->allocation.len > 0);
70 CHK_AS_BOOL(self->allocation.ptr != NULL);
71
72 // Invariant: If it is not successful, it should not return any results
73 const size_t result_len = BSLB_SecResultList_size(self->result_list);
74 if (self->is_success)
75 {
76 CHK_AS_BOOL(result_len > 0);
77 }
78 else
79 {
80 // Note, uncommenting this causes problems...
81 // CHK_AS_BOOL(result_len == 0);
82 }
83
84 // Invariant: Parameter list contains something (i.e., calling it doesn't cause problems)
85 // NOLINTNEXTLINE
86 CHK_AS_BOOL(BSLB_SecParamList_size(self->param_list) < 1000);
87 return true;
88}
89
90void BSL_SecOutcome_AppendResult(BSL_SecOutcome_t *self, const BSL_SecResult_t *sec_result)
91{
92 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
93 ASSERT_PRECONDITION(BSL_SecResult_IsConsistent(sec_result));
94
95 size_t size0 = BSLB_SecResultList_size(self->result_list);
96 BSLB_SecResultList_push_back(self->result_list, *sec_result);
97
98 ASSERT_POSTCONDITION(size0 + 1 == BSLB_SecResultList_size(self->result_list));
99 ASSERT_POSTCONDITION(BSL_SecOutcome_IsConsistent(self));
100}
101
102size_t BSL_SecOutcome_CountResults(const BSL_SecOutcome_t *self)
103{
104 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
105 return BSLB_SecResultList_size(self->result_list);
106}
107
108const BSL_SecResult_t *BSL_SecOutcome_GetResultAtIndex(const BSL_SecOutcome_t *self, size_t index)
109{
110 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
111 ASSERT_PRECONDITION(index < BSL_SecOutcome_CountResults(self));
112
113 return BSLB_SecResultList_cget(self->result_list, index);
114}
115
116size_t BSL_SecOutcome_CountParams(const BSL_SecOutcome_t *self)
117{
118 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
119
120 return BSLB_SecParamList_size(self->param_list);
121}
122
123const BSL_SecParam_t *BSL_SecOutcome_GetParamAt(const BSL_SecOutcome_t *self, size_t index)
124{
125 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
126 ASSERT_PRECONDITION(index < BSL_SecOutcome_CountParams(self));
127
128 return BSLB_SecParamList_cget(self->param_list, index);
129}
130
131void BSL_SecOutcome_AppendParam(BSL_SecOutcome_t *self, const BSL_SecParam_t *param)
132{
133 ASSERT_PRECONDITION(BSL_SecParam_IsConsistent(param));
134 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
135
136 size_t size0 = BSLB_SecParamList_size(self->param_list);
137 BSLB_SecParamList_push_back(self->param_list, *param);
138
139 ASSERT_POSTCONDITION(size0 + 1 == BSLB_SecParamList_size(self->param_list));
140 ASSERT_POSTCONDITION(BSL_SecOutcome_IsConsistent(self));
141}
142
143static bool BSL_AbsSecBlock_ContainsResult(const BSL_AbsSecBlock_t *abs_sec_block, const BSL_SecResult_t *actual)
144{
145 ASSERT_PRECONDITION(BSL_AbsSecBlock_IsConsistent(abs_sec_block));
146 ASSERT_POSTCONDITION(BSL_SecResult_IsConsistent(actual));
147
148 BSL_AbsSecBlock_Print(abs_sec_block);
149 for (size_t index = 0; index < BSLB_SecResultList_size(abs_sec_block->results); index++)
150 {
151 BSL_SecResult_t *expected = BSLB_SecResultList_get(abs_sec_block->results, index);
152 ASSERT_PROPERTY(expected != NULL);
153 bool hdr_matches = (actual->context_id == expected->context_id) && (actual->result_id == expected->result_id)
154 && (actual->target_block_num == expected->target_block_num)
155 && (actual->_bytelen == expected->_bytelen);
156 if (hdr_matches)
157 {
158 int cmp = memcmp(actual->_bytes, expected->_bytes, expected->_bytelen);
159 return cmp == 0;
160 }
161 }
162 return false;
163}
164
165bool BSL_SecOutcome_IsInAbsSecBlock(const BSL_SecOutcome_t *self, const BSL_AbsSecBlock_t *abs_sec_block)
166{
167 ASSERT_PRECONDITION(BSL_SecOutcome_IsConsistent(self));
168 ASSERT_PRECONDITION(BSL_AbsSecBlock_IsConsistent(abs_sec_block));
169
170 size_t found_matches = 0;
171 size_t expected_matches = BSLB_SecResultList_size(self->result_list);
172 if (expected_matches == 0)
173 {
174 return false;
175 }
176
177 for (size_t result_index = 0; result_index < expected_matches; result_index++)
178 {
179 const BSL_SecResult_t *actual_res = BSLB_SecResultList_get(self->result_list, result_index);
180 ASSERT_PROPERTY(actual_res != NULL);
181 if (BSL_AbsSecBlock_ContainsResult(abs_sec_block, actual_res))
182 {
183 found_matches++;
184 }
185 else
186 {
187 BSL_LOG_ERR("Security operation mismatch - ASB does NOT contain block %lu", actual_res->target_block_num);
188 }
189 }
190 BSL_LOG_DEBUG("Checking results: %lu expected, %lu found", expected_matches, found_matches);
191 return (expected_matches == found_matches) && (found_matches > 0);
192}
Concrete implementation of ASB and its functionality.
Single entry-point include file for all of the BPSec Lib (BSL) frontend API.
#define BSL_LOG_DEBUG(...)
This is an overloaded member function, provided for convenience. It differs from the above function o...
struct BSL_SecOutcome_s BSL_SecOutcome_t
Represents the output following execution of a security operation.
struct BSL_AbsSecBlock_s BSL_AbsSecBlock_t
Forward declaration of BSL_AbsSecBlock_t.
#define BSL_LOG_ERR(...)
This is an overloaded member function, provided for convenience. It differs from the above function o...
bool BSL_AbsSecBlock_IsConsistent(const BSL_AbsSecBlock_t *self)
Checks internal consistency and sanity of this structure.
void BSL_AbsSecBlock_Print(const BSL_AbsSecBlock_t *self)
Prints to LOG INFO.
bool BSL_SecOper_IsConsistent(const BSL_SecOper_t *self)
Returns true if internal consistency and sanity checks pass.
Defines the result of a security operation.
bool BSL_SecParam_IsConsistent(const BSL_SecParam_t *self)
Return true if invariant conditions pass.
Definition SecParam.c:92
bool BSL_SecResult_IsConsistent(const BSL_SecResult_t *self)
Return true when internal invariant checks pass.
Definition SecResult.c:47
int BSL_Data_Deinit(BSL_Data_t *data)
De-initialize a data struct, freeing if necessary.
int BSL_Data_InitBuffer(BSL_Data_t *data, size_t bytelen)
Initialize with an owned buffer of size bytelen.
size_t len
Size of the data buffer.
BSL_DataPtr_t ptr
Pointer to the front of the buffer.
const BSL_SecOper_t * sec_oper
Non-NULL pointer to Security Operation that provided the input.
Definition SecOutcome.h:51
bool is_success
Boolean indicating true when successful.
Definition SecOutcome.h:45
BSLB_SecResultList_t result_list
List of security results with metadata for receiver. Must be encoded into BTSD.
Definition SecOutcome.h:57
BSLB_SecParamList_t param_list
List of security parameters with metadata for receiver. Must be encoded into the BTSD.
Definition SecOutcome.h:54
BSL_Data_t allocation
Pre-allocated memory pool, lifetimes of all results and parameters are tied to this.
Definition SecOutcome.h:48
uint8_t _bytes[BSL_DEFAULT_BYTESTR_LEN+1]
Result as byte array, up to a given maximum.
Definition SecResult.h:90
uint64_t target_block_num
Target block id, put in here for convenience.
Definition SecResult.h:87
uint64_t result_id
Result ID, which is context depdendent, based on security context.
Definition SecResult.h:81
size_t _bytelen
Length of data (in bytes) of the contained bytestring. Always less than BSL_DEFAULT_BYTESTR_LEN.
Definition SecResult.h:93
uint64_t context_id
Context ID, put in here for convenience.
Definition SecResult.h:84