use of bftsmart.reconfiguration.views.View in project aware by bergerch.
the class ServiceProxy method invoke.
/**
* This method sends a request to the replicas, and returns the related reply.
* If the servers take more than invokeTimeout seconds the method returns null.
* This method is thread-safe.
*
* @param request Request to be sent
* @param reqType ORDERED_REQUEST/UNORDERED_REQUEST/UNORDERED_HASHED_REQUEST for normal requests, and RECONFIG for
* reconfiguration requests.
*
* @return The reply from the replicas related to request
*/
public byte[] invoke(byte[] request, TOMMessageType reqType) {
try {
canSendLock.lock();
// Clean all statefull data to prepare for receiving next replies
Arrays.fill(replies, null);
receivedReplies = 0;
response = null;
replyQuorum = getReplyQuorum();
// Send the request to the replicas, and get its ID
reqId = generateRequestId(reqType);
operationId = generateOperationId();
requestType = reqType;
replyServer = -1;
hashResponseController = null;
if (requestType == TOMMessageType.UNORDERED_HASHED_REQUEST) {
replyServer = getRandomlyServerId();
logger.debug("[" + this.getClass().getName() + "] replyServerId(" + replyServer + ") " + "pos(" + getViewManager().getCurrentViewPos(replyServer) + ")");
hashResponseController = new HashResponseController(getViewManager().getCurrentViewPos(replyServer), getViewManager().getCurrentViewProcesses().length);
TOMMessage sm = new TOMMessage(getProcessId(), getSession(), reqId, operationId, request, getViewManager().getCurrentViewId(), requestType);
sm.setReplyServer(replyServer);
TOMulticast(sm);
} else {
TOMulticast(request, reqId, operationId, reqType);
}
logger.debug("Sending request (" + reqType + ") with reqId=" + reqId);
logger.debug("Expected number of matching replies: " + replyQuorum);
// by the client side communication system
try {
if (reqType == TOMMessageType.UNORDERED_HASHED_REQUEST) {
if (!this.sm.tryAcquire(invokeUnorderedHashedTimeout, TimeUnit.SECONDS)) {
logger.info("######## UNORDERED HASHED REQUEST TIMOUT ########");
canSendLock.unlock();
return invoke(request, TOMMessageType.ORDERED_REQUEST);
}
} else {
if (!this.sm.tryAcquire(invokeTimeout, TimeUnit.SECONDS)) {
logger.info("###################TIMEOUT#######################");
logger.info("Reply timeout for reqId=" + reqId + ", Replies received: " + receivedReplies);
canSendLock.unlock();
return null;
}
}
} catch (InterruptedException ex) {
logger.error("Problem aquiring semaphore", ex);
}
logger.debug("Response extracted = " + response);
byte[] ret = null;
if (response == null) {
// the response can be null if n-f replies are received but there isn't
// a replyQuorum of matching replies
logger.debug("Received n-f replies and no response could be extracted.");
canSendLock.unlock();
if (reqType == TOMMessageType.UNORDERED_REQUEST || reqType == TOMMessageType.UNORDERED_HASHED_REQUEST) {
// invoke the operation again, whitout the read-only flag
logger.debug("###################RETRY#######################");
return invokeOrdered(request);
} else {
throw new RuntimeException("Received n-f replies without f+1 of them matching.");
}
} else {
// ******* EDUARDO BEGIN **************//
if (reqType == TOMMessageType.ORDERED_REQUEST) {
// Reply to a normal request!
if (response.getViewID() == getViewManager().getCurrentViewId()) {
// return the response
ret = response.getContent();
} else {
// if(response.getViewID() > getViewManager().getCurrentViewId())
// updated view received
reconfigureTo((View) TOMUtil.getObject(response.getContent()));
canSendLock.unlock();
return invoke(request, reqType);
}
} else if (reqType == TOMMessageType.UNORDERED_REQUEST || reqType == TOMMessageType.UNORDERED_HASHED_REQUEST) {
if (response.getViewID() == getViewManager().getCurrentViewId()) {
// return the response
ret = response.getContent();
} else {
canSendLock.unlock();
return invoke(request, TOMMessageType.ORDERED_REQUEST);
}
} else {
if (response.getViewID() > getViewManager().getCurrentViewId()) {
// Reply to a reconfigure request!
logger.debug("Reconfiguration request' reply received!");
Object r = TOMUtil.getObject(response.getContent());
if (r instanceof View) {
// did not executed the request because it is using an outdated view
reconfigureTo((View) r);
canSendLock.unlock();
return invoke(request, reqType);
} else if (r instanceof ReconfigureReply) {
// reconfiguration executed!
reconfigureTo(((ReconfigureReply) r).getView());
ret = response.getContent();
} else {
logger.debug("Unknown response type");
}
} else {
logger.debug("Unexpected execution flow");
}
}
}
return ret;
} finally {
// always release lock
if (canSendLock.isHeldByCurrentThread())
canSendLock.unlock();
}
}
use of bftsmart.reconfiguration.views.View in project aware by bergerch.
the class StateManager method enoughViews.
protected boolean enoughViews(View view) {
Collection<View> views = senderViews.values();
int counter = 0;
for (View v : views) {
if (view.equals(v)) {
counter++;
}
}
boolean result = counter > SVController.getQuorum();
return result;
}
use of bftsmart.reconfiguration.views.View in project aware by bergerch.
the class ReconfigurationTest method run.
public void run(int id) {
/* ServiceProxy proxy = new ServiceProxy(id);
ReconfigureRequest request = new ReconfigureRequest(id);
request.setProperty("f","1");
System.out.println("Going to send a reconf!!!");
byte[] reply = proxy.invoke(TOMUtil.getBytes(request), ReconfigurationManager.TOM_RECONFIG_REQUEST, false);
ReconfigureReply r = (ReconfigureReply)TOMUtil.getObject(reply);*/
Reconfiguration rec = new Reconfiguration(id, "", null);
// rec.setReconfiguration(ReconfigurationManager.CHANGE_F,"1");
rec.setF(2);
ReconfigureReply r = rec.execute();
View v = r.getView();
System.out.println("New view f: " + v.getF());
rec.close();
}
use of bftsmart.reconfiguration.views.View in project bftsmart by blockchain-jd-com.
the class ConsensusTest_ method createClient.
/**
* 准备共识客户端
*/
public void createClient(int nodeNum) {
TOMConfiguration config = loadClientConfig(nodeNum);
latestView = new View(0, config.getInitialView(), config.getF(), addresses.toArray(new NodeNetwork[addresses.size()]));
ViewStorage viewStorage = new MemoryBasedViewStorage(latestView);
clientProxy = new AsynchServiceProxy(config, viewStorage);
Random random = new Random();
bytes = new byte[4];
random.nextBytes(bytes);
}
use of bftsmart.reconfiguration.views.View in project bftsmart by blockchain-jd-com.
the class Synchronizer method startSynchronization.
// this method is called when a timeout occurs or when a STOP message is
// recevied
private synchronized void startSynchronization(LeaderRegencyPropose regencyPropose) {
LOGGER.info("(Synchronizer.startSynchronization) [{}] -> I am proc {}, initialize synchr phase", this.execManager.getTOMLayer().getRealName(), controller.getStaticConf().getProcessId());
// Ask to start the synchronizations phase if enough messages have been received
// already
final int proposedRegencyId = regencyPropose.getRegency().getId();
// 如果此时已经处于选举进程,则不作后续处理;
if (!lcManager.isInProgress()) {
// 对非领导者而言,如果请求是有当前执政期的领导者节点主动触发的,并计入自己的一票;
LeaderRegency currentRegency = lcManager.getCurrentRegency();
if ((!tom.isLeader()) && regencyPropose.getSender() == currentRegency.getLeaderId() && regencyPropose.getRegency().getId() == currentRegency.getId() + 1) {
// 这是来自当前执政期领导者的主动选举提议;
// 进一步校验视图的一致性;
// 基于当前视图预测下一个执政期(即:当前执政期Id + 1),校验预测结果与来自远程的领导者的提议是否一致;
// 如果一致,则直接投赞成票,并主动发出 STOP_APPEND 消息;
View currentView = controller.getCurrentView();
LeaderRegencyPropose nextRegencyPropose = LeaderRegencyPropose.chooseFromView(currentRegency.getId() + 1, currentView, this.getCurrentId());
if (regencyPropose.isViewEquals(currentView) && nextRegencyPropose.getRegency().getLeaderId() == regencyPropose.getRegency().getLeaderId()) {
lcManager.addStop(nextRegencyPropose);
// 发送 STOP_APPEND 消息;
sendSTOP_APPEND(nextRegencyPropose);
}
}
if (lcManager.isUpToBeginQuorum(proposedRegencyId)) {
beginElection(regencyPropose);
}
}
// Did the synchronization phase really started?
// LCManager有两种状态:
// 1: 进入“选举中”状态;
// 2:在本次“选举周期”下并发地收到其它节点的 STOPDATA 消息,完成了本次轮选举;
ElectionResult electionResult = lcManager.generateQuorumElectionResult(proposedRegencyId);
if (lcManager.isInProgress(proposedRegencyId) && electionResult != null) {
commitElection(proposedRegencyId);
}
// End of: if (canSendStopData && lcManager.getNextReg() >
// lcManager.getLastReg());
}
Aggregations