From 7c4f88b596e6a46387d1a8372c043ec627d1ff2e Mon Sep 17 00:00:00 2001 From: Steffen Pohle Date: Fri, 19 Apr 2024 01:07:01 +0200 Subject: [PATCH] fixed alot of bugs.. --- checkdumpfile.cc | 154 ++++++++++++++++++++++++++++++++++++++++--- convert.cc | 8 ++- debug.cc | 25 +++++++ debug.h | 1 + output.cc | 5 +- videodev-dumpfile.cc | 42 +++++++++--- videodev-svbcam.cc | 10 ++- videodev-svbcam.h | 2 +- videodev.cc | 27 ++++++++ videodev.h | 2 + videoframe.cc | 1 + 11 files changed, 248 insertions(+), 29 deletions(-) diff --git a/checkdumpfile.cc b/checkdumpfile.cc index cf3e693..a194c4a 100644 --- a/checkdumpfile.cc +++ b/checkdumpfile.cc @@ -27,25 +27,142 @@ std::string convert_from_pixelformat (uint32_t fmt) { -int main(int argc, char **argv) { - int fd; +int fixfile(char *src, char *dest) { + int fd, fd2; int cnt = 0; char *inbuf = NULL; int inbufsize = 0; + int frmcnt = 0; uint32_t i; - uint32_t size; + uint32_t size, size2; + + printf ("fix file:'%s' output file:'%s'\n", src, dest); + + if ((fd = open (src, O_RDONLY)) < 0) { + printf ("could not open input file: %s\n", strerror(errno)); + return -1; + } + + if ((fd2 = open (dest, O_WRONLY | O_CREAT | O_TRUNC), S_IRUSR | S_IWUSR) < 0) { + printf ("could not open output file: %s\n", strerror(errno)); + close (fd); + return -1; + } + + // + // read header w, h, pixfmt + if (read (fd, &i, 4) != 4) { + printf ("could not read all bytes.\n"); + close (fd); + return -1; + } + if (write (fd2, &i, 4) != 4) { + printf ("could not write all bytes.\n"); + close (fd2); + close (fd); + return -1; + } + printf (" Width: %d\n", ntohl(i)); + + if (read (fd, &i, 4) != 4) { + printf ("could not read all bytes.\n"); + close (fd); + return -1; + } + if (write (fd2, &i, 4) != 4) { + printf ("could not write all bytes.\n"); + close (fd2); + close (fd); + return -1; + } + printf (" Height: %d\n", ntohl(i)); - if (argc != 2) { - printf ("please give a file name as parameter.\n"); - printf ("checkdumpfile FILE\n"); - printf ("\n"); + if (read (fd, &i, 4) != 4) { + printf ("could not read all bytes.\n"); + close (fd); return -1; } + if (write (fd2, &i, 4) != 4) { + printf ("could not write all bytes.\n"); + close (fd2); + close (fd); + return -1; + } + printf(" Pixfmt: %s\n", convert_from_pixelformat(ntohl(i)).c_str()); - printf ("reading file :'%s'\n", argv[1]); - if ((fd = open (argv[1], O_RDONLY)) < 0) { + // + // read frame + while (read (fd, &size, 4) == 4) { + size = ntohl(size); + size2 = htonl(size / 2); + if (write (fd2, &size2, 4) != 4) { + printf ("could not write framesize of frame %d.\n", frmcnt); + close (fd2); + close (fd); + return -1; + } + + if (read (fd, &i, 4) != 4) { + printf ("could not read all bytes.\n"); + close (fd); + return -1; + } + if (write (fd2, &i, 4) != 4) { + printf ("could not write timestamp of frame %d.\n", frmcnt); + close (fd2); + close (fd); + return -1; + } + i = ntohl(i); + + if (inbuf == NULL){ + inbuf = (char*) malloc (size); + inbufsize = size; + } + else if (inbufsize < size) { + inbuf = (char*)realloc(inbuf, size); + inbufsize = size; + } + + if (inbuf == NULL) { + printf ("Error could not allocate enough memory\n"); + close (fd); + return -1; + } + if (read (fd, inbuf, size) != size) { + printf ("could not read to next frame.\n"); + close (fd); + return -1; + } + if (write (fd2, inbuf, size/2) != size/2) { + printf ("could not write frame %d.\n", frmcnt); + close (fd2); + close (fd); + return -1; + } + + printf ("Frame: %-9d Timestamp:%-9d Size:%d\n", cnt++, i, size); + } + + close (fd); + close (fd2); + return 0; +} + + +int checkfile(char *src) { + uint32_t i; + uint32_t size; + int fd; + int cnt = 0; + char *inbuf = NULL; + int inbufsize = 0; + + printf ("reading file :'%s'\n", src); + + if ((fd = open (src, O_RDONLY)) < 0) { printf ("could not open file: %s\n", strerror(errno)); } @@ -111,5 +228,22 @@ int main(int argc, char **argv) { close (fd); return 0; -} +}; + +int main(int argc, char **argv) { + + if (argc == 2) { + checkfile(argv[1]); + } + else if (argc == 3) { + fixfile(argv[1], argv[2]); + } + else { + printf ("please give a file name as parameter.\n"); + printf ("checkdumpfile FILE to check file\n"); + printf ("checkdumpfile SRCFILE DESTFILE to fix file\n"); + printf ("\n"); + } + return 0; +} diff --git a/convert.cc b/convert.cc index 9d5c795..1235455 100644 --- a/convert.cc +++ b/convert.cc @@ -532,20 +532,22 @@ int PixCopy(unsigned char *srcdata, uint32_t srcpixfmt, int srcw, int srch, dsize = (*dsth) * (*dstw) * bytesperpixel; if ((*dstsize) < dsize || (*dstdataptr) == NULL) { *dstdataptr = (unsigned char*) realloc (*dstdataptr, dsize); + if (*dstdataptr == NULL) { + errorexit((char*)"%s:%d could not realloc memory. dsize:%d error:%s\n", __FILE__, __LINE__, dsize, strerror(errno)); + } *dstsize = dsize; printf ("%s:%d reallocate memory for destination raw image\n", __FILE__, __LINE__); } unsigned char *dptr, *sptr; - int y, dy, x, dx; + int y, dy, x; // debug_drawraw(srcdata, srcpixfmt, srcw, srch); for (y = regiony & (~1), dy = 0; dy < *dsth && y < srch; y++, dy++) { x = regionx & (~1); dptr = (*dstdataptr) + bytesperpixel * (dy * *dstw); sptr = (srcdata) + bytesperpixel * ( y * srcw + x); - for (dx = (*dstw*bytesperpixel); dx > 0; dx--, dptr++, sptr++) - *dptr = *sptr; + memcpy (dptr, sptr, *dstw * bytesperpixel); } if (config.show_debugwin) debug_drawraw(*dstdataptr, srcpixfmt, *dstw, *dsth); diff --git a/debug.cc b/debug.cc index 0d43dc2..b1f8a6b 100644 --- a/debug.cc +++ b/debug.cc @@ -6,6 +6,7 @@ #include #include #include +#include #include "debug.h" #include "convert.h" @@ -144,3 +145,27 @@ void debug_drawraw(unsigned char *data, int pixfmt, int w, int h) { debug_unlock_mutex(); }; + +#define BT_BUF_SIZE 100 +void debug_backtrace () { + unsigned int nptrs; + void *buffer[BT_BUF_SIZE]; + char **strings; + + nptrs = backtrace(buffer, BT_BUF_SIZE); + printf("backtrace() returned %d addresses\n", nptrs); + + /* The call backtrace_symbols_fd(buffer, nptrs, STDOUT_FILENO) + * would produce similar output to the following: */ + + strings = backtrace_symbols(buffer, nptrs); + if (strings == NULL) { + perror("backtrace_symbols"); + exit(EXIT_FAILURE); + } + + for (size_t j = 0; j < nptrs; j++) + printf("%s\n", strings[j]); + free(strings); +}; + diff --git a/debug.h b/debug.h index 9e52f20..e4e7518 100644 --- a/debug.h +++ b/debug.h @@ -28,6 +28,7 @@ extern void debug_tofile(char *fname, int isheader, char *fmt, ...); extern inline void debug_lock_mutex(); extern inline void debug_unlock_mutex(); void debug_drawraw(unsigned char *data, int pixfmt, int w, int h); +void debug_backtrace (); #endif diff --git a/output.cc b/output.cc index 38c9533..0ea44f4 100644 --- a/output.cc +++ b/output.cc @@ -204,7 +204,7 @@ void Output::Thread() { } if (outputser) outputser->setObserver((char *)"FIXME:read username from OS"); if (outputser) outputser->setTelescope((char *)"FIXME:not implemented yet"); - if (outputser) outputser->setInstrument((char *)"FIXME:just read device from dirver"); + if (outputser) outputser->setInstrument((char *)"FIXME:just read device from driver"); if (outputser) outputser->setNumberOfFrames(0); if (outputser) outputser->writeHeader(); } @@ -226,12 +226,13 @@ void Output::Thread() { outputser->appendFrame(inFrame.data); } } + inFrameNew = 0; } UnLockInMutex(); - usleep (10000); // sleep 10ms + usleep (1000); // sleep 10ms } } diff --git a/videodev-dumpfile.cc b/videodev-dumpfile.cc index 9e45334..185bd51 100644 --- a/videodev-dumpfile.cc +++ b/videodev-dumpfile.cc @@ -249,6 +249,8 @@ int VideoDev_Dumpfile::Grab(VideoFrameRaw *vf) { LockMutex(); vf->CopyFrom(pixformat, w, h, inframe_size, inframe); + UnLockMutex(); + ctrl = vidctrls.begin(); if (ctrl->value == 0) { // fixed framesize -> calculate frames @@ -262,10 +264,10 @@ int VideoDev_Dumpfile::Grab(VideoFrameRaw *vf) { fixedframesize = 4 * w * h; break; case(V4L2_PIX_FMT_SGRBG8): - fixedframesize = 2 * w * h; + fixedframesize = 1 * w * h; break; case(V4L2_PIX_FMT_SGRBG16): - fixedframesize = 4 * w * h; + fixedframesize = 2 * w * h; break; default: ctrl->max = 0; @@ -279,11 +281,11 @@ int VideoDev_Dumpfile::Grab(VideoFrameRaw *vf) { if (ctrl->value != -1) ctrl->value++; - UnLockMutex(); - // // read next frame + LockMutex(); ReadFrame(); + UnLockMutex(); return VDEV_STATUS_OK; } @@ -337,7 +339,7 @@ int VideoDev_Dumpfile::ReadFrame() { // allocate memory and read frame if (inframe == NULL) { Close(); - printf ("%s:%d cloud not allocate enought memory\n", __FILE__, __LINE__); + printf ("%s:%d could not allocate enough memory\n", __FILE__, __LINE__); return VDEV_CBSTATUS_ERROR; } if (read (fd, inframe, inframe_size) != inframe_size) { @@ -360,20 +362,40 @@ int VideoDev_Dumpfile::ReadFrame() { */ int VideoDev_Dumpfile::SetDevCtrl(unsigned int id, int value) { std::list::iterator ctrl; + int framerest; + off_t newfilepos = 0; printf ("%s:%d VideoDev_Dumpfile::SetDevCtrl Set Offset to %d id:%d fixedframesize:%d\n", __FILE__, __LINE__, value, id, fixedframesize); + struct timeval curtv; if (id == 1) { ctrl = vidctrls.begin(); if (value != ctrl->value && value < ctrl->max) { - filepos = SIZE_DUMPHEADER + (value * (SIZE_FRAMEHEADER + fixedframesize)); - ctrl->value = value; - if (lseek (fd, filepos, SEEK_SET) < 0) { + filepos = SIZE_DUMPHEADER + ((off_t)value * (SIZE_FRAMEHEADER + (off_t)fixedframesize)); + printf ("%s:%d filepos:%ld\n", __FILE__, __LINE__, filepos); + + if ((newfilepos = lseek (fd, filepos, SEEK_SET)) < 0) { printf ("%s:%d ******* lseek error:%s\n", __FILE__, __LINE__, strerror(errno)); } + else { + framerest = (newfilepos - SIZE_DUMPHEADER)%(SIZE_FRAMEHEADER + fixedframesize); + ctrl->value = (newfilepos - SIZE_DUMPHEADER)/(SIZE_FRAMEHEADER + fixedframesize); + if (ctrl->value != value || framerest != 0) { + printf ("%s:%d could not set file to correct position. ctrl->value:%d value:%d Framerest:%d\n", __FILE__, __LINE__, ctrl->value, value, framerest); + } + else { + // + // read first frame + ReadFrame(); + gettimeofday(&curtv, NULL); + starttv.tv_sec = curtv.tv_sec - (inframe_nexttime/1000); + } + } } - else printf ("%s:%d could not set video position (ctrl->value:%d value:%d max:%d)\n", - __FILE__, __LINE__, ctrl->value, value, ctrl->max); + + // else printf ("%s:%d could not set video position (ctrl->value:%d value:%d max:%d)\n", + // __FILE__, __LINE__, ctrl->value, value, ctrl->max); } + return VDEV_STATUS_OK; }; diff --git a/videodev-svbcam.cc b/videodev-svbcam.cc index 40f63ee..164e87e 100644 --- a/videodev-svbcam.cc +++ b/videodev-svbcam.cc @@ -289,8 +289,11 @@ int VideoDev_SVBCam::CaptureStart() { // // allocate memory for frame data if (inframe != NULL) free (inframe); - inframe_size = 4 * inframe_w * inframe_h; + inframe_size = get_bytesperpixel(inframe_pixfmt) * inframe_w * inframe_h; inframe = (unsigned char*) malloc(inframe_size); + if (inframe == NULL) { + errorexit ((char*)"%s:%d could not allocate memory for framebuffer. Error:%s\n", __FILE__, __LINE__, strerror(errno)); + } pixelformat = inframe_pixfmt; return VDEV_STATUS_OK; @@ -326,7 +329,7 @@ int VideoDev_SVBCam::CaptureStop() { * Return code VDEV_STATUS_AGAIN is not an error. There was no video image ready to read. */ // FIXME: SVBGetVideoData needs to be outside of Lock/UnLockMutex - using inside thread inbuffer -int VideoDev_SVBCam::Grab(VideoFrameRaw *vf) { +int VideoDev_SVBCam::Grab(VideoFrameRaw *vfr) { int err; if (inframe == NULL) return VDEV_STATUS_ERROR; @@ -341,7 +344,8 @@ int VideoDev_SVBCam::Grab(VideoFrameRaw *vf) { } } LockMutex(); - vf->CopyFrom(inframe_pixfmt, inframe_w, inframe_h, inframe_size, inframe); + + vfr->CopyFrom(inframe_pixfmt, inframe_w, inframe_h, inframe_size, inframe); UnLockMutex(); return VDEV_STATUS_OK; diff --git a/videodev-svbcam.h b/videodev-svbcam.h index 7a1ce44..01fbe01 100644 --- a/videodev-svbcam.h +++ b/videodev-svbcam.h @@ -44,7 +44,7 @@ private: ConvertData cdata; int camid; - int Grab(VideoFrameRaw *vf); + int Grab(VideoFrameRaw *vfr); int Open(); int Close(); int CaptureStart(); diff --git a/videodev.cc b/videodev.cc index 29ba340..e50307d 100644 --- a/videodev.cc +++ b/videodev.cc @@ -29,6 +29,7 @@ #include "convert.h" + VideoDev::VideoDev() { printf ("%s:%d %s\n", __FILE__, __LINE__, __FUNCTION__); conf_device = ""; @@ -235,3 +236,29 @@ list VideoDev::GetCtrlsMinMaxValue() { }; +int VideoDev::get_bytesperpixel (uint32_t pixfmt) { + int bytesperpixel = 4; + + switch (pixfmt) { + case (V4L2_PIX_FMT_SGRBG8): + bytesperpixel = 1; + break; + case (V4L2_PIX_FMT_SGRBG16): + bytesperpixel = 2; + break; + case (V4L2_PIX_FMT_BGR32): + case (V4L2_PIX_FMT_RGB32): + bytesperpixel = 4; + break; + case (V4L2_PIX_FMT_BGR24): + case (V4L2_PIX_FMT_RGB24): + bytesperpixel = 3; + break; + default: + errorexit((char*)"%s:%d unsupported pixelformat %s\n", convert_from_pixelformat(pixfmt).c_str()); + break; + } + return bytesperpixel; +} + + diff --git a/videodev.h b/videodev.h index 03271e0..2116ae8 100644 --- a/videodev.h +++ b/videodev.h @@ -136,6 +136,8 @@ public: VideoDev(); virtual ~VideoDev(); + static int get_bytesperpixel (uint32_t pixfmt); + void SetConfig(std::string dev, int w, int h, std::string format, std::string parameter, gboolean (*callback_func)(gpointer data)); void ThreadProcess(); void Stop(); diff --git a/videoframe.cc b/videoframe.cc index d7bdcea..f26d6b1 100644 --- a/videoframe.cc +++ b/videoframe.cc @@ -72,6 +72,7 @@ int VideoFrameRaw::ReAlloc(int newsize) { else if (size < newsize || size > newsize) { if ((newdata = (unsigned char*) realloc (data, newsize)) == NULL) { free (data); + data = NULL; size = 0; return -1; }