summaryrefslogtreecommitdiff
path: root/include
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@athlon.transmeta.com>2002-02-05 00:16:39 -0800
committerLinus Torvalds <torvalds@athlon.transmeta.com>2002-02-05 00:16:39 -0800
commit463727d199b089c420e750d43f75ea9403a45e12 (patch)
tree5bc53f8216433d437c754729fc8208a908f7b7dd /include
parent0713f0290054eb9769d588120712e3dccfb3ec34 (diff)
v2.5.2.2 -> v2.5.2.3
- Al Viro: VFS inode allocation moved down to filesystem, trim inodes - Greg KH: USB update, hotplug documentation - Kai Germaschewski: ISDN update - Ingo Molnar: scheduler tweaking ("J2") - Arnaldo: emu10k kdev_t updates - Ben Collins: firewire updates - Björn Wesen: cris arch update - Hal Duston: ps2esdi driver bio/kdev_t fixes - Jean Tourrilhes: move wireless drivers into drivers/net/wireless, update wireless API #1 - Richard Gooch: devfs race fix - OGAWA Hirofumi: FATFS update
Diffstat (limited to 'include')
-rw-r--r--include/asm-cris/bitops.h90
-rw-r--r--include/asm-cris/elf.h52
-rw-r--r--include/asm-cris/ethernet.h18
-rw-r--r--include/asm-cris/irq.h38
-rw-r--r--include/asm-cris/page.h10
-rw-r--r--include/asm-cris/pgalloc.h8
-rw-r--r--include/asm-cris/pgtable.h10
-rw-r--r--include/asm-cris/processor.h2
-rw-r--r--include/asm-cris/scatterlist.h18
-rw-r--r--include/asm-cris/unistd.h1
-rw-r--r--include/asm-cris/user.h45
-rw-r--r--include/asm-i386/hw_irq.h5
-rw-r--r--include/linux/affs_fs.h2
-rw-r--r--include/linux/affs_fs_i.h10
-rw-r--r--include/linux/amigaffs.h12
-rw-r--r--include/linux/coda.h1
-rw-r--r--include/linux/coda_fs_i.h1
-rw-r--r--include/linux/coda_linux.h5
-rw-r--r--include/linux/dnotify.h2
-rw-r--r--include/linux/efs_fs.h10
-rw-r--r--include/linux/efs_fs_i.h1
-rw-r--r--include/linux/ext2_fs.h97
-rw-r--r--include/linux/ext2_fs_i.h41
-rw-r--r--include/linux/ext3_fs.h9
-rw-r--r--include/linux/ext3_fs_i.h1
-rw-r--r--include/linux/ext3_jbd.h2
-rw-r--r--include/linux/fs.h29
-rw-r--r--include/linux/hpfs_fs_i.h19
-rw-r--r--include/linux/netdevice.h4
-rw-r--r--include/linux/nfs_fs.h160
-rw-r--r--include/linux/nfs_fs_i.h81
-rw-r--r--include/linux/qnx4_fs.h16
-rw-r--r--include/linux/qnx4_fs_i.h39
-rw-r--r--include/linux/sched.h3
-rw-r--r--include/linux/shmem_fs.h7
-rw-r--r--include/linux/ufs_fs.h223
-rw-r--r--include/linux/ufs_fs_i.h1
-rw-r--r--include/linux/ufs_fs_sb.h221
-rw-r--r--include/linux/umsdos_fs.p5
-rw-r--r--include/linux/usb.h9
-rw-r--r--include/linux/usbdev_fs_i.h11
-rw-r--r--include/linux/usbdev_fs_sb.h13
-rw-r--r--include/linux/wireless.h117
-rw-r--r--include/net/iw_handler.h374
44 files changed, 1149 insertions, 674 deletions
diff --git a/include/asm-cris/bitops.h b/include/asm-cris/bitops.h
index 86b07d546759..4d9856538d92 100644
--- a/include/asm-cris/bitops.h
+++ b/include/asm-cris/bitops.h
@@ -22,6 +22,7 @@
/* We use generic_ffs so get it; include guards resolve the possible
mutually inclusion. */
#include <linux/bitops.h>
+#include <linux/compiler.h>
/*
* Some hacks to defeat gcc over-optimizations..
@@ -43,6 +44,8 @@ struct __dummy { unsigned long a[100]; };
#define set_bit(nr, addr) (void)test_and_set_bit(nr, addr)
+#define __set_bit(nr, addr) (void)__test_and_set_bit(nr, addr)
+
/*
* clear_bit - Clears a bit in memory
* @nr: Bit to clear
@@ -56,6 +59,8 @@ struct __dummy { unsigned long a[100]; };
#define clear_bit(nr, addr) (void)test_and_clear_bit(nr, addr)
+#define __clear_bit(nr, addr) (void)__test_and_clear_bit(nr, addr)
+
/*
* change_bit - Toggle a bit in memory
* @nr: Bit to clear
@@ -89,7 +94,7 @@ struct __dummy { unsigned long a[100]; };
* It also implies a memory barrier.
*/
-static __inline__ int test_and_set_bit(int nr, void *addr)
+static inline int test_and_set_bit(int nr, void *addr)
{
unsigned int mask, retval;
unsigned long flags;
@@ -105,6 +110,18 @@ static __inline__ int test_and_set_bit(int nr, void *addr)
return retval;
}
+static inline int __test_and_set_bit(int nr, void *addr)
+{
+ unsigned int mask, retval;
+ unsigned int *adr = (unsigned int *)addr;
+
+ adr += nr >> 5;
+ mask = 1 << (nr & 0x1f);
+ retval = (mask & *adr) != 0;
+ *adr |= mask;
+ return retval;
+}
+
/*
* clear_bit() doesn't provide any barrier for the compiler.
*/
@@ -120,7 +137,7 @@ static __inline__ int test_and_set_bit(int nr, void *addr)
* It also implies a memory barrier.
*/
-static __inline__ int test_and_clear_bit(int nr, void *addr)
+static inline int test_and_clear_bit(int nr, void *addr)
{
unsigned int mask, retval;
unsigned long flags;
@@ -146,7 +163,7 @@ static __inline__ int test_and_clear_bit(int nr, void *addr)
* but actually fail. You must protect multiple accesses with a lock.
*/
-static __inline__ int __test_and_clear_bit(int nr, void *addr)
+static inline int __test_and_clear_bit(int nr, void *addr)
{
unsigned int mask, retval;
unsigned int *adr = (unsigned int *)addr;
@@ -166,7 +183,7 @@ static __inline__ int __test_and_clear_bit(int nr, void *addr)
* It also implies a memory barrier.
*/
-static __inline__ int test_and_change_bit(int nr, void *addr)
+static inline int test_and_change_bit(int nr, void *addr)
{
unsigned int mask, retval;
unsigned long flags;
@@ -183,7 +200,7 @@ static __inline__ int test_and_change_bit(int nr, void *addr)
/* WARNING: non atomic and it can be reordered! */
-static __inline__ int __test_and_change_bit(int nr, void *addr)
+static inline int __test_and_change_bit(int nr, void *addr)
{
unsigned int mask, retval;
unsigned int *adr = (unsigned int *)addr;
@@ -204,7 +221,7 @@ static __inline__ int __test_and_change_bit(int nr, void *addr)
* This routine doesn't need to be atomic.
*/
-static __inline__ int test_bit(int nr, const void *addr)
+static inline int test_bit(int nr, const void *addr)
{
unsigned int mask;
unsigned int *adr = (unsigned int *)addr;
@@ -225,7 +242,7 @@ static __inline__ int test_bit(int nr, const void *addr)
* number. They differ in that the first function also inverts all bits
* in the input.
*/
-static __inline__ unsigned long cris_swapnwbrlz(unsigned long w)
+static inline unsigned long cris_swapnwbrlz(unsigned long w)
{
/* Let's just say we return the result in the same register as the
input. Saying we clobber the input but can return the result
@@ -241,7 +258,7 @@ static __inline__ unsigned long cris_swapnwbrlz(unsigned long w)
return res;
}
-static __inline__ unsigned long cris_swapwbrlz(unsigned long w)
+static inline unsigned long cris_swapwbrlz(unsigned long w)
{
unsigned res;
__asm__ ("swapwbr %0 \n\t"
@@ -255,7 +272,7 @@ static __inline__ unsigned long cris_swapwbrlz(unsigned long w)
* ffz = Find First Zero in word. Undefined if no zero exists,
* so code should check against ~0UL first..
*/
-static __inline__ unsigned long ffz(unsigned long w)
+static inline unsigned long ffz(unsigned long w)
{
/* The generic_ffs function is used to avoid the asm when the
argument is a constant. */
@@ -268,7 +285,7 @@ static __inline__ unsigned long ffz(unsigned long w)
* Somewhat like ffz but the equivalent of generic_ffs: in contrast to
* ffz we return the first one-bit *plus one*.
*/
-static __inline__ unsigned long ffs(unsigned long w)
+static inline unsigned long ffs(unsigned long w)
{
/* The generic_ffs function is used to avoid the asm when the
argument is a constant. */
@@ -283,7 +300,7 @@ static __inline__ unsigned long ffs(unsigned long w)
* @offset: The bitnumber to start searching at
* @size: The maximum size to search
*/
-static __inline__ int find_next_zero_bit (void * addr, int size, int offset)
+static inline int find_next_zero_bit (void * addr, int size, int offset)
{
unsigned long *p = ((unsigned long *) addr) + (offset >> 5);
unsigned long result = offset & ~31UL;
@@ -331,6 +348,17 @@ static __inline__ int find_next_zero_bit (void * addr, int size, int offset)
#define find_first_zero_bit(addr, size) \
find_next_zero_bit((addr), (size), 0)
+/*
+ * hweightN - returns the hamming weight of a N-bit word
+ * @x: the word to weigh
+ *
+ * The Hamming Weight of a number is the total number of bits set in it.
+ */
+
+#define hweight32(x) generic_hweight32(x)
+#define hweight16(x) generic_hweight16(x)
+#define hweight8(x) generic_hweight8(x)
+
#define ext2_set_bit test_and_set_bit
#define ext2_clear_bit test_and_clear_bit
#define ext2_test_bit test_bit
@@ -343,7 +371,45 @@ static __inline__ int find_next_zero_bit (void * addr, int size, int offset)
#define minix_test_bit(nr,addr) test_bit(nr,addr)
#define minix_find_first_zero_bit(addr,size) find_first_zero_bit(addr,size)
-#endif /* __KERNEL__ */
+#if 0
+/* TODO: see below */
+#define sched_find_first_zero_bit(addr) find_first_zero_bit(addr, 168)
+
+#else
+/* TODO: left out pending where to put it.. (there are .h dependencies) */
+ /*
+ * Every architecture must define this function. It's the fastest
+ * way of searching a 168-bit bitmap where the first 128 bits are
+ * unlikely to be set. It's guaranteed that at least one of the 168
+ * bits is cleared.
+ */
+#if 0
+#if MAX_RT_PRIO != 128 || MAX_PRIO != 168
+# error update this function.
+#endif
+#else
+#define MAX_RT_PRIO 128
+#define MAX_PRIO 168
+#endif
+
+static inline int sched_find_first_zero_bit(char *bitmap)
+{
+ unsigned int *b = (unsigned int *)bitmap;
+ unsigned int rt;
+
+ rt = b[0] & b[1] & b[2] & b[3];
+ if (unlikely(rt != 0xffffffff))
+ return find_first_zero_bit(bitmap, MAX_RT_PRIO);
+
+ if (b[4] != ~0)
+ return ffz(b[4]) + MAX_RT_PRIO;
+ return ffz(b[5]) + 32 + MAX_RT_PRIO;
+}
+#undef MAX_PRIO
+#undef MAX_RT_PRIO
+#endif
+
+#endif /* __KERNEL__ */
#endif /* _CRIS_BITOPS_H */
diff --git a/include/asm-cris/elf.h b/include/asm-cris/elf.h
index 085c43dd7b57..dba80d0609ef 100644
--- a/include/asm-cris/elf.h
+++ b/include/asm-cris/elf.h
@@ -9,8 +9,9 @@
typedef unsigned long elf_greg_t;
-/* These probably need fixing. */
-#define ELF_NGREG (sizeof (struct pt_regs) / sizeof(elf_greg_t))
+/* Note that NGREG is defined to ELF_NGREG in include/linux/elfcore.h, and is
+ thus exposed to user-space. */
+#define ELF_NGREG (sizeof (struct user_regs_struct) / sizeof(elf_greg_t))
typedef elf_greg_t elf_gregset_t[ELF_NGREG];
/* A placeholder; CRIS does not have any fp regs. */
@@ -45,7 +46,52 @@ typedef unsigned long elf_fpregset_t;
(_r)->r1 = 0; (_r)->r0 = 0; (_r)->mof = 0; (_r)->srp = 0; \
} while (0)
-#undef USE_ELF_CORE_DUMP
+#define USE_ELF_CORE_DUMP
+
+/* The additional layer below is because the stack pointer is missing in
+ the pt_regs struct, but needed in a core dump. pr_reg is a elf_gregset_t,
+ and should be filled in according to the layout of the user_regs_struct
+ struct; regs is a pt_regs struct. We dump all registers, though several are
+ obviously unnecessary. That way there's less need for intelligence at
+ the receiving end (i.e. gdb). */
+#define ELF_CORE_COPY_REGS(pr_reg, regs) \
+ pr_reg[0] = regs->r0; \
+ pr_reg[1] = regs->r1; \
+ pr_reg[2] = regs->r2; \
+ pr_reg[3] = regs->r3; \
+ pr_reg[4] = regs->r4; \
+ pr_reg[5] = regs->r5; \
+ pr_reg[6] = regs->r6; \
+ pr_reg[7] = regs->r7; \
+ pr_reg[8] = regs->r8; \
+ pr_reg[9] = regs->r9; \
+ pr_reg[10] = regs->r10; \
+ pr_reg[11] = regs->r11; \
+ pr_reg[12] = regs->r12; \
+ pr_reg[13] = regs->r13; \
+ pr_reg[14] = rdusp(); /* sp */ \
+ pr_reg[15] = regs->irp; /* pc */ \
+ pr_reg[16] = 0; /* p0 */ \
+ pr_reg[17] = rdvr(); /* vr */ \
+ pr_reg[18] = 0; /* p2 */ \
+ pr_reg[19] = 0; /* p3 */ \
+ pr_reg[20] = 0; /* p4 */ \
+ pr_reg[21] = (regs->dccr & 0xffff); /* ccr */ \
+ pr_reg[22] = 0; /* p6 */ \
+ pr_reg[23] = regs->mof; /* mof */ \
+ pr_reg[24] = 0; /* p8 */ \
+ pr_reg[25] = 0; /* ibr */ \
+ pr_reg[26] = 0; /* irp */ \
+ pr_reg[27] = regs->srp; /* srp */ \
+ pr_reg[28] = 0; /* bar */ \
+ pr_reg[29] = regs->dccr; /* dccr */ \
+ pr_reg[30] = 0; /* brp */ \
+ pr_reg[31] = rdusp(); /* usp */ \
+ pr_reg[32] = 0; /* csrinstr */ \
+ pr_reg[33] = 0; /* csraddr */ \
+ pr_reg[34] = 0; /* csrdata */
+
+
#define ELF_EXEC_PAGESIZE 8192
/* This is the location that an ET_DYN program is loaded if exec'ed. Typical
diff --git a/include/asm-cris/ethernet.h b/include/asm-cris/ethernet.h
new file mode 100644
index 000000000000..30da58a7d00d
--- /dev/null
+++ b/include/asm-cris/ethernet.h
@@ -0,0 +1,18 @@
+/*
+ * ioctl defines for ethernet driver
+ *
+ * Copyright (c) 2001 Axis Communications AB
+ *
+ * Author: Mikael Starvik
+ *
+ */
+
+#ifndef _CRIS_ETHERNET_H
+#define _CRIS_ETHERNET_H
+#define SET_ETH_SPEED_AUTO SIOCDEVPRIVATE /* Auto neg speed */
+#define SET_ETH_SPEED_10 SIOCDEVPRIVATE+1 /* 10 Mbps */
+#define SET_ETH_SPEED_100 SIOCDEVPRIVATE+2 /* 100 Mbps. */
+#define SET_ETH_DUPLEX_AUTO SIOCDEVPRIVATE+3 /* Auto neg duplex */
+#define SET_ETH_DUPLEX_HALF SIOCDEVPRIVATE+4 /* Full duplex */
+#define SET_ETH_DUPLEX_FULL SIOCDEVPRIVATE+5 /* Half duplex */
+#endif /* _CRIS_ETHERNET_H */
diff --git a/include/asm-cris/irq.h b/include/asm-cris/irq.h
index b1b5ada6ff5a..5e4fb8db6735 100644
--- a/include/asm-cris/irq.h
+++ b/include/asm-cris/irq.h
@@ -126,6 +126,9 @@ void set_break_vector(int n, irqvectptr addr);
/* the asm IRQ handler makes sure the causing IRQ is blocked, then it calls
* do_IRQ (with irq disabled still). after that it unblocks and jumps to
* ret_from_intr (entry.S)
+ *
+ * The reason the IRQ is blocked is to allow an sti() before the handler which
+ * will acknowledge the interrupt is run.
*/
#define BUILD_IRQ(nr,mask) \
@@ -151,6 +154,41 @@ __asm__ ( \
"reti\n\t" \
"nop\n");
+/* This is subtle. The timer interrupt is crucial and it should not be disabled for
+ * too long. However, if it had been a normal interrupt as per BUILD_IRQ, it would
+ * have been BLOCK'ed, and then softirq's are run before we return here to UNBLOCK.
+ * If the softirq's take too much time to run, the timer irq won't run and the
+ * watchdog will kill us.
+ *
+ * Furthermore, if a lot of other irq's occur before we return here, the multiple_irq
+ * handler is run and it prioritizes the timer interrupt. However if we had BLOCK'ed
+ * it here, we would not get the multiple_irq at all.
+ *
+ * The non-blocking here is based on the knowledge that the timer interrupt is
+ * registred as a fast interrupt (SA_INTERRUPT) so that we _know_ there will not
+ * be an sti() before the timer irq handler is run to acknowledge the interrupt.
+ */
+
+#define BUILD_TIMER_IRQ(nr,mask) \
+void IRQ_NAME(nr); \
+void sIRQ_NAME(nr); \
+void BAD_IRQ_NAME(nr); \
+__asm__ ( \
+ ".text\n\t" \
+ "IRQ" #nr "_interrupt:\n\t" \
+ SAVE_ALL \
+ "sIRQ" #nr "_interrupt:\n\t" /* shortcut for the multiple irq handler */ \
+ "moveq "#nr",$r10\n\t" \
+ "move.d $sp,$r11\n\t" \
+ "jsr do_IRQ\n\t" /* irq.c, r10 and r11 are arguments */ \
+ "moveq 0,$r9\n\t" /* make ret_from_intr realise we came from an irq */ \
+ "jump ret_from_intr\n\t" \
+ "bad_IRQ" #nr "_interrupt:\n\t" \
+ "push $r0\n\t" \
+ BLOCK_IRQ(mask,nr) \
+ "pop $r0\n\t" \
+ "reti\n\t" \
+ "nop\n");
#endif /* _ASM_IRQ_H */
diff --git a/include/asm-cris/page.h b/include/asm-cris/page.h
index 549345ff4f19..5950e9c1275f 100644
--- a/include/asm-cris/page.h
+++ b/include/asm-cris/page.h
@@ -105,8 +105,14 @@ typedef unsigned long pgprot_t;
* to arm and m68k I think)
*/
-#define virt_to_page(kaddr) (mem_map + (((unsigned long)kaddr - PAGE_OFFSET) >> PAGE_SHIFT))
-#define VALID_PAGE(page) ((page - mem_map) < max_mapnr)
+#define virt_to_page(kaddr) (mem_map + (((unsigned long)(kaddr) - PAGE_OFFSET) >> PAGE_SHIFT))
+#define VALID_PAGE(page) (((page) - mem_map) < max_mapnr)
+
+/* convert a page (based on mem_map and forward) to a physical address
+ * do this by figuring out the virtual address and then use __pa
+ */
+
+#define page_to_phys(page) __pa((((page) - mem_map) << PAGE_SHIFT) + PAGE_OFFSET)
/* from linker script */
diff --git a/include/asm-cris/pgalloc.h b/include/asm-cris/pgalloc.h
index 550c5fab2a39..80e73be0d2b0 100644
--- a/include/asm-cris/pgalloc.h
+++ b/include/asm-cris/pgalloc.h
@@ -21,7 +21,7 @@ extern struct pgtable_cache_struct {
* Allocate and free page tables.
*/
-extern __inline__ pgd_t *get_pgd_slow(void)
+static inline pgd_t *get_pgd_slow(void)
{
pgd_t *ret = (pgd_t *)__get_free_page(GFP_KERNEL);
@@ -33,12 +33,12 @@ extern __inline__ pgd_t *get_pgd_slow(void)
return ret;
}
-extern __inline__ void free_pgd_slow(pgd_t *pgd)
+static inline void free_pgd_slow(pgd_t *pgd)
{
free_page((unsigned long)pgd);
}
-extern __inline__ pgd_t *get_pgd_fast(void)
+static inline pgd_t *get_pgd_fast(void)
{
unsigned long *ret;
@@ -51,7 +51,7 @@ extern __inline__ pgd_t *get_pgd_fast(void)
return (pgd_t *)ret;
}
-extern __inline__ void free_pgd_fast(pgd_t *pgd)
+static inline void free_pgd_fast(pgd_t *pgd)
{
*(unsigned long *)pgd = (unsigned long) pgd_quicklist;
pgd_quicklist = (unsigned long *) pgd;
diff --git a/include/asm-cris/pgtable.h b/include/asm-cris/pgtable.h
index a99f35703c7f..e533400551c0 100644
--- a/include/asm-cris/pgtable.h
+++ b/include/asm-cris/pgtable.h
@@ -3,6 +3,12 @@
* HISTORY:
*
* $Log: pgtable.h,v $
+ * Revision 1.14 2001/12/10 03:08:50 bjornw
+ * Added pgtable_cache_init dummy
+ *
+ * Revision 1.13 2001/11/12 18:05:38 pkj
+ * Added declaration of paging_init().
+ *
* Revision 1.12 2001/08/11 00:28:00 bjornw
* PAGE_CHG_MASK and PAGE_NONE had somewhat untraditional values
*
@@ -106,6 +112,8 @@
* the CRIS page table tree.
*/
+extern void paging_init(void);
+
/* The cache doesn't need to be flushed when TLB entries change because
* the cache is mapped to physical memory, not virtual memory
*/
@@ -507,6 +515,6 @@ static inline void update_mmu_cache(struct vm_area_struct * vma,
/*
* No page table caches to initialise
*/
-#define pgtable_cache_init() do { } while (0)
+#define pgtable_cache_init() do { } while (0)
#endif /* _CRIS_PGTABLE_H */
diff --git a/include/asm-cris/processor.h b/include/asm-cris/processor.h
index a9b11b89eced..7fba87a5aa1b 100644
--- a/include/asm-cris/processor.h
+++ b/include/asm-cris/processor.h
@@ -142,6 +142,6 @@ extern inline unsigned long thread_saved_pc(struct thread_struct *t)
#define init_task (init_task_union.task)
#define init_stack (init_task_union.stack)
-#define cpu_relax() do { } while (0)
+#define cpu_relax() do { } while (0)
#endif /* __ASM_CRIS_PROCESSOR_H */
diff --git a/include/asm-cris/scatterlist.h b/include/asm-cris/scatterlist.h
new file mode 100644
index 000000000000..11a64f5fe30b
--- /dev/null
+++ b/include/asm-cris/scatterlist.h
@@ -0,0 +1,18 @@
+#ifndef __ASM_CRIS_SCATTERLIST_H
+#define __ASM_CRIS_SCATTERLIST_H
+
+struct scatterlist {
+ char * address; /* Location data is to be transferred to */
+ unsigned int length;
+
+ /* The following is i386 highmem junk - not used by us */
+ struct page * page; /* Location for highmem page, if any */
+ unsigned int offset;/* for highmem, page offset */
+
+};
+
+/* i386 junk */
+
+#define ISA_DMA_THRESHOLD (0x1fffffff)
+
+#endif /* !(__ASM_CRIS_SCATTERLIST_H) */
diff --git a/include/asm-cris/unistd.h b/include/asm-cris/unistd.h
index d42c6b383fad..9fe719c8089e 100644
--- a/include/asm-cris/unistd.h
+++ b/include/asm-cris/unistd.h
@@ -378,6 +378,7 @@ static inline _syscall3(int,open,const char *,file,int,flag,int,mode)
static inline _syscall1(int,close,int,fd)
static inline _syscall1(int,_exit,int,exitcode)
static inline _syscall3(pid_t,waitpid,pid_t,pid,int *,wait_stat,int,options)
+static inline _syscall3(off_t,lseek,int,fd,off_t,offset,int,count)
/* the following are just while developing the elinux port! */
diff --git a/include/asm-cris/user.h b/include/asm-cris/user.h
index 79c7048a345d..982f4163bc94 100644
--- a/include/asm-cris/user.h
+++ b/include/asm-cris/user.h
@@ -28,8 +28,51 @@
* to write an integer number of pages.
*/
+/* User mode registers, used for core dumps. In order to keep ELF_NGREG
+ sensible we let all registers be 32 bits. The csr registers are included
+ for future use. */
+struct user_regs_struct {
+ unsigned long r0; /* General registers. */
+ unsigned long r1;
+ unsigned long r2;
+ unsigned long r3;
+ unsigned long r4;
+ unsigned long r5;
+ unsigned long r6;
+ unsigned long r7;
+ unsigned long r8;
+ unsigned long r9;
+ unsigned long r10;
+ unsigned long r11;
+ unsigned long r12;
+ unsigned long r13;
+ unsigned long sp; /* Stack pointer. */
+ unsigned long pc; /* Program counter. */
+ unsigned long p0; /* Constant zero (only 8 bits). */
+ unsigned long vr; /* Version register (only 8 bits). */
+ unsigned long p2; /* Reserved. */
+ unsigned long p3; /* Reserved. */
+ unsigned long p4; /* Constant zero (only 16 bits). */
+ unsigned long ccr; /* Condition code register (only 16 bits). */
+ unsigned long p6; /* Reserved. */
+ unsigned long mof; /* Multiply overflow register. */
+ unsigned long p8; /* Constant zero. */
+ unsigned long ibr; /* Not accessible. */
+ unsigned long irp; /* Not accessible. */
+ unsigned long srp; /* Subroutine return pointer. */
+ unsigned long bar; /* Not accessible. */
+ unsigned long dccr; /* Dword condition code register. */
+ unsigned long brp; /* Not accessible. */
+ unsigned long usp; /* User-mode stack pointer. Same as sp when
+ in user mode. */
+ unsigned long csrinstr; /* Internal status registers. */
+ unsigned long csraddr;
+ unsigned long csrdata;
+};
+
+
struct user {
- struct pt_regs regs; /* entire machine state */
+ struct user_regs_struct regs; /* entire machine state */
size_t u_tsize; /* text size (pages) */
size_t u_dsize; /* data size (pages) */
size_t u_ssize; /* stack size (pages) */
diff --git a/include/asm-i386/hw_irq.h b/include/asm-i386/hw_irq.h
index fc8b17144adf..e6d7377a70d8 100644
--- a/include/asm-i386/hw_irq.h
+++ b/include/asm-i386/hw_irq.h
@@ -35,13 +35,14 @@
* into a single vector (CALL_FUNCTION_VECTOR) to save vector space.
* TLB, reschedule and local APIC vectors are performance-critical.
*
- * Vectors 0xf0-0xfa are free (reserved for future Linux use).
+ * Vectors 0xf0-0xf9 are free (reserved for future Linux use).
*/
#define SPURIOUS_APIC_VECTOR 0xff
#define ERROR_APIC_VECTOR 0xfe
#define INVALIDATE_TLB_VECTOR 0xfd
#define RESCHEDULE_VECTOR 0xfc
-#define CALL_FUNCTION_VECTOR 0xfb
+#define TASK_MIGRATION_VECTOR 0xfb
+#define CALL_FUNCTION_VECTOR 0xfa
/*
* Local APIC timer IRQ vector is on a different priority level,
diff --git a/include/linux/affs_fs.h b/include/linux/affs_fs.h
index 68ba0f768bfa..7859a5e1883c 100644
--- a/include/linux/affs_fs.h
+++ b/include/linux/affs_fs.h
@@ -6,6 +6,8 @@
#include <linux/types.h>
+#include <linux/affs_fs_i.h>
+
#define AFFS_SUPER_MAGIC 0xadff
struct affs_date;
diff --git a/include/linux/affs_fs_i.h b/include/linux/affs_fs_i.h
index 430ff682f641..c32f69ca18f7 100644
--- a/include/linux/affs_fs_i.h
+++ b/include/linux/affs_fs_i.h
@@ -3,9 +3,6 @@
#include <linux/a.out.h>
-// move this to linux/coda.h!!!
-#include <linux/time.h>
-
#define AFFS_CACHE_SIZE PAGE_SIZE
//#define AFFS_CACHE_SIZE (4*4)
@@ -48,10 +45,13 @@ struct affs_inode_info {
unsigned char i_pad;
s32 i_parent; /* parent ino */
#endif
+ struct inode vfs_inode;
};
/* short cut to get to the affs specific inode data */
-#define AFFS_INODE (&inode->u.affs_i)
-#define AFFS_DIR (&dir->u.affs_i)
+static inline struct affs_inode_info *AFFS_I(struct inode *inode)
+{
+ return list_entry(inode, struct affs_inode_info, vfs_inode);
+}
#endif
diff --git a/include/linux/amigaffs.h b/include/linux/amigaffs.h
index 1e7d6e8fa676..b4b1d430c306 100644
--- a/include/linux/amigaffs.h
+++ b/include/linux/amigaffs.h
@@ -93,32 +93,32 @@ affs_adjust_bitmapchecksum(struct buffer_head *bh, u32 val)
static inline void
affs_lock_link(struct inode *inode)
{
- down(&AFFS_INODE->i_link_lock);
+ down(&AFFS_I(inode)->i_link_lock);
}
static inline void
affs_unlock_link(struct inode *inode)
{
- up(&AFFS_INODE->i_link_lock);
+ up(&AFFS_I(inode)->i_link_lock);
}
static inline void
affs_lock_dir(struct inode *inode)
{
- down(&AFFS_INODE->i_hash_lock);
+ down(&AFFS_I(inode)->i_hash_lock);
}
static inline void
affs_unlock_dir(struct inode *inode)
{
- up(&AFFS_INODE->i_hash_lock);
+ up(&AFFS_I(inode)->i_hash_lock);
}
static inline void
affs_lock_ext(struct inode *inode)
{
- down(&AFFS_INODE->i_ext_lock);
+ down(&AFFS_I(inode)->i_ext_lock);
}
static inline void
affs_unlock_ext(struct inode *inode)
{
- up(&AFFS_INODE->i_ext_lock);
+ up(&AFFS_I(inode)->i_ext_lock);
}
#ifdef __LITTLE_ENDIAN
diff --git a/include/linux/coda.h b/include/linux/coda.h
index f96edc7c7a37..0d168b715ed7 100644
--- a/include/linux/coda.h
+++ b/include/linux/coda.h
@@ -99,6 +99,7 @@ typedef unsigned long long u_quad_t;
#if defined(__linux__)
+#include <linux/time.h>
#define cdev_t u_quad_t
#ifndef __KERNEL__
#if !defined(_UQUAD_T_) && (!defined(__GLIBC__) || __GLIBC__ < 2)
diff --git a/include/linux/coda_fs_i.h b/include/linux/coda_fs_i.h
index 43d63d77697d..959fb24a94ad 100644
--- a/include/linux/coda_fs_i.h
+++ b/include/linux/coda_fs_i.h
@@ -24,6 +24,7 @@ struct coda_inode_info {
unsigned int c_contcount; /* refcount for container file */
struct coda_cred c_cached_cred; /* credentials of cached perms */
unsigned int c_cached_perm; /* cached access permissions */
+ struct inode vfs_inode;
};
/* flags */
diff --git a/include/linux/coda_linux.h b/include/linux/coda_linux.h
index d514f908a3a5..de66780b8d2c 100644
--- a/include/linux/coda_linux.h
+++ b/include/linux/coda_linux.h
@@ -111,7 +111,10 @@ do { \
/* inode to cnode access functions */
-#define ITOC(inode) (&((inode)->u.coda_i))
+static inline struct coda_inode_info *ITOC(struct inode *inode)
+{
+ return list_entry(inode, struct coda_inode_info, vfs_inode);
+}
static __inline__ struct ViceFid *coda_i2f(struct inode *inode)
{
diff --git a/include/linux/dnotify.h b/include/linux/dnotify.h
index 5e231462b645..90813c505064 100644
--- a/include/linux/dnotify.h
+++ b/include/linux/dnotify.h
@@ -4,6 +4,8 @@
* Copyright 2000 (C) Stephen Rothwell
*/
+#include <linux/fs.h>
+
struct dnotify_struct {
struct dnotify_struct * dn_next;
int dn_magic;
diff --git a/include/linux/efs_fs.h b/include/linux/efs_fs.h
index ae049ed2f147..99d468975d06 100644
--- a/include/linux/efs_fs.h
+++ b/include/linux/efs_fs.h
@@ -37,13 +37,11 @@ static const char cprt[] = "EFS: "EFS_VERSION" - (c) 1999 Al Smith <Al.Smith@aes
#define MAX(a, b) (((a) > (b)) ? (a) : (b))
#endif
-#ifdef _EFS_USE_GENERIC
-#define INODE_INFO(i) (struct efs_inode_info *) &((i)->u.generic_ip)
-#define SUPER_INFO(s) (struct efs_sb_info *) &((s)->u.generic_sbp)
-#else
-#define INODE_INFO(i) &((i)->u.efs_i)
+static inline struct efs_inode_info *INODE_INFO(struct inode *inode)
+{
+ return list_entry(inode, struct efs_inode_info, vfs_inode);
+}
#define SUPER_INFO(s) &((s)->u.efs_sb)
-#endif
extern struct inode_operations efs_dir_inode_operations;
extern struct file_operations efs_dir_operations;
diff --git a/include/linux/efs_fs_i.h b/include/linux/efs_fs_i.h
index de55021ad24e..64fe538acc88 100644
--- a/include/linux/efs_fs_i.h
+++ b/include/linux/efs_fs_i.h
@@ -61,6 +61,7 @@ struct efs_inode_info {
int lastextent;
efs_extent extents[EFS_DIRECTEXTENTS];
+ struct inode vfs_inode;
};
#endif /* __EFS_FS_I_H__ */
diff --git a/include/linux/ext2_fs.h b/include/linux/ext2_fs.h
index 03112a82fadb..2b3624d801b3 100644
--- a/include/linux/ext2_fs.h
+++ b/include/linux/ext2_fs.h
@@ -532,101 +532,4 @@ enum {
#define EXT2_DIR_REC_LEN(name_len) (((name_len) + 8 + EXT2_DIR_ROUND) & \
~EXT2_DIR_ROUND)
-#ifdef __KERNEL__
-/*
- * Function prototypes
- */
-
-/*
- * Ok, these declarations are also in <linux/kernel.h> but none of the
- * ext2 source programs needs to include it so they are duplicated here.
- */
-# define NORET_TYPE /**/
-# define ATTRIB_NORET __attribute__((noreturn))
-# define NORET_AND noreturn,
-
-/* balloc.c */
-extern int ext2_bg_has_super(struct super_block *sb, int group);
-extern unsigned long ext2_bg_num_gdb(struct super_block *sb, int group);
-extern int ext2_new_block (struct inode *, unsigned long,
- __u32 *, __u32 *, int *);
-extern void ext2_free_blocks (struct inode *, unsigned long,
- unsigned long);
-extern unsigned long ext2_count_free_blocks (struct super_block *);
-extern void ext2_check_blocks_bitmap (struct super_block *);
-extern struct ext2_group_desc * ext2_get_group_desc(struct super_block * sb,
- unsigned int block_group,
- struct buffer_head ** bh);
-
-/* dir.c */
-extern int ext2_add_link (struct dentry *, struct inode *);
-extern ino_t ext2_inode_by_name(struct inode *, struct dentry *);
-extern int ext2_make_empty(struct inode *, struct inode *);
-extern struct ext2_dir_entry_2 * ext2_find_entry (struct inode *,struct dentry *, struct page **);
-extern int ext2_delete_entry (struct ext2_dir_entry_2 *, struct page *);
-extern int ext2_empty_dir (struct inode *);
-extern struct ext2_dir_entry_2 * ext2_dotdot (struct inode *, struct page **);
-extern void ext2_set_link(struct inode *, struct ext2_dir_entry_2 *, struct page *, struct inode *);
-
-/* fsync.c */
-extern int ext2_sync_file (struct file *, struct dentry *, int);
-extern int ext2_fsync_inode (struct inode *, int);
-
-/* ialloc.c */
-extern struct inode * ext2_new_inode (const struct inode *, int);
-extern void ext2_free_inode (struct inode *);
-extern unsigned long ext2_count_free_inodes (struct super_block *);
-extern void ext2_check_inodes_bitmap (struct super_block *);
-extern unsigned long ext2_count_free (struct buffer_head *, unsigned);
-
-/* inode.c */
-extern void ext2_read_inode (struct inode *);
-extern void ext2_write_inode (struct inode *, int);
-extern void ext2_put_inode (struct inode *);
-extern void ext2_delete_inode (struct inode *);
-extern int ext2_sync_inode (struct inode *);
-extern void ext2_discard_prealloc (struct inode *);
-extern void ext2_truncate (struct inode *);
-
-/* ioctl.c */
-extern int ext2_ioctl (struct inode *, struct file *, unsigned int,
- unsigned long);
-
-/* super.c */
-extern void ext2_error (struct super_block *, const char *, const char *, ...)
- __attribute__ ((format (printf, 3, 4)));
-extern NORET_TYPE void ext2_panic (struct super_block *, const char *,
- const char *, ...)
- __attribute__ ((NORET_AND format (printf, 3, 4)));
-extern void ext2_warning (struct super_block *, const char *, const char *, ...)
- __attribute__ ((format (printf, 3, 4)));
-extern void ext2_update_dynamic_rev (struct super_block *sb);
-extern void ext2_put_super (struct super_block *);
-extern void ext2_write_super (struct super_block *);
-extern int ext2_remount (struct super_block *, int *, char *);
-extern struct super_block * ext2_read_super (struct super_block *,void *,int);
-extern int ext2_statfs (struct super_block *, struct statfs *);
-
-/*
- * Inodes and files operations
- */
-
-/* dir.c */
-extern struct file_operations ext2_dir_operations;
-
-/* file.c */
-extern struct inode_operations ext2_file_inode_operations;
-extern struct file_operations ext2_file_operations;
-
-/* inode.c */
-extern struct address_space_operations ext2_aops;
-
-/* namei.c */
-extern struct inode_operations ext2_dir_inode_operations;
-
-/* symlink.c */
-extern struct inode_operations ext2_fast_symlink_inode_operations;
-
-#endif /* __KERNEL__ */
-
#endif /* _LINUX_EXT2_FS_H */
diff --git a/include/linux/ext2_fs_i.h b/include/linux/ext2_fs_i.h
deleted file mode 100644
index 7f02e7537ba3..000000000000
--- a/include/linux/ext2_fs_i.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * linux/include/linux/ext2_fs_i.h
- *
- * Copyright (C) 1992, 1993, 1994, 1995
- * Remy Card (card@masi.ibp.fr)
- * Laboratoire MASI - Institut Blaise Pascal
- * Universite Pierre et Marie Curie (Paris VI)
- *
- * from
- *
- * linux/include/linux/minix_fs_i.h
- *
- * Copyright (C) 1991, 1992 Linus Torvalds
- */
-
-#ifndef _LINUX_EXT2_FS_I
-#define _LINUX_EXT2_FS_I
-
-/*
- * second extended file system inode data in memory
- */
-struct ext2_inode_info {
- __u32 i_data[15];
- __u32 i_flags;
- __u32 i_faddr;
- __u8 i_frag_no;
- __u8 i_frag_size;
- __u16 i_osync;
- __u32 i_file_acl;
- __u32 i_dir_acl;
- __u32 i_dtime;
- __u32 i_block_group;
- __u32 i_next_alloc_block;
- __u32 i_next_alloc_goal;
- __u32 i_prealloc_block;
- __u32 i_prealloc_count;
- __u32 i_dir_start_lookup;
- int i_new_inode:1; /* Is a freshly allocated inode */
-};
-
-#endif /* _LINUX_EXT2_FS_I */
diff --git a/include/linux/ext3_fs.h b/include/linux/ext3_fs.h
index db5de1462107..c7fed24a7c76 100644
--- a/include/linux/ext3_fs.h
+++ b/include/linux/ext3_fs.h
@@ -443,7 +443,10 @@ struct ext3_super_block {
#ifdef __KERNEL__
#define EXT3_SB(sb) (&((sb)->u.ext3_sb))
-#define EXT3_I(inode) (&((inode)->u.ext3_i))
+static inline struct ext3_inode_info *EXT3_I(struct inode *inode)
+{
+ return list_entry(inode, struct ext3_inode_info, vfs_inode);
+}
#else
/* Assume that user mode programs are passing in an ext3fs superblock, not
* a kernel struct super_block. This will allow us to call the feature-test
@@ -451,7 +454,7 @@ struct ext3_super_block {
#define EXT3_SB(sb) (sb)
#endif
-#define NEXT_ORPHAN(inode) (inode)->u.ext3_i.i_dtime
+#define NEXT_ORPHAN(inode) EXT3_I(inode)->i_dtime
/*
* Codes for operating systems
@@ -620,7 +623,7 @@ extern int ext3_check_dir_entry(const char *, struct inode *,
extern int ext3_sync_file (struct file *, struct dentry *, int);
/* ialloc.c */
-extern struct inode * ext3_new_inode (handle_t *, const struct inode *, int);
+extern struct inode * ext3_new_inode (handle_t *, struct inode *, int);
extern void ext3_free_inode (handle_t *, struct inode *);
extern struct inode * ext3_orphan_get (struct super_block *, ino_t);
extern unsigned long ext3_count_free_inodes (struct super_block *);
diff --git a/include/linux/ext3_fs_i.h b/include/linux/ext3_fs_i.h
index 3c8d398a8103..104aea4e0c19 100644
--- a/include/linux/ext3_fs_i.h
+++ b/include/linux/ext3_fs_i.h
@@ -73,6 +73,7 @@ struct ext3_inode_info {
* by other means, so we have truncate_sem.
*/
struct rw_semaphore truncate_sem;
+ struct inode vfs_inode;
};
#endif /* _LINUX_EXT3_FS_I */
diff --git a/include/linux/ext3_jbd.h b/include/linux/ext3_jbd.h
index 88bb8a516bf6..ece9ec115665 100644
--- a/include/linux/ext3_jbd.h
+++ b/include/linux/ext3_jbd.h
@@ -289,7 +289,7 @@ static inline int ext3_should_journal_data(struct inode *inode)
return 1;
if (test_opt(inode->i_sb, DATA_FLAGS) == EXT3_MOUNT_JOURNAL_DATA)
return 1;
- if (inode->u.ext3_i.i_flags & EXT3_JOURNAL_DATA_FL)
+ if (EXT3_I(inode)->i_flags & EXT3_JOURNAL_DATA_FL)
return 1;
return 0;
}
diff --git a/include/linux/fs.h b/include/linux/fs.h
index 4e5de1286d87..6bda17aed79a 100644
--- a/include/linux/fs.h
+++ b/include/linux/fs.h
@@ -288,25 +288,15 @@ extern void set_bh_page(struct buffer_head *bh, struct page *page, unsigned long
#include <linux/pipe_fs_i.h>
#include <linux/minix_fs_i.h>
-#include <linux/ext2_fs_i.h>
-#include <linux/ext3_fs_i.h>
-#include <linux/hpfs_fs_i.h>
#include <linux/ntfs_fs_i.h>
#include <linux/msdos_fs_i.h>
#include <linux/umsdos_fs_i.h>
#include <linux/iso_fs_i.h>
-#include <linux/nfs_fs_i.h>
#include <linux/sysv_fs_i.h>
-#include <linux/affs_fs_i.h>
-#include <linux/ufs_fs_i.h>
-#include <linux/efs_fs_i.h>
-#include <linux/coda_fs_i.h>
#include <linux/romfs_fs_i.h>
-#include <linux/shmem_fs.h>
#include <linux/smb_fs_i.h>
#include <linux/hfs_fs_i.h>
#include <linux/adfs_fs_i.h>
-#include <linux/qnx4_fs_i.h>
#include <linux/reiserfs_fs_i.h>
#include <linux/bfs_fs_i.h>
#include <linux/udf_fs_i.h>
@@ -477,25 +467,15 @@ struct inode {
__u32 i_generation;
union {
struct minix_inode_info minix_i;
- struct ext2_inode_info ext2_i;
- struct ext3_inode_info ext3_i;
- struct hpfs_inode_info hpfs_i;
struct ntfs_inode_info ntfs_i;
struct msdos_inode_info msdos_i;
struct umsdos_inode_info umsdos_i;
struct iso_inode_info isofs_i;
- struct nfs_inode_info nfs_i;
struct sysv_inode_info sysv_i;
- struct affs_inode_info affs_i;
- struct ufs_inode_info ufs_i;
- struct efs_inode_info efs_i;
struct romfs_inode_info romfs_i;
- struct shmem_inode_info shmem_i;
- struct coda_inode_info coda_i;
struct smb_inode_info smbfs_i;
struct hfs_inode_info hfs_i;
struct adfs_inode_info adfs_i;
- struct qnx4_inode_info qnx4_i;
struct reiserfs_inode_info reiserfs_i;
struct bfs_inode_info bfs_i;
struct udf_inode_info udf_i;
@@ -507,6 +487,12 @@ struct inode {
} u;
};
+#include <linux/shmem_fs.h>
+/* will die */
+#include <linux/coda_fs_i.h>
+#include <linux/ext3_fs_i.h>
+#include <linux/efs_fs_i.h>
+
struct fown_struct {
int pid; /* pid or -pgrp where SIGIO should be sent */
uid_t uid, euid; /* uid/euid of process setting the owner */
@@ -563,6 +549,9 @@ extern int init_private_file(struct file *, struct dentry *, int);
*/
typedef struct files_struct *fl_owner_t;
+/* that will die - we need it for nfs_lock_info */
+#include <linux/nfs_fs_i.h>
+
struct file_lock {
struct file_lock *fl_next; /* singly linked list for this inode */
struct list_head fl_link; /* doubly linked list of all locks */
diff --git a/include/linux/hpfs_fs_i.h b/include/linux/hpfs_fs_i.h
index 56a758b1627a..c4d6cce5d607 100644
--- a/include/linux/hpfs_fs_i.h
+++ b/include/linux/hpfs_fs_i.h
@@ -18,24 +18,7 @@ struct hpfs_inode_info {
unsigned i_dirty : 1;
struct semaphore i_sem; /* semaphore */
loff_t **i_rddir_off;
+ struct inode vfs_inode;
};
-#define i_hpfs_dno u.hpfs_i.i_dno
-#define i_hpfs_parent_dir u.hpfs_i.i_parent_dir
-#define i_hpfs_n_secs u.hpfs_i.i_n_secs
-#define i_hpfs_file_sec u.hpfs_i.i_file_sec
-#define i_hpfs_disk_sec u.hpfs_i.i_disk_sec
-#define i_hpfs_dpos u.hpfs_i.i_dpos
-#define i_hpfs_dsubdno u.hpfs_i.i_dsubdno
-#define i_hpfs_ea_size u.hpfs_i.i_ea_size
-#define i_hpfs_conv u.hpfs_i.i_conv
-#define i_hpfs_ea_mode u.hpfs_i.i_ea_mode
-#define i_hpfs_ea_uid u.hpfs_i.i_ea_uid
-#define i_hpfs_ea_gid u.hpfs_i.i_ea_gid
-/*#define i_hpfs_lock u.hpfs_i.i_lock*/
-/*#define i_hpfs_queue u.hpfs_i.i_queue*/
-#define i_hpfs_sem u.hpfs_i.i_sem
-#define i_hpfs_rddir_off u.hpfs_i.i_rddir_off
-#define i_hpfs_dirty u.hpfs_i.i_dirty
-
#endif
diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index 97f3ecaf1f97..8096e640c416 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -278,6 +278,10 @@ struct net_device
struct net_device_stats* (*get_stats)(struct net_device *dev);
struct iw_statistics* (*get_wireless_stats)(struct net_device *dev);
+ /* List of functions to handle Wireless Extensions (instead of ioctl).
+ * See <net/iw_handler.h> for details. Jean II */
+ struct iw_handler_def * wireless_handlers;
+
/*
* This marks the end of the "visible" part of the structure. All
* fields hereafter are internal to the system, and may change at
diff --git a/include/linux/nfs_fs.h b/include/linux/nfs_fs.h
index efbbdba3a1bc..93aae0c5fb6a 100644
--- a/include/linux/nfs_fs.h
+++ b/include/linux/nfs_fs.h
@@ -63,67 +63,154 @@
*/
#define NFS_SUPER_MAGIC 0x6969
-static inline struct nfs_inode_info *NFS_I(struct inode *inode)
+/*
+ * These are the default flags for swap requests
+ */
+#define NFS_RPC_SWAPFLAGS (RPC_TASK_SWAPPER|RPC_TASK_ROOTCREDS)
+
+/* Flags in the RPC client structure */
+#define NFS_CLNTF_BUFSIZE 0x0001 /* readdir buffer in longwords */
+
+#define NFS_RW_SYNC 0x0001 /* O_SYNC handling */
+#define NFS_RW_SWAP 0x0002 /* This is a swap request */
+
+/*
+ * When flushing a cluster of dirty pages, there can be different
+ * strategies:
+ */
+#define FLUSH_AGING 0 /* only flush old buffers */
+#define FLUSH_SYNC 1 /* file being synced, or contention */
+#define FLUSH_WAIT 2 /* wait for completion */
+#define FLUSH_STABLE 4 /* commit to stable storage */
+
+#ifdef __KERNEL__
+
+/*
+ * nfs fs inode data in memory
+ */
+struct nfs_inode {
+ /*
+ * The 64bit 'inode number'
+ */
+ __u64 fsid;
+ __u64 fileid;
+
+ /*
+ * NFS file handle
+ */
+ struct nfs_fh fh;
+
+ /*
+ * Various flags
+ */
+ unsigned short flags;
+
+ /*
+ * read_cache_jiffies is when we started read-caching this inode,
+ * and read_cache_mtime is the mtime of the inode at that time.
+ * attrtimeo is for how long the cached information is assumed
+ * to be valid. A successful attribute revalidation doubles
+ * attrtimeo (up to acregmax/acdirmax), a failure resets it to
+ * acregmin/acdirmin.
+ *
+ * We need to revalidate the cached attrs for this inode if
+ *
+ * jiffies - read_cache_jiffies > attrtimeo
+ *
+ * and invalidate any cached data/flush out any dirty pages if
+ * we find that
+ *
+ * mtime != read_cache_mtime
+ */
+ unsigned long read_cache_jiffies;
+ __u64 read_cache_ctime;
+ __u64 read_cache_mtime;
+ __u64 read_cache_isize;
+ unsigned long attrtimeo;
+ unsigned long attrtimeo_timestamp;
+
+ /*
+ * This is the cookie verifier used for NFSv3 readdir
+ * operations
+ */
+ __u32 cookieverf[2];
+
+ /*
+ * This is the list of dirty unwritten pages.
+ */
+ struct list_head read;
+ struct list_head dirty;
+ struct list_head commit;
+ struct list_head writeback;
+
+ unsigned int nread,
+ ndirty,
+ ncommit,
+ npages;
+
+ /* Flush daemon info */
+ struct inode *hash_next,
+ *hash_prev;
+ unsigned long nextscan;
+
+ /* Credentials for shared mmap */
+ struct rpc_cred *mm_cred;
+
+ struct inode vfs_inode;
+};
+
+/*
+ * Legal inode flag values
+ */
+#define NFS_INO_STALE 0x0001 /* possible stale inode */
+#define NFS_INO_ADVISE_RDPLUS 0x0002 /* advise readdirplus */
+#define NFS_INO_REVALIDATING 0x0004 /* revalidating attrs */
+#define NFS_IS_SNAPSHOT 0x0010 /* a snapshot file */
+#define NFS_INO_FLUSH 0x0020 /* inode is due for flushing */
+#define NFS_INO_NEW 0x0040 /* hadn't been filled yet */
+
+static inline struct nfs_inode *NFS_I(struct inode *inode)
{
- return &inode->u.nfs_i;
+ return list_entry(inode, struct nfs_inode, vfs_inode);
}
-#define NFS_FH(inode) (&(inode)->u.nfs_i.fh)
+#define NFS_FH(inode) (&NFS_I(inode)->fh)
#define NFS_SERVER(inode) (&(inode)->i_sb->u.nfs_sb.s_server)
#define NFS_CLIENT(inode) (NFS_SERVER(inode)->client)
#define NFS_PROTO(inode) (NFS_SERVER(inode)->rpc_ops)
#define NFS_REQUESTLIST(inode) (NFS_SERVER(inode)->rw_requests)
#define NFS_ADDR(inode) (RPC_PEERADDR(NFS_CLIENT(inode)))
#define NFS_CONGESTED(inode) (RPC_CONGESTED(NFS_CLIENT(inode)))
-#define NFS_COOKIEVERF(inode) ((inode)->u.nfs_i.cookieverf)
-#define NFS_READTIME(inode) ((inode)->u.nfs_i.read_cache_jiffies)
-#define NFS_CACHE_CTIME(inode) ((inode)->u.nfs_i.read_cache_ctime)
-#define NFS_CACHE_MTIME(inode) ((inode)->u.nfs_i.read_cache_mtime)
-#define NFS_CACHE_ISIZE(inode) ((inode)->u.nfs_i.read_cache_isize)
-#define NFS_NEXTSCAN(inode) ((inode)->u.nfs_i.nextscan)
+#define NFS_COOKIEVERF(inode) (NFS_I(inode)->cookieverf)
+#define NFS_READTIME(inode) (NFS_I(inode)->read_cache_jiffies)
+#define NFS_CACHE_CTIME(inode) (NFS_I(inode)->read_cache_ctime)
+#define NFS_CACHE_MTIME(inode) (NFS_I(inode)->read_cache_mtime)
+#define NFS_CACHE_ISIZE(inode) (NFS_I(inode)->read_cache_isize)
+#define NFS_NEXTSCAN(inode) (NFS_I(inode)->nextscan)
#define NFS_CACHEINV(inode) \
do { \
NFS_READTIME(inode) = jiffies - NFS_MAXATTRTIMEO(inode) - 1; \
} while (0)
-#define NFS_ATTRTIMEO(inode) ((inode)->u.nfs_i.attrtimeo)
+#define NFS_ATTRTIMEO(inode) (NFS_I(inode)->attrtimeo)
#define NFS_MINATTRTIMEO(inode) \
(S_ISDIR(inode->i_mode)? NFS_SERVER(inode)->acdirmin \
: NFS_SERVER(inode)->acregmin)
#define NFS_MAXATTRTIMEO(inode) \
(S_ISDIR(inode->i_mode)? NFS_SERVER(inode)->acdirmax \
: NFS_SERVER(inode)->acregmax)
-#define NFS_ATTRTIMEO_UPDATE(inode) ((inode)->u.nfs_i.attrtimeo_timestamp)
+#define NFS_ATTRTIMEO_UPDATE(inode) (NFS_I(inode)->attrtimeo_timestamp)
-#define NFS_FLAGS(inode) ((inode)->u.nfs_i.flags)
+#define NFS_FLAGS(inode) (NFS_I(inode)->flags)
#define NFS_REVALIDATING(inode) (NFS_FLAGS(inode) & NFS_INO_REVALIDATING)
#define NFS_STALE(inode) (NFS_FLAGS(inode) & NFS_INO_STALE)
+#define NFS_NEW(inode) (NFS_FLAGS(inode) & NFS_INO_NEW)
-#define NFS_FILEID(inode) ((inode)->u.nfs_i.fileid)
-#define NFS_FSID(inode) ((inode)->u.nfs_i.fsid)
+#define NFS_FILEID(inode) (NFS_I(inode)->fileid)
+#define NFS_FSID(inode) (NFS_I(inode)->fsid)
/* Inode Flags */
#define NFS_USE_READDIRPLUS(inode) ((NFS_FLAGS(inode) & NFS_INO_ADVISE_RDPLUS) ? 1 : 0)
-/*
- * These are the default flags for swap requests
- */
-#define NFS_RPC_SWAPFLAGS (RPC_TASK_SWAPPER|RPC_TASK_ROOTCREDS)
-
-/* Flags in the RPC client structure */
-#define NFS_CLNTF_BUFSIZE 0x0001 /* readdir buffer in longwords */
-
-#define NFS_RW_SYNC 0x0001 /* O_SYNC handling */
-#define NFS_RW_SWAP 0x0002 /* This is a swap request */
-
-/*
- * When flushing a cluster of dirty pages, there can be different
- * strategies:
- */
-#define FLUSH_AGING 0 /* only flush old buffers */
-#define FLUSH_SYNC 1 /* file being synced, or contention */
-#define FLUSH_WAIT 2 /* wait for completion */
-#define FLUSH_STABLE 4 /* commit to stable storage */
-
static inline
loff_t page_offset(struct page *page)
{
@@ -136,7 +223,6 @@ unsigned long page_index(struct page *page)
return page->index;
}
-#ifdef __KERNEL__
/*
* linux/fs/nfs/inode.c
*/
@@ -220,13 +306,13 @@ extern int nfs_scan_lru_commit_timeout(struct nfs_server *, struct list_head *)
static inline int
nfs_have_read(struct inode *inode)
{
- return !list_empty(&inode->u.nfs_i.read);
+ return !list_empty(&NFS_I(inode)->read);
}
static inline int
nfs_have_writebacks(struct inode *inode)
{
- return !list_empty(&inode->u.nfs_i.writeback);
+ return !list_empty(&NFS_I(inode)->writeback);
}
static inline int
diff --git a/include/linux/nfs_fs_i.h b/include/linux/nfs_fs_i.h
index 7fc3bae2278b..5a4fa8d54801 100644
--- a/include/linux/nfs_fs_i.h
+++ b/include/linux/nfs_fs_i.h
@@ -6,87 +6,6 @@
#include <linux/nfs.h>
/*
- * nfs fs inode data in memory
- */
-struct nfs_inode_info {
- /*
- * The 64bit 'inode number'
- */
- __u64 fsid;
- __u64 fileid;
-
- /*
- * NFS file handle
- */
- struct nfs_fh fh;
-
- /*
- * Various flags
- */
- unsigned short flags;
-
- /*
- * read_cache_jiffies is when we started read-caching this inode,
- * and read_cache_mtime is the mtime of the inode at that time.
- * attrtimeo is for how long the cached information is assumed
- * to be valid. A successful attribute revalidation doubles
- * attrtimeo (up to acregmax/acdirmax), a failure resets it to
- * acregmin/acdirmin.
- *
- * We need to revalidate the cached attrs for this inode if
- *
- * jiffies - read_cache_jiffies > attrtimeo
- *
- * and invalidate any cached data/flush out any dirty pages if
- * we find that
- *
- * mtime != read_cache_mtime
- */
- unsigned long read_cache_jiffies;
- __u64 read_cache_ctime;
- __u64 read_cache_mtime;
- __u64 read_cache_isize;
- unsigned long attrtimeo;
- unsigned long attrtimeo_timestamp;
-
- /*
- * This is the cookie verifier used for NFSv3 readdir
- * operations
- */
- __u32 cookieverf[2];
-
- /*
- * This is the list of dirty unwritten pages.
- */
- struct list_head read;
- struct list_head dirty;
- struct list_head commit;
- struct list_head writeback;
-
- unsigned int nread,
- ndirty,
- ncommit,
- npages;
-
- /* Flush daemon info */
- struct inode *hash_next,
- *hash_prev;
- unsigned long nextscan;
-
- /* Credentials for shared mmap */
- struct rpc_cred *mm_cred;
-};
-
-/*
- * Legal inode flag values
- */
-#define NFS_INO_STALE 0x0001 /* possible stale inode */
-#define NFS_INO_ADVISE_RDPLUS 0x0002 /* advise readdirplus */
-#define NFS_INO_REVALIDATING 0x0004 /* revalidating attrs */
-#define NFS_IS_SNAPSHOT 0x0010 /* a snapshot file */
-#define NFS_INO_FLUSH 0x0020 /* inode is due for flushing */
-
-/*
* NFS lock info
*/
struct nfs_lock_info {
diff --git a/include/linux/qnx4_fs.h b/include/linux/qnx4_fs.h
index 55ba2f99d9a2..fc1912a3fd72 100644
--- a/include/linux/qnx4_fs.h
+++ b/include/linux/qnx4_fs.h
@@ -97,6 +97,12 @@ struct qnx4_super_block {
#define QNX4DEBUG(X) (void) 0
#endif
+struct qnx4_inode_info {
+ struct qnx4_inode_entry raw;
+ unsigned long mmu_private;
+ struct inode vfs_inode;
+};
+
extern struct dentry *qnx4_lookup(struct inode *dir, struct dentry *dentry);
extern unsigned long qnx4_count_free_blocks(struct super_block *sb);
extern unsigned long qnx4_block_map(struct inode *inode, long iblock);
@@ -120,6 +126,16 @@ extern int qnx4_sync_file(struct file *file, struct dentry *dentry, int);
extern int qnx4_sync_inode(struct inode *inode);
extern int qnx4_get_block(struct inode *inode, sector_t iblock, struct buffer_head *bh, int create);
+static inline struct qnx4_inode_info *qnx4_i(struct inode *inode)
+{
+ return list_entry(inode, struct qnx4_inode_info, vfs_inode);
+}
+
+static inline struct qnx4_inode_entry *qnx4_raw_inode(struct inode *inode)
+{
+ return &qnx4_i(inode)->raw;
+}
+
#endif /* __KERNEL__ */
#endif
diff --git a/include/linux/qnx4_fs_i.h b/include/linux/qnx4_fs_i.h
deleted file mode 100644
index b0fe8463e7e1..000000000000
--- a/include/linux/qnx4_fs_i.h
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Name : qnx4_fs_i.h
- * Author : Richard Frowijn
- * Function : qnx4 inode definitions
- * Version : 1.0.2
- * Last modified : 2000-01-06
- *
- * History : 23-03-1998 created
- *
- */
-#ifndef _QNX4_FS_I
-#define _QNX4_FS_I
-
-#include <linux/qnxtypes.h>
-
-/*
- * qnx4 fs inode entry
- */
-struct qnx4_inode_info {
- char i_reserved[16]; /* 16 */
- qnx4_off_t i_size; /* 4 */
- qnx4_xtnt_t i_first_xtnt; /* 8 */
- __u32 i_xblk; /* 4 */
- __s32 i_ftime; /* 4 */
- __s32 i_mtime; /* 4 */
- __s32 i_atime; /* 4 */
- __s32 i_ctime; /* 4 */
- qnx4_nxtnt_t i_num_xtnts; /* 2 */
- qnx4_mode_t i_mode; /* 2 */
- qnx4_muid_t i_uid; /* 2 */
- qnx4_mgid_t i_gid; /* 2 */
- qnx4_nlink_t i_nlink; /* 2 */
- __u8 i_zero[4]; /* 4 */
- qnx4_ftype_t i_type; /* 1 */
- __u8 i_status; /* 1 */
- unsigned long mmu_private;
-};
-
-#endif
diff --git a/include/linux/sched.h b/include/linux/sched.h
index 3797423a4fbe..b34544b8380f 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -141,6 +141,7 @@ typedef struct task_struct task_t;
extern void sched_init(void);
extern void init_idle(void);
+extern void idle_startup_done(void);
extern void show_state(void);
extern void cpu_init (void);
extern void trap_init(void);
@@ -148,6 +149,8 @@ extern void update_process_times(int user);
extern void update_one_process(struct task_struct *p, unsigned long user,
unsigned long system, int cpu);
extern void scheduler_tick(struct task_struct *p);
+extern void sched_task_migrated(struct task_struct *p);
+extern void smp_migrate_task(int cpu, task_t *task);
#define MAX_SCHEDULE_TIMEOUT LONG_MAX
extern signed long FASTCALL(schedule_timeout(signed long timeout));
diff --git a/include/linux/shmem_fs.h b/include/linux/shmem_fs.h
index 070eef7b5137..183b1e49dbe8 100644
--- a/include/linux/shmem_fs.h
+++ b/include/linux/shmem_fs.h
@@ -28,7 +28,7 @@ struct shmem_inode_info {
unsigned long swapped;
int locked; /* into memory */
struct list_head list;
- struct inode *inode;
+ struct inode vfs_inode;
};
struct shmem_sb_info {
@@ -39,6 +39,9 @@ struct shmem_sb_info {
spinlock_t stat_lock;
};
-#define SHMEM_I(inode) (&inode->u.shmem_i)
+static inline struct shmem_inode_info *SHMEM_I(struct inode *inode)
+{
+ return list_entry(inode, struct shmem_inode_info, vfs_inode);
+}
#endif
diff --git a/include/linux/ufs_fs.h b/include/linux/ufs_fs.h
index f776030c8b04..609d0dab2c6f 100644
--- a/include/linux/ufs_fs.h
+++ b/include/linux/ufs_fs.h
@@ -223,7 +223,7 @@
#define UFS_MAXNAMLEN 255
#define UFS_MAXMNTLEN 512
-#define UFS_MAXCSBUFS 31
+/* #define UFS_MAXCSBUFS 31 */
#define UFS_LINK_MAX 32000
/*
@@ -508,6 +508,218 @@ struct ufs_inode {
#define UFS_SF_APPEND 0x00040000 /* append-only */
#define UFS_SF_NOUNLINK 0x00100000 /* can't be removed or renamed */
+/*
+ * This structure is used for reading disk structures larger
+ * than the size of fragment.
+ */
+struct ufs_buffer_head {
+ unsigned fragment; /* first fragment */
+ unsigned count; /* number of fragments */
+ struct buffer_head * bh[UFS_MAXFRAG]; /* buffers */
+};
+
+struct ufs_cg_private_info {
+ struct ufs_cylinder_group ucg;
+ __u32 c_cgx; /* number of cylidner group */
+ __u16 c_ncyl; /* number of cyl's this cg */
+ __u16 c_niblk; /* number of inode blocks this cg */
+ __u32 c_ndblk; /* number of data blocks this cg */
+ __u32 c_rotor; /* position of last used block */
+ __u32 c_frotor; /* position of last used frag */
+ __u32 c_irotor; /* position of last used inode */
+ __u32 c_btotoff; /* (__u32) block totals per cylinder */
+ __u32 c_boff; /* (short) free block positions */
+ __u32 c_iusedoff; /* (char) used inode map */
+ __u32 c_freeoff; /* (u_char) free block map */
+ __u32 c_nextfreeoff; /* (u_char) next available space */
+ __u32 c_clustersumoff;/* (u_int32) counts of avail clusters */
+ __u32 c_clusteroff; /* (u_int8) free cluster map */
+ __u32 c_nclusterblks; /* number of clusters this cg */
+};
+
+struct ufs_sb_private_info {
+ struct ufs_buffer_head s_ubh; /* buffer containing super block */
+ __u32 s_sblkno; /* offset of super-blocks in filesys */
+ __u32 s_cblkno; /* offset of cg-block in filesys */
+ __u32 s_iblkno; /* offset of inode-blocks in filesys */
+ __u32 s_dblkno; /* offset of first data after cg */
+ __u32 s_cgoffset; /* cylinder group offset in cylinder */
+ __u32 s_cgmask; /* used to calc mod fs_ntrak */
+ __u32 s_size; /* number of blocks (fragments) in fs */
+ __u32 s_dsize; /* number of data blocks in fs */
+ __u32 s_ncg; /* number of cylinder groups */
+ __u32 s_bsize; /* size of basic blocks */
+ __u32 s_fsize; /* size of fragments */
+ __u32 s_fpb; /* fragments per block */
+ __u32 s_minfree; /* minimum percentage of free blocks */
+ __u32 s_bmask; /* `blkoff'' calc of blk offsets */
+ __u32 s_fmask; /* s_fsize mask */
+ __u32 s_bshift; /* `lblkno'' calc of logical blkno */
+ __u32 s_fshift; /* s_fsize shift */
+ __u32 s_fpbshift; /* fragments per block shift */
+ __u32 s_fsbtodb; /* fsbtodb and dbtofsb shift constant */
+ __u32 s_sbsize; /* actual size of super block */
+ __u32 s_csmask; /* csum block offset */
+ __u32 s_csshift; /* csum block number */
+ __u32 s_nindir; /* value of NINDIR */
+ __u32 s_inopb; /* value of INOPB */
+ __u32 s_nspf; /* value of NSPF */
+ __u32 s_npsect; /* # sectors/track including spares */
+ __u32 s_interleave; /* hardware sector interleave */
+ __u32 s_trackskew; /* sector 0 skew, per track */
+ __u32 s_csaddr; /* blk addr of cyl grp summary area */
+ __u32 s_cssize; /* size of cyl grp summary area */
+ __u32 s_cgsize; /* cylinder group size */
+ __u32 s_ntrak; /* tracks per cylinder */
+ __u32 s_nsect; /* sectors per track */
+ __u32 s_spc; /* sectors per cylinder */
+ __u32 s_ipg; /* inodes per group */
+ __u32 s_fpg; /* fragments per group */
+ __u32 s_cpc; /* cyl per cycle in postbl */
+ __s32 s_contigsumsize;/* size of cluster summary array, 44bsd */
+ __s64 s_qbmask; /* ~usb_bmask */
+ __s64 s_qfmask; /* ~usb_fmask */
+ __s32 s_postblformat; /* format of positional layout tables */
+ __s32 s_nrpos; /* number of rotational positions */
+ __s32 s_postbloff; /* (__s16) rotation block list head */
+ __s32 s_rotbloff; /* (__u8) blocks for each rotation */
+
+ __u32 s_fpbmask; /* fragments per block mask */
+ __u32 s_apb; /* address per block */
+ __u32 s_2apb; /* address per block^2 */
+ __u32 s_3apb; /* address per block^3 */
+ __u32 s_apbmask; /* address per block mask */
+ __u32 s_apbshift; /* address per block shift */
+ __u32 s_2apbshift; /* address per block shift * 2 */
+ __u32 s_3apbshift; /* address per block shift * 3 */
+ __u32 s_nspfshift; /* number of sector per fragment shift */
+ __u32 s_nspb; /* number of sector per block */
+ __u32 s_inopf; /* inodes per fragment */
+ __u32 s_sbbase; /* offset of NeXTstep superblock */
+ __u32 s_bpf; /* bits per fragment */
+ __u32 s_bpfshift; /* bits per fragment shift*/
+ __u32 s_bpfmask; /* bits per fragment mask */
+
+ __u32 s_maxsymlinklen;/* upper limit on fast symlinks' size */
+};
+
+/*
+ * Sizes of this structures are:
+ * ufs_super_block_first 512
+ * ufs_super_block_second 512
+ * ufs_super_block_third 356
+ */
+struct ufs_super_block_first {
+ __u32 fs_link;
+ __u32 fs_rlink;
+ __u32 fs_sblkno;
+ __u32 fs_cblkno;
+ __u32 fs_iblkno;
+ __u32 fs_dblkno;
+ __u32 fs_cgoffset;
+ __u32 fs_cgmask;
+ __u32 fs_time;
+ __u32 fs_size;
+ __u32 fs_dsize;
+ __u32 fs_ncg;
+ __u32 fs_bsize;
+ __u32 fs_fsize;
+ __u32 fs_frag;
+ __u32 fs_minfree;
+ __u32 fs_rotdelay;
+ __u32 fs_rps;
+ __u32 fs_bmask;
+ __u32 fs_fmask;
+ __u32 fs_bshift;
+ __u32 fs_fshift;
+ __u32 fs_maxcontig;
+ __u32 fs_maxbpg;
+ __u32 fs_fragshift;
+ __u32 fs_fsbtodb;
+ __u32 fs_sbsize;
+ __u32 fs_csmask;
+ __u32 fs_csshift;
+ __u32 fs_nindir;
+ __u32 fs_inopb;
+ __u32 fs_nspf;
+ __u32 fs_optim;
+ union {
+ struct {
+ __u32 fs_npsect;
+ } fs_sun;
+ struct {
+ __s32 fs_state;
+ } fs_sunx86;
+ } fs_u1;
+ __u32 fs_interleave;
+ __u32 fs_trackskew;
+ __u32 fs_id[2];
+ __u32 fs_csaddr;
+ __u32 fs_cssize;
+ __u32 fs_cgsize;
+ __u32 fs_ntrak;
+ __u32 fs_nsect;
+ __u32 fs_spc;
+ __u32 fs_ncyl;
+ __u32 fs_cpg;
+ __u32 fs_ipg;
+ __u32 fs_fpg;
+ struct ufs_csum fs_cstotal;
+ __s8 fs_fmod;
+ __s8 fs_clean;
+ __s8 fs_ronly;
+ __s8 fs_flags;
+ __s8 fs_fsmnt[UFS_MAXMNTLEN - 212];
+
+};
+
+struct ufs_super_block_second {
+ __s8 fs_fsmnt[212];
+ __u32 fs_cgrotor;
+ __u32 fs_csp[UFS_MAXCSBUFS];
+ __u32 fs_maxcluster;
+ __u32 fs_cpc;
+ __u16 fs_opostbl[82];
+};
+
+struct ufs_super_block_third {
+ __u16 fs_opostbl[46];
+ union {
+ struct {
+ __s32 fs_sparecon[53];/* reserved for future constants */
+ __s32 fs_reclaim;
+ __s32 fs_sparecon2[1];
+ __s32 fs_state; /* file system state time stamp */
+ __u32 fs_qbmask[2]; /* ~usb_bmask */
+ __u32 fs_qfmask[2]; /* ~usb_fmask */
+ } fs_sun;
+ struct {
+ __s32 fs_sparecon[53];/* reserved for future constants */
+ __s32 fs_reclaim;
+ __s32 fs_sparecon2[1];
+ __u32 fs_npsect; /* # sectors/track including spares */
+ __u32 fs_qbmask[2]; /* ~usb_bmask */
+ __u32 fs_qfmask[2]; /* ~usb_fmask */
+ } fs_sunx86;
+ struct {
+ __s32 fs_sparecon[50];/* reserved for future constants */
+ __s32 fs_contigsumsize;/* size of cluster summary array */
+ __s32 fs_maxsymlinklen;/* max length of an internal symlink */
+ __s32 fs_inodefmt; /* format of on-disk inodes */
+ __u32 fs_maxfilesize[2]; /* max representable file size */
+ __u32 fs_qbmask[2]; /* ~usb_bmask */
+ __u32 fs_qfmask[2]; /* ~usb_fmask */
+ __s32 fs_state; /* file system state time stamp */
+ } fs_44;
+ } fs_u2;
+ __s32 fs_postblformat;
+ __s32 fs_nrpos;
+ __s32 fs_postbloff;
+ __s32 fs_rotbloff;
+ __s32 fs_magic;
+ __u8 fs_space[1];
+};
+
#ifdef __KERNEL__
/* balloc.c */
@@ -539,7 +751,7 @@ extern struct address_space_operations ufs_aops;
/* ialloc.c */
extern void ufs_free_inode (struct inode *inode);
-extern struct inode * ufs_new_inode (const struct inode *, int);
+extern struct inode * ufs_new_inode (struct inode *, int);
/* inode.c */
extern int ufs_frag_map (struct inode *, int);
@@ -567,6 +779,13 @@ extern struct inode_operations ufs_fast_symlink_inode_operations;
/* truncate.c */
extern void ufs_truncate (struct inode *);
+#include <linux/ufs_fs_i.h>
+
+static inline struct ufs_inode_info *UFS_I(struct inode *inode)
+{
+ return list_entry(inode, struct ufs_inode_info, vfs_inode);
+}
+
#endif /* __KERNEL__ */
#endif /* __LINUX_UFS_FS_H */
diff --git a/include/linux/ufs_fs_i.h b/include/linux/ufs_fs_i.h
index 5f0287ab0139..1b7586441822 100644
--- a/include/linux/ufs_fs_i.h
+++ b/include/linux/ufs_fs_i.h
@@ -26,6 +26,7 @@ struct ufs_inode_info {
__u32 i_oeftflag;
__u16 i_osync;
__u32 i_lastfrag;
+ struct inode vfs_inode;
};
#endif /* _LINUX_UFS_FS_I_H */
diff --git a/include/linux/ufs_fs_sb.h b/include/linux/ufs_fs_sb.h
index 41b6ccc1eebe..c1be4c226486 100644
--- a/include/linux/ufs_fs_sb.h
+++ b/include/linux/ufs_fs_sb.h
@@ -14,107 +14,15 @@
#ifndef __LINUX_UFS_FS_SB_H
#define __LINUX_UFS_FS_SB_H
-#include <linux/ufs_fs.h>
-
-/*
- * This structure is used for reading disk structures larger
- * than the size of fragment.
- */
-struct ufs_buffer_head {
- unsigned fragment; /* first fragment */
- unsigned count; /* number of fragments */
- struct buffer_head * bh[UFS_MAXFRAG]; /* buffers */
-};
-
-struct ufs_cg_private_info {
- struct ufs_cylinder_group ucg;
- __u32 c_cgx; /* number of cylidner group */
- __u16 c_ncyl; /* number of cyl's this cg */
- __u16 c_niblk; /* number of inode blocks this cg */
- __u32 c_ndblk; /* number of data blocks this cg */
- __u32 c_rotor; /* position of last used block */
- __u32 c_frotor; /* position of last used frag */
- __u32 c_irotor; /* position of last used inode */
- __u32 c_btotoff; /* (__u32) block totals per cylinder */
- __u32 c_boff; /* (short) free block positions */
- __u32 c_iusedoff; /* (char) used inode map */
- __u32 c_freeoff; /* (u_char) free block map */
- __u32 c_nextfreeoff; /* (u_char) next available space */
- __u32 c_clustersumoff;/* (u_int32) counts of avail clusters */
- __u32 c_clusteroff; /* (u_int8) free cluster map */
- __u32 c_nclusterblks; /* number of clusters this cg */
-};
-
-struct ufs_sb_private_info {
- struct ufs_buffer_head s_ubh; /* buffer containing super block */
- __u32 s_sblkno; /* offset of super-blocks in filesys */
- __u32 s_cblkno; /* offset of cg-block in filesys */
- __u32 s_iblkno; /* offset of inode-blocks in filesys */
- __u32 s_dblkno; /* offset of first data after cg */
- __u32 s_cgoffset; /* cylinder group offset in cylinder */
- __u32 s_cgmask; /* used to calc mod fs_ntrak */
- __u32 s_size; /* number of blocks (fragments) in fs */
- __u32 s_dsize; /* number of data blocks in fs */
- __u32 s_ncg; /* number of cylinder groups */
- __u32 s_bsize; /* size of basic blocks */
- __u32 s_fsize; /* size of fragments */
- __u32 s_fpb; /* fragments per block */
- __u32 s_minfree; /* minimum percentage of free blocks */
- __u32 s_bmask; /* `blkoff'' calc of blk offsets */
- __u32 s_fmask; /* s_fsize mask */
- __u32 s_bshift; /* `lblkno'' calc of logical blkno */
- __u32 s_fshift; /* s_fsize shift */
- __u32 s_fpbshift; /* fragments per block shift */
- __u32 s_fsbtodb; /* fsbtodb and dbtofsb shift constant */
- __u32 s_sbsize; /* actual size of super block */
- __u32 s_csmask; /* csum block offset */
- __u32 s_csshift; /* csum block number */
- __u32 s_nindir; /* value of NINDIR */
- __u32 s_inopb; /* value of INOPB */
- __u32 s_nspf; /* value of NSPF */
- __u32 s_npsect; /* # sectors/track including spares */
- __u32 s_interleave; /* hardware sector interleave */
- __u32 s_trackskew; /* sector 0 skew, per track */
- __u32 s_csaddr; /* blk addr of cyl grp summary area */
- __u32 s_cssize; /* size of cyl grp summary area */
- __u32 s_cgsize; /* cylinder group size */
- __u32 s_ntrak; /* tracks per cylinder */
- __u32 s_nsect; /* sectors per track */
- __u32 s_spc; /* sectors per cylinder */
- __u32 s_ipg; /* inodes per group */
- __u32 s_fpg; /* fragments per group */
- __u32 s_cpc; /* cyl per cycle in postbl */
- __s32 s_contigsumsize;/* size of cluster summary array, 44bsd */
- __s64 s_qbmask; /* ~usb_bmask */
- __s64 s_qfmask; /* ~usb_fmask */
- __s32 s_postblformat; /* format of positional layout tables */
- __s32 s_nrpos; /* number of rotational positions */
- __s32 s_postbloff; /* (__s16) rotation block list head */
- __s32 s_rotbloff; /* (__u8) blocks for each rotation */
-
- __u32 s_fpbmask; /* fragments per block mask */
- __u32 s_apb; /* address per block */
- __u32 s_2apb; /* address per block^2 */
- __u32 s_3apb; /* address per block^3 */
- __u32 s_apbmask; /* address per block mask */
- __u32 s_apbshift; /* address per block shift */
- __u32 s_2apbshift; /* address per block shift * 2 */
- __u32 s_3apbshift; /* address per block shift * 3 */
- __u32 s_nspfshift; /* number of sector per fragment shift */
- __u32 s_nspb; /* number of sector per block */
- __u32 s_inopf; /* inodes per fragment */
- __u32 s_sbbase; /* offset of NeXTstep superblock */
- __u32 s_bpf; /* bits per fragment */
- __u32 s_bpfshift; /* bits per fragment shift*/
- __u32 s_bpfmask; /* bits per fragment mask */
-
- __u32 s_maxsymlinklen;/* upper limit on fast symlinks' size */
-};
-
#define UFS_MAX_GROUP_LOADED 8
#define UFS_CGNO_EMPTY ((unsigned)-1)
+struct ufs_sb_private_info;
+struct ufs_cg_private_info;
+struct ufs_csum;
+#define UFS_MAXCSBUFS 31
+
struct ufs_sb_info {
struct ufs_sb_private_info * s_uspi;
struct ufs_csum * s_csp[UFS_MAXCSBUFS];
@@ -127,121 +35,4 @@ struct ufs_sb_info {
unsigned s_mount_opt;
};
-/*
- * Sizes of this structures are:
- * ufs_super_block_first 512
- * ufs_super_block_second 512
- * ufs_super_block_third 356
- */
-struct ufs_super_block_first {
- __u32 fs_link;
- __u32 fs_rlink;
- __u32 fs_sblkno;
- __u32 fs_cblkno;
- __u32 fs_iblkno;
- __u32 fs_dblkno;
- __u32 fs_cgoffset;
- __u32 fs_cgmask;
- __u32 fs_time;
- __u32 fs_size;
- __u32 fs_dsize;
- __u32 fs_ncg;
- __u32 fs_bsize;
- __u32 fs_fsize;
- __u32 fs_frag;
- __u32 fs_minfree;
- __u32 fs_rotdelay;
- __u32 fs_rps;
- __u32 fs_bmask;
- __u32 fs_fmask;
- __u32 fs_bshift;
- __u32 fs_fshift;
- __u32 fs_maxcontig;
- __u32 fs_maxbpg;
- __u32 fs_fragshift;
- __u32 fs_fsbtodb;
- __u32 fs_sbsize;
- __u32 fs_csmask;
- __u32 fs_csshift;
- __u32 fs_nindir;
- __u32 fs_inopb;
- __u32 fs_nspf;
- __u32 fs_optim;
- union {
- struct {
- __u32 fs_npsect;
- } fs_sun;
- struct {
- __s32 fs_state;
- } fs_sunx86;
- } fs_u1;
- __u32 fs_interleave;
- __u32 fs_trackskew;
- __u32 fs_id[2];
- __u32 fs_csaddr;
- __u32 fs_cssize;
- __u32 fs_cgsize;
- __u32 fs_ntrak;
- __u32 fs_nsect;
- __u32 fs_spc;
- __u32 fs_ncyl;
- __u32 fs_cpg;
- __u32 fs_ipg;
- __u32 fs_fpg;
- struct ufs_csum fs_cstotal;
- __s8 fs_fmod;
- __s8 fs_clean;
- __s8 fs_ronly;
- __s8 fs_flags;
- __s8 fs_fsmnt[UFS_MAXMNTLEN - 212];
-
-};
-
-struct ufs_super_block_second {
- __s8 fs_fsmnt[212];
- __u32 fs_cgrotor;
- __u32 fs_csp[UFS_MAXCSBUFS];
- __u32 fs_maxcluster;
- __u32 fs_cpc;
- __u16 fs_opostbl[82];
-};
-
-struct ufs_super_block_third {
- __u16 fs_opostbl[46];
- union {
- struct {
- __s32 fs_sparecon[53];/* reserved for future constants */
- __s32 fs_reclaim;
- __s32 fs_sparecon2[1];
- __s32 fs_state; /* file system state time stamp */
- __u32 fs_qbmask[2]; /* ~usb_bmask */
- __u32 fs_qfmask[2]; /* ~usb_fmask */
- } fs_sun;
- struct {
- __s32 fs_sparecon[53];/* reserved for future constants */
- __s32 fs_reclaim;
- __s32 fs_sparecon2[1];
- __u32 fs_npsect; /* # sectors/track including spares */
- __u32 fs_qbmask[2]; /* ~usb_bmask */
- __u32 fs_qfmask[2]; /* ~usb_fmask */
- } fs_sunx86;
- struct {
- __s32 fs_sparecon[50];/* reserved for future constants */
- __s32 fs_contigsumsize;/* size of cluster summary array */
- __s32 fs_maxsymlinklen;/* max length of an internal symlink */
- __s32 fs_inodefmt; /* format of on-disk inodes */
- __u32 fs_maxfilesize[2]; /* max representable file size */
- __u32 fs_qbmask[2]; /* ~usb_bmask */
- __u32 fs_qfmask[2]; /* ~usb_fmask */
- __s32 fs_state; /* file system state time stamp */
- } fs_44;
- } fs_u2;
- __s32 fs_postblformat;
- __s32 fs_nrpos;
- __s32 fs_postbloff;
- __s32 fs_rotbloff;
- __s32 fs_magic;
- __u8 fs_space[1];
-};
-
-#endif /* __LINUX_UFS_FS_SB_H */
+#endif
diff --git a/include/linux/umsdos_fs.p b/include/linux/umsdos_fs.p
index 2752cb004c0f..99e6eefa8229 100644
--- a/include/linux/umsdos_fs.p
+++ b/include/linux/umsdos_fs.p
@@ -93,3 +93,8 @@ int UMSDOS_rename (struct inode *old_dir,
/* rdir.c 22/03/95 03.31.42 */
struct dentry *umsdos_rlookup_x (struct inode *dir, struct dentry *dentry, int nopseudo);
struct dentry *UMSDOS_rlookup (struct inode *dir, struct dentry *dentry);
+
+static inline struct umsdos_inode_info *UMSDOS_I(struct inode *inode)
+{
+ return &inode->u.umsdos_i;
+}
diff --git a/include/linux/usb.h b/include/linux/usb.h
index d53844b91db3..5309034e511e 100644
--- a/include/linux/usb.h
+++ b/include/linux/usb.h
@@ -576,13 +576,12 @@ extern void usb_deregister(struct usb_driver *);
/* ... less overhead for QUEUE_BULK */
#define USB_TIMEOUT_KILLED 0x1000 /* only set by HCD! */
-typedef struct
-{
+struct usb_iso_packet_descriptor {
unsigned int offset;
unsigned int length; /* expected length */
unsigned int actual_length;
unsigned int status;
-} iso_packet_descriptor_t;
+};
struct urb;
@@ -741,11 +740,9 @@ struct urb
int timeout; /* (in) timeout, in jiffies */
void *context; /* (in) context for completion */
usb_complete_t complete; /* (in) completion routine */
- iso_packet_descriptor_t iso_frame_desc[0]; /* (in) ISO ONLY */
+ struct usb_iso_packet_descriptor iso_frame_desc[0]; /* (in) ISO ONLY */
};
-typedef struct urb urb_t;
-
/**
* usb_fill_control_urb - initializes a control urb
* @urb: pointer to the urb to initialize.
diff --git a/include/linux/usbdev_fs_i.h b/include/linux/usbdev_fs_i.h
deleted file mode 100644
index 13bfad5406bd..000000000000
--- a/include/linux/usbdev_fs_i.h
+++ /dev/null
@@ -1,11 +0,0 @@
-struct usb_device;
-struct usb_bus;
-
-struct usbdev_inode_info {
- struct list_head dlist;
- struct list_head slist;
- union {
- struct usb_device *dev;
- struct usb_bus *bus;
- } p;
-};
diff --git a/include/linux/usbdev_fs_sb.h b/include/linux/usbdev_fs_sb.h
deleted file mode 100644
index 6027b1a20921..000000000000
--- a/include/linux/usbdev_fs_sb.h
+++ /dev/null
@@ -1,13 +0,0 @@
-struct usbdev_sb_info {
- struct list_head slist;
- struct list_head ilist;
- uid_t devuid;
- gid_t devgid;
- umode_t devmode;
- uid_t busuid;
- gid_t busgid;
- umode_t busmode;
- uid_t listuid;
- gid_t listgid;
- umode_t listmode;
-};
diff --git a/include/linux/wireless.h b/include/linux/wireless.h
index 3fe8709b469d..fa3c64f78b32 100644
--- a/include/linux/wireless.h
+++ b/include/linux/wireless.h
@@ -1,9 +1,10 @@
/*
* This file define a set of standard wireless extensions
*
- * Version : 12 5.10.01
+ * Version : 13 6.12.01
*
* Authors : Jean Tourrilhes - HPL - <jt@hpl.hp.com>
+ * Copyright (c) 1997-2001 Jean Tourrilhes, All Rights Reserved.
*/
#ifndef _LINUX_WIRELESS_H
@@ -11,6 +12,8 @@
/************************** DOCUMENTATION **************************/
/*
+ * Initial APIs (1996 -> onward) :
+ * -----------------------------
* Basically, the wireless extensions are for now a set of standard ioctl
* call + /proc/net/wireless
*
@@ -27,16 +30,27 @@
* We have the list of command plus a structure descibing the
* data exchanged...
* Note that to add these ioctl, I was obliged to modify :
- * net/core/dev.c (two place + add include)
- * net/ipv4/af_inet.c (one place + add include)
+ * # net/core/dev.c (two place + add include)
+ * # net/ipv4/af_inet.c (one place + add include)
*
* /proc/net/wireless is a copy of /proc/net/dev.
* We have a structure for data passed from the driver to /proc/net/wireless
* Too add this, I've modified :
- * net/core/dev.c (two other places)
- * include/linux/netdevice.h (one place)
- * include/linux/proc_fs.h (one place)
+ * # net/core/dev.c (two other places)
+ * # include/linux/netdevice.h (one place)
+ * # include/linux/proc_fs.h (one place)
*
+ * New driver API (2001 -> onward) :
+ * -------------------------------
+ * This file is only concerned with the user space API and common definitions.
+ * The new driver API is defined and documented in :
+ * # include/net/iw_handler.h
+ *
+ * Note as well that /proc/net/wireless implementation has now moved in :
+ * # include/linux/wireless.c
+ *
+ * Other comments :
+ * --------------
* Do not add here things that are redundant with other mechanisms
* (drivers init, ifconfig, /proc/net/dev, ...) and with are not
* wireless specific.
@@ -54,16 +68,14 @@
#include <linux/socket.h> /* for "struct sockaddr" et al */
#include <linux/if.h> /* for IFNAMSIZ and co... */
-/**************************** CONSTANTS ****************************/
-
-/* --------------------------- VERSION --------------------------- */
+/***************************** VERSION *****************************/
/*
* This constant is used to know the availability of the wireless
* extensions and to know which version of wireless extensions it is
* (there is some stuff that will be added in the future...)
* I just plan to increment with each new version.
*/
-#define WIRELESS_EXT 12
+#define WIRELESS_EXT 13
/*
* Changes :
@@ -123,12 +135,20 @@
* - Add DEV PRIVATE IOCTL to avoid collisions in SIOCDEVPRIVATE space
* - Add new statistics (frag, retry, beacon)
* - Add average quality (for user space calibration)
+ *
+ * V12 to V13
+ * ----------
+ * - Document creation of new driver API.
+ * - Extract union iwreq_data from struct iwreq (for new driver API).
+ * - Rename SIOCSIWNAME as SIOCSIWCOMMIT
*/
+/**************************** CONSTANTS ****************************/
+
/* -------------------------- IOCTL LIST -------------------------- */
/* Basic operations */
-#define SIOCSIWNAME 0x8B00 /* Unused */
+#define SIOCSIWCOMMIT 0x8B00 /* Commit pending changes to driver */
#define SIOCGIWNAME 0x8B01 /* get name == wireless protocol */
#define SIOCSIWNWID 0x8B02 /* set network id (the cell) */
#define SIOCGIWNWID 0x8B03 /* get network id */
@@ -414,13 +434,49 @@ struct iw_statistics
/* ------------------------ IOCTL REQUEST ------------------------ */
/*
+ * This structure defines the payload of an ioctl, and is used
+ * below.
+ *
+ * Note that this structure should fit on the memory footprint
+ * of iwreq (which is the same as ifreq), which mean a max size of
+ * 16 octets = 128 bits. Warning, pointers might be 64 bits wide...
+ * You should check this when increasing the structures defined
+ * above in this file...
+ */
+union iwreq_data
+{
+ /* Config - generic */
+ char name[IFNAMSIZ];
+ /* Name : used to verify the presence of wireless extensions.
+ * Name of the protocol/provider... */
+
+ struct iw_point essid; /* Extended network name */
+ struct iw_param nwid; /* network id (or domain - the cell) */
+ struct iw_freq freq; /* frequency or channel :
+ * 0-1000 = channel
+ * > 1000 = frequency in Hz */
+
+ struct iw_param sens; /* signal level threshold */
+ struct iw_param bitrate; /* default bit rate */
+ struct iw_param txpower; /* default transmit power */
+ struct iw_param rts; /* RTS threshold threshold */
+ struct iw_param frag; /* Fragmentation threshold */
+ __u32 mode; /* Operation mode */
+ struct iw_param retry; /* Retry limits & lifetime */
+
+ struct iw_point encoding; /* Encoding stuff : tokens */
+ struct iw_param power; /* PM duration/timeout */
+
+ struct sockaddr ap_addr; /* Access point address */
+
+ struct iw_point data; /* Other large parameters */
+};
+
+/*
* The structure to exchange data for ioctl.
* This structure is the same as 'struct ifreq', but (re)defined for
* convenience...
- *
- * Note that it should fit on the same memory footprint !
- * You should check this when increasing the above structures (16 octets)
- * 16 octets = 128 bits. Warning, pointers might be 64 bits wide...
+ * Do I need to remind you about structure size (32 octets) ?
*/
struct iwreq
{
@@ -429,35 +485,8 @@ struct iwreq
char ifrn_name[IFNAMSIZ]; /* if name, e.g. "eth0" */
} ifr_ifrn;
- /* Data part */
- union
- {
- /* Config - generic */
- char name[IFNAMSIZ];
- /* Name : used to verify the presence of wireless extensions.
- * Name of the protocol/provider... */
-
- struct iw_point essid; /* Extended network name */
- struct iw_param nwid; /* network id (or domain - the cell) */
- struct iw_freq freq; /* frequency or channel :
- * 0-1000 = channel
- * > 1000 = frequency in Hz */
-
- struct iw_param sens; /* signal level threshold */
- struct iw_param bitrate; /* default bit rate */
- struct iw_param txpower; /* default transmit power */
- struct iw_param rts; /* RTS threshold threshold */
- struct iw_param frag; /* Fragmentation threshold */
- __u32 mode; /* Operation mode */
- struct iw_param retry; /* Retry limits & lifetime */
-
- struct iw_point encoding; /* Encoding stuff : tokens */
- struct iw_param power; /* PM duration/timeout */
-
- struct sockaddr ap_addr; /* Access point address */
-
- struct iw_point data; /* Other large parameters */
- } u;
+ /* Data part (defined just above) */
+ union iwreq_data u;
};
/* -------------------------- IOCTL DATA -------------------------- */
diff --git a/include/net/iw_handler.h b/include/net/iw_handler.h
new file mode 100644
index 000000000000..7151337eebcf
--- /dev/null
+++ b/include/net/iw_handler.h
@@ -0,0 +1,374 @@
+/*
+ * This file define the new driver API for Wireless Extensions
+ *
+ * Version : 2 6.12.01
+ *
+ * Authors : Jean Tourrilhes - HPL - <jt@hpl.hp.com>
+ * Copyright (c) 2001 Jean Tourrilhes, All Rights Reserved.
+ */
+
+#ifndef _IW_HANDLER_H
+#define _IW_HANDLER_H
+
+/************************** DOCUMENTATION **************************/
+/*
+ * Initial driver API (1996 -> onward) :
+ * -----------------------------------
+ * The initial API just sends the IOCTL request received from user space
+ * to the driver (via the driver ioctl handler). The driver has to
+ * handle all the rest...
+ *
+ * The initial API also defines a specific handler in struct net_device
+ * to handle wireless statistics.
+ *
+ * The initial APIs served us well and has proven a reasonably good design.
+ * However, there is a few shortcommings :
+ * o No events, everything is a request to the driver.
+ * o Large ioctl function in driver with gigantic switch statement
+ * (i.e. spaghetti code).
+ * o Driver has to mess up with copy_to/from_user, and in many cases
+ * does it unproperly. Common mistakes are :
+ * * buffer overflows (no checks or off by one checks)
+ * * call copy_to/from_user with irq disabled
+ * o The user space interface is tied to ioctl because of the use
+ * copy_to/from_user.
+ *
+ * New driver API (2001 -> onward) :
+ * -------------------------------
+ * The new driver API is just a bunch of standard functions (handlers),
+ * each handling a specific Wireless Extension. The driver just export
+ * the list of handler it supports, and those will be called apropriately.
+ *
+ * I tried to keep the main advantage of the previous API (simplicity,
+ * efficiency and light weight), and also I provide a good dose of backward
+ * compatibility (most structures are the same, driver can use both API
+ * simultaneously, ...).
+ * Hopefully, I've also addressed the shortcomming of the initial API.
+ *
+ * The advantage of the new API are :
+ * o Handling of Extensions in driver broken in small contained functions
+ * o Tighter checks of ioctl before calling the driver
+ * o Flexible commit strategy (at least, the start of it)
+ * o Backward compatibility (can be mixed with old API)
+ * o Driver doesn't have to worry about memory and user-space issues
+ * The last point is important for the following reasons :
+ * o You are now able to call the new driver API from any API you
+ * want (including from within other parts of the kernel).
+ * o Common mistakes are avoided (buffer overflow, user space copy
+ * with irq disabled and so on).
+ *
+ * The Drawback of the new API are :
+ * o bloat (especially kernel)
+ * o need to migrate existing drivers to new API
+ * My initial testing shows that the new API adds around 3kB to the kernel
+ * and save between 0 and 5kB from a typical driver.
+ * Also, as all structures and data types are unchanged, the migration is
+ * quite straightforward (but tedious).
+ *
+ * ---
+ *
+ * The new driver API is defined below in this file. User space should
+ * not be aware of what's happening down there...
+ *
+ * A new kernel wrapper is in charge of validating the IOCTLs and calling
+ * the appropriate driver handler. This is implemented in :
+ * # net/core/wireless.c
+ *
+ * The driver export the list of handlers in :
+ * # include/linux/netdevice.h (one place)
+ *
+ * The new driver API is available for WIRELESS_EXT >= 13.
+ * Good luck with migration to the new API ;-)
+ */
+
+/* ---------------------- THE IMPLEMENTATION ---------------------- */
+/*
+ * Some of the choice I've made are pretty controversials. Defining an
+ * API is very much weighting compromises. This goes into some of the
+ * details and the thinking behind the implementation.
+ *
+ * Implementation goals :
+ * --------------------
+ * The implementation goals were as follow :
+ * o Obvious : you should not need a PhD to understand what's happening,
+ * the benefit is easier maintainance.
+ * o Flexible : it should accomodate a wide variety of driver
+ * implementations and be as flexible as the old API.
+ * o Lean : it should be efficient memory wise to minimise the impact
+ * on kernel footprint.
+ * o Transparent to user space : the large number of user space
+ * applications that use Wireless Extensions should not need
+ * any modifications.
+ *
+ * Array of functions versus Struct of functions
+ * ---------------------------------------------
+ * 1) Having an array of functions allow the kernel code to access the
+ * handler in a single lookup, which is much more efficient (think hash
+ * table here).
+ * 2) The only drawback is that driver writer may put their handler in
+ * the wrong slot. This is trivial to test (I set the frequency, the
+ * bitrate changes). Once the handler is in the proper slot, it will be
+ * there forever, because the array is only extended at the end.
+ * 3) Backward/forward compatibility : adding new handler just require
+ * extending the array, so you can put newer driver in older kernel
+ * without having to patch the kernel code (and vice versa).
+ *
+ * All handler are of the same generic type
+ * ----------------------------------------
+ * That's a feature !!!
+ * 1) Having a generic handler allow to have generic code, which is more
+ * efficient. If each of the handler was individually typed I would need
+ * to add a big switch in the kernel (== more bloat). This solution is
+ * more scalable, adding new Wireless Extensions doesn't add new code.
+ * 2) You can use the same handler in different slots of the array. For
+ * hardware, it may be more efficient or logical to handle multiple
+ * Wireless Extensions with a single function, and the API allow you to
+ * do that. (An example would be a single record on the card to control
+ * both bitrate and frequency, the handler would read the old record,
+ * modify it according to info->cmd and rewrite it).
+ *
+ * Functions prototype uses union iwreq_data
+ * -----------------------------------------
+ * Some would have prefered functions defined this way :
+ * static int mydriver_ioctl_setrate(struct net_device *dev,
+ * long rate, int auto)
+ * 1) The kernel code doesn't "validate" the content of iwreq_data, and
+ * can't do it (different hardware may have different notion of what a
+ * valid frequency is), so we don't pretend that we do it.
+ * 2) The above form is not extendable. If I want to add a flag (for
+ * example to distinguish setting max rate and basic rate), I would
+ * break the prototype. Using iwreq_data is more flexible.
+ * 3) Also, the above form is not generic (see above).
+ * 4) I don't expect driver developper using the wrong field of the
+ * union (Doh !), so static typechecking doesn't add much value.
+ * 5) Lastly, you can skip the union by doing :
+ * static int mydriver_ioctl_setrate(struct net_device *dev,
+ * struct iw_request_info *info,
+ * struct iw_param *rrq,
+ * char *extra)
+ * And then adding the handler in the array like this :
+ * (iw_handler) mydriver_ioctl_setrate, // SIOCSIWRATE
+ *
+ * Using functions and not a registry
+ * ----------------------------------
+ * Another implementation option would have been for every instance to
+ * define a registry (a struct containing all the Wireless Extensions)
+ * and only have a function to commit the registry to the hardware.
+ * 1) This approach can be emulated by the current code, but not
+ * vice versa.
+ * 2) Some drivers don't keep any configuration in the driver, for them
+ * adding such a registry would be a significant bloat.
+ * 3) The code to translate from Wireless Extension to native format is
+ * needed anyway, so it would not reduce significantely the amount of code.
+ * 4) The current approach only selectively translate Wireless Extensions
+ * to native format and only selectively set, whereas the registry approach
+ * would require to translate all WE and set all parameters for any single
+ * change.
+ * 5) For many Wireless Extensions, the GET operation return the current
+ * dynamic value, not the value that was set.
+ *
+ * This header is <net/iw_handler.h>
+ * ---------------------------------
+ * 1) This header is kernel space only and should not be exported to
+ * user space. Headers in "include/linux/" are exported, headers in
+ * "include/net/" are not.
+ *
+ * Mixed 32/64 bit issues
+ * ----------------------
+ * The Wireless Extensions are designed to be 64 bit clean, by using only
+ * datatypes with explicit storage size.
+ * There are some issues related to kernel and user space using different
+ * memory model, and in particular 64bit kernel with 32bit user space.
+ * The problem is related to struct iw_point, that contains a pointer
+ * that *may* need to be translated.
+ * This is quite messy. The new API doesn't solve this problem (it can't),
+ * but is a step in the right direction :
+ * 1) Meta data about each ioctl is easily available, so we know what type
+ * of translation is needed.
+ * 2) The move of data between kernel and user space is only done in a single
+ * place in the kernel, so adding specific hooks in there is possible.
+ * 3) In the long term, it allows to move away from using ioctl as the
+ * user space API.
+ *
+ * So many comments and so few code
+ * --------------------------------
+ * That's a feature. Comments won't bloat the resulting kernel binary.
+ */
+
+/***************************** INCLUDES *****************************/
+
+#include <linux/wireless.h> /* IOCTL user space API */
+
+/***************************** VERSION *****************************/
+/*
+ * This constant is used to know which version of the driver API is
+ * available. Hopefully, this will be pretty stable and no changes
+ * will be needed...
+ * I just plan to increment with each new version.
+ */
+#define IW_HANDLER_VERSION 2
+
+/**************************** CONSTANTS ****************************/
+
+/* Special error message for the driver to indicate that we
+ * should do a commit after return from the iw_handler */
+#define EIWCOMMIT EINPROGRESS
+
+/* Flags available in struct iw_request_info */
+#define IW_REQUEST_FLAG_NONE 0x0000 /* No flag so far */
+
+/* Type of headers we know about (basically union iwreq_data) */
+#define IW_HEADER_TYPE_NULL 0 /* Not available */
+#define IW_HEADER_TYPE_CHAR 2 /* char [IFNAMSIZ] */
+#define IW_HEADER_TYPE_UINT 4 /* __u32 */
+#define IW_HEADER_TYPE_FREQ 5 /* struct iw_freq */
+#define IW_HEADER_TYPE_POINT 6 /* struct iw_point */
+#define IW_HEADER_TYPE_PARAM 7 /* struct iw_param */
+#define IW_HEADER_TYPE_ADDR 8 /* struct sockaddr */
+
+/* Handling flags */
+/* Most are not implemented. I just use them as a reminder of some
+ * cool features we might need one day ;-) */
+#define IW_DESCR_FLAG_NONE 0x0000 /* Obvious */
+/* Wrapper level flags */
+#define IW_DESCR_FLAG_DUMP 0x0001 /* Not part of the dump command */
+#define IW_DESCR_FLAG_EVENT 0x0002 /* Generate an event on SET */
+#define IW_DESCR_FLAG_RESTRICT 0x0004 /* GET request is ROOT only */
+/* Driver level flags */
+#define IW_DESCR_FLAG_WAIT 0x0100 /* Wait for driver event */
+
+/****************************** TYPES ******************************/
+
+/* ----------------------- WIRELESS HANDLER ----------------------- */
+/*
+ * A wireless handler is just a standard function, that looks like the
+ * ioctl handler.
+ * We also define there how a handler list look like... As the Wireless
+ * Extension space is quite dense, we use a simple array, which is faster
+ * (that's the perfect hash table ;-).
+ */
+
+/*
+ * Meta data about the request passed to the iw_handler.
+ * Most handlers can safely ignore what's in there.
+ * The 'cmd' field might come handy if you want to use the same handler
+ * for multiple command...
+ * This struct is also my long term insurance. I can add new fields here
+ * without breaking the prototype of iw_handler...
+ */
+struct iw_request_info
+{
+ __u16 cmd; /* Wireless Extension command */
+ __u16 flags; /* More to come ;-) */
+};
+
+/*
+ * This is how a function handling a Wireless Extension should look
+ * like (both get and set, standard and private).
+ */
+typedef int (*iw_handler)(struct net_device *dev, struct iw_request_info *info,
+ union iwreq_data *wrqu, char *extra);
+
+/*
+ * This define all the handler that the driver export.
+ * As you need only one per driver type, please use a static const
+ * shared by all driver instances... Same for the members...
+ * This will be linked from net_device in <linux/netdevice.h>
+ */
+struct iw_handler_def
+{
+ /* Number of handlers defined (more precisely, index of the
+ * last defined handler + 1) */
+ __u16 num_standard;
+ __u16 num_private;
+ /* Number of private arg description */
+ __u16 num_private_args;
+
+ /* Array of handlers for standard ioctls
+ * We will call dev->wireless_handlers->standard[ioctl - SIOCSIWNAME]
+ */
+ iw_handler * standard;
+
+ /* Array of handlers for private ioctls
+ * Will call dev->wireless_handlers->private[ioctl - SIOCIWFIRSTPRIV]
+ */
+ iw_handler * private;
+
+ /* Arguments of private handler. This one is just a list, so you
+ * can put it in any order you want and should not leave holes...
+ * We will automatically export that to user space... */
+ struct iw_priv_args * private_args;
+
+ /* In the long term, get_wireless_stats will move from
+ * 'struct net_device' to here, to minimise bloat. */
+};
+
+/* ----------------------- WIRELESS EVENTS ----------------------- */
+/*
+ * Currently we don't support events, so let's just plan for the
+ * future...
+ */
+
+/*
+ * A Wireless Event.
+ */
+// How do we define short header ? We don't want a flag on length.
+// Probably a flag on event ? Highest bit to zero...
+struct iw_event
+{
+ __u16 length; /* Lenght of this stuff */
+ __u16 event; /* Wireless IOCTL */
+ union iwreq_data header; /* IOCTL fixed payload */
+ char extra[0]; /* Optional IOCTL data */
+};
+
+/* ---------------------- IOCTL DESCRIPTION ---------------------- */
+/*
+ * One of the main goal of the new interface is to deal entirely with
+ * user space/kernel space memory move.
+ * For that, we need to know :
+ * o if iwreq is a pointer or contain the full data
+ * o what is the size of the data to copy
+ *
+ * For private IOCTLs, we use the same rules as used by iwpriv and
+ * defined in struct iw_priv_args.
+ *
+ * For standard IOCTLs, things are quite different and we need to
+ * use the stuctures below. Actually, this struct is also more
+ * efficient, but that's another story...
+ */
+
+/*
+ * Describe how a standard IOCTL looks like.
+ */
+struct iw_ioctl_description
+{
+ __u8 header_type; /* NULL, iw_point or other */
+ __u8 token_type; /* Future */
+ __u16 token_size; /* Granularity of payload */
+ __u16 min_tokens; /* Min acceptable token number */
+ __u16 max_tokens; /* Max acceptable token number */
+ __u32 flags; /* Special handling of the request */
+};
+
+/* Need to think of short header translation table. Later. */
+
+/**************************** PROTOTYPES ****************************/
+/*
+ * Functions part of the Wireless Extensions (defined in net/core/wireless.c).
+ * Those may be called only within the kernel.
+ */
+
+/* First : function strictly used inside the kernel */
+
+/* Handle /proc/net/wireless, called in net/code/dev.c */
+extern int dev_get_wireless_info(char * buffer, char **start, off_t offset,
+ int length);
+
+/* Handle IOCTLs, called in net/code/dev.c */
+extern int wireless_process_ioctl(struct ifreq *ifr, unsigned int cmd);
+
+/* Second : functions that may be called by driver modules */
+/* None yet */
+
+#endif /* _LINUX_WIRELESS_H */