Linux的晶片驅動firmware自動升級之一:功能說明

來源:互聯網
上載者:User

        在驅動開發過程中,我們有時會碰到這種應用:比如說某款晶片的韌體不是固定的,是可以後期升級的。那麼在每次系統開機時,需要做個檢測,如果檢測到提供了新的韌體,那麼在第一次開機時就升級韌體。之後由於儲存了新的韌體版本號碼可供檢測,就不用再開機升級了。

        以一款I2C的觸控螢幕晶片為例,假設供應商提供的新韌體檔案名稱是Us3x06eb_use.it,將該檔案放在觸控螢幕驅動.c的同目錄下,那麼需要做的就是在觸控螢幕的Probe函數裡面加入對應的版本號碼檢測處理,並決定是否升級。如果需要升級,將目標韌體通過I2C寫入即可。

typedef enum{       ERR_OK,       ERR_MODE,       ERR_READID,       ERR_ERASE,       ERR_STATUS,       ERR_ECC,       ERR_DL_ERASE_FAIL,       ERR_DL_PROGRAM_FAIL,       ERR_DL_VERIFY_FAIL}E_UPGRADE_ERR_TYPE;#define    FTS_PACKET_LENGTH        2    //一次寫兩個位元組,作為一個PACKETstatic unsigned char CTPM_FW[] =            //載入目標韌體{      #include "Us3x06eb_use.it"};static int fts_i2c_txdata(u8 *txdata, int length)   //一次通過I2C傳輸多位元組資料{       int ret;       struct i2c_msg msg;       msg.addr = i2c_client->addr;       msg.flags = 0;       msg.len = length;       msg.buf = txdata;       ret = i2c_transfer(i2c_client->adapter, &msg, 1);       if(ret < 0)       {             pr_err("%s i2c write error: %d\n", __func__, ret);       }       return ret;}static bool i2c_write_interface(u8 *pbt_buf, int dw_lenth)    //通過I2C寫多個資料{       int ret;       ret = i2c_master_send(i2c_client, pbt_buf, dw_lenth);       if(ret <= 0)       {             printk("[TSP]i2c_write_interface error line = %d, ret = %d\n", __LINE__, ret);             return FTS_FALSE;       }       return FTS_TRUE;}static bool i2c_read_interface(u8 *pbt_buf, int dw_lenth)   //通過I2C讀多個資料{       int ret;       ret = i2c_master_recv(i2c_client, pbt_buf, dw_lenth);       if(ret <= 0)       {              printk("[TSP]i2c_read_interface error\n");              return FTS_FALSE;       }       return FTS_TRUE;}static bool fts_register_write(u8 reg_name, u8 *tx_buf)     //往寄存器寫單位元組資料{       u8 write_cmd[2] = {0};       write_cmd[0] = reg_name;       write_cmd[1] = *tx_buf;       return i2c_write_interface(write_cmd, 2);}static bool fts_register_read(u8 reg_name, u8 *rx_buf, int rx_length)    //從寄存器讀多個資料{       u8 read_cmd[2] = {0};       u8 cmd_len  = 0;       read_cmd[0] = reg_name;       cmd_len = 1;       /*send register addr*/       if(!i2c_write_interface(&read_cmd[0], cmd_len))       {              return FTS_FALSE;       }       if(!i2c_read_interface(rx_buf, rx_length))       {              return FTS_FALSE;       }       return FTS_TRUE;}

      E_UPGRADE_ERR_TYPE  fts_ctpm_fw_upgrade(u8 *pbt_buf, int dw_lenth)   //編程燒錄細節不闡述,執行個體會在本部落格的續篇中列出

{

       //將資料劃分成相應的PACKET,一次通過I2C寫入晶片中。有幾個問題需要注意:(1)要注意分包的銜接,資料長度未必恰好能劃分成整數個包,那麼最後一個包要單獨

       //處理;(2)資料校正,比如說晶片帶自動異或校正的話,一方面我們在發送的過程中要及時進行資料校正運算,另一方面在資料發送完畢後,可以把這個校正值跟校正

       //寄存器的值進行比較,從而判斷當前傳輸是否有效。

}

int fts_ctpm_fw_upgrade_with_i_file(void){       u8     *pbt_buf = 0x0;       int ret;       pbt_buf = CTPM_FW;       ret =  fts_ctpm_fw_upgrade(pbt_buf, sizeof(CTPM_FW));     //升級特定檔案       return ret;}static int __devinit tpd_probe(struct i2c_client *client, const struct i2c_device_id *id) //TP的probe函數{        .............        {                u8 reg_val=0;               mdelay(50);               fts_register_read(0xA6,_val,1);     //讀出目前的版本號                 if(reg_val<TP_LIB_VERSION)    //如果目前的版本號小於待升級版本號碼,進行升級                {                       printk("TP firmware version OK, start upgrade\n");                        fts_ctpm_fw_upgrade_with_i_file();                 }       }        .............}

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.