changeset 220:2cc7a17c3859

pirelli/rfcal: new understanding
author Mychaela Falconia <falcon@freecalypso.org>
date Thu, 16 Nov 2017 04:19:58 +0000
parents e3bbb8cfbbc0
children 9f2e0c34fe33
files pirelli/rfcal
diffstat 1 files changed, 116 insertions(+), 17 deletions(-) [+]
line wrap: on
line diff
--- a/pirelli/rfcal	Sun May 28 20:33:26 2017 +0000
+++ b/pirelli/rfcal	Thu Nov 16 04:19:58 2017 +0000
@@ -2,13 +2,30 @@
 contains per-unit factory data, including the IMEI and RF calibration values.
 The location of the IMEI record (at offset 0x504) was found back in 2013-07 and
 its encryption was figured out in 2013-11, but it took a bit longer to find the
-RF calibration data.  But I finally found most of the latter as well.  Here
-they are:
+RF calibration data.  Most of the RF calibration bits were found in 2014-07,
+but the complete picture presented below has only been reconstructed in 2017-11.
+
+The data structure corresponding to TI's RF calibration files listed in the
+config_files_common[] and config_files_band[] arrays in l1_cust.c begins at
+offset 0x528, and has space allocated for each and every one of the files
+listed in those arrays in TI's canonical version, in the same order as in that
+canonical version, with the single exception of /sys/uartswitch.  Behold:
 
 Hex offset	Corresponding FFS file in TI's canonical version
 ----------------------------------------------------------------
+0528		/gsm/rf/afcdac
+052A		    checksum byte
+052B		442 (0x1BA) unused (all FF) bytes making room for:
+		    /gsm/rf/stdmap
+		    /gsm/rf/afcparams
+		    /gsm/rf/rx/agcglobals
+		    /gsm/rf/rx/il2agc
+		    /gsm/rf/rx/agcwords
+
 06E5		/sys/adccal
 0709		    checksum byte
+070A		33 (0x21) unused (all FF) bytes making room for:
+		    /sys/abb
 
 072B		/gsm/rf/tx/ramps.900
 092B		    checksum byte
@@ -28,6 +45,10 @@
 0FB2		    checksum byte
 0FB3		/gsm/rf/tx/calchan.1900
 1033		    checksum byte
+1034		123 (0x7B) unused (all FF) bytes making room for:
+		    /gsm/rf/tx/caltemp.900
+		    /gsm/rf/tx/caltemp.1800
+		    /gsm/rf/tx/caltemp.1900
 
 10AF		/gsm/rf/rx/calchan.900
 10D7		    checksum byte
@@ -41,25 +62,103 @@
 113B		    checksum byte
 113C		/gsm/rf/rx/agcparams.1900
 1144		    checksum byte
+1145		more than enough unused (all FF) bytes to fit:
+		    /gsm/rf/rx/caltemp.900
+		    /gsm/rf/rx/caltemp.1800
+		    /gsm/rf/rx/caltemp.1900
+
+TI's canonical version classifies each of the files listed in those
+config_files_common[] and config_files_band[] arrays into one of 8 categories:
+
+f = RF calibration
+F = RF config
+r = Rx calibration
+R = Rx config
+t = Tx calibration
+T = Tx config
+s = system calibration
+S = system config
+
+Pirelli's factory data structure allocates space for all of the possible files
+in all 8 categories, but out of all these spaces, the only ones that are
+actually filled with bits (not all FF) are the ones corresponding to the 4
+"calibration" categories, and not the "config" ones.  It is my (Mychaela's)
+guess that Foxconn folks probably preserved the logic invoked by me 102 through
+me 109 commands unchanged from TI's original, and thus had the theoretical
+ability to write everything into their invented data structure, but only issued
+the me 102/104/106/108 commands in their factory production flow, hence only
+the "calibration" record slots got filled.
+
+Please note that the slots corresponding to the missing files in the "config"
+categories are filled with all FF bytes, and do NOT contain the "standard" or
+"never changed" bits compiled into the firmware.  Because these bits are not
+present in the factory record in the flash, any aftermarket firmware running on
+these phones needs to provide these bits on its own.  This category very notably
+includes the afcparams table.
 
 Each calibration record is followed by a checksum byte.  It is a simple ripple-
 carry sum of all bytes in the preceding record.  Note that this checksum byte
 is always 0 for the ramps records, as each correctly-formed ramp adds up to 128
-(0x80), and the array has an even number of ramps in total.
+(0x80), and the array has an even number of ramps in total.  It is also my
+(Mychaela's) guess that Pirelli's fw probably uses this checksum byte to detect
+that the "config" files are missing and avoid loading the FF bytes into the
+corresponding L1 RAM data structures: the sum of all FF bytes in the data space
+does not equal FF unless the record length is 1 byte or 257 or 513... bytes,
+and none of TI's calibration/config records match those byte lengths.
+
+Absence of the afcparams table
+==============================
 
-Unfortunately though, I have not been able to locate these two records:
-
-/gsm/rf/afcdac
-/gsm/rf/afcparams
+The afcparams table is placed in the "RF config" category in TI's TCS211
+reference fw, rather than "RF calibration".  It appears that in the very old
+days of Sara RF (before the D-Sample) this table contained only the Psi
+constants (no min/max/nominal DAC), and these Psi constants were tweaked in the
+source code in l1_rfN.h, rather than via per-unit calibration - hence the
+"config" rather than "calibration" classification.  Then RF 10 (Clara) came
+along, TI started using "plain" VCXOs without the "TC" part, they implemented a
+new AFC algorithm (VCXO_ALGO), and the min/max/nominal DAC fields got added to
+the afcparams table.  The complete story is not clear, but the end result is
+that when the days of Openmoko came around, FIC (OM's factory) had a production
+line calibration program, presumably from TI (I never got a copy of it, but I
+was told it was a Windows binary sans source), that performed individual
+per-unit calibration of the VCXO along with the expected Rx and Tx band
+calibrations, and the afcparams table is calibrated per unit on Openmoko
+devices.
 
-These two files appear in Openmoko's FFS on GTA02 modems, and the byte content
-differs for each physical unit, so I assume that these values really do need to
-be calibrated per unit, but I haven't been able to locate them in Pirelli's
-factory data block.  /gsm/rf/afcdac is only 2 bytes long, thus very hard to
-spot visually in a hex dump of an unknown larger data structure;
-/gsm/rf/afcparams is 24 bytes long and has some structure to it, so I was
-hoping to recognize the latter, but no luck.
+Both theory and practice indicate that OM's way of calibrating the afcparams
+table on a per-unit basis is not the only way: the per-unit calibration does
+not help much in practice because of the strong temperature sensitivity, and
+the new AFC algorithm implemented by TI has to deal with wide uncertainties in
+the initial VCXO frequency.  Instead it appears to be sufficient to calibrate
+the VCXO and the settings in the afcparams table on a per-design basis, rather
+than per unit, and it appears that Motorola/Compal did just that on their C1xx
+phones - which use a "plain" VCXO and not a VCTCXO like the Pirelli.
+
+Querying Pirelli's fw for the actively used afcparams table via rftr 9 returns
+the following:
+
+rf_table afcparams
+
+      6974	# psi_sta_inv
+         8	# psi_st
+    492713	# psi_st_32
+      8717	# psi_st_inv
 
-We will have to try running uncalibrated, or perhaps we'll find the code in
-Pirelli's fw that fills the parts of the T_RF structure that are normally read
-from these files.
+       888	# dac_center
+     -9568	# dac_min
+     11352	# dac_max
+      2560	# snr_thr
+
+Because the slot in the factory data structure where the afcparams record ought
+to go is all FF bytes, the table returned by the fw above can only be hard-coded
+in the fw itself.  The 4 numbers in the second group are exactly the same as
+the hard-coded numbers in l1_rf12.h in TI's reference fw, but the Psi numbers
+are different - Foxconn/Pirelli folks must have tuned them for their VCTCXO.
+
+In this light, it is worthy to note that the afcdac record *is* present in
+Pirelli's factory data block, and it differs from one unit to the next, i.e.,
+it has been calibrated on a per-unit basis.  TI's reference fw selects the
+ALGO_AFC_LQG_PREDICTOR AFC algorithm which does not use this afcdac setting
+at all, but perhaps Pirelli's fw does something different because of their use
+of a VCTCXO instead of a "plain" VCXO - we don't know, and the reverse eng
+effort to find the needed answers would be more than we can currently justify.