Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8487b198 authored by TreeHugger Robot's avatar TreeHugger Robot Committed by Android (Google) Code Review
Browse files

Merge "Increase Bluetooth MIDI maximum size"

parents 66d49474 3688b228
Loading
Loading
Loading
Loading
+28 −12
Original line number Diff line number Diff line
@@ -39,7 +39,6 @@ import com.android.internal.midi.MidiEventScheduler.MidiEvent;
import libcore.io.IoUtils;

import java.io.IOException;
import java.util.List;
import java.util.UUID;

/**
@@ -50,7 +49,8 @@ public final class BluetoothMidiDevice {
    private static final String TAG = "BluetoothMidiDevice";
    private static final boolean DEBUG = false;

    private static final int MAX_PACKET_SIZE = 20;
    private static final int DEFAULT_PACKET_SIZE = 20;
    private static final int MAX_PACKET_SIZE = 512;

    //  Bluetooth MIDI Gatt service UUID
    private static final UUID MIDI_SERVICE = UUID.fromString(
@@ -103,6 +103,11 @@ public final class BluetoothMidiDevice {
                Log.d(TAG, "Connected to GATT server.");
                Log.d(TAG, "Attempting to start service discovery:" +
                        mBluetoothGatt.discoverServices());
                if (!mBluetoothGatt.requestMtu(MAX_PACKET_SIZE)) {
                    Log.e(TAG, "request mtu failed");
                    mPacketEncoder.setMaxPacketSize(DEFAULT_PACKET_SIZE);
                    mPacketDecoder.setMaxPacketSize(DEFAULT_PACKET_SIZE);
                }
            } else if (newState == BluetoothProfile.STATE_DISCONNECTED) {
                Log.i(TAG, "Disconnected from GATT server.");
                close();
@@ -182,21 +187,27 @@ public final class BluetoothMidiDevice {
            }
            mPacketDecoder.decodePacket(characteristic.getValue(), mOutputReceiver);
        }

        @Override
        public void onMtuChanged(BluetoothGatt gatt, int mtu, int status) {
            Log.d(TAG, "onMtuChanged callback received. mtu: " + mtu + ", status: " + status);
            if (status == BluetoothGatt.GATT_SUCCESS) {
                mPacketEncoder.setMaxPacketSize(Math.min(mtu, MAX_PACKET_SIZE));
                mPacketDecoder.setMaxPacketSize(Math.min(mtu, MAX_PACKET_SIZE));
            } else {
                mPacketEncoder.setMaxPacketSize(DEFAULT_PACKET_SIZE);
                mPacketDecoder.setMaxPacketSize(DEFAULT_PACKET_SIZE);
            }
        }
    };

    // This receives MIDI data that has already been passed through our MidiEventScheduler
    // and has been normalized by our MidiFramer.

    private class PacketReceiver implements PacketEncoder.PacketReceiver {
        // buffers of every possible packet size
        private final byte[][] mWriteBuffers;
        private byte[] mCachedBuffer;

        public PacketReceiver() {
            // Create buffers of every possible packet size
            mWriteBuffers = new byte[MAX_PACKET_SIZE + 1][];
            for (int i = 0; i <= MAX_PACKET_SIZE; i++) {
                mWriteBuffers[i] = new byte[i];
            }
        }

        @Override
@@ -205,9 +216,14 @@ public final class BluetoothMidiDevice {
                Log.w(TAG, "not ready to send packet yet");
                return;
            }
            byte[] writeBuffer = mWriteBuffers[count];
            System.arraycopy(buffer, 0, writeBuffer, 0, count);
            mCharacteristic.setValue(writeBuffer);

            // Cache the previous buffer for writePacket so buffers aren't
            // consistently created if the buffer sizes are consistent.
            if ((mCachedBuffer == null) || (mCachedBuffer.length != count)) {
                mCachedBuffer = new byte[count];
            }
            System.arraycopy(buffer, 0, mCachedBuffer, 0, count);
            mCharacteristic.setValue(mCachedBuffer);
            if (DEBUG) {
                logByteArray("Sent ", mCharacteristic.getValue(), 0,
                       mCharacteristic.getValue().length);
+11 −1
Original line number Diff line number Diff line
@@ -30,6 +30,7 @@ public class BluetoothPacketDecoder extends PacketDecoder {
    private static final String TAG = "BluetoothPacketDecoder";

    private final byte[] mBuffer;
    private int mMaxPacketSize;
    private int mBytesInBuffer;
    private MidiBtleTimeTracker mTimeTracker;

@@ -42,6 +43,14 @@ public class BluetoothPacketDecoder extends PacketDecoder {

    public BluetoothPacketDecoder(int maxPacketSize) {
        mBuffer = new byte[maxPacketSize];
        setMaxPacketSize(maxPacketSize);
    }

    /**
     * Dynamically sets the maximum packet size
     */
    public void setMaxPacketSize(int maxPacketSize) {
        mMaxPacketSize = Math.min(maxPacketSize, mBuffer.length);
    }

    private void flushOutput(MidiReceiver receiver) {
@@ -83,6 +92,7 @@ public class BluetoothPacketDecoder extends PacketDecoder {
        int previousLowTimestamp = 0;
        int currentTimestamp = highTimestamp | mLowTimestamp;

        int curMaxPacketSize = mMaxPacketSize;
        // Iterate through the rest of the packet, separating MIDI data from timestamps.
        for (int i = 1; i < buffer.length; i++) {
            byte b = buffer[i];
@@ -113,7 +123,7 @@ public class BluetoothPacketDecoder extends PacketDecoder {
            } else {
                lastWasTimestamp = false;
                // Flush if full before adding more data.
                if (mBytesInBuffer == mBuffer.length) {
                if (mBytesInBuffer >= curMaxPacketSize) {
                    flushOutput(receiver);
                }
                mBuffer[mBytesInBuffer++] = b;
+16 −4
Original line number Diff line number Diff line
@@ -45,6 +45,8 @@ public class BluetoothPacketEncoder extends PacketEncoder {
    private int mPacketTimestamp;
    // current running status, or zero if none
    private byte mRunningStatus;
    // max size of a packet
    private int mMaxPacketSize;

    private boolean mWritePending;

@@ -86,7 +88,7 @@ public class BluetoothPacketEncoder extends PacketEncoder {
                if (needsTimestamp) bytesNeeded++;  // add one for timestamp byte
                if (status == mRunningStatus) bytesNeeded--;    // subtract one for status byte

                if (mAccumulatedBytes + bytesNeeded > mAccumulationBuffer.length) {
                if (mAccumulatedBytes + bytesNeeded > mMaxPacketSize) {
                    // write out our data if there is no more room
                    // if necessary, block until previous packet is sent
                    flushLocked(true);
@@ -112,14 +114,14 @@ public class BluetoothPacketEncoder extends PacketEncoder {
                    int remaining = (hasSysExEnd ? count - 1 : count);

                    while (remaining > 0) {
                        if (mAccumulatedBytes == mAccumulationBuffer.length) {
                        if (mAccumulatedBytes == mMaxPacketSize) {
                            // write out our data if there is no more room
                            // if necessary, block until previous packet is sent
                            flushLocked(true);
                            appendHeader(milliTimestamp);
                        }

                        int copy = mAccumulationBuffer.length - mAccumulatedBytes;
                        int copy = mMaxPacketSize - mAccumulatedBytes;
                        if (copy > remaining) copy = remaining;
                        System.arraycopy(msg, offset, mAccumulationBuffer, mAccumulatedBytes, copy);
                        mAccumulatedBytes += copy;
@@ -129,7 +131,7 @@ public class BluetoothPacketEncoder extends PacketEncoder {

                    if (hasSysExEnd) {
                        // SysEx End command must be preceeded by a timestamp byte
                        if (mAccumulatedBytes + 2 > mAccumulationBuffer.length) {
                        if (mAccumulatedBytes + 2 > mMaxPacketSize) {
                            // write out our data if there is no more room
                            // if necessary, block until previous packet is sent
                            flushLocked(true);
@@ -182,6 +184,16 @@ public class BluetoothPacketEncoder extends PacketEncoder {
    public BluetoothPacketEncoder(PacketReceiver packetReceiver, int maxPacketSize) {
        mPacketReceiver = packetReceiver;
        mAccumulationBuffer = new byte[maxPacketSize];
        setMaxPacketSize(maxPacketSize);
    }

    /**
     * Dynamically sets the maximum packet size
     */
    public void setMaxPacketSize(int maxPacketSize) {
        synchronized (mLock) {
            mMaxPacketSize = Math.min(maxPacketSize, mAccumulationBuffer.length);
        }
    }

    @Override