1. 程式人生 > >Qualcomm 平臺觸控式螢幕驅動移植 筆記

Qualcomm 平臺觸控式螢幕驅動移植 筆記

TP觸控式螢幕,應該是驅動開發中比較簡單並且適合新手入手的模組。不過雖然簡單,但涉及到的內容還是比較多的,其中Linux相關主要的機制:

1. input 機制

2. 中斷、定時器

3. I2C

1.TP的原理:TP一般為電容或為電阻屏,不過現在基本上都是電容屏,可能一些WINCE的裝置還會用電阻屏,但Android的基本現在為電容屏,且多點觸控和手套觸控都整合在TP的IC中。當用戶觸控電容屏時,由於人體電場,使用者手指和工作面形成一個耦合電容,因為工作面上接有高頻訊號,於是手指吸收走一個很小的電流,這個電流分別從屏的四個角上的電極中流出,且理論上流經四個電極的電流與手指頭到四角的距離成比例,控制器通過對四個電流比例的精密計算,得出位置。可以達到99%的精確度,具備小於3ms的響應速度。在實際產品中,當螢幕感應到手指的接觸或者靠近,會產生一個外部中斷給CPU,在中斷中,一般中斷下半部,通過I2C匯流排,從TP的IC中讀取相關的資訊,經過一定的資料處理,上報X,Y座標值。

2.linux input機制:

linux輸入子系統(linux input subsystem)從上到下由三層實現,分別為:輸入子系統事件處理層(EventHandler)、輸入子系統核心層(InputCore)和輸入子系統裝置驅動層。

對於輸入子系統裝置驅動層而言,主要實現對硬體裝置的讀寫訪問,中斷設定,並把硬體產生的事件轉換為核心層定義的規範提交給事件處理層。(工程師主要做的事情)

對於核心層而言,為裝置驅動層提供了規範和介面。裝置驅動層只要關心如何驅動硬體並獲得硬體資料(例如按下的按鍵資料),然後呼叫核心層提供的介面,核心層會自動把資料提交給事件處理層。

對於事件處理層而言,則是使用者程式設計的介面(裝置節點),並處理驅動層提交的資料處理。

3. 中斷

中斷是指在CPU正常執行期間,由於內外部事件或由程式預先安排的事件引起的CPU暫時停止正在執行的程式,轉而為該內部或外部事件或預先安排的事件服務的程式中去,服務完畢後再返回去繼續執行被暫時中斷的程式。Linux中通常分為外部中斷(又叫硬體中斷)和內部中斷(又叫異常)。

Linux中斷分為兩個半部:上半部(tophalf)和下半部(bottom half)。上半部的功能是"登記中斷",當一箇中斷髮生時,它進行相應地硬體讀寫後就把中斷例程的下半部掛到該裝置的下半部執行佇列中去。因此,上半部執行的速度就會很快,可以服務更多的中斷請求。但是,僅有"登記中斷"是遠遠不夠的,因為中斷的事件可能很複雜。因此,Linux引入了一個下半部,來完成中斷事件的絕大多數使命。下半部和上半部最大的不同是下半部是可中斷的,而上半部是不可中斷的,下半部幾乎做了中斷處理程式所有的事情,而且可以被新的中斷打斷!下半部則相對來說並不是非常緊急的,通常還是比較耗時的,因此由系統自行安排執行時機,不在中斷服務上下文中執行。

4. 定時器

兩種裝置進行計時:系統定時器和實時時鐘。

實時時鐘(RTC):用來持久存放系統時間的裝置,即便系統關閉後,靠主機板上的微型電池提供電力保持系統的計時。系統啟動核心通過讀取RTC來初始化牆上時間,改時間存放在xtime變數中。

系統定時器:核心定時機制,註冊中斷處理程式,週期性觸發中斷,響應中斷處理程式,進行處理執行以下工作:

5.I2C協議

2條雙向序列線,一條資料線SDA,一條時鐘線SCL。

SDA傳輸資料是大端傳輸,每次傳輸8bit,即一位元組。   支援多主控(multimastering),任何時間點只能有一個主控。   總線上每個裝置都有自己的一個addr,共7個bit,廣播地址全0.

   系統中可能有多個同種晶片,為此addr分為固定部分和可程式設計部份,細節視晶片而定,看datasheet。

上一篇主要講的與TP相關的知識點,講這個主要是,你對這一模組有個基本的概念,知道其工作原理,這樣在實際開發過程中,你才知道怎麼去寫起的驅動,碰到問題時,出現在哪一塊,該怎麼去解決。

      這一篇,主要根據程式碼來講上一篇涉及到的相關機制。TP的連線很簡單,一路I2C,一根中斷線,VCC、GND,reset。

1. TP主要相關demo:

驅動demo:\kernel\drivers\input\touchscreen\Ft5x06_ts.c 

    \kernel\drivers\input\touchscreen\Ft5x06_ts.h

dtsi檔案:\kernel\arch\arm\boot\dts\qcom\Msm8X16-qrd.dtsi

2. dtsi的相關解釋

[email protected]{ //TP所連的I2C的暫存器
[email protected]
compatible = "focaltech,5x06"; //I2C驅動match的內容
reg = <0x38>; //I2C地址
interrupt-parent = <&msmgpio>;  //中斷引腳
interrupts = <1 0x2>;
vdd-supply = <&pm8110_l19>;     //I2C供電的電影控制
vcc_i2c-supply = <&pm8110_l14>;
focaltech,name = "ft6x06";     //tp型別
focaltech,family-id = <0x06>;   
focaltech,reset-gpio = <&msmgpio 0 0x00>; //復位引腳,,用於初始化時序
focaltech,irq-gpio = <&msmgpio 1 0x00>;   //中斷引腳
focaltech,display-coords = <0 0 480 800>; //TP的觸點範圍
focaltech,panel-coords = <0 0 480 800>;
focaltech,button-map= <139 102 158>;     //虛擬按鍵
focaltech,no-force-update;
focaltech,i2c-pull-up;
focaltech,group-id = <1>;
focaltech,hard-reset-delay-ms = <20>;
focaltech,soft-reset-delay-ms = <150>;
focaltech,num-max-touches = <2>;
focaltech,fw-name = "ft_8610_qrd_fw.bin"; //TP韌體
focaltech,fw-delay-aa-ms = <100>;
focaltech,fw-delay-55-ms = <30>;
focaltech,fw-upgrade-id1 = <0x79>;
focaltech,fw-upgrade-id2 = <0x08>;
focaltech,fw-delay-readid-ms = <10>;
focaltech,fw-delay-era-flsh-ms = <2000>;
};
}; 

3. 驅動檔案

3.1 I2C驅動註冊

static int __init ft5x06_ts_init(void)
{
pr_err("start \n");
return i2c_add_driver(&ft5x06_ts_driver); //I2C驅動註冊
pr_err("end \n");
}

3.2 檔案介面,of_match_table,需要DTSI中compatible定義的一致。

static struct i2c_driver ft5x06_ts_driver = {
.probe = ft5x06_ts_probe,
.remove = ft5x06_ts_remove,
.driver = {
  .name = "ft5x06_ts",
  .owner = THIS_MODULE,
.of_match_table = ft5x06_match_tabl
#ifdef CONFIG_PM
  .pm = &ft5x06_ts_pm_ops,
#endif
  },
.id_table = ft5x06_ts_id,
};

3.3 probe

這個裡面程式碼量太多,就不詳細一一說明,這裡主要講解一些基本的步驟。

一般,先給相關的結構體分配儲存空間,然後從dt裝置樹中讀取相關的資訊,測試I2C是否通。

input_dev = input_allocate_device();//分配輸入子系統

data->input_dev = input_dev;
data->client = client;
data->pdata = pdata;
input_dev->name = "ft5x06_ts";
input_dev->id.bustype = BUS_I2C;
input_dev->dev.parent = &client->dev;
input_set_drvdata(input_dev, data);
i2c_set_clientdata(client, data);
__set_bit(EV_KEY, input_dev->evbit);  //設定有什麼事件 按鍵事件 tp虛擬按鍵
__set_bit(EV_ABS, input_dev->evbit);  //絕對事件 
__set_bit(BTN_TOUCH, input_dev->keybit);
__set_bit(INPUT_PROP_DIRECT, input_dev->propbit);
input_mt_init_slots(input_dev, pdata->num_max_touches, 0);
input_set_abs_params(input_dev, ABS_MT_POSITION_X, pdata->x_min, //X座標事件
    pdata->x_max, 0, 0);
input_set_abs_params(input_dev, ABS_MT_POSITION_Y, pdata->y_min, //Y座標事件
    pdata->y_max, 0, 0);

ft5x06_power_init(data, true); //電源、GPIO相關的初始化

ft5x06_power_on(data, true); // 上電,時序初始化

err = request_threaded_irq(client->irq, NULL,ft5x06_ts_interrupt,IRQF_ONESHOT,
client->dev.driver->name, data); //請求中斷,並把事件處理放在下半部。

psensor_input_dev = input_allocate_device(); 分配子輸入裝置

err = input_register_device(psensor_input_dev);

ft5x06_update_fw_ver(data); //匯入韌體資訊
ft5x06_update_fw_vendor_id(data); //獲取韌體版本ID

3.4 中斷處理程式ft5x06_ts_interrupt

static irqreturn_t ft5x06_ts_interrupt(int irq, void *dev_id)

這個裡面主要是讀I2C,根據晶片手冊,進行資料出來,然後上報事件。

input_report_abs(ip_dev, ABS_MT_POSITION_X, x);
input_report_abs(ip_dev, ABS_MT_POSITION_Y, y);

input_sync(ip_dev);

當然有些TP,如GT9xxxx,會申請工作佇列,然後中斷產生會在上半部,啟動工作佇列,然後遮蔽當前中斷,在工作佇列事件處理完後,使能中斷。有些還會當中斷請求失敗時,申請一個高精度的定時器,會一直輪詢啟動工作執行緒,上報事件。

4. 除錯相關經驗

4.1 一般TP驅動開發,屏產都會給驅動程式碼或者PATCH,這時主要合程式碼進去。

一般找程式碼內現有的一個TP驅動,按它的新增。主要:

1. 把驅動檔案放入kernel\drivers\input\touchscreen\,

2. 修改kconfig和Makefile,加入需要根據巨集才能編進去,那麼需要在deconfig配置檔案中設定為Y.

3. 在DTSI中加入該TP的配置。

 4.2 編譯boot,在out/target/product/msmXXX/obj/KERNEL_OBJ/driver/input/touchscreen/下,看是否有.o檔案沒有,有則編譯成功。

4.3 把新的boot檔案刷入板子,檢視核心log,cat proc/kmsg,看是否有該TP驅動的列印資訊。

4.4 根據列印資訊,判斷出錯的問題。

一般問題,中斷註冊不上,資源分配不成功,I2C裝置通訊失敗。

一些經驗,I2C匯流排不通,可能是因為I2C供電的電源沒有供電,或者該總線上掛的裝置太多影響的,前期調最好I2C總線上,只掛一個裝置。

若probe成功,可在中斷或者工作執行緒裡面加一些列印log。在adb shell進入終端,輸入getevent,手按TP,檢視是否有資料打出,對於該TP的輸入裝置。

5. 檢視I2C裝置:


相關推薦

Qualcomm 平臺觸控式螢幕驅動移植 筆記

TP觸控式螢幕,應該是驅動開發中比較簡單並且適合新手入手的模組。不過雖然簡單,但涉及到的內容還是比較多的,其中Linux相關主要的機制: 1. input 機制 2. 中斷、定時器 3. I2C 1

I.MX6Q(TQIMX6Q/TQE9)學習筆記——新版BSP之觸控式螢幕驅動移植

之所以說是驅動移植是因為之前已經在TQ210、AM335x兩個平臺上移植過了,因此,僅需要少量修改就可以將驅動移植到imx6q。下面開始觸控驅動移植。 DTS編寫 參考其它DTS的i2c裝置寫法,我們可以新增如下內容: &i2c1 { clock-frequen

Android gt911觸控式螢幕驅動移植記錄

 基本上參考“GT9XX驅動移植說明書_for_Android”來做就好的,有幾點注意的地方提一下: 1、替換配置資訊表的時候,如果你的屏驅動晶片gt9xx有設定sensor ID的話,配置資訊應該配置到對應的陣列中(CTP_CFG_GROUP) 2、我的弄完後發現屏的

基於imx6的gt911觸控式螢幕驅動移植

參考:https://blog.csdn.net/zhuyuming/article/details/52652525?locationNum=3 實驗平臺:TQ_iMX6Q     其實在Linux核心官網(https://www.kernel.org/)上下載適合自己

Qualcomm平臺camera除錯移植入門

    高通平臺對於camera的程式碼組織,大體上還是遵循Android的框架:即上層應用和HAL層互動,高通平臺在HAL層裡面實現自己的一套管理策略;在kernel中實現sensor的底層驅動。但是,對於最核心的sensor端的底層設定、ISP效果相關等程式碼則是單獨進行了抽離,放在了一個daemon程

【TINY4412】LINUX移植筆記:(23)裝置樹LCD觸控式螢幕驅動

【TINY4412】LINUX移植筆記:(23)裝置樹 LCD觸控式螢幕驅動 宿主機 : 虛擬機器 Ubuntu 16.04 LTS / X64 目標板[底板]: Tiny4412SDK - 1506 目標板[核心板]

MT3561平臺 GT928觸控式螢幕驅動客製化觸控的開關

MT3561 開光觸控式螢幕GT928邏輯 1 . MT3561 觸控式螢幕的驅動檔案路徑: kernel-3.18/drivers/input/touchscreen/mediatek/GT928/gt9xx_driver.c 2. 需求: 提供介面控制觸

嵌入式系統移植筆記(七) --第三方驅動移植(黑盒子移植

由於嵌入式系統分層,應用層要想操作硬體需通過核心層。驅動對上提供系統呼叫函式,對下封裝了對底層硬體的一些基本操作。筆者是不瞭解驅動程式的編輯,所以本章是在已經有驅動程式(fs4412_led_drv.c)和對應的應用程式(fs4412_led_app.c),來實現黑盒子移植(

rk3128 平臺rk818電源管理驅動移植

一、rk3128加上rk818電源管理驅動 RK3128 加上rk818電源管理驅動之後,導致核心宕機、工作各種穩定。宕機現象各不相同,核心起來之後跑一下死在printk 列印函式裡面、遇到NULL kernel painc 記憶體異常、Internal error:

【TINY4412】LINUX移植筆記:(24)裝置樹EEPROM驅動

【TINY4412】LINUX移植筆記:(24)裝置樹 EEPROM驅動 宿主機 : 虛擬機器 Ubuntu 16.04 LTS / X64 目標板[底板]: Tiny4412SDK - 1506 目標板[核心板]:

AM335x(TQ335x)學習筆記——WM8960音效卡驅動移植

經過一段時間的除錯,終於調好了TQ335x的音效卡驅動。TQ335x採用的Codec是WM8960,本文來總結下WM8960驅動在AM335x平臺上的移植方法。Linux音效卡驅動架構有OSS和ALSA兩種架構,目前最常用的架構是ALSA,本文也使用ALSA架構對WM

[RK3288][Android5.1] 移植筆記 --- gsl3673 觸控驅動

# #obj-$(CONFIG_TOUCHSCREEN_GSLX680)    += rockchip_gslX680_firefly.o #obj-$(CONFIG_TOUCHSCREEN_GSLX680) += gsl_point_id.o #$(obj)/gsl_point_id.o: $(srctre

8 Android平臺開發-WIFI 驅動移植 -- 詳細

一、WIFI的基本架構(程式碼路徑)     1、WIFI Settings應用程式:        packages/apps/Settings/src/com/android/setting

展訊平臺tp和lcd驅動除錯筆記

這些天在除錯展訊平臺上的tp和lcd驅動,這是一些小的總結。 螢幕出現豎條紋,(在視覺上給人的感覺是螢幕出現輕微的閃爍),這個可以調節vcom電壓,來調節這個電壓值,可以修復豎條紋. 但是無論怎麼修改都沒怎麼改善屏閃現象,可修改畫素點的翻轉方式,一般螢幕預設的翻轉方式是列

【TINY4412】LINUX移植筆記:(27)裝置樹LCD驅動

【TINY4412】LINUX移植筆記:(27)裝置樹 LCD驅動 宿主機 : 虛擬機器 Ubuntu 16.04 LTS / X64 目標板[底板]: Tiny4412SDK - 1506 目標板[核心板]: Ti

AM335x(TQ335x)學習筆記——LCD驅動移植

TI的LCD控制器驅動是非常完善的,共通的地方已經由驅動封裝好了,與按鍵一樣,我們可以通過DTS配置完成LCD的顯示。下面,我們來討論下使用DTS方式配置核心完成LCD驅動的思路。 (1)初步分析 由於TQ335x使用的晶片是AM335x,故仍然可以參考am335x-evm

S5PV210(TQ210)學習筆記——觸控式螢幕驅動編寫

電阻式觸控式螢幕的驅動比較簡單,可以採用輸入子系統驅動框架來編寫,而電容式觸控式螢幕的驅動程式相對比較複雜,因為電容觸控一般採用I2C引腳才控制,我在自己編寫電容觸控驅動的時候鬱悶了好幾天,當然,並不是因為I2C電容觸控驅動繁瑣,主要是天嵌TQ210的觸控式螢幕驅動程式是以模組方式提供的,並不開發原始

AM335x(TQ335x)學習筆記——USB驅動移植

對於AM335x來講,TI維護的USB驅動已經非常完善了,本文稱之為移植,實際上僅僅是配置核心選項使能USB HOST/OTG功能。廢話少說,直接動手開啟AM335x的USB驅動配置項。 Step1. 配置核心支援USB 預設的配置項沒有配置USB相關的選項,但是DTS已

IMX6Q移植ft5x06_ts觸控式螢幕驅動

一、附上原理圖     第一張圖是開發板的觸控式螢幕原理圖,第二張是顯示屏觸控式螢幕介面原理圖。對應起來只用到了六個腳,開發板7、8腳不用管。     從開發板觸控式螢幕介面可以看到用到了i2c2_scl、i2c2_sda,RST、INT四個主要的引腳,這裡要檢視觸控式螢

【TINY4412】LINUX移植筆記:(22)裝置樹LCD按鍵驅動

【TINY4412】LINUX移植筆記:(22)裝置樹 LCD按鍵驅動 宿主機 : 虛擬機器 Ubuntu 16.04 LTS / X64 目標板[底板]: Tiny4412SDK - 1506 目標板[核心板]: