Files
pip/main.cpp
2013-03-18 12:07:44 +04:00

468 lines
16 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/*
PIP - Platform Independent Primitives
Test program
Copyright (C) 2013 Ivan Pelipenko peri4ko@gmail.com
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "pip.h"
class ThreadTest: public PIThread {
public:
ThreadTest(): PIThread() {cnt = 0; b = r = e = false;}
int cnt;
bool b, r, e;
private:
void begin() {b = true; cout << " thread begin\n";}
void run() {r = true; cout << " thread run " << cnt++ << endl; if (cnt == 10) stop();}
void end() {e = true; cout << " thread end\n";}
};
PIMutex mutex_;
bool m = false;
int cnt = 0, gm = 0;
class MutexTest: public PIThread {
public:
MutexTest(): PIThread() {;}
private:
void run() {mutex_.lock(); if (m && cnt > 1) gm++; m = true; cout << " " << flush; if (cnt++ >= 128) stop(); msleep(1); mutex_.unlock();}
};
class MutexTest2: public PIThread {
public:
MutexTest2(): PIThread() {;}
private:
void run() {mutex_.lock(); if (!m && cnt > 1) gm++; m = false; cout << "|" << flush; if (cnt++ >= 128) stop(); msleep(1); mutex_.unlock();}
};
void signalFunc(PISignals::Signal signal) {
if (signal != PISignals::Interrupt) return;
cout << "Ctrl+C pressed, exiting ..." << endl;
exit(0);
};
bool t = false;
void timerEvent(void * data, int delim) {
t = true;
cout << " tick from constuctor, delimiter = " << delim << ", data = " << data << endl;
};
bool t2 = false;
void timerEvent2(void * data, int delim) {
t2 = true;
cout << " tick from delimiter " << delim << ", data = " << data << endl;
};
class ObjectTest: public PIObject {
public:
ObjectTest(const PIString & name = PIString()): PIObject(name) {h = hi = ht = false;}
EVENT_HANDLER(ObjectTest, void, handler) {h = true; cout << " handler in \"" << name() << "\"" << endl;}
EVENT_HANDLER2(ObjectTest, void, handler_i_s, int, i, PIString, s) {hi = true; cout << " handler_i_s in \"" << name() << "\", i = " << i << ", s = \"" << s << "\"" << endl;}
EVENT_HANDLER2(ObjectTest, void, handler_timeout, void * , data, int, delim) {ht = true; cout << " handler_timeout in \"" << name() << "\", data = " << data << ", delim = " << delim << endl;}
bool h, hi, ht;
};
class ObjectTest2: public PIObject {
public:
ObjectTest2(const PIString & name = PIString()): PIObject(name) {;}
void raise0(const PIString & e) {cout << " event \"" << e << "\" from \"" << name() << "\"" << endl; raiseEvent(this, e);}
void raise2(const PIString & e, int i, const PIString & s) {cout << " event \"" << e << "\" from \"" << name() << "\"" << endl; raiseEvent<int, PIString>(this, e, i, s);}
EVENT(ObjectTest2, event0)
EVENT(ObjectTest2, event2)
};
class CA: public PIObject {
public:
CA(const PIString & n): PIObject(n) {;}
EVENT_HANDLER(CA, void, handler_ca) {a = true; cout << " handler CA" << endl;}
EVENT(CA, event_ca)
bool a;
};
class CB: public CA {
public:
CB(const PIString & n): CA(n) {;}
EVENT_HANDLER(CB, void, handler_cb) {b = true; cout << " handler CB" << endl;}
bool b;
};
class CC: public CB {
public:
CC(const PIString & n): CB(n) {;}
EVENT_HANDLER(CC, void, handler_cc) {c = true; cout << " handler CC" << endl;}
bool c;
};
class CD: public CC {
public:
CD(const PIString & n): CC(n) {;}
EVENT_HANDLER(CD, void, handler_cd) {d = true; cout << " handler CD" << endl;}
bool d;
};
struct Packet {
int from;
int to;
float data;
int cs;
};
#pragma pack(push,1)
struct InpuData {
uint first_number; // Номер первого отсчета
struct {
uchar packet_number: 7; // Идентификационный код пакета
uchar packet_last : 1; // Признак последнего пакета
};
struct {
uchar antenna_number : 3; // Номер антенного канала
uchar frequency_number: 3; // Номер частотного канала
uchar data_type : 2; // Вид передаваемой информации: 0 оцифровка, 1 измеренные параметры
};
uchar data[122]; // Данные
};
struct msgHeader {
char sign[4];
unsigned short size;
unsigned short cnt;
unsigned char fragment;
unsigned short msg_id;
unsigned char sys_id;
unsigned char subsys_id;
unsigned char security;
bool verify_sign()
{
bool ok;
ok = sign[0] == 'B';
ok = ok && sign[1] == 'R';
ok = ok && sign[2] == 'K';
ok = ok && sign[3] == 'D';
return ok;
}
};
struct FilterCommand {
FilterCommand() {
memset(this, 0, sizeof(FilterCommand));
header.sign[0] = 'B'; header.sign[1] = 'R'; header.sign[2] = 'K'; header.sign[3] = 'D';
header.size = sizeof(FilterCommand);
header.cnt = header.fragment = header.security = 0;
header.msg_id = 2102;
header.sys_id = header.subsys_id = 2;
command = 3;
}
msgHeader header;
uchar command; // 3
struct {
uchar fi_number: 7; // номер частотного участка, 1 - 36
uchar bort : 1; // борт: 0 - левый, 1 - правый
};
ushort freq_start; // начальная частота, 0 - 6100
ushort freq_end; // конечная частота, 0 - 6100
uchar filter_bandwith; // полоса проспускания фильтра
ushort filter_time_step; // время шага фильтра по времени
uchar reserve;
ushort record_time_start; // начальное время записи, 1 - 60 мс
ushort record_time_end; // конечное время записи, 1 - 60 мс
uchar record_channels; // номера каналов для записи, 0 - 5 биты
uchar play_channels; // номера каналов для воспроизведения, 0 - 5 биты
uchar signal_type; // тип сигнала для выдачи, 0 - С3, 1 - С4, 2 - С4Ф, 3 - выборка
ushort play_time_start; // начальное время воспроизведения, 1 - 60 мс
ushort play_time_end; // конечное время воспроизведения, 1 - 60 мс
uchar checksum;
};
#pragma pack(pop)
void te(void*, int);
PITimer tm_(te);
PISerial ser("/dev/ttyS0");
bool pins[9];
void te(void*, int) {
for (int i = 1; i <= 9; ++i)
pins[i - 1] = ser.isPin(i);
}
void ke(char key, void*) {
int p = key - '0';
if (key >= '1' && key <= '9')
ser.setPin(p, !pins[p - 1]);
}
int main(int argc, char * argv[]) {
/*tm_.start(10.);
PIConsole con(false, ke);
con.enableExitCapture();
//ser.setParameter(PISerial::HardwareFlowControl);
ser.open();
con.addVariable("1 (CAR)", pins);
con.addVariable("2 (SR) ", pins + 1);
con.addVariable("3 (ST) ", pins + 2);
con.addVariable("4 (DTR)", pins + 3);
con.addVariable("5 (GND)", pins + 4);
con.addVariable("6 (DSR)", pins + 5);
con.addVariable("7 (RTS)", pins + 6);
con.addVariable("8 (CTS)", pins + 7);
con.addVariable("9 (RNG)", pins + 8);
con.start();
con.waitForFinish();
return 0;*/
/*FilterCommand fc;
PIEthernet eth(PIEthernet::TCP_SingleTCP);
eth.open("127.0.0.1:10201");
while (1) {
eth.read(&fc, sizeof(fc));
cout << int(fc.fi_number) << ", " << int(fc.bort) << ", " << int(fc.freq_start) << ", " << int(fc.freq_end) << ", " << int(fc.play_channels) << ", " << int(fc.record_channels) << endl;
}
return 0;*/
/*PIDir dir(argv[1]);
FILE*f = popen("cd ../ && pwd", "w");
char fd[4096];
int ret = fread(fd, 4096, 1, f);
pclose(f);
cout << PIString(fd, ret);
f = popen("cd ../ && pwd", "w");
ret = fread(fd, 4096, 1, f);
pclose(f);
cout << PIString(fd, ret);
return 0;
cout << dir.path() << endl;
dir.up();
cout << dir.path() << endl;
PIVector<PIDir::DirEntry> ent = dir.entries();
piForeachC (PIDir::DirEntry & i, ent)
cout << i.mode << " " << PIString::readableSize(i.size).expandRightTo(10, ' ') << " " << i.name << endl;*/
/*PISystemTime st_time, inc_time;
PITimer tm_;
tm_.reset();
inc_time = PISystemTime::fromMilliseconds(50);
st_time = currentSystemTime() + inc_time;
int cnt = 100;
while (cnt--) {
(st_time - currentSystemTime()).sleep();
{
msleep(49);
cout << "tick " << cnt << endl;
}
st_time += inc_time;
}
cout << tm_.elapsed_s() - 0.049 << endl;*/
/*PISystemTime t0, inc_time;
PITimer tm_;
tm_.reset();
inc_time = PISystemTime::fromMilliseconds(50);
inc_time.sleep();
int cnt = 100;
while (cnt--) {
t0 = currentSystemTime();
{
msleep(49);
cout << "tick " << cnt << endl;
}
(inc_time - (currentSystemTime() - t0)).sleep();
}
cout << tm_.elapsed_s() - 0.049 << endl;*/
//return 0;
/*InpuData data;
PIEthernet eth(PIEthernet::UDP);
data.first_number = 0;
data.packet_number = 0;
data.packet_last = 0;
data.antenna_number = data.frequency_number = data.data_type = 0;
PIBitArray ba_;
for (int i = 0; i < 97; ++i) {
for (int b = 0; b < 10; ++b)
ba_.push_back(((i >> b) & 1) == 1);
}
//cout << ba_.byteSize() << ", " << ba_.bitSize() << endl;
memcpy(data.data, ba_.data(), 122);
cout << ba_ << endl;
for (int i = 0; i < 122; ++i)
cout << int(data.data[i]) << ", ";
cout << endl;
eth.send("127.0.0.1:5000", &data, sizeof(data));
return 0;*/
/*QApplication app(argc, argv);
PIFFT fft;
PIVector<complexd> in;
in.resize(50*1000);
for (int i=400; i<404; i++) in[i] = complexd(1,0);
PITimer timer_;
fft.prepareFFT(in.size());
timer_.reset();
PIVector<complexd> * out = fft.calcFFT(in);
cout << timer_.elapsed_m() << endl;
Graphic * g = new Graphic();
QVector<QPointF> res;
fft.getAmplitude();
for (int i=0; i<out->size(); i++) res.append(QPointF(i,abs(out->at(i))));
g->setGraphicData(res);
g->addGraphic("arg", Qt::darkBlue);
res.clear();
for (int i=0; i< out->size(); i++) res.append(QPointF(i,arg(out->at(i))));
g->setGraphicData(res, 1);
g->show();
return app.exec();*/
bool r_string = true, r_thread = true, r_mutex = true, r_timer = true, r_file = true, r_eval = true, r_event = true;
bool succ = true;
cout << "== PIP test program ==" << endl;
cout << "== Built with PIP " << PIPVersion() << " ==" << endl << endl;
cout << "== String test ==" << endl;
PIString string("test string");
cout << " \"test string\" -> \"" << string << "\"" << endl;
if (string.length() != 11) succ = r_string = false;
cout << " to char * = \"" << string.data() << "\"" << endl;
cout << " to std::string = \"" << string.stdString() << "\"" << endl;
if (string.stdString().length() != 11) succ = r_string = false;
#ifdef HAS_LOCALE
cout << " to std::wstring = \"" << string.stdWString() << "\"" << endl;
if (string.stdWString().length() != 11) succ = r_string = false;
#endif
if (succ) cout << " convertions success" << endl;
else cout << " convertions fail" << endl;
succ = true;
string = PIString("αβγ°℃");
cout << " \"αβγ°℃\" -> \"" << string << "\"" << endl;
if (string.length() != 5) succ = r_string = false;
cout << " to char * = \"" << string.data() << "\"" << endl;
cout << " to std::string = \"" << string.stdString() << "\"" << endl;
if (string.stdString().length() != 11) succ = r_string = false;
#ifdef HAS_LOCALE
cout << " to std::wstring = \"" << string.stdWString() << "\"" << endl;
if (string.stdWString().length() != 5) succ = r_string = false;
#endif
if (succ) cout << " complex convertions success" << endl;
else cout << " complex convertions fail" << endl;
if (r_string) cout << "== Success ==" << endl;
else cout << "== Fail ==" << endl;
cout << endl << "== Thread test ==" << endl;
ThreadTest thread;
thread.start(100);
msleep(10);
thread.waitForFinish();
r_thread = thread.b && thread.r && thread.e && thread.cnt == 10;
if (r_thread) cout << "== Success ==" << endl;
else cout << "== Fail ==" << endl;
cout << endl << "== Mutex test ==" << endl << " ";
MutexTest thread_m;
MutexTest2 thread_m2;
thread_m.start();
thread_m2.start();
thread_m.waitForFinish();
thread_m2.waitForFinish();
cout << endl;
r_mutex = gm < 5;
if (r_mutex) cout << "== Success ==" << endl;
else cout << "== Fail ==" << endl;
cout << endl << "== Timer test ==" << endl;
PITimer timer(timerEvent, (void*)255);
timer.addDelimiter(2);
timer.addDelimiter(5, timerEvent2);
timer.start(100.f);
msleep(1005);
timer.stop();
r_timer = t && t2;
if (r_timer) cout << "== Success ==" << endl;
else cout << "== Fail ==" << endl;
cout << endl << "== File test ==" << endl;
PIFile file(" file_test", PIIODevice::ReadWrite);
cout << " file \"" << file.path() << "\" is ";
if (!file.isOpened()) cout << "not ";
cout << "opened" << endl;
file.clear();
file << "test string";
cout << " write " << file.pos() << " bytes" << endl;
if (file.pos() != 11) r_file = false;
PIByteArray ba = file.readAll();
if (ba.size() != 11) r_file = false;
cout << " read " << ba.size() << " bytes: \"" << PIString(ba) << '\"' << endl;
file.remove();
if (r_file) cout << "== Success ==" << endl;
else cout << "== Fail ==" << endl;
cout << endl << "== Evaluator test ==" << endl;
PIEvaluator evaluator;
evaluator.setVariable("x", complexd(2., 1.));
PIString expression("2x^2 + i");
evaluator.check(expression);
cout << " expression = \"" << expression << '\"' << endl;
cout << " recognized = \"" << evaluator.expression() << '\"' << endl;
cout << " error = \"" << evaluator.error() << '\"' << endl;
cout << " \"x\" = " << evaluator.content.variable("x").value << endl;
cout << " result = " << evaluator.evaluate() << endl;
r_eval = round(evaluator.lastResult()) == complexd(6., 9.);
if (r_eval) cout << "== Success ==" << endl;
else cout << "== Fail ==" << endl;
cout << endl << "== Event test ==" << endl;
ObjectTest object("obj");
ObjectTest2 object2("obj2");
PITimer timer2;
timer2.setData((void * )128);
timer2.addDelimiter(2);
timer2.addDelimiter(5);
CONNECT0(void, &object2, event0, &object, handler);
CONNECT2(void, int, PIString, &object2, event2, &object, handler_i_s);
CONNECT2(void, void * , int, &timer2, timeout, &object, handler_timeout);
object2.raise0("event0");
object2.raise2("event2", 123, "string");
timer2.start(100.f);
msleep(505);
timer2.stop();
CA ca("cd");
CD cd("cd");
CONNECT(void, &ca, event_ca, &cd, handler_cd);
CONNECT(void, &ca, event_ca, &cd, handler_cc);
CONNECT(void, &ca, event_ca, &cd, handler_cb);
CONNECT(void, &ca, event_ca, &cd, handler_ca);
PIObject::raiseEvent(&ca, "event_ca");
r_event = object.h && object.hi && object.ht && cd.a && cd.b && cd.c && cd.d;
if (r_event) cout << "== Success ==" << endl;
else cout << "== Fail ==" << endl;
cout << endl << "== Results ==" << endl;
cout << "= String " << r_string << " =" << endl;
cout << "= Thread " << r_thread << " =" << endl;
cout << "= Mutex " << r_mutex << " =" << endl;
cout << "= Timer " << r_timer << " =" << endl;
cout << "= File " << r_file << " =" << endl;
cout << "= Evaluator " << r_eval << " =" << endl;
cout << "= Event " << r_event << " =" << endl;
if (r_string && r_thread && r_mutex && r_timer && r_file && r_eval && r_event)
cout << "== All tests successful ==" << endl;
};