diff --git a/go.mod b/go.mod
index 47f1fe94e2e5d51d1d0048ac29fb15c710b5185d..4526aae3d5501de31344e16c149200b281287a1c 100644
--- a/go.mod
+++ b/go.mod
@@ -15,7 +15,6 @@ require (
 	github.com/labstack/echo v3.3.10+incompatible
 	github.com/labstack/gommon v0.2.9 // indirect
 	github.com/magiconair/properties v1.8.1
-	github.com/panjf2000/ants v1.1.0
 	github.com/pkg/errors v0.8.1
 	github.com/rivo/tview v0.0.0-20190721135419-23dc8a0944e4
 	github.com/rivo/uniseg v0.1.0 // indirect
diff --git a/go.sum b/go.sum
index ab297780047b1a4dccb9870593f9875073a28612..331a8ca2b0606ab27d583513ff5d7204af6baa29 100644
--- a/go.sum
+++ b/go.sum
@@ -79,8 +79,6 @@ github.com/onsi/ginkgo v1.8.0 h1:VkHVNpR4iVnU8XQR6DBm8BqYjN7CRzw+xKUbVVbbW9w=
 github.com/onsi/ginkgo v1.8.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE=
 github.com/onsi/gomega v1.5.0 h1:izbySO9zDPmjJ8rDjLvkA2zJHIo+HkYXHnf7eN7SSyo=
 github.com/onsi/gomega v1.5.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY=
-github.com/panjf2000/ants v1.1.0 h1:z1311FxGnwySXwQum1k4ZlHkWs86Xy18il4fuRzQemw=
-github.com/panjf2000/ants v1.1.0/go.mod h1:AaACblRPzq35m1g3enqYcxspbbiOJJYaxU2wMpm1cXY=
 github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic=
 github.com/pkg/errors v0.8.1 h1:iURUrRGxPUNPdy5/HRSm+Yj6okJ6UtLINN0Q9M4+h3I=
 github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
diff --git a/packages/database/badger_instance.go b/packages/database/badger_instance.go
index 50b5d8ba0593b887d69e71d8733f6c9c6a6b14be..6cf834f7140df321e9971e1c439dbd1a86bf1fdb 100644
--- a/packages/database/badger_instance.go
+++ b/packages/database/badger_instance.go
@@ -6,48 +6,63 @@ import (
 
 	"github.com/dgraph-io/badger"
 	"github.com/dgraph-io/badger/options"
+	"github.com/pkg/errors"
 )
 
 var instance *badger.DB
+var once sync.Once
 
-var openLock sync.Mutex
-
-func GetBadgerInstance() (result *badger.DB, err error) {
-	openLock.Lock()
+// Returns whether the given file or directory exists.
+func exists(path string) (bool, error) {
+	_, err := os.Stat(path)
+	if err == nil {
+		return true, nil
+	}
+	if os.IsNotExist(err) {
+		return false, nil
+	}
+	return false, err
+}
 
-	if instance == nil {
-		directory := *DIRECTORY.Value
+func checkDir(dir string) error {
+	exists, err := exists(dir)
+	if err != nil {
+		return err
+	}
 
-		if _, osErr := os.Stat(directory); os.IsNotExist(osErr) {
-			if osErr := os.Mkdir(directory, 0700); osErr != nil {
-				err = osErr
+	if !exists {
+		return os.Mkdir(dir, 0700)
+	}
+	return nil
+}
 
-				return
-			}
-		} else if osErr != nil {
-			err = osErr
+func createDB() (*badger.DB, error) {
+	directory := *DIRECTORY.Value
+	if err := checkDir(directory); err != nil {
+		return nil, errors.Wrap(err, "Could not check directory")
+	}
 
-			return
-		}
+	opts := badger.DefaultOptions(directory)
+	opts.Logger = &logger{}
+	opts.Truncate = true
+	opts.TableLoadingMode = options.MemoryMap
 
-		opts := badger.DefaultOptions(directory)
-		opts.Logger = &logger{}
-		opts.Truncate = true
-		opts.TableLoadingMode = options.MemoryMap
+	db, err := badger.Open(opts)
+	if err != nil {
+		return nil, errors.Wrap(err, "Could not open new DB")
+	}
 
-		db, badgerErr := badger.Open(opts)
-		if badgerErr != nil {
-			err = badgerErr
+	return db, nil
+}
 
-			return
+func GetBadgerInstance() *badger.DB {
+	once.Do(func() {
+		db, err := createDB()
+		if err != nil {
+			// errors should cause a panic to avoid singleton deadlocks
+			panic(err)
 		}
-
 		instance = db
-	}
-
-	openLock.Unlock()
-
-	result = instance
-
-	return
+	})
+	return instance
 }
diff --git a/packages/database/database.go b/packages/database/database.go
index 4a0e9657f6e66182154ff3ca1dae9cfc39d1eebe..573d0dd4168c2ec79d511de94b1a400243a4face 100644
--- a/packages/database/database.go
+++ b/packages/database/database.go
@@ -6,12 +6,10 @@ import (
 	"github.com/dgraph-io/badger"
 )
 
-var databasesByName = make(map[string]*databaseImpl)
-var getLock sync.Mutex
+var dbMap = make(map[string]*prefixDb)
+var mu sync.Mutex
 
-var ErrKeyNotFound = badger.ErrKeyNotFound
-
-type databaseImpl struct {
+type prefixDb struct {
 	db       *badger.DB
 	name     string
 	prefix   []byte
@@ -19,30 +17,32 @@ type databaseImpl struct {
 }
 
 func Get(name string) (Database, error) {
-	getLock.Lock()
-	defer getLock.Unlock()
-
-	if database, exists := databasesByName[name]; exists {
-		return database, nil
+	// avoid locking if it's a clean hit
+	if db, exists := dbMap[name]; exists {
+		return db, nil
 	}
 
-	badgerInstance, err := GetBadgerInstance()
-	if err != nil {
-		return nil, err
+	mu.Lock()
+	defer mu.Unlock()
+
+	// needs to be re-checked after locking
+	if db, exists := dbMap[name]; exists {
+		return db, nil
 	}
 
-	database := &databaseImpl{
-		db:     badgerInstance,
+	badger := GetBadgerInstance()
+	db := &prefixDb{
+		db:     badger,
 		name:   name,
 		prefix: []byte(name + "_"),
 	}
 
-	databasesByName[name] = database
+	dbMap[name] = db
 
-	return databasesByName[name], nil
+	return db, nil
 }
 
-func (this *databaseImpl) Set(key []byte, value []byte) error {
+func (this *prefixDb) Set(key []byte, value []byte) error {
 	if err := this.db.Update(func(txn *badger.Txn) error { return txn.Set(append(this.prefix, key...), value) }); err != nil {
 		return err
 	}
@@ -50,7 +50,7 @@ func (this *databaseImpl) Set(key []byte, value []byte) error {
 	return nil
 }
 
-func (this *databaseImpl) Contains(key []byte) (bool, error) {
+func (this *prefixDb) Contains(key []byte) (bool, error) {
 	err := this.db.View(func(txn *badger.Txn) error {
 		_, err := txn.Get(append(this.prefix, key...))
 		if err != nil {
@@ -60,14 +60,14 @@ func (this *databaseImpl) Contains(key []byte) (bool, error) {
 		return nil
 	})
 
-	if err == ErrKeyNotFound {
+	if err == badger.ErrKeyNotFound {
 		return false, nil
 	} else {
 		return err == nil, err
 	}
 }
 
-func (this *databaseImpl) Get(key []byte) ([]byte, error) {
+func (this *prefixDb) Get(key []byte) ([]byte, error) {
 	var result []byte = nil
 
 	err := this.db.View(func(txn *badger.Txn) error {
@@ -86,7 +86,7 @@ func (this *databaseImpl) Get(key []byte) ([]byte, error) {
 	return result, err
 }
 
-func (this *databaseImpl) Delete(key []byte) error {
+func (this *prefixDb) Delete(key []byte) error {
 	err := this.db.Update(func(txn *badger.Txn) error {
 		err := txn.Delete(append(this.prefix, key...))
 		return err
@@ -94,10 +94,10 @@ func (this *databaseImpl) Delete(key []byte) error {
 	return err
 }
 
-func (this *databaseImpl) ForEach(consumer func([]byte, []byte)) error {
+func (this *prefixDb) ForEach(consumer func([]byte, []byte)) error {
 	err := this.db.View(func(txn *badger.Txn) error {
 		iteratorOptions := badger.DefaultIteratorOptions
-		iteratorOptions.Prefix = this.prefix
+		iteratorOptions.Prefix = this.prefix // filter by prefix
 
 		// create an iterator the default options
 		it := txn.NewIterator(iteratorOptions)
diff --git a/packages/datastructure/weakmap_test.go b/packages/datastructure/weakmap_test.go
deleted file mode 100644
index 2c239962d5c449f1834ec318cd0d1c977e1cb9b6..0000000000000000000000000000000000000000
--- a/packages/datastructure/weakmap_test.go
+++ /dev/null
@@ -1,92 +0,0 @@
-package datastructure
-
-import (
-	"fmt"
-	"testing"
-)
-import "runtime"
-import "unsafe"
-import "errors"
-import "time"
-
-func TestWeakmap(t *testing.T) {
-	generateA(6)
-	fmt.Println("")
-
-	debugWeakMap(6)
-	fmt.Println("")
-
-	runtime.GC()
-	fmt.Println("GC runned.")
-
-	time.Sleep(1 * time.Second)
-
-	debugWeakMap(6)
-}
-
-func generateA(n int) {
-
-	for i := 0; i < n; i++ {
-		a := NewA()
-		WMap.Add(a)
-		fmt.Println("Added to WM A with id =", a.Id)
-	}
-
-}
-
-func debugWeakMap(n int) {
-	for i := 0; i < n; i++ {
-		if WMap.Has(i) {
-			fmt.Println("Has id =", i)
-		} else {
-			fmt.Println("Hasn't id =", i)
-		}
-	}
-}
-
-var aId int
-
-func NewA() *A {
-	aId++
-	return &A{aId}
-}
-
-var WMap = &WeakMap{weakMap: make(map[int]uintptr)}
-
-type WeakMap struct {
-	weakMap map[int]uintptr
-}
-
-type A struct {
-	Id int
-}
-
-func (w *WeakMap) Add(a *A) {
-	runtime.SetFinalizer(a, finalizer)
-
-	w.weakMap[a.Id] = uintptr(unsafe.Pointer(a))
-}
-
-func (w *WeakMap) Get(id int) (*A, error) {
-	if !w.Has(id) {
-		return nil, errors.New("")
-	}
-
-	a := (*A)(unsafe.Pointer(w.weakMap[id]))
-
-	return a, nil
-}
-
-func (w *WeakMap) Has(id int) bool {
-	_, ok := w.weakMap[id]
-	return ok
-}
-
-func (w *WeakMap) Remove(a *A) {
-	delete(w.weakMap, a.Id)
-}
-
-func finalizer(a *A) {
-	fmt.Println(a.Id)
-	WMap.Remove(a)
-}
diff --git a/packages/events/event_test.go b/packages/events/event_test.go
index 45084ba6faa58371eb5eb55c2ba2d1b084f95a85..37d91bd9a02fe5a49457656f83055eb33c7014d9 100644
--- a/packages/events/event_test.go
+++ b/packages/events/event_test.go
@@ -25,7 +25,7 @@ func intStringCaller(handler interface{}, params ...interface{}) {
 	handler.(func(int, string))(params[0].(int), params[1].(string))
 }
 
-func ExampleHelloWorld() {
+func ExampleEvent() {
 	// create event object (usually exposed through a public struct that holds all the different event types)
 	event := NewEvent(intStringCaller)
 
diff --git a/packages/workerpool/workerpool_test.go b/packages/workerpool/workerpool_test.go
index fb8f83e38adfe543488cc7170d77776fc74d66ca..deab7db7027dc68d0917321e23cad534601af24a 100644
--- a/packages/workerpool/workerpool_test.go
+++ b/packages/workerpool/workerpool_test.go
@@ -15,11 +15,11 @@ func Benchmark(b *testing.B) {
 	for i := 0; i < b.N; i++ {
 		wg.Add(1)
 
-		go func() {
+		go func(i int) {
 			<-pool.Submit(i)
 
 			wg.Done()
-		}()
+		}(i)
 	}
 
 	wg.Wait()
diff --git a/plugins/autopeering/types/peerregister/peer_register.go b/plugins/autopeering/types/peerregister/peer_register.go
index b90608dd84d1063e2352002af1109da3bd813a09..4b233d9491a1d33a5579f12aa2538f76693e20a9 100644
--- a/plugins/autopeering/types/peerregister/peer_register.go
+++ b/plugins/autopeering/types/peerregister/peer_register.go
@@ -73,7 +73,9 @@ func (this *PeerRegister) Remove(key string, lock ...bool) {
 		if len(lock) == 0 || lock[0] {
 			defer this.Lock()()
 
-			if peerEntry, exists := this.Peers[key]; exists {
+			// needs to be updated after locking
+			peerEntry, exists = this.Peers[key]
+			if exists {
 				delete(this.Peers, key)
 
 				this.Events.Remove.Trigger(peerEntry)
diff --git a/plugins/validator/plugin.go b/plugins/validator/plugin.go
index 10e80653233b88f608c2dce6ac59ad163ba50420..f5785b9869d3c26d0d097c4a6ede8f5142858622 100644
--- a/plugins/validator/plugin.go
+++ b/plugins/validator/plugin.go
@@ -6,8 +6,6 @@ import (
 	"github.com/iotaledger/goshimmer/packages/model/value_transaction"
 	"github.com/iotaledger/goshimmer/packages/node"
 	"github.com/iotaledger/goshimmer/plugins/bundleprocessor"
-	"github.com/iotaledger/iota.go/address"
-	. "github.com/iotaledger/iota.go/consts"
 	"github.com/iotaledger/iota.go/kerl"
 	"github.com/iotaledger/iota.go/signing"
 	. "github.com/iotaledger/iota.go/trinary"
@@ -15,31 +13,6 @@ import (
 
 var PLUGIN = node.NewPlugin("Validator", node.Enabled, configure, run)
 
-// Creates bundle signature fragments and the corresponding address to validate against.
-// Each signature fragment after the first must go into its own meta transaction with value = 0.
-func demoSign(seed Trytes, index uint64, sec SecurityLevel, bundleHash Hash) (Hash, []Trytes) {
-	addr, _ := address.GenerateAddress(seed, index, sec)
-
-	// compute seed based on address index
-	subseed, _ := signing.Subseed(seed, index)
-	// generate the private key
-	prvKey, _ := signing.Key(subseed, sec)
-
-	normalizedBundleHash := signing.NormalizedBundleHash(bundleHash)
-
-	signatureFragments := make([]Trytes, sec)
-	for i := 0; i < int(sec); i++ {
-		// each security level signs one third of the (normalized) bundle hash
-		signedFragTrits, _ := signing.SignatureFragment(
-			normalizedBundleHash[i*HashTrytesSize/3:(i+1)*HashTrytesSize/3],
-			prvKey[i*KeyFragmentLength:(i+1)*KeyFragmentLength],
-		)
-		signatureFragments[i] = MustTritsToTrytes(signedFragTrits)
-	}
-
-	return addr, signatureFragments
-}
-
 func validateSignatures(bundleHash Hash, txs []*value_transaction.ValueTransaction) (bool, error) {
 	for i, tx := range txs {
 		// ignore all non-input transactions
diff --git a/plugins/validator/validator_test.go b/plugins/validator/validator_test.go
new file mode 100644
index 0000000000000000000000000000000000000000..fd4f70b431db7fc3765c5847e235d1888571b4bb
--- /dev/null
+++ b/plugins/validator/validator_test.go
@@ -0,0 +1,54 @@
+package validator
+
+import (
+	"fmt"
+
+	"github.com/iotaledger/iota.go/address"
+	. "github.com/iotaledger/iota.go/consts"
+	"github.com/iotaledger/iota.go/signing"
+	. "github.com/iotaledger/iota.go/trinary"
+)
+
+const (
+	exampleHash  = "999999999999999999999999999999999999999999999999999999999999999999999999999999999"
+	exampleSeed  = exampleHash
+	exmapleIndex = 0
+	exampleSec   = SecurityLevelLow
+)
+
+// Creates bundle signature fragments for the given address index and bundle hash.
+// Each signature fragment after the first must go into its own meta transaction with value = 0.
+func signature(seed Trytes, index uint64, sec SecurityLevel, bundleHash Hash) []Trytes {
+	// compute seed based on address index
+	subseed, _ := signing.Subseed(seed, index)
+	// generate the private key
+	prvKey, _ := signing.Key(subseed, sec)
+
+	normalizedBundleHash := signing.NormalizedBundleHash(bundleHash)
+
+	signatureFragments := make([]Trytes, sec)
+	for i := 0; i < int(sec); i++ {
+		// each security level signs one third of the (normalized) bundle hash
+		signedFragTrits, _ := signing.SignatureFragment(
+			normalizedBundleHash[i*HashTrytesSize/3:(i+1)*HashTrytesSize/3],
+			prvKey[i*KeyFragmentLength:(i+1)*KeyFragmentLength],
+		)
+		signatureFragments[i] = MustTritsToTrytes(signedFragTrits)
+	}
+
+	return signatureFragments
+}
+
+func ExamplePLUGIN() {
+	// corresponding address to validate against.
+	addr, _ := address.GenerateAddress(exampleSeed, exmapleIndex, exampleSec)
+	fmt.Println(addr)
+
+	// compute the signature fragments which would be added to the (meta) transactions
+	signatureFragments := signature(exampleSeed, exmapleIndex, exampleSec, exampleHash)
+	fmt.Println(signatureFragments[0])
+
+	// Output:
+	// BSIXFJENGVJSOWPVHVALMPOPO9PUKHXDQI9VDELCBJXN9TCNQPTFEDMPQCVBOJSZUHEOABYYYAT9IAHHY
+	// GHHKPBXOOBOEHGGEEKYPH9MANWEKSQTQJFJ9KUTMJQAVITYRZMNLUESQARNHAWUJAPPZSQ9A9RUKABCE9KZPJDUEHVZEOSCQMTCC9AWBGWZLZEXMJ9YOQUVIBGMXSINCOLUATYDDUBAALHCBIONNRQIVIPUFPOIFHYRBFBGXXNVYXFZUSTTA9LYGGITTAJCVDE9GCFRGIOTXLQ9ZJDLONDLZ9OPS9TNYVKLTCGFBH9QPJWLIGADWMTJVCLAUCOZFDSRRCAMVWYFXRPGPMIOPIW9GBWANVSMPONQOTNLLYYHXAMZMMNRHMRXHEIXPVNORNGZZ9ZAU9RAWASOZNIBKDWYZWKCMLEUE9UVDHZ9XXGPXZABB9FGTNDTDFTYCKLKRRC9GZFKHKDGAWPBWEUPPWISYBBNZCIBERPXTMZPZHPKKUQUPBIJBIKZAGFHDDNAGCRQMWOMLUMAYKRBMHPMDWZK9JRBDWCJCBJQYMDUBNKOIRSJSVTCNKROZ9KLFBZLOXQOASLCFETCNZRPZULOABOFCUO9WKNQILLLTQ9GWVDBASBGSKUHFHRXOKQIBRCLUYZBZMTXTIG9BJNYHTJQQOECXOWLIDOYKMFJWKRCYW99VZILSPU9I9ZSTTBZVGISUHPCWLGKCFNLIHJNCL9OWQDNAKJAGRKTGCTDRHXVAYXOHNFVJYBMZLMXV9VINNIAWONYDYOKHHMOFFEOOVBMVMYABWRWLZTWJECKKAGPCIMUDZZIEJCFBXFIYKDRMWZIOEUZNLOXZJRDHVVKOTJWMLTIXVIRJSXUBLFGOCCLEIZVCDYD9FEMCRUOERPRDFGUJSALRSOBN9J9XDTUAJZFLHUGQI9MCXZCYWTTIHNQUPUYPDRJLRZG9HAXHYQDSSCQNPTBYKNQUWZDE9QUESZJASRXHNW9OKAVUKLLMVGOJJRZCPRXSRYUECLNQEFIHI9S9NNEN9KACVIKCZYDEKCDNUASUJWMTVLSPBOBQMQEMZJXJVQAMUGBTMNWEWVJSXNZKIAADSQCCLISYSUZICSIVXZUG9MTICGWXKXKJDW9TOUBS9BTOUFUKWEBVIIJTGD9IBLRHBCPICWSZQNJQERTBOZGLJFCXKGQTAHIWKOSGHRMMWXABQYHVHOPG9XDIXMIRBXHOSYBCHSFWORNLUD9JAB9ICBIPXYVLIXYNRHJVEDMIRSAGXKZKSFZADJ9GA9DGJZAJTXZGIKRXVBCCBGJPJWJJZXZRQNWLEUZEFTWOXUBTAGDPPKKPKRYPGXVSRWLRNEDAXHZYT9DRN9L9ZWXPTTOSKMGTPQQXHACAKESRQXVXXNOLIATRKDGGJNIDWWYKQSLTC9ERTPMNXQHZNVNSBGIRRQHMOCOGDWPQAU9WPRSGZMPXZWQADUFUAWVGESLIWZNV9WNANDMZAOLXIHAOSFBADWVVAHMJVFNX9BGMMYGMJCUOYCSKJWIUMYHQFQXCFQXQNB9VTBLAYGKUZLFH9UVWIQJVLMLOZDLLIPJZSNXBPWAKKZWKCVSWUSBSQLBIAX9SQGMNPCJWTQDQEASSWWCSTVJRFDBPBLNYU9CNFUYINVMQPJZGKKUH9QBMUVWFSLPXWKBBWKNLMHGCEMJWCTNXZYWCFXYU9XLTWDSROJDTCRARMBNYDDD99HCFMXMUCO9NJSRA9G9HGWRTWNDBDQLBTCNYIVRMWRWPDJDDYCDODGEBNFTNINPNMZYMJJHVZSNEIJOAPGHAIVCZHQIULTRIZ9ML9LCWTQVGLBKKBGJYZTOZZIYUBCBKHKYUHCFGZKDERTWYHNYWSWLGPUGRB9WNQTHOMBFPKUQZREUQCNXL9MFSZCNBN9PTAVCERMWTTFDZL9BJQMC9OUBWGDTURAEYTYRDNFUBATOWFSVNXJC9JUPARMU9MINY9RWRHIXBPNIUADFAEP9F9FWNJNRPNGLWHRYYCV9ZIWBOUZPFZTWDLOCNOYZQLWFJHZ99ZBLUDSIQBJOJXMQJBUCYYMROBCJJJNCETVUYRXKHAWGUBIWOKQXOIOYBQKNDXZCKXQZLWEMXYLJPODRMOQUYOAATZZQ9JZDR9KPIHRQKIEAQNO9OVXNHDFCUUIZRQDWYGKUAYIGHGIIJIOIERLVNDUEBZUAQGDZMWNGXQPYSNWUEGF9BQDFJEQRPEGFGJTQFWO9PWECFGNDH9LW
+}