int amqp_encode_table(amqp_bytes_t encoded, amqp_table_t *input, int *offsetptr) { int offset = *offsetptr; int tablesize_offset = offset; int i; offset += 4; /* skip space for the size of the table to be filled in later */ for (i = 0; i < input->num_entries; i++) { amqp_table_entry_t *entry = &(input->entries[i]); E_8(encoded, offset, entry->key.len); offset++; E_BYTES(encoded, offset, entry->key.len, entry->key.bytes); offset += entry->key.len; E_8(encoded, offset, entry->kind); offset++; switch (entry->kind) { case 'S': E_32(encoded, offset, entry->value.bytes.len); offset += 4; E_BYTES(encoded, offset, entry->value.bytes.len, entry->value.bytes.bytes); offset += entry->value.bytes.len; break; case 'I': E_32(encoded, offset, (uint32_t) entry->value.i32); offset += 4; break; case 'D': E_8(encoded, offset, entry->value.decimal.decimals); offset++; E_32(encoded, offset, entry->value.decimal.value); offset += 4; break; case 'T': E_64(encoded, offset, entry->value.u64); offset += 8; break; case 'F': AMQP_CHECK_RESULT(amqp_encode_table(encoded, &(entry->value.table), &offset)); break; default: return -EINVAL; } } E_32(encoded, tablesize_offset, (offset - *offsetptr - 4)); *offsetptr = offset; return 0; }
static int inner_send_frame(amqp_connection_state_t state, amqp_frame_t const *frame, amqp_bytes_t *encoded, int *payload_len) { int separate_body; E_8(state->outbound_buffer, 0, frame->frame_type); E_16(state->outbound_buffer, 1, frame->channel); switch (frame->frame_type) { case AMQP_FRAME_METHOD: E_32(state->outbound_buffer, HEADER_SIZE, frame->payload.method.id); encoded->len = state->outbound_buffer.len - (HEADER_SIZE + 4 + FOOTER_SIZE); encoded->bytes = D_BYTES(state->outbound_buffer, HEADER_SIZE + 4, encoded->len); *payload_len = AMQP_CHECK_RESULT(amqp_encode_method(frame->payload.method.id, frame->payload.method.decoded, *encoded)) + 4; separate_body = 0; break; case AMQP_FRAME_HEADER: E_16(state->outbound_buffer, HEADER_SIZE, frame->payload.properties.class_id); E_16(state->outbound_buffer, HEADER_SIZE+2, 0); /* "weight" */ E_64(state->outbound_buffer, HEADER_SIZE+4, frame->payload.properties.body_size); encoded->len = state->outbound_buffer.len - (HEADER_SIZE + 12 + FOOTER_SIZE); encoded->bytes = D_BYTES(state->outbound_buffer, HEADER_SIZE + 12, encoded->len); *payload_len = AMQP_CHECK_RESULT(amqp_encode_properties(frame->payload.properties.class_id, frame->payload.properties.decoded, *encoded)) + 12; separate_body = 0; break; case AMQP_FRAME_BODY: *encoded = frame->payload.body_fragment; *payload_len = encoded->len; separate_body = 1; break; case AMQP_FRAME_HEARTBEAT: *encoded = AMQP_EMPTY_BYTES; *payload_len = 0; separate_body = 0; break; default: return -EINVAL; } E_32(state->outbound_buffer, 3, *payload_len); if (!separate_body) { E_8(state->outbound_buffer, *payload_len + HEADER_SIZE, AMQP_FRAME_END); } #if 0 if (separate_body) { printf("sending body frame (header):\n"); amqp_dump(state->outbound_buffer.bytes, HEADER_SIZE); printf("sending body frame (payload):\n"); amqp_dump(encoded->bytes, *payload_len); } else { printf("sending:\n"); amqp_dump(state->outbound_buffer.bytes, *payload_len + HEADER_SIZE + FOOTER_SIZE); } #endif return separate_body; }