ioremap(cookie, size)を使用してドライバーを作成する
ioremap マクロは asm/io.h で定義されています。
例:IMX6U_CCM_CCGR1 = ioremap(CCM_CCGR1_BASE, 4);
iounmap を使用してドライバーを登録解除します。
2. ioremap() 関連関数の分析
I/O メモリ リソースの物理アドレスをコア仮想アドレスにマッピングした後、理論的に言えば、RAM の読み書きのように、I/O メモリ リソースを直接読み書きできます。ドライバーのクロスプラットフォーム移植性を確保するために、コア仮想アドレスへのポインターを使用する代わりに、Linux の特定の関数を使用して I/O メモリ リソースにアクセスする必要があります。
I/O を読み書きするための関数は次のとおりです。
a -- writel()
writel() はメモリ マップド I/O 空間にデータを書き込み、wirtel() は 32 ビット データ (4 バイト) を I/O に書き込みます。
原型:void writel (unsigned char data , unsigned int addr )
b -- readl()
readl() はメモリ マップド I/O 空間からデータを読み取り、readl は I/O から 32 ビット データ (4 バイト) を読み取ります。
プロトタイプ: unsigned char readl (unsigned int addr)
例えば:
/* 2. GPIO1 クロックを有効にします*/
val = readl(IMX6U_CCM_CCGR1);
val &= ~(3 << 26); /* 以前の設定をクリアします*/
val |= (3 << 26); /* 新しい設定を設定します値 */
writel(val, IMX6U_CCM_CCGR1);
readl() と writel() が連携して、LED の点滅などを実現します。
void led_switch(u8 sta)
{ u32 val = 0; if(sta == LEDON) { val = readl(GPIO1_DR);//GPIO1_DR レジスタの値を読み取る val &= ~(1 << 3); //Register For 1を3ビット左にシフトした値を反転し、valと論理積してvalに代入 write(val, GPIO1_DR);//GPIO1_DRレジスタにvalを書き込む } else if(sta == LEDOFF ) { val = readl (GPIO1_DR); val|= (1 << 3); write(val, GPIO1_DR); } }