See:
Devices:
gates.h// gates.h
#pragma once
#include "circuit.h"
class Inverter: public eDevice
{
public:
Inverter(): eDevice(2) { }
int getNodeCount() const { return 2; }
string getType() const { return "inverter"; }
static const string code;
string codeString() const { return code; }
int eval(eNode *nodes[]);
};
class Buffer: public eDevice
{
public:
Buffer(): eDevice(2) { }
int getNodeCount() const { return 2; }
string getType() const { return "buffer"; }
static const string code;
string codeString() const { return code; }
//int eval();
};
class And: public eDevice
{
public:
And(): eDevice(3) { }
int getNodeCount() const { return 3; }
string getType() const { return "and"; }
static const string code;
string codeString() const { return code; }
int eval(eNode *nodes[]);
};
class Nand: public eDevice
{
public:
Nand(): eDevice(3) { }
int getNodeCount() const { return 3; }
string getType() const { return "nand"; }
static const string code;
string codeString() const { return code; }
int eval(eNode *nodes[]);
};
class Or: public eDevice
{
public:
Or(): eDevice(3) { }
int getNodeCount() const { return 3; }
string getType() const { return "or"; }
static const string code;
string codeString() const { return code; }
int eval(eNode *nodes[]);
};
class Nor: public eDevice
{
public:
Nor(): eDevice(3) { }
int getNodeCount() const { return 3; }
string getType() const { return "nor"; }
static const string code;
string codeString() const { return code; }
int eval(eNode *nodes[]);
};
class Xor: public eDevice
{
public:
Xor(): eDevice(3) { }
int getNodeCount() const { return 3; }
string getType() const { return "xor"; }
static const string code;
string codeString() const { return code; }
int eval(eNode *nodes[]);
};
class Xnor: public eDevice
{
public:
Xnor(): eDevice(3) { }
int getNodeCount() const { return 3; }
string getType() const { return "xnor"; }
static const string code;
string codeString() const { return code; }
int eval(eNode *nodes[]);
};
gates.cpp// gates.cpp
#include "stdafx.h"
#include <math.h>
#include "gates.h"
const string Inverter::code = "INV";
const string Buffer::code = "BUF";
const string And::code = "AND";
const string Nand::code = "NAND";
const string Or::code = "OR";
const string Nor::code = "NOR";
const string Xor::code = "XOR";
const string Xnor::code = "XNOR";
eDevice *eCircuit::doDigital(string type)
{
if (type==Inverter::code) return new Inverter();
if (type==Buffer::code) return new Buffer();
if (type==And::code) return new And();
if (type==Nand::code) return new Nand();
if (type==Or::code) return new Or();
if (type==Nor::code) return new Nor();
if (type==Xor::code) return new Xor();
if (type==Xnor::code) return new Xnor();
return 0;
}
int Inverter::eval(eNode *nodes[])
{
eNode *inp = nodes[ndx[0]];
eNode *oup = nodes[ndx[1]];
if (!inp->isDefined()) return 1;
double value = 0.5;
if (inp->value<eNode::low) value = 1.0;
else if (inp->value>eNode::high) value = 0.0;
oup->set(value);
return 0;
}
void eCircuit::reset_nodes()
{
for (int i=0; i<ncount; i++) {
eNode *node = nodes[i];
node->defined = false;
}
}
int eCircuit::eval()
{
int count = 0;
eDevice *dev;
for (int i=0; i<ndevices; i++) {
dev = devices[i];
count += dev->eval(nodes);
}
return count;
}
int eCircuit::run()
{
int count, prev_count;
prev_count = count = eval();
cycles=1;
while (count) {
count = eval();
cycles++;
if (count == prev_count) break;
prev_count = count;
}
return count;
}
int aoi(eNode *arg[3], int in, int out)
{
bool defined = true;
double result = (out? 0: 1);
eNode *node;
for (int i=1; i<3; i++) {
node = arg[i];
if (!node->isDefined()) defined = false;
else if (fabs(node->value-in)<0.2) {
result = out;
defined = true;
break;
}
}
if (!defined) return 1;
arg[0]->set(result);
return 0;
}
int And::eval(eNode *nodes[])
{
eNode *arg[3];
for (int i=0; i<3; i++) arg[i] = nodes[ndx[i]];
return aoi(arg,0,0);
}
int Nand::eval(eNode *nodes[])
{
eNode *arg[3];
for (int i=0; i<3; i++) arg[i] = nodes[ndx[i]];
return aoi(arg,0,1);
}
int Or::eval(eNode *nodes[])
{
eNode *arg[3];
for (int i=0; i<3; i++) arg[i] = nodes[ndx[i]];
return aoi(arg,1,1);
}
int Nor::eval(eNode *nodes[])
{
eNode *arg[3];
for (int i=0; i<3; i++) arg[i] = nodes[ndx[i]];
return aoi(arg,1,0);
}
int Xor::eval(eNode *nodes[])
{
eNode *arg[3];
for (int i=0; i<3; i++) arg[i] = nodes[ndx[i]];
if (!arg[1]->isDefined() || !arg[2]->isDefined()) return 1;
if (arg[1]->isLow() && arg[2]->isLow()) arg[0]->set(0.0);
else if (arg[1]->isHigh() && arg[2]->isHigh()) arg[0]->set(0.0);
else arg[0]->set(1.0);
return 0;
}
int Xnor::eval(eNode *nodes[])
{
eNode *arg[3];
for (int i=0; i<3; i++) arg[i] = nodes[ndx[i]];
if (!arg[1]->isDefined() || !arg[2]->isDefined()) return 1;
if (arg[1]->isLow() && arg[2]->isLow()) arg[0]->set(1.0);
else if (arg[1]->isHigh() && arg[2]->isHigh()) arg[0]->set(1.0);
else arg[0]->set(0.0);
return 0;
}
Maintained by John Loomis, updated Wed Feb 14 10:45:51 2007