@@ -30,6 +30,39 @@ static void webu_stream_mjpeg_checkbuffers(struct webui_ctx *webui) {
3030
3131}
3232
33+ static void webu_stream_mjpeg_delay (struct webui_ctx * webui ) {
34+ /* Sleep required time to get to the user requested frame
35+ * rate for the stream
36+ */
37+
38+ long stream_rate ;
39+ struct timeval time_curr ;
40+ long stream_delay ;
41+
42+ gettimeofday (& time_curr , NULL );
43+
44+ /* The stream rate MUST be less than 1000000000 otherwise undefined behaviour
45+ * will occur with the SLEEP function.
46+ */
47+ stream_delay = ((time_curr .tv_usec - webui -> time_last .tv_usec )* 1000000 ) -
48+ ((time_curr .tv_sec - webui -> time_last .tv_sec )* 1000000000 );
49+ if (stream_delay < 0 ) stream_delay = 0 ;
50+ if (stream_delay > 1000000000 ) stream_delay = 1000000000 ;
51+
52+ if (webui -> cnt -> conf .stream_maxrate > 1 ){
53+ stream_rate = ( (1000000000 / webui -> cnt -> conf .stream_maxrate ) - stream_delay );
54+ if ((stream_rate > 0 ) && (stream_rate < 1000000000 )){
55+ SLEEP (0 ,stream_rate );
56+ } else if (stream_rate == 1000000000 ) {
57+ SLEEP (1 ,0 );
58+ }
59+ } else {
60+ SLEEP (1 ,0 );
61+ }
62+ gettimeofday (& webui -> time_last , NULL );
63+
64+ }
65+
3366static void webu_stream_mjpeg_getimg (struct webui_ctx * webui ) {
3467 long jpeg_size ;
3568 char resp_head [80 ];
@@ -84,52 +117,38 @@ static ssize_t webu_stream_mjpeg_response (void *cls, uint64_t pos, char *buf, s
84117 * browser. We sleep the requested amount of time between fetching images to match
85118 * the user configuration parameters. This function may be called multiple times for
86119 * a single image so we can write what we can to the buffer and pick up remaining bytes
87- * to send based upon the static variable of stream position
120+ * to send based upon the stream position
88121 */
89122 struct webui_ctx * webui = cls ;
90- static uint64_t stream_pos ;
91123 size_t sent_bytes ;
92- long stream_rate ;
93- static int indx_start ;
94124
95125 (void )pos ; /*Remove compiler warning */
96126
97127 if (webui -> cnt -> webcontrol_finish ) return -1 ;
98128
99- /* We use indx_start to send a few extra images when the stream starts*/
100- if ((stream_pos == 0 ) || (webui -> resp_used == 0 )){
101- if (webui -> resp_used == 0 ){
102- indx_start = 1 ;
103- } else if (indx_start < 4 ) {
104- indx_start ++ ;
105- } else {
106- if (webui -> cnt -> conf .stream_maxrate > 1 ){
107- stream_rate = (1000000000 / webui -> cnt -> conf .stream_maxrate );
108- SLEEP (0 ,stream_rate );
109- } else {
110- SLEEP (1 ,0 );
111- }
112- }
129+ if ((webui -> stream_pos == 0 ) || (webui -> resp_used == 0 )){
113130
114- stream_pos = 0 ;
131+ webu_stream_mjpeg_delay (webui );
132+
133+ webui -> stream_pos = 0 ;
115134 webui -> resp_used = 0 ;
116135
117136 webu_stream_mjpeg_getimg (webui );
118137
119138 if (webui -> resp_used == 0 ) return 0 ;
120139 }
121140
122- if ((webui -> resp_used - stream_pos ) > max ) {
141+ if ((webui -> resp_used - webui -> stream_pos ) > max ) {
123142 sent_bytes = max ;
124143 } else {
125- sent_bytes = webui -> resp_used - stream_pos ;
144+ sent_bytes = webui -> resp_used - webui -> stream_pos ;
126145 }
127146
128- memcpy (buf , webui -> resp_page + stream_pos , sent_bytes );
147+ memcpy (buf , webui -> resp_page + webui -> stream_pos , sent_bytes );
129148
130- stream_pos = stream_pos + sent_bytes ;
131- if (stream_pos >= webui -> resp_used ){
132- stream_pos = 0 ;
149+ webui -> stream_pos = webui -> stream_pos + sent_bytes ;
150+ if (webui -> stream_pos >= webui -> resp_used ){
151+ webui -> stream_pos = 0 ;
133152 }
134153
135154 return sent_bytes ;
@@ -249,6 +268,8 @@ int webu_stream_mjpeg(struct webui_ctx *webui) {
249268
250269 webu_stream_mjpeg_checkbuffers (webui );
251270
271+ gettimeofday (& webui -> time_last , NULL );
272+
252273 response = MHD_create_response_from_callback (MHD_SIZE_UNKNOWN , 1024
253274 ,& webu_stream_mjpeg_response , webui , NULL );
254275 if (!response ){
0 commit comments