Browse Source

Shadow record handling as pre-processing.

Bernd Fix 2 months ago
parent
commit
be4b72828c
2 changed files with 44 additions and 37 deletions
  1. 43
    36
      src/gnunet/service/gns/block_handler.go
  2. 1
    1
      src/gnunet/service/gns/module.go

+ 43
- 36
src/gnunet/service/gns/block_handler.go View File

@@ -81,33 +81,56 @@ type BlockHandler interface {
81 81
 
82 82
 // BlockHandlerList is a list of block handlers instantiated.
83 83
 type BlockHandlerList struct {
84
-	list    map[int]BlockHandler         // list of handler instances
85
-	counts  util.CounterMap              // count number of RRs by type
86
-	shadows []*message.GNSResourceRecord // list of shadow records
84
+	list   map[int]BlockHandler // list of handler instances
85
+	counts util.CounterMap      // count number of RRs by type
87 86
 }
88 87
 
89 88
 // NewBlockHandlerList instantiates an a list of active block handlers
90 89
 // for a given set of records (GNS block).
91
-func NewBlockHandlerList(records []*message.GNSResourceRecord, labels []string) (*BlockHandlerList, error) {
90
+func NewBlockHandlerList(records []*message.GNSResourceRecord, labels []string) (*BlockHandlerList, []*message.GNSResourceRecord, error) {
92 91
 	// initialize block handler list
93 92
 	hl := &BlockHandlerList{
94
-		list:    make(map[int]BlockHandler),
95
-		counts:  make(util.CounterMap),
96
-		shadows: make([]*message.GNSResourceRecord, 0),
93
+		list:   make(map[int]BlockHandler),
94
+		counts: make(util.CounterMap),
97 95
 	}
98 96
 
99
-	// Traverse record list and build list of handler instances
97
+	// first pass: build list of shadow records in this block
98
+	shadows := make([]*message.GNSResourceRecord, 0)
100 99
 	for _, rec := range records {
100
+		// filter out shadow records...
101
+		if (int(rec.Flags) & enums.GNS_FLAG_SHADOW) != 0 {
102
+			shadows = append(shadows, rec)
103
+		}
104
+	}
105
+	// second pass: normalize block by filtering out expired records (and
106
+	// replacing them with shadow records if available
107
+	active := make([]*message.GNSResourceRecord, 0)
108
+	for _, rec := range records {
109
+		// don't process shadow records again
110
+		if (int(rec.Flags) & enums.GNS_FLAG_SHADOW) != 0 {
111
+			continue
112
+		}
113
+		// check for expired record
114
+		if rec.Expires.Expired() {
115
+			// do we have an associated shadow record?
116
+			for _, shadow := range shadows {
117
+				if shadow.Type == rec.Type && !shadow.Expires.Expired() {
118
+					// deliver un-expired shadow record instead.
119
+					shadow.Flags &^= uint32(enums.GNS_FLAG_SHADOW)
120
+					active = append(active, shadow)
121
+				}
122
+			}
123
+		} else {
124
+			active = append(active, rec)
125
+		}
126
+	}
127
+
128
+	// Third pass: Traverse active list and build list of handler instances.
129
+	for _, rec := range active {
101 130
 		// update counter map
102 131
 		rrType := int(rec.Type)
103 132
 		hl.counts.Add(rrType)
104 133
 
105
-		// check for SHADOW record.
106
-		if (int(rec.Flags) & enums.GNS_FLAG_SHADOW) != 0 {
107
-			// add to list of shadows
108
-			hl.shadows = append(hl.shadows, rec)
109
-		}
110
-
111 134
 		// check for custom handler type
112 135
 		if creat, ok := customHandler[rrType]; ok {
113 136
 			// check if a handler for given type already exists
@@ -118,13 +141,13 @@ func NewBlockHandlerList(records []*message.GNSResourceRecord, labels []string)
118 141
 			if hdlr, ok = hl.list[rrType]; ok {
119 142
 				// add record to existing handler
120 143
 				if err = hdlr.AddRecord(rec, labels); err != nil {
121
-					return nil, err
144
+					return nil, active, err
122 145
 				}
123 146
 				continue
124 147
 			}
125 148
 			// create a new handler instance
126 149
 			if hdlr, err = creat(rec, labels); err != nil {
127
-				return nil, err
150
+				return nil, active, err
128 151
 			}
129 152
 			// store handler in list
130 153
 			hl.list[rrType] = hdlr
@@ -136,11 +159,11 @@ func NewBlockHandlerList(records []*message.GNSResourceRecord, labels []string)
136 159
 	for _, hdlr := range hl.list {
137 160
 		if !hdlr.Coexist(hl.counts) {
138 161
 			logger.Printf(logger.ERROR, "[gns] %s.Coexist() failed!\n", hdlr.Name())
139
-			return nil, ErrInvalidRecordMix
162
+			return nil, active, ErrInvalidRecordMix
140 163
 		}
141 164
 	}
142 165
 	// return assembled handler list
143
-	return hl, nil
166
+	return hl, active, nil
144 167
 }
145 168
 
146 169
 // GetHandler returns a BlockHandler for the given key. If no block handler exists
@@ -154,25 +177,9 @@ func (hl *BlockHandlerList) GetHandler(t int) BlockHandler {
154 177
 	return nil
155 178
 }
156 179
 
157
-// FinalizeRecord post-processes records: Filtering out expired records (and
158
-// replacing them with a shadow record if available).
180
+// FinalizeRecord post-processes records
159 181
 func (hl *BlockHandlerList) FinalizeRecord(rec *message.GNSResourceRecord) *message.GNSResourceRecord {
160
-	// filter out shadow records...
161
-	if (int(rec.Flags) & enums.GNS_FLAG_SHADOW) != 0 {
162
-		return nil
163
-	}
164
-	// check for expired record
165
-	if rec.Expires.Expired() {
166
-		// do we have an associated shadow record?
167
-		for _, shadow := range hl.shadows {
168
-			if shadow.Type == rec.Type && !shadow.Expires.Expired() {
169
-				// deliver un-expired shadow record instead.
170
-				return shadow
171
-			}
172
-		}
173
-		// expired and un-shadowed record is dropped
174
-		return nil
175
-	}
182
+	// no implementation yet
176 183
 	return rec
177 184
 }
178 185
 

+ 1
- 1
src/gnunet/service/gns/module.go View File

@@ -167,7 +167,7 @@ func (gns *GNSModule) ResolveRelative(labels []string, pkey *ed25519.PublicKey,
167 167
 		// assemble a list of block handlers for this block: if multiple
168 168
 		// block handlers are present, they are consistent with all block
169 169
 		// records.
170
-		if hdlrs, err = NewBlockHandlerList(records, labels[1:]); err != nil {
170
+		if hdlrs, records, err = NewBlockHandlerList(records, labels[1:]); err != nil {
171 171
 			// conflicting block handler records found: terminate with error.
172 172
 			// (N.B.: The BlockHandlerList class executes the logic which mix
173 173
 			// of resource records in a single block is considered valid.)

Loading…
Cancel
Save