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

Commit 1b00dc66 authored by Wink Saville's avatar Wink Saville Committed by Android Git Automerger
Browse files

am 3156a8c1: Merge "Move ProcessedMessage into HierarchicalStateMachine." into honeycomb-LTE

* commit '3156a8c1':
  Move ProcessedMessage into HierarchicalStateMachine.
parents 2df36fd6 3156a8c1
Loading
Loading
Loading
Loading
+190 −17
Original line number Diff line number Diff line
@@ -24,6 +24,7 @@ import android.util.Log;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Vector;

/**
 * {@hide}
@@ -433,6 +434,180 @@ public class HierarchicalStateMachine {
     */
    public static final boolean NOT_HANDLED = false;

    /**
     * {@hide}
     *
     * The information maintained for a processed message.
     */
    public static class ProcessedMessageInfo {
        private int what;
        private HierarchicalState state;
        private HierarchicalState orgState;

        /**
         * Constructor
         * @param message
         * @param state that handled the message
         * @param orgState is the first state the received the message but
         * did not processes the message.
         */
        ProcessedMessageInfo(Message message, HierarchicalState state, HierarchicalState orgState) {
            update(message, state, orgState);
        }

        /**
         * Update the information in the record.
         * @param state that handled the message
         * @param orgState is the first state the received the message but
         * did not processes the message.
         */
        public void update(Message message, HierarchicalState state, HierarchicalState orgState) {
            this.what = message.what;
            this.state = state;
            this.orgState = orgState;
        }

        /**
         * @return the command that was executing
         */
        public int getWhat() {
            return what;
        }

        /**
         * @return the state that handled this message
         */
        public HierarchicalState getState() {
            return state;
        }

        /**
         * @return the original state that received the message.
         */
        public HierarchicalState getOriginalState() {
            return orgState;
        }

        /**
         * @return as string
         */
        @Override
        public String toString() {
            StringBuilder sb = new StringBuilder();
            sb.append("what=");
            sb.append(what);
            sb.append(" state=");
            sb.append(cn(state));
            sb.append(" orgState=");
            sb.append(cn(orgState));
            return sb.toString();
        }

        /**
         * @return an objects class name
         */
        private String cn(Object n) {
            if (n == null) {
                return "null";
            } else {
                String name = n.getClass().getName();
                int lastDollar = name.lastIndexOf('$');
                return name.substring(lastDollar + 1);
            }
        }
    }

    /**
     * A list of messages recently processed by the state machine.
     *
     * The class maintains a list of messages that have been most
     * recently processed. The list is finite and may be set in the
     * constructor or by calling setSize. The public interface also
     * includes size which returns the number of recent messages,
     * count which is the number of message processed since the
     * the last setSize, get which returns a processed message and
     * add which adds a processed messaged.
     */
    private static class ProcessedMessages {

        private static final int DEFAULT_SIZE = 20;

        private Vector<ProcessedMessageInfo> mMessages = new Vector<ProcessedMessageInfo>();
        private int mMaxSize = DEFAULT_SIZE;
        private int mOldestIndex = 0;
        private int mCount = 0;

        /**
         * Constructor
         */
        ProcessedMessages() {
        }

        /**
         * Set size of messages to maintain and clears all current messages.
         *
         * @param maxSize number of messages to maintain at anyone time.
        */
        void setSize(int maxSize) {
            mMaxSize = maxSize;
            mCount = 0;
            mMessages.clear();
        }

        /**
         * @return the number of recent messages.
         */
        int size() {
            return mMessages.size();
        }

        /**
         * @return the total number of messages processed since size was set.
         */
        int count() {
            return mCount;
        }

        /**
         * @return the information on a particular record. 0 is the oldest
         * record and size()-1 is the newest record. If the index is to
         * large null is returned.
         */
        ProcessedMessageInfo get(int index) {
            int nextIndex = mOldestIndex + index;
            if (nextIndex >= mMaxSize) {
                nextIndex -= mMaxSize;
            }
            if (nextIndex >= size()) {
                return null;
            } else {
                return mMessages.get(nextIndex);
            }
        }

        /**
         * Add a processed message.
         *
         * @param message
         * @param state that handled the message
         * @param orgState is the first state the received the message but
         * did not processes the message.
         */
        void add(Message message, HierarchicalState state, HierarchicalState orgState) {
            mCount += 1;
            if (mMessages.size() < mMaxSize) {
                mMessages.add(new ProcessedMessageInfo(message, state, orgState));
            } else {
                ProcessedMessageInfo pmi = mMessages.get(mOldestIndex);
                mOldestIndex += 1;
                if (mOldestIndex >= mMaxSize) {
                    mOldestIndex = 0;
                }
                pmi.update(message, state, orgState);
            }
        }
    }

    private static class HsmHandler extends Handler {

        /** The debug flag */
@@ -441,9 +616,6 @@ public class HierarchicalStateMachine {
        /** The quit object */
        private static final Object mQuitObj = new Object();

        /** The initialization message */
        private static final Message mInitMsg = null;

        /** The current message */
        private Message mMsg;

@@ -615,8 +787,9 @@ public class HierarchicalStateMachine {
                     */
                    mHsm.quitting();
                    if (mHsm.mHsmThread != null) {
                        // If we made the thread then quit looper
                        // If we made the thread then quit looper which stops the thread.
                        getLooper().quit();
                        mHsm.mHsmThread = null;
                    }
                } else if (destState == mHaltingState) {
                    /**
@@ -963,8 +1136,8 @@ public class HierarchicalStateMachine {
            return mProcessedMessages.count();
        }

        /** @see HierarchicalStateMachine#getProcessedMessage(int) */
        private final ProcessedMessages.Info getProcessedMessage(int index) {
        /** @see HierarchicalStateMachine#getProcessedMessageInfo(int) */
        private final ProcessedMessageInfo getProcessedMessageInfo(int index) {
            return mProcessedMessages.get(index);
        }

@@ -1090,9 +1263,7 @@ public class HierarchicalStateMachine {
     * @param msg that couldn't be handled.
     */
    protected void unhandledMessage(Message msg) {
        if (false) {
            Log.e(TAG, mName + " - unhandledMessage: msg.what=" + msg.what);
        }
        if (mHsmHandler.mDbg) Log.e(TAG, mName + " - unhandledMessage: msg.what=" + msg.what);
    }

    /**
@@ -1103,16 +1274,18 @@ public class HierarchicalStateMachine {
    }

    /**
     * Called after the message that called transitionToHalting
     * is called and should be overridden by StateMachine's that
     * call transitionToHalting.
     * This will be called once after handling a message that called
     * transitionToHalting. All subsequent messages will invoke
     * {@link HierarchicalStateMachine#haltedProcessMessage(Message)}
     */
    protected void halting() {
    }

    /**
     * Called after the quitting message was NOT handled and
     * just before the quit actually occurs.
     * This will be called once after a quit message that was NOT handled by
     * the derived HSM. The HSM will stop and any subsequent messages will be
     * ignored. In addition, if this HSM created the thread, the thread will
     * be stopped after this method returns.
     */
    protected void quitting() {
    }
@@ -1148,10 +1321,10 @@ public class HierarchicalStateMachine {
    }

    /**
     * @return a processed message
     * @return a processed message information
     */
    public final ProcessedMessages.Info getProcessedMessage(int index) {
        return mHsmHandler.getProcessedMessage(index);
    public final ProcessedMessageInfo getProcessedMessageInfo(int index) {
        return mHsmHandler.getProcessedMessageInfo(index);
    }

    /**
+0 −198
Original line number Diff line number Diff line
/**
 * Copyright (C) 2009 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.android.internal.util;

import android.os.Message;

import java.util.Vector;

/**
 * {@hide}
 *
 * A list of messages recently processed by the state machine.
 *
 * The class maintains a list of messages that have been most
 * recently processed. The list is finite and may be set in the
 * constructor or by calling setSize. The public interface also
 * includes size which returns the number of recent messages,
 * count which is the number of message processed since the
 * the last setSize, get which returns a processed message and
 * add which adds a processed messaged.
 */
public class ProcessedMessages {

    public static final int DEFAULT_SIZE = 20;

    /**
     * The information maintained for a processed message.
     */
    public class Info {
        private int what;
        private HierarchicalState state;
        private HierarchicalState orgState;

        /**
         * Constructor
         * @param message
         * @param state that handled the message
         * @param orgState is the first state the received the message but
         * did not processes the message.
         */
        Info(Message message, HierarchicalState state, HierarchicalState orgState) {
            update(message, state, orgState);
        }

        /**
         * Update the information in the record.
         * @param state that handled the message
         * @param orgState is the first state the received the message but
         * did not processes the message.
         */
        public void update(Message message, HierarchicalState state, HierarchicalState orgState) {
            this.what = message.what;
            this.state = state;
            this.orgState = orgState;
        }

        /**
         * @return the command that was executing
         */
        public int getWhat() {
            return what;
        }

        /**
         * @return the state that handled this message
         */
        public HierarchicalState getState() {
            return state;
        }

        /**
         * @return the original state that received the message.
         */
        public HierarchicalState getOriginalState() {
            return orgState;
        }

        /**
         * @return as string
         */
        public String toString() {
            StringBuilder sb = new StringBuilder();
            sb.append("what=");
            sb.append(what);
            sb.append(" state=");
            sb.append(cn(state));
            sb.append(" orgState=");
            sb.append(cn(orgState));
            return sb.toString();
        }

        /**
         * @return an objects class name
         */
        private String cn(Object n) {
            if (n == null) {
                return "null";
            } else {
                String name = n.getClass().getName();
                int lastDollar = name.lastIndexOf('$');
                return name.substring(lastDollar + 1);
            }
        }
    }

    private Vector<Info> mMessages = new Vector<Info>();
    private int mMaxSize = DEFAULT_SIZE;
    private int mOldestIndex = 0;
    private int mCount = 0;

    /**
     * Constructor
     */
    ProcessedMessages() {
    }

    ProcessedMessages(int maxSize) {
        setSize(maxSize);
    }

    /**
     * Set size of messages to maintain and clears all current messages.
     *
     * @param maxSize number of messages to maintain at anyone time.
    */
    void setSize(int maxSize) {
        mMaxSize = maxSize;
        mCount = 0;
        mMessages.clear();
    }

    /**
     * @return the number of recent messages.
     */
    int size() {
        return mMessages.size();
    }

    /**
     * @return the total number of messages processed since size was set.
     */
    int count() {
        return mCount;
    }

    /**
     * @return the information on a particular record. 0 is the oldest
     * record and size()-1 is the newest record. If the index is to
     * large null is returned.
     */
    Info get(int index) {
        int nextIndex = mOldestIndex + index;
        if (nextIndex >= mMaxSize) {
            nextIndex -= mMaxSize;
        }
        if (nextIndex >= size()) {
            return null;
        } else {
            return mMessages.get(nextIndex);
        }
    }

    /**
     * Add a processed message.
     *
     * @param message
     * @param state that handled the message
     * @param orgState is the first state the received the message but
     * did not processes the message.
     */
    void add(Message message, HierarchicalState state, HierarchicalState orgState) {
        mCount += 1;
        if (mMessages.size() < mMaxSize) {
            mMessages.add(new Info(message, state, orgState));
        } else {
            Info info = mMessages.get(mOldestIndex);
            mOldestIndex += 1;
            if (mOldestIndex >= mMaxSize) {
                mOldestIndex = 0;
            }
            info.update(message, state, orgState);
        }
    }
}
+40 −40
Original line number Diff line number Diff line
@@ -24,7 +24,7 @@ import android.os.SystemClock;

import com.android.internal.util.HierarchicalState;
import com.android.internal.util.HierarchicalStateMachine;
import com.android.internal.util.ProcessedMessages;
import com.android.internal.util.HierarchicalStateMachine.ProcessedMessageInfo;

import android.test.suitebuilder.annotation.MediumTest;
import android.test.suitebuilder.annotation.SmallTest;
@@ -125,21 +125,21 @@ public class HierarchicalStateMachineTest extends TestCase {

        assertTrue(smQuitTest.getProcessedMessagesCount() == 9);

        ProcessedMessages.Info pmi;
        ProcessedMessageInfo pmi;

        // The first two message didn't quit and were handled by mS1
        pmi = smQuitTest.getProcessedMessage(6);
        pmi = smQuitTest.getProcessedMessageInfo(6);
        assertEquals(HierarchicalStateMachine.HSM_QUIT_CMD, pmi.getWhat());
        assertEquals(smQuitTest.mS1, pmi.getState());
        assertEquals(smQuitTest.mS1, pmi.getOriginalState());

        pmi = smQuitTest.getProcessedMessage(7);
        pmi = smQuitTest.getProcessedMessageInfo(7);
        assertEquals(HierarchicalStateMachine.HSM_QUIT_CMD, pmi.getWhat());
        assertEquals(smQuitTest.mS1, pmi.getState());
        assertEquals(smQuitTest.mS1, pmi.getOriginalState());

        // The last message was never handled so the states are null
        pmi = smQuitTest.getProcessedMessage(8);
        pmi = smQuitTest.getProcessedMessageInfo(8);
        assertEquals(HierarchicalStateMachine.HSM_QUIT_CMD, pmi.getWhat());
        assertEquals(null, pmi.getState());
        assertEquals(null, pmi.getOriginalState());
@@ -285,10 +285,10 @@ public class HierarchicalStateMachineTest extends TestCase {

        assertTrue(smEnterExitTranstionToTest.getProcessedMessagesCount() == 1);

        ProcessedMessages.Info pmi;
        ProcessedMessageInfo pmi;

        // Message should be handled by mS2.
        pmi = smEnterExitTranstionToTest.getProcessedMessage(0);
        pmi = smEnterExitTranstionToTest.getProcessedMessageInfo(0);
        assertEquals(TEST_CMD_1, pmi.getWhat());
        assertEquals(smEnterExitTranstionToTest.mS2, pmi.getState());
        assertEquals(smEnterExitTranstionToTest.mS2, pmi.getOriginalState());
@@ -369,18 +369,18 @@ public class HierarchicalStateMachineTest extends TestCase {
        assertTrue(sm0.getProcessedMessagesCount() == 6);
        assertTrue(sm0.getProcessedMessagesSize() == 3);

        ProcessedMessages.Info pmi;
        pmi = sm0.getProcessedMessage(0);
        ProcessedMessageInfo pmi;
        pmi = sm0.getProcessedMessageInfo(0);
        assertEquals(TEST_CMD_4, pmi.getWhat());
        assertEquals(sm0.mS1, pmi.getState());
        assertEquals(sm0.mS1, pmi.getOriginalState());

        pmi = sm0.getProcessedMessage(1);
        pmi = sm0.getProcessedMessageInfo(1);
        assertEquals(TEST_CMD_5, pmi.getWhat());
        assertEquals(sm0.mS1, pmi.getState());
        assertEquals(sm0.mS1, pmi.getOriginalState());

        pmi = sm0.getProcessedMessage(2);
        pmi = sm0.getProcessedMessageInfo(2);
        assertEquals(TEST_CMD_6, pmi.getWhat());
        assertEquals(sm0.mS1, pmi.getState());
        assertEquals(sm0.mS1, pmi.getOriginalState());
@@ -469,13 +469,13 @@ public class HierarchicalStateMachineTest extends TestCase {

        assertTrue(sm1.getProcessedMessagesSize() == 2);

        ProcessedMessages.Info pmi;
        pmi = sm1.getProcessedMessage(0);
        ProcessedMessageInfo pmi;
        pmi = sm1.getProcessedMessageInfo(0);
        assertEquals(TEST_CMD_1, pmi.getWhat());
        assertEquals(sm1.mS1, pmi.getState());
        assertEquals(sm1.mS1, pmi.getOriginalState());

        pmi = sm1.getProcessedMessage(1);
        pmi = sm1.getProcessedMessageInfo(1);
        assertEquals(TEST_CMD_2, pmi.getWhat());
        assertEquals(sm1.mS1, pmi.getState());
        assertEquals(sm1.mS1, pmi.getOriginalState());
@@ -571,20 +571,20 @@ public class HierarchicalStateMachineTest extends TestCase {

        assertTrue(sm2.getProcessedMessagesSize() == 4);

        ProcessedMessages.Info pmi;
        pmi = sm2.getProcessedMessage(0);
        ProcessedMessageInfo pmi;
        pmi = sm2.getProcessedMessageInfo(0);
        assertEquals(TEST_CMD_1, pmi.getWhat());
        assertEquals(sm2.mS1, pmi.getState());

        pmi = sm2.getProcessedMessage(1);
        pmi = sm2.getProcessedMessageInfo(1);
        assertEquals(TEST_CMD_2, pmi.getWhat());
        assertEquals(sm2.mS1, pmi.getState());

        pmi = sm2.getProcessedMessage(2);
        pmi = sm2.getProcessedMessageInfo(2);
        assertEquals(TEST_CMD_1, pmi.getWhat());
        assertEquals(sm2.mS2, pmi.getState());

        pmi = sm2.getProcessedMessage(3);
        pmi = sm2.getProcessedMessageInfo(3);
        assertEquals(TEST_CMD_2, pmi.getWhat());
        assertEquals(sm2.mS2, pmi.getState());

@@ -663,13 +663,13 @@ public class HierarchicalStateMachineTest extends TestCase {

        assertTrue(sm3.getProcessedMessagesSize() == 2);

        ProcessedMessages.Info pmi;
        pmi = sm3.getProcessedMessage(0);
        ProcessedMessageInfo pmi;
        pmi = sm3.getProcessedMessageInfo(0);
        assertEquals(TEST_CMD_1, pmi.getWhat());
        assertEquals(sm3.mParentState, pmi.getState());
        assertEquals(sm3.mChildState, pmi.getOriginalState());

        pmi = sm3.getProcessedMessage(1);
        pmi = sm3.getProcessedMessageInfo(1);
        assertEquals(TEST_CMD_2, pmi.getWhat());
        assertEquals(sm3.mParentState, pmi.getState());
        assertEquals(sm3.mChildState, pmi.getOriginalState());
@@ -757,13 +757,13 @@ public class HierarchicalStateMachineTest extends TestCase {

        assertTrue(sm4.getProcessedMessagesSize() == 2);

        ProcessedMessages.Info pmi;
        pmi = sm4.getProcessedMessage(0);
        ProcessedMessageInfo pmi;
        pmi = sm4.getProcessedMessageInfo(0);
        assertEquals(TEST_CMD_1, pmi.getWhat());
        assertEquals(sm4.mChildState1, pmi.getState());
        assertEquals(sm4.mChildState1, pmi.getOriginalState());

        pmi = sm4.getProcessedMessage(1);
        pmi = sm4.getProcessedMessageInfo(1);
        assertEquals(TEST_CMD_2, pmi.getWhat());
        assertEquals(sm4.mParentState, pmi.getState());
        assertEquals(sm4.mChildState2, pmi.getOriginalState());
@@ -1050,33 +1050,33 @@ public class HierarchicalStateMachineTest extends TestCase {
        assertEquals(1, sm5.mChildState5EnterCount);
        assertEquals(1, sm5.mChildState5ExitCount);

        ProcessedMessages.Info pmi;
        pmi = sm5.getProcessedMessage(0);
        ProcessedMessageInfo pmi;
        pmi = sm5.getProcessedMessageInfo(0);
        assertEquals(TEST_CMD_1, pmi.getWhat());
        assertEquals(sm5.mChildState1, pmi.getState());
        assertEquals(sm5.mChildState1, pmi.getOriginalState());

        pmi = sm5.getProcessedMessage(1);
        pmi = sm5.getProcessedMessageInfo(1);
        assertEquals(TEST_CMD_2, pmi.getWhat());
        assertEquals(sm5.mChildState2, pmi.getState());
        assertEquals(sm5.mChildState2, pmi.getOriginalState());

        pmi = sm5.getProcessedMessage(2);
        pmi = sm5.getProcessedMessageInfo(2);
        assertEquals(TEST_CMD_3, pmi.getWhat());
        assertEquals(sm5.mChildState5, pmi.getState());
        assertEquals(sm5.mChildState5, pmi.getOriginalState());

        pmi = sm5.getProcessedMessage(3);
        pmi = sm5.getProcessedMessageInfo(3);
        assertEquals(TEST_CMD_4, pmi.getWhat());
        assertEquals(sm5.mChildState3, pmi.getState());
        assertEquals(sm5.mChildState3, pmi.getOriginalState());

        pmi = sm5.getProcessedMessage(4);
        pmi = sm5.getProcessedMessageInfo(4);
        assertEquals(TEST_CMD_5, pmi.getWhat());
        assertEquals(sm5.mChildState4, pmi.getState());
        assertEquals(sm5.mChildState4, pmi.getOriginalState());

        pmi = sm5.getProcessedMessage(5);
        pmi = sm5.getProcessedMessageInfo(5);
        assertEquals(TEST_CMD_6, pmi.getWhat());
        assertEquals(sm5.mParentState2, pmi.getState());
        assertEquals(sm5.mParentState2, pmi.getOriginalState());
@@ -1434,7 +1434,7 @@ public class HierarchicalStateMachineTest extends TestCase {
        for (StateMachineSharedThread sm : sms) {
            assertTrue(sm.getProcessedMessagesCount() == 4);
            for (int i = 0; i < sm.getProcessedMessagesCount(); i++) {
                ProcessedMessages.Info pmi = sm.getProcessedMessage(i);
                ProcessedMessageInfo pmi = sm.getProcessedMessageInfo(i);
                assertEquals(i+1, pmi.getWhat());
                assertEquals(sm.mS1, pmi.getState());
                assertEquals(sm.mS1, pmi.getOriginalState());
@@ -1464,37 +1464,37 @@ public class HierarchicalStateMachineTest extends TestCase {
        }

        assertEquals(7, sm.getProcessedMessagesCount());
        ProcessedMessages.Info pmi = sm.getProcessedMessage(0);
        ProcessedMessageInfo pmi = sm.getProcessedMessageInfo(0);
        assertEquals(Hsm1.CMD_1, pmi.getWhat());
        assertEquals(sm.mS1, pmi.getState());
        assertEquals(sm.mS1, pmi.getOriginalState());

        pmi = sm.getProcessedMessage(1);
        pmi = sm.getProcessedMessageInfo(1);
        assertEquals(Hsm1.CMD_2, pmi.getWhat());
        assertEquals(sm.mP1, pmi.getState());
        assertEquals(sm.mS1, pmi.getOriginalState());

        pmi = sm.getProcessedMessage(2);
        pmi = sm.getProcessedMessageInfo(2);
        assertEquals(Hsm1.CMD_2, pmi.getWhat());
        assertEquals(sm.mS2, pmi.getState());
        assertEquals(sm.mS2, pmi.getOriginalState());

        pmi = sm.getProcessedMessage(3);
        pmi = sm.getProcessedMessageInfo(3);
        assertEquals(Hsm1.CMD_3, pmi.getWhat());
        assertEquals(sm.mS2, pmi.getState());
        assertEquals(sm.mS2, pmi.getOriginalState());

        pmi = sm.getProcessedMessage(4);
        pmi = sm.getProcessedMessageInfo(4);
        assertEquals(Hsm1.CMD_3, pmi.getWhat());
        assertEquals(sm.mP2, pmi.getState());
        assertEquals(sm.mP2, pmi.getOriginalState());

        pmi = sm.getProcessedMessage(5);
        pmi = sm.getProcessedMessageInfo(5);
        assertEquals(Hsm1.CMD_4, pmi.getWhat());
        assertEquals(sm.mP2, pmi.getState());
        assertEquals(sm.mP2, pmi.getOriginalState());

        pmi = sm.getProcessedMessage(6);
        pmi = sm.getProcessedMessageInfo(6);
        assertEquals(Hsm1.CMD_5, pmi.getWhat());
        assertEquals(sm.mP2, pmi.getState());
        assertEquals(sm.mP2, pmi.getOriginalState());