From: Paul Butler <paul.but...@windriver.com>

This patch adds the register definitions,
support for PW messages, destination IDs, direct IO and
driver support.

Signed-off-by: Paul Butler <paul.but...@windriver.com>
---
 include/asm-generic/vmlinux.lds.h |   10 ++
 include/linux/rio.h               |  231 ++++++++++++++++++++++++++++++-------
 include/linux/rio_dio.h           |   67 +++++++++++
 include/linux/rio_drv.h           |  202 +++++++++++++++++++++++++-------
 include/linux/rio_ids.h           |    7 ++
 include/linux/rio_regs.h          |   26 +++++
 include/linux/riopw.h             |   30 +++++
 7 files changed, 490 insertions(+), 83 deletions(-)
 create mode 100644 include/linux/rio_dio.h
 create mode 100644 include/linux/riopw.h

diff --git a/include/asm-generic/vmlinux.lds.h 
b/include/asm-generic/vmlinux.lds.h
index 5d2ca6f..290711d 100644
--- a/include/asm-generic/vmlinux.lds.h
+++ b/include/asm-generic/vmlinux.lds.h
@@ -274,6 +274,16 @@
        }                                                               \
                                                                        \
        /* RapidIO route ops */                                         \
+       .rio_dev_fixup : AT(ADDR(.rio_dev_fixup) - LOAD_OFFSET) {       \
+               VMLINUX_SYMBOL(__start_rio_dev_fixup_early) = .;        \
+               *(.rio_dev_fixup_early)                                 \
+               VMLINUX_SYMBOL(__end_rio_dev_fixup_early) = .;          \
+               VMLINUX_SYMBOL(__start_rio_dev_fixup_enable) = .;       \
+               *(.rio_dev_fixup_enable)                                \
+               VMLINUX_SYMBOL(__end_rio_dev_fixup_enable) = .;         \
+       }                                                               \
+                                                                       \
+       /* RapidIO route ops */                                         \
        .rio_ops        : AT(ADDR(.rio_ops) - LOAD_OFFSET) {            \
                VMLINUX_SYMBOL(__start_rio_switch_ops) = .;             \
                *(.rio_switch_ops)                                      \
diff --git a/include/linux/rio.h b/include/linux/rio.h
index 4d50611..ef300e2 100644
--- a/include/linux/rio.h
+++ b/include/linux/rio.h
@@ -20,6 +20,8 @@
 #include <linux/errno.h>
 #include <linux/device.h>
 #include <linux/rio_regs.h>
+#include <linux/radix-tree.h>
+#include <asm/rio.h>
 
 #define RIO_NO_HOPCOUNT                -1
 #define RIO_INVALID_DESTID     0xffff
@@ -37,10 +39,14 @@
                                           entry is invalid (no route
                                           exists for the device ID) */
 
+#define RIO_INVALID_ROUTE_WEIGHT       0xff  /* Indicates that a route weight
+                                               entry is invalid (no route
+                                               exists for the device ID) */
+
 #define RIO_MAX_ROUTE_ENTRIES(size)    (size ? (1 << 16) : (1 << 8))
 #define RIO_ANY_DESTID(size)           (size ? 0xffff : 0xff)
 
-#define RIO_MAX_MBOX           4
+#define RIO_MAX_MBOX           8
 #define RIO_MAX_MSG_SIZE       0x1000
 
 /*
@@ -77,6 +83,9 @@
 #define RIO_CTAG_RESRVD        0xfffe0000 /* Reserved */
 #define RIO_CTAG_UDEVID        0x0001ffff /* Unique device identifier */
 
+#define RIO_DEVICE_INSERTION    1
+#define RIO_DEVICE_EXTRACTION   2
+
 extern struct bus_type rio_bus_type;
 extern struct device rio_bus;
 extern struct list_head rio_devices;   /* list of all devices */
@@ -85,6 +94,15 @@ struct rio_mport;
 struct rio_dev;
 union rio_pw_msg;
 
+struct rio_switch_port {
+       struct rio_dev *rdev;
+#ifdef CONFIG_RAPIDIO_DYNAMIC_ROUTES
+       u8 *route_weights_table;
+#endif
+};
+
+#define NEW_STYLE 1
+
 /**
  * struct rio_switch - RIO switch info
  * @node: Node in global list of switches
@@ -104,7 +122,12 @@ union rio_pw_msg;
 struct rio_switch {
        struct list_head node;
        u16 switchid;
+#ifdef OLD_STYLE
        u8 *route_table;
+#else
+       u32 port_init;
+       int update_lut;
+#endif
        u32 port_ok;
        int (*add_entry) (struct rio_mport *mport, u16 destid, u8 hopcount,
                          u16 table, u16 route_destid, u8 route_port);
@@ -119,7 +142,9 @@ struct rio_switch {
        int (*em_init) (struct rio_dev *dev);
        int (*em_handle) (struct rio_dev *dev, u8 swport);
        int (*sw_sysfs) (struct rio_dev *dev, int create);
-       struct rio_dev *nextdev[0];
+#ifdef OLD_STYLE
+       struct rio_switch_port port[0];
+#endif
 };
 
 /**
@@ -151,10 +176,19 @@ struct rio_switch {
  * @prev: Previous RIO device connected to the current one
  * @rswitch: struct rio_switch (if valid for this device)
  */
+#ifdef NEW_STYLE
+struct rio_dyn {
+       int prev_port;
+       u16 prev_destid;
+       u32 swpinfo;
+};
+#endif
+
 struct rio_dev {
        struct list_head global_list;   /* node in list of all RIO devices */
        struct list_head net_list;      /* node in per net list */
-       struct rio_net *net;    /* RIO net this device resides in */
+       struct list_head route_list;    /* node in per net list */
+       struct rio_mport *hport;        /* RIO net this device resides in */
        u16 did;
        u16 vid;
        u32 device_rev;
@@ -176,7 +210,15 @@ struct rio_dev {
        int (*pwcback) (struct rio_dev *rdev, union rio_pw_msg *msg, int step);
        u16 destid;
        u8 hopcount;
+#ifdef NEW_STYLE
+       int use_hw_lock;
+       int local_domain;       /* Device enumerated/Device discovered */
+       int prev_port;
+       u16 prev_destid;
+       u8 return_port;
+#else
        struct rio_dev *prev;
+#endif
        struct rio_switch rswitch[0];   /* RIO switch info */
 };
 
@@ -190,9 +232,15 @@ struct rio_dev {
  * @res: Mailbox resource
  * @mcback: Message event callback
  */
-struct rio_msg {
+struct rio_outb_msg {
        struct resource *res;
-       void (*mcback) (struct rio_mport * mport, void *dev_id, int mbox, int 
slot);
+       void (*mcback) (struct rio_mport *mport,
+       void *dev_id, int mbox, int rc, void *cookie);
+};
+struct rio_inb_msg {
+       struct resource *res;
+       void (*mcback) (struct rio_mport *mport,
+       void *dev_id, int mbox, int letter);
 };
 
 /**
@@ -205,7 +253,8 @@ struct rio_msg {
 struct rio_dbell {
        struct list_head node;
        struct resource *res;
-       void (*dinb) (struct rio_mport *mport, void *dev_id, u16 src, u16 dst, 
u16 info);
+       void (*dinb) (struct rio_mport *mport, void *dev_id,
+                     u16 src, u16 dst, u16 info);
        void *dev_id;
 };
 
@@ -214,6 +263,46 @@ enum rio_phy_type {
        RIO_PHY_SERIAL,
 };
 
+struct rio_map_addr {
+       void __iomem *va;
+       resource_size_t phys;
+};
+
+/**
+ * Struct for RIO memory definition.
+ * @req_outb: The function for requesting outbound memory window.
+ * @map_outb: The function for mapping outbound memory window.
+ * @release_outb: The function for releasing outbound memory window.
+ */
+struct rio_mem_ops {
+       int (*req_outb) (struct rio_mport *, resource_size_t,
+                        const char *, u32, u32 *);
+       int (*map_outb) (struct rio_mport *, u32,
+                        u16, u32, u32, struct rio_map_addr *);
+       void (*release_outb) (struct rio_mport *, u32);
+};
+/**
+ * struct rio_net - RIO network info
+ * @node: Node in global list of RIO networks
+ * @devices: List of devices in this network
+ * @mports: List of master ports accessing this network
+ * @hport: Default port for accessing this network
+ * @id: RIO network ID
+ */
+struct rio_net {
+#ifdef NEW_STYLE
+       struct radix_tree_root dev_tree;
+       atomic_t rio_dev_num;
+       struct radix_tree_root dst_tree;
+       atomic_t rio_dst_num;
+       atomic_t rio_max_dest;
+       spinlock_t tree_lock;
+#else
+       struct list_head devices;       /* list of devices in this net */
+#endif
+       unsigned char id;       /* RIO network ID */
+};
+
 /**
  * struct rio_mport - RIO master port info
  * @dbells: List of doorbell events
@@ -236,13 +325,19 @@ enum rio_phy_type {
 struct rio_mport {
        struct list_head dbells;        /* list of doorbell events */
        struct list_head node;  /* node in global list of ports */
-       struct list_head nnode; /* node in net list of ports */
+       struct rio_net net;
+
+#if defined(CONFIG_RAPIDIO_STATIC_DESTID) || defined(CONFIG_RAPIDIO_HOTPLUG)
+       struct device dev;
+#endif
        struct resource iores;
        struct resource riores[RIO_MAX_MPORT_RESOURCES];
-       struct rio_msg inb_msg[RIO_MAX_MBOX];
-       struct rio_msg outb_msg[RIO_MAX_MBOX];
+       struct rio_inb_msg  inb_msg[RIO_MAX_MBOX];
+       struct rio_outb_msg outb_msg[RIO_MAX_MBOX];
        int host_deviceid;      /* Host device ID */
+       int enum_host;
        struct rio_ops *ops;    /* low-level architecture-dependent routines */
+       struct rio_mem_ops *mops; /* Memory functions */
        unsigned char id;       /* port ID, unique among all ports */
        unsigned char index;    /* port index, unique among all port
                                   interfaces of the same type */
@@ -256,28 +351,33 @@ struct rio_mport {
        void *priv;             /* Master port private data */
 };
 
-/**
- * struct rio_net - RIO network info
- * @node: Node in global list of RIO networks
- * @devices: List of devices in this network
- * @mports: List of master ports accessing this network
- * @hport: Default port for accessing this network
- * @id: RIO network ID
- */
-struct rio_net {
-       struct list_head node;  /* node in list of networks */
-       struct list_head devices;       /* list of devices in this net */
-       struct list_head mports;        /* list of ports accessing net */
-       struct rio_mport *hport;        /* primary port for accessing net */
-       unsigned char id;       /* RIO network ID */
-};
 
 /* Definitions used by switch sysfs initialization callback */
 #define RIO_SW_SYSFS_CREATE    1       /* Create switch attributes */
 #define RIO_SW_SYSFS_REMOVE    0       /* Remove switch attributes */
 
 /* Low-level architecture-dependent routines */
-
+#ifdef CONFIG_RAPIDIO_HOTPLUG
+
+#define RIO_HOT_SWAP_EXTRACT         0x1
+#define RIO_HOT_SWAP_INSERT          0x2
+#define RIO_HOT_SWAP_MPORT           0x4
+#define RIO_HOT_SWAP_LINK_PARTNER    0x8
+
+#define RIO_EXTRACT_LP(f) (((f) & \
+               (RIO_HOT_SWAP_EXTRACT | RIO_HOT_SWAP_LINK_PARTNER)) == \
+               (RIO_HOT_SWAP_EXTRACT | RIO_HOT_SWAP_LINK_PARTNER))
+#define RIO_EXTRACT_MP(f) (((f) & \
+               (RIO_HOT_SWAP_EXTRACT | RIO_HOT_SWAP_MPORT)) == \
+               (RIO_HOT_SWAP_EXTRACT | RIO_HOT_SWAP_MPORT))
+#define RIO_INSERT_LP(f) (((f) & \
+               (RIO_HOT_SWAP_INSERT | RIO_HOT_SWAP_LINK_PARTNER)) == \
+               (RIO_HOT_SWAP_INSERT | RIO_HOT_SWAP_LINK_PARTNER))
+#define RIO_INSERT_MP(f) (((f) & \
+               (RIO_HOT_SWAP_INSERT | RIO_HOT_SWAP_MPORT)) == \
+               (RIO_HOT_SWAP_INSERT | RIO_HOT_SWAP_MPORT))
+
+#endif
 /**
  * struct rio_ops - Low-level RIO configuration space operations
  * @lcread: Callback to perform local (master port) read of config space.
@@ -295,28 +395,47 @@ struct rio_net {
  * @get_inb_message: Callback to get a message from an inbound mailbox queue.
  */
 struct rio_ops {
-       int (*lcread) (struct rio_mport *mport, int index, u32 offset, int len,
-                       u32 *data);
-       int (*lcwrite) (struct rio_mport *mport, int index, u32 offset, int len,
-                       u32 data);
+       int (*lcread) (struct rio_mport *mport, int index, u32 offset,
+                       int len, u32 *data);
+       int (*lcwrite) (struct rio_mport *mport, int index, u32 offset,
+                       int len, u32 data);
        int (*cread) (struct rio_mport *mport, int index, u16 destid,
                        u8 hopcount, u32 offset, int len, u32 *data);
        int (*cwrite) (struct rio_mport *mport, int index, u16 destid,
                        u8 hopcount, u32 offset, int len, u32 data);
-       int (*dsend) (struct rio_mport *mport, int index, u16 destid, u16 data);
+       int (*dsend) (struct rio_mport *mport, int index,
+                       u16 destid, u16 data);
        int (*pwenable) (struct rio_mport *mport, int enable);
        int (*open_outb_mbox)(struct rio_mport *mport, void *dev_id,
-                             int mbox, int entries);
+                             int mbox, int entries, int prio);
        void (*close_outb_mbox)(struct rio_mport *mport, int mbox);
        int  (*open_inb_mbox)(struct rio_mport *mport, void *dev_id,
                             int mbox, int entries);
        void (*close_inb_mbox)(struct rio_mport *mport, int mbox);
        int  (*add_outb_message)(struct rio_mport *mport, struct rio_dev *rdev,
-                                int mbox, void *buffer, size_t len);
+                               int mbox_dest, int letter, int flags,
+                               void *buffer, size_t len, void *cookie);
        int (*add_inb_buffer)(struct rio_mport *mport, int mbox, void *buf);
-       void *(*get_inb_message)(struct rio_mport *mport, int mbox);
+       void *(*get_inb_message)(struct rio_mport *mport, int mbox, int letter,
+                                int *sz, int *slot, u16 *destid);
+#ifdef CONFIG_RAPIDIO_HOTPLUG
+       int (*hotswap)(struct rio_mport *mport, u8 flags);
+       int (*port_notify_cb)(struct rio_mport *mport,
+                             int enable,
+                             void (*cb)(struct rio_mport *mport));
+       int (*port_op_state)(struct rio_mport *mport);
+#endif
+};
+
+#ifdef CONFIG_RAPIDIO_STATIC_DESTID
+
+struct rio_static_route {
+       u16 sw_destid;
+       u8 sw_port;
 };
 
+#endif
+
 #define RIO_RESOURCE_MEM       0x00000100
 #define RIO_RESOURCE_DOORBELL  0x00000200
 #define RIO_RESOURCE_MAILBOX   0x00000400
@@ -341,19 +460,25 @@ struct rio_ops {
  * Provides info on a RIO device driver for insertion/removal and
  * power management purposes.
  */
+struct rio_dynids {
+       spinlock_t lock;            /* protects list, index */
+       struct list_head list;      /* for IDs added at runtime */
+};
+
 struct rio_driver {
        struct list_head node;
        char *name;
        const struct rio_device_id *id_table;
-       int (*probe) (struct rio_dev * dev, const struct rio_device_id * id);
-       void (*remove) (struct rio_dev * dev);
-       int (*suspend) (struct rio_dev * dev, u32 state);
-       int (*resume) (struct rio_dev * dev);
-       int (*enable_wake) (struct rio_dev * dev, u32 state, int enable);
+       int (*probe) (struct rio_dev *dev, const struct rio_device_id *id);
+       void (*remove) (struct rio_dev *dev);
+       int (*suspend) (struct rio_dev *dev, u32 state);
+       int (*resume) (struct rio_dev *dev);
+       int (*enable_wake) (struct rio_dev *dev, u32 state, int enable);
        struct device_driver driver;
+       struct rio_dynids dynids;
 };
 
-#define        to_rio_driver(drv) container_of(drv,struct rio_driver, driver)
+#define        to_rio_driver(drv) container_of(drv, struct rio_driver, driver)
 
 /**
  * struct rio_device_id - RIO device identifier
@@ -383,6 +508,25 @@ struct rio_switch_ops {
        u16 vid, did;
        int (*init_hook) (struct rio_dev *rdev, int do_enum);
 };
+struct rio_dev_fixup {
+       u16 vid, did;
+       void (*fixup_hook) (struct rio_dev *rdev, u16 destid, u8 hopcount);
+};
+enum rio_fixup_pass {
+       rio_fixup_early,
+       rio_fixup_enable,
+};
+
+
+#define DECLARE_RIO_DEV_FIXUP_SECTION(section, name, vid, did, fixup_hook) \
+       static const struct rio_dev_fixup __rio_dev_fixup_##name __used \
+       __section(section) = { vid, did, fixup_hook };
+#define DECLARE_RIO_DEV_FIXUP_EARLY(vid, did, fixup_hook)              \
+       DECLARE_RIO_DEV_FIXUP_SECTION(.rio_dev_fixup_early,             \
+       vid##did##fixup_hook, vid, did, fixup_hook)
+#define DECLARE_RIO_DEV_FIXUP_ENABLE(vid, did, fixup_hook)             \
+       DECLARE_RIO_DEV_FIXUP_SECTION(.rio_dev_fixup_enable,            \
+       vid##did##fixup_hook, vid, did, fixup_hook)
 
 union rio_pw_msg {
        struct {
@@ -394,6 +538,13 @@ union rio_pw_msg {
        } em;
        u32 raw[RIO_PW_MSG_SIZE/sizeof(u32)];
 };
+void rio_fixup_dev(enum rio_fixup_pass pass,
+                  struct rio_dev *rdev,
+                  u16 destid,
+                  u8 hopcount);
+
+
+
 
 /* Architecture and hardware-specific functions */
 extern int rio_register_mport(struct rio_mport *);
@@ -401,5 +552,5 @@ extern int rio_open_inb_mbox(struct rio_mport *, void *, 
int, int);
 extern void rio_close_inb_mbox(struct rio_mport *, int);
 extern int rio_open_outb_mbox(struct rio_mport *, void *, int, int);
 extern void rio_close_outb_mbox(struct rio_mport *, int);
-
+extern int rio_init_device(struct rio_dev *rdev);
 #endif                         /* LINUX_RIO_H */
diff --git a/include/linux/rio_dio.h b/include/linux/rio_dio.h
new file mode 100644
index 0000000..4469278
--- /dev/null
+++ b/include/linux/rio_dio.h
@@ -0,0 +1,67 @@
+#ifndef _RIO_DIO_H_
+#define _RIO_DIO_H_
+
+
+#define RIO_IO_READ_HOME        0x00
+#define RIO_MAINT_READ         0x01
+#define RIO_MAINT_WRITE                0x10
+#define RIO_NREAD              0x02
+#define RIO_NWRITE             0x20
+#define RIO_NWRITE_R           0x40
+#define RIO_SWRITE             0x80
+
+#ifdef __KERNEL__
+
+#include <linux/kernel.h>
+#include <linux/kref.h>
+#include <linux/rio.h>
+#include <linux/rio_drv.h>
+#include <linux/dma-mapping.h>
+#include <linux/dmaengine.h>
+
+struct rio_dio_win {
+       struct list_head node;
+       void *dio_channel;
+       struct rio_dev *rdev;
+       unsigned outb_win;
+       resource_size_t win_size;
+       struct kref kref;
+};
+
+/*
+ Setup / release methods
+*/
+struct rio_dio_win *rio_dio_req_region(void *dio_channel,
+                                      struct rio_dev *rdev,
+                                      resource_size_t size,
+                                      u32 flags);
+void rio_dio_region_put(struct rio_dio_win *io_win);
+int rio_dio_method_setup(void **dio_channel);
+void rio_dio_method_put(void *dio_channel);
+
+/*
+  Access methods
+*/
+int rio_dio_read_8(struct rio_dio_win *io_win, u32 offset,
+                  u32 mflags, u8 *value);
+int rio_dio_read_16(struct rio_dio_win *io_win, u32 offset,
+                   u32 mflags, u16 *value);
+int rio_dio_read_32(struct rio_dio_win *io_win, u32 offset,
+                   u32 mflags, u32 *value);
+int rio_dio_read_buff(struct rio_dio_win *io_win, u32 offset,
+                     u8 *dst, u32 mflags, u32 len);
+int rio_dio_write_8(struct rio_dio_win *io_win,
+                   u32 offset, u32 mflags, u8 *src);
+int rio_dio_write_16(struct rio_dio_win *io_win,
+                    u32 offset, u32 mflags, u16 *src);
+int rio_dio_write_32(struct rio_dio_win *io_win, u32 offset,
+                    u32 mflags, u32 *src);
+int rio_dio_write_buff(struct rio_dio_win *io_win, u32 offset,
+                      u8 *src, u32 mflags, u32 len);
+
+int rio_dio_const_win(struct rio_dio_win *io_win, void *buf, u32 len,
+                     enum dma_data_direction dir, struct rio_map_addr *res);
+
+#endif /* __KERNEL__ */
+
+#endif
diff --git a/include/linux/rio_drv.h b/include/linux/rio_drv.h
index 7f07470..c320d77 100644
--- a/include/linux/rio_drv.h
+++ b/include/linux/rio_drv.h
@@ -21,28 +21,28 @@
 #include <linux/rio.h>
 
 extern int __rio_local_read_config_32(struct rio_mport *port, u32 offset,
-                                     u32 * data);
+                                     u32 *data);
 extern int __rio_local_write_config_32(struct rio_mport *port, u32 offset,
                                       u32 data);
 extern int __rio_local_read_config_16(struct rio_mport *port, u32 offset,
-                                     u16 * data);
+                                     u16 *data);
 extern int __rio_local_write_config_16(struct rio_mport *port, u32 offset,
                                       u16 data);
 extern int __rio_local_read_config_8(struct rio_mport *port, u32 offset,
-                                    u8 * data);
+                                    u8 *data);
 extern int __rio_local_write_config_8(struct rio_mport *port, u32 offset,
                                      u8 data);
 
 extern int rio_mport_read_config_32(struct rio_mport *port, u16 destid,
-                                   u8 hopcount, u32 offset, u32 * data);
+                                   u8 hopcount, u32 offset, u32 *data);
 extern int rio_mport_write_config_32(struct rio_mport *port, u16 destid,
                                     u8 hopcount, u32 offset, u32 data);
 extern int rio_mport_read_config_16(struct rio_mport *port, u16 destid,
-                                   u8 hopcount, u32 offset, u16 * data);
+                                   u8 hopcount, u32 offset, u16 *data);
 extern int rio_mport_write_config_16(struct rio_mport *port, u16 destid,
                                     u8 hopcount, u32 offset, u16 data);
 extern int rio_mport_read_config_8(struct rio_mport *port, u16 destid,
-                                  u8 hopcount, u32 offset, u8 * data);
+                                  u8 hopcount, u32 offset, u8 *data);
 extern int rio_mport_write_config_8(struct rio_mport *port, u16 destid,
                                    u8 hopcount, u32 offset, u8 data);
 
@@ -56,7 +56,7 @@ extern int rio_mport_write_config_8(struct rio_mport *port, 
u16 destid,
  * device's configuration space.
  */
 static inline int rio_local_read_config_32(struct rio_mport *port, u32 offset,
-                                          u32 * data)
+                                          u32 *data)
 {
        return __rio_local_read_config_32(port, offset, data);
 }
@@ -86,7 +86,7 @@ static inline int rio_local_write_config_32(struct rio_mport 
*port, u32 offset,
  * device's configuration space.
  */
 static inline int rio_local_read_config_16(struct rio_mport *port, u32 offset,
-                                          u16 * data)
+                                          u16 *data)
 {
        return __rio_local_read_config_16(port, offset, data);
 }
@@ -117,7 +117,7 @@ static inline int rio_local_write_config_16(struct 
rio_mport *port, u32 offset,
  * device's configuration space.
  */
 static inline int rio_local_read_config_8(struct rio_mport *port, u32 offset,
-                                         u8 * data)
+                                         u8 *data)
 {
        return __rio_local_read_config_8(port, offset, data);
 }
@@ -147,10 +147,13 @@ static inline int rio_local_write_config_8(struct 
rio_mport *port, u32 offset,
  * RIO device's configuration space.
  */
 static inline int rio_read_config_32(struct rio_dev *rdev, u32 offset,
-                                    u32 * data)
+                                    u32 *data)
 {
-       return rio_mport_read_config_32(rdev->net->hport, rdev->destid,
-                                       rdev->hopcount, offset, data);
+       if (likely(rdev->destid != rdev->hport->host_deviceid))
+               return rio_mport_read_config_32(rdev->hport, rdev->destid,
+                                               rdev->hopcount, offset, data);
+       else
+               return rio_local_read_config_32(rdev->hport, offset, data);
 };
 
 /**
@@ -165,8 +168,11 @@ static inline int rio_read_config_32(struct rio_dev *rdev, 
u32 offset,
 static inline int rio_write_config_32(struct rio_dev *rdev, u32 offset,
                                      u32 data)
 {
-       return rio_mport_write_config_32(rdev->net->hport, rdev->destid,
-                                        rdev->hopcount, offset, data);
+       if (likely(rdev->destid != rdev->hport->host_deviceid))
+               return rio_mport_write_config_32(rdev->hport, rdev->destid,
+                                                rdev->hopcount, offset, data);
+       else
+               return rio_local_write_config_32(rdev->hport, offset, data);
 };
 
 /**
@@ -179,10 +185,13 @@ static inline int rio_write_config_32(struct rio_dev 
*rdev, u32 offset,
  * RIO device's configuration space.
  */
 static inline int rio_read_config_16(struct rio_dev *rdev, u32 offset,
-                                    u16 * data)
+                                    u16 *data)
 {
-       return rio_mport_read_config_16(rdev->net->hport, rdev->destid,
-                                       rdev->hopcount, offset, data);
+       if (likely(rdev->destid != rdev->hport->host_deviceid))
+               return rio_mport_read_config_16(rdev->hport, rdev->destid,
+                                               rdev->hopcount, offset, data);
+       else
+               return rio_local_read_config_16(rdev->hport, offset, data);
 };
 
 /**
@@ -197,8 +206,11 @@ static inline int rio_read_config_16(struct rio_dev *rdev, 
u32 offset,
 static inline int rio_write_config_16(struct rio_dev *rdev, u32 offset,
                                      u16 data)
 {
-       return rio_mport_write_config_16(rdev->net->hport, rdev->destid,
-                                        rdev->hopcount, offset, data);
+       if (likely(rdev->destid != rdev->hport->host_deviceid))
+               return rio_mport_write_config_16(rdev->hport, rdev->destid,
+                                                rdev->hopcount, offset, data);
+       else
+               return rio_local_write_config_16(rdev->hport, offset, data);
 };
 
 /**
@@ -210,10 +222,13 @@ static inline int rio_write_config_16(struct rio_dev 
*rdev, u32 offset,
  * Reads 8 bits of data from the specified offset within the
  * RIO device's configuration space.
  */
-static inline int rio_read_config_8(struct rio_dev *rdev, u32 offset, u8 * 
data)
+static inline int rio_read_config_8(struct rio_dev *rdev, u32 offset, u8 *data)
 {
-       return rio_mport_read_config_8(rdev->net->hport, rdev->destid,
-                                      rdev->hopcount, offset, data);
+       if (likely(rdev->destid != rdev->hport->host_deviceid))
+               return rio_mport_read_config_8(rdev->hport, rdev->destid,
+                                              rdev->hopcount, offset, data);
+       else
+               return rio_local_read_config_8(rdev->hport, offset, data);
 };
 
 /**
@@ -227,8 +242,11 @@ static inline int rio_read_config_8(struct rio_dev *rdev, 
u32 offset, u8 * data)
  */
 static inline int rio_write_config_8(struct rio_dev *rdev, u32 offset, u8 data)
 {
-       return rio_mport_write_config_8(rdev->net->hport, rdev->destid,
-                                       rdev->hopcount, offset, data);
+       if (likely(rdev->destid != rdev->hport->host_deviceid))
+               return rio_mport_write_config_8(rdev->hport, rdev->destid,
+                                               rdev->hopcount, offset, data);
+       else
+               return rio_local_write_config_8(rdev->hport, offset, data);
 };
 
 extern int rio_mport_send_doorbell(struct rio_mport *mport, u16 destid,
@@ -244,7 +262,7 @@ extern int rio_mport_send_doorbell(struct rio_mport *mport, 
u16 destid,
  */
 static inline int rio_send_doorbell(struct rio_dev *rdev, u16 data)
 {
-       return rio_mport_send_doorbell(rdev->net->hport, rdev->destid, data);
+       return rio_mport_send_doorbell(rdev->hport, rdev->destid, data);
 };
 
 /**
@@ -292,13 +310,13 @@ static inline void rio_init_dbell_res(struct resource 
*res, u16 start, u16 end)
  * specific device.  The assembly vendor and assembly device fields
  * will be set to %RIO_ANY_ID.
  */
-#define RIO_DEVICE(dev,ven) \
+#define RIO_DEVICE(dev, ven) \
        .did = (dev), .vid = (ven), \
        .asm_did = RIO_ANY_ID, .asm_vid = RIO_ANY_ID
 
 /* Mailbox management */
-extern int rio_request_outb_mbox(struct rio_mport *, void *, int, int,
-                                void (*)(struct rio_mport *, void *,int, int));
+extern int rio_request_outb_mbox(struct rio_mport *, void *, int, int, int,
+                      void (*)(struct rio_mport *, void *, int, int, void *));
 extern int rio_release_outb_mbox(struct rio_mport *, int);
 
 /**
@@ -313,15 +331,18 @@ extern int rio_release_outb_mbox(struct rio_mport *, int);
  * transmission. Returns 0 on success.
  */
 static inline int rio_add_outb_message(struct rio_mport *mport,
-                                      struct rio_dev *rdev, int mbox,
-                                      void *buffer, size_t len)
+                                      struct rio_dev *rdev,
+                                      int mbox_dest, int letter, int flags,
+                                      void *buffer, size_t len,
+                                      void *cookie)
 {
-       return mport->ops->add_outb_message(mport, rdev, mbox,
-                                                  buffer, len);
+       return mport->ops->add_outb_message(mport, rdev,
+                                           mbox_dest, letter, flags,
+                                           buffer, len, cookie);
 }
 
 extern int rio_request_inb_mbox(struct rio_mport *, void *, int, int,
-                               void (*)(struct rio_mport *, void *, int, int));
+                       void (*)(struct rio_mport *, void *, int, int));
 extern int rio_release_inb_mbox(struct rio_mport *, int);
 
 /**
@@ -346,30 +367,33 @@ static inline int rio_add_inb_buffer(struct rio_mport 
*mport, int mbox,
  *
  * Get a RIO message from an inbound mailbox queue. Returns 0 on success.
  */
-static inline void *rio_get_inb_message(struct rio_mport *mport, int mbox)
+static inline void *rio_get_inb_message(struct rio_mport *mport, int mbox,
+                               int letter, int *sz, int *slot, u16 *destid)
 {
-       return mport->ops->get_inb_message(mport, mbox);
+       return mport->ops->get_inb_message(mport, mbox, letter, \
+                                          sz, slot, destid);
 }
 
 /* Doorbell management */
 extern int rio_request_inb_dbell(struct rio_mport *, void *, u16, u16,
-                                void (*)(struct rio_mport *, void *, u16, u16, 
u16));
+                       void (*)(struct rio_mport *, void *, u16, u16, u16));
 extern int rio_release_inb_dbell(struct rio_mport *, u16, u16);
 extern struct resource *rio_request_outb_dbell(struct rio_dev *, u16, u16);
 extern int rio_release_outb_dbell(struct rio_dev *, struct resource *);
 
-/* Memory region management */
-int rio_claim_resource(struct rio_dev *, int);
-int rio_request_regions(struct rio_dev *, char *);
-void rio_release_regions(struct rio_dev *);
-int rio_request_region(struct rio_dev *, int, char *);
-void rio_release_region(struct rio_dev *, int);
+/* Memory low-level mapping functions */
+extern int rio_req_outb_region(struct rio_mport *, resource_size_t,
+                              const char *, u32, u32*);
+extern int rio_map_outb_mem(struct rio_mport *,
+                           u32, u16, u32, u32, struct rio_map_addr*);
+extern void rio_release_outb_region(struct rio_mport *, u32);
 
 /* Port-Write management */
 extern int rio_request_inb_pwrite(struct rio_dev *,
                        int (*)(struct rio_dev *, union rio_pw_msg*, int));
 extern int rio_release_inb_pwrite(struct rio_dev *);
-extern int rio_inb_pwrite_handler(union rio_pw_msg *pw_msg);
+extern int rio_inb_pwrite_handler(struct rio_mport *mport, \
+                                 union rio_pw_msg *pw_msg);
 
 /* LDM support */
 int rio_register_driver(struct rio_driver *);
@@ -419,5 +443,97 @@ extern u16 rio_local_get_device_id(struct rio_mport *port);
 extern struct rio_dev *rio_get_device(u16 vid, u16 did, struct rio_dev *from);
 extern struct rio_dev *rio_get_asm(u16 vid, u16 did, u16 asm_vid, u16 asm_did,
                                   struct rio_dev *from);
+extern struct rio_mport *rio_get_mport(int hostid, struct rio_mport *from);
+extern struct rio_dev **rio_get_all_devices(struct rio_mport *mport, int *n);
+extern struct rio_dev *lookup_rdev(struct rio_mport *mport, u16 destid);
+#define RIO_JOB_FLAG_STATIC   0x1
+
+extern int rio_job_init(struct rio_mport *mport, struct rio_dev *rdev,
+                       int port, u32 flags, int hw_access, int event);
+extern struct rio_dev *rio_get_root_node(struct rio_mport *mport);
+extern int rio_lookup_next_destid(struct rio_mport *mport, u16 parent_destid,
+                                 int port_num, u8 hopcount, u16 *id);
+
+#if defined(CONFIG_RAPIDIO_HOTPLUG)
+
+extern void rio_rescan_mport(struct rio_mport *mport);
+extern void rio_remove_mport_net(struct rio_mport *mport, int hw_access);
+
+static inline int rio_hotswap(struct rio_mport *mport, u8 flags)
+{
+       if (mport->ops->hotswap)
+               return mport->ops->hotswap(mport, flags);
+       else
+               return -EINVAL;
+}
+static inline int rio_request_mport_cb(struct rio_mport *mport,
+                                      int enable,
+                                      void (*cb)(struct rio_mport *mport))
+{
+       if (mport->ops->port_notify_cb)
+               return mport->ops->port_notify_cb(mport, enable, cb);
+       else
+               return -EINVAL;
+}
+#define MPORT_STATE_OPERATIONAL 0
+#define MPORT_STATE_DOWN        1
+#define MPORT_STATE_UNKNOWN     3
+static inline int rio_port_op_state(struct rio_mport *mport)
+{
+       if (mport->ops->port_op_state)
+               return mport->ops->port_op_state(mport);
+       else
+               return MPORT_STATE_UNKNOWN;
+}
+
+extern int rio_setup_event(struct rio_dev *rdev, int portnum, int event);
+extern int rio_setup_event_force(struct rio_dev *rdev, int portnum, int event);
+
+#endif
+
+#ifdef CONFIG_RAPIDIO_STATIC_DESTID
+extern int rio_add_netid(u16 mport_destid, int net_id, int comptag);
+
+extern int rio_add_destid(struct rio_mport *mport,
+                         u16 parent_destid, int parent_port,
+                         int hopcount, u16 destid, u16 comptag);
+extern int rio_block_destid_route(struct rio_mport *mport,
+                                 u16 parent_destid, int parent_port,
+                                 int hopcount, u16 destid, u16 comptag);
+extern int rio_split_destid_route(struct rio_mport *mport, u16 parent_destid,
+                                 int parent_port, int hopcount, u16 destid,
+                                 u16 comptag, u8 return_port);
+extern int rio_legacy_destid_route(struct rio_mport *mport,
+                                  u16 parent_destid, int parent_port,
+                                  int hopcount, u16 destid, u16 comptag,
+                                  u8 lock_hw, u8 lut_update);
+extern void rio_release_destid(struct rio_mport *mport, u16 parent_destid,
+                              int parent_port, int hopcount);
+extern int rio_add_static_route(struct rio_mport *mport, u16 parent_destid,
+                               int parent_port, int hopcount,
+                              struct rio_static_route *route, int num_routes);
+extern int rio_update_static_route(struct rio_mport *mport, u16 parent_destid,
+                               int parent_port, int hopcount,
+                              struct rio_static_route *route, int num_routes);
+extern int rio_remove_static_route(struct rio_mport *mport, u16 parent_destid,
+                               int parent_port, int hopcount,
+                              struct rio_static_route *route, int num_routes);
+extern int rio_lookup_static_routes(struct rio_mport *mport, u16 parent_destid,
+                               int parent_port, int hopcount,
+                             struct rio_static_route *sroute, int num_routes);
+extern struct rio_static_route *rio_static_route_table(struct rio_mport *mport,
+                                                      u16 parent_destid,
+                                                      int parent_port,
+                                                      int hopcount,
+                                                      u16 *destid,
+                                                      int *n);
+extern int rio_remove_netid(u16 mport_destid, int net_id);
+extern int rio_find_netid(u16 mport_destid, int *net_id);
+extern int rio_release_node_table(struct rio_mport *mport);
+#endif
+
+#if defined(CONFIG_RAPIDIO_HOTPLUG) || defined(CONFIG_RAPIDIO_STATIC_DESTID)
+extern ssize_t rio_net_nodes_show(struct rio_mport *mport, char *buf);
+#endif
 
 #endif                         /* LINUX_RIO_DRV_H */
diff --git a/include/linux/rio_ids.h b/include/linux/rio_ids.h
index b66d13d..ffca266 100644
--- a/include/linux/rio_ids.h
+++ b/include/linux/rio_ids.h
@@ -40,5 +40,12 @@
 #define RIO_DID_IDTVPS1616             0x0377
 #define RIO_DID_IDTSPS1616             0x0378
 #define RIO_DID_TSI721                 0x80ab
+#define RIO_VID_JENNIC                  0x005a
+#define RIO_DID_ERICSSON_ULMA           0x0000
+#define RIO_DID_ERICSSON_MERCURY        0x0006
+#define RIO_DID_ERICSSON_HERMES         0x0007
+#define RIO_VID_TEXAS                   0x0030
+#define RIO_DID_TEXAS_TCI6616           0xb941
+#define RIO_DID_TEXAS_TCI6616X          0x009d
 
 #endif                         /* LINUX_RIO_IDS_H */
diff --git a/include/linux/rio_regs.h b/include/linux/rio_regs.h
index 218168a..d178b9b 100644
--- a/include/linux/rio_regs.h
+++ b/include/linux/rio_regs.h
@@ -42,8 +42,13 @@
 #define  RIO_PEF_INB_MBOX2             0x00200000      /* [II, <= 1.2] Mailbox 
2 */
 #define  RIO_PEF_INB_MBOX3             0x00100000      /* [II, <= 1.2] Mailbox 
3 */
 #define  RIO_PEF_INB_DOORBELL          0x00080000      /* [II, <= 1.2] 
Doorbells */
+#define  RIO_PEF_FLOW_ARB     0x00000800 /* [III] Flow Arbitration support */
+#define  RIO_PEF_MCAST       0x00000400 /* [III] Multicast support */
 #define  RIO_PEF_EXT_RT                        0x00000200      /* [III, 1.3] 
Extended route table support */
 #define  RIO_PEF_STD_RT                        0x00000100      /* [III, 1.3] 
Standard route table support */
+#define  RIO_PEF_FCS         0x00000080 /* [III] Flow Control Support */
+#define  RIO_PEF_CRC_ERR_REC  0x00000040 /* [III] CRC Error Recovery */
+#define  RIO_PEF_CRFS        0x00000020 /* [III] Critical Request Flow Supt */
 #define  RIO_PEF_CTLS                  0x00000010      /* [III] CTLS */
 #define  RIO_PEF_EXT_FEATURES          0x00000008      /* [I] EFT_PTR valid */
 #define  RIO_PEF_ADDR_66               0x00000004      /* [I] 66 bits */
@@ -167,6 +172,25 @@
 #define RIO_STD_RTE_CONF_PORT_SEL_CSR  0x74
 #define RIO_STD_RTE_DEFAULT_PORT       0x78
 
+#define  RIO_MCAST_MASK_PORT_CSR       0x80    /* Multicast Mask Port CSR */
+#define  RIO_MCAST_MASK(x)             ((x) << 16)  /* Multicast Mask */
+#define  RIO_EGRESS_PORT_NUMBER(x)     ((x) << 8)   /* Port Number */
+#define  RIO_MASK_CMD_ADD_PORT         (0x1 << 4)   /* Add Port Command */
+#define  RIO_MASK_CMD_DEL_PORT         (0x2 << 4)   /* Delete Port Command */
+#define  RIO_MASK_CMD_DEL_ALL_PORTS    (0x4 << 4)   /* Delete All Ports Cmd */
+#define  RIO_MASK_CMD_ADD_ALL_PORTS    (0x5 << 4)   /* Add All Ports Cmd */
+#define  RIO_MCAST_PORT_PRESENT                (0x00000001) /* Port Present 
from Write
+                                                       to Verify command */
+
+#define  RIO_MCAST_ASSOC_SEL_CSR       0x84  /* Multicast Assoc Select CSR */
+#define  RIO_MCAST_LARGE_DEST_ID(x)    ((x) << 24)  /* Large Destination Id */
+#define  RIO_MCAST_DEST_ID(x)          ((x) << 16)  /* Destination Id */
+#define  RIO_MCAST_MASK_NO(x)          (x)          /* Multicast Mask # */
+
+#define  RIO_MCAST_ASSOC_OP_CSR        0x88 /* Multicast Assoc Operation CSR */
+#define  RIO_MCAST_TRANS_ASSOC(x)      ((x) << 7)  /* Transport Association */
+#define  RIO_MCAST_DEL_ASSOC           (0x1 << 5)  /* Delete Association */
+#define  RIO_MCAST_ADD_ASSOC           (0x3 << 5)  /* Add Association */
                                        /* 0x7c-0xf8 *//* Reserved */
                                        /* 0x100-0xfff8 *//* [I] Extended 
Features Space */
                                        /* 0x10000-0xfffff8 *//* [I] 
Implementation-defined Space */
@@ -251,10 +275,12 @@
 #define  RIO_PORT_N_CTL_PWIDTH_4       0x40000000
 #define  RIO_PORT_N_CTL_P_TYP_SER      0x00000001
 #define  RIO_PORT_N_CTL_LOCKOUT                0x00000002
+#define RIO_PORT_N_CTL_PORT_DIS                0x00800000
 #define  RIO_PORT_N_CTL_EN_RX_SER      0x00200000
 #define  RIO_PORT_N_CTL_EN_TX_SER      0x00400000
 #define  RIO_PORT_N_CTL_EN_RX_PAR      0x08000000
 #define  RIO_PORT_N_CTL_EN_TX_PAR      0x40000000
+#define RIO_PORT_N_CTL_ENUM_BOUNDARY   0x00020000
 
 /*
  * Error Management Extensions (RapidIO 1.3+, Part 8)
diff --git a/include/linux/riopw.h b/include/linux/riopw.h
new file mode 100644
index 0000000..ec7ef76f
--- /dev/null
+++ b/include/linux/riopw.h
@@ -0,0 +1,30 @@
+#ifndef _RIOPW_H_
+#define _RIOPW_H_
+
+#define RIOPW_IOC_MAGIC        'j'     /* Arbitrary */
+#define RIOPW_IOC_MINNR        0x40
+#define RIOPW_IOC_MAXNR        0x80
+
+#define IOCTL_MPORT_GETHID     _IOR(RIOPW_IOC_MAGIC, 0x40, int)
+#define IOCTL_MPORT_GETPWMSG   _IOR(RIOPW_IOC_MAGIC, 0x45, int)
+
+#ifdef __KERNEL__
+#else
+
+#define RIO_PW_MSG_SIZE                64
+
+union rio_pw_msg {
+       struct {
+               unsigned int comptag;   /* Component Tag CSR */
+               unsigned int errdetect; /* Port N Error Detect CSR */
+               unsigned int is_port;   /* Implementation specific + PortID */
+               unsigned int ltlerrdet; /* LTL Error Detect CSR */
+               unsigned int padding[12];
+       } em;
+       unsigned int raw[RIO_PW_MSG_SIZE/sizeof(unsigned int)];
+};
+
+#endif
+
+
+#endif
-- 
1.7.9.5

-- 
_______________________________________________
linux-yocto mailing list
linux-yocto@yoctoproject.org
https://lists.yoctoproject.org/listinfo/linux-yocto

Reply via email to