0 ) { if ( count($rSockets) != 1 ) { if ($semaphore) sem_release($semaphore); ajaxError('Bogus return from select, '.count($rSockets).' sockets available', HTTP_STATUS_OK, STREAM_ERR_TRANSIENT); } } $nbytes = @socket_recvfrom($socket, $msg, MSG_DATA_SIZE, 0, $remSockFile); if ($semaphore) sem_release($semaphore); switch ($nbytes) { case -1 : ajaxError("socket_recvfrom( $remSockFile ) failed: ".socket_strerror(socket_last_error()), HTTP_STATUS_OK, STREAM_ERR_TRANSIENT); break; case 0 : // socket_recvfrom() returns false on error, and false == 0 under switch's // loose comparison, so a timed-out select lands here rather than on -1. if ($select_timed_out) { ajaxError("Timed out waiting for msg $remSockFile after waiting $timeout milliseconds", HTTP_STATUS_OK, STREAM_ERR_TIMEOUT); } else { ajaxError('No data to read from socket', HTTP_STATUS_OK, STREAM_ERR_TRANSIENT); } break; default : if ( $nbytes != MSG_DATA_SIZE ) { ajaxError("Got unexpected message size, got $nbytes, expected ".MSG_DATA_SIZE, HTTP_STATUS_OK, STREAM_ERR_TRANSIENT); } break; } $data = unpack('ltype', $msg); switch ( $data['type'] ) { case MSG_DATA_WATCH : $data = unpack('ltype/imonitor/istate/dfps/dcapturefps/danalysisfps/ilevel/irate/ddelay/izoom/iscale/Cdelayed/Cpaused/Cenabled/Cforced/iscore/ianalysing/Canalysisimage/Cstopped', $msg); $data['fps'] = round( $data['fps'], 2 ); $data['capturefps'] = round( $data['capturefps'], 2 ); $data['analysisfps'] = round( $data['analysisfps'], 2 ); $data['rate'] /= RATE_BASE; $data['delay'] = round( $data['delay'], 2 ); $data['zoom'] = round( $data['zoom']/SCALE_BASE, 1 ); #$data['scale'] = $data['scale']; if (ZM_OPT_USE_AUTH) { if (ZM_AUTH_RELAY == 'hashed') { # Send the hash unconditionally. Withholding it when it matched the hash # the request carried meant a client whose copy had drifted could never be # corrected, and reconnecting streams then baked the drifted hash into # their src and 403'd against zms indefinitely. $data['auth'] = generateAuthHash(ZM_AUTH_HASH_IPS); } $data['auth_relay'] = get_auth_relay(); } ajaxResponse(array('status'=>$data)); break; case MSG_DATA_EVENT : if ( PHP_INT_SIZE===4 || version_compare( phpversion(), '5.6.0', '<') ) { ZM\Debug('Using old unpack methods to handle 64bit event id'); $data = unpack('ltype/ieventlow/ieventhigh/dduration/dprogress/dfps/irate/izoom/iscale/Cpaused/Cstopped', $msg); $data['event'] = $data['eventhigh'] << 32 | $data['eventlow']; } else { $data = unpack('ltype/Qevent/dduration/dprogress/dfps/irate/izoom/iscale/Cpaused/Cstopped', $msg); } $data['rate'] /= RATE_BASE; $data['zoom'] = round($data['zoom']/SCALE_BASE, 1); $data['fps'] = round( $data['fps'], 2 ); if ( ZM_OPT_USE_AUTH ) { if (ZM_AUTH_RELAY == 'hashed') { # Unconditional, for the reason given in the MSG_DATA_WATCH branch above. $data['auth'] = generateAuthHash(ZM_AUTH_HASH_IPS); } $data['auth_relay'] = get_auth_relay(); } ajaxResponse(array('status'=>$data)); break; default : ajaxError('Unexpected received message type '.$data['type'], HTTP_STATUS_OK, STREAM_ERR_INVALID); } ajaxError('Unrecognised action or insufficient permissions in ajax/stream', HTTP_STATUS_OK, STREAM_ERR_INVALID); function ajaxCleanup() { global $socket, $localSocketFile; if ( !empty($socket) ) @socket_close($socket); if ( !empty($localSocketFile) ) @unlink($localSocketFile); } ?>