diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/Kconfig.debug | 12 | ||||
-rw-r--r-- | lib/Makefile | 5 | ||||
-rw-r--r-- | lib/bitmap.c | 16 | ||||
-rw-r--r-- | lib/cpumask.c | 18 | ||||
-rw-r--r-- | lib/devres.c | 26 | ||||
-rw-r--r-- | lib/div64.c | 22 | ||||
-rw-r--r-- | lib/fault-inject.c | 41 | ||||
-rw-r--r-- | lib/genalloc.c | 4 | ||||
-rw-r--r-- | lib/kobject.c | 67 | ||||
-rw-r--r-- | lib/kobject_uevent.c | 28 | ||||
-rw-r--r-- | lib/kref.c | 2 | ||||
-rw-r--r-- | lib/string.c | 28 | ||||
-rw-r--r-- | lib/swiotlb.c | 184 | ||||
-rw-r--r-- | lib/textsearch.c | 2 | ||||
-rw-r--r-- | lib/vsprintf.c | 26 |
15 files changed, 247 insertions, 234 deletions
diff --git a/lib/Kconfig.debug b/lib/Kconfig.debug index 4448f91b865..79afd00bbe5 100644 --- a/lib/Kconfig.debug +++ b/lib/Kconfig.debug @@ -261,7 +261,7 @@ config LOCKDEP bool depends on DEBUG_KERNEL && TRACE_IRQFLAGS_SUPPORT && STACKTRACE_SUPPORT && LOCKDEP_SUPPORT select STACKTRACE - select FRAME_POINTER if !X86 + select FRAME_POINTER if !X86 && !MIPS select KALLSYMS select KALLSYMS_ALL @@ -411,8 +411,6 @@ config LKDTM config FAULT_INJECTION bool "Fault-injection framework" depends on DEBUG_KERNEL - depends on STACKTRACE - select FRAME_POINTER help Provide fault-injection framework. For more details, see Documentation/fault-injection/. @@ -440,3 +438,11 @@ config FAULT_INJECTION_DEBUG_FS depends on FAULT_INJECTION && SYSFS && DEBUG_FS help Enable configuration of fault-injection capabilities via debugfs. + +config FAULT_INJECTION_STACKTRACE_FILTER + bool "stacktrace filter for fault-injection capabilities" + depends on FAULT_INJECTION_DEBUG_FS && STACKTRACE_SUPPORT + select STACKTRACE + select FRAME_POINTER + help + Provide stacktrace filter for fault-injection capabilities diff --git a/lib/Makefile b/lib/Makefile index 992a39ef9ff..ae57f357fec 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -4,7 +4,7 @@ lib-y := ctype.o string.o vsprintf.o cmdline.o \ rbtree.o radix-tree.o dump_stack.o \ - idr.o div64.o int_sqrt.o bitmap.o extable.o prio_tree.o \ + idr.o int_sqrt.o bitmap.o extable.o prio_tree.o \ sha1.o irq_regs.o reciprocal_div.o lib-$(CONFIG_MMU) += ioremap.o @@ -12,7 +12,8 @@ lib-$(CONFIG_SMP) += cpumask.o lib-y += kobject.o kref.o kobject_uevent.o klist.o -obj-y += sort.o parser.o halfmd4.o debug_locks.o random32.o bust_spinlocks.o +obj-y += div64.o sort.o parser.o halfmd4.o debug_locks.o random32.o \ + bust_spinlocks.o ifeq ($(CONFIG_DEBUG_KOBJECT),y) CFLAGS_kobject.o += -DDEBUG diff --git a/lib/bitmap.c b/lib/bitmap.c index ee6e58fce8f..26ebafa8c41 100644 --- a/lib/bitmap.c +++ b/lib/bitmap.c @@ -97,10 +97,10 @@ EXPORT_SYMBOL(__bitmap_complement); /** * __bitmap_shift_right - logical right shift of the bits in a bitmap - * @dst - destination bitmap - * @src - source bitmap - * @nbits - shift by this many bits - * @bits - bitmap size, in bits + * @dst : destination bitmap + * @src : source bitmap + * @shift : shift by this many bits + * @bits : bitmap size, in bits * * Shifting right (dividing) means moving bits in the MS -> LS bit * direction. Zeros are fed into the vacated MS positions and the @@ -141,10 +141,10 @@ EXPORT_SYMBOL(__bitmap_shift_right); /** * __bitmap_shift_left - logical left shift of the bits in a bitmap - * @dst - destination bitmap - * @src - source bitmap - * @nbits - shift by this many bits - * @bits - bitmap size, in bits + * @dst : destination bitmap + * @src : source bitmap + * @shift : shift by this many bits + * @bits : bitmap size, in bits * * Shifting left (multiplying) means moving bits in the LS -> MS * direction. Zeros are fed into the vacated LS bit positions diff --git a/lib/cpumask.c b/lib/cpumask.c index 3a67dc5ada7..1ea2c184315 100644 --- a/lib/cpumask.c +++ b/lib/cpumask.c @@ -15,22 +15,8 @@ int __next_cpu(int n, const cpumask_t *srcp) } EXPORT_SYMBOL(__next_cpu); -/* - * Find the highest possible smp_processor_id() - * - * Note: if we're prepared to assume that cpu_possible_map never changes - * (reasonable) then this function should cache its return value. - */ -int highest_possible_processor_id(void) -{ - unsigned int cpu; - unsigned highest = 0; - - for_each_cpu_mask(cpu, cpu_possible_map) - highest = cpu; - return highest; -} -EXPORT_SYMBOL(highest_possible_processor_id); +int nr_cpu_ids; +EXPORT_SYMBOL(nr_cpu_ids); int __any_online_cpu(const cpumask_t *mask) { diff --git a/lib/devres.c b/lib/devres.c index eb38849aa71..b1d336ce7f3 100644 --- a/lib/devres.c +++ b/lib/devres.c @@ -296,5 +296,31 @@ int pcim_iomap_regions(struct pci_dev *pdev, u16 mask, const char *name) return rc; } EXPORT_SYMBOL(pcim_iomap_regions); + +/** + * pcim_iounmap_regions - Unmap and release PCI BARs + * @pdev: PCI device to map IO resources for + * @mask: Mask of BARs to unmap and release + * + * Unamp and release regions specified by @mask. + */ +void pcim_iounmap_regions(struct pci_dev *pdev, u16 mask) +{ + void __iomem * const *iomap; + int i; + + iomap = pcim_iomap_table(pdev); + if (!iomap) + return; + + for (i = 0; i < DEVICE_COUNT_RESOURCE; i++) { + if (!(mask & (1 << i))) + continue; + + pcim_iounmap(pdev, iomap[i]); + pci_release_region(pdev, i); + } +} +EXPORT_SYMBOL(pcim_iounmap_regions); #endif #endif diff --git a/lib/div64.c b/lib/div64.c index 365719f8483..b71cf93c529 100644 --- a/lib/div64.c +++ b/lib/div64.c @@ -23,7 +23,7 @@ /* Not needed on 64bit architectures */ #if BITS_PER_LONG == 32 -uint32_t __div64_32(uint64_t *n, uint32_t base) +uint32_t __attribute__((weak)) __div64_32(uint64_t *n, uint32_t base) { uint64_t rem = *n; uint64_t b = base; @@ -58,4 +58,24 @@ uint32_t __div64_32(uint64_t *n, uint32_t base) EXPORT_SYMBOL(__div64_32); +/* 64bit divisor, dividend and result. dynamic precision */ +uint64_t div64_64(uint64_t dividend, uint64_t divisor) +{ + uint32_t high, d; + + high = divisor >> 32; + if (high) { + unsigned int shift = fls(high); + + d = divisor >> shift; + dividend >>= shift; + } else + d = divisor; + + do_div(dividend, d); + + return dividend; +} +EXPORT_SYMBOL(div64_64); + #endif /* BITS_PER_LONG == 32 */ diff --git a/lib/fault-inject.c b/lib/fault-inject.c index b5a90fc056d..0fabd12c39d 100644 --- a/lib/fault-inject.c +++ b/lib/fault-inject.c @@ -55,7 +55,7 @@ static bool fail_task(struct fault_attr *attr, struct task_struct *task) #define MAX_STACK_TRACE_DEPTH 32 -#if defined(CONFIG_STACKTRACE) +#ifdef CONFIG_FAULT_INJECTION_STACKTRACE_FILTER static bool fail_stacktrace(struct fault_attr *attr) { @@ -90,17 +90,10 @@ static bool fail_stacktrace(struct fault_attr *attr) static inline bool fail_stacktrace(struct fault_attr *attr) { - static bool firsttime = true; - - if (firsttime) { - printk(KERN_WARNING - "This architecture does not implement save_stack_trace()\n"); - firsttime = false; - } - return false; + return true; } -#endif +#endif /* CONFIG_FAULT_INJECTION_STACKTRACE_FILTER */ /* * This code is stolen from failmalloc-1.0 @@ -217,6 +210,8 @@ void cleanup_fault_attr_dentries(struct fault_attr *attr) debugfs_remove(attr->dentries.task_filter_file); attr->dentries.task_filter_file = NULL; +#ifdef CONFIG_FAULT_INJECTION_STACKTRACE_FILTER + debugfs_remove(attr->dentries.stacktrace_depth_file); attr->dentries.stacktrace_depth_file = NULL; @@ -232,6 +227,8 @@ void cleanup_fault_attr_dentries(struct fault_attr *attr) debugfs_remove(attr->dentries.reject_end_file); attr->dentries.reject_end_file = NULL; +#endif /* CONFIG_FAULT_INJECTION_STACKTRACE_FILTER */ + if (attr->dentries.dir) WARN_ON(!simple_empty(attr->dentries.dir)); @@ -269,6 +266,13 @@ int init_fault_attr_dentries(struct fault_attr *attr, const char *name) attr->dentries.task_filter_file = debugfs_create_bool("task-filter", mode, dir, &attr->task_filter); + if (!attr->dentries.probability_file || !attr->dentries.interval_file || + !attr->dentries.times_file || !attr->dentries.space_file || + !attr->dentries.verbose_file || !attr->dentries.task_filter_file) + goto fail; + +#ifdef CONFIG_FAULT_INJECTION_STACKTRACE_FILTER + attr->dentries.stacktrace_depth_file = debugfs_create_ul_MAX_STACK_TRACE_DEPTH( "stacktrace-depth", mode, dir, &attr->stacktrace_depth); @@ -285,18 +289,15 @@ int init_fault_attr_dentries(struct fault_attr *attr, const char *name) attr->dentries.reject_end_file = debugfs_create_ul("reject-end", mode, dir, &attr->reject_end); - - if (!attr->dentries.probability_file || !attr->dentries.interval_file - || !attr->dentries.times_file || !attr->dentries.space_file - || !attr->dentries.verbose_file || !attr->dentries.task_filter_file - || !attr->dentries.stacktrace_depth_file - || !attr->dentries.require_start_file - || !attr->dentries.require_end_file - || !attr->dentries.reject_start_file - || !attr->dentries.reject_end_file - ) + if (!attr->dentries.stacktrace_depth_file || + !attr->dentries.require_start_file || + !attr->dentries.require_end_file || + !attr->dentries.reject_start_file || + !attr->dentries.reject_end_file) goto fail; +#endif /* CONFIG_FAULT_INJECTION_STACKTRACE_FILTER */ + return 0; fail: cleanup_fault_attr_dentries(attr); diff --git a/lib/genalloc.c b/lib/genalloc.c index 75ae68ce03e..eb7c2bab9eb 100644 --- a/lib/genalloc.c +++ b/lib/genalloc.c @@ -148,7 +148,7 @@ unsigned long gen_pool_alloc(struct gen_pool *pool, size_t size) addr = chunk->start_addr + ((unsigned long)start_bit << order); while (nbits--) - __set_bit(start_bit++, &chunk->bits); + __set_bit(start_bit++, chunk->bits); spin_unlock_irqrestore(&chunk->lock, flags); read_unlock(&pool->lock); return addr; @@ -187,7 +187,7 @@ void gen_pool_free(struct gen_pool *pool, unsigned long addr, size_t size) spin_lock_irqsave(&chunk->lock, flags); bit = (addr - chunk->start_addr) >> order; while (nbits--) - __clear_bit(bit++, &chunk->bits); + __clear_bit(bit++, chunk->bits); spin_unlock_irqrestore(&chunk->lock, flags); break; } diff --git a/lib/kobject.c b/lib/kobject.c index 2782f49e906..cecf2fbede3 100644 --- a/lib/kobject.c +++ b/lib/kobject.c @@ -157,7 +157,7 @@ static void unlink(struct kobject * kobj) } /** - * kobject_add - add an object to the hierarchy. + * kobject_shadow_add - add an object to the hierarchy. * @kobj: object. * @shadow_parent: sysfs directory to add to. */ @@ -171,9 +171,10 @@ int kobject_shadow_add(struct kobject * kobj, struct dentry *shadow_parent) return -ENOENT; if (!kobj->k_name) kobj->k_name = kobj->name; - if (!kobj->k_name) { + if (!*kobj->k_name) { pr_debug("kobject attempted to be registered with no name!\n"); WARN_ON(1); + kobject_put(kobj); return -EINVAL; } parent = kobject_get(kobj->parent); @@ -190,8 +191,8 @@ int kobject_shadow_add(struct kobject * kobj, struct dentry *shadow_parent) list_add_tail(&kobj->entry,&kobj->kset->list); spin_unlock(&kobj->kset->list_lock); + kobj->parent = parent; } - kobj->parent = parent; error = create_dir(kobj, shadow_parent); if (error) { @@ -311,13 +312,43 @@ EXPORT_SYMBOL(kobject_set_name); int kobject_rename(struct kobject * kobj, const char *new_name) { int error = 0; + const char *devpath = NULL; + char *devpath_string = NULL; + char *envp[2]; kobj = kobject_get(kobj); if (!kobj) return -EINVAL; if (!kobj->parent) return -EINVAL; + + devpath = kobject_get_path(kobj, GFP_KERNEL); + if (!devpath) { + error = -ENOMEM; + goto out; + } + devpath_string = kmalloc(strlen(devpath) + 15, GFP_KERNEL); + if (!devpath_string) { + error = -ENOMEM; + goto out; + } + sprintf(devpath_string, "DEVPATH_OLD=%s", devpath); + envp[0] = devpath_string; + envp[1] = NULL; + /* Note : if we want to send the new name alone, not the full path, + * we could probably use kobject_name(kobj); */ + error = sysfs_rename_dir(kobj, kobj->parent->dentry, new_name); + + /* This function is mostly/only used for network interface. + * Some hotplug package track interfaces by their name and + * therefore want to know when the name is changed by the user. */ + if (!error) + kobject_uevent_env(kobj, KOBJ_MOVE, envp); + +out: + kfree(devpath_string); + kfree(devpath); kobject_put(kobj); return error; @@ -326,6 +357,7 @@ int kobject_rename(struct kobject * kobj, const char *new_name) /** * kobject_rename - change the name of an object * @kobj: object in question. + * @new_parent: object's new parent * @new_name: object's new name */ @@ -384,9 +416,11 @@ int kobject_move(struct kobject *kobj, struct kobject *new_parent) goto out; old_parent = kobj->parent; kobj->parent = new_parent; + new_parent = NULL; kobject_put(old_parent); kobject_uevent_env(kobj, KOBJ_MOVE, envp); out: + kobject_put(new_parent); kobject_put(kobj); kfree(devpath_string); kfree(devpath); @@ -485,13 +519,15 @@ static struct kobj_type dir_ktype = { }; /** - * kobject_add_dir - add sub directory of object. + * kobject_kset_add_dir - add sub directory of object. + * @kset: kset the directory is belongs to. * @parent: object in which a directory is created. * @name: directory name. * * Add a plain directory object as child of given object. */ -struct kobject *kobject_add_dir(struct kobject *parent, const char *name) +struct kobject *kobject_kset_add_dir(struct kset *kset, + struct kobject *parent, const char *name) { struct kobject *k; int ret; @@ -503,13 +539,14 @@ struct kobject *kobject_add_dir(struct kobject *parent, const char *name) if (!k) return NULL; + k->kset = kset; k->parent = parent; k->ktype = &dir_ktype; kobject_set_name(k, name); ret = kobject_register(k); if (ret < 0) { - printk(KERN_WARNING "kobject_add_dir: " - "kobject_register error: %d\n", ret); + printk(KERN_WARNING "%s: kobject_register error: %d\n", + __func__, ret); kobject_del(k); return NULL; } @@ -518,6 +555,18 @@ struct kobject *kobject_add_dir(struct kobject *parent, const char *name) } /** + * kobject_add_dir - add sub directory of object. + * @parent: object in which a directory is created. + * @name: directory name. + * + * Add a plain directory object as child of given object. + */ +struct kobject *kobject_add_dir(struct kobject *parent, const char *name) +{ + return kobject_kset_add_dir(NULL, parent, name); +} + +/** * kset_init - initialize a kset for use * @k: kset */ @@ -610,7 +659,6 @@ struct kobject * kset_find_obj(struct kset * kset, const char * name) void subsystem_init(struct subsystem * s) { - init_rwsem(&s->rwsem); kset_init(&s->kset); } @@ -619,8 +667,7 @@ void subsystem_init(struct subsystem * s) * @s: the subsystem we're registering. * * Once we register the subsystem, we want to make sure that - * the kset points back to this subsystem for correct usage of - * the rwsem. + * the kset points back to this subsystem. */ int subsystem_register(struct subsystem * s) diff --git a/lib/kobject_uevent.c b/lib/kobject_uevent.c index 84272ed77f0..12e311dc664 100644 --- a/lib/kobject_uevent.c +++ b/lib/kobject_uevent.c @@ -42,10 +42,6 @@ static char *action_to_string(enum kobject_action action) return "remove"; case KOBJ_CHANGE: return "change"; - case KOBJ_MOUNT: - return "mount"; - case KOBJ_UMOUNT: - return "umount"; case KOBJ_OFFLINE: return "offline"; case KOBJ_ONLINE: @@ -95,10 +91,8 @@ int kobject_uevent_env(struct kobject *kobj, enum kobject_action action, /* search the kset we belong to */ top_kobj = kobj; - if (!top_kobj->kset && top_kobj->parent) { - do { - top_kobj = top_kobj->parent; - } while (!top_kobj->kset && top_kobj->parent); + while (!top_kobj->kset && top_kobj->parent) { + top_kobj = top_kobj->parent; } if (!top_kobj->kset) { pr_debug("kobject attempted to send uevent without kset!\n"); @@ -115,6 +109,16 @@ int kobject_uevent_env(struct kobject *kobj, enum kobject_action action, return 0; } + /* originating subsystem */ + if (uevent_ops && uevent_ops->name) + subsystem = uevent_ops->name(kset, kobj); + else + subsystem = kobject_name(&kset->kobj); + if (!subsystem) { + pr_debug("unset subsytem caused the event to drop!\n"); + return 0; + } + /* environment index */ envp = kzalloc(NUM_ENVP * sizeof (char *), GFP_KERNEL); if (!envp) @@ -134,12 +138,6 @@ int kobject_uevent_env(struct kobject *kobj, enum kobject_action action, goto exit; } - /* originating subsystem */ - if (uevent_ops && uevent_ops->name) - subsystem = uevent_ops->name(kset, kobj); - else - subsystem = kobject_name(&kset->kobj); - /* event environemnt for helper process only */ envp[i++] = "HOME=/"; envp[i++] = "PATH=/sbin:/bin:/usr/sbin:/usr/bin"; @@ -293,7 +291,7 @@ EXPORT_SYMBOL_GPL(add_uevent_var); static int __init kobject_uevent_init(void) { uevent_sock = netlink_kernel_create(NETLINK_KOBJECT_UEVENT, 1, NULL, - THIS_MODULE); + NULL, THIS_MODULE); if (!uevent_sock) { printk(KERN_ERR diff --git a/lib/kref.c b/lib/kref.c index 0d07cc31c81..a6dc3ec328e 100644 --- a/lib/kref.c +++ b/lib/kref.c @@ -21,6 +21,7 @@ void kref_init(struct kref *kref) { atomic_set(&kref->refcount,1); + smp_mb(); } /** @@ -31,6 +32,7 @@ void kref_get(struct kref *kref) { WARN_ON(!atomic_read(&kref->refcount)); atomic_inc(&kref->refcount); + smp_mb__after_atomic_inc(); } /** diff --git a/lib/string.c b/lib/string.c index bab440fb0df..5efafed3d6b 100644 --- a/lib/string.c +++ b/lib/string.c @@ -60,6 +60,34 @@ int strnicmp(const char *s1, const char *s2, size_t len) EXPORT_SYMBOL(strnicmp); #endif +#ifndef __HAVE_ARCH_STRCASECMP +int strcasecmp(const char *s1, const char *s2) +{ + int c1, c2; + + do { + c1 = tolower(*s1++); + c2 = tolower(*s2++); + } while (c1 == c2 && c1 != 0); + return c1 - c2; +} +EXPORT_SYMBOL(strcasecmp); +#endif + +#ifndef __HAVE_ARCH_STRNCASECMP +int strncasecmp(const char *s1, const char *s2, size_t n) +{ + int c1, c2; + + do { + c1 = tolower(*s1++); + c2 = tolower(*s2++); + } while ((--n > 0) && c1 == c2 && c1 != 0); + return c1 - c2; +} +EXPORT_SYMBOL(strncasecmp); +#endif + #ifndef __HAVE_ARCH_STRCPY /** * strcpy - Copy a %NUL terminated string diff --git a/lib/swiotlb.c b/lib/swiotlb.c index 623a68af8b1..9970e55c90b 100644 --- a/lib/swiotlb.c +++ b/lib/swiotlb.c @@ -28,7 +28,6 @@ #include <asm/io.h> #include <asm/dma.h> #include <asm/scatterlist.h> -#include <asm/swiotlb.h> #include <linux/init.h> #include <linux/bootmem.h> @@ -36,10 +35,8 @@ #define OFFSET(val,align) ((unsigned long) \ ( (val) & ( (align) - 1))) -#ifndef SG_ENT_VIRT_ADDRESS #define SG_ENT_VIRT_ADDRESS(sg) (page_address((sg)->page) + (sg)->offset) #define SG_ENT_PHYS_ADDRESS(sg) virt_to_bus(SG_ENT_VIRT_ADDRESS(sg)) -#endif /* * Maximum allowable number of contiguous slabs to map, @@ -104,25 +101,13 @@ static unsigned int io_tlb_index; * We need to save away the original address corresponding to a mapped entry * for the sync operations. */ -#ifndef SWIOTLB_ARCH_HAS_IO_TLB_ADDR_T -typedef char *io_tlb_addr_t; -#define swiotlb_orig_addr_null(buffer) (!(buffer)) -#define ptr_to_io_tlb_addr(ptr) (ptr) -#define page_to_io_tlb_addr(pg, off) (page_address(pg) + (off)) -#define sg_to_io_tlb_addr(sg) SG_ENT_VIRT_ADDRESS(sg) -#endif -static io_tlb_addr_t *io_tlb_orig_addr; +static unsigned char **io_tlb_orig_addr; /* * Protect the above data structures in the map and unmap calls */ static DEFINE_SPINLOCK(io_tlb_lock); -#ifdef SWIOTLB_EXTRA_VARIABLES -SWIOTLB_EXTRA_VARIABLES; -#endif - -#ifndef SWIOTLB_ARCH_HAS_SETUP_IO_TLB_NPAGES static int __init setup_io_tlb_npages(char *str) { @@ -137,25 +122,9 @@ setup_io_tlb_npages(char *str) swiotlb_force = 1; return 1; } -#endif __setup("swiotlb=", setup_io_tlb_npages); /* make io_tlb_overflow tunable too? */ -#ifndef swiotlb_adjust_size -#define swiotlb_adjust_size(size) ((void)0) -#endif - -#ifndef swiotlb_adjust_seg -#define swiotlb_adjust_seg(start, size) ((void)0) -#endif - -#ifndef swiotlb_print_info -#define swiotlb_print_info(bytes) \ - printk(KERN_INFO "Placing %luMB software IO TLB between 0x%lx - " \ - "0x%lx\n", bytes >> 20, \ - virt_to_bus(io_tlb_start), virt_to_bus(io_tlb_end)) -#endif - /* * Statically reserve bounce buffer space and initialize bounce buffer data * structures for the software IO TLB used to implement the DMA API. @@ -169,8 +138,6 @@ swiotlb_init_with_default_size(size_t default_size) io_tlb_nslabs = (default_size >> IO_TLB_SHIFT); io_tlb_nslabs = ALIGN(io_tlb_nslabs, IO_TLB_SEGSIZE); } - swiotlb_adjust_size(io_tlb_nslabs); - swiotlb_adjust_size(io_tlb_overflow); bytes = io_tlb_nslabs << IO_TLB_SHIFT; @@ -188,14 +155,10 @@ swiotlb_init_with_default_size(size_t default_size) * between io_tlb_start and io_tlb_end. */ io_tlb_list = alloc_bootmem(io_tlb_nslabs * sizeof(int)); - for (i = 0; i < io_tlb_nslabs; i++) { - if ( !(i % IO_TLB_SEGSIZE) ) - swiotlb_adjust_seg(io_tlb_start + (i << IO_TLB_SHIFT), - IO_TLB_SEGSIZE << IO_TLB_SHIFT); + for (i = 0; i < io_tlb_nslabs; i++) io_tlb_list[i] = IO_TLB_SEGSIZE - OFFSET(i, IO_TLB_SEGSIZE); - } io_tlb_index = 0; - io_tlb_orig_addr = alloc_bootmem(io_tlb_nslabs * sizeof(io_tlb_addr_t)); + io_tlb_orig_addr = alloc_bootmem(io_tlb_nslabs * sizeof(char *)); /* * Get the overflow emergency buffer @@ -203,21 +166,17 @@ swiotlb_init_with_default_size(size_t default_size) io_tlb_overflow_buffer = alloc_bootmem_low(io_tlb_overflow); if (!io_tlb_overflow_buffer) panic("Cannot allocate SWIOTLB overflow buffer!\n"); - swiotlb_adjust_seg(io_tlb_overflow_buffer, io_tlb_overflow); - swiotlb_print_info(bytes); + printk(KERN_INFO "Placing software IO TLB between 0x%lx - 0x%lx\n", + virt_to_bus(io_tlb_start), virt_to_bus(io_tlb_end)); } -#ifndef __swiotlb_init_with_default_size -#define __swiotlb_init_with_default_size swiotlb_init_with_default_size -#endif void __init swiotlb_init(void) { - __swiotlb_init_with_default_size(64 * (1<<20)); /* default to 64MB */ + swiotlb_init_with_default_size(64 * (1<<20)); /* default to 64MB */ } -#ifdef SWIOTLB_ARCH_NEED_LATE_INIT /* * Systems with larger DMA zones (those that don't support ISA) can * initialize the swiotlb later using the slab allocator if needed. @@ -275,12 +234,12 @@ swiotlb_late_init_with_default_size(size_t default_size) io_tlb_list[i] = IO_TLB_SEGSIZE - OFFSET(i, IO_TLB_SEGSIZE); io_tlb_index = 0; - io_tlb_orig_addr = (io_tlb_addr_t *)__get_free_pages(GFP_KERNEL, - get_order(io_tlb_nslabs * sizeof(io_tlb_addr_t))); + io_tlb_orig_addr = (unsigned char **)__get_free_pages(GFP_KERNEL, + get_order(io_tlb_nslabs * sizeof(char *))); if (!io_tlb_orig_addr) goto cleanup3; - memset(io_tlb_orig_addr, 0, io_tlb_nslabs * sizeof(io_tlb_addr_t)); + memset(io_tlb_orig_addr, 0, io_tlb_nslabs * sizeof(char *)); /* * Get the overflow emergency buffer @@ -290,17 +249,19 @@ swiotlb_late_init_with_default_size(size_t default_size) if (!io_tlb_overflow_buffer) goto cleanup4; - swiotlb_print_info(bytes); + printk(KERN_INFO "Placing %luMB software IO TLB between 0x%lx - " + "0x%lx\n", bytes >> 20, + virt_to_bus(io_tlb_start), virt_to_bus(io_tlb_end)); return 0; cleanup4: - free_pages((unsigned long)io_tlb_orig_addr, - get_order(io_tlb_nslabs * sizeof(io_tlb_addr_t))); + free_pages((unsigned long)io_tlb_orig_addr, get_order(io_tlb_nslabs * + sizeof(char *))); io_tlb_orig_addr = NULL; cleanup3: - free_pages((unsigned long)io_tlb_list, - get_order(io_tlb_nslabs * sizeof(int))); + free_pages((unsigned long)io_tlb_list, get_order(io_tlb_nslabs * + sizeof(int))); io_tlb_list = NULL; cleanup2: io_tlb_end = NULL; @@ -310,9 +271,7 @@ cleanup1: io_tlb_nslabs = req_nslabs; return -ENOMEM; } -#endif -#ifndef SWIOTLB_ARCH_HAS_NEEDS_MAPPING static int address_needs_mapping(struct device *hwdev, dma_addr_t addr) { @@ -323,35 +282,11 @@ address_needs_mapping(struct device *hwdev, dma_addr_t addr) return (addr & ~mask) != 0; } -static inline int range_needs_mapping(const void *ptr, size_t size) -{ - return swiotlb_force; -} - -static inline int order_needs_mapping(unsigned int order) -{ - return 0; -} -#endif - -static void -__sync_single(io_tlb_addr_t buffer, char *dma_addr, size_t size, int dir) -{ -#ifndef SWIOTLB_ARCH_HAS_SYNC_SINGLE - if (dir == DMA_TO_DEVICE) - memcpy(dma_addr, buffer, size); - else - memcpy(buffer, dma_addr, size); -#else - __swiotlb_arch_sync_single(buffer, dma_addr, size, dir); -#endif -} - /* * Allocates bounce buffer and returns its kernel virtual address. */ static void * -map_single(struct device *hwdev, io_tlb_addr_t buffer, size_t size, int dir) +map_single(struct device *hwdev, char *buffer, size_t size, int dir) { unsigned long flags; char *dma_addr; @@ -424,7 +359,7 @@ map_single(struct device *hwdev, io_tlb_addr_t buffer, size_t size, int dir) */ io_tlb_orig_addr[index] = buffer; if (dir == DMA_TO_DEVICE || dir == DMA_BIDIRECTIONAL) - __sync_single(buffer, dma_addr, size, DMA_TO_DEVICE); + memcpy(dma_addr, buffer, size); return dma_addr; } @@ -438,18 +373,17 @@ unmap_single(struct device *hwdev, char *dma_addr, size_t size, int dir) unsigned long flags; int i, count, nslots = ALIGN(size, 1 << IO_TLB_SHIFT) >> IO_TLB_SHIFT; int index = (dma_addr - io_tlb_start) >> IO_TLB_SHIFT; - io_tlb_addr_t buffer = io_tlb_orig_addr[index]; + char *buffer = io_tlb_orig_addr[index]; /* * First, sync the memory before unmapping the entry */ - if (!swiotlb_orig_addr_null(buffer) - && ((dir == DMA_FROM_DEVICE) || (dir == DMA_BIDIRECTIONAL))) + if (buffer && ((dir == DMA_FROM_DEVICE) || (dir == DMA_BIDIRECTIONAL))) /* * bounce... copy the data back into the original buffer * and * delete the bounce buffer. */ - __sync_single(buffer, dma_addr, size, DMA_FROM_DEVICE); + memcpy(buffer, dma_addr, size); /* * Return the buffer to the free list by setting the corresponding @@ -482,18 +416,18 @@ sync_single(struct device *hwdev, char *dma_addr, size_t size, int dir, int target) { int index = (dma_addr - io_tlb_start) >> IO_TLB_SHIFT; - io_tlb_addr_t buffer = io_tlb_orig_addr[index]; + char *buffer = io_tlb_orig_addr[index]; switch (target) { case SYNC_FOR_CPU: if (likely(dir == DMA_FROM_DEVICE || dir == DMA_BIDIRECTIONAL)) - __sync_single(buffer, dma_addr, size, DMA_FROM_DEVICE); + memcpy(buffer, dma_addr, size); else BUG_ON(dir != DMA_TO_DEVICE); break; case SYNC_FOR_DEVICE: if (likely(dir == DMA_TO_DEVICE || dir == DMA_BIDIRECTIONAL)) - __sync_single(buffer, dma_addr, size, DMA_TO_DEVICE); + memcpy(dma_addr, buffer, size); else BUG_ON(dir != DMA_FROM_DEVICE); break; @@ -502,8 +436,6 @@ sync_single(struct device *hwdev, char *dma_addr, size_t size, } } -#ifdef SWIOTLB_ARCH_NEED_ALLOC - void * swiotlb_alloc_coherent(struct device *hwdev, size_t size, dma_addr_t *dma_handle, gfp_t flags) @@ -519,10 +451,7 @@ swiotlb_alloc_coherent(struct device *hwdev, size_t size, */ flags |= GFP_DMA; - if (!order_needs_mapping(order)) - ret = (void *)__get_free_pages(flags, order); - else - ret = NULL; + ret = (void *)__get_free_pages(flags, order); if (ret && address_needs_mapping(hwdev, virt_to_bus(ret))) { /* * The allocated memory isn't reachable by the device. @@ -560,7 +489,6 @@ swiotlb_alloc_coherent(struct device *hwdev, size_t size, *dma_handle = dev_addr; return ret; } -EXPORT_SYMBOL(swiotlb_alloc_coherent); void swiotlb_free_coherent(struct device *hwdev, size_t size, void *vaddr, @@ -573,9 +501,6 @@ swiotlb_free_coherent(struct device *hwdev, size_t size, void *vaddr, /* DMA_TO_DEVICE to avoid memcpy in unmap_single */ swiotlb_unmap_single (hwdev, dma_handle, size, DMA_TO_DEVICE); } -EXPORT_SYMBOL(swiotlb_free_coherent); - -#endif static void swiotlb_full(struct device *dev, size_t size, int dir, int do_panic) @@ -617,14 +542,13 @@ swiotlb_map_single(struct device *hwdev, void *ptr, size_t size, int dir) * we can safely return the device addr and not worry about bounce * buffering it. */ - if (!range_needs_mapping(ptr, size) - && !address_needs_mapping(hwdev, dev_addr)) + if (!address_needs_mapping(hwdev, dev_addr) && !swiotlb_force) return dev_addr; /* * Oh well, have to allocate and map a bounce buffer. */ - map = map_single(hwdev, ptr_to_io_tlb_addr(ptr), size, dir); + map = map_single(hwdev, ptr, size, dir); if (!map) { swiotlb_full(hwdev, size, dir, 1); map = io_tlb_overflow_buffer; @@ -752,16 +676,17 @@ int swiotlb_map_sg(struct device *hwdev, struct scatterlist *sg, int nelems, int dir) { + void *addr; dma_addr_t dev_addr; int i; BUG_ON(dir == DMA_NONE); for (i = 0; i < nelems; i++, sg++) { - dev_addr = SG_ENT_PHYS_ADDRESS(sg); - if (range_needs_mapping(SG_ENT_VIRT_ADDRESS(sg), sg->length) - || address_needs_mapping(hwdev, dev_addr)) { - void *map = map_single(hwdev, sg_to_io_tlb_addr(sg), sg->length, dir); + addr = SG_ENT_VIRT_ADDRESS(sg); + dev_addr = virt_to_bus(addr); + if (swiotlb_force || address_needs_mapping(hwdev, dev_addr)) { + void *map = map_single(hwdev, addr, sg->length, dir); if (!map) { /* Don't panic here, we expect map_sg users to do proper error handling. */ @@ -835,44 +760,6 @@ swiotlb_sync_sg_for_device(struct device *hwdev, struct scatterlist *sg, swiotlb_sync_sg(hwdev, sg, nelems, dir, SYNC_FOR_DEVICE); } -#ifdef SWIOTLB_ARCH_NEED_MAP_PAGE - -dma_addr_t -swiotlb_map_page(struct device *hwdev, struct page *page, - unsigned long offset, size_t size, - enum dma_data_direction direction) -{ - dma_addr_t dev_addr; - char *map; - - dev_addr = page_to_bus(page) + offset; - if (address_needs_mapping(hwdev, dev_addr)) { - map = map_single(hwdev, page_to_io_tlb_addr(page, offset), size, direction); - if (!map) { - swiotlb_full(hwdev, size, direction, 1); - map = io_tlb_overflow_buffer; - } - dev_addr = virt_to_bus(map); - } - - return dev_addr; -} - -void -swiotlb_unmap_page(struct device *hwdev, dma_addr_t dev_addr, - size_t size, enum dma_data_direction direction) -{ - char *dma_addr = bus_to_virt(dev_addr); - - BUG_ON(direction == DMA_NONE); - if (dma_addr >= io_tlb_start && dma_addr < io_tlb_end) - unmap_single(hwdev, dma_addr, size, direction); - else if (direction == DMA_FROM_DEVICE) - dma_mark_clean(dma_addr, size); -} - -#endif - int swiotlb_dma_mapping_error(dma_addr_t dma_addr) { @@ -885,13 +772,10 @@ swiotlb_dma_mapping_error(dma_addr_t dma_addr) * during bus mastering, then you would pass 0x00ffffff as the mask to * this function. */ -#ifndef __swiotlb_dma_supported -#define __swiotlb_dma_supported(hwdev, mask) (virt_to_bus(io_tlb_end - 1) <= (mask)) -#endif int swiotlb_dma_supported(struct device *hwdev, u64 mask) { - return __swiotlb_dma_supported(hwdev, mask); + return virt_to_bus(io_tlb_end - 1) <= mask; } EXPORT_SYMBOL(swiotlb_init); @@ -906,4 +790,6 @@ EXPORT_SYMBOL_GPL(swiotlb_sync_single_range_for_device); EXPORT_SYMBOL(swiotlb_sync_sg_for_cpu); EXPORT_SYMBOL(swiotlb_sync_sg_for_device); EXPORT_SYMBOL(swiotlb_dma_mapping_error); +EXPORT_SYMBOL(swiotlb_alloc_coherent); +EXPORT_SYMBOL(swiotlb_free_coherent); EXPORT_SYMBOL(swiotlb_dma_supported); diff --git a/lib/textsearch.c b/lib/textsearch.c index 9e2a002c5b5..88c98a2ec8d 100644 --- a/lib/textsearch.c +++ b/lib/textsearch.c @@ -40,7 +40,7 @@ * configuration according to the specified parameters. * (3) User starts the search(es) by calling _find() or _next() to * fetch subsequent occurrences. A state variable is provided - * to the algorihtm to store persistent variables. + * to the algorithm to store persistent variables. * (4) Core eventually resets the search offset and forwards the find() * request to the algorithm. * (5) Algorithm calls get_next_block() provided by the user continously diff --git a/lib/vsprintf.c b/lib/vsprintf.c index b025864d2e4..cbab1df150c 100644 --- a/lib/vsprintf.c +++ b/lib/vsprintf.c @@ -851,23 +851,35 @@ EXPORT_SYMBOL(sscanf); /* Simplified asprintf. */ -char *kasprintf(gfp_t gfp, const char *fmt, ...) +char *kvasprintf(gfp_t gfp, const char *fmt, va_list ap) { - va_list ap; unsigned int len; char *p; + va_list aq; - va_start(ap, fmt); - len = vsnprintf(NULL, 0, fmt, ap); - va_end(ap); + va_copy(aq, ap); + len = vsnprintf(NULL, 0, fmt, aq); + va_end(aq); p = kmalloc(len+1, gfp); if (!p) return NULL; - va_start(ap, fmt); + vsnprintf(p, len+1, fmt, ap); - va_end(ap); + return p; } +EXPORT_SYMBOL(kvasprintf); + +char *kasprintf(gfp_t gfp, const char *fmt, ...) +{ + va_list ap; + char *p; + va_start(ap, fmt); + p = kvasprintf(gfp, fmt, ap); + va_end(ap); + + return p; +} EXPORT_SYMBOL(kasprintf); |