| 314 | } |
| 315 | |
| 316 | static backend_run run_backend(const std::string & backend_name, |
| 317 | bool use_gpu, |
| 318 | const std::string & model_path, |
| 319 | const std::string & ref_dir, |
| 320 | const sam3_pvs_params & pvs_params, |
| 321 | const std::string & phase6_case_id) { |
| 322 | backend_run run; |
| 323 | run.backend = backend_name; |
| 324 | |
| 325 | sam3_params params; |
| 326 | params.model_path = model_path; |
| 327 | params.n_threads = 4; |
| 328 | params.use_gpu = use_gpu; |
| 329 | |
| 330 | auto model = sam3_load_model(params); |
| 331 | if (!model) { |
| 332 | fprintf(stderr, "Failed to load model for backend=%s\n", backend_name.c_str()); |
| 333 | return run; |
| 334 | } |
| 335 | auto state = sam3_create_state(*model, params); |
| 336 | if (!state) { |
| 337 | fprintf(stderr, "Failed to create state for backend=%s\n", backend_name.c_str()); |
| 338 | return run; |
| 339 | } |
| 340 | |
| 341 | auto pre = load_ref_f32(ref_dir + "/preprocessed"); |
| 342 | if (pre.data.empty()) { |
| 343 | fprintf(stderr, "Missing preprocessed tensor in %s\n", ref_dir.c_str()); |
| 344 | return run; |
| 345 | } |
| 346 | |
| 347 | const std::string dump_root = "/tmp/sam3_pyref_" + backend_name; |
| 348 | ensure_dir(dump_root); |
| 349 | |
| 350 | auto t0 = std::chrono::high_resolution_clock::now(); |
| 351 | const bool ok = sam3_encode_image_from_preprocessed(*state, *model, pre.data.data(), 1008); |
| 352 | auto t1 = std::chrono::high_resolution_clock::now(); |
| 353 | run.encode_ms = std::chrono::duration<double, std::milli>(t1 - t0).count(); |
| 354 | if (!ok) { |
| 355 | fprintf(stderr, "sam3_encode_image_from_preprocessed failed for backend=%s\n", backend_name.c_str()); |
| 356 | return run; |
| 357 | } |
| 358 | |
| 359 | const char * nhwc_tensors[] = { |
| 360 | "dbg_patch_embed", |
| 361 | "dbg_after_pos_embed", |
| 362 | "dbg_after_ln_pre", |
| 363 | "dbg_block_0_out", |
| 364 | "dbg_block_1_out", |
| 365 | "dbg_block_2_out", |
| 366 | "dbg_block_10_out", |
| 367 | "dbg_block_14_out", |
| 368 | "dbg_block_15_out", |
| 369 | "dbg_block_16_out", |
| 370 | }; |
| 371 | for (const char * name : nhwc_tensors) { |
| 372 | std::string ref_name = name; |
| 373 | if (strncmp(name, "dbg_", 4) == 0) { |
no test coverage detected