This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TPS65987D: I2C read "Data byte" is always 0xFF when Patch bundle flow

Part Number: TPS65987D
Other Parts Discussed in Thread: TPS65988, TPS65987, ,

Our platform is PTS65987D without Flash ROM with external MPU.

We are trying Patch bundle flow as shown page 5 of slva972a.pdf (TPS65987 and TPS65988 SPI Less Host Programming Over I 2C).

At "ReadyForPatch Notification Received?", we read Register 0x14, we got "Byte Count"=0x0b correctly, but "Data Byte 1~11" are all 0xFF.

Next "Command Execution Successful?", we read Register 0x08, we got "Byte Count"=0x04 correctly, but "Data Byte 1~4" are all 0xFF.

We think 0xFF is not correct value. Please advice what should we do to read correct value.

Regards,

Hirosawa

  • Hi Hirosawa,

    Could you confirm you are following the process shown on page 6? The 4CC commands must be written in the order shown, the data for the command in DataX register and then the 4CC code in CMDx register.

    Thank you,

    Hari

  • Hi Hari,

    Thank you for your reply.

    Yes, we write the data(0x0300) in Data1 register(0x09) first then write 4CC command "PTCs" (0x50544373) in Cmd1 Register (0x08).

    (I found mistake it should be 0x03, not 0x0300)

    Just in case, Could you please check our code below?

    And also i found ADCIN1 port (BUSPOWERZ Configurations) set 0.60~0.68 (Configllation4).

    Should it set 0.30~0.38 (BP_ECWait_Internal) for download the patch bundle?

    //---------------------------------------
    U8 PD_Init1(void)
    //Initialization
    //=0:OK,  =1:Error,  =2:ReadyForPatch Error
    {
    	volatile U8 i1 , i2;
    	volatile U16 areano , array_rng;
    	
    	areano = 0;
    	FW_timer = 10000;	//10 seconds Timer Set
    	PD_Flag = 0;		//0 means PowerDelivery Not supported
    	array_rng = 13120;	//Number of table 
    
    	while(1){
    		i1 = TPS65987_RegRead(0x14);
    		if (i1 == 0){
    			if ((IICBuf[10] & BIT1) == BIT1) break;
    		}
    		if (FW_timer == 0)return 2;
    	}
    	//Write 2 byte data(0x0300) into Register 0x09(Data1)
    	IICBuf[0] = 0x03;
    	IICBuf[1] = 0x00;
    	if (TPS65987_RegWrite(0x09,2) == 1) return 1;
    	//Write PTCs command (“PTCs”(0x50544373) into Register 0x08(Cmd1)
    	IICBuf[0] = 0x50;
    	IICBuf[1] = 0x54;
    	IICBuf[2] = 0x43;
    	IICBuf[3] = 0x73;
    	if (TPS65987_RegWrite(0x08,4) == 1) return 1;
    	//Poling Register 0x08, it means success if 0x0000_0000,  it means fail if ”!CMD”
    	i1 = TPS65987_RegRead(0x08);
    	if (i1 == 0){
    		if ((IICBuf[0] != 0) || (IICBuf[1] != 0) || (IICBuf[2] != 0) || (IICBuf[3] == 0)) return 1;
    	}
    	else{
    		return 1;
    	}
    	while(1){
    		//Write each 64 bytes of Patch_bundle.c into Register 0x09(Data1)
    		for(i1 = 0; i1 < 64; i1++){
    			IICBuf[i1] = tps65987x_lowregion_i2c_array[areano];
    			areano ++;
    		}
    		if (TPS65987_RegWrite(0x09,64) == 1) return 1;
    		//Write PTCd command(“PTCd”(0x50544364) into Register 0x08(Cmd1)
    		IICBuf[0] = 0x50;
    		IICBuf[1] = 0x54;
    		IICBuf[2] = 0x43;
    		IICBuf[3] = 0x64;
    		if (TPS65987_RegWrite(0x08,4) == 1) return 1;
    		//Poling Register 0x08, it means success if 0x0000_0000,  it means fail if ”!CMD”
    		i1 = TPS65987_RegRead(0x08);
    		if (i1 == 0){
    			if ((IICBuf[0] != 0) || (IICBuf[1] != 0) || (IICBuf[2] != 0) || (IICBuf[3] == 0)) return 1;
    		}
    		else{
    			return 1;
    		}
    		if (areano >= array_rng)break;
    	}
    	//Write PTCs command (“PTCc”(0x50544363) into Register 0x08(Cmd1)
    	IICBuf[0] = 0x50;
    	IICBuf[1] = 0x54;
    	IICBuf[2] = 0x43;
    	IICBuf[3] = 0x63;
    	if (TPS65987_RegWrite(0x80,4) == 1) return 1;
    	//Read Register 0x09(Data1),  it means success if Byte3 = 0x00 and Byte4 = 0x00
    	i1 = TPS65987_RegRead(0x09);
    	if (i1 == 0){
    			if ((IICBuf[2] != 0) || (IICBuf[3] != 0)) return 1;
    		}
    	else{
    		return 1;
    	}
    	PD_Flag = 1;   //PowerDelivery supported
    	return 0;
    }
    //---------------------------------------
    //Read reg data Write IICBuf()
    //=0:OK,  =1:Error
    U8 TPS65987_RegRead(U8 reg)	
    {
    	volatile U8 slvadd;
    	volatile U8 i1 , i2;
    	
    	slvadd = 0x70;
    
    	IICStart();	//Start condition
    	if (IICWriteOne(slvadd) == 1)return 1;  //Slave address
    	if (IICWriteOne(reg) == 1)return 1;      //Regster Address
    	
    	IICReStart();	//Start condition
    	if (IICWriteOne((slvadd | 1)) == 1) return 1;  //Slave address (bit0=1 , Read)
    	
    	//Data recieved
    	ACKDT1 = 0;//AckSet
    	i2 = IICReadByte();   //Get Data byte
    	for(i1 = 0; i1 < i2; i1++){
    		IICBuf[i1] = IICReadByte();   //get 1 byte
    		IICAckTx();//Ackout
    	}
    	//Last 1 byte
    	ACKDT1 = 1;   //NoAckSet
    	IICBuf[i1] = IICReadByte();  //Get 1 byte
    	//NoAckout
    	IICAckTx();
    
    	IICStop();
    	return 0;
    }
    //---------------------------------------
    U8 TPS65987_RegWrite(U8 reg , U8 lng)
    //Write IICBuf() into reg
    //=0: ok,  =1:Error
    {
    	volatile U8 slvadd;
    	volatile U8 i1 , i2;
    	
    	slvadd = 0x70;
    
    	IICStart();
    	if (IICWriteOne(slvadd) == 1)return 1;
    	if (IICWriteOne(reg) == 1)return 1;  //Regster Address
    	
    	for(i1 = 0; i1 < lng; i1++){
    		if (IICWriteOne(IICBuf[i1]) == 1)return 1;
    	}
    	IICStop();
    	return 0;
    }
    //---------------------------------------
    

  • Hi Koji,

    I am not able to look into the code too much since this can vary for each system. However, if you are following the I2C format shown in the datasheet for the 4CC commands, that should be fine.

    For loading the patch via EC, yes you will need to set it to either BP_ECWait_Internal or BP_ECWait_External.

    Thank you,

    Hari

  • Hi Hari,

    Thank you for your reply.

    But we did not resolve yet. May i confirm one by one?

    1.  We are using I2C2 port for path bundle, is it OK?

    2. "BP_ECWait_Internal" is set  by ADCIN1 DIV R2/(R1+R2) = (0.30~0.38). is it OK?

    3. In the first step of batch bundle, at "READY_FOR_PATCH Notification",  we are polling if bit1(ReadyForPatch) of byte11 in Register 0x14(IntEvent1) is 1. Is it correct procedure?

    4. When polling register 0x14, we got always "byte count" = 0x00, not 0x0b after set "BP_ECWait_Internal". What is wrong?

    Regards,

    Hirosawa 

  • Hi Koji,

    Yes no problem.

    1. Yes that's fine.

    2. Yes, this configuration is fine.

    3. I believe since you are using I2C2, you will actually need to poll 0x15, byte 11.

    4. I think because of step 3, you may not be seeing this since it is correlated to I2C1, so please check 0x15 and let me know if you are able to see this update.

    Thank you,

    Hari

  • Hi Hari,

    Thank you for your reply.

    But we already tried to poll register 0x15, but result was same, "byte count" = 0x00.

    5. We did poll like below, is it no problem?  (underline is the data form TPS65987)

         S+ Unique address(0111000)+Wr(0), ACK, Register(0x15), ACK, Sr+ Unique address(0111000)+Rd(1), ACK, Byte Count=0x00, ACK,P

    6.  After power on, may we do poll 0x15 soon?  Or should we wait some seconds?

    Please advice what we should do.

    Regards,

    Hirosawa

  • Hi, could you confirm you are reading the reg. values? I'm not sure why it would keep giving byte count. Are you able to send the I2C message following the I2C read protocol from the datasheet Figure 8-27? If the PD controller is powered via VBUS then you should be able to read but you could try adding in a small delay as well.

    Thank you,

    Hari

  • Hi Hari,

    Yes, we are following this protocol for I2C read.   (I found document is revised this August, my document is figure 30, not 8-27)

    First we can get "Byte count" (See below Red rectangle) which shows the number of following read data byte.

    if Byte count is 0x00, we cannot read any more. So we are focusing Byte count now. 

    Our environment has no VBUS power, but we supplied 3.3V for VIN3V3 (#5 pin). I think it is enough for I2C access. 

    Do we still need VBUS power?  

    We tried to add delay. but no ACK after Register Number.... getting worse.  Hu~~~m

    Regards,

    Hirosawa

  • Hi,

    Yes VIN_3V3 should be fine, this signal should also provide power to the LDO_3V3, could you also confirm this is true in your design?

    It seems that when you are not in APP mode, the PD controller may not allow host to access some register info and therefore you can safely assume that the first I2C IRQ notification is ReadyForPatch interrupt. At this point the host can start the PTCx patch download process.

    One more thing to note is that, since you are using the BP_ECWait_Internal configuration, you will need to make sure that the PD controller is in PTCH mode, to accept the patch from host. Alternatively, a way you can be sure it will stay in PTCH mode for the host is to change the configuration to Infinite_Wait.

    Thank you,

    Hari

  • Hi Hari, 

    Yes, I confirmed that LDO_3V3 is 3.3V.

    I am confused. You mean it is like below sequence?

    First, PD controller is in APP mode, we can access 0x15 to check if ReadyForPatch. After that we send PTCs 4CC command.

    Then PD controller changed to PATCH mode, host send patch bundle data. Right?

    How can we set PD controller is in APP mode or PATCH mode?  I think it is automatically set depend on external flash is present or not.

    If external flash is present, it set APP mode. If no external flash (our environment case), it is PATCH mode. Right?

    Regards,

    Hirosawa

  • Hi Koji,

    No, I apologize, the PD controller would boot up in PTCH mode and then depending on your ADC configuration, it would either load a default configuration or load from host. During this PTCH mode, the EC needs to push the patch to the PD controller. However, if your default configuration is not set to Infinite_Wait, what can happen is if the EC does not push a patch in time, then the PD controller will go to APP mode and load the default configuration. When the PD controller goes to APP mode, the EC won't be able to load a patch. Therefore, if there is an EC which will push the configurations to the PD, the Infinite_Wait setting would be more recommended.

    Thank you,

    Hari

  • Hi Hari,

    As i wrote before, we set  "BP_ECWait_Internal (Infinite_Wait)"  by ADCIN1 DIV = (0.30~0.38). I confirmed ADCIN1 is 1.13V (=3.3V*0.34).

    But host cannot access by I2C2. 

    Just in case, Could you please check if there are any mistake in our circuit diagram?  (CN5 is USB3 terminal)

    Regards,

    Hirosawa

  • Hi,

    It looks like you have a lot of things different that I was not aware of. Typically, the TPS65987D would refer to the DH version, however I see that you are using the TPS65987DDJ version of the device. I would recommend using the DH as the DJ version is only applicable for Thunderbolt devices.

    Also, I noticed some of your pins weren't following the datasheet recommendations, could you please double check the pin functions and specifications sections of the datasheet? You could also compare your datasheet with the Typical Application schematic from the datasheet as well. I see that the VBUS1 and VBUS2 are not connected together, also I don't see any capacitors connected to LDO_3V3 or LDO_1V8. Are you able to scope the LDO_3V3 and verify you are able to see this voltage when another device plugs in?

    To sink power also, I believe by default PPHV1 will be used to sink power from the other device but it looks like you have this pin left open.

    Thank you,

    Hari

  • Hi Hari,

    Thank you for your reply.

    FYI, Our platform is for PD source device. 

    i reworked our board as your mentioned and data sheet like below circuit diagram(Red letter).

    But it still same symptom,  When MCU read TPS65987 register 0x15, TPS65987 always send "byte count" = 0x00 (It should be 0x0B), subsequent data are all 0xFF.

    I tried to read other register 0x04((Type), read back data are 0x04 FF FF FF FF.  0x04 is "byte count", it is correct value, but next 4 bytes should be ascii "I2C ".

    register 0x05 also same 0x04 FF FF FF FF. 

    What happened?

    [Rework items]

      - TPS65987DDJ  --> TPS65987DDH   (It just Circuit diagram mistake)

      - VBUS1 and VBUS2 are connected

      - 10uF capacitors connected to LDO_3V3 or LDO_1V8.

      - PPHV1 and PPHV2 are connected

      - SPI_MOSI, CLK and SS are connected to GND

      -  I2C1_SDA and SCL are pulled up via 10k  registers. 

    Regards,

    Hirosawa

  • Hi,

    Could you please try sending out the PTCx commands after boot-up without reading the register? The PD controller will not allow reading this register in PTCH mode so you will need to start the process without this step by first sending out the PTCs.

    Thank you,

    Hari

  • Hi Hari,

    I tried sending out the PTCs commands after boot-up without reading. But NACK was received after "Byte Count" sent, like below.

    S, 0x38(UniqueAdrs)+Wr, ACK,

    0x09(Register Data1), ACK,

    0x01(ByteCount), NACK,

    0x03, NACK, P

    S, 0x38(UniqueAdrs)+Wr, ACK,

    0x08(Register Cmd1), ACK,

    0x04(ByteCount), NACK,

    0x50("P"), NACK

    0x54("T"), NACK

    0x43("C"), NACK

    0x73("s"), NACK, P

    I tried send cmd2/ data2 Register = 0x10/0x11) and/or via I2C1(UniquAdrs=0x22). Result are all same.

    Regards,

    Hirosawa

  • Hi,

    Could you please capture the I2C log file so that I can review it?

    Thank you,

    Hari

  • Hi Hari,

    We don't have I2C analyzer, therefore i got Oscilloscope capture one by one.

    Please check attached pdf file.

    4834.I2C.pdf

    Regards,

    Hirosawa

  • Hi,

    I will take a look to see if I can find any I2C issues.

    Thank you,

    Hari