Linux Kernel
3.7.1
Main Page
Related Pages
Modules
Namespaces
Data Structures
Files
File List
Globals
All
Data Structures
Namespaces
Files
Functions
Variables
Typedefs
Enumerations
Enumerator
Macros
Groups
Pages
drivers
of
device.c
Go to the documentation of this file.
1
#include <linux/string.h>
2
#include <linux/kernel.h>
3
#include <
linux/of.h
>
4
#include <
linux/of_device.h
>
5
#include <
linux/init.h
>
6
#include <linux/module.h>
7
#include <
linux/mod_devicetable.h
>
8
#include <linux/slab.h>
9
10
#include <asm/errno.h>
11
20
const
struct
of_device_id
*
of_match_device
(
const
struct
of_device_id
*matches,
21
const
struct
device
*
dev
)
22
{
23
if
((!matches) || (!dev->
of_node
))
24
return
NULL
;
25
return
of_match_node
(matches, dev->
of_node
);
26
}
27
EXPORT_SYMBOL
(
of_match_device
);
28
29
struct
platform_device
*
of_dev_get
(
struct
platform_device
*
dev
)
30
{
31
struct
device
*
tmp
;
32
33
if
(!dev)
34
return
NULL
;
35
tmp =
get_device
(&dev->
dev
);
36
if
(tmp)
37
return
to_platform_device
(tmp);
38
else
39
return
NULL
;
40
}
41
EXPORT_SYMBOL
(
of_dev_get
);
42
43
void
of_dev_put
(
struct
platform_device
*
dev
)
44
{
45
if
(dev)
46
put_device
(&dev->
dev
);
47
}
48
EXPORT_SYMBOL
(
of_dev_put
);
49
50
int
of_device_add
(
struct
platform_device
*ofdev)
51
{
52
BUG_ON
(ofdev->
dev
.of_node ==
NULL
);
53
54
/* name and id have to be set so that the platform bus doesn't get
55
* confused on matching */
56
ofdev->
name
= dev_name(&ofdev->
dev
);
57
ofdev->
id
= -1;
58
59
/* device_add will assume that this device is on the same node as
60
* the parent. If there is no parent defined, set the node
61
* explicitly */
62
if
(!ofdev->
dev
.parent)
63
set_dev_node(&ofdev->
dev
,
of_node_to_nid
(ofdev->
dev
.of_node));
64
65
return
device_add
(&ofdev->
dev
);
66
}
67
68
int
of_device_register
(
struct
platform_device
*pdev)
69
{
70
device_initialize
(&pdev->
dev
);
71
return
of_device_add
(pdev);
72
}
73
EXPORT_SYMBOL
(
of_device_register
);
74
75
void
of_device_unregister
(
struct
platform_device
*ofdev)
76
{
77
device_unregister
(&ofdev->
dev
);
78
}
79
EXPORT_SYMBOL
(
of_device_unregister
);
80
81
ssize_t
of_device_get_modalias
(
struct
device
*
dev
,
char
*
str
,
ssize_t
len)
82
{
83
const
char
*compat;
84
int
cplen,
i
;
85
ssize_t
tsize, csize, repend;
86
87
/* Name & Type */
88
csize =
snprintf
(str, len,
"of:N%sT%s"
, dev->
of_node
->name,
89
dev->
of_node
->type);
90
91
/* Get compatible property if any */
92
compat =
of_get_property
(dev->
of_node
,
"compatible"
, &cplen);
93
if
(!compat)
94
return
csize;
95
96
/* Find true end (we tolerate multiple \0 at the end */
97
for
(i = (cplen - 1); i >= 0 && !compat[
i
]; i--)
98
cplen--;
99
if
(!cplen)
100
return
csize;
101
cplen++;
102
103
/* Check space (need cplen+1 chars including final \0) */
104
tsize = csize + cplen;
105
repend = tsize;
106
107
if
(csize >= len)
/* @ the limit, all is already filled */
108
return
tsize;
109
110
if
(tsize >= len) {
/* limit compat list */
111
cplen = len - csize - 1;
112
repend = len;
113
}
114
115
/* Copy and do char replacement */
116
memcpy
(&str[csize + 1], compat, cplen);
117
for
(i = csize; i < repend; i++) {
118
char
c
= str[
i
];
119
if
(c ==
'\0'
)
120
str[
i
] =
'C'
;
121
else
if
(c ==
' '
)
122
str[
i
] =
'_'
;
123
}
124
125
return
tsize;
126
}
127
131
void
of_device_uevent
(
struct
device
*
dev
,
struct
kobj_uevent_env
*
env
)
132
{
133
const
char
*compat;
134
int
seen = 0, cplen,
sl
;
135
136
if
((!dev) || (!dev->
of_node
))
137
return
;
138
139
add_uevent_var
(env,
"OF_NAME=%s"
, dev->
of_node
->name);
140
add_uevent_var
(env,
"OF_FULLNAME=%s"
, dev->
of_node
->full_name);
141
if
(dev->
of_node
->type &&
strcmp
(
"<NULL>"
, dev->
of_node
->type) != 0)
142
add_uevent_var
(env,
"OF_TYPE=%s"
, dev->
of_node
->type);
143
144
/* Since the compatible field can contain pretty much anything
145
* it's not really legal to split it out with commas. We split it
146
* up using a number of environment variables instead. */
147
compat =
of_get_property
(dev->
of_node
,
"compatible"
, &cplen);
148
while
(compat && *compat && cplen > 0) {
149
add_uevent_var
(env,
"OF_COMPATIBLE_%d=%s"
, seen, compat);
150
sl =
strlen
(compat) + 1;
151
compat +=
sl
;
152
cplen -=
sl
;
153
seen++;
154
}
155
add_uevent_var
(env,
"OF_COMPATIBLE_N=%d"
, seen);
156
}
157
158
int
of_device_uevent_modalias
(
struct
device
*
dev
,
struct
kobj_uevent_env
*
env
)
159
{
160
int
sl
;
161
162
if
((!dev) || (!dev->
of_node
))
163
return
-
ENODEV
;
164
165
/* Devicetree modalias is tricky, we add it in 2 steps */
166
if
(
add_uevent_var
(env,
"MODALIAS="
))
167
return
-
ENOMEM
;
168
169
sl =
of_device_get_modalias
(dev, &env->
buf
[env->
buflen
-1],
170
sizeof
(env->
buf
) - env->
buflen
);
171
if
(sl >= (
sizeof
(env->
buf
) - env->
buflen
))
172
return
-
ENOMEM
;
173
env->
buflen
+=
sl
;
174
175
return
0;
176
}
Generated on Thu Jan 10 2013 13:08:22 for Linux Kernel by
1.8.2