-
Notifications
You must be signed in to change notification settings - Fork 1
/
Tangle.h
170 lines (117 loc) · 5.75 KB
/
Tangle.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
#pragma once
#include <array>
#include <vector>
#include <memory>
#include <map>
#include <utility>
#include <random>
#include <ctime>
#include <omnetpp.h>
struct Tx;
class Tangle;
class TxActor;
const unsigned int APPROVE_VAL = 2;
using t_ptrTx = Tx*;
using t_txApproved = std::vector<t_ptrTx>;
struct Tx
{
//Other transactions that have approved this transaction
std::vector<t_ptrTx> m_approvedBy;
//Transactions approved by this transactions
t_txApproved m_TxApproved;
//The transactor that issued this transaction
TxActor * m_issuedBy;
//Time that the transaction was issued - set by TxActor on intialisation in TxActor::Attach
omnetpp::simtime_t timeStamp;
//Time this transaction ceased to be a tip
omnetpp::simtime_t firstApprovedTime;
int m_walkBacktracks;
bool isGenesisBlock = false;
bool isApproved = false;
// Only used by ComputeWeight and _computeWeight, set when the recursion visits this transaction
// reset to false in ComputeWeight
bool isVisited = false;
bool hasApprovees();
// Keep track of how many transactions have been created, use this number on construction to set
// an identifier per transaction
static long int tx_totalCount;
long int TxNumber;
//Define constructor to set TxNumber - no other reason, otherwise POD
Tx();
};
class Tangle
{
//TODO: Make singleton
private:
// Keep a record of all the current unapproved transactions
std::map<int, t_ptrTx> m_tips;
// The first transaction - initialised on construction
t_ptrTx m_genesisBlock;
// RNG in tangle to simplify tip selection
//TODO: Reimplement to take as a param from omnet ned file
std::mt19937 tipSelectGen;
public:
Tangle();
// Determines how far back a transactor will look into the tangle for a start point, from which they will
// move out to a tip to approve (tip selection)
//TODO: Move this to TXactor - can then be configurable per transactor
int walkDepth;
//All transactions
std::vector<t_ptrTx> allTx;
// Returns a copy of the current tips from the Tangle (Needs to be a copy to simulate an asynchronous view of the tangle per transactor)
std::map<int, t_ptrTx> giveTips();
// Compares the tips just approved ( removeTips ) with the tangles tip view, if it finds any references to the tips just approved
// it will remove them from the tangle's view
void ReconcileTips(const t_txApproved& removeTips);
// Newly issued transaction is added to the list of unconfirmed transactions
void addTip(t_ptrTx newTip);
// Returns ref to the RNG, used in all TxActor methods
// TODO: Needs refactoring, perhaps a static RNG for each use in TxActor?
std::mt19937& getRandGen();
// Return current number of unapproved transactions
int getTipNumber();
// Returns a reference to the first transaction
const t_ptrTx& giveGenBlock() const;
// Debug
static int TangleGiveTipsCount;
};
class TxActor
{
private:
// All the transactions this transactor has issued
std::vector<t_ptrTx> m_MyTx;
Tangle * tanglePtr = nullptr;
// Recursive func to compute cumulative weight of a transaction, called from public func ComputeWeight
int _computeWeight( std::vector<t_ptrTx>& visited, t_ptrTx& current, omnetpp::simtime_t timeStamp );
public:
TxActor();
// Tip selection method that picks uniformly between all the tips in the transactors view
t_txApproved URTipSelection( std::map<int, t_ptrTx> tips );
// Uses internal reference to Tangle object to approve transactions it has chosen via a tip selection methpod, then maks sure the Tangle
// object is has a reference to has update it's tip view
//TODO: Potential for a static method in a hitherto undefined Tangle namespace instead of a member
void attach( std::map<int, t_ptrTx>& storedTips, omnetpp::simtime_t attachTime, t_txApproved& chosen );
//returns a tip to approve via a walk - randomness determined by param
t_ptrTx WalkTipSelection( t_ptrTx start, double alphaVal, std::map<int, t_ptrTx>& tips, omnetpp::simtime_t timeStamp );
t_ptrTx EasyWalkTipSelection( t_ptrTx start, double alphaVal, std::map<int, t_ptrTx>& tips, omnetpp::simtime_t timeStamp );
//Wrapper for Walk tip selection where k is the number of walkers to release into the tangle
// first APPROVE_VAL back are the chosen tips
t_txApproved NKWalkTipSelection( double alphaVal, std::map<int, t_ptrTx>& tips, omnetpp::simtime_t timeStamp, int kMultiplier, int backTrackDist);
// Return the pointer to the Tangle object this transactor is referring to
// see todo in Tangle
Tangle* getTanglePtr() const;
void setTanglePtr( Tangle* tn );
//Returns a reference to all the transactions this transaction has issued
const std::vector<t_ptrTx>& getMyTx() const;
//computes cumulative weight of any given transaction - used heavily in walk tip selection
//indirect recursion
int ComputeWeight( t_ptrTx tx, omnetpp::simtime_t timeStamp );
//backtrack a determined distance in the tangle to find a start point for a random walk
t_ptrTx getWalkStart( std::map<int, t_ptrTx>& tips, int backTrackDist );
//checks if TxActor sees the tx its walker is on as a tip
bool isRelativeTip( t_ptrTx& toCheck, std::map<int, t_ptrTx>& tips );
void filterView( std::vector<t_ptrTx>& view, omnetpp::simtime_t timeStamp );
//Returns the index of the heaviest tx in the actors tip view
int findMaxWeightIndex( std::vector<t_ptrTx>& view, omnetpp::simtime_t timeStamp );
static int actorCount;
};