Commit 083a5094 authored by David Mosberger's avatar David Mosberger

ia64: Manual merge of Bjorn Helgaas' sba_iommu patch to make it use seq_file.

parent 6a1a1239
...@@ -30,6 +30,7 @@ ...@@ -30,6 +30,7 @@
#include <linux/string.h> #include <linux/string.h>
#include <linux/pci.h> #include <linux/pci.h>
#include <linux/proc_fs.h> #include <linux/proc_fs.h>
#include <linux/seq_file.h>
#include <linux/acpi.h> #include <linux/acpi.h>
#include <linux/efi.h> #include <linux/efi.h>
...@@ -1705,25 +1706,52 @@ ioc_init(u64 hpa, void *handle) ...@@ -1705,25 +1706,52 @@ ioc_init(u64 hpa, void *handle)
**************************************************************************/ **************************************************************************/
#ifdef CONFIG_PROC_FS #ifdef CONFIG_PROC_FS
static void *
ioc_start(struct seq_file *s, loff_t *pos)
{
struct ioc *ioc;
loff_t n = *pos;
for (ioc = ioc_list; ioc; ioc = ioc->next)
if (!n--)
return ioc;
return NULL;
}
static void *
ioc_next(struct seq_file *s, void *v, loff_t *pos)
{
struct ioc *ioc = v;
++*pos;
return ioc->next;
}
static void
ioc_stop(struct seq_file *s, void *v)
{
}
static int static int
sba_proc_info_one(char *buf, struct ioc *ioc) ioc_show(struct seq_file *s, void *v)
{ {
struct ioc *ioc = v;
int total_pages = (int) (ioc->res_size << 3); /* 8 bits per byte */ int total_pages = (int) (ioc->res_size << 3); /* 8 bits per byte */
unsigned long i = 0, avg = 0, min, max; unsigned long i = 0, avg = 0, min, max;
sprintf(buf, "Hewlett Packard %s IOC rev %d.%d\n", seq_printf(s, "Hewlett Packard %s IOC rev %d.%d\n",
ioc->name, ((ioc->rev >> 4) & 0xF), (ioc->rev & 0xF)); ioc->name, ((ioc->rev >> 4) & 0xF), (ioc->rev & 0xF));
sprintf(buf, "%sIO PDIR size : %d bytes (%d entries)\n", seq_printf(s, "IO PDIR size : %d bytes (%d entries)\n",
buf,
(int) ((ioc->res_size << 3) * sizeof(u64)), /* 8 bits/byte */ (int) ((ioc->res_size << 3) * sizeof(u64)), /* 8 bits/byte */
total_pages); total_pages);
sprintf(buf, "%sIO PDIR entries : %ld free %ld used (%d%%)\n", buf, seq_printf(s, "IO PDIR entries : %ld free %ld used (%d%%)\n",
total_pages - ioc->used_pages, ioc->used_pages, total_pages - ioc->used_pages, ioc->used_pages,
(int) (ioc->used_pages * 100 / total_pages)); (int) (ioc->used_pages * 100 / total_pages));
sprintf(buf, "%sResource bitmap : %d bytes (%d pages)\n", seq_printf(s, "Resource bitmap : %d bytes (%d pages)\n",
buf, ioc->res_size, ioc->res_size << 3); /* 8 bits per byte */ ioc->res_size, ioc->res_size << 3); /* 8 bits per byte */
min = max = ioc->avg_search[0]; min = max = ioc->avg_search[0];
for (i = 0; i < SBA_SEARCH_SAMPLE; i++) { for (i = 0; i < SBA_SEARCH_SAMPLE; i++) {
...@@ -1732,92 +1760,103 @@ sba_proc_info_one(char *buf, struct ioc *ioc) ...@@ -1732,92 +1760,103 @@ sba_proc_info_one(char *buf, struct ioc *ioc)
if (ioc->avg_search[i] < min) min = ioc->avg_search[i]; if (ioc->avg_search[i] < min) min = ioc->avg_search[i];
} }
avg /= SBA_SEARCH_SAMPLE; avg /= SBA_SEARCH_SAMPLE;
sprintf(buf, "%s Bitmap search : %ld/%ld/%ld (min/avg/max CPU Cycles)\n", seq_printf(s, " Bitmap search : %ld/%ld/%ld (min/avg/max CPU Cycles)\n", min, avg, max);
buf, min, avg, max);
sprintf(buf, "%spci_map_single(): %12ld calls %12ld pages (avg %d/1000)\n", seq_printf(s, "pci_map_single(): %12ld calls %12ld pages (avg %d/1000)\n",
buf, ioc->msingle_calls, ioc->msingle_pages, ioc->msingle_calls, ioc->msingle_pages,
(int) ((ioc->msingle_pages * 1000)/ioc->msingle_calls)); (int) ((ioc->msingle_pages * 1000)/ioc->msingle_calls));
#ifdef ALLOW_IOV_BYPASS #ifdef ALLOW_IOV_BYPASS
sprintf(buf, "%spci_map_single(): %12ld bypasses\n", seq_printf(s, "pci_map_single(): %12ld bypasses\n", ioc->msingle_bypass);
buf, ioc->msingle_bypass);
#endif #endif
sprintf(buf, "%spci_unmap_single: %12ld calls %12ld pages (avg %d/1000)\n", seq_printf(s, "pci_unmap_single: %12ld calls %12ld pages (avg %d/1000)\n",
buf, ioc->usingle_calls, ioc->usingle_pages, ioc->usingle_calls, ioc->usingle_pages,
(int) ((ioc->usingle_pages * 1000)/ioc->usingle_calls)); (int) ((ioc->usingle_pages * 1000)/ioc->usingle_calls));
#ifdef ALLOW_IOV_BYPASS #ifdef ALLOW_IOV_BYPASS
sprintf(buf, "%spci_unmap_single: %12ld bypasses\n", seq_printf(s, "pci_unmap_single: %12ld bypasses\n", ioc->usingle_bypass);
buf, ioc->usingle_bypass);
#endif #endif
sprintf(buf, "%spci_map_sg() : %12ld calls %12ld pages (avg %d/1000)\n", seq_printf(s, "pci_map_sg() : %12ld calls %12ld pages (avg %d/1000)\n",
buf, ioc->msg_calls, ioc->msg_pages, ioc->msg_calls, ioc->msg_pages,
(int) ((ioc->msg_pages * 1000)/ioc->msg_calls)); (int) ((ioc->msg_pages * 1000)/ioc->msg_calls));
#ifdef ALLOW_IOV_BYPASS #ifdef ALLOW_IOV_BYPASS
sprintf(buf, "%spci_map_sg() : %12ld bypasses\n", seq_printf(s, "pci_map_sg() : %12ld bypasses\n", ioc->msg_bypass);
buf, ioc->msg_bypass);
#endif #endif
sprintf(buf, "%spci_unmap_sg() : %12ld calls %12ld pages (avg %d/1000)\n", seq_printf(s, "pci_unmap_sg() : %12ld calls %12ld pages (avg %d/1000)\n",
buf, ioc->usg_calls, ioc->usg_pages, ioc->usg_calls, ioc->usg_pages, (int) ((ioc->usg_pages * 1000)/ioc->usg_calls));
(int) ((ioc->usg_pages * 1000)/ioc->usg_calls));
return strlen(buf); return 0;
} }
static struct seq_operations ioc_seq_ops = {
.start = ioc_start,
.next = ioc_next,
.stop = ioc_stop,
.show = ioc_show
};
static int static int
sba_proc_info(char *buf, char **start, off_t offset, int len) ioc_open(struct inode *inode, struct file *file)
{ {
struct ioc *ioc; return seq_open(file, &ioc_seq_ops);
char *base = buf;
for (ioc = ioc_list; ioc; ioc = ioc->next) {
buf += sba_proc_info_one(buf, ioc);
}
return strlen(base);
} }
static struct file_operations ioc_fops = {
.open = ioc_open,
.read = seq_read,
.llseek = seq_lseek,
.release = seq_release
};
static int static int
sba_resource_map_one(char *buf, struct ioc *ioc) ioc_map_show(struct seq_file *s, void *v)
{ {
struct ioc *ioc = v;
unsigned int *res_ptr = (unsigned int *)ioc->res_map; unsigned int *res_ptr = (unsigned int *)ioc->res_map;
int i; int i;
buf[0] = '\0'; for (i = 0; i < (ioc->res_size / sizeof(unsigned int)); ++i, ++res_ptr)
for(i = 0; i < (ioc->res_size / sizeof(unsigned int)); ++i, ++res_ptr) { seq_printf(s, "%s%08x", (i & 7) ? " " : "\n ", *res_ptr);
if ((i & 7) == 0) seq_printf(s, "\n");
strcat(buf,"\n ");
sprintf(buf, "%s %08x", buf, *res_ptr);
}
strcat(buf, "\n");
return strlen(buf); return 0;
} }
static struct seq_operations ioc_map_ops = {
.start = ioc_start,
.next = ioc_next,
.stop = ioc_stop,
.show = ioc_map_show
};
static int static int
sba_resource_map(char *buf, char **start, off_t offset, int len) ioc_map_open(struct inode *inode, struct file *file)
{ {
struct ioc *ioc; return seq_open(file, &ioc_map_ops);
char *base = buf;
for (ioc = ioc_list; ioc; ioc = ioc->next) {
buf += sba_resource_map_one(buf, ioc);
}
return strlen(base);
} }
static struct file_operations ioc_map_fops = {
.open = ioc_map_open,
.read = seq_read,
.llseek = seq_lseek,
.release = seq_release
};
static void __init static void __init
sba_proc_init(void) ioc_proc_init(void)
{ {
if (ioc_list) { if (ioc_list) {
struct proc_dir_entry * proc_mckinley_root; struct proc_dir_entry *dir, *entry;
dir = proc_mkdir("bus/mckinley", 0);
entry = create_proc_entry(ioc_list->name, 0, dir);
if (entry)
entry->proc_fops = &ioc_fops;
proc_mckinley_root = proc_mkdir("bus/mckinley", 0); entry = create_proc_entry("bitmap", 0, dir);
create_proc_info_entry(ioc_list->name, 0, proc_mckinley_root, sba_proc_info); if (entry)
create_proc_info_entry("bitmap", 0, proc_mckinley_root, sba_resource_map); entry->proc_fops = &ioc_map_fops;
} }
} }
#endif #endif
...@@ -1908,7 +1947,7 @@ sba_init(void) ...@@ -1908,7 +1947,7 @@ sba_init(void)
sba_connect_bus(b); sba_connect_bus(b);
#ifdef CONFIG_PROC_FS #ifdef CONFIG_PROC_FS
sba_proc_init(); ioc_proc_init();
#endif #endif
return 0; return 0;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment