diff options
author | Android Build Coastguard Worker <android-build-coastguard-worker@google.com> | 2021-07-15 01:59:55 +0000 |
---|---|---|
committer | Android Build Coastguard Worker <android-build-coastguard-worker@google.com> | 2021-07-15 01:59:55 +0000 |
commit | 9c34e4ee64f16075b94cf7bc1ef27fa4bd024537 (patch) | |
tree | b5c9dba3443e70e74b56d818c77c4ebbe28d7414 | |
parent | 9f148638a95930cc855a0f01121c234505a3ed32 (diff) | |
parent | 4487addc960985c41151cdf50c8050fc220a141d (diff) | |
download | goldfish-android12-mainline-captiveportallogin-release.tar.gz |
Snap for 7550930 from 4487addc960985c41151cdf50c8050fc220a141d to mainline-captiveportallogin-releaseandroid-mainline-12.0.0_r6android-mainline-12.0.0_r23android12-mainline-captiveportallogin-release
Change-Id: I39c038a917d44dcfe5c324d12b63c8fb60038b35
355 files changed, 8720 insertions, 21700 deletions
diff --git a/64bitonly/manifest.xml b/64bitonly/manifest.xml new file mode 100644 index 00000000..f39a4ae7 --- /dev/null +++ b/64bitonly/manifest.xml @@ -0,0 +1,113 @@ +<manifest version="1.0" type="device" target-level="4"> + <hal format="hidl"> + <name>android.hardware.bluetooth</name> + <transport>hwbinder</transport> + <version>1.1</version> + <interface> + <name>IBluetoothHci</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.bluetooth.audio</name> + <transport>hwbinder</transport> + <version>2.0</version> + <interface> + <name>IBluetoothAudioProvidersFactory</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.drm</name> + <transport>hwbinder</transport> + <version>1.0</version> + <interface> + <name>ICryptoFactory</name> + <instance>default</instance> + </interface> + <interface> + <name>IDrmFactory</name> + <instance>default</instance> + </interface> + <fqname>@1.2::ICryptoFactory/clearkey</fqname> + <fqname>@1.2::IDrmFactory/clearkey</fqname> + </hal> + <hal format="hidl"> + <name>android.hardware.audio.effect</name> + <transport>hwbinder</transport> + <version>6.0</version> + <interface> + <name>IEffectsFactory</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.authsecret</name> + <transport>hwbinder</transport> + <version>1.0</version> + <interface> + <name>IAuthSecret</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.graphics.allocator</name> + <transport>hwbinder</transport> + <version>3.0</version> + <interface> + <name>IAllocator</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.graphics.mapper</name> + <transport arch="32+64">passthrough</transport> + <version>3.0</version> + <interface> + <name>IMapper</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.graphics.composer</name> + <transport>hwbinder</transport> + <version>2.3</version> + <interface> + <name>IComposer</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.media.c2</name> + <transport>hwbinder</transport> + <version>1.1</version> + <interface> + <name>IComponentStore</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.radio.config</name> + <transport>hwbinder</transport> + <version>1.3</version> + <interface> + <name>IRadioConfig</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.radio</name> + <transport>hwbinder</transport> + <version>1.6</version> + <interface> + <name>IRadio</name> + <instance>slot1</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.camera.provider</name> + <transport>hwbinder</transport> + <fqname>@2.4::ICameraProvider/legacy/0</fqname> + </hal> + <kernel target-level="5"/> +</manifest> diff --git a/64bitonly/product/arm64-vendor.mk b/64bitonly/product/arm64-vendor.mk new file mode 100644 index 00000000..c676559a --- /dev/null +++ b/64bitonly/product/arm64-vendor.mk @@ -0,0 +1,47 @@ +include device/generic/goldfish/arm64-kernel.mk + +PRODUCT_PROPERTY_OVERRIDES += \ + vendor.rild.libpath=/vendor/lib64/libgoldfish-ril.so + +PRODUCT_PACKAGES += \ + emulatorip + +PRODUCT_PROPERTY_OVERRIDES += \ + ro.crypto.dm_default_key.options_format.version=2 + +PRODUCT_SHIPPING_API_LEVEL := 31 +PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS := false +TARGET_USES_MKE2FS := true + +# Note: the following lines need to stay at the beginning so that it can +# take priority and override the rules it inherit from other mk files +# see copy file rules in core/Makefile +ifeq ($(QEMU_USE_SYSTEM_EXT_PARTITIONS),true) + PRODUCT_COPY_FILES += \ + device/generic/goldfish/fstab.ranchu.initrd.arm.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.initrd.arm.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.arm.ex:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu \ + device/generic/goldfish/data/etc/encryptionkey.img:encryptionkey.img \ + device/generic/goldfish/task_profiles.json:$(TARGET_COPY_OUT_VENDOR)/etc/task_profiles.json +else + PRODUCT_COPY_FILES += \ + device/generic/goldfish/fstab.ranchu.initrd.arm:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.initrd.arm:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.arm:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu \ + device/generic/goldfish/data/etc/encryptionkey.img:encryptionkey.img \ + device/generic/goldfish/task_profiles.json:$(TARGET_COPY_OUT_VENDOR)/etc/task_profiles.json +endif + + +PRODUCT_COPY_FILES += \ + $(EMULATOR_KERNEL_FILE):kernel-ranchu \ + device/generic/goldfish/data/etc/advancedFeatures.ini.arm:advancedFeatures.ini \ + device/generic/goldfish/camera/media_codecs_performance_c2_arm64.xml:$(TARGET_COPY_OUT_VENDOR)/etc/media_codecs_performance_c2.xml \ + +EMULATOR_VENDOR_NO_GNSS := true + +ifeq ($(QEMU_DISABLE_AVB),true) + PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/etc/dummy.vbmeta.img:$(PRODUCT_OUT)/vbmeta.img \ + +endif diff --git a/64bitonly/product/emulator64_vendor.mk b/64bitonly/product/emulator64_vendor.mk new file mode 100644 index 00000000..f258266c --- /dev/null +++ b/64bitonly/product/emulator64_vendor.mk @@ -0,0 +1,52 @@ +# +# Copyright (C) 2012 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. + +# +# This file is included by other product makefiles to add all the +# emulator-related modules to PRODUCT_PACKAGES. +# + +$(call inherit-product, $(SRC_TARGET_DIR)/product/handheld_vendor.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/telephony_vendor.mk) + +# need this for gles libraries to load properly +# after moving to /vendor/lib/ +PRODUCT_PACKAGES += \ + vndk-sp + +DEVICE_PACKAGE_OVERLAYS := device/generic/goldfish/overlay + +PRODUCT_CHARACTERISTICS := emulator + +PRODUCT_FULL_TREBLE_OVERRIDE := true + +# goldfish vendor partition configurations +$(call inherit-product-if-exists, device/generic/goldfish/64bitonly/product/vendor.mk) + +#watchdog tiggers reboot because location service is not +#responding, disble it for now. +#still keep it on internal master as it is still working +#once it is fixed in aosp, remove this block of comment. +#PRODUCT_DEFAULT_PROPERTY_OVERRIDES += \ +#config.disable_location=true + +# enable Google-specific location features, +# like NetworkLocationProvider and LocationCollector +PRODUCT_SYSTEM_EXT_PROPERTIES += \ + ro.com.google.locationfeatures=1 + +# disable setupwizard +PRODUCT_SYSTEM_EXT_PROPERTIES += \ + ro.setupwizard.mode=DISABLED diff --git a/64bitonly/product/install_mediafiles.mk b/64bitonly/product/install_mediafiles.mk new file mode 100644 index 00000000..919c6548 --- /dev/null +++ b/64bitonly/product/install_mediafiles.mk @@ -0,0 +1,18 @@ +# This is to speed up presubmit of media related tests by asking emulator +# to run the media.adb script upon boot complete to copy those media files +# to sdcard/test + +PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/media/test/media.adb:data/adbscripts/media.adb + +PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/media/test/swirl_136x144_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_136x144_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_132x130_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_132x130_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_130x132_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_130x132_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_144x136_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_144x136_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_128x128_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_128x128_mpeg4.mp4 + + +PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/etc/empty_data_disk:data/empty_data_disk + diff --git a/64bitonly/product/sdk_phone64_arm64.mk b/64bitonly/product/sdk_phone64_arm64.mk new file mode 100644 index 00000000..d6652467 --- /dev/null +++ b/64bitonly/product/sdk_phone64_arm64.mk @@ -0,0 +1,58 @@ +# +# 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. +# +QEMU_USE_SYSTEM_EXT_PARTITIONS := true +PRODUCT_USE_DYNAMIC_PARTITIONS := true + +# This is a build configuration for a full-featured build of the +# Open-Source part of the tree. It's geared toward a US-centric +# build quite specifically for the emulator, and might not be +# entirely appropriate to inherit from for on-device configurations. + +PRODUCT_ENFORCE_ARTIFACT_PATH_REQUIREMENTS := relaxed + +# +# All components inherited here go to system image +# +$(call inherit-product, $(SRC_TARGET_DIR)/product/core_64_bit.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/generic_system.mk) + +# +# All components inherited here go to system_ext image +# +$(call inherit-product, $(SRC_TARGET_DIR)/product/handheld_system_ext.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/telephony_system_ext.mk) + +# +# All components inherited here go to product image +# +$(call inherit-product, $(SRC_TARGET_DIR)/product/aosp_product.mk) + +# +# All components inherited here go to vendor or vendor_boot image +# +$(call inherit-product, device/generic/goldfish/arm64-vendor.mk) +$(call inherit-product, device/generic/goldfish/64bitonly/product/emulator64_vendor.mk) +$(call inherit-product, device/generic/goldfish/emulator64_arm64/device.mk) + +# Define the host tools and libs that are parts of the SDK. +$(call inherit-product-if-exists, sdk/build/product_sdk.mk) +$(call inherit-product-if-exists, development/build/product_sdk.mk) + +# Overrides +PRODUCT_BRAND := Android +PRODUCT_NAME := sdk_phone64_arm64 +PRODUCT_DEVICE := emulator64_arm64 +PRODUCT_MODEL := Android SDK built for arm64 diff --git a/64bitonly/product/sdk_phone64_x86_64.mk b/64bitonly/product/sdk_phone64_x86_64.mk new file mode 100644 index 00000000..26869542 --- /dev/null +++ b/64bitonly/product/sdk_phone64_x86_64.mk @@ -0,0 +1,56 @@ +# +# 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. +# +QEMU_USE_SYSTEM_EXT_PARTITIONS := true +PRODUCT_USE_DYNAMIC_PARTITIONS := true + +# +# All components inherited here go to system image +# +$(call inherit-product, $(SRC_TARGET_DIR)/product/core_64_bit.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/generic_system.mk) + +# Enable mainline checking for excat this product name +ifeq (sdk_phone64_x86_64,$(TARGET_PRODUCT)) +PRODUCT_ENFORCE_ARTIFACT_PATH_REQUIREMENTS := relaxed +endif + +# +# All components inherited here go to system_ext image +# +$(call inherit-product, $(SRC_TARGET_DIR)/product/handheld_system_ext.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/telephony_system_ext.mk) + +# +# All components inherited here go to product image +# +$(call inherit-product, $(SRC_TARGET_DIR)/product/aosp_product.mk) + +# +# All components inherited here go to vendor image +# +$(call inherit-product, device/generic/goldfish/64bitonly/product/x86_64-vendor.mk) +$(call inherit-product, device/generic/goldfish/64bitonly/product/emulator64_vendor.mk) +$(call inherit-product, device/generic/goldfish/emulator64_x86_64/device.mk) + +# Define the host tools and libs that are parts of the SDK. +$(call inherit-product-if-exists, sdk/build/product_sdk.mk) +$(call inherit-product-if-exists, development/build/product_sdk.mk) + +# Overrides +PRODUCT_BRAND := Android +PRODUCT_NAME := sdk_phone64_x86_64 +PRODUCT_DEVICE := emulator64_x86_64 +PRODUCT_MODEL := Android SDK built for x86_64 diff --git a/64bitonly/product/vendor.mk b/64bitonly/product/vendor.mk new file mode 100644 index 00000000..b3f5d026 --- /dev/null +++ b/64bitonly/product/vendor.mk @@ -0,0 +1,331 @@ +# +# Copyright (C) 2018 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. + +# +# This file is to configure vendor/data partitions of emulator-related products +# +$(call inherit-product-if-exists, frameworks/native/build/phone-xhdpi-2048-dalvik-heap.mk) + +# Enable Scoped Storage related +$(call inherit-product, $(SRC_TARGET_DIR)/product/emulated_storage.mk) + +PRODUCT_SOONG_NAMESPACES += \ + device/generic/goldfish \ + device/generic/goldfish-opengl + +PRODUCT_SYSTEM_EXT_PROPERTIES += ro.lockscreen.disable.default=1 + +DISABLE_RILD_OEM_HOOK := true + +DEVICE_MANIFEST_FILE := device/generic/goldfish/64bitonly/manifest.xml +PRODUCT_SOONG_NAMESPACES += hardware/google/camera +PRODUCT_SOONG_NAMESPACES += hardware/google/camera/devices/EmulatedCamera + +# Device modules +PRODUCT_PACKAGES += \ + vulkan.ranchu \ + libandroidemu \ + libOpenglCodecCommon \ + libOpenglSystemCommon \ + libcuttlefish-ril-2 \ + libgoldfish-rild \ + qemu-adb-keys \ + qemu-props \ + stagefright \ + fingerprint.ranchu \ + android.hardware.graphics.composer@2.3-impl \ + android.hardware.graphics.composer@2.3-service \ + android.hardware.graphics.allocator@3.0-service \ + android.hardware.graphics.mapper@3.0-impl-ranchu \ + hwcomposer.ranchu \ + toybox_vendor \ + android.hardware.wifi@1.0-service \ + android.hardware.biometrics.fingerprint@2.1-service \ + android.hardware.media.c2@1.0-service-goldfish \ + libcodec2_goldfish_vp8dec \ + libcodec2_goldfish_vp9dec \ + libcodec2_goldfish_avcdec \ + sh_vendor \ + ip_vendor \ + iw_vendor \ + local_time.default \ + SdkSetup \ + EmulatorRadioConfig \ + EmulatorTetheringConfigOverlay \ + MultiDisplayProvider \ + libGoldfishProfiler + +ifneq ($(BUILD_EMULATOR_OPENGL),false) +PRODUCT_PACKAGES += \ + libGLESv1_CM_emulation \ + lib_renderControl_enc \ + libEGL_emulation \ + libGLESv2_enc \ + libvulkan_enc \ + libGLESv2_emulation \ + libGLESv1_enc \ + libEGL_angle \ + libGLESv1_CM_angle \ + libGLESv2_angle \ + libfeature_support_angle.so +endif + +PRODUCT_PACKAGES += \ + android.hardware.bluetooth@1.1-service.sim \ + android.hardware.bluetooth.audio@2.0-impl +PRODUCT_PROPERTY_OVERRIDES += vendor.bt.rootcanal_test_console=off + +PRODUCT_PACKAGES += \ + android.hardware.health@2.1-service \ + android.hardware.health@2.1-impl \ + android.hardware.health.storage@1.0-service \ + +PRODUCT_PACKAGES += \ + android.hardware.neuralnetworks@1.3-service-sample-all \ + android.hardware.neuralnetworks@1.3-service-sample-float-fast \ + android.hardware.neuralnetworks@1.3-service-sample-float-slow \ + android.hardware.neuralnetworks@1.3-service-sample-minimal \ + android.hardware.neuralnetworks@1.3-service-sample-quant + +PRODUCT_PACKAGES += \ + android.hardware.keymaster@4.1-service + +PRODUCT_PACKAGES += \ + DisplayCutoutEmulationEmu01Overlay \ + EmulationPixel5Overlay \ + SystemUIEmulationPixel5Overlay \ + EmulationPixel4XLOverlay 4\ + SystemUIEmulationPixel4XLOverlay \ + EmulationPixel4Overlay \ + SystemUIEmulationPixel4Overlay \ + EmulationPixel4aOverlay \ + SystemUIEmulationPixel4aOverlay \ + EmulationPixel3XLOverlay \ + SystemUIEmulationPixel3XLOverlay \ + SystemUIEmulationPixel3Overlay \ + SystemUIEmulationPixel3aOverlay \ + SystemUIEmulationPixel3aXLOverlay \ + EmulationPixel2XLOverlay \ + SystemUIEmulationPixel2XLOverlay \ + NavigationBarMode2ButtonOverlay \ + +ifneq ($(EMULATOR_VENDOR_NO_GNSS),true) +#disable the following as it does not support gnss yet +#PRODUCT_PACKAGES += android.hardware.gnss-service.example +PRODUCT_PACKAGES += android.hardware.gnss@2.0-service.ranchu +endif + +ifneq ($(EMULATOR_VENDOR_NO_SENSORS),true) +PRODUCT_PACKAGES += \ + android.hardware.sensors@2.1-service.multihal \ + android.hardware.sensors@2.1-impl.ranchu +# TODO(rkir): +# add a soong namespace and move this into a.h.sensors@2.1-impl.ranchu +# as prebuilt_etc. For now soong_namespace causes a build break because the fw +# refers to our wifi HAL in random places. +PRODUCT_COPY_FILES += \ + device/generic/goldfish/sensors/hals.conf:$(TARGET_COPY_OUT_VENDOR)/etc/sensors/hals.conf +endif + +PRODUCT_PACKAGES += \ + android.hardware.drm@1.0-service \ + android.hardware.drm@1.0-impl \ + android.hardware.drm@1.4-service.clearkey \ + +PRODUCT_PACKAGES += \ + android.hardware.power-service.example \ + +PRODUCT_PROPERTY_OVERRIDES += ro.control_privapp_permissions=enforce +PRODUCT_PROPERTY_OVERRIDES += ro.hardware.power=ranchu +PRODUCT_PROPERTY_OVERRIDES += ro.crypto.volume.filenames_mode=aes-256-cts +PRODUCT_VENDOR_PROPERTIES += graphics.gpu.profiler.support=true + +PRODUCT_PROPERTY_OVERRIDES += persist.sys.zram_enabled=1 \ + +PRODUCT_PACKAGES += \ + android.hardware.dumpstate@1.1-service.example \ + +# Prevent logcat from getting canceled early on in boot +PRODUCT_PROPERTY_OVERRIDES += ro.logd.size=1M \ + +ifneq ($(EMULATOR_VENDOR_NO_CAMERA),true) +PRODUCT_PACKAGES += \ + android.hardware.camera.provider@2.4-service_64 \ + android.hardware.camera.provider@2.4-impl \ + camera.ranchu \ + camera.ranchu.jpeg \ + android.hardware.camera.provider@2.7-service-google \ + libgooglecamerahwl_impl \ + android.hardware.camera.provider@2.7-impl-google +endif + +ifneq ($(EMULATOR_VENDOR_NO_SOUND),true) +PRODUCT_PACKAGES += \ + android.hardware.audio.service \ + android.hardware.audio@6.0-impl.ranchu \ + android.hardware.soundtrigger@2.2-impl.ranchu \ + android.hardware.audio.effect@6.0-impl \ + +PRODUCT_COPY_FILES += \ + device/generic/goldfish/audio/policy/audio_policy_configuration.xml:$(TARGET_COPY_OUT_VENDOR)/etc/audio_policy_configuration.xml \ + device/generic/goldfish/audio/policy/primary_audio_policy_configuration.xml:$(TARGET_COPY_OUT_VENDOR)/etc/primary_audio_policy_configuration.xml \ + frameworks/av/services/audiopolicy/config/r_submix_audio_policy_configuration.xml:$(TARGET_COPY_OUT_VENDOR)/etc/r_submix_audio_policy_configuration.xml \ + frameworks/av/services/audiopolicy/config/audio_policy_volumes.xml:$(TARGET_COPY_OUT_VENDOR)/etc/audio_policy_volumes.xml \ + frameworks/av/services/audiopolicy/config/default_volume_tables.xml:$(TARGET_COPY_OUT_VENDOR)/etc/default_volume_tables.xml \ + frameworks/av/media/libeffects/data/audio_effects.xml:$(TARGET_COPY_OUT_VENDOR)/etc/audio_effects.xml \ + +endif + +PRODUCT_PACKAGES += \ + android.hardware.gatekeeper@1.0-service.software + +# WiFi: vendor side +PRODUCT_PACKAGES += \ + mac80211_create_radios \ + createns \ + dhcpclient \ + execns \ + hostapd \ + hostapd_nohidl \ + netmgr \ + wifi_forwarder \ + wpa_supplicant \ + +PRODUCT_PACKAGES += \ + android.hardware.usb@1.0-service + +# Thermal +PRODUCT_PACKAGES += \ + android.hardware.thermal@2.0-service.mock + +# Atrace +PRODUCT_PACKAGES += \ + android.hardware.atrace@1.0-service + +# Vibrator +PRODUCT_PACKAGES += \ + android.hardware.vibrator-service.example + +# Authsecret +PRODUCT_PACKAGES += \ + android.hardware.authsecret@1.0-service + +# Identity +PRODUCT_PACKAGES += \ + android.hardware.identity-service.example + +# Input Classifier HAL +PRODUCT_PACKAGES += \ + android.hardware.input.classifier@1.0-service.default + +# lights +PRODUCT_PACKAGES += \ + android.hardware.lights-service.example + +# power stats +PRODUCT_PACKAGES += \ + android.hardware.power.stats@1.0-service.mock + +# Reboot escrow +PRODUCT_PACKAGES += \ + android.hardware.rebootescrow-service.default + +# Extension implementation for Jetpack WindowManager +PRODUCT_PACKAGES += \ + androidx.window.sidecar + +PRODUCT_PACKAGES += \ + android.hardware.biometrics.face@1.0-service.example + +PRODUCT_PACKAGES += \ + android.hardware.contexthub@1.1-service.mock + + +PRODUCT_PROPERTY_OVERRIDES += \ + debug.stagefright.c2inputsurface=-1 \ + debug.stagefright.ccodec=4 + +# Enable Incremental on the device via kernel driver +PRODUCT_PROPERTY_OVERRIDES += ro.incremental.enable=yes + + +PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/etc/dtb.img:dtb.img \ + device/generic/goldfish/data/etc/apns-conf.xml:data/misc/apns/apns-conf.xml \ + device/generic/goldfish/radio/RadioConfig/radioconfig.xml:data/misc/emulator/config/radioconfig.xml \ + device/generic/goldfish/data/etc/iccprofile_for_sim0.xml:data/misc/modem_simulator/iccprofile_for_sim0.xml \ + device/google/cuttlefish/host/commands/modem_simulator/files/iccprofile_for_sim0_for_CtsCarrierApiTestCases.xml:data/misc/modem_simulator/iccprofile_for_carrierapitests.xml \ + device/generic/goldfish/data/etc/numeric_operator.xml:data/misc/modem_simulator/etc/modem_simulator/files/numeric_operator.xml \ + device/generic/goldfish/data/etc/local.prop:data/local.prop \ + device/generic/goldfish/init.qemu-adb-keys.sh:$(TARGET_COPY_OUT_SYSTEM_EXT)/bin/init.qemu-adb-keys.sh \ + device/generic/goldfish/init.ranchu-core.sh:$(TARGET_COPY_OUT_VENDOR)/bin/init.ranchu-core.sh \ + device/generic/goldfish/init.ranchu-net.sh:$(TARGET_COPY_OUT_VENDOR)/bin/init.ranchu-net.sh \ + device/generic/goldfish/wifi/init.wifi.sh:$(TARGET_COPY_OUT_VENDOR)/bin/init.wifi.sh \ + device/generic/goldfish/init.ranchu.rc:$(TARGET_COPY_OUT_VENDOR)/etc/init/hw/init.ranchu.rc \ + device/generic/goldfish/init.system_ext.rc:$(TARGET_COPY_OUT_SYSTEM_EXT)/etc/init/init.system_ext.rc \ + device/generic/goldfish/fstab.ranchu:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu \ + device/generic/goldfish/ueventd.ranchu.rc:$(TARGET_COPY_OUT_VENDOR)/ueventd.rc \ + device/generic/goldfish/input/goldfish_rotary.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/goldfish_rotary.idc \ + device/generic/goldfish/input/qwerty2.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/qwerty2.idc \ + device/generic/goldfish/input/qwerty.kl:$(TARGET_COPY_OUT_VENDOR)/usr/keylayout/qwerty.kl \ + device/generic/goldfish/input/virtio_input_multi_touch_1.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_1.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_2.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_2.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_3.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_3.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_4.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_4.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_5.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_5.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_6.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_6.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_7.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_7.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_8.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_8.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_9.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_9.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_10.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_10.idc \ + device/generic/goldfish/input/virtio_input_multi_touch_11.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_11.idc \ + device/generic/goldfish/display_settings_freeform.xml:$(TARGET_COPY_OUT_VENDOR)/etc/display_settings_freeform.xml \ + device/generic/goldfish/device_state_configuration.xml:$(TARGET_COPY_OUT_VENDOR)/etc/devicestate/device_state_configuration.xml \ + device/generic/goldfish/data/etc/config.ini:config.ini \ + device/generic/goldfish/wifi/simulated_hostapd.conf:$(TARGET_COPY_OUT_VENDOR)/etc/simulated_hostapd.conf \ + device/generic/goldfish/wifi/wpa_supplicant.conf:$(TARGET_COPY_OUT_VENDOR)/etc/wifi/wpa_supplicant.conf \ + frameworks/native/data/etc/android.hardware.bluetooth_le.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.bluetooth_le.xml \ + frameworks/native/data/etc/android.hardware.bluetooth.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.bluetooth.xml \ + system/bt/vendor_libs/test_vendor_lib/data/controller_properties.json:vendor/etc/bluetooth/controller_properties.json \ + frameworks/native/data/etc/android.hardware.wifi.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.wifi.xml \ + frameworks/native/data/etc/android.hardware.wifi.passpoint.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.wifi.passpoint.xml \ + frameworks/native/data/etc/android.hardware.wifi.direct.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.wifi.direct.xml \ + device/generic/goldfish/data/etc/handheld_core_hardware.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/handheld_core_hardware.xml \ + device/generic/goldfish/camera/media_profiles.xml:$(TARGET_COPY_OUT_VENDOR)/etc/media_profiles_V1_0.xml \ + frameworks/av/media/libstagefright/data/media_codecs_google_audio.xml:$(TARGET_COPY_OUT_VENDOR)/etc/media_codecs_google_audio.xml \ + frameworks/av/media/libstagefright/data/media_codecs_google_telephony.xml:$(TARGET_COPY_OUT_VENDOR)/etc/media_codecs_google_telephony.xml \ + device/generic/goldfish/camera/media_codecs_google_video_default.xml:${TARGET_COPY_OUT_VENDOR}/etc/media_codecs_google_video.xml \ + device/generic/goldfish/camera/media_codecs.xml:$(TARGET_COPY_OUT_VENDOR)/etc/media_codecs.xml \ + device/generic/goldfish/camera/media_codecs_performance.xml:$(TARGET_COPY_OUT_VENDOR)/etc/media_codecs_performance.xml \ + device/generic/goldfish/camera/media_codecs_performance_c2.xml:$(TARGET_COPY_OUT_VENDOR)/etc/media_codecs_performance_c2.xml \ + frameworks/native/data/etc/android.hardware.touchscreen.multitouch.jazzhand.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.touchscreen.multitouch.jazzhand.xml \ + frameworks/native/data/etc/android.hardware.camera.ar.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.camera.ar.xml \ + frameworks/native/data/etc/android.hardware.camera.flash-autofocus.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.camera.flash-autofocus.xml \ + frameworks/native/data/etc/android.hardware.camera.concurrent.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.camera.concurrent.xml \ + frameworks/native/data/etc/android.hardware.camera.front.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.camera.front.xml \ + frameworks/native/data/etc/android.hardware.camera.full.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.camera.full.xml \ + frameworks/native/data/etc/android.hardware.camera.raw.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.camera.raw.xml \ + frameworks/native/data/etc/android.hardware.fingerprint.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.fingerprint.xml \ + frameworks/native/data/etc/android.hardware.vulkan.level-1.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.vulkan.level.xml \ + frameworks/native/data/etc/android.hardware.vulkan.compute-0.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.vulkan.compute.xml \ + frameworks/native/data/etc/android.hardware.vulkan.version-1_1.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.vulkan.version.xml \ + frameworks/native/data/etc/android.software.vulkan.deqp.level-2020-03-01.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.software.vulkan.deqp.level.xml \ + frameworks/native/data/etc/android.software.opengles.deqp.level-2020-03-01.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.software.opengles.deqp.level.xml \ + frameworks/native/data/etc/android.software.autofill.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.software.autofill.xml \ + frameworks/native/data/etc/android.software.verified_boot.xml:${TARGET_COPY_OUT_PRODUCT}/etc/permissions/android.software.verified_boot.xml \ + device/generic/goldfish/data/etc/permissions/privapp-permissions-goldfish.xml:$(TARGET_COPY_OUT_PRODUCT)/etc/permissions/privapp-permissions-goldfish.xml \ + hardware/google/camera/devices/EmulatedCamera/hwl/configs/emu_camera_back.json:$(TARGET_COPY_OUT_VENDOR)/etc/config/emu_camera_back.json \ + hardware/google/camera/devices/EmulatedCamera/hwl/configs/emu_camera_front.json:$(TARGET_COPY_OUT_VENDOR)/etc/config/emu_camera_front.json \ + hardware/google/camera/devices/EmulatedCamera/hwl/configs/emu_camera_depth.json:$(TARGET_COPY_OUT_VENDOR)/etc/config/emu_camera_depth.json \ diff --git a/64bitonly/product/x86_64-vendor.mk b/64bitonly/product/x86_64-vendor.mk new file mode 100644 index 00000000..f130b0ad --- /dev/null +++ b/64bitonly/product/x86_64-vendor.mk @@ -0,0 +1,64 @@ +include device/generic/goldfish/x86_64-kernel.mk + +PRODUCT_PROPERTY_OVERRIDES += \ + vendor.rild.libpath=/vendor/lib64/libgoldfish-ril.so + +# This is a build configuration for a full-featured build of the +# Open-Source part of the tree. It's geared toward a US-centric +# build quite specifically for the emulator, and might not be +# entirely appropriate to inherit from for on-device configurations. +PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/etc/config.ini.xl:config.ini \ + device/generic/goldfish/data/etc/advancedFeatures.ini:advancedFeatures.ini \ + device/generic/goldfish/data/etc/encryptionkey.img:encryptionkey.img \ + device/generic/goldfish/task_profiles.json:$(TARGET_COPY_OUT_VENDOR)/etc/task_profiles.json \ + $(EMULATOR_KERNEL_FILE):kernel-ranchu + +PRODUCT_SDK_ADDON_COPY_FILES += \ + device/generic/goldfish/data/etc/advancedFeatures.ini:images/x86_64/advancedFeatures.ini \ + device/generic/goldfish/data/etc/encryptionkey.img:images/x86_64/encryptionkey.img \ + $(EMULATOR_KERNEL_FILE):images/x86_64/kernel-ranchu + +PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/etc/configs/gpu.config:data/misc/gceconfigs/gpu.config + +PRODUCT_PACKAGES += \ + emulatorip + +PRODUCT_PROPERTY_OVERRIDES += \ + ro.crypto.dm_default_key.options_format.version=2 + +PRODUCT_SHIPPING_API_LEVEL := 31 +PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS := false +TARGET_USES_MKE2FS := true + +PRODUCT_PROPERTY_OVERRIDES += \ + debug.stagefright.ccodec=4 + +ifeq ($(QEMU_DISABLE_AVB),true) + ifeq ($(QEMU_USE_SYSTEM_EXT_PARTITIONS),true) + PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/etc/dummy.vbmeta.img:$(PRODUCT_OUT)/vbmeta.img \ + device/generic/goldfish/fstab.ranchu.initrd.noavb.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.initrd.noavb.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.noavb.ex:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu + else + PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/etc/dummy.vbmeta.img:$(PRODUCT_OUT)/vbmeta.img \ + device/generic/goldfish/fstab.ranchu.initrd.noavb:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.initrd.noavb:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.noavb:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu + endif +endif + +ifeq ($(QEMU_USE_SYSTEM_EXT_PARTITIONS),true) +PRODUCT_COPY_FILES += \ + device/generic/goldfish/fstab.ranchu.initrd.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.initrd.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.ex:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu +else +PRODUCT_COPY_FILES += \ + device/generic/goldfish/fstab.ranchu.initrd:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu.initrd:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ + device/generic/goldfish/fstab.ranchu:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu +endif @@ -19,3 +19,34 @@ soong_namespace { "device/generic/goldfish-opengl", ], } + +package { + default_applicable_licenses: ["device_generic_goldfish_license"], +} + +// Added automatically by a large-scale-change that took the approach of +// 'apply every license found to every target'. While this makes sure we respect +// every license restriction, it may not be entirely correct. +// +// e.g. GPL in an MIT project might only apply to the contrib/ directory. +// +// Please consider splitting the single license below into multiple licenses, +// taking care not to lose any license_kind information, and overriding the +// default license using the 'licenses: [...]' property on targets as needed. +// +// For unused files, consider creating a 'fileGroup' with "//visibility:private" +// to attach the license to, and including a comment whether the files may be +// used in the current project. +// +// large-scale-change filtered out the below license kinds as false-positives: +// SPDX-license-identifier-GPL-2.0 +// See: http://go/android-license-faq +license { + name: "device_generic_goldfish_license", + visibility: [":__subpackages__"], + license_kinds: [ + "SPDX-license-identifier-Apache-2.0", + "SPDX-license-identifier-BSD", + ], + // large-scale-change unable to identify any license_text files +} @@ -19,6 +19,7 @@ LOCAL_PATH := $(call my-dir) ifeq ($(BUILD_QEMU_IMAGES),true) QEMU_CUSTOMIZATIONS := true endif + ifeq ($(QEMU_CUSTOMIZATIONS),true) INSTALLED_EMULATOR_INFO_TXT_TARGET := $(PRODUCT_OUT)/emulator-info.txt emulator_info_txt := $(wildcard ${LOCAL_PATH}/emulator-info.txt) @@ -32,4 +33,6 @@ ifeq ($(QEMU_CUSTOMIZATIONS),true) subdir_makefiles=$(call first-makefiles-under,$(LOCAL_PATH)) $(foreach mk,$(subdir_makefiles),$(info including $(mk) ...)$(eval include $(mk))) + + include device/generic/goldfish/tasks/emu_img_zip.mk endif diff --git a/AndroidProducts.mk b/AndroidProducts.mk index 364f4ed7..a4ff006a 100644 --- a/AndroidProducts.mk +++ b/AndroidProducts.mk @@ -1,3 +1,6 @@ PRODUCT_MAKEFILES := \ $(LOCAL_DIR)/sdk_phone_x86_vendor.mk \ - $(LOCAL_DIR)/fvp.mk + $(LOCAL_DIR)/64bitonly/product/sdk_phone64_x86_64.mk \ + $(LOCAL_DIR)/64bitonly/product/sdk_phone64_arm64.mk \ + $(LOCAL_DIR)/fvp.mk \ + $(LOCAL_DIR)/fvp_mini.mk diff --git a/METADATA b/METADATA new file mode 100644 index 00000000..d97975ca --- /dev/null +++ b/METADATA @@ -0,0 +1,3 @@ +third_party { + license_type: NOTICE +} diff --git a/MultiDisplayProvider/Android.bp b/MultiDisplayProvider/Android.bp index b0bd4387..4ae51515 100644 --- a/MultiDisplayProvider/Android.bp +++ b/MultiDisplayProvider/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + android_app { name: "MultiDisplayProvider", diff --git a/MultiDisplayProvider/AndroidManifest.xml b/MultiDisplayProvider/AndroidManifest.xml index 591b189a..3b3b1e34 100644 --- a/MultiDisplayProvider/AndroidManifest.xml +++ b/MultiDisplayProvider/AndroidManifest.xml @@ -23,15 +23,16 @@ <uses-sdk android:minSdkVersion="19" /> <application android:label="@string/app_name" android:persistent="true"> - <receiver android:name=".MultiDisplayServiceReceiver" > + <receiver android:name=".MultiDisplayServiceReceiver" + android:exported="true"> <intent-filter> <action android:name="com.android.emulator.multidisplay.START" /> </intent-filter> </receiver> <service android:name=".MultiDisplayService" - android:label="@string/app_name" - android:exported="true"> + android:label="@string/app_name" + android:exported="true"> </service> </application> diff --git a/MultiDisplayProvider/jni/Android.bp b/MultiDisplayProvider/jni/Android.bp index 474377b2..aceac6da 100644 --- a/MultiDisplayProvider/jni/Android.bp +++ b/MultiDisplayProvider/jni/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_shared { name: "libemulator_multidisplay_jni", diff --git a/MultiDisplayProvider/jni/com_android_emulator_multidisplay.cpp b/MultiDisplayProvider/jni/com_android_emulator_multidisplay.cpp index 61aac843..10e92828 100644 --- a/MultiDisplayProvider/jni/com_android_emulator_multidisplay.cpp +++ b/MultiDisplayProvider/jni/com_android_emulator_multidisplay.cpp @@ -21,7 +21,6 @@ #include <gui/Surface.h> #include <gui/ISurfaceComposer.h> #include <gui/SurfaceComposerClient.h> -#include <ui/DisplayInfo.h> #include <sys/epoll.h> diff --git a/MultiDisplayProvider/src/com/android/emulator/multidisplay/MultiDisplayService.java b/MultiDisplayProvider/src/com/android/emulator/multidisplay/MultiDisplayService.java index 49d5611c..9d3c1f5b 100644 --- a/MultiDisplayProvider/src/com/android/emulator/multidisplay/MultiDisplayService.java +++ b/MultiDisplayProvider/src/com/android/emulator/multidisplay/MultiDisplayService.java @@ -43,6 +43,7 @@ public class MultiDisplayService extends Service { private static final int mFlags = DisplayManager.VIRTUAL_DISPLAY_FLAG_PUBLIC | DisplayManager.VIRTUAL_DISPLAY_FLAG_OWN_CONTENT_ONLY | DisplayManager.VIRTUAL_DISPLAY_FLAG_ROTATES_WITH_CONTENT | + DisplayManager.VIRTUAL_DISPLAY_FLAG_TRUSTED | 1 << 6 |//DisplayManager.VIRTUAL_DISPLAY_FLAG_SUPPORTS_TOUCH 1 << 9; //DisplayManager.VIRTUAL_DISPLAY_FLAG_SHOULD_SHOW_SYSTEM_DECORATIONS; private DisplayManager mDisplayManager; @@ -2,3 +2,4 @@ bohu@google.com rkir@google.com lfy@google.com huans@google.com +pcc@google.com diff --git a/arm64-kernel.mk b/arm64-kernel.mk new file mode 100644 index 00000000..261715cb --- /dev/null +++ b/arm64-kernel.mk @@ -0,0 +1,12 @@ +TARGET_KERNEL_USE ?= 5.10 + +KERNEL_MODULES_PATH := kernel/prebuilts/common-modules/virtual-device/$(TARGET_KERNEL_USE)/arm64 + +KERNEL_MODULES_EXCLUDE := \ + $(KERNEL_MODULES_PATH)/virt_wifi.ko \ + $(KERNEL_MODULES_PATH)/virt_wifi_sim.ko + +BOARD_VENDOR_RAMDISK_KERNEL_MODULES += \ + $(filter-out $(KERNEL_MODULES_EXCLUDE), $(wildcard $(KERNEL_MODULES_PATH)/*.ko)) + +EMULATOR_KERNEL_FILE := kernel/prebuilts/$(TARGET_KERNEL_USE)/arm64/kernel-$(TARGET_KERNEL_USE)-gz diff --git a/arm64-vendor.mk b/arm64-vendor.mk index d8f54e93..c45cc6da 100644 --- a/arm64-vendor.mk +++ b/arm64-vendor.mk @@ -1,10 +1,18 @@ -PRODUCT_KERNEL_VERSION := 5.4 -BOARD_VENDOR_RAMDISK_KERNEL_MODULES += \ - $(wildcard prebuilts/qemu-kernel/arm64/$(PRODUCT_KERNEL_VERSION)/ko/*.ko) +include device/generic/goldfish/arm64-kernel.mk PRODUCT_PROPERTY_OVERRIDES += \ vendor.rild.libpath=/vendor/lib64/libgoldfish-ril.so +PRODUCT_PACKAGES += \ + emulatorip + +PRODUCT_PROPERTY_OVERRIDES += \ + ro.crypto.dm_default_key.options_format.version=2 + +PRODUCT_SHIPPING_API_LEVEL := 31 +PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS := false +TARGET_USES_MKE2FS := true + # Note: the following lines need to stay at the beginning so that it can # take priority and override the rules it inherit from other mk files # see copy file rules in core/Makefile @@ -12,17 +20,21 @@ ifeq ($(QEMU_USE_SYSTEM_EXT_PARTITIONS),true) PRODUCT_COPY_FILES += \ device/generic/goldfish/fstab.ranchu.initrd.arm.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ device/generic/goldfish/fstab.ranchu.initrd.arm.ex:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ - device/generic/goldfish/fstab.ranchu.arm.ex:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu + device/generic/goldfish/fstab.ranchu.arm.ex:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu \ + device/generic/goldfish/data/etc/encryptionkey.img:encryptionkey.img \ + device/generic/goldfish/task_profiles.json:$(TARGET_COPY_OUT_VENDOR)/etc/task_profiles.json else PRODUCT_COPY_FILES += \ device/generic/goldfish/fstab.ranchu.initrd.arm:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.ranchu \ device/generic/goldfish/fstab.ranchu.initrd.arm:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/fstab.ranchu \ - device/generic/goldfish/fstab.ranchu.arm:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu + device/generic/goldfish/fstab.ranchu.arm:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu \ + device/generic/goldfish/data/etc/encryptionkey.img:encryptionkey.img \ + device/generic/goldfish/task_profiles.json:$(TARGET_COPY_OUT_VENDOR)/etc/task_profiles.json endif PRODUCT_COPY_FILES += \ - prebuilts/qemu-kernel/arm64/$(PRODUCT_KERNEL_VERSION)/kernel-qemu2:kernel-ranchu \ + $(EMULATOR_KERNEL_FILE):kernel-ranchu \ device/generic/goldfish/data/etc/advancedFeatures.ini.arm:advancedFeatures.ini \ EMULATOR_VENDOR_NO_GNSS := true diff --git a/audio/Android.bp b/audio/Android.bp index 27dfbf8e..e7c8f764 100644 --- a/audio/Android.bp +++ b/audio/Android.bp @@ -13,10 +13,33 @@ // See the License for the specific language governing permissions and // limitations under the License. -cc_binary { - name: "android.hardware.audio.service.ranchu", +package { + default_applicable_licenses: ["device_generic_goldfish_audio_license"], +} + +// Added automatically by a large-scale-change +// See: http://go/android-license-faq +license { + name: "device_generic_goldfish_audio_license", + visibility: [":__subpackages__"], + license_kinds: [ + "SPDX-license-identifier-Apache-2.0", + ], + license_text: [ + "NOTICE", + ], +} + +cc_library_shared { + name: "android.hardware.audio.legacy@6.0-impl.ranchu", + defaults: ["android.hardware.audio@6.0-impl_default"], + relative_install_path: "hw", + vendor: true, +} + +cc_library_shared { + name: "android.hardware.audio@6.0-impl.ranchu", vendor: true, - init_rc: ["android.hardware.audio.service.ranchu.rc"], vintf_fragments: ["android.hardware.audio@6.0-impl.ranchu.xml"], relative_install_path: "hw", defaults: ["hidl_defaults"], @@ -31,6 +54,8 @@ cc_binary { "device_port_source.cpp", "device_port_sink.cpp", "talsa.cpp", + "ring_buffer.cpp", + "audio_ops.cpp", "util.cpp", ], shared_libs: [ @@ -39,7 +64,6 @@ cc_binary { "android.hardware.audio.common@6.0-util", "libaudioutils", "libbase", - "libbinder", "libcutils", "libhidlbase", "liblog", @@ -52,13 +76,13 @@ cc_binary { "libaudio_system_headers", ], cflags: [ - "-DLOG_TAG=\"android.hardware.audio.service.ranchu\"", + "-DLOG_TAG=\"android.hardware.audio@6.0-impl.ranchu\"", ], - // android.hardware.audio.service.ranchu loads android.hardware.audio@6.0-impl + // a.h.audio@6.0-impl.ranchu (see above) loads a.h.audio.legacy@6.0-impl // which loads audio.r_submix.default which provides the r_submix device, // see b/161485545. Should be retired once a better r_submix is available. required: [ - "android.hardware.audio@6.0-impl", + "android.hardware.audio.legacy@6.0-impl.ranchu", "audio.r_submix.default", ], } diff --git a/audio/android.hardware.audio.service.ranchu.rc b/audio/android.hardware.audio.service.ranchu.rc deleted file mode 100644 index 777c2297..00000000 --- a/audio/android.hardware.audio.service.ranchu.rc +++ /dev/null @@ -1,9 +0,0 @@ -service vendor.audio-hal /vendor/bin/hw/android.hardware.audio.service.ranchu - class hal - user audioserver - # media gid needed for /dev/fm (radio) and for /data/misc/media (tee) - group audio camera drmrpc inet media mediadrm net_bt net_bt_admin net_bw_acct wakelock context_hub - capabilities BLOCK_SUSPEND - ioprio rt 4 - task_profiles ProcessCapacityHigh HighPerformance - onrestart restart audioserver diff --git a/audio/audio_ops.cpp b/audio/audio_ops.cpp new file mode 100644 index 00000000..088c9349 --- /dev/null +++ b/audio/audio_ops.cpp @@ -0,0 +1,79 @@ +/* + * Copyright (C) 2020 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. + */ + +#include <string.h> +#include <math.h> +#include "audio_ops.h" + +namespace android { +namespace hardware { +namespace audio { +namespace V6_0 { +namespace implementation { +namespace aops { + +void multiplyByVolume(const float volume, int16_t *a, const size_t n) { + constexpr int_fast32_t kDenominator = 32768; + const int_fast32_t numerator = + static_cast<int_fast32_t>(round(volume * kDenominator)); + + if (numerator >= kDenominator) { + return; // (numerator > kDenominator) is not expected + } else if (numerator <= 0) { + memset(a, 0, n * sizeof(*a)); + return; // (numerator < 0) is not expected + } + + int16_t *end = a + n; + + // The unroll code below is to save on CPU branch instructions. + // 8 is arbitrary chosen. + +#define STEP \ + *a = (*a * numerator + kDenominator / 2) / kDenominator; \ + ++a + + switch (n % 8) { + case 7: goto l7; + case 6: goto l6; + case 5: goto l5; + case 4: goto l4; + case 3: goto l3; + case 2: goto l2; + case 1: goto l1; + default: break; + } + + while (a < end) { + STEP; +l7: STEP; +l6: STEP; +l5: STEP; +l4: STEP; +l3: STEP; +l2: STEP; +l1: STEP; + } + +#undef STEP +} + +} // namespace aops +} // namespace implementation +} // namespace V6_0 +} // namespace audio +} // namespace hardware +} // namespace android diff --git a/audio/audio_ops.h b/audio/audio_ops.h new file mode 100644 index 00000000..3822a139 --- /dev/null +++ b/audio/audio_ops.h @@ -0,0 +1,34 @@ +/* + * Copyright (C) 2020 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. + */ + +#pragma once +#include <stdint.h> + +namespace android { +namespace hardware { +namespace audio { +namespace V6_0 { +namespace implementation { +namespace aops { + +void multiplyByVolume(float volume, int16_t *a, size_t n); + +} // namespace aops +} // namespace implementation +} // namespace V6_0 +} // namespace audio +} // namespace hardware +} // namespace android diff --git a/audio/device_factory.cpp b/audio/device_factory.cpp index 32a9a04a..d399b5ba 100644 --- a/audio/device_factory.cpp +++ b/audio/device_factory.cpp @@ -36,7 +36,7 @@ using ::android::hardware::Void; DevicesFactory::DevicesFactory() { mLegacyLib.reset(dlopen( - LIB_PATH_PREFIX "android.hardware.audio@6.0-impl.so", RTLD_NOW)); + LIB_PATH_PREFIX "android.hardware.audio.legacy@6.0-impl.ranchu.so", RTLD_NOW)); LOG_ALWAYS_FATAL_IF(!mLegacyLib); typedef IDevicesFactory *(*Func)(const char *); diff --git a/audio/device_port_sink.cpp b/audio/device_port_sink.cpp index 0a34eb21..3c4de41c 100644 --- a/audio/device_port_sink.cpp +++ b/audio/device_port_sink.cpp @@ -14,10 +14,15 @@ * limitations under the License. */ +#include <chrono> +#include <thread> #include <log/log.h> #include <utils/Timers.h> +#include <utils/ThreadDefs.h> #include "device_port_sink.h" #include "talsa.h" +#include "audio_ops.h" +#include "ring_buffer.h" #include "util.h" #include "debug.h" @@ -29,50 +34,179 @@ namespace implementation { namespace { +constexpr int kMaxJitterUs = 3000; // Enforced by CTS, should be <= 6ms + struct TinyalsaSink : public DevicePortSink { TinyalsaSink(unsigned pcmCard, unsigned pcmDevice, - const AudioConfig &cfg, uint64_t &frames) - : mFrames(frames) + const AudioConfig &cfg, + uint64_t &frames) + : mStartNs(systemTime(SYSTEM_TIME_MONOTONIC)) + , mSampleRateHz(cfg.sampleRateHz) + , mFrameSize(util::countChannels(cfg.channelMask) * sizeof(int16_t)) + , mWriteSizeFrames(cfg.frameCount) + , mFrames(frames) + , mRingBuffer(mFrameSize * cfg.frameCount * 3) + , mMixer(pcmCard) , mPcm(talsa::pcmOpen(pcmCard, pcmDevice, util::countChannels(cfg.channelMask), cfg.sampleRateHz, cfg.frameCount, - true /* isOut */)) {} + true /* isOut */)) { + mConsumeThread = std::thread(&TinyalsaSink::consumeThread, this); + } + + ~TinyalsaSink() { + mConsumeThreadRunning = false; + mConsumeThread.join(); + } Result getPresentationPosition(uint64_t &frames, TimeSpec &ts) override { + const nsecs_t nowNs = systemTime(SYSTEM_TIME_MONOTONIC); + const uint64_t nowFrames = getPresentationFrames(nowNs); + mFrames += (nowFrames - mPreviousFrames); + mPreviousFrames = nowFrames; + frames = mFrames; - ts = util::nsecs2TimeSpec(systemTime(SYSTEM_TIME_MONOTONIC)); + ts = util::nsecs2TimeSpec(nowNs); return Result::OK; } - int write(const void *data, size_t nBytes) override { - const int res = ::pcm_write(mPcm.get(), data, nBytes); - if (res < 0) { - return FAILURE(res); - } else if (res == 0) { - mFrames += ::pcm_bytes_to_frames(mPcm.get(), nBytes); - return nBytes; - } else { - mFrames += ::pcm_bytes_to_frames(mPcm.get(), res); - return res; + uint64_t getPresentationFrames(const nsecs_t nowNs) const { + return uint64_t(mSampleRateHz) * ns2us(nowNs - mStartNs) / 1000000; + } + + uint64_t getAvailableFrames(const nsecs_t nowNs) const { + return getPresentationFrames(nowNs) - mReceivedFrames; + } + + uint64_t getAvailableFramesNow() const { + return getAvailableFrames(systemTime(SYSTEM_TIME_MONOTONIC)); + } + + size_t getWaitFramesNow(const size_t requestedFrames) const { + const size_t availableFrames = getAvailableFramesNow(); + return (requestedFrames > availableFrames) + ? (requestedFrames - availableFrames) : 0; + } + + size_t write(float volume, size_t bytesToWrite, IReader &reader) { + size_t framesLost = 0; + const size_t waitFrames = getWaitFramesNow(bytesToWrite / mFrameSize); + const auto blockUntil = + std::chrono::high_resolution_clock::now() + + + std::chrono::microseconds(waitFrames * 1000000 / mSampleRateHz); + + while (bytesToWrite > 0) { + if (mRingBuffer.waitForProduceAvailable(blockUntil + + std::chrono::microseconds(kMaxJitterUs))) { + auto produceChunk = mRingBuffer.getProduceChunk(); + if (produceChunk.size >= bytesToWrite) { + // Since the ring buffer has more bytes free than we need, + // make sure we are not too early here: tinyalsa is jittery, + // we don't want to go faster than SYSTEM_TIME_MONOTONIC + std::this_thread::sleep_until(blockUntil); + } + + const size_t szFrames = + std::min(produceChunk.size, bytesToWrite) / mFrameSize; + const size_t szBytes = szFrames * mFrameSize; + LOG_ALWAYS_FATAL_IF(reader(produceChunk.data, szBytes) < szBytes); + + aops::multiplyByVolume(volume, + static_cast<int16_t *>(produceChunk.data), + szBytes / sizeof(int16_t)); + + LOG_ALWAYS_FATAL_IF(mRingBuffer.produce(szBytes) < szBytes); + mReceivedFrames += szFrames; + bytesToWrite -= szBytes; + } else { + ALOGV("TinyalsaSink::%s:%d pcm_write was late reading " + "frames, dropping %zu us of audio", + __func__, __LINE__, + size_t(1000000 * bytesToWrite / mFrameSize / mSampleRateHz)); + + // drop old audio to make room for new + const size_t bytesLost = mRingBuffer.makeRoomForProduce(bytesToWrite); + framesLost += bytesLost / mFrameSize; + + while (bytesToWrite > 0) { + auto produceChunk = mRingBuffer.getProduceChunk(); + const size_t szFrames = + std::min(produceChunk.size, bytesToWrite) / mFrameSize; + const size_t szBytes = szFrames * mFrameSize; + LOG_ALWAYS_FATAL_IF(reader(produceChunk.data, szBytes) < szBytes); + + aops::multiplyByVolume(volume, + static_cast<int16_t *>(produceChunk.data), + szBytes / sizeof(int16_t)); + + LOG_ALWAYS_FATAL_IF(mRingBuffer.produce(szBytes) < szBytes); + mReceivedFrames += szFrames; + bytesToWrite -= szBytes; + } + break; + } + } + + return framesLost; + } + + void consumeThread() { + util::setThreadPriority(PRIORITY_URGENT_AUDIO); + std::vector<uint8_t> writeBuffer(mWriteSizeFrames * mFrameSize); + + while (mConsumeThreadRunning) { + if (mRingBuffer.waitForConsumeAvailable( + std::chrono::high_resolution_clock::now() + + std::chrono::microseconds(100000))) { + size_t szBytes; + { + auto chunk = mRingBuffer.getConsumeChunk(); + szBytes = std::min(writeBuffer.size(), chunk.size); + // We have to memcpy because the consumer holds the lock + // into RingBuffer and pcm_write takes too long to hold + // this lock. + memcpy(writeBuffer.data(), chunk.data, szBytes); + LOG_ALWAYS_FATAL_IF(mRingBuffer.consume(chunk, szBytes) < szBytes); + } + + int res = ::pcm_write(mPcm.get(), writeBuffer.data(), szBytes); + if (res < 0) { + ALOGW("TinyalsaSink::%s:%d pcm_write failed with res=%d", + __func__, __LINE__, res); + } + } } } static std::unique_ptr<TinyalsaSink> create(unsigned pcmCard, unsigned pcmDevice, const AudioConfig &cfg, + size_t readerBufferSizeHint, uint64_t &frames) { - auto src = std::make_unique<TinyalsaSink>(pcmCard, pcmDevice, cfg, frames); - if (src->mPcm) { - return src; + (void)readerBufferSizeHint; + auto sink = std::make_unique<TinyalsaSink>(pcmCard, pcmDevice, + cfg, frames); + if (sink->mMixer && sink->mPcm) { + return sink; } else { return FAILURE(nullptr); } } private: + const nsecs_t mStartNs; + const unsigned mSampleRateHz; + const unsigned mFrameSize; + const unsigned mWriteSizeFrames; uint64_t &mFrames; + uint64_t mPreviousFrames = 0; + uint64_t mReceivedFrames = 0; + RingBuffer mRingBuffer; + talsa::Mixer mMixer; talsa::PcmPtr mPcm; + std::thread mConsumeThread; + std::atomic<bool> mConsumeThreadRunning = true; }; struct NullSink : public DevicePortSink { @@ -89,10 +223,20 @@ struct NullSink : public DevicePortSink { return Result::OK; } - int write(const void *, size_t nBytes) override { - simulatePresentationPosition(); - mAvailableFrames += nBytes / mNChannels / sizeof(int16_t); - return nBytes; + size_t write(float volume, size_t bytesToWrite, IReader &reader) override { + (void)volume; + + while (bytesToWrite > 0) { + size_t chunkSize = std::min(bytesToWrite, sizeof(mWriteBuffer)); + chunkSize = reader(mWriteBuffer, chunkSize); + if (chunkSize > 0) { + bytesToWrite -= chunkSize; + } else { + break; // reader failed + } + } + + return 0; } void simulatePresentationPosition() { @@ -111,7 +255,9 @@ struct NullSink : public DevicePortSink { } static std::unique_ptr<NullSink> create(const AudioConfig &cfg, + size_t readerBufferSizeHint, uint64_t &frames) { + (void)readerBufferSizeHint; return std::make_unique<NullSink>(cfg, frames); } @@ -121,12 +267,14 @@ private: const unsigned mNChannels; uint64_t mAvailableFrames = 0; nsecs_t mTimestamp; + char mWriteBuffer[1024]; }; } // namespace std::unique_ptr<DevicePortSink> -DevicePortSink::create(const DeviceAddress &address, +DevicePortSink::create(size_t readerBufferSizeHint, + const DeviceAddress &address, const AudioConfig &cfg, const hidl_bitfield<AudioOutputFlag> &flags, uint64_t &frames) { @@ -139,15 +287,22 @@ DevicePortSink::create(const DeviceAddress &address, switch (address.device) { case AudioDevice::OUT_SPEAKER: - return TinyalsaSink::create(talsa::kPcmCard, talsa::kPcmDevice, - cfg, frames); + { + auto sinkptr = TinyalsaSink::create(talsa::kPcmCard, talsa::kPcmDevice, cfg, readerBufferSizeHint, frames); + if (sinkptr == nullptr) { + ALOGW("%s:%d failed to create alsa sink; created nullsink instead.", __func__, __LINE__); + return NullSink::create(cfg, readerBufferSizeHint, frames); + } else { + return sinkptr; + } + } case AudioDevice::OUT_TELEPHONY_TX: - return NullSink::create(cfg, frames); + return NullSink::create(cfg, readerBufferSizeHint, frames); default: - ALOGE("%s:%d unsupported device: %x", __func__, __LINE__, address.device); - return FAILURE(nullptr); + ALOGW("%s:%d unsupported device: %x created nullsink", __func__, __LINE__, address.device); + return NullSink::create(cfg, readerBufferSizeHint, frames); } } diff --git a/audio/device_port_sink.h b/audio/device_port_sink.h index 5714cd06..5159b509 100644 --- a/audio/device_port_sink.h +++ b/audio/device_port_sink.h @@ -18,6 +18,7 @@ #include <memory> #include <android/hardware/audio/common/6.0/types.h> #include <android/hardware/audio/6.0/types.h> +#include "ireader.h" namespace android { namespace hardware { @@ -31,9 +32,10 @@ using namespace ::android::hardware::audio::V6_0; struct DevicePortSink { virtual ~DevicePortSink() {} virtual Result getPresentationPosition(uint64_t &frames, TimeSpec &ts) = 0; - virtual int write(const void *data, size_t nBytes) = 0; + virtual size_t write(float volume, size_t bytesToWrite, IReader &) = 0; - static std::unique_ptr<DevicePortSink> create(const DeviceAddress &, + static std::unique_ptr<DevicePortSink> create(size_t readerBufferSizeHint, + const DeviceAddress &, const AudioConfig &, const hidl_bitfield<AudioOutputFlag> &, uint64_t &frames); diff --git a/audio/device_port_source.cpp b/audio/device_port_source.cpp index a82d281f..3bdb766a 100644 --- a/audio/device_port_source.cpp +++ b/audio/device_port_source.cpp @@ -17,12 +17,16 @@ #include <cmath> #include <chrono> #include <thread> +#include <unistd.h> #include <audio_utils/channels.h> #include <audio_utils/format.h> #include <log/log.h> +#include <utils/ThreadDefs.h> #include <utils/Timers.h> #include "device_port_source.h" #include "talsa.h" +#include "ring_buffer.h" +#include "audio_ops.h" #include "util.h" #include "debug.h" @@ -34,41 +38,156 @@ namespace implementation { namespace { +constexpr int kMaxJitterUs = 3000; // Enforced by CTS, should be <= 6ms + struct TinyalsaSource : public DevicePortSource { TinyalsaSource(unsigned pcmCard, unsigned pcmDevice, const AudioConfig &cfg, uint64_t &frames) - : mFrames(frames) + : mStartNs(systemTime(SYSTEM_TIME_MONOTONIC)) + , mSampleRateHz(cfg.sampleRateHz) + , mFrameSize(util::countChannels(cfg.channelMask) * sizeof(int16_t)) + , mReadSizeFrames(cfg.frameCount) + , mFrames(frames) + , mRingBuffer(mFrameSize * cfg.frameCount * 3) + , mMixer(pcmCard) , mPcm(talsa::pcmOpen(pcmCard, pcmDevice, util::countChannels(cfg.channelMask), cfg.sampleRateHz, cfg.frameCount, - false /* isOut */)) {} + false /* isOut */)) { + mProduceThread = std::thread(&TinyalsaSource::producerThread, this); + } + + ~TinyalsaSource() { + mProduceThreadRunning = false; + mProduceThread.join(); + } Result getCapturePosition(uint64_t &frames, uint64_t &time) override { + const nsecs_t nowNs = systemTime(SYSTEM_TIME_MONOTONIC); + const uint64_t nowFrames = getCaptureFrames(nowNs); + mFrames += (nowFrames - mPreviousFrames); + mPreviousFrames = nowFrames; + frames = mFrames; - time = systemTime(SYSTEM_TIME_MONOTONIC); + time = nowNs; return Result::OK; } - int read(void *data, size_t toReadBytes) override { - const int res = ::pcm_read(mPcm.get(), data, toReadBytes); + uint64_t getCaptureFrames(const nsecs_t nowNs) const { + return uint64_t(mSampleRateHz) * ns2us(nowNs - mStartNs) / 1000000; + } + + uint64_t getAvailableFrames(const nsecs_t nowNs) const { + return getCaptureFrames(nowNs) - mSentFrames; + } + + uint64_t getAvailableFramesNow() const { + return getAvailableFrames(systemTime(SYSTEM_TIME_MONOTONIC)); + } + + size_t getWaitFramesNow(const size_t requestedFrames) const { + const size_t availableFrames = getAvailableFramesNow(); + return (requestedFrames > availableFrames) + ? (requestedFrames - availableFrames) : 0; + } + + size_t read(float volume, size_t bytesToRead, IWriter &writer) override { + const size_t waitFrames = getWaitFramesNow(bytesToRead / mFrameSize); + const auto blockUntil = + std::chrono::high_resolution_clock::now() + + + std::chrono::microseconds(waitFrames * 1000000 / mSampleRateHz); + + while (bytesToRead > 0) { + if (mRingBuffer.waitForConsumeAvailable(blockUntil + + std::chrono::microseconds(kMaxJitterUs))) { + if (mRingBuffer.availableToConsume() >= bytesToRead) { + // Since the ring buffer has all bytes we need, make sure we + // are not too early here: tinyalsa is jittery, we don't + // want to go faster than SYSTEM_TIME_MONOTONIC + std::this_thread::sleep_until(blockUntil); + } + + auto chunk = mRingBuffer.getConsumeChunk(); + const size_t writeBufSzBytes = std::min(chunk.size, bytesToRead); + + aops::multiplyByVolume(volume, + static_cast<int16_t *>(chunk.data), + writeBufSzBytes / sizeof(int16_t)); + + writer(chunk.data, writeBufSzBytes); + LOG_ALWAYS_FATAL_IF(mRingBuffer.consume(chunk, writeBufSzBytes) < writeBufSzBytes); + + bytesToRead -= writeBufSzBytes; + mSentFrames += writeBufSzBytes / mFrameSize; + } else { + ALOGW("TinyalsaSource::%s:%d pcm_read was late delivering " + "frames, inserting %zu us of silence", + __func__, __LINE__, + size_t(1000000 * bytesToRead / mFrameSize / mSampleRateHz)); + + static const uint8_t zeroes[256] = {0}; + + while (bytesToRead > 0) { + const size_t nZeroFrames = + std::min(bytesToRead, sizeof(zeroes)) / mFrameSize; + const size_t nZeroBytes = nZeroFrames * mFrameSize; + + writer(zeroes, nZeroBytes); + mSentFrames += nZeroFrames; + bytesToRead -= nZeroBytes; + } + break; + } + } + + return mFramesLost.exchange(0); + } + + void producerThread() { + util::setThreadPriority(PRIORITY_URGENT_AUDIO); + std::vector<uint8_t> readBuf(mReadSizeFrames * mFrameSize); + + while (mProduceThreadRunning) { + const size_t bytesLost = mRingBuffer.makeRoomForProduce(readBuf.size()); + mFramesLost += bytesLost / mFrameSize; + + auto produceChunk = mRingBuffer.getProduceChunk(); + if (produceChunk.size < readBuf.size()) { + const size_t sz = doRead(readBuf.data(), readBuf.size()); + if (sz > 0) { + LOG_ALWAYS_FATAL_IF(mRingBuffer.produce(readBuf.data(), sz) < sz); + } + } else { + const size_t sz = doRead(produceChunk.data, readBuf.size()); + if (sz > 0) { + LOG_ALWAYS_FATAL_IF(mRingBuffer.produce(readBuf.size()) < sz); + } + } + } + } + + size_t doRead(void *dst, size_t sz) { + const int res = ::pcm_read(mPcm.get(), dst, sz); if (res < 0) { - return FAILURE(res); - } else if (res == 0) { - mFrames += ::pcm_bytes_to_frames(mPcm.get(), toReadBytes); - return toReadBytes; - } else { - mFrames += ::pcm_bytes_to_frames(mPcm.get(), res); - return res; + ALOGW("TinyalsaSource::%s:%d pcm_read failed with res=%d", + __func__, __LINE__, res); + return 0; } + + return sz; } static std::unique_ptr<TinyalsaSource> create(unsigned pcmCard, unsigned pcmDevice, const AudioConfig &cfg, + size_t writerBufferSizeHint, uint64_t &frames) { - auto src = std::make_unique<TinyalsaSource>(pcmCard, pcmDevice, cfg, frames); - if (src->mPcm) { + (void)writerBufferSizeHint; + + auto src = std::make_unique<TinyalsaSource>(pcmCard, pcmDevice, + cfg, frames); + if (src->mMixer && src->mPcm) { return src; } else { return FAILURE(nullptr); @@ -76,13 +195,28 @@ struct TinyalsaSource : public DevicePortSource { } private: + const nsecs_t mStartNs; + const unsigned mSampleRateHz; + const unsigned mFrameSize; + const unsigned mReadSizeFrames; uint64_t &mFrames; + uint64_t mPreviousFrames = 0; + uint64_t mSentFrames = 0; + std::atomic<uint32_t> mFramesLost = 0; + RingBuffer mRingBuffer; + talsa::Mixer mMixer; talsa::PcmPtr mPcm; + std::thread mProduceThread; + std::atomic<bool> mProduceThreadRunning = true; }; template <class G> struct GeneratedSource : public DevicePortSource { - GeneratedSource(const AudioConfig &cfg, uint64_t &frames, G generator) - : mFrames(frames) + GeneratedSource(const AudioConfig &cfg, + size_t writerBufferSizeHint, + uint64_t &frames, + G generator) + : mWriteBuffer(writerBufferSizeHint / sizeof(int16_t)) + , mFrames(frames) , mStartNs(systemTime(SYSTEM_TIME_MONOTONIC)) , mSampleRateHz(cfg.sampleRateHz) , mNChannels(util::countChannels(cfg.channelMask)) @@ -90,7 +224,7 @@ template <class G> struct GeneratedSource : public DevicePortSource { Result getCapturePosition(uint64_t &frames, uint64_t &time) override { const nsecs_t nowNs = systemTime(SYSTEM_TIME_MONOTONIC); - const uint64_t nowFrames = getNowFrames(nowNs); + const uint64_t nowFrames = getCaptureFrames(nowNs); mFrames += (nowFrames - mPreviousFrames); mPreviousFrames = nowFrames; frames = mFrames; @@ -98,19 +232,25 @@ template <class G> struct GeneratedSource : public DevicePortSource { return Result::OK; } - uint64_t getNowFrames(const nsecs_t nowNs) const { - return uint64_t(mSampleRateHz) * ns2ms(nowNs - mStartNs) / 1000; + uint64_t getCaptureFrames(const nsecs_t nowNs) const { + return uint64_t(mSampleRateHz) * ns2us(nowNs - mStartNs) / 1000000; } - int read(void *data, size_t toReadBytes) override { - int16_t *samples = static_cast<int16_t *>(data); + uint64_t getAvailableFrames(const nsecs_t nowNs) const { + return getCaptureFrames(nowNs) - mSentFrames; + } + + size_t read(float volume, size_t bytesToRead, IWriter &writer) override { + mWriteBuffer.resize(bytesToRead / sizeof(int16_t)); + + int16_t *samples = mWriteBuffer.data(); const unsigned nChannels = mNChannels; - const unsigned requestedFrames = toReadBytes / nChannels / sizeof(*samples); + const unsigned requestedFrames = bytesToRead / nChannels / sizeof(*samples); unsigned availableFrames; while (true) { const nsecs_t nowNs = systemTime(SYSTEM_TIME_MONOTONIC); - availableFrames = getNowFrames(nowNs) - mSentFrames; + availableFrames = getAvailableFrames(nowNs); if (availableFrames < requestedFrames / 2) { const unsigned neededMoreFrames = requestedFrames / 2 - availableFrames; @@ -128,12 +268,18 @@ template <class G> struct GeneratedSource : public DevicePortSource { adjust_channels(samples, 1, samples, nChannels, sizeof(*samples), sizeBytes); } - mSentFrames += nFrames; - return sizeBytes; + + aops::multiplyByVolume(volume, + mWriteBuffer.data(), + sizeBytes / sizeof(int16_t)); + + writer(mWriteBuffer.data(), sizeBytes); + return 0; } private: + std::vector<int16_t> mWriteBuffer; uint64_t &mFrames; const nsecs_t mStartNs; const unsigned mSampleRateHz; @@ -236,14 +382,21 @@ std::vector<float> generateSinePattern(uint32_t sampleRateHz, } template <class G> std::unique_ptr<GeneratedSource<G>> -createGeneratedSource(const AudioConfig &cfg, uint64_t &frames, G generator) { - return std::make_unique<GeneratedSource<G>>(cfg, frames, std::move(generator)); +createGeneratedSource(const AudioConfig &cfg, + size_t writerBufferSizeHint, + uint64_t &frames, + G generator) { + return std::make_unique<GeneratedSource<G>>(cfg, + writerBufferSizeHint, + frames, + std::move(generator)); } } // namespace std::unique_ptr<DevicePortSource> -DevicePortSource::create(const DeviceAddress &address, +DevicePortSource::create(size_t writerBufferSizeHint, + const DeviceAddress &address, const AudioConfig &cfg, const hidl_bitfield<AudioOutputFlag> &flags, uint64_t &frames) { @@ -257,15 +410,15 @@ DevicePortSource::create(const DeviceAddress &address, switch (address.device) { case AudioDevice::IN_BUILTIN_MIC: return TinyalsaSource::create(talsa::kPcmCard, talsa::kPcmDevice, - cfg, frames); + cfg, writerBufferSizeHint, frames); case AudioDevice::IN_TELEPHONY_RX: - return createGeneratedSource(cfg, frames, + return createGeneratedSource(cfg, writerBufferSizeHint, frames, BusySignalGenerator(cfg.sampleRateHz)); case AudioDevice::IN_FM_TUNER: return createGeneratedSource( - cfg, frames, + cfg, writerBufferSizeHint, frames, RepeatGenerator(generateSinePattern(cfg.sampleRateHz, 440.0, 1.0))); default: diff --git a/audio/device_port_source.h b/audio/device_port_source.h index 3cc39ffe..16b5d27c 100644 --- a/audio/device_port_source.h +++ b/audio/device_port_source.h @@ -18,6 +18,7 @@ #include <memory> #include <android/hardware/audio/common/6.0/types.h> #include <android/hardware/audio/6.0/types.h> +#include "iwriter.h" namespace android { namespace hardware { @@ -31,9 +32,10 @@ using namespace ::android::hardware::audio::V6_0; struct DevicePortSource { virtual ~DevicePortSource() {} virtual Result getCapturePosition(uint64_t &frames, uint64_t &time) = 0; - virtual int read(void *data, size_t nBytes) = 0; + virtual size_t read(float volume, size_t bytesToRead, IWriter &) = 0; - static std::unique_ptr<DevicePortSource> create(const DeviceAddress &, + static std::unique_ptr<DevicePortSource> create(size_t writerBufferSizeHint, + const DeviceAddress &, const AudioConfig &, const hidl_bitfield<AudioOutputFlag> &, uint64_t &frames); diff --git a/audio/entry.cpp b/audio/entry.cpp index 7cbeb6d1..1d48f432 100644 --- a/audio/entry.cpp +++ b/audio/entry.cpp @@ -14,37 +14,12 @@ * limitations under the License. */ -#include <binder/ProcessState.h> -#include <hwbinder/ProcessState.h> -#include <hidl/LegacySupport.h> #include "device_factory.h" -int main(int, char**) { - using ::android::sp; - using ::android::OK; - using ::android::hardware::audio::V6_0::IDevicesFactory; - using ::android::hardware::audio::V6_0::implementation::DevicesFactory; - using ::android::hardware::registerPassthroughServiceImplementation; +using android::hardware::audio::V6_0::IDevicesFactory; +using android::hardware::audio::V6_0::implementation::DevicesFactory; - ::android::ProcessState::initWithDriver("/dev/vndbinder"); - ::android::ProcessState::self()->startThreadPool(); - ::android::hardware::configureRpcThreadpool(16, true /* callerWillJoin */); - - sp<IDevicesFactory> factory(new DevicesFactory()); - if (factory->registerAsService() != ::android::NO_ERROR) { - return -EINVAL; - } - - if (registerPassthroughServiceImplementation( - "android.hardware.audio.effect@6.0::IEffectsFactory") != OK) { - return -EINVAL; - } - - if (registerPassthroughServiceImplementation( - "android.hardware.soundtrigger@2.2::ISoundTriggerHw") != OK) { - return -EINVAL; - } - - ::android::hardware::joinRpcThreadpool(); - return 0; +extern "C" IDevicesFactory* HIDL_FETCH_IDevicesFactory(const char* name) { + (void)name; + return new DevicesFactory(); } diff --git a/audio/ireader.h b/audio/ireader.h new file mode 100644 index 00000000..cb20e2b6 --- /dev/null +++ b/audio/ireader.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2020 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. + */ + +#pragma once +#include <stdint.h> + +namespace android { +namespace hardware { +namespace audio { +namespace V6_0 { +namespace implementation { + +struct IReader { + virtual ~IReader() {} + virtual size_t operator()(void* dst, size_t szBytes) = 0; +}; + +} // namespace implementation +} // namespace V6_0 +} // namespace audio +} // namespace hardware +} // namespace android diff --git a/audio/iwriter.h b/audio/iwriter.h new file mode 100644 index 00000000..d204ab1e --- /dev/null +++ b/audio/iwriter.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2020 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. + */ + +#pragma once +#include <stdint.h> + +namespace android { +namespace hardware { +namespace audio { +namespace V6_0 { +namespace implementation { + +struct IWriter { + virtual ~IWriter() {} + virtual size_t operator()(const void* src, size_t szBytes) = 0; +}; + +} // namespace implementation +} // namespace V6_0 +} // namespace audio +} // namespace hardware +} // namespace android diff --git a/audio/primary_device.cpp b/audio/primary_device.cpp index 9f39d088..3ba4bf8f 100644 --- a/audio/primary_device.cpp +++ b/audio/primary_device.cpp @@ -33,23 +33,10 @@ constexpr size_t kOutBufferDurationMs = 22; using ::android::hardware::Void; -PrimaryDevice::PrimaryDevice() - : mMixer(talsa::mixerOpen(talsa::kPcmDevice)) { - if (mMixer) { - mMixerMasterVolumeCtl = mixer_get_ctl_by_name(mMixer.get(), "Master Playback Volume"); - mMixerCaptureVolumeCtl = mixer_get_ctl_by_name(mMixer.get(), "Capture Volume"); - mMixerMasterPaybackSwitchCtl = mixer_get_ctl_by_name(mMixer.get(), "Master Playback Switch"); - mMixerCaptureSwitchCtl = mixer_get_ctl_by_name(mMixer.get(), "Capture Switch"); - - talsa::mixerSetPercentAll(mMixerMasterVolumeCtl, 100); - talsa::mixerSetPercentAll(mMixerCaptureVolumeCtl, 100); - talsa::mixerSetValueAll(mMixerMasterPaybackSwitchCtl, 1); - talsa::mixerSetValueAll(mMixerCaptureSwitchCtl, 1); - } -} +PrimaryDevice::PrimaryDevice() {} Return<Result> PrimaryDevice::initCheck() { - return mMixer ? Result::OK : FAILURE(Result::NOT_INITIALIZED); + return Result::OK; } Return<Result> PrimaryDevice::setMasterVolume(float volume) { @@ -57,61 +44,35 @@ Return<Result> PrimaryDevice::setMasterVolume(float volume) { return FAILURE(Result::INVALID_ARGUMENTS); } - if (!mMixerMasterVolumeCtl) { - return FAILURE(Result::INVALID_STATE); - } - - talsa::mixerSetPercentAll(mMixerMasterVolumeCtl, int(100 * volume)); mMasterVolume = volume; + updateOutputStreamVolume(mMasterMute ? 0.0f : volume); return Result::OK; } Return<void> PrimaryDevice::getMasterVolume(getMasterVolume_cb _hidl_cb) { - if (mMixerMasterVolumeCtl) { - _hidl_cb(Result::OK, mMasterVolume); - } else { - _hidl_cb(FAILURE(Result::INVALID_STATE), 0); - } - + _hidl_cb(Result::OK, mMasterVolume); return Void(); } Return<Result> PrimaryDevice::PrimaryDevice::setMicMute(bool mute) { - if (mMixerCaptureSwitchCtl) { - talsa::mixerSetValueAll(mMixerCaptureSwitchCtl, mute ? 0 : 1); - return Result::OK; - } else { - return FAILURE(Result::INVALID_STATE); - } + mMicMute = mute; + updateInputStreamMicMute(mute); + return Result::OK; } Return<void> PrimaryDevice::getMicMute(getMicMute_cb _hidl_cb) { - if (mMixerCaptureSwitchCtl) { - const int value = mixer_ctl_get_value(mMixerCaptureSwitchCtl, 0); - _hidl_cb(Result::OK, value == 0); - } else { - _hidl_cb(FAILURE(Result::INVALID_STATE), 0); - } + _hidl_cb(Result::OK, mMicMute); return Void(); } Return<Result> PrimaryDevice::setMasterMute(bool mute) { - if (mMixerMasterPaybackSwitchCtl) { - talsa::mixerSetValueAll(mMixerMasterPaybackSwitchCtl, mute ? 0 : 1); - return Result::OK; - } else { - return FAILURE(Result::INVALID_STATE); - } + mMasterMute = mute; + updateOutputStreamVolume(mute ? 0.0f : mMasterVolume); + return Result::OK; } Return<void> PrimaryDevice::getMasterMute(getMasterMute_cb _hidl_cb) { - if (mMixerMasterPaybackSwitchCtl) { - const int value = mixer_ctl_get_value(mMixerMasterPaybackSwitchCtl, 0); - _hidl_cb(Result::OK, value == 0); - } else { - _hidl_cb(FAILURE(Result::NOT_SUPPORTED), 0); - } - + _hidl_cb(Result::OK, mMasterMute); return Void(); } @@ -141,11 +102,17 @@ Return<void> PrimaryDevice::openOutputStream(int32_t ioHandle, openOutputStream_cb _hidl_cb) { AudioConfig suggestedConfig; if (util::checkAudioConfig(true, kOutBufferDurationMs, config, suggestedConfig)) { - ++mNStreams; - _hidl_cb(Result::OK, - new StreamOut(this, &unrefDevice, - ioHandle, device, suggestedConfig, flags, sourceMetadata), - config); + auto stream = std::make_unique<StreamOut>( + this, ioHandle, device, suggestedConfig, flags, sourceMetadata); + + stream->setMasterVolume(mMasterMute ? 0.0f : mMasterVolume); + + { + std::lock_guard<std::mutex> guard(mMutex); + LOG_ALWAYS_FATAL_IF(!mOutputStreams.insert(stream.get()).second); + } + + _hidl_cb(Result::OK, stream.release(), config); } else { ALOGE("PrimaryDevice::%s:%d failed", __func__, __LINE__); _hidl_cb(FAILURE(Result::INVALID_ARGUMENTS), nullptr, suggestedConfig); @@ -162,11 +129,17 @@ Return<void> PrimaryDevice::openInputStream(int32_t ioHandle, openInputStream_cb _hidl_cb) { AudioConfig suggestedConfig; if (util::checkAudioConfig(false, kInBufferDurationMs, config, suggestedConfig)) { - ++mNStreams; - _hidl_cb(Result::OK, - new StreamIn(this, &unrefDevice, - ioHandle, device, suggestedConfig, flags, sinkMetadata), - config); + auto stream = std::make_unique<StreamIn>( + this, ioHandle, device, suggestedConfig, flags, sinkMetadata); + + stream->setMicMute(mMicMute); + + { + std::lock_guard<std::mutex> guard(mMutex); + LOG_ALWAYS_FATAL_IF(!mInputStreams.insert(stream.get()).second); + } + + _hidl_cb(Result::OK, stream.release(), config); } else { ALOGE("PrimaryDevice::%s:%d failed", __func__, __LINE__); _hidl_cb(FAILURE(Result::INVALID_ARGUMENTS), nullptr, suggestedConfig); @@ -282,18 +255,10 @@ Return<Result> PrimaryDevice::setConnectedState(const DeviceAddress& dev_addr, b } Return<Result> PrimaryDevice::close() { - if (mNStreams > 0) { - return FAILURE(Result::INVALID_STATE); - } else if (mMixer) { - mMixerMasterVolumeCtl = nullptr; - mMixerCaptureVolumeCtl = nullptr; - mMixerMasterPaybackSwitchCtl = nullptr; - mMixerCaptureSwitchCtl = nullptr; - mMixer.reset(); - return Result::OK; - } else { - return FAILURE(Result::INVALID_STATE); - } + std::lock_guard<std::mutex> guard(mMutex); + + return (mInputStreams.empty() && mOutputStreams.empty()) + ? Result::OK : FAILURE(Result::INVALID_STATE); } Return<Result> PrimaryDevice::addDeviceEffect(AudioPortHandle device, uint64_t effectId) { @@ -395,12 +360,28 @@ Return<Result> PrimaryDevice::updateRotation(IPrimaryDevice::Rotation rotation) return FAILURE(Result::NOT_SUPPORTED); } -void PrimaryDevice::unrefDevice(IDevice *dev) { - static_cast<PrimaryDevice *>(dev)->unrefDeviceImpl(); +void PrimaryDevice::unrefDevice(StreamIn *sin) { + std::lock_guard<std::mutex> guard(mMutex); + LOG_ALWAYS_FATAL_IF(mInputStreams.erase(sin) < 1); +} + +void PrimaryDevice::unrefDevice(StreamOut *sout) { + std::lock_guard<std::mutex> guard(mMutex); + LOG_ALWAYS_FATAL_IF(mOutputStreams.erase(sout) < 1); } -void PrimaryDevice::unrefDeviceImpl() { - LOG_ALWAYS_FATAL_IF(--mNStreams < 0); +void PrimaryDevice::updateOutputStreamVolume(float masterVolume) const { + std::lock_guard<std::mutex> guard(mMutex); + for (StreamOut *stream : mOutputStreams) { + stream->setMasterVolume(masterVolume); + } +} + +void PrimaryDevice::updateInputStreamMicMute(bool micMute) const { + std::lock_guard<std::mutex> guard(mMutex); + for (StreamIn *stream : mInputStreams) { + stream->setMicMute(micMute); + } } } // namespace implementation diff --git a/audio/primary_device.h b/audio/primary_device.h index 05964f3e..2a956806 100644 --- a/audio/primary_device.h +++ b/audio/primary_device.h @@ -16,9 +16,9 @@ #pragma once #include <android/hardware/audio/6.0/IPrimaryDevice.h> -#include <atomic> +#include <mutex> #include <unordered_map> -#include "talsa.h" +#include <unordered_set> namespace android { namespace hardware { @@ -35,6 +35,9 @@ using ::android::hardware::Return; using namespace ::android::hardware::audio::common::V6_0; using namespace ::android::hardware::audio::V6_0; +struct StreamIn; +struct StreamOut; + struct PrimaryDevice : public IPrimaryDevice { PrimaryDevice(); @@ -100,16 +103,13 @@ struct PrimaryDevice : public IPrimaryDevice { Return<Result> updateRotation(IPrimaryDevice::Rotation rotation) override; private: - static void unrefDevice(IDevice*); - void unrefDeviceImpl(); + friend StreamIn; + friend StreamOut; - talsa::MixerPtr mMixer; - talsa::mixer_ctl_t *mMixerMasterVolumeCtl = nullptr; - talsa::mixer_ctl_t *mMixerCaptureVolumeCtl = nullptr; - talsa::mixer_ctl_t *mMixerMasterPaybackSwitchCtl = nullptr; - talsa::mixer_ctl_t *mMixerCaptureSwitchCtl = nullptr; - float mMasterVolume = 1.0f; - std::atomic<int> mNStreams = 0; + void unrefDevice(StreamIn *); + void unrefDevice(StreamOut *); + void updateOutputStreamVolume(float masterVolume) const; + void updateInputStreamMicMute(bool micMute) const; struct AudioPatch { AudioPortConfig source; @@ -118,6 +118,14 @@ private: AudioPatchHandle mNextAudioPatchHandle = 0; std::unordered_map<AudioPatchHandle, AudioPatch> mAudioPatches; + + std::unordered_set<StreamIn *> mInputStreams; // requires mMutex + std::unordered_set<StreamOut *> mOutputStreams; // requires mMutex + mutable std::mutex mMutex; + + float mMasterVolume = 1.0f; + bool mMasterMute = false; + bool mMicMute = false; }; } // namespace implementation diff --git a/audio/ring_buffer.cpp b/audio/ring_buffer.cpp new file mode 100644 index 00000000..b2cc8c4f --- /dev/null +++ b/audio/ring_buffer.cpp @@ -0,0 +1,155 @@ +/* + * Copyright (C) 2020 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. + */ + +#include <log/log.h> +#include "ring_buffer.h" + +namespace android { +namespace hardware { +namespace audio { +namespace V6_0 { +namespace implementation { + +RingBuffer::RingBuffer(size_t capacity) + : mBuffer(new uint8_t[capacity]) + , mCapacity(capacity) {} + +size_t RingBuffer::availableToProduce() const { + std::lock_guard<std::mutex> guard(mMutex); + return mCapacity - mAvailableToConsume; +} + +size_t RingBuffer::availableToConsume() const { + std::unique_lock<std::mutex> lock(mMutex); + return mAvailableToConsume; +} + +size_t RingBuffer::makeRoomForProduce(size_t atLeast) { + std::unique_lock<std::mutex> lock(mMutex); + LOG_ALWAYS_FATAL_IF(atLeast >= mCapacity); + + const size_t toProduce = mCapacity - mAvailableToConsume; + const size_t toDrop = (atLeast <= toProduce) + ? 0 : atLeast - toProduce; + + mConsumePos = (mConsumePos + toDrop) % mCapacity; + mAvailableToConsume -= toDrop; + + return toDrop; +} + +bool RingBuffer::waitForProduceAvailable(Timepoint blockUntil) const { + std::unique_lock<std::mutex> lock(mMutex); + while (true) { + if (mAvailableToConsume < mCapacity) { + return true; + } else if (mProduceAvailable.wait_until(lock, blockUntil) == std::cv_status::timeout) { + return false; + } + } +} + +RingBuffer::ContiniousChunk RingBuffer::getProduceChunk() const { + std::unique_lock<std::mutex> lock(mMutex); + const int availableToProduce = mCapacity - mAvailableToConsume; + + ContiniousChunk chunk; + + chunk.data = &mBuffer[mProducePos]; + chunk.size = (mProducePos >= mConsumePos) + ? std::min(mCapacity - mProducePos, availableToProduce) + : std::min(mConsumePos - mProducePos, availableToProduce); + + return chunk; +} + +size_t RingBuffer::produce(size_t size) { + std::unique_lock<std::mutex> lock(mMutex); + const int availableToProduce = mCapacity - mAvailableToConsume; + size = std::min(size, size_t(availableToProduce)); + + mProducePos = (mProducePos + size) % mCapacity; + mAvailableToConsume += size; + + mConsumeAvailable.notify_one(); + return size; +} + +size_t RingBuffer::produce(const void *srcRaw, size_t size) { + std::unique_lock<std::mutex> lock(mMutex); + int produceSize = std::min(mCapacity - mAvailableToConsume, int(size)); + size = produceSize; + const uint8_t *src = static_cast<const uint8_t *>(srcRaw); + + while (produceSize > 0) { + const int availableToProduce = mCapacity - mAvailableToConsume; + const int chunkSz = (mProducePos >= mConsumePos) + ? std::min(mCapacity - mProducePos, availableToProduce) + : std::min(mConsumePos - mProducePos, availableToProduce); + void *dst = &mBuffer[mProducePos]; + + memcpy(dst, src, chunkSz); + src += chunkSz; + mProducePos = (mProducePos + chunkSz) % mCapacity; + mAvailableToConsume += chunkSz; + produceSize -= chunkSz; + } + + mConsumeAvailable.notify_one(); + return size; +} + +bool RingBuffer::waitForConsumeAvailable(Timepoint blockUntil) const { + std::unique_lock<std::mutex> lock(mMutex); + while (true) { + if (mAvailableToConsume > 0) { + return true; + } else if (mConsumeAvailable.wait_until(lock, blockUntil) == std::cv_status::timeout) { + return false; + } + } +} + +RingBuffer::ContiniousLockedChunk RingBuffer::getConsumeChunk() const { + std::unique_lock<std::mutex> lock(mMutex); + + ContiniousLockedChunk chunk; + + chunk.data = &mBuffer[mConsumePos]; + chunk.size = (mConsumePos >= mProducePos) + ? std::min(mCapacity - mConsumePos, mAvailableToConsume) + : std::min(mProducePos - mConsumePos, mAvailableToConsume); + chunk.lock = std::move(lock); + + return chunk; +} + +size_t RingBuffer::consume(const ContiniousLockedChunk &lock, size_t size) { + (void)lock; // the lock is provided by getConsumeChunk + size = std::min(size, size_t(mAvailableToConsume)); + + mConsumePos = (mConsumePos + size) % mCapacity; + mAvailableToConsume -= size; + + mProduceAvailable.notify_one(); + return size; +} + +} // namespace implementation +} // namespace V6_0 +} // namespace audio +} // namespace hardware +} // namespace android diff --git a/audio/ring_buffer.h b/audio/ring_buffer.h new file mode 100644 index 00000000..41916779 --- /dev/null +++ b/audio/ring_buffer.h @@ -0,0 +1,102 @@ +/* + * Copyright (C) 2020 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. + */ + +#pragma once +#include <memory> +#include <chrono> +#include <utility> +#include <condition_variable> +#include <mutex> +#include <stdint.h> + +namespace android { +namespace hardware { +namespace audio { +namespace V6_0 { +namespace implementation { + +// A one-producer-one-consumer ring buffer. +struct RingBuffer { + typedef std::chrono::time_point<std::chrono::high_resolution_clock> Timepoint; + + RingBuffer(size_t capacity); + + size_t capacity() const { return mCapacity; } + size_t availableToProduce() const; + size_t availableToConsume() const; + + struct ContiniousChunk { + void *data; + size_t size; + std::unique_lock<std::mutex> lock; + }; + + struct ContiniousLockedChunk : public ContiniousChunk{ + std::unique_lock<std::mutex> lock; + }; + + size_t makeRoomForProduce(size_t atLeast); + + bool waitForProduceAvailable(Timepoint blockUntil) const; + + // `getProduceChunk` is a non-blocking function which returns a pointer + // (`result.data`) inside RingBuffer's buffer, `result.size` is the + // size of the continious chunk (can be smaller than availableToProduce()). + ContiniousChunk getProduceChunk() const; + + // Tries to move the `produce` cursor by `size`, returns the actual size + // moved. + size_t produce(size_t size); + + // Tried to write `size` bytes into the internal buffer from `data`, + // returns the actual size written. + size_t produce(const void *data, size_t size); + + bool waitForConsumeAvailable(Timepoint blockUntil) const; + + // `getConsumeChunk` is a non-blocking function which a pointer + // (`result.data`) inside RingBuffer's buffer, `result.size` is the + // size of the continious chunk (can be smaller than availableToConsume()). + // IMPORTANT: do not call long running functions while have an instance of + // ContiniousLockedChunk, it might block the producer because + // it need to drop the stale audio data to replace it with + // more recent one. + // NOTE: ContiniousLockedChunk holds a lock inside, it might deadlock + // if you calling other RingBuffer's functions that assume it is + // unlocked, in this case you want to introduce a function like + // `consume` below. + ContiniousLockedChunk getConsumeChunk() const; + + // Tries to move the `consume` cursor by `size`, returns the actual size + // moved. + size_t consume(const ContiniousLockedChunk&, size_t size); + +private: + std::unique_ptr<uint8_t[]> mBuffer; + mutable std::condition_variable mProduceAvailable; + mutable std::condition_variable mConsumeAvailable; + mutable std::mutex mMutex; + const int mCapacity; + int mAvailableToConsume = 0; + int mProducePos = 0; + int mConsumePos = 0; +}; + +} // namespace implementation +} // namespace V6_0 +} // namespace audio +} // namespace hardware +} // namespace android diff --git a/audio/stream_in.cpp b/audio/stream_in.cpp index c3ef62f2..ee7bcfcd 100644 --- a/audio/stream_in.cpp +++ b/audio/stream_in.cpp @@ -19,17 +19,15 @@ #include <fmq/MessageQueue.h> #include <hidl/MQDescriptor.h> #include <hidl/Status.h> +#include <utils/ThreadDefs.h> +#include <future> +#include <thread> #include "stream_in.h" #include "device_port_source.h" #include "deleters.h" +#include "audio_ops.h" #include "util.h" #include "debug.h" -#include <sys/resource.h> -#include <pthread.h> -#include <cutils/sched_policy.h> -#include <utils/ThreadDefs.h> -#include <future> -#include <thread> namespace android { namespace hardware { @@ -98,8 +96,7 @@ struct ReadThread : public IOThread { } void threadLoop() { - setpriority(PRIO_PROCESS, 0, PRIORITY_URGENT_AUDIO); - set_sched_policy(0, SP_FOREGROUND); + util::setThreadPriority(PRIORITY_URGENT_AUDIO); mTid.set_value(pthread_self()); while (true) { @@ -112,15 +109,12 @@ struct ReadThread : public IOThread { if (efState & STAND_BY_REQUEST) { mSource.reset(); - mBuffer.reset(); } if (efState & (MessageQueueFlagBits::NOT_FULL | 0)) { if (!mSource) { - mBuffer.reset(new uint8_t[mDataMQ.getQuantumCount()]); - LOG_ALWAYS_FATAL_IF(!mBuffer); - - mSource = DevicePortSource::create(mStream->getDeviceAddress(), + mSource = DevicePortSource::create(mDataMQ.getQuantumCount(), + mStream->getDeviceAddress(), mStream->getAudioConfig(), mStream->getAudioOutputFlags(), mStream->getFrameCounter()); @@ -166,36 +160,40 @@ struct ReadThread : public IOThread { } IStreamIn::ReadStatus doRead(const IStreamIn::ReadParameters &rParameters) { + struct MQWriter : public IWriter { + explicit MQWriter(DataMQ &mq) : dataMQ(mq) {} + + size_t operator()(const void *dst, size_t sz) override { + if (dataMQ.write(static_cast<const uint8_t *>(dst), sz)) { + totalWritten += sz; + return sz; + } else { + ALOGE("WriteThread::%s:%d: DataMQ::write failed", + __func__, __LINE__); + return 0; + } + } + + size_t totalWritten = 0; + DataMQ &dataMQ; + }; + const size_t bytesToRead = std::min(mDataMQ.availableToWrite(), static_cast<size_t>(rParameters.params.read)); - IStreamIn::ReadStatus status; - size_t read = 0; - status.retval = doReadImpl(&mBuffer[0], bytesToRead, read); - if (status.retval == Result::OK) { - if (!mDataMQ.write(&mBuffer[0], read)) { - ALOGE("ReadThread::%s:%d: mDataMQ.write failed", __func__, __LINE__); - } - status.reply.read = read; + MQWriter writer(mDataMQ); + const size_t framesLost = + mSource->read(mStream->getEffectiveVolume(), bytesToRead, writer); + if (framesLost > 0) { + mStream->addInputFramesLost(framesLost); } + IStreamIn::ReadStatus status; + status.retval = Result::OK; + status.reply.read = writer.totalWritten; return status; } - Result doReadImpl(uint8_t *const data, const size_t toRead, size_t &read) { - const int res = mSource->read(data, toRead); - if (res < 0) { - memset(data, 0, toRead); - read = toRead; - ALOGE("StreamInReadThread::%s:%d pcm_read failed with %s", - __func__, __LINE__, strerror(-res)); - } else { - read = res; - } - - return Result::OK; - } - IStreamIn::ReadStatus doGetCapturePosition() { IStreamIn::ReadStatus status; @@ -211,7 +209,6 @@ struct ReadThread : public IOThread { StatusMQ mStatusMQ; DataMQ mDataMQ; std::unique_ptr<EventFlag, deleters::forEventFlag> mEfGroup; - std::unique_ptr<uint8_t[]> mBuffer; std::unique_ptr<DevicePortSource> mSource; std::thread mThread; std::promise<pthread_t> mTid; @@ -219,15 +216,13 @@ struct ReadThread : public IOThread { } // namespace -StreamIn::StreamIn(sp<IDevice> dev, - void (*unrefDevice)(IDevice*), +StreamIn::StreamIn(sp<PrimaryDevice> dev, int32_t ioHandle, const DeviceAddress& device, const AudioConfig& config, hidl_bitfield<AudioInputFlag> flags, const SinkMetadata& sinkMetadata) : mDev(std::move(dev)) - , mUnrefDevice(unrefDevice) , mCommon(ioHandle, device, config, flags) , mSinkMetadata(sinkMetadata) { } @@ -364,7 +359,7 @@ Return<void> StreamIn::getMmapPosition(getMmapPosition_cb _hidl_cb) { Result StreamIn::closeImpl(const bool fromDctor) { if (mDev) { mReadThread.reset(); - mUnrefDevice(mDev.get()); + mDev->unrefDevice(this); mDev = nullptr; return Result::OK; } else if (fromDctor) { @@ -449,6 +444,12 @@ Return<Result> StreamIn::setMicrophoneFieldDimension(float zoom) { return FAILURE(Result::NOT_SUPPORTED); } +void StreamIn::setMicMute(bool mute) { + mEffectiveVolume = + (mute && (getDeviceAddress().device & AudioDevice::IN_BUILTIN_MIC)) + ? 0.0f : 1.0f; +} + } // namespace implementation } // namespace V6_0 } // namespace audio diff --git a/audio/stream_in.h b/audio/stream_in.h index 2a769814..dfc38a65 100644 --- a/audio/stream_in.h +++ b/audio/stream_in.h @@ -19,6 +19,7 @@ #include <android/hardware/audio/6.0/IDevice.h> #include "stream_common.h" #include "io_thread.h" +#include "primary_device.h" namespace android { namespace hardware { @@ -35,8 +36,7 @@ using namespace ::android::hardware::audio::common::V6_0; using namespace ::android::hardware::audio::V6_0; struct StreamIn : public IStreamIn { - StreamIn(sp<IDevice> dev, - void (*unrefDevice)(IDevice*), + StreamIn(sp<PrimaryDevice> dev, int32_t ioHandle, const DeviceAddress& device, const AudioConfig& config, @@ -92,18 +92,23 @@ struct StreamIn : public IStreamIn { const hidl_bitfield<AudioOutputFlag> &getAudioOutputFlags() const { return mCommon.m_flags; } uint64_t &getFrameCounter() { return mFrames; } + void setMicMute(bool mute); + void addInputFramesLost(size_t n) { mInputFramesLost += n; } + float getEffectiveVolume() const { return mEffectiveVolume; } private: Result closeImpl(bool fromDctor); - sp<IDevice> mDev; - void (* const mUnrefDevice)(IDevice*); + sp<PrimaryDevice> mDev; const StreamCommon mCommon; const SinkMetadata mSinkMetadata; std::unique_ptr<IOThread> mReadThread; // The count is not reset to zero when output enters standby. uint64_t mFrames = 0; + + std::atomic<uint32_t> mInputFramesLost = 0; + std::atomic<float> mEffectiveVolume = 1.0f; }; } // namespace implementation diff --git a/audio/stream_out.cpp b/audio/stream_out.cpp index 72b826fe..a34c2c6e 100644 --- a/audio/stream_out.cpp +++ b/audio/stream_out.cpp @@ -19,18 +19,15 @@ #include <fmq/MessageQueue.h> #include <hidl/MQDescriptor.h> #include <hidl/Status.h> -#include <math.h> +#include <utils/ThreadDefs.h> +#include <future> +#include <thread> #include "stream_out.h" #include "device_port_sink.h" #include "deleters.h" +#include "audio_ops.h" #include "util.h" #include "debug.h" -#include <sys/resource.h> -#include <pthread.h> -#include <cutils/sched_policy.h> -#include <utils/ThreadDefs.h> -#include <future> -#include <thread> namespace android { namespace hardware { @@ -101,8 +98,7 @@ struct WriteThread : public IOThread { } void threadLoop() { - setpriority(PRIO_PROCESS, 0, PRIORITY_URGENT_AUDIO); - set_sched_policy(0, SP_FOREGROUND); + util::setThreadPriority(PRIORITY_URGENT_AUDIO); mTid.set_value(pthread_self()); while (true) { @@ -119,10 +115,8 @@ struct WriteThread : public IOThread { if (efState & (MessageQueueFlagBits::NOT_EMPTY | 0)) { if (!mSink) { - mBuffer.reset(new uint8_t[mDataMQ.getQuantumCount()]); - LOG_ALWAYS_FATAL_IF(!mBuffer); - - mSink = DevicePortSink::create(mStream->getDeviceAddress(), + mSink = DevicePortSink::create(mDataMQ.getQuantumCount(), + mStream->getDeviceAddress(), mStream->getAudioConfig(), mStream->getAudioOutputFlags(), mStream->getFrameCounter()); @@ -172,35 +166,31 @@ struct WriteThread : public IOThread { } IStreamOut::WriteStatus doWrite() { - IStreamOut::WriteStatus status; - - const size_t availToRead = mDataMQ.availableToRead(); - size_t written = 0; - if (mDataMQ.read(&mBuffer[0], availToRead)) { - applyVolume(&mBuffer[0], availToRead, mStream->getVolumeNumerator()); - status.retval = doWriteImpl(&mBuffer[0], availToRead, written); - status.reply.written = written; - } else { - ALOGE("WriteThread::%s:%d: mDataMQ.read failed", __func__, __LINE__); - status.retval = Result::OK; - } + struct MQReader : public IReader { + explicit MQReader(DataMQ &mq) : dataMQ(mq) {} + + size_t operator()(void *dst, size_t sz) override { + if (dataMQ.read(static_cast<uint8_t *>(dst), sz)) { + totalRead += sz; + return sz; + } else { + ALOGE("WriteThread::%s:%d: DataMQ::read failed", + __func__, __LINE__); + return 0; + } + } - return status; - } + size_t totalRead = 0; + DataMQ &dataMQ; + }; - static void applyVolume(void *buf, const size_t szBytes, const int32_t numerator) { - constexpr int32_t kDenominator = StreamOut::kVolumeDenominator; + MQReader reader(mDataMQ); + mSink->write(mStream->getEffectiveVolume(), mDataMQ.availableToRead(), reader); - if (numerator == kDenominator) { - return; - } - - int16_t *samples = static_cast<int16_t *>(buf); - std::for_each(samples, - samples + szBytes / sizeof(*samples), - [numerator](int16_t &x) { - x = (x * numerator + kDenominator / 2) / kDenominator; - }); + IStreamOut::WriteStatus status; + status.retval = Result::OK; + status.reply.written = reader.totalRead; + return status; } IStreamOut::WriteStatus doGetPresentationPosition() { @@ -222,27 +212,11 @@ struct WriteThread : public IOThread { return status; } - Result doWriteImpl(const uint8_t *const data, - const size_t toWrite, - size_t &written) { - const int res = mSink->write(data, toWrite); - if (res < 0) { - ALOGE("WriteThread::%s:%d: DevicePortSink::write failed with %s", - __func__, __LINE__, strerror(-res)); - written = toWrite; - } else { - written = res; - } - - return Result::OK; - } - StreamOut *const mStream; CommandMQ mCommandMQ; StatusMQ mStatusMQ; DataMQ mDataMQ; std::unique_ptr<EventFlag, deleters::forEventFlag> mEfGroup; - std::unique_ptr<uint8_t[]> mBuffer; std::unique_ptr<DevicePortSink> mSink; std::thread mThread; std::promise<pthread_t> mTid; @@ -250,15 +224,13 @@ struct WriteThread : public IOThread { } // namespace -StreamOut::StreamOut(sp<IDevice> dev, - void (*unrefDevice)(IDevice*), +StreamOut::StreamOut(sp<PrimaryDevice> dev, int32_t ioHandle, const DeviceAddress& device, const AudioConfig& config, hidl_bitfield<AudioOutputFlag> flags, const SourceMetadata& sourceMetadata) : mDev(std::move(dev)) - , mUnrefDevice(unrefDevice) , mCommon(ioHandle, device, config, flags) , mSourceMetadata(sourceMetadata) {} @@ -374,7 +346,7 @@ Return<Result> StreamOut::setHwAvSync(uint32_t hwAvSync) { Result StreamOut::closeImpl(const bool fromDctor) { if (mDev) { mWriteThread.reset(); - mUnrefDevice(mDev.get()); + mDev->unrefDevice(this); mDev = nullptr; return Result::OK; } else if (fromDctor) { @@ -420,7 +392,9 @@ Return<Result> StreamOut::setVolume(float left, float right) { return FAILURE(Result::INVALID_ARGUMENTS); } - mVolumeNumerator = int16_t((left + right) * kVolumeDenominator / 2); + std::lock_guard<std::mutex> guard(mMutex); + mStreamVolume = (left + right) / 2.0f; + updateEffectiveVolumeLocked(); return Result::OK; } @@ -551,6 +525,16 @@ Return<Result> StreamOut::setPlaybackRateParameters(const PlaybackRate &playback return FAILURE(Result::NOT_SUPPORTED); } +void StreamOut::setMasterVolume(float masterVolume) { + std::lock_guard<std::mutex> guard(mMutex); + mMasterVolume = masterVolume; + updateEffectiveVolumeLocked(); +} + +void StreamOut::updateEffectiveVolumeLocked() { + mEffectiveVolume = mMasterVolume * mStreamVolume; +} + } // namespace implementation } // namespace V6_0 } // namespace audio diff --git a/audio/stream_out.h b/audio/stream_out.h index 79adef34..20e42286 100644 --- a/audio/stream_out.h +++ b/audio/stream_out.h @@ -20,6 +20,7 @@ #include <android/hardware/audio/6.0/IDevice.h> #include "stream_common.h" #include "io_thread.h" +#include "primary_device.h" namespace android { namespace hardware { @@ -36,8 +37,7 @@ using namespace ::android::hardware::audio::common::V6_0; using namespace ::android::hardware::audio::V6_0; struct StreamOut : public IStreamOut { - StreamOut(sp<IDevice> dev, - void (*unrefDevice)(IDevice*), + StreamOut(sp<PrimaryDevice> dev, int32_t ioHandle, const DeviceAddress& device, const AudioConfig& config, @@ -45,8 +45,6 @@ struct StreamOut : public IStreamOut { const SourceMetadata& sourceMetadata); ~StreamOut(); - static constexpr int16_t kVolumeDenominator = 1 << 14; - // IStream Return<uint64_t> getFrameSize() override; Return<uint64_t> getFrameCount() override; @@ -104,7 +102,8 @@ struct StreamOut : public IStreamOut { Return<void> getPlaybackRateParameters(getPlaybackRateParameters_cb _hidl_cb) override; Return<Result> setPlaybackRateParameters(const PlaybackRate &playbackRate) override; - int16_t getVolumeNumerator() const { return mVolumeNumerator; }; + void setMasterVolume(float volume); + float getEffectiveVolume() const { return mEffectiveVolume; } const DeviceAddress &getDeviceAddress() const { return mCommon.m_device; } const AudioConfig &getAudioConfig() const { return mCommon.m_config; } const hidl_bitfield<AudioOutputFlag> &getAudioOutputFlags() const { return mCommon.m_flags; } @@ -113,13 +112,17 @@ struct StreamOut : public IStreamOut { private: Result closeImpl(bool fromDctor); + void updateEffectiveVolumeLocked(); - sp<IDevice> mDev; - void (* const mUnrefDevice)(IDevice*); + sp<PrimaryDevice> mDev; const StreamCommon mCommon; const SourceMetadata mSourceMetadata; std::unique_ptr<IOThread> mWriteThread; - std::atomic<int16_t> mVolumeNumerator = kVolumeDenominator; + + float mMasterVolume = 1.0f; // requires mMutex + float mStreamVolume = 1.0f; // requires mMutex + std::atomic<float> mEffectiveVolume = 1.0f; + std::mutex mMutex; // The count is not reset to zero when output enters standby. uint64_t mFrames = 0; diff --git a/audio/talsa.cpp b/audio/talsa.cpp index 12c22b0a..5afb8156 100644 --- a/audio/talsa.cpp +++ b/audio/talsa.cpp @@ -14,6 +14,7 @@ * limitations under the License. */ +#include <mutex> #include <log/log.h> #include "talsa.h" #include "debug.h" @@ -25,14 +26,81 @@ namespace V6_0 { namespace implementation { namespace talsa { -void PcmDeleter::operator()(pcm_t *x) const { - LOG_ALWAYS_FATAL_IF(pcm_close(x) != 0); -}; +namespace { + +struct mixer *gMixer0 = nullptr; +int gMixerRefcounter0 = 0; +std::mutex gMixerMutex; + +void mixerSetValueAll(struct mixer_ctl *ctl, int value) { + const unsigned int n = mixer_ctl_get_num_values(ctl); + for (unsigned int i = 0; i < n; i++) { + ::mixer_ctl_set_value(ctl, i, value); + } +} + +void mixerSetPercentAll(struct mixer_ctl *ctl, int percent) { + const unsigned int n = mixer_ctl_get_num_values(ctl); + for (unsigned int i = 0; i < n; i++) { + ::mixer_ctl_set_percent(ctl, i, percent); + } +} + +struct mixer *mixerGetOrOpenImpl(const unsigned card, + struct mixer *&gMixer, + int &refcounter) { + if (!gMixer) { + struct mixer *mixer = ::mixer_open(card); + if (!mixer) { + return FAILURE(nullptr); + } + + mixerSetPercentAll(::mixer_get_ctl_by_name(mixer, "Master Playback Volume"), 100); + mixerSetPercentAll(::mixer_get_ctl_by_name(mixer, "Capture Volume"), 100); + + mixerSetValueAll(::mixer_get_ctl_by_name(mixer, "Master Playback Switch"), 1); + mixerSetValueAll(::mixer_get_ctl_by_name(mixer, "Capture Switch"), 1); + + gMixer = mixer; + } + + ++refcounter; + return gMixer; +} + +struct mixer *mixerGetOrOpen(const unsigned card) { + std::lock_guard<std::mutex> guard(gMixerMutex); -void MixerDeleter::operator()(struct mixer *x) const { - mixer_close(x); + switch (card) { + case 0: return mixerGetOrOpenImpl(card, gMixer0, gMixerRefcounter0); + default: return FAILURE(nullptr); + } +} + +bool mixerUnrefImpl(struct mixer *mixer, struct mixer *&gMixer, int &refcounter) { + if (mixer == gMixer) { + if (0 == --refcounter) { + ::mixer_close(mixer); + gMixer = nullptr; + } + return true; + } else { + return false; + } } +bool mixerUnref(struct mixer *mixer) { + std::lock_guard<std::mutex> guard(gMixerMutex); + + return mixerUnrefImpl(mixer, gMixer0, gMixerRefcounter0); +} + +} // namespace + +void PcmDeleter::operator()(pcm_t *x) const { + LOG_ALWAYS_FATAL_IF(::pcm_close(x) != 0); +}; + std::unique_ptr<pcm_t, PcmDeleter> pcmOpen(const unsigned int dev, const unsigned int card, const unsigned int nChannels, @@ -45,7 +113,7 @@ std::unique_ptr<pcm_t, PcmDeleter> pcmOpen(const unsigned int dev, pcm_config.channels = nChannels; pcm_config.rate = sampleRateHz; pcm_config.period_size = frameCount; // Approx frames between interrupts - pcm_config.period_count = 4; // Approx interrupts per buffer + pcm_config.period_count = 8; // Approx interrupts per buffer pcm_config.format = PCM_FORMAT_S16_LE; pcm_config.start_threshold = 0; pcm_config.stop_threshold = isOut ? 0 : INT_MAX; @@ -65,25 +133,14 @@ std::unique_ptr<pcm_t, PcmDeleter> pcmOpen(const unsigned int dev, } } -MixerPtr mixerOpen(unsigned int card) { - return MixerPtr(::mixer_open(card)); -} - -void mixerSetValueAll(mixer_ctl_t *ctl, int value) { - const unsigned int n = mixer_ctl_get_num_values(ctl); - for (unsigned int i = 0; i < n; i++) { - mixer_ctl_set_value(ctl, i, value); - } -} +Mixer::Mixer(unsigned card): mMixer(mixerGetOrOpen(card)) {} -void mixerSetPercentAll(mixer_ctl_t *ctl, int percent) { - const unsigned int n = mixer_ctl_get_num_values(ctl); - for (unsigned int i = 0; i < n; i++) { - mixer_ctl_set_percent(ctl, i, percent); +Mixer::~Mixer() { + if (mMixer) { + LOG_ALWAYS_FATAL_IF(!mixerUnref(mMixer)); } } - } // namespace talsa } // namespace implementation } // namespace V6_0 diff --git a/audio/talsa.h b/audio/talsa.h index 0b05bfc8..b461d63c 100644 --- a/audio/talsa.h +++ b/audio/talsa.h @@ -33,13 +33,21 @@ struct PcmDeleter { void operator()(pcm_t *x) const; }; typedef std::unique_ptr<pcm_t, PcmDeleter> PcmPtr; PcmPtr pcmOpen(unsigned int dev, unsigned int card, unsigned int nChannels, size_t sampleRateHz, size_t frameCount, bool isOut); -typedef struct mixer mixer_t; -typedef struct mixer_ctl mixer_ctl_t; -struct MixerDeleter { void operator()(struct mixer *m) const; }; -typedef std::unique_ptr<mixer_t, MixerDeleter> MixerPtr; -MixerPtr mixerOpen(unsigned int card); -void mixerSetValueAll(mixer_ctl_t *ctl, int value); -void mixerSetPercentAll(mixer_ctl_t *ctl, int percent); +class Mixer { +public: + Mixer(unsigned card); + ~Mixer(); + + operator bool() const { return mMixer != nullptr; } + + Mixer(const Mixer &) = delete; + Mixer &operator=(const Mixer &) = delete; + Mixer(Mixer &&) = delete; + Mixer &operator=(Mixer &&) = delete; + +private: + struct mixer *mMixer; +}; } // namespace talsa } // namespace implementation diff --git a/audio/util.cpp b/audio/util.cpp index dbe620ba..00678d59 100644 --- a/audio/util.cpp +++ b/audio/util.cpp @@ -16,7 +16,10 @@ #include <log/log.h> #include <cutils/bitops.h> +#include <cutils/sched_policy.h> #include <system/audio.h> +#include <sys/resource.h> +#include <pthread.h> #include "util.h" #include "debug.h" @@ -153,6 +156,11 @@ TimeSpec nsecs2TimeSpec(nsecs_t ns) { return ts; } +void setThreadPriority(int prio) { + setpriority(PRIO_PROCESS, 0, prio); + set_sched_policy(0, SP_FOREGROUND); +} + } // namespace util } // namespace implementation } // namespace V6_0 diff --git a/audio/util.h b/audio/util.h index aae8f535..5337c7b6 100644 --- a/audio/util.h +++ b/audio/util.h @@ -45,6 +45,8 @@ bool checkAudioConfig(bool isOut, TimeSpec nsecs2TimeSpec(nsecs_t); +void setThreadPriority(int prio); + } // namespace util } // namespace implementation } // namespace V6_0 diff --git a/camera/Android.bp b/camera/Android.bp index bc6716c0..e75f72a4 100644 --- a/camera/Android.bp +++ b/camera/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_shared { name: "camera.ranchu", vendor: true, @@ -60,9 +69,7 @@ cc_library_shared { "libdl", "libjpeg", "libcamera_metadata", - "libui", - "android.hardware.graphics.mapper@2.0", - "libqemupipe.ranchu", + "libqemupipe.ranchu", ], static_libs: [ "libqemud.ranchu", diff --git a/camera/EmulatedCamera.cpp b/camera/EmulatedCamera.cpp index 89888f07..90fdc1e4 100755 --- a/camera/EmulatedCamera.cpp +++ b/camera/EmulatedCamera.cpp @@ -701,7 +701,7 @@ status_t EmulatedCamera::setParameters(const char* parms) return NO_ERROR; } -/* A dumb variable indicating "no params" / error on the exit from +/* A variable indicating "no params" / error on the exit from * EmulatedCamera::getParameters(). */ static char lNoParam = '\0'; char* EmulatedCamera::getParameters() diff --git a/camera/EmulatedCamera2.cpp b/camera/EmulatedCamera2.cpp index 72e1c07f..3dd5047d 100644 --- a/camera/EmulatedCamera2.cpp +++ b/camera/EmulatedCamera2.cpp @@ -404,7 +404,8 @@ camera2_device_ops_t EmulatedCamera2::sDeviceOps = { EmulatedCamera2::trigger_action, EmulatedCamera2::set_notify_callback, EmulatedCamera2::get_metadata_vendor_tag_ops, - EmulatedCamera2::dump + EmulatedCamera2::dump, + /* UNUSED: get_instance_metadata */ nullptr }; }; /* namespace android */ diff --git a/camera/EmulatedCamera3.cpp b/camera/EmulatedCamera3.cpp index 0cc373ae..3592b5c0 100644 --- a/camera/EmulatedCamera3.cpp +++ b/camera/EmulatedCamera3.cpp @@ -251,7 +251,10 @@ camera3_device_ops_t EmulatedCamera3::sDeviceOps = { EmulatedCamera3::process_capture_request, /* DEPRECATED: get_metadata_vendor_tag_ops */ nullptr, EmulatedCamera3::dump, - EmulatedCamera3::flush + EmulatedCamera3::flush, + /* UNUSED: signal_stream_flush */ nullptr, + /* UNUSED: is_reconfiguration_required */ nullptr, + /* RESERVED */ { nullptr }, }; const char* EmulatedCamera3::sAvailableCapabilitiesStrings[NUM_CAPABILITIES] = { diff --git a/camera/EmulatedCameraFactory.cpp b/camera/EmulatedCameraFactory.cpp index d4b08f35..fb11b412 100755 --- a/camera/EmulatedCameraFactory.cpp +++ b/camera/EmulatedCameraFactory.cpp @@ -399,7 +399,7 @@ EmulatedCameraFactory::createFakeCameraImpl(bool backCamera, return std::make_unique<EmulatedFakeCamera2>(cameraId, backCamera, module, mGBM); case 3: { - static const char key[] = "ro.kernel.qemu.camera.fake.rotating"; + static const char key[] = "ro.boot.qemu.camera.fake.rotating"; char prop[PROPERTY_VALUE_MAX]; if (property_get(key, prop, nullptr) > 0) { @@ -436,7 +436,7 @@ void EmulatedCameraFactory::createFakeCamera(bool backCamera) { void EmulatedCameraFactory::waitForQemuSfFakeCameraPropertyAvailable() { /* * Camera service may start running before qemu-props sets - * qemu.sf.fake_camera to any of the follwing four values: + * vendor.qemu.sf.fake_camera to any of the following four values: * "none,front,back,both"; so we need to wait. * * android/camera/camera-service.c @@ -446,25 +446,25 @@ void EmulatedCameraFactory::waitForQemuSfFakeCameraPropertyAvailable() { char prop[PROPERTY_VALUE_MAX]; bool timeout = true; for (int i = 0; i < numAttempts; ++i) { - if (property_get("qemu.sf.fake_camera", prop, nullptr) != 0 ) { + if (property_get("vendor.qemu.sf.fake_camera", prop, nullptr) != 0 ) { timeout = false; break; } usleep(5000); } if (timeout) { - ALOGE("timeout (%dms) waiting for property qemu.sf.fake_camera to be set\n", 5 * numAttempts); + ALOGE("timeout (%dms) waiting for property vendor.qemu.sf.fake_camera to be set\n", 5 * numAttempts); } } bool EmulatedCameraFactory::isFakeCameraEmulationOn(bool backCamera) { // Always return false, because another HAL (Google Camera HAL) // will create the fake cameras - if (!property_get_bool("ro.kernel.qemu.legacy_fake_camera", false)) { + if (!property_get_bool("ro.boot.qemu.legacy_fake_camera", false)) { return false; } char prop[PROPERTY_VALUE_MAX]; - if ((property_get("qemu.sf.fake_camera", prop, nullptr) > 0) && + if ((property_get("vendor.qemu.sf.fake_camera", prop, nullptr) > 0) && (!strcmp(prop, "both") || !strcmp(prop, backCamera ? "back" : "front"))) { return true; diff --git a/camera/EmulatedFakeCamera.cpp b/camera/EmulatedFakeCamera.cpp index 0aa159a8..69fabb36 100755 --- a/camera/EmulatedFakeCamera.cpp +++ b/camera/EmulatedFakeCamera.cpp @@ -38,7 +38,7 @@ EmulatedFakeCamera::EmulatedFakeCamera(int cameraId, mFacingBack(facingBack), mFakeCameraDevice(nullptr) { - const char *key = "ro.kernel.qemu.camera.fake.rotating"; + const char *key = "ro.boot.qemu.camera.fake.rotating"; char prop[PROPERTY_VALUE_MAX]; if (property_get(key, prop, nullptr) > 0) { mFakeCameraDevice = new EmulatedFakeRotatingCameraDevice(this); diff --git a/camera/EmulatedFakeCamera3.cpp b/camera/EmulatedFakeCamera3.cpp index 2da2c4da..30592620 100644 --- a/camera/EmulatedFakeCamera3.cpp +++ b/camera/EmulatedFakeCamera3.cpp @@ -362,7 +362,7 @@ status_t EmulatedFakeCamera3::configureStreams( if (newStream->format == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED) { if (newStream->usage & GRALLOC_USAGE_HW_CAMERA_WRITE) { if (newStream->usage & GRALLOC_USAGE_HW_TEXTURE) { - newStream->format = HAL_PIXEL_FORMAT_RGBA_8888; + newStream->format = HAL_PIXEL_FORMAT_YCbCr_420_888; } else if (newStream->usage & GRALLOC_USAGE_HW_VIDEO_ENCODER) { newStream->format = HAL_PIXEL_FORMAT_YCbCr_420_888; @@ -916,7 +916,7 @@ status_t EmulatedFakeCamera3::processCaptureRequest( if (srcBuf.stream->format == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED) { if (srcBuf.stream->usage & GRALLOC_USAGE_HW_CAMERA_WRITE) { if (srcBuf.stream->usage & GRALLOC_USAGE_HW_TEXTURE) { - destBuf.format = HAL_PIXEL_FORMAT_RGBA_8888; + destBuf.format = HAL_PIXEL_FORMAT_YCbCr_420_888; } else if (srcBuf.stream->usage & GRALLOC_USAGE_HW_VIDEO_ENCODER) { destBuf.format = HAL_PIXEL_FORMAT_YCbCr_420_888; @@ -952,7 +952,7 @@ status_t EmulatedFakeCamera3::processCaptureRequest( android_ycbcr ycbcr = {}; res = mGBM->lockYCbCr( *(destBuf.buffer), - GRALLOC_USAGE_HW_CAMERA_WRITE, + GRALLOC_USAGE_SW_READ_OFTEN | GRALLOC_USAGE_SW_WRITE_OFTEN, Rect(0, 0, destBuf.width, destBuf.height), &ycbcr); // This is only valid because we know that emulator's @@ -966,7 +966,7 @@ status_t EmulatedFakeCamera3::processCaptureRequest( } else { res = mGBM->lock( *(destBuf.buffer), - GRALLOC_USAGE_HW_CAMERA_WRITE, + GRALLOC_USAGE_SW_READ_OFTEN | GRALLOC_USAGE_SW_WRITE_OFTEN, Rect(0, 0, destBuf.width, destBuf.height), (void**)&(destBuf.img)); diff --git a/camera/EmulatedFakeCamera3.h b/camera/EmulatedFakeCamera3.h index 9a933a94..86331658 100644 --- a/camera/EmulatedFakeCamera3.h +++ b/camera/EmulatedFakeCamera3.h @@ -225,7 +225,7 @@ private: private: static const nsecs_t kWaitPerLoop = 10000000L; // 10 ms static const nsecs_t kMaxWaitLoops = 1000; - static const size_t kMaxQueueSize = 2; + static const size_t kMaxQueueSize = 4; EmulatedFakeCamera3 *mParent; Mutex mLock; diff --git a/camera/EmulatedFakeRotatingCameraDevice.cpp b/camera/EmulatedFakeRotatingCameraDevice.cpp index 39148823..6220084f 100755 --- a/camera/EmulatedFakeRotatingCameraDevice.cpp +++ b/camera/EmulatedFakeRotatingCameraDevice.cpp @@ -34,7 +34,6 @@ #include <stdio.h> #include <stdlib.h> #include <math.h> -#include <ui/DisplayInfo.h> #include <fcntl.h> #undef min diff --git a/camera/EmulatedQemuCamera3.cpp b/camera/EmulatedQemuCamera3.cpp index 991d9283..44517a47 100644 --- a/camera/EmulatedQemuCamera3.cpp +++ b/camera/EmulatedQemuCamera3.cpp @@ -46,7 +46,6 @@ #include <vector> namespace android { - /* * Constants for Camera Capabilities */ @@ -88,7 +87,6 @@ EmulatedQemuCamera3::EmulatedQemuCamera3(int cameraId, struct hw_module_t* modul GraphicBufferMapper* gbm) : EmulatedCamera3(cameraId, module), mGBM(gbm) { ALOGI("Constructing emulated qemu camera 3: ID %d", mCameraID); - for (size_t i = 0; i < CAMERA3_TEMPLATE_COUNT; ++i) { mDefaultTemplates[i] = nullptr; } @@ -942,7 +940,9 @@ status_t EmulatedQemuCamera3::processCaptureRequest( android_ycbcr ycbcr = {}; res = mGBM->lockYCbCr( *(destBuf.buffer), - GRALLOC_USAGE_HW_CAMERA_WRITE, + GRALLOC_USAGE_HW_CAMERA_WRITE | + GRALLOC_USAGE_SW_READ_OFTEN | + GRALLOC_USAGE_SW_WRITE_OFTEN, Rect(0, 0, destBuf.width, destBuf.height), &ycbcr); /* @@ -958,7 +958,9 @@ status_t EmulatedQemuCamera3::processCaptureRequest( } else { res = mGBM->lock( *(destBuf.buffer), - GRALLOC_USAGE_HW_CAMERA_WRITE, + GRALLOC_USAGE_HW_CAMERA_WRITE | + GRALLOC_USAGE_SW_READ_OFTEN | + GRALLOC_USAGE_SW_WRITE_OFTEN, Rect(0, 0, destBuf.width, destBuf.height), (void**)&(destBuf.img)); diff --git a/camera/EmulatedQemuCamera3.h b/camera/EmulatedQemuCamera3.h index 3461e3ea..c554accc 100644 --- a/camera/EmulatedQemuCamera3.h +++ b/camera/EmulatedQemuCamera3.h @@ -226,7 +226,7 @@ private: private: static const nsecs_t kWaitPerLoop = 10000000L; // 10 ms static const nsecs_t kMaxWaitLoops = 1000; - static const size_t kMaxQueueSize = 2; + static const size_t kMaxQueueSize = 4; EmulatedQemuCamera3 *mParent; Mutex mLock; diff --git a/camera/Exif.cpp b/camera/Exif.cpp index 0f451ffd..9e9f159c 100644 --- a/camera/Exif.cpp +++ b/camera/Exif.cpp @@ -233,11 +233,11 @@ static bool getCameraParam(const CameraParameters& parameters, int64_t* outValue) { const char* value = parameters.get(parameterKey); if (value) { - char dummy = 0; + char trailing = 0; // Attempt to scan an extra character and then make sure it was not // scanned by checking that the return value indicates only one item. // This way we fail on any trailing characters - if (sscanf(value, "%" SCNd64 "%c", outValue, &dummy) == 1) { + if (sscanf(value, "%" SCNd64 "%c", outValue, &trailing) == 1) { return true; } } diff --git a/camera/QemuClient.cpp b/camera/QemuClient.cpp index cceca04e..6fa143d7 100755 --- a/camera/QemuClient.cpp +++ b/camera/QemuClient.cpp @@ -21,6 +21,7 @@ #define LOG_NDEBUG 1 #define LOG_TAG "EmulatedCamera_QemuClient" +#include <inttypes.h> #include <log/log.h> #include "EmulatedCamera.h" #include "QemuClient.h" @@ -576,11 +577,11 @@ status_t CameraQemuClient::queryFrame(int width, float exposure_comp, int64_t* frame_time) { - ALOGV("%s: w %d h %d %.4s offset 0x%llx", __FUNCTION__, width, height, + ALOGV("%s: w %d h %d %.4s offset 0x%" PRIu64 "", __FUNCTION__, width, height, (char*)(&pixel_format), offset); char query_str[256]; - snprintf(query_str, sizeof(query_str), "%s dim=%dx%d pix=%d offset=%llu whiteb=%g,%g,%g expcomp=%g time=%d", + snprintf(query_str, sizeof(query_str), "%s dim=%dx%d pix=%d offset=%" PRIu64 " whiteb=%g,%g,%g expcomp=%g time=%d", mQueryFrame, width, height, pixel_format, offset, r_scale, g_scale, b_scale, exposure_comp, frame_time != nullptr ? 1 : 0); diff --git a/camera/fake-pipeline2/Sensor.cpp b/camera/fake-pipeline2/Sensor.cpp index 064f48f4..dc2e97de 100644 --- a/camera/fake-pipeline2/Sensor.cpp +++ b/camera/fake-pipeline2/Sensor.cpp @@ -32,6 +32,7 @@ #include "Sensor.h" #include <cmath> #include <cstdlib> +#include <cutils/properties.h> #include "system/camera_metadata.h" namespace android { @@ -96,7 +97,25 @@ float sqrtf_approx(float r) { return *(float*)(&r_i); } +#define GRALLOC_PROP "ro.hardware.gralloc" +static bool getIsMinigbmFromProperty() { + char grallocValue[PROPERTY_VALUE_MAX] = ""; + property_get(GRALLOC_PROP, grallocValue, ""); + bool isValid = grallocValue[0] != '\0'; + + if (!isValid) return false; + + bool res = 0 == strcmp("minigbm", grallocValue); + + if (res) { + ALOGV("%s: Is using minigbm, in minigbm mode.\n", __func__); + } else { + ALOGV("%s: Is not using minigbm, in goldfish mode.\n", __func__); + } + + return res; +} Sensor::Sensor(uint32_t width, uint32_t height): Thread(false), @@ -107,10 +126,11 @@ Sensor::Sensor(uint32_t width, uint32_t height): mExposureTime(kFrameDurationRange[0]-kMinVerticalBlank), mFrameDuration(kFrameDurationRange[0]), mGainFactor(kDefaultSensitivity), - mNextBuffers(NULL), + mNextBuffers(nullptr), mFrameNumber(0), - mCapturedBuffers(NULL), - mListener(NULL), + mCapturedBuffers(nullptr), + mListener(nullptr), + mIsMinigbm(getIsMinigbmFromProperty()), mSceneWidth((width < Scene::kMaxWidth) ? width : Scene::kMaxWidth), mSceneHeight((height < Scene::kMaxHeight) ? height : Scene::kMaxHeight), mScene(mSceneWidth, mSceneHeight, kElectronsPerLuxSecond) @@ -353,7 +373,11 @@ bool Sensor::threadLoop() { } break; case HAL_PIXEL_FORMAT_YCbCr_420_888: - captureYU12(b.img, gain, b.width, b.height); + if (mIsMinigbm) { + captureNV12(b.img, gain, b.width, b.height); + } else { + captureYU12(b.img, gain, b.width, b.height); + } break; case HAL_PIXEL_FORMAT_YV12: // TODO: @@ -562,7 +586,65 @@ void Sensor::captureYU12(uint8_t *img, uint32_t gain, uint32_t width, uint32_t h } } } - ALOGVV("YU21 sensor image captured"); + ALOGVV("YU12 sensor image captured"); +} + +void Sensor::captureNV12(uint8_t *img, uint32_t gain, uint32_t width, uint32_t height) { + ATRACE_CALL(); + float totalGain = gain/100.0 * kBaseGainFactor; + // Using fixed-point math with 6 bits of fractional precision. + // In fixed-point math, calculate total scaling from electrons to 8bpp + const int scale64x = 64 * totalGain * 255 / kMaxRawValue; + // In fixed-point math, saturation point of sensor after gain + const int saturationPoint = 64 * 255; + // Fixed-point coefficients for RGB-YUV transform + // Based on JFIF RGB->YUV transform. + // Cb/Cr offset scaled by 64x twice since they're applied post-multiply + float rgbToY[] = {19.0, 37.0, 7.0, 0.0}; + float rgbToCb[] = {-10.0,-21.0, 32.0, 524288.0}; + float rgbToCr[] = {32.0,-26.0, -5.0, 524288.0}; + // Scale back to 8bpp non-fixed-point + const int scaleOut = 64; + const int scaleOutSq = scaleOut * scaleOut; // after multiplies + const double invscaleOutSq = 1.0/scaleOutSq; + for (int i=0; i < 4; ++i) { + rgbToY[i] *= invscaleOutSq; + rgbToCb[i] *= invscaleOutSq; + rgbToCr[i] *= invscaleOutSq; + } + + unsigned int DivH= (float)mSceneHeight/height * (0x1 << 10); + unsigned int DivW = (float)mSceneWidth/width * (0x1 << 10); + for (unsigned int outY = 0; outY < height; outY++) { + unsigned int y = outY * DivH >> 10; + uint8_t *pxY = img + outY * width; + uint8_t *pxVU = img + (height + outY / 2) * width; + mScene.setReadoutPixel(0, y); + unsigned int lastX = 0; + const uint32_t *pixel = mScene.getPixelElectrons(); + for (unsigned int outX = 0; outX < width; outX++) { + int32_t rCount, gCount, bCount; + unsigned int x = outX * DivW >> 10; + if (x - lastX > 0) { + for (unsigned int k = 0; k < (x-lastX); k++) { + pixel = mScene.getPixelElectrons(); + } + } + lastX = x; + rCount = pixel[Scene::R] * scale64x; + rCount = rCount < saturationPoint ? rCount : saturationPoint; + gCount = pixel[Scene::Gr] * scale64x; + gCount = gCount < saturationPoint ? gCount : saturationPoint; + bCount = pixel[Scene::B] * scale64x; + bCount = bCount < saturationPoint ? bCount : saturationPoint; + *pxY++ = (rgbToY[0] * rCount + rgbToY[1] * gCount + rgbToY[2] * bCount); + if (outY % 2 == 0 && outX % 2 == 0) { + *pxVU++ = (rgbToCb[0] * rCount + rgbToCb[1] * gCount + rgbToCb[2] * bCount + rgbToCb[3]); + *pxVU++ = (rgbToCr[0] * rCount + rgbToCr[1] * gCount + rgbToCr[2] * bCount + rgbToCr[3]); + } + } + } + ALOGVV("NV12 sensor image captured"); } void Sensor::captureDepth(uint8_t *img, uint32_t gain, uint32_t width, uint32_t height) { diff --git a/camera/fake-pipeline2/Sensor.h b/camera/fake-pipeline2/Sensor.h index 0dc99622..d2400e60 100644 --- a/camera/fake-pipeline2/Sensor.h +++ b/camera/fake-pipeline2/Sensor.h @@ -81,7 +81,6 @@ #include "Scene.h" #include "Base.h" - namespace android { class EmulatedFakeCamera2; @@ -219,6 +218,8 @@ class Sensor: private Thread, public virtual RefBase { // Time of sensor startup, used for simulation zero-time point nsecs_t mStartupTime; + bool mIsMinigbm; + /** * Inherited Thread virtual overrides, and members only used by the * processing thread @@ -239,6 +240,7 @@ class Sensor: private Thread, public virtual RefBase { void captureRGBA(uint8_t *img, uint32_t gain, uint32_t width, uint32_t height); void captureRGB(uint8_t *img, uint32_t gain, uint32_t width, uint32_t height); void captureYU12(uint8_t *img, uint32_t gain, uint32_t width, uint32_t height); + void captureNV12(uint8_t *img, uint32_t gain, uint32_t width, uint32_t height); void captureDepth(uint8_t *img, uint32_t gain, uint32_t width, uint32_t height); void captureDepthCloud(uint8_t *img); diff --git a/camera/jpeg-stub/Android.bp b/camera/jpeg-stub/Android.bp index 8fb142ff..b2fbd954 100644 --- a/camera/jpeg-stub/Android.bp +++ b/camera/jpeg-stub/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_shared { name: "camera.ranchu.jpeg", vendor: true, diff --git a/camera/media_codecs.xml b/camera/media_codecs.xml index 81cffc93..f226fbf7 100644 --- a/camera/media_codecs.xml +++ b/camera/media_codecs.xml @@ -92,6 +92,16 @@ Only the three quirks included above are recognized at this point: <Limit name="concurrent-instances" max="4" /> </MediaCodec> + <MediaCodec name="c2.goldfish.h264.decoder" type="video/avc" > + <Limit name="concurrent-instances" max="4" /> + </MediaCodec> + <MediaCodec name="c2.goldfish.vp8.decoder" type="video/x-vnd.on2.vp8" > + <Limit name="concurrent-instances" max="4" /> + </MediaCodec> + <MediaCodec name="c2.goldfish.vp9.decoder" type="video/x-vnd.on2.vp9" > + <Limit name="concurrent-instances" max="4" /> + </MediaCodec> + <Include href="media_codecs_google_audio.xml" /> <Include href="media_codecs_google_telephony.xml" /> <Include href="media_codecs_google_video.xml" /> diff --git a/camera/media_codecs_google_video_default.xml b/camera/media_codecs_google_video_default.xml index 588ead52..1a0ee971 100644 --- a/camera/media_codecs_google_video_default.xml +++ b/camera/media_codecs_google_video_default.xml @@ -50,6 +50,21 @@ <Limit name="measured-frame-rate-3840x2160" range="235-247" /> <Feature name="adaptive-playback" /> </MediaCodec> + <MediaCodec name="c2.goldfish.h264.decoder" type="video/avc"> + <Limit name="size" min="96x96" max="4096x4096" /> + <Limit name="alignment" value="2x2" /> + <Limit name="block-size" value="16x16" /> + <Limit name="blocks-per-second" range="24-2073600" /> + <Limit name="bitrate" range="1-120000000" /> + <Limit name="frame-rate" range="1-480" /> + <Limit name="performance-point-3840x2160" value="30" /> + <Limit name="measured-frame-rate-320x240" range="1000-1500" /> + <Limit name="measured-frame-rate-720x480" range="400-800" /> + <Limit name="measured-frame-rate-1280x720" range="227-251" /> + <Limit name="measured-frame-rate-1920x1080" range="235-247" /> + <Limit name="measured-frame-rate-3840x2160" range="235-247" /> + <Feature name="adaptive-playback" /> + </MediaCodec> <MediaCodec name="OMX.google.h264.decoder" type="video/avc"> <Limit name="size" min="2x2" max="2560x2560" /> <Limit name="alignment" value="2x2" /> @@ -106,6 +121,36 @@ <Limit name="measured-frame-rate-3840x2160" range="30-90" /> <Feature name="adaptive-playback" /> </MediaCodec> + <MediaCodec name="c2.goldfish.vp8.decoder" type="video/x-vnd.on2.vp8"> + <Limit name="size" min="96x96" max="3840x2160" /> + <Limit name="alignment" value="2x2" /> + <Limit name="block-size" value="16x16" /> + <Limit name="blocks-per-second" min="24" max="2073600" /> + <Limit name="bitrate" range="1-120000000" /> + <Limit name="frame-rate" range="1-480" /> + <Limit name="performance-point-3840x2160" value="30" /> + <Limit name="measured-frame-rate-320x180" range="743-817" /> + <Limit name="measured-frame-rate-640x360" range="237-258" /> + <Limit name="measured-frame-rate-1280x720" range="60-160" /> + <Limit name="measured-frame-rate-1920x1080" range="30-160" /> + <Limit name="measured-frame-rate-3840x2160" range="30-90" /> + <Feature name="adaptive-playback" /> + </MediaCodec> + <MediaCodec name="c2.goldfish.vp9.decoder" type="video/x-vnd.on2.vp9"> + <Limit name="size" min="96x96" max="3840x2160" /> + <Limit name="alignment" value="2x2" /> + <Limit name="block-size" value="16x16" /> + <Limit name="blocks-per-second" min="24" max="2073600" /> + <Limit name="bitrate" range="1-120000000" /> + <Limit name="frame-rate" range="1-480" /> + <Limit name="performance-point-3840x2160" value="30" /> + <Limit name="measured-frame-rate-320x180" range="237-258" /> + <Limit name="measured-frame-rate-640x360" range="237-258" /> + <Limit name="measured-frame-rate-1280x720" range="237-258" /> + <Limit name="measured-frame-rate-1920x1080" range="293-302" /> + <Limit name="measured-frame-rate-3840x2160" range="30-90" /> + <Feature name="adaptive-playback" /> + </MediaCodec> <MediaCodec name="OMX.google.vp8.decoder" type="video/x-vnd.on2.vp8"> <Limit name="size" min="2x2" max="2560x2560" /> <Limit name="alignment" value="2x2" /> diff --git a/camera/media_codecs_performance_c2.xml b/camera/media_codecs_performance_c2.xml new file mode 100644 index 00000000..7c0268e2 --- /dev/null +++ b/camera/media_codecs_performance_c2.xml @@ -0,0 +1,93 @@ +<?xml version="1.0" encoding="utf-8" ?> +<!-- Copyright 2020 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. +--> + +<MediaCodecs> + <Decoders> + + <MediaCodec name="c2.android.avc.decoder" type="video/avc" update="true"> + <Limit name="measured-frame-rate-320x240" range="486-504" /> <!-- N=50 v96%=1.3 --> + <Limit name="measured-frame-rate-720x480" range="128-130" /> <!-- v90%=1.0 --> + <Limit name="measured-frame-rate-1280x720" range="48-49" /> <!-- v90%=1.0 --> + <Limit name="measured-frame-rate-1920x1080" range="22-22" /> <!-- v90%=1.0 --> + </MediaCodec> + <MediaCodec name="c2.android.hevc.decoder" type="video/hevc" update="true"> + <Limit name="measured-frame-rate-352x288" range="469-485" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-640x360" range="267-275" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-720x480" range="248-248" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-1280x720" range="103-105" /> <!-- v90%=1.0 --> + <Limit name="measured-frame-rate-1920x1080" range="57-58" /> <!-- v90%=1.0 --> + </MediaCodec> + <MediaCodec name="c2.android.vp8.decoder" type="video/x-vnd.on2.vp8" update="true"> + <!-- measured 90%:799-924 med:815 N=12 --> + <Limit name="measured-frame-rate-320x180" range="814-859" /> <!-- v90%=1.1 --> + <!-- measured 90%:338-379 med:345 N=12 --> + <Limit name="measured-frame-rate-640x360" range="344-358" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-1280x720" range="88-92" /> <!-- N=50 v90%=1.1 --> + <!-- measured 90%:35-40 med:36 N=12 --> + <Limit name="measured-frame-rate-1920x1080" range="35-37" /> <!-- v90%=1.1 --> + </MediaCodec> + <MediaCodec name="c2.android.vp9.decoder" type="video/x-vnd.on2.vp9" update="true"> + <!-- measured 90%:621-650 med:634 N=12 --> + <Limit name="measured-frame-rate-320x180" range="633-635" /> <!-- v90%=1.0 --> + <!-- measured 90%:225-231 med:228 N=12 --> + <Limit name="measured-frame-rate-640x360" range="228-228" /> <!-- v90%=1.0 --> + <!-- measured 90%:91-94 med:93 N=12 --> + <Limit name="measured-frame-rate-1280x720" range="92-93" /> <!-- v90%=1.0 --> + <!-- measured 90%:56-58 med:57 N=12 --> + <Limit name="measured-frame-rate-1920x1080" range="57-57" /> <!-- v90%=1.0 --> + </MediaCodec> + <MediaCodec name="c2.android.h263.decoder" type="video/3gpp" update="true"> + <!-- measured 90%:1219-1704 med:1479 N=12 --> + <Limit name="measured-frame-rate-176x144" range="1441-1441" /> <!-- v90%=1.2 --> + <!-- measured 96%:889-1227 med:922 SLOW --> + <Limit name="measured-frame-rate-352x288" range="921-1045" /> <!-- N=50 v96%=1.2 --> + </MediaCodec> + <MediaCodec name="c2.android.mpeg4.decoder" type="video/mp4v-es" update="true"> + <!-- measured 90%:1298-1653 med:1316 SLOW N=12 --> + <Limit name="measured-frame-rate-176x144" range="1315-1465" /> <!-- v90%=1.1 --> + </MediaCodec> + </Decoders> + + <Encoders> + + <MediaCodec name="c2.android.h263.encoder" type="video/3gpp" update="true"> + <Limit name="measured-frame-rate-176x144" range="287-459" /> <!-- TWEAKED N=224 --> + </MediaCodec> + <MediaCodec name="c2.android.avc.encoder" type="video/avc" update="true"> + <Limit name="measured-frame-rate-320x240" range="287-326" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-720x480" range="122-124" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1280x720" range="76-80" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1920x1080" range="44-49" /> <!-- Manual N=20 --> + </MediaCodec> + <MediaCodec name="c2.android.hevc.encoder" type="video/hevc" update="true"> + <Limit name="measured-frame-rate-320x240" range="47-60" /> <!-- Manual N=20 --> + </MediaCodec> + <MediaCodec name="c2.android.mpeg4.encoder" type="video/mp4v-es" update="true"> + <Limit name="measured-frame-rate-176x144" range="203-445" /> <!-- SHOULDN'T HAVE TWEAKED N=220 v90%=4.0 --> + </MediaCodec> + <MediaCodec name="c2.android.vp8.encoder" type="video/x-vnd.on2.vp8" update="true"> + <Limit name="measured-frame-rate-320x180" range="178-245" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-640x360" range="100-126" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1280x720" range="35-37" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1920x1080" range="24-31" /> <!-- Manual N=20 --> + </MediaCodec> + <MediaCodec name="c2.android.vp9.encoder" type="video/x-vnd.on2.vp9" update="true"> + <Limit name="measured-frame-rate-320x180" range="109-109" /> <!-- v93%=1.3 --> + <Limit name="measured-frame-rate-640x360" range="61-61" /> <!-- v95%=1.1 --> + <Limit name="measured-frame-rate-1280x720" range="20-20" /> <!-- v95%=1.3 --> + </MediaCodec> + </Encoders> +</MediaCodecs> diff --git a/camera/media_codecs_performance_c2_arm64.xml b/camera/media_codecs_performance_c2_arm64.xml new file mode 100644 index 00000000..2d207cf5 --- /dev/null +++ b/camera/media_codecs_performance_c2_arm64.xml @@ -0,0 +1,93 @@ +<?xml version="1.0" encoding="utf-8" ?> +<!-- Copyright 2020 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. +--> + +<MediaCodecs> + <Decoders> + + <MediaCodec name="c2.android.avc.decoder" type="video/avc" update="true"> + <Limit name="measured-frame-rate-320x240" range="486-504" /> <!-- N=50 v96%=1.3 --> + <Limit name="measured-frame-rate-720x480" range="360-410" /> <!-- v90%=1.0 --> + <Limit name="measured-frame-rate-1280x720" range="150-170" /> <!-- v90%=1.0 --> + <Limit name="measured-frame-rate-1920x1080" range="70-90" /> <!-- v90%=1.0 --> + </MediaCodec> + <MediaCodec name="c2.android.hevc.decoder" type="video/hevc" update="true"> + <Limit name="measured-frame-rate-352x288" range="469-485" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-640x360" range="267-275" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-720x480" range="248-248" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-1280x720" range="220-260" /> <!-- v90%=1.0 --> + <Limit name="measured-frame-rate-1920x1080" range="130-170" /> <!-- v90%=1.0 --> + </MediaCodec> + <MediaCodec name="c2.android.vp8.decoder" type="video/x-vnd.on2.vp8" update="true"> + <!-- measured 90%:799-924 med:815 N=12 --> + <Limit name="measured-frame-rate-320x180" range="814-859" /> <!-- v90%=1.1 --> + <!-- measured 90%:338-379 med:345 N=12 --> + <Limit name="measured-frame-rate-640x360" range="344-358" /> <!-- v90%=1.1 --> + <Limit name="measured-frame-rate-1280x720" range="88-92" /> <!-- N=50 v90%=1.1 --> + <!-- measured 90%:35-40 med:36 N=12 --> + <Limit name="measured-frame-rate-1920x1080" range="35-37" /> <!-- v90%=1.1 --> + </MediaCodec> + <MediaCodec name="c2.android.vp9.decoder" type="video/x-vnd.on2.vp9" update="true"> + <!-- measured 90%:621-650 med:634 N=12 --> + <Limit name="measured-frame-rate-320x180" range="633-635" /> <!-- v90%=1.0 --> + <!-- measured 90%:225-231 med:228 N=12 --> + <Limit name="measured-frame-rate-640x360" range="520-580" /> <!-- v90%=1.0 --> + <!-- measured 90%:91-94 med:93 N=12 --> + <Limit name="measured-frame-rate-1280x720" range="220-260" /> <!-- v90%=1.0 --> + <!-- measured 90%:56-58 med:57 N=12 --> + <Limit name="measured-frame-rate-1920x1080" range="120-160" /> <!-- v90%=1.0 --> + </MediaCodec> + <MediaCodec name="c2.android.h263.decoder" type="video/3gpp" update="true"> + <!-- measured 90%:1219-1704 med:1479 N=12 --> + <Limit name="measured-frame-rate-176x144" range="1441-1441" /> <!-- v90%=1.2 --> + <!-- measured 96%:889-1227 med:922 SLOW --> + <Limit name="measured-frame-rate-352x288" range="921-1045" /> <!-- N=50 v96%=1.2 --> + </MediaCodec> + <MediaCodec name="c2.android.mpeg4.decoder" type="video/mp4v-es" update="true"> + <!-- measured 90%:1298-1653 med:1316 SLOW N=12 --> + <Limit name="measured-frame-rate-176x144" range="1315-1465" /> <!-- v90%=1.1 --> + </MediaCodec> + </Decoders> + + <Encoders> + + <MediaCodec name="c2.android.h263.encoder" type="video/3gpp" update="true"> + <Limit name="measured-frame-rate-176x144" range="2200-2500" /> <!-- TWEAKED N=224 --> + </MediaCodec> + <MediaCodec name="c2.android.avc.encoder" type="video/avc" update="true"> + <Limit name="measured-frame-rate-320x240" range="1200-1400" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-720x480" range="660-720" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1280x720" range="420-500" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1920x1080" range="220-280" /> <!-- Manual N=20 --> + </MediaCodec> + <MediaCodec name="c2.android.hevc.encoder" type="video/hevc" update="true"> + <Limit name="measured-frame-rate-320x240" range="160-210" /> <!-- Manual N=20 --> + </MediaCodec> + <MediaCodec name="c2.android.mpeg4.encoder" type="video/mp4v-es" update="true"> + <Limit name="measured-frame-rate-176x144" range="2200-2500" /> <!-- SHOULDN'T HAVE TWEAKED N=220 v90%=4.0 --> + </MediaCodec> + <MediaCodec name="c2.android.vp8.encoder" type="video/x-vnd.on2.vp8" update="true"> + <Limit name="measured-frame-rate-320x180" range="750-800" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-640x360" range="420-480" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1280x720" range="100-130" /> <!-- Manual N=20 --> + <Limit name="measured-frame-rate-1920x1080" range="24-31" /> <!-- Manual N=20 --> + </MediaCodec> + <MediaCodec name="c2.android.vp9.encoder" type="video/x-vnd.on2.vp9" update="true"> + <Limit name="measured-frame-rate-320x180" range="109-109" /> <!-- v93%=1.3 --> + <Limit name="measured-frame-rate-640x360" range="61-61" /> <!-- v95%=1.1 --> + <Limit name="measured-frame-rate-1280x720" range="20-20" /> <!-- v95%=1.3 --> + </MediaCodec> + </Encoders> +</MediaCodecs> diff --git a/camera/qemu-pipeline3/QemuSensor.cpp b/camera/qemu-pipeline3/QemuSensor.cpp index 7066b6b4..e5bf18d6 100644 --- a/camera/qemu-pipeline3/QemuSensor.cpp +++ b/camera/qemu-pipeline3/QemuSensor.cpp @@ -52,7 +52,27 @@ const nsecs_t QemuSensor::kMinVerticalBlank = 10000L; const int32_t QemuSensor::kSensitivityRange[2] = {100, 1600}; const uint32_t QemuSensor::kDefaultSensitivity = 100; -const char QemuSensor::kHostCameraVerString[] = "ro.kernel.qemu.camera_protocol_ver"; +const char QemuSensor::kHostCameraVerString[] = "ro.boot.qemu.camera_protocol_ver"; + +#define GRALLOC_PROP "ro.hardware.gralloc" + +static bool getIsMinigbmFromProperty() { + char grallocValue[PROPERTY_VALUE_MAX] = ""; + property_get(GRALLOC_PROP, grallocValue, ""); + bool isValid = grallocValue[0] != '\0'; + + if (!isValid) return false; + + bool res = 0 == strcmp("minigbm", grallocValue); + + if (res) { + ALOGV("%s: Is using minigbm, in minigbm mode.\n", __func__); + } else { + ALOGV("%s: Is not using minigbm, in goldfish mode.\n", __func__); + } + + return res; +} QemuSensor::QemuSensor(const char *deviceName, uint32_t width, uint32_t height, GraphicBufferMapper* gbm): @@ -71,7 +91,8 @@ QemuSensor::QemuSensor(const char *deviceName, uint32_t width, uint32_t height, mNextBuffers(nullptr), mFrameNumber(0), mCapturedBuffers(nullptr), - mListener(nullptr) { + mListener(nullptr), + mIsMinigbm(getIsMinigbmFromProperty()) { mHostCameraVer = property_get_int32(kHostCameraVerString, 0); ALOGV("QemuSensor created with pixel array %d x %d", width, height); } @@ -292,7 +313,7 @@ bool QemuSensor::threadLoop() { captureRGB(b.img, b.width, b.height, b.stride, ×tamp); break; case HAL_PIXEL_FORMAT_RGBA_8888: - if (mHostCameraVer == 1) { + if (mHostCameraVer == 1 && !mIsMinigbm) { captureRGBA(b.width, b.height, b.stride, ×tamp, b.buffer); } else { captureRGBA(b.img, b.width, b.height, b.stride, ×tamp); @@ -312,7 +333,7 @@ bool QemuSensor::threadLoop() { bAux.height = b.height; bAux.format = HAL_PIXEL_FORMAT_YCbCr_420_888; bAux.stride = b.width; - if (mHostCameraVer == 1) { + if (mHostCameraVer == 1 && !mIsMinigbm) { const uint64_t usage = GRALLOC_USAGE_HW_CAMERA_READ | GRALLOC_USAGE_HW_CAMERA_WRITE | @@ -349,7 +370,7 @@ bool QemuSensor::threadLoop() { } break; case HAL_PIXEL_FORMAT_YCbCr_420_888: - if (mHostCameraVer == 1) { + if (mHostCameraVer == 1 && !mIsMinigbm) { captureYU12(b.width, b.height, b.stride, ×tamp, b.buffer); } else { captureYU12(b.img, b.width, b.height, b.stride, ×tamp); @@ -532,7 +553,7 @@ void QemuSensor::captureYU12(uint8_t *img, uint32_t width, uint32_t height, uint * and asks for the video format from the pixFmt parameter, which is * V4L2_PIX_FMT_YUV420 in our implementation. */ - uint32_t pixFmt = V4L2_PIX_FMT_YUV420; + uint32_t pixFmt = mIsMinigbm ? V4L2_PIX_FMT_NV12 : V4L2_PIX_FMT_YUV420; res = mCameraQemuClient.queryStart(pixFmt, width, height); if (res == NO_ERROR) { mLastRequestWidth = width; diff --git a/camera/qemu-pipeline3/QemuSensor.h b/camera/qemu-pipeline3/QemuSensor.h index a73e4bbd..e510dcaa 100644 --- a/camera/qemu-pipeline3/QemuSensor.h +++ b/camera/qemu-pipeline3/QemuSensor.h @@ -177,6 +177,7 @@ class QemuSensor: private Thread, public virtual RefBase { // Time of sensor startup (used for simulation zero-time point). nsecs_t mStartupTime; int32_t mHostCameraVer; + bool mIsMinigbm; private: /* diff --git a/car/AndroidProducts.mk b/car/AndroidProducts.mk new file mode 100644 index 00000000..7883584a --- /dev/null +++ b/car/AndroidProducts.mk @@ -0,0 +1,29 @@ +# +# Copyright (C) 2017 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. +# + +PRODUCT_MAKEFILES := \ + $(LOCAL_DIR)/sdk_car_arm64.mk \ + $(LOCAL_DIR)/sdk_car_arm.mk \ + $(LOCAL_DIR)/sdk_car_x86.mk \ + $(LOCAL_DIR)/sdk_car_x86_64.mk \ + +COMMON_LUNCH_CHOICES := \ + sdk_car_arm-userdebug \ + sdk_car_arm64-userdebug \ + sdk_car_x86-userdebug \ + sdk_car_x86_64-userdebug \ + +EMULATOR_VENDOR_NO_SOUND_TRIGGER := false diff --git a/car/sdk_car_arm.mk b/car/sdk_car_arm.mk new file mode 100644 index 00000000..4a69a771 --- /dev/null +++ b/car/sdk_car_arm.mk @@ -0,0 +1,25 @@ +# +# Copyright (C) 2021 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. + +PRODUCT_PACKAGE_OVERLAYS := device/generic/car/common/overlay + +$(call inherit-product, device/generic/car/emulator/aosp_car_emulator.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/sdk.mk) + +EMULATOR_VENDOR_NO_SOUND := true +PRODUCT_NAME := sdk_car_arm +PRODUCT_DEVICE := emulator_arm +PRODUCT_BRAND := Android +PRODUCT_MODEL := Car on ARM emulator diff --git a/car/sdk_car_arm64.mk b/car/sdk_car_arm64.mk new file mode 100644 index 00000000..41ed1b2f --- /dev/null +++ b/car/sdk_car_arm64.mk @@ -0,0 +1,25 @@ +# +# 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. + +PRODUCT_PACKAGE_OVERLAYS := device/generic/car/common/overlay + +$(call inherit-product, device/generic/car/emulator/aosp_car_emulator.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/sdk_arm64.mk) + +EMULATOR_VENDOR_NO_SOUND := true +PRODUCT_NAME := sdk_car_arm64 +PRODUCT_DEVICE := emulator_arm64 +PRODUCT_BRAND := Android +PRODUCT_MODEL := Car on arm64 emulator diff --git a/car/sdk_car_x86.mk b/car/sdk_car_x86.mk new file mode 100644 index 00000000..5fa54e8a --- /dev/null +++ b/car/sdk_car_x86.mk @@ -0,0 +1,25 @@ +# +# 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. + +PRODUCT_PACKAGE_OVERLAYS := device/generic/car/common/overlay + +$(call inherit-product, device/generic/car/emulator/aosp_car_emulator.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/sdk_x86.mk) + +EMULATOR_VENDOR_NO_SOUND := true +PRODUCT_NAME := sdk_car_x86 +PRODUCT_DEVICE := emulator_x86 +PRODUCT_BRAND := Android +PRODUCT_MODEL := Car on x86 emulator diff --git a/car/sdk_car_x86_64.mk b/car/sdk_car_x86_64.mk new file mode 100644 index 00000000..5f70e64d --- /dev/null +++ b/car/sdk_car_x86_64.mk @@ -0,0 +1,25 @@ +# +# 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. + +PRODUCT_PACKAGE_OVERLAYS := device/generic/car/common/overlay + +$(call inherit-product, device/generic/car/emulator/aosp_car_emulator.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/sdk_x86_64.mk) + +EMULATOR_VENDOR_NO_SOUND := true +PRODUCT_NAME := sdk_car_x86_64 +PRODUCT_DEVICE := emulator_x86_64 +PRODUCT_BRAND := Android +PRODUCT_MODEL := Car on x86_64 emulator diff --git a/data/etc/Android.bp b/data/etc/Android.bp new file mode 100644 index 00000000..d87c1c9f --- /dev/null +++ b/data/etc/Android.bp @@ -0,0 +1,48 @@ +// Copyright (C) 2020 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 { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + +cc_prebuilt_binary { + name: "emulatorip", + arch: { + arm64: { + srcs: ["arm64/emulatorip"], + }, + x86: { + srcs: ["x86/emulatorip"], + }, + x86_64: { + srcs: ["x86_64/emulatorip"], + }, + }, + stem: "ip", + shared_libs: [ + "libc", + "libc++", + "libdl", + "libm", + ], + vendor: true, + strip: { + none: true, + }, +} diff --git a/data/etc/advancedFeatures.ini b/data/etc/advancedFeatures.ini index 73a8fc25..48227135 100644 --- a/data/etc/advancedFeatures.ini +++ b/data/etc/advancedFeatures.ini @@ -5,12 +5,13 @@ GLESDynamicVersion = on GLDMA = on EncryptUserData = on IntelPerformanceMonitoringUnit = on -Wifi = on +VirtioWifi = on HostComposition = on RefCountPipe = on VirtioInput = on DynamicPartition = on HardwareDecoder = on +ModemSimulator= on YUVCache = on GLDirectMem = on Vulkan = on @@ -18,3 +19,9 @@ MultiDisplay = on VulkanNullOptionalStrings = on VulkanIgnoredHandles = on Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/advancedFeatures.ini.arm b/data/etc/advancedFeatures.ini.arm index 0acc6d55..11d6b13d 100644 --- a/data/etc/advancedFeatures.ini.arm +++ b/data/etc/advancedFeatures.ini.arm @@ -1,6 +1,26 @@ GrallocSync = on +GLDMA = on LogcatPipe = on GLAsyncSwap = on GLESDynamicVersion = on -GLDMA = on +EncryptUserData = on +VirtioWifi = on +HostComposition = on +RefCountPipe = on +VirtioInput = on DynamicPartition = on +HardwareDecoder = on +ModemSimulator= on +MultiDisplay = on +YUVCache = on +GLDirectMem = on +Vulkan = on +VulkanNullOptionalStrings = on +VulkanIgnoredHandles = on +Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/arm64/emulatorip b/data/etc/arm64/emulatorip Binary files differnew file mode 100755 index 00000000..23d053e6 --- /dev/null +++ b/data/etc/arm64/emulatorip diff --git a/data/etc/config.ini.foldable b/data/etc/config.ini.foldable index a8f94ba5..64cc02cf 100644 --- a/data/etc/config.ini.foldable +++ b/data/etc/config.ini.foldable @@ -1,16 +1,15 @@ avd.ini.encoding=UTF-8 -disk.dataPartition.size=2G +disk.dataPartition.size=6G fastboot.forceColdBoot = yes hw.accelerometer=yes hw.audioInput=yes hw.battery=yes -hw.camera.back=emulated +hw.camera.back=virtualscene hw.camera.front=emulated hw.dPad=no hw.gps=yes hw.gpu.enabled=yes hw.keyboard=yes -hw.lcd.density=420 hw.mainKeys=no hw.ramSize=4096 hw.sensors.orientation=yes @@ -18,5 +17,32 @@ hw.sensors.proximity=yes hw.keyboard.lid=yes image.sysdir.1=x86/ skin.dynamic=no -skin.name=1536x2152 -skin.path=1536x2152 + +#main display +hw.lcd.density=480 +hw.lcd.height=2208 +hw.lcd.width=1768 + +#secondary display when folded +hw.displayRegion.0.1.height = 2208 +hw.displayRegion.0.1.width = 884 +hw.displayRegion.0.1.xOffset = 0 +hw.displayRegion.0.1.yOffset = 0 + +#foldable parameters +hw.keyboard.lid=yes +hw.sensor.hinge = yes +## x-y-width-height format +hw.sensor.hinge.areas = 884-0-1-2208 +hw.sensor.hinge.count = 1 +## default degree +hw.sensor.hinge.defaults = 180 +hw.sensor.hinge.ranges = 0-180 +## fold=0 or hinge=1 +hw.sensor.hinge.sub_type = 1 +## horizontal==0 or vertical==1 +hw.sensor.hinge.type = 1 +## each angle range corresponds to the posture in the posture_list +hw.sensor.hinge_angles_posture_definitions = 0-30, 30-150, 150-180 +## list of supported postures by index. 0: unknown, 1: closed, 2: half-open, 3: open, 4: flipped, 5: tent +hw.sensor.posture_list = 1,2,3 diff --git a/data/etc/config.ini.nexus7tab b/data/etc/config.ini.nexus7tab new file mode 100644 index 00000000..3dd8e2f5 --- /dev/null +++ b/data/etc/config.ini.nexus7tab @@ -0,0 +1,23 @@ +avd.ini.encoding=UTF-8 +disk.dataPartition.size=6G +fastboot.forceColdBoot = yes +hw.accelerometer=yes +hw.audioInput=yes +hw.battery=yes +hw.camera.back=emulated +hw.camera.front=emulated +hw.dPad=no +hw.gps=yes +hw.cpu.ncore=4 +hw.gpu.enabled=yes +hw.keyboard=yes +hw.lcd.density=320 +hw.mainKeys=no +hw.ramSize=4096 +hw.sensors.orientation=yes +hw.sensors.proximity=yes +image.sysdir.1=x86_64/ +skin.dynamic=no +skin.name=1200x1920 +skin.path=1200x1920 + diff --git a/data/etc/config.ini.xl b/data/etc/config.ini.xl index 32d26659..21f55542 100644 --- a/data/etc/config.ini.xl +++ b/data/etc/config.ini.xl @@ -1,5 +1,6 @@ avd.ini.encoding=UTF-8 -disk.dataPartition.size=2G +disk.dataPartition.size=6G +fastboot.forceColdBoot = yes hw.accelerometer=yes hw.audioInput=yes hw.battery=yes diff --git a/data/etc/empty_data_disk b/data/etc/empty_data_disk new file mode 100644 index 00000000..ad425310 --- /dev/null +++ b/data/etc/empty_data_disk @@ -0,0 +1 @@ +This mean the content in data image will start as empty diff --git a/data/etc/google/64bit/user/advancedFeatures.ini b/data/etc/google/64bit/user/advancedFeatures.ini new file mode 100644 index 00000000..1c72df4f --- /dev/null +++ b/data/etc/google/64bit/user/advancedFeatures.ini @@ -0,0 +1,28 @@ +GrallocSync = on +GLDMA = on +LogcatPipe = on +GLAsyncSwap = on +GLESDynamicVersion = on +PlayStoreImage = on +EncryptUserData = on +IntelPerformanceMonitoringUnit = on +VirtioWifi = on +HostComposition = on +RefCountPipe = on +VirtioInput = on +HardwareDecoder = on +DynamicPartition = on +ModemSimulator= on +MultiDisplay = on +YUVCache = on +GLDirectMem = on +Vulkan = on +VulkanNullOptionalStrings = on +VulkanIgnoredHandles = on +Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/google/64bit/user/arm64/advancedFeatures.ini b/data/etc/google/64bit/user/arm64/advancedFeatures.ini new file mode 100644 index 00000000..d9a710d4 --- /dev/null +++ b/data/etc/google/64bit/user/arm64/advancedFeatures.ini @@ -0,0 +1,27 @@ +GrallocSync = on +GLDMA = on +LogcatPipe = on +GLAsyncSwap = on +GLESDynamicVersion = on +PlayStoreImage = on +EncryptUserData = on +VirtioWifi = on +HostComposition = on +RefCountPipe = on +VirtioInput = on +HardwareDecoder = on +DynamicPartition = on +ModemSimulator= on +MultiDisplay = on +YUVCache = on +GLDirectMem = on +Vulkan = on +VulkanNullOptionalStrings = on +VulkanIgnoredHandles = on +Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/google/64bit/userdebug/advancedFeatures.ini b/data/etc/google/64bit/userdebug/advancedFeatures.ini new file mode 100644 index 00000000..1c72df4f --- /dev/null +++ b/data/etc/google/64bit/userdebug/advancedFeatures.ini @@ -0,0 +1,28 @@ +GrallocSync = on +GLDMA = on +LogcatPipe = on +GLAsyncSwap = on +GLESDynamicVersion = on +PlayStoreImage = on +EncryptUserData = on +IntelPerformanceMonitoringUnit = on +VirtioWifi = on +HostComposition = on +RefCountPipe = on +VirtioInput = on +HardwareDecoder = on +DynamicPartition = on +ModemSimulator= on +MultiDisplay = on +YUVCache = on +GLDirectMem = on +Vulkan = on +VulkanNullOptionalStrings = on +VulkanIgnoredHandles = on +Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/google/64bit/userdebug/arm64/advancedFeatures.ini b/data/etc/google/64bit/userdebug/arm64/advancedFeatures.ini new file mode 100644 index 00000000..f21ef43f --- /dev/null +++ b/data/etc/google/64bit/userdebug/arm64/advancedFeatures.ini @@ -0,0 +1,26 @@ +GrallocSync = on +GLDMA = on +LogcatPipe = on +GLAsyncSwap = on +GLESDynamicVersion = on +EncryptUserData = on +VirtioWifi = on +HostComposition = on +RefCountPipe = on +VirtioInput = on +HardwareDecoder = on +DynamicPartition = on +ModemSimulator= on +MultiDisplay = on +YUVCache = on +GLDirectMem = on +Vulkan = on +VulkanNullOptionalStrings = on +VulkanIgnoredHandles = on +Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/google/user/advancedFeatures.ini b/data/etc/google/user/advancedFeatures.ini index 85b5c3ab..34eccba4 100644 --- a/data/etc/google/user/advancedFeatures.ini +++ b/data/etc/google/user/advancedFeatures.ini @@ -6,12 +6,13 @@ GLESDynamicVersion = on PlayStoreImage = on EncryptUserData = on IntelPerformanceMonitoringUnit = on -Wifi = on +VirtioWifi = on HostComposition = on RefCountPipe = on VirtioInput = on DynamicPartition = on HardwareDecoder = on +ModemSimulator= on MultiDisplay = on YUVCache = on GLDirectMem = on @@ -19,3 +20,9 @@ Vulkan = on VulkanNullOptionalStrings = on VulkanIgnoredHandles = on Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/google/user/arm64/advancedFeatures.ini b/data/etc/google/user/arm64/advancedFeatures.ini new file mode 100644 index 00000000..37fc7e09 --- /dev/null +++ b/data/etc/google/user/arm64/advancedFeatures.ini @@ -0,0 +1,27 @@ +GrallocSync = on +GLDMA = on +LogcatPipe = on +GLAsyncSwap = on +GLESDynamicVersion = on +PlayStoreImage = on +EncryptUserData = on +VirtioWifi = on +HostComposition = on +RefCountPipe = on +VirtioInput = on +DynamicPartition = on +HardwareDecoder = on +ModemSimulator= on +MultiDisplay = on +YUVCache = on +GLDirectMem = on +Vulkan = on +VulkanNullOptionalStrings = on +VulkanIgnoredHandles = on +Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/google/userdebug/advancedFeatures.ini b/data/etc/google/userdebug/advancedFeatures.ini index 85b5c3ab..fe5ccd03 100644 --- a/data/etc/google/userdebug/advancedFeatures.ini +++ b/data/etc/google/userdebug/advancedFeatures.ini @@ -6,12 +6,13 @@ GLESDynamicVersion = on PlayStoreImage = on EncryptUserData = on IntelPerformanceMonitoringUnit = on -Wifi = on +VirtioWifi = on HostComposition = on RefCountPipe = on VirtioInput = on DynamicPartition = on HardwareDecoder = on +ModemSimulator= on MultiDisplay = on YUVCache = on GLDirectMem = on @@ -19,3 +20,10 @@ Vulkan = on VulkanNullOptionalStrings = on VulkanIgnoredHandles = on Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +GnssGrpcV1= on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/google/userdebug/arm64/advancedFeatures.ini b/data/etc/google/userdebug/arm64/advancedFeatures.ini new file mode 100644 index 00000000..11d6b13d --- /dev/null +++ b/data/etc/google/userdebug/arm64/advancedFeatures.ini @@ -0,0 +1,26 @@ +GrallocSync = on +GLDMA = on +LogcatPipe = on +GLAsyncSwap = on +GLESDynamicVersion = on +EncryptUserData = on +VirtioWifi = on +HostComposition = on +RefCountPipe = on +VirtioInput = on +DynamicPartition = on +HardwareDecoder = on +ModemSimulator= on +MultiDisplay = on +YUVCache = on +GLDirectMem = on +Vulkan = on +VulkanNullOptionalStrings = on +VulkanIgnoredHandles = on +Mac80211hwsimUserspaceManaged = on +VirtconsoleLogcat = on +VirtioVsockPipe = on +AndroidbootProps2 = on +DeviceSkinOverlay = on +VulkanQueueSubmitWithCommands = on +VulkanBatchedDescriptorSetUpdate = on diff --git a/data/etc/handheld_core_hardware.xml b/data/etc/handheld_core_hardware.xml index 3fe79abb..97ee3491 100644 --- a/data/etc/handheld_core_hardware.xml +++ b/data/etc/handheld_core_hardware.xml @@ -54,6 +54,7 @@ <feature name="android.hardware.sensor.hinge_angle" /> <feature name="android.hardware.telephony" /> <feature name="android.hardware.telephony.gsm" /> + <feature name="android.hardware.telephony.ims" /> <feature name="android.hardware.touchscreen" /> <feature name="android.hardware.microphone" /> <feature name="android.hardware.screen.portrait" /> @@ -82,6 +83,10 @@ <feature name="android.software.activities_on_secondary_displays" /> <feature name="android.software.cts" /> + + <!-- Feature to specify if the device supports controls. --> + <feature name="android.software.controls" /> + <!-- devices with GPS must include android.hardware.location.gps.xml --> <!-- devices with an autofocus camera and/or flash must include either android.hardware.camera.autofocus.xml or diff --git a/data/etc/iccprofile_for_sim0.xml b/data/etc/iccprofile_for_sim0.xml new file mode 100644 index 00000000..28037933 --- /dev/null +++ b/data/etc/iccprofile_for_sim0.xml @@ -0,0 +1,178 @@ +<IccProfile> + <MF path="3F00"> + <EF name="EF_DIR" id="2F00" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621A8205422100300483022F008A01058B032F0601800200C08801F0</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="30" data="">144,0,61184F10A0000003431002FF86FF0389FFFFFFFF50044353494DFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="2" p2="4" p3="30" data="">144,0,61184F10A0000000871002FF86FF0389FFFFFFFF50045553494DFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="3" p2="4" p3="30" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="4" p2="4" p3="30" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + </EF> + <EF name="EF_ICCID" id="2FE2" structure="transparent"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,62178202412183022FE28A01058B032F06038002000A880110</SIMIO> + <SIMIO cmd="B0" p1="0" p2="0" p3="A" data="">144,0,98683081462002318379</SIMIO> + <!-- Special ATC to read ICCID from modem cache --> + <CCID>89860318640220133897</CCID> + </EF> + <EF name="EF_PL" id="2F05" structure="transparent"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,62178202412183022F058A01058B032F060280020004880128</SIMIO> + <SIMIO cmd="B0" p1="0" p2="0" p3="4" data="">144,0,FFFFFFFF</SIMIO> + </EF> + + <DF name="TELECOM" path="7F10"> + <DF name="PHONEBOOK" path="5F3A"> + <EF name="EF_PBR" id="4F30" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,62198205422100400283024F308A01058B036F0606800200808800</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="40" data="">144,0,A81EC0034F3A01C1034F3306C5034F0902C4034F1104C6034F2503C9034F3107A905CA034F5008AA0FC2034F4A09C7034F4B0AC8034F4C0BFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="2" p2="4" p3="40" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + </EF> + <EF name="EF_GAS" id="4F4C" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621A8205422100140A83024F4C8A01058B036F060E800200C8880158</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="2" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="3" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="4" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="5" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="6" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="7" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="8" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="9" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="A" p2="4" p3="E" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + </EF> + <EF name="EF_ADN" id="4F3A" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621A82054221001C1483024F3A8A01058B036F060E80020230880108</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="2" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="3" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="4" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="5" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="6" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="7" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="8" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="9" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="A" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="B" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="C" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="D" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="E" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="F" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="10" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="11" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="12" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="13" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="14" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + </EF> + <EF name="EF_IAP" id="4F33" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621A820542210001FA83024F338A01058B036F060E800200FA880130</SIMIO> + </EF> + <EF name="EF_PBC" id="4F09" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621A820542210002FA83024F098A01058B036F060E800201F4880110</SIMIO> + </EF> + <EF name="EF_ANR" id="4F11" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621A82054221000FFA83024F118A01058B036F060E80020EA6880120</SIMIO> + </EF> + <!-- EF_SNE, EF_AAS, EF_EXT1, EF_GRP, EF_UID, EF_EMAIL, EF_CCP1, EF_PUR1 ... --> + </DF> + </DF> + + <ADF name="USIM" path="7FFF" aid="A0000000871002FF86FF0389FFFFFFFF"> + <EF name="EF_IMSI" id="6F07" structure="transparent"> + <CIMI>310260000000000</CIMI> + </EF> + <EF name="EF_MSISDN" id="6F40" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621982054221001C0283026F408A01058B036F0605800200388800</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="1C" data="">144,0,000000000000000000000000000007915155214365F7FFFFFFFFFFFF</SIMIO> + </EF> + <EF name="EF_MBI" id="6FC9" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,62198205422100050183026FC98A01058B036F0602800200058800</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="5" data="">144,0,0100000000</SIMIO> + </EF> + <EF name="EF_MBDN" id="6FC7" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621982054221001C0283026F408A01058B036F06058002003E8800</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF07915155674523F1FFFFFFFFFFFF</SIMIO> + </EF> + <EF name="EF_AD" id="6FAD" structure="transparent"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,62178202412183026FAD8A01058B036F060180020004880118</SIMIO> + <SIMIO cmd="B0" p1="0" p2="0" p3="4" data="">144,0,00000003</SIMIO> + </EF> + <EF name="EF_MWIS" id="6FCA" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,62198205422100050183026FCA8A01058B036F060E800200058800</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="5" data="">144,0,0000000000</SIMIO> + </EF> + <EF name="EF_VOICE_MAIL_INDICATOR_CPHS" id="6F11" structure="transparent"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">106,130</SIMIO> + </EF> + <EF name="EF_FPLMN" id="6F7B" structure="transparent"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621C8202412183026F7BA5038001718A01058B036F06038002001E880168</SIMIO> + <SIMIO cmd="B0" p1="0" p2="0" p3="1E" data="">144,0,64F00064F02064F04064F07064F080FFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + </EF> + <EF name="EF_FDN" id="6F3B" structure="linear fixed"> + <SIMIO cmd="C0" p1="0" p2="0" p3="F" data="">144,0,621982054221001C0A83026F3B8A01058B036F0605800201188800</SIMIO> + <SIMIO cmd="B2" p1="1" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="2" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="3" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="4" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="5" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="6" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="7" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="8" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="9" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + <SIMIO cmd="B2" p1="A" p2="4" p3="1C" data="">144,0,FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF</SIMIO> + </EF> + <!-- Other USIM files... --> + </ADF> + </MF> + + <ADF name="PKCS15" aid="A000000063504B43532D3135"> + <CGLA cmd="A40004025031">4,6124</CGLA> + <CGLA cmd="C0000024">76,62228202412183025031A503C001408A01058B066F0601010001800200108102002288009000 </CGLA> + <CGLA cmd="B0000010">36,A706300404024401A5063004040244029000</CGLA> + </ADF> + + <ADF name="" aid=""> + <CSIM cmd='10,"0070000001"'>6,019000</CSIM> + <CGLA cmd='1,14,"81F2FF0000"'>4,6b00</CGLA> + <!-- more CGLA Command --> + </ADF> + + <PinProfile> + <!-- PIN: PINSTATE_ENABLED_NOT_VERIFIED --> + <!-- PUK: PINSTATE_ENABLED_BLOCKED --> + <!-- Ready: PINSTATE_UNKNOWN --> + <PINSTATE>PINSTATE_UNKNOWN</PINSTATE> + <PINCODE>1234</PINCODE> + <PUKCODE>12345678</PUKCODE> + <PINREMAINTIMES>3</PINREMAINTIMES> + <PUKREMAINTIMES>10</PUKREMAINTIMES> + <PIN2CODE>1234</PIN2CODE> + <PUK2CODE>12345678</PUK2CODE> + <PIN2REMAINTIMES>3</PIN2REMAINTIMES> + <PUK2REMAINTIMES>10</PUK2REMAINTIMES> + </PinProfile> + + <FacilityLock> + <SC>DISABLE</SC> + <FD>DISABLE</FD> + <AO>DISABLE</AO> + <OI>DISABLE</OI> + <AI>DISABLE</AI> + <IR>DISABLE</IR> + <AB>DISABLE</AB> + <AG>DISABLE</AG> + <AC>DISABLE</AC> + </FacilityLock> + <SETUPMENU cmd="25" text="D048810301250082028182850D800054004D006F0062006C00658F18508000530049004D00200054006F006F006C006B006900748F144E80005500530049004D00200043006100720064"> + <SELECTITEM id="1" cmd="24" menuId="50" text="D02D8103012400820281828F0A0180006D0065006E00758F0A02800049006E0066006F8F0A038000480065006C0070"> + <SELECTITEM id="1" cmd="24" menuId="01" text="D0318103012400820281828F1201800041006400640020006D0065006E00758F12028000440065006C0020006D0065006E0075"> + <DISPLAYTEXT id="1" cmd="21" menuId="01" text="D02A8103012181820281028D1F08004E006F007400200069006D0070006C0065006D0065006E007400650064"/> + <DISPLAYTEXT id="2" cmd="21" menuId="02" text="D02A8103012101820281028D1F08004E006F007400200069006D0070006C0065006D0065006E007400650064"/> + </SELECTITEM> + <DISPLAYTEXT id="2" cmd="21" menuId="02" text="D0368103012181820281028D2B0800410064006400740069006F006E0061006C00200069006E0066006F0072006D006100740069006F006E"/> + <DISPLAYTEXT id="3" cmd="21" menuId="03" text="D0228103012181820281028D170800560065007200730069006F006E00200031002E0030"/> + </SELECTITEM> + <SELECTITEM id="2" cmd="24" menuId="4E" text="D046810301240082028182851380005500530049004D002000430061007200648F0A018000540079007000658F10028000530074006F00720061006700658F080380004F00540041"> + <DISPLAYTEXT id="1" cmd="21" menuId="01" text="D0268103012181820281028D1B08005500530049004D0020004300610072006400200032002E0030"/> + <DISPLAYTEXT id="2" cmd="21" menuId="02" text="D04C8103012181820281028D410800350030003000200063006F006E0074006100630074007300200061006E006400200035003000200053004D00530020006D0065007300730061006700650073"/> + <DISPLAYTEXT id="3" cmd="21" menuId="03" text="D02A8103012101820281028D1F08004E006F007400200069006D0070006C0065006D0065006E007400650064"/> + </SELECTITEM> + </SETUPMENU> +</IccProfile> diff --git a/data/etc/numeric_operator.xml b/data/etc/numeric_operator.xml new file mode 100644 index 00000000..e5b45220 --- /dev/null +++ b/data/etc/numeric_operator.xml @@ -0,0 +1,7 @@ +<?xml version="1.0" encoding="utf-8"?> +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <add-resource name="numeric_to_operator" type="array"/> + <string-array name="numeric_to_operator"> + <item numeric="310260">T-Mobile=TMOBILE</item> + </string-array> +</resources> diff --git a/data/etc/x86_64/emulatorip b/data/etc/x86_64/emulatorip Binary files differnew file mode 100755 index 00000000..0ba4abeb --- /dev/null +++ b/data/etc/x86_64/emulatorip diff --git a/data/media/test/media.adb b/data/media/test/media.adb new file mode 100644 index 00000000..d860ef15 --- /dev/null +++ b/data/media/test/media.adb @@ -0,0 +1,5 @@ +push media/0/test/CtsMediaTestCases-1.4/swirl_136x144_mpeg4.mp4 /sdcard/test/CtsMediaTestCases-1.4/swirl_136x144_mpeg4.mp4 +push media/0/test/CtsMediaTestCases-1.4/swirl_132x130_mpeg4.mp4 /sdcard/test/CtsMediaTestCases-1.4/swirl_132x130_mpeg4.mp4 +push media/0/test/CtsMediaTestCases-1.4/swirl_130x132_mpeg4.mp4 /sdcard/test/CtsMediaTestCases-1.4/swirl_130x132_mpeg4.mp4 +push media/0/test/CtsMediaTestCases-1.4/swirl_144x136_mpeg4.mp4 /sdcard/test/CtsMediaTestCases-1.4/swirl_144x136_mpeg4.mp4 +push media/0/test/CtsMediaTestCases-1.4/swirl_128x128_mpeg4.mp4 /sdcard/test/CtsMediaTestCases-1.4/swirl_128x128_mpeg4.mp4 diff --git a/data/media/test/swirl_128x128_mpeg4.mp4 b/data/media/test/swirl_128x128_mpeg4.mp4 Binary files differnew file mode 100644 index 00000000..694ce95c --- /dev/null +++ b/data/media/test/swirl_128x128_mpeg4.mp4 diff --git a/data/media/test/swirl_130x132_mpeg4.mp4 b/data/media/test/swirl_130x132_mpeg4.mp4 Binary files differnew file mode 100644 index 00000000..ed6b5294 --- /dev/null +++ b/data/media/test/swirl_130x132_mpeg4.mp4 diff --git a/data/media/test/swirl_132x130_mpeg4.mp4 b/data/media/test/swirl_132x130_mpeg4.mp4 Binary files differnew file mode 100644 index 00000000..ed975db9 --- /dev/null +++ b/data/media/test/swirl_132x130_mpeg4.mp4 diff --git a/data/media/test/swirl_136x144_mpeg4.mp4 b/data/media/test/swirl_136x144_mpeg4.mp4 Binary files differnew file mode 100644 index 00000000..c74bd969 --- /dev/null +++ b/data/media/test/swirl_136x144_mpeg4.mp4 diff --git a/data/media/test/swirl_144x136_mpeg4.mp4 b/data/media/test/swirl_144x136_mpeg4.mp4 Binary files differnew file mode 100644 index 00000000..81c1db3c --- /dev/null +++ b/data/media/test/swirl_144x136_mpeg4.mp4 diff --git a/device_state_configuration.xml b/device_state_configuration.xml new file mode 100644 index 00000000..17a09c45 --- /dev/null +++ b/device_state_configuration.xml @@ -0,0 +1,18 @@ +<device-state-config> + <device-state> + <identifier>0</identifier> + <conditions> + <lid-switch> + <open>false</open> + </lid-switch> + </conditions> + </device-state> + <device-state> + <identifier>1</identifier> + <conditions> + <lid-switch> + <open>true</open> + </lid-switch> + </conditions> + </device-state> +</device-state-config> diff --git a/dhcp/client/Android.bp b/dhcp/client/Android.bp index 852c24ec..5937a21e 100644 --- a/dhcp/client/Android.bp +++ b/dhcp/client/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "dhcpclient", srcs: [ diff --git a/dhcp/client/dhcpclient.cpp b/dhcp/client/dhcpclient.cpp index a7b4b24d..7404fad4 100644 --- a/dhcp/client/dhcpclient.cpp +++ b/dhcp/client/dhcpclient.cpp @@ -421,7 +421,7 @@ bool DhcpClient::configureDhcp(const Message& msg) { } char propName[64]; - snprintf(propName, sizeof(propName), "net.%s.gw", + snprintf(propName, sizeof(propName), "vendor.net.%s.gw", mInterface.getName().c_str()); if (property_set(propName, addrToStr(mDhcpInfo.gateway).c_str()) != 0) { ALOGE("Failed to set %s: %s", propName, strerror(errno)); @@ -429,7 +429,7 @@ bool DhcpClient::configureDhcp(const Message& msg) { int numDnsEntries = sizeof(mDhcpInfo.dns) / sizeof(mDhcpInfo.dns[0]); for (int i = 0; i < numDnsEntries; ++i) { - snprintf(propName, sizeof(propName), "net.%s.dns%d", + snprintf(propName, sizeof(propName), "vendor.net.%s.dns%d", mInterface.getName().c_str(), i + 1); if (mDhcpInfo.dns[i] != 0) { if (property_set(propName, diff --git a/dhcp/common/Android.bp b/dhcp/common/Android.bp index 2df9f970..9dd0aaa2 100644 --- a/dhcp/common/Android.bp +++ b/dhcp/common/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_static { name: "libdhcpclient", srcs: [ diff --git a/emulator-info.txt b/emulator-info.txt index fb45a7e0..532435c5 100644 --- a/emulator-info.txt +++ b/emulator-info.txt @@ -1,2 +1,2 @@ # Emulator (stable) version -require version-emulator=6629878 +require version-emulator=7479360 diff --git a/emulator64_arm64/BoardConfig.mk b/emulator64_arm64/BoardConfig.mk new file mode 100644 index 00000000..57b1cdb9 --- /dev/null +++ b/emulator64_arm64/BoardConfig.mk @@ -0,0 +1,40 @@ +# Copyright (C) 2020 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. +# + +# arm64 emulator specific definitions +TARGET_ARCH := arm64 +TARGET_ARCH_VARIANT := armv8-a +TARGET_CPU_VARIANT := generic +TARGET_CPU_ABI := arm64-v8a + +TARGET_2ND_ARCH_VARIANT := armv8-a +TARGET_2ND_CPU_VARIANT := generic + +include build/make/target/board/BoardConfigGsiCommon.mk +include build/make/target/board/BoardConfigEmuCommon.mk + +BOARD_BOOTIMAGE_PARTITION_SIZE := 0x02000000 +BOARD_USERDATAIMAGE_PARTITION_SIZE := 576716800 + +# Wifi. +BOARD_WLAN_DEVICE := emulator +BOARD_HOSTAPD_DRIVER := NL80211 +BOARD_WPA_SUPPLICANT_DRIVER := NL80211 +BOARD_HOSTAPD_PRIVATE_LIB := lib_driver_cmd_simulated +BOARD_WPA_SUPPLICANT_PRIVATE_LIB := lib_driver_cmd_simulated +WPA_SUPPLICANT_VERSION := VER_0_8_X +WIFI_DRIVER_FW_PATH_PARAM := "/dev/null" +WIFI_DRIVER_FW_PATH_STA := "/dev/null" +WIFI_DRIVER_FW_PATH_AP := "/dev/null" diff --git a/emulator64_arm64/device.mk b/emulator64_arm64/device.mk new file mode 100644 index 00000000..af023eb2 --- /dev/null +++ b/emulator64_arm64/device.mk @@ -0,0 +1,18 @@ +# +# Copyright (C) 2020 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. +# + +PRODUCT_SOONG_NAMESPACES += device/generic/goldfish # for libwifi-hal-emu +PRODUCT_SOONG_NAMESPACES += device/generic/goldfish-opengl # for goldfish deps. diff --git a/emulator64_x86_64/BoardConfig.mk b/emulator64_x86_64/BoardConfig.mk new file mode 100755 index 00000000..fcb97ead --- /dev/null +++ b/emulator64_x86_64/BoardConfig.mk @@ -0,0 +1,41 @@ +# Copyright (C) 2020 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. +# + +# x86_64 emulator specific definitions +TARGET_CPU_ABI := x86_64 +TARGET_ARCH := x86_64 +TARGET_ARCH_VARIANT := x86_64 +TARGET_2ND_ARCH_VARIANT := x86_64 + +BOARD_DO_NOT_STRIP_VENDOR_MODULES := true + +TARGET_PRELINK_MODULE := false +include build/make/target/board/BoardConfigGsiCommon.mk +include build/make/target/board/BoardConfigEmuCommon.mk + +BOARD_USERDATAIMAGE_PARTITION_SIZE := 576716800 + +BOARD_SEPOLICY_DIRS += device/generic/goldfish/sepolicy/x86 + +# Wifi. +BOARD_WLAN_DEVICE := emulator +BOARD_HOSTAPD_DRIVER := NL80211 +BOARD_WPA_SUPPLICANT_DRIVER := NL80211 +BOARD_HOSTAPD_PRIVATE_LIB := lib_driver_cmd_simulated +BOARD_WPA_SUPPLICANT_PRIVATE_LIB := lib_driver_cmd_simulated +WPA_SUPPLICANT_VERSION := VER_0_8_X +WIFI_DRIVER_FW_PATH_PARAM := "/dev/null" +WIFI_DRIVER_FW_PATH_STA := "/dev/null" +WIFI_DRIVER_FW_PATH_AP := "/dev/null" diff --git a/emulator64_x86_64/README.txt b/emulator64_x86_64/README.txt new file mode 100644 index 00000000..ee36d6cd --- /dev/null +++ b/emulator64_x86_64/README.txt @@ -0,0 +1,10 @@ +The "emulator64_x86_64" product defines a non-hardware-specific IA target +without a kernel or bootloader. + +This only supports 64bit abi + +It can be used to build the entire user-level system, and +will work with the IA version of the emulator, + +It is not a product "base class"; no other products inherit +from it or use it in any way. diff --git a/emulator64_x86_64/device.mk b/emulator64_x86_64/device.mk new file mode 100755 index 00000000..8a9d8da9 --- /dev/null +++ b/emulator64_x86_64/device.mk @@ -0,0 +1,27 @@ +# +# Copyright (C) 2020 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. +# + +PRODUCT_SOONG_NAMESPACES += device/generic/goldfish # for libwifi-hal-emu +PRODUCT_SOONG_NAMESPACES += device/generic/goldfish-opengl # for goldfish deps. + +ifdef NET_ETH0_STARTONBOOT + PRODUCT_VENDOR_PROPERTIES += net.eth0.startonboot=1 +endif + +# Ensure we package the BIOS files too. +PRODUCT_HOST_PACKAGES += \ + bios.bin \ + vgabios-cirrus.bin \ diff --git a/emulator64_x86_64/system_ext.prop b/emulator64_x86_64/system_ext.prop new file mode 100644 index 00000000..9fc45992 --- /dev/null +++ b/emulator64_x86_64/system_ext.prop @@ -0,0 +1,5 @@ +# +# system.prop for generic sdk +# +# the following is no longer needed +#rild.libpath=/vendor/lib64/libreference-ril.so diff --git a/emulator64_x86_64_arm64/BoardConfig.mk b/emulator64_x86_64_arm64/BoardConfig.mk new file mode 100755 index 00000000..ce88f07c --- /dev/null +++ b/emulator64_x86_64_arm64/BoardConfig.mk @@ -0,0 +1,50 @@ +# Copyright (C) 2020 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. +# + +# x86_64 emulator specific definitions +TARGET_CPU_ABI := x86_64 +TARGET_ARCH := x86_64 +TARGET_ARCH_VARIANT := x86_64 +TARGET_2ND_ARCH_VARIANT := x86_64 + +TARGET_NATIVE_BRIDGE_ARCH := arm64 +TARGET_NATIVE_BRIDGE_ARCH_VARIANT := armv8-a +TARGET_NATIVE_BRIDGE_CPU_VARIANT := generic +TARGET_NATIVE_BRIDGE_ABI := arm64-v8a + +BUILD_BROKEN_DUP_RULES := true + +TARGET_PRELINK_MODULE := false + +include build/make/target/board/BoardConfigMainlineCommon.mk +include build/make/target/board/BoardConfigEmuCommon.mk + +# the settings differ from BoardConfigMainlineCommon.mk +BOARD_USES_SYSTEM_OTHER_ODEX := + +BOARD_USERDATAIMAGE_PARTITION_SIZE := 576716800 + +BOARD_SEPOLICY_DIRS += device/generic/goldfish/sepolicy/x86 + +# Wifi. +BOARD_WLAN_DEVICE := emulator +BOARD_HOSTAPD_DRIVER := NL80211 +BOARD_WPA_SUPPLICANT_DRIVER := NL80211 +BOARD_HOSTAPD_PRIVATE_LIB := lib_driver_cmd_simulated +BOARD_WPA_SUPPLICANT_PRIVATE_LIB := lib_driver_cmd_simulated +WPA_SUPPLICANT_VERSION := VER_0_8_X +WIFI_DRIVER_FW_PATH_PARAM := "/dev/null" +WIFI_DRIVER_FW_PATH_STA := "/dev/null" +WIFI_DRIVER_FW_PATH_AP := "/dev/null" diff --git a/emulator64_x86_64_arm64/README.txt b/emulator64_x86_64_arm64/README.txt new file mode 100644 index 00000000..cb2ac556 --- /dev/null +++ b/emulator64_x86_64_arm64/README.txt @@ -0,0 +1,10 @@ +The "emulator64_x86_64_arm64" product defines a non-hardware-specific IA target +without a kernel or bootloader. + +This only supports 64bit abi and ndk-translated arm64 abi + +It can be used to build the entire user-level system, and +will work with the IA version of the emulator, + +It is not a product "base class"; no other products inherit +from it or use it in any way. diff --git a/emulator64_x86_64_arm64/device.mk b/emulator64_x86_64_arm64/device.mk new file mode 100755 index 00000000..0fe29f68 --- /dev/null +++ b/emulator64_x86_64_arm64/device.mk @@ -0,0 +1,22 @@ +# +# Copyright (C) 2020 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. +# + +PRODUCT_SOONG_NAMESPACES += device/generic/goldfish # for libwifi-hal-emu +PRODUCT_SOONG_NAMESPACES += device/generic/goldfish-opengl # for goldfish deps. + +ifdef NET_ETH0_STARTONBOOT + PRODUCT_VENDOR_PROPERTIES += net.eth0.startonboot=1 +endif diff --git a/fingerprint/Android.bp b/fingerprint/Android.bp index 66ba14de..c9eb8c7d 100644 --- a/fingerprint/Android.bp +++ b/fingerprint/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_shared { name: "fingerprint.ranchu", vendor: true, diff --git a/fstab.goldfish b/fstab.goldfish index c626f400..77f6b138 100644 --- a/fstab.goldfish +++ b/fstab.goldfish @@ -3,5 +3,5 @@ # The filesystem that contains the filesystem checker binary (typically /system) cannot # specify MF_CHECK, and must come before any filesystems that do specify MF_CHECK /dev/block/mtdblock0 /system ext4 ro,barrier=1 wait -/dev/block/mtdblock1 /data ext4 noatime,nosuid,nodev,barrier=1,nomblk_io_submit wait,check +/dev/block/mtdblock1 /data ext4 noatime,nosuid,nodev,barrier=1,nomblk_io_submit wait,check,latemount /devices/platform/goldfish_mmc.0* auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata diff --git a/fstab.ranchu b/fstab.ranchu index f4e46e8c..157c9ed1 100644 --- a/fstab.ranchu +++ b/fstab.ranchu @@ -2,7 +2,7 @@ #<dev> <mnt_point> <type> <mnt_flags options> <fs_mgr_flags> system /system ext4 ro,barrier=1 wait,logical,avb=vbmeta,first_stage_mount vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount -/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M +/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M,latemount /dev/block/pci/pci0000:00/0000:00:06.0/by-name/metadata /metadata ext4 noatime,nosuid,nodev wait,formattable,first_stage_mount /devices/*/block/vdf auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata dev/block/zram0 none swap defaults zramsize=75% diff --git a/fstab.ranchu.arm b/fstab.ranchu.arm index a821e979..9ef7f023 100644 --- a/fstab.ranchu.arm +++ b/fstab.ranchu.arm @@ -4,5 +4,5 @@ # specify MF_CHECK, and must come before any filesystems that do specify MF_CHECK system /system ext4 ro,barrier=1 wait,logical,first_stage_mount vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount -/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota +/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,latemount /devices/*/block/vde auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata diff --git a/fstab.ranchu.arm.ex b/fstab.ranchu.arm.ex index 9946b6aa..837deef0 100644 --- a/fstab.ranchu.arm.ex +++ b/fstab.ranchu.arm.ex @@ -6,5 +6,6 @@ system /system ext4 ro,barrier=1 wait,logical,first_stage_mount vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount product /product ext4 ro,barrier=1 wait,logical,first_stage_mount system_ext /system_ext ext4 ro,barrier=1 wait,logical,first_stage_mount -/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota -/devices/*/block/vde auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata +/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M,fsverity,keydirectory=/metadata/vold/metadata_encryption,latemount +/dev/block/platform/a003c00.virtio_mmio/by-name/metadata /metadata ext4 noatime,nosuid,nodev wait,formattable,first_stage_mount +/devices/*/block/vdf auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata diff --git a/fstab.ranchu.ex b/fstab.ranchu.ex index 9dc7eb36..5fe5b801 100644 --- a/fstab.ranchu.ex +++ b/fstab.ranchu.ex @@ -4,7 +4,7 @@ system /system ext4 ro,barrier=1 wait,logical,avb=vbmeta,first_stag vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount product /product ext4 ro,barrier=1 wait,logical,first_stage_mount system_ext /system_ext ext4 ro,barrier=1 wait,logical,first_stage_mount -/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M +/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M,fsverity,keydirectory=/metadata/vold/metadata_encryption,latemount /dev/block/pci/pci0000:00/0000:00:06.0/by-name/metadata /metadata ext4 noatime,nosuid,nodev wait,formattable,first_stage_mount /devices/*/block/vdf auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata dev/block/zram0 none swap defaults zramsize=75% diff --git a/fstab.ranchu.initrd.arm.ex b/fstab.ranchu.initrd.arm.ex index d9398413..b9e30f17 100644 --- a/fstab.ranchu.initrd.arm.ex +++ b/fstab.ranchu.initrd.arm.ex @@ -4,3 +4,4 @@ system /system ext4 ro,barrier=1 wait,logical,first_stage_mount vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount product /product ext4 ro,barrier=1 wait,logical,first_stage_mount system_ext /system_ext ext4 ro,barrier=1 wait,logical,first_stage_mount +/dev/block/platform/a003c00.virtio_mmio/by-name/metadata /metadata ext4 noatime,nosuid,nodev wait,formattable,first_stage_mount diff --git a/fstab.ranchu.mips b/fstab.ranchu.mips index 3eed0bee..251966ba 100644 --- a/fstab.ranchu.mips +++ b/fstab.ranchu.mips @@ -2,5 +2,5 @@ #<src> <mnt_point> <type> <mnt_flags and options> <fs_mgr_flags> # The filesystem that contains the filesystem checker binary (typically /system) cannot # specify MF_CHECK, and must come before any filesystems that do specify MF_CHECK -/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check +/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,latemount /devices/*/block/vde auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata diff --git a/fstab.ranchu.noavb b/fstab.ranchu.noavb index 88e009df..cec831e3 100644 --- a/fstab.ranchu.noavb +++ b/fstab.ranchu.noavb @@ -2,7 +2,7 @@ #<dev> <mnt_point> <type> <mnt_flags options> <fs_mgr_flags> system /system ext4 ro,barrier=1 wait,logical,first_stage_mount vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount -/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M +/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M,latemount /dev/block/pci/pci0000:00/0000:00:06.0/by-name/metadata /metadata ext4 noatime,nosuid,nodev wait,formattable,first_stage_mount /devices/*/block/vdf auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata dev/block/zram0 none swap defaults zramsize=75% diff --git a/fstab.ranchu.noavb.ex b/fstab.ranchu.noavb.ex index 7b4b921f..9a0df81b 100644 --- a/fstab.ranchu.noavb.ex +++ b/fstab.ranchu.noavb.ex @@ -4,7 +4,7 @@ system /system ext4 ro,barrier=1 wait,logical,first_stage_mount vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount product /product ext4 ro,barrier=1 wait,logical,first_stage_mount system_ext /system_ext ext4 ro,barrier=1 wait,logical,first_stage_mount -/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M +/dev/block/vdc /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota,fileencryption=aes-256-xts:aes-256-cts,reservedsize=128M,latemount /dev/block/pci/pci0000:00/0000:00:06.0/by-name/metadata /metadata ext4 noatime,nosuid,nodev wait,formattable,first_stage_mount /devices/*/block/vdf auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata dev/block/zram0 none swap defaults zramsize=75% @@ -1,5 +1,5 @@ # -# Copyright 2019 The Android Open Source Project +# Copyright 2020 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. @@ -23,7 +23,7 @@ PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS := false # All components inherited here go to system image # $(call inherit-product, $(SRC_TARGET_DIR)/product/core_64_bit.mk) -$(call inherit-product, $(SRC_TARGET_DIR)/product/mainline_system.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/generic_system.mk) # # All components inherited here go to system_ext image @@ -40,18 +40,19 @@ $(call inherit-product, $(SRC_TARGET_DIR)/product/aosp_product.mk) # All components inherited here go to vendor image # $(call inherit-product, $(SRC_TARGET_DIR)/product/media_vendor.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/product/emulated_storage.mk) PRODUCT_SOONG_NAMESPACES += device/generic/goldfish PRODUCT_PACKAGES += \ - android.hardware.audio@2.0-service \ - android.hardware.audio@4.0-impl:32 \ - android.hardware.audio.effect@4.0-impl:32 \ + android.hardware.audio.service \ + android.hardware.audio@6.0-impl:32 \ + android.hardware.audio.effect@6.0-impl:32 \ audio.primary.default \ audio.r_submix.default \ android.hardware.drm@1.0-service \ android.hardware.drm@1.0-impl \ - android.hardware.drm@1.3-service.clearkey \ + android.hardware.drm@1.4-service.clearkey \ android.hardware.gatekeeper@1.0-service.software \ android.hardware.graphics.allocator@2.0-service \ android.hardware.graphics.allocator@2.0-impl \ @@ -61,10 +62,19 @@ PRODUCT_PACKAGES += \ android.hardware.health@2.0-service \ android.hardware.keymaster@4.0-service \ android.hardware.keymaster@4.0-impl \ + gralloc.minigbm \ + hwcomposer.drm_minigbm \ libEGL_swiftshader \ libGLESv1_CM_swiftshader \ libGLESv2_swiftshader \ +PRODUCT_PACKAGES += \ + android.hardware.bluetooth@1.1-service.sim \ + android.hardware.bluetooth.audio@2.0-impl +PRODUCT_PROPERTY_OVERRIDES += vendor.bt.rootcanal_test_console=off + +PRODUCT_HOST_PACKAGES += bind_to_localhost + PRODUCT_PACKAGE_OVERLAYS := device/generic/goldfish/overlay PRODUCT_NAME := fvp @@ -75,9 +85,19 @@ PRODUCT_MODEL := AOSP on FVP PRODUCT_COPY_FILES += \ device/generic/goldfish/data/etc/handheld_core_hardware.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/handheld_core_hardware.xml \ frameworks/native/data/etc/android.hardware.ethernet.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.ethernet.xml \ + frameworks/native/data/etc/android.hardware.bluetooth_le.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.bluetooth_le.xml \ + frameworks/native/data/etc/android.hardware.bluetooth.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.bluetooth.xml \ + frameworks/native/data/etc/android.hardware.wifi.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.wifi.xml \ + frameworks/native/data/etc/android.hardware.usb.host.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.usb.host.xml \ + system/bt/vendor_libs/test_vendor_lib/data/controller_properties.json:vendor/etc/bluetooth/controller_properties.json \ device/generic/goldfish/fvpbase/fstab.fvpbase:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.fvpbase \ - device/generic/goldfish/fvpbase/fstab.fvpbase.initrd:$(TARGET_COPY_OUT_RAMDISK)/fstab.fvpbase \ + device/generic/goldfish/fvpbase/fstab.qemu:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.qemu \ + device/generic/goldfish/fvpbase/fstab.initrd:$(TARGET_COPY_OUT_RAMDISK)/fstab.fvpbase \ + device/generic/goldfish/fvpbase/fstab.initrd:$(TARGET_COPY_OUT_RAMDISK)/fstab.qemu \ device/generic/goldfish/fvpbase/init.fvpbase.rc:$(TARGET_COPY_OUT_VENDOR)/etc/init/hw/init.fvpbase.rc \ + device/generic/goldfish/fvpbase/init.qemu.rc:$(TARGET_COPY_OUT_VENDOR)/etc/init/hw/init.qemu.rc \ + device/generic/goldfish/fvpbase/required_images:required_images \ + device/generic/goldfish/fvpbase/ueventd.fvp.rc:$(TARGET_COPY_OUT_VENDOR)/ueventd.rc \ frameworks/av/services/audiopolicy/config/audio_policy_configuration_generic.xml:$(TARGET_COPY_OUT_VENDOR)/etc/audio_policy_configuration.xml \ frameworks/av/services/audiopolicy/config/primary_audio_policy_configuration.xml:$(TARGET_COPY_OUT_VENDOR)/etc/primary_audio_policy_configuration.xml \ frameworks/av/services/audiopolicy/config/r_submix_audio_policy_configuration.xml:$(TARGET_COPY_OUT_VENDOR)/etc/r_submix_audio_policy_configuration.xml \ @@ -85,8 +105,12 @@ PRODUCT_COPY_FILES += \ frameworks/av/services/audiopolicy/config/default_volume_tables.xml:$(TARGET_COPY_OUT_VENDOR)/etc/default_volume_tables.xml \ frameworks/av/services/audiopolicy/config/surround_sound_configuration_5_0.xml:$(TARGET_COPY_OUT_VENDOR)/etc/surround_sound_configuration_5_0.xml \ +PRODUCT_BUILD_BOOT_IMAGE := true + PRODUCT_DEFAULT_PROPERTY_OVERRIDES += \ + qemu.hw.mainkeys=0 \ ro.hardware.egl=swiftshader \ + ro.hw_timeout_multiplier=50 \ debug.sf.nobootanimation=1 \ PRODUCT_REQUIRES_INSECURE_EXECMEM_FOR_SWIFTSHADER := true @@ -96,11 +120,6 @@ WITH_DEXPREOPT_BOOT_IMG_AND_SYSTEM_SERVER_ONLY := false DEVICE_MANIFEST_FILE := device/generic/goldfish/fvpbase/manifest.xml -# Normally, the bootloader is supposed to concatenate the Android initramfs -# and the initramfs for the kernel modules and let the kernel combine -# them. However, the bootloader that we're using with FVP (U-Boot) doesn't -# support concatenation, so we implement it in the build system. -droid: $(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/boot/ramdisk.img +# Use a multilib setup (see fvpbase/BoardConfig.mk). +FVP_MULTILIB_BUILD := true -$(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/boot/ramdisk.img: $(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/ramdisk.img $(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/boot/initramfs.img - gzip -dc $^ > $@ diff --git a/fvp_mini.mk b/fvp_mini.mk new file mode 100644 index 00000000..d1fd401b --- /dev/null +++ b/fvp_mini.mk @@ -0,0 +1,63 @@ +# +# Copyright 2020 Arm Ltd. All rights reserved. +# +# 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. +# + +$(call inherit-product, $(LOCAL_PATH)/minimal_system.mk) + +$(call inherit-product, $(SRC_TARGET_DIR)/product/updatable_apex.mk) + +$(call inherit-product, $(SRC_TARGET_DIR)/product/core_64_bit_only.mk) + +PRODUCT_NAME := fvp_mini +PRODUCT_DEVICE := fvpbase +PRODUCT_BRAND := Android +PRODUCT_MODEL := AOSP on FVP +PRODUCT_SOONG_NAMESPACES += device/generic/goldfish + +PRODUCT_SHIPPING_API_LEVEL := 29 +PRODUCT_USE_DYNAMIC_PARTITIONS := true +PRODUCT_FULL_TREBLE_OVERRIDE := true +PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS := false +PRODUCT_BUILD_BOOT_IMAGE := true + +OVERRIDE_TARGET_FLATTEN_APEX := true + +# Use a multilib setup (see fvpbase/BoardConfig.mk). +FVP_MULTILIB_BUILD ?= true + +# The check would fail because there are no boot jars. +SKIP_BOOT_JARS_CHECK ?= true + +PRODUCT_PACKAGES += \ + com.android.runtime \ + gdbserver \ + init_vendor \ + ip \ + ping \ + selinux_policy_nonsystem \ + +PRODUCT_HOST_PACKAGES += \ + bind_to_localhost + +PRODUCT_COPY_FILES += \ + device/generic/goldfish/fvpbase/fstab.fvpbase:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.fvpbase \ + device/generic/goldfish/fvpbase/fstab.qemu:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.qemu \ + device/generic/goldfish/fvpbase/fstab.initrd:$(TARGET_COPY_OUT_RAMDISK)/fstab.fvpbase \ + device/generic/goldfish/fvpbase/fstab.initrd:$(TARGET_COPY_OUT_RAMDISK)/fstab.qemu \ + device/generic/goldfish/fvpbase/init.fvpbase.rc:$(TARGET_COPY_OUT_VENDOR)/etc/init/hw/init.fvpbase.rc \ + device/generic/goldfish/fvpbase/init.qemu.rc:$(TARGET_COPY_OUT_VENDOR)/etc/init/hw/init.qemu.rc \ + device/generic/goldfish/fvpbase/mini_network.rc:system/etc/init/mini_network.rc \ + device/generic/goldfish/fvpbase/mini_network.sh:/system/bin/mini_network.sh \ + device/generic/goldfish/fvpbase/required_images:required_images \ diff --git a/fvpbase/BoardConfig.mk b/fvpbase/BoardConfig.mk index 234645e7..59c554cc 100644 --- a/fvpbase/BoardConfig.mk +++ b/fvpbase/BoardConfig.mk @@ -1,4 +1,4 @@ -# Copyright (C) 2019 The Android Open Source Project +# Copyright (C) 2020 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. @@ -18,16 +18,16 @@ TARGET_ARCH_VARIANT := armv8-a TARGET_CPU_VARIANT := generic TARGET_CPU_ABI := arm64-v8a +ifeq ($(FVP_MULTILIB_BUILD),true) TARGET_2ND_ARCH := arm TARGET_2ND_CPU_ABI := armeabi-v7a TARGET_2ND_CPU_ABI2 := armeabi TARGET_2ND_ARCH_VARIANT := armv8-a TARGET_2ND_CPU_VARIANT := generic +endif include build/make/target/board/BoardConfigMainlineCommon.mk -TARGET_NO_KERNEL := true - BOARD_USES_SYSTEM_OTHER_ODEX := BUILD_QEMU_IMAGES := true @@ -44,8 +44,28 @@ TARGET_COPY_OUT_SYSTEM_EXT := system/system_ext BOARD_VENDORIMAGE_FILE_SYSTEM_TYPE := ext4 -BOARD_USERDATAIMAGE_PARTITION_SIZE := 576716800 +BOARD_USERDATAIMAGE_PARTITION_SIZE := 1153433600 -BOARD_SEPOLICY_DIRS += device/generic/goldfish/fvpbase/sepolicy +BOARD_BOOTIMAGE_PARTITION_SIZE := 33554432 + +# Normally, the bootloader is supposed to concatenate the Android initramfs +# and the initramfs for the kernel modules and let the kernel combine +# them. However, the bootloader that we're using with FVP (U-Boot) doesn't +# support concatenation, so we implement it in the build system. +$(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/boot.img: $(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/combined-ramdisk.img + +$(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/combined-ramdisk.img: $(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/ramdisk.img $(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/initramfs.img + cat $^ > $@ -TARGET_EXPERIMENTAL_MTE := true +BOARD_MKBOOTIMG_ARGS := --header_version 2 --ramdisk $(OUT_DIR)/target/product/$(PRODUCT_DEVICE)/combined-ramdisk.img +BOARD_INCLUDE_DTB_IN_BOOTIMG := true +BOARD_PREBUILT_DTBIMAGE_DIR := $(OUT_DIR)/target/product/$(PRODUCT_DEVICE) + +BOARD_KERNEL_CMDLINE := \ + console=ttyAMA0 \ + earlycon=pl011,0x1c090000 \ + androidboot.hardware=fvpbase \ + androidboot.boot_device=bus@8000000/bus@8000000:motherboard-bus/bus@8000000:motherboard-bus:iofpga-bus@300000000/1c130000.virtio-block \ + loglevel=9 \ + +BOARD_SEPOLICY_DIRS += device/generic/goldfish/fvpbase/sepolicy diff --git a/fvpbase/README.md b/fvpbase/README.md index 7a15d7ce..03e03026 100644 --- a/fvpbase/README.md +++ b/fvpbase/README.md @@ -1,45 +1,55 @@ This document describes how to build and run an Android system image targeting -the ARM Fixed Virtual Platform. +the ARM Fixed Virtual Platform or QEMU. -### Building userspace +## New to Android? -``` -. build/envsetup.sh -lunch fvp-eng # or fvp-userdebug -m -``` +If you do not already have the ``repo`` tool, or a copy of the Android +source tree, please follow the Android instructions for [downloading the +source](https://source.android.com/setup/build/downloading). -Note that running ``m`` requires that the kernel is built first following -the instructions below. - -### Building the kernel +## Building the kernel ``` mkdir android-kernel-mainline cd android-kernel-mainline +export FVP_KERNEL_PATH=$(pwd) repo init -u https://android.googlesource.com/kernel/manifest -b common-android-mainline repo sync -BUILD_CONFIG=common/build.config.fvp build/build.sh +repo start fvp-patches common -r 79f312ba371eeba2f3ab043b9b56823a459052c8 +``` + +To support graphics on FVP, one additional cherry pick is required. This only +applies to the ``fvp`` target, and not ``fvp_mini``, and it is also not required +for QEMU. + +``` +repo download -c common 1463463 ``` -The resulting kernel image and DTB must then be copied into the product output directory: +Then, build the kernel. ``` -mkdir -p $ANDROID_PRODUCT_OUT/boot -cp out/android-mainline/dist/Image out/android-mainline/dist/initramfs.img $ANDROID_PRODUCT_OUT/boot/ -cp out/android-mainline/dist/fvp-base-revc.dtb $ANDROID_PRODUCT_OUT/boot/devtree.dtb +BUILD_CONFIG=common/build.config.gki.aarch64 build/build.sh -j$(nproc) +BUILD_CONFIG=common-modules/virtual-device/build.config.virtual_device.aarch64 build/build.sh -j$(nproc) ``` -### Building the firmware (ARM Trusted Firmware and U-Boot) +## Building the firmware (ARM Trusted Firmware and U-Boot) (FVP only, not required on QEMU) First, install ``dtc``, the device tree compiler. On Debian, this is in the -``device-tree-compiler`` package. Then run: +``device-tree-compiler`` package. Return to the top level directory (`cd ..`), and run: ``` mkdir platform cd platform +export FVP_FIRMWARE_PATH=$(pwd) repo init -u https://git.linaro.org/landing-teams/working/arm/manifest.git -m pinned-uboot.xml -b 20.01 repo sync +# The included copy of U-Boot is incompatible with this version of AOSP, switch to a recent upstream checkout. +cd u-boot +git fetch https://gitlab.denx.de/u-boot/u-boot.git/ master +git checkout 18b9c98024ec89e00a57707f07ff6ada06089d26 +cd .. + mkdir -p tools/gcc cd tools/gcc wget https://releases.linaro.org/components/toolchain/binaries/6.2-2016.11/aarch64-linux-gnu/gcc-linaro-6.2.1-2016.11-x86_64_aarch64-linux-gnu.tar.xz @@ -49,64 +59,110 @@ cd ../.. build-scripts/build-test-uboot.sh -p fvp all ``` -These components must then be copied into the product output directory: +## Building userspace + +Follow the Android instructions to [download the +source](https://source.android.com/setup/build/downloading), and run the +following in the source directory. ``` -cp output/fvp/fvp-uboot/uboot/{bl1,fip}.bin $ANDROID_PRODUCT_OUT/boot/ +. build/envsetup.sh +lunch fvp-eng # or fvp-userdebug, fvp_mini-eng, fvp_mini-userdebug ``` -### Obtaining the model +The fvp-* lunch targets will build a full Android with UI support, while +`fvp_mini-*` will build a small subset needed to boot to shell and support +command line executables. -The model may be obtained from [ARM's -website](https://developer.arm.com/tools-and-software/simulation-models/fixed-virtual-platforms) -(under "Armv8-A Base Platform FVP"). +Prepopulate the build directory with the kernel and firmware binaries. Normally, +these are copied from the source tree as part of the build process, but not for +this target yet. -### Running the model - -From a lunched environment, first set the value of the ``MODEL_BIN`` -environment variable to the path to the model executable. Then run the -following command to launch the model: ``` -device/generic/goldfish/fvpbase/run_model +mkdir -p $ANDROID_PRODUCT_OUT +cp $FVP_KERNEL_PATH/out/android-mainline/dist/Image $ANDROID_PRODUCT_OUT/kernel +cp $FVP_KERNEL_PATH/out/android-mainline/dist/{fvp-base-revc.dtb,initramfs.img} $ANDROID_PRODUCT_OUT/ + +# FVP only! QEMU doesn't require custom-built firmware. +cp $FVP_FIRMWARE_PATH/output/fvp/fvp-uboot/uboot/{bl1,fip}.bin $ANDROID_PRODUCT_OUT/ ``` -Additional model parameters may be passed by appending them to the -``run_model`` command. -To terminate the model, press ``Ctrl-] Ctrl-D`` to terminate the telnet -connection. +Set any additional build environment variables. +* To enable MTE on all platform binaries (by default it is only enabled on a + small subset) add `export SANITIZE_TARGET=memtag_heap` for Async mode, or + `export SANITIZE_TARGET=memtag_heap SANITIZE_TARGET_DIAG=memtag_heap` for Sync + mode. +* To disable 32 bit support in fvp_mini-* targets use + `export FVP_MULTILIB_BUILD=false`. -### MTE support +Finally, build the userspace image with `m`. -**WARNING**: The kernel MTE support patches are experimental and the userspace -interface is subject to change. +## Running -To launch the model with MTE support, the following additional parameters -must be used: +The same image can be used with either ARM Fixed Virtual Platform simulator, or +with QEMU. Slowdown from QEMU is roughly 10-20x, where ARM's FVP is 100-200x. + +### Running the image in FVP + +The model may be obtained from [ARM's +website](https://developer.arm.com/tools-and-software/simulation-models/fixed-virtual-platforms/arm-ecosystem-models) +(under "Armv-A Base RevC AEM FVP"). + +From a lunched environment, first set the value of the ``MODEL_BIN`` environment +variable to the path to the model executable (it should end with something like +`FVP_Base_RevC-2xAEMv8A/models/Linux64_GCC-6.4/FVP_Base_RevC-2xAEMv8A`). Then +run the following command to launch the model: +``` +device/generic/goldfish/fvpbase/run_model +``` +Additional model parameters may be passed by appending them to the +``run_model`` command. Add the following to enable MTE support in the model: ``` -C cluster0.has_arm_v8-5=1 \ -C cluster0.memory_tagging_support_level=2 \ -C bp.dram_metadata.is_enabled=1 ``` -MTE in userspace requires a patched common kernel with MTE support. To build -the kernel, follow the kernel instructions above, but before running the -``build.sh`` command, run: + +To terminate the model, press ``Ctrl-] Ctrl-D`` to terminate the telnet +connection. + +### Running the image in QEMU + +As an alternative to using FVP, the image may also be run in QEMU. +QEMU is generally much faster than FVP, but its support for the +latest ARM architectural features is relatively new compared to FVP, +so it may have more bugs. + +As of the time of writing, no released version of QEMU can successfully +boot the system to GUI due to bugs in its MTE support, so a development +version with bug fixes must be used. The instructions below check out a +commit that has been successfully tested. + +Check [QEMU wiki](https://wiki.qemu.org/Hosts/Linux#Building_QEMU_for_Linux) for +the list of build dependencies. Common missing packages include `ninja-build`, +`libpixman-1-dev`, and `libgtk-3-dev` for GUI support. + ``` -cd common -git fetch https://github.com/pcc/linux android-experimental-mte -git checkout FETCH_HEAD -cd .. +git clone https://github.com/qemu/qemu +cd qemu +git checkout 5c6295a45b4fceac913c11abc62488c49c02b9fd +mkdir build +cd build +../configure --target-list=aarch64-softmmu +ninja +export QEMU_BIN=$(pwd)/qemu-system-aarch64 ``` -Then replace the prebuilt binutils with binutils 2.33.1: + +Then run the following command in a lunched environment to start the emulator: ``` -cd binutils-2.33.1 -./configure --prefix=$PWD/inst --target=aarch64-linux-gnu -make -make install -for i in $PWD/inst/bin/*; do - ln -sf $i /path/to/android-kernel-mainline/prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9/bin/$(basename $i) - ln -sf $i /path/to/android-kernel-mainline/prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9/bin/$(basename $i | sed -e 's/gnu/android/g') -done +device/generic/goldfish/fvpbase/run_qemu ``` +Additional QEMU arguments may be passed by appending them to the ``run_qemu`` +command. One useful argument is ``-nographic``, which disables the GUI, which +may be useful when working with ``fvp_mini`` or if the GUI is not needed. + +To terminate the emulator, press ``Ctrl-A c q <Enter>`` or close the GUI +window. ### Accessing the model via adb diff --git a/fvpbase/fstab.fvpbase.initrd b/fvpbase/fstab.initrd index 56056634..56056634 100644 --- a/fvpbase/fstab.fvpbase.initrd +++ b/fvpbase/fstab.initrd diff --git a/fvpbase/fstab.qemu b/fvpbase/fstab.qemu new file mode 100644 index 00000000..a56c8663 --- /dev/null +++ b/fvpbase/fstab.qemu @@ -0,0 +1,8 @@ +# Android fstab file. +#<src> <mnt_point> <type> <mnt_flags and options> <fs_mgr_flags> +# The filesystem that contains the filesystem checker binary (typically /system) cannot +# specify MF_CHECK, and must come before any filesystems that do specify MF_CHECK +system /system ext4 ro,barrier=1 wait,logical,first_stage_mount +vendor /vendor ext4 ro,barrier=1 wait,logical,first_stage_mount +/dev/block/vda /data ext4 noatime,nosuid,nodev,nomblk_io_submit,errors=panic wait,check,quota +/devices/*/block/vde auto auto defaults voldmanaged=sdcard:auto,encryptable=userdata diff --git a/fvpbase/init.qemu.rc b/fvpbase/init.qemu.rc new file mode 100644 index 00000000..621b45c6 --- /dev/null +++ b/fvpbase/init.qemu.rc @@ -0,0 +1,7 @@ +on fs + mount_all /vendor/etc/fstab.qemu + +on early-init + setprop ro.hardware.gralloc minigbm + setprop ro.hardware.hwcomposer drm_minigbm + setprop ro.sf.lcd_density 150 diff --git a/fvpbase/manifest.xml b/fvpbase/manifest.xml index bd369aee..51c7f933 100644 --- a/fvpbase/manifest.xml +++ b/fvpbase/manifest.xml @@ -1,8 +1,26 @@ <manifest version="1.0" type="device" target-level="3"> <hal format="hidl"> + <name>android.hardware.bluetooth</name> + <transport>hwbinder</transport> + <version>1.1</version> + <interface> + <name>IBluetoothHci</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> + <name>android.hardware.bluetooth.audio</name> + <transport>hwbinder</transport> + <version>2.0</version> + <interface> + <name>IBluetoothAudioProvidersFactory</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> <name>android.hardware.audio</name> <transport>hwbinder</transport> - <version>4.0</version> + <version>6.0</version> <interface> <name>IDevicesFactory</name> <instance>default</instance> @@ -11,7 +29,7 @@ <hal format="hidl"> <name>android.hardware.audio.effect</name> <transport>hwbinder</transport> - <version>4.0</version> + <version>6.0</version> <interface> <name>IEffectsFactory</name> <instance>default</instance> diff --git a/fvpbase/mini_network.rc b/fvpbase/mini_network.rc new file mode 100644 index 00000000..15a13f87 --- /dev/null +++ b/fvpbase/mini_network.rc @@ -0,0 +1,19 @@ +# +# Copyright 2020 Arm Ltd. All rights reserved. +# +# 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. +# + +service mini_network /system/bin/mini_network.sh + class core + oneshot diff --git a/fvpbase/mini_network.sh b/fvpbase/mini_network.sh new file mode 100755 index 00000000..f2c90673 --- /dev/null +++ b/fvpbase/mini_network.sh @@ -0,0 +1,24 @@ +#!/system/bin/sh +# +# Copyright 2020 Arm Ltd. All rights reserved. +# +# 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. +# + +# The Android network stack is not included in Nano, so we need to +# configure the network manually. The configuration below is the same as +# would be obtained from the fast model's emulated DHCP. + +ip address add 172.20.51.1/24 broadcast 172.20.51.255 dev eth0 +ip link set eth0 up +ip route add default via 172.20.51.254 diff --git a/fvpbase/required_images b/fvpbase/required_images new file mode 100644 index 00000000..741ddc54 --- /dev/null +++ b/fvpbase/required_images @@ -0,0 +1,5 @@ +bl1.bin +boot.img +fip.bin +system-qemu.img +userdata.img diff --git a/fvpbase/run_model b/fvpbase/run_model index 3e2a798a..d6788371 100755 --- a/fvpbase/run_model +++ b/fvpbase/run_model @@ -1,6 +1,6 @@ #!/bin/sh -eu # -# Copyright 2019 The Android Open Source Project +# Copyright 2020 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. @@ -19,28 +19,9 @@ tmp="$(mktemp -d)" trap "rm -rf $tmp" EXIT mkfifo $tmp/port -"$MODEL_BIN" \ - -C bp.secureflashloader.fname="$ANDROID_PRODUCT_OUT/boot/bl1.bin" \ - -C bp.flashloader0.fname="$ANDROID_PRODUCT_OUT/boot/fip.bin" \ - -C cluster0.cpu0.semihosting-cwd="$ANDROID_PRODUCT_OUT/boot" \ - -C bp.virtioblockdevice.image_path="$ANDROID_PRODUCT_OUT/system-qemu.img" \ - -C bp.mmc.p_mmc_file="$ANDROID_PRODUCT_OUT/userdata.img" \ - -C bp.secure_memory=0 \ - -C cache_state_modelled=0 \ - -C bp.pl011_uart0.unbuffered_output=1 \ - -C bp.pl011_uart0.out_file="$ANDROID_PRODUCT_OUT/uart0.log" \ - -C bp.pl011_uart1.out_file="$ANDROID_PRODUCT_OUT/uart1.log" \ +"$(dirname $0)/run_model_only" \ + -C bp.terminal_0.start_telnet=1 \ -C bp.terminal_0.terminal_command="echo %port > $tmp/port" \ - -C bp.terminal_1.start_telnet=0 \ - -C bp.ve_sysregs.mmbSiteDefault=0 \ - -C bp.ve_sysregs.exit_on_shutdown=1 \ - -C bp.virtio_net.hostbridge.userNetworking=1 \ - -C bp.virtio_net.hostbridge.userNetPorts=5555=5555 \ - -C bp.virtio_net.enabled=1 \ - -C cluster0.NUM_CORES=1 \ - -C cluster0.cpu0.clock_multiplier=20 \ - -C cluster0.cpu0.enable_crc32=1 \ - -C cluster1.NUM_CORES=0 \ "$@" & read port < $tmp/port diff --git a/fvpbase/run_model_only b/fvpbase/run_model_only new file mode 100755 index 00000000..c2cfe6f0 --- /dev/null +++ b/fvpbase/run_model_only @@ -0,0 +1,42 @@ +#!/bin/sh -eu +# +# Copyright 2020 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. +# + +export LD_PRELOAD="$ANDROID_HOST_OUT/lib64/bind_to_localhost.so" + +exec "$MODEL_BIN" \ + -C bp.secureflashloader.fname="$ANDROID_PRODUCT_OUT/bl1.bin" \ + -C bp.flashloader0.fname="$ANDROID_PRODUCT_OUT/fip.bin" \ + -C cluster0.cpu0.semihosting-cwd="$ANDROID_PRODUCT_OUT" \ + -C bp.virtioblockdevice.image_path="$ANDROID_PRODUCT_OUT/system-qemu.img" \ + -C bp.mmc.p_mmc_file="$ANDROID_PRODUCT_OUT/userdata.img" \ + -C bp.secure_memory=0 \ + -C cache_state_modelled=0 \ + -C bp.pl011_uart0.unbuffered_output=1 \ + -C bp.pl011_uart0.out_file="$ANDROID_PRODUCT_OUT/uart0.log" \ + -C bp.pl011_uart1.out_file="$ANDROID_PRODUCT_OUT/uart1.log" \ + -C bp.terminal_0.start_telnet=0 \ + -C bp.terminal_1.start_telnet=0 \ + -C bp.ve_sysregs.mmbSiteDefault=0 \ + -C bp.ve_sysregs.exit_on_shutdown=1 \ + -C bp.virtio_net.hostbridge.userNetworking=1 \ + -C bp.virtio_net.hostbridge.userNetPorts=5555=5555 \ + -C bp.virtio_net.enabled=1 \ + -C cluster0.NUM_CORES=1 \ + -C cluster0.cpu0.clock_multiplier=20 \ + -C cluster0.cpu0.enable_crc32=1 \ + -C cluster1.NUM_CORES=0 \ + "$@" diff --git a/fvpbase/run_qemu b/fvpbase/run_qemu new file mode 100755 index 00000000..f4894db0 --- /dev/null +++ b/fvpbase/run_qemu @@ -0,0 +1,38 @@ +#!/bin/sh -eu +# +# Copyright 2021 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. +# + +"$QEMU_BIN" \ + -kernel "$ANDROID_PRODUCT_OUT/kernel" \ + -initrd "$ANDROID_PRODUCT_OUT/combined-ramdisk.img" \ + -machine virt,mte=on \ + -cpu max \ + -drive "driver=raw,file=$ANDROID_PRODUCT_OUT/system-qemu.img,if=none,id=system" \ + -device virtio-blk-device,drive=system \ + -drive "driver=raw,file=$ANDROID_PRODUCT_OUT/userdata.img,if=none,id=userdata" \ + -device virtio-blk-device,drive=userdata \ + -append "console=ttyAMA0 earlyprintk=ttyAMA0 androidboot.hardware=qemu androidboot.boot_devices=a003e00.virtio_mmio loglevel=9" \ + -m 4096 \ + -no-reboot \ + -nic user,model=virtio-net-pci-non-transitional,hostfwd=tcp:127.0.0.1:5555-172.20.51.1:5555,host=172.20.51.254,net=172.20.51.0/24,dhcpstart=172.20.51.1 \ + -device virtio-gpu-pci \ + -smp 8 \ + -usb \ + -device usb-ehci \ + -device usb-kbd \ + -device usb-mouse \ + -serial mon:stdio \ + "$@" diff --git a/fvpbase/sepolicy/file_contexts b/fvpbase/sepolicy/file_contexts index 31cea9a1..88865bf8 100644 --- a/fvpbase/sepolicy/file_contexts +++ b/fvpbase/sepolicy/file_contexts @@ -1,7 +1,11 @@ /data/vendor/var/run(/.*)? u:object_r:varrun_file:s0 /dev/block/mmcblk0 u:object_r:userdata_block_device:s0 +/dev/block/vda u:object_r:userdata_block_device:s0 +/dev/dri/card0 u:object_r:gpu_device:s0 +/dev/dri/renderD128 u:object_r:gpu_device:s0 +/vendor/bin/hw/android\.hardware\.bluetooth@1\.1-service\.sim u:object_r:hal_bluetooth_sim_exec:s0 /vendor/bin/hw/android\.hardware\.drm@[0-9]+\.[0-9]+-service\.clearkey u:object_r:hal_drm_clearkey_exec:s0 /vendor/bin/hw/android\.hardware\.gatekeeper@1\.0-service.software u:object_r:hal_gatekeeper_default_exec:s0 -/vendor/lib(64)?/libEGL_swiftshader\.so u:object_r:same_process_hal_file:s0 -/vendor/lib(64)?/libGLESv1_CM_swiftshader\.so u:object_r:same_process_hal_file:s0 -/vendor/lib(64)?/libGLESv2_swiftshader\.so u:object_r:same_process_hal_file:s0 +/vendor/lib(64)?/hw/gralloc\.minigbm\.so u:object_r:same_process_hal_file:s0 +/vendor/lib(64)?/libdrm\.so u:object_r:same_process_hal_file:s0 +/system/bin/mini_network.sh u:object_r:mini_network_exec:s0 diff --git a/fvpbase/sepolicy/hal_bluetooth_sim.te b/fvpbase/sepolicy/hal_bluetooth_sim.te new file mode 120000 index 00000000..47e3f6c1 --- /dev/null +++ b/fvpbase/sepolicy/hal_bluetooth_sim.te @@ -0,0 +1 @@ +../../sepolicy/common/hal_bluetooth_sim.te
\ No newline at end of file diff --git a/fvpbase/sepolicy/hal_graphics_composer_default.te b/fvpbase/sepolicy/hal_graphics_composer_default.te new file mode 100644 index 00000000..2cc0bde0 --- /dev/null +++ b/fvpbase/sepolicy/hal_graphics_composer_default.te @@ -0,0 +1 @@ +allow hal_graphics_composer_default self:netlink_kobject_uevent_socket create_socket_perms_no_ioctl; diff --git a/fvpbase/sepolicy/mini_network.te b/fvpbase/sepolicy/mini_network.te new file mode 100644 index 00000000..c330c8c4 --- /dev/null +++ b/fvpbase/sepolicy/mini_network.te @@ -0,0 +1,10 @@ +type mini_network, domain, coredomain; +type mini_network_exec, exec_type, system_file_type, file_type; + +init_daemon_domain(mini_network) + +allow mini_network self:capability net_admin; +allow mini_network self:netlink_route_socket { bind create getattr nlmsg_write read setopt write }; +allow mini_network self:udp_socket { create ioctl }; +allow mini_network shell_exec:file { execute getattr map read }; +allow mini_network system_file:file execute_no_trans; diff --git a/fvpbase/sepolicy/property.te b/fvpbase/sepolicy/property.te index f014ad52..50f7b343 100644 --- a/fvpbase/sepolicy/property.te +++ b/fvpbase/sepolicy/property.te @@ -1 +1 @@ -type vendor_device_prop, property_type; +vendor_internal_prop(vendor_device_prop) diff --git a/fvpbase/sepolicy/property_contexts b/fvpbase/sepolicy/property_contexts index c389bdd3..3ab9778b 100644 --- a/fvpbase/sepolicy/property_contexts +++ b/fvpbase/sepolicy/property_contexts @@ -1 +1,3 @@ vendor.all.modules.ready u:object_r:vendor_device_prop:s0 +vendor.bt.rootcanal_mac_address u:object_r:vendor_bt_rootcanal_prop:s0 +vendor.bt.rootcanal_test_console u:object_r:vendor_bt_rootcanal_prop:s0 diff --git a/fvpbase/sepolicy/vendor_init.te b/fvpbase/sepolicy/vendor_init.te new file mode 100644 index 00000000..2f93fa70 --- /dev/null +++ b/fvpbase/sepolicy/vendor_init.te @@ -0,0 +1 @@ +set_prop(vendor_init, vendor_bt_rootcanal_prop); diff --git a/fvpbase/tools/Android.bp b/fvpbase/tools/Android.bp new file mode 100644 index 00000000..7fcd1f18 --- /dev/null +++ b/fvpbase/tools/Android.bp @@ -0,0 +1,31 @@ +// Copyright (C) 2020 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. + +// The ARM FVP binds to all network interfaces for telnet and adb. This library +// is a workaround to that. The corresponding LD_PRELOAD additions in +// fvpbase/run_model ensure that we only bind to localhost. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + +cc_library_host_shared { + name: "bind_to_localhost", + srcs: ["bind_to_localhost.cpp"], + stl: "none", +} diff --git a/fvpbase/tools/bind_to_localhost.cpp b/fvpbase/tools/bind_to_localhost.cpp new file mode 100644 index 00000000..923455b3 --- /dev/null +++ b/fvpbase/tools/bind_to_localhost.cpp @@ -0,0 +1,30 @@ +// Copyright (C) 2020 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. + +#include <dlfcn.h> +#include <netinet/in.h> +#include <sys/socket.h> +#include <sys/types.h> + +static int (*real_bind)(int sockfd, const sockaddr* addr, socklen_t addrlen) = + (int (*)(int, const sockaddr*, socklen_t))dlsym(RTLD_NEXT, "bind"); + +extern "C" int bind(int sockfd, const sockaddr* addr, socklen_t addrlen) { + if (addr->sa_family != AF_INET) return real_bind(sockfd, addr, addrlen); + const sockaddr_in* sin = (const sockaddr_in*)addr; + if (sin->sin_addr.s_addr != 0) return real_bind(sockfd, addr, addrlen); + sockaddr_in new_sin = *sin; + new_sin.sin_addr.s_addr = 0x0100007f; + return real_bind(sockfd, (sockaddr*)&new_sin, addrlen); +} diff --git a/fvpbase/ueventd.fvp.rc b/fvpbase/ueventd.fvp.rc new file mode 100644 index 00000000..921bdf2e --- /dev/null +++ b/fvpbase/ueventd.fvp.rc @@ -0,0 +1 @@ +/dev/ion 0664 system system diff --git a/gnss/Android.bp b/gnss/Android.bp index 0c5de5dd..add0c70d 100644 --- a/gnss/Android.bp +++ b/gnss/Android.bp @@ -14,6 +14,15 @@ * limitations under the License. */ +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "android.hardware.gnss@2.0-service.ranchu", vendor: true, diff --git a/gnss/data_sink.cpp b/gnss/data_sink.cpp index 4b0c52cf..357ee7fe 100644 --- a/gnss/data_sink.cpp +++ b/gnss/data_sink.cpp @@ -21,7 +21,7 @@ namespace goldfish { void DataSink::gnssLocation(const ahg20::GnssLocation& loc) const { std::unique_lock<std::mutex> lock(mtx); - if (cb20) { + if (cb20 && isWarmedUd()) { cb20->gnssLocationCb_2_0(loc); } } @@ -43,7 +43,7 @@ void DataSink::gnssStatus(const ahg10::IGnssCallback::GnssStatusValue status) co void DataSink::gnssNmea(const ahg10::GnssUtcTime t, const hidl_string& nmea) const { std::unique_lock<std::mutex> lock(mtx); - if (cb20) { + if (cb20 && isWarmedUd()) { cb20->gnssNmeaCb(t, nmea); } } @@ -58,4 +58,13 @@ void DataSink::cleanup() { cb20 = nullptr; } +void DataSink::start() { + std::unique_lock<std::mutex> lock(mtx); + warmedUpTime = std::chrono::steady_clock::now() + std::chrono::milliseconds(3500); +} + +bool DataSink::isWarmedUd() const { + return std::chrono::steady_clock::now() >= warmedUpTime; +} + } // namespace goldfish diff --git a/gnss/data_sink.h b/gnss/data_sink.h index d182f2d0..7c6678bf 100644 --- a/gnss/data_sink.h +++ b/gnss/data_sink.h @@ -16,6 +16,7 @@ #pragma once #include <android/hardware/gnss/2.0/IGnss.h> +#include <chrono> #include <mutex> namespace goldfish { @@ -35,10 +36,14 @@ public: void gnssNmea(const ahg10::GnssUtcTime, const hidl_string&) const; void setCallback20(sp<ahg20::IGnssCallback>); + void start(); void cleanup(); private: + bool isWarmedUd() const; + sp<ahg20::IGnssCallback> cb20; + std::chrono::steady_clock::time_point warmedUpTime; mutable std::mutex mtx; }; diff --git a/gnss/gnss.cpp b/gnss/gnss.cpp index 8fa81fcc..d1a4f832 100644 --- a/gnss/gnss.cpp +++ b/gnss/gnss.cpp @@ -96,6 +96,7 @@ Return<bool> Gnss20::setPositionMode_1_1(ahg10::IGnss::GnssPositionMode mode, Return<bool> Gnss20::start() { std::unique_lock<std::mutex> lock(m_gnssHwConnMtx); if (m_gnssHwConn) { + m_dataSink.start(); return m_gnssHwConn->start(); } else { return false; diff --git a/gnss/gnss_measurement.cpp b/gnss/gnss_measurement.cpp index 6acedd4f..0885c284 100644 --- a/gnss/gnss_measurement.cpp +++ b/gnss/gnss_measurement.cpp @@ -16,10 +16,82 @@ #include <chrono> #include "gnss_measurement.h" -#include "util.h" namespace goldfish { using ::android::hardware::hidl_vec; +using GnssClockFlags10 = ahg10::IGnssMeasurementCallback::GnssClockFlags; +using GnssMeasurementT20 = ahg20::IGnssMeasurementCallback::GnssMeasurement; + +namespace { +void initGnssData(GnssData20& data, + int64_t elapsedRealtimeNs, + int64_t timeNs, + int64_t fullBiasNs, + double biasUncertaintyNs, + size_t nMeasurements) { + data.elapsedRealtime.flags = ahg20::ElapsedRealtimeFlags::HAS_TIMESTAMP_NS | 0; + data.elapsedRealtime.timestampNs = static_cast<uint64_t>(elapsedRealtimeNs); + data.clock.gnssClockFlags = GnssClockFlags10::HAS_FULL_BIAS | 0; + data.clock.timeNs = timeNs; + data.clock.fullBiasNs = fullBiasNs; + data.clock.biasUncertaintyNs = biasUncertaintyNs; + data.measurements.resize(nMeasurements); +} + +GnssMeasurementT20 makeGnssMeasurementT20(int svid, + int state, + int64_t receivedSvTimeInNs, + int64_t receivedSvTimeUncertaintyInNs, + double cN0DbHz, + double pseudorangeRateMps, + double pseudorangeRateUncertaintyMps, + int accumulatedDeltaRangeState, + double accumulatedDeltaRangeM, + double accumulatedDeltaRangeUncertaintyM, + int multipathIndicator, + int constellation) { + using GnssMeasurementFlags10 = ahg10::IGnssMeasurementCallback::GnssMeasurementFlags; + using GnssMultipathIndicator10 = ahg10::IGnssMeasurementCallback::GnssMultipathIndicator; + using GnssAccumulatedDeltaRangeState11 = ahg11::IGnssMeasurementCallback::GnssAccumulatedDeltaRangeState; + using GnssMeasurementState20 = ahg20::IGnssMeasurementCallback::GnssMeasurementState; + + GnssMeasurementT20 m20; + auto& m11 = m20.v1_1; + auto& m10 = m11.v1_0; + + m10.flags = GnssMeasurementFlags10::HAS_CARRIER_FREQUENCY | 0; + m10.svid = svid; + m10.receivedSvTimeInNs = receivedSvTimeInNs; + m10.receivedSvTimeUncertaintyInNs = receivedSvTimeUncertaintyInNs; + m10.cN0DbHz = cN0DbHz; + m10.pseudorangeRateMps = pseudorangeRateMps; + m10.pseudorangeRateUncertaintyMps = pseudorangeRateUncertaintyMps; + m10.accumulatedDeltaRangeM = accumulatedDeltaRangeM; + m10.accumulatedDeltaRangeUncertaintyM = accumulatedDeltaRangeUncertaintyM; + m10.carrierFrequencyHz = 1.59975e+09; + m10.multipathIndicator = static_cast<GnssMultipathIndicator10>(multipathIndicator); + m11.accumulatedDeltaRangeState = + GnssAccumulatedDeltaRangeState11::ADR_STATE_UNKNOWN | accumulatedDeltaRangeState; + m20.codeType = "UNKNOWN"; + m20.state = GnssMeasurementState20::STATE_UNKNOWN | state; + m20.constellation = static_cast<ahg20::GnssConstellationType>(constellation); + + return m20; +} +} // namespace + +GnssMeasurement20::GnssMeasurement20() { + m_gnssData.resize(1); + + initGnssData(m_gnssData[0], 139287, 116834000000, -1189181444165780000, 5.26068202130163, 7); + m_gnssData[0].measurements[0] = makeGnssMeasurementT20(22, 47, 3927349114, 29, 29.9917297363281, 245.509362821673, 0.148940800975766, 1, 6620.74237064615, 0.00271145859733223, 0, 1); + m_gnssData[0].measurements[1] = makeGnssMeasurementT20(23, 47, 3920005435, 14, 36.063377380371, -731.947951627658, 0.0769754027959242, 1, -23229.096048105, 0.00142954161856323, 0, 1); + m_gnssData[0].measurements[2] = makeGnssMeasurementT20(25, 47, 3923720994, 56, 24.5171585083007, -329.789995021822, 0.277918601850871, 1, -15511.1976492851, 0.00509250536561012, 0, 1); + m_gnssData[0].measurements[3] = makeGnssMeasurementT20(31, 47, 3925772934, 11, 37.9193840026855, -380.23772244582, 0.0602980729893803, 1, -11325.9094456612, 0.00115450704470276, 0, 1); + m_gnssData[0].measurements[4] = makeGnssMeasurementT20(32, 47, 3919018415, 21, 32.8980560302734, 581.800347848025, 0.109060249597082, 1, 15707.8963147985, 0.00205808319151401, 0, 1); + m_gnssData[0].measurements[5] = makeGnssMeasurementT20(10, 227, 69142929947304, 127, 23.432445526123, 259.17838762857, 0.31591691295607, 4, 8152.78081298147, 3.40282346638528E+38, 0, 3); + m_gnssData[0].measurements[6] = makeGnssMeasurementT20(2, 227, 69142935176327, 41, 33.180908203125, -53.8773853795901, 0.104984458760586, 1, -1708.08166640048, 0.00196184404194355, 0, 3); +} GnssMeasurement20::~GnssMeasurement20() { if (m_isRunning) { @@ -72,74 +144,10 @@ void GnssMeasurement20::stopLocked() { } void GnssMeasurement20::update() { - using GnssMeasurement20 = ahg20::IGnssMeasurementCallback::GnssMeasurement; - using GnssAccumulatedDeltaRangeState10 = ahg10::IGnssMeasurementCallback::GnssAccumulatedDeltaRangeState; - using GnssMeasurementFlags10 = ahg10::IGnssMeasurementCallback::GnssMeasurementFlags; - using GnssMultipathIndicator10 = ahg10::IGnssMeasurementCallback::GnssMultipathIndicator; - using GnssMeasurementState20 = ahg20::IGnssMeasurementCallback::GnssMeasurementState; - using GnssData = ahg20::IGnssMeasurementCallback::GnssData; - - ahg10::IGnssMeasurementCallback::GnssMeasurement measurement10 = { - .flags = GnssMeasurementFlags10::HAS_CARRIER_FREQUENCY | 0, - .svid = 6, - .constellation = ahg10::GnssConstellationType::GPS, - .timeOffsetNs = 0.0, - .receivedSvTimeInNs = 8195997131077, - .receivedSvTimeUncertaintyInNs = 15, - .cN0DbHz = 30.0, - .pseudorangeRateMps = -484.13739013671875, - .pseudorangeRateUncertaintyMps = 0.12, - .accumulatedDeltaRangeState = GnssAccumulatedDeltaRangeState10::ADR_STATE_UNKNOWN | 0, - .accumulatedDeltaRangeM = 0.0, - .accumulatedDeltaRangeUncertaintyM = 0.0, - .carrierFrequencyHz = 1.59975e+09, - .multipathIndicator = GnssMultipathIndicator10::INDICATOR_UNKNOWN - }; - ahg11::IGnssMeasurementCallback::GnssMeasurement measurement11 = { - .v1_0 = measurement10, - .accumulatedDeltaRangeState = 0 - }; - - ahg20::IGnssMeasurementCallback::GnssMeasurement measurement20 = { - .v1_1 = measurement11, - .codeType = "C", - .state = GnssMeasurementState20::STATE_CODE_LOCK | - GnssMeasurementState20::STATE_BIT_SYNC | - GnssMeasurementState20::STATE_SUBFRAME_SYNC | - GnssMeasurementState20::STATE_TOW_DECODED | - GnssMeasurementState20::STATE_GLO_STRING_SYNC | - GnssMeasurementState20::STATE_GLO_TOD_DECODED, - .constellation = ahg20::GnssConstellationType::GPS, - }; - - hidl_vec<GnssMeasurement20> measurements(1); - measurements[0] = measurement20; - - const int64_t nowNs = util::nowNanos(); - const int64_t fullBiasNs = (nowNs % 15331) * ((nowNs & 1) ? -1 : 1); - const int64_t hwTimeNs = nowNs + fullBiasNs; // local hardware clock - - ahg10::IGnssMeasurementCallback::GnssClock clock10 = { - .gnssClockFlags = 0, - .leapSecond = 0, - .timeNs = hwTimeNs, - .timeUncertaintyNs = 4.5, - .fullBiasNs = fullBiasNs, - .biasNs = 1.5, - .biasUncertaintyNs = .7, - .driftNsps = -51.757811607455452, - .driftUncertaintyNsps = 310.64968328491528, - .hwClockDiscontinuityCount = 1 - }; - - GnssData gnssData = { - .measurements = measurements, - .clock = clock10, - .elapsedRealtime = util::makeElapsedRealtime(util::nowNanos()) - }; - std::unique_lock<std::mutex> lock(m_mtx); - m_callback->gnssMeasurementCb_2_0(gnssData); + + m_callback->gnssMeasurementCb_2_0(m_gnssData[m_gnssDataIndex]); + m_gnssDataIndex = (m_gnssDataIndex + 1) % m_gnssData.size(); } /// old and deprecated ///////////////////////////////////////////////////////// @@ -151,5 +159,4 @@ Return<GnssMeasurementStatus10> GnssMeasurement20::setCallback(const sp<ahg10::I return GnssMeasurementStatus10::ERROR_GENERIC; } - } // namespace goldfish diff --git a/gnss/gnss_measurement.h b/gnss/gnss_measurement.h index 8da3b4c1..10110807 100644 --- a/gnss/gnss_measurement.h +++ b/gnss/gnss_measurement.h @@ -26,11 +26,13 @@ namespace ahg20 = ahg::V2_0; namespace ahg11 = ahg::V1_1; namespace ahg10 = ahg::V1_0; using GnssMeasurementStatus10 = ahg10::IGnssMeasurement::GnssMeasurementStatus; +using GnssData20 = ahg20::IGnssMeasurementCallback::GnssData; using ::android::sp; using ::android::hardware::Return; struct GnssMeasurement20 : public ahg20::IGnssMeasurement { + GnssMeasurement20(); ~GnssMeasurement20(); // Methods from V2_0::IGnssMeasurement follow. @@ -51,7 +53,10 @@ private: sp<ahg20::IGnssMeasurementCallback> m_callback; std::thread m_thread; std::atomic<bool> m_isRunning; + int m_gnssDataIndex = 0; mutable std::mutex m_mtx; + + std::vector<GnssData20> m_gnssData; }; } // namespace goldfish diff --git a/init.goldfish.rc b/init.goldfish.rc deleted file mode 100644 index efe12572..00000000 --- a/init.goldfish.rc +++ /dev/null @@ -1,115 +0,0 @@ - -on init - -on boot - setprop ARGH ARGH - setprop net.eth0.gw 10.0.2.2 - setprop net.eth0.dns1 10.0.2.3 - setprop net.dns1 10.0.2.3 - setprop net.gprs.local-ip 10.0.2.15 - setprop persist.adb.notify 1 - setprop persist.sys.usb.config adb - setprop qemu.adb.secure 0 - setprop ro.adb.secure 1 - setprop ro.radio.use-ppp no - setprop ro.build.product generic - setprop ro.product.device generic - -# fake some battery state - setprop status.battery.state Slow - setprop status.battery.level 5 - setprop status.battery.level_raw 50 - setprop status.battery.level_scale 9 - -# set up the GPU caching - setprop ro.hwui.texture_cache_size 72 - setprop ro.hwui.layer_cache_size 48 - setprop ro.hwui.r_buffer_cache_size 8 - setprop ro.hwui.path_cache_size 32 - setprop ro.hwui.gradient_cache_size 1 - setprop ro.hwui.drop_shadow_cache_size 6 - setprop ro.hwui.texture_cache_flushrate 0.4 - setprop ro.hwui.text_small_cache_width 1024 - setprop ro.hwui.text_small_cache_height 1024 - setprop ro.hwui.text_large_cache_width 2048 - setprop ro.hwui.text_large_cache_height 1024 - -# disable some daemons the emulator doesn't want - stop dund - stop akmd - -# start essential services - start qemud - start goldfish-logcat - start goldfish-setup - - setprop ro.setupwizard.mode EMULATOR - -# enable Google-specific location features, -# like NetworkLocationProvider and LocationCollector - setprop ro.com.google.locationfeatures 1 - -# For the emulator, which bypasses Setup Wizard, you can specify -# account info for the device via these two properties. Google -# Login Service will insert these accounts into the database when -# it is created (ie, after a data wipe). -# -# setprop ro.config.hosted_account username@hosteddomain.org:password -# setprop ro.config.google_account username@gmail.com:password -# -# You MUST have a Google account on the device, and you MAY -# additionally have a hosted account. No other configuration is -# supported, and arbitrary breakage may result if you specify -# something else. - -on fs - mount_all /fstab.goldfish - -#emulator is not much useful before boot complete -#start it later -on property:sys.boot_completed=1 - setprop sys.usb.config adb - start adbd - -service goldfish-setup /system/etc/init.goldfish.sh - user root - group root - oneshot - -# The qemu-props program is used to set various system -# properties on boot. It must be run early during the boot -# process to avoid race conditions with other daemons that -# might read them (e.g. surface flinger), so define it in -# class 'core' -# -service qemu-props /system/bin/qemu-props - class core - user root - group root - oneshot - -service qemud /system/bin/qemud - socket qemud stream 666 - oneshot - -# -Q is a special logcat option that forces the -# program to check wether it runs on the emulator -# if it does, it redirects its output to the device -# named by the androidboot.console kernel option -# if not, is simply exits immediately -# logd user added to prevent logcat from logging content. -# log group added to support access to read logs socket. -service goldfish-logcat /system/bin/logcat -Q - user logd - group log - oneshot - -service fingerprintd /system/bin/fingerprintd - class late_start - user system - -service bugreport /system/bin/dumpstate -d -p - class main - disabled - oneshot - keycodes 114 115 116 diff --git a/init.goldfish.sh b/init.goldfish.sh deleted file mode 100755 index 025a9c45..00000000 --- a/init.goldfish.sh +++ /dev/null @@ -1,77 +0,0 @@ -#!/system/bin/sh - -# Setup networking when boot starts -ifconfig eth0 10.0.2.15 netmask 255.255.255.0 up -route add default gw 10.0.2.2 dev eth0 - -wifi=`getprop ro.kernel.qemu.wifi` -case "$wifi" in - 1) /system/bin/init.wifi.sh - ;; -esac - -# ro.kernel.android.qemud is normally set when we -# want the RIL (radio interface layer) to talk to -# the emulated modem through qemud. -# -# However, this will be undefined in two cases: -# -# - When we want the RIL to talk directly to a guest -# serial device that is connected to a host serial -# device by the emulator. -# -# - We don't want to use the RIL but the VM-based -# modem emulation that runs inside the guest system -# instead. -# -# The following detects the latter case and sets up the -# system for it. -# -qemud=`getprop ro.kernel.android.qemud` -case "$qemud" in - "") - radio_ril=`getprop ro.kernel.android.ril` - case "$radio_ril" in - "") - # no need for the radio interface daemon - # telephony is entirely emulated in Java - setprop ro.radio.noril yes - stop ril-daemon - ;; - esac - ;; -esac - -# Setup additionnal DNS servers if needed -num_dns=`getprop ro.kernel.ndns` -case "$num_dns" in - 2) setprop net.eth0.dns2 10.0.2.4 - ;; - 3) setprop net.eth0.dns2 10.0.2.4 - setprop net.eth0.dns3 10.0.2.5 - ;; - 4) setprop net.eth0.dns2 10.0.2.4 - setprop net.eth0.dns3 10.0.2.5 - setprop net.eth0.dns4 10.0.2.6 - ;; -esac - -# disable boot animation for a faster boot sequence when needed -boot_anim=`getprop ro.kernel.android.bootanim` -case "$boot_anim" in - 0) setprop debug.sf.nobootanimation 1 - ;; -esac - -# set up the second interface (for inter-emulator connections) -# if required -my_ip=`getprop net.shared_net_ip` -case "$my_ip" in - "") - ;; - *) ifconfig eth1 "$my_ip" netmask 255.255.255.0 up - ;; -esac - -# take the wake lock -echo "emulator_wake_lock" > /sys/power/wake_lock diff --git a/init.qemu-adb-keys.sh b/init.qemu-adb-keys.sh new file mode 100755 index 00000000..8e304849 --- /dev/null +++ b/init.qemu-adb-keys.sh @@ -0,0 +1,8 @@ +#!/system/bin/sh + +if [[ -f /data/misc/adb/adb_keys ]]; then + echo "qemu-adb-setup: /data/misc/adb/adb_keys exists. Skipping qemu adb setup" > /dev/kmsg +else + echo "qemu-adb-setup: Copying over adb_keys" > /dev/kmsg + setprop vendor.qemu.adb.copykey 1 +fi diff --git a/init.ranchu-core.sh b/init.ranchu-core.sh index e6c9de4e..9575dffb 100755 --- a/init.ranchu-core.sh +++ b/init.ranchu-core.sh @@ -1,17 +1,7 @@ #!/vendor/bin/sh -#init cannot access ro.kernel.android.bootanim, -#so do a translation into vendor.qemu space -bootanim=`getprop ro.kernel.android.bootanim` -case "$bootanim" in - "") - ;; - *) setprop vendor.qemu.android.bootanim 0 - ;; -esac - # take the wake lock -allowsuspend=`getprop ro.kernel.qemu.allowsuspend` +allowsuspend=`getprop ro.boot.qemu.allowsuspend` case "$allowsuspend" in "") echo "emulator_wake_lock" > /sys/power/wake_lock ;; diff --git a/init.ranchu-net.sh b/init.ranchu-net.sh index a5d9acfc..fa468a68 100755 --- a/init.ranchu-net.sh +++ b/init.ranchu-net.sh @@ -1,17 +1,21 @@ #!/vendor/bin/sh -# Check if VirtIO Wi-Fi is enabled. If so, run the DHCP client - -wifi_virtio=`getprop ro.kernel.qemu.virtiowifi` +# Check if VirtIO Wi-Fi is enabled. If so, create a mac80211_hwsim radio +# and run the DHCP client +wifi_virtio=`getprop ro.boot.qemu.virtiowifi` case "$wifi_virtio" in - 1) setprop ctl.start dhcpclient_wifi - ;; + 1) wifi_mac_prefix=`getprop vendor.net.wifi_mac_prefix` + if [ -n "$wifi_mac_prefix" ]; then + /vendor/bin/mac80211_create_radios 1 $wifi_mac_prefix || exit 1 + fi + setprop ctl.start dhcpclient_wifi + ;; esac # Check if WiFi with mac80211_hwsim is enabled. If so, run the WiFi init script. If not we just # have to run the DHCP client in the default namespace and that will set up # all the networking. -wifi_hwsim=`getprop ro.kernel.qemu.wifi` +wifi_hwsim=`getprop ro.boot.qemu.wifi` case "$wifi_hwsim" in 1) /vendor/bin/init.wifi.sh ;; @@ -21,7 +25,7 @@ esac # set up the second interface (for inter-emulator connections) # if required -my_ip=`getprop net.shared_net_ip` +my_ip=`getprop vendor.net.shared_net_ip` case "$my_ip" in "") ;; diff --git a/init.ranchu.rc b/init.ranchu.rc index d2e5bded..d4cef384 100644 --- a/init.ranchu.rc +++ b/init.ranchu.rc @@ -1,11 +1,30 @@ +on early-fs + start vold + on fs - mount_all /vendor/etc/fstab.ranchu + mount_all /vendor/etc/fstab.ranchu --early + +on late-fs + # Mount RW partitions which need run fsck + exec_start wait_for_keymaster + mount_all /vendor/etc/fstab.ranchu --late on early-init mount proc proc /proc remount hidepid=2,gid=3009 - setprop ro.hardware.egl emulation setprop ro.hardware.vulkan ranchu + # true if ram is <= 2G + setprop ro.config.low_ram ${ro.boot.config.low_ram} + setprop dalvik.vm.dex2oat64.enabled 1 + + setprop ro.soc.manufacturer AOSP + setprop ro.soc.model ranchu + + # DEPRECATED, use ro.boot.qemu instead. The GTS tests still refer to + # ro.kernel.qemu to decide if a device is emulator. Should be removed once + # GTS tests are migrated to ro.boot.qemu. + setprop ro.kernel.qemu 1 + on init # set RLIMIT_MEMLOCK to 8MB for BPF network statistics setrlimit memlock 8388608 8388608 @@ -43,10 +62,12 @@ on init on post-fs-data setprop vold.post_fs_data_done 1 + mkdir /data/vendor/adb 0755 root root mkdir /data/vendor/var 0755 root root mkdir /data/vendor/var/run 0755 root root mkdir /data/vendor/var/run/netns 0755 root root - start ranchu-net + + start qemu-adb-keys on zygote-start # Create the directories used by the Wireless subsystem @@ -55,19 +76,19 @@ on zygote-start mkdir /data/vendor/wifi/wpa/sockets 0770 wifi wifi on boot - setprop ro.hardware.egl emulation - setprop debug.sf.vsync_reactor 0 + setprop ro.hardware.egl ${ro.boot.hardwareegl:-emulation} + setprop debug.sf.vsync_reactor_ignore_present_fences true setprop debug.hwui.renderer opengl - setprop debug.hwui.renderer ${ro.kernel.qemu.uirenderer} - setprop ro.opengles.version ${ro.kernel.qemu.opengles.version} + setprop debug.hwui.renderer ${ro.boot.debug.hwui.renderer} + setprop ro.opengles.version ${ro.boot.opengles.version} + setprop ro.surface_flinger.supports_background_blur 1 setprop ro.zygote.disable_gl_preload 1 - # 0: omx; 4: c2 default now - setprop debug.stagefright.ccodec 4 - setprop debug.stagefright.ccodec ${ro.kernel.qemu.media.ccodec} + setprop debug.stagefright.ccodec ${ro.boot.debug.stagefright.ccodec} setprop dalvik.vm.heapsize 192m - setprop dalvik.vm.heapsize ${ro.kernel.qemu.dalvik.vm.heapsize} + setprop dalvik.vm.heapsize ${ro.boot.dalvik.vm.heapsize} + setprop dalvik.vm.checkjni ${ro.boot.dalvik.vm.checkjni} chown root system /sys/power/wake_lock chown root system /sys/power/wake_unlock setprop ro.hardware.audio.primary goldfish @@ -75,9 +96,7 @@ on boot setprop wifi.interface wlan0 setprop wifi.direct.interface p2p-dev-wlan0 - start goldfish-logcat - - # Create a dummy USB gadget to allow sysfs testing + # Create an unused USB gadget to allow sysfs testing mkdir /config/usb_gadget/g1 0770 root root service ranchu-setup /vendor/bin/init.ranchu-core.sh @@ -86,16 +105,35 @@ service ranchu-setup /vendor/bin/init.ranchu-core.sh group root oneshot +service qemu-adb-setup /system_ext/bin/init.qemu-adb-keys.sh + class core + user root + group shell + disabled # Started when qemu-adb-keys is stopped + oneshot + +on property:vendor.qemu.vport.gnss=* + symlink ${vendor.qemu.vport.gnss} /dev/gnss0 + on property:vendor.qemu.timezone=* setprop persist.sys.timezone ${vendor.qemu.timezone} -on property:vendor.qemu.android.bootanim=0 +on property:ro.boot.debug.sf.nobootanimation=1 setprop debug.sf.nobootanimation 1 on property:dev.bootcomplete=1 setprop vendor.qemu.dev.bootcomplete 1 start ranchu-setup +on post-fs-data && property:ro.boot.qemu.wifi=1 + start create_router_ns + +on post-fs-data && property:ro.boot.qemu.virtiowifi=1 + start ranchu-net + +on property:vendor.qemu.networknamespace=ready + start ranchu-net + service ranchu-net /vendor/bin/init.ranchu-net.sh class late_start user root @@ -113,6 +151,12 @@ service netmgr /vendor/bin/execns router /vendor/bin/netmgr --if-prefix wlan1 -- group root wifi disabled +service create_router_ns /vendor/bin/createns router + user root + group root + disabled + oneshot + service wifi_forwarder /vendor/bin/wifi_forwarder user root group root wifi @@ -148,18 +192,17 @@ service qemu-props /vendor/bin/qemu-props group root oneshot -# -Q is a special logcat option that forces the -# program to check wether it runs on the emulator -# if it does, it redirects its output to the device -# named by the androidboot.console kernel option -# if not, is simply exits immediately -# logd user added to prevent logcat from logging content. -# log group added to support access to read logs socket. -service goldfish-logcat /system/bin/logcat -Q - user logd - group log +service qemu-adb-keys /vendor/bin/qemu-adb-keys + class core + user root + group root oneshot +service goldfish-logcat /system/bin/logcat -f /dev/hvc1 ${ro.boot.logcat} + class main + user logd + group root logd + service bugreport /system/bin/dumpstate -d -p -z class main disabled diff --git a/init.system_ext.rc b/init.system_ext.rc new file mode 100644 index 00000000..5f8cb4e0 --- /dev/null +++ b/init.system_ext.rc @@ -0,0 +1,7 @@ +on property:init.svc.qemu-adb-keys=stopped + start qemu-adb-setup + +on property:vendor.qemu.adb.copykey=1 + copy /data/vendor/adb/adb_keys /data/misc/adb/adb_keys + chown system shell /data/misc/adb/adb_keys + chmod 0640 /data/misc/adb/adb_keys diff --git a/manifest.xml b/manifest.xml index 8d8d572e..6f504a06 100644 --- a/manifest.xml +++ b/manifest.xml @@ -51,15 +51,6 @@ </interface> </hal> <hal format="hidl"> - <name>android.hardware.configstore</name> - <transport>hwbinder</transport> - <version>1.1</version> - <interface> - <name>ISurfaceFlingerConfigs</name> - <instance>default</instance> - </interface> - </hal> - <hal format="hidl"> <name>android.hardware.graphics.allocator</name> <transport>hwbinder</transport> <version>3.0</version> @@ -87,6 +78,15 @@ </interface> </hal> <hal format="hidl"> + <name>android.hardware.media.c2</name> + <transport>hwbinder</transport> + <version>1.0</version> + <interface> + <name>IComponentStore</name> + <instance>default</instance> + </interface> + </hal> + <hal format="hidl"> <name>android.hardware.media.omx</name> <transport>hwbinder</transport> <version>1.0</version> @@ -99,10 +99,19 @@ <instance>default</instance> </interface> </hal> + <hal format="hidl"> + <name>android.hardware.radio.config</name> + <transport>hwbinder</transport> + <version>1.3</version> + <interface> + <name>IRadioConfig</name> + <instance>default</instance> + </interface> + </hal> <hal format="hidl"> <name>android.hardware.radio</name> <transport>hwbinder</transport> - <version>1.1</version> + <version>1.6</version> <interface> <name>IRadio</name> <instance>slot1</instance> diff --git a/minimal_system.mk b/minimal_system.mk new file mode 100644 index 00000000..95539d98 --- /dev/null +++ b/minimal_system.mk @@ -0,0 +1,63 @@ +# +# Copyright 2020 Arm Ltd. All rights reserved. +# +# 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. +# + +# This file contains system partition contents needed for a minimal +# Android build that boots to shell. The items here should be present in +# build/make/target/product/base_system.mk. + +PRODUCT_PACKAGES += \ + adbd_system_api \ + apexd \ + boringssl_self_test \ + cgroups.json \ + com.android.adbd \ + com.android.conscrypt \ + debuggerd \ + hwservicemanager \ + init.environ.rc \ + init_system \ + libbinder \ + libc.bootstrap \ + libdl.bootstrap \ + libdl_android.bootstrap \ + libm.bootstrap \ + libstdc++ \ + linker \ + linkerconfig \ + logcat \ + logd \ + odsign \ + run-as \ + selinux_policy_system \ + servicemanager \ + shell_and_utilities_system \ + tombstoned \ + vold \ + +PRODUCT_HOST_PACKAGES += \ + adb \ + +PRODUCT_COPY_FILES += \ + system/core/rootdir/init.usb.rc:system/etc/init/hw/init.usb.rc \ + system/core/rootdir/init.usb.configfs.rc:system/etc/init/hw/init.usb.configfs.rc \ + system/core/rootdir/etc/hosts:system/etc/hosts \ + system/core/rootdir/etc/public.libraries.android.txt:/system/etc/public.libraries.txt + +PRODUCT_SYSTEM_PROPERTIES += debug.atrace.tags.enableflags=0 + +PRODUCT_PACKAGES_DEBUG := \ + strace \ + su \ diff --git a/network/netmgr/Android.bp b/network/netmgr/Android.bp index cc8f8758..e5d95140 100644 --- a/network/netmgr/Android.bp +++ b/network/netmgr/Android.bp @@ -14,6 +14,15 @@ // limitations under the License. // +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "netmgr", vendor: true, diff --git a/network/wifi_forwarder/Android.bp b/network/wifi_forwarder/Android.bp index e08bc25c..26fd018c 100644 --- a/network/wifi_forwarder/Android.bp +++ b/network/wifi_forwarder/Android.bp @@ -14,6 +14,15 @@ // limitations under the License. // +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "wifi_forwarder", vendor: true, diff --git a/network/wifi_forwarder/remote_connection.cpp b/network/wifi_forwarder/remote_connection.cpp index 48fca7ff..69e7b87c 100644 --- a/network/wifi_forwarder/remote_connection.cpp +++ b/network/wifi_forwarder/remote_connection.cpp @@ -285,7 +285,7 @@ bool RemoteConnection::sendFrame(std::unique_ptr<Frame> frame) { } totalSize -= written; // Determine how much is left to write after this - while (current < count && written >= iov[current].iov_len) { + while (current < count && static_cast<size_t>(written) >= iov[current].iov_len) { written -= iov[current++].iov_len; } if (current == count) { diff --git a/overlay/frameworks/base/core/res/res/values/config.xml b/overlay/frameworks/base/core/res/res/values/config.xml index b9f0babf..119ac533 100644 --- a/overlay/frameworks/base/core/res/res/values/config.xml +++ b/overlay/frameworks/base/core/res/res/values/config.xml @@ -54,4 +54,13 @@ <item>0:2:15</item> <!-- ID0:Fingerprint:Strong --> </string-array> + <!-- The device states (supplied by DeviceStateManager) that should be treated as folded by the + display fold controller. --> + <integer-array name="config_foldedDeviceStates" translatable="false"> + <item>0</item> <!-- CLOSED --> + </integer-array> + + <!-- This device is able to support the microphone and camera global toggles. --> + <bool name="config_supportsMicToggle">true</bool> + <bool name="config_supportsCamToggle">true</bool> </resources> diff --git a/overlay/frameworks/base/packages/overlays/DisplayCutoutEmulationEmu01/Android.bp b/overlay/frameworks/base/packages/overlays/DisplayCutoutEmulationEmu01/Android.bp deleted file mode 100644 index 1bb89a1d..00000000 --- a/overlay/frameworks/base/packages/overlays/DisplayCutoutEmulationEmu01/Android.bp +++ /dev/null @@ -1,10 +0,0 @@ -runtime_resource_overlay { - name: "DisplayCutoutEmulationEmu01Overlay", - package_name: "DisplayCutoutEmulationEmu01Overlay", - theme: "DisplayCutoutEmulationEmu01", - certificate: "platform", - resource_dirs: [ - "res", - ], - product_specific: true, -} diff --git a/overlay/frameworks/base/packages/overlays/DisplayCutoutEmulationEmu01/Android.mk b/overlay/frameworks/base/packages/overlays/DisplayCutoutEmulationEmu01/Android.mk new file mode 100644 index 00000000..4b70089f --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/DisplayCutoutEmulationEmu01/Android.mk @@ -0,0 +1,16 @@ +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := DisplayCutoutEmulationEmu01 +LOCAL_CERTIFICATE := platform + +LOCAL_SRC_FILES := $(call all-subdir-java-files) + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := DisplayCutoutEmulationEmu01Overlay +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/Android.mk new file mode 100644 index 00000000..6973d811 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/Android.mk @@ -0,0 +1,31 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := EmulationPixel2XL + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := EmulationPixel2XLOverlay +LOCAL_SDK_VERSION := current + +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/AndroidManifest.xml new file mode 100644 index 00000000..a3802baa --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.internal.emulation.pixel_2_xl" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="android" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/radio/ril/misc.h b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/res/values/config.xml index 9e65ab3d..8cf674f7 100644 --- a/radio/ril/misc.h +++ b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/res/values/config.xml @@ -1,6 +1,7 @@ -/* //device/system/reference-ril/misc.h -** -** Copyright 2006, The Android Open Source Project +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2021, 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. @@ -14,9 +15,9 @@ ** See the License for the specific language governing permissions and ** limitations under the License. */ -#include <stdbool.h> +--> -/** returns 1 if line starts with prefix, 0 if it does not */ -int strStartsWith(const char *line, const char *prefix); -/** Returns true iff running this process in an emulator VM */ -bool isInEmulator(void);
\ No newline at end of file +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- Height of the status bar --> + <dimen name="status_bar_height_portrait">28dp</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/~Android.bp b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/~Android.bp new file mode 100644 index 00000000..a9cbf8c6 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_2_xl/AndroidOverlay/~Android.bp @@ -0,0 +1,30 @@ +// +// Copyright (C) 2021, 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 { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "frameworks_base_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["frameworks_base_license"], +} + +runtime_resource_overlay { + name: "EmulationPixel2XLOverlay", + theme: "EmulationPixel2XL", + product_specific: true, +} diff --git a/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..413d5852 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/Android.mk @@ -0,0 +1,31 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel2XL + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel2XLOverlay +LOCAL_SDK_VERSION := current + +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..39925fb3 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_2_xl" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..2a782d86 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_2_xl/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,20 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2019, 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. +*/ +--> +<resources> + <dimen name="rounded_corner_content_padding">8dp</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..ba204586 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel3 + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel3Overlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..87336d45 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_3" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..1f2e4026 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,27 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2021, 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. +*/ +--> +<resources> + <dimen name="rounded_corner_content_padding">28px</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">450px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">780px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">980px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/Android.mk new file mode 100644 index 00000000..41e28043 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/Android.mk @@ -0,0 +1,31 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := EmulationPixel3XL + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := EmulationPixel3XLOverlay +LOCAL_SDK_VERSION := current + +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/AndroidManifest.xml new file mode 100644 index 00000000..a557c09b --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.internal.emulation.pixel_3_xl" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="android" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/res/values/config.xml new file mode 100644 index 00000000..6db3171a --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3_xl/AndroidOverlay/res/values/config.xml @@ -0,0 +1,66 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2021, 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. +*/ +--> + +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- The bounding path of the cutout region of the main built-in display. + Must either be empty if there is no cutout region, or a string that is parsable by + {@link android.util.PathParser}. + + The path is assumed to be specified in display coordinates with pixel units and in + the display's native orientation, with the origin of the coordinate system at the + center top of the display. + + To facilitate writing device-independent emulation overlays, the marker `@dp` can be + appended after the path string to interpret coordinates in dp instead of px units. + Note that a physical cutout should be configured in pixels for the best results. + --> + <string translatable="false" name="config_mainBuiltInDisplayCutoutRectApproximation"> + M -258,0 + v 171 + h 516 + v -171 + q + </string> + + <string translatable="false" name="config_mainBuiltInDisplayCutout"> + M -338,0 + q 86,-4 80,71.5 v 8 q 4,90 95,91.5 + h 163 v -171 z + M 338,0 + q -86,-4 -80,71.5 v 8 q -4,90 -95,91.5 + h -163 v -171 z + </string> + + <!-- Whether the display cutout region of the main built-in display should be forced to + black in software (to avoid aliasing or emulate a cutout that is not physically existent). + --> + <bool name="config_fillMainBuiltInDisplayCutout">false</bool> + + <!-- Height of the status bar --> + <dimen name="status_bar_height_portrait">171px</dimen> + <dimen name="status_bar_height_landscape">28dp</dimen> + <!-- Height of area above QQS where battery/time go (equal to status bar height if > 48dp) --> + <dimen name="quick_qs_offset_height">171px</dimen> + <!-- Total height of QQS (quick_qs_offset_height + 128dp) --> + <dimen name="quick_qs_total_height">177dp</dimen> + + <!-- How much we expand the touchable region of the status bar below the notch to catch touches + that just start below the notch. --> + <dimen name="display_cutout_touchable_region_size">60px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..e20aaedc --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/Android.mk @@ -0,0 +1,31 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel3XL + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel3XLOverlay +LOCAL_SDK_VERSION := current + +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..3ca25c58 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_3_xl" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..2dc4813b --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3_xl/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,38 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2021, 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. +*/ +--> +<resources> + <dimen name="rounded_corner_content_padding">28px</dimen> + + <dimen name="display_cutout_margin_consumption">0px</dimen> + + <!-- Height of the status bar header bar when on Keyguard (match status_bar_portrait) --> + <dimen name="status_bar_header_height_keyguard">49dp</dimen> + + <!-- Margin end of the system icons super container when the avatar is missing. --> + <dimen name="system_icons_super_container_avatarless_margin_end">10dp</dimen> + + <!-- end margin for multi user switch in collapsed quick settings --> + <dimen name="multi_user_switch_keyguard_margin">7dp</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">780px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">1180px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">1380px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..f196ae73 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel3a + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel3aOverlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..a45b3d70 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_3a" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..02f6d69d --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3a/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,29 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2021, 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. +*/ +--> +<resources> + <dimen name="rounded_corner_content_padding">28px</dimen> + <!-- Height of the status bar --> + <dimen name="status_bar_height_portrait">28dp</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">530px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">890px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">1060px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..1cae0e9f --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/Android.mk @@ -0,0 +1,31 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel3aXL + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel3aXLOverlay +LOCAL_SDK_VERSION := current + +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..5cb96159 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_3a_xl" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..cbccc087 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_3a_xl/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,29 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2021, 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. +*/ +--> +<resources> + <dimen name="rounded_corner_content_padding">28px</dimen> + <!-- Height of the status bar --> + <dimen name="status_bar_height_portrait">28dp</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">500px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">800px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">1000px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/Android.mk new file mode 100644 index 00000000..30697b3b --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := EmulationPixel4 + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := EmulationPixel4Overlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/AndroidManifest.xml new file mode 100644 index 00000000..89f85801 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.internal.emulation.pixel_4" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="android" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/radio/ril/at_tok.h b/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/res/values/config.xml index a85ea636..cfd537e5 100644 --- a/radio/ril/at_tok.h +++ b/overlay/frameworks/base/packages/overlays/pixel_4/AndroidOverlay/res/values/config.xml @@ -1,6 +1,7 @@ -/* //device/system/reference-ril/at_tok.h -** -** Copyright 2006, The Android Open Source Project +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2021, 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. @@ -14,17 +15,9 @@ ** See the License for the specific language governing permissions and ** limitations under the License. */ +--> -#ifndef AT_TOK_H -#define AT_TOK_H 1 - -int at_tok_start(char **p_cur); -int at_tok_nextint(char **p_cur, int *p_out); -int at_tok_nexthexint(char **p_cur, int *p_out); - -int at_tok_nextbool(char **p_cur, char *p_out); -int at_tok_nextstr(char **p_cur, char **out); - -int at_tok_hasmore(char **p_cur); - -#endif /*AT_TOK_H */ +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- Height of the status bar --> + <dimen name="status_bar_height_portrait">30dp</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..17948e67 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel4 + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel4Overlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..ee649ebd --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_4" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/res/values/config.xml new file mode 100644 index 00000000..8970cd22 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/res/values/config.xml @@ -0,0 +1,24 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2018, 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. +*/ +--> + +<!-- These resources are around just to allow their values to be customized + for different hardware and product builds. --> +<resources> + <string name="config_rounded_mask" translatable="false">M22,0C19.94,0.01 18.83,0.04 17.73,0.11C16.91,0.17 16.09,0.25 15.3,0.36C14.5,0.48 13.72,0.62 12.95,0.81C11.42,1.19 9.97,1.72 8.65,2.43C7.32,3.14 6.12,4.02 5.08,5.07C4.04,6.11 3.15,7.31 2.44,8.64C1.73,9.97 1.19,11.42 0.82,12.94C0.63,13.7 0.48,14.49 0.37,15.29C0.25,16.09 0.17,16.9 0.12,17.72C0.05,18.82 0.02,19.93 0.01,21.55</string> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..196e4a68 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,31 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2019, 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. +*/ +--> +<resources> + <!-- for 20dp of padding at 2.75px/dp at default density --> + <dimen name="rounded_corner_content_padding">55px</dimen> + + <!-- the padding on the top of the statusbar (usually 0) --> + <dimen name="status_bar_padding_top">1dp</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">480px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">805px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">1005px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/Android.mk new file mode 100644 index 00000000..128e5557 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := EmulationPixel4XL + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := EmulationPixel4XLOverlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/AndroidManifest.xml new file mode 100644 index 00000000..a215b59d --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.internal.emulation.pixel_4_xl" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="android" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/res/values/config.xml new file mode 100644 index 00000000..8cf674f7 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4_xl/AndroidOverlay/res/values/config.xml @@ -0,0 +1,23 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2021, 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. +*/ +--> + +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- Height of the status bar --> + <dimen name="status_bar_height_portrait">28dp</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..358d418d --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel4XL + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel4XLOverlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..5eb23b0b --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_4_xl" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/res/values/config.xml new file mode 100644 index 00000000..fb7ad12c --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/res/values/config.xml @@ -0,0 +1,24 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2018, 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. +*/ +--> + +<!-- These resources are around just to allow their values to be customized + for different hardware and product builds. --> +<resources> + <string name="config_rounded_mask" translatable="false">M21,0C19.94,0.01 18.83,0.04 17.73,0.11C16.91,0.17 16.09,0.25 15.3,0.36C14.5,0.48 13.72,0.62 12.95,0.81C11.42,1.19 9.97,1.72 8.65,2.43C7.32,3.14 6.12,4.02 5.08,5.07C4.04,6.11 3.15,7.31 2.44,8.64C1.73,9.97 1.19,11.42 0.82,12.94C0.63,13.7 0.48,14.49 0.37,15.29C0.25,16.09 0.17,16.9 0.12,17.72C0.05,18.82 0.02,19.93 0.01,21.55</string> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..cb819ec8 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4_xl/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,31 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2019, 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. +*/ +--> +<resources> + <!-- for 20dp of padding at 3.5px/dp at default density --> + <dimen name="rounded_corner_content_padding">70px</dimen> + + <!-- the padding on the top of the statusbar (usually 0) --> + <dimen name="status_bar_padding_top">1dp</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">705px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">1115px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">1345px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/Android.mk new file mode 100644 index 00000000..0fa319e8 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/Android.mk @@ -0,0 +1,31 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := EmulationPixel4a + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := EmulationPixel4aOverlay +LOCAL_SDK_VERSION := current + +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/AndroidManifest.xml new file mode 100644 index 00000000..c4b68921 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.internal.emulation.pixel_4a" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="android" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/res/values/config.xml new file mode 100644 index 00000000..08869a08 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4a/AndroidOverlay/res/values/config.xml @@ -0,0 +1,53 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2021, 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. +*/ +--> + +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- Whether the display cutout region of the main built-in display should be forced to + black in software (to avoid aliasing or emulate a cutout that is not physically existent). + --> + <bool name="config_fillMainBuiltInDisplayCutout">false</bool> + + <!-- Display cutout configuration --> + <string translatable="false" name="config_mainBuiltInDisplayCutout"> + <!-- The hole punch dimensions are this: + M 41,83 a 42,42 0 1,0 84,0 a 42,42 0 1,0 -84,0 + but using a radius 43 circle for now to see the antialiasing. + --> + M 40,83 a 42.75,42.75 0 1 0 85.5,0 42.75,42.75 0 1 0 -85.5,0 Z + @left + </string> + + <string translatable="false" name="config_mainBuiltInDisplayCutoutRectApproximation"> + M 0.0,0.0 + h 136 + v 136 + h -136 + Z + @left + </string> + + <!-- Height of the status bar in portrait. The height should be + Max((status bar content height + waterfall top size), top cutout size) --> + <dimen name="status_bar_height_portrait">136px</dimen> + <dimen name="status_bar_height_landscape">28dp</dimen> + <!-- Height of area above QQS where battery/time go (equal to status bar) --> + <dimen name="quick_qs_offset_height">136px</dimen> + <!-- Total height of QQS (quick_qs_offset_height + 128) --> + <dimen name="quick_qs_total_height">488px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..cb9b062c --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/Android.mk @@ -0,0 +1,31 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel4a + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel4aOverlay +LOCAL_SDK_VERSION := current + +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..6e11b3bb --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_4a" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/res/values/config.xml new file mode 100644 index 00000000..9238f8f6 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/res/values/config.xml @@ -0,0 +1,39 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2018, 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. +*/ +--> + +<!-- These resources are around just to allow their values to be customized + for different hardware and product builds. --> +<resources> + <!-- Default rounded corner curve (a Bezier). Must match (the curved path in) rounded.xml. + Note that while rounded.xml includes the entire path (including the horizontal and vertical + corner edges), this pulls out just the curve. + --> + <string name="config_rounded_mask" translatable="false">M146,0 C100,2 60,0 30,30 C0,60 2,100 0,146</string> + + <bool name="config_roundedCornerMultipleRadius">true</bool> + + <!-- Configure 11px of extra protection around the front-facing camera --> + <string translatable="false" name="config_frontBuiltInDisplayCutoutProtection"> + M 30,83 + a 53,53 0 1 0 106,0 + a 53,53 0 1 0 -106,0 + Z + </string> + <bool name="config_enableDisplayCutoutProtection">true</bool> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..7e32ad21 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_4a/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,34 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2019, 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. +*/ +--> +<resources> + <!-- Padding around the status bar --> + <dimen name="rounded_corner_content_padding">30px</dimen> + + <!-- Height of the status bar header bar when on Keyguard (match status_bar_portrait) --> + <dimen name="status_bar_header_height_keyguard">@*android:dimen/status_bar_height_portrait</dimen> + + <!-- the padding on the top of the statusbar (usually 0) --> + <dimen name="status_bar_padding_top">11dp</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">640px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">970px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">1170px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/Android.mk new file mode 100644 index 00000000..b410659e --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := EmulationPixel5 + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := EmulationPixel5Overlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/AndroidManifest.xml new file mode 100644 index 00000000..f73cea9a --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.internal.emulation.pixel_5" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="android" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/res/values/config.xml new file mode 100644 index 00000000..85ef0f4d --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_5/AndroidOverlay/res/values/config.xml @@ -0,0 +1,51 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2021, 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. +*/ +--> + +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- Whether the display cutout region of the main built-in display should be forced to + black in software (to avoid aliasing or emulate a cutout that is not physically existent). + --> + <bool name="config_fillMainBuiltInDisplayCutout">false</bool> + <!-- Display cutout configuration --> + <string translatable="false" name="config_mainBuiltInDisplayCutout"> + <!-- The hole punch dimensions are this: + M 42,77 a 39,39 0 1,0 78,0 a 39,39 0 1,0 -78,0 + but using a radius 40 circle for now to see the antialiasing. + --> + M 41,77 a 40,40 0 1 0 80,0 40,40 0 1 0 -80,0 Z + + @left + </string> + + <string translatable="false" name="config_mainBuiltInDisplayCutoutRectApproximation"> + M 0.0,0.0 + h 136 + v 136 + h -136 + Z + @left + </string> + + <!-- Height of the status bar in portrait. The height should be + Max((status bar content height + waterfall top size), top cutout size) --> + <dimen name="status_bar_height_portrait">145px</dimen> + <dimen name="status_bar_height_landscape">28dp</dimen> + <!-- Height of area above QQS where battery/time go (equal to status bar) --> + <dimen name="quick_qs_offset_height">145px</dimen> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/Android.mk b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/Android.mk new file mode 100644 index 00000000..cf4d5f5b --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/Android.mk @@ -0,0 +1,29 @@ +# +# Copyright 2019, 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. +# + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_RRO_THEME := SystemUIEmulationPixel5 + +LOCAL_PRODUCT_MODULE := true + +LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/res + +LOCAL_PACKAGE_NAME := SystemUIEmulationPixel5Overlay +LOCAL_SDK_VERSION := current + +include $(BUILD_RRO_PACKAGE) diff --git a/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/AndroidManifest.xml b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/AndroidManifest.xml new file mode 100644 index 00000000..470dd502 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/AndroidManifest.xml @@ -0,0 +1,24 @@ +<!-- +/** + * Copyright (c) 2019, 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.systemui.emulation.pixel_5" + android:versionCode="1" + android:versionName="1.0"> + <overlay android:targetPackage="com.android.systemui" android:priority="1"/> + <application android:label="Filled" android:hasCode="false"/> +</manifest> diff --git a/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/res/values/config.xml b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/res/values/config.xml new file mode 100644 index 00000000..bfb55d8f --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/res/values/config.xml @@ -0,0 +1,46 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2021, 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. +*/ +--> + +<!-- These resources are around just to allow their values to be customized + for different hardware and product builds. --> +<resources> + <!-- Height of the status bar header bar when on Keyguard (match status_bar_portrait) --> + <dimen name="status_bar_header_height_keyguard">@*android:dimen/status_bar_height_portrait</dimen> + <!-- Default rounded corner curve (a Bezier). Must match (the curved path in) rounded.xml. + Note that while rounded.xml includes the entire path (including the horizontal and vertical + corner edges), this pulls out just the curve. + --> + <string name="config_rounded_mask" translatable="false">M156,0 C76,4 58,5 31,31 5,58 4,76 0,156</string> + <bool name="config_roundedCornerMultipleRadius">true</bool> + <!-- Configure 13px of extra protection around the front-facing camera --> + <string translatable="false" name="config_frontBuiltInDisplayCutoutProtection"> + M 29,77 + a 52,52 0 1 0 104,0 + a 52,52 0 1 0 -104,0 + Z + </string> + <!-- Camera 1 is the front camera on bramble --> + <string translatable="false" name="config_protectedCameraId">1</string> + + <!-- Comma-separated list of packages to exclude from camera protection. In our case, + ignore the gaze detection package --> + <string translatable="false" name="config_cameraProtectionExcludedPackages">com.google.android.as</string> + + <bool name="config_enableDisplayCutoutProtection">true</bool> +</resources> diff --git a/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/res/values/dimens.xml b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/res/values/dimens.xml new file mode 100644 index 00000000..d4480e76 --- /dev/null +++ b/overlay/frameworks/base/packages/overlays/pixel_5/SystemUIOverlay/res/values/dimens.xml @@ -0,0 +1,41 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- + * Copyright (c) 2021, 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. +*/ +--> +<resources> + <!-- for 20dp of padding at 3.5px/dp at default density --> + <dimen name="rounded_corner_content_padding">50px</dimen> + <!-- the padding on the top of the statusbar (usually 0) --> + <dimen name="status_bar_padding_top">2dp</dimen> + <!-- Padding for the system icons on the keyguard (when no multi user switch is showing). + The icons always have a 4dp padding in the container so we only need 56 extra px of padding + for the corners --> + <dimen name="system_icons_super_container_avatarless_margin_end">56px</dimen> + <!-- Multi user switch has some intrinsic padding to it --> + <dimen name="multi_user_switch_keyguard_margin">40px</dimen> + <dimen name="keyguard_carrier_text_margin">0px</dimen> + + <dimen name="config_rounded_mask_size">156px</dimen> + <dimen name="config_rounded_mask_size_top">156px</dimen> + <dimen name="config_rounded_mask_size_bottom">156px</dimen> + + <!-- Location on the screen of the center of the physical power button. --> + <dimen name="physical_power_button_center_screen_location_y">620px</dimen> + + <!-- Location on the screen of the center of the physical volume up/down buttons. --> + <dimen name="physical_volume_up_button_center_screen_location_y">950px</dimen> + <dimen name="physical_volume_down_button_center_screen_location_y">1150px</dimen> +</resources> diff --git a/overlay/packages/services/Telephony/res/values/config.xml b/overlay/packages/services/Telephony/res/values/config.xml new file mode 100644 index 00000000..38944e74 --- /dev/null +++ b/overlay/packages/services/Telephony/res/values/config.xml @@ -0,0 +1,25 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- Copyright (C) 2021 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. +--> + +<!-- Phone app resources that may need to be customized + for different hardware or product builds. --> +<resources> + <!-- String indicating the package name of the device ImsService implementation for MMTEL. --> + <string name="config_ims_mmtel_package" translatable="false">org.codeaurora.ims</string> + + <!-- String indicating the package name of the device ImsService implementation for RCS. --> + <string name="config_ims_rcs_package" translatable="false">com.android.service.ims</string> +</resources> diff --git a/qemu-adb-keys/Android.bp b/qemu-adb-keys/Android.bp new file mode 100644 index 00000000..e9e316ab --- /dev/null +++ b/qemu-adb-keys/Android.bp @@ -0,0 +1,45 @@ +// Copyright (C) 2021 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. + +// this file is used to build emulator-specific program tools +// that should only run in the emulator. +// + +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + +cc_binary { + name: "qemu-adb-keys", + vendor: true, + srcs: [ + "qemu-adb-keys.cpp", + ], + shared_libs: [ + "libbase", + "liblog", + ], + static_libs: [ + "libfstab", + ], + cflags: [ + "-DLOG_TAG=\"qemu-adb-keys\"", + ], + +} diff --git a/qemu-adb-keys/qemu-adb-keys.cpp b/qemu-adb-keys/qemu-adb-keys.cpp new file mode 100644 index 00000000..3eaafcdd --- /dev/null +++ b/qemu-adb-keys/qemu-adb-keys.cpp @@ -0,0 +1,74 @@ +/* + * Copyright (C) 2021 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. + */ + +/* this program is used to read a set of system properties and their values + * from the emulator program and set them in the currently-running emulated + * system. It does so by connecting to the 'boot-properties' qemud service. + * + * This program should be run as root and called from + * /system/etc/init.ranchu.rc exclusively. + */ + +#define LOG_TAG "qemu-adb-keys" + +#define DEBUG 0 +//#define LOG_NDEBUG 0 + +#include <sys/stat.h> + +#include <fstream> +#include <iostream> +#include <string.h> + +#include <log/log.h> + +#if DEBUG +# define DD(...) ALOGD(__VA_ARGS__) +#else +# define DD(...) ((void)0) +#endif + +#define ADB_PUBKEY_PROP "qemu.adb.pubkey" +// init will copy over this file to /data/misc/adb/adb_keys +#define ADB_KEYS_FILE "/data/vendor/adb/adb_keys" + +extern bool fs_mgr_get_boot_config(const std::string& key, std::string* out_val); + +int main(void) { + struct stat st; + if (stat(ADB_KEYS_FILE, &st) == 0) { + ALOGV("%s already exists", ADB_KEYS_FILE); + return 0; + } + + std::string adbkey_pub; + if (!fs_mgr_get_boot_config(ADB_PUBKEY_PROP, &adbkey_pub)) { + ALOGE("Failed to read %s bootconfig prop", ADB_PUBKEY_PROP); + exit(1); + } + + std::ofstream f; + f.open(ADB_KEYS_FILE); + if (!f.is_open()) { + ALOGE("Failed to open %s\n", ADB_KEYS_FILE); + exit(1); + } + + ALOGV("Got %s=[%s]", ADB_PUBKEY_PROP, adbkey_pub.c_str()); + f << adbkey_pub; + f.close(); + return 0; +} diff --git a/qemu-props/Android.bp b/qemu-props/Android.bp index 30833f13..7bd74ffa 100644 --- a/qemu-props/Android.bp +++ b/qemu-props/Android.bp @@ -16,11 +16,24 @@ // that should only run in the emulator. // +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "qemu-props", vendor: true, - srcs: ["qemu-props.c"], + srcs: [ + "qemu-props.cpp", + "vport_parser.cpp", + ], shared_libs: [ + "libbase", "libcutils", "liblog", ], @@ -28,4 +41,8 @@ cc_binary { "libqemud.ranchu", "libqemupipe.ranchu", ], + cflags: [ + "-DLOG_TAG=\"qemu-props\"", + ], + } diff --git a/qemu-props/qemu-props.c b/qemu-props/qemu-props.cpp index b5216b9a..3bddbd5b 100644 --- a/qemu-props/qemu-props.c +++ b/qemu-props/qemu-props.cpp @@ -19,7 +19,7 @@ * system. It does so by connecting to the 'boot-properties' qemud service. * * This program should be run as root and called from - * /system/etc/init.goldfish.rc exclusively. + * /system/etc/init.ranchu.rc exclusively. */ #define LOG_TAG "qemu-props" @@ -33,6 +33,7 @@ # define DD(...) ((void)0) #endif +#include <string_view> #include <cutils/properties.h> #include <unistd.h> #include <qemu_pipe_bp.h> @@ -48,12 +49,47 @@ #define QEMU_MISC_PIPE "QemuMiscPipe" +namespace { +// qemu-props will not set these properties. +const char* const k_properties_to_ignore[] = { + "dalvik.vm.heapsize", + "ro.opengles.version", + "qemu.adb.secure", + nullptr, +}; + +// These properties will not be prefixed with "vendor.". +const char* const k_system_properties[] = { + "qemu.sf.lcd_density", + "qemu.hw.mainkeys", + nullptr, +}; + +bool check_if_property_in_list(const char* prop_name, const char* const* prop_list) { + for (; *prop_list; ++prop_list) { + if (!strcmp(prop_name, *prop_list)) { + return true; + } + } + return false; +} + +// We don't want to rename properties which already have the prefix +// or the system properties. +bool need_prepend_prefix(const char* prop, const std::string_view prefix) { + return strncmp(prefix.data(), prop, prefix.size()) && + !check_if_property_in_list(prop, k_system_properties); +} +} // namespace + int s_QemuMiscPipe = -1; void static notifyHostBootComplete(); void static sendHeartBeat(); void static sendMessage(const char* mesg); +void static closeMiscPipe(); +extern void parse_virtio_serial(); -int main(void) +int main(void) { int qemud_fd, count = 0; @@ -61,7 +97,7 @@ int main(void) { int tries = MAX_TRIES; - while (1) { + while (true) { qemud_fd = qemud_channel_open( "boot-properties" ); if (qemud_fd >= 0) break; @@ -87,56 +123,63 @@ int main(void) /* read each system property as a single line from the service, * until exhaustion. */ - for (;;) - { + while (true) { #define BUFF_SIZE (PROPERTY_KEY_MAX + PROPERTY_VALUE_MAX + 2) DD("receiving.."); - char* q; + char* prop_value; char temp[BUFF_SIZE]; - char vendortemp[BUFF_SIZE]; int len = qemud_channel_recv(qemud_fd, temp, sizeof(temp) - 1); /* lone NUL-byte signals end of properties */ - if (len < 0 || len > BUFF_SIZE-1 || temp[0] == '\0') + if (len < 0 || len > (BUFF_SIZE - 1) || !temp[0]) { break; + } temp[len] = '\0'; /* zero-terminate string */ DD("received: %.*s", len, temp); /* separate propery name from value */ - q = strchr(temp, '='); - if (q == NULL) { + prop_value = strchr(temp, '='); + if (!prop_value) { DD("invalid format, ignored."); continue; } - *q++ = '\0'; - char* final_prop_name = NULL; - if (strcmp(temp, "qemu.sf.lcd.density") == 0 ) { - final_prop_name = temp; - } else if (strcmp(temp, "qemu.hw.mainkeys") == 0 ) { - final_prop_name = temp; - } else if (strcmp(temp, "qemu.cmdline") == 0 ) { - final_prop_name = temp; - } else if (strcmp(temp, "dalvik.vm.heapsize") == 0 ) { - continue; /* cannot set it here */ - } else if (strcmp(temp, "ro.opengles.version") == 0 ) { - continue; /* cannot set it here */ + *prop_value = 0; + ++prop_value; + + if (check_if_property_in_list(temp, k_properties_to_ignore)) { + ALOGI("ignoring '%s' property", temp); + continue; // do not set these + } + + char renamed_property[BUFF_SIZE]; + const char* final_prop_name = nullptr; + + using namespace std::literals; + static constexpr std::string_view k_vendor_prefix = "vendor."sv; + if (need_prepend_prefix(temp, k_vendor_prefix)) { + snprintf(renamed_property, sizeof(renamed_property), "%.*s%s", + int(k_vendor_prefix.size()), k_vendor_prefix.data(), temp); + + final_prop_name = renamed_property; } else { - snprintf(vendortemp, sizeof(vendortemp), "vendor.%s", temp); - final_prop_name = vendortemp; + final_prop_name = temp; } - if (property_set(temp, q) < 0) { - ALOGW("could not set property '%s' to '%s'", final_prop_name, q); + + if (property_set(final_prop_name, prop_value) < 0) { + ALOGW("could not set property '%s' to '%s'", final_prop_name, prop_value); } else { - ALOGI("successfully set property '%s' to '%s'", final_prop_name, q); + ALOGI("successfully set property '%s' to '%s'", final_prop_name, prop_value); count += 1; } } close(qemud_fd); + parse_virtio_serial(); + char temp[BUFF_SIZE]; sendHeartBeat(); while (s_QemuMiscPipe >= 0) { @@ -157,10 +200,7 @@ int main(void) } /* finally, close the channel and exit */ - if (s_QemuMiscPipe >= 0) { - close(s_QemuMiscPipe); - s_QemuMiscPipe = -1; - } + closeMiscPipe(); DD("exiting (%d properties set).", count); return 0; } @@ -181,13 +221,33 @@ void sendMessage(const char* mesg) { return; } } - char set[64]; - snprintf(set, sizeof(set), "%s", mesg); - int pipe_command_length = strlen(set)+1; //including trailing '\0' - qemu_pipe_write_fully(s_QemuMiscPipe, &pipe_command_length, sizeof(pipe_command_length)); - qemu_pipe_write_fully(s_QemuMiscPipe, set, pipe_command_length); - qemu_pipe_read_fully(s_QemuMiscPipe, &pipe_command_length, sizeof(pipe_command_length)); - if (pipe_command_length > (int)(sizeof(set)) || pipe_command_length <= 0) + + int32_t cmd_len = strlen(mesg) + 1; //including trailing '\0' + qemu_pipe_write_fully(s_QemuMiscPipe, &cmd_len, sizeof(cmd_len)); + qemu_pipe_write_fully(s_QemuMiscPipe, mesg, cmd_len); + + int r = qemu_pipe_read_fully(s_QemuMiscPipe, &cmd_len, sizeof(cmd_len)); + if (r || (cmd_len < 0)) { + closeMiscPipe(); return; - qemu_pipe_read_fully(s_QemuMiscPipe, set, pipe_command_length); + } + + while (cmd_len > 0) { + char buf[64]; + const size_t chunk = std::min<size_t>(cmd_len, sizeof(buf)); + r = qemu_pipe_read_fully(s_QemuMiscPipe, buf, chunk); + if (r) { + closeMiscPipe(); + return; + } else { + cmd_len -= chunk; + } + } +} + +void closeMiscPipe() { + if (s_QemuMiscPipe >= 0) { + close(s_QemuMiscPipe); + s_QemuMiscPipe = -1; + } } diff --git a/qemu-props/vport_parser.cpp b/qemu-props/vport_parser.cpp new file mode 100644 index 00000000..7de9cd02 --- /dev/null +++ b/qemu-props/vport_parser.cpp @@ -0,0 +1,92 @@ +/* + * Copyright (C) 2020 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. + */ + +/* this program is used to read a set of system properties and their values + * from the emulator program and set them in the currently-running emulated + * system. It does so by connecting to the 'boot-properties' qemud service. + * + * This file parses the sys/class/virtio-ports/<id>/name + * and set up vendor.qemu.vport.modem=/dev/<id> so that reference-ril + * can open it later + */ + +#include <fstream> +#include <string> +#include <android-base/strings.h> +#include <log/log.h> +#include <cutils/properties.h> + +#include <dirent.h> +#include <error.h> +#include <string.h> +#include <unistd.h> + +static void set_port_prop(const char* filename, const char* portname) { + std::ifstream myfile(filename); + if (myfile.is_open()) { + const std::string portdev = std::string{"/dev/"} + portname; + + for (std::string line; std::getline(myfile, line); ) { + std::string serialname = android::base::Trim(line); + if (serialname.empty()) { + continue; + } + serialname = std::string("vendor.qemu.vport.") + serialname; + if(property_set(serialname.c_str(), portdev.c_str()) < 0) { + ALOGW("could not set property '%s' to '%s'", serialname.c_str(), + portdev.c_str()); + } else { + ALOGI("successfully set property '%s' to '%s'", serialname.c_str(), portdev.c_str()); + } + } + myfile.close(); + } else { + ALOGW("could not open '%s'", filename); + } +} + +static void close_dir(DIR *dp) { closedir(dp); } + +static void read_virio_ports_dir(const char *cpath) +{ + std::unique_ptr<DIR, decltype(&close_dir)> mydp(opendir(cpath), + &close_dir); + + if (!mydp) { + ALOGW("cannot open dir %s; %s\n", cpath, strerror(errno)); + return; + } + + const std::string path(cpath); + + struct dirent *files; + while ((files = readdir(mydp.get())) != NULL) { + if (strcmp(files->d_name, ".") == 0 || + strcmp(files->d_name, "..") == 0) { + continue; + } + + std::string filename = path + std::string("/") + std::string(files->d_name) + "/name"; + set_port_prop(filename.c_str(), files->d_name); + } +} + +void parse_virtio_serial() { + read_virio_ports_dir("/sys/class/virtio-ports"); +} + + + diff --git a/qemud/Android.bp b/qemud/Android.bp index 05e61c7d..2018882f 100644 --- a/qemud/Android.bp +++ b/qemud/Android.bp @@ -14,6 +14,15 @@ * limitations under the License. */ +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library { name: "libqemud.ranchu", vendor_available: true, diff --git a/radio/Android.bp b/radio/Android.bp new file mode 100644 index 00000000..d1cc13be --- /dev/null +++ b/radio/Android.bp @@ -0,0 +1,14 @@ +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + +cc_library_headers { + name: "goldfish_ril_headers", + vendor: true, + export_include_dirs: ["include"], +} diff --git a/radio/RadioConfig/Android.bp b/radio/RadioConfig/Android.bp index 47857ae5..6d84f250 100644 --- a/radio/RadioConfig/Android.bp +++ b/radio/RadioConfig/Android.bp @@ -1,3 +1,22 @@ +package { + default_applicable_licenses: [ + "device_generic_goldfish_radio_RadioConfig_license", + ], +} + +// Added automatically by a large-scale-change +// See: http://go/android-license-faq +license { + name: "device_generic_goldfish_radio_RadioConfig_license", + visibility: [":__subpackages__"], + license_kinds: [ + "SPDX-license-identifier-Apache-2.0", + ], + license_text: [ + "NOTICE", + ], +} + prebuilt_etc { name: "privapp_whitelist_com.android.emulator.radio.config", system_ext_specific: true, diff --git a/radio/RadioConfig/Android.mk b/radio/RadioConfig/Android.mk index 393b4017..a044870d 100644 --- a/radio/RadioConfig/Android.mk +++ b/radio/RadioConfig/Android.mk @@ -5,6 +5,9 @@ LOCAL_MODULE_TAGS := optional LOCAL_PRIVILEGED_MODULE := true LOCAL_SRC_FILES := $(call all-subdir-java-files) LOCAL_PACKAGE_NAME := EmulatorRadioConfig +LOCAL_LICENSE_KINDS := SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS := notice +LOCAL_NOTICE_FILE := $(LOCAL_PATH)/NOTICE LOCAL_PRIVATE_PLATFORM_APIS := true LOCAL_CERTIFICATE := platform LOCAL_SYSTEM_EXT_MODULE := true diff --git a/radio/include/libril/ril_ex.h b/radio/include/libril/ril_ex.h new file mode 100644 index 00000000..757bcf9d --- /dev/null +++ b/radio/include/libril/ril_ex.h @@ -0,0 +1,49 @@ +/* +* Copyright (C) 2014 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. +*/ + +#ifndef RIL_EX_H_INCLUDED +#define RIL_EX_H_INCLUDED + +#include <telephony/ril.h> +#include <telephony/record_stream.h> + +#define NUM_ELEMS_SOCKET(a) (sizeof (a) / sizeof (a)[0]) + +struct ril_event; + +void rilEventAddWakeup_helper(struct ril_event *ev); +int blockingWrite_helper(int fd, void* data, size_t len); + +enum SocketWakeType {DONT_WAKE, WAKE_PARTIAL}; + +typedef enum { + RIL_TELEPHONY_SOCKET, + RIL_SAP_SOCKET +} RIL_SOCKET_TYPE; + +typedef struct SocketListenParam { + RIL_SOCKET_ID socket_id; + int fdListen; + int fdCommand; + const char* processName; + struct ril_event* commands_event; + struct ril_event* listen_event; + void (*processCommandsCallback)(int fd, short flags, void *param); + RecordStream *p_rs; + RIL_SOCKET_TYPE type; +} SocketListenParam; + +#endif diff --git a/radio/libril/sap_service.h b/radio/include/telephony/librilutils.h index cb5ae104..d06b3e9b 100644 --- a/radio/libril/sap_service.h +++ b/radio/include/telephony/librilutils.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016 The Android Open Source Project + * Copyright (C) 2013 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. @@ -14,20 +14,25 @@ * limitations under the License. */ -#ifndef SAP_SERVICE_H -#define SAP_SERVICE_H +#ifndef LIBRILUTILS_H +#define LIBRILUTILS_H -#include <telephony/ril.h> -#include <ril_internal.h> -#include <RilSapSocket.h> -#include <hardware/ril/librilutils/proto/sap-api.pb.h> +#include <stdint.h> -namespace sap { +#ifdef __cplusplus +extern "C" { +#endif -void registerService(const RIL_RadioFunctions *callbacks); -void processResponse(MsgHeader *rsp, RilSapSocket *sapSocket); -void processUnsolResponse(MsgHeader *rsp, RilSapSocket *sapSocket); +/** + * Return system time in nanos. + * + * This is a monotonicly increasing clock and + * return the same value as System.nanoTime in java. + */ +uint64_t ril_nano_time(); -} // namespace android +#ifdef __cplusplus +} +#endif -#endif // RIL_SERVICE_H +#endif // LIBRILUTILS_H diff --git a/radio/include/telephony/record_stream.h b/radio/include/telephony/record_stream.h new file mode 100644 index 00000000..7a89ae4f --- /dev/null +++ b/radio/include/telephony/record_stream.h @@ -0,0 +1,43 @@ +/* + * Copyright (C) 2006 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. + */ + +/* + * A simple utility for reading fixed records out of a stream fd + */ + +#ifndef _LIBRIL_RECORD_STREAM_H +#define _LIBRIL_RECORD_STREAM_H + +#ifdef __cplusplus +extern "C" { +#endif + + +typedef struct RecordStream RecordStream; + +extern RecordStream *record_stream_new(int fd, size_t maxRecordLen); +extern void record_stream_free(RecordStream *p_rs); + +extern int record_stream_get_next (RecordStream *p_rs, void ** p_outRecord, + size_t *p_outRecordLen); + +#ifdef __cplusplus +} +#endif + + +#endif /*_LIBRIL_RECORD_STREAM_H*/ + diff --git a/radio/ril/ril.h b/radio/include/telephony/ril.h index 56bbcfad..c879873d 100644 --- a/radio/ril/ril.h +++ b/radio/include/telephony/ril.h @@ -262,8 +262,7 @@ typedef enum { RADIO_TECH_GSM = 16, // Only supports voice RADIO_TECH_TD_SCDMA = 17, RADIO_TECH_IWLAN = 18, - RADIO_TECH_LTE_CA = 19, - RADIO_TECH_NR = 20 + RADIO_TECH_LTE_CA = 19 } RIL_RadioTechnology; typedef enum { @@ -285,8 +284,7 @@ typedef enum { RAF_HSPAP = (1 << RADIO_TECH_HSPAP), RAF_GSM = (1 << RADIO_TECH_GSM), RAF_TD_SCDMA = (1 << RADIO_TECH_TD_SCDMA), - RAF_LTE_CA = (1 << RADIO_TECH_LTE_CA), - RAF_NR = (1 << RADIO_TECH_NR) + RAF_LTE_CA = (1 << RADIO_TECH_LTE_CA) } RIL_RadioAccessFamily; typedef enum { @@ -745,8 +743,8 @@ typedef struct { typedef struct { int32_t len_allowed_carriers; /* length of array allowed_carriers */ int32_t len_excluded_carriers; /* length of array excluded_carriers */ - RIL_Carrier * allowed_carriers; /* whitelist for allowed carriers */ - RIL_Carrier * excluded_carriers; /* blacklist for explicitly excluded carriers + RIL_Carrier * allowed_carriers; /* list of allowed carriers */ + RIL_Carrier * excluded_carriers; /* list of explicitly excluded carriers * which match allowed_carriers. Eg. allowed_carriers match * mcc/mnc, excluded_carriers has same mcc/mnc and gid1 * is ABCD. It means except the carrier whose gid1 is ABCD, @@ -7025,9 +7023,6 @@ typedef struct { */ #define RIL_UNSOL_KEEPALIVE_STATUS 1050 - -#define RIL_UNSOL_PHYSICAL_CHANNEL_CONFIGS 1051 - /***********************************************************************/ diff --git a/radio/include/telephony/ril_cdma_sms.h b/radio/include/telephony/ril_cdma_sms.h new file mode 100644 index 00000000..835bc92a --- /dev/null +++ b/radio/include/telephony/ril_cdma_sms.h @@ -0,0 +1,806 @@ +/* + * Copyright (C) 2006 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. + */ + +/* + * ISSUES: + * + */ + +/** + * TODO + * + * + */ + + +#ifndef ANDROID_RIL_CDMA_SMS_H +#define ANDROID_RIL_CDMA_SMS_H 1 + +#include <stdlib.h> + +#ifdef __cplusplus +extern "C" { +#endif + +/* Used by RIL_REQUEST_CDMA_SEND_SMS and RIL_UNSOL_RESPONSE_CDMA_NEW_SMS */ + +#define RIL_CDMA_SMS_ADDRESS_MAX 36 +#define RIL_CDMA_SMS_SUBADDRESS_MAX 36 +#define RIL_CDMA_SMS_BEARER_DATA_MAX 255 + +typedef enum { + RIL_CDMA_SMS_DIGIT_MODE_4_BIT = 0, /* DTMF digits */ + RIL_CDMA_SMS_DIGIT_MODE_8_BIT = 1, + RIL_CDMA_SMS_DIGIT_MODE_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_DigitMode; + +typedef enum { + RIL_CDMA_SMS_NUMBER_MODE_NOT_DATA_NETWORK = 0, + RIL_CDMA_SMS_NUMBER_MODE_DATA_NETWORK = 1, + RIL_CDMA_SMS_NUMBER_MODE_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_NumberMode; + +typedef enum { + RIL_CDMA_SMS_NUMBER_TYPE_UNKNOWN = 0, + RIL_CDMA_SMS_NUMBER_TYPE_INTERNATIONAL_OR_DATA_IP = 1, + /* INTERNATIONAL is used when number mode is not data network address. + * DATA_IP is used when the number mode is data network address + */ + RIL_CDMA_SMS_NUMBER_TYPE_NATIONAL_OR_INTERNET_MAIL = 2, + /* NATIONAL is used when the number mode is not data network address. + * INTERNET_MAIL is used when the number mode is data network address. + * For INTERNET_MAIL, in the address data "digits", each byte contains + * an ASCII character. Examples are "x@y.com,a@b.com - ref TIA/EIA-637A 3.4.3.3 + */ + RIL_CDMA_SMS_NUMBER_TYPE_NETWORK = 3, + RIL_CDMA_SMS_NUMBER_TYPE_SUBSCRIBER = 4, + RIL_CDMA_SMS_NUMBER_TYPE_ALPHANUMERIC = 5, + /* GSM SMS: address value is GSM 7-bit chars */ + RIL_CDMA_SMS_NUMBER_TYPE_ABBREVIATED = 6, + RIL_CDMA_SMS_NUMBER_TYPE_RESERVED_7 = 7, + RIL_CDMA_SMS_NUMBER_TYPE_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_NumberType; + +typedef enum { + RIL_CDMA_SMS_NUMBER_PLAN_UNKNOWN = 0, + RIL_CDMA_SMS_NUMBER_PLAN_TELEPHONY = 1, /* CCITT E.164 and E.163, including ISDN plan */ + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_2 = 2, + RIL_CDMA_SMS_NUMBER_PLAN_DATA = 3, /* CCITT X.121 */ + RIL_CDMA_SMS_NUMBER_PLAN_TELEX = 4, /* CCITT F.69 */ + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_5 = 5, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_6 = 6, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_7 = 7, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_8 = 8, + RIL_CDMA_SMS_NUMBER_PLAN_PRIVATE = 9, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_10 = 10, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_11 = 11, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_12 = 12, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_13 = 13, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_14 = 14, + RIL_CDMA_SMS_NUMBER_PLAN_RESERVED_15 = 15, + RIL_CDMA_SMS_NUMBER_PLAN_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_NumberPlan; + +typedef struct { + RIL_CDMA_SMS_DigitMode digit_mode; + /* Indicates 4-bit or 8-bit */ + RIL_CDMA_SMS_NumberMode number_mode; + /* Used only when digitMode is 8-bit */ + RIL_CDMA_SMS_NumberType number_type; + /* Used only when digitMode is 8-bit. + * To specify an international address, use the following: + * digitMode = RIL_CDMA_SMS_DIGIT_MODE_8_BIT + * numberMode = RIL_CDMA_SMS_NOT_DATA_NETWORK + * numberType = RIL_CDMA_SMS_NUMBER_TYPE_INTERNATIONAL_OR_DATA_IP + * numberPlan = RIL_CDMA_SMS_NUMBER_PLAN_TELEPHONY + * numberOfDigits = number of digits + * digits = ASCII digits, e.g. '1', '2', '3'3, '4', and '5' + */ + RIL_CDMA_SMS_NumberPlan number_plan; + /* Used only when digitMode is 8-bit */ + unsigned char number_of_digits; + unsigned char digits[ RIL_CDMA_SMS_ADDRESS_MAX ]; + /* Each byte in this array represnts a 4-bit or 8-bit digit of address data */ +} RIL_CDMA_SMS_Address; + +typedef enum { + RIL_CDMA_SMS_SUBADDRESS_TYPE_NSAP = 0, /* CCITT X.213 or ISO 8348 AD2 */ + RIL_CDMA_SMS_SUBADDRESS_TYPE_USER_SPECIFIED = 1, /* e.g. X.25 */ + RIL_CDMA_SMS_SUBADDRESS_TYPE_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_SubaddressType; + +typedef struct { + RIL_CDMA_SMS_SubaddressType subaddressType; + /* 1 means the last byte's lower 4 bits should be ignored */ + unsigned char odd; + unsigned char number_of_digits; + /* Each byte respresents a 8-bit digit of subaddress data */ + unsigned char digits[ RIL_CDMA_SMS_SUBADDRESS_MAX ]; +} RIL_CDMA_SMS_Subaddress; + +typedef struct { + int uTeleserviceID; + unsigned char bIsServicePresent; + int uServicecategory; + RIL_CDMA_SMS_Address sAddress; + RIL_CDMA_SMS_Subaddress sSubAddress; + int uBearerDataLen; + unsigned char aBearerData[ RIL_CDMA_SMS_BEARER_DATA_MAX ]; +} RIL_CDMA_SMS_Message; + +/* Used by RIL_REQUEST_CDMA_SMS_ACKNOWLEDGE */ + +typedef enum { + RIL_CDMA_SMS_NO_ERROR = 0, + RIL_CDMA_SMS_ERROR = 1, + RIL_CDMA_SMS_ERROR_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_ErrorClass; + +typedef struct { + RIL_CDMA_SMS_ErrorClass uErrorClass; + int uSMSCauseCode; /* As defined in N.S00005, 6.5.2.125. + Currently, only 35 (resource shortage) and + 39 (other terminal problem) are reported. */ +} RIL_CDMA_SMS_Ack; + +/* Used by RIL_REQUEST_CDMA_SMS_GET_BROADCAST_CONFIG and + RIL_REQUEST_CDMA_SMS_SET_BROADCAST_CONFIG */ + +typedef struct { + int service_category; + int language; + unsigned char selected; +} RIL_CDMA_BroadcastSmsConfigInfo; + +/* Used by RIL_REQUEST_CDMA_WRITE_SMS_TO_RUIM */ + +typedef struct { + int status; /* Status of message. See TS 27.005 3.1, "<stat>": */ + /* 0 = "REC UNREAD" */ + /* 1 = "REC READ" */ + /* 2 = "STO UNSENT" */ + /* 3 = "STO SENT" */ + + RIL_CDMA_SMS_Message message; +} RIL_CDMA_SMS_WriteArgs; + + +/* Used by RIL_REQUEST_ENCODE_CDMA_SMS and RIL_REQUEST_DECODE_CDMA_SMS*/ + +#define RIL_CDMA_SMS_UDH_MAX_SND_SIZE 128 +#define RIL_CDMA_SMS_UDH_EO_DATA_SEGMENT_MAX 131 /* 140 - 3 - 6 */ +#define RIL_CDMA_SMS_MAX_UD_HEADERS 7 +#define RIL_CDMA_SMS_USER_DATA_MAX 229 +#define RIL_CDMA_SMS_ADDRESS_MAX 36 +#define RIL_CDMA_SMS_UDH_LARGE_PIC_SIZE 128 +#define RIL_CDMA_SMS_UDH_SMALL_PIC_SIZE 32 +#define RIL_CDMA_SMS_UDH_VAR_PIC_SIZE 134 +#define RIL_CDMA_SMS_UDH_ANIM_NUM_BITMAPS 4 +#define RIL_CDMA_SMS_UDH_LARGE_BITMAP_SIZE 32 +#define RIL_CDMA_SMS_UDH_SMALL_BITMAP_SIZE 8 +#define RIL_CDMA_SMS_UDH_OTHER_SIZE 226 +#define RIL_CDMA_SMS_IP_ADDRESS_SIZE 4 + +/* ------------------- */ +/* ---- User Data ---- */ +/* ------------------- */ +typedef enum { + RIL_CDMA_SMS_UDH_CONCAT_8 = 0x00, + RIL_CDMA_SMS_UDH_SPECIAL_SM, + /* 02 - 03 Reserved */ + RIL_CDMA_SMS_UDH_PORT_8 = 0x04, + RIL_CDMA_SMS_UDH_PORT_16, + RIL_CDMA_SMS_UDH_SMSC_CONTROL, + RIL_CDMA_SMS_UDH_SOURCE, + RIL_CDMA_SMS_UDH_CONCAT_16, + RIL_CDMA_SMS_UDH_WCMP, + RIL_CDMA_SMS_UDH_TEXT_FORMATING, + RIL_CDMA_SMS_UDH_PRE_DEF_SOUND, + RIL_CDMA_SMS_UDH_USER_DEF_SOUND, + RIL_CDMA_SMS_UDH_PRE_DEF_ANIM, + RIL_CDMA_SMS_UDH_LARGE_ANIM, + RIL_CDMA_SMS_UDH_SMALL_ANIM, + RIL_CDMA_SMS_UDH_LARGE_PICTURE, + RIL_CDMA_SMS_UDH_SMALL_PICTURE, + RIL_CDMA_SMS_UDH_VAR_PICTURE, + + RIL_CDMA_SMS_UDH_USER_PROMPT = 0x13, + RIL_CDMA_SMS_UDH_EXTENDED_OBJECT = 0x14, + + /* 15 - 1F Reserved for future EMS */ + + RIL_CDMA_SMS_UDH_RFC822 = 0x20, + + /* 21 - 6F Reserved for future use */ + /* 70 - 7f Reserved for (U)SIM Toolkit Security Headers */ + /* 80 - 9F SME to SME specific use */ + /* A0 - BF Reserved for future use */ + /* C0 - DF SC specific use */ + /* E0 - FF Reserved for future use */ + + RIL_CDMA_SMS_UDH_OTHER = 0xFFFF, /* For unsupported or proprietary headers */ + RIL_CDMA_SMS_UDH_ID_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ + +} RIL_CDMA_SMS_UdhId; + +typedef struct { + /*indicates the reference number for a particular concatenated short message. */ + /*it is constant for every short message which makes up a particular concatenated short message*/ + unsigned char msg_ref; + + /*indicates the total number of short messages within the concatenated short message. + The value shall start at 1 and remain constant for every + short message which makes up the concatenated short message. + if it is 0 then the receiving entity shall ignore the whole Information Element*/ + unsigned char total_sm; + + /* + * it indicates the sequence number of a particular short message within the concatenated short + * message. The value shall start at 1 and increment by one for every short message sent + * within the concatenated short message. If the value is zero or the value is + * greater than the value in octet 2 then the receiving + * entity shall ignore the whole Information Element. + */ + unsigned char seq_num; +} RIL_CDMA_SMS_UdhConcat8; + +/* GW message waiting actions +*/ +typedef enum { + RIL_CDMA_SMS_GW_MSG_WAITING_NONE, + RIL_CDMA_SMS_GW_MSG_WAITING_DISCARD, + RIL_CDMA_SMS_GW_MSG_WAITING_STORE, + RIL_CDMA_SMS_GW_MSG_WAITING_NONE_1111, + RIL_CDMA_SMS_GW_MSG_WAITING_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_GWMsgWaiting; + +/* GW message waiting types +*/ +typedef enum { + RIL_CDMA_SMS_GW_MSG_WAITING_VOICEMAIL, + RIL_CDMA_SMS_GW_MSG_WAITING_FAX, + RIL_CDMA_SMS_GW_MSG_WAITING_EMAIL, + RIL_CDMA_SMS_GW_MSG_WAITING_OTHER, + RIL_CDMA_SMS_GW_MSG_WAITING_KIND_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_GWMsgWaitingKind; + +typedef struct { + RIL_CDMA_SMS_GWMsgWaiting msg_waiting; + RIL_CDMA_SMS_GWMsgWaitingKind msg_waiting_kind; + + /*it indicates the number of messages of the type specified in Octet 1 waiting.*/ + unsigned char message_count; +} RIL_CDMA_SMS_UdhSpecialSM; + +typedef struct { + unsigned char dest_port; + unsigned char orig_port; +} RIL_CDMA_SMS_UdhWap8; + +typedef struct { + unsigned short dest_port; + unsigned short orig_port; +} RIL_CDMA_SMS_UdhWap16; + +typedef struct { + unsigned short msg_ref; + unsigned char total_sm; + unsigned char seq_num; + +} RIL_CDMA_SMS_UdhConcat16; + +typedef enum { + RIL_CDMA_SMS_UDH_LEFT_ALIGNMENT = 0, + RIL_CDMA_SMS_UDH_CENTER_ALIGNMENT, + RIL_CDMA_SMS_UDH_RIGHT_ALIGNMENT, + RIL_CDMA_SMS_UDH_DEFAULT_ALIGNMENT, + RIL_CDMA_SMS_UDH_MAX_ALIGNMENT, + RIL_CDMA_SMS_UDH_ALIGNMENT_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_UdhAlignment; + +typedef enum { + RIL_CDMA_SMS_UDH_FONT_NORMAL = 0, + RIL_CDMA_SMS_UDH_FONT_LARGE, + RIL_CDMA_SMS_UDH_FONT_SMALL, + RIL_CDMA_SMS_UDH_FONT_RESERVED, + RIL_CDMA_SMS_UDH_FONT_MAX, + RIL_CDMA_SMS_UDH_FONT_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_UdhFontSize; + +typedef enum { + RIL_CDMA_SMS_UDH_TEXT_COLOR_BLACK = 0x0, + RIL_CDMA_SMS_UDH_TEXT_COLOR_DARK_GREY = 0x1, + RIL_CDMA_SMS_UDH_TEXT_COLOR_DARK_RED = 0x2, + RIL_CDMA_SMS_UDH_TEXT_COLOR_DARK_YELLOW = 0x3, + RIL_CDMA_SMS_UDH_TEXT_COLOR_DARK_GREEN = 0x4, + RIL_CDMA_SMS_UDH_TEXT_COLOR_DARK_CYAN = 0x5, + RIL_CDMA_SMS_UDH_TEXT_COLOR_DARK_BLUE = 0x6, + RIL_CDMA_SMS_UDH_TEXT_COLOR_DARK_MAGENTA = 0x7, + RIL_CDMA_SMS_UDH_TEXT_COLOR_GREY = 0x8, + RIL_CDMA_SMS_UDH_TEXT_COLOR_WHITE = 0x9, + RIL_CDMA_SMS_UDH_TEXT_COLOR_BRIGHT_RED = 0xA, + RIL_CDMA_SMS_UDH_TEXT_COLOR_BRIGHT_YELLOW = 0xB, + RIL_CDMA_SMS_UDH_TEXT_COLOR_BRIGHT_GREEN = 0xC, + RIL_CDMA_SMS_UDH_TEXT_COLOR_BRIGHT_CYAN = 0xD, + RIL_CDMA_SMS_UDH_TEXT_COLOR_BRIGHT_BLUE = 0xE, + RIL_CDMA_SMS_UDH_TEXT_COLOR_BRIGHT_MAGENTA = 0xF, + RIL_CDMA_SMS_UDH_TEXT_COLOR_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_UdhTextColor; + +typedef struct { + unsigned char start_position; + unsigned char text_formatting_length; + RIL_CDMA_SMS_UdhAlignment alignment_type ; /*bit 0 and bit 1*/ + RIL_CDMA_SMS_UdhFontSize font_size ; /*bit 3 and bit 2*/ + unsigned char style_bold; /*bit 4 */ + unsigned char style_italic; /*bit 5 */ + unsigned char style_underlined; /*bit 6 */ + unsigned char style_strikethrough; /*bit 7 */ + + /* if FALSE, ignore the following color information */ + unsigned char is_color_present; + RIL_CDMA_SMS_UdhTextColor text_color_foreground; + RIL_CDMA_SMS_UdhTextColor text_color_background; + +} RIL_CDMA_SMS_UdhTextFormating; + +/* Predefined sound +*/ +typedef struct { + unsigned char position; + unsigned char snd_number; +} RIL_CDMA_SMS_UdhPreDefSound; + +/* User Defined sound +*/ +typedef struct { + unsigned char data_length; + unsigned char position; + unsigned char user_def_sound[RIL_CDMA_SMS_UDH_MAX_SND_SIZE]; +} RIL_CDMA_SMS_UdhUserDefSound; + +/* Large picture +*/ +typedef struct { + unsigned char position; + unsigned char data[RIL_CDMA_SMS_UDH_LARGE_PIC_SIZE]; +} RIL_CDMA_SMS_UdhLargePictureData; + +/* Small picture +*/ +typedef struct { + unsigned char position; + unsigned char data[RIL_CDMA_SMS_UDH_SMALL_PIC_SIZE]; +} RIL_CDMA_SMS_UdhSmallPictureData; + +/* Variable length picture +*/ +typedef struct { + unsigned char position; + unsigned char width; /* Number of pixels - Should be a mutliple of 8 */ + unsigned char height; + unsigned char data[RIL_CDMA_SMS_UDH_VAR_PIC_SIZE]; +} RIL_CDMA_SMS_UdhVarPicture; + +/* Predefined animation +*/ +typedef struct { + unsigned char position; + unsigned char animation_number; +} RIL_CDMA_SMS_UdhPreDefAnim; + +/* Large animation +*/ +typedef struct { + unsigned char position; + unsigned char data[RIL_CDMA_SMS_UDH_ANIM_NUM_BITMAPS][RIL_CDMA_SMS_UDH_LARGE_BITMAP_SIZE]; +} RIL_CDMA_SMS_UdhLargeAnim; + +/* Small animation +*/ +typedef struct { + unsigned char position; + unsigned char data[RIL_CDMA_SMS_UDH_ANIM_NUM_BITMAPS][RIL_CDMA_SMS_UDH_SMALL_BITMAP_SIZE]; +} RIL_CDMA_SMS_UdhSmallAnim; + +/* User Prompt Indicator UDH +*/ +typedef struct { + unsigned char number_of_objects; + /* Number of objects of the same kind that follow this header which will + ** be stitched together by the applications. For example, 5 small pictures + ** are to be stitched together horizontally, or 6 iMelody tones are to be + ** connected together with intermediate iMelody header and footer ignored. + ** Allowed objects to be stitched: + ** - Images (small, large, variable) + ** - User defined sounds + */ +} RIL_CDMA_SMS_UdhUserPrompt; + +typedef struct { + unsigned char length; + + unsigned char data[RIL_CDMA_SMS_UDH_EO_DATA_SEGMENT_MAX]; + /* RIL_CDMA_SMS_UDH_EO_VCARD: See http://www.imc.org/pdi/vcard-21.doc for payload */ + /* RIL_CDMA_SMS_UDH_EO_VCALENDAR: See http://www.imc.org/pdi/vcal-10.doc */ + /* Or: Unsupported/proprietary extended objects */ + +} RIL_CDMA_SMS_UdhEoContent; + +/* Extended Object UDH +*/ +/* Extended Object IDs/types +*/ +typedef enum { + RIL_CDMA_SMS_UDH_EO_VCARD = 0x09, + RIL_CDMA_SMS_UDH_EO_VCALENDAR = 0x0A, + RIL_CDMA_SMS_UDH_EO_MAX32 = 0x10000000 /* Force constant ENUM size in structures */ +} RIL_CDMA_SMS_UdhEoId; + +typedef struct { + /* Extended objects are to be used together with 16-bit concatenation + ** UDH. The max number of segments supported for E.O. is 8 at least. + */ + RIL_CDMA_SMS_UdhEoContent content; + + unsigned char first_segment; + /* The following fields are only present in the first segment of a + ** concatenated SMS message. + */ + unsigned char reference; + /* Identify those extended object segments which should be linked together + */ + unsigned short length; + /* Length of the whole extended object data + */ + unsigned char control; + RIL_CDMA_SMS_UdhEoId type; + unsigned short position; + /* Absolute position of the E.O. in the whole text after concatenation, + ** starting from 1. + */ +} RIL_CDMA_SMS_UdhEo; + +typedef struct { + RIL_CDMA_SMS_UdhId header_id; + unsigned char header_length; + unsigned char data[RIL_CDMA_SMS_UDH_OTHER_SIZE]; +} RIL_CDMA_SMS_UdhOther; + +typedef struct { + unsigned char header_length; +} RIL_CDMA_SMS_UdhRfc822; + +typedef struct { + RIL_CDMA_SMS_UdhId header_id; + + union { + RIL_CDMA_SMS_UdhConcat8 concat_8; // 00 + + RIL_CDMA_SMS_UdhSpecialSM special_sm; // 01 + RIL_CDMA_SMS_UdhWap8 wap_8; // 04 + RIL_CDMA_SMS_UdhWap16 wap_16; // 05 + RIL_CDMA_SMS_UdhConcat16 concat_16; // 08 + RIL_CDMA_SMS_UdhTextFormating text_formating; // 0a + RIL_CDMA_SMS_UdhPreDefSound pre_def_sound; // 0b + RIL_CDMA_SMS_UdhUserDefSound user_def_sound; // 0c + RIL_CDMA_SMS_UdhPreDefAnim pre_def_anim; // 0d + RIL_CDMA_SMS_UdhLargeAnim large_anim; // 0e + RIL_CDMA_SMS_UdhSmallAnim small_anim; // 0f + RIL_CDMA_SMS_UdhLargePictureData large_picture; // 10 + RIL_CDMA_SMS_UdhSmallPictureData small_picture; // 11 + RIL_CDMA_SMS_UdhVarPicture var_picture; // 12 + + RIL_CDMA_SMS_UdhUserPrompt user_prompt; // 13 + RIL_CDMA_SMS_UdhEo eo; // 14 + + RIL_CDMA_SMS_UdhRfc822 rfc822; // 20 + RIL_CDMA_SMS_UdhOther other; + + }u; +} RIL_CDMA_SMS_Udh; + +/* ----------------------------- */ +/* -- User data encoding type -- */ +/* ----------------------------- */ +typedef enum { + RIL_CDMA_SMS_ENCODING_OCTET = 0, /* 8-bit */ + RIL_CDMA_SMS_ENCODING_IS91EP, /* varies */ + RIL_CDMA_SMS_ENCODING_ASCII, /* 7-bit */ + RIL_CDMA_SMS_ENCODING_IA5, /* 7-bit */ + RIL_CDMA_SMS_ENCODING_UNICODE, /* 16-bit */ + RIL_CDMA_SMS_ENCODING_SHIFT_JIS, /* 8 or 16-bit */ + RIL_CDMA_SMS_ENCODING_KOREAN, /* 8 or 16-bit */ + RIL_CDMA_SMS_ENCODING_LATIN_HEBREW, /* 8-bit */ + RIL_CDMA_SMS_ENCODING_LATIN, /* 8-bit */ + RIL_CDMA_SMS_ENCODING_GSM_7_BIT_DEFAULT, /* 7-bit */ + RIL_CDMA_SMS_ENCODING_MAX32 = 0x10000000 + +} RIL_CDMA_SMS_UserDataEncoding; + +/* ------------------------ */ +/* -- IS-91 EP data type -- */ +/* ------------------------ */ +typedef enum { + RIL_CDMA_SMS_IS91EP_VOICE_MAIL = 0x82, + RIL_CDMA_SMS_IS91EP_SHORT_MESSAGE_FULL = 0x83, + RIL_CDMA_SMS_IS91EP_CLI_ORDER = 0x84, + RIL_CDMA_SMS_IS91EP_SHORT_MESSAGE = 0x85, + RIL_CDMA_SMS_IS91EP_MAX32 = 0x10000000 + +} RIL_CDMA_SMS_IS91EPType; + +typedef struct { + /* NOTE: If message_id.udh_present == TRUE: + ** 'num_headers' is the number of User Data Headers (UDHs), + ** and 'headers' include all those headers. + */ + unsigned char num_headers; + RIL_CDMA_SMS_Udh headers[RIL_CDMA_SMS_MAX_UD_HEADERS]; + + RIL_CDMA_SMS_UserDataEncoding encoding; + RIL_CDMA_SMS_IS91EPType is91ep_type; + + /*---------------------------------------------------------------------- + 'data_len' indicates the valid number of bytes in the 'data' array. + + 'padding_bits' (0-7) indicates how many bits in the last byte of 'data' + are invalid bits. This parameter is only used for Mobile-Originated + messages. There is no way for the API to tell how many padding bits + exist in the received message. Instead, the application can find out how + many padding bits exist in the user data when decoding the user data. + + 'data' has the raw bits of the user data field of the SMS message. + The client software should decode the raw user data according to its + supported encoding types and languages. + + EXCEPTION 1: CMT-91 user data raw bits are first translated into BD fields + (e.g. num_messages, callback, etc.) The translated user data field in + VMN and Short Message is in the form of ASCII characters, each occupying + a byte in the resulted 'data'. + + EXCEPTION 2: GSM 7-bit Default characters are decoded so that each byte + has one 7-bit GSM character. + + 'number_of_digits' is the number of digits/characters (7, 8, 16, or + whatever bits) in the raw user data, which can be used by the client + when decoding the user data according to the encoding type and language. + -------------------------------------------------------------------------*/ + unsigned char data_len; + unsigned char padding_bits; + unsigned char data[ RIL_CDMA_SMS_USER_DATA_MAX ]; + unsigned char number_of_digits; + +} RIL_CDMA_SMS_CdmaUserData; + +/* -------------------- */ +/* ---- Message Id ---- */ +/* -------------------- */ +typedef enum { + RIL_CDMA_SMS_BD_TYPE_RESERVED_0 = 0, + RIL_CDMA_SMS_BD_TYPE_DELIVER, /* MT only */ + RIL_CDMA_SMS_BD_TYPE_SUBMIT, /* MO only */ + RIL_CDMA_SMS_BD_TYPE_CANCELLATION, /* MO only */ + RIL_CDMA_SMS_BD_TYPE_DELIVERY_ACK, /* MT only */ + RIL_CDMA_SMS_BD_TYPE_USER_ACK, /* MT & MO */ + RIL_CDMA_SMS_BD_TYPE_READ_ACK, /* MT & MO */ + RIL_CDMA_SMS_BD_TYPE_MAX32 = 0x10000000 + +} RIL_CDMA_SMS_BdMessageType; + +typedef unsigned int RIL_CDMA_SMS_MessageNumber; + +typedef struct { + RIL_CDMA_SMS_BdMessageType type; + RIL_CDMA_SMS_MessageNumber id_number; + unsigned char udh_present; + /* NOTE: if FEATURE_SMS_UDH is not defined, + ** udh_present should be ignored. + */ +} RIL_CDMA_SMS_MessageId; + +typedef unsigned char RIL_CDMA_SMS_UserResponse; + +/* ------------------- */ +/* ---- Timestamp ---- */ +/* ------------------- */ +typedef struct { + /* If 'year' is between 96 and 99, the actual year is 1900 + 'year'; + if 'year' is between 00 and 95, the actual year is 2000 + 'year'. + NOTE: Each field has two BCD digits and byte arrangement is <MSB, ... ,LSB> + */ + unsigned char year; /* 0x00-0x99 */ + unsigned char month; /* 0x01-0x12 */ + unsigned char day; /* 0x01-0x31 */ + unsigned char hour; /* 0x00-0x23 */ + unsigned char minute; /* 0x00-0x59 */ + unsigned char second; /* 0x00-0x59 */ + signed char timezone; /* +/-, [-48,+48] number of 15 minutes - GW only */ +} RIL_CDMA_SMS_Timestamp; + +/* ------------------ */ +/* ---- Priority ---- */ +/* ------------------ */ +typedef enum { + RIL_CDMA_SMS_PRIORITY_NORMAL = 0, + RIL_CDMA_SMS_PRIORITY_INTERACTIVE, + RIL_CDMA_SMS_PRIORITY_URGENT, + RIL_CDMA_SMS_PRIORITY_EMERGENCY, + RIL_CDMA_SMS_PRIORITY_MAX32 = 0x10000000 + +} RIL_CDMA_SMS_Priority; + +/* ----------------- */ +/* ---- Privacy ---- */ +/* ----------------- */ +typedef enum { + RIL_CDMA_SMS_PRIVACY_NORMAL = 0, + RIL_CDMA_SMS_PRIVACY_RESTRICTED, + RIL_CDMA_SMS_PRIVACY_CONFIDENTIAL, + RIL_CDMA_SMS_PRIVACY_SECRET, + RIL_CDMA_SMS_PRIVACY_MAX32 = 0x10000000 + +} RIL_CDMA_SMS_Privacy; + +/* ---------------------- */ +/* ---- Reply option ---- */ +/* ---------------------- */ +typedef struct { + /* whether user ack is requested + */ + unsigned char user_ack_requested; + + /* whether delivery ack is requested. + Should be FALSE for incoming messages. + */ + unsigned char delivery_ack_requested; + + /* Message originator requests the receiving phone to send back a READ_ACK + ** message automatically when the user reads the received message. + */ + unsigned char read_ack_requested; + +} RIL_CDMA_SMS_ReplyOption; + +typedef enum { + RIL_CDMA_SMS_ALERT_MODE_DEFAULT = 0, + RIL_CDMA_SMS_ALERT_MODE_LOW_PRIORITY = 1, + RIL_CDMA_SMS_ALERT_MODE_MEDIUM_PRIORITY = 2, + RIL_CDMA_SMS_ALERT_MODE_HIGH_PRIORITY = 3, + + /* For pre-IS637A implementations, alert_mode only has values of True/False: + */ + RIL_CDMA_SMS_ALERT_MODE_OFF = 0, + RIL_CDMA_SMS_ALERT_MODE_ON = 1 + +} RIL_CDMA_SMS_AlertMode; + +/* ------------------ */ +/* ---- Language ---- */ +/* ------------------ */ +typedef enum { + RIL_CDMA_SMS_LANGUAGE_UNSPECIFIED = 0, + RIL_CDMA_SMS_LANGUAGE_ENGLISH, + RIL_CDMA_SMS_LANGUAGE_FRENCH, + RIL_CDMA_SMS_LANGUAGE_SPANISH, + RIL_CDMA_SMS_LANGUAGE_JAPANESE, + RIL_CDMA_SMS_LANGUAGE_KOREAN, + RIL_CDMA_SMS_LANGUAGE_CHINESE, + RIL_CDMA_SMS_LANGUAGE_HEBREW, + RIL_CDMA_SMS_LANGUAGE_MAX32 = 0x10000000 + +} RIL_CDMA_SMS_Language; + +/* ---------------------------------- */ +/* ---------- Display Mode ---------- */ +/* ---------------------------------- */ +typedef enum { + RIL_CDMA_SMS_DISPLAY_MODE_IMMEDIATE = 0, + RIL_CDMA_SMS_DISPLAY_MODE_DEFAULT = 1, + RIL_CDMA_SMS_DISPLAY_MODE_USER_INVOKE = 2, + RIL_CDMA_SMS_DISPLAY_MODE_RESERVED = 3 +} RIL_CDMA_SMS_DisplayMode; + +/* IS-637B parameters/fields +*/ + +/* ---------------------------------- */ +/* ---------- Delivery Status ------- */ +/* ---------------------------------- */ +typedef enum { + RIL_CDMA_SMS_DELIVERY_STATUS_ACCEPTED = 0, /* ERROR_CLASS_NONE */ + RIL_CDMA_SMS_DELIVERY_STATUS_DEPOSITED_TO_INTERNET = 1, /* ERROR_CLASS_NONE */ + RIL_CDMA_SMS_DELIVERY_STATUS_DELIVERED = 2, /* ERROR_CLASS_NONE */ + RIL_CDMA_SMS_DELIVERY_STATUS_CANCELLED = 3, /* ERROR_CLASS_NONE */ + + RIL_CDMA_SMS_DELIVERY_STATUS_NETWORK_CONGESTION = 4, /* ERROR_CLASS_TEMP & PERM */ + RIL_CDMA_SMS_DELIVERY_STATUS_NETWORK_ERROR = 5, /* ERROR_CLASS_TEMP & PERM */ + RIL_CDMA_SMS_DELIVERY_STATUS_CANCEL_FAILED = 6, /* ERROR_CLASS_PERM */ + RIL_CDMA_SMS_DELIVERY_STATUS_BLOCKED_DESTINATION = 7, /* ERROR_CLASS_PERM */ + RIL_CDMA_SMS_DELIVERY_STATUS_TEXT_TOO_LONG = 8, /* ERROR_CLASS_PERM */ + RIL_CDMA_SMS_DELIVERY_STATUS_DUPLICATE_MESSAGE = 9, /* ERROR_CLASS_PERM */ + RIL_CDMA_SMS_DELIVERY_STATUS_INVALID_DESTINATION = 10, /* ERROR_CLASS_PERM */ + RIL_CDMA_SMS_DELIVERY_STATUS_MESSAGE_EXPIRED = 13, /* ERROR_CLASS_PERM */ + + RIL_CDMA_SMS_DELIVERY_STATUS_UNKNOWN_ERROR = 0x1F /* ERROR_CLASS_PERM */ + + /* All the other values are reserved */ + +} RIL_CDMA_SMS_DeliveryStatusE; + +typedef struct { + RIL_CDMA_SMS_ErrorClass error_class; + RIL_CDMA_SMS_DeliveryStatusE status; +} RIL_CDMA_SMS_DeliveryStatus; + +typedef struct { + unsigned char address[RIL_CDMA_SMS_IP_ADDRESS_SIZE]; + unsigned char is_valid; +} RIL_CDMA_SMS_IpAddress; + +/* This special parameter captures any unrecognized/proprietary parameters +*/ +typedef struct { + unsigned char input_other_len; + unsigned char desired_other_len; /* used during decoding */ + unsigned char * other_data; +} RIL_CDMA_SMS_OtherParm; + +typedef struct { + /* the mask indicates which fields are present in this message */ + unsigned int mask; + + RIL_CDMA_SMS_MessageId message_id; + RIL_CDMA_SMS_CdmaUserData user_data; + RIL_CDMA_SMS_UserResponse user_response; + RIL_CDMA_SMS_Timestamp mc_time; + RIL_CDMA_SMS_Timestamp validity_absolute; + RIL_CDMA_SMS_Timestamp validity_relative; + RIL_CDMA_SMS_Timestamp deferred_absolute; + RIL_CDMA_SMS_Timestamp deferred_relative; + RIL_CDMA_SMS_Priority priority; + RIL_CDMA_SMS_Privacy privacy; + RIL_CDMA_SMS_ReplyOption reply_option; + unsigned char num_messages; /* the actual value; not BCDs */ + RIL_CDMA_SMS_AlertMode alert_mode; + /* For pre-IS-637A implementations, alert_mode is either Off or On. */ + RIL_CDMA_SMS_Language language; + RIL_CDMA_SMS_Address callback; + RIL_CDMA_SMS_DisplayMode display_mode; + + RIL_CDMA_SMS_DeliveryStatus delivery_status; + unsigned int deposit_index; + + RIL_CDMA_SMS_IpAddress ip_address; + unsigned char rsn_no_notify; + + /* See function comments of wms_ts_decode() and + ** wms_ts_decode_cdma_bd_with_other() for details regarding 'other' parameters + */ + RIL_CDMA_SMS_OtherParm other; + +} RIL_CDMA_SMS_ClientBd; + +typedef struct { + unsigned char length; /* length, in bytes, of the encoded SMS message */ + unsigned char * data; /* the encoded SMS message (max 255 bytes) */ +} RIL_CDMA_Encoded_SMS; + +#ifdef __cplusplus +} +#endif + +#endif /*ANDROID_RIL_CDMA_SMS_H*/ diff --git a/radio/include/telephony/ril_mcc.h b/radio/include/telephony/ril_mcc.h new file mode 100644 index 00000000..dc56b126 --- /dev/null +++ b/radio/include/telephony/ril_mcc.h @@ -0,0 +1,71 @@ +/* + * Copyright (C) 2019 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. + */ + +#ifndef RIL_MCC_H +#define RIL_MCC_H + +#include <climits> +#include <cstdio> +#include <string> + +namespace ril { +namespace util { +namespace mcc { + +/** + * Decode an integer mcc and encode as 3 digit string + * + * @param an integer mcc, its range should be in 0 to 999. + * + * @return string representation of an encoded MCC or an empty string + * if the MCC is not a valid MCC value. + */ +static inline std::string decode(int mcc) { + char mccStr[4] = {0}; + if (mcc > 999 || mcc < 0) return ""; + + snprintf(mccStr, sizeof(mccStr), "%03d", mcc); + return mccStr; +} + +// echo -e "#include \"hardware/ril/include/telephony/ril_mcc.h\"\nint main()"\ +// "{ return ril::util::mcc::test(); }" > ril_test.cpp \ +// && g++ -o /tmp/ril_test -DTEST_RIL_MCC ril_test.cpp; \ +// rm ril_test.cpp; /tmp/ril_test && [ $? ] && echo "passed" +#ifdef TEST_RIL_MCC +static int test() { + const struct mcc_ints { const int in; const char * out; } legacy_mccs[] = { + {INT_MAX, ""}, + {1, "001"}, + {11, "011"}, + {111, "111"}, + {0, "000"}, + {9999, ""}, + {-12, ""}, + }; + + for (int i=0; i < sizeof(legacy_mccs) / sizeof(struct mcc_ints); i++) { + if (decode(legacy_mccs[i].in).compare(legacy_mccs[i].out)) return 1; + } + + return 0; +} +#endif + +} +} +} +#endif /* !defined(RIL_MCC_H) */ diff --git a/radio/include/telephony/ril_mnc.h b/radio/include/telephony/ril_mnc.h new file mode 100644 index 00000000..fcbae997 --- /dev/null +++ b/radio/include/telephony/ril_mnc.h @@ -0,0 +1,149 @@ +/* + * Copyright (C) 2018 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. + */ + +#ifndef RIL_MNC_H +#define RIL_MNC_H + +#include <climits> +#include <cstdio> +#include <string> + +namespace ril { +namespace util { +namespace mnc { + +/** + * Decode an MNC with an optional length indicator provided in the most-significant nibble. + * + * @param mnc an encoded MNC value; if no encoding is provided, then the string is returned + * as a minimum length string representing the provided integer. + * + * @return string representation of an encoded MNC or an empty string if the MNC is not a valid + * MNC value. + */ +static inline std::string decode(int mnc) { + if (mnc == INT_MAX || mnc < 0) return ""; + unsigned umnc = mnc; + char mncNumDigits = (umnc >> (sizeof(int) * 8 - 4)) & 0xF; + + umnc = (umnc << 4) >> 4; + if (umnc > 999) return ""; + + char mncStr[4] = {0}; + switch (mncNumDigits) { + case 0: + // Legacy MNC report hasn't set the number of digits; preserve current + // behavior and make a string of the minimum number of required digits. + return std::to_string(umnc); + + case 2: + snprintf(mncStr, sizeof(mncStr), "%03.3u", umnc); + return mncStr + 1; + + case 3: + snprintf(mncStr, sizeof(mncStr), "%03.3u", umnc); + return mncStr; + + default: + // Error case + return ""; + } + +} + +/** + * Encode an MNC of the given value and a given number of digits + * + * @param mnc an MNC value 0-999 or INT_MAX if unknown + * @param numDigits the number of MNC digits {2, 3} or 0 if unknown + * + * @return an encoded MNC with embedded length information + */ +static inline int encode(int mnc, int numDigits) { + if (mnc > 999 || mnc < 0) return INT_MAX; + switch (numDigits) { + case 0: // fall through + case 2: // fall through + case 3: + break; + + default: + return INT_MAX; + }; + + return (numDigits << (sizeof(int) * 8 - 4)) | mnc; +} + +/** + * Encode an MNC of the given value + * + * @param mnc the string representation of the MNC, with the length equal to the length of the + * provided string. + * + * @return an encoded MNC with embedded length information + */ +static inline int encode(const std::string & mnc) { + return encode(std::stoi(mnc), mnc.length()); +} + +// echo -e "#include \"hardware/ril/include/telephony/ril_mnc.h\"\nint main()"\ +// "{ return ril::util::mnc::test(); }" > ril_test.cpp \ +// && g++ -o /tmp/ril_test -DTEST_RIL_MNC ril_test.cpp; \ +// rm ril_test.cpp; /tmp/ril_test && [ $? ] && echo "passed" +#ifdef TEST_RIL_MNC +static int test() { + const struct mnc_strings { const char * in; const char * out; } mncs[] = { + {"0001",""}, + {"9999",""}, + {"0",""}, + {"9",""}, + {"123","123"}, + {"000","000"}, + {"001","001"}, + {"011","011"}, + {"111","111"}, + {"00","00"}, + {"01","01"}, + {"11","11"}, + {"09","09"}, + {"099","099"}, + {"999", "999"}}; + + for (int i=0; i< sizeof(mncs) / sizeof(struct mnc_strings); i++) { + if (decode(encode(mncs[i].in)).compare(mncs[i].out)) return 1; + } + + const struct mnc_ints { const int in; const char * out; } legacy_mncs[] = { + {INT_MAX, ""}, + {1, "1"}, + {11, "11"}, + {111, "111"}, + {0, "0"}, + {9999, ""}, + }; + + for (int i=0; i < sizeof(legacy_mncs) / sizeof(struct mnc_ints); i++) { + if (decode(legacy_mncs[i].in).compare(legacy_mncs[i].out)) return 1; + } + + return 0; +} +#endif + +} +} +} +#endif /* !defined(RIL_MNC_H) */ diff --git a/radio/include/telephony/ril_msim.h b/radio/include/telephony/ril_msim.h new file mode 100644 index 00000000..5c0b8c51 --- /dev/null +++ b/radio/include/telephony/ril_msim.h @@ -0,0 +1,48 @@ +/* + * Copyright (C) 2014 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. + */ + + +#ifndef ANDROID_RIL_MSIM_H +#define ANDROID_RIL_MSIM_H 1 + +#ifdef __cplusplus +extern "C" { +#endif + +typedef enum { + RIL_UICC_SUBSCRIPTION_DEACTIVATE = 0, + RIL_UICC_SUBSCRIPTION_ACTIVATE = 1 +} RIL_UiccSubActStatus; + +typedef enum { + RIL_SUBSCRIPTION_1 = 0, + RIL_SUBSCRIPTION_2 = 1, + RIL_SUBSCRIPTION_3 = 2 +} RIL_SubscriptionType; + +typedef struct { + int slot; /* 0, 1, ... etc. */ + int app_index; /* array subscriptor from applications[RIL_CARD_MAX_APPS] in + RIL_REQUEST_GET_SIM_STATUS */ + RIL_SubscriptionType sub_type; /* Indicates subscription 1 or subscription 2 */ + RIL_UiccSubActStatus act_status; +} RIL_SelectUiccSub; + +#ifdef __cplusplus +} +#endif + +#endif /*ANDROID_RIL_MSIM_H*/ diff --git a/radio/include/telephony/ril_nv_items.h b/radio/include/telephony/ril_nv_items.h new file mode 100644 index 00000000..748ea072 --- /dev/null +++ b/radio/include/telephony/ril_nv_items.h @@ -0,0 +1,88 @@ +/* + * Copyright (C) 2014 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. + */ + +#ifndef ANDROID_RIL_NV_ITEMS_H +#define ANDROID_RIL_NV_ITEMS_H 1 + +#include <stdlib.h> + +#ifdef __cplusplus +extern "C" { +#endif + +/* Must match the values in RadioNVItems.java in frameworks/opt/telephony. */ +typedef enum { + + // CDMA radio and account information (items 1-10) + RIL_NV_CDMA_MEID = 1, // CDMA MEID (hex) + RIL_NV_CDMA_MIN = 2, // CDMA MIN (MSID) + RIL_NV_CDMA_MDN = 3, // CDMA MDN + RIL_NV_CDMA_ACCOLC = 4, // CDMA access overload control + + // Carrier device provisioning (items 11-30) + RIL_NV_DEVICE_MSL = 11, // device MSL + RIL_NV_RTN_RECONDITIONED_STATUS = 12, // RTN reconditioned status + RIL_NV_RTN_ACTIVATION_DATE = 13, // RTN activation date + RIL_NV_RTN_LIFE_TIMER = 14, // RTN life timer + RIL_NV_RTN_LIFE_CALLS = 15, // RTN life calls + RIL_NV_RTN_LIFE_DATA_TX = 16, // RTN life data TX + RIL_NV_RTN_LIFE_DATA_RX = 17, // RTN life data RX + RIL_NV_OMADM_HFA_LEVEL = 18, // HFA in progress + + // Mobile IP profile information (items 31-50) + RIL_NV_MIP_PROFILE_NAI = 31, // NAI realm + RIL_NV_MIP_PROFILE_HOME_ADDRESS = 32, // MIP home address + RIL_NV_MIP_PROFILE_AAA_AUTH = 33, // AAA auth + RIL_NV_MIP_PROFILE_HA_AUTH = 34, // HA auth + RIL_NV_MIP_PROFILE_PRI_HA_ADDR = 35, // primary HA address + RIL_NV_MIP_PROFILE_SEC_HA_ADDR = 36, // secondary HA address + RIL_NV_MIP_PROFILE_REV_TUN_PREF = 37, // reverse TUN preference + RIL_NV_MIP_PROFILE_HA_SPI = 38, // HA SPI + RIL_NV_MIP_PROFILE_AAA_SPI = 39, // AAA SPI + RIL_NV_MIP_PROFILE_MN_HA_SS = 40, // HA shared secret + RIL_NV_MIP_PROFILE_MN_AAA_SS = 41, // AAA shared secret + + // CDMA network and band config (items 51-70) + RIL_NV_CDMA_PRL_VERSION = 51, // CDMA PRL version + RIL_NV_CDMA_BC10 = 52, // CDMA band class 10 + RIL_NV_CDMA_BC14 = 53, // CDMA band class 14 + RIL_NV_CDMA_SO68 = 54, // CDMA SO68 + RIL_NV_CDMA_SO73_COP0 = 55, // CDMA SO73 COP0 + RIL_NV_CDMA_SO73_COP1TO7 = 56, // CDMA SO73 COP1-7 + RIL_NV_CDMA_1X_ADVANCED_ENABLED = 57, // CDMA 1X Advanced enabled + RIL_NV_CDMA_EHRPD_ENABLED = 58, // CDMA eHRPD enabled + RIL_NV_CDMA_EHRPD_FORCED = 59, // CDMA eHRPD forced + + // LTE network and band config (items 71-90) + RIL_NV_LTE_BAND_ENABLE_25 = 71, // LTE band 25 enable + RIL_NV_LTE_BAND_ENABLE_26 = 72, // LTE band 26 enable + RIL_NV_LTE_BAND_ENABLE_41 = 73, // LTE band 41 enable + + RIL_NV_LTE_SCAN_PRIORITY_25 = 74, // LTE band 25 scan priority + RIL_NV_LTE_SCAN_PRIORITY_26 = 75, // LTE band 26 scan priority + RIL_NV_LTE_SCAN_PRIORITY_41 = 76, // LTE band 41 scan priority + + RIL_NV_LTE_HIDDEN_BAND_PRIORITY_25 = 77, // LTE hidden band 25 priority + RIL_NV_LTE_HIDDEN_BAND_PRIORITY_26 = 78, // LTE hidden band 26 priority + RIL_NV_LTE_HIDDEN_BAND_PRIORITY_41 = 79, // LTE hidden band 41 priority + +} RIL_NV_Item; + +#ifdef __cplusplus +} +#endif + +#endif /* ANDROID_RIL_NV_ITEMS_H */ diff --git a/radio/libril/Android.mk b/radio/libril/Android.mk deleted file mode 100644 index e435c09f..00000000 --- a/radio/libril/Android.mk +++ /dev/null @@ -1,53 +0,0 @@ -# Copyright 2006 The Android Open Source Project - -LOCAL_PATH:= $(call my-dir) -include $(CLEAR_VARS) - -LOCAL_VENDOR_MODULE := true - -LOCAL_SRC_FILES:= \ - ril.cpp \ - ril_event.cpp\ - RilSapSocket.cpp \ - ril_service.cpp \ - sap_service.cpp - -LOCAL_SHARED_LIBRARIES := \ - liblog \ - libutils \ - libcutils \ - libhardware_legacy \ - librilutils \ - android.hardware.radio@1.0 \ - android.hardware.radio@1.1 \ - android.hardware.radio@1.2 \ - android.hardware.radio@1.3 \ - android.hardware.radio@1.4 \ - android.hardware.radio.deprecated@1.0 \ - libhidlbase \ - -LOCAL_STATIC_LIBRARIES := \ - libprotobuf-c-nano-enable_malloc-32bit \ - -LOCAL_CFLAGS += -Wall -Wextra -Wno-unused-parameter -Werror -LOCAL_CFLAGS += -DPB_FIELD_32BIT - -ifeq ($(SIM_COUNT), 2) - LOCAL_CFLAGS += -DANDROID_MULTI_SIM -DDSDA_RILD1 - LOCAL_CFLAGS += -DANDROID_SIM_COUNT_2 -endif - -ifneq ($(DISABLE_RILD_OEM_HOOK),) - LOCAL_CFLAGS += -DOEM_HOOK_DISABLED -endif - -LOCAL_C_INCLUDES += external/nanopb-c -LOCAL_C_INCLUDES += device/generic/goldfish/ -#LOCAL_C_INCLUDES += $(LOCAL_PATH)/../include -LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)/../include - -LOCAL_MODULE:= libril-goldfish-fork -LOCAL_SANITIZE := integer - -include $(BUILD_SHARED_LIBRARY) - diff --git a/radio/libril/MODULE_LICENSE_APACHE2 b/radio/libril/MODULE_LICENSE_APACHE2 deleted file mode 100644 index e69de29b..00000000 --- a/radio/libril/MODULE_LICENSE_APACHE2 +++ /dev/null diff --git a/radio/libril/NOTICE b/radio/libril/NOTICE deleted file mode 100644 index c5b1efa7..00000000 --- a/radio/libril/NOTICE +++ /dev/null @@ -1,190 +0,0 @@ - - Copyright (c) 2005-2008, 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. - - 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. - - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - diff --git a/radio/libril/RilSapSocket.cpp b/radio/libril/RilSapSocket.cpp deleted file mode 100644 index 211371e2..00000000 --- a/radio/libril/RilSapSocket.cpp +++ /dev/null @@ -1,295 +0,0 @@ -/* -* Copyright (C) 2014 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 __STDC_LIMIT_MACROS -#include <stdint.h> -#define RIL_SHLIB -#include "telephony/ril.h" -#include "RilSapSocket.h" -#include "pb_decode.h" -#include "pb_encode.h" -#undef LOG_TAG -#define LOG_TAG "RIL_UIM_SOCKET" -#include <utils/Log.h> -#include <arpa/inet.h> -#include <errno.h> -#include <sap_service.h> - -static RilSapSocket::RilSapSocketList *head = NULL; - -extern "C" void -RIL_requestTimedCallback (RIL_TimedCallback callback, void *param, - const struct timeval *relativeTime); - -struct RIL_Env RilSapSocket::uimRilEnv = { - .OnRequestComplete = RilSapSocket::sOnRequestComplete, - .OnUnsolicitedResponse = RilSapSocket::sOnUnsolicitedResponse, - .RequestTimedCallback = RIL_requestTimedCallback -}; - -void RilSapSocket::sOnRequestComplete (RIL_Token t, - RIL_Errno e, - void *response, - size_t responselen) { - RilSapSocket *sap_socket; - SapSocketRequest *request = (SapSocketRequest*) t; - - RLOGD("Socket id:%d", request->socketId); - - sap_socket = getSocketById(request->socketId); - - if (sap_socket) { - sap_socket->onRequestComplete(t,e,response,responselen); - } else { - RLOGE("Invalid socket id"); - if (request->curr) { - free(request->curr); - } - free(request); - } -} - -#if defined(ANDROID_MULTI_SIM) -void RilSapSocket::sOnUnsolicitedResponse(int unsolResponse, - const void *data, - size_t datalen, - RIL_SOCKET_ID socketId) { - RilSapSocket *sap_socket = getSocketById(socketId); - if (sap_socket) { - sap_socket->onUnsolicitedResponse(unsolResponse, (void *)data, datalen); - } -} -#else -void RilSapSocket::sOnUnsolicitedResponse(int unsolResponse, - const void *data, - size_t datalen) { - RilSapSocket *sap_socket = getSocketById(RIL_SOCKET_1); - if(sap_socket){ - sap_socket->onUnsolicitedResponse(unsolResponse, (void *)data, datalen); - } -} -#endif - -void RilSapSocket::printList() { - RilSapSocketList *current = head; - RLOGD("Printing socket list"); - while(NULL != current) { - RLOGD("SocketName:%s",current->socket->name); - RLOGD("Socket id:%d",current->socket->id); - current = current->next; - } -} - -RilSapSocket *RilSapSocket::getSocketById(RIL_SOCKET_ID socketId) { - RilSapSocket *sap_socket; - RilSapSocketList *current = head; - - RLOGD("Entered getSocketById"); - printList(); - - while(NULL != current) { - if(socketId == current->socket->id) { - sap_socket = current->socket; - return sap_socket; - } - current = current->next; - } - return NULL; -} - -void RilSapSocket::initSapSocket(const char *socketName, - const RIL_RadioFunctions *uimFuncs) { - - if (strcmp(socketName, RIL1_SERVICE_NAME) == 0) { - if(!SocketExists(socketName)) { - addSocketToList(socketName, RIL_SOCKET_1, uimFuncs); - } - } - -#if (SIM_COUNT >= 2) - if (strcmp(socketName, RIL2_SERVICE_NAME) == 0) { - if(!SocketExists(socketName)) { - addSocketToList(socketName, RIL_SOCKET_2, uimFuncs); - } - } -#endif - -#if (SIM_COUNT >= 3) - if (strcmp(socketName, RIL3_SERVICE_NAME) == 0) { - if(!SocketExists(socketName)) { - addSocketToList(socketName, RIL_SOCKET_3, uimFuncs); - } - } -#endif - -#if (SIM_COUNT >= 4) - if (strcmp(socketName, RIL4_SERVICE_NAME) == 0) { - if(!SocketExists(socketName)) { - addSocketToList(socketName, RIL_SOCKET_4, uimFuncs); - } - } -#endif -} - -void RilSapSocket::addSocketToList(const char *socketName, RIL_SOCKET_ID socketid, - const RIL_RadioFunctions *uimFuncs) { - RilSapSocket* socket = NULL; - RilSapSocketList *current; - - if(!SocketExists(socketName)) { - socket = new RilSapSocket(socketName, socketid, uimFuncs); - RilSapSocketList* listItem = (RilSapSocketList*)malloc(sizeof(RilSapSocketList)); - if (!listItem) { - RLOGE("addSocketToList: OOM"); - delete socket; - return; - } - listItem->socket = socket; - listItem->next = NULL; - - RLOGD("Adding socket with id: %d", socket->id); - - if(NULL == head) { - head = listItem; - head->next = NULL; - } - else { - current = head; - while(NULL != current->next) { - current = current->next; - } - current->next = listItem; - } - } -} - -bool RilSapSocket::SocketExists(const char *socketName) { - RilSapSocketList* current = head; - - while(NULL != current) { - if(strcmp(current->socket->name, socketName) == 0) { - return true; - } - current = current->next; - } - return false; -} - -RilSapSocket::RilSapSocket(const char *socketName, - RIL_SOCKET_ID socketId, - const RIL_RadioFunctions *inputUimFuncs): - RilSocket(socketName, socketId) { - if (inputUimFuncs) { - uimFuncs = inputUimFuncs; - } -} - -void RilSapSocket::dispatchRequest(MsgHeader *req) { - // SapSocketRequest will be deallocated in onRequestComplete() - SapSocketRequest* currRequest=(SapSocketRequest*)malloc(sizeof(SapSocketRequest)); - if (!currRequest) { - RLOGE("dispatchRequest: OOM"); - // Free MsgHeader allocated in pushRecord() - free(req); - return; - } - currRequest->token = req->token; - currRequest->curr = req; - currRequest->p_next = NULL; - currRequest->socketId = id; - - pendingResponseQueue.enqueue(currRequest); - - if (uimFuncs) { - RLOGI("RilSapSocket::dispatchRequest [%d] > SAP REQUEST type: %d. id: %d. error: %d, \ - token 0x%p", - req->token, - req->type, - req->id, - req->error, - currRequest ); - -#if defined(ANDROID_MULTI_SIM) - uimFuncs->onRequest(req->id, req->payload->bytes, req->payload->size, currRequest, id); -#else - uimFuncs->onRequest(req->id, req->payload->bytes, req->payload->size, currRequest); -#endif - } -} - -void RilSapSocket::onRequestComplete(RIL_Token t, RIL_Errno e, void *response, - size_t response_len) { - SapSocketRequest* request= (SapSocketRequest*)t; - - if (!request || !request->curr) { - RLOGE("RilSapSocket::onRequestComplete: request/request->curr is NULL"); - return; - } - - MsgHeader *hdr = request->curr; - - MsgHeader rsp; - rsp.token = request->curr->token; - rsp.type = MsgType_RESPONSE; - rsp.id = request->curr->id; - rsp.error = (Error)e; - rsp.payload = (pb_bytes_array_t *)calloc(1, sizeof(pb_bytes_array_t) + response_len); - if (!rsp.payload) { - RLOGE("onRequestComplete: OOM"); - } else { - if (response && response_len > 0) { - memcpy(rsp.payload->bytes, response, response_len); - rsp.payload->size = response_len; - } else { - rsp.payload->size = 0; - } - - RLOGE("RilSapSocket::onRequestComplete: Token:%d, MessageId:%d ril token 0x%p", - hdr->token, hdr->id, t); - - sap::processResponse(&rsp, this); - free(rsp.payload); - } - - // Deallocate SapSocketRequest - if(!pendingResponseQueue.checkAndDequeue(hdr->id, hdr->token)) { - RLOGE("Token:%d, MessageId:%d", hdr->token, hdr->id); - RLOGE ("RilSapSocket::onRequestComplete: invalid Token or Message Id"); - } - - // Deallocate MsgHeader - free(hdr); -} - -void RilSapSocket::onUnsolicitedResponse(int unsolResponse, void *data, size_t datalen) { - if (data && datalen > 0) { - pb_bytes_array_t *payload = (pb_bytes_array_t *)calloc(1, - sizeof(pb_bytes_array_t) + datalen); - if (!payload) { - RLOGE("onUnsolicitedResponse: OOM"); - return; - } - memcpy(payload->bytes, data, datalen); - payload->size = datalen; - MsgHeader rsp; - rsp.payload = payload; - rsp.type = MsgType_UNSOL_RESPONSE; - rsp.id = (MsgId)unsolResponse; - rsp.error = Error_RIL_E_SUCCESS; - sap::processUnsolResponse(&rsp, this); - free(payload); - } -} diff --git a/radio/libril/RilSapSocket.h b/radio/libril/RilSapSocket.h deleted file mode 100644 index 1a816c58..00000000 --- a/radio/libril/RilSapSocket.h +++ /dev/null @@ -1,200 +0,0 @@ -/* -* Copyright (C) 2014 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. -*/ - -#ifndef RIL_UIM_SOCKET_H_INCLUDED -#define RIL_UIM_SOCKET_H_INCLUDED -#define RIL_SHLIB -#include "telephony/ril.h" -#include "RilSocket.h" -#include <hardware/ril/librilutils/proto/sap-api.pb.h> - -/** - * RilSapSocket is a derived class, derived from the RilSocket abstract - * class, representing sockets for communication between bluetooth SAP module and - * the ril daemon. - * <p> - * This class performs the following functions : - * <ul> - * <li>Initialize the socket. - * <li>Process the requests coming on the socket. - * <li>Provide handlers for Unsolicited and request responses. - * <li>Request and pending response queue handling. - * </ul> - */ -class RilSapSocket : public RilSocket { - /** - * Place holder for the radio functions returned by the initialization - * function. Currenty only onRequest handler is being used. - */ - const RIL_RadioFunctions* uimFuncs; - - /** - * Wrapper struct for handling the requests in the queue. - */ - typedef struct SapSocketRequest { - int token; - MsgHeader* curr; - struct SapSocketRequest* p_next; - RIL_SOCKET_ID socketId; - } SapSocketRequest; - - /** - * Queue for requests that are pending dispatch. - */ - Ril_queue<SapSocketRequest> dispatchQueue; - - /** - * Queue for requests that are dispatched but are pending response - */ - Ril_queue<SapSocketRequest> pendingResponseQueue; - - public: - /** - * Initialize the socket and add the socket to the list. - * - * @param Name of the socket. - * @param Radio functions to be used by the socket. - */ - static void initSapSocket(const char *socketName, - const RIL_RadioFunctions *uimFuncs); - - /** - * Ril envoronment variable that holds the request and - * unsol response handlers. - */ - static struct RIL_Env uimRilEnv; - - /** - * Function to print the socket list. - */ - static void printList(); - - /** - * Dispatches the request to the lower layers. - * It calls the on request function. - * - * @param request The request message. - */ - void dispatchRequest(MsgHeader *request); - - /** - * Class method to get the socket from the socket list. - * - * @param socketId Socket id. - * @return the sap socket. - */ - static RilSapSocket* getSocketById(RIL_SOCKET_ID socketId); - - /** - * Datatype to handle the socket list. - */ - typedef struct RilSapSocketList { - RilSapSocket* socket; - RilSapSocketList *next; - } RilSapSocketList; - - protected: - /** - * Socket handler to be called when a request has - * been completed. - * - * @param Token associated with the request. - * @param Error, if any, while processing the request. - * @param The response payload. - * @param Response payload length. - */ - void onRequestComplete(RIL_Token t,RIL_Errno e, - void *response, size_t response_len); - - /** - * Socket handler to be called when there is an - * unsolicited response. - * - * @param Message id. - * @param Response data. - * @param Response data length. - */ - void onUnsolicitedResponse(int unsolResponse, - void *data, size_t datalen); - - /** - * Class method to add the sap socket to the list of sockets. - * Does nothing if the socket is already present in the list. - * Otherwise, calls the constructor of the parent class(To startlistening) - * and add socket to the socket list. - */ - static void addSocketToList(const char *socketName, RIL_SOCKET_ID socketid, - const RIL_RadioFunctions *uimFuncs); - - /** - * Check if a socket of the given name exists in the socket list. - * - * @param Socket name. - * @return true if exists, false otherwise. - */ - static bool SocketExists(const char *socketName); - - private: - /** - * Constructor. - * - * @param Socket name. - * @param Socket id. - * @param Radio functions. - */ - RilSapSocket(const char *socketName, - RIL_SOCKET_ID socketId, - const RIL_RadioFunctions *inputUimFuncs); - - /** - * Class method that selects the socket on which the onRequestComplete - * is called. - * - * @param Token associated with the request. - * @param Error, if any, while processing the request. - * @param The response payload. - * @param Response payload length. - */ - static void sOnRequestComplete(RIL_Token t, - RIL_Errno e, void *response, size_t responselen); - -#if defined(ANDROID_MULTI_SIM) - /** - * Class method that selects the socket on which the onUnsolicitedResponse - * is called. - * - * @param Message id. - * @param Response data. - * @param Response data length. - * @param Socket id. - */ - static void sOnUnsolicitedResponse(int unsolResponse, const void *data, - size_t datalen, RIL_SOCKET_ID socket_id); -#else - /** - * Class method that selects the socket on which the onUnsolicitedResponse - * is called. - * - * @param Message id. - * @param Response data. - * @param Response data length. - */ - static void sOnUnsolicitedResponse(int unsolResponse, const void *data, - size_t datalen); -#endif -}; - -#endif /*RIL_UIM_SOCKET_H_INCLUDED*/ diff --git a/radio/libril/RilSocket.h b/radio/libril/RilSocket.h deleted file mode 100644 index 53b00c9d..00000000 --- a/radio/libril/RilSocket.h +++ /dev/null @@ -1,70 +0,0 @@ -/* -* Copyright (C) 2014 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. -*/ - -#ifndef RIL_SOCKET_H_INCLUDED -#define RIL_SOCKET_H_INCLUDED -#include <libril/ril_ex.h> -#include "rilSocketQueue.h" -#include <ril_event.h> - -/** - * Abstract socket class representing sockets in rild. - * <p> - * This class performs the following functions : - * <ul> - * <li> Start socket listen. - * <li> Handle socket listen and command callbacks. - * </ul> - */ -class RilSocket { - protected: - - /** - * Socket name. - */ - const char* name; - - /** - * Socket id. - */ - RIL_SOCKET_ID id; - - public: - - /** - * Constructor. - * - * @param Socket name. - * @param Socket id. - */ - RilSocket(const char* socketName, RIL_SOCKET_ID socketId) { - name = socketName; - id = socketId; - } - - /** - * Get socket id. - * - * @return RIL_SOCKET_ID socket id. - */ - RIL_SOCKET_ID getSocketId(void) { - return id; - } - - virtual ~RilSocket(){} -}; - -#endif diff --git a/radio/libril/ril.cpp b/radio/libril/ril.cpp deleted file mode 100644 index 54eda3d9..00000000 --- a/radio/libril/ril.cpp +++ /dev/null @@ -1,1241 +0,0 @@ -/* //device/libs/telephony/ril.cpp -** -** Copyright 2006, 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_TAG "RILC" - -#include <hardware_legacy/power.h> -#include <radio/ril/ril.h> -#include <telephony/ril_cdma_sms.h> -#include <cutils/sockets.h> -#include <telephony/record_stream.h> -#include <utils/Log.h> -#include <utils/SystemClock.h> -#include <pthread.h> -#include <sys/types.h> -#include <sys/limits.h> -#include <sys/system_properties.h> -#include <pwd.h> -#include <stdio.h> -#include <stdlib.h> -#include <stdarg.h> -#include <string.h> -#include <unistd.h> -#include <fcntl.h> -#include <time.h> -#include <errno.h> -#include <assert.h> -#include <ctype.h> -#include <sys/un.h> -#include <assert.h> -#include <netinet/in.h> -#include <cutils/properties.h> -#include <RilSapSocket.h> -#include <ril_service.h> -#include <sap_service.h> - -extern "C" void -RIL_onRequestComplete(RIL_Token t, RIL_Errno e, void *response, size_t responselen); - -extern "C" void -RIL_onRequestAck(RIL_Token t); -namespace android { - -#define PHONE_PROCESS "radio" -#define BLUETOOTH_PROCESS "bluetooth" - -#define ANDROID_WAKE_LOCK_NAME "radio-interface" - -#define ANDROID_WAKE_LOCK_SECS 0 -#define ANDROID_WAKE_LOCK_USECS 200000 - -#define PROPERTY_RIL_IMPL "gsm.version.ril-impl" - -// match with constant in RIL.java -#define MAX_COMMAND_BYTES (8 * 1024) - -// Basically: memset buffers that the client library -// shouldn't be using anymore in an attempt to find -// memory usage issues sooner. -#define MEMSET_FREED 1 - -#define NUM_ELEMS(a) (sizeof (a) / sizeof (a)[0]) - -/* Negative values for private RIL errno's */ -#define RIL_ERRNO_INVALID_RESPONSE (-1) -#define RIL_ERRNO_NO_MEMORY (-12) - -// request, response, and unsolicited msg print macro -#define PRINTBUF_SIZE 8096 - -enum WakeType {DONT_WAKE, WAKE_PARTIAL}; - -typedef struct { - int requestNumber; - int (*responseFunction) (int slotId, int responseType, int token, - RIL_Errno e, void *response, size_t responselen); - WakeType wakeType; -} UnsolResponseInfo; - -typedef struct UserCallbackInfo { - RIL_TimedCallback p_callback; - void *userParam; - struct ril_event event; - struct UserCallbackInfo *p_next; -} UserCallbackInfo; - -extern "C" const char * failCauseToString(RIL_Errno); -extern "C" const char * callStateToString(RIL_CallState); -extern "C" const char * radioStateToString(RIL_RadioState); -extern "C" const char * rilSocketIdToString(RIL_SOCKET_ID socket_id); - -extern "C" -char ril_service_name_base[MAX_SERVICE_NAME_LENGTH] = RIL_SERVICE_NAME_BASE; -extern "C" -char ril_service_name[MAX_SERVICE_NAME_LENGTH] = RIL1_SERVICE_NAME; -/*******************************************************************/ - -RIL_RadioFunctions s_callbacks = {0, NULL, NULL, NULL, NULL, NULL}; -static int s_registerCalled = 0; - -static pthread_t s_tid_dispatch; -static int s_started = 0; - -static int s_fdWakeupRead; -static int s_fdWakeupWrite; - -int s_wakelock_count = 0; - -static struct ril_event s_wakeupfd_event; - -static pthread_mutex_t s_pendingRequestsMutex = PTHREAD_MUTEX_INITIALIZER; -static pthread_mutex_t s_wakeLockCountMutex = PTHREAD_MUTEX_INITIALIZER; -static RequestInfo *s_pendingRequests = NULL; - -#if (SIM_COUNT >= 2) -static pthread_mutex_t s_pendingRequestsMutex_socket2 = PTHREAD_MUTEX_INITIALIZER; -static RequestInfo *s_pendingRequests_socket2 = NULL; -#endif - -#if (SIM_COUNT >= 3) -static pthread_mutex_t s_pendingRequestsMutex_socket3 = PTHREAD_MUTEX_INITIALIZER; -static RequestInfo *s_pendingRequests_socket3 = NULL; -#endif - -#if (SIM_COUNT >= 4) -static pthread_mutex_t s_pendingRequestsMutex_socket4 = PTHREAD_MUTEX_INITIALIZER; -static RequestInfo *s_pendingRequests_socket4 = NULL; -#endif - -static const struct timeval TIMEVAL_WAKE_TIMEOUT = {ANDROID_WAKE_LOCK_SECS,ANDROID_WAKE_LOCK_USECS}; - - -static pthread_mutex_t s_startupMutex = PTHREAD_MUTEX_INITIALIZER; -static pthread_cond_t s_startupCond = PTHREAD_COND_INITIALIZER; - -static UserCallbackInfo *s_last_wake_timeout_info = NULL; - -static void *s_lastNITZTimeData = NULL; -static size_t s_lastNITZTimeDataSize; - -#if RILC_LOG - static char printBuf[PRINTBUF_SIZE]; -#endif - -/*******************************************************************/ -static void grabPartialWakeLock(); -void releaseWakeLock(); -static void wakeTimeoutCallback(void *); - -#ifdef RIL_SHLIB -#if defined(ANDROID_MULTI_SIM) -extern "C" void RIL_onUnsolicitedResponse(int unsolResponse, const void *data, - size_t datalen, RIL_SOCKET_ID socket_id); -#else -extern "C" void RIL_onUnsolicitedResponse(int unsolResponse, const void *data, - size_t datalen); -#endif -#endif - -#if defined(ANDROID_MULTI_SIM) -#define RIL_UNSOL_RESPONSE(a, b, c, d) RIL_onUnsolicitedResponse((a), (b), (c), (d)) -#else -#define RIL_UNSOL_RESPONSE(a, b, c, d) RIL_onUnsolicitedResponse((a), (b), (c)) -#endif - -static UserCallbackInfo * internalRequestTimedCallback - (RIL_TimedCallback callback, void *param, - const struct timeval *relativeTime); - -/** Index == requestNumber */ -static CommandInfo s_commands[] = { -#include "ril_commands.h" -}; - -static UnsolResponseInfo s_unsolResponses[] = { -#include "ril_unsol_commands.h" -}; - -char * RIL_getServiceName() { - return ril_service_name; -} - -RequestInfo * -addRequestToList(int serial, int slotId, int request) { - RequestInfo *pRI; - int ret; - RIL_SOCKET_ID socket_id = (RIL_SOCKET_ID) slotId; - /* Hook for current context */ - /* pendingRequestsMutextHook refer to &s_pendingRequestsMutex */ - pthread_mutex_t* pendingRequestsMutexHook = &s_pendingRequestsMutex; - /* pendingRequestsHook refer to &s_pendingRequests */ - RequestInfo** pendingRequestsHook = &s_pendingRequests; - -#if (SIM_COUNT >= 2) - if (socket_id == RIL_SOCKET_2) { - pendingRequestsMutexHook = &s_pendingRequestsMutex_socket2; - pendingRequestsHook = &s_pendingRequests_socket2; - } -#if (SIM_COUNT >= 3) - else if (socket_id == RIL_SOCKET_3) { - pendingRequestsMutexHook = &s_pendingRequestsMutex_socket3; - pendingRequestsHook = &s_pendingRequests_socket3; - } -#endif -#if (SIM_COUNT >= 4) - else if (socket_id == RIL_SOCKET_4) { - pendingRequestsMutexHook = &s_pendingRequestsMutex_socket4; - pendingRequestsHook = &s_pendingRequests_socket4; - } -#endif -#endif - - pRI = (RequestInfo *)calloc(1, sizeof(RequestInfo)); - if (pRI == NULL) { - RLOGE("Memory allocation failed for request %s", requestToString(request)); - return NULL; - } - - pRI->token = serial; - pRI->pCI = &(s_commands[request]); - pRI->socket_id = socket_id; - - ret = pthread_mutex_lock(pendingRequestsMutexHook); - assert (ret == 0); - - pRI->p_next = *pendingRequestsHook; - *pendingRequestsHook = pRI; - - ret = pthread_mutex_unlock(pendingRequestsMutexHook); - assert (ret == 0); - - return pRI; -} - -static void triggerEvLoop() { - int ret; - if (!pthread_equal(pthread_self(), s_tid_dispatch)) { - /* trigger event loop to wakeup. No reason to do this, - * if we're in the event loop thread */ - do { - ret = write (s_fdWakeupWrite, " ", 1); - } while (ret < 0 && errno == EINTR); - } -} - -static void rilEventAddWakeup(struct ril_event *ev) { - ril_event_add(ev); - triggerEvLoop(); -} - -/** - * A write on the wakeup fd is done just to pop us out of select() - * We empty the buffer here and then ril_event will reset the timers on the - * way back down - */ -static void processWakeupCallback(int fd, short flags, void *param) { - char buff[16]; - int ret; - - RLOGV("processWakeupCallback"); - - /* empty our wakeup socket out */ - do { - ret = read(s_fdWakeupRead, &buff, sizeof(buff)); - } while (ret > 0 || (ret < 0 && errno == EINTR)); -} - -static void resendLastNITZTimeData(RIL_SOCKET_ID socket_id) { - if (s_lastNITZTimeData != NULL) { - int responseType = (s_callbacks.version >= 13) - ? RESPONSE_UNSOLICITED_ACK_EXP - : RESPONSE_UNSOLICITED; - // acquire read lock for the service before calling nitzTimeReceivedInd() since it reads - // nitzTimeReceived in ril_service - pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock( - (int) socket_id); - int rwlockRet = pthread_rwlock_rdlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - - int ret = radio::nitzTimeReceivedInd( - (int)socket_id, responseType, 0, - RIL_E_SUCCESS, s_lastNITZTimeData, s_lastNITZTimeDataSize); - if (ret == 0) { - free(s_lastNITZTimeData); - s_lastNITZTimeData = NULL; - } - - rwlockRet = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - } -} - -void onNewCommandConnect(RIL_SOCKET_ID socket_id) { - // Inform we are connected and the ril version - int rilVer = s_callbacks.version; - RIL_UNSOL_RESPONSE(RIL_UNSOL_RIL_CONNECTED, - &rilVer, sizeof(rilVer), socket_id); - - // implicit radio state changed - RIL_UNSOL_RESPONSE(RIL_UNSOL_RESPONSE_RADIO_STATE_CHANGED, - NULL, 0, socket_id); - - // Send last NITZ time data, in case it was missed - if (s_lastNITZTimeData != NULL) { - resendLastNITZTimeData(socket_id); - } - - // Get version string - if (s_callbacks.getVersion != NULL) { - const char *version; - version = s_callbacks.getVersion(); - RLOGI("RIL Daemon version: %s\n", version); - - property_set(PROPERTY_RIL_IMPL, version); - } else { - RLOGI("RIL Daemon version: unavailable\n"); - property_set(PROPERTY_RIL_IMPL, "unavailable"); - } - -} - -static void userTimerCallback (int fd, short flags, void *param) { - UserCallbackInfo *p_info; - - p_info = (UserCallbackInfo *)param; - - p_info->p_callback(p_info->userParam); - - - // FIXME generalize this...there should be a cancel mechanism - if (s_last_wake_timeout_info != NULL && s_last_wake_timeout_info == p_info) { - s_last_wake_timeout_info = NULL; - } - - free(p_info); -} - - -static void * -eventLoop(void *param) { - int ret; - int filedes[2]; - - ril_event_init(); - - pthread_mutex_lock(&s_startupMutex); - - s_started = 1; - pthread_cond_broadcast(&s_startupCond); - - pthread_mutex_unlock(&s_startupMutex); - - ret = pipe(filedes); - - if (ret < 0) { - RLOGE("Error in pipe() errno:%d", errno); - return NULL; - } - - s_fdWakeupRead = filedes[0]; - s_fdWakeupWrite = filedes[1]; - - fcntl(s_fdWakeupRead, F_SETFL, O_NONBLOCK); - - ril_event_set (&s_wakeupfd_event, s_fdWakeupRead, true, - processWakeupCallback, NULL); - - rilEventAddWakeup (&s_wakeupfd_event); - - // Only returns on error - ril_event_loop(); - RLOGE ("error in event_loop_base errno:%d", errno); - // kill self to restart on error - kill(0, SIGKILL); - - return NULL; -} - -extern "C" void -RIL_startEventLoop(void) { - /* spin up eventLoop thread and wait for it to get started */ - s_started = 0; - pthread_mutex_lock(&s_startupMutex); - - pthread_attr_t attr; - pthread_attr_init(&attr); - pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); - - int result = pthread_create(&s_tid_dispatch, &attr, eventLoop, NULL); - if (result != 0) { - RLOGE("Failed to create dispatch thread: %s", strerror(result)); - goto done; - } - - while (s_started == 0) { - pthread_cond_wait(&s_startupCond, &s_startupMutex); - } - -done: - pthread_mutex_unlock(&s_startupMutex); -} - -// Used for testing purpose only. -extern "C" void RIL_setcallbacks (const RIL_RadioFunctions *callbacks) { - memcpy(&s_callbacks, callbacks, sizeof (RIL_RadioFunctions)); -} - -extern "C" void -RIL_register (const RIL_RadioFunctions *callbacks) { - RLOGI("SIM_COUNT: %d", SIM_COUNT); - - if (callbacks == NULL) { - RLOGE("RIL_register: RIL_RadioFunctions * null"); - return; - } - if (callbacks->version < RIL_VERSION_MIN) { - RLOGE("RIL_register: version %d is to old, min version is %d", - callbacks->version, RIL_VERSION_MIN); - return; - } - - RLOGE("RIL_register: RIL version %d", callbacks->version); - - if (s_registerCalled > 0) { - RLOGE("RIL_register has been called more than once. " - "Subsequent call ignored"); - return; - } - - memcpy(&s_callbacks, callbacks, sizeof (RIL_RadioFunctions)); - - s_registerCalled = 1; - - RLOGI("s_registerCalled flag set, %d", s_started); - // Little self-check - - for (int i = 0; i < (int)NUM_ELEMS(s_commands); i++) { - assert(i == s_commands[i].requestNumber); - } - - for (int i = 0; i < (int)NUM_ELEMS(s_unsolResponses); i++) { - assert(i + RIL_UNSOL_RESPONSE_BASE - == s_unsolResponses[i].requestNumber); - } - - radio::registerService(&s_callbacks, s_commands); - RLOGI("RILHIDL called registerService"); - -} - -extern "C" void -RIL_register_socket (const RIL_RadioFunctions *(*Init)(const struct RIL_Env *, int, char **), - RIL_SOCKET_TYPE socketType, int argc, char **argv) { - - const RIL_RadioFunctions* UimFuncs = NULL; - - if(Init) { - UimFuncs = Init(&RilSapSocket::uimRilEnv, argc, argv); - - switch(socketType) { - case RIL_SAP_SOCKET: - RilSapSocket::initSapSocket(RIL1_SERVICE_NAME, UimFuncs); - -#if (SIM_COUNT >= 2) - RilSapSocket::initSapSocket(RIL2_SERVICE_NAME, UimFuncs); -#endif - -#if (SIM_COUNT >= 3) - RilSapSocket::initSapSocket(RIL3_SERVICE_NAME, UimFuncs); -#endif - -#if (SIM_COUNT >= 4) - RilSapSocket::initSapSocket(RIL4_SERVICE_NAME, UimFuncs); -#endif - break; - default:; - } - - RLOGI("RIL_register_socket: calling registerService"); - sap::registerService(UimFuncs); - } -} - -// Check and remove RequestInfo if its a response and not just ack sent back -static int -checkAndDequeueRequestInfoIfAck(struct RequestInfo *pRI, bool isAck) { - int ret = 0; - /* Hook for current context - pendingRequestsMutextHook refer to &s_pendingRequestsMutex */ - pthread_mutex_t* pendingRequestsMutexHook = &s_pendingRequestsMutex; - /* pendingRequestsHook refer to &s_pendingRequests */ - RequestInfo ** pendingRequestsHook = &s_pendingRequests; - - if (pRI == NULL) { - return 0; - } - -#if (SIM_COUNT >= 2) - if (pRI->socket_id == RIL_SOCKET_2) { - pendingRequestsMutexHook = &s_pendingRequestsMutex_socket2; - pendingRequestsHook = &s_pendingRequests_socket2; - } -#if (SIM_COUNT >= 3) - if (pRI->socket_id == RIL_SOCKET_3) { - pendingRequestsMutexHook = &s_pendingRequestsMutex_socket3; - pendingRequestsHook = &s_pendingRequests_socket3; - } -#endif -#if (SIM_COUNT >= 4) - if (pRI->socket_id == RIL_SOCKET_4) { - pendingRequestsMutexHook = &s_pendingRequestsMutex_socket4; - pendingRequestsHook = &s_pendingRequests_socket4; - } -#endif -#endif - pthread_mutex_lock(pendingRequestsMutexHook); - - for(RequestInfo **ppCur = pendingRequestsHook - ; *ppCur != NULL - ; ppCur = &((*ppCur)->p_next) - ) { - if (pRI == *ppCur) { - ret = 1; - if (isAck) { // Async ack - if (pRI->wasAckSent == 1) { - RLOGD("Ack was already sent for %s", requestToString(pRI->pCI->requestNumber)); - } else { - pRI->wasAckSent = 1; - } - } else { - *ppCur = (*ppCur)->p_next; - } - break; - } - } - - pthread_mutex_unlock(pendingRequestsMutexHook); - - return ret; -} - -extern "C" void -RIL_onRequestAck(RIL_Token t) { - RequestInfo *pRI; - - RIL_SOCKET_ID socket_id = RIL_SOCKET_1; - - pRI = (RequestInfo *)t; - - if (!checkAndDequeueRequestInfoIfAck(pRI, true)) { - RLOGE ("RIL_onRequestAck: invalid RIL_Token"); - return; - } - - socket_id = pRI->socket_id; - -#if VDBG - RLOGD("Request Ack, %s", rilSocketIdToString(socket_id)); -#endif - - appendPrintBuf("Ack [%04d]< %s", pRI->token, requestToString(pRI->pCI->requestNumber)); - - if (pRI->cancelled == 0) { - pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock( - (int) socket_id); - int rwlockRet = pthread_rwlock_rdlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - - radio::acknowledgeRequest((int) socket_id, pRI->token); - - rwlockRet = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - } -} -extern "C" void -RIL_onRequestComplete(RIL_Token t, RIL_Errno e, void *response, size_t responselen) { - RequestInfo *pRI; - int ret; - RIL_SOCKET_ID socket_id = RIL_SOCKET_1; - - pRI = (RequestInfo *)t; - - if (!checkAndDequeueRequestInfoIfAck(pRI, false)) { - RLOGE ("RIL_onRequestComplete: invalid RIL_Token"); - return; - } - - socket_id = pRI->socket_id; -#if VDBG - RLOGD("RequestComplete, %s", rilSocketIdToString(socket_id)); -#endif - - if (pRI->local > 0) { - // Locally issued command...void only! - // response does not go back up the command socket - RLOGD("C[locl]< %s", requestToString(pRI->pCI->requestNumber)); - - free(pRI); - return; - } - - appendPrintBuf("[%04d]< %s", - pRI->token, requestToString(pRI->pCI->requestNumber)); - - if (pRI->cancelled == 0) { - int responseType; - if (s_callbacks.version >= 13 && pRI->wasAckSent == 1) { - // If ack was already sent, then this call is an asynchronous response. So we need to - // send id indicating that we expect an ack from RIL.java as we acquire wakelock here. - responseType = RESPONSE_SOLICITED_ACK_EXP; - grabPartialWakeLock(); - } else { - responseType = RESPONSE_SOLICITED; - } - - // there is a response payload, no matter success or not. -#if VDBG - RLOGE ("Calling responseFunction() for token %d", pRI->token); -#endif - - pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock((int) socket_id); - int rwlockRet = pthread_rwlock_rdlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - - ret = pRI->pCI->responseFunction((int) socket_id, - responseType, pRI->token, e, response, responselen); - - rwlockRet = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - } - free(pRI); -} - -static void -grabPartialWakeLock() { - if (s_callbacks.version >= 13) { - int ret; - ret = pthread_mutex_lock(&s_wakeLockCountMutex); - assert(ret == 0); - acquire_wake_lock(PARTIAL_WAKE_LOCK, ANDROID_WAKE_LOCK_NAME); - - UserCallbackInfo *p_info = - internalRequestTimedCallback(wakeTimeoutCallback, NULL, &TIMEVAL_WAKE_TIMEOUT); - if (p_info == NULL) { - release_wake_lock(ANDROID_WAKE_LOCK_NAME); - } else { - s_wakelock_count++; - if (s_last_wake_timeout_info != NULL) { - s_last_wake_timeout_info->userParam = (void *)1; - } - s_last_wake_timeout_info = p_info; - } - ret = pthread_mutex_unlock(&s_wakeLockCountMutex); - assert(ret == 0); - } else { - acquire_wake_lock(PARTIAL_WAKE_LOCK, ANDROID_WAKE_LOCK_NAME); - } -} - -void -releaseWakeLock() { - if (s_callbacks.version >= 13) { - int ret; - ret = pthread_mutex_lock(&s_wakeLockCountMutex); - assert(ret == 0); - - if (s_wakelock_count > 1) { - s_wakelock_count--; - } else { - s_wakelock_count = 0; - release_wake_lock(ANDROID_WAKE_LOCK_NAME); - if (s_last_wake_timeout_info != NULL) { - s_last_wake_timeout_info->userParam = (void *)1; - } - } - - ret = pthread_mutex_unlock(&s_wakeLockCountMutex); - assert(ret == 0); - } else { - release_wake_lock(ANDROID_WAKE_LOCK_NAME); - } -} - -/** - * Timer callback to put us back to sleep before the default timeout - */ -static void -wakeTimeoutCallback (void *param) { - // We're using "param != NULL" as a cancellation mechanism - if (s_callbacks.version >= 13) { - if (param == NULL) { - int ret; - ret = pthread_mutex_lock(&s_wakeLockCountMutex); - assert(ret == 0); - s_wakelock_count = 0; - release_wake_lock(ANDROID_WAKE_LOCK_NAME); - ret = pthread_mutex_unlock(&s_wakeLockCountMutex); - assert(ret == 0); - } - } else { - if (param == NULL) { - releaseWakeLock(); - } - } -} - -#if defined(ANDROID_MULTI_SIM) -extern "C" -void RIL_onUnsolicitedResponse(int unsolResponse, const void *data, - size_t datalen, RIL_SOCKET_ID socket_id) -#else -extern "C" -void RIL_onUnsolicitedResponse(int unsolResponse, const void *data, - size_t datalen) -#endif -{ - int unsolResponseIndex; - int ret; - bool shouldScheduleTimeout = false; - RIL_SOCKET_ID soc_id = RIL_SOCKET_1; - -#if defined(ANDROID_MULTI_SIM) - soc_id = socket_id; -#endif - - - if (s_registerCalled == 0) { - // Ignore RIL_onUnsolicitedResponse before RIL_register - RLOGW("RIL_onUnsolicitedResponse called before RIL_register"); - return; - } - - unsolResponseIndex = unsolResponse - RIL_UNSOL_RESPONSE_BASE; - - if ((unsolResponseIndex < 0) - || (unsolResponseIndex >= (int32_t)NUM_ELEMS(s_unsolResponses))) { - RLOGE("unsupported unsolicited response code %d", unsolResponse); - return; - } - - // Grab a wake lock if needed for this reponse, - // as we exit we'll either release it immediately - // or set a timer to release it later. - switch (s_unsolResponses[unsolResponseIndex].wakeType) { - case WAKE_PARTIAL: - grabPartialWakeLock(); - shouldScheduleTimeout = true; - break; - - case DONT_WAKE: - default: - // No wake lock is grabed so don't set timeout - shouldScheduleTimeout = false; - break; - } - - appendPrintBuf("[UNSL]< %s", requestToString(unsolResponse)); - - int responseType; - if (s_callbacks.version >= 13 - && s_unsolResponses[unsolResponseIndex].wakeType == WAKE_PARTIAL) { - responseType = RESPONSE_UNSOLICITED_ACK_EXP; - } else { - responseType = RESPONSE_UNSOLICITED; - } - - pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock((int) soc_id); - int rwlockRet; - - if (unsolResponse == RIL_UNSOL_NITZ_TIME_RECEIVED) { - // get a write lock in caes of NITZ since setNitzTimeReceived() is called - rwlockRet = pthread_rwlock_wrlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - radio::setNitzTimeReceived((int) soc_id, android::elapsedRealtime()); - } else { - rwlockRet = pthread_rwlock_rdlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - } - - if (s_unsolResponses[unsolResponseIndex].responseFunction) { - ret = s_unsolResponses[unsolResponseIndex].responseFunction( - (int) soc_id, responseType, 0, RIL_E_SUCCESS, const_cast<void*>(data), - datalen); - } - - rwlockRet = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(rwlockRet == 0); - - if (s_callbacks.version < 13) { - if (shouldScheduleTimeout) { - UserCallbackInfo *p_info = internalRequestTimedCallback(wakeTimeoutCallback, NULL, - &TIMEVAL_WAKE_TIMEOUT); - - if (p_info == NULL) { - goto error_exit; - } else { - // Cancel the previous request - if (s_last_wake_timeout_info != NULL) { - s_last_wake_timeout_info->userParam = (void *)1; - } - s_last_wake_timeout_info = p_info; - } - } - } - -#if VDBG - RLOGI("%s UNSOLICITED: %s length:%zu", rilSocketIdToString(soc_id), - requestToString(unsolResponse), datalen); -#endif - - if (ret != 0 && unsolResponse == RIL_UNSOL_NITZ_TIME_RECEIVED) { - // Unfortunately, NITZ time is not poll/update like everything - // else in the system. So, if the upstream client isn't connected, - // keep a copy of the last NITZ response (with receive time noted - // above) around so we can deliver it when it is connected - - if (s_lastNITZTimeData != NULL) { - free(s_lastNITZTimeData); - s_lastNITZTimeData = NULL; - } - - s_lastNITZTimeData = calloc(datalen, 1); - if (s_lastNITZTimeData == NULL) { - RLOGE("Memory allocation failed in RIL_onUnsolicitedResponse"); - goto error_exit; - } - s_lastNITZTimeDataSize = datalen; - memcpy(s_lastNITZTimeData, data, datalen); - } - - // Normal exit - return; - -error_exit: - if (shouldScheduleTimeout) { - releaseWakeLock(); - } -} - -/** FIXME generalize this if you track UserCAllbackInfo, clear it - when the callback occurs -*/ -static UserCallbackInfo * -internalRequestTimedCallback (RIL_TimedCallback callback, void *param, - const struct timeval *relativeTime) -{ - struct timeval myRelativeTime; - UserCallbackInfo *p_info; - - p_info = (UserCallbackInfo *) calloc(1, sizeof(UserCallbackInfo)); - if (p_info == NULL) { - RLOGE("Memory allocation failed in internalRequestTimedCallback"); - return p_info; - - } - - p_info->p_callback = callback; - p_info->userParam = param; - - if (relativeTime == NULL) { - /* treat null parameter as a 0 relative time */ - memset (&myRelativeTime, 0, sizeof(myRelativeTime)); - } else { - /* FIXME I think event_add's tv param is really const anyway */ - memcpy (&myRelativeTime, relativeTime, sizeof(myRelativeTime)); - } - - ril_event_set(&(p_info->event), -1, false, userTimerCallback, p_info); - - ril_timer_add(&(p_info->event), &myRelativeTime); - - triggerEvLoop(); - return p_info; -} - - -extern "C" void -RIL_requestTimedCallback (RIL_TimedCallback callback, void *param, - const struct timeval *relativeTime) { - internalRequestTimedCallback (callback, param, relativeTime); -} - -const char * -failCauseToString(RIL_Errno e) { - switch(e) { - case RIL_E_SUCCESS: return "E_SUCCESS"; - case RIL_E_RADIO_NOT_AVAILABLE: return "E_RADIO_NOT_AVAILABLE"; - case RIL_E_GENERIC_FAILURE: return "E_GENERIC_FAILURE"; - case RIL_E_PASSWORD_INCORRECT: return "E_PASSWORD_INCORRECT"; - case RIL_E_SIM_PIN2: return "E_SIM_PIN2"; - case RIL_E_SIM_PUK2: return "E_SIM_PUK2"; - case RIL_E_REQUEST_NOT_SUPPORTED: return "E_REQUEST_NOT_SUPPORTED"; - case RIL_E_CANCELLED: return "E_CANCELLED"; - case RIL_E_OP_NOT_ALLOWED_DURING_VOICE_CALL: return "E_OP_NOT_ALLOWED_DURING_VOICE_CALL"; - case RIL_E_OP_NOT_ALLOWED_BEFORE_REG_TO_NW: return "E_OP_NOT_ALLOWED_BEFORE_REG_TO_NW"; - case RIL_E_SMS_SEND_FAIL_RETRY: return "E_SMS_SEND_FAIL_RETRY"; - case RIL_E_SIM_ABSENT:return "E_SIM_ABSENT"; - case RIL_E_ILLEGAL_SIM_OR_ME:return "E_ILLEGAL_SIM_OR_ME"; -#ifdef FEATURE_MULTIMODE_ANDROID - case RIL_E_SUBSCRIPTION_NOT_AVAILABLE:return "E_SUBSCRIPTION_NOT_AVAILABLE"; - case RIL_E_MODE_NOT_SUPPORTED:return "E_MODE_NOT_SUPPORTED"; -#endif - case RIL_E_FDN_CHECK_FAILURE: return "E_FDN_CHECK_FAILURE"; - case RIL_E_MISSING_RESOURCE: return "E_MISSING_RESOURCE"; - case RIL_E_NO_SUCH_ELEMENT: return "E_NO_SUCH_ELEMENT"; - case RIL_E_DIAL_MODIFIED_TO_USSD: return "E_DIAL_MODIFIED_TO_USSD"; - case RIL_E_DIAL_MODIFIED_TO_SS: return "E_DIAL_MODIFIED_TO_SS"; - case RIL_E_DIAL_MODIFIED_TO_DIAL: return "E_DIAL_MODIFIED_TO_DIAL"; - case RIL_E_USSD_MODIFIED_TO_DIAL: return "E_USSD_MODIFIED_TO_DIAL"; - case RIL_E_USSD_MODIFIED_TO_SS: return "E_USSD_MODIFIED_TO_SS"; - case RIL_E_USSD_MODIFIED_TO_USSD: return "E_USSD_MODIFIED_TO_USSD"; - case RIL_E_SS_MODIFIED_TO_DIAL: return "E_SS_MODIFIED_TO_DIAL"; - case RIL_E_SS_MODIFIED_TO_USSD: return "E_SS_MODIFIED_TO_USSD"; - case RIL_E_SUBSCRIPTION_NOT_SUPPORTED: return "E_SUBSCRIPTION_NOT_SUPPORTED"; - case RIL_E_SS_MODIFIED_TO_SS: return "E_SS_MODIFIED_TO_SS"; - case RIL_E_LCE_NOT_SUPPORTED: return "E_LCE_NOT_SUPPORTED"; - case RIL_E_NO_MEMORY: return "E_NO_MEMORY"; - case RIL_E_INTERNAL_ERR: return "E_INTERNAL_ERR"; - case RIL_E_SYSTEM_ERR: return "E_SYSTEM_ERR"; - case RIL_E_MODEM_ERR: return "E_MODEM_ERR"; - case RIL_E_INVALID_STATE: return "E_INVALID_STATE"; - case RIL_E_NO_RESOURCES: return "E_NO_RESOURCES"; - case RIL_E_SIM_ERR: return "E_SIM_ERR"; - case RIL_E_INVALID_ARGUMENTS: return "E_INVALID_ARGUMENTS"; - case RIL_E_INVALID_SIM_STATE: return "E_INVALID_SIM_STATE"; - case RIL_E_INVALID_MODEM_STATE: return "E_INVALID_MODEM_STATE"; - case RIL_E_INVALID_CALL_ID: return "E_INVALID_CALL_ID"; - case RIL_E_NO_SMS_TO_ACK: return "E_NO_SMS_TO_ACK"; - case RIL_E_NETWORK_ERR: return "E_NETWORK_ERR"; - case RIL_E_REQUEST_RATE_LIMITED: return "E_REQUEST_RATE_LIMITED"; - case RIL_E_SIM_BUSY: return "E_SIM_BUSY"; - case RIL_E_SIM_FULL: return "E_SIM_FULL"; - case RIL_E_NETWORK_REJECT: return "E_NETWORK_REJECT"; - case RIL_E_OPERATION_NOT_ALLOWED: return "E_OPERATION_NOT_ALLOWED"; - case RIL_E_EMPTY_RECORD: return "E_EMPTY_RECORD"; - case RIL_E_INVALID_SMS_FORMAT: return "E_INVALID_SMS_FORMAT"; - case RIL_E_ENCODING_ERR: return "E_ENCODING_ERR"; - case RIL_E_INVALID_SMSC_ADDRESS: return "E_INVALID_SMSC_ADDRESS"; - case RIL_E_NO_SUCH_ENTRY: return "E_NO_SUCH_ENTRY"; - case RIL_E_NETWORK_NOT_READY: return "E_NETWORK_NOT_READY"; - case RIL_E_NOT_PROVISIONED: return "E_NOT_PROVISIONED"; - case RIL_E_NO_SUBSCRIPTION: return "E_NO_SUBSCRIPTION"; - case RIL_E_NO_NETWORK_FOUND: return "E_NO_NETWORK_FOUND"; - case RIL_E_DEVICE_IN_USE: return "E_DEVICE_IN_USE"; - case RIL_E_ABORTED: return "E_ABORTED"; - case RIL_E_INVALID_RESPONSE: return "INVALID_RESPONSE"; - case RIL_E_OEM_ERROR_1: return "E_OEM_ERROR_1"; - case RIL_E_OEM_ERROR_2: return "E_OEM_ERROR_2"; - case RIL_E_OEM_ERROR_3: return "E_OEM_ERROR_3"; - case RIL_E_OEM_ERROR_4: return "E_OEM_ERROR_4"; - case RIL_E_OEM_ERROR_5: return "E_OEM_ERROR_5"; - case RIL_E_OEM_ERROR_6: return "E_OEM_ERROR_6"; - case RIL_E_OEM_ERROR_7: return "E_OEM_ERROR_7"; - case RIL_E_OEM_ERROR_8: return "E_OEM_ERROR_8"; - case RIL_E_OEM_ERROR_9: return "E_OEM_ERROR_9"; - case RIL_E_OEM_ERROR_10: return "E_OEM_ERROR_10"; - case RIL_E_OEM_ERROR_11: return "E_OEM_ERROR_11"; - case RIL_E_OEM_ERROR_12: return "E_OEM_ERROR_12"; - case RIL_E_OEM_ERROR_13: return "E_OEM_ERROR_13"; - case RIL_E_OEM_ERROR_14: return "E_OEM_ERROR_14"; - case RIL_E_OEM_ERROR_15: return "E_OEM_ERROR_15"; - case RIL_E_OEM_ERROR_16: return "E_OEM_ERROR_16"; - case RIL_E_OEM_ERROR_17: return "E_OEM_ERROR_17"; - case RIL_E_OEM_ERROR_18: return "E_OEM_ERROR_18"; - case RIL_E_OEM_ERROR_19: return "E_OEM_ERROR_19"; - case RIL_E_OEM_ERROR_20: return "E_OEM_ERROR_20"; - case RIL_E_OEM_ERROR_21: return "E_OEM_ERROR_21"; - case RIL_E_OEM_ERROR_22: return "E_OEM_ERROR_22"; - case RIL_E_OEM_ERROR_23: return "E_OEM_ERROR_23"; - case RIL_E_OEM_ERROR_24: return "E_OEM_ERROR_24"; - case RIL_E_OEM_ERROR_25: return "E_OEM_ERROR_25"; - default: return "<unknown error>"; - } -} - -const char * -radioStateToString(RIL_RadioState s) { - switch(s) { - case RADIO_STATE_OFF: return "RADIO_OFF"; - case RADIO_STATE_UNAVAILABLE: return "RADIO_UNAVAILABLE"; - case RADIO_STATE_ON:return"RADIO_ON"; - default: return "<unknown state>"; - } -} - -const char * -callStateToString(RIL_CallState s) { - switch(s) { - case RIL_CALL_ACTIVE : return "ACTIVE"; - case RIL_CALL_HOLDING: return "HOLDING"; - case RIL_CALL_DIALING: return "DIALING"; - case RIL_CALL_ALERTING: return "ALERTING"; - case RIL_CALL_INCOMING: return "INCOMING"; - case RIL_CALL_WAITING: return "WAITING"; - default: return "<unknown state>"; - } -} - -const char * -requestToString(int request) { -/* - cat libs/telephony/ril_commands.h \ - | egrep "^ *{RIL_" \ - | sed -re 's/\{RIL_([^,]+),[^,]+,([^}]+).+/case RIL_\1: return "\1";/' - - - cat libs/telephony/ril_unsol_commands.h \ - | egrep "^ *{RIL_" \ - | sed -re 's/\{RIL_([^,]+),([^}]+).+/case RIL_\1: return "\1";/' - -*/ - switch(request) { - case RIL_REQUEST_GET_SIM_STATUS: return "GET_SIM_STATUS"; - case RIL_REQUEST_ENTER_SIM_PIN: return "ENTER_SIM_PIN"; - case RIL_REQUEST_ENTER_SIM_PUK: return "ENTER_SIM_PUK"; - case RIL_REQUEST_ENTER_SIM_PIN2: return "ENTER_SIM_PIN2"; - case RIL_REQUEST_ENTER_SIM_PUK2: return "ENTER_SIM_PUK2"; - case RIL_REQUEST_CHANGE_SIM_PIN: return "CHANGE_SIM_PIN"; - case RIL_REQUEST_CHANGE_SIM_PIN2: return "CHANGE_SIM_PIN2"; - case RIL_REQUEST_ENTER_NETWORK_DEPERSONALIZATION: return "ENTER_NETWORK_DEPERSONALIZATION"; - case RIL_REQUEST_GET_CURRENT_CALLS: return "GET_CURRENT_CALLS"; - case RIL_REQUEST_DIAL: return "DIAL"; - case RIL_REQUEST_GET_IMSI: return "GET_IMSI"; - case RIL_REQUEST_HANGUP: return "HANGUP"; - case RIL_REQUEST_HANGUP_WAITING_OR_BACKGROUND: return "HANGUP_WAITING_OR_BACKGROUND"; - case RIL_REQUEST_HANGUP_FOREGROUND_RESUME_BACKGROUND: return "HANGUP_FOREGROUND_RESUME_BACKGROUND"; - case RIL_REQUEST_SWITCH_WAITING_OR_HOLDING_AND_ACTIVE: return "SWITCH_WAITING_OR_HOLDING_AND_ACTIVE"; - case RIL_REQUEST_CONFERENCE: return "CONFERENCE"; - case RIL_REQUEST_UDUB: return "UDUB"; - case RIL_REQUEST_LAST_CALL_FAIL_CAUSE: return "LAST_CALL_FAIL_CAUSE"; - case RIL_REQUEST_SIGNAL_STRENGTH: return "SIGNAL_STRENGTH"; - case RIL_REQUEST_VOICE_REGISTRATION_STATE: return "VOICE_REGISTRATION_STATE"; - case RIL_REQUEST_DATA_REGISTRATION_STATE: return "DATA_REGISTRATION_STATE"; - case RIL_REQUEST_OPERATOR: return "OPERATOR"; - case RIL_REQUEST_RADIO_POWER: return "RADIO_POWER"; - case RIL_REQUEST_DTMF: return "DTMF"; - case RIL_REQUEST_SEND_SMS: return "SEND_SMS"; - case RIL_REQUEST_SEND_SMS_EXPECT_MORE: return "SEND_SMS_EXPECT_MORE"; - case RIL_REQUEST_SETUP_DATA_CALL: return "SETUP_DATA_CALL"; - case RIL_REQUEST_SIM_IO: return "SIM_IO"; - case RIL_REQUEST_SEND_USSD: return "SEND_USSD"; - case RIL_REQUEST_CANCEL_USSD: return "CANCEL_USSD"; - case RIL_REQUEST_GET_CLIR: return "GET_CLIR"; - case RIL_REQUEST_SET_CLIR: return "SET_CLIR"; - case RIL_REQUEST_QUERY_CALL_FORWARD_STATUS: return "QUERY_CALL_FORWARD_STATUS"; - case RIL_REQUEST_SET_CALL_FORWARD: return "SET_CALL_FORWARD"; - case RIL_REQUEST_QUERY_CALL_WAITING: return "QUERY_CALL_WAITING"; - case RIL_REQUEST_SET_CALL_WAITING: return "SET_CALL_WAITING"; - case RIL_REQUEST_SMS_ACKNOWLEDGE: return "SMS_ACKNOWLEDGE"; - case RIL_REQUEST_GET_IMEI: return "GET_IMEI"; - case RIL_REQUEST_GET_IMEISV: return "GET_IMEISV"; - case RIL_REQUEST_ANSWER: return "ANSWER"; - case RIL_REQUEST_DEACTIVATE_DATA_CALL: return "DEACTIVATE_DATA_CALL"; - case RIL_REQUEST_QUERY_FACILITY_LOCK: return "QUERY_FACILITY_LOCK"; - case RIL_REQUEST_SET_FACILITY_LOCK: return "SET_FACILITY_LOCK"; - case RIL_REQUEST_CHANGE_BARRING_PASSWORD: return "CHANGE_BARRING_PASSWORD"; - case RIL_REQUEST_QUERY_NETWORK_SELECTION_MODE: return "QUERY_NETWORK_SELECTION_MODE"; - case RIL_REQUEST_SET_NETWORK_SELECTION_AUTOMATIC: return "SET_NETWORK_SELECTION_AUTOMATIC"; - case RIL_REQUEST_SET_NETWORK_SELECTION_MANUAL: return "SET_NETWORK_SELECTION_MANUAL"; - case RIL_REQUEST_QUERY_AVAILABLE_NETWORKS: return "QUERY_AVAILABLE_NETWORKS"; - case RIL_REQUEST_DTMF_START: return "DTMF_START"; - case RIL_REQUEST_DTMF_STOP: return "DTMF_STOP"; - case RIL_REQUEST_BASEBAND_VERSION: return "BASEBAND_VERSION"; - case RIL_REQUEST_SEPARATE_CONNECTION: return "SEPARATE_CONNECTION"; - case RIL_REQUEST_SET_MUTE: return "SET_MUTE"; - case RIL_REQUEST_GET_MUTE: return "GET_MUTE"; - case RIL_REQUEST_QUERY_CLIP: return "QUERY_CLIP"; - case RIL_REQUEST_LAST_DATA_CALL_FAIL_CAUSE: return "LAST_DATA_CALL_FAIL_CAUSE"; - case RIL_REQUEST_DATA_CALL_LIST: return "DATA_CALL_LIST"; - case RIL_REQUEST_RESET_RADIO: return "RESET_RADIO"; - case RIL_REQUEST_OEM_HOOK_RAW: return "OEM_HOOK_RAW"; - case RIL_REQUEST_OEM_HOOK_STRINGS: return "OEM_HOOK_STRINGS"; - case RIL_REQUEST_SCREEN_STATE: return "SCREEN_STATE"; - case RIL_REQUEST_SET_SUPP_SVC_NOTIFICATION: return "SET_SUPP_SVC_NOTIFICATION"; - case RIL_REQUEST_WRITE_SMS_TO_SIM: return "WRITE_SMS_TO_SIM"; - case RIL_REQUEST_DELETE_SMS_ON_SIM: return "DELETE_SMS_ON_SIM"; - case RIL_REQUEST_SET_BAND_MODE: return "SET_BAND_MODE"; - case RIL_REQUEST_QUERY_AVAILABLE_BAND_MODE: return "QUERY_AVAILABLE_BAND_MODE"; - case RIL_REQUEST_STK_GET_PROFILE: return "STK_GET_PROFILE"; - case RIL_REQUEST_STK_SET_PROFILE: return "STK_SET_PROFILE"; - case RIL_REQUEST_STK_SEND_ENVELOPE_COMMAND: return "STK_SEND_ENVELOPE_COMMAND"; - case RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE: return "STK_SEND_TERMINAL_RESPONSE"; - case RIL_REQUEST_STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM: return "STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM"; - case RIL_REQUEST_EXPLICIT_CALL_TRANSFER: return "EXPLICIT_CALL_TRANSFER"; - case RIL_REQUEST_SET_PREFERRED_NETWORK_TYPE: return "SET_PREFERRED_NETWORK_TYPE"; - case RIL_REQUEST_GET_PREFERRED_NETWORK_TYPE: return "GET_PREFERRED_NETWORK_TYPE"; - case RIL_REQUEST_GET_NEIGHBORING_CELL_IDS: return "GET_NEIGHBORING_CELL_IDS"; - case RIL_REQUEST_SET_LOCATION_UPDATES: return "SET_LOCATION_UPDATES"; - case RIL_REQUEST_CDMA_SET_SUBSCRIPTION_SOURCE: return "CDMA_SET_SUBSCRIPTION_SOURCE"; - case RIL_REQUEST_CDMA_SET_ROAMING_PREFERENCE: return "CDMA_SET_ROAMING_PREFERENCE"; - case RIL_REQUEST_CDMA_QUERY_ROAMING_PREFERENCE: return "CDMA_QUERY_ROAMING_PREFERENCE"; - case RIL_REQUEST_SET_TTY_MODE: return "SET_TTY_MODE"; - case RIL_REQUEST_QUERY_TTY_MODE: return "QUERY_TTY_MODE"; - case RIL_REQUEST_CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE: return "CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE"; - case RIL_REQUEST_CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE: return "CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE"; - case RIL_REQUEST_CDMA_FLASH: return "CDMA_FLASH"; - case RIL_REQUEST_CDMA_BURST_DTMF: return "CDMA_BURST_DTMF"; - case RIL_REQUEST_CDMA_VALIDATE_AND_WRITE_AKEY: return "CDMA_VALIDATE_AND_WRITE_AKEY"; - case RIL_REQUEST_CDMA_SEND_SMS: return "CDMA_SEND_SMS"; - case RIL_REQUEST_CDMA_SMS_ACKNOWLEDGE: return "CDMA_SMS_ACKNOWLEDGE"; - case RIL_REQUEST_GSM_GET_BROADCAST_SMS_CONFIG: return "GSM_GET_BROADCAST_SMS_CONFIG"; - case RIL_REQUEST_GSM_SET_BROADCAST_SMS_CONFIG: return "GSM_SET_BROADCAST_SMS_CONFIG"; - case RIL_REQUEST_GSM_SMS_BROADCAST_ACTIVATION: return "GSM_SMS_BROADCAST_ACTIVATION"; - case RIL_REQUEST_CDMA_GET_BROADCAST_SMS_CONFIG: return "CDMA_GET_BROADCAST_SMS_CONFIG"; - case RIL_REQUEST_CDMA_SET_BROADCAST_SMS_CONFIG: return "CDMA_SET_BROADCAST_SMS_CONFIG"; - case RIL_REQUEST_CDMA_SMS_BROADCAST_ACTIVATION: return "CDMA_SMS_BROADCAST_ACTIVATION"; - case RIL_REQUEST_CDMA_SUBSCRIPTION: return "CDMA_SUBSCRIPTION"; - case RIL_REQUEST_CDMA_WRITE_SMS_TO_RUIM: return "CDMA_WRITE_SMS_TO_RUIM"; - case RIL_REQUEST_CDMA_DELETE_SMS_ON_RUIM: return "CDMA_DELETE_SMS_ON_RUIM"; - case RIL_REQUEST_DEVICE_IDENTITY: return "DEVICE_IDENTITY"; - case RIL_REQUEST_EXIT_EMERGENCY_CALLBACK_MODE: return "EXIT_EMERGENCY_CALLBACK_MODE"; - case RIL_REQUEST_GET_SMSC_ADDRESS: return "GET_SMSC_ADDRESS"; - case RIL_REQUEST_SET_SMSC_ADDRESS: return "SET_SMSC_ADDRESS"; - case RIL_REQUEST_REPORT_SMS_MEMORY_STATUS: return "REPORT_SMS_MEMORY_STATUS"; - case RIL_REQUEST_REPORT_STK_SERVICE_IS_RUNNING: return "REPORT_STK_SERVICE_IS_RUNNING"; - case RIL_REQUEST_CDMA_GET_SUBSCRIPTION_SOURCE: return "CDMA_GET_SUBSCRIPTION_SOURCE"; - case RIL_REQUEST_ISIM_AUTHENTICATION: return "ISIM_AUTHENTICATION"; - case RIL_REQUEST_ACKNOWLEDGE_INCOMING_GSM_SMS_WITH_PDU: return "ACKNOWLEDGE_INCOMING_GSM_SMS_WITH_PDU"; - case RIL_REQUEST_STK_SEND_ENVELOPE_WITH_STATUS: return "STK_SEND_ENVELOPE_WITH_STATUS"; - case RIL_REQUEST_VOICE_RADIO_TECH: return "VOICE_RADIO_TECH"; - case RIL_REQUEST_GET_CELL_INFO_LIST: return "GET_CELL_INFO_LIST"; - case RIL_REQUEST_SET_UNSOL_CELL_INFO_LIST_RATE: return "SET_UNSOL_CELL_INFO_LIST_RATE"; - case RIL_REQUEST_SET_INITIAL_ATTACH_APN: return "SET_INITIAL_ATTACH_APN"; - case RIL_REQUEST_IMS_REGISTRATION_STATE: return "IMS_REGISTRATION_STATE"; - case RIL_REQUEST_IMS_SEND_SMS: return "IMS_SEND_SMS"; - case RIL_REQUEST_SIM_TRANSMIT_APDU_BASIC: return "SIM_TRANSMIT_APDU_BASIC"; - case RIL_REQUEST_SIM_OPEN_CHANNEL: return "SIM_OPEN_CHANNEL"; - case RIL_REQUEST_SIM_CLOSE_CHANNEL: return "SIM_CLOSE_CHANNEL"; - case RIL_REQUEST_SIM_TRANSMIT_APDU_CHANNEL: return "SIM_TRANSMIT_APDU_CHANNEL"; - case RIL_REQUEST_NV_READ_ITEM: return "NV_READ_ITEM"; - case RIL_REQUEST_NV_WRITE_ITEM: return "NV_WRITE_ITEM"; - case RIL_REQUEST_NV_WRITE_CDMA_PRL: return "NV_WRITE_CDMA_PRL"; - case RIL_REQUEST_NV_RESET_CONFIG: return "NV_RESET_CONFIG"; - case RIL_REQUEST_SET_UICC_SUBSCRIPTION: return "SET_UICC_SUBSCRIPTION"; - case RIL_REQUEST_ALLOW_DATA: return "ALLOW_DATA"; - case RIL_REQUEST_GET_HARDWARE_CONFIG: return "GET_HARDWARE_CONFIG"; - case RIL_REQUEST_SIM_AUTHENTICATION: return "SIM_AUTHENTICATION"; - case RIL_REQUEST_GET_DC_RT_INFO: return "GET_DC_RT_INFO"; - case RIL_REQUEST_SET_DC_RT_INFO_RATE: return "SET_DC_RT_INFO_RATE"; - case RIL_REQUEST_SET_DATA_PROFILE: return "SET_DATA_PROFILE"; - case RIL_REQUEST_SHUTDOWN: return "SHUTDOWN"; - case RIL_REQUEST_GET_RADIO_CAPABILITY: return "GET_RADIO_CAPABILITY"; - case RIL_REQUEST_SET_RADIO_CAPABILITY: return "SET_RADIO_CAPABILITY"; - case RIL_REQUEST_START_LCE: return "START_LCE"; - case RIL_REQUEST_STOP_LCE: return "STOP_LCE"; - case RIL_REQUEST_PULL_LCEDATA: return "PULL_LCEDATA"; - case RIL_REQUEST_GET_ACTIVITY_INFO: return "GET_ACTIVITY_INFO"; - case RIL_REQUEST_SET_CARRIER_RESTRICTIONS: return "SET_CARRIER_RESTRICTIONS"; - case RIL_REQUEST_GET_CARRIER_RESTRICTIONS: return "GET_CARRIER_RESTRICTIONS"; - case RIL_REQUEST_SET_CARRIER_INFO_IMSI_ENCRYPTION: return "SET_CARRIER_INFO_IMSI_ENCRYPTION"; - case RIL_RESPONSE_ACKNOWLEDGEMENT: return "RESPONSE_ACKNOWLEDGEMENT"; - case RIL_UNSOL_RESPONSE_RADIO_STATE_CHANGED: return "UNSOL_RESPONSE_RADIO_STATE_CHANGED"; - case RIL_UNSOL_RESPONSE_CALL_STATE_CHANGED: return "UNSOL_RESPONSE_CALL_STATE_CHANGED"; - case RIL_UNSOL_RESPONSE_VOICE_NETWORK_STATE_CHANGED: return "UNSOL_RESPONSE_VOICE_NETWORK_STATE_CHANGED"; - case RIL_UNSOL_RESPONSE_NEW_SMS: return "UNSOL_RESPONSE_NEW_SMS"; - case RIL_UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT: return "UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT"; - case RIL_UNSOL_RESPONSE_NEW_SMS_ON_SIM: return "UNSOL_RESPONSE_NEW_SMS_ON_SIM"; - case RIL_UNSOL_ON_USSD: return "UNSOL_ON_USSD"; - case RIL_UNSOL_ON_USSD_REQUEST: return "UNSOL_ON_USSD_REQUEST"; - case RIL_UNSOL_NITZ_TIME_RECEIVED: return "UNSOL_NITZ_TIME_RECEIVED"; - case RIL_UNSOL_SIGNAL_STRENGTH: return "UNSOL_SIGNAL_STRENGTH"; - case RIL_UNSOL_DATA_CALL_LIST_CHANGED: return "UNSOL_DATA_CALL_LIST_CHANGED"; - case RIL_UNSOL_SUPP_SVC_NOTIFICATION: return "UNSOL_SUPP_SVC_NOTIFICATION"; - case RIL_UNSOL_STK_SESSION_END: return "UNSOL_STK_SESSION_END"; - case RIL_UNSOL_STK_PROACTIVE_COMMAND: return "UNSOL_STK_PROACTIVE_COMMAND"; - case RIL_UNSOL_STK_EVENT_NOTIFY: return "UNSOL_STK_EVENT_NOTIFY"; - case RIL_UNSOL_STK_CALL_SETUP: return "UNSOL_STK_CALL_SETUP"; - case RIL_UNSOL_SIM_SMS_STORAGE_FULL: return "UNSOL_SIM_SMS_STORAGE_FULL"; - case RIL_UNSOL_SIM_REFRESH: return "UNSOL_SIM_REFRESH"; - case RIL_UNSOL_CALL_RING: return "UNSOL_CALL_RING"; - case RIL_UNSOL_RESPONSE_SIM_STATUS_CHANGED: return "UNSOL_RESPONSE_SIM_STATUS_CHANGED"; - case RIL_UNSOL_RESPONSE_CDMA_NEW_SMS: return "UNSOL_RESPONSE_CDMA_NEW_SMS"; - case RIL_UNSOL_RESPONSE_NEW_BROADCAST_SMS: return "UNSOL_RESPONSE_NEW_BROADCAST_SMS"; - case RIL_UNSOL_CDMA_RUIM_SMS_STORAGE_FULL: return "UNSOL_CDMA_RUIM_SMS_STORAGE_FULL"; - case RIL_UNSOL_RESTRICTED_STATE_CHANGED: return "UNSOL_RESTRICTED_STATE_CHANGED"; - case RIL_UNSOL_ENTER_EMERGENCY_CALLBACK_MODE: return "UNSOL_ENTER_EMERGENCY_CALLBACK_MODE"; - case RIL_UNSOL_CDMA_CALL_WAITING: return "UNSOL_CDMA_CALL_WAITING"; - case RIL_UNSOL_CDMA_OTA_PROVISION_STATUS: return "UNSOL_CDMA_OTA_PROVISION_STATUS"; - case RIL_UNSOL_CDMA_INFO_REC: return "UNSOL_CDMA_INFO_REC"; - case RIL_UNSOL_OEM_HOOK_RAW: return "UNSOL_OEM_HOOK_RAW"; - case RIL_UNSOL_RINGBACK_TONE: return "UNSOL_RINGBACK_TONE"; - case RIL_UNSOL_RESEND_INCALL_MUTE: return "UNSOL_RESEND_INCALL_MUTE"; - case RIL_UNSOL_CDMA_SUBSCRIPTION_SOURCE_CHANGED: return "UNSOL_CDMA_SUBSCRIPTION_SOURCE_CHANGED"; - case RIL_UNSOL_CDMA_PRL_CHANGED: return "UNSOL_CDMA_PRL_CHANGED"; - case RIL_UNSOL_EXIT_EMERGENCY_CALLBACK_MODE: return "UNSOL_EXIT_EMERGENCY_CALLBACK_MODE"; - case RIL_UNSOL_RIL_CONNECTED: return "UNSOL_RIL_CONNECTED"; - case RIL_UNSOL_VOICE_RADIO_TECH_CHANGED: return "UNSOL_VOICE_RADIO_TECH_CHANGED"; - case RIL_UNSOL_CELL_INFO_LIST: return "UNSOL_CELL_INFO_LIST"; - case RIL_UNSOL_RESPONSE_IMS_NETWORK_STATE_CHANGED: return "UNSOL_RESPONSE_IMS_NETWORK_STATE_CHANGED"; - case RIL_UNSOL_UICC_SUBSCRIPTION_STATUS_CHANGED: return "UNSOL_UICC_SUBSCRIPTION_STATUS_CHANGED"; - case RIL_UNSOL_SRVCC_STATE_NOTIFY: return "UNSOL_SRVCC_STATE_NOTIFY"; - case RIL_UNSOL_HARDWARE_CONFIG_CHANGED: return "UNSOL_HARDWARE_CONFIG_CHANGED"; - case RIL_UNSOL_DC_RT_INFO_CHANGED: return "UNSOL_DC_RT_INFO_CHANGED"; - case RIL_UNSOL_RADIO_CAPABILITY: return "UNSOL_RADIO_CAPABILITY"; - case RIL_UNSOL_MODEM_RESTART: return "UNSOL_MODEM_RESTART"; - case RIL_UNSOL_CARRIER_INFO_IMSI_ENCRYPTION: return "UNSOL_CARRIER_INFO_IMSI_ENCRYPTION"; - case RIL_UNSOL_ON_SS: return "UNSOL_ON_SS"; - case RIL_UNSOL_STK_CC_ALPHA_NOTIFY: return "UNSOL_STK_CC_ALPHA_NOTIFY"; - case RIL_UNSOL_LCEDATA_RECV: return "UNSOL_LCEDATA_RECV"; - case RIL_UNSOL_PCO_DATA: return "UNSOL_PCO_DATA"; - default: return "<unknown request>"; - } -} - -const char * -rilSocketIdToString(RIL_SOCKET_ID socket_id) -{ - switch(socket_id) { - case RIL_SOCKET_1: - return "RIL_SOCKET_1"; -#if (SIM_COUNT >= 2) - case RIL_SOCKET_2: - return "RIL_SOCKET_2"; -#endif -#if (SIM_COUNT >= 3) - case RIL_SOCKET_3: - return "RIL_SOCKET_3"; -#endif -#if (SIM_COUNT >= 4) - case RIL_SOCKET_4: - return "RIL_SOCKET_4"; -#endif - default: - return "not a valid RIL"; - } -} - -} /* namespace android */ diff --git a/radio/libril/rilSocketQueue.h b/radio/libril/rilSocketQueue.h deleted file mode 100644 index eaa51552..00000000 --- a/radio/libril/rilSocketQueue.h +++ /dev/null @@ -1,167 +0,0 @@ -/* -* Copyright (C) 2014 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. -*/ - -#include "pb_decode.h" -#include <pthread.h> -#include <hardware/ril/librilutils/proto/sap-api.pb.h> -#include <utils/Log.h> - -using namespace std; - -/** - * Template queue class to handling requests for a rild socket. - * <p> - * This class performs the following functions : - * <ul> - * <li>Enqueue. - * <li>Dequeue. - * <li>Check and dequeue. - * </ul> - */ - -template <typename T> -class Ril_queue { - - /** - * Mutex attribute used in queue mutex initialization. - */ - pthread_mutexattr_t attr; - - /** - * Queue mutex variable for synchronized queue access. - */ - pthread_mutex_t mutex_instance; - - /** - * Condition to be waited on for dequeuing. - */ - pthread_cond_t cond; - - /** - * Front of the queue. - */ - T *front; - - public: - - /** - * Remove the first element of the queue. - * - * @return first element of the queue. - */ - T* dequeue(void); - - /** - * Add a request to the front of the queue. - * - * @param Request to be added. - */ - void enqueue(T* request); - - /** - * Check if the queue is empty. - */ - int empty(void); - - /** - * Check and remove an element with a particular message id and token. - * - * @param Request message id. - * @param Request token. - */ - int checkAndDequeue( MsgId id, int token); - - /** - * Queue constructor. - */ - Ril_queue(void); -}; - -template <typename T> -Ril_queue<T>::Ril_queue(void) { - pthread_mutexattr_init(&attr); - pthread_mutex_init(&mutex_instance, &attr); - cond = PTHREAD_COND_INITIALIZER; - front = NULL; -} - -template <typename T> -T* Ril_queue<T>::dequeue(void) { - T* temp = NULL; - - pthread_mutex_lock(&mutex_instance); - while(empty()) { - pthread_cond_wait(&cond, &mutex_instance); - } - temp = this->front; - if(NULL != this->front->p_next) { - this->front = this->front->p_next; - } else { - this->front = NULL; - } - pthread_mutex_unlock(&mutex_instance); - - return temp; -} - -template <typename T> -void Ril_queue<T>::enqueue(T* request) { - - pthread_mutex_lock(&mutex_instance); - - if(NULL == this->front) { - this->front = request; - request->p_next = NULL; - } else { - request->p_next = this->front; - this->front = request; - } - pthread_cond_broadcast(&cond); - pthread_mutex_unlock(&mutex_instance); -} - -template <typename T> -int Ril_queue<T>::checkAndDequeue(MsgId id, int token) { - int ret = 0; - T* temp; - - pthread_mutex_lock(&mutex_instance); - - for(T **ppCur = &(this->front); *ppCur != NULL; ppCur = &((*ppCur)->p_next)) { - if (token == (*ppCur)->token && id == (*ppCur)->curr->id) { - ret = 1; - temp = *ppCur; - *ppCur = (*ppCur)->p_next; - free(temp); - break; - } - } - - pthread_mutex_unlock(&mutex_instance); - - return ret; -} - - -template <typename T> -int Ril_queue<T>::empty(void) { - - if(this->front == NULL) { - return 1; - } else { - return 0; - } -} diff --git a/radio/libril/ril_commands.h b/radio/libril/ril_commands.h deleted file mode 100644 index 94c2a267..00000000 --- a/radio/libril/ril_commands.h +++ /dev/null @@ -1,162 +0,0 @@ -/* //device/libs/telephony/ril_commands.h -** -** Copyright 2006, 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. -*/ - {0, NULL}, //none - {RIL_REQUEST_GET_SIM_STATUS, radio::getIccCardStatusResponse}, - {RIL_REQUEST_ENTER_SIM_PIN, radio::supplyIccPinForAppResponse}, - {RIL_REQUEST_ENTER_SIM_PUK, radio::supplyIccPukForAppResponse}, - {RIL_REQUEST_ENTER_SIM_PIN2, radio::supplyIccPin2ForAppResponse}, - {RIL_REQUEST_ENTER_SIM_PUK2, radio::supplyIccPuk2ForAppResponse}, - {RIL_REQUEST_CHANGE_SIM_PIN, radio::changeIccPinForAppResponse}, - {RIL_REQUEST_CHANGE_SIM_PIN2, radio::changeIccPin2ForAppResponse}, - {RIL_REQUEST_ENTER_NETWORK_DEPERSONALIZATION, radio::supplyNetworkDepersonalizationResponse}, - {RIL_REQUEST_GET_CURRENT_CALLS, radio::getCurrentCallsResponse}, - {RIL_REQUEST_DIAL, radio::dialResponse}, - {RIL_REQUEST_GET_IMSI, radio::getIMSIForAppResponse}, - {RIL_REQUEST_HANGUP, radio::hangupConnectionResponse}, - {RIL_REQUEST_HANGUP_WAITING_OR_BACKGROUND, radio::hangupWaitingOrBackgroundResponse}, - {RIL_REQUEST_HANGUP_FOREGROUND_RESUME_BACKGROUND, radio::hangupForegroundResumeBackgroundResponse}, - {RIL_REQUEST_SWITCH_WAITING_OR_HOLDING_AND_ACTIVE, radio::switchWaitingOrHoldingAndActiveResponse}, - {RIL_REQUEST_CONFERENCE, radio::conferenceResponse}, - {RIL_REQUEST_UDUB, radio::rejectCallResponse}, - {RIL_REQUEST_LAST_CALL_FAIL_CAUSE, radio::getLastCallFailCauseResponse}, - {RIL_REQUEST_SIGNAL_STRENGTH, radio::getSignalStrengthResponse}, - {RIL_REQUEST_VOICE_REGISTRATION_STATE, radio::getVoiceRegistrationStateResponse}, - {RIL_REQUEST_DATA_REGISTRATION_STATE, radio::getDataRegistrationStateResponse}, - {RIL_REQUEST_OPERATOR, radio::getOperatorResponse}, - {RIL_REQUEST_RADIO_POWER, radio::setRadioPowerResponse}, - {RIL_REQUEST_DTMF, radio::sendDtmfResponse}, - {RIL_REQUEST_SEND_SMS, radio::sendSmsResponse}, - {RIL_REQUEST_SEND_SMS_EXPECT_MORE, radio::sendSMSExpectMoreResponse}, - {RIL_REQUEST_SETUP_DATA_CALL, radio::setupDataCallResponse}, - {RIL_REQUEST_SIM_IO, radio::iccIOForAppResponse}, - {RIL_REQUEST_SEND_USSD, radio::sendUssdResponse}, - {RIL_REQUEST_CANCEL_USSD, radio::cancelPendingUssdResponse}, - {RIL_REQUEST_GET_CLIR, radio::getClirResponse}, - {RIL_REQUEST_SET_CLIR, radio::setClirResponse}, - {RIL_REQUEST_QUERY_CALL_FORWARD_STATUS, radio::getCallForwardStatusResponse}, - {RIL_REQUEST_SET_CALL_FORWARD, radio::setCallForwardResponse}, - {RIL_REQUEST_QUERY_CALL_WAITING, radio::getCallWaitingResponse}, - {RIL_REQUEST_SET_CALL_WAITING, radio::setCallWaitingResponse}, - {RIL_REQUEST_SMS_ACKNOWLEDGE, radio::acknowledgeLastIncomingGsmSmsResponse}, - {RIL_REQUEST_GET_IMEI, NULL}, - {RIL_REQUEST_GET_IMEISV, NULL}, - {RIL_REQUEST_ANSWER, radio::acceptCallResponse}, - {RIL_REQUEST_DEACTIVATE_DATA_CALL, radio::deactivateDataCallResponse}, - {RIL_REQUEST_QUERY_FACILITY_LOCK, radio::getFacilityLockForAppResponse}, - {RIL_REQUEST_SET_FACILITY_LOCK, radio::setFacilityLockForAppResponse}, - {RIL_REQUEST_CHANGE_BARRING_PASSWORD, radio::setBarringPasswordResponse}, - {RIL_REQUEST_QUERY_NETWORK_SELECTION_MODE, radio::getNetworkSelectionModeResponse}, - {RIL_REQUEST_SET_NETWORK_SELECTION_AUTOMATIC, radio::setNetworkSelectionModeAutomaticResponse}, - {RIL_REQUEST_SET_NETWORK_SELECTION_MANUAL, radio::setNetworkSelectionModeManualResponse}, - {RIL_REQUEST_QUERY_AVAILABLE_NETWORKS , radio::getAvailableNetworksResponse}, - {RIL_REQUEST_DTMF_START, radio::startDtmfResponse}, - {RIL_REQUEST_DTMF_STOP, radio::stopDtmfResponse}, - {RIL_REQUEST_BASEBAND_VERSION, radio::getBasebandVersionResponse}, - {RIL_REQUEST_SEPARATE_CONNECTION, radio::separateConnectionResponse}, - {RIL_REQUEST_SET_MUTE, radio::setMuteResponse}, - {RIL_REQUEST_GET_MUTE, radio::getMuteResponse}, - {RIL_REQUEST_QUERY_CLIP, radio::getClipResponse}, - {RIL_REQUEST_LAST_DATA_CALL_FAIL_CAUSE, NULL}, - {RIL_REQUEST_DATA_CALL_LIST, radio::getDataCallListResponse}, - {RIL_REQUEST_RESET_RADIO, NULL}, - {RIL_REQUEST_OEM_HOOK_RAW, radio::sendRequestRawResponse}, - {RIL_REQUEST_OEM_HOOK_STRINGS, radio::sendRequestStringsResponse}, - {RIL_REQUEST_SCREEN_STATE, radio::sendDeviceStateResponse}, // Note the response function is different. - {RIL_REQUEST_SET_SUPP_SVC_NOTIFICATION, radio::setSuppServiceNotificationsResponse}, - {RIL_REQUEST_WRITE_SMS_TO_SIM, radio::writeSmsToSimResponse}, - {RIL_REQUEST_DELETE_SMS_ON_SIM, radio::deleteSmsOnSimResponse}, - {RIL_REQUEST_SET_BAND_MODE, radio::setBandModeResponse}, - {RIL_REQUEST_QUERY_AVAILABLE_BAND_MODE, radio::getAvailableBandModesResponse}, - {RIL_REQUEST_STK_GET_PROFILE, NULL}, - {RIL_REQUEST_STK_SET_PROFILE, NULL}, - {RIL_REQUEST_STK_SEND_ENVELOPE_COMMAND, radio::sendEnvelopeResponse}, - {RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE, radio::sendTerminalResponseToSimResponse}, - {RIL_REQUEST_STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM, radio::handleStkCallSetupRequestFromSimResponse}, - {RIL_REQUEST_EXPLICIT_CALL_TRANSFER, radio::explicitCallTransferResponse}, - {RIL_REQUEST_SET_PREFERRED_NETWORK_TYPE, radio::setPreferredNetworkTypeResponse}, - {RIL_REQUEST_GET_PREFERRED_NETWORK_TYPE, radio::getPreferredNetworkTypeResponse}, - {RIL_REQUEST_GET_NEIGHBORING_CELL_IDS, radio::getNeighboringCidsResponse}, - {RIL_REQUEST_SET_LOCATION_UPDATES, radio::setLocationUpdatesResponse}, - {RIL_REQUEST_CDMA_SET_SUBSCRIPTION_SOURCE, radio::setCdmaSubscriptionSourceResponse}, - {RIL_REQUEST_CDMA_SET_ROAMING_PREFERENCE, radio::setCdmaRoamingPreferenceResponse}, - {RIL_REQUEST_CDMA_QUERY_ROAMING_PREFERENCE, radio::getCdmaRoamingPreferenceResponse}, - {RIL_REQUEST_SET_TTY_MODE, radio::setTTYModeResponse}, - {RIL_REQUEST_QUERY_TTY_MODE, radio::getTTYModeResponse}, - {RIL_REQUEST_CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE, radio::setPreferredVoicePrivacyResponse}, - {RIL_REQUEST_CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE, radio::getPreferredVoicePrivacyResponse}, - {RIL_REQUEST_CDMA_FLASH, radio::sendCDMAFeatureCodeResponse}, - {RIL_REQUEST_CDMA_BURST_DTMF, radio::sendBurstDtmfResponse}, - {RIL_REQUEST_CDMA_VALIDATE_AND_WRITE_AKEY, NULL}, - {RIL_REQUEST_CDMA_SEND_SMS, radio::sendCdmaSmsResponse}, - {RIL_REQUEST_CDMA_SMS_ACKNOWLEDGE, radio::acknowledgeLastIncomingCdmaSmsResponse}, - {RIL_REQUEST_GSM_GET_BROADCAST_SMS_CONFIG, radio::getGsmBroadcastConfigResponse}, - {RIL_REQUEST_GSM_SET_BROADCAST_SMS_CONFIG, radio::setGsmBroadcastConfigResponse}, - {RIL_REQUEST_GSM_SMS_BROADCAST_ACTIVATION, radio::setGsmBroadcastActivationResponse}, - {RIL_REQUEST_CDMA_GET_BROADCAST_SMS_CONFIG, radio::getCdmaBroadcastConfigResponse}, - {RIL_REQUEST_CDMA_SET_BROADCAST_SMS_CONFIG, radio::setCdmaBroadcastConfigResponse}, - {RIL_REQUEST_CDMA_SMS_BROADCAST_ACTIVATION, radio::setCdmaBroadcastActivationResponse}, - {RIL_REQUEST_CDMA_SUBSCRIPTION, radio::getCDMASubscriptionResponse}, - {RIL_REQUEST_CDMA_WRITE_SMS_TO_RUIM, radio::writeSmsToRuimResponse}, - {RIL_REQUEST_CDMA_DELETE_SMS_ON_RUIM, radio::deleteSmsOnRuimResponse}, - {RIL_REQUEST_DEVICE_IDENTITY, radio::getDeviceIdentityResponse}, - {RIL_REQUEST_EXIT_EMERGENCY_CALLBACK_MODE, radio::exitEmergencyCallbackModeResponse}, - {RIL_REQUEST_GET_SMSC_ADDRESS, radio::getSmscAddressResponse}, - {RIL_REQUEST_SET_SMSC_ADDRESS, radio::setSmscAddressResponse}, - {RIL_REQUEST_REPORT_SMS_MEMORY_STATUS, radio::reportSmsMemoryStatusResponse}, - {RIL_REQUEST_REPORT_STK_SERVICE_IS_RUNNING, radio::reportStkServiceIsRunningResponse}, - {RIL_REQUEST_CDMA_GET_SUBSCRIPTION_SOURCE, radio::getCdmaSubscriptionSourceResponse}, - {RIL_REQUEST_ISIM_AUTHENTICATION, radio::requestIsimAuthenticationResponse}, - {RIL_REQUEST_ACKNOWLEDGE_INCOMING_GSM_SMS_WITH_PDU, radio::acknowledgeIncomingGsmSmsWithPduResponse}, - {RIL_REQUEST_STK_SEND_ENVELOPE_WITH_STATUS, radio::sendEnvelopeWithStatusResponse}, - {RIL_REQUEST_VOICE_RADIO_TECH, radio::getVoiceRadioTechnologyResponse}, - {RIL_REQUEST_GET_CELL_INFO_LIST, radio::getCellInfoListResponse}, - {RIL_REQUEST_SET_UNSOL_CELL_INFO_LIST_RATE, radio::setCellInfoListRateResponse}, - {RIL_REQUEST_SET_INITIAL_ATTACH_APN, radio::setInitialAttachApnResponse}, - {RIL_REQUEST_IMS_REGISTRATION_STATE, radio::getImsRegistrationStateResponse}, - {RIL_REQUEST_IMS_SEND_SMS, radio::sendImsSmsResponse}, - {RIL_REQUEST_SIM_TRANSMIT_APDU_BASIC, radio::iccTransmitApduBasicChannelResponse}, - {RIL_REQUEST_SIM_OPEN_CHANNEL, radio::iccOpenLogicalChannelResponse}, - {RIL_REQUEST_SIM_CLOSE_CHANNEL, radio::iccCloseLogicalChannelResponse}, - {RIL_REQUEST_SIM_TRANSMIT_APDU_CHANNEL, radio::iccTransmitApduLogicalChannelResponse}, - {RIL_REQUEST_NV_READ_ITEM, radio::nvReadItemResponse}, - {RIL_REQUEST_NV_WRITE_ITEM, radio::nvWriteItemResponse}, - {RIL_REQUEST_NV_WRITE_CDMA_PRL, radio::nvWriteCdmaPrlResponse}, - {RIL_REQUEST_NV_RESET_CONFIG, radio::nvResetConfigResponse}, - {RIL_REQUEST_SET_UICC_SUBSCRIPTION, radio::setUiccSubscriptionResponse}, - {RIL_REQUEST_ALLOW_DATA, radio::setDataAllowedResponse}, - {RIL_REQUEST_GET_HARDWARE_CONFIG, radio::getHardwareConfigResponse}, - {RIL_REQUEST_SIM_AUTHENTICATION, radio::requestIccSimAuthenticationResponse}, - {RIL_REQUEST_GET_DC_RT_INFO, NULL}, - {RIL_REQUEST_SET_DC_RT_INFO_RATE, NULL}, - {RIL_REQUEST_SET_DATA_PROFILE, radio::setDataProfileResponse}, - {RIL_REQUEST_SHUTDOWN, radio::requestShutdownResponse}, - {RIL_REQUEST_GET_RADIO_CAPABILITY, radio::getRadioCapabilityResponse}, - {RIL_REQUEST_SET_RADIO_CAPABILITY, radio::setRadioCapabilityResponse}, - {RIL_REQUEST_START_LCE, radio::startLceServiceResponse}, - {RIL_REQUEST_STOP_LCE, radio::stopLceServiceResponse}, - {RIL_REQUEST_PULL_LCEDATA, radio::pullLceDataResponse}, - {RIL_REQUEST_GET_ACTIVITY_INFO, radio::getModemActivityInfoResponse}, - {RIL_REQUEST_SET_CARRIER_RESTRICTIONS, radio::setAllowedCarriersResponse}, - {RIL_REQUEST_GET_CARRIER_RESTRICTIONS, radio::getAllowedCarriersResponse}, - {RIL_REQUEST_SEND_DEVICE_STATE, radio::sendDeviceStateResponse}, - {RIL_REQUEST_SET_UNSOLICITED_RESPONSE_FILTER, radio::setIndicationFilterResponse}, - {RIL_REQUEST_SET_SIM_CARD_POWER, radio::setSimCardPowerResponse}, - {RIL_REQUEST_SET_CARRIER_INFO_IMSI_ENCRYPTION, radio::setCarrierInfoForImsiEncryptionResponse}, - {RIL_REQUEST_START_NETWORK_SCAN, radio::startNetworkScanResponse}, - {RIL_REQUEST_STOP_NETWORK_SCAN, radio::stopNetworkScanResponse}, - {RIL_REQUEST_START_KEEPALIVE, radio::startKeepaliveResponse}, - {RIL_REQUEST_STOP_KEEPALIVE, radio::stopKeepaliveResponse}, diff --git a/radio/libril/ril_event.cpp b/radio/libril/ril_event.cpp deleted file mode 100644 index 84b8b72a..00000000 --- a/radio/libril/ril_event.cpp +++ /dev/null @@ -1,384 +0,0 @@ -/* //device/libs/telephony/ril_event.cpp -** -** Copyright 2008, 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_TAG "RILC" - -#include <stdlib.h> -#include <unistd.h> -#include <errno.h> -#include <fcntl.h> -#include <utils/Log.h> -#include <ril_event.h> -#include <string.h> -#include <sys/time.h> -#include <time.h> - -#include <pthread.h> -static pthread_mutex_t listMutex; -#define MUTEX_ACQUIRE() pthread_mutex_lock(&listMutex) -#define MUTEX_RELEASE() pthread_mutex_unlock(&listMutex) -#define MUTEX_INIT() pthread_mutex_init(&listMutex, NULL) -#define MUTEX_DESTROY() pthread_mutex_destroy(&listMutex) - -#ifndef timeradd -#define timeradd(tvp, uvp, vvp) \ - do { \ - (vvp)->tv_sec = (tvp)->tv_sec + (uvp)->tv_sec; \ - (vvp)->tv_usec = (tvp)->tv_usec + (uvp)->tv_usec; \ - if ((vvp)->tv_usec >= 1000000) { \ - (vvp)->tv_sec++; \ - (vvp)->tv_usec -= 1000000; \ - } \ - } while (0) -#endif - -#ifndef timercmp -#define timercmp(a, b, op) \ - ((a)->tv_sec == (b)->tv_sec \ - ? (a)->tv_usec op (b)->tv_usec \ - : (a)->tv_sec op (b)->tv_sec) -#endif - -#ifndef timersub -#define timersub(a, b, res) \ - do { \ - (res)->tv_sec = (a)->tv_sec - (b)->tv_sec; \ - (res)->tv_usec = (a)->tv_usec - (b)->tv_usec; \ - if ((res)->tv_usec < 0) { \ - (res)->tv_usec += 1000000; \ - (res)->tv_sec -= 1; \ - } \ - } while(0); -#endif - -static fd_set readFds; -static int nfds = 0; - -static struct ril_event * watch_table[MAX_FD_EVENTS]; -static struct ril_event timer_list; -static struct ril_event pending_list; - -#define DEBUG 0 - -#if DEBUG -#define dlog(x...) RLOGD( x ) -static void dump_event(struct ril_event * ev) -{ - dlog("~~~~ Event %x ~~~~", (unsigned int)ev); - dlog(" next = %x", (unsigned int)ev->next); - dlog(" prev = %x", (unsigned int)ev->prev); - dlog(" fd = %d", ev->fd); - dlog(" pers = %d", ev->persist); - dlog(" timeout = %ds + %dus", (int)ev->timeout.tv_sec, (int)ev->timeout.tv_usec); - dlog(" func = %x", (unsigned int)ev->func); - dlog(" param = %x", (unsigned int)ev->param); - dlog("~~~~~~~~~~~~~~~~~~"); -} -#else -#define dlog(x...) do {} while(0) -#define dump_event(x) do {} while(0) -#endif - -static void getNow(struct timeval * tv) -{ - struct timespec ts; - clock_gettime(CLOCK_MONOTONIC, &ts); - tv->tv_sec = ts.tv_sec; - tv->tv_usec = ts.tv_nsec/1000; -} - -static void init_list(struct ril_event * list) -{ - memset(list, 0, sizeof(struct ril_event)); - list->next = list; - list->prev = list; - list->fd = -1; -} - -static void addToList(struct ril_event * ev, struct ril_event * list) -{ - ev->next = list; - ev->prev = list->prev; - ev->prev->next = ev; - list->prev = ev; - dump_event(ev); -} - -static void removeFromList(struct ril_event * ev) -{ - dlog("~~~~ +removeFromList ~~~~"); - dump_event(ev); - - ev->next->prev = ev->prev; - ev->prev->next = ev->next; - ev->next = NULL; - ev->prev = NULL; - dlog("~~~~ -removeFromList ~~~~"); -} - - -static void removeWatch(struct ril_event * ev, int index) -{ - dlog("~~~~ +removeWatch ~~~~"); - watch_table[index] = NULL; - ev->index = -1; - - FD_CLR(ev->fd, &readFds); - - if (ev->fd+1 == nfds) { - int n = 0; - - for (int i = 0; i < MAX_FD_EVENTS; i++) { - struct ril_event * rev = watch_table[i]; - - if ((rev != NULL) && (rev->fd > n)) { - n = rev->fd; - } - } - nfds = n + 1; - dlog("~~~~ nfds = %d ~~~~", nfds); - } - dlog("~~~~ -removeWatch ~~~~"); -} - -static void processTimeouts() -{ - dlog("~~~~ +processTimeouts ~~~~"); - MUTEX_ACQUIRE(); - struct timeval now; - struct ril_event * tev = timer_list.next; - struct ril_event * next; - - getNow(&now); - // walk list, see if now >= ev->timeout for any events - - dlog("~~~~ Looking for timers <= %ds + %dus ~~~~", (int)now.tv_sec, (int)now.tv_usec); - while ((tev != &timer_list) && (timercmp(&now, &tev->timeout, >))) { - // Timer expired - dlog("~~~~ firing timer ~~~~"); - next = tev->next; - removeFromList(tev); - addToList(tev, &pending_list); - tev = next; - } - MUTEX_RELEASE(); - dlog("~~~~ -processTimeouts ~~~~"); -} - -static void processReadReadies(fd_set * rfds, int n) -{ - dlog("~~~~ +processReadReadies (%d) ~~~~", n); - MUTEX_ACQUIRE(); - - for (int i = 0; (i < MAX_FD_EVENTS) && (n > 0); i++) { - struct ril_event * rev = watch_table[i]; - if (rev != NULL && FD_ISSET(rev->fd, rfds)) { - addToList(rev, &pending_list); - if (rev->persist == false) { - removeWatch(rev, i); - } - n--; - } - } - - MUTEX_RELEASE(); - dlog("~~~~ -processReadReadies (%d) ~~~~", n); -} - -static void firePending() -{ - dlog("~~~~ +firePending ~~~~"); - struct ril_event * ev = pending_list.next; - while (ev != &pending_list) { - struct ril_event * next = ev->next; - removeFromList(ev); - ev->func(ev->fd, 0, ev->param); - ev = next; - } - dlog("~~~~ -firePending ~~~~"); -} - -static int calcNextTimeout(struct timeval * tv) -{ - struct ril_event * tev = timer_list.next; - struct timeval now; - - getNow(&now); - - // Sorted list, so calc based on first node - if (tev == &timer_list) { - // no pending timers - return -1; - } - - dlog("~~~~ now = %ds + %dus ~~~~", (int)now.tv_sec, (int)now.tv_usec); - dlog("~~~~ next = %ds + %dus ~~~~", - (int)tev->timeout.tv_sec, (int)tev->timeout.tv_usec); - if (timercmp(&tev->timeout, &now, >)) { - timersub(&tev->timeout, &now, tv); - } else { - // timer already expired. - tv->tv_sec = tv->tv_usec = 0; - } - return 0; -} - -// Initialize internal data structs -void ril_event_init() -{ - MUTEX_INIT(); - - FD_ZERO(&readFds); - init_list(&timer_list); - init_list(&pending_list); - memset(watch_table, 0, sizeof(watch_table)); -} - -// Initialize an event -void ril_event_set(struct ril_event * ev, int fd, bool persist, ril_event_cb func, void * param) -{ - dlog("~~~~ ril_event_set %x ~~~~", (unsigned int)ev); - memset(ev, 0, sizeof(struct ril_event)); - ev->fd = fd; - ev->index = -1; - ev->persist = persist; - ev->func = func; - ev->param = param; - fcntl(fd, F_SETFL, O_NONBLOCK); -} - -// Add event to watch list -void ril_event_add(struct ril_event * ev) -{ - dlog("~~~~ +ril_event_add ~~~~"); - MUTEX_ACQUIRE(); - for (int i = 0; i < MAX_FD_EVENTS; i++) { - if (watch_table[i] == NULL) { - watch_table[i] = ev; - ev->index = i; - dlog("~~~~ added at %d ~~~~", i); - dump_event(ev); - FD_SET(ev->fd, &readFds); - if (ev->fd >= nfds) nfds = ev->fd+1; - dlog("~~~~ nfds = %d ~~~~", nfds); - break; - } - } - MUTEX_RELEASE(); - dlog("~~~~ -ril_event_add ~~~~"); -} - -// Add timer event -void ril_timer_add(struct ril_event * ev, struct timeval * tv) -{ - dlog("~~~~ +ril_timer_add ~~~~"); - MUTEX_ACQUIRE(); - - struct ril_event * list; - if (tv != NULL) { - // add to timer list - list = timer_list.next; - ev->fd = -1; // make sure fd is invalid - - struct timeval now; - getNow(&now); - timeradd(&now, tv, &ev->timeout); - - // keep list sorted - while (timercmp(&list->timeout, &ev->timeout, < ) - && (list != &timer_list)) { - list = list->next; - } - // list now points to the first event older than ev - addToList(ev, list); - } - - MUTEX_RELEASE(); - dlog("~~~~ -ril_timer_add ~~~~"); -} - -// Remove event from watch or timer list -void ril_event_del(struct ril_event * ev) -{ - dlog("~~~~ +ril_event_del ~~~~"); - MUTEX_ACQUIRE(); - - if (ev->index < 0 || ev->index >= MAX_FD_EVENTS) { - MUTEX_RELEASE(); - return; - } - - removeWatch(ev, ev->index); - - MUTEX_RELEASE(); - dlog("~~~~ -ril_event_del ~~~~"); -} - -#if DEBUG -static void printReadies(fd_set * rfds) -{ - for (int i = 0; (i < MAX_FD_EVENTS); i++) { - struct ril_event * rev = watch_table[i]; - if (rev != NULL && FD_ISSET(rev->fd, rfds)) { - dlog("DON: fd=%d is ready", rev->fd); - } - } -} -#else -#define printReadies(rfds) do {} while(0) -#endif - -void ril_event_loop() -{ - int n; - fd_set rfds; - struct timeval tv; - struct timeval * ptv; - - - for (;;) { - - // make local copy of read fd_set - memcpy(&rfds, &readFds, sizeof(fd_set)); - if (-1 == calcNextTimeout(&tv)) { - // no pending timers; block indefinitely - dlog("~~~~ no timers; blocking indefinitely ~~~~"); - ptv = NULL; - } else { - dlog("~~~~ blocking for %ds + %dus ~~~~", (int)tv.tv_sec, (int)tv.tv_usec); - ptv = &tv; - } - printReadies(&rfds); - n = select(nfds, &rfds, NULL, NULL, ptv); - printReadies(&rfds); - dlog("~~~~ %d events fired ~~~~", n); - if (n < 0) { - if (errno == EINTR) continue; - - RLOGE("ril_event: select error (%d)", errno); - // bail? - return; - } - - // Check for timeouts - processTimeouts(); - // Check for read-ready - processReadReadies(&rfds, n); - // Fire away - firePending(); - } -} diff --git a/radio/libril/ril_event.h b/radio/libril/ril_event.h deleted file mode 100644 index 7ba231b7..00000000 --- a/radio/libril/ril_event.h +++ /dev/null @@ -1,52 +0,0 @@ -/* //device/libs/telephony/ril_event.h -** -** Copyright 2008, 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. -*/ - -// Max number of fd's we watch at any one time. Increase if necessary. -#define MAX_FD_EVENTS 8 - -typedef void (*ril_event_cb)(int fd, short events, void *userdata); - -struct ril_event { - struct ril_event *next; - struct ril_event *prev; - - int fd; - int index; - bool persist; - struct timeval timeout; - ril_event_cb func; - void *param; -}; - -// Initialize internal data structs -void ril_event_init(); - -// Initialize an event -void ril_event_set(struct ril_event * ev, int fd, bool persist, ril_event_cb func, void * param); - -// Add event to watch list -void ril_event_add(struct ril_event * ev); - -// Add timer event -void ril_timer_add(struct ril_event * ev, struct timeval * tv); - -// Remove event from watch list -void ril_event_del(struct ril_event * ev); - -// Event loop -void ril_event_loop(); - diff --git a/radio/libril/ril_internal.h b/radio/libril/ril_internal.h deleted file mode 100644 index 350791b2..00000000 --- a/radio/libril/ril_internal.h +++ /dev/null @@ -1,98 +0,0 @@ -/* - * 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. - */ - -#ifndef ANDROID_RIL_INTERNAL_H -#define ANDROID_RIL_INTERNAL_H - -namespace android { - -#define RIL_SERVICE_NAME_BASE "slot" -#define RIL1_SERVICE_NAME "slot1" -#define RIL2_SERVICE_NAME "slot2" -#define RIL3_SERVICE_NAME "slot3" -#define RIL4_SERVICE_NAME "slot4" - -/* Constants for response types */ -#define RESPONSE_SOLICITED 0 -#define RESPONSE_UNSOLICITED 1 -#define RESPONSE_SOLICITED_ACK 2 -#define RESPONSE_SOLICITED_ACK_EXP 3 -#define RESPONSE_UNSOLICITED_ACK_EXP 4 - -// Enable verbose logging -#define VDBG 0 - -#define MIN(a,b) ((a)<(b) ? (a) : (b)) - -// Enable RILC log -#define RILC_LOG 0 - -#if RILC_LOG - #define startRequest sprintf(printBuf, "(") - #define closeRequest sprintf(printBuf, "%s)", printBuf) - #define printRequest(token, req) \ - RLOGD("[%04d]> %s %s", token, requestToString(req), printBuf) - - #define startResponse sprintf(printBuf, "%s {", printBuf) - #define closeResponse sprintf(printBuf, "%s}", printBuf) - #define printResponse RLOGD("%s", printBuf) - - #define clearPrintBuf printBuf[0] = 0 - #define removeLastChar printBuf[strlen(printBuf)-1] = 0 - #define appendPrintBuf(x...) snprintf(printBuf, PRINTBUF_SIZE, x) -#else - #define startRequest - #define closeRequest - #define printRequest(token, req) - #define startResponse - #define closeResponse - #define printResponse - #define clearPrintBuf - #define removeLastChar - #define appendPrintBuf(x...) -#endif - -typedef struct CommandInfo CommandInfo; - -extern "C" const char * requestToString(int request); - -typedef struct RequestInfo { - int32_t token; //this is not RIL_Token - CommandInfo *pCI; - struct RequestInfo *p_next; - char cancelled; - char local; // responses to local commands do not go back to command process - RIL_SOCKET_ID socket_id; - int wasAckSent; // Indicates whether an ack was sent earlier -} RequestInfo; - -typedef struct CommandInfo { - int requestNumber; - int(*responseFunction) (int slotId, int responseType, int token, - RIL_Errno e, void *response, size_t responselen); -} CommandInfo; - -RequestInfo * addRequestToList(int serial, int slotId, int request); - -char * RIL_getServiceName(); - -void releaseWakeLock(); - -void onNewCommandConnect(RIL_SOCKET_ID socket_id); - -} // namespace android - -#endif //ANDROID_RIL_INTERNAL_H diff --git a/radio/libril/ril_service.cpp b/radio/libril/ril_service.cpp deleted file mode 100755 index 073398af..00000000 --- a/radio/libril/ril_service.cpp +++ /dev/null @@ -1,8714 +0,0 @@ -/* - * 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. - */ - -#define LOG_TAG "RILC" - -#include <android/hardware/radio/1.4/IRadio.h> -#include <android/hardware/radio/1.4/IRadioResponse.h> -#include <android/hardware/radio/1.4/IRadioIndication.h> -#include <android/hardware/radio/1.4/types.h> - -#include <android/hardware/radio/deprecated/1.0/IOemHook.h> - -#include <hwbinder/IPCThreadState.h> -#include <hwbinder/ProcessState.h> -#include <radio/ril/ril.h> -#include <telephony/ril_mnc.h> -#include <telephony/ril_mcc.h> -#include <ril_service.h> -#include <hidl/HidlTransportSupport.h> -#include <utils/SystemClock.h> -#include <inttypes.h> - -#define INVALID_HEX_CHAR 16 - -using namespace android::hardware::radio; -using namespace android::hardware::radio::V1_0; -using namespace android::hardware::radio::deprecated::V1_0; -using DataRegStateResultV1_4 = android::hardware::radio::V1_4::DataRegStateResult; -using PhysicalChannelConfigV1_4 = - android::hardware::radio::V1_4::PhysicalChannelConfig; -using RadioTechnologyV1_4 = android::hardware::radio::V1_4::RadioTechnology; -using ::android::hardware::configureRpcThreadpool; -using ::android::hardware::joinRpcThreadpool; -using ::android::hardware::Return; -using ::android::hardware::hidl_string; -using ::android::hardware::hidl_vec; -using ::android::hardware::hidl_array; -using ::android::hardware::Void; -using android::CommandInfo; -using android::RequestInfo; -using android::requestToString; -using android::sp; - -#define BOOL_TO_INT(x) (x ? 1 : 0) -#define ATOI_NULL_HANDLED(x) (x ? atoi(x) : -1) -#define ATOI_NULL_HANDLED_DEF(x, defaultVal) (x ? atoi(x) : defaultVal) - -#if defined(ANDROID_MULTI_SIM) -#define CALL_ONREQUEST(a, b, c, d, e) \ - s_vendorFunctions->onRequest((a), (b), (c), (d), ((RIL_SOCKET_ID)(e))) -#define CALL_ONSTATEREQUEST(a) s_vendorFunctions->onStateRequest((RIL_SOCKET_ID)(a)) -#else -#define CALL_ONREQUEST(a, b, c, d, e) s_vendorFunctions->onRequest((a), (b), (c), (d)) -#define CALL_ONSTATEREQUEST(a) s_vendorFunctions->onStateRequest() -#endif - -#ifdef OEM_HOOK_DISABLED -constexpr bool kOemHookEnabled = false; -#else -constexpr bool kOemHookEnabled = true; -#endif - -RIL_RadioFunctions *s_vendorFunctions = NULL; -static CommandInfo *s_commands; - -struct RadioImpl; -struct OemHookImpl; - -#if (SIM_COUNT >= 2) -sp<RadioImpl> radioService[SIM_COUNT]; -sp<OemHookImpl> oemHookService[SIM_COUNT]; -int64_t nitzTimeReceived[SIM_COUNT]; -// counter used for synchronization. It is incremented every time response callbacks are updated. -volatile int32_t mCounterRadio[SIM_COUNT]; -volatile int32_t mCounterOemHook[SIM_COUNT]; -#else -sp<RadioImpl> radioService[1]; -sp<OemHookImpl> oemHookService[1]; -int64_t nitzTimeReceived[1]; -// counter used for synchronization. It is incremented every time response callbacks are updated. -volatile int32_t mCounterRadio[1]; -volatile int32_t mCounterOemHook[1]; -#endif - -static pthread_rwlock_t radioServiceRwlock = PTHREAD_RWLOCK_INITIALIZER; - -#if (SIM_COUNT >= 2) -static pthread_rwlock_t radioServiceRwlock2 = PTHREAD_RWLOCK_INITIALIZER; -#if (SIM_COUNT >= 3) -static pthread_rwlock_t radioServiceRwlock3 = PTHREAD_RWLOCK_INITIALIZER; -#if (SIM_COUNT >= 4) -static pthread_rwlock_t radioServiceRwlock4 = PTHREAD_RWLOCK_INITIALIZER; -#endif -#endif -#endif - -void convertRilHardwareConfigListToHal(void *response, size_t responseLen, - hidl_vec<HardwareConfig>& records); - -void convertRilRadioCapabilityToHal(void *response, size_t responseLen, RadioCapability& rc); - -void convertRilLceDataInfoToHal(void *response, size_t responseLen, LceDataInfo& lce); - -void convertRilSignalStrengthToHal(void *response, size_t responseLen, - SignalStrength& signalStrength); - -void convertRilDataCallToHal(RIL_Data_Call_Response_v11 *dcResponse, - SetupDataCallResult& dcResult); - -void convertRilDataCallListToHal(void *response, size_t responseLen, - hidl_vec<SetupDataCallResult>& dcResultList); - -void convertRilCellInfoListToHal(void *response, size_t responseLen, hidl_vec<CellInfo>& records); - -struct RadioImpl : public V1_1::IRadio { - int32_t mSlotId; - sp<IRadioResponse> mRadioResponse; - sp<IRadioIndication> mRadioIndication; - sp<V1_1::IRadioResponse> mRadioResponseV1_1; - sp<V1_1::IRadioIndication> mRadioIndicationV1_1; - sp<V1_4::IRadioResponse> mRadioResponseV1_4; - sp<V1_4::IRadioIndication> mRadioIndicationV1_4; - - - Return<void> setResponseFunctions( - const ::android::sp<IRadioResponse>& radioResponse, - const ::android::sp<IRadioIndication>& radioIndication); - - Return<void> getIccCardStatus(int32_t serial); - - Return<void> supplyIccPinForApp(int32_t serial, const hidl_string& pin, - const hidl_string& aid); - - Return<void> supplyIccPukForApp(int32_t serial, const hidl_string& puk, - const hidl_string& pin, const hidl_string& aid); - - Return<void> supplyIccPin2ForApp(int32_t serial, - const hidl_string& pin2, - const hidl_string& aid); - - Return<void> supplyIccPuk2ForApp(int32_t serial, const hidl_string& puk2, - const hidl_string& pin2, const hidl_string& aid); - - Return<void> changeIccPinForApp(int32_t serial, const hidl_string& oldPin, - const hidl_string& newPin, const hidl_string& aid); - - Return<void> changeIccPin2ForApp(int32_t serial, const hidl_string& oldPin2, - const hidl_string& newPin2, const hidl_string& aid); - - Return<void> supplyNetworkDepersonalization(int32_t serial, const hidl_string& netPin); - - Return<void> getCurrentCalls(int32_t serial); - - Return<void> dial(int32_t serial, const Dial& dialInfo); - - Return<void> getImsiForApp(int32_t serial, - const ::android::hardware::hidl_string& aid); - - Return<void> hangup(int32_t serial, int32_t gsmIndex); - - Return<void> hangupWaitingOrBackground(int32_t serial); - - Return<void> hangupForegroundResumeBackground(int32_t serial); - - Return<void> switchWaitingOrHoldingAndActive(int32_t serial); - - Return<void> conference(int32_t serial); - - Return<void> rejectCall(int32_t serial); - - Return<void> getLastCallFailCause(int32_t serial); - - Return<void> getSignalStrength(int32_t serial); - - Return<void> getVoiceRegistrationState(int32_t serial); - - Return<void> getDataRegistrationState(int32_t serial); - - Return<void> getOperator(int32_t serial); - - Return<void> setRadioPower(int32_t serial, bool on); - - Return<void> sendDtmf(int32_t serial, - const ::android::hardware::hidl_string& s); - - Return<void> sendSms(int32_t serial, const GsmSmsMessage& message); - - Return<void> sendSMSExpectMore(int32_t serial, const GsmSmsMessage& message); - - Return<void> setupDataCall(int32_t serial, - RadioTechnology radioTechnology, - const DataProfileInfo& profileInfo, - bool modemCognitive, - bool roamingAllowed, - bool isRoaming); - - Return<void> iccIOForApp(int32_t serial, - const IccIo& iccIo); - - Return<void> sendUssd(int32_t serial, - const ::android::hardware::hidl_string& ussd); - - Return<void> cancelPendingUssd(int32_t serial); - - Return<void> getClir(int32_t serial); - - Return<void> setClir(int32_t serial, int32_t status); - - Return<void> getCallForwardStatus(int32_t serial, - const CallForwardInfo& callInfo); - - Return<void> setCallForward(int32_t serial, - const CallForwardInfo& callInfo); - - Return<void> getCallWaiting(int32_t serial, int32_t serviceClass); - - Return<void> setCallWaiting(int32_t serial, bool enable, int32_t serviceClass); - - Return<void> acknowledgeLastIncomingGsmSms(int32_t serial, - bool success, SmsAcknowledgeFailCause cause); - - Return<void> acceptCall(int32_t serial); - - Return<void> deactivateDataCall(int32_t serial, - int32_t cid, bool reasonRadioShutDown); - - Return<void> getFacilityLockForApp(int32_t serial, - const ::android::hardware::hidl_string& facility, - const ::android::hardware::hidl_string& password, - int32_t serviceClass, - const ::android::hardware::hidl_string& appId); - - Return<void> setFacilityLockForApp(int32_t serial, - const ::android::hardware::hidl_string& facility, - bool lockState, - const ::android::hardware::hidl_string& password, - int32_t serviceClass, - const ::android::hardware::hidl_string& appId); - - Return<void> setBarringPassword(int32_t serial, - const ::android::hardware::hidl_string& facility, - const ::android::hardware::hidl_string& oldPassword, - const ::android::hardware::hidl_string& newPassword); - - Return<void> getNetworkSelectionMode(int32_t serial); - - Return<void> setNetworkSelectionModeAutomatic(int32_t serial); - - Return<void> setNetworkSelectionModeManual(int32_t serial, - const ::android::hardware::hidl_string& operatorNumeric); - - Return<void> getAvailableNetworks(int32_t serial); - - Return<void> startNetworkScan(int32_t serial, const V1_1::NetworkScanRequest& request); - - Return<void> stopNetworkScan(int32_t serial); - - Return<void> startDtmf(int32_t serial, - const ::android::hardware::hidl_string& s); - - Return<void> stopDtmf(int32_t serial); - - Return<void> getBasebandVersion(int32_t serial); - - Return<void> separateConnection(int32_t serial, int32_t gsmIndex); - - Return<void> setMute(int32_t serial, bool enable); - - Return<void> getMute(int32_t serial); - - Return<void> getClip(int32_t serial); - - Return<void> getDataCallList(int32_t serial); - - Return<void> setSuppServiceNotifications(int32_t serial, bool enable); - - Return<void> writeSmsToSim(int32_t serial, - const SmsWriteArgs& smsWriteArgs); - - Return<void> deleteSmsOnSim(int32_t serial, int32_t index); - - Return<void> setBandMode(int32_t serial, RadioBandMode mode); - - Return<void> getAvailableBandModes(int32_t serial); - - Return<void> sendEnvelope(int32_t serial, - const ::android::hardware::hidl_string& command); - - Return<void> sendTerminalResponseToSim(int32_t serial, - const ::android::hardware::hidl_string& commandResponse); - - Return<void> handleStkCallSetupRequestFromSim(int32_t serial, bool accept); - - Return<void> explicitCallTransfer(int32_t serial); - - Return<void> setPreferredNetworkType(int32_t serial, PreferredNetworkType nwType); - - Return<void> getPreferredNetworkType(int32_t serial); - - Return<void> getNeighboringCids(int32_t serial); - - Return<void> setLocationUpdates(int32_t serial, bool enable); - - Return<void> setCdmaSubscriptionSource(int32_t serial, - CdmaSubscriptionSource cdmaSub); - - Return<void> setCdmaRoamingPreference(int32_t serial, CdmaRoamingType type); - - Return<void> getCdmaRoamingPreference(int32_t serial); - - Return<void> setTTYMode(int32_t serial, TtyMode mode); - - Return<void> getTTYMode(int32_t serial); - - Return<void> setPreferredVoicePrivacy(int32_t serial, bool enable); - - Return<void> getPreferredVoicePrivacy(int32_t serial); - - Return<void> sendCDMAFeatureCode(int32_t serial, - const ::android::hardware::hidl_string& featureCode); - - Return<void> sendBurstDtmf(int32_t serial, - const ::android::hardware::hidl_string& dtmf, - int32_t on, - int32_t off); - - Return<void> sendCdmaSms(int32_t serial, const CdmaSmsMessage& sms); - - Return<void> acknowledgeLastIncomingCdmaSms(int32_t serial, - const CdmaSmsAck& smsAck); - - Return<void> getGsmBroadcastConfig(int32_t serial); - - Return<void> setGsmBroadcastConfig(int32_t serial, - const hidl_vec<GsmBroadcastSmsConfigInfo>& configInfo); - - Return<void> setGsmBroadcastActivation(int32_t serial, bool activate); - - Return<void> getCdmaBroadcastConfig(int32_t serial); - - Return<void> setCdmaBroadcastConfig(int32_t serial, - const hidl_vec<CdmaBroadcastSmsConfigInfo>& configInfo); - - Return<void> setCdmaBroadcastActivation(int32_t serial, bool activate); - - Return<void> getCDMASubscription(int32_t serial); - - Return<void> writeSmsToRuim(int32_t serial, const CdmaSmsWriteArgs& cdmaSms); - - Return<void> deleteSmsOnRuim(int32_t serial, int32_t index); - - Return<void> getDeviceIdentity(int32_t serial); - - Return<void> exitEmergencyCallbackMode(int32_t serial); - - Return<void> getSmscAddress(int32_t serial); - - Return<void> setSmscAddress(int32_t serial, - const ::android::hardware::hidl_string& smsc); - - Return<void> reportSmsMemoryStatus(int32_t serial, bool available); - - Return<void> reportStkServiceIsRunning(int32_t serial); - - Return<void> getCdmaSubscriptionSource(int32_t serial); - - Return<void> requestIsimAuthentication(int32_t serial, - const ::android::hardware::hidl_string& challenge); - - Return<void> acknowledgeIncomingGsmSmsWithPdu(int32_t serial, - bool success, - const ::android::hardware::hidl_string& ackPdu); - - Return<void> sendEnvelopeWithStatus(int32_t serial, - const ::android::hardware::hidl_string& contents); - - Return<void> getVoiceRadioTechnology(int32_t serial); - - Return<void> getCellInfoList(int32_t serial); - - Return<void> setCellInfoListRate(int32_t serial, int32_t rate); - - Return<void> setInitialAttachApn(int32_t serial, const DataProfileInfo& dataProfileInfo, - bool modemCognitive, bool isRoaming); - - Return<void> getImsRegistrationState(int32_t serial); - - Return<void> sendImsSms(int32_t serial, const ImsSmsMessage& message); - - Return<void> iccTransmitApduBasicChannel(int32_t serial, const SimApdu& message); - - Return<void> iccOpenLogicalChannel(int32_t serial, - const ::android::hardware::hidl_string& aid, int32_t p2); - - Return<void> iccCloseLogicalChannel(int32_t serial, int32_t channelId); - - Return<void> iccTransmitApduLogicalChannel(int32_t serial, const SimApdu& message); - - Return<void> nvReadItem(int32_t serial, NvItem itemId); - - Return<void> nvWriteItem(int32_t serial, const NvWriteItem& item); - - Return<void> nvWriteCdmaPrl(int32_t serial, - const ::android::hardware::hidl_vec<uint8_t>& prl); - - Return<void> nvResetConfig(int32_t serial, ResetNvType resetType); - - Return<void> setUiccSubscription(int32_t serial, const SelectUiccSub& uiccSub); - - Return<void> setDataAllowed(int32_t serial, bool allow); - - Return<void> getHardwareConfig(int32_t serial); - - Return<void> requestIccSimAuthentication(int32_t serial, - int32_t authContext, - const ::android::hardware::hidl_string& authData, - const ::android::hardware::hidl_string& aid); - - Return<void> setDataProfile(int32_t serial, - const ::android::hardware::hidl_vec<DataProfileInfo>& profiles, bool isRoaming); - - Return<void> requestShutdown(int32_t serial); - - Return<void> getRadioCapability(int32_t serial); - - Return<void> setRadioCapability(int32_t serial, const RadioCapability& rc); - - Return<void> startLceService(int32_t serial, int32_t reportInterval, bool pullMode); - - Return<void> stopLceService(int32_t serial); - - Return<void> pullLceData(int32_t serial); - - Return<void> getModemActivityInfo(int32_t serial); - - Return<void> setAllowedCarriers(int32_t serial, - bool allAllowed, - const CarrierRestrictions& carriers); - - Return<void> getAllowedCarriers(int32_t serial); - - Return<void> sendDeviceState(int32_t serial, DeviceStateType deviceStateType, bool state); - - Return<void> setIndicationFilter(int32_t serial, int32_t indicationFilter); - - Return<void> startKeepalive(int32_t serial, const V1_1::KeepaliveRequest& keepalive); - - Return<void> stopKeepalive(int32_t serial, int32_t sessionHandle); - - Return<void> setSimCardPower(int32_t serial, bool powerUp); - Return<void> setSimCardPower_1_1(int32_t serial, - const V1_1::CardPowerState state); - - Return<void> responseAcknowledgement(); - - Return<void> setCarrierInfoForImsiEncryption(int32_t serial, - const V1_1::ImsiEncryptionInfo& message); - - void checkReturnStatus(Return<void>& ret); -}; - -struct OemHookImpl : public IOemHook { - int32_t mSlotId; - sp<IOemHookResponse> mOemHookResponse; - sp<IOemHookIndication> mOemHookIndication; - - Return<void> setResponseFunctions( - const ::android::sp<IOemHookResponse>& oemHookResponse, - const ::android::sp<IOemHookIndication>& oemHookIndication); - - Return<void> sendRequestRaw(int32_t serial, - const ::android::hardware::hidl_vec<uint8_t>& data); - - Return<void> sendRequestStrings(int32_t serial, - const ::android::hardware::hidl_vec<::android::hardware::hidl_string>& data); -}; - -void memsetAndFreeStrings(int numPointers, ...) { - va_list ap; - va_start(ap, numPointers); - for (int i = 0; i < numPointers; i++) { - char *ptr = va_arg(ap, char *); - if (ptr) { -#ifdef MEMSET_FREED -#define MAX_STRING_LENGTH 4096 - memset(ptr, 0, strnlen(ptr, MAX_STRING_LENGTH)); -#endif - free(ptr); - } - } - va_end(ap); -} - -void sendErrorResponse(RequestInfo *pRI, RIL_Errno err) { - pRI->pCI->responseFunction((int) pRI->socket_id, - (int) RadioResponseType::SOLICITED, pRI->token, err, NULL, 0); -} - -/** - * Copies over src to dest. If memory allocation fails, responseFunction() is called for the - * request with error RIL_E_NO_MEMORY. The size() method is used to determine the size of the - * destination buffer into which the HIDL string is copied. If there is a discrepancy between - * the string length reported by the size() method, and the length of the string returned by - * the c_str() method, the function will return false indicating a failure. - * - * Returns true on success, and false on failure. - */ -bool copyHidlStringToRil(char **dest, const hidl_string &src, RequestInfo *pRI, bool allowEmpty) { - size_t len = src.size(); - if (len == 0 && !allowEmpty) { - *dest = NULL; - return true; - } - *dest = (char *) calloc(len + 1, sizeof(char)); - if (*dest == NULL) { - RLOGE("Memory allocation failed for request %s", requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return false; - } - if (strlcpy(*dest, src.c_str(), len + 1) >= (len + 1)) { - RLOGE("Copy of the HIDL string has been truncated, as " - "the string length reported by size() does not " - "match the length of string returned by c_str()."); - free(*dest); - *dest = NULL; - sendErrorResponse(pRI, RIL_E_INTERNAL_ERR); - return false; - } - return true; -} - -bool copyHidlStringToRil(char **dest, const hidl_string &src, RequestInfo *pRI) { - return copyHidlStringToRil(dest, src, pRI, false); -} - -hidl_string convertCharPtrToHidlString(const char *ptr) { - hidl_string ret; - if (ptr != NULL) { - // TODO: replace this with strnlen - ret.setToExternal(ptr, strlen(ptr)); - } - return ret; -} - -bool dispatchVoid(int serial, int slotId, int request) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - CALL_ONREQUEST(request, NULL, 0, pRI, slotId); - return true; -} - -bool dispatchString(int serial, int slotId, int request, const char * str) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - - char *pString; - if (!copyHidlStringToRil(&pString, str, pRI)) { - return false; - } - - CALL_ONREQUEST(request, pString, sizeof(char *), pRI, slotId); - - memsetAndFreeStrings(1, pString); - return true; -} - -bool dispatchStrings(int serial, int slotId, int request, bool allowEmpty, int countStrings, ...) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - - char **pStrings; - pStrings = (char **)calloc(countStrings, sizeof(char *)); - if (pStrings == NULL) { - RLOGE("Memory allocation failed for request %s", requestToString(request)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return false; - } - va_list ap; - va_start(ap, countStrings); - for (int i = 0; i < countStrings; i++) { - const char* str = va_arg(ap, const char *); - if (!copyHidlStringToRil(&pStrings[i], hidl_string(str), pRI, allowEmpty)) { - va_end(ap); - for (int j = 0; j < i; j++) { - memsetAndFreeStrings(1, pStrings[j]); - } - free(pStrings); - return false; - } - } - va_end(ap); - - CALL_ONREQUEST(request, pStrings, countStrings * sizeof(char *), pRI, slotId); - - if (pStrings != NULL) { - for (int i = 0 ; i < countStrings ; i++) { - memsetAndFreeStrings(1, pStrings[i]); - } - -#ifdef MEMSET_FREED - memset(pStrings, 0, countStrings * sizeof(char *)); -#endif - free(pStrings); - } - return true; -} - -bool dispatchStrings(int serial, int slotId, int request, const hidl_vec<hidl_string>& data) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - - int countStrings = data.size(); - char **pStrings; - pStrings = (char **)calloc(countStrings, sizeof(char *)); - if (pStrings == NULL) { - RLOGE("Memory allocation failed for request %s", requestToString(request)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return false; - } - - for (int i = 0; i < countStrings; i++) { - if (!copyHidlStringToRil(&pStrings[i], data[i], pRI)) { - for (int j = 0; j < i; j++) { - memsetAndFreeStrings(1, pStrings[j]); - } - free(pStrings); - return false; - } - } - - CALL_ONREQUEST(request, pStrings, countStrings * sizeof(char *), pRI, slotId); - - if (pStrings != NULL) { - for (int i = 0 ; i < countStrings ; i++) { - memsetAndFreeStrings(1, pStrings[i]); - } - -#ifdef MEMSET_FREED - memset(pStrings, 0, countStrings * sizeof(char *)); -#endif - free(pStrings); - } - return true; -} - -bool dispatchInts(int serial, int slotId, int request, int countInts, ...) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - - int *pInts = (int *)calloc(countInts, sizeof(int)); - - if (pInts == NULL) { - RLOGE("Memory allocation failed for request %s", requestToString(request)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return false; - } - va_list ap; - va_start(ap, countInts); - for (int i = 0; i < countInts; i++) { - pInts[i] = va_arg(ap, int); - } - va_end(ap); - - CALL_ONREQUEST(request, pInts, countInts * sizeof(int), pRI, slotId); - - if (pInts != NULL) { -#ifdef MEMSET_FREED - memset(pInts, 0, countInts * sizeof(int)); -#endif - free(pInts); - } - return true; -} - -bool dispatchCallForwardStatus(int serial, int slotId, int request, - const CallForwardInfo& callInfo) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - - RIL_CallForwardInfo cf; - cf.status = (int) callInfo.status; - cf.reason = callInfo.reason; - cf.serviceClass = callInfo.serviceClass; - cf.toa = callInfo.toa; - cf.timeSeconds = callInfo.timeSeconds; - - if (!copyHidlStringToRil(&cf.number, callInfo.number, pRI)) { - return false; - } - - CALL_ONREQUEST(request, &cf, sizeof(cf), pRI, slotId); - - memsetAndFreeStrings(1, cf.number); - - return true; -} - -bool dispatchRaw(int serial, int slotId, int request, const hidl_vec<uint8_t>& rawBytes) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - - const uint8_t *uData = rawBytes.data(); - - CALL_ONREQUEST(request, (void *) uData, rawBytes.size(), pRI, slotId); - - return true; -} - -bool dispatchIccApdu(int serial, int slotId, int request, const SimApdu& message) { - RequestInfo *pRI = android::addRequestToList(serial, slotId, request); - if (pRI == NULL) { - return false; - } - - RIL_SIM_APDU apdu = {}; - - apdu.sessionid = message.sessionId; - apdu.cla = message.cla; - apdu.instruction = message.instruction; - apdu.p1 = message.p1; - apdu.p2 = message.p2; - apdu.p3 = message.p3; - - if (!copyHidlStringToRil(&apdu.data, message.data, pRI)) { - return false; - } - - CALL_ONREQUEST(request, &apdu, sizeof(apdu), pRI, slotId); - - memsetAndFreeStrings(1, apdu.data); - - return true; -} - -void checkReturnStatus(int32_t slotId, Return<void>& ret, bool isRadioService) { - if (ret.isOk() == false) { - RLOGE("checkReturnStatus: unable to call response/indication callback"); - // Remote process hosting the callbacks must be dead. Reset the callback objects; - // there's no other recovery to be done here. When the client process is back up, it will - // call setResponseFunctions() - - // Caller should already hold rdlock, release that first - // note the current counter to avoid overwriting updates made by another thread before - // write lock is acquired. - int counter = isRadioService ? mCounterRadio[slotId] : mCounterOemHook[slotId]; - pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock(slotId); - int ret = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(ret == 0); - - // acquire wrlock - ret = pthread_rwlock_wrlock(radioServiceRwlockPtr); - assert(ret == 0); - - // make sure the counter value has not changed - if (counter == (isRadioService ? mCounterRadio[slotId] : mCounterOemHook[slotId])) { - if (isRadioService) { - radioService[slotId]->mRadioResponse = NULL; - radioService[slotId]->mRadioIndication = NULL; - radioService[slotId]->mRadioResponseV1_1 = NULL; - radioService[slotId]->mRadioIndicationV1_1 = NULL; - } else { - oemHookService[slotId]->mOemHookResponse = NULL; - oemHookService[slotId]->mOemHookIndication = NULL; - } - isRadioService ? mCounterRadio[slotId]++ : mCounterOemHook[slotId]++; - } else { - RLOGE("checkReturnStatus: not resetting responseFunctions as they likely " - "got updated on another thread"); - } - - // release wrlock - ret = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(ret == 0); - - // Reacquire rdlock - ret = pthread_rwlock_rdlock(radioServiceRwlockPtr); - assert(ret == 0); - } -} - -void RadioImpl::checkReturnStatus(Return<void>& ret) { - ::checkReturnStatus(mSlotId, ret, true); -} - -Return<void> RadioImpl::setResponseFunctions( - const ::android::sp<IRadioResponse>& radioResponseParam, - const ::android::sp<IRadioIndication>& radioIndicationParam) { - RLOGD("setResponseFunctions"); - - pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock(mSlotId); - int ret = pthread_rwlock_wrlock(radioServiceRwlockPtr); - assert(ret == 0); - - mRadioResponse = radioResponseParam; - mRadioIndication = radioIndicationParam; - mRadioResponseV1_1 = V1_1::IRadioResponse::castFrom(mRadioResponse).withDefault(nullptr); - mRadioIndicationV1_1 = V1_1::IRadioIndication::castFrom(mRadioIndication).withDefault(nullptr); - if (mRadioResponseV1_1 == nullptr || mRadioIndicationV1_1 == nullptr) { - mRadioResponseV1_1 = nullptr; - mRadioIndicationV1_1 = nullptr; - } - - mRadioResponseV1_4 = V1_4::IRadioResponse::castFrom(mRadioResponse).withDefault(nullptr); - mRadioIndicationV1_4 = V1_4::IRadioIndication::castFrom(mRadioIndication).withDefault(nullptr); - if (mRadioResponseV1_4 == nullptr || mRadioIndicationV1_4 == nullptr) { - mRadioResponseV1_4 = nullptr; - mRadioIndicationV1_4 = nullptr; - } - - mCounterRadio[mSlotId]++; - - ret = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(ret == 0); - - // client is connected. Send initial indications. - android::onNewCommandConnect((RIL_SOCKET_ID) mSlotId); - - return Void(); -} - -Return<void> RadioImpl::getIccCardStatus(int32_t serial) { -#if VDBG - RLOGD("getIccCardStatus: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_SIM_STATUS); - return Void(); -} - -Return<void> RadioImpl::supplyIccPinForApp(int32_t serial, const hidl_string& pin, - const hidl_string& aid) { -#if VDBG - RLOGD("supplyIccPinForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PIN, true, - 2, pin.c_str(), aid.c_str()); - return Void(); -} - -Return<void> RadioImpl::supplyIccPukForApp(int32_t serial, const hidl_string& puk, - const hidl_string& pin, const hidl_string& aid) { -#if VDBG - RLOGD("supplyIccPukForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PUK, true, - 3, puk.c_str(), pin.c_str(), aid.c_str()); - return Void(); -} - -Return<void> RadioImpl::supplyIccPin2ForApp(int32_t serial, const hidl_string& pin2, - const hidl_string& aid) { -#if VDBG - RLOGD("supplyIccPin2ForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PIN2, true, - 2, pin2.c_str(), aid.c_str()); - return Void(); -} - -Return<void> RadioImpl::supplyIccPuk2ForApp(int32_t serial, const hidl_string& puk2, - const hidl_string& pin2, const hidl_string& aid) { -#if VDBG - RLOGD("supplyIccPuk2ForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_SIM_PUK2, true, - 3, puk2.c_str(), pin2.c_str(), aid.c_str()); - return Void(); -} - -Return<void> RadioImpl::changeIccPinForApp(int32_t serial, const hidl_string& oldPin, - const hidl_string& newPin, const hidl_string& aid) { -#if VDBG - RLOGD("changeIccPinForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_CHANGE_SIM_PIN, true, - 3, oldPin.c_str(), newPin.c_str(), aid.c_str()); - return Void(); -} - -Return<void> RadioImpl::changeIccPin2ForApp(int32_t serial, const hidl_string& oldPin2, - const hidl_string& newPin2, const hidl_string& aid) { -#if VDBG - RLOGD("changeIccPin2ForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_CHANGE_SIM_PIN2, true, - 3, oldPin2.c_str(), newPin2.c_str(), aid.c_str()); - return Void(); -} - -Return<void> RadioImpl::supplyNetworkDepersonalization(int32_t serial, - const hidl_string& netPin) { -#if VDBG - RLOGD("supplyNetworkDepersonalization: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_ENTER_NETWORK_DEPERSONALIZATION, true, - 1, netPin.c_str()); - return Void(); -} - -Return<void> RadioImpl::getCurrentCalls(int32_t serial) { -#if VDBG - RLOGD("getCurrentCalls: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CURRENT_CALLS); - return Void(); -} - -Return<void> RadioImpl::dial(int32_t serial, const Dial& dialInfo) { -#if VDBG - RLOGD("dial: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_DIAL); - if (pRI == NULL) { - return Void(); - } - RIL_Dial dial = {}; - RIL_UUS_Info uusInfo = {}; - int32_t sizeOfDial = sizeof(dial); - - if (!copyHidlStringToRil(&dial.address, dialInfo.address, pRI)) { - return Void(); - } - dial.clir = (int) dialInfo.clir; - - if (dialInfo.uusInfo.size() != 0) { - uusInfo.uusType = (RIL_UUS_Type) dialInfo.uusInfo[0].uusType; - uusInfo.uusDcs = (RIL_UUS_DCS) dialInfo.uusInfo[0].uusDcs; - - if (dialInfo.uusInfo[0].uusData.size() == 0) { - uusInfo.uusData = NULL; - uusInfo.uusLength = 0; - } else { - if (!copyHidlStringToRil(&uusInfo.uusData, dialInfo.uusInfo[0].uusData, pRI)) { - memsetAndFreeStrings(1, dial.address); - return Void(); - } - uusInfo.uusLength = dialInfo.uusInfo[0].uusData.size(); - } - - dial.uusInfo = &uusInfo; - } - - CALL_ONREQUEST(RIL_REQUEST_DIAL, &dial, sizeOfDial, pRI, mSlotId); - - memsetAndFreeStrings(2, dial.address, uusInfo.uusData); - - return Void(); -} - -Return<void> RadioImpl::getImsiForApp(int32_t serial, const hidl_string& aid) { -#if VDBG - RLOGD("getImsiForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_GET_IMSI, false, - 1, aid.c_str()); - return Void(); -} - -Return<void> RadioImpl::hangup(int32_t serial, int32_t gsmIndex) { -#if VDBG - RLOGD("hangup: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_HANGUP, 1, gsmIndex); - return Void(); -} - -Return<void> RadioImpl::hangupWaitingOrBackground(int32_t serial) { -#if VDBG - RLOGD("hangupWaitingOrBackground: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_HANGUP_WAITING_OR_BACKGROUND); - return Void(); -} - -Return<void> RadioImpl::hangupForegroundResumeBackground(int32_t serial) { -#if VDBG - RLOGD("hangupForegroundResumeBackground: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_HANGUP_FOREGROUND_RESUME_BACKGROUND); - return Void(); -} - -Return<void> RadioImpl::switchWaitingOrHoldingAndActive(int32_t serial) { -#if VDBG - RLOGD("switchWaitingOrHoldingAndActive: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_SWITCH_WAITING_OR_HOLDING_AND_ACTIVE); - return Void(); -} - -Return<void> RadioImpl::conference(int32_t serial) { -#if VDBG - RLOGD("conference: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_CONFERENCE); - return Void(); -} - -Return<void> RadioImpl::rejectCall(int32_t serial) { -#if VDBG - RLOGD("rejectCall: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_UDUB); - return Void(); -} - -Return<void> RadioImpl::getLastCallFailCause(int32_t serial) { -#if VDBG - RLOGD("getLastCallFailCause: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_LAST_CALL_FAIL_CAUSE); - return Void(); -} - -Return<void> RadioImpl::getSignalStrength(int32_t serial) { -#if VDBG - RLOGD("getSignalStrength: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_SIGNAL_STRENGTH); - return Void(); -} - -Return<void> RadioImpl::getVoiceRegistrationState(int32_t serial) { -#if VDBG - RLOGD("getVoiceRegistrationState: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_VOICE_REGISTRATION_STATE); - return Void(); -} - -Return<void> RadioImpl::getDataRegistrationState(int32_t serial) { -#if VDBG - RLOGD("getDataRegistrationState: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_DATA_REGISTRATION_STATE); - return Void(); -} - -Return<void> RadioImpl::getOperator(int32_t serial) { -#if VDBG - RLOGD("getOperator: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_OPERATOR); - return Void(); -} - -Return<void> RadioImpl::setRadioPower(int32_t serial, bool on) { - RLOGD("setRadioPower: serial %d on %d", serial, on); - dispatchInts(serial, mSlotId, RIL_REQUEST_RADIO_POWER, 1, BOOL_TO_INT(on)); - return Void(); -} - -Return<void> RadioImpl::sendDtmf(int32_t serial, const hidl_string& s) { -#if VDBG - RLOGD("sendDtmf: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_DTMF, s.c_str()); - return Void(); -} - -Return<void> RadioImpl::sendSms(int32_t serial, const GsmSmsMessage& message) { -#if VDBG - RLOGD("sendSms: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_SEND_SMS, false, - 2, message.smscPdu.c_str(), message.pdu.c_str()); - return Void(); -} - -Return<void> RadioImpl::sendSMSExpectMore(int32_t serial, const GsmSmsMessage& message) { -#if VDBG - RLOGD("sendSMSExpectMore: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_SEND_SMS_EXPECT_MORE, false, - 2, message.smscPdu.c_str(), message.pdu.c_str()); - return Void(); -} - -static bool convertMvnoTypeToString(MvnoType type, char *&str) { - switch (type) { - case MvnoType::IMSI: - str = (char *)"imsi"; - return true; - case MvnoType::GID: - str = (char *)"gid"; - return true; - case MvnoType::SPN: - str = (char *)"spn"; - return true; - case MvnoType::NONE: - str = (char *)""; - return true; - } - return false; -} - -Return<void> RadioImpl::setupDataCall(int32_t serial, RadioTechnology radioTechnology, - const DataProfileInfo& dataProfileInfo, bool modemCognitive, - bool roamingAllowed, bool isRoaming) { - -#if VDBG - RLOGD("setupDataCall: serial %d", serial); -#endif - - if (s_vendorFunctions->version >= 4 && s_vendorFunctions->version <= 14) { - const hidl_string &protocol = - (isRoaming ? dataProfileInfo.roamingProtocol : dataProfileInfo.protocol); - dispatchStrings(serial, mSlotId, RIL_REQUEST_SETUP_DATA_CALL, true, 7, - std::to_string((int) radioTechnology + 2).c_str(), - std::to_string((int) dataProfileInfo.profileId).c_str(), - dataProfileInfo.apn.c_str(), - dataProfileInfo.user.c_str(), - dataProfileInfo.password.c_str(), - std::to_string((int) dataProfileInfo.authType).c_str(), - protocol.c_str()); - } else if (s_vendorFunctions->version >= 15) { - char *mvnoTypeStr = NULL; - if (!convertMvnoTypeToString(dataProfileInfo.mvnoType, mvnoTypeStr)) { - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_SETUP_DATA_CALL); - if (pRI != NULL) { - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - } - return Void(); - } - dispatchStrings(serial, mSlotId, RIL_REQUEST_SETUP_DATA_CALL, true, 15, - std::to_string((int) radioTechnology + 2).c_str(), - std::to_string((int) dataProfileInfo.profileId).c_str(), - dataProfileInfo.apn.c_str(), - dataProfileInfo.user.c_str(), - dataProfileInfo.password.c_str(), - std::to_string((int) dataProfileInfo.authType).c_str(), - dataProfileInfo.protocol.c_str(), - dataProfileInfo.roamingProtocol.c_str(), - std::to_string(dataProfileInfo.supportedApnTypesBitmap).c_str(), - std::to_string(dataProfileInfo.bearerBitmap).c_str(), - modemCognitive ? "1" : "0", - std::to_string(dataProfileInfo.mtu).c_str(), - mvnoTypeStr, - dataProfileInfo.mvnoMatchData.c_str(), - roamingAllowed ? "1" : "0"); - } else { - RLOGE("Unsupported RIL version %d, min version expected 4", s_vendorFunctions->version); - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_SETUP_DATA_CALL); - if (pRI != NULL) { - sendErrorResponse(pRI, RIL_E_REQUEST_NOT_SUPPORTED); - } - } - return Void(); -} - -Return<void> RadioImpl::iccIOForApp(int32_t serial, const IccIo& iccIo) { -#if VDBG - RLOGD("iccIOForApp: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SIM_IO); - if (pRI == NULL) { - return Void(); - } - - RIL_SIM_IO_v6 rilIccIo = {}; - rilIccIo.command = iccIo.command; - rilIccIo.fileid = iccIo.fileId; - if (!copyHidlStringToRil(&rilIccIo.path, iccIo.path, pRI)) { - return Void(); - } - - rilIccIo.p1 = iccIo.p1; - rilIccIo.p2 = iccIo.p2; - rilIccIo.p3 = iccIo.p3; - - if (!copyHidlStringToRil(&rilIccIo.data, iccIo.data, pRI)) { - memsetAndFreeStrings(1, rilIccIo.path); - return Void(); - } - - if (!copyHidlStringToRil(&rilIccIo.pin2, iccIo.pin2, pRI)) { - memsetAndFreeStrings(2, rilIccIo.path, rilIccIo.data); - return Void(); - } - - if (!copyHidlStringToRil(&rilIccIo.aidPtr, iccIo.aid, pRI)) { - memsetAndFreeStrings(3, rilIccIo.path, rilIccIo.data, rilIccIo.pin2); - return Void(); - } - - CALL_ONREQUEST(RIL_REQUEST_SIM_IO, &rilIccIo, sizeof(rilIccIo), pRI, mSlotId); - - memsetAndFreeStrings(4, rilIccIo.path, rilIccIo.data, rilIccIo.pin2, rilIccIo.aidPtr); - - return Void(); -} - -Return<void> RadioImpl::sendUssd(int32_t serial, const hidl_string& ussd) { -#if VDBG - RLOGD("sendUssd: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_SEND_USSD, ussd.c_str()); - return Void(); -} - -Return<void> RadioImpl::cancelPendingUssd(int32_t serial) { -#if VDBG - RLOGD("cancelPendingUssd: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_CANCEL_USSD); - return Void(); -} - -Return<void> RadioImpl::getClir(int32_t serial) { -#if VDBG - RLOGD("getClir: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CLIR); - return Void(); -} - -Return<void> RadioImpl::setClir(int32_t serial, int32_t status) { -#if VDBG - RLOGD("setClir: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_CLIR, 1, status); - return Void(); -} - -Return<void> RadioImpl::getCallForwardStatus(int32_t serial, const CallForwardInfo& callInfo) { -#if VDBG - RLOGD("getCallForwardStatus: serial %d", serial); -#endif - dispatchCallForwardStatus(serial, mSlotId, RIL_REQUEST_QUERY_CALL_FORWARD_STATUS, - callInfo); - return Void(); -} - -Return<void> RadioImpl::setCallForward(int32_t serial, const CallForwardInfo& callInfo) { -#if VDBG - RLOGD("setCallForward: serial %d", serial); -#endif - dispatchCallForwardStatus(serial, mSlotId, RIL_REQUEST_SET_CALL_FORWARD, - callInfo); - return Void(); -} - -Return<void> RadioImpl::getCallWaiting(int32_t serial, int32_t serviceClass) { -#if VDBG - RLOGD("getCallWaiting: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_QUERY_CALL_WAITING, 1, serviceClass); - return Void(); -} - -Return<void> RadioImpl::setCallWaiting(int32_t serial, bool enable, int32_t serviceClass) { -#if VDBG - RLOGD("setCallWaiting: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_CALL_WAITING, 2, BOOL_TO_INT(enable), - serviceClass); - return Void(); -} - -Return<void> RadioImpl::acknowledgeLastIncomingGsmSms(int32_t serial, - bool success, SmsAcknowledgeFailCause cause) { -#if VDBG - RLOGD("acknowledgeLastIncomingGsmSms: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SMS_ACKNOWLEDGE, 2, BOOL_TO_INT(success), - cause); - return Void(); -} - -Return<void> RadioImpl::acceptCall(int32_t serial) { -#if VDBG - RLOGD("acceptCall: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_ANSWER); - return Void(); -} - -Return<void> RadioImpl::deactivateDataCall(int32_t serial, - int32_t cid, bool reasonRadioShutDown) { -#if VDBG - RLOGD("deactivateDataCall: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_DEACTIVATE_DATA_CALL, false, - 2, (std::to_string(cid)).c_str(), reasonRadioShutDown ? "1" : "0"); - return Void(); -} - -Return<void> RadioImpl::getFacilityLockForApp(int32_t serial, const hidl_string& facility, - const hidl_string& password, int32_t serviceClass, - const hidl_string& appId) { -#if VDBG - RLOGD("getFacilityLockForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_QUERY_FACILITY_LOCK, true, - 4, facility.c_str(), password.c_str(), - (std::to_string(serviceClass)).c_str(), appId.c_str()); - return Void(); -} - -Return<void> RadioImpl::setFacilityLockForApp(int32_t serial, const hidl_string& facility, - bool lockState, const hidl_string& password, - int32_t serviceClass, const hidl_string& appId) { -#if VDBG - RLOGD("setFacilityLockForApp: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_SET_FACILITY_LOCK, true, - 5, facility.c_str(), lockState ? "1" : "0", password.c_str(), - (std::to_string(serviceClass)).c_str(), appId.c_str() ); - return Void(); -} - -Return<void> RadioImpl::setBarringPassword(int32_t serial, const hidl_string& facility, - const hidl_string& oldPassword, - const hidl_string& newPassword) { -#if VDBG - RLOGD("setBarringPassword: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_CHANGE_BARRING_PASSWORD, true, - 3, facility.c_str(), oldPassword.c_str(), newPassword.c_str()); - return Void(); -} - -Return<void> RadioImpl::getNetworkSelectionMode(int32_t serial) { -#if VDBG - RLOGD("getNetworkSelectionMode: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_NETWORK_SELECTION_MODE); - return Void(); -} - -Return<void> RadioImpl::setNetworkSelectionModeAutomatic(int32_t serial) { -#if VDBG - RLOGD("setNetworkSelectionModeAutomatic: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_SET_NETWORK_SELECTION_AUTOMATIC); - return Void(); -} - -Return<void> RadioImpl::setNetworkSelectionModeManual(int32_t serial, - const hidl_string& operatorNumeric) { -#if VDBG - RLOGD("setNetworkSelectionModeManual: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_SET_NETWORK_SELECTION_MANUAL, - operatorNumeric.c_str()); - return Void(); -} - -Return<void> RadioImpl::getAvailableNetworks(int32_t serial) { -#if VDBG - RLOGD("getAvailableNetworks: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_AVAILABLE_NETWORKS); - return Void(); -} - -Return<void> RadioImpl::startNetworkScan(int32_t serial, const V1_1::NetworkScanRequest& request) { -#if VDBG - RLOGD("startNetworkScan: serial %d", serial); -#endif - - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_START_NETWORK_SCAN); - if (pRI == NULL) { - return Void(); - } - - if (request.specifiers.size() > MAX_RADIO_ACCESS_NETWORKS) { - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - - RIL_NetworkScanRequest scan_request = {}; - - scan_request.type = (RIL_ScanType) request.type; - scan_request.interval = request.interval; - scan_request.specifiers_length = request.specifiers.size(); - for (size_t i = 0; i < request.specifiers.size(); ++i) { - if (request.specifiers[i].geranBands.size() > MAX_BANDS || - request.specifiers[i].utranBands.size() > MAX_BANDS || - request.specifiers[i].eutranBands.size() > MAX_BANDS || - request.specifiers[i].channels.size() > MAX_CHANNELS) { - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - const V1_1::RadioAccessSpecifier& ras_from = - request.specifiers[i]; - RIL_RadioAccessSpecifier& ras_to = scan_request.specifiers[i]; - - ras_to.radio_access_network = (RIL_RadioAccessNetworks) ras_from.radioAccessNetwork; - ras_to.channels_length = ras_from.channels.size(); - - std::copy(ras_from.channels.begin(), ras_from.channels.end(), ras_to.channels); - const std::vector<uint32_t> * bands = nullptr; - switch (request.specifiers[i].radioAccessNetwork) { - case V1_1::RadioAccessNetworks::GERAN: - ras_to.bands_length = ras_from.geranBands.size(); - bands = (std::vector<uint32_t> *) &ras_from.geranBands; - break; - case V1_1::RadioAccessNetworks::UTRAN: - ras_to.bands_length = ras_from.utranBands.size(); - bands = (std::vector<uint32_t> *) &ras_from.utranBands; - break; - case V1_1::RadioAccessNetworks::EUTRAN: - ras_to.bands_length = ras_from.eutranBands.size(); - bands = (std::vector<uint32_t> *) &ras_from.eutranBands; - break; - default: - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - // safe to copy to geran_bands because it's a union member - for (size_t idx = 0; idx < ras_to.bands_length; ++idx) { - ras_to.bands.geran_bands[idx] = (RIL_GeranBands) (*bands)[idx]; - } - } - - CALL_ONREQUEST(RIL_REQUEST_START_NETWORK_SCAN, &scan_request, sizeof(scan_request), pRI, - mSlotId); - - return Void(); -} - -Return<void> RadioImpl::stopNetworkScan(int32_t serial) { -#if VDBG - RLOGD("stopNetworkScan: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_STOP_NETWORK_SCAN); - return Void(); -} - -Return<void> RadioImpl::startDtmf(int32_t serial, const hidl_string& s) { -#if VDBG - RLOGD("startDtmf: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_DTMF_START, - s.c_str()); - return Void(); -} - -Return<void> RadioImpl::stopDtmf(int32_t serial) { -#if VDBG - RLOGD("stopDtmf: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_DTMF_STOP); - return Void(); -} - -Return<void> RadioImpl::getBasebandVersion(int32_t serial) { -#if VDBG - RLOGD("getBasebandVersion: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_BASEBAND_VERSION); - return Void(); -} - -Return<void> RadioImpl::separateConnection(int32_t serial, int32_t gsmIndex) { -#if VDBG - RLOGD("separateConnection: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SEPARATE_CONNECTION, 1, gsmIndex); - return Void(); -} - -Return<void> RadioImpl::setMute(int32_t serial, bool enable) { -#if VDBG - RLOGD("setMute: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_MUTE, 1, BOOL_TO_INT(enable)); - return Void(); -} - -Return<void> RadioImpl::getMute(int32_t serial) { -#if VDBG - RLOGD("getMute: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_MUTE); - return Void(); -} - -Return<void> RadioImpl::getClip(int32_t serial) { -#if VDBG - RLOGD("getClip: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_CLIP); - return Void(); -} - -Return<void> RadioImpl::getDataCallList(int32_t serial) { -#if VDBG - RLOGD("getDataCallList: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_DATA_CALL_LIST); - return Void(); -} - -Return<void> RadioImpl::setSuppServiceNotifications(int32_t serial, bool enable) { -#if VDBG - RLOGD("setSuppServiceNotifications: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_SUPP_SVC_NOTIFICATION, 1, - BOOL_TO_INT(enable)); - return Void(); -} - -Return<void> RadioImpl::writeSmsToSim(int32_t serial, const SmsWriteArgs& smsWriteArgs) { -#if VDBG - RLOGD("writeSmsToSim: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_WRITE_SMS_TO_SIM); - if (pRI == NULL) { - return Void(); - } - - RIL_SMS_WriteArgs args; - args.status = (int) smsWriteArgs.status; - - if (!copyHidlStringToRil(&args.pdu, smsWriteArgs.pdu, pRI)) { - return Void(); - } - - if (!copyHidlStringToRil(&args.smsc, smsWriteArgs.smsc, pRI)) { - memsetAndFreeStrings(1, args.pdu); - return Void(); - } - - CALL_ONREQUEST(RIL_REQUEST_WRITE_SMS_TO_SIM, &args, sizeof(args), pRI, mSlotId); - - memsetAndFreeStrings(2, args.smsc, args.pdu); - - return Void(); -} - -Return<void> RadioImpl::deleteSmsOnSim(int32_t serial, int32_t index) { -#if VDBG - RLOGD("deleteSmsOnSim: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_DELETE_SMS_ON_SIM, 1, index); - return Void(); -} - -Return<void> RadioImpl::setBandMode(int32_t serial, RadioBandMode mode) { -#if VDBG - RLOGD("setBandMode: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_BAND_MODE, 1, mode); - return Void(); -} - -Return<void> RadioImpl::getAvailableBandModes(int32_t serial) { -#if VDBG - RLOGD("getAvailableBandModes: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_AVAILABLE_BAND_MODE); - return Void(); -} - -Return<void> RadioImpl::sendEnvelope(int32_t serial, const hidl_string& command) { -#if VDBG - RLOGD("sendEnvelope: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_STK_SEND_ENVELOPE_COMMAND, - command.c_str()); - return Void(); -} - -Return<void> RadioImpl::sendTerminalResponseToSim(int32_t serial, - const hidl_string& commandResponse) { -#if VDBG - RLOGD("sendTerminalResponseToSim: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_STK_SEND_TERMINAL_RESPONSE, - commandResponse.c_str()); - return Void(); -} - -Return<void> RadioImpl::handleStkCallSetupRequestFromSim(int32_t serial, bool accept) { -#if VDBG - RLOGD("handleStkCallSetupRequestFromSim: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_STK_HANDLE_CALL_SETUP_REQUESTED_FROM_SIM, - 1, BOOL_TO_INT(accept)); - return Void(); -} - -Return<void> RadioImpl::explicitCallTransfer(int32_t serial) { -#if VDBG - RLOGD("explicitCallTransfer: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_EXPLICIT_CALL_TRANSFER); - return Void(); -} - -Return<void> RadioImpl::setPreferredNetworkType(int32_t serial, PreferredNetworkType nwType) { -#if VDBG - RLOGD("setPreferredNetworkType: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_PREFERRED_NETWORK_TYPE, 1, nwType); - return Void(); -} - -Return<void> RadioImpl::getPreferredNetworkType(int32_t serial) { -#if VDBG - RLOGD("getPreferredNetworkType: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_PREFERRED_NETWORK_TYPE); - return Void(); -} - -Return<void> RadioImpl::getNeighboringCids(int32_t serial) { -#if VDBG - RLOGD("getNeighboringCids: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_NEIGHBORING_CELL_IDS); - return Void(); -} - -Return<void> RadioImpl::setLocationUpdates(int32_t serial, bool enable) { -#if VDBG - RLOGD("setLocationUpdates: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_LOCATION_UPDATES, 1, BOOL_TO_INT(enable)); - return Void(); -} - -Return<void> RadioImpl::setCdmaSubscriptionSource(int32_t serial, CdmaSubscriptionSource cdmaSub) { -#if VDBG - RLOGD("setCdmaSubscriptionSource: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SET_SUBSCRIPTION_SOURCE, 1, cdmaSub); - return Void(); -} - -Return<void> RadioImpl::setCdmaRoamingPreference(int32_t serial, CdmaRoamingType type) { -#if VDBG - RLOGD("setCdmaRoamingPreference: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SET_ROAMING_PREFERENCE, 1, type); - return Void(); -} - -Return<void> RadioImpl::getCdmaRoamingPreference(int32_t serial) { -#if VDBG - RLOGD("getCdmaRoamingPreference: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_QUERY_ROAMING_PREFERENCE); - return Void(); -} - -Return<void> RadioImpl::setTTYMode(int32_t serial, TtyMode mode) { -#if VDBG - RLOGD("setTTYMode: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_TTY_MODE, 1, mode); - return Void(); -} - -Return<void> RadioImpl::getTTYMode(int32_t serial) { -#if VDBG - RLOGD("getTTYMode: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_QUERY_TTY_MODE); - return Void(); -} - -Return<void> RadioImpl::setPreferredVoicePrivacy(int32_t serial, bool enable) { -#if VDBG - RLOGD("setPreferredVoicePrivacy: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE, - 1, BOOL_TO_INT(enable)); - return Void(); -} - -Return<void> RadioImpl::getPreferredVoicePrivacy(int32_t serial) { -#if VDBG - RLOGD("getPreferredVoicePrivacy: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE); - return Void(); -} - -Return<void> RadioImpl::sendCDMAFeatureCode(int32_t serial, const hidl_string& featureCode) { -#if VDBG - RLOGD("sendCDMAFeatureCode: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_CDMA_FLASH, - featureCode.c_str()); - return Void(); -} - -Return<void> RadioImpl::sendBurstDtmf(int32_t serial, const hidl_string& dtmf, int32_t on, - int32_t off) { -#if VDBG - RLOGD("sendBurstDtmf: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_CDMA_BURST_DTMF, false, - 3, dtmf.c_str(), (std::to_string(on)).c_str(), - (std::to_string(off)).c_str()); - return Void(); -} - -void constructCdmaSms(RIL_CDMA_SMS_Message &rcsm, const CdmaSmsMessage& sms) { - rcsm.uTeleserviceID = sms.teleserviceId; - rcsm.bIsServicePresent = BOOL_TO_INT(sms.isServicePresent); - rcsm.uServicecategory = sms.serviceCategory; - rcsm.sAddress.digit_mode = (RIL_CDMA_SMS_DigitMode) sms.address.digitMode; - rcsm.sAddress.number_mode = (RIL_CDMA_SMS_NumberMode) sms.address.numberMode; - rcsm.sAddress.number_type = (RIL_CDMA_SMS_NumberType) sms.address.numberType; - rcsm.sAddress.number_plan = (RIL_CDMA_SMS_NumberPlan) sms.address.numberPlan; - - rcsm.sAddress.number_of_digits = sms.address.digits.size(); - int digitLimit= MIN((rcsm.sAddress.number_of_digits), RIL_CDMA_SMS_ADDRESS_MAX); - for (int i = 0; i < digitLimit; i++) { - rcsm.sAddress.digits[i] = sms.address.digits[i]; - } - - rcsm.sSubAddress.subaddressType = (RIL_CDMA_SMS_SubaddressType) sms.subAddress.subaddressType; - rcsm.sSubAddress.odd = BOOL_TO_INT(sms.subAddress.odd); - - rcsm.sSubAddress.number_of_digits = sms.subAddress.digits.size(); - digitLimit= MIN((rcsm.sSubAddress.number_of_digits), RIL_CDMA_SMS_SUBADDRESS_MAX); - for (int i = 0; i < digitLimit; i++) { - rcsm.sSubAddress.digits[i] = sms.subAddress.digits[i]; - } - - rcsm.uBearerDataLen = sms.bearerData.size(); - digitLimit= MIN((rcsm.uBearerDataLen), RIL_CDMA_SMS_BEARER_DATA_MAX); - for (int i = 0; i < digitLimit; i++) { - rcsm.aBearerData[i] = sms.bearerData[i]; - } -} - -Return<void> RadioImpl::sendCdmaSms(int32_t serial, const CdmaSmsMessage& sms) { -#if VDBG - RLOGD("sendCdmaSms: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_CDMA_SEND_SMS); - if (pRI == NULL) { - return Void(); - } - - RIL_CDMA_SMS_Message rcsm = {}; - constructCdmaSms(rcsm, sms); - - CALL_ONREQUEST(pRI->pCI->requestNumber, &rcsm, sizeof(rcsm), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::acknowledgeLastIncomingCdmaSms(int32_t serial, const CdmaSmsAck& smsAck) { -#if VDBG - RLOGD("acknowledgeLastIncomingCdmaSms: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_CDMA_SMS_ACKNOWLEDGE); - if (pRI == NULL) { - return Void(); - } - - RIL_CDMA_SMS_Ack rcsa = {}; - - rcsa.uErrorClass = (RIL_CDMA_SMS_ErrorClass) smsAck.errorClass; - rcsa.uSMSCauseCode = smsAck.smsCauseCode; - - CALL_ONREQUEST(pRI->pCI->requestNumber, &rcsa, sizeof(rcsa), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::getGsmBroadcastConfig(int32_t serial) { -#if VDBG - RLOGD("getGsmBroadcastConfig: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GSM_GET_BROADCAST_SMS_CONFIG); - return Void(); -} - -Return<void> RadioImpl::setGsmBroadcastConfig(int32_t serial, - const hidl_vec<GsmBroadcastSmsConfigInfo>& - configInfo) { -#if VDBG - RLOGD("setGsmBroadcastConfig: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_GSM_SET_BROADCAST_SMS_CONFIG); - if (pRI == NULL) { - return Void(); - } - - int num = configInfo.size(); - if (num > MAX_BROADCAST_SMS_CONFIG_INFO) { - RLOGE("setGsmBroadcastConfig: Invalid configInfo length %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - RIL_GSM_BroadcastSmsConfigInfo gsmBci[num]; - RIL_GSM_BroadcastSmsConfigInfo *gsmBciPtrs[num]; - - for (int i = 0 ; i < num ; i++ ) { - gsmBciPtrs[i] = &gsmBci[i]; - gsmBci[i].fromServiceId = configInfo[i].fromServiceId; - gsmBci[i].toServiceId = configInfo[i].toServiceId; - gsmBci[i].fromCodeScheme = configInfo[i].fromCodeScheme; - gsmBci[i].toCodeScheme = configInfo[i].toCodeScheme; - gsmBci[i].selected = BOOL_TO_INT(configInfo[i].selected); - } - - CALL_ONREQUEST(pRI->pCI->requestNumber, gsmBciPtrs, - num * sizeof(RIL_GSM_BroadcastSmsConfigInfo *), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::setGsmBroadcastActivation(int32_t serial, bool activate) { -#if VDBG - RLOGD("setGsmBroadcastActivation: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_GSM_SMS_BROADCAST_ACTIVATION, - 1, BOOL_TO_INT(!activate)); - return Void(); -} - -Return<void> RadioImpl::getCdmaBroadcastConfig(int32_t serial) { -#if VDBG - RLOGD("getCdmaBroadcastConfig: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_GET_BROADCAST_SMS_CONFIG); - return Void(); -} - -Return<void> RadioImpl::setCdmaBroadcastConfig(int32_t serial, - const hidl_vec<CdmaBroadcastSmsConfigInfo>& - configInfo) { -#if VDBG - RLOGD("setCdmaBroadcastConfig: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_CDMA_SET_BROADCAST_SMS_CONFIG); - if (pRI == NULL) { - return Void(); - } - - int num = configInfo.size(); - if (num > MAX_BROADCAST_SMS_CONFIG_INFO) { - RLOGE("setCdmaBroadcastConfig: Invalid configInfo length %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - RIL_CDMA_BroadcastSmsConfigInfo cdmaBci[num]; - RIL_CDMA_BroadcastSmsConfigInfo *cdmaBciPtrs[num]; - - for (int i = 0 ; i < num ; i++ ) { - cdmaBciPtrs[i] = &cdmaBci[i]; - cdmaBci[i].service_category = configInfo[i].serviceCategory; - cdmaBci[i].language = configInfo[i].language; - cdmaBci[i].selected = BOOL_TO_INT(configInfo[i].selected); - } - - CALL_ONREQUEST(pRI->pCI->requestNumber, cdmaBciPtrs, - num * sizeof(RIL_CDMA_BroadcastSmsConfigInfo *), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::setCdmaBroadcastActivation(int32_t serial, bool activate) { -#if VDBG - RLOGD("setCdmaBroadcastActivation: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_SMS_BROADCAST_ACTIVATION, - 1, BOOL_TO_INT(!activate)); - return Void(); -} - -Return<void> RadioImpl::getCDMASubscription(int32_t serial) { -#if VDBG - RLOGD("getCDMASubscription: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_SUBSCRIPTION); - return Void(); -} - -Return<void> RadioImpl::writeSmsToRuim(int32_t serial, const CdmaSmsWriteArgs& cdmaSms) { -#if VDBG - RLOGD("writeSmsToRuim: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_CDMA_WRITE_SMS_TO_RUIM); - if (pRI == NULL) { - return Void(); - } - - RIL_CDMA_SMS_WriteArgs rcsw = {}; - rcsw.status = (int) cdmaSms.status; - constructCdmaSms(rcsw.message, cdmaSms.message); - - CALL_ONREQUEST(pRI->pCI->requestNumber, &rcsw, sizeof(rcsw), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::deleteSmsOnRuim(int32_t serial, int32_t index) { -#if VDBG - RLOGD("deleteSmsOnRuim: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_CDMA_DELETE_SMS_ON_RUIM, 1, index); - return Void(); -} - -Return<void> RadioImpl::getDeviceIdentity(int32_t serial) { -#if VDBG - RLOGD("getDeviceIdentity: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_DEVICE_IDENTITY); - return Void(); -} - -Return<void> RadioImpl::exitEmergencyCallbackMode(int32_t serial) { -#if VDBG - RLOGD("exitEmergencyCallbackMode: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_EXIT_EMERGENCY_CALLBACK_MODE); - return Void(); -} - -Return<void> RadioImpl::getSmscAddress(int32_t serial) { -#if VDBG - RLOGD("getSmscAddress: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_SMSC_ADDRESS); - return Void(); -} - -Return<void> RadioImpl::setSmscAddress(int32_t serial, const hidl_string& smsc) { -#if VDBG - RLOGD("setSmscAddress: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_SET_SMSC_ADDRESS, - smsc.c_str()); - return Void(); -} - -Return<void> RadioImpl::reportSmsMemoryStatus(int32_t serial, bool available) { -#if VDBG - RLOGD("reportSmsMemoryStatus: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_REPORT_SMS_MEMORY_STATUS, 1, - BOOL_TO_INT(available)); - return Void(); -} - -Return<void> RadioImpl::reportStkServiceIsRunning(int32_t serial) { -#if VDBG - RLOGD("reportStkServiceIsRunning: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_REPORT_STK_SERVICE_IS_RUNNING); - return Void(); -} - -Return<void> RadioImpl::getCdmaSubscriptionSource(int32_t serial) { -#if VDBG - RLOGD("getCdmaSubscriptionSource: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_CDMA_GET_SUBSCRIPTION_SOURCE); - return Void(); -} - -Return<void> RadioImpl::requestIsimAuthentication(int32_t serial, const hidl_string& challenge) { -#if VDBG - RLOGD("requestIsimAuthentication: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_ISIM_AUTHENTICATION, - challenge.c_str()); - return Void(); -} - -Return<void> RadioImpl::acknowledgeIncomingGsmSmsWithPdu(int32_t serial, bool success, - const hidl_string& ackPdu) { -#if VDBG - RLOGD("acknowledgeIncomingGsmSmsWithPdu: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_ACKNOWLEDGE_INCOMING_GSM_SMS_WITH_PDU, false, - 2, success ? "1" : "0", ackPdu.c_str()); - return Void(); -} - -Return<void> RadioImpl::sendEnvelopeWithStatus(int32_t serial, const hidl_string& contents) { -#if VDBG - RLOGD("sendEnvelopeWithStatus: serial %d", serial); -#endif - dispatchString(serial, mSlotId, RIL_REQUEST_STK_SEND_ENVELOPE_WITH_STATUS, - contents.c_str()); - return Void(); -} - -Return<void> RadioImpl::getVoiceRadioTechnology(int32_t serial) { -#if VDBG - RLOGD("getVoiceRadioTechnology: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_VOICE_RADIO_TECH); - return Void(); -} - -Return<void> RadioImpl::getCellInfoList(int32_t serial) { -#if VDBG - RLOGD("getCellInfoList: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CELL_INFO_LIST); - return Void(); -} - -Return<void> RadioImpl::setCellInfoListRate(int32_t serial, int32_t rate) { -#if VDBG - RLOGD("setCellInfoListRate: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_UNSOL_CELL_INFO_LIST_RATE, 1, rate); - return Void(); -} - -Return<void> RadioImpl::setInitialAttachApn(int32_t serial, const DataProfileInfo& dataProfileInfo, - bool modemCognitive, bool isRoaming) { -#if VDBG - RLOGD("setInitialAttachApn: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_SET_INITIAL_ATTACH_APN); - if (pRI == NULL) { - return Void(); - } - - if (s_vendorFunctions->version <= 14) { - RIL_InitialAttachApn iaa = {}; - - if (!copyHidlStringToRil(&iaa.apn, dataProfileInfo.apn, pRI, true)) { - return Void(); - } - - const hidl_string &protocol = - (isRoaming ? dataProfileInfo.roamingProtocol : dataProfileInfo.protocol); - - if (!copyHidlStringToRil(&iaa.protocol, protocol, pRI)) { - memsetAndFreeStrings(1, iaa.apn); - return Void(); - } - iaa.authtype = (int) dataProfileInfo.authType; - if (!copyHidlStringToRil(&iaa.username, dataProfileInfo.user, pRI)) { - memsetAndFreeStrings(2, iaa.apn, iaa.protocol); - return Void(); - } - if (!copyHidlStringToRil(&iaa.password, dataProfileInfo.password, pRI)) { - memsetAndFreeStrings(3, iaa.apn, iaa.protocol, iaa.username); - return Void(); - } - - CALL_ONREQUEST(RIL_REQUEST_SET_INITIAL_ATTACH_APN, &iaa, sizeof(iaa), pRI, mSlotId); - - memsetAndFreeStrings(4, iaa.apn, iaa.protocol, iaa.username, iaa.password); - } else { - RIL_InitialAttachApn_v15 iaa = {}; - - if (!copyHidlStringToRil(&iaa.apn, dataProfileInfo.apn, pRI, true)) { - return Void(); - } - - if (!copyHidlStringToRil(&iaa.protocol, dataProfileInfo.protocol, pRI)) { - memsetAndFreeStrings(1, iaa.apn); - return Void(); - } - if (!copyHidlStringToRil(&iaa.roamingProtocol, dataProfileInfo.roamingProtocol, pRI)) { - memsetAndFreeStrings(2, iaa.apn, iaa.protocol); - return Void(); - } - iaa.authtype = (int) dataProfileInfo.authType; - if (!copyHidlStringToRil(&iaa.username, dataProfileInfo.user, pRI)) { - memsetAndFreeStrings(3, iaa.apn, iaa.protocol, iaa.roamingProtocol); - return Void(); - } - if (!copyHidlStringToRil(&iaa.password, dataProfileInfo.password, pRI)) { - memsetAndFreeStrings(4, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username); - return Void(); - } - iaa.supportedTypesBitmask = dataProfileInfo.supportedApnTypesBitmap; - iaa.bearerBitmask = dataProfileInfo.bearerBitmap; - iaa.modemCognitive = BOOL_TO_INT(modemCognitive); - iaa.mtu = dataProfileInfo.mtu; - - if (!convertMvnoTypeToString(dataProfileInfo.mvnoType, iaa.mvnoType)) { - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - memsetAndFreeStrings(5, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username, - iaa.password); - return Void(); - } - - if (!copyHidlStringToRil(&iaa.mvnoMatchData, dataProfileInfo.mvnoMatchData, pRI)) { - memsetAndFreeStrings(5, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username, - iaa.password); - return Void(); - } - - CALL_ONREQUEST(RIL_REQUEST_SET_INITIAL_ATTACH_APN, &iaa, sizeof(iaa), pRI, mSlotId); - - memsetAndFreeStrings(6, iaa.apn, iaa.protocol, iaa.roamingProtocol, iaa.username, - iaa.password, iaa.mvnoMatchData); - } - - return Void(); -} - -Return<void> RadioImpl::getImsRegistrationState(int32_t serial) { -#if VDBG - RLOGD("getImsRegistrationState: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_IMS_REGISTRATION_STATE); - return Void(); -} - -bool dispatchImsGsmSms(const ImsSmsMessage& message, RequestInfo *pRI) { - RIL_IMS_SMS_Message rism = {}; - char **pStrings; - int countStrings = 2; - int dataLen = sizeof(char *) * countStrings; - - rism.tech = RADIO_TECH_3GPP; - rism.retry = BOOL_TO_INT(message.retry); - rism.messageRef = message.messageRef; - - if (message.gsmMessage.size() != 1) { - RLOGE("dispatchImsGsmSms: Invalid len %s", requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return false; - } - - pStrings = (char **)calloc(countStrings, sizeof(char *)); - if (pStrings == NULL) { - RLOGE("dispatchImsGsmSms: Memory allocation failed for request %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return false; - } - - if (!copyHidlStringToRil(&pStrings[0], message.gsmMessage[0].smscPdu, pRI)) { -#ifdef MEMSET_FREED - memset(pStrings, 0, dataLen); -#endif - free(pStrings); - return false; - } - - if (!copyHidlStringToRil(&pStrings[1], message.gsmMessage[0].pdu, pRI)) { - memsetAndFreeStrings(1, pStrings[0]); -#ifdef MEMSET_FREED - memset(pStrings, 0, dataLen); -#endif - free(pStrings); - return false; - } - - rism.message.gsmMessage = pStrings; - CALL_ONREQUEST(pRI->pCI->requestNumber, &rism, sizeof(RIL_RadioTechnologyFamily) + - sizeof(uint8_t) + sizeof(int32_t) + dataLen, pRI, pRI->socket_id); - - for (int i = 0 ; i < countStrings ; i++) { - memsetAndFreeStrings(1, pStrings[i]); - } - -#ifdef MEMSET_FREED - memset(pStrings, 0, dataLen); -#endif - free(pStrings); - - return true; -} - -struct ImsCdmaSms { - RIL_IMS_SMS_Message imsSms; - RIL_CDMA_SMS_Message cdmaSms; -}; - -bool dispatchImsCdmaSms(const ImsSmsMessage& message, RequestInfo *pRI) { - ImsCdmaSms temp = {}; - - if (message.cdmaMessage.size() != 1) { - RLOGE("dispatchImsCdmaSms: Invalid len %s", requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return false; - } - - temp.imsSms.tech = RADIO_TECH_3GPP2; - temp.imsSms.retry = BOOL_TO_INT(message.retry); - temp.imsSms.messageRef = message.messageRef; - temp.imsSms.message.cdmaMessage = &temp.cdmaSms; - - constructCdmaSms(temp.cdmaSms, message.cdmaMessage[0]); - - // Vendor code expects payload length to include actual msg payload - // (sizeof(RIL_CDMA_SMS_Message)) instead of (RIL_CDMA_SMS_Message *) + size of other fields in - // RIL_IMS_SMS_Message - int payloadLen = sizeof(RIL_RadioTechnologyFamily) + sizeof(uint8_t) + sizeof(int32_t) - + sizeof(RIL_CDMA_SMS_Message); - - CALL_ONREQUEST(pRI->pCI->requestNumber, &temp.imsSms, payloadLen, pRI, pRI->socket_id); - - return true; -} - -Return<void> RadioImpl::sendImsSms(int32_t serial, const ImsSmsMessage& message) { -#if VDBG - RLOGD("sendImsSms: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_IMS_SEND_SMS); - if (pRI == NULL) { - return Void(); - } - - RIL_RadioTechnologyFamily format = (RIL_RadioTechnologyFamily) message.tech; - - if (RADIO_TECH_3GPP == format) { - dispatchImsGsmSms(message, pRI); - } else if (RADIO_TECH_3GPP2 == format) { - dispatchImsCdmaSms(message, pRI); - } else { - RLOGE("sendImsSms: Invalid radio tech %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - } - return Void(); -} - -Return<void> RadioImpl::iccTransmitApduBasicChannel(int32_t serial, const SimApdu& message) { -#if VDBG - RLOGD("iccTransmitApduBasicChannel: serial %d", serial); -#endif - dispatchIccApdu(serial, mSlotId, RIL_REQUEST_SIM_TRANSMIT_APDU_BASIC, message); - return Void(); -} - -Return<void> RadioImpl::iccOpenLogicalChannel(int32_t serial, const hidl_string& aid, int32_t p2) { -#if VDBG - RLOGD("iccOpenLogicalChannel: serial %d", serial); -#endif - if (s_vendorFunctions->version < 15) { - dispatchString(serial, mSlotId, RIL_REQUEST_SIM_OPEN_CHANNEL, aid.c_str()); - } else { - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SIM_OPEN_CHANNEL); - if (pRI == NULL) { - return Void(); - } - - RIL_OpenChannelParams params = {}; - - params.p2 = p2; - - if (!copyHidlStringToRil(¶ms.aidPtr, aid, pRI)) { - return Void(); - } - - CALL_ONREQUEST(pRI->pCI->requestNumber, ¶ms, sizeof(params), pRI, mSlotId); - - memsetAndFreeStrings(1, params.aidPtr); - } - return Void(); -} - -Return<void> RadioImpl::iccCloseLogicalChannel(int32_t serial, int32_t channelId) { -#if VDBG - RLOGD("iccCloseLogicalChannel: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SIM_CLOSE_CHANNEL, 1, channelId); - return Void(); -} - -Return<void> RadioImpl::iccTransmitApduLogicalChannel(int32_t serial, const SimApdu& message) { -#if VDBG - RLOGD("iccTransmitApduLogicalChannel: serial %d", serial); -#endif - dispatchIccApdu(serial, mSlotId, RIL_REQUEST_SIM_TRANSMIT_APDU_CHANNEL, message); - return Void(); -} - -Return<void> RadioImpl::nvReadItem(int32_t serial, NvItem itemId) { -#if VDBG - RLOGD("nvReadItem: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_NV_READ_ITEM); - if (pRI == NULL) { - return Void(); - } - - RIL_NV_ReadItem nvri = {}; - nvri.itemID = (RIL_NV_Item) itemId; - - CALL_ONREQUEST(pRI->pCI->requestNumber, &nvri, sizeof(nvri), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::nvWriteItem(int32_t serial, const NvWriteItem& item) { -#if VDBG - RLOGD("nvWriteItem: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_NV_WRITE_ITEM); - if (pRI == NULL) { - return Void(); - } - - RIL_NV_WriteItem nvwi = {}; - - nvwi.itemID = (RIL_NV_Item) item.itemId; - - if (!copyHidlStringToRil(&nvwi.value, item.value, pRI)) { - return Void(); - } - - CALL_ONREQUEST(pRI->pCI->requestNumber, &nvwi, sizeof(nvwi), pRI, mSlotId); - - memsetAndFreeStrings(1, nvwi.value); - return Void(); -} - -Return<void> RadioImpl::nvWriteCdmaPrl(int32_t serial, const hidl_vec<uint8_t>& prl) { -#if VDBG - RLOGD("nvWriteCdmaPrl: serial %d", serial); -#endif - dispatchRaw(serial, mSlotId, RIL_REQUEST_NV_WRITE_CDMA_PRL, prl); - return Void(); -} - -Return<void> RadioImpl::nvResetConfig(int32_t serial, ResetNvType resetType) { - int rilResetType = -1; -#if VDBG - RLOGD("nvResetConfig: serial %d", serial); -#endif - /* Convert ResetNvType to RIL.h values - * RIL_REQUEST_NV_RESET_CONFIG - * 1 - reload all NV items - * 2 - erase NV reset (SCRTN) - * 3 - factory reset (RTN) - */ - switch(resetType) { - case ResetNvType::RELOAD: - rilResetType = 1; - break; - case ResetNvType::ERASE: - rilResetType = 2; - break; - case ResetNvType::FACTORY_RESET: - rilResetType = 3; - break; - } - dispatchInts(serial, mSlotId, RIL_REQUEST_NV_RESET_CONFIG, 1, rilResetType); - return Void(); -} - -Return<void> RadioImpl::setUiccSubscription(int32_t serial, const SelectUiccSub& uiccSub) { -#if VDBG - RLOGD("setUiccSubscription: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_SET_UICC_SUBSCRIPTION); - if (pRI == NULL) { - return Void(); - } - - RIL_SelectUiccSub rilUiccSub = {}; - - rilUiccSub.slot = uiccSub.slot; - rilUiccSub.app_index = uiccSub.appIndex; - rilUiccSub.sub_type = (RIL_SubscriptionType) uiccSub.subType; - rilUiccSub.act_status = (RIL_UiccSubActStatus) uiccSub.actStatus; - - CALL_ONREQUEST(pRI->pCI->requestNumber, &rilUiccSub, sizeof(rilUiccSub), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::setDataAllowed(int32_t serial, bool allow) { -#if VDBG - RLOGD("setDataAllowed: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_ALLOW_DATA, 1, BOOL_TO_INT(allow)); - return Void(); -} - -Return<void> RadioImpl::getHardwareConfig(int32_t serial) { -#if VDBG - RLOGD("getHardwareConfig: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_HARDWARE_CONFIG); - return Void(); -} - -Return<void> RadioImpl::requestIccSimAuthentication(int32_t serial, int32_t authContext, - const hidl_string& authData, const hidl_string& aid) { -#if VDBG - RLOGD("requestIccSimAuthentication: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SIM_AUTHENTICATION); - if (pRI == NULL) { - return Void(); - } - - RIL_SimAuthentication pf = {}; - - pf.authContext = authContext; - - if (!copyHidlStringToRil(&pf.authData, authData, pRI)) { - return Void(); - } - - if (!copyHidlStringToRil(&pf.aid, aid, pRI)) { - memsetAndFreeStrings(1, pf.authData); - return Void(); - } - - CALL_ONREQUEST(pRI->pCI->requestNumber, &pf, sizeof(pf), pRI, mSlotId); - - memsetAndFreeStrings(2, pf.authData, pf.aid); - return Void(); -} - -/** - * @param numProfiles number of data profile - * @param dataProfiles the pointer to the actual data profiles. The acceptable type is - RIL_DataProfileInfo or RIL_DataProfileInfo_v15. - * @param dataProfilePtrs the pointer to the pointers that point to each data profile structure - * @param numfields number of string-type member in the data profile structure - * @param ... the variadic parameters are pointers to each string-type member - **/ -template <typename T> -void freeSetDataProfileData(int numProfiles, T *dataProfiles, T **dataProfilePtrs, - int numfields, ...) { - va_list args; - va_start(args, numfields); - - // Iterate through each string-type field that need to be free. - for (int i = 0; i < numfields; i++) { - // Iterate through each data profile and free that specific string-type field. - // The type 'char *T::*' is a type of pointer to a 'char *' member inside T structure. - char *T::*ptr = va_arg(args, char *T::*); - for (int j = 0; j < numProfiles; j++) { - memsetAndFreeStrings(1, dataProfiles[j].*ptr); - } - } - - va_end(args); - -#ifdef MEMSET_FREED - memset(dataProfiles, 0, numProfiles * sizeof(T)); - memset(dataProfilePtrs, 0, numProfiles * sizeof(T *)); -#endif - free(dataProfiles); - free(dataProfilePtrs); -} - -Return<void> RadioImpl::setDataProfile(int32_t serial, const hidl_vec<DataProfileInfo>& profiles, - bool isRoaming) { -#if VDBG - RLOGD("setDataProfile: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SET_DATA_PROFILE); - if (pRI == NULL) { - return Void(); - } - - size_t num = profiles.size(); - bool success = false; - - if (s_vendorFunctions->version <= 14) { - - RIL_DataProfileInfo *dataProfiles = - (RIL_DataProfileInfo *) calloc(num, sizeof(RIL_DataProfileInfo)); - - if (dataProfiles == NULL) { - RLOGE("Memory allocation failed for request %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return Void(); - } - - RIL_DataProfileInfo **dataProfilePtrs = - (RIL_DataProfileInfo **) calloc(num, sizeof(RIL_DataProfileInfo *)); - if (dataProfilePtrs == NULL) { - RLOGE("Memory allocation failed for request %s", - requestToString(pRI->pCI->requestNumber)); - free(dataProfiles); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return Void(); - } - - for (size_t i = 0; i < num; i++) { - dataProfilePtrs[i] = &dataProfiles[i]; - - success = copyHidlStringToRil(&dataProfiles[i].apn, profiles[i].apn, pRI, true); - - const hidl_string &protocol = - (isRoaming ? profiles[i].roamingProtocol : profiles[i].protocol); - - if (success && !copyHidlStringToRil(&dataProfiles[i].protocol, protocol, pRI, true)) { - success = false; - } - - if (success && !copyHidlStringToRil(&dataProfiles[i].user, profiles[i].user, pRI, - true)) { - success = false; - } - if (success && !copyHidlStringToRil(&dataProfiles[i].password, profiles[i].password, - pRI, true)) { - success = false; - } - - if (!success) { - freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 4, - &RIL_DataProfileInfo::apn, &RIL_DataProfileInfo::protocol, - &RIL_DataProfileInfo::user, &RIL_DataProfileInfo::password); - return Void(); - } - - dataProfiles[i].profileId = (RIL_DataProfile) profiles[i].profileId; - dataProfiles[i].authType = (int) profiles[i].authType; - dataProfiles[i].type = (int) profiles[i].type; - dataProfiles[i].maxConnsTime = profiles[i].maxConnsTime; - dataProfiles[i].maxConns = profiles[i].maxConns; - dataProfiles[i].waitTime = profiles[i].waitTime; - dataProfiles[i].enabled = BOOL_TO_INT(profiles[i].enabled); - } - - CALL_ONREQUEST(RIL_REQUEST_SET_DATA_PROFILE, dataProfilePtrs, - num * sizeof(RIL_DataProfileInfo *), pRI, mSlotId); - - freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 4, - &RIL_DataProfileInfo::apn, &RIL_DataProfileInfo::protocol, - &RIL_DataProfileInfo::user, &RIL_DataProfileInfo::password); - } else { - RIL_DataProfileInfo_v15 *dataProfiles = - (RIL_DataProfileInfo_v15 *) calloc(num, sizeof(RIL_DataProfileInfo_v15)); - - if (dataProfiles == NULL) { - RLOGE("Memory allocation failed for request %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return Void(); - } - - RIL_DataProfileInfo_v15 **dataProfilePtrs = - (RIL_DataProfileInfo_v15 **) calloc(num, sizeof(RIL_DataProfileInfo_v15 *)); - if (dataProfilePtrs == NULL) { - RLOGE("Memory allocation failed for request %s", - requestToString(pRI->pCI->requestNumber)); - free(dataProfiles); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return Void(); - } - - for (size_t i = 0; i < num; i++) { - dataProfilePtrs[i] = &dataProfiles[i]; - - success = copyHidlStringToRil(&dataProfiles[i].apn, profiles[i].apn, pRI, true); - if (success && !copyHidlStringToRil(&dataProfiles[i].protocol, profiles[i].protocol, - pRI)) { - success = false; - } - if (success && !copyHidlStringToRil(&dataProfiles[i].roamingProtocol, - profiles[i].roamingProtocol, pRI, true)) { - success = false; - } - if (success && !copyHidlStringToRil(&dataProfiles[i].user, profiles[i].user, pRI, - true)) { - success = false; - } - if (success && !copyHidlStringToRil(&dataProfiles[i].password, profiles[i].password, - pRI, true)) { - success = false; - } - if (success && !copyHidlStringToRil(&dataProfiles[i].mvnoMatchData, - profiles[i].mvnoMatchData, pRI, true)) { - success = false; - } - - if (success && !convertMvnoTypeToString(profiles[i].mvnoType, - dataProfiles[i].mvnoType)) { - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - success = false; - } - - if (!success) { - freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 6, - &RIL_DataProfileInfo_v15::apn, &RIL_DataProfileInfo_v15::protocol, - &RIL_DataProfileInfo_v15::roamingProtocol, &RIL_DataProfileInfo_v15::user, - &RIL_DataProfileInfo_v15::password, &RIL_DataProfileInfo_v15::mvnoMatchData); - return Void(); - } - - dataProfiles[i].profileId = (RIL_DataProfile) profiles[i].profileId; - dataProfiles[i].authType = (int) profiles[i].authType; - dataProfiles[i].type = (int) profiles[i].type; - dataProfiles[i].maxConnsTime = profiles[i].maxConnsTime; - dataProfiles[i].maxConns = profiles[i].maxConns; - dataProfiles[i].waitTime = profiles[i].waitTime; - dataProfiles[i].enabled = BOOL_TO_INT(profiles[i].enabled); - dataProfiles[i].supportedTypesBitmask = profiles[i].supportedApnTypesBitmap; - dataProfiles[i].bearerBitmask = profiles[i].bearerBitmap; - dataProfiles[i].mtu = profiles[i].mtu; - } - - CALL_ONREQUEST(RIL_REQUEST_SET_DATA_PROFILE, dataProfilePtrs, - num * sizeof(RIL_DataProfileInfo_v15 *), pRI, mSlotId); - - freeSetDataProfileData(num, dataProfiles, dataProfilePtrs, 6, - &RIL_DataProfileInfo_v15::apn, &RIL_DataProfileInfo_v15::protocol, - &RIL_DataProfileInfo_v15::roamingProtocol, &RIL_DataProfileInfo_v15::user, - &RIL_DataProfileInfo_v15::password, &RIL_DataProfileInfo_v15::mvnoMatchData); - } - - return Void(); -} - -Return<void> RadioImpl::requestShutdown(int32_t serial) { -#if VDBG - RLOGD("requestShutdown: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_SHUTDOWN); - return Void(); -} - -Return<void> RadioImpl::getRadioCapability(int32_t serial) { -#if VDBG - RLOGD("getRadioCapability: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_RADIO_CAPABILITY); - return Void(); -} - -Return<void> RadioImpl::setRadioCapability(int32_t serial, const RadioCapability& rc) { -#if VDBG - RLOGD("setRadioCapability: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_SET_RADIO_CAPABILITY); - if (pRI == NULL) { - return Void(); - } - - RIL_RadioCapability rilRc = {}; - - // TODO : set rilRc.version using HIDL version ? - rilRc.session = rc.session; - rilRc.phase = (int) rc.phase; - rilRc.rat = (int) rc.raf; - rilRc.status = (int) rc.status; - strlcpy(rilRc.logicalModemUuid, rc.logicalModemUuid.c_str(), sizeof(rilRc.logicalModemUuid)); - - CALL_ONREQUEST(pRI->pCI->requestNumber, &rilRc, sizeof(rilRc), pRI, mSlotId); - - return Void(); -} - -Return<void> RadioImpl::startLceService(int32_t serial, int32_t reportInterval, bool pullMode) { -#if VDBG - RLOGD("startLceService: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_START_LCE, 2, reportInterval, - BOOL_TO_INT(pullMode)); - return Void(); -} - -Return<void> RadioImpl::stopLceService(int32_t serial) { -#if VDBG - RLOGD("stopLceService: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_STOP_LCE); - return Void(); -} - -Return<void> RadioImpl::pullLceData(int32_t serial) { -#if VDBG - RLOGD("pullLceData: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_PULL_LCEDATA); - return Void(); -} - -Return<void> RadioImpl::getModemActivityInfo(int32_t serial) { -#if VDBG - RLOGD("getModemActivityInfo: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_ACTIVITY_INFO); - return Void(); -} - -Return<void> RadioImpl::setAllowedCarriers(int32_t serial, bool allAllowed, - const CarrierRestrictions& carriers) { -#if VDBG - RLOGD("setAllowedCarriers: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_SET_CARRIER_RESTRICTIONS); - if (pRI == NULL) { - return Void(); - } - - RIL_CarrierRestrictions cr = {}; - RIL_Carrier *allowedCarriers = NULL; - RIL_Carrier *excludedCarriers = NULL; - - cr.len_allowed_carriers = carriers.allowedCarriers.size(); - allowedCarriers = (RIL_Carrier *)calloc(cr.len_allowed_carriers, sizeof(RIL_Carrier)); - if (allowedCarriers == NULL) { - RLOGE("setAllowedCarriers: Memory allocation failed for request %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); - return Void(); - } - cr.allowed_carriers = allowedCarriers; - - cr.len_excluded_carriers = carriers.excludedCarriers.size(); - excludedCarriers = (RIL_Carrier *)calloc(cr.len_excluded_carriers, sizeof(RIL_Carrier)); - if (excludedCarriers == NULL) { - RLOGE("setAllowedCarriers: Memory allocation failed for request %s", - requestToString(pRI->pCI->requestNumber)); - sendErrorResponse(pRI, RIL_E_NO_MEMORY); -#ifdef MEMSET_FREED - memset(allowedCarriers, 0, cr.len_allowed_carriers * sizeof(RIL_Carrier)); -#endif - free(allowedCarriers); - return Void(); - } - cr.excluded_carriers = excludedCarriers; - - for (int i = 0; i < cr.len_allowed_carriers; i++) { - allowedCarriers[i].mcc = carriers.allowedCarriers[i].mcc.c_str(); - allowedCarriers[i].mnc = carriers.allowedCarriers[i].mnc.c_str(); - allowedCarriers[i].match_type = (RIL_CarrierMatchType) carriers.allowedCarriers[i].matchType; - allowedCarriers[i].match_data = carriers.allowedCarriers[i].matchData.c_str(); - } - - for (int i = 0; i < cr.len_excluded_carriers; i++) { - excludedCarriers[i].mcc = carriers.excludedCarriers[i].mcc.c_str(); - excludedCarriers[i].mnc = carriers.excludedCarriers[i].mnc.c_str(); - excludedCarriers[i].match_type = - (RIL_CarrierMatchType) carriers.excludedCarriers[i].matchType; - excludedCarriers[i].match_data = carriers.excludedCarriers[i].matchData.c_str(); - } - - CALL_ONREQUEST(pRI->pCI->requestNumber, &cr, sizeof(RIL_CarrierRestrictions), pRI, mSlotId); - -#ifdef MEMSET_FREED - memset(allowedCarriers, 0, cr.len_allowed_carriers * sizeof(RIL_Carrier)); - memset(excludedCarriers, 0, cr.len_excluded_carriers * sizeof(RIL_Carrier)); -#endif - free(allowedCarriers); - free(excludedCarriers); - return Void(); -} - -Return<void> RadioImpl::getAllowedCarriers(int32_t serial) { -#if VDBG - RLOGD("getAllowedCarriers: serial %d", serial); -#endif - dispatchVoid(serial, mSlotId, RIL_REQUEST_GET_CARRIER_RESTRICTIONS); - return Void(); -} - -Return<void> RadioImpl::sendDeviceState(int32_t serial, DeviceStateType deviceStateType, - bool state) { -#if VDBG - RLOGD("sendDeviceState: serial %d", serial); -#endif - if (s_vendorFunctions->version < 15) { - if (deviceStateType == DeviceStateType::LOW_DATA_EXPECTED) { - RLOGD("sendDeviceState: calling screen state %d", BOOL_TO_INT(!state)); - dispatchInts(serial, mSlotId, RIL_REQUEST_SCREEN_STATE, 1, BOOL_TO_INT(!state)); - } else { - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_SEND_DEVICE_STATE); - sendErrorResponse(pRI, RIL_E_REQUEST_NOT_SUPPORTED); - } - return Void(); - } - dispatchInts(serial, mSlotId, RIL_REQUEST_SEND_DEVICE_STATE, 2, (int) deviceStateType, - BOOL_TO_INT(state)); - return Void(); -} - -Return<void> RadioImpl::setIndicationFilter(int32_t serial, int32_t indicationFilter) { -#if VDBG - RLOGD("setIndicationFilter: serial %d", serial); -#endif - if (s_vendorFunctions->version < 15) { - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, - RIL_REQUEST_SET_UNSOLICITED_RESPONSE_FILTER); - sendErrorResponse(pRI, RIL_E_REQUEST_NOT_SUPPORTED); - return Void(); - } - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_UNSOLICITED_RESPONSE_FILTER, 1, indicationFilter); - return Void(); -} - -Return<void> RadioImpl::setSimCardPower(int32_t serial, bool powerUp) { -#if VDBG - RLOGD("setSimCardPower: serial %d", serial); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_SIM_CARD_POWER, 1, BOOL_TO_INT(powerUp)); - return Void(); -} - -Return<void> RadioImpl::setSimCardPower_1_1(int32_t serial, const V1_1::CardPowerState state) { -#if VDBG - RLOGD("setSimCardPower_1_1: serial %d state %d", serial, state); -#endif - dispatchInts(serial, mSlotId, RIL_REQUEST_SET_SIM_CARD_POWER, 1, state); - return Void(); -} - -Return<void> RadioImpl::setCarrierInfoForImsiEncryption(int32_t serial, - const V1_1::ImsiEncryptionInfo& data) { -#if VDBG - RLOGD("setCarrierInfoForImsiEncryption: serial %d", serial); -#endif - RequestInfo *pRI = android::addRequestToList( - serial, mSlotId, RIL_REQUEST_SET_CARRIER_INFO_IMSI_ENCRYPTION); - if (pRI == NULL) { - return Void(); - } - - RIL_CarrierInfoForImsiEncryption imsiEncryption = {}; - - if (!copyHidlStringToRil(&imsiEncryption.mnc, data.mnc, pRI)) { - return Void(); - } - if (!copyHidlStringToRil(&imsiEncryption.mcc, data.mcc, pRI)) { - memsetAndFreeStrings(1, imsiEncryption.mnc); - return Void(); - } - if (!copyHidlStringToRil(&imsiEncryption.keyIdentifier, data.keyIdentifier, pRI)) { - memsetAndFreeStrings(2, imsiEncryption.mnc, imsiEncryption.mcc); - return Void(); - } - imsiEncryption.carrierKeyLength = data.carrierKey.size(); - imsiEncryption.carrierKey = new uint8_t[imsiEncryption.carrierKeyLength]; - memcpy(imsiEncryption.carrierKey, data.carrierKey.data(), imsiEncryption.carrierKeyLength); - imsiEncryption.expirationTime = data.expirationTime; - CALL_ONREQUEST(pRI->pCI->requestNumber, &imsiEncryption, - sizeof(RIL_CarrierInfoForImsiEncryption), pRI, mSlotId); - delete(imsiEncryption.carrierKey); - return Void(); -} - -Return<void> RadioImpl::startKeepalive(int32_t serial, const V1_1::KeepaliveRequest& keepalive) { -#if VDBG - RLOGD("%s(): %d", __FUNCTION__, serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_START_KEEPALIVE); - if (pRI == NULL) { - return Void(); - } - - RIL_KeepaliveRequest kaReq = {}; - - kaReq.type = static_cast<RIL_KeepaliveType>(keepalive.type); - switch(kaReq.type) { - case NATT_IPV4: - if (keepalive.sourceAddress.size() != 4 || - keepalive.destinationAddress.size() != 4) { - RLOGE("Invalid address for keepalive!"); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - break; - case NATT_IPV6: - if (keepalive.sourceAddress.size() != 16 || - keepalive.destinationAddress.size() != 16) { - RLOGE("Invalid address for keepalive!"); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - break; - default: - RLOGE("Unknown packet keepalive type!"); - sendErrorResponse(pRI, RIL_E_INVALID_ARGUMENTS); - return Void(); - } - - ::memcpy(kaReq.sourceAddress, keepalive.sourceAddress.data(), keepalive.sourceAddress.size()); - kaReq.sourcePort = keepalive.sourcePort; - - ::memcpy(kaReq.destinationAddress, - keepalive.destinationAddress.data(), keepalive.destinationAddress.size()); - kaReq.destinationPort = keepalive.destinationPort; - - kaReq.maxKeepaliveIntervalMillis = keepalive.maxKeepaliveIntervalMillis; - kaReq.cid = keepalive.cid; // This is the context ID of the data call - - CALL_ONREQUEST(pRI->pCI->requestNumber, &kaReq, sizeof(RIL_KeepaliveRequest), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::stopKeepalive(int32_t serial, int32_t sessionHandle) { -#if VDBG - RLOGD("%s(): %d", __FUNCTION__, serial); -#endif - RequestInfo *pRI = android::addRequestToList(serial, mSlotId, RIL_REQUEST_STOP_KEEPALIVE); - if (pRI == NULL) { - return Void(); - } - - CALL_ONREQUEST(pRI->pCI->requestNumber, &sessionHandle, sizeof(uint32_t), pRI, mSlotId); - return Void(); -} - -Return<void> RadioImpl::responseAcknowledgement() { - android::releaseWakeLock(); - return Void(); -} - -Return<void> OemHookImpl::setResponseFunctions( - const ::android::sp<IOemHookResponse>& oemHookResponseParam, - const ::android::sp<IOemHookIndication>& oemHookIndicationParam) { -#if VDBG - RLOGD("OemHookImpl::setResponseFunctions"); -#endif - - pthread_rwlock_t *radioServiceRwlockPtr = radio::getRadioServiceRwlock(mSlotId); - int ret = pthread_rwlock_wrlock(radioServiceRwlockPtr); - assert(ret == 0); - - mOemHookResponse = oemHookResponseParam; - mOemHookIndication = oemHookIndicationParam; - mCounterOemHook[mSlotId]++; - - ret = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(ret == 0); - - return Void(); -} - -Return<void> OemHookImpl::sendRequestRaw(int32_t serial, const hidl_vec<uint8_t>& data) { -#if VDBG - RLOGD("OemHookImpl::sendRequestRaw: serial %d", serial); -#endif - dispatchRaw(serial, mSlotId, RIL_REQUEST_OEM_HOOK_RAW, data); - return Void(); -} - -Return<void> OemHookImpl::sendRequestStrings(int32_t serial, - const hidl_vec<hidl_string>& data) { -#if VDBG - RLOGD("OemHookImpl::sendRequestStrings: serial %d", serial); -#endif - dispatchStrings(serial, mSlotId, RIL_REQUEST_OEM_HOOK_STRINGS, data); - return Void(); -} - -/*************************************************************************************************** - * RESPONSE FUNCTIONS - * Functions above are used for requests going from framework to vendor code. The ones below are - * responses for those requests coming back from the vendor code. - **************************************************************************************************/ - -void radio::acknowledgeRequest(int slotId, int serial) { - if (radioService[slotId]->mRadioResponse != NULL) { - Return<void> retStatus = radioService[slotId]->mRadioResponse->acknowledgeRequest(serial); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("acknowledgeRequest: radioService[%d]->mRadioResponse == NULL", slotId); - } -} - -void populateResponseInfo(RadioResponseInfo& responseInfo, int serial, int responseType, - RIL_Errno e) { - responseInfo.serial = serial; - switch (responseType) { - case RESPONSE_SOLICITED: - responseInfo.type = RadioResponseType::SOLICITED; - break; - case RESPONSE_SOLICITED_ACK_EXP: - responseInfo.type = RadioResponseType::SOLICITED_ACK_EXP; - break; - } - responseInfo.error = (RadioError) e; -} - -int responseIntOrEmpty(RadioResponseInfo& responseInfo, int serial, int responseType, RIL_Errno e, - void *response, size_t responseLen) { - populateResponseInfo(responseInfo, serial, responseType, e); - int ret = -1; - - if (response == NULL && responseLen == 0) { - // Earlier RILs did not send a response for some cases although the interface - // expected an integer as response. Do not return error if response is empty. Instead - // Return -1 in those cases to maintain backward compatibility. - } else if (response == NULL || responseLen != sizeof(int)) { - RLOGE("responseIntOrEmpty: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *p_int = (int *) response; - ret = p_int[0]; - } - return ret; -} - -int responseInt(RadioResponseInfo& responseInfo, int serial, int responseType, RIL_Errno e, - void *response, size_t responseLen) { - populateResponseInfo(responseInfo, serial, responseType, e); - int ret = -1; - - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("responseInt: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *p_int = (int *) response; - ret = p_int[0]; - } - return ret; -} - -int radio::getIccCardStatusResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - CardStatus cardStatus = {CardState::ABSENT, PinState::UNKNOWN, -1, -1, -1, {}}; - RIL_CardStatus_v6 *p_cur = ((RIL_CardStatus_v6 *) response); - if (response == NULL || responseLen != sizeof(RIL_CardStatus_v6) - || p_cur->gsm_umts_subscription_app_index >= p_cur->num_applications - || p_cur->cdma_subscription_app_index >= p_cur->num_applications - || p_cur->ims_subscription_app_index >= p_cur->num_applications) { - RLOGE("getIccCardStatusResponse: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - cardStatus.cardState = (CardState) p_cur->card_state; - cardStatus.universalPinState = (PinState) p_cur->universal_pin_state; - cardStatus.gsmUmtsSubscriptionAppIndex = p_cur->gsm_umts_subscription_app_index; - cardStatus.cdmaSubscriptionAppIndex = p_cur->cdma_subscription_app_index; - cardStatus.imsSubscriptionAppIndex = p_cur->ims_subscription_app_index; - - RIL_AppStatus *rilAppStatus = p_cur->applications; - cardStatus.applications.resize(p_cur->num_applications); - AppStatus *appStatus = cardStatus.applications.data(); -#if VDBG - RLOGD("getIccCardStatusResponse: num_applications %d", p_cur->num_applications); -#endif - for (int i = 0; i < p_cur->num_applications; i++) { - appStatus[i].appType = (AppType) rilAppStatus[i].app_type; - appStatus[i].appState = (AppState) rilAppStatus[i].app_state; - appStatus[i].persoSubstate = (PersoSubstate) rilAppStatus[i].perso_substate; - appStatus[i].aidPtr = convertCharPtrToHidlString(rilAppStatus[i].aid_ptr); - appStatus[i].appLabelPtr = convertCharPtrToHidlString( - rilAppStatus[i].app_label_ptr); - appStatus[i].pin1Replaced = rilAppStatus[i].pin1_replaced; - appStatus[i].pin1 = (PinState) rilAppStatus[i].pin1; - appStatus[i].pin2 = (PinState) rilAppStatus[i].pin2; - } - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - getIccCardStatusResponse(responseInfo, cardStatus); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getIccCardStatusResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::supplyIccPinForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("supplyIccPinForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - supplyIccPinForAppResponse(responseInfo, ret); - RLOGE("supplyIccPinForAppResponse: amit ret %d", ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("supplyIccPinForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::supplyIccPukForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("supplyIccPukForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse->supplyIccPukForAppResponse( - responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("supplyIccPukForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::supplyIccPin2ForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("supplyIccPin2ForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - supplyIccPin2ForAppResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("supplyIccPin2ForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::supplyIccPuk2ForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("supplyIccPuk2ForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - supplyIccPuk2ForAppResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("supplyIccPuk2ForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::changeIccPinForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("changeIccPinForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - changeIccPinForAppResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("changeIccPinForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::changeIccPin2ForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("changeIccPin2ForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - changeIccPin2ForAppResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("changeIccPin2ForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::supplyNetworkDepersonalizationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("supplyNetworkDepersonalizationResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - supplyNetworkDepersonalizationResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("supplyNetworkDepersonalizationResponse: radioService[%d]->mRadioResponse == " - "NULL", slotId); - } - - return 0; -} - -int radio::getCurrentCallsResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getCurrentCallsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - hidl_vec<Call> calls; - if ((response == NULL && responseLen != 0) - || (responseLen % sizeof(RIL_Call *)) != 0) { - RLOGE("getCurrentCallsResponse: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int num = responseLen / sizeof(RIL_Call *); - calls.resize(num); - - for (int i = 0 ; i < num ; i++) { - RIL_Call *p_cur = ((RIL_Call **) response)[i]; - /* each call info */ - calls[i].state = (CallState) p_cur->state; - calls[i].index = p_cur->index; - calls[i].toa = p_cur->toa; - calls[i].isMpty = p_cur->isMpty; - calls[i].isMT = p_cur->isMT; - calls[i].als = p_cur->als; - calls[i].isVoice = p_cur->isVoice; - calls[i].isVoicePrivacy = p_cur->isVoicePrivacy; - calls[i].number = convertCharPtrToHidlString(p_cur->number); - calls[i].numberPresentation = (CallPresentation) p_cur->numberPresentation; - calls[i].name = convertCharPtrToHidlString(p_cur->name); - calls[i].namePresentation = (CallPresentation) p_cur->namePresentation; - if (p_cur->uusInfo != NULL && p_cur->uusInfo->uusData != NULL) { - RIL_UUS_Info *uusInfo = p_cur->uusInfo; - calls[i].uusInfo.resize(1); - calls[i].uusInfo[0].uusType = (UusType) uusInfo->uusType; - calls[i].uusInfo[0].uusDcs = (UusDcs) uusInfo->uusDcs; - // convert uusInfo->uusData to a null-terminated string - char *nullTermStr = strndup(uusInfo->uusData, uusInfo->uusLength); - calls[i].uusInfo[0].uusData = nullTermStr; - free(nullTermStr); - } - } - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - getCurrentCallsResponse(responseInfo, calls); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getCurrentCallsResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::dialResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("dialResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->dialResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("dialResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getIMSIForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getIMSIForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->getIMSIForAppResponse( - responseInfo, convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getIMSIForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::hangupConnectionResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("hangupConnectionResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->hangupConnectionResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("hangupConnectionResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::hangupWaitingOrBackgroundResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("hangupWaitingOrBackgroundResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = - radioService[slotId]->mRadioResponse->hangupWaitingOrBackgroundResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("hangupWaitingOrBackgroundResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::hangupForegroundResumeBackgroundResponse(int slotId, int responseType, int serial, - RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("hangupWaitingOrBackgroundResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = - radioService[slotId]->mRadioResponse->hangupWaitingOrBackgroundResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("hangupWaitingOrBackgroundResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::switchWaitingOrHoldingAndActiveResponse(int slotId, int responseType, int serial, - RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("switchWaitingOrHoldingAndActiveResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = - radioService[slotId]->mRadioResponse->switchWaitingOrHoldingAndActiveResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("switchWaitingOrHoldingAndActiveResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::conferenceResponse(int slotId, int responseType, - int serial, RIL_Errno e, void *response, size_t responseLen) { -#if VDBG - RLOGD("conferenceResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->conferenceResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("conferenceResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::rejectCallResponse(int slotId, int responseType, - int serial, RIL_Errno e, void *response, size_t responseLen) { -#if VDBG - RLOGD("rejectCallResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->rejectCallResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("rejectCallResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getLastCallFailCauseResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getLastCallFailCauseResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - LastCallFailCauseInfo info = {}; - info.vendorCause = hidl_string(); - if (response == NULL) { - RLOGE("getCurrentCallsResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else if (responseLen == sizeof(int)) { - int *pInt = (int *) response; - info.causeCode = (LastCallFailCause) pInt[0]; - } else if (responseLen == sizeof(RIL_LastCallFailCauseInfo)) { - RIL_LastCallFailCauseInfo *pFailCauseInfo = (RIL_LastCallFailCauseInfo *) response; - info.causeCode = (LastCallFailCause) pFailCauseInfo->cause_code; - info.vendorCause = convertCharPtrToHidlString(pFailCauseInfo->vendor_cause); - } else { - RLOGE("getCurrentCallsResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->getLastCallFailCauseResponse( - responseInfo, info); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getLastCallFailCauseResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getSignalStrengthResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getSignalStrengthResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - SignalStrength signalStrength = {}; - if (response == NULL || responseLen != sizeof(RIL_SignalStrength_v10)) { - RLOGE("getSignalStrengthResponse: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - convertRilSignalStrengthToHal(response, responseLen, signalStrength); - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->getSignalStrengthResponse( - responseInfo, signalStrength); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getSignalStrengthResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -RIL_CellInfoType getCellInfoTypeRadioTechnology(char *rat) { - if (rat == NULL) { - return RIL_CELL_INFO_TYPE_NONE; - } - - int radioTech = atoi(rat); - - switch(radioTech) { - - case RADIO_TECH_GPRS: - case RADIO_TECH_EDGE: - case RADIO_TECH_GSM: { - return RIL_CELL_INFO_TYPE_GSM; - } - - case RADIO_TECH_UMTS: - case RADIO_TECH_HSDPA: - case RADIO_TECH_HSUPA: - case RADIO_TECH_HSPA: - case RADIO_TECH_HSPAP: { - return RIL_CELL_INFO_TYPE_WCDMA; - } - - case RADIO_TECH_IS95A: - case RADIO_TECH_IS95B: - case RADIO_TECH_1xRTT: - case RADIO_TECH_EVDO_0: - case RADIO_TECH_EVDO_A: - case RADIO_TECH_EVDO_B: - case RADIO_TECH_EHRPD: { - return RIL_CELL_INFO_TYPE_CDMA; - } - - case RADIO_TECH_LTE: - case RADIO_TECH_LTE_CA: { - return RIL_CELL_INFO_TYPE_LTE; - } - - case RADIO_TECH_TD_SCDMA: { - return RIL_CELL_INFO_TYPE_TD_SCDMA; - } - - default: { - break; - } - } - - return RIL_CELL_INFO_TYPE_NONE; - -} - -void fillCellIdentityResponse(CellIdentity &cellIdentity, RIL_CellIdentity_v16 &rilCellIdentity) { - - cellIdentity.cellIdentityGsm.resize(0); - cellIdentity.cellIdentityWcdma.resize(0); - cellIdentity.cellIdentityCdma.resize(0); - cellIdentity.cellIdentityTdscdma.resize(0); - cellIdentity.cellIdentityLte.resize(0); - cellIdentity.cellInfoType = (CellInfoType)rilCellIdentity.cellInfoType; - switch(rilCellIdentity.cellInfoType) { - - case RIL_CELL_INFO_TYPE_GSM: { - cellIdentity.cellIdentityGsm.resize(1); - cellIdentity.cellIdentityGsm[0].mcc = - ril::util::mcc::decode(rilCellIdentity.cellIdentityGsm.mcc); - cellIdentity.cellIdentityGsm[0].mnc = - ril::util::mnc::decode(rilCellIdentity.cellIdentityGsm.mnc); - - if (cellIdentity.cellIdentityGsm[0].mcc == "-1") { - cellIdentity.cellIdentityGsm[0].mcc = ""; - } - - cellIdentity.cellIdentityGsm[0].lac = rilCellIdentity.cellIdentityGsm.lac; - cellIdentity.cellIdentityGsm[0].cid = rilCellIdentity.cellIdentityGsm.cid; - cellIdentity.cellIdentityGsm[0].arfcn = rilCellIdentity.cellIdentityGsm.arfcn; - cellIdentity.cellIdentityGsm[0].bsic = rilCellIdentity.cellIdentityGsm.bsic; - break; - } - - case RIL_CELL_INFO_TYPE_WCDMA: { - cellIdentity.cellIdentityWcdma.resize(1); - cellIdentity.cellIdentityWcdma[0].mcc = - ril::util::mcc::decode(rilCellIdentity.cellIdentityWcdma.mcc); - cellIdentity.cellIdentityWcdma[0].mnc = - ril::util::mnc::decode(rilCellIdentity.cellIdentityWcdma.mnc); - - if (cellIdentity.cellIdentityWcdma[0].mcc == "-1") { - cellIdentity.cellIdentityWcdma[0].mcc = ""; - } - - cellIdentity.cellIdentityWcdma[0].lac = rilCellIdentity.cellIdentityWcdma.lac; - cellIdentity.cellIdentityWcdma[0].cid = rilCellIdentity.cellIdentityWcdma.cid; - cellIdentity.cellIdentityWcdma[0].psc = rilCellIdentity.cellIdentityWcdma.psc; - cellIdentity.cellIdentityWcdma[0].uarfcn = rilCellIdentity.cellIdentityWcdma.uarfcn; - break; - } - - case RIL_CELL_INFO_TYPE_CDMA: { - cellIdentity.cellIdentityCdma.resize(1); - cellIdentity.cellIdentityCdma[0].networkId = rilCellIdentity.cellIdentityCdma.networkId; - cellIdentity.cellIdentityCdma[0].systemId = rilCellIdentity.cellIdentityCdma.systemId; - cellIdentity.cellIdentityCdma[0].baseStationId = - rilCellIdentity.cellIdentityCdma.basestationId; - cellIdentity.cellIdentityCdma[0].longitude = rilCellIdentity.cellIdentityCdma.longitude; - cellIdentity.cellIdentityCdma[0].latitude = rilCellIdentity.cellIdentityCdma.latitude; - break; - } - - case RIL_CELL_INFO_TYPE_LTE: { - cellIdentity.cellIdentityLte.resize(1); - cellIdentity.cellIdentityLte[0].mcc = - ril::util::mcc::decode(rilCellIdentity.cellIdentityLte.mcc); - cellIdentity.cellIdentityLte[0].mnc = - ril::util::mnc::decode(rilCellIdentity.cellIdentityLte.mnc); - - if (cellIdentity.cellIdentityLte[0].mcc == "-1") { - cellIdentity.cellIdentityLte[0].mcc = ""; - } - - cellIdentity.cellIdentityLte[0].ci = rilCellIdentity.cellIdentityLte.ci; - cellIdentity.cellIdentityLte[0].pci = rilCellIdentity.cellIdentityLte.pci; - cellIdentity.cellIdentityLte[0].tac = rilCellIdentity.cellIdentityLte.tac; - cellIdentity.cellIdentityLte[0].earfcn = rilCellIdentity.cellIdentityLte.earfcn; - break; - } - - case RIL_CELL_INFO_TYPE_TD_SCDMA: { - cellIdentity.cellIdentityTdscdma.resize(1); - cellIdentity.cellIdentityTdscdma[0].mcc = - ril::util::mcc::decode(rilCellIdentity.cellIdentityTdscdma.mcc); - cellIdentity.cellIdentityTdscdma[0].mnc = - ril::util::mnc::decode(rilCellIdentity.cellIdentityTdscdma.mnc); - - if (cellIdentity.cellIdentityTdscdma[0].mcc == "-1") { - cellIdentity.cellIdentityTdscdma[0].mcc = ""; - } - - cellIdentity.cellIdentityTdscdma[0].lac = rilCellIdentity.cellIdentityTdscdma.lac; - cellIdentity.cellIdentityTdscdma[0].cid = rilCellIdentity.cellIdentityTdscdma.cid; - cellIdentity.cellIdentityTdscdma[0].cpid = rilCellIdentity.cellIdentityTdscdma.cpid; - break; - } - - default: { - break; - } - } -} - -int convertResponseStringEntryToInt(char **response, int index, int numStrings) { - if ((response != NULL) && (numStrings > index) && (response[index] != NULL)) { - return atoi(response[index]); - } - - return -1; -} - -int convertResponseHexStringEntryToInt(char **response, int index, int numStrings) { - const int hexBase = 16; - if ((response != NULL) && (numStrings > index) && (response[index] != NULL)) { - return strtol(response[index], NULL, hexBase); - } - - return -1; -} - -/* Fill Cell Identity info from Voice Registration State Response. - * This fucntion is applicable only for RIL Version < 15. - * Response is a "char **". - * First and Second entries are in hex string format - * and rest are integers represented in ascii format. */ -void fillCellIdentityFromVoiceRegStateResponseString(CellIdentity &cellIdentity, - int numStrings, char** response) { - - RIL_CellIdentity_v16 rilCellIdentity; - memset(&rilCellIdentity, -1, sizeof(RIL_CellIdentity_v16)); - - rilCellIdentity.cellInfoType = getCellInfoTypeRadioTechnology(response[3]); - switch(rilCellIdentity.cellInfoType) { - - case RIL_CELL_INFO_TYPE_GSM: { - /* valid LAC are hexstrings in the range 0x0000 - 0xffff */ - rilCellIdentity.cellIdentityGsm.lac = - convertResponseHexStringEntryToInt(response, 1, numStrings); - - /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */ - rilCellIdentity.cellIdentityGsm.cid = - convertResponseHexStringEntryToInt(response, 2, numStrings); - break; - } - - case RIL_CELL_INFO_TYPE_WCDMA: { - /* valid LAC are hexstrings in the range 0x0000 - 0xffff */ - rilCellIdentity.cellIdentityWcdma.lac = - convertResponseHexStringEntryToInt(response, 1, numStrings); - - /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */ - rilCellIdentity.cellIdentityWcdma.cid = - convertResponseHexStringEntryToInt(response, 2, numStrings); - rilCellIdentity.cellIdentityWcdma.psc = - convertResponseStringEntryToInt(response, 14, numStrings); - break; - } - - case RIL_CELL_INFO_TYPE_TD_SCDMA:{ - /* valid LAC are hexstrings in the range 0x0000 - 0xffff */ - rilCellIdentity.cellIdentityTdscdma.lac = - convertResponseHexStringEntryToInt(response, 1, numStrings); - - /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */ - rilCellIdentity.cellIdentityTdscdma.cid = - convertResponseHexStringEntryToInt(response, 2, numStrings); - break; - } - - case RIL_CELL_INFO_TYPE_CDMA:{ - rilCellIdentity.cellIdentityCdma.basestationId = - convertResponseStringEntryToInt(response, 4, numStrings); - /* Order of Lat. and Long. swapped between RIL and HIDL interface versions. */ - rilCellIdentity.cellIdentityCdma.latitude = - convertResponseStringEntryToInt(response, 5, numStrings); - rilCellIdentity.cellIdentityCdma.longitude = - convertResponseStringEntryToInt(response, 6, numStrings); - rilCellIdentity.cellIdentityCdma.systemId = - convertResponseStringEntryToInt(response, 8, numStrings); - rilCellIdentity.cellIdentityCdma.networkId = - convertResponseStringEntryToInt(response, 9, numStrings); - break; - } - - case RIL_CELL_INFO_TYPE_LTE:{ - /* valid TAC are hexstrings in the range 0x0000 - 0xffff */ - rilCellIdentity.cellIdentityLte.tac = - convertResponseHexStringEntryToInt(response, 1, numStrings); - - /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */ - rilCellIdentity.cellIdentityLte.ci = - convertResponseHexStringEntryToInt(response, 2, numStrings); - break; - } - - default: { - break; - } - } - - fillCellIdentityResponse(cellIdentity, rilCellIdentity); -} - -/* Fill Cell Identity info from Data Registration State Response. - * This fucntion is applicable only for RIL Version < 15. - * Response is a "char **". - * First and Second entries are in hex string format - * and rest are integers represented in ascii format. */ -void fillCellIdentityFromDataRegStateResponseString(CellIdentity &cellIdentity, - int numStrings, char** response) { - - RIL_CellIdentity_v16 rilCellIdentity; - memset(&rilCellIdentity, -1, sizeof(RIL_CellIdentity_v16)); - - rilCellIdentity.cellInfoType = getCellInfoTypeRadioTechnology(response[3]); - switch(rilCellIdentity.cellInfoType) { - case RIL_CELL_INFO_TYPE_GSM: { - /* valid LAC are hexstrings in the range 0x0000 - 0xffff */ - rilCellIdentity.cellIdentityGsm.lac = - convertResponseHexStringEntryToInt(response, 1, numStrings); - - /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */ - rilCellIdentity.cellIdentityGsm.cid = - convertResponseHexStringEntryToInt(response, 2, numStrings); - - if (numStrings >= 13) { - rilCellIdentity.cellIdentityGsm.mcc = - convertResponseStringEntryToInt(response, 11, numStrings); - - rilCellIdentity.cellIdentityGsm.mnc = - convertResponseStringEntryToInt(response, 12, numStrings); - } - break; - } - case RIL_CELL_INFO_TYPE_WCDMA: { - /* valid LAC are hexstrings in the range 0x0000 - 0xffff */ - rilCellIdentity.cellIdentityWcdma.lac = - convertResponseHexStringEntryToInt(response, 1, numStrings); - - /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */ - rilCellIdentity.cellIdentityWcdma.cid = - convertResponseHexStringEntryToInt(response, 2, numStrings); - - if (numStrings >= 13) { - rilCellIdentity.cellIdentityWcdma.mcc = - convertResponseStringEntryToInt(response, 11, numStrings); - - rilCellIdentity.cellIdentityWcdma.mnc = - convertResponseStringEntryToInt(response, 12, numStrings); - } - break; - } - case RIL_CELL_INFO_TYPE_TD_SCDMA:{ - /* valid LAC are hexstrings in the range 0x0000 - 0xffff */ - rilCellIdentity.cellIdentityTdscdma.lac = - convertResponseHexStringEntryToInt(response, 1, numStrings); - - /* valid CID are hexstrings in the range 0x00000000 - 0xffffffff */ - rilCellIdentity.cellIdentityTdscdma.cid = - convertResponseHexStringEntryToInt(response, 2, numStrings); - - if (numStrings >= 13) { - rilCellIdentity.cellIdentityTdscdma.mcc = - convertResponseStringEntryToInt(response, 11, numStrings); - - rilCellIdentity.cellIdentityTdscdma.mnc = - convertResponseStringEntryToInt(response, 12, numStrings); - } - break; - } - case RIL_CELL_INFO_TYPE_LTE: { - rilCellIdentity.cellIdentityLte.tac = - convertResponseStringEntryToInt(response, 6, numStrings); - rilCellIdentity.cellIdentityLte.pci = - convertResponseStringEntryToInt(response, 7, numStrings); - rilCellIdentity.cellIdentityLte.ci = - convertResponseStringEntryToInt(response, 8, numStrings); - - if (numStrings >= 13) { - rilCellIdentity.cellIdentityLte.mcc = - convertResponseStringEntryToInt(response, 11, numStrings); - - rilCellIdentity.cellIdentityLte.mnc = - convertResponseStringEntryToInt(response, 12, numStrings); - } - break; - } - default: { - break; - } - } - - fillCellIdentityResponse(cellIdentity, rilCellIdentity); -} - -int radio::getVoiceRegistrationStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getVoiceRegistrationStateResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - VoiceRegStateResult voiceRegResponse = {}; - int numStrings = responseLen / sizeof(char *); - if (response == NULL) { - RLOGE("getVoiceRegistrationStateResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else if (s_vendorFunctions->version <= 14) { - if (numStrings != 15) { - RLOGE("getVoiceRegistrationStateResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - char **resp = (char **) response; - voiceRegResponse.regState = (RegState) ATOI_NULL_HANDLED_DEF(resp[0], 4); - voiceRegResponse.rat = ATOI_NULL_HANDLED(resp[3]); - voiceRegResponse.cssSupported = ATOI_NULL_HANDLED_DEF(resp[7], 0); - voiceRegResponse.roamingIndicator = ATOI_NULL_HANDLED(resp[10]); - voiceRegResponse.systemIsInPrl = ATOI_NULL_HANDLED_DEF(resp[11], 0); - voiceRegResponse.defaultRoamingIndicator = ATOI_NULL_HANDLED_DEF(resp[12], 0); - voiceRegResponse.reasonForDenial = ATOI_NULL_HANDLED_DEF(resp[13], 0); - fillCellIdentityFromVoiceRegStateResponseString(voiceRegResponse.cellIdentity, - numStrings, resp); - } - } else { - RIL_VoiceRegistrationStateResponse *voiceRegState = - (RIL_VoiceRegistrationStateResponse *)response; - - if (responseLen != sizeof(RIL_VoiceRegistrationStateResponse)) { - RLOGE("getVoiceRegistrationStateResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - voiceRegResponse.regState = (RegState) voiceRegState->regState; - voiceRegResponse.rat = voiceRegState->rat;; - voiceRegResponse.cssSupported = voiceRegState->cssSupported; - voiceRegResponse.roamingIndicator = voiceRegState->roamingIndicator; - voiceRegResponse.systemIsInPrl = voiceRegState->systemIsInPrl; - voiceRegResponse.defaultRoamingIndicator = voiceRegState->defaultRoamingIndicator; - voiceRegResponse.reasonForDenial = voiceRegState->reasonForDenial; - fillCellIdentityResponse(voiceRegResponse.cellIdentity, - voiceRegState->cellIdentity); - } - } - - Return<void> retStatus = - radioService[slotId]->mRadioResponse->getVoiceRegistrationStateResponse( - responseInfo, voiceRegResponse); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getVoiceRegistrationStateResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getDataRegistrationStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getDataRegistrationStateResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - DataRegStateResult dataRegResponse = {}; - if (response == NULL) { - RLOGE("getDataRegistrationStateResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else if (s_vendorFunctions->version <= 14) { - int numStrings = responseLen / sizeof(char *); - if ((numStrings != 6) && (numStrings != 11) && (numStrings != 13)) { - RLOGE("getDataRegistrationStateResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - char **resp = (char **) response; - dataRegResponse.regState = (RegState) ATOI_NULL_HANDLED_DEF(resp[0], 4); - dataRegResponse.rat = ATOI_NULL_HANDLED_DEF(resp[3], 0); - dataRegResponse.reasonDataDenied = ATOI_NULL_HANDLED(resp[4]); - dataRegResponse.maxDataCalls = ATOI_NULL_HANDLED_DEF(resp[5], 1); - fillCellIdentityFromDataRegStateResponseString(dataRegResponse.cellIdentity, numStrings, resp); - - if (radioService[slotId]->mRadioResponseV1_4 != NULL) { - DataRegStateResultV1_4 dataRegResponse14 = {}; - dataRegResponse14.base.regState = - (RegState)ATOI_NULL_HANDLED_DEF(resp[0], 4); - dataRegResponse14.base.rat = - ATOI_NULL_HANDLED_DEF(resp[3], 0); - dataRegResponse14.base.reasonDataDenied = - ATOI_NULL_HANDLED(resp[4]); - dataRegResponse14.base.maxDataCalls = - ATOI_NULL_HANDLED_DEF(resp[5], 1); - dataRegResponse14.base.cellIdentity.cellInfoType = dataRegResponse.cellIdentity.cellInfoType; - //const bool enableNR = (dataRegResponse14.base.rat == (int)android::hardware::radio::V1_4::RadioTechnology::LTE); - const bool enableNR = (dataRegResponse14.base.rat == (int)android::hardware::radio::V1_4::RadioTechnology::NR); - - dataRegResponse14.nrIndicators.isEndcAvailable = enableNR ? 1 : 0; - dataRegResponse14.nrIndicators.isDcNrRestricted = enableNR ? 0 : 1; - dataRegResponse14.nrIndicators.isNrAvailable = enableNR ? 1 : 0; - // override the NR: note, at the moment, NR_SA is not common, so switch to - // NR_NSA(on top of LTE) - if (enableNR) { - dataRegResponse14.base.rat = (int)android::hardware::radio::V1_4::RadioTechnology::LTE_CA; - } - if (enableNR) { - RLOGD("getDataRegistrationStateResponse enabled 5g"); - } else { - RLOGD("getDataRegistrationStateResponse disable 5g"); - } - Return<void> retStatus = - radioService[slotId] - ->mRadioResponseV1_4 - ->getDataRegistrationStateResponse_1_4( - responseInfo, dataRegResponse14); - radioService[slotId]->checkReturnStatus(retStatus); - return 0; - } - } - } else { - RIL_DataRegistrationStateResponse *dataRegState = - (RIL_DataRegistrationStateResponse *)response; - - if (responseLen != sizeof(RIL_DataRegistrationStateResponse)) { - RLOGE("getDataRegistrationStateResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - dataRegResponse.regState = (RegState) dataRegState->regState; - dataRegResponse.rat = dataRegState->rat;; - dataRegResponse.reasonDataDenied = dataRegState->reasonDataDenied; - dataRegResponse.maxDataCalls = dataRegState->maxDataCalls; - fillCellIdentityResponse(dataRegResponse.cellIdentity, dataRegState->cellIdentity); - } - } - - Return<void> retStatus = - radioService[slotId]->mRadioResponse->getDataRegistrationStateResponse(responseInfo, - dataRegResponse); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getDataRegistrationStateResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getOperatorResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getOperatorResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_string longName; - hidl_string shortName; - hidl_string numeric; - int numStrings = responseLen / sizeof(char *); - if (response == NULL || numStrings != 3) { - RLOGE("getOperatorResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - - } else { - char **resp = (char **) response; - longName = convertCharPtrToHidlString(resp[0]); - shortName = convertCharPtrToHidlString(resp[1]); - numeric = convertCharPtrToHidlString(resp[2]); - } - Return<void> retStatus = radioService[slotId]->mRadioResponse->getOperatorResponse( - responseInfo, longName, shortName, numeric); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getOperatorResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setRadioPowerResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { - RLOGD("setRadioPowerResponse: serial %d", serial); - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->setRadioPowerResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setRadioPowerResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::sendDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("sendDtmfResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->sendDtmfResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendDtmfResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -SendSmsResult makeSendSmsResult(RadioResponseInfo& responseInfo, int serial, int responseType, - RIL_Errno e, void *response, size_t responseLen) { - populateResponseInfo(responseInfo, serial, responseType, e); - SendSmsResult result = {}; - - if (response == NULL || responseLen != sizeof(RIL_SMS_Response)) { - RLOGE("Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - result.ackPDU = hidl_string(); - } else { - RIL_SMS_Response *resp = (RIL_SMS_Response *) response; - result.messageRef = resp->messageRef; - result.ackPDU = convertCharPtrToHidlString(resp->ackPDU); - result.errorCode = resp->errorCode; - } - return result; -} - -int radio::sendSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("sendSmsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus = radioService[slotId]->mRadioResponse->sendSmsResponse(responseInfo, - result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendSmsResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::sendSMSExpectMoreResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("sendSMSExpectMoreResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus = radioService[slotId]->mRadioResponse->sendSMSExpectMoreResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendSMSExpectMoreResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setupDataCallResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("setupDataCallResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - SetupDataCallResult result = {}; - if (response == NULL || (responseLen % sizeof(RIL_Data_Call_Response_v11)) != 0) { - if (response != NULL) { - RLOGE("setupDataCallResponse: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } - result.status = DataCallFailCause::ERROR_UNSPECIFIED; - result.type = hidl_string(); - result.ifname = hidl_string(); - result.addresses = hidl_string(); - result.dnses = hidl_string(); - result.gateways = hidl_string(); - result.pcscf = hidl_string(); - } else { - convertRilDataCallToHal((RIL_Data_Call_Response_v11 *) response, result); - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->setupDataCallResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setupDataCallResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -IccIoResult responseIccIo(RadioResponseInfo& responseInfo, int serial, int responseType, - RIL_Errno e, void *response, size_t responseLen) { - populateResponseInfo(responseInfo, serial, responseType, e); - IccIoResult result = {}; - - if (response == NULL || responseLen != sizeof(RIL_SIM_IO_Response)) { - RLOGE("Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - result.simResponse = hidl_string(); - } else { - RIL_SIM_IO_Response *resp = (RIL_SIM_IO_Response *) response; - result.sw1 = resp->sw1; - result.sw2 = resp->sw2; - result.simResponse = convertCharPtrToHidlString(resp->simResponse); - } - return result; -} - -int radio::iccIOForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("iccIOForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus = radioService[slotId]->mRadioResponse->iccIOForAppResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("iccIOForAppResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::sendUssdResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("sendUssdResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->sendUssdResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendUssdResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::cancelPendingUssdResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("cancelPendingUssdResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->cancelPendingUssdResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cancelPendingUssdResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getClirResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getClirResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - int n = -1, m = -1; - int numInts = responseLen / sizeof(int); - if (response == NULL || numInts != 2) { - RLOGE("getClirResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *pInt = (int *) response; - n = pInt[0]; - m = pInt[1]; - } - Return<void> retStatus = radioService[slotId]->mRadioResponse->getClirResponse(responseInfo, - n, m); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getClirResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setClirResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("setClirResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->setClirResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setClirResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getCallForwardStatusResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getCallForwardStatusResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<CallForwardInfo> callForwardInfos; - - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_CallForwardInfo *) != 0) { - RLOGE("getCallForwardStatusResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int num = responseLen / sizeof(RIL_CallForwardInfo *); - callForwardInfos.resize(num); - for (int i = 0 ; i < num; i++) { - RIL_CallForwardInfo *resp = ((RIL_CallForwardInfo **) response)[i]; - callForwardInfos[i].status = (CallForwardInfoStatus) resp->status; - callForwardInfos[i].reason = resp->reason; - callForwardInfos[i].serviceClass = resp->serviceClass; - callForwardInfos[i].toa = resp->toa; - callForwardInfos[i].number = convertCharPtrToHidlString(resp->number); - callForwardInfos[i].timeSeconds = resp->timeSeconds; - } - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->getCallForwardStatusResponse( - responseInfo, callForwardInfos); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getCallForwardStatusResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setCallForwardResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("setCallForwardResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->setCallForwardResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCallForwardResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getCallWaitingResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getCallWaitingResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - bool enable = false; - int serviceClass = -1; - int numInts = responseLen / sizeof(int); - if (response == NULL || numInts != 2) { - RLOGE("getCallWaitingResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *pInt = (int *) response; - enable = pInt[0] == 1 ? true : false; - serviceClass = pInt[1]; - } - Return<void> retStatus = radioService[slotId]->mRadioResponse->getCallWaitingResponse( - responseInfo, enable, serviceClass); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getCallWaitingResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setCallWaitingResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("setCallWaitingResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->setCallWaitingResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCallWaitingResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::acknowledgeLastIncomingGsmSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("acknowledgeLastIncomingGsmSmsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = - radioService[slotId]->mRadioResponse->acknowledgeLastIncomingGsmSmsResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("acknowledgeLastIncomingGsmSmsResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::acceptCallResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("acceptCallResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->acceptCallResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("acceptCallResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::deactivateDataCallResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("deactivateDataCallResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->deactivateDataCallResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("deactivateDataCallResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getFacilityLockForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getFacilityLockForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - getFacilityLockForAppResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getFacilityLockForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setFacilityLockForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setFacilityLockForAppResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseIntOrEmpty(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setFacilityLockForAppResponse(responseInfo, - ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setFacilityLockForAppResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setBarringPasswordResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("acceptCallResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setBarringPasswordResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setBarringPasswordResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getNetworkSelectionModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getNetworkSelectionModeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - bool manual = false; - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("getNetworkSelectionModeResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *pInt = (int *) response; - manual = pInt[0] == 1 ? true : false; - } - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getNetworkSelectionModeResponse( - responseInfo, - manual); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getNetworkSelectionModeResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setNetworkSelectionModeAutomaticResponse(int slotId, int responseType, int serial, - RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("setNetworkSelectionModeAutomaticResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setNetworkSelectionModeAutomaticResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setNetworkSelectionModeAutomaticResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::setNetworkSelectionModeManualResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setNetworkSelectionModeManualResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setNetworkSelectionModeManualResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("acceptCallResponse: radioService[%d]->setNetworkSelectionModeManualResponse " - "== NULL", slotId); - } - - return 0; -} - -int convertOperatorStatusToInt(const char *str) { - if (strncmp("unknown", str, 9) == 0) { - return (int) OperatorStatus::UNKNOWN; - } else if (strncmp("available", str, 9) == 0) { - return (int) OperatorStatus::AVAILABLE; - } else if (strncmp("current", str, 9) == 0) { - return (int) OperatorStatus::CURRENT; - } else if (strncmp("forbidden", str, 9) == 0) { - return (int) OperatorStatus::FORBIDDEN; - } else { - return -1; - } -} - -int radio::getAvailableNetworksResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getAvailableNetworksResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<OperatorInfo> networks; - if ((response == NULL && responseLen != 0) - || responseLen % (4 * sizeof(char *))!= 0) { - RLOGE("getAvailableNetworksResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - char **resp = (char **) response; - int numStrings = responseLen / sizeof(char *); - networks.resize(numStrings/4); - for (int i = 0, j = 0; i < numStrings; i = i + 4, j++) { - networks[j].alphaLong = convertCharPtrToHidlString(resp[i]); - networks[j].alphaShort = convertCharPtrToHidlString(resp[i + 1]); - networks[j].operatorNumeric = convertCharPtrToHidlString(resp[i + 2]); - int status = convertOperatorStatusToInt(resp[i + 3]); - if (status == -1) { - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - networks[j].status = (OperatorStatus) status; - } - } - } - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getAvailableNetworksResponse(responseInfo, - networks); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getAvailableNetworksResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::startDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("startDtmfResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->startDtmfResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("startDtmfResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::stopDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("stopDtmfResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->stopDtmfResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stopDtmfResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getBasebandVersionResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getBasebandVersionResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getBasebandVersionResponse(responseInfo, - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getBasebandVersionResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::separateConnectionResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("separateConnectionResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->separateConnectionResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("separateConnectionResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setMuteResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setMuteResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setMuteResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setMuteResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getMuteResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getMuteResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - bool enable = false; - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("getMuteResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *pInt = (int *) response; - enable = pInt[0] == 1 ? true : false; - } - Return<void> retStatus = radioService[slotId]->mRadioResponse->getMuteResponse(responseInfo, - enable); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getMuteResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getClipResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getClipResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus = radioService[slotId]->mRadioResponse->getClipResponse(responseInfo, - (ClipStatus) ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getClipResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getDataCallListResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getDataCallListResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - hidl_vec<SetupDataCallResult> ret; - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_Data_Call_Response_v11) != 0) { - RLOGE("getDataCallListResponse: invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - convertRilDataCallListToHal(response, responseLen, ret); - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->getDataCallListResponse( - responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getDataCallListResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setSuppServiceNotificationsResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setSuppServiceNotificationsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setSuppServiceNotificationsResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setSuppServiceNotificationsResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::deleteSmsOnSimResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("deleteSmsOnSimResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->deleteSmsOnSimResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("deleteSmsOnSimResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setBandModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setBandModeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setBandModeResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setBandModeResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::writeSmsToSimResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("writeSmsToSimResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->writeSmsToSimResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("writeSmsToSimResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getAvailableBandModesResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getAvailableBandModesResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<RadioBandMode> modes; - if ((response == NULL && responseLen != 0)|| responseLen % sizeof(int) != 0) { - RLOGE("getAvailableBandModesResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *pInt = (int *) response; - int numInts = responseLen / sizeof(int); - modes.resize(numInts); - for (int i = 0; i < numInts; i++) { - modes[i] = (RadioBandMode) pInt[i]; - } - } - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getAvailableBandModesResponse(responseInfo, - modes); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getAvailableBandModesResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::sendEnvelopeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("sendEnvelopeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendEnvelopeResponse(responseInfo, - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendEnvelopeResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::sendTerminalResponseToSimResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("sendTerminalResponseToSimResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendTerminalResponseToSimResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendTerminalResponseToSimResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::handleStkCallSetupRequestFromSimResponse(int slotId, - int responseType, int serial, - RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("handleStkCallSetupRequestFromSimResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->handleStkCallSetupRequestFromSimResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("handleStkCallSetupRequestFromSimResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::explicitCallTransferResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("explicitCallTransferResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->explicitCallTransferResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("explicitCallTransferResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setPreferredNetworkTypeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setPreferredNetworkTypeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setPreferredNetworkTypeResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setPreferredNetworkTypeResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - - -int radio::getPreferredNetworkTypeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getPreferredNetworkTypeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getPreferredNetworkTypeResponse( - responseInfo, (PreferredNetworkType) ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getPreferredNetworkTypeResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getNeighboringCidsResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getNeighboringCidsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<NeighboringCell> cells; - - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_NeighboringCell *) != 0) { - RLOGE("getNeighboringCidsResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int num = responseLen / sizeof(RIL_NeighboringCell *); - cells.resize(num); - for (int i = 0 ; i < num; i++) { - RIL_NeighboringCell *resp = ((RIL_NeighboringCell **) response)[i]; - cells[i].cid = convertCharPtrToHidlString(resp->cid); - cells[i].rssi = resp->rssi; - } - } - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getNeighboringCidsResponse(responseInfo, - cells); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getNeighboringCidsResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setLocationUpdatesResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setLocationUpdatesResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setLocationUpdatesResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setLocationUpdatesResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setCdmaSubscriptionSourceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setCdmaSubscriptionSourceResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setCdmaSubscriptionSourceResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCdmaSubscriptionSourceResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setCdmaRoamingPreferenceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setCdmaRoamingPreferenceResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setCdmaRoamingPreferenceResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCdmaRoamingPreferenceResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getCdmaRoamingPreferenceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getCdmaRoamingPreferenceResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getCdmaRoamingPreferenceResponse( - responseInfo, (CdmaRoamingType) ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getCdmaRoamingPreferenceResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setTTYModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setTTYModeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setTTYModeResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setTTYModeResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getTTYModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getTTYModeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getTTYModeResponse(responseInfo, - (TtyMode) ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getTTYModeResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setPreferredVoicePrivacyResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setPreferredVoicePrivacyResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setPreferredVoicePrivacyResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setPreferredVoicePrivacyResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getPreferredVoicePrivacyResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getPreferredVoicePrivacyResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - bool enable = false; - int numInts = responseLen / sizeof(int); - if (response == NULL || numInts != 1) { - RLOGE("getPreferredVoicePrivacyResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *pInt = (int *) response; - enable = pInt[0] == 1 ? true : false; - } - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getPreferredVoicePrivacyResponse( - responseInfo, enable); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getPreferredVoicePrivacyResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::sendCDMAFeatureCodeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("sendCDMAFeatureCodeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendCDMAFeatureCodeResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendCDMAFeatureCodeResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::sendBurstDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("sendBurstDtmfResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendBurstDtmfResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendBurstDtmfResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::sendCdmaSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("sendCdmaSmsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendCdmaSmsResponse(responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendCdmaSmsResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::acknowledgeLastIncomingCdmaSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("acknowledgeLastIncomingCdmaSmsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->acknowledgeLastIncomingCdmaSmsResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("acknowledgeLastIncomingCdmaSmsResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::getGsmBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getGsmBroadcastConfigResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<GsmBroadcastSmsConfigInfo> configs; - - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_GSM_BroadcastSmsConfigInfo *) != 0) { - RLOGE("getGsmBroadcastConfigResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int num = responseLen / sizeof(RIL_GSM_BroadcastSmsConfigInfo *); - configs.resize(num); - for (int i = 0 ; i < num; i++) { - RIL_GSM_BroadcastSmsConfigInfo *resp = - ((RIL_GSM_BroadcastSmsConfigInfo **) response)[i]; - configs[i].fromServiceId = resp->fromServiceId; - configs[i].toServiceId = resp->toServiceId; - configs[i].fromCodeScheme = resp->fromCodeScheme; - configs[i].toCodeScheme = resp->toCodeScheme; - configs[i].selected = resp->selected == 1 ? true : false; - } - } - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getGsmBroadcastConfigResponse(responseInfo, - configs); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getGsmBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setGsmBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setGsmBroadcastConfigResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setGsmBroadcastConfigResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setGsmBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setGsmBroadcastActivationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setGsmBroadcastActivationResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setGsmBroadcastActivationResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setGsmBroadcastActivationResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getCdmaBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getCdmaBroadcastConfigResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<CdmaBroadcastSmsConfigInfo> configs; - - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_CDMA_BroadcastSmsConfigInfo *) != 0) { - RLOGE("getCdmaBroadcastConfigResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int num = responseLen / sizeof(RIL_CDMA_BroadcastSmsConfigInfo *); - configs.resize(num); - for (int i = 0 ; i < num; i++) { - RIL_CDMA_BroadcastSmsConfigInfo *resp = - ((RIL_CDMA_BroadcastSmsConfigInfo **) response)[i]; - configs[i].serviceCategory = resp->service_category; - configs[i].language = resp->language; - configs[i].selected = resp->selected == 1 ? true : false; - } - } - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getCdmaBroadcastConfigResponse(responseInfo, - configs); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getCdmaBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setCdmaBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setCdmaBroadcastConfigResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setCdmaBroadcastConfigResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCdmaBroadcastConfigResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setCdmaBroadcastActivationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setCdmaBroadcastActivationResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setCdmaBroadcastActivationResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCdmaBroadcastActivationResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getCDMASubscriptionResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getCDMASubscriptionResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - int numStrings = responseLen / sizeof(char *); - hidl_string emptyString; - if (response == NULL || numStrings != 5) { - RLOGE("getOperatorResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getCDMASubscriptionResponse( - responseInfo, emptyString, emptyString, emptyString, emptyString, emptyString); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - char **resp = (char **) response; - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getCDMASubscriptionResponse( - responseInfo, - convertCharPtrToHidlString(resp[0]), - convertCharPtrToHidlString(resp[1]), - convertCharPtrToHidlString(resp[2]), - convertCharPtrToHidlString(resp[3]), - convertCharPtrToHidlString(resp[4])); - radioService[slotId]->checkReturnStatus(retStatus); - } - } else { - RLOGE("getCDMASubscriptionResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::writeSmsToRuimResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("writeSmsToRuimResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->writeSmsToRuimResponse(responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("writeSmsToRuimResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::deleteSmsOnRuimResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("deleteSmsOnRuimResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->deleteSmsOnRuimResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("deleteSmsOnRuimResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getDeviceIdentityResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getDeviceIdentityResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - int numStrings = responseLen / sizeof(char *); - hidl_string emptyString; - if (response == NULL || numStrings != 4) { - RLOGE("getDeviceIdentityResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getDeviceIdentityResponse(responseInfo, - emptyString, emptyString, emptyString, emptyString); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - char **resp = (char **) response; - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getDeviceIdentityResponse(responseInfo, - convertCharPtrToHidlString(resp[0]), - convertCharPtrToHidlString(resp[1]), - convertCharPtrToHidlString(resp[2]), - convertCharPtrToHidlString(resp[3])); - radioService[slotId]->checkReturnStatus(retStatus); - } - } else { - RLOGE("getDeviceIdentityResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::exitEmergencyCallbackModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("exitEmergencyCallbackModeResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->exitEmergencyCallbackModeResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("exitEmergencyCallbackModeResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getSmscAddressResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getSmscAddressResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getSmscAddressResponse(responseInfo, - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getSmscAddressResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setSmscAddressResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setSmscAddressResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setSmscAddressResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setSmscAddressResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::reportSmsMemoryStatusResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("reportSmsMemoryStatusResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->reportSmsMemoryStatusResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("reportSmsMemoryStatusResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::reportStkServiceIsRunningResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("reportStkServiceIsRunningResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse-> - reportStkServiceIsRunningResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("reportStkServiceIsRunningResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getCdmaSubscriptionSourceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getCdmaSubscriptionSourceResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getCdmaSubscriptionSourceResponse( - responseInfo, (CdmaSubscriptionSource) ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getCdmaSubscriptionSourceResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::requestIsimAuthenticationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("requestIsimAuthenticationResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->requestIsimAuthenticationResponse( - responseInfo, - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("requestIsimAuthenticationResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::acknowledgeIncomingGsmSmsWithPduResponse(int slotId, - int responseType, - int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("acknowledgeIncomingGsmSmsWithPduResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->acknowledgeIncomingGsmSmsWithPduResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("acknowledgeIncomingGsmSmsWithPduResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::sendEnvelopeWithStatusResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("sendEnvelopeWithStatusResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, - response, responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendEnvelopeWithStatusResponse(responseInfo, - result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendEnvelopeWithStatusResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getVoiceRadioTechnologyResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getVoiceRadioTechnologyResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getVoiceRadioTechnologyResponse( - responseInfo, (RadioTechnology) ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getVoiceRadioTechnologyResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getCellInfoListResponse(int slotId, - int responseType, - int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("getCellInfoListResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - hidl_vec<CellInfo> ret; - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_CellInfo_v12) != 0) { - RLOGE("getCellInfoListResponse: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - convertRilCellInfoListToHal(response, responseLen, ret); - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->getCellInfoListResponse( - responseInfo, ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getCellInfoListResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setCellInfoListRateResponse(int slotId, - int responseType, - int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("setCellInfoListRateResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setCellInfoListRateResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCellInfoListRateResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setInitialAttachApnResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setInitialAttachApnResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setInitialAttachApnResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setInitialAttachApnResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getImsRegistrationStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getImsRegistrationStateResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - bool isRegistered = false; - int ratFamily = 0; - int numInts = responseLen / sizeof(int); - if (response == NULL || numInts != 2) { - RLOGE("getImsRegistrationStateResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - int *pInt = (int *) response; - isRegistered = pInt[0] == 1 ? true : false; - ratFamily = pInt[1]; - } - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getImsRegistrationStateResponse( - responseInfo, isRegistered, (RadioTechnologyFamily) ratFamily); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getImsRegistrationStateResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::sendImsSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("sendImsSmsResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - SendSmsResult result = makeSendSmsResult(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendImsSmsResponse(responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendSmsResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::iccTransmitApduBasicChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("iccTransmitApduBasicChannelResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->iccTransmitApduBasicChannelResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("iccTransmitApduBasicChannelResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::iccOpenLogicalChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("iccOpenLogicalChannelResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - int channelId = -1; - hidl_vec<int8_t> selectResponse; - int numInts = responseLen / sizeof(int); - if (response == NULL || responseLen % sizeof(int) != 0) { - RLOGE("iccOpenLogicalChannelResponse Invalid response: NULL"); - if (response != NULL) { - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } - } else { - int *pInt = (int *) response; - channelId = pInt[0]; - selectResponse.resize(numInts - 1); - for (int i = 1; i < numInts; i++) { - selectResponse[i - 1] = (int8_t) pInt[i]; - } - } - Return<void> retStatus - = radioService[slotId]->mRadioResponse->iccOpenLogicalChannelResponse(responseInfo, - channelId, selectResponse); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("iccOpenLogicalChannelResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::iccCloseLogicalChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("iccCloseLogicalChannelResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->iccCloseLogicalChannelResponse( - responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("iccCloseLogicalChannelResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::iccTransmitApduLogicalChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("iccTransmitApduLogicalChannelResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->iccTransmitApduLogicalChannelResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("iccTransmitApduLogicalChannelResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::nvReadItemResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("nvReadItemResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponse->nvReadItemResponse( - responseInfo, - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("nvReadItemResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::nvWriteItemResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("nvWriteItemResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->nvWriteItemResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("nvWriteItemResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::nvWriteCdmaPrlResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("nvWriteCdmaPrlResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->nvWriteCdmaPrlResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("nvWriteCdmaPrlResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::nvResetConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("nvResetConfigResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->nvResetConfigResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("nvResetConfigResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setUiccSubscriptionResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setUiccSubscriptionResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setUiccSubscriptionResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setUiccSubscriptionResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setDataAllowedResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setDataAllowedResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setDataAllowedResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setDataAllowedResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getHardwareConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getHardwareConfigResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - hidl_vec<HardwareConfig> result; - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_HardwareConfig) != 0) { - RLOGE("hardwareConfigChangedInd: invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - convertRilHardwareConfigListToHal(response, responseLen, result); - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->getHardwareConfigResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getHardwareConfigResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::requestIccSimAuthenticationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("requestIccSimAuthenticationResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - IccIoResult result = responseIccIo(responseInfo, serial, responseType, e, response, - responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->requestIccSimAuthenticationResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("requestIccSimAuthenticationResponse: radioService[%d]->mRadioResponse " - "== NULL", slotId); - } - - return 0; -} - -int radio::setDataProfileResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setDataProfileResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setDataProfileResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setDataProfileResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::requestShutdownResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("requestShutdownResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->requestShutdownResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("requestShutdownResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -void responseRadioCapability(RadioResponseInfo& responseInfo, int serial, - int responseType, RIL_Errno e, void *response, size_t responseLen, RadioCapability& rc) { - populateResponseInfo(responseInfo, serial, responseType, e); - - if (response == NULL || responseLen != sizeof(RIL_RadioCapability)) { - RLOGE("responseRadioCapability: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - rc.logicalModemUuid = hidl_string(); - } else { - convertRilRadioCapabilityToHal(response, responseLen, rc); - } -} - -int radio::getRadioCapabilityResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getRadioCapabilityResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - RadioCapability result = {}; - responseRadioCapability(responseInfo, serial, responseType, e, response, responseLen, - result); - Return<void> retStatus = radioService[slotId]->mRadioResponse->getRadioCapabilityResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getRadioCapabilityResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setRadioCapabilityResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setRadioCapabilityResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - RadioCapability result = {}; - responseRadioCapability(responseInfo, serial, responseType, e, response, responseLen, - result); - Return<void> retStatus = radioService[slotId]->mRadioResponse->setRadioCapabilityResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setRadioCapabilityResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -LceStatusInfo responseLceStatusInfo(RadioResponseInfo& responseInfo, int serial, int responseType, - RIL_Errno e, void *response, size_t responseLen) { - populateResponseInfo(responseInfo, serial, responseType, e); - LceStatusInfo result = {}; - - if (response == NULL || responseLen != sizeof(RIL_LceStatusInfo)) { - RLOGE("Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - RIL_LceStatusInfo *resp = (RIL_LceStatusInfo *) response; - result.lceStatus = (LceStatus) resp->lce_status; - result.actualIntervalMs = (uint8_t) resp->actual_interval_ms; - } - return result; -} - -int radio::startLceServiceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("startLceServiceResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - LceStatusInfo result = responseLceStatusInfo(responseInfo, serial, responseType, e, - response, responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->startLceServiceResponse(responseInfo, - result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("startLceServiceResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::stopLceServiceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("stopLceServiceResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - LceStatusInfo result = responseLceStatusInfo(responseInfo, serial, responseType, e, - response, responseLen); - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->stopLceServiceResponse(responseInfo, - result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stopLceServiceResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::pullLceDataResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("pullLceDataResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - LceDataInfo result = {}; - if (response == NULL || responseLen != sizeof(RIL_LceDataInfo)) { - RLOGE("pullLceDataResponse: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - convertRilLceDataInfoToHal(response, responseLen, result); - } - - Return<void> retStatus = radioService[slotId]->mRadioResponse->pullLceDataResponse( - responseInfo, result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("pullLceDataResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::getModemActivityInfoResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getModemActivityInfoResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - ActivityStatsInfo info; - if (response == NULL || responseLen != sizeof(RIL_ActivityStatsInfo)) { - RLOGE("getModemActivityInfoResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - RIL_ActivityStatsInfo *resp = (RIL_ActivityStatsInfo *)response; - info.sleepModeTimeMs = resp->sleep_mode_time_ms; - info.idleModeTimeMs = resp->idle_mode_time_ms; - for(int i = 0; i < RIL_NUM_TX_POWER_LEVELS; i++) { - info.txmModetimeMs[i] = resp->tx_mode_time_ms[i]; - } - info.rxModeTimeMs = resp->rx_mode_time_ms; - } - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getModemActivityInfoResponse(responseInfo, - info); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getModemActivityInfoResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setAllowedCarriersResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setAllowedCarriersResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - int ret = responseInt(responseInfo, serial, responseType, e, response, responseLen); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setAllowedCarriersResponse(responseInfo, - ret); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setAllowedCarriersResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::getAllowedCarriersResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("getAllowedCarriersResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - CarrierRestrictions carrierInfo = {}; - bool allAllowed = true; - if (response == NULL) { -#if VDBG - RLOGD("getAllowedCarriersResponse response is NULL: all allowed"); -#endif - carrierInfo.allowedCarriers.resize(0); - carrierInfo.excludedCarriers.resize(0); - } else if (responseLen != sizeof(RIL_CarrierRestrictions)) { - RLOGE("getAllowedCarriersResponse Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - RIL_CarrierRestrictions *pCr = (RIL_CarrierRestrictions *)response; - if (pCr->len_allowed_carriers > 0 || pCr->len_excluded_carriers > 0) { - allAllowed = false; - } - - carrierInfo.allowedCarriers.resize(pCr->len_allowed_carriers); - for(int i = 0; i < pCr->len_allowed_carriers; i++) { - RIL_Carrier *carrier = pCr->allowed_carriers + i; - carrierInfo.allowedCarriers[i].mcc = convertCharPtrToHidlString(carrier->mcc); - carrierInfo.allowedCarriers[i].mnc = convertCharPtrToHidlString(carrier->mnc); - carrierInfo.allowedCarriers[i].matchType = (CarrierMatchType) carrier->match_type; - carrierInfo.allowedCarriers[i].matchData = - convertCharPtrToHidlString(carrier->match_data); - } - - carrierInfo.excludedCarriers.resize(pCr->len_excluded_carriers); - for(int i = 0; i < pCr->len_excluded_carriers; i++) { - RIL_Carrier *carrier = pCr->excluded_carriers + i; - carrierInfo.excludedCarriers[i].mcc = convertCharPtrToHidlString(carrier->mcc); - carrierInfo.excludedCarriers[i].mnc = convertCharPtrToHidlString(carrier->mnc); - carrierInfo.excludedCarriers[i].matchType = (CarrierMatchType) carrier->match_type; - carrierInfo.excludedCarriers[i].matchData = - convertCharPtrToHidlString(carrier->match_data); - } - } - - Return<void> retStatus - = radioService[slotId]->mRadioResponse->getAllowedCarriersResponse(responseInfo, - allAllowed, carrierInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("getAllowedCarriersResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::sendDeviceStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen) { -#if VDBG - RLOGD("sendDeviceStateResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->sendDeviceStateResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("sendDeviceStateResponse: radioService[%d]->mRadioResponse == NULL", slotId); - } - - return 0; -} - -int radio::setCarrierInfoForImsiEncryptionResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { - RLOGD("setCarrierInfoForImsiEncryptionResponse: serial %d", serial); - if (radioService[slotId]->mRadioResponseV1_1 != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus = radioService[slotId]->mRadioResponseV1_1-> - setCarrierInfoForImsiEncryptionResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setCarrierInfoForImsiEncryptionResponse: radioService[%d]->mRadioResponseV1_1 == " - "NULL", slotId); - } - return 0; -} - -int radio::setIndicationFilterResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen) { -#if VDBG - RLOGD("setIndicationFilterResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setIndicationFilterResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("setIndicationFilterResponse: radioService[%d]->mRadioResponse == NULL", - slotId); - } - - return 0; -} - -int radio::setSimCardPowerResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("setSimCardPowerResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponse != NULL - || radioService[slotId]->mRadioResponseV1_1 != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - if (radioService[slotId]->mRadioResponseV1_1 != NULL) { - Return<void> retStatus = radioService[slotId]->mRadioResponseV1_1-> - setSimCardPowerResponse_1_1(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGD("setSimCardPowerResponse: radioService[%d]->mRadioResponseV1_1 == NULL", - slotId); - Return<void> retStatus - = radioService[slotId]->mRadioResponse->setSimCardPowerResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } - } else { - RLOGE("setSimCardPowerResponse: radioService[%d]->mRadioResponse == NULL && " - "radioService[%d]->mRadioResponseV1_1 == NULL", slotId, slotId); - } - return 0; -} - -int radio::startNetworkScanResponse(int slotId, int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("startNetworkScanResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponseV1_1 != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponseV1_1->startNetworkScanResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("startNetworkScanResponse: radioService[%d]->mRadioResponseV1_1 == NULL", slotId); - } - - return 0; -} - -int radio::stopNetworkScanResponse(int slotId, int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("stopNetworkScanResponse: serial %d", serial); -#endif - - if (radioService[slotId]->mRadioResponseV1_1 != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - Return<void> retStatus - = radioService[slotId]->mRadioResponseV1_1->stopNetworkScanResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stopNetworkScanResponse: radioService[%d]->mRadioResponseV1_1 == NULL", slotId); - } - - return 0; -} - -void convertRilKeepaliveStatusToHal(const RIL_KeepaliveStatus *rilStatus, - V1_1::KeepaliveStatus& halStatus) { - halStatus.sessionHandle = rilStatus->sessionHandle; - halStatus.code = static_cast<V1_1::KeepaliveStatusCode>(rilStatus->code); -} - -int radio::startKeepaliveResponse(int slotId, int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("%s(): %d", __FUNCTION__, serial); -#endif - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - // If we don't have a radio service, there's nothing we can do - if (radioService[slotId]->mRadioResponseV1_1 == NULL) { - RLOGE("%s: radioService[%d]->mRadioResponseV1_1 == NULL", __FUNCTION__, slotId); - return 0; - } - - V1_1::KeepaliveStatus ks = {}; - if (response == NULL || responseLen != sizeof(V1_1::KeepaliveStatus)) { - RLOGE("%s: invalid response - %d", __FUNCTION__, static_cast<int>(e)); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - convertRilKeepaliveStatusToHal(static_cast<RIL_KeepaliveStatus*>(response), ks); - } - - Return<void> retStatus = - radioService[slotId]->mRadioResponseV1_1->startKeepaliveResponse(responseInfo, ks); - radioService[slotId]->checkReturnStatus(retStatus); - return 0; -} - -int radio::stopKeepaliveResponse(int slotId, int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("%s(): %d", __FUNCTION__, serial); -#endif - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - - // If we don't have a radio service, there's nothing we can do - if (radioService[slotId]->mRadioResponseV1_1 == NULL) { - RLOGE("%s: radioService[%d]->mRadioResponseV1_1 == NULL", __FUNCTION__, slotId); - return 0; - } - - Return<void> retStatus = - radioService[slotId]->mRadioResponseV1_1->stopKeepaliveResponse(responseInfo); - radioService[slotId]->checkReturnStatus(retStatus); - return 0; -} - -int radio::sendRequestRawResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("sendRequestRawResponse: serial %d", serial); -#endif - - if (!kOemHookEnabled) return 0; - - if (oemHookService[slotId]->mOemHookResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<uint8_t> data; - - if (response == NULL) { - RLOGE("sendRequestRawResponse: Invalid response"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - data.setToExternal((uint8_t *) response, responseLen); - } - Return<void> retStatus = oemHookService[slotId]->mOemHookResponse-> - sendRequestRawResponse(responseInfo, data); - checkReturnStatus(slotId, retStatus, false); - } else { - RLOGE("sendRequestRawResponse: oemHookService[%d]->mOemHookResponse == NULL", - slotId); - } - - return 0; -} - -int radio::sendRequestStringsResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen) { -#if VDBG - RLOGD("sendRequestStringsResponse: serial %d", serial); -#endif - - if (!kOemHookEnabled) return 0; - - if (oemHookService[slotId]->mOemHookResponse != NULL) { - RadioResponseInfo responseInfo = {}; - populateResponseInfo(responseInfo, serial, responseType, e); - hidl_vec<hidl_string> data; - - if ((response == NULL && responseLen != 0) || responseLen % sizeof(char *) != 0) { - RLOGE("sendRequestStringsResponse Invalid response: NULL"); - if (e == RIL_E_SUCCESS) responseInfo.error = RadioError::INVALID_RESPONSE; - } else { - char **resp = (char **) response; - int numStrings = responseLen / sizeof(char *); - data.resize(numStrings); - for (int i = 0; i < numStrings; i++) { - data[i] = convertCharPtrToHidlString(resp[i]); - } - } - Return<void> retStatus - = oemHookService[slotId]->mOemHookResponse->sendRequestStringsResponse( - responseInfo, data); - checkReturnStatus(slotId, retStatus, false); - } else { - RLOGE("sendRequestStringsResponse: oemHookService[%d]->mOemHookResponse == " - "NULL", slotId); - } - - return 0; -} - -/*************************************************************************************************** - * INDICATION FUNCTIONS - * The below function handle unsolicited messages coming from the Radio - * (messages for which there is no pending request) - **************************************************************************************************/ - -RadioIndicationType convertIntToRadioIndicationType(int indicationType) { - return indicationType == RESPONSE_UNSOLICITED ? (RadioIndicationType::UNSOLICITED) : - (RadioIndicationType::UNSOLICITED_ACK_EXP); -} - -int radio::radioStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - RadioState radioState = - (RadioState) CALL_ONSTATEREQUEST(slotId); - RLOGD("radioStateChangedInd: radioState %d", radioState); - Return<void> retStatus = radioService[slotId]->mRadioIndication->radioStateChanged( - convertIntToRadioIndicationType(indicationType), radioState); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("radioStateChangedInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::callStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("callStateChangedInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->callStateChanged( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("callStateChangedInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::networkStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("networkStateChangedInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->networkStateChanged( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("networkStateChangedInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -uint8_t hexCharToInt(uint8_t c) { - if (c >= '0' && c <= '9') return (c - '0'); - if (c >= 'A' && c <= 'F') return (c - 'A' + 10); - if (c >= 'a' && c <= 'f') return (c - 'a' + 10); - - return INVALID_HEX_CHAR; -} - -uint8_t * convertHexStringToBytes(void *response, size_t responseLen) { - if (responseLen % 2 != 0) { - return NULL; - } - - uint8_t *bytes = (uint8_t *)calloc(responseLen/2, sizeof(uint8_t)); - if (bytes == NULL) { - RLOGE("convertHexStringToBytes: cannot allocate memory for bytes string"); - return NULL; - } - uint8_t *hexString = (uint8_t *)response; - - for (size_t i = 0; i < responseLen; i += 2) { - uint8_t hexChar1 = hexCharToInt(hexString[i]); - uint8_t hexChar2 = hexCharToInt(hexString[i + 1]); - - if (hexChar1 == INVALID_HEX_CHAR || hexChar2 == INVALID_HEX_CHAR) { - RLOGE("convertHexStringToBytes: invalid hex char %d %d", - hexString[i], hexString[i + 1]); - free(bytes); - return NULL; - } - bytes[i/2] = ((hexChar1 << 4) | hexChar2); - } - - return bytes; -} - -int radio::newSmsInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("newSmsInd: invalid response"); - return 0; - } - - uint8_t *bytes = convertHexStringToBytes(response, responseLen); - if (bytes == NULL) { - RLOGE("newSmsInd: convertHexStringToBytes failed"); - return 0; - } - - hidl_vec<uint8_t> pdu; - pdu.setToExternal(bytes, responseLen/2); -#if VDBG - RLOGD("newSmsInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->newSms( - convertIntToRadioIndicationType(indicationType), pdu); - radioService[slotId]->checkReturnStatus(retStatus); - free(bytes); - } else { - RLOGE("newSmsInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::newSmsStatusReportInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("newSmsStatusReportInd: invalid response"); - return 0; - } - - uint8_t *bytes = convertHexStringToBytes(response, responseLen); - if (bytes == NULL) { - RLOGE("newSmsStatusReportInd: convertHexStringToBytes failed"); - return 0; - } - - hidl_vec<uint8_t> pdu; - pdu.setToExternal(bytes, responseLen/2); -#if VDBG - RLOGD("newSmsStatusReportInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->newSmsStatusReport( - convertIntToRadioIndicationType(indicationType), pdu); - radioService[slotId]->checkReturnStatus(retStatus); - free(bytes); - } else { - RLOGE("newSmsStatusReportInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::newSmsOnSimInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("newSmsOnSimInd: invalid response"); - return 0; - } - int32_t recordNumber = ((int32_t *) response)[0]; -#if VDBG - RLOGD("newSmsOnSimInd: slotIndex %d", recordNumber); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->newSmsOnSim( - convertIntToRadioIndicationType(indicationType), recordNumber); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("newSmsOnSimInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::onUssdInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != 2 * sizeof(char *)) { - RLOGE("onUssdInd: invalid response"); - return 0; - } - char **strings = (char **) response; - char *mode = strings[0]; - hidl_string msg = convertCharPtrToHidlString(strings[1]); - UssdModeType modeType = (UssdModeType) atoi(mode); -#if VDBG - RLOGD("onUssdInd: mode %s", mode); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->onUssd( - convertIntToRadioIndicationType(indicationType), modeType, msg); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("onUssdInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::nitzTimeReceivedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("nitzTimeReceivedInd: invalid response"); - return 0; - } - hidl_string nitzTime = convertCharPtrToHidlString((char *) response); -#if VDBG - RLOGD("nitzTimeReceivedInd: nitzTime %s receivedTime %" PRId64, nitzTime.c_str(), - nitzTimeReceived[slotId]); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->nitzTimeReceived( - convertIntToRadioIndicationType(indicationType), nitzTime, - nitzTimeReceived[slotId]); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("nitzTimeReceivedInd: radioService[%d]->mRadioIndication == NULL", slotId); - return -1; - } - - return 0; -} - -int radio::reportPhysicalChannelConfigs(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndicationV1_4 != NULL) { - int *configs = (int*)response; - ::android::hardware::hidl_vec<PhysicalChannelConfigV1_4> physChanConfig; - physChanConfig.resize(1); - physChanConfig[0].base.status = (::android::hardware::radio::V1_2::CellConnectionStatus)configs[0]; - physChanConfig[0].base.cellBandwidthDownlink = configs[1]; - physChanConfig[0].rat = (::android::hardware::radio::V1_4::RadioTechnology)configs[2]; - physChanConfig[0].rfInfo.range((::android::hardware::radio::V1_4::FrequencyRange)configs[3]); - physChanConfig[0].contextIds.resize(1); - physChanConfig[0].contextIds[0] = configs[4]; - RLOGD("reportPhysicalChannelConfigs: %d %d %d %d %d", configs[0], - configs[1], configs[2], configs[3], configs[4]); - radioService[slotId] - ->mRadioIndicationV1_4->currentPhysicalChannelConfigs_1_4( - RadioIndicationType::UNSOLICITED, physChanConfig); - } else { - RLOGE("reportPhysicalChannelConfigs: radioService[%d]->mRadioIndicationV1_4 == NULL", slotId); - return -1; - } - - return 0; -} - - -void convertRilSignalStrengthToHal(void *response, size_t responseLen, - SignalStrength& signalStrength) { - RIL_SignalStrength_v10 *rilSignalStrength = (RIL_SignalStrength_v10 *) response; - - // Fixup LTE for backwards compatibility - // signalStrength: -1 -> 99 - if (rilSignalStrength->LTE_SignalStrength.signalStrength == -1) { - rilSignalStrength->LTE_SignalStrength.signalStrength = 99; - } - // rsrp: -1 -> INT_MAX all other negative value to positive. - // So remap here - if (rilSignalStrength->LTE_SignalStrength.rsrp == -1) { - rilSignalStrength->LTE_SignalStrength.rsrp = INT_MAX; - } else if (rilSignalStrength->LTE_SignalStrength.rsrp < -1) { - rilSignalStrength->LTE_SignalStrength.rsrp = -rilSignalStrength->LTE_SignalStrength.rsrp; - } - // rsrq: -1 -> INT_MAX - if (rilSignalStrength->LTE_SignalStrength.rsrq == -1) { - rilSignalStrength->LTE_SignalStrength.rsrq = INT_MAX; - } - // Not remapping rssnr is already using INT_MAX - // cqi: -1 -> INT_MAX - if (rilSignalStrength->LTE_SignalStrength.cqi == -1) { - rilSignalStrength->LTE_SignalStrength.cqi = INT_MAX; - } - - signalStrength.gw.signalStrength = rilSignalStrength->GW_SignalStrength.signalStrength; - signalStrength.gw.bitErrorRate = rilSignalStrength->GW_SignalStrength.bitErrorRate; - // RIL_SignalStrength_v10 not support gw.timingAdvance. Set to INT_MAX as - // invalid value. - signalStrength.gw.timingAdvance = INT_MAX; - - signalStrength.cdma.dbm = rilSignalStrength->CDMA_SignalStrength.dbm; - signalStrength.cdma.ecio = rilSignalStrength->CDMA_SignalStrength.ecio; - signalStrength.evdo.dbm = rilSignalStrength->EVDO_SignalStrength.dbm; - signalStrength.evdo.ecio = rilSignalStrength->EVDO_SignalStrength.ecio; - signalStrength.evdo.signalNoiseRatio = - rilSignalStrength->EVDO_SignalStrength.signalNoiseRatio; - signalStrength.lte.signalStrength = rilSignalStrength->LTE_SignalStrength.signalStrength; - signalStrength.lte.rsrp = rilSignalStrength->LTE_SignalStrength.rsrp; - signalStrength.lte.rsrq = rilSignalStrength->LTE_SignalStrength.rsrq; - signalStrength.lte.rssnr = rilSignalStrength->LTE_SignalStrength.rssnr; - signalStrength.lte.cqi = rilSignalStrength->LTE_SignalStrength.cqi; - signalStrength.lte.timingAdvance = rilSignalStrength->LTE_SignalStrength.timingAdvance; - signalStrength.tdScdma.rscp = rilSignalStrength->TD_SCDMA_SignalStrength.rscp; -} - -int radio::currentSignalStrengthInd(int slotId, - int indicationType, int token, RIL_Errno e, - void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_SignalStrength_v10)) { - RLOGE("currentSignalStrengthInd: invalid response"); - return 0; - } - - SignalStrength signalStrength = {}; - convertRilSignalStrengthToHal(response, responseLen, signalStrength); - -#if VDBG - RLOGD("currentSignalStrengthInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->currentSignalStrength( - convertIntToRadioIndicationType(indicationType), signalStrength); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("currentSignalStrengthInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -void convertRilDataCallToHal(RIL_Data_Call_Response_v11 *dcResponse, - SetupDataCallResult& dcResult) { - dcResult.status = (DataCallFailCause) dcResponse->status; - dcResult.suggestedRetryTime = dcResponse->suggestedRetryTime; - dcResult.cid = dcResponse->cid; - dcResult.active = dcResponse->active; - dcResult.type = convertCharPtrToHidlString(dcResponse->type); - dcResult.ifname = convertCharPtrToHidlString(dcResponse->ifname); - dcResult.addresses = convertCharPtrToHidlString(dcResponse->addresses); - dcResult.dnses = convertCharPtrToHidlString(dcResponse->dnses); - dcResult.gateways = convertCharPtrToHidlString(dcResponse->gateways); - dcResult.pcscf = convertCharPtrToHidlString(dcResponse->pcscf); - dcResult.mtu = dcResponse->mtu; -} - -void convertRilDataCallListToHal(void *response, size_t responseLen, - hidl_vec<SetupDataCallResult>& dcResultList) { - int num = responseLen / sizeof(RIL_Data_Call_Response_v11); - - RIL_Data_Call_Response_v11 *dcResponse = (RIL_Data_Call_Response_v11 *) response; - dcResultList.resize(num); - for (int i = 0; i < num; i++) { - convertRilDataCallToHal(&dcResponse[i], dcResultList[i]); - } -} - -int radio::dataCallListChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_Data_Call_Response_v11) != 0) { - RLOGE("dataCallListChangedInd: invalid response"); - return 0; - } - hidl_vec<SetupDataCallResult> dcList; - convertRilDataCallListToHal(response, responseLen, dcList); -#if VDBG - RLOGD("dataCallListChangedInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->dataCallListChanged( - convertIntToRadioIndicationType(indicationType), dcList); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("dataCallListChangedInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::suppSvcNotifyInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_SuppSvcNotification)) { - RLOGE("suppSvcNotifyInd: invalid response"); - return 0; - } - - SuppSvcNotification suppSvc = {}; - RIL_SuppSvcNotification *ssn = (RIL_SuppSvcNotification *) response; - suppSvc.isMT = ssn->notificationType; - suppSvc.code = ssn->code; - suppSvc.index = ssn->index; - suppSvc.type = ssn->type; - suppSvc.number = convertCharPtrToHidlString(ssn->number); - -#if VDBG - RLOGD("suppSvcNotifyInd: isMT %d code %d index %d type %d", - suppSvc.isMT, suppSvc.code, suppSvc.index, suppSvc.type); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->suppSvcNotify( - convertIntToRadioIndicationType(indicationType), suppSvc); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("suppSvcNotifyInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::stkSessionEndInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("stkSessionEndInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->stkSessionEnd( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stkSessionEndInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::stkProactiveCommandInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("stkProactiveCommandInd: invalid response"); - return 0; - } -#if VDBG - RLOGD("stkProactiveCommandInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->stkProactiveCommand( - convertIntToRadioIndicationType(indicationType), - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stkProactiveCommandInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::stkEventNotifyInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("stkEventNotifyInd: invalid response"); - return 0; - } -#if VDBG - RLOGD("stkEventNotifyInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->stkEventNotify( - convertIntToRadioIndicationType(indicationType), - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stkEventNotifyInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::stkCallSetupInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("stkCallSetupInd: invalid response"); - return 0; - } - int32_t timeout = ((int32_t *) response)[0]; -#if VDBG - RLOGD("stkCallSetupInd: timeout %d", timeout); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->stkCallSetup( - convertIntToRadioIndicationType(indicationType), timeout); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stkCallSetupInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::simSmsStorageFullInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("simSmsStorageFullInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->simSmsStorageFull( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("simSmsStorageFullInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::simRefreshInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_SimRefreshResponse_v7)) { - RLOGE("simRefreshInd: invalid response"); - return 0; - } - - SimRefreshResult refreshResult = {}; - RIL_SimRefreshResponse_v7 *simRefreshResponse = ((RIL_SimRefreshResponse_v7 *) response); - refreshResult.type = - (V1_0::SimRefreshType) simRefreshResponse->result; - refreshResult.efId = simRefreshResponse->ef_id; - refreshResult.aid = convertCharPtrToHidlString(simRefreshResponse->aid); - -#if VDBG - RLOGD("simRefreshInd: type %d efId %d", refreshResult.type, refreshResult.efId); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->simRefresh( - convertIntToRadioIndicationType(indicationType), refreshResult); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("simRefreshInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -void convertRilCdmaSignalInfoRecordToHal(RIL_CDMA_SignalInfoRecord *signalInfoRecord, - CdmaSignalInfoRecord& record) { - record.isPresent = signalInfoRecord->isPresent; - record.signalType = signalInfoRecord->signalType; - record.alertPitch = signalInfoRecord->alertPitch; - record.signal = signalInfoRecord->signal; -} - -int radio::callRingInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - bool isGsm; - CdmaSignalInfoRecord record = {}; - if (response == NULL || responseLen == 0) { - isGsm = true; - } else { - isGsm = false; - if (responseLen != sizeof (RIL_CDMA_SignalInfoRecord)) { - RLOGE("callRingInd: invalid response"); - return 0; - } - convertRilCdmaSignalInfoRecordToHal((RIL_CDMA_SignalInfoRecord *) response, record); - } - -#if VDBG - RLOGD("callRingInd: isGsm %d", isGsm); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->callRing( - convertIntToRadioIndicationType(indicationType), isGsm, record); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("callRingInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::simStatusChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("simStatusChangedInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->simStatusChanged( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("simStatusChangedInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::cdmaNewSmsInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_CDMA_SMS_Message)) { - RLOGE("cdmaNewSmsInd: invalid response"); - return 0; - } - - CdmaSmsMessage msg = {}; - RIL_CDMA_SMS_Message *rilMsg = (RIL_CDMA_SMS_Message *) response; - msg.teleserviceId = rilMsg->uTeleserviceID; - msg.isServicePresent = rilMsg->bIsServicePresent; - msg.serviceCategory = rilMsg->uServicecategory; - msg.address.digitMode = - (V1_0::CdmaSmsDigitMode) rilMsg->sAddress.digit_mode; - msg.address.numberMode = - (V1_0::CdmaSmsNumberMode) rilMsg->sAddress.number_mode; - msg.address.numberType = - (V1_0::CdmaSmsNumberType) rilMsg->sAddress.number_type; - msg.address.numberPlan = - (V1_0::CdmaSmsNumberPlan) rilMsg->sAddress.number_plan; - - int digitLimit = MIN((rilMsg->sAddress.number_of_digits), RIL_CDMA_SMS_ADDRESS_MAX); - msg.address.digits.setToExternal(rilMsg->sAddress.digits, digitLimit); - - msg.subAddress.subaddressType = (V1_0::CdmaSmsSubaddressType) - rilMsg->sSubAddress.subaddressType; - msg.subAddress.odd = rilMsg->sSubAddress.odd; - - digitLimit= MIN((rilMsg->sSubAddress.number_of_digits), RIL_CDMA_SMS_SUBADDRESS_MAX); - msg.subAddress.digits.setToExternal(rilMsg->sSubAddress.digits, digitLimit); - - digitLimit = MIN((rilMsg->uBearerDataLen), RIL_CDMA_SMS_BEARER_DATA_MAX); - msg.bearerData.setToExternal(rilMsg->aBearerData, digitLimit); - -#if VDBG - RLOGD("cdmaNewSmsInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaNewSms( - convertIntToRadioIndicationType(indicationType), msg); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cdmaNewSmsInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::newBroadcastSmsInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("newBroadcastSmsInd: invalid response"); - return 0; - } - - hidl_vec<uint8_t> data; - data.setToExternal((uint8_t *) response, responseLen); -#if VDBG - RLOGD("newBroadcastSmsInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->newBroadcastSms( - convertIntToRadioIndicationType(indicationType), data); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("newBroadcastSmsInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::cdmaRuimSmsStorageFullInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("cdmaRuimSmsStorageFullInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaRuimSmsStorageFull( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cdmaRuimSmsStorageFullInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::restrictedStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("restrictedStateChangedInd: invalid response"); - return 0; - } - int32_t state = ((int32_t *) response)[0]; -#if VDBG - RLOGD("restrictedStateChangedInd: state %d", state); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->restrictedStateChanged( - convertIntToRadioIndicationType(indicationType), (PhoneRestrictedState) state); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("restrictedStateChangedInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::enterEmergencyCallbackModeInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("enterEmergencyCallbackModeInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->enterEmergencyCallbackMode( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("enterEmergencyCallbackModeInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::cdmaCallWaitingInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_CDMA_CallWaiting_v6)) { - RLOGE("cdmaCallWaitingInd: invalid response"); - return 0; - } - - CdmaCallWaiting callWaitingRecord = {}; - RIL_CDMA_CallWaiting_v6 *callWaitingRil = ((RIL_CDMA_CallWaiting_v6 *) response); - callWaitingRecord.number = convertCharPtrToHidlString(callWaitingRil->number); - callWaitingRecord.numberPresentation = - (CdmaCallWaitingNumberPresentation) callWaitingRil->numberPresentation; - callWaitingRecord.name = convertCharPtrToHidlString(callWaitingRil->name); - convertRilCdmaSignalInfoRecordToHal(&callWaitingRil->signalInfoRecord, - callWaitingRecord.signalInfoRecord); - callWaitingRecord.numberType = (CdmaCallWaitingNumberType) callWaitingRil->number_type; - callWaitingRecord.numberPlan = (CdmaCallWaitingNumberPlan) callWaitingRil->number_plan; - -#if VDBG - RLOGD("cdmaCallWaitingInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaCallWaiting( - convertIntToRadioIndicationType(indicationType), callWaitingRecord); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cdmaCallWaitingInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::cdmaOtaProvisionStatusInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("cdmaOtaProvisionStatusInd: invalid response"); - return 0; - } - int32_t status = ((int32_t *) response)[0]; -#if VDBG - RLOGD("cdmaOtaProvisionStatusInd: status %d", status); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaOtaProvisionStatus( - convertIntToRadioIndicationType(indicationType), (CdmaOtaProvisionStatus) status); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cdmaOtaProvisionStatusInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::cdmaInfoRecInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_CDMA_InformationRecords)) { - RLOGE("cdmaInfoRecInd: invalid response"); - return 0; - } - - CdmaInformationRecords records = {}; - RIL_CDMA_InformationRecords *recordsRil = (RIL_CDMA_InformationRecords *) response; - - char* string8 = NULL; - int num = MIN(recordsRil->numberOfInfoRecs, RIL_CDMA_MAX_NUMBER_OF_INFO_RECS); - if (recordsRil->numberOfInfoRecs > RIL_CDMA_MAX_NUMBER_OF_INFO_RECS) { - RLOGE("cdmaInfoRecInd: received %d recs which is more than %d, dropping " - "additional ones", recordsRil->numberOfInfoRecs, - RIL_CDMA_MAX_NUMBER_OF_INFO_RECS); - } - records.infoRec.resize(num); - for (int i = 0 ; i < num ; i++) { - CdmaInformationRecord *record = &records.infoRec[i]; - RIL_CDMA_InformationRecord *infoRec = &recordsRil->infoRec[i]; - record->name = (CdmaInfoRecName) infoRec->name; - // All vectors should be size 0 except one which will be size 1. Set everything to - // size 0 initially. - record->display.resize(0); - record->number.resize(0); - record->signal.resize(0); - record->redir.resize(0); - record->lineCtrl.resize(0); - record->clir.resize(0); - record->audioCtrl.resize(0); - switch (infoRec->name) { - case RIL_CDMA_DISPLAY_INFO_REC: - case RIL_CDMA_EXTENDED_DISPLAY_INFO_REC: { - if (infoRec->rec.display.alpha_len > CDMA_ALPHA_INFO_BUFFER_LENGTH) { - RLOGE("cdmaInfoRecInd: invalid display info response length %d " - "expected not more than %d", (int) infoRec->rec.display.alpha_len, - CDMA_ALPHA_INFO_BUFFER_LENGTH); - return 0; - } - string8 = (char*) malloc((infoRec->rec.display.alpha_len + 1) * sizeof(char)); - if (string8 == NULL) { - RLOGE("cdmaInfoRecInd: Memory allocation failed for " - "responseCdmaInformationRecords"); - return 0; - } - memcpy(string8, infoRec->rec.display.alpha_buf, infoRec->rec.display.alpha_len); - string8[(int)infoRec->rec.display.alpha_len] = '\0'; - - record->display.resize(1); - record->display[0].alphaBuf = string8; - free(string8); - string8 = NULL; - break; - } - - case RIL_CDMA_CALLED_PARTY_NUMBER_INFO_REC: - case RIL_CDMA_CALLING_PARTY_NUMBER_INFO_REC: - case RIL_CDMA_CONNECTED_NUMBER_INFO_REC: { - if (infoRec->rec.number.len > CDMA_NUMBER_INFO_BUFFER_LENGTH) { - RLOGE("cdmaInfoRecInd: invalid display info response length %d " - "expected not more than %d", (int) infoRec->rec.number.len, - CDMA_NUMBER_INFO_BUFFER_LENGTH); - return 0; - } - string8 = (char*) malloc((infoRec->rec.number.len + 1) * sizeof(char)); - if (string8 == NULL) { - RLOGE("cdmaInfoRecInd: Memory allocation failed for " - "responseCdmaInformationRecords"); - return 0; - } - memcpy(string8, infoRec->rec.number.buf, infoRec->rec.number.len); - string8[(int)infoRec->rec.number.len] = '\0'; - - record->number.resize(1); - record->number[0].number = string8; - free(string8); - string8 = NULL; - record->number[0].numberType = infoRec->rec.number.number_type; - record->number[0].numberPlan = infoRec->rec.number.number_plan; - record->number[0].pi = infoRec->rec.number.pi; - record->number[0].si = infoRec->rec.number.si; - break; - } - - case RIL_CDMA_SIGNAL_INFO_REC: { - record->signal.resize(1); - record->signal[0].isPresent = infoRec->rec.signal.isPresent; - record->signal[0].signalType = infoRec->rec.signal.signalType; - record->signal[0].alertPitch = infoRec->rec.signal.alertPitch; - record->signal[0].signal = infoRec->rec.signal.signal; - break; - } - - case RIL_CDMA_REDIRECTING_NUMBER_INFO_REC: { - if (infoRec->rec.redir.redirectingNumber.len > - CDMA_NUMBER_INFO_BUFFER_LENGTH) { - RLOGE("cdmaInfoRecInd: invalid display info response length %d " - "expected not more than %d\n", - (int)infoRec->rec.redir.redirectingNumber.len, - CDMA_NUMBER_INFO_BUFFER_LENGTH); - return 0; - } - string8 = (char*) malloc((infoRec->rec.redir.redirectingNumber.len + 1) * - sizeof(char)); - if (string8 == NULL) { - RLOGE("cdmaInfoRecInd: Memory allocation failed for " - "responseCdmaInformationRecords"); - return 0; - } - memcpy(string8, infoRec->rec.redir.redirectingNumber.buf, - infoRec->rec.redir.redirectingNumber.len); - string8[(int)infoRec->rec.redir.redirectingNumber.len] = '\0'; - - record->redir.resize(1); - record->redir[0].redirectingNumber.number = string8; - free(string8); - string8 = NULL; - record->redir[0].redirectingNumber.numberType = - infoRec->rec.redir.redirectingNumber.number_type; - record->redir[0].redirectingNumber.numberPlan = - infoRec->rec.redir.redirectingNumber.number_plan; - record->redir[0].redirectingNumber.pi = infoRec->rec.redir.redirectingNumber.pi; - record->redir[0].redirectingNumber.si = infoRec->rec.redir.redirectingNumber.si; - record->redir[0].redirectingReason = - (CdmaRedirectingReason) infoRec->rec.redir.redirectingReason; - break; - } - - case RIL_CDMA_LINE_CONTROL_INFO_REC: { - record->lineCtrl.resize(1); - record->lineCtrl[0].lineCtrlPolarityIncluded = - infoRec->rec.lineCtrl.lineCtrlPolarityIncluded; - record->lineCtrl[0].lineCtrlToggle = infoRec->rec.lineCtrl.lineCtrlToggle; - record->lineCtrl[0].lineCtrlReverse = infoRec->rec.lineCtrl.lineCtrlReverse; - record->lineCtrl[0].lineCtrlPowerDenial = - infoRec->rec.lineCtrl.lineCtrlPowerDenial; - break; - } - - case RIL_CDMA_T53_CLIR_INFO_REC: { - record->clir.resize(1); - record->clir[0].cause = infoRec->rec.clir.cause; - break; - } - - case RIL_CDMA_T53_AUDIO_CONTROL_INFO_REC: { - record->audioCtrl.resize(1); - record->audioCtrl[0].upLink = infoRec->rec.audioCtrl.upLink; - record->audioCtrl[0].downLink = infoRec->rec.audioCtrl.downLink; - break; - } - - case RIL_CDMA_T53_RELEASE_INFO_REC: - RLOGE("cdmaInfoRecInd: RIL_CDMA_T53_RELEASE_INFO_REC: INVALID"); - return 0; - - default: - RLOGE("cdmaInfoRecInd: Incorrect name value"); - return 0; - } - } - -#if VDBG - RLOGD("cdmaInfoRecInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaInfoRec( - convertIntToRadioIndicationType(indicationType), records); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cdmaInfoRecInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::indicateRingbackToneInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("indicateRingbackToneInd: invalid response"); - return 0; - } - bool start = ((int32_t *) response)[0]; -#if VDBG - RLOGD("indicateRingbackToneInd: start %d", start); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->indicateRingbackTone( - convertIntToRadioIndicationType(indicationType), start); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("indicateRingbackToneInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::resendIncallMuteInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("resendIncallMuteInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->resendIncallMute( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("resendIncallMuteInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::cdmaSubscriptionSourceChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, - void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("cdmaSubscriptionSourceChangedInd: invalid response"); - return 0; - } - int32_t cdmaSource = ((int32_t *) response)[0]; -#if VDBG - RLOGD("cdmaSubscriptionSourceChangedInd: cdmaSource %d", cdmaSource); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication-> - cdmaSubscriptionSourceChanged(convertIntToRadioIndicationType(indicationType), - (CdmaSubscriptionSource) cdmaSource); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cdmaSubscriptionSourceChangedInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::cdmaPrlChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("cdmaPrlChangedInd: invalid response"); - return 0; - } - int32_t version = ((int32_t *) response)[0]; -#if VDBG - RLOGD("cdmaPrlChangedInd: version %d", version); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->cdmaPrlChanged( - convertIntToRadioIndicationType(indicationType), version); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cdmaPrlChangedInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::exitEmergencyCallbackModeInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("exitEmergencyCallbackModeInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->exitEmergencyCallbackMode( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("exitEmergencyCallbackModeInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::rilConnectedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - RLOGD("rilConnectedInd"); - Return<void> retStatus = radioService[slotId]->mRadioIndication->rilConnected( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("rilConnectedInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::voiceRadioTechChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("voiceRadioTechChangedInd: invalid response"); - return 0; - } - int32_t rat = ((int32_t *) response)[0]; -#if VDBG - RLOGD("voiceRadioTechChangedInd: rat %d", rat); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->voiceRadioTechChanged( - convertIntToRadioIndicationType(indicationType), (RadioTechnology) rat); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("voiceRadioTechChangedInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -void convertRilCellInfoListToHal(void *response, size_t responseLen, hidl_vec<CellInfo>& records) { - int num = responseLen / sizeof(RIL_CellInfo_v12); - records.resize(num); - - RIL_CellInfo_v12 *rillCellInfo = (RIL_CellInfo_v12 *) response; - for (int i = 0; i < num; i++) { - records[i].cellInfoType = (CellInfoType) rillCellInfo->cellInfoType; - records[i].registered = rillCellInfo->registered; - records[i].timeStampType = (TimeStampType) rillCellInfo->timeStampType; - records[i].timeStamp = rillCellInfo->timeStamp; - // All vectors should be size 0 except one which will be size 1. Set everything to - // size 0 initially. - records[i].gsm.resize(0); - records[i].wcdma.resize(0); - records[i].cdma.resize(0); - records[i].lte.resize(0); - records[i].tdscdma.resize(0); - switch(rillCellInfo->cellInfoType) { - case RIL_CELL_INFO_TYPE_GSM: { - records[i].gsm.resize(1); - CellInfoGsm *cellInfoGsm = &records[i].gsm[0]; - cellInfoGsm->cellIdentityGsm.mcc = - ril::util::mcc::decode(rillCellInfo->CellInfo.gsm.cellIdentityGsm.mcc); - cellInfoGsm->cellIdentityGsm.mnc = - ril::util::mnc::decode(rillCellInfo->CellInfo.gsm.cellIdentityGsm.mnc); - cellInfoGsm->cellIdentityGsm.lac = - rillCellInfo->CellInfo.gsm.cellIdentityGsm.lac; - cellInfoGsm->cellIdentityGsm.cid = - rillCellInfo->CellInfo.gsm.cellIdentityGsm.cid; - cellInfoGsm->cellIdentityGsm.arfcn = - rillCellInfo->CellInfo.gsm.cellIdentityGsm.arfcn; - cellInfoGsm->cellIdentityGsm.bsic = - rillCellInfo->CellInfo.gsm.cellIdentityGsm.bsic; - cellInfoGsm->signalStrengthGsm.signalStrength = - rillCellInfo->CellInfo.gsm.signalStrengthGsm.signalStrength; - cellInfoGsm->signalStrengthGsm.bitErrorRate = - rillCellInfo->CellInfo.gsm.signalStrengthGsm.bitErrorRate; - cellInfoGsm->signalStrengthGsm.timingAdvance = - rillCellInfo->CellInfo.gsm.signalStrengthGsm.timingAdvance; - break; - } - - case RIL_CELL_INFO_TYPE_WCDMA: { - records[i].wcdma.resize(1); - CellInfoWcdma *cellInfoWcdma = &records[i].wcdma[0]; - cellInfoWcdma->cellIdentityWcdma.mcc = - ril::util::mcc::decode(rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.mcc); - cellInfoWcdma->cellIdentityWcdma.mnc = - ril::util::mnc::decode(rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.mnc); - cellInfoWcdma->cellIdentityWcdma.lac = - rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.lac; - cellInfoWcdma->cellIdentityWcdma.cid = - rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.cid; - cellInfoWcdma->cellIdentityWcdma.psc = - rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.psc; - cellInfoWcdma->cellIdentityWcdma.uarfcn = - rillCellInfo->CellInfo.wcdma.cellIdentityWcdma.uarfcn; - cellInfoWcdma->signalStrengthWcdma.signalStrength = - rillCellInfo->CellInfo.wcdma.signalStrengthWcdma.signalStrength; - cellInfoWcdma->signalStrengthWcdma.bitErrorRate = - rillCellInfo->CellInfo.wcdma.signalStrengthWcdma.bitErrorRate; - break; - } - - case RIL_CELL_INFO_TYPE_CDMA: { - records[i].cdma.resize(1); - CellInfoCdma *cellInfoCdma = &records[i].cdma[0]; - cellInfoCdma->cellIdentityCdma.networkId = - rillCellInfo->CellInfo.cdma.cellIdentityCdma.networkId; - cellInfoCdma->cellIdentityCdma.systemId = - rillCellInfo->CellInfo.cdma.cellIdentityCdma.systemId; - cellInfoCdma->cellIdentityCdma.baseStationId = - rillCellInfo->CellInfo.cdma.cellIdentityCdma.basestationId; - cellInfoCdma->cellIdentityCdma.longitude = - rillCellInfo->CellInfo.cdma.cellIdentityCdma.longitude; - cellInfoCdma->cellIdentityCdma.latitude = - rillCellInfo->CellInfo.cdma.cellIdentityCdma.latitude; - cellInfoCdma->signalStrengthCdma.dbm = - rillCellInfo->CellInfo.cdma.signalStrengthCdma.dbm; - cellInfoCdma->signalStrengthCdma.ecio = - rillCellInfo->CellInfo.cdma.signalStrengthCdma.ecio; - cellInfoCdma->signalStrengthEvdo.dbm = - rillCellInfo->CellInfo.cdma.signalStrengthEvdo.dbm; - cellInfoCdma->signalStrengthEvdo.ecio = - rillCellInfo->CellInfo.cdma.signalStrengthEvdo.ecio; - cellInfoCdma->signalStrengthEvdo.signalNoiseRatio = - rillCellInfo->CellInfo.cdma.signalStrengthEvdo.signalNoiseRatio; - break; - } - - case RIL_CELL_INFO_TYPE_LTE: { - records[i].lte.resize(1); - CellInfoLte *cellInfoLte = &records[i].lte[0]; - cellInfoLte->cellIdentityLte.mcc = - ril::util::mcc::decode(rillCellInfo->CellInfo.lte.cellIdentityLte.mcc); - cellInfoLte->cellIdentityLte.mnc = - ril::util::mnc::decode(rillCellInfo->CellInfo.lte.cellIdentityLte.mnc); - cellInfoLte->cellIdentityLte.ci = - rillCellInfo->CellInfo.lte.cellIdentityLte.ci; - cellInfoLte->cellIdentityLte.pci = - rillCellInfo->CellInfo.lte.cellIdentityLte.pci; - cellInfoLte->cellIdentityLte.tac = - rillCellInfo->CellInfo.lte.cellIdentityLte.tac; - cellInfoLte->cellIdentityLte.earfcn = - rillCellInfo->CellInfo.lte.cellIdentityLte.earfcn; - cellInfoLte->signalStrengthLte.signalStrength = - rillCellInfo->CellInfo.lte.signalStrengthLte.signalStrength; - cellInfoLte->signalStrengthLte.rsrp = - rillCellInfo->CellInfo.lte.signalStrengthLte.rsrp; - cellInfoLte->signalStrengthLte.rsrq = - rillCellInfo->CellInfo.lte.signalStrengthLte.rsrq; - cellInfoLte->signalStrengthLte.rssnr = - rillCellInfo->CellInfo.lte.signalStrengthLte.rssnr; - cellInfoLte->signalStrengthLte.cqi = - rillCellInfo->CellInfo.lte.signalStrengthLte.cqi; - cellInfoLte->signalStrengthLte.timingAdvance = - rillCellInfo->CellInfo.lte.signalStrengthLte.timingAdvance; - break; - } - - case RIL_CELL_INFO_TYPE_TD_SCDMA: { - records[i].tdscdma.resize(1); - CellInfoTdscdma *cellInfoTdscdma = &records[i].tdscdma[0]; - cellInfoTdscdma->cellIdentityTdscdma.mcc = - ril::util::mcc::decode( - rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.mcc); - cellInfoTdscdma->cellIdentityTdscdma.mnc = - ril::util::mnc::decode( - rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.mnc); - cellInfoTdscdma->cellIdentityTdscdma.lac = - rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.lac; - cellInfoTdscdma->cellIdentityTdscdma.cid = - rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.cid; - cellInfoTdscdma->cellIdentityTdscdma.cpid = - rillCellInfo->CellInfo.tdscdma.cellIdentityTdscdma.cpid; - cellInfoTdscdma->signalStrengthTdscdma.rscp = - rillCellInfo->CellInfo.tdscdma.signalStrengthTdscdma.rscp; - break; - } - default: { - break; - } - } - rillCellInfo += 1; - } -} - -int radio::cellInfoListInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if ((response == NULL && responseLen != 0) || responseLen % sizeof(RIL_CellInfo_v12) != 0) { - RLOGE("cellInfoListInd: invalid response"); - return 0; - } - - hidl_vec<CellInfo> records; - convertRilCellInfoListToHal(response, responseLen, records); - -#if VDBG - RLOGD("cellInfoListInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->cellInfoList( - convertIntToRadioIndicationType(indicationType), records); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("cellInfoListInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::imsNetworkStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { -#if VDBG - RLOGD("imsNetworkStateChangedInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->imsNetworkStateChanged( - convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("imsNetworkStateChangedInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::subscriptionStatusChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("subscriptionStatusChangedInd: invalid response"); - return 0; - } - bool activate = ((int32_t *) response)[0]; -#if VDBG - RLOGD("subscriptionStatusChangedInd: activate %d", activate); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->subscriptionStatusChanged( - convertIntToRadioIndicationType(indicationType), activate); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("subscriptionStatusChangedInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -int radio::srvccStateNotifyInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(int)) { - RLOGE("srvccStateNotifyInd: invalid response"); - return 0; - } - int32_t state = ((int32_t *) response)[0]; -#if VDBG - RLOGD("srvccStateNotifyInd: rat %d", state); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->srvccStateNotify( - convertIntToRadioIndicationType(indicationType), (SrvccState) state); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("srvccStateNotifyInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -void convertRilHardwareConfigListToHal(void *response, size_t responseLen, - hidl_vec<HardwareConfig>& records) { - int num = responseLen / sizeof(RIL_HardwareConfig); - records.resize(num); - - RIL_HardwareConfig *rilHardwareConfig = (RIL_HardwareConfig *) response; - for (int i = 0; i < num; i++) { - records[i].type = (HardwareConfigType) rilHardwareConfig[i].type; - records[i].uuid = convertCharPtrToHidlString(rilHardwareConfig[i].uuid); - records[i].state = (HardwareConfigState) rilHardwareConfig[i].state; - switch (rilHardwareConfig[i].type) { - case RIL_HARDWARE_CONFIG_MODEM: { - records[i].modem.resize(1); - records[i].sim.resize(0); - HardwareConfigModem *hwConfigModem = &records[i].modem[0]; - hwConfigModem->rat = rilHardwareConfig[i].cfg.modem.rat; - hwConfigModem->maxVoice = rilHardwareConfig[i].cfg.modem.maxVoice; - hwConfigModem->maxData = rilHardwareConfig[i].cfg.modem.maxData; - hwConfigModem->maxStandby = rilHardwareConfig[i].cfg.modem.maxStandby; - break; - } - - case RIL_HARDWARE_CONFIG_SIM: { - records[i].sim.resize(1); - records[i].modem.resize(0); - records[i].sim[0].modemUuid = - convertCharPtrToHidlString(rilHardwareConfig[i].cfg.sim.modemUuid); - break; - } - } - } -} - -int radio::hardwareConfigChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if ((response == NULL && responseLen != 0) - || responseLen % sizeof(RIL_HardwareConfig) != 0) { - RLOGE("hardwareConfigChangedInd: invalid response"); - return 0; - } - - hidl_vec<HardwareConfig> configs; - convertRilHardwareConfigListToHal(response, responseLen, configs); - -#if VDBG - RLOGD("hardwareConfigChangedInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->hardwareConfigChanged( - convertIntToRadioIndicationType(indicationType), configs); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("hardwareConfigChangedInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -void convertRilRadioCapabilityToHal(void *response, size_t responseLen, RadioCapability& rc) { - RIL_RadioCapability *rilRadioCapability = (RIL_RadioCapability *) response; - rc.session = rilRadioCapability->session; - rc.phase = (V1_0::RadioCapabilityPhase) rilRadioCapability->phase; - rc.raf = rilRadioCapability->rat; - rc.logicalModemUuid = convertCharPtrToHidlString(rilRadioCapability->logicalModemUuid); - rc.status = (V1_0::RadioCapabilityStatus) rilRadioCapability->status; -} - -int radio::radioCapabilityIndicationInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_RadioCapability)) { - RLOGE("radioCapabilityIndicationInd: invalid response"); - return 0; - } - - RadioCapability rc = {}; - convertRilRadioCapabilityToHal(response, responseLen, rc); - -#if VDBG - RLOGD("radioCapabilityIndicationInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->radioCapabilityIndication( - convertIntToRadioIndicationType(indicationType), rc); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("radioCapabilityIndicationInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -bool isServiceTypeCfQuery(RIL_SsServiceType serType, RIL_SsRequestType reqType) { - if ((reqType == SS_INTERROGATION) && - (serType == SS_CFU || - serType == SS_CF_BUSY || - serType == SS_CF_NO_REPLY || - serType == SS_CF_NOT_REACHABLE || - serType == SS_CF_ALL || - serType == SS_CF_ALL_CONDITIONAL)) { - return true; - } - return false; -} - -int radio::onSupplementaryServiceIndicationInd(int slotId, - int indicationType, int token, RIL_Errno e, - void *response, size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_StkCcUnsolSsResponse)) { - RLOGE("onSupplementaryServiceIndicationInd: invalid response"); - return 0; - } - - RIL_StkCcUnsolSsResponse *rilSsResponse = (RIL_StkCcUnsolSsResponse *) response; - StkCcUnsolSsResult ss = {}; - ss.serviceType = (SsServiceType) rilSsResponse->serviceType; - ss.requestType = (SsRequestType) rilSsResponse->requestType; - ss.teleserviceType = (SsTeleserviceType) rilSsResponse->teleserviceType; - ss.serviceClass = rilSsResponse->serviceClass; - ss.result = (RadioError) rilSsResponse->result; - - if (isServiceTypeCfQuery(rilSsResponse->serviceType, rilSsResponse->requestType)) { -#if VDBG - RLOGD("onSupplementaryServiceIndicationInd CF type, num of Cf elements %d", - rilSsResponse->cfData.numValidIndexes); -#endif - if (rilSsResponse->cfData.numValidIndexes > NUM_SERVICE_CLASSES) { - RLOGE("onSupplementaryServiceIndicationInd numValidIndexes is greater than " - "max value %d, truncating it to max value", NUM_SERVICE_CLASSES); - rilSsResponse->cfData.numValidIndexes = NUM_SERVICE_CLASSES; - } - - ss.cfData.resize(1); - ss.ssInfo.resize(0); - - /* number of call info's */ - ss.cfData[0].cfInfo.resize(rilSsResponse->cfData.numValidIndexes); - - for (int i = 0; i < rilSsResponse->cfData.numValidIndexes; i++) { - RIL_CallForwardInfo cf = rilSsResponse->cfData.cfInfo[i]; - CallForwardInfo *cfInfo = &ss.cfData[0].cfInfo[i]; - - cfInfo->status = (CallForwardInfoStatus) cf.status; - cfInfo->reason = cf.reason; - cfInfo->serviceClass = cf.serviceClass; - cfInfo->toa = cf.toa; - cfInfo->number = convertCharPtrToHidlString(cf.number); - cfInfo->timeSeconds = cf.timeSeconds; -#if VDBG - RLOGD("onSupplementaryServiceIndicationInd: " - "Data: %d,reason=%d,cls=%d,toa=%d,num=%s,tout=%d],", cf.status, - cf.reason, cf.serviceClass, cf.toa, (char*)cf.number, cf.timeSeconds); -#endif - } - } else { - ss.ssInfo.resize(1); - ss.cfData.resize(0); - - /* each int */ - ss.ssInfo[0].ssInfo.resize(SS_INFO_MAX); - for (int i = 0; i < SS_INFO_MAX; i++) { -#if VDBG - RLOGD("onSupplementaryServiceIndicationInd: Data: %d", - rilSsResponse->ssInfo[i]); -#endif - ss.ssInfo[0].ssInfo[i] = rilSsResponse->ssInfo[i]; - } - } - -#if VDBG - RLOGD("onSupplementaryServiceIndicationInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication-> - onSupplementaryServiceIndication(convertIntToRadioIndicationType(indicationType), - ss); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("onSupplementaryServiceIndicationInd: " - "radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::stkCallControlAlphaNotifyInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("stkCallControlAlphaNotifyInd: invalid response"); - return 0; - } -#if VDBG - RLOGD("stkCallControlAlphaNotifyInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->stkCallControlAlphaNotify( - convertIntToRadioIndicationType(indicationType), - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("stkCallControlAlphaNotifyInd: radioService[%d]->mRadioIndication == NULL", - slotId); - } - - return 0; -} - -void convertRilLceDataInfoToHal(void *response, size_t responseLen, LceDataInfo& lce) { - RIL_LceDataInfo *rilLceDataInfo = (RIL_LceDataInfo *)response; - lce.lastHopCapacityKbps = rilLceDataInfo->last_hop_capacity_kbps; - lce.confidenceLevel = rilLceDataInfo->confidence_level; - lce.lceSuspended = rilLceDataInfo->lce_suspended; -} - -int radio::lceDataInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_LceDataInfo)) { - RLOGE("lceDataInd: invalid response"); - return 0; - } - - LceDataInfo lce = {}; - convertRilLceDataInfoToHal(response, responseLen, lce); -#if VDBG - RLOGD("lceDataInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->lceData( - convertIntToRadioIndicationType(indicationType), lce); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("lceDataInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::pcoDataInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen != sizeof(RIL_PCO_Data)) { - RLOGE("pcoDataInd: invalid response"); - return 0; - } - - PcoDataInfo pco = {}; - RIL_PCO_Data *rilPcoData = (RIL_PCO_Data *)response; - pco.cid = rilPcoData->cid; - pco.bearerProto = convertCharPtrToHidlString(rilPcoData->bearer_proto); - pco.pcoId = rilPcoData->pco_id; - pco.contents.setToExternal((uint8_t *) rilPcoData->contents, rilPcoData->contents_length); - -#if VDBG - RLOGD("pcoDataInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->pcoData( - convertIntToRadioIndicationType(indicationType), pco); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("pcoDataInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::modemResetInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("modemResetInd: invalid response"); - return 0; - } -#if VDBG - RLOGD("modemResetInd"); -#endif - Return<void> retStatus = radioService[slotId]->mRadioIndication->modemReset( - convertIntToRadioIndicationType(indicationType), - convertCharPtrToHidlString((char *) response)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("modemResetInd: radioService[%d]->mRadioIndication == NULL", slotId); - } - - return 0; -} - -int radio::networkScanResultInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("networkScanResultInd"); -#endif - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndicationV1_1 != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("networkScanResultInd: invalid response"); - return 0; - } - RLOGD("networkScanResultInd"); - -#if VDBG - RLOGD("networkScanResultInd"); -#endif - - RIL_NetworkScanResult *networkScanResult = (RIL_NetworkScanResult *) response; - - V1_1::NetworkScanResult result; - result.status = (V1_1::ScanStatus) networkScanResult->status; - result.error = (RadioError) networkScanResult->error; - convertRilCellInfoListToHal( - networkScanResult->network_infos, - networkScanResult->network_infos_length * sizeof(RIL_CellInfo_v12), - result.networkInfos); - - Return<void> retStatus = radioService[slotId]->mRadioIndicationV1_1->networkScanResult( - convertIntToRadioIndicationType(indicationType), result); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("networkScanResultInd: radioService[%d]->mRadioIndicationV1_1 == NULL", slotId); - } - return 0; -} - -int radio::carrierInfoForImsiEncryption(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (radioService[slotId] != NULL && radioService[slotId]->mRadioIndicationV1_1 != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("carrierInfoForImsiEncryption: invalid response"); - return 0; - } - RLOGD("carrierInfoForImsiEncryption"); - Return<void> retStatus = radioService[slotId]->mRadioIndicationV1_1-> - carrierInfoForImsiEncryption(convertIntToRadioIndicationType(indicationType)); - radioService[slotId]->checkReturnStatus(retStatus); - } else { - RLOGE("carrierInfoForImsiEncryption: radioService[%d]->mRadioIndicationV1_1 == NULL", - slotId); - } - - return 0; -} - -int radio::keepaliveStatusInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { -#if VDBG - RLOGD("%s(): token=%d", __FUNCTION__, token); -#endif - if (radioService[slotId] == NULL || radioService[slotId]->mRadioIndication == NULL) { - RLOGE("%s: radioService[%d]->mRadioIndication == NULL", __FUNCTION__, slotId); - return 0; - } - - auto ret = V1_1::IRadioIndication::castFrom( - radioService[slotId]->mRadioIndication); - if (!ret.isOk()) { - RLOGE("%s: ret.isOk() == false for radioService[%d]", __FUNCTION__, slotId); - return 0; - } - sp<V1_1::IRadioIndication> radioIndicationV1_1 = ret; - - if (response == NULL || responseLen != sizeof(V1_1::KeepaliveStatus)) { - RLOGE("%s: invalid response", __FUNCTION__); - return 0; - } - - V1_1::KeepaliveStatus ks; - convertRilKeepaliveStatusToHal(static_cast<RIL_KeepaliveStatus*>(response), ks); - - Return<void> retStatus = radioIndicationV1_1->keepaliveStatus( - convertIntToRadioIndicationType(indicationType), ks); - radioService[slotId]->checkReturnStatus(retStatus); - return 0; -} - -int radio::oemHookRawInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen) { - if (!kOemHookEnabled) return 0; - - if (oemHookService[slotId] != NULL && oemHookService[slotId]->mOemHookIndication != NULL) { - if (response == NULL || responseLen == 0) { - RLOGE("oemHookRawInd: invalid response"); - return 0; - } - - hidl_vec<uint8_t> data; - data.setToExternal((uint8_t *) response, responseLen); -#if VDBG - RLOGD("oemHookRawInd"); -#endif - Return<void> retStatus = oemHookService[slotId]->mOemHookIndication->oemHookRaw( - convertIntToRadioIndicationType(indicationType), data); - checkReturnStatus(slotId, retStatus, false); - } else { - RLOGE("oemHookRawInd: oemHookService[%d]->mOemHookIndication == NULL", slotId); - } - - return 0; -} - -void radio::registerService(RIL_RadioFunctions *callbacks, CommandInfo *commands) { - using namespace android::hardware; - int simCount = 1; - const char *serviceNames[] = { - android::RIL_getServiceName() - #if (SIM_COUNT >= 2) - , RIL2_SERVICE_NAME - #if (SIM_COUNT >= 3) - , RIL3_SERVICE_NAME - #if (SIM_COUNT >= 4) - , RIL4_SERVICE_NAME - #endif - #endif - #endif - }; - - #if (SIM_COUNT >= 2) - simCount = SIM_COUNT; - #endif - - s_vendorFunctions = callbacks; - s_commands = commands; - - configureRpcThreadpool(1, true /* callerWillJoin */); - for (int i = 0; i < simCount; i++) { - pthread_rwlock_t *radioServiceRwlockPtr = getRadioServiceRwlock(i); - int ret = pthread_rwlock_wrlock(radioServiceRwlockPtr); - assert(ret == 0); - - radioService[i] = new RadioImpl; - radioService[i]->mSlotId = i; - RLOGD("registerService: starting android::hardware::radio::V1_1::IRadio %s", - serviceNames[i]); - android::status_t status = radioService[i]->registerAsService(serviceNames[i]); - - if (kOemHookEnabled) { - oemHookService[i] = new OemHookImpl; - oemHookService[i]->mSlotId = i; - status = oemHookService[i]->registerAsService(serviceNames[i]); - } - - ret = pthread_rwlock_unlock(radioServiceRwlockPtr); - assert(ret == 0); - } -} - -void rilc_thread_pool() { - joinRpcThreadpool(); -} - -pthread_rwlock_t * radio::getRadioServiceRwlock(int slotId) { - pthread_rwlock_t *radioServiceRwlockPtr = &radioServiceRwlock; - - #if (SIM_COUNT >= 2) - if (slotId == 2) radioServiceRwlockPtr = &radioServiceRwlock2; - #if (SIM_COUNT >= 3) - if (slotId == 3) radioServiceRwlockPtr = &radioServiceRwlock3; - #if (SIM_COUNT >= 4) - if (slotId == 4) radioServiceRwlockPtr = &radioServiceRwlock4; - #endif - #endif - #endif - - return radioServiceRwlockPtr; -} - -// should acquire write lock for the corresponding service before calling this -void radio::setNitzTimeReceived(int slotId, long timeReceived) { - nitzTimeReceived[slotId] = timeReceived; -} diff --git a/radio/libril/ril_service.h b/radio/libril/ril_service.h deleted file mode 100644 index ba4f0d20..00000000 --- a/radio/libril/ril_service.h +++ /dev/null @@ -1,753 +0,0 @@ -/* - * 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. - */ - -#ifndef RIL_SERVICE_H -#define RIL_SERVICE_H - -#include <telephony/ril.h> -#include <ril_internal.h> - -namespace radio { -void registerService(RIL_RadioFunctions *callbacks, android::CommandInfo *commands); - -int getIccCardStatusResponse(int slotId, int responseType, - int token, RIL_Errno e, void *response, size_t responselen); - -int supplyIccPinForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int supplyIccPukForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int supplyIccPin2ForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int supplyIccPuk2ForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int changeIccPinForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int changeIccPin2ForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int supplyNetworkDepersonalizationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int getCurrentCallsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int dialResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, size_t responselen); - -int getIMSIForAppResponse(int slotId, int responseType, - int serial, RIL_Errno e, void *response, size_t responselen); - -int hangupConnectionResponse(int slotId, int responseType, - int serial, RIL_Errno e, void *response, size_t responselen); - -int hangupWaitingOrBackgroundResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int hangupForegroundResumeBackgroundResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int switchWaitingOrHoldingAndActiveResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int conferenceResponse(int slotId, int responseType, - int serial, RIL_Errno e, void *response, size_t responselen); - -int rejectCallResponse(int slotId, int responseType, - int serial, RIL_Errno e, void *response, size_t responselen); - -int getLastCallFailCauseResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getSignalStrengthResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int getVoiceRegistrationStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getDataRegistrationStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getOperatorResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setRadioPowerResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendSMSExpectMoreResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setupDataCallResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responseLen); - -int iccIOForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendUssdResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int cancelPendingUssdResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getClirResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, size_t responselen); - -int setClirResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, size_t responselen); - -int getCallForwardStatusResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setCallForwardResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getCallWaitingResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setCallWaitingResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int acknowledgeLastIncomingGsmSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int acceptCallResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int deactivateDataCallResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getFacilityLockForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setFacilityLockForAppResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setBarringPasswordResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getNetworkSelectionModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setNetworkSelectionModeAutomaticResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setNetworkSelectionModeManualResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getAvailableNetworksResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int startNetworkScanResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int stopNetworkScanResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int startDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int stopDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getBasebandVersionResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int separateConnectionResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setMuteResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getMuteResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getClipResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getDataCallListResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int setSuppServiceNotificationsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int writeSmsToSimResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int deleteSmsOnSimResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setBandModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getAvailableBandModesResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendEnvelopeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendTerminalResponseToSimResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int handleStkCallSetupRequestFromSimResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int explicitCallTransferResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setPreferredNetworkTypeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getPreferredNetworkTypeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getNeighboringCidsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setLocationUpdatesResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setCdmaSubscriptionSourceResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setCdmaRoamingPreferenceResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getCdmaRoamingPreferenceResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setTTYModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getTTYModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setPreferredVoicePrivacyResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getPreferredVoicePrivacyResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendCDMAFeatureCodeResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int sendBurstDtmfResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int sendCdmaSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int acknowledgeLastIncomingCdmaSmsResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getGsmBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setGsmBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setGsmBroadcastActivationResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getCdmaBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setCdmaBroadcastConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setCdmaBroadcastActivationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int getCDMASubscriptionResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int writeSmsToRuimResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int deleteSmsOnRuimResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getDeviceIdentityResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int exitEmergencyCallbackModeResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getSmscAddressResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int setCdmaBroadcastActivationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setSmscAddressResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int reportSmsMemoryStatusResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int reportStkServiceIsRunningResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int getCdmaSubscriptionSourceResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int requestIsimAuthenticationResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int acknowledgeIncomingGsmSmsWithPduResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int sendEnvelopeWithStatusResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - -int getVoiceRadioTechnologyResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int getCellInfoListResponse(int slotId, - int responseType, - int serial, RIL_Errno e, void *response, - size_t responseLen); - -int setCellInfoListRateResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setInitialAttachApnResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int getImsRegistrationStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int sendImsSmsResponse(int slotId, int responseType, - int serial, RIL_Errno e, void *response, size_t responselen); - -int iccTransmitApduBasicChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int iccOpenLogicalChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, void *response, - size_t responselen); - - -int iccCloseLogicalChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int iccTransmitApduLogicalChannelResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int nvReadItemResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - - -int nvWriteItemResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int nvWriteCdmaPrlResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int nvResetConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setUiccSubscriptionResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setDataAllowedResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int getHardwareConfigResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int requestIccSimAuthenticationResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setDataProfileResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int requestShutdownResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int getRadioCapabilityResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int setRadioCapabilityResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int startLceServiceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int stopLceServiceResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int pullLceDataResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int getModemActivityInfoResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setAllowedCarriersResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int getAllowedCarriersResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int sendDeviceStateResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setIndicationFilterResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int setSimCardPowerResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int startKeepaliveResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -int stopKeepaliveResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responselen); - -void acknowledgeRequest(int slotId, int serial); - -int radioStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responseLen); - -int callStateChangedInd(int slotId, int indType, int token, - RIL_Errno e, void *response, size_t responselen); - -int networkStateChangedInd(int slotId, int indType, - int token, RIL_Errno e, void *response, size_t responselen); - -int newSmsInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int newSmsStatusReportInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int newSmsOnSimInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int onUssdInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int nitzTimeReceivedInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int reportPhysicalChannelConfigs(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int currentSignalStrengthInd(int slotId, - int indicationType, int token, RIL_Errno e, - void *response, size_t responselen); - -int dataCallListChangedInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int suppSvcNotifyInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int stkSessionEndInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int stkProactiveCommandInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int stkEventNotifyInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int stkCallSetupInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int simSmsStorageFullInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int simRefreshInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int callRingInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int simStatusChangedInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int cdmaNewSmsInd(int slotId, int indicationType, - int token, RIL_Errno e, void *response, size_t responselen); - -int newBroadcastSmsInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int cdmaRuimSmsStorageFullInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int restrictedStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int enterEmergencyCallbackModeInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int cdmaCallWaitingInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int cdmaOtaProvisionStatusInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int cdmaInfoRecInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int oemHookRawInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int indicateRingbackToneInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int resendIncallMuteInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int cdmaSubscriptionSourceChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, - void *response, size_t responselen); - -int cdmaPrlChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int exitEmergencyCallbackModeInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int rilConnectedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int voiceRadioTechChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int cellInfoListInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int imsNetworkStateChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int subscriptionStatusChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int srvccStateNotifyInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int hardwareConfigChangedInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int radioCapabilityIndicationInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int onSupplementaryServiceIndicationInd(int slotId, - int indicationType, int token, RIL_Errno e, - void *response, size_t responselen); - -int stkCallControlAlphaNotifyInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int lceDataInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int pcoDataInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int modemResetInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int networkScanResultInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int keepaliveStatusInd(int slotId, - int indicationType, int token, RIL_Errno e, void *response, - size_t responselen); - -int sendRequestRawResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int sendRequestStringsResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int setCarrierInfoForImsiEncryptionResponse(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -int carrierInfoForImsiEncryption(int slotId, - int responseType, int serial, RIL_Errno e, - void *response, size_t responseLen); - -pthread_rwlock_t * getRadioServiceRwlock(int slotId); - -void setNitzTimeReceived(int slotId, long timeReceived); - -} // namespace radio - -#endif // RIL_SERVICE_H diff --git a/radio/libril/ril_unsol_commands.h b/radio/libril/ril_unsol_commands.h deleted file mode 100644 index 5ec37caf..00000000 --- a/radio/libril/ril_unsol_commands.h +++ /dev/null @@ -1,68 +0,0 @@ -/* //device/libs/telephony/ril_unsol_commands.h -** -** Copyright 2006, 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. -*/ - {RIL_UNSOL_RESPONSE_RADIO_STATE_CHANGED, radio::radioStateChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_CALL_STATE_CHANGED, radio::callStateChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_VOICE_NETWORK_STATE_CHANGED, radio::networkStateChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_NEW_SMS, radio::newSmsInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT, radio::newSmsStatusReportInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_NEW_SMS_ON_SIM, radio::newSmsOnSimInd, WAKE_PARTIAL}, - {RIL_UNSOL_ON_USSD, radio::onUssdInd, WAKE_PARTIAL}, - {RIL_UNSOL_ON_USSD_REQUEST, radio::onUssdInd, DONT_WAKE}, - {RIL_UNSOL_NITZ_TIME_RECEIVED, radio::nitzTimeReceivedInd, WAKE_PARTIAL}, - {RIL_UNSOL_SIGNAL_STRENGTH, radio::currentSignalStrengthInd, DONT_WAKE}, - {RIL_UNSOL_DATA_CALL_LIST_CHANGED, radio::dataCallListChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_SUPP_SVC_NOTIFICATION, radio::suppSvcNotifyInd, WAKE_PARTIAL}, - {RIL_UNSOL_STK_SESSION_END, radio::stkSessionEndInd, WAKE_PARTIAL}, - {RIL_UNSOL_STK_PROACTIVE_COMMAND, radio::stkProactiveCommandInd, WAKE_PARTIAL}, - {RIL_UNSOL_STK_EVENT_NOTIFY, radio::stkEventNotifyInd, WAKE_PARTIAL}, - {RIL_UNSOL_STK_CALL_SETUP, radio::stkCallSetupInd, WAKE_PARTIAL}, - {RIL_UNSOL_SIM_SMS_STORAGE_FULL, radio::simSmsStorageFullInd, WAKE_PARTIAL}, - {RIL_UNSOL_SIM_REFRESH, radio::simRefreshInd, WAKE_PARTIAL}, - {RIL_UNSOL_CALL_RING, radio::callRingInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_SIM_STATUS_CHANGED, radio::simStatusChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_CDMA_NEW_SMS, radio::cdmaNewSmsInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_NEW_BROADCAST_SMS, radio::newBroadcastSmsInd, WAKE_PARTIAL}, - {RIL_UNSOL_CDMA_RUIM_SMS_STORAGE_FULL, radio::cdmaRuimSmsStorageFullInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESTRICTED_STATE_CHANGED, radio::restrictedStateChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_ENTER_EMERGENCY_CALLBACK_MODE, radio::enterEmergencyCallbackModeInd, WAKE_PARTIAL}, - {RIL_UNSOL_CDMA_CALL_WAITING, radio::cdmaCallWaitingInd, WAKE_PARTIAL}, - {RIL_UNSOL_CDMA_OTA_PROVISION_STATUS, radio::cdmaOtaProvisionStatusInd, WAKE_PARTIAL}, - {RIL_UNSOL_CDMA_INFO_REC, radio::cdmaInfoRecInd, WAKE_PARTIAL}, - {RIL_UNSOL_OEM_HOOK_RAW, radio::oemHookRawInd, WAKE_PARTIAL}, - {RIL_UNSOL_RINGBACK_TONE, radio::indicateRingbackToneInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESEND_INCALL_MUTE, radio::resendIncallMuteInd, WAKE_PARTIAL}, - {RIL_UNSOL_CDMA_SUBSCRIPTION_SOURCE_CHANGED, radio::cdmaSubscriptionSourceChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_CDMA_PRL_CHANGED, radio::cdmaPrlChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_EXIT_EMERGENCY_CALLBACK_MODE, radio::exitEmergencyCallbackModeInd, WAKE_PARTIAL}, - {RIL_UNSOL_RIL_CONNECTED, radio::rilConnectedInd, WAKE_PARTIAL}, - {RIL_UNSOL_VOICE_RADIO_TECH_CHANGED, radio::voiceRadioTechChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_CELL_INFO_LIST, radio::cellInfoListInd, WAKE_PARTIAL}, - {RIL_UNSOL_RESPONSE_IMS_NETWORK_STATE_CHANGED, radio::imsNetworkStateChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_UICC_SUBSCRIPTION_STATUS_CHANGED, radio::subscriptionStatusChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_SRVCC_STATE_NOTIFY, radio::srvccStateNotifyInd, WAKE_PARTIAL}, - {RIL_UNSOL_HARDWARE_CONFIG_CHANGED, radio::hardwareConfigChangedInd, WAKE_PARTIAL}, - {RIL_UNSOL_DC_RT_INFO_CHANGED, NULL, WAKE_PARTIAL}, - {RIL_UNSOL_RADIO_CAPABILITY, radio::radioCapabilityIndicationInd, WAKE_PARTIAL}, - {RIL_UNSOL_ON_SS, radio::onSupplementaryServiceIndicationInd, WAKE_PARTIAL}, - {RIL_UNSOL_STK_CC_ALPHA_NOTIFY, radio::stkCallControlAlphaNotifyInd, WAKE_PARTIAL}, - {RIL_UNSOL_LCEDATA_RECV, radio::lceDataInd, WAKE_PARTIAL}, - {RIL_UNSOL_PCO_DATA, radio::pcoDataInd, WAKE_PARTIAL}, - {RIL_UNSOL_MODEM_RESTART, radio::modemResetInd, WAKE_PARTIAL}, - {RIL_UNSOL_CARRIER_INFO_IMSI_ENCRYPTION, radio::carrierInfoForImsiEncryption, WAKE_PARTIAL}, - {RIL_UNSOL_NETWORK_SCAN_RESULT, radio::networkScanResultInd, WAKE_PARTIAL}, - {RIL_UNSOL_KEEPALIVE_STATUS, radio::keepaliveStatusInd, WAKE_PARTIAL}, - {RIL_UNSOL_PHYSICAL_CHANNEL_CONFIGS, radio::reportPhysicalChannelConfigs, WAKE_PARTIAL}, diff --git a/radio/libril/sap_service.cpp b/radio/libril/sap_service.cpp deleted file mode 100644 index cd5b1378..00000000 --- a/radio/libril/sap_service.cpp +++ /dev/null @@ -1,966 +0,0 @@ -/* - * 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. - */ - -#define LOG_TAG "RIL_SAP" - -#include <android/hardware/radio/1.1/ISap.h> - -#include <hwbinder/IPCThreadState.h> -#include <hwbinder/ProcessState.h> -#include <sap_service.h> -#include "pb_decode.h" -#include "pb_encode.h" - -using namespace android::hardware::radio::V1_0; -using ::android::hardware::Return; -using ::android::hardware::hidl_vec; -using ::android::hardware::hidl_array; -using ::android::hardware::Void; -using android::CommandInfo; -using android::RequestInfo; -using android::requestToString; -using android::sp; - -struct SapImpl; - -#if (SIM_COUNT >= 2) -sp<SapImpl> sapService[SIM_COUNT]; -#else -sp<SapImpl> sapService[1]; -#endif - -struct SapImpl : public android::hardware::radio::V1_1::ISap { - int32_t slotId; - sp<ISapCallback> sapCallback; - RIL_SOCKET_ID rilSocketId; - - Return<void> setCallback(const ::android::sp<ISapCallback>& sapCallbackParam); - - Return<void> connectReq(int32_t token, int32_t maxMsgSize); - - Return<void> disconnectReq(int32_t token); - - Return<void> apduReq(int32_t token, SapApduType type, const hidl_vec<uint8_t>& command); - - Return<void> transferAtrReq(int32_t token); - - Return<void> powerReq(int32_t token, bool state); - - Return<void> resetSimReq(int32_t token); - - Return<void> transferCardReaderStatusReq(int32_t token); - - Return<void> setTransferProtocolReq(int32_t token, SapTransferProtocol transferProtocol); - - MsgHeader* createMsgHeader(MsgId msgId, int32_t token); - - Return<void> addPayloadAndDispatchRequest(MsgHeader *msg, uint16_t reqLen, uint8_t *reqPtr); - - void sendFailedResponse(MsgId msgId, int32_t token, int numPointers, ...); - - void checkReturnStatus(Return<void>& ret); -}; - -void SapImpl::checkReturnStatus(Return<void>& ret) { - if (ret.isOk() == false) { - RLOGE("checkReturnStatus: unable to call response/indication callback: %s", - ret.description().c_str()); - // Remote process (SapRilReceiver.java) hosting the callback must be dead. Reset the - // callback object; there's no other recovery to be done here. When the client process is - // back up, it will call setCallback() - sapCallback = NULL; - } -} - -Return<void> SapImpl::setCallback(const ::android::sp<ISapCallback>& sapCallbackParam) { - RLOGD("SapImpl::setCallback for slotId %d", slotId); - sapCallback = sapCallbackParam; - return Void(); -} - -MsgHeader* SapImpl::createMsgHeader(MsgId msgId, int32_t token) { - // Memory for msg will be freed by RilSapSocket::onRequestComplete() - MsgHeader *msg = (MsgHeader *)calloc(1, sizeof(MsgHeader)); - if (msg == NULL) { - return NULL; - } - msg->token = token; - msg->type = MsgType_REQUEST; - msg->id = msgId; - msg->error = Error_RIL_E_SUCCESS; - return msg; -} - -Return<void> SapImpl::addPayloadAndDispatchRequest(MsgHeader *msg, uint16_t reqLen, - uint8_t *reqPtr) { - pb_bytes_array_t *payload = (pb_bytes_array_t *) malloc(sizeof(pb_bytes_array_t) - 1 + reqLen); - if (payload == NULL) { - sendFailedResponse(msg->id, msg->token, 2, reqPtr, msg); - return Void(); - } - - msg->payload = payload; - msg->payload->size = reqLen; - memcpy(msg->payload->bytes, reqPtr, reqLen); - - RilSapSocket *sapSocket = RilSapSocket::getSocketById(rilSocketId); - if (sapSocket) { - RLOGD("SapImpl::addPayloadAndDispatchRequest: calling dispatchRequest"); - sapSocket->dispatchRequest(msg); - } else { - RLOGE("SapImpl::addPayloadAndDispatchRequest: sapSocket is null"); - sendFailedResponse(msg->id, msg->token, 3, payload, reqPtr, msg); - return Void(); - } - free(msg->payload); - free(reqPtr); - return Void(); -} - -void SapImpl::sendFailedResponse(MsgId msgId, int32_t token, int numPointers, ...) { - va_list ap; - va_start(ap, numPointers); - for (int i = 0; i < numPointers; i++) { - void *ptr = va_arg(ap, void *); - if (ptr) free(ptr); - } - va_end(ap); - Return<void> retStatus; - switch(msgId) { - case MsgId_RIL_SIM_SAP_CONNECT: - retStatus = sapCallback->connectResponse(token, SapConnectRsp::CONNECT_FAILURE, 0); - break; - - case MsgId_RIL_SIM_SAP_DISCONNECT: - retStatus = sapCallback->disconnectResponse(token); - break; - - case MsgId_RIL_SIM_SAP_APDU: { - hidl_vec<uint8_t> apduRsp; - retStatus = sapCallback->apduResponse(token, SapResultCode::GENERIC_FAILURE, apduRsp); - break; - } - - case MsgId_RIL_SIM_SAP_TRANSFER_ATR: { - hidl_vec<uint8_t> atr; - retStatus = sapCallback->transferAtrResponse(token, SapResultCode::GENERIC_FAILURE, - atr); - break; - } - - case MsgId_RIL_SIM_SAP_POWER: - retStatus = sapCallback->powerResponse(token, SapResultCode::GENERIC_FAILURE); - break; - - case MsgId_RIL_SIM_SAP_RESET_SIM: - retStatus = sapCallback->resetSimResponse(token, SapResultCode::GENERIC_FAILURE); - break; - - case MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS: - retStatus = sapCallback->transferCardReaderStatusResponse(token, - SapResultCode::GENERIC_FAILURE, 0); - break; - - case MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL: - retStatus = sapCallback->transferProtocolResponse(token, SapResultCode::NOT_SUPPORTED); - break; - - default: - return; - } - sapService[slotId]->checkReturnStatus(retStatus); -} - -Return<void> SapImpl::connectReq(int32_t token, int32_t maxMsgSize) { - RLOGD("SapImpl::connectReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_CONNECT, token); - if (msg == NULL) { - RLOGE("SapImpl::connectReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_CONNECT, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_CONNECT_REQ *****/ - RIL_SIM_SAP_CONNECT_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_CONNECT_REQ)); - req.max_message_size = maxMsgSize; - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_CONNECT_REQ_fields, &req)) { - RLOGE("SapImpl::connectReq: Error getting encoded size for RIL_SIM_SAP_CONNECT_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_CONNECT, token, 1, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::connectReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_CONNECT, token, 1, msg); - return Void(); - } - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::connectReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_CONNECT_REQ_fields, &req)) { - RLOGE("SapImpl::connectReq: Error encoding RIL_SIM_SAP_CONNECT_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_CONNECT, token, 2, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_CONNECT_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -Return<void> SapImpl::disconnectReq(int32_t token) { - RLOGD("SapImpl::disconnectReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_DISCONNECT, token); - if (msg == NULL) { - RLOGE("SapImpl::disconnectReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_DISCONNECT, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_DISCONNECT_REQ *****/ - RIL_SIM_SAP_DISCONNECT_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_DISCONNECT_REQ)); - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_DISCONNECT_REQ_fields, &req)) { - RLOGE("SapImpl::disconnectReq: Error getting encoded size for RIL_SIM_SAP_DISCONNECT_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_DISCONNECT, token, 1, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::disconnectReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_DISCONNECT, token, 1, msg); - return Void(); - } - - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::disconnectReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_DISCONNECT_REQ_fields, &req)) { - RLOGE("SapImpl::disconnectReq: Error encoding RIL_SIM_SAP_DISCONNECT_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_DISCONNECT, token, 2, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_DISCONNECT_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -Return<void> SapImpl::apduReq(int32_t token, SapApduType type, const hidl_vec<uint8_t>& command) { - RLOGD("SapImpl::apduReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_APDU, token); - if (msg == NULL) { - RLOGE("SapImpl::apduReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_APDU, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_APDU_REQ *****/ - RIL_SIM_SAP_APDU_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_APDU_REQ)); - req.type = (RIL_SIM_SAP_APDU_REQ_Type)type; - - if (command.size() > 0) { - req.command = (pb_bytes_array_t *)malloc(sizeof(pb_bytes_array_t) - 1 + command.size()); - if (req.command == NULL) { - RLOGE("SapImpl::apduReq: Error allocating memory for req.command"); - sendFailedResponse(MsgId_RIL_SIM_SAP_APDU, token, 1, msg); - return Void(); - } - req.command->size = command.size(); - memcpy(req.command->bytes, command.data(), command.size()); - } - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_APDU_REQ_fields, &req)) { - RLOGE("SapImpl::apduReq: Error getting encoded size for RIL_SIM_SAP_APDU_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_APDU, token, 2, req.command, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::apduReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_APDU, token, 2, req.command, msg); - return Void(); - } - - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::apduReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_APDU_REQ_fields, &req)) { - RLOGE("SapImpl::apduReq: Error encoding RIL_SIM_SAP_APDU_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_APDU, token, 3, req.command, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_APDU_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -Return<void> SapImpl::transferAtrReq(int32_t token) { - RLOGD("SapImpl::transferAtrReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_TRANSFER_ATR, token); - if (msg == NULL) { - RLOGE("SapImpl::transferAtrReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_ATR, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_TRANSFER_ATR_REQ *****/ - RIL_SIM_SAP_TRANSFER_ATR_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_TRANSFER_ATR_REQ)); - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_TRANSFER_ATR_REQ_fields, &req)) { - RLOGE("SapImpl::transferAtrReq: Error getting encoded size for " - "RIL_SIM_SAP_TRANSFER_ATR_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_ATR, token, 1, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::transferAtrReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_ATR, token, 1, msg); - return Void(); - } - - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::transferAtrReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_TRANSFER_ATR_REQ_fields, &req)) { - RLOGE("SapImpl::transferAtrReq: Error encoding RIL_SIM_SAP_TRANSFER_ATR_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_ATR, token, 2, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_TRANSFER_ATR_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -Return<void> SapImpl::powerReq(int32_t token, bool state) { - RLOGD("SapImpl::powerReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_POWER, token); - if (msg == NULL) { - RLOGE("SapImpl::powerReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_POWER, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_POWER_REQ *****/ - RIL_SIM_SAP_POWER_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_POWER_REQ)); - req.state = state; - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_POWER_REQ_fields, &req)) { - RLOGE("SapImpl::powerReq: Error getting encoded size for RIL_SIM_SAP_POWER_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_POWER, token, 1, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::powerReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_POWER, token, 1, msg); - return Void(); - } - - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::powerReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_POWER_REQ_fields, &req)) { - RLOGE("SapImpl::powerReq: Error encoding RIL_SIM_SAP_POWER_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_POWER, token, 2, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_POWER_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -Return<void> SapImpl::resetSimReq(int32_t token) { - RLOGD("SapImpl::resetSimReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_RESET_SIM, token); - if (msg == NULL) { - RLOGE("SapImpl::resetSimReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_RESET_SIM, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_RESET_SIM_REQ *****/ - RIL_SIM_SAP_RESET_SIM_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_RESET_SIM_REQ)); - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_RESET_SIM_REQ_fields, &req)) { - RLOGE("SapImpl::resetSimReq: Error getting encoded size for RIL_SIM_SAP_RESET_SIM_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_RESET_SIM, token, 1, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::resetSimReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_RESET_SIM, token, 1, msg); - return Void(); - } - - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::resetSimReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_RESET_SIM_REQ_fields, &req)) { - RLOGE("SapImpl::resetSimReq: Error encoding RIL_SIM_SAP_RESET_SIM_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_RESET_SIM, token, 2, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_RESET_SIM_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -Return<void> SapImpl::transferCardReaderStatusReq(int32_t token) { - RLOGD("SapImpl::transferCardReaderStatusReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS, token); - if (msg == NULL) { - RLOGE("SapImpl::transferCardReaderStatusReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ *****/ - RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ)); - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ_fields, - &req)) { - RLOGE("SapImpl::transferCardReaderStatusReq: Error getting encoded size for " - "RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS, token, 1, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::transferCardReaderStatusReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS, token, 1, msg); - return Void(); - } - - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::transferCardReaderStatusReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ_fields, &req)) { - RLOGE("SapImpl::transferCardReaderStatusReq: Error encoding " - "RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS, token, 2, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -Return<void> SapImpl::setTransferProtocolReq(int32_t token, SapTransferProtocol transferProtocol) { - RLOGD("SapImpl::setTransferProtocolReq"); - MsgHeader *msg = createMsgHeader(MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL, token); - if (msg == NULL) { - RLOGE("SapImpl::setTransferProtocolReq: Error allocating memory for msg"); - sendFailedResponse(MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL, token, 0); - return Void(); - } - - /***** Encode RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ *****/ - RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ req; - memset(&req, 0, sizeof(RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ)); - req.protocol = (RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ_Protocol)transferProtocol; - - size_t encodedSize = 0; - if (!pb_get_encoded_size(&encodedSize, RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ_fields, &req)) { - RLOGE("SapImpl::setTransferProtocolReq: Error getting encoded size for " - "RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL, token, 1, msg); - return Void(); - } - - uint8_t *buffer = (uint8_t *)calloc(1, encodedSize); - if (buffer == NULL) { - RLOGE("SapImpl::setTransferProtocolReq: Error allocating memory for buffer"); - sendFailedResponse(MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL, token, 1, msg); - return Void(); - } - - pb_ostream_t stream = pb_ostream_from_buffer(buffer, encodedSize); - - RLOGD("SapImpl::setTransferProtocolReq calling pb_encode"); - if (!pb_encode(&stream, RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ_fields, &req)) { - RLOGE("SapImpl::setTransferProtocolReq: Error encoding " - "RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ"); - sendFailedResponse(MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL, token, 2, buffer, msg); - return Void(); - } - /***** Encode RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ done *****/ - - /* encoded req is payload */ - return addPayloadAndDispatchRequest(msg, stream.bytes_written, buffer); -} - -void *sapDecodeMessage(MsgId msgId, MsgType msgType, uint8_t *payloadPtr, size_t payloadLen) { - void *responsePtr = NULL; - pb_istream_t stream; - - /* Create the stream */ - stream = pb_istream_from_buffer((uint8_t *)payloadPtr, payloadLen); - - /* Decode based on the message id */ - switch (msgId) - { - case MsgId_RIL_SIM_SAP_CONNECT: - responsePtr = malloc(sizeof(RIL_SIM_SAP_CONNECT_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_CONNECT_RSP_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_CONNECT_RSP"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_DISCONNECT: - if (msgType == MsgType_RESPONSE) { - responsePtr = malloc(sizeof(RIL_SIM_SAP_DISCONNECT_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_DISCONNECT_RSP_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_DISCONNECT_RSP"); - return NULL; - } - } - } else { - responsePtr = malloc(sizeof(RIL_SIM_SAP_DISCONNECT_IND)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_DISCONNECT_IND_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_DISCONNECT_IND"); - return NULL; - } - } - } - break; - - case MsgId_RIL_SIM_SAP_APDU: - responsePtr = malloc(sizeof(RIL_SIM_SAP_APDU_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_APDU_RSP_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_APDU_RSP"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_TRANSFER_ATR: - responsePtr = malloc(sizeof(RIL_SIM_SAP_TRANSFER_ATR_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_TRANSFER_ATR_RSP_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_TRANSFER_ATR_RSP"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_POWER: - responsePtr = malloc(sizeof(RIL_SIM_SAP_POWER_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_POWER_RSP_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_POWER_RSP"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_RESET_SIM: - responsePtr = malloc(sizeof(RIL_SIM_SAP_RESET_SIM_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_RESET_SIM_RSP_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_RESET_SIM_RSP"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_STATUS: - responsePtr = malloc(sizeof(RIL_SIM_SAP_STATUS_IND)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_STATUS_IND_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_STATUS_IND"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS: - responsePtr = malloc(sizeof(RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP_fields, - responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_ERROR_RESP: - responsePtr = malloc(sizeof(RIL_SIM_SAP_ERROR_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_ERROR_RSP_fields, responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_ERROR_RSP"); - return NULL; - } - } - break; - - case MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL: - responsePtr = malloc(sizeof(RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_RSP)); - if (responsePtr) { - if (!pb_decode(&stream, RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_RSP_fields, - responsePtr)) { - RLOGE("Error decoding RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_RSP"); - return NULL; - } - } - break; - - default: - break; - } - return responsePtr; -} /* sapDecodeMessage */ - -sp<SapImpl> getSapImpl(RilSapSocket *sapSocket) { - switch (sapSocket->getSocketId()) { - case RIL_SOCKET_1: - RLOGD("getSapImpl: returning sapService[0]"); - return sapService[0]; - #if (SIM_COUNT >= 2) - case RIL_SOCKET_2: - return sapService[1]; - #if (SIM_COUNT >= 3) - case RIL_SOCKET_3: - return sapService[2]; - #if (SIM_COUNT >= 4) - case RIL_SOCKET_4: - return sapService[3]; - #endif - #endif - #endif - default: - return NULL; - } -} - -SapResultCode convertApduResponseProtoToHal(RIL_SIM_SAP_APDU_RSP_Response responseProto) { - switch(responseProto) { - case RIL_SIM_SAP_APDU_RSP_Response_RIL_E_SUCCESS: - return SapResultCode::SUCCESS; - case RIL_SIM_SAP_APDU_RSP_Response_RIL_E_GENERIC_FAILURE: - return SapResultCode::GENERIC_FAILURE; - case RIL_SIM_SAP_APDU_RSP_Response_RIL_E_SIM_NOT_READY: - return SapResultCode::CARD_NOT_ACCESSSIBLE; - case RIL_SIM_SAP_APDU_RSP_Response_RIL_E_SIM_ALREADY_POWERED_OFF: - return SapResultCode::CARD_ALREADY_POWERED_OFF; - case RIL_SIM_SAP_APDU_RSP_Response_RIL_E_SIM_ABSENT: - return SapResultCode::CARD_REMOVED; - default: - return SapResultCode::GENERIC_FAILURE; - } -} - -SapResultCode convertTransferAtrResponseProtoToHal( - RIL_SIM_SAP_TRANSFER_ATR_RSP_Response responseProto) { - switch(responseProto) { - case RIL_SIM_SAP_TRANSFER_ATR_RSP_Response_RIL_E_SUCCESS: - return SapResultCode::SUCCESS; - case RIL_SIM_SAP_TRANSFER_ATR_RSP_Response_RIL_E_GENERIC_FAILURE: - return SapResultCode::GENERIC_FAILURE; - case RIL_SIM_SAP_TRANSFER_ATR_RSP_Response_RIL_E_SIM_ALREADY_POWERED_OFF: - return SapResultCode::CARD_ALREADY_POWERED_OFF; - case RIL_SIM_SAP_TRANSFER_ATR_RSP_Response_RIL_E_SIM_ABSENT: - return SapResultCode::CARD_REMOVED; - case RIL_SIM_SAP_TRANSFER_ATR_RSP_Response_RIL_E_SIM_DATA_NOT_AVAILABLE: - return SapResultCode::DATA_NOT_AVAILABLE; - default: - return SapResultCode::GENERIC_FAILURE; - } -} - -SapResultCode convertPowerResponseProtoToHal(RIL_SIM_SAP_POWER_RSP_Response responseProto) { - switch(responseProto) { - case RIL_SIM_SAP_POWER_RSP_Response_RIL_E_SUCCESS: - return SapResultCode::SUCCESS; - case RIL_SIM_SAP_POWER_RSP_Response_RIL_E_GENERIC_FAILURE: - return SapResultCode::GENERIC_FAILURE; - case RIL_SIM_SAP_POWER_RSP_Response_RIL_E_SIM_ABSENT: - return SapResultCode::CARD_REMOVED; - case RIL_SIM_SAP_POWER_RSP_Response_RIL_E_SIM_ALREADY_POWERED_OFF: - return SapResultCode::CARD_ALREADY_POWERED_OFF; - case RIL_SIM_SAP_POWER_RSP_Response_RIL_E_SIM_ALREADY_POWERED_ON: - return SapResultCode::CARD_ALREADY_POWERED_ON; - default: - return SapResultCode::GENERIC_FAILURE; - } -} - -SapResultCode convertResetSimResponseProtoToHal(RIL_SIM_SAP_RESET_SIM_RSP_Response responseProto) { - switch(responseProto) { - case RIL_SIM_SAP_RESET_SIM_RSP_Response_RIL_E_SUCCESS: - return SapResultCode::SUCCESS; - case RIL_SIM_SAP_RESET_SIM_RSP_Response_RIL_E_GENERIC_FAILURE: - return SapResultCode::GENERIC_FAILURE; - case RIL_SIM_SAP_RESET_SIM_RSP_Response_RIL_E_SIM_ABSENT: - return SapResultCode::CARD_REMOVED; - case RIL_SIM_SAP_RESET_SIM_RSP_Response_RIL_E_SIM_NOT_READY: - return SapResultCode::CARD_NOT_ACCESSSIBLE; - case RIL_SIM_SAP_RESET_SIM_RSP_Response_RIL_E_SIM_ALREADY_POWERED_OFF: - return SapResultCode::CARD_ALREADY_POWERED_OFF; - } - return SapResultCode::GENERIC_FAILURE; -} - -SapResultCode convertTransferCardReaderStatusResponseProtoToHal( - RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP_Response responseProto) { - switch(responseProto) { - case RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP_Response_RIL_E_SUCCESS: - return SapResultCode::SUCCESS; - case RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP_Response_RIL_E_GENERIC_FAILURE: - return SapResultCode::GENERIC_FAILURE; - case RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP_Response_RIL_E_SIM_DATA_NOT_AVAILABLE: - return SapResultCode::DATA_NOT_AVAILABLE; - } - return SapResultCode::GENERIC_FAILURE; -} - -void processResponse(MsgHeader *rsp, RilSapSocket *sapSocket, MsgType msgType) { - MsgId msgId = rsp->id; - uint8_t *data = rsp->payload->bytes; - size_t dataLen = rsp->payload->size; - - void *messagePtr = sapDecodeMessage(msgId, msgType, data, dataLen); - - sp<SapImpl> sapImpl = getSapImpl(sapSocket); - if (sapImpl->sapCallback == NULL) { - RLOGE("processResponse: sapCallback == NULL; msgId = %d; msgType = %d", - msgId, msgType); - return; - } - - if (messagePtr == NULL) { - RLOGE("processResponse: *messagePtr == NULL; msgId = %d; msgType = %d", - msgId, msgType); - sapImpl->sendFailedResponse(msgId, rsp->token, 0); - return; - } - - RLOGD("processResponse: sapCallback != NULL; msgId = %d; msgType = %d", - msgId, msgType); - - Return<void> retStatus; - switch (msgId) { - case MsgId_RIL_SIM_SAP_CONNECT: { - RIL_SIM_SAP_CONNECT_RSP *connectRsp = (RIL_SIM_SAP_CONNECT_RSP *)messagePtr; - RLOGD("processResponse: calling sapCallback->connectResponse %d %d %d", - rsp->token, - connectRsp->response, - connectRsp->max_message_size); - retStatus = sapImpl->sapCallback->connectResponse(rsp->token, - (SapConnectRsp)connectRsp->response, - connectRsp->max_message_size); - break; - } - - case MsgId_RIL_SIM_SAP_DISCONNECT: - if (msgType == MsgType_RESPONSE) { - RLOGD("processResponse: calling sapCallback->disconnectResponse %d", rsp->token); - retStatus = sapImpl->sapCallback->disconnectResponse(rsp->token); - } else { - RIL_SIM_SAP_DISCONNECT_IND *disconnectInd = - (RIL_SIM_SAP_DISCONNECT_IND *)messagePtr; - RLOGD("processResponse: calling sapCallback->disconnectIndication %d %d", - rsp->token, disconnectInd->disconnectType); - retStatus = sapImpl->sapCallback->disconnectIndication(rsp->token, - (SapDisconnectType)disconnectInd->disconnectType); - } - break; - - case MsgId_RIL_SIM_SAP_APDU: { - RIL_SIM_SAP_APDU_RSP *apduRsp = (RIL_SIM_SAP_APDU_RSP *)messagePtr; - SapResultCode apduResponse = convertApduResponseProtoToHal(apduRsp->response); - RLOGD("processResponse: calling sapCallback->apduResponse %d %d", - rsp->token, apduResponse); - hidl_vec<uint8_t> apduRspVec; - if (apduRsp->apduResponse != NULL && apduRsp->apduResponse->size > 0) { - apduRspVec.setToExternal(apduRsp->apduResponse->bytes, apduRsp->apduResponse->size); - } - retStatus = sapImpl->sapCallback->apduResponse(rsp->token, apduResponse, apduRspVec); - break; - } - - case MsgId_RIL_SIM_SAP_TRANSFER_ATR: { - RIL_SIM_SAP_TRANSFER_ATR_RSP *transferAtrRsp = - (RIL_SIM_SAP_TRANSFER_ATR_RSP *)messagePtr; - SapResultCode transferAtrResponse = - convertTransferAtrResponseProtoToHal(transferAtrRsp->response); - RLOGD("processResponse: calling sapCallback->transferAtrResponse %d %d", - rsp->token, transferAtrResponse); - hidl_vec<uint8_t> transferAtrRspVec; - if (transferAtrRsp->atr != NULL && transferAtrRsp->atr->size > 0) { - transferAtrRspVec.setToExternal(transferAtrRsp->atr->bytes, - transferAtrRsp->atr->size); - } - retStatus = sapImpl->sapCallback->transferAtrResponse(rsp->token, transferAtrResponse, - transferAtrRspVec); - break; - } - - case MsgId_RIL_SIM_SAP_POWER: { - SapResultCode powerResponse = convertPowerResponseProtoToHal( - ((RIL_SIM_SAP_POWER_RSP *)messagePtr)->response); - RLOGD("processResponse: calling sapCallback->powerResponse %d %d", - rsp->token, powerResponse); - retStatus = sapImpl->sapCallback->powerResponse(rsp->token, powerResponse); - break; - } - - case MsgId_RIL_SIM_SAP_RESET_SIM: { - SapResultCode resetSimResponse = convertResetSimResponseProtoToHal( - ((RIL_SIM_SAP_RESET_SIM_RSP *)messagePtr)->response); - RLOGD("processResponse: calling sapCallback->resetSimResponse %d %d", - rsp->token, resetSimResponse); - retStatus = sapImpl->sapCallback->resetSimResponse(rsp->token, resetSimResponse); - break; - } - - case MsgId_RIL_SIM_SAP_STATUS: { - RIL_SIM_SAP_STATUS_IND *statusInd = (RIL_SIM_SAP_STATUS_IND *)messagePtr; - RLOGD("processResponse: calling sapCallback->statusIndication %d %d", - rsp->token, statusInd->statusChange); - retStatus = sapImpl->sapCallback->statusIndication(rsp->token, - (SapStatus)statusInd->statusChange); - break; - } - - case MsgId_RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS: { - RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP *transferStatusRsp = - (RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP *)messagePtr; - SapResultCode transferCardReaderStatusResponse = - convertTransferCardReaderStatusResponseProtoToHal( - transferStatusRsp->response); - RLOGD("processResponse: calling sapCallback->transferCardReaderStatusResponse %d %d %d", - rsp->token, - transferCardReaderStatusResponse, - transferStatusRsp->CardReaderStatus); - retStatus = sapImpl->sapCallback->transferCardReaderStatusResponse(rsp->token, - transferCardReaderStatusResponse, - transferStatusRsp->CardReaderStatus); - break; - } - - case MsgId_RIL_SIM_SAP_ERROR_RESP: { - RLOGD("processResponse: calling sapCallback->errorResponse %d", rsp->token); - retStatus = sapImpl->sapCallback->errorResponse(rsp->token); - break; - } - - case MsgId_RIL_SIM_SAP_SET_TRANSFER_PROTOCOL: { - SapResultCode setTransferProtocolResponse; - if (((RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_RSP *)messagePtr)->response == - RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_RSP_Response_RIL_E_SUCCESS) { - setTransferProtocolResponse = SapResultCode::SUCCESS; - } else { - setTransferProtocolResponse = SapResultCode::NOT_SUPPORTED; - } - RLOGD("processResponse: calling sapCallback->transferProtocolResponse %d %d", - rsp->token, setTransferProtocolResponse); - retStatus = sapImpl->sapCallback->transferProtocolResponse(rsp->token, - setTransferProtocolResponse); - break; - } - - default: - return; - } - sapImpl->checkReturnStatus(retStatus); -} - -void sap::processResponse(MsgHeader *rsp, RilSapSocket *sapSocket) { - processResponse(rsp, sapSocket, MsgType_RESPONSE); -} - -void sap::processUnsolResponse(MsgHeader *rsp, RilSapSocket *sapSocket) { - processResponse(rsp, sapSocket, MsgType_UNSOL_RESPONSE); -} - -void sap::registerService(const RIL_RadioFunctions *callbacks) { - using namespace android::hardware; - int simCount = 1; - const char *serviceNames[] = { - android::RIL_getServiceName() - #if (SIM_COUNT >= 2) - , RIL2_SERVICE_NAME - #if (SIM_COUNT >= 3) - , RIL3_SERVICE_NAME - #if (SIM_COUNT >= 4) - , RIL4_SERVICE_NAME - #endif - #endif - #endif - }; - - RIL_SOCKET_ID socketIds[] = { - RIL_SOCKET_1 - #if (SIM_COUNT >= 2) - , RIL_SOCKET_2 - #if (SIM_COUNT >= 3) - , RIL_SOCKET_3 - #if (SIM_COUNT >= 4) - , RIL_SOCKET_4 - #endif - #endif - #endif - }; - #if (SIM_COUNT >= 2) - simCount = SIM_COUNT; - #endif - - for (int i = 0; i < simCount; i++) { - sapService[i] = new SapImpl; - sapService[i]->slotId = i; - sapService[i]->rilSocketId = socketIds[i]; - RLOGD("registerService: starting ISap %s for slotId %d", serviceNames[i], i); - android::status_t status = sapService[i]->registerAsService(serviceNames[i]); - RLOGD("registerService: started ISap %s status %d", serviceNames[i], status); - } -} diff --git a/radio/librilutils/Android.bp b/radio/librilutils/Android.bp new file mode 100644 index 00000000..ff76027f --- /dev/null +++ b/radio/librilutils/Android.bp @@ -0,0 +1,46 @@ +// Copyright 2013 The Android Open Source Project + +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + +cc_library { + name: "librilutils-goldfish-fork", + + srcs: [ + "librilutils.c", + "record_stream.c", + "proto/sap-api.proto", + ], + + header_libs: ["goldfish_ril_headers"], + export_header_lib_headers: ["goldfish_ril_headers"], + + cflags: [ + "-Wall", + "-Wextra", + "-Werror", + "-DPB_FIELD_32BIT" + ], + + proto: { + type: "nanopb-c-enable_malloc-32bit", + export_proto_headers: true, + }, + + vendor: true, +} + +// Create java protobuf code +java_library { + name: "goldfish-fork-sap-api-java-static", + srcs: ["proto/sap-api.proto"], + proto: { + type: "micro", + }, +} diff --git a/radio/librilutils/librilutils.c b/radio/librilutils/librilutils.c new file mode 100644 index 00000000..b1b930ea --- /dev/null +++ b/radio/librilutils/librilutils.c @@ -0,0 +1,24 @@ +/* + * Copyright (C) 2013 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. + */ + +#include <telephony/librilutils.h> +#include <time.h> + +uint64_t ril_nano_time() { + struct timespec now; + clock_gettime(CLOCK_MONOTONIC, &now); + return now.tv_sec * 1000000000LL + now.tv_nsec; +} diff --git a/radio/librilutils/proto/sap-api.options b/radio/librilutils/proto/sap-api.options new file mode 100644 index 00000000..f76ba931 --- /dev/null +++ b/radio/librilutils/proto/sap-api.options @@ -0,0 +1,23 @@ +# +# Copyright (C) 2014 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. +# + +MsgHeader.payload type:FT_POINTER +RIL_SIM_SAP_APDU_REQ.command type:FT_POINTER +RIL_SIM_SAP_APDU_RSP.apduResponse type:FT_POINTER +RIL_SIM_SAP_TRANSFER_ATR_RSP.atr type:FT_POINTER + +#RIL_SIM_SAP_REQUEST.apdu type:FT_POINTER +#RIL_SIM_SAP_RESPONSE.apdu type:FT_POINTER diff --git a/radio/librilutils/proto/sap-api.proto b/radio/librilutils/proto/sap-api.proto new file mode 100644 index 00000000..5d125e47 --- /dev/null +++ b/radio/librilutils/proto/sap-api.proto @@ -0,0 +1,306 @@ +syntax = "proto2"; + +option java_package = "org.android.btsap"; +option java_outer_classname = "SapApi"; + +// +// SAP Interface to RIL +// +// The protocol for the binary wire format to RIL shall consist of +// the serialized format of MsgHeader. +// MsgHeader payload field will contain the serialized format of +// the actual message being sent, as described by the type and id +// fields. +// e.g. If type = REQUEST and id == RIL_SIM_SAP_CONNECT, payload +// will contain the serialized wire format of a +// RIL_SIM_SAP_CONNECT_REQ message. +// + +// Message Header +// Each SAP message stream will always be prepended with a MsgHeader +message MsgHeader { + required fixed32 token = 1; // generated dynamically + required MsgType type = 2; + required MsgId id = 3; + required Error error = 4; + required bytes payload = 5; +} + +enum MsgType { + UNKNOWN = 0; + REQUEST = 1; + RESPONSE = 2; + UNSOL_RESPONSE = 3; + } + +enum MsgId { + UNKNOWN_REQ = 0; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_CONNECT, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_CONNECT_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_CONNECT, Error:Valid errors, + // Message: message RIL_SIM_SAP_CONNECT_RSP + // + RIL_SIM_SAP_CONNECT = 1; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_DISCONNECT, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_DISCONNECT_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_DISCONNECT, Error:Valid errors, + // Message: message RIL_SIM_SAP_DISCONNECT_RSP + // For MsgType: UNSOL_RESPONSE, MsgId: RIL_SIM_SAP_DISCONNECT, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_DISCONNECT_IND + // + RIL_SIM_SAP_DISCONNECT = 2; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_APDU, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_APDU_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_APDU, Error:Valid errors, + // Message: message RIL_SIM_SAP_APDU_RSP + // + RIL_SIM_SAP_APDU = 3; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_TRANSFER_ATR, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_TRANSFER_ATR_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_TRANSFER_ATR, Error:Valid errors, + // Message: message RIL_SIM_SAP_TRANSFER_ATR_RSP + // + RIL_SIM_SAP_TRANSFER_ATR = 4; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_POWER, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_POWER_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_POWER, Error:Valid errors, + // Message: message RIL_SIM_SAP_POWER_RSP + // + RIL_SIM_SAP_POWER = 5; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_RESET_SIM, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_RESET_SIM_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_RESET_SIM, Error:Valid errors, + // Message: message RIL_SIM_SAP_RESET_SIM_RSP + // + RIL_SIM_SAP_RESET_SIM = 6; + + // + // For MsgType: UNSOL_RESPONSE, MsgId: RIL_SIM_SAP_STATUS, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_STATUS_IND + // + RIL_SIM_SAP_STATUS = 7; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS, Error:Valid errors, + // Message: message RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP + // + RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS = 8; + + // + // For MsgType: UNSOL_RESPONSE, MsgId: RIL_SIM_SAP_ERROR_RESP, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_ERROR_RSP + // + RIL_SIM_SAP_ERROR_RESP = 9; + + // + // For MsgType: REQUEST ,MsgId: RIL_SIM_SAP_SET_TRANSFER_PROTOCOL, Error: RIL_E_UNUSED, + // Message: message RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ + // For MsgType: RESPONSE, MsgId: RIL_SIM_SAP_SET_TRANSFER_PROTOCOL, Error:Valid errors, + // Message: message RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_RSP + // + RIL_SIM_SAP_SET_TRANSFER_PROTOCOL = 10; + } + + enum Error { + RIL_E_SUCCESS = 0; + RIL_E_RADIO_NOT_AVAILABLE = 1; + RIL_E_GENERIC_FAILURE = 2; + RIL_E_REQUEST_NOT_SUPPORTED = 3; + RIL_E_CANCELLED = 4; + RIL_E_INVALID_PARAMETER = 5; + RIL_E_UNUSED = 6; + } + +// SAP 1.1 spec 5.1.1 +message RIL_SIM_SAP_CONNECT_REQ { + required int32 max_message_size = 1; +} + +// SAP 1.1 spec 5.1.2 +message RIL_SIM_SAP_CONNECT_RSP { + enum Response { + RIL_E_SUCCESS = 0; + RIL_E_SAP_CONNECT_FAILURE = 1; + RIL_E_SAP_MSG_SIZE_TOO_LARGE = 2; + RIL_E_SAP_MSG_SIZE_TOO_SMALL = 3; + RIL_E_SAP_CONNECT_OK_CALL_ONGOING = 4; + } + required Response response = 1; +// must be present for RIL_E_SAP_MSG_SIZE_TOO_LARGE and contain the +// the suitable message size + optional int32 max_message_size = 2; +} + +// SAP 1.1 spec 5.1.3 +message RIL_SIM_SAP_DISCONNECT_REQ { + //no params +} + + +// SAP 1.1 spec 5.1.4 +message RIL_SIM_SAP_DISCONNECT_RSP { + //no params +} + + +// SAP 1.1 spec 5.1.5 +message RIL_SIM_SAP_DISCONNECT_IND { + enum DisconnectType { + RIL_S_DISCONNECT_TYPE_GRACEFUL = 0; + RIL_S_DISCONNECT_TYPE_IMMEDIATE = 1; + } + required DisconnectType disconnectType = 1; +} + +// SAP 1.1 spec 5.1.6 +message RIL_SIM_SAP_APDU_REQ { //handles both APDU and APDU7816 + enum Type { + RIL_TYPE_APDU = 0; + RIL_TYPE_APDU7816 = 1; + } + required Type type = 1; + required bytes command = 2; +} + +// SAP 1.1 spec 5.1.7 +message RIL_SIM_SAP_APDU_RSP { //handles both APDU and APDU7816 + enum Type { + RIL_TYPE_APDU = 0; + RIL_TYPE_APDU7816 = 1; + } + required Type type = 1; + enum Response { + RIL_E_SUCCESS = 0; + RIL_E_GENERIC_FAILURE = 1; + RIL_E_SIM_NOT_READY = 2; + RIL_E_SIM_ALREADY_POWERED_OFF = 3; + RIL_E_SIM_ABSENT = 4; + } + required Response response = 2; + optional bytes apduResponse = 3; +} + +// SAP 1.1 spec 5.1.8 +message RIL_SIM_SAP_TRANSFER_ATR_REQ { + // no params +} + +// SAP 1.1 spec 5.1.9 +message RIL_SIM_SAP_TRANSFER_ATR_RSP { + enum Response { + RIL_E_SUCCESS = 0; + RIL_E_GENERIC_FAILURE = 1; + RIL_E_SIM_ALREADY_POWERED_OFF = 3; + RIL_E_SIM_ALREADY_POWERED_ON = 18; + RIL_E_SIM_ABSENT = 4; + RIL_E_SIM_DATA_NOT_AVAILABLE = 6; + } + required Response response = 1; + + optional bytes atr = 2; //must be present on SUCCESS +} + + +// SAP 1.1 spec 5.1.10 +5.1.12 +message RIL_SIM_SAP_POWER_REQ { + required bool state = 1; //true = on, False = off +} + +// SAP 1.1 spec 5.1.11 +5.1.13 +message RIL_SIM_SAP_POWER_RSP { + enum Response { + RIL_E_SUCCESS = 0; + RIL_E_GENERIC_FAILURE = 2; + RIL_E_SIM_ABSENT = 11; + RIL_E_SIM_ALREADY_POWERED_OFF = 17; + RIL_E_SIM_ALREADY_POWERED_ON = 18; + } + required Response response = 1; +} + +// SAP 1.1 spec 5.1.14 +message RIL_SIM_SAP_RESET_SIM_REQ { + // no params +} + +// SAP 1.1 spec 5.1.15 +message RIL_SIM_SAP_RESET_SIM_RSP { + enum Response { + RIL_E_SUCCESS = 0; + RIL_E_GENERIC_FAILURE = 2; + RIL_E_SIM_ABSENT = 11; + RIL_E_SIM_NOT_READY = 16; + RIL_E_SIM_ALREADY_POWERED_OFF = 17; + } + required Response response = 1; +} + +// SAP 1.1 spec 5.1.16 +message RIL_SIM_SAP_STATUS_IND { + enum Status { + RIL_SIM_STATUS_UNKNOWN_ERROR = 0; + RIL_SIM_STATUS_CARD_RESET = 1; + RIL_SIM_STATUS_CARD_NOT_ACCESSIBLE = 2; + RIL_SIM_STATUS_CARD_REMOVED = 3; + RIL_SIM_STATUS_CARD_INSERTED = 4; + RIL_SIM_STATUS_RECOVERED = 5; + } + required Status statusChange = 1; +} + +// SAP 1.1 spec 5.1.17 +message RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_REQ { + //no params + +} + +// SAP 1.1 spec 5.1.18 +message RIL_SIM_SAP_TRANSFER_CARD_READER_STATUS_RSP { + enum Response { + RIL_E_SUCCESS = 0; + RIL_E_GENERIC_FAILURE = 2; + RIL_E_SIM_DATA_NOT_AVAILABLE = 6; + } + required Response response = 1; + optional int32 CardReaderStatus = 2; +} + +// SAP 1.1 spec 5.1.19 +message RIL_SIM_SAP_ERROR_RSP { + //no params +} + +// SAP 1.1 spec 5.1.20 +message RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_REQ { + enum Protocol { + t0 = 0; + t1 = 1; + } + required Protocol protocol = 1; +} + +// SAP 1.1 spec 5.1.21 +message RIL_SIM_SAP_SET_TRANSFER_PROTOCOL_RSP { + enum Response { + RIL_E_SUCCESS = 0; + RIL_E_GENERIC_FAILURE = 2; + RIL_E_SIM_ABSENT = 11; + RIL_E_SIM_NOT_READY = 16; + RIL_E_SIM_ALREADY_POWERED_OFF = 17; + } + required Response response = 1; +} diff --git a/radio/librilutils/record_stream.c b/radio/librilutils/record_stream.c new file mode 100644 index 00000000..566f6661 --- /dev/null +++ b/radio/librilutils/record_stream.c @@ -0,0 +1,186 @@ +/* +** +** Copyright 2006, 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. +*/ + +#include <stdlib.h> +#include <unistd.h> +#include <assert.h> +#include <errno.h> +#include <telephony/record_stream.h> +#include <string.h> +#include <stdint.h> +#if defined(_WIN32) +#include <winsock2.h> /* for ntohl */ +#else +#include <netinet/in.h> +#endif + +#define HEADER_SIZE 4 + +struct RecordStream { + int fd; + size_t maxRecordLen; + + unsigned char *buffer; + + unsigned char *unconsumed; + unsigned char *read_end; + unsigned char *buffer_end; +}; + + +extern RecordStream *record_stream_new(int fd, size_t maxRecordLen) +{ + RecordStream *ret; + + assert (maxRecordLen <= 0xffff); + + ret = (RecordStream *)calloc(1, sizeof(RecordStream)); + + ret->fd = fd; + ret->maxRecordLen = maxRecordLen; + ret->buffer = (unsigned char *)malloc (maxRecordLen + HEADER_SIZE); + + ret->unconsumed = ret->buffer; + ret->read_end = ret->buffer; + ret->buffer_end = ret->buffer + maxRecordLen + HEADER_SIZE; + + return ret; +} + + +extern void record_stream_free(RecordStream *rs) +{ + free(rs->buffer); + free(rs); +} + + +/* returns NULL; if there isn't a full record in the buffer */ +static unsigned char * getEndOfRecord (unsigned char *p_begin, + unsigned char *p_end) +{ + size_t len; + unsigned char * p_ret; + + if (p_end < p_begin + HEADER_SIZE) { + return NULL; + } + + //First four bytes are length + len = ntohl(*((uint32_t *)p_begin)); + + p_ret = p_begin + HEADER_SIZE + len; + + if (p_end < p_ret) { + return NULL; + } + + return p_ret; +} + +static void *getNextRecord (RecordStream *p_rs, size_t *p_outRecordLen) +{ + unsigned char *record_start, *record_end; + + record_end = getEndOfRecord (p_rs->unconsumed, p_rs->read_end); + + if (record_end != NULL) { + /* one full line in the buffer */ + record_start = p_rs->unconsumed + HEADER_SIZE; + p_rs->unconsumed = record_end; + + *p_outRecordLen = record_end - record_start; + + return record_start; + } + + return NULL; +} + +/** + * Reads the next record from stream fd + * Records are prefixed by a 16-bit big endian length value + * Records may not be larger than maxRecordLen + * + * Doesn't guard against EINTR + * + * p_outRecord and p_outRecordLen may not be NULL + * + * Return 0 on success, -1 on fail + * Returns 0 with *p_outRecord set to NULL on end of stream + * Returns -1 / errno = EAGAIN if it needs to read again + */ +int record_stream_get_next (RecordStream *p_rs, void ** p_outRecord, + size_t *p_outRecordLen) +{ + void *ret; + + ssize_t countRead; + + /* is there one record already in the buffer? */ + ret = getNextRecord (p_rs, p_outRecordLen); + + if (ret != NULL) { + *p_outRecord = ret; + return 0; + } + + // if the buffer is full and we don't have a full record + if (p_rs->unconsumed == p_rs->buffer + && p_rs->read_end == p_rs->buffer_end + ) { + // this should never happen + //ALOGE("max record length exceeded\n"); + assert (0); + errno = EFBIG; + return -1; + } + + if (p_rs->unconsumed != p_rs->buffer) { + // move remainder to the beginning of the buffer + size_t toMove; + + toMove = p_rs->read_end - p_rs->unconsumed; + if (toMove) { + memmove(p_rs->buffer, p_rs->unconsumed, toMove); + } + + p_rs->read_end = p_rs->buffer + toMove; + p_rs->unconsumed = p_rs->buffer; + } + + countRead = read (p_rs->fd, p_rs->read_end, p_rs->buffer_end - p_rs->read_end); + + if (countRead <= 0) { + /* note: end-of-stream drops through here too */ + *p_outRecord = NULL; + return countRead; + } + + p_rs->read_end += countRead; + + ret = getNextRecord (p_rs, p_outRecordLen); + + if (ret == NULL) { + /* not enough of a buffer to for a whole command */ + errno = EAGAIN; + return -1; + } + + *p_outRecord = ret; + return 0; +} diff --git a/radio/ril/Android.mk b/radio/ril/Android.mk deleted file mode 100644 index 4d1b14e1..00000000 --- a/radio/ril/Android.mk +++ /dev/null @@ -1,44 +0,0 @@ -# Copyright 2006 The Android Open Source Project - -# XXX using libutils for simulator build only... -# -LOCAL_PATH:= $(call my-dir) -include $(CLEAR_VARS) - -LOCAL_SRC_FILES:= \ - reference-ril.c \ - atchannel.c \ - if_monitor.cpp \ - ipv6_monitor.cpp \ - misc.c \ - at_tok.c - -LOCAL_SHARED_LIBRARIES += \ - liblog libcutils libutils libril-goldfish-fork librilutils - -LOCAL_STATIC_LIBRARIES += libbase libqemud.ranchu - -# for asprinf -LOCAL_CFLAGS := -D_GNU_SOURCE -LOCAL_CFLAGS += -Wall -Wextra -Wno-unused-variable -Wno-unused-function -Werror - -ifeq ($(TARGET_DEVICE),sooner) - LOCAL_CFLAGS += -DUSE_TI_COMMANDS -endif - -ifeq ($(TARGET_DEVICE),surf) - LOCAL_CFLAGS += -DPOLL_CALL_STATE -DUSE_QMI -endif - -ifeq ($(TARGET_DEVICE),dream) - LOCAL_CFLAGS += -DPOLL_CALL_STATE -DUSE_QMI -endif - -LOCAL_VENDOR_MODULE:= true - -#build shared library -LOCAL_SHARED_LIBRARIES += \ - libcutils libutils -LOCAL_CFLAGS += -DRIL_SHLIB -LOCAL_MODULE:= libgoldfish-ril -include $(BUILD_SHARED_LIBRARY) diff --git a/radio/ril/MODULE_LICENSE_APACHE2 b/radio/ril/MODULE_LICENSE_APACHE2 deleted file mode 100644 index e69de29b..00000000 --- a/radio/ril/MODULE_LICENSE_APACHE2 +++ /dev/null diff --git a/radio/ril/NOTICE b/radio/ril/NOTICE deleted file mode 100644 index c5b1efa7..00000000 --- a/radio/ril/NOTICE +++ /dev/null @@ -1,190 +0,0 @@ - - Copyright (c) 2005-2008, 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. - - 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. - - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - diff --git a/radio/ril/at_tok.c b/radio/ril/at_tok.c deleted file mode 100644 index 204a69e6..00000000 --- a/radio/ril/at_tok.c +++ /dev/null @@ -1,190 +0,0 @@ -/* //device/system/reference-ril/at_tok.c -** -** Copyright 2006, 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. -*/ - -#include "at_tok.h" -#include <string.h> -#include <ctype.h> -#include <stdlib.h> - -/** - * Starts tokenizing an AT response string - * returns -1 if this is not a valid response string, 0 on success. - * updates *p_cur with current position - */ -int at_tok_start(char **p_cur) -{ - if (*p_cur == NULL) { - return -1; - } - - // skip prefix - // consume "^[^:]:" - - *p_cur = strchr(*p_cur, ':'); - - if (*p_cur == NULL) { - return -1; - } - - (*p_cur)++; - - return 0; -} - -static void skipWhiteSpace(char **p_cur) -{ - if (*p_cur == NULL) return; - - while (**p_cur != '\0' && isspace(**p_cur)) { - (*p_cur)++; - } -} - -static void skipNextComma(char **p_cur) -{ - if (*p_cur == NULL) return; - - while (**p_cur != '\0' && **p_cur != ',') { - (*p_cur)++; - } - - if (**p_cur == ',') { - (*p_cur)++; - } -} - -static char * nextTok(char **p_cur) -{ - char *ret = NULL; - - skipWhiteSpace(p_cur); - - if (*p_cur == NULL) { - ret = NULL; - } else if (**p_cur == '"') { - (*p_cur)++; - ret = strsep(p_cur, "\""); - skipNextComma(p_cur); - } else { - ret = strsep(p_cur, ","); - } - - return ret; -} - - -/** - * Parses the next integer in the AT response line and places it in *p_out - * returns 0 on success and -1 on fail - * updates *p_cur - * "base" is the same as the base param in strtol - */ - -static int at_tok_nextint_base(char **p_cur, int *p_out, int base, int uns) -{ - char *ret; - - if (*p_cur == NULL) { - return -1; - } - - ret = nextTok(p_cur); - - if (ret == NULL) { - return -1; - } else { - long l; - char *end; - - if (uns) - l = strtoul(ret, &end, base); - else - l = strtol(ret, &end, base); - - *p_out = (int)l; - - if (end == ret) { - return -1; - } - } - - return 0; -} - -/** - * Parses the next base 10 integer in the AT response line - * and places it in *p_out - * returns 0 on success and -1 on fail - * updates *p_cur - */ -int at_tok_nextint(char **p_cur, int *p_out) -{ - return at_tok_nextint_base(p_cur, p_out, 10, 0); -} - -/** - * Parses the next base 16 integer in the AT response line - * and places it in *p_out - * returns 0 on success and -1 on fail - * updates *p_cur - */ -int at_tok_nexthexint(char **p_cur, int *p_out) -{ - return at_tok_nextint_base(p_cur, p_out, 16, 1); -} - -int at_tok_nextbool(char **p_cur, char *p_out) -{ - int ret; - int result; - - ret = at_tok_nextint(p_cur, &result); - - if (ret < 0) { - return -1; - } - - // booleans should be 0 or 1 - if (!(result == 0 || result == 1)) { - return -1; - } - - if (p_out != NULL) { - *p_out = (char)result; - } - - return ret; -} - -int at_tok_nextstr(char **p_cur, char **p_out) -{ - if (*p_cur == NULL) { - return -1; - } - - *p_out = nextTok(p_cur); - - return 0; -} - -/** returns 1 on "has more tokens" and 0 if no */ -int at_tok_hasmore(char **p_cur) -{ - return ! (*p_cur == NULL || **p_cur == '\0'); -} - - diff --git a/radio/ril/atchannel.c b/radio/ril/atchannel.c deleted file mode 100644 index 407a204e..00000000 --- a/radio/ril/atchannel.c +++ /dev/null @@ -1,976 +0,0 @@ -/* //device/system/reference-ril/atchannel.c -** -** Copyright 2006, 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. -*/ - -#include "atchannel.h" -#include "at_tok.h" - -#include <stdio.h> -#include <string.h> -#include <pthread.h> -#include <ctype.h> -#include <poll.h> -#include <stdlib.h> -#include <errno.h> -#include <fcntl.h> -#include <sys/time.h> -#include <time.h> -#include <unistd.h> - -#define LOG_NDEBUG 0 -#define LOG_TAG "AT" -#include <utils/Log.h> - -#include "misc.h" - - -#define NUM_ELEMS(x) (sizeof(x)/sizeof((x)[0])) - -#define MAX_AT_RESPONSE (8 * 1024) -#define HANDSHAKE_RETRY_COUNT 8 -#define HANDSHAKE_TIMEOUT_MSEC 250 - -static pthread_t s_tid_reader; -static int s_fd = -1; /* fd of the AT channel */ -static ATUnsolHandler s_unsolHandler; - -/* for input buffering */ - -static char s_ATBuffer[MAX_AT_RESPONSE+1]; -static char *s_ATBufferCur = s_ATBuffer; - -#if AT_DEBUG -void AT_DUMP(const char* prefix, const char* buff, int len) -{ - if (len < 0) - len = strlen(buff); - RLOGD("%.*s", len, buff); -} -#endif - -/* - * There is one reader thread |s_tid_reader| and potentially multiple writer - * threads. |s_commandmutex| and |s_commandcond| are used to maintain the - * condition that the writer thread will not read from |sp_response| until the - * reader thread has signaled itself is finished, etc. |s_writeMutex| is used to - * prevent multiple writer threads from calling at_send_command_full_nolock - * function at the same time. - */ - -static pthread_mutex_t s_commandmutex = PTHREAD_MUTEX_INITIALIZER; -static pthread_cond_t s_commandcond = PTHREAD_COND_INITIALIZER; -static pthread_mutex_t s_writeMutex = PTHREAD_MUTEX_INITIALIZER; - -static ATCommandType s_type; -static const char *s_responsePrefix = NULL; -static const char *s_smsPDU = NULL; -static ATResponse *sp_response = NULL; - -static void (*s_onTimeout)(void) = NULL; -static void (*s_onReaderClosed)(void) = NULL; -static int s_readerClosed; - -static void onReaderClosed(); -static int writeCtrlZ (const char *s); -static int writeline (const char *s); - -#define NS_PER_S 1000000000 -static void setTimespecRelative(struct timespec *p_ts, long long msec) -{ - struct timeval tv; - - gettimeofday(&tv, (struct timezone *) NULL); - - p_ts->tv_sec = tv.tv_sec + (msec / 1000); - p_ts->tv_nsec = (tv.tv_usec + (msec % 1000) * 1000L ) * 1000L; - /* assuming tv.tv_usec < 10^6 */ - if (p_ts->tv_nsec >= NS_PER_S) { - p_ts->tv_sec++; - p_ts->tv_nsec -= NS_PER_S; - } -} - -static void sleepMsec(long long msec) -{ - struct timespec ts; - int err; - - ts.tv_sec = (msec / 1000); - ts.tv_nsec = (msec % 1000) * 1000 * 1000; - - do { - err = nanosleep (&ts, &ts); - } while (err < 0 && errno == EINTR); -} - - - -/** add an intermediate response to sp_response*/ -static void addIntermediate(const char *line) -{ - ATLine *p_new; - - p_new = (ATLine *) malloc(sizeof(ATLine)); - - p_new->line = strdup(line); - - /* note: this adds to the head of the list, so the list - will be in reverse order of lines received. the order is flipped - again before passing on to the command issuer */ - p_new->p_next = sp_response->p_intermediates; - sp_response->p_intermediates = p_new; -} - - -/** - * returns 1 if line is a final response indicating error - * See 27.007 annex B - * WARNING: NO CARRIER and others are sometimes unsolicited - */ -static const char * s_finalResponsesError[] = { - "ERROR", - "+CMS ERROR:", - "+CME ERROR:", - "NO CARRIER", /* sometimes! */ - "NO ANSWER", - "NO DIALTONE", -}; -static int isFinalResponseError(const char *line) -{ - size_t i; - - for (i = 0 ; i < NUM_ELEMS(s_finalResponsesError) ; i++) { - if (strStartsWith(line, s_finalResponsesError[i])) { - return 1; - } - } - - return 0; -} - -/** - * returns 1 if line is a final response indicating success - * See 27.007 annex B - * WARNING: NO CARRIER and others are sometimes unsolicited - */ -static const char * s_finalResponsesSuccess[] = { - "OK", - "CONNECT" /* some stacks start up data on another channel */ -}; -static int isFinalResponseSuccess(const char *line) -{ - size_t i; - - for (i = 0 ; i < NUM_ELEMS(s_finalResponsesSuccess) ; i++) { - if (strStartsWith(line, s_finalResponsesSuccess[i])) { - return 1; - } - } - - return 0; -} - -/** - * returns 1 if line is a final response, either error or success - * See 27.007 annex B - * WARNING: NO CARRIER and others are sometimes unsolicited - */ -static int isFinalResponse(const char *line) -{ - return isFinalResponseSuccess(line) || isFinalResponseError(line); -} - - -/** - * returns 1 if line is the first line in (what will be) a two-line - * SMS unsolicited response - */ -static const char * s_smsUnsoliciteds[] = { - "+CMT:", - "+CDS:", - "+CBM:" -}; -static int isSMSUnsolicited(const char *line) -{ - size_t i; - - for (i = 0 ; i < NUM_ELEMS(s_smsUnsoliciteds) ; i++) { - if (strStartsWith(line, s_smsUnsoliciteds[i])) { - return 1; - } - } - - return 0; -} - - -/** assumes s_commandmutex is held */ -static void handleFinalResponse(const char *line) -{ - sp_response->finalResponse = strdup(line); - - pthread_cond_signal(&s_commandcond); -} - -static void handleUnsolicited(const char *line) -{ - if (s_unsolHandler != NULL) { - s_unsolHandler(line, NULL); - } -} - -static void processLine(const char *line) -{ - pthread_mutex_lock(&s_commandmutex); - - if (sp_response == NULL) { - /* no command pending */ - handleUnsolicited(line); - } else if (isFinalResponseSuccess(line)) { - sp_response->success = 1; - handleFinalResponse(line); - } else if (isFinalResponseError(line)) { - sp_response->success = 0; - handleFinalResponse(line); - } else if (s_smsPDU != NULL && 0 == strcmp(line, "> ")) { - // See eg. TS 27.005 4.3 - // Commands like AT+CMGS have a "> " prompt - writeCtrlZ(s_smsPDU); - s_smsPDU = NULL; - } else switch (s_type) { - case NO_RESULT: - handleUnsolicited(line); - break; - case NUMERIC: - if (sp_response->p_intermediates == NULL - && isdigit(line[0]) - ) { - addIntermediate(line); - } else { - /* either we already have an intermediate response or - the line doesn't begin with a digit */ - handleUnsolicited(line); - } - break; - case SINGLELINE: - if (sp_response->p_intermediates == NULL - && strStartsWith (line, s_responsePrefix) - ) { - addIntermediate(line); - } else { - /* we already have an intermediate response */ - handleUnsolicited(line); - } - break; - case MULTILINE: - if (strStartsWith (line, s_responsePrefix)) { - addIntermediate(line); - } else { - handleUnsolicited(line); - } - break; - - default: /* this should never be reached */ - RLOGE("Unsupported AT command type %d\n", s_type); - handleUnsolicited(line); - break; - } - - pthread_mutex_unlock(&s_commandmutex); -} - - -/** - * Returns a pointer to the end of the next line - * special-cases the "> " SMS prompt - * - * returns NULL if there is no complete line - */ -static char * findNextEOL(char *cur) -{ - if (cur[0] == '>' && cur[1] == ' ' && cur[2] == '\0') { - /* SMS prompt character...not \r terminated */ - return cur+2; - } - - // Find next newline - while (*cur != '\0' && *cur != '\r' && *cur != '\n') cur++; - - return *cur == '\0' ? NULL : cur; -} - - -/** - * Reads a line from the AT channel, returns NULL on timeout. - * Assumes it has exclusive read access to the FD - * - * This line is valid only until the next call to readline - * - * This function exists because as of writing, android libc does not - * have buffered stdio. - */ - -static const char *readline() -{ - ssize_t count; - - char *p_read = NULL; - char *p_eol = NULL; - char *ret; - - /* this is a little odd. I use *s_ATBufferCur == 0 to - * mean "buffer consumed completely". If it points to a character, than - * the buffer continues until a \0 - */ - if (*s_ATBufferCur == '\0') { - /* empty buffer */ - s_ATBufferCur = s_ATBuffer; - *s_ATBufferCur = '\0'; - p_read = s_ATBuffer; - } else { /* *s_ATBufferCur != '\0' */ - /* there's data in the buffer from the last read */ - - // skip over leading newlines - while (*s_ATBufferCur == '\r' || *s_ATBufferCur == '\n') - s_ATBufferCur++; - - p_eol = findNextEOL(s_ATBufferCur); - - if (p_eol == NULL) { - /* a partial line. move it up and prepare to read more */ - size_t len; - - len = strlen(s_ATBufferCur); - - memmove(s_ATBuffer, s_ATBufferCur, len + 1); - p_read = s_ATBuffer + len; - s_ATBufferCur = s_ATBuffer; - } - /* Otherwise, (p_eol !- NULL) there is a complete line */ - /* that will be returned the while () loop below */ - } - - while (p_eol == NULL) { - if (0 == MAX_AT_RESPONSE - (p_read - s_ATBuffer)) { - RLOGE("ERROR: Input line exceeded buffer\n"); - /* ditch buffer and start over again */ - s_ATBufferCur = s_ATBuffer; - *s_ATBufferCur = '\0'; - p_read = s_ATBuffer; - } - - do { - count = read(s_fd, p_read, - MAX_AT_RESPONSE - (p_read - s_ATBuffer)); - } while (count < 0 && errno == EINTR); - - if (count > 0) { - AT_DUMP( "<< ", p_read, count ); - - p_read[count] = '\0'; - - // skip over leading newlines - while (*s_ATBufferCur == '\r' || *s_ATBufferCur == '\n') - s_ATBufferCur++; - - p_eol = findNextEOL(s_ATBufferCur); - p_read += count; - } else if (count <= 0) { - /* read error encountered or EOF reached */ - if(count == 0) { - RLOGD("atchannel: EOF reached"); - } else { - RLOGD("atchannel: read error %s", strerror(errno)); - } - return NULL; - } - } - - /* a full line in the buffer. Place a \0 over the \r and return */ - - ret = s_ATBufferCur; - *p_eol = '\0'; - s_ATBufferCur = p_eol + 1; /* this will always be <= p_read, */ - /* and there will be a \0 at *p_read */ - - RLOGD("AT< %s\n", ret); - return ret; -} - - -static void onReaderClosed() -{ - if (s_onReaderClosed != NULL && s_readerClosed == 0) { - - pthread_mutex_lock(&s_commandmutex); - - s_readerClosed = 1; - - pthread_cond_signal(&s_commandcond); - - pthread_mutex_unlock(&s_commandmutex); - - s_onReaderClosed(); - } -} - - -static void *readerLoop(void *arg __unused) -{ - for (;;) { - const char * line; - - line = readline(); - - if (line == NULL) { - break; - } - - if(isSMSUnsolicited(line)) { - char *line1; - const char *line2; - - // The scope of string returned by 'readline()' is valid only - // till next call to 'readline()' hence making a copy of line - // before calling readline again. - line1 = strdup(line); - line2 = readline(); - - if (line2 == NULL) { - free(line1); - break; - } - - if (s_unsolHandler != NULL) { - s_unsolHandler (line1, line2); - } - free(line1); - } else { - processLine(line); - } - } - - onReaderClosed(); - - return NULL; -} - -/** - * Sends string s to the radio with a \r appended. - * Returns AT_ERROR_* on error, 0 on success - * - * This function exists because as of writing, android libc does not - * have buffered stdio. - */ -static int writeline (const char *s) -{ - size_t cur = 0; - size_t len = strlen(s); - ssize_t written; - - if (s_fd < 0 || s_readerClosed > 0) { - return AT_ERROR_CHANNEL_CLOSED; - } - - RLOGD("AT> %s\n", s); - - AT_DUMP( ">> ", s, strlen(s) ); - - /* the main string */ - while (cur < len) { - do { - written = write (s_fd, s + cur, len - cur); - } while (written < 0 && errno == EINTR); - - if (written < 0) { - return AT_ERROR_GENERIC; - } - - cur += written; - } - - /* the \r */ - - do { - written = write (s_fd, "\r" , 1); - } while ((written < 0 && errno == EINTR) || (written == 0)); - - if (written < 0) { - return AT_ERROR_GENERIC; - } - - return 0; -} -static int writeCtrlZ (const char *s) -{ - size_t cur = 0; - size_t len = strlen(s); - ssize_t written; - - if (s_fd < 0 || s_readerClosed > 0) { - return AT_ERROR_CHANNEL_CLOSED; - } - - RLOGD("AT> %s^Z\n", s); - - AT_DUMP( ">* ", s, strlen(s) ); - - /* the main string */ - while (cur < len) { - do { - written = write (s_fd, s + cur, len - cur); - } while (written < 0 && errno == EINTR); - - if (written < 0) { - return AT_ERROR_GENERIC; - } - - cur += written; - } - - /* the ^Z */ - - do { - written = write (s_fd, "\032" , 1); - } while ((written < 0 && errno == EINTR) || (written == 0)); - - if (written < 0) { - return AT_ERROR_GENERIC; - } - - return 0; -} - -static void clearPendingCommand() -{ - if (sp_response != NULL) { - at_response_free(sp_response); - } - - sp_response = NULL; - s_responsePrefix = NULL; - s_smsPDU = NULL; -} - - -/** - * Starts AT handler on stream "fd' - * returns 0 on success, -1 on error - */ -int at_open(int fd, ATUnsolHandler h) -{ - int ret; - pthread_t tid; - pthread_attr_t attr; - - s_fd = fd; - s_unsolHandler = h; - s_readerClosed = 0; - - s_responsePrefix = NULL; - s_smsPDU = NULL; - sp_response = NULL; - - pthread_attr_init (&attr); - pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); - - ret = pthread_create(&s_tid_reader, &attr, readerLoop, &attr); - - if (ret < 0) { - perror ("pthread_create"); - return -1; - } - - - return 0; -} - -/* FIXME is it ok to call this from the reader and the command thread? */ -void at_close() -{ - if (s_fd >= 0) { - close(s_fd); - } - s_fd = -1; - - pthread_mutex_lock(&s_commandmutex); - - s_readerClosed = 1; - - pthread_cond_signal(&s_commandcond); - - pthread_mutex_unlock(&s_commandmutex); - - /* the reader thread should eventually die */ -} - -static ATResponse * at_response_new() -{ - return (ATResponse *) calloc(1, sizeof(ATResponse)); -} - -void at_response_free(ATResponse *p_response) -{ - ATLine *p_line; - - if (p_response == NULL) return; - - p_line = p_response->p_intermediates; - - while (p_line != NULL) { - ATLine *p_toFree; - - p_toFree = p_line; - p_line = p_line->p_next; - - free(p_toFree->line); - free(p_toFree); - } - - free (p_response->finalResponse); - free (p_response); -} - -/** - * The line reader places the intermediate responses in reverse order - * here we flip them back - */ -static void reverseIntermediates(ATResponse *p_response) -{ - ATLine *pcur,*pnext; - - pcur = p_response->p_intermediates; - p_response->p_intermediates = NULL; - - while (pcur != NULL) { - pnext = pcur->p_next; - pcur->p_next = p_response->p_intermediates; - p_response->p_intermediates = pcur; - pcur = pnext; - } -} - -/** - * Internal send_command implementation - * Doesn't lock or call the timeout callback - * - * timeoutMsec == 0 means infinite timeout - */ - -static int at_send_command_full_nolock (const char *command, ATCommandType type, - const char *responsePrefix, const char *smspdu, - long long timeoutMsec, ATResponse **pp_outResponse) -{ - int err = 0; - struct timespec ts; - - if(sp_response != NULL) { - err = AT_ERROR_COMMAND_PENDING; - goto error; - } - - err = writeline (command); - - if (err < 0) { - goto error; - } - - s_type = type; - s_responsePrefix = responsePrefix; - s_smsPDU = smspdu; - sp_response = at_response_new(); - - if (timeoutMsec != 0) { - setTimespecRelative(&ts, timeoutMsec); - } - - while (sp_response->finalResponse == NULL && s_readerClosed == 0) { - if (timeoutMsec != 0) { - err = pthread_cond_timedwait(&s_commandcond, &s_commandmutex, &ts); - } else { - err = pthread_cond_wait(&s_commandcond, &s_commandmutex); - } - - if (err == ETIMEDOUT) { - err = AT_ERROR_TIMEOUT; - goto error; - } - } - - if (pp_outResponse == NULL) { - at_response_free(sp_response); - } else { - /* line reader stores intermediate responses in reverse order */ - reverseIntermediates(sp_response); - *pp_outResponse = sp_response; - } - - sp_response = NULL; - - if(s_readerClosed > 0) { - err = AT_ERROR_CHANNEL_CLOSED; - goto error; - } - - err = 0; -error: - clearPendingCommand(); - - return err; -} - -/** - * Internal send_command implementation - * - * timeoutMsec == 0 means infinite timeout - */ -static int at_send_command_full (const char *command, ATCommandType type, - const char *responsePrefix, const char *smspdu, - long long timeoutMsec, ATResponse **pp_outResponse) -{ - int err; - bool inEmulator; - - if (0 != pthread_equal(s_tid_reader, pthread_self())) { - /* cannot be called from reader thread */ - return AT_ERROR_INVALID_THREAD; - } - inEmulator = isInEmulator(); - if (inEmulator) { - pthread_mutex_lock(&s_writeMutex); - } - pthread_mutex_lock(&s_commandmutex); - - err = at_send_command_full_nolock(command, type, - responsePrefix, smspdu, - timeoutMsec, pp_outResponse); - - pthread_mutex_unlock(&s_commandmutex); - if (inEmulator) { - pthread_mutex_unlock(&s_writeMutex); - } - - if (err == AT_ERROR_TIMEOUT && s_onTimeout != NULL) { - s_onTimeout(); - } - - return err; -} - - -/** - * Issue a single normal AT command with no intermediate response expected - * - * "command" should not include \r - * pp_outResponse can be NULL - * - * if non-NULL, the resulting ATResponse * must be eventually freed with - * at_response_free - */ -int at_send_command (const char *command, ATResponse **pp_outResponse) -{ - int err; - - err = at_send_command_full (command, NO_RESULT, NULL, - NULL, 0, pp_outResponse); - - return err; -} - - -int at_send_command_singleline (const char *command, - const char *responsePrefix, - ATResponse **pp_outResponse) -{ - int err; - - err = at_send_command_full (command, SINGLELINE, responsePrefix, - NULL, 0, pp_outResponse); - - if (err == 0 && pp_outResponse != NULL - && (*pp_outResponse)->success > 0 - && (*pp_outResponse)->p_intermediates == NULL - ) { - /* successful command must have an intermediate response */ - at_response_free(*pp_outResponse); - *pp_outResponse = NULL; - return AT_ERROR_INVALID_RESPONSE; - } - - return err; -} - - -int at_send_command_numeric (const char *command, - ATResponse **pp_outResponse) -{ - int err; - - err = at_send_command_full (command, NUMERIC, NULL, - NULL, 0, pp_outResponse); - - if (err == 0 && pp_outResponse != NULL - && (*pp_outResponse)->success > 0 - && (*pp_outResponse)->p_intermediates == NULL - ) { - /* successful command must have an intermediate response */ - at_response_free(*pp_outResponse); - *pp_outResponse = NULL; - return AT_ERROR_INVALID_RESPONSE; - } - - return err; -} - - -int at_send_command_sms (const char *command, - const char *pdu, - const char *responsePrefix, - ATResponse **pp_outResponse) -{ - int err; - - err = at_send_command_full (command, SINGLELINE, responsePrefix, - pdu, 0, pp_outResponse); - - if (err == 0 && pp_outResponse != NULL - && (*pp_outResponse)->success > 0 - && (*pp_outResponse)->p_intermediates == NULL - ) { - /* successful command must have an intermediate response */ - at_response_free(*pp_outResponse); - *pp_outResponse = NULL; - return AT_ERROR_INVALID_RESPONSE; - } - - return err; -} - - -int at_send_command_multiline (const char *command, - const char *responsePrefix, - ATResponse **pp_outResponse) -{ - int err; - - err = at_send_command_full (command, MULTILINE, responsePrefix, - NULL, 0, pp_outResponse); - - return err; -} - - -/** This callback is invoked on the command thread */ -void at_set_on_timeout(void (*onTimeout)(void)) -{ - s_onTimeout = onTimeout; -} - -/** - * This callback is invoked on the reader thread (like ATUnsolHandler) - * when the input stream closes before you call at_close - * (not when you call at_close()) - * You should still call at_close() - */ - -void at_set_on_reader_closed(void (*onClose)(void)) -{ - s_onReaderClosed = onClose; -} - - -/** - * Periodically issue an AT command and wait for a response. - * Used to ensure channel has start up and is active - */ - -int at_handshake() -{ - int i; - int err = 0; - bool inEmulator; - - if (0 != pthread_equal(s_tid_reader, pthread_self())) { - /* cannot be called from reader thread */ - return AT_ERROR_INVALID_THREAD; - } - inEmulator = isInEmulator(); - if (inEmulator) { - pthread_mutex_lock(&s_writeMutex); - } - pthread_mutex_lock(&s_commandmutex); - - for (i = 0 ; i < HANDSHAKE_RETRY_COUNT ; i++) { - /* some stacks start with verbose off */ - err = at_send_command_full_nolock ("ATE0Q0V1", NO_RESULT, - NULL, NULL, HANDSHAKE_TIMEOUT_MSEC, NULL); - - if (err == 0) { - break; - } - } - - if (err == 0) { - /* pause for a bit to let the input buffer drain any unmatched OK's - (they will appear as extraneous unsolicited responses) */ - - sleepMsec(HANDSHAKE_TIMEOUT_MSEC); - } - - pthread_mutex_unlock(&s_commandmutex); - if (inEmulator) { - pthread_mutex_unlock(&s_writeMutex); - } - - return err; -} - -/** - * Returns error code from response - * Assumes AT+CMEE=1 (numeric) mode - */ -AT_CME_Error at_get_cme_error(const ATResponse *p_response) -{ - int ret; - int err; - char *p_cur; - - if (p_response->success > 0) { - return CME_SUCCESS; - } - - if (p_response->finalResponse == NULL - || !strStartsWith(p_response->finalResponse, "+CME ERROR:") - ) { - return CME_ERROR_NON_CME; - } - - p_cur = p_response->finalResponse; - err = at_tok_start(&p_cur); - - if (err < 0) { - return CME_ERROR_NON_CME; - } - - err = at_tok_nextint(&p_cur, &ret); - - if (err < 0) { - return CME_ERROR_NON_CME; - } - - return (AT_CME_Error) ret; -} - diff --git a/radio/ril/atchannel.h b/radio/ril/atchannel.h deleted file mode 100644 index 94011417..00000000 --- a/radio/ril/atchannel.h +++ /dev/null @@ -1,125 +0,0 @@ -/* //device/system/reference-ril/atchannel.h -** -** Copyright 2006, 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. -*/ - -#ifndef ATCHANNEL_H -#define ATCHANNEL_H 1 - -#ifdef __cplusplus -extern "C" { -#endif - -/* define AT_DEBUG to send AT traffic to /tmp/radio-at.log" */ -#define AT_DEBUG 0 - -#if AT_DEBUG -extern void AT_DUMP(const char* prefix, const char* buff, int len); -#else -#define AT_DUMP(prefix,buff,len) do{}while(0) -#endif - -#define AT_ERROR_GENERIC (-1) -#define AT_ERROR_COMMAND_PENDING (-2) -#define AT_ERROR_CHANNEL_CLOSED (-3) -#define AT_ERROR_TIMEOUT (-4) -#define AT_ERROR_INVALID_THREAD (-5) /* AT commands may not be issued from - reader thread (or unsolicited response - callback */ -#define AT_ERROR_INVALID_RESPONSE (-6) /* eg an at_send_command_singleline that - did not get back an intermediate - response */ - - -typedef enum { - NO_RESULT, /* no intermediate response expected */ - NUMERIC, /* a single intermediate response starting with a 0-9 */ - SINGLELINE, /* a single intermediate response starting with a prefix */ - MULTILINE /* multiple line intermediate response - starting with a prefix */ -} ATCommandType; - -/** a singly-lined list of intermediate responses */ -typedef struct ATLine { - struct ATLine *p_next; - char *line; -} ATLine; - -/** Free this with at_response_free() */ -typedef struct { - int success; /* true if final response indicates - success (eg "OK") */ - char *finalResponse; /* eg OK, ERROR */ - ATLine *p_intermediates; /* any intermediate responses */ -} ATResponse; - -/** - * a user-provided unsolicited response handler function - * this will be called from the reader thread, so do not block - * "s" is the line, and "sms_pdu" is either NULL or the PDU response - * for multi-line TS 27.005 SMS PDU responses (eg +CMT:) - */ -typedef void (*ATUnsolHandler)(const char *s, const char *sms_pdu); - -int at_open(int fd, ATUnsolHandler h); -void at_close(); - -/* This callback is invoked on the command thread. - You should reset or handshake here to avoid getting out of sync */ -void at_set_on_timeout(void (*onTimeout)(void)); -/* This callback is invoked on the reader thread (like ATUnsolHandler) - when the input stream closes before you call at_close - (not when you call at_close()) - You should still call at_close() - It may also be invoked immediately from the current thread if the read - channel is already closed */ -void at_set_on_reader_closed(void (*onClose)(void)); - -int at_send_command_singleline (const char *command, - const char *responsePrefix, - ATResponse **pp_outResponse); - -int at_send_command_numeric (const char *command, - ATResponse **pp_outResponse); - -int at_send_command_multiline (const char *command, - const char *responsePrefix, - ATResponse **pp_outResponse); - - -int at_handshake(); - -int at_send_command (const char *command, ATResponse **pp_outResponse); - -int at_send_command_sms (const char *command, const char *pdu, - const char *responsePrefix, - ATResponse **pp_outResponse); - -void at_response_free(ATResponse *p_response); - -typedef enum { - CME_ERROR_NON_CME = -1, - CME_SUCCESS = 0, - CME_SIM_NOT_INSERTED = 10, - CME_INVALID_INDEX = 21, -} AT_CME_Error; - -AT_CME_Error at_get_cme_error(const ATResponse *p_response); - -#ifdef __cplusplus -} -#endif - -#endif /*ATCHANNEL_H*/ diff --git a/radio/ril/if_monitor.cpp b/radio/ril/if_monitor.cpp deleted file mode 100644 index 87681f57..00000000 --- a/radio/ril/if_monitor.cpp +++ /dev/null @@ -1,415 +0,0 @@ -/* - * Copyright 2018, 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. - */ - -#include "if_monitor.h" - -#include <arpa/inet.h> -#include <errno.h> -#include <ifaddrs.h> -#include <linux/rtnetlink.h> -#include <net/if.h> -#include <poll.h> -#include <stdio.h> -#include <string.h> -#include <sys/socket.h> -#include <sys/types.h> -#include <unistd.h> - -#include <memory> -#include <mutex> -#include <thread> -#include <unordered_map> -#include <unordered_set> -#include <vector> - -#define LOG_TAG "RIL-IFMON" -#include <utils/Log.h> - -static const size_t kReadBufferSize = 32768; - -static const size_t kControlServer = 0; -static const size_t kControlClient = 1; - -// A list of commands that can be sent to the monitor. These should be one -// character long as that is all that the monitor will read and process. -static const char kMonitorStopCommand[] = "\1"; -static const char kMonitorAckCommand[] = "\2"; - -static size_t addrLength(int addrFamily) { - switch (addrFamily) { - case AF_INET: - return 4; - case AF_INET6: - return 16; - default: - return 0; - } -} - -static const void* getSockAddrData(const struct sockaddr* addr) { - switch (addr->sa_family) { - case AF_INET: - return &reinterpret_cast<const struct sockaddr_in*>(addr)->sin_addr; - case AF_INET6: - return - &reinterpret_cast<const struct sockaddr_in6*>(addr)->sin6_addr; - default: - return nullptr; - } -} - -bool operator==(const struct ifAddress& left, const struct ifAddress& right) { - // The prefix length does not factor in to whether two addresses are the - // same or not. Only the family and the address data. This matches the - // kernel behavior when attempting to add the same address with different - // prefix lengths, those changes are rejected because the address already - // exists. - return left.family == right.family && - memcmp(&left.addr, &right.addr, addrLength(left.family)) == 0; -} - -class InterfaceMonitor { -public: - InterfaceMonitor() : mSocketFd(-1) { - mControlSocket[kControlServer] = -1; - mControlSocket[kControlClient] = -1; - } - - ~InterfaceMonitor() { - if (mControlSocket[kControlClient] != -1) { - ::close(mControlSocket[kControlClient]); - mControlSocket[kControlClient] = -1; - } - if (mControlSocket[kControlServer] != -1) { - ::close(mControlSocket[kControlServer]); - mControlSocket[kControlServer] = -1; - } - - if (mSocketFd != -1) { - ::close(mSocketFd); - mSocketFd = -1; - } - } - - bool init() { - if (mSocketFd != -1) { - RLOGE("InterfaceMonitor already initialized"); - return false; - } - - mSocketFd = ::socket(AF_NETLINK, - SOCK_DGRAM | SOCK_CLOEXEC, - NETLINK_ROUTE); - if (mSocketFd == -1) { - RLOGE("InterfaceMonitor failed to open socket: %s", strerror(errno)); - return false; - } - - if (::socketpair(AF_UNIX, SOCK_DGRAM, 0, mControlSocket) != 0) { - RLOGE("Unable to create control socket pair: %s", strerror(errno)); - return false; - } - - struct sockaddr_nl addr; - memset(&addr, 0, sizeof(addr)); - addr.nl_family = AF_NETLINK; - addr.nl_groups = (1 << (RTNLGRP_IPV4_IFADDR - 1)) | - (1 << (RTNLGRP_IPV6_IFADDR - 1)); - - struct sockaddr* sa = reinterpret_cast<struct sockaddr*>(&addr); - if (::bind(mSocketFd, sa, sizeof(addr)) != 0) { - RLOGE("InterfaceMonitor failed to bind socket: %s", - strerror(errno)); - return false; - } - - return true; - } - - void setCallback(ifMonitorCallback callback) { - mOnAddressChangeCallback = callback; - } - - void runAsync() { - std::unique_lock<std::mutex> lock(mThreadMutex); - mThread = std::make_unique<std::thread>([this]() { run(); }); - } - - void requestAddresses() { - struct ifaddrs* addresses = nullptr; - - if (getifaddrs(&addresses) != 0) { - RLOGE("Unable to retrieve list of interfaces, cannot get initial " - "interface addresses: %s", strerror(errno)); - return; - } - - for (struct ifaddrs* cur = addresses; cur; cur = cur->ifa_next) { - if (cur->ifa_name == nullptr || - cur->ifa_addr == nullptr || - cur->ifa_netmask == nullptr) { - // Interface doesn't have all the information we need. Rely on - // the netlink notification to catch this interface later if it - // is configured correctly. - continue; - } - if (cur->ifa_flags & IFF_LOOPBACK) { - // Not interested in loopback devices, they will never be radio - // interfaces. - continue; - } - unsigned int ifIndex = if_nametoindex(cur->ifa_name); - if (ifIndex == 0) { - RLOGE("Encountered interface %s with no index: %s", - cur->ifa_name, strerror(errno)); - continue; - } - ifAddress addr; - addr.family = cur->ifa_addr->sa_family; - addr.prefix = getPrefix(cur->ifa_netmask); - memcpy(addr.addr, - getSockAddrData(cur->ifa_addr), - addrLength(cur->ifa_addr->sa_family)); - mAddresses[ifIndex].push_back(addr); - } - freeifaddrs(addresses); - - if (mOnAddressChangeCallback) { - for (const auto& ifAddr : mAddresses) { - mOnAddressChangeCallback(ifAddr.first, - ifAddr.second.data(), - ifAddr.second.size()); - } - } - } - - int getPrefix(const struct sockaddr* addr) { - // This uses popcnt, a built-in instruction on some CPUs, to count - // the number of bits in a 32-bit word. The number of bits in a netmask - // equals the width of the prefix. For example a netmask of - // 255.255.255.0 has 24 bits set and that's also its width. - if (addr->sa_family == AF_INET) { - auto v4 = reinterpret_cast<const struct sockaddr_in*>(addr); - return __builtin_popcount(v4->sin_addr.s_addr); - } else if (addr->sa_family == AF_INET6) { - auto v6 = reinterpret_cast<const struct sockaddr_in6*>(addr); - // Copy to our own array to avoid aliasing - uint64_t words[2]; - memcpy(words, v6->sin6_addr.s6_addr, sizeof(words)); - return __builtin_popcountll(words[0]) + - __builtin_popcountll(words[1]); - } - return 0; - } - - void run() { - requestAddresses(); - - std::vector<struct pollfd> fds(2); - fds[0].events = POLLIN; - fds[0].fd = mControlSocket[kControlServer]; - fds[1].events = POLLIN; - fds[1].fd = mSocketFd; - while (true) { - int status = ::poll(fds.data(), fds.size(), -1); - if (status < 0) { - if (errno == EINTR) { - // Interrupted, just keep going - continue; - } - // Actual error, time to quit - RLOGE("Polling failed: %s", strerror(errno)); - break; - } else if (status == 0) { - // Timeout - continue; - } - - if (fds[0].revents & POLLIN) { - // Control message received - char command = -1; - if (::read(mControlSocket[kControlServer], - &command, - sizeof(command)) == 1) { - if (command == kMonitorStopCommand[0]) { - break; - } - } - } else if (fds[1].revents & POLLIN) { - onReadAvailable(); - } - } - ::write(mControlSocket[kControlServer], kMonitorAckCommand, 1); - } - - void stop() { - std::unique_lock<std::mutex> lock(mThreadMutex); - if (mThread) { - ::write(mControlSocket[kControlClient], kMonitorStopCommand, 1); - char ack = -1; - while (ack != kMonitorAckCommand[0]) { - ::read(mControlSocket[kControlClient], &ack, sizeof(ack)); - } - mThread->join(); - mThread.reset(); - } - } - -private: - void onReadAvailable() { - char buffer[kReadBufferSize]; - struct sockaddr_storage storage; - - while (true) { - socklen_t addrSize = sizeof(storage); - int status = ::recvfrom(mSocketFd, - buffer, - sizeof(buffer), - MSG_DONTWAIT, - reinterpret_cast<struct sockaddr*>(&storage), - &addrSize); - if (status < 0 && (errno == EAGAIN || errno == EWOULDBLOCK)) { - // Nothing to receive, everything is fine - return; - } else if (status < 0 && errno == EINTR) { - // Caught interrupt, try again - continue; - } else if (status < 0) { - RLOGE("InterfaceMonitor receive failed: %s", strerror(errno)); - return; - } else if (addrSize < 0 || - static_cast<size_t>(addrSize) != sizeof(struct sockaddr_nl)) { - RLOGE("InterfaceMonitor received invalid address size"); - return; - } - - size_t length = static_cast<size_t>(status); - - auto hdr = reinterpret_cast<struct nlmsghdr*>(buffer); - while (NLMSG_OK(hdr, length) && hdr->nlmsg_type != NLMSG_DONE) { - switch (hdr->nlmsg_type) { - case RTM_NEWADDR: - case RTM_DELADDR: - handleAddressChange(hdr); - break; - default: - RLOGE("Received message type %d", (int)hdr->nlmsg_type); - break; - } - hdr = NLMSG_NEXT(hdr, length); - } - } - } - - std::string getInterfaceName(unsigned int ifIndex) { - char buffer[IF_NAMESIZE] = { '\0' }; - return if_indextoname(ifIndex, buffer); - } - - void handleAddressChange(const struct nlmsghdr* hdr) { - if (!mOnAddressChangeCallback) { - return; - } - - auto msg = reinterpret_cast<const struct ifaddrmsg*>(NLMSG_DATA(hdr)); - std::vector<ifAddress>& ifAddrs = mAddresses[msg->ifa_index]; - - auto attr = reinterpret_cast<const struct rtattr*>(IFA_RTA(msg)); - int attrLen = IFA_PAYLOAD(hdr); - - bool somethingChanged = false; - for (;attr && RTA_OK(attr, attrLen); attr = RTA_NEXT(attr, attrLen)) { - if (attr->rta_type != IFA_LOCAL && attr->rta_type != IFA_ADDRESS) { - continue; - } - - ifAddress addr; - memset(&addr, 0, sizeof(addr)); - - // Ensure that the payload matches the expected address length - if (RTA_PAYLOAD(attr) >= addrLength(msg->ifa_family)) { - addr.family = msg->ifa_family; - addr.prefix = msg->ifa_prefixlen; - memcpy(&addr.addr, RTA_DATA(attr), addrLength(addr.family)); - } else { - RLOGE("Invalid address family (%d) and size (%d) combination", - int(msg->ifa_family), int(RTA_PAYLOAD(attr))); - continue; - } - - auto it = std::find(ifAddrs.begin(), ifAddrs.end(), addr); - if (hdr->nlmsg_type == RTM_NEWADDR && it == ifAddrs.end()) { - // New address does not exist, add it - ifAddrs.push_back(addr); - somethingChanged = true; - } else if (hdr->nlmsg_type == RTM_DELADDR && it != ifAddrs.end()) { - // Address was removed and it exists, remove it - ifAddrs.erase(it); - somethingChanged = true; - } - } - - if (somethingChanged) { - mOnAddressChangeCallback(msg->ifa_index, - ifAddrs.data(), - ifAddrs.size()); - } - } - - ifMonitorCallback mOnAddressChangeCallback; - std::unordered_map<unsigned int, std::vector<ifAddress>> mAddresses; - std::unique_ptr<std::thread> mThread; - std::mutex mThreadMutex; - int mSocketFd; - int mControlSocket[2]; -}; - -extern "C" -struct ifMonitor* ifMonitorCreate() { - auto monitor = std::make_unique<InterfaceMonitor>(); - if (!monitor || !monitor->init()) { - return nullptr; - } - return reinterpret_cast<struct ifMonitor*>(monitor.release()); -} - -extern "C" -void ifMonitorFree(struct ifMonitor* ifMonitor) { - InterfaceMonitor* monitor = reinterpret_cast<InterfaceMonitor*>(ifMonitor); - delete monitor; -} - -extern "C" -void ifMonitorSetCallback(struct ifMonitor* ifMonitor, - ifMonitorCallback callback) { - InterfaceMonitor* monitor = reinterpret_cast<InterfaceMonitor*>(ifMonitor); - monitor->setCallback(callback); -} - -extern "C" -void ifMonitorRunAsync(struct ifMonitor* ifMonitor) { - InterfaceMonitor* monitor = reinterpret_cast<InterfaceMonitor*>(ifMonitor); - - monitor->runAsync(); -} - -extern "C" -void ifMonitorStop(struct ifMonitor* ifMonitor) { - InterfaceMonitor* monitor = reinterpret_cast<InterfaceMonitor*>(ifMonitor); - - monitor->stop(); -} - diff --git a/radio/ril/if_monitor.h b/radio/ril/if_monitor.h deleted file mode 100644 index 118bf880..00000000 --- a/radio/ril/if_monitor.h +++ /dev/null @@ -1,49 +0,0 @@ -/* - * Copyright 2018, 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. - */ - -#pragma once - -#include <stddef.h> - -#ifdef __cplusplus -extern "C" { -#endif - -struct ifMonitor; - -struct ifAddress { - int family; - int prefix; - unsigned char addr[16]; -}; - -// A callback for when the addresses on an interface changes -typedef void (*ifMonitorCallback)(unsigned int /*interface index*/, - const struct ifAddress* /*addresses*/, - size_t /*number of addresses */); - -struct ifMonitor* ifMonitorCreate(); -void ifMonitorFree(struct ifMonitor* monitor); - -void ifMonitorSetCallback(struct ifMonitor* monitor, - ifMonitorCallback callback); -void ifMonitorRunAsync(struct ifMonitor* monitor); -void ifMonitorStop(struct ifMonitor* monitor); - -#ifdef __cplusplus -} // extern "C" -#endif - diff --git a/radio/ril/ipv6_monitor.cpp b/radio/ril/ipv6_monitor.cpp deleted file mode 100644 index 8d577bc4..00000000 --- a/radio/ril/ipv6_monitor.cpp +++ /dev/null @@ -1,496 +0,0 @@ -/* - * Copyright 2019, 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. - */ - -#include "ipv6_monitor.h" - -#include <errno.h> -#include <linux/filter.h> -#include <net/if.h> -#include <netinet/ether.h> -#include <netinet/icmp6.h> -#include <netinet/ip6.h> -#include <poll.h> -#include <string.h> -#include <unistd.h> - -#include <array> -#include <mutex> -#include <string> -#include <thread> -#include <unordered_set> -#include <vector> - -#define LOG_TAG "RIL-IPV6MON" -#include <utils/Log.h> - -static constexpr size_t kReadBufferSize = 32768; - -static constexpr size_t kRecursiveDnsOptHeaderSize = 8; - -static constexpr size_t kControlClient = 0; -static constexpr size_t kControlServer = 1; - -static constexpr char kMonitorAckCommand = '\1'; -static constexpr char kMonitorStopCommand = '\2'; - -// The amount of time to wait before trying to initialize interface again if -// it's not ready when rild starts. -static constexpr int kDeferredTimeoutMilliseconds = 1000; - -bool operator==(const in6_addr& left, const in6_addr& right) { - return ::memcmp(left.s6_addr, right.s6_addr, sizeof(left.s6_addr)) == 0; -} - -bool operator!=(const in6_addr& left, const in6_addr& right) { - return ::memcmp(left.s6_addr, right.s6_addr, sizeof(left.s6_addr)) != 0; -} - -template<class T> -static inline void hash_combine(size_t& seed, const T& value) { - std::hash<T> hasher; - seed ^= hasher(value) + 0x9e3779b9 + (seed << 6) + (seed >> 2); -} - -namespace std { -template<> struct hash<in6_addr> { - size_t operator()(const in6_addr& ad) const { - size_t seed = 0; - hash_combine(seed, *reinterpret_cast<const uint32_t*>(&ad.s6_addr[0])); - hash_combine(seed, *reinterpret_cast<const uint32_t*>(&ad.s6_addr[4])); - hash_combine(seed, *reinterpret_cast<const uint32_t*>(&ad.s6_addr[8])); - hash_combine(seed, *reinterpret_cast<const uint32_t*>(&ad.s6_addr[12])); - return seed; - } -}; -} // namespace std - -static constexpr uint32_t kIpTypeOffset = offsetof(ip6_hdr, ip6_nxt); -static constexpr uint32_t kIcmpTypeOffset = sizeof(ip6_hdr) + - offsetof(icmp6_hdr, icmp6_type); - -// This is BPF program that will filter out anything that is not an NDP router -// advertisement. It's a very basic assembler syntax. The jumps indicate how -// many instructions to jump in addition to the automatic increment of the -// program counter. So a jump statement with a zero means to go to the next -// instruction, a value of 3 means that the next instruction will be the 4th -// after the current one. -static const struct sock_filter kNdpFilter[] = { - // Load byte at absolute address kIpTypeOffset - BPF_STMT(BPF_LD | BPF_B | BPF_ABS, kIpTypeOffset), - // Jump, if byte is IPPROTO_ICMPV6 jump 0 instructions, if not jump 3. - BPF_JUMP(BPF_JMP | BPF_JEQ | BPF_K, IPPROTO_ICMPV6, 0, 3), - // Load byte at absolute address kIcmpTypeOffset - BPF_STMT(BPF_LD | BPF_B | BPF_ABS, kIcmpTypeOffset), - // Jump, if byte is ND_ROUTER_ADVERT jump 0 instructions, if not jump 1 - BPF_JUMP(BPF_JMP | BPF_JEQ | BPF_K, ND_ROUTER_ADVERT, 0, 1), - // Return the number of bytes to accept, accept all of them - BPF_STMT(BPF_RET | BPF_K, std::numeric_limits<uint32_t>::max()), - // Accept zero bytes, this is where the failed jumps go - BPF_STMT(BPF_RET | BPF_K, 0) -}; -static constexpr size_t kNdpFilterSize = - sizeof(kNdpFilter) / sizeof(kNdpFilter[0]); - -class Ipv6Monitor { -public: - Ipv6Monitor(const char* interfaceName); - ~Ipv6Monitor(); - - enum class InitResult { - Error, - Deferred, - Success, - }; - InitResult init(); - void setCallback(ipv6MonitorCallback callback); - void runAsync(); - void stop(); - -private: - InitResult initInterfaces(); - void run(); - void onReadAvailable(); - - ipv6MonitorCallback mMonitorCallback; - - in6_addr mGateway; - std::unordered_set<in6_addr> mDnsServers; - - std::unique_ptr<std::thread> mThread; - std::mutex mThreadMutex; - - std::string mInterfaceName; - int mSocketFd; - int mControlSocket[2]; - int mPollTimeout = -1; - bool mFullyInitialized = false; -}; - -Ipv6Monitor::Ipv6Monitor(const char* interfaceName) : - mMonitorCallback(nullptr), - mInterfaceName(interfaceName), - mSocketFd(-1) { - memset(&mGateway, 0, sizeof(mGateway)); - mControlSocket[0] = -1; - mControlSocket[1] = -1; -} - -Ipv6Monitor::~Ipv6Monitor() { - for (int& fd : mControlSocket) { - if (fd != -1) { - ::close(fd); - fd = -1; - } - } - if (mSocketFd != -1) { - ::close(mSocketFd); - mSocketFd = -1; - } -} - -Ipv6Monitor::InitResult Ipv6Monitor::init() { - if (mSocketFd != -1) { - RLOGE("Ipv6Monitor already initialized"); - return InitResult::Error; - } - - if (::socketpair(AF_UNIX, SOCK_DGRAM, 0, mControlSocket) != 0) { - RLOGE("Ipv6Monitor failed to create control socket pair: %s", - strerror(errno)); - return InitResult::Error; - } - - mSocketFd = ::socket(AF_PACKET, SOCK_DGRAM | SOCK_CLOEXEC, ETH_P_IPV6); - if (mSocketFd == -1) { - RLOGE("Ipv6Monitor failed to open socket: %s", strerror(errno)); - return InitResult::Error; - } - // If interface initialization fails we'll retry later - return initInterfaces(); -} - -void Ipv6Monitor::setCallback(ipv6MonitorCallback callback) { - mMonitorCallback = callback; -} - -Ipv6Monitor::InitResult Ipv6Monitor::initInterfaces() { - if (mFullyInitialized) { - RLOGE("Ipv6Monitor already initialized"); - return InitResult::Error; - } - struct ifreq request; - memset(&request, 0, sizeof(request)); - strlcpy(request.ifr_name, mInterfaceName.c_str(), sizeof(request.ifr_name)); - - // Set the ALLMULTI flag so we can capture multicast traffic - int status = ::ioctl(mSocketFd, SIOCGIFFLAGS, &request); - if (status != 0) { - if (errno == ENODEV) { - // It is not guaranteed that the network is entirely set up by the - // time rild has started. If that's the case the radio interface - // might not be up yet, try again later. - RLOGE("Ipv6Monitor could not initialize %s yet, retrying later", - mInterfaceName.c_str()); - mPollTimeout = kDeferredTimeoutMilliseconds; - return InitResult::Deferred; - } - RLOGE("Ipv6Monitor failed to get interface flags for %s: %s", - mInterfaceName.c_str(), strerror(errno)); - return InitResult::Error; - } - - if ((request.ifr_flags & IFF_ALLMULTI) == 0) { - // The flag is not set, we have to make another call - request.ifr_flags |= IFF_ALLMULTI; - - status = ::ioctl(mSocketFd, SIOCSIFFLAGS, &request); - if (status != 0) { - RLOGE("Ipv6Monitor failed to set interface flags for %s: %s", - mInterfaceName.c_str(), strerror(errno)); - return InitResult::Error; - } - } - - // Add a BPF filter to the socket so that we only receive the specific - // type of packet we're interested in. Otherwise we will receive ALL - // traffic on this interface. - struct sock_fprog filter; - filter.len = kNdpFilterSize; - // The API doesn't have const but it's not going to modify it so this is OK - filter.filter = const_cast<struct sock_filter*>(kNdpFilter); - status = ::setsockopt(mSocketFd, - SOL_SOCKET, - SO_ATTACH_FILTER, - &filter, - sizeof(filter)); - if (status != 0) { - RLOGE("Ipv6Monitor failed to set socket filter: %s", strerror(errno)); - return InitResult::Error; - } - - // Get the hardware address of the interface into a sockaddr struct for bind - struct sockaddr_ll ethAddr; - memset(ðAddr, 0, sizeof(ethAddr)); - ethAddr.sll_family = AF_PACKET; - ethAddr.sll_protocol = htons(ETH_P_IPV6); - ethAddr.sll_ifindex = if_nametoindex(mInterfaceName.c_str()); - if (ethAddr.sll_ifindex == 0) { - RLOGE("Ipv6Monitor failed to find index for %s: %s", - mInterfaceName.c_str(), strerror(errno)); - return InitResult::Error; - } - - status = ::ioctl(mSocketFd, SIOCGIFHWADDR, &request); - if (status != 0) { - RLOGE("Ipv6Monitor failed to get hardware address for %s: %s", - mInterfaceName.c_str(), strerror(errno)); - return InitResult::Error; - } - memcpy(ethAddr.sll_addr, request.ifr_addr.sa_data, ETH_ALEN); - - // Now bind to the hardware address - status = ::bind(mSocketFd, - reinterpret_cast<const struct sockaddr*>(ðAddr), - sizeof(ethAddr)); - if (status != 0) { - RLOGE("Ipv6Monitor failed to bind to %s hardware address: %s", - mInterfaceName.c_str(), strerror(errno)); - return InitResult::Error; - } - mFullyInitialized = true; - return InitResult::Success; -} - -void Ipv6Monitor::runAsync() { - std::unique_lock<std::mutex> lock(mThreadMutex); - mThread = std::make_unique<std::thread>([this]() { run(); }); -} - -void Ipv6Monitor::stop() { - std::unique_lock<std::mutex> lock(mThreadMutex); - if (!mThread) { - return; - } - ::write(mControlSocket[kControlClient], &kMonitorStopCommand, 1); - char ack = -1; - while (ack != kMonitorAckCommand) { - ::read(mControlSocket[kControlClient], &ack, sizeof(ack)); - } - mThread->join(); - mThread.reset(); -} - -void Ipv6Monitor::run() { - std::array<struct pollfd, 2> fds; - fds[0].events = POLLIN; - fds[0].fd = mControlSocket[kControlServer]; - fds[1].events = POLLIN; - fds[1].fd = mSocketFd; - - bool running = true; - while (running) { - int status = ::poll(fds.data(), fds.size(), mPollTimeout); - if (status < 0) { - if (errno == EINTR) { - // Interrupted, keep going - continue; - } - // An error occurred - RLOGE("Ipv6Monitor fatal failure polling failed; %s", - strerror(errno)); - break; - } else if (status == 0) { - // Timeout, nothing to read - if (!mFullyInitialized) { - InitResult result = initInterfaces(); - switch (result) { - case InitResult::Error: - // Something went wrong this time and we can't recover - running = false; - break; - case InitResult::Deferred: - // We need to keep waiting and then try again - mPollTimeout = kDeferredTimeoutMilliseconds; - break; - case InitResult::Success: - // Interfaces are initialized, no need to timeout again - mPollTimeout = -1; - break; - } - } - continue; - } - - if (fds[0].revents & POLLIN) { - // Control message received - char command = -1; - if (::read(mControlSocket[kControlServer], - &command, - sizeof(command)) == 1) { - if (command == kMonitorStopCommand) { - break; - } - } - } else if (fds[1].revents & POLLIN) { - onReadAvailable(); - } - } - ::write(mControlSocket[kControlServer], &kMonitorAckCommand, 1); -} - -void Ipv6Monitor::onReadAvailable() { - char buffer[kReadBufferSize]; - - ssize_t bytesRead = 0; - while (true) { - bytesRead = ::recv(mSocketFd, buffer, sizeof(buffer), 0); - if (bytesRead < 0) { - if (errno == EINTR) { - // Interrupted, try again right away - continue; - } - if (errno != EAGAIN && errno != EWOULDBLOCK) { - // Do not report an error for the above error codes, they are - // part of the normal turn of events. We just need to try again - // later when we run into those errors. - RLOGE("Ipv6Monitor failed to receive data: %s", - strerror(errno)); - } - return; - } - break; - } - - if (mMonitorCallback == nullptr) { - // No point in doing anything, we have read the data so the socket - // buffer doesn't fill up and that's all we can do. - return; - } - - if (static_cast<size_t>(bytesRead) < sizeof(ip6_hdr) + sizeof(icmp6_hdr)) { - // This message cannot be an ICMPv6 packet, ignore it - return; - } - - auto ipv6 = reinterpret_cast<const ip6_hdr*>(buffer); - uint8_t version = (ipv6->ip6_vfc & 0xF0) >> 4; - if (version != 6 || ipv6->ip6_nxt != IPPROTO_ICMPV6) { - // This message is not an IPv6 packet or not an ICMPv6 packet, ignore it - return; - } - - // The ICMP header starts right after the IPv6 header - auto icmp = reinterpret_cast<const icmp6_hdr*>(buffer + sizeof(ip6_hdr)); - if (icmp->icmp6_code != 0) { - // All packets we care about have an icmp code of zero. - return; - } - - if (icmp->icmp6_type != ND_ROUTER_ADVERT) { - // We only care about router advertisements - return; - } - - // At this point we know it's a valid packet, let's look inside - - // The gateway is the same as the source in the IP header - in6_addr gateway = ipv6->ip6_src; - - // Search through the options for DNS servers - const char* options = buffer + sizeof(ip6_hdr) + sizeof(nd_router_advert); - const nd_opt_hdr* option = reinterpret_cast<const nd_opt_hdr*>(options); - - std::vector<in6_addr> dnsServers; - const nd_opt_hdr* nextOpt = nullptr; - for (const nd_opt_hdr* opt = option; opt; opt = nextOpt) { - auto nextOptLoc = - reinterpret_cast<const char*>(opt) + opt->nd_opt_len * 8u; - if (nextOptLoc > buffer + bytesRead) { - // Not enough room for this option, abort - break; - } - if (nextOptLoc < buffer + bytesRead) { - nextOpt = reinterpret_cast<const nd_opt_hdr*>(nextOptLoc); - } else { - nextOpt = nullptr; - } - if (opt->nd_opt_type != 25 || opt->nd_opt_len < 1) { - // Not an RNDSS option, skip it - continue; - } - - size_t numEntries = (opt->nd_opt_len - 1) / 2; - const char* addrLoc = reinterpret_cast<const char*>(opt); - addrLoc += kRecursiveDnsOptHeaderSize; - auto addrs = reinterpret_cast<const in6_addr*>(addrLoc); - - for (size_t i = 0; i < numEntries; ++i) { - dnsServers.push_back(addrs[i]); - } - } - - bool changed = false; - if (gateway != mGateway) { - changed = true; - mGateway = gateway; - } - - for (const auto& dns : dnsServers) { - if (mDnsServers.find(dns) == mDnsServers.end()) { - mDnsServers.insert(dns); - changed = true; - } - } - - if (changed) { - mMonitorCallback(&gateway, dnsServers.data(), dnsServers.size()); - } -} - -extern "C" -struct ipv6Monitor* ipv6MonitorCreate(const char* interfaceName) { - auto monitor = std::make_unique<Ipv6Monitor>(interfaceName); - if (!monitor || monitor->init() == Ipv6Monitor::InitResult::Error) { - return nullptr; - } - return reinterpret_cast<struct ipv6Monitor*>(monitor.release()); -} - -extern "C" -void ipv6MonitorFree(struct ipv6Monitor* ipv6Monitor) { - auto monitor = reinterpret_cast<Ipv6Monitor*>(ipv6Monitor); - delete monitor; -} - -extern "C" -void ipv6MonitorSetCallback(struct ipv6Monitor* ipv6Monitor, - ipv6MonitorCallback callback) { - auto monitor = reinterpret_cast<Ipv6Monitor*>(ipv6Monitor); - monitor->setCallback(callback); -} - -extern "C" -void ipv6MonitorRunAsync(struct ipv6Monitor* ipv6Monitor) { - auto monitor = reinterpret_cast<Ipv6Monitor*>(ipv6Monitor); - monitor->runAsync(); -} - -extern "C" -void ipv6MonitorStop(struct ipv6Monitor* ipv6Monitor) { - auto monitor = reinterpret_cast<Ipv6Monitor*>(ipv6Monitor); - monitor->stop(); -} - diff --git a/radio/ril/ipv6_monitor.h b/radio/ril/ipv6_monitor.h deleted file mode 100644 index b58402dd..00000000 --- a/radio/ril/ipv6_monitor.h +++ /dev/null @@ -1,47 +0,0 @@ -/* - * Copyright 2019, 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. - */ - -#pragma once - -#include <netinet/in.h> - -#ifdef __cplusplus -extern "C" { -#endif - -struct ipv6Monitor; - -// A callback for when the IPv6 configuration changes. -typedef void (*ipv6MonitorCallback)(const struct in6_addr* /*gateway*/, - const struct in6_addr* /*dns servers*/, - size_t /*number of dns servers */); - -// Create an IPv6 monitor that will monitor |interfaceName| for IPv6 router -// advertisements. The monitor will trigger a callback if the gateway and/or -// DNS servers provided by router advertisements change at any point. -struct ipv6Monitor* ipv6MonitorCreate(const char* interfaceName); -void ipv6MonitorFree(struct ipv6Monitor* monitor); - -void ipv6MonitorSetCallback(struct ipv6Monitor* monitor, - ipv6MonitorCallback callback); -void ipv6MonitorRunAsync(struct ipv6Monitor* monitor); -void ipv6MonitorStop(struct ipv6Monitor* monitor); - -#ifdef __cplusplus -} // extern "C" -#endif - - diff --git a/radio/ril/misc.c b/radio/ril/misc.c deleted file mode 100644 index c0e9b6ef..00000000 --- a/radio/ril/misc.c +++ /dev/null @@ -1,40 +0,0 @@ -/* //device/system/reference-ril/misc.c -** -** Copyright 2006, 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. -*/ -#include <sys/system_properties.h> - -#include "misc.h" -/** returns 1 if line starts with prefix, 0 if it does not */ -int strStartsWith(const char *line, const char *prefix) -{ - for ( ; *line != '\0' && *prefix != '\0' ; line++, prefix++) { - if (*line != *prefix) { - return 0; - } - } - - return *prefix == '\0'; -} - -// Returns true iff running this process in an emulator VM -bool isInEmulator(void) { - static int inQemu = -1; - if (inQemu < 0) { - char propValue[PROP_VALUE_MAX]; - inQemu = (__system_property_get("ro.kernel.qemu", propValue) != 0); - } - return inQemu == 1; -} diff --git a/radio/ril/reference-ril.c b/radio/ril/reference-ril.c deleted file mode 100644 index 41f7315a..00000000 --- a/radio/ril/reference-ril.c +++ /dev/null @@ -1,4289 +0,0 @@ -/* //device/system/reference-ril/reference-ril.c -** -** Copyright 2006, 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_TAG "RIL" - -#include <telephony/ril_cdma_sms.h> -#include <telephony/librilutils.h> -#include <stdio.h> -#include <assert.h> -#include <string.h> -#include <errno.h> -#include <unistd.h> -#include <sys/cdefs.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <inttypes.h> -#include <fcntl.h> -#include <pthread.h> -#include <alloca.h> -#include "atchannel.h" -#include "at_tok.h" -#include "misc.h" -#include <getopt.h> -#include <sys/socket.h> -#include <cutils/properties.h> -#include <cutils/sockets.h> -#include <termios.h> -#include <qemud.h> -#include <sys/wait.h> -#include <stdbool.h> -#include <net/if.h> -#include <arpa/inet.h> -#include <netinet/in.h> - -#include "if_monitor.h" -#include "ipv6_monitor.h" -#include "ril.h" - -#define EMULATOR_DUMMY_SIM_CHANNEL_NAME "A00000015144414300" -#include <utils/Log.h> - -#define MAX(x, y) ({\ - __typeof__(x) _x = (x); \ - __typeof__(y) _y = (y); \ - _x > _y ? _x : _y; }) - -static void *noopRemoveWarning( void *a ) { return a; } -#define RIL_UNUSED_PARM(a) noopRemoveWarning((void *)&(a)); - -#define MAX_AT_RESPONSE 0x1000 - -/* pathname returned from RIL_REQUEST_SETUP_DATA_CALL / RIL_REQUEST_SETUP_DEFAULT_PDP */ -// This is used if Wifi is not supported, plain old eth0 -#define PPP_TTY_PATH_ETH0 "eth0" -// This is used if Wifi is supported to separate radio and wifi interface -#define PPP_TTY_PATH_RADIO0 "radio0" - -// This is the IP address to provide for radio0 when WiFi is enabled -// When WiFi is not enabled the RIL should provide the address given by -// the modem. -#define RADIO0_IPV4_ADDRESS "192.168.200.2/24" - -// Default MTU value -#define DEFAULT_MTU 1500 - -#ifdef USE_TI_COMMANDS - -// Enable a workaround -// 1) Make incoming call, do not answer -// 2) Hangup remote end -// Expected: call should disappear from CLCC line -// Actual: Call shows as "ACTIVE" before disappearing -#define WORKAROUND_ERRONEOUS_ANSWER 1 - -// Some varients of the TI stack do not support the +CGEV unsolicited -// response. However, they seem to send an unsolicited +CME ERROR: 150 -#define WORKAROUND_FAKE_CGEV 1 -#endif - -/* Modem Technology bits */ -#define MDM_GSM 0x01 -#define MDM_WCDMA 0x02 -#define MDM_CDMA 0x04 -#define MDM_EVDO 0x08 -#define MDM_LTE 0x10 - -typedef struct { - int supportedTechs; // Bitmask of supported Modem Technology bits - int currentTech; // Technology the modem is currently using (in the format used by modem) - int isMultimode; - - // Preferred mode bitmask. This is actually 4 byte-sized bitmasks with different priority values, - // in which the byte number from LSB to MSB give the priority. - // - // |MSB| | |LSB - // value: |00 |00 |00 |00 - // byte #: |3 |2 |1 |0 - // - // Higher byte order give higher priority. Thus, a value of 0x0000000f represents - // a preferred mode of GSM, WCDMA, CDMA, and EvDo in which all are equally preferrable, whereas - // 0x00000201 represents a mode with GSM and WCDMA, in which WCDMA is preferred over GSM - int32_t preferredNetworkMode; - int subscription_source; - -} ModemInfo; - -static ModemInfo *sMdmInfo; -// TECH returns the current technology in the format used by the modem. -// It can be used as an l-value -#define TECH(mdminfo) ((mdminfo)->currentTech) -// TECH_BIT returns the bitmask equivalent of the current tech -#define TECH_BIT(mdminfo) (1 << ((mdminfo)->currentTech)) -#define IS_MULTIMODE(mdminfo) ((mdminfo)->isMultimode) -#define TECH_SUPPORTED(mdminfo, tech) ((mdminfo)->supportedTechs & (tech)) -#define PREFERRED_NETWORK(mdminfo) ((mdminfo)->preferredNetworkMode) -// CDMA Subscription Source -#define SSOURCE(mdminfo) ((mdminfo)->subscription_source) - -static int net2modem[] = { - MDM_GSM | MDM_WCDMA, // 0 - GSM / WCDMA Pref - MDM_GSM, // 1 - GSM only - MDM_WCDMA, // 2 - WCDMA only - MDM_GSM | MDM_WCDMA, // 3 - GSM / WCDMA Auto - MDM_CDMA | MDM_EVDO, // 4 - CDMA / EvDo Auto - MDM_CDMA, // 5 - CDMA only - MDM_EVDO, // 6 - EvDo only - MDM_GSM | MDM_WCDMA | MDM_CDMA | MDM_EVDO, // 7 - GSM/WCDMA, CDMA, EvDo - MDM_LTE | MDM_CDMA | MDM_EVDO, // 8 - LTE, CDMA and EvDo - MDM_LTE | MDM_GSM | MDM_WCDMA, // 9 - LTE, GSM/WCDMA - MDM_LTE | MDM_CDMA | MDM_EVDO | MDM_GSM | MDM_WCDMA, // 10 - LTE, CDMA, EvDo, GSM/WCDMA - MDM_LTE, // 11 - LTE only -}; - -static int32_t net2pmask[] = { - MDM_GSM | (MDM_WCDMA << 8), // 0 - GSM / WCDMA Pref - MDM_GSM, // 1 - GSM only - MDM_WCDMA, // 2 - WCDMA only - MDM_GSM | MDM_WCDMA, // 3 - GSM / WCDMA Auto - MDM_CDMA | MDM_EVDO, // 4 - CDMA / EvDo Auto - MDM_CDMA, // 5 - CDMA only - MDM_EVDO, // 6 - EvDo only - MDM_GSM | MDM_WCDMA | MDM_CDMA | MDM_EVDO, // 7 - GSM/WCDMA, CDMA, EvDo - MDM_LTE | MDM_CDMA | MDM_EVDO, // 8 - LTE, CDMA and EvDo - MDM_LTE | MDM_GSM | MDM_WCDMA, // 9 - LTE, GSM/WCDMA - MDM_LTE | MDM_CDMA | MDM_EVDO | MDM_GSM | MDM_WCDMA, // 10 - LTE, CDMA, EvDo, GSM/WCDMA - MDM_LTE, // 11 - LTE only -}; - -static int is3gpp2(int radioTech) { - switch (radioTech) { - case RADIO_TECH_IS95A: - case RADIO_TECH_IS95B: - case RADIO_TECH_1xRTT: - case RADIO_TECH_EVDO_0: - case RADIO_TECH_EVDO_A: - case RADIO_TECH_EVDO_B: - case RADIO_TECH_EHRPD: - return 1; - default: - return 0; - } -} - -typedef enum { - SIM_ABSENT = 0, - SIM_NOT_READY = 1, - SIM_READY = 2, - SIM_PIN = 3, - SIM_PUK = 4, - SIM_NETWORK_PERSONALIZATION = 5, - SIM_RESTRICTED = 6, - - RUIM_ABSENT = 7, - RUIM_NOT_READY = 8, - RUIM_READY = 9, - RUIM_PIN = 10, - RUIM_PUK = 11, - RUIM_NETWORK_PERSONALIZATION = 12, - RUIM_RESTRICTED = 13, - - ISIM_ABSENT = 14, - ISIM_NOT_READY = 15, - ISIM_READY = 16, - ISIM_PIN = 17, - ISIM_PUK = 18, - ISIM_NETWORK_PERSONALIZATION = 19, - ISIM_RESTRICTED = 20 - -} SIM_Status; - -static void onRequest (int request, void *data, size_t datalen, RIL_Token t); -static RIL_RadioState currentState(); -static int onSupports (int requestCode); -static void onCancel (RIL_Token t); -static const char *getVersion(); -static int isRadioOn(); -static SIM_Status getSIMStatus(); -static int getCardStatus(RIL_CardStatus_v6 **pp_card_status); -static void freeCardStatus(RIL_CardStatus_v6 *p_card_status); -static void onDataCallListChanged(void *param); - -extern const char * requestToString(int request); - -/*** Static Variables ***/ -static const RIL_RadioFunctions s_callbacks = { - RIL_VERSION, - onRequest, - currentState, - onSupports, - onCancel, - getVersion -}; - -#ifdef RIL_SHLIB -static const struct RIL_Env *s_rilenv; - -#define RIL_onRequestComplete(t, e, response, responselen) s_rilenv->OnRequestComplete(t,e, response, responselen) -#define RIL_onUnsolicitedResponse(a,b,c) s_rilenv->OnUnsolicitedResponse(a,b,c) -#define RIL_requestTimedCallback(a,b,c) s_rilenv->RequestTimedCallback(a,b,c) -#endif - -static RIL_RadioState sState = RADIO_STATE_UNAVAILABLE; - -static int s_sim_update_started = 0; - -static pthread_mutex_t s_state_mutex = PTHREAD_MUTEX_INITIALIZER; -static pthread_cond_t s_state_cond = PTHREAD_COND_INITIALIZER; - -static int s_port = -1; -static const char * s_device_path = NULL; -static int s_device_socket = 0; - -/* trigger change to this with s_state_cond */ -static int s_closed = 0; - -static int sFD; /* file desc of AT channel */ -static char sATBuffer[MAX_AT_RESPONSE+1]; -static char *sATBufferCur = NULL; - -static const struct timeval TIMEVAL_SIMPOLL = {1,0}; -static const struct timeval TIMEVAL_CALLSTATEPOLL = {0,500000}; -static const struct timeval TIMEVAL_0 = {0,0}; - -static int s_ims_registered = 0; // 0==unregistered -static int s_ims_services = 1; // & 0x1 == sms over ims supported -static int s_ims_format = 1; // FORMAT_3GPP(1) vs FORMAT_3GPP2(2); -static int s_ims_cause_retry = 0; // 1==causes sms over ims to temp fail -static int s_ims_cause_perm_failure = 0; // 1==causes sms over ims to permanent fail -static int s_ims_gsm_retry = 0; // 1==causes sms over gsm to temp fail -static int s_ims_gsm_fail = 0; // 1==causes sms over gsm to permanent fail - -#ifdef WORKAROUND_ERRONEOUS_ANSWER -// Max number of times we'll try to repoll when we think -// we have a AT+CLCC race condition -#define REPOLL_CALLS_COUNT_MAX 4 - -// Line index that was incoming or waiting at last poll, or -1 for none -static int s_incomingOrWaitingLine = -1; -// Number of times we've asked for a repoll of AT+CLCC -static int s_repollCallsCount = 0; -// Should we expect a call to be answered in the next CLCC? -static int s_expectAnswer = 0; -#endif /* WORKAROUND_ERRONEOUS_ANSWER */ - - -static int s_cell_info_rate_ms = INT_MAX; -static int s_mcc = 0; -static int s_mnc = 0; -static int s_lac = 0; -static int s_cid = 0; - -// A string containing all IP addresses of the radio interface -static char s_if_addresses[8192]; -// A string containing the IPv6 gateway of the radio interface -static char s_ipv6_gateway[INET6_ADDRSTRLEN]; -// A string containing the IPv6 DNS servers of the radio interface -static char s_ipv6_dns[8192]; -static pthread_mutex_t s_addresses_mutex = PTHREAD_MUTEX_INITIALIZER; - -static void pollSIMState (void *param); -static void setRadioState(RIL_RadioState newState); -static void setRadioTechnology(ModemInfo *mdm, int newtech); -static int query_ctec(ModemInfo *mdm, int *current, int32_t *preferred); -static int parse_technology_response(const char *response, int *current, int32_t *preferred); -static int techFromModemType(int mdmtype); - -static int clccStateToRILState(int state, RIL_CallState *p_state) - -{ - switch(state) { - case 0: *p_state = RIL_CALL_ACTIVE; return 0; - case 1: *p_state = RIL_CALL_HOLDING; return 0; - case 2: *p_state = RIL_CALL_DIALING; return 0; - case 3: *p_state = RIL_CALL_ALERTING; return 0; - case 4: *p_state = RIL_CALL_INCOMING; return 0; - case 5: *p_state = RIL_CALL_WAITING; return 0; - default: return -1; - } -} - -/** - * Note: directly modified line and has *p_call point directly into - * modified line - */ -static int callFromCLCCLine(char *line, RIL_Call *p_call) -{ - //+CLCC: 1,0,2,0,0,\"+18005551212\",145 - // index,isMT,state,mode,isMpty(,number,TOA)? - - int err; - int state; - int mode; - - err = at_tok_start(&line); - if (err < 0) goto error; - - err = at_tok_nextint(&line, &(p_call->index)); - if (err < 0) goto error; - - err = at_tok_nextbool(&line, &(p_call->isMT)); - if (err < 0) goto error; - - err = at_tok_nextint(&line, &state); - if (err < 0) goto error; - - err = clccStateToRILState(state, &(p_call->state)); - if (err < 0) goto error; - - err = at_tok_nextint(&line, &mode); - if (err < 0) goto error; - - p_call->isVoice = (mode == 0); - - err = at_tok_nextbool(&line, &(p_call->isMpty)); - if (err < 0) goto error; - - if (at_tok_hasmore(&line)) { - err = at_tok_nextstr(&line, &(p_call->number)); - - /* tolerate null here */ - if (err < 0) return 0; - - // Some lame implementations return strings - // like "NOT AVAILABLE" in the CLCC line - if (p_call->number != NULL - && 0 == strspn(p_call->number, "+0123456789") - ) { - p_call->number = NULL; - } - - err = at_tok_nextint(&line, &p_call->toa); - if (err < 0) goto error; - } - - p_call->uusInfo = NULL; - - return 0; - -error: - RLOGE("invalid CLCC line\n"); - return -1; -} - -static int parseSimResponseLine(char* line, RIL_SIM_IO_Response* response) { - int err; - - err = at_tok_start(&line); - if (err < 0) return err; - err = at_tok_nextint(&line, &response->sw1); - if (err < 0) return err; - err = at_tok_nextint(&line, &response->sw2); - if (err < 0) return err; - - if (at_tok_hasmore(&line)) { - err = at_tok_nextstr(&line, &response->simResponse); - if (err < 0) return err; - } - return 0; -} - -enum InterfaceState { - kInterfaceUp, - kInterfaceDown, -}; - -static RIL_Errno setInterfaceState(const char* interfaceName, - enum InterfaceState state) { - struct ifreq request; - int status = 0; - int sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); - if (sock == -1) { - RLOGE("Failed to open interface socket: %s (%d)", - strerror(errno), errno); - return RIL_E_GENERIC_FAILURE; - } - - memset(&request, 0, sizeof(request)); - strncpy(request.ifr_name, interfaceName, sizeof(request.ifr_name)); - request.ifr_name[sizeof(request.ifr_name) - 1] = '\0'; - status = ioctl(sock, SIOCGIFFLAGS, &request); - if (status != 0) { - RLOGE("Failed to get interface flags for %s: %s (%d)", - interfaceName, strerror(errno), errno); - close(sock); - return RIL_E_RADIO_NOT_AVAILABLE; - } - - bool isUp = (request.ifr_flags & IFF_UP); - if ((state == kInterfaceUp && isUp) || (state == kInterfaceDown && !isUp)) { - // Interface already in desired state - close(sock); - return RIL_E_SUCCESS; - } - - // Simply toggle the flag since we know it's the opposite of what we want - request.ifr_flags ^= IFF_UP; - - status = ioctl(sock, SIOCSIFFLAGS, &request); - if (status != 0) { - RLOGE("Failed to set interface flags for %s: %s (%d)", - interfaceName, strerror(errno), errno); - close(sock); - return RIL_E_GENERIC_FAILURE; - } - - close(sock); - return RIL_E_SUCCESS; -} - -static void parseAuthResponse(char* line, RIL_SIM_IO_Response* response) { - // example string +CSIM=number, "<base64string>9000" - // get the status first - int len = strlen(line); - char* first_double_quote = strchr(line, '"'); - if (first_double_quote == NULL) { - RLOGE("%s bad response %s", __func__, line); - return; - } - char* data_ptr = first_double_quote + 1; - sscanf(line + (len -5), "%2x%2x", &(response->sw1), &(response->sw2)); - line[len-5] = '\0'; - response->simResponse = strdup(data_ptr); -} - -/** do post-AT+CFUN=1 initialization */ -static void onRadioPowerOn() -{ -#ifdef USE_TI_COMMANDS - /* Must be after CFUN=1 */ - /* TI specific -- notifications for CPHS things such */ - /* as CPHS message waiting indicator */ - - at_send_command("AT%CPHS=1", NULL); - - /* TI specific -- enable NITZ unsol notifs */ - at_send_command("AT%CTZV=1", NULL); -#endif - - /* Golfish specific -- enable physical channel config unsol notifs - for 5g support - */ - at_send_command("AT%CGFPCCFG=1", NULL); - pollSIMState(NULL); -} - -/** do post- SIM ready initialization */ -static void onSIMReady() -{ - at_send_command_singleline("AT+CSMS=1", "+CSMS:", NULL); - /* - * Always send SMS messages directly to the TE - * - * mode = 1 // discard when link is reserved (link should never be - * reserved) - * mt = 2 // most messages routed to TE - * bm = 2 // new cell BM's routed to TE - * ds = 1 // Status reports routed to TE - * bfr = 1 // flush buffer - */ - at_send_command("AT+CNMI=1,2,2,1,1", NULL); -} - -static void requestRadioPower(void *data, size_t datalen __unused, RIL_Token t) -{ - int onOff; - - int err; - ATResponse *p_response = NULL; - - assert (datalen >= sizeof(int *)); - onOff = ((int *)data)[0]; - - if (onOff == 0 && sState != RADIO_STATE_OFF) { - err = at_send_command("AT+CFUN=0", &p_response); - if (err < 0 || p_response->success == 0) goto error; - setRadioState(RADIO_STATE_OFF); - } else if (onOff > 0 && sState == RADIO_STATE_OFF) { - err = at_send_command("AT+CFUN=1", &p_response); - if (err < 0|| p_response->success == 0) { - // Some stacks return an error when there is no SIM, - // but they really turn the RF portion on - // So, if we get an error, let's check to see if it - // turned on anyway - - if (isRadioOn() != 1) { - goto error; - } - } - setRadioState(RADIO_STATE_ON); - } - - at_response_free(p_response); - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - return; -error: - at_response_free(p_response); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static void requestShutdown(RIL_Token t) -{ - int onOff; - - int err; - ATResponse *p_response = NULL; - - if (sState != RADIO_STATE_OFF) { - err = at_send_command("AT+CFUN=0", &p_response); - setRadioState(RADIO_STATE_UNAVAILABLE); - } - - at_response_free(p_response); - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - return; -} - -static void requestOrSendDataCallList(RIL_Token *t); - -static void onDataCallListChanged(void *param __unused) -{ - requestOrSendDataCallList(NULL); -} - -static void requestDataCallList(void *data __unused, size_t datalen __unused, RIL_Token t) -{ - requestOrSendDataCallList(&t); -} - -// Hang up, reject, conference, call waiting -static void requestCallSelection( - void *data __unused, size_t datalen __unused, RIL_Token t, int request) -{ - // 3GPP 22.030 6.5.5 - static char hangupWaiting[] = "AT+CHLD=0"; - static char hangupForeground[] = "AT+CHLD=1"; - static char switchWaiting[] = "AT+CHLD=2"; - static char conference[] = "AT+CHLD=3"; - static char reject[] = "ATH"; - - char* atCommand; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_RADIO_NOT_AVAILABLE, NULL, 0); - return; - } - - switch(request) { - case RIL_REQUEST_HANGUP_WAITING_OR_BACKGROUND: - // "Releases all held calls or sets User Determined User Busy - // (UDUB) for a waiting call." - atCommand = hangupWaiting; - break; - case RIL_REQUEST_HANGUP_FOREGROUND_RESUME_BACKGROUND: - // "Releases all active calls (if any exist) and accepts - // the other (held or waiting) call." - atCommand = hangupForeground; - break; - case RIL_REQUEST_SWITCH_WAITING_OR_HOLDING_AND_ACTIVE: - // "Places all active calls (if any exist) on hold and accepts - // the other (held or waiting) call." - atCommand = switchWaiting; -#ifdef WORKAROUND_ERRONEOUS_ANSWER - s_expectAnswer = 1; -#endif /* WORKAROUND_ERRONEOUS_ANSWER */ - break; - case RIL_REQUEST_CONFERENCE: - // "Adds a held call to the conversation" - atCommand = conference; - break; - case RIL_REQUEST_UDUB: - // User determined user busy (reject) - atCommand = reject; - break; - default: - assert(0); - } - at_send_command(atCommand, NULL); - // Success or failure is ignored by the upper layer here. - // It will call GET_CURRENT_CALLS and determine success that way. - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); -} - -static bool hasWifiCapability() -{ - char propValue[PROP_VALUE_MAX]; - return property_get("ro.kernel.qemu.wifi", propValue, "") > 0 && - strcmp("1", propValue) == 0; -} - -static const char* getRadioInterfaceName(bool hasWifi) -{ - return hasWifi ? PPP_TTY_PATH_RADIO0 : PPP_TTY_PATH_ETH0; -} - -static void requestOrSendDataCallList(RIL_Token *t) -{ - ATResponse *p_response; - ATLine *p_cur; - int err; - int n = 0; - char *out; - char propValue[PROP_VALUE_MAX]; - bool hasWifi = hasWifiCapability(); - const char* radioInterfaceName = getRadioInterfaceName(hasWifi); - char ipv6Gateway[INET6_ADDRSTRLEN]; - char ipv6Dns[8192]; - - err = at_send_command_multiline ("AT+CGACT?", "+CGACT:", &p_response); - if (err != 0 || p_response->success == 0) { - if (t != NULL) - RIL_onRequestComplete(*t, RIL_E_GENERIC_FAILURE, NULL, 0); - else - RIL_onUnsolicitedResponse(RIL_UNSOL_DATA_CALL_LIST_CHANGED, - NULL, 0); - return; - } - - for (p_cur = p_response->p_intermediates; p_cur != NULL; - p_cur = p_cur->p_next) - n++; - - RIL_Data_Call_Response_v11 *responses = - alloca(n * sizeof(RIL_Data_Call_Response_v11)); - - int i; - for (i = 0; i < n; i++) { - responses[i].status = -1; - responses[i].suggestedRetryTime = -1; - responses[i].cid = -1; - responses[i].active = -1; - responses[i].type = ""; - responses[i].ifname = ""; - responses[i].addresses = ""; - responses[i].dnses = ""; - responses[i].gateways = ""; - responses[i].pcscf = ""; - responses[i].mtu = 0; - } - - RIL_Data_Call_Response_v11 *response = responses; - for (p_cur = p_response->p_intermediates; p_cur != NULL; - p_cur = p_cur->p_next) { - char *line = p_cur->line; - - err = at_tok_start(&line); - if (err < 0) - goto error; - - err = at_tok_nextint(&line, &response->cid); - if (err < 0) - goto error; - - err = at_tok_nextint(&line, &response->active); - if (err < 0) - goto error; - - response++; - } - - at_response_free(p_response); - - err = at_send_command_multiline ("AT+CGDCONT?", "+CGDCONT:", &p_response); - if (err != 0 || p_response->success == 0) { - if (t != NULL) - RIL_onRequestComplete(*t, RIL_E_GENERIC_FAILURE, NULL, 0); - else - RIL_onUnsolicitedResponse(RIL_UNSOL_DATA_CALL_LIST_CHANGED, - NULL, 0); - return; - } - - for (p_cur = p_response->p_intermediates; p_cur != NULL; - p_cur = p_cur->p_next) { - char *line = p_cur->line; - int cid; - - err = at_tok_start(&line); - if (err < 0) - goto error; - - err = at_tok_nextint(&line, &cid); - if (err < 0) - goto error; - - for (i = 0; i < n; i++) { - if (responses[i].cid == cid) - break; - } - - if (i >= n) { - /* details for a context we didn't hear about in the last request */ - continue; - } - - // Assume no error - responses[i].status = 0; - - // type - err = at_tok_nextstr(&line, &out); - if (err < 0) - goto error; - - int type_size = strlen(out) + 1; - responses[i].type = alloca(type_size); - strlcpy(responses[i].type, out, type_size); - - // APN ignored for v5 - err = at_tok_nextstr(&line, &out); - if (err < 0) - goto error; - - int ifname_size = strlen(radioInterfaceName) + 1; - responses[i].ifname = alloca(ifname_size); - strlcpy(responses[i].ifname, radioInterfaceName, ifname_size); - - // The next token is the IPv4 address provided by the emulator, only use - // it if WiFi is not enabled. When WiFi is enabled the network setup is - // specific to the system image and the emulator only provides the - // IP address for the external interface in the router namespace. - err = at_tok_nextstr(&line, &out); - if (err < 0) - goto error; - - pthread_mutex_lock(&s_addresses_mutex); - - // Extra space for null terminator - int addresses_size = MAX(strlen(out), strlen(s_if_addresses)) + 1; - responses[i].addresses = alloca(addresses_size); - if (*s_if_addresses) { - // Interface addresses exist, use them. - strlcpy(responses[i].addresses, s_if_addresses, addresses_size); - } else { - // No known interface address, use whatever the modem provided - strlcpy(responses[i].addresses, out, addresses_size); - } - - strlcpy(ipv6Gateway, s_ipv6_gateway, sizeof(ipv6Gateway)); - strlcpy(ipv6Dns, s_ipv6_dns, sizeof(ipv6Dns)); - - pthread_mutex_unlock(&s_addresses_mutex); - - if (isInEmulator()) { - /* We are in the emulator - the dns servers are listed - * by the following system properties, setup in - * /system/etc/init.goldfish.sh: - * - net.eth0.dns1 - * - net.eth0.dns2 - * - net.eth0.dns3 - * - net.eth0.dns4 - */ - const int dnslist_sz = 256; - char* dnslist = alloca(dnslist_sz); - const char* separator = ""; - int nn; - char propName[PROP_NAME_MAX]; - char propValue[PROP_VALUE_MAX]; - char* gateways = NULL; - size_t gatewaysSize = 0; - - dnslist[0] = 0; - for (nn = 1; nn <= 4; nn++) { - /* Probe net.eth0.dns<n> */ - - snprintf(propName, sizeof propName, "net.%s.dns%d", - radioInterfaceName, nn); - - /* Ignore if undefined */ - if (property_get(propName, propValue, "") <= 0) { - continue; - } - - /* Append the DNS IP address */ - strlcat(dnslist, separator, dnslist_sz); - strlcat(dnslist, propValue, dnslist_sz); - separator = " "; - } - for (nn = 1; nn <= 4; ++nn) { - /* Probe net.eth0.ipv6dns<n> for IPv6 DNS servers */ - snprintf(propName, sizeof propName, "net.%s.ipv6dns%d", - radioInterfaceName, nn); - /* Ignore if undefined */ - if (property_get(propName, propValue, "") <= 0) { - continue; - } - strlcat(dnslist, separator, dnslist_sz); - strlcat(dnslist, propValue, dnslist_sz); - separator = " "; - } - - responses[i].dnses = dnslist; - - /* There is only one gateway in the emulator. */ - snprintf(propName, sizeof propName, "net.%s.gw", - radioInterfaceName); - - gatewaysSize = strlen(ipv6Gateway); - if (property_get(propName, propValue, "") > 0) { - if (gatewaysSize > 0) { - // Room for a separating space - ++gatewaysSize; - } - gatewaysSize += strlen(propValue); - } - if (gatewaysSize > 0) { - // Room for a terminating null byte - ++gatewaysSize; - responses[i].gateways = alloca(gatewaysSize); - if (ipv6Gateway[0]) { - strlcpy(responses[i].gateways, ipv6Gateway, gatewaysSize); - } - if (propValue[0]) { - if (responses[i].gateways[0] != '\0') { - strlcat(responses[i].gateways, " ", gatewaysSize); - } - strlcat(responses[i].gateways, propValue, gatewaysSize); - } - } else { - responses[i].gateways = ""; - } - responses[i].mtu = DEFAULT_MTU; - } - else { - /* I don't know where we are, so use the public Google DNS - * servers by default and no gateway. - */ - responses[i].dnses = "8.8.8.8 8.8.4.4"; - responses[i].gateways = ""; - } - } - - at_response_free(p_response); - - if (t != NULL) { - RIL_onRequestComplete(*t, RIL_E_SUCCESS, responses, - n * sizeof(RIL_Data_Call_Response_v11)); - } else { - RIL_onUnsolicitedResponse(RIL_UNSOL_DATA_CALL_LIST_CHANGED, - responses, - n * sizeof(RIL_Data_Call_Response_v11)); - } - - return; - -error: - if (t != NULL) - RIL_onRequestComplete(*t, RIL_E_GENERIC_FAILURE, NULL, 0); - else - RIL_onUnsolicitedResponse(RIL_UNSOL_DATA_CALL_LIST_CHANGED, - NULL, 0); - - at_response_free(p_response); -} - -static void setNetworkSelectionAutomatic(RIL_Token t) -{ - int err; - ATResponse *p_response = NULL; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_RADIO_NOT_AVAILABLE, NULL, 0); - return; - } - - err = at_send_command("AT+COPS=0", &p_response); - - if (err < 0 || p_response == NULL || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } - - at_response_free(p_response); -} - -static void requestQueryNetworkSelectionMode( - void *data __unused, size_t datalen __unused, RIL_Token t) -{ - int err; - ATResponse *p_response = NULL; - int response = 0; - char *line; - - err = at_send_command_singleline("AT+COPS?", "+COPS:", &p_response); - - if (err < 0 || p_response->success == 0) { - goto error; - } - - line = p_response->p_intermediates->line; - - err = at_tok_start(&line); - - if (err < 0) { - goto error; - } - - err = at_tok_nextint(&line, &response); - - if (err < 0) { - goto error; - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &response, sizeof(int)); - at_response_free(p_response); - return; -error: - at_response_free(p_response); - RLOGE("requestQueryNetworkSelectionMode must never return error when radio is on"); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static void sendCallStateChanged(void *param __unused) -{ - RIL_onUnsolicitedResponse ( - RIL_UNSOL_RESPONSE_CALL_STATE_CHANGED, - NULL, 0); -} - -static void requestGetCurrentCalls(void *data __unused, size_t datalen __unused, RIL_Token t) -{ - int err; - ATResponse *p_response; - ATLine *p_cur; - int countCalls; - int countValidCalls; - RIL_Call *p_calls; - RIL_Call **pp_calls; - int i; - int needRepoll = 0; - -#ifdef WORKAROUND_ERRONEOUS_ANSWER - int prevIncomingOrWaitingLine; - - prevIncomingOrWaitingLine = s_incomingOrWaitingLine; - s_incomingOrWaitingLine = -1; -#endif /*WORKAROUND_ERRONEOUS_ANSWER*/ - - err = at_send_command_multiline ("AT+CLCC", "+CLCC:", &p_response); - - if (err != 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - - /* count the calls */ - for (countCalls = 0, p_cur = p_response->p_intermediates - ; p_cur != NULL - ; p_cur = p_cur->p_next - ) { - countCalls++; - } - - /* yes, there's an array of pointers and then an array of structures */ - - pp_calls = (RIL_Call **)alloca(countCalls * sizeof(RIL_Call *)); - p_calls = (RIL_Call *)alloca(countCalls * sizeof(RIL_Call)); - memset (p_calls, 0, countCalls * sizeof(RIL_Call)); - - /* init the pointer array */ - for(i = 0; i < countCalls ; i++) { - pp_calls[i] = &(p_calls[i]); - } - - for (countValidCalls = 0, p_cur = p_response->p_intermediates - ; p_cur != NULL - ; p_cur = p_cur->p_next - ) { - err = callFromCLCCLine(p_cur->line, p_calls + countValidCalls); - - if (err != 0) { - continue; - } - -#ifdef WORKAROUND_ERRONEOUS_ANSWER - if (p_calls[countValidCalls].state == RIL_CALL_INCOMING - || p_calls[countValidCalls].state == RIL_CALL_WAITING - ) { - s_incomingOrWaitingLine = p_calls[countValidCalls].index; - } -#endif /*WORKAROUND_ERRONEOUS_ANSWER*/ - - if (p_calls[countValidCalls].state != RIL_CALL_ACTIVE - && p_calls[countValidCalls].state != RIL_CALL_HOLDING - ) { - needRepoll = 1; - } - - countValidCalls++; - } - -#ifdef WORKAROUND_ERRONEOUS_ANSWER - // Basically: - // A call was incoming or waiting - // Now it's marked as active - // But we never answered it - // - // This is probably a bug, and the call will probably - // disappear from the call list in the next poll - if (prevIncomingOrWaitingLine >= 0 - && s_incomingOrWaitingLine < 0 - && s_expectAnswer == 0 - ) { - for (i = 0; i < countValidCalls ; i++) { - - if (p_calls[i].index == prevIncomingOrWaitingLine - && p_calls[i].state == RIL_CALL_ACTIVE - && s_repollCallsCount < REPOLL_CALLS_COUNT_MAX - ) { - RLOGI( - "Hit WORKAROUND_ERRONOUS_ANSWER case." - " Repoll count: %d\n", s_repollCallsCount); - s_repollCallsCount++; - goto error; - } - } - } - - s_expectAnswer = 0; - s_repollCallsCount = 0; -#endif /*WORKAROUND_ERRONEOUS_ANSWER*/ - - RIL_onRequestComplete(t, RIL_E_SUCCESS, pp_calls, - countValidCalls * sizeof (RIL_Call *)); - - at_response_free(p_response); - -#ifdef POLL_CALL_STATE - if (countValidCalls) { // We don't seem to get a "NO CARRIER" message from - // smd, so we're forced to poll until the call ends. -#else - if (needRepoll) { -#endif - RIL_requestTimedCallback (sendCallStateChanged, NULL, &TIMEVAL_CALLSTATEPOLL); - } - - return; -#ifdef WORKAROUND_ERRONEOUS_ANSWER -error: - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); -#endif -} - -static void requestDial(void *data, size_t datalen __unused, RIL_Token t) -{ - RIL_Dial *p_dial; - char *cmd; - const char *clir; - int ret; - - p_dial = (RIL_Dial *)data; - - switch (p_dial->clir) { - case 1: clir = "I"; break; /*invocation*/ - case 2: clir = "i"; break; /*suppression*/ - default: - case 0: clir = ""; break; /*subscription default*/ - } - - asprintf(&cmd, "ATD%s%s;", p_dial->address, clir); - - ret = at_send_command(cmd, NULL); - - free(cmd); - - /* success or failure is ignored by the upper layer here. - it will call GET_CURRENT_CALLS and determine success that way */ - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); -} - -static void requestWriteSmsToSim(void *data, size_t datalen __unused, RIL_Token t) -{ - RIL_SMS_WriteArgs *p_args; - char *cmd; - int length; - int err; - ATResponse *p_response = NULL; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_SIM_ABSENT, NULL, 0); - return; - } - - p_args = (RIL_SMS_WriteArgs *)data; - - length = strlen(p_args->pdu)/2; - asprintf(&cmd, "AT+CMGW=%d,%d", length, p_args->status); - - err = at_send_command_sms(cmd, p_args->pdu, "+CMGW:", &p_response); - - if (err != 0 || p_response->success == 0) goto error; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - at_response_free(p_response); - - return; -error: - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); -} - -static void requestHangup(void *data, size_t datalen __unused, RIL_Token t) -{ - int *p_line; - - int ret; - char *cmd; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_MODEM_ERR, NULL, 0); - return; - } - p_line = (int *)data; - - // 3GPP 22.030 6.5.5 - // "Releases a specific active call X" - asprintf(&cmd, "AT+CHLD=1%d", p_line[0]); - - ret = at_send_command(cmd, NULL); - - free(cmd); - - /* success or failure is ignored by the upper layer here. - it will call GET_CURRENT_CALLS and determine success that way */ - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); -} - -static void requestSignalStrength(void *data __unused, size_t datalen __unused, RIL_Token t) -{ - ATResponse *p_response = NULL; - int err; - char *line; - int count = 0; - // Accept a response that is at least v6, and up to v10 - int minNumOfElements=sizeof(RIL_SignalStrength_v6)/sizeof(int); - int maxNumOfElements=sizeof(RIL_SignalStrength_v10)/sizeof(int); - int response[maxNumOfElements]; - - memset(response, 0, sizeof(response)); - - err = at_send_command_singleline("AT+CSQ", "+CSQ:", &p_response); - - if (err < 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - goto error; - } - - line = p_response->p_intermediates->line; - - err = at_tok_start(&line); - if (err < 0) goto error; - - for (count = 0; count < maxNumOfElements; count++) { - err = at_tok_nextint(&line, &(response[count])); - if (err < 0 && count < minNumOfElements) goto error; - } - - // remove gsm/cdma/evdo,just keep LTE - int numSignalsToIgnore = sizeof(RIL_SignalStrength_v5)/sizeof(int); - for (int i=0; i < numSignalsToIgnore; ++i) { - response[i] = INT_MAX; - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, response, sizeof(response)); - - at_response_free(p_response); - return; - -error: - RLOGE("requestSignalStrength must never return an error when radio is on"); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); -} - -/** - * networkModePossible. Decides whether the network mode is appropriate for the - * specified modem - */ -static int networkModePossible(ModemInfo *mdm, int nm) -{ - if ((net2modem[nm] & mdm->supportedTechs) == net2modem[nm]) { - return 1; - } - return 0; -} -static void requestSetPreferredNetworkType( int request __unused, void *data, - size_t datalen __unused, RIL_Token t ) -{ - ATResponse *p_response = NULL; - char *cmd = NULL; - int value = *(int *)data; - int current, old; - int err; - int32_t preferred = net2pmask[value]; - - RLOGD("requestSetPreferredNetworkType: current: %x. New: %x", PREFERRED_NETWORK(sMdmInfo), preferred); - if (!networkModePossible(sMdmInfo, value)) { - RIL_onRequestComplete(t, RIL_E_MODE_NOT_SUPPORTED, NULL, 0); - return; - } - if (query_ctec(sMdmInfo, ¤t, NULL) < 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - old = PREFERRED_NETWORK(sMdmInfo); - RLOGD("old != preferred: %d", old != preferred); - if (old != preferred) { - asprintf(&cmd, "AT+CTEC=%d,\"%x\"", current, preferred); - RLOGD("Sending command: <%s>", cmd); - err = at_send_command_singleline(cmd, "+CTEC:", &p_response); - free(cmd); - if (err || !p_response->success) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - PREFERRED_NETWORK(sMdmInfo) = value; - if (!strstr( p_response->p_intermediates->line, "DONE") ) { - int current; - int res = parse_technology_response(p_response->p_intermediates->line, ¤t, NULL); - switch (res) { - case -1: // Error or unable to parse - break; - case 1: // Only able to parse current - case 0: // Both current and preferred were parsed - setRadioTechnology(sMdmInfo, current); - break; - } - } - } - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); -} - -static void requestGetPreferredNetworkType(int request __unused, void *data __unused, - size_t datalen __unused, RIL_Token t) -{ - int preferred; - unsigned i; - - switch ( query_ctec(sMdmInfo, NULL, &preferred) ) { - case -1: // Error or unable to parse - case 1: // Only able to parse current - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - break; - case 0: // Both current and preferred were parsed - for ( i = 0 ; i < sizeof(net2pmask) / sizeof(int32_t) ; i++ ) { - if (preferred == net2pmask[i]) { - RIL_onRequestComplete(t, RIL_E_SUCCESS, &i, sizeof(int)); - return; - } - } - RLOGE("Unknown preferred mode received from modem: %d", preferred); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - break; - } - -} - -static void requestCdmaPrlVersion(int request __unused, void *data __unused, - size_t datalen __unused, RIL_Token t) -{ - int err; - char * responseStr; - ATResponse *p_response = NULL; - const char *cmd; - char *line; - - err = at_send_command_singleline("AT+WPRL?", "+WPRL:", &p_response); - if (err < 0 || !p_response->success) goto error; - line = p_response->p_intermediates->line; - err = at_tok_start(&line); - if (err < 0) goto error; - err = at_tok_nextstr(&line, &responseStr); - if (err < 0 || !responseStr) goto error; - RIL_onRequestComplete(t, RIL_E_SUCCESS, responseStr, strlen(responseStr)); - at_response_free(p_response); - return; -error: - at_response_free(p_response); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static void requestCdmaBaseBandVersion(int request __unused, void *data __unused, - size_t datalen __unused, RIL_Token t) -{ - int err; - char * responseStr; - ATResponse *p_response = NULL; - const char *cmd; - const char *prefix; - char *line, *p; - int commas; - int skip; - int count = 4; - - // Fixed values. TODO: query modem - responseStr = strdup("1.0.0.0"); - RIL_onRequestComplete(t, RIL_E_SUCCESS, responseStr, sizeof(responseStr)); - free(responseStr); -} - -static void requestDeviceIdentity(int request __unused, void *data __unused, - size_t datalen __unused, RIL_Token t) -{ - int err; - int response[4]; - char * responseStr[4]; - ATResponse *p_response = NULL; - const char *cmd; - const char *prefix; - char *line, *p; - int commas; - int skip; - int count = 4; - - // Fixed values. TODO: Query modem - responseStr[0] = "----"; - responseStr[1] = "----"; - responseStr[2] = "77777777"; - responseStr[3] = ""; // default empty for non-CDMA - - err = at_send_command_numeric("AT+CGSN", &p_response); - if (err < 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } else { - if (TECH_BIT(sMdmInfo) == MDM_CDMA) { - responseStr[3] = p_response->p_intermediates->line; - } else { - responseStr[0] = p_response->p_intermediates->line; - } - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, responseStr, count*sizeof(char*)); - at_response_free(p_response); -} - -static void requestCdmaGetSubscriptionSource(int request __unused, void *data, - size_t datalen __unused, RIL_Token t) -{ - int err; - int *ss = (int *)data; - ATResponse *p_response = NULL; - char *cmd = NULL; - char *line = NULL; - int response; - - asprintf(&cmd, "AT+CCSS?"); - if (!cmd) goto error; - - err = at_send_command_singleline(cmd, "+CCSS:", &p_response); - if (err < 0 || !p_response->success) - goto error; - - line = p_response->p_intermediates->line; - err = at_tok_start(&line); - if (err < 0) goto error; - - err = at_tok_nextint(&line, &response); - free(cmd); - cmd = NULL; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &response, sizeof(response)); - - return; -error: - free(cmd); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static void requestCdmaSetSubscriptionSource(int request __unused, void *data, - size_t datalen, RIL_Token t) -{ - int err; - int *ss = (int *)data; - ATResponse *p_response = NULL; - char *cmd = NULL; - - if (!ss || !datalen) { - RLOGE("RIL_REQUEST_CDMA_SET_SUBSCRIPTION without data!"); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - asprintf(&cmd, "AT+CCSS=%d", ss[0]); - if (!cmd) goto error; - - err = at_send_command(cmd, &p_response); - if (err < 0 || !p_response->success) - goto error; - free(cmd); - cmd = NULL; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - - RIL_onUnsolicitedResponse(RIL_UNSOL_CDMA_SUBSCRIPTION_SOURCE_CHANGED, ss, sizeof(ss[0])); - - return; -error: - free(cmd); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static void requestCdmaSubscription(int request __unused, void *data __unused, - size_t datalen __unused, RIL_Token t) -{ - int err; - int response[5]; - char * responseStr[5]; - ATResponse *p_response = NULL; - const char *cmd; - const char *prefix; - char *line, *p; - int commas; - int skip; - int count = 5; - - // Fixed values. TODO: Query modem - responseStr[0] = "8587777777"; // MDN - responseStr[1] = "1"; // SID - responseStr[2] = "1"; // NID - responseStr[3] = "8587777777"; // MIN - responseStr[4] = "1"; // PRL Version - RIL_onRequestComplete(t, RIL_E_SUCCESS, responseStr, count*sizeof(char*)); -} - -static void requestCdmaGetRoamingPreference(int request __unused, void *data __unused, - size_t datalen __unused, RIL_Token t) -{ - int roaming_pref = -1; - ATResponse *p_response = NULL; - char *line; - int res; - - res = at_send_command_singleline("AT+WRMP?", "+WRMP:", &p_response); - if (res < 0 || !p_response->success) { - goto error; - } - line = p_response->p_intermediates->line; - - res = at_tok_start(&line); - if (res < 0) goto error; - - res = at_tok_nextint(&line, &roaming_pref); - if (res < 0) goto error; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &roaming_pref, sizeof(roaming_pref)); - return; -error: - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static void requestCdmaSetRoamingPreference(int request __unused, void *data, - size_t datalen __unused, RIL_Token t) -{ - int *pref = (int *)data; - ATResponse *p_response = NULL; - char *line; - int res; - char *cmd = NULL; - - asprintf(&cmd, "AT+WRMP=%d", *pref); - if (cmd == NULL) goto error; - - res = at_send_command(cmd, &p_response); - if (res < 0 || !p_response->success) - goto error; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - free(cmd); - return; -error: - free(cmd); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static int parseRegistrationState(char *str, int *type, int *items, int **response) -{ - int err; - char *line = str, *p; - int *resp = NULL; - int skip; - int count = 3; - int commas; - - RLOGD("parseRegistrationState. Parsing: %s",str); - err = at_tok_start(&line); - if (err < 0) goto error; - - /* Ok you have to be careful here - * The solicited version of the CREG response is - * +CREG: n, stat, [lac, cid] - * and the unsolicited version is - * +CREG: stat, [lac, cid] - * The <n> parameter is basically "is unsolicited creg on?" - * which it should always be - * - * Now we should normally get the solicited version here, - * but the unsolicited version could have snuck in - * so we have to handle both - * - * Also since the LAC and CID are only reported when registered, - * we can have 1, 2, 3, or 4 arguments here - * - * finally, a +CGREG: answer may have a fifth value that corresponds - * to the network type, as in; - * - * +CGREG: n, stat [,lac, cid [,networkType]] - */ - - /* count number of commas */ - commas = 0; - for (p = line ; *p != '\0' ;p++) { - if (*p == ',') commas++; - } - - resp = (int *)calloc(commas + 1, sizeof(int)); - if (!resp) goto error; - switch (commas) { - case 0: /* +CREG: <stat> */ - err = at_tok_nextint(&line, &resp[0]); - if (err < 0) goto error; - resp[1] = -1; - resp[2] = -1; - break; - - case 1: /* +CREG: <n>, <stat> */ - err = at_tok_nextint(&line, &skip); - if (err < 0) goto error; - err = at_tok_nextint(&line, &resp[0]); - if (err < 0) goto error; - resp[1] = -1; - resp[2] = -1; - if (err < 0) goto error; - break; - - case 2: /* +CREG: <stat>, <lac>, <cid> */ - err = at_tok_nextint(&line, &resp[0]); - if (err < 0) goto error; - err = at_tok_nexthexint(&line, &resp[1]); - if (err < 0) goto error; - err = at_tok_nexthexint(&line, &resp[2]); - if (err < 0) goto error; - break; - case 3: /* +CREG: <n>, <stat>, <lac>, <cid> */ - err = at_tok_nextint(&line, &skip); - if (err < 0) goto error; - err = at_tok_nextint(&line, &resp[0]); - if (err < 0) goto error; - err = at_tok_nexthexint(&line, &resp[1]); - if (err < 0) goto error; - err = at_tok_nexthexint(&line, &resp[2]); - if (err < 0) goto error; - break; - /* special case for CGREG, there is a fourth parameter - * that is the network type (unknown/gprs/edge/umts) - */ - case 4: /* +CGREG: <n>, <stat>, <lac>, <cid>, <networkType> */ - err = at_tok_nextint(&line, &skip); - if (err < 0) goto error; - err = at_tok_nextint(&line, &resp[0]); - if (err < 0) goto error; - err = at_tok_nexthexint(&line, &resp[1]); - if (err < 0) goto error; - err = at_tok_nexthexint(&line, &resp[2]); - if (err < 0) goto error; - err = at_tok_nexthexint(&line, &resp[3]); - if (err < 0) goto error; - count = 4; - break; - default: - goto error; - } - s_lac = resp[1]; - s_cid = resp[2]; - if (response) - *response = resp; - if (items) - *items = commas + 1; - if (type) - *type = techFromModemType(TECH(sMdmInfo)); - return 0; -error: - free(resp); - return -1; -} - -#define REG_STATE_LEN 15 -#define REG_DATA_STATE_LEN 6 -static void requestRegistrationState(int request, void *data __unused, - size_t datalen __unused, RIL_Token t) -{ - int err; - int *registration; - char **responseStr = NULL; - ATResponse *p_response = NULL; - const char *cmd; - const char *prefix; - char *line; - int i = 0, j, numElements = 0; - int count = 3; - int type, startfrom; - - RLOGD("requestRegistrationState"); - if(s_sim_update_started == 0) { - RLOGD("too early, sim card is not done yet"); - goto error; - } - - if (request == RIL_REQUEST_VOICE_REGISTRATION_STATE) { - cmd = "AT+CREG?"; - prefix = "+CREG:"; - numElements = REG_STATE_LEN; - } else if (request == RIL_REQUEST_DATA_REGISTRATION_STATE) { - cmd = "AT+CGREG?"; - prefix = "+CGREG:"; - numElements = REG_DATA_STATE_LEN; - } else { - assert(0); - goto error; - } - - err = at_send_command_singleline(cmd, prefix, &p_response); - - if (err != 0) goto error; - - line = p_response->p_intermediates->line; - - if (parseRegistrationState(line, &type, &count, ®istration)) goto error; - - responseStr = malloc(numElements * sizeof(char *)); - if (!responseStr) goto error; - memset(responseStr, 0, numElements * sizeof(char *)); - /** - * The first '4' bytes for both registration states remain the same. - * But if the request is 'DATA_REGISTRATION_STATE', - * the 5th and 6th byte(s) are optional. - */ - if (is3gpp2(type) == 1) { - RLOGD("registration state type: 3GPP2"); - // TODO: Query modem - startfrom = 3; - if(request == RIL_REQUEST_VOICE_REGISTRATION_STATE) { - asprintf(&responseStr[3], "8"); // EvDo revA - asprintf(&responseStr[4], "1"); // BSID - asprintf(&responseStr[5], "123"); // Latitude - asprintf(&responseStr[6], "222"); // Longitude - asprintf(&responseStr[7], "0"); // CSS Indicator - asprintf(&responseStr[8], "4"); // SID - asprintf(&responseStr[9], "65535"); // NID - asprintf(&responseStr[10], "0"); // Roaming indicator - asprintf(&responseStr[11], "1"); // System is in PRL - asprintf(&responseStr[12], "0"); // Default Roaming indicator - asprintf(&responseStr[13], "0"); // Reason for denial - asprintf(&responseStr[14], "0"); // Primary Scrambling Code of Current cell - } else if (request == RIL_REQUEST_DATA_REGISTRATION_STATE) { - asprintf(&responseStr[3], "8"); // Available data radio technology - } - } else { // type == RADIO_TECH_3GPP - RLOGD("registration state type: 3GPP"); - startfrom = 0; - asprintf(&responseStr[1], "%x", registration[1]); - asprintf(&responseStr[2], "%x", registration[2]); - if (count > 3) - asprintf(&responseStr[3], "%d", registration[3]); - } - asprintf(&responseStr[0], "%d", registration[0]); - - /** - * Optional bytes for DATA_REGISTRATION_STATE request - * 4th byte : Registration denial code - * 5th byte : The max. number of simultaneous Data Calls - */ - if(request == RIL_REQUEST_DATA_REGISTRATION_STATE) { - // asprintf(&responseStr[4], "3"); - // asprintf(&responseStr[5], "1"); - } - - for (j = startfrom; j < numElements; j++) { - if (!responseStr[i]) goto error; - } - free(registration); - registration = NULL; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, responseStr, numElements*sizeof(responseStr)); - for (j = 0; j < numElements; j++ ) { - free(responseStr[j]); - responseStr[j] = NULL; - } - free(responseStr); - responseStr = NULL; - at_response_free(p_response); - - return; -error: - if (responseStr) { - for (j = 0; j < numElements; j++) { - free(responseStr[j]); - responseStr[j] = NULL; - } - free(responseStr); - responseStr = NULL; - } - RLOGE("requestRegistrationState must never return an error when radio is on"); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); -} - -static void requestOperator(void *data __unused, size_t datalen __unused, RIL_Token t) -{ - int err; - int i; - int skip; - ATLine *p_cur; - char *response[3]; - - memset(response, 0, sizeof(response)); - - ATResponse *p_response = NULL; - - err = at_send_command_multiline( - "AT+COPS=3,0;+COPS?;+COPS=3,1;+COPS?;+COPS=3,2;+COPS?", - "+COPS:", &p_response); - - /* we expect 3 lines here: - * +COPS: 0,0,"T - Mobile" - * +COPS: 0,1,"TMO" - * +COPS: 0,2,"310170" - */ - - if (err != 0) goto error; - - for (i = 0, p_cur = p_response->p_intermediates - ; p_cur != NULL - ; p_cur = p_cur->p_next, i++ - ) { - char *line = p_cur->line; - - err = at_tok_start(&line); - if (err < 0) goto error; - - err = at_tok_nextint(&line, &skip); - if (err < 0) goto error; - - // If we're unregistered, we may just get - // a "+COPS: 0" response - if (!at_tok_hasmore(&line)) { - response[i] = NULL; - continue; - } - - err = at_tok_nextint(&line, &skip); - if (err < 0) goto error; - - // a "+COPS: 0, n" response is also possible - if (!at_tok_hasmore(&line)) { - response[i] = NULL; - continue; - } - - err = at_tok_nextstr(&line, &(response[i])); - if (err < 0) goto error; - // Simple assumption that mcc and mnc are 3 digits each - if (strlen(response[i]) == 6) { - if (sscanf(response[i], "%3d%3d", &s_mcc, &s_mnc) != 2) { - RLOGE("requestOperator expected mccmnc to be 6 decimal digits"); - } - } - } - - if (i != 3) { - /* expect 3 lines exactly */ - goto error; - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, response, sizeof(response)); - at_response_free(p_response); - - return; -error: - RLOGE("requestOperator must not return error when radio is on"); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); -} - -static void requestCdmaSendSMS(void *data, size_t datalen, RIL_Token t) -{ - int err = 1; // Set to go to error: - RIL_SMS_Response response; - RIL_CDMA_SMS_Message* rcsm; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_SIM_ABSENT, NULL, 0); - return; - } - - RLOGD("requestCdmaSendSMS datalen=%zu, sizeof(RIL_CDMA_SMS_Message)=%zu", - datalen, sizeof(RIL_CDMA_SMS_Message)); - - // verify data content to test marshalling/unmarshalling: - rcsm = (RIL_CDMA_SMS_Message*)data; - RLOGD("TeleserviceID=%d, bIsServicePresent=%d, \ - uServicecategory=%d, sAddress.digit_mode=%d, \ - sAddress.Number_mode=%d, sAddress.number_type=%d, ", - rcsm->uTeleserviceID, rcsm->bIsServicePresent, - rcsm->uServicecategory,rcsm->sAddress.digit_mode, - rcsm->sAddress.number_mode,rcsm->sAddress.number_type); - - if (err != 0) goto error; - - // Cdma Send SMS implementation will go here: - // But it is not implemented yet. - - memset(&response, 0, sizeof(response)); - response.messageRef = 1; - RIL_onRequestComplete(t, RIL_E_SUCCESS, &response, sizeof(response)); - return; - -error: - // Cdma Send SMS will always cause send retry error. - response.messageRef = -1; - RIL_onRequestComplete(t, RIL_E_SMS_SEND_FAIL_RETRY, &response, sizeof(response)); -} - -static void requestSendSMS(void *data, size_t datalen, RIL_Token t) -{ - int err; - const char *smsc; - const char *pdu; - int tpLayerLength; - char *cmd1, *cmd2; - RIL_SMS_Response response; - ATResponse *p_response = NULL; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_SIM_ABSENT, NULL, 0); - return; - } - - memset(&response, 0, sizeof(response)); - RLOGD("requestSendSMS datalen =%zu", datalen); - - if (s_ims_gsm_fail != 0) goto error; - if (s_ims_gsm_retry != 0) goto error2; - - smsc = ((const char **)data)[0]; - pdu = ((const char **)data)[1]; - - tpLayerLength = strlen(pdu)/2; - - // "NULL for default SMSC" - if (smsc == NULL) { - smsc= "00"; - } - - asprintf(&cmd1, "AT+CMGS=%d", tpLayerLength); - asprintf(&cmd2, "%s%s", smsc, pdu); - - err = at_send_command_sms(cmd1, cmd2, "+CMGS:", &p_response); - - free(cmd1); - free(cmd2); - - if (err != 0 || p_response->success == 0) goto error; - - /* FIXME fill in messageRef and ackPDU */ - response.messageRef = 1; - RIL_onRequestComplete(t, RIL_E_SUCCESS, &response, sizeof(response)); - at_response_free(p_response); - - return; -error: - response.messageRef = -2; - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, &response, sizeof(response)); - at_response_free(p_response); - return; -error2: - // send retry error. - response.messageRef = -1; - RIL_onRequestComplete(t, RIL_E_SMS_SEND_FAIL_RETRY, &response, sizeof(response)); - at_response_free(p_response); - return; -} - -static void requestImsSendSMS(void *data, size_t datalen, RIL_Token t) -{ - RIL_IMS_SMS_Message *p_args; - RIL_SMS_Response response; - - memset(&response, 0, sizeof(response)); - - RLOGD("requestImsSendSMS: datalen=%zu, " - "registered=%d, service=%d, format=%d, ims_perm_fail=%d, " - "ims_retry=%d, gsm_fail=%d, gsm_retry=%d", - datalen, s_ims_registered, s_ims_services, s_ims_format, - s_ims_cause_perm_failure, s_ims_cause_retry, s_ims_gsm_fail, - s_ims_gsm_retry); - - // figure out if this is gsm/cdma format - // then route it to requestSendSMS vs requestCdmaSendSMS respectively - p_args = (RIL_IMS_SMS_Message *)data; - - if (0 != s_ims_cause_perm_failure ) goto error; - - // want to fail over ims and this is first request over ims - if (0 != s_ims_cause_retry && 0 == p_args->retry) goto error2; - - if (RADIO_TECH_3GPP == p_args->tech) { - return requestSendSMS(p_args->message.gsmMessage, - datalen - sizeof(RIL_RadioTechnologyFamily), - t); - } else if (RADIO_TECH_3GPP2 == p_args->tech) { - return requestCdmaSendSMS(p_args->message.cdmaMessage, - datalen - sizeof(RIL_RadioTechnologyFamily), - t); - } else { - RLOGE("requestImsSendSMS invalid format value =%d", p_args->tech); - } - -error: - response.messageRef = -2; - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, &response, sizeof(response)); - return; - -error2: - response.messageRef = -1; - RIL_onRequestComplete(t, RIL_E_SMS_SEND_FAIL_RETRY, &response, sizeof(response)); -} - -static void requestSimOpenChannel(void *data, size_t datalen, RIL_Token t) -{ - ATResponse *p_response = NULL; - int32_t session_id[3]; - int err; - char cmd[32]; - char dummy; - char *line; - - const char *pdata = data ? data : EMULATOR_DUMMY_SIM_CHANNEL_NAME; - - // Max length is 16 bytes according to 3GPP spec 27.007 section 8.45 - if (pdata == NULL || datalen == 0 || datalen > 16) { - RLOGE("Invalid data passed to requestSimOpenChannel"); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - - snprintf(cmd, sizeof(cmd), "AT+CCHO=%s", pdata); - - err = at_send_command_numeric(cmd, &p_response); - if (err < 0 || p_response == NULL || p_response->success == 0) { - RLOGE("Error %d opening logical channel: %d", - err, p_response ? p_response->success : 0); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); - return; - } - - memset(session_id, 0, sizeof(session_id)); - - // Ensure integer only by scanning for an extra char but expect one result - line = p_response->p_intermediates->line; - if (sscanf(line, "%" SCNd32 "%c", session_id, &dummy) != 1) { - RLOGE("Invalid AT response, expected integer, was '%s'", line); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - - session_id[1] = 0x90; - RIL_onRequestComplete(t, RIL_E_SUCCESS, session_id, sizeof(session_id)); - at_response_free(p_response); -} - -static void requestSimCloseChannel(void *data, size_t datalen, RIL_Token t) -{ - ATResponse *p_response = NULL; - int32_t session_id; - int err; - char cmd[32]; - - if (data == NULL || datalen != sizeof(session_id)) { - ALOGE("Invalid data passed to requestSimCloseChannel"); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - session_id = ((int32_t *)data)[0]; - snprintf(cmd, sizeof(cmd), "AT+CCHC=%" PRId32, session_id); - err = at_send_command_singleline(cmd, "+CCHC", &p_response); - - if (err < 0 || p_response == NULL || p_response->success == 0) { - AT_CME_Error cme = p_response ? at_get_cme_error(p_response) : - CME_ERROR_NON_CME; - RIL_Errno ril_e = (cme == CME_INVALID_INDEX) ? RIL_E_INVALID_ARGUMENTS : - RIL_E_GENERIC_FAILURE; - - ALOGE("Error %d closing logical channel %d: %d", - err, session_id, p_response ? p_response->success : 0); - RIL_onRequestComplete(t, ril_e, NULL, 0); - at_response_free(p_response); - return; - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - - at_response_free(p_response); -} - -static void requestSimTransmitApduChannel(void *data, - size_t datalen, - RIL_Token t) -{ - ATResponse *p_response = NULL; - int err; - char *cmd; - char *line; - size_t cmd_size; - RIL_SIM_IO_Response sim_response; - memset(&sim_response, 0, sizeof(sim_response)); - RIL_SIM_APDU *apdu = (RIL_SIM_APDU *)data; - - if (apdu == NULL || datalen != sizeof(RIL_SIM_APDU)) { - RLOGE("Error input invalid %p %d %d", apdu, (int)datalen, (int)(sizeof(RIL_SIM_APDU))); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - - cmd_size = 10 + (apdu->data ? strlen(apdu->data) : 0); - asprintf(&cmd, "AT+CGLA=%d,%zu,%02x%02x%02x%02x%02x%s", - apdu->sessionid, cmd_size, apdu->cla, apdu->instruction, - apdu->p1, apdu->p2, apdu->p3, apdu->data ? apdu->data : ""); - - err = at_send_command_singleline(cmd, "+CGLA", &p_response); - free(cmd); - if (err < 0 || p_response == NULL || p_response->success == 0) { - RLOGE("Error %d transmitting APDU: %d", - err, p_response ? p_response->success : 0); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); - return; - } - - line = p_response->p_intermediates->line; - err = parseSimResponseLine(line, &sim_response); - - if (err == 0) { - RIL_onRequestComplete(t, RIL_E_SUCCESS, - &sim_response, sizeof(sim_response)); - } else { - RLOGE("Error %d parsing SIM response line: %s", err, line); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } - at_response_free(p_response); -} - -static void requestSetupDataCall(void *data, size_t datalen, RIL_Token t) -{ - const char *apn; - char *cmd; - int err; - ATResponse *p_response = NULL; - - apn = ((const char **)data)[2]; - -#ifdef USE_TI_COMMANDS - // Config for multislot class 10 (probably default anyway eh?) - err = at_send_command("AT%CPRIM=\"GMM\",\"CONFIG MULTISLOT_CLASS=<10>\"", - NULL); - - err = at_send_command("AT%DATA=2,\"UART\",1,,\"SER\",\"UART\",0", NULL); -#endif /* USE_TI_COMMANDS */ - - int fd, qmistatus; - size_t cur = 0; - size_t len; - ssize_t written, rlen; - char status[32] = {0}; - int retry = 10; - const char *pdp_type; - - RLOGD("requesting data connection to APN '%s'", apn); - - fd = open ("/dev/qmi", O_RDWR); - if (fd >= 0) { /* the device doesn't exist on the emulator */ - - RLOGD("opened the qmi device\n"); - asprintf(&cmd, "up:%s", apn); - len = strlen(cmd); - - while (cur < len) { - do { - written = write (fd, cmd + cur, len - cur); - } while (written < 0 && errno == EINTR); - - if (written < 0) { - RLOGE("### ERROR writing to /dev/qmi"); - close(fd); - goto error; - } - - cur += written; - } - - // wait for interface to come online - - do { - sleep(1); - do { - rlen = read(fd, status, 31); - } while (rlen < 0 && errno == EINTR); - - if (rlen < 0) { - RLOGE("### ERROR reading from /dev/qmi"); - close(fd); - goto error; - } else { - status[rlen] = '\0'; - RLOGD("### status: %s", status); - } - } while (strncmp(status, "STATE=up", 8) && strcmp(status, "online") && --retry); - - close(fd); - - if (retry == 0) { - RLOGE("### Failed to get data connection up\n"); - goto error; - } - - qmistatus = system("netcfg rmnet0 dhcp"); - - RLOGD("netcfg rmnet0 dhcp: status %d\n", qmistatus); - - if (qmistatus < 0) goto error; - - } else { - bool hasWifi = hasWifiCapability(); - const char* radioInterfaceName = getRadioInterfaceName(hasWifi); - if (setInterfaceState(radioInterfaceName, kInterfaceUp) != RIL_E_SUCCESS) { - goto error; - } - - if (datalen > 6 * sizeof(char *)) { - pdp_type = ((const char **)data)[6]; - } else { - pdp_type = "IP"; - } - - asprintf(&cmd, "AT+CGDCONT=1,\"%s\",\"%s\",,0,0", pdp_type, apn); - //FIXME check for error here - err = at_send_command(cmd, NULL); - free(cmd); - - // Set required QoS params to default - err = at_send_command("AT+CGQREQ=1", NULL); - - // Set minimum QoS params to default - err = at_send_command("AT+CGQMIN=1", NULL); - - // packet-domain event reporting - err = at_send_command("AT+CGEREP=1,0", NULL); - - // Hangup anything that's happening there now - err = at_send_command("AT+CGACT=1,0", NULL); - - // Start data on PDP context 1 - err = at_send_command("ATD*99***1#", &p_response); - - if (err < 0 || p_response->success == 0) { - goto error; - } - } - - requestOrSendDataCallList(&t); - - at_response_free(p_response); - - return; -error: - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); - -} - -static void requestDeactivateDataCall(RIL_Token t) -{ - bool hasWifi = hasWifiCapability(); - const char* radioInterfaceName = getRadioInterfaceName(hasWifi); - RIL_Errno rilErrno = setInterfaceState(radioInterfaceName, kInterfaceDown); - RIL_onRequestComplete(t, rilErrno, NULL, 0); -} - -static void requestSMSAcknowledge(void *data, size_t datalen __unused, RIL_Token t) -{ - int ackSuccess; - int err; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_RADIO_NOT_AVAILABLE, NULL, 0); - return; - } - - ackSuccess = ((int *)data)[0]; - - if (ackSuccess == 1) { - err = at_send_command("AT+CNMA=1", NULL); - } else if (ackSuccess == 0) { - err = at_send_command("AT+CNMA=2", NULL); - } else { - RLOGE("unsupported arg to RIL_REQUEST_SMS_ACKNOWLEDGE\n"); - goto error; - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); -error: - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - -} - -static void requestSIM_IO(void *data, size_t datalen __unused, RIL_Token t) -{ - ATResponse *p_response = NULL; - RIL_SIM_IO_Response sr; - int err; - char *cmd = NULL; - RIL_SIM_IO_v6 *p_args; - char *line; - - memset(&sr, 0, sizeof(sr)); - - p_args = (RIL_SIM_IO_v6 *)data; - - /* FIXME handle pin2 */ - - if (p_args->data == NULL) { - asprintf(&cmd, "AT+CRSM=%d,%d,%d,%d,%d", - p_args->command, p_args->fileid, - p_args->p1, p_args->p2, p_args->p3); - } else { - asprintf(&cmd, "AT+CRSM=%d,%d,%d,%d,%d,%s", - p_args->command, p_args->fileid, - p_args->p1, p_args->p2, p_args->p3, p_args->data); - } - - if (p_args->command == 0xdc) { - s_sim_update_started = 1; - } - - err = at_send_command_singleline(cmd, "+CRSM:", &p_response); - - if (err < 0 || p_response->success == 0) { - goto error; - } - - line = p_response->p_intermediates->line; - - err = parseSimResponseLine(line, &sr); - if (err < 0) { - goto error; - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &sr, sizeof(sr)); - at_response_free(p_response); - free(cmd); - - return; -error: - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); - free(cmd); - -} - -static void requestEnterSimPin(void* data, size_t datalen, RIL_Token t) -{ - ATResponse *p_response = NULL; - int err; - char* cmd = NULL; - const char** strings = (const char**)data;; - - if ( datalen == sizeof(char*) ) { - asprintf(&cmd, "AT+CPIN=%s", strings[0]); - } else if ( datalen == 2*sizeof(char*) ) { - asprintf(&cmd, "AT+CPIN=%s,%s", strings[0], strings[1]); - } else - goto error; - - err = at_send_command_singleline(cmd, "+CPIN:", &p_response); - free(cmd); - - if (err < 0 || p_response->success == 0) { -error: - RIL_onRequestComplete(t, RIL_E_PASSWORD_INCORRECT, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } - at_response_free(p_response); -} - - -static void requestSendUSSD(void *data, size_t datalen __unused, RIL_Token t) -{ - const char *ussdRequest; - - ussdRequest = (char *)(data); - - - RIL_onRequestComplete(t, RIL_E_REQUEST_NOT_SUPPORTED, NULL, 0); - -// @@@ TODO - -} - -static void requestExitEmergencyMode(void *data __unused, size_t datalen __unused, RIL_Token t) -{ - int err; - ATResponse *p_response = NULL; - - err = at_send_command("AT+WSOS=0", &p_response); - - if (err < 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - return; - } - - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); -} - -// TODO: Use all radio types -static int techFromModemType(int mdmtype) -{ - int ret = -1; - switch (1 << mdmtype) { - case MDM_CDMA: - ret = RADIO_TECH_1xRTT; - break; - case MDM_EVDO: - ret = RADIO_TECH_EVDO_A; - break; - case MDM_GSM: - ret = RADIO_TECH_GPRS; - break; - case MDM_WCDMA: - ret = RADIO_TECH_HSPA; - break; - case MDM_LTE: - ret = RADIO_TECH_LTE; - break; - } - return ret; -} - -static void requestGetCellInfoList(void *data __unused, size_t datalen __unused, RIL_Token t) -{ - uint64_t curTime = ril_nano_time(); - RIL_CellInfo_v12 ci[1] = - { - { // ci[0] - 1, // cellInfoType - 1, // registered - RIL_TIMESTAMP_TYPE_MODEM, - curTime - 1000, // Fake some time in the past - { // union CellInfo - { // RIL_CellInfoGsm gsm - { // gsm.cellIdneityGsm - s_mcc, // mcc - s_mnc, // mnc - s_lac, // lac - s_cid, // cid - 0, //arfcn unknown - 0xFF, // bsic unknown - }, - { // gsm.signalStrengthGsm - 10, // signalStrength - 0 // bitErrorRate - , INT_MAX // timingAdvance invalid value - } - } - } - } - }; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, ci, sizeof(ci)); -} - - -static void requestSetCellInfoListRate(void *data, size_t datalen __unused, RIL_Token t) -{ - // For now we'll save the rate but no RIL_UNSOL_CELL_INFO_LIST messages - // will be sent. - assert (datalen == sizeof(int)); - s_cell_info_rate_ms = ((int *)data)[0]; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); -} - -static void requestGetHardwareConfig(void *data, size_t datalen, RIL_Token t) -{ - // TODO - hook this up with real query/info from radio. - - RIL_HardwareConfig hwCfg; - memset(&hwCfg, 0, sizeof(hwCfg)); - - RIL_UNUSED_PARM(data); - RIL_UNUSED_PARM(datalen); - - hwCfg.type = -1; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &hwCfg, sizeof(hwCfg)); -} - -static void requestGetTtyMode(void *data, size_t datalen, RIL_Token t) -{ - int ttyModeResponse; - - RIL_UNUSED_PARM(data); - RIL_UNUSED_PARM(datalen); - - ttyModeResponse = (getSIMStatus() == SIM_READY) ? 1 // TTY Full - : 0; // TTY Off - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &ttyModeResponse, sizeof(ttyModeResponse)); -} - -static void requestGetRadioCapability(void *data, size_t datalen, RIL_Token t) -{ - RIL_RadioCapability radioCapability; - - RIL_UNUSED_PARM(data); - RIL_UNUSED_PARM(datalen); - - radioCapability.version = RIL_RADIO_CAPABILITY_VERSION; - radioCapability.session = 0; - radioCapability.phase = 0; - radioCapability.rat = RAF_NR | RAF_LTE | RAF_UMTS | RAF_GSM; - radioCapability.logicalModemUuid[0] = '\0'; - radioCapability.status = RC_STATUS_SUCCESS; - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &radioCapability, sizeof(radioCapability)); -} - -static void requestGetMute(void *data, size_t datalen, RIL_Token t) -{ - int muteResponse; - - RIL_UNUSED_PARM(data); - RIL_UNUSED_PARM(datalen); - - muteResponse = 0; // Mute disabled - - RIL_onRequestComplete(t, RIL_E_SUCCESS, &muteResponse, sizeof(muteResponse)); -} - -static void requestGetSimAuthentication(void *data, size_t datalen __unused, RIL_Token t) -{ - // TODO - hook this up with real query/info from radio. - RIL_SimAuthentication* auth = (RIL_SimAuthentication*)data; - - RIL_SIM_IO_Response auth_response = { - 0x90, - 0x00, - "" - }; - - // special case: empty authData, should return empty response - if (auth->authData == NULL || strlen(auth->authData) == 0) { - char reply[] = ""; - RIL_onRequestComplete(t, RIL_E_SUCCESS, &auth_response, sizeof(auth_response)); - RLOGD("%s empty data in", __func__); - return; - } - - //talk to modem - ATResponse *p_response = NULL; - memset(&auth_response, 0, sizeof(auth_response)); - int err; - char *cmd = NULL; - int auth_len = strlen(auth->authData); - int total_len = auth_len + 12; - asprintf(&cmd, "AT+CSIM=%d, \"008800%02x%02x%s00\"", total_len, auth->authContext, - auth_len, auth->authData); - - err = at_send_command_singleline(cmd, "+CSIM:", &p_response); - if (err < 0 || p_response == NULL || p_response->success == 0) { - ALOGE("%s Error %d transmitting CSIM: %d", __func__, - err, p_response ? p_response->success : 0); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - at_response_free(p_response); - return; - } - - char* line = p_response->p_intermediates->line; - - parseAuthResponse(line, &auth_response); - RIL_onRequestComplete(t, auth_response.sw2, &auth_response, sizeof(auth_response)); - free(auth_response.simResponse); - free(p_response); -} - -static void requestModemActivityInfo(RIL_Token t) -{ - int err; - char *line; - ATResponse *p_response = NULL; - RIL_ActivityStatsInfo info; - - err = at_send_command_singleline("AT+MAI", "+MAI:", &p_response); - if (err < 0 || p_response == NULL || p_response->success == 0) { - ALOGE("Error transmitting AT+MAI, err=%d, success=%d", - err, (p_response ? p_response->success : 0)); - goto error; - } - - memset(&info, 0, sizeof(info)); - if (sscanf(p_response->p_intermediates->line, - "+MAI: sleep=%u idle=%u rx=%u tx0=%u tx1=%u tx2=%u tx3=%u tx4=%u", - &info.sleep_mode_time_ms, - &info.idle_mode_time_ms, - &info.rx_mode_time_ms, - &info.tx_mode_time_ms[0], - &info.tx_mode_time_ms[1], - &info.tx_mode_time_ms[2], - &info.tx_mode_time_ms[3], - &info.tx_mode_time_ms[4]) == 8) { - RIL_onRequestComplete(t, RIL_E_SUCCESS, &info, sizeof(info)); - at_response_free(p_response); - return; - } else { - ALOGE("Unexpected response for AT+MAI: '%s'", - p_response->p_intermediates->line); - } - -error: - at_response_free(p_response); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); -} - -static void requestSetCarrierRestrictions(const RIL_CarrierRestrictions *restrictions __unused, RIL_Token t) -{ - ATResponse *p_response = NULL; - int success; - int err; - char cmd[32]; - - snprintf(cmd, sizeof(cmd), "AT+CRRSTR=%d,%d", - restrictions->len_allowed_carriers, - restrictions->len_excluded_carriers); - - err = at_send_command_singleline(cmd, "+CRRSTR:", &p_response); - success = p_response ? p_response->success : 0; - at_response_free(p_response); - - if (err == 0 && success) { - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } else { - ALOGE("'%s' failed with err=%d success=%d", cmd, err, success); - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } -} - -/*** Callback methods from the RIL library to us ***/ - -/** - * Call from RIL to us to make a RIL_REQUEST - * - * Must be completed with a call to RIL_onRequestComplete() - * - * RIL_onRequestComplete() may be called from any thread, before or after - * this function returns. - * - * Because onRequest function could be called from multiple different thread, - * we must ensure that the underlying at_send_command_* function - * is atomic. - */ -static void -onRequest (int request, void *data, size_t datalen, RIL_Token t) -{ - ATResponse *p_response; - int err; - - RLOGD("onRequest: %s", requestToString(request)); - - /* Ignore all requests except RIL_REQUEST_GET_SIM_STATUS - * when RADIO_STATE_UNAVAILABLE. - */ - if (sState == RADIO_STATE_UNAVAILABLE - && request != RIL_REQUEST_GET_SIM_STATUS - ) { - RIL_onRequestComplete(t, RIL_E_RADIO_NOT_AVAILABLE, NULL, 0); - return; - } - - /* Ignore all non-power requests when RADIO_STATE_OFF - * (except RIL_REQUEST_GET_SIM_STATUS) - */ - if (sState == RADIO_STATE_OFF) { - switch(request) { - case RIL_REQUEST_BASEBAND_VERSION: - case RIL_REQUEST_CDMA_GET_SUBSCRIPTION_SOURCE: - case RIL_REQUEST_CDMA_QUERY_PREFERRED_VOICE_PRIVACY_MODE: - case RIL_REQUEST_CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE: - case RIL_REQUEST_CDMA_SET_ROAMING_PREFERENCE: - case RIL_REQUEST_CDMA_SET_SUBSCRIPTION_SOURCE: - case RIL_REQUEST_CDMA_SUBSCRIPTION: - case RIL_REQUEST_DEVICE_IDENTITY: - case RIL_REQUEST_EXIT_EMERGENCY_CALLBACK_MODE: - case RIL_REQUEST_GET_ACTIVITY_INFO: - case RIL_REQUEST_GET_CARRIER_RESTRICTIONS: - case RIL_REQUEST_GET_CURRENT_CALLS: - case RIL_REQUEST_GET_IMEI: - case RIL_REQUEST_GET_MUTE: - case RIL_REQUEST_GET_NEIGHBORING_CELL_IDS: - case RIL_REQUEST_GET_PREFERRED_NETWORK_TYPE: - case RIL_REQUEST_GET_RADIO_CAPABILITY: - case RIL_REQUEST_GET_SIM_STATUS: - case RIL_REQUEST_NV_RESET_CONFIG: - case RIL_REQUEST_QUERY_AVAILABLE_BAND_MODE: - case RIL_REQUEST_QUERY_NETWORK_SELECTION_MODE: - case RIL_REQUEST_QUERY_TTY_MODE: - case RIL_REQUEST_RADIO_POWER: - case RIL_REQUEST_SET_BAND_MODE: - case RIL_REQUEST_SET_CARRIER_RESTRICTIONS: - case RIL_REQUEST_SET_LOCATION_UPDATES: - case RIL_REQUEST_SET_PREFERRED_NETWORK_TYPE: - case RIL_REQUEST_SET_TTY_MODE: - case RIL_REQUEST_SET_UNSOL_CELL_INFO_LIST_RATE: - case RIL_REQUEST_STOP_LCE: - case RIL_REQUEST_VOICE_RADIO_TECH: - // Process all the above, even though the radio is off - break; - - default: - // For all others, say NOT_AVAILABLE because the radio is off - RIL_onRequestComplete(t, RIL_E_RADIO_NOT_AVAILABLE, NULL, 0); - return; - } - } - - switch (request) { - case RIL_REQUEST_GET_SIM_STATUS: { - RIL_CardStatus_v6 *p_card_status; - char *p_buffer; - int buffer_size; - - int result = getCardStatus(&p_card_status); - if (result == RIL_E_SUCCESS) { - p_buffer = (char *)p_card_status; - buffer_size = sizeof(*p_card_status); - } else { - p_buffer = NULL; - buffer_size = 0; - } - RIL_onRequestComplete(t, result, p_buffer, buffer_size); - freeCardStatus(p_card_status); - break; - } - case RIL_REQUEST_GET_CURRENT_CALLS: - requestGetCurrentCalls(data, datalen, t); - break; - case RIL_REQUEST_DIAL: - requestDial(data, datalen, t); - break; - case RIL_REQUEST_HANGUP: - requestHangup(data, datalen, t); - break; - case RIL_REQUEST_HANGUP_WAITING_OR_BACKGROUND: - case RIL_REQUEST_HANGUP_FOREGROUND_RESUME_BACKGROUND: - case RIL_REQUEST_SWITCH_WAITING_OR_HOLDING_AND_ACTIVE: - case RIL_REQUEST_CONFERENCE: - case RIL_REQUEST_UDUB: - requestCallSelection(data, datalen, t, request); - break; - case RIL_REQUEST_ANSWER: - at_send_command("ATA", NULL); - -#ifdef WORKAROUND_ERRONEOUS_ANSWER - s_expectAnswer = 1; -#endif /* WORKAROUND_ERRONEOUS_ANSWER */ - - if (getSIMStatus() != SIM_READY) { - RIL_onRequestComplete(t, RIL_E_MODEM_ERR, NULL, 0); - } else { - // Success or failure is ignored by the upper layer here. - // It will call GET_CURRENT_CALLS and determine success that way. - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } - break; - - case RIL_REQUEST_SEPARATE_CONNECTION: - { - char cmd[12]; - int party = ((int*)data)[0]; - - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_RADIO_NOT_AVAILABLE, NULL, 0); - return; - } - // Make sure that party is in a valid range. - // (Note: The Telephony middle layer imposes a range of 1 to 7. - // It's sufficient for us to just make sure it's single digit.) - if (party > 0 && party < 10) { - sprintf(cmd, "AT+CHLD=2%d", party); - at_send_command(cmd, NULL); - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } - } - break; - - case RIL_REQUEST_SIGNAL_STRENGTH: - requestSignalStrength(data, datalen, t); - break; - case RIL_REQUEST_VOICE_REGISTRATION_STATE: - case RIL_REQUEST_DATA_REGISTRATION_STATE: - requestRegistrationState(request, data, datalen, t); - break; - case RIL_REQUEST_OPERATOR: - requestOperator(data, datalen, t); - break; - case RIL_REQUEST_RADIO_POWER: - requestRadioPower(data, datalen, t); - break; - case RIL_REQUEST_DTMF: { - char c = ((char *)data)[0]; - char *cmd; - asprintf(&cmd, "AT+VTS=%c", (int)c); - at_send_command(cmd, NULL); - free(cmd); - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - break; - } - case RIL_REQUEST_SEND_SMS: - case RIL_REQUEST_SEND_SMS_EXPECT_MORE: - requestSendSMS(data, datalen, t); - break; - case RIL_REQUEST_CDMA_SEND_SMS: - requestCdmaSendSMS(data, datalen, t); - break; - case RIL_REQUEST_IMS_SEND_SMS: - requestImsSendSMS(data, datalen, t); - break; - case RIL_REQUEST_SIM_OPEN_CHANNEL: - requestSimOpenChannel(data, datalen, t); - break; - case RIL_REQUEST_SIM_CLOSE_CHANNEL: - requestSimCloseChannel(data, datalen, t); - break; - case RIL_REQUEST_SIM_TRANSMIT_APDU_CHANNEL: - requestSimTransmitApduChannel(data, datalen, t); - break; - case RIL_REQUEST_SIM_TRANSMIT_APDU_BASIC: - requestSimTransmitApduChannel(data, datalen, t); - break; - case RIL_REQUEST_SETUP_DATA_CALL: - requestSetupDataCall(data, datalen, t); - break; - case RIL_REQUEST_DEACTIVATE_DATA_CALL: - requestDeactivateDataCall(t); - break; - case RIL_REQUEST_SMS_ACKNOWLEDGE: - requestSMSAcknowledge(data, datalen, t); - break; - - case RIL_REQUEST_GET_IMSI: - p_response = NULL; - err = at_send_command_numeric("AT+CIMI", &p_response); - - if (err < 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_SUCCESS, - p_response->p_intermediates->line, sizeof(char *)); - } - at_response_free(p_response); - break; - - case RIL_REQUEST_GET_IMEI: - p_response = NULL; - err = at_send_command_numeric("AT+CGSN", &p_response); - - if (err < 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_SUCCESS, - p_response->p_intermediates->line, sizeof(char *)); - } - at_response_free(p_response); - break; - - case RIL_REQUEST_SIM_IO: - requestSIM_IO(data,datalen,t); - break; - - case RIL_REQUEST_SEND_USSD: - requestSendUSSD(data, datalen, t); - break; - - case RIL_REQUEST_CANCEL_USSD: - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_RADIO_NOT_AVAILABLE, NULL, 0); - return; - } - p_response = NULL; - err = at_send_command_numeric("AT+CUSD=2", &p_response); - - if (err < 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_SUCCESS, - p_response->p_intermediates->line, sizeof(char *)); - } - at_response_free(p_response); - break; - - case RIL_REQUEST_SET_NETWORK_SELECTION_AUTOMATIC: - setNetworkSelectionAutomatic(t); - break; - - case RIL_REQUEST_DATA_CALL_LIST: - requestDataCallList(data, datalen, t); - break; - - case RIL_REQUEST_QUERY_NETWORK_SELECTION_MODE: - requestQueryNetworkSelectionMode(data, datalen, t); - break; - - case RIL_REQUEST_OEM_HOOK_RAW: - // echo back data - RIL_onRequestComplete(t, RIL_E_SUCCESS, data, datalen); - break; - - - case RIL_REQUEST_OEM_HOOK_STRINGS: { - int i; - const char ** cur; - - RLOGD("got OEM_HOOK_STRINGS: 0x%8p %lu", data, (long)datalen); - - - for (i = (datalen / sizeof (char *)), cur = (const char **)data ; - i > 0 ; cur++, i --) { - RLOGD("> '%s'", *cur); - } - - // echo back strings - RIL_onRequestComplete(t, RIL_E_SUCCESS, data, datalen); - break; - } - - case RIL_REQUEST_WRITE_SMS_TO_SIM: - requestWriteSmsToSim(data, datalen, t); - break; - - case RIL_REQUEST_DELETE_SMS_ON_SIM: { - char * cmd; - p_response = NULL; - asprintf(&cmd, "AT+CMGD=%d", ((int *)data)[0]); - err = at_send_command(cmd, &p_response); - free(cmd); - if (err < 0 || p_response->success == 0) { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } - at_response_free(p_response); - break; - } - - case RIL_REQUEST_ENTER_SIM_PIN: - case RIL_REQUEST_ENTER_SIM_PUK: - case RIL_REQUEST_ENTER_SIM_PIN2: - case RIL_REQUEST_ENTER_SIM_PUK2: - case RIL_REQUEST_CHANGE_SIM_PIN: - case RIL_REQUEST_CHANGE_SIM_PIN2: - requestEnterSimPin(data, datalen, t); - break; - - case RIL_REQUEST_IMS_REGISTRATION_STATE: { - int reply[2]; - //0==unregistered, 1==registered - reply[0] = s_ims_registered; - - //to be used when changed to include service supporated info - //reply[1] = s_ims_services; - - // FORMAT_3GPP(1) vs FORMAT_3GPP2(2); - reply[1] = s_ims_format; - - RLOGD("IMS_REGISTRATION=%d, format=%d ", - reply[0], reply[1]); - if (reply[1] != -1) { - RIL_onRequestComplete(t, RIL_E_SUCCESS, reply, sizeof(reply)); - } else { - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - } - break; - } - - case RIL_REQUEST_VOICE_RADIO_TECH: - { - int tech = techFromModemType(TECH(sMdmInfo)); - if (tech < 0 ) - RIL_onRequestComplete(t, RIL_E_GENERIC_FAILURE, NULL, 0); - else - RIL_onRequestComplete(t, RIL_E_SUCCESS, &tech, sizeof(tech)); - } - break; - case RIL_REQUEST_SET_PREFERRED_NETWORK_TYPE: - requestSetPreferredNetworkType(request, data, datalen, t); - break; - - case RIL_REQUEST_GET_PREFERRED_NETWORK_TYPE: - requestGetPreferredNetworkType(request, data, datalen, t); - break; - - case RIL_REQUEST_GET_CELL_INFO_LIST: - requestGetCellInfoList(data, datalen, t); - break; - - case RIL_REQUEST_SET_UNSOL_CELL_INFO_LIST_RATE: - requestSetCellInfoListRate(data, datalen, t); - break; - - case RIL_REQUEST_GET_HARDWARE_CONFIG: - requestGetHardwareConfig(data, datalen, t); - break; - - case RIL_REQUEST_SHUTDOWN: - requestShutdown(t); - break; - - case RIL_REQUEST_QUERY_TTY_MODE: - requestGetTtyMode(data, datalen, t); - break; - - case RIL_REQUEST_GET_RADIO_CAPABILITY: - requestGetRadioCapability(data, datalen, t); - break; - - case RIL_REQUEST_GET_MUTE: - requestGetMute(data, datalen, t); - break; - - case RIL_REQUEST_SET_INITIAL_ATTACH_APN: - case RIL_REQUEST_ALLOW_DATA: - case RIL_REQUEST_ENTER_NETWORK_DEPERSONALIZATION: - case RIL_REQUEST_SET_CLIR: - case RIL_REQUEST_SET_SUPP_SVC_NOTIFICATION: - case RIL_REQUEST_SET_BAND_MODE: - case RIL_REQUEST_QUERY_AVAILABLE_BAND_MODE: - case RIL_REQUEST_GET_NEIGHBORING_CELL_IDS: - case RIL_REQUEST_SET_LOCATION_UPDATES: - case RIL_REQUEST_SET_TTY_MODE: - case RIL_REQUEST_CDMA_SET_PREFERRED_VOICE_PRIVACY_MODE: - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - break; - - case RIL_REQUEST_SIM_AUTHENTICATION: - requestGetSimAuthentication(data, datalen, t); - break; - - case RIL_REQUEST_BASEBAND_VERSION: - requestCdmaBaseBandVersion(request, data, datalen, t); - break; - - case RIL_REQUEST_DEVICE_IDENTITY: - requestDeviceIdentity(request, data, datalen, t); - break; - - case RIL_REQUEST_CDMA_SUBSCRIPTION: - requestCdmaSubscription(request, data, datalen, t); - break; - - case RIL_REQUEST_CDMA_GET_SUBSCRIPTION_SOURCE: - requestCdmaGetSubscriptionSource(request, data, datalen, t); - break; - - case RIL_REQUEST_START_LCE: - case RIL_REQUEST_STOP_LCE: - case RIL_REQUEST_PULL_LCEDATA: - if (getSIMStatus() == SIM_ABSENT) { - RIL_onRequestComplete(t, RIL_E_SIM_ABSENT, NULL, 0); - } else { - RIL_onRequestComplete(t, RIL_E_LCE_NOT_SUPPORTED, NULL, 0); - } - break; - - case RIL_REQUEST_CDMA_QUERY_ROAMING_PREFERENCE: - if (TECH_BIT(sMdmInfo) == MDM_CDMA) { - requestCdmaGetRoamingPreference(request, data, datalen, t); - } else { - RIL_onRequestComplete(t, RIL_E_REQUEST_NOT_SUPPORTED, NULL, 0); - } - break; - - case RIL_REQUEST_CDMA_SET_SUBSCRIPTION_SOURCE: - if (TECH_BIT(sMdmInfo) == MDM_CDMA) { - requestCdmaSetSubscriptionSource(request, data, datalen, t); - } else { - // VTS tests expect us to silently do nothing - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } - break; - - case RIL_REQUEST_CDMA_SET_ROAMING_PREFERENCE: - if (TECH_BIT(sMdmInfo) == MDM_CDMA) { - requestCdmaSetRoamingPreference(request, data, datalen, t); - } else { - // VTS tests expect us to silently do nothing - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } - break; - - case RIL_REQUEST_EXIT_EMERGENCY_CALLBACK_MODE: - if (TECH_BIT(sMdmInfo) == MDM_CDMA) { - requestExitEmergencyMode(data, datalen, t); - } else { - // VTS tests expect us to silently do nothing - RIL_onRequestComplete(t, RIL_E_SUCCESS, NULL, 0); - } - break; - - case RIL_REQUEST_GET_ACTIVITY_INFO: - requestModemActivityInfo(t); - break; - - case RIL_REQUEST_SET_CARRIER_RESTRICTIONS: - if (datalen == sizeof(RIL_CarrierRestrictions)) { - requestSetCarrierRestrictions((const RIL_CarrierRestrictions *)data, t); - } else { - /* unexpected sizeof */ - RIL_onRequestComplete(t, RIL_E_REQUEST_NOT_SUPPORTED, NULL, 0); - } - break; - - default: - RLOGD("Request not supported. Tech: %d",TECH(sMdmInfo)); - RIL_onRequestComplete(t, RIL_E_REQUEST_NOT_SUPPORTED, NULL, 0); - break; - } -} - -/** - * Synchronous call from the RIL to us to return current radio state. - * RADIO_STATE_UNAVAILABLE should be the initial state. - */ -static RIL_RadioState -currentState() -{ - return sState; -} -/** - * Call from RIL to us to find out whether a specific request code - * is supported by this implementation. - * - * Return 1 for "supported" and 0 for "unsupported" - */ - -static int -onSupports (int requestCode __unused) -{ - //@@@ todo - - return 1; -} - -static void onCancel (RIL_Token t __unused) -{ - //@@@todo - -} - -static const char * getVersion(void) -{ - return "android reference-ril 1.0"; -} - -static void -setRadioTechnology(ModemInfo *mdm, int newtech) -{ - RLOGD("setRadioTechnology(%d)", newtech); - - int oldtech = TECH(mdm); - - if (newtech != oldtech) { - RLOGD("Tech change (%d => %d)", oldtech, newtech); - TECH(mdm) = newtech; - if (techFromModemType(newtech) != techFromModemType(oldtech)) { - int tech = techFromModemType(TECH(sMdmInfo)); - if (tech > 0 ) { - RIL_onUnsolicitedResponse(RIL_UNSOL_VOICE_RADIO_TECH_CHANGED, - &tech, sizeof(tech)); - } - } - } -} - -static void -setRadioState(RIL_RadioState newState) -{ - RLOGD("setRadioState(%d)", newState); - RIL_RadioState oldState; - - pthread_mutex_lock(&s_state_mutex); - - oldState = sState; - - if (s_closed > 0) { - // If we're closed, the only reasonable state is - // RADIO_STATE_UNAVAILABLE - // This is here because things on the main thread - // may attempt to change the radio state after the closed - // event happened in another thread - newState = RADIO_STATE_UNAVAILABLE; - } - - if (sState != newState || s_closed > 0) { - sState = newState; - - pthread_cond_broadcast (&s_state_cond); - } - - pthread_mutex_unlock(&s_state_mutex); - - - /* do these outside of the mutex */ - if (sState != oldState) { - RIL_onUnsolicitedResponse (RIL_UNSOL_RESPONSE_RADIO_STATE_CHANGED, - NULL, 0); - // Sim state can change as result of radio state change - RIL_onUnsolicitedResponse (RIL_UNSOL_RESPONSE_SIM_STATUS_CHANGED, - NULL, 0); - - /* FIXME onSimReady() and onRadioPowerOn() cannot be called - * from the AT reader thread - * Currently, this doesn't happen, but if that changes then these - * will need to be dispatched on the request thread - */ - if (sState == RADIO_STATE_ON) { - onRadioPowerOn(); - } - } -} - -/** Returns RUIM_NOT_READY on error */ -static SIM_Status -getRUIMStatus() -{ - ATResponse *p_response = NULL; - int err; - int ret; - char *cpinLine; - char *cpinResult; - - if (sState == RADIO_STATE_OFF || sState == RADIO_STATE_UNAVAILABLE) { - ret = SIM_NOT_READY; - goto done; - } - - err = at_send_command_singleline("AT+CPIN?", "+CPIN:", &p_response); - - if (err != 0) { - ret = SIM_NOT_READY; - goto done; - } - - switch (at_get_cme_error(p_response)) { - case CME_SUCCESS: - break; - - case CME_SIM_NOT_INSERTED: - ret = SIM_ABSENT; - goto done; - - default: - ret = SIM_NOT_READY; - goto done; - } - - /* CPIN? has succeeded, now look at the result */ - - cpinLine = p_response->p_intermediates->line; - err = at_tok_start (&cpinLine); - - if (err < 0) { - ret = SIM_NOT_READY; - goto done; - } - - err = at_tok_nextstr(&cpinLine, &cpinResult); - - if (err < 0) { - ret = SIM_NOT_READY; - goto done; - } - - if (0 == strcmp (cpinResult, "SIM PIN")) { - ret = SIM_PIN; - goto done; - } else if (0 == strcmp (cpinResult, "SIM PUK")) { - ret = SIM_PUK; - goto done; - } else if (0 == strcmp (cpinResult, "PH-NET PIN")) { - return SIM_NETWORK_PERSONALIZATION; - } else if (0 != strcmp (cpinResult, "READY")) { - /* we're treating unsupported lock types as "sim absent" */ - ret = SIM_ABSENT; - goto done; - } - - at_response_free(p_response); - p_response = NULL; - cpinResult = NULL; - - ret = SIM_READY; - -done: - at_response_free(p_response); - return ret; -} - -/** Returns SIM_NOT_READY on error */ -static SIM_Status -getSIMStatus() -{ - ATResponse *p_response = NULL; - int err; - SIM_Status ret; - char *cpinLine; - char *cpinResult; - - RLOGD("getSIMStatus(). sState: %d",sState); - err = at_send_command_singleline("AT+CPIN?", "+CPIN:", &p_response); - - if (err != 0) { - ret = SIM_NOT_READY; - goto done; - } - - switch (at_get_cme_error(p_response)) { - case CME_SUCCESS: - break; - - case CME_SIM_NOT_INSERTED: - ret = SIM_ABSENT; - goto done; - - default: - ret = SIM_NOT_READY; - goto done; - } - - /* CPIN? has succeeded, now look at the result */ - - cpinLine = p_response->p_intermediates->line; - err = at_tok_start (&cpinLine); - - if (err < 0) { - ret = SIM_NOT_READY; - goto done; - } - - err = at_tok_nextstr(&cpinLine, &cpinResult); - - if (err < 0) { - ret = SIM_NOT_READY; - goto done; - } - - if (0 == strcmp (cpinResult, "SIM PIN")) { - ret = SIM_PIN; - } else if (0 == strcmp (cpinResult, "SIM PUK")) { - ret = SIM_PUK; - } else if (0 == strcmp (cpinResult, "PH-NET PIN")) { - ret = SIM_NETWORK_PERSONALIZATION; - } else if (0 == strcmp (cpinResult, "RESTRICTED")) { - ret = SIM_RESTRICTED; - } else if (0 == strcmp (cpinResult, "READY")) { - ret = (sState == RADIO_STATE_ON) ? SIM_READY : SIM_NOT_READY; - } else { - /* we're treating unsupported lock types as "sim absent" */ - ret = SIM_ABSENT; - } - -done: - at_response_free(p_response); - return ret; -} - - -/** - * Get the current card status. - * - * This must be freed using freeCardStatus. - * @return: On success returns RIL_E_SUCCESS - */ -static int getCardStatus(RIL_CardStatus_v6 **pp_card_status) { - static const RIL_AppStatus app_status_array[] = { - // SIM_ABSENT = 0 - { RIL_APPTYPE_UNKNOWN, RIL_APPSTATE_UNKNOWN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // SIM_NOT_READY = 1 - { RIL_APPTYPE_USIM, RIL_APPSTATE_DETECTED, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // SIM_READY = 2 - { RIL_APPTYPE_USIM, RIL_APPSTATE_READY, RIL_PERSOSUBSTATE_READY, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // SIM_PIN = 3 - { RIL_APPTYPE_USIM, RIL_APPSTATE_PIN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_NOT_VERIFIED, RIL_PINSTATE_UNKNOWN }, - // SIM_PUK = 4 - { RIL_APPTYPE_USIM, RIL_APPSTATE_PUK, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_BLOCKED, RIL_PINSTATE_UNKNOWN }, - // SIM_NETWORK_PERSONALIZATION = 5 - { RIL_APPTYPE_USIM, RIL_APPSTATE_SUBSCRIPTION_PERSO, RIL_PERSOSUBSTATE_SIM_NETWORK, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_NOT_VERIFIED, RIL_PINSTATE_UNKNOWN }, - // SIM_RESTRICTED = 6 - { RIL_APPTYPE_UNKNOWN, RIL_APPSTATE_UNKNOWN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - - // RUIM_ABSENT = 7 - { RIL_APPTYPE_UNKNOWN, RIL_APPSTATE_UNKNOWN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // RUIM_NOT_READY = 8 - { RIL_APPTYPE_RUIM, RIL_APPSTATE_DETECTED, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // RUIM_READY = 9 - { RIL_APPTYPE_RUIM, RIL_APPSTATE_READY, RIL_PERSOSUBSTATE_READY, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // RUIM_PIN = 10 - { RIL_APPTYPE_RUIM, RIL_APPSTATE_PIN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_NOT_VERIFIED, RIL_PINSTATE_UNKNOWN }, - // RUIM_PUK = 11 - { RIL_APPTYPE_RUIM, RIL_APPSTATE_PUK, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_BLOCKED, RIL_PINSTATE_UNKNOWN }, - // RUIM_NETWORK_PERSONALIZATION = 12 - { RIL_APPTYPE_RUIM, RIL_APPSTATE_SUBSCRIPTION_PERSO, RIL_PERSOSUBSTATE_SIM_NETWORK, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_NOT_VERIFIED, RIL_PINSTATE_UNKNOWN }, - // RUIM_RESTRICTED = 13 - { RIL_APPTYPE_UNKNOWN, RIL_APPSTATE_UNKNOWN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - - // ISIM_ABSENT = 14 - { RIL_APPTYPE_UNKNOWN, RIL_APPSTATE_UNKNOWN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // ISIM_NOT_READY = 15 - { RIL_APPTYPE_ISIM, RIL_APPSTATE_DETECTED, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // ISIM_READY = 16 - { RIL_APPTYPE_ISIM, RIL_APPSTATE_READY, RIL_PERSOSUBSTATE_READY, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - // ISIM_PIN = 17 - { RIL_APPTYPE_ISIM, RIL_APPSTATE_PIN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_NOT_VERIFIED, RIL_PINSTATE_UNKNOWN }, - // ISIM_PUK = 18 - { RIL_APPTYPE_ISIM, RIL_APPSTATE_PUK, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_BLOCKED, RIL_PINSTATE_UNKNOWN }, - // ISIM_NETWORK_PERSONALIZATION = 19 - { RIL_APPTYPE_ISIM, RIL_APPSTATE_SUBSCRIPTION_PERSO, RIL_PERSOSUBSTATE_SIM_NETWORK, - NULL, NULL, 0, RIL_PINSTATE_ENABLED_NOT_VERIFIED, RIL_PINSTATE_UNKNOWN }, - // ISIM_RESTRICTED = 20 - { RIL_APPTYPE_UNKNOWN, RIL_APPSTATE_UNKNOWN, RIL_PERSOSUBSTATE_UNKNOWN, - NULL, NULL, 0, RIL_PINSTATE_UNKNOWN, RIL_PINSTATE_UNKNOWN }, - }; - - RIL_CardState card_state; - int num_apps; - - SIM_Status sim_status = getSIMStatus(); - switch (sim_status) { - case SIM_ABSENT: - card_state = RIL_CARDSTATE_ABSENT; - num_apps = 0; - break; - - case SIM_RESTRICTED: - card_state = RIL_CARDSTATE_RESTRICTED; - num_apps = 0; - break; - - default: - card_state = RIL_CARDSTATE_PRESENT; - num_apps = 3; - break; - } - - // Allocate and initialize base card status. - RIL_CardStatus_v6 *p_card_status = malloc(sizeof(RIL_CardStatus_v6)); - p_card_status->card_state = card_state; - p_card_status->universal_pin_state = RIL_PINSTATE_UNKNOWN; - p_card_status->gsm_umts_subscription_app_index = -1; - p_card_status->cdma_subscription_app_index = -1; - p_card_status->ims_subscription_app_index = -1; - p_card_status->num_applications = num_apps; - - // Initialize application status - int i; - for (i = 0; i < RIL_CARD_MAX_APPS; i++) { - p_card_status->applications[i] = app_status_array[SIM_ABSENT]; - } - - // Pickup the appropriate application status - // that reflects sim_status for gsm. - if (num_apps != 0) { - p_card_status->num_applications = 3; - p_card_status->gsm_umts_subscription_app_index = 0; - p_card_status->cdma_subscription_app_index = 1; - p_card_status->ims_subscription_app_index = 2; - - // Get the correct app status - p_card_status->applications[0] = app_status_array[sim_status]; - p_card_status->applications[1] = app_status_array[sim_status + RUIM_ABSENT]; - p_card_status->applications[2] = app_status_array[sim_status + ISIM_ABSENT]; - } - - *pp_card_status = p_card_status; - return RIL_E_SUCCESS; -} - -/** - * Free the card status returned by getCardStatus - */ -static void freeCardStatus(RIL_CardStatus_v6 *p_card_status) { - free(p_card_status); -} - -/** - * SIM ready means any commands that access the SIM will work, including: - * AT+CPIN, AT+CSMS, AT+CNMI, AT+CRSM - * (all SMS-related commands) - */ - -static void pollSIMState (void *param __unused) -{ - ATResponse *p_response; - int ret; - - if (sState != RADIO_STATE_UNAVAILABLE) { - // no longer valid to poll - return; - } - - switch(getSIMStatus()) { - case SIM_ABSENT: - case SIM_PIN: - case SIM_PUK: - case SIM_NETWORK_PERSONALIZATION: - default: - RLOGI("SIM ABSENT or LOCKED"); - RIL_onUnsolicitedResponse(RIL_UNSOL_RESPONSE_SIM_STATUS_CHANGED, NULL, 0); - return; - - case SIM_NOT_READY: - RIL_requestTimedCallback (pollSIMState, NULL, &TIMEVAL_SIMPOLL); - return; - - case SIM_READY: - RLOGI("SIM_READY"); - onSIMReady(); - RIL_onUnsolicitedResponse(RIL_UNSOL_RESPONSE_SIM_STATUS_CHANGED, NULL, 0); - return; - } -} - -/** returns 1 if on, 0 if off, and -1 on error */ -static int isRadioOn() -{ - ATResponse *p_response = NULL; - int err; - char *line; - char ret; - - err = at_send_command_singleline("AT+CFUN?", "+CFUN:", &p_response); - - if (err < 0 || p_response->success == 0) { - // assume radio is off - goto error; - } - - line = p_response->p_intermediates->line; - - err = at_tok_start(&line); - if (err < 0) goto error; - - err = at_tok_nextbool(&line, &ret); - if (err < 0) goto error; - - at_response_free(p_response); - - return (int)ret; - -error: - - at_response_free(p_response); - return -1; -} - -/** - * Parse the response generated by a +CTEC AT command - * The values read from the response are stored in current and preferred. - * Both current and preferred may be null. The corresponding value is ignored in that case. - * - * @return: -1 if some error occurs (or if the modem doesn't understand the +CTEC command) - * 1 if the response includes the current technology only - * 0 if the response includes both current technology and preferred mode - */ -int parse_technology_response( const char *response, int *current, int32_t *preferred ) -{ - int err; - char *line, *p; - int ct; - int32_t pt = 0; - char *str_pt; - - line = p = strdup(response); - RLOGD("Response: %s", line); - err = at_tok_start(&p); - if (err || !at_tok_hasmore(&p)) { - RLOGD("err: %d. p: %s", err, p); - free(line); - return -1; - } - - err = at_tok_nextint(&p, &ct); - if (err) { - free(line); - return -1; - } - if (current) *current = ct; - - RLOGD("line remaining after int: %s", p); - - err = at_tok_nexthexint(&p, &pt); - if (err) { - free(line); - return 1; - } - if (preferred) { - *preferred = pt; - } - free(line); - - return 0; -} - -int query_supported_techs( ModemInfo *mdm __unused, int *supported ) -{ - ATResponse *p_response; - int err, val, techs = 0; - char *tok; - char *line; - - RLOGD("query_supported_techs"); - err = at_send_command_singleline("AT+CTEC=?", "+CTEC:", &p_response); - if (err || !p_response->success) - goto error; - line = p_response->p_intermediates->line; - err = at_tok_start(&line); - if (err || !at_tok_hasmore(&line)) - goto error; - while (!at_tok_nextint(&line, &val)) { - techs |= ( 1 << val ); - } - if (supported) *supported = techs; - return 0; -error: - at_response_free(p_response); - return -1; -} - -/** - * query_ctec. Send the +CTEC AT command to the modem to query the current - * and preferred modes. It leaves values in the addresses pointed to by - * current and preferred. If any of those pointers are NULL, the corresponding value - * is ignored, but the return value will still reflect if retreiving and parsing of the - * values suceeded. - * - * @mdm Currently unused - * @current A pointer to store the current mode returned by the modem. May be null. - * @preferred A pointer to store the preferred mode returned by the modem. May be null. - * @return -1 on error (or failure to parse) - * 1 if only the current mode was returned by modem (or failed to parse preferred) - * 0 if both current and preferred were returned correctly - */ -int query_ctec(ModemInfo *mdm __unused, int *current, int32_t *preferred) -{ - ATResponse *response = NULL; - int err; - int res; - - RLOGD("query_ctec. current: %p, preferred: %p", current, preferred); - err = at_send_command_singleline("AT+CTEC?", "+CTEC:", &response); - if (!err && response->success) { - res = parse_technology_response(response->p_intermediates->line, current, preferred); - at_response_free(response); - return res; - } - RLOGE("Error executing command: %d. response: %p. status: %d", err, response, response? response->success : -1); - at_response_free(response); - return -1; -} - -int is_multimode_modem(ModemInfo *mdm) -{ - ATResponse *response; - int err; - char *line; - int tech; - int32_t preferred; - - if (query_ctec(mdm, &tech, &preferred) == 0) { - mdm->currentTech = tech; - mdm->preferredNetworkMode = preferred; - if (query_supported_techs(mdm, &mdm->supportedTechs)) { - return 0; - } - return 1; - } - return 0; -} - -/** - * Find out if our modem is GSM, CDMA or both (Multimode) - */ -static void probeForModemMode(ModemInfo *info) -{ - ATResponse *response; - int err; - assert (info); - // Currently, our only known multimode modem is qemu's android modem, - // which implements the AT+CTEC command to query and set mode. - // Try that first - - if (is_multimode_modem(info)) { - RLOGI("Found Multimode Modem. Supported techs mask: %8.8x. Current tech: %d", - info->supportedTechs, info->currentTech); - return; - } - - /* Being here means that our modem is not multimode */ - info->isMultimode = 0; - - /* CDMA Modems implement the AT+WNAM command */ - err = at_send_command_singleline("AT+WNAM","+WNAM:", &response); - if (!err && response->success) { - at_response_free(response); - // TODO: find out if we really support EvDo - info->supportedTechs = MDM_CDMA | MDM_EVDO; - info->currentTech = MDM_CDMA; - RLOGI("Found CDMA Modem"); - return; - } - if (!err) at_response_free(response); - // TODO: find out if modem really supports WCDMA/LTE - info->supportedTechs = MDM_GSM | MDM_WCDMA | MDM_LTE; - info->currentTech = MDM_GSM; - RLOGI("Found GSM Modem"); -} - -/** - * Initialize everything that can be configured while we're still in - * AT+CFUN=0 - */ -static void initializeCallback(void *param __unused) -{ - ATResponse *p_response = NULL; - int err; - - setRadioState (RADIO_STATE_OFF); - - at_handshake(); - - probeForModemMode(sMdmInfo); - /* note: we don't check errors here. Everything important will - be handled in onATTimeout and onATReaderClosed */ - - /* atchannel is tolerant of echo but it must */ - /* have verbose result codes */ - at_send_command("ATE0Q0V1", NULL); - - /* No auto-answer */ - at_send_command("ATS0=0", NULL); - - /* Extended errors */ - at_send_command("AT+CMEE=1", NULL); - - /* Network registration events */ - err = at_send_command("AT+CREG=2", &p_response); - - /* some handsets -- in tethered mode -- don't support CREG=2 */ - if (err < 0 || p_response->success == 0) { - at_send_command("AT+CREG=1", NULL); - } - - at_response_free(p_response); - - /* GPRS registration events */ - at_send_command("AT+CGREG=1", NULL); - - /* Call Waiting notifications */ - at_send_command("AT+CCWA=1", NULL); - - /* Alternating voice/data off */ - at_send_command("AT+CMOD=0", NULL); - - /* Not muted */ - at_send_command("AT+CMUT=0", NULL); - - /* +CSSU unsolicited supp service notifications */ - at_send_command("AT+CSSN=0,1", NULL); - - /* no connected line identification */ - at_send_command("AT+COLP=0", NULL); - - /* HEX character set */ - at_send_command("AT+CSCS=\"HEX\"", NULL); - - /* USSD unsolicited */ - at_send_command("AT+CUSD=1", NULL); - - /* Enable +CGEV GPRS event notifications, but don't buffer */ - at_send_command("AT+CGEREP=1,0", NULL); - - /* SMS PDU mode */ - at_send_command("AT+CMGF=0", NULL); - -#ifdef USE_TI_COMMANDS - - at_send_command("AT%CPI=3", NULL); - - /* TI specific -- notifications when SMS is ready (currently ignored) */ - at_send_command("AT%CSTAT=1", NULL); - -#endif /* USE_TI_COMMANDS */ - - - /* assume radio is off on error */ - if (isRadioOn() > 0) { - setRadioState (RADIO_STATE_ON); - } -} - -static void waitForClose() -{ - pthread_mutex_lock(&s_state_mutex); - - while (s_closed == 0) { - pthread_cond_wait(&s_state_cond, &s_state_mutex); - } - - pthread_mutex_unlock(&s_state_mutex); -} - -static void sendUnsolImsNetworkStateChanged() -{ -#if 0 // to be used when unsol is changed to return data. - int reply[2]; - reply[0] = s_ims_registered; - reply[1] = s_ims_services; - reply[1] = s_ims_format; -#endif - RIL_onUnsolicitedResponse(RIL_UNSOL_RESPONSE_IMS_NETWORK_STATE_CHANGED, - NULL, 0); -} - -/** - * Called by atchannel when an unsolicited line appears - * This is called on atchannel's reader thread. AT commands may - * not be issued here - */ -static void onUnsolicited (const char *s, const char *sms_pdu) -{ - char *line = NULL, *p; - int err; - - /* Ignore unsolicited responses until we're initialized. - * This is OK because the RIL library will poll for initial state - */ - if (sState == RADIO_STATE_UNAVAILABLE) { - return; - } - -#define CGFPCCFG "%CGFPCCFG:" - if (strStartsWith(s, CGFPCCFG)) { - /* goldfish specific TODO: send phys channel cfg unsol - */ - char *response; - line = p = strdup(s); - RLOGD("got CGFPCCFG line %s and %s\n", s, p); - err = at_tok_start(&line); - if(err) { - RLOGE("invalid CGFPCCFG line %s and %s\n", s, p); - } -#define kSize 5 - int configs[kSize]; - for (int i=0; i < kSize && !err; ++i) { - err = at_tok_nextint(&line, &(configs[i])); - RLOGD("got i %d, val = %d", i, configs[i]); - } - if(err) { - RLOGE("invalid CGFPCCFG line %s and %s\n", s, p); - } else { - RIL_onUnsolicitedResponse ( - RIL_UNSOL_PHYSICAL_CHANNEL_CONFIGS, - configs, kSize); - } - free(p); - } else if (strStartsWith(s, "%CTZV:")) { - /* TI specific -- NITZ time */ - char *response; - - line = p = strdup(s); - at_tok_start(&p); - - err = at_tok_nextstr(&p, &response); - - if (err != 0) { - RLOGE("invalid NITZ line %s\n", s); - } else { - RIL_onUnsolicitedResponse ( - RIL_UNSOL_NITZ_TIME_RECEIVED, - response, strlen(response) + 1); - } - free(line); - } else if (strStartsWith(s,"+CRING:") - || strStartsWith(s,"RING") - || strStartsWith(s,"NO CARRIER") - || strStartsWith(s,"+CCWA") - ) { - RIL_onUnsolicitedResponse ( - RIL_UNSOL_RESPONSE_CALL_STATE_CHANGED, - NULL, 0); -#ifdef WORKAROUND_FAKE_CGEV - RIL_requestTimedCallback (onDataCallListChanged, NULL, NULL); //TODO use new function -#endif /* WORKAROUND_FAKE_CGEV */ - } else if (strStartsWith(s,"+CREG:") - || strStartsWith(s,"+CGREG:") - ) { - RIL_onUnsolicitedResponse ( - RIL_UNSOL_RESPONSE_VOICE_NETWORK_STATE_CHANGED, - NULL, 0); -#ifdef WORKAROUND_FAKE_CGEV - RIL_requestTimedCallback (onDataCallListChanged, NULL, NULL); -#endif /* WORKAROUND_FAKE_CGEV */ - } else if (strStartsWith(s, "+CMT:")) { - RIL_onUnsolicitedResponse ( - RIL_UNSOL_RESPONSE_NEW_SMS, - sms_pdu, strlen(sms_pdu)); - } else if (strStartsWith(s, "+CDS:")) { - RIL_onUnsolicitedResponse ( - RIL_UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT, - sms_pdu, strlen(sms_pdu)); - } else if (strStartsWith(s, "+CGEV:")) { - /* Really, we can ignore NW CLASS and ME CLASS events here, - * but right now we don't since extranous - * RIL_UNSOL_DATA_CALL_LIST_CHANGED calls are tolerated - */ - /* can't issue AT commands here -- call on main thread */ - RIL_requestTimedCallback (onDataCallListChanged, NULL, NULL); -#ifdef WORKAROUND_FAKE_CGEV - } else if (strStartsWith(s, "+CME ERROR: 150")) { - RIL_requestTimedCallback (onDataCallListChanged, NULL, NULL); -#endif /* WORKAROUND_FAKE_CGEV */ - } else if (strStartsWith(s, "+CTEC: ")) { - int tech, mask; - switch (parse_technology_response(s, &tech, NULL)) - { - case -1: // no argument could be parsed. - RLOGE("invalid CTEC line %s\n", s); - break; - case 1: // current mode correctly parsed - case 0: // preferred mode correctly parsed - mask = 1 << tech; - if (mask != MDM_GSM && mask != MDM_CDMA && - mask != MDM_WCDMA && mask != MDM_LTE) { - RLOGE("Unknown technology %d\n", tech); - } else { - setRadioTechnology(sMdmInfo, tech); - } - break; - } - } else if (strStartsWith(s, "+CCSS: ")) { - int source = 0; - line = p = strdup(s); - if (!line) { - RLOGE("+CCSS: Unable to allocate memory"); - return; - } - if (at_tok_start(&p) < 0) { - free(line); - return; - } - if (at_tok_nextint(&p, &source) < 0) { - RLOGE("invalid +CCSS response: %s", line); - free(line); - return; - } - SSOURCE(sMdmInfo) = source; - RIL_onUnsolicitedResponse(RIL_UNSOL_CDMA_SUBSCRIPTION_SOURCE_CHANGED, - &source, sizeof(source)); - } else if (strStartsWith(s, "+WSOS: ")) { - char state = 0; - int unsol; - line = p = strdup(s); - if (!line) { - RLOGE("+WSOS: Unable to allocate memory"); - return; - } - if (at_tok_start(&p) < 0) { - free(line); - return; - } - if (at_tok_nextbool(&p, &state) < 0) { - RLOGE("invalid +WSOS response: %s", line); - free(line); - return; - } - free(line); - - unsol = state ? - RIL_UNSOL_ENTER_EMERGENCY_CALLBACK_MODE : RIL_UNSOL_EXIT_EMERGENCY_CALLBACK_MODE; - - RIL_onUnsolicitedResponse(unsol, NULL, 0); - - } else if (strStartsWith(s, "+WPRL: ")) { - int version = -1; - line = p = strdup(s); - if (!line) { - RLOGE("+WPRL: Unable to allocate memory"); - return; - } - if (at_tok_start(&p) < 0) { - RLOGE("invalid +WPRL response: %s", s); - free(line); - return; - } - if (at_tok_nextint(&p, &version) < 0) { - RLOGE("invalid +WPRL response: %s", s); - free(line); - return; - } - free(line); - RIL_onUnsolicitedResponse(RIL_UNSOL_CDMA_PRL_CHANGED, &version, sizeof(version)); - } else if (strStartsWith(s, "+CFUN: 0")) { - setRadioState(RADIO_STATE_OFF); - } -} - -/* Called on command or reader thread */ -static void onATReaderClosed() -{ - RLOGI("AT channel closed\n"); - at_close(); - s_closed = 1; - - setRadioState (RADIO_STATE_UNAVAILABLE); -} - -/* Called on command thread */ -static void onATTimeout() -{ - RLOGI("AT channel timeout; closing\n"); - at_close(); - - s_closed = 1; - - /* FIXME cause a radio reset here */ - - setRadioState (RADIO_STATE_UNAVAILABLE); -} - -/* Called to pass hardware configuration information to telephony - * framework. - */ -static void setHardwareConfiguration(int num, RIL_HardwareConfig *cfg) -{ - RIL_onUnsolicitedResponse(RIL_UNSOL_HARDWARE_CONFIG_CHANGED, cfg, num*sizeof(*cfg)); -} - -static void usage(char *s __unused) -{ -#ifdef RIL_SHLIB - fprintf(stderr, "reference-ril requires: -p <tcp port> or -d /dev/tty_device\n"); -#else - fprintf(stderr, "usage: %s [-p <tcp port>] [-d /dev/tty_device]\n", s); - exit(-1); -#endif -} - -static void onInterfaceAddressChange(unsigned int ifIndex, - const struct ifAddress* addresses, - size_t numAddresses) { - char ifName[IF_NAMESIZE]; - size_t i; - bool hasWifi = hasWifiCapability(); - const char* radioIfName = getRadioInterfaceName(hasWifi); - char* currentLoc; - size_t remaining; - - if (if_indextoname(ifIndex, ifName) == NULL) { - RLOGE("Unable to get interface name for interface %u", ifIndex); - return; - } - if (strcmp(radioIfName, ifName) != 0) { - // This is not for the radio interface, ignore it - return; - } - - pthread_mutex_lock(&s_addresses_mutex); - // Clear out any existing addresses, we receive a full set of addresses - // that are going to replace the existing ones. - s_if_addresses[0] = '\0'; - currentLoc = s_if_addresses; - remaining = sizeof(s_if_addresses); - for (i = 0; i < numAddresses; ++i) { - char address[INET6_ADDRSTRLEN]; - if (inet_ntop(addresses[i].family, &addresses[i].addr, - address, sizeof(address))) { - int printed = 0; - if (s_if_addresses[0]) { - // We've already printed something, separate them - if (remaining < 1) { - continue; - } - *currentLoc++ = ' '; - --remaining; - } - printed = snprintf(currentLoc, remaining, "%s/%d", - address, addresses[i].prefix); - if (printed > 0) { - remaining -= (size_t)printed; - currentLoc += printed; - } - } else { - RLOGE("Unable to convert address to string for if %s", ifName); - } - } - pthread_mutex_unlock(&s_addresses_mutex); - - // Send unsolicited call list change to notify upper layers about the new - // addresses - requestOrSendDataCallList(NULL); -} - -static void onIpv6Change(const struct in6_addr* gateway, - const struct in6_addr* dnsServers, - size_t numDnsServers) { - char* dnsLoc = s_ipv6_dns; - size_t remaining = sizeof(s_ipv6_dns); - char address[INET6_ADDRSTRLEN]; - - pthread_mutex_lock(&s_addresses_mutex); - - inet_ntop(AF_INET6, gateway, s_ipv6_gateway, sizeof(s_ipv6_gateway)); - - s_ipv6_dns[0] = '\0'; - for (size_t i = 0; i < numDnsServers; ++i) { - if (inet_ntop(AF_INET6, &dnsServers[i], address, sizeof(address))) { - size_t len = strlcat(s_ipv6_dns, address, sizeof(s_ipv6_dns)); - if (i + 1 < numDnsServers && len + 1 < sizeof(s_ipv6_dns)) { - // There's more to come and there's room for more, separate - // multiple DNS servers by a space. - s_ipv6_dns[len] = ' '; - s_ipv6_dns[len + 1] = '\0'; - } - } - } - - pthread_mutex_unlock(&s_addresses_mutex); - - // Send unsolicited call list change to notify upper layers about the new - // addresses - requestOrSendDataCallList(NULL); -} - -static void * -mainLoop(void *param __unused) -{ - int fd; - int ret; - bool hasWifi = hasWifiCapability(); - const char* radioInterfaceName = getRadioInterfaceName(hasWifi); - struct ifMonitor* ifMonitor = ifMonitorCreate(); - struct ipv6Monitor* ipv6Monitor = ipv6MonitorCreate(radioInterfaceName); - - AT_DUMP("== ", "entering mainLoop()", -1 ); - at_set_on_reader_closed(onATReaderClosed); - at_set_on_timeout(onATTimeout); - - ifMonitorSetCallback(ifMonitor, &onInterfaceAddressChange); - ifMonitorRunAsync(ifMonitor); - - ipv6MonitorSetCallback(ipv6Monitor, &onIpv6Change); - ipv6MonitorRunAsync(ipv6Monitor); - - for (;;) { - fd = -1; - while (fd < 0) { - if (isInEmulator()) { - fd = qemud_channel_open("gsm"); - } else if (s_port > 0) { - fd = socket_network_client("localhost", s_port, SOCK_STREAM); - } else if (s_device_socket) { - fd = socket_local_client(s_device_path, - ANDROID_SOCKET_NAMESPACE_FILESYSTEM, - SOCK_STREAM); - } else if (s_device_path != NULL) { - fd = open (s_device_path, O_RDWR); - if ( fd >= 0 && !memcmp( s_device_path, "/dev/ttyS", 9 ) ) { - /* disable echo on serial ports */ - struct termios ios; - tcgetattr( fd, &ios ); - ios.c_lflag = 0; /* disable ECHO, ICANON, etc... */ - tcsetattr( fd, TCSANOW, &ios ); - } - } - - if (fd < 0) { - RLOGE("Error opening AT interface, retrying..."); - sleep(10); - /* never returns */ - } - } - - s_closed = 0; - - ret = at_open(fd, onUnsolicited); - if (ret < 0) { - RLOGE ("AT error %d on at_open\n", ret); - break; - } - - - RIL_requestTimedCallback(initializeCallback, NULL, &TIMEVAL_0); - - // Give initializeCallback a chance to dispatched, since - // we don't presently have a cancellation mechanism - sleep(1); - - waitForClose(); - RLOGI("Re-opening after close"); - } - - ifMonitorStop(ifMonitor); - ifMonitorFree(ifMonitor); - - ipv6MonitorStop(ipv6Monitor); - ipv6MonitorFree(ipv6Monitor); - - return NULL; -} - -#ifdef RIL_SHLIB - -pthread_t s_tid_mainloop; - -const RIL_RadioFunctions *RIL_Init(const struct RIL_Env *env, int argc, char **argv) -{ - int ret; - int fd = -1; - int opt; - pthread_attr_t attr; - - s_rilenv = env; - - while ( -1 != (opt = getopt(argc, argv, "p:d:s:c:"))) { - switch (opt) { - case 'p': - s_port = atoi(optarg); - if (s_port == 0) { - usage(argv[0]); - return NULL; - } - RLOGI("Opening loopback port %d\n", s_port); - break; - - case 'd': - s_device_path = optarg; - RLOGI("Opening tty device %s\n", s_device_path); - break; - - case 's': - s_device_path = optarg; - s_device_socket = 1; - RLOGI("Opening socket %s\n", s_device_path); - break; - - case 'c': - RLOGI("Client id received %s\n", optarg); - break; - - default: - usage(argv[0]); - return NULL; - } - } - - if (s_port < 0 && s_device_path == NULL && !isInEmulator()) { - usage(argv[0]); - return NULL; - } - - sMdmInfo = calloc(1, sizeof(ModemInfo)); - if (!sMdmInfo) { - RLOGE("Unable to alloc memory for ModemInfo"); - return NULL; - } - pthread_attr_init (&attr); - pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED); - ret = pthread_create(&s_tid_mainloop, &attr, mainLoop, NULL); - - return &s_callbacks; -} -#else /* RIL_SHLIB */ -int main (int argc, char **argv) -{ - int ret; - int fd = -1; - int opt; - - while ( -1 != (opt = getopt(argc, argv, "p:d:"))) { - switch (opt) { - case 'p': - s_port = atoi(optarg); - if (s_port == 0) { - usage(argv[0]); - } - RLOGI("Opening loopback port %d\n", s_port); - break; - - case 'd': - s_device_path = optarg; - RLOGI("Opening tty device %s\n", s_device_path); - break; - - case 's': - s_device_path = optarg; - s_device_socket = 1; - RLOGI("Opening socket %s\n", s_device_path); - break; - - default: - usage(argv[0]); - } - } - - if (s_port < 0 && s_device_path == NULL && !isInEmulator()) { - usage(argv[0]); - } - - RIL_register(&s_callbacks); - - mainLoop(NULL); - - return 0; -} - -#endif /* RIL_SHLIB */ diff --git a/radio/rild/Android.mk b/radio/rild/Android.mk index 8dc5cde0..13bc7a5e 100644 --- a/radio/rild/Android.mk +++ b/radio/rild/Android.mk @@ -12,11 +12,11 @@ LOCAL_SHARED_LIBRARIES := \ libcutils \ libdl \ liblog \ - libril-goldfish-fork + libril-modem-lib # Temporary hack for broken vendor RILs. LOCAL_WHOLE_STATIC_LIBRARIES := \ - librilutils + librilutils-goldfish-fork LOCAL_CFLAGS := -DRIL_SHLIB LOCAL_CFLAGS += -Wall -Wextra -Werror @@ -30,6 +30,9 @@ LOCAL_MODULE_RELATIVE_PATH := hw LOCAL_PROPRIETARY_MODULE := true #LOCAL_MODULE:= rild LOCAL_MODULE:= libgoldfish-rild +LOCAL_LICENSE_KINDS:= SPDX-license-identifier-Apache-2.0 +LOCAL_LICENSE_CONDITIONS:= notice +LOCAL_NOTICE_FILE:= $(LOCAL_PATH)/NOTICE LOCAL_OVERRIDES_PACKAGES := rild PACKAGES.$(LOCAL_MODULE).OVERRIDES := rild ifeq ($(PRODUCT_COMPATIBLE_PROPERTY),true) diff --git a/radio/rild/rild_goldfish.c b/radio/rild/rild_goldfish.c index 781db785..f50db36c 100644 --- a/radio/rild/rild_goldfish.c +++ b/radio/rild/rild_goldfish.c @@ -163,6 +163,9 @@ int main(int argc, char **argv) { } } + // force to use libcuttlefish-ril-2.so + rilLibPath = "libcuttlefish-ril-2.so"; + dlHandle = dlopen(rilLibPath, RTLD_NOW); if (dlHandle == NULL) { @@ -170,6 +173,8 @@ int main(int argc, char **argv) { exit(EXIT_FAILURE); } + RLOGI("dlopen good: %s", rilLibPath); + RIL_startEventLoop(); rilInit = diff --git a/rro_overlays/TetheringOverlay/Android.bp b/rro_overlays/TetheringOverlay/Android.bp new file mode 100644 index 00000000..1b1318c5 --- /dev/null +++ b/rro_overlays/TetheringOverlay/Android.bp @@ -0,0 +1,32 @@ +// +// Copyright (C) 2020 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 { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + // SPDX-license-identifier-BSD + default_applicable_licenses: ["device_generic_goldfish_license"], +} + +runtime_resource_overlay { + name: "EmulatorTetheringConfigOverlay", + resource_dirs: ["res"], + product_specific: true, + sdk_version: "current", +} diff --git a/rro_overlays/TetheringOverlay/AndroidManifest.xml b/rro_overlays/TetheringOverlay/AndroidManifest.xml new file mode 100644 index 00000000..fc8c8bd0 --- /dev/null +++ b/rro_overlays/TetheringOverlay/AndroidManifest.xml @@ -0,0 +1,11 @@ +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.networkstack.tethering.emulator" + android:versionCode="1" + android:versionName="1.0"> + <application android:hasCode="false" /> + <overlay + android:targetPackage="com.android.networkstack.tethering" + android:targetName="TetheringConfig" + android:isStatic="true" + android:priority="0"/> +</manifest> diff --git a/rro_overlays/TetheringOverlay/res/values/config.xml b/rro_overlays/TetheringOverlay/res/values/config.xml new file mode 100644 index 00000000..e3037685 --- /dev/null +++ b/rro_overlays/TetheringOverlay/res/values/config.xml @@ -0,0 +1,30 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* +** Copyright 2020, 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. +*/ +--> + +<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> + <!-- Allow testing SoftAP using the simulated interfaces on the emulator. --> + <string-array name="config_tether_wifi_regexs"> + <item>"wlan\\d"</item> + </string-array> + <string-array name="config_tether_wifi_p2p_regexs"> + <item>"p2p-wlan\\d-.*"</item> + <item>"p2p\\d"</item> + <item>"p2p-p2p\\d-.*"</item> + </string-array> +</resources> diff --git a/sdk_phone_x86_vendor.mk b/sdk_phone_x86_vendor.mk index 7c460683..501fc175 100644 --- a/sdk_phone_x86_vendor.mk +++ b/sdk_phone_x86_vendor.mk @@ -15,11 +15,11 @@ PRODUCT_PROPERTY_OVERRIDES := \ # Emulator for vendor $(call inherit-product-if-exists, device/generic/goldfish/x86-vendor.mk) $(call inherit-product, $(SRC_TARGET_DIR)/product/emulator_vendor.mk) -$(call inherit-product, $(SRC_TARGET_DIR)/board/generic_x86/device.mk) +$(call inherit-product, $(SRC_TARGET_DIR)/board/emulator_x86/device.mk) # Overrides PRODUCT_BRAND := google PRODUCT_MANUFACTURER := Google PRODUCT_NAME := sdk_phone_x86_vendor -PRODUCT_DEVICE := generic_x86 +PRODUCT_DEVICE := emulator_x86 PRODUCT_MODEL := Android SDK built for x86 diff --git a/sensors/Android.bp b/sensors/Android.bp index f6040f05..c86ecebc 100644 --- a/sensors/Android.bp +++ b/sensors/Android.bp @@ -14,6 +14,15 @@ * limitations under the License. */ +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_shared { name: "android.hardware.sensors@2.1-impl.ranchu", vendor: true, diff --git a/sensors/multihal_sensors.cpp b/sensors/multihal_sensors.cpp index 3502add9..38bf730b 100644 --- a/sensors/multihal_sensors.cpp +++ b/sensors/multihal_sensors.cpp @@ -24,9 +24,12 @@ namespace goldfish { using ahs21::SensorType; using ahs10::SensorFlagBits; +using ahs10::SensorStatus; using ahs10::MetaDataEventType; -MultihalSensors::MultihalSensors() : m_qemuSensorsFd(qemud_channel_open("sensors")) { +MultihalSensors::MultihalSensors() + : m_qemuSensorsFd(qemud_channel_open("sensors")) + , m_batchInfo(getSensorNumber()) { if (!m_qemuSensorsFd.ok()) { ALOGE("%s:%d: m_qemuSensorsFd is not opened", __func__, __LINE__); ::abort(); @@ -56,13 +59,16 @@ MultihalSensors::MultihalSensors() : m_qemuSensorsFd(qemud_channel_open("sensors ::abort(); } buffer[len] = 0; - uint32_t availableSensorsMask = 0; - if (sscanf(buffer, "%u", &availableSensorsMask) != 1) { + uint32_t hostSensorsMask = 0; + if (sscanf(buffer, "%u", &hostSensorsMask) != 1) { ALOGE("%s:%d: Can't parse qemud response", __func__, __LINE__); ::abort(); } m_availableSensorsMask = - availableSensorsMask & ((1u << getSensorNumber()) - 1); + hostSensorsMask & ((1u << getSensorNumber()) - 1); + + ALOGI("%s:%d: host sensors mask=%x, available sensors mask=%x", + __func__, __LINE__, hostSensorsMask, m_availableSensorsMask); if (!::android::base::Socketpair(AF_LOCAL, SOCK_STREAM, 0, &m_callersFd, &m_sensorThreadFd)) { @@ -70,11 +76,17 @@ MultihalSensors::MultihalSensors() : m_qemuSensorsFd(qemud_channel_open("sensors ::abort(); } - m_sensorThread = std::thread(qemuSensorListenerThreadStart, this); + m_sensorThread = std::thread(&MultihalSensors::qemuSensorListenerThread, this); + m_batchThread = std::thread(&MultihalSensors::batchThread, this); } MultihalSensors::~MultihalSensors() { - disableAllSensors(); + setAllQemuSensors(false); + + m_batchRunning = false; + m_batchUpdated.notify_one(); + m_batchThread.join(); + qemuSensorThreadSendCommand(kCMD_QUIT); m_sensorThread.join(); } @@ -104,7 +116,7 @@ Return<void> MultihalSensors::getSensorsList_2_1(getSensorsList_2_1_cb _hidl_cb) } Return<Result> MultihalSensors::setOperationMode(const OperationMode mode) { - std::unique_lock<std::mutex> lock(m_apiMtx); + std::unique_lock<std::mutex> lock(m_mtx); if (m_activeSensorsMask) { return Result::INVALID_OPERATION; @@ -120,25 +132,41 @@ Return<Result> MultihalSensors::activate(const int32_t sensorHandle, return Result::BAD_VALUE; } - std::unique_lock<std::mutex> lock(m_apiMtx); + std::unique_lock<std::mutex> lock(m_mtx); + BatchInfo& batchInfo = m_batchInfo[sensorHandle]; - uint32_t newActiveMask; if (enabled) { - newActiveMask = m_activeSensorsMask | (1u << sensorHandle); - } else { - newActiveMask = m_activeSensorsMask & ~(1u << sensorHandle); - } - if (m_activeSensorsMask == newActiveMask) { - return Result::OK; - } - - if (m_opMode == OperationMode::NORMAL) { - if (!activateQemuSensorImpl(m_qemuSensorsFd.get(), sensorHandle, enabled)) { - return Result::INVALID_OPERATION; + const SensorInfo* sensor = getSensorInfoByHandle(sensorHandle); + LOG_ALWAYS_FATAL_IF(!sensor); + if (!(sensor->flags & static_cast<uint32_t>(SensorFlagBits::ON_CHANGE_MODE))) { + if (batchInfo.samplingPeriodNs <= 0) { + return Result::BAD_VALUE; + } + + BatchEventRef batchEventRef; + batchEventRef.timestamp = + ::android::elapsedRealtimeNano() + batchInfo.samplingPeriodNs; + batchEventRef.sensorHandle = sensorHandle; + batchEventRef.generation = ++batchInfo.generation; + + m_batchQueue.push(batchEventRef); + m_batchUpdated.notify_one(); + } else if (sensor->type == SensorType::HEART_RATE){ + // Heart rate sensor's first data after activation should be + // SENSOR_STATUS_UNRELIABLE. + Event event; + event.u.heartRate.status = SensorStatus::UNRELIABLE; + event.u.heartRate.bpm = 0; + event.timestamp = ::android::elapsedRealtimeNano(); + event.sensorHandle = sensorHandle; + event.sensorType = SensorType::HEART_RATE; + doPostSensorEventLocked(*sensor, event); } - } - m_activeSensorsMask = newActiveMask; + m_activeSensorsMask = m_activeSensorsMask | (1u << sensorHandle); + } else { + m_activeSensorsMask = m_activeSensorsMask & ~(1u << sensorHandle); + } return Result::OK; } @@ -147,26 +175,35 @@ Return<Result> MultihalSensors::batch(const int32_t sensorHandle, const int64_t maxReportLatencyNs) { (void)maxReportLatencyNs; + if (!isSensorHandleValid(sensorHandle)) { + return Result::BAD_VALUE; + } + const SensorInfo* sensor = getSensorInfoByHandle(sensorHandle); - if (sensor) { - if (samplingPeriodNs >= sensor->minDelay) { - return Result::OK; - } else { - return Result::BAD_VALUE; - } - } else { + LOG_ALWAYS_FATAL_IF(!sensor); + + if (samplingPeriodNs < sensor->minDelay) { return Result::BAD_VALUE; } + + std::unique_lock<std::mutex> lock(m_mtx); + if (m_opMode == OperationMode::NORMAL) { + m_batchInfo[sensorHandle].samplingPeriodNs = samplingPeriodNs; + } + + return Result::OK; } Return<Result> MultihalSensors::flush(const int32_t sensorHandle) { - const SensorInfo* sensor = getSensorInfoByHandle(sensorHandle); - if (!sensor) { + if (!isSensorHandleValid(sensorHandle)) { return Result::BAD_VALUE; } - std::unique_lock<std::mutex> lock(m_apiMtx); - if (!(m_activeSensorsMask & (1u << sensorHandle))) { + const SensorInfo* sensor = getSensorInfoByHandle(sensorHandle); + LOG_ALWAYS_FATAL_IF(!sensor); + + std::unique_lock<std::mutex> lock(m_mtx); + if (!isSensorActive(sensorHandle)) { return Result::BAD_VALUE; } @@ -175,48 +212,58 @@ Return<Result> MultihalSensors::flush(const int32_t sensorHandle) { event.sensorType = SensorType::META_DATA; event.u.meta.what = MetaDataEventType::META_DATA_FLUSH_COMPLETE; - postSensorEventLocked(event); + doPostSensorEventLocked(*sensor, event); return Result::OK; } Return<Result> MultihalSensors::injectSensorData_2_1(const Event& event) { + if (!isSensorHandleValid(event.sensorHandle)) { + return Result::BAD_VALUE; + } if (event.sensorType == SensorType::ADDITIONAL_INFO) { return Result::OK; } - std::unique_lock<std::mutex> lock(m_apiMtx); + std::unique_lock<std::mutex> lock(m_mtx); if (m_opMode != OperationMode::DATA_INJECTION) { return Result::INVALID_OPERATION; } const SensorInfo* sensor = getSensorInfoByHandle(event.sensorHandle); - if (!sensor) { - return Result::BAD_VALUE; - } + LOG_ALWAYS_FATAL_IF(!sensor); if (sensor->type != event.sensorType) { return Result::BAD_VALUE; } - postSensorEventLocked(event); + doPostSensorEventLocked(*sensor, event); return Result::OK; } Return<Result> MultihalSensors::initialize(const sp<IHalProxyCallback>& halProxyCallback) { - std::unique_lock<std::mutex> lock(m_apiMtx); - disableAllSensors(); + std::unique_lock<std::mutex> lock(m_mtx); + setAllQemuSensors(true); // we need to start sampling sensors for batching m_opMode = OperationMode::NORMAL; m_halProxyCallback = halProxyCallback; return Result::OK; } void MultihalSensors::postSensorEvent(const Event& event) { - std::unique_lock<std::mutex> lock(m_apiMtx); - postSensorEventLocked(event); + const SensorInfo* sensor = getSensorInfoByHandle(event.sensorHandle); + LOG_ALWAYS_FATAL_IF(!sensor); + + std::unique_lock<std::mutex> lock(m_mtx); + if (sensor->flags & static_cast<uint32_t>(SensorFlagBits::ON_CHANGE_MODE)) { + if (isSensorActive(event.sensorHandle)) { + doPostSensorEventLocked(*sensor, event); + } + } else { // CONTINUOUS_MODE + m_batchInfo[event.sensorHandle].event = event; + } } -void MultihalSensors::postSensorEventLocked(const Event& event) { +void MultihalSensors::doPostSensorEventLocked(const SensorInfo& sensor, + const Event& event) { const bool isWakeupEvent = - getSensorInfoByHandle(event.sensorHandle)->flags & - static_cast<uint32_t>(SensorFlagBits::WAKE_UP); + sensor.flags & static_cast<uint32_t>(SensorFlagBits::WAKE_UP); m_halProxyCallback->postEvents( {event}, @@ -227,6 +274,62 @@ bool MultihalSensors::qemuSensorThreadSendCommand(const char cmd) const { return TEMP_FAILURE_RETRY(write(m_callersFd.get(), &cmd, 1)) == 1; } +bool MultihalSensors::isSensorHandleValid(int sensorHandle) const { + if (!goldfish::isSensorHandleValid(sensorHandle)) { + return false; + } + + if (!(m_availableSensorsMask & (1u << sensorHandle))) { + return false; + } + + return true; +} + +void MultihalSensors::batchThread() { + while (m_batchRunning) { + std::unique_lock<std::mutex> lock(m_mtx); + if (m_batchQueue.empty()) { + m_batchUpdated.wait(lock); + } else { + const int64_t d = + m_batchQueue.top().timestamp - ::android::elapsedRealtimeNano(); + m_batchUpdated.wait_for(lock, std::chrono::nanoseconds(d)); + } + + const int64_t nowNs = ::android::elapsedRealtimeNano(); + while (!m_batchQueue.empty() && (nowNs >= m_batchQueue.top().timestamp)) { + BatchEventRef evRef = m_batchQueue.top(); + m_batchQueue.pop(); + + const int sensorHandle = evRef.sensorHandle; + LOG_ALWAYS_FATAL_IF(!goldfish::isSensorHandleValid(sensorHandle)); + if (!isSensorActive(sensorHandle)) { + continue; + } + + BatchInfo &batchInfo = m_batchInfo[sensorHandle]; + if (batchInfo.event.sensorType == SensorType::META_DATA) { + ALOGW("%s:%d the host has not provided value yet for sensorHandle=%d", + __func__, __LINE__, sensorHandle); + } else { + batchInfo.event.timestamp = evRef.timestamp; + const SensorInfo* sensor = getSensorInfoByHandle(sensorHandle); + LOG_ALWAYS_FATAL_IF(!sensor); + doPostSensorEventLocked(*sensor, batchInfo.event); + } + + if (evRef.generation == batchInfo.generation) { + const int64_t samplingPeriodNs = batchInfo.samplingPeriodNs; + LOG_ALWAYS_FATAL_IF(samplingPeriodNs <= 0); + + evRef.timestamp += samplingPeriodNs; + m_batchQueue.push(evRef); + } + } + } +} + /// not supported ////////////////////////////////////////////////////////////// Return<void> MultihalSensors::registerDirectChannel(const SharedMemInfo& mem, registerDirectChannel_cb _hidl_cb) { diff --git a/sensors/multihal_sensors.h b/sensors/multihal_sensors.h index 80ed6a3b..91cde715 100644 --- a/sensors/multihal_sensors.h +++ b/sensors/multihal_sensors.h @@ -17,8 +17,12 @@ #pragma once #include <android-base/unique_fd.h> #include <V2_1/SubHal.h> +#include <atomic> +#include <condition_variable> #include <cstdint> +#include <queue> #include <thread> +#include <vector> namespace goldfish { namespace ahs = ::android::hardware::sensors; @@ -26,6 +30,7 @@ namespace ahs21 = ahs::V2_1; namespace ahs10 = ahs::V1_0; using ahs21::implementation::IHalProxyCallback; +using ahs21::SensorInfo; using ahs21::Event; using ahs10::OperationMode; using ahs10::RateLevel; @@ -79,16 +84,21 @@ private: float lastHingeAngle0Value = kSensorNoValue; float lastHingeAngle1Value = kSensorNoValue; float lastHingeAngle2Value = kSensorNoValue; + float lastHeartRateValue = kSensorNoValue; }; + bool isSensorHandleValid(int sensorHandle) const; + bool isSensorActive(int sensorHandle) const { + return m_activeSensorsMask & (1u << sensorHandle); // m_mtx required + } static bool activateQemuSensorImpl(int pipe, int sensorHandle, bool enabled); - bool disableAllSensors(); + bool setAllQemuSensors(bool enabled); void parseQemuSensorEvent(const int pipe, QemuSensorsProtocolState* state); void postSensorEvent(const Event& event); - void postSensorEventLocked(const Event& event); + void doPostSensorEventLocked(const SensorInfo& sensor, const Event& event); void qemuSensorListenerThread(); - static void qemuSensorListenerThreadStart(MultihalSensors* that); + void batchThread(); static constexpr char kCMD_QUIT = 'q'; bool qemuSensorThreadSendCommand(char cmd) const; @@ -105,7 +115,32 @@ private: uint32_t m_activeSensorsMask = 0; OperationMode m_opMode = OperationMode::NORMAL; sp<IHalProxyCallback> m_halProxyCallback; - mutable std::mutex m_apiMtx; + + // batching + struct BatchEventRef { + int64_t timestamp = -1; + int sensorHandle = -1; + int generation = 0; + + bool operator<(const BatchEventRef &rhs) const { + // not a typo, we want m_batchQueue.top() to be the smallest timestamp + return timestamp > rhs.timestamp; + } + }; + + struct BatchInfo { + Event event; + int64_t samplingPeriodNs = 0; + int generation = 0; + }; + + std::priority_queue<BatchEventRef> m_batchQueue; + std::vector<BatchInfo> m_batchInfo; + std::condition_variable m_batchUpdated; + std::thread m_batchThread; + std::atomic<bool> m_batchRunning = true; + + mutable std::mutex m_mtx; }; } // namespace goldfish diff --git a/sensors/multihal_sensors_epoll.cpp b/sensors/multihal_sensors_epoll.cpp index 0be12245..cf2ae56b 100644 --- a/sensors/multihal_sensors_epoll.cpp +++ b/sensors/multihal_sensors_epoll.cpp @@ -38,10 +38,6 @@ int qemuSensortThreadRcvCommand(const int fd) { } } // namespace -void MultihalSensors::qemuSensorListenerThreadStart(MultihalSensors* that) { - that->qemuSensorListenerThread(); -} - void MultihalSensors::qemuSensorListenerThread() { const unique_fd epollFd(epoll_create1(0)); if (!epollFd.ok()) { diff --git a/sensors/multihal_sensors_qemu.cpp b/sensors/multihal_sensors_qemu.cpp index a07d569b..10bd162d 100644 --- a/sensors/multihal_sensors_qemu.cpp +++ b/sensors/multihal_sensors_qemu.cpp @@ -69,19 +69,16 @@ bool MultihalSensors::activateQemuSensorImpl(const int pipe, } } -bool MultihalSensors::disableAllSensors() { - if (m_opMode == OperationMode::NORMAL) { - uint32_t mask = m_activeSensorsMask; - for (int i = 0; mask; ++i, mask >>= 1) { - if (mask & 1) { - if (!activateQemuSensorImpl(m_qemuSensorsFd.get(), i, false)) { - return false; - } +bool MultihalSensors::setAllQemuSensors(const bool enabled) { + uint32_t mask = m_availableSensorsMask; + for (int i = 0; mask; ++i, mask >>= 1) { + if (mask & 1) { + if (!activateQemuSensorImpl(m_qemuSensorsFd.get(), i, enabled)) { + return false; } } } - m_activeSensorsMask = 0; return true; } @@ -258,6 +255,19 @@ void MultihalSensors::parseQemuSensorEvent(const int pipe, } parsed = true; } + } else if (const char* values = testPrefix(buf, end, "heart-rate", ':')) { + if (sscanf(values, "%f", &payload->heartRate.bpm) == 1) { + if (!approximatelyEqual(state->lastHeartRateValue, + payload->heartRate.bpm, 0.001)) { + payload->heartRate.status = SensorStatus::ACCURACY_HIGH; + event.timestamp = nowNs + state->timeBiasNs; + event.sensorHandle = kSensorHandleHeartRate; + event.sensorType = SensorType::HEART_RATE; + postSensorEvent(event); + state->lastHeartRateValue = payload->heartRate.bpm; + } + parsed = true; + } } else if (const char* values = testPrefix(buf, end, "guest-sync", ':')) { long long value; if ((sscanf(values, "%lld", &value) == 1) && (value >= 0)) { diff --git a/sensors/sensor_list.cpp b/sensors/sensor_list.cpp index 245379fa..c5a374cb 100644 --- a/sensors/sensor_list.cpp +++ b/sensors/sensor_list.cpp @@ -37,6 +37,7 @@ const char* const kQemuSensorName[] = { "hinge-angle0", "hinge-angle1", "hinge-angle2", + "heart-rate", }; const SensorInfo kAllSensors[] = { @@ -122,11 +123,11 @@ const SensorInfo kAllSensors[] = { .maxRange = 80.0, .resolution = 1.0, .power = 0.0, - .minDelay = 10000, + .minDelay = 0, .fifoReservedEventCount = 0, .fifoMaxEventCount = 0, .requiredPermission = "", - .maxDelay = 500000, + .maxDelay = 0, .flags = SensorFlagBits::DATA_INJECTION | SensorFlagBits::ON_CHANGE_MODE }, @@ -140,11 +141,11 @@ const SensorInfo kAllSensors[] = { .maxRange = 1.0, .resolution = 1.0, .power = 20.0, - .minDelay = 10000, + .minDelay = 0, .fifoReservedEventCount = 0, .fifoMaxEventCount = 0, .requiredPermission = "", - .maxDelay = 500000, + .maxDelay = 0, .flags = SensorFlagBits::DATA_INJECTION | SensorFlagBits::ON_CHANGE_MODE | SensorFlagBits::WAKE_UP @@ -159,11 +160,11 @@ const SensorInfo kAllSensors[] = { .maxRange = 40000.0, .resolution = 1.0, .power = 20.0, - .minDelay = 10000, + .minDelay = 0, .fifoReservedEventCount = 0, .fifoMaxEventCount = 0, .requiredPermission = "", - .maxDelay = 500000, + .maxDelay = 0, .flags = SensorFlagBits::DATA_INJECTION | SensorFlagBits::ON_CHANGE_MODE }, @@ -195,11 +196,11 @@ const SensorInfo kAllSensors[] = { .maxRange = 100.0, .resolution = 1.0, .power = 20.0, - .minDelay = 10000, + .minDelay = 0, .fifoReservedEventCount = 0, .fifoMaxEventCount = 0, .requiredPermission = "", - .maxDelay = 500000, + .maxDelay = 0, .flags = SensorFlagBits::DATA_INJECTION | SensorFlagBits::ON_CHANGE_MODE }, @@ -248,11 +249,11 @@ const SensorInfo kAllSensors[] = { .maxRange = 360, .resolution = 1.0, .power = 3.0, - .minDelay = 10000, + .minDelay = 0, .fifoReservedEventCount = 0, .fifoMaxEventCount = 0, .requiredPermission = "", - .maxDelay = 500000, + .maxDelay = 0, .flags = SensorFlagBits::DATA_INJECTION | SensorFlagBits::ON_CHANGE_MODE | SensorFlagBits::WAKE_UP @@ -267,11 +268,11 @@ const SensorInfo kAllSensors[] = { .maxRange = 360, .resolution = 1.0, .power = 3.0, - .minDelay = 10000, + .minDelay = 0, .fifoReservedEventCount = 0, .fifoMaxEventCount = 0, .requiredPermission = "", - .maxDelay = 500000, + .maxDelay = 0, .flags = SensorFlagBits::DATA_INJECTION | SensorFlagBits::ON_CHANGE_MODE | SensorFlagBits::WAKE_UP @@ -286,14 +287,32 @@ const SensorInfo kAllSensors[] = { .maxRange = 360, .resolution = 1.0, .power = 3.0, - .minDelay = 10000, + .minDelay = 0, .fifoReservedEventCount = 0, .fifoMaxEventCount = 0, .requiredPermission = "", - .maxDelay = 500000, + .maxDelay = 0, .flags = SensorFlagBits::DATA_INJECTION | SensorFlagBits::ON_CHANGE_MODE | SensorFlagBits::WAKE_UP + }, + { + .sensorHandle = kSensorHandleHeartRate, + .name = "Goldfish Heart rate sensor", + .vendor = kAospVendor, + .version = 1, + .type = SensorType::HEART_RATE, + .typeAsString = "android.sensor.heart_rate", + .maxRange = 500.0, + .resolution = 1.0, + .power = 20.0, + .minDelay = 0, + .fifoReservedEventCount = 0, + .fifoMaxEventCount = 0, + .requiredPermission = "android.permission.BODY_SENSORS", + .maxDelay = 500000, + .flags = SensorFlagBits::DATA_INJECTION | + SensorFlagBits::ON_CHANGE_MODE }}; constexpr int kSensorNumber = sizeof(kAllSensors) / sizeof(kAllSensors[0]); diff --git a/sensors/sensor_list.h b/sensors/sensor_list.h index b74fce9c..ee7950ba 100644 --- a/sensors/sensor_list.h +++ b/sensors/sensor_list.h @@ -36,6 +36,7 @@ constexpr int kSensorHandleGyroscopeFieldUncalibrated = 10; constexpr int kSensorHandleHingeAngle0 = 11; constexpr int kSensorHandleHingeAngle1 = 12; constexpr int kSensorHandleHingeAngle2 = 13; +constexpr int kSensorHandleHeartRate = 14; int getSensorNumber(); bool isSensorHandleValid(int h); diff --git a/sepolicy/OWNERS b/sepolicy/OWNERS new file mode 100644 index 00000000..6dc2b867 --- /dev/null +++ b/sepolicy/OWNERS @@ -0,0 +1 @@ +include platform/system/sepolicy:/OWNERS diff --git a/sepolicy/common/OWNERS b/sepolicy/common/OWNERS index e6fbbd47..bbe0cccc 100644 --- a/sepolicy/common/OWNERS +++ b/sepolicy/common/OWNERS @@ -5,5 +5,4 @@ jeffv@google.com jgalenson@google.com nnk@google.com sspatil@google.com -tomcherry@google.com trong@google.com diff --git a/sepolicy/common/adbd.te b/sepolicy/common/adbd.te index 9546c1a4..6835639e 100644 --- a/sepolicy/common/adbd.te +++ b/sepolicy/common/adbd.te @@ -1 +1,4 @@ set_prop(adbd, ctl_mdnsd_prop); + +allow adbd self:vsock_socket { create_socket_perms_no_ioctl listen accept }; +allow adbd unlabeled:vsock_socket rw_socket_perms_no_ioctl; diff --git a/sepolicy/common/bootanim.te b/sepolicy/common/bootanim.te index 4d011e10..3a5a7802 100644 --- a/sepolicy/common/bootanim.te +++ b/sepolicy/common/bootanim.te @@ -5,6 +5,5 @@ dontaudit bootanim system_data_file:dir read; allow bootanim graphics_device:chr_file { read ioctl open }; allow bootanim gpu_device:chr_file { read ioctl open }; - -typeattribute bootanim system_writes_vendor_properties_violators; -set_prop(bootanim, qemu_prop) +allow bootanim self:vsock_socket create_socket_perms_no_ioctl; +allow bootanim hal_graphics_allocator_default:vsock_socket { read write getattr }; diff --git a/sepolicy/common/bug_map b/sepolicy/common/bug_map index 2174a4d2..0d26fca6 100644 --- a/sepolicy/common/bug_map +++ b/sepolicy/common/bug_map @@ -1,19 +1,8 @@ -gsid gsid capability b/146356992 -hal_wifi_default default_prop file b/131598173 -hal_wifi_default vendor_default_prop property_service b/131598173 -init unlabeled dir b/131596633 -init vendor_toolbox_exec file b/132695863 -installd device file b/131595213 -kernel kernel system b/131597442 -netd device file b/131598170 -platform_app vendor_default_prop file b/130684647 -priv_app property_socket sock_file b/131598844 -priv_app varrun_file dir b/131598844 -storaged device file b/131598843 -toolbox unlabeled dir b/131599097 -toolbox toolbox capability b/131599097 -ueventd metadata_file dir b/131594529 -vendor_init exported2_default_prop property_service b/131601458 -init serial_device chr_file b/134145307 -gsid device file b/133324244 -gmscore_app varrun_file dir b/131598844 +init vendor_toolbox_exec file b/183668221 +toolbox dropbox_data_file dir b/183668221 +toolbox heapdump_data_file dir b/183668221 +toolbox system_unsolzygote_socket sock_file b/183668221 +toolbox packages_list_file file b/183668221 +toolbox environ_system_data_file dir b/183668221 +toolbox system_ndebug_socket sock_file b/183668221 +toolbox unlabeled dir b/183668221 diff --git a/sepolicy/common/cameraserver.te b/sepolicy/common/cameraserver.te index 6cf5d6ae..148afacc 100644 --- a/sepolicy/common/cameraserver.te +++ b/sepolicy/common/cameraserver.te @@ -1,2 +1,3 @@ allow cameraserver system_file:dir { open read }; allow cameraserver hal_allocator:fd use; +allow cameraserver gpu_device:chr_file { open read write ioctl }; diff --git a/sepolicy/common/createns.te b/sepolicy/common/createns.te index 1eaf9ef5..4464ddb7 100644 --- a/sepolicy/common/createns.te +++ b/sepolicy/common/createns.te @@ -9,6 +9,7 @@ allow createns varrun_file:dir { add_name search write }; allow createns varrun_file:file { create mounton open read write }; #Allow createns itself to be run by init in its own domain -domain_auto_trans(goldfish_setup, createns_exec, createns); +domain_auto_trans(init, createns_exec, createns); allow createns goldfish_setup:fd use; +set_prop(createns, vendor_qemu_prop); diff --git a/sepolicy/common/dhcpclient.te b/sepolicy/common/dhcpclient.te index a0d7e604..8e22a7ac 100644 --- a/sepolicy/common/dhcpclient.te +++ b/sepolicy/common/dhcpclient.te @@ -7,11 +7,10 @@ net_domain(dhcpclient) allow dhcpclient execns:fd use; -set_prop(dhcpclient, net_wlan0_prop); -set_prop(dhcpclient, net_eth0_prop); -set_prop(dhcpclient, net_radio0_prop); -dontaudit dhcpclient kernel:system module_request; -allow dhcpclient self:capability { net_admin net_raw }; +set_prop(dhcpclient, vendor_net_wlan0_prop); +set_prop(dhcpclient, vendor_net_eth0_prop); +set_prop(dhcpclient, vendor_net_radio0_prop); +allow dhcpclient self:capability { net_admin net_raw sys_module }; allow dhcpclient self:netlink_route_socket { ioctl write nlmsg_write }; allow dhcpclient varrun_file:dir search; allow dhcpclient self:packet_socket { create bind write read }; diff --git a/sepolicy/common/dhcprelay.te b/sepolicy/common/dhcprelay.te deleted file mode 100644 index bcf19afd..00000000 --- a/sepolicy/common/dhcprelay.te +++ /dev/null @@ -1,22 +0,0 @@ -# DHCP relay -type dhcprelay, domain; -type dhcprelay_exec, exec_type, vendor_file_type, file_type; - -init_daemon_domain(dhcprelay) -net_domain(dhcprelay) - -allow dhcprelay execns:fd use; - -set_prop(dhcprelay, net_wlan0_prop); -set_prop(dhcprelay, net_eth0_prop); -dontaudit dhcprelay kernel:system module_request; -allow dhcprelay self:capability { net_admin net_bind_service net_raw }; -allow dhcprelay self:udp_socket create; -allow dhcprelay self:netlink_route_socket { write nlmsg_write }; -allow dhcprelay varrun_file:dir search; -allow dhcprelay self:packet_socket { create bind write read }; -allowxperm dhcprelay self:udp_socket ioctl { SIOCSIFFLAGS - SIOCSIFADDR - SIOCSIFNETMASK - SIOCSIFMTU - SIOCGIFHWADDR }; diff --git a/sepolicy/common/domain.te b/sepolicy/common/domain.te index 3706dbaa..2e3cd776 100644 --- a/sepolicy/common/domain.te +++ b/sepolicy/common/domain.te @@ -1,3 +1,3 @@ allow domain qemu_device:chr_file rw_file_perms; -get_prop(domain, qemu_prop) +get_prop(domain, vendor_qemu_prop) diff --git a/sepolicy/common/file_contexts b/sepolicy/common/file_contexts index f009b7cd..aeeecbba 100644 --- a/sepolicy/common/file_contexts +++ b/sepolicy/common/file_contexts @@ -12,17 +12,25 @@ /dev/block/zram0 u:object_r:swap_block_device:s0 /dev/goldfish_pipe u:object_r:qemu_device:s0 +/dev/vport.*p.* u:object_r:qemu_device:s0 /dev/goldfish_sync u:object_r:qemu_device:s0 /dev/goldfish_address_space u:object_r:qemu_device:s0 -/dev/qemu_.* u:object_r:qemu_device:s0 /dev/dri/card0 u:object_r:gpu_device:s0 /dev/dri/controlD64 u:object_r:gpu_device:s0 /dev/dri/renderD128 u:object_r:gpu_device:s0 /dev/ttyGF[0-9]* u:object_r:serial_device:s0 /dev/ttyS2 u:object_r:console_device:s0 + +# kernel console +/dev/hvc0 u:object_r:serial_device:s0 +# logcat +/dev/hvc1 u:object_r:serial_device:s0 + +/system_ext/bin/init\.qemu-adb-keys\.sh u:object_r:goldfish_system_setup_exec:s0 /vendor/bin/init\.ranchu-core\.sh u:object_r:goldfish_setup_exec:s0 /vendor/bin/init\.ranchu-net\.sh u:object_r:goldfish_setup_exec:s0 /vendor/bin/init\.wifi\.sh u:object_r:goldfish_setup_exec:s0 +/vendor/bin/qemu-adb-keys u:object_r:qemu_adb_keys_exec:s0 /vendor/bin/qemu-props u:object_r:qemu_props_exec:s0 /vendor/bin/mac80211_create_radios u:object_r:mac80211_create_radios_exec:s0 /vendor/bin/createns u:object_r:createns_exec:s0 @@ -46,7 +54,7 @@ /vendor/bin/hw/android\.hardware\.gnss@2\.0-service\.ranchu u:object_r:hal_gnss_default_exec:s0 /vendor/bin/hw/android\.hardware\.neuralnetworks@1\.3-service-sample-.* u:object_r:hal_neuralnetworks_sample_exec:s0 /vendor/bin/hw/android\.hardware\.audio\.service.ranchu u:object_r:hal_audio_default_exec:s0 - +/vendor/bin/hw/android\.hardware\.media\.c2@1\.0-service-goldfish u:object_r:mediacodec_exec:s0 /vendor/lib(64)?/hw/vulkan\.ranchu\.so u:object_r:same_process_hal_file:s0 /vendor/lib(64)?/libEGL_emulation\.so u:object_r:same_process_hal_file:s0 /vendor/lib(64)?/libGLESv1_CM_emulation\.so u:object_r:same_process_hal_file:s0 @@ -60,12 +68,19 @@ /vendor/lib(64)?/libandroidemu\.so u:object_r:same_process_hal_file:s0 /vendor/lib(64)?/libdrm.so u:object_r:same_process_hal_file:s0 /vendor/lib(64)?/hw/android\.hardware\.graphics\.mapper@3\.0-impl-ranchu\.so u:object_r:same_process_hal_file:s0 +/vendor/lib(64)?/libGoldfishProfiler\.so u:object_r:same_process_hal_file:s0 # data /data/vendor/mediadrm(/.*)? u:object_r:mediadrm_vendor_data_file:s0 /data/vendor/var/run(/.*)? u:object_r:varrun_file:s0 # not yet AOSP HALs -/vendor/bin/hw/android\.hardware\.camera\.provider@2\.6-service-google u:object_r:hal_camera_default_exec:s0 +/vendor/bin/hw/android\.hardware\.camera\.provider@2\.7-service-google u:object_r:hal_camera_default_exec:s0 /vendor/bin/hw/android\.hardware\.rebootescrow-service\.default u:object_r:hal_rebootescrow_default_exec:s0 /vendor/bin/hw/android\.hardware\.contexthub@1\.1-service\.mock u:object_r:hal_contexthub_default_exec:s0 + +/vendor/lib(64)?/libEGL_angle\.so u:object_r:same_process_hal_file:s0 +/vendor/lib(64)?/libGLESv1_CM_angle\.so u:object_r:same_process_hal_file:s0 +/vendor/lib(64)?/libGLESv2_angle\.so u:object_r:same_process_hal_file:s0 +/vendor/lib(64)?/libfeature_support_angle\.so u:object_r:same_process_hal_file:s0 + diff --git a/sepolicy/common/genfs_contexts b/sepolicy/common/genfs_contexts index 728e0a2c..3484eae9 100644 --- a/sepolicy/common/genfs_contexts +++ b/sepolicy/common/genfs_contexts @@ -76,11 +76,45 @@ genfscon sysfs /devices/LNXSYSTM:00/LNXSYBUS:00/PNP0A03:00/device:20/wakeup/wake genfscon sysfs /devices/LNXSYSTM:00/LNXSYBUS:00/PNP0A03:00/wakeup/wakeup u:object_r:sysfs_wakeup:s0 genfscon sysfs /devices/platform/GFSH0001:00/power_supply/ac/wakeup u:object_r:sysfs_wakeup:s0 genfscon sysfs /devices/platform/GFSH0001:00/power_supply/battery/wakeup u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup28 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup28/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup29 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup29/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup30 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup30/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup31 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup31/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup32 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/alarmtimer.0.auto/wakeup/wakeup32/event_count u:object_r:sysfs_wakeup:s0 genfscon sysfs /devices/pnp0/00:00/rtc/rtc0/wakeup u:object_r:sysfs_wakeup:s0 genfscon sysfs /devices/pnp0/00:00/wakeup/wakeup u:object_r:sysfs_wakeup:s0 genfscon sysfs /devices/virtual/wakeup/wakeup u:object_r:sysfs_wakeup:s0 -genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup33 u:object_r:sysfs_wakeup:s0 -genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup34 u:object_r:sysfs_wakeup:s0 + +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup34 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup34/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup35 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup35/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup36 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup36/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup37 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup37/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup38 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup38/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup39 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.1/wakeup/wakeup39/event_count u:object_r:sysfs_wakeup:s0 + +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup35 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup35/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup36 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup36/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup37 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup37/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup38 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup38/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup39 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup39/event_count u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup40 u:object_r:sysfs_wakeup:s0 +genfscon sysfs /devices/platform/rtc-test.2/wakeup/wakeup40/event_count u:object_r:sysfs_wakeup:s0 genfscon sysfs /bus/iio/devices u:object_r:sysfs_iio_devices:s0 diff --git a/sepolicy/common/gmscore_app.te b/sepolicy/common/gmscore_app.te index 557b14f8..1d630392 100644 --- a/sepolicy/common/gmscore_app.te +++ b/sepolicy/common/gmscore_app.te @@ -1,2 +1,3 @@ # b/149481633: dontaudit directory traversal dontaudit gmscore_app varrun_file:dir search; +allow gmscore_app self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/goldfish_setup.te b/sepolicy/common/goldfish_setup.te index c6b3361b..5ef4d2c1 100644 --- a/sepolicy/common/goldfish_setup.te +++ b/sepolicy/common/goldfish_setup.te @@ -32,13 +32,10 @@ allow goldfish_setup proc_net:file rw_file_perms; allow goldfish_setup proc:file r_file_perms; allow goldfish_setup nsfs:file r_file_perms; allow goldfish_setup system_data_file:dir getattr; -allow goldfish_setup kernel:system module_request; -set_prop(goldfish_setup, qemu_prop); -get_prop(goldfish_setup, net_share_prop); +set_prop(goldfish_setup, vendor_qemu_prop); +get_prop(goldfish_setup, vendor_net_share_prop); # Allow goldfish_setup to run init.wifi.sh allow goldfish_setup goldfish_setup_exec:file execute_no_trans; -#Allow goldfish_setup to run createns in its own domain -domain_auto_trans(goldfish_setup, createns_exec, createns); # iw allow goldfish_setup sysfs:file { read open }; # iptables diff --git a/sepolicy/common/goldfish_system_setup.te b/sepolicy/common/goldfish_system_setup.te new file mode 100644 index 00000000..53934049 --- /dev/null +++ b/sepolicy/common/goldfish_system_setup.te @@ -0,0 +1,18 @@ +# goldfish-system-setup service: runs init.qemu-adb-keys.sh script +type goldfish_system_setup, domain, coredomain; +type goldfish_system_setup_exec, system_file_type, exec_type, file_type; + +init_daemon_domain(goldfish_system_setup) + +allow goldfish_system_setup shell_exec:file { rx_file_perms }; + +# Allow write to /dev/kmsg +allow goldfish_system_setup kmsg_device:chr_file rw_file_perms; + +# Allow read /data/misc/adb/adb_keys +allow goldfish_system_setup adb_keys_file:file r_file_perms; +allow goldfish_system_setup adb_keys_file:dir search; + +# Set qemu.adb.copykey +allow goldfish_system_setup toolbox_exec:file { getattr execute read open execute_no_trans map }; +set_prop(goldfish_system_setup, vendor_qemu_adb_prop); diff --git a/sepolicy/common/hal_audio_default.te b/sepolicy/common/hal_audio_default.te index 745092f2..4e764b00 100644 --- a/sepolicy/common/hal_audio_default.te +++ b/sepolicy/common/hal_audio_default.te @@ -1,2 +1 @@ -type hal_audio_default_prop, property_type; -get_prop(hal_audio_default, hal_audio_default_prop) +allow hal_audio_default self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/hal_bluetooth_sim.te b/sepolicy/common/hal_bluetooth_sim.te index 82bab59a..d29b1a9d 100644 --- a/sepolicy/common/hal_bluetooth_sim.te +++ b/sepolicy/common/hal_bluetooth_sim.te @@ -1,9 +1,9 @@ type hal_bluetooth_sim, domain; type hal_bluetooth_sim_exec, exec_type, vendor_file_type, file_type; -type hal_bluetooth_sim_prop, property_type; +vendor_internal_prop(vendor_bt_rootcanal_prop) hal_server_domain(hal_bluetooth_sim, hal_bluetooth) init_daemon_domain(hal_bluetooth_sim) -get_prop(hal_bluetooth_sim, hal_bluetooth_sim_prop) +get_prop(hal_bluetooth_sim, vendor_bt_rootcanal_prop) diff --git a/sepolicy/common/hal_camera_default.te b/sepolicy/common/hal_camera_default.te index 5aff5584..d433214f 100644 --- a/sepolicy/common/hal_camera_default.te +++ b/sepolicy/common/hal_camera_default.te @@ -6,3 +6,7 @@ hal_client_domain(hal_camera_default, hal_graphics_composer); # For camera hal to talk with sensor service binder_call(hal_camera_default, sensor_service_server) binder_call(sensor_service_server, hal_camera_default) +allow hal_camera_default self:vsock_socket create_socket_perms_no_ioctl; + +# camera hal with minigbm +allow hal_camera_default gpu_device:chr_file { open read write ioctl map }; diff --git a/sepolicy/common/hal_drm_default.te b/sepolicy/common/hal_drm_default.te index 5a07433c..dd5483d1 100644 --- a/sepolicy/common/hal_drm_default.te +++ b/sepolicy/common/hal_drm_default.te @@ -1,2 +1,5 @@ vndbinder_use(hal_drm_default); hal_client_domain(hal_drm_default, hal_graphics_composer) + +allow hal_drm_default mediadrm_vendor_data_file:dir create_dir_perms; +allow hal_drm_default mediadrm_vendor_data_file:file create_file_perms; diff --git a/sepolicy/common/hal_dumpstate_default.te b/sepolicy/common/hal_dumpstate_default.te deleted file mode 100644 index df68c1ce..00000000 --- a/sepolicy/common/hal_dumpstate_default.te +++ /dev/null @@ -1,2 +0,0 @@ -type hal_dumpstate_default_prop, property_type; -set_prop(hal_dumpstate_default, hal_dumpstate_default_prop) diff --git a/sepolicy/common/hal_fingerprint_default.te b/sepolicy/common/hal_fingerprint_default.te new file mode 100644 index 00000000..93ee40bd --- /dev/null +++ b/sepolicy/common/hal_fingerprint_default.te @@ -0,0 +1 @@ +allow hal_fingerprint_default self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/hal_gnss_default.te b/sepolicy/common/hal_gnss_default.te index 715cc567..3aad424e 100644 --- a/sepolicy/common/hal_gnss_default.te +++ b/sepolicy/common/hal_gnss_default.te @@ -1,3 +1,3 @@ #============= hal_gnss_default ============== allow hal_gnss_default vndbinder_device:chr_file { ioctl open read write map }; - +allow hal_gnss_default self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/hal_graphics_allocator_default.te b/sepolicy/common/hal_graphics_allocator_default.te index 527cabdb..4664eaa2 100644 --- a/sepolicy/common/hal_graphics_allocator_default.te +++ b/sepolicy/common/hal_graphics_allocator_default.te @@ -4,3 +4,4 @@ allow hal_graphics_allocator_default gpu_device:dir search; allow hal_graphics_allocator_default gpu_device:chr_file { ioctl open read write map rw_file_perms }; allow hal_graphics_allocator_default dumpstate:fd use; allow hal_graphics_allocator_default dumpstate:fifo_file write; +allow hal_graphics_allocator_default self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/hal_graphics_composer_default.te b/sepolicy/common/hal_graphics_composer_default.te index ba7ca649..16145fba 100644 --- a/sepolicy/common/hal_graphics_composer_default.te +++ b/sepolicy/common/hal_graphics_composer_default.te @@ -4,3 +4,6 @@ hal_client_domain(hal_graphics_composer_default, hal_graphics_allocator); allow hal_graphics_composer_default vndbinder_device:chr_file { ioctl open read write map }; allow hal_graphics_composer_default graphics_device:chr_file { ioctl open read write map }; allow hal_graphics_composer_default gpu_device:chr_file { ioctl open read write map }; +allow hal_graphics_composer_default self:vsock_socket create_socket_perms_no_ioctl; +allow hal_graphics_composer_default hal_graphics_allocator_default:vsock_socket { read write getattr }; +allow hal_graphics_composer_default self:netlink_kobject_uevent_socket { create bind read }; diff --git a/sepolicy/common/hal_health_default.te b/sepolicy/common/hal_health_default.te new file mode 100644 index 00000000..64e4b191 --- /dev/null +++ b/sepolicy/common/hal_health_default.te @@ -0,0 +1 @@ +allow hal_health_default sysfs:file { getattr open read }; diff --git a/sepolicy/common/hal_sensors_default.te b/sepolicy/common/hal_sensors_default.te new file mode 100644 index 00000000..c27c6c58 --- /dev/null +++ b/sepolicy/common/hal_sensors_default.te @@ -0,0 +1 @@ +allow hal_sensors_default self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/hal_wifi_default.te b/sepolicy/common/hal_wifi_default.te index cb07766f..59aab2c5 100644 --- a/sepolicy/common/hal_wifi_default.te +++ b/sepolicy/common/hal_wifi_default.te @@ -1,2 +1,4 @@ allow hal_wifi_default hal_wifi_default:netlink_route_socket { create bind write read nlmsg_read nlmsg_readpriv }; +allow hal_wifi_default self:capability { sys_module }; +set_prop(hal_wifi_default, vendor_wlan_versions_prop); diff --git a/sepolicy/common/hostapd_nohidl.te b/sepolicy/common/hostapd_nohidl.te index 8763668c..ec058c24 100644 --- a/sepolicy/common/hostapd_nohidl.te +++ b/sepolicy/common/hostapd_nohidl.te @@ -5,9 +5,6 @@ init_daemon_domain(hostapd_nohidl) net_domain(hostapd_nohidl) allow hostapd_nohidl execns:fd use; - -allow hostapd_nohidl kernel:system module_request; - allow hostapd_nohidl hostapd_data_file:file r_file_perms; allow hostapd_nohidl hostapd_data_file:dir r_dir_perms; allow hostapd_nohidl self:capability { net_admin net_raw setgid setuid }; diff --git a/sepolicy/common/init.te b/sepolicy/common/init.te index 15d68144..fdfe7aea 100644 --- a/sepolicy/common/init.te +++ b/sepolicy/common/init.te @@ -1,6 +1,5 @@ allow init tmpfs:lnk_file create_file_perms; allow init proc:dir { mounton }; -dontaudit init kernel:system module_request; allow init serial_device:chr_file { ioctl open read write }; allow init proc:dir mounton; allow init binfmt_miscfs:file write;
\ No newline at end of file diff --git a/sepolicy/common/kernel.te b/sepolicy/common/kernel.te deleted file mode 100644 index f71a3fac..00000000 --- a/sepolicy/common/kernel.te +++ /dev/null @@ -1 +0,0 @@ -dontaudit kernel kernel:system module_request; diff --git a/sepolicy/common/logpersist.te b/sepolicy/common/logpersist.te index 3fc02501..226cb00b 100644 --- a/sepolicy/common/logpersist.te +++ b/sepolicy/common/logpersist.te @@ -1,13 +1,4 @@ -# goldfish logcat service: runs logcat -Q in logpersist domain - -# See global logcat.te/logpersist.te, only set for eng & userdebug, -# allow for all builds in a non-conflicting manner. - -domain_auto_trans(init, logcat_exec, logpersist) - -# Read from logd. -unix_socket_connect(logpersist, logdr, logd) - -# Write to /dev/ttyS2 and /dev/ttyGF2. -allow logpersist serial_device:chr_file { write open }; -get_prop(logpersist, qemu_cmdline) +# Output to virtual serial console. Needed because seriallogging daemon +# runs logcat and directs its output to hvcX the /dev filesystem. +allow logpersist device:dir r_dir_perms; +allow logpersist serial_device:chr_file ra_file_perms; diff --git a/sepolicy/common/netmgr.te b/sepolicy/common/netmgr.te index c7abcb92..7150cfca 100644 --- a/sepolicy/common/netmgr.te +++ b/sepolicy/common/netmgr.te @@ -33,5 +33,5 @@ allow netmgr goldfish_ip_exec:file execute_no_trans; allow netmgr self:netlink_route_socket nlmsg_write; # Packet socket for wifi forwarding allow netmgr self:packet_socket { bind create read setopt write }; -allow netmgr kernel:system module_request; allow netmgr self:capability sys_module; +allow netmgr self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/platform_app.te b/sepolicy/common/platform_app.te new file mode 100644 index 00000000..44c22652 --- /dev/null +++ b/sepolicy/common/platform_app.te @@ -0,0 +1,2 @@ +allow platform_app self:vsock_socket create_socket_perms_no_ioctl; +allow platform_app hal_graphics_allocator_default:vsock_socket { read write getattr }; diff --git a/sepolicy/common/priv_app.te b/sepolicy/common/priv_app.te index 3d16f32b..98063129 100644 --- a/sepolicy/common/priv_app.te +++ b/sepolicy/common/priv_app.te @@ -3,3 +3,5 @@ dontaudit priv_app firstboot_prop:file { getattr open }; dontaudit priv_app device:dir { open read }; dontaudit priv_app proc_interrupts:file { getattr open read }; dontaudit priv_app proc_modules:file { getattr open read }; +allow priv_app self:vsock_socket create_socket_perms_no_ioctl; +allow priv_app hal_graphics_allocator_default:vsock_socket { read write getattr }; diff --git a/sepolicy/common/property.te b/sepolicy/common/property.te index d0e4c1da..9b081d7f 100644 --- a/sepolicy/common/property.te +++ b/sepolicy/common/property.te @@ -1,9 +1,9 @@ -type qemu_prop, property_type; -type qemu_cmdline, property_type; -type radio_noril_prop, property_type; -type net_wlan0_prop, property_type; -type net_eth0_prop, property_type; -type net_radio0_prop, property_type; -type net_share_prop, property_type; -type vendor_net, property_type; -type vendor_build_prop, property_type; +system_restricted_prop(vendor_qemu_adb_prop) +vendor_restricted_prop(vendor_qemu_prop) +vendor_restricted_prop(vendor_net_wlan0_prop) +vendor_restricted_prop(vendor_net_eth0_prop) +vendor_restricted_prop(vendor_net_radio0_prop) +vendor_restricted_prop(vendor_net_share_prop) +vendor_restricted_prop(vendor_net) +vendor_restricted_prop(vendor_build_prop) +vendor_restricted_prop(vendor_wlan_versions_prop) diff --git a/sepolicy/common/property_contexts b/sepolicy/common/property_contexts index f720a058..70d8c5c1 100644 --- a/sepolicy/common/property_contexts +++ b/sepolicy/common/property_contexts @@ -1,17 +1,30 @@ -qemu. u:object_r:qemu_prop:s0 -qemu.cmdline u:object_r:qemu_cmdline:s0 -vendor.qemu u:object_r:qemu_prop:s0 -vendor.network u:object_r:vendor_net:s0 -ro.aae.simulateMultiZoneAudio u:object_r:hal_audio_default_prop:s0 -ro.emu. u:object_r:qemu_prop:s0 -ro.emulator. u:object_r:qemu_prop:s0 -ro.radio.noril u:object_r:radio_noril_prop:s0 -net.wlan0. u:object_r:net_wlan0_prop:s0 -net.eth0. u:object_r:net_eth0_prop:s0 -net.radio0. u:object_r:net_radio0_prop:s0 -net.shared_net_ip u:object_r:net_share_prop:s0 -net.wifi_mac_prefix u:object_r:net_share_prop:s0 -ro.zygote.disable_gl_preload u:object_r:qemu_prop:s0 -persist.dumpstate.verbose_logging.enabled u:object_r:hal_dumpstate_default_prop:s0 -bt.rootcanal_mac_address u:object_r:hal_bluetooth_sim_prop:s0 -bt.rootcanal_test_console u:object_r:hal_bluetooth_sim_prop:s0 +vendor.qemu.adb.copykey u:object_r:vendor_qemu_adb_prop:s0 exact bool +vendor.qemu.keyboard_layout u:object_r:vendor_qemu_prop:s0 exact string +vendor.qemu.networknamespace u:object_r:vendor_qemu_prop:s0 exact string +vendor.qemu.logcat_filter u:object_r:vendor_qemu_prop:s0 exact string +vendor.qemu.sf.fake_camera u:object_r:vendor_qemu_prop:s0 exact string +vendor.qemu.vport.modem u:object_r:vendor_qemu_prop:s0 exact string +vendor.qemu.vport.gnss u:object_r:vendor_qemu_prop:s0 exact string +vendor.qemu.timezone u:object_r:vendor_qemu_prop:s0 exact string +vendor.network.bridged u:object_r:vendor_net:s0 exact string +vendor.net.wlan0.gw u:object_r:vendor_net_wlan0_prop:s0 exact string +vendor.net.wlan0.dns1 u:object_r:vendor_net_wlan0_prop:s0 exact string +vendor.net.wlan0.dns2 u:object_r:vendor_net_wlan0_prop:s0 exact string +vendor.net.wlan0.dns3 u:object_r:vendor_net_wlan0_prop:s0 exact string +vendor.net.wlan0.dns4 u:object_r:vendor_net_wlan0_prop:s0 exact string +vendor.net.eth0.gw u:object_r:vendor_net_eth0_prop:s0 exact string +vendor.net.eth0.dns1 u:object_r:vendor_net_eth0_prop:s0 exact string +vendor.net.eth0.dns2 u:object_r:vendor_net_eth0_prop:s0 exact string +vendor.net.eth0.dns3 u:object_r:vendor_net_eth0_prop:s0 exact string +vendor.net.eth0.dns4 u:object_r:vendor_net_eth0_prop:s0 exact string +vendor.net.radio0.gw u:object_r:vendor_net_radio0_prop:s0 exact string +vendor.net.radio0.dns1 u:object_r:vendor_net_radio0_prop:s0 exact string +vendor.net.radio0.dns2 u:object_r:vendor_net_radio0_prop:s0 exact string +vendor.net.radio0.dns3 u:object_r:vendor_net_radio0_prop:s0 exact string +vendor.net.radio0.dns4 u:object_r:vendor_net_radio0_prop:s0 exact string +vendor.net.shared_net_ip u:object_r:vendor_net_share_prop:s0 exact string +vendor.net.wifi_mac_prefix u:object_r:vendor_net_share_prop:s0 exact string +vendor.bt.rootcanal_mac_address u:object_r:vendor_bt_rootcanal_prop:s0 exact string +vendor.bt.rootcanal_test_console u:object_r:vendor_bt_rootcanal_prop:s0 exact string +vendor.wlan.firmware.version u:object_r:vendor_wlan_versions_prop:s0 exact string +vendor.wlan.driver.version u:object_r:vendor_wlan_versions_prop:s0 exact string diff --git a/sepolicy/common/qemu_adb_keys.te b/sepolicy/common/qemu_adb_keys.te new file mode 100644 index 00000000..8a09c166 --- /dev/null +++ b/sepolicy/common/qemu_adb_keys.te @@ -0,0 +1,13 @@ +# qemu-adb-keys service: Writes host adb key for adbd on boot. +type qemu_adb_keys, domain; +type qemu_adb_keys_exec, vendor_file_type, exec_type, file_type; + +init_daemon_domain(qemu_adb_keys) + +# Allow qemu_adb_keys to read /proc/bootconfig +allow qemu_adb_keys proc_cmdline:file r_file_perms; +allow qemu_adb_keys proc_bootconfig:file r_file_perms; + +# Permission to write to /data/vendor/adb/adb_keys. +allow qemu_adb_keys vendor_data_file:dir create_dir_perms; +allow qemu_adb_keys vendor_data_file:file create_file_perms; diff --git a/sepolicy/common/qemu_props.te b/sepolicy/common/qemu_props.te index f2c253c9..03e9f6f9 100644 --- a/sepolicy/common/qemu_props.te +++ b/sepolicy/common/qemu_props.te @@ -4,8 +4,14 @@ type qemu_props_exec, vendor_file_type, exec_type, file_type; init_daemon_domain(qemu_props) -set_prop(qemu_props, qemu_prop) -set_prop(qemu_props, net_share_prop) +set_prop(qemu_props, qemu_hw_prop) +set_prop(qemu_props, qemu_sf_lcd_density_prop) +set_prop(qemu_props, vendor_qemu_prop) +set_prop(qemu_props, vendor_net_share_prop) # TODO(b/79502552): Invalid property access from emulator vendor -#set_prop(qemu_props, qemu_cmdline) -set_prop(qemu_props, qemu_cmdline) +allow qemu_props self:vsock_socket create_socket_perms_no_ioctl; +allow qemu_props sysfs:dir read; +allow qemu_props sysfs:dir open; +allow qemu_props sysfs:file getattr; +allow qemu_props sysfs:file read; +allow qemu_props sysfs:file open; diff --git a/sepolicy/common/radio.te b/sepolicy/common/radio.te index 38faf6fa..2454755d 100644 --- a/sepolicy/common/radio.te +++ b/sepolicy/common/radio.te @@ -1,4 +1,4 @@ # Allow the radio to read these properties, they only have an SELinux label in # the emulator. -get_prop(radio, net_eth0_prop); -allow radio net_radio0_prop:file { getattr read open map }; +get_prop(radio, vendor_net_eth0_prop); +allow radio vendor_net_radio0_prop:file { getattr read open map }; diff --git a/sepolicy/common/rild.te b/sepolicy/common/rild.te index c17fa5e7..7ddb21ca 100644 --- a/sepolicy/common/rild.te +++ b/sepolicy/common/rild.te @@ -1,10 +1,11 @@ # Allow rild to read these properties, they only have an SELinux label in the # emulator. -get_prop(rild, net_eth0_prop); -get_prop(rild, net_radio0_prop); +get_prop(rild, vendor_net_eth0_prop); +get_prop(rild, vendor_net_radio0_prop); # IPv6 router advertisement detection allow rild self:packet_socket { bind create ioctl read setopt }; allowxperm rild self:packet_socket ioctl { SIOCGIFFLAGS SIOCSIFFLAGS SIOCGIFHWADDR }; +allow rild self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/shell.te b/sepolicy/common/shell.te index c96ca319..9eba714a 100644 --- a/sepolicy/common/shell.te +++ b/sepolicy/common/shell.te @@ -1,2 +1,4 @@ allow shell serial_device:chr_file rw_file_perms; -allow shell kernel:system module_request; +allow shell aac_drc_prop:file { getattr map open }; +allow shell device_config_runtime_native_boot_prop:file { getattr map open read }; +allow shell adbd:{ socket vsock_socket } rw_socket_perms_no_ioctl; diff --git a/sepolicy/common/surfaceflinger.te b/sepolicy/common/surfaceflinger.te index 575ec1bd..f583ef72 100644 --- a/sepolicy/common/surfaceflinger.te +++ b/sepolicy/common/surfaceflinger.te @@ -1,6 +1,5 @@ allow surfaceflinger self:process execmem; allow surfaceflinger ashmem_device:chr_file execute; allow surfaceflinger gpu_device:chr_file { ioctl open read write map }; - -typeattribute surfaceflinger system_writes_vendor_properties_violators; -set_prop(surfaceflinger, qemu_prop) +allow surfaceflinger self:vsock_socket create_socket_perms_no_ioctl; +allow surfaceflinger hal_graphics_allocator_default:vsock_socket { read write getattr }; diff --git a/sepolicy/common/system_app.te b/sepolicy/common/system_app.te new file mode 100644 index 00000000..41e61a9a --- /dev/null +++ b/sepolicy/common/system_app.te @@ -0,0 +1,2 @@ +allow system_app self:vsock_socket create_socket_perms_no_ioctl; +allow system_app hal_graphics_allocator_default:vsock_socket { read write getattr }; diff --git a/sepolicy/common/system_server.te b/sepolicy/common/system_server.te index dd70b12d..548f206f 100644 --- a/sepolicy/common/system_server.te +++ b/sepolicy/common/system_server.te @@ -1 +1,2 @@ -get_prop(system_server, radio_noril_prop) +allow system_server self:vsock_socket create_socket_perms_no_ioctl; +allow system_server hal_graphics_allocator_default:vsock_socket { read write getattr }; diff --git a/sepolicy/common/vendor_init.te b/sepolicy/common/vendor_init.te index 3249ab09..c4ecff91 100644 --- a/sepolicy/common/vendor_init.te +++ b/sepolicy/common/vendor_init.te @@ -1,5 +1,6 @@ -set_prop(vendor_init, qemu_prop) -allow vendor_init kernel:system module_request; +set_prop(vendor_init, vendor_qemu_prop) allow vendor_init ram_device:blk_file setattr; -set_prop(vendor_init, hal_bluetooth_sim_prop); +set_prop(vendor_init, vendor_bt_rootcanal_prop) set_prop(vendor_init, vendor_build_prop); +set_prop(vendor_init, exported_system_prop); + diff --git a/sepolicy/common/vold.te b/sepolicy/common/vold.te index 6b3b1f3d..3ab24e68 100644 --- a/sepolicy/common/vold.te +++ b/sepolicy/common/vold.te @@ -1,4 +1,3 @@ -dontaudit vold kernel:system module_request; allow vold sysfs_devices_block:file w_file_perms; allow vold sysfs_virtio_block:file w_file_perms; allow vold nsfs:file r_file_perms; diff --git a/sepolicy/common/wifi_forwarder.te b/sepolicy/common/wifi_forwarder.te index 3eb7bbac..536476ba 100644 --- a/sepolicy/common/wifi_forwarder.te +++ b/sepolicy/common/wifi_forwarder.te @@ -8,4 +8,4 @@ net_domain(wifi_forwarder) allow wifi_forwarder self:capability { net_admin }; # Generic netlink socket for wifi forwarding allow wifi_forwarder self:netlink_generic_socket { bind create getattr setopt read write }; - +allow wifi_forwarder self:vsock_socket create_socket_perms_no_ioctl; diff --git a/sepolicy/common/zygote.te b/sepolicy/common/zygote.te index da403b5d..390a507a 100644 --- a/sepolicy/common/zygote.te +++ b/sepolicy/common/zygote.te @@ -1,5 +1,3 @@ -typeattribute zygote system_writes_vendor_properties_violators; -set_prop(zygote, qemu_prop) # TODO (b/63631799) fix this access # Suppress denials to storage. Webview zygote should not be accessing. dontaudit webview_zygote mnt_expand_file:dir getattr; diff --git a/sepolicy/x86/OWNERS b/sepolicy/x86/OWNERS index e6fbbd47..bbe0cccc 100644 --- a/sepolicy/x86/OWNERS +++ b/sepolicy/x86/OWNERS @@ -5,5 +5,4 @@ jeffv@google.com jgalenson@google.com nnk@google.com sspatil@google.com -tomcherry@google.com trong@google.com diff --git a/soundtrigger/Android.bp b/soundtrigger/Android.bp index 8576aae1..0d790178 100644 --- a/soundtrigger/Android.bp +++ b/soundtrigger/Android.bp @@ -13,6 +13,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_shared { name: "android.hardware.soundtrigger@2.2-impl.ranchu", vendor: true, diff --git a/soundtrigger/main.cpp b/soundtrigger/main.cpp index 6bf27737..1d901fc2 100644 --- a/soundtrigger/main.cpp +++ b/soundtrigger/main.cpp @@ -34,7 +34,7 @@ struct SoundTriggerHw : public ISoundTriggerHw { props.implementor = "The Android Open Source Project"; props.description = "The Andtoid Studio Emulator Soundtrigger no-op implementation"; - props.version = 0; + props.version = 254868980; props.uuid = (Uuid){ .timeLow = 0x04030201, .timeMid = 0x0605, diff --git a/task_profiles.json b/task_profiles.json index cad37156..a0a898c6 100644 --- a/task_profiles.json +++ b/task_profiles.json @@ -1,47 +1,4 @@ { - "Attributes": [ - { - "Name": "LowCapacityCPUs", - "Controller": "cpuset", - "File": "background/cpus" - }, - { - "Name": "HighCapacityCPUs", - "Controller": "cpuset", - "File": "foreground/cpus" - }, - { - "Name": "MaxCapacityCPUs", - "Controller": "cpuset", - "File": "top-app/cpus" - }, - { - "Name": "MemLimit", - "Controller": "memory", - "File": "memory.limit_in_bytes" - }, - { - "Name": "MemSoftLimit", - "Controller": "memory", - "File": "memory.soft_limit_in_bytes" - }, - { - "Name": "MemSwappiness", - "Controller": "memory", - "File": "memory.swappiness" - }, - { - "Name": "UClampMin", - "Controller": "cpu", - "File": "cpu.util.min" - }, - { - "Name": "UClampMax", - "Controller": "cpu", - "File": "cpu.util.max" - } - ], - "Profiles": [ { "Name": "HighEnergySaving", diff --git a/tasks/emu_img_zip.mk b/tasks/emu_img_zip.mk new file mode 100644 index 00000000..9291facd --- /dev/null +++ b/tasks/emu_img_zip.mk @@ -0,0 +1,116 @@ +# Rules to generate a zip file that contains google emulator images +# and other files for distribution + +ifeq ($(filter $(TARGET_PRODUCT), qemu_trusty_arm64),) +ifeq ($(filter $(MAKECMDGOALS), sdk win_sdk sdk_repo goog_emu_imgs),) +emulator_img_source_prop := $(TARGET_OUT_INTERMEDIATES)/source.properties +$(emulator_img_source_prop): $(PRODUCT_SDK_ADDON_SYS_IMG_SOURCE_PROP) + @echo Generate $@ + $(hide) mkdir -p $(dir $@) + $(hide) sed \ + -e 's/$${PLATFORM_VERSION}/$(PLATFORM_VERSION)/' \ + -e 's/$${PLATFORM_SDK_VERSION}/$(PLATFORM_SDK_VERSION)/' \ + -e 's/$${PLATFORM_VERSION_CODENAME}/$(subst REL,,$(PLATFORM_VERSION_CODENAME))/' \ + -e 's/$${TARGET_ARCH}/$(TARGET_ARCH)/' \ + -e 's/$${TARGET_CPU_ABI}/$(TARGET_CPU_ABI)/' \ + -e 's/$${SYSTEM_IMAGE_TAG_ID}/$(SYSTEM_IMAGE_TAG_ID)/' \ + -e 's/$${SYSTEM_IMAGE_TAG_DISPLAY}/$(SYSTEM_IMAGE_TAG_DISPLAY)/' \ + $< > $@ && sed -i -e '/^AndroidVersion.CodeName=\s*$$/d' $@ + +INTERNAL_EMULATOR_PACKAGE_FILES := \ + $(target_notice_file_txt) \ + $(emulator_img_source_prop) \ + $(PRODUCT_OUT)/system/build.prop \ + +ifneq ($(filter $(TARGET_PRODUCT), sdk_goog3_x86 sdk_goog3_x86_64 sdk_goog3_x86_arm),) + INTERNAL_EMULATOR_PACKAGE_FILES += \ + $(HOST_OUT_EXECUTABLES)/dex2oats \ + $(HOST_OUT_EXECUTABLES)/dex2oatds +endif + +ifeq ($(BUILD_QEMU_IMAGES),true) +ifeq ($(BOARD_AVB_ENABLE),true) +INTERNAL_EMULATOR_PACKAGE_FILES += \ + $(PRODUCT_OUT)/VerifiedBootParams.textproto +endif +endif + +INTERNAL_EMULATOR_PACKAGE_SOURCE := $(PRODUCT_OUT)/emulator + +INSTALLED_QEMU_SYSTEMIMAGE := $(PRODUCT_OUT)/system-qemu.img +FINAL_INSTALLED_QEMU_SYSTEMIMAGE := $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI)/system.img +$(eval $(call copy-one-file,$(INSTALLED_QEMU_SYSTEMIMAGE),$(FINAL_INSTALLED_QEMU_SYSTEMIMAGE))) + +INSTALLED_QEMU_RAMDISKIMAGE := $(PRODUCT_OUT)/ramdisk-qemu.img +FINAL_INSTALLED_QEMU_RAMDISKIMAGE := $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI)/ramdisk.img +$(eval $(call copy-one-file,$(INSTALLED_QEMU_RAMDISKIMAGE),$(FINAL_INSTALLED_QEMU_RAMDISKIMAGE))) + +INSTALLED_QEMU_VENDORIMAGE := $(PRODUCT_OUT)/vendor-qemu.img +FINAL_INSTALLED_QEMU_VENDORIMAGE := $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI)/vendor.img +$(eval $(call copy-one-file,$(INSTALLED_QEMU_VENDORIMAGE),$(FINAL_INSTALLED_QEMU_VENDORIMAGE))) + + +INTERNAL_EMULATOR_PACKAGE_FILES += device/generic/goldfish/data/etc/encryptionkey.img +INTERNAL_EMULATOR_PACKAGE_FILES += device/generic/goldfish/data/etc/userdata.img + +INTERNAL_EMULATOR_FEATURE_DIR := . +ifneq ($(filter sdk_phone64_% sdk_gphone64_%, $(TARGET_PRODUCT)),) +INTERNAL_EMULATOR_FEATURE_DIR := 64bit +endif + +ifeq ($(TARGET_BUILD_VARIANT),user) +INTERNAL_EMULATOR_PACKAGE_FILES += device/generic/goldfish/data/etc/google/$(INTERNAL_EMULATOR_FEATURE_DIR)/user/advancedFeatures.ini +ifeq ($(TARGET_ARCH),arm64) +INTERNAL_EMULATOR_PACKAGE_FILES += device/generic/goldfish/data/etc/google/$(INTERNAL_EMULATOR_FEATURE_DIR)/user/arm64/advancedFeatures.ini +endif +else +INTERNAL_EMULATOR_PACKAGE_FILES += device/generic/goldfish/data/etc/google/$(INTERNAL_EMULATOR_FEATURE_DIR)/userdebug/advancedFeatures.ini +ifeq ($(TARGET_ARCH),arm64) +INTERNAL_EMULATOR_PACKAGE_FILES += device/generic/goldfish/data/etc/google/$(INTERNAL_EMULATOR_FEATURE_DIR)/userdebug/arm64/advancedFeatures.ini +endif +endif + + + +name := sdk-repo-linux-system-images-$(FILE_NAME_TAG) + + +INTERNAL_EMULATOR_PACKAGE_TARGET := $(PRODUCT_OUT)/$(name).zip + +ifeq ($(TARGET_ARCH), x86) +EMULATOR_KERNEL_ARCH := x86_64 +EMULATOR_KERNEL_DIST_NAME := kernel-ranchu-64 +else +ifeq ($(TARGET_ARCH), x86_64) +EMULATOR_KERNEL_ARCH := $(TARGET_ARCH) +EMULATOR_KERNEL_DIST_NAME := kernel-ranchu +else +ifeq ($(TARGET_ARCH), arm64) +EMULATOR_KERNEL_ARCH := $(TARGET_ARCH) +EMULATOR_KERNEL_DIST_NAME := kernel-ranchu +else +ifeq ($(TARGET_ARCH), arm) +EMULATOR_KERNEL_ARCH := $(TARGET_ARCH) +EMULATOR_KERNEL_DIST_NAME := kernel-ranchu +EMULATOR_KERNEL_VERSION := 3.18 +EMULATOR_KERNEL_FILE := prebuilts/qemu-kernel/$(EMULATOR_KERNEL_ARCH)/$(EMULATOR_KERNEL_VERSION)/kernel-qemu2 +else +$(error unsupported arch: $(TARGET_ARCH)) +endif # arm +endif # arm64 +endif # x86_64 +endif # x86 + +$(INTERNAL_EMULATOR_PACKAGE_TARGET): $(INTERNAL_EMULATOR_PACKAGE_FILES) $(FINAL_INSTALLED_QEMU_SYSTEMIMAGE) $(FINAL_INSTALLED_QEMU_RAMDISKIMAGE) $(FINAL_INSTALLED_QEMU_VENDORIMAGE) $(EMULATOR_KERNEL_FILE) + @echo "Package: $@" + $(hide) mkdir -p $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI) + $(hide) $(foreach f,$(INTERNAL_EMULATOR_PACKAGE_FILES), $(ACP) $(f) $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI)/$(notdir $(f));) + $(hide) ($(ACP) $(EMULATOR_KERNEL_FILE) $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI)/${EMULATOR_KERNEL_DIST_NAME}) + $(hide) $(ACP) -r $(PRODUCT_OUT)/data $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI) + $(hide) $(SOONG_ZIP) -o $@ -C $(INTERNAL_EMULATOR_PACKAGE_SOURCE) -D $(INTERNAL_EMULATOR_PACKAGE_SOURCE)/$(TARGET_CPU_ABI) + +.PHONY: emu_img_zip +emu_img_zip: $(INTERNAL_EMULATOR_PACKAGE_TARGET) + +endif +endif diff --git a/tnc/Android.bp b/tnc/Android.bp index fb0236fd..aead392d 100644 --- a/tnc/Android.bp +++ b/tnc/Android.bp @@ -14,6 +14,16 @@ // limitations under the License. // +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + // SPDX-license-identifier-BSD + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "tnc", vendor: true, @@ -29,4 +39,3 @@ cc_binary { "liblog", ], } - diff --git a/tools/Android.bp b/tools/Android.bp index 8cb1ad02..347512e0 100644 --- a/tools/Android.bp +++ b/tools/Android.bp @@ -14,6 +14,16 @@ // limitations under the License. // +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + // SPDX-license-identifier-BSD + default_applicable_licenses: ["device_generic_goldfish_license"], +} + python_binary_host { name: "mk_combined_img", srcs: ["mk_combined_img.py"], diff --git a/tools/Android.mk b/tools/Android.mk index 7aad2415..4ba4b5a7 100644 --- a/tools/Android.mk +++ b/tools/Android.mk @@ -50,21 +50,34 @@ EMU_EXTRA_TARGET := $(PRODUCT_OUT)/$(name).zip EMULATOR_KERNEL_ARCH := $(TARGET_ARCH) EMULATOR_KERNEL_DIST_NAME := kernel-ranchu -# Below should be the same as PRODUCT_KERNEL_VERSION set in +# Below should be the same as TARGET_KERNEL_USE set in # device/generic/goldfish/(arm|x86)*-vendor.mk -EMULATOR_KERNEL_VERSION := 5.4 +TARGET_KERNEL_USE ?= 5.10 # Use 64-bit kernel even for 32-bit Android ifeq ($(TARGET_ARCH), x86) EMULATOR_KERNEL_ARCH := x86_64 EMULATOR_KERNEL_DIST_NAME := kernel-ranchu-64 -endif +else +ifeq ($(TARGET_ARCH), x86_64) +EMULATOR_KERNEL_ARCH := $(TARGET_ARCH) +EMULATOR_KERNEL_DIST_NAME := kernel-ranchu +else +ifeq ($(TARGET_ARCH), arm64) +EMULATOR_KERNEL_ARCH := $(TARGET_ARCH) +EMULATOR_KERNEL_DIST_NAME := kernel-ranchu +else ifeq ($(TARGET_ARCH), arm) -EMULATOR_KERNEL_ARCH := arm64 -EMULATOR_KERNEL_DIST_NAME := kernel-ranchu-64 -endif - +EMULATOR_KERNEL_ARCH := $(TARGET_ARCH) +EMULATOR_KERNEL_DIST_NAME := kernel-ranchu +EMULATOR_KERNEL_VERSION := 3.18 EMULATOR_KERNEL_FILE := prebuilts/qemu-kernel/$(EMULATOR_KERNEL_ARCH)/$(EMULATOR_KERNEL_VERSION)/kernel-qemu2 +else +$(error unsupported arch: $(TARGET_ARCH)) +endif # arm +endif # arm64 +endif # x86_64 +endif # x86 $(EMU_EXTRA_TARGET): PRIVATE_PACKAGE_SRC := \ $(call intermediates-dir-for, PACKAGING, emu_extra_target) diff --git a/tools/mk_verified_boot_params.sh b/tools/mk_verified_boot_params.sh index 15813cb6..f1ea9415 100755 --- a/tools/mk_verified_boot_params.sh +++ b/tools/mk_verified_boot_params.sh @@ -79,7 +79,7 @@ readonly ROOT_DIGEST=${DM_SPLIT[15]} readonly SALT=${DM_SPLIT[16]} readonly NUM_OPTIONAL_PARAMS=1 -# Sanity Checks +# Validity Checks [[ $ROOT_DIGEST =~ [[:xdigit:]]{40} ]] || die "ROOT_DIGEST looks incorrect: $ROOT_DIGEST" [[ $SALT =~ [[:xdigit:]]{40} ]] || die "SALT looks incorrect: $SALT" diff --git a/ueventd.ranchu.rc b/ueventd.ranchu.rc index 5be82974..1f4f0fbe 100644 --- a/ueventd.ranchu.rc +++ b/ueventd.ranchu.rc @@ -4,7 +4,11 @@ /dev/goldfish_pipe 0666 system system /dev/ttyS* 0666 system system /dev/goldfish_sync 0666 system system +/dev/vport* 0666 system system /dev/goldfish_address_space 0666 system system /dev/dri/card0 0660 system graphics /dev/dri/controlD64 0660 system graphics /dev/dri/renderD128 0666 system graphics + +# logcat virtconsole +/dev/hvc1 0660 system logd @@ -39,9 +39,9 @@ PRODUCT_PACKAGES += \ libandroidemu \ libOpenglCodecCommon \ libOpenglSystemCommon \ - libgoldfish-ril \ + libcuttlefish-ril-2 \ libgoldfish-rild \ - libril-goldfish-fork \ + qemu-adb-keys \ qemu-props \ stagefright \ fingerprint.ranchu \ @@ -53,16 +53,22 @@ PRODUCT_PACKAGES += \ toybox_vendor \ android.hardware.wifi@1.0-service \ android.hardware.biometrics.fingerprint@2.1-service \ + android.hardware.media.c2@1.0-service-goldfish \ + libcodec2_goldfish_vp8dec \ + libcodec2_goldfish_vp9dec \ + libcodec2_goldfish_avcdec \ sh_vendor \ ip_vendor \ iw_vendor \ local_time.default \ SdkSetup \ EmulatorRadioConfig \ + EmulatorTetheringConfigOverlay \ libstagefrighthw \ libstagefright_goldfish_vpxdec \ libstagefright_goldfish_avcdec \ - MultiDisplayProvider + MultiDisplayProvider \ + libGoldfishProfiler \ ifneq ($(BUILD_EMULATOR_OPENGL),false) PRODUCT_PACKAGES += \ @@ -72,13 +78,17 @@ PRODUCT_PACKAGES += \ libGLESv2_enc \ libvulkan_enc \ libGLESv2_emulation \ - libGLESv1_enc + libGLESv1_enc \ + libEGL_angle \ + libGLESv1_CM_angle \ + libGLESv2_angle \ + libfeature_support_angle.so endif PRODUCT_PACKAGES += \ android.hardware.bluetooth@1.1-service.sim \ android.hardware.bluetooth.audio@2.0-impl -PRODUCT_PROPERTY_OVERRIDES += bt.rootcanal_test_console=off +PRODUCT_PROPERTY_OVERRIDES += vendor.bt.rootcanal_test_console=off PRODUCT_PACKAGES += \ android.hardware.health@2.1-service \ @@ -97,10 +107,25 @@ PRODUCT_PACKAGES += \ PRODUCT_PACKAGES += \ DisplayCutoutEmulationEmu01Overlay \ + EmulationPixel5Overlay \ + SystemUIEmulationPixel5Overlay \ + EmulationPixel4XLOverlay \ + SystemUIEmulationPixel4XLOverlay \ + EmulationPixel4Overlay \ + SystemUIEmulationPixel4Overlay \ + EmulationPixel4aOverlay \ + SystemUIEmulationPixel4aOverlay \ + EmulationPixel3XLOverlay \ + SystemUIEmulationPixel3XLOverlay \ + SystemUIEmulationPixel3Overlay \ + SystemUIEmulationPixel3aOverlay \ + SystemUIEmulationPixel3aXLOverlay \ + EmulationPixel2XLOverlay \ + SystemUIEmulationPixel2XLOverlay \ NavigationBarMode2ButtonOverlay \ ifneq ($(EMULATOR_VENDOR_NO_GNSS),true) -PRODUCT_PACKAGES += android.hardware.gnss@2.0-service.ranchu +PRODUCT_PACKAGES += android.hardware.gnss-service.example endif ifneq ($(EMULATOR_VENDOR_NO_SENSORS),true) @@ -118,15 +143,16 @@ endif PRODUCT_PACKAGES += \ android.hardware.drm@1.0-service \ android.hardware.drm@1.0-impl \ - android.hardware.drm@1.3-service.clearkey \ - android.hardware.drm@1.3-service.widevine + android.hardware.drm@1.4-service.clearkey \ + PRODUCT_PACKAGES += \ android.hardware.power-service.example \ -PRODUCT_PROPERTY_OVERRIDES += ro.control_privapp_permissions=enforce +PRODUCT_PROPERTY_OVERRIDES += ro.control_privapp_permissions?=enforce PRODUCT_PROPERTY_OVERRIDES += ro.hardware.power=ranchu PRODUCT_PROPERTY_OVERRIDES += ro.crypto.volume.filenames_mode=aes-256-cts +PRODUCT_VENDOR_PROPERTIES += graphics.gpu.profiler.support=true PRODUCT_PROPERTY_OVERRIDES += persist.sys.zram_enabled=1 \ @@ -138,20 +164,20 @@ PRODUCT_PROPERTY_OVERRIDES += ro.logd.size=1M \ ifneq ($(EMULATOR_VENDOR_NO_CAMERA),true) PRODUCT_PACKAGES += \ - camera.device@1.0-impl \ android.hardware.camera.provider@2.4-service \ android.hardware.camera.provider@2.4-impl \ camera.ranchu \ camera.ranchu.jpeg \ - android.hardware.camera.provider@2.6-service-google \ + android.hardware.camera.provider@2.7-service-google \ libgooglecamerahwl_impl \ - android.hardware.camera.provider@2.6-impl-google + android.hardware.camera.provider@2.7-impl-google DEVICE_MANIFEST_FILE += device/generic/goldfish/manifest.camera.xml endif ifneq ($(EMULATOR_VENDOR_NO_SOUND),true) PRODUCT_PACKAGES += \ - android.hardware.audio.service.ranchu \ + android.hardware.audio.service \ + android.hardware.audio@6.0-impl.ranchu \ android.hardware.soundtrigger@2.2-impl.ranchu \ android.hardware.audio.effect@6.0-impl \ @@ -229,12 +255,11 @@ PRODUCT_PACKAGES += \ PRODUCT_PACKAGES += \ android.hardware.contexthub@1.1-service.mock -# Goldfish does not support ION needed for Codec 2.0 -# still disable it until b/143473631 is fixed -# now this is setup on init.ranchu.rc +# for 32, 32+64 guest, default using omx, but can be +# modified at command line as follows # -qemu -append qemu.media.ccodec=<value> can override it; default 0 -#PRODUCT_PROPERTY_OVERRIDES += \ -# debug.stagefright.ccodec=0 +PRODUCT_PROPERTY_OVERRIDES += \ + debug.stagefright.ccodec=0 # Enable Incremental on the device via kernel driver PRODUCT_PROPERTY_OVERRIDES += ro.incremental.enable=yes @@ -244,11 +269,16 @@ PRODUCT_COPY_FILES += \ device/generic/goldfish/data/etc/dtb.img:dtb.img \ device/generic/goldfish/data/etc/apns-conf.xml:data/misc/apns/apns-conf.xml \ device/generic/goldfish/radio/RadioConfig/radioconfig.xml:data/misc/emulator/config/radioconfig.xml \ + device/generic/goldfish/data/etc/iccprofile_for_sim0.xml:data/misc/modem_simulator/iccprofile_for_sim0.xml \ + device/google/cuttlefish/host/commands/modem_simulator/files/iccprofile_for_sim0_for_CtsCarrierApiTestCases.xml:data/misc/modem_simulator/iccprofile_for_carrierapitests.xml \ + device/generic/goldfish/data/etc/numeric_operator.xml:data/misc/modem_simulator/etc/modem_simulator/files/numeric_operator.xml \ device/generic/goldfish/data/etc/local.prop:data/local.prop \ + device/generic/goldfish/init.qemu-adb-keys.sh:$(TARGET_COPY_OUT_SYSTEM_EXT)/bin/init.qemu-adb-keys.sh \ device/generic/goldfish/init.ranchu-core.sh:$(TARGET_COPY_OUT_VENDOR)/bin/init.ranchu-core.sh \ device/generic/goldfish/init.ranchu-net.sh:$(TARGET_COPY_OUT_VENDOR)/bin/init.ranchu-net.sh \ device/generic/goldfish/wifi/init.wifi.sh:$(TARGET_COPY_OUT_VENDOR)/bin/init.wifi.sh \ device/generic/goldfish/init.ranchu.rc:$(TARGET_COPY_OUT_VENDOR)/etc/init/hw/init.ranchu.rc \ + device/generic/goldfish/init.system_ext.rc:$(TARGET_COPY_OUT_SYSTEM_EXT)/etc/init/init.system_ext.rc \ device/generic/goldfish/fstab.ranchu:$(TARGET_COPY_OUT_VENDOR)/etc/fstab.ranchu \ device/generic/goldfish/ueventd.ranchu.rc:$(TARGET_COPY_OUT_VENDOR)/ueventd.rc \ device/generic/goldfish/input/goldfish_rotary.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/goldfish_rotary.idc \ @@ -265,10 +295,11 @@ PRODUCT_COPY_FILES += \ device/generic/goldfish/input/virtio_input_multi_touch_9.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_9.idc \ device/generic/goldfish/input/virtio_input_multi_touch_10.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_10.idc \ device/generic/goldfish/input/virtio_input_multi_touch_11.idc:$(TARGET_COPY_OUT_VENDOR)/usr/idc/virtio_input_multi_touch_11.idc \ + device/generic/goldfish/display_settings_freeform.xml:$(TARGET_COPY_OUT_VENDOR)/etc/display_settings_freeform.xml \ + device/generic/goldfish/device_state_configuration.xml:$(TARGET_COPY_OUT_VENDOR)/etc/devicestate/device_state_configuration.xml \ device/generic/goldfish/data/etc/config.ini:config.ini \ device/generic/goldfish/wifi/simulated_hostapd.conf:$(TARGET_COPY_OUT_VENDOR)/etc/simulated_hostapd.conf \ device/generic/goldfish/wifi/wpa_supplicant.conf:$(TARGET_COPY_OUT_VENDOR)/etc/wifi/wpa_supplicant.conf \ - device/generic/goldfish/wifi/WifiConfigStore.xml:data/misc/wifi/WifiConfigStore.xml \ frameworks/native/data/etc/android.hardware.bluetooth_le.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.bluetooth_le.xml \ frameworks/native/data/etc/android.hardware.bluetooth.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.bluetooth.xml \ system/bt/vendor_libs/test_vendor_lib/data/controller_properties.json:vendor/etc/bluetooth/controller_properties.json \ @@ -293,14 +324,11 @@ PRODUCT_COPY_FILES += \ frameworks/native/data/etc/android.hardware.vulkan.level-1.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.vulkan.level.xml \ frameworks/native/data/etc/android.hardware.vulkan.compute-0.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.vulkan.compute.xml \ frameworks/native/data/etc/android.hardware.vulkan.version-1_1.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.hardware.vulkan.version.xml \ - device/generic/goldfish/data/etc/android.software.vulkan.deqp.level-2019-03-01.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.software.vulkan.deqp.level-2019-03-01.xml \ + frameworks/native/data/etc/android.software.vulkan.deqp.level-2020-03-01.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.software.vulkan.deqp.level.xml \ + frameworks/native/data/etc/android.software.opengles.deqp.level-2020-03-01.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.software.opengles.deqp.level.xml \ frameworks/native/data/etc/android.software.autofill.xml:$(TARGET_COPY_OUT_VENDOR)/etc/permissions/android.software.autofill.xml \ frameworks/native/data/etc/android.software.verified_boot.xml:${TARGET_COPY_OUT_PRODUCT}/etc/permissions/android.software.verified_boot.xml \ device/generic/goldfish/data/etc/permissions/privapp-permissions-goldfish.xml:$(TARGET_COPY_OUT_PRODUCT)/etc/permissions/privapp-permissions-goldfish.xml \ hardware/google/camera/devices/EmulatedCamera/hwl/configs/emu_camera_back.json:$(TARGET_COPY_OUT_VENDOR)/etc/config/emu_camera_back.json \ hardware/google/camera/devices/EmulatedCamera/hwl/configs/emu_camera_front.json:$(TARGET_COPY_OUT_VENDOR)/etc/config/emu_camera_front.json \ hardware/google/camera/devices/EmulatedCamera/hwl/configs/emu_camera_depth.json:$(TARGET_COPY_OUT_VENDOR)/etc/config/emu_camera_depth.json \ - -# Windowing settings config files -PRODUCT_COPY_FILES += \ - device/generic/goldfish/display_settings_freeform.xml:$(TARGET_COPY_OUT_DATA)/system/display_settings_freeform.xml diff --git a/wifi/WifiConfigStore.xml b/wifi/WifiConfigStore.xml deleted file mode 100644 index bb5645aa..00000000 --- a/wifi/WifiConfigStore.xml +++ /dev/null @@ -1,48 +0,0 @@ -<?xml version='1.0' encoding='utf-8' standalone='yes' ?> -<WifiConfigStoreData> - <int name="Version" value="1" /> - <NetworkList> - <Network> - <WifiConfiguration> - <string name="ConfigKey">"AndroidWifi"NONE</string> - <string name="SSID">"AndroidWifi"</string> - <null name="BSSID" /> - <null name="PreSharedKey" /> - <null name="WEPKeys" /> - <int name="WEPTxKeyIndex" value="0" /> - <boolean name="HiddenSSID" value="false" /> - <boolean name="RequirePMF" value="false" /> - <byte-array name="AllowedKeyMgmt" num="1">01</byte-array> - <byte-array name="AllowedProtocols" num="1">03</byte-array> - <byte-array name="AllowedAuthAlgos" num="1">01</byte-array> - <byte-array name="AllowedGroupCiphers" num="1">0f</byte-array> - <byte-array name="AllowedPairwiseCiphers" num="1">06</byte-array> - <boolean name="Shared" value="true" /> - <int name="Status" value="0" /> - <null name="FQDN" /> - <null name="ProviderFriendlyName" /> - <null name="LinkedNetworksList" /> - <null name="DefaultGwMacAddress" /> - <boolean name="ValidatedInternetAccess" value="true" /> - <boolean name="NoInternetAccessExpected" value="false" /> - <int name="UserApproved" value="0" /> - <boolean name="MeteredHint" value="false" /> - <boolean name="UseExternalScores" value="false" /> - <int name="NumAssociation" value="2" /> - <boolean name="IsLegacyPasspointConfig" value="false" /> - <long-array name="RoamingConsortiumOIs" num="0" /> - </WifiConfiguration> - <NetworkStatus> - <string name="SelectionStatus">NETWORK_SELECTION_ENABLED</string> - <string name="DisableReason">NETWORK_SELECTION_ENABLE</string> - </NetworkStatus> - <IpConfiguration> - <string name="IpAssignment">DHCP</string> - <string name="ProxySettings">NONE</string> - </IpConfiguration> - </Network> - </NetworkList> - <PasspointConfigData> - <long name="ProviderIndex" value="0" /> - </PasspointConfigData> -</WifiConfigStoreData> diff --git a/wifi/createns/Android.bp b/wifi/createns/Android.bp index e8de9a91..bd6a40fd 100644 --- a/wifi/createns/Android.bp +++ b/wifi/createns/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "createns", srcs: ["createns.cpp"], diff --git a/wifi/createns/createns.cpp b/wifi/createns/createns.cpp index 95aff530..73e2c63e 100644 --- a/wifi/createns/createns.cpp +++ b/wifi/createns/createns.cpp @@ -17,6 +17,7 @@ #define LOG_TAG "createns" #include <log/log.h> +#include <cutils/properties.h> #include <errno.h> #include <fcntl.h> #include <inttypes.h> @@ -148,85 +149,11 @@ static bool writeNamespacePid(const char* name, pid_t pid) { return true; } -static pid_t daemonize(int fd) { - // This convoluted way of demonizing the process is described in - // man (7) daemon. - - // (1) Close all files, we don't have any open files at this point - // (2) Reset all signal handlers to default, they already are - // (3) Reset the signal mask, we never changed it - // (4) Sanitize environment block, we didn't change the environment - // (5) Call fork - pid_t pid = ::fork(); - if (pid != 0) { - // In the parent, nothing more to do - return pid; - } - - // (6) Acquire a new session to detach from terminal - ::setsid(); - - // (7) Fork again to avoid the daemon being attached to a terminal again - pid = ::fork(); - if (pid != 0) { - // (8) This is the first child, needs to call exit - exit(0); - return pid; - } - // (9) Connect /dev/null to stdin, stdout, stderr - ::close(STDIN_FILENO); - ::close(STDOUT_FILENO); - ::close(STDERR_FILENO); - // Since open will always reuse the lowest available fd and we have closed - // every single fd at this point we can just open them in the correct order. - if (::open("/dev/null", O_RDONLY) == -1) { - ALOGE("Unable to open /dev/null as stdin"); - } - if (::open("/dev/null", O_WRONLY) == -1) { - ALOGE("Unable to open /dev/null as stdout"); - } - if (::open("/dev/null", O_WRONLY) == -1) { - ALOGE("Unable to open /dev/null as stderr"); - } - // (10) Reset umask to zero - ::umask(0); - // (11) Change directory to root (/) - if (::chdir("/") != 0) { - ALOGE("Failed to set working directory to root: %s", strerror(errno)); - } - // (12) Write the pid of the daemon to a file, we're passing this to - // the process that starts the daemon to ensure that the pid file exists - // once that process exits. Atomicity is guaranteed by that write requiring - // that the pid file does not exist to begin with. - pid = ::getpid(); - if (::write(fd, &pid, sizeof(pid)) != sizeof(pid)) { - ALOGE("Unable to write pid to pipe: %s", strerror(errno)); - ::close(fd); - exit(1); - } - ::close(fd); - // (13) Drop privileges, doing this causes problems for execns when it's - // trying to open the proc/ns/net file of this process so we can't do that. - // (14) Notify the starting process that the daemon is running, this is done - // in step (12) above. - // (15) Exit starting process happens in main where it returns. - return 0; -} - int main(int argc, char* argv[]) { if (argc != 2) { usage(argv[0]); return 1; } - int fds[2]; - if (::pipe2(fds, O_CLOEXEC) != 0) { - ALOGE("Failed to create pipe: %s", strerror(errno)); - return 1; - } - - Fd readPipe(fds[0]); - Fd writePipe(fds[1]); - if (::unshare(CLONE_NEWNET) != 0) { ALOGE("Failed to create network namespace '%s': %s", argv[1], @@ -240,8 +167,7 @@ int main(int argc, char* argv[]) { } { // Open and then immediately close the fd - Fd fd(::open(path.c_str(), O_CREAT | O_TRUNC | O_RDONLY | O_CLOEXEC, - S_IRUSR | S_IWUSR | S_IRGRP)); + Fd fd(::open(path.c_str(), O_CREAT|O_RDONLY, S_IRUSR | S_IRGRP)); if (fd.get() == -1) { ALOGE("Failed to open file %s: %s", path.c_str(), strerror(errno)); return 1; @@ -257,28 +183,13 @@ int main(int argc, char* argv[]) { return 1; } - // At this point we fork. This way we keep a process in the namespace alive - // without this command being blocking. This is valuable because it allows - // us to write the pid to a file before we exit. That way we can guarantee - // that after this command completes there is a pid to be read, there is no - // asynchronous behavior going on. - pid_t pid = daemonize(writePipe.get()); - if (pid == 0) { - // In the child - for (;;) { - pause(); - } - } else { - // In the parent, read the pid of the daemon from the pipe and write it - // to a file. - pid_t child = 0; - if (::read(readPipe.get(), &child, sizeof(child)) != sizeof(child)) { - ALOGE("Failed to read child PID from pipe: %s", strerror(errno)); - return 1; - } - if (!writeNamespacePid(argv[1], child)) { - return 1; - } + if (!writeNamespacePid(argv[1], ::getpid())) { + return 1; + } + property_set("vendor.qemu.networknamespace", "ready"); + + for (;;) { + pause(); } return 0; diff --git a/wifi/execns/Android.bp b/wifi/execns/Android.bp index a6093771..2d780f33 100644 --- a/wifi/execns/Android.bp +++ b/wifi/execns/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "execns", srcs: ["execns.cpp"], diff --git a/wifi/init.wifi.sh b/wifi/init.wifi.sh index 511d4e66..a884c96a 100755 --- a/wifi/init.wifi.sh +++ b/wifi/init.wifi.sh @@ -41,13 +41,12 @@ # | *********** *********** # -wifi_mac_prefix=`getprop net.wifi_mac_prefix` +wifi_mac_prefix=`getprop vendor.net.wifi_mac_prefix` if [ -n "$wifi_mac_prefix" ]; then /vendor/bin/mac80211_create_radios 2 $wifi_mac_prefix || exit 1 fi NAMESPACE="router" -createns ${NAMESPACE} # createns will have created a file that contains the process id (pid) of a # process running in the network namespace. This pid is needed for some commands diff --git a/wifi/mac80211_create_radios/Android.bp b/wifi/mac80211_create_radios/Android.bp index a0be8f3c..2f39a4fe 100644 --- a/wifi/mac80211_create_radios/Android.bp +++ b/wifi/mac80211_create_radios/Android.bp @@ -1,3 +1,12 @@ +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_binary { name: "mac80211_create_radios", vendor: true, diff --git a/wifi/mac80211_create_radios/main.cpp b/wifi/mac80211_create_radios/main.cpp index 6400a1fa..3b9f1493 100644 --- a/wifi/mac80211_create_radios/main.cpp +++ b/wifi/mac80211_create_radios/main.cpp @@ -71,6 +71,7 @@ struct nl_msg_deleter { constexpr char kHwSimFamilyName[] = "MAC80211_HWSIM"; constexpr int kHwSimVersion = 1; +constexpr int kChannels = 2; const char* nlErrStr(const int e) { return (e < 0) ? nl_geterror(e) : ""; } @@ -114,6 +115,9 @@ buildCreateRadioMessage(const int family, const uint8_t mac[ETH_ALEN]) { ret = nla_put_flag(msg.get(), HWSIM_ATTR_SUPPORT_P2P_DEVICE); if (ret) { RETURN_NL_ERROR("nla_put(HWSIM_ATTR_SUPPORT_P2P_DEVICE)", ret, nullptr); } + ret = nla_put_u32(msg.get(), HWSIM_ATTR_CHANNELS, kChannels); + if (ret) { RETURN_NL_ERROR("nla_put(HWSIM_ATTR_CHANNELS)", ret, nullptr); } + RETURN(msg); } diff --git a/wifi/wifi_hal/Android.bp b/wifi/wifi_hal/Android.bp index 88c1e30d..b21ddb46 100644 --- a/wifi/wifi_hal/Android.bp +++ b/wifi/wifi_hal/Android.bp @@ -12,6 +12,15 @@ // See the License for the specific language governing permissions and // limitations under the License. +package { + // See: http://go/android-license-faq + // A large-scale-change added 'default_applicable_licenses' to import + // all of the 'license_kinds' from "device_generic_goldfish_license" + // to get the below license kinds: + // SPDX-license-identifier-Apache-2.0 + default_applicable_licenses: ["device_generic_goldfish_license"], +} + cc_library_static { name: "libwifi-hal-emu", cflags: [ @@ -28,6 +37,7 @@ cc_library_static { "wifi_hal.cpp", ], shared_libs: [ + "libnl", "liblog", "libcutils", "libhardware_legacy", diff --git a/wifi/wifi_hal/interface.cpp b/wifi/wifi_hal/interface.cpp index 7c683e52..397896b1 100644 --- a/wifi/wifi_hal/interface.cpp +++ b/wifi/wifi_hal/interface.cpp @@ -22,6 +22,8 @@ #include <linux/rtnetlink.h> +#include <future> + // Provide some arbitrary firmware and driver versions for now static const char kFirmwareVersion[] = "1.0"; static const char kDriverVersion[] = "1.0"; @@ -86,6 +88,9 @@ wifi_error Interface::getName(char* name, size_t size) { return WIFI_SUCCESS; } +// Wifi legacy HAL implicitly assumes getLinkStats is blocking and +// handler will be set to nullptr immediately after invocation. +// Therefore, this function will wait until onLinkStatsReply is called. wifi_error Interface::getLinkStats(wifi_request_id requestId, wifi_stats_result_handler handler) { NetlinkMessage message(RTM_GETLINK, mNetlink.getSequenceNumber()); @@ -97,12 +102,20 @@ wifi_error Interface::getLinkStats(wifi_request_id requestId, info->ifi_flags = 0; info->ifi_change = 0xFFFFFFFF; - bool success = mNetlink.sendMessage(message, - std::bind(&Interface::onLinkStatsReply, - this, - requestId, - handler, - std::placeholders::_1)); + std::promise<void> p; + + auto callback = [this, requestId, &handler, + &p] (const NetlinkMessage& message) { + onLinkStatsReply(requestId, handler, message); + p.set_value(); + }; + + bool success = mNetlink.sendMessage(message, callback); + // Only wait when callback will be invoked. Therefore, test if the message + // is sent successfully first. + if (success) { + p.get_future().wait(); + } return success ? WIFI_SUCCESS : WIFI_ERROR_UNKNOWN; } diff --git a/wifi/wifi_hal/netlinkmessage.cpp b/wifi/wifi_hal/netlinkmessage.cpp index baf5800d..06bb7438 100644 --- a/wifi/wifi_hal/netlinkmessage.cpp +++ b/wifi/wifi_hal/netlinkmessage.cpp @@ -22,6 +22,7 @@ #include <linux/rtnetlink.h> #include <sys/types.h> #include <unistd.h> +#include <netlink/msg.h> size_t getSpaceForMessageType(uint16_t type) { switch (type) { @@ -51,13 +52,12 @@ NetlinkMessage::NetlinkMessage(const char* data, size_t size) bool NetlinkMessage::getAttribute(int attributeId, void* data, size_t size) const { const void* value = nullptr; - uint16_t attrSize = 0; - if (!findAttribute(attributeId, &value, &attrSize)) { - return false; - } - if (size > attrSize) { + const auto attr = nlmsg_find_attr((struct nlmsghdr*)mData.data(), sizeof(ifinfomsg), attributeId); + if (!attr) { return false; } + value = (const uint8_t*) attr + NLA_HDRLEN; + size = attr->nla_len; memcpy(data, value, size); return true; } @@ -71,30 +71,3 @@ uint32_t NetlinkMessage::sequence() const { auto header = reinterpret_cast<const nlmsghdr*>(mData.data()); return header->nlmsg_seq; } - -bool NetlinkMessage::findAttribute(int attributeId, - const void** value, - uint16_t* size) const { - const uint8_t* end = mData.data() + mData.size(); - size_t attrOffset = getSpaceForMessageType(type()); - if (attrOffset == 0) { - return false; - } - const uint8_t* attribute = mData.data() + attrOffset; - while (attribute < end) { - auto header = reinterpret_cast<const nlattr*>(attribute); - if (header->nla_len == 0) { - // The length should include the header so the length should always - // be greater than zero. If it doesn't we're going to end up looping - // forever so ignore this. - return false; - } - if (header->nla_type == attributeId) { - *value = attribute + NLA_HDRLEN; - *size = header->nla_len; - return true; - } - attribute += header->nla_len; - } - return false; -} diff --git a/wifi/wifi_hal/netlinkmessage.h b/wifi/wifi_hal/netlinkmessage.h index 45fd7cdb..5e1a3b80 100644 --- a/wifi/wifi_hal/netlinkmessage.h +++ b/wifi/wifi_hal/netlinkmessage.h @@ -60,9 +60,6 @@ private: NetlinkMessage& operator=(const NetlinkMessage&) = delete; bool getAttribute(int attributeId, void* data, size_t size) const; - bool findAttribute(int attributeId, - const void** value, - uint16_t* size) const; std::vector<uint8_t> mData; }; diff --git a/wifi/wpa_supplicant_8_lib/Android.mk b/wifi/wpa_supplicant_8_lib/Android.mk index 76b09691..4c565d41 100644 --- a/wifi/wpa_supplicant_8_lib/Android.mk +++ b/wifi/wpa_supplicant_8_lib/Android.mk @@ -64,6 +64,8 @@ L_CFLAGS += -Wno-unused-parameter include $(CLEAR_VARS) LOCAL_MODULE := lib_driver_cmd_simulated +LOCAL_LICENSE_KINDS := SPDX-license-identifier-BSD +LOCAL_LICENSE_CONDITIONS := notice LOCAL_VENDOR_MODULE := true LOCAL_SHARED_LIBRARIES := libc libcutils liblog LOCAL_HEADER_LIBRARIES := libcutils_headers diff --git a/x86-vendor.mk b/x86-vendor.mk index 720dfb57..3341835f 100644 --- a/x86-vendor.mk +++ b/x86-vendor.mk @@ -1,6 +1,4 @@ -PRODUCT_KERNEL_VERSION := 5.4 -BOARD_VENDOR_RAMDISK_KERNEL_MODULES += \ - $(wildcard prebuilts/qemu-kernel/x86_64/$(PRODUCT_KERNEL_VERSION)/ko/*.ko) +include device/generic/goldfish/x86_64-kernel.mk PRODUCT_PROPERTY_OVERRIDES += \ vendor.rild.libpath=/vendor/lib/libgoldfish-ril.so @@ -10,21 +8,25 @@ PRODUCT_PROPERTY_OVERRIDES += \ # build quite specifically for the emulator, and might not be # entirely appropriate to inherit from for on-device configurations. PRODUCT_COPY_FILES += \ - device/generic/goldfish/data/etc/config.ini.nexus5:config.ini \ + device/generic/goldfish/data/etc/config.ini.xl:config.ini \ device/generic/goldfish/data/etc/advancedFeatures.ini:advancedFeatures.ini \ device/generic/goldfish/data/etc/encryptionkey.img:encryptionkey.img \ device/generic/goldfish/task_profiles.json:$(TARGET_COPY_OUT_VENDOR)/etc/task_profiles.json \ - prebuilts/qemu-kernel/x86_64/$(PRODUCT_KERNEL_VERSION)/kernel-qemu2:kernel-ranchu-64 + $(EMULATOR_KERNEL_FILE):kernel-ranchu-64 + PRODUCT_SDK_ADDON_COPY_FILES += \ device/generic/goldfish/data/etc/advancedFeatures.ini:images/x86/advancedFeatures.ini \ device/generic/goldfish/data/etc/encryptionkey.img:images/x86/encryptionkey.img \ - prebuilts/qemu-kernel/x86_64/$(PRODUCT_KERNEL_VERSION)/kernel-qemu2:images/x86/kernel-ranchu-64 + $(EMULATOR_KERNEL_FILE):images/x86/kernel-ranchu-64 -PRODUCT_COPY_FILES += \ - device/generic/goldfish/data/etc/x86/emulatorip:$(TARGET_COPY_OUT_VENDOR)/bin/ip +PRODUCT_PACKAGES += \ + emulatorip +PRODUCT_PROPERTY_OVERRIDES += \ + ro.crypto.dm_default_key.options_format.version=2 -PRODUCT_SHIPPING_API_LEVEL := 28 +PRODUCT_SHIPPING_API_LEVEL := 31 +PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS := false TARGET_USES_MKE2FS := true ifeq ($(QEMU_DISABLE_AVB),true) diff --git a/x86_64-kernel.mk b/x86_64-kernel.mk new file mode 100644 index 00000000..db4dbe1e --- /dev/null +++ b/x86_64-kernel.mk @@ -0,0 +1,12 @@ +TARGET_KERNEL_USE ?= 5.10 + +KERNEL_MODULES_PATH := kernel/prebuilts/common-modules/virtual-device/$(TARGET_KERNEL_USE)/x86-64 + +KERNEL_MODULES_EXCLUDE := \ + $(KERNEL_MODULES_PATH)/virt_wifi.ko \ + $(KERNEL_MODULES_PATH)/virt_wifi_sim.ko + +BOARD_VENDOR_RAMDISK_KERNEL_MODULES += \ + $(filter-out $(KERNEL_MODULES_EXCLUDE), $(wildcard $(KERNEL_MODULES_PATH)/*.ko)) + +EMULATOR_KERNEL_FILE := kernel/prebuilts/$(TARGET_KERNEL_USE)/x86_64/kernel-$(TARGET_KERNEL_USE) diff --git a/x86_64-vendor.mk b/x86_64-vendor.mk index 6dfadc0e..be16c323 100644 --- a/x86_64-vendor.mk +++ b/x86_64-vendor.mk @@ -1,6 +1,4 @@ -PRODUCT_KERNEL_VERSION := 5.4 -BOARD_VENDOR_RAMDISK_KERNEL_MODULES += \ - $(wildcard prebuilts/qemu-kernel/x86_64/$(PRODUCT_KERNEL_VERSION)/ko/*.ko) +include device/generic/goldfish/x86_64-kernel.mk PRODUCT_PROPERTY_OVERRIDES += \ vendor.rild.libpath=/vendor/lib64/libgoldfish-ril.so @@ -10,23 +8,39 @@ PRODUCT_PROPERTY_OVERRIDES += \ # build quite specifically for the emulator, and might not be # entirely appropriate to inherit from for on-device configurations. PRODUCT_COPY_FILES += \ - device/generic/goldfish/data/etc/config.ini.nexus5:config.ini \ + device/generic/goldfish/data/etc/config.ini.xl:config.ini \ device/generic/goldfish/data/etc/advancedFeatures.ini:advancedFeatures.ini \ device/generic/goldfish/data/etc/encryptionkey.img:encryptionkey.img \ device/generic/goldfish/task_profiles.json:$(TARGET_COPY_OUT_VENDOR)/etc/task_profiles.json \ - prebuilts/qemu-kernel/x86_64/$(PRODUCT_KERNEL_VERSION)/kernel-qemu2:kernel-ranchu + $(EMULATOR_KERNEL_FILE):kernel-ranchu PRODUCT_SDK_ADDON_COPY_FILES += \ device/generic/goldfish/data/etc/advancedFeatures.ini:images/x86_64/advancedFeatures.ini \ device/generic/goldfish/data/etc/encryptionkey.img:images/x86_64/encryptionkey.img \ - prebuilts/qemu-kernel/x86_64/$(PRODUCT_KERNEL_VERSION)/kernel-qemu2:images/x86_64/kernel-ranchu + $(EMULATOR_KERNEL_FILE):images/x86_64/kernel-ranchu PRODUCT_COPY_FILES += \ - device/generic/goldfish/data/etc/configs/gpu.config:data/misc/gceconfigs/gpu.config \ - device/generic/goldfish/data/etc/x86/emulatorip:$(TARGET_COPY_OUT_VENDOR)/bin/ip + device/generic/goldfish/data/etc/configs/gpu.config:data/misc/gceconfigs/gpu.config +# a hack to reduce presubmit time where CTS tries to install media files one by one +# taking more than 30 minutes; following is just the list of files needed by current +# tests on presubmit +PRODUCT_COPY_FILES += \ + device/generic/goldfish/data/media/test/swirl_136x144_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_136x144_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_132x130_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_132x130_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_130x132_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_130x132_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_144x136_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_144x136_mpeg4.mp4 \ + device/generic/goldfish/data/media/test/swirl_128x128_mpeg4.mp4:data/media/0/test/CtsMediaTestCases-1.4/swirl_128x128_mpeg4.mp4 + + +PRODUCT_PACKAGES += \ + emulatorip + +PRODUCT_PROPERTY_OVERRIDES += \ + ro.crypto.dm_default_key.options_format.version=2 -PRODUCT_SHIPPING_API_LEVEL := 28 +PRODUCT_SHIPPING_API_LEVEL := 31 +PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS := false TARGET_USES_MKE2FS := true |