diff --git a/core/jni/Android.mk b/core/jni/Android.mk
index 30a7e68..84568e4 100644
--- a/core/jni/Android.mk
+++ b/core/jni/Android.mk
@@ -140,6 +140,7 @@
     android_hardware_camera2_legacy_LegacyCameraDevice.cpp \
     android_hardware_camera2_legacy_PerfMeasurement.cpp \
     android_hardware_camera2_DngCreator.cpp \
+    android_hardware_Radio.cpp \
     android_hardware_SensorManager.cpp \
     android_hardware_SerialPort.cpp \
     android_hardware_SoundTrigger.cpp \
@@ -236,10 +237,12 @@
     libpdfium \
     libimg_utils \
     libnetd_client \
+    libradio \
     libsoundtrigger \
     libminikin \
     libprocessgroup \
-    libnativebridge
+    libnativebridge \
+    libradio_metadata
 
 LOCAL_SHARED_LIBRARIES += \
     libhwui \
diff --git a/core/jni/AndroidRuntime.cpp b/core/jni/AndroidRuntime.cpp
index ad52e3f..441af15 100644
--- a/core/jni/AndroidRuntime.cpp
+++ b/core/jni/AndroidRuntime.cpp
@@ -81,6 +81,7 @@
 extern int register_android_hardware_camera2_legacy_LegacyCameraDevice(JNIEnv *env);
 extern int register_android_hardware_camera2_legacy_PerfMeasurement(JNIEnv *env);
 extern int register_android_hardware_camera2_DngCreator(JNIEnv *env);
+extern int register_android_hardware_Radio(JNIEnv *env);
 extern int register_android_hardware_SensorManager(JNIEnv *env);
 extern int register_android_hardware_SerialPort(JNIEnv *env);
 extern int register_android_hardware_SoundTrigger(JNIEnv *env);
@@ -1254,6 +1255,7 @@
     REG_JNI(register_android_hardware_camera2_legacy_LegacyCameraDevice),
     REG_JNI(register_android_hardware_camera2_legacy_PerfMeasurement),
     REG_JNI(register_android_hardware_camera2_DngCreator),
+    REG_JNI(register_android_hardware_Radio),
     REG_JNI(register_android_hardware_SensorManager),
     REG_JNI(register_android_hardware_SerialPort),
     REG_JNI(register_android_hardware_SoundTrigger),
diff --git a/core/jni/android_hardware_Radio.cpp b/core/jni/android_hardware_Radio.cpp
new file mode 100644
index 0000000..b9dd77a
--- /dev/null
+++ b/core/jni/android_hardware_Radio.cpp
@@ -0,0 +1,936 @@
+/*
+**
+** Copyright 2015, 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.
+*/
+
+//#define LOG_NDEBUG 0
+#define LOG_TAG "Radio-JNI"
+#include <utils/Log.h>
+
+#include "jni.h"
+#include "JNIHelp.h"
+#include "core_jni_helpers.h"
+#include <system/radio.h>
+#include <system/radio_metadata.h>
+#include <radio/RadioCallback.h>
+#include <radio/Radio.h>
+#include <utils/RefBase.h>
+#include <utils/Vector.h>
+#include <binder/IMemory.h>
+#include <binder/MemoryDealer.h>
+
+using namespace android;
+
+static jclass gArrayListClass;
+static struct {
+    jmethodID    add;
+} gArrayListMethods;
+
+static const char* const kRadioManagerClassPathName = "android/hardware/radio/RadioManager";
+static jclass gRadioManagerClass;
+
+static const char* const kRadioModuleClassPathName = "android/hardware/radio/RadioModule";
+static jclass gRadioModuleClass;
+static struct {
+    jfieldID    mNativeContext;
+    jfieldID    mId;
+} gModuleFields;
+static jmethodID gPostEventFromNative;
+
+static const char* const kModulePropertiesClassPathName =
+                                     "android/hardware/radio/RadioManager$ModuleProperties";
+static jclass gModulePropertiesClass;
+static jmethodID gModulePropertiesCstor;
+
+
+static const char* const kRadioBandDescriptorClassPathName =
+                             "android/hardware/radio/RadioManager$BandDescriptor";
+static jclass gRadioBandDescriptorClass;
+static struct {
+    jfieldID mRegion;
+    jfieldID mType;
+    jfieldID mLowerLimit;
+    jfieldID mUpperLimit;
+    jfieldID mSpacing;
+} gRadioBandDescriptorFields;
+
+static const char* const kRadioFmBandDescriptorClassPathName =
+                             "android/hardware/radio/RadioManager$FmBandDescriptor";
+static jclass gRadioFmBandDescriptorClass;
+static jmethodID gRadioFmBandDescriptorCstor;
+
+static const char* const kRadioAmBandDescriptorClassPathName =
+                             "android/hardware/radio/RadioManager$AmBandDescriptor";
+static jclass gRadioAmBandDescriptorClass;
+static jmethodID gRadioAmBandDescriptorCstor;
+
+static const char* const kRadioBandConfigClassPathName =
+                             "android/hardware/radio/RadioManager$BandConfig";
+static jclass gRadioBandConfigClass;
+static struct {
+    jfieldID mDescriptor;
+} gRadioBandConfigFields;
+
+
+static const char* const kRadioFmBandConfigClassPathName =
+                             "android/hardware/radio/RadioManager$FmBandConfig";
+static jclass gRadioFmBandConfigClass;
+static jmethodID gRadioFmBandConfigCstor;
+static struct {
+    jfieldID mStereo;
+    jfieldID mRds;
+    jfieldID mTa;
+    jfieldID mAf;
+} gRadioFmBandConfigFields;
+
+static const char* const kRadioAmBandConfigClassPathName =
+                             "android/hardware/radio/RadioManager$AmBandConfig";
+static jclass gRadioAmBandConfigClass;
+static jmethodID gRadioAmBandConfigCstor;
+static struct {
+    jfieldID mStereo;
+} gRadioAmBandConfigFields;
+
+
+static const char* const kRadioProgramInfoClassPathName =
+                             "android/hardware/radio/RadioManager$ProgramInfo";
+static jclass gRadioProgramInfoClass;
+static jmethodID gRadioProgramInfoCstor;
+
+static const char* const kRadioMetadataClassPathName =
+                             "android/hardware/radio/RadioMetadata";
+static jclass gRadioMetadataClass;
+static jmethodID gRadioMetadataCstor;
+static struct {
+    jmethodID putIntFromNative;
+    jmethodID putStringFromNative;
+    jmethodID putBitmapFromNative;
+} gRadioMetadataMethods;
+
+static Mutex gLock;
+
+enum {
+    RADIO_STATUS_OK = 0,
+    RADIO_STATUS_ERROR = INT_MIN,
+    RADIO_PERMISSION_DENIED = -1,
+    RADIO_STATUS_NO_INIT = -19,
+    RADIO_STATUS_BAD_VALUE = -22,
+    RADIO_STATUS_DEAD_OBJECT = -32,
+    RADIO_STATUS_INVALID_OPERATION = -38,
+    RADIO_STATUS_TIMED_OUT = -110,
+};
+
+
+// ----------------------------------------------------------------------------
+
+static sp<Radio> getRadio(JNIEnv* env, jobject thiz)
+{
+    Mutex::Autolock l(gLock);
+    Radio* const radio = (Radio*)env->GetLongField(thiz, gModuleFields.mNativeContext);
+    return sp<Radio>(radio);
+}
+
+static sp<Radio> setRadio(JNIEnv* env, jobject thiz, const sp<Radio>& module)
+{
+    Mutex::Autolock l(gLock);
+    sp<Radio> old = (Radio*)env->GetLongField(thiz, gModuleFields.mNativeContext);
+    if (module.get()) {
+        module->incStrong((void*)setRadio);
+    }
+    if (old != 0) {
+        old->decStrong((void*)setRadio);
+    }
+    env->SetLongField(thiz, gModuleFields.mNativeContext, (jlong)module.get());
+    return old;
+}
+
+static jint convertBandDescriptorFromNative(JNIEnv *env,
+                                           jobject *jBandDescriptor,
+                                           const radio_band_config_t *nBandconfig)
+{
+    ALOGV("%s type %d region %d", __FUNCTION__, nBandconfig->band.type, nBandconfig->region);
+
+    if (nBandconfig->band.type == RADIO_BAND_FM ||
+            nBandconfig->band.type == RADIO_BAND_FM_HD) {
+        *jBandDescriptor = env->NewObject(gRadioFmBandDescriptorClass, gRadioFmBandDescriptorCstor,
+                                      nBandconfig->region, nBandconfig->band.type,
+                                      nBandconfig->band.lower_limit, nBandconfig->band.upper_limit,
+                                      nBandconfig->band.spacings[0],
+                                      nBandconfig->band.fm.stereo,
+                                      nBandconfig->band.fm.rds != RADIO_RDS_NONE,
+                                      nBandconfig->band.fm.ta,
+                                      nBandconfig->band.fm.af);
+    } else if (nBandconfig->band.type == RADIO_BAND_AM) {
+        *jBandDescriptor = env->NewObject(gRadioAmBandDescriptorClass, gRadioAmBandDescriptorCstor,
+                                      nBandconfig->region, nBandconfig->band.type,
+                                      nBandconfig->band.lower_limit, nBandconfig->band.upper_limit,
+                                      nBandconfig->band.spacings[0],
+                                      nBandconfig->band.am.stereo);
+    } else {
+        ALOGE("%s unknown band type %d", __FUNCTION__, nBandconfig->band.type);
+        return (jint)RADIO_STATUS_BAD_VALUE;
+    }
+
+    if (*jBandDescriptor == NULL) {
+        return (jint)RADIO_STATUS_NO_INIT;
+    }
+
+    return (jint)RADIO_STATUS_OK;
+}
+
+static jint convertBandConfigFromNative(JNIEnv *env,
+                                           jobject *jBandConfig,
+                                           const radio_band_config_t *nBandconfig)
+{
+    ALOGV("%s type %d region %d", __FUNCTION__, nBandconfig->band.type, nBandconfig->region);
+
+    if (nBandconfig->band.type == RADIO_BAND_FM ||
+            nBandconfig->band.type == RADIO_BAND_FM_HD) {
+        *jBandConfig = env->NewObject(gRadioFmBandConfigClass, gRadioFmBandConfigCstor,
+                                      nBandconfig->region, nBandconfig->band.type,
+                                      nBandconfig->band.lower_limit, nBandconfig->band.upper_limit,
+                                      nBandconfig->band.spacings[0],
+                                      nBandconfig->band.fm.stereo,
+                                      nBandconfig->band.fm.rds != RADIO_RDS_NONE,
+                                      nBandconfig->band.fm.ta,
+                                      nBandconfig->band.fm.af);
+    } else if (nBandconfig->band.type == RADIO_BAND_AM) {
+        *jBandConfig = env->NewObject(gRadioAmBandConfigClass, gRadioAmBandConfigCstor,
+                                      nBandconfig->region, nBandconfig->band.type,
+                                      nBandconfig->band.lower_limit, nBandconfig->band.upper_limit,
+                                      nBandconfig->band.spacings[0],
+                                      nBandconfig->band.am.stereo);
+    } else {
+        ALOGE("%s unknown band type %d", __FUNCTION__, nBandconfig->band.type);
+        return (jint)RADIO_STATUS_BAD_VALUE;
+    }
+
+    if (*jBandConfig == NULL) {
+        return (jint)RADIO_STATUS_NO_INIT;
+    }
+
+    return (jint)RADIO_STATUS_OK;
+}
+
+static jint convertMetadataFromNative(JNIEnv *env,
+                                           jobject *jMetadata,
+                                           const radio_metadata_t *nMetadata)
+{
+    ALOGV("%s", __FUNCTION__);
+    int count = radio_metadata_get_count(nMetadata);
+    if (count <= 0) {
+        return (jint)count;
+    }
+    *jMetadata = env->NewObject(gRadioMetadataClass, gRadioMetadataCstor);
+
+    jint jCount = 0;
+    jint jStatus = 0;
+    for (unsigned int i = 0; i < (unsigned int)count; i++) {
+        radio_metadata_key_t key;
+        radio_metadata_type_t type;
+        void *value;
+        unsigned int size;
+        if (radio_metadata_get_at_index(nMetadata, i , &key, &type, &value, &size) != 0) {
+            continue;
+        }
+        switch (type) {
+            case RADIO_METADATA_TYPE_INT: {
+                ALOGV("%s RADIO_METADATA_TYPE_INT %d", __FUNCTION__, key);
+                jStatus = env->CallIntMethod(*jMetadata,
+                                   gRadioMetadataMethods.putIntFromNative,
+                                   key, *(jint *)value);
+                if (jStatus == 0) {
+                    jCount++;
+                }
+            } break;
+            case RADIO_METADATA_TYPE_TEXT: {
+                ALOGV("%s RADIO_METADATA_TYPE_TEXT %d", __FUNCTION__, key);
+                jstring jText = env->NewStringUTF((char *)value);
+                jStatus = env->CallIntMethod(*jMetadata,
+                                   gRadioMetadataMethods.putStringFromNative,
+                                   key, jText);
+                if (jStatus == 0) {
+                    jCount++;
+                }
+                env->DeleteLocalRef(jText);
+            } break;
+            case RADIO_METADATA_TYPE_RAW: {
+                ALOGV("%s RADIO_METADATA_TYPE_RAW %d size %u", __FUNCTION__, key, size);
+                if (size == 0) {
+                    break;
+                }
+                jbyteArray jData = env->NewByteArray(size);
+                if (jData == NULL) {
+                    break;
+                }
+                env->SetByteArrayRegion(jData, 0, size, (jbyte *)value);
+                jStatus = env->CallIntMethod(*jMetadata,
+                                   gRadioMetadataMethods.putBitmapFromNative,
+                                   key, jData);
+                if (jStatus == 0) {
+                    jCount++;
+                }
+                env->DeleteLocalRef(jData);
+            } break;
+        }
+    }
+    return jCount;
+}
+
+static jint convertProgramInfoFromNative(JNIEnv *env,
+                                           jobject *jProgramInfo,
+                                           const radio_program_info_t *nProgramInfo)
+{
+    ALOGV("%s", __FUNCTION__);
+    int jStatus;
+    jobject jMetadata = NULL;
+    if (nProgramInfo->metadata != NULL) {
+        ALOGV("%s metadata %p", __FUNCTION__, nProgramInfo->metadata);
+        jStatus = convertMetadataFromNative(env, &jMetadata, nProgramInfo->metadata);
+        if (jStatus < 0) {
+            return jStatus;
+        }
+    }
+
+    ALOGV("%s channel %d tuned %d", __FUNCTION__, nProgramInfo->channel, nProgramInfo->tuned);
+
+    *jProgramInfo = env->NewObject(gRadioProgramInfoClass, gRadioProgramInfoCstor,
+                                  nProgramInfo->channel, nProgramInfo->sub_channel,
+                                  nProgramInfo->tuned, nProgramInfo->stereo,
+                                  nProgramInfo->digital, nProgramInfo->signal_strength,
+                                  jMetadata);
+
+    env->DeleteLocalRef(jMetadata);
+    return (jint)RADIO_STATUS_OK;
+}
+
+
+static jint convertBandConfigToNative(JNIEnv *env,
+                                      radio_band_config_t *nBandconfig,
+                                      jobject jBandConfig)
+{
+    ALOGV("%s", __FUNCTION__);
+
+    jobject jDescriptor = env->GetObjectField(jBandConfig, gRadioBandConfigFields.mDescriptor);
+
+    if (jDescriptor == NULL) {
+        return (jint)RADIO_STATUS_NO_INIT;
+    }
+
+    nBandconfig->region =
+            (radio_region_t)env->GetIntField(jDescriptor, gRadioBandDescriptorFields.mRegion);
+    nBandconfig->band.type =
+            (radio_band_t)env->GetIntField(jDescriptor, gRadioBandDescriptorFields.mType);
+    nBandconfig->band.lower_limit =
+            env->GetIntField(jDescriptor, gRadioBandDescriptorFields.mLowerLimit);
+    nBandconfig->band.upper_limit =
+            env->GetIntField(jDescriptor, gRadioBandDescriptorFields.mUpperLimit);
+    nBandconfig->band.num_spacings = 1;
+    nBandconfig->band.spacings[0] =
+            env->GetIntField(jDescriptor, gRadioBandDescriptorFields.mSpacing);
+
+    if (env->IsInstanceOf(jBandConfig, gRadioFmBandConfigClass)) {
+        nBandconfig->band.fm.deemphasis = radio_demephasis_for_region(nBandconfig->region);
+        nBandconfig->band.fm.stereo =
+                env->GetBooleanField(jBandConfig, gRadioFmBandConfigFields.mStereo);
+        nBandconfig->band.fm.rds =
+                radio_rds_for_region(env->GetBooleanField(jBandConfig,
+                                                          gRadioFmBandConfigFields.mRds),
+                                     nBandconfig->region);
+        nBandconfig->band.fm.ta = env->GetBooleanField(jBandConfig, gRadioFmBandConfigFields.mTa);
+        nBandconfig->band.fm.af = env->GetBooleanField(jBandConfig, gRadioFmBandConfigFields.mAf);
+    } else if (env->IsInstanceOf(jBandConfig, gRadioAmBandConfigClass)) {
+        nBandconfig->band.am.stereo =
+                env->GetBooleanField(jBandConfig, gRadioAmBandConfigFields.mStereo);
+    } else {
+        return (jint)RADIO_STATUS_BAD_VALUE;
+    }
+
+    return (jint)RADIO_STATUS_OK;
+}
+
+static jint
+android_hardware_Radio_listModules(JNIEnv *env, jobject clazz,
+                                          jobject jModules)
+{
+    ALOGV("%s", __FUNCTION__);
+
+    if (jModules == NULL) {
+        ALOGE("listModules NULL ArrayList");
+        return RADIO_STATUS_BAD_VALUE;
+    }
+    if (!env->IsInstanceOf(jModules, gArrayListClass)) {
+        ALOGE("listModules not an arraylist");
+        return RADIO_STATUS_BAD_VALUE;
+    }
+
+    unsigned int numModules = 0;
+    radio_properties_t *nModules = NULL;
+
+    status_t status = Radio::listModules(nModules, &numModules);
+    if (status != NO_ERROR || numModules == 0) {
+        return (jint)status;
+    }
+
+    nModules = (radio_properties_t *)calloc(numModules, sizeof(radio_properties_t));
+
+    status = Radio::listModules(nModules, &numModules);
+    ALOGV("%s Radio::listModules status %d numModules %d", __FUNCTION__, status, numModules);
+
+    if (status != NO_ERROR) {
+        numModules = 0;
+    }
+
+    for (size_t i = 0; i < numModules; i++) {
+        if (nModules[i].num_bands == 0) {
+            continue;
+        }
+        ALOGV("%s module %zu id %d implementor %s product %s",
+              __FUNCTION__, i, nModules[i].handle, nModules[i].implementor,
+              nModules[i].product);
+
+
+        jobjectArray jBands = env->NewObjectArray(nModules[i].num_bands,
+                                                  gRadioBandDescriptorClass, NULL);
+
+        for (size_t j = 0; j < nModules[i].num_bands; j++) {
+            jobject jBandDescriptor;
+            int jStatus =
+                    convertBandDescriptorFromNative(env, &jBandDescriptor, &nModules[i].bands[j]);
+            if (jStatus != RADIO_STATUS_OK) {
+                continue;
+            }
+            env->SetObjectArrayElement(jBands, j, jBandDescriptor);
+            env->DeleteLocalRef(jBandDescriptor);
+        }
+
+        if (env->GetArrayLength(jBands) == 0) {
+            continue;
+        }
+        jstring jImplementor = env->NewStringUTF(nModules[i].implementor);
+        jstring jProduct = env->NewStringUTF(nModules[i].product);
+        jstring jVersion = env->NewStringUTF(nModules[i].version);
+        jstring jSerial = env->NewStringUTF(nModules[i].serial);
+        jobject jModule = env->NewObject(gModulePropertiesClass, gModulePropertiesCstor,
+                                               nModules[i].handle, nModules[i].class_id,
+                                               jImplementor, jProduct, jVersion, jSerial,
+                                               nModules[i].num_tuners,
+                                               nModules[i].num_audio_sources,
+                                               nModules[i].supports_capture,
+                                               jBands);
+
+        env->DeleteLocalRef(jImplementor);
+        env->DeleteLocalRef(jProduct);
+        env->DeleteLocalRef(jVersion);
+        env->DeleteLocalRef(jSerial);
+        env->DeleteLocalRef(jBands);
+        if (jModule == NULL) {
+            continue;
+        }
+        env->CallBooleanMethod(jModules, gArrayListMethods.add, jModule);
+    }
+
+    free(nModules);
+    return (jint) status;
+}
+
+// ----------------------------------------------------------------------------
+
+class JNIRadioCallback: public RadioCallback
+{
+public:
+    JNIRadioCallback(JNIEnv* env, jobject thiz, jobject weak_thiz);
+    ~JNIRadioCallback();
+
+    virtual void onEvent(struct radio_event *event);
+
+private:
+    jclass      mClass;     // Reference to Radio class
+    jobject     mObject;    // Weak ref to Radio Java object to call on
+};
+
+JNIRadioCallback::JNIRadioCallback(JNIEnv* env, jobject thiz, jobject weak_thiz)
+{
+
+    // Hold onto the RadioModule class for use in calling the static method
+    // that posts events to the application thread.
+    jclass clazz = env->GetObjectClass(thiz);
+    if (clazz == NULL) {
+        ALOGE("Can't find class %s", kRadioModuleClassPathName);
+        return;
+    }
+    mClass = (jclass)env->NewGlobalRef(clazz);
+
+    // We use a weak reference so the RadioModule object can be garbage collected.
+    // The reference is only used as a proxy for callbacks.
+    mObject  = env->NewGlobalRef(weak_thiz);
+}
+
+JNIRadioCallback::~JNIRadioCallback()
+{
+    // remove global references
+    JNIEnv *env = AndroidRuntime::getJNIEnv();
+    if (env == NULL) {
+        return;
+    }
+    env->DeleteGlobalRef(mObject);
+    env->DeleteGlobalRef(mClass);
+}
+
+void JNIRadioCallback::onEvent(struct radio_event *event)
+{
+    JNIEnv *env = AndroidRuntime::getJNIEnv();
+    if (env == NULL) {
+        return;
+    }
+
+    ALOGV("%s", __FUNCTION__);
+
+    jobject jObj = NULL;
+    jint jArg2 = 0;
+    jint jStatus = RADIO_STATUS_OK;
+    switch (event->type) {
+        case RADIO_EVENT_CONFIG:
+            jStatus = convertBandConfigFromNative(env, &jObj, &event->config);
+            break;
+        case RADIO_EVENT_TUNED:
+        case RADIO_EVENT_AF_SWITCH:
+            ALOGV("%s RADIO_EVENT_TUNED channel %d", __FUNCTION__, event->info.channel);
+            jStatus = convertProgramInfoFromNative(env, &jObj, &event->info);
+            break;
+        case RADIO_EVENT_METADATA:
+            jStatus = convertMetadataFromNative(env, &jObj, event->metadata);
+            if (jStatus >= 0) {
+                jStatus = RADIO_STATUS_OK;
+            }
+            break;
+        case RADIO_EVENT_ANTENNA:
+        case RADIO_EVENT_TA:
+        case RADIO_EVENT_CONTROL:
+            jArg2 = event->on ? 1 : 0;
+            break;
+    }
+
+    if (jStatus != RADIO_STATUS_OK) {
+        return;
+    }
+    env->CallStaticVoidMethod(mClass, gPostEventFromNative, mObject,
+                              event->type, event->status, jArg2, jObj);
+
+    env->DeleteLocalRef(jObj);
+    if (env->ExceptionCheck()) {
+        ALOGW("An exception occurred while notifying an event.");
+        env->ExceptionClear();
+    }
+}
+
+// ----------------------------------------------------------------------------
+
+static void
+android_hardware_Radio_setup(JNIEnv *env, jobject thiz,
+                             jobject weak_this, jobject jConfig, jboolean withAudio)
+{
+    ALOGV("%s", __FUNCTION__);
+
+    setRadio(env, thiz, 0);
+
+    sp<JNIRadioCallback> callback = new JNIRadioCallback(env, thiz, weak_this);
+
+    radio_handle_t handle = (radio_handle_t)env->GetIntField(thiz, gModuleFields.mId);
+
+    struct radio_band_config nConfig;
+    struct radio_band_config *configPtr = NULL;
+    if (jConfig != NULL) {
+        jint jStatus = convertBandConfigToNative(env, &nConfig, jConfig);
+        if (jStatus != RADIO_STATUS_OK) {
+            return;
+        }
+        configPtr = &nConfig;
+    }
+    sp<Radio> module = Radio::attach(handle, configPtr, (bool)withAudio, callback);
+    if (module == 0) {
+        return;
+    }
+
+    setRadio(env, thiz, module);
+}
+
+static void
+android_hardware_Radio_close(JNIEnv *env, jobject thiz)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = setRadio(env, thiz, 0);
+    ALOGV("detach module %p", module.get());
+    if (module != 0) {
+        ALOGV("detach module->detach()");
+        module->detach();
+    }
+}
+
+static void
+android_hardware_Radio_finalize(JNIEnv *env, jobject thiz)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module != 0) {
+        ALOGW("Radio finalized without being detached");
+    }
+    android_hardware_Radio_close(env, thiz);
+}
+
+static jint
+android_hardware_Radio_setConfiguration(JNIEnv *env, jobject thiz, jobject jConfig)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+
+    if (!env->IsInstanceOf(jConfig, gRadioFmBandConfigClass) &&
+            !env->IsInstanceOf(jConfig, gRadioAmBandConfigClass)) {
+        return RADIO_STATUS_BAD_VALUE;
+    }
+
+    struct radio_band_config nConfig;
+    jint jStatus = convertBandConfigToNative(env, &nConfig, jConfig);
+    if (jStatus != RADIO_STATUS_OK) {
+        return jStatus;
+    }
+
+    status_t status = module->setConfiguration(&nConfig);
+    return (jint)status;
+}
+
+static jint
+android_hardware_Radio_getConfiguration(JNIEnv *env, jobject thiz, jobjectArray jConfigs)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+    if (env->GetArrayLength(jConfigs) != 1) {
+        return (jint)RADIO_STATUS_BAD_VALUE;
+    }
+
+    struct radio_band_config nConfig;
+
+    status_t status = module->getConfiguration(&nConfig);
+    if (status != NO_ERROR) {
+        return (jint)status;
+    }
+    jobject jConfig;
+    int jStatus = convertBandConfigFromNative(env, &jConfig, &nConfig);
+    if (jStatus != RADIO_STATUS_OK) {
+        return jStatus;
+    }
+    env->SetObjectArrayElement(jConfigs, 0, jConfig);
+    env->DeleteLocalRef(jConfig);
+    return RADIO_STATUS_OK;
+}
+
+static jint
+android_hardware_Radio_setMute(JNIEnv *env, jobject thiz, jboolean mute)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+    status_t status = module->setMute((bool)mute);
+    return (jint)status;
+}
+
+static jboolean
+android_hardware_Radio_getMute(JNIEnv *env, jobject thiz)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return true;
+    }
+    bool mute = true;
+    status_t status = module->getMute(&mute);
+    if (status != NO_ERROR) {
+        return true;
+    }
+    return (jboolean)mute;
+}
+
+static jint
+android_hardware_Radio_step(JNIEnv *env, jobject thiz, jint direction, jboolean skipSubChannel)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+    status_t status = module->step((radio_direction_t)direction, (bool)skipSubChannel);
+    return (jint)status;
+}
+
+static jint
+android_hardware_Radio_scan(JNIEnv *env, jobject thiz, jint direction, jboolean skipSubChannel)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+    status_t status = module->scan((radio_direction_t)direction, (bool)skipSubChannel);
+    return (jint)status;
+}
+
+static jint
+android_hardware_Radio_tune(JNIEnv *env, jobject thiz, jint channel, jint subChannel)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+    status_t status = module->tune((unsigned int)channel, (unsigned int)subChannel);
+    return (jint)status;
+}
+
+static jint
+android_hardware_Radio_cancel(JNIEnv *env, jobject thiz)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+    status_t status = module->cancel();
+    return (jint)status;
+}
+
+static jint
+android_hardware_Radio_getProgramInformation(JNIEnv *env, jobject thiz, jobjectArray jInfos)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return RADIO_STATUS_NO_INIT;
+    }
+    if (env->GetArrayLength(jInfos) != 1) {
+        return (jint)RADIO_STATUS_BAD_VALUE;
+    }
+
+    struct radio_program_info nInfo;
+    radio_metadata_allocate(&nInfo.metadata, 0, 0);
+    jobject jInfo = NULL;
+    int jStatus;
+
+    jStatus = (int)module->getProgramInformation(&nInfo);
+    if (jStatus != RADIO_STATUS_OK) {
+        goto exit;
+    }
+    jStatus = convertProgramInfoFromNative(env, &jInfo, &nInfo);
+    if (jStatus != RADIO_STATUS_OK) {
+        goto exit;
+    }
+    env->SetObjectArrayElement(jInfos, 0, jInfo);
+
+exit:
+    if (jInfo != NULL) {
+        env->DeleteLocalRef(jInfo);
+    }
+    radio_metadata_deallocate(nInfo.metadata);
+    return jStatus;
+}
+
+static jboolean
+android_hardware_Radio_isAntennaConnected(JNIEnv *env, jobject thiz)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return false;
+    }
+
+    struct radio_band_config nConfig;
+
+    status_t status = module->getConfiguration(&nConfig);
+    if (status != NO_ERROR) {
+        return false;
+    }
+
+    return (jboolean)nConfig.band.antenna_connected;
+}
+
+
+static jboolean
+android_hardware_Radio_hasControl(JNIEnv *env, jobject thiz)
+{
+    ALOGV("%s", __FUNCTION__);
+    sp<Radio> module = getRadio(env, thiz);
+    if (module == NULL) {
+        return false;
+    }
+
+    bool hasControl;
+    status_t status = module->hasControl(&hasControl);
+    if (status != NO_ERROR) {
+        return false;
+    }
+
+    return (jboolean)hasControl;
+}
+
+
+static JNINativeMethod gMethods[] = {
+    {"listModules",
+        "(Ljava/util/List;)I",
+        (void *)android_hardware_Radio_listModules},
+};
+
+static JNINativeMethod gModuleMethods[] = {
+    {"native_setup",
+        "(Ljava/lang/Object;Landroid/hardware/radio/RadioManager$BandConfig;Z)V",
+        (void *)android_hardware_Radio_setup},
+    {"native_finalize",
+        "()V",
+        (void *)android_hardware_Radio_finalize},
+    {"close",
+        "()V",
+        (void *)android_hardware_Radio_close},
+    {"setConfiguration",
+        "(Landroid/hardware/radio/RadioManager$BandConfig;)I",
+        (void *)android_hardware_Radio_setConfiguration},
+    {"getConfiguration",
+        "([Landroid/hardware/radio/RadioManager$BandConfig;)I",
+        (void *)android_hardware_Radio_getConfiguration},
+    {"setMute",
+        "(Z)I",
+        (void *)android_hardware_Radio_setMute},
+    {"getMute",
+        "()Z",
+        (void *)android_hardware_Radio_getMute},
+    {"step",
+        "(IZ)I",
+        (void *)android_hardware_Radio_step},
+    {"scan",
+        "(IZ)I",
+        (void *)android_hardware_Radio_scan},
+    {"tune",
+        "(II)I",
+        (void *)android_hardware_Radio_tune},
+    {"cancel",
+        "()I",
+        (void *)android_hardware_Radio_cancel},
+    {"getProgramInformation",
+        "([Landroid/hardware/radio/RadioManager$ProgramInfo;)I",
+        (void *)android_hardware_Radio_getProgramInformation},
+    {"isAntennaConnected",
+        "()Z",
+        (void *)android_hardware_Radio_isAntennaConnected},
+    {"hasControl",
+        "()Z",
+        (void *)android_hardware_Radio_hasControl},
+};
+
+int register_android_hardware_Radio(JNIEnv *env)
+{
+    jclass arrayListClass = FindClassOrDie(env, "java/util/ArrayList");
+    gArrayListClass = MakeGlobalRefOrDie(env, arrayListClass);
+    gArrayListMethods.add = GetMethodIDOrDie(env, arrayListClass, "add", "(Ljava/lang/Object;)Z");
+
+    jclass lClass = FindClassOrDie(env, kRadioManagerClassPathName);
+    gRadioManagerClass = MakeGlobalRefOrDie(env, lClass);
+
+    jclass moduleClass = FindClassOrDie(env, kRadioModuleClassPathName);
+    gRadioModuleClass = MakeGlobalRefOrDie(env, moduleClass);
+    gPostEventFromNative = GetStaticMethodIDOrDie(env, moduleClass, "postEventFromNative",
+                                                  "(Ljava/lang/Object;IIILjava/lang/Object;)V");
+    gModuleFields.mNativeContext = GetFieldIDOrDie(env, moduleClass, "mNativeContext", "J");
+    gModuleFields.mId = GetFieldIDOrDie(env, moduleClass, "mId", "I");
+
+    jclass modulePropertiesClass = FindClassOrDie(env, kModulePropertiesClassPathName);
+    gModulePropertiesClass = MakeGlobalRefOrDie(env, modulePropertiesClass);
+    gModulePropertiesCstor = GetMethodIDOrDie(env, modulePropertiesClass, "<init>",
+            "(IILjava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;IIZ[Landroid/hardware/radio/RadioManager$BandDescriptor;)V");
+
+    jclass bandDescriptorClass = FindClassOrDie(env, kRadioBandDescriptorClassPathName);
+    gRadioBandDescriptorClass = MakeGlobalRefOrDie(env, bandDescriptorClass);
+    gRadioBandDescriptorFields.mRegion = GetFieldIDOrDie(env, bandDescriptorClass, "mRegion", "I");
+    gRadioBandDescriptorFields.mType = GetFieldIDOrDie(env, bandDescriptorClass, "mType", "I");
+    gRadioBandDescriptorFields.mLowerLimit =
+            GetFieldIDOrDie(env, bandDescriptorClass, "mLowerLimit", "I");
+    gRadioBandDescriptorFields.mUpperLimit =
+            GetFieldIDOrDie(env, bandDescriptorClass, "mUpperLimit", "I");
+    gRadioBandDescriptorFields.mSpacing =
+            GetFieldIDOrDie(env, bandDescriptorClass, "mSpacing", "I");
+
+    jclass fmBandDescriptorClass = FindClassOrDie(env, kRadioFmBandDescriptorClassPathName);
+    gRadioFmBandDescriptorClass = MakeGlobalRefOrDie(env, fmBandDescriptorClass);
+    gRadioFmBandDescriptorCstor = GetMethodIDOrDie(env, fmBandDescriptorClass, "<init>",
+            "(IIIIIZZZZ)V");
+
+    jclass amBandDescriptorClass = FindClassOrDie(env, kRadioAmBandDescriptorClassPathName);
+    gRadioAmBandDescriptorClass = MakeGlobalRefOrDie(env, amBandDescriptorClass);
+    gRadioAmBandDescriptorCstor = GetMethodIDOrDie(env, amBandDescriptorClass, "<init>",
+            "(IIIIIZ)V");
+
+    jclass bandConfigClass = FindClassOrDie(env, kRadioBandConfigClassPathName);
+    gRadioBandConfigClass = MakeGlobalRefOrDie(env, bandConfigClass);
+    gRadioBandConfigFields.mDescriptor =
+            GetFieldIDOrDie(env, bandConfigClass, "mDescriptor",
+                            "Landroid/hardware/radio/RadioManager$BandDescriptor;");
+
+    jclass fmBandConfigClass = FindClassOrDie(env, kRadioFmBandConfigClassPathName);
+    gRadioFmBandConfigClass = MakeGlobalRefOrDie(env, fmBandConfigClass);
+    gRadioFmBandConfigCstor = GetMethodIDOrDie(env, fmBandConfigClass, "<init>",
+            "(IIIIIZZZZ)V");
+    gRadioFmBandConfigFields.mStereo = GetFieldIDOrDie(env, fmBandConfigClass, "mStereo", "Z");
+    gRadioFmBandConfigFields.mRds = GetFieldIDOrDie(env, fmBandConfigClass, "mRds", "Z");
+    gRadioFmBandConfigFields.mTa = GetFieldIDOrDie(env, fmBandConfigClass, "mTa", "Z");
+    gRadioFmBandConfigFields.mAf = GetFieldIDOrDie(env, fmBandConfigClass, "mAf", "Z");
+
+
+    jclass amBandConfigClass = FindClassOrDie(env, kRadioAmBandConfigClassPathName);
+    gRadioAmBandConfigClass = MakeGlobalRefOrDie(env, amBandConfigClass);
+    gRadioAmBandConfigCstor = GetMethodIDOrDie(env, amBandConfigClass, "<init>",
+            "(IIIIIZ)V");
+    gRadioAmBandConfigFields.mStereo = GetFieldIDOrDie(env, amBandConfigClass, "mStereo", "Z");
+
+    jclass programInfoClass = FindClassOrDie(env, kRadioProgramInfoClassPathName);
+    gRadioProgramInfoClass = MakeGlobalRefOrDie(env, programInfoClass);
+    gRadioProgramInfoCstor = GetMethodIDOrDie(env, programInfoClass, "<init>",
+            "(IIZZZILandroid/hardware/radio/RadioMetadata;)V");
+
+    jclass metadataClass = FindClassOrDie(env, kRadioMetadataClassPathName);
+    gRadioMetadataClass = MakeGlobalRefOrDie(env, metadataClass);
+    gRadioMetadataCstor = GetMethodIDOrDie(env, metadataClass, "<init>", "()V");
+    gRadioMetadataMethods.putIntFromNative = GetMethodIDOrDie(env, metadataClass,
+                                                              "putIntFromNative",
+                                                              "(II)I");
+    gRadioMetadataMethods.putStringFromNative = GetMethodIDOrDie(env, metadataClass,
+                                                                 "putStringFromNative",
+                                                                 "(ILjava/lang/String;)I");
+    gRadioMetadataMethods.putBitmapFromNative = GetMethodIDOrDie(env, metadataClass,
+                                                                 "putBitmapFromNative",
+                                                                 "(I[B)I");
+
+
+    RegisterMethodsOrDie(env, kRadioManagerClassPathName, gMethods, NELEM(gMethods));
+
+    int ret = RegisterMethodsOrDie(env, kRadioModuleClassPathName, gModuleMethods, NELEM(gModuleMethods));
+
+    ALOGI("%s DONE", __FUNCTION__);
+
+    return ret;
+}
