summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/xhiv.h3
-rw-r--r--src/server.c36
2 files changed, 27 insertions, 12 deletions
diff --git a/include/xhiv.h b/include/xhiv.h
index 0063cf3..426918c 100644
--- a/include/xhiv.h
+++ b/include/xhiv.h
@@ -36,7 +36,10 @@
#define XHIV_NO_SET_SEQUENCE 0x01 /* Don't set sequence number in reply */
typedef struct xhiv_response {
+ /* next is used to make up the list of responses to search through.
+ Once one is found, all the responses along the chain are sent. */
struct xhiv_response *next;
+ struct xhiv_response *chain;
uint16_t reqType; /* Request code, extension number or XHIV_REQ constant */
uint16_t reqMinor; /* Extension minor request code */
uint32_t sequence; /* Sequence number, or XHIV_SEQ_IGNORE */
diff --git a/src/server.c b/src/server.c
index 38fa584..24a9872 100644
--- a/src/server.c
+++ b/src/server.c
@@ -227,29 +227,41 @@ static client_response_buffer *
AddResponseToBuffer(client_response_buffer *crb, const xhiv_response *response,
uint32_t sequence)
{
- client_response_buffer *new_crb;
+ client_response_buffer *new_crb_head = NULL, *new_crb_tail = NULL;
+ const xhiv_response *r;
- uint64_t total_bytes= ((uint64_t) response->length) << 2;
- assert(total_bytes >= response->response_datalen);
+ for (r = response; r != NULL; r = r->chain) {
+ client_response_buffer *new_crb;
- new_crb = calloc(1, sizeof(client_response_buffer));
- assert(new_crb != NULL);
+ uint64_t total_bytes= ((uint64_t) r->length) << 2;
+ assert(total_bytes >= r->response_datalen);
- new_crb->response_data = response->response_data;
- new_crb->response_datalen = response->response_datalen;
- new_crb->length = response->length;
- new_crb->response_sequence = (response->flags & XHIV_NO_SET_SEQUENCE)
- ? XHIV_SEQ_IGNORE : sequence;
+ new_crb = calloc(1, sizeof(client_response_buffer));
+ assert(new_crb != NULL);
+
+ new_crb->response_data = r->response_data;
+ new_crb->response_datalen = r->response_datalen;
+ new_crb->length = r->length;
+ new_crb->response_sequence = (r->flags & XHIV_NO_SET_SEQUENCE)
+ ? XHIV_SEQ_IGNORE : sequence;
+
+ if (new_crb_tail != NULL) {
+ new_crb_tail->next = new_crb;
+ new_crb_tail = new_crb;
+ } else {
+ new_crb_head = new_crb_tail = new_crb;
+ }
+ }
if (crb == NULL)
- crb = new_crb;
+ crb = new_crb_head;
else {
client_response_buffer *n;
for (n = crb ; n->next != NULL; n = n->next) {
/* find end of list */
}
- n->next = new_crb;
+ n->next = new_crb_head;
}
return crb;
}