This guide covers Pixel 6, 6 Pro, 6a, 7, 7 Pro, 7a, Fold, 8, 8 Pro, 8a, 9, 9 Pro, 9 Pro XL, 9 Pro Fold, 9a
For context and prior discussions, please see:
A rooted device must be used to perform any actions. All changes will persist after a factory reset and bootloader lock, and this guide does not encourage you to have a rooted device as a daily driver. For educational and research purposes only
Background
Since the release of the Pixel 6 in 2021, Google has switched from Qualcomm to Samsung modems in their G-series Tensor SoCs. The modemâs codename is called âShannonâ and it is largely the same as used on Exynos devices.
For Google, Samsung added a few extra AT commands to interact with the modem, presumably for carrier testing and other regulatory requirements. A small subset of what was possible to send to it is documented here:
Notice the AT+GOOGSETNV prefix, everything starts with AT+GOOG is Pixel specific on those modems. We will come to that later.
The IMEI, together with all other hardware identifiers is stored in a file called devinfo.
A simple parser in Python can be found here:
Steps
To get devinfo, we first need to get a root shell:
adb shell
su
dd if=/dev/block/by-name/devinfo of=/sdcard/devinfo.img
adb pull /sdcard/devinfo.img
From here, you can change the SKU of the device, for example to change the JP variant to US one, if for some reason you run the stock OS and wanât to avoid the camera shutter sound. But we are here for the more interesting values.
We now need to find the original IMEI string in our devinfo, and modify it with a hex editor.
Make sure to not just enter random numbers there but from a device you legally own. This way you make sure that you donât break the law as well as not looking suspicious from the carrier side.
adb push ./devinfo_modified.img /sdcard/
adb shell
su
dd if=/sdcard/devinfo_modified.img of=/dev/block/by-name/devinfo
exit
adb reboot bootloader
fastboot oem set_config bootmode factory
fastboot reboot
You will see a red screen from the bootloader saying the phone is booted in factory mode.
We now have to recalculate the SHA hashes of the new IMEI values. For that, we execute:
echo âAT+GOOGGETIMEISHA\râ > /dev/umts_router & cat /dev/umts_router
You will see a SHA256 string in a response, i.e:
+GOOGGETIMEISHA:494b450c0a1f5af2ce470010fc0e33cb4917083839b7add4cf9d100c8bad17b7
Copy that string to /mnt/vendor/persist/modem/cpsha, thatâs our new IMEI verification hash:
echo 494b450c0a1f5af2ce470010fc0e33cb4917083839b7add4cf9d100c8bad17b7 > /mnt/vendor/persist/modem/cpsha
echo âAT+GOOGBACKUPNV\râ > /dev/umts_router
Now we saved the backup to EFS as well, although it is not necessary.
reboot bootloader
fastboot oem rm_config bootmode
fastboot reboot
You should have your IMEI changed, and now itâs safe to do a factory reset and lock the bootloader back.
If you have a carrier that supports displaying your current connected IMEI online, you can use it to verify everything went well. But if you see it in *#06# it will be enough, the baseband reads it from devinfo.
P.S.
There is a nice FOSS utility that kind of automates what I described here, so big thanks to @luxferre: