0
  • 聊天消息
  • 系統(tǒng)消息
  • 評論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

linux--sysfs文件系統(tǒng)

Rice嵌入式開發(fā)技術(shù)分享 ? 來源:Rice嵌入式 ? 作者:Rice嵌入式 ? 2024-07-08 11:37 ? 次閱讀

sysfs文件系統(tǒng)

sysfs,全稱為System Filesystem,是一個由Linux內(nèi)核實(shí)現(xiàn)的虛擬文件系統(tǒng)。它扮演著一個橋梁的角色,將內(nèi)核中的設(shè)備和驅(qū)動程序信息以文件的形式呈現(xiàn)給用戶空間。與/proc文件系統(tǒng)相似,sysfs專注于展示設(shè)備和驅(qū)動程序的細(xì)節(jié),而/proc則主要反映進(jìn)程信息。

在sysfs中,信息被組織成層次化的文件系統(tǒng)結(jié)構(gòu)。每個設(shè)備或內(nèi)核對象在文件系統(tǒng)中都有其對應(yīng)的表示,通常是以文件或目錄的形式存在。這些文件不僅存儲了設(shè)備的屬性和狀態(tài)信息,而且很多文件還允許用戶通過讀寫操作來對設(shè)備進(jìn)行配置或控制。

sysfs默認(rèn)掛載在文件系統(tǒng)的/sys路徑下。通過這個虛擬文件系統(tǒng),用戶空間的應(yīng)用程序能夠以一種直觀和動態(tài)的方式訪問和管理系統(tǒng)設(shè)備,無需進(jìn)行復(fù)雜的內(nèi)核空間交互。這種設(shè)計(jì)提供了一種高效且用戶友好的接口,使得設(shè)備管理變得更加簡單和靈活。

kernel Object

在Linux內(nèi)核架構(gòu)中,kobject扮演著一個核心角色,它是一個用于抽象化內(nèi)核對象的框架。kobject不僅構(gòu)成了內(nèi)核中各種子系統(tǒng)的基礎(chǔ)構(gòu)件,而且能夠代表設(shè)備、驅(qū)動程序、總線等多樣化的內(nèi)核實(shí)體。

kobject架構(gòu)提供了一種靈活且統(tǒng)一的模型,用以維護(hù)和管理內(nèi)核對象。每個Kobject實(shí)例都擁有一個獨(dú)一無二的標(biāo)識符和指向其上層Kobject的鏈接,這樣的設(shè)計(jì)允許它們形成一個有序的層級網(wǎng)絡(luò)。更進(jìn)一步,Kobject可以附加多種屬性,這些屬性反映了對象的特征或狀態(tài),并且可以通過sysfs這一虛擬文件系統(tǒng)對外公布,使得用戶空間程序能夠訪問和操作這些屬性。

Sysfs作為Kobject信息呈現(xiàn)的媒介,將內(nèi)核內(nèi)部的設(shè)備和驅(qū)動程序等對象的狀態(tài)和信息以文件的形式展現(xiàn)給用戶空間。每當(dāng)內(nèi)核中新增設(shè)備或驅(qū)動程序時,相應(yīng)的Kobject實(shí)例也會被動態(tài)創(chuàng)建,并通過Sysfs將這些信息映射到用戶空間可訪問的路徑下。

在Linux內(nèi)核的源碼樹中,struct kobject這一數(shù)據(jù)結(jié)構(gòu)在"linux/kobject.h"頭文件里定義。它經(jīng)常作為其他結(jié)構(gòu)體的成員出現(xiàn),使得這些結(jié)構(gòu)體所代表的內(nèi)核對象能夠整合進(jìn)Kobject的管理體系中。通過這種方式,內(nèi)核開發(fā)者可以輕松地為各種內(nèi)核對象實(shí)現(xiàn)統(tǒng)一的管理和訪問接口。

structkobject{
constchar*name;
structlist_headentry;
structkobject*parent;
structkset*kset;
structkobj_type*ktype;
structkernfs_node*sd;/*sysfsdirectoryentry*/
structkrefkref;
...
};

其中:- kref:提供kobject的引用技術(shù)。- ktype:kobject關(guān)聯(lián)的類型。- kset:指向同一類kobject集合的指針。- sd:當(dāng)前kobject在/sys下的目錄條目。

sysfs使用方式

Linux內(nèi)核中使用sysfs的步驟比較簡單:(1)在sys路徑下創(chuàng)建目錄;(2)創(chuàng)建sysfs文件。下面將詳細(xì)展開這兩步涉及的內(nèi)核API。

在sys下創(chuàng)建目錄

structkobject*kobject_create_and_add(constchar*name,structkobject*parent);

Linux內(nèi)核預(yù)定義了幾個常用的parent參數(shù):- kernel_kobj:在/sys/kernel下創(chuàng)建目錄;- firmware_kobj:在/sys/firmware下創(chuàng)建目錄;- fs_kobj:在/sys/fs下創(chuàng)建目錄。- 如果parent取值為NULL,則在/sys下面創(chuàng)建目錄。

相應(yīng)地,如果需要刪除對應(yīng)的sysfs目錄,可以用:

voidkobject_put(structkobject*kobj);

創(chuàng)建sysfs文件

sysfs文件可以通過sysfs屬性來創(chuàng)建,它定義在頭文件"sysfs.h"中:

structkobj_attribute{
structattributeattr;
ssize_t(*show)(structkobject*kobj,structkobj_attribute*attr,char*buf);
ssize_t(*store)(structkobject*kobj,structkobj_attribute*attr,constchar*buf,size_tcount);
};

attr表示將要創(chuàng)建的文件(屬性),而show和store分別表示對應(yīng)的sysfs文件在讀和寫操作時的回調(diào)函數(shù)。

struct kobj_attribute可以通過__ATTR宏來創(chuàng)建:

__ATTR(name,permission,show_ptr,store_ptr);

準(zhǔn)備好attr之后,可以通過sysfs_create_file來創(chuàng)建出sysfs文件:

intsysfs_create_file(structkobject*kobj,conststructattribute*attr);

如果需要刪除對應(yīng)的sysfs文件,可以用:

voidsysfs_remove_file(structkobject*kobj,conststructattribute*attr);

sysfs創(chuàng)建設(shè)備節(jié)點(diǎn)

前面描述了如何創(chuàng)建一個基本的sysfs,接下載描述的是如何創(chuàng)建設(shè)備節(jié)點(diǎn)的sysfs。

實(shí)際創(chuàng)建設(shè)備節(jié)點(diǎn)的sysf跟基本的sysfs是一樣的,只是結(jié)構(gòu)體換了一個名字。它使用DEVICE_ATTR宏,可以定義一個struct device_attribute設(shè)備屬性,使用sysfs_create_file便可以在設(shè)備目錄下創(chuàng)建具有show和store方法的節(jié)點(diǎn)。

DEVICE_ATTR宏定義

DEVICE_ATTR宏定義如下:

#defineDEVICE_ATTR(_name,_mode,_show,_store)
structdevice_attributedev_attr_##_name=__ATTR(_name,_mode,_show,_store)

__ATTR宏定義,宏定義在include/linux/sysfs.h文件中,如下:

#define__ATTR(_name,_mode,_show,_store){
.attr={.name=__stringify(_name),
.mode=VERIFY_OCTAL_PERMISSIONS(_mode)},
.show=_show,
.store=_store,
}

struct device_attribute結(jié)構(gòu)體,該結(jié)構(gòu)體的定義在include /linux/device.h,其定義如下:

structdevice_attribute{
structattributeattr;
ssize_t(*show)(structdevice*dev,structdevice_attribute*attr,
char*buf);
ssize_t(*store)(structdevice*dev,structdevice_attribute*attr,
constchar*buf,size_tcount);
};

struct attribute結(jié)構(gòu)體, 該結(jié)構(gòu)體的定義在include /linux/device.h,其定義如下:

structattribute{
constchar*name;
umode_tmode;
#ifdefCONFIG_DEBUG_LOCK_ALLOC
boolignore_lockdep:1;
structlock_class_key*key;
structlock_class_keyskey;
#endif
};

DEVICE_ATTR宏定義等價(jià)說明

我們頂一個文件的范式如下

DEVICE_ATTR(_name,_mode,_show,_store)

等價(jià)于:

structdevice_attributedev_attr_##_name={
.attr={.name=__stringify(_name),
.mode=VERIFY_OCTAL_PERMISSIONS(_mode)},
.show=_show,
.store=_store,
}

show函數(shù)的詳細(xì)描述:

ssize_t(*show)(structdevice*dev,structdevice_attribute*attr,char*buf);

參數(shù)說明:

入?yún)uf是需要我們填充的string即我們cat屬性節(jié)點(diǎn)時要顯示的內(nèi)容;-函數(shù)的返回值是我們填充buf的長度,且長度應(yīng)當(dāng)小于一個頁面的大?。?096字節(jié));

其他參數(shù)一般不用關(guān)心。

實(shí)例說明,當(dāng)我們使用cat命令的時候,將調(diào)用該函數(shù)

staticssize_tshow_youyeetoo_device(structdevice*dev,
structdevice_attribute*attr,char*buf)
{
returnsprintf(buf,"%sn",mybuf);
}

store函數(shù)的詳細(xì)描述:

ssize_t(*store)(structdevice*dev,structdevice_attribute*attr,constchar*buf,size_tcount);

參數(shù)說明:

入?yún)uf是用戶傳入的字符串,即echo到屬性節(jié)點(diǎn)的內(nèi)容;

入?yún)ount是buf中字符串的長度。

函數(shù)的返回值通常返回count即可。

其他參數(shù)一般不用關(guān)心。

實(shí)例說明,當(dāng)我們使用echo命令的時候,將調(diào)用該函數(shù):

staticssize_tstore_youyeetoo_device(structdevice*dev,
structdevice_attribute*attr,
constchar*buf,size_tcount)
{
sprintf(mybuf,"%s",buf);
returncount;
}

mode的權(quán)限定義,在kernel/include/uapi/linux/stat.h中:

#defineS_IRWXU00700//用戶可讀寫和執(zhí)行
#defineS_IRUSR00400//用戶可讀
#defineS_IWUSR00200//用戶可寫
#defineS_IXUSR00100//用戶可執(zhí)行

#defineS_IRWXG00070//用戶組可讀寫和執(zhí)行
#defineS_IRGRP00040//用戶組可讀
#defineS_IWGRP00020//用戶組可寫
#defineS_IXGRP00010//用戶組可執(zhí)行

#defineS_IRWXO00007//其他可讀寫和執(zhí)行
#defineS_IROTH00004//其他可讀
#defineS_IWOTH00002//其他可寫
#defineS_IXOTH00001//其他可執(zhí)行

至此,我們已經(jīng)定義好了.show和.store函數(shù),那么就可以使用DEVICE_ATTR了。

staticDEVICE_ATTR(youyeetoo_device,S_IWUSR|S_IRUSR,show_youyeetoo_device,store_youyeetoo_device);

device attribute添加到sysfs

上面描述的是sysfs的讀寫接口的定義方式,他還需要注冊到sysfs中。才會在對應(yīng)驅(qū)動中顯示我們的文件,其中:

注冊函數(shù):sysfs_create_file();

注銷函數(shù):sysfs_remove_file();

樣例代碼代碼:

注冊樣例:

sysfs_create_file(&(youyeetoo_dev->kobj),&dev_attr_youyeetoo.attr);

注銷樣例:

sysfs_remove_file(&(youyeetoo_dev->kobj),&dev_attr_youyeetoo.attr);

sysfs樣例測試

完整的測試代碼,在sysfs的驅(qū)動節(jié)點(diǎn)里面生成一個youyeetoo文件,文件支持讀寫功能。

#include
#include
#include
#include
#include

staticintmajor;
staticstructclass*youyeetoo_class;
structdevice*youyeetoo_dev;
staticcharyouyeetoo_buff[100]="youyeetoo";

staticssize_tshow_youyeetoo_device(structdevice*dev,
structdevice_attribute*attr,char*buf)
{
returnsprintf(buf,"%sn",youyeetoo_buff);
}

staticssize_tstore_youyeetoo_device(structdevice*dev,
structdevice_attribute*attr,
constchar*buf,size_tcount)
{
sprintf(youyeetoo_buff,"%s",buf);
returncount;
}
staticDEVICE_ATTR(youyeetoo,S_IWUSR|S_IRUSR,show_youyeetoo_device,store_youyeetoo_device);

structfile_operationsyouyeetoo_ops={
.owner=THIS_MODULE,
};

staticintyouyeetoo_init(void)
{
major=register_chrdev(0,"youyeetoo",&youyeetoo_ops);
youyeetoo_class=class_create(THIS_MODULE,"youyeetoo");
youyeetoo_dev=device_create(youyeetoo_class,0,MKDEV(major,0),NULL,"youyeetoo");
if(sysfs_create_file(&(youyeetoo_dev->kobj),&dev_attr_youyeetoo.attr))
{//在mytest_device設(shè)備目錄下創(chuàng)建一個sys_device_file屬性文件
return-1;
}

return0;
}

staticvoidyouyeetoo_exit(void)
{
device_destroy(youyeetoo_class,MKDEV(major,0));
class_destroy(youyeetoo_class);
unregister_chrdev(major,"youyeetoo");
sysfs_remove_file(&(youyeetoo_dev->kobj),&dev_attr_youyeetoo.attr);
}

module_init(youyeetoo_init);
module_exit(youyeetoo_exit);
MODULE_AUTHOR("youyeetoo");
MODULE_LICENSE("GPL");

將上面驅(qū)動編譯燒錄之后,就可以sysfs下看到我們創(chuàng)建的文件:

4ccf9d98-3bf9-11ef-82a0-92fbcf53809c.png

測試我們創(chuàng)建的sysfs

4cdd524e-3bf9-11ef-82a0-92fbcf53809c.png

4ce0f1ec-3bf9-11ef-82a0-92fbcf53809c.png

審核編輯 黃宇

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請聯(lián)系本站處理。 舉報(bào)投訴
  • Linux
    +關(guān)注

    關(guān)注

    87

    文章

    11414

    瀏覽量

    212249
  • Sysfs
    +關(guān)注

    關(guān)注

    0

    文章

    15

    瀏覽量

    6273
收藏 人收藏

    評論

    相關(guān)推薦

    飛凌嵌入式ElfBoard ELF 1板卡-應(yīng)用編程示例控制LED燈之sysfs文件系統(tǒng)

    sysfs文件系統(tǒng)概念 sysfsLinux2.6以上的內(nèi)核在發(fā)展迭代過程中衍生出來的一個功能,它的作用是通過一個內(nèi)存文件系統(tǒng)將信息導(dǎo)出
    發(fā)表于 10-18 09:31

    【AWorks試用體驗(yàn)】使用sysfs文件系統(tǒng) 控制IED(1) Shell 點(diǎn)亮LED

    在嵌入式設(shè)備中控制GPIO 一般做法是通過寫一個單獨(dú)的驅(qū)動程序。而大多數(shù)資料顯示都是使用這一種方法。 但其實(shí)Linux下有一個通用的 GPIO 控制接口, 就是 sysfs文件系統(tǒng)什么是sys
    發(fā)表于 08-16 19:17

    Linux文件系統(tǒng)課程

    本章學(xué)習(xí)目標(biāo)理解什么是文件系統(tǒng)了解文件系統(tǒng)工作原理理解Fedora Core Linux文件系統(tǒng)的結(jié)構(gòu)掌握Fedora Core Linux
    發(fā)表于 04-10 17:07 ?0次下載

    Linux文件系統(tǒng)簡介

    Linux文件系統(tǒng)簡介 什么是根文件   根文件系統(tǒng)首先是一種文件系統(tǒng),但是相對于普通的文件系統(tǒng)
    發(fā)表于 04-21 17:01 ?5156次閱讀

    玩轉(zhuǎn)Linux,先把文件系統(tǒng)搞懂

    Linux 支持多種文件系統(tǒng),包括 ext2 、 ext3 、 vfat 、 ntfs 、 iso9660 、 jffs 、 romfs 和 nfs 等,為了對各類文件系統(tǒng)進(jìn)行統(tǒng)一管理, Li
    發(fā)表于 08-16 10:50 ?2141次閱讀
    玩轉(zhuǎn)<b class='flag-5'>Linux</b>,先把<b class='flag-5'>文件系統(tǒng)</b>搞懂

    Linux設(shè)備驅(qū)動開發(fā)詳解》第5章、Linux文件系統(tǒng)與設(shè)備文件系統(tǒng)

    Linux設(shè)備驅(qū)動開發(fā)詳解》第5章、Linux文件系統(tǒng)與設(shè)備文件系統(tǒng)
    發(fā)表于 10-27 14:13 ?0次下載
    《<b class='flag-5'>Linux</b>設(shè)備驅(qū)動開發(fā)詳解》第5章、<b class='flag-5'>Linux</b><b class='flag-5'>文件系統(tǒng)</b>與設(shè)備<b class='flag-5'>文件系統(tǒng)</b>

    Linux 內(nèi)核/sys 文件系統(tǒng)介紹

    linux2.6內(nèi)核引入sysfs文件系統(tǒng),sysfs可以看成與proc,devfs和devpty同類別的文件系統(tǒng),該
    發(fā)表于 04-25 16:20 ?4418次閱讀
    <b class='flag-5'>Linux</b> 內(nèi)核/sys <b class='flag-5'>文件系統(tǒng)</b>介紹

    學(xué)會使用Linux 文件系統(tǒng):procfs, sysfs, debugfs

    sysfs 中,有另外一個常見用法,那就是在一個 kobject 對應(yīng)的目錄下創(chuàng)建一個符號(屬性文件)指向另外一個 kobject 對應(yīng)的目錄,通常這個是為了方便記憶和訪問。這個API是 sysfs_create_link。
    發(fā)表于 04-25 17:19 ?1281次閱讀

    可以了解的Linux 文件系統(tǒng)結(jié)構(gòu)

    Linux中的文件是什么?它的文件系統(tǒng)又是什么?那些配置文件又在哪里?我下載好的程序保存在哪里了?在 Linux
    發(fā)表于 04-27 14:06 ?780次閱讀
    可以了解的<b class='flag-5'>Linux</b> <b class='flag-5'>文件系統(tǒng)</b>結(jié)構(gòu)

    Linux最新UBI文件系統(tǒng)介紹

    嵌入式linux中文站關(guān)注嵌入式linux文件系統(tǒng)的發(fā)展。在linux-2.6.27以前,談到Flash文件系統(tǒng),大家很多時候多會想到cra
    發(fā)表于 04-27 19:37 ?6482次閱讀

    Linux設(shè)備模型:sysfs

    sysfs是一個基于RAM的文件系統(tǒng),它和Kobject一起,可以將Kernel的數(shù)據(jù)結(jié)構(gòu)導(dǎo)出到用戶空間,以文件目錄結(jié)構(gòu)的形式,提供對這些數(shù)據(jù)結(jié)構(gòu)(以及數(shù)據(jù)結(jié)構(gòu)的屬性)的訪問支持。
    發(fā)表于 05-12 09:50 ?1429次閱讀

    Linux文件系統(tǒng)解析

    Linux 中,最直觀、最可見的部分就是 文件系統(tǒng)(file system)。下面我們就來一起探討一下關(guān)于 Linux 中國的文件系統(tǒng),系統(tǒng)
    的頭像 發(fā)表于 09-16 11:29 ?2649次閱讀
    <b class='flag-5'>Linux</b><b class='flag-5'>文件系統(tǒng)</b>解析

    適用于Linux的最佳通用文件系統(tǒng) Linux文件系統(tǒng)的安裝

    為您的計(jì)算機(jī)選擇正確的文件系統(tǒng)可能是一個困難的過程。您可能會想知道:為什么文件系統(tǒng)很重要?有沒有適用于安裝 Linux 的特定文件系統(tǒng)? 事實(shí)證明,有兩種
    發(fā)表于 08-03 10:22 ?445次閱讀
    適用于<b class='flag-5'>Linux</b>的最佳通用<b class='flag-5'>文件系統(tǒng)</b> <b class='flag-5'>Linux</b><b class='flag-5'>文件系統(tǒng)</b>的安裝

    Linux文件系統(tǒng)特點(diǎn)

    Linux文件系統(tǒng)特點(diǎn) 文件系統(tǒng)要有嚴(yán)格的組織形式,使得文件能夠以塊為單位進(jìn)行存儲。 文件系統(tǒng)中也要有索引區(qū),用來方便查找一個
    的頭像 發(fā)表于 11-09 14:48 ?1441次閱讀
    <b class='flag-5'>Linux</b>的<b class='flag-5'>文件系統(tǒng)</b>特點(diǎn)

    Linux文件系統(tǒng)的掛載過程

    Linux文件系統(tǒng)(rootfs)是Linux系統(tǒng)中所有其他文件系統(tǒng)和目錄的起點(diǎn),它是內(nèi)核啟動時掛載的第一個
    的頭像 發(fā)表于 10-05 16:50 ?750次閱讀

    電子發(fā)燒友

    中國電子工程師最喜歡的網(wǎng)站

    • 2931785位工程師會員交流學(xué)習(xí)
    • 獲取您個性化的科技前沿技術(shù)信息
    • 參加活動獲取豐厚的禮品