diff options
Diffstat (limited to 'drivers/net/wireless/iwlwifi/iwl-trans.h')
-rw-r--r-- | drivers/net/wireless/iwlwifi/iwl-trans.h | 95 |
1 files changed, 51 insertions, 44 deletions
diff --git a/drivers/net/wireless/iwlwifi/iwl-trans.h b/drivers/net/wireless/iwlwifi/iwl-trans.h index 0c81cbaa8088..66c54c1b404e 100644 --- a/drivers/net/wireless/iwlwifi/iwl-trans.h +++ b/drivers/net/wireless/iwlwifi/iwl-trans.h | |||
@@ -162,6 +162,8 @@ struct iwl_cmd_header { | |||
162 | 162 | ||
163 | 163 | ||
164 | #define FH_RSCSR_FRAME_SIZE_MSK 0x00003FFF /* bits 0-13 */ | 164 | #define FH_RSCSR_FRAME_SIZE_MSK 0x00003FFF /* bits 0-13 */ |
165 | #define FH_RSCSR_FRAME_INVALID 0x55550000 | ||
166 | #define FH_RSCSR_FRAME_ALIGN 0x40 | ||
165 | 167 | ||
166 | struct iwl_rx_packet { | 168 | struct iwl_rx_packet { |
167 | /* | 169 | /* |
@@ -260,27 +262,42 @@ static inline void iwl_free_resp(struct iwl_host_cmd *cmd) | |||
260 | 262 | ||
261 | struct iwl_rx_cmd_buffer { | 263 | struct iwl_rx_cmd_buffer { |
262 | struct page *_page; | 264 | struct page *_page; |
265 | int _offset; | ||
266 | bool _page_stolen; | ||
263 | }; | 267 | }; |
264 | 268 | ||
265 | static inline void *rxb_addr(struct iwl_rx_cmd_buffer *r) | 269 | static inline void *rxb_addr(struct iwl_rx_cmd_buffer *r) |
266 | { | 270 | { |
267 | return page_address(r->_page); | 271 | return (void *)((unsigned long)page_address(r->_page) + r->_offset); |
272 | } | ||
273 | |||
274 | static inline int rxb_offset(struct iwl_rx_cmd_buffer *r) | ||
275 | { | ||
276 | return r->_offset; | ||
268 | } | 277 | } |
269 | 278 | ||
270 | static inline struct page *rxb_steal_page(struct iwl_rx_cmd_buffer *r) | 279 | static inline struct page *rxb_steal_page(struct iwl_rx_cmd_buffer *r) |
271 | { | 280 | { |
272 | struct page *p = r->_page; | 281 | r->_page_stolen = true; |
273 | r->_page = NULL; | 282 | get_page(r->_page); |
274 | return p; | 283 | return r->_page; |
275 | } | 284 | } |
276 | 285 | ||
277 | #define MAX_NO_RECLAIM_CMDS 6 | 286 | #define MAX_NO_RECLAIM_CMDS 6 |
278 | 287 | ||
288 | /* | ||
289 | * Maximum number of HW queues the transport layer | ||
290 | * currently supports | ||
291 | */ | ||
292 | #define IWL_MAX_HW_QUEUES 32 | ||
293 | |||
279 | /** | 294 | /** |
280 | * struct iwl_trans_config - transport configuration | 295 | * struct iwl_trans_config - transport configuration |
281 | * | 296 | * |
282 | * @op_mode: pointer to the upper layer. | 297 | * @op_mode: pointer to the upper layer. |
283 | * Must be set before any other call. | 298 | * @queue_to_fifo: queue to FIFO mapping to set up by |
299 | * default | ||
300 | * @n_queue_to_fifo: number of queues to set up | ||
284 | * @cmd_queue: the index of the command queue. | 301 | * @cmd_queue: the index of the command queue. |
285 | * Must be set before start_fw. | 302 | * Must be set before start_fw. |
286 | * @no_reclaim_cmds: Some devices erroneously don't set the | 303 | * @no_reclaim_cmds: Some devices erroneously don't set the |
@@ -291,6 +308,9 @@ static inline struct page *rxb_steal_page(struct iwl_rx_cmd_buffer *r) | |||
291 | */ | 308 | */ |
292 | struct iwl_trans_config { | 309 | struct iwl_trans_config { |
293 | struct iwl_op_mode *op_mode; | 310 | struct iwl_op_mode *op_mode; |
311 | const u8 *queue_to_fifo; | ||
312 | u8 n_queue_to_fifo; | ||
313 | |||
294 | u8 cmd_queue; | 314 | u8 cmd_queue; |
295 | const u8 *no_reclaim_cmds; | 315 | const u8 *no_reclaim_cmds; |
296 | int n_no_reclaim_cmds; | 316 | int n_no_reclaim_cmds; |
@@ -322,8 +342,6 @@ struct iwl_trans_config { | |||
322 | * Must be atomic | 342 | * Must be atomic |
323 | * @reclaim: free packet until ssn. Returns a list of freed packets. | 343 | * @reclaim: free packet until ssn. Returns a list of freed packets. |
324 | * Must be atomic | 344 | * Must be atomic |
325 | * @tx_agg_alloc: allocate resources for a TX BA session | ||
326 | * Must be atomic | ||
327 | * @tx_agg_setup: setup a tx queue for AMPDU - will be called once the HW is | 345 | * @tx_agg_setup: setup a tx queue for AMPDU - will be called once the HW is |
328 | * ready and a successful ADDBA response has been received. | 346 | * ready and a successful ADDBA response has been received. |
329 | * May sleep | 347 | * May sleep |
@@ -346,6 +364,7 @@ struct iwl_trans_config { | |||
346 | * @configure: configure parameters required by the transport layer from | 364 | * @configure: configure parameters required by the transport layer from |
347 | * the op_mode. May be called several times before start_fw, can't be | 365 | * the op_mode. May be called several times before start_fw, can't be |
348 | * called after that. | 366 | * called after that. |
367 | * @set_pmi: set the power pmi state | ||
349 | */ | 368 | */ |
350 | struct iwl_trans_ops { | 369 | struct iwl_trans_ops { |
351 | 370 | ||
@@ -360,18 +379,13 @@ struct iwl_trans_ops { | |||
360 | int (*send_cmd)(struct iwl_trans *trans, struct iwl_host_cmd *cmd); | 379 | int (*send_cmd)(struct iwl_trans *trans, struct iwl_host_cmd *cmd); |
361 | 380 | ||
362 | int (*tx)(struct iwl_trans *trans, struct sk_buff *skb, | 381 | int (*tx)(struct iwl_trans *trans, struct sk_buff *skb, |
363 | struct iwl_device_cmd *dev_cmd, enum iwl_rxon_context_id ctx, | 382 | struct iwl_device_cmd *dev_cmd, int queue); |
364 | u8 sta_id, u8 tid); | 383 | void (*reclaim)(struct iwl_trans *trans, int queue, int ssn, |
365 | int (*reclaim)(struct iwl_trans *trans, int sta_id, int tid, | 384 | struct sk_buff_head *skbs); |
366 | int txq_id, int ssn, struct sk_buff_head *skbs); | 385 | |
367 | 386 | void (*tx_agg_setup)(struct iwl_trans *trans, int queue, int fifo, | |
368 | int (*tx_agg_disable)(struct iwl_trans *trans, | 387 | int sta_id, int tid, int frame_limit, u16 ssn); |
369 | int sta_id, int tid); | 388 | void (*tx_agg_disable)(struct iwl_trans *trans, int queue); |
370 | int (*tx_agg_alloc)(struct iwl_trans *trans, | ||
371 | int sta_id, int tid); | ||
372 | void (*tx_agg_setup)(struct iwl_trans *trans, | ||
373 | enum iwl_rxon_context_id ctx, int sta_id, int tid, | ||
374 | int frame_limit, u16 ssn); | ||
375 | 389 | ||
376 | void (*free)(struct iwl_trans *trans); | 390 | void (*free)(struct iwl_trans *trans); |
377 | 391 | ||
@@ -387,6 +401,7 @@ struct iwl_trans_ops { | |||
387 | u32 (*read32)(struct iwl_trans *trans, u32 ofs); | 401 | u32 (*read32)(struct iwl_trans *trans, u32 ofs); |
388 | void (*configure)(struct iwl_trans *trans, | 402 | void (*configure)(struct iwl_trans *trans, |
389 | const struct iwl_trans_config *trans_cfg); | 403 | const struct iwl_trans_config *trans_cfg); |
404 | void (*set_pmi)(struct iwl_trans *trans, bool state); | ||
390 | }; | 405 | }; |
391 | 406 | ||
392 | /** | 407 | /** |
@@ -507,55 +522,42 @@ static inline int iwl_trans_send_cmd(struct iwl_trans *trans, | |||
507 | } | 522 | } |
508 | 523 | ||
509 | static inline int iwl_trans_tx(struct iwl_trans *trans, struct sk_buff *skb, | 524 | static inline int iwl_trans_tx(struct iwl_trans *trans, struct sk_buff *skb, |
510 | struct iwl_device_cmd *dev_cmd, enum iwl_rxon_context_id ctx, | 525 | struct iwl_device_cmd *dev_cmd, int queue) |
511 | u8 sta_id, u8 tid) | ||
512 | { | ||
513 | if (trans->state != IWL_TRANS_FW_ALIVE) | ||
514 | IWL_ERR(trans, "%s bad state = %d", __func__, trans->state); | ||
515 | |||
516 | return trans->ops->tx(trans, skb, dev_cmd, ctx, sta_id, tid); | ||
517 | } | ||
518 | |||
519 | static inline int iwl_trans_reclaim(struct iwl_trans *trans, int sta_id, | ||
520 | int tid, int txq_id, int ssn, | ||
521 | struct sk_buff_head *skbs) | ||
522 | { | 526 | { |
523 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, | 527 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, |
524 | "%s bad state = %d", __func__, trans->state); | 528 | "%s bad state = %d", __func__, trans->state); |
525 | 529 | ||
526 | return trans->ops->reclaim(trans, sta_id, tid, txq_id, ssn, skbs); | 530 | return trans->ops->tx(trans, skb, dev_cmd, queue); |
527 | } | 531 | } |
528 | 532 | ||
529 | static inline int iwl_trans_tx_agg_disable(struct iwl_trans *trans, | 533 | static inline void iwl_trans_reclaim(struct iwl_trans *trans, int queue, |
530 | int sta_id, int tid) | 534 | int ssn, struct sk_buff_head *skbs) |
531 | { | 535 | { |
532 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, | 536 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, |
533 | "%s bad state = %d", __func__, trans->state); | 537 | "%s bad state = %d", __func__, trans->state); |
534 | 538 | ||
535 | return trans->ops->tx_agg_disable(trans, sta_id, tid); | 539 | trans->ops->reclaim(trans, queue, ssn, skbs); |
536 | } | 540 | } |
537 | 541 | ||
538 | static inline int iwl_trans_tx_agg_alloc(struct iwl_trans *trans, | 542 | static inline void iwl_trans_tx_agg_disable(struct iwl_trans *trans, int queue) |
539 | int sta_id, int tid) | ||
540 | { | 543 | { |
541 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, | 544 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, |
542 | "%s bad state = %d", __func__, trans->state); | 545 | "%s bad state = %d", __func__, trans->state); |
543 | 546 | ||
544 | return trans->ops->tx_agg_alloc(trans, sta_id, tid); | 547 | trans->ops->tx_agg_disable(trans, queue); |
545 | } | 548 | } |
546 | 549 | ||
547 | 550 | static inline void iwl_trans_tx_agg_setup(struct iwl_trans *trans, int queue, | |
548 | static inline void iwl_trans_tx_agg_setup(struct iwl_trans *trans, | 551 | int fifo, int sta_id, int tid, |
549 | enum iwl_rxon_context_id ctx, | 552 | int frame_limit, u16 ssn) |
550 | int sta_id, int tid, | ||
551 | int frame_limit, u16 ssn) | ||
552 | { | 553 | { |
553 | might_sleep(); | 554 | might_sleep(); |
554 | 555 | ||
555 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, | 556 | WARN_ONCE(trans->state != IWL_TRANS_FW_ALIVE, |
556 | "%s bad state = %d", __func__, trans->state); | 557 | "%s bad state = %d", __func__, trans->state); |
557 | 558 | ||
558 | trans->ops->tx_agg_setup(trans, ctx, sta_id, tid, frame_limit, ssn); | 559 | trans->ops->tx_agg_setup(trans, queue, fifo, sta_id, tid, |
560 | frame_limit, ssn); | ||
559 | } | 561 | } |
560 | 562 | ||
561 | static inline void iwl_trans_free(struct iwl_trans *trans) | 563 | static inline void iwl_trans_free(struct iwl_trans *trans) |
@@ -611,6 +613,11 @@ static inline u32 iwl_trans_read32(struct iwl_trans *trans, u32 ofs) | |||
611 | return trans->ops->read32(trans, ofs); | 613 | return trans->ops->read32(trans, ofs); |
612 | } | 614 | } |
613 | 615 | ||
616 | static inline void iwl_trans_set_pmi(struct iwl_trans *trans, bool state) | ||
617 | { | ||
618 | trans->ops->set_pmi(trans, state); | ||
619 | } | ||
620 | |||
614 | /***************************************************** | 621 | /***************************************************** |
615 | * Transport layers implementations + their allocation function | 622 | * Transport layers implementations + their allocation function |
616 | ******************************************************/ | 623 | ******************************************************/ |