Rework locking in ZMPacket by using a new class called ZMLockedPacket.
parent
6a11b23aaf
commit
9903e909af
|
@ -1813,12 +1813,13 @@ bool Monitor::Analyse() {
|
||||||
// if have event, send frames until we find a video packet, at which point do analysis. Adaptive skip should only affect which frames we do analysis on.
|
// if have event, send frames until we find a video packet, at which point do analysis. Adaptive skip should only affect which frames we do analysis on.
|
||||||
|
|
||||||
// get_analysis_packet will lock the packet and may wait if analysis_it is at the end
|
// get_analysis_packet will lock the packet and may wait if analysis_it is at the end
|
||||||
ZMPacket *snap = packetqueue.get_packet(analysis_it);
|
ZMLockedPacket *packet_lock = packetqueue.get_packet(analysis_it);
|
||||||
if (!snap) return false;
|
if (!packet_lock) return false;
|
||||||
|
ZMPacket *snap = packet_lock->packet_;
|
||||||
|
|
||||||
// Is it possible for snap->score to be ! -1 ? Not if everything is working correctly
|
// Is it possible for snap->score to be ! -1 ? Not if everything is working correctly
|
||||||
if (snap->score != -1) {
|
if (snap->score != -1) {
|
||||||
snap->unlock();
|
delete packet_lock;
|
||||||
packetqueue.increment_it(analysis_it);
|
packetqueue.increment_it(analysis_it);
|
||||||
Error("skipping because score was %d", snap->score);
|
Error("skipping because score was %d", snap->score);
|
||||||
return false;
|
return false;
|
||||||
|
@ -1844,7 +1845,7 @@ bool Monitor::Analyse() {
|
||||||
// Ready means that we have captured the warmup # of frames
|
// Ready means that we have captured the warmup # of frames
|
||||||
if (!Ready()) {
|
if (!Ready()) {
|
||||||
Debug(3, "Not ready?");
|
Debug(3, "Not ready?");
|
||||||
snap->unlock();
|
delete packet_lock;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1896,10 +1897,10 @@ bool Monitor::Analyse() {
|
||||||
while (!snap->image and !snap->decoded) {
|
while (!snap->image and !snap->decoded) {
|
||||||
// Need to wait for the decoder thread.
|
// Need to wait for the decoder thread.
|
||||||
Debug(1, "Waiting for decode");
|
Debug(1, "Waiting for decode");
|
||||||
snap->wait();
|
packet_lock->wait();
|
||||||
if (!snap->image and snap->decoded) {
|
if (!snap->image and snap->decoded) {
|
||||||
Debug(1, "No image but was decoded, giving up");
|
Debug(1, "No image but was decoded, giving up");
|
||||||
snap->unlock();
|
delete packet_lock;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
} // end while ! decoded
|
} // end while ! decoded
|
||||||
|
@ -2010,22 +2011,32 @@ bool Monitor::Analyse() {
|
||||||
);
|
);
|
||||||
|
|
||||||
// This gets a lock on the starting packet
|
// This gets a lock on the starting packet
|
||||||
ZMPacket *starting_packet = ( *start_it == snap_it ) ? snap : packetqueue.get_packet(start_it);
|
|
||||||
|
ZMLockedPacket *starting_packet_lock = nullptr;
|
||||||
|
ZMPacket *starting_packet = nullptr;
|
||||||
|
if ( *start_it != snap_it ) {
|
||||||
|
starting_packet_lock = packetqueue.get_packet(start_it);
|
||||||
|
if (!starting_packet_lock) return false;
|
||||||
|
starting_packet = starting_packet_lock->packet_;
|
||||||
|
} else {
|
||||||
|
starting_packet = snap;
|
||||||
|
}
|
||||||
|
|
||||||
event = new Event(this, *(starting_packet->timestamp), "Continuous", noteSetMap);
|
event = new Event(this, *(starting_packet->timestamp), "Continuous", noteSetMap);
|
||||||
// Write out starting packets, do not modify packetqueue it will garbage collect itself
|
// Write out starting packets, do not modify packetqueue it will garbage collect itself
|
||||||
while ( starting_packet and (*start_it) != snap_it ) {
|
while ( starting_packet and ((*start_it) != snap_it) ) {
|
||||||
event->AddPacket(starting_packet);
|
event->AddPacket(starting_packet);
|
||||||
// Have added the packet, don't want to unlock it until we have locked the next
|
// Have added the packet, don't want to unlock it until we have locked the next
|
||||||
|
|
||||||
packetqueue.increment_it(start_it);
|
packetqueue.increment_it(start_it);
|
||||||
if ( (*start_it) == snap_it ) {
|
if ( (*start_it) == snap_it ) {
|
||||||
starting_packet->unlock();
|
if (starting_packet_lock) delete starting_packet_lock;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
ZMPacket *p = packetqueue.get_packet(start_it);
|
ZMLockedPacket *lp = packetqueue.get_packet(start_it);
|
||||||
starting_packet->unlock();
|
delete starting_packet_lock;
|
||||||
starting_packet = p;
|
starting_packet_lock = lp;
|
||||||
|
starting_packet = lp->packet_;
|
||||||
}
|
}
|
||||||
packetqueue.free_it(start_it);
|
packetqueue.free_it(start_it);
|
||||||
delete start_it;
|
delete start_it;
|
||||||
|
@ -2094,7 +2105,16 @@ bool Monitor::Analyse() {
|
||||||
snap_it,
|
snap_it,
|
||||||
(pre_event_count > alarm_frame_count ? pre_event_count : alarm_frame_count)
|
(pre_event_count > alarm_frame_count ? pre_event_count : alarm_frame_count)
|
||||||
);
|
);
|
||||||
ZMPacket *starting_packet = ( *start_it == snap_it ) ? snap : packetqueue.get_packet(start_it);
|
|
||||||
|
ZMLockedPacket *starting_packet_lock = nullptr;
|
||||||
|
ZMPacket *starting_packet = nullptr;
|
||||||
|
if ( *start_it != snap_it ) {
|
||||||
|
starting_packet_lock = packetqueue.get_packet(start_it);
|
||||||
|
if (!starting_packet_lock) return false;
|
||||||
|
starting_packet = starting_packet_lock->packet_;
|
||||||
|
} else {
|
||||||
|
starting_packet = snap;
|
||||||
|
}
|
||||||
|
|
||||||
event = new Event(this, *(starting_packet->timestamp), cause, noteSetMap);
|
event = new Event(this, *(starting_packet->timestamp), cause, noteSetMap);
|
||||||
shared_data->last_event_id = event->Id();
|
shared_data->last_event_id = event->Id();
|
||||||
|
@ -2108,12 +2128,13 @@ bool Monitor::Analyse() {
|
||||||
|
|
||||||
packetqueue.increment_it(start_it);
|
packetqueue.increment_it(start_it);
|
||||||
if ( (*start_it) == snap_it ) {
|
if ( (*start_it) == snap_it ) {
|
||||||
starting_packet->unlock();
|
if (starting_packet_lock) delete starting_packet_lock;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
ZMPacket *p = packetqueue.get_packet(start_it);
|
ZMLockedPacket *lp = packetqueue.get_packet(start_it);
|
||||||
starting_packet->unlock();
|
delete starting_packet_lock;
|
||||||
starting_packet = p;
|
starting_packet_lock = lp;
|
||||||
|
starting_packet = lp->packet_;
|
||||||
}
|
}
|
||||||
packetqueue.free_it(start_it);
|
packetqueue.free_it(start_it);
|
||||||
delete start_it;
|
delete start_it;
|
||||||
|
@ -2266,7 +2287,7 @@ bool Monitor::Analyse() {
|
||||||
if (event) event->AddPacket(snap);
|
if (event) event->AddPacket(snap);
|
||||||
|
|
||||||
// popPacket will have placed a second lock on snap, so release it here.
|
// popPacket will have placed a second lock on snap, so release it here.
|
||||||
snap->unlock();
|
delete packet_lock;
|
||||||
|
|
||||||
if ( snap->image_index > 0 ) {
|
if ( snap->image_index > 0 ) {
|
||||||
// Only do these if it's a video packet.
|
// Only do these if it's a video packet.
|
||||||
|
@ -2705,11 +2726,12 @@ int Monitor::Capture() {
|
||||||
bool Monitor::Decode() {
|
bool Monitor::Decode() {
|
||||||
if (!decoder_it) decoder_it = packetqueue.get_video_it(true);
|
if (!decoder_it) decoder_it = packetqueue.get_video_it(true);
|
||||||
|
|
||||||
ZMPacket *packet = packetqueue.get_packet(decoder_it);
|
ZMLockedPacket *packet_lock = packetqueue.get_packet(decoder_it);
|
||||||
if (!packet) return false;
|
if (!packet_lock) return false;
|
||||||
|
ZMPacket *packet = packet_lock->packet_;
|
||||||
packetqueue.increment_it(decoder_it);
|
packetqueue.increment_it(decoder_it);
|
||||||
if (packet->image or (packet->codec_type != AVMEDIA_TYPE_VIDEO)) {
|
if (packet->image or (packet->codec_type != AVMEDIA_TYPE_VIDEO)) {
|
||||||
packet->unlock();
|
delete packet_lock;
|
||||||
return true; // Don't need decode
|
return true; // Don't need decode
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2788,7 +2810,7 @@ bool Monitor::Decode() {
|
||||||
} // end if have image
|
} // end if have image
|
||||||
} // end if did decoding
|
} // end if did decoding
|
||||||
packet->decoded = true;
|
packet->decoded = true;
|
||||||
packet->unlock(); // unlock will also signal
|
delete packet_lock;
|
||||||
|
|
||||||
shared_data->signal = ( capture_image and signal_check_points ) ? CheckSignal(capture_image) : true;
|
shared_data->signal = ( capture_image and signal_check_points ) ? CheckSignal(capture_image) : true;
|
||||||
shared_data->last_write_index = index;
|
shared_data->last_write_index = index;
|
||||||
|
@ -3112,7 +3134,7 @@ int Monitor::PrimeCapture() {
|
||||||
audio_fifo = new Fifo(shared_data->audio_fifo_path, true);
|
audio_fifo = new Fifo(shared_data->audio_fifo_path, true);
|
||||||
}
|
}
|
||||||
} // end if rtsp_server
|
} // end if rtsp_server
|
||||||
decoder = new DecoderThread(this);
|
if (decoding_enabled) decoder = new DecoderThread(this);
|
||||||
} else {
|
} else {
|
||||||
Debug(2, "Failed to prime %d", ret);
|
Debug(2, "Failed to prime %d", ret);
|
||||||
}
|
}
|
||||||
|
@ -3140,25 +3162,25 @@ Monitor::Orientation Monitor::getOrientation() const { return orientation; }
|
||||||
// So this should be done as the first task in the analysis thread startup.
|
// So this should be done as the first task in the analysis thread startup.
|
||||||
// This function is deprecated.
|
// This function is deprecated.
|
||||||
void Monitor::get_ref_image() {
|
void Monitor::get_ref_image() {
|
||||||
ZMPacket *snap = nullptr;
|
ZMLockedPacket *snap_lock = nullptr;
|
||||||
|
|
||||||
if ( !analysis_it )
|
if ( !analysis_it )
|
||||||
analysis_it = packetqueue.get_video_it(true);
|
analysis_it = packetqueue.get_video_it(true);
|
||||||
|
|
||||||
while (
|
while (
|
||||||
(
|
(
|
||||||
!( snap = packetqueue.get_packet(analysis_it))
|
!( snap_lock = packetqueue.get_packet(analysis_it))
|
||||||
or
|
or
|
||||||
( snap->codec_type != AVMEDIA_TYPE_VIDEO )
|
( snap_lock->packet_->codec_type != AVMEDIA_TYPE_VIDEO )
|
||||||
or
|
or
|
||||||
! snap->image
|
! snap_lock->packet_->image
|
||||||
)
|
)
|
||||||
and !zm_terminate) {
|
and !zm_terminate) {
|
||||||
|
|
||||||
Debug(1, "Waiting for capture daemon lastwriteindex(%d) lastwritetime(%d)",
|
Debug(1, "Waiting for capture daemon lastwriteindex(%d) lastwritetime(%d)",
|
||||||
shared_data->last_write_index, shared_data->last_write_time);
|
shared_data->last_write_index, shared_data->last_write_time);
|
||||||
if ( snap and ! snap->image ) {
|
if ( snap_lock and ! snap_lock->packet_->image ) {
|
||||||
snap->unlock();
|
delete snap_lock;
|
||||||
// can't analyse it anyways, incremement
|
// can't analyse it anyways, incremement
|
||||||
packetqueue.increment_it(analysis_it);
|
packetqueue.increment_it(analysis_it);
|
||||||
}
|
}
|
||||||
|
@ -3167,6 +3189,7 @@ void Monitor::get_ref_image() {
|
||||||
if ( zm_terminate )
|
if ( zm_terminate )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
ZMPacket *snap = snap_lock->packet_;
|
||||||
Debug(1, "get_ref_image: packet.stream %d ?= video_stream %d, packet image id %d packet image %p",
|
Debug(1, "get_ref_image: packet.stream %d ?= video_stream %d, packet image id %d packet image %p",
|
||||||
snap->packet.stream_index, video_stream_id, snap->image_index, snap->image );
|
snap->packet.stream_index, video_stream_id, snap->image_index, snap->image );
|
||||||
// Might not have been decoded yet FIXME
|
// Might not have been decoded yet FIXME
|
||||||
|
@ -3177,7 +3200,7 @@ void Monitor::get_ref_image() {
|
||||||
} else {
|
} else {
|
||||||
Debug(2, "Have no ref image about to unlock");
|
Debug(2, "Have no ref image about to unlock");
|
||||||
}
|
}
|
||||||
snap->unlock();
|
delete snap_lock;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<Group *> Monitor::Groups() {
|
std::vector<Group *> Monitor::Groups() {
|
||||||
|
|
|
@ -27,7 +27,6 @@ using namespace std;
|
||||||
AVPixelFormat target_format = AV_PIX_FMT_NONE;
|
AVPixelFormat target_format = AV_PIX_FMT_NONE;
|
||||||
|
|
||||||
ZMPacket::ZMPacket() :
|
ZMPacket::ZMPacket() :
|
||||||
lck(mutex,std::defer_lock),
|
|
||||||
keyframe(0),
|
keyframe(0),
|
||||||
in_frame(nullptr),
|
in_frame(nullptr),
|
||||||
out_frame(nullptr),
|
out_frame(nullptr),
|
||||||
|
|
|
@ -37,6 +37,8 @@ class Image;
|
||||||
class ZMPacket {
|
class ZMPacket {
|
||||||
public:
|
public:
|
||||||
|
|
||||||
|
std::mutex mutex_;
|
||||||
|
std::condition_variable condition_;
|
||||||
|
|
||||||
int keyframe;
|
int keyframe;
|
||||||
AVStream *stream; // Input stream
|
AVStream *stream; // Input stream
|
||||||
|
@ -68,43 +70,44 @@ class ZMPacket {
|
||||||
ZMPacket();
|
ZMPacket();
|
||||||
~ZMPacket();
|
~ZMPacket();
|
||||||
|
|
||||||
std::unique_lock<std::mutex> * lock() {
|
|
||||||
std::unique_lock<std::mutex> *lck = new std::unique_lock<std::mutex>(mutex);
|
|
||||||
Debug(4, "packet %d locked", this->image_index);
|
|
||||||
return lck;
|
|
||||||
};
|
|
||||||
std::unique_lock<std::mutex> * trylock() {
|
|
||||||
std::unique_lock<std::mutex> *lck = new std::unique_lock<std::mutex>(mutex, std::defer_lock);
|
|
||||||
Debug(4, "TryLocking packet %d", this->image_index);
|
|
||||||
if ( lck.try_lock() )
|
|
||||||
return lck;
|
|
||||||
delete lck;
|
|
||||||
return nullptr;
|
|
||||||
};
|
|
||||||
void unlock(std::unique_lock<std::mutex> *lck) {
|
|
||||||
Debug(4, "packet %d unlocked", this->image_index);
|
|
||||||
lck->unlock();
|
|
||||||
condition.notify_all();
|
|
||||||
};
|
|
||||||
void wait(std::unique_lock<std::mutex> *lck) {
|
|
||||||
Debug(4, "packet %d waiting", this->image_index);
|
|
||||||
// We already have a lock, but it's a recursive mutex.. so this may be ok
|
|
||||||
condition.wait(*lck);
|
|
||||||
}
|
|
||||||
AVFrame *get_out_frame(const AVCodecContext *ctx);
|
AVFrame *get_out_frame(const AVCodecContext *ctx);
|
||||||
int get_codec_imgsize() { return codec_imgsize; };
|
int get_codec_imgsize() { return codec_imgsize; };
|
||||||
};
|
};
|
||||||
|
|
||||||
class ZMLockedPacket : public ZMPacket {
|
class ZMLockedPacket {
|
||||||
public:
|
public:
|
||||||
std::mutex mutex_;
|
|
||||||
std::condition_variable condition_;
|
|
||||||
std::unique_lock<std::mutex> lck_;
|
|
||||||
ZMPacket *packet_;
|
ZMPacket *packet_;
|
||||||
|
std::unique_lock<std::mutex> lck_;
|
||||||
|
|
||||||
ZMLockedPacket(ZMPacket *p) : packet_(packet), lck_(mutex_) {
|
ZMLockedPacket(ZMPacket *p) :
|
||||||
|
packet_(p),
|
||||||
|
lck_(packet_->mutex_, std::defer_lock) {
|
||||||
|
}
|
||||||
|
~ZMLockedPacket() {
|
||||||
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
void lock() {
|
||||||
|
Debug(4, "locking packet %d", packet_->image_index);
|
||||||
|
lck_.lock();
|
||||||
|
Debug(4, "packet %d locked", packet_->image_index);
|
||||||
|
};
|
||||||
|
bool trylock() {
|
||||||
|
Debug(4, "TryLocking packet %d", packet_->image_index);
|
||||||
|
return lck_.try_lock();
|
||||||
|
};
|
||||||
|
void unlock() {
|
||||||
|
Debug(4, "packet %d unlocked", packet_->image_index);
|
||||||
|
lck_.unlock();
|
||||||
|
packet_->condition_.notify_all();
|
||||||
|
};
|
||||||
|
|
||||||
|
void wait() {
|
||||||
|
Debug(4, "packet %d waiting", packet_->image_index);
|
||||||
|
// We already have a lock, but it's a recursive mutex.. so this may be ok
|
||||||
|
packet_->condition_.wait(lck_);
|
||||||
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
#endif /* ZM_PACKET_H */
|
#endif /* ZM_PACKET_H */
|
||||||
|
|
|
@ -144,17 +144,19 @@ void PacketQueue::clearPackets(ZMPacket *add_packet) {
|
||||||
|
|
||||||
// First packet is special because we know it is a video keyframe and only need to check for lock
|
// First packet is special because we know it is a video keyframe and only need to check for lock
|
||||||
ZMPacket *zm_packet = *it;
|
ZMPacket *zm_packet = *it;
|
||||||
if ( zm_packet->trylock() ) {
|
ZMLockedPacket *lp = new ZMLockedPacket(zm_packet);
|
||||||
|
if ( lp->trylock() ) {
|
||||||
++it;
|
++it;
|
||||||
zm_packet->unlock();
|
delete lp;
|
||||||
|
|
||||||
// Since we have many packets in the queue, we should NOT be pointing at end so don't need to test for that
|
// Since we have many packets in the queue, we should NOT be pointing at end so don't need to test for that
|
||||||
while ( *it != add_packet ) {
|
while ( *it != add_packet ) {
|
||||||
zm_packet = *it;
|
zm_packet = *it;
|
||||||
if ( !zm_packet->trylock() ) {
|
lp = new ZMLockedPacket(zm_packet);
|
||||||
|
if ( !lp->trylock() ) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
zm_packet->unlock();
|
delete lp;
|
||||||
|
|
||||||
if ( is_there_an_iterator_pointing_to_packet(zm_packet) ) {
|
if ( is_there_an_iterator_pointing_to_packet(zm_packet) ) {
|
||||||
Warning("Found iterator at beginning of queue. Some thread isn't keeping up");
|
Warning("Found iterator at beginning of queue. Some thread isn't keeping up");
|
||||||
|
@ -200,7 +202,7 @@ void PacketQueue::clearPackets(ZMPacket *add_packet) {
|
||||||
return;
|
return;
|
||||||
} // end voidPacketQueue::clearPackets(ZMPacket* zm_packet)
|
} // end voidPacketQueue::clearPackets(ZMPacket* zm_packet)
|
||||||
|
|
||||||
ZMPacket* PacketQueue::popPacket( ) {
|
ZMLockedPacket* PacketQueue::popPacket( ) {
|
||||||
Debug(4, "pktQueue size %d", pktQueue.size());
|
Debug(4, "pktQueue size %d", pktQueue.size());
|
||||||
if ( pktQueue.empty() ) {
|
if ( pktQueue.empty() ) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
@ -222,14 +224,15 @@ ZMPacket* PacketQueue::popPacket( ) {
|
||||||
}
|
}
|
||||||
} // end foreach iterator
|
} // end foreach iterator
|
||||||
|
|
||||||
zm_packet->lock();
|
ZMLockedPacket *lp = new ZMLockedPacket (zm_packet);
|
||||||
|
lp->lock();
|
||||||
|
|
||||||
pktQueue.pop_front();
|
pktQueue.pop_front();
|
||||||
packet_counts[zm_packet->packet.stream_index] -= 1;
|
packet_counts[zm_packet->packet.stream_index] -= 1;
|
||||||
|
|
||||||
mutex.unlock();
|
mutex.unlock();
|
||||||
|
|
||||||
return zm_packet;
|
return lp;
|
||||||
} // popPacket
|
} // popPacket
|
||||||
|
|
||||||
|
|
||||||
|
@ -325,9 +328,9 @@ void PacketQueue::clear() {
|
||||||
while (!pktQueue.empty()) {
|
while (!pktQueue.empty()) {
|
||||||
ZMPacket *packet = pktQueue.front();
|
ZMPacket *packet = pktQueue.front();
|
||||||
// Someone might have this packet, but not for very long and since we have locked the queue they won't be able to get another one
|
// Someone might have this packet, but not for very long and since we have locked the queue they won't be able to get another one
|
||||||
packet->lock();
|
ZMLockedPacket lp(packet);
|
||||||
|
lp.lock();
|
||||||
pktQueue.pop_front();
|
pktQueue.pop_front();
|
||||||
packet->unlock();
|
|
||||||
delete packet;
|
delete packet;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -452,7 +455,7 @@ int PacketQueue::packet_count(int stream_id) {
|
||||||
|
|
||||||
|
|
||||||
// Returns a packet. Packet will be locked
|
// Returns a packet. Packet will be locked
|
||||||
ZMPacket *PacketQueue::get_packet(packetqueue_iterator *it) {
|
ZMLockedPacket *PacketQueue::get_packet(packetqueue_iterator *it) {
|
||||||
if ( deleting or zm_terminate )
|
if ( deleting or zm_terminate )
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
|
@ -477,16 +480,17 @@ ZMPacket *PacketQueue::get_packet(packetqueue_iterator *it) {
|
||||||
Error("Null p?!");
|
Error("Null p?!");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
ZMLockedPacket *lp = new ZMLockedPacket(p);
|
||||||
Debug(3, "get_packet %p image_index: %d, about to lock packet", p, p->image_index);
|
Debug(3, "get_packet %p image_index: %d, about to lock packet", p, p->image_index);
|
||||||
while (!(zm_terminate or deleting) and !p->trylock()) {
|
while (!(zm_terminate or deleting) and !lp->trylock()) {
|
||||||
Debug(3, "waiting on index %d. Queue size %d it == end? %d",
|
Debug(3, "waiting on index %d. Queue size %d it == end? %d",
|
||||||
p->image_index, pktQueue.size(), ( *it == pktQueue.end() ) );
|
p->image_index, pktQueue.size(), ( *it == pktQueue.end() ) );
|
||||||
ZM_DUMP_PACKET(p->packet, "");
|
ZM_DUMP_PACKET(p->packet, "");
|
||||||
condition.wait(lck);
|
condition.wait(lck);
|
||||||
}
|
}
|
||||||
Debug(2, "Locked packet, unlocking packetqueue mutex");
|
Debug(2, "Locked packet, unlocking packetqueue mutex");
|
||||||
return p;
|
return lp;
|
||||||
} // end ZMPacket *PacketQueue::get_packet(it)
|
} // end ZMLockedPacket *PacketQueue::get_packet(it)
|
||||||
|
|
||||||
bool PacketQueue::increment_it(packetqueue_iterator *it) {
|
bool PacketQueue::increment_it(packetqueue_iterator *it) {
|
||||||
Debug(2, "Incrementing %p, queue size %d, end? %d", it, pktQueue.size(), ((*it) == pktQueue.end()));
|
Debug(2, "Incrementing %p, queue size %d, end? %d", it, pktQueue.size(), ((*it) == pktQueue.end()));
|
||||||
|
|
|
@ -24,6 +24,7 @@
|
||||||
#include <mutex>
|
#include <mutex>
|
||||||
|
|
||||||
class ZMPacket;
|
class ZMPacket;
|
||||||
|
class ZMLockedPacket;
|
||||||
|
|
||||||
typedef std::list<ZMPacket *>::iterator packetqueue_iterator;
|
typedef std::list<ZMPacket *>::iterator packetqueue_iterator;
|
||||||
|
|
||||||
|
@ -52,7 +53,7 @@ class PacketQueue {
|
||||||
void setMaxVideoPackets(int p);
|
void setMaxVideoPackets(int p);
|
||||||
|
|
||||||
bool queuePacket(ZMPacket* packet);
|
bool queuePacket(ZMPacket* packet);
|
||||||
ZMPacket * popPacket();
|
ZMLockedPacket * popPacket();
|
||||||
bool popVideoPacket(ZMPacket* packet);
|
bool popVideoPacket(ZMPacket* packet);
|
||||||
bool popAudioPacket(ZMPacket* packet);
|
bool popAudioPacket(ZMPacket* packet);
|
||||||
unsigned int clear(unsigned int video_frames_to_keep, int stream_id);
|
unsigned int clear(unsigned int video_frames_to_keep, int stream_id);
|
||||||
|
@ -68,7 +69,7 @@ class PacketQueue {
|
||||||
|
|
||||||
bool increment_it(packetqueue_iterator *it);
|
bool increment_it(packetqueue_iterator *it);
|
||||||
bool increment_it(packetqueue_iterator *it, int stream_id);
|
bool increment_it(packetqueue_iterator *it, int stream_id);
|
||||||
ZMPacket *get_packet(packetqueue_iterator *);
|
ZMLockedPacket *get_packet(packetqueue_iterator *);
|
||||||
packetqueue_iterator *get_video_it(bool wait);
|
packetqueue_iterator *get_video_it(bool wait);
|
||||||
packetqueue_iterator *get_stream_it(int stream_id);
|
packetqueue_iterator *get_stream_it(int stream_id);
|
||||||
void free_it(packetqueue_iterator *);
|
void free_it(packetqueue_iterator *);
|
||||||
|
|
|
@ -1211,29 +1211,6 @@ int VideoStore::writeAudioFramePacket(ZMPacket *zm_packet) {
|
||||||
return 0;
|
return 0;
|
||||||
} // end int VideoStore::writeAudioFramePacket(AVPacket *ipkt)
|
} // end int VideoStore::writeAudioFramePacket(AVPacket *ipkt)
|
||||||
|
|
||||||
int VideoStore::write_packets(PacketQueue &queue) {
|
|
||||||
// Need to write out all the frames from the last keyframe?
|
|
||||||
// No... need to write out all frames from when the event began. Due to PreEventFrames, this could be more than since the last keyframe.
|
|
||||||
unsigned int packet_count = 0;
|
|
||||||
ZMPacket *queued_packet;
|
|
||||||
|
|
||||||
while ( ( queued_packet = queue.popPacket() ) ) {
|
|
||||||
AVPacket *avp = queued_packet->av_packet();
|
|
||||||
|
|
||||||
packet_count += 1;
|
|
||||||
//Write the packet to our video store
|
|
||||||
Debug(2, "Writing queued packet stream: %d KEY %d, remaining (%d)",
|
|
||||||
avp->stream_index, avp->flags & AV_PKT_FLAG_KEY, queue.size() );
|
|
||||||
int ret = this->writePacket( queued_packet );
|
|
||||||
if ( ret < 0 ) {
|
|
||||||
//Less than zero and we skipped a frame
|
|
||||||
}
|
|
||||||
delete queued_packet;
|
|
||||||
} // end while packets in the packetqueue
|
|
||||||
Debug(2, "Wrote %d queued packets", packet_count );
|
|
||||||
return packet_count;
|
|
||||||
} // end int VideoStore::write_packets( PacketQueue &queue ) {
|
|
||||||
|
|
||||||
int VideoStore::write_packet(AVPacket *pkt, AVStream *stream) {
|
int VideoStore::write_packet(AVPacket *pkt, AVStream *stream) {
|
||||||
pkt->pos = -1;
|
pkt->pos = -1;
|
||||||
pkt->stream_index = stream->index;
|
pkt->stream_index = stream->index;
|
||||||
|
|
Loading…
Reference in New Issue