X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=mixer.cpp;h=6e1e45d953762ba55523248ea9a38345fe669c23;hb=0fff2c95c89541e5b23611962a00886c64c00daa;hp=74d2bf6f19b79466f1e8d7858563e0f7d64fdd77;hpb=3cafda5de945dd02d321634abd61aa1e261f2384;p=nageru diff --git a/mixer.cpp b/mixer.cpp index 74d2bf6..6e1e45d 100644 --- a/mixer.cpp +++ b/mixer.cpp @@ -74,10 +74,27 @@ void insert_new_frame(RefCountedFrame frame, unsigned field_num, bool interlaced } } +string generate_local_dump_filename(int frame) +{ + time_t now = time(NULL); + tm now_tm; + localtime_r(&now, &now_tm); + + char timestamp[256]; + strftime(timestamp, sizeof(timestamp), "%F-%T%z", &now_tm); + + // Use the frame number to disambiguate between two cuts starting + // on the same second. + char filename[256]; + snprintf(filename, sizeof(filename), "%s%s-f%02d%s", + LOCAL_DUMP_PREFIX, timestamp, frame % 100, LOCAL_DUMP_SUFFIX); + return filename; +} + } // namespace Mixer::Mixer(const QSurfaceFormat &format, unsigned num_cards) - : httpd(LOCAL_DUMP_FILE_NAME, WIDTH, HEIGHT), + : httpd(WIDTH, HEIGHT), num_cards(num_cards), mixer_surface(create_surface(format)), h264_encoder_surface(create_surface(format)), @@ -85,6 +102,7 @@ Mixer::Mixer(const QSurfaceFormat &format, unsigned num_cards) limiter(OUTPUT_FREQUENCY), compressor(OUTPUT_FREQUENCY) { + httpd.open_output_file(generate_local_dump_filename(/*frame=*/0).c_str()); httpd.start(9095); CHECK(init_movit(MOVIT_SHADER_DIR, MOVIT_DEBUG_OFF)); @@ -204,7 +222,7 @@ float find_peak(const float *samples, size_t num_samples) { float m = fabs(samples[0]); for (size_t i = 1; i < num_samples; ++i) { - m = std::max(m, fabs(samples[i])); + m = max(m, fabs(samples[i])); } return m; } @@ -312,11 +330,12 @@ void Mixer::bm_frame(unsigned card_index, uint16_t timecode, if (card->should_quit) return; } + size_t expected_length = width * (height + extra_lines_top + extra_lines_bottom) * 2; if (video_frame.len - video_offset == 0 || - video_frame.len - video_offset != size_t(width * (height + extra_lines_top + extra_lines_bottom) * 2)) { + video_frame.len - video_offset != expected_length) { if (video_frame.len != 0) { - printf("Card %d: Dropping video frame with wrong length (%ld)\n", - card_index, video_frame.len - video_offset); + printf("Card %d: Dropping video frame with wrong length (%ld; expected %ld)\n", + card_index, video_frame.len - video_offset, expected_length); } if (video_frame.owner) { video_frame.owner->release_frame(video_frame); @@ -352,6 +371,8 @@ void Mixer::bm_frame(unsigned card_index, uint16_t timecode, clock_gettime(CLOCK_MONOTONIC, &frame_upload_start); } userdata->last_interlaced = interlaced; + userdata->last_frame_rate_nom = frame_rate_nom; + userdata->last_frame_rate_den = frame_rate_den; RefCountedFrame new_frame(video_frame); // Upload the textures. @@ -623,6 +644,15 @@ void Mixer::thread_func() // chain->print_phase_timing(); } + if (should_cut.exchange(false)) { // Test and clear. + string filename = generate_local_dump_filename(frame); + printf("Starting new recording: %s\n", filename.c_str()); + h264_encoder->shutdown(); + httpd.close_output_file(); + httpd.open_output_file(filename.c_str()); + h264_encoder.reset(new H264Encoder(h264_encoder_surface, WIDTH, HEIGHT, &httpd)); + } + #if 0 // Reset every 100 frames, so that local variations in frame times // (especially for the first few frames, when the shaders are