From 7312e58d17e331d71d4f47e21bf15499609bace8 Mon Sep 17 00:00:00 2001 From: dieter kovacic Date: Tue, 9 Jul 2002 12:41:56 +0000 Subject: This commit was generated by cvs2svn to compensate for changes in r33, which included commits to RCS files with non-trunk default branches. svn path=/trunk/externals/ext13/; revision=34 --- streamin13~.c | 302 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 302 insertions(+) create mode 100644 streamin13~.c (limited to 'streamin13~.c') diff --git a/streamin13~.c b/streamin13~.c new file mode 100644 index 0000000..c4efded --- /dev/null +++ b/streamin13~.c @@ -0,0 +1,302 @@ + /* Written by Guenter Geiger (C) 1999, adapted and changed to streamin13~ by d13@klingt.org */ + +#include "m_pd.h" +#include "stream13.h" + +#include +#include +#ifdef unix +#include +#include +#include +#include +#include +#include +#define SOCKET_ERROR -1 +#else +#include +#endif + + + +#ifdef NT +#pragma warning( disable : 4244 ) +#pragma warning( disable : 4305 ) +#endif + +#define INBUFSIZE 8192 +#define MAXDROPS 99 + +/* Utility functions */ + +static void sys_sockerror(char *s) +{ +#ifdef unix + int err = errno; +#else + int err = WSAGetLastError(); + if (err == 10054) return; +#endif + post("%s: %s (%d)\n", s, strerror(err), err); +} + + +static void sys_closesocket(int fd) +{ +#ifdef UNIX + close(fd); +#endif +#ifdef NT + closesocket(fd); +#endif +} + +/* ------------------------ streamin13~ ----------------------------- */ + + +static t_class *streamin13_class; + +typedef struct _streamin13 +{ + t_object x_obj; + int x_connectsocket; + int x_nconnections; + int x_ndrops; + int x_ndone; + int x_fd; + int x_format; + int x_n; + short* cbuf; + int nsamples; +// t_outlet *x_out2; + int blocksperreceive; + int blockssincereceive; +} t_streamin13; + + +static void streamin13_tempbuf(t_streamin13 *x,int size) +{ + int fullsize = size * x->x_n; + if (!x->cbuf) + x->cbuf = getbytes(fullsize*sizeof(t_float)*x->blocksperreceive+4); + else + x->cbuf = resizebytes(x->cbuf,x->nsamples*sizeof(t_float),fullsize*sizeof(t_float)*x->blocksperreceive+4); + x->nsamples = size; + x->blockssincereceive=0; +} + + +static int streamin13_listen(t_streamin13 *x,int portno) +{ + struct sockaddr_in server; + int sockfd; + static int on = 1; + + + shutdown(x->x_connectsocket,SHUT_RDWR); + sys_closesocket(x->x_connectsocket); + + sockfd = socket(AF_INET, SOCK_DGRAM, 0); + if (sockfd < 0) + { + sys_sockerror("streamin-socket"); + x->x_connectsocket = 0; + return (0); + } + server.sin_family = AF_INET; + server.sin_addr.s_addr = INADDR_ANY; + + #ifdef unix + if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on)) < 0) + post("setsockopt failed\n"); + #endif + + /* assign server port number */ + server.sin_port = htons((u_short)portno); + post("listening to port number %d", portno); + + /* name the socket */ + if (bind(sockfd, (struct sockaddr *)&server, sizeof(server)) < 0) + { + sys_sockerror("streamin-bind"); + sys_closesocket(sockfd); + x->x_connectsocket = 0; + }else { + x->x_connectsocket = sockfd; + x->x_nconnections = 0; + x->x_ndrops = 0; + x->x_format = SF_FLOAT; + x->cbuf = NULL; + x->blocksperreceive=16; + x->blockssincereceive=0; + streamin13_tempbuf(x,64); + } + + +} + +static void *streamin13_new(t_floatarg fportno ,t_floatarg xn) +{ + int i; + t_streamin13 *x = (t_streamin13 *)pd_new(streamin13_class); + struct sockaddr_in server; + streamin13_listen(x,(int)fportno); + outlet_new(&x->x_obj, &s_signal); + x->x_n = xn; + for (i = 0 ;i < x->x_n - 1;i++){ + outlet_new(&x->x_obj, gensym("signal")); + } + + return (x); +} + + + +static void streamin13_free(t_streamin13 *x) +{ + /* LATER make me clean up open connections */ +} + + + + + +static t_int *streamin13_perform(t_int *w) +{ + t_streamin13* x = (t_streamin13*) (w[1]); + int offset = 3; + int i,j; + t_float *out[x->x_n]; + int n = (int)(w[2]); + struct timeval timeout; + int packsize; + int ret; + int length; + short* cbuf; + +#ifndef NT + fd_set fdset; +#endif + for (i=0;i < x->x_n;i++) { + out[i] = (t_float *)(w[offset+i]); + } + if (x->x_connectsocket){ + timeout.tv_sec = 0; + timeout.tv_usec = 0; + + if (n != x->nsamples) + streamin13_tempbuf(x,n); + + + // cbuf = x->cbuf + x->blockssincereceive * n * x->x_n; + + #ifndef NT + FD_SET(x->x_connectsocket,&fdset); + if (!select(x->x_connectsocket+1,&fdset,NULL,NULL,&timeout) + || !FD_ISSET(x->x_connectsocket,&fdset)) { + x->x_ndrops++; + if (x->x_ndrops <= MAXDROPS) { +/* post("streamin13: drop"); */ + while (n--){ + for (j=0;jx_n;j++){ + *(out[j]++) = 0.0; + } + } + } + + return (w+offset+1+i); + } else { + x->x_ndone++; + } + #endif + + if (x->x_ndrops > MAXDROPS) { + post("streamin13: dropped %d signal vectors, received %d sigvecs.",x->x_ndrops,x->x_ndone); + x->x_ndrops=0; + x->x_ndone=0; + } + if (!(x->blockssincereceive < x->blocksperreceive -1)) { + + length=x->x_n * x->nsamples * SF_SIZEOF(x->x_format) * x->blocksperreceive +4; + ret = recv(x->x_connectsocket, (char*) x->cbuf,length, 0); + x->blockssincereceive=0; + if (x->x_format != *x->cbuf){ + x->x_format= (short) *x->cbuf; + } + cbuf = (short*) x->cbuf + 1; + if (x->blocksperreceive != (short) *cbuf){ + x->blocksperreceive=(short) *cbuf; + streamin13_tempbuf(x,x->nsamples); + } + }else{ + x->blockssincereceive++; + } + packsize=n * x->x_n * sizeof(short) * x->blocksperreceive + 2; + switch (x->x_format) { + case SF_FLOAT:{ + t_float* fbuf = (t_float*) x->cbuf + x->blockssincereceive * n * x->x_n + 1; + while (n--){ + for (j=0;jx_n;j++){ + *out[j]++ = *fbuf++; + } + } + + break; + } + case SF_16BIT: + { + cbuf = x->cbuf + x->blockssincereceive * n * x->x_n + 2; + while (n--){ + for (j=0;jx_n;j++){ + *out[j]++ = (float) *cbuf++/32767.; + } + } + break; + } + case SF_8BIT: { + signed char* cbuf = (signed char*) x->cbuf + x->blockssincereceive * n * x->x_n + 4; + while (n--){ + for (j=0;jx_n;j++){ + *out[j]++ = (float) *cbuf++/127.; + } + } + break; + } + default: + break; + } + } + return (w+offset+1+i); +} + + + +static void streamin13_dsp(t_streamin13 *x, t_signal **sp) +{ + int i; + t_int** myvec = getbytes(sizeof(t_int)*(x->x_n + 3)); + + myvec[0] = (t_int*)x; + myvec[1] = (t_int*)sp[0]->s_n; + for (i=0;i < x->x_n;i++) + myvec[2 + i] = (t_int*)sp[i]->s_vec; + dsp_addv(streamin13_perform, x->x_n + 3, (t_int*)myvec); + freebytes(myvec,sizeof(t_int)*(x->x_n + 3)); + +} + +static void streamin13_port(t_streamin13 *x,t_floatarg port) +{ + streamin13_listen(x, (int)port); +} + +void streamin13_setup(void) +{ + streamin13_class = class_new(gensym("streamin13~"), + (t_newmethod) streamin13_new, (t_method) streamin13_free, + sizeof(t_streamin13), A_DEFSYM, A_DEFFLOAT, A_DEFFLOAT, 0); + class_sethelpsymbol(streamin13_class, gensym("streamio13~")); + class_addmethod(streamin13_class, nullfn, gensym("signal"), 0); + class_addmethod(streamin13_class, (t_method) streamin13_dsp, gensym("dsp"), 0); + class_addmethod(streamin13_class, (t_method)streamin13_port,gensym("port"),A_DEFFLOAT,0); +} -- cgit v1.2.1