Skip to content

Commit

Permalink
server GetField ensure no duplicate reply
Browse files Browse the repository at this point in the history
  • Loading branch information
mdavidsaver committed Nov 6, 2017
1 parent 84a0729 commit 3b565d0
Show file tree
Hide file tree
Showing 4 changed files with 14 additions and 7 deletions.
1 change: 1 addition & 0 deletions src/server/pv/responseHandlers.h
Expand Up @@ -687,6 +687,7 @@ class ServerGetFieldRequesterImpl :
void destroy();
void send(epics::pvData::ByteBuffer* buffer, TransportSendControl* control);
private:
bool done;
epics::pvData::Status _status;
epics::pvData::FieldConstPtr _field;
};
Expand Down
2 changes: 1 addition & 1 deletion src/server/pv/serverChannelImpl.h
Expand Up @@ -48,7 +48,7 @@ class ServerChannel
void unregisterRequest(pvAccessID id);

void installGetField(const GetFieldRequester::shared_pointer& gf);
void completeGetField();
void completeGetField(GetFieldRequester *req);

//! may return NULL
Destroyable::shared_pointer getRequest(pvAccessID id);
Expand Down
13 changes: 9 additions & 4 deletions src/server/responseHandlers.cpp
Expand Up @@ -2783,20 +2783,25 @@ void ServerGetFieldHandler::getFieldFailureResponse(Transport::shared_pointer co
ServerGetFieldRequesterImpl::ServerGetFieldRequesterImpl(
ServerContextImpl::shared_pointer const & context, ServerChannel::shared_pointer const & channel,
const pvAccessID ioid, Transport::shared_pointer const & transport) :
BaseChannelRequester(context, channel, ioid, transport), _field()
BaseChannelRequester(context, channel, ioid, transport), done(false)
{
}

void ServerGetFieldRequesterImpl::getDone(const Status& status, FieldConstPtr const & field)
{
bool twice;
{
Lock guard(_mutex);
_status = status;
_field = field;
twice = done;
done = true;
}
TransportSender::shared_pointer thisSender = shared_from_this();
_transport->enqueueSendRequest(thisSender);
_channel->completeGetField();
if(!twice) {
TransportSender::shared_pointer thisSender = shared_from_this();
_transport->enqueueSendRequest(thisSender);
}
_channel->completeGetField(this);
}

void ServerGetFieldRequesterImpl::destroy()
Expand Down
5 changes: 3 additions & 2 deletions src/server/serverChannelImpl.cpp
Expand Up @@ -121,12 +121,13 @@ void ServerChannel::installGetField(const GetFieldRequester::shared_pointer& gf)
}
}

void ServerChannel::completeGetField()
void ServerChannel::completeGetField(GetFieldRequester *req)
{
GetFieldRequester::shared_pointer prev;
{
epicsGuard<epicsMutex> G(_mutex);
prev.swap(_active_requester);
if(_active_requester.get()==req)
prev.swap(_active_requester);
}
}

Expand Down

0 comments on commit 3b565d0

Please sign in to comment.