mirror of
https://github.com/moonlight-stream/moonlight-common-c.git
synced 2025-08-18 01:15:46 +00:00
Add capability to combine video receive and decode thread
This commit is contained in:
parent
c829d9c742
commit
812f356868
@ -71,6 +71,7 @@ typedef struct _DECODER_RENDERER_CALLBACKS {
|
|||||||
DecoderRendererSetup setup;
|
DecoderRendererSetup setup;
|
||||||
DecoderRendererCleanup cleanup;
|
DecoderRendererCleanup cleanup;
|
||||||
DecoderRendererSubmitDecodeUnit submitDecodeUnit;
|
DecoderRendererSubmitDecodeUnit submitDecodeUnit;
|
||||||
|
int capabilities;
|
||||||
} DECODER_RENDERER_CALLBACKS, *PDECODER_RENDERER_CALLBACKS;
|
} DECODER_RENDERER_CALLBACKS, *PDECODER_RENDERER_CALLBACKS;
|
||||||
|
|
||||||
// This callback initializes the audio renderer
|
// This callback initializes the audio renderer
|
||||||
|
@ -29,7 +29,9 @@ typedef struct _BUFFER_DESC {
|
|||||||
|
|
||||||
/* Init */
|
/* Init */
|
||||||
void initializeVideoDepacketizer(int pktSize) {
|
void initializeVideoDepacketizer(int pktSize) {
|
||||||
LbqInitializeLinkedBlockingQueue(&decodeUnitQueue, 15);
|
if ((VideoCallbacks.capabilities & CAPABILITY_DIRECT_SUBMIT) == 0) {
|
||||||
|
LbqInitializeLinkedBlockingQueue(&decodeUnitQueue, 15);
|
||||||
|
}
|
||||||
nominalPacketDataLength = pktSize - sizeof(NV_VIDEO_PACKET);
|
nominalPacketDataLength = pktSize - sizeof(NV_VIDEO_PACKET);
|
||||||
|
|
||||||
nextFrameNumber = 1;
|
nextFrameNumber = 1;
|
||||||
@ -91,7 +93,9 @@ static void freeDecodeUnitList(PLINKED_BLOCKING_QUEUE_ENTRY entry) {
|
|||||||
|
|
||||||
/* Cleanup video depacketizer and free malloced memory */
|
/* Cleanup video depacketizer and free malloced memory */
|
||||||
void destroyVideoDepacketizer(void) {
|
void destroyVideoDepacketizer(void) {
|
||||||
freeDecodeUnitList(LbqDestroyLinkedBlockingQueue(&decodeUnitQueue));
|
if ((VideoCallbacks.capabilities & CAPABILITY_DIRECT_SUBMIT) == 0) {
|
||||||
|
freeDecodeUnitList(LbqDestroyLinkedBlockingQueue(&decodeUnitQueue));
|
||||||
|
}
|
||||||
|
|
||||||
cleanupAvcFrameState();
|
cleanupAvcFrameState();
|
||||||
}
|
}
|
||||||
@ -183,23 +187,34 @@ static void reassembleAvcFrame(int frameNumber) {
|
|||||||
nalChainHead = NULL;
|
nalChainHead = NULL;
|
||||||
nalChainDataLength = 0;
|
nalChainDataLength = 0;
|
||||||
|
|
||||||
if (LbqOfferQueueItem(&decodeUnitQueue, qdu, &qdu->entry) == LBQ_BOUND_EXCEEDED) {
|
if ((VideoCallbacks.capabilities & CAPABILITY_DIRECT_SUBMIT) == 0) {
|
||||||
Limelog("Video decode unit queue overflow\n");
|
if (LbqOfferQueueItem(&decodeUnitQueue, qdu, &qdu->entry) == LBQ_BOUND_EXCEEDED) {
|
||||||
|
Limelog("Video decode unit queue overflow\n");
|
||||||
|
|
||||||
// Clear frame state and wait for an IDR
|
// Clear frame state and wait for an IDR
|
||||||
nalChainHead = qdu->decodeUnit.bufferList;
|
nalChainHead = qdu->decodeUnit.bufferList;
|
||||||
nalChainDataLength = qdu->decodeUnit.fullLength;
|
nalChainDataLength = qdu->decodeUnit.fullLength;
|
||||||
dropAvcFrameState();
|
dropAvcFrameState();
|
||||||
|
|
||||||
// Free the DU
|
// Free the DU
|
||||||
free(qdu);
|
free(qdu);
|
||||||
|
|
||||||
// Flush the decode unit queue
|
// Flush the decode unit queue
|
||||||
freeDecodeUnitList(LbqFlushQueueItems(&decodeUnitQueue));
|
freeDecodeUnitList(LbqFlushQueueItems(&decodeUnitQueue));
|
||||||
|
|
||||||
// FIXME: Get proper lower bound
|
// FIXME: Get proper lower bound
|
||||||
connectionSinkTooSlow(0, frameNumber);
|
connectionSinkTooSlow(0, frameNumber);
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
int ret = VideoCallbacks.submitDecodeUnit(&qdu->decodeUnit);
|
||||||
|
|
||||||
|
freeQueuedDecodeUnit(qdu);
|
||||||
|
|
||||||
|
if (ret == DR_NEED_IDR) {
|
||||||
|
Limelog("Request IDR frame on behalf of DR\n");
|
||||||
|
requestIdrOnDemand();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Notify the control connection
|
// Notify the control connection
|
||||||
|
@ -150,7 +150,9 @@ int readFirstFrame(void) {
|
|||||||
void stopVideoStream(void) {
|
void stopVideoStream(void) {
|
||||||
PltInterruptThread(&udpPingThread);
|
PltInterruptThread(&udpPingThread);
|
||||||
PltInterruptThread(&receiveThread);
|
PltInterruptThread(&receiveThread);
|
||||||
PltInterruptThread(&decoderThread);
|
if ((VideoCallbacks.capabilities & CAPABILITY_DIRECT_SUBMIT) == 0) {
|
||||||
|
PltInterruptThread(&decoderThread);
|
||||||
|
}
|
||||||
|
|
||||||
if (firstFrameSocket != INVALID_SOCKET) {
|
if (firstFrameSocket != INVALID_SOCKET) {
|
||||||
closesocket(firstFrameSocket);
|
closesocket(firstFrameSocket);
|
||||||
@ -163,11 +165,15 @@ void stopVideoStream(void) {
|
|||||||
|
|
||||||
PltJoinThread(&udpPingThread);
|
PltJoinThread(&udpPingThread);
|
||||||
PltJoinThread(&receiveThread);
|
PltJoinThread(&receiveThread);
|
||||||
PltJoinThread(&decoderThread);
|
if ((VideoCallbacks.capabilities & CAPABILITY_DIRECT_SUBMIT) == 0) {
|
||||||
|
PltJoinThread(&decoderThread);
|
||||||
|
}
|
||||||
|
|
||||||
PltCloseThread(&udpPingThread);
|
PltCloseThread(&udpPingThread);
|
||||||
PltCloseThread(&receiveThread);
|
PltCloseThread(&receiveThread);
|
||||||
PltCloseThread(&decoderThread);
|
if ((VideoCallbacks.capabilities & CAPABILITY_DIRECT_SUBMIT) == 0) {
|
||||||
|
PltCloseThread(&decoderThread);
|
||||||
|
}
|
||||||
|
|
||||||
VideoCallbacks.cleanup();
|
VideoCallbacks.cleanup();
|
||||||
}
|
}
|
||||||
@ -191,9 +197,11 @@ int startVideoStream(void* rendererContext, int drFlags) {
|
|||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
err = PltCreateThread(DecoderThreadProc, NULL, &decoderThread);
|
if ((VideoCallbacks.capabilities & CAPABILITY_DIRECT_SUBMIT) == 0) {
|
||||||
if (err != 0) {
|
err = PltCreateThread(DecoderThreadProc, NULL, &decoderThread);
|
||||||
return err;
|
if (err != 0) {
|
||||||
|
return err;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ServerMajorVersion == 3) {
|
if (ServerMajorVersion == 3) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user