Magellan Linux

Annotation of /trunk/kernel26-alx/patches-2.6.20-r6/0121-2.6.20.21-all-fixes.patch

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1175 - (hide annotations) (download)
Thu Oct 14 12:15:46 2010 UTC (13 years, 7 months ago) by niro
File size: 36574 byte(s)
-2.6.20-alx-r6 new magellan 0.5.2 kernel
1 niro 1175 diff --git a/arch/i386/kernel/sysenter.c b/arch/i386/kernel/sysenter.c
2     index 666f70d..0577312 100644
3     --- a/arch/i386/kernel/sysenter.c
4     +++ b/arch/i386/kernel/sysenter.c
5     @@ -183,7 +183,9 @@ struct vm_area_struct *get_gate_vma(struct task_struct *tsk)
6    
7     int in_gate_area(struct task_struct *task, unsigned long addr)
8     {
9     - return 0;
10     + const struct vm_area_struct *vma = get_gate_vma(task);
11     +
12     + return vma && addr >= vma->vm_start && addr < vma->vm_end;
13     }
14    
15     int in_gate_area_no_task(unsigned long addr)
16     diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
17     index f3d4dd5..21d4caf 100644
18     --- a/arch/powerpc/kernel/process.c
19     +++ b/arch/powerpc/kernel/process.c
20     @@ -84,7 +84,7 @@ void flush_fp_to_thread(struct task_struct *tsk)
21     */
22     BUG_ON(tsk != current);
23     #endif
24     - giveup_fpu(current);
25     + giveup_fpu(tsk);
26     }
27     preempt_enable();
28     }
29     @@ -144,7 +144,7 @@ void flush_altivec_to_thread(struct task_struct *tsk)
30     #ifdef CONFIG_SMP
31     BUG_ON(tsk != current);
32     #endif
33     - giveup_altivec(current);
34     + giveup_altivec(tsk);
35     }
36     preempt_enable();
37     }
38     @@ -183,7 +183,7 @@ void flush_spe_to_thread(struct task_struct *tsk)
39     #ifdef CONFIG_SMP
40     BUG_ON(tsk != current);
41     #endif
42     - giveup_spe(current);
43     + giveup_spe(tsk);
44     }
45     preempt_enable();
46     }
47     diff --git a/arch/sparc64/kernel/traps.c b/arch/sparc64/kernel/traps.c
48     index ad67784..ab72e91 100644
49     --- a/arch/sparc64/kernel/traps.c
50     +++ b/arch/sparc64/kernel/traps.c
51     @@ -2146,12 +2146,20 @@ static void user_instruction_dump (unsigned int __user *pc)
52     void show_stack(struct task_struct *tsk, unsigned long *_ksp)
53     {
54     unsigned long pc, fp, thread_base, ksp;
55     - void *tp = task_stack_page(tsk);
56     + struct thread_info *tp;
57     struct reg_window *rw;
58     int count = 0;
59    
60     ksp = (unsigned long) _ksp;
61     -
62     + if (!tsk)
63     + tsk = current;
64     + tp = task_thread_info(tsk);
65     + if (ksp == 0UL) {
66     + if (tsk == current)
67     + asm("mov %%fp, %0" : "=r" (ksp));
68     + else
69     + ksp = tp->ksp;
70     + }
71     if (tp == current_thread_info())
72     flushw_all();
73    
74     @@ -2180,11 +2188,7 @@ void show_stack(struct task_struct *tsk, unsigned long *_ksp)
75    
76     void dump_stack(void)
77     {
78     - unsigned long *ksp;
79     -
80     - __asm__ __volatile__("mov %%fp, %0"
81     - : "=r" (ksp));
82     - show_stack(current, ksp);
83     + show_stack(current, NULL);
84     }
85    
86     EXPORT_SYMBOL(dump_stack);
87     diff --git a/arch/sparc64/mm/fault.c b/arch/sparc64/mm/fault.c
88     index 55ae802..f6377b4 100644
89     --- a/arch/sparc64/mm/fault.c
90     +++ b/arch/sparc64/mm/fault.c
91     @@ -129,15 +129,12 @@ static void __kprobes unhandled_fault(unsigned long address,
92    
93     static void bad_kernel_pc(struct pt_regs *regs, unsigned long vaddr)
94     {
95     - unsigned long *ksp;
96     -
97     printk(KERN_CRIT "OOPS: Bogus kernel PC [%016lx] in fault handler\n",
98     regs->tpc);
99     printk(KERN_CRIT "OOPS: RPC [%016lx]\n", regs->u_regs[15]);
100     print_symbol("RPC: <%s>\n", regs->u_regs[15]);
101     printk(KERN_CRIT "OOPS: Fault was to vaddr[%lx]\n", vaddr);
102     - __asm__("mov %%sp, %0" : "=r" (ksp));
103     - show_stack(current, ksp);
104     + dump_stack();
105     unhandled_fault(regs->tpc, current, regs);
106     }
107    
108     diff --git a/block/ll_rw_blk.c b/block/ll_rw_blk.c
109     index 38c293b..dbb0192 100644
110     --- a/block/ll_rw_blk.c
111     +++ b/block/ll_rw_blk.c
112     @@ -1072,12 +1072,6 @@ void blk_queue_end_tag(request_queue_t *q, struct request *rq)
113     */
114     return;
115    
116     - if (unlikely(!__test_and_clear_bit(tag, bqt->tag_map))) {
117     - printk(KERN_ERR "%s: attempt to clear non-busy tag (%d)\n",
118     - __FUNCTION__, tag);
119     - return;
120     - }
121     -
122     list_del_init(&rq->queuelist);
123     rq->cmd_flags &= ~REQ_QUEUED;
124     rq->tag = -1;
125     @@ -1087,6 +1081,13 @@ void blk_queue_end_tag(request_queue_t *q, struct request *rq)
126     __FUNCTION__, tag);
127    
128     bqt->tag_index[tag] = NULL;
129     +
130     + if (unlikely(!test_and_clear_bit(tag, bqt->tag_map))) {
131     + printk(KERN_ERR "%s: attempt to clear non-busy tag (%d)\n",
132     + __FUNCTION__, tag);
133     + return;
134     + }
135     +
136     bqt->busy--;
137     }
138    
139     diff --git a/crypto/blkcipher.c b/crypto/blkcipher.c
140     index 6e93004..cb95fa8 100644
141     --- a/crypto/blkcipher.c
142     +++ b/crypto/blkcipher.c
143     @@ -58,11 +58,13 @@ static inline void blkcipher_unmap_dst(struct blkcipher_walk *walk)
144     scatterwalk_unmap(walk->dst.virt.addr, 1);
145     }
146    
147     +/* Get a spot of the specified length that does not straddle a page.
148     + * The caller needs to ensure that there is enough space for this operation.
149     + */
150     static inline u8 *blkcipher_get_spot(u8 *start, unsigned int len)
151     {
152     - if (offset_in_page(start + len) < len)
153     - return (u8 *)((unsigned long)(start + len) & PAGE_MASK);
154     - return start;
155     + u8 *end_page = (u8 *)(((unsigned long)(start + len - 1)) & PAGE_MASK);
156     + return start > end_page ? start : end_page;
157     }
158    
159     static inline unsigned int blkcipher_done_slow(struct crypto_blkcipher *tfm,
160     @@ -154,7 +156,8 @@ static inline int blkcipher_next_slow(struct blkcipher_desc *desc,
161     if (walk->buffer)
162     goto ok;
163    
164     - n = bsize * 2 + (alignmask & ~(crypto_tfm_ctx_alignment() - 1));
165     + n = bsize * 3 - (alignmask + 1) +
166     + (alignmask & ~(crypto_tfm_ctx_alignment() - 1));
167     walk->buffer = kmalloc(n, GFP_ATOMIC);
168     if (!walk->buffer)
169     return blkcipher_walk_done(desc, walk, -ENOMEM);
170     diff --git a/drivers/acpi/events/evgpeblk.c b/drivers/acpi/events/evgpeblk.c
171     index 95ddeb4..2ae48c2 100644
172     --- a/drivers/acpi/events/evgpeblk.c
173     +++ b/drivers/acpi/events/evgpeblk.c
174     @@ -586,6 +586,10 @@ acpi_ev_delete_gpe_xrupt(struct acpi_gpe_xrupt_info *gpe_xrupt)
175     flags = acpi_os_acquire_lock(acpi_gbl_gpe_lock);
176     if (gpe_xrupt->previous) {
177     gpe_xrupt->previous->next = gpe_xrupt->next;
178     + } else {
179     + /* No previous, update list head */
180     +
181     + acpi_gbl_gpe_xrupt_list_head = gpe_xrupt->next;
182     }
183    
184     if (gpe_xrupt->next) {
185     diff --git a/drivers/ieee1394/ieee1394_core.c b/drivers/ieee1394/ieee1394_core.c
186     index 9a48ca2..3fc3895 100644
187     --- a/drivers/ieee1394/ieee1394_core.c
188     +++ b/drivers/ieee1394/ieee1394_core.c
189     @@ -1170,7 +1170,7 @@ static void __exit ieee1394_cleanup(void)
190     unregister_chrdev_region(IEEE1394_CORE_DEV, 256);
191     }
192    
193     -fs_initcall(ieee1394_init); /* same as ohci1394 */
194     +module_init(ieee1394_init);
195     module_exit(ieee1394_cleanup);
196    
197     /* Exported symbols */
198     diff --git a/drivers/ieee1394/ohci1394.c b/drivers/ieee1394/ohci1394.c
199     index 628130a..ec301a8 100644
200     --- a/drivers/ieee1394/ohci1394.c
201     +++ b/drivers/ieee1394/ohci1394.c
202     @@ -3785,7 +3785,5 @@ static int __init ohci1394_init(void)
203     return pci_register_driver(&ohci1394_pci_driver);
204     }
205    
206     -/* Register before most other device drivers.
207     - * Useful for remote debugging via physical DMA, e.g. using firescope. */
208     -fs_initcall(ohci1394_init);
209     +module_init(ohci1394_init);
210     module_exit(ohci1394_cleanup);
211     diff --git a/drivers/media/video/cx88/cx88-mpeg.c b/drivers/media/video/cx88/cx88-mpeg.c
212     index 1fe1a83..1093ff4 100644
213     --- a/drivers/media/video/cx88/cx88-mpeg.c
214     +++ b/drivers/media/video/cx88/cx88-mpeg.c
215     @@ -556,7 +556,7 @@ struct cx8802_dev * cx8802_get_device(struct inode *inode)
216    
217     list_for_each(list,&cx8802_devlist) {
218     h = list_entry(list, struct cx8802_dev, devlist);
219     - if (h->mpeg_dev->minor == minor)
220     + if (h->mpeg_dev && h->mpeg_dev->minor == minor)
221     return h;
222     }
223    
224     diff --git a/drivers/media/video/pwc/pwc-if.c b/drivers/media/video/pwc/pwc-if.c
225     index a996aad..957694a 100644
226     --- a/drivers/media/video/pwc/pwc-if.c
227     +++ b/drivers/media/video/pwc/pwc-if.c
228     @@ -1196,12 +1196,19 @@ static int pwc_video_open(struct inode *inode, struct file *file)
229     return 0;
230     }
231    
232     +
233     +static void pwc_cleanup(struct pwc_device *pdev)
234     +{
235     + pwc_remove_sysfs_files(pdev->vdev);
236     + video_unregister_device(pdev->vdev);
237     +}
238     +
239     /* Note that all cleanup is done in the reverse order as in _open */
240     static int pwc_video_close(struct inode *inode, struct file *file)
241     {
242     struct video_device *vdev = file->private_data;
243     struct pwc_device *pdev;
244     - int i;
245     + int i, hint;
246    
247     PWC_DEBUG_OPEN(">> video_close called(vdev = 0x%p).\n", vdev);
248    
249     @@ -1224,8 +1231,9 @@ static int pwc_video_close(struct inode *inode, struct file *file)
250     pwc_isoc_cleanup(pdev);
251     pwc_free_buffers(pdev);
252    
253     + lock_kernel();
254     /* Turn off LEDS and power down camera, but only when not unplugged */
255     - if (pdev->error_status != EPIPE) {
256     + if (!pdev->unplugged) {
257     /* Turn LEDs off */
258     if (pwc_set_leds(pdev, 0, 0) < 0)
259     PWC_DEBUG_MODULE("Failed to set LED on/off time.\n");
260     @@ -1234,9 +1242,19 @@ static int pwc_video_close(struct inode *inode, struct file *file)
261     if (i < 0)
262     PWC_ERROR("Failed to power down camera (%d)\n", i);
263     }
264     + pdev->vopen--;
265     + PWC_DEBUG_OPEN("<< video_close() vopen=%d\n", i);
266     + } else {
267     + pwc_cleanup(pdev);
268     + /* Free memory (don't set pdev to 0 just yet) */
269     + kfree(pdev);
270     + /* search device_hint[] table if we occupy a slot, by any chance */
271     + for (hint = 0; hint < MAX_DEV_HINTS; hint++)
272     + if (device_hint[hint].pdev == pdev)
273     + device_hint[hint].pdev = NULL;
274     }
275     - pdev->vopen--;
276     - PWC_DEBUG_OPEN("<< video_close() vopen=%d\n", pdev->vopen);
277     + unlock_kernel();
278     +
279     return 0;
280     }
281    
282     @@ -1783,21 +1801,21 @@ static void usb_pwc_disconnect(struct usb_interface *intf)
283     /* Alert waiting processes */
284     wake_up_interruptible(&pdev->frameq);
285     /* Wait until device is closed */
286     - while (pdev->vopen)
287     - schedule();
288     - /* Device is now closed, so we can safely unregister it */
289     - PWC_DEBUG_PROBE("Unregistering video device in disconnect().\n");
290     - pwc_remove_sysfs_files(pdev->vdev);
291     - video_unregister_device(pdev->vdev);
292     -
293     - /* Free memory (don't set pdev to 0 just yet) */
294     - kfree(pdev);
295     + if(pdev->vopen) {
296     + pdev->unplugged = 1;
297     + } else {
298     + /* Device is closed, so we can safely unregister it */
299     + PWC_DEBUG_PROBE("Unregistering video device in disconnect().\n");
300     + pwc_cleanup(pdev);
301     + /* Free memory (don't set pdev to 0 just yet) */
302     + kfree(pdev);
303    
304     disconnect_out:
305     - /* search device_hint[] table if we occupy a slot, by any chance */
306     - for (hint = 0; hint < MAX_DEV_HINTS; hint++)
307     - if (device_hint[hint].pdev == pdev)
308     - device_hint[hint].pdev = NULL;
309     + /* search device_hint[] table if we occupy a slot, by any chance */
310     + for (hint = 0; hint < MAX_DEV_HINTS; hint++)
311     + if (device_hint[hint].pdev == pdev)
312     + device_hint[hint].pdev = NULL;
313     + }
314    
315     unlock_kernel();
316     }
317     diff --git a/drivers/media/video/pwc/pwc.h b/drivers/media/video/pwc/pwc.h
318     index 7e9c423..7dae6c4 100644
319     --- a/drivers/media/video/pwc/pwc.h
320     +++ b/drivers/media/video/pwc/pwc.h
321     @@ -198,6 +198,7 @@ struct pwc_device
322     char vsnapshot; /* snapshot mode */
323     char vsync; /* used by isoc handler */
324     char vmirror; /* for ToUCaM series */
325     + char unplugged;
326    
327     int cmd_len;
328     unsigned char cmd_buf[13];
329     diff --git a/drivers/net/forcedeth.c b/drivers/net/forcedeth.c
330     index c383dc3..f18edd8 100644
331     --- a/drivers/net/forcedeth.c
332     +++ b/drivers/net/forcedeth.c
333     @@ -554,6 +554,7 @@ union ring_type {
334     #define PHY_OUI_MARVELL 0x5043
335     #define PHY_OUI_CICADA 0x03f1
336     #define PHY_OUI_VITESSE 0x01c1
337     +#define PHY_OUI_REALTEK 0x0732
338     #define PHYID1_OUI_MASK 0x03ff
339     #define PHYID1_OUI_SHFT 6
340     #define PHYID2_OUI_MASK 0xfc00
341     diff --git a/drivers/net/r8169.c b/drivers/net/r8169.c
342     index 1aafa71..2847a0c 100644
343     --- a/drivers/net/r8169.c
344     +++ b/drivers/net/r8169.c
345     @@ -2646,14 +2646,16 @@ rtl8169_interrupt(int irq, void *dev_instance)
346     rtl8169_check_link_status(dev, tp, ioaddr);
347    
348     #ifdef CONFIG_R8169_NAPI
349     - RTL_W16(IntrMask, rtl8169_intr_mask & ~rtl8169_napi_event);
350     - tp->intr_mask = ~rtl8169_napi_event;
351     -
352     - if (likely(netif_rx_schedule_prep(dev)))
353     - __netif_rx_schedule(dev);
354     - else if (netif_msg_intr(tp)) {
355     - printk(KERN_INFO "%s: interrupt %04x taken in poll\n",
356     - dev->name, status);
357     + if (status & rtl8169_napi_event) {
358     + RTL_W16(IntrMask, rtl8169_intr_mask & ~rtl8169_napi_event);
359     + tp->intr_mask = ~rtl8169_napi_event;
360     +
361     + if (likely(netif_rx_schedule_prep(dev)))
362     + __netif_rx_schedule(dev);
363     + else if (netif_msg_intr(tp)) {
364     + printk(KERN_INFO "%s: interrupt %04x in poll\n",
365     + dev->name, status);
366     + }
367     }
368     break;
369     #else
370     diff --git a/drivers/scsi/3w-9xxx.c b/drivers/scsi/3w-9xxx.c
371     index b091a0f..9040564 100644
372     --- a/drivers/scsi/3w-9xxx.c
373     +++ b/drivers/scsi/3w-9xxx.c
374     @@ -4,7 +4,7 @@
375     Written By: Adam Radford <linuxraid@amcc.com>
376     Modifications By: Tom Couch <linuxraid@amcc.com>
377    
378     - Copyright (C) 2004-2006 Applied Micro Circuits Corporation.
379     + Copyright (C) 2004-2007 Applied Micro Circuits Corporation.
380    
381     This program is free software; you can redistribute it and/or modify
382     it under the terms of the GNU General Public License as published by
383     @@ -69,6 +69,7 @@
384     2.26.02.008 - Free irq handler in __twa_shutdown().
385     Serialize reset code.
386     Add support for 9650SE controllers.
387     + 2.26.02.009 - Fix dma mask setting to fallback to 32-bit if 64-bit fails.
388     */
389    
390     #include <linux/module.h>
391     @@ -92,7 +93,7 @@
392     #include "3w-9xxx.h"
393    
394     /* Globals */
395     -#define TW_DRIVER_VERSION "2.26.02.008"
396     +#define TW_DRIVER_VERSION "2.26.02.009"
397     static TW_Device_Extension *twa_device_extension_list[TW_MAX_SLOT];
398     static unsigned int twa_device_extension_count;
399     static int twa_major = -1;
400     @@ -2063,11 +2064,14 @@ static int __devinit twa_probe(struct pci_dev *pdev, const struct pci_device_id
401    
402     pci_set_master(pdev);
403    
404     - retval = pci_set_dma_mask(pdev, sizeof(dma_addr_t) > 4 ? DMA_64BIT_MASK : DMA_32BIT_MASK);
405     - if (retval) {
406     - TW_PRINTK(host, TW_DRIVER, 0x23, "Failed to set dma mask");
407     - goto out_disable_device;
408     - }
409     + if (pci_set_dma_mask(pdev, DMA_64BIT_MASK)
410     + || pci_set_consistent_dma_mask(pdev, DMA_64BIT_MASK))
411     + if (pci_set_dma_mask(pdev, DMA_32BIT_MASK)
412     + || pci_set_consistent_dma_mask(pdev, DMA_32BIT_MASK)) {
413     + TW_PRINTK(host, TW_DRIVER, 0x23, "Failed to set dma mask");
414     + retval = -ENODEV;
415     + goto out_disable_device;
416     + }
417    
418     host = scsi_host_alloc(&driver_template, sizeof(TW_Device_Extension));
419     if (!host) {
420     diff --git a/drivers/usb/core/driver.c b/drivers/usb/core/driver.c
421     index d6eb5ce..c5dc61a 100644
422     --- a/drivers/usb/core/driver.c
423     +++ b/drivers/usb/core/driver.c
424     @@ -66,7 +66,7 @@ static ssize_t store_new_id(struct device_driver *driver,
425     dynid->id.match_flags = USB_DEVICE_ID_MATCH_DEVICE;
426    
427     spin_lock(&usb_drv->dynids.lock);
428     - list_add_tail(&usb_drv->dynids.list, &dynid->node);
429     + list_add_tail(&dynid->node, &usb_drv->dynids.list);
430     spin_unlock(&usb_drv->dynids.lock);
431    
432     if (get_driver(driver)) {
433     diff --git a/drivers/usb/core/message.c b/drivers/usb/core/message.c
434     index 149aa8b..dec1337 100644
435     --- a/drivers/usb/core/message.c
436     +++ b/drivers/usb/core/message.c
437     @@ -608,12 +608,12 @@ int usb_get_descriptor(struct usb_device *dev, unsigned char type, unsigned char
438     memset(buf,0,size); // Make sure we parse really received data
439    
440     for (i = 0; i < 3; ++i) {
441     - /* retry on length 0 or stall; some devices are flakey */
442     + /* retry on length 0 or error; some devices are flakey */
443     result = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0),
444     USB_REQ_GET_DESCRIPTOR, USB_DIR_IN,
445     (type << 8) + index, 0, buf, size,
446     USB_CTRL_GET_TIMEOUT);
447     - if (result == 0 || result == -EPIPE)
448     + if (result <= 0 && result != -ETIMEDOUT)
449     continue;
450     if (result > 1 && ((u8 *)buf)[1] != type) {
451     result = -EPROTO;
452     diff --git a/fs/ext3/namei.c b/fs/ext3/namei.c
453     index 4df39c4..99f0f72 100644
454     --- a/fs/ext3/namei.c
455     +++ b/fs/ext3/namei.c
456     @@ -380,13 +380,28 @@ dx_probe(struct dentry *dentry, struct inode *dir,
457    
458     entries = (struct dx_entry *) (((char *)&root->info) +
459     root->info.info_length);
460     - assert(dx_get_limit(entries) == dx_root_limit(dir,
461     - root->info.info_length));
462     +
463     + if (dx_get_limit(entries) != dx_root_limit(dir,
464     + root->info.info_length)) {
465     + ext3_warning(dir->i_sb, __FUNCTION__,
466     + "dx entry: limit != root limit");
467     + brelse(bh);
468     + *err = ERR_BAD_DX_DIR;
469     + goto fail;
470     + }
471     +
472     dxtrace (printk("Look up %x", hash));
473     while (1)
474     {
475     count = dx_get_count(entries);
476     - assert (count && count <= dx_get_limit(entries));
477     + if (!count || count > dx_get_limit(entries)) {
478     + ext3_warning(dir->i_sb, __FUNCTION__,
479     + "dx entry: no count or count > limit");
480     + brelse(bh);
481     + *err = ERR_BAD_DX_DIR;
482     + goto fail2;
483     + }
484     +
485     p = entries + 1;
486     q = entries + count - 1;
487     while (p <= q)
488     @@ -424,8 +439,15 @@ dx_probe(struct dentry *dentry, struct inode *dir,
489     if (!(bh = ext3_bread (NULL,dir, dx_get_block(at), 0, err)))
490     goto fail2;
491     at = entries = ((struct dx_node *) bh->b_data)->entries;
492     - assert (dx_get_limit(entries) == dx_node_limit (dir));
493     + if (dx_get_limit(entries) != dx_node_limit (dir)) {
494     + ext3_warning(dir->i_sb, __FUNCTION__,
495     + "dx entry: limit != node limit");
496     + brelse(bh);
497     + *err = ERR_BAD_DX_DIR;
498     + goto fail2;
499     + }
500     frame++;
501     + frame->bh = NULL;
502     }
503     fail2:
504     while (frame >= frame_in) {
505     @@ -433,6 +455,10 @@ fail2:
506     frame--;
507     }
508     fail:
509     + if (*err == ERR_BAD_DX_DIR)
510     + ext3_warning(dir->i_sb, __FUNCTION__,
511     + "Corrupt dir inode %ld, running e2fsck is "
512     + "recommended.", dir->i_ino);
513     return NULL;
514     }
515    
516     diff --git a/fs/ext4/namei.c b/fs/ext4/namei.c
517     index e5a74a5..5edc327 100644
518     --- a/fs/ext4/namei.c
519     +++ b/fs/ext4/namei.c
520     @@ -380,13 +380,28 @@ dx_probe(struct dentry *dentry, struct inode *dir,
521    
522     entries = (struct dx_entry *) (((char *)&root->info) +
523     root->info.info_length);
524     - assert(dx_get_limit(entries) == dx_root_limit(dir,
525     - root->info.info_length));
526     +
527     + if (dx_get_limit(entries) != dx_root_limit(dir,
528     + root->info.info_length)) {
529     + ext4_warning(dir->i_sb, __FUNCTION__,
530     + "dx entry: limit != root limit");
531     + brelse(bh);
532     + *err = ERR_BAD_DX_DIR;
533     + goto fail;
534     + }
535     +
536     dxtrace (printk("Look up %x", hash));
537     while (1)
538     {
539     count = dx_get_count(entries);
540     - assert (count && count <= dx_get_limit(entries));
541     + if (!count || count > dx_get_limit(entries)) {
542     + ext4_warning(dir->i_sb, __FUNCTION__,
543     + "dx entry: no count or count > limit");
544     + brelse(bh);
545     + *err = ERR_BAD_DX_DIR;
546     + goto fail2;
547     + }
548     +
549     p = entries + 1;
550     q = entries + count - 1;
551     while (p <= q)
552     @@ -424,8 +439,15 @@ dx_probe(struct dentry *dentry, struct inode *dir,
553     if (!(bh = ext4_bread (NULL,dir, dx_get_block(at), 0, err)))
554     goto fail2;
555     at = entries = ((struct dx_node *) bh->b_data)->entries;
556     - assert (dx_get_limit(entries) == dx_node_limit (dir));
557     + if (dx_get_limit(entries) != dx_node_limit (dir)) {
558     + ext4_warning(dir->i_sb, __FUNCTION__,
559     + "dx entry: limit != node limit");
560     + brelse(bh);
561     + *err = ERR_BAD_DX_DIR;
562     + goto fail2;
563     + }
564     frame++;
565     + frame->bh = NULL;
566     }
567     fail2:
568     while (frame >= frame_in) {
569     @@ -433,6 +455,10 @@ fail2:
570     frame--;
571     }
572     fail:
573     + if (*err == ERR_BAD_DX_DIR)
574     + ext4_warning(dir->i_sb, __FUNCTION__,
575     + "Corrupt dir inode %ld, running e2fsck is "
576     + "recommended.", dir->i_ino);
577     return NULL;
578     }
579    
580     diff --git a/fs/locks.c b/fs/locks.c
581     index 52a8100..bcdfebc 100644
582     --- a/fs/locks.c
583     +++ b/fs/locks.c
584     @@ -790,7 +790,7 @@ find_conflict:
585     if (request->fl_flags & FL_ACCESS)
586     goto out;
587     locks_copy_lock(new_fl, request);
588     - locks_insert_lock(&inode->i_flock, new_fl);
589     + locks_insert_lock(before, new_fl);
590     new_fl = NULL;
591     error = 0;
592    
593     diff --git a/fs/nfs/super.c b/fs/nfs/super.c
594     index 28108c8..c81fcd8 100644
595     --- a/fs/nfs/super.c
596     +++ b/fs/nfs/super.c
597     @@ -180,8 +180,8 @@ void __exit unregister_nfs_fs(void)
598     remove_shrinker(acl_shrinker);
599     #ifdef CONFIG_NFS_V4
600     unregister_filesystem(&nfs4_fs_type);
601     - nfs_unregister_sysctl();
602     #endif
603     + nfs_unregister_sysctl();
604     unregister_filesystem(&nfs_fs_type);
605     }
606    
607     diff --git a/fs/sysfs/dir.c b/fs/sysfs/dir.c
608     index 511edef..3743086 100644
609     --- a/fs/sysfs/dir.c
610     +++ b/fs/sysfs/dir.c
611     @@ -29,6 +29,14 @@ static struct dentry_operations sysfs_dentry_ops = {
612     .d_iput = sysfs_d_iput,
613     };
614    
615     +static unsigned int sysfs_inode_counter;
616     +ino_t sysfs_get_inum(void)
617     +{
618     + if (unlikely(sysfs_inode_counter < 3))
619     + sysfs_inode_counter = 3;
620     + return sysfs_inode_counter++;
621     +}
622     +
623     /*
624     * Allocates a new sysfs_dirent and links it to the parent sysfs_dirent
625     */
626     @@ -42,6 +50,7 @@ static struct sysfs_dirent * sysfs_new_dirent(struct sysfs_dirent * parent_sd,
627     return NULL;
628    
629     memset(sd, 0, sizeof(*sd));
630     + sd->s_ino = sysfs_get_inum();
631     atomic_set(&sd->s_count, 1);
632     atomic_set(&sd->s_event, 1);
633     INIT_LIST_HEAD(&sd->s_children);
634     @@ -461,7 +470,7 @@ static int sysfs_readdir(struct file * filp, void * dirent, filldir_t filldir)
635    
636     switch (i) {
637     case 0:
638     - ino = dentry->d_inode->i_ino;
639     + ino = parent_sd->s_ino;
640     if (filldir(dirent, ".", 1, i, ino, DT_DIR) < 0)
641     break;
642     filp->f_pos++;
643     @@ -490,10 +499,7 @@ static int sysfs_readdir(struct file * filp, void * dirent, filldir_t filldir)
644    
645     name = sysfs_get_name(next);
646     len = strlen(name);
647     - if (next->s_dentry)
648     - ino = next->s_dentry->d_inode->i_ino;
649     - else
650     - ino = iunique(sysfs_sb, 2);
651     + ino = next->s_ino;
652    
653     if (filldir(dirent, name, len, filp->f_pos, ino,
654     dt_type(next)) < 0)
655     diff --git a/fs/sysfs/inode.c b/fs/sysfs/inode.c
656     index e79e38d..bb2da9d 100644
657     --- a/fs/sysfs/inode.c
658     +++ b/fs/sysfs/inode.c
659     @@ -129,6 +129,7 @@ struct inode * sysfs_new_inode(mode_t mode, struct sysfs_dirent * sd)
660     inode->i_mapping->a_ops = &sysfs_aops;
661     inode->i_mapping->backing_dev_info = &sysfs_backing_dev_info;
662     inode->i_op = &sysfs_inode_operations;
663     + inode->i_ino = sd->s_ino;
664     lockdep_set_class(&inode->i_mutex, &sysfs_inode_imutex_key);
665    
666     if (sd->s_iattr) {
667     diff --git a/fs/sysfs/mount.c b/fs/sysfs/mount.c
668     index e503f85..4305e46 100644
669     --- a/fs/sysfs/mount.c
670     +++ b/fs/sysfs/mount.c
671     @@ -29,6 +29,7 @@ static struct sysfs_dirent sysfs_root = {
672     .s_element = NULL,
673     .s_type = SYSFS_ROOT,
674     .s_iattr = NULL,
675     + .s_ino = 1,
676     };
677    
678     static int sysfs_fill_super(struct super_block *sb, void *data, int silent)
679     diff --git a/include/asm-avr32/atomic.h b/include/asm-avr32/atomic.h
680     index c40b603..7df7b75 100644
681     --- a/include/asm-avr32/atomic.h
682     +++ b/include/asm-avr32/atomic.h
683     @@ -101,7 +101,7 @@ static inline int atomic_sub_unless(atomic_t *v, int a, int u)
684     " mov %1, 1\n"
685     "1:"
686     : "=&r"(tmp), "=&r"(result), "=o"(v->counter)
687     - : "m"(v->counter), "rKs21"(a), "rKs21"(u)
688     + : "m"(v->counter), "rKs21"(a), "rKs21"(u), "1"(result)
689     : "cc", "memory");
690    
691     return result;
692     @@ -137,7 +137,7 @@ static inline int atomic_add_unless(atomic_t *v, int a, int u)
693     " mov %1, 1\n"
694     "1:"
695     : "=&r"(tmp), "=&r"(result), "=o"(v->counter)
696     - : "m"(v->counter), "r"(a), "ir"(u)
697     + : "m"(v->counter), "r"(a), "ir"(u), "1"(result)
698     : "cc", "memory");
699     }
700    
701     diff --git a/include/linux/netfilter/Kbuild b/include/linux/netfilter/Kbuild
702     index 6328175..ab399fc 100644
703     --- a/include/linux/netfilter/Kbuild
704     +++ b/include/linux/netfilter/Kbuild
705     @@ -28,6 +28,7 @@ header-y += xt_policy.h
706     header-y += xt_realm.h
707     header-y += xt_sctp.h
708     header-y += xt_state.h
709     +header-y += xt_statistic.h
710     header-y += xt_string.h
711     header-y += xt_tcpmss.h
712     header-y += xt_tcpudp.h
713     diff --git a/include/linux/sysfs.h b/include/linux/sysfs.h
714     index 2129d1b..8799dc3 100644
715     --- a/include/linux/sysfs.h
716     +++ b/include/linux/sysfs.h
717     @@ -73,6 +73,7 @@ struct sysfs_dirent {
718     void * s_element;
719     int s_type;
720     umode_t s_mode;
721     + ino_t s_ino;
722     struct dentry * s_dentry;
723     struct iattr * s_iattr;
724     atomic_t s_event;
725     diff --git a/include/net/tcp.h b/include/net/tcp.h
726     index cd8fa0c..da5bac3 100644
727     --- a/include/net/tcp.h
728     +++ b/include/net/tcp.h
729     @@ -273,7 +273,7 @@ extern int tcp_v4_remember_stamp(struct sock *sk);
730    
731     extern int tcp_v4_tw_remember_stamp(struct inet_timewait_sock *tw);
732    
733     -extern int tcp_sendmsg(struct kiocb *iocb, struct sock *sk,
734     +extern int tcp_sendmsg(struct kiocb *iocb, struct socket *sock,
735     struct msghdr *msg, size_t size);
736     extern ssize_t tcp_sendpage(struct socket *sock, struct page *page, int offset, size_t size, int flags);
737    
738     diff --git a/kernel/futex_compat.c b/kernel/futex_compat.c
739     index 50f24ee..5f0115f 100644
740     --- a/kernel/futex_compat.c
741     +++ b/kernel/futex_compat.c
742     @@ -61,10 +61,10 @@ void compat_exit_robust_list(struct task_struct *curr)
743     if (fetch_robust_entry(&upending, &pending,
744     &head->list_op_pending, &pip))
745     return;
746     - if (upending)
747     + if (pending)
748     handle_futex_death((void __user *)pending + futex_offset, curr, pip);
749    
750     - while (compat_ptr(uentry) != &head->list) {
751     + while (entry != (struct robust_list __user *) &head->list) {
752     /*
753     * A pending lock might already be on the list, so
754     * dont process it twice:
755     diff --git a/kernel/signal.c b/kernel/signal.c
756     index 5630255..4975f4c 100644
757     --- a/kernel/signal.c
758     +++ b/kernel/signal.c
759     @@ -1345,20 +1345,19 @@ struct sigqueue *sigqueue_alloc(void)
760     void sigqueue_free(struct sigqueue *q)
761     {
762     unsigned long flags;
763     + spinlock_t *lock = &current->sighand->siglock;
764     +
765     BUG_ON(!(q->flags & SIGQUEUE_PREALLOC));
766     /*
767     * If the signal is still pending remove it from the
768     - * pending queue.
769     + * pending queue. We must hold ->siglock while testing
770     + * q->list to serialize with collect_signal().
771     */
772     - if (unlikely(!list_empty(&q->list))) {
773     - spinlock_t *lock = &current->sighand->siglock;
774     - read_lock(&tasklist_lock);
775     - spin_lock_irqsave(lock, flags);
776     - if (!list_empty(&q->list))
777     - list_del_init(&q->list);
778     - spin_unlock_irqrestore(lock, flags);
779     - read_unlock(&tasklist_lock);
780     - }
781     + spin_lock_irqsave(lock, flags);
782     + if (!list_empty(&q->list))
783     + list_del_init(&q->list);
784     + spin_unlock_irqrestore(lock, flags);
785     +
786     q->flags &= ~SIGQUEUE_PREALLOC;
787     __sigqueue_free(q);
788     }
789     diff --git a/kernel/sys.c b/kernel/sys.c
790     index 475ddbb..17f8447 100644
791     --- a/kernel/sys.c
792     +++ b/kernel/sys.c
793     @@ -1358,7 +1358,6 @@ asmlinkage long sys_times(struct tms __user * tbuf)
794     * Auch. Had to add the 'did_exec' flag to conform completely to POSIX.
795     * LBT 04.03.94
796     */
797     -
798     asmlinkage long sys_setpgid(pid_t pid, pid_t pgid)
799     {
800     struct task_struct *p;
801     @@ -1386,7 +1385,7 @@ asmlinkage long sys_setpgid(pid_t pid, pid_t pgid)
802     if (!thread_group_leader(p))
803     goto out;
804    
805     - if (p->real_parent == group_leader) {
806     + if (p->real_parent->tgid == group_leader->tgid) {
807     err = -EPERM;
808     if (process_session(p) != process_session(group_leader))
809     goto out;
810     diff --git a/net/802/psnap.c b/net/802/psnap.c
811     index 270b9d2..44dc3f9 100644
812     --- a/net/802/psnap.c
813     +++ b/net/802/psnap.c
814     @@ -55,6 +55,9 @@ static int snap_rcv(struct sk_buff *skb, struct net_device *dev,
815     .type = __constant_htons(ETH_P_SNAP),
816     };
817    
818     + if (unlikely(!pskb_may_pull(skb, 5)))
819     + goto drop;
820     +
821     rcu_read_lock();
822     proto = find_snap_client(skb->h.raw);
823     if (proto) {
824     @@ -62,14 +65,18 @@ static int snap_rcv(struct sk_buff *skb, struct net_device *dev,
825     skb->h.raw += 5;
826     skb_pull_rcsum(skb, 5);
827     rc = proto->rcvfunc(skb, dev, &snap_packet_type, orig_dev);
828     - } else {
829     - skb->sk = NULL;
830     - kfree_skb(skb);
831     - rc = 1;
832     }
833     -
834     rcu_read_unlock();
835     +
836     + if (unlikely(!proto))
837     + goto drop;
838     +
839     +out:
840     return rc;
841     +
842     +drop:
843     + kfree_skb(skb);
844     + goto out;
845     }
846    
847     /*
848     diff --git a/net/core/datagram.c b/net/core/datagram.c
849     index 797fdd4..5d55a2e 100644
850     --- a/net/core/datagram.c
851     +++ b/net/core/datagram.c
852     @@ -444,6 +444,9 @@ int skb_copy_and_csum_datagram_iovec(struct sk_buff *skb,
853     __wsum csum;
854     int chunk = skb->len - hlen;
855    
856     + if (!chunk)
857     + return 0;
858     +
859     /* Skip filled elements.
860     * Pretty silly, look at memcpy_toiovec, though 8)
861     */
862     diff --git a/net/dccp/ccids/ccid2.c b/net/dccp/ccids/ccid2.c
863     index fd38b05..05324db 100644
864     --- a/net/dccp/ccids/ccid2.c
865     +++ b/net/dccp/ccids/ccid2.c
866     @@ -298,7 +298,7 @@ static void ccid2_hc_tx_packet_sent(struct sock *sk, int more, unsigned int len)
867     int rc;
868    
869     ccid2_pr_debug("allocating more space in history\n");
870     - rc = ccid2_hc_tx_alloc_seq(hctx, CCID2_SEQBUF_LEN, GFP_KERNEL);
871     + rc = ccid2_hc_tx_alloc_seq(hctx, CCID2_SEQBUF_LEN, gfp_any());
872     BUG_ON(rc); /* XXX what do we do? */
873    
874     next = hctx->ccid2hctx_seqh->ccid2s_next;
875     diff --git a/net/ipv4/af_inet.c b/net/ipv4/af_inet.c
876     index 8640096..d8e6f77 100644
877     --- a/net/ipv4/af_inet.c
878     +++ b/net/ipv4/af_inet.c
879     @@ -803,7 +803,7 @@ const struct proto_ops inet_stream_ops = {
880     .shutdown = inet_shutdown,
881     .setsockopt = sock_common_setsockopt,
882     .getsockopt = sock_common_getsockopt,
883     - .sendmsg = inet_sendmsg,
884     + .sendmsg = tcp_sendmsg,
885     .recvmsg = sock_common_recvmsg,
886     .mmap = sock_no_mmap,
887     .sendpage = tcp_sendpage,
888     diff --git a/net/ipv4/ah4.c b/net/ipv4/ah4.c
889     index 67a5509..41ad421 100644
890     --- a/net/ipv4/ah4.c
891     +++ b/net/ipv4/ah4.c
892     @@ -46,7 +46,7 @@ static int ip_clear_mutable_options(struct iphdr *iph, __be32 *daddr)
893     memcpy(daddr, optptr+optlen-4, 4);
894     /* Fall through */
895     default:
896     - memset(optptr+2, 0, optlen-2);
897     + memset(optptr, 0, optlen);
898     }
899     l -= optlen;
900     optptr += optlen;
901     diff --git a/net/ipv4/tcp.c b/net/ipv4/tcp.c
902     index 6842474..a3818f2 100644
903     --- a/net/ipv4/tcp.c
904     +++ b/net/ipv4/tcp.c
905     @@ -658,9 +658,10 @@ static inline int select_size(struct sock *sk, struct tcp_sock *tp)
906     return tmp;
907     }
908    
909     -int tcp_sendmsg(struct kiocb *iocb, struct sock *sk, struct msghdr *msg,
910     +int tcp_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr *msg,
911     size_t size)
912     {
913     + struct sock *sk = sock->sk;
914     struct iovec *iov;
915     struct tcp_sock *tp = tcp_sk(sk);
916     struct sk_buff *skb;
917     diff --git a/net/ipv4/tcp_ipv4.c b/net/ipv4/tcp_ipv4.c
918     index 12de90a..9c4862f 100644
919     --- a/net/ipv4/tcp_ipv4.c
920     +++ b/net/ipv4/tcp_ipv4.c
921     @@ -2427,7 +2427,6 @@ struct proto tcp_prot = {
922     .shutdown = tcp_shutdown,
923     .setsockopt = tcp_setsockopt,
924     .getsockopt = tcp_getsockopt,
925     - .sendmsg = tcp_sendmsg,
926     .recvmsg = tcp_recvmsg,
927     .backlog_rcv = tcp_v4_do_rcv,
928     .hash = tcp_v4_hash,
929     diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c
930     index 0e0e426..30c8299 100644
931     --- a/net/ipv6/af_inet6.c
932     +++ b/net/ipv6/af_inet6.c
933     @@ -473,7 +473,7 @@ const struct proto_ops inet6_stream_ops = {
934     .shutdown = inet_shutdown, /* ok */
935     .setsockopt = sock_common_setsockopt, /* ok */
936     .getsockopt = sock_common_getsockopt, /* ok */
937     - .sendmsg = inet_sendmsg, /* ok */
938     + .sendmsg = tcp_sendmsg, /* ok */
939     .recvmsg = sock_common_recvmsg, /* ok */
940     .mmap = sock_no_mmap,
941     .sendpage = tcp_sendpage,
942     diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c
943     index 7b7bd44..2c613fa 100644
944     --- a/net/ipv6/ip6_output.c
945     +++ b/net/ipv6/ip6_output.c
946     @@ -1357,8 +1357,9 @@ void ip6_flush_pending_frames(struct sock *sk)
947     struct sk_buff *skb;
948    
949     while ((skb = __skb_dequeue_tail(&sk->sk_write_queue)) != NULL) {
950     - IP6_INC_STATS(ip6_dst_idev(skb->dst),
951     - IPSTATS_MIB_OUTDISCARDS);
952     + if (skb->dst)
953     + IP6_INC_STATS(ip6_dst_idev(skb->dst),
954     + IPSTATS_MIB_OUTDISCARDS);
955     kfree_skb(skb);
956     }
957    
958     diff --git a/net/ipv6/raw.c b/net/ipv6/raw.c
959     index 9479fbd..ddbe790 100644
960     --- a/net/ipv6/raw.c
961     +++ b/net/ipv6/raw.c
962     @@ -851,11 +851,10 @@ back_from_confirm:
963     ip6_flush_pending_frames(sk);
964     else if (!(msg->msg_flags & MSG_MORE))
965     err = rawv6_push_pending_frames(sk, &fl, rp);
966     + release_sock(sk);
967     }
968     done:
969     dst_release(dst);
970     - if (!inet->hdrincl)
971     - release_sock(sk);
972     out:
973     fl6_sock_release(flowlabel);
974     return err<0?err:len;
975     diff --git a/net/ipv6/tcp_ipv6.c b/net/ipv6/tcp_ipv6.c
976     index 03f53f5..f6214b7 100644
977     --- a/net/ipv6/tcp_ipv6.c
978     +++ b/net/ipv6/tcp_ipv6.c
979     @@ -2127,7 +2127,6 @@ struct proto tcpv6_prot = {
980     .shutdown = tcp_shutdown,
981     .setsockopt = tcp_setsockopt,
982     .getsockopt = tcp_getsockopt,
983     - .sendmsg = tcp_sendmsg,
984     .recvmsg = tcp_recvmsg,
985     .backlog_rcv = tcp_v6_do_rcv,
986     .hash = tcp_v6_hash,
987     diff --git a/net/socket.c b/net/socket.c
988     index afb6085..d9bae01 100644
989     --- a/net/socket.c
990     +++ b/net/socket.c
991     @@ -1147,7 +1147,7 @@ static int __sock_create(int family, int type, int protocol,
992     module_put(pf->owner);
993     err = security_socket_post_create(sock, family, type, protocol, kern);
994     if (err)
995     - goto out_release;
996     + goto out_sock_release;
997     *res = sock;
998    
999     return 0;
1000     diff --git a/sound/core/memalloc.c b/sound/core/memalloc.c
1001     index bc0bd09..02c2ce6 100644
1002     --- a/sound/core/memalloc.c
1003     +++ b/sound/core/memalloc.c
1004     @@ -27,6 +27,7 @@
1005     #include <linux/pci.h>
1006     #include <linux/slab.h>
1007     #include <linux/mm.h>
1008     +#include <linux/seq_file.h>
1009     #include <asm/uaccess.h>
1010     #include <linux/dma-mapping.h>
1011     #include <linux/moduleparam.h>
1012     @@ -483,10 +484,8 @@ static void free_all_reserved_pages(void)
1013     #define SND_MEM_PROC_FILE "driver/snd-page-alloc"
1014     static struct proc_dir_entry *snd_mem_proc;
1015    
1016     -static int snd_mem_proc_read(char *page, char **start, off_t off,
1017     - int count, int *eof, void *data)
1018     +static int snd_mem_proc_read(struct seq_file *seq, void *offset)
1019     {
1020     - int len = 0;
1021     long pages = snd_allocated_pages >> (PAGE_SHIFT-12);
1022     struct list_head *p;
1023     struct snd_mem_list *mem;
1024     @@ -494,44 +493,47 @@ static int snd_mem_proc_read(char *page, char **start, off_t off,
1025     static char *types[] = { "UNKNOWN", "CONT", "DEV", "DEV-SG", "SBUS" };
1026    
1027     mutex_lock(&list_mutex);
1028     - len += snprintf(page + len, count - len,
1029     - "pages : %li bytes (%li pages per %likB)\n",
1030     - pages * PAGE_SIZE, pages, PAGE_SIZE / 1024);
1031     + seq_printf(seq, "pages : %li bytes (%li pages per %likB)\n",
1032     + pages * PAGE_SIZE, pages, PAGE_SIZE / 1024);
1033     devno = 0;
1034     list_for_each(p, &mem_list_head) {
1035     mem = list_entry(p, struct snd_mem_list, list);
1036     devno++;
1037     - len += snprintf(page + len, count - len,
1038     - "buffer %d : ID %08x : type %s\n",
1039     - devno, mem->id, types[mem->buffer.dev.type]);
1040     - len += snprintf(page + len, count - len,
1041     - " addr = 0x%lx, size = %d bytes\n",
1042     - (unsigned long)mem->buffer.addr, (int)mem->buffer.bytes);
1043     + seq_printf(seq, "buffer %d : ID %08x : type %s\n",
1044     + devno, mem->id, types[mem->buffer.dev.type]);
1045     + seq_printf(seq, " addr = 0x%lx, size = %d bytes\n",
1046     + (unsigned long)mem->buffer.addr,
1047     + (int)mem->buffer.bytes);
1048     }
1049     mutex_unlock(&list_mutex);
1050     - return len;
1051     + return 0;
1052     +}
1053     +
1054     +static int snd_mem_proc_open(struct inode *inode, struct file *file)
1055     +{
1056     + return single_open(file, snd_mem_proc_read, NULL);
1057     }
1058    
1059     /* FIXME: for pci only - other bus? */
1060     #ifdef CONFIG_PCI
1061     #define gettoken(bufp) strsep(bufp, " \t\n")
1062    
1063     -static int snd_mem_proc_write(struct file *file, const char __user *buffer,
1064     - unsigned long count, void *data)
1065     +static ssize_t snd_mem_proc_write(struct file *file, const char __user * buffer,
1066     + size_t count, loff_t * ppos)
1067     {
1068     char buf[128];
1069     char *token, *p;
1070    
1071     - if (count > ARRAY_SIZE(buf) - 1)
1072     - count = ARRAY_SIZE(buf) - 1;
1073     + if (count > sizeof(buf) - 1)
1074     + return -EINVAL;
1075     if (copy_from_user(buf, buffer, count))
1076     return -EFAULT;
1077     - buf[ARRAY_SIZE(buf) - 1] = '\0';
1078     + buf[count] = '\0';
1079    
1080     p = buf;
1081     token = gettoken(&p);
1082     if (! token || *token == '#')
1083     - return (int)count;
1084     + return count;
1085     if (strcmp(token, "add") == 0) {
1086     char *endp;
1087     int vendor, device, size, buffers;
1088     @@ -552,7 +554,7 @@ static int snd_mem_proc_write(struct file *file, const char __user *buffer,
1089     (buffers = simple_strtol(token, NULL, 0)) <= 0 ||
1090     buffers > 4) {
1091     printk(KERN_ERR "snd-page-alloc: invalid proc write format\n");
1092     - return (int)count;
1093     + return count;
1094     }
1095     vendor &= 0xffff;
1096     device &= 0xffff;
1097     @@ -564,7 +566,7 @@ static int snd_mem_proc_write(struct file *file, const char __user *buffer,
1098     if (pci_set_dma_mask(pci, mask) < 0 ||
1099     pci_set_consistent_dma_mask(pci, mask) < 0) {
1100     printk(KERN_ERR "snd-page-alloc: cannot set DMA mask %lx for pci %04x:%04x\n", mask, vendor, device);
1101     - return (int)count;
1102     + return count;
1103     }
1104     }
1105     for (i = 0; i < buffers; i++) {
1106     @@ -574,7 +576,7 @@ static int snd_mem_proc_write(struct file *file, const char __user *buffer,
1107     size, &dmab) < 0) {
1108     printk(KERN_ERR "snd-page-alloc: cannot allocate buffer pages (size = %d)\n", size);
1109     pci_dev_put(pci);
1110     - return (int)count;
1111     + return count;
1112     }
1113     snd_dma_reserve_buf(&dmab, snd_dma_pci_buf_id(pci));
1114     }
1115     @@ -600,9 +602,21 @@ static int snd_mem_proc_write(struct file *file, const char __user *buffer,
1116     free_all_reserved_pages();
1117     else
1118     printk(KERN_ERR "snd-page-alloc: invalid proc cmd\n");
1119     - return (int)count;
1120     + return count;
1121     }
1122     #endif /* CONFIG_PCI */
1123     +
1124     +static const struct file_operations snd_mem_proc_fops = {
1125     + .owner = THIS_MODULE,
1126     + .open = snd_mem_proc_open,
1127     + .read = seq_read,
1128     +#ifdef CONFIG_PCI
1129     + .write = snd_mem_proc_write,
1130     +#endif
1131     + .llseek = seq_lseek,
1132     + .release = single_release,
1133     +};
1134     +
1135     #endif /* CONFIG_PROC_FS */
1136    
1137     /*
1138     @@ -613,12 +627,8 @@ static int __init snd_mem_init(void)
1139     {
1140     #ifdef CONFIG_PROC_FS
1141     snd_mem_proc = create_proc_entry(SND_MEM_PROC_FILE, 0644, NULL);
1142     - if (snd_mem_proc) {
1143     - snd_mem_proc->read_proc = snd_mem_proc_read;
1144     -#ifdef CONFIG_PCI
1145     - snd_mem_proc->write_proc = snd_mem_proc_write;
1146     -#endif
1147     - }
1148     + if (snd_mem_proc)
1149     + snd_mem_proc->proc_fops = &snd_mem_proc_fops;
1150     #endif
1151     return 0;
1152     }