1// Copyright 2016 The Fuchsia Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include <zircon/compiler.h>
6#include <assert.h>
7#include <stdint.h>
8
9#include "midi.h"
10
11// Number of bytes in a message nc from 8c to Ec
12static const int CHANNEL_BYTE_LENGTHS[] = { 3, 3, 3, 3, 2, 2, 3 };
13
14// Number of bytes in a message Fn from F0 to FF */
15static const int SYSTEM_BYTE_LENGTHS[] = { 1, 2, 3, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 };
16
17int get_midi_message_length(uint8_t status_byte) {
18    if (status_byte >= 0xF0) {
19        // System messages use low nibble for size.
20        static_assert(countof(SYSTEM_BYTE_LENGTHS) >= 16, "SYSTEM_BYTE_LENGTHS too small");
21        return SYSTEM_BYTE_LENGTHS[status_byte & 0x0F];
22    } else if(status_byte >= 0x80) {
23        // Channel voice messages use high nibble for size.
24        static_assert(countof(CHANNEL_BYTE_LENGTHS) >= 0xE - 8, "CHANNEL_BYTE_LENGTHS too small");
25        return CHANNEL_BYTE_LENGTHS[(status_byte >> 4) - 8];
26    } else {
27        return 0; // data byte
28    }
29}
30