src/api/native_tensor_misc.cpp
| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | // native_tensor_misc.cpp — bodies for the "misc" restored group: the | ||
| 2 | // gated-deltanet L2 norm pair, three remaining loss entry points and the | ||
| 3 | // diffusion sampler steps + timestep embedding. See native_tensor_misc_decl.h | ||
| 4 | // for the provenance of each function and native_tensor_nn.cpp for the | ||
| 5 | // mechanism these bodies copy (need() / BROTENSOR_API_TRY / the error slot). | ||
| 6 | |||
| 7 | #include "native_tensor_misc_decl.h" | ||
| 8 | #include "api_internal.h" | ||
| 9 | #include "native_register.h" | ||
| 10 | |||
| 11 | #include <string> | ||
| 12 | |||
| 13 | using namespace brotensor::api; | ||
| 14 | |||
| 15 | namespace { | ||
| 16 | |||
| 17 | // X is (L, numHeads*headDim), both positive. | ||
| 18 | 6 | bool needHeadCols(const char* L, const brotensor::Tensor* x, int32_t headDim, int32_t numHeads) { | |
| 19 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 6 times.
|
6 | if (!needPositive(L, {headDim, numHeads})) return false; |
| 20 |
2/2✓ Branch 0 taken 2 times.
✓ Branch 1 taken 4 times.
|
6 | if (static_cast<int64_t>(x->cols) != static_cast<int64_t>(numHeads) * headDim) { |
| 21 |
2/4✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
|
2 | setError(std::string(L) + ": X must have numHeads*headDim columns"); |
| 22 | 2 | return false; | |
| 23 | } | ||
| 24 | 4 | return true; | |
| 25 | 6 | } | |
| 26 | |||
| 27 | } // namespace | ||
| 28 | |||
| 29 | extern "C" { | ||
| 30 | |||
| 31 | // ---- L2 norm --------------------------------------------------------------- | ||
| 32 | |||
| 33 | 4 | void bro_tensor_l2NormForward(void* X, int32_t headDim, int32_t numHeads, double eps, void* Y) { | |
| 34 |
3/4✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 2 times.
|
4 | if (!need("l2NormForward", {X, Y}) || !needHeadCols("l2NormForward", toTensor(X), headDim, numHeads)) return; |
| 35 | BROTENSOR_API_TRY | ||
| 36 |
3/6✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
|
2 | brotensor::l2_norm_forward(*toTensor(X), headDim, numHeads, static_cast<float>(eps), *toTensor(Y)); |
| 37 |
0/12✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
2 | BROTENSOR_API_CATCH("l2NormForward") |
| 38 | 4 | } | |
| 39 | |||
| 40 | 2 | void bro_tensor_l2NormBackward(void* X, int32_t headDim, int32_t numHeads, double eps, void* dY, void* dX) { | |
| 41 |
2/4✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
|
2 | if (!need("l2NormBackward", {X, dY, dX}) || !needHeadCols("l2NormBackward", toTensor(X), headDim, numHeads)) return; |
| 42 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
2 | if (!needPair("l2NormBackward", "dY", toTensor(dY), toTensor(X))) return; |
| 43 | BROTENSOR_API_TRY | ||
| 44 |
2/4✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
|
4 | brotensor::l2_norm_backward(*toTensor(X), headDim, numHeads, static_cast<float>(eps), |
| 45 |
2/4✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
|
2 | *toTensor(dY), *toTensor(dX)); |
| 46 |
0/12✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
2 | BROTENSOR_API_CATCH("l2NormBackward") |
| 47 | 2 | } | |
| 48 | |||
| 49 | // ---- losses ---------------------------------------------------------------- | ||
| 50 | |||
| 51 | 6 | void bro_tensor_bceWithLogitsFusedBatched(void* logits_BL, void* target_BL, uint64_t mask_bits, | |
| 52 | double posWeight, void* probs_BL, void* dLogits_BL, | ||
| 53 | void* lossPerSample) { | ||
| 54 | 6 | const char* L = "bceWithLogitsFusedBatched"; | |
| 55 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 6 times.
|
6 | if (!need(L, {logits_BL, target_BL, probs_BL, dLogits_BL, lossPerSample})) return; |
| 56 |
1/2✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
|
6 | if (!needPair(L, "target_BL", toTensor(target_BL), toTensor(logits_BL))) return; |
| 57 |
1/2✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
|
6 | if (!needMask(L, tensorFromValue(mask_bits), toTensor(logits_BL)->size())) return; |
| 58 | BROTENSOR_API_TRY | ||
| 59 |
3/6✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 6 times.
✗ Branch 5 not taken.
|
12 | brotensor::bce_with_logits_fused_batched(*toTensor(logits_BL), *toTensor(target_BL), |
| 60 |
1/2✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
|
6 | maskPtr(mask_bits), static_cast<float>(posWeight), |
| 61 |
2/4✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
✗ Branch 3 not taken.
|
6 | *toTensor(probs_BL), *toTensor(dLogits_BL), |
| 62 |
1/2✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
|
6 | *toTensor(lossPerSample)); |
| 63 |
0/12✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
6 | BROTENSOR_API_CATCH("bceWithLogitsFusedBatched") |
| 64 | 6 | } | |
| 65 | |||
| 66 | // Host buffers: the op takes raw `const float*` / `float*` (CPU-only), so the | ||
| 67 | // four arrays cross as f32[] pairs and probs / dLogits are written in place. | ||
| 68 | // An empty mask array is "no mask" — the old binding's `mask|null`. | ||
| 69 | 4 | double bro_tensor_softmaxXentSegment(const float* logits, uint32_t logits_len, | |
| 70 | const float* target, uint32_t target_len, | ||
| 71 | float* probs, uint32_t probs_len, | ||
| 72 | float* dLogits, uint32_t dLogits_len, | ||
| 73 | int32_t n, | ||
| 74 | const float* mask, uint32_t mask_len) { | ||
| 75 |
4/8✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 4 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 4 times.
|
4 | if (!logits || !target || !probs || !dLogits) { |
| 76 | ✗ | setError("softmaxXentSegment: logits/target/probs/dLogits must be Float32Array"); | |
| 77 | ✗ | return 0.0; | |
| 78 | } | ||
| 79 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 4 times.
|
4 | if (n <= 0) { |
| 80 | ✗ | setError("softmaxXentSegment: n must be positive"); | |
| 81 | ✗ | return 0.0; | |
| 82 | } | ||
| 83 | 4 | const auto un = static_cast<uint32_t>(n); | |
| 84 |
4/8✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 4 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 4 times.
|
4 | if (logits_len < un || target_len < un || probs_len < un || dLogits_len < un) { |
| 85 | ✗ | setError("softmaxXentSegment: a buffer holds fewer than n=" + std::to_string(n) + " elements"); | |
| 86 | ✗ | return 0.0; | |
| 87 | } | ||
| 88 |
3/4✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 2 times.
|
4 | const float* mask_ptr = (mask && mask_len > 0) ? mask : nullptr; |
| 89 |
3/4✓ Branch 0 taken 2 times.
✓ Branch 1 taken 2 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
|
4 | if (mask_ptr && mask_len < un) { |
| 90 | ✗ | setError("softmaxXentSegment: mask holds fewer than n=" + std::to_string(n) + " elements"); | |
| 91 | ✗ | return 0.0; | |
| 92 | } | ||
| 93 | BROTENSOR_API_TRY | ||
| 94 |
1/2✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
|
4 | return brotensor::softmax_xent_segment(logits, target, probs, dLogits, n, mask_ptr); |
| 95 | ✗ | BROTENSOR_API_CATCH("softmaxXentSegment") | |
| 96 | ✗ | return 0.0; | |
| 97 | 4 | } | |
| 98 | |||
| 99 | // mseScalar(pred, target) -> [loss, dPred]: the pair as a length-2 f64[]. | ||
| 100 | 4 | void bro_tensor_mseScalar(double pred, double target, bronze_native_buffer* out) { | |
| 101 | static thread_local double pair[2]; | ||
| 102 |
1/2✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
|
4 | if (!out) return; |
| 103 | 4 | out->data = nullptr; | |
| 104 | 4 | out->length = 0; | |
| 105 | 4 | out->release = nullptr; | |
| 106 | 4 | out->ctx = nullptr; | |
| 107 | BROTENSOR_API_TRY | ||
| 108 | 4 | float dPred = 0.0f; | |
| 109 |
1/2✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
|
4 | const float loss = brotensor::mse_scalar(static_cast<float>(pred), static_cast<float>(target), dPred); |
| 110 | 4 | pair[0] = loss; | |
| 111 | 4 | pair[1] = dPred; | |
| 112 | 4 | out->data = pair; | |
| 113 | 4 | out->length = 2; | |
| 114 |
0/12✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
4 | BROTENSOR_API_CATCH("mseScalar") |
| 115 | 4 | } | |
| 116 | |||
| 117 | // ---- diffusion sampler steps + timestep embedding -------------------------- | ||
| 118 | |||
| 119 | 2 | void bro_tensor_ddimStep(void* x_t, void* eps_pred, double alphaT, double alphaPrev, | |
| 120 | double sigmaT, void* x_prev) { | ||
| 121 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
|
2 | if (!need("ddimStep", {x_t, eps_pred, x_prev})) return; |
| 122 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
2 | if (!needPair("ddimStep", "eps_pred", toTensor(eps_pred), toTensor(x_t))) return; |
| 123 | BROTENSOR_API_TRY | ||
| 124 |
3/6✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
|
2 | brotensor::ddim_step(*toTensor(x_t), *toTensor(eps_pred), static_cast<float>(alphaT), |
| 125 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
2 | static_cast<float>(alphaPrev), static_cast<float>(sigmaT), *toTensor(x_prev)); |
| 126 |
0/12✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
2 | BROTENSOR_API_CATCH("ddimStep") |
| 127 | 2 | } | |
| 128 | |||
| 129 | 2 | void bro_tensor_eulerStep(void* x_t, void* eps_pred, double sigmaT, double sigmaPrev, void* x_prev) { | |
| 130 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
|
2 | if (!need("eulerStep", {x_t, eps_pred, x_prev})) return; |
| 131 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
2 | if (!needPair("eulerStep", "eps_pred", toTensor(eps_pred), toTensor(x_t))) return; |
| 132 | BROTENSOR_API_TRY | ||
| 133 |
3/6✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
|
2 | brotensor::euler_step(*toTensor(x_t), *toTensor(eps_pred), static_cast<float>(sigmaT), |
| 134 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
2 | static_cast<float>(sigmaPrev), *toTensor(x_prev)); |
| 135 |
0/12✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
2 | BROTENSOR_API_CATCH("eulerStep") |
| 136 | 2 | } | |
| 137 | |||
| 138 | 2 | void bro_tensor_dpmpp2mStep(void* x_t, void* eps_pred, void* x0_prev, double sigmaT, | |
| 139 | double c_xt, double c_x0t, double c_x0prev, | ||
| 140 | void* x_prev, void* x0_out) { | ||
| 141 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
|
2 | if (!need("dpmpp2mStep", {x_t, eps_pred, x0_prev, x_prev, x0_out})) return; |
| 142 |
2/4✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
|
2 | if (!needPair("dpmpp2mStep", "eps_pred", toTensor(eps_pred), toTensor(x_t)) || |
| 143 | 2 | !needPair("dpmpp2mStep", "x0_prev", toTensor(x0_prev), toTensor(x_t))) return; | |
| 144 | BROTENSOR_API_TRY | ||
| 145 |
4/8✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
|
4 | brotensor::dpmpp_2m_step(*toTensor(x_t), *toTensor(eps_pred), *toTensor(x0_prev), |
| 146 | 2 | static_cast<float>(sigmaT), static_cast<float>(c_xt), | |
| 147 | 2 | static_cast<float>(c_x0t), static_cast<float>(c_x0prev), | |
| 148 |
2/4✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
|
2 | *toTensor(x_prev), *toTensor(x0_out)); |
| 149 |
0/12✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
2 | BROTENSOR_API_CATCH("dpmpp2mStep") |
| 150 | 2 | } | |
| 151 | |||
| 152 | 8 | void bro_tensor_timestepEmbedding(void* timesteps, int32_t dim, double maxPeriod, void* Y) { | |
| 153 |
2/4✗ Branch 0 not taken.
✓ Branch 1 taken 8 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 8 times.
|
8 | if (!need("timestepEmbedding", {timesteps, Y}) || !needNonNegative("timestepEmbedding", {dim})) return; |
| 154 | BROTENSOR_API_TRY | ||
| 155 |
4/6✓ Branch 0 taken 8 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 8 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 6 times.
✓ Branch 5 taken 2 times.
|
8 | brotensor::timestep_embedding(*toTensor(timesteps), dim, static_cast<float>(maxPeriod), *toTensor(Y)); |
| 156 |
5/12✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
|
8 | BROTENSOR_API_CATCH("timestepEmbedding") |
| 157 | 10 | } | |
| 158 | |||
| 159 | } // extern "C" | ||
| 160 | |||
| 161 | namespace brotensor::api { | ||
| 162 | |||
| 163 | 3 | bool registerTensorNatives_misc(std::string* error) { | |
| 164 | using namespace brotensor::api::reg; | ||
| 165 | 3 | return | |
| 166 | 6 | fn("__bro_native.tensor.l2NormForward", p(&bro_tensor_l2NormForward), "void", | |
| 167 |
2/4✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | {kTensorCls, "i32", "i32", "f64", kTensorCls}, error) && |
| 168 | 6 | fn("__bro_native.tensor.l2NormBackward", p(&bro_tensor_l2NormBackward), "void", | |
| 169 |
2/4✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | {kTensorCls, "i32", "i32", "f64", kTensorCls, kTensorCls}, error) && |
| 170 | 6 | fn("__bro_native.tensor.bceWithLogitsFusedBatched", p(&bro_tensor_bceWithLogitsFusedBatched), "void", | |
| 171 |
2/4✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | {kTensorCls, kTensorCls, kDyn, "f64", kTensorCls, kTensorCls, kTensorCls}, error) && |
| 172 | 6 | fn("__bro_native.tensor.softmaxXentSegment", p(&bro_tensor_softmaxXentSegment), "f64", | |
| 173 |
2/4✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | {"f32[]", "f32[]", "f32[]", "f32[]", "i32", "f32[]"}, error) && |
| 174 | 6 | fn("__bro_native.tensor.mseScalar", p(&bro_tensor_mseScalar), "f64[]", | |
| 175 |
2/4✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | {"f64", "f64"}, error) && |
| 176 | 6 | fn("__bro_native.tensor.ddimStep", p(&bro_tensor_ddimStep), "void", | |
| 177 |
2/4✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | {kTensorCls, kTensorCls, "f64", "f64", "f64", kTensorCls}, error) && |
| 178 | 6 | fn("__bro_native.tensor.eulerStep", p(&bro_tensor_eulerStep), "void", | |
| 179 |
2/4✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | {kTensorCls, kTensorCls, "f64", "f64", kTensorCls}, error) && |
| 180 | 6 | fn("__bro_native.tensor.dpmpp2mStep", p(&bro_tensor_dpmpp2mStep), "void", | |
| 181 |
2/4✗ Branch 0 not taken.
✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 3 times.
|
6 | {kTensorCls, kTensorCls, kTensorCls, "f64", "f64", "f64", "f64", kTensorCls, kTensorCls}, error) && |
| 182 | 6 | fn("__bro_native.tensor.timestepEmbedding", p(&bro_tensor_timestepEmbedding), "void", | |
| 183 | 3 | {kTensorCls, "i32", "f64", kTensorCls}, error); | |
| 184 | } | ||
| 185 | |||
| 186 | } // namespace brotensor::api | ||
| 187 |