serval-dna/responses.c

129 lines
3.1 KiB
C
Raw Normal View History

/*
Serval Distributed Numbering Architecture (DNA)
Copyright (C) 2010 Paul Gardner-Stephen
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include "serval.h"
int dumpResponses(struct response_set *responses)
{
struct response *r;
if (!responses) {
DEBUG("Response set is NULL");
return 0;
}
DEBUGF("Response set claims to contain %d entries.", responses->response_count);
r = responses->responses;
while(r) {
DEBUGF(" response code 0x%02x", r->code);
if (r->next && r->next->prev != r)
DEBUG(" !! response chain is broken");
r = r->next;
}
return 0;
}
int clearResponse(struct response **response)
{
while(*response)
{
struct response *r=*response;
*response=(*response)->next;
if (r->response) free(r->response);
r->response=NULL;
free(r);
}
return 0;
}
int eraseLastResponse(struct response_set *responses)
{
if (!responses) return -1;
if (responses->last_response)
{
struct response *newtail;
if (responses->last_response->prev) responses->last_response->prev->next=NULL;
newtail=responses->last_response->prev;
if (responses->responses==responses->last_response) responses->responses=NULL;
clearResponse(&responses->last_response);
responses->last_response=newtail;
responses->response_count--;
}
return 0;
}
int responseFromPeer(struct response_set *responses,int peerId)
{
int byte;
int bit;
if (peerId<0||peerId>=peer_count) return -1;
if (!responses) return -1;
if (!responses->reply_bitmask)
{
responses->reply_bitmask=calloc(1,(peer_count>>3)+(peer_count&7)?1:0);
if (!responses->reply_bitmask) return -1;
}
byte=peerId>>3;
bit=peerId&7;
responses->reply_bitmask[byte]|=1<<bit;
return 0;
}
int responseFromPeerP(struct response_set *responses,int peerId)
{
int byte;
int bit;
if (!responses) return 0;
if (!responses->reply_bitmask) return 0;
if (peerId<0||peerId>=peer_count) return 0;
byte=peerId>>3;
bit=peerId&7;
return responses->reply_bitmask[byte]&(1<<bit);
}
int clearResponses(struct response_set *responses)
{
struct response *r;
if (!responses) return -1;
r=responses->responses;
while(r)
{
struct response *rr=r;
r=r->next;
free(rr);
}
if (responses->reply_bitmask) free(responses->reply_bitmask);
responses->reply_bitmask=NULL;
responses->last_response=NULL;
responses->responses=NULL;
responses->response_count=0;
return 0;
}