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
misc
ti-st
st_ll.c
Go to the documentation of this file.
1
/*
2
* Shared Transport driver
3
* HCI-LL module responsible for TI proprietary HCI_LL protocol
4
* Copyright (C) 2009-2010 Texas Instruments
5
* Author: Pavan Savoy <
[email protected]
>
6
*
7
* This program is free software; you can redistribute it and/or modify
8
* it under the terms of the GNU General Public License version 2 as
9
* published by the Free Software Foundation.
10
*
11
* This program is distributed in the hope that it will be useful,
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
* GNU General Public License for more details.
15
*
16
* You should have received a copy of the GNU General Public License
17
* along with this program; if not, write to the Free Software
18
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19
*
20
*/
21
22
#define pr_fmt(fmt) "(stll) :" fmt
23
#include <
linux/skbuff.h
>
24
#include <linux/module.h>
25
#include <
linux/platform_device.h
>
26
#include <
linux/ti_wilink_st.h
>
27
28
/**********************************************************************/
29
/* internal functions */
30
static
void
send_ll_cmd(
struct
st_data_s
*st_data,
31
unsigned
char
cmd
)
32
{
33
34
pr_debug
(
"%s: writing %x"
, __func__, cmd);
35
st_int_write
(st_data, &cmd, 1);
36
return
;
37
}
38
39
static
void
ll_device_want_to_sleep(
struct
st_data_s
*st_data)
40
{
41
struct
kim_data_s
*kim_data;
42
struct
ti_st_plat_data
*
pdata
;
43
44
pr_debug
(
"%s"
, __func__);
45
/* sanity check */
46
if
(st_data->
ll_state
!=
ST_LL_AWAKE
)
47
pr_err
(
"ERR hcill: ST_LL_GO_TO_SLEEP_IND"
48
"in state %ld"
, st_data->
ll_state
);
49
50
send_ll_cmd(st_data,
LL_SLEEP_ACK
);
51
/* update state */
52
st_data->
ll_state
=
ST_LL_ASLEEP
;
53
54
/* communicate to platform about chip asleep */
55
kim_data = st_data->
kim_data
;
56
pdata = kim_data->
kim_pdev
->dev.platform_data;
57
if
(pdata->
chip_asleep
)
58
pdata->
chip_asleep
(
NULL
);
59
}
60
61
static
void
ll_device_want_to_wakeup(
struct
st_data_s
*st_data)
62
{
63
struct
kim_data_s
*kim_data;
64
struct
ti_st_plat_data
*
pdata
;
65
66
/* diff actions in diff states */
67
switch
(st_data->
ll_state
) {
68
case
ST_LL_ASLEEP
:
69
send_ll_cmd(st_data,
LL_WAKE_UP_ACK
);
/* send wake_ack */
70
break
;
71
case
ST_LL_ASLEEP_TO_AWAKE
:
72
/* duplicate wake_ind */
73
pr_err
(
"duplicate wake_ind while waiting for Wake ack"
);
74
break
;
75
case
ST_LL_AWAKE
:
76
/* duplicate wake_ind */
77
pr_err
(
"duplicate wake_ind already AWAKE"
);
78
break
;
79
case
ST_LL_AWAKE_TO_ASLEEP
:
80
/* duplicate wake_ind */
81
pr_err
(
"duplicate wake_ind"
);
82
break
;
83
}
84
/* update state */
85
st_data->
ll_state
=
ST_LL_AWAKE
;
86
87
/* communicate to platform about chip wakeup */
88
kim_data = st_data->
kim_data
;
89
pdata = kim_data->
kim_pdev
->dev.platform_data;
90
if
(pdata->
chip_awake
)
91
pdata->
chip_awake
(
NULL
);
92
}
93
94
/**********************************************************************/
95
/* functions invoked by ST Core */
96
97
/* called when ST Core wants to
98
* enable ST LL */
99
void
st_ll_enable
(
struct
st_data_s
*ll)
100
{
101
ll->
ll_state
=
ST_LL_AWAKE
;
102
}
103
104
/* called when ST Core /local module wants to
105
* disable ST LL */
106
void
st_ll_disable
(
struct
st_data_s
*ll)
107
{
108
ll->
ll_state
=
ST_LL_INVALID
;
109
}
110
111
/* called when ST Core wants to update the state */
112
void
st_ll_wakeup
(
struct
st_data_s
*ll)
113
{
114
if
(
likely
(ll->
ll_state
!=
ST_LL_AWAKE
)) {
115
send_ll_cmd(ll,
LL_WAKE_UP_IND
);
/* WAKE_IND */
116
ll->
ll_state
=
ST_LL_ASLEEP_TO_AWAKE
;
117
}
else
{
118
/* don't send the duplicate wake_indication */
119
pr_err
(
" Chip already AWAKE "
);
120
}
121
}
122
123
/* called when ST Core wants the state */
124
unsigned
long
st_ll_getstate
(
struct
st_data_s
*ll)
125
{
126
pr_debug
(
" returning state %ld"
, ll->
ll_state
);
127
return
ll->
ll_state
;
128
}
129
130
/* called from ST Core, when a PM related packet arrives */
131
unsigned
long
st_ll_sleep_state
(
struct
st_data_s
*st_data,
132
unsigned
char
cmd
)
133
{
134
switch
(cmd) {
135
case
LL_SLEEP_IND
:
/* sleep ind */
136
pr_debug
(
"sleep indication recvd"
);
137
ll_device_want_to_sleep(st_data);
138
break
;
139
case
LL_SLEEP_ACK
:
/* sleep ack */
140
pr_err
(
"sleep ack rcvd: host shouldn't"
);
141
break
;
142
case
LL_WAKE_UP_IND
:
/* wake ind */
143
pr_debug
(
"wake indication recvd"
);
144
ll_device_want_to_wakeup(st_data);
145
break
;
146
case
LL_WAKE_UP_ACK
:
/* wake ack */
147
pr_debug
(
"wake ack rcvd"
);
148
st_data->
ll_state
=
ST_LL_AWAKE
;
149
break
;
150
default
:
151
pr_err
(
" unknown input/state "
);
152
return
-
EINVAL
;
153
}
154
return
0;
155
}
156
157
/* Called from ST CORE to initialize ST LL */
158
long
st_ll_init
(
struct
st_data_s
*ll)
159
{
160
/* set state to invalid */
161
ll->
ll_state
=
ST_LL_INVALID
;
162
return
0;
163
}
164
165
/* Called from ST CORE to de-initialize ST LL */
166
long
st_ll_deinit
(
struct
st_data_s
*ll)
167
{
168
return
0;
169
}
Generated on Thu Jan 10 2013 13:55:11 for Linux Kernel by
1.8.2