There is an error in Define_Module(OLT) when i try to build my code.
Am i doing something wrong?
D:\omnetpp-4.6\ptixiaki\XGPON/OLT.cc:18: undefined reference to `OLT::OLT()'
collect2.exe: error: ld returned 1 exit status
make: *** [out/gcc-debug//XGPON.exe] Error 1
Makefile:94: recipe for target 'out/gcc-debug//XGPON.exe' failed
//XGPON.NED
package xgpon;
import ned.DelayChannel;
import ned.IdealChannel;
simple OLT
{
#display("i=device/mainframe");
gates:
input splitter_to_OLT;
output OLT_to_splitter;
}
simple Splitter
{
#display("i=device/modem");
gates:
input ONU_splitter[];
input OLT_splitter;
output splitter_OLT;
output splitter_ONU[];
}
simple ONU
{
#display("i=device/laptop");
gates:
input splitter_to_ONU;
output ONU_to_splitter;
}
network XGPON
{
parameters:
#display("bgb=550,234;i=block/network2");
int n_nodes = 6;
types:
channel upstream extends ned.DatarateChannel
{
datarate = 2.48832 Gbps; //datarate of the channel
}
channel downstream extends ned.DatarateChannel
{
datarate = 9.95328 Gbps; //datarate of the channel
}
submodules:
splitter: Splitter {
#display("p=258,109");
}
olt: OLT {
#display("p=57,59");
}
onu: ONU {
#display("p=393,87");
}
connections:
olt.OLT_to_splitter --> downstream -->splitter.OLT_splitter;
splitter.splitter_OLT --> downstream --> onu.splitter_to_ONU;
splitter.splitter_ONU++ --> upstream --> olt.splitter_to_OLT;
onu.ONU_to_splitter --> upstream --> splitter.ONU_splitter++;
}
//OLT.H
#ifndef OLT_H_
#define OLT_H_
#include <omnetpp.h>
#include <string.h>
#include <iostream>
#include <stdio.h>
#include "Packet_m.h"
#include "DownstreamFrame_m.h"
#include "UpstreamFrame_m.h"
#define FRAME_TIME 691.2
class OLT : public cSimpleModule
{
private:
int source;
//int destination;
simsignal_t arrivalSignal;
int no_sent;
int no_rcvd;
cMessage *DownstreamFrameSendEvent, *NewPacketArrivalEvent;
simtime_t sendTimeout, bufferTimeout;
XGPONpacket *downFragment;
cPacketQueue *OLTBuffer;
std::vector<double> distance, RTT, BandwidthUtilizationProfile, AllocationWeight;
//std::vector<long double> accumulatedRequestedBandwidth , accumulatedAllocatedBandwidth;
std:: vector<int> upstreamBandwidthDemands, DownPacketsForONU, destination;
int oltId, numberOfOnus, headerSize, PSBd, parityBytes, PLOAMdMessages, FrameQueueSize, fragmentBytes, BWMap;
//int FixedGuarandeedBandwidth, totalUpstreamBandwidth, AssuredGuarandeedBandwidth, firstPhaseNonGuarandeedBandwidth;
//long double totalBytesCreated, totalBytesReceived, SumDelay, SquareSumDelay, totalUpDelay, SumBUP;
//double ABU, ProtectionParameter, OverloadedOnusAllocationWeighSum, UpdatingImpact, SW;
double ONU_time_counter ; /* a local time counter for file results */
double variate; /* the final exponenetial variate (interarrivals) */
double sum_variate ; /* used to compute the experimental mean for variate */
double sum_rnd; /* used to compute the experimental mean for UD */
long loops ; /* counter for loops */
long pkt_per_time_unit ; /* nb of pkts per unit of time */
double time; /* our simulated time in us */
double mean,start_pktime,ref_time,end_pktime;
double rnd_nb; /* the uniform random number */
public :
OLT();
virtual ~OLT();
protected:
virtual void initialize();
virtual void handleMessage(cMessage *msg);
virtual XGPONpacket *generatePacket();
virtual void generateFrame(cPacketQueue *queue);
//virtual void generateHeader(cPacketQueue *queue);
virtual void forwardFrame(XGPONpacket *msg);
virtual void finish();
//virtual int defragmentation(cPacketQueue *queue);
};
#endif /* OLT_H_ */
//OLT.CC
#include "OLT.h"
Define_Module(OLT); //the error is here
void OLT::initialize()
{
numberOfOnus = 6;
cPacketQueue* OLTBuffer = new cPacketQueue("OLTBuffer");
for(int i = 0; i<= numberOfOnus; i++){
OLTBuffer->insert(generatePacket());
XGPONpacket *packet = (XGPONpacket *) OLTBuffer->pop();
//Distance
distance.push_back(destination.at(i) + 20);
EV << "My distance is " << distance[i] << " numbers.\n \n";
EV << "My destination is " << packet->getDestination()/2 << ".\n \n";
//RTT
RTT.push_back(distance.at(i) / 3*(10^8));
EV << "My RTT is " << RTT[i] << " numbers.\n \n";
}
EV << "My buffer size is " << OLTBuffer->getLength() << " numbers.\n \n";
//generateFrame(OLTBuffer);
}
void OLT::handleMessage(cMessage *msg)
{
XGPONpacket *ttmsg = check_and_cast<XGPONpacket *>(msg);
forwardFrame(ttmsg);
}
void OLT::generateFrame(cPacketQueue *OLTBuffer)
{
DownFrame *queue = new DownFrame();
//Fmqueue Fmqueue;
queue->~DownFrame();
//FrameQueueSize = queue -> getFrameSize();
//cPacketQueue *queue = new cPacketQueue();
//FrameQueueSize = 155520;
for(int i=0 ; i <OLTBuffer->getLength(); i++)
{
//EV << "GAMW TI MANA SOU " << OLTBuffer->getLength() << " numbers.\n \n";
XGPONpacket *packet = (XGPONpacket *) OLTBuffer->pop();
simtime_t waitingTime = simTime() - packet->getCreationTime();
double processTime = (packet->getBitLength()/(9.95328 * pow (10,9))) + (RTT.at(packet->getDestination())/2);
simtime_t receptTime = waitingTime + processTime;
packet->setReceptionTime(receptTime);
EV << "<<<<<<< OLT (id =" << oltId << ") : Packet " << packet->getName() << "reception time:" << packet->getReceptionTime() << ">>>>> \n";
OLTBuffer -> insert(packet);
}
while ((queue->getByteLength() < FrameQueueSize) && (OLTBuffer->isEmpty() == false))
{
XGPONpacket *max = (XGPONpacket *) OLTBuffer->pop();
for(int i=0; i<OLTBuffer->length(); i++)
{
XGPONpacket *data = (XGPONpacket *) OLTBuffer->pop();
if(max->getReceptionTime() >= data->getReceptionTime())
{
OLTBuffer -> insert(data);
}
else
{
OLTBuffer->insert(max);
max = data->dup();
delete data;
}
}
EV <<"<<<< OLT (id =" << oltId <<") : Packet " << max->getName() << " reception time:" << max->getReceptionTime() << "inserted to frame >>>>\n";
queue->insert(max);
}
}
XGPONpacket *OLT::generatePacket()
{
// Produce source and destination addresses.
//source = getIndex(); // our module index
//Destinationn
int time_limit = 60;
for(source = 1; source <= numberOfOnus-1; source++)
{
ONU_time_counter = 0;
pkt_per_time_unit = 0;
sum_variate = 0;
sum_rnd = 0;
loops = 0;
time=0;
destination.push_back(intuniform(2,numberOfOnus-1));
start_pktime=0.7;
end_pktime=12.7; //1gb prepei na brw transmision time
mean = start_pktime;
ref_time = time;
while( time < time_limit )
{
if(ONU_time_counter >= FRAME_TIME)
{
mean = (double) mean +(end_pktime - start_pktime)/((time_limit - ref_time)/FRAME_TIME);
ONU_time_counter = ONU_time_counter - FRAME_TIME;
/* prints the nb of pkts / unit time */
//fprintf(files1, "\n%ld", pkt_per_time_unit);
pkt_per_time_unit = 0;
}
//rnd_nb = (random()/limit); /* the random number 0<= x <=1 */
rnd_nb = uniform(0,1);
/* compute the IAT */
variate = (-mean)*log(rnd_nb); /* Poisson IAT */
//wait(variate);
XGPONpacket *msg = new XGPONpacket();
msg->setSource(source);
msg->setDestination(destination[source]);
msg->setByteLength(intuniform(64,1518));
return msg;
}
}
}
void OLT::forwardFrame(XGPONpacket *msg)
{
// Same routing as before: random gate.
int n = gateSize("out");
//int k = destination;
//EV << "Forwarding message " << msg << " on gate[" << k << "]\n";
send(msg, "out");
}
void OLT::finish()
{
//recordScalar("#sent", no_sent);
//recordScalar("received", no_rcvd);
}
In OLT.CC add at least an empty constructor and destructor:
OLT::OLT() {
}
OLT::~OLT() {
}
This program is supposed to read acceleration values from a Wii remote and light up LEDs based on those values. The only error I'm getting that prevents compilation is that pBase isn't defined in main.cpp. main.cpp includes ZedBoard.h and ZedBoard.cpp where pBase is defined so I'm failing to see the issue here. I've been trying to solve this for a while and I can't figure it out.
ZedBoard.h
#ifndef ZEDBOARD_H
#define ZEDBOARD_H
const int gpio_led1_offset = 0x12C; // Offset for LED1
const int gpio_led2_offset = 0x130; // Offset for LED2
const int gpio_led3_offset = 0x134; // Offset for LED3
const int gpio_led4_offset = 0x138; // Offset for LED4
const int gpio_led5_offset = 0x13C; // Offset for LED5
const int gpio_led6_offset = 0x140; // Offset for LED6
const int gpio_led7_offset = 0x144; // Offset for LED7
const int gpio_led8_offset = 0x148; // Offset for LED8
const int gpio_sw1_offset = 0x14C; // Offset for Switch 1
const int gpio_sw2_offset = 0x150; // Offset for Switch 2
const int gpio_sw3_offset = 0x154; // Offset for Switch 3
const int gpio_sw4_offset = 0x158; // Offset for Switch 4
const int gpio_sw5_offset = 0x15C; // Offset for Switch 5
const int gpio_sw6_offset = 0x160; // Offset for Switch 6
const int gpio_sw7_offset = 0x164; // Offset for Switch 7
const int gpio_sw8_offset = 0x168; // Offset for Switch 8
const int gpio_pbtnl_offset = 0x16C; // Offset for left push button
const int gpio_pbtnr_offset = 0x170; // Offset for right push button
const int gpio_pbtnu_offset = 0x174; // Offset for up push button
const int gpio_pbtnd_offset = 0x178; // Offset for down push button
const int gpio_pbtnc_offset = 0x17C; // Offset for center push button
// Physical base address of GPIO
const unsigned gpio_address = 0x400d0000;
// Length of memory-mapped IO window
const unsigned gpio_size = 0xff;
// Class Definition
class ZedBoard {
private:
char *pBase; // virtual address where I/O was mapped
int fd; // file descriptor for dev memory
int dummyValue; // for testing without a Zedboard
public:
ZedBoard(); // Default Constructor
~ZedBoard(); // Destructor
void RegisterWrite(char *pBase, int offset, int value);
int RegisterRead(int offset);
void Write1Led(char *pBase, int ledNum, int state);
void WriteAllLeds(int value);
int Read1Switch(int switchNum);
int ReadAllSwitches();
};
#endif
ZedBoard.cpp
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
#include <sys/mman.h>
#include <iostream>
#include "ZedBoard.h"
using namespace std;
/**
* Constructor Initialize general-purpose I/O
* - Opens access to physical memory /dev/mem
* - Maps memory at offset 'gpio_address' into virtual address space
*
* #param None Default constructor does not need arguments.
* #return None Default constructor does not return anything.
*/
ZedBoard::ZedBoard(){
cout << "\nStarting...." << endl;
// dummyValue = 99;
// Uncomment this block of code when connected to the Zedboard
fd = open( "/dev/mem", O_RDWR);
pBase = (char *) mmap(NULL,gpio_size,PROT_READ | PROT_WRITE,
MAP_SHARED,fd,gpio_address);
// Check error
if (pBase == MAP_FAILED)
{
cerr << "Mapping I/O memory failed - Did you run with 'sudo'? \n";
exit(1); // Returns 1 to the operating system;
}
}
/**
* Destructor to close general-purpose I/O.
* - Uses virtual address where I/O was mapped.
* - Uses file descriptor previously returned by 'open'.
*
* #param None Destructor does not need arguments.
* #return None Destructor does not return anything.
*/
ZedBoard::~ZedBoard(){
munmap(pBase, gpio_size);
}
/*
* Write a 4-byte value at the specified general-purpose I/O location.
*
* - Uses base address returned by 'mmap'.
* #parem offset Offset where device is mapped.
* #param value Value to be written.
*/
void ZedBoard::RegisterWrite(char *pBase, int offset, int value)
{
* (int *) (pBase + offset) = value;
// dummyValue = value;
}
/**
* Read a 4-byte value from the specified general-purpose I/O location.
- Uses base address returned by 'mmap'.
#param offset Offset where device is mapped.
#return Value read.
*/
int ZedBoard::RegisterRead(int offset)
{
return * (int *) (pBase + offset);
// return dummyValue;
}
/*
Changes the state of an LED (ON or OFF)
- Uses base address of I/O
#param ledNum LED number (0 to 7)
#param state State to change to (ON or OFF)
*/
/*
Show lower 8 bits of integer value on LEDs
- Calls Write1Led() to set all LEDs
#param value Value to show on LEDs
*/
void ZedBoard::WriteAllLeds(int value)
{
cout << "\nWriting to all LEDs...." << endl;
for(int i = 0; i < 8; i++) {// write to all LEDs
Write1Led(pBase, i, (value / (1<<i)) % 2);
}
}
void ZedBoard::Write1Led(char *pBase, int ledNum, int state)
{
cout << "\nWriting to LED " << ledNum << ": LED state = " << state << endl;
if (ledNum == 1)
{
RegisterWrite(pBase, gpio_led1_offset, state);
}
else
{
RegisterWrite(pBase, gpio_led1_offset + (ledNum * 4), state);
}
}
/*
Reads the value of a switch
- Uses base address of I/O
#param switchNum Switch number (0 to 7)
#return Switch value read
*/
int ZedBoard::Read1Switch(int switchNum)
{
cout << "\nReading Switch " << switchNum << endl;
//return RegisterRead(gpio_sw1_offset + (switchNum * 4));
return switchNum;
}
/*
Reads the switch values into a decimal integer
- Calls Read1Switch() to read all switches
#return Switches' value read
*/
int ZedBoard::ReadAllSwitches()
{
int switchValue = 0;
cout << "\nReading all switches...." << endl;
for(int i = 7; i >= 0; i--) {// read all switches
switchValue = (switchValue << 1) + Read1Switch(i);
}
return switchValue;
}
WiimoteAccel.h
#ifndef WIIMOTEACCEL_H
#define WIIMOTEACCEL_H
class WiimoteAccel{
public:
WiimoteAccel();
~WiimoteAccel();
void Wiimote();
void Listen();
virtual void AccelerationEvent(int code, int acceleration);
private:
int fd;
};
#endif
WiimoteAccel.cpp
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
#include <iostream>
#include "ZedBoard.h"
#include "WiimoteAccel.h"
WiimoteAccel::WiimoteAccel()
{
}
WiimoteAccel::~WiimoteAccel()
{
}
void WiimoteAccel::Wiimote()
{
fd = open("/dev/input/event0", O_RDONLY);
if (fd == -1)
{
std::cerr << "Error: Could not open event file - forgot sudo?\n";
exit(1);
}
}
void WiimoteAccel::Listen()
{
for (;;)
{
// Read a packet of 16 bytes from Wiimote
char buffer[16];
read(fd, buffer, 16);
// Extract code (byte 10) and value (byte 12) from packet
int code = buffer[10];
short acceleration = * (short *) (buffer + 12);
this->AccelerationEvent(code, acceleration);
}
}
void WiimoteAccel::AccelerationEvent(int code, int acceleration)
{
// Print them
std::cout << "Code = " << code << ", acceleration = " << acceleration << '\n';
}
main.cpp
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
#include <iostream>
#include "WiimoteAccel.h"
#include "ZedBoard.h"
#include "ZedBoard.cpp"
using namespace std;
class WiimoteToLed : public WiimoteAccel {
private:
ZedBoard* zed_board;
public:
WiimoteToLed(ZedBoard* zed_board);
~WiimoteToLed();
void AccelerationEvent(int code, int acceleration)
{
int x = 0;
for(;;)
{
if (code == 3)
{
cout << "ACCELERATION IS "<< acceleration <<"!\n";
if(acceleration == 0)
{
x = 0;
}
else if(acceleration > -100 && acceleration <= -75)
{
x = 1;
}
else if(acceleration > -75 && acceleration <= -50)
{
x = 2;
}
else if(acceleration > -50 && acceleration <= -25)
{
x = 3;
}
else if(acceleration > -25 && acceleration > 0)
{
x = 4;
}
else if(acceleration < 0 && acceleration >= 25)
{
x = 5;
}
else if(acceleration < 25 && acceleration >= 50)
{
x = 6;
}
else if(acceleration < 50 && acceleration >= 75)
{
x = 7;
}
else if(acceleration < 75 && acceleration >= 100)
{
x = 8;
}
switch(x)
{
case 0:
cout << "Wiimote isn't moving\n";
zed_board->Write1Led(pBase,1,0);
zed_board->Write1Led(pBase,2,0);
zed_board->Write1Led(pBase,3,0);
zed_board->Write1Led(pBase,4,0);
zed_board->Write1Led(pBase,5,0);
zed_board->Write1Led(pBase,6,0);
zed_board->Write1Led(pBase,7,0);
zed_board->Write1Led(pBase,8,0);
case 1:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,0);
zed_board->Write1Led(pBase,3,0);
zed_board->Write1Led(pBase,4,0);
zed_board->Write1Led(pBase,5,0);
zed_board->Write1Led(pBase,6,0);
zed_board->Write1Led(pBase,7,0);
zed_board->Write1Led(pBase,8,0);
case 2:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,1);
zed_board->Write1Led(pBase,3,0);
zed_board->Write1Led(pBase,4,0);
zed_board->Write1Led(pBase,5,0);
zed_board->Write1Led(pBase,6,0);
zed_board->Write1Led(pBase,7,0);
zed_board->Write1Led(pBase,8,0);
case 3:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,1);
zed_board->Write1Led(pBase,3,1);
zed_board->Write1Led(pBase,4,0);
zed_board->Write1Led(pBase,5,0);
zed_board->Write1Led(pBase,6,0);
zed_board->Write1Led(pBase,7,0);
zed_board->Write1Led(pBase,8,0);
case 4:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,1);
zed_board->Write1Led(pBase,3,1);
zed_board->Write1Led(pBase,4,1);
zed_board->Write1Led(pBase,5,0);
zed_board->Write1Led(pBase,6,0);
zed_board->Write1Led(pBase,7,0);
zed_board->Write1Led(pBase,8,0);
case 5:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,1);
zed_board->Write1Led(pBase,3,1);
zed_board->Write1Led(pBase,4,1);
zed_board->Write1Led(pBase,5,1);
zed_board->Write1Led(pBase,6,0);
zed_board->Write1Led(pBase,7,0);
zed_board->Write1Led(pBase,8,0);
case 6:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,1);
zed_board->Write1Led(pBase,3,1);
zed_board->Write1Led(pBase,4,1);
zed_board->Write1Led(pBase,5,1);
zed_board->Write1Led(pBase,6,1);
zed_board->Write1Led(pBase,7,0);
zed_board->Write1Led(pBase,8,0);
case 7:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,1);
zed_board->Write1Led(pBase,3,1);
zed_board->Write1Led(pBase,4,1);
zed_board->Write1Led(pBase,5,1);
zed_board->Write1Led(pBase,6,1);
zed_board->Write1Led(pBase,7,1);
zed_board->Write1Led(pBase,8,0);
case 8:
zed_board->Write1Led(pBase,1,1);
zed_board->Write1Led(pBase,2,1);
zed_board->Write1Led(pBase,3,1);
zed_board->Write1Led(pBase,4,1);
zed_board->Write1Led(pBase,5,1);
zed_board->Write1Led(pBase,6,1);
zed_board->Write1Led(pBase,7,1);
zed_board->Write1Led(pBase,8,1);
default:
cout << "Code = " << code <<'\n';
}
}
else
{
continue;
}
}
}
};
WiimoteToLed::WiimoteToLed(ZedBoard* zed_board)
{
Wiimote();
}
WiimoteToLed::~WiimoteToLed()
{
}
int main()
{
// Instantiate ZedBoard object statically
ZedBoard zed_board;
// Instantiate WiimoteToLed object statically, passing a pointer to the
// recently created ZedBoard object.
WiimoteToLed wiimote_to_led(&zed_board);
// Enter infinite loop listening to events. The overridden function
// WiimoteToLed::AccelerationEvent() will be invoked when the user moves
// the Wiimote.
wiimote_to_led.Listen();
// Unreachable code, previous function has an infinite loop
return 0;
}
makefile
WiimoteAccel: main.o WiimoteAccel.o
g++ main.o WiimoteAccel.o -o WiimoteAccel
main.o: main.cpp WiimoteAccel.h
g++ -g -Wall -c main.cpp
WiimoteAccel.o: WiimoteAccel.cpp WiimoteAccel.h
g++ -g -Wall -c WiimoteAccel.cpp
clean:
rm main.o WiimoteAccel.o WiimoteAccel
In WiimoteToLed::AccelerationEvent you call
zed_board->Write1Led(pBase,1,1);
but pBase is not declared in this scope. You have a pBase member of the zed_board, but that is a different one.
I have to write a simple sinthesizer at university which uses sdl_mixer to generate sine waves. I got a code from my teacher which work on windows correctly, but in ubuntu it exits with segmentation fault.
I installed both sdl_mixer1.2-dev and sdl1.2-dev packages.
I tried a code that generates tone with sdl_audio. It worked fine, but I heard that for multi-channel playback, sdl_mixer is the solution.
The getch() part of the code is working well, the problem is with the sound manager part.
Can somebody help me to solve this problem?
Here is my code:
#include <iostream>
#include <termios.h>
#include <stdio.h>
#include<cmath>
#include <SDL/SDL_mixer.h>
#include<vector>
using namespace std;
class SoundManager
{
int channelnum;
vector<Mix_Chunk*> chunks;
public:
void init()
{
if (Mix_OpenAudio(48000,AUDIO_S16, 2, 1024) == -1)
{
cerr << "audio hiba" << endl;
exit(1);
}
}
SoundManager(int asked_channelnum=64)
{
channelnum = Mix_AllocateChannels(asked_channelnum);
chunks.assign(channelnum, (Mix_Chunk*)0);
}
int get_channelnum() const
{
return channelnum;
}
void play_stereo(const vector<short int>& v, int volume=128)
{
const short int *p = &(v[0]);
// short int * p = new short int[v.size()];
// for (size_t i=0;i<v.size();i++) {
// p[i]=v[i];
// }
Mix_Chunk * ownsample = new Mix_Chunk;
ownsample->alen = v.size()*2;
ownsample->abuf = (Uint8*)p;
ownsample->allocated = 1;
ownsample->volume = volume;
int playchannel = Mix_PlayChannel(-1, ownsample, 0);
if (playchannel != -1 && chunks[playchannel])
{
delete[] chunks[playchannel]->abuf;
Mix_FreeChunk(chunks[playchannel]);
}
if (playchannel != -1)
chunks[playchannel] = ownsample;
}
};
Mix_Chunk *ownsample = 0;
Mix_Chunk *samples = 0;
void hang()
{
if (Mix_OpenAudio(48000,AUDIO_S16, 2, 1024) == -1)
{
cerr << "audio hiba" << endl;
exit(1);
}
vector<short> s(48000*2,0);
for (int i=0; i<s.size()/2; i++)
{
s[i*2] = sin(i/10.0+i*i/10000.0)*32000*(1/sqrt(i/100.0));
s[i*2+1] = sin(i/10.0)*32000*(1/sqrt(i/100.0));
}
samples = Mix_LoadWAV("ding.wav");
ownsample = new Mix_Chunk;
ownsample->alen = s.size()*2;
ownsample->abuf =(unsigned char*) &(s[0]);
ownsample->allocated = 0;
ownsample->volume = 128;
cout << samples->alen << endl;
if (!samples)
{
cerr << "wav 'ding.wav' open error" << endl;
exit(1);
}
int channelnum = Mix_AllocateChannels(64);
if (channelnum != 64)
{
cerr << "warning: not as many channels are reserved as attended"<<endl;
}
if (Mix_PlayChannel(-1, ownsample, 0)==-1 )
{
cerr << "error on play" << endl;
}
// if (Mix_PlayChannel(-1, samples, 0)==-1 ) {
// cerr << "error on play" << endl;
// }
}
void pitty(SoundManager &sm)
{
vector<short> s(48000*2,0);
for (int i=0; i<s.size()/2; i++)
{
s[i*2] = sin(i/10.0+i*i/10000.0)*32000*(1/sqrt(i/100.0));
s[i*2+1] = sin(i/10.0)*32000*(1/sqrt(i/100.0));
}
sm.play_stereo(s);
}
static struct termios old, New;
/* Initialize New terminal i/o settings */
void initTermios(int echo)
{
tcgetattr(0, &old); /* grab old terminal i/o settings */
New = old; /* make New settings same as old settings */
New.c_lflag &= ~ICANON; /* disable buffered i/o */
New.c_lflag &= echo ? ECHO : ~ECHO; /* set echo mode */
tcsetattr(0, TCSANOW, &New); /* use these New terminal i/o settings now */
}
/* Restore old terminal i/o settings */
void resetTermios(void)
{
tcsetattr(0, TCSANOW, &old);
}
/* Read 1 character - echo defines echo mode */
char getch_(int echo)
{
int ch;
initTermios(echo);
ch = getchar();
resetTermios();
return ch;
}
/* Read 1 character without echo */
int getch(void)
{
return getch_(o);
}
/* Read 1 character with echo */
int getche(void)
{
return getch_(1);
}
int main(void)
{
SoundManager sm(16);
sm.init();
vector<short> s(48000*2,0);
for (int i=0; i<s.size()/2; i++)
{
s[i*2] = sin(i/10.0+i*i/10000.0)*32000*(1/sqrt(i/100.0));
s[i*2+1] = sin(i/10.0)*32000*(1/sqrt(i/100.0));
}
int c;
while (1)
{
c = getch();
cout <<"keycode:\n";
cout <<c;
sm.play_stereo(s);
}
return 0;
}
Thank you for your help in advance.
Greetings,
Istvan Velegi
(1) if you are getting a segmentation fault can you recompile the code with debugging symbols on (if you are using g++ or clang++); use -g3.
(2) run the program using a debugger and get a stack trace of where the code segmentation faults (use gdb).
This looks absolutely, totally bogus:
void play_stereo(const vector<short int>& v, int volume=128)
{
const short int *p = &(v[0]);
//...
ownsample->abuf = (Uint8*)p;
//...
delete[] chunks[playchannel]->abuf;
Yes, I realize chunks[playchannel] isn't ownsample yet, but you do put ownsample into the chunks queue, so eventually you will come back around and try to delete[] the internal array storage of a vector<short int>.
That's very bad.
This commented-out code actually seems to be the correct thing to have in place of const short int *p = &(v[0]):
// short int * p = new short int[v.size()];
// for (size_t i=0;i<v.size();i++) {
// p[i]=v[i];
// }
I am trying to develop a console application, where I will display the system date and time in real time (or as real as I can get). This is the easy part. The hard part is that I must also have the cursor available for the user to enter information through. I can't use NCurses in my application, nor any other library that it not included in vanilla GCC 4.4 (there goes boost! Noooo....)
This is my code so far:
The realtime class, where I am incorporating the solution given by Jeremy Friesner here pthreads in c++ inside classes
#ifndef _REALTIME_H_
#define _REALTIME_H_
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
class MyThreadClass
{
public:
MyThreadClass() {/* empty */}
virtual ~MyThreadClass() {/* empty */}
/** Returns true if the thread was successfully started, false if there was an error starting the thread */
bool startMainThread()
{
return (pthread_create(&_mainThread, NULL, mainRunnerFunc, this) == 0);
}
bool startDisplayThread()
{
return (pthread_create(&_displayThread, NULL, displayThreadFunc, this) == 0);
}
/** Will not return until the main thread has exited. */
void waitForMainThreadToExit()
{
(void) pthread_join(_mainThread, NULL);
}
void waitForDisplayThreadToExit()
{
(void) pthread_join(_displayThread, NULL);
}
protected:
/** Implement this method in your subclass with the code you want your thread to run. */
virtual void mainRunner() = 0;
virtual void displayTime() = 0;
private:
static void * mainRunnerFunc(void * This) {((MyThreadClass *)This)->mainRunner(); return NULL;}
static void * displayThreadFunc(void * This) {((MyThreadClass *)This)->displayTime(); return NULL;}
pthread_t _mainThread;
pthread_t _displayThread;
};
class DynamicTime : public MyThreadClass
{
private:
const string currentDate();
void gotoxy(int,int);
void displayTime();
void mainRunner();
pthread_mutex_t mutex1;
public:
// pthread_mutex_t mutex1;
DynamicTime();
unsigned int lifeTime;
unsigned int updateTime;
void start();
int Exit;
};
const string DynamicTime::currentDate()
{
time_t now = time(0);
struct tm tstruct;
char buf[80];
tstruct = *localtime(&now);
strftime(buf,sizeof(buf),"%I:%M:%S %p, %d-%m-%y",&tstruct);
return buf;
}
DynamicTime::DynamicTime()
{
pthread_mutex_init(&(mutex1),NULL);
lifeTime=-1; /* 100 seconds */
updateTime = 1; /* 5 seconds interval */
Exit=1;
}
void DynamicTime::gotoxy(int x,int y)
{
/* go to location */
printf("\033[%d;%df",y,x);
}
void DynamicTime::displayTime()
{
pthread_mutex_lock(&mutex1);
/* save the cursor location */
printf("\033[s");
gotoxy(75,30);
cout << "Date : " << currentDate() << endl;
/* restore the cursor location */
printf("\033[u");
pthread_mutex_unlock(&mutex1);
}
void DynamicTime::mainRunner()
{
unsigned long iterate, iterate2;
int iret1,iret2;
if(lifeTime!=-1)
{
for(iterate=0;iterate<lifeTime*100000;iterate++)
{
if(iterate%(updateTime*50)==0)
{
iret2 = startDisplayThread();
waitForDisplayThreadToExit();
}
for(iterate2=0;iterate2<100000;iterate2++);
}
std::cout << "Ending main thread..." << endl;
}
else
{
while(1&Exit) /* infinitely */
{
iret2 = startDisplayThread();
waitForDisplayThreadToExit();
for(iterate2=0;iterate2<100000;iterate2++);
}
std::cout << "Exiting Application.... " << endl;
}
}
void DynamicTime::start()
{
//system("clear");
//cout << "Starting...." << endl;
if(startMainThread()==false)
{
std::cerr << "Coudln't start main Thread! " << endl;
}
/* call this function in the main program
* else
{
waitForMainThreadToExit();
}*/
}
/* Example
* on how to use the program
* int main()
{
DynamicTime DT;
DT.lifeTime = 100;
DT.start();
return 0;
}
*/
#endif
and my example program, where I am trying to read data from the user, while showing the time at the same time:
//#include <iostream>
#include "realtime2.h"
int main()
{
DynamicTime DT;
string temp="abcd";
DT.start();
while(temp!="exit")
{
std::cout << "$> " ;
std::cin >> temp;
}
DT.waitForMainThreadToExit();
return 0;
}
This would be called a fully-functional program, if only I could get the user to enter data without interruption from the display thread. Any ideas as to how to get around this ? Or if I can't get around this, what would be the proper way to do so ?
I'm writing a server and I wanted to use XML with my Java client. I'm using CygWin with XercesC 3.1.1 for my development test and this works fine (I looped 30000 with this function and had no crash). However, on my target machine it's running HP-UX with XercesC 2.7. To implement the differences in the XercesC implementation I wrote a separate class to handle each version.
When I try to run the code with XercesC 2.7. I always get a NULL pointer when I try to create the DOMWriter, and a SIGABORT when trying again.
Since I couldn't find anyything on google I hope that someone can shed some light on what I'm doing wrong here. I've been looking at the sample code provided with the XercesC souorce, and I also have some production code from fellow programmers, and I can't see any difference for the live of it.
I tried to create an SSCE which is a bit long, but it is the shortest sample that I could create.
xml_serialize.h
#ifndef XML_SERIALIZE_H_
#define XML_SERIALIZE_H_
#include <string>
#include <xercesc/util/PlatformUtils.hpp>
#include <xercesc/util/XMLString.hpp>
#include <xercesc/dom/DOM.hpp>
#if defined(XERCES_NEW_IOSTREAMS)
#include <iostream>
#else
#include <iostream.h>
#endif
#include <xercesc/util/OutOfMemoryException.hpp>
class XStr
{
public :
// -----------------------------------------------------------------------
// Constructors and Destructor
// -----------------------------------------------------------------------
XStr(const char* const toTranscode)
{
// Call the private transcoding method
fUnicodeForm = xercesc::XMLString::transcode(toTranscode);
}
~XStr()
{
xercesc::XMLString::release(&fUnicodeForm);
}
// -----------------------------------------------------------------------
// Getter methods
// -----------------------------------------------------------------------
const XMLCh* unicodeForm() const
{
return fUnicodeForm;
}
private :
// -----------------------------------------------------------------------
// Private data members
//
// fUnicodeForm
// This is the Unicode XMLCh format of the string.
// -----------------------------------------------------------------------
XMLCh* fUnicodeForm;
};
#define X(str) XStr(str).unicodeForm()
std::string fromXMLString(XMLCh *oXMLString);
class XMLSerialize
{
private:
xercesc::DOMImplementation *mImpl;
protected:
xercesc::DOMImplementation *getDOMImplementation(void);
public:
XMLSerialize(void);
virtual ~XMLSerialize(void);
public:
/**
* Creates an empty DOM
*/
xercesc::DOMDocument *createDocument(const std::string &oDocumentName);
/**
* Parses an XML from a string.
*/
xercesc::DOMDocument *parseDocument(const std::string &oDocumentName, std::string const &oReferenceId);
/**
* Serializes the document into a string
*/
int serialize(xercesc::DOMDocument *oDocument, std::string &oXMLOut, bool bDocumentRelease = true);
};
#endif /* XML_SERIALIZE_H_ */
xml_serialize.cpp
#include <xercesc/util/XMLString.hpp>
#include <xercesc/dom/DOM.hpp>
#include <xercesc/util/TransService.hpp>
#include <xercesc/framework/MemBufFormatTarget.hpp>
#include <xercesc/util/OutOfMemoryException.hpp>
#include <sstream>
#include <vector>
#include <iostream>
#include "xml_serialize.h"
int serializeEnvironment(void);
XMLSerialize *serializer = NULL;
XMLSerialize::XMLSerialize()
{
mImpl = xercesc::DOMImplementationRegistry::getDOMImplementation(X("Core"));
}
XMLSerialize::~XMLSerialize()
{
}
xercesc::DOMDocument *XMLSerialize::createDocument(const std::string &oDocumentName)
{
if(mImpl == NULL)
return NULL;
xercesc::DOMDocument *doc = mImpl->createDocument(
0, // root element namespace URI.
X(oDocumentName.c_str()), // root element name
0); // document type object (DTD).
if(doc == NULL)
return NULL;
return doc;
}
int XMLSerialize::serialize(xercesc::DOMDocument *oDocument, std::string &oXMLOut, bool bDocumentRelease)
{
int result = 0;
XMLCh *xmlUnicode = NULL;
char *strXML = NULL;
xercesc::DOMWriter *serializer = NULL;
if(mImpl == NULL)
{
oXMLOut = "ERROR: XercesC DOMImplementationRegistry not initialized";
result = 1;
goto Quit;
}
serializer = ((xercesc::DOMImplementationLS*)mImpl)->createDOMWriter();
if(serializer == NULL)
{
oXMLOut = "ERROR: XercesC unable to instantiate a DOMWriter!";
result = 2;
goto Quit;
}
xmlUnicode = serializer->writeToString(*oDocument);
strXML = xercesc::XMLString::transcode(xmlUnicode);
oXMLOut = strXML;
if(bDocumentRelease == true)
oDocument->release();
result = 0;
Quit:
if(strXML != NULL)
xercesc::XMLString::release(&strXML);
if(xmlUnicode != NULL)
xercesc::XMLString::release(&xmlUnicode);
if(serializer != NULL)
serializer->release();
return result;
}
int serializeEnvironment(void)
{
int errorCode = 0;
xercesc::DOMElement *rootElem = NULL;
xercesc::DOMElement *item = NULL;
xercesc::DOMElement *element = NULL;
xercesc::DOMText *nameNode = NULL;
xercesc::DOMCDATASection *dataNode = NULL;
std::string xml;
try
{
xercesc::DOMDocument *doc = serializer->createDocument("EnvironmentList");
if(doc == NULL)
return 1;
rootElem = doc->getDocumentElement();
std::vector<std::pair<std::string, std::string> > env;
for(int i = 0; i < 5; i++)
{
std::string key;
std::string value;
std::stringstream ss;
ss << "KEY";
ss << i;
ss >> key;
ss.clear();
ss << "VALUE";
ss << i;
ss >> value;
ss.clear();
env.push_back(std::make_pair(key, value));
}
for(std::vector<std::pair<std::string, std::string> >::const_iterator it = env.begin(); it != env.end(); ++it)
{
std::pair<std::string, std::string>entry = *it;
std::string name = entry.first;
std::string value = entry.second;
if(value.empty())
value = "";
item = doc->createElement(X("item"));
rootElem->appendChild(item);
element = doc->createElement(X("item"));
nameNode = doc->createTextNode(X(name.c_str()));
item->appendChild(element);
element->appendChild(nameNode);
element = doc->createElement(X("item"));
dataNode = doc->createCDATASection(X(value.c_str()));
item->appendChild(element);
element->appendChild(dataNode);
}
errorCode = serializer->serialize(doc, xml);
std::cout << xml << std::endl;
doc->release();
errorCode = 0;
}
catch (const xercesc::OutOfMemoryException&)
{
XERCES_STD_QUALIFIER cerr << "OutOfMemoryException" << XERCES_STD_QUALIFIER endl;
errorCode = 2;
}
catch (const xercesc::DOMException& e)
{
XERCES_STD_QUALIFIER cerr << "DOMException code is: " << e.code << XERCES_STD_QUALIFIER endl;
errorCode = 3;
}
catch (...)
{
XERCES_STD_QUALIFIER cerr << "An error occurred creating the document" << XERCES_STD_QUALIFIER endl;
errorCode = 4;
}
return errorCode;
}
int main()
{
xercesc::XMLPlatformUtils::Initialize();
serializer = new XMLSerialize();
int error = 0;
for(int i = 0; i < 2; i++)
{
std::cout << "Serializing:" << i << " ... " << std::endl;
if((error = serializeEnvironment()) != 0)
std::cout << "ERROR" << error << std::endl;
std::cout << "Done" << std::endl;
}
xercesc::XMLPlatformUtils::Terminate();
return 0;
}
output
Serializing:0 ...
ERROR: XercesC unable to instantiate a DOMWriter!
Done
Serializing:1 ...
aCC runtime: pure virtual function called for class "xercesc_2_7::DOMImplementationLS".
Abort(coredump)
update
I finally managed to compile 2.7 for cygwin and tested the above code there. This works fine, so there must be some problem with the HP-UX environment.
I was compiling the code with gcc and aparently the xerces library was compiled with aCC. So nopw I switched to aCC in my makefile and now it works.
One should expect that the produced libraries are compatible, but apparently this is not the case. So the above code is actually correct.