[PD-cvs] pd/src d_soundfile.c, 1.4.4.11.2.10.2.19, 1.4.4.11.2.10.2.20

Mathieu Bouchard matju at users.sourceforge.net
Thu Jul 19 06:24:22 CEST 2007


Update of /cvsroot/pure-data/pd/src
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv21108

Modified Files:
      Tag: desiredata
	d_soundfile.c 
Log Message:
cleanup; added macros EAT_ARG and LOOP


Index: d_soundfile.c
===================================================================
RCS file: /cvsroot/pure-data/pd/src/d_soundfile.c,v
retrieving revision 1.4.4.11.2.10.2.19
retrieving revision 1.4.4.11.2.10.2.20
diff -C2 -d -r1.4.4.11.2.10.2.19 -r1.4.4.11.2.10.2.20
*** d_soundfile.c	19 Jul 2007 03:02:07 -0000	1.4.4.11.2.10.2.19
--- d_soundfile.c	19 Jul 2007 04:24:20 -0000	1.4.4.11.2.10.2.20
***************
*** 42,45 ****
--- 42,47 ----
  static bool debug=0;
  
+ #define EAT_ARG(ATYPE,VAR) if (argc<1 || argv->a_type != ATYPE) goto usage; else {VAR = *argv++; argc--;}
+ 
  /***************** soundfile header structures ************************/
  
***************
*** 333,337 ****
      long itemsread, unsigned char *buf, int nitems, int bytespersamp, int bigendian) {
      unsigned char *sp, *sp2;
-     float *fp;
      int nchannels = (sfchannels < nvecs ? sfchannels : nvecs);
      int bytesperframe = bytespersamp * sfchannels;
--- 335,338 ----
***************
*** 340,367 ****
          int j;
          sp2=sp;
!         fp=vecs[i] + itemsread;
          if (bytespersamp == 2) {
!             if (bigendian) {
!                 for (j=0; j<nitems; j++, sp2 += bytesperframe, fp++) *fp = SCALE * ((sp2[0]<<24) | (sp2[1]<<16));
!             } else {
!                 for (j=0; j<nitems; j++, sp2 += bytesperframe, fp++) *fp = SCALE * ((sp2[1]<<24) | (sp2[0]<<16));
!             }
          } else if (bytespersamp == 3) {
!             if (bigendian) {
!                 for (j=0; j<nitems; j++, sp2 += bytesperframe, fp++) *fp = SCALE * ((sp2[0]<<24) | (sp2[1]<<16) | (sp2[2]<<8));
!             } else {
!                 for (j=0; j<nitems; j++, sp2 += bytesperframe, fp++) *fp = SCALE * ((sp2[2]<<24) | (sp2[1]<<16) | (sp2[0]<<8));
!             }
          } else if (bytespersamp == 4) {
!             if (bigendian) {
!                 for (j=0; j<nitems; j++, sp2 += bytesperframe, fp++) *(long *)fp = (sp2[0]<<24) | (sp2[1]<<16) | (sp2[2]<<8) | sp2[3];
!             } else {
!                 for (j=0; j<nitems; j++, sp2 += bytesperframe, fp++) *(long *)fp = (sp2[3]<<24) | (sp2[2]<<16) | (sp2[1]<<8) | sp2[0];
!             }
          }
      }
      /* zero out other outputs */
      for (int i=sfchannels; i < nvecs; i++) {
!         fp=vecs[i];
          for (int j=nitems; j--; ) *fp++ = 0;
      }
--- 341,361 ----
          int j;
          sp2=sp;
!         float *fp=vecs[i] + itemsread;
! 	#define LOOP for (j=0; j<nitems; j++, sp2 += bytesperframe, fp++)
          if (bytespersamp == 2) {
!             if (bigendian) LOOP {*fp = SCALE * ((sp2[0]<<24) | (sp2[1]<<16));}
!             else           LOOP {*fp = SCALE * ((sp2[1]<<24) | (sp2[0]<<16));}
          } else if (bytespersamp == 3) {
!             if (bigendian) LOOP {*fp = SCALE * ((sp2[0]<<24) | (sp2[1]<<16) | (sp2[2]<<8));}
!             else           LOOP {*fp = SCALE * ((sp2[2]<<24) | (sp2[1]<<16) | (sp2[0]<<8));}
          } else if (bytespersamp == 4) {
!             if (bigendian) LOOP {*(long *)fp = (sp2[0]<<24) | (sp2[1]<<16) | (sp2[2]<<8) | sp2[3];}
!             else           LOOP {*(long *)fp = (sp2[3]<<24) | (sp2[2]<<16) | (sp2[1]<<8) | sp2[0];}
          }
+ 	#undef LOOP
      }
      /* zero out other outputs */
      for (int i=sfchannels; i < nvecs; i++) {
!         float *fp=vecs[i];
          for (int j=nitems; j--; ) *fp++ = 0;
      }
***************
*** 370,382 ****
  /* soundfiler_write ...
     usage: write [flags] filename table ...
!    flags:
!         -nframes <frames>
!         -skip <frames>
!         -bytes <bytes per sample>
!         -normalize
!         -nextstep
!         -wave
!         -big
!         -little
      the routine which actually does the work should LATER also be called from garray_write16.
      Parse arguments for writing.  The "obj" argument is only for flagging
--- 364,368 ----
  /* soundfiler_write ...
     usage: write [flags] filename table ...
!    flags: -nframes <frames> -skip <frames> -bytes <bytes per sample> -normalize -nextstep -wave -big -little
      the routine which actually does the work should LATER also be called from garray_write16.
      Parse arguments for writing.  The "obj" argument is only for flagging
***************
*** 396,407 ****
  	argc--; argv++;
          if (!strcmp(flag, "skip")) {
!             if (argc < 1 || argv[0].a_type != A_FLOAT || ((onset = (long) argv[0].a_float) < 0)) goto usage;
!             argc--; argv++;
          } else if (!strcmp(flag, "nframes")) {
!             if (argc < 1 || argv[0].a_type != A_FLOAT || ((nframes = (long) argv[0].a_float) < 0)) goto usage;
!             argc--; argv++;
          } else if (!strcmp(flag, "bytes")) {
!             if (argc < 1 || argv[0].a_type != A_FLOAT || ((bytespersamp = (int) argv[0].a_float) < 2) || bytespersamp > 4) goto usage;
!             argc--; argv++;
          } else if (!strcmp(flag, "normalize")) {normalize = 1;
  	} else if (!strcmp(flag, "wave"))      {filetype = FORMAT_WAVE;
--- 382,390 ----
  	argc--; argv++;
          if (!strcmp(flag, "skip")) {
!             EAT_ARG(A_FLOAT,onset); if (onset<0) goto usage;
          } else if (!strcmp(flag, "nframes")) {
!             EAT_ARG(A_FLOAT,nframes); if (nframes<0) goto usage;
          } else if (!strcmp(flag, "bytes")) {
!             EAT_ARG(A_FLOAT,bytespersamp); if (bytespersamp<2 || bytespersamp>4) goto usage;
          } else if (!strcmp(flag, "normalize")) {normalize = 1;
  	} else if (!strcmp(flag, "wave"))      {filetype = FORMAT_WAVE;
***************
*** 411,416 ****
          } else if (!strcmp(flag, "little"))    {endianness = 0;
          } else if (!strcmp(flag, "r") || !strcmp(flag, "rate")) {
!             if (argc < 2 || argv[1].a_type != A_FLOAT || ((rate = argv[1].a_float) <= 0)) goto usage;
!             argc--; argv++;
          } else goto usage;
      }
--- 394,398 ----
          } else if (!strcmp(flag, "little"))    {endianness = 0;
          } else if (!strcmp(flag, "r") || !strcmp(flag, "rate")) {
!             EAT_ARG(A_FLOAT,rate); if (rate<0) goto usage;
          } else goto usage;
      }
***************
*** 577,626 ****
  static void soundfile_xferout(int nchannels, float **vecs, unsigned char *buf, int nitems, long onset, int bytespersamp,
  int bigendian, float normalfactor) {
!     int i, j;
!     unsigned char *sp, *sp2;
      float *fp;
      int bytesperframe = bytespersamp * nchannels;
!     for (i = 0, sp = buf; i < nchannels; i++, sp += bytespersamp) {
          sp2 = sp; fp = vecs[i] + onset;
          if (bytespersamp == 2) {
              float ff = normalfactor * 32768.;
!             if (bigendian) {
!                 for (j = 0; j < nitems; j++, sp2 += bytesperframe, fp++) {
!                     int xx = clip(int(32768. + (*fp * ff)) - 0x8000,-0x7fff,+0x7fff);
!                     sp2[0] = xx>>8; sp2[1] = xx;
!                 }
!             } else {
!                 for (j = 0; j < nitems; j++, sp2 += bytesperframe, fp++) {
!                     int xx = clip(int(32768. + (*fp * ff)) - 0x8000,-0x7fff,+0x7fff);
!                     sp2[1] = xx>>8; sp2[0] = xx;
!                 }
              }
          } else if (bytespersamp == 3) {
              float ff = normalfactor * 8388608.;
!             if (bigendian) {
!                 for (j = 0; j < nitems; j++, sp2 += bytesperframe, fp++) {
!                     int xx = clip(int(8388608. + (*fp * ff)) - 0x800000,-0x7fffff,+0x7fffff);
!                     sp2[0] = xx>>16; sp2[1] = xx>>8; sp2[2] = xx;
!                 }
!             } else {
!                 for (j = 0; j < nitems; j++, sp2 += bytesperframe, fp++) {
!                     int xx = clip(int(8388608. + (*fp * ff)) - 0x800000,-0x7fffff,+0x7fffff);
!                     sp2[2] = xx>>16; sp2[1] = xx>>8; sp2[0] = xx;
!                 }
              }
          } else if (bytespersamp == 4) {
!             if (bigendian) {
!                 for (j = 0; j < nitems; j++, sp2 += bytesperframe, fp++) {
!                     float f2 = *fp * normalfactor; long xx = *(long *)&f2;
!                     sp2[0] = xx >> 24; sp2[1] = xx >> 16; sp2[2] = xx >> 8; sp2[3] = xx;
!                 }
!             } else {
!                 for (j = 0; j < nitems; j++, sp2 += bytesperframe, fp++) {
!                     float f2 = *fp * normalfactor; long xx = *(long *)&f2;
!                     sp2[3] = xx >> 24; sp2[2] = xx >> 16; sp2[1] = xx >> 8; sp2[0] = xx;
!                 }
              }
          }
      }
  }
  
--- 559,597 ----
  static void soundfile_xferout(int nchannels, float **vecs, unsigned char *buf, int nitems, long onset, int bytespersamp,
  int bigendian, float normalfactor) {
!     unsigned char *sp=buf, *sp2;
      float *fp;
      int bytesperframe = bytespersamp * nchannels;
!     #define LOOP for (int j=0; j<nitems; j++, sp2 += bytesperframe, fp++)
!     for (int i = 0; i < nchannels; i++, sp += bytespersamp) {
          sp2 = sp; fp = vecs[i] + onset;
          if (bytespersamp == 2) {
              float ff = normalfactor * 32768.;
!             if (bigendian) LOOP {
!                 int xx = clip(int(32768. + (*fp * ff)) - 0x8000,-0x7fff,+0x7fff);
!                 sp2[0] = xx>>8; sp2[1] = xx;
!             } else LOOP {
!                 int xx = clip(int(32768. + (*fp * ff)) - 0x8000,-0x7fff,+0x7fff);
!                 sp2[1] = xx>>8; sp2[0] = xx;
              }
          } else if (bytespersamp == 3) {
              float ff = normalfactor * 8388608.;
!             if (bigendian) LOOP {
!                 int xx = clip(int(8388608. + (*fp * ff)) - 0x800000,-0x7fffff,+0x7fffff);
!                 sp2[0] = xx>>16; sp2[1] = xx>>8; sp2[2] = xx;
!             } else LOOP {
!                 int xx = clip(int(8388608. + (*fp * ff)) - 0x800000,-0x7fffff,+0x7fffff);
!                 sp2[2] = xx>>16; sp2[1] = xx>>8; sp2[0] = xx;
              }
          } else if (bytespersamp == 4) {
!             if (bigendian) LOOP {
!                 float f2 = *fp * normalfactor; long xx = *(long *)&f2;
!                 sp2[0] = xx >> 24; sp2[1] = xx >> 16; sp2[2] = xx >> 8; sp2[3] = xx;
!             } else LOOP {
!                 float f2 = *fp * normalfactor; long xx = *(long *)&f2;
!                 sp2[3] = xx >> 24; sp2[2] = xx >> 16; sp2[1] = xx >> 8; sp2[0] = xx;
              }
          }
      }
+     #undef LOOP
  }
  
***************
*** 775,796 ****
  }
  
!     /* soundfiler_read
!     usage: read [flags] filename table ...
!     flags:
!     	-skip <frames> ... frames to skip in file
! 	-nframes <frames>
! 	-onset <frames> ... onset in table to read into (NOT DONE YET)
! 	-raw <headersize channels bytes endian>
! 	-resize
! 	-maxsize <max-size>
! 
!     TB: adapted for threaded use
!     */
! 
! /* callback prototypes */
! static t_int soundfiler_read_update_garray(t_int * w);
! static t_int soundfiler_read_update_graphics(t_int * w);
! static t_int soundfiler_read_output(t_int * w);
! 
  static void soundfiler_t_read(t_soundfiler *x, t_symbol *s, int argc, t_atom *argv) {
      int headersize = -1, channels = 0, bytespersamp = 0, bigendian = 0, resize = 0, i, j;
--- 746,758 ----
  }
  
! /* soundfiler_read
!    usage: read [flags] filename table ...
!    flags: -skip <frames> ... frames to skip in file
! 	-nframes <frames> -onset <frames> ... onset in table to read into (NOT DONE YET)
! 	-raw <headersize channels bytes endian> -resize -maxsize <max-size>
!     TB: adapted for threaded use */
! static t_int soundfiler_read_update_garray(t_int *w);
! static t_int soundfiler_read_update_graphics(t_int *w);
! static t_int soundfiler_read_output(t_int *w);
  static void soundfiler_t_read(t_soundfiler *x, t_symbol *s, int argc, t_atom *argv) {
      int headersize = -1, channels = 0, bytespersamp = 0, bigendian = 0, resize = 0, i, j;
***************
*** 812,838 ****
  	argc--; argv++;
  	if (!strcmp(flag, "skip")) {
! 	    if (argc < 1 || argv[0].a_type != A_FLOAT || ((skipframes = long(argv[0].a_float)) < 0)) goto usage;
! 	    argc--; argv++;
  	} else if (!strcmp(flag, "nframes")) {
! 	    if (argc < 1 || argv[0].a_type != A_FLOAT || ((nframes = long(argv[0].a_float)) < 0)) goto usage;
! 	    argc--; argv++;
  	} else if (!strcmp(flag, "raw")) {
! 		if (argc < 4 ||
! 			argv[0].a_type != A_FLOAT || ((headersize   = int(argv[0].a_float)) < 0) ||
! 			argv[1].a_type != A_FLOAT || ((channels     = int(argv[1].a_float)) < 1) || (channels > MAXSFCHANS) ||
! 			argv[2].a_type != A_FLOAT || ((bytespersamp = int(argv[2].a_float)) < 2) || (bytespersamp > 4) ||
! 			argv[3].a_type != A_SYMBOL ||
! 			((endianness = argv[3].a_symbol->name[0]) != 'b' && endianness != 'l' && endianness != 'n'))
! 			goto usage;
! 		if      (endianness == 'b') bigendian = 1;
! 		else if (endianness == 'l') bigendian = 0;
! 		else	bigendian = garray_ambigendian();
! 		argc -= 4; argv += 4;
  	} else if (!strcmp(flag, "resize")) {
! 		resize = 1;
  	} else if (!strcmp(flag, "maxsize")) {
! 		if (argc < 1 || argv[0].a_type != A_FLOAT || ((maxsize = long(argv[0].a_float)) < 0)) goto usage;
! 		resize = 1;     /* maxsize implies resize. */
! 		argc--; argv++;
  	} else goto usage;
      }
--- 774,793 ----
  	argc--; argv++;
  	if (!strcmp(flag, "skip")) {
! 	    EAT_ARG(A_FLOAT,skipframes); if (skipframes<0) goto usage;
  	} else if (!strcmp(flag, "nframes")) {
! 	    EAT_ARG(A_FLOAT,nframes); if (nframes<0) goto usage;
  	} else if (!strcmp(flag, "raw")) {
!             EAT_ARG(A_FLOAT,headersize); if (headersize<0) goto usage;
!             EAT_ARG(A_FLOAT,channels); if (channels<1) goto usage;
!             EAT_ARG(A_FLOAT,bytespersamp); if (bytespersamp<2 || bytespersamp>4) goto usage;
!             EAT_ARG(A_SYMBOL,endianness); if (endianness!='b' && endianness!='l' && endianness!='n') goto usage;
! 	    if      (endianness == 'b') bigendian = 1;
! 	    else if (endianness == 'l') bigendian = 0;
! 	    else bigendian = garray_ambigendian();
  	} else if (!strcmp(flag, "resize")) {
! 	    resize = 1;
  	} else if (!strcmp(flag, "maxsize")) {
! 	    EAT_ARG(A_FLOAT,maxsize); if (maxsize<0) goto usage;
! 	    resize = 1;     /* maxsize implies resize. */
  	} else goto usage;
      }
***************
*** 842,854 ****
      for (i = 0; i < argc; i++) {
      	if (argv[i].a_type != A_SYMBOL) goto usage;
! 	if (!(garrays[i] = (t_garray *)pd_findbyclass(argv[i].a_symbol, garray_class))) {
! 		pd_error(x, "%s: no such table", argv[i].a_symbol->name);
! 		goto done;
! 	}
!     	else if (!garray_getfloatarray(garrays[i], &vecsize[i], &vecs[i]))
      	    error("%s: bad template for tabwrite", argv[i].a_symbol->name);
      	if (finalsize && finalsize != vecsize[i] && !resize) {
! 		post("soundfiler_read: arrays have different lengths; resizing...");
! 		resize = 1;
  	}
  	finalsize = vecsize[i];
--- 797,809 ----
      for (i = 0; i < argc; i++) {
      	if (argv[i].a_type != A_SYMBOL) goto usage;
! 	garrays[i] = (t_garray *)pd_findbyclass(argv[i].a_symbol, garray_class);
! 	if (!garrays[i]) {
! 	    pd_error(x, "%s: no such table", argv[i].a_symbol->name);
! 	    goto done;
! 	} else if (!garray_getfloatarray(garrays[i], &vecsize[i], &vecs[i]))
      	    error("%s: bad template for tabwrite", argv[i].a_symbol->name);
      	if (finalsize && finalsize != vecsize[i] && !resize) {
! 	    post("soundfiler_read: arrays have different lengths; resizing...");
! 	    resize = 1;
  	}
  	finalsize = vecsize[i];
***************
*** 868,881 ****
  	framesinfile = (eofis - poswas) / (channels * bytespersamp);
  	if (framesinfile > maxsize) {
! 		pd_error(x, "soundfiler_read: truncated to %d elements", maxsize);
! 		framesinfile = maxsize;
  	}
!         if (framesinfile > bytelimit / (channels * bytespersamp))
!             framesinfile = bytelimit / (channels * bytespersamp);
  	finalsize = framesinfile;
      }
      if (!finalsize) finalsize = 0x7fffffff;
!     if (finalsize > bytelimit / (channels * bytespersamp))
!     	finalsize = bytelimit / (channels * bytespersamp);
      fp = fdopen(fd, "rb");
      bufframes = SAMPBUFSIZE / (channels * bytespersamp);
--- 823,834 ----
  	framesinfile = (eofis - poswas) / (channels * bytespersamp);
  	if (framesinfile > maxsize) {
! 	    pd_error(x, "soundfiler_read: truncated to %d elements", maxsize);
! 	    framesinfile = maxsize;
  	}
!         framesinfile = min(framesinfile, bytelimit / (channels * bytespersamp));
  	finalsize = framesinfile;
      }
      if (!finalsize) finalsize = 0x7fffffff;
!     finalsize = min(finalsize, bytelimit / (channels * bytespersamp));
      fp = fdopen(fd, "rb");
      bufframes = SAMPBUFSIZE / (channels * bytespersamp);
***************
*** 886,956 ****
      munlockall();
      /* allocate memory for new array */
! 	if (resize)
! 		for (i = 0; i < argc; i++) {
! 			nvecs[i] = (float *)getalignedbytes(finalsize * sizeof(t_float));
! 			/* if we are out of memory, free it again and quit */
! 			if (nvecs[i]==0) {
! 				pd_error(x, "resize failed");
! 				/* if the resizing fails, we'll have to free all arrays again */
! 				for (j=0; j!=i;++j) freealignedbytes (nvecs[i],finalsize * sizeof(t_float));
! 				goto done;
! 			}
! 		}
! 	else
! 		for (i = 0; i < argc; i++) {
! 			nvecs[i] = (float *)getalignedbytes(vecsize[i] * sizeof(t_float));
! 			/* if we are out of memory, free it again and quit */
! 			if (nvecs[i]==0) {
! 				pd_error(x, "resize failed");
! 				/* if the resizing fails, we'll have to free all arrays again */
! 				for (j=0; j!=i;++j) freealignedbytes (nvecs[i],vecsize[i] * sizeof(t_float));
! 				goto done;
! 			}
  		}
- 	if(i > channels) memset(nvecs[i],0,vecsize[i] * sizeof(t_float));
- 	if (debug) post("transfer soundfile");
- 	for (itemsread = 0; itemsread < finalsize; ) {
- 		int thisread = finalsize - itemsread;
- 		thisread = (thisread > bufframes ? bufframes : thisread);
- 		nitems = fread(sampbuf, channels * bytespersamp, thisread, fp);
- 		if (nitems <= 0) break;
- 		soundfile_xferin(channels, argc, nvecs, itemsread, (unsigned char *)sampbuf, nitems, bytespersamp, bigendian);
- 		itemsread += nitems;
- 	}
- 	if (debug) post("zeroing remaining elements");
- 	/* zero out remaining elements of vectors */
- 	for (i = 0; i < argc; i++) {
- 		for (j = itemsread; j < finalsize; j++) nvecs[i][j] = 0;
- 	}
- 	/* set idle callback to switch pointers */
- 	if (debug) post("locked");
- 	for (i = 0; i < argc; i++) {
- 		t_int* w = (t_int*)getbytes(4*sizeof(t_int));
- 		w[0] = (t_int)(garrays[i]);
- 		w[1] = (t_int)nvecs[i];
- 		w[2] = (t_int)finalsize;
- 		w[3] = (t_int)(&resume_after_callback);
- 		sys_callback(&soundfiler_read_update_garray, w, 4);
- 		pthread_cond_wait(&resume_after_callback, &resume_after_callback_mutex);
  	}
! 	if (debug) post("unlocked, doing graphics updates");
! 	/* do all graphics updates. run this in the main thread via callback */
! 	for (i = 0; i < argc; i++) {
! 		t_int* w = (t_int*)getbytes(2*sizeof(t_int));
! 		w[0] = (t_int)(garrays[i]);
! 		w[1] = (t_int)finalsize;
! 		sys_callback(&soundfiler_read_update_graphics, w, 2);
  	}
! 	/* free the old arrays */
! 	for (i = 0; i < argc; i++) freealignedbytes(vecs[i], vecsize[i] * sizeof(t_float));
! 
      fclose(fp);
      fd = -1;
      goto done;
!  usage:
      pd_error(x, "usage: read [flags] filename tablename...");
      post("flags: -skip <n> -nframes <n> -resize -maxsize <n> ...");
      post("-raw <headerbytes> <channels> <bytespersamp> <endian (b, l, or n)>.");
!  done:
      if (fd>=0) close(fd);
      mlockall(MCL_FUTURE);
--- 839,906 ----
      munlockall();
      /* allocate memory for new array */
!     if (resize)
! 	for (int i=0; i<argc; i++) {
! 		nvecs[i] = (float *)getalignedbytes(finalsize * sizeof(t_float));
! 		/* if we are out of memory, free it again and quit */
! 		if (nvecs[i]==0) {
! 			pd_error(x, "resize failed");
! 			/* if the resizing fails, we'll have to free all arrays again */
! 			for (j=0; j!=i;++j) freealignedbytes (nvecs[i],finalsize * sizeof(t_float));
! 			goto done;
  		}
  	}
!     else
! 	for (int i=0; i<argc; i++) {
! 		nvecs[i] = (float *)getalignedbytes(vecsize[i] * sizeof(t_float));
! 		/* if we are out of memory, free it again and quit */
! 		if (nvecs[i]==0) {
! 			pd_error(x, "resize failed");
! 			/* if the resizing fails, we'll have to free all arrays again */
! 			for (j=0; j!=i;++j) freealignedbytes (nvecs[i],vecsize[i] * sizeof(t_float));
! 			goto done;
! 		}
  	}
!     if(i > channels) memset(nvecs[i],0,vecsize[i] * sizeof(t_float));
!     if (debug) post("transfer soundfile");
!     for (itemsread = 0; itemsread < finalsize; ) {
! 	int thisread = finalsize - itemsread;
! 	thisread = (thisread > bufframes ? bufframes : thisread);
! 	nitems = fread(sampbuf, channels * bytespersamp, thisread, fp);
! 	if (nitems <= 0) break;
! 	soundfile_xferin(channels, argc, nvecs, itemsread, (unsigned char *)sampbuf, nitems, bytespersamp, bigendian);
! 	itemsread += nitems;
!     }
!     if (debug) post("zeroing remaining elements");
!     /* zero out remaining elements of vectors */
!     for (int i=0; i<argc; i++) for (int j=itemsread; j<finalsize; j++) nvecs[i][j] = 0;
!     /* set idle callback to switch pointers */
!     if (debug) post("locked");
!     for (int i=0; i<argc; i++) {
! 	t_int *w = (t_int*)getbytes(4*sizeof(t_int));
! 	w[0] = (t_int)(garrays[i]);
! 	w[1] = (t_int)nvecs[i];
! 	w[2] = (t_int)finalsize;
! 	w[3] = (t_int)(&resume_after_callback);
! 	sys_callback(&soundfiler_read_update_garray, w, 4);
! 	pthread_cond_wait(&resume_after_callback, &resume_after_callback_mutex);
!     }
!     if (debug) post("unlocked, doing graphics updates");
!     /* do all graphics updates. run this in the main thread via callback */
!     for (int i=0; i<argc; i++) {
! 	t_int *w = (t_int*)getbytes(2*sizeof(t_int));
! 	w[0] = (t_int)(garrays[i]);
! 	w[1] = (t_int)finalsize;
! 	sys_callback(&soundfiler_read_update_graphics, w, 2);
!     }
!     /* free the old arrays */
!     for (int i=0; i<argc; i++) freealignedbytes(vecs[i], vecsize[i] * sizeof(t_float));
      fclose(fp);
      fd = -1;
      goto done;
! usage:
      pd_error(x, "usage: read [flags] filename tablename...");
      post("flags: -skip <n> -nframes <n> -resize -maxsize <n> ...");
      post("-raw <headerbytes> <channels> <bytespersamp> <endian (b, l, or n)>.");
! done:
      if (fd>=0) close(fd);
      mlockall(MCL_FUTURE);
***************
*** 999,1003 ****
  /* this is broken out from soundfiler_write below so garray_write can call it too... not done yet though. */
  long soundfiler_t_dowrite(void *obj, t_canvas *canvas, int argc, t_atom *argv) {
!     int bytespersamp, bigendian, swap, filetype, normalize, i, j, nchannels;
      long onset, nframes, itemswritten = 0;
      t_garray *garrays[MAXSFCHANS];
--- 949,953 ----
  /* this is broken out from soundfiler_write below so garray_write can call it too... not done yet though. */
  long soundfiler_t_dowrite(void *obj, t_canvas *canvas, int argc, t_atom *argv) {
!     int bytespersamp, bigendian, swap, filetype, normalize, nchannels;
      long onset, nframes, itemswritten = 0;
      t_garray *garrays[MAXSFCHANS];
***************
*** 1008,1012 ****
      float normfactor, biggest = 0, samplerate;
      t_symbol *filesym;
- 
      if (soundfiler_writeargparse(obj, &argc, &argv, &filesym, &filetype,
  	&bytespersamp, &swap, &bigendian, &normalize, &onset, &nframes, &samplerate))
--- 958,961 ----
***************
*** 1015,1019 ****
      if (nchannels < 1 || nchannels > MAXSFCHANS) goto usage;
      if (samplerate < 0) samplerate = sys_getsr();
!     for (i = 0; i < nchannels; i++) {
      	int vecsize;
      	if (argv[i].a_type != A_SYMBOL) goto usage;
--- 964,968 ----
      if (nchannels < 1 || nchannels > MAXSFCHANS) goto usage;
      if (samplerate < 0) samplerate = sys_getsr();
!     for (int i=0; i<nchannels; i++) {
      	int vecsize;
      	if (argv[i].a_type != A_SYMBOL) goto usage;
***************
*** 1026,1030 ****
      	if (nframes > vecsize - onset)
  	    nframes = vecsize - onset;
! 	for (j = 0; j < vecsize; j++) {
  	    if      (+vecs[i][j] > biggest) biggest = +vecs[i][j];
  	    else if (-vecs[i][j] > biggest) biggest = -vecs[i][j];
--- 975,979 ----
      	if (nframes > vecsize - onset)
  	    nframes = vecsize - onset;
! 	for (int j=0; j<vecsize; j++) {
  	    if      (+vecs[i][j] > biggest) biggest = +vecs[i][j];
  	    else if (-vecs[i][j] > biggest) biggest = -vecs[i][j];
***************
*** 1213,1227 ****
  /* soundfiler_read ...
      usage: read [flags] filename table ...
!     flags:
!         -skip <frames> ... frames to skip in file
!         -nframes <frames>
!         -onset <frames> ... onset in table to read into (NOT DONE YET)
!         -raw <headersize channels bytes endian>
!         -resize
!         -maxsize <max-size>
!     */
! 
  static void soundfiler_read(t_soundfiler *x, t_symbol *s, int argc, t_atom *argv) {
!     int headersize = -1, channels = 0, bytespersamp = 0, bigendian = 0, resize = 0, i, j;
      long skipframes = 0, nframes = 0, finalsize = 0, maxsize = DEFMAXSIZE, itemsread = 0, bytelimit  = 0x7fffffff;
      int fd = -1;
--- 1162,1170 ----
  /* soundfiler_read ...
      usage: read [flags] filename table ...
!     flags: -skip <frames> ... frames to skip in file
!         -nframes <frames> -onset <frames> ... onset in table to read into (NOT DONE YET)
!         -raw <headersize channels bytes endian> -resize -maxsize <max-size> */
  static void soundfiler_read(t_soundfiler *x, t_symbol *s, int argc, t_atom *argv) {
!     int headersize = -1, channels = 0, bytespersamp = 0, bigendian = 0, resize = 0;
      long skipframes = 0, nframes = 0, finalsize = 0, maxsize = DEFMAXSIZE, itemsread = 0, bytelimit  = 0x7fffffff;
      int fd = -1;
***************
*** 1236,1262 ****
  	argc--; argv++;
          if (!strcmp(flag, "skip")) {
!             if (argc < 1 || argv[0].a_type != A_FLOAT || ((skipframes = long(argv[0].a_float)) < 0)) goto usage;
!             argc--; argv++;
          } else if (!strcmp(flag, "nframes")) {
!             if (argc < 1 || argv[0].a_type != A_FLOAT || ((nframes = long(argv[0].a_float)) < 0)) goto usage;
!             argc--; argv++;
          } else if (!strcmp(flag, "raw")) {
!             if (argc < 4 ||
!                 argv[0].a_type != A_FLOAT || ((headersize   = int(argv[0].a_float)) < 0) ||
!                 argv[1].a_type != A_FLOAT || ((channels     = int(argv[1].a_float)) < 1) || (channels > MAXSFCHANS) ||
!                 argv[2].a_type != A_FLOAT || ((bytespersamp = int(argv[2].a_float)) < 2) || (bytespersamp > 4) ||
!                 argv[3].a_type != A_SYMBOL ||
!                     ((endianness = argv[3].a_symbol->name[0]) != 'b' && endianness != 'l' && endianness != 'n'))
!                         goto usage;
              if      (endianness == 'b') bigendian = 1;
              else if (endianness == 'l') bigendian = 0;
              else bigendian = garray_ambigendian();
-             argc -= 4; argv += 4;
          } else if (!strcmp(flag, "resize")) {
              resize = 1;
          } else if (!strcmp(flag, "maxsize")) {
!             if (argc < 1 || argv[0].a_type != A_FLOAT || ((maxsize = long(argv[0].a_float)) < 0)) goto usage;
              resize = 1;     /* maxsize implies resize. */
-             argc--; argv++;
          } else goto usage;
      }
--- 1179,1198 ----
  	argc--; argv++;
          if (!strcmp(flag, "skip")) {
!             EAT_ARG(A_FLOAT,skipframes); if (skipframes<0) goto usage;
          } else if (!strcmp(flag, "nframes")) {
!             EAT_ARG(A_FLOAT,nframes); if (nframes<0) goto usage;
          } else if (!strcmp(flag, "raw")) {
!             EAT_ARG(A_FLOAT,headersize); if (headersize<0) goto usage;
!             EAT_ARG(A_FLOAT,channels); if (channels<1) goto usage;
!             EAT_ARG(A_FLOAT,bytespersamp); if (bytespersamp<2 || bytespersamp>4) goto usage;
!             EAT_ARG(A_SYMBOL,endianness); if (endianness!='b' && endianness!='l' && endianness!='n') goto usage;
              if      (endianness == 'b') bigendian = 1;
              else if (endianness == 'l') bigendian = 0;
              else bigendian = garray_ambigendian();
          } else if (!strcmp(flag, "resize")) {
              resize = 1;
          } else if (!strcmp(flag, "maxsize")) {
!             EAT_ARG(A_FLOAT,maxsize); if (maxsize<0) goto usage;
              resize = 1;     /* maxsize implies resize. */
          } else goto usage;
      }
***************
*** 1264,1271 ****
      filename = argv[0].a_symbol->name;
      argc--; argv++;
!     for (i = 0; i < argc; i++) {
          int vecsize;
          if (argv[i].a_type != A_SYMBOL) goto usage;
!         if (!(garrays[i] = (t_garray *)pd_findbyclass(argv[i].a_symbol, garray_class))) {
              pd_error(x, "%s: no such table", argv[i].a_symbol->name);
              goto done;
--- 1200,1208 ----
      filename = argv[0].a_symbol->name;
      argc--; argv++;
!     for (int i=0; i<argc; i++) {
          int vecsize;
          if (argv[i].a_type != A_SYMBOL) goto usage;
!         garrays[i] = (t_garray *)pd_findbyclass(argv[i].a_symbol, garray_class);
! 	if (!garrays) {
              pd_error(x, "%s: no such table", argv[i].a_symbol->name);
              goto done;
***************
*** 1280,1285 ****
      fd = open_soundfile_via_canvas(x->canvas, filename, headersize, &bytespersamp, &bigendian, &channels, &bytelimit, skipframes);
      if (fd < 0) {
!         pd_error(x, "soundfiler_read: %s: %s", filename, (errno == EIO ?
!             "unknown or bad header format" : strerror(errno)));
          goto done;
      }
--- 1217,1221 ----
      fd = open_soundfile_via_canvas(x->canvas, filename, headersize, &bytespersamp, &bigendian, &channels, &bytelimit, skipframes);
      if (fd < 0) {
!         pd_error(x, "soundfiler_read: %s: %s", filename, (errno == EIO ? "unknown or bad header format" : strerror(errno)));
          goto done;
      }
***************
*** 1296,1303 ****
              framesinfile = maxsize;
          }
!         if (framesinfile > bytelimit / (channels * bytespersamp))
!             framesinfile = bytelimit / (channels * bytespersamp);
          finalsize = framesinfile;
!         for (i = 0; i < argc; i++) {
              int vecsize;
              garray_resize(garrays[i], finalsize);
--- 1232,1238 ----
              framesinfile = maxsize;
          }
!         framesinfile = min(framesinfile, bytelimit / (channels * bytespersamp));
          finalsize = framesinfile;
!         for (int i=0; i<argc; i++) {
              int vecsize;
              garray_resize(garrays[i], finalsize);
***************
*** 1310,1321 ****
      }
      if (!finalsize) finalsize = 0x7fffffff;
!     if (finalsize > bytelimit / (channels * bytespersamp))
!         finalsize = bytelimit / (channels * bytespersamp);
      fp = fdopen(fd, "rb");
      bufframes = SAMPBUFSIZE / (channels * bytespersamp);
- 
      for (itemsread = 0; itemsread < finalsize; ) {
          int thisread = finalsize - itemsread;
!         thisread = (thisread > bufframes ? bufframes : thisread);
          nitems = fread(sampbuf, channels * bytespersamp, thisread, fp);
          if (nitems <= 0) break;
--- 1245,1254 ----
      }
      if (!finalsize) finalsize = 0x7fffffff;
!     finalsize = min(finalsize, bytelimit / (channels * bytespersamp));
      fp = fdopen(fd, "rb");
      bufframes = SAMPBUFSIZE / (channels * bytespersamp);
      for (itemsread = 0; itemsread < finalsize; ) {
          int thisread = finalsize - itemsread;
!         thisread = min(thisread,bufframes);
          nitems = fread(sampbuf, channels * bytespersamp, thisread, fp);
          if (nitems <= 0) break;
***************
*** 1324,1341 ****
      }
      /* zero out remaining elements of vectors */
!     for (i = 0; i < argc; i++) {
!         int vecsize;
!         garray_getfloatarray(garrays[i], &vecsize, &vecs[i]);
!         for (j = itemsread; j < vecsize; j++) vecs[i][j] = 0;
      }
      /* zero out vectors in excess of number of channels */
!     for (i = channels; i < argc; i++) {
!         int vecsize;
!         float *foo;
!         garray_getfloatarray(garrays[i], &vecsize, &foo);
!         for (j = 0; j < vecsize; j++) foo[j] = 0;
      }
      /* do all graphics updates */
!     for (i = 0; i < argc; i++) garray_redraw(garrays[i]);
      fclose(fp);
      fd = -1;
--- 1257,1271 ----
      }
      /* zero out remaining elements of vectors */
!     for (int i=0; i<argc; i++) {
!         int vecsize; garray_getfloatarray(garrays[i], &vecsize, &vecs[i]);
!         for (int j=itemsread; j<vecsize; j++) vecs[i][j]=0;
      }
      /* zero out vectors in excess of number of channels */
!     for (int i=channels; i<argc; i++) {
!         int vecsize; float *foo; garray_getfloatarray(garrays[i], &vecsize, &foo);
!         for (int j=0; j<vecsize; j++) foo[j]=0;
      }
      /* do all graphics updates */
!     for (int i=0; i<argc; i++) garray_redraw(garrays[i]);
      fclose(fp);
      fd = -1;
***************
*** 1353,1357 ****
     call it too... not done yet though. */
  long soundfiler_dowrite(void *obj, t_canvas *canvas, int argc, t_atom *argv) {
!     int bytespersamp, bigendian, swap, filetype, normalize, i, j, nchannels;
      long onset, nframes, itemswritten = 0;
      t_garray *garrays[MAXSFCHANS];
--- 1283,1287 ----
     call it too... not done yet though. */
  long soundfiler_dowrite(void *obj, t_canvas *canvas, int argc, t_atom *argv) {
!     int bytespersamp, bigendian, swap, filetype, normalize, nchannels;
      long onset, nframes, itemswritten = 0;
      t_garray *garrays[MAXSFCHANS];
***************
*** 1362,1366 ****
      float normfactor, biggest = 0, samplerate;
      t_symbol *filesym;
- 
      if (soundfiler_writeargparse(obj, &argc, &argv, &filesym, &filetype,
          &bytespersamp, &swap, &bigendian, &normalize, &onset, &nframes,
--- 1292,1295 ----
***************
*** 1370,1374 ****
      if (nchannels < 1 || nchannels > MAXSFCHANS) goto usage;
      if (samplerate < 0) samplerate = sys_getsr();
!     for (i = 0; i < nchannels; i++) {
          int vecsize;
          if (argv[i].a_type != A_SYMBOL) goto usage;
--- 1299,1303 ----
      if (nchannels < 1 || nchannels > MAXSFCHANS) goto usage;
      if (samplerate < 0) samplerate = sys_getsr();
!     for (int i=0; i<nchannels; i++) {
          int vecsize;
          if (argv[i].a_type != A_SYMBOL) goto usage;
***************
*** 1379,1385 ****
          else if (!garray_getfloatarray(garrays[i], &vecsize, &vecs[i]))
              error("%s: bad template for tabwrite", argv[i].a_symbol->name);
!         if (nframes > vecsize - onset)
!             nframes = vecsize - onset;
!         for (j = 0; j < vecsize; j++) {
              if      (+vecs[i][j] > biggest) biggest = +vecs[i][j];
              else if (-vecs[i][j] > biggest) biggest = -vecs[i][j];
--- 1308,1313 ----
          else if (!garray_getfloatarray(garrays[i], &vecsize, &vecs[i]))
              error("%s: bad template for tabwrite", argv[i].a_symbol->name);
!         nframes = min(nframes, vecsize - onset);
!         for (int j=0; j<vecsize; j++) {
              if      (+vecs[i][j] > biggest) biggest = +vecs[i][j];
              else if (-vecs[i][j] > biggest) biggest = -vecs[i][j];
***************
*** 1488,1498 ****
      t_canvas *canvas;
      t_clock *clock;
!     char *buf;                            /* soundfile buffer */
!     int bufsize;                          /* buffer size in bytes */
!     int noutlets;                         /* number of audio outlets */
!     t_sample *(outvec[MAXSFCHANS]);       /* audio vectors */
!     int vecsize;                          /* vector size for transfers */
!     t_outlet *bangout;                    /* bang-on-done outlet */
!     int state;                            /* opened, running, or idle */
      float insamplerate;   /* sample rate of input signal if known */
          /* parameters to communicate with subthread */
--- 1416,1426 ----
      t_canvas *canvas;
      t_clock *clock;
!     char *buf;                      /* soundfile buffer */
!     int bufsize;                    /* buffer size in bytes */
!     int noutlets;                   /* number of audio outlets */
!     t_sample *(outvec[MAXSFCHANS]); /* audio vectors */
!     int vecsize;                    /* vector size for transfers */
!     t_outlet *bangout;              /* bang-on-done outlet */
!     int state;                      /* opened, running, or idle */
      float insamplerate;   /* sample rate of input signal if known */
          /* parameters to communicate with subthread */
***************
*** 1717,1722 ****
  static t_int *readsf_perform(t_int *w) {
      t_readsf *x = (t_readsf *)(w[1]);
!     int vecsize = x->vecsize, noutlets = x->noutlets, i, j, bytespersample = x->bytespersample, bigendian = x->bigendian;
!     float *fp;
      if (x->state == STATE_STREAM) {
          int wantbytes, sfchannels = x->sfchannels;
--- 1645,1649 ----
  static t_int *readsf_perform(t_int *w) {
      t_readsf *x = (t_readsf *)(w[1]);
!     int vecsize = x->vecsize, noutlets = x->noutlets, bytespersample = x->bytespersample, bigendian = x->bigendian;
      if (x->state == STATE_STREAM) {
          int wantbytes, sfchannels = x->sfchannels;
***************
*** 1742,1748 ****
              }
              /* then zero out the (rest of the) output */
!             for (int i=0; i<noutlets; i++)
!                 for (j = vecsize, fp = x->outvec[i] + xfersize; j--; )
!                     *fp++ = 0;
              sfread_cond_signal(&x->requestcondition);
              pthread_mutex_unlock(&x->mutex);
--- 1669,1676 ----
              }
              /* then zero out the (rest of the) output */
!             for (int i=0; i<noutlets; i++) {
! 		float *fp = x->outvec[i] + xfersize;
!                 for (int j=vecsize; j--; ) *fp++ = 0;
! 	    }
              sfread_cond_signal(&x->requestcondition);
              pthread_mutex_unlock(&x->mutex);
***************
*** 1758,1764 ****
          pthread_mutex_unlock(&x->mutex);
      } else {
!         for (i = 0; i < noutlets; i++)
!             for (j = vecsize, fp = x->outvec[i]; j--; )
!                 *fp++ = 0;
      }
      return w+2;
--- 1686,1693 ----
          pthread_mutex_unlock(&x->mutex);
      } else {
!         for (int i=0; i<noutlets; i++) {
! 	    float *fp = x->outvec[i];
!             for (int j=vecsize; j--; ) *fp++=0;
! 	}
      }
      return w+2;
***************
*** 1881,1886 ****
          } else if (x->requestcode == REQUEST_OPEN) {
              int fd, sysrtn, writebytes;
!             /* copy file stuff out of the data structure so we can
!                relinquish the mutex while we're in open_soundfile(). */
              int bytespersample = x->bytespersample;
              int sfchannels = x->sfchannels;
--- 1810,1814 ----
          } else if (x->requestcode == REQUEST_OPEN) {
              int fd, sysrtn, writebytes;
!             /* copy file stuff out of the data structure so we can relinquish the mutex while we're in open_soundfile(). */
              int bytespersample = x->bytespersample;
              int sfchannels = x->sfchannels;
***************
*** 1890,1898 ****
              t_canvas *canvas = x->canvas;
              float samplerate = x->samplerate;
- 
              /* alter the request code so that an ensuing "open" will get noticed. */
              x->requestcode = REQUEST_BUSY;
              x->fileerror = 0;
- 
              /* if there's already a file open, close it. This should never happen since
  		writesf_open() calls stop if needed and then waits until we're idle. */
--- 1818,1824 ----
***************
*** 1987,1993 ****
  
  static void *writesf_new(t_floatarg fnchannels, t_floatarg fbufsize) {
-     t_writesf *x;
      int nchannels = int(fnchannels), bufsize = int(fbufsize), i;
-     char *buf;
      if (nchannels < 1) nchannels = 1;
      else if (nchannels > MAXSFCHANS) nchannels = MAXSFCHANS;
--- 1913,1917 ----
***************
*** 1995,2001 ****
      else if (bufsize < MINBUFSIZE) bufsize = MINBUFSIZE;
      else if (bufsize > MAXBUFSIZE) bufsize = MAXBUFSIZE;
!     buf = (char *)getbytes(bufsize);
      if (!buf) return 0;
!     x = (t_writesf *)pd_new(writesf_class);
      for (i = 1; i < nchannels; i++) inlet_new(x,x, &s_signal, &s_signal);
      x->f = 0;
--- 1919,1925 ----
      else if (bufsize < MINBUFSIZE) bufsize = MINBUFSIZE;
      else if (bufsize > MAXBUFSIZE) bufsize = MAXBUFSIZE;
!     char *buf = (char *)getbytes(bufsize);
      if (!buf) return 0;
!     t_writesf *x = (t_writesf *)pd_new(writesf_class);
      for (i = 1; i < nchannels; i++) inlet_new(x,x, &s_signal, &s_signal);
      x->f = 0;





More information about the Pd-cvs mailing list