Skip to content

Commit

Permalink
Introducing the epoll mechanism in video threads
Browse files Browse the repository at this point in the history
  • Loading branch information
wberube committed Sep 5, 2024
1 parent 3bf53b1 commit a0d42f5
Show file tree
Hide file tree
Showing 21 changed files with 378 additions and 404 deletions.
6 changes: 4 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ _* At the moment, only text, 24-bit and 32-bit RGB overlays are handled, matrici
[^9]: GK7202V300, GK7205V200/300 and GK7605V100
[^10]: Hi3516AV200 and Hi3519V101
[^11]: RV110\[3/7/8/9\] and RV1106\(G2/G3\)
[^12]: MSC313E, MSC316\[DC/DE/QE\] and MSC318
[^12]: MSC313E, MSC316\[DC/Q\] and MSC318
[^13]: SSC323, SSC325\(D/DE\) and SSC327\(D/DE/Q\)
[^14]: SSC33\[3/5/7\]\(DE\)
[^15]: SSC30K\[D/Q\], SSC336\[D/Q\], SSC338\[D/G/Q\] and SSC339G
Expand All @@ -70,9 +70,11 @@ _* At the moment, only text, 24-bit and 32-bit RGB overlays are handled, matrici

### Roadmap

- [ ] Audio adjustments (source, input gain, output volume)
- [ ] Motors and PTZ control
- [ ] ONVIF services
- [ ] Additional WebUI functionalities
- [ ] Motion detection reimplementation
- [ ] Hardware support improvement (older SoCs, general usage chips)
- [ ] Alternative audio codecs


Expand Down
74 changes: 35 additions & 39 deletions src/hal/hisi/v1_hal.c
Original file line number Diff line number Diff line change
Expand Up @@ -591,7 +591,9 @@ void v1_video_request_idr(char index)

int v1_video_snapshot_grab(char index, hal_jpegdata *jpeg)
{
int ret;
int ret, epollEvt;
struct epoll_event events[5], event = { .events = EPOLLIN|EPOLLET };
int epollFd = epoll_create1(0);

if (ret = v1_channel_bind(index)) {
HAL_DANGER("v1_venc", "Binding the encoder channel "
Expand All @@ -607,21 +609,15 @@ int v1_video_snapshot_grab(char index, hal_jpegdata *jpeg)
}

int fd = v1_venc.fnGetDescriptor(index);

struct timeval timeout = { .tv_sec = 2, .tv_usec = 0 };
fd_set readFds;
FD_ZERO(&readFds);
FD_SET(fd, &readFds);
ret = select(fd + 1, &readFds, NULL, NULL, &timeout);
if (ret < 0) {
HAL_DANGER("v1_venc", "Select operation failed!\n");
goto abort;
} else if (ret == 0) {
HAL_DANGER("v1_venc", "Capture stream timed out!\n");
event.data.fd = fd;
if (ret = epoll_ctl(epollFd, EPOLL_CTL_ADD, fd, &event)) {
HAL_DANGER("v1_venc", "Adding the encoder descriptor to "
"the polling set failed with %#x!\n", ret);
goto abort;
}

if (FD_ISSET(fd, &readFds)) {
epollEvt = epoll_wait(epollFd, events, 5, 2000);
for (int e = 0; e < epollEvt; e++) {
v1_venc_stat stat;
if (ret = v1_venc.fnQuery(index, &stat)) {
HAL_DANGER("v1_venc", "Querying the encoder channel "
Expand Down Expand Up @@ -672,6 +668,9 @@ int v1_video_snapshot_grab(char index, hal_jpegdata *jpeg)
v1_venc.fnFreeStream(index, &strm);
}

if (close(epollFd))
HAL_DANGER("v1_venc", "Closing the polling descriptor failed!\n");

v1_venc.fnStopReceiving(index);

v1_channel_unbind(index);
Expand All @@ -681,8 +680,14 @@ int v1_video_snapshot_grab(char index, hal_jpegdata *jpeg)

void *v1_video_thread(void)
{
int ret;
int maxFd = 0;
int ret, epollEvt;
struct epoll_event events[5], event = { .events = EPOLLIN|EPOLLET };
int epollFd = epoll_create1(0);

if (epollFd < 0) {
HAL_DANGER("v1_venc", "Creating the polling descriptor failed!\n");
return (void*)0;
}

for (int i = 0; i < V1_VENC_CHN_NUM; i++) {
if (!v1_state[i].enable) continue;
Expand All @@ -691,41 +696,27 @@ void *v1_video_thread(void)
ret = v1_venc.fnGetDescriptor(i);
if (ret < 0) {
HAL_DANGER("v1_venc", "Getting the encoder descriptor failed with %#x!\n", ret);
return NULL;
return (void*)0;
}
v1_state[i].fileDesc = ret;

if (maxFd <= v1_state[i].fileDesc)
maxFd = v1_state[i].fileDesc;
event.data.fd = ret;
if (ret = epoll_ctl(epollFd, EPOLL_CTL_ADD, ret, &event)) {
HAL_DANGER("v1_venc", "Adding the encoder descriptor to "
"the polling set failed with %#x!\n", ret);
return (void*)0;
}
}

v1_venc_stat stat;
v1_venc_strm stream;
struct timeval timeout;
fd_set readFds;

while (keepRunning) {
FD_ZERO(&readFds);
for(int i = 0; i < V1_VENC_CHN_NUM; i++) {
if (!v1_state[i].enable) continue;
if (!v1_state[i].mainLoop) continue;
FD_SET(v1_state[i].fileDesc, &readFds);
}

timeout.tv_sec = 2;
timeout.tv_usec = 0;
ret = select(maxFd + 1, &readFds, NULL, NULL, &timeout);
if (ret < 0) {
HAL_DANGER("v1_venc", "Select operation failed!\n");
break;
} else if (ret == 0) {
HAL_WARNING("v1_venc", "Main stream loop timed out!\n");
continue;
} else {
epollEvt = epoll_wait(epollFd, events, 5, 2000);
for (int e = 0; e < epollEvt; e++) {
for (int i = 0; i < V1_VENC_CHN_NUM; i++) {
if (!v1_state[i].enable) continue;
if (!v1_state[i].mainLoop) continue;
if (FD_ISSET(v1_state[i].fileDesc, &readFds)) {
if (v1_state[i].fileDesc == events[e].data.fd) {
memset(&stream, 0, sizeof(stream));

if (ret = v1_venc.fnQuery(i, &stat)) {
Expand Down Expand Up @@ -783,10 +774,15 @@ void *v1_video_thread(void)
}
free(stream.packet);
stream.packet = NULL;
break;
}
}
}
}

if (close(epollFd))
HAL_DANGER("v1_venc", "Closing the polling descriptor failed!\n");

HAL_INFO("v1_venc", "Shutting down encoding thread...\n");
}

Expand Down
3 changes: 1 addition & 2 deletions src/hal/hisi/v1_hal.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,8 @@
#include "v1_vpss.h"

#include <fcntl.h>
#include <pthread.h>
#include <sys/epoll.h>
#include <sys/ioctl.h>
#include <sys/select.h>
#include <unistd.h>

extern char keepRunning;
Expand Down
72 changes: 35 additions & 37 deletions src/hal/hisi/v2_hal.c
Original file line number Diff line number Diff line change
Expand Up @@ -634,7 +634,9 @@ void v2_video_request_idr(char index)

int v2_video_snapshot_grab(char index, hal_jpegdata *jpeg)
{
int ret;
int ret, epollEvt;
struct epoll_event events[5], event = { .events = EPOLLIN|EPOLLET };
int epollFd = epoll_create1(0);

if (ret = v2_channel_bind(index)) {
HAL_DANGER("v2_venc", "Binding the encoder channel "
Expand All @@ -650,21 +652,15 @@ int v2_video_snapshot_grab(char index, hal_jpegdata *jpeg)
}

int fd = v2_venc.fnGetDescriptor(index);

struct timeval timeout = { .tv_sec = 2, .tv_usec = 0 };
fd_set readFds;
FD_ZERO(&readFds);
FD_SET(fd, &readFds);
ret = select(fd + 1, &readFds, NULL, NULL, &timeout);
if (ret < 0) {
HAL_DANGER("v2_venc", "Select operation failed!\n");
goto abort;
} else if (ret == 0) {
HAL_DANGER("v2_venc", "Capture stream timed out!\n");
event.data.fd = fd;
if (ret = epoll_ctl(epollFd, EPOLL_CTL_ADD, fd, &event)) {
HAL_DANGER("v2_venc", "Adding the encoder descriptor to "
"the polling set failed with %#x!\n", ret);
goto abort;
}

if (FD_ISSET(fd, &readFds)) {
epollEvt = epoll_wait(epollFd, events, 5, 2000);
for (int e = 0; e < epollEvt; e++) {
v2_venc_stat stat;
if (ret = v2_venc.fnQuery(index, &stat)) {
HAL_DANGER("v2_venc", "Querying the encoder channel "
Expand Down Expand Up @@ -715,6 +711,9 @@ int v2_video_snapshot_grab(char index, hal_jpegdata *jpeg)
v2_venc.fnFreeStream(index, &strm);
}

if (close(epollFd))
HAL_DANGER("v2_venc", "Closing the polling descriptor failed!\n");

v2_venc.fnFreeDescriptor(index);

v2_venc.fnStopReceiving(index);
Expand All @@ -726,8 +725,14 @@ int v2_video_snapshot_grab(char index, hal_jpegdata *jpeg)

void *v2_video_thread(void)
{
int ret;
int maxFd = 0;
int ret, epollEvt;
struct epoll_event events[5], event = { .events = EPOLLIN|EPOLLET };
int epollFd = epoll_create1(0);

if (epollFd < 0) {
HAL_DANGER("v2_venc", "Creating the polling descriptor failed!\n");
return (void*)0;
}

for (int i = 0; i < V2_VENC_CHN_NUM; i++) {
if (!v2_state[i].enable) continue;
Expand All @@ -736,12 +741,15 @@ void *v2_video_thread(void)
ret = v2_venc.fnGetDescriptor(i);
if (ret < 0) {
HAL_DANGER("v2_venc", "Getting the encoder descriptor failed with %#x!\n", ret);
return NULL;
return (void*)0;
}
v2_state[i].fileDesc = ret;

if (maxFd <= v2_state[i].fileDesc)
maxFd = v2_state[i].fileDesc;
event.data.fd = ret;
if (ret = epoll_ctl(epollFd, EPOLL_CTL_ADD, ret, &event)) {
HAL_DANGER("v2_venc", "Adding the encoder descriptor to "
"the polling set failed with %#x!\n", ret);
return (void*)0;
}
}

v2_venc_stat stat;
Expand All @@ -750,27 +758,12 @@ void *v2_video_thread(void)
fd_set readFds;

while (keepRunning) {
FD_ZERO(&readFds);
for(int i = 0; i < V2_VENC_CHN_NUM; i++) {
if (!v2_state[i].enable) continue;
if (!v2_state[i].mainLoop) continue;
FD_SET(v2_state[i].fileDesc, &readFds);
}

timeout.tv_sec = 2;
timeout.tv_usec = 0;
ret = select(maxFd + 1, &readFds, NULL, NULL, &timeout);
if (ret < 0) {
HAL_DANGER("v2_venc", "Select operation failed!\n");
break;
} else if (ret == 0) {
HAL_WARNING("v2_venc", "Main stream loop timed out!\n");
continue;
} else {
epollEvt = epoll_wait(epollFd, events, 5, 2000);
for (int e = 0; e < epollEvt; e++) {
for (int i = 0; i < V2_VENC_CHN_NUM; i++) {
if (!v2_state[i].enable) continue;
if (!v2_state[i].mainLoop) continue;
if (FD_ISSET(v2_state[i].fileDesc, &readFds)) {
if (v2_state[i].fileDesc == events[e].data.fd) {
memset(&stream, 0, sizeof(stream));

if (ret = v2_venc.fnQuery(i, &stat)) {
Expand Down Expand Up @@ -831,10 +824,15 @@ void *v2_video_thread(void)
}
free(stream.packet);
stream.packet = NULL;
break;
}
}
}
}

if (close(epollFd))
HAL_DANGER("v2_venc", "Closing the polling descriptor failed!\n");

HAL_INFO("v2_venc", "Shutting down encoding thread...\n");
}

Expand Down
3 changes: 1 addition & 2 deletions src/hal/hisi/v2_hal.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,8 @@
#include "v2_vpss.h"

#include <fcntl.h>
#include <pthread.h>
#include <sys/epoll.h>
#include <sys/ioctl.h>
#include <sys/select.h>
#include <unistd.h>

extern char keepRunning;
Expand Down
Loading

0 comments on commit a0d42f5

Please sign in to comment.