#include "inference_session.hpp" #include "camera_pipeline.hpp" #include #include #include #include namespace cms { std::uint64_t monotonicNs() { return std::chrono::duration_cast(std::chrono::steady_clock::now().time_since_epoch()).count(); } } using namespace cms; void check(bool condition,char const* message){if(!condition)throw std::runtime_error(message);} template void rejects(F f){bool failed=false;try{f();}catch(std::exception const&){failed=true;}check(failed,"Expected rejection");} int main(int argc,char** argv)try { if(argc!=2)return 2; std::filesystem::path root=argv[1]; PipelineConfig c;c.record_session=root/"recorded";c.engines=root;c.door_mask=root/"mask.json"; c.camera.width=64;c.camera.height=48;c.detector_confidence=.42; std::ofstream(c.door_mask)<<"{}"; for(auto name:{"yolo11s.engine","rtmw_l_384.engine"})std::ofstream(root/name)<<"fixture"; auto im=std::make_shared();im->width=64;im->height=48;im->stride=200; im->pixels.resize(9600); for(int y=0;y<48;++y)for(int x=0;x<192;++x)im->pixels[y*200+x]=32+x/3+y%4; FrameResult r;r.image=im;r.frame_index=3;r.capture.frame_index=3;r.capture.driver_sequence=42; r.capture.capture_monotonic_ns=123;r.capture.received_monotonic_ns=124; { SessionWriter writer(c);writer.write(r,{{"raw_keypoints",{1,2,3}}}); r.frame_index=9;r.capture.frame_index=9; for(auto& pixel:im->pixels)pixel+=80; writer.write(r,{{"raw_keypoints",{4,5,6}}}); writer.finish();writer.finish(); rejects([&]{writer.write(r,{});}); } rejects([&]{SessionWriter duplicate(c);}); PipelineConfig replay;replay.replay_session=c.record_session; SessionReader reader(replay);check(replay.camera.width==64&&replay.detector_confidence==.42,"Settings not restored"); auto first=reader.read();check(first&&first->metadata.frame_index==3,"First index mismatch"); check(first->metadata.driver_sequence==42&&first->metadata.capture_monotonic_ns!=123,"Capture metadata mismatch"); check(first->replay_record->at("capture").at("capture_monotonic_ns")==123,"Original clock lost"); for(int y=0;y<48;++y)for(int x=0;x<192;++x)check(std::abs(int(first->image->pixels[y*192+x])-(32+x/3+y%4))<12,"Decoded first frame mismatch"); auto second=reader.read();check(second&&second->metadata.frame_index==9,"Gap/order lost"); check(second->image->pixels[0]>first->image->pixels[0]+60,"Video frame order lost"); check(!reader.read(),"EOF not drained"); // Unindexed temporary metadata must not become input. std::ofstream(c.record_session/"frames/000000000002.json.tmp")<<"incomplete"; SessionReader prefix(replay);check(prefix.read()&&prefix.read()&&!prefix.read(),"Uncommitted data replayed"); std::filesystem::remove(c.record_session/"frames/000000000001.json"); SessionReader missing(replay);missing.read();rejects([&]{missing.read();}); std::ofstream(c.record_session/"frames.txt",std::ios::trunc)<<"../bad\n"; SessionReader invalid(replay);rejects([&]{invalid.read();}); std::ofstream(c.record_session/"frames.txt",std::ios::trunc)<<"000000000000"; SessionReader truncated(replay);rejects([&]{truncated.read();}); std::ofstream(c.record_session/"frames.txt",std::ios::trunc)<<"000000000000\n"; SessionReader shortIndex(replay);shortIndex.read();rejects([&]{shortIndex.read();}); std::filesystem::remove(c.record_session/"complete.json"); rejects([&]{SessionReader incomplete(replay);}); c.record_session=root/"empty"; {SessionWriter empty(c);empty.finish();} replay.replay_session=c.record_session; SessionReader empty(replay);check(!empty.read(),"Empty recording has frames"); c.camera.width=63;c.record_session=root/"odd"; rejects([&]{SessionWriter odd(c);}); std::cout<<"H.264 encode/decode, settings, order, EOF, stop finalization and corruption checks passed\n"; }catch(std::exception const& e){std::cerr<