void _parse_aiff_comm(Buffer *buf, uint32_t chunk_size, HV *info) { uint16_t channels = buffer_get_short(buf); uint32_t frames = buffer_get_int(buf); uint16_t bits_per_sample = buffer_get_short(buf); double samplerate = buffer_get_ieee_float(buf); my_hv_store( info, "channels", newSVuv(channels) ); my_hv_store( info, "bits_per_sample", newSVuv(bits_per_sample) ); my_hv_store( info, "samplerate", newSVuv(samplerate) ); my_hv_store( info, "bitrate", newSVuv( samplerate * channels * bits_per_sample ) ); my_hv_store( info, "song_length_ms", newSVuv( ((frames * 1.0) / samplerate) * 1000 ) ); my_hv_store( info, "block_align", newSVuv( channels * bits_per_sample / 8 ) ); if (chunk_size > 18) { // AIFC extra data my_hv_store( info, "compression_type", newSVpvn( buffer_ptr(buf), 4 ) ); buffer_consume(buf, 4); my_hv_store( info, "compression_name", newSVpvn( buffer_ptr(buf), chunk_size - 22 ) ); buffer_consume(buf, chunk_size - 22); } }
packet_t* packet_decode(buffer_t* buffer) { int error = buffer_ok; uint16_t length; uint8_t id; buffer->position = 0; error |= buffer_get_short(buffer, &length); error |= buffer_get_byte(buffer, &id); error |= buffer_available(buffer) == length; if (error || length > 5000 || length == 0) return NULL; uint8_t payload[length]; memcpy(payload, buffer->payload + buffer->position, length); packet_t* packet = safe_alloc(sizeof(packet_t)); packet->id = id; packet->buffer = buffer_wrap(payload, length); packet->buffer->position = 0; return packet; }