#include "message.h" wsd_Message *wsd_Message_create(wsd_Frame *frame) { wsd_Message *message = calloc(1, sizeof(wsd_Message)); if (message == NULL) return NULL; message->frames = wsd_Queue_create(); if (message->frames == NULL) { free(message); return NULL; } message->length = 0; if (!wsd_Message_push_frame(message, frame)) { WSD_CLEAR_POINTER(wsd_Queue_destroy, message->frames); free(message); return NULL; } message->opcode = frame->opcode; message->rsv1 = frame->rsv1; message->rsv2 = frame->rsv2; message->rsv3 = frame->rsv3; return message; } void wsd_Message_destroy(wsd_Message *message) { if (message == NULL) return; wsd_Queue_each(message->frames, (wsd_Queue_cb)wsd_Frame_destroy); WSD_CLEAR_POINTER(wsd_Queue_destroy, message->frames); free(message); } int wsd_Message_would_overflow(wsd_Message *message, wsd_Frame *frame) { uint64_t mlen = (message == NULL) ? 0 : message->length, flen = frame->length; return flen > WSD_MAX_MESSAGE_LENGTH - mlen; } int wsd_Message_push_frame(wsd_Message *message, wsd_Frame *frame) { if (!wsd_Queue_push(message->frames, frame)) return 0; message->length += frame->length; return 1; } size_t wsd_Message_copy(wsd_Message *message, wsd_Chunk *target) { size_t offset = 0; wsd_QueueIter *iter = wsd_QueueIter_create(message->frames); if (iter == NULL) return 0; for (; iter->value != NULL; wsd_QueueIter_next(iter)) { offset = wsd_Frame_copy(iter->value, target, offset); } wsd_QueueIter_destroy(iter); return offset; }