MCPcopy Create free account
hub / github.com/PABannier/sam3.cpp / sam3_encode_memory

Function sam3_encode_memory

sam3.cpp:11510–11715  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

11508}
11509
11510static bool sam3_encode_memory(
11511 sam3_tracker& tracker, sam3_state& state, const sam3_model& model,
11512 int inst_id, const float* mask_logits, int mask_h, int mask_w,
11513 int frame_idx, bool is_cond, float obj_score) {
11514 const auto& hp = model.hparams;
11515 const int D = hp.neck_dim, MD = hp.mem_out_dim;
11516 const int H = sam3_eff_feat_size(state, hp);
11517 const int HIGH_RES = sam3_eff_img_size(state, hp);
11518 const int INTERPOL = H * 16;
11519
11520 // Mask preprocessing: mask_logits → HIGH_RES → sigmoid → scale/bias → INTERPOL
11521 auto m_hires = sam3_bilinear_interpolate(mask_logits, mask_w, mask_h, HIGH_RES, HIGH_RES);
11522 const float sig_scale = hp.sigmoid_scale(), sig_bias = hp.sigmoid_bias();
11523 for (auto& v : m_hires) { float s = 1.0f / (1.0f + expf(-v)); v = s * sig_scale + sig_bias; }
11524 auto m_interp = sam3_bilinear_interpolate(m_hires.data(), HIGH_RES, HIGH_RES, INTERPOL, INTERPOL);
11525
11526 const size_t bs = ggml_tensor_overhead() * 16384 + ggml_graph_overhead();
11527 struct ggml_init_params gp = {bs, nullptr, true};
11528 auto* ctx0 = ggml_init(gp);
11529 if (!ctx0) return false;
11530
11531 auto* mask_in = ggml_new_tensor_4d(ctx0, GGML_TYPE_F32, INTERPOL, INTERPOL, 1, 1);
11532 ggml_set_name(mask_in, "mem_mask");
11533 ggml_set_input(mask_in);
11534
11535 // Learned mask downsampler: 4 stages conv+LN+GELU + final 1×1
11536 // Conv output is in ggml "conv" layout. permute(1,2,0,3) converts to "internal" layout
11537 // where ne[0]=channel for LN2d. permute(2,0,1,3) converts back to "conv" layout.
11538 auto* ds = mask_in;
11539 for (int s = 0; s < 4; ++s) {
11540 int out_ch = (int)model.mem_enc.ds_conv_w[s]->ne[3];
11541 ds = ggml_conv_2d(ctx0, model.mem_enc.ds_conv_w[s], ds, 2, 2, 1, 1, 1, 1);
11542 ds = ggml_add(ctx0, ds, ggml_reshape_4d(ctx0, model.mem_enc.ds_conv_b[s], 1, 1, out_ch, 1));
11543 ds = ggml_cont(ctx0, ggml_permute(ctx0, ds, 1, 2, 0, 3)); // conv→internal (ne[0]=channel)
11544 ds = sam3_layer_norm_2d(ctx0, ds, model.mem_enc.ds_norm_w[s], model.mem_enc.ds_norm_b[s]);
11545 ds = ggml_gelu(ctx0, ds);
11546 ds = ggml_cont(ctx0, ggml_permute(ctx0, ds, 2, 0, 1, 3)); // internal→conv
11547 }
11548 ds = ggml_conv_2d(ctx0, model.mem_enc.ds_conv_w[4], ds, 1, 1, 0, 0, 1, 1);
11549 ds = ggml_add(ctx0, ds, ggml_reshape_4d(ctx0, model.mem_enc.ds_conv_b[4], 1, 1, D, 1));
11550 ds = ggml_cont(ctx0, ggml_permute(ctx0, ds, 1, 2, 0, 3)); // conv→internal [D, ...]
11551
11552 // Pixel projection — use fresh input tensor to avoid pulling in the
11553 // entire ViT+neck recomputation from state.neck_trk[2]'s dependency tree
11554 auto* pix_in_raw = ggml_new_tensor_4d(ctx0, GGML_TYPE_F32, D, H, H, 1);
11555 ggml_set_name(pix_in_raw, "mem_pix_feat");
11556 ggml_set_input(pix_in_raw);
11557 auto* pix_in = ggml_cont(ctx0, ggml_permute(ctx0, pix_in_raw, 2, 0, 1, 3));
11558 auto* pix = ggml_conv_2d(ctx0, model.mem_enc.pix_proj_w, pix_in, 1, 1, 0, 0, 1, 1);
11559 pix = ggml_add(ctx0, pix, ggml_reshape_4d(ctx0, model.mem_enc.pix_proj_b, 1, 1, D, 1));
11560 pix = ggml_cont(ctx0, ggml_permute(ctx0, pix, 1, 2, 0, 3));
11561
11562 // Fusion: ADD (not multiply)
11563 auto* fused = ggml_add(ctx0, pix, ds);
11564 for (int i = 0; i < 2; ++i)
11565 fused = sam3_cxblock_forward(ctx0, fused,
11566 model.mem_enc.fuser_dw_w[i], model.mem_enc.fuser_dw_b[i],
11567 model.mem_enc.fuser_norm_w[i], model.mem_enc.fuser_norm_b[i],

Callers 3

sam3_track_frameFunction · 0.85
sam3_propagate_frameFunction · 0.85

Calls 10

sam3_eff_feat_sizeFunction · 0.85
sam3_eff_img_sizeFunction · 0.85
sam3_layer_norm_2dFunction · 0.85
sam3_cxblock_forwardFunction · 0.85
sam3_graph_computeFunction · 0.85
sigmoid_scaleMethod · 0.80
sigmoid_biasMethod · 0.80

Tested by

no test coverage detected