I have completed the USB backport to 2.0.38 and the header file is attached. It is to be included in include/linux/ and added to the usb files. The backport does not support USB PCI cards at the moment, only the USB in the actual computer. The problem with using the USB PCI card is that when the usb-uhci driver sends the "get_descriptor" urb for the newly attached device (in my case a camera), no interrupt is generated through "uhci_interrupt" to signal a response from the camera. Therefore, it just times out in the end after trying a number of times. The usb-uhci driver is able to configure the PCI card as a hub correctly and sense a "hub port connect change" when the device is plugged in. The USB PCI card works using the USB backport for 2.2 (but not for 2.0). Would anyone be able to give me any suggestions on why the usb-uhci driver isn't registering any interrupts when a USB PCI card (using a VIA VT83C572 PCI to USB controller chipset) is used? Is it a 2.2 to 2.0 compatibility issue or a PCI to USB controller chipset issue? Where should I start looking or has anyone had a similar problem before? thank-you very much, Daniel Djamaludin
/* * sysdep-2.1.h -- a trial to centralize changes between 2.0 and 2.1.43 * * export rules changed in 2.1.18 * poll.h is there * cpu_to_le15 etc. appeared in 2.1.10 * they "p" and "s" forms appeared in 2.1.43 */ #ifndef _SYSDEP_21_H_ #define _SYSDEP_21_H_ #ifndef LINUX_VERSION_CODE # include <linux/version.h> #endif #ifndef VERSION_CODE # define VERSION_CODE(vers,rel,seq) ( ((vers)<<16) | ((rel)<<8) | (seq) ) #endif /* only allow 2.0.x and 2.1.y */ #if LINUX_VERSION_CODE < VERSION_CODE(2,0,0) # error "This kernel is too old: not supported by this file" #endif #if LINUX_VERSION_CODE < VERSION_CODE(2,1,0) # define LINUX_20 #endif #include <linux/types.h> /* used later in this header */ /* Modularization issues */ #if LINUX_VERSION_CODE < VERSION_CODE(2,1,18) # define __USE_OLD_SYMTAB__ # define EXPORT_NO_SYMBOLS register_symtab(NULL); # define REGISTER_SYMTAB(tab) register_symtab(tab) #else # define REGISTER_SYMTAB(tab) /* nothing */ #endif #ifdef __USE_OLD_SYMTAB__ # define __MODULE_STRING(s) /* nothing */ # define MODULE_PARM(v,t) /* nothing */ # define MODULE_PARM_DESC(v,t) /* nothing */ # define MODULE_AUTHOR(n) /* nothing */ # define MODULE_DESCRIPTION(d) /* nothing */ # define MODULE_SUPPORTED_DEVICE(n) /* nothing */ #endif /* * "select" changed in 2.1.23. The implementation is twin, but this * header is new */ #if LINUX_VERSION_CODE < VERSION_CODE(2,1,22) # define __USE_OLD_SELECT__ #endif /* * "select" changed in 2.1.23. The implementation is twin, but this * header is new * */ #ifdef LINUX_20 # define __USE_OLD_SELECT__ # define INODE_FROM_F(filp) ((filp)->f_inode) #else # include <linux/poll.h> # define INODE_FROM_F(filp) ((filp)->f_dentry->d_inode) #endif /* implement capable() for 2.0 */ #ifdef LINUX_20 # define capable(anything) suser() #endif /* * /proc has changed a lot across the versions... */ #ifdef LINUX_20 # define USE_PROC_REGISTER # endif /* Other change in the fops are solved using pseudo-types */ #ifdef LINUX_20 # define lseek_t int # define lseek_off_t off_t #endif /* changed the prototype of read/write */ #if defined(LINUX_21) || defined(__alpha__) # define count_t unsigned long # define read_write_t long #else # define count_t int # define read_write_t int #endif #if LINUX_VERSION_CODE < VERSION_CODE(2,1,31) # define release_t void # define release_return(x) return #else # define release_t int # define release_return(x) return (x) #endif /* * access to user space: use the 2.1 functions, * and implement them as macros for 2.0 */ #ifdef LINUX_20 # include <asm/segment.h> # define access_ok(t,a,sz) (verify_area((t),(a),(sz)) ? 0 : 1) # define verify_area_20 verify_area # define copy_to_user(t,f,n) (memcpy_tofs(t,f,n), 0) # define __copy_to_user(t,f,n) copy_to_user((t),(f),(n)) # define copy_to_user_ret(t,f,n,r) copy_to_user((t),(f),(n)) # define copy_from_user(t,f,n) (memcpy_fromfs((t),(f),(n)), 0) # define __copy_from_user(t,f,n) copy_from_user((t),(f),(n)) # define copy_from_user_ret(t,f,n,r) copy_from_user((t),(f),(n)) # define PUT_USER(val,add) (put_user((val),(add)), 0) # define __PUT_USER(val,add) PUT_USER((val),(add)) # define PUT_USER_RET(val,add,ret) PUT_USER((val),(add)) # define GET_USER(dest,add) ((dest)=get_user((add)), 0) # define __GET_USER(dest,add) GET_USER((dest),(add)) # define GET_USER_RET(dest,add,ret) GET_USER((dest),(add)) #endif #ifdef LINUX_20 /* Changes 20-4 */ /* interrupt control. from system.h*/ # include <asm/system.h> # define __sti() sti() # define __cli() cli() # define __save_flags(x) save_flags((x)) # define __restore_flags(x) restore_flags((x)) /* Changes 21-4 */ #endif #ifdef LINUX_20 # include <asm/atomic.h> # define atomic_set(v,i) (*(v) = (i)) #endif #ifdef LINUX_20 # include <asm/atomic.h> # define __KERNEL_SYSCALLS__ # include <linux/unistd.h> # include <linux/sched.h> /* Changes 21-4 */ static inline void process_timeout(unsigned long __data) { struct task_struct * p = (struct task_struct *) __data; //p->timeout = 0; wake_up_process(p); } static inline signed long schedule_timeout(signed long timeout) { struct timer_list timer; unsigned long expire; /* current->state = TASK_INTERRUPTIBLE; */ switch (timeout) { case ((long)(~0UL>>1)): /* * These two special cases are useful to be comfortable * in the caller. Nothing more. We could take * MAX_SCHEDULE_TIMEOUT from one of the negative value * but I' d like to return a valid offset (>=0) to allow * the caller to do everything it want with the retval. */ schedule(); goto out; default: /* * Another bit of PARANOID. Note that the retval will be * 0 since no piece of kernel is supposed to do a check * for a negative retval of schedule_timeout() (since it * should never happens anyway). You just have the printk() * that will tell you if something is gone wrong and where. */ if (timeout < 0) { printk(KERN_ERR "schedule_timeout: wrong timeout " "value %lx from %p\n", timeout, __builtin_return_address(0)); goto out; } } expire = timeout + jiffies; init_timer(&timer); timer.expires = expire; timer.data = (unsigned long) current; timer.function = process_timeout; add_timer(&timer); schedule(); del_timer(&timer); timeout = expire - jiffies; out: return timeout < 0 ? 0 : timeout; } /* schedule_timeout & interruptible_sleep_on_timeout*/ /* static inline signed long schedule_timeout(signed long timeout) { current->timeout = jiffies + timeout; current->state = TASK_INTERRUPTIBLE; schedule(); return timeout; } */ /* * Put all the gunge required to become a kernel thread without * attached user resources in one place where it belongs. */ static inline void daemonize(void) { struct fs_struct *fs; /* * If we were started as result of loading a module, close all of the * user space pages. We don't need them, and if we didn't close them * they would be locked into memory. */ exit_mm(current); current->session = 1; current->pgrp = 1; /* Become as one with the init task */ exit_fs(current); /* current->fs->count--; */ fs = init_task.fs; current->fs = fs; atomic_inc((atomic_t*)&fs->count); } /* initialisation to free memory*/ #define __init #define __initdata #define __initfunc(func) func #endif #ifdef LINUX_20 /* Changes 21-4 */ /* pci */ # include <linux/pci.h> /* Changes 21-4 */ # include <linux/bios32.h> /* Changes 21-4 */ static inline struct pci_dev * pci_find_class(unsigned int class, struct pci_dev *from) { if (!from) from = pci_devices; else from = from->next; while (from && from->class != class) from = from->next; return from; } static inline struct pci_dev * pci_find_device(unsigned int vendor, unsigned int device, struct pci_dev *from) { if (!from) from = pci_devices; else from = from->next; while (from && (from->vendor != vendor || from->device != device)) from = from->next; return from; } static inline int pci_read_config_byte(struct pci_dev *dev, u8 where, u8 *val) { return pcibios_read_config_byte(dev->bus->number, dev->devfn, where, val); } static inline int pci_read_config_word(struct pci_dev *dev, u8 where, u16 *val) { return pcibios_read_config_word(dev->bus->number, dev->devfn, where, val); } static inline int pci_write_config_word(struct pci_dev *dev, u8 where, u16 val) { return pcibios_write_config_word(dev->bus->number, dev->devfn, where, val); } #endif /* * In 2.0, there is no real need for spinlocks, and they weren't really * implemented anyway. * * XXX the _irqsave variant should be defined eventually to do the * right thing. */ #ifdef LINUX_20 typedef int spinlock_t; # define spin_lock(lock) # define spin_unlock(lock) # define spin_lock_init(lock) # define spin_lock_irqsave(a,b) # define spin_unlock_irqrestore(a,b) #endif #ifdef LINUX_20 // #undef DEBUG_SLAB # define kmem_cache_alloc(a,b) # define kmem_cache_free(a,b) # define kmem_cache_create(a,b,c,d,e,f) # define kmem_cache_destroy(a) #endif #ifdef LINUX_20 # include <linux/mm.h> # include <asm/pgtable.h> /* Changes 21-4 pgd_offset is already defined in pgtable.h*/ /* Changes 14-4 */ /* to find an entry in a kernel page-table-directory */ # define pgd_offset(mm,address) \ ((mm)->pgd + ((address) >> PGDIR_SHIFT)) # define pgd_offset_k(address) pgd_offset(&init_mm, address) # define PAGE_OFFSET_RAW 0x40000000 # define __PAGE_OFFSET_2 (PAGE_OFFSET_RAW) # define PAGE_OFFSET_2 ((unsigned long)__PAGE_OFFSET_2) # define __pa(x) ((unsigned long)(x)-PAGE_OFFSET_2) # define __va(x) ((void *)((unsigned long)(x)+PAGE_OFFSET_2)) # define MAP_NR_2(addr) (__pa(addr) >> PAGE_SHIFT) #endif #ifdef LINUX_20 # define signal_pending(current) (current->signal & ~current->blocked) // # define current_got_fatal_signal() (signal_pending(current)) #endif #ifdef LINUX_20 // from the 2.2 kernel <linux/smp_lock.h> # define lock_kernel() do { } while(0) # define unlock_kernel() do { } while(0) # define release_kernel_lock(task, cpu) do { } while(0) # define reacquire_kernel_lock(task) do { } while(0) #endif /* ioremap */ //#ifdef LINUX_20 //# define ioremap vremap //# define iounmap vfree //#endif /* The use_count of exec_domain and binfmt changed in 2.1.23 */ #ifdef LINUX_20 # define INCRCOUNT(p) ((p)->module ? __MOD_INC_USE_COUNT((p)->module) : 0) # define CURRCOUNT(p) ((p)->module && (p)->module->usecount) # define DECRCOUNT(p) ((p)->module ? __MOD_DEC_USE_COUNT((p)->module) : 0) #else # define INCRCOUNT(p) ((p)->use_count++) # define CURRCOUNT(p) ((p)->use_count) # define DECRCOUNT(p) ((p)->use_count--) #endif /* register_dynamic no more existent -- just have 0 as inum */ #if LINUX_VERSION_CODE < VERSION_CODE(2,1,37) # define test_and_set_bit(nr,addr) test_bit((nr),(addr)) # define test_and_clear_bit(nr,addr) clear_bit((nr),(addr)) # define test_and_change_bit(nr,addr) change_bit((nr),(addr)) #endif /* 2.1.10 and 2.1.43 introduced new functions. They are worth using */ #if LINUX_VERSION_CODE < VERSION_CODE(2,1,10) # include <asm/byteorder.h> # ifdef __LITTLE_ENDIAN # define cpu_to_le16(x) (x) # define cpu_to_le32(x) (x) # define cpu_to_be16(x) htons((x)) # define cpu_to_be32(x) htonl((x)) # else # define cpu_to_be16(x) (x) # define cpu_to_be32(x) (x) extern inline __u16 cpu_to_le16(__u16 x) { return (x<<8) | (x>>8);} extern inline __u32 cpu_to_le32(__u32 x) { return((x>>24) | ((x>>8)&0xff00) | ((x<<8)&0xff0000) | (x<<24));} # endif # define le16_to_cpu(x) cpu_to_le16(x) # define le32_to_cpu(x) cpu_to_le32(x) # define be16_to_cpu(x) cpu_to_be16(x) # define be32_to_cpu(x) cpu_to_be32(x) #endif #if LINUX_VERSION_CODE < VERSION_CODE(2,1,43) # define cpu_to_le16p(addr) (cpu_to_le16(*(addr))) # define cpu_to_le32p(addr) (cpu_to_le32(*(addr))) # define cpu_to_be16p(addr) (cpu_to_be16(*(addr))) # define cpu_to_be32p(addr) (cpu_to_be32(*(addr))) extern inline void cpu_to_le16s(__u16 *a) {*a = cpu_to_le16(*a);} extern inline void cpu_to_le32s(__u16 *a) {*a = cpu_to_le32(*a);} extern inline void cpu_to_be16s(__u16 *a) {*a = cpu_to_be16(*a);} extern inline void cpu_to_be32s(__u16 *a) {*a = cpu_to_be32(*a);} # define le16_to_cpup(x) cpu_to_le16p(x) # define le32_to_cpup(x) cpu_to_le32p(x) # define be16_to_cpup(x) cpu_to_be16p(x) # define be32_to_cpup(x) cpu_to_be32p(x) # define le16_to_cpus(x) cpu_to_le16s(x) # define le32_to_cpus(x) cpu_to_le32s(x) # define be16_to_cpus(x) cpu_to_be16s(x) # define be32_to_cpus(x) cpu_to_be32s(x) #endif #if LINUX_VERSION_CODE < VERSION_CODE(2,1,15) # define __USE_OLD_REBUILD_HEADER__ #endif /* * 2.0 didn't include sema_init, so we make our own - but only if it * looks like semaphore.h got included. */ #ifdef LINUX_20 # ifdef MUTEX_LOCKED extern inline void sema_init (struct semaphore *sem, int val) { sem->count = val; sem->waking = sem->lock = 0; sem->wait = NULL; } # endif #endif /* LINUX_20 */ #if LINUX_VERSION_CODE < VERSION_CODE(2,1,30) # define in_interrupt() (intr_count!=0) /* Note redefinition in delay.h */ # define mdelay2(x) udelay((x)*1000) #endif #endif /* _SYSDEP_21_H_ */
--------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]