aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/firewire
diff options
context:
space:
mode:
authorStefan Richter <stefanr@s5r6.in-berlin.de>2009-01-04 10:23:29 -0500
committerStefan Richter <stefanr@s5r6.in-berlin.de>2009-03-24 15:56:43 -0400
commit97c18b7fd6df4ae0d32509f292a2eb0d4b26d623 (patch)
treebd8f79c6577bd57a09275988e01ac7ea783f9d08 /drivers/firewire
parentfb4430367b0bbee2420132faf16c7c762a39c0bb (diff)
firewire: cdev: unify names of struct types and of their instances
to indicate that they are specializations of struct event or of struct client_resource, respectively. struct response was both an event and a client_resource; it is now split into struct outbound_transaction_resource and ~_event in order to document more explicitly which types of client resources exist. struct request and struct_request_event are renamed to struct inbound_transaction_resource and ~_event because requests and responses occur in outbound and in inbound transactions. Signed-off-by: Stefan Richter <stefanr@s5r6.in-berlin.de>
Diffstat (limited to 'drivers/firewire')
-rw-r--r--drivers/firewire/fw-cdev.c337
1 files changed, 169 insertions, 168 deletions
diff --git a/drivers/firewire/fw-cdev.c b/drivers/firewire/fw-cdev.c
index 81362c14ef44..85e866e28a27 100644
--- a/drivers/firewire/fw-cdev.c
+++ b/drivers/firewire/fw-cdev.c
@@ -41,43 +41,6 @@
41#include "fw-topology.h" 41#include "fw-topology.h"
42#include "fw-device.h" 42#include "fw-device.h"
43 43
44struct client;
45struct client_resource;
46typedef void (*client_resource_release_fn_t)(struct client *,
47 struct client_resource *);
48struct client_resource {
49 client_resource_release_fn_t release;
50 int handle;
51};
52
53/*
54 * dequeue_event() just kfree()'s the event, so the event has to be
55 * the first field in the struct.
56 */
57
58struct event {
59 struct { void *data; size_t size; } v[2];
60 struct list_head link;
61};
62
63struct bus_reset {
64 struct event event;
65 struct fw_cdev_event_bus_reset reset;
66};
67
68struct response {
69 struct event event;
70 struct fw_transaction transaction;
71 struct client *client;
72 struct client_resource resource;
73 struct fw_cdev_event_response response;
74};
75
76struct iso_interrupt {
77 struct event event;
78 struct fw_cdev_event_iso_interrupt interrupt;
79};
80
81struct client { 44struct client {
82 u32 version; 45 u32 version;
83 struct fw_device *device; 46 struct fw_device *device;
@@ -116,6 +79,70 @@ static void client_put(struct client *client)
116 kref_put(&client->kref, client_release); 79 kref_put(&client->kref, client_release);
117} 80}
118 81
82struct client_resource;
83typedef void (*client_resource_release_fn_t)(struct client *,
84 struct client_resource *);
85struct client_resource {
86 client_resource_release_fn_t release;
87 int handle;
88};
89
90struct address_handler_resource {
91 struct client_resource resource;
92 struct fw_address_handler handler;
93 __u64 closure;
94 struct client *client;
95};
96
97struct outbound_transaction_resource {
98 struct client_resource resource;
99 struct fw_transaction transaction;
100};
101
102struct inbound_transaction_resource {
103 struct client_resource resource;
104 struct fw_request *request;
105 void *data;
106 size_t length;
107};
108
109struct descriptor_resource {
110 struct client_resource resource;
111 struct fw_descriptor descriptor;
112 u32 data[0];
113};
114
115/*
116 * dequeue_event() just kfree()'s the event, so the event has to be
117 * the first field in a struct XYZ_event.
118 */
119struct event {
120 struct { void *data; size_t size; } v[2];
121 struct list_head link;
122};
123
124struct bus_reset_event {
125 struct event event;
126 struct fw_cdev_event_bus_reset reset;
127};
128
129struct outbound_transaction_event {
130 struct event event;
131 struct client *client;
132 struct outbound_transaction_resource r;
133 struct fw_cdev_event_response response;
134};
135
136struct inbound_transaction_event {
137 struct event event;
138 struct fw_cdev_event_request request;
139};
140
141struct iso_interrupt_event {
142 struct event event;
143 struct fw_cdev_event_iso_interrupt interrupt;
144};
145
119static inline void __user *u64_to_uptr(__u64 value) 146static inline void __user *u64_to_uptr(__u64 value)
120{ 147{
121 return (void __user *)(unsigned long)value; 148 return (void __user *)(unsigned long)value;
@@ -263,18 +290,18 @@ static void for_each_client(struct fw_device *device,
263 290
264static void queue_bus_reset_event(struct client *client) 291static void queue_bus_reset_event(struct client *client)
265{ 292{
266 struct bus_reset *bus_reset; 293 struct bus_reset_event *e;
267 294
268 bus_reset = kzalloc(sizeof(*bus_reset), GFP_KERNEL); 295 e = kzalloc(sizeof(*e), GFP_KERNEL);
269 if (bus_reset == NULL) { 296 if (e == NULL) {
270 fw_notify("Out of memory when allocating bus reset event\n"); 297 fw_notify("Out of memory when allocating bus reset event\n");
271 return; 298 return;
272 } 299 }
273 300
274 fill_bus_reset_event(&bus_reset->reset, client); 301 fill_bus_reset_event(&e->reset, client);
275 302
276 queue_event(client, &bus_reset->event, 303 queue_event(client, &e->event,
277 &bus_reset->reset, sizeof(bus_reset->reset), NULL, 0); 304 &e->reset, sizeof(e->reset), NULL, 0);
278} 305}
279 306
280void fw_device_cdev_update(struct fw_device *device) 307void fw_device_cdev_update(struct fw_device *device)
@@ -389,24 +416,24 @@ static int release_client_resource(struct client *client, u32 handle,
389static void release_transaction(struct client *client, 416static void release_transaction(struct client *client,
390 struct client_resource *resource) 417 struct client_resource *resource)
391{ 418{
392 struct response *response = 419 struct outbound_transaction_resource *r = container_of(resource,
393 container_of(resource, struct response, resource); 420 struct outbound_transaction_resource, resource);
394 421
395 fw_cancel_transaction(client->device->card, &response->transaction); 422 fw_cancel_transaction(client->device->card, &r->transaction);
396} 423}
397 424
398static void complete_transaction(struct fw_card *card, int rcode, 425static void complete_transaction(struct fw_card *card, int rcode,
399 void *payload, size_t length, void *data) 426 void *payload, size_t length, void *data)
400{ 427{
401 struct response *response = data; 428 struct outbound_transaction_event *e = data;
402 struct client *client = response->client; 429 struct fw_cdev_event_response *rsp = &e->response;
430 struct client *client = e->client;
403 unsigned long flags; 431 unsigned long flags;
404 struct fw_cdev_event_response *r = &response->response;
405 432
406 if (length < r->length) 433 if (length < rsp->length)
407 r->length = length; 434 rsp->length = length;
408 if (rcode == RCODE_COMPLETE) 435 if (rcode == RCODE_COMPLETE)
409 memcpy(r->data, payload, r->length); 436 memcpy(rsp->data, payload, rsp->length);
410 437
411 spin_lock_irqsave(&client->lock, flags); 438 spin_lock_irqsave(&client->lock, flags);
412 /* 439 /*
@@ -420,28 +447,28 @@ static void complete_transaction(struct fw_card *card, int rcode,
420 * by release_client_resource and we must not drop it here. 447 * by release_client_resource and we must not drop it here.
421 */ 448 */
422 if (!client->in_shutdown && 449 if (!client->in_shutdown &&
423 idr_find(&client->resource_idr, response->resource.handle)) { 450 idr_find(&client->resource_idr, e->r.resource.handle)) {
424 idr_remove(&client->resource_idr, response->resource.handle); 451 idr_remove(&client->resource_idr, e->r.resource.handle);
425 /* Drop the idr's reference */ 452 /* Drop the idr's reference */
426 client_put(client); 453 client_put(client);
427 } 454 }
428 spin_unlock_irqrestore(&client->lock, flags); 455 spin_unlock_irqrestore(&client->lock, flags);
429 456
430 r->type = FW_CDEV_EVENT_RESPONSE; 457 rsp->type = FW_CDEV_EVENT_RESPONSE;
431 r->rcode = rcode; 458 rsp->rcode = rcode;
432 459
433 /* 460 /*
434 * In the case that sizeof(*r) doesn't align with the position of the 461 * In the case that sizeof(*rsp) doesn't align with the position of the
435 * data, and the read is short, preserve an extra copy of the data 462 * data, and the read is short, preserve an extra copy of the data
436 * to stay compatible with a pre-2.6.27 bug. Since the bug is harmless 463 * to stay compatible with a pre-2.6.27 bug. Since the bug is harmless
437 * for short reads and some apps depended on it, this is both safe 464 * for short reads and some apps depended on it, this is both safe
438 * and prudent for compatibility. 465 * and prudent for compatibility.
439 */ 466 */
440 if (r->length <= sizeof(*r) - offsetof(typeof(*r), data)) 467 if (rsp->length <= sizeof(*rsp) - offsetof(typeof(*rsp), data))
441 queue_event(client, &response->event, r, sizeof(*r), 468 queue_event(client, &e->event, rsp, sizeof(*rsp),
442 r->data, r->length); 469 rsp->data, rsp->length);
443 else 470 else
444 queue_event(client, &response->event, r, sizeof(*r) + r->length, 471 queue_event(client, &e->event, rsp, sizeof(*rsp) + rsp->length,
445 NULL, 0); 472 NULL, 0);
446 473
447 /* Drop the transaction callback's reference */ 474 /* Drop the transaction callback's reference */
@@ -452,23 +479,23 @@ static int ioctl_send_request(struct client *client, void *buffer)
452{ 479{
453 struct fw_device *device = client->device; 480 struct fw_device *device = client->device;
454 struct fw_cdev_send_request *request = buffer; 481 struct fw_cdev_send_request *request = buffer;
455 struct response *response; 482 struct outbound_transaction_event *e;
456 int ret; 483 int ret;
457 484
458 /* What is the biggest size we'll accept, really? */ 485 /* What is the biggest size we'll accept, really? */
459 if (request->length > 4096) 486 if (request->length > 4096)
460 return -EINVAL; 487 return -EINVAL;
461 488
462 response = kmalloc(sizeof(*response) + request->length, GFP_KERNEL); 489 e = kmalloc(sizeof(*e) + request->length, GFP_KERNEL);
463 if (response == NULL) 490 if (e == NULL)
464 return -ENOMEM; 491 return -ENOMEM;
465 492
466 response->client = client; 493 e->client = client;
467 response->response.length = request->length; 494 e->response.length = request->length;
468 response->response.closure = request->closure; 495 e->response.closure = request->closure;
469 496
470 if (request->data && 497 if (request->data &&
471 copy_from_user(response->response.data, 498 copy_from_user(e->response.data,
472 u64_to_uptr(request->data), request->length)) { 499 u64_to_uptr(request->data), request->length)) {
473 ret = -EFAULT; 500 ret = -EFAULT;
474 goto failed; 501 goto failed;
@@ -492,86 +519,66 @@ static int ioctl_send_request(struct client *client, void *buffer)
492 goto failed; 519 goto failed;
493 } 520 }
494 521
495 response->resource.release = release_transaction; 522 e->r.resource.release = release_transaction;
496 ret = add_client_resource(client, &response->resource, GFP_KERNEL); 523 ret = add_client_resource(client, &e->r.resource, GFP_KERNEL);
497 if (ret < 0) 524 if (ret < 0)
498 goto failed; 525 goto failed;
499 526
500 /* Get a reference for the transaction callback */ 527 /* Get a reference for the transaction callback */
501 client_get(client); 528 client_get(client);
502 529
503 fw_send_request(device->card, &response->transaction, 530 fw_send_request(device->card, &e->r.transaction,
504 request->tcode & 0x1f, 531 request->tcode & 0x1f,
505 device->node->node_id, 532 device->node->node_id,
506 request->generation, 533 request->generation,
507 device->max_speed, 534 device->max_speed,
508 request->offset, 535 request->offset,
509 response->response.data, request->length, 536 e->response.data, request->length,
510 complete_transaction, response); 537 complete_transaction, e);
511 538
512 if (request->data) 539 if (request->data)
513 return sizeof(request) + request->length; 540 return sizeof(request) + request->length;
514 else 541 else
515 return sizeof(request); 542 return sizeof(request);
516 failed: 543 failed:
517 kfree(response); 544 kfree(e);
518 545
519 return ret; 546 return ret;
520} 547}
521 548
522struct address_handler {
523 struct fw_address_handler handler;
524 __u64 closure;
525 struct client *client;
526 struct client_resource resource;
527};
528
529struct request {
530 struct fw_request *request;
531 void *data;
532 size_t length;
533 struct client_resource resource;
534};
535
536struct request_event {
537 struct event event;
538 struct fw_cdev_event_request request;
539};
540
541static void release_request(struct client *client, 549static void release_request(struct client *client,
542 struct client_resource *resource) 550 struct client_resource *resource)
543{ 551{
544 struct request *request = 552 struct inbound_transaction_resource *r = container_of(resource,
545 container_of(resource, struct request, resource); 553 struct inbound_transaction_resource, resource);
546 554
547 fw_send_response(client->device->card, request->request, 555 fw_send_response(client->device->card, r->request,
548 RCODE_CONFLICT_ERROR); 556 RCODE_CONFLICT_ERROR);
549 kfree(request); 557 kfree(r);
550} 558}
551 559
552static void handle_request(struct fw_card *card, struct fw_request *r, 560static void handle_request(struct fw_card *card, struct fw_request *request,
553 int tcode, int destination, int source, 561 int tcode, int destination, int source,
554 int generation, int speed, 562 int generation, int speed,
555 unsigned long long offset, 563 unsigned long long offset,
556 void *payload, size_t length, void *callback_data) 564 void *payload, size_t length, void *callback_data)
557{ 565{
558 struct address_handler *handler = callback_data; 566 struct address_handler_resource *handler = callback_data;
559 struct request *request; 567 struct inbound_transaction_resource *r;
560 struct request_event *e; 568 struct inbound_transaction_event *e;
561 struct client *client = handler->client;
562 int ret; 569 int ret;
563 570
564 request = kmalloc(sizeof(*request), GFP_ATOMIC); 571 r = kmalloc(sizeof(*r), GFP_ATOMIC);
565 e = kmalloc(sizeof(*e), GFP_ATOMIC); 572 e = kmalloc(sizeof(*e), GFP_ATOMIC);
566 if (request == NULL || e == NULL) 573 if (r == NULL || e == NULL)
567 goto failed; 574 goto failed;
568 575
569 request->request = r; 576 r->request = request;
570 request->data = payload; 577 r->data = payload;
571 request->length = length; 578 r->length = length;
572 579
573 request->resource.release = release_request; 580 r->resource.release = release_request;
574 ret = add_client_resource(client, &request->resource, GFP_ATOMIC); 581 ret = add_client_resource(handler->client, &r->resource, GFP_ATOMIC);
575 if (ret < 0) 582 if (ret < 0)
576 goto failed; 583 goto failed;
577 584
@@ -579,61 +586,61 @@ static void handle_request(struct fw_card *card, struct fw_request *r,
579 e->request.tcode = tcode; 586 e->request.tcode = tcode;
580 e->request.offset = offset; 587 e->request.offset = offset;
581 e->request.length = length; 588 e->request.length = length;
582 e->request.handle = request->resource.handle; 589 e->request.handle = r->resource.handle;
583 e->request.closure = handler->closure; 590 e->request.closure = handler->closure;
584 591
585 queue_event(client, &e->event, 592 queue_event(handler->client, &e->event,
586 &e->request, sizeof(e->request), payload, length); 593 &e->request, sizeof(e->request), payload, length);
587 return; 594 return;
588 595
589 failed: 596 failed:
590 kfree(request); 597 kfree(r);
591 kfree(e); 598 kfree(e);
592 fw_send_response(card, r, RCODE_CONFLICT_ERROR); 599 fw_send_response(card, request, RCODE_CONFLICT_ERROR);
593} 600}
594 601
595static void release_address_handler(struct client *client, 602static void release_address_handler(struct client *client,
596 struct client_resource *resource) 603 struct client_resource *resource)
597{ 604{
598 struct address_handler *handler = 605 struct address_handler_resource *r =
599 container_of(resource, struct address_handler, resource); 606 container_of(resource, struct address_handler_resource, resource);
600 607
601 fw_core_remove_address_handler(&handler->handler); 608 fw_core_remove_address_handler(&r->handler);
602 kfree(handler); 609 kfree(r);
603} 610}
604 611
605static int ioctl_allocate(struct client *client, void *buffer) 612static int ioctl_allocate(struct client *client, void *buffer)
606{ 613{
607 struct fw_cdev_allocate *request = buffer; 614 struct fw_cdev_allocate *request = buffer;
608 struct address_handler *handler; 615 struct address_handler_resource *r;
609 struct fw_address_region region; 616 struct fw_address_region region;
610 int ret; 617 int ret;
611 618
612 handler = kmalloc(sizeof(*handler), GFP_KERNEL); 619 r = kmalloc(sizeof(*r), GFP_KERNEL);
613 if (handler == NULL) 620 if (r == NULL)
614 return -ENOMEM; 621 return -ENOMEM;
615 622
616 region.start = request->offset; 623 region.start = request->offset;
617 region.end = request->offset + request->length; 624 region.end = request->offset + request->length;
618 handler->handler.length = request->length; 625 r->handler.length = request->length;
619 handler->handler.address_callback = handle_request; 626 r->handler.address_callback = handle_request;
620 handler->handler.callback_data = handler; 627 r->handler.callback_data = r;
621 handler->closure = request->closure; 628 r->closure = request->closure;
622 handler->client = client; 629 r->client = client;
623 630
624 ret = fw_core_add_address_handler(&handler->handler, &region); 631 ret = fw_core_add_address_handler(&r->handler, &region);
625 if (ret < 0) { 632 if (ret < 0) {
626 kfree(handler); 633 kfree(r);
627 return ret; 634 return ret;
628 } 635 }
629 636
630 handler->resource.release = release_address_handler; 637 r->resource.release = release_address_handler;
631 ret = add_client_resource(client, &handler->resource, GFP_KERNEL); 638 ret = add_client_resource(client, &r->resource, GFP_KERNEL);
632 if (ret < 0) { 639 if (ret < 0) {
633 release_address_handler(client, &handler->resource); 640 release_address_handler(client, &r->resource);
634 return ret; 641 return ret;
635 } 642 }
636 request->handle = handler->resource.handle; 643 request->handle = r->resource.handle;
637 644
638 return 0; 645 return 0;
639} 646}
@@ -650,13 +657,14 @@ static int ioctl_send_response(struct client *client, void *buffer)
650{ 657{
651 struct fw_cdev_send_response *request = buffer; 658 struct fw_cdev_send_response *request = buffer;
652 struct client_resource *resource; 659 struct client_resource *resource;
653 struct request *r; 660 struct inbound_transaction_resource *r;
654 661
655 if (release_client_resource(client, request->handle, 662 if (release_client_resource(client, request->handle,
656 release_request, &resource) < 0) 663 release_request, &resource) < 0)
657 return -EINVAL; 664 return -EINVAL;
658 665
659 r = container_of(resource, struct request, resource); 666 r = container_of(resource, struct inbound_transaction_resource,
667 resource);
660 if (request->length < r->length) 668 if (request->length < r->length)
661 r->length = request->length; 669 r->length = request->length;
662 if (copy_from_user(r->data, u64_to_uptr(request->data), r->length)) 670 if (copy_from_user(r->data, u64_to_uptr(request->data), r->length))
@@ -678,62 +686,55 @@ static int ioctl_initiate_bus_reset(struct client *client, void *buffer)
678 return fw_core_initiate_bus_reset(client->device->card, short_reset); 686 return fw_core_initiate_bus_reset(client->device->card, short_reset);
679} 687}
680 688
681struct descriptor {
682 struct fw_descriptor d;
683 struct client_resource resource;
684 u32 data[0];
685};
686
687static void release_descriptor(struct client *client, 689static void release_descriptor(struct client *client,
688 struct client_resource *resource) 690 struct client_resource *resource)
689{ 691{
690 struct descriptor *descriptor = 692 struct descriptor_resource *r =
691 container_of(resource, struct descriptor, resource); 693 container_of(resource, struct descriptor_resource, resource);
692 694
693 fw_core_remove_descriptor(&descriptor->d); 695 fw_core_remove_descriptor(&r->descriptor);
694 kfree(descriptor); 696 kfree(r);
695} 697}
696 698
697static int ioctl_add_descriptor(struct client *client, void *buffer) 699static int ioctl_add_descriptor(struct client *client, void *buffer)
698{ 700{
699 struct fw_cdev_add_descriptor *request = buffer; 701 struct fw_cdev_add_descriptor *request = buffer;
700 struct descriptor *descriptor; 702 struct descriptor_resource *r;
701 int ret; 703 int ret;
702 704
703 if (request->length > 256) 705 if (request->length > 256)
704 return -EINVAL; 706 return -EINVAL;
705 707
706 descriptor = 708 r = kmalloc(sizeof(*r) + request->length * 4, GFP_KERNEL);
707 kmalloc(sizeof(*descriptor) + request->length * 4, GFP_KERNEL); 709 if (r == NULL)
708 if (descriptor == NULL)
709 return -ENOMEM; 710 return -ENOMEM;
710 711
711 if (copy_from_user(descriptor->data, 712 if (copy_from_user(r->data,
712 u64_to_uptr(request->data), request->length * 4)) { 713 u64_to_uptr(request->data), request->length * 4)) {
713 ret = -EFAULT; 714 ret = -EFAULT;
714 goto failed; 715 goto failed;
715 } 716 }
716 717
717 descriptor->d.length = request->length; 718 r->descriptor.length = request->length;
718 descriptor->d.immediate = request->immediate; 719 r->descriptor.immediate = request->immediate;
719 descriptor->d.key = request->key; 720 r->descriptor.key = request->key;
720 descriptor->d.data = descriptor->data; 721 r->descriptor.data = r->data;
721 722
722 ret = fw_core_add_descriptor(&descriptor->d); 723 ret = fw_core_add_descriptor(&r->descriptor);
723 if (ret < 0) 724 if (ret < 0)
724 goto failed; 725 goto failed;
725 726
726 descriptor->resource.release = release_descriptor; 727 r->resource.release = release_descriptor;
727 ret = add_client_resource(client, &descriptor->resource, GFP_KERNEL); 728 ret = add_client_resource(client, &r->resource, GFP_KERNEL);
728 if (ret < 0) { 729 if (ret < 0) {
729 fw_core_remove_descriptor(&descriptor->d); 730 fw_core_remove_descriptor(&r->descriptor);
730 goto failed; 731 goto failed;
731 } 732 }
732 request->handle = descriptor->resource.handle; 733 request->handle = r->resource.handle;
733 734
734 return 0; 735 return 0;
735 failed: 736 failed:
736 kfree(descriptor); 737 kfree(r);
737 738
738 return ret; 739 return ret;
739} 740}
@@ -750,19 +751,19 @@ static void iso_callback(struct fw_iso_context *context, u32 cycle,
750 size_t header_length, void *header, void *data) 751 size_t header_length, void *header, void *data)
751{ 752{
752 struct client *client = data; 753 struct client *client = data;
753 struct iso_interrupt *irq; 754 struct iso_interrupt_event *e;
754 755
755 irq = kzalloc(sizeof(*irq) + header_length, GFP_ATOMIC); 756 e = kzalloc(sizeof(*e) + header_length, GFP_ATOMIC);
756 if (irq == NULL) 757 if (e == NULL)
757 return; 758 return;
758 759
759 irq->interrupt.type = FW_CDEV_EVENT_ISO_INTERRUPT; 760 e->interrupt.type = FW_CDEV_EVENT_ISO_INTERRUPT;
760 irq->interrupt.closure = client->iso_closure; 761 e->interrupt.closure = client->iso_closure;
761 irq->interrupt.cycle = cycle; 762 e->interrupt.cycle = cycle;
762 irq->interrupt.header_length = header_length; 763 e->interrupt.header_length = header_length;
763 memcpy(irq->interrupt.header, header, header_length); 764 memcpy(e->interrupt.header, header, header_length);
764 queue_event(client, &irq->event, &irq->interrupt, 765 queue_event(client, &e->event, &e->interrupt,
765 sizeof(irq->interrupt) + header_length, NULL, 0); 766 sizeof(e->interrupt) + header_length, NULL, 0);
766} 767}
767 768
768static int ioctl_create_iso_context(struct client *client, void *buffer) 769static int ioctl_create_iso_context(struct client *client, void *buffer)