Commit | Line | Data |
---|---|---|
1da177e4 LT |
1 | |
2 | sysfs - _The_ filesystem for exporting kernel objects. | |
3 | ||
4 | Patrick Mochel <mochel@osdl.org> | |
5 | ||
6 | 10 January 2003 | |
7 | ||
8 | ||
9 | What it is: | |
10 | ~~~~~~~~~~~ | |
11 | ||
12 | sysfs is a ram-based filesystem initially based on ramfs. It provides | |
13 | a means to export kernel data structures, their attributes, and the | |
14 | linkages between them to userspace. | |
15 | ||
16 | sysfs is tied inherently to the kobject infrastructure. Please read | |
17 | Documentation/kobject.txt for more information concerning the kobject | |
18 | interface. | |
19 | ||
20 | ||
21 | Using sysfs | |
22 | ~~~~~~~~~~~ | |
23 | ||
24 | sysfs is always compiled in. You can access it by doing: | |
25 | ||
26 | mount -t sysfs sysfs /sys | |
27 | ||
28 | ||
29 | Directory Creation | |
30 | ~~~~~~~~~~~~~~~~~~ | |
31 | ||
32 | For every kobject that is registered with the system, a directory is | |
33 | created for it in sysfs. That directory is created as a subdirectory | |
34 | of the kobject's parent, expressing internal object hierarchies to | |
35 | userspace. Top-level directories in sysfs represent the common | |
36 | ancestors of object hierarchies; i.e. the subsystems the objects | |
37 | belong to. | |
38 | ||
39 | Sysfs internally stores the kobject that owns the directory in the | |
40 | ->d_fsdata pointer of the directory's dentry. This allows sysfs to do | |
41 | reference counting directly on the kobject when the file is opened and | |
42 | closed. | |
43 | ||
44 | ||
45 | Attributes | |
46 | ~~~~~~~~~~ | |
47 | ||
48 | Attributes can be exported for kobjects in the form of regular files in | |
49 | the filesystem. Sysfs forwards file I/O operations to methods defined | |
50 | for the attributes, providing a means to read and write kernel | |
51 | attributes. | |
52 | ||
53 | Attributes should be ASCII text files, preferably with only one value | |
f8c34f98 | 54 | per file. It is noted that it may not be efficient to contain only one |
1da177e4 LT |
55 | value per file, so it is socially acceptable to express an array of |
56 | values of the same type. | |
57 | ||
58 | Mixing types, expressing multiple lines of data, and doing fancy | |
59 | formatting of data is heavily frowned upon. Doing these things may get | |
60 | you publically humiliated and your code rewritten without notice. | |
61 | ||
62 | ||
63 | An attribute definition is simply: | |
64 | ||
65 | struct attribute { | |
66 | char * name; | |
67 | mode_t mode; | |
68 | }; | |
69 | ||
70 | ||
71 | int sysfs_create_file(struct kobject * kobj, struct attribute * attr); | |
72 | void sysfs_remove_file(struct kobject * kobj, struct attribute * attr); | |
73 | ||
74 | ||
75 | A bare attribute contains no means to read or write the value of the | |
76 | attribute. Subsystems are encouraged to define their own attribute | |
77 | structure and wrapper functions for adding and removing attributes for | |
78 | a specific object type. | |
79 | ||
80 | For example, the driver model defines struct device_attribute like: | |
81 | ||
82 | struct device_attribute { | |
83 | struct attribute attr; | |
84 | ssize_t (*show)(struct device * dev, char * buf); | |
85 | ssize_t (*store)(struct device * dev, const char * buf); | |
86 | }; | |
87 | ||
88 | int device_create_file(struct device *, struct device_attribute *); | |
89 | void device_remove_file(struct device *, struct device_attribute *); | |
90 | ||
91 | It also defines this helper for defining device attributes: | |
92 | ||
f8d825bf | 93 | #define DEVICE_ATTR(_name, _mode, _show, _store) \ |
1da177e4 LT |
94 | struct device_attribute dev_attr_##_name = { \ |
95 | .attr = {.name = __stringify(_name) , .mode = _mode }, \ | |
96 | .show = _show, \ | |
97 | .store = _store, \ | |
98 | }; | |
99 | ||
100 | For example, declaring | |
101 | ||
91e49001 | 102 | static DEVICE_ATTR(foo, S_IWUSR | S_IRUGO, show_foo, store_foo); |
1da177e4 LT |
103 | |
104 | is equivalent to doing: | |
105 | ||
106 | static struct device_attribute dev_attr_foo = { | |
107 | .attr = { | |
108 | .name = "foo", | |
91e49001 | 109 | .mode = S_IWUSR | S_IRUGO, |
1da177e4 LT |
110 | }, |
111 | .show = show_foo, | |
112 | .store = store_foo, | |
113 | }; | |
114 | ||
115 | ||
116 | Subsystem-Specific Callbacks | |
117 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
118 | ||
119 | When a subsystem defines a new attribute type, it must implement a | |
120 | set of sysfs operations for forwarding read and write calls to the | |
121 | show and store methods of the attribute owners. | |
122 | ||
123 | struct sysfs_ops { | |
f8d825bf JV |
124 | ssize_t (*show)(struct kobject *, struct attribute *, char *); |
125 | ssize_t (*store)(struct kobject *, struct attribute *, const char *); | |
1da177e4 LT |
126 | }; |
127 | ||
128 | [ Subsystems should have already defined a struct kobj_type as a | |
129 | descriptor for this type, which is where the sysfs_ops pointer is | |
130 | stored. See the kobject documentation for more information. ] | |
131 | ||
132 | When a file is read or written, sysfs calls the appropriate method | |
133 | for the type. The method then translates the generic struct kobject | |
134 | and struct attribute pointers to the appropriate pointer types, and | |
135 | calls the associated methods. | |
136 | ||
137 | ||
138 | To illustrate: | |
139 | ||
f8d825bf | 140 | #define to_dev_attr(_attr) container_of(_attr, struct device_attribute, attr) |
1da177e4 LT |
141 | #define to_dev(d) container_of(d, struct device, kobj) |
142 | ||
143 | static ssize_t | |
144 | dev_attr_show(struct kobject * kobj, struct attribute * attr, char * buf) | |
145 | { | |
146 | struct device_attribute * dev_attr = to_dev_attr(attr); | |
147 | struct device * dev = to_dev(kobj); | |
148 | ssize_t ret = 0; | |
149 | ||
150 | if (dev_attr->show) | |
f8d825bf | 151 | ret = dev_attr->show(dev, buf); |
1da177e4 LT |
152 | return ret; |
153 | } | |
154 | ||
155 | ||
156 | ||
157 | Reading/Writing Attribute Data | |
158 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
159 | ||
160 | To read or write attributes, show() or store() methods must be | |
161 | specified when declaring the attribute. The method types should be as | |
162 | simple as those defined for device attributes: | |
163 | ||
164 | ssize_t (*show)(struct device * dev, char * buf); | |
165 | ssize_t (*store)(struct device * dev, const char * buf); | |
166 | ||
167 | IOW, they should take only an object and a buffer as parameters. | |
168 | ||
169 | ||
170 | sysfs allocates a buffer of size (PAGE_SIZE) and passes it to the | |
171 | method. Sysfs will call the method exactly once for each read or | |
172 | write. This forces the following behavior on the method | |
173 | implementations: | |
174 | ||
175 | - On read(2), the show() method should fill the entire buffer. | |
176 | Recall that an attribute should only be exporting one value, or an | |
177 | array of similar values, so this shouldn't be that expensive. | |
178 | ||
2424b5dd DW |
179 | This allows userspace to do partial reads and forward seeks |
180 | arbitrarily over the entire file at will. If userspace seeks back to | |
181 | zero or does a pread(2) with an offset of '0' the show() method will | |
182 | be called again, rearmed, to fill the buffer. | |
1da177e4 LT |
183 | |
184 | - On write(2), sysfs expects the entire buffer to be passed during the | |
185 | first write. Sysfs then passes the entire buffer to the store() | |
186 | method. | |
187 | ||
188 | When writing sysfs files, userspace processes should first read the | |
189 | entire file, modify the values it wishes to change, then write the | |
190 | entire buffer back. | |
191 | ||
192 | Attribute method implementations should operate on an identical | |
193 | buffer when reading and writing values. | |
194 | ||
195 | Other notes: | |
196 | ||
2424b5dd DW |
197 | - Writing causes the show() method to be rearmed regardless of current |
198 | file position. | |
199 | ||
1da177e4 LT |
200 | - The buffer will always be PAGE_SIZE bytes in length. On i386, this |
201 | is 4096. | |
202 | ||
203 | - show() methods should return the number of bytes printed into the | |
204 | buffer. This is the return value of snprintf(). | |
205 | ||
206 | - show() should always use snprintf(). | |
207 | ||
208 | - store() should return the number of bytes used from the buffer. This | |
209 | can be done using strlen(). | |
210 | ||
211 | - show() or store() can always return errors. If a bad value comes | |
212 | through, be sure to return an error. | |
213 | ||
214 | - The object passed to the methods will be pinned in memory via sysfs | |
215 | referencing counting its embedded object. However, the physical | |
216 | entity (e.g. device) the object represents may not be present. Be | |
217 | sure to have a way to check this, if necessary. | |
218 | ||
219 | ||
220 | A very simple (and naive) implementation of a device attribute is: | |
221 | ||
3eb8c783 | 222 | static ssize_t show_name(struct device *dev, struct device_attribute *attr, char *buf) |
1da177e4 | 223 | { |
f8d825bf | 224 | return snprintf(buf, PAGE_SIZE, "%s\n", dev->name); |
1da177e4 LT |
225 | } |
226 | ||
227 | static ssize_t store_name(struct device * dev, const char * buf) | |
228 | { | |
f8d825bf JV |
229 | sscanf(buf, "%20s", dev->name); |
230 | return strnlen(buf, PAGE_SIZE); | |
1da177e4 LT |
231 | } |
232 | ||
f8d825bf | 233 | static DEVICE_ATTR(name, S_IRUGO, show_name, store_name); |
1da177e4 LT |
234 | |
235 | ||
236 | (Note that the real implementation doesn't allow userspace to set the | |
237 | name for a device.) | |
238 | ||
239 | ||
240 | Top Level Directory Layout | |
241 | ~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
242 | ||
243 | The sysfs directory arrangement exposes the relationship of kernel | |
244 | data structures. | |
245 | ||
fff9289b | 246 | The top level sysfs directory looks like: |
1da177e4 LT |
247 | |
248 | block/ | |
249 | bus/ | |
250 | class/ | |
251 | devices/ | |
252 | firmware/ | |
253 | net/ | |
c86d90df | 254 | fs/ |
1da177e4 LT |
255 | |
256 | devices/ contains a filesystem representation of the device tree. It maps | |
257 | directly to the internal kernel device tree, which is a hierarchy of | |
258 | struct device. | |
259 | ||
260 | bus/ contains flat directory layout of the various bus types in the | |
261 | kernel. Each bus's directory contains two subdirectories: | |
262 | ||
263 | devices/ | |
264 | drivers/ | |
265 | ||
266 | devices/ contains symlinks for each device discovered in the system | |
267 | that point to the device's directory under root/. | |
268 | ||
269 | drivers/ contains a directory for each device driver that is loaded | |
270 | for devices on that particular bus (this assumes that drivers do not | |
271 | span multiple bus types). | |
272 | ||
c86d90df MS |
273 | fs/ contains a directory for some filesystems. Currently each |
274 | filesystem wanting to export attributes must create its own hierarchy | |
275 | below fs/ (see ./fuse.txt for an example). | |
276 | ||
1da177e4 LT |
277 | |
278 | More information can driver-model specific features can be found in | |
279 | Documentation/driver-model/. | |
280 | ||
281 | ||
282 | TODO: Finish this section. | |
283 | ||
284 | ||
285 | Current Interfaces | |
286 | ~~~~~~~~~~~~~~~~~~ | |
287 | ||
288 | The following interface layers currently exist in sysfs: | |
289 | ||
290 | ||
291 | - devices (include/linux/device.h) | |
292 | ---------------------------------- | |
293 | Structure: | |
294 | ||
295 | struct device_attribute { | |
296 | struct attribute attr; | |
297 | ssize_t (*show)(struct device * dev, char * buf); | |
298 | ssize_t (*store)(struct device * dev, const char * buf); | |
299 | }; | |
300 | ||
301 | Declaring: | |
302 | ||
f8d825bf | 303 | DEVICE_ATTR(_name, _str, _mode, _show, _store); |
1da177e4 LT |
304 | |
305 | Creation/Removal: | |
306 | ||
307 | int device_create_file(struct device *device, struct device_attribute * attr); | |
308 | void device_remove_file(struct device * dev, struct device_attribute * attr); | |
309 | ||
310 | ||
311 | - bus drivers (include/linux/device.h) | |
312 | -------------------------------------- | |
313 | Structure: | |
314 | ||
315 | struct bus_attribute { | |
316 | struct attribute attr; | |
317 | ssize_t (*show)(struct bus_type *, char * buf); | |
318 | ssize_t (*store)(struct bus_type *, const char * buf); | |
319 | }; | |
320 | ||
321 | Declaring: | |
322 | ||
f8d825bf | 323 | BUS_ATTR(_name, _mode, _show, _store) |
1da177e4 LT |
324 | |
325 | Creation/Removal: | |
326 | ||
327 | int bus_create_file(struct bus_type *, struct bus_attribute *); | |
328 | void bus_remove_file(struct bus_type *, struct bus_attribute *); | |
329 | ||
330 | ||
331 | - device drivers (include/linux/device.h) | |
332 | ----------------------------------------- | |
333 | ||
334 | Structure: | |
335 | ||
336 | struct driver_attribute { | |
337 | struct attribute attr; | |
338 | ssize_t (*show)(struct device_driver *, char * buf); | |
339 | ssize_t (*store)(struct device_driver *, const char * buf); | |
340 | }; | |
341 | ||
342 | Declaring: | |
343 | ||
f8d825bf | 344 | DRIVER_ATTR(_name, _mode, _show, _store) |
1da177e4 LT |
345 | |
346 | Creation/Removal: | |
347 | ||
348 | int driver_create_file(struct device_driver *, struct driver_attribute *); | |
349 | void driver_remove_file(struct device_driver *, struct driver_attribute *); | |
350 | ||
351 |