Home | History | Annotate | Download | only in Tremolo
      1 /************************************************************************
      2  * Copyright (C) 2002-2009, Xiph.org Foundation
      3  * Copyright (C) 2010, Robin Watts for Pinknoise Productions Ltd
      4  * All rights reserved.
      5  *
      6  * Redistribution and use in source and binary forms, with or without
      7  * modification, are permitted provided that the following conditions
      8  * are met:
      9  *
     10  *     * Redistributions of source code must retain the above copyright
     11  * notice, this list of conditions and the following disclaimer.
     12  *     * Redistributions in binary form must reproduce the above
     13  * copyright notice, this list of conditions and the following disclaimer
     14  * in the documentation and/or other materials provided with the
     15  * distribution.
     16  *     * Neither the names of the Xiph.org Foundation nor Pinknoise
     17  * Productions Ltd nor the names of its contributors may be used to
     18  * endorse or promote products derived from this software without
     19  * specific prior written permission.
     20  *
     21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     22  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     24  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     25  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     26  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     27  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     28  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     29  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     30  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     31  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     32  ************************************************************************/
     33 
     34 #define HEAD_ALIGN 64
     35 #include <stdlib.h>
     36 #include <string.h>
     37 #include <stdio.h>
     38 #define MISC_C
     39 #include "misc.h"
     40 //#include <sys/time.h>
     41 
     42 static void **pointers=NULL;
     43 static long *insertlist=NULL; /* We can't embed this in the pointer list;
     44 			  a pointer can have any value... */
     45 
     46 static char **files=NULL;
     47 static long *file_bytes=NULL;
     48 static int  filecount=0;
     49 
     50 static int ptop=0;
     51 static int palloced=0;
     52 static int pinsert=0;
     53 
     54 typedef struct {
     55   char *file;
     56   long line;
     57   long ptr;
     58   long bytes;
     59 } head;
     60 
     61 long global_bytes=0;
     62 long start_time=-1;
     63 
     64 static void *_insert(void *ptr,long bytes,char *file,long line){
     65   ((head *)ptr)->file=file;
     66   ((head *)ptr)->line=line;
     67   ((head *)ptr)->ptr=pinsert;
     68   ((head *)ptr)->bytes=bytes-HEAD_ALIGN;
     69 
     70   if(pinsert>=palloced){
     71     palloced+=64;
     72     if(pointers){
     73       pointers=(void **)realloc(pointers,sizeof(void **)*palloced);
     74       insertlist=(long *)realloc(insertlist,sizeof(long *)*palloced);
     75     }else{
     76       pointers=(void **)malloc(sizeof(void **)*palloced);
     77       insertlist=(long *)malloc(sizeof(long *)*palloced);
     78     }
     79   }
     80 
     81   pointers[pinsert]=ptr;
     82 
     83   if(pinsert==ptop)
     84     pinsert=++ptop;
     85   else
     86     pinsert=insertlist[pinsert];
     87 
     88 #ifdef _VDBG_GRAPHFILE
     89   {
     90     FILE *out;
     91     struct timeval tv;
     92     static struct timezone tz;
     93     int i;
     94     char buffer[80];
     95     gettimeofday(&tv,&tz);
     96 
     97     for(i=0;i<filecount;i++)
     98       if(!strcmp(file,files[i]))break;
     99 
    100     if(i==filecount){
    101       filecount++;
    102       if(!files){
    103 	files=malloc(filecount*sizeof(*files));
    104 	file_bytes=malloc(filecount*sizeof(*file_bytes));
    105       }else{
    106 	files=realloc(files,filecount*sizeof(*files));
    107 	file_bytes=realloc(file_bytes,filecount*sizeof(*file_bytes));
    108       }
    109       files[i]=strdup(file);
    110       file_bytes[i]=0;
    111     }
    112 
    113     file_bytes[i]+=bytes-HEAD_ALIGN;
    114 
    115     if(start_time==-1)start_time=(tv.tv_sec*1000)+(tv.tv_usec/1000);
    116 
    117     snprintf(buffer,80,"%s",file);
    118     if(strchr(buffer,'.'))strchr(buffer,'.')[0]=0;
    119     strcat(buffer,_VDBG_GRAPHFILE);
    120     out=fopen(buffer,"a");
    121     fprintf(out,"%ld, %ld\n",-start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    122 	    file_bytes[i]-(bytes-HEAD_ALIGN));
    123     fprintf(out,"%ld, %ld # FILE %s LINE %ld\n",
    124 	    -start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    125 	    file_bytes[i],file,line);
    126     fclose(out);
    127 
    128     out=fopen("total"_VDBG_GRAPHFILE,"a");
    129     fprintf(out,"%ld, %ld\n",-start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    130 	    global_bytes);
    131     fprintf(out,"%ld, %ld\n",-start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    132 	    global_bytes+(bytes-HEAD_ALIGN));
    133     fclose(out);
    134   }
    135 #endif
    136 
    137   global_bytes+=(bytes-HEAD_ALIGN);
    138 
    139   return(void *)(((char *)ptr)+HEAD_ALIGN);
    140 }
    141 
    142 static void _ripremove(void *ptr){
    143   int insert;
    144 
    145 #ifdef _VDBG_GRAPHFILE
    146   {
    147     FILE *out=fopen("total"_VDBG_GRAPHFILE,"a");
    148     struct timeval tv;
    149     static struct timezone tz;
    150     char buffer[80];
    151     char *file =((head *)ptr)->file;
    152     long bytes =((head *)ptr)->bytes;
    153     int i;
    154 
    155     gettimeofday(&tv,&tz);
    156     fprintf(out,"%ld, %ld\n",-start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    157 	    global_bytes);
    158     fprintf(out,"%ld, %ld\n",-start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    159 	    global_bytes-((head *)ptr)->bytes);
    160     fclose(out);
    161 
    162     for(i=0;i<filecount;i++)
    163       if(!strcmp(file,files[i]))break;
    164 
    165     snprintf(buffer,80,"%s",file);
    166     if(strchr(buffer,'.'))strchr(buffer,'.')[0]=0;
    167     strcat(buffer,_VDBG_GRAPHFILE);
    168     out=fopen(buffer,"a");
    169     fprintf(out,"%ld, %ld\n",-start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    170 	    file_bytes[i]);
    171     fprintf(out,"%ld, %ld\n",-start_time+(tv.tv_sec*1000)+(tv.tv_usec/1000),
    172 	    file_bytes[i]-bytes);
    173     fclose(out);
    174 
    175     file_bytes[i]-=bytes;
    176 
    177   }
    178 #endif
    179 
    180   global_bytes-=((head *)ptr)->bytes;
    181 
    182   insert=((head *)ptr)->ptr;
    183   insertlist[insert]=pinsert;
    184   pinsert=insert;
    185 
    186   if(pointers[insert]==NULL){
    187     fprintf(stderr,"DEBUGGING MALLOC ERROR: freeing previously freed memory\n");
    188     fprintf(stderr,"\t%s %ld\n",((head *)ptr)->file,((head *)ptr)->line);
    189   }
    190 
    191   if(global_bytes<0){
    192     fprintf(stderr,"DEBUGGING MALLOC ERROR: freeing unmalloced memory\n");
    193   }
    194 
    195   pointers[insert]=NULL;
    196 }
    197 
    198 void _VDBG_dump(void){
    199   int i;
    200   for(i=0;i<ptop;i++){
    201     head *ptr=pointers[i];
    202     if(ptr)
    203       fprintf(stderr,"unfreed bytes from %s:%ld\n",
    204 	      ptr->file,ptr->line);
    205   }
    206 
    207 }
    208 
    209 extern void *_VDBG_malloc(void *ptr,long bytes,char *file,long line){
    210   bytes+=HEAD_ALIGN;
    211   if(ptr){
    212     ptr=(void *)(((char *)ptr)-HEAD_ALIGN);
    213     _ripremove(ptr);
    214     ptr=realloc(ptr,bytes);
    215   }else{
    216     ptr=malloc(bytes);
    217     memset(ptr,0,bytes);
    218   }
    219   return _insert(ptr,bytes,file,line);
    220 }
    221 
    222 extern void _VDBG_free(void *ptr){
    223   if(ptr){
    224     ptr=(void *)(((char *)ptr)-HEAD_ALIGN);
    225     _ripremove(ptr);
    226     free(ptr);
    227   }
    228 }
    229 
    230