Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/ieee1394...
authorLinus Torvalds <torvalds@linux-foundation.org>
Thu, 27 May 2010 17:22:06 +0000 (10:22 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Thu, 27 May 2010 17:22:06 +0000 (10:22 -0700)
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/ieee1394/linux1394-2.6:
  ieee1394: schedule for removal
  firewire: core: use separate timeout for each transaction
  firewire: core: Fix tlabel exhaustion problem
  firewire: core: make transaction label allocation more robust
  firewire: core: clean up config ROM related defined constants
  ieee1394: mark char device files as not seekable
  firewire: cdev: mark char device files as not seekable
  firewire: ohci: cleanups and fix for nonstandard build without debug facility
  firewire: ohci: wait for PHY register accesses to complete
  firewire: ohci: fix up configuration of TI chips
  firewire: ohci: enable 1394a enhancements
  firewire: ohci: do not clear PHY interrupt status inadvertently
  firewire: ohci: add a function for reading PHY registers

Trivial conflicts in Documentation/feature-removal-schedule.txt

Documentation/feature-removal-schedule.txt
drivers/firewire/core-card.c
drivers/firewire/core-cdev.c
drivers/firewire/core-transaction.c
drivers/firewire/core.h
drivers/firewire/ohci.c
drivers/firewire/ohci.h
drivers/ieee1394/dv1394.c
drivers/ieee1394/raw1394.c
drivers/ieee1394/video1394.c
include/linux/firewire.h

index a86152a..672be01 100644 (file)
@@ -646,3 +646,13 @@ Who:       Thomas Gleixner <tglx@linutronix.de>
 
 ----------------------------
 
+What:  old ieee1394 subsystem (CONFIG_IEEE1394)
+When:  2.6.37
+Files: drivers/ieee1394/ except init_ohci1394_dma.c
+Why:   superseded by drivers/firewire/ (CONFIG_FIREWIRE) which offers more
+       features, better performance, and better security, all with smaller
+       and more modern code base
+Who:   Stefan Richter <stefanr@s5r6.in-berlin.de>
+
+----------------------------
+
index 5045156..9dcb304 100644 (file)
@@ -30,7 +30,6 @@
 #include <linux/module.h>
 #include <linux/mutex.h>
 #include <linux/spinlock.h>
-#include <linux/timer.h>
 #include <linux/workqueue.h>
 
 #include <asm/atomic.h>
@@ -63,7 +62,7 @@ static size_t config_rom_length = 1 + 4 + 1 + 1;
 #define BIB_CRC(v)             ((v) <<  0)
 #define BIB_CRC_LENGTH(v)      ((v) << 16)
 #define BIB_INFO_LENGTH(v)     ((v) << 24)
-
+#define BIB_BUS_NAME           0x31333934 /* "1394" */
 #define BIB_LINK_SPEED(v)      ((v) <<  0)
 #define BIB_GENERATION(v)      ((v) <<  4)
 #define BIB_MAX_ROM(v)         ((v) <<  8)
@@ -73,7 +72,8 @@ static size_t config_rom_length = 1 + 4 + 1 + 1;
 #define BIB_BMC                        ((1) << 28)
 #define BIB_ISC                        ((1) << 29)
 #define BIB_CMC                        ((1) << 30)
-#define BIB_IMC                        ((1) << 31)
+#define BIB_IRMC               ((1) << 31)
+#define NODE_CAPABILITIES      0x0c0083c0 /* per IEEE 1394 clause 8.3.2.6.5.2 */
 
 static void generate_config_rom(struct fw_card *card, __be32 *config_rom)
 {
@@ -91,18 +91,18 @@ static void generate_config_rom(struct fw_card *card, __be32 *config_rom)
 
        config_rom[0] = cpu_to_be32(
                BIB_CRC_LENGTH(4) | BIB_INFO_LENGTH(4) | BIB_CRC(0));
-       config_rom[1] = cpu_to_be32(0x31333934);
+       config_rom[1] = cpu_to_be32(BIB_BUS_NAME);
        config_rom[2] = cpu_to_be32(
                BIB_LINK_SPEED(card->link_speed) |
                BIB_GENERATION(card->config_rom_generation++ % 14 + 2) |
                BIB_MAX_ROM(2) |
                BIB_MAX_RECEIVE(card->max_receive) |
-               BIB_BMC | BIB_ISC | BIB_CMC | BIB_IMC);
+               BIB_BMC | BIB_ISC | BIB_CMC | BIB_IRMC);
        config_rom[3] = cpu_to_be32(card->guid >> 32);
        config_rom[4] = cpu_to_be32(card->guid);
 
        /* Generate root directory. */
-       config_rom[6] = cpu_to_be32(0x0c0083c0); /* node capabilities */
+       config_rom[6] = cpu_to_be32(NODE_CAPABILITIES);
        i = 7;
        j = 7 + descriptor_count;
 
@@ -407,13 +407,6 @@ static void fw_card_bm_work(struct work_struct *work)
        fw_card_put(card);
 }
 
-static void flush_timer_callback(unsigned long data)
-{
-       struct fw_card *card = (struct fw_card *)data;
-
-       fw_flush_transactions(card);
-}
-
 void fw_card_initialize(struct fw_card *card,
                        const struct fw_card_driver *driver,
                        struct device *device)
@@ -432,8 +425,6 @@ void fw_card_initialize(struct fw_card *card,
        init_completion(&card->done);
        INIT_LIST_HEAD(&card->transaction_list);
        spin_lock_init(&card->lock);
-       setup_timer(&card->flush_timer,
-                   flush_timer_callback, (unsigned long)card);
 
        card->local_node = NULL;
 
@@ -558,7 +549,6 @@ void fw_core_remove_card(struct fw_card *card)
        wait_for_completion(&card->done);
 
        WARN_ON(!list_empty(&card->transaction_list));
-       del_timer_sync(&card->flush_timer);
 }
 EXPORT_SYMBOL(fw_core_remove_card);
 
index 14a34d9..5bf106b 100644 (file)
@@ -227,7 +227,7 @@ static int fw_device_op_open(struct inode *inode, struct file *file)
        list_add_tail(&client->link, &device->client_list);
        mutex_unlock(&device->client_list_mutex);
 
-       return 0;
+       return nonseekable_open(inode, file);
 }
 
 static void queue_event(struct client *client, struct event *event,
@@ -1496,13 +1496,13 @@ static unsigned int fw_device_op_poll(struct file *file, poll_table * pt)
 
 const struct file_operations fw_device_ops = {
        .owner          = THIS_MODULE,
+       .llseek         = no_llseek,
        .open           = fw_device_op_open,
        .read           = fw_device_op_read,
        .unlocked_ioctl = fw_device_op_ioctl,
-       .poll           = fw_device_op_poll,
-       .release        = fw_device_op_release,
        .mmap           = fw_device_op_mmap,
-
+       .release        = fw_device_op_release,
+       .poll           = fw_device_op_poll,
 #ifdef CONFIG_COMPAT
        .compat_ioctl   = fw_device_op_compat_ioctl,
 #endif
index 673b03f..fdc33ff 100644 (file)
@@ -81,7 +81,7 @@ static int close_transaction(struct fw_transaction *transaction,
        spin_lock_irqsave(&card->lock, flags);
        list_for_each_entry(t, &card->transaction_list, link) {
                if (t == transaction) {
-                       list_del(&t->link);
+                       list_del_init(&t->link);
                        card->tlabel_mask &= ~(1ULL << t->tlabel);
                        break;
                }
@@ -89,6 +89,7 @@ static int close_transaction(struct fw_transaction *transaction,
        spin_unlock_irqrestore(&card->lock, flags);
 
        if (&t->link != &card->transaction_list) {
+               del_timer_sync(&t->split_timeout_timer);
                t->callback(card, rcode, NULL, 0, t->callback_data);
                return 0;
        }
@@ -121,6 +122,31 @@ int fw_cancel_transaction(struct fw_card *card,
 }
 EXPORT_SYMBOL(fw_cancel_transaction);
 
+static void split_transaction_timeout_callback(unsigned long data)
+{
+       struct fw_transaction *t = (struct fw_transaction *)data;
+       struct fw_card *card = t->card;
+       unsigned long flags;
+
+       spin_lock_irqsave(&card->lock, flags);
+       if (list_empty(&t->link)) {
+               spin_unlock_irqrestore(&card->lock, flags);
+               return;
+       }
+       list_del(&t->link);
+       card->tlabel_mask &= ~(1ULL << t->tlabel);
+       spin_unlock_irqrestore(&card->lock, flags);
+
+       card->driver->cancel_packet(card, &t->packet);
+
+       /*
+        * At this point cancel_packet will never call the transaction
+        * callback, since we just took the transaction out of the list.
+        * So do it here.
+        */
+       t->callback(card, RCODE_CANCELLED, NULL, 0, t->callback_data);
+}
+
 static void transmit_complete_callback(struct fw_packet *packet,
                                       struct fw_card *card, int status)
 {
@@ -229,6 +255,23 @@ static void fw_fill_request(struct fw_packet *packet, int tcode, int tlabel,
        packet->payload_mapped = false;
 }
 
+static int allocate_tlabel(struct fw_card *card)
+{
+       int tlabel;
+
+       tlabel = card->current_tlabel;
+       while (card->tlabel_mask & (1ULL << tlabel)) {
+               tlabel = (tlabel + 1) & 0x3f;
+               if (tlabel == card->current_tlabel)
+                       return -EBUSY;
+       }
+
+       card->current_tlabel = (tlabel + 1) & 0x3f;
+       card->tlabel_mask |= 1ULL << tlabel;
+
+       return tlabel;
+}
+
 /**
  * This function provides low-level access to the IEEE1394 transaction
  * logic.  Most C programs would use either fw_read(), fw_write() or
@@ -276,13 +319,6 @@ void fw_send_request(struct fw_card *card, struct fw_transaction *t, int tcode,
        unsigned long flags;
        int tlabel;
 
-       /*
-        * Bump the flush timer up 100ms first of all so we
-        * don't race with a flush timer callback.
-        */
-
-       mod_timer(&card->flush_timer, jiffies + DIV_ROUND_UP(HZ, 10));
-
        /*
         * Allocate tlabel from the bitmap and put the transaction on
         * the list while holding the card spinlock.
@@ -290,18 +326,20 @@ void fw_send_request(struct fw_card *card, struct fw_transaction *t, int tcode,
 
        spin_lock_irqsave(&card->lock, flags);
 
-       tlabel = card->current_tlabel;
-       if (card->tlabel_mask & (1ULL << tlabel)) {
+       tlabel = allocate_tlabel(card);
+       if (tlabel < 0) {
                spin_unlock_irqrestore(&card->lock, flags);
                callback(card, RCODE_SEND_ERROR, NULL, 0, callback_data);
                return;
        }
 
-       card->current_tlabel = (card->current_tlabel + 1) & 0x3f;
-       card->tlabel_mask |= (1ULL << tlabel);
-
        t->node_id = destination_id;
        t->tlabel = tlabel;
+       t->card = card;
+       setup_timer(&t->split_timeout_timer,
+                   split_transaction_timeout_callback, (unsigned long)t);
+       /* FIXME: start this timer later, relative to t->timestamp */
+       mod_timer(&t->split_timeout_timer, jiffies + DIV_ROUND_UP(HZ, 10));
        t->callback = callback;
        t->callback_data = callback_data;
 
@@ -347,11 +385,13 @@ int fw_run_transaction(struct fw_card *card, int tcode, int destination_id,
        struct transaction_callback_data d;
        struct fw_transaction t;
 
+       init_timer_on_stack(&t.split_timeout_timer);
        init_completion(&d.done);
        d.payload = payload;
        fw_send_request(card, &t, tcode, destination_id, generation, speed,
                        offset, payload, length, transaction_callback, &d);
        wait_for_completion(&d.done);
+       destroy_timer_on_stack(&t.split_timeout_timer);
 
        return d.rcode;
 }
@@ -394,30 +434,6 @@ void fw_send_phy_config(struct fw_card *card,
        mutex_unlock(&phy_config_mutex);
 }
 
-void fw_flush_transactions(struct fw_card *card)
-{
-       struct fw_transaction *t, *next;
-       struct list_head list;
-       unsigned long flags;
-
-       INIT_LIST_HEAD(&list);
-       spin_lock_irqsave(&card->lock, flags);
-       list_splice_init(&card->transaction_list, &list);
-       card->tlabel_mask = 0;
-       spin_unlock_irqrestore(&card->lock, flags);
-
-       list_for_each_entry_safe(t, next, &list, link) {
-               card->driver->cancel_packet(card, &t->packet);
-
-               /*
-                * At this point cancel_packet will never call the
-                * transaction callback, since we just took all the
-                * transactions out of the list.  So do it here.
-                */
-               t->callback(card, RCODE_CANCELLED, NULL, 0, t->callback_data);
-       }
-}
-
 static struct fw_address_handler *lookup_overlapping_address_handler(
        struct list_head *list, unsigned long long offset, size_t length)
 {
@@ -827,8 +843,8 @@ void fw_core_handle_response(struct fw_card *card, struct fw_packet *p)
        spin_lock_irqsave(&card->lock, flags);
        list_for_each_entry(t, &card->transaction_list, link) {
                if (t->node_id == source && t->tlabel == tlabel) {
-                       list_del(&t->link);
-                       card->tlabel_mask &= ~(1 << t->tlabel);
+                       list_del_init(&t->link);
+                       card->tlabel_mask &= ~(1ULL << t->tlabel);
                        break;
                }
        }
@@ -869,6 +885,8 @@ void fw_core_handle_response(struct fw_card *card, struct fw_packet *p)
                break;
        }
 
+       del_timer_sync(&t->split_timeout_timer);
+
        /*
         * The response handler may be executed while the request handler
         * is still pending.  Cancel the request handler.
index fb03213..0ecfcd9 100644 (file)
@@ -27,7 +27,12 @@ struct fw_packet;
 #define PHY_LINK_ACTIVE                0x80
 #define PHY_CONTENDER          0x40
 #define PHY_BUS_RESET          0x40
+#define PHY_EXTENDED_REGISTERS 0xe0
 #define PHY_BUS_SHORT_RESET    0x40
+#define PHY_INT_STATUS_BITS    0x3c
+#define PHY_ENABLE_ACCEL       0x02
+#define PHY_ENABLE_MULTI       0x01
+#define PHY_PAGE_SELECT                0xe0
 
 #define BANDWIDTH_AVAILABLE_INITIAL    4915
 #define BROADCAST_CHANNEL_INITIAL      (1 << 31 | 31)
@@ -215,7 +220,6 @@ void fw_core_handle_request(struct fw_card *card, struct fw_packet *request);
 void fw_core_handle_response(struct fw_card *card, struct fw_packet *packet);
 void fw_fill_response(struct fw_packet *response, u32 *request_header,
                      int rcode, void *payload, size_t length);
-void fw_flush_transactions(struct fw_card *card);
 void fw_send_phy_config(struct fw_card *card,
                        int node_id, int generation, int gap_count);
 
index a3b083a..9f627e7 100644 (file)
@@ -236,13 +236,15 @@ static char ohci_driver_name[] = KBUILD_MODNAME;
 #define QUIRK_CYCLE_TIMER              1
 #define QUIRK_RESET_PACKET             2
 #define QUIRK_BE_HEADERS               4
+#define QUIRK_NO_1394A                 8
 
 /* In case of multiple matches in ohci_quirks[], only the first one is used. */
 static const struct {
        unsigned short vendor, device, flags;
 } ohci_quirks[] = {
        {PCI_VENDOR_ID_TI,      PCI_DEVICE_ID_TI_TSB12LV22, QUIRK_CYCLE_TIMER |
-                                                           QUIRK_RESET_PACKET},
+                                                           QUIRK_RESET_PACKET |
+                                                           QUIRK_NO_1394A},
        {PCI_VENDOR_ID_TI,      PCI_ANY_ID,     QUIRK_RESET_PACKET},
        {PCI_VENDOR_ID_AL,      PCI_ANY_ID,     QUIRK_CYCLE_TIMER},
        {PCI_VENDOR_ID_NEC,     PCI_ANY_ID,     QUIRK_CYCLE_TIMER},
@@ -257,15 +259,16 @@ MODULE_PARM_DESC(quirks, "Chip quirks (default = 0"
        ", nonatomic cycle timer = "    __stringify(QUIRK_CYCLE_TIMER)
        ", reset packet generation = "  __stringify(QUIRK_RESET_PACKET)
        ", AR/selfID endianess = "      __stringify(QUIRK_BE_HEADERS)
+       ", no 1394a enhancements = "    __stringify(QUIRK_NO_1394A)
        ")");
 
-#ifdef CONFIG_FIREWIRE_OHCI_DEBUG
-
 #define OHCI_PARAM_DEBUG_AT_AR         1
 #define OHCI_PARAM_DEBUG_SELFIDS       2
 #define OHCI_PARAM_DEBUG_IRQS          4
 #define OHCI_PARAM_DEBUG_BUSRESETS     8 /* only effective before chip init */
 
+#ifdef CONFIG_FIREWIRE_OHCI_DEBUG
+
 static int param_debug;
 module_param_named(debug, param_debug, int, 0644);
 MODULE_PARM_DESC(debug, "Verbose logging (default = 0"
@@ -438,9 +441,10 @@ static void log_ar_at_event(char dir, int speed, u32 *header, int evt)
 
 #else
 
-#define log_irqs(evt)
-#define log_selfids(node_id, generation, self_id_count, sid)
-#define log_ar_at_event(dir, speed, header, evt)
+#define param_debug 0
+static inline void log_irqs(u32 evt) {}
+static inline void log_selfids(int node_id, int generation, int self_id_count, u32 *s) {}
+static inline void log_ar_at_event(char dir, int speed, u32 *header, int evt) {}
 
 #endif /* CONFIG_FIREWIRE_OHCI_DEBUG */
 
@@ -460,27 +464,71 @@ static inline void flush_writes(const struct fw_ohci *ohci)
        reg_read(ohci, OHCI1394_Version);
 }
 
-static int ohci_update_phy_reg(struct fw_card *card, int addr,
-                              int clear_bits, int set_bits)
+static int read_phy_reg(struct fw_ohci *ohci, int addr)
 {
-       struct fw_ohci *ohci = fw_ohci(card);
-       u32 val, old;
+       u32 val;
+       int i;
 
        reg_write(ohci, OHCI1394_PhyControl, OHCI1394_PhyControl_Read(addr));
-       flush_writes(ohci);
-       msleep(2);
-       val = reg_read(ohci, OHCI1394_PhyControl);
-       if ((val & OHCI1394_PhyControl_ReadDone) == 0) {
-               fw_error("failed to set phy reg bits.\n");
-               return -EBUSY;
+       for (i = 0; i < 10; i++) {
+               val = reg_read(ohci, OHCI1394_PhyControl);
+               if (val & OHCI1394_PhyControl_ReadDone)
+                       return OHCI1394_PhyControl_ReadData(val);
+
+               msleep(1);
        }
+       fw_error("failed to read phy reg\n");
+
+       return -EBUSY;
+}
+
+static int write_phy_reg(const struct fw_ohci *ohci, int addr, u32 val)
+{
+       int i;
 
-       old = OHCI1394_PhyControl_ReadData(val);
-       old = (old & ~clear_bits) | set_bits;
        reg_write(ohci, OHCI1394_PhyControl,
-                 OHCI1394_PhyControl_Write(addr, old));
+                 OHCI1394_PhyControl_Write(addr, val));
+       for (i = 0; i < 100; i++) {
+               val = reg_read(ohci, OHCI1394_PhyControl);
+               if (!(val & OHCI1394_PhyControl_WritePending))
+                       return 0;
 
-       return 0;
+               msleep(1);
+       }
+       fw_error("failed to write phy reg\n");
+
+       return -EBUSY;
+}
+
+static int ohci_update_phy_reg(struct fw_card *card, int addr,
+                              int clear_bits, int set_bits)
+{
+       struct fw_ohci *ohci = fw_ohci(card);
+       int ret;
+
+       ret = read_phy_reg(ohci, addr);
+       if (ret < 0)
+               return ret;
+
+       /*
+        * The interrupt status bits are cleared by writing a one bit.
+        * Avoid clearing them unless explicitly requested in set_bits.
+        */
+       if (addr == 5)
+               clear_bits |= PHY_INT_STATUS_BITS;
+
+       return write_phy_reg(ohci, addr, (ret & ~clear_bits) | set_bits);
+}
+
+static int read_paged_phy_reg(struct fw_ohci *ohci, int page, int addr)
+{
+       int ret;
+
+       ret = ohci_update_phy_reg(&ohci->card, 7, PHY_PAGE_SELECT, page << 5);
+       if (ret < 0)
+               return ret;
+
+       return read_phy_reg(ohci, addr);
 }
 
 static int ar_context_add_page(struct ar_context *ctx)
@@ -1495,13 +1543,64 @@ static void copy_config_rom(__be32 *dest, const __be32 *src, size_t length)
                memset(&dest[length], 0, CONFIG_ROM_SIZE - size);
 }
 
+static int configure_1394a_enhancements(struct fw_ohci *ohci)
+{
+       bool enable_1394a;
+       int ret, clear, set, offset;
+
+       /* Check if the driver should configure link and PHY. */
+       if (!(reg_read(ohci, OHCI1394_HCControlSet) &
+             OHCI1394_HCControl_programPhyEnable))
+               return 0;
+
+       /* Paranoia: check whether the PHY supports 1394a, too. */
+       enable_1394a = false;
+       ret = read_phy_reg(ohci, 2);
+       if (ret < 0)
+               return ret;
+       if ((ret & PHY_EXTENDED_REGISTERS) == PHY_EXTENDED_REGISTERS) {
+               ret = read_paged_phy_reg(ohci, 1, 8);
+               if (ret < 0)
+                       return ret;
+               if (ret >= 1)
+                       enable_1394a = true;
+       }
+
+       if (ohci->quirks & QUIRK_NO_1394A)
+               enable_1394a = false;
+
+       /* Configure PHY and link consistently. */
+       if (enable_1394a) {
+               clear = 0;
+               set = PHY_ENABLE_ACCEL | PHY_ENABLE_MULTI;
+       } else {
+               clear = PHY_ENABLE_ACCEL | PHY_ENABLE_MULTI;
+               set = 0;
+       }
+       ret = ohci_update_phy_reg(&ohci->card, 5, clear, set);
+       if (ret < 0)
+               return ret;
+
+       if (enable_1394a)
+               offset = OHCI1394_HCControlSet;
+       else
+               offset = OHCI1394_HCControlClear;
+       reg_write(ohci, offset, OHCI1394_HCControl_aPhyEnhanceEnable);
+
+       /* Clean up: configuration has been taken care of. */
+       reg_write(ohci, OHCI1394_HCControlClear,
+                 OHCI1394_HCControl_programPhyEnable);
+
+       return 0;
+}
+
 static int ohci_enable(struct fw_card *card,
                       const __be32 *config_rom, size_t length)
 {
        struct fw_ohci *ohci = fw_ohci(card);
        struct pci_dev *dev = to_pci_dev(card->device);
        u32 lps;
-       int i;
+       int i, ret;
 
        if (software_reset(ohci)) {
                fw_error("Failed to reset ohci card.\n");
@@ -1565,10 +1664,14 @@ static int ohci_enable(struct fw_card *card,
        if (param_debug & OHCI_PARAM_DEBUG_BUSRESETS)
                reg_write(ohci, OHCI1394_IntMaskSet, OHCI1394_busReset);
 
+       ret = configure_1394a_enhancements(ohci);
+       if (ret < 0)
+               return ret;
+
        /* Activate link_on bit and contender bit in our self ID packets.*/
-       if (ohci_update_phy_reg(card, 4, 0,
-                               PHY_LINK_ACTIVE | PHY_CONTENDER) < 0)
-               return -EIO;
+       ret = ohci_update_phy_reg(card, 4, 0, PHY_LINK_ACTIVE | PHY_CONTENDER);
+       if (ret < 0)
+               return ret;
 
        /*
         * When the link is not yet enabled, the atomic config rom
@@ -2304,7 +2407,7 @@ static const struct fw_card_driver ohci_driver = {
 };
 
 #ifdef CONFIG_PPC_PMAC
-static void ohci_pmac_on(struct pci_dev *dev)
+static void pmac_ohci_on(struct pci_dev *dev)
 {
        if (machine_is(powermac)) {
                struct device_node *ofn = pci_device_to_OF_node(dev);
@@ -2316,7 +2419,7 @@ static void ohci_pmac_on(struct pci_dev *dev)
        }
 }
 
-static void ohci_pmac_off(struct pci_dev *dev)
+static void pmac_ohci_off(struct pci_dev *dev)
 {
        if (machine_is(powermac)) {
                struct device_node *ofn = pci_device_to_OF_node(dev);
@@ -2328,15 +2431,15 @@ static void ohci_pmac_off(struct pci_dev *dev)
        }
 }
 #else
-#define ohci_pmac_on(dev)
-#define ohci_pmac_off(dev)
+static inline void pmac_ohci_on(struct pci_dev *dev) {}
+static inline void pmac_ohci_off(struct pci_dev *dev) {}
 #endif /* CONFIG_PPC_PMAC */
 
 static int __devinit pci_probe(struct pci_dev *dev,
                               const struct pci_device_id *ent)
 {
        struct fw_ohci *ohci;
-       u32 bus_options, max_receive, link_speed, version;
+       u32 bus_options, max_receive, link_speed, version, link_enh;
        u64 guid;
        int i, err, n_ir, n_it;
        size_t size;
@@ -2349,7 +2452,7 @@ static int __devinit pci_probe(struct pci_dev *dev,
 
        fw_card_initialize(&ohci->card, &ohci_driver, &dev->dev);
 
-       ohci_pmac_on(dev);
+       pmac_ohci_on(dev);
 
        err = pci_enable_device(dev);
        if (err) {
@@ -2389,6 +2492,23 @@ static int __devinit pci_probe(struct pci_dev *dev,
        if (param_quirks)
                ohci->quirks = param_quirks;
 
+       /* TI OHCI-Lynx and compatible: set recommended configuration bits. */
+       if (dev->vendor == PCI_VENDOR_ID_TI) {
+               pci_read_config_dword(dev, PCI_CFG_TI_LinkEnh, &link_enh);
+
+               /* adjust latency of ATx FIFO: use 1.7 KB threshold */
+               link_enh &= ~TI_LinkEnh_atx_thresh_mask;
+               link_enh |= TI_LinkEnh_atx_thresh_1_7K;
+
+               /* use priority arbitration for asynchronous responses */
+               link_enh |= TI_LinkEnh_enab_unfair;
+
+               /* required for aPhyEnhanceEnable to work */
+               link_enh |= TI_LinkEnh_enab_accel;
+
+               pci_write_config_dword(dev, PCI_CFG_TI_LinkEnh, link_enh);
+       }
+
        ar_context_init(&ohci->ar_request_ctx, ohci,
                        OHCI1394_AsReqRcvContextControlSet);
 
@@ -2466,7 +2586,7 @@ static int __devinit pci_probe(struct pci_dev *dev,
        pci_disable_device(dev);
  fail_free:
        kfree(&ohci->card);
-       ohci_pmac_off(dev);
+       pmac_ohci_off(dev);
  fail:
        if (err == -ENOMEM)
                fw_error("Out of memory\n");
@@ -2509,7 +2629,7 @@ static void pci_remove(struct pci_dev *dev)
        pci_release_region(dev, 0);
        pci_disable_device(dev);
        kfree(&ohci->card);
-       ohci_pmac_off(dev);
+       pmac_ohci_off(dev);
 
        fw_notify("Removed fw-ohci device.\n");
 }
@@ -2530,7 +2650,7 @@ static int pci_suspend(struct pci_dev *dev, pm_message_t state)
        err = pci_set_power_state(dev, pci_choose_state(dev, state));
        if (err)
                fw_error("pci_set_power_state failed with %d\n", err);
-       ohci_pmac_off(dev);
+       pmac_ohci_off(dev);
 
        return 0;
 }
@@ -2540,7 +2660,7 @@ static int pci_resume(struct pci_dev *dev)
        struct fw_ohci *ohci = pci_get_drvdata(dev);
        int err;
 
-       ohci_pmac_on(dev);
+       pmac_ohci_on(dev);
        pci_set_power_state(dev, PCI_D0);
        pci_restore_state(dev);
        err = pci_enable_device(dev);
index ba492d8..3bc9a5d 100644 (file)
@@ -67,7 +67,7 @@
 #define   OHCI1394_PhyControl_ReadDone         0x80000000
 #define   OHCI1394_PhyControl_ReadData(r)      (((r) & 0x00ff0000) >> 16)
 #define   OHCI1394_PhyControl_Write(addr, data)        (((addr) << 8) | (data) | 0x00004000)
-#define   OHCI1394_PhyControl_WriteDone                0x00004000
+#define   OHCI1394_PhyControl_WritePending     0x00004000
 #define OHCI1394_IsochronousCycleTimer        0x0F0
 #define OHCI1394_AsReqFilterHiSet             0x100
 #define OHCI1394_AsReqFilterHiClear           0x104
 
 #define OHCI1394_phy_tcode             0xe
 
+/* TI extensions */
+
+#define PCI_CFG_TI_LinkEnh             0xf4
+#define  TI_LinkEnh_enab_accel         0x00000002
+#define  TI_LinkEnh_enab_unfair                0x00000080
+#define  TI_LinkEnh_atx_thresh_mask    0x00003000
+#define  TI_LinkEnh_atx_thresh_1_7K    0x00001000
+
 #endif /* _FIREWIRE_OHCI_H */
index 9fd4a0d..adaefab 100644 (file)
@@ -1824,7 +1824,7 @@ static int dv1394_open(struct inode *inode, struct file *file)
               "and will not be available in the new firewire driver stack. "
               "Try libraw1394 based programs instead.\n", current->comm);
 
-       return 0;
+       return nonseekable_open(inode, file);
 }
 
 
@@ -2153,17 +2153,18 @@ static struct cdev dv1394_cdev;
 static const struct file_operations dv1394_fops=
 {
        .owner =        THIS_MODULE,
-       .poll =         dv1394_poll,
+       .poll =         dv1394_poll,
        .unlocked_ioctl = dv1394_ioctl,
 #ifdef CONFIG_COMPAT
        .compat_ioctl = dv1394_compat_ioctl,
 #endif
        .mmap =         dv1394_mmap,
        .open =         dv1394_open,
-       .write =        dv1394_write,
-       .read =         dv1394_read,
+       .write =        dv1394_write,
+       .read =         dv1394_read,
        .release =      dv1394_release,
-       .fasync =       dv1394_fasync,
+       .fasync =       dv1394_fasync,
+       .llseek =       no_llseek,
 };
 
 
index 8aa56ac..b563d5e 100644 (file)
@@ -2834,7 +2834,7 @@ static int raw1394_open(struct inode *inode, struct file *file)
 
        file->private_data = fi;
 
-       return 0;
+       return nonseekable_open(inode, file);
 }
 
 static int raw1394_release(struct inode *inode, struct file *file)
@@ -3035,6 +3035,7 @@ static const struct file_operations raw1394_fops = {
        .poll = raw1394_poll,
        .open = raw1394_open,
        .release = raw1394_release,
+       .llseek = no_llseek,
 };
 
 static int __init init_raw1394(void)
index 949064a..a42bd68 100644 (file)
@@ -1239,7 +1239,7 @@ static int video1394_open(struct inode *inode, struct file *file)
        ctx->current_ctx = NULL;
        file->private_data = ctx;
 
-       return 0;
+       return nonseekable_open(inode, file);
 }
 
 static int video1394_release(struct inode *inode, struct file *file)
@@ -1287,7 +1287,8 @@ static const struct file_operations video1394_fops=
        .poll =         video1394_poll,
        .mmap =         video1394_mmap,
        .open =         video1394_open,
-       .release =      video1394_release
+       .release =      video1394_release,
+       .llseek =       no_llseek,
 };
 
 /*** HOTPLUG STUFF **********************************************************/
index 4bd94bf..72e2b8a 100644 (file)
 #define CSR_DESCRIPTOR         0x01
 #define CSR_VENDOR             0x03
 #define CSR_HARDWARE_VERSION   0x04
-#define CSR_NODE_CAPABILITIES  0x0c
 #define CSR_UNIT               0x11
 #define CSR_SPECIFIER_ID       0x12
 #define CSR_VERSION            0x13
 #define CSR_DEPENDENT_INFO     0x14
 #define CSR_MODEL              0x17
-#define CSR_INSTANCE           0x18
 #define CSR_DIRECTORY_ID       0x20
 
 struct fw_csr_iterator {
@@ -89,7 +87,6 @@ struct fw_card {
        int current_tlabel;
        u64 tlabel_mask;
        struct list_head transaction_list;
-       struct timer_list flush_timer;
        unsigned long reset_jiffies;
 
        unsigned long long guid;
@@ -290,6 +287,8 @@ struct fw_transaction {
        int tlabel;
        int timestamp;
        struct list_head link;
+       struct fw_card *card;
+       struct timer_list split_timeout_timer;
 
        struct fw_packet packet;