MOXA linux-2.6.x / linux-2.6.9-uc0 from sdlinux-moxaart.tgz
[linux-2.6.9-moxart.git] / drivers / ieee1394 / raw1394.c
blobd57a000c5ddc0d23094d901611801ffa01005176
1 /*
2 * IEEE 1394 for Linux
4 * Raw interface to the bus
6 * Copyright (C) 1999, 2000 Andreas E. Bombe
7 * 2001, 2002 Manfred Weihs <weihs@ict.tuwien.ac.at>
8 * 2002 Christian Toegel <christian.toegel@gmx.at>
10 * This code is licensed under the GPL. See the file COPYING in the root
11 * directory of the kernel sources for details.
14 * Contributions:
16 * Manfred Weihs <weihs@ict.tuwien.ac.at>
17 * configuration ROM manipulation
18 * address range mapping
19 * adaptation for new (transparent) loopback mechanism
20 * sending of arbitrary async packets
21 * Christian Toegel <christian.toegel@gmx.at>
22 * address range mapping
23 * lock64 request
24 * transmit physical packet
25 * busreset notification control (switch on/off)
26 * busreset with selection of type (short/long)
27 * request_reply
30 #include <linux/kernel.h>
31 #include <linux/list.h>
32 #include <linux/string.h>
33 #include <linux/slab.h>
34 #include <linux/fs.h>
35 #include <linux/poll.h>
36 #include <linux/module.h>
37 #include <linux/init.h>
38 #include <linux/smp_lock.h>
39 #include <linux/interrupt.h>
40 #include <linux/vmalloc.h>
41 #include <linux/cdev.h>
42 #include <asm/uaccess.h>
43 #include <asm/atomic.h>
44 #include <linux/devfs_fs_kernel.h>
46 #include "csr1212.h"
47 #include "ieee1394.h"
48 #include "ieee1394_types.h"
49 #include "ieee1394_core.h"
50 #include "nodemgr.h"
51 #include "hosts.h"
52 #include "highlevel.h"
53 #include "iso.h"
54 #include "ieee1394_transactions.h"
55 #include "raw1394.h"
56 #include "raw1394-private.h"
58 #define int2ptr(x) ((void __user *)(unsigned long)x)
59 #define ptr2int(x) ((u64)(unsigned long)(void __user *)x)
61 #ifdef CONFIG_IEEE1394_VERBOSEDEBUG
62 #define RAW1394_DEBUG
63 #endif
65 #ifdef RAW1394_DEBUG
66 #define DBGMSG(fmt, args...) \
67 printk(KERN_INFO "raw1394:" fmt "\n" , ## args)
68 #else
69 #define DBGMSG(fmt, args...)
70 #endif
72 static LIST_HEAD(host_info_list);
73 static int host_count;
74 static spinlock_t host_info_lock = SPIN_LOCK_UNLOCKED;
75 static atomic_t internal_generation = ATOMIC_INIT(0);
77 static atomic_t iso_buffer_size;
78 static const int iso_buffer_max = 4 * 1024 * 1024; /* 4 MB */
80 static struct hpsb_highlevel raw1394_highlevel;
82 static int arm_read (struct hpsb_host *host, int nodeid, quadlet_t *buffer,
83 u64 addr, size_t length, u16 flags);
84 static int arm_write (struct hpsb_host *host, int nodeid, int destid,
85 quadlet_t *data, u64 addr, size_t length, u16 flags);
86 static int arm_lock (struct hpsb_host *host, int nodeid, quadlet_t *store,
87 u64 addr, quadlet_t data, quadlet_t arg, int ext_tcode, u16 flags);
88 static int arm_lock64 (struct hpsb_host *host, int nodeid, octlet_t *store,
89 u64 addr, octlet_t data, octlet_t arg, int ext_tcode, u16 flags);
90 static struct hpsb_address_ops arm_ops = {
91 .read = arm_read,
92 .write = arm_write,
93 .lock = arm_lock,
94 .lock64 = arm_lock64,
97 static void queue_complete_cb(struct pending_request *req);
99 static struct pending_request *__alloc_pending_request(int flags)
101 struct pending_request *req;
103 req = (struct pending_request *)kmalloc(sizeof(struct pending_request),
104 flags);
105 if (req != NULL) {
106 memset(req, 0, sizeof(struct pending_request));
107 INIT_LIST_HEAD(&req->list);
110 return req;
113 static inline struct pending_request *alloc_pending_request(void)
115 return __alloc_pending_request(SLAB_KERNEL);
118 static void free_pending_request(struct pending_request *req)
120 if (req->ibs) {
121 if (atomic_dec_and_test(&req->ibs->refcount)) {
122 atomic_sub(req->ibs->data_size, &iso_buffer_size);
123 kfree(req->ibs);
125 } else if (req->free_data) {
126 kfree(req->data);
128 hpsb_free_packet(req->packet);
129 kfree(req);
132 /* fi->reqlists_lock must be taken */
133 static void __queue_complete_req(struct pending_request *req)
135 struct file_info *fi = req->file_info;
136 list_del(&req->list);
137 list_add_tail(&req->list, &fi->req_complete);
139 up(&fi->complete_sem);
140 wake_up_interruptible(&fi->poll_wait_complete);
143 static void queue_complete_req(struct pending_request *req)
145 unsigned long flags;
146 struct file_info *fi = req->file_info;
148 spin_lock_irqsave(&fi->reqlists_lock, flags);
149 __queue_complete_req(req);
150 spin_unlock_irqrestore(&fi->reqlists_lock, flags);
153 static void queue_complete_cb(struct pending_request *req)
155 struct hpsb_packet *packet = req->packet;
156 int rcode = (packet->header[1] >> 12) & 0xf;
158 switch (packet->ack_code) {
159 case ACKX_NONE:
160 case ACKX_SEND_ERROR:
161 req->req.error = RAW1394_ERROR_SEND_ERROR;
162 break;
163 case ACKX_ABORTED:
164 req->req.error = RAW1394_ERROR_ABORTED;
165 break;
166 case ACKX_TIMEOUT:
167 req->req.error = RAW1394_ERROR_TIMEOUT;
168 break;
169 default:
170 req->req.error = (packet->ack_code << 16) | rcode;
171 break;
174 if (!((packet->ack_code == ACK_PENDING) && (rcode == RCODE_COMPLETE))) {
175 req->req.length = 0;
178 if ((req->req.type == RAW1394_REQ_ASYNC_READ) ||
179 (req->req.type == RAW1394_REQ_ASYNC_WRITE) ||
180 (req->req.type == RAW1394_REQ_ASYNC_STREAM) ||
181 (req->req.type == RAW1394_REQ_LOCK) ||
182 (req->req.type == RAW1394_REQ_LOCK64))
183 hpsb_free_tlabel(packet);
185 queue_complete_req(req);
189 static void add_host(struct hpsb_host *host)
191 struct host_info *hi;
192 unsigned long flags;
194 hi = (struct host_info *)kmalloc(sizeof(struct host_info), GFP_KERNEL);
196 if (hi != NULL) {
197 INIT_LIST_HEAD(&hi->list);
198 hi->host = host;
199 INIT_LIST_HEAD(&hi->file_info_list);
201 spin_lock_irqsave(&host_info_lock, flags);
202 list_add_tail(&hi->list, &host_info_list);
203 host_count++;
204 spin_unlock_irqrestore(&host_info_lock, flags);
207 atomic_inc(&internal_generation);
211 static struct host_info *find_host_info(struct hpsb_host *host)
213 struct host_info *hi;
215 list_for_each_entry(hi, &host_info_list, list)
216 if (hi->host == host)
217 return hi;
219 return NULL;
222 static void remove_host(struct hpsb_host *host)
224 struct host_info *hi;
225 unsigned long flags;
227 spin_lock_irqsave(&host_info_lock, flags);
228 hi = find_host_info(host);
230 if (hi != NULL) {
231 list_del(&hi->list);
232 host_count--;
234 FIXME: address ranges should be removed
235 and fileinfo states should be initialized
236 (including setting generation to
237 internal-generation ...)
240 spin_unlock_irqrestore(&host_info_lock, flags);
242 if (hi == NULL) {
243 printk(KERN_ERR "raw1394: attempt to remove unknown host "
244 "0x%p\n", host);
245 return;
248 kfree(hi);
250 atomic_inc(&internal_generation);
253 static void host_reset(struct hpsb_host *host)
255 unsigned long flags;
256 struct host_info *hi;
257 struct file_info *fi;
258 struct pending_request *req;
260 spin_lock_irqsave(&host_info_lock, flags);
261 hi = find_host_info(host);
263 if (hi != NULL) {
264 list_for_each_entry(fi, &hi->file_info_list, list) {
265 if (fi->notification == RAW1394_NOTIFY_ON) {
266 req = __alloc_pending_request(SLAB_ATOMIC);
268 if (req != NULL) {
269 req->file_info = fi;
270 req->req.type = RAW1394_REQ_BUS_RESET;
271 req->req.generation = get_hpsb_generation(host);
272 req->req.misc = (host->node_id << 16)
273 | host->node_count;
274 if (fi->protocol_version > 3) {
275 req->req.misc |= (NODEID_TO_NODE(host->irm_id)
276 << 8);
279 queue_complete_req(req);
284 spin_unlock_irqrestore(&host_info_lock, flags);
287 static void iso_receive(struct hpsb_host *host, int channel, quadlet_t *data,
288 size_t length)
290 unsigned long flags;
291 struct host_info *hi;
292 struct file_info *fi;
293 struct pending_request *req, *req_next;
294 struct iso_block_store *ibs = NULL;
295 LIST_HEAD(reqs);
297 if ((atomic_read(&iso_buffer_size) + length) > iso_buffer_max) {
298 HPSB_INFO("dropped iso packet");
299 return;
302 spin_lock_irqsave(&host_info_lock, flags);
303 hi = find_host_info(host);
305 if (hi != NULL) {
306 list_for_each_entry(fi, &hi->file_info_list, list) {
307 if (!(fi->listen_channels & (1ULL << channel)))
308 continue;
310 req = __alloc_pending_request(SLAB_ATOMIC);
311 if (!req) break;
313 if (!ibs) {
314 ibs = kmalloc(sizeof(struct iso_block_store)
315 + length, SLAB_ATOMIC);
316 if (!ibs) {
317 kfree(req);
318 break;
321 atomic_add(length, &iso_buffer_size);
322 atomic_set(&ibs->refcount, 0);
323 ibs->data_size = length;
324 memcpy(ibs->data, data, length);
327 atomic_inc(&ibs->refcount);
329 req->file_info = fi;
330 req->ibs = ibs;
331 req->data = ibs->data;
332 req->req.type = RAW1394_REQ_ISO_RECEIVE;
333 req->req.generation = get_hpsb_generation(host);
334 req->req.misc = 0;
335 req->req.recvb = ptr2int(fi->iso_buffer);
336 req->req.length = min(length, fi->iso_buffer_length);
338 list_add_tail(&req->list, &reqs);
341 spin_unlock_irqrestore(&host_info_lock, flags);
343 list_for_each_entry_safe(req, req_next, &reqs, list)
344 queue_complete_req(req);
347 static void fcp_request(struct hpsb_host *host, int nodeid, int direction,
348 int cts, u8 *data, size_t length)
350 unsigned long flags;
351 struct host_info *hi;
352 struct file_info *fi;
353 struct pending_request *req, *req_next;
354 struct iso_block_store *ibs = NULL;
355 LIST_HEAD(reqs);
357 if ((atomic_read(&iso_buffer_size) + length) > iso_buffer_max) {
358 HPSB_INFO("dropped fcp request");
359 return;
362 spin_lock_irqsave(&host_info_lock, flags);
363 hi = find_host_info(host);
365 if (hi != NULL) {
366 list_for_each_entry(fi, &hi->file_info_list, list) {
367 if (!fi->fcp_buffer)
368 continue;
370 req = __alloc_pending_request(SLAB_ATOMIC);
371 if (!req) break;
373 if (!ibs) {
374 ibs = kmalloc(sizeof(struct iso_block_store)
375 + length, SLAB_ATOMIC);
376 if (!ibs) {
377 kfree(req);
378 break;
381 atomic_add(length, &iso_buffer_size);
382 atomic_set(&ibs->refcount, 0);
383 ibs->data_size = length;
384 memcpy(ibs->data, data, length);
387 atomic_inc(&ibs->refcount);
389 req->file_info = fi;
390 req->ibs = ibs;
391 req->data = ibs->data;
392 req->req.type = RAW1394_REQ_FCP_REQUEST;
393 req->req.generation = get_hpsb_generation(host);
394 req->req.misc = nodeid | (direction << 16);
395 req->req.recvb = ptr2int(fi->fcp_buffer);
396 req->req.length = length;
398 list_add_tail(&req->list, &reqs);
401 spin_unlock_irqrestore(&host_info_lock, flags);
403 list_for_each_entry_safe(req, req_next, &reqs, list)
404 queue_complete_req(req);
408 static ssize_t raw1394_read(struct file *file, char __user *buffer, size_t count,
409 loff_t *offset_is_ignored)
411 struct file_info *fi = (struct file_info *)file->private_data;
412 struct list_head *lh;
413 struct pending_request *req;
415 if (count != sizeof(struct raw1394_request)) {
416 return -EINVAL;
419 if (!access_ok(VERIFY_WRITE, buffer, count)) {
420 return -EFAULT;
423 if (file->f_flags & O_NONBLOCK) {
424 if (down_trylock(&fi->complete_sem)) {
425 return -EAGAIN;
427 } else {
428 if (down_interruptible(&fi->complete_sem)) {
429 return -ERESTARTSYS;
433 spin_lock_irq(&fi->reqlists_lock);
434 lh = fi->req_complete.next;
435 list_del(lh);
436 spin_unlock_irq(&fi->reqlists_lock);
438 req = list_entry(lh, struct pending_request, list);
440 if (req->req.length) {
441 if (copy_to_user(int2ptr(req->req.recvb), req->data,
442 req->req.length)) {
443 req->req.error = RAW1394_ERROR_MEMFAULT;
446 __copy_to_user(buffer, &req->req, sizeof(req->req));
448 free_pending_request(req);
449 return sizeof(struct raw1394_request);
453 static int state_opened(struct file_info *fi, struct pending_request *req)
455 if (req->req.type == RAW1394_REQ_INITIALIZE) {
456 switch (req->req.misc) {
457 case RAW1394_KERNELAPI_VERSION:
458 case 3:
459 fi->state = initialized;
460 fi->protocol_version = req->req.misc;
461 req->req.error = RAW1394_ERROR_NONE;
462 req->req.generation = atomic_read(&internal_generation);
463 break;
465 default:
466 req->req.error = RAW1394_ERROR_COMPAT;
467 req->req.misc = RAW1394_KERNELAPI_VERSION;
469 } else {
470 req->req.error = RAW1394_ERROR_STATE_ORDER;
473 req->req.length = 0;
474 queue_complete_req(req);
475 return sizeof(struct raw1394_request);
478 static int state_initialized(struct file_info *fi, struct pending_request *req)
480 struct host_info *hi;
481 struct raw1394_khost_list *khl;
483 if (req->req.generation != atomic_read(&internal_generation)) {
484 req->req.error = RAW1394_ERROR_GENERATION;
485 req->req.generation = atomic_read(&internal_generation);
486 req->req.length = 0;
487 queue_complete_req(req);
488 return sizeof(struct raw1394_request);
491 switch (req->req.type) {
492 case RAW1394_REQ_LIST_CARDS:
493 spin_lock_irq(&host_info_lock);
494 khl = kmalloc(sizeof(struct raw1394_khost_list) * host_count,
495 SLAB_ATOMIC);
497 if (khl != NULL) {
498 req->req.misc = host_count;
499 req->data = (quadlet_t *)khl;
501 list_for_each_entry(hi, &host_info_list, list) {
502 khl->nodes = hi->host->node_count;
503 strcpy(khl->name, hi->host->driver->name);
504 khl++;
507 spin_unlock_irq(&host_info_lock);
509 if (khl != NULL) {
510 req->req.error = RAW1394_ERROR_NONE;
511 req->req.length = min(req->req.length,
512 (u32)(sizeof(struct raw1394_khost_list)
513 * req->req.misc));
514 req->free_data = 1;
515 } else {
516 return -ENOMEM;
518 break;
520 case RAW1394_REQ_SET_CARD:
521 spin_lock_irq(&host_info_lock);
522 if (req->req.misc < host_count) {
523 list_for_each_entry(hi, &host_info_list, list) {
524 if (!req->req.misc--)
525 break;
527 get_device(&hi->host->device); // XXX Need to handle failure case
528 list_add_tail(&fi->list, &hi->file_info_list);
529 fi->host = hi->host;
530 fi->state = connected;
532 req->req.error = RAW1394_ERROR_NONE;
533 req->req.generation = get_hpsb_generation(fi->host);
534 req->req.misc = (fi->host->node_id << 16)
535 | fi->host->node_count;
536 if (fi->protocol_version > 3) {
537 req->req.misc |= NODEID_TO_NODE(fi->host->irm_id) << 8;
539 } else {
540 req->req.error = RAW1394_ERROR_INVALID_ARG;
542 spin_unlock_irq(&host_info_lock);
544 req->req.length = 0;
545 break;
547 default:
548 req->req.error = RAW1394_ERROR_STATE_ORDER;
549 req->req.length = 0;
550 break;
553 queue_complete_req(req);
554 return sizeof(struct raw1394_request);
557 static void handle_iso_listen(struct file_info *fi, struct pending_request *req)
559 int channel = req->req.misc;
561 spin_lock_irq(&host_info_lock);
562 if ((channel > 63) || (channel < -64)) {
563 req->req.error = RAW1394_ERROR_INVALID_ARG;
564 } else if (channel >= 0) {
565 /* allocate channel req.misc */
566 if (fi->listen_channels & (1ULL << channel)) {
567 req->req.error = RAW1394_ERROR_ALREADY;
568 } else {
569 if (hpsb_listen_channel(&raw1394_highlevel, fi->host, channel)) {
570 req->req.error = RAW1394_ERROR_ALREADY;
571 } else {
572 fi->listen_channels |= 1ULL << channel;
573 fi->iso_buffer = int2ptr(req->req.recvb);
574 fi->iso_buffer_length = req->req.length;
577 } else {
578 /* deallocate channel (one's complement neg) req.misc */
579 channel = ~channel;
581 if (fi->listen_channels & (1ULL << channel)) {
582 hpsb_unlisten_channel(&raw1394_highlevel, fi->host, channel);
583 fi->listen_channels &= ~(1ULL << channel);
584 } else {
585 req->req.error = RAW1394_ERROR_INVALID_ARG;
589 req->req.length = 0;
590 queue_complete_req(req);
591 spin_unlock_irq(&host_info_lock);
594 static void handle_fcp_listen(struct file_info *fi, struct pending_request *req)
596 if (req->req.misc) {
597 if (fi->fcp_buffer) {
598 req->req.error = RAW1394_ERROR_ALREADY;
599 } else {
600 fi->fcp_buffer = int2ptr(req->req.recvb);
602 } else {
603 if (!fi->fcp_buffer) {
604 req->req.error = RAW1394_ERROR_ALREADY;
605 } else {
606 fi->fcp_buffer = NULL;
610 req->req.length = 0;
611 queue_complete_req(req);
615 static int handle_async_request(struct file_info *fi,
616 struct pending_request *req, int node)
618 struct hpsb_packet *packet = NULL;
619 u64 addr = req->req.address & 0xffffffffffffULL;
621 switch (req->req.type) {
622 case RAW1394_REQ_ASYNC_READ:
623 DBGMSG("read_request called");
624 packet = hpsb_make_readpacket(fi->host, node, addr, req->req.length);
626 if (!packet)
627 return -ENOMEM;
629 if (req->req.length == 4)
630 req->data = &packet->header[3];
631 else
632 req->data = packet->data;
634 break;
636 case RAW1394_REQ_ASYNC_WRITE:
637 DBGMSG("write_request called");
639 packet = hpsb_make_writepacket(fi->host, node, addr, NULL,
640 req->req.length);
641 if (!packet)
642 return -ENOMEM;
644 if (req->req.length == 4) {
645 if (copy_from_user(&packet->header[3], int2ptr(req->req.sendb),
646 req->req.length))
647 req->req.error = RAW1394_ERROR_MEMFAULT;
648 } else {
649 if (copy_from_user(packet->data, int2ptr(req->req.sendb),
650 req->req.length))
651 req->req.error = RAW1394_ERROR_MEMFAULT;
654 req->req.length = 0;
655 break;
657 case RAW1394_REQ_ASYNC_STREAM:
658 DBGMSG("stream_request called");
660 packet = hpsb_make_streampacket(fi->host, NULL, req->req.length, node & 0x3f/*channel*/,
661 (req->req.misc >> 16) & 0x3, req->req.misc & 0xf);
662 if (!packet)
663 return -ENOMEM;
665 if (copy_from_user(packet->data, int2ptr(req->req.sendb),
666 req->req.length))
667 req->req.error = RAW1394_ERROR_MEMFAULT;
669 req->req.length = 0;
670 break;
672 case RAW1394_REQ_LOCK:
673 DBGMSG("lock_request called");
674 if ((req->req.misc == EXTCODE_FETCH_ADD)
675 || (req->req.misc == EXTCODE_LITTLE_ADD)) {
676 if (req->req.length != 4) {
677 req->req.error = RAW1394_ERROR_INVALID_ARG;
678 break;
680 } else {
681 if (req->req.length != 8) {
682 req->req.error = RAW1394_ERROR_INVALID_ARG;
683 break;
687 packet = hpsb_make_lockpacket(fi->host, node, addr,
688 req->req.misc, NULL, 0);
689 if (!packet) return -ENOMEM;
691 if (copy_from_user(packet->data, int2ptr(req->req.sendb),
692 req->req.length)) {
693 req->req.error = RAW1394_ERROR_MEMFAULT;
694 break;
697 req->data = packet->data;
698 req->req.length = 4;
699 break;
701 case RAW1394_REQ_LOCK64:
702 DBGMSG("lock64_request called");
703 if ((req->req.misc == EXTCODE_FETCH_ADD)
704 || (req->req.misc == EXTCODE_LITTLE_ADD)) {
705 if (req->req.length != 8) {
706 req->req.error = RAW1394_ERROR_INVALID_ARG;
707 break;
709 } else {
710 if (req->req.length != 16) {
711 req->req.error = RAW1394_ERROR_INVALID_ARG;
712 break;
715 packet = hpsb_make_lock64packet(fi->host, node, addr,
716 req->req.misc, NULL, 0);
717 if (!packet) return -ENOMEM;
719 if (copy_from_user(packet->data, int2ptr(req->req.sendb),
720 req->req.length)) {
721 req->req.error = RAW1394_ERROR_MEMFAULT;
722 break;
725 req->data = packet->data;
726 req->req.length = 8;
727 break;
729 default:
730 req->req.error = RAW1394_ERROR_STATE_ORDER;
733 req->packet = packet;
735 if (req->req.error) {
736 req->req.length = 0;
737 queue_complete_req(req);
738 return sizeof(struct raw1394_request);
741 hpsb_set_packet_complete_task(packet, (void(*)(void*))queue_complete_cb, req);
743 spin_lock_irq(&fi->reqlists_lock);
744 list_add_tail(&req->list, &fi->req_pending);
745 spin_unlock_irq(&fi->reqlists_lock);
747 packet->generation = req->req.generation;
749 if (hpsb_send_packet(packet) < 0) {
750 req->req.error = RAW1394_ERROR_SEND_ERROR;
751 req->req.length = 0;
752 hpsb_free_tlabel(packet);
753 queue_complete_req(req);
755 return sizeof(struct raw1394_request);
758 static int handle_iso_send(struct file_info *fi, struct pending_request *req,
759 int channel)
761 struct hpsb_packet *packet;
763 packet = hpsb_make_isopacket(fi->host, req->req.length, channel & 0x3f,
764 (req->req.misc >> 16) & 0x3, req->req.misc & 0xf);
765 if (!packet)
766 return -ENOMEM;
768 packet->speed_code = req->req.address & 0x3;
770 req->packet = packet;
772 if (copy_from_user(packet->data, int2ptr(req->req.sendb),
773 req->req.length)) {
774 req->req.error = RAW1394_ERROR_MEMFAULT;
775 req->req.length = 0;
776 queue_complete_req(req);
777 return sizeof(struct raw1394_request);
780 req->req.length = 0;
781 hpsb_set_packet_complete_task(packet, (void (*)(void*))queue_complete_req, req);
783 spin_lock_irq(&fi->reqlists_lock);
784 list_add_tail(&req->list, &fi->req_pending);
785 spin_unlock_irq(&fi->reqlists_lock);
787 /* Update the generation of the packet just before sending. */
788 packet->generation = req->req.generation;
790 if (hpsb_send_packet(packet) < 0) {
791 req->req.error = RAW1394_ERROR_SEND_ERROR;
792 queue_complete_req(req);
795 return sizeof(struct raw1394_request);
798 static int handle_async_send(struct file_info *fi, struct pending_request *req)
800 struct hpsb_packet *packet;
801 int header_length = req->req.misc & 0xffff;
802 int expect_response = req->req.misc >> 16;
804 if ((header_length > req->req.length) ||
805 (header_length < 12)) {
806 req->req.error = RAW1394_ERROR_INVALID_ARG;
807 req->req.length = 0;
808 queue_complete_req(req);
809 return sizeof(struct raw1394_request);
812 packet = hpsb_alloc_packet(req->req.length-header_length);
813 req->packet = packet;
814 if (!packet) return -ENOMEM;
816 if (copy_from_user(packet->header, int2ptr(req->req.sendb),
817 header_length)) {
818 req->req.error = RAW1394_ERROR_MEMFAULT;
819 req->req.length = 0;
820 queue_complete_req(req);
821 return sizeof(struct raw1394_request);
824 if (copy_from_user(packet->data, int2ptr(req->req.sendb) + header_length,
825 packet->data_size)) {
826 req->req.error = RAW1394_ERROR_MEMFAULT;
827 req->req.length = 0;
828 queue_complete_req(req);
829 return sizeof(struct raw1394_request);
832 packet->type = hpsb_async;
833 packet->node_id = packet->header[0] >> 16;
834 packet->tcode = (packet->header[0] >> 4) & 0xf;
835 packet->tlabel = (packet->header[0] >> 10) &0x3f;
836 packet->host = fi->host;
837 packet->expect_response = expect_response;
838 packet->header_size=header_length;
839 packet->data_size=req->req.length-header_length;
841 req->req.length = 0;
842 hpsb_set_packet_complete_task(packet, (void(*)(void*))queue_complete_cb, req);
844 spin_lock_irq(&fi->reqlists_lock);
845 list_add_tail(&req->list, &fi->req_pending);
846 spin_unlock_irq(&fi->reqlists_lock);
848 /* Update the generation of the packet just before sending. */
849 packet->generation = req->req.generation;
851 if (hpsb_send_packet(packet) < 0) {
852 req->req.error = RAW1394_ERROR_SEND_ERROR;
853 queue_complete_req(req);
856 return sizeof(struct raw1394_request);
859 static int arm_read (struct hpsb_host *host, int nodeid, quadlet_t *buffer,
860 u64 addr, size_t length, u16 flags)
862 struct pending_request *req;
863 struct host_info *hi;
864 struct file_info *fi = NULL;
865 struct list_head *entry;
866 struct arm_addr *arm_addr = NULL;
867 struct arm_request *arm_req = NULL;
868 struct arm_response *arm_resp = NULL;
869 int found=0, size=0, rcode=-1;
870 struct arm_request_response *arm_req_resp = NULL;
872 DBGMSG("arm_read called by node: %X"
873 "addr: %4.4x %8.8x length: %Zu", nodeid,
874 (u16) ((addr >>32) & 0xFFFF), (u32) (addr & 0xFFFFFFFF),
875 length);
876 spin_lock(&host_info_lock);
877 hi = find_host_info(host); /* search address-entry */
878 if (hi != NULL) {
879 list_for_each_entry(fi, &hi->file_info_list, list) {
880 entry = fi->addr_list.next;
881 while (entry != &(fi->addr_list)) {
882 arm_addr = list_entry(entry, struct arm_addr, addr_list);
883 if (((arm_addr->start) <= (addr)) &&
884 ((arm_addr->end) >= (addr+length))) {
885 found = 1;
886 break;
888 entry = entry->next;
890 if (found) {
891 break;
895 rcode = -1;
896 if (!found) {
897 printk(KERN_ERR "raw1394: arm_read FAILED addr_entry not found"
898 " -> rcode_address_error\n");
899 spin_unlock(&host_info_lock);
900 return (RCODE_ADDRESS_ERROR);
901 } else {
902 DBGMSG("arm_read addr_entry FOUND");
904 if (arm_addr->rec_length < length) {
905 DBGMSG("arm_read blocklength too big -> rcode_data_error");
906 rcode = RCODE_DATA_ERROR; /* hardware error, data is unavailable */
908 if (rcode == -1) {
909 if (arm_addr->access_rights & ARM_READ) {
910 if (!(arm_addr->client_transactions & ARM_READ)) {
911 memcpy(buffer,(arm_addr->addr_space_buffer)+(addr-(arm_addr->start)),
912 length);
913 DBGMSG("arm_read -> (rcode_complete)");
914 rcode = RCODE_COMPLETE;
916 } else {
917 rcode = RCODE_TYPE_ERROR; /* function not allowed */
918 DBGMSG("arm_read -> rcode_type_error (access denied)");
921 if (arm_addr->notification_options & ARM_READ) {
922 DBGMSG("arm_read -> entering notification-section");
923 req = __alloc_pending_request(SLAB_ATOMIC);
924 if (!req) {
925 DBGMSG("arm_read -> rcode_conflict_error");
926 spin_unlock(&host_info_lock);
927 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
928 The request may be retried */
930 if (rcode == RCODE_COMPLETE) {
931 size = sizeof(struct arm_request)+sizeof(struct arm_response) +
932 length * sizeof(byte_t) +
933 sizeof (struct arm_request_response);
934 } else {
935 size = sizeof(struct arm_request)+sizeof(struct arm_response) +
936 sizeof (struct arm_request_response);
938 req->data = kmalloc(size, SLAB_ATOMIC);
939 if (!(req->data)) {
940 free_pending_request(req);
941 DBGMSG("arm_read -> rcode_conflict_error");
942 spin_unlock(&host_info_lock);
943 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
944 The request may be retried */
946 req->free_data=1;
947 req->file_info = fi;
948 req->req.type = RAW1394_REQ_ARM;
949 req->req.generation = get_hpsb_generation(host);
950 req->req.misc = ( ((length << 16) & (0xFFFF0000)) | (ARM_READ & 0xFF));
951 req->req.tag = arm_addr->arm_tag;
952 req->req.recvb = arm_addr->recvb;
953 req->req.length = size;
954 arm_req_resp = (struct arm_request_response *) (req->data);
955 arm_req = (struct arm_request *) ((byte_t *)(req->data) +
956 (sizeof (struct arm_request_response)));
957 arm_resp = (struct arm_response *) ((byte_t *)(arm_req) +
958 (sizeof(struct arm_request)));
959 arm_req->buffer = NULL;
960 arm_resp->buffer = NULL;
961 if (rcode == RCODE_COMPLETE) {
962 byte_t *buf = (byte_t *)arm_resp + sizeof(struct arm_response);
963 memcpy (buf,
964 (arm_addr->addr_space_buffer)+(addr-(arm_addr->start)),
965 length);
966 arm_resp->buffer = int2ptr((arm_addr->recvb) +
967 sizeof (struct arm_request_response) +
968 sizeof (struct arm_request) +
969 sizeof (struct arm_response));
971 arm_resp->buffer_length = (rcode == RCODE_COMPLETE) ? length : 0;
972 arm_resp->response_code = rcode;
973 arm_req->buffer_length = 0;
974 arm_req->generation = req->req.generation;
975 arm_req->extended_transaction_code = 0;
976 arm_req->destination_offset = addr;
977 arm_req->source_nodeid = nodeid;
978 arm_req->destination_nodeid = host->node_id;
979 arm_req->tlabel = (flags >> 10) & 0x3f;
980 arm_req->tcode = (flags >> 4) & 0x0f;
981 arm_req_resp->request = int2ptr((arm_addr->recvb) +
982 sizeof (struct arm_request_response));
983 arm_req_resp->response = int2ptr((arm_addr->recvb) +
984 sizeof (struct arm_request_response) +
985 sizeof (struct arm_request));
986 queue_complete_req(req);
988 spin_unlock(&host_info_lock);
989 return(rcode);
992 static int arm_write (struct hpsb_host *host, int nodeid, int destid,
993 quadlet_t *data, u64 addr, size_t length, u16 flags)
995 struct pending_request *req;
996 struct host_info *hi;
997 struct file_info *fi = NULL;
998 struct list_head *entry;
999 struct arm_addr *arm_addr = NULL;
1000 struct arm_request *arm_req = NULL;
1001 struct arm_response *arm_resp = NULL;
1002 int found=0, size=0, rcode=-1, length_conflict=0;
1003 struct arm_request_response *arm_req_resp = NULL;
1005 DBGMSG("arm_write called by node: %X"
1006 "addr: %4.4x %8.8x length: %Zu", nodeid,
1007 (u16) ((addr >>32) & 0xFFFF), (u32) (addr & 0xFFFFFFFF),
1008 length);
1009 spin_lock(&host_info_lock);
1010 hi = find_host_info(host); /* search address-entry */
1011 if (hi != NULL) {
1012 list_for_each_entry(fi, &hi->file_info_list, list) {
1013 entry = fi->addr_list.next;
1014 while (entry != &(fi->addr_list)) {
1015 arm_addr = list_entry(entry, struct arm_addr, addr_list);
1016 if (((arm_addr->start) <= (addr)) &&
1017 ((arm_addr->end) >= (addr+length))) {
1018 found = 1;
1019 break;
1021 entry = entry->next;
1023 if (found) {
1024 break;
1028 rcode = -1;
1029 if (!found) {
1030 printk(KERN_ERR "raw1394: arm_write FAILED addr_entry not found"
1031 " -> rcode_address_error\n");
1032 spin_unlock(&host_info_lock);
1033 return (RCODE_ADDRESS_ERROR);
1034 } else {
1035 DBGMSG("arm_write addr_entry FOUND");
1037 if (arm_addr->rec_length < length) {
1038 DBGMSG("arm_write blocklength too big -> rcode_data_error");
1039 length_conflict = 1;
1040 rcode = RCODE_DATA_ERROR; /* hardware error, data is unavailable */
1042 if (rcode == -1) {
1043 if (arm_addr->access_rights & ARM_WRITE) {
1044 if (!(arm_addr->client_transactions & ARM_WRITE)) {
1045 memcpy((arm_addr->addr_space_buffer)+(addr-(arm_addr->start)),
1046 data, length);
1047 DBGMSG("arm_write -> (rcode_complete)");
1048 rcode = RCODE_COMPLETE;
1050 } else {
1051 rcode = RCODE_TYPE_ERROR; /* function not allowed */
1052 DBGMSG("arm_write -> rcode_type_error (access denied)");
1055 if (arm_addr->notification_options & ARM_WRITE) {
1056 DBGMSG("arm_write -> entering notification-section");
1057 req = __alloc_pending_request(SLAB_ATOMIC);
1058 if (!req) {
1059 DBGMSG("arm_write -> rcode_conflict_error");
1060 spin_unlock(&host_info_lock);
1061 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
1062 The request my be retried */
1064 size = sizeof(struct arm_request)+sizeof(struct arm_response) +
1065 (length) * sizeof(byte_t) +
1066 sizeof (struct arm_request_response);
1067 req->data = kmalloc(size, SLAB_ATOMIC);
1068 if (!(req->data)) {
1069 free_pending_request(req);
1070 DBGMSG("arm_write -> rcode_conflict_error");
1071 spin_unlock(&host_info_lock);
1072 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
1073 The request may be retried */
1075 req->free_data=1;
1076 req->file_info = fi;
1077 req->req.type = RAW1394_REQ_ARM;
1078 req->req.generation = get_hpsb_generation(host);
1079 req->req.misc = ( ((length << 16) & (0xFFFF0000)) | (ARM_WRITE & 0xFF));
1080 req->req.tag = arm_addr->arm_tag;
1081 req->req.recvb = arm_addr->recvb;
1082 req->req.length = size;
1083 arm_req_resp = (struct arm_request_response *) (req->data);
1084 arm_req = (struct arm_request *) ((byte_t *)(req->data) +
1085 (sizeof (struct arm_request_response)));
1086 arm_resp = (struct arm_response *) ((byte_t *)(arm_req) +
1087 (sizeof(struct arm_request)));
1088 arm_resp->buffer = NULL;
1089 memcpy ((byte_t *)arm_resp + sizeof(struct arm_response),
1090 data, length);
1091 arm_req->buffer = int2ptr((arm_addr->recvb) +
1092 sizeof (struct arm_request_response) +
1093 sizeof (struct arm_request) +
1094 sizeof (struct arm_response));
1095 arm_req->buffer_length = length;
1096 arm_req->generation = req->req.generation;
1097 arm_req->extended_transaction_code = 0;
1098 arm_req->destination_offset = addr;
1099 arm_req->source_nodeid = nodeid;
1100 arm_req->destination_nodeid = destid;
1101 arm_req->tlabel = (flags >> 10) & 0x3f;
1102 arm_req->tcode = (flags >> 4) & 0x0f;
1103 arm_resp->buffer_length = 0;
1104 arm_resp->response_code = rcode;
1105 arm_req_resp->request = int2ptr((arm_addr->recvb) +
1106 sizeof (struct arm_request_response));
1107 arm_req_resp->response = int2ptr((arm_addr->recvb) +
1108 sizeof (struct arm_request_response) +
1109 sizeof (struct arm_request));
1110 queue_complete_req(req);
1112 spin_unlock(&host_info_lock);
1113 return(rcode);
1116 static int arm_lock (struct hpsb_host *host, int nodeid, quadlet_t *store,
1117 u64 addr, quadlet_t data, quadlet_t arg, int ext_tcode, u16 flags)
1119 struct pending_request *req;
1120 struct host_info *hi;
1121 struct file_info *fi = NULL;
1122 struct list_head *entry;
1123 struct arm_addr *arm_addr = NULL;
1124 struct arm_request *arm_req = NULL;
1125 struct arm_response *arm_resp = NULL;
1126 int found=0, size=0, rcode=-1;
1127 quadlet_t old, new;
1128 struct arm_request_response *arm_req_resp = NULL;
1130 if (((ext_tcode & 0xFF) == EXTCODE_FETCH_ADD) ||
1131 ((ext_tcode & 0xFF) == EXTCODE_LITTLE_ADD)) {
1132 DBGMSG("arm_lock called by node: %X "
1133 "addr: %4.4x %8.8x extcode: %2.2X data: %8.8X",
1134 nodeid, (u16) ((addr >>32) & 0xFFFF), (u32) (addr & 0xFFFFFFFF),
1135 ext_tcode & 0xFF , be32_to_cpu(data));
1136 } else {
1137 DBGMSG("arm_lock called by node: %X "
1138 "addr: %4.4x %8.8x extcode: %2.2X data: %8.8X arg: %8.8X",
1139 nodeid, (u16) ((addr >>32) & 0xFFFF), (u32) (addr & 0xFFFFFFFF),
1140 ext_tcode & 0xFF , be32_to_cpu(data), be32_to_cpu(arg));
1142 spin_lock(&host_info_lock);
1143 hi = find_host_info(host); /* search address-entry */
1144 if (hi != NULL) {
1145 list_for_each_entry(fi, &hi->file_info_list, list) {
1146 entry = fi->addr_list.next;
1147 while (entry != &(fi->addr_list)) {
1148 arm_addr = list_entry(entry, struct arm_addr, addr_list);
1149 if (((arm_addr->start) <= (addr)) &&
1150 ((arm_addr->end) >= (addr+sizeof(*store)))) {
1151 found = 1;
1152 break;
1154 entry = entry->next;
1156 if (found) {
1157 break;
1161 rcode = -1;
1162 if (!found) {
1163 printk(KERN_ERR "raw1394: arm_lock FAILED addr_entry not found"
1164 " -> rcode_address_error\n");
1165 spin_unlock(&host_info_lock);
1166 return (RCODE_ADDRESS_ERROR);
1167 } else {
1168 DBGMSG("arm_lock addr_entry FOUND");
1170 if (rcode == -1) {
1171 if (arm_addr->access_rights & ARM_LOCK) {
1172 if (!(arm_addr->client_transactions & ARM_LOCK)) {
1173 memcpy(&old,(arm_addr->addr_space_buffer)+(addr-(arm_addr->start)),
1174 sizeof(old));
1175 switch (ext_tcode) {
1176 case (EXTCODE_MASK_SWAP):
1177 new = data | (old & ~arg);
1178 break;
1179 case (EXTCODE_COMPARE_SWAP):
1180 if (old == arg) {
1181 new = data;
1182 } else {
1183 new = old;
1185 break;
1186 case (EXTCODE_FETCH_ADD):
1187 new = cpu_to_be32(be32_to_cpu(data) + be32_to_cpu(old));
1188 break;
1189 case (EXTCODE_LITTLE_ADD):
1190 new = cpu_to_le32(le32_to_cpu(data) + le32_to_cpu(old));
1191 break;
1192 case (EXTCODE_BOUNDED_ADD):
1193 if (old != arg) {
1194 new = cpu_to_be32(be32_to_cpu(data) +
1195 be32_to_cpu(old));
1196 } else {
1197 new = old;
1199 break;
1200 case (EXTCODE_WRAP_ADD):
1201 if (old != arg) {
1202 new = cpu_to_be32(be32_to_cpu(data) +
1203 be32_to_cpu(old));
1204 } else {
1205 new = data;
1207 break;
1208 default:
1209 rcode = RCODE_TYPE_ERROR; /* function not allowed */
1210 printk(KERN_ERR "raw1394: arm_lock FAILED "
1211 "ext_tcode not allowed -> rcode_type_error\n");
1212 break;
1213 } /*switch*/
1214 if (rcode == -1) {
1215 DBGMSG("arm_lock -> (rcode_complete)");
1216 rcode = RCODE_COMPLETE;
1217 memcpy (store, &old, sizeof(*store));
1218 memcpy ((arm_addr->addr_space_buffer)+
1219 (addr-(arm_addr->start)),
1220 &new, sizeof(*store));
1223 } else {
1224 rcode = RCODE_TYPE_ERROR; /* function not allowed */
1225 DBGMSG("arm_lock -> rcode_type_error (access denied)");
1228 if (arm_addr->notification_options & ARM_LOCK) {
1229 byte_t *buf1, *buf2;
1230 DBGMSG("arm_lock -> entering notification-section");
1231 req = __alloc_pending_request(SLAB_ATOMIC);
1232 if (!req) {
1233 DBGMSG("arm_lock -> rcode_conflict_error");
1234 spin_unlock(&host_info_lock);
1235 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
1236 The request may be retried */
1238 size = sizeof(struct arm_request)+sizeof(struct arm_response) +
1239 3 * sizeof(*store) +
1240 sizeof (struct arm_request_response); /* maximum */
1241 req->data = kmalloc(size, SLAB_ATOMIC);
1242 if (!(req->data)) {
1243 free_pending_request(req);
1244 DBGMSG("arm_lock -> rcode_conflict_error");
1245 spin_unlock(&host_info_lock);
1246 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
1247 The request may be retried */
1249 req->free_data=1;
1250 arm_req_resp = (struct arm_request_response *) (req->data);
1251 arm_req = (struct arm_request *) ((byte_t *)(req->data) +
1252 (sizeof (struct arm_request_response)));
1253 arm_resp = (struct arm_response *) ((byte_t *)(arm_req) +
1254 (sizeof(struct arm_request)));
1255 buf1 = (byte_t *)arm_resp + sizeof(struct arm_response);
1256 buf2 = buf1 + 2 * sizeof(*store);
1257 if ((ext_tcode == EXTCODE_FETCH_ADD) ||
1258 (ext_tcode == EXTCODE_LITTLE_ADD)) {
1259 arm_req->buffer_length = sizeof(*store);
1260 memcpy (buf1, &data, sizeof(*store));
1262 } else {
1263 arm_req->buffer_length = 2 * sizeof(*store);
1264 memcpy (buf1, &arg, sizeof(*store));
1265 memcpy (buf1 + sizeof(*store), &data, sizeof(*store));
1267 if (rcode == RCODE_COMPLETE) {
1268 arm_resp->buffer_length = sizeof(*store);
1269 memcpy (buf2, &old, sizeof(*store));
1270 } else {
1271 arm_resp->buffer_length = 0;
1273 req->file_info = fi;
1274 req->req.type = RAW1394_REQ_ARM;
1275 req->req.generation = get_hpsb_generation(host);
1276 req->req.misc = ( (((sizeof(*store)) << 16) & (0xFFFF0000)) |
1277 (ARM_LOCK & 0xFF));
1278 req->req.tag = arm_addr->arm_tag;
1279 req->req.recvb = arm_addr->recvb;
1280 req->req.length = size;
1281 arm_req->generation = req->req.generation;
1282 arm_req->extended_transaction_code = ext_tcode;
1283 arm_req->destination_offset = addr;
1284 arm_req->source_nodeid = nodeid;
1285 arm_req->destination_nodeid = host->node_id;
1286 arm_req->tlabel = (flags >> 10) & 0x3f;
1287 arm_req->tcode = (flags >> 4) & 0x0f;
1288 arm_resp->response_code = rcode;
1289 arm_req_resp->request = int2ptr((arm_addr->recvb) +
1290 sizeof (struct arm_request_response));
1291 arm_req_resp->response = int2ptr((arm_addr->recvb) +
1292 sizeof (struct arm_request_response) +
1293 sizeof (struct arm_request));
1294 arm_req->buffer = int2ptr((arm_addr->recvb) +
1295 sizeof (struct arm_request_response) +
1296 sizeof (struct arm_request) +
1297 sizeof (struct arm_response));
1298 arm_resp->buffer = int2ptr((arm_addr->recvb) +
1299 sizeof (struct arm_request_response) +
1300 sizeof (struct arm_request) +
1301 sizeof (struct arm_response) +
1302 2* sizeof (*store));
1303 queue_complete_req(req);
1305 spin_unlock(&host_info_lock);
1306 return(rcode);
1309 static int arm_lock64 (struct hpsb_host *host, int nodeid, octlet_t *store,
1310 u64 addr, octlet_t data, octlet_t arg, int ext_tcode, u16 flags)
1312 struct pending_request *req;
1313 struct host_info *hi;
1314 struct file_info *fi = NULL;
1315 struct list_head *entry;
1316 struct arm_addr *arm_addr = NULL;
1317 struct arm_request *arm_req = NULL;
1318 struct arm_response *arm_resp = NULL;
1319 int found=0, size=0, rcode=-1;
1320 octlet_t old, new;
1321 struct arm_request_response *arm_req_resp = NULL;
1323 if (((ext_tcode & 0xFF) == EXTCODE_FETCH_ADD) ||
1324 ((ext_tcode & 0xFF) == EXTCODE_LITTLE_ADD)) {
1325 DBGMSG("arm_lock64 called by node: %X "
1326 "addr: %4.4x %8.8x extcode: %2.2X data: %8.8X %8.8X ",
1327 nodeid, (u16) ((addr >>32) & 0xFFFF),
1328 (u32) (addr & 0xFFFFFFFF),
1329 ext_tcode & 0xFF ,
1330 (u32) ((be64_to_cpu(data) >> 32) & 0xFFFFFFFF),
1331 (u32) (be64_to_cpu(data) & 0xFFFFFFFF));
1332 } else {
1333 DBGMSG("arm_lock64 called by node: %X "
1334 "addr: %4.4x %8.8x extcode: %2.2X data: %8.8X %8.8X arg: "
1335 "%8.8X %8.8X ",
1336 nodeid, (u16) ((addr >>32) & 0xFFFF),
1337 (u32) (addr & 0xFFFFFFFF),
1338 ext_tcode & 0xFF ,
1339 (u32) ((be64_to_cpu(data) >> 32) & 0xFFFFFFFF),
1340 (u32) (be64_to_cpu(data) & 0xFFFFFFFF),
1341 (u32) ((be64_to_cpu(arg) >> 32) & 0xFFFFFFFF),
1342 (u32) (be64_to_cpu(arg) & 0xFFFFFFFF));
1344 spin_lock(&host_info_lock);
1345 hi = find_host_info(host); /* search addressentry in file_info's for host */
1346 if (hi != NULL) {
1347 list_for_each_entry(fi, &hi->file_info_list, list) {
1348 entry = fi->addr_list.next;
1349 while (entry != &(fi->addr_list)) {
1350 arm_addr = list_entry(entry, struct arm_addr, addr_list);
1351 if (((arm_addr->start) <= (addr)) &&
1352 ((arm_addr->end) >= (addr+sizeof(*store)))) {
1353 found = 1;
1354 break;
1356 entry = entry->next;
1358 if (found) {
1359 break;
1363 rcode = -1;
1364 if (!found) {
1365 printk(KERN_ERR "raw1394: arm_lock64 FAILED addr_entry not found"
1366 " -> rcode_address_error\n");
1367 spin_unlock(&host_info_lock);
1368 return (RCODE_ADDRESS_ERROR);
1369 } else {
1370 DBGMSG("arm_lock64 addr_entry FOUND");
1372 if (rcode == -1) {
1373 if (arm_addr->access_rights & ARM_LOCK) {
1374 if (!(arm_addr->client_transactions & ARM_LOCK)) {
1375 memcpy(&old,(arm_addr->addr_space_buffer)+(addr-(arm_addr->start)),
1376 sizeof(old));
1377 switch (ext_tcode) {
1378 case (EXTCODE_MASK_SWAP):
1379 new = data | (old & ~arg);
1380 break;
1381 case (EXTCODE_COMPARE_SWAP):
1382 if (old == arg) {
1383 new = data;
1384 } else {
1385 new = old;
1387 break;
1388 case (EXTCODE_FETCH_ADD):
1389 new = cpu_to_be64(be64_to_cpu(data) + be64_to_cpu(old));
1390 break;
1391 case (EXTCODE_LITTLE_ADD):
1392 new = cpu_to_le64(le64_to_cpu(data) + le64_to_cpu(old));
1393 break;
1394 case (EXTCODE_BOUNDED_ADD):
1395 if (old != arg) {
1396 new = cpu_to_be64(be64_to_cpu(data) +
1397 be64_to_cpu(old));
1398 } else {
1399 new = old;
1401 break;
1402 case (EXTCODE_WRAP_ADD):
1403 if (old != arg) {
1404 new = cpu_to_be64(be64_to_cpu(data) +
1405 be64_to_cpu(old));
1406 } else {
1407 new = data;
1409 break;
1410 default:
1411 printk(KERN_ERR "raw1394: arm_lock64 FAILED "
1412 "ext_tcode not allowed -> rcode_type_error\n");
1413 rcode = RCODE_TYPE_ERROR; /* function not allowed */
1414 break;
1415 } /*switch*/
1416 if (rcode == -1) {
1417 DBGMSG("arm_lock64 -> (rcode_complete)");
1418 rcode = RCODE_COMPLETE;
1419 memcpy (store, &old, sizeof(*store));
1420 memcpy ((arm_addr->addr_space_buffer)+
1421 (addr-(arm_addr->start)),
1422 &new, sizeof(*store));
1425 } else {
1426 rcode = RCODE_TYPE_ERROR; /* function not allowed */
1427 DBGMSG("arm_lock64 -> rcode_type_error (access denied)");
1430 if (arm_addr->notification_options & ARM_LOCK) {
1431 byte_t *buf1, *buf2;
1432 DBGMSG("arm_lock64 -> entering notification-section");
1433 req = __alloc_pending_request(SLAB_ATOMIC);
1434 if (!req) {
1435 spin_unlock(&host_info_lock);
1436 DBGMSG("arm_lock64 -> rcode_conflict_error");
1437 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
1438 The request may be retried */
1440 size = sizeof(struct arm_request)+sizeof(struct arm_response) +
1441 3 * sizeof(*store) +
1442 sizeof (struct arm_request_response); /* maximum */
1443 req->data = kmalloc(size, SLAB_ATOMIC);
1444 if (!(req->data)) {
1445 free_pending_request(req);
1446 spin_unlock(&host_info_lock);
1447 DBGMSG("arm_lock64 -> rcode_conflict_error");
1448 return(RCODE_CONFLICT_ERROR); /* A resource conflict was detected.
1449 The request may be retried */
1451 req->free_data=1;
1452 arm_req_resp = (struct arm_request_response *) (req->data);
1453 arm_req = (struct arm_request *) ((byte_t *)(req->data) +
1454 (sizeof (struct arm_request_response)));
1455 arm_resp = (struct arm_response *) ((byte_t *)(arm_req) +
1456 (sizeof(struct arm_request)));
1457 buf1 = (byte_t *)arm_resp + sizeof(struct arm_response);
1458 buf2 = buf1 + 2 * sizeof(*store);
1459 if ((ext_tcode == EXTCODE_FETCH_ADD) ||
1460 (ext_tcode == EXTCODE_LITTLE_ADD)) {
1461 arm_req->buffer_length = sizeof(*store);
1462 memcpy (buf1, &data, sizeof(*store));
1464 } else {
1465 arm_req->buffer_length = 2 * sizeof(*store);
1466 memcpy (buf1, &arg, sizeof(*store));
1467 memcpy (buf1 + sizeof(*store), &data, sizeof(*store));
1469 if (rcode == RCODE_COMPLETE) {
1470 arm_resp->buffer_length = sizeof(*store);
1471 memcpy (buf2, &old, sizeof(*store));
1472 } else {
1473 arm_resp->buffer_length = 0;
1475 req->file_info = fi;
1476 req->req.type = RAW1394_REQ_ARM;
1477 req->req.generation = get_hpsb_generation(host);
1478 req->req.misc = ( (((sizeof(*store)) << 16) & (0xFFFF0000)) |
1479 (ARM_LOCK & 0xFF));
1480 req->req.tag = arm_addr->arm_tag;
1481 req->req.recvb = arm_addr->recvb;
1482 req->req.length = size;
1483 arm_req->generation = req->req.generation;
1484 arm_req->extended_transaction_code = ext_tcode;
1485 arm_req->destination_offset = addr;
1486 arm_req->source_nodeid = nodeid;
1487 arm_req->destination_nodeid = host->node_id;
1488 arm_req->tlabel = (flags >> 10) & 0x3f;
1489 arm_req->tcode = (flags >> 4) & 0x0f;
1490 arm_resp->response_code = rcode;
1491 arm_req_resp->request = int2ptr((arm_addr->recvb) +
1492 sizeof (struct arm_request_response));
1493 arm_req_resp->response = int2ptr((arm_addr->recvb) +
1494 sizeof (struct arm_request_response) +
1495 sizeof (struct arm_request));
1496 arm_req->buffer = int2ptr((arm_addr->recvb) +
1497 sizeof (struct arm_request_response) +
1498 sizeof (struct arm_request) +
1499 sizeof (struct arm_response));
1500 arm_resp->buffer = int2ptr((arm_addr->recvb) +
1501 sizeof (struct arm_request_response) +
1502 sizeof (struct arm_request) +
1503 sizeof (struct arm_response) +
1504 2* sizeof (*store));
1505 queue_complete_req(req);
1507 spin_unlock(&host_info_lock);
1508 return(rcode);
1511 static int arm_register(struct file_info *fi, struct pending_request *req)
1513 int retval;
1514 struct arm_addr *addr;
1515 struct host_info *hi;
1516 struct file_info *fi_hlp = NULL;
1517 struct list_head *entry;
1518 struct arm_addr *arm_addr = NULL;
1519 int same_host, another_host;
1520 unsigned long flags;
1522 DBGMSG("arm_register called "
1523 "addr(Offset): %8.8x %8.8x length: %u "
1524 "rights: %2.2X notify: %2.2X "
1525 "max_blk_len: %4.4X",
1526 (u32) ((req->req.address >>32) & 0xFFFF),
1527 (u32) (req->req.address & 0xFFFFFFFF),
1528 req->req.length, ((req->req.misc >> 8) & 0xFF),
1529 (req->req.misc & 0xFF),((req->req.misc >> 16) & 0xFFFF));
1530 /* check addressrange */
1531 if ((((req->req.address) & ~(0xFFFFFFFFFFFFULL)) != 0) ||
1532 (((req->req.address + req->req.length) & ~(0xFFFFFFFFFFFFULL)) != 0)) {
1533 req->req.length = 0;
1534 return (-EINVAL);
1536 /* addr-list-entry for fileinfo */
1537 addr = (struct arm_addr *)kmalloc(sizeof(struct arm_addr), SLAB_KERNEL);
1538 if (!addr) {
1539 req->req.length = 0;
1540 return (-ENOMEM);
1542 /* allocation of addr_space_buffer */
1543 addr->addr_space_buffer = (u8 *)vmalloc(req->req.length);
1544 if (!(addr->addr_space_buffer)) {
1545 kfree(addr);
1546 req->req.length = 0;
1547 return (-ENOMEM);
1549 /* initialization of addr_space_buffer */
1550 if ((req->req.sendb)== (unsigned long)NULL) {
1551 /* init: set 0 */
1552 memset(addr->addr_space_buffer, 0,req->req.length);
1553 } else {
1554 /* init: user -> kernel */
1555 if (copy_from_user(addr->addr_space_buffer,int2ptr(req->req.sendb),
1556 req->req.length)) {
1557 vfree(addr->addr_space_buffer);
1558 kfree(addr);
1559 return (-EFAULT);
1562 INIT_LIST_HEAD(&addr->addr_list);
1563 addr->arm_tag = req->req.tag;
1564 addr->start = req->req.address;
1565 addr->end = req->req.address + req->req.length;
1566 addr->access_rights = (u8) (req->req.misc & 0x0F);
1567 addr->notification_options = (u8) ((req->req.misc >> 4) & 0x0F);
1568 addr->client_transactions = (u8) ((req->req.misc >> 8) & 0x0F);
1569 addr->access_rights |= addr->client_transactions;
1570 addr->notification_options |= addr->client_transactions;
1571 addr->recvb = req->req.recvb;
1572 addr->rec_length = (u16) ((req->req.misc >> 16) & 0xFFFF);
1573 spin_lock_irqsave(&host_info_lock, flags);
1574 hi = find_host_info(fi->host);
1575 same_host = 0;
1576 another_host = 0;
1577 /* same host with address-entry containing same addressrange ? */
1578 list_for_each_entry(fi_hlp, &hi->file_info_list, list) {
1579 entry = fi_hlp->addr_list.next;
1580 while (entry != &(fi_hlp->addr_list)) {
1581 arm_addr = list_entry(entry, struct arm_addr, addr_list);
1582 if ( (arm_addr->start == addr->start) &&
1583 (arm_addr->end == addr->end)) {
1584 DBGMSG("same host ownes same "
1585 "addressrange -> EALREADY");
1586 same_host = 1;
1587 break;
1589 entry = entry->next;
1591 if (same_host) {
1592 break;
1595 if (same_host) {
1596 /* addressrange occupied by same host */
1597 vfree(addr->addr_space_buffer);
1598 kfree(addr);
1599 spin_unlock_irqrestore(&host_info_lock, flags);
1600 return (-EALREADY);
1602 /* another host with valid address-entry containing same addressrange */
1603 list_for_each_entry(hi, &host_info_list, list) {
1604 if (hi->host != fi->host) {
1605 list_for_each_entry(fi_hlp, &hi->file_info_list, list) {
1606 entry = fi_hlp->addr_list.next;
1607 while (entry != &(fi_hlp->addr_list)) {
1608 arm_addr = list_entry(entry, struct arm_addr, addr_list);
1609 if ( (arm_addr->start == addr->start) &&
1610 (arm_addr->end == addr->end)) {
1611 DBGMSG("another host ownes same "
1612 "addressrange");
1613 another_host = 1;
1614 break;
1616 entry = entry->next;
1618 if (another_host) {
1619 break;
1624 if (another_host) {
1625 DBGMSG("another hosts entry is valid -> SUCCESS");
1626 if (copy_to_user(int2ptr(req->req.recvb),
1627 &addr->start,sizeof(u64))) {
1628 printk(KERN_ERR "raw1394: arm_register failed "
1629 " address-range-entry is invalid -> EFAULT !!!\n");
1630 vfree(addr->addr_space_buffer);
1631 kfree(addr);
1632 spin_unlock_irqrestore(&host_info_lock, flags);
1633 return (-EFAULT);
1635 free_pending_request(req); /* immediate success or fail */
1636 /* INSERT ENTRY */
1637 list_add_tail(&addr->addr_list, &fi->addr_list);
1638 spin_unlock_irqrestore(&host_info_lock, flags);
1639 return sizeof(struct raw1394_request);
1641 retval = hpsb_register_addrspace(&raw1394_highlevel, fi->host, &arm_ops, req->req.address,
1642 req->req.address + req->req.length);
1643 if (retval) {
1644 /* INSERT ENTRY */
1645 list_add_tail(&addr->addr_list, &fi->addr_list);
1646 } else {
1647 DBGMSG("arm_register failed errno: %d \n",retval);
1648 vfree(addr->addr_space_buffer);
1649 kfree(addr);
1650 spin_unlock_irqrestore(&host_info_lock, flags);
1651 return (-EALREADY);
1653 spin_unlock_irqrestore(&host_info_lock, flags);
1654 free_pending_request(req); /* immediate success or fail */
1655 return sizeof(struct raw1394_request);
1658 static int arm_unregister(struct file_info *fi, struct pending_request *req)
1660 int found = 0;
1661 int retval = 0;
1662 struct list_head *entry;
1663 struct arm_addr *addr = NULL;
1664 struct host_info *hi;
1665 struct file_info *fi_hlp = NULL;
1666 struct arm_addr *arm_addr = NULL;
1667 int another_host;
1668 unsigned long flags;
1670 DBGMSG("arm_Unregister called addr(Offset): "
1671 "%8.8x %8.8x",
1672 (u32) ((req->req.address >>32) & 0xFFFF),
1673 (u32) (req->req.address & 0xFFFFFFFF));
1674 spin_lock_irqsave(&host_info_lock, flags);
1675 /* get addr */
1676 entry = fi->addr_list.next;
1677 while (entry != &(fi->addr_list)) {
1678 addr = list_entry(entry, struct arm_addr, addr_list);
1679 if (addr->start == req->req.address) {
1680 found = 1;
1681 break;
1683 entry = entry->next;
1685 if (!found) {
1686 DBGMSG("arm_Unregister addr not found");
1687 spin_unlock_irqrestore(&host_info_lock, flags);
1688 return (-EINVAL);
1690 DBGMSG("arm_Unregister addr found");
1691 another_host = 0;
1692 /* another host with valid address-entry containing
1693 same addressrange */
1694 list_for_each_entry(hi, &host_info_list, list) {
1695 if (hi->host != fi->host) {
1696 list_for_each_entry(fi_hlp, &hi->file_info_list, list) {
1697 entry = fi_hlp->addr_list.next;
1698 while (entry != &(fi_hlp->addr_list)) {
1699 arm_addr = list_entry(entry,
1700 struct arm_addr, addr_list);
1701 if (arm_addr->start ==
1702 addr->start) {
1703 DBGMSG("another host ownes "
1704 "same addressrange");
1705 another_host = 1;
1706 break;
1708 entry = entry->next;
1710 if (another_host) {
1711 break;
1716 if (another_host) {
1717 DBGMSG("delete entry from list -> success");
1718 list_del(&addr->addr_list);
1719 vfree(addr->addr_space_buffer);
1720 kfree(addr);
1721 free_pending_request(req); /* immediate success or fail */
1722 spin_unlock_irqrestore(&host_info_lock, flags);
1723 return sizeof(struct raw1394_request);
1725 retval = hpsb_unregister_addrspace(&raw1394_highlevel, fi->host, addr->start);
1726 if (!retval) {
1727 printk(KERN_ERR "raw1394: arm_Unregister failed -> EINVAL\n");
1728 spin_unlock_irqrestore(&host_info_lock, flags);
1729 return (-EINVAL);
1731 DBGMSG("delete entry from list -> success");
1732 list_del(&addr->addr_list);
1733 spin_unlock_irqrestore(&host_info_lock, flags);
1734 vfree(addr->addr_space_buffer);
1735 kfree(addr);
1736 free_pending_request(req); /* immediate success or fail */
1737 return sizeof(struct raw1394_request);
1740 /* Copy data from ARM buffer(s) to user buffer. */
1741 static int arm_get_buf(struct file_info *fi, struct pending_request *req)
1743 struct arm_addr *arm_addr = NULL;
1744 unsigned long flags;
1745 unsigned long offset;
1747 struct list_head *entry;
1749 DBGMSG("arm_get_buf "
1750 "addr(Offset): %04X %08X length: %u",
1751 (u32) ((req->req.address >> 32) & 0xFFFF),
1752 (u32) (req->req.address & 0xFFFFFFFF),
1753 (u32) req->req.length);
1755 spin_lock_irqsave(&host_info_lock, flags);
1756 entry = fi->addr_list.next;
1757 while (entry != &(fi->addr_list)) {
1758 arm_addr = list_entry(entry, struct arm_addr, addr_list);
1759 if ((arm_addr->start <= req->req.address) &&
1760 (arm_addr->end > req->req.address)) {
1761 if (req->req.address + req->req.length <= arm_addr->end) {
1762 offset = req->req.address - arm_addr->start;
1764 DBGMSG("arm_get_buf copy_to_user( %08X, %p, %u )",
1765 (u32) req->req.recvb,
1766 arm_addr->addr_space_buffer+offset,
1767 (u32) req->req.length);
1769 if (copy_to_user(int2ptr(req->req.recvb), arm_addr->addr_space_buffer+offset, req->req.length)) {
1770 spin_unlock_irqrestore(&host_info_lock, flags);
1771 return (-EFAULT);
1774 spin_unlock_irqrestore(&host_info_lock, flags);
1775 /* We have to free the request, because we
1776 * queue no response, and therefore nobody
1777 * will free it. */
1778 free_pending_request(req);
1779 return sizeof(struct raw1394_request);
1780 } else {
1781 DBGMSG("arm_get_buf request exceeded mapping");
1782 spin_unlock_irqrestore(&host_info_lock, flags);
1783 return (-EINVAL);
1786 entry = entry->next;
1788 spin_unlock_irqrestore(&host_info_lock, flags);
1789 return (-EINVAL);
1793 /* Copy data from user buffer to ARM buffer(s). */
1794 static int arm_set_buf(struct file_info *fi, struct pending_request *req)
1796 struct arm_addr *arm_addr = NULL;
1797 unsigned long flags;
1798 unsigned long offset;
1800 struct list_head *entry;
1802 DBGMSG("arm_set_buf "
1803 "addr(Offset): %04X %08X length: %u",
1804 (u32) ((req->req.address >> 32) & 0xFFFF),
1805 (u32) (req->req.address & 0xFFFFFFFF),
1806 (u32) req->req.length);
1809 spin_lock_irqsave(&host_info_lock, flags);
1810 entry = fi->addr_list.next;
1811 while (entry != &(fi->addr_list)) {
1812 arm_addr = list_entry(entry, struct arm_addr, addr_list);
1813 if ((arm_addr->start <= req->req.address) &&
1814 (arm_addr->end > req->req.address)) {
1815 if (req->req.address + req->req.length <= arm_addr->end) {
1816 offset = req->req.address - arm_addr->start;
1818 DBGMSG("arm_set_buf copy_from_user( %p, %08X, %u )",
1819 arm_addr->addr_space_buffer+offset,
1820 (u32) req->req.sendb,
1821 (u32) req->req.length);
1823 if (copy_from_user(arm_addr->addr_space_buffer+offset, int2ptr(req->req.sendb), req->req.length)) {
1824 spin_unlock_irqrestore(&host_info_lock, flags);
1825 return (-EFAULT);
1828 spin_unlock_irqrestore(&host_info_lock, flags);
1829 free_pending_request(req); /* we have to free the request, because we queue no response, and therefore nobody will free it */
1830 return sizeof(struct raw1394_request);
1831 } else {
1832 DBGMSG("arm_set_buf request exceeded mapping");
1833 spin_unlock_irqrestore(&host_info_lock, flags);
1834 return (-EINVAL);
1837 entry = entry->next;
1839 spin_unlock_irqrestore(&host_info_lock, flags);
1840 return (-EINVAL);
1843 static int reset_notification(struct file_info *fi, struct pending_request *req)
1845 DBGMSG("reset_notification called - switch %s ",
1846 (req->req.misc == RAW1394_NOTIFY_OFF)?"OFF":"ON");
1847 if ((req->req.misc == RAW1394_NOTIFY_OFF) ||
1848 (req->req.misc == RAW1394_NOTIFY_ON)) {
1849 fi->notification=(u8)req->req.misc;
1850 free_pending_request(req); /* we have to free the request, because we queue no response, and therefore nobody will free it */
1851 return sizeof(struct raw1394_request);
1853 /* error EINVAL (22) invalid argument */
1854 return (-EINVAL);
1857 static int write_phypacket(struct file_info *fi, struct pending_request *req)
1859 struct hpsb_packet *packet = NULL;
1860 int retval=0;
1861 quadlet_t data;
1863 data = be32_to_cpu((u32)req->req.sendb);
1864 DBGMSG("write_phypacket called - quadlet 0x%8.8x ",data);
1865 packet = hpsb_make_phypacket (fi->host, data);
1866 if (!packet) return -ENOMEM;
1867 req->req.length=0;
1868 req->packet=packet;
1869 hpsb_set_packet_complete_task(packet, (void(*)(void*))queue_complete_cb, req);
1870 spin_lock_irq(&fi->reqlists_lock);
1871 list_add_tail(&req->list, &fi->req_pending);
1872 spin_unlock_irq(&fi->reqlists_lock);
1873 packet->generation = req->req.generation;
1874 retval = hpsb_send_packet(packet);
1875 DBGMSG("write_phypacket send_packet called => retval: %d ", retval);
1876 if (retval < 0) {
1877 req->req.error = RAW1394_ERROR_SEND_ERROR;
1878 req->req.length = 0;
1879 queue_complete_req(req);
1881 return sizeof(struct raw1394_request);
1884 static int get_config_rom(struct file_info *fi, struct pending_request *req)
1886 int ret=sizeof(struct raw1394_request);
1887 quadlet_t *data = kmalloc(req->req.length, SLAB_KERNEL);
1888 int status;
1890 if (!data) return -ENOMEM;
1892 status = csr1212_read(fi->host->csr.rom, CSR1212_CONFIG_ROM_SPACE_OFFSET,
1893 data, req->req.length);
1894 if (copy_to_user(int2ptr(req->req.recvb), data,
1895 req->req.length))
1896 ret = -EFAULT;
1897 if (copy_to_user(int2ptr(req->req.tag), &fi->host->csr.rom->cache_head->len,
1898 sizeof(fi->host->csr.rom->cache_head->len)))
1899 ret = -EFAULT;
1900 if (copy_to_user(int2ptr(req->req.address), &fi->host->csr.generation,
1901 sizeof(fi->host->csr.generation)))
1902 ret = -EFAULT;
1903 if (copy_to_user(int2ptr(req->req.sendb), &status,
1904 sizeof(status)))
1905 ret = -EFAULT;
1906 kfree(data);
1907 if (ret >= 0) {
1908 free_pending_request(req); /* we have to free the request, because we queue no response, and therefore nobody will free it */
1910 return ret;
1913 static int update_config_rom(struct file_info *fi, struct pending_request *req)
1915 int ret=sizeof(struct raw1394_request);
1916 quadlet_t *data = kmalloc(req->req.length, SLAB_KERNEL);
1917 if (!data) return -ENOMEM;
1918 if (copy_from_user(data,int2ptr(req->req.sendb),
1919 req->req.length)) {
1920 ret= -EFAULT;
1921 } else {
1922 int status = hpsb_update_config_rom(fi->host,
1923 data, req->req.length,
1924 (unsigned char) req->req.misc);
1925 if (copy_to_user(int2ptr(req->req.recvb),
1926 &status, sizeof(status)))
1927 ret = -ENOMEM;
1929 kfree(data);
1930 if (ret >= 0) {
1931 free_pending_request(req); /* we have to free the request, because we queue no response, and therefore nobody will free it */
1932 fi->cfgrom_upd = 1;
1934 return ret;
1937 static int modify_config_rom(struct file_info *fi, struct pending_request *req)
1939 struct csr1212_keyval *kv;
1940 struct csr1212_csr_rom_cache *cache;
1941 struct csr1212_dentry *dentry;
1942 u32 dr;
1943 int ret = 0;
1945 if (req->req.misc == ~0) {
1946 if (req->req.length == 0) return -EINVAL;
1948 /* Find an unused slot */
1949 for (dr = 0; dr < RAW1394_MAX_USER_CSR_DIRS && fi->csr1212_dirs[dr]; dr++);
1951 if (dr == RAW1394_MAX_USER_CSR_DIRS) return -ENOMEM;
1953 fi->csr1212_dirs[dr] = csr1212_new_directory(CSR1212_KV_ID_VENDOR);
1954 if (!fi->csr1212_dirs[dr]) return -ENOMEM;
1955 } else {
1956 dr = req->req.misc;
1957 if (!fi->csr1212_dirs[dr]) return -EINVAL;
1959 /* Delete old stuff */
1960 for (dentry = fi->csr1212_dirs[dr]->value.directory.dentries_head;
1961 dentry; dentry = dentry->next) {
1962 csr1212_detach_keyval_from_directory(fi->host->csr.rom->root_kv,
1963 dentry->kv);
1966 if (req->req.length == 0) {
1967 csr1212_release_keyval(fi->csr1212_dirs[dr]);
1968 fi->csr1212_dirs[dr] = NULL;
1970 hpsb_update_config_rom_image(fi->host);
1971 free_pending_request(req);
1972 return sizeof(struct raw1394_request);
1976 cache = csr1212_rom_cache_malloc(0, req->req.length);
1977 if (!cache) {
1978 csr1212_release_keyval(fi->csr1212_dirs[dr]);
1979 fi->csr1212_dirs[dr] = NULL;
1980 return -ENOMEM;
1983 cache->filled_head = kmalloc(sizeof(struct csr1212_cache_region), GFP_KERNEL);
1984 if (!cache->filled_head) {
1985 csr1212_release_keyval(fi->csr1212_dirs[dr]);
1986 fi->csr1212_dirs[dr] = NULL;
1987 CSR1212_FREE(cache);
1988 return -ENOMEM;
1990 cache->filled_tail = cache->filled_head;
1992 if (copy_from_user(cache->data, int2ptr(req->req.sendb),
1993 req->req.length)) {
1994 csr1212_release_keyval(fi->csr1212_dirs[dr]);
1995 fi->csr1212_dirs[dr] = NULL;
1996 CSR1212_FREE(cache);
1997 ret= -EFAULT;
1998 } else {
1999 cache->len = req->req.length;
2000 cache->filled_head->offset_start = 0;
2001 cache->filled_head->offset_end = cache->size -1;
2003 cache->layout_head = cache->layout_tail = fi->csr1212_dirs[dr];
2005 ret = CSR1212_SUCCESS;
2006 /* parse all the items */
2007 for (kv = cache->layout_head; ret == CSR1212_SUCCESS && kv;
2008 kv = kv->next) {
2009 ret = csr1212_parse_keyval(kv, cache);
2012 /* attach top level items to the root directory */
2013 for (dentry = fi->csr1212_dirs[dr]->value.directory.dentries_head;
2014 ret == CSR1212_SUCCESS && dentry; dentry = dentry->next) {
2015 ret = csr1212_attach_keyval_to_directory(fi->host->csr.rom->root_kv,
2016 dentry->kv);
2019 if (ret == CSR1212_SUCCESS) {
2020 ret = hpsb_update_config_rom_image(fi->host);
2022 if (ret >= 0 && copy_to_user(int2ptr(req->req.recvb),
2023 &dr, sizeof(dr))) {
2024 ret = -ENOMEM;
2028 kfree(cache->filled_head);
2029 kfree(cache);
2031 if (ret >= 0) {
2032 /* we have to free the request, because we queue no response,
2033 * and therefore nobody will free it */
2034 free_pending_request(req);
2035 return sizeof(struct raw1394_request);
2036 } else {
2037 for (dentry = fi->csr1212_dirs[dr]->value.directory.dentries_head;
2038 dentry; dentry = dentry->next) {
2039 csr1212_detach_keyval_from_directory(fi->host->csr.rom->root_kv,
2040 dentry->kv);
2042 csr1212_release_keyval(fi->csr1212_dirs[dr]);
2043 fi->csr1212_dirs[dr] = NULL;
2044 return ret;
2048 static int state_connected(struct file_info *fi, struct pending_request *req)
2050 int node = req->req.address >> 48;
2052 req->req.error = RAW1394_ERROR_NONE;
2054 switch (req->req.type) {
2056 case RAW1394_REQ_ECHO:
2057 queue_complete_req(req);
2058 return sizeof(struct raw1394_request);
2060 case RAW1394_REQ_ISO_SEND:
2061 return handle_iso_send(fi, req, node);
2063 case RAW1394_REQ_ARM_REGISTER:
2064 return arm_register(fi, req);
2066 case RAW1394_REQ_ARM_UNREGISTER:
2067 return arm_unregister(fi, req);
2069 case RAW1394_REQ_ARM_SET_BUF:
2070 return arm_set_buf(fi, req);
2072 case RAW1394_REQ_ARM_GET_BUF:
2073 return arm_get_buf(fi, req);
2075 case RAW1394_REQ_RESET_NOTIFY:
2076 return reset_notification(fi, req);
2078 case RAW1394_REQ_ISO_LISTEN:
2079 handle_iso_listen(fi, req);
2080 return sizeof(struct raw1394_request);
2082 case RAW1394_REQ_FCP_LISTEN:
2083 handle_fcp_listen(fi, req);
2084 return sizeof(struct raw1394_request);
2086 case RAW1394_REQ_RESET_BUS:
2087 if (req->req.misc == RAW1394_LONG_RESET) {
2088 DBGMSG("busreset called (type: LONG)");
2089 hpsb_reset_bus(fi->host, LONG_RESET);
2090 free_pending_request(req); /* we have to free the request, because we queue no response, and therefore nobody will free it */
2091 return sizeof(struct raw1394_request);
2093 if (req->req.misc == RAW1394_SHORT_RESET) {
2094 DBGMSG("busreset called (type: SHORT)");
2095 hpsb_reset_bus(fi->host, SHORT_RESET);
2096 free_pending_request(req); /* we have to free the request, because we queue no response, and therefore nobody will free it */
2097 return sizeof(struct raw1394_request);
2099 /* error EINVAL (22) invalid argument */
2100 return (-EINVAL);
2101 case RAW1394_REQ_GET_ROM:
2102 return get_config_rom(fi, req);
2104 case RAW1394_REQ_UPDATE_ROM:
2105 return update_config_rom(fi, req);
2107 case RAW1394_REQ_MODIFY_ROM:
2108 return modify_config_rom(fi, req);
2111 if (req->req.generation != get_hpsb_generation(fi->host)) {
2112 req->req.error = RAW1394_ERROR_GENERATION;
2113 req->req.generation = get_hpsb_generation(fi->host);
2114 req->req.length = 0;
2115 queue_complete_req(req);
2116 return sizeof(struct raw1394_request);
2119 switch (req->req.type) {
2120 case RAW1394_REQ_PHYPACKET:
2121 return write_phypacket(fi, req);
2122 case RAW1394_REQ_ASYNC_SEND:
2123 return handle_async_send(fi, req);
2126 if (req->req.length == 0) {
2127 req->req.error = RAW1394_ERROR_INVALID_ARG;
2128 queue_complete_req(req);
2129 return sizeof(struct raw1394_request);
2132 return handle_async_request(fi, req, node);
2136 static ssize_t raw1394_write(struct file *file, const char __user *buffer, size_t count,
2137 loff_t *offset_is_ignored)
2139 struct file_info *fi = (struct file_info *)file->private_data;
2140 struct pending_request *req;
2141 ssize_t retval = 0;
2143 if (count != sizeof(struct raw1394_request)) {
2144 return -EINVAL;
2147 req = alloc_pending_request();
2148 if (req == NULL) {
2149 return -ENOMEM;
2151 req->file_info = fi;
2153 if (copy_from_user(&req->req, buffer, sizeof(struct raw1394_request))) {
2154 free_pending_request(req);
2155 return -EFAULT;
2158 switch (fi->state) {
2159 case opened:
2160 retval = state_opened(fi, req);
2161 break;
2163 case initialized:
2164 retval = state_initialized(fi, req);
2165 break;
2167 case connected:
2168 retval = state_connected(fi, req);
2169 break;
2172 if (retval < 0) {
2173 free_pending_request(req);
2176 return retval;
2179 /* rawiso operations */
2181 /* check if any RAW1394_REQ_RAWISO_ACTIVITY event is already in the
2182 * completion queue (reqlists_lock must be taken) */
2183 static inline int __rawiso_event_in_queue(struct file_info *fi)
2185 struct pending_request *req;
2187 list_for_each_entry(req, &fi->req_complete, list)
2188 if (req->req.type == RAW1394_REQ_RAWISO_ACTIVITY)
2189 return 1;
2191 return 0;
2194 /* put a RAWISO_ACTIVITY event in the queue, if one isn't there already */
2195 static void queue_rawiso_event(struct file_info *fi)
2197 unsigned long flags;
2199 spin_lock_irqsave(&fi->reqlists_lock, flags);
2201 /* only one ISO activity event may be in the queue */
2202 if (!__rawiso_event_in_queue(fi)) {
2203 struct pending_request *req = __alloc_pending_request(SLAB_ATOMIC);
2205 if (req) {
2206 req->file_info = fi;
2207 req->req.type = RAW1394_REQ_RAWISO_ACTIVITY;
2208 req->req.generation = get_hpsb_generation(fi->host);
2209 __queue_complete_req(req);
2210 } else {
2211 /* on allocation failure, signal an overflow */
2212 if (fi->iso_handle) {
2213 atomic_inc(&fi->iso_handle->overflows);
2217 spin_unlock_irqrestore(&fi->reqlists_lock, flags);
2220 static void rawiso_activity_cb(struct hpsb_iso *iso)
2222 unsigned long flags;
2223 struct host_info *hi;
2224 struct file_info *fi;
2226 spin_lock_irqsave(&host_info_lock, flags);
2227 hi = find_host_info(iso->host);
2229 if (hi != NULL) {
2230 list_for_each_entry(fi, &hi->file_info_list, list) {
2231 if (fi->iso_handle == iso)
2232 queue_rawiso_event(fi);
2236 spin_unlock_irqrestore(&host_info_lock, flags);
2239 /* helper function - gather all the kernel iso status bits for returning to user-space */
2240 static void raw1394_iso_fill_status(struct hpsb_iso *iso, struct raw1394_iso_status *stat)
2242 stat->config.data_buf_size = iso->buf_size;
2243 stat->config.buf_packets = iso->buf_packets;
2244 stat->config.channel = iso->channel;
2245 stat->config.speed = iso->speed;
2246 stat->config.irq_interval = iso->irq_interval;
2247 stat->n_packets = hpsb_iso_n_ready(iso);
2248 stat->overflows = atomic_read(&iso->overflows);
2249 stat->xmit_cycle = iso->xmit_cycle;
2252 static int raw1394_iso_xmit_init(struct file_info *fi, void __user *uaddr)
2254 struct raw1394_iso_status stat;
2256 if (!fi->host)
2257 return -EINVAL;
2259 if (copy_from_user(&stat, uaddr, sizeof(stat)))
2260 return -EFAULT;
2262 fi->iso_handle = hpsb_iso_xmit_init(fi->host,
2263 stat.config.data_buf_size,
2264 stat.config.buf_packets,
2265 stat.config.channel,
2266 stat.config.speed,
2267 stat.config.irq_interval,
2268 rawiso_activity_cb);
2269 if (!fi->iso_handle)
2270 return -ENOMEM;
2272 fi->iso_state = RAW1394_ISO_XMIT;
2274 raw1394_iso_fill_status(fi->iso_handle, &stat);
2275 if (copy_to_user(uaddr, &stat, sizeof(stat)))
2276 return -EFAULT;
2278 /* queue an event to get things started */
2279 rawiso_activity_cb(fi->iso_handle);
2281 return 0;
2284 static int raw1394_iso_recv_init(struct file_info *fi, void __user *uaddr)
2286 struct raw1394_iso_status stat;
2288 if (!fi->host)
2289 return -EINVAL;
2291 if (copy_from_user(&stat, uaddr, sizeof(stat)))
2292 return -EFAULT;
2294 fi->iso_handle = hpsb_iso_recv_init(fi->host,
2295 stat.config.data_buf_size,
2296 stat.config.buf_packets,
2297 stat.config.channel,
2298 stat.config.dma_mode,
2299 stat.config.irq_interval,
2300 rawiso_activity_cb);
2301 if (!fi->iso_handle)
2302 return -ENOMEM;
2304 fi->iso_state = RAW1394_ISO_RECV;
2306 raw1394_iso_fill_status(fi->iso_handle, &stat);
2307 if (copy_to_user(uaddr, &stat, sizeof(stat)))
2308 return -EFAULT;
2309 return 0;
2312 static int raw1394_iso_get_status(struct file_info *fi, void __user *uaddr)
2314 struct raw1394_iso_status stat;
2315 struct hpsb_iso *iso = fi->iso_handle;
2317 raw1394_iso_fill_status(fi->iso_handle, &stat);
2318 if (copy_to_user(uaddr, &stat, sizeof(stat)))
2319 return -EFAULT;
2321 /* reset overflow counter */
2322 atomic_set(&iso->overflows, 0);
2324 return 0;
2327 /* copy N packet_infos out of the ringbuffer into user-supplied array */
2328 static int raw1394_iso_recv_packets(struct file_info *fi, void __user *uaddr)
2330 struct raw1394_iso_packets upackets;
2331 unsigned int packet = fi->iso_handle->first_packet;
2332 int i;
2334 if (copy_from_user(&upackets, uaddr, sizeof(upackets)))
2335 return -EFAULT;
2337 if (upackets.n_packets > hpsb_iso_n_ready(fi->iso_handle))
2338 return -EINVAL;
2340 /* ensure user-supplied buffer is accessible and big enough */
2341 if (verify_area(VERIFY_WRITE, upackets.infos,
2342 upackets.n_packets * sizeof(struct raw1394_iso_packet_info)))
2343 return -EFAULT;
2345 /* copy the packet_infos out */
2346 for (i = 0; i < upackets.n_packets; i++) {
2347 if (__copy_to_user(&upackets.infos[i],
2348 &fi->iso_handle->infos[packet],
2349 sizeof(struct raw1394_iso_packet_info)))
2350 return -EFAULT;
2352 packet = (packet + 1) % fi->iso_handle->buf_packets;
2355 return 0;
2358 /* copy N packet_infos from user to ringbuffer, and queue them for transmission */
2359 static int raw1394_iso_send_packets(struct file_info *fi, void __user *uaddr)
2361 struct raw1394_iso_packets upackets;
2362 int i, rv;
2364 if (copy_from_user(&upackets, uaddr, sizeof(upackets)))
2365 return -EFAULT;
2367 if (upackets.n_packets > hpsb_iso_n_ready(fi->iso_handle))
2368 return -EINVAL;
2370 /* ensure user-supplied buffer is accessible and big enough */
2371 if (verify_area(VERIFY_READ, upackets.infos,
2372 upackets.n_packets * sizeof(struct raw1394_iso_packet_info)))
2373 return -EFAULT;
2375 /* copy the infos structs in and queue the packets */
2376 for (i = 0; i < upackets.n_packets; i++) {
2377 struct raw1394_iso_packet_info info;
2379 if (__copy_from_user(&info, &upackets.infos[i],
2380 sizeof(struct raw1394_iso_packet_info)))
2381 return -EFAULT;
2383 rv = hpsb_iso_xmit_queue_packet(fi->iso_handle, info.offset,
2384 info.len, info.tag, info.sy);
2385 if (rv)
2386 return rv;
2389 return 0;
2392 static void raw1394_iso_shutdown(struct file_info *fi)
2394 if (fi->iso_handle)
2395 hpsb_iso_shutdown(fi->iso_handle);
2397 fi->iso_handle = NULL;
2398 fi->iso_state = RAW1394_ISO_INACTIVE;
2401 /* mmap the rawiso xmit/recv buffer */
2402 static int raw1394_mmap(struct file *file, struct vm_area_struct *vma)
2404 struct file_info *fi = file->private_data;
2406 if (fi->iso_state == RAW1394_ISO_INACTIVE)
2407 return -EINVAL;
2409 return dma_region_mmap(&fi->iso_handle->data_buf, file, vma);
2412 /* ioctl is only used for rawiso operations */
2413 static int raw1394_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)
2415 struct file_info *fi = file->private_data;
2416 void __user *argp = (void __user *)arg;
2418 switch(fi->iso_state) {
2419 case RAW1394_ISO_INACTIVE:
2420 switch(cmd) {
2421 case RAW1394_IOC_ISO_XMIT_INIT:
2422 return raw1394_iso_xmit_init(fi, argp);
2423 case RAW1394_IOC_ISO_RECV_INIT:
2424 return raw1394_iso_recv_init(fi, argp);
2425 default:
2426 break;
2428 break;
2429 case RAW1394_ISO_RECV:
2430 switch(cmd) {
2431 case RAW1394_IOC_ISO_RECV_START: {
2432 /* copy args from user-space */
2433 int args[3];
2434 if (copy_from_user(&args[0], argp, sizeof(args)))
2435 return -EFAULT;
2436 return hpsb_iso_recv_start(fi->iso_handle, args[0], args[1], args[2]);
2438 case RAW1394_IOC_ISO_XMIT_RECV_STOP:
2439 hpsb_iso_stop(fi->iso_handle);
2440 return 0;
2441 case RAW1394_IOC_ISO_RECV_LISTEN_CHANNEL:
2442 return hpsb_iso_recv_listen_channel(fi->iso_handle, arg);
2443 case RAW1394_IOC_ISO_RECV_UNLISTEN_CHANNEL:
2444 return hpsb_iso_recv_unlisten_channel(fi->iso_handle, arg);
2445 case RAW1394_IOC_ISO_RECV_SET_CHANNEL_MASK: {
2446 /* copy the u64 from user-space */
2447 u64 mask;
2448 if (copy_from_user(&mask, argp, sizeof(mask)))
2449 return -EFAULT;
2450 return hpsb_iso_recv_set_channel_mask(fi->iso_handle, mask);
2452 case RAW1394_IOC_ISO_GET_STATUS:
2453 return raw1394_iso_get_status(fi, argp);
2454 case RAW1394_IOC_ISO_RECV_PACKETS:
2455 return raw1394_iso_recv_packets(fi, argp);
2456 case RAW1394_IOC_ISO_RECV_RELEASE_PACKETS:
2457 return hpsb_iso_recv_release_packets(fi->iso_handle, arg);
2458 case RAW1394_IOC_ISO_RECV_FLUSH:
2459 return hpsb_iso_recv_flush(fi->iso_handle);
2460 case RAW1394_IOC_ISO_SHUTDOWN:
2461 raw1394_iso_shutdown(fi);
2462 return 0;
2463 case RAW1394_IOC_ISO_QUEUE_ACTIVITY:
2464 queue_rawiso_event(fi);
2465 return 0;
2467 break;
2468 case RAW1394_ISO_XMIT:
2469 switch(cmd) {
2470 case RAW1394_IOC_ISO_XMIT_START: {
2471 /* copy two ints from user-space */
2472 int args[2];
2473 if (copy_from_user(&args[0], argp, sizeof(args)))
2474 return -EFAULT;
2475 return hpsb_iso_xmit_start(fi->iso_handle, args[0], args[1]);
2477 case RAW1394_IOC_ISO_XMIT_SYNC:
2478 return hpsb_iso_xmit_sync(fi->iso_handle);
2479 case RAW1394_IOC_ISO_XMIT_RECV_STOP:
2480 hpsb_iso_stop(fi->iso_handle);
2481 return 0;
2482 case RAW1394_IOC_ISO_GET_STATUS:
2483 return raw1394_iso_get_status(fi, argp);
2484 case RAW1394_IOC_ISO_XMIT_PACKETS:
2485 return raw1394_iso_send_packets(fi, argp);
2486 case RAW1394_IOC_ISO_SHUTDOWN:
2487 raw1394_iso_shutdown(fi);
2488 return 0;
2489 case RAW1394_IOC_ISO_QUEUE_ACTIVITY:
2490 queue_rawiso_event(fi);
2491 return 0;
2493 break;
2494 default:
2495 break;
2498 return -EINVAL;
2501 static unsigned int raw1394_poll(struct file *file, poll_table *pt)
2503 struct file_info *fi = file->private_data;
2504 unsigned int mask = POLLOUT | POLLWRNORM;
2506 poll_wait(file, &fi->poll_wait_complete, pt);
2508 spin_lock_irq(&fi->reqlists_lock);
2509 if (!list_empty(&fi->req_complete)) {
2510 mask |= POLLIN | POLLRDNORM;
2512 spin_unlock_irq(&fi->reqlists_lock);
2514 return mask;
2517 static int raw1394_open(struct inode *inode, struct file *file)
2519 struct file_info *fi;
2521 fi = kmalloc(sizeof(struct file_info), SLAB_KERNEL);
2522 if (fi == NULL)
2523 return -ENOMEM;
2525 memset(fi, 0, sizeof(struct file_info));
2526 fi->notification = (u8) RAW1394_NOTIFY_ON; /* busreset notification */
2528 INIT_LIST_HEAD(&fi->list);
2529 fi->state = opened;
2530 INIT_LIST_HEAD(&fi->req_pending);
2531 INIT_LIST_HEAD(&fi->req_complete);
2532 sema_init(&fi->complete_sem, 0);
2533 spin_lock_init(&fi->reqlists_lock);
2534 init_waitqueue_head(&fi->poll_wait_complete);
2535 INIT_LIST_HEAD(&fi->addr_list);
2537 file->private_data = fi;
2539 return 0;
2542 static int raw1394_release(struct inode *inode, struct file *file)
2544 struct file_info *fi = file->private_data;
2545 struct list_head *lh;
2546 struct pending_request *req;
2547 int done = 0, i, fail = 0;
2548 int retval = 0;
2549 struct list_head *entry;
2550 struct arm_addr *addr = NULL;
2551 struct host_info *hi;
2552 struct file_info *fi_hlp = NULL;
2553 struct arm_addr *arm_addr = NULL;
2554 int another_host;
2555 int csr_mod = 0;
2557 if (fi->iso_state != RAW1394_ISO_INACTIVE)
2558 raw1394_iso_shutdown(fi);
2560 for (i = 0; i < 64; i++) {
2561 if (fi->listen_channels & (1ULL << i)) {
2562 hpsb_unlisten_channel(&raw1394_highlevel, fi->host, i);
2566 spin_lock_irq(&host_info_lock);
2567 fi->listen_channels = 0;
2568 spin_unlock_irq(&host_info_lock);
2570 fail = 0;
2571 /* set address-entries invalid */
2572 spin_lock_irq(&host_info_lock);
2574 while (!list_empty(&fi->addr_list)) {
2575 another_host = 0;
2576 lh = fi->addr_list.next;
2577 addr = list_entry(lh, struct arm_addr, addr_list);
2578 /* another host with valid address-entry containing
2579 same addressrange? */
2580 list_for_each_entry(hi, &host_info_list, list) {
2581 if (hi->host != fi->host) {
2582 list_for_each_entry(fi_hlp, &hi->file_info_list, list) {
2583 entry = fi_hlp->addr_list.next;
2584 while (entry != &(fi_hlp->addr_list)) {
2585 arm_addr = list_entry(entry,
2586 struct arm_addr, addr_list);
2587 if (arm_addr->start ==
2588 addr->start) {
2589 DBGMSG("raw1394_release: "
2590 "another host ownes "
2591 "same addressrange");
2592 another_host = 1;
2593 break;
2595 entry = entry->next;
2597 if (another_host) {
2598 break;
2603 if (!another_host) {
2604 DBGMSG("raw1394_release: call hpsb_arm_unregister");
2605 retval = hpsb_unregister_addrspace(&raw1394_highlevel, fi->host, addr->start);
2606 if (!retval) {
2607 ++fail;
2608 printk(KERN_ERR "raw1394_release arm_Unregister failed\n");
2611 DBGMSG("raw1394_release: delete addr_entry from list");
2612 list_del(&addr->addr_list);
2613 vfree(addr->addr_space_buffer);
2614 kfree(addr);
2615 } /* while */
2616 spin_unlock_irq(&host_info_lock);
2617 if (fail > 0) {
2618 printk(KERN_ERR "raw1394: during addr_list-release "
2619 "error(s) occurred \n");
2622 while (!done) {
2623 spin_lock_irq(&fi->reqlists_lock);
2625 while (!list_empty(&fi->req_complete)) {
2626 lh = fi->req_complete.next;
2627 list_del(lh);
2629 req = list_entry(lh, struct pending_request, list);
2631 free_pending_request(req);
2634 if (list_empty(&fi->req_pending)) done = 1;
2636 spin_unlock_irq(&fi->reqlists_lock);
2638 if (!done) down_interruptible(&fi->complete_sem);
2641 /* Remove any sub-trees left by user space programs */
2642 for (i = 0; i < RAW1394_MAX_USER_CSR_DIRS; i++) {
2643 struct csr1212_dentry *dentry;
2644 if (!fi->csr1212_dirs[i]) continue;
2645 for (dentry = fi->csr1212_dirs[i]->value.directory.dentries_head;
2646 dentry; dentry = dentry->next) {
2647 csr1212_detach_keyval_from_directory(fi->host->csr.rom->root_kv, dentry->kv);
2649 csr1212_release_keyval(fi->csr1212_dirs[i]);
2650 fi->csr1212_dirs[i] = NULL;
2651 csr_mod = 1;
2654 if ((csr_mod || fi->cfgrom_upd) && hpsb_update_config_rom_image(fi->host) < 0)
2655 HPSB_ERR("Failed to generate Configuration ROM image for host %d", fi->host->id);
2657 if (fi->state == connected) {
2658 spin_lock_irq(&host_info_lock);
2659 list_del(&fi->list);
2660 spin_unlock_irq(&host_info_lock);
2662 put_device(&fi->host->device);
2665 kfree(fi);
2667 return 0;
2671 /*** HOTPLUG STUFF **********************************************************/
2673 * Export information about protocols/devices supported by this driver.
2675 static struct ieee1394_device_id raw1394_id_table[] = {
2677 .match_flags = IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION,
2678 .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff,
2679 .version = AVC_SW_VERSION_ENTRY & 0xffffff
2682 .match_flags = IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION,
2683 .specifier_id = CAMERA_UNIT_SPEC_ID_ENTRY & 0xffffff,
2684 .version = CAMERA_SW_VERSION_ENTRY & 0xffffff
2689 MODULE_DEVICE_TABLE(ieee1394, raw1394_id_table);
2691 static struct hpsb_protocol_driver raw1394_driver = {
2692 .name = "raw1394 Driver",
2693 .id_table = raw1394_id_table,
2694 .driver = {
2695 .name = "raw1394",
2696 .bus = &ieee1394_bus_type,
2701 /******************************************************************************/
2704 static struct hpsb_highlevel raw1394_highlevel = {
2705 .name = RAW1394_DEVICE_NAME,
2706 .add_host = add_host,
2707 .remove_host = remove_host,
2708 .host_reset = host_reset,
2709 .iso_receive = iso_receive,
2710 .fcp_request = fcp_request,
2713 static struct cdev raw1394_cdev;
2714 static struct file_operations raw1394_fops = {
2715 .owner = THIS_MODULE,
2716 .read = raw1394_read,
2717 .write = raw1394_write,
2718 .mmap = raw1394_mmap,
2719 .ioctl = raw1394_ioctl,
2720 .poll = raw1394_poll,
2721 .open = raw1394_open,
2722 .release = raw1394_release,
2725 static int __init init_raw1394(void)
2727 int ret;
2729 hpsb_register_highlevel(&raw1394_highlevel);
2731 devfs_mk_cdev(MKDEV(IEEE1394_MAJOR, IEEE1394_MINOR_BLOCK_RAW1394 * 16),
2732 S_IFCHR | S_IRUSR | S_IWUSR, RAW1394_DEVICE_NAME);
2734 cdev_init(&raw1394_cdev, &raw1394_fops);
2735 raw1394_cdev.owner = THIS_MODULE;
2736 kobject_set_name(&raw1394_cdev.kobj, RAW1394_DEVICE_NAME);
2737 ret = cdev_add(&raw1394_cdev, IEEE1394_RAW1394_DEV, 1);
2738 if (ret) {
2739 HPSB_ERR("raw1394 failed to register minor device block");
2740 devfs_remove(RAW1394_DEVICE_NAME);
2741 hpsb_unregister_highlevel(&raw1394_highlevel);
2742 return ret;
2745 HPSB_INFO("raw1394: /dev/%s device initialized", RAW1394_DEVICE_NAME);
2747 ret = hpsb_register_protocol(&raw1394_driver);
2748 if (ret) {
2749 HPSB_ERR("raw1394: failed to register protocol");
2750 cdev_del(&raw1394_cdev);
2751 devfs_remove(RAW1394_DEVICE_NAME);
2752 hpsb_unregister_highlevel(&raw1394_highlevel);
2753 return ret;
2756 return 0;
2759 static void __exit cleanup_raw1394(void)
2761 hpsb_unregister_protocol(&raw1394_driver);
2762 cdev_del(&raw1394_cdev);
2763 devfs_remove(RAW1394_DEVICE_NAME);
2764 hpsb_unregister_highlevel(&raw1394_highlevel);
2767 module_init(init_raw1394);
2768 module_exit(cleanup_raw1394);
2769 MODULE_LICENSE("GPL");
2770 MODULE_ALIAS_CHARDEV(IEEE1394_MAJOR, IEEE1394_MINOR_BLOCK_RAW1394 * 16);