Browse code

dispatcher: sync on updating last used fields

Daniel-Constantin Mierla authored on 14/09/2020 11:00:25 • Julien Chavanton committed on 10/11/2020 17:52:19
Showing 1 changed files
... ...
@@ -2134,6 +2134,7 @@ int ds_manage_routes(sip_msg_t *msg, ds_select_state_t *rstate)
2134 2134
 	unsigned int hash;
2135 2135
 	ds_set_t *idx = NULL;
2136 2136
 	int ulast = 0;
2137
+	int vlast = 0;
2137 2138
 
2138 2139
 	if(msg == NULL) {
2139 2140
 		LM_ERR("bad parameters\n");
... ...
@@ -2188,8 +2189,11 @@ int ds_manage_routes(sip_msg_t *msg, ds_select_state_t *rstate)
2188 2189
 			}
2189 2190
 			break;
2190 2191
 		case DS_ALG_ROUNDROBIN: /* 4 - round robin */
2192
+			lock_get(&idx->lock);
2191 2193
 			hash = idx->last;
2192 2194
 			idx->last = (idx->last + 1) % idx->nr;
2195
+			vlast = idx->last;
2196
+			lock_release(&idx->lock);
2193 2197
 			ulast = 1;
2194 2198
 			break;
2195 2199
 		case DS_ALG_HASHAUTHUSER: /* 5 - hash auth username */
... ...
@@ -2200,8 +2204,11 @@ int ds_manage_routes(sip_msg_t *msg, ds_select_state_t *rstate)
2200 2204
 					break;
2201 2205
 				case 1:
2202 2206
 					/* No Authorization found: Use round robin */
2207
+					lock_get(&idx->lock);
2203 2208
 					hash = idx->last;
2204 2209
 					idx->last = (idx->last + 1) % idx->nr;
2210
+					vlast = idx->last;
2211
+					lock_release(&idx->lock);
2205 2212
 					ulast = 1;
2206 2213
 					break;
2207 2214
 				default:
... ...
@@ -2222,8 +2229,10 @@ int ds_manage_routes(sip_msg_t *msg, ds_select_state_t *rstate)
2222 2229
 			hash = 0;
2223 2230
 			break;
2224 2231
 		case DS_ALG_WEIGHT: /* 9 - weight based distribution */
2232
+			lock_get(&idx->lock);
2225 2233
 			hash = idx->wlist[idx->wlast];
2226 2234
 			idx->wlast = (idx->wlast + 1) % 100;
2235
+			lock_release(&idx->lock);
2227 2236
 			break;
2228 2237
 		case DS_ALG_CALLLOAD: /* 10 - call load based distribution */
2229 2238
 			/* only INVITE can start a call */
... ...
@@ -2253,8 +2262,10 @@ int ds_manage_routes(sip_msg_t *msg, ds_select_state_t *rstate)
2253 2262
 			}
2254 2263
 			break;
2255 2264
 		case DS_ALG_RELWEIGHT: /* 11 - relative weight based distribution */
2265
+			lock_get(&idx->lock);
2256 2266
 			hash = idx->rwlist[idx->rwlast];
2257 2267
 			idx->rwlast = (idx->rwlast + 1) % 100;
2268
+			lock_release(&idx->lock);
2258 2269
 			break;
2259 2270
 		case DS_ALG_PARALLEL: /* 12 - parallel dispatching */
2260 2271
 			hash = 0;
... ...
@@ -2304,10 +2315,13 @@ int ds_manage_routes(sip_msg_t *msg, ds_select_state_t *rstate)
2304 2315
 		rstate->emode = 1;
2305 2316
 	}
2306 2317
 
2307
-	/* update last field for next select to point after the current active used */
2308
-	if(ulast) {
2318
+	/* update last field for next select to point after the current active used,
2319
+	 * if not updated meanwhile */
2320
+	lock_get(&idx->lock);
2321
+	if(ulast && (vlast == idx->last)) {
2309 2322
 		idx->last = (hash + 1) % idx->nr;
2310 2323
 	}
2324
+	lock_release(&idx->lock);
2311 2325
 
2312 2326
 	LM_DBG("selected [%d-%d-%d/%d] <%.*s>\n", rstate->alg, rstate->setid,
2313 2327
 			rstate->umode, hash,