Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(55)

Side by Side Diff: chromeos/drivers/ath6kl/os/linux/ar6000_raw_if.c

Issue 646055: Atheros AR600x driver + build glue (Closed)
Patch Set: Created 10 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 /*
2 *
3 * Copyright (c) 2004-2007 Atheros Communications Inc.
4 * All rights reserved.
5 *
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 // Software distributed under the License is distributed on an "AS
12 // IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
13 // implied. See the License for the specific language governing
14 // rights and limitations under the License.
15 //
16 //
17 *
18 */
19
20 #include "ar6000_drv.h"
21
22 #ifdef HTC_RAW_INTERFACE
23
24 static void
25 ar6000_htc_raw_read_cb(void *Context, HTC_PACKET *pPacket)
26 {
27 AR_SOFTC_T *ar = (AR_SOFTC_T *)Context;
28 raw_htc_buffer *busy;
29 HTC_RAW_STREAM_ID streamID;
30
31 busy = (raw_htc_buffer *)pPacket->pPktContext;
32 A_ASSERT(busy != NULL);
33
34 if (pPacket->Status == A_ECANCELED) {
35 /*
36 * HTC provides A_ECANCELED status when it doesn't want to be refilled
37 * (probably due to a shutdown)
38 */
39 return;
40 }
41
42 streamID = arEndpoint2RawStreamID(ar,pPacket->Endpoint);
43 A_ASSERT(streamID != HTC_RAW_STREAM_NOT_MAPPED);
44
45 #ifdef CF
46 if (down_trylock(&ar->raw_htc_read_sem[streamID])) {
47 #else
48 if (down_interruptible(&ar->raw_htc_read_sem[streamID])) {
49 #endif /* CF */
50 AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("Unable to down the semaphore\n"));
51 }
52
53 A_ASSERT((pPacket->Status != A_OK) ||
54 (pPacket->pBuffer == (busy->data + HTC_HEADER_LEN)));
55
56 busy->length = pPacket->ActualLength + HTC_HEADER_LEN;
57 busy->currPtr = HTC_HEADER_LEN;
58 ar->read_buffer_available[streamID] = TRUE;
59 //AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("raw read cb: 0x%X 0x%X \n", busy->currPtr ,busy->length);
60 up(&ar->raw_htc_read_sem[streamID]);
61
62 /* Signal the waiting process */
63 AR_DEBUG_PRINTF(ATH_DEBUG_HTC_RAW,("Waking up the StreamID(%d) read process\ n", streamID));
64 wake_up_interruptible(&ar->raw_htc_read_queue[streamID]);
65 }
66
67 static void
68 ar6000_htc_raw_write_cb(void *Context, HTC_PACKET *pPacket)
69 {
70 AR_SOFTC_T *ar = (AR_SOFTC_T *)Context;
71 raw_htc_buffer *free;
72 HTC_RAW_STREAM_ID streamID;
73
74 free = (raw_htc_buffer *)pPacket->pPktContext;
75 A_ASSERT(free != NULL);
76
77 if (pPacket->Status == A_ECANCELED) {
78 /*
79 * HTC provides A_ECANCELED status when it doesn't want to be refilled
80 * (probably due to a shutdown)
81 */
82 return;
83 }
84
85 streamID = arEndpoint2RawStreamID(ar,pPacket->Endpoint);
86 A_ASSERT(streamID != HTC_RAW_STREAM_NOT_MAPPED);
87
88 #ifdef CF
89 if (down_trylock(&ar->raw_htc_write_sem[streamID])) {
90 #else
91 if (down_interruptible(&ar->raw_htc_write_sem[streamID])) {
92 #endif
93 AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("Unable to down the semaphore\n"));
94 }
95
96 A_ASSERT(pPacket->pBuffer == (free->data + HTC_HEADER_LEN));
97
98 free->length = 0;
99 ar->write_buffer_available[streamID] = TRUE;
100 up(&ar->raw_htc_write_sem[streamID]);
101
102 /* Signal the waiting process */
103 AR_DEBUG_PRINTF(ATH_DEBUG_HTC_RAW,("Waking up the StreamID(%d) write process \n", streamID));
104 wake_up_interruptible(&ar->raw_htc_write_queue[streamID]);
105 }
106
107 /* connect to a service */
108 static A_STATUS ar6000_connect_raw_service(AR_SOFTC_T *ar,
109 HTC_RAW_STREAM_ID StreamID)
110 {
111 A_STATUS status;
112 HTC_SERVICE_CONNECT_RESP response;
113 A_UINT8 streamNo;
114 HTC_SERVICE_CONNECT_REQ connect;
115
116 do {
117
118 A_MEMZERO(&connect,sizeof(connect));
119 /* pass the stream ID as meta data to the RAW streams service */
120 streamNo = (A_UINT8)StreamID;
121 connect.pMetaData = &streamNo;
122 connect.MetaDataLength = sizeof(A_UINT8);
123 /* these fields are the same for all endpoints */
124 connect.EpCallbacks.pContext = ar;
125 connect.EpCallbacks.EpTxComplete = ar6000_htc_raw_write_cb;
126 connect.EpCallbacks.EpRecv = ar6000_htc_raw_read_cb;
127 /* simple interface, we don't need these optional callbacks */
128 connect.EpCallbacks.EpRecvRefill = NULL;
129 connect.EpCallbacks.EpSendFull = NULL;
130 connect.MaxSendQueueDepth = RAW_HTC_WRITE_BUFFERS_NUM;
131
132 /* connect to the raw streams service, we may be able to get 1 or mo re
133 * connections, depending on WHAT is running on the target */
134 connect.ServiceID = HTC_RAW_STREAMS_SVC;
135
136 A_MEMZERO(&response,sizeof(response));
137
138 /* try to connect to the raw stream, it is okay if this fails with
139 * status HTC_SERVICE_NO_MORE_EP */
140 status = HTCConnectService(ar->arHtcTarget,
141 &connect,
142 &response);
143
144 if (A_FAILED(status)) {
145 if (response.ConnectRespCode == HTC_SERVICE_NO_MORE_EP) {
146 AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("HTC RAW , No more streams allowe d \n"));
147 status = A_OK;
148 }
149 break;
150 }
151
152 /* set endpoint mapping for the RAW HTC streams */
153 arSetRawStream2EndpointIDMap(ar,StreamID,response.Endpoint);
154
155 AR_DEBUG_PRINTF(ATH_DEBUG_HTC_RAW,("HTC RAW : stream ID: %d, endpoint: % d\n",
156 StreamID, arRawStream2EndpointID(ar,StreamID)));
157
158 } while (FALSE);
159
160 return status;
161 }
162
163 int ar6000_htc_raw_open(AR_SOFTC_T *ar)
164 {
165 A_STATUS status;
166 int streamID, endPt, count2;
167 raw_htc_buffer *buffer;
168 HTC_SERVICE_ID servicepriority;
169
170 A_ASSERT(ar->arHtcTarget != NULL);
171
172 /* wait for target */
173 status = HTCWaitTarget(ar->arHtcTarget);
174
175 if (A_FAILED(status)) {
176 AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("HTCWaitTarget failed (%d)\n", status));
177 return -ENODEV;
178 }
179
180 for (endPt = 0; endPt < ENDPOINT_MAX; endPt++) {
181 ar->arEp2RawMapping[endPt] = HTC_RAW_STREAM_NOT_MAPPED;
182 }
183
184 for (streamID = HTC_RAW_STREAM_0; streamID < HTC_RAW_STREAM_NUM_MAX; streamI D++) {
185 /* Initialize the data structures */
186 init_MUTEX(&ar->raw_htc_read_sem[streamID]);
187 init_MUTEX(&ar->raw_htc_write_sem[streamID]);
188 init_waitqueue_head(&ar->raw_htc_read_queue[streamID]);
189 init_waitqueue_head(&ar->raw_htc_write_queue[streamID]);
190
191 /* try to connect to the raw service */
192 status = ar6000_connect_raw_service(ar,streamID);
193
194 if (A_FAILED(status)) {
195 break;
196 }
197
198 if (arRawStream2EndpointID(ar,streamID) == 0) {
199 break;
200 }
201
202 for (count2 = 0; count2 < RAW_HTC_READ_BUFFERS_NUM; count2 ++) {
203 /* Initialize the receive buffers */
204 buffer = &ar->raw_htc_write_buffer[streamID][count2];
205 memset(buffer, 0, sizeof(raw_htc_buffer));
206 buffer = &ar->raw_htc_read_buffer[streamID][count2];
207 memset(buffer, 0, sizeof(raw_htc_buffer));
208
209 SET_HTC_PACKET_INFO_RX_REFILL(&buffer->HTCPacket,
210 buffer,
211 buffer->data,
212 HTC_RAW_BUFFER_SIZE,
213 arRawStream2EndpointID(ar,streamID));
214
215 /* Queue buffers to HTC for receive */
216 if ((status = HTCAddReceivePkt(ar->arHtcTarget, &buffer->HTCPacket)) != A_OK)
217 {
218 BMIInit();
219 return -EIO;
220 }
221 }
222
223 for (count2 = 0; count2 < RAW_HTC_WRITE_BUFFERS_NUM; count2 ++) {
224 /* Initialize the receive buffers */
225 buffer = &ar->raw_htc_write_buffer[streamID][count2];
226 memset(buffer, 0, sizeof(raw_htc_buffer));
227 }
228
229 ar->read_buffer_available[streamID] = FALSE;
230 ar->write_buffer_available[streamID] = TRUE;
231 }
232
233 if (A_FAILED(status)) {
234 return -EIO;
235 }
236
237 AR_DEBUG_PRINTF(ATH_DEBUG_INFO,("HTC RAW, number of streams the target suppo rts: %d \n", streamID));
238
239 servicepriority = HTC_RAW_STREAMS_SVC; /* only 1 */
240
241 /* set callbacks and priority list */
242 HTCSetCreditDistribution(ar->arHtcTarget,
243 ar,
244 NULL, /* use default */
245 NULL, /* use default */
246 &servicepriority,
247 1);
248
249 /* Start the HTC component */
250 if ((status = HTCStart(ar->arHtcTarget)) != A_OK) {
251 BMIInit();
252 return -EIO;
253 }
254
255 (ar)->arRawIfInit = TRUE;
256
257 return 0;
258 }
259
260 int ar6000_htc_raw_close(AR_SOFTC_T *ar)
261 {
262 A_PRINTF("ar6000_htc_raw_close called \n");
263 HTCStop(ar->arHtcTarget);
264
265 /* reset the device */
266 ar6000_reset_device(ar->arHifDevice, ar->arTargetType, TRUE, FALSE);
267 /* Initialize the BMI component */
268 BMIInit();
269
270 return 0;
271 }
272
273 raw_htc_buffer *
274 get_filled_buffer(AR_SOFTC_T *ar, HTC_RAW_STREAM_ID StreamID)
275 {
276 int count;
277 raw_htc_buffer *busy;
278
279 /* Check for data */
280 for (count = 0; count < RAW_HTC_READ_BUFFERS_NUM; count ++) {
281 busy = &ar->raw_htc_read_buffer[StreamID][count];
282 if (busy->length) {
283 break;
284 }
285 }
286 if (busy->length) {
287 ar->read_buffer_available[StreamID] = TRUE;
288 } else {
289 ar->read_buffer_available[StreamID] = FALSE;
290 }
291
292 return busy;
293 }
294
295 ssize_t ar6000_htc_raw_read(AR_SOFTC_T *ar, HTC_RAW_STREAM_ID StreamID,
296 char __user *buffer, size_t length)
297 {
298 int readPtr;
299 raw_htc_buffer *busy;
300
301 if (arRawStream2EndpointID(ar,StreamID) == 0) {
302 AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("StreamID(%d) not connected! \n", StreamI D));
303 return -EFAULT;
304 }
305
306 if (down_interruptible(&ar->raw_htc_read_sem[StreamID])) {
307 return -ERESTARTSYS;
308 }
309
310 busy = get_filled_buffer(ar,StreamID);
311 while (!ar->read_buffer_available[StreamID]) {
312 up(&ar->raw_htc_read_sem[StreamID]);
313
314 /* Wait for the data */
315 AR_DEBUG_PRINTF(ATH_DEBUG_HTC_RAW,("Sleeping StreamID(%d) read process\n ", StreamID));
316 if (wait_event_interruptible(ar->raw_htc_read_queue[StreamID],
317 ar->read_buffer_available[StreamID]))
318 {
319 return -EINTR;
320 }
321 if (down_interruptible(&ar->raw_htc_read_sem[StreamID])) {
322 return -ERESTARTSYS;
323 }
324 busy = get_filled_buffer(ar,StreamID);
325 }
326
327 /* Read the data */
328 readPtr = busy->currPtr;
329 if (length > busy->length - HTC_HEADER_LEN) {
330 length = busy->length - HTC_HEADER_LEN;
331 }
332 if (copy_to_user(buffer, &busy->data[readPtr], length)) {
333 up(&ar->raw_htc_read_sem[StreamID]);
334 return -EFAULT;
335 }
336
337 busy->currPtr += length;
338
339 if (busy->currPtr == busy->length)
340 {
341 busy->currPtr = 0;
342 busy->length = 0;
343 HTC_PACKET_RESET_RX(&busy->HTCPacket);
344 //AR_DEBUG_PRINTF(ATH_DEBUG_HTC_RAW,("raw read ioctl: ep for packet:%d \n", busy->HTCPacket.Endpoint));
345 HTCAddReceivePkt(ar->arHtcTarget, &busy->HTCPacket);
346 }
347 ar->read_buffer_available[StreamID] = FALSE;
348 up(&ar->raw_htc_read_sem[StreamID]);
349
350 return length;
351 }
352
353 static raw_htc_buffer *
354 get_free_buffer(AR_SOFTC_T *ar, HTC_ENDPOINT_ID StreamID)
355 {
356 int count;
357 raw_htc_buffer *free;
358
359 free = NULL;
360 for (count = 0; count < RAW_HTC_WRITE_BUFFERS_NUM; count ++) {
361 free = &ar->raw_htc_write_buffer[StreamID][count];
362 if (free->length == 0) {
363 break;
364 }
365 }
366 if (!free->length) {
367 ar->write_buffer_available[StreamID] = TRUE;
368 } else {
369 ar->write_buffer_available[StreamID] = FALSE;
370 }
371
372 return free;
373 }
374
375 ssize_t ar6000_htc_raw_write(AR_SOFTC_T *ar, HTC_RAW_STREAM_ID StreamID,
376 char __user *buffer, size_t length)
377 {
378 int writePtr;
379 raw_htc_buffer *free;
380
381 if (arRawStream2EndpointID(ar,StreamID) == 0) {
382 AR_DEBUG_PRINTF(ATH_DEBUG_ERR,("StreamID(%d) not connected! \n", StreamI D));
383 return -EFAULT;
384 }
385
386 if (down_interruptible(&ar->raw_htc_write_sem[StreamID])) {
387 return -ERESTARTSYS;
388 }
389
390 /* Search for a free buffer */
391 free = get_free_buffer(ar,StreamID);
392
393 /* Check if there is space to write else wait */
394 while (!ar->write_buffer_available[StreamID]) {
395 up(&ar->raw_htc_write_sem[StreamID]);
396
397 /* Wait for buffer to become free */
398 AR_DEBUG_PRINTF(ATH_DEBUG_HTC_RAW,("Sleeping StreamID(%d) write process\ n", StreamID));
399 if (wait_event_interruptible(ar->raw_htc_write_queue[StreamID],
400 ar->write_buffer_available[StreamID]))
401 {
402 return -EINTR;
403 }
404 if (down_interruptible(&ar->raw_htc_write_sem[StreamID])) {
405 return -ERESTARTSYS;
406 }
407 free = get_free_buffer(ar,StreamID);
408 }
409
410 /* Send the data */
411 writePtr = HTC_HEADER_LEN;
412 if (length > (HTC_RAW_BUFFER_SIZE - HTC_HEADER_LEN)) {
413 length = HTC_RAW_BUFFER_SIZE - HTC_HEADER_LEN;
414 }
415
416 if (copy_from_user(&free->data[writePtr], buffer, length)) {
417 up(&ar->raw_htc_read_sem[StreamID]);
418 return -EFAULT;
419 }
420
421 free->length = length;
422
423 SET_HTC_PACKET_INFO_TX(&free->HTCPacket,
424 free,
425 &free->data[writePtr],
426 length,
427 arRawStream2EndpointID(ar,StreamID),
428 AR6K_DATA_PKT_TAG);
429
430 HTCSendPkt(ar->arHtcTarget,&free->HTCPacket);
431
432 ar->write_buffer_available[StreamID] = FALSE;
433 up(&ar->raw_htc_write_sem[StreamID]);
434
435 return length;
436 }
437 #endif /* HTC_RAW_INTERFACE */
OLDNEW
« no previous file with comments | « chromeos/drivers/ath6kl/os/linux/ar6000_drv.c ('k') | chromeos/drivers/ath6kl/os/linux/cfg80211.c » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698