diff --git a/src/com/android/server/telecom/Call.java b/src/com/android/server/telecom/Call.java
index 3402cc4..4e3c79d 100644
--- a/src/com/android/server/telecom/Call.java
+++ b/src/com/android/server/telecom/Call.java
@@ -74,6 +74,11 @@
     public static final int CALL_DIRECTION_INCOMING = 2;
     public static final int CALL_DIRECTION_UNKNOWN = 3;
 
+    /** Identifies extras changes which originated from a connection service. */
+    public static final int SOURCE_CONNECTION_SERVICE = 1;
+    /** Identifies extras changes which originated from an incall service. */
+    public static final int SOURCE_INCALL_SERVICE = 2;
+
     /**
      * Listener for events on the call.
      */
@@ -95,7 +100,8 @@
         void onCallerInfoChanged(Call call);
         void onIsVoipAudioModeChanged(Call call);
         void onStatusHintsChanged(Call call);
-        void onExtrasChanged(Call call);
+        void onExtrasChanged(Call c, int source, Bundle extras);
+        void onExtrasRemoved(Call c, int source, List<String> keys);
         void onHandleChanged(Call call);
         void onCallerDisplayNameChanged(Call call);
         void onVideoStateChanged(Call call);
@@ -144,7 +150,9 @@
         @Override
         public void onStatusHintsChanged(Call call) {}
         @Override
-        public void onExtrasChanged(Call call) {}
+        public void onExtrasChanged(Call c, int source, Bundle extras) {}
+        @Override
+        public void onExtrasRemoved(Call c, int source, List<String> keys) {}
         @Override
         public void onHandleChanged(Call call) {}
         @Override
@@ -1069,7 +1077,7 @@
         setRingbackRequested(connection.isRingbackRequested());
         setIsVoipAudioMode(connection.getIsVoipAudioMode());
         setStatusHints(connection.getStatusHints());
-        setExtras(connection.getExtras());
+        putExtras(SOURCE_CONNECTION_SERVICE, connection.getExtras());
 
         mConferenceableCalls.clear();
         for (String id : connection.getConferenceableConnectionIds()) {
@@ -1327,10 +1335,64 @@
         return mExtras;
     }
 
-    void setExtras(Bundle extras) {
-        mExtras = extras;
+    /**
+     * Adds extras to the extras bundle associated with this {@link Call}.
+     *
+     * Note: this method needs to know the source of the extras change (see
+     * {@link #SOURCE_CONNECTION_SERVICE}, {@link #SOURCE_INCALL_SERVICE}).  Extras changes which
+     * originate from a connection service will only be notified to incall services.  Likewise,
+     * changes originating from the incall services will only notify the connection service of the
+     * change.
+     *
+     * @param source The source of the extras addition.
+     * @param extras The extras.
+     */
+    void putExtras(int source, Bundle extras) {
+        if (extras == null) {
+            return;
+        }
+        if (mExtras == null) {
+            mExtras = new Bundle();
+        }
+        mExtras.putAll(extras);
+
         for (Listener l : mListeners) {
-            l.onExtrasChanged(this);
+            l.onExtrasChanged(this, source, extras);
+        }
+
+        // If the change originated from an InCallService, notify the connection service.
+        if (source == SOURCE_INCALL_SERVICE) {
+            mConnectionService.onExtrasChanged(this, mExtras);
+        }
+    }
+
+    /**
+     * Removes extras from the extras bundle associated with this {@link Call}.
+     *
+     * Note: this method needs to know the source of the extras change (see
+     * {@link #SOURCE_CONNECTION_SERVICE}, {@link #SOURCE_INCALL_SERVICE}).  Extras changes which
+     * originate from a connection service will only be notified to incall services.  Likewise,
+     * changes originating from the incall services will only notify the connection service of the
+     * change.
+     *
+     * @param source The source of the extras removal.
+     * @param keys The extra keys to remove.
+     */
+    void removeExtras(int source, List<String> keys) {
+        if (mExtras == null) {
+            return;
+        }
+        for (String key : keys) {
+            mExtras.remove(key);
+        }
+
+        for (Listener l : mListeners) {
+            l.onExtrasRemoved(this, source, keys);
+        }
+
+        // If the change originated from an InCallService, notify the connection service.
+        if (source == SOURCE_INCALL_SERVICE) {
+            mConnectionService.onExtrasChanged(this, mExtras);
         }
     }
 
diff --git a/src/com/android/server/telecom/CallsManager.java b/src/com/android/server/telecom/CallsManager.java
index 73d5556..16e8f92 100644
--- a/src/com/android/server/telecom/CallsManager.java
+++ b/src/com/android/server/telecom/CallsManager.java
@@ -1144,7 +1144,14 @@
     }
 
     @Override
-    public void onExtrasChanged(Call call) {
+    public void onExtrasChanged(Call c, int source, Bundle extras) {
+        if (source != Call.SOURCE_CONNECTION_SERVICE) {
+            return;
+        }
+        handleCallTechnologyChange(c);
+    }
+
+    private void handleCallTechnologyChange(Call call) {
         if (call.getExtras() != null
                 && call.getExtras().containsKey(TelecomManager.EXTRA_CALL_TECHNOLOGY_TYPE)) {
 
@@ -1461,7 +1468,7 @@
         call.setVideoState(parcelableConference.getVideoState());
         call.setVideoProvider(parcelableConference.getVideoProvider());
         call.setStatusHints(parcelableConference.getStatusHints());
-        call.setExtras(parcelableConference.getExtras());
+        call.putExtras(Call.SOURCE_CONNECTION_SERVICE, parcelableConference.getExtras());
 
         // TODO: Move this to be a part of addCall()
         call.addListener(this);
diff --git a/src/com/android/server/telecom/ConnectionServiceWrapper.java b/src/com/android/server/telecom/ConnectionServiceWrapper.java
index 5543f9b..69c7573 100644
--- a/src/com/android/server/telecom/ConnectionServiceWrapper.java
+++ b/src/com/android/server/telecom/ConnectionServiceWrapper.java
@@ -487,16 +487,33 @@
         }
 
         @Override
-        public void setExtras(String callId, Bundle extras) {
-            Log.startSession("CSW.sE");
+        public void putExtras(String callId, Bundle extras) {
+            Log.startSession("CSW.pE");
             long token = Binder.clearCallingIdentity();
             try {
                 synchronized (mLock) {
                     Bundle.setDefusable(extras, true);
-                    logIncoming("setExtras %s %s", callId, extras);
                     Call call = mCallIdMapper.getCall(callId);
                     if (call != null) {
-                        call.setExtras(extras);
+                        call.putExtras(Call.SOURCE_CONNECTION_SERVICE, extras);
+                    }
+                }
+            } finally {
+                Binder.restoreCallingIdentity(token);
+                Log.endSession();
+            }
+        }
+
+        @Override
+        public void removeExtras(String callId, List<String> keys) {
+            Log.startSession("CSW.rE");
+            long token = Binder.clearCallingIdentity();
+            try {
+                synchronized (mLock) {
+                    logIncoming("removeExtra %s %s", callId, keys);
+                    Call call = mCallIdMapper.getCall(callId);
+                    if (call != null) {
+                        call.removeExtras(Call.SOURCE_CONNECTION_SERVICE, keys);
                     }
                 }
             } finally {
@@ -962,6 +979,17 @@
         }
     }
 
+    void onExtrasChanged(Call call, Bundle extras) {
+        final String callId = mCallIdMapper.getCallId(call);
+        if (callId != null && isServiceValid("onExtrasChanged")) {
+            try {
+                logOutgoing("onExtrasChanged %s %s", callId, extras);
+                mServiceInterface.onExtrasChanged(callId, extras);
+            } catch (RemoteException ignored) {
+            }
+        }
+    }
+
     /** {@inheritDoc} */
     @Override
     protected void setServiceInterface(IBinder binder) {
diff --git a/src/com/android/server/telecom/InCallAdapter.java b/src/com/android/server/telecom/InCallAdapter.java
index 4dd06d2..31d268e 100644
--- a/src/com/android/server/telecom/InCallAdapter.java
+++ b/src/com/android/server/telecom/InCallAdapter.java
@@ -22,6 +22,8 @@
 
 import com.android.internal.telecom.IInCallAdapter;
 
+import java.util.List;
+
 /**
  * Receives call commands and updates from in-call app and passes them through to CallsManager.
  * {@link InCallController} creates an instance of this class and passes it to the in-call app after
@@ -415,6 +417,50 @@
     }
 
     @Override
+    public void putExtras(String callId, Bundle extras) {
+        try {
+            Log.startSession("ICA.pE", mOwnerComponentName);
+            long token = Binder.clearCallingIdentity();
+            try {
+                synchronized (mLock) {
+                    Call call = mCallIdMapper.getCall(callId);
+                    if (call != null) {
+                        call.putExtras(Call.SOURCE_INCALL_SERVICE, extras);
+                    } else {
+                        Log.w(this, "putExtras, unknown call id: %s", callId);
+                    }
+                }
+            } finally {
+                Binder.restoreCallingIdentity(token);
+            }
+        } finally {
+            Log.endSession();
+        }
+    }
+
+    @Override
+    public void removeExtras(String callId, List<String> keys) {
+        try {
+            Log.startSession("ICA.rE", mOwnerComponentName);
+            long token = Binder.clearCallingIdentity();
+            try {
+                synchronized (mLock) {
+                    Call call = mCallIdMapper.getCall(callId);
+                    if (call != null) {
+                        call.removeExtras(Call.SOURCE_INCALL_SERVICE, keys);
+                    } else {
+                        Log.w(this, "removeExtra, unknown call id: %s", callId);
+                    }
+                }
+            } finally {
+                Binder.restoreCallingIdentity(token);
+            }
+        } finally {
+            Log.endSession();
+        }
+    }
+
+    @Override
     public void turnOnProximitySensor() {
         try {
             Log.startSession("ICA.tOnPS", mOwnerComponentName);
diff --git a/src/com/android/server/telecom/InCallController.java b/src/com/android/server/telecom/InCallController.java
index 93589ed..4ee6c20 100644
--- a/src/com/android/server/telecom/InCallController.java
+++ b/src/com/android/server/telecom/InCallController.java
@@ -33,6 +33,7 @@
 import android.os.Trace;
 import android.os.UserHandle;
 import android.telecom.CallAudioState;
+import android.telecom.ConnectionService;
 import android.telecom.DefaultDialerManager;
 import android.telecom.InCallService;
 import android.telecom.ParcelableCall;
@@ -104,8 +105,44 @@
             updateCall(call);
         }
 
+        /**
+         * Listens for changes to extras reported by a Telecom {@link Call}.
+         *
+         * Extras changes can originate from a {@link ConnectionService} or an {@link InCallService}
+         * so we will only trigger an update of the call information if the source of the extras
+         * change was a {@link ConnectionService}.
+         *
+         * @param call The call.
+         * @param source The source of the extras change ({@link Call#SOURCE_CONNECTION_SERVICE} or
+         *               {@link Call#SOURCE_INCALL_SERVICE}).
+         * @param extras The extras.
+         */
         @Override
-        public void onExtrasChanged(Call call) {
+        public void onExtrasChanged(Call call, int source, Bundle extras) {
+            // Do not inform InCallServices of changes which originated there.
+            if (source == Call.SOURCE_INCALL_SERVICE) {
+                return;
+            }
+            updateCall(call);
+        }
+
+        /**
+         * Listens for changes to extras reported by a Telecom {@link Call}.
+         *
+         * Extras changes can originate from a {@link ConnectionService} or an {@link InCallService}
+         * so we will only trigger an update of the call information if the source of the extras
+         * change was a {@link ConnectionService}.
+         *  @param call The call.
+         * @param source The source of the extras change ({@link Call#SOURCE_CONNECTION_SERVICE} or
+         *               {@link Call#SOURCE_INCALL_SERVICE}).
+         * @param keys The extra key removed
+         */
+        @Override
+        public void onExtrasRemoved(Call call, int source, List<String> keys) {
+            // Do not inform InCallServices of changes which originated there.
+            if (source == Call.SOURCE_INCALL_SERVICE) {
+                return;
+            }
             updateCall(call);
         }
 
diff --git a/testapps/src/com/android/server/telecom/testapps/TestConnectionService.java b/testapps/src/com/android/server/telecom/testapps/TestConnectionService.java
index c819838..b30e372 100644
--- a/testapps/src/com/android/server/telecom/testapps/TestConnectionService.java
+++ b/testapps/src/com/android/server/telecom/testapps/TestConnectionService.java
@@ -374,7 +374,7 @@
                 connectionExtras.putString(Connection.EXTRA_CALL_SUBJECT,
                         "This is a test of call subject lines.");
             }
-            connection.setExtras(connectionExtras);
+            connection.putExtras(connectionExtras);
 
             setAddress(connection, address);
 
diff --git a/tests/src/com/android/server/telecom/tests/BasicCallTests.java b/tests/src/com/android/server/telecom/tests/BasicCallTests.java
index ac080ae..6279c5e 100644
--- a/tests/src/com/android/server/telecom/tests/BasicCallTests.java
+++ b/tests/src/com/android/server/telecom/tests/BasicCallTests.java
@@ -585,33 +585,6 @@
         assertTrue(updatedConference.getChildCallIds().contains(callId3.mCallId));
     }
 
-    private ParcelableCall makeConferenceCall() throws Exception {
-        IdPair callId1 = startAndMakeActiveOutgoingCall("650-555-1212",
-                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
-
-        IdPair callId2 = startAndMakeActiveOutgoingCall("650-555-1213",
-                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
-
-        IInCallAdapter inCallAdapter = mInCallServiceFixtureX.getInCallAdapter();
-        inCallAdapter.conference(callId1.mCallId, callId2.mCallId);
-        // Wait for wacky non-deterministic behavior
-        Thread.sleep(200);
-        ParcelableCall call1 = mInCallServiceFixtureX.getCall(callId1.mCallId);
-        ParcelableCall call2 = mInCallServiceFixtureX.getCall(callId2.mCallId);
-        // Check that the two calls end up with a parent in the end
-        assertNotNull(call1.getParentCallId());
-        assertNotNull(call2.getParentCallId());
-        assertEquals(call1.getParentCallId(), call2.getParentCallId());
-
-        // Check to make sure that the parent call made it to the in-call service
-        String parentCallId = call1.getParentCallId();
-        ParcelableCall conferenceCall = mInCallServiceFixtureX.getCall(parentCallId);
-        assertEquals(2, conferenceCall.getChildCallIds().size());
-        assertTrue(conferenceCall.getChildCallIds().contains(callId1.mCallId));
-        assertTrue(conferenceCall.getChildCallIds().contains(callId2.mCallId));
-        return conferenceCall;
-    }
-
     /**
      * Tests the {@link Call#pullExternalCall()} API.  Verifies that if a call is not an external
      * call, no pull call request is made to the connection service.
diff --git a/tests/src/com/android/server/telecom/tests/CallExtrasTest.java b/tests/src/com/android/server/telecom/tests/CallExtrasTest.java
new file mode 100644
index 0000000..e9cd733
--- /dev/null
+++ b/tests/src/com/android/server/telecom/tests/CallExtrasTest.java
@@ -0,0 +1,433 @@
+/*
+ * Copyright (C) 2016 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.server.telecom.tests;
+
+import android.os.Bundle;
+import android.telecom.Call;
+import android.telecom.Conference;
+import android.telecom.Connection;
+import android.telecom.InCallService;
+import android.telecom.ParcelableCall;
+import android.test.suitebuilder.annotation.LargeTest;
+import android.test.suitebuilder.annotation.MediumTest;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+
+/**
+ * Tests the {@link Connection} and {@link Call} extras functionality.
+ */
+public class CallExtrasTest extends TelecomSystemTest {
+
+    public final static String EXTRA_KEY_STR = "STRINGKEY";
+    public final static String EXTRA_KEY_STR2 = "BLAHTEST";
+    public final static String EXTRA_KEY_INT = "INTKEY";
+    public final static String EXTRA_KEY_BOOL = "BOOLKEY";
+    public final static String EXTRA_VALUE_STR = "socks";
+    public final static String EXTRA_VALUE2_STR = "mozzarella";
+    public final static int EXTRA_VALUE_INT = 1234;
+
+    /**
+     * Tests setting extras on the connection side and ensuring they are propagated through to
+     * the InCallService.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testCsPutExtras() throws Exception {
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        // Communicate extras from the ConnectionService to the InCallService.
+        Bundle extras = new Bundle();
+        extras.putString(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        extras.putInt(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+        connection.putExtras(extras);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(
+                EXTRA_KEY_STR));
+        assertTrue(mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(
+                EXTRA_KEY_INT));
+    }
+
+    /**
+     * Tests setting extras on the connection side and ensuring they are propagated through to
+     * the InCallService.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testCsPutBooleanExtra() throws Exception {
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+        connection.putExtra(EXTRA_KEY_BOOL, true);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(mInCallServiceFixtureX.getCall(ids.mCallId).getExtras()
+                .containsKey(EXTRA_KEY_BOOL));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().getBoolean(EXTRA_KEY_BOOL));
+    }
+
+    /**
+     * Tests setting extras on the connection side and ensuring they are propagated through to
+     * the InCallService.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testCsPutIntExtra() throws Exception {
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+        connection.putExtra(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_INT));
+        assertEquals(EXTRA_VALUE_INT,
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().getInt(EXTRA_KEY_INT));
+    }
+
+    /**
+     * Tests setting extras on the connection side and ensuring they are propagated through to
+     * the InCallService.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testCsPutStringExtra() throws Exception {
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+        connection.putExtra(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertEquals(EXTRA_VALUE_STR,
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().getString(EXTRA_KEY_STR));
+    }
+
+    /**
+     * Tests remove extras on the connection side and ensuring the removal is reflected in the
+     * InCallService.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testCsRemoveExtra() throws Exception {
+        // Get a call up and running."STRING"
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        // Add something.
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+        connection.putExtra(EXTRA_KEY_STR2, EXTRA_VALUE_STR);
+        connection.putExtra(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertEquals(EXTRA_VALUE_STR,
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().getString(EXTRA_KEY_STR));
+
+        // Take it away.
+        connection.removeExtras(new ArrayList<String>(Arrays.asList(EXTRA_KEY_STR)));
+        mInCallServiceFixtureX.waitForUpdate();
+        assertFalse(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertTrue(mInCallServiceFixtureX.getCall(ids.mCallId).getExtras()
+                .containsKey(EXTRA_KEY_STR2));
+    }
+
+    /**
+     * Tests putting a new value for an existing extras key.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testCsUpdateExisting() throws Exception {
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+
+        // Communicate extras from the ConnectionService to the InCallService.
+        Bundle extras = new Bundle();
+        extras.putString(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        extras.putInt(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+        connection.putExtras(extras);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_INT));
+
+        connection.putExtra(EXTRA_KEY_STR, EXTRA_VALUE2_STR);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertEquals(EXTRA_VALUE2_STR,
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().getString(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_INT));
+    }
+
+    /**
+     * Tests ability of the deprecated setExtras method to detect changes to the extras bundle
+     * and merge these changes into the telecom extras.  The old setExtras worked by just replacing
+     * the entire extras bundle, so we need to ensure that we can properly handle cases where an
+     * API user has added or removed items from the extras, but still gracefully merge this into the
+     * extras maintained for the connection.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testCsSetExtras() throws Exception {
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+
+        // Set the initial bundle.
+        Bundle extras = new Bundle();
+        extras.putString(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        extras.putInt(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+        connection.setExtras(extras);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_INT));
+
+        // Modify the initial bundle to add a value and remove another.
+        extras.putString(EXTRA_KEY_STR2, EXTRA_VALUE2_STR);
+        extras.remove(EXTRA_KEY_STR);
+        connection.setExtras(extras);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertFalse(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_INT));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras()
+                        .containsKey(EXTRA_KEY_STR2));
+    }
+
+    /**
+     * Tests that additions to the extras via an {@link InCallService} are propagated back down to
+     * the {@link Connection}.
+     *
+     * @throws Exception
+     */
+    @MediumTest
+    public void testICSPutExtras() throws Exception {
+        Bundle extras = new Bundle();
+        extras.putString(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        extras.putInt(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+        mInCallServiceFixtureX.mInCallAdapter.putExtras(ids.mCallId, extras);
+        mConnectionServiceFixtureA.waitForExtras();
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+        assertNotNull(connection);
+        Bundle connectionExtras = connection.getExtras();
+        assertTrue(connectionExtras.containsKey(EXTRA_KEY_STR));
+        assertEquals(EXTRA_VALUE_STR, extras.getString(EXTRA_KEY_STR));
+        assertTrue(connectionExtras.containsKey(EXTRA_KEY_INT));
+        assertEquals(EXTRA_VALUE_INT, extras.getInt(EXTRA_KEY_INT));
+    }
+
+    /**
+     * A bi-directional test of the extras.  Tests setting extras from both the ConnectionService
+     * and InCall side and ensuring the bundles are merged appropriately.
+     *
+     * @throws Exception
+     */
+    @LargeTest
+    public void testExtrasBidirectional() throws Exception {
+        // Get a call up and running.
+        IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        Connection connection = mConnectionServiceFixtureA.mLatestConnection;
+
+        // Set the initial bundle.
+        Bundle someExtras = new Bundle();
+        someExtras.putString(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        someExtras.putInt(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+        connection.setExtras(someExtras);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_INT));
+
+        // From the InCall side, add another key
+        Bundle someMoreExtras = new Bundle();
+        someMoreExtras.putBoolean(EXTRA_KEY_BOOL, true);
+        mInCallServiceFixtureX.mInCallAdapter.putExtras(ids.mCallId, someMoreExtras);
+        mConnectionServiceFixtureA.waitForExtras();
+        Bundle connectionExtras = connection.getExtras();
+        assertTrue(connectionExtras.containsKey(EXTRA_KEY_STR));
+        assertTrue(connectionExtras.containsKey(EXTRA_KEY_INT));
+        assertTrue(connectionExtras.containsKey(EXTRA_KEY_BOOL));
+
+        // Modify the initial bundle to add a value and remove another.
+        someExtras.putString(EXTRA_KEY_STR2, EXTRA_VALUE2_STR);
+        someExtras.remove(EXTRA_KEY_STR);
+        connection.setExtras(someExtras);
+        mInCallServiceFixtureX.waitForUpdate();
+        assertFalse(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras().containsKey(EXTRA_KEY_INT));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras()
+                        .containsKey(EXTRA_KEY_STR2));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(ids.mCallId).getExtras()
+                        .containsKey(EXTRA_KEY_BOOL));
+    }
+
+    /**
+     * Similar to {@link #testCsSetExtras()}, tests to ensure the existing setExtras functionality
+     * is maintained.
+     *
+     * @throws Exception
+     */
+    @LargeTest
+    public void testConferenceSetExtras() throws Exception {
+        ParcelableCall call = makeConferenceCall();
+        String conferenceId = call.getId();
+
+        Conference conference = mConnectionServiceFixtureA.mLatestConference;
+        assertNotNull(conference);
+
+        Bundle someExtras = new Bundle();
+        someExtras.putString(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        someExtras.putInt(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+        conference.setExtras(someExtras);
+
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                        .containsKey(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                        .containsKey(EXTRA_KEY_INT));
+
+        someExtras.putString(EXTRA_KEY_STR2, EXTRA_VALUE2_STR);
+        someExtras.remove(EXTRA_KEY_INT);
+        conference.setExtras(someExtras);
+
+        mInCallServiceFixtureX.waitForUpdate();
+        assertTrue(
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                        .containsKey(EXTRA_KEY_STR));
+        assertFalse(
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                        .containsKey(EXTRA_KEY_INT));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                        .containsKey(EXTRA_KEY_STR2));
+    }
+
+    /**
+     * Tests putExtras for conferences.
+     *
+     * @throws Exception
+     */
+    @LargeTest
+    public void testConferenceExtraOperations() throws Exception {
+        ParcelableCall call = makeConferenceCall();
+        String conferenceId = call.getId();
+        Conference conference = mConnectionServiceFixtureA.mLatestConference;
+        assertNotNull(conference);
+
+        conference.putExtra(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        conference.putExtra(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+        conference.putExtra(EXTRA_KEY_BOOL, true);
+        mInCallServiceFixtureX.waitForUpdate();
+
+        assertTrue(mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                .containsKey(EXTRA_KEY_STR));
+        assertEquals(EXTRA_VALUE_STR,
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras().get(EXTRA_KEY_STR));
+        assertTrue(
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                        .containsKey(EXTRA_KEY_INT));
+        assertEquals(EXTRA_VALUE_INT,
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras().get(EXTRA_KEY_INT));
+        assertEquals(true,
+                mInCallServiceFixtureX.getCall(conferenceId).getExtras().get(EXTRA_KEY_BOOL));
+
+        conference.removeExtras(new ArrayList<String>(Arrays.asList(EXTRA_KEY_STR)));
+        mInCallServiceFixtureX.waitForUpdate();
+        assertFalse(mInCallServiceFixtureX.getCall(conferenceId).getExtras()
+                .containsKey(EXTRA_KEY_STR));
+    }
+
+    /**
+     * Tests communication of extras from an InCallService to a Conference.
+     *
+     * @throws Exception
+     */
+    @LargeTest
+    public void testConferenceICS() throws Exception {
+        ParcelableCall call = makeConferenceCall();
+        String conferenceId = call.getId();
+        Conference conference = mConnectionServiceFixtureA.mLatestConference;
+
+        Bundle someExtras = new Bundle();
+        someExtras.putString(EXTRA_KEY_STR, EXTRA_VALUE_STR);
+        mInCallServiceFixtureX.mInCallAdapter.putExtras(conferenceId, someExtras);
+        mConnectionServiceFixtureA.waitForExtras();
+
+        Bundle conferenceExtras = conference.getExtras();
+        assertTrue(conferenceExtras.containsKey(EXTRA_KEY_STR));
+
+        Bundle someMoreExtras = new Bundle();
+        someMoreExtras.putString(EXTRA_KEY_STR2, EXTRA_VALUE_STR);
+        someMoreExtras.putInt(EXTRA_KEY_INT, EXTRA_VALUE_INT);
+        someMoreExtras.putBoolean(EXTRA_KEY_BOOL, true);
+        mInCallServiceFixtureX.mInCallAdapter.putExtras(conferenceId, someMoreExtras);
+        mConnectionServiceFixtureA.waitForExtras();
+        conferenceExtras = conference.getExtras();
+        assertTrue(conferenceExtras.containsKey(EXTRA_KEY_STR));
+        assertTrue(conferenceExtras.containsKey(EXTRA_KEY_STR2));
+        assertTrue(conferenceExtras.containsKey(EXTRA_KEY_INT));
+        assertTrue(conferenceExtras.containsKey(EXTRA_KEY_BOOL));
+
+        mInCallServiceFixtureX.mInCallAdapter.removeExtras(conferenceId,
+                new ArrayList<String>(Arrays.asList(EXTRA_KEY_STR)));
+        mConnectionServiceFixtureA.waitForExtras();
+        conferenceExtras = conference.getExtras();
+        assertFalse(conferenceExtras.containsKey(EXTRA_KEY_STR));
+    }
+}
diff --git a/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java b/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java
index 27f169d..8d78f3d 100644
--- a/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java
+++ b/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java
@@ -48,11 +48,14 @@
 
 import java.lang.Override;
 import java.util.ArrayList;
+import java.util.Collection;
 import java.util.HashMap;
 import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
 import java.util.Set;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
 
 /**
  * Controls a test {@link IConnectionService} as would be provided by a source of connectivity
@@ -61,6 +64,7 @@
 public class ConnectionServiceFixture implements TestFixture<IConnectionService> {
     static int INVALID_VIDEO_STATE = -1;
     static int CAPABILITIES_NOT_SPECIFIED = 0;
+    public CountDownLatch mExtrasLock = new CountDownLatch(1);
 
     /**
      * Implementation of ConnectionService that performs no-ops for tasks normally meant for
@@ -73,7 +77,8 @@
         @Override
         public Connection onCreateUnknownConnection(
                 PhoneAccountHandle connectionManagerPhoneAccount, ConnectionRequest request) {
-            return new FakeConnection(request.getVideoState(), request.getAddress());
+            mLatestConnection = new FakeConnection(request.getVideoState(), request.getAddress());
+            return mLatestConnection;
         }
 
         @Override
@@ -82,6 +87,7 @@
             FakeConnection fakeConnection =  new FakeConnection(
                     mVideoState == INVALID_VIDEO_STATE ? request.getVideoState() : mVideoState,
                     request.getAddress());
+            mLatestConnection = fakeConnection;
             if (mCapabilities != CAPABILITIES_NOT_SPECIFIED) {
                 fakeConnection.setConnectionCapabilities(mCapabilities);
             }
@@ -92,7 +98,8 @@
         @Override
         public Connection onCreateOutgoingConnection(
                 PhoneAccountHandle connectionManagerPhoneAccount, ConnectionRequest request) {
-            return new FakeConnection(request.getVideoState(), request.getAddress());
+            mLatestConnection = new FakeConnection(request.getVideoState(), request.getAddress());
+            return mLatestConnection;
         }
 
         @Override
@@ -103,6 +110,7 @@
             Conference fakeConference = new FakeConference();
             fakeConference.addConnection(cxn1);
             fakeConference.addConnection(cxn2);
+            mLatestConference = fakeConference;
             addConference(fakeConference);
         }
     }
@@ -119,6 +127,11 @@
             setActive();
             setAddress(address, TelecomManager.PRESENTATION_ALLOWED);
         }
+
+        @Override
+        public void onExtrasChanged(Bundle extras) {
+            mExtrasLock.countDown();
+        }
     }
 
     public class FakeConference extends Conference {
@@ -136,6 +149,12 @@
             // Do nothing besides inform the connection that it was merged into this conference.
             connection.setConference(this);
         }
+
+        @Override
+        public void onExtrasChanged(Bundle extras) {
+            Log.w(this, "FakeConference onExtrasChanged");
+            mExtrasLock.countDown();
+        }
     }
 
     public class FakeConnectionService extends IConnectionService.Stub {
@@ -248,6 +267,10 @@
         public void sendCallEvent(String callId, String event, Bundle extras) throws RemoteException
         {}
 
+        public void onExtrasChanged(String callId, Bundle extras) throws RemoteException {
+            mConnectionServiceDelegateAdapter.onExtrasChanged(callId, extras);
+        }
+
         @Override
         public IBinder asBinder() {
             return this;
@@ -304,6 +327,8 @@
     }
 
     public String mLatestConnectionId;
+    public Connection mLatestConnection;
+    public Conference mLatestConference;
     public final Set<IConnectionServiceAdapter> mConnectionServiceAdapters = new HashSet<>();
     public final Map<String, ConnectionInfo> mConnectionById = new HashMap<>();
     public final Map<String, ConferenceInfo> mConferenceById = new HashMap<>();
@@ -491,6 +516,18 @@
         }
     }
 
+    /**
+     * Waits until the {@link Connection#onExtrasChanged(Bundle)} API has been called on a
+     * {@link Connection} or {@link Conference}.
+     */
+    public void waitForExtras() {
+        try {
+            mExtrasLock.await(TelecomSystemTest.TEST_TIMEOUT, TimeUnit.MILLISECONDS);
+        } catch (InterruptedException ie) {
+        }
+        mExtrasLock = new CountDownLatch(1);
+    }
+
     private ParcelableConference parcelable(ConferenceInfo c) {
         return new ParcelableConference(
                 c.phoneAccount,
diff --git a/tests/src/com/android/server/telecom/tests/InCallServiceFixture.java b/tests/src/com/android/server/telecom/tests/InCallServiceFixture.java
index eb007a3..bf12411 100644
--- a/tests/src/com/android/server/telecom/tests/InCallServiceFixture.java
+++ b/tests/src/com/android/server/telecom/tests/InCallServiceFixture.java
@@ -31,6 +31,8 @@
 
 import java.util.HashMap;
 import java.util.Map;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
 
 /**
  * Controls a test {@link IInCallService} as would be provided by an InCall UI on a system.
@@ -47,6 +49,7 @@
     public boolean mShowDialpad;
     public boolean mCanAddCall;
     public boolean mSilenceRinger;
+    public CountDownLatch mLock = new CountDownLatch(1);
 
     public class FakeInCallService extends IInCallService.Stub {
         @Override
@@ -76,6 +79,7 @@
             }
             mCallById.put(call.getId(), call);
             mLatestCallId = call.getId();
+            mLock.countDown();
         }
 
         @Override
@@ -144,4 +148,13 @@
     public IInCallAdapter getInCallAdapter() {
         return mInCallAdapter;
     }
+
+    public void waitForUpdate() {
+        try {
+            mLock.await(5000, TimeUnit.MILLISECONDS);
+        } catch (InterruptedException ie) {
+            return;
+        }
+        mLock = new CountDownLatch(1);
+    }
 }
diff --git a/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java b/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java
index 12d82b3..eeacd84 100644
--- a/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java
+++ b/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java
@@ -249,6 +249,33 @@
         super.tearDown();
     }
 
+    protected ParcelableCall makeConferenceCall() throws Exception {
+        IdPair callId1 = startAndMakeActiveOutgoingCall("650-555-1212",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        IdPair callId2 = startAndMakeActiveOutgoingCall("650-555-1213",
+                mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+
+        IInCallAdapter inCallAdapter = mInCallServiceFixtureX.getInCallAdapter();
+        inCallAdapter.conference(callId1.mCallId, callId2.mCallId);
+        // Wait for wacky non-deterministic behavior
+        Thread.sleep(200);
+        ParcelableCall call1 = mInCallServiceFixtureX.getCall(callId1.mCallId);
+        ParcelableCall call2 = mInCallServiceFixtureX.getCall(callId2.mCallId);
+        // Check that the two calls end up with a parent in the end
+        assertNotNull(call1.getParentCallId());
+        assertNotNull(call2.getParentCallId());
+        assertEquals(call1.getParentCallId(), call2.getParentCallId());
+
+        // Check to make sure that the parent call made it to the in-call service
+        String parentCallId = call1.getParentCallId();
+        ParcelableCall conferenceCall = mInCallServiceFixtureX.getCall(parentCallId);
+        assertEquals(2, conferenceCall.getChildCallIds().size());
+        assertTrue(conferenceCall.getChildCallIds().contains(callId1.mCallId));
+        assertTrue(conferenceCall.getChildCallIds().contains(callId2.mCallId));
+        return conferenceCall;
+    }
+
     private void setupTelecomSystem() throws Exception {
         // Use actual implementations instead of mocking the interface out.
         HeadsetMediaButtonFactory headsetMediaButtonFactory =
