1 // Copyright (c) 2017-2022, Lawrence Livermore National Security, LLC and other CEED contributors. 2 // All Rights Reserved. See the top-level LICENSE and NOTICE files for details. 3 // 4 // SPDX-License-Identifier: BSD-2-Clause 5 // 6 // This file is part of CEED: http://github.com/ceed 7 8 #include <ceed.h> 9 #include <ceed/backend.h> 10 #include <stdbool.h> 11 #include <string.h> 12 13 #include "ceed-ref.h" 14 15 //------------------------------------------------------------------------------ 16 // Has Valid Array 17 //------------------------------------------------------------------------------ 18 static int CeedVectorHasValidArray_Ref(CeedVector vec, bool *has_valid_array) { 19 CeedVector_Ref *impl; 20 21 CeedCallBackend(CeedVectorGetData(vec, &impl)); 22 23 *has_valid_array = impl->array; 24 return CEED_ERROR_SUCCESS; 25 } 26 27 //------------------------------------------------------------------------------ 28 // Check if has borrowed array of given type 29 //------------------------------------------------------------------------------ 30 static inline int CeedVectorHasBorrowedArrayOfType_Ref(const CeedVector vec, CeedMemType mem_type, bool *has_borrowed_array_of_type) { 31 Ceed ceed; 32 CeedVector_Ref *impl; 33 34 CeedCallBackend(CeedVectorGetData(vec, &impl)); 35 CeedCallBackend(CeedVectorGetCeed(vec, &ceed)); 36 CeedCheck(mem_type == CEED_MEM_HOST, ceed, CEED_ERROR_BACKEND, "Can only set HOST memory for this backend"); 37 *has_borrowed_array_of_type = impl->array_borrowed; 38 return CEED_ERROR_SUCCESS; 39 } 40 41 //------------------------------------------------------------------------------ 42 // Vector Set Array 43 //------------------------------------------------------------------------------ 44 static int CeedVectorSetArray_Ref(CeedVector vec, CeedMemType mem_type, CeedCopyMode copy_mode, CeedScalar *array) { 45 Ceed ceed; 46 CeedSize length; 47 CeedVector_Ref *impl; 48 49 CeedCallBackend(CeedVectorGetData(vec, &impl)); 50 CeedCallBackend(CeedVectorGetLength(vec, &length)); 51 CeedCallBackend(CeedVectorGetCeed(vec, &ceed)); 52 53 CeedCheck(mem_type == CEED_MEM_HOST, ceed, CEED_ERROR_BACKEND, "Can only set HOST memory for this backend"); 54 55 switch (copy_mode) { 56 case CEED_COPY_VALUES: 57 if (!impl->array_owned) { 58 CeedCallBackend(CeedCalloc(length, &impl->array_owned)); 59 } 60 impl->array_borrowed = NULL; 61 impl->array = impl->array_owned; 62 if (array) memcpy(impl->array, array, length * sizeof(array[0])); 63 break; 64 case CEED_OWN_POINTER: 65 CeedCallBackend(CeedFree(&impl->array_owned)); 66 impl->array_owned = array; 67 impl->array_borrowed = NULL; 68 impl->array = array; 69 break; 70 case CEED_USE_POINTER: 71 CeedCallBackend(CeedFree(&impl->array_owned)); 72 impl->array_borrowed = array; 73 impl->array = array; 74 } 75 return CEED_ERROR_SUCCESS; 76 } 77 78 //------------------------------------------------------------------------------ 79 // Vector Take Array 80 //------------------------------------------------------------------------------ 81 static int CeedVectorTakeArray_Ref(CeedVector vec, CeedMemType mem_type, CeedScalar **array) { 82 Ceed ceed; 83 CeedVector_Ref *impl; 84 85 CeedCallBackend(CeedVectorGetData(vec, &impl)); 86 CeedCallBackend(CeedVectorGetCeed(vec, &ceed)); 87 88 CeedCheck(mem_type == CEED_MEM_HOST, ceed, CEED_ERROR_BACKEND, "Can only provide HOST memory for this backend"); 89 90 (*array) = impl->array_borrowed; 91 impl->array_borrowed = NULL; 92 impl->array = NULL; 93 return CEED_ERROR_SUCCESS; 94 } 95 96 //------------------------------------------------------------------------------ 97 // Vector Get Array 98 //------------------------------------------------------------------------------ 99 static int CeedVectorGetArrayCore_Ref(CeedVector vec, CeedMemType mem_type, CeedScalar **array) { 100 Ceed ceed; 101 CeedVector_Ref *impl; 102 103 CeedCallBackend(CeedVectorGetData(vec, &impl)); 104 CeedCallBackend(CeedVectorGetCeed(vec, &ceed)); 105 106 CeedCheck(mem_type == CEED_MEM_HOST, ceed, CEED_ERROR_BACKEND, "Can only provide HOST memory for this backend"); 107 108 *array = impl->array; 109 return CEED_ERROR_SUCCESS; 110 } 111 112 //------------------------------------------------------------------------------ 113 // Vector Get Array Read 114 //------------------------------------------------------------------------------ 115 static int CeedVectorGetArrayRead_Ref(CeedVector vec, CeedMemType mem_type, const CeedScalar **array) { 116 return CeedVectorGetArrayCore_Ref(vec, mem_type, (CeedScalar **)array); 117 } 118 119 //------------------------------------------------------------------------------ 120 // Vector Get Array 121 //------------------------------------------------------------------------------ 122 static int CeedVectorGetArray_Ref(CeedVector vec, CeedMemType mem_type, CeedScalar **array) { 123 return CeedVectorGetArrayCore_Ref(vec, mem_type, array); 124 } 125 126 //------------------------------------------------------------------------------ 127 // Vector Get Array Write 128 //------------------------------------------------------------------------------ 129 static int CeedVectorGetArrayWrite_Ref(CeedVector vec, CeedMemType mem_type, CeedScalar **array) { 130 CeedVector_Ref *impl; 131 132 CeedCallBackend(CeedVectorGetData(vec, &impl)); 133 134 if (!impl->array) { 135 if (!impl->array_owned && !impl->array_borrowed) { 136 // Allocate if array is not yet allocated 137 CeedCallBackend(CeedVectorSetArray(vec, CEED_MEM_HOST, CEED_COPY_VALUES, NULL)); 138 } else { 139 // Select dirty array for GetArrayWrite 140 if (impl->array_borrowed) impl->array = impl->array_borrowed; 141 else impl->array = impl->array_owned; 142 } 143 } 144 return CeedVectorGetArrayCore_Ref(vec, mem_type, (CeedScalar **)array); 145 } 146 147 //------------------------------------------------------------------------------ 148 // Vector Restore Array 149 //------------------------------------------------------------------------------ 150 static int CeedVectorRestoreArray_Ref(CeedVector vec) { return CEED_ERROR_SUCCESS; } 151 152 //------------------------------------------------------------------------------ 153 // Vector Restore Array Read 154 //------------------------------------------------------------------------------ 155 static int CeedVectorRestoreArrayRead_Ref(CeedVector vec) { return CEED_ERROR_SUCCESS; } 156 157 //------------------------------------------------------------------------------ 158 // Vector Destroy 159 //------------------------------------------------------------------------------ 160 static int CeedVectorDestroy_Ref(CeedVector vec) { 161 CeedVector_Ref *impl; 162 163 CeedCallBackend(CeedVectorGetData(vec, &impl)); 164 CeedCallBackend(CeedFree(&impl->array_owned)); 165 CeedCallBackend(CeedFree(&impl)); 166 return CEED_ERROR_SUCCESS; 167 } 168 169 //------------------------------------------------------------------------------ 170 // Vector Create 171 //------------------------------------------------------------------------------ 172 int CeedVectorCreate_Ref(CeedSize n, CeedVector vec) { 173 Ceed ceed; 174 CeedVector_Ref *impl; 175 176 CeedCallBackend(CeedVectorGetCeed(vec, &ceed)); 177 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "HasValidArray", CeedVectorHasValidArray_Ref)); 178 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "HasBorrowedArrayOfType", CeedVectorHasBorrowedArrayOfType_Ref)); 179 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "SetArray", CeedVectorSetArray_Ref)); 180 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "TakeArray", CeedVectorTakeArray_Ref)); 181 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "GetArray", CeedVectorGetArray_Ref)); 182 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "GetArrayRead", CeedVectorGetArrayRead_Ref)); 183 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "GetArrayWrite", CeedVectorGetArrayWrite_Ref)); 184 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "RestoreArray", CeedVectorRestoreArray_Ref)); 185 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "RestoreArrayRead", CeedVectorRestoreArrayRead_Ref)); 186 CeedCallBackend(CeedSetBackendFunction(ceed, "Vector", vec, "Destroy", CeedVectorDestroy_Ref)); 187 CeedCallBackend(CeedCalloc(1, &impl)); 188 CeedCallBackend(CeedVectorSetData(vec, impl)); 189 return CEED_ERROR_SUCCESS; 190 } 191 192 //------------------------------------------------------------------------------ 193