summaryrefslogtreecommitdiff
path: root/compiler/optimizing/code_generator_mips.cc
AgeCommit message (Collapse)Author
2020-02-13Remove MIPS support from Optimizing.Vladimir Marko
Test: aosp_taimen-userdebug boots. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Bug: 147346243 Change-Id: I97fdc15e568ae3fe390efb1da690343025f84944
2019-10-14Revert "Make compiler/optimizing/ symbols hidden."Vladimir Marko
This reverts commit e2727154f25e0db9a5bb92af494d8e47b181dfcf. Reason for revert: Breaks ASAN tests (ODR violation). Bug: 142365358 Change-Id: I38103d74a1297256c81d90872b6902ff1e9ef7a4
2019-10-14Make compiler/optimizing/ symbols hidden.Vladimir Marko
Make symbols in compiler/optimizing hidden by a namespace attribute. The unit intrinsic_objects.{h,cc} is excluded as it is needed by dex2oat. As the symbols are no longer exported, gtests are now linked with the static version of the libartd-compiler library. libart-compiler.so size: - before: arm: 2396152 arm64: 3345280 - after: arm: 2016176 (-371KiB, -15.9%) arm64: 2874480 (-460KiB, -14.1%) Test: m test-art-host-gtest Test: testrunner.py --host --optimizing --jit Bug: 142365358 Change-Id: I1fb04a33351f53f00b389a1642e81a68e40912a8
2019-08-02ART: ARM64: Optimize frame size for SIMD graphs.Artem Serov
For SIMD graphs allocate 64 bit instead of 128 bit on stack for each FP register to be preserved by the callee in the frame entry as ABI suggests (currently 64-bit registers are preserved but more space on stack is allocated). Note: slow paths still require spilling full 128-bit Q-Registers for SIMD graphs due to register allocator restrictions. Test: test-art-target. Change-Id: Ie0b12e4b769158445f3d0f4562c70d4fb0ea7744
2019-07-30Compiler changes for boot image extension.Vladimir Marko
Test: m test-art-host-gtest Test: testrunnner.py --host --optimizing Test: aosp_taimen-userdebug boots. Test: run-gtest.sh Test: testrunner.py --target --optimizing Change-Id: I8e999c96ec908f26d8c529edc9d2a3be49a9379a
2019-07-16Clean up linker patches in codegens.Vladimir Marko
In preparation for introducing boot image extension, make sure that we can use both kBootImageLinkTimePcRelative and kBootImageRelRo load kinds at the same time. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Test: aosp_taimen-userdebug boots Test: run-gtests.sh Test: testrunner.py --target --optimizing Change-Id: I340f2d7d19e1c20699b37b0304d2e487d497da98
2019-05-16ART: Optimize StringBuilder append pattern.Vladimir Marko
Recognize appending with StringBuilder and replace the entire expression with a runtime call that perfoms the append in a more efficient manner. For now, require the entire pattern to be in a single block and be very strict about the StringBuilder environment uses. Also, do not accept StringBuilder/char[]/Object/float/double arguments as they throw non-OOME exceptions and/or require a call from the entrypoint back to a helper function in Java; these shall be implemented later. Boot image size for aosp_taimen-userdebug: - before: arm/boot*.oat: 19653872 arm64/boot*.oat: 23292784 oat/arm64/services.odex: 22408664 - after: arm/boot*.oat: 19432184 (-216KiB) arm64/boot*.oat: 22992488 (-293KiB) oat/arm64/services.odex: 22376776 (-31KiB) Note that const-string in compiled boot image methods cannot throw, but for apps it can and therefore its environment can prevent the optimization for apps. We could implement either a simple carve-out for const-string or generic environment pruning to allow this pattern to be applied more often. Results for the new StringBuilderAppendBenchmark on taimen: timeAppendLongStrings: ~700ns -> ~200ns timeAppendStringAndInt: ~220ns -> ~140ns timeAppendStrings: ~200ns -> 130ns Bug: 19575890 Test: 697-checker-string-append Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Test: aosp_taimen-userdebug boots. Test: run-gtests.sh Test: testrunner.py --target --optimizing Test: vogar --benchmark art/benchmark/stringbuilder-append/src/StringBuilderAppendBenchmark.java Change-Id: I51789bf299f5219f68ada4c077b6a1d3fe083964
2019-03-12Fix non-deterministic compilation for const-string...Vladimir Marko
... in inlined methods that are not in the boot profile. If such string is not in the boot image for other reasons, do not resolve the string and use the kBssEntry load kind. Boot image sizes for aosp_taimen-userdebug: - before: arm/boot*.art: 12349440 arm/boot*.oat: 19862024 arm64/boot*.art: 16609280 arm64/boot*.oat: 23568592 - after: arm/boot*.art: 12324864 (-24KiB) arm/boot*.oat: 19936612 (+73KiB) arm64/boot*.art: 16580608 (-28KiB) arm64/boot*.oat: 23642120 (+72KiB) Test: aosp_taimen-userdebug boots. Test: m test-art-host-gtest Bug: 26687569 Change-Id: I3e0b72cd5e8c67904517856208f25a6c379ab601
2018-12-27ART: Refactor for bugprone-argument-commentAndreas Gampe
Handles compiler. Bug: 116054210 Test: WITH_TIDY=1 mmma art Change-Id: I5cdfe73c31ac39144838a2736146b71de037425e
2018-11-29C++17 compatibility: make WITH_TIDY=1 happy again.Elliott Hughes
Bug: http://b/111067277 Test: builds Change-Id: I8b69ea3815e14bb6eb27f40c0dd01a85b340a355
2018-10-16Fix HNewArray with unresolved primitive array type.Vladimir Marko
And enable test 920-objects that was crashing because of this bug. Test: testrunner.py --host --jit-on-first-use -t 920 Test: testrunner.py --host --optimizing Test: m test-art-host-gtest Bug: 117638896 Change-Id: I47dc893b121c82de537b3147c86d37a6eecf2d62
2018-10-10ART: Completely remove the --compile-pic option.Vladimir Marko
And the PIC-related fields from image header. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing Bug: 77856493 Change-Id: I3787369378f12d8cd9003bebeae62830a67def33
2018-09-19Remove sharpening as an optimization pass.Nicolas Geoffray
Make the last sharpening helper (methods) like the other helpers: being invoked by the instruction builder. Test: test.py Change-Id: Ic80a454f9b59b0b4ef7825590b24402500ba851c
2018-08-28Use 'final' and 'override' specifiers directly in ART.Roland Levillain
Remove all uses of macros 'FINAL' and 'OVERRIDE' and replace them with 'final' and 'override' specifiers. Remove all definitions of these macros as well, which were located in these files: - libartbase/base/macros.h - test/913-heaps/heaps.cc - test/ti-agent/ti_macros.h ART is now using C++14; the 'final' and 'override' specifiers have been introduced in C++11. Test: mmma art Change-Id: I256c7758155a71a2940ef2574925a44076feeebf
2018-08-14Rename art::ReadBarrier::WhiteState as art::ReadBarrier::NonGrayState.Roland Levillain
The read barrier state recorded in object's lockword used to be a three-state value (white/gray/black), which was turned into a two-state value (white/gray), where the "black" state was conceptually merged into the "white" state. This change renames the "white" state as "non-gray" and adjusts corresponding comments. Test: art/test.py Change-Id: I2a17ed15651bdbbe99270c1b81b4d78a1c2c132b
2018-08-14Document the use of the biased card table in ART's code generators.Roland Levillain
Test: n/a Change-Id: Ie03a6f6dc87fd0766fc2b685ec39a0a0ebe3fb57
2018-08-03Rename type resolution entrypoints.Vladimir Marko
Rename the InitializeType and InitializeTypeAndVerifyAccess entrypoints to Resolve* to better match their semantics. Keep the InitializeStaticStorage name for now as the most appropriate name InitializeType would clash with the old name of the ResolveType entrypoint. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Change-Id: Ide55b58c490d085ab37d8536f90699f7ed571d59
2018-08-03Do not save/restore regs in ClinitCheck slow path.Vladimir Marko
The entrypoint is kSaveEverything, so the only register that needs to be saved is the argument/return value register. The size of the aosp_taimen-userdebug prebuilts: - before: arm/boot*.oat: 16811692 arm64/boot*.oat: 19801032 oat/arm64/services.odex: 20232208 - after: arm/boot*.oat: 16798804 (-12.6KiB, -0.08%) arm64/boot*.oat: 19804392 (+3.3KiB, +0.02%) oat/arm64/services.odex: 20227784 (-4.3KiB, -0.02%) Note that though there is less code, the metadata for the arm64/boot*.oat outweighs the code size reduction because of the register map encoding as value+shift introduced in https://android-review.googlesource.com/695682 which it's ill-suited for kSaveEverything entrypoints. We should reconsider that encoding. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing Change-Id: I5cd1deb90332a3b88a0a59d87925c557d9bff1ab
2018-08-02Rewrite Class init entrypoint to take a Class arg.Vladimir Marko
Fixes invalid type index being passed to the entrypoint for class init check across dex files when the target type does not have a TypeId in the compilation unit's DexFile. The size of the aosp_taimen-userdebug prebuilts: - before: arm/boot*.oat: 16782748 arm64/boot*.oat: 19764400 oat/arm64/services.odex: 20162432 - after: arm/boot*.oat: 16811692 (+28.3KiB, +0.17%) arm64/boot*.oat: 19801032 (+35.8KiB, +0.19%) oat/arm64/services.odex: 20232208 (+68.1KiB, +0.35%) This increase comes from doing two runtime calls instead of one for HLoadClass/kBssEntry that MustGenerateClinitCheck(). Test: Additional test in 476-clinit-inline-static-invoke Test: m test-art-host-gtest Test: testrunner.py --host --optimizing --jit Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing --jit Test: testrunner.py --jvm Bug: 111433619 Change-Id: I2fccd6944480ab4dac514f60d38e72c1014ae7b2
2018-07-16Always produce PIC code for AOT compilation.Vladimir Marko
Change sharpening to use PIC load kinds for AOT compilation and add "Jit" to the direct addressing load kind names. Use PIC code also for the Integer.valueOf() intrinsic codegen. Remove all support for non-PIC linker patches. The dex2oat --compile-pic option is retained for now but ignored by the compiler. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing Bug: 77856493 Change-Id: I54d666f6522f160a1b6ece4045a15d19363acbb6
2018-07-10Don't use StringFactory.newEmptyString in compiled codeAlex Light
When compiling debuggable code we would compile a new-instance String instruction into a StringFactory.newEmptyString invoke. This additional invoke could be observed using tracing and is inconsistent with the interpreter, where the string is simply allocated directly. In order to bring these two modes into alignment we added a new AllocStringObject quick entrypoint that will be used instead of the normal AllocObject<...> entrypoints when allocating a string. This entrypoint directly allocates a new string in the same manner the interpreter does. Needs next CL for test to work. Bug: 110884646 Test: ./test/testrunner/testrunner.py --host --runtime-option=-Xjitthreshold:0 --jit Test: Manual inspection of compiled code. Change-Id: I7b4b084bcf7dd9a23485c0e3cd2cd04a04b43d3d
2018-06-29Implement Integer.valueOf() intrinsic for boot image.Vladimir Marko
And generate only one "boot image live objects" array rather than one per boot*.art file. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing Bug: 71526895 Change-Id: I23af7f47fea5150805f801cd2512f2d152ee5b73
2018-06-25Move instruction_set_ to CompilerOptions.Vladimir Marko
Removes CompilerDriver dependency from ImageWriter and several other classes. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing Test: Pixel 2 XL boots. Test: m test-art-target-gtest Test: testrunner.py --target --optimizing Change-Id: I3c5b8ff73732128b9c4fad9405231a216ea72465
2018-06-21Implement Integer.valueOf() intrinsic for PIC.Vladimir Marko
And fix the intrinsic for JIT even in case when someone messes up the IntegerCache using reflection. Two cases are exposed with a regression test (one that previously failed randomly and one that failed 100%) but other crashes were possible; for example, we would need a read barrier for array reads when elements are not guaranteed to be in the boot image. The new approach loads references only from the boot image live objects array which cannot be touched by reflection. The referenced objects and IntegerCache.cache are exposed and can lead to weird behavior but not crashes. On x86, the pc_relative_fixups_86 actually checks the cache an additional time but discrepancies between this check and the location building at the beginning of codegen should be OK as the HIsX86ComputeBaseMethodAddress should be added for PIC regardless of whether pc_relative_fixups_86 thinks the method is intrinsified or not. Test: 717-integer-value-of Test: Pixel 2 XL boots. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing --pictest --npictest Test: testrunner.py --host --jit Test: testrunner.py --target --optimizing --pictest --npictest Test: testrunner.py --target --jit Bug: 71526895 Change-Id: I89b3245a62aba22980c86a99e2af480bfa250af1
2018-06-11ART: Adds an entrypoint for invoke-customOrion Hodson
Add support for the compiler to call into the runtime for invoke-custom bytecodes. Bug: 35337872 Test: art/test.py --host -r -t 952 Test: art/test.py --target --64 -r -t 952 Test: art/test.py --target --32 -r -t 952 Change-Id: I821432e7e5248c91b8e1d36c3112974c34171803
2018-05-30Remove the CodeOffset helper class.David Srbecky
I need to reduce the StackMapEntry to a POD type so that it can be used in BitTableBuilder. Test: test-art-host-gtest-stack_map_test Change-Id: I5f9ad7fdc9c9405f22669a11aea14f925ef06ef7
2018-05-11ART: Compiler support for const-method-handleOrion Hodson
Implemented as a runtime call. Bug: 66890674 Test: art/test.py --target -r -t 979 Test: art/test.py --target --64 -r -t 979 Test: art/test.py --host -r -t 979 Change-Id: I67f461c819a7d528d7455afda8b4a59e9aed381c
2018-05-10ART: Compiler support for const-method-typeOrion Hodson
Implemented as a runtime call. Bug: 66890674 Test: art/test.py --target -r -t 979 Test: art/test.py --target --64 -r -t 979 Test: art/test.py --host -r -t 979 Change-Id: I4b3d3969d455d0198cfe122eea8abd54e0ea20ee
2018-03-27Revert^4 "Compiler changes for bitstring based type checks."Vladimir Marko
Disabled the build time flag. (No image version bump needed.) Bug: 26687569 Bug: 64692057 Bug: 76420366 This reverts commit 3fbd3ad99fad077e5c760e7238bcd55b07d4c06e. Change-Id: I5d83c4ce8a7331c435d5155ac6e0ce1c77d60004
2018-03-26Revert^3 "Compiler changes for bitstring based type checks."Andreas Gampe
This reverts commit 3f41323cc9da335e9aa4f3fbad90a86caa82ee4d. Reason for revert: Fails sporadically. Bug: 26687569 Bug: 64692057 Bug: 76420366 Change-Id: I84d1e9e46c58aeecf17591ff71fbac6a1e583909
2018-03-22Revert^2 "Compiler changes for bitstring based type checks."Vladimir Marko
Add extra output for debugging failures and re-enable the bitstring type checks. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing --jit Test: testrunner.py --host -t 670-bitstring-type-check Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing --jit Test: testrunner.py --target -t 670-bitstring-type-check Bug: 64692057 Bug: 26687569 This reverts commit bff7a52e2c6c9e988c3ed1f12a2da0fa5fd37cfb. Change-Id: I090e241983f3ac6ed8394d842e17716087d169ac
2018-03-09Merge "Retrieve String/Class references from .data.bimg.rel.ro."Vladimir Marko
2018-03-08Merge "Load ArtMethod* from .data.bimg.rel.ro entries."Vladimir Marko
2018-03-08Retrieve String/Class references from .data.bimg.rel.ro.Vladimir Marko
For PIC AOT-compiled app, use the .data.bimg.rel.ro to load the boot image String/Class references instead of using the mmapped boot image ClassTable and InternTable. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing --pictest --npictest Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing --pictest --npictest Bug: 71526895 Change-Id: Id5703229777aecb589a933a41f92e44d3ec02a3d
2018-03-08Load ArtMethod* from .data.bimg.rel.ro entries.Vladimir Marko
Introduce a new .data.bimg.rel.ro section in oat files where we store offsets of boot image objects from the beginning of the boot image. At runtime we relocate these entries using the actual boot image address to turn offsets to pointers. Use the .data.bimg.rel.ro to prepare the boot image methods used by HInvokeStaticOrDirect for PIC AOT app compilation. Loading the ArtMethod* from .data.bimg.rel.ro instead of the .bss avoids the initial call to the resolution trampoline. Test: Additional test in 522-checker-sharpening Test: m test-art-host-gtest Test: testrunner.py --host --optimizing --pictest --npictest Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing --pictest --npictest Bug: 71526895 Change-Id: Ie5f5b1f622704877b36730377146e59092e46c0c
2018-03-07Minor cleanup of MIN/MAX code.Aart Bik
Rationale: Share the type dispatching code better. Bug: b/65164101 Test: test-art-host,target Change-Id: Ib06c915d570fd0a53f7734cdb316d2d16310db74
2018-03-07Introduce MIN/MAX/ABS as HIR nodes.Aart Bik
Rationale: Having explicit MIN/MAX/ABS operations (in contrast with intrinsics) simplifies recognition and optimization of these common operations (e.g. constant folding, hoisting, detection of saturation arithmetic). Furthermore, mapping conditionals, selectors, intrinsics, etc. (some still TBD) onto these operations generalizes the way they are optimized downstream substantially. Bug: b/65164101 Test: test-art-host,target Change-Id: I69240683339356e5a012802f179298f0b04c6726
2018-03-05Merge "Introduce ABS as HIR nodes."Treehugger Robot
2018-03-01Introduce ABS as HIR nodes.Aart Bik
NOTE: step 1 of 2 for "Introduce MIN/MAX/ABS as HIR nodes." Rationale: Having explicit MIN/MAX/ABS operations (in contrast with intrinsics) simplifies recognition and optimization of these common operations (e.g. constant folding, hoisting, detection of saturation arithmetic). Furthermore, mapping conditionals, selectors, intrinsics, etc. (some still TBD) onto these operations generalizes the way they are optimized downstream substantially. Bug: b/65164101 Test: test-art-host,target Change-Id: I9c93987197216158ba02c8aca2385086adedabc4
2018-03-01MIPS: Use sltiu instead of LoadConst32() + sltuLena Djokic
Bltu is sltu + bnez so we can use sltiu + bnez without loading constant (if it is 16-bit constant). Additionally, in VisitInvokeInterface() LoadConst32() is moved to before Jalr(T9) so the load can be taken into the delay slot. Test: ./testrunner.py --target --optimizing in QEMU Change-Id: Ic19f251aeba015be38b7d3690e78b2fe59e7c5ae
2018-02-20ART: Clean up patching data in codegens.Vladimir Marko
Reuse PatchInfo<> for additional architectures and make the naming more consistent across architectures. Change the DexFile reference to pointer in preparation for patching references to the upcoming .data.bimg.rel.ro section. Update obsolete comments; instead of referencing dex cache arrays which were used in the past, reference the .bss and the .data.bimg.rel.ro which shall be used in upcoming CLs. Test: Rely on TreeHugger. Change-Id: I03be4c4118918189e55c62105bb594500c6a42c1
2018-02-12Merge "MIPS32 Implement signed 64-bit division by powers of 2"Treehugger Robot
2018-02-08Add support for counting hotness in compiled code for MIPSGoran Jakovljevic
This is a follow up to I0f63c644527b74f6ef2649f481c2a1c731bb9f21. This fixes 674-hotness-compiled test failures for MIPS32 and MIPS64. Test: ./testrunner.py --target --optimizing in QEMU Change-Id: I22eb02594518f315d9e3a3e5fa895a6833574bba
2018-02-02Merge "MIPS: Clean up InstanceOf/CheckCast."Treehugger Robot
2018-02-01Clean up signed/unsigned in vectorizer.Aart Bik
Rationale: Currently we have some remaining ugliness around signed and unsigned SIMD operations due to lack of kUint32 and kUint64 in the HIR. By "softly" introducing these types, ABS/MIN/MAX/HALVING_ADD/SAD_ACCUMULATE operations can solely rely on the packed data types to distinguish between signed and unsigned operations. Cleaner, and also allows for some code removal in the current loop optimizer. Bug: 72709770 Test: test-art-host test-art-target Change-Id: I68e4cdfba325f622a7256adbe649735569cab2a3
2018-01-29Add compiler option for counting hotness in compiled code.Nicolas Geoffray
For eventually easier profiling of boot classpath and system server. bug: 30934496 Test: 674-hotness-compiled Change-Id: I0f63c644527b74f6ef2649f481c2a1c731bb9f21
2018-01-25MIPS: Clean up InstanceOf/CheckCast.Alexey Frunze
This is a MIPS-specific follow-up to https://android-review.googlesource.com/567637 Test: booted MIPS32R2 in QEMU Test: booted MIPS64R6 in QEMU Test: ./run-test --optimizing 603-checker-instanceof Change-Id: Ic5312d98e51aeff11c9f7371be394d5cad319bec
2018-01-25Revert "Compiler changes for bitstring based type checks."Nicolas Geoffray
Bug: 64692057 Bug: 71853552 Bug: 26687569 This reverts commit eb0ebed72432b3c6b8c7b38f8937d7ba736f4567. Change-Id: I7daeaa077960ba41b2ed42bc47f17501621be4be
2018-01-25MIPS32 Implement signed 64-bit division by powers of 2Lena Djokic
Test: ./testrunner.py --target --optimizing in QEMU Change-Id: I662770eb31d557392588b637f6b03dd5aee96a83
2018-01-23Compiler changes for bitstring based type checks.Vladimir Marko
We guard the use of this feature with a compile-time flag, set to true in this CL. Boot image size for aosp_taimen-userdebug in AOSP master: - before: arm boot*.oat: 63604740 arm64 boot*.oat: 74237864 - after: arm boot*.oat: 63531172 (-72KiB, -0.1%) arm64 boot*.oat: 74135008 (-100KiB, -0.1%) The new TypeCheckBenchmark yields the following changes using the little cores of taimen fixed at 1.4016GHz: 32-bit 64-bit timeCheckCastLevel1ToLevel1 11.48->15.80 11.47->15.78 timeCheckCastLevel2ToLevel1 15.08->15.79 15.08->15.79 timeCheckCastLevel3ToLevel1 19.01->15.82 17.94->15.81 timeCheckCastLevel9ToLevel1 42.55->15.79 42.63->15.81 timeCheckCastLevel9ToLevel2 39.70->14.36 39.70->14.35 timeInstanceOfLevel1ToLevel1 13.74->17.93 13.76->17.95 timeInstanceOfLevel2ToLevel1 17.02->17.95 16.99->17.93 timeInstanceOfLevel3ToLevel1 24.03->17.95 24.45->17.95 timeInstanceOfLevel9ToLevel1 47.13->17.95 47.14->18.00 timeInstanceOfLevel9ToLevel2 44.19->16.52 44.27->16.51 This suggests that the bitstring typecheck should not be used for exact type checks which would be equivalent to the "Level1ToLevel1" benchmark. Whether the implementation is a beneficial replacement for the kClassHierarchyCheck and kAbstractClassCheck on average depends on how many levels from the target class (or Object for a negative result) is a typical object's class. Test: m test-art-host-gtest Test: testrunner.py --host --optimizing --jit Test: testrunner.py --host -t 670-bitstring-type-check Test: Pixel 2 XL boots. Test: testrunner.py --target --optimizing --jit Test: testrunner.py --target -t 670-bitstring-type-check Bug: 64692057 Bug: 71853552 Bug: 26687569 Change-Id: I538d7e036b5a8ae2cc3fe77662a5903d74854562