我正在编写一个c / c ++ SDL合成器,它可以在linux,windows和psp上运行,我可以在代码的多个部分混合使用c / c ++。 我使用new / malloc,我不认为我混淆了它们,但如果我这样做,请告诉我在哪里以及为什么。
我的主程序现在接近20 000线,并且工作正常。 但是当我开始修改它时,我总是陷入一个错误,我无法理解并发现我的真实错误。
当我开始修改我的代码的某些部分时,我陷入了SIGSEV,我需要花费数小时才能让它工作而不理解为什么我会陷入这个问题。 经过一些修改后,它再次起作用,我不知道为什么我有一个SIGSEV以及为什么现在修复它以及我如何修改它以使其工作并防止将来的错误。 所以我请你解释一下我的真正错误。
这是一个带有真正剥离版本的gdb日志和我遇到的崩溃类型:
yoyz@yoyz-laptop:~/build/audio/picoloop/tmp/ gdb ./WaveTable
GNU gdb (GDB) 7.4.1-debian
Copyright (C) 2012 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "x86_64-linux-gnu".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>...
Reading symbols from /home/yoyz/build/audio/picoloop/tmp/WaveTable...done.
(gdb) r
Starting program: /home/yoyz/build/audio/picoloop/tmp/WaveTable
warning: the debug information found in "/lib64/ld-2.13.so" does not match "/lib64/ld-linux-x86-64.so.2" (CRC mismatch).
Generator::init() Allocating memory
Generator::one() 0x00604010
Generator::sine() 0x00604010
Generator::saw() 0x00604010
Generator::pulse() 0x00604010
Program received signal SIGSEGV, Segmentation fault.
_int_malloc (av=0x7ffff7639e40, bytes=32768) at malloc.c:4738
4738 malloc.c: No such file or directory.
(gdb)
以下是代码的精简版:
#include "MyMaster.h"
#include "Generator.h"
#include "WaveTable.h"
#include "WaveTableManager.h"
int main(int argc,char **argv)
{
Generator G;
WaveTableManager & WTM = WaveTableManager::getInstance();
WaveTable* WT;
G.init();
WT = new WaveTable();
WT->setSize(WAVETABLE_SIZE);
G.one();
memcpy(WT->getBuffer(),G.getBuffer(),WAVETABLE_SIZE*DEFAULTBITRATE/8);
WTM.insert(WT,PICO_WAVETABLE_ONE);
WT = new WaveTable();
WT->setSize(WAVETABLE_SIZE);
G.sine();
memcpy(WT->getBuffer(),G.getBuffer(),WAVETABLE_SIZE*DEFAULTBITRATE/8);
WTM.insert(WT,PICO_WAVETABLE_SINE);
WT = new WaveTable();
WT->setSize(WAVETABLE_SIZE);
G.saw();
memcpy(WT->getBuffer(),G.getBuffer(),WAVETABLE_SIZE*DEFAULTBITRATE/8);
WTM.insert(WT,PICO_WAVETABLE_SAW);
WT = new WaveTable();
WT->setSize(WAVETABLE_SIZE);
G.pulse();
memcpy(WT->getBuffer(),G.getBuffer(),WAVETABLE_SIZE*DEFAULTBITRATE/8);
WTM.insert(WT,PICO_WAVETABLE_PULSE);
WT = new WaveTable();
WT->setSize(WAVETABLE_SIZE);
G.triangle();
memcpy(WT->getBuffer(),G.getBuffer(),WAVETABLE_SIZE*DEFAULTBITRATE/8);
WTM.insert(WT,PICO_WAVETABLE_TRGL);
WT = new WaveTable();
WT->setSize(WAVETABLE_SIZE);
G.noise();
memcpy(WT->getBuffer(),G.getBuffer(),WAVETABLE_SIZE*DEFAULTBITRATE/8);
WTM.insert(WT,PICO_WAVETABLE_NOISE);
printf("wavetablemanager.getSize : %d\n",WTM.getSize());
}
MyMaster.h
#ifndef __MASTER____
#define __MASTER____
#include <SDL/SDL.h>
#define WAVETABLE_SIZE 1024*16
#define DEFAULTBITRATE 16
enum
{
PICO_WAVETABLE_SINE,
PICO_WAVETABLE_SAW,
PICO_WAVETABLE_PULSE,
PICO_WAVETABLE_TRGL,
PICO_WAVETABLE_NOISE,
PICO_WAVETABLE_ONE,
PICO_WAVETABLE_SIZE
};
#endif
Generator.h
using namespace std;
#include <SDL/SDL_types.h>
#include <math.h>
#include "MyMaster.h"
#ifndef __GENERATOR__
#define __GENERATOR__
class Generator
{
public:
Generator();
~Generator();
void init();
void sine();
void saw();
void pulse();
void triangle();
void noise();
void one();
Sint16 * getBuffer();
private:
Sint16 * table;
int table_size;
int index;
int d;
};
#endif
Generator.cpp
#include "Generator.h"
Generator::Generator()
{
table_size=WAVETABLE_SIZE;
}
Generator::~Generator()
{
}
void Generator::init()
{
if (table_size>0)
{
printf("Generator::init() Allocating memory\n");
table=(Sint16*)malloc(sizeof(Sint16)*table_size);
if (table==0)
{
printf("Error allocating memory\n");
//return 0;
}
}
}
void Generator::sine()
{
int i;
float f;
Sint16 s;
Sint16 bitdepth=16-1;
printf("Generator::sine() 0x%08.8X\n",table);
for (i=0;i<table_size;i++)
{
s=sin((2*3.14159*i*1)/table_size)*(1<<bitdepth-2);
table[i]=s;
//printf("table[%d]=%d\n",i,s);
}
}
void Generator::saw()
{
int i;
float f;
Sint16 s;
Sint16 bitdepth=16;
Sint16 dec;
printf("Generator::saw() 0x%08.8X\n",table);
s=(1<<(bitdepth-2));
dec=(1<<(bitdepth-2))/(table_size/2);
for (i=0;i<table_size;i++)
{
table[i]=s;
s=s-dec;
}
}
void Generator::pulse()
{
int i;
float f;
Sint16 s;
Sint16 bitdepth=16;
Sint16 dec=(1<<(bitdepth-2))/(table_size/2);
printf("Generator::pulse() 0x%08.8X\n",table);
for (i=0;i<table_size/2;i++)
{
table[i]=((1<<(bitdepth-2))/2);
}
for (i=table_size/2;i<table_size;i++)
{
table[i]=((1<<(bitdepth-2))*-1)/2;
}
}
void Generator::triangle()
{
int i;
float f;
Sint16 s=0;
Sint16 bitdepth=16;
Sint16 dec=(1<<(bitdepth-2))/(table_size/4);
printf("Generator::triangle() 0x%08.8X\n",table);
//table=(Sint16*)malloc(sizeof(Sint16)*table_size);
for (i=0;i<(table_size*1)/4;i++)
{
table[i]=s;
s=s+dec;
}
for (i=(table_size*1)/4;i<(table_size*3)/4;i++)
{
table[i]=s;
s=s-dec;
}
for (i=(table_size*3)/4;i<table_size;i++)
{
table[i]=s;
s=s+dec;
}
}
void Generator::noise()
{
int i;
float f;
Sint16 s;
Sint16 bitdepth=16;
printf("Generator::noise() 0x%08.8X\n",table);
srand(1<<(bitdepth-2));
for (i=0;i<table_size;i++)
{
if (rand()%2==0)
table[i]=rand()%8192;
else
table[i]=(rand()%8192)*-1;
}
}
void Generator::one()
{
int i;
float f;
Sint16 s;
Sint16 bitdepth=16;
printf("Generator::one() 0x%08.8X\n",table);
for (i=0;i<table_size;i++)
{
table[i]=1<<bitdepth-1;
}
}
Sint16 * Generator::getBuffer()
{
return table;
}
WaveTable.h
#include "MyMaster.h"
#include <SDL/SDL_types.h>
#ifndef __WAVETABLE__
#define __WAVETABLE__
class WaveTable
{
public:
WaveTable();
~WaveTable();
int setSize(int bufferSize);
int allocMemory();
int freeMemory();
Sint16 * getBuffer();
char * getName();
Sint32 getSize();
private:
Sint32 size;
Sint16 * buffer;
char * name;
};
#endif
WaveTable.cpp
#include "WaveTable.h"
using namespace std;
WaveTable::WaveTable()
{
size=0;
buffer=0;
name=0;
}
WaveTable::~WaveTable()
{
}
int WaveTable::allocMemory()
{
if (size>0)
{
buffer=(Sint16*)malloc(sizeof(Sint16)*size);
if (buffer==0)
{
printf("Error allocating memory\n");
return 0;
}
}
return size;
}
int WaveTable::freeMemory()
{
if (buffer!=0)
{
free(buffer);
buffer=0;
}
}
int WaveTable::setSize(int bufferSize)
{
if (bufferSize>=0)
size=bufferSize;
if (buffer!=0)
this->freeMemory();
return this->allocMemory();
}
Sint16 * WaveTable::getBuffer()
{
return buffer;
}
WaveTableManager.h
using namespace std;
#include <vector>
#include "WaveTable.h"
#ifndef __WAVETABLEMANAGER__
#define __WAVETABLEMANAGER__
class WaveTableManager
{
private:
WaveTableManager();
~WaveTableManager();
vector<WaveTable*> wtvector;
int size;
public:
static WaveTableManager& getInstance();
int getSize();
void insert(WaveTable * WT,int position);
WaveTable * get(int position);
};
#endif
WaveTableManager.cpp
#include "WaveTableManager.h"
WaveTableManager::WaveTableManager() : wtvector()
{
size=0;
}
WaveTableManager::~WaveTableManager()
{
}
WaveTableManager& WaveTableManager::getInstance()
{
static WaveTableManager instance;
return instance;
}
int WaveTableManager::getSize()
{
return wtvector.size();
}
void WaveTableManager::insert(WaveTable * WT,int position)
{
if (wtvector.size()<=position)
wtvector.resize(position);
wtvector[position]=WT;
}
WaveTable * WaveTableManager::get(int position)
{
return wtvector[position];
}
Makefile.WaveTable
CC=g++
CFLAGS=-O0 -DLINUX -D__RTAUDIO__ -DLINUX_DESKTOP -I. -LSDL/lib -g -fpermissive
SOURCES=WaveTableTest.cpp WaveTable.cpp WaveTableManager.cpp Generator.cpp
OBJECTS=$(SOURCES:.cpp=.o)
EXECUTABLE=WaveTable
all: $(SOURCES) $(EXECUTABLE)
$(EXECUTABLE): $(OBJECTS)
$(CC) $(LDFLAGS) $(OBJECTS) -o $@
.cpp.o:
$(CC) -c $(CFLAGS) $< -o $@
clean:
-rm -f $(OBJECTS) $(EXECUTABLE)
答案 0 :(得分:0)
这是一个问题:
void WaveTableManager::insert(WaveTable * WT,int position)
{
if (wtvector.size()<=position)
wtvector.resize(position);
wtvector[position]=WT; // < -- Out of bounds access
}
当您致电resize()
时,上限为vector::size()-1
。由于position
是向量的新大小,您可能想要的是:
wtvector[position - 1] = WT;