/***************************************************************************** * Write: standard write *****************************************************************************/ static ssize_t Write( sout_access_out_t *p_access, block_t *p_buffer ) { sout_access_out_sys_t *p_sys = p_access->p_sys; size_t i_write = 0; shout_sync( p_sys->p_shout ); while( p_buffer ) { block_t *p_next = p_buffer->p_next; if( shout_send( p_sys->p_shout, p_buffer->p_buffer, p_buffer->i_buffer ) == SHOUTERR_SUCCESS ) { i_write += p_buffer->i_buffer; } else { msg_Err( p_access, "cannot write to stream: %s", shout_get_error( p_sys->p_shout ) ); /* The most common cause seems to be a server disconnect, resulting in a Socket Error which can only be fixed by closing and reconnecting. Since we already began with a working connection, the most feasable approach to get out of this error status is a (timed) reconnect approach. */ shout_close( p_sys->p_shout ); msg_Warn( p_access, "server unavailable? trying to reconnect..." ); /* Re-open the connection (protocol params have already been set) and re-sync */ if( shout_open( p_sys->p_shout ) == SHOUTERR_SUCCESS ) { shout_sync( p_sys->p_shout ); msg_Warn( p_access, "reconnected to server" ); } else { msg_Err( p_access, "failed to reconnect to server" ); block_ChainRelease( p_buffer ); return VLC_EGENERIC; } } block_Release( p_buffer ); /* XXX: Unsure if that's the cause for some audio trouble... */ p_buffer = p_next; } return i_write; }
void *shout_thread(void *data) { STREAM_HDR *stream; size_t n; int ret; struct timespec nap; stream = (STREAM_HDR *)data; stream->streaming = 1; while (stream->streaming) { shout_sync(stream->shout); n = jack_ringbuffer_read_space(stream->ringbuf); if (n < 1) { nap.tv_sec = shout_wait.tv_sec; nap.tv_nsec = shout_wait.tv_nsec; while (nanosleep(&nap, &nap) != 0); continue; } if (n > stream->shoutbuf_size) { if (stream->shoutbuf != NULL) free(stream->shoutbuf); stream->shoutbuf = (char *)my_plain_malloc(n, "shout_thread"); stream->shoutbuf_size = n; } jack_ringbuffer_read(stream->ringbuf, stream->shoutbuf, n); ret = shout_send(stream->shout, (const unsigned char *)stream->shoutbuf, n); if (ret != SHOUTERR_SUCCESS) { log_msg("send err: %s\n", shout_get_error(stream->shout)); } } return NULL; }
static PyObject* pshoutobj_sync(ShoutObject* self) { Py_BEGIN_ALLOW_THREADS shout_sync(self->conn); Py_END_ALLOW_THREADS return Py_BuildValue("i", 1); }
void Shouter::start() { char buffer[4096]; size_t read,ret; stop_requested=false; refresh_metadata(); if (shout_open(shout) == SHOUTERR_SUCCESS) { printf("Connected to server...\n"); while (!stop_requested) { if(refresh_metadata_requested) { refresh_metadata_requested=false; log(0,"Refreshing metadata....."); do_refresh_metadata(); } read = source->get_data(buffer, 4096); if (read > 0) { ret = shout_send(shout, (unsigned char*)buffer, read); if (ret != SHOUTERR_SUCCESS) { printf("DEBUG: Send error: %s\n", shout_get_error(shout)); break; } } else { break; } shout_sync(shout); } } else { printf("Error connecting: %s\n", shout_get_error(shout)); } }
/***************************************************************************** * Write: standard write *****************************************************************************/ static int Write( sout_access_out_t *p_access, block_t *p_buffer ) { size_t i_write = 0; shout_sync( p_access->p_sys->p_shout ); while( p_buffer ) { block_t *p_next = p_buffer->p_next; if( shout_send( p_access->p_sys->p_shout, p_buffer->p_buffer, p_buffer->i_buffer ) == SHOUTERR_SUCCESS ) { i_write += p_buffer->i_buffer; } else { msg_Err( p_access, "cannot write to stream: %s", shout_get_error(p_access->p_sys->p_shout) ); } block_Release( p_buffer ); /* XXX: Unsure if that's the cause for some audio trouble... */ p_buffer = p_next; } return i_write; }
bool Shouter::start() { int res; char srv[64]; switch(login()) { case SHOUT_PROTOCOL_HTTP: sprintf(srv,"icecast2"); break; case SHOUT_PROTOCOL_ICY: sprintf(srv,"shoutcast"); break; default: sprintf(srv,"icecast 1"); break; } if(shout_get_connected(ice)) { // if allready connected, reconnect func("icecast still connected: disconnecting"); shout_sync(ice); shout_close(ice); } notice("Contacting %s server %s on port %u",srv,host(),port()); shout_sync(ice); res = shout_open(ice); func("Shouter::start() shout_open returns %i",res); if(res==SHOUTERR_SUCCESS) { notice("started streaming on %s",streamurl); running = true; } else { error("shout_open: %s",shout_get_error(ice)); shout_sync(ice); shout_close(ice); running = false; } return(running); }
void OutputIceCast::output(const char* buffer, uint32_t size) { if (getState() != CONNECTED) return; if (size != 0) { int r = shout_send(_shout, ( const unsigned char* )buffer, size); if (r != SHOUTERR_SUCCESS) { emit warn(QString("send error: ") + shout_get_error(_shout)); _state = DISCONNECTED; emit stateChanged(DISCONNECTED); emit stateChanged("offline"); emit requestReconnect(); _trial = 0; } shout_sync(_shout); } }
VideoEncoder::~VideoEncoder() { // flush all the ringbuffer to file and stream unsigned int encnum = 0; if(encbuf) { do { if((encnum = ringbuffer_read_space(ringbuffer)) > 0) encnum = ringbuffer_read(ringbuffer, encbuf, encnum); // ((audio_kbps + video_kbps)*1024)/24); if(encnum <= 0) break; if(write_to_disk && filedump_fd) { fwrite(encbuf, 1, encnum, filedump_fd); } if(write_to_stream && ice) { shout_sync(ice); shout_send(ice, (const unsigned char*)encbuf, encnum); } func("flushed %u bytes closing video encoder", encnum); } while(encnum > 0); free(encbuf); } // close the filedump if(filedump_fd) fclose(filedump_fd); // now deallocate the ringbuffer ringbuffer_free(ringbuffer); shout_close(ice); // shout_sync(ice); // shout_free(ice); shout_shutdown(); if(enc_y) free(enc_y); if(enc_u) free(enc_u); if(enc_v) free(enc_v); if(enc_yuyv) free(enc_yuyv); free(fps); }
int Shouter::send(short int *buf, unsigned int enc) { int res = 0; if(!running) return(0); if(enc<1) return res; shout_sync(ice); res = shout_send(ice,(unsigned char*) buf, enc); if(res) { error("shout_send: %s",shout_get_error(ice)); if (got_sigpipe && (res==SHOUTERR_SOCKET)) { errors++; got_sigpipe = false; if(errors>10) { res = -2; errors = 0; } } else res = -1; } else errors = 0; return(res); }
static GstFlowReturn gst_shout2send_render (GstBaseSink * basesink, GstBuffer * buf) { GstShout2send *sink; glong ret; sink = GST_SHOUT2SEND (basesink); /* presumably we connect here because we need to know the format before * we can set up the connection, which we don't know yet in _start() */ if (!sink->connected) { if (!gst_shout2send_connect (sink)) return GST_FLOW_ERROR; } /* FIXME: do we want to do syncing here at all? (tpm) */ /* GST_LOG_OBJECT (sink, "using libshout to sync"); */ shout_sync (sink->conn); GST_LOG_OBJECT (sink, "sending %u bytes of data", GST_BUFFER_SIZE (buf)); ret = shout_send (sink->conn, GST_BUFFER_DATA (buf), GST_BUFFER_SIZE (buf)); if (ret != SHOUTERR_SUCCESS) goto send_error; return GST_FLOW_OK; /* ERRORS */ send_error: { GST_ELEMENT_ERROR (sink, RESOURCE, WRITE, (NULL), ("shout_send() failed: %s", shout_get_error (sink->conn))); g_signal_emit (sink, gst_shout2send_signals[SIGNAL_CONNECTION_PROBLEM], 0, shout_get_errno (sink->conn)); return GST_FLOW_ERROR; } }
static inline void free_context(shout_context_t *context) { int ret; if (context) { switch_mutex_lock(context->audio_mutex); context->err++; switch_mutex_unlock(context->audio_mutex); if (context->stream_url) { int sanity = 0; while (context->thread_running) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Waiting for stream to terminate: %s\n", context->stream_url); switch_yield(500000); if (++sanity > 10) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Giving up waiting for stream to terminate: %s\n", context->stream_url); break; } } } switch_thread_rwlock_wrlock(context->rwlock); if (context->mh) { mpg123_close(context->mh); mpg123_delete(context->mh); } if (context->fp) { unsigned char mp3buffer[20480]; int len; int16_t blank[2048] = { 0 }, *r = NULL; if (context->channels == 2) { r = blank; } len = lame_encode_buffer(context->gfp, blank, r, sizeof(blank) / 2, mp3buffer, sizeof(mp3buffer)); if (len) { ret = fwrite(mp3buffer, 1, len, context->fp); } while ((len = lame_encode_flush(context->gfp, mp3buffer, sizeof(mp3buffer))) > 0) { ret = fwrite(mp3buffer, 1, len, context->fp); if (ret < 0) { break; } } lame_mp3_tags_fid(context->gfp, context->fp); fclose(context->fp); context->fp = NULL; } if (context->shout) { if (context->gfp) { unsigned char mp3buffer[8192]; int len; int16_t blank[2048] = { 0 }, *r = NULL; if (context->channels == 2) { r = blank; } len = lame_encode_buffer(context->gfp, blank, r, sizeof(blank) / 2, mp3buffer, sizeof(mp3buffer)); if (len) { ret = shout_send(context->shout, mp3buffer, len); if (ret == SHOUTERR_SUCCESS) { shout_sync(context->shout); } } while ((len = lame_encode_flush(context->gfp, mp3buffer, sizeof(mp3buffer))) > 0) { ret = shout_send(context->shout, mp3buffer, len); if (ret != SHOUTERR_SUCCESS) { break; } else { shout_sync(context->shout); } } } shout_close(context->shout); context->shout = NULL; } if (context->gfp) { lame_close(context->gfp); context->gfp = NULL; } if (context->audio_buffer) { switch_buffer_destroy(&context->audio_buffer); } switch_mutex_destroy(context->audio_mutex); switch_thread_rwlock_unlock(context->rwlock); switch_thread_rwlock_destroy(context->rwlock); } }
static void *SWITCH_THREAD_FUNC write_stream_thread(switch_thread_t *thread, void *obj) { shout_context_t *context = (shout_context_t *) obj; switch_thread_rwlock_rdlock(context->rwlock); if (context->thread_running) { context->thread_running++; } else { switch_thread_rwlock_unlock(context->rwlock); return NULL; } if (!context->lame_ready) { lame_init_params(context->gfp); lame_print_config(context->gfp); context->lame_ready = 1; } while (!context->err && context->thread_running) { unsigned char mp3buf[8192] = ""; int16_t audio[9600] = { 0 }; switch_size_t audio_read = 0; int rlen = 0; long ret = 0; switch_mutex_lock(context->audio_mutex); if (context->audio_buffer) { audio_read = switch_buffer_read(context->audio_buffer, audio, sizeof(audio)); } else { context->err++; } switch_mutex_unlock(context->audio_mutex); error_check(); if (!audio_read) { audio_read = sizeof(audio); memset(audio, 255, sizeof(audio)); } if (context->channels == 2) { int16_t l[4800] = { 0 }; int16_t r[4800] = { 0 }; int j = 0; switch_size_t i; for (i = 0; i < audio_read / 4; i++) { l[i] = audio[j++]; r[i] = audio[j++]; } if ((rlen = lame_encode_buffer(context->gfp, l, r, audio_read / 4, mp3buf, sizeof(mp3buf))) < 0) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "MP3 encode error %d!\n", rlen); goto error; } } else if (context->channels == 1) { if ((rlen = lame_encode_buffer(context->gfp, (void *) audio, NULL, audio_read / sizeof(int16_t), mp3buf, sizeof(mp3buf))) < 0) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "MP3 encode error %d!\n", rlen); goto error; } } if (rlen) { ret = shout_send(context->shout, mp3buf, rlen); if (ret != SHOUTERR_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Send error: %s\n", shout_get_error(context->shout)); goto error; } } else { memset(mp3buf, 0, 128); ret = shout_send(context->shout, mp3buf, 128); } shout_sync(context->shout); switch_yield(100000); } error: switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Write Thread Done\n"); switch_thread_rwlock_unlock(context->rwlock); context->thread_running = 0; return NULL; }
int sendStream(shout_t *shout, FILE *filepstream, const char *fileName, int isStdin, const char *songLenStr, struct timeval *tv) { unsigned char buff[4096]; size_t bytes_read, total, oldTotal; int ret; double kbps = -1.0; struct timeval timeStamp, *startTime = tv; struct timeval callTime, currentTime; if (startTime == NULL) { printf("%s: sendStream(): Internal error: startTime is NULL\n", __progname); abort(); } ez_gettimeofday((void *)&callTime); timeStamp.tv_sec = startTime->tv_sec; timeStamp.tv_usec = startTime->tv_usec; total = oldTotal = 0; ret = STREAM_DONE; while ((bytes_read = fread(buff, 1UL, sizeof(buff), filepstream)) > 0) { if (shout_get_connected(shout) != SHOUTERR_CONNECTED && reconnectServer(shout, 0) == 0) { ret = STREAM_SERVERR; break; } shout_sync(shout); if (shout_send(shout, buff, bytes_read) != SHOUTERR_SUCCESS) { printf("%s: shout_send(): %s\n", __progname, shout_get_error(shout)); if (reconnectServer(shout, 1)) break; else { ret = STREAM_SERVERR; break; } } if (quit) break; if (rereadPlaylist_notify) { rereadPlaylist_notify = 0; if (!pezConfig->fileNameIsProgram) printf("%s: SIGHUP signal received, will reread playlist after this file\n", __progname); } if (skipTrack) { skipTrack = 0; ret = STREAM_SKIP; break; } ez_gettimeofday((void *)¤tTime); if (queryMetadata || (pezConfig->metadataRefreshInterval != -1 && (currentTime.tv_sec - callTime.tv_sec >= pezConfig->metadataRefreshInterval) ) ) { queryMetadata = 0; if (metadataFromProgram) { ret = STREAM_UPDMDATA; break; } } total += bytes_read; if (qFlag && vFlag) { double oldTime, newTime; if (!isStdin && playlistMode) { if (pezConfig->fileNameIsProgram) { char *tmp = xstrdup(pezConfig->fileName); printf(" [%s]", local_basename(tmp)); xfree(tmp); } else printf(" [%4lu/%-4lu]", playlist_get_position(playlist), playlist_get_num_items(playlist)); } oldTime = (double)timeStamp.tv_sec + (double)timeStamp.tv_usec / 1000000.0; newTime = (double)currentTime.tv_sec + (double)currentTime.tv_usec / 1000000.0; if (songLenStr == NULL) printf(" [ %s]", getTimeString(currentTime.tv_sec - startTime->tv_sec)); else printf(" [ %s/%s]", getTimeString(currentTime.tv_sec - startTime->tv_sec), songLenStr); if (newTime - oldTime >= 1.0) { kbps = (((double)(total - oldTotal) / (newTime - oldTime)) * 8.0) / 1000.0; timeStamp.tv_sec = currentTime.tv_sec; timeStamp.tv_usec = currentTime.tv_usec; oldTotal = total; } if (kbps < 0) printf(" "); else printf(" [%8.2f kbps]", kbps); printf(" \r"); fflush(stdout); } } if (ferror(filepstream)) { if (errno == EINTR) { clearerr(filepstream); ret = STREAM_CONT; } else if (errno == EBADF && isStdin) printf("%s: No (more) data available on standard input\n", __progname); else printf("%s: sendStream(): Error while reading '%s': %s\n", __progname, fileName, strerror(errno)); } return (ret); }
static PyObject* pshoutobj_sync(ShoutObject* self) { shout_sync(self->conn); return Py_BuildValue("i", 1); }
int main (int argc, char * argv[]) { int rate = 44100; int bits = 16; int channels = 2; int codec = ROAR_CODEC_OGG_VORBIS; char * server = NULL; char * k; char * s_server = NULL; char * s_mount = NULL; char * s_pw = NULL; int s_port = -1; char * s_desc = NULL; char * s_genre = NULL; char * s_name = NULL; char * s_url = NULL; int s_public = 0; int fh; int i; char buf[BUFSIZE]; shout_t * shout; for (i = 1; i < argc; i++) { k = argv[i]; if ( strcmp(k, "--server") == 0 ) { server = argv[++i]; } else if ( strcmp(k, "--rate") == 0 ) { rate = atoi(argv[++i]); } else if ( strcmp(k, "--bits") == 0 ) { bits = atoi(argv[++i]); } else if ( strcmp(k, "--channels") == 0 || strcmp(k, "--chans") == 0 ) { channels = atoi(argv[++i]); } else if ( strcmp(k, "--codec") == 0 ) { codec = roar_str2codec(argv[++i]); } else if ( strcmp(k, "-p") == 0 || strcmp(k, "--public") == 0 ) { s_public = 1; } else if ( strcmp(k, "-d") == 0 ) { s_desc = argv[++i]; } else if ( strcmp(k, "-g") == 0 ) { s_genre = argv[++i]; } else if ( strcmp(k, "-n") == 0 ) { s_name = argv[++i]; } else if ( strcmp(k, "-u") == 0 ) { s_url = argv[++i]; } else if ( strcmp(k, "-h") == 0 || strcmp(k, "--help") == 0 ) { usage(); return 0; } else if ( s_server == NULL ) { s_server = k; } else if ( s_port == -1 ) { s_port = atoi(k); } else if ( s_pw == NULL ) { s_pw = k; } else if ( s_mount == NULL ) { s_mount = k; } else { fprintf(stderr, "Error: unknown argument: %s\n", k); usage(); return 1; } } if ( s_server == NULL ) s_server = "localhost"; if ( s_mount == NULL ) s_mount = "/roar.ogg"; if ( s_pw == NULL ) s_pw = "hackme"; if ( s_port == -1 ) s_port = 8000; shout_init(); if (!(shout = shout_new())) { ROAR_ERR("Can not create shout object"); return 1; } if (shout_set_host(shout, s_server) != SHOUTERR_SUCCESS) { ROAR_ERR("Error setting hostname: %s", shout_get_error(shout)); return 1; } if (shout_set_protocol(shout, SHOUT_PROTOCOL_HTTP) != SHOUTERR_SUCCESS) { ROAR_ERR("Error setting protocol: %s", shout_get_error(shout)); return 1; } if (shout_set_port(shout, s_port) != SHOUTERR_SUCCESS) { ROAR_ERR("Error setting port: %s", shout_get_error(shout)); return 1; } if (shout_set_password(shout, s_pw) != SHOUTERR_SUCCESS) { ROAR_ERR("Error setting password: %s", shout_get_error(shout)); return 1; } if (shout_set_mount(shout, s_mount) != SHOUTERR_SUCCESS) { ROAR_ERR("Error setting mount: %s", shout_get_error(shout)); return 1; } if (shout_set_user(shout, "source") != SHOUTERR_SUCCESS) { ROAR_ERR("Error setting user: %s", shout_get_error(shout)); return 1; } if (shout_set_format(shout, SHOUT_FORMAT_OGG) != SHOUTERR_SUCCESS) { ROAR_ERR("Error setting format: %s", shout_get_error(shout)); return 1; } shout_set_public(shout, s_public); if (s_desc != NULL) shout_set_description(shout, s_desc); if (s_genre != NULL) shout_set_genre(shout, s_genre); if (s_name != NULL) shout_set_name(shout, s_name); if (s_url != NULL) shout_set_url(shout, s_url); if ( (fh = roar_simple_monitor(rate, channels, bits, codec, server, "roarshout")) == -1 ) { fprintf(stderr, "Error: can not start monitoring\n"); return 1; } if (shout_open(shout) != SHOUTERR_SUCCESS) { ROAR_ERR("Can not open connection via libshout!"); return -1; } while((i = read(fh, buf, BUFSIZE))) if (shout_send(shout, (unsigned char*)buf, i) != SHOUTERR_SUCCESS) break; roar_simple_close(fh); shout_sync(shout); shout_close(shout); shout_shutdown(); return 0; }
int main() { shout_t *shout; char buff[4096]; long read, ret, total; shout_init(); if (!(shout = shout_new())) { printf("Could not allocate shout_t\n"); return 1; } if (shout_set_host(shout, "127.0.0.1") != SHOUTERR_SUCCESS) { printf("Error setting hostname: %s\n", shout_get_error(shout)); return 1; } if (shout_set_protocol(shout, SHOUT_PROTOCOL_HTTP) != SHOUTERR_SUCCESS) { printf("Error setting protocol: %s\n", shout_get_error(shout)); return 1; } if (shout_set_port(shout, 8000) != SHOUTERR_SUCCESS) { printf("Error setting port: %s\n", shout_get_error(shout)); return 1; } if (shout_set_password(shout, "hackme") != SHOUTERR_SUCCESS) { printf("Error setting password: %s\n", shout_get_error(shout)); return 1; } if (shout_set_mount(shout, "/example.ogg") != SHOUTERR_SUCCESS) { printf("Error setting mount: %s\n", shout_get_error(shout)); return 1; } if (shout_set_user(shout, "source") != SHOUTERR_SUCCESS) { printf("Error setting user: %s\n", shout_get_error(shout)); return 1; } if (shout_set_format(shout, SHOUT_FORMAT_OGG) != SHOUTERR_SUCCESS) { printf("Error setting user: %s\n", shout_get_error(shout)); return 1; } if (shout_open(shout) == SHOUTERR_SUCCESS) { printf("Connected to server...\n"); total = 0; while (1) { read = fread(buff, 1, sizeof(buff), stdin); total = total + read; if (read > 0) { ret = shout_send(shout, buff, read); if (ret != SHOUTERR_SUCCESS) { printf("DEBUG: Send error: %s\n", shout_get_error(shout)); break; } } else { break; } shout_sync(shout); } } else { printf("Error connecting: %s\n", shout_get_error(shout)); } shout_close(shout); shout_shutdown(); return 0; }
void VideoEncoder::thread_loop() { int encnum; int res; auto screen = this->screen.lock(); /* Convert picture from rgb to yuv420 planar two steps here: 1) rgb24a or bgr24a to yuv422 interlaced (yuyv) 2) yuv422 to yuv420 planar (yuv420p) to fix endiannes issues try adding #define ARCH_PPC and using mlt_convert_bgr24a_to_yuv422 or mlt_convert_argb_to_yuv422 (see mlt_frame.h in mltframework.org sourcecode) i can't tell as i don't have PPC, waiting for u mr.goil :) */ uint8_t *surface = (uint8_t *)screen->get_surface(); time_t *tm = (time_t *)malloc(sizeof(time_t)); time(tm); // std::cerr << "-- ENC:" << asctime(localtime(tm)); if(!surface) { fps->delay(); /* std::cout << "fps->start_tv.tv_sec :" << fps->start_tv.tv_sec << \ " tv_usec :" << fps->start_tv.tv_usec << " \r" << std::endl; */ return; } fps->delay(); //uncomment this to see how long it takes between two frames in us. /* timeval start_t; gettimeofday(&start_t,NULL); timeval did; timersub(&start_t, &m_lastTime, &did); m_lastTime.tv_sec = start_t.tv_sec; m_lastTime.tv_usec = start_t.tv_usec; std::cerr << "diff time :" << did.tv_usec << std::endl;*/ screen->lock(); auto & geo = screen->getGeometry(); switch(screen->get_pixel_format()) { case ViewPort::RGBA32: mlt_convert_rgb24a_to_yuv422(surface, geo.getSize().x(), geo.getSize().y(), geo.getSize().x() << 2, (uint8_t*)enc_yuyv, NULL); break; case ViewPort::BGRA32: mlt_convert_bgr24a_to_yuv422(surface, geo.getSize().x(), geo.getSize().y(), geo.getSize().x() << 2, (uint8_t*)enc_yuyv, NULL); break; case ViewPort::ARGB32: mlt_convert_argb_to_yuv422(surface, geo.getSize().x(), geo.getSize().y(), geo.getSize().x() << 2, (uint8_t*)enc_yuyv, NULL); break; default: error("Video Encoder %s doesn't supports Screen %s pixel format", name.c_str(), screen->getName().c_str()); } screen->unlock(); ccvt_yuyv_420p(geo.getSize().x(), geo.getSize().y(), enc_yuyv, enc_y, enc_u, enc_v); ////// got the YUV, do the encoding res = encode_frame(); if(res != 0) error("Can't encode frame"); /// proceed writing and streaming encoded data in encpipe encnum = 0; if(write_to_disk || write_to_stream) { if((encnum = ringbuffer_read_space(ringbuffer)) > 0) { encbuf = (char *)realloc(encbuf, encnum); // encbuf = (char *)realloc(encbuf, (((audio_kbps + video_kbps)*1024)/24)); //doesn't change anything for shifting problem encnum = ringbuffer_read(ringbuffer, encbuf, encnum); // encnum = ringbuffer_read(ringbuffer, encbuf, // ((audio_kbps + video_kbps)*1024)/24); } } if(encnum > 0) { // func("%s has encoded %i bytes", name, encnum); if(write_to_disk && filedump_fd) fwrite(encbuf, 1, encnum, filedump_fd); if(write_to_stream && ice) { /* int wait_ms; wait_ms = shout_delay(ice); std::cerr << "---- shout delay :" << wait_ms << std::endl;*/ shout_sync(ice); if(shout_send(ice, (const unsigned char*)encbuf, encnum) != SHOUTERR_SUCCESS) { error("shout_send: %s", shout_get_error(ice)); } // else //printf("%d %d\n", encnum, (int)shout_queuelen(ice)); } gettimeofday(&m_ActualTime, NULL); if(m_ActualTime.tv_sec == m_OldTime.tv_sec) m_ElapsedTime += ((double)(m_ActualTime.tv_usec - m_OldTime.tv_usec)) / 1000000.0; else m_ElapsedTime += ((double)(m_ActualTime.tv_sec - m_OldTime.tv_sec)) + \ (((double)(m_ActualTime.tv_usec - m_OldTime.tv_usec)) / 1000000.0); m_OldTime.tv_sec = m_ActualTime.tv_sec; m_OldTime.tv_usec = m_ActualTime.tv_usec; m_Streamed += encnum; if(m_ElapsedTime >= 3.0) { //calculate stream rate every minimum 3 seconds m_StreamRate = ((double)m_Streamed / m_ElapsedTime) / 1000.0; m_ElapsedTime = 0; m_Streamed = 0; } } }