Index: conf.c =================================================================== --- conf.c (revision 484) +++ conf.c (working copy) @@ -205,6 +205,22 @@ print_bool }, { + "disable_detection", + "# Disable motion detection (default: off)", + 0, + CONF_OFFSET(disable_detection), + copy_bool, + print_bool + }, + { + "jpeg_passthru", + "# no process jpeg stream and passthru and stream out. (default: off)", + 0, + CONF_OFFSET(jpeg_passthru), + copy_bool, + print_bool + }, + { "logfile", "# Use a file to save logs messages, if not defined stderr and syslog is used. (default: not defined)", 1, @@ -212,7 +228,6 @@ copy_string, print_string }, - { "videodevice", "\n###########################################################\n" @@ -1488,12 +1503,14 @@ * if necessary. This is accomplished by calling mystrcpy(); * see this function for more information. */ - while ((c = getopt(conf->argc, conf->argv, "c:d:hns?pl:")) != EOF) + while ((c = getopt(conf->argc, conf->argv, "c:d:hmns?pl:")) != EOF) switch (c) { case 'c': if (thread == -1) strcpy(cnt->conf_filename, optarg); break; + case 'm': + conf->disable_detection = 1; case 'n': cnt->daemon = 0; break; @@ -2199,6 +2216,7 @@ printf("-d level\t\tDebug mode.\n"); printf("-p process_id_file\tFull path and filename of process id file (pid file).\n"); printf("-l log file \t\tFull path and filename of log file.\n"); + printf("-m\t\tMotion detection disabled.\n"); printf("-h\t\t\tShow this screen.\n"); printf("\n"); printf("Motion is configured using a config file only. If none is supplied,\n"); Index: conf.h =================================================================== --- conf.h (revision 484) +++ conf.h (working copy) @@ -21,6 +21,8 @@ struct config { char *log_file; int setup_mode; + int disable_detection; + int jpeg_passthru; int width; int height; int quality; Index: motion.c =================================================================== --- motion.c (revision 484) +++ motion.c (working copy) @@ -698,6 +698,7 @@ cnt->imgs.ref = mymalloc(cnt->imgs.size); cnt->imgs.out = mymalloc(cnt->imgs.size); memset(cnt->imgs.out, 0, cnt->imgs.size); + cnt->imgs.image_original = mymalloc(3 * cnt->imgs.width * cnt->imgs.height); /* contains the moving objects of ref. frame */ cnt->imgs.ref_dyn = mymalloc(cnt->imgs.motionsize * sizeof(cnt->imgs.ref_dyn)); @@ -964,6 +965,11 @@ cnt->imgs.image_virgin = NULL; } + if (cnt->imgs.image_original) { + free(cnt->imgs.image_original); + cnt->imgs.image_original = NULL; + } + if (cnt->imgs.labels) { free(cnt->imgs.labels); cnt->imgs.labels = NULL; @@ -1077,6 +1083,9 @@ goto err; + if (cnt->conf.disable_detection) + motion_log(LOG_INFO, 0, "%s: Motion detection DISABLED", __FUNCTION__); + /* Initialize the double sized characters if needed. */ if (cnt->conf.text_double) text_size_factor = 2; @@ -1133,6 +1142,12 @@ /***** MOTION LOOP - PREPARE FOR NEW FRAME SECTION *****/ cnt->watchdog = WATCHDOG_TMO; + /* If jpeg_passthru is enabled, disable motion detection */ + /* BETTER LET USE FORCE THIS WITH disable_detection + if (cnt->conf.jpeg_passthru) + cnt->conf.disable_detection = 0; + */ + /* Get current time and preserver last time for frame interval calc. */ timebefore = timenow; gettimeofday(&tv1, NULL); @@ -1429,7 +1444,7 @@ * is called. */ if (cnt->process_thisframe) { - if (cnt->threshold && !cnt->pause) { + if (cnt->threshold && !cnt->conf.disable_detection) { /* if we've already detected motion and we want to see if there's * still motion, don't bother trying the fast one first. IF there's * motion, the alg_diff will trigger alg_diff_standard @@ -1615,7 +1630,7 @@ if (cnt->conf.text_changes) { char tmp[15]; - if (!cnt->pause) + if (!cnt->conf.disable_detection) sprintf(tmp, "%d", cnt->current_image->diffs); else sprintf(tmp, "-"); @@ -1680,7 +1695,7 @@ #ifdef HAVE_FFMPEG if (cnt->ffmpeg_output || (cnt->conf.useextpipe && cnt->extpipe)) { #else - if (cnt->conf.useextpipe && cnt->extpipe) { + if (cnt->conf.useextpipe && cnt->extpipe) { #endif /* Setup the postcap counter */ cnt->postcap = cnt->conf.post_capture; @@ -1690,6 +1705,7 @@ cnt->current_image->flags |= (IMAGE_TRIGGER | IMAGE_SAVE); motion_detected(cnt, cnt->video_dev, cnt->current_image); + } else if ((cnt->current_image->flags & IMAGE_MOTION) && (cnt->startup_frames == 0)) { /* Did we detect motion (like the cat just walked in :) )? * If so, ensure the motion is sustained if minimum_motion_frames @@ -1736,6 +1752,7 @@ /* we have motion in this frame, but not enought frames for trigger. Check postcap */ cnt->current_image->flags |= (IMAGE_POSTCAP | IMAGE_SAVE); cnt->postcap--; + if (debug_level >= CAMERA_DEBUG) motion_log(0, 0, "%s: post capture %d", __FUNCTION__, cnt->postcap); } else { Index: motion.h =================================================================== --- motion.h (revision 484) +++ motion.h (working copy) @@ -279,6 +279,8 @@ int image_ring_in; /* Index in image ring buffer we last added a image into */ int image_ring_out; /* Index in image ring buffer we want to process next time */ + unsigned char *image_original; /* Picture original from video device to use with passthru option */ + int image_original_size; /* Size of picture original from video device */ unsigned char *ref; /* The reference frame */ unsigned char *out; /* Picture buffer for motion images */ int *ref_dyn; /* Dynamic objects to be excluded from reference frame */ @@ -380,7 +382,6 @@ unsigned int lastrate; unsigned int startup_frames; unsigned int moved; - unsigned int pause; int missing_frame_counter; /* counts failed attempts to fetch picture frame from camera */ unsigned int lost_connection; Index: motion-dist.conf.in =================================================================== --- motion-dist.conf.in (revision 484) +++ motion-dist.conf.in (working copy) @@ -20,6 +20,8 @@ # Start in Setup-Mode, daemon disabled. (default: off) setup_mode off +# Disable motion detection (default: off) +disable_detection off # Use a file to save logs messages, if not defined stderr and syslog is used. (default: not defined) ;logfile @@ -472,6 +474,8 @@ # Default: not defined (Disabled) ; stream_authentication username:password +# no process jpeg stream and passthru and stream out. (default: off) +jpeg_passthru off ############################################################ # HTTP Based Control Index: webhttpd.c =================================================================== --- webhttpd.c (revision 484) +++ webhttpd.c (working copy) @@ -1090,12 +1090,12 @@ send_template_ini_client(client_socket, ini_template); sprintf(res, "<– back

Thread %hu" " Detection status %s\n", thread, thread, - (!cnt[thread]->running)? "NOT RUNNING": (cnt[thread]->pause)? "PAUSE":"ACTIVE"); + (!cnt[thread]->running)? "NOT RUNNING": (cnt[thread]->conf.disable_detection)? "PAUSE":"ACTIVE"); send_template(client_socket, res); send_template_end_client(client_socket); } else { sprintf(res, "Thread %hu Detection status %s\n", thread, - (!cnt[thread]->running)? "NOT RUNNING": (cnt[thread]->pause)? "PAUSE":"ACTIVE"); + (!cnt[thread]->running)? "NOT RUNNING": (cnt[thread]->conf.disable_detection)? "PAUSE":"ACTIVE"); send_template_ini_client_raw(client_socket); send_template_raw(client_socket, res); } @@ -1114,10 +1114,10 @@ if (thread == 0) { do { - cnt[i]->pause = 0; + cnt[i]->conf.disable_detection = 0; } while (cnt[++i]); } else { - cnt[thread]->pause = 0; + cnt[thread]->conf.disable_detection = 0; } if (cnt[0]->conf.webcontrol_html_output) { @@ -1146,10 +1146,10 @@ if (thread == 0) { do { - cnt[i]->pause = 1; + cnt[i]->conf.disable_detection = 1; } while (cnt[++i]); } else { - cnt[thread]->pause = 1; + cnt[thread]->conf.disable_detection = 1; } if (cnt[0]->conf.webcontrol_html_output) { Index: stream.c =================================================================== --- stream.c (revision 484) +++ stream.c (working copy) @@ -1102,9 +1102,15 @@ /* update our working pointer to point past header */ wptr += headlength; - /* create a jpeg image and place into tmpbuffer */ - tmpbuffer->size = put_picture_memory(cnt, wptr, cnt->imgs.size, image, - cnt->conf.stream_quality); + if (cnt->conf.jpeg_passthru) { + tmpbuffer->size = cnt->imgs.image_original_size; + memcpy(wptr, cnt->imgs.image_original, + tmpbuffer->size); + } else { + /* create a jpeg image and place into tmpbuffer */ + tmpbuffer->size = put_picture_memory(cnt, wptr, cnt->imgs.size, image, + cnt->conf.stream_quality); + } /* fill in the image length into the header */ imgsize = sprintf(len, "%9ld\r\n\r\n", tmpbuffer->size); Index: netcam.c =================================================================== --- netcam.c (revision 484) +++ netcam.c (working copy) @@ -2701,7 +2701,16 @@ */ if (setjmp(netcam->setjmp_buffer)) return NETCAM_GENERAL_ERROR | NETCAM_JPEG_CONV_ERROR; - + + /* if no detection and passthru enabled use the original image + * netcam->latest->content_length size + */ + if (netcam->cnt->conf.jpeg_passthru) { + cnt->imgs.image_original_size = netcam->latest->used; + memcpy(cnt->imgs.image_original, netcam->latest->ptr, netcam->latest->used); + return 0; + } + /* If there was no error, process the latest image buffer */ return netcam_proc_jpeg(netcam, image); } @@ -2731,12 +2740,10 @@ int retval; /* working var */ struct url_t url; /* for parsing netcam URL */ - if (debug_level > CAMERA_INFO) - motion_log(0, 0, "%s: entered netcam_start()", __FUNCTION__); - memset(&url, 0, sizeof(url)); - if (SETUP) - motion_log(LOG_INFO, 0, "%s: Camera thread starting...", __FUNCTION__); + + motion_log(LOG_INFO, 0, "%s: Network Camera thread starting... for url (%s)", + __FUNCTION__, cnt->conf.netcam_url); /* * Create a new netcam_context for this camera @@ -2748,6 +2755,11 @@ netcam = cnt->netcam; /* Just for clarity in remaining code */ netcam->cnt = cnt; /* Fill in the "parent" info */ + + if (netcam->cnt->conf.jpeg_passthru) + motion_log(LOG_INFO, 0, "%s: Jpeg Passthru ENABLED", __FUNCTION__); + + /* * Fill in our new netcam context with all known initial * values. @@ -2825,7 +2837,7 @@ netcam->connect_port = url.port; } - /* Get HTTP Mode (1.0 default, 1.0 Keep-Alive, 1.1) flag from config + /* Get HTTP Mode (1.0 default, 1.0 Keep-Alive, 1.1) flag from config * and report its stata for debug reasons. * The flags in the conf structure is read only and cannot be * unset if the Keep-Alive needs to be switched off (ie. netcam does Index: motion.1 =================================================================== --- motion.1 (revision 484) +++ motion.1 (working copy) @@ -17,6 +17,9 @@ .B \-h Show help screen. .TP +.B \-m +Disables motion detection. +.TP .B \-n Run in non-daemon mode. .TP @@ -95,6 +98,11 @@ .br Despeckle motion image using combinations of (E/e)rode or (D/d)ilate. And ending with optional (l)abeling. .TP +.B disable_detection boolean +Values: on, off / Default: off +.br +Disables motion detection. +.TP .B emulate_motion boolean Values: on, off / Default: off .br @@ -184,6 +192,12 @@ .br Enable or disable IPV6 for http control and stream. .TP +.B jpeg_passthru boolean +Values: on, off / Default: off +.br +Enable or disable process of jpeg stream, process means decompress jpeg image adquired from video device and convert to yup420 to let motion analyze it. +So enabling jpeg_passthru makes motion passthru jpeg images from source to stream out without touching it. +.TP .B lightswitch integer Values: 0 - 100 / Default: 0 (disabled) .br