diff options
author | David S. Miller <davem@davemloft.net> | 2009-11-18 22:19:03 -0800 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2009-11-18 22:19:03 -0800 |
commit | 3505d1a9fd65e2d3e00827857b6795d9d8983658 (patch) | |
tree | 941cfafdb57c427bb6b7ebf6354ee93b2a3693b5 | |
parent | dfef948ed2ba69cf041840b5e860d6b4e16fa0b1 (diff) | |
parent | 66b00a7c93ec782d118d2c03bd599cfd041e80a1 (diff) | |
download | lwn-3505d1a9fd65e2d3e00827857b6795d9d8983658.tar.gz lwn-3505d1a9fd65e2d3e00827857b6795d9d8983658.zip |
Merge branch 'master' of master.kernel.org:/pub/scm/linux/kernel/git/davem/net-2.6
Conflicts:
drivers/net/sfc/sfe4001.c
drivers/net/wireless/libertas/cmd.c
drivers/staging/Kconfig
drivers/staging/Makefile
drivers/staging/rtl8187se/Kconfig
drivers/staging/rtl8192e/Kconfig
1961 files changed, 85021 insertions, 28664 deletions
diff --git a/Documentation/ABI/testing/sysfs-class-usb_host b/Documentation/ABI/testing/sysfs-class-uwb_rc-wusbhc index 46b66ad1f1b4..4e8106f7cfd9 100644 --- a/Documentation/ABI/testing/sysfs-class-usb_host +++ b/Documentation/ABI/testing/sysfs-class-uwb_rc-wusbhc @@ -1,4 +1,4 @@ -What: /sys/class/usb_host/usb_hostN/wusb_chid +What: /sys/class/uwb_rc/uwbN/wusbhc/wusb_chid Date: July 2008 KernelVersion: 2.6.27 Contact: David Vrabel <david.vrabel@csr.com> @@ -9,7 +9,7 @@ Description: Set an all zero CHID to stop the host controller. -What: /sys/class/usb_host/usb_hostN/wusb_trust_timeout +What: /sys/class/uwb_rc/uwbN/wusbhc/wusb_trust_timeout Date: July 2008 KernelVersion: 2.6.27 Contact: David Vrabel <david.vrabel@csr.com> diff --git a/Documentation/ABI/testing/sysfs-devices-cache_disable b/Documentation/ABI/testing/sysfs-devices-cache_disable deleted file mode 100644 index 175bb4f70512..000000000000 --- a/Documentation/ABI/testing/sysfs-devices-cache_disable +++ /dev/null @@ -1,18 +0,0 @@ -What: /sys/devices/system/cpu/cpu*/cache/index*/cache_disable_X -Date: August 2008 -KernelVersion: 2.6.27 -Contact: mark.langsdorf@amd.com -Description: These files exist in every cpu's cache index directories. - There are currently 2 cache_disable_# files in each - directory. Reading from these files on a supported - processor will return that cache disable index value - for that processor and node. Writing to one of these - files will cause the specificed cache index to be disabled. - - Currently, only AMD Family 10h Processors support cache index - disable, and only for their L3 caches. See the BIOS and - Kernel Developer's Guide at - http://www.amd.com/us-en/assets/content_type/white_papers_and_tech_docs/31116-Public-GH-BKDG_3.20_2-4-09.pdf - for formatting information and other details on the - cache index disable. -Users: joachim.deguara@amd.com diff --git a/Documentation/ABI/testing/sysfs-devices-system-cpu b/Documentation/ABI/testing/sysfs-devices-system-cpu new file mode 100644 index 000000000000..a703b9e9aeb9 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-devices-system-cpu @@ -0,0 +1,156 @@ +What: /sys/devices/system/cpu/ +Date: pre-git history +Contact: Linux kernel mailing list <linux-kernel@vger.kernel.org> +Description: + A collection of both global and individual CPU attributes + + Individual CPU attributes are contained in subdirectories + named by the kernel's logical CPU number, e.g.: + + /sys/devices/system/cpu/cpu#/ + +What: /sys/devices/system/cpu/sched_mc_power_savings + /sys/devices/system/cpu/sched_smt_power_savings +Date: June 2006 +Contact: Linux kernel mailing list <linux-kernel@vger.kernel.org> +Description: Discover and adjust the kernel's multi-core scheduler support. + + Possible values are: + + 0 - No power saving load balance (default value) + 1 - Fill one thread/core/package first for long running threads + 2 - Also bias task wakeups to semi-idle cpu package for power + savings + + sched_mc_power_savings is dependent upon SCHED_MC, which is + itself architecture dependent. + + sched_smt_power_savings is dependent upon SCHED_SMT, which + is itself architecture dependent. + + The two files are independent of each other. It is possible + that one file may be present without the other. + + Introduced by git commit 5c45bf27. + + +What: /sys/devices/system/cpu/kernel_max + /sys/devices/system/cpu/offline + /sys/devices/system/cpu/online + /sys/devices/system/cpu/possible + /sys/devices/system/cpu/present +Date: December 2008 +Contact: Linux kernel mailing list <linux-kernel@vger.kernel.org> +Description: CPU topology files that describe kernel limits related to + hotplug. Briefly: + + kernel_max: the maximum cpu index allowed by the kernel + configuration. + + offline: cpus that are not online because they have been + HOTPLUGGED off or exceed the limit of cpus allowed by the + kernel configuration (kernel_max above). + + online: cpus that are online and being scheduled. + + possible: cpus that have been allocated resources and can be + brought online if they are present. + + present: cpus that have been identified as being present in + the system. + + See Documentation/cputopology.txt for more information. + + + +What: /sys/devices/system/cpu/cpu#/node +Date: October 2009 +Contact: Linux memory management mailing list <linux-mm@kvack.org> +Description: Discover NUMA node a CPU belongs to + + When CONFIG_NUMA is enabled, a symbolic link that points + to the corresponding NUMA node directory. + + For example, the following symlink is created for cpu42 + in NUMA node 2: + + /sys/devices/system/cpu/cpu42/node2 -> ../../node/node2 + + +What: /sys/devices/system/cpu/cpu#/topology/core_id + /sys/devices/system/cpu/cpu#/topology/core_siblings + /sys/devices/system/cpu/cpu#/topology/core_siblings_list + /sys/devices/system/cpu/cpu#/topology/physical_package_id + /sys/devices/system/cpu/cpu#/topology/thread_siblings + /sys/devices/system/cpu/cpu#/topology/thread_siblings_list +Date: December 2008 +Contact: Linux kernel mailing list <linux-kernel@vger.kernel.org> +Description: CPU topology files that describe a logical CPU's relationship + to other cores and threads in the same physical package. + + One cpu# directory is created per logical CPU in the system, + e.g. /sys/devices/system/cpu/cpu42/. + + Briefly, the files above are: + + core_id: the CPU core ID of cpu#. Typically it is the + hardware platform's identifier (rather than the kernel's). + The actual value is architecture and platform dependent. + + core_siblings: internal kernel map of cpu#'s hardware threads + within the same physical_package_id. + + core_siblings_list: human-readable list of the logical CPU + numbers within the same physical_package_id as cpu#. + + physical_package_id: physical package id of cpu#. Typically + corresponds to a physical socket number, but the actual value + is architecture and platform dependent. + + thread_siblings: internel kernel map of cpu#'s hardware + threads within the same core as cpu# + + thread_siblings_list: human-readable list of cpu#'s hardware + threads within the same core as cpu# + + See Documentation/cputopology.txt for more information. + + +What: /sys/devices/system/cpu/cpuidle/current_driver + /sys/devices/system/cpu/cpuidle/current_governer_ro +Date: September 2007 +Contact: Linux kernel mailing list <linux-kernel@vger.kernel.org> +Description: Discover cpuidle policy and mechanism + + Various CPUs today support multiple idle levels that are + differentiated by varying exit latencies and power + consumption during idle. + + Idle policy (governor) is differentiated from idle mechanism + (driver) + + current_driver: displays current idle mechanism + + current_governor_ro: displays current idle policy + + See files in Documentation/cpuidle/ for more information. + + +What: /sys/devices/system/cpu/cpu*/cache/index*/cache_disable_X +Date: August 2008 +KernelVersion: 2.6.27 +Contact: mark.langsdorf@amd.com +Description: These files exist in every cpu's cache index directories. + There are currently 2 cache_disable_# files in each + directory. Reading from these files on a supported + processor will return that cache disable index value + for that processor and node. Writing to one of these + files will cause the specificed cache index to be disabled. + + Currently, only AMD Family 10h Processors support cache index + disable, and only for their L3 caches. See the BIOS and + Kernel Developer's Guide at + http://www.amd.com/us-en/assets/content_type/white_papers_and_tech_docs/31116-Public-GH-BKDG_3.20_2-4-09.pdf + for formatting information and other details on the + cache index disable. +Users: joachim.deguara@amd.com diff --git a/Documentation/cgroups/cgroups.txt b/Documentation/cgroups/cgroups.txt index 455d4e6d346d..0b33bfe7dde9 100644 --- a/Documentation/cgroups/cgroups.txt +++ b/Documentation/cgroups/cgroups.txt @@ -227,7 +227,14 @@ as the path relative to the root of the cgroup file system. Each cgroup is represented by a directory in the cgroup file system containing the following files describing that cgroup: - - tasks: list of tasks (by pid) attached to that cgroup + - tasks: list of tasks (by pid) attached to that cgroup. This list + is not guaranteed to be sorted. Writing a thread id into this file + moves the thread into this cgroup. + - cgroup.procs: list of tgids in the cgroup. This list is not + guaranteed to be sorted or free of duplicate tgids, and userspace + should sort/uniquify the list if this property is required. + Writing a tgid into this file moves all threads with that tgid into + this cgroup. - notify_on_release flag: run the release agent on exit? - release_agent: the path to use for release notifications (this file exists in the top cgroup only) @@ -374,7 +381,7 @@ Now you want to do something with this cgroup. In this directory you can find several files: # ls -notify_on_release tasks +cgroup.procs notify_on_release tasks (plus whatever files added by the attached subsystems) Now attach your shell to this cgroup: diff --git a/Documentation/cputopology.txt b/Documentation/cputopology.txt index b41f3e58aefa..f1c5c4bccd3e 100644 --- a/Documentation/cputopology.txt +++ b/Documentation/cputopology.txt @@ -1,15 +1,28 @@ -Export cpu topology info via sysfs. Items (attributes) are similar +Export CPU topology info via sysfs. Items (attributes) are similar to /proc/cpuinfo. 1) /sys/devices/system/cpu/cpuX/topology/physical_package_id: -represent the physical package id of cpu X; + + physical package id of cpuX. Typically corresponds to a physical + socket number, but the actual value is architecture and platform + dependent. + 2) /sys/devices/system/cpu/cpuX/topology/core_id: -represent the cpu core id to cpu X; + + the CPU core ID of cpuX. Typically it is the hardware platform's + identifier (rather than the kernel's). The actual value is + architecture and platform dependent. + 3) /sys/devices/system/cpu/cpuX/topology/thread_siblings: -represent the thread siblings to cpu X in the same core; + + internel kernel map of cpuX's hardware threads within the same + core as cpuX + 4) /sys/devices/system/cpu/cpuX/topology/core_siblings: -represent the thread siblings to cpu X in the same physical package; + + internal kernel map of cpuX's hardware threads within the same + physical_package_id. To implement it in an architecture-neutral way, a new source file, drivers/base/topology.c, is to export the 4 attributes. @@ -32,32 +45,32 @@ not defined by include/asm-XXX/topology.h: 3) thread_siblings: just the given CPU 4) core_siblings: just the given CPU -Additionally, cpu topology information is provided under +Additionally, CPU topology information is provided under /sys/devices/system/cpu and includes these files. The internal source for the output is in brackets ("[]"). - kernel_max: the maximum cpu index allowed by the kernel configuration. + kernel_max: the maximum CPU index allowed by the kernel configuration. [NR_CPUS-1] - offline: cpus that are not online because they have been + offline: CPUs that are not online because they have been HOTPLUGGED off (see cpu-hotplug.txt) or exceed the limit - of cpus allowed by the kernel configuration (kernel_max + of CPUs allowed by the kernel configuration (kernel_max above). [~cpu_online_mask + cpus >= NR_CPUS] - online: cpus that are online and being scheduled [cpu_online_mask] + online: CPUs that are online and being scheduled [cpu_online_mask] - possible: cpus that have been allocated resources and can be + possible: CPUs that have been allocated resources and can be brought online if they are present. [cpu_possible_mask] - present: cpus that have been identified as being present in the + present: CPUs that have been identified as being present in the system. [cpu_present_mask] The format for the above output is compatible with cpulist_parse() [see <linux/cpumask.h>]. Some examples follow. -In this example, there are 64 cpus in the system but cpus 32-63 exceed +In this example, there are 64 CPUs in the system but cpus 32-63 exceed the kernel max which is limited to 0..31 by the NR_CPUS config option -being 32. Note also that cpus 2 and 4-31 are not online but could be +being 32. Note also that CPUs 2 and 4-31 are not online but could be brought online as they are both present and possible. kernel_max: 31 @@ -67,8 +80,8 @@ brought online as they are both present and possible. present: 0-31 In this example, the NR_CPUS config option is 128, but the kernel was -started with possible_cpus=144. There are 4 cpus in the system and cpu2 -was manually taken offline (and is the only cpu that can be brought +started with possible_cpus=144. There are 4 CPUs in the system and cpu2 +was manually taken offline (and is the only CPU that can be brought online.) kernel_max: 127 @@ -78,4 +91,4 @@ online.) present: 0-3 See cpu-hotplug.txt for the possible_cpus=NUM kernel start parameter -as well as more information on the various cpumask's. +as well as more information on the various cpumasks. diff --git a/Documentation/debugging-via-ohci1394.txt b/Documentation/debugging-via-ohci1394.txt index 59a91e5c6909..611f5a5499b1 100644 --- a/Documentation/debugging-via-ohci1394.txt +++ b/Documentation/debugging-via-ohci1394.txt @@ -64,14 +64,14 @@ be used to view the printk buffer of a remote machine, even with live update. Bernhard Kaindl enhanced firescope to support accessing 64-bit machines from 32-bit firescope and vice versa: -- ftp://ftp.suse.de/private/bk/firewire/tools/firescope-0.2.2.tar.bz2 +- http://halobates.de/firewire/firescope-0.2.2.tar.bz2 and he implemented fast system dump (alpha version - read README.txt): -- ftp://ftp.suse.de/private/bk/firewire/tools/firedump-0.1.tar.bz2 +- http://halobates.de/firewire/firedump-0.1.tar.bz2 There is also a gdb proxy for firewire which allows to use gdb to access data which can be referenced from symbols found by gdb in vmlinux: -- ftp://ftp.suse.de/private/bk/firewire/tools/fireproxy-0.33.tar.bz2 +- http://halobates.de/firewire/fireproxy-0.33.tar.bz2 The latest version of this gdb proxy (fireproxy-0.34) can communicate (not yet stable) with kgdb over an memory-based communication module (kgdbom). @@ -178,7 +178,7 @@ Step-by-step instructions for using firescope with early OHCI initialization: Notes ----- -Documentation and specifications: ftp://ftp.suse.de/private/bk/firewire/docs +Documentation and specifications: http://halobates.de/firewire/ FireWire is a trademark of Apple Inc. - for more information please refer to: http://en.wikipedia.org/wiki/FireWire diff --git a/Documentation/feature-removal-schedule.txt b/Documentation/feature-removal-schedule.txt index 89a47b5aff07..bc693fffabe0 100644 --- a/Documentation/feature-removal-schedule.txt +++ b/Documentation/feature-removal-schedule.txt @@ -418,6 +418,14 @@ When: 2.6.33 Why: Should be implemented in userspace, policy daemon. Who: Johannes Berg <johannes@sipsolutions.net> +--------------------------- + +What: CONFIG_INOTIFY +When: 2.6.33 +Why: last user (audit) will be converted to the newer more generic + and more easily maintained fsnotify subsystem +Who: Eric Paris <eparis@redhat.com> + ---------------------------- What: lock_policy_rwsem_* and unlock_policy_rwsem_* will not be @@ -451,3 +459,33 @@ Why: OSS sound_core grabs all legacy minors (0-255) of SOUND_MAJOR will also allow making ALSA OSS emulation independent of sound_core. The dependency will be broken then too. Who: Tejun Heo <tj@kernel.org> + +---------------------------- + +What: Support for VMware's guest paravirtuliazation technique [VMI] will be + dropped. +When: 2.6.37 or earlier. +Why: With the recent innovations in CPU hardware acceleration technologies + from Intel and AMD, VMware ran a few experiments to compare these + techniques to guest paravirtualization technique on VMware's platform. + These hardware assisted virtualization techniques have outperformed the + performance benefits provided by VMI in most of the workloads. VMware + expects that these hardware features will be ubiquitous in a couple of + years, as a result, VMware has started a phased retirement of this + feature from the hypervisor. We will be removing this feature from the + Kernel too. Right now we are targeting 2.6.37 but can retire earlier if + technical reasons (read opportunity to remove major chunk of pvops) + arise. + + Please note that VMI has always been an optimization and non-VMI kernels + still work fine on VMware's platform. + Latest versions of VMware's product which support VMI are, + Workstation 7.0 and VSphere 4.0 on ESX side, future maintainence + releases for these products will continue supporting VMI. + + For more details about VMI retirement take a look at this, + http://blogs.vmware.com/guestosguide/2009/09/vmi-retirement.html + +Who: Alok N Kataria <akataria@vmware.com> + +---------------------------- diff --git a/Documentation/filesystems/ext3.txt b/Documentation/filesystems/ext3.txt index 570f9bd9be2b..05d5cf1d743f 100644 --- a/Documentation/filesystems/ext3.txt +++ b/Documentation/filesystems/ext3.txt @@ -123,10 +123,18 @@ resuid=n The user ID which may use the reserved blocks. sb=n Use alternate superblock at this location. -quota -noquota -grpquota -usrquota +quota These options are ignored by the filesystem. They +noquota are used only by quota tools to recognize volumes +grpquota where quota should be turned on. See documentation +usrquota in the quota-tools package for more details + (http://sourceforge.net/projects/linuxquota). + +jqfmt=<quota type> These options tell filesystem details about quota +usrjquota=<file> so that quota information can be properly updated +grpjquota=<file> during journal replay. They replace the above + quota options. See documentation in the quota-tools + package for more details + (http://sourceforge.net/projects/linuxquota). bh (*) ext3 associates buffer heads to data pages to nobh (a) cache disk block mapping information diff --git a/Documentation/filesystems/ext4.txt b/Documentation/filesystems/ext4.txt index bf4f4b7e11b3..6d94e0696f8c 100644 --- a/Documentation/filesystems/ext4.txt +++ b/Documentation/filesystems/ext4.txt @@ -134,9 +134,15 @@ ro Mount filesystem read only. Note that ext4 will mount options "ro,noload" can be used to prevent writes to the filesystem. +journal_checksum Enable checksumming of the journal transactions. + This will allow the recovery code in e2fsck and the + kernel to detect corruption in the kernel. It is a + compatible change and will be ignored by older kernels. + journal_async_commit Commit block can be written to disk without waiting for descriptor blocks. If enabled older kernels cannot - mount the device. + mount the device. This will enable 'journal_checksum' + internally. journal=update Update the ext4 file system's journal to the current format. diff --git a/Documentation/flexible-arrays.txt b/Documentation/flexible-arrays.txt index 84eb26808dee..cb8a3a00cc92 100644 --- a/Documentation/flexible-arrays.txt +++ b/Documentation/flexible-arrays.txt @@ -1,5 +1,5 @@ Using flexible arrays in the kernel -Last updated for 2.6.31 +Last updated for 2.6.32 Jonathan Corbet <corbet@lwn.net> Large contiguous memory allocations can be unreliable in the Linux kernel. @@ -40,6 +40,13 @@ argument is passed directly to the internal memory allocation calls. With the current code, using flags to ask for high memory is likely to lead to notably unpleasant side effects. +It is also possible to define flexible arrays at compile time with: + + DEFINE_FLEX_ARRAY(name, element_size, total); + +This macro will result in a definition of an array with the given name; the +element size and total will be checked for validity at compile time. + Storing data into a flexible array is accomplished with a call to: int flex_array_put(struct flex_array *array, unsigned int element_nr, @@ -76,16 +83,30 @@ particular element has never been allocated. Note that it is possible to get back a valid pointer for an element which has never been stored in the array. Memory for array elements is allocated one page at a time; a single allocation could provide memory for several -adjacent elements. The flexible array code does not know if a specific -element has been written; it only knows if the associated memory is -present. So a flex_array_get() call on an element which was never stored -in the array has the potential to return a pointer to random data. If the -caller does not have a separate way to know which elements were actually -stored, it might be wise, at least, to add GFP_ZERO to the flags argument -to ensure that all elements are zeroed. - -There is no way to remove a single element from the array. It is possible, -though, to remove all elements with a call to: +adjacent elements. Flexible array elements are normally initialized to the +value FLEX_ARRAY_FREE (defined as 0x6c in <linux/poison.h>), so errors +involving that number probably result from use of unstored array entries. +Note that, if array elements are allocated with __GFP_ZERO, they will be +initialized to zero and this poisoning will not happen. + +Individual elements in the array can be cleared with: + + int flex_array_clear(struct flex_array *array, unsigned int element_nr); + +This function will set the given element to FLEX_ARRAY_FREE and return +zero. If storage for the indicated element is not allocated for the array, +flex_array_clear() will return -EINVAL instead. Note that clearing an +element does not release the storage associated with it; to reduce the +allocated size of an array, call: + + int flex_array_shrink(struct flex_array *array); + +The return value will be the number of pages of memory actually freed. +This function works by scanning the array for pages containing nothing but +FLEX_ARRAY_FREE bytes, so (1) it can be expensive, and (2) it will not work +if the array's pages are allocated with __GFP_ZERO. + +It is possible to remove all elements of an array with a call to: void flex_array_free_parts(struct flex_array *array); diff --git a/Documentation/hwmon/sysfs-interface b/Documentation/hwmon/sysfs-interface index dcbd502c8792..82def883361b 100644 --- a/Documentation/hwmon/sysfs-interface +++ b/Documentation/hwmon/sysfs-interface @@ -353,10 +353,20 @@ power[1-*]_average Average power use Unit: microWatt RO -power[1-*]_average_interval Power use averaging interval +power[1-*]_average_interval Power use averaging interval. A poll + notification is sent to this file if the + hardware changes the averaging interval. Unit: milliseconds RW +power[1-*]_average_interval_max Maximum power use averaging interval + Unit: milliseconds + RO + +power[1-*]_average_interval_min Minimum power use averaging interval + Unit: milliseconds + RO + power[1-*]_average_highest Historical average maximum power use Unit: microWatt RO @@ -365,6 +375,18 @@ power[1-*]_average_lowest Historical average minimum power use Unit: microWatt RO +power[1-*]_average_max A poll notification is sent to + power[1-*]_average when power use + rises above this value. + Unit: microWatt + RW + +power[1-*]_average_min A poll notification is sent to + power[1-*]_average when power use + sinks below this value. + Unit: microWatt + RW + power[1-*]_input Instantaneous power use Unit: microWatt RO @@ -381,6 +403,39 @@ power[1-*]_reset_history Reset input_highest, input_lowest, average_highest and average_lowest. WO +power[1-*]_accuracy Accuracy of the power meter. + Unit: Percent + RO + +power[1-*]_alarm 1 if the system is drawing more power than the + cap allows; 0 otherwise. A poll notification is + sent to this file when the power use exceeds the + cap. This file only appears if the cap is known + to be enforced by hardware. + RO + +power[1-*]_cap If power use rises above this limit, the + system should take action to reduce power use. + A poll notification is sent to this file if the + cap is changed by the hardware. The *_cap + files only appear if the cap is known to be + enforced by hardware. + Unit: microWatt + RW + +power[1-*]_cap_hyst Margin of hysteresis built around capping and + notification. + Unit: microWatt + RW + +power[1-*]_cap_max Maximum cap that can be set. + Unit: microWatt + RO + +power[1-*]_cap_min Minimum cap that can be set. + Unit: microWatt + RO + ********** * Energy * ********** diff --git a/Documentation/i2c/busses/i2c-piix4 b/Documentation/i2c/busses/i2c-piix4 index c5b37c570554..ac540c71c7eb 100644 --- a/Documentation/i2c/busses/i2c-piix4 +++ b/Documentation/i2c/busses/i2c-piix4 @@ -8,7 +8,7 @@ Supported adapters: Datasheet: Only available via NDA from ServerWorks * ATI IXP200, IXP300, IXP400, SB600, SB700 and SB800 southbridges Datasheet: Not publicly available - * AMD SB900 + * AMD Hudson-2 Datasheet: Not publicly available * Standard Microsystems (SMSC) SLC90E66 (Victory66) southbridge Datasheet: Publicly available at the SMSC website http://www.smsc.com diff --git a/Documentation/infiniband/user_mad.txt b/Documentation/infiniband/user_mad.txt index 744687dd195b..8a366959f5cc 100644 --- a/Documentation/infiniband/user_mad.txt +++ b/Documentation/infiniband/user_mad.txt @@ -128,8 +128,8 @@ Setting IsSM Capability Bit To create the appropriate character device files automatically with udev, a rule like - KERNEL="umad*", NAME="infiniband/%k" - KERNEL="issm*", NAME="infiniband/%k" + KERNEL=="umad*", NAME="infiniband/%k" + KERNEL=="issm*", NAME="infiniband/%k" can be used. This will create device nodes named diff --git a/Documentation/infiniband/user_verbs.txt b/Documentation/infiniband/user_verbs.txt index f847501e50b5..afe3f8da9018 100644 --- a/Documentation/infiniband/user_verbs.txt +++ b/Documentation/infiniband/user_verbs.txt @@ -58,7 +58,7 @@ Memory pinning To create the appropriate character device files automatically with udev, a rule like - KERNEL="uverbs*", NAME="infiniband/%k" + KERNEL=="uverbs*", NAME="infiniband/%k" can be used. This will create device nodes named diff --git a/Documentation/kernel-parameters.txt b/Documentation/kernel-parameters.txt index 02df20be7764..52c34b4f567e 100644 --- a/Documentation/kernel-parameters.txt +++ b/Documentation/kernel-parameters.txt @@ -671,6 +671,7 @@ and is between 256 and 4096 characters. It is defined in the file earlyprintk= [X86,SH,BLACKFIN] earlyprintk=vga earlyprintk=serial[,ttySn[,baudrate]] + earlyprintk=ttySn[,baudrate] earlyprintk=dbgp[debugController#] Append ",keep" to not disable it when the real console diff --git a/Documentation/lguest/lguest.c b/Documentation/lguest/lguest.c index ba9373f82ab5..098de5bce00a 100644 --- a/Documentation/lguest/lguest.c +++ b/Documentation/lguest/lguest.c @@ -42,7 +42,6 @@ #include <signal.h> #include "linux/lguest_launcher.h" #include "linux/virtio_config.h" -#include <linux/virtio_ids.h> #include "linux/virtio_net.h" #include "linux/virtio_blk.h" #include "linux/virtio_console.h" diff --git a/Documentation/scsi/hptiop.txt b/Documentation/scsi/hptiop.txt index a6eb4add1be6..9605179711f4 100644 --- a/Documentation/scsi/hptiop.txt +++ b/Documentation/scsi/hptiop.txt @@ -3,6 +3,25 @@ HIGHPOINT ROCKETRAID 3xxx/4xxx ADAPTER DRIVER (hptiop) Controller Register Map ------------------------- +For RR44xx Intel IOP based adapters, the controller IOP is accessed via PCI BAR0 and BAR2: + + BAR0 offset Register + 0x11C5C Link Interface IRQ Set + 0x11C60 Link Interface IRQ Clear + + BAR2 offset Register + 0x10 Inbound Message Register 0 + 0x14 Inbound Message Register 1 + 0x18 Outbound Message Register 0 + 0x1C Outbound Message Register 1 + 0x20 Inbound Doorbell Register + 0x24 Inbound Interrupt Status Register + 0x28 Inbound Interrupt Mask Register + 0x30 Outbound Interrupt Status Register + 0x34 Outbound Interrupt Mask Register + 0x40 Inbound Queue Port + 0x44 Outbound Queue Port + For Intel IOP based adapters, the controller IOP is accessed via PCI BAR0: BAR0 offset Register @@ -93,7 +112,7 @@ The driver exposes following sysfs attributes: ----------------------------------------------------------------------------- -Copyright (C) 2006-2007 HighPoint Technologies, Inc. All Rights Reserved. +Copyright (C) 2006-2009 HighPoint Technologies, Inc. All Rights Reserved. This file is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of diff --git a/Documentation/sound/alsa/ALSA-Configuration.txt b/Documentation/sound/alsa/ALSA-Configuration.txt index 1c8eb4518ce0..fd9a2f67edf2 100644 --- a/Documentation/sound/alsa/ALSA-Configuration.txt +++ b/Documentation/sound/alsa/ALSA-Configuration.txt @@ -522,7 +522,7 @@ Prior to version 0.9.0rc4 options had a 'snd_' prefix. This was removed. pcm_devs - Number of PCM devices assigned to each card (default = 1, up to 4) pcm_substreams - Number of PCM substreams assigned to each PCM - (default = 8, up to 16) + (default = 8, up to 128) hrtimer - Use hrtimer (=1, default) or system timer (=0) fake_buffer - Fake buffer allocations (default = 1) diff --git a/Documentation/sound/alsa/HD-Audio-Models.txt b/Documentation/sound/alsa/HD-Audio-Models.txt index 75fddb40f416..4c7f9aee5c4e 100644 --- a/Documentation/sound/alsa/HD-Audio-Models.txt +++ b/Documentation/sound/alsa/HD-Audio-Models.txt @@ -359,6 +359,7 @@ STAC9227/9228/9229/927x 5stack-no-fp D965 5stack without front panel dell-3stack Dell Dimension E520 dell-bios Fixes with Dell BIOS setup + volknob Fixes with volume-knob widget 0x24 auto BIOS setup (default) STAC92HD71B* diff --git a/Documentation/thermal/sysfs-api.txt b/Documentation/thermal/sysfs-api.txt index 70d68ce8640a..a87dc277a5ca 100644 --- a/Documentation/thermal/sysfs-api.txt +++ b/Documentation/thermal/sysfs-api.txt @@ -1,5 +1,5 @@ Generic Thermal Sysfs driver How To -========================= +=================================== Written by Sujith Thomas <sujith.thomas@intel.com>, Zhang Rui <rui.zhang@intel.com> @@ -10,20 +10,20 @@ Copyright (c) 2008 Intel Corporation 0. Introduction -The generic thermal sysfs provides a set of interfaces for thermal zone devices (sensors) -and thermal cooling devices (fan, processor...) to register with the thermal management -solution and to be a part of it. +The generic thermal sysfs provides a set of interfaces for thermal zone +devices (sensors) and thermal cooling devices (fan, processor...) to register +with the thermal management solution and to be a part of it. -This how-to focuses on enabling new thermal zone and cooling devices to participate -in thermal management. -This solution is platform independent and any type of thermal zone devices and -cooling devices should be able to make use of the infrastructure. +This how-to focuses on enabling new thermal zone and cooling devices to +participate in thermal management. +This solution is platform independent and any type of thermal zone devices +and cooling devices should be able to make use of the infrastructure. -The main task of the thermal sysfs driver is to expose thermal zone attributes as well -as cooling device attributes to the user space. -An intelligent thermal management application can make decisions based on inputs -from thermal zone attributes (the current temperature and trip point temperature) -and throttle appropriate devices. +The main task of the thermal sysfs driver is to expose thermal zone attributes +as well as cooling device attributes to the user space. +An intelligent thermal management application can make decisions based on +inputs from thermal zone attributes (the current temperature and trip point +temperature) and throttle appropriate devices. [0-*] denotes any positive number starting from 0 [1-*] denotes any positive number starting from 1 @@ -31,77 +31,77 @@ and throttle appropriate devices. 1. thermal sysfs driver interface functions 1.1 thermal zone device interface -1.1.1 struct thermal_zone_device *thermal_zone_device_register(char *name, int trips, - void *devdata, struct thermal_zone_device_ops *ops) - - This interface function adds a new thermal zone device (sensor) to - /sys/class/thermal folder as thermal_zone[0-*]. - It tries to bind all the thermal cooling devices registered at the same time. - - name: the thermal zone name. - trips: the total number of trip points this thermal zone supports. - devdata: device private data - ops: thermal zone device call-backs. - .bind: bind the thermal zone device with a thermal cooling device. - .unbind: unbind the thermal zone device with a thermal cooling device. - .get_temp: get the current temperature of the thermal zone. - .get_mode: get the current mode (user/kernel) of the thermal zone. - "kernel" means thermal management is done in kernel. - "user" will prevent kernel thermal driver actions upon trip points - so that user applications can take charge of thermal management. - .set_mode: set the mode (user/kernel) of the thermal zone. - .get_trip_type: get the type of certain trip point. - .get_trip_temp: get the temperature above which the certain trip point - will be fired. +1.1.1 struct thermal_zone_device *thermal_zone_device_register(char *name, + int trips, void *devdata, struct thermal_zone_device_ops *ops) + + This interface function adds a new thermal zone device (sensor) to + /sys/class/thermal folder as thermal_zone[0-*]. It tries to bind all the + thermal cooling devices registered at the same time. + + name: the thermal zone name. + trips: the total number of trip points this thermal zone supports. + devdata: device private data + ops: thermal zone device call-backs. + .bind: bind the thermal zone device with a thermal cooling device. + .unbind: unbind the thermal zone device with a thermal cooling device. + .get_temp: get the current temperature of the thermal zone. + .get_mode: get the current mode (user/kernel) of the thermal zone. + - "kernel" means thermal management is done in kernel. + - "user" will prevent kernel thermal driver actions upon trip points + so that user applications can take charge of thermal management. + .set_mode: set the mode (user/kernel) of the thermal zone. + .get_trip_type: get the type of certain trip point. + .get_trip_temp: get the temperature above which the certain trip point + will be fired. 1.1.2 void thermal_zone_device_unregister(struct thermal_zone_device *tz) - This interface function removes the thermal zone device. - It deletes the corresponding entry form /sys/class/thermal folder and unbind all - the thermal cooling devices it uses. + This interface function removes the thermal zone device. + It deletes the corresponding entry form /sys/class/thermal folder and + unbind all the thermal cooling devices it uses. 1.2 thermal cooling device interface 1.2.1 struct thermal_cooling_device *thermal_cooling_device_register(char *name, - void *devdata, struct thermal_cooling_device_ops *) - - This interface function adds a new thermal cooling device (fan/processor/...) to - /sys/class/thermal/ folder as cooling_device[0-*]. - It tries to bind itself to all the thermal zone devices register at the same time. - name: the cooling device name. - devdata: device private data. - ops: thermal cooling devices call-backs. - .get_max_state: get the Maximum throttle state of the cooling device. - .get_cur_state: get the Current throttle state of the cooling device. - .set_cur_state: set the Current throttle state of the cooling device. + void *devdata, struct thermal_cooling_device_ops *) + + This interface function adds a new thermal cooling device (fan/processor/...) + to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself + to all the thermal zone devices register at the same time. + name: the cooling device name. + devdata: device private data. + ops: thermal cooling devices call-backs. + .get_max_state: get the Maximum throttle state of the cooling device. + .get_cur_state: get the Current throttle state of the cooling device. + .set_cur_state: set the Current throttle state of the cooling device. 1.2.2 void thermal_cooling_device_unregister(struct thermal_cooling_device *cdev) - This interface function remove the thermal cooling device. - It deletes the corresponding entry form /sys/class/thermal folder and unbind - itself from all the thermal zone devices using it. + This interface function remove the thermal cooling device. + It deletes the corresponding entry form /sys/class/thermal folder and + unbind itself from all the thermal zone devices using it. 1.3 interface for binding a thermal zone device with a thermal cooling device 1.3.1 int thermal_zone_bind_cooling_device(struct thermal_zone_device *tz, - int trip, struct thermal_cooling_device *cdev); + int trip, struct thermal_cooling_device *cdev); - This interface function bind a thermal cooling device to the certain trip point - of a thermal zone device. - This function is usually called in the thermal zone device .bind callback. - tz: the thermal zone device - cdev: thermal cooling device - trip: indicates which trip point the cooling devices is associated with - in this thermal zone. + This interface function bind a thermal cooling device to the certain trip + point of a thermal zone device. + This function is usually called in the thermal zone device .bind callback. + tz: the thermal zone device + cdev: thermal cooling device + trip: indicates which trip point the cooling devices is associated with + in this thermal zone. 1.3.2 int thermal_zone_unbind_cooling_device(struct thermal_zone_device *tz, - int trip, struct thermal_cooling_device *cdev); + int trip, struct thermal_cooling_device *cdev); - This interface function unbind a thermal cooling device from the certain trip point - of a thermal zone device. - This function is usually called in the thermal zone device .unbind callback. - tz: the thermal zone device - cdev: thermal cooling device - trip: indicates which trip point the cooling devices is associated with - in this thermal zone. + This interface function unbind a thermal cooling device from the certain + trip point of a thermal zone device. This function is usually called in + the thermal zone device .unbind callback. + tz: the thermal zone device + cdev: thermal cooling device + trip: indicates which trip point the cooling devices is associated with + in this thermal zone. 2. sysfs attributes structure @@ -114,153 +114,166 @@ if hwmon is compiled in or built as a module. Thermal zone device sys I/F, created once it's registered: /sys/class/thermal/thermal_zone[0-*]: - |-----type: Type of the thermal zone - |-----temp: Current temperature - |-----mode: Working mode of the thermal zone - |-----trip_point_[0-*]_temp: Trip point temperature - |-----trip_point_[0-*]_type: Trip point type + |---type: Type of the thermal zone + |---temp: Current temperature + |---mode: Working mode of the thermal zone + |---trip_point_[0-*]_temp: Trip point temperature + |---trip_point_[0-*]_type: Trip point type Thermal cooling device sys I/F, created once it's registered: /sys/class/thermal/cooling_device[0-*]: - |-----type : Type of the cooling device(processor/fan/...) - |-----max_state: Maximum cooling state of the cooling device - |-----cur_state: Current cooling state of the cooling device + |---type: Type of the cooling device(processor/fan/...) + |---max_state: Maximum cooling state of the cooling device + |---cur_state: Current cooling state of the cooling device -These two dynamic attributes are created/removed in pairs. -They represent the relationship between a thermal zone and its associated cooling device. -They are created/removed for each -thermal_zone_bind_cooling_device/thermal_zone_unbind_cooling_device successful execution. +Then next two dynamic attributes are created/removed in pairs. They represent +the relationship between a thermal zone and its associated cooling device. +They are created/removed for each successful execution of +thermal_zone_bind_cooling_device/thermal_zone_unbind_cooling_device. -/sys/class/thermal/thermal_zone[0-*] - |-----cdev[0-*]: The [0-*]th cooling device in the current thermal zone - |-----cdev[0-*]_trip_point: Trip point that cdev[0-*] is associated with +/sys/class/thermal/thermal_zone[0-*]: + |---cdev[0-*]: [0-*]th cooling device in current thermal zone + |---cdev[0-*]_trip_point: Trip point that cdev[0-*] is associated with Besides the thermal zone device sysfs I/F and cooling device sysfs I/F, -the generic thermal driver also creates a hwmon sysfs I/F for each _type_ of -thermal zone device. E.g. the generic thermal driver registers one hwmon class device -and build the associated hwmon sysfs I/F for all the registered ACPI thermal zones. +the generic thermal driver also creates a hwmon sysfs I/F for each _type_ +of thermal zone device. E.g. the generic thermal driver registers one hwmon +class device and build the associated hwmon sysfs I/F for all the registered +ACPI thermal zones. + /sys/class/hwmon/hwmon[0-*]: - |-----name: The type of the thermal zone devices. - |-----temp[1-*]_input: The current temperature of thermal zone [1-*]. - |-----temp[1-*]_critical: The critical trip point of thermal zone [1-*]. + |---name: The type of the thermal zone devices + |---temp[1-*]_input: The current temperature of thermal zone [1-*] + |---temp[1-*]_critical: The critical trip point of thermal zone [1-*] + Please read Documentation/hwmon/sysfs-interface for additional information. *************************** * Thermal zone attributes * *************************** -type Strings which represent the thermal zone type. - This is given by thermal zone driver as part of registration. - Eg: "acpitz" indicates it's an ACPI thermal device. - In order to keep it consistent with hwmon sys attribute, - this should be a short, lowercase string, - not containing spaces nor dashes. - RO - Required - -temp Current temperature as reported by thermal zone (sensor) - Unit: millidegree Celsius - RO - Required - -mode One of the predefined values in [kernel, user] - This file gives information about the algorithm - that is currently managing the thermal zone. - It can be either default kernel based algorithm - or user space application. - RW - Optional - kernel = Thermal management in kernel thermal zone driver. - user = Preventing kernel thermal zone driver actions upon - trip points so that user application can take full - charge of the thermal management. - -trip_point_[0-*]_temp The temperature above which trip point will be fired - Unit: millidegree Celsius - RO - Optional - -trip_point_[0-*]_type Strings which indicate the type of the trip point - E.g. it can be one of critical, hot, passive, - active[0-*] for ACPI thermal zone. - RO - Optional - -cdev[0-*] Sysfs link to the thermal cooling device node where the sys I/F - for cooling device throttling control represents. - RO - Optional - -cdev[0-*]_trip_point The trip point with which cdev[0-*] is associated in this thermal zone - -1 means the cooling device is not associated with any trip point. - RO - Optional - -****************************** -* Cooling device attributes * -****************************** - -type String which represents the type of device - eg: For generic ACPI: this should be "Fan", - "Processor" or "LCD" - eg. For memory controller device on intel_menlow platform: - this should be "Memory controller" - RO - Required - -max_state The maximum permissible cooling state of this cooling device. - RO - Required - -cur_state The current cooling state of this cooling device. - the value can any integer numbers between 0 and max_state, - cur_state == 0 means no cooling - cur_state == max_state means the maximum cooling. - RW - Required +type + Strings which represent the thermal zone type. + This is given by thermal zone driver as part of registration. + E.g: "acpitz" indicates it's an ACPI thermal device. + In order to keep it consistent with hwmon sys attribute; this should + be a short, lowercase string, not containing spaces nor dashes. + RO, Required + +temp + Current temperature as reported by thermal zone (sensor). + Unit: millidegree Celsius + RO, Required + +mode + One of the predefined values in [kernel, user]. + This file gives information about the algorithm that is currently + managing the thermal zone. It can be either default kernel based + algorithm or user space application. + kernel = Thermal management in kernel thermal zone driver. + user = Preventing kernel thermal zone driver actions upon + trip points so that user application can take full + charge of the thermal management. + RW, Optional + +trip_point_[0-*]_temp + The temperature above which trip point will be fired. + Unit: millidegree Celsius + RO, Optional + +trip_point_[0-*]_type + Strings which indicate the type of the trip point. + E.g. it can be one of critical, hot, passive, active[0-*] for ACPI + thermal zone. + RO, Optional + +cdev[0-*] + Sysfs link to the thermal cooling device node where the sys I/F + for cooling device throttling control represents. + RO, Optional + +cdev[0-*]_trip_point + The trip point with which cdev[0-*] is associated in this thermal + zone; -1 means the cooling device is not associated with any trip + point. + RO, Optional + +passive + Attribute is only present for zones in which the passive cooling + policy is not supported by native thermal driver. Default is zero + and can be set to a temperature (in millidegrees) to enable a + passive trip point for the zone. Activation is done by polling with + an interval of 1 second. + Unit: millidegrees Celsius + RW, Optional + +***************************** +* Cooling device attributes * +***************************** + +type + String which represents the type of device, e.g: + - for generic ACPI: should be "Fan", "Processor" or "LCD" + - for memory controller device on intel_menlow platform: + should be "Memory controller". + RO, Required + +max_state + The maximum permissible cooling state of this cooling device. + RO, Required + +cur_state + The current cooling state of this cooling device. + The value can any integer numbers between 0 and max_state: + - cur_state == 0 means no cooling + - cur_state == max_state means the maximum cooling. + RW, Required 3. A simple implementation -ACPI thermal zone may support multiple trip points like critical/hot/passive/active. -If an ACPI thermal zone supports critical, passive, active[0] and active[1] at the same time, -it may register itself as a thermal_zone_device (thermal_zone1) with 4 trip points in all. -It has one processor and one fan, which are both registered as thermal_cooling_device. -If the processor is listed in _PSL method, and the fan is listed in _AL0 method, -the sys I/F structure will be built like this: +ACPI thermal zone may support multiple trip points like critical, hot, +passive, active. If an ACPI thermal zone supports critical, passive, +active[0] and active[1] at the same time, it may register itself as a +thermal_zone_device (thermal_zone1) with 4 trip points in all. +It has one processor and one fan, which are both registered as +thermal_cooling_device. + +If the processor is listed in _PSL method, and the fan is listed in _AL0 +method, the sys I/F structure will be built like this: /sys/class/thermal: |thermal_zone1: - |-----type: acpitz - |-----temp: 37000 - |-----mode: kernel - |-----trip_point_0_temp: 100000 - |-----trip_point_0_type: critical - |-----trip_point_1_temp: 80000 - |-----trip_point_1_type: passive - |-----trip_point_2_temp: 70000 - |-----trip_point_2_type: active0 - |-----trip_point_3_temp: 60000 - |-----trip_point_3_type: active1 - |-----cdev0: --->/sys/class/thermal/cooling_device0 - |-----cdev0_trip_point: 1 /* cdev0 can be used for passive */ - |-----cdev1: --->/sys/class/thermal/cooling_device3 - |-----cdev1_trip_point: 2 /* cdev1 can be used for active[0]*/ + |---type: acpitz + |---temp: 37000 + |---mode: kernel + |---trip_point_0_temp: 100000 + |---trip_point_0_type: critical + |---trip_point_1_temp: 80000 + |---trip_point_1_type: passive + |---trip_point_2_temp: 70000 + |---trip_point_2_type: active0 + |---trip_point_3_temp: 60000 + |---trip_point_3_type: active1 + |---cdev0: --->/sys/class/thermal/cooling_device0 + |---cdev0_trip_point: 1 /* cdev0 can be used for passive */ + |---cdev1: --->/sys/class/thermal/cooling_device3 + |---cdev1_trip_point: 2 /* cdev1 can be used for active[0]*/ |cooling_device0: - |-----type: Processor - |-----max_state: 8 - |-----cur_state: 0 + |---type: Processor + |---max_state: 8 + |---cur_state: 0 |cooling_device3: - |-----type: Fan - |-----max_state: 2 - |-----cur_state: 0 + |---type: Fan + |---max_state: 2 + |---cur_state: 0 /sys/class/hwmon: |hwmon0: - |-----name: acpitz - |-----temp1_input: 37000 - |-----temp1_crit: 100000 + |---name: acpitz + |---temp1_input: 37000 + |---temp1_crit: 100000 diff --git a/Documentation/trace/ftrace.txt b/Documentation/trace/ftrace.txt index 957b22fde2df..8179692fbb90 100644 --- a/Documentation/trace/ftrace.txt +++ b/Documentation/trace/ftrace.txt @@ -1231,6 +1231,7 @@ something like this simple program: #include <sys/stat.h> #include <fcntl.h> #include <unistd.h> +#include <string.h> #define _STR(x) #x #define STR(x) _STR(x) @@ -1265,6 +1266,7 @@ const char *find_debugfs(void) return NULL; } + strcat(debugfs, "/tracing/"); debugfs_found = 1; return debugfs; diff --git a/Documentation/vm/hwpoison.txt b/Documentation/vm/hwpoison.txt new file mode 100644 index 000000000000..3ffadf8da61f --- /dev/null +++ b/Documentation/vm/hwpoison.txt @@ -0,0 +1,136 @@ +What is hwpoison? + +Upcoming Intel CPUs have support for recovering from some memory errors +(``MCA recovery''). This requires the OS to declare a page "poisoned", +kill the processes associated with it and avoid using it in the future. + +This patchkit implements the necessary infrastructure in the VM. + +To quote the overview comment: + + * High level machine check handler. Handles pages reported by the + * hardware as being corrupted usually due to a 2bit ECC memory or cache + * failure. + * + * This focusses on pages detected as corrupted in the background. + * When the current CPU tries to consume corruption the currently + * running process can just be killed directly instead. This implies + * that if the error cannot be handled for some reason it's safe to + * just ignore it because no corruption has been consumed yet. Instead + * when that happens another machine check will happen. + * + * Handles page cache pages in various states. The tricky part + * here is that we can access any page asynchronous to other VM + * users, because memory failures could happen anytime and anywhere, + * possibly violating some of their assumptions. This is why this code + * has to be extremely careful. Generally it tries to use normal locking + * rules, as in get the standard locks, even if that means the + * error handling takes potentially a long time. + * + * Some of the operations here are somewhat inefficient and have non + * linear algorithmic complexity, because the data structures have not + * been optimized for this case. This is in particular the case + * for the mapping from a vma to a process. Since this case is expected + * to be rare we hope we can get away with this. + +The code consists of a the high level handler in mm/memory-failure.c, +a new page poison bit and various checks in the VM to handle poisoned +pages. + +The main target right now is KVM guests, but it works for all kinds +of applications. KVM support requires a recent qemu-kvm release. + +For the KVM use there was need for a new signal type so that +KVM can inject the machine check into the guest with the proper +address. This in theory allows other applications to handle +memory failures too. The expection is that near all applications +won't do that, but some very specialized ones might. + +--- + +There are two (actually three) modi memory failure recovery can be in: + +vm.memory_failure_recovery sysctl set to zero: + All memory failures cause a panic. Do not attempt recovery. + (on x86 this can be also affected by the tolerant level of the + MCE subsystem) + +early kill + (can be controlled globally and per process) + Send SIGBUS to the application as soon as the error is detected + This allows applications who can process memory errors in a gentle + way (e.g. drop affected object) + This is the mode used by KVM qemu. + +late kill + Send SIGBUS when the application runs into the corrupted page. + This is best for memory error unaware applications and default + Note some pages are always handled as late kill. + +--- + +User control: + +vm.memory_failure_recovery + See sysctl.txt + +vm.memory_failure_early_kill + Enable early kill mode globally + +PR_MCE_KILL + Set early/late kill mode/revert to system default + arg1: PR_MCE_KILL_CLEAR: Revert to system default + arg1: PR_MCE_KILL_SET: arg2 defines thread specific mode + PR_MCE_KILL_EARLY: Early kill + PR_MCE_KILL_LATE: Late kill + PR_MCE_KILL_DEFAULT: Use system global default +PR_MCE_KILL_GET + return current mode + + +--- + +Testing: + +madvise(MADV_POISON, ....) + (as root) + Poison a page in the process for testing + + +hwpoison-inject module through debugfs + /sys/debug/hwpoison/corrupt-pfn + +Inject hwpoison fault at PFN echoed into this file + + +Architecture specific MCE injector + +x86 has mce-inject, mce-test + +Some portable hwpoison test programs in mce-test, see blow. + +--- + +References: + +http://halobates.de/mce-lc09-2.pdf + Overview presentation from LinuxCon 09 + +git://git.kernel.org/pub/scm/utils/cpu/mce/mce-test.git + Test suite (hwpoison specific portable tests in tsrc) + +git://git.kernel.org/pub/scm/utils/cpu/mce/mce-inject.git + x86 specific injector + + +--- + +Limitations: + +- Not all page types are supported and never will. Most kernel internal +objects cannot be recovered, only LRU pages for now. +- Right now hugepage support is missing. + +--- +Andi Kleen, Oct 2009 + diff --git a/Documentation/vm/ksm.txt b/Documentation/vm/ksm.txt index 72a22f65960e..262d8e6793a3 100644 --- a/Documentation/vm/ksm.txt +++ b/Documentation/vm/ksm.txt @@ -52,15 +52,15 @@ The KSM daemon is controlled by sysfs files in /sys/kernel/mm/ksm/, readable by all but writable only by root: max_kernel_pages - set to maximum number of kernel pages that KSM may use - e.g. "echo 2000 > /sys/kernel/mm/ksm/max_kernel_pages" + e.g. "echo 100000 > /sys/kernel/mm/ksm/max_kernel_pages" Value 0 imposes no limit on the kernel pages KSM may use; but note that any process using MADV_MERGEABLE can cause KSM to allocate these pages, unswappable until it exits. - Default: 2000 (chosen for demonstration purposes) + Default: quarter of memory (chosen to not pin too much) pages_to_scan - how many present pages to scan before ksmd goes to sleep - e.g. "echo 200 > /sys/kernel/mm/ksm/pages_to_scan" - Default: 200 (chosen for demonstration purposes) + e.g. "echo 100 > /sys/kernel/mm/ksm/pages_to_scan" + Default: 100 (chosen for demonstration purposes) sleep_millisecs - how many milliseconds ksmd should sleep before next scan e.g. "echo 20 > /sys/kernel/mm/ksm/sleep_millisecs" @@ -70,7 +70,8 @@ run - set 0 to stop ksmd from running but keep merged pages, set 1 to run ksmd e.g. "echo 1 > /sys/kernel/mm/ksm/run", set 2 to stop ksmd and unmerge all pages currently merged, but leave mergeable areas registered for next run - Default: 1 (for immediate use by apps which register) + Default: 0 (must be changed to 1 to activate KSM, + except if CONFIG_SYSFS is disabled) The effectiveness of KSM and MADV_MERGEABLE is shown in /sys/kernel/mm/ksm/: @@ -86,4 +87,4 @@ pages_volatile embraces several different kinds of activity, but a high proportion there would also indicate poor use of madvise MADV_MERGEABLE. Izik Eidus, -Hugh Dickins, 30 July 2009 +Hugh Dickins, 24 Sept 2009 diff --git a/Documentation/vm/page-types.c b/Documentation/vm/page-types.c index fa1a30d9e9d5..4793c6aac733 100644 --- a/Documentation/vm/page-types.c +++ b/Documentation/vm/page-types.c @@ -2,7 +2,10 @@ * page-types: Tool for querying page flags * * Copyright (C) 2009 Intel corporation - * Copyright (C) 2009 Wu Fengguang <fengguang.wu@intel.com> + * + * Authors: Wu Fengguang <fengguang.wu@intel.com> + * + * Released under the General Public License (GPL). */ #define _LARGEFILE64_SOURCE @@ -69,7 +72,9 @@ #define KPF_COMPOUND_TAIL 16 #define KPF_HUGE 17 #define KPF_UNEVICTABLE 18 +#define KPF_HWPOISON 19 #define KPF_NOPAGE 20 +#define KPF_KSM 21 /* [32-] kernel hacking assistances */ #define KPF_RESERVED 32 @@ -116,7 +121,9 @@ static char *page_flag_names[] = { [KPF_COMPOUND_TAIL] = "T:compound_tail", [KPF_HUGE] = "G:huge", [KPF_UNEVICTABLE] = "u:unevictable", + [KPF_HWPOISON] = "X:hwpoison", [KPF_NOPAGE] = "n:nopage", + [KPF_KSM] = "x:ksm", [KPF_RESERVED] = "r:reserved", [KPF_MLOCKED] = "m:mlocked", @@ -152,9 +159,6 @@ static unsigned long opt_size[MAX_ADDR_RANGES]; static int nr_vmas; static unsigned long pg_start[MAX_VMAS]; static unsigned long pg_end[MAX_VMAS]; -static unsigned long voffset; - -static int pagemap_fd; #define MAX_BIT_FILTERS 64 static int nr_bit_filters; @@ -163,9 +167,16 @@ static uint64_t opt_bits[MAX_BIT_FILTERS]; static int page_size; -#define PAGES_BATCH (64 << 10) /* 64k pages */ +static int pagemap_fd; static int kpageflags_fd; +static int opt_hwpoison; +static int opt_unpoison; + +static char *hwpoison_debug_fs = "/debug/hwpoison"; +static int hwpoison_inject_fd; +static int hwpoison_forget_fd; + #define HASH_SHIFT 13 #define HASH_SIZE (1 << HASH_SHIFT) #define HASH_MASK (HASH_SIZE - 1) @@ -207,6 +218,74 @@ static void fatal(const char *x, ...) exit(EXIT_FAILURE); } +static int checked_open(const char *pathname, int flags) +{ + int fd = open(pathname, flags); + + if (fd < 0) { + perror(pathname); + exit(EXIT_FAILURE); + } + + return fd; +} + +/* + * pagemap/kpageflags routines + */ + +static unsigned long do_u64_read(int fd, char *name, + uint64_t *buf, + unsigned long index, + unsigned long count) +{ + long bytes; + + if (index > ULONG_MAX / 8) + fatal("index overflow: %lu\n", index); + + if (lseek(fd, index * 8, SEEK_SET) < 0) { + perror(name); + exit(EXIT_FAILURE); + } + + bytes = read(fd, buf, count * 8); + if (bytes < 0) { + perror(name); + exit(EXIT_FAILURE); + } + if (bytes % 8) + fatal("partial read: %lu bytes\n", bytes); + + return bytes / 8; +} + +static unsigned long kpageflags_read(uint64_t *buf, + unsigned long index, + unsigned long pages) +{ + return do_u64_read(kpageflags_fd, PROC_KPAGEFLAGS, buf, index, pages); +} + +static unsigned long pagemap_read(uint64_t *buf, + unsigned long index, + unsigned long pages) +{ + return do_u64_read(pagemap_fd, "/proc/pid/pagemap", buf, index, pages); +} + +static unsigned long pagemap_pfn(uint64_t val) +{ + unsigned long pfn; + + if (val & PM_PRESENT) + pfn = PM_PFRAME(val); + else + pfn = 0; + + return pfn; +} + /* * page flag names @@ -255,7 +334,8 @@ static char *page_flag_longname(uint64_t flags) * page list and summary */ -static void show_page_range(unsigned long offset, uint64_t flags) +static void show_page_range(unsigned long voffset, + unsigned long offset, uint64_t flags) { static uint64_t flags0; static unsigned long voff; @@ -281,7 +361,8 @@ static void show_page_range(unsigned long offset, uint64_t flags) count = 1; } -static void show_page(unsigned long offset, uint64_t flags) +static void show_page(unsigned long voffset, + unsigned long offset, uint64_t flags) { if (opt_pid) printf("%lx\t", voffset); @@ -362,6 +443,62 @@ static uint64_t well_known_flags(uint64_t flags) return flags; } +static uint64_t kpageflags_flags(uint64_t flags) +{ + flags = expand_overloaded_flags(flags); + + if (!opt_raw) + flags = well_known_flags(flags); + + return flags; +} + +/* + * page actions + */ + +static void prepare_hwpoison_fd(void) +{ + char buf[100]; + + if (opt_hwpoison && !hwpoison_inject_fd) { + sprintf(buf, "%s/corrupt-pfn", hwpoison_debug_fs); + hwpoison_inject_fd = checked_open(buf, O_WRONLY); + } + + if (opt_unpoison && !hwpoison_forget_fd) { + sprintf(buf, "%s/renew-pfn", hwpoison_debug_fs); + hwpoison_forget_fd = checked_open(buf, O_WRONLY); + } +} + +static int hwpoison_page(unsigned long offset) +{ + char buf[100]; + int len; + + len = sprintf(buf, "0x%lx\n", offset); + len = write(hwpoison_inject_fd, buf, len); + if (len < 0) { + perror("hwpoison inject"); + return len; + } + return 0; +} + +static int unpoison_page(unsigned long offset) +{ + char buf[100]; + int len; + + len = sprintf(buf, "0x%lx\n", offset); + len = write(hwpoison_forget_fd, buf, len); + if (len < 0) { + perror("hwpoison forget"); + return len; + } + return 0; +} /* * page frame walker @@ -394,104 +531,83 @@ static int hash_slot(uint64_t flags) exit(EXIT_FAILURE); } -static void add_page(unsigned long offset, uint64_t flags) +static void add_page(unsigned long voffset, + unsigned long offset, uint64_t flags) { - flags = expand_overloaded_flags(flags); - - if (!opt_raw) - flags = well_known_flags(flags); + flags = kpageflags_flags(flags); if (!bit_mask_ok(flags)) return; + if (opt_hwpoison) + hwpoison_page(offset); + if (opt_unpoison) + unpoison_page(offset); + if (opt_list == 1) - show_page_range(offset, flags); + show_page_range(voffset, offset, flags); else if (opt_list == 2) - show_page(offset, flags); + show_page(voffset, offset, flags); nr_pages[hash_slot(flags)]++; total_pages++; } -static void walk_pfn(unsigned long index, unsigned long count) +#define KPAGEFLAGS_BATCH (64 << 10) /* 64k pages */ +static void walk_pfn(unsigned long voffset, + unsigned long index, + unsigned long count) { + uint64_t buf[KPAGEFLAGS_BATCH]; unsigned long batch; - unsigned long n; + unsigned long pages; unsigned long i; - if (index > ULONG_MAX / KPF_BYTES) - fatal("index overflow: %lu\n", index); - - lseek(kpageflags_fd, index * KPF_BYTES, SEEK_SET); - while (count) { - uint64_t kpageflags_buf[KPF_BYTES * PAGES_BATCH]; - - batch = min_t(unsigned long, count, PAGES_BATCH); - n = read(kpageflags_fd, kpageflags_buf, batch * KPF_BYTES); - if (n == 0) + batch = min_t(unsigned long, count, KPAGEFLAGS_BATCH); + pages = kpageflags_read(buf, index, batch); + if (pages == 0) break; - if (n < 0) { - perror(PROC_KPAGEFLAGS); - exit(EXIT_FAILURE); - } - if (n % KPF_BYTES != 0) - fatal("partial read: %lu bytes\n", n); - n = n / KPF_BYTES; + for (i = 0; i < pages; i++) + add_page(voffset + i, index + i, buf[i]); - for (i = 0; i < n; i++) - add_page(index + i, kpageflags_buf[i]); - - index += batch; - count -= batch; + index += pages; + count -= pages; } } - -#define PAGEMAP_BATCH 4096 -static unsigned long task_pfn(unsigned long pgoff) +#define PAGEMAP_BATCH (64 << 10) +static void walk_vma(unsigned long index, unsigned long count) { - static uint64_t buf[PAGEMAP_BATCH]; - static unsigned long start; - static long count; - uint64_t pfn; + uint64_t buf[PAGEMAP_BATCH]; + unsigned long batch; + unsigned long pages; + unsigned long pfn; + unsigned long i; - if (pgoff < start || pgoff >= start + count) { - if (lseek64(pagemap_fd, - (uint64_t)pgoff * PM_ENTRY_BYTES, - SEEK_SET) < 0) { - perror("pagemap seek"); - exit(EXIT_FAILURE); - } - count = read(pagemap_fd, buf, sizeof(buf)); - if (count == 0) - return 0; - if (count < 0) { - perror("pagemap read"); - exit(EXIT_FAILURE); - } - if (count % PM_ENTRY_BYTES) { - fatal("pagemap read not aligned.\n"); - exit(EXIT_FAILURE); - } - count /= PM_ENTRY_BYTES; - start = pgoff; - } + while (count) { + batch = min_t(unsigned long, count, PAGEMAP_BATCH); + pages = pagemap_read(buf, index, batch); + if (pages == 0) + break; - pfn = buf[pgoff - start]; - if (pfn & PM_PRESENT) - pfn = PM_PFRAME(pfn); - else - pfn = 0; + for (i = 0; i < pages; i++) { + pfn = pagemap_pfn(buf[i]); + if (pfn) + walk_pfn(index + i, pfn, 1); + } - return pfn; + index += pages; + count -= pages; + } } static void walk_task(unsigned long index, unsigned long count) { - int i = 0; const unsigned long end = index + count; + unsigned long start; + int i = 0; while (index < end) { @@ -501,15 +617,11 @@ static void walk_task(unsigned long index, unsigned long count) if (pg_start[i] >= end) return; - voffset = max_t(unsigned long, pg_start[i], index); - index = min_t(unsigned long, pg_end[i], end); + start = max_t(unsigned long, pg_start[i], index); + index = min_t(unsigned long, pg_end[i], end); - assert(voffset < index); - for (; voffset < index; voffset++) { - unsigned long pfn = task_pfn(voffset); - if (pfn) - walk_pfn(pfn, 1); - } + assert(start < index); + walk_vma(start, index - start); } } @@ -527,18 +639,14 @@ static void walk_addr_ranges(void) { int i; - kpageflags_fd = open(PROC_KPAGEFLAGS, O_RDONLY); - if (kpageflags_fd < 0) { - perror(PROC_KPAGEFLAGS); - exit(EXIT_FAILURE); - } + kpageflags_fd = checked_open(PROC_KPAGEFLAGS, O_RDONLY); if (!nr_addr_ranges) add_addr_range(0, ULONG_MAX); for (i = 0; i < nr_addr_ranges; i++) if (!opt_pid) - walk_pfn(opt_offset[i], opt_size[i]); + walk_pfn(0, opt_offset[i], opt_size[i]); else walk_task(opt_offset[i], opt_size[i]); @@ -575,6 +683,8 @@ static void usage(void) " -l|--list Show page details in ranges\n" " -L|--list-each Show page details one by one\n" " -N|--no-summary Don't show summay info\n" +" -X|--hwpoison hwpoison pages\n" +" -x|--unpoison unpoison pages\n" " -h|--help Show this usage message\n" "addr-spec:\n" " N one page at offset N (unit: pages)\n" @@ -624,11 +734,7 @@ static void parse_pid(const char *str) opt_pid = parse_number(str); sprintf(buf, "/proc/%d/pagemap", opt_pid); - pagemap_fd = open(buf, O_RDONLY); - if (pagemap_fd < 0) { - perror(buf); - exit(EXIT_FAILURE); - } + pagemap_fd = checked_open(buf, O_RDONLY); sprintf(buf, "/proc/%d/maps", opt_pid); file = fopen(buf, "r"); @@ -788,6 +894,8 @@ static struct option opts[] = { { "list" , 0, NULL, 'l' }, { "list-each" , 0, NULL, 'L' }, { "no-summary", 0, NULL, 'N' }, + { "hwpoison" , 0, NULL, 'X' }, + { "unpoison" , 0, NULL, 'x' }, { "help" , 0, NULL, 'h' }, { NULL , 0, NULL, 0 } }; @@ -799,7 +907,7 @@ int main(int argc, char *argv[]) page_size = getpagesize(); while ((c = getopt_long(argc, argv, - "rp:f:a:b:lLNh", opts, NULL)) != -1) { + "rp:f:a:b:lLNXxh", opts, NULL)) != -1) { switch (c) { case 'r': opt_raw = 1; @@ -825,6 +933,14 @@ int main(int argc, char *argv[]) case 'N': opt_no_summary = 1; break; + case 'X': + opt_hwpoison = 1; + prepare_hwpoison_fd(); + break; + case 'x': + opt_unpoison = 1; + prepare_hwpoison_fd(); + break; case 'h': usage(); exit(0); @@ -844,7 +960,7 @@ int main(int argc, char *argv[]) walk_addr_ranges(); if (opt_list == 1) - show_page_range(0, 0); /* drain the buffer */ + show_page_range(0, 0, 0); /* drain the buffer */ if (opt_no_summary) return 0; diff --git a/Documentation/vm/pagemap.txt b/Documentation/vm/pagemap.txt index 600a304a828c..df09b9650a81 100644 --- a/Documentation/vm/pagemap.txt +++ b/Documentation/vm/pagemap.txt @@ -57,7 +57,9 @@ There are three components to pagemap: 16. COMPOUND_TAIL 16. HUGE 18. UNEVICTABLE + 19. HWPOISON 20. NOPAGE + 21. KSM Short descriptions to the page flags: @@ -86,9 +88,15 @@ Short descriptions to the page flags: 17. HUGE this is an integral part of a HugeTLB page +19. HWPOISON + hardware detected memory corruption on this page: don't touch the data! + 20. NOPAGE no page frame exists at the requested address +21. KSM + identical memory pages dynamically shared between one or more processes + [IO related page flags] 1. ERROR IO error occurred 3. UPTODATE page has up-to-date data diff --git a/MAINTAINERS b/MAINTAINERS index b2e3f3507ca3..808e4dfb34be 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -65,43 +65,51 @@ trivial patch so apply some common sense. 8. Happy hacking. - ----------------------------------- - -Maintainers List (try to look for most precise areas first) +Descriptions of section entries: + + P: Person (obsolete) + M: Mail patches to: FullName <address@domain> + L: Mailing list that is relevant to this area + W: Web-page with status/info + T: SCM tree type and location. Type is one of: git, hg, quilt, stgit. + S: Status, one of the following: + Supported: Someone is actually paid to look after this. + Maintained: Someone actually looks after it. + Odd Fixes: It has a maintainer but they don't have time to do + much other than throw the odd patch in. See below.. + Orphan: No current maintainer [but maybe you could take the + role as you write your new code]. + Obsolete: Old code. Something tagged obsolete generally means + it has been replaced by a better system and you + should be using that. + F: Files and directories with wildcard patterns. + A trailing slash includes all files and subdirectory files. + F: drivers/net/ all files in and below drivers/net + F: drivers/net/* all files in drivers/net, but not below + F: */net/* all files in "any top level directory"/net + One pattern per line. Multiple F: lines acceptable. + X: Files and directories that are NOT maintained, same rules as F: + Files exclusions are tested before file matches. + Can be useful for excluding a specific subdirectory, for instance: + F: net/ + X: net/ipv6/ + matches all files in and below net excluding net/ipv6/ + K: Keyword perl extended regex pattern to match content in a + patch or file. For instance: + K: of_get_profile + matches patches or files that contain "of_get_profile" + K: \b(printk|pr_(info|err))\b + matches patches or files that contain one or more of the words + printk, pr_info or pr_err + One regex pattern per line. Multiple K: lines acceptable. Note: For the hard of thinking, this list is meant to remain in alphabetical order. If you could add yourselves to it in alphabetical order that would be so much easier [Ed] -P: Person (obsolete) -M: Mail patches to: FullName <address@domain> -L: Mailing list that is relevant to this area -W: Web-page with status/info -T: SCM tree type and location. Type is one of: git, hg, quilt, stgit. -S: Status, one of the following: - - Supported: Someone is actually paid to look after this. - Maintained: Someone actually looks after it. - Odd Fixes: It has a maintainer but they don't have time to do - much other than throw the odd patch in. See below.. - Orphan: No current maintainer [but maybe you could take the - role as you write your new code]. - Obsolete: Old code. Something tagged obsolete generally means - it has been replaced by a better system and you - should be using that. +Maintainers List (try to look for most precise areas first) -F: Files and directories with wildcard patterns. - A trailing slash includes all files and subdirectory files. - F: drivers/net/ all files in and below drivers/net - F: drivers/net/* all files in drivers/net, but not below - F: */net/* all files in "any top level directory"/net - One pattern per line. Multiple F: lines acceptable. -X: Files and directories that are NOT maintained, same rules as F: - Files exclusions are tested before file matches. - Can be useful for excluding a specific subdirectory, for instance: - F: net/ - X: net/ipv6/ - matches all files in and below net excluding net/ipv6/ + ----------------------------------- 3C505 NETWORK DRIVER M: Philip Blundell <philb@gnu.org> @@ -174,7 +182,7 @@ M: Ron Minnich <rminnich@sandia.gov> M: Latchesar Ionkov <lucho@ionkov.net> L: v9fs-developer@lists.sourceforge.net W: http://swik.net/v9fs -T: git git://git.kernel.org/pub/scm/linux/kernel/ericvh/v9fs.git +T: git git://git.kernel.org/pub/scm/linux/kernel/git/ericvh/v9fs.git S: Maintained F: Documentation/filesystems/9p.txt F: fs/9p/ @@ -577,6 +585,11 @@ M: Mike Rapoport <mike@compulab.co.il> L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained +ARM/CONTEC MICRO9 MACHINE SUPPORT +M: Hubert Feurstein <hubert.feurstein@contec.at> +S: Maintained +F: arch/arm/mach-ep93xx/micro9.c + ARM/CORGI MACHINE SUPPORT M: Richard Purdie <rpurdie@rpsys.net> S: Maintained @@ -893,7 +906,6 @@ M: Karol Kozimor <sziwan@users.sourceforge.net> L: acpi4asus-user@lists.sourceforge.net W: http://acpi4asus.sf.net S: Maintained -F: arch/x86/kernel/acpi/boot.c F: drivers/platform/x86/asus_acpi.c ASUS ASB100 HARDWARE MONITOR DRIVER @@ -987,7 +999,7 @@ F: drivers/net/atlx/ ATM M: Chas Williams <chas@cmf.nrl.navy.mil> -L: linux-atm-general@lists.sourceforge.net (subscribers-only) +L: linux-atm-general@lists.sourceforge.net (moderated for non-subscribers) L: netdev@vger.kernel.org W: http://linux-atm.sourceforge.net S: Maintained @@ -1230,6 +1242,12 @@ L: netdev@vger.kernel.org S: Supported F: drivers/net/tg3.* +BROCADE BFA FC SCSI DRIVER +M: Jing Huang <huangj@brocade.com> +L: linux-scsi@vger.kernel.org +S: Supported +F: drivers/scsi/bfa/ + BSG (block layer generic sg v4 driver) M: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> L: linux-scsi@vger.kernel.org @@ -1467,6 +1485,7 @@ F: mm/*cgroup* CORETEMP HARDWARE MONITORING DRIVER M: Rudolf Marek <r.marek@assembler.cz> +M: Huaxu Wan <huaxu.wan@intel.com> L: lm-sensors@lm-sensors.org S: Maintained F: Documentation/hwmon/coretemp @@ -2057,7 +2076,7 @@ S: Maintained F: fs/* FINTEK F75375S HARDWARE MONITOR AND FAN CONTROLLER DRIVER -M: Riku Voipio <riku.vipio@iki.fi> +M: Riku Voipio <riku.voipio@iki.fi> L: lm-sensors@lm-sensors.org S: Maintained F: drivers/hwmon/f75375s.c @@ -2138,7 +2157,7 @@ S: Supported F: arch/powerpc/sysdev/qe_lib/ F: arch/powerpc/include/asm/*qe.h -FREESCALE USB PERIPHERIAL DRIVERS +FREESCALE USB PERIPHERAL DRIVERS M: Li Yang <leoli@freescale.com> L: linux-usb@vger.kernel.org L: linuxppc-dev@ozlabs.org @@ -2189,18 +2208,6 @@ F: Documentation/filesystems/caching/ F: fs/fscache/ F: include/linux/fscache*.h -TRACING -M: Steven Rostedt <rostedt@goodmis.org> -M: Frederic Weisbecker <fweisbec@gmail.com> -M: Ingo Molnar <mingo@redhat.com> -T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip.git tracing/core -S: Maintained -F: Documentation/trace/ftrace.txt -F: arch/*/*/*/ftrace.h -F: arch/*/kernel/ftrace.c -F: include/*/ftrace.h include/trace/ include/linux/trace*.h -F: kernel/trace/ - FUJITSU FR-V (FRV) PORT M: David Howells <dhowells@redhat.com> S: Maintained @@ -2259,9 +2266,8 @@ S: Maintained F: include/asm-generic GENERIC UIO DRIVER FOR PCI DEVICES -M: Michael S. Tsirkin <mst@redhat.com> +M: "Michael S. Tsirkin" <mst@redhat.com> L: kvm@vger.kernel.org -L: linux-kernel@vger.kernel.org S: Supported F: drivers/uio/uio_pci_generic.c @@ -2602,6 +2608,7 @@ L: linux1394-devel@lists.sourceforge.net W: http://www.linux1394.org/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/ieee1394/linux1394-2.6.git S: Maintained +F: Documentation/debugging-via-ohci1394.txt F: drivers/ieee1394/ IEEE 1394 RAW I/O DRIVER @@ -2815,7 +2822,7 @@ F: drivers/infiniband/hw/ipath/ IPMI SUBSYSTEM M: Corey Minyard <minyard@acm.org> -L: openipmi-developer@lists.sourceforge.net +L: openipmi-developer@lists.sourceforge.net (moderated for non-subscribers) W: http://openipmi.sourceforge.net/ S: Supported F: Documentation/IPMI.txt @@ -2990,8 +2997,8 @@ F: scripts/Makefile.* KERNEL JANITORS L: kernel-janitors@vger.kernel.org -W: http://www.kerneljanitors.org/ -S: Maintained +W: http://janitor.kernelnewbies.org/ +S: Odd Fixes KERNEL NFSD, SUNRPC, AND LOCKD SERVERS M: "J. Bruce Fields" <bfields@fieldses.org> @@ -3076,9 +3083,13 @@ F: kernel/kgdb.c KMEMCHECK M: Vegard Nossum <vegardno@ifi.uio.no> -P Pekka Enberg -M: penberg@cs.helsinki.fi +M: Pekka Enberg <penberg@cs.helsinki.fi> S: Maintained +F: Documentation/kmemcheck.txt +F: arch/x86/include/asm/kmemcheck.h +F: arch/x86/mm/kmemcheck/ +F: include/linux/kmemcheck.h +F: mm/kmemcheck.c KMEMLEAK M: Catalin Marinas <catalin.marinas@arm.com> @@ -3608,7 +3619,7 @@ L: netfilter@vger.kernel.org L: coreteam@netfilter.org W: http://www.netfilter.org/ W: http://www.iptables.org/ -T: git://git.kernel.org/pub/scm/linux/kernel/git/kaber/nf-2.6.git +T: git git://git.kernel.org/pub/scm/linux/kernel/git/kaber/nf-2.6.git S: Supported F: include/linux/netfilter* F: include/linux/netfilter/ @@ -3772,7 +3783,7 @@ F: drivers/video/riva/ F: drivers/video/nvidia/ OMAP SUPPORT -M: "Tony Lindgren <tony@atomide.com>" <tony@atomide.com> +M: Tony Lindgren <tony@atomide.com> L: linux-omap@vger.kernel.org W: http://www.muru.com/linux/omap/ W: http://linux.omap.com/ @@ -3877,6 +3888,15 @@ S: Maintained F: Documentation/i2c/busses/i2c-ocores F: drivers/i2c/busses/i2c-ocores.c +OPEN FIRMWARE AND FLATTENED DEVICE TREE +M: Grant Likely <grant.likely@secretlab.ca> +L: devicetree-discuss@lists.ozlabs.org +W: http://fdt.secretlab.ca +S: Maintained +F: drivers/of +F: include/linux/of*.h +K: of_get_property + OPROFILE M: Robert Richter <robert.richter@amd.com> L: oprofile-list@lists.sf.net @@ -3981,6 +4001,7 @@ F: drivers/block/paride/ PARISC ARCHITECTURE M: Kyle McMartin <kyle@mcmartin.ca> M: Helge Deller <deller@gmx.de> +M: "James E.J. Bottomley" <jejb@parisc-linux.org> L: linux-parisc@vger.kernel.org W: http://www.parisc-linux.org/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/kyle/parisc-2.6.git @@ -4064,6 +4085,13 @@ M: Peter Zijlstra <a.p.zijlstra@chello.nl> M: Paul Mackerras <paulus@samba.org> M: Ingo Molnar <mingo@elte.hu> S: Supported +F: kernel/perf_event.c +F: include/linux/perf_event.h +F: arch/*/*/kernel/perf_event.c +F: arch/*/include/asm/perf_event.h +F: arch/*/lib/perf_event.c +F: arch/*/kernel/perf_callchain.c +F: tools/perf/ PERSONALITY HANDLING M: Christoph Hellwig <hch@infradead.org> @@ -4515,12 +4543,11 @@ F: kernel/sched* F: include/linux/sched.h SCORE ARCHITECTURE -P: Chen Liqin -M: liqin.chen@sunplusct.com -P: Lennox Wu -M: lennox.wu@gmail.com +M: Chen Liqin <liqin.chen@sunplusct.com> +M: Lennox Wu <lennox.wu@gmail.com> W: http://www.sunplusct.com S: Supported +F: arch/score/ SCSI CDROM DRIVER M: Jens Axboe <axboe@kernel.dk> @@ -4593,27 +4620,27 @@ S: Maintained F: drivers/mmc/host/sdricoh_cs.c SECURE DIGITAL HOST CONTROLLER INTERFACE (SDHCI) DRIVER -S: Orphan -L: linux-mmc@vger.kernel.org -F: drivers/mmc/host/sdhci.* +S: Orphan +L: linux-mmc@vger.kernel.org +F: drivers/mmc/host/sdhci.* SECURE DIGITAL HOST CONTROLLER INTERFACE, OPEN FIRMWARE BINDINGS (SDHCI-OF) M: Anton Vorontsov <avorontsov@ru.mvista.com> L: linuxppc-dev@ozlabs.org -L: linux-mmc@vger.kernel.org +L: linux-mmc@vger.kernel.org S: Maintained -F: drivers/mmc/host/sdhci-of.* +F: drivers/mmc/host/sdhci-of.* SECURE DIGITAL HOST CONTROLLER INTERFACE (SDHCI) SAMSUNG DRIVER M: Ben Dooks <ben-linux@fluff.org> -L: linux-mmc@vger.kernel.org +L: linux-mmc@vger.kernel.org S: Maintained F: drivers/mmc/host/sdhci-s3c.c SECURITY SUBSYSTEM M: James Morris <jmorris@namei.org> L: linux-security-module@vger.kernel.org (suggested Cc:) -T: git git://www.kernel.org/pub/scm/linux/kernel/git/jmorris/security-testing-2.6.git +T: git git://git.kernel.org/pub/scm/linux/kernel/git/jmorris/security-testing-2.6.git W: http://security.wiki.kernel.org/ S: Supported F: security/ @@ -4648,6 +4675,13 @@ F: drivers/ata/ F: include/linux/ata.h F: include/linux/libata.h +SERVER ENGINES 10Gbps iSCSI - BladeEngine 2 DRIVER +M: Jayamohan Kallickal <jayamohank@serverengines.com> +L: linux-scsi@vger.kernel.org +W: http://www.serverengines.com +S: Supported +F: drivers/scsi/be2iscsi/ + SERVER ENGINES 10Gbps NIC - BladeEngine 2 DRIVER M: Sathya Perla <sathyap@serverengines.com> M: Subbu Seetharaman <subbus@serverengines.com> @@ -4701,8 +4735,7 @@ F: drivers/usb/gadget/lh7a40* F: drivers/usb/host/ohci-lh7a40* SIMPLE FIRMWARE INTERFACE (SFI) -P: Len Brown -M: lenb@kernel.org +M: Len Brown <lenb@kernel.org> L: sfi-devel@simplefirmware.org W: http://simplefirmware.org/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux-sfi-2.6.git @@ -5150,6 +5183,20 @@ L: tpmdd-devel@lists.sourceforge.net (moderated for non-subscribers) S: Maintained F: drivers/char/tpm/ +TRACING +M: Steven Rostedt <rostedt@goodmis.org> +M: Frederic Weisbecker <fweisbec@gmail.com> +M: Ingo Molnar <mingo@redhat.com> +T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip.git tracing/core +S: Maintained +F: Documentation/trace/ftrace.txt +F: arch/*/*/*/ftrace.h +F: arch/*/kernel/ftrace.c +F: include/*/ftrace.h +F: include/linux/trace*.h +F: include/trace/ +F: kernel/trace/ + TRIVIAL PATCHES M: Jiri Kosina <trivial@kernel.org> T: git git://git.kernel.org/pub/scm/linux/kernel/git/jikos/trivial.git @@ -5639,11 +5686,11 @@ F: drivers/vlynq/vlynq.c F: include/linux/vlynq.h VMWARE VMXNET3 ETHERNET DRIVER -M: Shreyas Bhatewara <sbhatewara@vmware.com> -M: VMware, Inc. <pv-drivers@vmware.com> -L: netdev@vger.kernel.org -S: Maintained -F: drivers/net/vmxnet3/ +M: Shreyas Bhatewara <sbhatewara@vmware.com> +M: "VMware, Inc." <pv-drivers@vmware.com> +L: netdev@vger.kernel.org +S: Maintained +F: drivers/net/vmxnet3/ VOLTAGE AND CURRENT REGULATOR FRAMEWORK M: Liam Girdwood <lrg@slimlogic.co.uk> @@ -5716,8 +5763,7 @@ S: Maintained F: drivers/scsi/wd7000.c WINBOND CIR DRIVER -P: David Hrdeman -M: david@hardeman.nu +M: David Härdeman <david@hardeman.nu> S: Maintained F: drivers/input/misc/winbond-cir.c @@ -5774,9 +5820,7 @@ F: drivers/input/touchscreen/*wm97* F: include/linux/wm97xx.h WOLFSON MICROELECTRONICS PMIC DRIVERS -P: Mark Brown -M: broonie@opensource.wolfsonmicro.com -L: linux-kernel@vger.kernel.org +M: Mark Brown <broonie@opensource.wolfsonmicro.com> T: git git://opensource.wolfsonmicro.com/linux-2.6-audioplus W: http://opensource.wolfsonmicro.com/node/8 S: Supported @@ -1,7 +1,7 @@ VERSION = 2 PATCHLEVEL = 6 SUBLEVEL = 32 -EXTRAVERSION = -rc3 +EXTRAVERSION = -rc7 NAME = Man-Eating Seals of Antiquity # *DOCUMENTATION* @@ -179,46 +179,9 @@ SUBARCH := $(shell uname -m | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ \ # Alternatively CROSS_COMPILE can be set in the environment. # Default value for CROSS_COMPILE is not to prefix executables # Note: Some architectures assign CROSS_COMPILE in their arch/*/Makefile -# -# To force ARCH and CROSS_COMPILE settings include kernel.* files -# in the kernel tree - do not patch this file. export KBUILD_BUILDHOST := $(SUBARCH) - -# Kbuild save the ARCH and CROSS_COMPILE setting in kernel.* files. -# Restore these settings and check that user did not specify -# conflicting values. - -saved_arch := $(shell cat include/generated/kernel.arch 2> /dev/null) -saved_cross := $(shell cat include/generated/kernel.cross 2> /dev/null) - -ifneq ($(CROSS_COMPILE),) - ifneq ($(saved_cross),) - ifneq ($(CROSS_COMPILE),$(saved_cross)) - $(error CROSS_COMPILE changed from \ - "$(saved_cross)" to \ - to "$(CROSS_COMPILE)". \ - Use "make mrproper" to fix it up) - endif - endif -else - CROSS_COMPILE := $(saved_cross) -endif - -ifneq ($(ARCH),) - ifneq ($(saved_arch),) - ifneq ($(saved_arch),$(ARCH)) - $(error ARCH changed from \ - "$(saved_arch)" to "$(ARCH)". \ - Use "make mrproper" to fix it up) - endif - endif -else - ifneq ($(saved_arch),) - ARCH := $(saved_arch) - else - ARCH := $(SUBARCH) - endif -endif +ARCH ?= $(SUBARCH) +CROSS_COMPILE ?= # Architecture as present in compile.h UTS_MACHINE := $(ARCH) @@ -258,7 +221,7 @@ CONFIG_SHELL := $(shell if [ -x "$$BASH" ]; then echo $$BASH; \ HOSTCC = gcc HOSTCXX = g++ -HOSTCFLAGS = -Wall -Wstrict-prototypes -O2 -fomit-frame-pointer +HOSTCFLAGS = -Wall -Wmissing-prototypes -Wstrict-prototypes -O2 -fomit-frame-pointer HOSTCXXFLAGS = -O2 # Decide whether to build built-in, modular, or both. @@ -483,11 +446,6 @@ ifeq ($(config-targets),1) include $(srctree)/arch/$(SRCARCH)/Makefile export KBUILD_DEFCONFIG KBUILD_KCONFIG -# save ARCH & CROSS_COMPILE settings -$(shell mkdir -p include/generated && \ - echo $(ARCH) > include/generated/kernel.arch && \ - echo $(CROSS_COMPILE) > include/generated/kernel.cross) - config: scripts_basic outputmakefile FORCE $(Q)mkdir -p include/linux include/config $(Q)$(MAKE) $(build)=scripts/kconfig $@ diff --git a/arch/alpha/boot/tools/objstrip.c b/arch/alpha/boot/tools/objstrip.c index 9d0727d18aee..367d53d031fc 100644 --- a/arch/alpha/boot/tools/objstrip.c +++ b/arch/alpha/boot/tools/objstrip.c @@ -35,7 +35,7 @@ const char * prog_name; -void +static void usage (void) { fprintf(stderr, diff --git a/arch/alpha/include/asm/fcntl.h b/arch/alpha/include/asm/fcntl.h index e42823e954aa..25da0017ec87 100644 --- a/arch/alpha/include/asm/fcntl.h +++ b/arch/alpha/include/asm/fcntl.h @@ -26,8 +26,6 @@ #define F_GETOWN 6 /* for sockets. */ #define F_SETSIG 10 /* for sockets. */ #define F_GETSIG 11 /* for sockets. */ -#define F_SETOWN_EX 12 -#define F_GETOWN_EX 13 /* for posix fcntl() and lockf() */ #define F_RDLCK 1 diff --git a/arch/alpha/include/asm/thread_info.h b/arch/alpha/include/asm/thread_info.h index 5076a8860b18..815680b585ed 100644 --- a/arch/alpha/include/asm/thread_info.h +++ b/arch/alpha/include/asm/thread_info.h @@ -50,12 +50,12 @@ struct thread_info { register struct thread_info *__current_thread_info __asm__("$8"); #define current_thread_info() __current_thread_info +#endif /* __ASSEMBLY__ */ + /* Thread information allocation. */ #define THREAD_SIZE_ORDER 1 #define THREAD_SIZE (2*PAGE_SIZE) -#endif /* __ASSEMBLY__ */ - #define PREEMPT_ACTIVE 0x40000000 /* diff --git a/arch/arm/configs/ams_delta_defconfig b/arch/arm/configs/ams_delta_defconfig index 764732529ea3..e8f7380b67d6 100644 --- a/arch/arm/configs/ams_delta_defconfig +++ b/arch/arm/configs/ams_delta_defconfig @@ -55,10 +55,10 @@ CONFIG_BLK_DEV_INITRD=y CONFIG_INITRAMFS_SOURCE="" CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y -# CONFIG_EMBEDDED is not set +CONFIG_EMBEDDED=y CONFIG_UID16=y CONFIG_SYSCTL_SYSCALL=y -CONFIG_KALLSYMS=y +# CONFIG_KALLSYMS is not set # CONFIG_KALLSYMS_ALL is not set # CONFIG_KALLSYMS_EXTRA_PASS is not set CONFIG_HOTPLUG=y @@ -224,7 +224,7 @@ CONFIG_CPU_CP15_MMU=y # # Processor Features # -# CONFIG_ARM_THUMB is not set +CONFIG_ARM_THUMB=y # CONFIG_CPU_ICACHE_DISABLE is not set # CONFIG_CPU_DCACHE_DISABLE is not set CONFIG_CPU_DCACHE_WRITETHROUGH=y @@ -248,7 +248,7 @@ CONFIG_CPU_DCACHE_WRITETHROUGH=y # CONFIG_HIGH_RES_TIMERS is not set CONFIG_PREEMPT=y CONFIG_HZ=100 -# CONFIG_AEABI is not set +CONFIG_AEABI=y # CONFIG_ARCH_DISCONTIGMEM_ENABLE is not set CONFIG_SELECT_MEMORY_MODEL=y CONFIG_FLATMEM_MANUAL=y @@ -299,7 +299,9 @@ CONFIG_BINFMT_ELF=y # # Power management options # -# CONFIG_PM is not set +CONFIG_PM=y +# CONFIG_SUSPEND is not set +CONFIG_PM_RUNTIME=y # # Networking @@ -670,7 +672,7 @@ CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024 CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768 # CONFIG_INPUT_JOYDEV is not set # CONFIG_INPUT_TSDEV is not set -# CONFIG_INPUT_EVDEV is not set +CONFIG_INPUT_EVDEV=y # CONFIG_INPUT_EVBUG is not set # @@ -784,6 +786,7 @@ CONFIG_I2C_OMAP=y # # CONFIG_SPI is not set # CONFIG_SPI_MASTER is not set +CONFIG_GPIO_SYSFS=y # # Dallas's 1-wire bus @@ -820,6 +823,7 @@ CONFIG_LEDS_AMS_DELTA=y CONFIG_LEDS_TRIGGERS=y CONFIG_LEDS_TRIGGER_TIMER=y CONFIG_LEDS_TRIGGER_HEARTBEAT=y +CONFIG_LEDS_TRIGGER_DEFAULT_ON=y # # Multimedia devices @@ -896,7 +900,13 @@ CONFIG_LOGO_LINUX_CLUT224=y # # Sound # -# CONFIG_SOUND is not set +CONFIG_SOUND=y +CONFIG_SND=y +CONFIG_SND_MIXER_OSS=y +CONFIG_SND_PCM_OSS=y +CONFIG_SND_SOC=y +CONFIG_SND_OMAP_SOC=y +CONFIG_SND_OMAP_SOC_AMS_DELTA=y # # HID Devices diff --git a/arch/arm/configs/kirkwood_defconfig b/arch/arm/configs/kirkwood_defconfig index af74cc2de8b6..bcfade33bca9 100644 --- a/arch/arm/configs/kirkwood_defconfig +++ b/arch/arm/configs/kirkwood_defconfig @@ -1,15 +1,13 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc4 -# Mon May 4 11:58:57 2009 +# Linux kernel version: 2.6.32-rc6 +# Sat Nov 7 20:31:18 2009 # CONFIG_ARM=y CONFIG_SYS_SUPPORTS_APM_EMULATION=y CONFIG_GENERIC_GPIO=y CONFIG_GENERIC_TIME=y CONFIG_GENERIC_CLOCKEVENTS=y -CONFIG_MMU=y -# CONFIG_NO_IOPORT is not set CONFIG_GENERIC_HARDIRQS=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -18,13 +16,12 @@ CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_HARDIRQS_SW_RESEND=y CONFIG_GENERIC_IRQ_PROBE=y CONFIG_RWSEM_GENERIC_SPINLOCK=y -# CONFIG_ARCH_HAS_ILOG2_U32 is not set -# CONFIG_ARCH_HAS_ILOG2_U64 is not set CONFIG_GENERIC_HWEIGHT=y CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y CONFIG_VECTORS_BASE=0xffff0000 CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -46,11 +43,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=19 # CONFIG_GROUP_SCHED is not set @@ -73,7 +71,6 @@ CONFIG_SYSCTL_SYSCALL=y CONFIG_KALLSYMS=y # CONFIG_KALLSYMS_ALL is not set # CONFIG_KALLSYMS_EXTRA_PASS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -86,6 +83,10 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y + +# +# Kernel Performance Events And Counters +# CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y @@ -95,13 +96,17 @@ CONFIG_SLUB=y # CONFIG_SLOB is not set CONFIG_PROFILING=y CONFIG_TRACEPOINTS=y -# CONFIG_MARKERS is not set CONFIG_OPROFILE=y CONFIG_HAVE_OPROFILE=y CONFIG_KPROBES=y CONFIG_KRETPROBES=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y + +# +# GCOV-based kernel profiling +# +# CONFIG_GCOV_KERNEL is not set # CONFIG_SLOW_WORK is not set CONFIG_HAVE_GENERIC_DMA_COHERENT=y CONFIG_SLABINFO=y @@ -114,7 +119,7 @@ CONFIG_MODULE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -135,19 +140,22 @@ CONFIG_DEFAULT_IOSCHED="cfq" # # System Type # +CONFIG_MMU=y # CONFIG_ARCH_AAEC2000 is not set # CONFIG_ARCH_INTEGRATOR is not set # CONFIG_ARCH_REALVIEW is not set # CONFIG_ARCH_VERSATILE is not set # CONFIG_ARCH_AT91 is not set # CONFIG_ARCH_CLPS711X is not set +# CONFIG_ARCH_GEMINI is not set # CONFIG_ARCH_EBSA110 is not set # CONFIG_ARCH_EP93XX is not set -# CONFIG_ARCH_GEMINI is not set # CONFIG_ARCH_FOOTBRIDGE is not set +# CONFIG_ARCH_MXC is not set +# CONFIG_ARCH_STMP3XXX is not set # CONFIG_ARCH_NETX is not set # CONFIG_ARCH_H720X is not set -# CONFIG_ARCH_IMX is not set +# CONFIG_ARCH_NOMADIK is not set # CONFIG_ARCH_IOP13XX is not set # CONFIG_ARCH_IOP32X is not set # CONFIG_ARCH_IOP33X is not set @@ -156,25 +164,27 @@ CONFIG_DEFAULT_IOSCHED="cfq" # CONFIG_ARCH_IXP4XX is not set # CONFIG_ARCH_L7200 is not set CONFIG_ARCH_KIRKWOOD=y -# CONFIG_ARCH_KS8695 is not set -# CONFIG_ARCH_NS9XXX is not set # CONFIG_ARCH_LOKI is not set # CONFIG_ARCH_MV78XX0 is not set -# CONFIG_ARCH_MXC is not set # CONFIG_ARCH_ORION5X is not set +# CONFIG_ARCH_MMP is not set +# CONFIG_ARCH_KS8695 is not set +# CONFIG_ARCH_NS9XXX is not set +# CONFIG_ARCH_W90X900 is not set # CONFIG_ARCH_PNX4008 is not set # CONFIG_ARCH_PXA is not set -# CONFIG_ARCH_MMP is not set +# CONFIG_ARCH_MSM is not set # CONFIG_ARCH_RPC is not set # CONFIG_ARCH_SA1100 is not set # CONFIG_ARCH_S3C2410 is not set # CONFIG_ARCH_S3C64XX is not set +# CONFIG_ARCH_S5PC1XX is not set # CONFIG_ARCH_SHARK is not set # CONFIG_ARCH_LH7A40X is not set +# CONFIG_ARCH_U300 is not set # CONFIG_ARCH_DAVINCI is not set # CONFIG_ARCH_OMAP is not set -# CONFIG_ARCH_MSM is not set -# CONFIG_ARCH_W90X900 is not set +# CONFIG_ARCH_BCMRING is not set # # Marvell Kirkwood Implementations @@ -185,6 +195,7 @@ CONFIG_MACH_RD88F6281=y CONFIG_MACH_MV88F6281GTW_GE=y CONFIG_MACH_SHEEVAPLUG=y CONFIG_MACH_TS219=y +CONFIG_MACH_OPENRD_BASE=y CONFIG_PLAT_ORION=y # @@ -195,7 +206,7 @@ CONFIG_CPU_FEROCEON=y # CONFIG_CPU_FEROCEON_OLD_ID is not set CONFIG_CPU_32v5=y CONFIG_CPU_ABRT_EV5T=y -CONFIG_CPU_PABRT_NOIFAR=y +CONFIG_CPU_PABRT_LEGACY=y CONFIG_CPU_CACHE_VIVT=y CONFIG_CPU_COPY_FEROCEON=y CONFIG_CPU_TLB_FEROCEON=y @@ -211,6 +222,7 @@ CONFIG_ARM_THUMB=y CONFIG_OUTER_CACHE=y CONFIG_CACHE_FEROCEON_L2=y # CONFIG_CACHE_FEROCEON_L2_WRITETHROUGH is not set +CONFIG_ARM_L1_CACHE_SHIFT=5 # # Bus support @@ -235,11 +247,12 @@ CONFIG_VMSPLIT_3G=y # CONFIG_VMSPLIT_2G is not set # CONFIG_VMSPLIT_1G is not set CONFIG_PAGE_OFFSET=0xC0000000 +# CONFIG_PREEMPT_NONE is not set +# CONFIG_PREEMPT_VOLUNTARY is not set CONFIG_PREEMPT=y CONFIG_HZ=100 CONFIG_AEABI=y # CONFIG_OABI_COMPAT is not set -CONFIG_ARCH_FLATMEM_HAS_HOLES=y # CONFIG_ARCH_SPARSEMEM_DEFAULT is not set # CONFIG_ARCH_SELECT_MEMORY_MODEL is not set # CONFIG_HIGHMEM is not set @@ -254,10 +267,12 @@ CONFIG_SPLIT_PTLOCK_CPUS=4096 # CONFIG_PHYS_ADDR_T_64BIT is not set CONFIG_ZONE_DMA_FLAG=0 CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_ALIGNMENT_TRAP=y +CONFIG_UACCESS_WITH_MEMCPY=y # # Boot options @@ -345,6 +360,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -367,6 +383,7 @@ CONFIG_NET_DSA_MV88E6123_61_65=y # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -383,17 +400,18 @@ CONFIG_NET_PKTGEN=m # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y CONFIG_CFG80211=y +# CONFIG_NL80211_TESTMODE is not set +# CONFIG_CFG80211_DEVELOPER_WARNINGS is not set # CONFIG_CFG80211_REG_DEBUG is not set +CONFIG_CFG80211_DEFAULT_PS=y +CONFIG_CFG80211_DEFAULT_PS_VALUE=1 +# CONFIG_CFG80211_DEBUGFS is not set CONFIG_WIRELESS_OLD_REGULATORY=y CONFIG_WIRELESS_EXT=y CONFIG_WIRELESS_EXT_SYSFS=y CONFIG_LIB80211=y # CONFIG_LIB80211_DEBUG is not set CONFIG_MAC80211=y - -# -# Rate control algorithm selection -# CONFIG_MAC80211_RC_MINSTREL=y # CONFIG_MAC80211_RC_DEFAULT_PID is not set CONFIG_MAC80211_RC_DEFAULT_MINSTREL=y @@ -414,6 +432,7 @@ CONFIG_MAC80211_RC_DEFAULT="minstrel" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -425,9 +444,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_AFS_PARTS is not set @@ -494,6 +513,7 @@ CONFIG_MTD_PHYSMAP=y # CONFIG_MTD_DATAFLASH is not set CONFIG_MTD_M25P80=y CONFIG_M25PXX_USE_FAST_READ=y +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -543,6 +563,7 @@ CONFIG_BLK_DEV_LOOP=y # CONFIG_BLK_DEV_RAM is not set # CONFIG_CDROM_PKTCDVD is not set # CONFIG_ATA_OVER_ETH is not set +# CONFIG_MG_DISK is not set # CONFIG_MISC_DEVICES is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -567,10 +588,6 @@ CONFIG_BLK_DEV_SR=m # CONFIG_BLK_DEV_SR_VENDOR is not set CONFIG_CHR_DEV_SG=m # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -587,6 +604,8 @@ CONFIG_SCSI_WAIT_SCAN=m # CONFIG_SCSI_SRP_ATTRS is not set CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set +# CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -595,6 +614,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_AIC7XXX_OLD is not set # CONFIG_SCSI_AIC79XX is not set # CONFIG_SCSI_AIC94XX is not set +# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_DPT_I2O is not set # CONFIG_SCSI_ADVANSYS is not set # CONFIG_SCSI_ARCMSR is not set @@ -611,7 +631,6 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_IPS is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set -# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_STEX is not set # CONFIG_SCSI_SYM53C8XX_2 is not set # CONFIG_SCSI_IPR is not set @@ -623,11 +642,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_SATA_AHCI=y # CONFIG_SATA_SIL24 is not set @@ -649,6 +671,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -676,6 +699,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -693,13 +717,16 @@ CONFIG_SATA_MV=y # # -# Enable only one of the two stacks, unless you know what you are doing +# You can enable one or both FireWire driver stacks. +# + +# +# See the help texts for more information. # # CONFIG_FIREWIRE is not set # CONFIG_IEEE1394 is not set # CONFIG_I2O is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -768,6 +795,9 @@ CONFIG_NET_PCI=y # CONFIG_SMSC9420 is not set # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set @@ -789,6 +819,7 @@ CONFIG_NETDEV_1000=y # CONFIG_VIA_VELOCITY is not set # CONFIG_TIGON3 is not set # CONFIG_BNX2 is not set +# CONFIG_CNIC is not set CONFIG_MV643XX_ETH=y # CONFIG_QLA3XXX is not set # CONFIG_ATL1 is not set @@ -797,10 +828,7 @@ CONFIG_MV643XX_ETH=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set CONFIG_WLAN_80211=y CONFIG_LIBERTAS=y @@ -820,9 +848,7 @@ CONFIG_LIBERTAS_SDIO=y # CONFIG_MAC80211_HWSIM is not set # CONFIG_MWL8K is not set # CONFIG_P54_COMMON is not set -# CONFIG_ATH5K is not set -# CONFIG_ATH9K is not set -# CONFIG_AR9170_USB is not set +# CONFIG_ATH_COMMON is not set # CONFIG_IPW2100 is not set # CONFIG_IPW2200 is not set # CONFIG_IWLWIFI is not set @@ -832,6 +858,8 @@ CONFIG_LIBERTAS_SDIO=y # CONFIG_ZD1211RW is not set # CONFIG_RT2X00 is not set # CONFIG_HERMES is not set +# CONFIG_WL12XX is not set +# CONFIG_IWM is not set # # Enable WiMAX (Networking options) to see the WiMAX drivers @@ -855,6 +883,7 @@ CONFIG_LIBERTAS_SDIO=y # CONFIG_NETPOLL is not set # CONFIG_NET_POLL_CONTROLLER is not set # CONFIG_ISDN is not set +# CONFIG_PHONE is not set # # Input device support @@ -878,13 +907,19 @@ CONFIG_INPUT_EVDEV=y # Input Device Drivers # CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ADP5588 is not set CONFIG_KEYBOARD_ATKBD=y -# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_QT2160 is not set # CONFIG_KEYBOARD_LKKBD is not set -# CONFIG_KEYBOARD_XTKBD is not set +CONFIG_KEYBOARD_GPIO=y +# CONFIG_KEYBOARD_MATRIX is not set +# CONFIG_KEYBOARD_LM8323 is not set +# CONFIG_KEYBOARD_MAX7359 is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set -CONFIG_KEYBOARD_GPIO=y +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_XTKBD is not set # CONFIG_INPUT_MOUSE is not set # CONFIG_INPUT_JOYSTICK is not set # CONFIG_INPUT_TABLET is not set @@ -943,6 +978,7 @@ CONFIG_LEGACY_PTY_COUNT=16 CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +# CONFIG_I2C_COMPAT is not set CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -998,10 +1034,6 @@ CONFIG_I2C_MV64XXX=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1023,11 +1055,47 @@ CONFIG_SPI_ORION=y # # CONFIG_SPI_SPIDEV is not set # CONFIG_SPI_TLE62X0 is not set + +# +# PPS support +# +# CONFIG_PPS is not set +CONFIG_ARCH_REQUIRE_GPIOLIB=y +CONFIG_GPIOLIB=y +# CONFIG_DEBUG_GPIO is not set +CONFIG_GPIO_SYSFS=y + +# +# Memory mapped GPIO expanders: +# + +# +# I2C GPIO expanders: +# +# CONFIG_GPIO_MAX732X is not set +# CONFIG_GPIO_PCA953X is not set +# CONFIG_GPIO_PCF857X is not set + +# +# PCI GPIO expanders: +# +# CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set + +# +# SPI GPIO expanders: +# +# CONFIG_GPIO_MAX7301 is not set +# CONFIG_GPIO_MCP23S08 is not set +# CONFIG_GPIO_MC33880 is not set + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1041,33 +1109,28 @@ CONFIG_SSB_POSSIBLE=y # # CONFIG_MFD_CORE is not set # CONFIG_MFD_SM501 is not set +# CONFIG_MFD_ASIC3 is not set +# CONFIG_HTC_EGPIO is not set # CONFIG_HTC_PASIC3 is not set +# CONFIG_TPS65010 is not set # CONFIG_TWL4030_CORE is not set # CONFIG_MFD_TMIO is not set +# CONFIG_MFD_TC6393XB is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -# CONFIG_DAB is not set +# CONFIG_MFD_MC13783 is not set +# CONFIG_AB3100_CORE is not set +# CONFIG_EZX_PCAP is not set +# CONFIG_REGULATOR is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support # +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1087,7 +1150,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1106,10 +1168,12 @@ CONFIG_HID_BELKIN=y CONFIG_HID_CHERRY=y CONFIG_HID_CHICONY=y CONFIG_HID_CYPRESS=y +CONFIG_HID_DRAGONRISE=y # CONFIG_DRAGONRISE_FF is not set CONFIG_HID_EZKEY=y CONFIG_HID_KYE=y CONFIG_HID_GYRATION=y +CONFIG_HID_TWINHAN=y CONFIG_HID_KENSINGTON=y CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1123,9 +1187,14 @@ CONFIG_HID_PETALYNX=y CONFIG_HID_SAMSUNG=y CONFIG_HID_SONY=y CONFIG_HID_SUNPLUS=y +CONFIG_HID_GREENASIA=y # CONFIG_GREENASIA_FF is not set +CONFIG_HID_SMARTJOYPLUS=y +# CONFIG_SMARTJOYPLUS_FF is not set CONFIG_HID_TOPSEED=y +CONFIG_HID_THRUSTMASTER=y # CONFIG_THRUSTMASTER_FF is not set +CONFIG_HID_ZEROPLUS=y # CONFIG_ZEROPLUS_FF is not set CONFIG_USB_SUPPORT=y CONFIG_USB_ARCH_HAS_HCD=y @@ -1150,18 +1219,21 @@ CONFIG_USB_DEVICE_CLASS=y # USB Host Controller Drivers # # CONFIG_USB_C67X00_HCD is not set +# CONFIG_USB_XHCI_HCD is not set CONFIG_USB_EHCI_HCD=y CONFIG_USB_EHCI_ROOT_HUB_TT=y CONFIG_USB_EHCI_TT_NEWSCHED=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set # CONFIG_USB_UHCI_HCD is not set # CONFIG_USB_SL811_HCD is not set # CONFIG_USB_R8A66597_HCD is not set # CONFIG_USB_WHCI_HCD is not set # CONFIG_USB_HWA_HCD is not set +# CONFIG_USB_MUSB_HDRC is not set # # USB Device Class drivers @@ -1252,11 +1324,14 @@ CONFIG_SDIO_UART=y # MMC/SD/SDIO Host Controller Drivers # # CONFIG_MMC_SDHCI is not set +# CONFIG_MMC_AT91 is not set +# CONFIG_MMC_ATMELMCI is not set # CONFIG_MMC_TIFM_SD is not set CONFIG_MMC_MVSDIO=y # CONFIG_MMC_SPI is not set +# CONFIG_MMC_CB710 is not set +# CONFIG_MMC_VIA_SDMMC is not set # CONFIG_MEMSTICK is not set -# CONFIG_ACCESSIBILITY is not set CONFIG_NEW_LEDS=y CONFIG_LEDS_CLASS=y @@ -1266,7 +1341,7 @@ CONFIG_LEDS_CLASS=y # CONFIG_LEDS_PCA9532 is not set CONFIG_LEDS_GPIO=y CONFIG_LEDS_GPIO_PLATFORM=y -# CONFIG_LEDS_LP5521 is not set +# CONFIG_LEDS_LP3944 is not set # CONFIG_LEDS_PCA955X is not set # CONFIG_LEDS_DAC124S085 is not set # CONFIG_LEDS_BD2802 is not set @@ -1278,11 +1353,14 @@ CONFIG_LEDS_TRIGGERS=y CONFIG_LEDS_TRIGGER_TIMER=y CONFIG_LEDS_TRIGGER_HEARTBEAT=y # CONFIG_LEDS_TRIGGER_BACKLIGHT is not set +# CONFIG_LEDS_TRIGGER_GPIO is not set CONFIG_LEDS_TRIGGER_DEFAULT_ON=y # # iptables trigger is under Netfilter config (LED target) # +# CONFIG_ACCESSIBILITY is not set +# CONFIG_INFINIBAND is not set CONFIG_RTC_LIB=y CONFIG_RTC_CLASS=y CONFIG_RTC_HCTOSYS=y @@ -1314,6 +1392,7 @@ CONFIG_RTC_INTF_DEV=y CONFIG_RTC_DRV_S35390A=y # CONFIG_RTC_DRV_FM3130 is not set # CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set # # SPI RTC drivers @@ -1325,6 +1404,7 @@ CONFIG_RTC_DRV_S35390A=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -1360,8 +1440,11 @@ CONFIG_DMA_ENGINE=y # CONFIG_ASYNC_TX_DMA is not set # CONFIG_DMATEST is not set # CONFIG_AUXDISPLAY is not set -# CONFIG_REGULATOR is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -1379,10 +1462,13 @@ CONFIG_JBD=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -1455,7 +1541,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1530,6 +1615,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -1547,6 +1633,7 @@ CONFIG_BOOTPARAM_HUNG_TASK_PANIC_VALUE=0 # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_PREEMPT is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set @@ -1567,12 +1654,14 @@ CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_BOOT_PRINTK_DELAY is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_KPROBES_SANITY_TEST is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_LKDTM is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set @@ -1581,25 +1670,12 @@ CONFIG_SYSCTL_SYSCALL_CHECK=y CONFIG_NOP_TRACER=y CONFIG_HAVE_FUNCTION_TRACER=y CONFIG_RING_BUFFER=y +CONFIG_EVENT_TRACING=y +CONFIG_CONTEXT_SWITCH_TRACER=y +CONFIG_RING_BUFFER_ALLOW_SWAP=y CONFIG_TRACING=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# -# CONFIG_FUNCTION_TRACER is not set -# CONFIG_IRQSOFF_TRACER is not set -# CONFIG_PREEMPT_TRACER is not set -# CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set -# CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set -# CONFIG_STACK_TRACER is not set -# CONFIG_KMEMTRACE is not set -# CONFIG_WORKQUEUE_TRACER is not set -# CONFIG_BLK_DEV_IO_TRACE is not set -# CONFIG_FTRACE_STARTUP_TEST is not set +# CONFIG_FTRACE is not set # CONFIG_DYNAMIC_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y @@ -1623,7 +1699,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1665,11 +1740,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=y +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set @@ -1714,6 +1791,7 @@ CONFIG_CRYPTO_ARC4=y # # CONFIG_CRYPTO_ANSI_CPRNG is not set CONFIG_CRYPTO_HW=y +CONFIG_CRYPTO_DEV_MV_CESA=y # CONFIG_CRYPTO_DEV_HIFN_795X is not set CONFIG_BINARY_PRINTF=y diff --git a/arch/arm/configs/n8x0_defconfig b/arch/arm/configs/n8x0_defconfig index 8da75dede52e..264f52b5c52d 100644 --- a/arch/arm/configs/n8x0_defconfig +++ b/arch/arm/configs/n8x0_defconfig @@ -304,7 +304,7 @@ CONFIG_ALIGNMENT_TRAP=y CONFIG_ZBOOT_ROM_TEXT=0x10C08000 CONFIG_ZBOOT_ROM_BSS=0x10200000 # CONFIG_ZBOOT_ROM is not set -CONFIG_CMDLINE="root=1f03 rootfstype=jffs2 console=ttyS0,115200n8" +CONFIG_CMDLINE="root=1f03 rootfstype=jffs2 console=ttyS2,115200n8" # CONFIG_XIP_KERNEL is not set # CONFIG_KEXEC is not set diff --git a/arch/arm/configs/omap3_beagle_defconfig b/arch/arm/configs/omap3_beagle_defconfig index 357d4021e2d0..b3c8cce0f8fb 100644 --- a/arch/arm/configs/omap3_beagle_defconfig +++ b/arch/arm/configs/omap3_beagle_defconfig @@ -969,7 +969,6 @@ CONFIG_USB_ETH_RNDIS=y # CONFIG_USB_OTG_UTILS=y # CONFIG_USB_GPIO_VBUS is not set -# CONFIG_ISP1301_OMAP is not set CONFIG_TWL4030_USB=y # CONFIG_NOP_USB_XCEIV is not set CONFIG_MMC=y diff --git a/arch/arm/configs/omap3_pandora_defconfig b/arch/arm/configs/omap3_pandora_defconfig index b54ad2e2da36..150deafb0a6a 100644 --- a/arch/arm/configs/omap3_pandora_defconfig +++ b/arch/arm/configs/omap3_pandora_defconfig @@ -611,7 +611,7 @@ CONFIG_INPUT_KEYBOARD=y # CONFIG_KEYBOARD_XTKBD is not set # CONFIG_KEYBOARD_NEWTON is not set # CONFIG_KEYBOARD_STOWAWAY is not set -# CONFIG_KEYBOARD_GPIO is not set +CONFIG_KEYBOARD_GPIO=y CONFIG_INPUT_MOUSE=y # CONFIG_MOUSE_PS2 is not set # CONFIG_MOUSE_SERIAL is not set @@ -634,7 +634,8 @@ CONFIG_TOUCHSCREEN_ADS7846=y # CONFIG_TOUCHSCREEN_TOUCHWIN is not set # CONFIG_TOUCHSCREEN_USB_COMPOSITE is not set # CONFIG_TOUCHSCREEN_TOUCHIT213 is not set -# CONFIG_INPUT_MISC is not set +CONFIG_INPUT_MISC=y +CONFIG_INPUT_TWL4030_PWRBUTTON=y # # Hardware I/O ports @@ -834,7 +835,29 @@ CONFIG_DAB=y # # CONFIG_VGA_CONSOLE is not set CONFIG_DUMMY_CONSOLE=y -# CONFIG_SOUND is not set +CONFIG_SOUND=y +CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y +CONFIG_SND=y +CONFIG_SND_TIMER=y +CONFIG_SND_PCM=y +CONFIG_SND_JACK=y +CONFIG_SND_OSSEMUL=y +CONFIG_SND_MIXER_OSS=y +CONFIG_SND_PCM_OSS=y +CONFIG_SND_PCM_OSS_PLUGINS=y +CONFIG_SND_SUPPORT_OLD_API=y +CONFIG_SND_VERBOSE_PROCFS=y +CONFIG_SND_VERBOSE_PRINTK=y +CONFIG_SND_DRIVERS=y +CONFIG_SND_USB=y +CONFIG_SND_SOC=y +CONFIG_SND_OMAP_SOC=y +CONFIG_SND_OMAP_SOC_MCBSP=y +CONFIG_SND_OMAP_SOC_OMAP3_PANDORA=y +CONFIG_SND_SOC_I2C_AND_SPI=y +CONFIG_SND_SOC_TWL4030=y + CONFIG_HID_SUPPORT=y CONFIG_HID=y # CONFIG_HID_DEBUG is not set @@ -1020,7 +1043,13 @@ CONFIG_MMC_BLOCK_BOUNCE=y # CONFIG_MMC_SPI is not set # CONFIG_MEMSTICK is not set # CONFIG_ACCESSIBILITY is not set -# CONFIG_NEW_LEDS is not set +CONFIG_NEW_LEDS=y +CONFIG_LEDS_CLASS=y +CONFIG_LEDS_GPIO=y +CONFIG_LEDS_GPIO_PLATFORM=y +CONFIG_LEDS_TRIGGERS=y +CONFIG_LEDS_TRIGGER_DEFAULT_ON=y + CONFIG_RTC_LIB=y CONFIG_RTC_CLASS=y CONFIG_RTC_HCTOSYS=y @@ -1084,9 +1113,12 @@ CONFIG_RTC_DRV_TWL4030=y # on-CPU RTC drivers # # CONFIG_DMADEVICES is not set -# CONFIG_REGULATOR is not set # CONFIG_UIO is not set +CONFIG_REGULATOR=y +CONFIG_REGULATOR_FIXED_VOLTAGE=y +CONFIG_REGULATOR_TWL4030=y + # # File systems # @@ -1407,3 +1439,10 @@ CONFIG_PLIST=y CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y + +# added by hand for now +CONFIG_KEYBOARD_TWL4030=y +CONFIG_USB_OTG_UTILS=y +CONFIG_TWL4030_USB=y +CONFIG_MMC_OMAP_HS=y + diff --git a/arch/arm/configs/omap_3430sdp_defconfig b/arch/arm/configs/omap_3430sdp_defconfig index 8a4a7e2ba87b..5a305f015307 100644 --- a/arch/arm/configs/omap_3430sdp_defconfig +++ b/arch/arm/configs/omap_3430sdp_defconfig @@ -1703,7 +1703,14 @@ CONFIG_RTC_DRV_TWL4030=y # on-CPU RTC drivers # # CONFIG_DMADEVICES is not set -# CONFIG_REGULATOR is not set +CONFIG_REGULATOR=y +# CONFIG_REGULATOR_DEBUG is not set +# CONFIG_REGULATOR_FIXED_VOLTAGE is not set +# CONFIG_REGULATOR_VIRTUAL_CONSUMER is not set +# CONFIG_REGULATOR_USERSPACE_CONSUMER is not set +# CONFIG_REGULATOR_BQ24022 is not set +# CONFIG_REGULATOR_MAX1586 is not set +CONFIG_REGULATOR_TWL4030=y # CONFIG_UIO is not set # CONFIG_STAGING is not set diff --git a/arch/arm/configs/orion5x_defconfig b/arch/arm/configs/orion5x_defconfig index 9e2385293ecb..5383cd0dff54 100644 --- a/arch/arm/configs/orion5x_defconfig +++ b/arch/arm/configs/orion5x_defconfig @@ -1,15 +1,13 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc4 -# Mon May 4 14:07:25 2009 +# Linux kernel version: 2.6.32-rc6 +# Sat Nov 7 20:52:21 2009 # CONFIG_ARM=y CONFIG_SYS_SUPPORTS_APM_EMULATION=y CONFIG_GENERIC_GPIO=y CONFIG_GENERIC_TIME=y CONFIG_GENERIC_CLOCKEVENTS=y -CONFIG_MMU=y -# CONFIG_NO_IOPORT is not set CONFIG_GENERIC_HARDIRQS=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -18,13 +16,12 @@ CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_HARDIRQS_SW_RESEND=y CONFIG_GENERIC_IRQ_PROBE=y CONFIG_RWSEM_GENERIC_SPINLOCK=y -# CONFIG_ARCH_HAS_ILOG2_U32 is not set -# CONFIG_ARCH_HAS_ILOG2_U64 is not set CONFIG_GENERIC_HWEIGHT=y CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y CONFIG_VECTORS_BASE=0xffff0000 CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -46,11 +43,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 # CONFIG_GROUP_SCHED is not set @@ -69,7 +67,6 @@ CONFIG_SYSCTL_SYSCALL=y CONFIG_KALLSYMS=y CONFIG_KALLSYMS_ALL=y # CONFIG_KALLSYMS_EXTRA_PASS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -82,6 +79,10 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y + +# +# Kernel Performance Events And Counters +# CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y # CONFIG_SLUB_DEBUG is not set @@ -91,13 +92,17 @@ CONFIG_SLUB=y # CONFIG_SLOB is not set CONFIG_PROFILING=y CONFIG_TRACEPOINTS=y -# CONFIG_MARKERS is not set CONFIG_OPROFILE=y CONFIG_HAVE_OPROFILE=y CONFIG_KPROBES=y CONFIG_KRETPROBES=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y + +# +# GCOV-based kernel profiling +# +# CONFIG_GCOV_KERNEL is not set # CONFIG_SLOW_WORK is not set CONFIG_HAVE_GENERIC_DMA_COHERENT=y CONFIG_RT_MUTEXES=y @@ -109,7 +114,7 @@ CONFIG_MODULE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -130,19 +135,22 @@ CONFIG_DEFAULT_IOSCHED="cfq" # # System Type # +CONFIG_MMU=y # CONFIG_ARCH_AAEC2000 is not set # CONFIG_ARCH_INTEGRATOR is not set # CONFIG_ARCH_REALVIEW is not set # CONFIG_ARCH_VERSATILE is not set # CONFIG_ARCH_AT91 is not set # CONFIG_ARCH_CLPS711X is not set +# CONFIG_ARCH_GEMINI is not set # CONFIG_ARCH_EBSA110 is not set # CONFIG_ARCH_EP93XX is not set -# CONFIG_ARCH_GEMINI is not set # CONFIG_ARCH_FOOTBRIDGE is not set +# CONFIG_ARCH_MXC is not set +# CONFIG_ARCH_STMP3XXX is not set # CONFIG_ARCH_NETX is not set # CONFIG_ARCH_H720X is not set -# CONFIG_ARCH_IMX is not set +# CONFIG_ARCH_NOMADIK is not set # CONFIG_ARCH_IOP13XX is not set # CONFIG_ARCH_IOP32X is not set # CONFIG_ARCH_IOP33X is not set @@ -151,25 +159,27 @@ CONFIG_DEFAULT_IOSCHED="cfq" # CONFIG_ARCH_IXP4XX is not set # CONFIG_ARCH_L7200 is not set # CONFIG_ARCH_KIRKWOOD is not set -# CONFIG_ARCH_KS8695 is not set -# CONFIG_ARCH_NS9XXX is not set # CONFIG_ARCH_LOKI is not set # CONFIG_ARCH_MV78XX0 is not set -# CONFIG_ARCH_MXC is not set CONFIG_ARCH_ORION5X=y +# CONFIG_ARCH_MMP is not set +# CONFIG_ARCH_KS8695 is not set +# CONFIG_ARCH_NS9XXX is not set +# CONFIG_ARCH_W90X900 is not set # CONFIG_ARCH_PNX4008 is not set # CONFIG_ARCH_PXA is not set -# CONFIG_ARCH_MMP is not set +# CONFIG_ARCH_MSM is not set # CONFIG_ARCH_RPC is not set # CONFIG_ARCH_SA1100 is not set # CONFIG_ARCH_S3C2410 is not set # CONFIG_ARCH_S3C64XX is not set +# CONFIG_ARCH_S5PC1XX is not set # CONFIG_ARCH_SHARK is not set # CONFIG_ARCH_LH7A40X is not set +# CONFIG_ARCH_U300 is not set # CONFIG_ARCH_DAVINCI is not set # CONFIG_ARCH_OMAP is not set -# CONFIG_ARCH_MSM is not set -# CONFIG_ARCH_W90X900 is not set +# CONFIG_ARCH_BCMRING is not set # # Orion Implementations @@ -187,6 +197,9 @@ CONFIG_MACH_WRT350N_V2=y CONFIG_MACH_TS78XX=y CONFIG_MACH_MV2120=y CONFIG_MACH_EDMINI_V2=y +CONFIG_MACH_D2NET=y +CONFIG_MACH_BIGDISK=y +CONFIG_MACH_NET2BIG=y CONFIG_MACH_MSS2=y CONFIG_MACH_WNR854T=y CONFIG_MACH_RD88F5181L_GE=y @@ -202,7 +215,7 @@ CONFIG_CPU_FEROCEON=y CONFIG_CPU_FEROCEON_OLD_ID=y CONFIG_CPU_32v5=y CONFIG_CPU_ABRT_EV5T=y -CONFIG_CPU_PABRT_NOIFAR=y +CONFIG_CPU_PABRT_LEGACY=y CONFIG_CPU_CACHE_VIVT=y CONFIG_CPU_COPY_FEROCEON=y CONFIG_CPU_TLB_FEROCEON=y @@ -215,7 +228,7 @@ CONFIG_CPU_CP15_MMU=y CONFIG_ARM_THUMB=y # CONFIG_CPU_ICACHE_DISABLE is not set # CONFIG_CPU_DCACHE_DISABLE is not set -# CONFIG_OUTER_CACHE is not set +CONFIG_ARM_L1_CACHE_SHIFT=5 # # Bus support @@ -240,11 +253,12 @@ CONFIG_VMSPLIT_3G=y # CONFIG_VMSPLIT_2G is not set # CONFIG_VMSPLIT_1G is not set CONFIG_PAGE_OFFSET=0xC0000000 +# CONFIG_PREEMPT_NONE is not set +# CONFIG_PREEMPT_VOLUNTARY is not set CONFIG_PREEMPT=y CONFIG_HZ=100 CONFIG_AEABI=y CONFIG_OABI_COMPAT=y -CONFIG_ARCH_FLATMEM_HAS_HOLES=y # CONFIG_ARCH_SPARSEMEM_DEFAULT is not set # CONFIG_ARCH_SELECT_MEMORY_MODEL is not set # CONFIG_HIGHMEM is not set @@ -259,12 +273,14 @@ CONFIG_SPLIT_PTLOCK_CPUS=4096 # CONFIG_PHYS_ADDR_T_64BIT is not set CONFIG_ZONE_DMA_FLAG=0 CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_LEDS=y CONFIG_LEDS_CPU=y CONFIG_ALIGNMENT_TRAP=y +CONFIG_UACCESS_WITH_MEMCPY=y # # Boot options @@ -308,6 +324,7 @@ CONFIG_PM=y # CONFIG_PM_DEBUG is not set # CONFIG_SUSPEND is not set # CONFIG_APM_EMULATION is not set +# CONFIG_PM_RUNTIME is not set CONFIG_ARCH_SUSPEND_POSSIBLE=y CONFIG_NET=y @@ -356,6 +373,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -378,6 +396,7 @@ CONFIG_NET_DSA_MV88E6123_61_65=y # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -394,11 +413,15 @@ CONFIG_NET_PKTGEN=m # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 # CONFIG_WIRELESS_OLD_REGULATORY is not set CONFIG_WIRELESS_EXT=y CONFIG_WIRELESS_EXT_SYSFS=y # CONFIG_LIB80211 is not set -# CONFIG_MAC80211 is not set + +# +# CFG80211 needs to be enabled for MAC80211 +# # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -411,6 +434,7 @@ CONFIG_WIRELESS_EXT_SYSFS=y # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -422,9 +446,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_AFS_PARTS is not set @@ -537,6 +561,7 @@ CONFIG_BLK_DEV_LOOP=y # CONFIG_BLK_DEV_RAM is not set # CONFIG_CDROM_PKTCDVD is not set # CONFIG_ATA_OVER_ETH is not set +# CONFIG_MG_DISK is not set CONFIG_MISC_DEVICES=y # CONFIG_PHANTOM is not set # CONFIG_SGI_IOC4 is not set @@ -552,7 +577,9 @@ CONFIG_MISC_DEVICES=y # # CONFIG_EEPROM_AT24 is not set # CONFIG_EEPROM_LEGACY is not set +# CONFIG_EEPROM_MAX6875 is not set # CONFIG_EEPROM_93CX6 is not set +# CONFIG_CB710_CORE is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -576,10 +603,6 @@ CONFIG_BLK_DEV_SR=m # CONFIG_BLK_DEV_SR_VENDOR is not set CONFIG_CHR_DEV_SG=m # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -596,6 +619,8 @@ CONFIG_SCSI_WAIT_SCAN=m # CONFIG_SCSI_SRP_ATTRS is not set CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set +# CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -604,6 +629,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_AIC7XXX_OLD is not set # CONFIG_SCSI_AIC79XX is not set # CONFIG_SCSI_AIC94XX is not set +# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_DPT_I2O is not set # CONFIG_SCSI_ADVANSYS is not set # CONFIG_SCSI_ARCMSR is not set @@ -620,7 +646,6 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_IPS is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set -# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_STEX is not set # CONFIG_SCSI_SYM53C8XX_2 is not set # CONFIG_SCSI_IPR is not set @@ -632,11 +657,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -658,6 +686,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -685,6 +714,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -703,13 +733,16 @@ CONFIG_SATA_MV=y # # -# Enable only one of the two stacks, unless you know what you are doing +# You can enable one or both FireWire driver stacks. +# + +# +# See the help texts for more information. # # CONFIG_FIREWIRE is not set # CONFIG_IEEE1394 is not set # CONFIG_I2O is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -777,6 +810,8 @@ CONFIG_NET_PCI=y # CONFIG_SMSC9420 is not set # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set @@ -798,6 +833,7 @@ CONFIG_NETDEV_1000=y # CONFIG_VIA_VELOCITY is not set # CONFIG_TIGON3 is not set # CONFIG_BNX2 is not set +# CONFIG_CNIC is not set CONFIG_MV643XX_ETH=y # CONFIG_QLA3XXX is not set # CONFIG_ATL1 is not set @@ -806,10 +842,7 @@ CONFIG_MV643XX_ETH=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -835,6 +868,7 @@ CONFIG_MV643XX_ETH=y # CONFIG_NETPOLL is not set # CONFIG_NET_POLL_CONTROLLER is not set # CONFIG_ISDN is not set +# CONFIG_PHONE is not set # # Input device support @@ -855,13 +889,19 @@ CONFIG_INPUT_EVDEV=y # Input Device Drivers # CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ADP5588 is not set # CONFIG_KEYBOARD_ATKBD is not set -# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_QT2160 is not set # CONFIG_KEYBOARD_LKKBD is not set -# CONFIG_KEYBOARD_XTKBD is not set +CONFIG_KEYBOARD_GPIO=y +# CONFIG_KEYBOARD_MATRIX is not set +# CONFIG_KEYBOARD_LM8323 is not set +# CONFIG_KEYBOARD_MAX7359 is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set -CONFIG_KEYBOARD_GPIO=y +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_XTKBD is not set # CONFIG_INPUT_MOUSE is not set # CONFIG_INPUT_JOYSTICK is not set # CONFIG_INPUT_TABLET is not set @@ -912,6 +952,7 @@ CONFIG_HW_RANDOM_TIMERIOMEM=m CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +# CONFIG_I2C_COMPAT is not set CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -967,20 +1008,55 @@ CONFIG_I2C_MV64XXX=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set # CONFIG_I2C_DEBUG_CHIP is not set # CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set +CONFIG_ARCH_REQUIRE_GPIOLIB=y +CONFIG_GPIOLIB=y +# CONFIG_DEBUG_GPIO is not set +CONFIG_GPIO_SYSFS=y + +# +# Memory mapped GPIO expanders: +# + +# +# I2C GPIO expanders: +# +# CONFIG_GPIO_MAX732X is not set +# CONFIG_GPIO_PCA953X is not set +# CONFIG_GPIO_PCF857X is not set + +# +# PCI GPIO expanders: +# +# CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set + +# +# SPI GPIO expanders: +# + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1030,6 +1106,8 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_SMSC47B397 is not set # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set +# CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1041,9 +1119,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1057,33 +1133,26 @@ CONFIG_SSB_POSSIBLE=y # # CONFIG_MFD_CORE is not set # CONFIG_MFD_SM501 is not set +# CONFIG_MFD_ASIC3 is not set +# CONFIG_HTC_EGPIO is not set # CONFIG_HTC_PASIC3 is not set +# CONFIG_TPS65010 is not set # CONFIG_TWL4030_CORE is not set # CONFIG_MFD_TMIO is not set +# CONFIG_MFD_TC6393XB is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -# CONFIG_DAB is not set +# CONFIG_AB3100_CORE is not set +# CONFIG_REGULATOR is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support # +# CONFIG_VGA_ARB is not set # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1097,7 +1166,6 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1116,10 +1184,11 @@ CONFIG_USB_HID=y # CONFIG_HID_CHERRY is not set # CONFIG_HID_CHICONY is not set # CONFIG_HID_CYPRESS is not set -# CONFIG_DRAGONRISE_FF is not set +# CONFIG_HID_DRAGONRISE is not set # CONFIG_HID_EZKEY is not set # CONFIG_HID_KYE is not set # CONFIG_HID_GYRATION is not set +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set # CONFIG_HID_LOGITECH is not set # CONFIG_HID_MICROSOFT is not set @@ -1130,10 +1199,11 @@ CONFIG_USB_HID=y # CONFIG_HID_SAMSUNG is not set # CONFIG_HID_SONY is not set # CONFIG_HID_SUNPLUS is not set -# CONFIG_GREENASIA_FF is not set +# CONFIG_HID_GREENASIA is not set +# CONFIG_HID_SMARTJOYPLUS is not set # CONFIG_HID_TOPSEED is not set -# CONFIG_THRUSTMASTER_FF is not set -# CONFIG_ZEROPLUS_FF is not set +# CONFIG_HID_THRUSTMASTER is not set +# CONFIG_HID_ZEROPLUS is not set CONFIG_USB_SUPPORT=y CONFIG_USB_ARCH_HAS_HCD=y CONFIG_USB_ARCH_HAS_OHCI=y @@ -1160,18 +1230,21 @@ CONFIG_USB_DEVICE_CLASS=y # USB Host Controller Drivers # # CONFIG_USB_C67X00_HCD is not set +# CONFIG_USB_XHCI_HCD is not set CONFIG_USB_EHCI_HCD=y CONFIG_USB_EHCI_ROOT_HUB_TT=y CONFIG_USB_EHCI_TT_NEWSCHED=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set # CONFIG_USB_UHCI_HCD is not set # CONFIG_USB_SL811_HCD is not set # CONFIG_USB_R8A66597_HCD is not set # CONFIG_USB_WHCI_HCD is not set # CONFIG_USB_HWA_HCD is not set +# CONFIG_USB_MUSB_HDRC is not set # # USB Device Class drivers @@ -1248,7 +1321,6 @@ CONFIG_USB_STORAGE_JUMPSHOT=y # CONFIG_UWB is not set # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set -# CONFIG_ACCESSIBILITY is not set CONFIG_NEW_LEDS=y CONFIG_LEDS_CLASS=y @@ -1258,7 +1330,7 @@ CONFIG_LEDS_CLASS=y # CONFIG_LEDS_PCA9532 is not set CONFIG_LEDS_GPIO=y CONFIG_LEDS_GPIO_PLATFORM=y -# CONFIG_LEDS_LP5521 is not set +# CONFIG_LEDS_LP3944 is not set # CONFIG_LEDS_PCA955X is not set # CONFIG_LEDS_BD2802 is not set @@ -1269,11 +1341,14 @@ CONFIG_LEDS_TRIGGERS=y CONFIG_LEDS_TRIGGER_TIMER=y CONFIG_LEDS_TRIGGER_HEARTBEAT=y # CONFIG_LEDS_TRIGGER_BACKLIGHT is not set +# CONFIG_LEDS_TRIGGER_GPIO is not set CONFIG_LEDS_TRIGGER_DEFAULT_ON=y # # iptables trigger is under Netfilter config (LED target) # +# CONFIG_ACCESSIBILITY is not set +# CONFIG_INFINIBAND is not set CONFIG_RTC_LIB=y CONFIG_RTC_CLASS=y CONFIG_RTC_HCTOSYS=y @@ -1306,6 +1381,7 @@ CONFIG_RTC_DRV_M41T80=y CONFIG_RTC_DRV_S35390A=y # CONFIG_RTC_DRV_FM3130 is not set # CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set # # SPI RTC drivers @@ -1344,8 +1420,11 @@ CONFIG_DMA_ENGINE=y # CONFIG_ASYNC_TX_DMA is not set # CONFIG_DMATEST is not set # CONFIG_AUXDISPLAY is not set -# CONFIG_REGULATOR is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -1358,10 +1437,10 @@ CONFIG_EXT3_FS=y # CONFIG_EXT3_DEFAULTS_TO_ORDERED is not set # CONFIG_EXT3_FS_XATTR is not set CONFIG_EXT4_FS=m -# CONFIG_EXT4DEV_COMPAT is not set CONFIG_EXT4_FS_XATTR=y # CONFIG_EXT4_FS_POSIX_ACL is not set # CONFIG_EXT4_FS_SECURITY is not set +# CONFIG_EXT4_DEBUG is not set CONFIG_JBD=y # CONFIG_JBD_DEBUG is not set CONFIG_JBD2=m @@ -1370,10 +1449,13 @@ CONFIG_FS_MBCACHE=m # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -1446,7 +1528,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1537,6 +1618,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -1552,6 +1634,7 @@ CONFIG_SCHED_DEBUG=y CONFIG_SCHEDSTATS=y # CONFIG_TIMER_STATS is not set # CONFIG_DEBUG_OBJECTS is not set +# CONFIG_DEBUG_KMEMLEAK is not set CONFIG_DEBUG_PREEMPT=y # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set @@ -1572,6 +1655,7 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set CONFIG_FRAME_POINTER=y # CONFIG_BOOT_PRINTK_DELAY is not set # CONFIG_RCU_TORTURE_TEST is not set @@ -1579,6 +1663,7 @@ CONFIG_FRAME_POINTER=y # CONFIG_KPROBES_SANITY_TEST is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_LKDTM is not set # CONFIG_FAULT_INJECTION is not set CONFIG_LATENCYTOP=y @@ -1587,25 +1672,12 @@ CONFIG_SYSCTL_SYSCALL_CHECK=y CONFIG_NOP_TRACER=y CONFIG_HAVE_FUNCTION_TRACER=y CONFIG_RING_BUFFER=y +CONFIG_EVENT_TRACING=y +CONFIG_CONTEXT_SWITCH_TRACER=y +CONFIG_RING_BUFFER_ALLOW_SWAP=y CONFIG_TRACING=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# -# CONFIG_FUNCTION_TRACER is not set -# CONFIG_IRQSOFF_TRACER is not set -# CONFIG_PREEMPT_TRACER is not set -# CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set -# CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set -# CONFIG_STACK_TRACER is not set -# CONFIG_KMEMTRACE is not set -# CONFIG_WORKQUEUE_TRACER is not set -# CONFIG_BLK_DEV_IO_TRACE is not set -# CONFIG_FTRACE_STARTUP_TEST is not set +# CONFIG_FTRACE is not set # CONFIG_DYNAMIC_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y @@ -1629,20 +1701,19 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set -CONFIG_CRYPTO_ALGAPI=m -CONFIG_CRYPTO_ALGAPI2=m -CONFIG_CRYPTO_AEAD2=m +CONFIG_CRYPTO_ALGAPI=y +CONFIG_CRYPTO_ALGAPI2=y +CONFIG_CRYPTO_AEAD2=y CONFIG_CRYPTO_BLKCIPHER=m -CONFIG_CRYPTO_BLKCIPHER2=m -CONFIG_CRYPTO_HASH2=m -CONFIG_CRYPTO_RNG2=m -CONFIG_CRYPTO_PCOMP=m +CONFIG_CRYPTO_BLKCIPHER2=y +CONFIG_CRYPTO_HASH2=y +CONFIG_CRYPTO_RNG2=y +CONFIG_CRYPTO_PCOMP=y CONFIG_CRYPTO_MANAGER=m -CONFIG_CRYPTO_MANAGER2=m +CONFIG_CRYPTO_MANAGER2=y # CONFIG_CRYPTO_GF128MUL is not set # CONFIG_CRYPTO_NULL is not set -CONFIG_CRYPTO_WORKQUEUE=m +CONFIG_CRYPTO_WORKQUEUE=y # CONFIG_CRYPTO_CRYPTD is not set # CONFIG_CRYPTO_AUTHENC is not set # CONFIG_CRYPTO_TEST is not set @@ -1670,11 +1741,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set @@ -1691,7 +1764,7 @@ CONFIG_CRYPTO_PCBC=m # # Ciphers # -# CONFIG_CRYPTO_AES is not set +CONFIG_CRYPTO_AES=y # CONFIG_CRYPTO_ANUBIS is not set # CONFIG_CRYPTO_ARC4 is not set # CONFIG_CRYPTO_BLOWFISH is not set @@ -1719,6 +1792,7 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_ANSI_CPRNG is not set CONFIG_CRYPTO_HW=y +CONFIG_CRYPTO_DEV_MV_CESA=y # CONFIG_CRYPTO_DEV_HIFN_795X is not set CONFIG_BINARY_PRINTF=y diff --git a/arch/arm/configs/u300_defconfig b/arch/arm/configs/u300_defconfig index 7d61ae6e75da..953ba0297fc4 100644 --- a/arch/arm/configs/u300_defconfig +++ b/arch/arm/configs/u300_defconfig @@ -1,14 +1,14 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc3 -# Thu Jul 16 23:36:10 2009 +# Linux kernel version: 2.6.32-rc5 +# Sat Oct 17 23:32:24 2009 # CONFIG_ARM=y CONFIG_SYS_SUPPORTS_APM_EMULATION=y CONFIG_GENERIC_GPIO=y CONFIG_GENERIC_TIME=y CONFIG_GENERIC_CLOCKEVENTS=y -CONFIG_MMU=y +CONFIG_HAVE_TCM=y CONFIG_GENERIC_HARDIRQS=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -44,11 +44,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 # CONFIG_GROUP_SCHED is not set @@ -80,17 +81,15 @@ CONFIG_SHMEM=y # CONFIG_AIO is not set # -# Performance Counters +# Kernel Performance Events And Counters # # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_KPROBES=y @@ -133,6 +132,7 @@ CONFIG_DEFAULT_IOSCHED="deadline" # # System Type # +CONFIG_MMU=y # CONFIG_ARCH_AAEC2000 is not set # CONFIG_ARCH_INTEGRATOR is not set # CONFIG_ARCH_REALVIEW is not set @@ -147,6 +147,7 @@ CONFIG_DEFAULT_IOSCHED="deadline" # CONFIG_ARCH_STMP3XXX is not set # CONFIG_ARCH_NETX is not set # CONFIG_ARCH_H720X is not set +# CONFIG_ARCH_NOMADIK is not set # CONFIG_ARCH_IOP13XX is not set # CONFIG_ARCH_IOP32X is not set # CONFIG_ARCH_IOP33X is not set @@ -169,11 +170,13 @@ CONFIG_DEFAULT_IOSCHED="deadline" # CONFIG_ARCH_SA1100 is not set # CONFIG_ARCH_S3C2410 is not set # CONFIG_ARCH_S3C64XX is not set +# CONFIG_ARCH_S5PC1XX is not set # CONFIG_ARCH_SHARK is not set # CONFIG_ARCH_LH7A40X is not set CONFIG_ARCH_U300=y # CONFIG_ARCH_DAVINCI is not set # CONFIG_ARCH_OMAP is not set +# CONFIG_ARCH_BCMRING is not set # # ST-Ericsson AB U300/U330/U335/U365 Platform @@ -195,6 +198,7 @@ CONFIG_MACH_U300_BS335=y CONFIG_MACH_U300_DUAL_RAM=y CONFIG_U300_DEBUG=y # CONFIG_MACH_U300_SEMI_IS_SHARED is not set +CONFIG_MACH_U300_SPIDUMMY=y # # All the settings below must match the bootloader's settings @@ -207,7 +211,7 @@ CONFIG_CPU_32=y CONFIG_CPU_ARM926T=y CONFIG_CPU_32v5=y CONFIG_CPU_ABRT_EV5TJ=y -CONFIG_CPU_PABRT_NOIFAR=y +CONFIG_CPU_PABRT_LEGACY=y CONFIG_CPU_CACHE_VIVT=y CONFIG_CPU_COPY_V4WB=y CONFIG_CPU_TLB_V4WBI=y @@ -222,6 +226,7 @@ CONFIG_ARM_THUMB=y # CONFIG_CPU_DCACHE_DISABLE is not set # CONFIG_CPU_DCACHE_WRITETHROUGH is not set # CONFIG_CPU_CACHE_ROUND_ROBIN is not set +CONFIG_ARM_L1_CACHE_SHIFT=5 CONFIG_ARM_VIC=y CONFIG_ARM_VIC_NR=2 CONFIG_COMMON_CLKDEV=y @@ -245,6 +250,8 @@ CONFIG_VMSPLIT_3G=y # CONFIG_VMSPLIT_2G is not set # CONFIG_VMSPLIT_1G is not set CONFIG_PAGE_OFFSET=0xC0000000 +# CONFIG_PREEMPT_NONE is not set +# CONFIG_PREEMPT_VOLUNTARY is not set CONFIG_PREEMPT=y CONFIG_HZ=100 CONFIG_AEABI=y @@ -265,6 +272,7 @@ CONFIG_ZONE_DMA_FLAG=0 CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_ALIGNMENT_TRAP=y # CONFIG_UACCESS_WITH_MEMCPY is not set @@ -313,6 +321,7 @@ CONFIG_PM=y # CONFIG_PM_DEBUG is not set # CONFIG_SUSPEND is not set # CONFIG_APM_EMULATION is not set +# CONFIG_PM_RUNTIME is not set CONFIG_ARCH_SUSPEND_POSSIBLE=y CONFIG_NET=y @@ -351,6 +360,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -391,6 +401,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y # CONFIG_PREVENT_FIRMWARE_BUILD is not set CONFIG_FW_LOADER=y @@ -402,9 +413,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_AFS_PARTS is not set @@ -453,6 +464,7 @@ CONFIG_MTD_CFI_I2=y # # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -520,6 +532,7 @@ CONFIG_HAVE_IDE=y # CONFIG_MD is not set # CONFIG_NETDEVICES is not set # CONFIG_ISDN is not set +# CONFIG_PHONE is not set # # Input device support @@ -540,12 +553,16 @@ CONFIG_INPUT_EVDEV=y # Input Device Drivers # CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ADP5588 is not set # CONFIG_KEYBOARD_ATKBD is not set +# CONFIG_QT2160 is not set # CONFIG_KEYBOARD_LKKBD is not set # CONFIG_KEYBOARD_GPIO is not set # CONFIG_KEYBOARD_MATRIX is not set # CONFIG_KEYBOARD_LM8323 is not set +# CONFIG_KEYBOARD_MAX7359 is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set # CONFIG_KEYBOARD_SUNKBD is not set # CONFIG_KEYBOARD_XTKBD is not set @@ -597,6 +614,7 @@ CONFIG_LEGACY_PTY_COUNT=16 # CONFIG_TCG_TPM is not set CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y # CONFIG_I2C_CHARDEV is not set CONFIG_I2C_HELPER_AUTO=y @@ -629,9 +647,6 @@ CONFIG_I2C_STU300=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -653,16 +668,21 @@ CONFIG_SPI_PL022=y # # CONFIG_SPI_SPIDEV is not set # CONFIG_SPI_TLE62X0 is not set + +# +# PPS support +# +# CONFIG_PPS is not set # CONFIG_W1 is not set CONFIG_POWER_SUPPLY=y # CONFIG_POWER_SUPPLY_DEBUG is not set # CONFIG_PDA_POWER is not set # CONFIG_BATTERY_DS2760 is not set +# CONFIG_BATTERY_DS2782 is not set # CONFIG_BATTERY_BQ27x00 is not set # CONFIG_BATTERY_MAX17040 is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -690,10 +710,24 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TC6387XB is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set CONFIG_AB3100_CORE=y +CONFIG_AB3100_OTP=y # CONFIG_EZX_PCAP is not set +CONFIG_REGULATOR=y +# CONFIG_REGULATOR_DEBUG is not set +# CONFIG_REGULATOR_FIXED_VOLTAGE is not set +# CONFIG_REGULATOR_VIRTUAL_CONSUMER is not set +# CONFIG_REGULATOR_USERSPACE_CONSUMER is not set +# CONFIG_REGULATOR_BQ24022 is not set +# CONFIG_REGULATOR_MAX1586 is not set +# CONFIG_REGULATOR_LP3971 is not set +CONFIG_REGULATOR_AB3100=y +# CONFIG_REGULATOR_TPS65023 is not set +# CONFIG_REGULATOR_TPS6507X is not set # CONFIG_MEDIA_SUPPORT is not set # @@ -792,9 +826,10 @@ CONFIG_MMC_BLOCK_BOUNCE=y # CONFIG_MMC_ARMMMCI=y # CONFIG_MMC_SDHCI is not set +# CONFIG_MMC_AT91 is not set +# CONFIG_MMC_ATMELMCI is not set # CONFIG_MMC_SPI is not set # CONFIG_MEMSTICK is not set -# CONFIG_ACCESSIBILITY is not set CONFIG_NEW_LEDS=y CONFIG_LEDS_CLASS=y @@ -820,10 +855,10 @@ CONFIG_LEDS_TRIGGER_BACKLIGHT=y # # iptables trigger is under Netfilter config (LED target) # +# CONFIG_ACCESSIBILITY is not set CONFIG_RTC_LIB=y CONFIG_RTC_CLASS=y -CONFIG_RTC_HCTOSYS=y -CONFIG_RTC_HCTOSYS_DEVICE="rtc0" +# CONFIG_RTC_HCTOSYS is not set # CONFIG_RTC_DEBUG is not set # @@ -863,6 +898,7 @@ CONFIG_RTC_INTF_DEV=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -878,27 +914,25 @@ CONFIG_RTC_INTF_DEV=y # CONFIG_RTC_DRV_M48T59 is not set # CONFIG_RTC_DRV_BQ4802 is not set # CONFIG_RTC_DRV_V3020 is not set +CONFIG_RTC_DRV_AB3100=y # # on-CPU RTC drivers # # CONFIG_RTC_DRV_PL030 is not set # CONFIG_RTC_DRV_PL031 is not set +CONFIG_RTC_DRV_COH901331=y CONFIG_DMADEVICES=y # # DMA Devices # # CONFIG_AUXDISPLAY is not set -CONFIG_REGULATOR=y -# CONFIG_REGULATOR_DEBUG is not set -# CONFIG_REGULATOR_FIXED_VOLTAGE is not set -# CONFIG_REGULATOR_VIRTUAL_CONSUMER is not set -# CONFIG_REGULATOR_USERSPACE_CONSUMER is not set -# CONFIG_REGULATOR_BQ24022 is not set -# CONFIG_REGULATOR_MAX1586 is not set -# CONFIG_REGULATOR_LP3971 is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -913,6 +947,7 @@ CONFIG_REGULATOR=y # CONFIG_XFS_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set @@ -975,7 +1010,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set # CONFIG_NETWORK_FILESYSTEMS is not set # @@ -1033,6 +1067,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1066,11 +1101,13 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_BOOT_PRINTK_DELAY is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set @@ -1121,6 +1158,7 @@ CONFIG_GENERIC_FIND_LAST_BIT=y # CONFIG_CRC32 is not set # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set +CONFIG_GENERIC_ALLOCATOR=y CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y diff --git a/arch/arm/include/asm/bitops.h b/arch/arm/include/asm/bitops.h index 63a481fbbed4..338ff19ae447 100644 --- a/arch/arm/include/asm/bitops.h +++ b/arch/arm/include/asm/bitops.h @@ -84,7 +84,7 @@ ____atomic_test_and_set_bit(unsigned int bit, volatile unsigned long *p) *p = res | mask; raw_local_irq_restore(flags); - return res & mask; + return (res & mask) != 0; } static inline int @@ -101,7 +101,7 @@ ____atomic_test_and_clear_bit(unsigned int bit, volatile unsigned long *p) *p = res & ~mask; raw_local_irq_restore(flags); - return res & mask; + return (res & mask) != 0; } static inline int @@ -118,7 +118,7 @@ ____atomic_test_and_change_bit(unsigned int bit, volatile unsigned long *p) *p = res ^ mask; raw_local_irq_restore(flags); - return res & mask; + return (res & mask) != 0; } #include <asm-generic/bitops/non-atomic.h> diff --git a/arch/arm/include/asm/cacheflush.h b/arch/arm/include/asm/cacheflush.h index fd03fb63a332..3d0cdd21b882 100644 --- a/arch/arm/include/asm/cacheflush.h +++ b/arch/arm/include/asm/cacheflush.h @@ -414,9 +414,14 @@ extern void __flush_dcache_page(struct address_space *mapping, struct page *page static inline void __flush_icache_all(void) { +#ifdef CONFIG_ARM_ERRATA_411920 + extern void v6_icache_inval_all(void); + v6_icache_inval_all(); +#else asm("mcr p15, 0, %0, c7, c5, 0 @ invalidate I-cache\n" : : "r" (0)); +#endif } #define ARCH_HAS_FLUSH_ANON_PAGE diff --git a/arch/arm/include/asm/elf.h b/arch/arm/include/asm/elf.h index c3b911ee9151..6aac3f5bb2f3 100644 --- a/arch/arm/include/asm/elf.h +++ b/arch/arm/include/asm/elf.h @@ -98,6 +98,9 @@ extern int elf_check_arch(const struct elf32_hdr *); extern int arm_elf_read_implies_exec(const struct elf32_hdr *, int); #define elf_read_implies_exec(ex,stk) arm_elf_read_implies_exec(&(ex), stk) +int dump_task_regs(struct task_struct *t, elf_gregset_t *elfregs); +#define ELF_CORE_COPY_TASK_REGS dump_task_regs + #define USE_ELF_CORE_DUMP #define ELF_EXEC_PAGESIZE 4096 diff --git a/arch/arm/include/asm/tlbflush.h b/arch/arm/include/asm/tlbflush.h index a45ab5dd8255..c2f1605de359 100644 --- a/arch/arm/include/asm/tlbflush.h +++ b/arch/arm/include/asm/tlbflush.h @@ -350,7 +350,7 @@ static inline void local_flush_tlb_mm(struct mm_struct *mm) if (tlb_flag(TLB_WB)) dsb(); - if (cpumask_test_cpu(smp_processor_id(), mm_cpumask(mm))) { + if (cpumask_test_cpu(get_cpu(), mm_cpumask(mm))) { if (tlb_flag(TLB_V3_FULL)) asm("mcr p15, 0, %0, c6, c0, 0" : : "r" (zero) : "cc"); if (tlb_flag(TLB_V4_U_FULL)) @@ -360,6 +360,7 @@ static inline void local_flush_tlb_mm(struct mm_struct *mm) if (tlb_flag(TLB_V4_I_FULL)) asm("mcr p15, 0, %0, c8, c5, 0" : : "r" (zero) : "cc"); } + put_cpu(); if (tlb_flag(TLB_V6_U_ASID)) asm("mcr p15, 0, %0, c8, c7, 2" : : "r" (asid) : "cc"); diff --git a/arch/arm/include/asm/unistd.h b/arch/arm/include/asm/unistd.h index 7020217fc49f..4e506d09e5f9 100644 --- a/arch/arm/include/asm/unistd.h +++ b/arch/arm/include/asm/unistd.h @@ -403,6 +403,15 @@ #define __ARM_NR_set_tls (__ARM_NR_BASE+5) /* + * *NOTE*: This is a ghost syscall private to the kernel. Only the + * __kuser_cmpxchg code in entry-armv.S should be aware of its + * existence. Don't ever use this from user code. + */ +#ifdef __KERNEL__ +#define __ARM_NR_cmpxchg (__ARM_NR_BASE+0x00fff0) +#endif + +/* * The following syscalls are obsolete and no longer available for EABI. */ #if defined(__ARM_EABI__) && !defined(__KERNEL__) diff --git a/arch/arm/kernel/entry-armv.S b/arch/arm/kernel/entry-armv.S index 322410be573c..d2903e3bc861 100644 --- a/arch/arm/kernel/entry-armv.S +++ b/arch/arm/kernel/entry-armv.S @@ -21,6 +21,7 @@ #include <mach/entry-macro.S> #include <asm/thread_notify.h> #include <asm/unwind.h> +#include <asm/unistd.h> #include "entry-header.S" @@ -608,33 +609,33 @@ call_fpe: THUMB( add pc, r8 ) nop - W(mov) pc, lr @ CP#0 + movw_pc lr @ CP#0 W(b) do_fpe @ CP#1 (FPE) W(b) do_fpe @ CP#2 (FPE) - W(mov) pc, lr @ CP#3 + movw_pc lr @ CP#3 #ifdef CONFIG_CRUNCH b crunch_task_enable @ CP#4 (MaverickCrunch) b crunch_task_enable @ CP#5 (MaverickCrunch) b crunch_task_enable @ CP#6 (MaverickCrunch) #else - W(mov) pc, lr @ CP#4 - W(mov) pc, lr @ CP#5 - W(mov) pc, lr @ CP#6 + movw_pc lr @ CP#4 + movw_pc lr @ CP#5 + movw_pc lr @ CP#6 #endif - W(mov) pc, lr @ CP#7 - W(mov) pc, lr @ CP#8 - W(mov) pc, lr @ CP#9 + movw_pc lr @ CP#7 + movw_pc lr @ CP#8 + movw_pc lr @ CP#9 #ifdef CONFIG_VFP W(b) do_vfp @ CP#10 (VFP) W(b) do_vfp @ CP#11 (VFP) #else - W(mov) pc, lr @ CP#10 (VFP) - W(mov) pc, lr @ CP#11 (VFP) + movw_pc lr @ CP#10 (VFP) + movw_pc lr @ CP#11 (VFP) #endif - W(mov) pc, lr @ CP#12 - W(mov) pc, lr @ CP#13 - W(mov) pc, lr @ CP#14 (Debug) - W(mov) pc, lr @ CP#15 (Control) + movw_pc lr @ CP#12 + movw_pc lr @ CP#13 + movw_pc lr @ CP#14 (Debug) + movw_pc lr @ CP#15 (Control) #ifdef CONFIG_NEON .align 6 @@ -908,10 +909,10 @@ __kuser_cmpxchg: @ 0xffff0fc0 * A special ghost syscall is used for that (see traps.c). */ stmfd sp!, {r7, lr} - mov r7, #0xff00 @ 0xfff0 into r7 for EABI - orr r7, r7, #0xf0 - swi #0x9ffff0 + ldr r7, =1f @ it's 20 bits + swi __ARM_NR_cmpxchg ldmfd sp!, {r7, pc} +1: .word __ARM_NR_cmpxchg #elif __LINUX_ARM_ARCH__ < 6 diff --git a/arch/arm/kernel/entry-header.S b/arch/arm/kernel/entry-header.S index ac34c0d9384b..7e9ed1eea40a 100644 --- a/arch/arm/kernel/entry-header.S +++ b/arch/arm/kernel/entry-header.S @@ -110,6 +110,13 @@ mov \rd, sp, lsr #13 mov \rd, \rd, lsl #13 .endm + + @ + @ 32-bit wide "mov pc, reg" + @ + .macro movw_pc, reg + mov pc, \reg + .endm #else /* CONFIG_THUMB2_KERNEL */ .macro svc_exit, rpsr clrex @ clear the exclusive monitor @@ -146,6 +153,14 @@ lsr \rd, \rd, #13 mov \rd, \rd, lsl #13 .endm + + @ + @ 32-bit wide "mov pc, reg" + @ + .macro movw_pc, reg + mov pc, \reg + nop + .endm #endif /* !CONFIG_THUMB2_KERNEL */ /* diff --git a/arch/arm/kernel/head-common.S b/arch/arm/kernel/head-common.S index 885a7214418d..b9505aa267c0 100644 --- a/arch/arm/kernel/head-common.S +++ b/arch/arm/kernel/head-common.S @@ -97,7 +97,7 @@ __error_a: bl printhex8 adr r0, str_a2 bl printascii - adr r3, 3f + adr r3, 4f ldmia r3, {r4, r5, r6} @ get machine desc list sub r4, r3, r4 @ get offset between virt&phys add r5, r5, r4 @ convert virt addresses to diff --git a/arch/arm/kernel/process.c b/arch/arm/kernel/process.c index 790fbee92ec5..0d96d0171c05 100644 --- a/arch/arm/kernel/process.c +++ b/arch/arm/kernel/process.c @@ -328,6 +328,15 @@ copy_thread(unsigned long clone_flags, unsigned long stack_start, } /* + * Fill in the task's elfregs structure for a core dump. + */ +int dump_task_regs(struct task_struct *t, elf_gregset_t *elfregs) +{ + elf_core_copy_regs(elfregs, task_pt_regs(t)); + return 1; +} + +/* * fill in the fpe structure for a core dump... */ int dump_fpu (struct pt_regs *regs, struct user_fp *fp) diff --git a/arch/arm/kernel/signal.c b/arch/arm/kernel/signal.c index 1423a3419789..2a573d4fea24 100644 --- a/arch/arm/kernel/signal.c +++ b/arch/arm/kernel/signal.c @@ -1,7 +1,7 @@ /* * linux/arch/arm/kernel/signal.c * - * Copyright (C) 1995-2002 Russell King + * Copyright (C) 1995-2009 Russell King * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as @@ -29,6 +29,7 @@ */ #define SWI_SYS_SIGRETURN (0xef000000|(__NR_sigreturn)|(__NR_OABI_SYSCALL_BASE)) #define SWI_SYS_RT_SIGRETURN (0xef000000|(__NR_rt_sigreturn)|(__NR_OABI_SYSCALL_BASE)) +#define SWI_SYS_RESTART (0xef000000|__NR_restart_syscall|__NR_OABI_SYSCALL_BASE) /* * With EABI, the syscall number has to be loaded into r7. @@ -49,6 +50,18 @@ const unsigned long sigreturn_codes[7] = { }; /* + * Either we support OABI only, or we have EABI with the OABI + * compat layer enabled. In the later case we don't know if + * user space is EABI or not, and if not we must not clobber r7. + * Always using the OABI syscall solves that issue and works for + * all those cases. + */ +const unsigned long syscall_restart_code[2] = { + SWI_SYS_RESTART, /* swi __NR_restart_syscall */ + 0xe49df004, /* ldr pc, [sp], #4 */ +}; + +/* * atomically swap in the new signal mask, and wait for a signal. */ asmlinkage int sys_sigsuspend(int restart, unsigned long oldmask, old_sigset_t mask) @@ -645,32 +658,12 @@ static void do_signal(struct pt_regs *regs, int syscall) regs->ARM_pc -= 4; #else u32 __user *usp; - u32 swival = __NR_restart_syscall; - regs->ARM_sp -= 12; + regs->ARM_sp -= 4; usp = (u32 __user *)regs->ARM_sp; - /* - * Either we supports OABI only, or we have - * EABI with the OABI compat layer enabled. - * In the later case we don't know if user - * space is EABI or not, and if not we must - * not clobber r7. Always using the OABI - * syscall solves that issue and works for - * all those cases. - */ - swival = swival - __NR_SYSCALL_BASE + __NR_OABI_SYSCALL_BASE; - - put_user(regs->ARM_pc, &usp[0]); - /* swi __NR_restart_syscall */ - put_user(0xef000000 | swival, &usp[1]); - /* ldr pc, [sp], #12 */ - put_user(0xe49df00c, &usp[2]); - - flush_icache_range((unsigned long)usp, - (unsigned long)(usp + 3)); - - regs->ARM_pc = regs->ARM_sp + 4; + put_user(regs->ARM_pc, usp); + regs->ARM_pc = KERN_RESTART_CODE; #endif } } diff --git a/arch/arm/kernel/signal.h b/arch/arm/kernel/signal.h index 27beece15502..6fcfe8398aa4 100644 --- a/arch/arm/kernel/signal.h +++ b/arch/arm/kernel/signal.h @@ -1,12 +1,14 @@ /* * linux/arch/arm/kernel/signal.h * - * Copyright (C) 2005 Russell King. + * Copyright (C) 2005-2009 Russell King. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. */ #define KERN_SIGRETURN_CODE (CONFIG_VECTORS_BASE + 0x00000500) +#define KERN_RESTART_CODE (KERN_SIGRETURN_CODE + sizeof(sigreturn_codes)) extern const unsigned long sigreturn_codes[7]; +extern const unsigned long syscall_restart_code[2]; diff --git a/arch/arm/kernel/smp_scu.c b/arch/arm/kernel/smp_scu.c index d3831f616ee9..9ab4149bd983 100644 --- a/arch/arm/kernel/smp_scu.c +++ b/arch/arm/kernel/smp_scu.c @@ -37,6 +37,10 @@ void __init scu_enable(void __iomem *scu_base) u32 scu_ctrl; scu_ctrl = __raw_readl(scu_base + SCU_CTRL); + /* already enabled? */ + if (scu_ctrl & 1) + return; + scu_ctrl |= 1; __raw_writel(scu_ctrl, scu_base + SCU_CTRL); diff --git a/arch/arm/kernel/time.c b/arch/arm/kernel/time.c index 4cdc4a0bd02d..d38cdf2c8276 100644 --- a/arch/arm/kernel/time.c +++ b/arch/arm/kernel/time.c @@ -21,6 +21,7 @@ #include <linux/interrupt.h> #include <linux/time.h> #include <linux/init.h> +#include <linux/sched.h> #include <linux/smp.h> #include <linux/timex.h> #include <linux/errno.h> diff --git a/arch/arm/kernel/traps.c b/arch/arm/kernel/traps.c index 467b69ed1021..3f361a783f43 100644 --- a/arch/arm/kernel/traps.c +++ b/arch/arm/kernel/traps.c @@ -1,7 +1,7 @@ /* * linux/arch/arm/kernel/traps.c * - * Copyright (C) 1995-2002 Russell King + * Copyright (C) 1995-2009 Russell King * Fragments that appear the same as linux/arch/i386/kernel/traps.c (C) Linus Torvalds * * This program is free software; you can redistribute it and/or modify @@ -45,21 +45,21 @@ static int __init user_debug_setup(char *str) __setup("user_debug=", user_debug_setup); #endif -static void dump_mem(const char *str, unsigned long bottom, unsigned long top); +static void dump_mem(const char *, const char *, unsigned long, unsigned long); void dump_backtrace_entry(unsigned long where, unsigned long from, unsigned long frame) { #ifdef CONFIG_KALLSYMS - printk("[<%08lx>] ", where); - print_symbol("(%s) ", where); - printk("from [<%08lx>] ", from); - print_symbol("(%s)\n", from); + char sym1[KSYM_SYMBOL_LEN], sym2[KSYM_SYMBOL_LEN]; + sprint_symbol(sym1, where); + sprint_symbol(sym2, from); + printk("[<%08lx>] (%s) from [<%08lx>] (%s)\n", where, sym1, from, sym2); #else printk("Function entered at [<%08lx>] from [<%08lx>]\n", where, from); #endif if (in_exception_text(where)) - dump_mem("Exception stack", frame + 4, frame + 4 + sizeof(struct pt_regs)); + dump_mem("", "Exception stack", frame + 4, frame + 4 + sizeof(struct pt_regs)); } #ifndef CONFIG_ARM_UNWIND @@ -81,9 +81,10 @@ static int verify_stack(unsigned long sp) /* * Dump out the contents of some memory nicely... */ -static void dump_mem(const char *str, unsigned long bottom, unsigned long top) +static void dump_mem(const char *lvl, const char *str, unsigned long bottom, + unsigned long top) { - unsigned long p = bottom & ~31; + unsigned long first; mm_segment_t fs; int i; @@ -95,33 +96,37 @@ static void dump_mem(const char *str, unsigned long bottom, unsigned long top) fs = get_fs(); set_fs(KERNEL_DS); - printk("%s(0x%08lx to 0x%08lx)\n", str, bottom, top); + printk("%s%s(0x%08lx to 0x%08lx)\n", lvl, str, bottom, top); - for (p = bottom & ~31; p < top;) { - printk("%04lx: ", p & 0xffff); + for (first = bottom & ~31; first < top; first += 32) { + unsigned long p; + char str[sizeof(" 12345678") * 8 + 1]; - for (i = 0; i < 8; i++, p += 4) { - unsigned int val; + memset(str, ' ', sizeof(str)); + str[sizeof(str) - 1] = '\0'; - if (p < bottom || p >= top) - printk(" "); - else { - __get_user(val, (unsigned long *)p); - printk("%08x ", val); + for (p = first, i = 0; i < 8 && p < top; i++, p += 4) { + if (p >= bottom && p < top) { + unsigned long val; + if (__get_user(val, (unsigned long *)p) == 0) + sprintf(str + i * 9, " %08lx", val); + else + sprintf(str + i * 9, " ????????"); } } - printk ("\n"); + printk("%s%04lx:%s\n", lvl, first & 0xffff, str); } set_fs(fs); } -static void dump_instr(struct pt_regs *regs) +static void dump_instr(const char *lvl, struct pt_regs *regs) { unsigned long addr = instruction_pointer(regs); const int thumb = thumb_mode(regs); const int width = thumb ? 4 : 8; mm_segment_t fs; + char str[sizeof("00000000 ") * 5 + 2 + 1], *p = str; int i; /* @@ -132,7 +137,6 @@ static void dump_instr(struct pt_regs *regs) fs = get_fs(); set_fs(KERNEL_DS); - printk("Code: "); for (i = -4; i < 1; i++) { unsigned int val, bad; @@ -142,13 +146,14 @@ static void dump_instr(struct pt_regs *regs) bad = __get_user(val, &((u32 *)addr)[i]); if (!bad) - printk(i == 0 ? "(%0*x) " : "%0*x ", width, val); + p += sprintf(p, i == 0 ? "(%0*x) " : "%0*x ", + width, val); else { - printk("bad PC value."); + p += sprintf(p, "bad PC value"); break; } } - printk("\n"); + printk("%sCode: %s\n", lvl, str); set_fs(fs); } @@ -224,18 +229,19 @@ static void __die(const char *str, int err, struct thread_info *thread, struct p struct task_struct *tsk = thread->task; static int die_counter; - printk("Internal error: %s: %x [#%d]" S_PREEMPT S_SMP "\n", + printk(KERN_EMERG "Internal error: %s: %x [#%d]" S_PREEMPT S_SMP "\n", str, err, ++die_counter); + sysfs_printk_last_file(); print_modules(); __show_regs(regs); - printk("Process %s (pid: %d, stack limit = 0x%p)\n", - tsk->comm, task_pid_nr(tsk), thread + 1); + printk(KERN_EMERG "Process %.*s (pid: %d, stack limit = 0x%p)\n", + TASK_COMM_LEN, tsk->comm, task_pid_nr(tsk), thread + 1); if (!user_mode(regs) || in_interrupt()) { - dump_mem("Stack: ", regs->ARM_sp, + dump_mem(KERN_EMERG, "Stack: ", regs->ARM_sp, THREAD_SIZE + (unsigned long)task_stack_page(tsk)); dump_backtrace(regs, tsk); - dump_instr(regs); + dump_instr(KERN_EMERG, regs); } } @@ -250,13 +256,14 @@ NORET_TYPE void die(const char *str, struct pt_regs *regs, int err) oops_enter(); - console_verbose(); spin_lock_irq(&die_lock); + console_verbose(); bust_spinlocks(1); __die(str, err, thread, regs); bust_spinlocks(0); add_taint(TAINT_DIE); spin_unlock_irq(&die_lock); + oops_exit(); if (in_interrupt()) panic("Fatal exception in interrupt"); @@ -264,7 +271,6 @@ NORET_TYPE void die(const char *str, struct pt_regs *regs, int err) if (panic_on_oops) panic("Fatal exception"); - oops_exit(); do_exit(SIGSEGV); } @@ -349,7 +355,7 @@ asmlinkage void __exception do_undefinstr(struct pt_regs *regs) if (user_debug & UDBG_UNDEFINED) { printk(KERN_INFO "%s (%d): undefined instruction: pc=%p\n", current->comm, task_pid_nr(current), pc); - dump_instr(regs); + dump_instr(KERN_INFO, regs); } #endif @@ -400,7 +406,7 @@ static int bad_syscall(int n, struct pt_regs *regs) if (user_debug & UDBG_SYSCALL) { printk(KERN_ERR "[%d] %s: obsolete system call %08x.\n", task_pid_nr(current), current->comm, n); - dump_instr(regs); + dump_instr(KERN_ERR, regs); } #endif @@ -522,7 +528,7 @@ asmlinkage int arm_syscall(int no, struct pt_regs *regs) * __kuser_cmpxchg code in entry-armv.S should be aware of its * existence. Don't ever use this from user code. */ - case 0xfff0: + case NR(cmpxchg): for (;;) { extern void do_DataAbort(unsigned long addr, unsigned int fsr, struct pt_regs *regs); @@ -567,7 +573,7 @@ asmlinkage int arm_syscall(int no, struct pt_regs *regs) if not implemented, rather than raising SIGILL. This way the calling program can gracefully determine whether a feature is supported. */ - if (no <= 0x7ff) + if ((no & 0xffff) <= 0x7ff) return -ENOSYS; break; } @@ -579,7 +585,7 @@ asmlinkage int arm_syscall(int no, struct pt_regs *regs) if (user_debug & UDBG_SYSCALL) { printk("[%d] %s: arm syscall %d\n", task_pid_nr(current), current->comm, no); - dump_instr(regs); + dump_instr("", regs); if (user_mode(regs)) { __show_regs(regs); c_backtrace(regs->ARM_fp, processor_mode(regs)); @@ -656,7 +662,7 @@ baddataabort(int code, unsigned long instr, struct pt_regs *regs) if (user_debug & UDBG_BADABORT) { printk(KERN_ERR "[%d] %s: bad data abort: code %d instr 0x%08lx\n", task_pid_nr(current), current->comm, code, instr); - dump_instr(regs); + dump_instr(KERN_ERR, regs); show_pte(current->mm, addr); } #endif @@ -745,6 +751,8 @@ void __init early_trap_init(void) */ memcpy((void *)KERN_SIGRETURN_CODE, sigreturn_codes, sizeof(sigreturn_codes)); + memcpy((void *)KERN_RESTART_CODE, syscall_restart_code, + sizeof(syscall_restart_code)); flush_icache_range(vectors, vectors + PAGE_SIZE); modify_domain(DOMAIN_USER, DOMAIN_CLIENT); diff --git a/arch/arm/kernel/unwind.c b/arch/arm/kernel/unwind.c index 39baf1128bfa..786ac2b6914a 100644 --- a/arch/arm/kernel/unwind.c +++ b/arch/arm/kernel/unwind.c @@ -26,6 +26,15 @@ * http://infocenter.arm.com/help/topic/com.arm.doc.subset.swdev.abi/index.html */ +#if !defined (__ARM_EABI__) +#warning Your compiler does not have EABI support. +#warning ARM unwind is known to compile only with EABI compilers. +#warning Change compiler or disable ARM_UNWIND option. +#elif (__GNUC__ == 4 && __GNUC_MINOR__ <= 2) +#warning Your compiler is too buggy; it is known to not compile ARM unwind support. +#warning Change compiler or disable ARM_UNWIND option. +#endif + #include <linux/kernel.h> #include <linux/init.h> #include <linux/module.h> diff --git a/arch/arm/mach-at91/Kconfig b/arch/arm/mach-at91/Kconfig index e35d54d43e70..2fd88437348b 100644 --- a/arch/arm/mach-at91/Kconfig +++ b/arch/arm/mach-at91/Kconfig @@ -289,13 +289,6 @@ config MACH_NEOCORE926 help Select this if you are using the Adeneo Neocore 926 board. -config MACH_AT91SAM9G20EK_2MMC - bool "Atmel AT91SAM9G20-EK Evaluation Kit modified for 2 MMC Slots" - depends on ARCH_AT91SAM9G20 - help - Select this if you are using an Atmel AT91SAM9G20-EK Evaluation Kit - Rev A or B modified for 2 MMC Slots. - endif # ---------------------------------------------------------- @@ -322,7 +315,16 @@ config MACH_AT91SAM9G20EK bool "Atmel AT91SAM9G20-EK Evaluation Kit" depends on ARCH_AT91SAM9G20 help - Select this if you are using Atmel's AT91SAM9G20-EK Evaluation Kit. + Select this if you are using Atmel's AT91SAM9G20-EK Evaluation Kit + that embeds only one SD/MMC slot. + +config MACH_AT91SAM9G20EK_2MMC + bool "Atmel AT91SAM9G20-EK Evaluation Kit with 2 SD/MMC Slots" + depends on ARCH_AT91SAM9G20 + help + Select this if you are using an Atmel AT91SAM9G20-EK Evaluation Kit + with 2 SD/MMC Slots. This is the case for AT91SAM9G20-EK rev. C and + onwards. config MACH_CPU9G20 bool "Eukrea CPU9G20 board" @@ -392,7 +394,7 @@ config MTD_AT91_DATAFLASH_CARD config MTD_NAND_ATMEL_BUSWIDTH_16 bool "Enable 16-bit data bus interface to NAND flash" - depends on (MACH_AT91SAM9260EK || MACH_AT91SAM9261EK || MACH_AT91SAM9G10EK || MACH_AT91SAM9263EK || MACH_AT91SAM9G20EK || MACH_AT91SAM9G45EKES || MACH_AT91CAP9ADK) + depends on (MACH_AT91SAM9260EK || MACH_AT91SAM9261EK || MACH_AT91SAM9G10EK || MACH_AT91SAM9263EK || MACH_AT91SAM9G20EK || MACH_AT91SAM9G20EK_2MMC || MACH_AT91SAM9G45EKES || MACH_AT91CAP9ADK) help On AT91SAM926x boards both types of NAND flash can be present (8 and 16 bit data bus width). diff --git a/arch/arm/mach-at91/at91sam9g45_devices.c b/arch/arm/mach-at91/at91sam9g45_devices.c index d581cff80c4c..332b784050b2 100644 --- a/arch/arm/mach-at91/at91sam9g45_devices.c +++ b/arch/arm/mach-at91/at91sam9g45_devices.c @@ -838,7 +838,7 @@ static void __init at91_add_device_rtt(void) * Watchdog * -------------------------------------------------------------------- */ -#if defined(CONFIG_AT91SAM9_WATCHDOG) || defined(CONFIG_AT91SAM9_WATCHDOG_MODULE) +#if defined(CONFIG_AT91SAM9X_WATCHDOG) || defined(CONFIG_AT91SAM9X_WATCHDOG_MODULE) static struct platform_device at91sam9g45_wdt_device = { .name = "at91_wdt", .id = -1, diff --git a/arch/arm/mach-at91/board-sam9g20ek-2slot-mmc.c b/arch/arm/mach-at91/board-sam9g20ek-2slot-mmc.c index a28e53faf71d..a4102d72cc9b 100644 --- a/arch/arm/mach-at91/board-sam9g20ek-2slot-mmc.c +++ b/arch/arm/mach-at91/board-sam9g20ek-2slot-mmc.c @@ -90,7 +90,7 @@ static struct at91_udc_data __initdata ek_udc_data = { * SPI devices. */ static struct spi_board_info ek_spi_devices[] = { -#if !defined(CONFIG_MMC_ATMELMCI) +#if !(defined(CONFIG_MMC_ATMELMCI) || defined(CONFIG_MMC_AT91)) { /* DataFlash chip */ .modalias = "mtd_dataflash", .chip_select = 1, @@ -113,7 +113,7 @@ static struct spi_board_info ek_spi_devices[] = { * MACB Ethernet device */ static struct at91_eth_data __initdata ek_macb_data = { - .phy_irq_pin = AT91_PIN_PC12, + .phy_irq_pin = AT91_PIN_PB0, .is_rmii = 1, }; @@ -194,24 +194,27 @@ static void __init ek_add_device_nand(void) /* * MCI (SD/MMC) - * det_pin and wp_pin are not connected + * wp_pin is not connected */ #if defined(CONFIG_MMC_ATMELMCI) || defined(CONFIG_MMC_ATMELMCI_MODULE) static struct mci_platform_data __initdata ek_mmc_data = { .slot[0] = { .bus_width = 4, - .detect_pin = -ENODEV, + .detect_pin = AT91_PIN_PC2, .wp_pin = -ENODEV, }, .slot[1] = { .bus_width = 4, - .detect_pin = -ENODEV, + .detect_pin = AT91_PIN_PC9, .wp_pin = -ENODEV, }, }; #else -static struct amci_platform_data __initdata ek_mmc_data = { +static struct at91_mmc_data __initdata ek_mmc_data = { + .slot_b = 1, /* Only one slot so use slot B */ + .wire4 = 1, + .det_pin = AT91_PIN_PC9, }; #endif @@ -221,13 +224,13 @@ static struct amci_platform_data __initdata ek_mmc_data = { static struct gpio_led ek_leds[] = { { /* "bottom" led, green, userled1 to be defined */ .name = "ds5", - .gpio = AT91_PIN_PB12, + .gpio = AT91_PIN_PB8, .active_low = 1, .default_trigger = "none", }, { /* "power" led, yellow */ .name = "ds1", - .gpio = AT91_PIN_PB13, + .gpio = AT91_PIN_PB9, .default_trigger = "heartbeat", } }; @@ -254,7 +257,11 @@ static void __init ek_board_init(void) /* Ethernet */ at91_add_device_eth(&ek_macb_data); /* MMC */ +#if defined(CONFIG_MMC_ATMELMCI) || defined(CONFIG_MMC_ATMELMCI_MODULE) at91_add_device_mci(0, &ek_mmc_data); +#else + at91_add_device_mmc(0, &ek_mmc_data); +#endif /* I2C */ at91_add_device_i2c(ek_i2c_devices, ARRAY_SIZE(ek_i2c_devices)); /* LEDs */ diff --git a/arch/arm/mach-at91/include/mach/cpu.h b/arch/arm/mach-at91/include/mach/cpu.h index 34a9502c48bc..c22df30ed5e5 100644 --- a/arch/arm/mach-at91/include/mach/cpu.h +++ b/arch/arm/mach-at91/include/mach/cpu.h @@ -25,6 +25,8 @@ #define ARCH_ID_AT91SAM9G20 0x019905a0 #define ARCH_ID_AT91SAM9RL64 0x019b03a0 #define ARCH_ID_AT91SAM9G45 0x819b05a0 +#define ARCH_ID_AT91SAM9G45MRL 0x819b05a2 /* aka 9G45-ES2 & non ES lots */ +#define ARCH_ID_AT91SAM9G45ES 0x819b05a1 /* 9G45-ES (Engineering Sample) */ #define ARCH_ID_AT91CAP9 0x039A03A0 #define ARCH_ID_AT91SAM9XE128 0x329973a0 @@ -41,6 +43,11 @@ static inline unsigned long at91_cpu_identify(void) return (at91_sys_read(AT91_DBGU_CIDR) & ~AT91_CIDR_VERSION); } +static inline unsigned long at91_cpu_fully_identify(void) +{ + return at91_sys_read(AT91_DBGU_CIDR); +} + #define ARCH_EXID_AT91SAM9M11 0x00000001 #define ARCH_EXID_AT91SAM9M10 0x00000002 #define ARCH_EXID_AT91SAM9G45 0x00000004 @@ -118,8 +125,10 @@ static inline unsigned long at91cap9_rev_identify(void) #ifdef CONFIG_ARCH_AT91SAM9G45 #define cpu_is_at91sam9g45() (at91_cpu_identify() == ARCH_ID_AT91SAM9G45) +#define cpu_is_at91sam9g45es() (at91_cpu_fully_identify() == ARCH_ID_AT91SAM9G45ES) #else #define cpu_is_at91sam9g45() (0) +#define cpu_is_at91sam9g45es() (0) #endif #ifdef CONFIG_ARCH_AT91CAP9 diff --git a/arch/arm/mach-bcmring/core.c b/arch/arm/mach-bcmring/core.c index 4b4f69251b31..e590bbe0a7b4 100644 --- a/arch/arm/mach-bcmring/core.c +++ b/arch/arm/mach-bcmring/core.c @@ -271,12 +271,12 @@ static struct irqaction bcmring_timer_irq = { .handler = bcmring_timer_interrupt, }; -static cycle_t bcmring_get_cycles_timer1(void) +static cycle_t bcmring_get_cycles_timer1(struct clocksource *cs) { return ~readl(TIMER1_VA_BASE + TIMER_VALUE); } -static cycle_t bcmring_get_cycles_timer3(void) +static cycle_t bcmring_get_cycles_timer3(struct clocksource *cs) { return ~readl(TIMER3_VA_BASE + TIMER_VALUE); } diff --git a/arch/arm/mach-bcmring/include/mach/system.h b/arch/arm/mach-bcmring/include/mach/system.h index cdbf93c694a6..38b37060d426 100644 --- a/arch/arm/mach-bcmring/include/mach/system.h +++ b/arch/arm/mach-bcmring/include/mach/system.h @@ -29,7 +29,7 @@ static inline void arch_idle(void) cpu_do_idle(); } -static inline void arch_reset(char mode, char *cmd) +static inline void arch_reset(char mode, const char *cmd) { printk("arch_reset:%c %x\n", mode, bcmring_arch_warm_reboot); diff --git a/arch/arm/mach-ep93xx/Kconfig b/arch/arm/mach-ep93xx/Kconfig index d7291c682a64..9167c3d2a5ed 100644 --- a/arch/arm/mach-ep93xx/Kconfig +++ b/arch/arm/mach-ep93xx/Kconfig @@ -17,13 +17,31 @@ config EP93XX_SDCE3_SYNC_PHYS_OFFSET bool "0x00000000 - SDCE3/SyncBoot" help Select this option if you want support for EP93xx boards with the - first SDRAM bank at 0x00000000 + first SDRAM bank at 0x00000000. config EP93XX_SDCE0_PHYS_OFFSET bool "0xc0000000 - SDCEO" help Select this option if you want support for EP93xx boards with the - first SDRAM bank at 0xc0000000 + first SDRAM bank at 0xc0000000. + +config EP93XX_SDCE1_PHYS_OFFSET + bool "0xd0000000 - SDCE1" + help + Select this option if you want support for EP93xx boards with the + first SDRAM bank at 0xd0000000. + +config EP93XX_SDCE2_PHYS_OFFSET + bool "0xe0000000 - SDCE2" + help + Select this option if you want support for EP93xx boards with the + first SDRAM bank at 0xe0000000. + +config EP93XX_SDCE3_ASYNC_PHYS_OFFSET + bool "0xf0000000 - SDCE3/AsyncBoot" + help + Select this option if you want support for EP93xx boards with the + first SDRAM bank at 0xf0000000. endchoice @@ -112,28 +130,36 @@ config MACH_MICRO9 bool config MACH_MICRO9H - bool "Support Contec Hypercontrol Micro9-H" + bool "Support Contec Micro9-High" depends on EP93XX_SDCE3_SYNC_PHYS_OFFSET select MACH_MICRO9 help Say 'Y' here if you want your kernel to support the - Contec Hypercontrol Micro9-H board. + Contec Micro9-High board. config MACH_MICRO9M - bool "Support Contec Hypercontrol Micro9-M" - depends on EP93XX_SDCE3_SYNC_PHYS_OFFSET + bool "Support Contec Micro9-Mid" + depends on EP93XX_SDCE3_ASYNC_PHYS_OFFSET select MACH_MICRO9 help Say 'Y' here if you want your kernel to support the - Contec Hypercontrol Micro9-M board. + Contec Micro9-Mid board. config MACH_MICRO9L - bool "Support Contec Hypercontrol Micro9-L" + bool "Support Contec Micro9-Lite" depends on EP93XX_SDCE3_SYNC_PHYS_OFFSET select MACH_MICRO9 help Say 'Y' here if you want your kernel to support the - Contec Hypercontrol Micro9-L board. + Contec Micro9-Lite board. + +config MACH_MICRO9S + bool "Support Contec Micro9-Slim" + depends on EP93XX_SDCE3_ASYNC_PHYS_OFFSET + select MACH_MICRO9 + help + Say 'Y' here if you want your kernel to support the + Contec Micro9-Slim board. config MACH_TS72XX bool "Support Technologic Systems TS-72xx SBC" diff --git a/arch/arm/mach-ep93xx/Makefile.boot b/arch/arm/mach-ep93xx/Makefile.boot index 27a085a8f12a..0ad33f15c622 100644 --- a/arch/arm/mach-ep93xx/Makefile.boot +++ b/arch/arm/mach-ep93xx/Makefile.boot @@ -3,3 +3,12 @@ params_phys-$(CONFIG_EP93XX_SDCE3_SYNC_PHYS_OFFSET) := 0x00000100 zreladdr-$(CONFIG_EP93XX_SDCE0_PHYS_OFFSET) := 0xc0008000 params_phys-$(CONFIG_EP93XX_SDCE0_PHYS_OFFSET) := 0xc0000100 + + zreladdr-$(CONFIG_EP93XX_SDCE1_PHYS_OFFSET) := 0xd0008000 +params_phys-$(CONFIG_EP93XX_SDCE1_PHYS_OFFSET) := 0xd0000100 + + zreladdr-$(CONFIG_EP93XX_SDCE2_PHYS_OFFSET) := 0xe0008000 +params_phys-$(CONFIG_EP93XX_SDCE2_PHYS_OFFSET) := 0xe0000100 + + zreladdr-$(CONFIG_EP93XX_SDCE3_ASYNC_PHYS_OFFSET) := 0xf0008000 +params_phys-$(CONFIG_EP93XX_SDCE3_ASYNC_PHYS_OFFSET) := 0xf0000100 diff --git a/arch/arm/mach-ep93xx/clock.c b/arch/arm/mach-ep93xx/clock.c index dda19cd76194..1d0f9d8aff2e 100644 --- a/arch/arm/mach-ep93xx/clock.c +++ b/arch/arm/mach-ep93xx/clock.c @@ -16,13 +16,16 @@ #include <linux/module.h> #include <linux/string.h> #include <linux/io.h> +#include <linux/spinlock.h> + +#include <mach/hardware.h> #include <asm/clkdev.h> #include <asm/div64.h> -#include <mach/hardware.h> struct clk { + struct clk *parent; unsigned long rate; int users; int sw_locked; @@ -39,40 +42,60 @@ static unsigned long get_uart_rate(struct clk *clk); static int set_keytchclk_rate(struct clk *clk, unsigned long rate); static int set_div_rate(struct clk *clk, unsigned long rate); + +static struct clk clk_xtali = { + .rate = EP93XX_EXT_CLK_RATE, +}; static struct clk clk_uart1 = { + .parent = &clk_xtali, .sw_locked = 1, .enable_reg = EP93XX_SYSCON_DEVCFG, .enable_mask = EP93XX_SYSCON_DEVCFG_U1EN, .get_rate = get_uart_rate, }; static struct clk clk_uart2 = { + .parent = &clk_xtali, .sw_locked = 1, .enable_reg = EP93XX_SYSCON_DEVCFG, .enable_mask = EP93XX_SYSCON_DEVCFG_U2EN, .get_rate = get_uart_rate, }; static struct clk clk_uart3 = { + .parent = &clk_xtali, .sw_locked = 1, .enable_reg = EP93XX_SYSCON_DEVCFG, .enable_mask = EP93XX_SYSCON_DEVCFG_U3EN, .get_rate = get_uart_rate, }; -static struct clk clk_pll1; -static struct clk clk_f; -static struct clk clk_h; -static struct clk clk_p; -static struct clk clk_pll2; +static struct clk clk_pll1 = { + .parent = &clk_xtali, +}; +static struct clk clk_f = { + .parent = &clk_pll1, +}; +static struct clk clk_h = { + .parent = &clk_pll1, +}; +static struct clk clk_p = { + .parent = &clk_pll1, +}; +static struct clk clk_pll2 = { + .parent = &clk_xtali, +}; static struct clk clk_usb_host = { + .parent = &clk_pll2, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_USH_EN, }; static struct clk clk_keypad = { + .parent = &clk_xtali, .sw_locked = 1, .enable_reg = EP93XX_SYSCON_KEYTCHCLKDIV, .enable_mask = EP93XX_SYSCON_KEYTCHCLKDIV_KEN, .set_rate = set_keytchclk_rate, }; static struct clk clk_pwm = { + .parent = &clk_xtali, .rate = EP93XX_EXT_CLK_RATE, }; @@ -85,50 +108,62 @@ static struct clk clk_video = { /* DMA Clocks */ static struct clk clk_m2p0 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P0, }; static struct clk clk_m2p1 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P1, }; static struct clk clk_m2p2 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P2, }; static struct clk clk_m2p3 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P3, }; static struct clk clk_m2p4 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P4, }; static struct clk clk_m2p5 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P5, }; static struct clk clk_m2p6 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P6, }; static struct clk clk_m2p7 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P7, }; static struct clk clk_m2p8 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P8, }; static struct clk clk_m2p9 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2P9, }; static struct clk clk_m2m0 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2M0, }; static struct clk clk_m2m1 = { + .parent = &clk_h, .enable_reg = EP93XX_SYSCON_PWRCNT, .enable_mask = EP93XX_SYSCON_PWRCNT_DMA_M2M1, }; @@ -137,6 +172,7 @@ static struct clk clk_m2m1 = { { .dev_id = dev, .con_id = con, .clk = ck } static struct clk_lookup clocks[] = { + INIT_CK(NULL, "xtali", &clk_xtali), INIT_CK("apb:uart1", NULL, &clk_uart1), INIT_CK("apb:uart2", NULL, &clk_uart2), INIT_CK("apb:uart3", NULL, &clk_uart3), @@ -163,48 +199,84 @@ static struct clk_lookup clocks[] = { INIT_CK(NULL, "m2m1", &clk_m2m1), }; +static DEFINE_SPINLOCK(clk_lock); + +static void __clk_enable(struct clk *clk) +{ + if (!clk->users++) { + if (clk->parent) + __clk_enable(clk->parent); + + if (clk->enable_reg) { + u32 v; + + v = __raw_readl(clk->enable_reg); + v |= clk->enable_mask; + if (clk->sw_locked) + ep93xx_syscon_swlocked_write(v, clk->enable_reg); + else + __raw_writel(v, clk->enable_reg); + } + } +} int clk_enable(struct clk *clk) { - if (!clk->users++ && clk->enable_reg) { - u32 value; + unsigned long flags; - value = __raw_readl(clk->enable_reg); - value |= clk->enable_mask; - if (clk->sw_locked) - ep93xx_syscon_swlocked_write(value, clk->enable_reg); - else - __raw_writel(value, clk->enable_reg); - } + if (!clk) + return -EINVAL; + + spin_lock_irqsave(&clk_lock, flags); + __clk_enable(clk); + spin_unlock_irqrestore(&clk_lock, flags); return 0; } EXPORT_SYMBOL(clk_enable); -void clk_disable(struct clk *clk) +static void __clk_disable(struct clk *clk) { - if (!--clk->users && clk->enable_reg) { - u32 value; + if (!--clk->users) { + if (clk->enable_reg) { + u32 v; + + v = __raw_readl(clk->enable_reg); + v &= ~clk->enable_mask; + if (clk->sw_locked) + ep93xx_syscon_swlocked_write(v, clk->enable_reg); + else + __raw_writel(v, clk->enable_reg); + } - value = __raw_readl(clk->enable_reg); - value &= ~clk->enable_mask; - if (clk->sw_locked) - ep93xx_syscon_swlocked_write(value, clk->enable_reg); - else - __raw_writel(value, clk->enable_reg); + if (clk->parent) + __clk_disable(clk->parent); } } + +void clk_disable(struct clk *clk) +{ + unsigned long flags; + + if (!clk) + return; + + spin_lock_irqsave(&clk_lock, flags); + __clk_disable(clk); + spin_unlock_irqrestore(&clk_lock, flags); +} EXPORT_SYMBOL(clk_disable); static unsigned long get_uart_rate(struct clk *clk) { + unsigned long rate = clk_get_rate(clk->parent); u32 value; value = __raw_readl(EP93XX_SYSCON_PWRCNT); if (value & EP93XX_SYSCON_PWRCNT_UARTBAUD) - return EP93XX_EXT_CLK_RATE; + return rate; else - return EP93XX_EXT_CLK_RATE / 2; + return rate / 2; } unsigned long clk_get_rate(struct clk *clk) @@ -244,16 +316,16 @@ static int set_keytchclk_rate(struct clk *clk, unsigned long rate) return 0; } -static unsigned long calc_clk_div(unsigned long rate, int *psel, int *esel, - int *pdiv, int *div) +static int calc_clk_div(struct clk *clk, unsigned long rate, + int *psel, int *esel, int *pdiv, int *div) { - unsigned long max_rate, best_rate = 0, - actual_rate = 0, mclk_rate = 0, rate_err = -1; + struct clk *mclk; + unsigned long max_rate, actual_rate, mclk_rate, rate_err = -1; int i, found = 0, __div = 0, __pdiv = 0; /* Don't exceed the maximum rate */ max_rate = max(max(clk_pll1.rate / 4, clk_pll2.rate / 4), - (unsigned long)EP93XX_EXT_CLK_RATE / 4); + clk_xtali.rate / 4); rate = min(rate, max_rate); /* @@ -267,11 +339,12 @@ static unsigned long calc_clk_div(unsigned long rate, int *psel, int *esel, */ for (i = 0; i < 3; i++) { if (i == 0) - mclk_rate = EP93XX_EXT_CLK_RATE * 2; + mclk = &clk_xtali; else if (i == 1) - mclk_rate = clk_pll1.rate * 2; - else if (i == 2) - mclk_rate = clk_pll2.rate * 2; + mclk = &clk_pll1; + else + mclk = &clk_pll2; + mclk_rate = mclk->rate * 2; /* Try each predivider value */ for (__pdiv = 4; __pdiv <= 6; __pdiv++) { @@ -286,7 +359,8 @@ static unsigned long calc_clk_div(unsigned long rate, int *psel, int *esel, *div = __div; *psel = (i == 2); *esel = (i != 0); - best_rate = actual_rate; + clk->parent = mclk; + clk->rate = actual_rate; rate_err = abs(actual_rate - rate); found = 1; } @@ -294,21 +368,19 @@ static unsigned long calc_clk_div(unsigned long rate, int *psel, int *esel, } if (!found) - return 0; + return -EINVAL; - return best_rate; + return 0; } static int set_div_rate(struct clk *clk, unsigned long rate) { - unsigned long actual_rate; - int psel = 0, esel = 0, pdiv = 0, div = 0; + int err, psel = 0, esel = 0, pdiv = 0, div = 0; u32 val; - actual_rate = calc_clk_div(rate, &psel, &esel, &pdiv, &div); - if (actual_rate == 0) - return -EINVAL; - clk->rate = actual_rate; + err = calc_clk_div(clk, rate, &psel, &esel, &pdiv, &div); + if (err) + return err; /* Clear the esel, psel, pdiv and div bits */ val = __raw_readl(clk->enable_reg); @@ -344,7 +416,7 @@ static unsigned long calc_pll_rate(u32 config_word) unsigned long long rate; int i; - rate = EP93XX_EXT_CLK_RATE; + rate = clk_xtali.rate; rate *= ((config_word >> 11) & 0x1f) + 1; /* X1FBD */ rate *= ((config_word >> 5) & 0x3f) + 1; /* X2FBD */ do_div(rate, (config_word & 0x1f) + 1); /* X2IPD */ @@ -377,7 +449,7 @@ static int __init ep93xx_clock_init(void) value = __raw_readl(EP93XX_SYSCON_CLOCK_SET1); if (!(value & 0x00800000)) { /* PLL1 bypassed? */ - clk_pll1.rate = EP93XX_EXT_CLK_RATE; + clk_pll1.rate = clk_xtali.rate; } else { clk_pll1.rate = calc_pll_rate(value); } @@ -388,7 +460,7 @@ static int __init ep93xx_clock_init(void) value = __raw_readl(EP93XX_SYSCON_CLOCK_SET2); if (!(value & 0x00080000)) { /* PLL2 bypassed? */ - clk_pll2.rate = EP93XX_EXT_CLK_RATE; + clk_pll2.rate = clk_xtali.rate; } else if (value & 0x00040000) { /* PLL2 enabled? */ clk_pll2.rate = calc_pll_rate(value); } else { diff --git a/arch/arm/mach-ep93xx/core.c b/arch/arm/mach-ep93xx/core.c index f7ebed942f66..b4357c388d2e 100644 --- a/arch/arm/mach-ep93xx/core.c +++ b/arch/arm/mach-ep93xx/core.c @@ -206,7 +206,6 @@ static void ep93xx_gpio_ab_irq_handler(unsigned int irq, struct irq_desc *desc) for (i = 0; i < 8; i++) { if (status & (1 << i)) { int gpio_irq = gpio_to_irq(EP93XX_GPIO_LINE_B(0)) + i; - desc = irq_desc + gpio_irq; generic_handle_irq(gpio_irq); } } @@ -550,13 +549,11 @@ void __init ep93xx_register_eth(struct ep93xx_eth_data *data, int copy_addr) platform_device_register(&ep93xx_eth_device); } -static struct i2c_gpio_platform_data ep93xx_i2c_data = { - .sda_pin = EP93XX_GPIO_LINE_EEDAT, - .sda_is_open_drain = 0, - .scl_pin = EP93XX_GPIO_LINE_EECLK, - .scl_is_open_drain = 0, - .udelay = 2, -}; + +/************************************************************************* + * EP93xx i2c peripheral handling + *************************************************************************/ +static struct i2c_gpio_platform_data ep93xx_i2c_data; static struct platform_device ep93xx_i2c_device = { .name = "i2c-gpio", @@ -564,8 +561,25 @@ static struct platform_device ep93xx_i2c_device = { .dev.platform_data = &ep93xx_i2c_data, }; -void __init ep93xx_register_i2c(struct i2c_board_info *devices, int num) +void __init ep93xx_register_i2c(struct i2c_gpio_platform_data *data, + struct i2c_board_info *devices, int num) { + /* + * Set the EEPROM interface pin drive type control. + * Defines the driver type for the EECLK and EEDAT pins as either + * open drain, which will require an external pull-up, or a normal + * CMOS driver. + */ + if (data->sda_is_open_drain && data->sda_pin != EP93XX_GPIO_LINE_EEDAT) + pr_warning("ep93xx: sda != EEDAT, open drain has no effect\n"); + if (data->scl_is_open_drain && data->scl_pin != EP93XX_GPIO_LINE_EECLK) + pr_warning("ep93xx: scl != EECLK, open drain has no effect\n"); + + __raw_writel((data->sda_is_open_drain << 1) | + (data->scl_is_open_drain << 0), + EP93XX_GPIO_EEDRIVE); + + ep93xx_i2c_data = *data; i2c_register_board_info(0, devices, num); platform_device_register(&ep93xx_i2c_device); } diff --git a/arch/arm/mach-ep93xx/edb93xx.c b/arch/arm/mach-ep93xx/edb93xx.c index 73145ae5d3fa..a4a7be308000 100644 --- a/arch/arm/mach-ep93xx/edb93xx.c +++ b/arch/arm/mach-ep93xx/edb93xx.c @@ -27,8 +27,10 @@ #include <linux/kernel.h> #include <linux/init.h> #include <linux/platform_device.h> -#include <linux/i2c.h> #include <linux/mtd/physmap.h> +#include <linux/gpio.h> +#include <linux/i2c.h> +#include <linux/i2c-gpio.h> #include <mach/hardware.h> @@ -76,13 +78,26 @@ static struct ep93xx_eth_data edb93xx_eth_data = { .phy_id = 1, }; -static struct i2c_board_info __initdata edb93xxa_i2c_data[] = { + +/************************************************************************* + * EDB93xx i2c peripheral handling + *************************************************************************/ +static struct i2c_gpio_platform_data edb93xx_i2c_gpio_data = { + .sda_pin = EP93XX_GPIO_LINE_EEDAT, + .sda_is_open_drain = 0, + .scl_pin = EP93XX_GPIO_LINE_EECLK, + .scl_is_open_drain = 0, + .udelay = 0, /* default to 100 kHz */ + .timeout = 0, /* default to 100 ms */ +}; + +static struct i2c_board_info __initdata edb93xxa_i2c_board_info[] = { { I2C_BOARD_INFO("isl1208", 0x6f), }, }; -static struct i2c_board_info __initdata edb93xx_i2c_data[] = { +static struct i2c_board_info __initdata edb93xx_i2c_board_info[] = { { I2C_BOARD_INFO("ds1337", 0x68), }, @@ -92,12 +107,14 @@ static void __init edb93xx_register_i2c(void) { if (machine_is_edb9302a() || machine_is_edb9307a() || machine_is_edb9315a()) { - ep93xx_register_i2c(edb93xxa_i2c_data, - ARRAY_SIZE(edb93xxa_i2c_data)); + ep93xx_register_i2c(&edb93xx_i2c_gpio_data, + edb93xxa_i2c_board_info, + ARRAY_SIZE(edb93xxa_i2c_board_info)); } else if (machine_is_edb9307() || machine_is_edb9312() || machine_is_edb9315()) { - ep93xx_register_i2c(edb93xx_i2c_data, - ARRAY_SIZE(edb93xx_i2c_data)); + ep93xx_register_i2c(&edb93xx_i2c_gpio_data, + edb93xx_i2c_board_info, + ARRAY_SIZE(edb93xx_i2c_board_info)); } } diff --git a/arch/arm/mach-ep93xx/include/mach/ep93xx-regs.h b/arch/arm/mach-ep93xx/include/mach/ep93xx-regs.h index 0fbf87b16338..b1f937eda29c 100644 --- a/arch/arm/mach-ep93xx/include/mach/ep93xx-regs.h +++ b/arch/arm/mach-ep93xx/include/mach/ep93xx-regs.h @@ -52,25 +52,27 @@ #define EP93XX_AHB_VIRT_BASE 0xfef00000 #define EP93XX_AHB_SIZE 0x00100000 +#define EP93XX_AHB_PHYS(x) (EP93XX_AHB_PHYS_BASE + (x)) #define EP93XX_AHB_IOMEM(x) IOMEM(EP93XX_AHB_VIRT_BASE + (x)) #define EP93XX_APB_PHYS_BASE 0x80800000 #define EP93XX_APB_VIRT_BASE 0xfed00000 #define EP93XX_APB_SIZE 0x00200000 +#define EP93XX_APB_PHYS(x) (EP93XX_APB_PHYS_BASE + (x)) #define EP93XX_APB_IOMEM(x) IOMEM(EP93XX_APB_VIRT_BASE + (x)) /* AHB peripherals */ #define EP93XX_DMA_BASE EP93XX_AHB_IOMEM(0x00000000) -#define EP93XX_ETHERNET_PHYS_BASE (EP93XX_AHB_PHYS_BASE + 0x00010000) +#define EP93XX_ETHERNET_PHYS_BASE EP93XX_AHB_PHYS(0x00010000) #define EP93XX_ETHERNET_BASE EP93XX_AHB_IOMEM(0x00010000) -#define EP93XX_USB_PHYS_BASE (EP93XX_AHB_PHYS_BASE + 0x00020000) +#define EP93XX_USB_PHYS_BASE EP93XX_AHB_PHYS(0x00020000) #define EP93XX_USB_BASE EP93XX_AHB_IOMEM(0x00020000) -#define EP93XX_RASTER_PHYS_BASE (EP93XX_AHB_PHYS_BASE + 0x00030000) +#define EP93XX_RASTER_PHYS_BASE EP93XX_AHB_PHYS(0x00030000) #define EP93XX_RASTER_BASE EP93XX_AHB_IOMEM(0x00030000) #define EP93XX_GRAPHICS_ACCEL_BASE EP93XX_AHB_IOMEM(0x00040000) @@ -112,21 +114,10 @@ #define EP93XX_GPIO_BASE EP93XX_APB_IOMEM(0x00040000) #define EP93XX_GPIO_REG(x) (EP93XX_GPIO_BASE + (x)) -#define EP93XX_GPIO_F_INT_TYPE1 EP93XX_GPIO_REG(0x4c) -#define EP93XX_GPIO_F_INT_TYPE2 EP93XX_GPIO_REG(0x50) -#define EP93XX_GPIO_F_INT_ACK EP93XX_GPIO_REG(0x54) -#define EP93XX_GPIO_F_INT_ENABLE EP93XX_GPIO_REG(0x58) #define EP93XX_GPIO_F_INT_STATUS EP93XX_GPIO_REG(0x5c) -#define EP93XX_GPIO_A_INT_TYPE1 EP93XX_GPIO_REG(0x90) -#define EP93XX_GPIO_A_INT_TYPE2 EP93XX_GPIO_REG(0x94) -#define EP93XX_GPIO_A_INT_ACK EP93XX_GPIO_REG(0x98) -#define EP93XX_GPIO_A_INT_ENABLE EP93XX_GPIO_REG(0x9c) #define EP93XX_GPIO_A_INT_STATUS EP93XX_GPIO_REG(0xa0) -#define EP93XX_GPIO_B_INT_TYPE1 EP93XX_GPIO_REG(0xac) -#define EP93XX_GPIO_B_INT_TYPE2 EP93XX_GPIO_REG(0xb0) -#define EP93XX_GPIO_B_INT_ACK EP93XX_GPIO_REG(0xb4) -#define EP93XX_GPIO_B_INT_ENABLE EP93XX_GPIO_REG(0xb8) #define EP93XX_GPIO_B_INT_STATUS EP93XX_GPIO_REG(0xbc) +#define EP93XX_GPIO_EEDRIVE EP93XX_GPIO_REG(0xc8) #define EP93XX_AAC_BASE EP93XX_APB_IOMEM(0x00080000) @@ -134,13 +125,13 @@ #define EP93XX_IRDA_BASE EP93XX_APB_IOMEM(0x000b0000) -#define EP93XX_UART1_PHYS_BASE (EP93XX_APB_PHYS_BASE + 0x000c0000) +#define EP93XX_UART1_PHYS_BASE EP93XX_APB_PHYS(0x000c0000) #define EP93XX_UART1_BASE EP93XX_APB_IOMEM(0x000c0000) -#define EP93XX_UART2_PHYS_BASE (EP93XX_APB_PHYS_BASE + 0x000d0000) +#define EP93XX_UART2_PHYS_BASE EP93XX_APB_PHYS(0x000d0000) #define EP93XX_UART2_BASE EP93XX_APB_IOMEM(0x000d0000) -#define EP93XX_UART3_PHYS_BASE (EP93XX_APB_PHYS_BASE + 0x000e0000) +#define EP93XX_UART3_PHYS_BASE EP93XX_APB_PHYS(0x000e0000) #define EP93XX_UART3_BASE EP93XX_APB_IOMEM(0x000e0000) #define EP93XX_KEY_MATRIX_BASE EP93XX_APB_IOMEM(0x000f0000) @@ -148,10 +139,10 @@ #define EP93XX_ADC_BASE EP93XX_APB_IOMEM(0x00100000) #define EP93XX_TOUCHSCREEN_BASE EP93XX_APB_IOMEM(0x00100000) -#define EP93XX_PWM_PHYS_BASE (EP93XX_APB_PHYS_BASE + 0x00110000) +#define EP93XX_PWM_PHYS_BASE EP93XX_APB_PHYS(0x00110000) #define EP93XX_PWM_BASE EP93XX_APB_IOMEM(0x00110000) -#define EP93XX_RTC_PHYS_BASE (EP93XX_APB_PHYS_BASE + 0x00120000) +#define EP93XX_RTC_PHYS_BASE EP93XX_APB_PHYS(0x00120000) #define EP93XX_RTC_BASE EP93XX_APB_IOMEM(0x00120000) #define EP93XX_SYSCON_BASE EP93XX_APB_IOMEM(0x00130000) @@ -218,6 +209,17 @@ #define EP93XX_SYSCON_KEYTCHCLKDIV_ADIV (1<<16) #define EP93XX_SYSCON_KEYTCHCLKDIV_KEN (1<<15) #define EP93XX_SYSCON_KEYTCHCLKDIV_KDIV (1<<0) +#define EP93XX_SYSCON_SYSCFG EP93XX_SYSCON_REG(0x9c) +#define EP93XX_SYSCON_SYSCFG_REV_MASK (0xf0000000) +#define EP93XX_SYSCON_SYSCFG_REV_SHIFT (28) +#define EP93XX_SYSCON_SYSCFG_SBOOT (1<<8) +#define EP93XX_SYSCON_SYSCFG_LCSN7 (1<<7) +#define EP93XX_SYSCON_SYSCFG_LCSN6 (1<<6) +#define EP93XX_SYSCON_SYSCFG_LASDO (1<<5) +#define EP93XX_SYSCON_SYSCFG_LEEDA (1<<4) +#define EP93XX_SYSCON_SYSCFG_LEECLK (1<<3) +#define EP93XX_SYSCON_SYSCFG_LCSN2 (1<<1) +#define EP93XX_SYSCON_SYSCFG_LCSN1 (1<<0) #define EP93XX_SYSCON_SWLOCK EP93XX_SYSCON_REG(0xc0) #define EP93XX_WATCHDOG_BASE EP93XX_APB_IOMEM(0x00140000) diff --git a/arch/arm/mach-ep93xx/include/mach/gpio.h b/arch/arm/mach-ep93xx/include/mach/gpio.h index 0a1498ae899a..c991b149bdf2 100644 --- a/arch/arm/mach-ep93xx/include/mach/gpio.h +++ b/arch/arm/mach-ep93xx/include/mach/gpio.h @@ -114,17 +114,9 @@ extern void ep93xx_gpio_int_debounce(unsigned int irq, int enable); * B0..B7 (7..15) to irq 72..79, and * F0..F7 (16..24) to irq 80..87. */ -static inline int gpio_to_irq(unsigned gpio) -{ - if (gpio <= EP93XX_GPIO_LINE_MAX_IRQ) - return 64 + gpio; - - return -EINVAL; -} - -static inline int irq_to_gpio(unsigned irq) -{ - return irq - gpio_to_irq(0); -} +#define gpio_to_irq(gpio) \ + (((gpio) <= EP93XX_GPIO_LINE_MAX_IRQ) ? (64 + (gpio)) : -EINVAL) + +#define irq_to_gpio(irq) ((irq) - gpio_to_irq(0)) #endif diff --git a/arch/arm/mach-ep93xx/include/mach/memory.h b/arch/arm/mach-ep93xx/include/mach/memory.h index 925b12ea0990..554064e90307 100644 --- a/arch/arm/mach-ep93xx/include/mach/memory.h +++ b/arch/arm/mach-ep93xx/include/mach/memory.h @@ -9,6 +9,12 @@ #define PHYS_OFFSET UL(0x00000000) #elif defined(CONFIG_EP93XX_SDCE0_PHYS_OFFSET) #define PHYS_OFFSET UL(0xc0000000) +#elif defined(CONFIG_EP93XX_SDCE1_PHYS_OFFSET) +#define PHYS_OFFSET UL(0xd0000000) +#elif defined(CONFIG_EP93XX_SDCE2_PHYS_OFFSET) +#define PHYS_OFFSET UL(0xe0000000) +#elif defined(CONFIG_EP93XX_SDCE3_ASYNC_PHYS_OFFSET) +#define PHYS_OFFSET UL(0xf0000000) #else #error "Kconfig bug: No EP93xx PHYS_OFFSET set" #endif diff --git a/arch/arm/mach-ep93xx/include/mach/platform.h b/arch/arm/mach-ep93xx/include/mach/platform.h index 01a0f0838e5b..469fd968d517 100644 --- a/arch/arm/mach-ep93xx/include/mach/platform.h +++ b/arch/arm/mach-ep93xx/include/mach/platform.h @@ -4,6 +4,7 @@ #ifndef __ASSEMBLY__ +struct i2c_gpio_platform_data; struct i2c_board_info; struct platform_device; struct ep93xxfb_mach_info; @@ -16,7 +17,6 @@ struct ep93xx_eth_data void ep93xx_map_io(void); void ep93xx_init_irq(void); -void ep93xx_init_time(unsigned long); /* EP93xx System Controller software locked register write */ void ep93xx_syscon_swlocked_write(unsigned int val, void __iomem *reg); @@ -33,7 +33,8 @@ static inline void ep93xx_devcfg_clear_bits(unsigned int bits) } void ep93xx_register_eth(struct ep93xx_eth_data *data, int copy_addr); -void ep93xx_register_i2c(struct i2c_board_info *devices, int num); +void ep93xx_register_i2c(struct i2c_gpio_platform_data *data, + struct i2c_board_info *devices, int num); void ep93xx_register_fb(struct ep93xxfb_mach_info *data); void ep93xx_register_pwm(int pwm0, int pwm1); int ep93xx_pwm_acquire_gpio(struct platform_device *pdev); diff --git a/arch/arm/mach-ep93xx/micro9.c b/arch/arm/mach-ep93xx/micro9.c index 0a313e82fb74..f3757a1c5a10 100644 --- a/arch/arm/mach-ep93xx/micro9.c +++ b/arch/arm/mach-ep93xx/micro9.c @@ -2,7 +2,9 @@ * linux/arch/arm/mach-ep93xx/micro9.c * * Copyright (C) 2006 Contec Steuerungstechnik & Automation GmbH - * Manfred Gruber <manfred.gruber@contec.at> + * Manfred Gruber <m.gruber@tirol.com> + * Copyright (C) 2009 Contec Steuerungstechnik & Automation GmbH + * Hubert Feurstein <hubert.feurstein@contec.at> * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as @@ -13,6 +15,7 @@ #include <linux/init.h> #include <linux/platform_device.h> #include <linux/mtd/physmap.h> +#include <linux/io.h> #include <mach/hardware.h> @@ -20,104 +23,124 @@ #include <asm/mach/arch.h> -static struct ep93xx_eth_data micro9_eth_data = { - .phy_id = 0x1f, -}; - -static void __init micro9_init(void) -{ - ep93xx_register_eth(µ9_eth_data, 1); -} - -/* - * Micro9-H - */ -#ifdef CONFIG_MACH_MICRO9H -static struct physmap_flash_data micro9h_flash_data = { - .width = 4, -}; - -static struct resource micro9h_flash_resource = { +/************************************************************************* + * Micro9 NOR Flash + * + * Micro9-High has up to 64MB of 32-bit flash on CS1 + * Micro9-Mid has up to 64MB of either 32-bit or 16-bit flash on CS1 + * Micro9-Lite uses a seperate MTD map driver for flash support + * Micro9-Slim has up to 64MB of either 32-bit or 16-bit flash on CS1 + *************************************************************************/ +static struct physmap_flash_data micro9_flash_data; + +static struct resource micro9_flash_resource = { .start = EP93XX_CS1_PHYS_BASE, .end = EP93XX_CS1_PHYS_BASE + SZ_64M - 1, .flags = IORESOURCE_MEM, }; -static struct platform_device micro9h_flash = { +static struct platform_device micro9_flash = { .name = "physmap-flash", .id = 0, .dev = { - .platform_data = µ9h_flash_data, + .platform_data = µ9_flash_data, }, .num_resources = 1, - .resource = µ9h_flash_resource, + .resource = µ9_flash_resource, }; -static void __init micro9h_init(void) +static void __init __micro9_register_flash(unsigned int width) +{ + micro9_flash_data.width = width; + + platform_device_register(µ9_flash); +} + +static unsigned int __init micro9_detect_bootwidth(void) +{ + u32 v; + + /* Detect the bus width of the external flash memory */ + v = __raw_readl(EP93XX_SYSCON_SYSCFG); + if (v & EP93XX_SYSCON_SYSCFG_LCSN7) + return 4; /* 32-bit */ + else + return 2; /* 16-bit */ +} + +static void __init micro9_register_flash(void) { - platform_device_register(µ9h_flash); + if (machine_is_micro9()) + __micro9_register_flash(4); + else if (machine_is_micro9m() || machine_is_micro9s()) + __micro9_register_flash(micro9_detect_bootwidth()); } -static void __init micro9h_init_machine(void) + +/************************************************************************* + * Micro9 Ethernet + *************************************************************************/ +static struct ep93xx_eth_data micro9_eth_data = { + .phy_id = 0x1f, +}; + + +static void __init micro9_init_machine(void) { ep93xx_init_devices(); - micro9_init(); - micro9h_init(); + ep93xx_register_eth(µ9_eth_data, 1); + micro9_register_flash(); } -MACHINE_START(MICRO9, "Contec Hypercontrol Micro9-H") - /* Maintainer: Manfred Gruber <manfred.gruber@contec.at> */ + +#ifdef CONFIG_MACH_MICRO9H +MACHINE_START(MICRO9, "Contec Micro9-High") + /* Maintainer: Hubert Feurstein <hubert.feurstein@contec.at> */ .phys_io = EP93XX_APB_PHYS_BASE, .io_pg_offst = ((EP93XX_APB_VIRT_BASE) >> 18) & 0xfffc, .boot_params = EP93XX_SDCE3_PHYS_BASE_SYNC + 0x100, .map_io = ep93xx_map_io, .init_irq = ep93xx_init_irq, .timer = &ep93xx_timer, - .init_machine = micro9h_init_machine, + .init_machine = micro9_init_machine, MACHINE_END #endif -/* - * Micro9-M - */ #ifdef CONFIG_MACH_MICRO9M -static void __init micro9m_init_machine(void) -{ - ep93xx_init_devices(); - micro9_init(); -} - -MACHINE_START(MICRO9M, "Contec Hypercontrol Micro9-M") - /* Maintainer: Manfred Gruber <manfred.gruber@contec.at> */ +MACHINE_START(MICRO9M, "Contec Micro9-Mid") + /* Maintainer: Hubert Feurstein <hubert.feurstein@contec.at> */ .phys_io = EP93XX_APB_PHYS_BASE, .io_pg_offst = ((EP93XX_APB_VIRT_BASE) >> 18) & 0xfffc, - .boot_params = EP93XX_SDCE3_PHYS_BASE_SYNC + 0x100, + .boot_params = EP93XX_SDCE3_PHYS_BASE_ASYNC + 0x100, .map_io = ep93xx_map_io, .init_irq = ep93xx_init_irq, .timer = &ep93xx_timer, - .init_machine = micro9m_init_machine, + .init_machine = micro9_init_machine, MACHINE_END #endif -/* - * Micro9-L - */ #ifdef CONFIG_MACH_MICRO9L -static void __init micro9l_init_machine(void) -{ - ep93xx_init_devices(); - micro9_init(); -} - -MACHINE_START(MICRO9L, "Contec Hypercontrol Micro9-L") - /* Maintainer: Manfred Gruber <manfred.gruber@contec.at> */ +MACHINE_START(MICRO9L, "Contec Micro9-Lite") + /* Maintainer: Hubert Feurstein <hubert.feurstein@contec.at> */ .phys_io = EP93XX_APB_PHYS_BASE, .io_pg_offst = ((EP93XX_APB_VIRT_BASE) >> 18) & 0xfffc, .boot_params = EP93XX_SDCE3_PHYS_BASE_SYNC + 0x100, .map_io = ep93xx_map_io, .init_irq = ep93xx_init_irq, .timer = &ep93xx_timer, - .init_machine = micro9l_init_machine, + .init_machine = micro9_init_machine, MACHINE_END #endif +#ifdef CONFIG_MACH_MICRO9S +MACHINE_START(MICRO9S, "Contec Micro9-Slim") + /* Maintainer: Hubert Feurstein <hubert.feurstein@contec.at> */ + .phys_io = EP93XX_APB_PHYS_BASE, + .io_pg_offst = ((EP93XX_APB_VIRT_BASE) >> 18) & 0xfffc, + .boot_params = EP93XX_SDCE3_PHYS_BASE_ASYNC + 0x100, + .map_io = ep93xx_map_io, + .init_irq = ep93xx_init_irq, + .timer = &ep93xx_timer, + .init_machine = micro9_init_machine, +MACHINE_END +#endif diff --git a/arch/arm/mach-integrator/include/mach/memory.h b/arch/arm/mach-integrator/include/mach/memory.h index 2b2e7a110724..4891828454f5 100644 --- a/arch/arm/mach-integrator/include/mach/memory.h +++ b/arch/arm/mach-integrator/include/mach/memory.h @@ -28,5 +28,6 @@ #define BUS_OFFSET UL(0x80000000) #define __virt_to_bus(x) ((x) - PAGE_OFFSET + BUS_OFFSET) #define __bus_to_virt(x) ((x) - BUS_OFFSET + PAGE_OFFSET) +#define __pfn_to_bus(x) (((x) << PAGE_SHIFT) + BUS_OFFSET) #endif diff --git a/arch/arm/mach-integrator/pci_v3.c b/arch/arm/mach-integrator/pci_v3.c index 901cc205015e..148d25fc636f 100644 --- a/arch/arm/mach-integrator/pci_v3.c +++ b/arch/arm/mach-integrator/pci_v3.c @@ -31,6 +31,7 @@ #include <mach/hardware.h> #include <asm/irq.h> +#include <asm/signal.h> #include <asm/system.h> #include <asm/mach/pci.h> #include <asm/irq_regs.h> diff --git a/arch/arm/mach-kirkwood/addr-map.c b/arch/arm/mach-kirkwood/addr-map.c index 1da5d1c18ecb..2e69168fc699 100644 --- a/arch/arm/mach-kirkwood/addr-map.c +++ b/arch/arm/mach-kirkwood/addr-map.c @@ -105,7 +105,7 @@ void __init kirkwood_setup_cpu_mbus(void) setup_cpu_win(0, KIRKWOOD_PCIE_IO_PHYS_BASE, KIRKWOOD_PCIE_IO_SIZE, TARGET_PCIE, ATTR_PCIE_IO, KIRKWOOD_PCIE_IO_BUS_BASE); setup_cpu_win(1, KIRKWOOD_PCIE_MEM_PHYS_BASE, KIRKWOOD_PCIE_MEM_SIZE, - TARGET_PCIE, ATTR_PCIE_MEM, -1); + TARGET_PCIE, ATTR_PCIE_MEM, KIRKWOOD_PCIE_MEM_BUS_BASE); /* * Setup window for NAND controller. diff --git a/arch/arm/mach-kirkwood/common.c b/arch/arm/mach-kirkwood/common.c index 0acb61f3c10b..242dd0775343 100644 --- a/arch/arm/mach-kirkwood/common.c +++ b/arch/arm/mach-kirkwood/common.c @@ -845,7 +845,7 @@ int __init kirkwood_find_tclk(void) return 166666667; } -static void kirkwood_timer_init(void) +static void __init kirkwood_timer_init(void) { kirkwood_tclk = kirkwood_find_tclk(); orion_time_init(IRQ_KIRKWOOD_BRIDGE, kirkwood_tclk); @@ -915,6 +915,14 @@ void __init kirkwood_init(void) kirkwood_uart0_data[0].uartclk = kirkwood_tclk; kirkwood_uart1_data[0].uartclk = kirkwood_tclk; + /* + * Disable propagation of mbus errors to the CPU local bus, + * as this causes mbus errors (which can occur for example + * for PCI aborts) to throw CPU aborts, which we're not set + * up to deal with. + */ + writel(readl(CPU_CONFIG) & ~CPU_CONFIG_ERROR_PROP, CPU_CONFIG); + kirkwood_setup_cpu_mbus(); #ifdef CONFIG_CACHE_FEROCEON_L2 diff --git a/arch/arm/mach-kirkwood/include/mach/bridge-regs.h b/arch/arm/mach-kirkwood/include/mach/bridge-regs.h index 9e80d9232c83..418f5017c50e 100644 --- a/arch/arm/mach-kirkwood/include/mach/bridge-regs.h +++ b/arch/arm/mach-kirkwood/include/mach/bridge-regs.h @@ -13,6 +13,9 @@ #include <mach/kirkwood.h> +#define CPU_CONFIG (BRIDGE_VIRT_BASE | 0x0100) +#define CPU_CONFIG_ERROR_PROP 0x00000004 + #define CPU_CONTROL (BRIDGE_VIRT_BASE | 0x0104) #define CPU_RESET 0x00000002 diff --git a/arch/arm/mach-kirkwood/include/mach/io.h b/arch/arm/mach-kirkwood/include/mach/io.h index a643a846d5fb..44e8be04f259 100644 --- a/arch/arm/mach-kirkwood/include/mach/io.h +++ b/arch/arm/mach-kirkwood/include/mach/io.h @@ -15,7 +15,7 @@ static inline void __iomem *__io(unsigned long addr) { - return (void __iomem *)((addr - KIRKWOOD_PCIE_IO_PHYS_BASE) + return (void __iomem *)((addr - KIRKWOOD_PCIE_IO_BUS_BASE) + KIRKWOOD_PCIE_IO_VIRT_BASE); } diff --git a/arch/arm/mach-kirkwood/include/mach/kirkwood.h b/arch/arm/mach-kirkwood/include/mach/kirkwood.h index 54c132731d2d..a15cf0ee22bd 100644 --- a/arch/arm/mach-kirkwood/include/mach/kirkwood.h +++ b/arch/arm/mach-kirkwood/include/mach/kirkwood.h @@ -43,6 +43,7 @@ #define KIRKWOOD_REGS_SIZE SZ_1M #define KIRKWOOD_PCIE_MEM_PHYS_BASE 0xe0000000 +#define KIRKWOOD_PCIE_MEM_BUS_BASE 0xe0000000 #define KIRKWOOD_PCIE_MEM_SIZE SZ_128M /* diff --git a/arch/arm/mach-kirkwood/openrd_base-setup.c b/arch/arm/mach-kirkwood/openrd_base-setup.c index 947dfb8cd5b2..77617c722299 100644 --- a/arch/arm/mach-kirkwood/openrd_base-setup.c +++ b/arch/arm/mach-kirkwood/openrd_base-setup.c @@ -70,8 +70,20 @@ static void __init openrd_base_init(void) kirkwood_ge00_init(&openrd_base_ge00_data); kirkwood_sata_init(&openrd_base_sata_data); kirkwood_sdio_init(&openrd_base_mvsdio_data); + + kirkwood_i2c_init(); } +static int __init openrd_base_pci_init(void) +{ + if (machine_is_openrd_base()) + kirkwood_pcie_init(); + + return 0; + } +subsys_initcall(openrd_base_pci_init); + + MACHINE_START(OPENRD_BASE, "Marvell OpenRD Base Board") /* Maintainer: Dhaval Vasa <dhaval.vasa@einfochips.com> */ .phys_io = KIRKWOOD_REGS_PHYS_BASE, diff --git a/arch/arm/mach-kirkwood/pcie.c b/arch/arm/mach-kirkwood/pcie.c index d90b9aae308d..a604b2a701aa 100644 --- a/arch/arm/mach-kirkwood/pcie.c +++ b/arch/arm/mach-kirkwood/pcie.c @@ -93,7 +93,7 @@ static struct pci_ops pcie_ops = { }; -static int kirkwood_pcie_setup(int nr, struct pci_sys_data *sys) +static int __init kirkwood_pcie_setup(int nr, struct pci_sys_data *sys) { struct resource *res; extern unsigned int kirkwood_clk_ctrl; @@ -115,7 +115,7 @@ static int kirkwood_pcie_setup(int nr, struct pci_sys_data *sys) */ res[0].name = "PCIe I/O Space"; res[0].flags = IORESOURCE_IO; - res[0].start = KIRKWOOD_PCIE_IO_PHYS_BASE; + res[0].start = KIRKWOOD_PCIE_IO_BUS_BASE; res[0].end = res[0].start + KIRKWOOD_PCIE_IO_SIZE - 1; if (request_resource(&ioport_resource, &res[0])) panic("Request PCIe IO resource failed\n"); @@ -126,7 +126,7 @@ static int kirkwood_pcie_setup(int nr, struct pci_sys_data *sys) */ res[1].name = "PCIe Memory Space"; res[1].flags = IORESOURCE_MEM; - res[1].start = KIRKWOOD_PCIE_MEM_PHYS_BASE; + res[1].start = KIRKWOOD_PCIE_MEM_BUS_BASE; res[1].end = res[1].start + KIRKWOOD_PCIE_MEM_SIZE - 1; if (request_resource(&iomem_resource, &res[1])) panic("Request PCIe Memory resource failed\n"); diff --git a/arch/arm/mach-ks8695/include/mach/regs-switch.h b/arch/arm/mach-ks8695/include/mach/regs-switch.h index 56d12e8de895..97e8acb1cf6c 100644 --- a/arch/arm/mach-ks8695/include/mach/regs-switch.h +++ b/arch/arm/mach-ks8695/include/mach/regs-switch.h @@ -25,7 +25,7 @@ #define KS8695_SEC1 (0x04) /* Switch Engine Control 1 */ #define KS8695_SEC2 (0x08) /* Switch Engine Control 2 */ -#define KS8695_P(x)_C(z) (0xc0 + (((x)-1)*3 + ((z)-1))*4) /* Port Configuration Registers */ +#define KS8695_SEPXCZ(x,z) (0x0c + (((x)-1)*3 + ((z)-1))*4) /* Port Configuration Registers */ #define KS8695_SEP12AN (0x48) /* Port 1 & 2 Auto-Negotiation */ #define KS8695_SEP34AN (0x4c) /* Port 3 & 4 Auto-Negotiation */ diff --git a/arch/arm/mach-mmp/include/mach/mfp-pxa910.h b/arch/arm/mach-mmp/include/mach/mfp-pxa910.h index bf1189ff9a34..7e8a80f25ddc 100644 --- a/arch/arm/mach-mmp/include/mach/mfp-pxa910.h +++ b/arch/arm/mach-mmp/include/mach/mfp-pxa910.h @@ -160,7 +160,7 @@ #define MMC1_WP_MMC1_WP MFP_CFG_DRV(MMC1_WP, AF0, MEDIUM) /* PWM */ -#define GPIO27 PWM3 AF2 MFP_CFG(GPIO27, AF2) +#define GPIO27_PWM3_AF2 MFP_CFG(GPIO27, AF2) #define GPIO51_PWM2_OUT MFP_CFG(GPIO51, AF2) #define GPIO117_PWM1_OUT MFP_CFG(GPIO117, AF2) #define GPIO118_PWM2_OUT MFP_CFG(GPIO118, AF2) diff --git a/arch/arm/mach-mv78xx0/common.c b/arch/arm/mach-mv78xx0/common.c index 1b22e4af8791..08465eb6a2c2 100644 --- a/arch/arm/mach-mv78xx0/common.c +++ b/arch/arm/mach-mv78xx0/common.c @@ -845,6 +845,8 @@ static char * __init mv78xx0_id(void) } else if (dev == MV78100_DEV_ID) { if (rev == MV78100_REV_A0) return "MV78100-A0"; + else if (rev == MV78100_REV_A1) + return "MV78100-A1"; else return "MV78100-Rev-Unsupported"; } else if (dev == MV78200_DEV_ID) { diff --git a/arch/arm/mach-mv78xx0/include/mach/mv78xx0.h b/arch/arm/mach-mv78xx0/include/mach/mv78xx0.h index d715b92b0908..788bdace1304 100644 --- a/arch/arm/mach-mv78xx0/include/mach/mv78xx0.h +++ b/arch/arm/mach-mv78xx0/include/mach/mv78xx0.h @@ -112,6 +112,7 @@ #define MV78100_DEV_ID 0x7810 #define MV78100_REV_A0 1 +#define MV78100_REV_A1 2 #define MV78200_DEV_ID 0x7820 #define MV78200_REV_A0 1 diff --git a/arch/arm/mach-mx2/clock_imx27.c b/arch/arm/mach-mx2/clock_imx27.c index 4089951acb47..ff5e33298914 100644 --- a/arch/arm/mach-mx2/clock_imx27.c +++ b/arch/arm/mach-mx2/clock_imx27.c @@ -638,9 +638,9 @@ static struct clk_lookup lookups[] = { _REGISTER_CLOCK("mxc-mmc.0", NULL, sdhc1_clk) _REGISTER_CLOCK("mxc-mmc.1", NULL, sdhc2_clk) _REGISTER_CLOCK("mxc-mmc.2", NULL, sdhc3_clk) - _REGISTER_CLOCK(NULL, "cspi1", cspi1_clk) - _REGISTER_CLOCK(NULL, "cspi2", cspi2_clk) - _REGISTER_CLOCK(NULL, "cspi3", cspi3_clk) + _REGISTER_CLOCK("spi_imx.0", NULL, cspi1_clk) + _REGISTER_CLOCK("spi_imx.1", NULL, cspi2_clk) + _REGISTER_CLOCK("spi_imx.2", NULL, cspi3_clk) _REGISTER_CLOCK("imx-fb.0", NULL, lcdc_clk) _REGISTER_CLOCK(NULL, "csi", csi_clk) _REGISTER_CLOCK("fsl-usb2-udc", "usb", usb_clk) @@ -665,7 +665,7 @@ static struct clk_lookup lookups[] = { _REGISTER_CLOCK(NULL, "sahara2", sahara2_clk) _REGISTER_CLOCK(NULL, "ata", ata_clk) _REGISTER_CLOCK(NULL, "mstick", mstick_clk) - _REGISTER_CLOCK(NULL, "wdog", wdog_clk) + _REGISTER_CLOCK("imx-wdt.0", NULL, wdog_clk) _REGISTER_CLOCK(NULL, "gpio", gpio_clk) _REGISTER_CLOCK("imx-i2c.0", NULL, i2c1_clk) _REGISTER_CLOCK("imx-i2c.1", NULL, i2c2_clk) diff --git a/arch/arm/mach-mx2/pcm038.c b/arch/arm/mach-mx2/pcm038.c index ee65dda584cf..906d59b0a7aa 100644 --- a/arch/arm/mach-mx2/pcm038.c +++ b/arch/arm/mach-mx2/pcm038.c @@ -23,6 +23,10 @@ #include <linux/mtd/plat-ram.h> #include <linux/mtd/physmap.h> #include <linux/platform_device.h> +#include <linux/regulator/machine.h> +#include <linux/mfd/mc13783.h> +#include <linux/spi/spi.h> +#include <linux/irq.h> #include <asm/mach-types.h> #include <asm/mach/arch.h> @@ -35,6 +39,7 @@ #include <mach/iomux.h> #include <mach/imx-uart.h> #include <mach/mxc_nand.h> +#include <mach/spi.h> #include "devices.h" @@ -78,8 +83,6 @@ static int pcm038_pins[] = { PC6_PF_I2C2_SCL, /* SPI1 */ PD25_PF_CSPI1_RDY, - PD27_PF_CSPI1_SS1, - PD28_PF_CSPI1_SS0, PD29_PF_CSPI1_SCLK, PD30_PF_CSPI1_MISO, PD31_PF_CSPI1_MOSI, @@ -196,6 +199,86 @@ static struct i2c_board_info pcm038_i2c_devices[] = { } }; +static int pcm038_spi_cs[] = {GPIO_PORTD + 28}; + +static struct spi_imx_master pcm038_spi_0_data = { + .chipselect = pcm038_spi_cs, + .num_chipselect = ARRAY_SIZE(pcm038_spi_cs), +}; + +static struct regulator_consumer_supply sdhc1_consumers[] = { + { + .dev = &mxc_sdhc_device1.dev, + .supply = "sdhc_vcc", + }, +}; + +static struct regulator_init_data sdhc1_data = { + .constraints = { + .min_uV = 3000000, + .max_uV = 3400000, + .valid_ops_mask = REGULATOR_CHANGE_VOLTAGE | + REGULATOR_CHANGE_MODE | REGULATOR_CHANGE_STATUS, + .valid_modes_mask = REGULATOR_MODE_NORMAL | + REGULATOR_MODE_FAST, + .always_on = 0, + .boot_on = 0, + }, + .num_consumer_supplies = ARRAY_SIZE(sdhc1_consumers), + .consumer_supplies = sdhc1_consumers, +}; + +static struct regulator_consumer_supply cam_consumers[] = { + { + .dev = NULL, + .supply = "imx_cam_vcc", + }, +}; + +static struct regulator_init_data cam_data = { + .constraints = { + .min_uV = 3000000, + .max_uV = 3400000, + .valid_ops_mask = REGULATOR_CHANGE_VOLTAGE | + REGULATOR_CHANGE_MODE | REGULATOR_CHANGE_STATUS, + .valid_modes_mask = REGULATOR_MODE_NORMAL | + REGULATOR_MODE_FAST, + .always_on = 0, + .boot_on = 0, + }, + .num_consumer_supplies = ARRAY_SIZE(cam_consumers), + .consumer_supplies = cam_consumers, +}; + +struct mc13783_regulator_init_data pcm038_regulators[] = { + { + .id = MC13783_REGU_VCAM, + .init_data = &cam_data, + }, { + .id = MC13783_REGU_VMMC1, + .init_data = &sdhc1_data, + }, +}; + +static struct mc13783_platform_data pcm038_pmic = { + .regulators = pcm038_regulators, + .num_regulators = ARRAY_SIZE(pcm038_regulators), + .flags = MC13783_USE_ADC | MC13783_USE_REGULATOR | + MC13783_USE_TOUCHSCREEN, +}; + +static struct spi_board_info pcm038_spi_board_info[] __initdata = { + { + .modalias = "mc13783", + .irq = IRQ_GPIOB(23), + .max_speed_hz = 300000, + .bus_num = 0, + .chip_select = 0, + .platform_data = &pcm038_pmic, + .mode = SPI_CS_HIGH, + } +}; + static void __init pcm038_init(void) { mxc_gpio_setup_multiple_pins(pcm038_pins, ARRAY_SIZE(pcm038_pins), @@ -219,6 +302,15 @@ static void __init pcm038_init(void) /* PE18 for user-LED D40 */ mxc_gpio_mode(GPIO_PORTE | 18 | GPIO_GPIO | GPIO_OUT); + mxc_gpio_mode(GPIO_PORTD | 28 | GPIO_GPIO | GPIO_OUT); + + /* MC13783 IRQ */ + mxc_gpio_mode(GPIO_PORTB | 23 | GPIO_GPIO | GPIO_IN); + + mxc_register_device(&mxc_spi_device0, &pcm038_spi_0_data); + spi_register_board_info(pcm038_spi_board_info, + ARRAY_SIZE(pcm038_spi_board_info)); + platform_add_devices(platform_devices, ARRAY_SIZE(platform_devices)); #ifdef CONFIG_MACH_PCM970_BASEBOARD diff --git a/arch/arm/mach-mx2/pcm970-baseboard.c b/arch/arm/mach-mx2/pcm970-baseboard.c index c261f59b0b4c..3cb7f457e5d0 100644 --- a/arch/arm/mach-mx2/pcm970-baseboard.c +++ b/arch/arm/mach-mx2/pcm970-baseboard.c @@ -39,7 +39,6 @@ static int pcm970_pins[] = { PB7_PF_SD2_D3, PB8_PF_SD2_CMD, PB9_PF_SD2_CLK, - GPIO_PORTC | 28 | GPIO_GPIO | GPIO_IN, /* card detect */ /* display */ PA5_PF_LSCLK, PA6_PF_LD0, @@ -228,6 +227,7 @@ void __init pcm970_baseboard_init(void) "PCM970"); mxc_register_device(&mxc_fb_device, &pcm038_fb_data); + mxc_gpio_mode(GPIO_PORTC | 28 | GPIO_GPIO | GPIO_IN); mxc_register_device(&mxc_sdhc_device1, &sdhc_pdata); platform_device_register(&pcm970_sja1000); } diff --git a/arch/arm/mach-mx25/devices.c b/arch/arm/mach-mx25/devices.c index eb12de1da42d..63511de3a559 100644 --- a/arch/arm/mach-mx25/devices.c +++ b/arch/arm/mach-mx25/devices.c @@ -1,4 +1,23 @@ +/* + * Copyright 2009 Sascha Hauer, <kernel@pengutronix.de> + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA. + */ + #include <linux/platform_device.h> +#include <linux/dma-mapping.h> #include <linux/gpio.h> #include <mach/mx25.h> #include <mach/irqs.h> diff --git a/arch/arm/mach-mx25/mx25pdk.c b/arch/arm/mach-mx25/mx25pdk.c index 92aa4fd19d99..d23ae571c03f 100644 --- a/arch/arm/mach-mx25/mx25pdk.c +++ b/arch/arm/mach-mx25/mx25pdk.c @@ -1,3 +1,21 @@ +/* + * Copyright 2009 Sascha Hauer, <kernel@pengutronix.de> + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA. + */ + #include <linux/types.h> #include <linux/init.h> #include <linux/clk.h> @@ -23,19 +41,12 @@ static struct imxuart_platform_data uart_pdata = { .flags = IMXUART_HAVE_RTSCTS, }; -static struct mxc_nand_platform_data nand_board_info = { - .width = 1, - .hw_ecc = 1, -}; - static void __init mx25pdk_init(void) { mxc_register_device(&mxc_uart_device0, &uart_pdata); mxc_register_device(&mxc_usbh2, NULL); - mxc_register_device(&mxc_nand_device, &nand_board_info); } - static void __init mx25pdk_timer_init(void) { mx25_clocks_init(26000000); diff --git a/arch/arm/mach-mx3/clock-imx35.c b/arch/arm/mach-mx3/clock-imx35.c index fe5c4217322e..c595260ec1f9 100644 --- a/arch/arm/mach-mx3/clock-imx35.c +++ b/arch/arm/mach-mx3/clock-imx35.c @@ -443,7 +443,7 @@ static struct clk_lookup lookups[] = { _REGISTER_CLOCK("mxc-ehci.1", "usb", usbotg_clk) _REGISTER_CLOCK("mxc-ehci.2", "usb", usbotg_clk) _REGISTER_CLOCK("fsl-usb2-udc", "usb", usbotg_clk) - _REGISTER_CLOCK("mxc_wdt.0", NULL, wdog_clk) + _REGISTER_CLOCK("imx-wdt.0", NULL, wdog_clk) _REGISTER_CLOCK(NULL, "max", max_clk) _REGISTER_CLOCK(NULL, "admux", admux_clk) _REGISTER_CLOCK(NULL, "csi", csi_clk) diff --git a/arch/arm/mach-mx3/clock.c b/arch/arm/mach-mx3/clock.c index 06bd6180bfc3..b2a3bcf8266e 100644 --- a/arch/arm/mach-mx3/clock.c +++ b/arch/arm/mach-mx3/clock.c @@ -530,7 +530,7 @@ static struct clk_lookup lookups[] = { _REGISTER_CLOCK("spi_imx.2", NULL, cspi3_clk) _REGISTER_CLOCK(NULL, "gpt", gpt_clk) _REGISTER_CLOCK(NULL, "pwm", pwm_clk) - _REGISTER_CLOCK(NULL, "wdog", wdog_clk) + _REGISTER_CLOCK("imx-wdt.0", NULL, wdog_clk) _REGISTER_CLOCK(NULL, "rtc", rtc_clk) _REGISTER_CLOCK(NULL, "epit", epit1_clk) _REGISTER_CLOCK(NULL, "epit", epit2_clk) diff --git a/arch/arm/mach-mx3/devices.c b/arch/arm/mach-mx3/devices.c index 8a577f367250..e6abe181b967 100644 --- a/arch/arm/mach-mx3/devices.c +++ b/arch/arm/mach-mx3/devices.c @@ -459,7 +459,7 @@ struct platform_device mxc_usbh2 = { * SPI master controller * 3 channels */ -static struct resource imx_spi_0_resources[] = { +static struct resource mxc_spi_0_resources[] = { { .start = CSPI1_BASE_ADDR, .end = CSPI1_BASE_ADDR + SZ_4K - 1, @@ -471,7 +471,7 @@ static struct resource imx_spi_0_resources[] = { }, }; -static struct resource imx_spi_1_resources[] = { +static struct resource mxc_spi_1_resources[] = { { .start = CSPI2_BASE_ADDR, .end = CSPI2_BASE_ADDR + SZ_4K - 1, @@ -483,7 +483,7 @@ static struct resource imx_spi_1_resources[] = { }, }; -static struct resource imx_spi_2_resources[] = { +static struct resource mxc_spi_2_resources[] = { { .start = CSPI3_BASE_ADDR, .end = CSPI3_BASE_ADDR + SZ_4K - 1, @@ -495,25 +495,25 @@ static struct resource imx_spi_2_resources[] = { }, }; -struct platform_device imx_spi_device0 = { +struct platform_device mxc_spi_device0 = { .name = "spi_imx", .id = 0, - .num_resources = ARRAY_SIZE(imx_spi_0_resources), - .resource = imx_spi_0_resources, + .num_resources = ARRAY_SIZE(mxc_spi_0_resources), + .resource = mxc_spi_0_resources, }; -struct platform_device imx_spi_device1 = { +struct platform_device mxc_spi_device1 = { .name = "spi_imx", .id = 1, - .num_resources = ARRAY_SIZE(imx_spi_1_resources), - .resource = imx_spi_1_resources, + .num_resources = ARRAY_SIZE(mxc_spi_1_resources), + .resource = mxc_spi_1_resources, }; -struct platform_device imx_spi_device2 = { +struct platform_device mxc_spi_device2 = { .name = "spi_imx", .id = 2, - .num_resources = ARRAY_SIZE(imx_spi_2_resources), - .resource = imx_spi_2_resources, + .num_resources = ARRAY_SIZE(mxc_spi_2_resources), + .resource = mxc_spi_2_resources, }; #ifdef CONFIG_ARCH_MX35 diff --git a/arch/arm/mach-mx3/devices.h b/arch/arm/mach-mx3/devices.h index 79f2be45d139..ab87419dc9a0 100644 --- a/arch/arm/mach-mx3/devices.h +++ b/arch/arm/mach-mx3/devices.h @@ -20,7 +20,7 @@ extern struct platform_device mxc_otg_host; extern struct platform_device mxc_usbh1; extern struct platform_device mxc_usbh2; extern struct platform_device mxc_rnga_device; -extern struct platform_device imx_spi_device0; -extern struct platform_device imx_spi_device1; -extern struct platform_device imx_spi_device2; +extern struct platform_device mxc_spi_device0; +extern struct platform_device mxc_spi_device1; +extern struct platform_device mxc_spi_device2; diff --git a/arch/arm/mach-mx3/mm.c b/arch/arm/mach-mx3/mm.c index ad5a1122d765..bedf5b8d976a 100644 --- a/arch/arm/mach-mx3/mm.c +++ b/arch/arm/mach-mx3/mm.c @@ -81,6 +81,7 @@ void __init mx31_map_io(void) iotable_init(mxc_io_desc, ARRAY_SIZE(mxc_io_desc)); } +#ifdef CONFIG_ARCH_MX35 void __init mx35_map_io(void) { mxc_set_cpu_type(MXC_CPU_MX35); @@ -89,6 +90,7 @@ void __init mx35_map_io(void) iotable_init(mxc_io_desc, ARRAY_SIZE(mxc_io_desc)); } +#endif void __init mx31_init_irq(void) { diff --git a/arch/arm/mach-omap1/board-ams-delta.c b/arch/arm/mach-omap1/board-ams-delta.c index 42920f9c1a11..8ad5cc3e83e3 100644 --- a/arch/arm/mach-omap1/board-ams-delta.c +++ b/arch/arm/mach-omap1/board-ams-delta.c @@ -219,6 +219,10 @@ static struct platform_device *ams_delta_devices[] __initdata = { static void __init ams_delta_init(void) { + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + iotable_init(ams_delta_io_desc, ARRAY_SIZE(ams_delta_io_desc)); omap_board_config = ams_delta_config; @@ -231,6 +235,8 @@ static void __init ams_delta_init(void) omap_usb_init(&ams_delta_usb_config); platform_add_devices(ams_delta_devices, ARRAY_SIZE(ams_delta_devices)); + + omap_writew(omap_readw(ARM_RSTCT1) | 0x0004, ARM_RSTCT1); } static struct plat_serial8250_port ams_delta_modem_ports[] = { diff --git a/arch/arm/mach-omap1/board-generic.c b/arch/arm/mach-omap1/board-generic.c index fb47239da72f..6c8a41f20e51 100644 --- a/arch/arm/mach-omap1/board-generic.c +++ b/arch/arm/mach-omap1/board-generic.c @@ -64,6 +64,14 @@ static void __init omap_generic_init(void) { #ifdef CONFIG_ARCH_OMAP15XX if (cpu_is_omap15xx()) { + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + omap_cfg_reg(UART2_TX); + omap_cfg_reg(UART2_RTS); + omap_cfg_reg(UART3_TX); + omap_cfg_reg(UART3_RX); + omap_usb_init(&generic1510_usb_config); } #endif diff --git a/arch/arm/mach-omap1/board-innovator.c b/arch/arm/mach-omap1/board-innovator.c index cc2abbb2d0f4..cd6c39514826 100644 --- a/arch/arm/mach-omap1/board-innovator.c +++ b/arch/arm/mach-omap1/board-innovator.c @@ -376,6 +376,26 @@ static void __init innovator_init(void) { #ifdef CONFIG_ARCH_OMAP15XX if (cpu_is_omap1510()) { + unsigned char reg; + + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + omap_cfg_reg(UART2_TX); + omap_cfg_reg(UART2_RTS); + omap_cfg_reg(UART3_TX); + omap_cfg_reg(UART3_RX); + + reg = fpga_read(OMAP1510_FPGA_POWER); + reg |= OMAP1510_FPGA_PCR_COM1_EN; + fpga_write(reg, OMAP1510_FPGA_POWER); + udelay(10); + + reg = fpga_read(OMAP1510_FPGA_POWER); + reg |= OMAP1510_FPGA_PCR_COM2_EN; + fpga_write(reg, OMAP1510_FPGA_POWER); + udelay(10); + platform_add_devices(innovator1510_devices, ARRAY_SIZE(innovator1510_devices)); spi_register_board_info(innovator1510_boardinfo, ARRAY_SIZE(innovator1510_boardinfo)); diff --git a/arch/arm/mach-omap1/board-palmte.c b/arch/arm/mach-omap1/board-palmte.c index 90dd0431b0dc..4de258420f39 100644 --- a/arch/arm/mach-omap1/board-palmte.c +++ b/arch/arm/mach-omap1/board-palmte.c @@ -342,6 +342,14 @@ static void __init palmte_misc_gpio_setup(void) static void __init omap_palmte_init(void) { + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + omap_cfg_reg(UART2_TX); + omap_cfg_reg(UART2_RTS); + omap_cfg_reg(UART3_TX); + omap_cfg_reg(UART3_RX); + omap_board_config = palmte_config; omap_board_config_size = ARRAY_SIZE(palmte_config); diff --git a/arch/arm/mach-omap1/board-palmtt.c b/arch/arm/mach-omap1/board-palmtt.c index 8256139891ff..d972cf941b76 100644 --- a/arch/arm/mach-omap1/board-palmtt.c +++ b/arch/arm/mach-omap1/board-palmtt.c @@ -289,6 +289,14 @@ static void __init omap_mpu_wdt_mode(int mode) { static void __init omap_palmtt_init(void) { + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + omap_cfg_reg(UART2_TX); + omap_cfg_reg(UART2_RTS); + omap_cfg_reg(UART3_TX); + omap_cfg_reg(UART3_RX); + omap_mpu_wdt_mode(0); omap_board_config = palmtt_config; diff --git a/arch/arm/mach-omap1/board-palmz71.c b/arch/arm/mach-omap1/board-palmz71.c index 81b6bde1c5a3..986bd4df0e97 100644 --- a/arch/arm/mach-omap1/board-palmz71.c +++ b/arch/arm/mach-omap1/board-palmz71.c @@ -307,6 +307,14 @@ palmz71_gpio_setup(int early) static void __init omap_palmz71_init(void) { + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + omap_cfg_reg(UART2_TX); + omap_cfg_reg(UART2_RTS); + omap_cfg_reg(UART3_TX); + omap_cfg_reg(UART3_RX); + palmz71_gpio_setup(1); omap_mpu_wdt_mode(0); diff --git a/arch/arm/mach-omap1/board-sx1.c b/arch/arm/mach-omap1/board-sx1.c index 02c85ca2e1df..056ae64e0f55 100644 --- a/arch/arm/mach-omap1/board-sx1.c +++ b/arch/arm/mach-omap1/board-sx1.c @@ -377,6 +377,14 @@ static struct omap_board_config_kernel sx1_config[] __initdata = { static void __init omap_sx1_init(void) { + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + omap_cfg_reg(UART2_TX); + omap_cfg_reg(UART2_RTS); + omap_cfg_reg(UART3_TX); + omap_cfg_reg(UART3_RX); + platform_add_devices(sx1_devices, ARRAY_SIZE(sx1_devices)); omap_board_config = sx1_config; diff --git a/arch/arm/mach-omap1/board-voiceblue.c b/arch/arm/mach-omap1/board-voiceblue.c index c06e7a553472..07b07522d5bf 100644 --- a/arch/arm/mach-omap1/board-voiceblue.c +++ b/arch/arm/mach-omap1/board-voiceblue.c @@ -152,6 +152,14 @@ static void __init voiceblue_init_irq(void) static void __init voiceblue_init(void) { + /* mux pins for uarts */ + omap_cfg_reg(UART1_TX); + omap_cfg_reg(UART1_RTS); + omap_cfg_reg(UART2_TX); + omap_cfg_reg(UART2_RTS); + omap_cfg_reg(UART3_TX); + omap_cfg_reg(UART3_RX); + /* Watchdog */ gpio_request(0, "Watchdog"); /* smc91x reset */ diff --git a/arch/arm/mach-omap1/serial.c b/arch/arm/mach-omap1/serial.c index d496e50fec40..d23979bc0fd5 100644 --- a/arch/arm/mach-omap1/serial.c +++ b/arch/arm/mach-omap1/serial.c @@ -131,8 +131,6 @@ void __init omap_serial_init(void) } for (i = 0; i < OMAP_MAX_NR_PORTS; i++) { - unsigned char reg; - switch (i) { case 0: uart1_ck = clk_get(NULL, "uart1_ck"); @@ -143,16 +141,6 @@ void __init omap_serial_init(void) if (cpu_is_omap15xx()) clk_set_rate(uart1_ck, 12000000); } - if (cpu_is_omap15xx()) { - omap_cfg_reg(UART1_TX); - omap_cfg_reg(UART1_RTS); - if (machine_is_omap_innovator()) { - reg = fpga_read(OMAP1510_FPGA_POWER); - reg |= OMAP1510_FPGA_PCR_COM1_EN; - fpga_write(reg, OMAP1510_FPGA_POWER); - udelay(10); - } - } break; case 1: uart2_ck = clk_get(NULL, "uart2_ck"); @@ -165,16 +153,6 @@ void __init omap_serial_init(void) else clk_set_rate(uart2_ck, 48000000); } - if (cpu_is_omap15xx()) { - omap_cfg_reg(UART2_TX); - omap_cfg_reg(UART2_RTS); - if (machine_is_omap_innovator()) { - reg = fpga_read(OMAP1510_FPGA_POWER); - reg |= OMAP1510_FPGA_PCR_COM2_EN; - fpga_write(reg, OMAP1510_FPGA_POWER); - udelay(10); - } - } break; case 2: uart3_ck = clk_get(NULL, "uart3_ck"); @@ -185,10 +163,6 @@ void __init omap_serial_init(void) if (cpu_is_omap15xx()) clk_set_rate(uart3_ck, 12000000); } - if (cpu_is_omap15xx()) { - omap_cfg_reg(UART3_TX); - omap_cfg_reg(UART3_RX); - } break; } omap_serial_reset(&serial_platform_data[i]); diff --git a/arch/arm/mach-omap2/Kconfig b/arch/arm/mach-omap2/Kconfig index 75b1c7efae7e..aad194f61a33 100644 --- a/arch/arm/mach-omap2/Kconfig +++ b/arch/arm/mach-omap2/Kconfig @@ -73,9 +73,21 @@ config MACH_OMAP_3430SDP bool "OMAP 3430 SDP board" depends on ARCH_OMAP3 && ARCH_OMAP34XX +config MACH_NOKIA_N800 + bool + +config MACH_NOKIA_N810 + bool + +config MACH_NOKIA_N810_WIMAX + bool + config MACH_NOKIA_N8X0 bool "Nokia N800/N810" depends on ARCH_OMAP2420 + select MACH_NOKIA_N800 + select MACH_NOKIA_N810 + select MACH_NOKIA_N810_WIMAX config MACH_NOKIA_RX51 bool "Nokia RX-51 board" diff --git a/arch/arm/mach-omap2/board-3430sdp.c b/arch/arm/mach-omap2/board-3430sdp.c index efaf053eba85..0acb5560229c 100644 --- a/arch/arm/mach-omap2/board-3430sdp.c +++ b/arch/arm/mach-omap2/board-3430sdp.c @@ -17,6 +17,7 @@ #include <linux/platform_device.h> #include <linux/delay.h> #include <linux/input.h> +#include <linux/input/matrix_keypad.h> #include <linux/spi/spi.h> #include <linux/spi/ads7846.h> #include <linux/i2c/twl4030.h> @@ -38,7 +39,6 @@ #include <mach/gpmc.h> #include <mach/control.h> -#include <mach/keypad.h> #include <mach/gpmc-smc91x.h> #include "sdram-qimonda-hyb18m512160af-6.h" diff --git a/arch/arm/mach-omap2/board-4430sdp.c b/arch/arm/mach-omap2/board-4430sdp.c index eb37c40ea83a..609a5a4a7e29 100644 --- a/arch/arm/mach-omap2/board-4430sdp.c +++ b/arch/arm/mach-omap2/board-4430sdp.c @@ -58,6 +58,8 @@ static void __init gic_init_irq(void) static void __init omap_4430sdp_init_irq(void) { + omap_board_config = sdp4430_config; + omap_board_config_size = ARRAY_SIZE(sdp4430_config); omap2_init_common_hw(NULL, NULL); #ifdef CONFIG_OMAP_32K_TIMER omap2_gp_clockevent_set_gptimer(1); @@ -70,8 +72,6 @@ static void __init omap_4430sdp_init_irq(void) static void __init omap_4430sdp_init(void) { platform_add_devices(sdp4430_devices, ARRAY_SIZE(sdp4430_devices)); - omap_board_config = sdp4430_config; - omap_board_config_size = ARRAY_SIZE(sdp4430_config); omap_serial_init(); } diff --git a/arch/arm/mach-omap2/board-ldp.c b/arch/arm/mach-omap2/board-ldp.c index d110a7fdfbd8..d57ec2f4d0a9 100644 --- a/arch/arm/mach-omap2/board-ldp.c +++ b/arch/arm/mach-omap2/board-ldp.c @@ -16,6 +16,7 @@ #include <linux/platform_device.h> #include <linux/delay.h> #include <linux/input.h> +#include <linux/input/matrix_keypad.h> #include <linux/gpio_keys.h> #include <linux/workqueue.h> #include <linux/err.h> @@ -41,7 +42,6 @@ #include <asm/delay.h> #include <mach/control.h> #include <mach/usb.h> -#include <mach/keypad.h> #include "mmc-twl4030.h" diff --git a/arch/arm/mach-omap2/board-omap3beagle.c b/arch/arm/mach-omap2/board-omap3beagle.c index 70df6b4dbcd4..08b0816afa61 100644 --- a/arch/arm/mach-omap2/board-omap3beagle.c +++ b/arch/arm/mach-omap2/board-omap3beagle.c @@ -162,7 +162,7 @@ static int beagle_twl_gpio_setup(struct device *dev, /* TWL4030_GPIO_MAX + 0 == ledA, EHCI nEN_USB_PWR (out, active low) */ gpio_request(gpio + TWL4030_GPIO_MAX, "nEN_USB_PWR"); - gpio_direction_output(gpio + TWL4030_GPIO_MAX, 1); + gpio_direction_output(gpio + TWL4030_GPIO_MAX, 0); /* TWL4030_GPIO_MAX + 1 == ledB, PMU_STAT (out, active low LED) */ gpio_leds[2].gpio = gpio + TWL4030_GPIO_MAX + 1; diff --git a/arch/arm/mach-omap2/board-omap3evm.c b/arch/arm/mach-omap2/board-omap3evm.c index e4ec0c591216..4c4d7f8dbd72 100644 --- a/arch/arm/mach-omap2/board-omap3evm.c +++ b/arch/arm/mach-omap2/board-omap3evm.c @@ -20,6 +20,7 @@ #include <linux/clk.h> #include <linux/gpio.h> #include <linux/input.h> +#include <linux/input/matrix_keypad.h> #include <linux/leds.h> #include <linux/spi/spi.h> @@ -37,7 +38,6 @@ #include <mach/usb.h> #include <mach/common.h> #include <mach/mcspi.h> -#include <mach/keypad.h> #include "sdram-micron-mt46h32m32lf-6.h" #include "mmc-twl4030.h" diff --git a/arch/arm/mach-omap2/board-omap3pandora.c b/arch/arm/mach-omap2/board-omap3pandora.c index 7f6bf8772af7..7519edb69155 100644 --- a/arch/arm/mach-omap2/board-omap3pandora.c +++ b/arch/arm/mach-omap2/board-omap3pandora.c @@ -27,6 +27,7 @@ #include <linux/i2c/twl4030.h> #include <linux/leds.h> #include <linux/input.h> +#include <linux/input/matrix_keypad.h> #include <linux/gpio_keys.h> #include <asm/mach-types.h> @@ -39,7 +40,6 @@ #include <mach/hardware.h> #include <mach/mcspi.h> #include <mach/usb.h> -#include <mach/keypad.h> #include <mach/mux.h> #include "sdram-micron-mt46h32m32lf-6.h" @@ -134,50 +134,50 @@ static void __init pandora_keys_gpio_init(void) } static int board_keymap[] = { - /* col, row, code */ + /* row, col, code */ KEY(0, 0, KEY_9), - KEY(0, 1, KEY_0), - KEY(0, 2, KEY_BACKSPACE), - KEY(0, 3, KEY_O), - KEY(0, 4, KEY_P), - KEY(0, 5, KEY_K), - KEY(0, 6, KEY_L), - KEY(0, 7, KEY_ENTER), - KEY(1, 0, KEY_8), + KEY(0, 1, KEY_8), + KEY(0, 2, KEY_I), + KEY(0, 3, KEY_J), + KEY(0, 4, KEY_N), + KEY(0, 5, KEY_M), + KEY(1, 0, KEY_0), KEY(1, 1, KEY_7), - KEY(1, 2, KEY_6), - KEY(1, 3, KEY_5), - KEY(1, 4, KEY_4), - KEY(1, 5, KEY_3), - KEY(1, 6, KEY_2), - KEY(1, 7, KEY_1), - KEY(2, 0, KEY_I), - KEY(2, 1, KEY_U), + KEY(1, 2, KEY_U), + KEY(1, 3, KEY_H), + KEY(1, 4, KEY_B), + KEY(1, 5, KEY_SPACE), + KEY(2, 0, KEY_BACKSPACE), + KEY(2, 1, KEY_6), KEY(2, 2, KEY_Y), - KEY(2, 3, KEY_T), - KEY(2, 4, KEY_R), - KEY(2, 5, KEY_E), - KEY(2, 6, KEY_W), - KEY(2, 7, KEY_Q), - KEY(3, 0, KEY_J), - KEY(3, 1, KEY_H), - KEY(3, 2, KEY_G), + KEY(2, 3, KEY_G), + KEY(2, 4, KEY_V), + KEY(2, 5, KEY_FN), + KEY(3, 0, KEY_O), + KEY(3, 1, KEY_5), + KEY(3, 2, KEY_T), KEY(3, 3, KEY_F), - KEY(3, 4, KEY_D), - KEY(3, 5, KEY_S), - KEY(3, 6, KEY_A), - KEY(3, 7, KEY_LEFTSHIFT), - KEY(4, 0, KEY_N), - KEY(4, 1, KEY_B), - KEY(4, 2, KEY_V), - KEY(4, 3, KEY_C), + KEY(3, 4, KEY_C), + KEY(4, 0, KEY_P), + KEY(4, 1, KEY_4), + KEY(4, 2, KEY_R), + KEY(4, 3, KEY_D), KEY(4, 4, KEY_X), - KEY(4, 5, KEY_Z), - KEY(4, 6, KEY_DOT), - KEY(4, 7, KEY_COMMA), - KEY(5, 0, KEY_M), - KEY(5, 1, KEY_SPACE), - KEY(5, 2, KEY_FN), + KEY(5, 0, KEY_K), + KEY(5, 1, KEY_3), + KEY(5, 2, KEY_E), + KEY(5, 3, KEY_S), + KEY(5, 4, KEY_Z), + KEY(6, 0, KEY_L), + KEY(6, 1, KEY_2), + KEY(6, 2, KEY_W), + KEY(6, 3, KEY_A), + KEY(6, 4, KEY_DOT), + KEY(7, 0, KEY_ENTER), + KEY(7, 1, KEY_1), + KEY(7, 2, KEY_Q), + KEY(7, 3, KEY_LEFTSHIFT), + KEY(7, 4, KEY_COMMA), }; static struct matrix_keymap_data board_map_data = { diff --git a/arch/arm/mach-omap2/board-rx51-peripherals.c b/arch/arm/mach-omap2/board-rx51-peripherals.c index b45ad312c587..e34d96a825e3 100644 --- a/arch/arm/mach-omap2/board-rx51-peripherals.c +++ b/arch/arm/mach-omap2/board-rx51-peripherals.c @@ -12,6 +12,7 @@ #include <linux/init.h> #include <linux/platform_device.h> #include <linux/input.h> +#include <linux/input/matrix_keypad.h> #include <linux/spi/spi.h> #include <linux/i2c.h> #include <linux/i2c/twl4030.h> @@ -27,7 +28,6 @@ #include <mach/common.h> #include <mach/dma.h> #include <mach/gpmc.h> -#include <mach/keypad.h> #include <mach/onenand.h> #include <mach/gpmc-smc91x.h> @@ -38,49 +38,49 @@ static int board_keymap[] = { KEY(0, 0, KEY_Q), - KEY(0, 1, KEY_W), - KEY(0, 2, KEY_E), - KEY(0, 3, KEY_R), - KEY(0, 4, KEY_T), - KEY(0, 5, KEY_Y), - KEY(0, 6, KEY_U), - KEY(0, 7, KEY_I), - KEY(1, 0, KEY_O), + KEY(0, 1, KEY_O), + KEY(0, 2, KEY_P), + KEY(0, 3, KEY_COMMA), + KEY(0, 4, KEY_BACKSPACE), + KEY(0, 6, KEY_A), + KEY(0, 7, KEY_S), + KEY(1, 0, KEY_W), KEY(1, 1, KEY_D), - KEY(1, 2, KEY_DOT), - KEY(1, 3, KEY_V), - KEY(1, 4, KEY_DOWN), - KEY(2, 0, KEY_P), - KEY(2, 1, KEY_F), + KEY(1, 2, KEY_F), + KEY(1, 3, KEY_G), + KEY(1, 4, KEY_H), + KEY(1, 5, KEY_J), + KEY(1, 6, KEY_K), + KEY(1, 7, KEY_L), + KEY(2, 0, KEY_E), + KEY(2, 1, KEY_DOT), KEY(2, 2, KEY_UP), - KEY(2, 3, KEY_B), - KEY(2, 4, KEY_RIGHT), - KEY(3, 0, KEY_COMMA), - KEY(3, 1, KEY_G), - KEY(3, 2, KEY_ENTER), + KEY(2, 3, KEY_ENTER), + KEY(2, 5, KEY_Z), + KEY(2, 6, KEY_X), + KEY(2, 7, KEY_C), + KEY(3, 0, KEY_R), + KEY(3, 1, KEY_V), + KEY(3, 2, KEY_B), KEY(3, 3, KEY_N), - KEY(4, 0, KEY_BACKSPACE), - KEY(4, 1, KEY_H), - KEY(4, 3, KEY_M), + KEY(3, 4, KEY_M), + KEY(3, 5, KEY_SPACE), + KEY(3, 6, KEY_SPACE), + KEY(3, 7, KEY_LEFT), + KEY(4, 0, KEY_T), + KEY(4, 1, KEY_DOWN), + KEY(4, 2, KEY_RIGHT), KEY(4, 4, KEY_LEFTCTRL), - KEY(5, 1, KEY_J), - KEY(5, 2, KEY_Z), - KEY(5, 3, KEY_SPACE), - KEY(5, 4, KEY_LEFTSHIFT), - KEY(6, 0, KEY_A), - KEY(6, 1, KEY_K), - KEY(6, 2, KEY_X), - KEY(6, 3, KEY_SPACE), - KEY(6, 4, KEY_FN), - KEY(7, 0, KEY_S), - KEY(7, 1, KEY_L), - KEY(7, 2, KEY_C), - KEY(7, 3, KEY_LEFT), - KEY(0xff, 0, KEY_F6), - KEY(0xff, 1, KEY_F7), - KEY(0xff, 2, KEY_F8), - KEY(0xff, 4, KEY_F9), - KEY(0xff, 5, KEY_F10), + KEY(4, 5, KEY_RIGHTALT), + KEY(4, 6, KEY_LEFTSHIFT), + KEY(5, 0, KEY_Y), + KEY(6, 0, KEY_U), + KEY(7, 0, KEY_I), + KEY(7, 1, KEY_F7), + KEY(7, 2, KEY_F8), + KEY(0xff, 2, KEY_F9), + KEY(0xff, 4, KEY_F10), + KEY(0xff, 5, KEY_F11), }; static struct matrix_keymap_data board_map_data = { @@ -444,7 +444,7 @@ static int __init rx51_i2c_init(void) rx51_twldata.vaux3 = &rx51_vaux3_cam; rx51_twldata.vmmc2 = &rx51_vmmc2; } - omap_register_i2c_bus(1, 2600, rx51_peripherals_i2c_board_info_1, + omap_register_i2c_bus(1, 2200, rx51_peripherals_i2c_board_info_1, ARRAY_SIZE(rx51_peripherals_i2c_board_info_1)); omap_register_i2c_bus(2, 100, NULL, 0); omap_register_i2c_bus(3, 400, NULL, 0); diff --git a/arch/arm/mach-omap2/board-rx51.c b/arch/arm/mach-omap2/board-rx51.c index f9196c3b1a7b..78869a9a1cc2 100644 --- a/arch/arm/mach-omap2/board-rx51.c +++ b/arch/arm/mach-omap2/board-rx51.c @@ -26,7 +26,6 @@ #include <mach/mux.h> #include <mach/board.h> #include <mach/common.h> -#include <mach/keypad.h> #include <mach/dma.h> #include <mach/gpmc.h> #include <mach/usb.h> diff --git a/arch/arm/mach-omap2/board-zoom2.c b/arch/arm/mach-omap2/board-zoom2.c index b7b32208ced7..51e0b3ba5f3a 100644 --- a/arch/arm/mach-omap2/board-zoom2.c +++ b/arch/arm/mach-omap2/board-zoom2.c @@ -13,6 +13,7 @@ #include <linux/init.h> #include <linux/platform_device.h> #include <linux/input.h> +#include <linux/input/matrix_keypad.h> #include <linux/gpio.h> #include <linux/i2c/twl4030.h> #include <linux/regulator/machine.h> @@ -22,64 +23,63 @@ #include <mach/common.h> #include <mach/usb.h> -#include <mach/keypad.h> #include "mmc-twl4030.h" +#include "sdram-micron-mt46h32m32lf-6.h" /* Zoom2 has Qwerty keyboard*/ static int board_keymap[] = { KEY(0, 0, KEY_E), - KEY(1, 0, KEY_R), - KEY(2, 0, KEY_T), - KEY(3, 0, KEY_HOME), - KEY(6, 0, KEY_I), - KEY(7, 0, KEY_LEFTSHIFT), - KEY(0, 1, KEY_D), + KEY(0, 1, KEY_R), + KEY(0, 2, KEY_T), + KEY(0, 3, KEY_HOME), + KEY(0, 6, KEY_I), + KEY(0, 7, KEY_LEFTSHIFT), + KEY(1, 0, KEY_D), KEY(1, 1, KEY_F), - KEY(2, 1, KEY_G), - KEY(3, 1, KEY_SEND), - KEY(6, 1, KEY_K), - KEY(7, 1, KEY_ENTER), - KEY(0, 2, KEY_X), - KEY(1, 2, KEY_C), + KEY(1, 2, KEY_G), + KEY(1, 3, KEY_SEND), + KEY(1, 6, KEY_K), + KEY(1, 7, KEY_ENTER), + KEY(2, 0, KEY_X), + KEY(2, 1, KEY_C), KEY(2, 2, KEY_V), - KEY(3, 2, KEY_END), - KEY(6, 2, KEY_DOT), - KEY(7, 2, KEY_CAPSLOCK), - KEY(0, 3, KEY_Z), - KEY(1, 3, KEY_KPPLUS), - KEY(2, 3, KEY_B), + KEY(2, 3, KEY_END), + KEY(2, 6, KEY_DOT), + KEY(2, 7, KEY_CAPSLOCK), + KEY(3, 0, KEY_Z), + KEY(3, 1, KEY_KPPLUS), + KEY(3, 2, KEY_B), KEY(3, 3, KEY_F1), - KEY(6, 3, KEY_O), - KEY(7, 3, KEY_SPACE), - KEY(0, 4, KEY_W), - KEY(1, 4, KEY_Y), - KEY(2, 4, KEY_U), - KEY(3, 4, KEY_F2), + KEY(3, 6, KEY_O), + KEY(3, 7, KEY_SPACE), + KEY(4, 0, KEY_W), + KEY(4, 1, KEY_Y), + KEY(4, 2, KEY_U), + KEY(4, 3, KEY_F2), KEY(4, 4, KEY_VOLUMEUP), - KEY(6, 4, KEY_L), - KEY(7, 4, KEY_LEFT), - KEY(0, 5, KEY_S), - KEY(1, 5, KEY_H), - KEY(2, 5, KEY_J), - KEY(3, 5, KEY_F3), + KEY(4, 6, KEY_L), + KEY(4, 7, KEY_LEFT), + KEY(5, 0, KEY_S), + KEY(5, 1, KEY_H), + KEY(5, 2, KEY_J), + KEY(5, 3, KEY_F3), KEY(5, 5, KEY_VOLUMEDOWN), - KEY(6, 5, KEY_M), - KEY(4, 5, KEY_ENTER), - KEY(7, 5, KEY_RIGHT), - KEY(0, 6, KEY_Q), - KEY(1, 6, KEY_A), - KEY(2, 6, KEY_N), - KEY(3, 6, KEY_BACKSPACE), + KEY(5, 6, KEY_M), + KEY(5, 7, KEY_ENTER), + KEY(6, 0, KEY_Q), + KEY(6, 1, KEY_A), + KEY(6, 2, KEY_N), + KEY(6, 3, KEY_BACKSPACE), KEY(6, 6, KEY_P), - KEY(7, 6, KEY_UP), KEY(6, 7, KEY_SELECT), - KEY(7, 7, KEY_DOWN), - KEY(0, 7, KEY_PROG1), /*MACRO 1 <User defined> */ - KEY(1, 7, KEY_PROG2), /*MACRO 2 <User defined> */ - KEY(2, 7, KEY_PROG3), /*MACRO 3 <User defined> */ - KEY(3, 7, KEY_PROG4), /*MACRO 4 <User defined> */ - 0 + KEY(7, 0, KEY_PROG1), /*MACRO 1 <User defined> */ + KEY(7, 1, KEY_PROG2), /*MACRO 2 <User defined> */ + KEY(7, 2, KEY_PROG3), /*MACRO 3 <User defined> */ + KEY(7, 3, KEY_PROG4), /*MACRO 4 <User defined> */ + KEY(7, 5, KEY_RIGHT), + KEY(7, 6, KEY_UP), + KEY(7, 7, KEY_DOWN) }; static struct matrix_keymap_data board_map_data = { @@ -213,7 +213,8 @@ static void __init omap_zoom2_init_irq(void) { omap_board_config = zoom2_config; omap_board_config_size = ARRAY_SIZE(zoom2_config); - omap2_init_common_hw(NULL, NULL); + omap2_init_common_hw(mt46h32m32lf6_sdrc_params, + mt46h32m32lf6_sdrc_params); omap_init_irq(); omap_gpio_init(); } diff --git a/arch/arm/mach-omap2/clock24xx.c b/arch/arm/mach-omap2/clock24xx.c index bc5d3ac66611..e2dbedd581e8 100644 --- a/arch/arm/mach-omap2/clock24xx.c +++ b/arch/arm/mach-omap2/clock24xx.c @@ -769,6 +769,7 @@ int __init omap2_clk_init(void) if (c->cpu & cpu_mask) { clkdev_add(&c->lk); clk_register(c->lk.clk); + omap2_init_clk_clkdm(c->lk.clk); } /* Check the MPU rate set by bootloader */ diff --git a/arch/arm/mach-omap2/clock34xx.c b/arch/arm/mach-omap2/clock34xx.c index fafcd32e6907..7c5c00df3c70 100644 --- a/arch/arm/mach-omap2/clock34xx.c +++ b/arch/arm/mach-omap2/clock34xx.c @@ -338,6 +338,13 @@ static struct omap_clk omap34xx_clks[] = { */ #define SDRC_MPURATE_LOOPS 96 +/* + * DPLL5_FREQ_FOR_USBHOST: USBHOST and USBTLL are the only clocks + * that are sourced by DPLL5, and both of these require this clock + * to be at 120 MHz for proper operation. + */ +#define DPLL5_FREQ_FOR_USBHOST 120000000 + /** * omap3430es2_clk_ssi_find_idlest - return CM_IDLEST info for SSI * @clk: struct clk * being enabled @@ -466,7 +473,7 @@ static u16 _omap3_dpll_compute_freqsel(struct clk *clk, u8 n) unsigned long fint; u16 f = 0; - fint = clk->dpll_data->clk_ref->rate / (n + 1); + fint = clk->dpll_data->clk_ref->rate / n; pr_debug("clock: fint is %lu\n", fint); @@ -1056,6 +1063,28 @@ void omap2_clk_prepare_for_reboot(void) #endif } +static void omap3_clk_lock_dpll5(void) +{ + struct clk *dpll5_clk; + struct clk *dpll5_m2_clk; + + dpll5_clk = clk_get(NULL, "dpll5_ck"); + clk_set_rate(dpll5_clk, DPLL5_FREQ_FOR_USBHOST); + clk_enable(dpll5_clk); + + /* Enable autoidle to allow it to enter low power bypass */ + omap3_dpll_allow_idle(dpll5_clk); + + /* Program dpll5_m2_clk divider for no division */ + dpll5_m2_clk = clk_get(NULL, "dpll5_m2_ck"); + clk_enable(dpll5_m2_clk); + clk_set_rate(dpll5_m2_clk, DPLL5_FREQ_FOR_USBHOST); + + clk_disable(dpll5_m2_clk); + clk_disable(dpll5_clk); + return; +} + /* REVISIT: Move this init stuff out into clock.c */ /* @@ -1148,6 +1177,12 @@ int __init omap2_clk_init(void) */ clk_enable_init_clocks(); + /* + * Lock DPLL5 and put it in autoidle. + */ + if (omap_rev() >= OMAP3430_REV_ES2_0) + omap3_clk_lock_dpll5(); + /* Avoid sleeping during omap2_clk_prepare_for_reboot() */ /* REVISIT: not yet ready for 343x */ #if 0 diff --git a/arch/arm/mach-omap2/clock34xx.h b/arch/arm/mach-omap2/clock34xx.h index c8119781e00a..9565c05bebd2 100644 --- a/arch/arm/mach-omap2/clock34xx.h +++ b/arch/arm/mach-omap2/clock34xx.h @@ -489,9 +489,9 @@ static struct clk core_ck = { static struct clk dpll3_m2x2_ck = { .name = "dpll3_m2x2_ck", .ops = &clkops_null, - .parent = &dpll3_x2_ck, + .parent = &dpll3_m2_ck, .clkdm_name = "dpll3_clkdm", - .recalc = &followparent_recalc, + .recalc = &omap3_clkoutx2_recalc, }; /* The PWRDN bit is apparently only available on 3430ES2 and above */ diff --git a/arch/arm/mach-omap2/clockdomain.c b/arch/arm/mach-omap2/clockdomain.c index 4ef7b4f5474e..58aff8485df9 100644 --- a/arch/arm/mach-omap2/clockdomain.c +++ b/arch/arm/mach-omap2/clockdomain.c @@ -137,6 +137,36 @@ static void _clkdm_del_autodeps(struct clockdomain *clkdm) } } +/* + * _omap2_clkdm_set_hwsup - set the hwsup idle transition bit + * @clkdm: struct clockdomain * + * @enable: int 0 to disable, 1 to enable + * + * Internal helper for actually switching the bit that controls hwsup + * idle transitions for clkdm. + */ +static void _omap2_clkdm_set_hwsup(struct clockdomain *clkdm, int enable) +{ + u32 v; + + if (cpu_is_omap24xx()) { + if (enable) + v = OMAP24XX_CLKSTCTRL_ENABLE_AUTO; + else + v = OMAP24XX_CLKSTCTRL_DISABLE_AUTO; + } else if (cpu_is_omap34xx()) { + if (enable) + v = OMAP34XX_CLKSTCTRL_ENABLE_AUTO; + else + v = OMAP34XX_CLKSTCTRL_DISABLE_AUTO; + } else { + BUG(); + } + + cm_rmw_mod_reg_bits(clkdm->clktrctrl_mask, + v << __ffs(clkdm->clktrctrl_mask), + clkdm->pwrdm.ptr->prcm_offs, CM_CLKSTCTRL); +} static struct clockdomain *_clkdm_lookup(const char *name) { @@ -456,8 +486,6 @@ int omap2_clkdm_wakeup(struct clockdomain *clkdm) */ void omap2_clkdm_allow_idle(struct clockdomain *clkdm) { - u32 v; - if (!clkdm) return; @@ -473,18 +501,7 @@ void omap2_clkdm_allow_idle(struct clockdomain *clkdm) if (atomic_read(&clkdm->usecount) > 0) _clkdm_add_autodeps(clkdm); - if (cpu_is_omap24xx()) - v = OMAP24XX_CLKSTCTRL_ENABLE_AUTO; - else if (cpu_is_omap34xx()) - v = OMAP34XX_CLKSTCTRL_ENABLE_AUTO; - else - BUG(); - - - cm_rmw_mod_reg_bits(clkdm->clktrctrl_mask, - v << __ffs(clkdm->clktrctrl_mask), - clkdm->pwrdm.ptr->prcm_offs, - CM_CLKSTCTRL); + _omap2_clkdm_set_hwsup(clkdm, 1); pwrdm_clkdm_state_switch(clkdm); } @@ -500,8 +517,6 @@ void omap2_clkdm_allow_idle(struct clockdomain *clkdm) */ void omap2_clkdm_deny_idle(struct clockdomain *clkdm) { - u32 v; - if (!clkdm) return; @@ -514,16 +529,7 @@ void omap2_clkdm_deny_idle(struct clockdomain *clkdm) pr_debug("clockdomain: disabling automatic idle transitions for %s\n", clkdm->name); - if (cpu_is_omap24xx()) - v = OMAP24XX_CLKSTCTRL_DISABLE_AUTO; - else if (cpu_is_omap34xx()) - v = OMAP34XX_CLKSTCTRL_DISABLE_AUTO; - else - BUG(); - - cm_rmw_mod_reg_bits(clkdm->clktrctrl_mask, - v << __ffs(clkdm->clktrctrl_mask), - clkdm->pwrdm.ptr->prcm_offs, CM_CLKSTCTRL); + _omap2_clkdm_set_hwsup(clkdm, 0); if (atomic_read(&clkdm->usecount) > 0) _clkdm_del_autodeps(clkdm); @@ -569,10 +575,14 @@ int omap2_clkdm_clk_enable(struct clockdomain *clkdm, struct clk *clk) v = omap2_clkdm_clktrctrl_read(clkdm); if ((cpu_is_omap34xx() && v == OMAP34XX_CLKSTCTRL_ENABLE_AUTO) || - (cpu_is_omap24xx() && v == OMAP24XX_CLKSTCTRL_ENABLE_AUTO)) + (cpu_is_omap24xx() && v == OMAP24XX_CLKSTCTRL_ENABLE_AUTO)) { + /* Disable HW transitions when we are changing deps */ + _omap2_clkdm_set_hwsup(clkdm, 0); _clkdm_add_autodeps(clkdm); - else + _omap2_clkdm_set_hwsup(clkdm, 1); + } else { omap2_clkdm_wakeup(clkdm); + } pwrdm_wait_transition(clkdm->pwrdm.ptr); pwrdm_clkdm_state_switch(clkdm); @@ -623,10 +633,14 @@ int omap2_clkdm_clk_disable(struct clockdomain *clkdm, struct clk *clk) v = omap2_clkdm_clktrctrl_read(clkdm); if ((cpu_is_omap34xx() && v == OMAP34XX_CLKSTCTRL_ENABLE_AUTO) || - (cpu_is_omap24xx() && v == OMAP24XX_CLKSTCTRL_ENABLE_AUTO)) + (cpu_is_omap24xx() && v == OMAP24XX_CLKSTCTRL_ENABLE_AUTO)) { + /* Disable HW transitions when we are changing deps */ + _omap2_clkdm_set_hwsup(clkdm, 0); _clkdm_del_autodeps(clkdm); - else + _omap2_clkdm_set_hwsup(clkdm, 1); + } else { omap2_clkdm_sleep(clkdm); + } pwrdm_clkdm_state_switch(clkdm); diff --git a/arch/arm/mach-omap2/gpmc.c b/arch/arm/mach-omap2/gpmc.c index 15876828db23..f3c992e29651 100644 --- a/arch/arm/mach-omap2/gpmc.c +++ b/arch/arm/mach-omap2/gpmc.c @@ -366,7 +366,7 @@ int gpmc_cs_request(int cs, unsigned long size, unsigned long *base) if (r < 0) goto out; - gpmc_cs_enable_mem(cs, res->start, res->end - res->start + 1); + gpmc_cs_enable_mem(cs, res->start, resource_size(res)); *base = res->start; gpmc_cs_set_reserved(cs, 1); out: @@ -378,7 +378,7 @@ EXPORT_SYMBOL(gpmc_cs_request); void gpmc_cs_free(int cs) { spin_lock(&gpmc_mem_lock); - if (cs >= GPMC_CS_NUM || !gpmc_cs_reserved(cs)) { + if (cs >= GPMC_CS_NUM || cs < 0 || !gpmc_cs_reserved(cs)) { printk(KERN_ERR "Trying to free non-reserved GPMC CS%d\n", cs); BUG(); spin_unlock(&gpmc_mem_lock); diff --git a/arch/arm/mach-omap2/io.c b/arch/arm/mach-omap2/io.c index e3a3bad1d84f..56be87d13edb 100644 --- a/arch/arm/mach-omap2/io.c +++ b/arch/arm/mach-omap2/io.c @@ -302,7 +302,9 @@ void __init omap2_init_common_hw(struct omap_sdrc_params *sdrc_cs0, pwrdm_init(powerdomains_omap); clkdm_init(clockdomains_omap, clkdm_pwrdm_autodeps); omap2_clk_init(); +#endif omap_serial_early_init(); +#ifndef CONFIG_ARCH_OMAP4 omap_hwmod_late_init(); omap_pm_if_init(); omap2_sdrc_init(sdrc_cs0, sdrc_cs1); diff --git a/arch/arm/mach-omap2/mailbox.c b/arch/arm/mach-omap2/mailbox.c index c035ad3426d0..ef57b38a56a4 100644 --- a/arch/arm/mach-omap2/mailbox.c +++ b/arch/arm/mach-omap2/mailbox.c @@ -300,7 +300,7 @@ static int __devinit omap2_mbox_probe(struct platform_device *pdev) dev_err(&pdev->dev, "invalid mem resource\n"); return -ENODEV; } - mbox_base = ioremap(res->start, res->end - res->start); + mbox_base = ioremap(res->start, resource_size(res)); if (!mbox_base) return -ENOMEM; diff --git a/arch/arm/mach-omap2/pm-debug.c b/arch/arm/mach-omap2/pm-debug.c index 1b4c1600f8d8..2fc4d6abbd0a 100644 --- a/arch/arm/mach-omap2/pm-debug.c +++ b/arch/arm/mach-omap2/pm-debug.c @@ -541,7 +541,7 @@ static int __init pm_dbg_init(void) printk(KERN_ERR "%s: only OMAP3 supported\n", __func__); return -ENODEV; } - + d = debugfs_create_dir("pm_debug", NULL); if (IS_ERR(d)) return PTR_ERR(d); @@ -551,7 +551,7 @@ static int __init pm_dbg_init(void) (void) debugfs_create_file("time", S_IRUGO, d, (void *)DEBUG_FILE_TIMERS, &debug_fops); - pwrdm_for_each(pwrdms_setup, (void *)d); + pwrdm_for_each_nolock(pwrdms_setup, (void *)d); pm_dbg_dir = debugfs_create_dir("registers", d); if (IS_ERR(pm_dbg_dir)) diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c index 0ff5a6c53aa0..89463190923a 100644 --- a/arch/arm/mach-omap2/pm34xx.c +++ b/arch/arm/mach-omap2/pm34xx.c @@ -51,97 +51,112 @@ static void (*_omap_sram_idle)(u32 *addr, int save_state); static struct powerdomain *mpu_pwrdm; -/* PRCM Interrupt Handler for wakeups */ -static irqreturn_t prcm_interrupt_handler (int irq, void *dev_id) +/* + * PRCM Interrupt Handler Helper Function + * + * The purpose of this function is to clear any wake-up events latched + * in the PRCM PM_WKST_x registers. It is possible that a wake-up event + * may occur whilst attempting to clear a PM_WKST_x register and thus + * set another bit in this register. A while loop is used to ensure + * that any peripheral wake-up events occurring while attempting to + * clear the PM_WKST_x are detected and cleared. + */ +static int prcm_clear_mod_irqs(s16 module, u8 regs) { - u32 wkst, irqstatus_mpu; - u32 fclk, iclk; - - /* WKUP */ - wkst = prm_read_mod_reg(WKUP_MOD, PM_WKST); + u32 wkst, fclk, iclk, clken; + u16 wkst_off = (regs == 3) ? OMAP3430ES2_PM_WKST3 : PM_WKST1; + u16 fclk_off = (regs == 3) ? OMAP3430ES2_CM_FCLKEN3 : CM_FCLKEN1; + u16 iclk_off = (regs == 3) ? CM_ICLKEN3 : CM_ICLKEN1; + u16 grpsel_off = (regs == 3) ? + OMAP3430ES2_PM_MPUGRPSEL3 : OMAP3430_PM_MPUGRPSEL; + int c = 0; + + wkst = prm_read_mod_reg(module, wkst_off); + wkst &= prm_read_mod_reg(module, grpsel_off); if (wkst) { - iclk = cm_read_mod_reg(WKUP_MOD, CM_ICLKEN); - fclk = cm_read_mod_reg(WKUP_MOD, CM_FCLKEN); - cm_set_mod_reg_bits(wkst, WKUP_MOD, CM_ICLKEN); - cm_set_mod_reg_bits(wkst, WKUP_MOD, CM_FCLKEN); - prm_write_mod_reg(wkst, WKUP_MOD, PM_WKST); - while (prm_read_mod_reg(WKUP_MOD, PM_WKST)) - cpu_relax(); - cm_write_mod_reg(iclk, WKUP_MOD, CM_ICLKEN); - cm_write_mod_reg(fclk, WKUP_MOD, CM_FCLKEN); + iclk = cm_read_mod_reg(module, iclk_off); + fclk = cm_read_mod_reg(module, fclk_off); + while (wkst) { + clken = wkst; + cm_set_mod_reg_bits(clken, module, iclk_off); + /* + * For USBHOST, we don't know whether HOST1 or + * HOST2 woke us up, so enable both f-clocks + */ + if (module == OMAP3430ES2_USBHOST_MOD) + clken |= 1 << OMAP3430ES2_EN_USBHOST2_SHIFT; + cm_set_mod_reg_bits(clken, module, fclk_off); + prm_write_mod_reg(wkst, module, wkst_off); + wkst = prm_read_mod_reg(module, wkst_off); + c++; + } + cm_write_mod_reg(iclk, module, iclk_off); + cm_write_mod_reg(fclk, module, fclk_off); } - /* CORE */ - wkst = prm_read_mod_reg(CORE_MOD, PM_WKST1); - if (wkst) { - iclk = cm_read_mod_reg(CORE_MOD, CM_ICLKEN1); - fclk = cm_read_mod_reg(CORE_MOD, CM_FCLKEN1); - cm_set_mod_reg_bits(wkst, CORE_MOD, CM_ICLKEN1); - cm_set_mod_reg_bits(wkst, CORE_MOD, CM_FCLKEN1); - prm_write_mod_reg(wkst, CORE_MOD, PM_WKST1); - while (prm_read_mod_reg(CORE_MOD, PM_WKST1)) - cpu_relax(); - cm_write_mod_reg(iclk, CORE_MOD, CM_ICLKEN1); - cm_write_mod_reg(fclk, CORE_MOD, CM_FCLKEN1); - } - wkst = prm_read_mod_reg(CORE_MOD, OMAP3430ES2_PM_WKST3); - if (wkst) { - iclk = cm_read_mod_reg(CORE_MOD, CM_ICLKEN3); - fclk = cm_read_mod_reg(CORE_MOD, OMAP3430ES2_CM_FCLKEN3); - cm_set_mod_reg_bits(wkst, CORE_MOD, CM_ICLKEN3); - cm_set_mod_reg_bits(wkst, CORE_MOD, OMAP3430ES2_CM_FCLKEN3); - prm_write_mod_reg(wkst, CORE_MOD, OMAP3430ES2_PM_WKST3); - while (prm_read_mod_reg(CORE_MOD, OMAP3430ES2_PM_WKST3)) - cpu_relax(); - cm_write_mod_reg(iclk, CORE_MOD, CM_ICLKEN3); - cm_write_mod_reg(fclk, CORE_MOD, OMAP3430ES2_CM_FCLKEN3); - } + return c; +} - /* PER */ - wkst = prm_read_mod_reg(OMAP3430_PER_MOD, PM_WKST); - if (wkst) { - iclk = cm_read_mod_reg(OMAP3430_PER_MOD, CM_ICLKEN); - fclk = cm_read_mod_reg(OMAP3430_PER_MOD, CM_FCLKEN); - cm_set_mod_reg_bits(wkst, OMAP3430_PER_MOD, CM_ICLKEN); - cm_set_mod_reg_bits(wkst, OMAP3430_PER_MOD, CM_FCLKEN); - prm_write_mod_reg(wkst, OMAP3430_PER_MOD, PM_WKST); - while (prm_read_mod_reg(OMAP3430_PER_MOD, PM_WKST)) - cpu_relax(); - cm_write_mod_reg(iclk, OMAP3430_PER_MOD, CM_ICLKEN); - cm_write_mod_reg(fclk, OMAP3430_PER_MOD, CM_FCLKEN); - } +static int _prcm_int_handle_wakeup(void) +{ + int c; + c = prcm_clear_mod_irqs(WKUP_MOD, 1); + c += prcm_clear_mod_irqs(CORE_MOD, 1); + c += prcm_clear_mod_irqs(OMAP3430_PER_MOD, 1); if (omap_rev() > OMAP3430_REV_ES1_0) { - /* USBHOST */ - wkst = prm_read_mod_reg(OMAP3430ES2_USBHOST_MOD, PM_WKST); - if (wkst) { - iclk = cm_read_mod_reg(OMAP3430ES2_USBHOST_MOD, - CM_ICLKEN); - fclk = cm_read_mod_reg(OMAP3430ES2_USBHOST_MOD, - CM_FCLKEN); - cm_set_mod_reg_bits(wkst, OMAP3430ES2_USBHOST_MOD, - CM_ICLKEN); - cm_set_mod_reg_bits(wkst, OMAP3430ES2_USBHOST_MOD, - CM_FCLKEN); - prm_write_mod_reg(wkst, OMAP3430ES2_USBHOST_MOD, - PM_WKST); - while (prm_read_mod_reg(OMAP3430ES2_USBHOST_MOD, - PM_WKST)) - cpu_relax(); - cm_write_mod_reg(iclk, OMAP3430ES2_USBHOST_MOD, - CM_ICLKEN); - cm_write_mod_reg(fclk, OMAP3430ES2_USBHOST_MOD, - CM_FCLKEN); - } + c += prcm_clear_mod_irqs(CORE_MOD, 3); + c += prcm_clear_mod_irqs(OMAP3430ES2_USBHOST_MOD, 1); } - irqstatus_mpu = prm_read_mod_reg(OCP_MOD, - OMAP3_PRM_IRQSTATUS_MPU_OFFSET); - prm_write_mod_reg(irqstatus_mpu, OCP_MOD, - OMAP3_PRM_IRQSTATUS_MPU_OFFSET); + return c; +} + +/* + * PRCM Interrupt Handler + * + * The PRM_IRQSTATUS_MPU register indicates if there are any pending + * interrupts from the PRCM for the MPU. These bits must be cleared in + * order to clear the PRCM interrupt. The PRCM interrupt handler is + * implemented to simply clear the PRM_IRQSTATUS_MPU in order to clear + * the PRCM interrupt. Please note that bit 0 of the PRM_IRQSTATUS_MPU + * register indicates that a wake-up event is pending for the MPU and + * this bit can only be cleared if the all the wake-up events latched + * in the various PM_WKST_x registers have been cleared. The interrupt + * handler is implemented using a do-while loop so that if a wake-up + * event occurred during the processing of the prcm interrupt handler + * (setting a bit in the corresponding PM_WKST_x register and thus + * preventing us from clearing bit 0 of the PRM_IRQSTATUS_MPU register) + * this would be handled. + */ +static irqreturn_t prcm_interrupt_handler (int irq, void *dev_id) +{ + u32 irqstatus_mpu; + int c = 0; + + do { + irqstatus_mpu = prm_read_mod_reg(OCP_MOD, + OMAP3_PRM_IRQSTATUS_MPU_OFFSET); + + if (irqstatus_mpu & (OMAP3430_WKUP_ST | OMAP3430_IO_ST)) { + c = _prcm_int_handle_wakeup(); + + /* + * Is the MPU PRCM interrupt handler racing with the + * IVA2 PRCM interrupt handler ? + */ + WARN(c == 0, "prcm: WARNING: PRCM indicated MPU wakeup " + "but no wakeup sources are marked\n"); + } else { + /* XXX we need to expand our PRCM interrupt handler */ + WARN(1, "prcm: WARNING: PRCM interrupt received, but " + "no code to handle it (%08x)\n", irqstatus_mpu); + } + + prm_write_mod_reg(irqstatus_mpu, OCP_MOD, + OMAP3_PRM_IRQSTATUS_MPU_OFFSET); - while (prm_read_mod_reg(OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET)) - cpu_relax(); + } while (prm_read_mod_reg(OCP_MOD, OMAP3_PRM_IRQSTATUS_MPU_OFFSET)); return IRQ_HANDLED; } @@ -624,6 +639,17 @@ static void __init prcm_setup_regs(void) prm_write_mod_reg(OMAP3430_IO_EN | OMAP3430_WKUP_EN, OCP_MOD, OMAP3_PRM_IRQENABLE_MPU_OFFSET); + /* Enable wakeups in PER */ + prm_write_mod_reg(OMAP3430_EN_GPIO2 | OMAP3430_EN_GPIO3 | + OMAP3430_EN_GPIO4 | OMAP3430_EN_GPIO5 | + OMAP3430_EN_GPIO6 | OMAP3430_EN_UART3, + OMAP3430_PER_MOD, PM_WKEN); + /* and allow them to wake up MPU */ + prm_write_mod_reg(OMAP3430_GRPSEL_GPIO2 | OMAP3430_EN_GPIO3 | + OMAP3430_GRPSEL_GPIO4 | OMAP3430_EN_GPIO5 | + OMAP3430_GRPSEL_GPIO6 | OMAP3430_EN_UART3, + OMAP3430_PER_MOD, OMAP3430_PM_MPUGRPSEL); + /* Don't attach IVA interrupts */ prm_write_mod_reg(0, WKUP_MOD, OMAP3430_PM_IVAGRPSEL); prm_write_mod_reg(0, CORE_MOD, OMAP3430_PM_IVAGRPSEL1); diff --git a/arch/arm/mach-omap2/powerdomain.c b/arch/arm/mach-omap2/powerdomain.c index 2594cbff3947..f00289abd30f 100644 --- a/arch/arm/mach-omap2/powerdomain.c +++ b/arch/arm/mach-omap2/powerdomain.c @@ -273,35 +273,50 @@ struct powerdomain *pwrdm_lookup(const char *name) } /** - * pwrdm_for_each - call function on each registered clockdomain + * pwrdm_for_each_nolock - call function on each registered clockdomain * @fn: callback function * * * Call the supplied function for each registered powerdomain. The * callback function can return anything but 0 to bail out early from - * the iterator. The callback function is called with the pwrdm_rwlock - * held for reading, so no powerdomain structure manipulation - * functions should be called from the callback, although hardware - * powerdomain control functions are fine. Returns the last return - * value of the callback function, which should be 0 for success or - * anything else to indicate failure; or -EINVAL if the function - * pointer is null. + * the iterator. Returns the last return value of the callback function, which + * should be 0 for success or anything else to indicate failure; or -EINVAL if + * the function pointer is null. */ -int pwrdm_for_each(int (*fn)(struct powerdomain *pwrdm, void *user), - void *user) +int pwrdm_for_each_nolock(int (*fn)(struct powerdomain *pwrdm, void *user), + void *user) { struct powerdomain *temp_pwrdm; - unsigned long flags; int ret = 0; if (!fn) return -EINVAL; - read_lock_irqsave(&pwrdm_rwlock, flags); list_for_each_entry(temp_pwrdm, &pwrdm_list, node) { ret = (*fn)(temp_pwrdm, user); if (ret) break; } + + return ret; +} + +/** + * pwrdm_for_each - call function on each registered clockdomain + * @fn: callback function * + * + * This function is the same as 'pwrdm_for_each_nolock()', but keeps the + * &pwrdm_rwlock locked for reading, so no powerdomain structure manipulation + * functions should be called from the callback, although hardware powerdomain + * control functions are fine. + */ +int pwrdm_for_each(int (*fn)(struct powerdomain *pwrdm, void *user), + void *user) +{ + unsigned long flags; + int ret; + + read_lock_irqsave(&pwrdm_rwlock, flags); + ret = pwrdm_for_each_nolock(fn, user); read_unlock_irqrestore(&pwrdm_rwlock, flags); return ret; diff --git a/arch/arm/mach-omap2/serial.c b/arch/arm/mach-omap2/serial.c index ae2186892c85..54dfeb5d5667 100644 --- a/arch/arm/mach-omap2/serial.c +++ b/arch/arm/mach-omap2/serial.c @@ -109,16 +109,6 @@ static struct plat_serial8250_port serial_platform_data2[] = { .regshift = 2, .uartclk = OMAP24XX_BASE_BAUD * 16, }, { -#ifdef CONFIG_ARCH_OMAP4 - .membase = OMAP2_IO_ADDRESS(OMAP_UART4_BASE), - .mapbase = OMAP_UART4_BASE, - .irq = 70, - .flags = UPF_BOOT_AUTOCONF, - .iotype = UPIO_MEM, - .regshift = 2, - .uartclk = OMAP24XX_BASE_BAUD * 16, - }, { -#endif .flags = 0 } }; diff --git a/arch/arm/mach-pxa/cm-x300.c b/arch/arm/mach-pxa/cm-x300.c index aac2cda60e09..102916f1e465 100644 --- a/arch/arm/mach-pxa/cm-x300.c +++ b/arch/arm/mach-pxa/cm-x300.c @@ -43,10 +43,10 @@ #define CM_X300_ETH_PHYS 0x08000010 -#define GPIO82_MMC2_IRQ (82) -#define GPIO85_MMC2_WP (85) +#define GPIO82_MMC_IRQ (82) +#define GPIO85_MMC_WP (85) -#define CM_X300_MMC2_IRQ IRQ_GPIO(GPIO82_MMC2_IRQ) +#define CM_X300_MMC_IRQ IRQ_GPIO(GPIO82_MMC_IRQ) #define GPIO95_RTC_CS (95) #define GPIO96_RTC_WR (96) @@ -292,37 +292,37 @@ static inline void cm_x300_init_nand(void) {} #endif #if defined(CONFIG_MMC) || defined(CONFIG_MMC_MODULE) -/* The first MMC slot of CM-X300 is hardwired to Libertas card and has +static struct pxamci_platform_data cm_x300_mci_platform_data = { + .detect_delay = 20, + .ocr_mask = MMC_VDD_32_33|MMC_VDD_33_34, + .gpio_card_detect = GPIO82_MMC_IRQ, + .gpio_card_ro = GPIO85_MMC_WP, + .gpio_power = -1, +}; + +/* The second MMC slot of CM-X300 is hardwired to Libertas card and has no detection/ro pins */ -static int cm_x300_mci_init(struct device *dev, - irq_handler_t cm_x300_detect_int, - void *data) +static int cm_x300_mci2_init(struct device *dev, + irq_handler_t cm_x300_detect_int, + void *data) { return 0; } -static void cm_x300_mci_exit(struct device *dev, void *data) +static void cm_x300_mci2_exit(struct device *dev, void *data) { } -static struct pxamci_platform_data cm_x300_mci_platform_data = { +static struct pxamci_platform_data cm_x300_mci2_platform_data = { .detect_delay = 20, .ocr_mask = MMC_VDD_32_33|MMC_VDD_33_34, - .init = cm_x300_mci_init, - .exit = cm_x300_mci_exit, + .init = cm_x300_mci2_init, + .exit = cm_x300_mci2_exit, .gpio_card_detect = -1, .gpio_card_ro = -1, .gpio_power = -1, }; -static struct pxamci_platform_data cm_x300_mci2_platform_data = { - .detect_delay = 20, - .ocr_mask = MMC_VDD_32_33|MMC_VDD_33_34, - .gpio_card_detect = GPIO82_MMC2_IRQ, - .gpio_card_ro = GPIO85_MMC2_WP, - .gpio_power = -1, -}; - static void __init cm_x300_init_mmc(void) { pxa_set_mci_info(&cm_x300_mci_platform_data); diff --git a/arch/arm/mach-pxa/colibri-pxa320.c b/arch/arm/mach-pxa/colibri-pxa320.c index 494572825c7d..ec0e14b96682 100644 --- a/arch/arm/mach-pxa/colibri-pxa320.c +++ b/arch/arm/mach-pxa/colibri-pxa320.c @@ -27,6 +27,7 @@ #include <mach/colibri.h> #include <mach/pxafb.h> #include <mach/ohci.h> +#include <mach/audio.h> #include "generic.h" #include "devices.h" @@ -145,7 +146,8 @@ static void __init colibri_pxa320_init_lcd(void) static inline void colibri_pxa320_init_lcd(void) {} #endif -#if defined(SND_AC97_CODEC) || defined(SND_AC97_CODEC_MODULE) +#if defined(CONFIG_SND_AC97_CODEC) || \ + defined(CONFIG_SND_AC97_CODEC_MODULE) static mfp_cfg_t colibri_pxa320_ac97_pin_config[] __initdata = { GPIO34_AC97_SYSCLK, GPIO35_AC97_SDATA_IN_0, diff --git a/arch/arm/mach-pxa/cpufreq-pxa2xx.c b/arch/arm/mach-pxa/cpufreq-pxa2xx.c index 3a8ee2272add..983cc8c20081 100644 --- a/arch/arm/mach-pxa/cpufreq-pxa2xx.c +++ b/arch/arm/mach-pxa/cpufreq-pxa2xx.c @@ -155,7 +155,7 @@ MODULE_PARM_DESC(pxa255_turbo_table, "Selects the frequency table (0 = run table static pxa_freqs_t pxa27x_freqs[] = { {104000, 104000, PXA27x_CCCR(1, 8, 2), 0, CCLKCFG2(1, 0, 1), 900000, 1705000 }, - {156000, 104000, PXA27x_CCCR(1, 8, 6), 0, CCLKCFG2(1, 1, 1), 1000000, 1705000 }, + {156000, 104000, PXA27x_CCCR(1, 8, 3), 0, CCLKCFG2(1, 0, 1), 1000000, 1705000 }, {208000, 208000, PXA27x_CCCR(0, 16, 2), 1, CCLKCFG2(0, 0, 1), 1180000, 1705000 }, {312000, 208000, PXA27x_CCCR(1, 16, 3), 1, CCLKCFG2(1, 0, 1), 1250000, 1705000 }, {416000, 208000, PXA27x_CCCR(1, 16, 4), 1, CCLKCFG2(1, 0, 1), 1350000, 1705000 }, diff --git a/arch/arm/mach-pxa/csb726.c b/arch/arm/mach-pxa/csb726.c index 79141f862728..965480eb4fe6 100644 --- a/arch/arm/mach-pxa/csb726.c +++ b/arch/arm/mach-pxa/csb726.c @@ -238,7 +238,7 @@ static struct resource csb726_lan_resources[] = { }; struct smsc911x_platform_config csb726_lan_config = { - .irq_type = SMSC911X_IRQ_POLARITY_ACTIVE_LOW, + .irq_polarity = SMSC911X_IRQ_POLARITY_ACTIVE_LOW, .irq_type = SMSC911X_IRQ_TYPE_PUSH_PULL, .flags = SMSC911X_USE_32BIT, .phy_interface = PHY_INTERFACE_MODE_MII, diff --git a/arch/arm/mach-pxa/hx4700.c b/arch/arm/mach-pxa/hx4700.c index abff9e132749..83bd3c6e3884 100644 --- a/arch/arm/mach-pxa/hx4700.c +++ b/arch/arm/mach-pxa/hx4700.c @@ -604,7 +604,7 @@ static struct platform_device gpio_vbus = { static const struct ads7846_platform_data tsc2046_info = { .model = 7846, .vref_delay_usecs = 100, - .pressure_max = 512, + .pressure_max = 1024, .debounce_max = 10, .debounce_tol = 3, .debounce_rep = 1, diff --git a/arch/arm/mach-pxa/include/mach/entry-macro.S b/arch/arm/mach-pxa/include/mach/entry-macro.S index 241880608ac6..a73bc86a3c26 100644 --- a/arch/arm/mach-pxa/include/mach/entry-macro.S +++ b/arch/arm/mach-pxa/include/mach/entry-macro.S @@ -46,5 +46,6 @@ beq 1001f bic \irqstat, \irqstat, #0x80000000 mov \irqnr, \irqstat, lsr #16 + add \irqnr, \irqnr, #(PXA_IRQ(0)) 1001: .endm diff --git a/arch/arm/mach-pxa/irq.c b/arch/arm/mach-pxa/irq.c index d694ce289668..6112af431fa4 100644 --- a/arch/arm/mach-pxa/irq.c +++ b/arch/arm/mach-pxa/irq.c @@ -25,6 +25,8 @@ #include "generic.h" +#define MAX_INTERNAL_IRQS 128 + #define IRQ_BIT(n) (((n) - PXA_IRQ(0)) & 0x1f) #define _ICMR(n) (*((((n) - PXA_IRQ(0)) & ~0x1f) ? &ICMR2 : &ICMR)) #define _ICLR(n) (*((((n) - PXA_IRQ(0)) & ~0x1f) ? &ICLR2 : &ICLR)) @@ -122,6 +124,8 @@ void __init pxa_init_irq(int irq_nr, set_wake_t fn) { int irq, i; + BUG_ON(irq_nr > MAX_INTERNAL_IRQS); + pxa_internal_irq_nr = irq_nr; for (irq = PXA_IRQ(0); irq < PXA_IRQ(irq_nr); irq += 32) { @@ -149,7 +153,8 @@ void __init pxa_init_irq(int irq_nr, set_wake_t fn) } #ifdef CONFIG_PM -static unsigned long saved_icmr[2]; +static unsigned long saved_icmr[MAX_INTERNAL_IRQS/32]; +static unsigned long saved_ipr[MAX_INTERNAL_IRQS]; static int pxa_irq_suspend(struct sys_device *dev, pm_message_t state) { @@ -159,6 +164,8 @@ static int pxa_irq_suspend(struct sys_device *dev, pm_message_t state) saved_icmr[i] = _ICMR(irq); _ICMR(irq) = 0; } + for (i = 0; i < pxa_internal_irq_nr; i++) + saved_ipr[i] = IPR(i); return 0; } @@ -171,6 +178,8 @@ static int pxa_irq_resume(struct sys_device *dev) _ICMR(irq) = saved_icmr[i]; _ICLR(irq) = 0; } + for (i = 0; i < pxa_internal_irq_nr; i++) + IPR(i) = saved_ipr[i]; ICCR = 1; return 0; diff --git a/arch/arm/mach-pxa/palmtc.c b/arch/arm/mach-pxa/palmtc.c index bb2cc0dd44ec..0b92291a58f6 100644 --- a/arch/arm/mach-pxa/palmtc.c +++ b/arch/arm/mach-pxa/palmtc.c @@ -292,10 +292,10 @@ const static unsigned int palmtc_keypad_col_gpios[] = { static struct matrix_keypad_platform_data palmtc_keypad_platform_data = { .keymap_data = &palmtc_keymap_data, - .col_gpios = palmtc_keypad_row_gpios, - .num_col_gpios = 12, - .row_gpios = palmtc_keypad_col_gpios, - .num_row_gpios = 4, + .row_gpios = palmtc_keypad_row_gpios, + .num_row_gpios = ARRAY_SIZE(palmtc_keypad_row_gpios), + .col_gpios = palmtc_keypad_col_gpios, + .num_col_gpios = ARRAY_SIZE(palmtc_keypad_col_gpios), .active_low = 1, .debounce_ms = 20, diff --git a/arch/arm/mach-pxa/spitz.c b/arch/arm/mach-pxa/spitz.c index ee8d6038ce82..3da45d051743 100644 --- a/arch/arm/mach-pxa/spitz.c +++ b/arch/arm/mach-pxa/spitz.c @@ -15,6 +15,7 @@ #include <linux/kernel.h> #include <linux/platform_device.h> #include <linux/delay.h> +#include <linux/gpio_keys.h> #include <linux/gpio.h> #include <linux/leds.h> #include <linux/mtd/physmap.h> @@ -375,6 +376,43 @@ static struct platform_device spitzkbd_device = { }; +static struct gpio_keys_button spitz_gpio_keys[] = { + { + .type = EV_PWR, + .code = KEY_SUSPEND, + .gpio = SPITZ_GPIO_ON_KEY, + .desc = "On/Off", + .wakeup = 1, + }, + /* Two buttons detecting the lid state */ + { + .type = EV_SW, + .code = 0, + .gpio = SPITZ_GPIO_SWA, + .desc = "Display Down", + }, + { + .type = EV_SW, + .code = 1, + .gpio = SPITZ_GPIO_SWB, + .desc = "Lid Closed", + }, +}; + +static struct gpio_keys_platform_data spitz_gpio_keys_platform_data = { + .buttons = spitz_gpio_keys, + .nbuttons = ARRAY_SIZE(spitz_gpio_keys), +}; + +static struct platform_device spitz_gpio_keys_device = { + .name = "gpio-keys", + .id = -1, + .dev = { + .platform_data = &spitz_gpio_keys_platform_data, + }, +}; + + /* * Spitz LEDs */ @@ -689,6 +727,7 @@ static struct platform_device sharpsl_rom_device = { static struct platform_device *devices[] __initdata = { &spitzscoop_device, &spitzkbd_device, + &spitz_gpio_keys_device, &spitzled_device, &sharpsl_nand_device, &sharpsl_rom_device, @@ -740,11 +779,34 @@ static void __init common_init(void) pxa_set_i2c_info(NULL); } +#if defined(CONFIG_MACH_AKITA) || defined(CONFIG_MACH_BORZOI) +static struct nand_bbt_descr sharpsl_akita_bbt = { + .options = 0, + .offs = 4, + .len = 1, + .pattern = scan_ff_pattern +}; + +static struct nand_ecclayout akita_oobinfo = { + .eccbytes = 24, + .eccpos = { + 0x5, 0x1, 0x2, 0x3, 0x6, 0x7, 0x15, 0x11, + 0x12, 0x13, 0x16, 0x17, 0x25, 0x21, 0x22, 0x23, + 0x26, 0x27, 0x35, 0x31, 0x32, 0x33, 0x36, 0x37}, + .oobfree = {{0x08, 0x09}} +}; +#endif + #if defined(CONFIG_MACH_SPITZ) || defined(CONFIG_MACH_BORZOI) static void __init spitz_init(void) { spitz_ficp_platform_data.gpio_pwdown = SPITZ_GPIO_IR_ON; + if (machine_is_borzoi()) { + sharpsl_nand_platform_data.badblock_pattern = &sharpsl_akita_bbt; + sharpsl_nand_platform_data.ecc_layout = &akita_oobinfo; + } + platform_scoop_config = &spitz_pcmcia_config; common_init(); @@ -769,22 +831,6 @@ static struct i2c_board_info akita_i2c_board_info[] = { }, }; -static struct nand_bbt_descr sharpsl_akita_bbt = { - .options = 0, - .offs = 4, - .len = 1, - .pattern = scan_ff_pattern -}; - -static struct nand_ecclayout akita_oobinfo = { - .eccbytes = 24, - .eccpos = { - 0x5, 0x1, 0x2, 0x3, 0x6, 0x7, 0x15, 0x11, - 0x12, 0x13, 0x16, 0x17, 0x25, 0x21, 0x22, 0x23, - 0x26, 0x27, 0x35, 0x31, 0x32, 0x33, 0x36, 0x37}, - .oobfree = {{0x08, 0x09}} -}; - static void __init akita_init(void) { spitz_ficp_platform_data.gpio_pwdown = AKITA_GPIO_IR_ON; diff --git a/arch/arm/mach-realview/Kconfig b/arch/arm/mach-realview/Kconfig index dfc9b0bc6eb2..c48e1f2c3349 100644 --- a/arch/arm/mach-realview/Kconfig +++ b/arch/arm/mach-realview/Kconfig @@ -70,6 +70,8 @@ config MACH_REALVIEW_PBX bool "Support RealView/PBX platform" select ARM_GIC select HAVE_PATA_PLATFORM + select ARCH_SPARSEMEM_ENABLE if CPU_V7 && !HIGH_PHYS_OFFSET + select ZONE_DMA if SPARSEMEM help Include support for the ARM(R) RealView PBX platform. @@ -82,6 +84,7 @@ config REALVIEW_HIGH_PHYS_OFFSET 0x70000000, 256MB of which being mirrored at 0x00000000. If the board supports 512MB of RAM, this option allows the memory to be accessed contiguously at the high physical - offset. + offset. On the PBX board, disabling this option allows 1GB of + RAM to be used with SPARSEMEM. endmenu diff --git a/arch/arm/mach-realview/core.c b/arch/arm/mach-realview/core.c index a2083b60e3fb..9f293438e020 100644 --- a/arch/arm/mach-realview/core.c +++ b/arch/arm/mach-realview/core.c @@ -59,6 +59,25 @@ /* used by entry-macro.S and platsmp.c */ void __iomem *gic_cpu_base_addr; +#ifdef CONFIG_ZONE_DMA +/* + * Adjust the zones if there are restrictions for DMA access. + */ +void __init realview_adjust_zones(int node, unsigned long *size, + unsigned long *hole) +{ + unsigned long dma_size = SZ_256M >> PAGE_SHIFT; + + if (!machine_is_realview_pbx() || node || (size[0] <= dma_size)) + return; + + size[ZONE_NORMAL] = size[0] - dma_size; + size[ZONE_DMA] = dma_size; + hole[ZONE_NORMAL] = hole[0]; + hole[ZONE_DMA] = 0; +} +#endif + /* * This is the RealView sched_clock implementation. This has * a resolution of 41.7ns, and a maximum value of about 179s. @@ -543,7 +562,7 @@ static int realview_clcd_setup(struct clcd_fb *fb) fb->panel = realview_clcd_panel(); fb->fb.screen_base = dma_alloc_writecombine(&fb->dev->dev, framesize, - &dma, GFP_KERNEL); + &dma, GFP_KERNEL | GFP_DMA); if (!fb->fb.screen_base) { printk(KERN_ERR "CLCD: unable to map framebuffer\n"); return -ENOMEM; @@ -788,3 +807,24 @@ void __init realview_timer_init(unsigned int timer_irq) realview_clocksource_init(); realview_clockevents_init(timer_irq); } + +/* + * Setup the memory banks. + */ +void realview_fixup(struct machine_desc *mdesc, struct tag *tags, char **from, + struct meminfo *meminfo) +{ + /* + * Most RealView platforms have 512MB contiguous RAM at 0x70000000. + * Half of this is mirrored at 0. + */ +#ifdef CONFIG_REALVIEW_HIGH_PHYS_OFFSET + meminfo->bank[0].start = 0x70000000; + meminfo->bank[0].size = SZ_512M; + meminfo->nr_banks = 1; +#else + meminfo->bank[0].start = 0; + meminfo->bank[0].size = SZ_256M; + meminfo->nr_banks = 1; +#endif +} diff --git a/arch/arm/mach-realview/core.h b/arch/arm/mach-realview/core.h index 46cd6acb4d40..781bca68a9fa 100644 --- a/arch/arm/mach-realview/core.h +++ b/arch/arm/mach-realview/core.h @@ -25,6 +25,7 @@ #include <linux/amba/bus.h> #include <linux/io.h> +#include <asm/setup.h> #include <asm/leds.h> #define AMBA_DEVICE(name,busid,base,plat) \ @@ -44,6 +45,8 @@ static struct amba_device name##_device = { \ /* .dma = base##_DMA,*/ \ } +struct machine_desc; + extern struct platform_device realview_flash_device; extern struct platform_device realview_cf_device; extern struct platform_device realview_i2c_device; @@ -61,5 +64,8 @@ extern void realview_timer_init(unsigned int timer_irq); extern int realview_flash_register(struct resource *res, u32 num); extern int realview_eth_register(const char *name, struct resource *res); extern int realview_usb_register(struct resource *res); +extern void realview_fixup(struct machine_desc *mdesc, struct tag *tags, + char **from, struct meminfo *meminfo); +extern void (*realview_reset)(char); #endif diff --git a/arch/arm/mach-realview/include/mach/board-pb1176.h b/arch/arm/mach-realview/include/mach/board-pb1176.h index 98f8e7eeacc2..34b80b7d40b8 100644 --- a/arch/arm/mach-realview/include/mach/board-pb1176.h +++ b/arch/arm/mach-realview/include/mach/board-pb1176.h @@ -73,4 +73,9 @@ #define REALVIEW_PB1176_GIC_DIST_BASE 0x10041000 /* GIC distributor, on FPGA */ #define REALVIEW_PB1176_L220_BASE 0x10110000 /* L220 registers */ +/* + * Control register SYS_RESETCTL is set to 1 to force a soft reset + */ +#define REALVIEW_PB1176_SYS_LOCKVAL_RSTCTL 0x0100 + #endif /* __ASM_ARCH_BOARD_PB1176_H */ diff --git a/arch/arm/mach-realview/include/mach/board-pb11mp.h b/arch/arm/mach-realview/include/mach/board-pb11mp.h index f0d68e0fea01..7abf918b77e9 100644 --- a/arch/arm/mach-realview/include/mach/board-pb11mp.h +++ b/arch/arm/mach-realview/include/mach/board-pb11mp.h @@ -81,4 +81,16 @@ #define REALVIEW_TC11MP_GIC_DIST_BASE 0x1F001000 /* Test chip interrupt controller distributor */ #define REALVIEW_TC11MP_L220_BASE 0x1F002000 /* L220 registers */ + /* + * Values for REALVIEW_SYS_RESET_CTRL + */ +#define REALVIEW_PB11MP_SYS_CTRL_RESET_CONFIGCLR 0x01 +#define REALVIEW_PB11MP_SYS_CTRL_RESET_CONFIGINIT 0x02 +#define REALVIEW_PB11MP_SYS_CTRL_RESET_DLLRESET 0x03 +#define REALVIEW_PB11MP_SYS_CTRL_RESET_PLLRESET 0x04 +#define REALVIEW_PB11MP_SYS_CTRL_RESET_POR 0x05 +#define REALVIEW_PB11MP_SYS_CTRL_RESET_DoC 0x06 + +#define REALVIEW_PB11MP_SYS_CTRL_LED (1 << 0) + #endif /* __ASM_ARCH_BOARD_PB11MP_H */ diff --git a/arch/arm/mach-realview/include/mach/memory.h b/arch/arm/mach-realview/include/mach/memory.h index 293c30025e7e..2417bbcf97fd 100644 --- a/arch/arm/mach-realview/include/mach/memory.h +++ b/arch/arm/mach-realview/include/mach/memory.h @@ -29,4 +29,53 @@ #define PHYS_OFFSET UL(0x00000000) #endif +#if !defined(__ASSEMBLY__) && defined(CONFIG_ZONE_DMA) +extern void realview_adjust_zones(int node, unsigned long *size, + unsigned long *hole); +#define arch_adjust_zones(node, size, hole) \ + realview_adjust_zones(node, size, hole) + +#define ISA_DMA_THRESHOLD (PHYS_OFFSET + SZ_256M - 1) +#define MAX_DMA_ADDRESS (PAGE_OFFSET + SZ_256M) +#endif + +#ifdef CONFIG_SPARSEMEM + +/* + * Sparsemem definitions for RealView PBX. + * + * The RealView PBX board has another block of 512MB of RAM at 0x20000000, + * however only the block at 0x70000000 (or the 256MB mirror at 0x00000000) + * may be used for DMA. + * + * The macros below define a section size of 256MB and a non-linear virtual to + * physical mapping: + * + * 256MB @ 0x00000000 -> PAGE_OFFSET + * 512MB @ 0x20000000 -> PAGE_OFFSET + 0x10000000 + * 256MB @ 0x80000000 -> PAGE_OFFSET + 0x30000000 + */ +#ifdef CONFIG_REALVIEW_HIGH_PHYS_OFFSET +#error "SPARSEMEM not available with REALVIEW_HIGH_PHYS_OFFSET" +#endif + +#define MAX_PHYSMEM_BITS 32 +#define SECTION_SIZE_BITS 28 + +/* bank page offsets */ +#define PAGE_OFFSET1 (PAGE_OFFSET + 0x10000000) +#define PAGE_OFFSET2 (PAGE_OFFSET + 0x30000000) + +#define __phys_to_virt(phys) \ + ((phys) >= 0x80000000 ? (phys) - 0x80000000 + PAGE_OFFSET2 : \ + (phys) >= 0x20000000 ? (phys) - 0x20000000 + PAGE_OFFSET1 : \ + (phys) + PAGE_OFFSET) + +#define __virt_to_phys(virt) \ + ((virt) >= PAGE_OFFSET2 ? (virt) - PAGE_OFFSET2 + 0x80000000 : \ + (virt) >= PAGE_OFFSET1 ? (virt) - PAGE_OFFSET1 + 0x20000000 : \ + (virt) - PAGE_OFFSET) + +#endif /* CONFIG_SPARSEMEM */ + #endif diff --git a/arch/arm/mach-realview/include/mach/platform.h b/arch/arm/mach-realview/include/mach/platform.h index c8f50835fed2..4f46bf71e752 100644 --- a/arch/arm/mach-realview/include/mach/platform.h +++ b/arch/arm/mach-realview/include/mach/platform.h @@ -119,19 +119,6 @@ #define REALVIEW_SYS_TEST_OSC3 (REALVIEW_SYS_BASE + REALVIEW_SYS_TEST_OSC3_OFFSET) #define REALVIEW_SYS_TEST_OSC4 (REALVIEW_SYS_BASE + REALVIEW_SYS_TEST_OSC4_OFFSET) -/* - * Values for REALVIEW_SYS_RESET_CTRL - */ -#define REALVIEW_SYS_CTRL_RESET_CONFIGCLR 0x01 -#define REALVIEW_SYS_CTRL_RESET_CONFIGINIT 0x02 -#define REALVIEW_SYS_CTRL_RESET_DLLRESET 0x03 -#define REALVIEW_SYS_CTRL_RESET_PLLRESET 0x04 -#define REALVIEW_SYS_CTRL_RESET_POR 0x05 -#define REALVIEW_SYS_CTRL_RESET_DoC 0x06 - -#define REALVIEW_SYS_CTRL_LED (1 << 0) - - /* ------------------------------------------------------------------------ * RealView control registers * ------------------------------------------------------------------------ @@ -153,7 +140,7 @@ * SYS_CLD, SYS_BOOTCS */ #define REALVIEW_SYS_LOCK_LOCKED (1 << 16) -#define REALVIEW_SYS_LOCKVAL_MASK 0xFFFF /* write 0xA05F to enable write access */ +#define REALVIEW_SYS_LOCKVAL_MASK 0xA05F /* Enable write access */ /* * REALVIEW_SYS_FLASH diff --git a/arch/arm/mach-realview/include/mach/system.h b/arch/arm/mach-realview/include/mach/system.h index 1a15a441e027..a30f2e3ec178 100644 --- a/arch/arm/mach-realview/include/mach/system.h +++ b/arch/arm/mach-realview/include/mach/system.h @@ -25,6 +25,8 @@ #include <mach/hardware.h> #include <mach/platform.h> +void (*realview_reset)(char mode); + static inline void arch_idle(void) { /* @@ -36,16 +38,12 @@ static inline void arch_idle(void) static inline void arch_reset(char mode, const char *cmd) { - void __iomem *hdr_ctrl = __io_address(REALVIEW_SYS_BASE) + REALVIEW_SYS_RESETCTL_OFFSET; - unsigned int val; - /* * To reset, we hit the on-board reset register * in the system FPGA */ - val = __raw_readl(hdr_ctrl); - val |= REALVIEW_SYS_CTRL_RESET_CONFIGCLR; - __raw_writel(val, hdr_ctrl); + if (realview_reset) + realview_reset(mode); } #endif diff --git a/arch/arm/mach-realview/platsmp.c b/arch/arm/mach-realview/platsmp.c index a88458b4799d..009265818d55 100644 --- a/arch/arm/mach-realview/platsmp.c +++ b/arch/arm/mach-realview/platsmp.c @@ -146,11 +146,8 @@ static void __init poke_milo(void) * register. The BootMonitor waits for this register to become * non-zero. */ -#define REALVIEW_SYS_FLAGSS_OFFSET 0x30 -#define REALVIEW_SYS_FLAGSC_OFFSET 0x34 __raw_writel(BSYM(virt_to_phys(realview_secondary_startup)), - __io_address(REALVIEW_SYS_BASE) + - REALVIEW_SYS_FLAGSS_OFFSET); + __io_address(REALVIEW_SYS_FLAGSSET)); mb(); } diff --git a/arch/arm/mach-realview/realview_eb.c b/arch/arm/mach-realview/realview_eb.c index 1d65e64ae571..917f8ca3abff 100644 --- a/arch/arm/mach-realview/realview_eb.c +++ b/arch/arm/mach-realview/realview_eb.c @@ -415,6 +415,7 @@ MACHINE_START(REALVIEW_EB, "ARM-RealView EB") .phys_io = REALVIEW_EB_UART0_BASE, .io_pg_offst = (IO_ADDRESS(REALVIEW_EB_UART0_BASE) >> 18) & 0xfffc, .boot_params = PHYS_OFFSET + 0x00000100, + .fixup = realview_fixup, .map_io = realview_eb_map_io, .init_irq = gic_init_irq, .timer = &realview_eb_timer, diff --git a/arch/arm/mach-realview/realview_pb1176.c b/arch/arm/mach-realview/realview_pb1176.c index 2817fe099319..7fb726d5f8b9 100644 --- a/arch/arm/mach-realview/realview_pb1176.c +++ b/arch/arm/mach-realview/realview_pb1176.c @@ -290,6 +290,28 @@ static struct sys_timer realview_pb1176_timer = { .init = realview_pb1176_timer_init, }; +static void realview_pb1176_reset(char mode) +{ + void __iomem *hdr_ctrl = __io_address(REALVIEW_SYS_BASE) + + REALVIEW_SYS_RESETCTL_OFFSET; + void __iomem *rst_hdr_ctrl = __io_address(REALVIEW_SYS_BASE) + + REALVIEW_SYS_LOCK_OFFSET; + __raw_writel(REALVIEW_SYS_LOCKVAL_MASK, rst_hdr_ctrl); + __raw_writel(REALVIEW_PB1176_SYS_LOCKVAL_RSTCTL, hdr_ctrl); +} + +static void realview_pb1176_fixup(struct machine_desc *mdesc, + struct tag *tags, char **from, + struct meminfo *meminfo) +{ + /* + * RealView PB1176 only has 128MB of RAM mapped at 0. + */ + meminfo->bank[0].start = 0; + meminfo->bank[0].size = SZ_128M; + meminfo->nr_banks = 1; +} + static void __init realview_pb1176_init(void) { int i; @@ -313,6 +335,7 @@ static void __init realview_pb1176_init(void) #ifdef CONFIG_LEDS leds_event = realview_leds_event; #endif + realview_reset = realview_pb1176_reset; } MACHINE_START(REALVIEW_PB1176, "ARM-RealView PB1176") @@ -320,6 +343,7 @@ MACHINE_START(REALVIEW_PB1176, "ARM-RealView PB1176") .phys_io = REALVIEW_PB1176_UART0_BASE, .io_pg_offst = (IO_ADDRESS(REALVIEW_PB1176_UART0_BASE) >> 18) & 0xfffc, .boot_params = PHYS_OFFSET + 0x00000100, + .fixup = realview_pb1176_fixup, .map_io = realview_pb1176_map_io, .init_irq = gic_init_irq, .timer = &realview_pb1176_timer, diff --git a/arch/arm/mach-realview/realview_pb11mp.c b/arch/arm/mach-realview/realview_pb11mp.c index 94680fcf726d..9bbbfc05f225 100644 --- a/arch/arm/mach-realview/realview_pb11mp.c +++ b/arch/arm/mach-realview/realview_pb11mp.c @@ -299,6 +299,21 @@ static struct sys_timer realview_pb11mp_timer = { .init = realview_pb11mp_timer_init, }; +static void realview_pb11mp_reset(char mode) +{ + void __iomem *hdr_ctrl = __io_address(REALVIEW_SYS_BASE) + + REALVIEW_SYS_RESETCTL_OFFSET; + unsigned int val; + + /* + * To reset, we hit the on-board reset register + * in the system FPGA + */ + val = __raw_readl(hdr_ctrl); + val |= REALVIEW_PB11MP_SYS_CTRL_RESET_CONFIGCLR; + __raw_writel(val, hdr_ctrl); +} + static void __init realview_pb11mp_init(void) { int i; @@ -324,6 +339,7 @@ static void __init realview_pb11mp_init(void) #ifdef CONFIG_LEDS leds_event = realview_leds_event; #endif + realview_reset = realview_pb11mp_reset; } MACHINE_START(REALVIEW_PB11MP, "ARM-RealView PB11MPCore") @@ -331,6 +347,7 @@ MACHINE_START(REALVIEW_PB11MP, "ARM-RealView PB11MPCore") .phys_io = REALVIEW_PB11MP_UART0_BASE, .io_pg_offst = (IO_ADDRESS(REALVIEW_PB11MP_UART0_BASE) >> 18) & 0xfffc, .boot_params = PHYS_OFFSET + 0x00000100, + .fixup = realview_fixup, .map_io = realview_pb11mp_map_io, .init_irq = gic_init_irq, .timer = &realview_pb11mp_timer, diff --git a/arch/arm/mach-realview/realview_pba8.c b/arch/arm/mach-realview/realview_pba8.c index 941beb2b9709..fe861e96c566 100644 --- a/arch/arm/mach-realview/realview_pba8.c +++ b/arch/arm/mach-realview/realview_pba8.c @@ -298,6 +298,7 @@ MACHINE_START(REALVIEW_PBA8, "ARM-RealView PB-A8") .phys_io = REALVIEW_PBA8_UART0_BASE, .io_pg_offst = (IO_ADDRESS(REALVIEW_PBA8_UART0_BASE) >> 18) & 0xfffc, .boot_params = PHYS_OFFSET + 0x00000100, + .fixup = realview_fixup, .map_io = realview_pba8_map_io, .init_irq = gic_init_irq, .timer = &realview_pba8_timer, diff --git a/arch/arm/mach-realview/realview_pbx.c b/arch/arm/mach-realview/realview_pbx.c index 7e4bc6cdca52..ec39488e2b42 100644 --- a/arch/arm/mach-realview/realview_pbx.c +++ b/arch/arm/mach-realview/realview_pbx.c @@ -304,6 +304,26 @@ static struct sys_timer realview_pbx_timer = { .init = realview_pbx_timer_init, }; +static void realview_pbx_fixup(struct machine_desc *mdesc, struct tag *tags, + char **from, struct meminfo *meminfo) +{ +#ifdef CONFIG_SPARSEMEM + /* + * Memory configuration with SPARSEMEM enabled on RealView PBX (see + * asm/mach/memory.h for more information). + */ + meminfo->bank[0].start = 0; + meminfo->bank[0].size = SZ_256M; + meminfo->bank[1].start = 0x20000000; + meminfo->bank[1].size = SZ_512M; + meminfo->bank[2].start = 0x80000000; + meminfo->bank[2].size = SZ_256M; + meminfo->nr_banks = 3; +#else + realview_fixup(mdesc, tags, from, meminfo); +#endif +} + static void __init realview_pbx_init(void) { int i; @@ -345,6 +365,7 @@ MACHINE_START(REALVIEW_PBX, "ARM-RealView PBX") .phys_io = REALVIEW_PBX_UART0_BASE, .io_pg_offst = (IO_ADDRESS(REALVIEW_PBX_UART0_BASE) >> 18) & 0xfffc, .boot_params = PHYS_OFFSET + 0x00000100, + .fixup = realview_pbx_fixup, .map_io = realview_pbx_map_io, .init_irq = gic_init_irq, .timer = &realview_pbx_timer, diff --git a/arch/arm/mach-s3c2410/gpio.c b/arch/arm/mach-s3c2410/gpio.c index 7974afca297c..9664e011dae2 100644 --- a/arch/arm/mach-s3c2410/gpio.c +++ b/arch/arm/mach-s3c2410/gpio.c @@ -28,6 +28,7 @@ #include <linux/io.h> #include <mach/hardware.h> +#include <mach/gpio-fns.h> #include <asm/irq.h> #include <mach/regs-gpio.h> diff --git a/arch/arm/mach-s3c2410/include/mach/dma.h b/arch/arm/mach-s3c2410/include/mach/dma.h index c3a2629e0ded..92e2687009ea 100644 --- a/arch/arm/mach-s3c2410/include/mach/dma.h +++ b/arch/arm/mach-s3c2410/include/mach/dma.h @@ -110,6 +110,8 @@ enum s3c2410_dma_loadst { * waiting for reloads */ #define S3C2410_DMAF_AUTOSTART (1<<1) /* auto-start if buffer queued */ +#define S3C2410_DMAF_CIRCULAR (1 << 2) /* no circular dma support */ + /* dma buffer */ struct s3c2410_dma_buf; @@ -194,4 +196,9 @@ struct s3c2410_dma_chan { typedef unsigned long dma_device_t; +static inline bool s3c_dma_has_circular(void) +{ + return false; +} + #endif /* __ASM_ARCH_DMA_H */ diff --git a/arch/arm/mach-s3c2440/Kconfig b/arch/arm/mach-s3c2440/Kconfig index d7bba919a77e..a8b69d77571b 100644 --- a/arch/arm/mach-s3c2440/Kconfig +++ b/arch/arm/mach-s3c2440/Kconfig @@ -103,6 +103,7 @@ config MACH_MINI2440 select LEDS_TRIGGER_BACKLIGHT select SND_S3C24XX_SOC_S3C24XX_UDA134X select S3C_DEV_NAND + select S3C_DEV_USB_HOST help Say Y here to select support for the MINI2440. Is a 10cm x 10cm board available via various sources. It can come with a 3.5" or 7" touch LCD. diff --git a/arch/arm/mach-s3c2440/mach-mini2440.c b/arch/arm/mach-s3c2440/mach-mini2440.c index ec71a6965786..1c3382fefdd2 100644 --- a/arch/arm/mach-s3c2440/mach-mini2440.c +++ b/arch/arm/mach-s3c2440/mach-mini2440.c @@ -144,7 +144,7 @@ static struct s3c2410_udc_mach_info mini2440_udc_cfg __initdata = { .type = (S3C2410_LCDCON1_TFT16BPP |\ S3C2410_LCDCON1_TFT) -struct s3c2410fb_display mini2440_lcd_cfg[] __initdata = { +static struct s3c2410fb_display mini2440_lcd_cfg[] __initdata = { [0] = { /* mini2440 + 3.5" TFT + touchscreen */ _LCD_DECLARE( 7, /* The 3.5 is quite fast */ @@ -191,7 +191,7 @@ struct s3c2410fb_display mini2440_lcd_cfg[] __initdata = { #define S3C2410_GPCCON_MASK(x) (3 << ((x) * 2)) #define S3C2410_GPDCON_MASK(x) (3 << ((x) * 2)) -struct s3c2410fb_mach_info mini2440_fb_info __initdata = { +static struct s3c2410fb_mach_info mini2440_fb_info __initdata = { .displays = &mini2440_lcd_cfg[0], /* not constant! see init */ .num_displays = 1, .default_display = 0, diff --git a/arch/arm/mach-s3c6400/include/mach/dma.h b/arch/arm/mach-s3c6400/include/mach/dma.h index 1067619f0ba0..6723860748be 100644 --- a/arch/arm/mach-s3c6400/include/mach/dma.h +++ b/arch/arm/mach-s3c6400/include/mach/dma.h @@ -58,12 +58,9 @@ enum dma_ch { DMACH_MAX /* the end */ }; -static __inline__ int s3c_dma_has_circular(void) +static __inline__ bool s3c_dma_has_circular(void) { - /* we will be supporting ciruclar buffers as soon as we have DMA - * engine support. - */ - return 1; + return true; } #define S3C2410_DMAF_CIRCULAR (1 << 0) diff --git a/arch/arm/mach-s3c6410/Kconfig b/arch/arm/mach-s3c6410/Kconfig index 53fc3ff657f7..72d4b11b2077 100644 --- a/arch/arm/mach-s3c6410/Kconfig +++ b/arch/arm/mach-s3c6410/Kconfig @@ -77,6 +77,7 @@ config SMDK6410_WM1190_EV1 depends on MACH_SMDK6410 select REGULATOR select REGULATOR_WM8350 + select S3C24XX_GPIO_EXTRA64 select MFD_WM8350_I2C select MFD_WM8350_CONFIG_MODE_0 select MFD_WM8350_CONFIG_MODE_3 diff --git a/arch/arm/mach-s3c6410/mach-smdk6410.c b/arch/arm/mach-s3c6410/mach-smdk6410.c index ea51dbe76e3e..9f1a21462620 100644 --- a/arch/arm/mach-s3c6410/mach-smdk6410.c +++ b/arch/arm/mach-s3c6410/mach-smdk6410.c @@ -320,6 +320,9 @@ static int __init smdk6410_wm8350_init(struct wm8350 *wm8350) { int i; + /* Configure the IRQ line */ + s3c_gpio_setpull(S3C64XX_GPN(12), S3C_GPIO_PULL_UP); + /* Instantiate the regulators */ for (i = 0; i < ARRAY_SIZE(wm1190_regulators); i++) wm8350_register_regulator(wm8350, diff --git a/arch/arm/mach-sa1100/Makefile b/arch/arm/mach-sa1100/Makefile index 8a5546e6d547..bb7b8198d0c4 100644 --- a/arch/arm/mach-sa1100/Makefile +++ b/arch/arm/mach-sa1100/Makefile @@ -25,6 +25,7 @@ led-$(CONFIG_SA1100_CERF) += leds-cerf.o obj-$(CONFIG_SA1100_COLLIE) += collie.o +obj-$(CONFIG_SA1100_H3100) += h3600.o obj-$(CONFIG_SA1100_H3600) += h3600.o obj-$(CONFIG_SA1100_HACKKIT) += hackkit.o diff --git a/arch/arm/mach-u300/core.c b/arch/arm/mach-u300/core.c index be60d6deee8b..653e25be3dd8 100644 --- a/arch/arm/mach-u300/core.c +++ b/arch/arm/mach-u300/core.c @@ -408,7 +408,7 @@ static struct platform_device keypad_device = { }; static struct platform_device rtc_device = { - .name = "rtc0", + .name = "rtc-coh901331", .id = -1, .num_resources = ARRAY_SIZE(rtc_resources), .resource = rtc_resources, diff --git a/arch/arm/mm/Kconfig b/arch/arm/mm/Kconfig index e993140edd88..9264d814cd7a 100644 --- a/arch/arm/mm/Kconfig +++ b/arch/arm/mm/Kconfig @@ -122,10 +122,7 @@ config CPU_ARM920T select CPU_TLB_V4WBI if MMU help The ARM920T is licensed to be produced by numerous vendors, - and is used in the Maverick EP9312 and the Samsung S3C2410. - - More information on the Maverick EP9312 at - <http://linuxdevices.com/products/PD2382866068.html>. + and is used in the Cirrus EP93xx and the Samsung S3C2410. Say Y if you want support for the ARM920T processor. Otherwise, say N. diff --git a/arch/arm/mm/cache-v6.S b/arch/arm/mm/cache-v6.S index 8f5c13f4c936..295e25dd6381 100644 --- a/arch/arm/mm/cache-v6.S +++ b/arch/arm/mm/cache-v6.S @@ -12,6 +12,7 @@ #include <linux/linkage.h> #include <linux/init.h> #include <asm/assembler.h> +#include <asm/unwind.h> #include "proc-macros.S" @@ -121,11 +122,13 @@ ENTRY(v6_coherent_kern_range) * - the Icache does not read data from the write buffer */ ENTRY(v6_coherent_user_range) - + UNWIND(.fnstart ) #ifdef HARVARD_CACHE bic r0, r0, #CACHE_LINE_SIZE - 1 -1: mcr p15, 0, r0, c7, c10, 1 @ clean D line +1: + USER( mcr p15, 0, r0, c7, c10, 1 ) @ clean D line add r0, r0, #CACHE_LINE_SIZE +2: cmp r0, r1 blo 1b #endif @@ -143,6 +146,19 @@ ENTRY(v6_coherent_user_range) mov pc, lr /* + * Fault handling for the cache operation above. If the virtual address in r0 + * isn't mapped, just try the next page. + */ +9001: + mov r0, r0, lsr #12 + mov r0, r0, lsl #12 + add r0, r0, #4096 + b 2b + UNWIND(.fnend ) +ENDPROC(v6_coherent_user_range) +ENDPROC(v6_coherent_kern_range) + +/* * v6_flush_kern_dcache_page(kaddr) * * Ensure that the data held in the page kaddr is written back diff --git a/arch/arm/mm/cache-v7.S b/arch/arm/mm/cache-v7.S index bda0ec31a4e2..e1bd9759617f 100644 --- a/arch/arm/mm/cache-v7.S +++ b/arch/arm/mm/cache-v7.S @@ -13,6 +13,7 @@ #include <linux/linkage.h> #include <linux/init.h> #include <asm/assembler.h> +#include <asm/unwind.h> #include "proc-macros.S" @@ -153,13 +154,16 @@ ENTRY(v7_coherent_kern_range) * - the Icache does not read data from the write buffer */ ENTRY(v7_coherent_user_range) + UNWIND(.fnstart ) dcache_line_size r2, r3 sub r3, r2, #1 bic r0, r0, r3 -1: mcr p15, 0, r0, c7, c11, 1 @ clean D line to the point of unification +1: + USER( mcr p15, 0, r0, c7, c11, 1 ) @ clean D line to the point of unification dsb - mcr p15, 0, r0, c7, c5, 1 @ invalidate I line + USER( mcr p15, 0, r0, c7, c5, 1 ) @ invalidate I line add r0, r0, r2 +2: cmp r0, r1 blo 1b mov r0, #0 @@ -167,6 +171,17 @@ ENTRY(v7_coherent_user_range) dsb isb mov pc, lr + +/* + * Fault handling for the cache operation above. If the virtual address in r0 + * isn't mapped, just try the next page. + */ +9001: + mov r0, r0, lsr #12 + mov r0, r0, lsl #12 + add r0, r0, #4096 + b 2b + UNWIND(.fnend ) ENDPROC(v7_coherent_kern_range) ENDPROC(v7_coherent_user_range) diff --git a/arch/arm/mm/context.c b/arch/arm/mm/context.c index 6bda76a43199..a9e22e31eaa1 100644 --- a/arch/arm/mm/context.c +++ b/arch/arm/mm/context.c @@ -50,10 +50,7 @@ void __new_context(struct mm_struct *mm) isb(); flush_tlb_all(); if (icache_is_vivt_asid_tagged()) { - asm("mcr p15, 0, %0, c7, c5, 0 @ invalidate I-cache\n" - "mcr p15, 0, %0, c7, c5, 6 @ flush BTAC/BTB\n" - : - : "r" (0)); + __flush_icache_all(); dsb(); } } diff --git a/arch/arm/mm/dma-mapping.c b/arch/arm/mm/dma-mapping.c index b30925fcbcdc..b9590a7085ca 100644 --- a/arch/arm/mm/dma-mapping.c +++ b/arch/arm/mm/dma-mapping.c @@ -205,7 +205,7 @@ __dma_alloc(struct device *dev, size_t size, dma_addr_t *handle, gfp_t gfp, order = get_order(size); - if (mask != 0xffffffff) + if (mask < 0xffffffffULL) gfp |= GFP_DMA; page = alloc_pages(gfp, order); @@ -289,7 +289,7 @@ __dma_alloc(struct device *dev, size_t size, dma_addr_t *handle, gfp_t gfp, if (!mask) goto error; - if (mask != 0xffffffff) + if (mask < 0xffffffffULL) gfp |= GFP_DMA; virt = kmalloc(size, gfp); if (!virt) diff --git a/arch/arm/mm/fault-armv.c b/arch/arm/mm/fault-armv.c index bc0099d5ae85..d0d17b6a3703 100644 --- a/arch/arm/mm/fault-armv.c +++ b/arch/arm/mm/fault-armv.c @@ -153,14 +153,11 @@ void update_mmu_cache(struct vm_area_struct *vma, unsigned long addr, pte_t pte) page = pfn_to_page(pfn); mapping = page_mapping(page); - if (mapping) { #ifndef CONFIG_SMP - int dirty = test_and_clear_bit(PG_dcache_dirty, &page->flags); - - if (dirty) - __flush_dcache_page(mapping, page); + if (test_and_clear_bit(PG_dcache_dirty, &page->flags)) + __flush_dcache_page(mapping, page); #endif - + if (mapping) { if (cache_is_vivt()) make_coherent(mapping, vma, addr, pfn); else if (vma->vm_flags & VM_EXEC) diff --git a/arch/arm/mm/fault.c b/arch/arm/mm/fault.c index ae0e25f5a70e..10e06801afb3 100644 --- a/arch/arm/mm/fault.c +++ b/arch/arm/mm/fault.c @@ -292,6 +292,11 @@ do_page_fault(unsigned long addr, unsigned int fsr, struct pt_regs *regs) * down_read() */ might_sleep(); +#ifdef CONFIG_DEBUG_VM + if (!user_mode(regs) && + !search_exception_tables(regs->ARM_pc)) + goto no_context; +#endif } fault = __do_page_fault(mm, addr, fsr, tsk); diff --git a/arch/arm/mm/flush.c b/arch/arm/mm/flush.c index b27942909b23..7f294f307c83 100644 --- a/arch/arm/mm/flush.c +++ b/arch/arm/mm/flush.c @@ -18,10 +18,6 @@ #include "mm.h" -#ifdef CONFIG_ARM_ERRATA_411920 -extern void v6_icache_inval_all(void); -#endif - #ifdef CONFIG_CPU_CACHE_VIPT #define ALIAS_FLUSH_START 0xffff4000 @@ -35,16 +31,11 @@ static void flush_pfn_alias(unsigned long pfn, unsigned long vaddr) flush_tlb_kernel_page(to); asm( "mcrr p15, 0, %1, %0, c14\n" - " mcr p15, 0, %2, c7, c10, 4\n" -#ifndef CONFIG_ARM_ERRATA_411920 - " mcr p15, 0, %2, c7, c5, 0\n" -#endif + " mcr p15, 0, %2, c7, c10, 4" : : "r" (to), "r" (to + PAGE_SIZE - L1_CACHE_BYTES), "r" (zero) : "cc"); -#ifdef CONFIG_ARM_ERRATA_411920 - v6_icache_inval_all(); -#endif + __flush_icache_all(); } void flush_cache_mm(struct mm_struct *mm) @@ -57,16 +48,11 @@ void flush_cache_mm(struct mm_struct *mm) if (cache_is_vipt_aliasing()) { asm( "mcr p15, 0, %0, c7, c14, 0\n" - " mcr p15, 0, %0, c7, c10, 4\n" -#ifndef CONFIG_ARM_ERRATA_411920 - " mcr p15, 0, %0, c7, c5, 0\n" -#endif + " mcr p15, 0, %0, c7, c10, 4" : : "r" (0) : "cc"); -#ifdef CONFIG_ARM_ERRATA_411920 - v6_icache_inval_all(); -#endif + __flush_icache_all(); } } @@ -81,16 +67,11 @@ void flush_cache_range(struct vm_area_struct *vma, unsigned long start, unsigned if (cache_is_vipt_aliasing()) { asm( "mcr p15, 0, %0, c7, c14, 0\n" - " mcr p15, 0, %0, c7, c10, 4\n" -#ifndef CONFIG_ARM_ERRATA_411920 - " mcr p15, 0, %0, c7, c5, 0\n" -#endif + " mcr p15, 0, %0, c7, c10, 4" : : "r" (0) : "cc"); -#ifdef CONFIG_ARM_ERRATA_411920 - v6_icache_inval_all(); -#endif + __flush_icache_all(); } } diff --git a/arch/arm/mm/highmem.c b/arch/arm/mm/highmem.c index 73cae57fa707..30f82fb5918c 100644 --- a/arch/arm/mm/highmem.c +++ b/arch/arm/mm/highmem.c @@ -46,6 +46,8 @@ void *kmap_atomic(struct page *page, enum km_type type) if (!PageHighMem(page)) return page_address(page); + debug_kmap_atomic(type); + kmap = kmap_high_get(page); if (kmap) return kmap; diff --git a/arch/arm/mm/init.c b/arch/arm/mm/init.c index 877c492f8e10..52c40d155672 100644 --- a/arch/arm/mm/init.c +++ b/arch/arm/mm/init.c @@ -273,7 +273,6 @@ static void __init bootmem_init_node(int node, struct meminfo *mi, struct membank *bank = &mi->bank[i]; if (!bank->highmem) free_bootmem_node(pgdat, bank_phys_start(bank), bank_phys_size(bank)); - memory_present(node, bank_pfn_start(bank), bank_pfn_end(bank)); } /* @@ -370,6 +369,19 @@ int pfn_valid(unsigned long pfn) return 0; } EXPORT_SYMBOL(pfn_valid); + +static void arm_memory_present(struct meminfo *mi, int node) +{ +} +#else +static void arm_memory_present(struct meminfo *mi, int node) +{ + int i; + for_each_nodebank(i, mi, node) { + struct membank *bank = &mi->bank[i]; + memory_present(node, bank_pfn_start(bank), bank_pfn_end(bank)); + } +} #endif static int __init meminfo_cmp(const void *_a, const void *_b) @@ -427,6 +439,12 @@ void __init bootmem_init(void) */ if (node == initrd_node) bootmem_reserve_initrd(node); + + /* + * Sparsemem tries to allocate bootmem in memory_present(), + * so must be done after the fixed reservations + */ + arm_memory_present(mi, node); } /* @@ -483,7 +501,7 @@ free_memmap(int node, unsigned long start_pfn, unsigned long end_pfn) /* * Convert start_pfn/end_pfn to a struct page pointer. */ - start_pg = pfn_to_page(start_pfn); + start_pg = pfn_to_page(start_pfn - 1) + 1; end_pg = pfn_to_page(end_pfn); /* diff --git a/arch/arm/mm/mmu.c b/arch/arm/mm/mmu.c index 02243eeccf50..ea67be0223ac 100644 --- a/arch/arm/mm/mmu.c +++ b/arch/arm/mm/mmu.c @@ -117,6 +117,13 @@ static void __init early_cachepolicy(char **p) } if (i == ARRAY_SIZE(cache_policies)) printk(KERN_ERR "ERROR: unknown or unsupported cache policy\n"); + /* + * This restriction is partly to do with the way we boot; it is + * unpredictable to have memory mapped using two different sets of + * memory attributes (shared, type, and cache attribs). We can not + * change these attributes once the initial assembly has setup the + * page tables. + */ if (cpu_architecture() >= CPU_ARCH_ARMv6) { printk(KERN_WARNING "Only cachepolicy=writeback supported on ARMv6 and later\n"); cachepolicy = CPOLICY_WRITEBACK; diff --git a/arch/arm/mm/proc-v6.S b/arch/arm/mm/proc-v6.S index 194737d60a22..70f75d2e3ead 100644 --- a/arch/arm/mm/proc-v6.S +++ b/arch/arm/mm/proc-v6.S @@ -32,8 +32,10 @@ #ifndef CONFIG_SMP #define TTB_FLAGS TTB_RGN_WBWA +#define PMD_FLAGS PMD_SECT_WB #else #define TTB_FLAGS TTB_RGN_WBWA|TTB_S +#define PMD_FLAGS PMD_SECT_WBWA|PMD_SECT_S #endif ENTRY(cpu_v6_proc_init) @@ -222,10 +224,9 @@ __v6_proc_info: .long 0x0007b000 .long 0x0007f000 .long PMD_TYPE_SECT | \ - PMD_SECT_BUFFERABLE | \ - PMD_SECT_CACHEABLE | \ PMD_SECT_AP_WRITE | \ - PMD_SECT_AP_READ + PMD_SECT_AP_READ | \ + PMD_FLAGS .long PMD_TYPE_SECT | \ PMD_SECT_XN | \ PMD_SECT_AP_WRITE | \ diff --git a/arch/arm/mm/proc-v7.S b/arch/arm/mm/proc-v7.S index 23ebcf6eab9f..3a285218fd15 100644 --- a/arch/arm/mm/proc-v7.S +++ b/arch/arm/mm/proc-v7.S @@ -33,9 +33,11 @@ #ifndef CONFIG_SMP /* PTWs cacheable, inner WB not shareable, outer WB not shareable */ #define TTB_FLAGS TTB_IRGN_WB|TTB_RGN_OC_WB +#define PMD_FLAGS PMD_SECT_WB #else /* PTWs cacheable, inner WBWA shareable, outer WBWA not shareable */ #define TTB_FLAGS TTB_IRGN_WBWA|TTB_S|TTB_NOS|TTB_RGN_OC_WBWA +#define PMD_FLAGS PMD_SECT_WBWA|PMD_SECT_S #endif ENTRY(cpu_v7_proc_init) @@ -184,9 +186,10 @@ cpu_v7_name: */ __v7_setup: #ifdef CONFIG_SMP - mrc p15, 0, r0, c1, c0, 1 @ Enable SMP/nAMP mode and - orr r0, r0, #(1 << 6) | (1 << 0) @ TLB ops broadcasting - mcr p15, 0, r0, c1, c0, 1 + mrc p15, 0, r0, c1, c0, 1 + tst r0, #(1 << 6) @ SMP/nAMP mode enabled? + orreq r0, r0, #(1 << 6) | (1 << 0) @ Enable SMP/nAMP mode and + mcreq p15, 0, r0, c1, c0, 1 @ TLB ops broadcasting #endif adr r12, __v7_setup_stack @ the local stack stmia r12, {r0-r5, r7, r9, r11, lr} @@ -326,10 +329,9 @@ __v7_proc_info: .long 0x000f0000 @ Required ID value .long 0x000f0000 @ Mask for ID .long PMD_TYPE_SECT | \ - PMD_SECT_BUFFERABLE | \ - PMD_SECT_CACHEABLE | \ PMD_SECT_AP_WRITE | \ - PMD_SECT_AP_READ + PMD_SECT_AP_READ | \ + PMD_FLAGS .long PMD_TYPE_SECT | \ PMD_SECT_XN | \ PMD_SECT_AP_WRITE | \ diff --git a/arch/arm/oprofile/op_model_v6.c b/arch/arm/oprofile/op_model_v6.c index fe581383d3e2..f7d2ec5ee9a1 100644 --- a/arch/arm/oprofile/op_model_v6.c +++ b/arch/arm/oprofile/op_model_v6.c @@ -33,6 +33,9 @@ static int irqs[] = { #ifdef CONFIG_ARCH_OMAP2 3, #endif +#ifdef CONFIG_ARCH_BCMRING + IRQ_PMUIRQ, /* for BCMRING, ARM PMU interrupt is 43 */ +#endif }; static void armv6_pmu_stop(void) diff --git a/arch/arm/plat-omap/cpu-omap.c b/arch/arm/plat-omap/cpu-omap.c index 1868c0d8f9b5..341235c278ac 100644 --- a/arch/arm/plat-omap/cpu-omap.c +++ b/arch/arm/plat-omap/cpu-omap.c @@ -127,7 +127,7 @@ static int __init omap_cpu_init(struct cpufreq_policy *policy) } /* FIXME: what's the actual transition time? */ - policy->cpuinfo.transition_latency = 10 * 1000 * 1000; + policy->cpuinfo.transition_latency = 300 * 1000; return 0; } diff --git a/arch/arm/plat-omap/dma.c b/arch/arm/plat-omap/dma.c index fd3154ae69b1..68eaae324b6a 100644 --- a/arch/arm/plat-omap/dma.c +++ b/arch/arm/plat-omap/dma.c @@ -691,13 +691,16 @@ static inline void disable_lnk(int lch) static inline void omap2_enable_irq_lch(int lch) { u32 val; + unsigned long flags; if (!cpu_class_is_omap2()) return; + spin_lock_irqsave(&dma_chan_lock, flags); val = dma_read(IRQENABLE_L0); val |= 1 << lch; dma_write(val, IRQENABLE_L0); + spin_unlock_irqrestore(&dma_chan_lock, flags); } int omap_request_dma(int dev_id, const char *dev_name, @@ -799,10 +802,13 @@ void omap_free_dma(int lch) if (cpu_class_is_omap2()) { u32 val; + + spin_lock_irqsave(&dma_chan_lock, flags); /* Disable interrupts */ val = dma_read(IRQENABLE_L0); val &= ~(1 << lch); dma_write(val, IRQENABLE_L0); + spin_unlock_irqrestore(&dma_chan_lock, flags); /* Clear the CSR register and IRQ status register */ dma_write(OMAP2_DMA_CSR_CLEAR_MASK, CSR(lch)); @@ -829,10 +835,10 @@ EXPORT_SYMBOL(omap_free_dma); * * @param arb_rate * @param max_fifo_depth - * @param tparams - Number of thereads to reserve : DMA_THREAD_RESERVE_NORM - * DMA_THREAD_RESERVE_ONET - * DMA_THREAD_RESERVE_TWOT - * DMA_THREAD_RESERVE_THREET + * @param tparams - Number of threads to reserve : DMA_THREAD_RESERVE_NORM + * DMA_THREAD_RESERVE_ONET + * DMA_THREAD_RESERVE_TWOT + * DMA_THREAD_RESERVE_THREET */ void omap_dma_set_global_params(int arb_rate, int max_fifo_depth, int tparams) @@ -844,11 +850,14 @@ omap_dma_set_global_params(int arb_rate, int max_fifo_depth, int tparams) return; } + if (max_fifo_depth == 0) + max_fifo_depth = 1; if (arb_rate == 0) arb_rate = 1; - reg = (arb_rate & 0xff) << 16; - reg |= (0xff & max_fifo_depth); + reg = 0xff & max_fifo_depth; + reg |= (0x3 & tparams) << 12; + reg |= (arb_rate & 0xff) << 16; dma_write(reg, GCR); } @@ -975,6 +984,14 @@ void omap_stop_dma(int lch) { u32 l; + /* Disable all interrupts on the channel */ + if (cpu_class_is_omap1()) + dma_write(0, CICR(lch)); + + l = dma_read(CCR(lch)); + l &= ~OMAP_DMA_CCR_EN; + dma_write(l, CCR(lch)); + if (!omap_dma_in_1510_mode() && dma_chan[lch].next_lch != -1) { int next_lch, cur_lch = lch; char dma_chan_link_map[OMAP_DMA4_LOGICAL_DMA_CH_COUNT]; @@ -992,18 +1009,8 @@ void omap_stop_dma(int lch) next_lch = dma_chan[cur_lch].next_lch; cur_lch = next_lch; } while (next_lch != -1); - - return; } - /* Disable all interrupts on the channel */ - if (cpu_class_is_omap1()) - dma_write(0, CICR(lch)); - - l = dma_read(CCR(lch)); - l &= ~OMAP_DMA_CCR_EN; - dma_write(l, CCR(lch)); - dma_chan[lch].flags &= ~OMAP_DMA_ACTIVE; } EXPORT_SYMBOL(omap_stop_dma); @@ -1107,6 +1114,14 @@ int omap_dma_running(void) { int lch; + /* + * On OMAP1510, internal LCD controller will start the transfer + * when it gets enabled, so assume DMA running if LCD enabled. + */ + if (cpu_is_omap1510()) + if (omap_readw(0xfffec000 + 0x00) & (1 << 0)) + return 1; + /* Check if LCD DMA is running */ if (cpu_is_omap16xx()) if (omap_readw(OMAP1610_DMA_LCD_CCR) & OMAP_DMA_CCR_EN) diff --git a/arch/arm/plat-omap/gpio.c b/arch/arm/plat-omap/gpio.c index 71ebd7fcfea1..7c345b757df1 100644 --- a/arch/arm/plat-omap/gpio.c +++ b/arch/arm/plat-omap/gpio.c @@ -373,7 +373,7 @@ static inline int gpio_valid(int gpio) static int check_gpio(int gpio) { - if (unlikely(gpio_valid(gpio)) < 0) { + if (unlikely(gpio_valid(gpio) < 0)) { printk(KERN_ERR "omap-gpio: invalid GPIO %d\n", gpio); dump_stack(); return -1; diff --git a/arch/arm/plat-omap/include/mach/cpu.h b/arch/arm/plat-omap/include/mach/cpu.h index 11e73d9e8928..f129efb3075e 100644 --- a/arch/arm/plat-omap/include/mach/cpu.h +++ b/arch/arm/plat-omap/include/mach/cpu.h @@ -303,32 +303,21 @@ IS_OMAP_TYPE(3430, 0x3430) #define cpu_is_omap2430() 0 #define cpu_is_omap3430() 0 -#if defined(MULTI_OMAP1) -# if defined(CONFIG_ARCH_OMAP730) -# undef cpu_is_omap730 -# define cpu_is_omap730() is_omap730() -# endif -# if defined(CONFIG_ARCH_OMAP850) -# undef cpu_is_omap850 -# define cpu_is_omap850() is_omap850() -# endif -#else -# if defined(CONFIG_ARCH_OMAP730) -# undef cpu_is_omap730 -# define cpu_is_omap730() 1 -# endif -#endif -#else -# if defined(CONFIG_ARCH_OMAP850) -# undef cpu_is_omap850 -# define cpu_is_omap850() 1 -# endif -#endif - /* * Whether we have MULTI_OMAP1 or not, we still need to distinguish - * between 330 vs. 1510 and 1611B/5912 vs. 1710. + * between 730 vs 850, 330 vs. 1510 and 1611B/5912 vs. 1710. */ + +#if defined(CONFIG_ARCH_OMAP730) +# undef cpu_is_omap730 +# define cpu_is_omap730() is_omap730() +#endif + +#if defined(CONFIG_ARCH_OMAP850) +# undef cpu_is_omap850 +# define cpu_is_omap850() is_omap850() +#endif + #if defined(CONFIG_ARCH_OMAP15XX) # undef cpu_is_omap310 # undef cpu_is_omap1510 @@ -433,3 +422,5 @@ IS_OMAP_TYPE(3430, 0x3430) int omap_chip_is(struct omap_chip_id oci); void omap2_check_revision(void); + +#endif diff --git a/arch/arm/plat-omap/include/mach/keypad.h b/arch/arm/plat-omap/include/mach/keypad.h index d91b9be334ff..3ae52ccc793c 100644 --- a/arch/arm/plat-omap/include/mach/keypad.h +++ b/arch/arm/plat-omap/include/mach/keypad.h @@ -10,7 +10,7 @@ #ifndef ASMARM_ARCH_KEYPAD_H #define ASMARM_ARCH_KEYPAD_H -#include <linux/input/matrix_keypad.h> +#warning: Please update the board to use matrix_keypad.h instead struct omap_kp_platform_data { int rows; @@ -37,6 +37,9 @@ struct omap_kp_platform_data { #define KEY_PERSISTENT 0x00800000 #define KEYNUM_MASK 0x00EFFFFF +#define KEY(col, row, val) (((col) << 28) | ((row) << 24) | (val)) +#define PERSISTENT_KEY(col, row) (((col) << 28) | ((row) << 24) | \ + KEY_PERSISTENT) #endif diff --git a/arch/arm/plat-omap/include/mach/powerdomain.h b/arch/arm/plat-omap/include/mach/powerdomain.h index 6271d8556a40..fa6461423bd0 100644 --- a/arch/arm/plat-omap/include/mach/powerdomain.h +++ b/arch/arm/plat-omap/include/mach/powerdomain.h @@ -135,6 +135,8 @@ struct powerdomain *pwrdm_lookup(const char *name); int pwrdm_for_each(int (*fn)(struct powerdomain *pwrdm, void *user), void *user); +int pwrdm_for_each_nolock(int (*fn)(struct powerdomain *pwrdm, void *user), + void *user); int pwrdm_add_clkdm(struct powerdomain *pwrdm, struct clockdomain *clkdm); int pwrdm_del_clkdm(struct powerdomain *pwrdm, struct clockdomain *clkdm); diff --git a/arch/arm/plat-omap/iommu.c b/arch/arm/plat-omap/iommu.c index 4b6012707307..94584f167a82 100644 --- a/arch/arm/plat-omap/iommu.c +++ b/arch/arm/plat-omap/iommu.c @@ -664,7 +664,7 @@ static size_t iopgtable_clear_entry_core(struct iommu *obj, u32 da) nent = 1; /* for the next L1 entry */ } else { bytes = IOPGD_SIZE; - if (*iopgd & IOPGD_SUPER) { + if ((*iopgd & IOPGD_SUPER) == IOPGD_SUPER) { nent *= 16; /* rewind to the 1st entry */ iopgd = (u32 *)((u32)iopgd & IOSUPER_MASK); diff --git a/arch/arm/plat-omap/iovmm.c b/arch/arm/plat-omap/iovmm.c index 57f7122a0919..dc3fac3dd0ea 100644 --- a/arch/arm/plat-omap/iovmm.c +++ b/arch/arm/plat-omap/iovmm.c @@ -47,7 +47,7 @@ * 'va': mpu virtual address * * 'c': contiguous memory area - * 'd': dicontiguous memory area + * 'd': discontiguous memory area * 'a': anonymous memory allocation * '()': optional feature * @@ -363,8 +363,9 @@ void *da_to_va(struct iommu *obj, u32 da) goto out; } va = area->va; - mutex_unlock(&obj->mmap_lock); out: + mutex_unlock(&obj->mmap_lock); + return va; } EXPORT_SYMBOL_GPL(da_to_va); @@ -398,7 +399,7 @@ static inline void sgtable_drain_vmalloc(struct sg_table *sgt) { /* * Actually this is not necessary at all, just exists for - * consistency of the code readibility. + * consistency of the code readability. */ BUG_ON(!sgt); } @@ -434,7 +435,7 @@ static inline void sgtable_drain_kmalloc(struct sg_table *sgt) { /* * Actually this is not necessary at all, just exists for - * consistency of the code readibility + * consistency of the code readability */ BUG_ON(!sgt); } diff --git a/arch/arm/plat-omap/mcbsp.c b/arch/arm/plat-omap/mcbsp.c index 88ac9768f1c1..e664b912d7bb 100644 --- a/arch/arm/plat-omap/mcbsp.c +++ b/arch/arm/plat-omap/mcbsp.c @@ -595,7 +595,7 @@ void omap_mcbsp_stop(unsigned int id, int tx, int rx) rx &= 1; if (cpu_is_omap2430() || cpu_is_omap34xx()) { w = OMAP_MCBSP_READ(io_base, RCCR); - w |= (tx ? RDISABLE : 0); + w |= (rx ? RDISABLE : 0); OMAP_MCBSP_WRITE(io_base, RCCR, w); } w = OMAP_MCBSP_READ(io_base, SPCR1); diff --git a/arch/arm/plat-omap/sram.c b/arch/arm/plat-omap/sram.c index 925f64711c37..75d1f26e5b17 100644 --- a/arch/arm/plat-omap/sram.c +++ b/arch/arm/plat-omap/sram.c @@ -270,7 +270,8 @@ void * omap_sram_push(void * start, unsigned long size) omap_sram_ceil -= size; omap_sram_ceil = ROUND_DOWN(omap_sram_ceil, sizeof(void *)); memcpy((void *)omap_sram_ceil, start, size); - flush_icache_range((unsigned long)start, (unsigned long)(start + size)); + flush_icache_range((unsigned long)omap_sram_ceil, + (unsigned long)(omap_sram_ceil + size)); return (void *)omap_sram_ceil; } diff --git a/arch/arm/plat-pxa/include/plat/mfp.h b/arch/arm/plat-pxa/include/plat/mfp.h index 22086e696e8e..857a6839071c 100644 --- a/arch/arm/plat-pxa/include/plat/mfp.h +++ b/arch/arm/plat-pxa/include/plat/mfp.h @@ -16,7 +16,7 @@ #ifndef __ASM_PLAT_MFP_H #define __ASM_PLAT_MFP_H -#define mfp_to_gpio(m) ((m) % 128) +#define mfp_to_gpio(m) ((m) % 256) /* list of all the configurable MFP pins */ enum { diff --git a/arch/arm/plat-pxa/mfp.c b/arch/arm/plat-pxa/mfp.c index 9405d0379c85..be58f9fe65b0 100644 --- a/arch/arm/plat-pxa/mfp.c +++ b/arch/arm/plat-pxa/mfp.c @@ -207,7 +207,7 @@ unsigned long mfp_read(int mfp) { unsigned long val, flags; - BUG_ON(mfp >= MFP_PIN_MAX); + BUG_ON(mfp < 0 || mfp >= MFP_PIN_MAX); spin_lock_irqsave(&mfp_spin_lock, flags); val = mfpr_readl(mfp_table[mfp].mfpr_off); @@ -220,7 +220,7 @@ void mfp_write(int mfp, unsigned long val) { unsigned long flags; - BUG_ON(mfp >= MFP_PIN_MAX); + BUG_ON(mfp < 0 || mfp >= MFP_PIN_MAX); spin_lock_irqsave(&mfp_spin_lock, flags); mfpr_writel(mfp_table[mfp].mfpr_off, val); diff --git a/arch/arm/plat-s3c24xx/adc.c b/arch/arm/plat-s3c24xx/adc.c index 11117a7ba911..df47322492d5 100644 --- a/arch/arm/plat-s3c24xx/adc.c +++ b/arch/arm/plat-s3c24xx/adc.c @@ -14,6 +14,7 @@ #include <linux/module.h> #include <linux/kernel.h> #include <linux/platform_device.h> +#include <linux/sched.h> #include <linux/list.h> #include <linux/err.h> #include <linux/clk.h> @@ -188,7 +189,7 @@ int s3c_adc_read(struct s3c_adc_client *client, unsigned int ch) err: return ret; } -EXPORT_SYMBOL_GPL(s3c_adc_convert); +EXPORT_SYMBOL_GPL(s3c_adc_read); static void s3c_adc_default_select(struct s3c_adc_client *client, unsigned select) diff --git a/arch/arm/plat-s3c24xx/cpu.c b/arch/arm/plat-s3c24xx/cpu.c index 5447e60f3936..4af9dd948793 100644 --- a/arch/arm/plat-s3c24xx/cpu.c +++ b/arch/arm/plat-s3c24xx/cpu.c @@ -61,6 +61,7 @@ static const char name_s3c2410[] = "S3C2410"; static const char name_s3c2412[] = "S3C2412"; static const char name_s3c2440[] = "S3C2440"; static const char name_s3c2442[] = "S3C2442"; +static const char name_s3c2442b[] = "S3C2442B"; static const char name_s3c2443[] = "S3C2443"; static const char name_s3c2410a[] = "S3C2410A"; static const char name_s3c2440a[] = "S3C2440A"; @@ -112,6 +113,15 @@ static struct cpu_table cpu_ids[] __initdata = { .name = name_s3c2442 }, { + .idcode = 0x32440aab, + .idmask = 0xffffffff, + .map_io = s3c244x_map_io, + .init_clocks = s3c244x_init_clocks, + .init_uarts = s3c244x_init_uarts, + .init = s3c2442_init, + .name = name_s3c2442b + }, + { .idcode = 0x32412001, .idmask = 0xffffffff, .map_io = s3c2412_map_io, diff --git a/arch/arm/plat-s3c24xx/dma.c b/arch/arm/plat-s3c24xx/dma.c index 196b19123653..f046f8c51084 100644 --- a/arch/arm/plat-s3c24xx/dma.c +++ b/arch/arm/plat-s3c24xx/dma.c @@ -208,14 +208,14 @@ s3c2410_dma_loadbuffer(struct s3c2410_dma_chan *chan, { unsigned long reload; - pr_debug("s3c2410_chan_loadbuffer: loading buff %p (0x%08lx,0x%06x)\n", - buf, (unsigned long)buf->data, buf->size); - if (buf == NULL) { dmawarn("buffer is NULL\n"); return -EINVAL; } + pr_debug("s3c2410_chan_loadbuffer: loading buff %p (0x%08lx,0x%06x)\n", + buf, (unsigned long)buf->data, buf->size); + /* check the state of the channel before we do anything */ if (chan->load_state == S3C2410_DMALOAD_1LOADED) { diff --git a/arch/arm/plat-s3c24xx/gpio.c b/arch/arm/plat-s3c24xx/gpio.c index 95df059b5a1d..5467470badfd 100644 --- a/arch/arm/plat-s3c24xx/gpio.c +++ b/arch/arm/plat-s3c24xx/gpio.c @@ -29,6 +29,7 @@ #include <linux/io.h> #include <mach/hardware.h> +#include <mach/gpio-fns.h> #include <asm/irq.h> #include <mach/regs-gpio.h> diff --git a/arch/arm/plat-s3c24xx/include/plat/cpu-freq-core.h b/arch/arm/plat-s3c24xx/include/plat/cpu-freq-core.h index efeb025affc7..c776120b99e6 100644 --- a/arch/arm/plat-s3c24xx/include/plat/cpu-freq-core.h +++ b/arch/arm/plat-s3c24xx/include/plat/cpu-freq-core.h @@ -222,7 +222,9 @@ extern struct clk *s3c_cpufreq_clk_get(struct device *, const char *); /* S3C2410 and compatible exported functions */ extern void s3c2410_cpufreq_setrefresh(struct s3c_cpufreq_config *cfg); +extern void s3c2410_set_fvco(struct s3c_cpufreq_config *cfg); +#ifdef CONFIG_S3C2410_IOTIMING extern int s3c2410_iotiming_calc(struct s3c_cpufreq_config *cfg, struct s3c_iotimings *iot); @@ -231,8 +233,11 @@ extern int s3c2410_iotiming_get(struct s3c_cpufreq_config *cfg, extern void s3c2410_iotiming_set(struct s3c_cpufreq_config *cfg, struct s3c_iotimings *iot); - -extern void s3c2410_set_fvco(struct s3c_cpufreq_config *cfg); +#else +#define s3c2410_iotiming_calc NULL +#define s3c2410_iotiming_get NULL +#define s3c2410_iotiming_set NULL +#endif /* CONFIG_S3C2410_IOTIMING */ /* S3C2412 compatible routines */ diff --git a/arch/arm/plat-s3c24xx/include/plat/s3c2410.h b/arch/arm/plat-s3c24xx/include/plat/s3c2410.h index b6deeef8f663..82ab4aad1bbe 100644 --- a/arch/arm/plat-s3c24xx/include/plat/s3c2410.h +++ b/arch/arm/plat-s3c24xx/include/plat/s3c2410.h @@ -27,6 +27,7 @@ extern void s3c2410_init_clocks(int xtal); #define s3c2410_init_uarts NULL #define s3c2410_map_io NULL #define s3c2410_init NULL +#define s3c2410a_init NULL #endif extern int s3c2410_baseclk_add(void); diff --git a/arch/arm/plat-s3c64xx/dma.c b/arch/arm/plat-s3c64xx/dma.c index 266a10745a85..d554b936fcfb 100644 --- a/arch/arm/plat-s3c64xx/dma.c +++ b/arch/arm/plat-s3c64xx/dma.c @@ -151,8 +151,6 @@ static void s3c64xx_dma_fill_lli(struct s3c2410_dma_chan *chan, src = chan->dev_addr; dst = data; control0 = PL080_CONTROL_SRC_AHB2; - control0 |= (u32)chan->hw_width << PL080_CONTROL_SWIDTH_SHIFT; - control0 |= 2 << PL080_CONTROL_DWIDTH_SHIFT; control0 |= PL080_CONTROL_DST_INCR; break; @@ -160,8 +158,6 @@ static void s3c64xx_dma_fill_lli(struct s3c2410_dma_chan *chan, src = data; dst = chan->dev_addr; control0 = PL080_CONTROL_DST_AHB2; - control0 |= (u32)chan->hw_width << PL080_CONTROL_DWIDTH_SHIFT; - control0 |= 2 << PL080_CONTROL_SWIDTH_SHIFT; control0 |= PL080_CONTROL_SRC_INCR; break; default: @@ -173,6 +169,8 @@ static void s3c64xx_dma_fill_lli(struct s3c2410_dma_chan *chan, control1 = size >> chan->hw_width; /* size in no of xfers */ control0 |= PL080_CONTROL_PROT_SYS; /* always in priv. mode */ control0 |= PL080_CONTROL_TC_IRQ_EN; /* always fire IRQ */ + control0 |= (u32)chan->hw_width << PL080_CONTROL_DWIDTH_SHIFT; + control0 |= (u32)chan->hw_width << PL080_CONTROL_SWIDTH_SHIFT; lli->src_addr = src; lli->dst_addr = dst; @@ -339,6 +337,7 @@ int s3c2410_dma_enqueue(unsigned int channel, void *id, struct s3c64xx_dma_buff *next; struct s3c64xx_dma_buff *buff; struct pl080s_lli *lli; + unsigned long flags; int ret; WARN_ON(!chan); @@ -366,6 +365,8 @@ int s3c2410_dma_enqueue(unsigned int channel, void *id, s3c64xx_dma_fill_lli(chan, lli, data, size); + local_irq_save(flags); + if ((next = chan->next) != NULL) { struct s3c64xx_dma_buff *end = chan->end; struct pl080s_lli *endlli = end->lli; @@ -397,6 +398,8 @@ int s3c2410_dma_enqueue(unsigned int channel, void *id, s3c64xx_lli_to_regs(chan, lli); } + local_irq_restore(flags); + show_lli(lli); dbg_showchan(chan); @@ -560,26 +563,11 @@ int s3c2410_dma_free(unsigned int channel, struct s3c2410_dma_client *client) EXPORT_SYMBOL(s3c2410_dma_free); - -static void s3c64xx_dma_tcirq(struct s3c64xx_dmac *dmac, int offs) -{ - struct s3c2410_dma_chan *chan = dmac->channels + offs; - - /* note, we currently do not bother to work out which buffer - * or buffers have been completed since the last tc-irq. */ - - if (chan->callback_fn) - (chan->callback_fn)(chan, chan->curr->pw, 0, S3C2410_RES_OK); -} - -static void s3c64xx_dma_errirq(struct s3c64xx_dmac *dmac, int offs) -{ - printk(KERN_DEBUG "%s: offs %d\n", __func__, offs); -} - static irqreturn_t s3c64xx_dma_irq(int irq, void *pw) { struct s3c64xx_dmac *dmac = pw; + struct s3c2410_dma_chan *chan; + enum s3c2410_dma_buffresult res; u32 tcstat, errstat; u32 bit; int offs; @@ -588,14 +576,54 @@ static irqreturn_t s3c64xx_dma_irq(int irq, void *pw) errstat = readl(dmac->regs + PL080_ERR_STATUS); for (offs = 0, bit = 1; offs < 8; offs++, bit <<= 1) { + struct s3c64xx_dma_buff *buff; + + if (!(errstat & bit) && !(tcstat & bit)) + continue; + + chan = dmac->channels + offs; + res = S3C2410_RES_ERR; + if (tcstat & bit) { writel(bit, dmac->regs + PL080_TC_CLEAR); - s3c64xx_dma_tcirq(dmac, offs); + res = S3C2410_RES_OK; } - if (errstat & bit) { - s3c64xx_dma_errirq(dmac, offs); + if (errstat & bit) writel(bit, dmac->regs + PL080_ERR_CLEAR); + + /* 'next' points to the buffer that is next to the + * currently active buffer. + * For CIRCULAR queues, 'next' will be same as 'curr' + * when 'end' is the active buffer. + */ + buff = chan->curr; + while (buff && buff != chan->next + && buff->next != chan->next) + buff = buff->next; + + if (!buff) + BUG(); + + if (buff == chan->next) + buff = chan->end; + + s3c64xx_dma_bufffdone(chan, buff, res); + + /* Free the node and update curr, if non-circular queue */ + if (!(chan->flags & S3C2410_DMAF_CIRCULAR)) { + chan->curr = buff->next; + s3c64xx_dma_freebuff(buff); + } + + /* Update 'next' */ + buff = chan->next; + if (chan->next == chan->end) { + chan->next = chan->curr; + if (!(chan->flags & S3C2410_DMAF_CIRCULAR)) + chan->end = NULL; + } else { + chan->next = buff->next; } } diff --git a/arch/arm/plat-s3c64xx/include/plat/regs-clock.h b/arch/arm/plat-s3c64xx/include/plat/regs-clock.h index a8777a755dfa..ff46e7fa957a 100644 --- a/arch/arm/plat-s3c64xx/include/plat/regs-clock.h +++ b/arch/arm/plat-s3c64xx/include/plat/regs-clock.h @@ -51,8 +51,8 @@ #define S3C6400_CLKDIV0_HCLK_SHIFT (8) #define S3C6400_CLKDIV0_MPLL_MASK (0x1 << 4) #define S3C6400_CLKDIV0_MPLL_SHIFT (4) -#define S3C6400_CLKDIV0_ARM_MASK (0x3 << 0) -#define S3C6410_CLKDIV0_ARM_MASK (0x7 << 0) +#define S3C6400_CLKDIV0_ARM_MASK (0x7 << 0) +#define S3C6410_CLKDIV0_ARM_MASK (0xf << 0) #define S3C6400_CLKDIV0_ARM_SHIFT (0) /* CLKDIV1 */ diff --git a/arch/arm/plat-s3c64xx/s3c6400-clock.c b/arch/arm/plat-s3c64xx/s3c6400-clock.c index 9745852261e0..6ffa21eb1b91 100644 --- a/arch/arm/plat-s3c64xx/s3c6400-clock.c +++ b/arch/arm/plat-s3c64xx/s3c6400-clock.c @@ -677,6 +677,9 @@ void __init_or_cpufreq s3c6400_setup_clocks(void) printk(KERN_DEBUG "%s: xtal is %ld\n", __func__, xtal); + /* For now assume the mux always selects the crystal */ + clk_ext_xtal_mux.parent = xtal_clk; + epll = s3c6400_get_epll(xtal); mpll = s3c6400_get_pll(xtal, __raw_readl(S3C_MPLL_CON)); apll = s3c6400_get_pll(xtal, __raw_readl(S3C_APLL_CON)); diff --git a/arch/avr32/mach-at32ap/include/mach/cpu.h b/arch/avr32/mach-at32ap/include/mach/cpu.h index 44d0bfa1f409..9c96a130f3a8 100644 --- a/arch/avr32/mach-at32ap/include/mach/cpu.h +++ b/arch/avr32/mach-at32ap/include/mach/cpu.h @@ -31,5 +31,8 @@ #define cpu_is_at91sam9263() (0) #define cpu_is_at91sam9rl() (0) #define cpu_is_at91cap9() (0) +#define cpu_is_at91sam9g10() (0) +#define cpu_is_at91sam9g45() (0) +#define cpu_is_at91sam9g45es() (0) #endif /* __ASM_ARCH_CPU_H */ diff --git a/arch/blackfin/ADI_BSD.txt b/arch/blackfin/ADI_BSD.txt new file mode 100644 index 000000000000..501d0b645943 --- /dev/null +++ b/arch/blackfin/ADI_BSD.txt @@ -0,0 +1,41 @@ +This BSD-Style License applies to a few files in ./arch/blackfin directory, +and is included here, so people understand which code they can use outside +the Linux kernel, in non-GPL based projects. + +Using the files released under the "ADI BSD" license, must comply with +these license terms. + +-------------------------------------------------------------------------- + +Copyright Analog Devices, Inc. + +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions +are met: + - Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + - Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in + the documentation and/or other materials provided with the + distribution. + - Neither the name of Analog Devices, Inc. nor the names of its + contributors may be used to endorse or promote products derived + from this software without specific prior written permission. + - The use of this software may or may not infringe the patent rights + of one or more patent holders. This license does not release you + from the requirement that you obtain separate licenses from these + patent holders to use this software. + +THIS SOFTWARE IS PROVIDED BY ANALOG DEVICES "AS IS" AND ANY EXPRESS OR +IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, NON-INFRINGEMENT, +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +IN NO EVENT SHALL ANALOG DEVICES BE LIABLE FOR ANY DIRECT, INDIRECT, +INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, +BUT NOT LIMITED TO, INTELLECTUAL PROPERTY RIGHTS, PROCUREMENT OF +SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR +BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, +WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR +OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF +ADVISED OF THE POSSIBILITY OF SUCH DAMAGE diff --git a/arch/blackfin/Kconfig b/arch/blackfin/Kconfig index 9a01d445eca8..ae6a60f10120 100644 --- a/arch/blackfin/Kconfig +++ b/arch/blackfin/Kconfig @@ -47,6 +47,9 @@ config GENERIC_HARDIRQS config GENERIC_IRQ_PROBE def_bool y +config GENERIC_HARDIRQS_NO__DO_IRQ + def_bool y + config GENERIC_GPIO def_bool y @@ -229,7 +232,7 @@ endchoice config SMP depends on BF561 - select GENERIC_TIME + select GENERIC_CLOCKEVENTS bool "Symmetric multi-processing support" ---help--- This enables support for systems with more than one CPU, @@ -613,12 +616,10 @@ comment "Kernel Timer/Scheduler" source kernel/Kconfig.hz config GENERIC_TIME - bool "Generic time" - default y + def_bool y config GENERIC_CLOCKEVENTS bool "Generic clock events" - depends on GENERIC_TIME default y choice @@ -653,6 +654,10 @@ config GPTMR0_CLOCKSOURCE depends on GENERIC_CLOCKEVENTS depends on !TICKSOURCE_GPTMR0 +config ARCH_USES_GETTIMEOFFSET + depends on !GENERIC_CLOCKEVENTS + def_bool y + source kernel/time/Kconfig comment "Misc" diff --git a/arch/blackfin/include/asm/atomic.h b/arch/blackfin/include/asm/atomic.h index 88f36d599fe8..d27c6274247d 100644 --- a/arch/blackfin/include/asm/atomic.h +++ b/arch/blackfin/include/asm/atomic.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __ARCH_BLACKFIN_ATOMIC__ #define __ARCH_BLACKFIN_ATOMIC__ diff --git a/arch/blackfin/include/asm/bfin-global.h b/arch/blackfin/include/asm/bfin-global.h index aef0594e7865..10064f902d20 100644 --- a/arch/blackfin/include/asm/bfin-global.h +++ b/arch/blackfin/include/asm/bfin-global.h @@ -1,29 +1,9 @@ /* - * File: include/asm-blackfin/bfin-global.h - * Based on: - * Author: * - * Created: - * Description: Global extern defines for blackfin + * Global extern defines for blackfin * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. + * Copyright 2006-2009 Analog Devices Inc. * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef _BFIN_GLOBAL_H_ diff --git a/arch/blackfin/include/asm/bfin5xx_spi.h b/arch/blackfin/include/asm/bfin5xx_spi.h index c281c6328276..ed4f8c6db0cd 100644 --- a/arch/blackfin/include/asm/bfin5xx_spi.h +++ b/arch/blackfin/include/asm/bfin5xx_spi.h @@ -3,8 +3,6 @@ * * Copyright 2004-2008 Analog Devices Inc. * - * Enter bugs at http://blackfin.uclinux.org/ - * * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/include/asm/bfin_rotary.h b/arch/blackfin/include/asm/bfin_rotary.h index 425ece64fd5e..abdb2af52902 100644 --- a/arch/blackfin/include/asm/bfin_rotary.h +++ b/arch/blackfin/include/asm/bfin_rotary.h @@ -1,6 +1,10 @@ /* * board initialization should put one of these structures into platform_data * and place the bfin-rotary onto platform_bus named "bfin-rotary". + * + * Copyright 2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ #ifndef _BFIN_ROTARY_H diff --git a/arch/blackfin/include/asm/bfin_simple_timer.h b/arch/blackfin/include/asm/bfin_simple_timer.h index fccbb595464a..5248c133bc68 100644 --- a/arch/blackfin/include/asm/bfin_simple_timer.h +++ b/arch/blackfin/include/asm/bfin_simple_timer.h @@ -1,3 +1,9 @@ +/* + * Copyright 2006-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _bfin_simple_timer_h_ #define _bfin_simple_timer_h_ diff --git a/arch/blackfin/include/asm/bitops.h b/arch/blackfin/include/asm/bitops.h index daffa71576d4..a2ff3fb3568d 100644 --- a/arch/blackfin/include/asm/bitops.h +++ b/arch/blackfin/include/asm/bitops.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_BITOPS_H #define _BLACKFIN_BITOPS_H diff --git a/arch/blackfin/include/asm/blackfin.h b/arch/blackfin/include/asm/blackfin.h index 4d4439583396..eb7c1441d8f9 100644 --- a/arch/blackfin/include/asm/blackfin.h +++ b/arch/blackfin/include/asm/blackfin.h @@ -1,6 +1,9 @@ /* - * Common header file for blackfin family of processors. + * Common header file for Blackfin family of processors. * + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ #ifndef _BLACKFIN_H_ diff --git a/arch/blackfin/include/asm/bug.h b/arch/blackfin/include/asm/bug.h index 655e49540e41..6f4548a13555 100644 --- a/arch/blackfin/include/asm/bug.h +++ b/arch/blackfin/include/asm/bug.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_BUG_H #define _BLACKFIN_BUG_H diff --git a/arch/blackfin/include/asm/byteorder.h b/arch/blackfin/include/asm/byteorder.h index 3e69106a4d37..9558416d578b 100644 --- a/arch/blackfin/include/asm/byteorder.h +++ b/arch/blackfin/include/asm/byteorder.h @@ -1,6 +1 @@ -#ifndef _BLACKFIN_BYTEORDER_H -#define _BLACKFIN_BYTEORDER_H - #include <linux/byteorder/little_endian.h> - -#endif /* _BLACKFIN_BYTEORDER_H */ diff --git a/arch/blackfin/include/asm/cache.h b/arch/blackfin/include/asm/cache.h index 477050ad5c53..8542bc31f63c 100644 --- a/arch/blackfin/include/asm/cache.h +++ b/arch/blackfin/include/asm/cache.h @@ -1,6 +1,9 @@ /* - * include/asm-blackfin/cache.h + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ + #ifndef __ARCH_BLACKFIN_CACHE_H #define __ARCH_BLACKFIN_CACHE_H @@ -35,10 +38,10 @@ #if defined(CONFIG_SMP) && \ !defined(CONFIG_BFIN_CACHE_COHERENT) -# if defined(CONFIG_BFIN_ICACHEABLE) || defined(CONFIG_BFIN_L2_ICACHEABLE) +# if defined(CONFIG_BFIN_EXTMEM_ICACHEABLE) || defined(CONFIG_BFIN_L2_ICACHEABLE) # define __ARCH_SYNC_CORE_ICACHE # endif -# if defined(CONFIG_BFIN_DCACHEABLE) || defined(CONFIG_BFIN_L2_DCACHEABLE) +# if defined(CONFIG_BFIN_EXTMEM_DCACHEABLE) || defined(CONFIG_BFIN_L2_DCACHEABLE) # define __ARCH_SYNC_CORE_DCACHE # endif #ifndef __ASSEMBLY__ diff --git a/arch/blackfin/include/asm/cacheflush.h b/arch/blackfin/include/asm/cacheflush.h index 7e55549e180f..af03a36c7a4e 100644 --- a/arch/blackfin/include/asm/cacheflush.h +++ b/arch/blackfin/include/asm/cacheflush.h @@ -1,30 +1,9 @@ /* - * File: include/asm-blackfin/cacheflush.h - * Based on: include/asm-m68knommu/cacheflush.h - * Author: LG Soft India - * Copyright (C) 2004 Analog Devices Inc. - * Created: Tue Sep 21 2004 - * Description: Blackfin low-level cache routines adapted from the i386 - * and PPC versions by Greg Ungerer (gerg@snapgear.com) + * Blackfin low-level cache routines * - * Modified: + * Copyright 2004-2009 Analog Devices Inc. * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _BLACKFIN_CACHEFLUSH_H diff --git a/arch/blackfin/include/asm/cdef_LPBlackfin.h b/arch/blackfin/include/asm/cdef_LPBlackfin.h index 35f841bce57d..8778e0f03730 100644 --- a/arch/blackfin/include/asm/cdef_LPBlackfin.h +++ b/arch/blackfin/include/asm/cdef_LPBlackfin.h @@ -1,30 +1,8 @@ - /* - * File: include/asm-blackfin/mach-common/cdef_LPBlackfin.h - * Based on: - * Author: unknown - * COPYRIGHT 2005 Analog Devices - * Created: ? - * Description: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - */ +/* + * Copyright 2005-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ #ifndef _CDEF_LPBLACKFIN_H #define _CDEF_LPBLACKFIN_H diff --git a/arch/blackfin/include/asm/checksum.h b/arch/blackfin/include/asm/checksum.h index 793581fc9556..a23415be0de1 100644 --- a/arch/blackfin/include/asm/checksum.h +++ b/arch/blackfin/include/asm/checksum.h @@ -1,9 +1,14 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * akbar.hussain@lineo.com + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BFIN_CHECKSUM_H #define _BFIN_CHECKSUM_H /* - * MODIFIED FOR BFIN April 30, 2001 akbar.hussain@lineo.com - * * computes the checksum of a memory block at buff, length len, * and adds in "sum" (32-bit) * diff --git a/arch/blackfin/include/asm/clocks.h b/arch/blackfin/include/asm/clocks.h index 033bba92d61c..f80dad5ff257 100644 --- a/arch/blackfin/include/asm/clocks.h +++ b/arch/blackfin/include/asm/clocks.h @@ -1,30 +1,9 @@ /* - * File: include/asm-blackfin/mach-common/clocks.h - * Based on: include/asm-blackfin/mach-bf537/bf537.h - * Author: Robin Getz <rgetz@blackfin.uclinux.org> + * Common Clock definitions for various kernel files * - * Created: 25Jul07 - * Description: Common Clock definitions for various kernel files + * Copyright 2007-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef _BFIN_CLOCKS_H diff --git a/arch/blackfin/include/asm/context.S b/arch/blackfin/include/asm/context.S index f8a664f022b1..5dffaf582a22 100644 --- a/arch/blackfin/include/asm/context.S +++ b/arch/blackfin/include/asm/context.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/context.S - * Based on: - * Author: + * Copyright 2007-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ /* diff --git a/arch/blackfin/include/asm/cplb.h b/arch/blackfin/include/asm/cplb.h index d18d16837a6d..fda96261ed62 100644 --- a/arch/blackfin/include/asm/cplb.h +++ b/arch/blackfin/include/asm/cplb.h @@ -1,30 +1,7 @@ /* - * File: include/asm-blackfin/cplb.h - * Based on: include/asm-blackfin/mach-bf537/bf537.h - * Author: Robin Getz <rgetz@blackfin.uclinux.org> + * Copyright 2004-2009 Analog Devices Inc. * - * Created: 2000 - * Description: Common CPLB definitions for CPLB init - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef _CPLB_H diff --git a/arch/blackfin/include/asm/cplbinit.h b/arch/blackfin/include/asm/cplbinit.h index 05b14a631d0c..f315c83a015d 100644 --- a/arch/blackfin/include/asm/cplbinit.h +++ b/arch/blackfin/include/asm/cplbinit.h @@ -1,30 +1,9 @@ /* - * File: include/asm-blackfin/cplbinit.h - * Based on: - * Author: + * Common CPLB definitions for CPLB init * - * Created: - * Description: + * Copyright 2006-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __ASM_CPLBINIT_H__ diff --git a/arch/blackfin/include/asm/cpu.h b/arch/blackfin/include/asm/cpu.h index fadfa82f93b2..b191dc662bd8 100644 --- a/arch/blackfin/include/asm/cpu.h +++ b/arch/blackfin/include/asm/cpu.h @@ -1,23 +1,8 @@ /* - * File: arch/blackfin/include/asm/cpu.h. - * Author: Philippe Gerum <rpm@xenomai.org> + * Copyright 2007-2009 Analog Devices Inc. + * Philippe Gerum <rpm@xenomai.org> * - * Copyright 2007 Analog Devices Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __ASM_BLACKFIN_CPU_H diff --git a/arch/blackfin/include/asm/def_LPBlackfin.h b/arch/blackfin/include/asm/def_LPBlackfin.h index 6341eebff3dc..25906468622f 100644 --- a/arch/blackfin/include/asm/def_LPBlackfin.h +++ b/arch/blackfin/include/asm/def_LPBlackfin.h @@ -1,32 +1,10 @@ - /* - * File: include/asm-blackfin/mach-common/def_LPBlackfin.h - * Based on: - * Author: unknown - * COPYRIGHT 2005 Analog Devices - * Created: ? - * Description: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - */ - -/* LP Blackfin CORE REGISTER BIT & ADDRESS DEFINITIONS FOR ADSP-BF532/33 */ +/* + * Blackfin core register bit & address definitions + * + * Copyright 2005-2008 Analog Devices Inc. + * + * Licensed under the ADI BSD license or GPL-2 (or later). + */ #ifndef _DEF_LPBLACKFIN_H #define _DEF_LPBLACKFIN_H diff --git a/arch/blackfin/include/asm/dma-mapping.h b/arch/blackfin/include/asm/dma-mapping.h index ed6b1f3cccce..7a23d824ac96 100644 --- a/arch/blackfin/include/asm/dma-mapping.h +++ b/arch/blackfin/include/asm/dma-mapping.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_DMA_MAPPING_H #define _BLACKFIN_DMA_MAPPING_H diff --git a/arch/blackfin/include/asm/dpmc.h b/arch/blackfin/include/asm/dpmc.h index 96e8208f929a..925e66cb2d49 100644 --- a/arch/blackfin/include/asm/dpmc.h +++ b/arch/blackfin/include/asm/dpmc.h @@ -1,9 +1,11 @@ /* - * include/asm-blackfin/dpmc.h - Miscellaneous IOCTL commands for Dynamic Power - * Management Controller Driver. + * Miscellaneous IOCTL commands for Dynamic Power Management Controller Driver + * * Copyright (C) 2004-2008 Analog Device Inc. * + * Licensed under the GPL-2 */ + #ifndef _BLACKFIN_DPMC_H_ #define _BLACKFIN_DPMC_H_ diff --git a/arch/blackfin/include/asm/early_printk.h b/arch/blackfin/include/asm/early_printk.h index 53a762b6fcd2..68a910db8864 100644 --- a/arch/blackfin/include/asm/early_printk.h +++ b/arch/blackfin/include/asm/early_printk.h @@ -1,27 +1,11 @@ /* - * File: include/asm-blackfin/early_printk.h - * Author: Robin Getz <rgetz@blackfin.uclinux.org + * function prototpyes for early printk * - * Created: 14Aug2007 - * Description: function prototpyes for early printk + * Copyright 2007-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Licensed under the GPL-2 or later. */ - #ifndef __ASM_EARLY_PRINTK_H__ #define __ASM_EARLY_PRINTK_H__ diff --git a/arch/blackfin/include/asm/elf.h b/arch/blackfin/include/asm/elf.h index c823e8ebbfa1..8e0764c81eaf 100644 --- a/arch/blackfin/include/asm/elf.h +++ b/arch/blackfin/include/asm/elf.h @@ -1,4 +1,8 @@ -/* Changes made by LG Soft Oct 2004*/ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ #ifndef __ASMBFIN_ELF_H #define __ASMBFIN_ELF_H diff --git a/arch/blackfin/include/asm/entry.h b/arch/blackfin/include/asm/entry.h index 55b808fced71..a6886f6e4819 100644 --- a/arch/blackfin/include/asm/entry.h +++ b/arch/blackfin/include/asm/entry.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __BFIN_ENTRY_H #define __BFIN_ENTRY_H diff --git a/arch/blackfin/include/asm/fcntl.h b/arch/blackfin/include/asm/fcntl.h index 9c4037127857..8727b2b382f1 100644 --- a/arch/blackfin/include/asm/fcntl.h +++ b/arch/blackfin/include/asm/fcntl.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BFIN_FCNTL_H #define _BFIN_FCNTL_H diff --git a/arch/blackfin/include/asm/fixed_code.h b/arch/blackfin/include/asm/fixed_code.h index 32c4d495d847..73fe53e7fd24 100644 --- a/arch/blackfin/include/asm/fixed_code.h +++ b/arch/blackfin/include/asm/fixed_code.h @@ -1,5 +1,11 @@ -/* This file defines the fixed addresses where userspace programs can find - atomic code sequences. */ +/* + * This file defines the fixed addresses where userspace programs + * can find atomic code sequences. + * + * Copyright 2007-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ #ifndef __BFIN_ASM_FIXED_CODE_H__ #define __BFIN_ASM_FIXED_CODE_H__ diff --git a/arch/blackfin/include/asm/flat.h b/arch/blackfin/include/asm/flat.h index 733a178d782d..c1314c56dd18 100644 --- a/arch/blackfin/include/asm/flat.h +++ b/arch/blackfin/include/asm/flat.h @@ -1,8 +1,9 @@ /* - * include/asm-blackfin/flat.h -- uClinux flat-format executables + * uClinux flat-format executables * - * Copyright (C) 2003, + * Copyright 2003-2009 Analog Devices Inc. * + * Licensed under the GPL-2 */ #ifndef __BLACKFIN_FLAT_H__ diff --git a/arch/blackfin/include/asm/gpio.h b/arch/blackfin/include/asm/gpio.h index fe139619351f..5b44d05ca53e 100644 --- a/arch/blackfin/include/asm/gpio.h +++ b/arch/blackfin/include/asm/gpio.h @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/bfin_gpio.h - * Based on: - * Author: Michael Hennerich (hennerich@blackfin.uclinux.org) + * Copyright 2006-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __ARCH_BLACKFIN_GPIO_H__ diff --git a/arch/blackfin/include/asm/hardirq.h b/arch/blackfin/include/asm/hardirq.h index 0b78b873df51..c078dd78d998 100644 --- a/arch/blackfin/include/asm/hardirq.h +++ b/arch/blackfin/include/asm/hardirq.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __BFIN_HARDIRQ_H #define __BFIN_HARDIRQ_H diff --git a/arch/blackfin/include/asm/io.h b/arch/blackfin/include/asm/io.h index 37053eca200e..d1f5029189a7 100644 --- a/arch/blackfin/include/asm/io.h +++ b/arch/blackfin/include/asm/io.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BFIN_IO_H #define _BFIN_IO_H diff --git a/arch/blackfin/include/asm/irq.h b/arch/blackfin/include/asm/irq.h index 42a15f5ce0d0..e7c0623f9091 100644 --- a/arch/blackfin/include/asm/irq.h +++ b/arch/blackfin/include/asm/irq.h @@ -1,17 +1,10 @@ /* - * This file is subject to the terms and conditions of the GNU General Public - * License. See the file COPYING in the main directory of this archive - * for more details. + * Copyright 2004-2009 Analog Devices Inc. + * 2003 HuTao + * 2002 Arcturus Networks Inc. (www.arcturusnetworks.com + * Ted Ma <mated@sympatico.ca> * - * Changed by HuTao Apr18, 2003 - * - * Copyright was missing when I got the code so took from MIPS arch ...MaTed--- - * Copyright (C) 1994 by Waldorf GMBH, written by Ralf Baechle - * Copyright (C) 1995, 96, 97, 98, 99, 2000, 2001 by Ralf Baechle - * - * Adapted for BlackFin (ADI) by Ted Ma <mated@sympatico.ca> - * Copyright (c) 2002 Arcturus Networks Inc. (www.arcturusnetworks.com) - * Copyright (c) 2002 Lineo, Inc. <mattw@lineo.com> + * Licensed under the GPL-2 */ #ifndef _BFIN_IRQ_H_ @@ -19,6 +12,8 @@ #include <linux/irqflags.h> +#include <mach/anomaly.h> + /* SYS_IRQS and NR_IRQS are defined in <mach-bf5xx/irq.h> */ #include <mach/irq.h> diff --git a/arch/blackfin/include/asm/irq_handler.h b/arch/blackfin/include/asm/irq_handler.h index 7d9e2d3bbede..7fbe42307b9a 100644 --- a/arch/blackfin/include/asm/irq_handler.h +++ b/arch/blackfin/include/asm/irq_handler.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _IRQ_HANDLER_H #define _IRQ_HANDLER_H diff --git a/arch/blackfin/include/asm/l1layout.h b/arch/blackfin/include/asm/l1layout.h index 79dbefaa5bef..c87e68647a2b 100644 --- a/arch/blackfin/include/asm/l1layout.h +++ b/arch/blackfin/include/asm/l1layout.h @@ -1,6 +1,9 @@ /* - * l1layout.h * Defines a layout of L1 scratchpad memory that userspace can rely on. + * + * Copyright 2006-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ #ifndef _L1LAYOUT_H_ diff --git a/arch/blackfin/include/asm/linkage.h b/arch/blackfin/include/asm/linkage.h index 5a822bb790f7..f7d6d47a048d 100644 --- a/arch/blackfin/include/asm/linkage.h +++ b/arch/blackfin/include/asm/linkage.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __ASM_LINKAGE_H #define __ASM_LINKAGE_H diff --git a/arch/blackfin/include/asm/mmu.h b/arch/blackfin/include/asm/mmu.h index dbfd686360e6..26f6b70b11e2 100644 --- a/arch/blackfin/include/asm/mmu.h +++ b/arch/blackfin/include/asm/mmu.h @@ -1,8 +1,13 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * 2002 David McCullough <davidm@snapgear.com> + * + * Licensed under the GPL-2. + */ + #ifndef __MMU_H #define __MMU_H -/* Copyright (C) 2002, David McCullough <davidm@snapgear.com> */ - struct sram_list_struct { struct sram_list_struct *next; void *addr; diff --git a/arch/blackfin/include/asm/mmu_context.h b/arch/blackfin/include/asm/mmu_context.h index 040410bb07e1..4a3be376ad5b 100644 --- a/arch/blackfin/include/asm/mmu_context.h +++ b/arch/blackfin/include/asm/mmu_context.h @@ -1,30 +1,7 @@ /* - * File: include/asm-blackfin/mmu_context.h - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __BLACKFIN_MMU_CONTEXT_H__ diff --git a/arch/blackfin/include/asm/module.h b/arch/blackfin/include/asm/module.h index e3128df139d6..9c1cfffddd9b 100644 --- a/arch/blackfin/include/asm/module.h +++ b/arch/blackfin/include/asm/module.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _ASM_BFIN_MODULE_H #define _ASM_BFIN_MODULE_H diff --git a/arch/blackfin/include/asm/mutex.h b/arch/blackfin/include/asm/mutex.h index 5cc641c50834..f726e3a80ad0 100644 --- a/arch/blackfin/include/asm/mutex.h +++ b/arch/blackfin/include/asm/mutex.h @@ -4,6 +4,10 @@ * TODO: implement optimized primitives instead, or leave the generic * implementation in place, or pick the atomic_xchg() based generic * implementation. (see asm-generic/mutex-xchg.h for details) + * + * Copyright 2006-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ #ifndef _ASM_MUTEX_H diff --git a/arch/blackfin/include/asm/nand.h b/arch/blackfin/include/asm/nand.h index afbaafa793f1..3ae8b569edfc 100644 --- a/arch/blackfin/include/asm/nand.h +++ b/arch/blackfin/include/asm/nand.h @@ -1,13 +1,9 @@ -/* linux/include/asm-blackfin/nand.h - * - * Copyright (c) 2007 Analog Devices, Inc. - * Bryan Wu <bryan.wu@analog.com> - * +/* * BF5XX - NAND flash controller platfrom_device info * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. + * Copyright 2007-2008 Analog Devices, Inc. + * + * Licensed under the GPL-2 */ /* struct bf5xx_nand_platform diff --git a/arch/blackfin/include/asm/page.h b/arch/blackfin/include/asm/page.h index 29dcf75c6112..944a07c6cfd6 100644 --- a/arch/blackfin/include/asm/page.h +++ b/arch/blackfin/include/asm/page.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_PAGE_H #define _BLACKFIN_PAGE_H diff --git a/arch/blackfin/include/asm/page_offset.h b/arch/blackfin/include/asm/page_offset.h index cbaff24b4b25..d06a89b89d20 100644 --- a/arch/blackfin/include/asm/page_offset.h +++ b/arch/blackfin/include/asm/page_offset.h @@ -1,5 +1,10 @@ - -/* This handles the memory map.. */ +/* + * This handles the memory map + * + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ #ifdef CONFIG_BLACKFIN #define PAGE_OFFSET_RAW 0x00000000 diff --git a/arch/blackfin/include/asm/pda.h b/arch/blackfin/include/asm/pda.h index a6f95695731d..d49bb261d9b7 100644 --- a/arch/blackfin/include/asm/pda.h +++ b/arch/blackfin/include/asm/pda.h @@ -1,23 +1,8 @@ /* - * File: arch/blackfin/include/asm/pda.h - * Author: Philippe Gerum <rpm@xenomai.org> + * Copyright 2007-2009 Analog Devices Inc. + * Philippe Gerum <rpm@xenomai.org> * - * Copyright 2007 Analog Devices Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef _ASM_BLACKFIN_PDA_H diff --git a/arch/blackfin/include/asm/pgtable.h b/arch/blackfin/include/asm/pgtable.h index 783c8f7f8f8c..821c699c2238 100644 --- a/arch/blackfin/include/asm/pgtable.h +++ b/arch/blackfin/include/asm/pgtable.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_PGTABLE_H #define _BLACKFIN_PGTABLE_H @@ -92,6 +98,12 @@ extern unsigned int kobjsize(const void *objp); #define VMALLOC_START 0 #define VMALLOC_END 0xffffffff +/* provide a special get_unmapped_area for framebuffer mmaps of nommu */ +extern unsigned long get_fb_unmapped_area(struct file *filp, unsigned long, + unsigned long, unsigned long, + unsigned long); +#define HAVE_ARCH_FB_UNMAPPED_AREA + #include <asm-generic/pgtable.h> #endif /* _BLACKFIN_PGTABLE_H */ diff --git a/arch/blackfin/include/asm/poll.h b/arch/blackfin/include/asm/poll.h index a0556671357b..072d8966c5c3 100644 --- a/arch/blackfin/include/asm/poll.h +++ b/arch/blackfin/include/asm/poll.h @@ -1,3 +1,10 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + * + */ + #ifndef __BFIN_POLL_H #define __BFIN_POLL_H diff --git a/arch/blackfin/include/asm/portmux.h b/arch/blackfin/include/asm/portmux.h index 88eb5c07cc24..edd8ef3a3788 100644 --- a/arch/blackfin/include/asm/portmux.h +++ b/arch/blackfin/include/asm/portmux.h @@ -1,6 +1,9 @@ /* - * Common header file for blackfin family of processors. + * Common header file for Blackfin family of processors * + * Copyright 2007-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ #ifndef _PORTMUX_H_ diff --git a/arch/blackfin/include/asm/posix_types.h b/arch/blackfin/include/asm/posix_types.h index 80c9d64eb26c..41bc1875c4d7 100644 --- a/arch/blackfin/include/asm/posix_types.h +++ b/arch/blackfin/include/asm/posix_types.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __ARCH_BFIN_POSIX_TYPES_H #define __ARCH_BFIN_POSIX_TYPES_H diff --git a/arch/blackfin/include/asm/processor.h b/arch/blackfin/include/asm/processor.h index a36ad8dac068..aea880274de7 100644 --- a/arch/blackfin/include/asm/processor.h +++ b/arch/blackfin/include/asm/processor.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __ASM_BFIN_PROCESSOR_H #define __ASM_BFIN_PROCESSOR_H diff --git a/arch/blackfin/include/asm/ptrace.h b/arch/blackfin/include/asm/ptrace.h index e3f086dc7268..27290c955a7a 100644 --- a/arch/blackfin/include/asm/ptrace.h +++ b/arch/blackfin/include/asm/ptrace.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BFIN_PTRACE_H #define _BFIN_PTRACE_H diff --git a/arch/blackfin/include/asm/sections.h b/arch/blackfin/include/asm/sections.h index ae4dae1e370b..1f5381fbb4a7 100644 --- a/arch/blackfin/include/asm/sections.h +++ b/arch/blackfin/include/asm/sections.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_SECTIONS_H #define _BLACKFIN_SECTIONS_H diff --git a/arch/blackfin/include/asm/segment.h b/arch/blackfin/include/asm/segment.h index 02cfd09b5a99..f8e1984ffc7e 100644 --- a/arch/blackfin/include/asm/segment.h +++ b/arch/blackfin/include/asm/segment.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BFIN_SEGMENT_H #define _BFIN_SEGMENT_H diff --git a/arch/blackfin/include/asm/sigcontext.h b/arch/blackfin/include/asm/sigcontext.h index ce00b03c2775..ce4081a4d815 100644 --- a/arch/blackfin/include/asm/sigcontext.h +++ b/arch/blackfin/include/asm/sigcontext.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _ASM_BLACKFIN_SIGCONTEXT_H #define _ASM_BLACKFIN_SIGCONTEXT_H diff --git a/arch/blackfin/include/asm/siginfo.h b/arch/blackfin/include/asm/siginfo.h index eca4565cea37..3e81306394e2 100644 --- a/arch/blackfin/include/asm/siginfo.h +++ b/arch/blackfin/include/asm/siginfo.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BFIN_SIGINFO_H #define _BFIN_SIGINFO_H diff --git a/arch/blackfin/include/asm/smp.h b/arch/blackfin/include/asm/smp.h index 118deeeae7c0..6a0fe94b84a6 100644 --- a/arch/blackfin/include/asm/smp.h +++ b/arch/blackfin/include/asm/smp.h @@ -1,23 +1,8 @@ /* - * File: arch/blackfin/include/asm/smp.h - * Author: Philippe Gerum <rpm@xenomai.org> + * Copyright 2007-2009 Analog Devices Inc. + * Philippe Gerum <rpm@xenomai.org> * - * Copyright 2007 Analog Devices Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __ASM_BLACKFIN_SMP_H diff --git a/arch/blackfin/include/asm/spinlock.h b/arch/blackfin/include/asm/spinlock.h index d6ff4b59fcb1..b0c7f0ee4b03 100644 --- a/arch/blackfin/include/asm/spinlock.h +++ b/arch/blackfin/include/asm/spinlock.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __BFIN_SPINLOCK_H #define __BFIN_SPINLOCK_H diff --git a/arch/blackfin/include/asm/spinlock_types.h b/arch/blackfin/include/asm/spinlock_types.h index b1e3c4c7b382..be75762c0610 100644 --- a/arch/blackfin/include/asm/spinlock_types.h +++ b/arch/blackfin/include/asm/spinlock_types.h @@ -1,3 +1,9 @@ +/* + * Copyright 2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __ASM_SPINLOCK_TYPES_H #define __ASM_SPINLOCK_TYPES_H diff --git a/arch/blackfin/include/asm/stat.h b/arch/blackfin/include/asm/stat.h index d2b6f11ec231..2e27665c4e91 100644 --- a/arch/blackfin/include/asm/stat.h +++ b/arch/blackfin/include/asm/stat.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2006 Analog Devices Inc. + * + * Licensed under the GPL-2. + */ + #ifndef _BFIN_STAT_H #define _BFIN_STAT_H diff --git a/arch/blackfin/include/asm/string.h b/arch/blackfin/include/asm/string.h index 321f4d96e4ae..d7f0ccb418c3 100644 --- a/arch/blackfin/include/asm/string.h +++ b/arch/blackfin/include/asm/string.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_STRING_H_ #define _BLACKFIN_STRING_H_ diff --git a/arch/blackfin/include/asm/swab.h b/arch/blackfin/include/asm/swab.h index d442113de515..89de6507ca2b 100644 --- a/arch/blackfin/include/asm/swab.h +++ b/arch/blackfin/include/asm/swab.h @@ -1,3 +1,9 @@ +/* + * Copyright 2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_SWAB_H #define _BLACKFIN_SWAB_H diff --git a/arch/blackfin/include/asm/system.h b/arch/blackfin/include/asm/system.h index 85e8f16cf8c2..dde19b1d25f5 100644 --- a/arch/blackfin/include/asm/system.h +++ b/arch/blackfin/include/asm/system.h @@ -1,34 +1,8 @@ /* - * File: include/asm/system.h - * Based on: - * Author: Tony Kou (tonyko@lineo.ca) - * Copyright (c) 2002 Arcturus Networks Inc. - * (www.arcturusnetworks.com) - * Copyright (c) 2003 Metrowerks (www.metrowerks.com) - * Copyright (c) 2004 Analog Device Inc. - * Created: 25Jan2001 - Tony Kou - * Description: system.h include file + * Copyright 2004-2009 Analog Devices Inc. + * Tony Kou (tonyko@lineo.ca) * - * Modified: 22Sep2006 - Robin Getz - * - move include blackfin.h down, so I can get access to - * irq functions in other include files. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _BLACKFIN_SYSTEM_H diff --git a/arch/blackfin/include/asm/thread_info.h b/arch/blackfin/include/asm/thread_info.h index 2bbfdd950afc..afb3a8626380 100644 --- a/arch/blackfin/include/asm/thread_info.h +++ b/arch/blackfin/include/asm/thread_info.h @@ -1,27 +1,7 @@ /* - * File: include/asm-blackfin/thread_info.h - * Based on: include/asm-m68knommu/thread_info.h - * Author: LG Soft India - * Copyright (C) 2004-2005 Analog Devices Inc. - * Created: Tue Sep 21 2004 - * Description: Blackfin low-level thread information - * Modified: - * Bugs: Enter bugs at http://blackfin.uclinux.org/ + * Copyright 2004-2009 Analog Devices Inc. * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _ASM_THREAD_INFO_H diff --git a/arch/blackfin/include/asm/tlb.h b/arch/blackfin/include/asm/tlb.h index 89a12ee916d8..a74ae08af1a7 100644 --- a/arch/blackfin/include/asm/tlb.h +++ b/arch/blackfin/include/asm/tlb.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BLACKFIN_TLB_H #define _BLACKFIN_TLB_H diff --git a/arch/blackfin/include/asm/trace.h b/arch/blackfin/include/asm/trace.h index 312b596b9731..609ad3c84189 100644 --- a/arch/blackfin/include/asm/trace.h +++ b/arch/blackfin/include/asm/trace.h @@ -1,6 +1,9 @@ /* - * Common header file for blackfin family of processors. + * header file for hardware trace functions * + * Copyright 2007-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ #ifndef _BLACKFIN_TRACE_ diff --git a/arch/blackfin/include/asm/traps.h b/arch/blackfin/include/asm/traps.h index 3cdc454cde23..9fe0da612c09 100644 --- a/arch/blackfin/include/asm/traps.h +++ b/arch/blackfin/include/asm/traps.h @@ -1,13 +1,10 @@ /* - * linux/include/asm/traps.h + * Copyright 2004-2009 Analog Devices Inc. + * 2001 Lineo, Inc + * Tony Kou + * 1993 Hamish Macdonald * - * Copyright (C) 1993 Hamish Macdonald - * - * Lineo, Inc Jul 2001 Tony Kou - * - * This file is subject to the terms and conditions of the GNU General Public - * License. See the file COPYING in the main directory of this archive - * for more details. + * Licensed under the GPL-2 */ #ifndef _BFIN_TRAPS_H diff --git a/arch/blackfin/include/asm/uaccess.h b/arch/blackfin/include/asm/uaccess.h index 2f469a1f80fb..c03b8532aad3 100644 --- a/arch/blackfin/include/asm/uaccess.h +++ b/arch/blackfin/include/asm/uaccess.h @@ -1,4 +1,7 @@ -/* Changes made by Lineo Inc. May 2001 +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. * * Based on: include/asm-m68knommu/uaccess.h */ diff --git a/arch/blackfin/include/asm/unistd.h b/arch/blackfin/include/asm/unistd.h index 02b1529dad57..779be02a910a 100644 --- a/arch/blackfin/include/asm/unistd.h +++ b/arch/blackfin/include/asm/unistd.h @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef __ASM_BFIN_UNISTD_H #define __ASM_BFIN_UNISTD_H /* diff --git a/arch/blackfin/kernel/asm-offsets.c b/arch/blackfin/kernel/asm-offsets.c index f05d1b99b0ef..bd32c09b9349 100644 --- a/arch/blackfin/kernel/asm-offsets.c +++ b/arch/blackfin/kernel/asm-offsets.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/kernel/asm-offsets.c - * Based on: - * Author: + * generate definitions needed by assembly language modules * - * Created: - * Description: generate definitions needed by assembly language modules. + * Copyright 2004-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/stddef.h> diff --git a/arch/blackfin/kernel/bfin_dma_5xx.c b/arch/blackfin/kernel/bfin_dma_5xx.c index 384868dedac3..1f170216d2f9 100644 --- a/arch/blackfin/kernel/bfin_dma_5xx.c +++ b/arch/blackfin/kernel/bfin_dma_5xx.c @@ -2,6 +2,7 @@ * bfin_dma_5xx.c - Blackfin DMA implementation * * Copyright 2004-2008 Analog Devices Inc. + * * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/kernel/bfin_gpio.c b/arch/blackfin/kernel/bfin_gpio.c index fc4681c0170e..22705eeff34f 100644 --- a/arch/blackfin/kernel/bfin_gpio.c +++ b/arch/blackfin/kernel/bfin_gpio.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/kernel/bfin_gpio.c - * Based on: - * Author: Michael Hennerich (hennerich@blackfin.uclinux.org) + * GPIO Abstraction Layer * - * Created: - * Description: GPIO Abstraction Layer + * Copyright 2006-2009 Analog Devices Inc. * - * Modified: - * Copyright 2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/delay.h> diff --git a/arch/blackfin/kernel/cplb-mpu/cplbinit.c b/arch/blackfin/kernel/cplb-mpu/cplbinit.c index 36193eed9a1f..f7b9cdce8239 100644 --- a/arch/blackfin/kernel/cplb-mpu/cplbinit.c +++ b/arch/blackfin/kernel/cplb-mpu/cplbinit.c @@ -1,25 +1,11 @@ /* * Blackfin CPLB initialization * - * Copyright 2004-2007 Analog Devices Inc. + * Copyright 2008-2009 Analog Devices Inc. * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ + #include <linux/module.h> #include <asm/blackfin.h> diff --git a/arch/blackfin/kernel/cplb-mpu/cplbmgr.c b/arch/blackfin/kernel/cplb-mpu/cplbmgr.c index 8e1e9e9e9632..69e0e530d70f 100644 --- a/arch/blackfin/kernel/cplb-mpu/cplbmgr.c +++ b/arch/blackfin/kernel/cplb-mpu/cplbmgr.c @@ -1,22 +1,11 @@ /* - * Blackfin CPLB exception handling. - * Copyright 2004-2007 Analog Devices Inc. + * Blackfin CPLB exception handling for when MPU in on * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. + * Copyright 2008-2009 Analog Devices Inc. * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ + #include <linux/module.h> #include <linux/mm.h> diff --git a/arch/blackfin/kernel/cplb-nompu/cplbinit.c b/arch/blackfin/kernel/cplb-nompu/cplbinit.c index 5d8ad503f82a..fd9a2f31e686 100644 --- a/arch/blackfin/kernel/cplb-nompu/cplbinit.c +++ b/arch/blackfin/kernel/cplb-nompu/cplbinit.c @@ -1,24 +1,9 @@ /* * Blackfin CPLB initialization * - * Copyright 2004-2007 Analog Devices Inc. + * Copyright 2007-2009 Analog Devices Inc. * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/kernel/cplb-nompu/cplbmgr.c b/arch/blackfin/kernel/cplb-nompu/cplbmgr.c index d9ea46c6e41a..5b88861d6183 100644 --- a/arch/blackfin/kernel/cplb-nompu/cplbmgr.c +++ b/arch/blackfin/kernel/cplb-nompu/cplbmgr.c @@ -1,26 +1,14 @@ /* - * File: arch/blackfin/kernel/cplb-nompu-c/cplbmgr.c * Based on: arch/blackfin/kernel/cplb-mpu/cplbmgr.c * Author: Michael McTernan <mmcternan@airvana.com> * - * Created: 01Nov2008 * Description: CPLB miss handler. * * Modified: * Copyright 2008 Airvana Inc. - * Copyright 2004-2007 Analog Devices Inc. + * Copyright 2008-2009 Analog Devices Inc. * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Licensed under the GPL-2 or later */ #include <linux/kernel.h> diff --git a/arch/blackfin/kernel/cplbinfo.c b/arch/blackfin/kernel/cplbinfo.c index 64d78300dd08..0bdaa517a501 100644 --- a/arch/blackfin/kernel/cplbinfo.c +++ b/arch/blackfin/kernel/cplbinfo.c @@ -2,6 +2,7 @@ * arch/blackfin/kernel/cplbinfo.c - display CPLB status * * Copyright 2004-2008 Analog Devices Inc. + * * Licensed under the GPL-2 or later. */ @@ -111,24 +112,21 @@ static const struct seq_operations cplbinfo_sops = { .show = cplbinfo_show, }; +#define CPLBINFO_DCPLB_FLAG 0x80000000 + static int cplbinfo_open(struct inode *inode, struct file *file) { - char buf[256], *path, *p; + struct proc_dir_entry *pde = PDE(file->f_path.dentry->d_inode); + char cplb_type; unsigned int cpu; - char *s_cpu, *s_cplb; int ret; struct seq_file *m; struct cplbinfo_data *cdata; - path = d_path(&file->f_path, buf, sizeof(buf)); - if (IS_ERR(path)) - return PTR_ERR(path); - s_cpu = strstr(path, "/cpu"); - s_cplb = strrchr(path, '/'); - if (!s_cpu || !s_cplb) - return -EINVAL; + cpu = (unsigned int)pde->data; + cplb_type = cpu & CPLBINFO_DCPLB_FLAG ? 'D' : 'I'; + cpu &= ~CPLBINFO_DCPLB_FLAG; - cpu = simple_strtoul(s_cpu + 4, &p, 10); if (!cpu_online(cpu)) return -ENODEV; @@ -139,7 +137,7 @@ static int cplbinfo_open(struct inode *inode, struct file *file) cdata = m->private; cdata->pos = 0; - cdata->cplb_type = toupper(s_cplb[1]); + cdata->cplb_type = cplb_type; cplbinfo_seq_init(cdata, cpu); return 0; @@ -168,8 +166,10 @@ static int __init cplbinfo_init(void) if (!cpu_dir) return -ENOMEM; - proc_create("icplb", S_IRUGO, cpu_dir, &cplbinfo_fops); - proc_create("dcplb", S_IRUGO, cpu_dir, &cplbinfo_fops); + proc_create_data("icplb", S_IRUGO, cpu_dir, &cplbinfo_fops, + (void *)cpu); + proc_create_data("dcplb", S_IRUGO, cpu_dir, &cplbinfo_fops, + (void *)(cpu | CPLBINFO_DCPLB_FLAG)); } return 0; diff --git a/arch/blackfin/kernel/dma-mapping.c b/arch/blackfin/kernel/dma-mapping.c index 2f62a9f4058a..e74e74d7733f 100644 --- a/arch/blackfin/kernel/dma-mapping.c +++ b/arch/blackfin/kernel/dma-mapping.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/kernel/dma-mapping.c - * Based on: - * Author: + * Dynamic DMA mapping support * - * Created: - * Description: Dynamic DMA mapping support. + * Copyright 2005-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/types.h> diff --git a/arch/blackfin/kernel/early_printk.c b/arch/blackfin/kernel/early_printk.c index 931c78b5ea1f..84ed8375113c 100644 --- a/arch/blackfin/kernel/early_printk.c +++ b/arch/blackfin/kernel/early_printk.c @@ -1,25 +1,10 @@ /* - * File: arch/blackfin/kernel/early_printk.c - * Based on: arch/x86_64/kernel/early_printk.c - * Author: Robin Getz <rgetz@blackfin.uclinux.org + * allow a console to be used for early printk + * derived from arch/x86/kernel/early_printk.c * - * Created: 14Aug2007 - * Description: allow a console to be used for early printk + * Copyright 2007-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Licensed under the GPL-2 */ #include <linux/kernel.h> diff --git a/arch/blackfin/kernel/entry.S b/arch/blackfin/kernel/entry.S index 3f8769b7db54..f27dc2292e1b 100644 --- a/arch/blackfin/kernel/entry.S +++ b/arch/blackfin/kernel/entry.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/entry.S - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/linkage.h> diff --git a/arch/blackfin/kernel/fixed_code.S b/arch/blackfin/kernel/fixed_code.S index 0d2d9e0968c8..0565917f23ba 100644 --- a/arch/blackfin/kernel/fixed_code.S +++ b/arch/blackfin/kernel/fixed_code.S @@ -6,7 +6,12 @@ * These are aligned to 16 bytes, so that we have some space to replace * these sequences with something else (e.g. kernel traps if we ever do * BF561 SMP). + * + * Copyright 2007-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. */ + #include <linux/linkage.h> #include <linux/init.h> #include <linux/unistd.h> diff --git a/arch/blackfin/kernel/flat.c b/arch/blackfin/kernel/flat.c index d188b2430536..a88daddbf074 100644 --- a/arch/blackfin/kernel/flat.c +++ b/arch/blackfin/kernel/flat.c @@ -1,21 +1,7 @@ /* - * arch/blackfin/kernel/flat.c + * Copyright 2007 Analog Devices Inc. * - * Copyright (C) 2007 Analog Devices, Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * Licensed under the GPL-2. */ #include <linux/module.h> diff --git a/arch/blackfin/kernel/init_task.c b/arch/blackfin/kernel/init_task.c index c26c34de9f3c..118c5b9dedac 100644 --- a/arch/blackfin/kernel/init_task.c +++ b/arch/blackfin/kernel/init_task.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/init_task.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/mm.h> diff --git a/arch/blackfin/kernel/irqchip.c b/arch/blackfin/kernel/irqchip.c index 4b5fd36187d9..db9f9c91f11f 100644 --- a/arch/blackfin/kernel/irqchip.c +++ b/arch/blackfin/kernel/irqchip.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/irqchip.c - * Based on: - * Author: + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/kernel_stat.h> diff --git a/arch/blackfin/kernel/module.c b/arch/blackfin/kernel/module.c index 67fc7a56c865..a6dfa6b71e63 100644 --- a/arch/blackfin/kernel/module.c +++ b/arch/blackfin/kernel/module.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/module.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #define pr_fmt(fmt) "module %s: " fmt diff --git a/arch/blackfin/kernel/process.c b/arch/blackfin/kernel/process.c index f5b286189647..430ae39456e8 100644 --- a/arch/blackfin/kernel/process.c +++ b/arch/blackfin/kernel/process.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/kernel/process.c - * Based on: - * Author: + * Blackfin architecture-dependent process handling * - * Created: - * Description: Blackfin architecture-dependent process handling. + * Copyright 2004-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/module.h> diff --git a/arch/blackfin/kernel/ptrace.c b/arch/blackfin/kernel/ptrace.c index 30f4828277ad..0982b5d5af10 100644 --- a/arch/blackfin/kernel/ptrace.c +++ b/arch/blackfin/kernel/ptrace.c @@ -1,30 +1,8 @@ /* - * File: arch/blackfin/kernel/ptrace.c - * Based on: Taken from linux/kernel/ptrace.c - * Author: linux/kernel/ptrace.c is by Ross Biro 1/23/92, edited by Linus Torvalds + * linux/kernel/ptrace.c is by Ross Biro 1/23/92, edited by Linus Torvalds + * these modifications are Copyright 2004-2009 Analog Devices Inc. * - * Created: 1/23/92 - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 */ #include <linux/kernel.h> diff --git a/arch/blackfin/kernel/setup.c b/arch/blackfin/kernel/setup.c index 369535b61ed1..c202a44d1416 100644 --- a/arch/blackfin/kernel/setup.c +++ b/arch/blackfin/kernel/setup.c @@ -1,9 +1,5 @@ /* - * arch/blackfin/kernel/setup.c - * - * Copyright 2004-2006 Analog Devices Inc. - * - * Enter bugs at http://blackfin.uclinux.org/ + * Copyright 2004-2009 Analog Devices Inc. * * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/kernel/shadow_console.c b/arch/blackfin/kernel/shadow_console.c index 8b8c7107a162..557e9fef406a 100644 --- a/arch/blackfin/kernel/shadow_console.c +++ b/arch/blackfin/kernel/shadow_console.c @@ -4,8 +4,6 @@ * * Copyright 2009 Analog Devices Inc. * - * Enter bugs at http://blackfin.uclinux.org/ - * * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/kernel/signal.c b/arch/blackfin/kernel/signal.c index dbc3bbf846be..9d90c18fab23 100644 --- a/arch/blackfin/kernel/signal.c +++ b/arch/blackfin/kernel/signal.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/signal.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/signal.h> diff --git a/arch/blackfin/kernel/sys_bfin.c b/arch/blackfin/kernel/sys_bfin.c index 3da60fb13ce4..afcef129d4e8 100644 --- a/arch/blackfin/kernel/sys_bfin.c +++ b/arch/blackfin/kernel/sys_bfin.c @@ -1,32 +1,10 @@ /* - * File: arch/blackfin/kernel/sys_bfin.c - * Based on: - * Author: + * contains various random system calls that have a non-standard + * calling sequence on the Linux/Blackfin platform. * - * Created: - * Description: This file contains various random system calls that - * have a non-standard calling sequence on the Linux/bfin - * platform. + * Copyright 2004-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/spinlock.h> @@ -91,3 +69,14 @@ asmlinkage void *sys_dma_memcpy(void *dest, const void *src, size_t len) { return safe_dma_memcpy(dest, src, len); } + +#if defined(CONFIG_FB) || defined(CONFIG_FB_MODULE) +#include <linux/fb.h> +unsigned long get_fb_unmapped_area(struct file *filp, unsigned long orig_addr, + unsigned long len, unsigned long pgoff, unsigned long flags) +{ + struct fb_info *info = filp->private_data; + return (unsigned long)info->screen_base; +} +EXPORT_SYMBOL(get_fb_unmapped_area); +#endif diff --git a/arch/blackfin/kernel/time-ts.c b/arch/blackfin/kernel/time-ts.c index f9715764383e..359cfb1815ca 100644 --- a/arch/blackfin/kernel/time-ts.c +++ b/arch/blackfin/kernel/time-ts.c @@ -1,13 +1,13 @@ /* - * linux/arch/kernel/time-ts.c - * * Based on arm clockevents implementation and old bfin time tick. * - * Copyright(C) 2008, GeoTechnologies, Vitja Makarov + * Copyright 2008-2009 Analog Devics Inc. + * 2008 GeoTechnologies + * Vitja Makarov * - * This code is licenced under the GPL version 2. For details see - * kernel-base/COPYING. + * Licensed under the GPL-2 */ + #include <linux/module.h> #include <linux/profile.h> #include <linux/interrupt.h> diff --git a/arch/blackfin/kernel/time.c b/arch/blackfin/kernel/time.c index adb54aa7d7c8..bd3b53da295e 100644 --- a/arch/blackfin/kernel/time.c +++ b/arch/blackfin/kernel/time.c @@ -14,6 +14,7 @@ #include <linux/time.h> #include <linux/irq.h> #include <linux/delay.h> +#include <linux/sched.h> #include <asm/blackfin.h> #include <asm/time.h> @@ -81,11 +82,11 @@ time_sched_init(irqreturn_t(*timer_routine) (int, void *)) #endif } +#ifdef CONFIG_ARCH_USES_GETTIMEOFFSET /* * Should return useconds since last timer tick */ -#ifndef CONFIG_GENERIC_TIME -static unsigned long gettimeoffset(void) +u32 arch_gettimeoffset(void) { unsigned long offset; unsigned long clocks_per_jiffy; @@ -184,65 +185,6 @@ void __init time_init(void) time_sched_init(timer_interrupt); } -#ifndef CONFIG_GENERIC_TIME -void do_gettimeofday(struct timeval *tv) -{ - unsigned long flags; - unsigned long seq; - unsigned long usec, sec; - - do { - seq = read_seqbegin_irqsave(&xtime_lock, flags); - usec = gettimeoffset(); - sec = xtime.tv_sec; - usec += (xtime.tv_nsec / NSEC_PER_USEC); - } - while (read_seqretry_irqrestore(&xtime_lock, seq, flags)); - - while (usec >= USEC_PER_SEC) { - usec -= USEC_PER_SEC; - sec++; - } - - tv->tv_sec = sec; - tv->tv_usec = usec; -} -EXPORT_SYMBOL(do_gettimeofday); - -int do_settimeofday(struct timespec *tv) -{ - time_t wtm_sec, sec = tv->tv_sec; - long wtm_nsec, nsec = tv->tv_nsec; - - if ((unsigned long)tv->tv_nsec >= NSEC_PER_SEC) - return -EINVAL; - - write_seqlock_irq(&xtime_lock); - /* - * This is revolting. We need to set the xtime.tv_usec - * correctly. However, the value in this location is - * is value at the last tick. - * Discover what correction gettimeofday - * would have done, and then undo it! - */ - nsec -= (gettimeoffset() * NSEC_PER_USEC); - - wtm_sec = wall_to_monotonic.tv_sec + (xtime.tv_sec - sec); - wtm_nsec = wall_to_monotonic.tv_nsec + (xtime.tv_nsec - nsec); - - set_normalized_timespec(&xtime, sec, nsec); - set_normalized_timespec(&wall_to_monotonic, wtm_sec, wtm_nsec); - - ntp_clear(); - - write_sequnlock_irq(&xtime_lock); - clock_was_set(); - - return 0; -} -EXPORT_SYMBOL(do_settimeofday); -#endif /* !CONFIG_GENERIC_TIME */ - /* * Scheduler clock - returns current time in nanosec units. */ diff --git a/arch/blackfin/kernel/traps.c b/arch/blackfin/kernel/traps.c index 56464cb8edf3..6b7325d634af 100644 --- a/arch/blackfin/kernel/traps.c +++ b/arch/blackfin/kernel/traps.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/traps.c - * Based on: - * Author: Hamish Macdonald + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: uses S/W interrupt 15 for the system calls - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #include <linux/bug.h> diff --git a/arch/blackfin/kernel/vmlinux.lds.S b/arch/blackfin/kernel/vmlinux.lds.S index ffd90fbbc8f9..10e12539000e 100644 --- a/arch/blackfin/kernel/vmlinux.lds.S +++ b/arch/blackfin/kernel/vmlinux.lds.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/kernel/vmlinux.lds.S - * Based on: none - original work - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: Tue Sep 21 2004 - * Description: Master linker script for blackfin architecture - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #define VMLINUX_SYMBOL(_sym_) _##_sym_ diff --git a/arch/blackfin/lib/ashldi3.c b/arch/blackfin/lib/ashldi3.c index a8c279e9b192..ab69d8768afc 100644 --- a/arch/blackfin/lib/ashldi3.c +++ b/arch/blackfin/lib/ashldi3.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/ashldi3.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include "gcclib.h" diff --git a/arch/blackfin/lib/ashrdi3.c b/arch/blackfin/lib/ashrdi3.c index a0d3419329ca..b5b351e82e10 100644 --- a/arch/blackfin/lib/ashrdi3.c +++ b/arch/blackfin/lib/ashrdi3.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/ashrdi3.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include "gcclib.h" diff --git a/arch/blackfin/lib/checksum.c b/arch/blackfin/lib/checksum.c index cd605e7d8518..c62969dc1bbb 100644 --- a/arch/blackfin/lib/checksum.c +++ b/arch/blackfin/lib/checksum.c @@ -1,32 +1,12 @@ /* - * File: arch/blackfin/lib/checksum.c - * Based on: none - original work - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: An implementation of the TCP/IP protocol suite for the LINUX - * operating system. INET is implemented using the BSD Socket - * interface as the means of communication with the user level. + * Licensed under the GPL-2 or later. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. + * An implementation of the TCP/IP protocol suite for the LINUX operating + * system. INET is implemented using the BSD Socket interface as the + * means of communication with the user level. * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ #include <linux/module.h> diff --git a/arch/blackfin/lib/divsi3.S b/arch/blackfin/lib/divsi3.S index 2ac59c70dd94..f89c5a49c47b 100644 --- a/arch/blackfin/lib/divsi3.S +++ b/arch/blackfin/lib/divsi3.S @@ -1,10 +1,9 @@ /* - * File: arch/blackfin/lib/divsi3.S - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: 16 / 32 bit signed division. + * Licensed under the ADI BSD license or the GPL-2 (or later) + * + * 16 / 32 bit signed division. * Special cases : * 1) If(numerator == 0) * return 0 @@ -22,25 +21,6 @@ * R0 - Quotient (o) * Registers Used : R2-R7,P0-P2 * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ .global ___divsi3; diff --git a/arch/blackfin/lib/gcclib.h b/arch/blackfin/lib/gcclib.h index 9ccd39a135ee..724f07f14f8d 100644 --- a/arch/blackfin/lib/gcclib.h +++ b/arch/blackfin/lib/gcclib.h @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/gcclib.h - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #define BITS_PER_UNIT 8 diff --git a/arch/blackfin/lib/lshrdi3.c b/arch/blackfin/lib/lshrdi3.c index e57bf6fbdf3f..53f1741047e5 100644 --- a/arch/blackfin/lib/lshrdi3.c +++ b/arch/blackfin/lib/lshrdi3.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/lshrdi3.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include "gcclib.h" diff --git a/arch/blackfin/lib/memchr.S b/arch/blackfin/lib/memchr.S index 5da428134d32..542e40f8775f 100644 --- a/arch/blackfin/lib/memchr.S +++ b/arch/blackfin/lib/memchr.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/memchr.S - * Based on: - * Author: + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #include <linux/linkage.h> diff --git a/arch/blackfin/lib/memcmp.S b/arch/blackfin/lib/memcmp.S index 219fa2877c62..ce5b9f1a8267 100644 --- a/arch/blackfin/lib/memcmp.S +++ b/arch/blackfin/lib/memcmp.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/memcmp.S - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #include <linux/linkage.h> diff --git a/arch/blackfin/lib/memcpy.S b/arch/blackfin/lib/memcpy.S index e654a18a0754..c31bf22aab19 100644 --- a/arch/blackfin/lib/memcpy.S +++ b/arch/blackfin/lib/memcpy.S @@ -1,36 +1,13 @@ /* - * File: arch/blackfin/lib/memcpy.S - * Based on: - * Author: + * internal version of memcpy(), issued by the compiler to copy blocks of + * data around. This is really memmove() - it has to be able to deal with + * possible overlaps, because that ambiguity is when the compiler gives up + * and calls a function. We have our own, internal version so that we get + * something we trust, even if the user has redefined the normal symbol. * - * Created: - * Description: internal version of memcpy(), issued by the compiler - * to copy blocks of data around. - * This is really memmove() - it has to be able to deal with - * possible overlaps, because that ambiguity is when the compiler - * gives up and calls a function. We have our own, internal version - * so that we get something we trust, even if the user has redefined - * the normal symbol. + * Copyright 2004-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #include <linux/linkage.h> diff --git a/arch/blackfin/lib/memmove.S b/arch/blackfin/lib/memmove.S index 33f8653145b7..80c240acac60 100644 --- a/arch/blackfin/lib/memmove.S +++ b/arch/blackfin/lib/memmove.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/memmove.S - * Based on: - * Author: + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #include <linux/linkage.h> diff --git a/arch/blackfin/lib/memset.S b/arch/blackfin/lib/memset.S index 8159136a29ea..c30d99b10969 100644 --- a/arch/blackfin/lib/memset.S +++ b/arch/blackfin/lib/memset.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/memset.S - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #include <linux/linkage.h> diff --git a/arch/blackfin/lib/modsi3.S b/arch/blackfin/lib/modsi3.S index ca1dd3973b39..8b0c7d4052af 100644 --- a/arch/blackfin/lib/modsi3.S +++ b/arch/blackfin/lib/modsi3.S @@ -1,36 +1,12 @@ /* - * File: arch/blackfin/lib/modsi3.S - * Based on: - * Author: + * This program computes 32 bit signed remainder. It calls div32 function + * for quotient estimation. + * Registers in: R0, R1 = Numerator/ Denominator + * Registers out: R0 = Remainder * - * Created: - * Description: This program computes 32 bit signed remainder. It calls div32 function - * for quotient estimation. + * Copyright 2004-2009 Analog Devices Inc. * - * Registers used : - * Numerator/ Denominator in R0, R1 - * R0 - returns remainder. - * R2-R7 - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ .global ___modsi3; diff --git a/arch/blackfin/lib/muldi3.S b/arch/blackfin/lib/muldi3.S index abde120ee230..953a38a1d1d1 100644 --- a/arch/blackfin/lib/muldi3.S +++ b/arch/blackfin/lib/muldi3.S @@ -1,3 +1,9 @@ +/* + * Copyright 2008 Analog Devices Inc. + * + * Licensed under the ADI BSD license or the GPL-2 (or later) + */ + .align 2 .global ___muldi3; .type ___muldi3, STT_FUNC; diff --git a/arch/blackfin/lib/outs.S b/arch/blackfin/lib/outs.S index 4685b7aa0080..250f4d4b9436 100644 --- a/arch/blackfin/lib/outs.S +++ b/arch/blackfin/lib/outs.S @@ -1,30 +1,11 @@ /* - * File: arch/blackfin/lib/outs.S - * Based on: - * Author: Bas Vermeulen <bas@buyways.nl> + * Implementation of outs{bwl} for BlackFin processors using zero overhead loops. * - * Created: Tue Mar 22 15:27:24 CEST 2005 - * Description: Implementation of outs{bwl} for BlackFin processors using zero overhead loops. + * Copyright 2005-2009 Analog Devices Inc. + * 2005 BuyWays BV + * Bas Vermeulen <bas@buyways.nl> * - * Modified: Copyright (C) 2005 Bas Vermeulen, BuyWays BV <bas@buyways.nl> - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2. */ #include <linux/linkage.h> diff --git a/arch/blackfin/lib/smulsi3_highpart.S b/arch/blackfin/lib/smulsi3_highpart.S index e383cd3eca5d..99ee8c5de38b 100644 --- a/arch/blackfin/lib/smulsi3_highpart.S +++ b/arch/blackfin/lib/smulsi3_highpart.S @@ -1,3 +1,9 @@ +/* + * Copyright 2007 Analog Devices Inc. + * + * Licensed under the ADI BSD license or the GPL-2 (or later) + */ + .align 2 .global ___smulsi3_highpart; .type ___smulsi3_highpart, STT_FUNC; diff --git a/arch/blackfin/lib/udivsi3.S b/arch/blackfin/lib/udivsi3.S index 58fd96d74766..97e904315ec6 100644 --- a/arch/blackfin/lib/udivsi3.S +++ b/arch/blackfin/lib/udivsi3.S @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/lib/udivsi3.S - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #include <linux/linkage.h> diff --git a/arch/blackfin/lib/umodsi3.S b/arch/blackfin/lib/umodsi3.S index 4f2b76ee7626..168eba7c64c8 100644 --- a/arch/blackfin/lib/umodsi3.S +++ b/arch/blackfin/lib/umodsi3.S @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/lib/umodsi3.S - * Based on: - * Author: + * libgcc1 routines for Blackfin 5xx * - * Created: - * Description: libgcc1 routines for Blackfin 5xx + * Copyright 2004-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifdef CONFIG_ARITHMETIC_OPS_L1 diff --git a/arch/blackfin/lib/umulsi3_highpart.S b/arch/blackfin/lib/umulsi3_highpart.S index 67b799351e3e..051824a6ed00 100644 --- a/arch/blackfin/lib/umulsi3_highpart.S +++ b/arch/blackfin/lib/umulsi3_highpart.S @@ -1,3 +1,9 @@ +/* + * Copyright 2007 Analog Devices Inc. + * + * Licensed under the ADI BSD license or the GPL-2 (or later) + */ + .align 2 .global ___umulsi3_highpart; .type ___umulsi3_highpart, STT_FUNC; diff --git a/arch/blackfin/mach-bf518/boards/ezbrd.c b/arch/blackfin/mach-bf518/boards/ezbrd.c index 03e4a9941f01..01975c017116 100644 --- a/arch/blackfin/mach-bf518/boards/ezbrd.c +++ b/arch/blackfin/mach-bf518/boards/ezbrd.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf518/boards/ezbrd.c - * Based on: arch/blackfin/mach-bf527/boards/ezbrd.c - * Author: Bryan Wu <cooloney@kernel.org> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -571,19 +549,6 @@ static struct platform_device bf51x_sdh_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - static const unsigned int cclk_vlev_datasheet[] = { VRPAIR(VLEV_100, 400000000), @@ -660,8 +625,6 @@ static struct platform_device *stamp_devices[] __initdata = { #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) &ezbrd_flash_device, #endif - - &bfin_gpios_device, }; static int __init ezbrd_init(void) diff --git a/arch/blackfin/mach-bf518/dma.c b/arch/blackfin/mach-bf518/dma.c index 698e88ca5104..78b43605a0b5 100644 --- a/arch/blackfin/mach-bf518/dma.c +++ b/arch/blackfin/mach-bf518/dma.c @@ -1,31 +1,11 @@ /* - * File: arch/blackfin/mach-bf518/dma.c - * Based on: - * Author: Bryan Wu <cooloney@kernel.org> + * the simple DMA Implementation for Blackfin * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin + * Copyright 2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ + #include <linux/module.h> #include <asm/blackfin.h> diff --git a/arch/blackfin/mach-bf518/include/mach/bf518.h b/arch/blackfin/mach-bf518/include/mach/bf518.h index 78da1a07ee73..856b330ecf0b 100644 --- a/arch/blackfin/mach-bf518/include/mach/bf518.h +++ b/arch/blackfin/mach-bf518/include/mach/bf518.h @@ -1,30 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/bf518.h - * Based on: include/asm-blackfin/mach-bf527/bf527.h - * Author: Michael Hennerich (michael.hennerich@analog.com) + * Copyright 2008 Analog Devices Inc. * - * Created: - * Description: SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF518 - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __MACH_BF518_H__ diff --git a/arch/blackfin/mach-bf518/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf518/include/mach/bfin_serial_5xx.h index dbade93395eb..970d310021e7 100644 --- a/arch/blackfin/mach-bf518/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf518/include/mach/bfin_serial_5xx.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf518/bfin_serial_5xx.h - * based on: - * author: + * Copyright 2008-2009 Analog Devices Inc. * - * created: - * description: - * blackfin serial driver head file - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later */ #include <linux/serial.h> diff --git a/arch/blackfin/mach-bf518/include/mach/blackfin.h b/arch/blackfin/mach-bf518/include/mach/blackfin.h index 83421d393148..6cfb246aebec 100644 --- a/arch/blackfin/mach-bf518/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf518/include/mach/blackfin.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/blackfin.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _MACH_BLACKFIN_H_ diff --git a/arch/blackfin/mach-bf518/include/mach/cdefBF512.h b/arch/blackfin/mach-bf518/include/mach/cdefBF512.h index 820c13c4daaa..493020d0a65a 100644 --- a/arch/blackfin/mach-bf518/include/mach/cdefBF512.h +++ b/arch/blackfin/mach-bf518/include/mach/cdefBF512.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/cdefbf512.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _CDEF_BF512_H diff --git a/arch/blackfin/mach-bf518/include/mach/cdefBF514.h b/arch/blackfin/mach-bf518/include/mach/cdefBF514.h index dfe492dfe54e..e1d99911025d 100644 --- a/arch/blackfin/mach-bf518/include/mach/cdefBF514.h +++ b/arch/blackfin/mach-bf518/include/mach/cdefBF514.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/cdefbf514.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF514_H diff --git a/arch/blackfin/mach-bf518/include/mach/cdefBF516.h b/arch/blackfin/mach-bf518/include/mach/cdefBF516.h index 14df43d4677a..6b364eda4947 100644 --- a/arch/blackfin/mach-bf518/include/mach/cdefBF516.h +++ b/arch/blackfin/mach-bf518/include/mach/cdefBF516.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/cdefbf516.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF516_H diff --git a/arch/blackfin/mach-bf518/include/mach/cdefBF518.h b/arch/blackfin/mach-bf518/include/mach/cdefBF518.h index bafb370cfb3c..929b90650bd4 100644 --- a/arch/blackfin/mach-bf518/include/mach/cdefBF518.h +++ b/arch/blackfin/mach-bf518/include/mach/cdefBF518.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/cdefbf518.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF518_H @@ -211,6 +186,47 @@ #define bfin_read_EMAC_TXC_ABORT() bfin_read32(EMAC_TXC_ABORT) #define bfin_write_EMAC_TXC_ABORT(val) bfin_write32(EMAC_TXC_ABORT, val) +#define bfin_read_EMAC_PTP_CTL() bfin_read16(EMAC_PTP_CTL) +#define bfin_write_EMAC_PTP_CTL(val) bfin_write16(EMAC_PTP_CTL, val) +#define bfin_read_EMAC_PTP_IE() bfin_read16(EMAC_PTP_IE) +#define bfin_write_EMAC_PTP_IE(val) bfin_write16(EMAC_PTP_IE, val) +#define bfin_read_EMAC_PTP_ISTAT() bfin_read16(EMAC_PTP_ISTAT) +#define bfin_write_EMAC_PTP_ISTAT(val) bfin_write16(EMAC_PTP_ISTAT, val) +#define bfin_read_EMAC_PTP_FOFF() bfin_read32(EMAC_PTP_FOFF) +#define bfin_write_EMAC_PTP_FOFF(val) bfin_write32(EMAC_PTP_FOFF, val) +#define bfin_read_EMAC_PTP_FV1() bfin_read32(EMAC_PTP_FV1) +#define bfin_write_EMAC_PTP_FV1(val) bfin_write32(EMAC_PTP_FV1, val) +#define bfin_read_EMAC_PTP_FV2() bfin_read32(EMAC_PTP_FV2) +#define bfin_write_EMAC_PTP_FV2(val) bfin_write32(EMAC_PTP_FV2, val) +#define bfin_read_EMAC_PTP_FV3() bfin_read32(EMAC_PTP_FV3) +#define bfin_write_EMAC_PTP_FV3(val) bfin_write32(EMAC_PTP_FV3, val) +#define bfin_read_EMAC_PTP_ADDEND() bfin_read32(EMAC_PTP_ADDEND) +#define bfin_write_EMAC_PTP_ADDEND(val) bfin_write32(EMAC_PTP_ADDEND, val) +#define bfin_read_EMAC_PTP_ACCR() bfin_read32(EMAC_PTP_ACCR) +#define bfin_write_EMAC_PTP_ACCR(val) bfin_write32(EMAC_PTP_ACCR, val) +#define bfin_read_EMAC_PTP_OFFSET() bfin_read32(EMAC_PTP_OFFSET) +#define bfin_write_EMAC_PTP_OFFSET(val) bfin_write32(EMAC_PTP_OFFSET, val) +#define bfin_read_EMAC_PTP_TIMELO() bfin_read32(EMAC_PTP_TIMELO) +#define bfin_write_EMAC_PTP_TIMELO(val) bfin_write32(EMAC_PTP_TIMELO, val) +#define bfin_read_EMAC_PTP_TIMEHI() bfin_read32(EMAC_PTP_TIMEHI) +#define bfin_write_EMAC_PTP_TIMEHI(val) bfin_write32(EMAC_PTP_TIMEHI, val) +#define bfin_read_EMAC_PTP_RXSNAPLO() bfin_read32(EMAC_PTP_RXSNAPLO) +#define bfin_read_EMAC_PTP_RXSNAPHI() bfin_read32(EMAC_PTP_RXSNAPHI) +#define bfin_read_EMAC_PTP_TXSNAPLO() bfin_read32(EMAC_PTP_TXSNAPLO) +#define bfin_read_EMAC_PTP_TXSNAPHI() bfin_read32(EMAC_PTP_TXSNAPHI) +#define bfin_read_EMAC_PTP_ALARMLO() bfin_read32(EMAC_PTP_ALARMLO) +#define bfin_write_EMAC_PTP_ALARMLO(val) bfin_write32(EMAC_PTP_ALARMLO, val) +#define bfin_read_EMAC_PTP_ALARMHI() bfin_read32(EMAC_PTP_ALARMHI) +#define bfin_write_EMAC_PTP_ALARMHI(val) bfin_write32(EMAC_PTP_ALARMHI, val) +#define bfin_read_EMAC_PTP_ID_OFF() bfin_read16(EMAC_PTP_ID_OFF) +#define bfin_write_EMAC_PTP_ID_OFF(val) bfin_write16(EMAC_PTP_ID_OFF, val) +#define bfin_read_EMAC_PTP_ID_SNAP() bfin_read32(EMAC_PTP_ID_SNAP) +#define bfin_write_EMAC_PTP_ID_SNAP(val) bfin_write32(EMAC_PTP_ID_SNAP, val) +#define bfin_read_EMAC_PTP_PPS_STARTHI() bfin_read32(EMAC_PTP_PPS_STARTHI) +#define bfin_write_EMAC_PTP_PPS_STARTHI(val) bfin_write32(EMAC_PTP_PPS_STARTHI, val) +#define bfin_read_EMAC_PTP_PPS_PERIOD() bfin_read32(EMAC_PTP_PPS_PERIOD) +#define bfin_write_EMAC_PTP_PPS_PERIOD(val) bfin_write32(EMAC_PTP_PPS_PERIOD, val) + /* Removable Storage Interface Registers */ #define bfin_read_RSI_PWR_CTL() bfin_read16(RSI_PWR_CONTROL) diff --git a/arch/blackfin/mach-bf518/include/mach/cdefBF51x_base.h b/arch/blackfin/mach-bf518/include/mach/cdefBF51x_base.h index ee3d4733369c..1d970df7aee9 100644 --- a/arch/blackfin/mach-bf518/include/mach/cdefBF51x_base.h +++ b/arch/blackfin/mach-bf518/include/mach/cdefBF51x_base.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/cdefBF51x_base.h - * Based on: - * Author: + * Copyright 2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF52X_H diff --git a/arch/blackfin/mach-bf518/include/mach/defBF512.h b/arch/blackfin/mach-bf518/include/mach/defBF512.h index a96ca90154dd..9b505bb0cb2d 100644 --- a/arch/blackfin/mach-bf518/include/mach/defBF512.h +++ b/arch/blackfin/mach-bf518/include/mach/defBF512.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/defBF512.h - * Based on: - * Author: + * Copyright 2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF512_H diff --git a/arch/blackfin/mach-bf518/include/mach/defBF514.h b/arch/blackfin/mach-bf518/include/mach/defBF514.h index 56ee5a7c2007..b5adca23a788 100644 --- a/arch/blackfin/mach-bf518/include/mach/defBF514.h +++ b/arch/blackfin/mach-bf518/include/mach/defBF514.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/defBF514.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF514_H diff --git a/arch/blackfin/mach-bf518/include/mach/defBF516.h b/arch/blackfin/mach-bf518/include/mach/defBF516.h index dfc93843517d..7eb18774d727 100644 --- a/arch/blackfin/mach-bf518/include/mach/defBF516.h +++ b/arch/blackfin/mach-bf518/include/mach/defBF516.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/defBF516.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF516_H diff --git a/arch/blackfin/mach-bf518/include/mach/defBF518.h b/arch/blackfin/mach-bf518/include/mach/defBF518.h index 6e982abf4ede..794cf06eb5ba 100644 --- a/arch/blackfin/mach-bf518/include/mach/defBF518.h +++ b/arch/blackfin/mach-bf518/include/mach/defBF518.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/defBF518.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF518_H @@ -648,4 +624,32 @@ #define RWR 0x1 /* Read Wait Request */ +/* Bit masks for EMAC_PTP_CTL */ + +#define PTP_EN 0x1 /* Enable the PTP_TSYNC module */ +#define TL 0x2 /* Timestamp lock control */ +#define ASEN 0x10 /* Auxiliary snapshot control */ +#define PPSEN 0x80 /* Pulse-per-second (PPS) control */ +#define CKOEN 0x2000 /* Clock output control */ + +/* Bit masks for EMAC_PTP_IE */ + +#define ALIE 0x1 /* Alarm interrupt enable */ +#define RXEIE 0x2 /* Receive event interrupt enable */ +#define RXGIE 0x4 /* Receive general interrupt enable */ +#define TXIE 0x8 /* Transmit interrupt enable */ +#define RXOVE 0x10 /* Receive overrun error interrupt enable */ +#define TXOVE 0x20 /* Transmit overrun error interrupt enable */ +#define ASIE 0x40 /* Auxiliary snapshot interrupt enable */ + +/* Bit masks for EMAC_PTP_ISTAT */ + +#define ALS 0x1 /* Alarm status */ +#define RXEL 0x2 /* Receive event interrupt status */ +#define RXGL 0x4 /* Receive general interrupt status */ +#define TXTL 0x8 /* Transmit snapshot status */ +#define RXOV 0x10 /* Receive snapshot overrun status */ +#define TXOV 0x20 /* Transmit snapshot overrun status */ +#define ASL 0x40 /* Auxiliary snapshot interrupt status */ + #endif /* _DEF_BF518_H */ diff --git a/arch/blackfin/mach-bf518/include/mach/defBF51x_base.h b/arch/blackfin/mach-bf518/include/mach/defBF51x_base.h index 1bec8d1c2a73..e06f4112c695 100644 --- a/arch/blackfin/mach-bf518/include/mach/defBF51x_base.h +++ b/arch/blackfin/mach-bf518/include/mach/defBF51x_base.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf518/defBF51x_base.h - * Based on: - * Author: + * Copyright 2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF51X_H diff --git a/arch/blackfin/mach-bf518/include/mach/gpio.h b/arch/blackfin/mach-bf518/include/mach/gpio.h index 9757683c3948..bbab2d76499c 100644 --- a/arch/blackfin/mach-bf518/include/mach/gpio.h +++ b/arch/blackfin/mach-bf518/include/mach/gpio.h @@ -1,7 +1,4 @@ /* - * File: arch/blackfin/mach-bf518/include/mach/gpio.h - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * * Copyright (C) 2008 Analog Devices Inc. * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-bf518/include/mach/irq.h b/arch/blackfin/mach-bf518/include/mach/irq.h index 3ff0f093313d..14e52ec7afa5 100644 --- a/arch/blackfin/mach-bf518/include/mach/irq.h +++ b/arch/blackfin/mach-bf518/include/mach/irq.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf518/irq.h - * based on: include/asm-blackfin/mach-bf527/irq.h - * author: Michael Hennerich (michael.hennerich@analog.com) + * Copyright 2008 Analog Devices Inc. * - * created: - * description: - * system mmr register map - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later */ #ifndef _BF518_IRQ_H_ diff --git a/arch/blackfin/mach-bf518/include/mach/portmux.h b/arch/blackfin/mach-bf518/include/mach/portmux.h index a0fc77fd3315..e352910f7f99 100644 --- a/arch/blackfin/mach-bf518/include/mach/portmux.h +++ b/arch/blackfin/mach-bf518/include/mach/portmux.h @@ -1,3 +1,9 @@ +/* + * Copyright 2008-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later + */ + #ifndef _MACH_PORTMUX_H_ #define _MACH_PORTMUX_H_ diff --git a/arch/blackfin/mach-bf518/ints-priority.c b/arch/blackfin/mach-bf518/ints-priority.c index 3151fd5501ca..bb05bef34ec0 100644 --- a/arch/blackfin/mach-bf518/ints-priority.c +++ b/arch/blackfin/mach-bf518/ints-priority.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf518/ints-priority.c - * Based on: arch/blackfin/mach-bf527/ints-priority.c - * Author: Bryan Wu <cooloney@kernel.org> + * Set up the interrupt priorities * - * Created: - * Description: Set up the interrupt priorities + * Copyright 2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf527/boards/cm_bf527.c b/arch/blackfin/mach-bf527/boards/cm_bf527.c index 08a3f01c9886..f1996b13a3da 100644 --- a/arch/blackfin/mach-bf527/boards/cm_bf527.c +++ b/arch/blackfin/mach-bf527/boards/cm_bf527.c @@ -1,31 +1,10 @@ /* - * File: arch/blackfin/mach-bf527/boards/cm-bf527.c - * Based on: arch/blackfin/mach-bf537/boards/stamp.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Bluetechnix + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -616,12 +595,6 @@ static struct platform_device bfin_spi0_device = { }; #endif /* spi master and devices */ -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) -static struct platform_device bfin_fb_adv7393_device = { - .name = "bfin-adv7393", -}; -#endif - #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) static struct mtd_partition cm_partitions[] = { { @@ -786,6 +759,11 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { .irq = IRQ_PF8, }, #endif +#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) + { + I2C_BOARD_INFO("bfin-adv7393", 0x2B), + }, +#endif }; #if defined(CONFIG_SERIAL_BFIN_SPORT) || defined(CONFIG_SERIAL_BFIN_SPORT_MODULE) @@ -821,19 +799,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - static const unsigned int cclk_vlev_datasheet[] = { VRPAIR(VLEV_100, 400000000), @@ -909,10 +874,6 @@ static struct platform_device *cmbf527_devices[] __initdata = { &bfin_spi0_device, #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) - &bfin_fb_adv7393_device, -#endif - #if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) &bfin_uart_device, #endif @@ -942,8 +903,6 @@ static struct platform_device *cmbf527_devices[] __initdata = { #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) &cm_flash_device, #endif - - &bfin_gpios_device, }; static int __init cm_init(void) diff --git a/arch/blackfin/mach-bf527/boards/ezbrd.c b/arch/blackfin/mach-bf527/boards/ezbrd.c index 68b4c804364c..cad23b15d83c 100644 --- a/arch/blackfin/mach-bf527/boards/ezbrd.c +++ b/arch/blackfin/mach-bf527/boards/ezbrd.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf527/boards/ezbrd.c - * Based on: arch/blackfin/mach-bf537/boards/stamp.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -611,19 +589,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - static const unsigned int cclk_vlev_datasheet[] = { VRPAIR(VLEV_100, 400000000), @@ -732,8 +697,6 @@ static struct platform_device *stamp_devices[] __initdata = { #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) &ezbrd_flash_device, #endif - - &bfin_gpios_device, }; static int __init ezbrd_init(void) diff --git a/arch/blackfin/mach-bf527/boards/ezkit.c b/arch/blackfin/mach-bf527/boards/ezkit.c index 2849b09abe99..f09665f74ba0 100644 --- a/arch/blackfin/mach-bf527/boards/ezkit.c +++ b/arch/blackfin/mach-bf527/boards/ezkit.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf527/boards/ezkit.c - * Based on: arch/blackfin/mach-bf537/boards/stamp.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -716,12 +694,6 @@ static struct platform_device bfin_fb_device = { }; #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) -static struct platform_device bfin_fb_adv7393_device = { - .name = "bfin-adv7393", -}; -#endif - #if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) static struct resource bfin_uart_resources[] = { #ifdef CONFIG_SERIAL_BFIN_UART0 @@ -837,6 +809,11 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { .irq = IRQ_PF8, }, #endif +#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) + { + I2C_BOARD_INFO("bfin-adv7393", 0x2B), + }, +#endif }; #if defined(CONFIG_SERIAL_BFIN_SPORT) || defined(CONFIG_SERIAL_BFIN_SPORT_MODULE) @@ -905,19 +882,6 @@ static struct platform_device bfin_rotary_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - static const unsigned int cclk_vlev_datasheet[] = { VRPAIR(VLEV_100, 400000000), @@ -1001,10 +965,6 @@ static struct platform_device *stamp_devices[] __initdata = { &bf52x_t350mcqb_device, #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) - &bfin_fb_adv7393_device, -#endif - #if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) &bfin_uart_device, #endif @@ -1038,8 +998,6 @@ static struct platform_device *stamp_devices[] __initdata = { #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) &ezkit_flash_device, #endif - - &bfin_gpios_device, }; static int __init ezkit_init(void) diff --git a/arch/blackfin/mach-bf527/dma.c b/arch/blackfin/mach-bf527/dma.c index 231877578243..7bc7577d6c4f 100644 --- a/arch/blackfin/mach-bf527/dma.c +++ b/arch/blackfin/mach-bf527/dma.c @@ -1,31 +1,11 @@ /* - * File: arch/blackfin/mach-bf527/dma.c - * Based on: - * Author: + * This file contains the simple DMA Implementation for Blackfin * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin + * Copyright 2007-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ + #include <linux/module.h> #include <asm/blackfin.h> diff --git a/arch/blackfin/mach-bf527/include/mach/bf527.h b/arch/blackfin/mach-bf527/include/mach/bf527.h index 3832aab11e9a..ff68c8897087 100644 --- a/arch/blackfin/mach-bf527/include/mach/bf527.h +++ b/arch/blackfin/mach-bf527/include/mach/bf527.h @@ -1,30 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/bf527.h - * Based on: include/asm-blackfin/mach-bf537/bf537.h - * Author: Michael Hennerich (michael.hennerich@analog.com) + * Copyright 2007-2009 Analog Devices Inc. * - * Created: - * Description: SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF527 - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __MACH_BF527_H__ diff --git a/arch/blackfin/mach-bf527/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf527/include/mach/bfin_serial_5xx.h index ebd6cebc1fbc..c1d55b878b45 100644 --- a/arch/blackfin/mach-bf527/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf527/include/mach/bfin_serial_5xx.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf527/bfin_serial_5xx.h - * based on: - * author: + * Copyright 2007-2009 Analog Devices Inc. * - * created: - * description: - * blackfin serial driver head file - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later */ #include <linux/serial.h> diff --git a/arch/blackfin/mach-bf527/include/mach/blackfin.h b/arch/blackfin/mach-bf527/include/mach/blackfin.h index ea9cb0fef8bc..e7d6034f268f 100644 --- a/arch/blackfin/mach-bf527/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf527/include/mach/blackfin.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/blackfin.h - * Based on: - * Author: + * Copyright 2007-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _MACH_BLACKFIN_H_ diff --git a/arch/blackfin/mach-bf527/include/mach/cdefBF522.h b/arch/blackfin/mach-bf527/include/mach/cdefBF522.h index 663c2bbdfd91..1079af8c7aef 100644 --- a/arch/blackfin/mach-bf527/include/mach/cdefBF522.h +++ b/arch/blackfin/mach-bf527/include/mach/cdefBF522.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/cdefbf522.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF522_H diff --git a/arch/blackfin/mach-bf527/include/mach/cdefBF525.h b/arch/blackfin/mach-bf527/include/mach/cdefBF525.h index 00377eb59b75..dc3119e9f663 100644 --- a/arch/blackfin/mach-bf527/include/mach/cdefBF525.h +++ b/arch/blackfin/mach-bf527/include/mach/cdefBF525.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/cdefbf525.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF525_H diff --git a/arch/blackfin/mach-bf527/include/mach/cdefBF527.h b/arch/blackfin/mach-bf527/include/mach/cdefBF527.h index fca8db708119..d6579449ee46 100644 --- a/arch/blackfin/mach-bf527/include/mach/cdefBF527.h +++ b/arch/blackfin/mach-bf527/include/mach/cdefBF527.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/cdefbf527.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF527_H diff --git a/arch/blackfin/mach-bf527/include/mach/cdefBF52x_base.h b/arch/blackfin/mach-bf527/include/mach/cdefBF52x_base.h index 1fe76d8e0403..7014dde10dd6 100644 --- a/arch/blackfin/mach-bf527/include/mach/cdefBF52x_base.h +++ b/arch/blackfin/mach-bf527/include/mach/cdefBF52x_base.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/cdefBF52x_base.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF52X_H diff --git a/arch/blackfin/mach-bf527/include/mach/defBF522.h b/arch/blackfin/mach-bf527/include/mach/defBF522.h index 0a8cdcdf0b49..cb139a254810 100644 --- a/arch/blackfin/mach-bf527/include/mach/defBF522.h +++ b/arch/blackfin/mach-bf527/include/mach/defBF522.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/defBF522.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF522_H diff --git a/arch/blackfin/mach-bf527/include/mach/defBF525.h b/arch/blackfin/mach-bf527/include/mach/defBF525.h index 5cd7576fef76..82abefc1ef6c 100644 --- a/arch/blackfin/mach-bf527/include/mach/defBF525.h +++ b/arch/blackfin/mach-bf527/include/mach/defBF525.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/defBF525.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF525_H diff --git a/arch/blackfin/mach-bf527/include/mach/defBF527.h b/arch/blackfin/mach-bf527/include/mach/defBF527.h index f040f364afa3..570a125df025 100644 --- a/arch/blackfin/mach-bf527/include/mach/defBF527.h +++ b/arch/blackfin/mach-bf527/include/mach/defBF527.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/defBF527.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF527_H diff --git a/arch/blackfin/mach-bf527/include/mach/defBF52x_base.h b/arch/blackfin/mach-bf527/include/mach/defBF52x_base.h index 68b55d03fedf..f821700716ee 100644 --- a/arch/blackfin/mach-bf527/include/mach/defBF52x_base.h +++ b/arch/blackfin/mach-bf527/include/mach/defBF52x_base.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf527/defBF52x_base.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF52X_H diff --git a/arch/blackfin/mach-bf527/include/mach/gpio.h b/arch/blackfin/mach-bf527/include/mach/gpio.h index 06b6eebf0d49..104bff85290d 100644 --- a/arch/blackfin/mach-bf527/include/mach/gpio.h +++ b/arch/blackfin/mach-bf527/include/mach/gpio.h @@ -1,7 +1,4 @@ /* - * File: arch/blackfin/mach-bf527/include/mach/gpio.h - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * * Copyright (C) 2008 Analog Devices Inc. * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-bf527/include/mach/irq.h b/arch/blackfin/mach-bf527/include/mach/irq.h index 8ea660d8151f..aa6579a64a2f 100644 --- a/arch/blackfin/mach-bf527/include/mach/irq.h +++ b/arch/blackfin/mach-bf527/include/mach/irq.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf527/irq.h - * based on: include/asm-blackfin/mach-bf537/irq.h - * author: Michael Hennerich (michael.hennerich@analog.com) + * Copyright 2007-2008 Analog Devices Inc. * - * created: - * description: - * system mmr register map - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later */ #ifndef _BF527_IRQ_H_ diff --git a/arch/blackfin/mach-bf527/include/mach/portmux.h b/arch/blackfin/mach-bf527/include/mach/portmux.h index 72b1652be4da..d4518b6f4adf 100644 --- a/arch/blackfin/mach-bf527/include/mach/portmux.h +++ b/arch/blackfin/mach-bf527/include/mach/portmux.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later + */ + #ifndef _MACH_PORTMUX_H_ #define _MACH_PORTMUX_H_ diff --git a/arch/blackfin/mach-bf527/ints-priority.c b/arch/blackfin/mach-bf527/ints-priority.c index f8c8acd73e30..44ca215bf164 100644 --- a/arch/blackfin/mach-bf527/ints-priority.c +++ b/arch/blackfin/mach-bf527/ints-priority.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf537/ints-priority.c - * Based on: arch/blackfin/mach-bf533/ints-priority.c - * Author: Michael Hennerich (michael.hennerich@analog.com) + * Set up the interrupt priorities * - * Created: - * Description: Set up the interrupt priorities + * Copyright 2007-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf533/boards/H8606.c b/arch/blackfin/mach-bf533/boards/H8606.c index 6c2b47fe4fe4..43f43a095a99 100644 --- a/arch/blackfin/mach-bf533/boards/H8606.c +++ b/arch/blackfin/mach-bf533/boards/H8606.c @@ -1,32 +1,11 @@ /* - * File: arch/blackfin/mach-bf533/H8606.c - * Based on: arch/blackfin/mach-bf533/stamp.c - * Author: Javier Herrero <jherrero@hvsistemas.es> + * Copyright 2004-2009 Analog Devices Inc. + * 2007-2008 HV Sistemas S.L. + * Javier Herrero <jherrero@hvsistemas.es> + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2007 - * Description: Board Info File for the HV Sistemas H8606 board - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc - * Copyright 2007,2008 HV Sistemas S.L. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> diff --git a/arch/blackfin/mach-bf533/boards/blackstamp.c b/arch/blackfin/mach-bf533/boards/blackstamp.c index 8208d67e2c97..b580884848d4 100644 --- a/arch/blackfin/mach-bf533/boards/blackstamp.c +++ b/arch/blackfin/mach-bf533/boards/blackstamp.c @@ -1,16 +1,10 @@ /* - * File: arch/blackfin/mach-bf533/blackstamp.c - * Based on: arch/blackfin/mach-bf533/stamp.c - * Author: Benjamin Matthews <bmat@lle.rochester.edu> - * Aidan Williams <aidan@nicta.com.au> + * Board Info File for the BlackStamp * - * Created: 2008 - * Description: Board Info File for the BlackStamp - * - * Copyright 2005 National ICT Australia (NICTA) * Copyright 2004-2008 Analog Devices Inc. - * - * Enter bugs at http://blackfin.uclinux.org/ + * 2008 Benjamin Matthews <bmat@lle.rochester.edu> + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * * More info about the BlackStamp at: * http://blackfin.uclinux.org/gf/project/blackstamp/ @@ -281,19 +275,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_I2C_GPIO) || defined(CONFIG_I2C_GPIO_MODULE) #include <linux/i2c-gpio.h> @@ -384,8 +365,6 @@ static struct platform_device *stamp_devices[] __initdata = { #if defined(CONFIG_I2C_GPIO) || defined(CONFIG_I2C_GPIO_MODULE) &i2c_gpio_device, #endif - - &bfin_gpios_device, }; static int __init blackstamp_init(void) diff --git a/arch/blackfin/mach-bf533/boards/cm_bf533.c b/arch/blackfin/mach-bf533/boards/cm_bf533.c index 7443b26c80c5..7fc3b860d4ae 100644 --- a/arch/blackfin/mach-bf533/boards/cm_bf533.c +++ b/arch/blackfin/mach-bf533/boards/cm_bf533.c @@ -1,30 +1,10 @@ /* - * File: arch/blackfin/mach-bf533/boards/cm_bf533.c - * Based on: arch/blackfin/mach-bf533/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> Copyright 2005 + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Bluetechnix + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2005 - * Description: Board description file - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -261,19 +241,6 @@ static struct platform_device smsc911x_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) static struct resource bfin_uart_resources[] = { { @@ -506,8 +473,6 @@ static struct platform_device *cm_bf533_devices[] __initdata = { #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) ¶_flash_device, #endif - - &bfin_gpios_device, }; static int __init cm_bf533_init(void) diff --git a/arch/blackfin/mach-bf533/boards/ezkit.c b/arch/blackfin/mach-bf533/boards/ezkit.c index fd518e383b79..d4689dcc198e 100644 --- a/arch/blackfin/mach-bf533/boards/ezkit.c +++ b/arch/blackfin/mach-bf533/boards/ezkit.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf533/ezkit.c - * Based on: Original Work - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2005 - * Description: - * - * Modified: Robin Getz <rgetz@blackfin.uclinux.org> - Named the boards - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -33,12 +11,14 @@ #include <linux/mtd/mtd.h> #include <linux/mtd/partitions.h> #include <linux/mtd/plat-ram.h> +#include <linux/mtd/physmap.h> #include <linux/spi/spi.h> #include <linux/spi/flash.h> #if defined(CONFIG_USB_ISP1362_HCD) || defined(CONFIG_USB_ISP1362_HCD_MODULE) #include <linux/usb/isp1362.h> #endif #include <linux/irq.h> +#include <linux/i2c.h> #include <asm/dma.h> #include <asm/bfin5xx_spi.h> #include <asm/portmux.h> @@ -56,12 +36,6 @@ static struct platform_device rtc_device = { }; #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) -static struct platform_device bfin_fb_adv7393_device = { - .name = "bfin-adv7393", -}; -#endif - /* * USB-LAN EzExtender board * Driver needs to know address, irq and flag pin. @@ -98,54 +72,69 @@ static struct platform_device smc91x_device = { }; #endif -#if defined(CONFIG_MTD_PSD4256G) || defined(CONFIG_MTD_PSD4256G_MODULE) -static const char *map_probes[] = { - "stm_flash", - NULL, +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) +static struct mtd_partition ezkit_partitions_a[] = { + { + .name = "bootloader(nor a)", + .size = 0x40000, + .offset = 0, + }, { + .name = "linux kernel(nor a)", + .size = MTDPART_SIZ_FULL, + .offset = MTDPART_OFS_APPEND, + }, }; -static struct platdata_mtd_ram stm_pri_data_a = { - .mapname = "Flash A Primary", - .map_probes = map_probes, - .bankwidth = 2, +static struct physmap_flash_data ezkit_flash_data_a = { + .width = 2, + .parts = ezkit_partitions_a, + .nr_parts = ARRAY_SIZE(ezkit_partitions_a), }; -static struct resource stm_pri_resource_a = { +static struct resource ezkit_flash_resource_a = { .start = 0x20000000, .end = 0x200fffff, .flags = IORESOURCE_MEM, }; -static struct platform_device stm_pri_device_a = { - .name = "mtd-ram", +static struct platform_device ezkit_flash_device_a = { + .name = "physmap-flash", .id = 0, .dev = { - .platform_data = &stm_pri_data_a, + .platform_data = &ezkit_flash_data_a, }, .num_resources = 1, - .resource = &stm_pri_resource_a, + .resource = &ezkit_flash_resource_a, +}; + +static struct mtd_partition ezkit_partitions_b[] = { + { + .name = "file system(nor b)", + .size = MTDPART_SIZ_FULL, + .offset = MTDPART_OFS_APPEND, + }, }; -static struct platdata_mtd_ram stm_pri_data_b = { - .mapname = "Flash B Primary", - .map_probes = map_probes, - .bankwidth = 2, +static struct physmap_flash_data ezkit_flash_data_b = { + .width = 2, + .parts = ezkit_partitions_b, + .nr_parts = ARRAY_SIZE(ezkit_partitions_b), }; -static struct resource stm_pri_resource_b = { +static struct resource ezkit_flash_resource_b = { .start = 0x20100000, .end = 0x201fffff, .flags = IORESOURCE_MEM, }; -static struct platform_device stm_pri_device_b = { - .name = "mtd-ram", +static struct platform_device ezkit_flash_device_b = { + .name = "physmap-flash", .id = 4, .dev = { - .platform_data = &stm_pri_data_b, + .platform_data = &ezkit_flash_data_b, }, .num_resources = 1, - .resource = &stm_pri_resource_b, + .resource = &ezkit_flash_resource_b, }; #endif @@ -400,19 +389,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_I2C_GPIO) || defined(CONFIG_I2C_GPIO_MODULE) #include <linux/i2c-gpio.h> @@ -460,13 +436,21 @@ static struct platform_device bfin_dpmc = { }, }; +static struct i2c_board_info __initdata bfin_i2c_board_info[] = { +#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) + { + I2C_BOARD_INFO("bfin-adv7393", 0x2B), + }, +#endif +}; + static struct platform_device *ezkit_devices[] __initdata = { &bfin_dpmc, -#if defined(CONFIG_MTD_PSD4256G) || defined(CONFIG_MTD_PSD4256G_MODULE) - &stm_pri_device_a, - &stm_pri_device_b, +#if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) + &ezkit_flash_device_a, + &ezkit_flash_device_b, #endif #if defined(CONFIG_MTD_PLATRAM) || defined(CONFIG_MTD_PLATRAM_MODULE) @@ -482,10 +466,6 @@ static struct platform_device *ezkit_devices[] __initdata = { &bfin_spi0_device, #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) - &bfin_fb_adv7393_device, -#endif - #if defined(CONFIG_RTC_DRV_BFIN) || defined(CONFIG_RTC_DRV_BFIN_MODULE) &rtc_device, #endif @@ -507,8 +487,6 @@ static struct platform_device *ezkit_devices[] __initdata = { #if defined(CONFIG_I2C_GPIO) || defined(CONFIG_I2C_GPIO_MODULE) &i2c_gpio_device, #endif - - &bfin_gpios_device, }; static int __init ezkit_init(void) @@ -516,6 +494,8 @@ static int __init ezkit_init(void) printk(KERN_INFO "%s(): registering device resources\n", __func__); platform_add_devices(ezkit_devices, ARRAY_SIZE(ezkit_devices)); spi_register_board_info(bfin_spi_board_info, ARRAY_SIZE(bfin_spi_board_info)); + i2c_register_board_info(0, bfin_i2c_board_info, + ARRAY_SIZE(bfin_i2c_board_info)); return 0; } diff --git a/arch/blackfin/mach-bf533/boards/ip0x.c b/arch/blackfin/mach-bf533/boards/ip0x.c index f19b63378b12..644be5e5ab6f 100644 --- a/arch/blackfin/mach-bf533/boards/ip0x.c +++ b/arch/blackfin/mach-bf533/boards/ip0x.c @@ -1,34 +1,12 @@ /* - * File: arch/blackfin/mach-bf533/ip0x.c - * Based on: arch/blackfin/mach-bf533/bf1.c - * Based on: arch/blackfin/mach-bf533/stamp.c - * Author: Ivan Danov <idanov@gmail.com> - * Modified for IP0X David Rowe + * Copyright 2004-2009 Analog Devices Inc. + * 2007 David Rowe + * 2006 Intratrade Ltd. + * Ivan Danov <idanov@gmail.com> + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2007 - * Description: Board info file for the IP04/IP08 boards, which - * are derived from the BlackfinOne V2.0 boards. - * - * Modified: - * COpyright 2007 David Rowe - * Copyright 2006 Intratrade Ltd. - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -145,7 +123,6 @@ static struct bfin5xx_spi_chip mmc_spi_chip_info = { .ctl_reg = 0x1000, /* CPOL=0,CPHA=0,Sandisk 1G work */ .enable_dma = 0, /* if 1 - block!!! */ .bits_per_word = 8, - .cs_change_per_word = 0, }; #endif diff --git a/arch/blackfin/mach-bf533/boards/stamp.c b/arch/blackfin/mach-bf533/boards/stamp.c index 729fd7c26336..82f70efd66e7 100644 --- a/arch/blackfin/mach-bf533/boards/stamp.c +++ b/arch/blackfin/mach-bf533/boards/stamp.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf533/stamp.c - * Based on: arch/blackfin/mach-bf533/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2005 - * Description: Board Info File for the BF533-STAMP - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -95,12 +73,6 @@ static struct platform_device smc91x_device = { }; #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) -static struct platform_device bfin_fb_adv7393_device = { - .name = "bfin-adv7393", -}; -#endif - #if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) static struct resource net2272_bfin_resources[] = { { @@ -436,19 +408,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_I2C_GPIO) || defined(CONFIG_I2C_GPIO_MODULE) #include <linux/i2c-gpio.h> @@ -487,6 +446,11 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { .irq = 39, }, #endif +#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) + { + I2C_BOARD_INFO("bfin-adv7393", 0x2B), + }, +#endif }; static const unsigned int cclk_vlev_datasheet[] = @@ -528,10 +492,6 @@ static struct platform_device *stamp_devices[] __initdata = { &smc91x_device, #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) - &bfin_fb_adv7393_device, -#endif - #if defined(CONFIG_USB_NET2272) || defined(CONFIG_USB_NET2272_MODULE) &net2272_bfin_device, #endif @@ -563,8 +523,6 @@ static struct platform_device *stamp_devices[] __initdata = { &i2c_gpio_device, #endif - &bfin_gpios_device, - #if defined(CONFIG_MTD_BFIN_ASYNC) || defined(CONFIG_MTD_BFIN_ASYNC_MODULE) &stamp_flash_device, #endif diff --git a/arch/blackfin/mach-bf533/dma.c b/arch/blackfin/mach-bf533/dma.c index 7a443c37fb9f..4a14a46a9a68 100644 --- a/arch/blackfin/mach-bf533/dma.c +++ b/arch/blackfin/mach-bf533/dma.c @@ -1,31 +1,11 @@ /* - * File: arch/blackfin/mach-bf533/dma.c - * Based on: - * Author: + * simple DMA Implementation for Blackfin * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin + * Copyright 2007-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ + #include <linux/module.h> #include <asm/blackfin.h> diff --git a/arch/blackfin/mach-bf533/include/mach/bf533.h b/arch/blackfin/mach-bf533/include/mach/bf533.h index cf4427cd3f72..e3e05f8f7af9 100644 --- a/arch/blackfin/mach-bf533/include/mach/bf533.h +++ b/arch/blackfin/mach-bf533/include/mach/bf533.h @@ -1,30 +1,9 @@ /* - * File: include/asm-blackfin/mach-bf533/bf533.h - * Based on: - * Author: + * SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF561 * - * Created: - * Description: SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF561 + * Copyright 2005-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __MACH_BF533_H__ diff --git a/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h index 6965b4088c44..9e1f3defb6bc 100644 --- a/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf533/include/mach/bfin_serial_5xx.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf533/bfin_serial_5xx.h - * based on: - * author: + * Copyright 2006-2009 Analog Devices Inc. * - * created: - * description: - * blackfin serial driver head file - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later */ #include <linux/serial.h> diff --git a/arch/blackfin/mach-bf533/include/mach/blackfin.h b/arch/blackfin/mach-bf533/include/mach/blackfin.h index 499e897a4f4f..f4bd6df5d968 100644 --- a/arch/blackfin/mach-bf533/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf533/include/mach/blackfin.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf533/blackfin.h - * Based on: - * Author: + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _MACH_BLACKFIN_H_ diff --git a/arch/blackfin/mach-bf533/include/mach/cdefBF532.h b/arch/blackfin/mach-bf533/include/mach/cdefBF532.h index bbc3c8386d48..feb2392c43ea 100644 --- a/arch/blackfin/mach-bf533/include/mach/cdefBF532.h +++ b/arch/blackfin/mach-bf533/include/mach/cdefBF532.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf533/cdefBF532.h - * Based on: - * Author: + * Copyright 2005-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF532_H diff --git a/arch/blackfin/mach-bf533/include/mach/defBF532.h b/arch/blackfin/mach-bf533/include/mach/defBF532.h index 7f4633223e6d..02b328eb0e07 100644 --- a/arch/blackfin/mach-bf533/include/mach/defBF532.h +++ b/arch/blackfin/mach-bf533/include/mach/defBF532.h @@ -1,48 +1,10 @@ -/************************************************************************ - * - * This file is subject to the terms and conditions of the GNU Public - * License. See the file "COPYING" in the main directory of this archive - * for more details. - * - * Non-GPL License also available as part of VisualDSP++ - * http://www.analog.com/processors/resources/crosscore/visualDspDevSoftware.html - * - * (c) Copyright 2001-2005 Analog Devices, Inc. All rights reserved - * - * This file under source code control, please send bugs or changes to: - * dsptools.support@analog.com - * - ************************************************************************/ /* - * File: include/asm-blackfin/mach-bf533/defBF532.h - * Based on: - * Author: - * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. + * System & MMR bit and Address definitions for ADSP-BF532 * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Copyright 2005-2008 Analog Devices Inc. * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ -/* SYSTEM & MM REGISTER BIT & ADDRESS DEFINITIONS FOR ADSP-BF532 */ #ifndef _DEF_BF532_H #define _DEF_BF532_H diff --git a/arch/blackfin/mach-bf533/include/mach/gpio.h b/arch/blackfin/mach-bf533/include/mach/gpio.h index e45c17077aff..2af19d69a7a7 100644 --- a/arch/blackfin/mach-bf533/include/mach/gpio.h +++ b/arch/blackfin/mach-bf533/include/mach/gpio.h @@ -1,7 +1,4 @@ /* - * File: arch/blackfin/mach-bf533/include/mach/gpio.h - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * * Copyright (C) 2008 Analog Devices Inc. * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-bf533/include/mach/irq.h b/arch/blackfin/mach-bf533/include/mach/irq.h index db1e346cd1aa..c31498be0bbb 100644 --- a/arch/blackfin/mach-bf533/include/mach/irq.h +++ b/arch/blackfin/mach-bf533/include/mach/irq.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf533/defBF532.h - * Based on: - * Author: + * Copyright 2005-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _BF533_IRQ_H_ diff --git a/arch/blackfin/mach-bf533/include/mach/portmux.h b/arch/blackfin/mach-bf533/include/mach/portmux.h index 2f59ce0b0cb5..075dae1af164 100644 --- a/arch/blackfin/mach-bf533/include/mach/portmux.h +++ b/arch/blackfin/mach-bf533/include/mach/portmux.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later + */ + #ifndef _MACH_PORTMUX_H_ #define _MACH_PORTMUX_H_ diff --git a/arch/blackfin/mach-bf533/ints-priority.c b/arch/blackfin/mach-bf533/ints-priority.c index f51994b7a2b9..8f714cf8135b 100644 --- a/arch/blackfin/mach-bf533/ints-priority.c +++ b/arch/blackfin/mach-bf533/ints-priority.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf533/ints-priority.c - * Based on: - * Author: Michael Hennerich + * Set up the interrupt priorities * - * Created: ? - * Description: Set up the interrupt priorities + * Copyright 2005-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf537/boards/cm_bf537e.c b/arch/blackfin/mach-bf537/boards/cm_bf537e.c index 87acb7dd2df3..c85f4d770535 100644 --- a/arch/blackfin/mach-bf537/boards/cm_bf537e.c +++ b/arch/blackfin/mach-bf537/boards/cm_bf537e.c @@ -1,31 +1,10 @@ /* - * File: arch/blackfin/mach-bf537/boards/cm_bf537.c - * Based on: arch/blackfin/mach-bf533/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Bluetechnix + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2005 - * Description: Board description file - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -297,19 +276,6 @@ static struct platform_device net2272_bfin_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) static struct mtd_partition cm_partitions[] = { { @@ -699,8 +665,6 @@ static struct platform_device *cm_bf537e_devices[] __initdata = { #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) &cm_flash_device, #endif - - &bfin_gpios_device, }; static int __init cm_bf537e_init(void) diff --git a/arch/blackfin/mach-bf537/boards/cm_bf537u.c b/arch/blackfin/mach-bf537/boards/cm_bf537u.c index 8219dc3d65bd..ea11aa81340d 100644 --- a/arch/blackfin/mach-bf537/boards/cm_bf537u.c +++ b/arch/blackfin/mach-bf537/boards/cm_bf537u.c @@ -1,31 +1,10 @@ /* - * File: arch/blackfin/mach-bf537/boards/cm_bf537u.c - * Based on: arch/blackfin/mach-bf533/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Bluetechnix + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2005 - * Description: Board description file - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -298,19 +277,6 @@ static struct platform_device net2272_bfin_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) static struct mtd_partition cm_partitions[] = { { @@ -605,8 +571,6 @@ static struct platform_device *cm_bf537u_devices[] __initdata = { #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) &cm_flash_device, #endif - - &bfin_gpios_device, }; static int __init cm_bf537u_init(void) diff --git a/arch/blackfin/mach-bf537/boards/minotaur.c b/arch/blackfin/mach-bf537/boards/minotaur.c index 399f81da7b93..0da927252701 100644 --- a/arch/blackfin/mach-bf537/boards/minotaur.c +++ b/arch/blackfin/mach-bf537/boards/minotaur.c @@ -1,4 +1,10 @@ /* + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Cambridge Signal Processing + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> + * + * Licensed under the GPL-2 or later. */ #include <linux/device.h> diff --git a/arch/blackfin/mach-bf537/boards/pnav10.c b/arch/blackfin/mach-bf537/boards/pnav10.c index 10b35b838bac..9ba290466b56 100644 --- a/arch/blackfin/mach-bf537/boards/pnav10.c +++ b/arch/blackfin/mach-bf537/boards/pnav10.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf537/boards/stamp.c - * Based on: arch/blackfin/mach-bf533/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -302,7 +280,6 @@ static struct bfin5xx_spi_chip mmc_spi_chip_info = { #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) static struct bfin5xx_spi_chip spi_ad7877_chip_info = { - .cs_change_per_word = 0, .enable_dma = 0, .bits_per_word = 16, }; diff --git a/arch/blackfin/mach-bf537/boards/stamp.c b/arch/blackfin/mach-bf537/boards/stamp.c index 9db6b40743e0..c46baa5e6d9b 100644 --- a/arch/blackfin/mach-bf537/boards/stamp.c +++ b/arch/blackfin/mach-bf537/boards/stamp.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf537/boards/stamp.c - * Based on: arch/blackfin/mach-bf533/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -121,19 +99,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_BFIN_CFPCMCIA) || defined(CONFIG_BFIN_CFPCMCIA_MODULE) static struct resource bfin_pcmcia_cf_resources[] = { { @@ -1078,12 +1043,6 @@ static struct platform_device bfin_fb_device = { }; #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) -static struct platform_device bfin_fb_adv7393_device = { - .name = "bfin-adv7393", -}; -#endif - #if defined(CONFIG_FB_BFIN_LQ035Q1) || defined(CONFIG_FB_BFIN_LQ035Q1_MODULE) #include <asm/bfin-lq035q1.h> @@ -1498,6 +1457,11 @@ static struct i2c_board_info __initdata bfin_i2c_board_info[] = { .platform_data = (void *)&adp5588_gpio_data, }, #endif +#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) + { + I2C_BOARD_INFO("bfin-adv7393", 0x2B), + }, +#endif }; #if defined(CONFIG_SERIAL_BFIN_SPORT) || defined(CONFIG_SERIAL_BFIN_SPORT_MODULE) @@ -1668,10 +1632,6 @@ static struct platform_device *stamp_devices[] __initdata = { &bfin_lq035q1_device, #endif -#if defined(CONFIG_FB_BFIN_7393) || defined(CONFIG_FB_BFIN_7393_MODULE) - &bfin_fb_adv7393_device, -#endif - #if defined(CONFIG_SERIAL_BFIN) || defined(CONFIG_SERIAL_BFIN_MODULE) &bfin_uart_device, #endif @@ -1702,8 +1662,6 @@ static struct platform_device *stamp_devices[] __initdata = { &bfin_device_gpiokeys, #endif - &bfin_gpios_device, - #if defined(CONFIG_MTD_NAND_PLATFORM) || defined(CONFIG_MTD_NAND_PLATFORM_MODULE) &bfin_async_nand_device, #endif diff --git a/arch/blackfin/mach-bf537/boards/tcm_bf537.c b/arch/blackfin/mach-bf537/boards/tcm_bf537.c index 61353f7bcb9e..57163b65a4f5 100644 --- a/arch/blackfin/mach-bf537/boards/tcm_bf537.c +++ b/arch/blackfin/mach-bf537/boards/tcm_bf537.c @@ -1,31 +1,10 @@ /* - * File: arch/blackfin/mach-bf537/boards/tcm_bf537.c - * Based on: arch/blackfin/mach-bf533/boards/cm_bf537.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Bluetechnix + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2005 - * Description: Board description file - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -298,19 +277,6 @@ static struct platform_device net2272_bfin_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) static struct mtd_partition cm_partitions[] = { { @@ -607,8 +573,6 @@ static struct platform_device *cm_bf537_devices[] __initdata = { #if defined(CONFIG_MTD_GPIO_ADDR) || defined(CONFIG_MTD_GPIO_ADDR_MODULE) &cm_flash_device, #endif - - &bfin_gpios_device, }; static int __init tcm_bf537_init(void) diff --git a/arch/blackfin/mach-bf537/dma.c b/arch/blackfin/mach-bf537/dma.c index d23fc0edf2b9..5c8c4ed517bb 100644 --- a/arch/blackfin/mach-bf537/dma.c +++ b/arch/blackfin/mach-bf537/dma.c @@ -1,31 +1,11 @@ /* - * File: arch/blackfin/mach-bf537/dma.c - * Based on: - * Author: + * Copyright 2007-2009 Analog Devices Inc. * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin + * Licensed under the GPL-2 or later. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * This file contains the simple DMA Implementation for Blackfin */ + #include <linux/module.h> #include <asm/blackfin.h> diff --git a/arch/blackfin/mach-bf537/include/mach/bf537.h b/arch/blackfin/mach-bf537/include/mach/bf537.h index f194a848ae8e..17fab4474669 100644 --- a/arch/blackfin/mach-bf537/include/mach/bf537.h +++ b/arch/blackfin/mach-bf537/include/mach/bf537.h @@ -1,30 +1,9 @@ /* - * File: include/asm-blackfin/mach-bf537/bf537.h - * Based on: - * Author: + * System MMR Register and memory map for ADSP-BF537 * - * Created: - * Description: SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF537 + * Copyright 2005-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __MACH_BF537_H__ diff --git a/arch/blackfin/mach-bf537/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf537/include/mach/bfin_serial_5xx.h index e95d54f9af6c..635c91c526a3 100644 --- a/arch/blackfin/mach-bf537/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf537/include/mach/bfin_serial_5xx.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf537/bfin_serial_5xx.h - * based on: - * author: + * Copyright 2006-2009 Analog Devices Inc. * - * created: - * description: - * blackfin serial driver header files - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later */ #include <linux/serial.h> diff --git a/arch/blackfin/mach-bf537/include/mach/blackfin.h b/arch/blackfin/mach-bf537/include/mach/blackfin.h index 9ee8834c8f1a..eab006d260c5 100644 --- a/arch/blackfin/mach-bf537/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf537/include/mach/blackfin.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf537/blackfin.h - * Based on: - * Author: + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _MACH_BLACKFIN_H_ diff --git a/arch/blackfin/mach-bf537/include/mach/cdefBF534.h b/arch/blackfin/mach-bf537/include/mach/cdefBF534.h index 5f8b5f845be6..91825c9bd226 100644 --- a/arch/blackfin/mach-bf537/include/mach/cdefBF534.h +++ b/arch/blackfin/mach-bf537/include/mach/cdefBF534.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf537/cdefbf534.h - * Based on: - * Author: + * Copyright 2005-2008 Analog Devices Inc. * - * Created: - * Description: system mmr register map - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF534_H diff --git a/arch/blackfin/mach-bf537/include/mach/cdefBF537.h b/arch/blackfin/mach-bf537/include/mach/cdefBF537.h index b8fc949a991f..9363c3990421 100644 --- a/arch/blackfin/mach-bf537/include/mach/cdefBF537.h +++ b/arch/blackfin/mach-bf537/include/mach/cdefBF537.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf537/cdefBF537.h - * Based on: - * Author: + * Copyright 2005-2008 Analog Devices Inc. * - * Created: - * Description: - * System MMR Register Map - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later */ #ifndef _CDEF_BF537_H diff --git a/arch/blackfin/mach-bf537/include/mach/defBF534.h b/arch/blackfin/mach-bf537/include/mach/defBF534.h index a3227f9003ff..cebb14feb1ba 100644 --- a/arch/blackfin/mach-bf537/include/mach/defBF534.h +++ b/arch/blackfin/mach-bf537/include/mach/defBF534.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf537/cdefBF537.h - * Based on: - * Author: + * Copyright 2005-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF534_H diff --git a/arch/blackfin/mach-bf537/include/mach/defBF537.h b/arch/blackfin/mach-bf537/include/mach/defBF537.h index 3d6c83e31b1e..8cb5d5cf0c94 100644 --- a/arch/blackfin/mach-bf537/include/mach/defBF537.h +++ b/arch/blackfin/mach-bf537/include/mach/defBF537.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf537/defbf537.h - * based on: - * author: + * Copyright 2005-2008 Analog Devices Inc. * - * created: - * description: - * system mmr register map - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF537_H diff --git a/arch/blackfin/mach-bf537/include/mach/gpio.h b/arch/blackfin/mach-bf537/include/mach/gpio.h index d77a31e45a30..104bff85290d 100644 --- a/arch/blackfin/mach-bf537/include/mach/gpio.h +++ b/arch/blackfin/mach-bf537/include/mach/gpio.h @@ -1,7 +1,4 @@ /* - * File: arch/blackfin/mach-bf537/include/mach/gpio.h - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * * Copyright (C) 2008 Analog Devices Inc. * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-bf537/include/mach/irq.h b/arch/blackfin/mach-bf537/include/mach/irq.h index b2a71d5d4e5f..0defa9457e7f 100644 --- a/arch/blackfin/mach-bf537/include/mach/irq.h +++ b/arch/blackfin/mach-bf537/include/mach/irq.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf537/irq.h - * based on: - * author: + * Copyright 2005-2008 Analog Devices Inc. * - * created: - * description: - * system mmr register map - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later */ #ifndef _BF537_IRQ_H_ diff --git a/arch/blackfin/mach-bf537/include/mach/portmux.h b/arch/blackfin/mach-bf537/include/mach/portmux.h index 87285e75e903..da9760329e49 100644 --- a/arch/blackfin/mach-bf537/include/mach/portmux.h +++ b/arch/blackfin/mach-bf537/include/mach/portmux.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later + */ + #ifndef _MACH_PORTMUX_H_ #define _MACH_PORTMUX_H_ diff --git a/arch/blackfin/mach-bf537/ints-priority.c b/arch/blackfin/mach-bf537/ints-priority.c index 51c48087e03b..f6500622b35d 100644 --- a/arch/blackfin/mach-bf537/ints-priority.c +++ b/arch/blackfin/mach-bf537/ints-priority.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf537/ints-priority.c - * Based on: arch/blackfin/mach-bf533/ints-priority.c - * Author: Michael Hennerich + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: Set up the interrupt priorities + * Licensed under the GPL-2 or later. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Set up the interrupt priorities */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf538/boards/ezkit.c b/arch/blackfin/mach-bf538/boards/ezkit.c index f2ac3b0ebf24..14af5c2088d4 100644 --- a/arch/blackfin/mach-bf538/boards/ezkit.c +++ b/arch/blackfin/mach-bf538/boards/ezkit.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf538/boards/ezkit.c - * Based on: arch/blackfin/mach-bf537/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 */ #include <linux/device.h> @@ -237,7 +215,6 @@ static struct flash_platform_data bfin_spi_flash_data = { static struct bfin5xx_spi_chip spi_flash_chip_info = { .enable_dma = 0, /* use dma transfer with this chip*/ .bits_per_word = 8, - .cs_change_per_word = 0, }; #endif @@ -506,19 +483,6 @@ static struct platform_device i2c_bfin_twi1_device = { #endif #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_KEYBOARD_GPIO) || defined(CONFIG_KEYBOARD_GPIO_MODULE) #include <linux/gpio_keys.h> @@ -658,8 +622,6 @@ static struct platform_device *cm_bf538_devices[] __initdata = { &bfin_device_gpiokeys, #endif - &bfin_gpios_device, - #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) &ezkit_flash_device, #endif diff --git a/arch/blackfin/mach-bf538/dma.c b/arch/blackfin/mach-bf538/dma.c index d6837fbf94ea..5dc022589214 100644 --- a/arch/blackfin/mach-bf538/dma.c +++ b/arch/blackfin/mach-bf538/dma.c @@ -1,31 +1,11 @@ /* - * File: arch/blackfin/mach-bf538/dma.c - * Based on: - * Author: + * the simple DMA Implementation for Blackfin * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin + * Copyright 2008 Analog Devices Inc. * - * Modified: - * Copyright 2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ + #include <linux/module.h> #include <asm/blackfin.h> diff --git a/arch/blackfin/mach-bf538/include/mach/bf538.h b/arch/blackfin/mach-bf538/include/mach/bf538.h index 9c8abb307908..0cf5bf8dab84 100644 --- a/arch/blackfin/mach-bf538/include/mach/bf538.h +++ b/arch/blackfin/mach-bf538/include/mach/bf538.h @@ -1,30 +1,9 @@ /* - * File: include/asm-blackfin/mach-bf538/bf538.h - * Based on: include/asm-blackfin/mach-bf537/bf537.h - * Author: Michael Hennerich (michael.hennerich@analog.com) + * SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF538 * - * Created: - * Description: SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF527 + * Copyright 2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __MACH_BF538_H__ diff --git a/arch/blackfin/mach-bf538/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf538/include/mach/bfin_serial_5xx.h index 999f239fe1a6..5c148142f041 100644 --- a/arch/blackfin/mach-bf538/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf538/include/mach/bfin_serial_5xx.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf538/bfin_serial_5xx.h - * based on: - * author: + * Copyright 2008-2009 Analog Devices Inc. * - * created: - * description: - * blackfin serial driver header files - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later. */ #include <linux/serial.h> diff --git a/arch/blackfin/mach-bf538/include/mach/blackfin.h b/arch/blackfin/mach-bf538/include/mach/blackfin.h index 5ecee1690957..278e8942eef2 100644 --- a/arch/blackfin/mach-bf538/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf538/include/mach/blackfin.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf538/blackfin.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _MACH_BLACKFIN_H_ diff --git a/arch/blackfin/mach-bf538/include/mach/cdefBF538.h b/arch/blackfin/mach-bf538/include/mach/cdefBF538.h index 1de67515dc9d..401ebd79d0aa 100644 --- a/arch/blackfin/mach-bf538/include/mach/cdefBF538.h +++ b/arch/blackfin/mach-bf538/include/mach/cdefBF538.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf538/cdefBF538.h - * Based on: - * Author: + * Copyright 2008-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF538_H diff --git a/arch/blackfin/mach-bf538/include/mach/defBF539.h b/arch/blackfin/mach-bf538/include/mach/defBF539.h index 1c58914a8740..5f6c34dfd08e 100644 --- a/arch/blackfin/mach-bf538/include/mach/defBF539.h +++ b/arch/blackfin/mach-bf538/include/mach/defBF539.h @@ -1,47 +1,9 @@ -/************************************************************************ - * - * This file is subject to the terms and conditions of the GNU Public - * License. See the file "COPYING" in the main directory of this archive - * for more details. - * - * Non-GPL License also available as part of VisualDSP++ - * http://www.analog.com/processors/resources/crosscore/visualDspDevSoftware.html - * - * (c) Copyright 2001-2005 Analog Devices, Inc. All rights reserved - * - * This file under source code control, please send bugs or changes to: - * dsptools.support@analog.com - * - ************************************************************************/ /* - * File: include/asm-blackfin/mach-bf538/defBF539.h - * Based on: - * Author: - * - * Created: - * Description: + * Copyright 2008-2009 Analog Devices Inc. * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ + /* SYSTEM & MM REGISTER BIT & ADDRESS DEFINITIONS FOR ADSP-BF538/9 */ #ifndef _DEF_BF539_H diff --git a/arch/blackfin/mach-bf538/include/mach/gpio.h b/arch/blackfin/mach-bf538/include/mach/gpio.h index 30f4f723f7cc..295c78a465c2 100644 --- a/arch/blackfin/mach-bf538/include/mach/gpio.h +++ b/arch/blackfin/mach-bf538/include/mach/gpio.h @@ -1,7 +1,4 @@ /* - * File: arch/blackfin/mach-bf538/include/mach/gpio.h - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * * Copyright (C) 2008 Analog Devices Inc. * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-bf538/include/mach/irq.h b/arch/blackfin/mach-bf538/include/mach/irq.h index fdc87fe2c174..a4b7fcbc556b 100644 --- a/arch/blackfin/mach-bf538/include/mach/irq.h +++ b/arch/blackfin/mach-bf538/include/mach/irq.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf538/irq.h - * based on: include/asm-blackfin/mach-bf537/irq.h - * author: Michael Hennerich (michael.hennerich@analog.com) + * Copyright 2008 Analog Devices Inc. * - * created: - * description: - * system mmr register map - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later. */ #ifndef _BF538_IRQ_H_ diff --git a/arch/blackfin/mach-bf538/include/mach/portmux.h b/arch/blackfin/mach-bf538/include/mach/portmux.h index c8db264e3e4d..6121cf8b5872 100644 --- a/arch/blackfin/mach-bf538/include/mach/portmux.h +++ b/arch/blackfin/mach-bf538/include/mach/portmux.h @@ -1,3 +1,9 @@ +/* + * Copyright 2008-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _MACH_PORTMUX_H_ #define _MACH_PORTMUX_H_ diff --git a/arch/blackfin/mach-bf538/ints-priority.c b/arch/blackfin/mach-bf538/ints-priority.c index 70d17e550e05..1fa793ced347 100644 --- a/arch/blackfin/mach-bf538/ints-priority.c +++ b/arch/blackfin/mach-bf538/ints-priority.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf538/ints-priority.c - * Based on: arch/blackfin/mach-bf533/ints-priority.c - * Author: Michael Hennerich + * Set up the interrupt priorities * - * Created: - * Description: Set up the interrupt priorities + * Copyright 2008 Analog Devices Inc. * - * Modified: - * Copyright 2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf548/boards/cm_bf548.c b/arch/blackfin/mach-bf548/boards/cm_bf548.c index e565aae11d72..ccdcd6da2e9f 100644 --- a/arch/blackfin/mach-bf548/boards/cm_bf548.c +++ b/arch/blackfin/mach-bf548/boards/cm_bf548.c @@ -1,31 +1,10 @@ /* - * File: arch/blackfin/mach-bf548/boards/cm_bf548.c - * Based on: arch/blackfin/mach-bf537/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Bluetechnix + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -380,19 +359,6 @@ static struct platform_device musb_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_PATA_BF54X) || defined(CONFIG_PATA_BF54X_MODULE) static struct resource bfin_atapi_resources[] = { { @@ -546,13 +512,11 @@ static struct flash_platform_data bfin_spi_flash_data = { static struct bfin5xx_spi_chip spi_flash_chip_info = { .enable_dma = 0, /* use dma transfer with this chip*/ .bits_per_word = 8, - .cs_change_per_word = 0, }; #endif #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) static struct bfin5xx_spi_chip spi_ad7877_chip_info = { - .cs_change_per_word = 0, .enable_dma = 0, .bits_per_word = 16, }; @@ -853,8 +817,6 @@ static struct platform_device *cm_bf548_devices[] __initdata = { #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) ¶_flash_device, #endif - - &bfin_gpios_device, }; static int __init cm_bf548_init(void) diff --git a/arch/blackfin/mach-bf548/boards/ezkit.c b/arch/blackfin/mach-bf548/boards/ezkit.c index c66f3801274f..1a5286bbb3fa 100644 --- a/arch/blackfin/mach-bf548/boards/ezkit.c +++ b/arch/blackfin/mach-bf548/boards/ezkit.c @@ -1,31 +1,9 @@ /* - * File: arch/blackfin/mach-bf548/boards/ezkit.c - * Based on: arch/blackfin/mach-bf537/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2005 National ICT Australia (NICTA) - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -208,7 +186,6 @@ static struct platform_device bfin_rotary_device = { #endif #if defined(CONFIG_INPUT_ADXL34X) || defined(CONFIG_INPUT_ADXL34X_MODULE) -#include <linux/input.h> #include <linux/spi/adxl34x.h> static const struct adxl34x_platform_data adxl34x_info = { .x_axis_offset = 0, @@ -636,7 +613,6 @@ static struct flash_platform_data bfin_spi_flash_data = { static struct bfin5xx_spi_chip spi_flash_chip_info = { .enable_dma = 0, /* use dma transfer with this chip*/ .bits_per_word = 8, - .cs_change_per_word = 0, }; #endif @@ -650,7 +626,6 @@ static struct bfin5xx_spi_chip ad1836_spi_chip_info = { #if defined(CONFIG_TOUCHSCREEN_AD7877) || defined(CONFIG_TOUCHSCREEN_AD7877_MODULE) static struct bfin5xx_spi_chip spi_ad7877_chip_info = { - .cs_change_per_word = 0, .enable_dma = 0, .bits_per_word = 16, }; @@ -681,7 +656,6 @@ static struct bfin5xx_spi_chip spidev_chip_info = { static struct bfin5xx_spi_chip spi_adxl34x_chip_info = { .enable_dma = 0, /* use dma transfer with this chip*/ .bits_per_word = 8, - .cs_change_per_word = 0, }; #endif @@ -908,19 +882,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - static const unsigned int cclk_vlev_datasheet[] = { /* @@ -1028,8 +989,6 @@ static struct platform_device *ezkit_devices[] __initdata = { &bfin_device_gpiokeys, #endif - &bfin_gpios_device, - #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) &ezkit_flash_device, #endif diff --git a/arch/blackfin/mach-bf548/dma.c b/arch/blackfin/mach-bf548/dma.c index d9239bc05dd4..039a6d9d38f3 100644 --- a/arch/blackfin/mach-bf548/dma.c +++ b/arch/blackfin/mach-bf548/dma.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf548/dma.c - * Based on: - * Author: + * the simple DMA Implementation for Blackfin * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin + * Copyright 2007-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf548/include/mach/bf548.h b/arch/blackfin/mach-bf548/include/mach/bf548.h index cd31f72bdd82..7bead5ce0f3b 100644 --- a/arch/blackfin/mach-bf548/include/mach/bf548.h +++ b/arch/blackfin/mach-bf548/include/mach/bf548.h @@ -1,30 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/bf548.h - * Based on: - * Author: + * Copyright 2007-2009 Analog Devices Inc. * - * Created: - * Description: System MMR register and memory map for ADSP-BF548 - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __MACH_BF548_H__ diff --git a/arch/blackfin/mach-bf548/include/mach/bf54x-lq043.h b/arch/blackfin/mach-bf548/include/mach/bf54x-lq043.h index 9c7ca62a45eb..8821efe57fbc 100644 --- a/arch/blackfin/mach-bf548/include/mach/bf54x-lq043.h +++ b/arch/blackfin/mach-bf548/include/mach/bf54x-lq043.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef BF54X_LQ043_H #define BF54X_LQ043_H diff --git a/arch/blackfin/mach-bf548/include/mach/bf54x_keys.h b/arch/blackfin/mach-bf548/include/mach/bf54x_keys.h index 1fb4ec77cc25..49338ae299ab 100644 --- a/arch/blackfin/mach-bf548/include/mach/bf54x_keys.h +++ b/arch/blackfin/mach-bf548/include/mach/bf54x_keys.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _BFIN_KPAD_H #define _BFIN_KPAD_H diff --git a/arch/blackfin/mach-bf548/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf548/include/mach/bfin_serial_5xx.h index 2d1b5fa3cca0..dd44aa75fe72 100644 --- a/arch/blackfin/mach-bf548/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf548/include/mach/bfin_serial_5xx.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf548/bfin_serial_5xx.h - * based on: - * author: + * Copyright 2007-2009 Analog Devices Inc. * - * created: - * description: - * blackfin serial driver head file - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later. */ #include <linux/serial.h> diff --git a/arch/blackfin/mach-bf548/include/mach/blackfin.h b/arch/blackfin/mach-bf548/include/mach/blackfin.h index 318667b2f036..13302b67857a 100644 --- a/arch/blackfin/mach-bf548/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf548/include/mach/blackfin.h @@ -1,32 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/blackfin.h - * Based on: - * Author: + * Copyright 2007-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _MACH_BLACKFIN_H_ diff --git a/arch/blackfin/mach-bf548/include/mach/cdefBF542.h b/arch/blackfin/mach-bf548/include/mach/cdefBF542.h index 07aefb9ed79b..42f4a9469549 100644 --- a/arch/blackfin/mach-bf548/include/mach/cdefBF542.h +++ b/arch/blackfin/mach-bf548/include/mach/cdefBF542.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/cdefBF542.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF542_H diff --git a/arch/blackfin/mach-bf548/include/mach/cdefBF544.h b/arch/blackfin/mach-bf548/include/mach/cdefBF544.h index 431a69278991..2207799575ff 100644 --- a/arch/blackfin/mach-bf548/include/mach/cdefBF544.h +++ b/arch/blackfin/mach-bf548/include/mach/cdefBF544.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/cdefBF544.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF544_H diff --git a/arch/blackfin/mach-bf548/include/mach/cdefBF547.h b/arch/blackfin/mach-bf548/include/mach/cdefBF547.h index 93376e90dfc5..423421515134 100644 --- a/arch/blackfin/mach-bf548/include/mach/cdefBF547.h +++ b/arch/blackfin/mach-bf548/include/mach/cdefBF547.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/cdefBF547.h - * Based on: - * Author: + * Copyright 2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF548_H diff --git a/arch/blackfin/mach-bf548/include/mach/cdefBF548.h b/arch/blackfin/mach-bf548/include/mach/cdefBF548.h index 9cd74384136f..df84180410c4 100644 --- a/arch/blackfin/mach-bf548/include/mach/cdefBF548.h +++ b/arch/blackfin/mach-bf548/include/mach/cdefBF548.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/cdefBF548.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF548_H diff --git a/arch/blackfin/mach-bf548/include/mach/cdefBF549.h b/arch/blackfin/mach-bf548/include/mach/cdefBF549.h index ead360b69dea..34c84c7fb256 100644 --- a/arch/blackfin/mach-bf548/include/mach/cdefBF549.h +++ b/arch/blackfin/mach-bf548/include/mach/cdefBF549.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf549/cdefBF549.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF549_H diff --git a/arch/blackfin/mach-bf548/include/mach/cdefBF54x_base.h b/arch/blackfin/mach-bf548/include/mach/cdefBF54x_base.h index 6e636c418cb0..a2e9d9849eba 100644 --- a/arch/blackfin/mach-bf548/include/mach/cdefBF54x_base.h +++ b/arch/blackfin/mach-bf548/include/mach/cdefBF54x_base.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/cdefBF54x_base.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF54X_H diff --git a/arch/blackfin/mach-bf548/include/mach/defBF542.h b/arch/blackfin/mach-bf548/include/mach/defBF542.h index b1316541b8d6..d3bc6d1df547 100644 --- a/arch/blackfin/mach-bf548/include/mach/defBF542.h +++ b/arch/blackfin/mach-bf548/include/mach/defBF542.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/defBF542.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF542_H diff --git a/arch/blackfin/mach-bf548/include/mach/defBF544.h b/arch/blackfin/mach-bf548/include/mach/defBF544.h index c2c785bdc5fc..dd414ae4ba4c 100644 --- a/arch/blackfin/mach-bf548/include/mach/defBF544.h +++ b/arch/blackfin/mach-bf548/include/mach/defBF544.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/defBF544.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF544_H diff --git a/arch/blackfin/mach-bf548/include/mach/defBF547.h b/arch/blackfin/mach-bf548/include/mach/defBF547.h index 661f0d877bd1..5a9dbabe0a68 100644 --- a/arch/blackfin/mach-bf548/include/mach/defBF547.h +++ b/arch/blackfin/mach-bf548/include/mach/defBF547.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/defBF547.h - * Based on: - * Author: + * Copyright 2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF548_H diff --git a/arch/blackfin/mach-bf548/include/mach/defBF548.h b/arch/blackfin/mach-bf548/include/mach/defBF548.h index 85d4bade911d..82cd593f7391 100644 --- a/arch/blackfin/mach-bf548/include/mach/defBF548.h +++ b/arch/blackfin/mach-bf548/include/mach/defBF548.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/defBF548.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF548_H diff --git a/arch/blackfin/mach-bf548/include/mach/defBF549.h b/arch/blackfin/mach-bf548/include/mach/defBF549.h index 096734541644..6fc6e39ab61b 100644 --- a/arch/blackfin/mach-bf548/include/mach/defBF549.h +++ b/arch/blackfin/mach-bf548/include/mach/defBF549.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/defBF549.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF549_H diff --git a/arch/blackfin/mach-bf548/include/mach/defBF54x_base.h b/arch/blackfin/mach-bf548/include/mach/defBF54x_base.h index e022e896cb18..8590c8c78336 100644 --- a/arch/blackfin/mach-bf548/include/mach/defBF54x_base.h +++ b/arch/blackfin/mach-bf548/include/mach/defBF54x_base.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf548/defBF54x_base.h - * Based on: - * Author: + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF54X_H diff --git a/arch/blackfin/mach-bf548/include/mach/gpio.h b/arch/blackfin/mach-bf548/include/mach/gpio.h index 3a2051709787..850e39d193e3 100644 --- a/arch/blackfin/mach-bf548/include/mach/gpio.h +++ b/arch/blackfin/mach-bf548/include/mach/gpio.h @@ -1,34 +1,8 @@ /* - * File: include/asm-blackfin/mach-bf548/gpio.h - * Based on: - * Author: Michael Hennerich (hennerich@blackfin.uclinux.org) - * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Copyright 2007-2009 Analog Devices Inc. + * Licensed under the GPL-2 or later. */ - - #define GPIO_PA0 0 #define GPIO_PA1 1 #define GPIO_PA2 2 diff --git a/arch/blackfin/mach-bf548/include/mach/irq.h b/arch/blackfin/mach-bf548/include/mach/irq.h index f194625f6821..106db05684ae 100644 --- a/arch/blackfin/mach-bf548/include/mach/irq.h +++ b/arch/blackfin/mach-bf548/include/mach/irq.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf548/irq.h - * based on: include/asm-blackfin/mach-bf537/irq.h - * author: Roy Huang (roy.huang@analog.com) + * Copyright 2007-2009 Analog Devices Inc. * - * created: - * description: - * system mmr register map - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later. */ #ifndef _BF548_IRQ_H_ diff --git a/arch/blackfin/mach-bf548/include/mach/portmux.h b/arch/blackfin/mach-bf548/include/mach/portmux.h index ce372ba0f046..89ad6a886362 100644 --- a/arch/blackfin/mach-bf548/include/mach/portmux.h +++ b/arch/blackfin/mach-bf548/include/mach/portmux.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _MACH_PORTMUX_H_ #define _MACH_PORTMUX_H_ diff --git a/arch/blackfin/mach-bf548/ints-priority.c b/arch/blackfin/mach-bf548/ints-priority.c index 9dd0fa3ac4de..48dd3a4bc4a5 100644 --- a/arch/blackfin/mach-bf548/ints-priority.c +++ b/arch/blackfin/mach-bf548/ints-priority.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf537/ints-priority.c - * Based on: arch/blackfin/mach-bf533/ints-priority.c - * Author: Michael Hennerich + * Copyright 2007-2008 Analog Devices Inc. * - * Created: - * Description: Set up the interrupt priorities + * Licensed under the GPL-2 or later. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Set up the interrupt priorities */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf561/atomic.S b/arch/blackfin/mach-bf561/atomic.S index 9439bc6bd01f..0261a5e751b3 100644 --- a/arch/blackfin/mach-bf561/atomic.S +++ b/arch/blackfin/mach-bf561/atomic.S @@ -1,23 +1,8 @@ /* - * File: arch/blackfin/mach-bf561/atomic.S - * Author: Philippe Gerum <rpm@xenomai.org> + * Copyright 2007-2008 Analog Devices Inc. + * Philippe Gerum <rpm@xenomai.org> * - * Copyright 2007 Analog Devices Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/linkage.h> diff --git a/arch/blackfin/mach-bf561/boards/cm_bf561.c b/arch/blackfin/mach-bf561/boards/cm_bf561.c index 6577ecfcf11e..dfc8d5b77986 100644 --- a/arch/blackfin/mach-bf561/boards/cm_bf561.c +++ b/arch/blackfin/mach-bf561/boards/cm_bf561.c @@ -1,30 +1,10 @@ /* - * File: arch/blackfin/mach-bf533/boards/cm_bf561.c - * Based on: arch/blackfin/mach-bf533/boards/ezkit.c - * Author: Aidan Williams <aidan@nicta.com.au> Copyright 2005 + * Copyright 2004-2009 Analog Devices Inc. + * 2008-2009 Bluetechnix + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: 2006 - * Description: Board description file - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -285,19 +265,6 @@ static struct platform_device net2272_bfin_device = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_USB_ISP1362_HCD) || defined(CONFIG_USB_ISP1362_HCD_MODULE) static struct resource isp1362_hcd_resources[] = { { @@ -532,8 +499,6 @@ static struct platform_device *cm_bf561_devices[] __initdata = { #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) ¶_flash_device, #endif - - &bfin_gpios_device, }; static int __init cm_bf561_init(void) diff --git a/arch/blackfin/mach-bf561/boards/ezkit.c b/arch/blackfin/mach-bf561/boards/ezkit.c index caed96bb957e..9e2d8cfba546 100644 --- a/arch/blackfin/mach-bf561/boards/ezkit.c +++ b/arch/blackfin/mach-bf561/boards/ezkit.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf561/ezkit.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/device.h> @@ -387,19 +366,6 @@ static struct platform_device bfin_device_gpiokeys = { }; #endif -static struct resource bfin_gpios_resources = { - .start = 0, - .end = MAX_BLACKFIN_GPIOS - 1, - .flags = IORESOURCE_IRQ, -}; - -static struct platform_device bfin_gpios_device = { - .name = "simple-gpio", - .id = -1, - .num_resources = 1, - .resource = &bfin_gpios_resources, -}; - #if defined(CONFIG_I2C_GPIO) || defined(CONFIG_I2C_GPIO_MODULE) #include <linux/i2c-gpio.h> @@ -493,8 +459,6 @@ static struct platform_device *ezkit_devices[] __initdata = { &isp1362_hcd_device, #endif - &bfin_gpios_device, - #if defined(CONFIG_MTD_PHYSMAP) || defined(CONFIG_MTD_PHYSMAP_MODULE) &ezkit_flash_device, #endif diff --git a/arch/blackfin/mach-bf561/boards/tepla.c b/arch/blackfin/mach-bf561/boards/tepla.c index 6f77dbe952f5..8ba7252455e1 100644 --- a/arch/blackfin/mach-bf561/boards/tepla.c +++ b/arch/blackfin/mach-bf561/boards/tepla.c @@ -1,15 +1,13 @@ /* - * File: arch/blackfin/mach-bf561/tepla.c + * Copyright 2004-2007 Analog Devices Inc. + * 2005 National ICT Australia (NICTA) + * Aidan Williams <aidan@nicta.com.au> * - * Copyright 2004-2007 Analog Devices Inc. - * Only SMSC91C1111 was registered, may do more later. + * Thanks to Jamey Hicks. * - * Copyright 2005 National ICT Australia (NICTA), Aidan Williams <aidan@nicta.com.au> - * Thanks to Jamey Hicks. + * Only SMSC91C1111 was registered, may do more later. * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. + * Licensed under the GPL-2 */ #include <linux/device.h> diff --git a/arch/blackfin/mach-bf561/dma.c b/arch/blackfin/mach-bf561/dma.c index 42b0037afe61..c938c3c7355d 100644 --- a/arch/blackfin/mach-bf561/dma.c +++ b/arch/blackfin/mach-bf561/dma.c @@ -1,31 +1,11 @@ /* - * File: arch/blackfin/mach-bf561/dma.c - * Based on: - * Author: + * the simple DMA Implementation for Blackfin * - * Created: - * Description: This file contains the simple DMA Implementation for Blackfin + * Copyright 2007-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ + #include <linux/module.h> #include <asm/blackfin.h> diff --git a/arch/blackfin/mach-bf561/include/mach/bf561.h b/arch/blackfin/mach-bf561/include/mach/bf561.h index 9968362a2ee4..9f9a367e6a24 100644 --- a/arch/blackfin/mach-bf561/include/mach/bf561.h +++ b/arch/blackfin/mach-bf561/include/mach/bf561.h @@ -1,30 +1,9 @@ /* - * File: include/asm-blackfin/mach-bf561/bf561.h - * Based on: - * Author: + * SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF561 * - * Created: - * Description: SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF561 + * Copyright 2005-2008 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __MACH_BF561_H__ diff --git a/arch/blackfin/mach-bf561/include/mach/bfin_serial_5xx.h b/arch/blackfin/mach-bf561/include/mach/bfin_serial_5xx.h index fd5e8878b8c4..e33e158bc16d 100644 --- a/arch/blackfin/mach-bf561/include/mach/bfin_serial_5xx.h +++ b/arch/blackfin/mach-bf561/include/mach/bfin_serial_5xx.h @@ -1,32 +1,7 @@ /* - * file: include/asm-blackfin/mach-bf561/bfin_serial_5xx.h - * based on: - * author: + * Copyright 2006-2009 Analog Devices Inc. * - * created: - * description: - * blackfin serial driver head file - * rev: - * - * modified: - * - * - * bugs: enter bugs at http://blackfin.uclinux.org/ - * - * this program is free software; you can redistribute it and/or modify - * it under the terms of the gnu general public license as published by - * the free software foundation; either version 2, or (at your option) - * any later version. - * - * this program is distributed in the hope that it will be useful, - * but without any warranty; without even the implied warranty of - * merchantability or fitness for a particular purpose. see the - * gnu general public license for more details. - * - * you should have received a copy of the gnu general public license - * along with this program; see the file copying. - * if not, write to the free software foundation, - * 59 temple place - suite 330, boston, ma 02111-1307, usa. + * Licensed under the GPL-2 or later. */ #include <linux/serial.h> diff --git a/arch/blackfin/mach-bf561/include/mach/blackfin.h b/arch/blackfin/mach-bf561/include/mach/blackfin.h index 8be31358ef88..67d6bdcd3fa8 100644 --- a/arch/blackfin/mach-bf561/include/mach/blackfin.h +++ b/arch/blackfin/mach-bf561/include/mach/blackfin.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf561/blackfin.h - * Based on: - * Author: + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _MACH_BLACKFIN_H_ diff --git a/arch/blackfin/mach-bf561/include/mach/cdefBF561.h b/arch/blackfin/mach-bf561/include/mach/cdefBF561.h index 9d9858c2be68..81ecdb71c6af 100644 --- a/arch/blackfin/mach-bf561/include/mach/cdefBF561.h +++ b/arch/blackfin/mach-bf561/include/mach/cdefBF561.h @@ -1,31 +1,7 @@ /* - * File: include/asm-blackfin/mach-bf561/cdefBF561.h - * Based on: - * Author: + * Copyright 2005-2009 Analog Devices Inc. * - * Created: - * Description: C POINTERS TO SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF561 - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _CDEF_BF561_H diff --git a/arch/blackfin/mach-bf561/include/mach/defBF561.h b/arch/blackfin/mach-bf561/include/mach/defBF561.h index 5fc0f05026e0..a31e509553fb 100644 --- a/arch/blackfin/mach-bf561/include/mach/defBF561.h +++ b/arch/blackfin/mach-bf561/include/mach/defBF561.h @@ -1,32 +1,7 @@ - /* - * File: include/asm-blackfin/mach-bf561/defBF561.h - * Based on: - * Author: - * - * Created: - * Description: - * SYSTEM MMR REGISTER AND MEMORY MAP FOR ADSP-BF561 - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Copyright 2005-2009 Analog Devices Inc. * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the ADI BSD license or the GPL-2 (or later) */ #ifndef _DEF_BF561_H diff --git a/arch/blackfin/mach-bf561/include/mach/gpio.h b/arch/blackfin/mach-bf561/include/mach/gpio.h index 7882f79e1ade..a651a8cf805f 100644 --- a/arch/blackfin/mach-bf561/include/mach/gpio.h +++ b/arch/blackfin/mach-bf561/include/mach/gpio.h @@ -1,7 +1,4 @@ /* - * File: arch/blackfin/mach-bf561/include/mach/gpio.h - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * * Copyright (C) 2008 Analog Devices Inc. * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-bf561/include/mach/irq.h b/arch/blackfin/mach-bf561/include/mach/irq.h index 6698389c5564..7b208db267bf 100644 --- a/arch/blackfin/mach-bf561/include/mach/irq.h +++ b/arch/blackfin/mach-bf561/include/mach/irq.h @@ -1,32 +1,7 @@ - /* - * File: include/asm-blackfin/mach-bf561/irq.h - * Based on: - * Author: - * - * Created: - * Description: - * - * Rev: - * - * Modified: - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Copyright 2005-2008 Analog Devices Inc. * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. - * If not, write to the Free Software Foundation, - * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * Licensed under the GPL-2 or later. */ #ifndef _BF561_IRQ_H_ diff --git a/arch/blackfin/mach-bf561/include/mach/portmux.h b/arch/blackfin/mach-bf561/include/mach/portmux.h index 2e5ad6347dea..3a7b46bbe849 100644 --- a/arch/blackfin/mach-bf561/include/mach/portmux.h +++ b/arch/blackfin/mach-bf561/include/mach/portmux.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2009 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _MACH_PORTMUX_H_ #define _MACH_PORTMUX_H_ diff --git a/arch/blackfin/mach-bf561/include/mach/smp.h b/arch/blackfin/mach-bf561/include/mach/smp.h index f9e65ebe81b2..390c7f4ae7b3 100644 --- a/arch/blackfin/mach-bf561/include/mach/smp.h +++ b/arch/blackfin/mach-bf561/include/mach/smp.h @@ -1,3 +1,9 @@ +/* + * Copyright 2007-2008 Analog Devices Inc. + * + * Licensed under the GPL-2 or later. + */ + #ifndef _MACH_BF561_SMP #define _MACH_BF561_SMP diff --git a/arch/blackfin/mach-bf561/ints-priority.c b/arch/blackfin/mach-bf561/ints-priority.c index 9d2f23344720..b4424172ad9e 100644 --- a/arch/blackfin/mach-bf561/ints-priority.c +++ b/arch/blackfin/mach-bf561/ints-priority.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-bf561/ints-priority.c - * Based on: arch/blackfin/mach-bf537/ints-priority.c - * Author: Michael Hennerich + * Set up the interrupt priorities * - * Created: - * Description: Set up the interrupt priorities + * Copyright 2005-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/mach-bf561/secondary.S b/arch/blackfin/mach-bf561/secondary.S index f72a6af20c4f..8e6050369c06 100644 --- a/arch/blackfin/mach-bf561/secondary.S +++ b/arch/blackfin/mach-bf561/secondary.S @@ -1,26 +1,10 @@ /* - * File: arch/blackfin/mach-bf561/secondary.S - * Based on: arch/blackfin/mach-bf561/head.S - * Author: Philippe Gerum <rpm@xenomai.org> + * BF561 coreB bootstrap file * - * Copyright 2007 Analog Devices Inc. + * Copyright 2007-2009 Analog Devices Inc. + * Philippe Gerum <rpm@xenomai.org> * - * Description: BF561 coreB bootstrap file - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/linkage.h> diff --git a/arch/blackfin/mach-bf561/smp.c b/arch/blackfin/mach-bf561/smp.c index 8c10701c251f..510f57641495 100644 --- a/arch/blackfin/mach-bf561/smp.c +++ b/arch/blackfin/mach-bf561/smp.c @@ -1,23 +1,8 @@ /* - * File: arch/blackfin/mach-bf561/smp.c - * Author: Philippe Gerum <rpm@xenomai.org> + * Copyright 2007-2009 Analog Devices Inc. + * Philippe Gerum <rpm@xenomai.org> * - * Copyright 2007 Analog Devices Inc. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/init.h> diff --git a/arch/blackfin/mach-common/arch_checks.c b/arch/blackfin/mach-common/arch_checks.c index 5998d8632a73..9dbafcdcf479 100644 --- a/arch/blackfin/mach-common/arch_checks.c +++ b/arch/blackfin/mach-common/arch_checks.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-common/arch_checks.c - * Based on: - * Author: Robin Getz <rgetz@blackfin.uclinux.org> + * Do some checking to make sure things are OK * - * Created: 25Jul07 - * Description: Do some checking to make sure things are OK + * Copyright 2007-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <asm/fixed_code.h> diff --git a/arch/blackfin/mach-common/cache-c.c b/arch/blackfin/mach-common/cache-c.c index 4ebbd78db3a4..a60a24f5035d 100644 --- a/arch/blackfin/mach-common/cache-c.c +++ b/arch/blackfin/mach-common/cache-c.c @@ -3,8 +3,6 @@ * * Copyright 2004-2009 Analog Devices Inc. * - * Enter bugs at http://blackfin.uclinux.org/ - * * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-common/cache.S b/arch/blackfin/mach-common/cache.S index d9666fe6c3d6..ea540318a228 100644 --- a/arch/blackfin/mach-common/cache.S +++ b/arch/blackfin/mach-common/cache.S @@ -3,8 +3,6 @@ * * Copyright 2004-2008 Analog Devices Inc. * - * Enter bugs at http://blackfin.uclinux.org/ - * * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-common/cpufreq.c b/arch/blackfin/mach-common/cpufreq.c index 85c658083279..01506504e6d0 100644 --- a/arch/blackfin/mach-common/cpufreq.c +++ b/arch/blackfin/mach-common/cpufreq.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-common/cpufreq.c - * Based on: - * Author: + * Blackfin core clock scaling * - * Created: - * Description: Blackfin core clock scaling + * Copyright 2008-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/kernel.h> diff --git a/arch/blackfin/mach-common/entry.S b/arch/blackfin/mach-common/entry.S index 48692724b74c..a50637a8b9bd 100644 --- a/arch/blackfin/mach-common/entry.S +++ b/arch/blackfin/mach-common/entry.S @@ -1,32 +1,11 @@ /* - * File: arch/blackfin/mach-common/entry.S - * Based on: - * Author: Linus Torvalds + * Contains the system-call and fault low-level handling routines. + * This also contains the timer-interrupt handler, as well as all + * interrupts and faults that can result in a task-switch. * - * Created: ? - * Description: contains the system-call and fault low-level handling routines. - * This also contains the timer-interrupt handler, as well as all - * interrupts and faults that can result in a task-switch. + * Copyright 2005-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ /* NOTE: This code handles signal-recognition, which happens every time diff --git a/arch/blackfin/mach-common/head.S b/arch/blackfin/mach-common/head.S index 9c79dfea2a53..cab0a0031eee 100644 --- a/arch/blackfin/mach-common/head.S +++ b/arch/blackfin/mach-common/head.S @@ -3,8 +3,6 @@ * * Copyright 2004-2008 Analog Devices Inc. * - * Enter bugs at http://blackfin.uclinux.org/ - * * Licensed under the GPL-2 or later. */ diff --git a/arch/blackfin/mach-common/interrupt.S b/arch/blackfin/mach-common/interrupt.S index 82d417ef4b5b..8085ff1cce00 100644 --- a/arch/blackfin/mach-common/interrupt.S +++ b/arch/blackfin/mach-common/interrupt.S @@ -1,31 +1,11 @@ /* - * File: arch/blackfin/mach-common/interrupt.S - * Based on: - * Author: D. Jeff Dionne <jeff@ryeham.ee.ryerson.ca> - * Kenneth Albanowski <kjahds@kjahds.com> - * - * Created: ? - * Description: Interrupt Entries - * - * Modified: - * Copyright 2004-2006 Analog Devices Inc. + * Interrupt Entries * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. + * Copyright 2005-2009 Analog Devices Inc. + * D. Jeff Dionne <jeff@ryeham.ee.ryerson.ca> + * Kenneth Albanowski <kjahds@kjahds.com> * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <asm/blackfin.h> diff --git a/arch/blackfin/mach-common/ints-priority.c b/arch/blackfin/mach-common/ints-priority.c index 6ffda78aaf9d..660ea1bec54c 100644 --- a/arch/blackfin/mach-common/ints-priority.c +++ b/arch/blackfin/mach-common/ints-priority.c @@ -1,33 +1,14 @@ /* - * File: arch/blackfin/mach-common/ints-priority.c + * Set up the interrupt priorities * - * Description: Set up the interrupt priorities + * Copyright 2004-2009 Analog Devices Inc. + * 2003 Bas Vermeulen <bas@buyways.nl> + * 2002 Arcturus Networks Inc. MaTed <mated@sympatico.ca> + * 2000-2001 Lineo, Inc. D. Jefff Dionne <jeff@lineo.ca> + * 1999 D. Jeff Dionne <jeff@uclinux.org> + * 1996 Roman Zippel * - * Modified: - * 1996 Roman Zippel - * 1999 D. Jeff Dionne <jeff@uclinux.org> - * 2000-2001 Lineo, Inc. D. Jefff Dionne <jeff@lineo.ca> - * 2002 Arcturus Networks Inc. MaTed <mated@sympatico.ca> - * 2003 Metrowerks/Motorola - * 2003 Bas Vermeulen <bas@buyways.nl> - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 */ #include <linux/module.h> diff --git a/arch/blackfin/mach-common/irqpanic.c b/arch/blackfin/mach-common/irqpanic.c index 883e3241b17e..c6496249e2bc 100644 --- a/arch/blackfin/mach-common/irqpanic.c +++ b/arch/blackfin/mach-common/irqpanic.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mach-common/irqpanic.c - * Based on: - * Author: + * panic kernel with dump information * - * Created: ? - * Description: panic kernel with dump information + * Copyright 2005-2009 Analog Devices Inc. * - * Modified: rgetz - added cache checking code 14Feb06 - * Copyright 2004-2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/blackfin/mach-common/pm.c b/arch/blackfin/mach-common/pm.c index 0e3d4ff9d8b6..8837be4edb4a 100644 --- a/arch/blackfin/mach-common/pm.c +++ b/arch/blackfin/mach-common/pm.c @@ -1,35 +1,11 @@ /* - * File: arch/blackfin/mach-common/pm.c - * Based on: arm/mach-omap/pm.c - * Author: Cliff Brake <cbrake@accelent.com> Copyright (c) 2001 + * Blackfin power management * - * Created: 2001 - * Description: Blackfin power management + * Copyright 2006-2009 Analog Devices Inc. * - * Modified: Nicolas Pitre - PXA250 support - * Copyright (c) 2002 Monta Vista Software, Inc. - * David Singleton - OMAP1510 - * Copyright (c) 2002 Monta Vista Software, Inc. - * Dirk Behme <dirk.behme@de.bosch.com> - OMAP1510/1610 - * Copyright 2004 - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 + * based on arm/mach-omap/pm.c + * Copyright 2001, Cliff Brake <cbrake@accelent.com> and others */ #include <linux/suspend.h> diff --git a/arch/blackfin/mach-common/smp.c b/arch/blackfin/mach-common/smp.c index 349ee3f5466a..d98585f3237d 100644 --- a/arch/blackfin/mach-common/smp.c +++ b/arch/blackfin/mach-common/smp.c @@ -1,24 +1,10 @@ /* - * File: arch/blackfin/kernel/smp.c - * Author: Philippe Gerum <rpm@xenomai.org> - * IPI management based on arch/arm/kernel/smp.c. + * IPI management based on arch/arm/kernel/smp.c (Copyright 2002 ARM Limited) * - * Copyright 2007 Analog Devices Inc. + * Copyright 2007-2009 Analog Devices Inc. + * Philippe Gerum <rpm@xenomai.org> * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2. */ #include <linux/module.h> diff --git a/arch/blackfin/mm/blackfin_sram.h b/arch/blackfin/mm/blackfin_sram.h index bc0062884fde..fb0b1599cfb7 100644 --- a/arch/blackfin/mm/blackfin_sram.h +++ b/arch/blackfin/mm/blackfin_sram.h @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mm/blackfin_sram.h - * Based on: arch/blackfin/mm/blackfin_sram.c - * Author: Mike Frysinger + * Local prototypes meant for internal use only * - * Created: Aug 2006 - * Description: Local prototypes meant for internal use only + * Copyright 2006-2009 Analog Devices Inc. * - * Modified: - * Copyright 2006 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #ifndef __BLACKFIN_SRAM_H__ diff --git a/arch/blackfin/mm/init.c b/arch/blackfin/mm/init.c index b88ce7fda548..bb9c98f9cb5b 100644 --- a/arch/blackfin/mm/init.c +++ b/arch/blackfin/mm/init.c @@ -1,30 +1,7 @@ /* - * File: arch/blackfin/mm/init.c - * Based on: - * Author: + * Copyright 2004-2009 Analog Devices Inc. * - * Created: - * Description: - * - * Modified: - * Copyright 2004-2007 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/swap.h> diff --git a/arch/blackfin/mm/isram-driver.c b/arch/blackfin/mm/isram-driver.c index beb1a608824c..84cdc5a1c139 100644 --- a/arch/blackfin/mm/isram-driver.c +++ b/arch/blackfin/mm/isram-driver.c @@ -1,19 +1,9 @@ /* - * Description: Instruction SRAM accessor functions for the Blackfin + * Instruction SRAM accessor functions for the Blackfin * * Copyright 2008 Analog Devices Inc. * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later */ #define pr_fmt(fmt) "isram: " fmt diff --git a/arch/blackfin/mm/sram-alloc.c b/arch/blackfin/mm/sram-alloc.c index eb63ab353e5a..f068c11ea98f 100644 --- a/arch/blackfin/mm/sram-alloc.c +++ b/arch/blackfin/mm/sram-alloc.c @@ -1,30 +1,9 @@ /* - * File: arch/blackfin/mm/sram-alloc.c - * Based on: - * Author: + * SRAM allocator for Blackfin on-chip memory * - * Created: - * Description: SRAM allocator for Blackfin L1 and L2 memory + * Copyright 2004-2009 Analog Devices Inc. * - * Modified: - * Copyright 2004-2008 Analog Devices Inc. - * - * Bugs: Enter bugs at http://blackfin.uclinux.org/ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, see the file COPYING, or write - * to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + * Licensed under the GPL-2 or later. */ #include <linux/module.h> diff --git a/arch/frv/kernel/signal.c b/arch/frv/kernel/signal.c index 6b0a2b6fed6a..0974c0ecc594 100644 --- a/arch/frv/kernel/signal.c +++ b/arch/frv/kernel/signal.c @@ -527,7 +527,7 @@ static void do_signal(void) no_signal: /* Did we come from a system call? */ - if (__frame->syscallno >= 0) { + if (__frame->syscallno != -1) { /* Restart the system call - no handlers present */ switch (__frame->gr8) { case -ERESTARTNOHAND: diff --git a/arch/ia64/include/asm/spinlock.h b/arch/ia64/include/asm/spinlock.h index 30bb930e1111..239ecdc9516d 100644 --- a/arch/ia64/include/asm/spinlock.h +++ b/arch/ia64/include/asm/spinlock.h @@ -25,61 +25,82 @@ * by atomically noting the tail and incrementing it by one (thus adding * ourself to the queue and noting our position), then waiting until the head * becomes equal to the the initial value of the tail. + * The pad bits in the middle are used to prevent the next_ticket number + * overflowing into the now_serving number. * - * 63 32 31 0 + * 31 17 16 15 14 0 * +----------------------------------------------------+ - * | next_ticket_number | now_serving | + * | now_serving | padding | next_ticket | * +----------------------------------------------------+ */ -#define TICKET_SHIFT 32 +#define TICKET_SHIFT 17 +#define TICKET_BITS 15 +#define TICKET_MASK ((1 << TICKET_BITS) - 1) static __always_inline void __ticket_spin_lock(raw_spinlock_t *lock) { - int *p = (int *)&lock->lock, turn, now_serving; + int *p = (int *)&lock->lock, ticket, serve; - now_serving = *p; - turn = ia64_fetchadd(1, p+1, acq); + ticket = ia64_fetchadd(1, p, acq); - if (turn == now_serving) + if (!(((ticket >> TICKET_SHIFT) ^ ticket) & TICKET_MASK)) return; - do { + ia64_invala(); + + for (;;) { + asm volatile ("ld4.c.nc %0=[%1]" : "=r"(serve) : "r"(p) : "memory"); + + if (!(((serve >> TICKET_SHIFT) ^ ticket) & TICKET_MASK)) + return; cpu_relax(); - } while (ACCESS_ONCE(*p) != turn); + } } static __always_inline int __ticket_spin_trylock(raw_spinlock_t *lock) { - long tmp = ACCESS_ONCE(lock->lock), try; - - if (!(((tmp >> TICKET_SHIFT) ^ tmp) & ((1L << TICKET_SHIFT) - 1))) { - try = tmp + (1L << TICKET_SHIFT); + int tmp = ACCESS_ONCE(lock->lock); - return ia64_cmpxchg(acq, &lock->lock, tmp, try, sizeof (tmp)) == tmp; - } + if (!(((tmp >> TICKET_SHIFT) ^ tmp) & TICKET_MASK)) + return ia64_cmpxchg(acq, &lock->lock, tmp, tmp + 1, sizeof (tmp)) == tmp; return 0; } static __always_inline void __ticket_spin_unlock(raw_spinlock_t *lock) { - int *p = (int *)&lock->lock; + unsigned short *p = (unsigned short *)&lock->lock + 1, tmp; - (void)ia64_fetchadd(1, p, rel); + asm volatile ("ld2.bias %0=[%1]" : "=r"(tmp) : "r"(p)); + ACCESS_ONCE(*p) = (tmp + 2) & ~1; +} + +static __always_inline void __ticket_spin_unlock_wait(raw_spinlock_t *lock) +{ + int *p = (int *)&lock->lock, ticket; + + ia64_invala(); + + for (;;) { + asm volatile ("ld4.c.nc %0=[%1]" : "=r"(ticket) : "r"(p) : "memory"); + if (!(((ticket >> TICKET_SHIFT) ^ ticket) & TICKET_MASK)) + return; + cpu_relax(); + } } static inline int __ticket_spin_is_locked(raw_spinlock_t *lock) { long tmp = ACCESS_ONCE(lock->lock); - return !!(((tmp >> TICKET_SHIFT) ^ tmp) & ((1L << TICKET_SHIFT) - 1)); + return !!(((tmp >> TICKET_SHIFT) ^ tmp) & TICKET_MASK); } static inline int __ticket_spin_is_contended(raw_spinlock_t *lock) { long tmp = ACCESS_ONCE(lock->lock); - return (((tmp >> TICKET_SHIFT) - tmp) & ((1L << TICKET_SHIFT) - 1)) > 1; + return ((tmp - (tmp >> TICKET_SHIFT)) & TICKET_MASK) > 1; } static inline int __raw_spin_is_locked(raw_spinlock_t *lock) @@ -116,8 +137,7 @@ static __always_inline void __raw_spin_lock_flags(raw_spinlock_t *lock, static inline void __raw_spin_unlock_wait(raw_spinlock_t *lock) { - while (__raw_spin_is_locked(lock)) - cpu_relax(); + __ticket_spin_unlock_wait(lock); } #define __raw_read_can_lock(rw) (*(volatile int *)(rw) >= 0) diff --git a/arch/ia64/include/asm/spinlock_types.h b/arch/ia64/include/asm/spinlock_types.h index b61d136d9bc2..474e46f1ab4a 100644 --- a/arch/ia64/include/asm/spinlock_types.h +++ b/arch/ia64/include/asm/spinlock_types.h @@ -6,7 +6,7 @@ #endif typedef struct { - volatile unsigned long lock; + volatile unsigned int lock; } raw_spinlock_t; #define __RAW_SPIN_LOCK_UNLOCKED { 0 } diff --git a/arch/ia64/kernel/mca.c b/arch/ia64/kernel/mca.c index d2877a7bfe2e..496ac7a99488 100644 --- a/arch/ia64/kernel/mca.c +++ b/arch/ia64/kernel/mca.c @@ -887,6 +887,60 @@ ia64_mca_modify_comm(const struct task_struct *previous_current) memcpy(current->comm, comm, sizeof(current->comm)); } +static void +finish_pt_regs(struct pt_regs *regs, const pal_min_state_area_t *ms, + unsigned long *nat) +{ + const u64 *bank; + + /* If ipsr.ic then use pmsa_{iip,ipsr,ifs}, else use + * pmsa_{xip,xpsr,xfs} + */ + if (ia64_psr(regs)->ic) { + regs->cr_iip = ms->pmsa_iip; + regs->cr_ipsr = ms->pmsa_ipsr; + regs->cr_ifs = ms->pmsa_ifs; + } else { + regs->cr_iip = ms->pmsa_xip; + regs->cr_ipsr = ms->pmsa_xpsr; + regs->cr_ifs = ms->pmsa_xfs; + } + regs->pr = ms->pmsa_pr; + regs->b0 = ms->pmsa_br0; + regs->ar_rsc = ms->pmsa_rsc; + copy_reg(&ms->pmsa_gr[1-1], ms->pmsa_nat_bits, ®s->r1, nat); + copy_reg(&ms->pmsa_gr[2-1], ms->pmsa_nat_bits, ®s->r2, nat); + copy_reg(&ms->pmsa_gr[3-1], ms->pmsa_nat_bits, ®s->r3, nat); + copy_reg(&ms->pmsa_gr[8-1], ms->pmsa_nat_bits, ®s->r8, nat); + copy_reg(&ms->pmsa_gr[9-1], ms->pmsa_nat_bits, ®s->r9, nat); + copy_reg(&ms->pmsa_gr[10-1], ms->pmsa_nat_bits, ®s->r10, nat); + copy_reg(&ms->pmsa_gr[11-1], ms->pmsa_nat_bits, ®s->r11, nat); + copy_reg(&ms->pmsa_gr[12-1], ms->pmsa_nat_bits, ®s->r12, nat); + copy_reg(&ms->pmsa_gr[13-1], ms->pmsa_nat_bits, ®s->r13, nat); + copy_reg(&ms->pmsa_gr[14-1], ms->pmsa_nat_bits, ®s->r14, nat); + copy_reg(&ms->pmsa_gr[15-1], ms->pmsa_nat_bits, ®s->r15, nat); + if (ia64_psr(regs)->bn) + bank = ms->pmsa_bank1_gr; + else + bank = ms->pmsa_bank0_gr; + copy_reg(&bank[16-16], ms->pmsa_nat_bits, ®s->r16, nat); + copy_reg(&bank[17-16], ms->pmsa_nat_bits, ®s->r17, nat); + copy_reg(&bank[18-16], ms->pmsa_nat_bits, ®s->r18, nat); + copy_reg(&bank[19-16], ms->pmsa_nat_bits, ®s->r19, nat); + copy_reg(&bank[20-16], ms->pmsa_nat_bits, ®s->r20, nat); + copy_reg(&bank[21-16], ms->pmsa_nat_bits, ®s->r21, nat); + copy_reg(&bank[22-16], ms->pmsa_nat_bits, ®s->r22, nat); + copy_reg(&bank[23-16], ms->pmsa_nat_bits, ®s->r23, nat); + copy_reg(&bank[24-16], ms->pmsa_nat_bits, ®s->r24, nat); + copy_reg(&bank[25-16], ms->pmsa_nat_bits, ®s->r25, nat); + copy_reg(&bank[26-16], ms->pmsa_nat_bits, ®s->r26, nat); + copy_reg(&bank[27-16], ms->pmsa_nat_bits, ®s->r27, nat); + copy_reg(&bank[28-16], ms->pmsa_nat_bits, ®s->r28, nat); + copy_reg(&bank[29-16], ms->pmsa_nat_bits, ®s->r29, nat); + copy_reg(&bank[30-16], ms->pmsa_nat_bits, ®s->r30, nat); + copy_reg(&bank[31-16], ms->pmsa_nat_bits, ®s->r31, nat); +} + /* On entry to this routine, we are running on the per cpu stack, see * mca_asm.h. The original stack has not been touched by this event. Some of * the original stack's registers will be in the RBS on this stack. This stack @@ -921,7 +975,6 @@ ia64_mca_modify_original_stack(struct pt_regs *regs, u64 r12 = ms->pmsa_gr[12-1], r13 = ms->pmsa_gr[13-1]; u64 ar_bspstore = regs->ar_bspstore; u64 ar_bsp = regs->ar_bspstore + (loadrs >> 16); - const u64 *bank; const char *msg; int cpu = smp_processor_id(); @@ -1024,54 +1077,9 @@ ia64_mca_modify_original_stack(struct pt_regs *regs, p = (char *)r12 - sizeof(*regs); old_regs = (struct pt_regs *)p; memcpy(old_regs, regs, sizeof(*regs)); - /* If ipsr.ic then use pmsa_{iip,ipsr,ifs}, else use - * pmsa_{xip,xpsr,xfs} - */ - if (ia64_psr(regs)->ic) { - old_regs->cr_iip = ms->pmsa_iip; - old_regs->cr_ipsr = ms->pmsa_ipsr; - old_regs->cr_ifs = ms->pmsa_ifs; - } else { - old_regs->cr_iip = ms->pmsa_xip; - old_regs->cr_ipsr = ms->pmsa_xpsr; - old_regs->cr_ifs = ms->pmsa_xfs; - } - old_regs->pr = ms->pmsa_pr; - old_regs->b0 = ms->pmsa_br0; old_regs->loadrs = loadrs; - old_regs->ar_rsc = ms->pmsa_rsc; old_unat = old_regs->ar_unat; - copy_reg(&ms->pmsa_gr[1-1], ms->pmsa_nat_bits, &old_regs->r1, &old_unat); - copy_reg(&ms->pmsa_gr[2-1], ms->pmsa_nat_bits, &old_regs->r2, &old_unat); - copy_reg(&ms->pmsa_gr[3-1], ms->pmsa_nat_bits, &old_regs->r3, &old_unat); - copy_reg(&ms->pmsa_gr[8-1], ms->pmsa_nat_bits, &old_regs->r8, &old_unat); - copy_reg(&ms->pmsa_gr[9-1], ms->pmsa_nat_bits, &old_regs->r9, &old_unat); - copy_reg(&ms->pmsa_gr[10-1], ms->pmsa_nat_bits, &old_regs->r10, &old_unat); - copy_reg(&ms->pmsa_gr[11-1], ms->pmsa_nat_bits, &old_regs->r11, &old_unat); - copy_reg(&ms->pmsa_gr[12-1], ms->pmsa_nat_bits, &old_regs->r12, &old_unat); - copy_reg(&ms->pmsa_gr[13-1], ms->pmsa_nat_bits, &old_regs->r13, &old_unat); - copy_reg(&ms->pmsa_gr[14-1], ms->pmsa_nat_bits, &old_regs->r14, &old_unat); - copy_reg(&ms->pmsa_gr[15-1], ms->pmsa_nat_bits, &old_regs->r15, &old_unat); - if (ia64_psr(old_regs)->bn) - bank = ms->pmsa_bank1_gr; - else - bank = ms->pmsa_bank0_gr; - copy_reg(&bank[16-16], ms->pmsa_nat_bits, &old_regs->r16, &old_unat); - copy_reg(&bank[17-16], ms->pmsa_nat_bits, &old_regs->r17, &old_unat); - copy_reg(&bank[18-16], ms->pmsa_nat_bits, &old_regs->r18, &old_unat); - copy_reg(&bank[19-16], ms->pmsa_nat_bits, &old_regs->r19, &old_unat); - copy_reg(&bank[20-16], ms->pmsa_nat_bits, &old_regs->r20, &old_unat); - copy_reg(&bank[21-16], ms->pmsa_nat_bits, &old_regs->r21, &old_unat); - copy_reg(&bank[22-16], ms->pmsa_nat_bits, &old_regs->r22, &old_unat); - copy_reg(&bank[23-16], ms->pmsa_nat_bits, &old_regs->r23, &old_unat); - copy_reg(&bank[24-16], ms->pmsa_nat_bits, &old_regs->r24, &old_unat); - copy_reg(&bank[25-16], ms->pmsa_nat_bits, &old_regs->r25, &old_unat); - copy_reg(&bank[26-16], ms->pmsa_nat_bits, &old_regs->r26, &old_unat); - copy_reg(&bank[27-16], ms->pmsa_nat_bits, &old_regs->r27, &old_unat); - copy_reg(&bank[28-16], ms->pmsa_nat_bits, &old_regs->r28, &old_unat); - copy_reg(&bank[29-16], ms->pmsa_nat_bits, &old_regs->r29, &old_unat); - copy_reg(&bank[30-16], ms->pmsa_nat_bits, &old_regs->r30, &old_unat); - copy_reg(&bank[31-16], ms->pmsa_nat_bits, &old_regs->r31, &old_unat); + finish_pt_regs(old_regs, ms, &old_unat); /* Next stack a struct switch_stack. mca_asm.S built a partial * switch_stack, copy it and fill in the blanks using pt_regs and @@ -1141,6 +1149,8 @@ ia64_mca_modify_original_stack(struct pt_regs *regs, no_mod: mprintk(KERN_INFO "cpu %d, %s %s, original stack not modified\n", smp_processor_id(), type, msg); + old_unat = regs->ar_unat; + finish_pt_regs(regs, ms, &old_unat); return previous_current; } diff --git a/arch/ia64/kernel/unaligned.c b/arch/ia64/kernel/unaligned.c index 6db08599ebbc..776dd40397e2 100644 --- a/arch/ia64/kernel/unaligned.c +++ b/arch/ia64/kernel/unaligned.c @@ -60,7 +60,6 @@ dump (const char *str, void *vp, size_t len) */ int no_unaligned_warning; int unaligned_dump_stack; -static int noprint_warning; /* * For M-unit: @@ -1357,9 +1356,8 @@ ia64_handle_unaligned (unsigned long ifa, struct pt_regs *regs) /* watch for command names containing %s */ printk(KERN_WARNING "%s", buf); } else { - if (no_unaligned_warning && !noprint_warning) { - noprint_warning = 1; - printk(KERN_WARNING "%s(%d) encountered an " + if (no_unaligned_warning) { + printk_once(KERN_WARNING "%s(%d) encountered an " "unaligned exception which required\n" "kernel assistance, which degrades " "the performance of the application.\n" diff --git a/arch/ia64/mm/tlb.c b/arch/ia64/mm/tlb.c index f426dc78d959..ee09d261f2e6 100644 --- a/arch/ia64/mm/tlb.c +++ b/arch/ia64/mm/tlb.c @@ -100,24 +100,36 @@ wrap_mmu_context (struct mm_struct *mm) * this primitive it can be moved up to a spinaphore.h header. */ struct spinaphore { - atomic_t cur; + unsigned long ticket; + unsigned long serve; }; static inline void spinaphore_init(struct spinaphore *ss, int val) { - atomic_set(&ss->cur, val); + ss->ticket = 0; + ss->serve = val; } static inline void down_spin(struct spinaphore *ss) { - while (unlikely(!atomic_add_unless(&ss->cur, -1, 0))) - while (atomic_read(&ss->cur) == 0) - cpu_relax(); + unsigned long t = ia64_fetchadd(1, &ss->ticket, acq), serve; + + if (time_before(t, ss->serve)) + return; + + ia64_invala(); + + for (;;) { + asm volatile ("ld4.c.nc %0=[%1]" : "=r"(serve) : "r"(&ss->serve) : "memory"); + if (time_before(t, serve)) + return; + cpu_relax(); + } } static inline void up_spin(struct spinaphore *ss) { - atomic_add(1, &ss->cur); + ia64_fetchadd(1, &ss->serve, rel); } static struct spinaphore ptcg_sem; diff --git a/arch/ia64/pci/pci.c b/arch/ia64/pci/pci.c index 7de76dd352fe..c0fca2c1c858 100644 --- a/arch/ia64/pci/pci.c +++ b/arch/ia64/pci/pci.c @@ -56,10 +56,13 @@ int raw_pci_read(unsigned int seg, unsigned int bus, unsigned int devfn, if ((seg | reg) <= 255) { addr = PCI_SAL_ADDRESS(seg, bus, devfn, reg); mode = 0; - } else { + } else if (sal_revision >= SAL_VERSION_CODE(3,2)) { addr = PCI_SAL_EXT_ADDRESS(seg, bus, devfn, reg); mode = 1; + } else { + return -EINVAL; } + result = ia64_sal_pci_config_read(addr, mode, len, &data); if (result != 0) return -EINVAL; @@ -80,9 +83,11 @@ int raw_pci_write(unsigned int seg, unsigned int bus, unsigned int devfn, if ((seg | reg) <= 255) { addr = PCI_SAL_ADDRESS(seg, bus, devfn, reg); mode = 0; - } else { + } else if (sal_revision >= SAL_VERSION_CODE(3,2)) { addr = PCI_SAL_EXT_ADDRESS(seg, bus, devfn, reg); mode = 1; + } else { + return -EINVAL; } result = ia64_sal_pci_config_write(addr, mode, len, value); if (result != 0) diff --git a/arch/ia64/sn/kernel/io_common.c b/arch/ia64/sn/kernel/io_common.c index 25831c47c579..308e6595110e 100644 --- a/arch/ia64/sn/kernel/io_common.c +++ b/arch/ia64/sn/kernel/io_common.c @@ -119,7 +119,6 @@ sn_pcidev_info_get(struct pci_dev *dev) * Additionally note that the struct sn_flush_device_war also has to be * removed from arch/ia64/sn/include/xtalk/hubdev.h */ -static u8 war_implemented = 0; static s64 sn_device_fixup_war(u64 nasid, u64 widget, int device, struct sn_flush_device_common *common) @@ -128,11 +127,8 @@ static s64 sn_device_fixup_war(u64 nasid, u64 widget, int device, struct sn_flush_device_war *dev_entry; struct ia64_sal_retval isrv = {0,0,0,0}; - if (!war_implemented) { - printk(KERN_WARNING "PROM version < 4.50 -- implementing old " - "PROM flush WAR\n"); - war_implemented = 1; - } + printk_once(KERN_WARNING + "PROM version < 4.50 -- implementing old PROM flush WAR\n"); war_list = kzalloc(DEV_PER_WIDGET * sizeof(*war_list), GFP_KERNEL); BUG_ON(!war_list); diff --git a/arch/ia64/sn/kernel/sn2/sn_hwperf.c b/arch/ia64/sn/kernel/sn2/sn_hwperf.c index 4c7e74790958..55ac3c4e11d2 100644 --- a/arch/ia64/sn/kernel/sn2/sn_hwperf.c +++ b/arch/ia64/sn/kernel/sn2/sn_hwperf.c @@ -786,17 +786,18 @@ sn_hwperf_ioctl(struct inode *in, struct file *fp, u32 op, unsigned long arg) break; case SN_HWPERF_GET_OBJ_NODE: - if (a.sz != sizeof(u64) || a.arg < 0) { + i = a.arg; + if (a.sz != sizeof(u64) || i < 0) { r = -EINVAL; goto error; } if ((r = sn_hwperf_enum_objects(&nobj, &objs)) == 0) { - if (a.arg >= nobj) { + if (i >= nobj) { r = -EINVAL; vfree(objs); goto error; } - if (objs[(i = a.arg)].id != a.arg) { + if (objs[i].id != a.arg) { for (i = 0; i < nobj; i++) { if (objs[i].id == a.arg) break; diff --git a/arch/m32r/Kconfig b/arch/m32r/Kconfig index c41234f1b825..3a9319f93e89 100644 --- a/arch/m32r/Kconfig +++ b/arch/m32r/Kconfig @@ -11,6 +11,9 @@ config M32R select HAVE_IDE select HAVE_OPROFILE select INIT_ALL_POSSIBLE + select HAVE_KERNEL_GZIP + select HAVE_KERNEL_BZIP2 + select HAVE_KERNEL_LZMA config SBUS bool diff --git a/arch/m32r/boot/compressed/Makefile b/arch/m32r/boot/compressed/Makefile index 560484ae35ec..177716b1d613 100644 --- a/arch/m32r/boot/compressed/Makefile +++ b/arch/m32r/boot/compressed/Makefile @@ -1,11 +1,11 @@ # -# linux/arch/sh/boot/compressed/Makefile +# linux/arch/m32r/boot/compressed/Makefile # # create a compressed vmlinux image from the original vmlinux # -targets := vmlinux vmlinux.bin vmlinux.bin.gz head.o misc.o \ - piggy.o vmlinux.lds +targets := vmlinux vmlinux.bin vmlinux.bin.gz vmlinux.bin.bz2 \ + vmlinux.bin.lzma head.o misc.o piggy.o vmlinux.lds OBJECTS = $(obj)/head.o $(obj)/misc.o @@ -27,6 +27,12 @@ $(obj)/vmlinux.bin: vmlinux FORCE $(obj)/vmlinux.bin.gz: $(obj)/vmlinux.bin FORCE $(call if_changed,gzip) +$(obj)/vmlinux.bin.bz2: $(obj)/vmlinux.bin FORCE + $(call if_changed,bzip2) + +$(obj)/vmlinux.bin.lzma: $(obj)/vmlinux.bin FORCE + $(call if_changed,lzma) + CFLAGS_misc.o += -fpic ifdef CONFIG_MMU @@ -37,5 +43,9 @@ endif OBJCOPYFLAGS += -R .empty_zero_page -$(obj)/piggy.o: $(obj)/vmlinux.scr $(obj)/vmlinux.bin.gz FORCE +suffix_$(CONFIG_KERNEL_GZIP) = gz +suffix_$(CONFIG_KERNEL_BZIP2) = bz2 +suffix_$(CONFIG_KERNEL_LZMA) = lzma + +$(obj)/piggy.o: $(obj)/vmlinux.scr $(obj)/vmlinux.bin.$(suffix-y) FORCE $(call if_changed,ld) diff --git a/arch/m32r/boot/compressed/misc.c b/arch/m32r/boot/compressed/misc.c index d394292498c0..370d60881977 100644 --- a/arch/m32r/boot/compressed/misc.c +++ b/arch/m32r/boot/compressed/misc.c @@ -9,140 +9,49 @@ * Adapted for SH by Stuart Menefy, Aug 1999 * * 2003-02-12: Support M32R by Takeo Takahashi - * This is based on arch/sh/boot/compressed/misc.c. */ -#include <linux/string.h> - /* * gzip declarations */ - -#define OF(args) args #define STATIC static #undef memset #undef memcpy #define memzero(s, n) memset ((s), 0, (n)) -typedef unsigned char uch; -typedef unsigned short ush; -typedef unsigned long ulg; - -#define WSIZE 0x8000 /* Window size must be at least 32k, */ - /* and a power of two */ - -static uch *inbuf; /* input buffer */ -static uch window[WSIZE]; /* Sliding window buffer */ - -static unsigned insize = 0; /* valid bytes in inbuf */ -static unsigned inptr = 0; /* index of next byte to be processed in inbuf */ -static unsigned outcnt = 0; /* bytes in output buffer */ - -/* gzip flag byte */ -#define ASCII_FLAG 0x01 /* bit 0 set: file probably ASCII text */ -#define CONTINUATION 0x02 /* bit 1 set: continuation of multi-part gzip file */ -#define EXTRA_FIELD 0x04 /* bit 2 set: extra field present */ -#define ORIG_NAME 0x08 /* bit 3 set: original file name present */ -#define COMMENT 0x10 /* bit 4 set: file comment present */ -#define ENCRYPTED 0x20 /* bit 5 set: file is encrypted */ -#define RESERVED 0xC0 /* bit 6,7: reserved */ - -#define get_byte() (inptr < insize ? inbuf[inptr++] : fill_inbuf()) - -/* Diagnostic functions */ -#ifdef DEBUG -# define Assert(cond,msg) {if(!(cond)) error(msg);} -# define Trace(x) fprintf x -# define Tracev(x) {if (verbose) fprintf x ;} -# define Tracevv(x) {if (verbose>1) fprintf x ;} -# define Tracec(c,x) {if (verbose && (c)) fprintf x ;} -# define Tracecv(c,x) {if (verbose>1 && (c)) fprintf x ;} -#else -# define Assert(cond,msg) -# define Trace(x) -# define Tracev(x) -# define Tracevv(x) -# define Tracec(c,x) -# define Tracecv(c,x) -#endif - -static int fill_inbuf(void); -static void flush_window(void); static void error(char *m); -static unsigned char *input_data; -static int input_len; - -static long bytes_out = 0; -static uch *output_data; -static unsigned long output_ptr = 0; - #include "m32r_sio.c" static unsigned long free_mem_ptr; static unsigned long free_mem_end_ptr; -#define HEAP_SIZE 0x10000 - -#include "../../../../lib/inflate.c" - -void* memset(void* s, int c, size_t n) +#ifdef CONFIG_KERNEL_BZIP2 +static void *memset(void *s, int c, size_t n) { - int i; - char *ss = (char*)s; + char *ss = s; - for (i=0;i<n;i++) ss[i] = c; + while (n--) + *ss++ = c; return s; } +#endif -void* memcpy(void* __dest, __const void* __src, - size_t __n) -{ - int i; - char *d = (char *)__dest, *s = (char *)__src; - - for (i=0;i<__n;i++) d[i] = s[i]; - return __dest; -} - -/* =========================================================================== - * Fill the input buffer. This is called only when the buffer is empty - * and at least one byte is really needed. - */ -static int fill_inbuf(void) -{ - if (insize != 0) { - error("ran out of input data"); - } - - inbuf = input_data; - insize = input_len; - inptr = 1; - return inbuf[0]; -} +#ifdef CONFIG_KERNEL_GZIP +#define BOOT_HEAP_SIZE 0x10000 +#include "../../../../lib/decompress_inflate.c" +#endif -/* =========================================================================== - * Write the output window window[0..outcnt-1] and update crc and bytes_out. - * (Used for the decompressed data only.) - */ -static void flush_window(void) -{ - ulg c = crc; /* temporary variable */ - unsigned n; - uch *in, *out, ch; +#ifdef CONFIG_KERNEL_BZIP2 +#define BOOT_HEAP_SIZE 0x400000 +#include "../../../../lib/decompress_bunzip2.c" +#endif - in = window; - out = &output_data[output_ptr]; - for (n = 0; n < outcnt; n++) { - ch = *out++ = *in++; - c = crc_32_tab[((int)c ^ ch) & 0xff] ^ (c >> 8); - } - crc = c; - bytes_out += (ulg)outcnt; - output_ptr += (ulg)outcnt; - outcnt = 0; -} +#ifdef CONFIG_KERNEL_LZMA +#define BOOT_HEAP_SIZE 0x10000 +#include "../../../../lib/decompress_unlzma.c" +#endif static void error(char *x) { @@ -153,20 +62,20 @@ static void error(char *x) while(1); /* Halt */ } -/* return decompressed size */ void decompress_kernel(int mmu_on, unsigned char *zimage_data, unsigned int zimage_len, unsigned long heap) { + unsigned char *input_data = zimage_data; + int input_len = zimage_len; + unsigned char *output_data; + output_data = (unsigned char *)CONFIG_MEMORY_START + 0x2000 + (mmu_on ? 0x80000000 : 0); free_mem_ptr = heap; - free_mem_end_ptr = free_mem_ptr + HEAP_SIZE; - input_data = zimage_data; - input_len = zimage_len; + free_mem_end_ptr = free_mem_ptr + BOOT_HEAP_SIZE; - makecrc(); - puts("Uncompressing Linux... "); - gunzip(); - puts("Ok, booting the kernel.\n"); + puts("\nDecompressing Linux... "); + decompress(input_data, input_len, NULL, NULL, output_data, NULL, error); + puts("done.\nBooting the kernel.\n"); } diff --git a/arch/m32r/kernel/smp.c b/arch/m32r/kernel/smp.c index 1b7598e6f6e8..31cef20b2996 100644 --- a/arch/m32r/kernel/smp.c +++ b/arch/m32r/kernel/smp.c @@ -17,6 +17,7 @@ #include <linux/irq.h> #include <linux/interrupt.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/mm.h> #include <linux/smp.h> @@ -805,7 +806,7 @@ unsigned long send_IPI_mask_phys(cpumask_t physid_mask, int ipi_num, if (mask & ~physids_coerce(phys_cpu_present_map)) BUG(); - if (ipi_num >= NR_IPIS) + if (ipi_num >= NR_IPIS || ipi_num < 0) BUG(); mask <<= IPI_SHIFT; diff --git a/arch/m32r/kernel/time.c b/arch/m32r/kernel/time.c index e7fee0f198d5..9cedcef11575 100644 --- a/arch/m32r/kernel/time.c +++ b/arch/m32r/kernel/time.c @@ -75,7 +75,7 @@ u32 arch_gettimeoffset(void) count = 0; count = (latch - count) * TICK_SIZE; - elapsed_time = (count + latch / 2) / latch; + elapsed_time = DIV_ROUND_CLOSEST(count, latch); /* NOTE: LATCH is equal to the "interval" value (= reload count). */ #else /* CONFIG_SMP */ @@ -93,7 +93,7 @@ u32 arch_gettimeoffset(void) p_count = count; count = (latch - count) * TICK_SIZE; - elapsed_time = (count + latch / 2) / latch; + elapsed_time = DIV_ROUND_CLOSEST(count, latch); /* NOTE: LATCH is equal to the "interval" value (= reload count). */ #endif /* CONFIG_SMP */ #elif defined(CONFIG_CHIP_M32310) @@ -211,7 +211,7 @@ void __init time_init(void) bus_clock = boot_cpu_data.bus_clock; divide = boot_cpu_data.timer_divide; - latch = (bus_clock/divide + HZ / 2) / HZ; + latch = DIV_ROUND_CLOSEST(bus_clock/divide, HZ); printk("Timer start : latch = %ld\n", latch); diff --git a/arch/m32r/kernel/vmlinux.lds.S b/arch/m32r/kernel/vmlinux.lds.S index 8ceb6181d805..7da94eaa082b 100644 --- a/arch/m32r/kernel/vmlinux.lds.S +++ b/arch/m32r/kernel/vmlinux.lds.S @@ -42,6 +42,8 @@ SECTIONS _etext = .; /* End of text section */ EXCEPTION_TABLE(16) + NOTES + RODATA RW_DATA_SECTION(32, PAGE_SIZE, THREAD_SIZE) _edata = .; /* End of data section */ diff --git a/arch/m68k/Kconfig b/arch/m68k/Kconfig index 29dd8489ffec..ecdc19a299b2 100644 --- a/arch/m68k/Kconfig +++ b/arch/m68k/Kconfig @@ -561,7 +561,7 @@ config HPAPCI config MVME147_SCC bool "SCC support for MVME147 serial ports" - depends on MVME147 + depends on MVME147 && BROKEN help This is the driver for the serial ports on the Motorola MVME147 boards. Everyone using one of these boards should say Y here. @@ -576,14 +576,14 @@ config SERIAL167 config MVME162_SCC bool "SCC support for MVME162 serial ports" - depends on MVME16x + depends on MVME16x && BROKEN help This is the driver for the serial ports on the Motorola MVME162 and 172 boards. Everyone using one of these boards should say Y here. config BVME6000_SCC bool "SCC support for BVME6000 serial ports" - depends on BVME6000 + depends on BVME6000 && BROKEN help This is the driver for the serial ports on the BVME4000 and BVME6000 boards from BVM Ltd. Everyone using one of these boards should say diff --git a/arch/m68knommu/kernel/asm-offsets.c b/arch/m68knommu/kernel/asm-offsets.c index 594ee0e657fe..9a8876f715d8 100644 --- a/arch/m68knommu/kernel/asm-offsets.c +++ b/arch/m68knommu/kernel/asm-offsets.c @@ -45,25 +45,25 @@ int main(void) DEFINE(THREAD_FPSTATE, offsetof(struct thread_struct, fpstate)); /* offsets into the pt_regs */ - DEFINE(PT_D0, offsetof(struct pt_regs, d0)); - DEFINE(PT_ORIG_D0, offsetof(struct pt_regs, orig_d0)); - DEFINE(PT_D1, offsetof(struct pt_regs, d1)); - DEFINE(PT_D2, offsetof(struct pt_regs, d2)); - DEFINE(PT_D3, offsetof(struct pt_regs, d3)); - DEFINE(PT_D4, offsetof(struct pt_regs, d4)); - DEFINE(PT_D5, offsetof(struct pt_regs, d5)); - DEFINE(PT_A0, offsetof(struct pt_regs, a0)); - DEFINE(PT_A1, offsetof(struct pt_regs, a1)); - DEFINE(PT_A2, offsetof(struct pt_regs, a2)); - DEFINE(PT_PC, offsetof(struct pt_regs, pc)); - DEFINE(PT_SR, offsetof(struct pt_regs, sr)); + DEFINE(PT_OFF_D0, offsetof(struct pt_regs, d0)); + DEFINE(PT_OFF_ORIG_D0, offsetof(struct pt_regs, orig_d0)); + DEFINE(PT_OFF_D1, offsetof(struct pt_regs, d1)); + DEFINE(PT_OFF_D2, offsetof(struct pt_regs, d2)); + DEFINE(PT_OFF_D3, offsetof(struct pt_regs, d3)); + DEFINE(PT_OFF_D4, offsetof(struct pt_regs, d4)); + DEFINE(PT_OFF_D5, offsetof(struct pt_regs, d5)); + DEFINE(PT_OFF_A0, offsetof(struct pt_regs, a0)); + DEFINE(PT_OFF_A1, offsetof(struct pt_regs, a1)); + DEFINE(PT_OFF_A2, offsetof(struct pt_regs, a2)); + DEFINE(PT_OFF_PC, offsetof(struct pt_regs, pc)); + DEFINE(PT_OFF_SR, offsetof(struct pt_regs, sr)); #ifdef CONFIG_COLDFIRE /* bitfields are a bit difficult */ - DEFINE(PT_FORMATVEC, offsetof(struct pt_regs, sr) - 2); + DEFINE(PT_OFF_FORMATVEC, offsetof(struct pt_regs, sr) - 2); #else /* bitfields are a bit difficult */ - DEFINE(PT_VECTOR, offsetof(struct pt_regs, pc) + 4); + DEFINE(PT_OFF_VECTOR, offsetof(struct pt_regs, pc) + 4); #endif /* signal defines */ diff --git a/arch/m68knommu/kernel/entry.S b/arch/m68knommu/kernel/entry.S index f56faa5c9cd9..56043ade3941 100644 --- a/arch/m68knommu/kernel/entry.S +++ b/arch/m68knommu/kernel/entry.S @@ -46,7 +46,7 @@ ENTRY(buserr) SAVE_ALL moveq #-1,%d0 - movel %d0,%sp@(PT_ORIG_D0) + movel %d0,%sp@(PT_OFF_ORIG_D0) movel %sp,%sp@- /* stack frame pointer argument */ jsr buserr_c addql #4,%sp @@ -55,7 +55,7 @@ ENTRY(buserr) ENTRY(trap) SAVE_ALL moveq #-1,%d0 - movel %d0,%sp@(PT_ORIG_D0) + movel %d0,%sp@(PT_OFF_ORIG_D0) movel %sp,%sp@- /* stack frame pointer argument */ jsr trap_c addql #4,%sp @@ -67,7 +67,7 @@ ENTRY(trap) ENTRY(dbginterrupt) SAVE_ALL moveq #-1,%d0 - movel %d0,%sp@(PT_ORIG_D0) + movel %d0,%sp@(PT_OFF_ORIG_D0) movel %sp,%sp@- /* stack frame pointer argument */ jsr dbginterrupt_c addql #4,%sp diff --git a/arch/m68knommu/mm/init.c b/arch/m68knommu/mm/init.c index b1703c67a4f1..f3236d0b522d 100644 --- a/arch/m68knommu/mm/init.c +++ b/arch/m68knommu/mm/init.c @@ -162,7 +162,7 @@ void free_initrd_mem(unsigned long start, unsigned long end) totalram_pages++; pages++; } - printk (KERN_NOTICE "Freeing initrd memory: %dk freed\n", pages); + printk (KERN_NOTICE "Freeing initrd memory: %dk freed\n", pages * (PAGE_SIZE / 1024)); } #endif diff --git a/arch/m68knommu/platform/5206e/config.c b/arch/m68knommu/platform/5206e/config.c index 0f41ba82a3b5..942397984c66 100644 --- a/arch/m68knommu/platform/5206e/config.c +++ b/arch/m68knommu/platform/5206e/config.c @@ -17,7 +17,6 @@ #include <asm/mcfsim.h> #include <asm/mcfuart.h> #include <asm/mcfdma.h> -#include <asm/mcfuart.h> /***************************************************************************/ diff --git a/arch/m68knommu/platform/68328/entry.S b/arch/m68knommu/platform/68328/entry.S index b1aef72f3baf..9d80d2c42866 100644 --- a/arch/m68knommu/platform/68328/entry.S +++ b/arch/m68knommu/platform/68328/entry.S @@ -39,17 +39,17 @@ .globl inthandler7 badsys: - movel #-ENOSYS,%sp@(PT_D0) + movel #-ENOSYS,%sp@(PT_OFF_D0) jra ret_from_exception do_trace: - movel #-ENOSYS,%sp@(PT_D0) /* needed for strace*/ + movel #-ENOSYS,%sp@(PT_OFF_D0) /* needed for strace*/ subql #4,%sp SAVE_SWITCH_STACK jbsr syscall_trace RESTORE_SWITCH_STACK addql #4,%sp - movel %sp@(PT_ORIG_D0),%d1 + movel %sp@(PT_OFF_ORIG_D0),%d1 movel #-ENOSYS,%d0 cmpl #NR_syscalls,%d1 jcc 1f @@ -57,7 +57,7 @@ do_trace: lea sys_call_table, %a0 jbsr %a0@(%d1) -1: movel %d0,%sp@(PT_D0) /* save the return value */ +1: movel %d0,%sp@(PT_OFF_D0) /* save the return value */ subql #4,%sp /* dummy return address */ SAVE_SWITCH_STACK jbsr syscall_trace @@ -75,7 +75,7 @@ ENTRY(system_call) jbsr set_esp0 addql #4,%sp - movel %sp@(PT_ORIG_D0),%d0 + movel %sp@(PT_OFF_ORIG_D0),%d0 movel %sp,%d1 /* get thread_info pointer */ andl #-THREAD_SIZE,%d1 @@ -88,10 +88,10 @@ ENTRY(system_call) lea sys_call_table,%a0 movel %a0@(%d0), %a0 jbsr %a0@ - movel %d0,%sp@(PT_D0) /* save the return value*/ + movel %d0,%sp@(PT_OFF_D0) /* save the return value*/ ret_from_exception: - btst #5,%sp@(PT_SR) /* check if returning to kernel*/ + btst #5,%sp@(PT_OFF_SR) /* check if returning to kernel*/ jeq Luser_return /* if so, skip resched, signals*/ Lkernel_return: @@ -133,7 +133,7 @@ Lreturn: */ inthandler1: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -144,7 +144,7 @@ inthandler1: inthandler2: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -155,7 +155,7 @@ inthandler2: inthandler3: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -166,7 +166,7 @@ inthandler3: inthandler4: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -177,7 +177,7 @@ inthandler4: inthandler5: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -188,7 +188,7 @@ inthandler5: inthandler6: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -199,7 +199,7 @@ inthandler6: inthandler7: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -210,7 +210,7 @@ inthandler7: inthandler: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and #0x3ff, %d0 movel %sp,%sp@- @@ -224,7 +224,7 @@ ret_from_interrupt: 2: RESTORE_ALL 1: - moveb %sp@(PT_SR), %d0 + moveb %sp@(PT_OFF_SR), %d0 and #7, %d0 jhi 2b diff --git a/arch/m68knommu/platform/68360/entry.S b/arch/m68knommu/platform/68360/entry.S index 55dfefe38642..6d3460a39cac 100644 --- a/arch/m68knommu/platform/68360/entry.S +++ b/arch/m68knommu/platform/68360/entry.S @@ -35,17 +35,17 @@ .globl inthandler badsys: - movel #-ENOSYS,%sp@(PT_D0) + movel #-ENOSYS,%sp@(PT_OFF_D0) jra ret_from_exception do_trace: - movel #-ENOSYS,%sp@(PT_D0) /* needed for strace*/ + movel #-ENOSYS,%sp@(PT_OFF_D0) /* needed for strace*/ subql #4,%sp SAVE_SWITCH_STACK jbsr syscall_trace RESTORE_SWITCH_STACK addql #4,%sp - movel %sp@(PT_ORIG_D0),%d1 + movel %sp@(PT_OFF_ORIG_D0),%d1 movel #-ENOSYS,%d0 cmpl #NR_syscalls,%d1 jcc 1f @@ -53,7 +53,7 @@ do_trace: lea sys_call_table, %a0 jbsr %a0@(%d1) -1: movel %d0,%sp@(PT_D0) /* save the return value */ +1: movel %d0,%sp@(PT_OFF_D0) /* save the return value */ subql #4,%sp /* dummy return address */ SAVE_SWITCH_STACK jbsr syscall_trace @@ -79,10 +79,10 @@ ENTRY(system_call) lea sys_call_table,%a0 movel %a0@(%d0), %a0 jbsr %a0@ - movel %d0,%sp@(PT_D0) /* save the return value*/ + movel %d0,%sp@(PT_OFF_D0) /* save the return value*/ ret_from_exception: - btst #5,%sp@(PT_SR) /* check if returning to kernel*/ + btst #5,%sp@(PT_OFF_SR) /* check if returning to kernel*/ jeq Luser_return /* if so, skip resched, signals*/ Lkernel_return: @@ -124,7 +124,7 @@ Lreturn: */ inthandler: SAVE_ALL - movew %sp@(PT_VECTOR), %d0 + movew %sp@(PT_OFF_VECTOR), %d0 and.l #0x3ff, %d0 lsr.l #0x02, %d0 @@ -139,7 +139,7 @@ ret_from_interrupt: 2: RESTORE_ALL 1: - moveb %sp@(PT_SR), %d0 + moveb %sp@(PT_OFF_SR), %d0 and #7, %d0 jhi 2b /* check if we need to do software interrupts */ diff --git a/arch/m68knommu/platform/coldfire/entry.S b/arch/m68knommu/platform/coldfire/entry.S index 3b471c0da24a..dd7d591f70ea 100644 --- a/arch/m68knommu/platform/coldfire/entry.S +++ b/arch/m68knommu/platform/coldfire/entry.S @@ -81,11 +81,11 @@ ENTRY(system_call) movel %d3,%a0 jbsr %a0@ - movel %d0,%sp@(PT_D0) /* save the return value */ + movel %d0,%sp@(PT_OFF_D0) /* save the return value */ jra ret_from_exception 1: - movel #-ENOSYS,%d2 /* strace needs -ENOSYS in PT_D0 */ - movel %d2,PT_D0(%sp) /* on syscall entry */ + movel #-ENOSYS,%d2 /* strace needs -ENOSYS in PT_OFF_D0 */ + movel %d2,PT_OFF_D0(%sp) /* on syscall entry */ subql #4,%sp SAVE_SWITCH_STACK jbsr syscall_trace @@ -93,7 +93,7 @@ ENTRY(system_call) addql #4,%sp movel %d3,%a0 jbsr %a0@ - movel %d0,%sp@(PT_D0) /* save the return value */ + movel %d0,%sp@(PT_OFF_D0) /* save the return value */ subql #4,%sp /* dummy return address */ SAVE_SWITCH_STACK jbsr syscall_trace @@ -104,7 +104,7 @@ ret_from_signal: ret_from_exception: move #0x2700,%sr /* disable intrs */ - btst #5,%sp@(PT_SR) /* check if returning to kernel */ + btst #5,%sp@(PT_OFF_SR) /* check if returning to kernel */ jeq Luser_return /* if so, skip resched, signals */ #ifdef CONFIG_PREEMPT @@ -142,8 +142,8 @@ Luser_return: Lreturn: move #0x2700,%sr /* disable intrs */ movel sw_usp,%a0 /* get usp */ - movel %sp@(PT_PC),%a0@- /* copy exception program counter */ - movel %sp@(PT_FORMATVEC),%a0@-/* copy exception format/vector/sr */ + movel %sp@(PT_OFF_PC),%a0@- /* copy exception program counter */ + movel %sp@(PT_OFF_FORMATVEC),%a0@- /* copy exception format/vector/sr */ moveml %sp@,%d1-%d5/%a0-%a2 lea %sp@(32),%sp /* space for 8 regs */ movel %sp@+,%d0 @@ -181,9 +181,9 @@ Lsignal_return: ENTRY(inthandler) SAVE_ALL moveq #-1,%d0 - movel %d0,%sp@(PT_ORIG_D0) + movel %d0,%sp@(PT_OFF_ORIG_D0) - movew %sp@(PT_FORMATVEC),%d0 /* put exception # in d0 */ + movew %sp@(PT_OFF_FORMATVEC),%d0 /* put exception # in d0 */ andl #0x03fc,%d0 /* mask out vector only */ movel %sp,%sp@- /* push regs arg */ @@ -203,7 +203,7 @@ ENTRY(inthandler) ENTRY(fasthandler) SAVE_LOCAL - movew %sp@(PT_FORMATVEC),%d0 + movew %sp@(PT_OFF_FORMATVEC),%d0 andl #0x03fc,%d0 /* mask out vector only */ movel %sp,%sp@- /* push regs arg */ diff --git a/arch/microblaze/kernel/entry.S b/arch/microblaze/kernel/entry.S index acc1f05d1e2c..e3ecb36dd554 100644 --- a/arch/microblaze/kernel/entry.S +++ b/arch/microblaze/kernel/entry.S @@ -592,6 +592,8 @@ C_ENTRY(full_exception_trap): nop mfs r7, rfsr; /* save FSR */ nop + mts rfsr, r0; /* Clear sticky fsr */ + nop la r12, r0, full_exception set_vms; rtbd r12, 0; diff --git a/arch/microblaze/kernel/hw_exception_handler.S b/arch/microblaze/kernel/hw_exception_handler.S index 6b0288ebccd6..2b86c03aa841 100644 --- a/arch/microblaze/kernel/hw_exception_handler.S +++ b/arch/microblaze/kernel/hw_exception_handler.S @@ -384,7 +384,7 @@ handle_other_ex: /* Handle Other exceptions here */ addk r8, r17, r0; /* Load exception address */ bralid r15, full_exception; /* Branch to the handler */ nop; - mts r0, rfsr; /* Clear sticky fsr */ + mts rfsr, r0; /* Clear sticky fsr */ nop /* diff --git a/arch/microblaze/kernel/process.c b/arch/microblaze/kernel/process.c index 4201c743cc9f..c592d475b3d8 100644 --- a/arch/microblaze/kernel/process.c +++ b/arch/microblaze/kernel/process.c @@ -235,7 +235,9 @@ void start_thread(struct pt_regs *regs, unsigned long pc, unsigned long usp) regs->pc = pc; regs->r1 = usp; regs->pt_mode = 0; +#ifdef CONFIG_MMU regs->msr |= MSR_UMS; +#endif } #ifdef CONFIG_MMU diff --git a/arch/mips/Kconfig b/arch/mips/Kconfig index 705a7a9170f3..1aad0d9f5074 100644 --- a/arch/mips/Kconfig +++ b/arch/mips/Kconfig @@ -1,6 +1,7 @@ config MIPS bool default y + select HAVE_GENERIC_DMA_COHERENT select HAVE_IDE select HAVE_OPROFILE select HAVE_ARCH_KGDB @@ -1012,9 +1013,9 @@ config BOOT_ELF32 config MIPS_L1_CACHE_SHIFT int - default "4" if MACH_DECSTATION || MIKROTIK_RB532 + default "4" if MACH_DECSTATION || MIKROTIK_RB532 || PMC_MSP4200_EVAL + default "6" if MIPS_CPU_SCACHE default "7" if SGI_IP22 || SGI_IP27 || SGI_IP28 || SNI_RM || CPU_CAVIUM_OCTEON - default "4" if PMC_MSP4200_EVAL default "5" config HAVE_STD_PC_SERIAL_PORT diff --git a/arch/mips/alchemy/common/irq.c b/arch/mips/alchemy/common/irq.c index c88c821b4c36..d670928afcfd 100644 --- a/arch/mips/alchemy/common/irq.c +++ b/arch/mips/alchemy/common/irq.c @@ -354,6 +354,28 @@ static void au1x_ic1_ack(unsigned int irq_nr) au_sync(); } +static void au1x_ic0_maskack(unsigned int irq_nr) +{ + unsigned int bit = irq_nr - AU1000_INTC0_INT_BASE; + + au_writel(1 << bit, IC0_WAKECLR); + au_writel(1 << bit, IC0_MASKCLR); + au_writel(1 << bit, IC0_RISINGCLR); + au_writel(1 << bit, IC0_FALLINGCLR); + au_sync(); +} + +static void au1x_ic1_maskack(unsigned int irq_nr) +{ + unsigned int bit = irq_nr - AU1000_INTC1_INT_BASE; + + au_writel(1 << bit, IC1_WAKECLR); + au_writel(1 << bit, IC1_MASKCLR); + au_writel(1 << bit, IC1_RISINGCLR); + au_writel(1 << bit, IC1_FALLINGCLR); + au_sync(); +} + static int au1x_ic1_setwake(unsigned int irq, unsigned int on) { unsigned int bit = irq - AU1000_INTC1_INT_BASE; @@ -379,25 +401,21 @@ static int au1x_ic1_setwake(unsigned int irq, unsigned int on) /* * irq_chips for both ICs; this way the mask handlers can be * as short as possible. - * - * NOTE: the ->ack() callback is used by the handle_edge_irq - * flowhandler only, the ->mask_ack() one by handle_level_irq, - * so no need for an irq_chip for each type of irq (level/edge). */ static struct irq_chip au1x_ic0_chip = { .name = "Alchemy-IC0", - .ack = au1x_ic0_ack, /* edge */ + .ack = au1x_ic0_ack, .mask = au1x_ic0_mask, - .mask_ack = au1x_ic0_mask, /* level */ + .mask_ack = au1x_ic0_maskack, .unmask = au1x_ic0_unmask, .set_type = au1x_ic_settype, }; static struct irq_chip au1x_ic1_chip = { .name = "Alchemy-IC1", - .ack = au1x_ic1_ack, /* edge */ + .ack = au1x_ic1_ack, .mask = au1x_ic1_mask, - .mask_ack = au1x_ic1_mask, /* level */ + .mask_ack = au1x_ic1_maskack, .unmask = au1x_ic1_unmask, .set_type = au1x_ic_settype, .set_wake = au1x_ic1_setwake, diff --git a/arch/mips/alchemy/mtx-1/board_setup.c b/arch/mips/alchemy/mtx-1/board_setup.c index cc32c69a74ad..45b61c9b82b9 100644 --- a/arch/mips/alchemy/mtx-1/board_setup.c +++ b/arch/mips/alchemy/mtx-1/board_setup.c @@ -69,6 +69,7 @@ void __init board_setup(void) #else au_writel(0xf, Au1500_PCI_CFG); #endif + board_pci_idsel = mtx1_pci_idsel; #endif /* Initialize sys_pinfunc */ @@ -85,8 +86,6 @@ void __init board_setup(void) alchemy_gpio_direction_output(211, 1); /* green on */ alchemy_gpio_direction_output(212, 0); /* red off */ - board_pci_idsel = mtx1_pci_idsel; - printk(KERN_INFO "4G Systems MTX-1 Board\n"); } diff --git a/arch/mips/ar7/platform.c b/arch/mips/ar7/platform.c index e2278c04459d..835f3f0319ca 100644 --- a/arch/mips/ar7/platform.c +++ b/arch/mips/ar7/platform.c @@ -503,6 +503,7 @@ static int __init ar7_register_devices(void) { u16 chip_id; int res; + u32 *bootcr, val; #ifdef CONFIG_SERIAL_8250 static struct uart_port uart_port[2]; @@ -595,7 +596,13 @@ static int __init ar7_register_devices(void) ar7_wdt_res.end = ar7_wdt_res.start + 0x20; - res = platform_device_register(&ar7_wdt); + bootcr = (u32 *)ioremap_nocache(AR7_REGS_DCL, 4); + val = *bootcr; + iounmap(bootcr); + + /* Register watchdog only if enabled in hardware */ + if (val & AR7_WDT_HW_ENA) + res = platform_device_register(&ar7_wdt); return res; } diff --git a/arch/mips/bcm47xx/prom.c b/arch/mips/bcm47xx/prom.c index 079e33d52783..fb284c3b2cff 100644 --- a/arch/mips/bcm47xx/prom.c +++ b/arch/mips/bcm47xx/prom.c @@ -100,7 +100,7 @@ static __init void prom_init_console(void) static __init void prom_init_cmdline(void) { - char buf[CL_SIZE]; + static char buf[CL_SIZE] __initdata; /* Get the kernel command line from CFE */ if (cfe_getenv("LINUX_CMDLINE", buf, CL_SIZE) >= 0) { diff --git a/arch/mips/bcm63xx/Makefile b/arch/mips/bcm63xx/Makefile index c146d1ededed..00064b660809 100644 --- a/arch/mips/bcm63xx/Makefile +++ b/arch/mips/bcm63xx/Makefile @@ -1,5 +1,5 @@ obj-y += clk.o cpu.o cs.o gpio.o irq.o prom.o setup.o timer.o \ - dev-dsp.o dev-enet.o dev-pcmcia.o dev-uart.o + dev-dsp.o dev-enet.o dev-pcmcia.o dev-uart.o dev-wdt.o obj-$(CONFIG_EARLY_PRINTK) += early_printk.o obj-y += boards/ diff --git a/arch/mips/bcm63xx/boards/board_bcm963xx.c b/arch/mips/bcm63xx/boards/board_bcm963xx.c index 78e155d21be6..05a35cf5963d 100644 --- a/arch/mips/bcm63xx/boards/board_bcm963xx.c +++ b/arch/mips/bcm63xx/boards/board_bcm963xx.c @@ -24,7 +24,6 @@ #include <bcm63xx_dev_enet.h> #include <bcm63xx_dev_dsp.h> #include <bcm63xx_dev_pcmcia.h> -#include <bcm63xx_dev_uart.h> #include <board_bcm963xx.h> #define PFX "board_bcm963xx: " @@ -794,8 +793,6 @@ int __init board_register_devices(void) { u32 val; - bcm63xx_uart_register(); - if (board.has_pccard) bcm63xx_pcmcia_register(); diff --git a/arch/mips/bcm63xx/cpu.c b/arch/mips/bcm63xx/cpu.c index 6dc43f0483e8..70378bb5e3f9 100644 --- a/arch/mips/bcm63xx/cpu.c +++ b/arch/mips/bcm63xx/cpu.c @@ -10,6 +10,7 @@ #include <linux/kernel.h> #include <linux/module.h> #include <linux/cpu.h> +#include <asm/cpu-info.h> #include <bcm63xx_cpu.h> #include <bcm63xx_regs.h> #include <bcm63xx_io.h> @@ -284,6 +285,7 @@ void __init bcm63xx_cpu_init(void) { unsigned int tmp, expected_cpu_id; struct cpuinfo_mips *c = ¤t_cpu_data; + unsigned int cpu = smp_processor_id(); /* soc registers location depends on cpu type */ expected_cpu_id = 0; @@ -293,6 +295,7 @@ void __init bcm63xx_cpu_init(void) * BCM6338 as the same PrId as BCM3302 see arch/mips/kernel/cpu-probe.c */ case CPU_BCM3302: + __cpu_name[cpu] = "Broadcom BCM6338"; expected_cpu_id = BCM6338_CPU_ID; bcm63xx_regs_base = bcm96338_regs_base; bcm63xx_irqs = bcm96338_irqs; diff --git a/arch/mips/bcm63xx/dev-uart.c b/arch/mips/bcm63xx/dev-uart.c index 5f3d89c4a988..b0519461ad9b 100644 --- a/arch/mips/bcm63xx/dev-uart.c +++ b/arch/mips/bcm63xx/dev-uart.c @@ -10,7 +10,6 @@ #include <linux/kernel.h> #include <linux/platform_device.h> #include <bcm63xx_cpu.h> -#include <bcm63xx_dev_uart.h> static struct resource uart_resources[] = { { @@ -39,3 +38,4 @@ int __init bcm63xx_uart_register(void) uart_resources[1].start = bcm63xx_get_irq_number(IRQ_UART0); return platform_device_register(&bcm63xx_uart_device); } +arch_initcall(bcm63xx_uart_register); diff --git a/arch/mips/bcm63xx/dev-wdt.c b/arch/mips/bcm63xx/dev-wdt.c new file mode 100644 index 000000000000..3e6c716a4c11 --- /dev/null +++ b/arch/mips/bcm63xx/dev-wdt.c @@ -0,0 +1,37 @@ +/* + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + * + * Copyright (C) 2008 Florian Fainelli <florian@openwrt.org> + */ + +#include <linux/init.h> +#include <linux/kernel.h> +#include <linux/platform_device.h> +#include <bcm63xx_cpu.h> + +static struct resource wdt_resources[] = { + { + .start = -1, /* filled at runtime */ + .end = -1, /* filled at runtime */ + .flags = IORESOURCE_MEM, + }, +}; + +static struct platform_device bcm63xx_wdt_device = { + .name = "bcm63xx-wdt", + .id = 0, + .num_resources = ARRAY_SIZE(wdt_resources), + .resource = wdt_resources, +}; + +int __init bcm63xx_wdt_register(void) +{ + wdt_resources[0].start = bcm63xx_regset_address(RSET_WDT); + wdt_resources[0].end = wdt_resources[0].start; + wdt_resources[0].end += RSET_WDT_SIZE - 1; + + return platform_device_register(&bcm63xx_wdt_device); +} +arch_initcall(bcm63xx_wdt_register); diff --git a/arch/mips/bcm63xx/setup.c b/arch/mips/bcm63xx/setup.c index b18a0ca926fa..d0056598fbfc 100644 --- a/arch/mips/bcm63xx/setup.c +++ b/arch/mips/bcm63xx/setup.c @@ -75,7 +75,9 @@ void bcm63xx_machine_reboot(void) bcm6348_a1_reboot(); printk(KERN_INFO "triggering watchdog soft-reset...\n"); - bcm_perf_writel(SYS_PLL_SOFT_RESET, PERF_SYS_PLL_CTL_REG); + reg = bcm_perf_readl(PERF_SYS_PLL_CTL_REG); + reg |= SYS_PLL_SOFT_RESET; + bcm_perf_writel(reg, PERF_SYS_PLL_CTL_REG); while (1) ; } diff --git a/arch/mips/cavium-octeon/octeon-irq.c b/arch/mips/cavium-octeon/octeon-irq.c index 384f1842bfb1..6f2acf09328d 100644 --- a/arch/mips/cavium-octeon/octeon-irq.c +++ b/arch/mips/cavium-octeon/octeon-irq.c @@ -17,6 +17,15 @@ DEFINE_RWLOCK(octeon_irq_ciu0_rwlock); DEFINE_RWLOCK(octeon_irq_ciu1_rwlock); DEFINE_SPINLOCK(octeon_irq_msi_lock); +static int octeon_coreid_for_cpu(int cpu) +{ +#ifdef CONFIG_SMP + return cpu_logical_map(cpu); +#else + return cvmx_get_core_num(); +#endif +} + static void octeon_irq_core_ack(unsigned int irq) { unsigned int bit = irq - OCTEON_IRQ_SW0; @@ -152,11 +161,10 @@ static void octeon_irq_ciu0_disable(unsigned int irq) int bit = irq - OCTEON_IRQ_WORKQ0; /* Bit 0-63 of EN0 */ unsigned long flags; uint64_t en0; -#ifdef CONFIG_SMP int cpu; write_lock_irqsave(&octeon_irq_ciu0_rwlock, flags); for_each_online_cpu(cpu) { - int coreid = cpu_logical_map(cpu); + int coreid = octeon_coreid_for_cpu(cpu); en0 = cvmx_read_csr(CVMX_CIU_INTX_EN0(coreid * 2)); en0 &= ~(1ull << bit); cvmx_write_csr(CVMX_CIU_INTX_EN0(coreid * 2), en0); @@ -167,26 +175,57 @@ static void octeon_irq_ciu0_disable(unsigned int irq) */ cvmx_read_csr(CVMX_CIU_INTX_EN0(cvmx_get_core_num() * 2)); write_unlock_irqrestore(&octeon_irq_ciu0_rwlock, flags); -#else - int coreid = cvmx_get_core_num(); - local_irq_save(flags); - en0 = cvmx_read_csr(CVMX_CIU_INTX_EN0(coreid * 2)); - en0 &= ~(1ull << bit); - cvmx_write_csr(CVMX_CIU_INTX_EN0(coreid * 2), en0); - cvmx_read_csr(CVMX_CIU_INTX_EN0(coreid * 2)); - local_irq_restore(flags); -#endif +} + +/* + * Enable the irq on the current core for chips that have the EN*_W1{S,C} + * registers. + */ +static void octeon_irq_ciu0_enable_v2(unsigned int irq) +{ + int index = cvmx_get_core_num() * 2; + u64 mask = 1ull << (irq - OCTEON_IRQ_WORKQ0); + + cvmx_write_csr(CVMX_CIU_INTX_EN0_W1S(index), mask); +} + +/* + * Disable the irq on the current core for chips that have the EN*_W1{S,C} + * registers. + */ +static void octeon_irq_ciu0_disable_v2(unsigned int irq) +{ + int index = cvmx_get_core_num() * 2; + u64 mask = 1ull << (irq - OCTEON_IRQ_WORKQ0); + + cvmx_write_csr(CVMX_CIU_INTX_EN0_W1C(index), mask); +} + +/* + * Disable the irq on the all cores for chips that have the EN*_W1{S,C} + * registers. + */ +static void octeon_irq_ciu0_disable_all_v2(unsigned int irq) +{ + u64 mask = 1ull << (irq - OCTEON_IRQ_WORKQ0); + int index; + int cpu; + for_each_online_cpu(cpu) { + index = octeon_coreid_for_cpu(cpu) * 2; + cvmx_write_csr(CVMX_CIU_INTX_EN0_W1C(index), mask); + } } #ifdef CONFIG_SMP static int octeon_irq_ciu0_set_affinity(unsigned int irq, const struct cpumask *dest) { int cpu; + unsigned long flags; int bit = irq - OCTEON_IRQ_WORKQ0; /* Bit 0-63 of EN0 */ - write_lock(&octeon_irq_ciu0_rwlock); + write_lock_irqsave(&octeon_irq_ciu0_rwlock, flags); for_each_online_cpu(cpu) { - int coreid = cpu_logical_map(cpu); + int coreid = octeon_coreid_for_cpu(cpu); uint64_t en0 = cvmx_read_csr(CVMX_CIU_INTX_EN0(coreid * 2)); if (cpumask_test_cpu(cpu, dest)) @@ -200,11 +239,45 @@ static int octeon_irq_ciu0_set_affinity(unsigned int irq, const struct cpumask * * of them are done. */ cvmx_read_csr(CVMX_CIU_INTX_EN0(cvmx_get_core_num() * 2)); - write_unlock(&octeon_irq_ciu0_rwlock); + write_unlock_irqrestore(&octeon_irq_ciu0_rwlock, flags); return 0; } + +/* + * Set affinity for the irq for chips that have the EN*_W1{S,C} + * registers. + */ +static int octeon_irq_ciu0_set_affinity_v2(unsigned int irq, + const struct cpumask *dest) +{ + int cpu; + int index; + u64 mask = 1ull << (irq - OCTEON_IRQ_WORKQ0); + for_each_online_cpu(cpu) { + index = octeon_coreid_for_cpu(cpu) * 2; + if (cpumask_test_cpu(cpu, dest)) + cvmx_write_csr(CVMX_CIU_INTX_EN0_W1S(index), mask); + else + cvmx_write_csr(CVMX_CIU_INTX_EN0_W1C(index), mask); + } + return 0; +} +#endif + +/* + * Newer octeon chips have support for lockless CIU operation. + */ +static struct irq_chip octeon_irq_chip_ciu0_v2 = { + .name = "CIU0", + .enable = octeon_irq_ciu0_enable_v2, + .disable = octeon_irq_ciu0_disable_all_v2, + .ack = octeon_irq_ciu0_disable_v2, + .eoi = octeon_irq_ciu0_enable_v2, +#ifdef CONFIG_SMP + .set_affinity = octeon_irq_ciu0_set_affinity_v2, #endif +}; static struct irq_chip octeon_irq_chip_ciu0 = { .name = "CIU0", @@ -269,11 +342,10 @@ static void octeon_irq_ciu1_disable(unsigned int irq) int bit = irq - OCTEON_IRQ_WDOG0; /* Bit 0-63 of EN1 */ unsigned long flags; uint64_t en1; -#ifdef CONFIG_SMP int cpu; write_lock_irqsave(&octeon_irq_ciu1_rwlock, flags); for_each_online_cpu(cpu) { - int coreid = cpu_logical_map(cpu); + int coreid = octeon_coreid_for_cpu(cpu); en1 = cvmx_read_csr(CVMX_CIU_INTX_EN1(coreid * 2 + 1)); en1 &= ~(1ull << bit); cvmx_write_csr(CVMX_CIU_INTX_EN1(coreid * 2 + 1), en1); @@ -284,26 +356,58 @@ static void octeon_irq_ciu1_disable(unsigned int irq) */ cvmx_read_csr(CVMX_CIU_INTX_EN1(cvmx_get_core_num() * 2 + 1)); write_unlock_irqrestore(&octeon_irq_ciu1_rwlock, flags); -#else - int coreid = cvmx_get_core_num(); - local_irq_save(flags); - en1 = cvmx_read_csr(CVMX_CIU_INTX_EN1(coreid * 2 + 1)); - en1 &= ~(1ull << bit); - cvmx_write_csr(CVMX_CIU_INTX_EN1(coreid * 2 + 1), en1); - cvmx_read_csr(CVMX_CIU_INTX_EN1(coreid * 2 + 1)); - local_irq_restore(flags); -#endif +} + +/* + * Enable the irq on the current core for chips that have the EN*_W1{S,C} + * registers. + */ +static void octeon_irq_ciu1_enable_v2(unsigned int irq) +{ + int index = cvmx_get_core_num() * 2 + 1; + u64 mask = 1ull << (irq - OCTEON_IRQ_WDOG0); + + cvmx_write_csr(CVMX_CIU_INTX_EN1_W1S(index), mask); +} + +/* + * Disable the irq on the current core for chips that have the EN*_W1{S,C} + * registers. + */ +static void octeon_irq_ciu1_disable_v2(unsigned int irq) +{ + int index = cvmx_get_core_num() * 2 + 1; + u64 mask = 1ull << (irq - OCTEON_IRQ_WDOG0); + + cvmx_write_csr(CVMX_CIU_INTX_EN1_W1C(index), mask); +} + +/* + * Disable the irq on the all cores for chips that have the EN*_W1{S,C} + * registers. + */ +static void octeon_irq_ciu1_disable_all_v2(unsigned int irq) +{ + u64 mask = 1ull << (irq - OCTEON_IRQ_WDOG0); + int index; + int cpu; + for_each_online_cpu(cpu) { + index = octeon_coreid_for_cpu(cpu) * 2 + 1; + cvmx_write_csr(CVMX_CIU_INTX_EN1_W1C(index), mask); + } } #ifdef CONFIG_SMP -static int octeon_irq_ciu1_set_affinity(unsigned int irq, const struct cpumask *dest) +static int octeon_irq_ciu1_set_affinity(unsigned int irq, + const struct cpumask *dest) { int cpu; + unsigned long flags; int bit = irq - OCTEON_IRQ_WDOG0; /* Bit 0-63 of EN1 */ - write_lock(&octeon_irq_ciu1_rwlock); + write_lock_irqsave(&octeon_irq_ciu1_rwlock, flags); for_each_online_cpu(cpu) { - int coreid = cpu_logical_map(cpu); + int coreid = octeon_coreid_for_cpu(cpu); uint64_t en1 = cvmx_read_csr(CVMX_CIU_INTX_EN1 (coreid * 2 + 1)); @@ -318,12 +422,46 @@ static int octeon_irq_ciu1_set_affinity(unsigned int irq, const struct cpumask * * of them are done. */ cvmx_read_csr(CVMX_CIU_INTX_EN1(cvmx_get_core_num() * 2 + 1)); - write_unlock(&octeon_irq_ciu1_rwlock); + write_unlock_irqrestore(&octeon_irq_ciu1_rwlock, flags); + + return 0; +} +/* + * Set affinity for the irq for chips that have the EN*_W1{S,C} + * registers. + */ +static int octeon_irq_ciu1_set_affinity_v2(unsigned int irq, + const struct cpumask *dest) +{ + int cpu; + int index; + u64 mask = 1ull << (irq - OCTEON_IRQ_WDOG0); + for_each_online_cpu(cpu) { + index = octeon_coreid_for_cpu(cpu) * 2 + 1; + if (cpumask_test_cpu(cpu, dest)) + cvmx_write_csr(CVMX_CIU_INTX_EN1_W1S(index), mask); + else + cvmx_write_csr(CVMX_CIU_INTX_EN1_W1C(index), mask); + } return 0; } #endif +/* + * Newer octeon chips have support for lockless CIU operation. + */ +static struct irq_chip octeon_irq_chip_ciu1_v2 = { + .name = "CIU0", + .enable = octeon_irq_ciu1_enable_v2, + .disable = octeon_irq_ciu1_disable_all_v2, + .ack = octeon_irq_ciu1_disable_v2, + .eoi = octeon_irq_ciu1_enable_v2, +#ifdef CONFIG_SMP + .set_affinity = octeon_irq_ciu1_set_affinity_v2, +#endif +}; + static struct irq_chip octeon_irq_chip_ciu1 = { .name = "CIU1", .enable = octeon_irq_ciu1_enable, @@ -420,6 +558,8 @@ static struct irq_chip octeon_irq_chip_msi = { void __init arch_init_irq(void) { int irq; + struct irq_chip *chip0; + struct irq_chip *chip1; #ifdef CONFIG_SMP /* Set the default affinity to the boot cpu. */ @@ -430,6 +570,16 @@ void __init arch_init_irq(void) if (NR_IRQS < OCTEON_IRQ_LAST) pr_err("octeon_irq_init: NR_IRQS is set too low\n"); + if (OCTEON_IS_MODEL(OCTEON_CN58XX_PASS2_X) || + OCTEON_IS_MODEL(OCTEON_CN56XX_PASS2_X) || + OCTEON_IS_MODEL(OCTEON_CN52XX_PASS2_X)) { + chip0 = &octeon_irq_chip_ciu0_v2; + chip1 = &octeon_irq_chip_ciu1_v2; + } else { + chip0 = &octeon_irq_chip_ciu0; + chip1 = &octeon_irq_chip_ciu1; + } + /* 0 - 15 reserved for i8259 master and slave controller. */ /* 17 - 23 Mips internal */ @@ -440,14 +590,12 @@ void __init arch_init_irq(void) /* 24 - 87 CIU_INT_SUM0 */ for (irq = OCTEON_IRQ_WORKQ0; irq <= OCTEON_IRQ_BOOTDMA; irq++) { - set_irq_chip_and_handler(irq, &octeon_irq_chip_ciu0, - handle_percpu_irq); + set_irq_chip_and_handler(irq, chip0, handle_percpu_irq); } /* 88 - 151 CIU_INT_SUM1 */ for (irq = OCTEON_IRQ_WDOG0; irq <= OCTEON_IRQ_RESERVED151; irq++) { - set_irq_chip_and_handler(irq, &octeon_irq_chip_ciu1, - handle_percpu_irq); + set_irq_chip_and_handler(irq, chip1, handle_percpu_irq); } #ifdef CONFIG_PCI_MSI @@ -505,14 +653,10 @@ asmlinkage void plat_irq_dispatch(void) #ifdef CONFIG_HOTPLUG_CPU static int is_irq_enabled_on_cpu(unsigned int irq, unsigned int cpu) { - unsigned int isset; -#ifdef CONFIG_SMP - int coreid = cpu_logical_map(cpu); -#else - int coreid = cvmx_get_core_num(); -#endif + unsigned int isset; + int coreid = octeon_coreid_for_cpu(cpu); int bit = (irq < OCTEON_IRQ_WDOG0) ? - irq - OCTEON_IRQ_WORKQ0 : irq - OCTEON_IRQ_WDOG0; + irq - OCTEON_IRQ_WORKQ0 : irq - OCTEON_IRQ_WDOG0; if (irq < 64) { isset = (cvmx_read_csr(CVMX_CIU_INTX_EN0(coreid * 2)) & (1ull << bit)) >> bit; diff --git a/arch/mips/cavium-octeon/smp.c b/arch/mips/cavium-octeon/smp.c index 32d51a31dc48..c198efdf583e 100644 --- a/arch/mips/cavium-octeon/smp.c +++ b/arch/mips/cavium-octeon/smp.c @@ -65,11 +65,12 @@ void octeon_send_ipi_single(int cpu, unsigned int action) cvmx_write_csr(CVMX_CIU_MBOX_SETX(coreid), action); } -static inline void octeon_send_ipi_mask(cpumask_t mask, unsigned int action) +static inline void octeon_send_ipi_mask(const struct cpumask *mask, + unsigned int action) { unsigned int i; - for_each_cpu_mask(i, mask) + for_each_cpu_mask(i, *mask) octeon_send_ipi_single(i, action); } diff --git a/arch/mips/configs/rbtx49xx_defconfig b/arch/mips/configs/rbtx49xx_defconfig index c69813b8488c..6c6a19aebe1f 100644 --- a/arch/mips/configs/rbtx49xx_defconfig +++ b/arch/mips/configs/rbtx49xx_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.29-rc7 -# Wed Mar 4 23:08:06 2009 +# Linux kernel version: 2.6.32-rc6 +# Sun Nov 8 22:59:47 2009 # CONFIG_MIPS=y @@ -9,16 +9,18 @@ CONFIG_MIPS=y # Machine selection # # CONFIG_MACH_ALCHEMY is not set +# CONFIG_AR7 is not set # CONFIG_BASLER_EXCITE is not set # CONFIG_BCM47XX is not set +# CONFIG_BCM63XX is not set # CONFIG_MIPS_COBALT is not set # CONFIG_MACH_DECSTATION is not set # CONFIG_MACH_JAZZ is not set # CONFIG_LASAT is not set -# CONFIG_LEMOTE_FULONG is not set +# CONFIG_MACH_LOONGSON is not set # CONFIG_MIPS_MALTA is not set # CONFIG_MIPS_SIM is not set -# CONFIG_MACH_EMMA is not set +# CONFIG_NEC_MARKEINS is not set # CONFIG_MACH_VR41XX is not set # CONFIG_NXP_STB220 is not set # CONFIG_NXP_STB225 is not set @@ -45,6 +47,7 @@ CONFIG_MACH_TX49XX=y # CONFIG_WR_PPMC is not set # CONFIG_CAVIUM_OCTEON_SIMULATOR is not set # CONFIG_CAVIUM_OCTEON_REFERENCE_BOARD is not set +# CONFIG_ALCHEMY_GPIO_INDIRECT is not set CONFIG_MACH_TXX9=y CONFIG_TOSHIBA_RBTX4927=y CONFIG_TOSHIBA_RBTX4938=y @@ -86,7 +89,6 @@ CONFIG_DMA_NONCOHERENT=y CONFIG_DMA_NEED_PCI_MAP_STATE=y CONFIG_EARLY_PRINTK=y CONFIG_SYS_HAS_EARLY_PRINTK=y -# CONFIG_HOTPLUG_CPU is not set # CONFIG_NO_IOPORT is not set CONFIG_GENERIC_GPIO=y CONFIG_CPU_BIG_ENDIAN=y @@ -101,7 +103,7 @@ CONFIG_MIPS_L1_CACHE_SHIFT=5 # # CPU selection # -# CONFIG_CPU_LOONGSON2 is not set +# CONFIG_CPU_LOONGSON2E is not set # CONFIG_CPU_MIPS32_R1 is not set # CONFIG_CPU_MIPS32_R2 is not set # CONFIG_CPU_MIPS64_R1 is not set @@ -137,6 +139,7 @@ CONFIG_32BIT=y CONFIG_PAGE_SIZE_4KB=y # CONFIG_PAGE_SIZE_8KB is not set # CONFIG_PAGE_SIZE_16KB is not set +# CONFIG_PAGE_SIZE_32KB is not set # CONFIG_PAGE_SIZE_64KB is not set CONFIG_CPU_HAS_PREFETCH=y CONFIG_MIPS_MT_DISABLED=y @@ -154,7 +157,10 @@ CONFIG_SPLIT_PTLOCK_CPUS=4 # CONFIG_PHYS_ADDR_T_64BIT is not set CONFIG_ZONE_DMA_FLAG=0 CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y +CONFIG_HAVE_MLOCK=y +CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_TICK_ONESHOT=y CONFIG_NO_HZ=y CONFIG_HIGH_RES_TIMERS=y @@ -175,6 +181,7 @@ CONFIG_PREEMPT_NONE=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -194,11 +201,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -209,8 +217,12 @@ CONFIG_SYSFS_DEPRECATED_V2=y # CONFIG_NAMESPACES is not set CONFIG_BLK_DEV_INITRD=y CONFIG_INITRAMFS_SOURCE="" +CONFIG_RD_GZIP=y +# CONFIG_RD_BZIP2 is not set +# CONFIG_RD_LZMA is not set CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y +CONFIG_ANON_INODES=y CONFIG_EMBEDDED=y CONFIG_SYSCTL_SYSCALL=y CONFIG_KALLSYMS=y @@ -220,25 +232,35 @@ CONFIG_PRINTK=y CONFIG_BUG=y CONFIG_ELF_CORE=y # CONFIG_PCSPKR_PLATFORM is not set -CONFIG_COMPAT_BRK=y CONFIG_BASE_FULL=y -# CONFIG_FUTEX is not set -CONFIG_ANON_INODES=y +CONFIG_FUTEX=y # CONFIG_EPOLL is not set CONFIG_SIGNALFD=y CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y + +# +# Kernel Performance Events And Counters +# CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y +CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set CONFIG_HAVE_OPROFILE=y -# CONFIG_HAVE_GENERIC_DMA_COHERENT is not set + +# +# GCOV-based kernel profiling +# +# CONFIG_GCOV_KERNEL is not set +# CONFIG_SLOW_WORK is not set +CONFIG_HAVE_GENERIC_DMA_COHERENT=y CONFIG_SLABINFO=y +CONFIG_RT_MUTEXES=y CONFIG_BASE_SMALL=0 CONFIG_MODULES=y # CONFIG_MODULE_FORCE_LOAD is not set @@ -246,8 +268,8 @@ CONFIG_MODULE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set -# CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_LBDAF is not set +# CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set # @@ -274,6 +296,7 @@ CONFIG_PCI_DOMAINS=y # CONFIG_ARCH_SUPPORTS_MSI is not set # CONFIG_PCI_LEGACY is not set # CONFIG_PCI_STUB is not set +# CONFIG_PCI_IOV is not set CONFIG_MMU=y # @@ -288,6 +311,7 @@ CONFIG_TRAD_SIGNALS=y # # Power management options # +CONFIG_ARCH_HIBERNATION_POSSIBLE=y CONFIG_ARCH_SUSPEND_POSSIBLE=y # CONFIG_PM is not set CONFIG_NET=y @@ -295,7 +319,6 @@ CONFIG_NET=y # # Networking options # -CONFIG_COMPAT_NET_DEV_OPS=y CONFIG_PACKET=y # CONFIG_PACKET_MMAP is not set CONFIG_UNIX=y @@ -311,6 +334,7 @@ CONFIG_IP_PNP=y # CONFIG_NET_IPIP is not set # CONFIG_NET_IPGRE is not set # CONFIG_IP_MROUTE is not set +# CONFIG_ARPD is not set # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set # CONFIG_INET_ESP is not set @@ -336,6 +360,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_LLC2 is not set # CONFIG_IPX is not set # CONFIG_ATALK is not set +# CONFIG_PHONET is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -347,7 +372,6 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_CAN is not set # CONFIG_IRDA is not set # CONFIG_BT is not set -# CONFIG_PHONET is not set # CONFIG_WIRELESS is not set # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set @@ -365,9 +389,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_AR7_PARTS is not set @@ -376,9 +400,9 @@ CONFIG_MTD_CMDLINE_PARTS=y # User Modules And Translation Layers # CONFIG_MTD_CHAR=y -# CONFIG_MTD_BLKDEVS is not set -# CONFIG_MTD_BLOCK is not set -# CONFIG_MTD_BLOCK_RO is not set +CONFIG_MTD_BLKDEVS=m +CONFIG_MTD_BLOCK=m +CONFIG_MTD_BLOCK_RO=m # CONFIG_FTL is not set # CONFIG_NFTL is not set # CONFIG_INFTL is not set @@ -414,16 +438,20 @@ CONFIG_MTD_CFI_UTIL=y # # Mapping drivers for chip access # -# CONFIG_MTD_COMPLEX_MAPPINGS is not set +CONFIG_MTD_COMPLEX_MAPPINGS=y CONFIG_MTD_PHYSMAP=y # CONFIG_MTD_PHYSMAP_COMPAT is not set +# CONFIG_MTD_PCI is not set +# CONFIG_MTD_GPIO_ADDR is not set # CONFIG_MTD_INTEL_VR_NOR is not set +CONFIG_MTD_RBTX4939=y # CONFIG_MTD_PLATRAM is not set # # Self-contained MTD device drivers # # CONFIG_MTD_PMC551 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -435,7 +463,15 @@ CONFIG_MTD_PHYSMAP=y # CONFIG_MTD_DOC2000 is not set # CONFIG_MTD_DOC2001 is not set # CONFIG_MTD_DOC2001PLUS is not set -# CONFIG_MTD_NAND is not set +CONFIG_MTD_NAND=m +# CONFIG_MTD_NAND_VERIFY_WRITE is not set +# CONFIG_MTD_NAND_ECC_SMC is not set +# CONFIG_MTD_NAND_MUSEUM_IDS is not set +CONFIG_MTD_NAND_IDS=m +# CONFIG_MTD_NAND_CAFE is not set +# CONFIG_MTD_NAND_NANDSIM is not set +# CONFIG_MTD_NAND_PLATFORM is not set +CONFIG_MTD_NAND_TXX9NDFMC=m # CONFIG_MTD_ONENAND is not set # @@ -471,6 +507,7 @@ CONFIG_IDE=y # # Please see Documentation/ide/ide.txt for help/info on IDE drives # +CONFIG_IDE_XFER_MODE=y CONFIG_IDE_TIMINGS=y # CONFIG_BLK_DEV_IDE_SATA is not set CONFIG_IDE_GD=y @@ -534,8 +571,13 @@ CONFIG_BLK_DEV_IDEDMA=y # # -# A new alternative FireWire stack is available with EXPERIMENTAL=y +# You can enable one or both FireWire driver stacks. # + +# +# See the help texts for more information. +# +# CONFIG_FIREWIRE is not set # CONFIG_IEEE1394 is not set # CONFIG_I2O is not set CONFIG_NETDEVICES=y @@ -574,6 +616,8 @@ CONFIG_MII=y # CONFIG_NET_VENDOR_3COM is not set CONFIG_SMC91X=y # CONFIG_DM9000 is not set +# CONFIG_ETHOC is not set +# CONFIG_DNET is not set # CONFIG_NET_TULIP is not set # CONFIG_HP100 is not set CONFIG_NE2000=y @@ -602,18 +646,15 @@ CONFIG_TC35815=y # CONFIG_SMSC9420 is not set # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_ATL2 is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# -# CONFIG_WLAN_PRE80211 is not set -# CONFIG_WLAN_80211 is not set -# CONFIG_IWLWIFI_LEDS is not set +# CONFIG_WLAN is not set # # Enable WiMAX (Networking options) to see the WiMAX drivers @@ -653,6 +694,7 @@ CONFIG_DEVKMEM=y # # Non-8250 serial port support # +# CONFIG_SERIAL_MAX3100 is not set CONFIG_SERIAL_CORE=y CONFIG_SERIAL_CORE_CONSOLE=y CONFIG_SERIAL_TXX9=y @@ -666,7 +708,9 @@ CONFIG_UNIX98_PTYS=y CONFIG_LEGACY_PTYS=y CONFIG_LEGACY_PTY_COUNT=256 # CONFIG_IPMI_HANDLER is not set -# CONFIG_HW_RANDOM is not set +CONFIG_HW_RANDOM=m +# CONFIG_HW_RANDOM_TIMERIOMEM is not set +CONFIG_HW_RANDOM_TX4939=m # CONFIG_R3964 is not set # CONFIG_APPLICOM is not set # CONFIG_RAW_DRIVER is not set @@ -686,6 +730,10 @@ CONFIG_SPI_TXX9=y # SPI Protocol Masters # # CONFIG_SPI_TLE62X0 is not set + +# +# PPS support +# CONFIG_ARCH_REQUIRE_GPIOLIB=y CONFIG_GPIOLIB=y @@ -701,17 +749,22 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # # CONFIG_GPIO_MAX7301 is not set # CONFIG_GPIO_MCP23S08 is not set +# CONFIG_GPIO_MC33880 is not set + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -740,28 +793,17 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_CORE is not set # CONFIG_MFD_SM501 is not set # CONFIG_HTC_PASIC3 is not set +# CONFIG_UCB1400_CORE is not set # CONFIG_MFD_TMIO is not set +# CONFIG_MFD_MC13783 is not set +# CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -# CONFIG_DAB is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support # +# CONFIG_VGA_ARB is not set # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -772,7 +814,42 @@ CONFIG_SSB_POSSIBLE=y # Display device support # # CONFIG_DISPLAY_SUPPORT is not set -# CONFIG_SOUND is not set +CONFIG_SOUND=m +# CONFIG_SOUND_OSS_CORE is not set +CONFIG_SND=m +CONFIG_SND_TIMER=m +CONFIG_SND_PCM=m +# CONFIG_SND_SEQUENCER is not set +# CONFIG_SND_MIXER_OSS is not set +# CONFIG_SND_PCM_OSS is not set +# CONFIG_SND_HRTIMER is not set +# CONFIG_SND_DYNAMIC_MINORS is not set +# CONFIG_SND_SUPPORT_OLD_API is not set +# CONFIG_SND_VERBOSE_PROCFS is not set +# CONFIG_SND_VERBOSE_PRINTK is not set +# CONFIG_SND_DEBUG is not set +CONFIG_SND_VMASTER=y +# CONFIG_SND_RAWMIDI_SEQ is not set +# CONFIG_SND_OPL3_LIB_SEQ is not set +# CONFIG_SND_OPL4_LIB_SEQ is not set +# CONFIG_SND_SBAWE_SEQ is not set +# CONFIG_SND_EMU10K1_SEQ is not set +CONFIG_SND_AC97_CODEC=m +# CONFIG_SND_DRIVERS is not set +# CONFIG_SND_PCI is not set +# CONFIG_SND_SPI is not set +# CONFIG_SND_MIPS is not set +CONFIG_SND_SOC=m +CONFIG_SND_SOC_AC97_BUS=y +CONFIG_SND_SOC_TXX9ACLC=m +CONFIG_HAS_TXX9_ACLC=y +CONFIG_SND_SOC_TXX9ACLC_AC97=m +CONFIG_SND_SOC_TXX9ACLC_GENERIC=m +CONFIG_SND_SOC_I2C_AND_SPI=m +# CONFIG_SND_SOC_ALL_CODECS is not set +CONFIG_SND_SOC_AC97_CODEC=m +# CONFIG_SOUND_PRIME is not set +CONFIG_AC97_BUS=m # CONFIG_USB_SUPPORT is not set # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set @@ -783,6 +860,8 @@ CONFIG_LEDS_CLASS=y # LED drivers # CONFIG_LEDS_GPIO=y +CONFIG_LEDS_GPIO_PLATFORM=y +# CONFIG_LEDS_DAC124S085 is not set # # LED Triggers @@ -792,7 +871,12 @@ CONFIG_LEDS_TRIGGERS=y CONFIG_LEDS_TRIGGER_IDE_DISK=y CONFIG_LEDS_TRIGGER_HEARTBEAT=y # CONFIG_LEDS_TRIGGER_BACKLIGHT is not set +# CONFIG_LEDS_TRIGGER_GPIO is not set # CONFIG_LEDS_TRIGGER_DEFAULT_ON is not set + +# +# iptables trigger is under Netfilter config (LED target) +# # CONFIG_ACCESSIBILITY is not set # CONFIG_INFINIBAND is not set CONFIG_RTC_LIB=y @@ -820,6 +904,7 @@ CONFIG_RTC_INTF_DEV_UIE_EMUL=y # CONFIG_RTC_DRV_R9701 is not set CONFIG_RTC_DRV_RS5C348=y # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -840,8 +925,26 @@ CONFIG_RTC_DRV_DS1742=y # on-CPU RTC drivers # CONFIG_RTC_DRV_TX4939=y -# CONFIG_DMADEVICES is not set +CONFIG_DMADEVICES=y + +# +# DMA Devices +# +CONFIG_TXX9_DMAC=m +CONFIG_DMA_ENGINE=y + +# +# DMA Clients +# +# CONFIG_NET_DMA is not set +# CONFIG_ASYNC_TX_DMA is not set +# CONFIG_DMATEST is not set +# CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -853,9 +956,10 @@ CONFIG_RTC_DRV_TX4939=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set CONFIG_FS_POSIX_ACL=y -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set # CONFIG_OCFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -866,6 +970,10 @@ CONFIG_INOTIFY_USER=y CONFIG_GENERIC_ACL=y # +# Caches +# + +# # CD-ROM/DVD Filesystems # # CONFIG_ISO9660_FS is not set @@ -890,7 +998,27 @@ CONFIG_TMPFS=y CONFIG_TMPFS_POSIX_ACL=y # CONFIG_HUGETLB_PAGE is not set # CONFIG_CONFIGFS_FS is not set -# CONFIG_MISC_FILESYSTEMS is not set +CONFIG_MISC_FILESYSTEMS=y +# CONFIG_HFSPLUS_FS is not set +CONFIG_JFFS2_FS=m +CONFIG_JFFS2_FS_DEBUG=0 +CONFIG_JFFS2_FS_WRITEBUFFER=y +# CONFIG_JFFS2_FS_WBUF_VERIFY is not set +# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set +CONFIG_JFFS2_ZLIB=y +# CONFIG_JFFS2_LZO is not set +CONFIG_JFFS2_RTIME=y +# CONFIG_JFFS2_RUBIN is not set +# CONFIG_CRAMFS is not set +# CONFIG_SQUASHFS is not set +# CONFIG_VXFS_FS is not set +# CONFIG_MINIX_FS is not set +# CONFIG_OMFS_FS is not set +# CONFIG_HPFS_FS is not set +# CONFIG_QNX4FS_FS is not set +# CONFIG_ROMFS_FS is not set +# CONFIG_SYSV_FS is not set +# CONFIG_UFS_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -922,6 +1050,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +CONFIG_STRIP_ASM_SYMS=y # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -929,11 +1058,9 @@ CONFIG_DEBUG_FS=y # CONFIG_DEBUG_MEMORY_INIT is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set CONFIG_SYSCTL_SYSCALL_CHECK=y - -# -# Tracers -# -# CONFIG_DYNAMIC_PRINTK_DEBUG is not set +CONFIG_TRACING_SUPPORT=y +# CONFIG_FTRACE is not set +# CONFIG_DYNAMIC_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y CONFIG_CMDLINE="" @@ -946,6 +1073,7 @@ CONFIG_CMDLINE="" # CONFIG_SECURITYFS is not set # CONFIG_SECURITY_FILE_CAPABILITIES is not set # CONFIG_CRYPTO is not set +# CONFIG_BINARY_PRINTF is not set # # Library routines @@ -959,6 +1087,10 @@ CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC32=y # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set +CONFIG_ZLIB_INFLATE=y +CONFIG_ZLIB_DEFLATE=m +CONFIG_DECOMPRESS_GZIP=y CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y +CONFIG_NLATTR=y diff --git a/arch/mips/include/asm/dma-mapping.h b/arch/mips/include/asm/dma-mapping.h index d16afddb09a9..664ba53dc32a 100644 --- a/arch/mips/include/asm/dma-mapping.h +++ b/arch/mips/include/asm/dma-mapping.h @@ -3,6 +3,7 @@ #include <asm/scatterlist.h> #include <asm/cache.h> +#include <asm-generic/dma-coherent.h> void *dma_alloc_noncoherent(struct device *dev, size_t size, dma_addr_t *dma_handle, gfp_t flag); @@ -73,14 +74,4 @@ extern int dma_is_consistent(struct device *dev, dma_addr_t dma_addr); extern void dma_cache_sync(struct device *dev, void *vaddr, size_t size, enum dma_data_direction direction); -#if 0 -#define ARCH_HAS_DMA_DECLARE_COHERENT_MEMORY - -extern int dma_declare_coherent_memory(struct device *dev, dma_addr_t bus_addr, - dma_addr_t device_addr, size_t size, int flags); -extern void dma_release_declared_memory(struct device *dev); -extern void * dma_mark_declared_memory_occupied(struct device *dev, - dma_addr_t device_addr, size_t size); -#endif - #endif /* _ASM_DMA_MAPPING_H */ diff --git a/arch/mips/include/asm/fixmap.h b/arch/mips/include/asm/fixmap.h index efeddc8db8b1..0b89b83e2055 100644 --- a/arch/mips/include/asm/fixmap.h +++ b/arch/mips/include/asm/fixmap.h @@ -48,9 +48,9 @@ enum fixed_addresses { #define FIX_N_COLOURS 8 FIX_CMAP_BEGIN, #ifdef CONFIG_MIPS_MT_SMTC - FIX_CMAP_END = FIX_CMAP_BEGIN + (FIX_N_COLOURS * NR_CPUS), + FIX_CMAP_END = FIX_CMAP_BEGIN + (FIX_N_COLOURS * NR_CPUS * 2), #else - FIX_CMAP_END = FIX_CMAP_BEGIN + FIX_N_COLOURS, + FIX_CMAP_END = FIX_CMAP_BEGIN + (FIX_N_COLOURS * 2), #endif #ifdef CONFIG_HIGHMEM /* reserved pte's for temporary kernel mappings */ diff --git a/arch/mips/include/asm/gcmpregs.h b/arch/mips/include/asm/gcmpregs.h index 36fd969d64d6..c0cf76a2ca89 100644 --- a/arch/mips/include/asm/gcmpregs.h +++ b/arch/mips/include/asm/gcmpregs.h @@ -19,15 +19,20 @@ #define GCMP_GDB_OFS 0x8000 /* Global Debug Block */ /* Offsets to individual GCMP registers from GCMP base */ -#define GCMPOFS(block, tag, reg) (GCMP_##block##_OFS + GCMP_##tag##_##reg##_OFS) +#define GCMPOFS(block, tag, reg) \ + (GCMP_##block##_OFS + GCMP_##tag##_##reg##_OFS) +#define GCMPOFSn(block, tag, reg, n) \ + (GCMP_##block##_OFS + GCMP_##tag##_##reg##_OFS(n)) #define GCMPGCBOFS(reg) GCMPOFS(GCB, GCB, reg) +#define GCMPGCBOFSn(reg, n) GCMPOFSn(GCB, GCB, reg, n) #define GCMPCLCBOFS(reg) GCMPOFS(CLCB, CCB, reg) #define GCMPCOCBOFS(reg) GCMPOFS(COCB, CCB, reg) #define GCMPGDBOFS(reg) GCMPOFS(GDB, GDB, reg) /* GCMP register access */ #define GCMPGCB(reg) REGP(_gcmp_base, GCMPGCBOFS(reg)) +#define GCMPGCBn(reg, n) REGP(_gcmp_base, GCMPGCBOFSn(reg, n)) #define GCMPCLCB(reg) REGP(_gcmp_base, GCMPCLCBOFS(reg)) #define GCMPCOCB(reg) REGP(_gcmp_base, GCMPCOCBOFS(reg)) #define GCMPGDB(reg) REGP(_gcmp_base, GCMPGDBOFS(reg)) @@ -49,10 +54,10 @@ #define GCMP_GCB_GCMPB_GCMPBASE_MSK GCMPGCBMSK(GCMPB_GCMPBASE, 17) #define GCMP_GCB_GCMPB_CMDEFTGT_SHF 0 #define GCMP_GCB_GCMPB_CMDEFTGT_MSK GCMPGCBMSK(GCMPB_CMDEFTGT, 2) -#define GCMP_GCB_GCMPB_CMDEFTGT_MEM 0 -#define GCMP_GCB_GCMPB_CMDEFTGT_MEM1 1 -#define GCMP_GCB_GCMPB_CMDEFTGT_IOCU1 2 -#define GCMP_GCB_GCMPB_CMDEFTGT_IOCU2 3 +#define GCMP_GCB_GCMPB_CMDEFTGT_DISABLED 0 +#define GCMP_GCB_GCMPB_CMDEFTGT_MEM 1 +#define GCMP_GCB_GCMPB_CMDEFTGT_IOCU1 2 +#define GCMP_GCB_GCMPB_CMDEFTGT_IOCU2 3 #define GCMP_GCB_CCMC_OFS 0x0010 /* Global CM Control */ #define GCMP_GCB_GCSRAP_OFS 0x0020 /* Global CSR Access Privilege */ #define GCMP_GCB_GCSRAP_CMACCESS_SHF 0 @@ -115,5 +120,6 @@ #define GCMP_CCB_DBGGROUP_OFS 0x0100 /* DebugBreak Group */ extern int __init gcmp_probe(unsigned long, unsigned long); - +extern int __init gcmp_niocu(void); +extern void __init gcmp_setregion(int, unsigned long, unsigned long, int); #endif /* _ASM_GCMPREGS_H */ diff --git a/arch/mips/include/asm/gic.h b/arch/mips/include/asm/gic.h index a8f57341f123..9b9436a4d816 100644 --- a/arch/mips/include/asm/gic.h +++ b/arch/mips/include/asm/gic.h @@ -12,7 +12,6 @@ #define _ASM_GICREGS_H #undef GICISBYTELITTLEENDIAN -#define GICISWORDLITTLEENDIAN /* Constants */ #define GIC_POL_POS 1 @@ -20,11 +19,7 @@ #define GIC_TRIG_EDGE 1 #define GIC_TRIG_LEVEL 0 -#ifdef CONFIG_SMP #define GIC_NUM_INTRS (24 + NR_CPUS * 2) -#else -#define GIC_NUM_INTRS 32 -#endif #define MSK(n) ((1 << (n)) - 1) #define REG32(addr) (*(volatile unsigned int *) (addr)) @@ -70,13 +65,13 @@ #define USM_VISIBLE_SECTION_SIZE 0x10000 /* Register Map for Shared Section */ -#if defined(CONFIG_CPU_LITTLE_ENDIAN) || defined(GICISWORDLITTLEENDIAN) #define GIC_SH_CONFIG_OFS 0x0000 /* Shared Global Counter */ #define GIC_SH_COUNTER_31_00_OFS 0x0010 #define GIC_SH_COUNTER_63_32_OFS 0x0014 +#define GIC_SH_REVISIONID_OFS 0x0020 /* Interrupt Polarity */ #define GIC_SH_POL_31_0_OFS 0x0100 @@ -164,24 +159,31 @@ (GIC_SH_INTR_MAP_TO_VPE_BASE_OFS + (32 * (intr)) + (((vpe) / 32) * 4)) #define GIC_SH_MAP_TO_VPE_REG_BIT(vpe) (1 << ((vpe) % 32)) +/* Convert an interrupt number to a byte offset/bit for multi-word registers */ +#define GIC_INTR_OFS(intr) (((intr) / 32)*4) +#define GIC_INTR_BIT(intr) ((intr) % 32) + /* Polarity : Reset Value is always 0 */ #define GIC_SH_SET_POLARITY_OFS 0x0100 #define GIC_SET_POLARITY(intr, pol) \ - GICBIS(GIC_REG_ADDR(SHARED, GIC_SH_SET_POLARITY_OFS + (((intr) / 32) * 4)), (pol) << ((intr) % 32)) + GICBIS(GIC_REG_ADDR(SHARED, GIC_SH_SET_POLARITY_OFS + \ + GIC_INTR_OFS(intr)), (pol) << GIC_INTR_BIT(intr)) /* Triggering : Reset Value is always 0 */ #define GIC_SH_SET_TRIGGER_OFS 0x0180 #define GIC_SET_TRIGGER(intr, trig) \ - GICBIS(GIC_REG_ADDR(SHARED, GIC_SH_SET_TRIGGER_OFS + (((intr) / 32) * 4)), (trig) << ((intr) % 32)) + GICBIS(GIC_REG_ADDR(SHARED, GIC_SH_SET_TRIGGER_OFS + \ + GIC_INTR_OFS(intr)), (trig) << GIC_INTR_BIT(intr)) /* Mask manipulation */ #define GIC_SH_SMASK_OFS 0x0380 -#define GIC_SET_INTR_MASK(intr, val) \ - GICWRITE(GIC_REG_ADDR(SHARED, GIC_SH_SMASK_OFS + (((intr) / 32) * 4)), ((val) << ((intr) % 32))) - +#define GIC_SET_INTR_MASK(intr) \ + GICWRITE(GIC_REG_ADDR(SHARED, GIC_SH_SMASK_OFS + \ + GIC_INTR_OFS(intr)), 1 << GIC_INTR_BIT(intr)) #define GIC_SH_RMASK_OFS 0x0300 -#define GIC_CLR_INTR_MASK(intr, val) \ - GICWRITE(GIC_REG_ADDR(SHARED, GIC_SH_RMASK_OFS + (((intr) / 32) * 4)), ((val) << ((intr) % 32))) +#define GIC_CLR_INTR_MASK(intr) \ + GICWRITE(GIC_REG_ADDR(SHARED, GIC_SH_RMASK_OFS + \ + GIC_INTR_OFS(intr)), 1 << GIC_INTR_BIT(intr)) /* Register Map for Local Section */ #define GIC_VPE_CTL_OFS 0x0000 @@ -219,161 +221,6 @@ #define GIC_UMV_SH_COUNTER_31_00_OFS 0x0000 #define GIC_UMV_SH_COUNTER_63_32_OFS 0x0004 -#else /* CONFIG_CPU_BIG_ENDIAN */ - -#define GIC_SH_CONFIG_OFS 0x0000 - -/* Shared Global Counter */ -#define GIC_SH_COUNTER_31_00_OFS 0x0014 -#define GIC_SH_COUNTER_63_32_OFS 0x0010 - -/* Interrupt Polarity */ -#define GIC_SH_POL_31_0_OFS 0x0104 -#define GIC_SH_POL_63_32_OFS 0x0100 -#define GIC_SH_POL_95_64_OFS 0x010c -#define GIC_SH_POL_127_96_OFS 0x0108 -#define GIC_SH_POL_159_128_OFS 0x0114 -#define GIC_SH_POL_191_160_OFS 0x0110 -#define GIC_SH_POL_223_192_OFS 0x011c -#define GIC_SH_POL_255_224_OFS 0x0118 - -/* Edge/Level Triggering */ -#define GIC_SH_TRIG_31_0_OFS 0x0184 -#define GIC_SH_TRIG_63_32_OFS 0x0180 -#define GIC_SH_TRIG_95_64_OFS 0x018c -#define GIC_SH_TRIG_127_96_OFS 0x0188 -#define GIC_SH_TRIG_159_128_OFS 0x0194 -#define GIC_SH_TRIG_191_160_OFS 0x0190 -#define GIC_SH_TRIG_223_192_OFS 0x019c -#define GIC_SH_TRIG_255_224_OFS 0x0198 - -/* Dual Edge Triggering */ -#define GIC_SH_DUAL_31_0_OFS 0x0204 -#define GIC_SH_DUAL_63_32_OFS 0x0200 -#define GIC_SH_DUAL_95_64_OFS 0x020c -#define GIC_SH_DUAL_127_96_OFS 0x0208 -#define GIC_SH_DUAL_159_128_OFS 0x0214 -#define GIC_SH_DUAL_191_160_OFS 0x0210 -#define GIC_SH_DUAL_223_192_OFS 0x021c -#define GIC_SH_DUAL_255_224_OFS 0x0218 - -/* Set/Clear corresponding bit in Edge Detect Register */ -#define GIC_SH_WEDGE_OFS 0x0280 - -/* Reset Mask - Disables Interrupt */ -#define GIC_SH_RMASK_31_0_OFS 0x0304 -#define GIC_SH_RMASK_63_32_OFS 0x0300 -#define GIC_SH_RMASK_95_64_OFS 0x030c -#define GIC_SH_RMASK_127_96_OFS 0x0308 -#define GIC_SH_RMASK_159_128_OFS 0x0314 -#define GIC_SH_RMASK_191_160_OFS 0x0310 -#define GIC_SH_RMASK_223_192_OFS 0x031c -#define GIC_SH_RMASK_255_224_OFS 0x0318 - -/* Set Mask (WO) - Enables Interrupt */ -#define GIC_SH_SMASK_31_0_OFS 0x0384 -#define GIC_SH_SMASK_63_32_OFS 0x0380 -#define GIC_SH_SMASK_95_64_OFS 0x038c -#define GIC_SH_SMASK_127_96_OFS 0x0388 -#define GIC_SH_SMASK_159_128_OFS 0x0394 -#define GIC_SH_SMASK_191_160_OFS 0x0390 -#define GIC_SH_SMASK_223_192_OFS 0x039c -#define GIC_SH_SMASK_255_224_OFS 0x0398 - -/* Global Interrupt Mask Register (RO) - Bit Set == Interrupt enabled */ -#define GIC_SH_MASK_31_0_OFS 0x0404 -#define GIC_SH_MASK_63_32_OFS 0x0400 -#define GIC_SH_MASK_95_64_OFS 0x040c -#define GIC_SH_MASK_127_96_OFS 0x0408 -#define GIC_SH_MASK_159_128_OFS 0x0414 -#define GIC_SH_MASK_191_160_OFS 0x0410 -#define GIC_SH_MASK_223_192_OFS 0x041c -#define GIC_SH_MASK_255_224_OFS 0x0418 - -/* Pending Global Interrupts (RO) */ -#define GIC_SH_PEND_31_0_OFS 0x0484 -#define GIC_SH_PEND_63_32_OFS 0x0480 -#define GIC_SH_PEND_95_64_OFS 0x048c -#define GIC_SH_PEND_127_96_OFS 0x0488 -#define GIC_SH_PEND_159_128_OFS 0x0494 -#define GIC_SH_PEND_191_160_OFS 0x0490 -#define GIC_SH_PEND_223_192_OFS 0x049c -#define GIC_SH_PEND_255_224_OFS 0x0498 - -#define GIC_SH_INTR_MAP_TO_PIN_BASE_OFS 0x0500 - -/* Maps Interrupt X to a Pin */ -#define GIC_SH_MAP_TO_PIN(intr) \ - (GIC_SH_INTR_MAP_TO_PIN_BASE_OFS + (4 * intr)) - -#define GIC_SH_INTR_MAP_TO_VPE_BASE_OFS 0x2004 - -/* - * Maps Interrupt X to a VPE. This is more complex than the LE case, as - * odd and even registers need to be transposed. It does work - trust me! - */ -#define GIC_SH_MAP_TO_VPE_REG_OFF(intr, vpe) \ - (GIC_SH_INTR_MAP_TO_VPE_BASE_OFS + (32 * (intr)) + \ - (((((vpe) / 32) ^ 1) - 1) * 4)) -#define GIC_SH_MAP_TO_VPE_REG_BIT(vpe) (1 << ((vpe) % 32)) - -/* Polarity */ -#define GIC_SH_SET_POLARITY_OFS 0x0100 -#define GIC_SET_POLARITY(intr, pol) \ - GICBIS(GIC_REG_ADDR(SHARED, GIC_SH_SET_POLARITY_OFS + 4 + (((((intr) / 32) ^ 1) - 1) * 4)), (pol) << ((intr) % 32)) - -/* Triggering */ -#define GIC_SH_SET_TRIGGER_OFS 0x0180 -#define GIC_SET_TRIGGER(intr, trig) \ - GICBIS(GIC_REG_ADDR(SHARED, GIC_SH_SET_TRIGGER_OFS + 4 + (((((intr) / 32) ^ 1) - 1) * 4)), (trig) << ((intr) % 32)) - -/* Mask manipulation */ -#define GIC_SH_SMASK_OFS 0x0380 -#define GIC_SET_INTR_MASK(intr, val) \ - GICWRITE(GIC_REG_ADDR(SHARED, GIC_SH_SMASK_OFS + 4 + (((((intr) / 32) ^ 1) - 1) * 4)), ((val) << ((intr) % 32))) - -#define GIC_SH_RMASK_OFS 0x0300 -#define GIC_CLR_INTR_MASK(intr, val) \ - GICWRITE(GIC_REG_ADDR(SHARED, GIC_SH_RMASK_OFS + 4 + (((((intr) / 32) ^ 1) - 1) * 4)), ((val) << ((intr) % 32))) - -/* Register Map for Local Section */ -#define GIC_VPE_CTL_OFS 0x0000 -#define GIC_VPE_PEND_OFS 0x0004 -#define GIC_VPE_MASK_OFS 0x0008 -#define GIC_VPE_RMASK_OFS 0x000c -#define GIC_VPE_SMASK_OFS 0x0010 -#define GIC_VPE_WD_MAP_OFS 0x0040 -#define GIC_VPE_COMPARE_MAP_OFS 0x0044 -#define GIC_VPE_TIMER_MAP_OFS 0x0048 -#define GIC_VPE_PERFCTR_MAP_OFS 0x0050 -#define GIC_VPE_SWINT0_MAP_OFS 0x0054 -#define GIC_VPE_SWINT1_MAP_OFS 0x0058 -#define GIC_VPE_OTHER_ADDR_OFS 0x0080 -#define GIC_VPE_WD_CONFIG0_OFS 0x0090 -#define GIC_VPE_WD_COUNT0_OFS 0x0094 -#define GIC_VPE_WD_INITIAL0_OFS 0x0098 -#define GIC_VPE_COMPARE_LO_OFS 0x00a4 -#define GIC_VPE_COMPARE_HI_OFS 0x00a0 - -#define GIC_VPE_EIC_SHADOW_SET_BASE 0x0100 -#define GIC_VPE_EIC_SS(intr) \ - (GIC_EIC_SHADOW_SET_BASE + (4 * intr)) - -#define GIC_VPE_EIC_VEC_BASE 0x0800 -#define GIC_VPE_EIC_VEC(intr) \ - (GIC_VPE_EIC_VEC_BASE + (4 * intr)) - -#define GIC_VPE_TENABLE_NMI_OFS 0x1000 -#define GIC_VPE_TENABLE_YQ_OFS 0x1004 -#define GIC_VPE_TENABLE_INT_31_0_OFS 0x1080 -#define GIC_VPE_TENABLE_INT_63_32_OFS 0x1084 - -/* User Mode Visible Section Register Map */ -#define GIC_UMV_SH_COUNTER_31_00_OFS 0x0004 -#define GIC_UMV_SH_COUNTER_63_32_OFS 0x0000 - -#endif /* !LE */ - /* Masks */ #define GIC_SH_CONFIG_COUNTSTOP_SHF 28 #define GIC_SH_CONFIG_COUNTSTOP_MSK (MSK(1) << GIC_SH_CONFIG_COUNTSTOP_SHF) @@ -473,12 +320,13 @@ struct gic_intrmask_regs { * in building ipi_map. */ struct gic_intr_map { - unsigned int intrnum; /* Ext Intr Num */ unsigned int cpunum; /* Directed to this CPU */ unsigned int pin; /* Directed to this Pin */ unsigned int polarity; /* Polarity : +/- */ unsigned int trigtype; /* Trigger : Edge/Levl */ - unsigned int ipiflag; /* Is used for IPI ? */ + unsigned int flags; /* Misc flags */ +#define GIC_FLAG_IPI 0x01 +#define GIC_FLAG_TRANSPARENT 0x02 }; extern void gic_init(unsigned long gic_base_addr, diff --git a/arch/mips/include/asm/mach-ar7/ar7.h b/arch/mips/include/asm/mach-ar7/ar7.h index de71694614de..21cbbc706448 100644 --- a/arch/mips/include/asm/mach-ar7/ar7.h +++ b/arch/mips/include/asm/mach-ar7/ar7.h @@ -78,6 +78,9 @@ #define AR7_REF_CLOCK 25000000 #define AR7_XTAL_CLOCK 24000000 +/* DCL */ +#define AR7_WDT_HW_ENA 0x10 + struct plat_cpmac_data { int reset_bit; int power_bit; diff --git a/arch/mips/include/asm/mach-au1x00/gpio-au1000.h b/arch/mips/include/asm/mach-au1x00/gpio-au1000.h index feea00148b5d..91595fa89034 100644 --- a/arch/mips/include/asm/mach-au1x00/gpio-au1000.h +++ b/arch/mips/include/asm/mach-au1x00/gpio-au1000.h @@ -104,6 +104,8 @@ static inline int au1100_gpio2_to_irq(int gpio) if ((gpio >= 8) && (gpio <= 15)) return MAKE_IRQ(0, 29); /* shared GPIO208_215 */ + + return -ENXIO; } #ifdef CONFIG_SOC_AU1100 diff --git a/arch/mips/include/asm/mach-bcm63xx/bcm63xx_dev_uart.h b/arch/mips/include/asm/mach-bcm63xx/bcm63xx_dev_uart.h deleted file mode 100644 index bf348f573bbc..000000000000 --- a/arch/mips/include/asm/mach-bcm63xx/bcm63xx_dev_uart.h +++ /dev/null @@ -1,6 +0,0 @@ -#ifndef BCM63XX_DEV_UART_H_ -#define BCM63XX_DEV_UART_H_ - -int bcm63xx_uart_register(void); - -#endif /* BCM63XX_DEV_UART_H_ */ diff --git a/arch/mips/include/asm/mach-ip27/topology.h b/arch/mips/include/asm/mach-ip27/topology.h index f6837422fe65..09a59bcc1b07 100644 --- a/arch/mips/include/asm/mach-ip27/topology.h +++ b/arch/mips/include/asm/mach-ip27/topology.h @@ -44,8 +44,8 @@ extern unsigned char __node_distances[MAX_COMPACT_NODES][MAX_COMPACT_NODES]; .busy_factor = 32, \ .imbalance_pct = 125, \ .cache_nice_tries = 1, \ - .flags = SD_LOAD_BALANCE \ - | SD_BALANCE_EXEC \ + .flags = SD_LOAD_BALANCE | \ + SD_BALANCE_EXEC, \ .last_balance = jiffies, \ .balance_interval = 1, \ .nr_balance_failed = 0, \ diff --git a/arch/mips/include/asm/mach-loongson/cpu-feature-overrides.h b/arch/mips/include/asm/mach-loongson/cpu-feature-overrides.h index ce5b6e270e3f..9947e57c91de 100644 --- a/arch/mips/include/asm/mach-loongson/cpu-feature-overrides.h +++ b/arch/mips/include/asm/mach-loongson/cpu-feature-overrides.h @@ -29,7 +29,7 @@ #define cpu_has_cache_cdex_p 0 #define cpu_has_cache_cdex_s 0 #define cpu_has_counter 1 -#define cpu_has_dc_aliases 1 +#define cpu_has_dc_aliases (PAGE_SIZE < 0x4000) #define cpu_has_divec 0 #define cpu_has_dsp 0 #define cpu_has_ejtag 0 @@ -54,6 +54,5 @@ #define cpu_has_vce 0 #define cpu_has_vtag_icache 0 #define cpu_has_watch 1 -#define cpu_icache_snoops_remote_store 1 #endif /* __ASM_MACH_LOONGSON_CPU_FEATURE_OVERRIDES_H */ diff --git a/arch/mips/include/asm/mmu_context.h b/arch/mips/include/asm/mmu_context.h index d9743536a621..6083db586500 100644 --- a/arch/mips/include/asm/mmu_context.h +++ b/arch/mips/include/asm/mmu_context.h @@ -16,6 +16,7 @@ #include <linux/smp.h> #include <linux/slab.h> #include <asm/cacheflush.h> +#include <asm/hazards.h> #include <asm/tlbflush.h> #ifdef CONFIG_MIPS_MT_SMTC #include <asm/mipsmtregs.h> @@ -36,11 +37,13 @@ extern unsigned long pgd_current[]; #ifdef CONFIG_32BIT #define TLBMISS_HANDLER_SETUP() \ write_c0_context((unsigned long) smp_processor_id() << 25); \ + back_to_back_c0_hazard(); \ TLBMISS_HANDLER_SETUP_PGD(swapper_pg_dir) #endif #ifdef CONFIG_64BIT #define TLBMISS_HANDLER_SETUP() \ write_c0_context((unsigned long) smp_processor_id() << 26); \ + back_to_back_c0_hazard(); \ TLBMISS_HANDLER_SETUP_PGD(swapper_pg_dir) #endif @@ -165,12 +168,12 @@ static inline void switch_mm(struct mm_struct *prev, struct mm_struct *next, * having ASID_MASK smaller than the hardware maximum, * make sure no "soft" bits become "hard"... */ - write_c0_entryhi((read_c0_entryhi() & ~HW_ASID_MASK) - | (cpu_context(cpu, next) & ASID_MASK)); + write_c0_entryhi((read_c0_entryhi() & ~HW_ASID_MASK) | + cpu_asid(cpu, next)); ehb(); /* Make sure it propagates to TCStatus */ evpe(mtflags); #else - write_c0_entryhi(cpu_context(cpu, next)); + write_c0_entryhi(cpu_asid(cpu, next)); #endif /* CONFIG_MIPS_MT_SMTC */ TLBMISS_HANDLER_SETUP_PGD(next->pgd); @@ -226,11 +229,11 @@ activate_mm(struct mm_struct *prev, struct mm_struct *next) } /* See comments for similar code above */ write_c0_entryhi((read_c0_entryhi() & ~HW_ASID_MASK) | - (cpu_context(cpu, next) & ASID_MASK)); + cpu_asid(cpu, next)); ehb(); /* Make sure it propagates to TCStatus */ evpe(mtflags); #else - write_c0_entryhi(cpu_context(cpu, next)); + write_c0_entryhi(cpu_asid(cpu, next)); #endif /* CONFIG_MIPS_MT_SMTC */ TLBMISS_HANDLER_SETUP_PGD(next->pgd); diff --git a/arch/mips/include/asm/setup.h b/arch/mips/include/asm/setup.h index e600cedda976..50511aac04e9 100644 --- a/arch/mips/include/asm/setup.h +++ b/arch/mips/include/asm/setup.h @@ -1,7 +1,7 @@ #ifndef _MIPS_SETUP_H #define _MIPS_SETUP_H -#define COMMAND_LINE_SIZE 256 +#define COMMAND_LINE_SIZE 4096 #ifdef __KERNEL__ extern void setup_early_printk(void); diff --git a/arch/mips/include/asm/smtc_ipi.h b/arch/mips/include/asm/smtc_ipi.h index 8ce517574340..15278dbd7e79 100644 --- a/arch/mips/include/asm/smtc_ipi.h +++ b/arch/mips/include/asm/smtc_ipi.h @@ -45,6 +45,7 @@ struct smtc_ipi_q { spinlock_t lock; struct smtc_ipi *tail; int depth; + int resched_flag; /* reschedule already queued */ }; static inline void smtc_ipi_nq(struct smtc_ipi_q *q, struct smtc_ipi *p) diff --git a/arch/mips/include/asm/spram.h b/arch/mips/include/asm/spram.h new file mode 100644 index 000000000000..0b89006e4907 --- /dev/null +++ b/arch/mips/include/asm/spram.h @@ -0,0 +1,10 @@ +#ifndef _MIPS_SPRAM_H +#define _MIPS_SPRAM_H + +#ifdef CONFIG_CPU_MIPSR2 +extern __init void spram_config(void); +#else +static inline void spram_config(void) { }; +#endif /* CONFIG_CPU_MIPSR2 */ + +#endif /* _MIPS_SPRAM_H */ diff --git a/arch/mips/include/asm/thread_info.h b/arch/mips/include/asm/thread_info.h index 01cc1630b66c..845da2107ed1 100644 --- a/arch/mips/include/asm/thread_info.h +++ b/arch/mips/include/asm/thread_info.h @@ -86,14 +86,7 @@ register struct thread_info *__current_thread_info __asm__("$28"); #define __HAVE_ARCH_THREAD_INFO_ALLOCATOR #ifdef CONFIG_DEBUG_STACK_USAGE -#define alloc_thread_info(tsk) \ -({ \ - struct thread_info *ret; \ - \ - ret = kzalloc(THREAD_SIZE, GFP_KERNEL); \ - \ - ret; \ -}) +#define alloc_thread_info(tsk) kzalloc(THREAD_SIZE, GFP_KERNEL) #else #define alloc_thread_info(tsk) kmalloc(THREAD_SIZE, GFP_KERNEL) #endif diff --git a/arch/mips/jazz/irq.c b/arch/mips/jazz/irq.c index 7fd170d007e7..7bd32d04c2cc 100644 --- a/arch/mips/jazz/irq.c +++ b/arch/mips/jazz/irq.c @@ -134,7 +134,7 @@ static irqreturn_t r4030_timer_interrupt(int irq, void *dev_id) static struct irqaction r4030_timer_irqaction = { .handler = r4030_timer_interrupt, - .flags = IRQF_DISABLED, + .flags = IRQF_DISABLED | IRQF_TIMER, .name = "R4030 timer", }; diff --git a/arch/mips/kernel/cevt-bcm1480.c b/arch/mips/kernel/cevt-bcm1480.c index e02f79b1eb51..bfea327c636c 100644 --- a/arch/mips/kernel/cevt-bcm1480.c +++ b/arch/mips/kernel/cevt-bcm1480.c @@ -144,7 +144,7 @@ void __cpuinit sb1480_clockevent_init(void) bcm1480_unmask_irq(cpu, irq); action->handler = sibyte_counter_handler; - action->flags = IRQF_DISABLED | IRQF_PERCPU; + action->flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER; action->name = name; action->dev_id = cd; diff --git a/arch/mips/kernel/cevt-ds1287.c b/arch/mips/kernel/cevt-ds1287.c index 6996da4d74a2..00a4da277cbb 100644 --- a/arch/mips/kernel/cevt-ds1287.c +++ b/arch/mips/kernel/cevt-ds1287.c @@ -107,7 +107,7 @@ static irqreturn_t ds1287_interrupt(int irq, void *dev_id) static struct irqaction ds1287_irqaction = { .handler = ds1287_interrupt, - .flags = IRQF_DISABLED | IRQF_PERCPU, + .flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER, .name = "ds1287", }; diff --git a/arch/mips/kernel/cevt-gt641xx.c b/arch/mips/kernel/cevt-gt641xx.c index 92351e00ae0e..f5d265eb6eae 100644 --- a/arch/mips/kernel/cevt-gt641xx.c +++ b/arch/mips/kernel/cevt-gt641xx.c @@ -113,7 +113,7 @@ static irqreturn_t gt641xx_timer0_interrupt(int irq, void *dev_id) static struct irqaction gt641xx_timer0_irqaction = { .handler = gt641xx_timer0_interrupt, - .flags = IRQF_DISABLED | IRQF_PERCPU, + .flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER, .name = "gt641xx_timer0", }; diff --git a/arch/mips/kernel/cevt-r4k.c b/arch/mips/kernel/cevt-r4k.c index 2652362ce047..b469ad05d520 100644 --- a/arch/mips/kernel/cevt-r4k.c +++ b/arch/mips/kernel/cevt-r4k.c @@ -83,7 +83,7 @@ out: struct irqaction c0_compare_irqaction = { .handler = c0_compare_interrupt, - .flags = IRQF_DISABLED | IRQF_PERCPU, + .flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER, .name = "timer", }; diff --git a/arch/mips/kernel/cevt-sb1250.c b/arch/mips/kernel/cevt-sb1250.c index ac5903d1b20e..da78eeaea6e8 100644 --- a/arch/mips/kernel/cevt-sb1250.c +++ b/arch/mips/kernel/cevt-sb1250.c @@ -143,7 +143,7 @@ void __cpuinit sb1250_clockevent_init(void) sb1250_unmask_irq(cpu, irq); action->handler = sibyte_counter_handler; - action->flags = IRQF_DISABLED | IRQF_PERCPU; + action->flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER; action->name = name; action->dev_id = cd; diff --git a/arch/mips/kernel/cevt-smtc.c b/arch/mips/kernel/cevt-smtc.c index 98bd7de75778..b102e4f1630e 100644 --- a/arch/mips/kernel/cevt-smtc.c +++ b/arch/mips/kernel/cevt-smtc.c @@ -173,11 +173,12 @@ void smtc_distribute_timer(int vpe) unsigned int mtflags; int cpu; struct clock_event_device *cd; - unsigned long nextstamp = 0L; + unsigned long nextstamp; unsigned long reference; repeat: + nextstamp = 0L; for_each_online_cpu(cpu) { /* * Find virtual CPUs within the current VPE who have diff --git a/arch/mips/kernel/cevt-txx9.c b/arch/mips/kernel/cevt-txx9.c index 0037f21baf0d..218ee6bda935 100644 --- a/arch/mips/kernel/cevt-txx9.c +++ b/arch/mips/kernel/cevt-txx9.c @@ -146,7 +146,7 @@ static irqreturn_t txx9tmr_interrupt(int irq, void *dev_id) static struct irqaction txx9tmr_irq = { .handler = txx9tmr_interrupt, - .flags = IRQF_DISABLED | IRQF_PERCPU, + .flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER, .name = "txx9tmr", .dev_id = &txx9_clock_event_device, }; diff --git a/arch/mips/kernel/cpu-probe.c b/arch/mips/kernel/cpu-probe.c index f709657e4dcd..7a51866068a4 100644 --- a/arch/mips/kernel/cpu-probe.c +++ b/arch/mips/kernel/cpu-probe.c @@ -23,7 +23,7 @@ #include <asm/mipsregs.h> #include <asm/system.h> #include <asm/watch.h> - +#include <asm/spram.h> /* * Not all of the MIPS CPUs have the "wait" instruction available. Moreover, * the implementation of the "wait" feature differs between CPU families. This @@ -711,12 +711,6 @@ static void __cpuinit decode_configs(struct cpuinfo_mips *c) mips_probe_watch_registers(c); } -#ifdef CONFIG_CPU_MIPSR2 -extern void spram_config(void); -#else -static inline void spram_config(void) {} -#endif - static inline void cpu_probe_mips(struct cpuinfo_mips *c, unsigned int cpu) { decode_configs(c); diff --git a/arch/mips/kernel/head.S b/arch/mips/kernel/head.S index 531ce7b16124..ea695d9605e9 100644 --- a/arch/mips/kernel/head.S +++ b/arch/mips/kernel/head.S @@ -191,6 +191,7 @@ NESTED(kernel_entry, 16, sp) # kernel entry point /* Set the SP after an empty pt_regs. */ PTR_LI sp, _THREAD_SIZE - 32 - PT_SIZE PTR_ADDU sp, $28 + back_to_back_c0_hazard set_saved_sp sp, t0, t1 PTR_SUBU sp, 4 * SZREG # init stack pointer diff --git a/arch/mips/kernel/i8253.c b/arch/mips/kernel/i8253.c index f7d8d5d0ddbf..ed5c441615e4 100644 --- a/arch/mips/kernel/i8253.c +++ b/arch/mips/kernel/i8253.c @@ -98,7 +98,7 @@ static irqreturn_t timer_interrupt(int irq, void *dev_id) static struct irqaction irq0 = { .handler = timer_interrupt, - .flags = IRQF_DISABLED | IRQF_NOBALANCING, + .flags = IRQF_DISABLED | IRQF_NOBALANCING | IRQF_TIMER, .name = "timer" }; diff --git a/arch/mips/kernel/irq-gic.c b/arch/mips/kernel/irq-gic.c index d2072cd38592..b181f2f0ea8e 100644 --- a/arch/mips/kernel/irq-gic.c +++ b/arch/mips/kernel/irq-gic.c @@ -14,38 +14,23 @@ static unsigned long _gic_base; -static unsigned int _irqbase, _mapsize, numvpes, numintrs; -static struct gic_intr_map *_intrmap; +static unsigned int _irqbase; +static unsigned int gic_irq_flags[GIC_NUM_INTRS]; +#define GIC_IRQ_FLAG_EDGE 0x0001 -static struct gic_pcpu_mask pcpu_masks[NR_CPUS]; +struct gic_pcpu_mask pcpu_masks[NR_CPUS]; static struct gic_pending_regs pending_regs[NR_CPUS]; static struct gic_intrmask_regs intrmask_regs[NR_CPUS]; -#define gic_wedgeb2bok 0 /* - * Can GIC handle b2b writes to wedge register? - */ -#if gic_wedgeb2bok == 0 -static DEFINE_SPINLOCK(gic_wedgeb2b_lock); -#endif - void gic_send_ipi(unsigned int intr) { -#if gic_wedgeb2bok == 0 - unsigned long flags; -#endif pr_debug("CPU%d: %s status %08x\n", smp_processor_id(), __func__, read_c0_status()); - if (!gic_wedgeb2bok) - spin_lock_irqsave(&gic_wedgeb2b_lock, flags); GICWRITE(GIC_REG(SHARED, GIC_SH_WEDGE), 0x80000000 | intr); - if (!gic_wedgeb2bok) { - (void) GIC_REG(SHARED, GIC_SH_CONFIG); - spin_unlock_irqrestore(&gic_wedgeb2b_lock, flags); - } } /* This is Malta specific and needs to be exported */ -static void vpe_local_setup(unsigned int numvpes) +static void __init vpe_local_setup(unsigned int numvpes) { int i; unsigned long timer_interrupt = 5, perf_interrupt = 5; @@ -105,44 +90,34 @@ unsigned int gic_get_int(void) static unsigned int gic_irq_startup(unsigned int irq) { - pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); irq -= _irqbase; - GIC_SET_INTR_MASK(irq, 1); + pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); + GIC_SET_INTR_MASK(irq); return 0; } static void gic_irq_ack(unsigned int irq) { -#if gic_wedgeb2bok == 0 - unsigned long flags; -#endif - pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); irq -= _irqbase; - GIC_CLR_INTR_MASK(irq, 1); + pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); + GIC_CLR_INTR_MASK(irq); - if (_intrmap[irq].trigtype == GIC_TRIG_EDGE) { - if (!gic_wedgeb2bok) - spin_lock_irqsave(&gic_wedgeb2b_lock, flags); + if (gic_irq_flags[irq] & GIC_IRQ_FLAG_EDGE) GICWRITE(GIC_REG(SHARED, GIC_SH_WEDGE), irq); - if (!gic_wedgeb2bok) { - (void) GIC_REG(SHARED, GIC_SH_CONFIG); - spin_unlock_irqrestore(&gic_wedgeb2b_lock, flags); - } - } } static void gic_mask_irq(unsigned int irq) { - pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); irq -= _irqbase; - GIC_CLR_INTR_MASK(irq, 1); + pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); + GIC_CLR_INTR_MASK(irq); } static void gic_unmask_irq(unsigned int irq) { - pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); irq -= _irqbase; - GIC_SET_INTR_MASK(irq, 1); + pr_debug("CPU%d: %s: irq%d\n", smp_processor_id(), __func__, irq); + GIC_SET_INTR_MASK(irq); } #ifdef CONFIG_SMP @@ -155,9 +130,8 @@ static int gic_set_affinity(unsigned int irq, const struct cpumask *cpumask) unsigned long flags; int i; - pr_debug(KERN_DEBUG "%s called\n", __func__); irq -= _irqbase; - + pr_debug(KERN_DEBUG "%s(%d) called\n", __func__, irq); cpumask_and(&tmp, cpumask, cpu_online_mask); if (cpus_empty(tmp)) return -1; @@ -168,13 +142,6 @@ static int gic_set_affinity(unsigned int irq, const struct cpumask *cpumask) /* Re-route this IRQ */ GIC_SH_MAP_TO_VPE_SMASK(irq, first_cpu(tmp)); - /* - * FIXME: assumption that _intrmap is ordered and has no holes - */ - - /* Update the intr_map */ - _intrmap[irq].cpunum = first_cpu(tmp); - /* Update the pcpu_masks */ for (i = 0; i < NR_CPUS; i++) clear_bit(irq, pcpu_masks[i].pcpu_mask); @@ -201,8 +168,9 @@ static struct irq_chip gic_irq_controller = { #endif }; -static void __init setup_intr(unsigned int intr, unsigned int cpu, - unsigned int pin, unsigned int polarity, unsigned int trigtype) +static void __init gic_setup_intr(unsigned int intr, unsigned int cpu, + unsigned int pin, unsigned int polarity, unsigned int trigtype, + unsigned int flags) { /* Setup Intr to Pin mapping */ if (pin & GIC_MAP_TO_NMI_MSK) { @@ -227,38 +195,43 @@ static void __init setup_intr(unsigned int intr, unsigned int cpu, GIC_SET_TRIGGER(intr, trigtype); /* Init Intr Masks */ - GIC_SET_INTR_MASK(intr, 0); + GIC_CLR_INTR_MASK(intr); + /* Initialise per-cpu Interrupt software masks */ + if (flags & GIC_FLAG_IPI) + set_bit(intr, pcpu_masks[cpu].pcpu_mask); + if (flags & GIC_FLAG_TRANSPARENT) + GIC_SET_INTR_MASK(intr); + if (trigtype == GIC_TRIG_EDGE) + gic_irq_flags[intr] |= GIC_IRQ_FLAG_EDGE; } -static void __init gic_basic_init(void) +static void __init gic_basic_init(int numintrs, int numvpes, + struct gic_intr_map *intrmap, int mapsize) { unsigned int i, cpu; /* Setup defaults */ - for (i = 0; i < GIC_NUM_INTRS; i++) { + for (i = 0; i < numintrs; i++) { GIC_SET_POLARITY(i, GIC_POL_POS); GIC_SET_TRIGGER(i, GIC_TRIG_LEVEL); - GIC_SET_INTR_MASK(i, 0); + GIC_CLR_INTR_MASK(i); + if (i < GIC_NUM_INTRS) + gic_irq_flags[i] = 0; } /* Setup specifics */ - for (i = 0; i < _mapsize; i++) { - cpu = _intrmap[i].cpunum; + for (i = 0; i < mapsize; i++) { + cpu = intrmap[i].cpunum; if (cpu == X) continue; - - if (cpu == 0 && i != 0 && _intrmap[i].intrnum == 0 && - _intrmap[i].ipiflag == 0) + if (cpu == 0 && i != 0 && intrmap[i].flags == 0) continue; - - setup_intr(_intrmap[i].intrnum, - _intrmap[i].cpunum, - _intrmap[i].pin, - _intrmap[i].polarity, - _intrmap[i].trigtype); - /* Initialise per-cpu Interrupt software masks */ - if (_intrmap[i].ipiflag) - set_bit(_intrmap[i].intrnum, pcpu_masks[cpu].pcpu_mask); + gic_setup_intr(i, + intrmap[i].cpunum, + intrmap[i].pin, + intrmap[i].polarity, + intrmap[i].trigtype, + intrmap[i].flags); } vpe_local_setup(numvpes); @@ -273,12 +246,11 @@ void __init gic_init(unsigned long gic_base_addr, unsigned int irqbase) { unsigned int gicconfig; + int numvpes, numintrs; _gic_base = (unsigned long) ioremap_nocache(gic_base_addr, gic_addrspace_size); _irqbase = irqbase; - _intrmap = intr_map; - _mapsize = intr_map_size; GICREAD(GIC_REG(SHARED, GIC_SH_CONFIG), gicconfig); numintrs = (gicconfig & GIC_SH_CONFIG_NUMINTRS_MSK) >> @@ -290,5 +262,5 @@ void __init gic_init(unsigned long gic_base_addr, pr_debug("%s called\n", __func__); - gic_basic_init(); + gic_basic_init(numintrs, numvpes, intr_map, intr_map_size); } diff --git a/arch/mips/kernel/linux32.c b/arch/mips/kernel/linux32.c index 6242bc68add7..b77fefaff9da 100644 --- a/arch/mips/kernel/linux32.c +++ b/arch/mips/kernel/linux32.c @@ -428,3 +428,9 @@ _sys32_clone(nabi_no_regargs struct pt_regs regs) return do_fork(clone_flags, newsp, ®s, 0, parent_tidptr, child_tidptr); } + +asmlinkage long sys32_lookup_dcookie(u32 a0, u32 a1, char __user *buf, + size_t len) +{ + return sys_lookup_dcookie(merge_64(a0, a1), buf, len); +} diff --git a/arch/mips/kernel/scall64-o32.S b/arch/mips/kernel/scall64-o32.S index d0eff53d7cb9..23b842be83ea 100644 --- a/arch/mips/kernel/scall64-o32.S +++ b/arch/mips/kernel/scall64-o32.S @@ -450,7 +450,7 @@ sys_call_table: PTR sys_io_submit PTR sys_io_cancel /* 4245 */ PTR sys_exit_group - PTR sys_lookup_dcookie + PTR sys32_lookup_dcookie PTR sys_epoll_create PTR sys_epoll_ctl PTR sys_epoll_wait /* 4250 */ @@ -505,7 +505,7 @@ sys_call_table: PTR sys_fchmodat PTR sys_faccessat /* 4300 */ PTR compat_sys_pselect6 - PTR sys_ppoll + PTR compat_sys_ppoll PTR sys_unshare PTR sys_splice PTR sys32_sync_file_range /* 4305 */ diff --git a/arch/mips/kernel/smtc.c b/arch/mips/kernel/smtc.c index 4d181df44a40..24630fd8ef60 100644 --- a/arch/mips/kernel/smtc.c +++ b/arch/mips/kernel/smtc.c @@ -75,7 +75,6 @@ unsigned long irq_hwmask[NR_IRQS]; asiduse smtc_live_asid[MAX_SMTC_TLBS][MAX_SMTC_ASIDS]; - /* * Number of InterProcessor Interrupt (IPI) message buffers to allocate */ @@ -388,6 +387,7 @@ void smtc_prepare_cpus(int cpus) IPIQ[i].head = IPIQ[i].tail = NULL; spin_lock_init(&IPIQ[i].lock); IPIQ[i].depth = 0; + IPIQ[i].resched_flag = 0; /* No reschedules queued initially */ } /* cpu_data index starts at zero */ @@ -741,11 +741,24 @@ void smtc_forward_irq(unsigned int irq) static void smtc_ipi_qdump(void) { int i; + struct smtc_ipi *temp; for (i = 0; i < NR_CPUS ;i++) { - printk("IPIQ[%d]: head = 0x%x, tail = 0x%x, depth = %d\n", + pr_info("IPIQ[%d]: head = 0x%x, tail = 0x%x, depth = %d\n", i, (unsigned)IPIQ[i].head, (unsigned)IPIQ[i].tail, IPIQ[i].depth); + temp = IPIQ[i].head; + + while (temp != IPIQ[i].tail) { + pr_debug("%d %d %d: ", temp->type, temp->dest, + (int)temp->arg); +#ifdef SMTC_IPI_DEBUG + pr_debug("%u %lu\n", temp->sender, temp->stamp); +#else + pr_debug("\n"); +#endif + temp = temp->flink; + } } } @@ -784,11 +797,16 @@ void smtc_send_ipi(int cpu, int type, unsigned int action) int mtflags; unsigned long tcrestart; extern void r4k_wait_irqoff(void), __pastwait(void); + int set_resched_flag = (type == LINUX_SMP_IPI && + action == SMP_RESCHEDULE_YOURSELF); if (cpu == smp_processor_id()) { printk("Cannot Send IPI to self!\n"); return; } + if (set_resched_flag && IPIQ[cpu].resched_flag != 0) + return; /* There is a reschedule queued already */ + /* Set up a descriptor, to be delivered either promptly or queued */ pipi = smtc_ipi_dq(&freeIPIq); if (pipi == NULL) { @@ -801,6 +819,7 @@ void smtc_send_ipi(int cpu, int type, unsigned int action) pipi->dest = cpu; if (cpu_data[cpu].vpe_id != cpu_data[smp_processor_id()].vpe_id) { /* If not on same VPE, enqueue and send cross-VPE interrupt */ + IPIQ[cpu].resched_flag |= set_resched_flag; smtc_ipi_nq(&IPIQ[cpu], pipi); LOCK_CORE_PRA(); settc(cpu_data[cpu].tc_id); @@ -847,6 +866,7 @@ void smtc_send_ipi(int cpu, int type, unsigned int action) */ write_tc_c0_tchalt(0); UNLOCK_CORE_PRA(); + IPIQ[cpu].resched_flag |= set_resched_flag; smtc_ipi_nq(&IPIQ[cpu], pipi); } else { postdirect: @@ -996,12 +1016,15 @@ void deferred_smtc_ipi(void) * already enabled. */ local_irq_save(flags); - spin_lock(&q->lock); pipi = __smtc_ipi_dq(q); spin_unlock(&q->lock); - if (pipi != NULL) + if (pipi != NULL) { + if (pipi->type == LINUX_SMP_IPI && + (int)pipi->arg == SMP_RESCHEDULE_YOURSELF) + IPIQ[cpu].resched_flag = 0; ipi_decode(pipi); + } /* * The use of the __raw_local restore isn't * as obviously necessary here as in smtc_ipi_replay(), @@ -1082,6 +1105,9 @@ static irqreturn_t ipi_interrupt(int irq, void *dev_idm) * with interrupts off */ local_irq_save(flags); + if (pipi->type == LINUX_SMP_IPI && + (int)pipi->arg == SMP_RESCHEDULE_YOURSELF) + IPIQ[cpu].resched_flag = 0; ipi_decode(pipi); local_irq_restore(flags); } diff --git a/arch/mips/kernel/spram.c b/arch/mips/kernel/spram.c index 6ddb507a87ef..1821d12a6410 100644 --- a/arch/mips/kernel/spram.c +++ b/arch/mips/kernel/spram.c @@ -13,7 +13,6 @@ #include <linux/ptrace.h> #include <linux/stddef.h> -#include <asm/cpu.h> #include <asm/fpu.h> #include <asm/mipsregs.h> #include <asm/system.h> @@ -198,8 +197,7 @@ static __cpuinit void probe_spram(char *type, offset += 2 * SPRAM_TAG_STRIDE; } } - -__cpuinit void spram_config(void) +void __cpuinit spram_config(void) { struct cpuinfo_mips *c = ¤t_cpu_data; unsigned int config0; @@ -208,6 +206,7 @@ __cpuinit void spram_config(void) case CPU_24K: case CPU_34K: case CPU_74K: + case CPU_1004K: config0 = read_c0_config(); /* FIXME: addresses are Malta specific */ if (config0 & (1<<24)) { diff --git a/arch/mips/kernel/vpe.c b/arch/mips/kernel/vpe.c index 03092ab2a296..60477529362e 100644 --- a/arch/mips/kernel/vpe.c +++ b/arch/mips/kernel/vpe.c @@ -1116,8 +1116,6 @@ static int vpe_open(struct inode *inode, struct file *filp) v->shared_ptr = NULL; v->__start = 0; - unlock_kernel(); - return 0; } diff --git a/arch/mips/loongson/common/irq.c b/arch/mips/loongson/common/irq.c index f368c735cbd3..b32b4a3e5137 100644 --- a/arch/mips/loongson/common/irq.c +++ b/arch/mips/loongson/common/irq.c @@ -55,7 +55,6 @@ void __init arch_init_irq(void) * int-handler is not on bootstrap */ clear_c0_status(ST0_IM | ST0_BEV); - local_irq_disable(); /* setting irq trigger mode */ set_irq_trigger_mode(); diff --git a/arch/mips/math-emu/cp1emu.c b/arch/mips/math-emu/cp1emu.c index 890f77927d62..454b53924490 100644 --- a/arch/mips/math-emu/cp1emu.c +++ b/arch/mips/math-emu/cp1emu.c @@ -163,33 +163,34 @@ static int isBranchInstr(mips_instruction * i) /* * In the Linux kernel, we support selection of FPR format on the - * basis of the Status.FR bit. This does imply that, if a full 32 - * FPRs are desired, there needs to be a flip-flop that can be written - * to one at that bit position. In any case, O32 MIPS ABI uses - * only the even FPRs (Status.FR = 0). + * basis of the Status.FR bit. If an FPU is not present, the FR bit + * is hardwired to zero, which would imply a 32-bit FPU even for + * 64-bit CPUs. For 64-bit kernels with no FPU we use TIF_32BIT_REGS + * as a proxy for the FR bit so that a 64-bit FPU is emulated. In any + * case, for a 32-bit kernel which uses the O32 MIPS ABI, only the + * even FPRs are used (Status.FR = 0). */ - -#define CP0_STATUS_FR_SUPPORT - -#ifdef CP0_STATUS_FR_SUPPORT -#define FR_BIT ST0_FR +static inline int cop1_64bit(struct pt_regs *xcp) +{ + if (cpu_has_fpu) + return xcp->cp0_status & ST0_FR; +#ifdef CONFIG_64BIT + return !test_thread_flag(TIF_32BIT_REGS); #else -#define FR_BIT 0 + return 0; #endif +} + +#define SIFROMREG(si, x) ((si) = cop1_64bit(xcp) || !(x & 1) ? \ + (int)ctx->fpr[x] : (int)(ctx->fpr[x & ~1] >> 32)) -#define SIFROMREG(si, x) ((si) = \ - (xcp->cp0_status & FR_BIT) || !(x & 1) ? \ - (int)ctx->fpr[x] : \ - (int)(ctx->fpr[x & ~1] >> 32 )) -#define SITOREG(si, x) (ctx->fpr[x & ~((xcp->cp0_status & FR_BIT) == 0)] = \ - (xcp->cp0_status & FR_BIT) || !(x & 1) ? \ +#define SITOREG(si, x) (ctx->fpr[x & ~(cop1_64bit(xcp) == 0)] = \ + cop1_64bit(xcp) || !(x & 1) ? \ ctx->fpr[x & ~1] >> 32 << 32 | (u32)(si) : \ ctx->fpr[x & ~1] << 32 >> 32 | (u64)(si) << 32) -#define DIFROMREG(di, x) ((di) = \ - ctx->fpr[x & ~((xcp->cp0_status & FR_BIT) == 0)]) -#define DITOREG(di, x) (ctx->fpr[x & ~((xcp->cp0_status & FR_BIT) == 0)] \ - = (di)) +#define DIFROMREG(di, x) ((di) = ctx->fpr[x & ~(cop1_64bit(xcp) == 0)]) +#define DITOREG(di, x) (ctx->fpr[x & ~(cop1_64bit(xcp) == 0)] = (di)) #define SPFROMREG(sp, x) SIFROMREG((sp).bits, x) #define SPTOREG(sp, x) SITOREG((sp).bits, x) diff --git a/arch/mips/math-emu/dp_simple.c b/arch/mips/math-emu/dp_simple.c index 1c555e6c6a9f..d9ae1dbabda7 100644 --- a/arch/mips/math-emu/dp_simple.c +++ b/arch/mips/math-emu/dp_simple.c @@ -62,8 +62,6 @@ ieee754dp ieee754dp_neg(ieee754dp x) return ieee754dp_nanxcpt(y, "neg"); } - if (ieee754dp_isnan(x)) /* but not infinity */ - return ieee754dp_nanxcpt(x, "neg", x); return x; } @@ -76,15 +74,12 @@ ieee754dp ieee754dp_abs(ieee754dp x) CLEARCX; FLUSHXDP; + /* Clear sign ALWAYS, irrespective of NaN */ + DPSIGN(x) = 0; + if (xc == IEEE754_CLASS_SNAN) { - SETCX(IEEE754_INVALID_OPERATION); - return ieee754dp_nanxcpt(ieee754dp_indef(), "neg"); + return ieee754dp_nanxcpt(ieee754dp_indef(), "abs"); } - if (ieee754dp_isnan(x)) /* but not infinity */ - return ieee754dp_nanxcpt(x, "abs", x); - - /* quick fix up */ - DPSIGN(x) = 0; return x; } diff --git a/arch/mips/math-emu/sp_simple.c b/arch/mips/math-emu/sp_simple.c index 770f0f4677cd..3175477d36f6 100644 --- a/arch/mips/math-emu/sp_simple.c +++ b/arch/mips/math-emu/sp_simple.c @@ -62,8 +62,6 @@ ieee754sp ieee754sp_neg(ieee754sp x) return ieee754sp_nanxcpt(y, "neg"); } - if (ieee754sp_isnan(x)) /* but not infinity */ - return ieee754sp_nanxcpt(x, "neg", x); return x; } @@ -76,15 +74,12 @@ ieee754sp ieee754sp_abs(ieee754sp x) CLEARCX; FLUSHXSP; + /* Clear sign ALWAYS, irrespective of NaN */ + SPSIGN(x) = 0; + if (xc == IEEE754_CLASS_SNAN) { - SETCX(IEEE754_INVALID_OPERATION); return ieee754sp_nanxcpt(ieee754sp_indef(), "abs"); } - if (ieee754sp_isnan(x)) /* but not infinity */ - return ieee754sp_nanxcpt(x, "abs", x); - - /* quick fix up */ - SPSIGN(x) = 0; return x; } diff --git a/arch/mips/mm/dma-default.c b/arch/mips/mm/dma-default.c index 7e48e76148aa..9367e33fbd18 100644 --- a/arch/mips/mm/dma-default.c +++ b/arch/mips/mm/dma-default.c @@ -90,6 +90,9 @@ void *dma_alloc_coherent(struct device *dev, size_t size, { void *ret; + if (dma_alloc_from_coherent(dev, size, dma_handle, &ret)) + return ret; + gfp = massage_gfp_flags(dev, gfp); ret = (void *) __get_free_pages(gfp, get_order(size)); @@ -122,6 +125,10 @@ void dma_free_coherent(struct device *dev, size_t size, void *vaddr, dma_addr_t dma_handle) { unsigned long addr = (unsigned long) vaddr; + int order = get_order(size); + + if (dma_release_from_coherent(dev, order, vaddr)) + return; plat_unmap_dma_mem(dev, dma_handle, size, DMA_BIDIRECTIONAL); diff --git a/arch/mips/mm/init.c b/arch/mips/mm/init.c index 15aa1902a788..8d1f4f363049 100644 --- a/arch/mips/mm/init.c +++ b/arch/mips/mm/init.c @@ -27,6 +27,7 @@ #include <linux/swap.h> #include <linux/proc_fs.h> #include <linux/pfn.h> +#include <linux/hardirq.h> #include <asm/asm-offsets.h> #include <asm/bootinfo.h> @@ -132,7 +133,10 @@ void *kmap_coherent(struct page *page, unsigned long addr) inc_preempt_count(); idx = (addr >> PAGE_SHIFT) & (FIX_N_COLOURS - 1); #ifdef CONFIG_MIPS_MT_SMTC - idx += FIX_N_COLOURS * smp_processor_id(); + idx += FIX_N_COLOURS * smp_processor_id() + + (in_interrupt() ? (FIX_N_COLOURS * NR_CPUS) : 0); +#else + idx += in_interrupt() ? FIX_N_COLOURS : 0; #endif vaddr = __fix_to_virt(FIX_CMAP_END - idx); pte = mk_pte(page, PAGE_KERNEL); diff --git a/arch/mips/mti-malta/malta-amon.c b/arch/mips/mti-malta/malta-amon.c index df9e526312a2..469d9b0cee6d 100644 --- a/arch/mips/mti-malta/malta-amon.c +++ b/arch/mips/mti-malta/malta-amon.c @@ -70,11 +70,12 @@ void amon_cpu_start(int cpu, launch->sp = sp; launch->a0 = a0; - /* Make sure target sees parameters before the go bit */ - smp_mb(); - + smp_wmb(); /* Target must see parameters before go */ launch->flags |= LAUNCH_FGO; + smp_wmb(); /* Target must see go before we poll */ + while ((launch->flags & LAUNCH_FGONE) == 0) ; + smp_rmb(); /* Target will be updating flags soon */ pr_debug("launch: cpu%d gone!\n", cpu); } diff --git a/arch/mips/mti-malta/malta-int.c b/arch/mips/mti-malta/malta-int.c index 3e0a9b35ba5c..4c3fca18a171 100644 --- a/arch/mips/mti-malta/malta-int.c +++ b/arch/mips/mti-malta/malta-int.c @@ -87,7 +87,7 @@ static inline int mips_pcibios_iack(void) dummy = BONITO_PCIMAP_CFG; iob(); /* sync */ - irq = readl((u32 *)_pcictrl_bonito_pcicfg); + irq = __raw_readl((u32 *)_pcictrl_bonito_pcicfg); iob(); /* sync */ irq &= 0xff; BONITO_PCIMAP_CFG = 0; @@ -379,38 +379,43 @@ static msc_irqmap_t __initdata msc_eicirqmap[] = { static int __initdata msc_nr_eicirqs = ARRAY_SIZE(msc_eicirqmap); -#if defined(CONFIG_MIPS_MT_SMP) /* * This GIC specific tabular array defines the association between External * Interrupts and CPUs/Core Interrupts. The nature of the External * Interrupts is also defined here - polarity/trigger. */ + +#define GIC_CPU_NMI GIC_MAP_TO_NMI_MSK static struct gic_intr_map gic_intr_map[GIC_NUM_INTRS] = { - { GIC_EXT_INTR(0), X, X, X, X, 0 }, - { GIC_EXT_INTR(1), X, X, X, X, 0 }, - { GIC_EXT_INTR(2), X, X, X, X, 0 }, - { GIC_EXT_INTR(3), 0, GIC_CPU_INT0, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(4), 0, GIC_CPU_INT1, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(5), 0, GIC_CPU_INT2, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(6), 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(7), 0, GIC_CPU_INT4, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(8), 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(9), 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(10), X, X, X, X, 0 }, - { GIC_EXT_INTR(11), X, X, X, X, 0 }, - { GIC_EXT_INTR(12), 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(13), 0, GIC_MAP_TO_NMI_MSK, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(14), 0, GIC_MAP_TO_NMI_MSK, GIC_POL_POS, GIC_TRIG_LEVEL, 0 }, - { GIC_EXT_INTR(15), X, X, X, X, 0 }, -/* This is the end of the general interrupts now we do IPI ones */ + { X, X, X, X, 0 }, + { X, X, X, X, 0 }, + { X, X, X, X, 0 }, + { 0, GIC_CPU_INT0, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_INT1, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_INT2, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_INT4, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { X, X, X, X, 0 }, + { X, X, X, X, 0 }, + { 0, GIC_CPU_INT3, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_NMI, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { 0, GIC_CPU_NMI, GIC_POL_POS, GIC_TRIG_LEVEL, GIC_FLAG_TRANSPARENT }, + { X, X, X, X, 0 }, + /* The remainder of this table is initialised by fill_ipi_map */ }; -#endif /* * GCMP needs to be detected before any SMP initialisation */ int __init gcmp_probe(unsigned long addr, unsigned long size) { + if (mips_revision_sconid != MIPS_REVISION_SCON_ROCIT) { + gcmp_present = 0; + return gcmp_present; + } + if (gcmp_present >= 0) return gcmp_present; @@ -419,20 +424,35 @@ int __init gcmp_probe(unsigned long addr, unsigned long size) gcmp_present = (GCMPGCB(GCMPB) & GCMP_GCB_GCMPB_GCMPBASE_MSK) == GCMP_BASE_ADDR; if (gcmp_present) - printk(KERN_DEBUG "GCMP present\n"); + pr_debug("GCMP present\n"); return gcmp_present; } +/* Return the number of IOCU's present */ +int __init gcmp_niocu(void) +{ + return gcmp_present ? + (GCMPGCB(GC) & GCMP_GCB_GC_NUMIOCU_MSK) >> GCMP_GCB_GC_NUMIOCU_SHF : + 0; +} + +/* Set GCMP region attributes */ +void __init gcmp_setregion(int region, unsigned long base, + unsigned long mask, int type) +{ + GCMPGCBn(CMxBASE, region) = base; + GCMPGCBn(CMxMASK, region) = mask | type; +} + #if defined(CONFIG_MIPS_MT_SMP) static void __init fill_ipi_map1(int baseintr, int cpu, int cpupin) { int intr = baseintr + cpu; - gic_intr_map[intr].intrnum = GIC_EXT_INTR(intr); gic_intr_map[intr].cpunum = cpu; gic_intr_map[intr].pin = cpupin; gic_intr_map[intr].polarity = GIC_POL_POS; gic_intr_map[intr].trigtype = GIC_TRIG_EDGE; - gic_intr_map[intr].ipiflag = 1; + gic_intr_map[intr].flags = GIC_FLAG_IPI; ipi_map[cpu] |= (1 << (cpupin + 2)); } @@ -447,6 +467,12 @@ static void __init fill_ipi_map(void) } #endif +void __init arch_init_ipiirq(int irq, struct irqaction *action) +{ + setup_irq(irq, action); + set_irq_handler(irq, handle_percpu_irq); +} + void __init arch_init_irq(void) { init_i8259_irqs(); @@ -458,12 +484,17 @@ void __init arch_init_irq(void) GCMPGCB(GICBA) = GIC_BASE_ADDR | GCMP_GCB_GICBA_EN_MSK; gic_present = 1; } else { - _msc01_biu_base = (unsigned long) ioremap_nocache(MSC01_BIU_REG_BASE, MSC01_BIU_ADDRSPACE_SZ); - gic_present = (REG(_msc01_biu_base, MSC01_SC_CFG) & - MSC01_SC_CFG_GICPRES_MSK) >> MSC01_SC_CFG_GICPRES_SHF; + if (mips_revision_sconid == MIPS_REVISION_SCON_ROCIT) { + _msc01_biu_base = (unsigned long) + ioremap_nocache(MSC01_BIU_REG_BASE, + MSC01_BIU_ADDRSPACE_SZ); + gic_present = (REG(_msc01_biu_base, MSC01_SC_CFG) & + MSC01_SC_CFG_GICPRES_MSK) >> + MSC01_SC_CFG_GICPRES_SHF; + } } if (gic_present) - printk(KERN_DEBUG "GIC present\n"); + pr_debug("GIC present\n"); switch (mips_revision_sconid) { case MIPS_REVISION_SCON_SOCIT: @@ -526,16 +557,16 @@ void __init arch_init_irq(void) &corehi_irqaction); } -#if defined(CONFIG_MIPS_MT_SMP) if (gic_present) { /* FIXME */ int i; - +#if defined(CONFIG_MIPS_MT_SMP) gic_call_int_base = GIC_NUM_INTRS - NR_CPUS; gic_resched_int_base = gic_call_int_base - NR_CPUS; - fill_ipi_map(); - gic_init(GIC_BASE_ADDR, GIC_ADDRSPACE_SZ, gic_intr_map, ARRAY_SIZE(gic_intr_map), MIPS_GIC_IRQ_BASE); +#endif + gic_init(GIC_BASE_ADDR, GIC_ADDRSPACE_SZ, gic_intr_map, + ARRAY_SIZE(gic_intr_map), MIPS_GIC_IRQ_BASE); if (!gcmp_present) { /* Enable the GIC */ i = REG(_msc01_biu_base, MSC01_SC_CFG); @@ -543,7 +574,7 @@ void __init arch_init_irq(void) (i | (0x1 << MSC01_SC_CFG_GICENA_SHF)); pr_debug("GIC Enabled\n"); } - +#if defined(CONFIG_MIPS_MT_SMP) /* set up ipi interrupts */ if (cpu_has_vint) { set_vi_handler(MIPSCPU_INT_IPI0, malta_ipi_irqdispatch); @@ -556,16 +587,14 @@ void __init arch_init_irq(void) write_c0_status(0x1100dc00); printk("CPU%d: status register frc %08x\n", smp_processor_id(), read_c0_status()); for (i = 0; i < NR_CPUS; i++) { - setup_irq(MIPS_GIC_IRQ_BASE + - GIC_RESCHED_INT(i), &irq_resched); - setup_irq(MIPS_GIC_IRQ_BASE + - GIC_CALL_INT(i), &irq_call); - set_irq_handler(MIPS_GIC_IRQ_BASE + - GIC_RESCHED_INT(i), handle_percpu_irq); - set_irq_handler(MIPS_GIC_IRQ_BASE + - GIC_CALL_INT(i), handle_percpu_irq); + arch_init_ipiirq(MIPS_GIC_IRQ_BASE + + GIC_RESCHED_INT(i), &irq_resched); + arch_init_ipiirq(MIPS_GIC_IRQ_BASE + + GIC_CALL_INT(i), &irq_call); } +#endif } else { +#if defined(CONFIG_MIPS_MT_SMP) /* set up ipi interrupts */ if (cpu_has_veic) { set_vi_handler (MSC01E_INT_SW0, ipi_resched_dispatch); @@ -580,14 +609,10 @@ void __init arch_init_irq(void) cpu_ipi_resched_irq = MIPS_CPU_IRQ_BASE + MIPS_CPU_IPI_RESCHED_IRQ; cpu_ipi_call_irq = MIPS_CPU_IRQ_BASE + MIPS_CPU_IPI_CALL_IRQ; } - - setup_irq(cpu_ipi_resched_irq, &irq_resched); - setup_irq(cpu_ipi_call_irq, &irq_call); - - set_irq_handler(cpu_ipi_resched_irq, handle_percpu_irq); - set_irq_handler(cpu_ipi_call_irq, handle_percpu_irq); - } + arch_init_ipiirq(cpu_ipi_resched_irq, &irq_resched); + arch_init_ipiirq(cpu_ipi_call_irq, &irq_call); #endif + } } void malta_be_init(void) diff --git a/arch/mips/mti-malta/malta-memory.c b/arch/mips/mti-malta/malta-memory.c index 61888ff72c87..9035c64bc5ed 100644 --- a/arch/mips/mti-malta/malta-memory.c +++ b/arch/mips/mti-malta/malta-memory.c @@ -54,7 +54,8 @@ static struct prom_pmemblock * __init prom_getmdesc(void) { char *memsize_str; unsigned int memsize; - char cmdline[CL_SIZE], *ptr; + char *ptr; + static char cmdline[CL_SIZE] __initdata; /* otherwise look in the environment */ memsize_str = prom_getenv("memsize"); diff --git a/arch/mips/mti-malta/malta-pci.c b/arch/mips/mti-malta/malta-pci.c index b9743190609a..2fbfa1a8c3a9 100644 --- a/arch/mips/mti-malta/malta-pci.c +++ b/arch/mips/mti-malta/malta-pci.c @@ -27,7 +27,7 @@ #include <linux/init.h> #include <asm/gt64120.h> - +#include <asm/gcmpregs.h> #include <asm/mips-boards/generic.h> #include <asm/mips-boards/bonito64.h> #include <asm/mips-boards/msc01_pci.h> @@ -201,7 +201,11 @@ void __init mips_pcibios_init(void) msc_mem_resource.start = start & mask; msc_mem_resource.end = (start & mask) | ~mask; msc_controller.mem_offset = (start & mask) - (map & mask); - +#ifdef CONFIG_MIPS_CMP + if (gcmp_niocu()) + gcmp_setregion(0, start, mask, + GCMP_GCB_GCMPB_CMDEFTGT_IOCU1); +#endif MSC_READ(MSC01_PCI_SC2PIOBASL, start); MSC_READ(MSC01_PCI_SC2PIOMSKL, mask); MSC_READ(MSC01_PCI_SC2PIOMAPL, map); @@ -209,7 +213,11 @@ void __init mips_pcibios_init(void) msc_io_resource.end = (map & mask) | ~mask; msc_controller.io_offset = 0; ioport_resource.end = ~mask; - +#ifdef CONFIG_MIPS_CMP + if (gcmp_niocu()) + gcmp_setregion(1, start, mask, + GCMP_GCB_GCMPB_CMDEFTGT_IOCU1); +#endif /* If ranges overlap I/O takes precedence. */ start = start & mask; end = start | ~mask; @@ -241,3 +249,16 @@ void __init mips_pcibios_init(void) register_pci_controller(controller); } + +/* Enable PCI 2.1 compatibility in PIIX4 */ +static void __init quirk_dlcsetup(struct pci_dev *dev) +{ + u8 odlc, ndlc; + (void) pci_read_config_byte(dev, 0x82, &odlc); + /* Enable passive releases and delayed transaction */ + ndlc = odlc | 7; + (void) pci_write_config_byte(dev, 0x82, ndlc); +} + +DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82371AB_0, + quirk_dlcsetup); diff --git a/arch/mips/nxp/pnx8550/common/int.c b/arch/mips/nxp/pnx8550/common/int.c index f080f114a1bf..7aca7d5375e5 100644 --- a/arch/mips/nxp/pnx8550/common/int.c +++ b/arch/mips/nxp/pnx8550/common/int.c @@ -172,7 +172,7 @@ static struct irqaction gic_action = { static struct irqaction timer_action = { .handler = no_action, - .flags = IRQF_DISABLED, + .flags = IRQF_DISABLED | IRQF_TIMER, .name = "Timer", }; diff --git a/arch/mips/nxp/pnx8550/common/time.c b/arch/mips/nxp/pnx8550/common/time.c index 18b192784877..8836c6203df0 100644 --- a/arch/mips/nxp/pnx8550/common/time.c +++ b/arch/mips/nxp/pnx8550/common/time.c @@ -59,7 +59,7 @@ static irqreturn_t pnx8xxx_timer_interrupt(int irq, void *dev_id) static struct irqaction pnx8xxx_timer_irq = { .handler = pnx8xxx_timer_interrupt, - .flags = IRQF_DISABLED | IRQF_PERCPU, + .flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER, .name = "pnx8xxx_timer", }; @@ -72,7 +72,7 @@ static irqreturn_t monotonic_interrupt(int irq, void *dev_id) static struct irqaction monotonic_irqaction = { .handler = monotonic_interrupt, - .flags = IRQF_DISABLED, + .flags = IRQF_DISABLED | IRQF_TIMER, .name = "Monotonic timer", }; diff --git a/arch/mips/oprofile/op_model_loongson2.c b/arch/mips/oprofile/op_model_loongson2.c index deed1d5d4982..575cd1473475 100644 --- a/arch/mips/oprofile/op_model_loongson2.c +++ b/arch/mips/oprofile/op_model_loongson2.c @@ -22,7 +22,7 @@ * otherwise, the oprofile tool will not recognize this and complain about * "cpu_type 'unset' is not valid". */ -#define LOONGSON2_CPU_TYPE "mips/godson2" +#define LOONGSON2_CPU_TYPE "mips/loongson2" #define LOONGSON2_COUNTER1_EVENT(event) ((event & 0x0f) << 5) #define LOONGSON2_COUNTER2_EVENT(event) ((event & 0x0f) << 9) diff --git a/arch/mips/rb532/prom.c b/arch/mips/rb532/prom.c index 46ca24dbcc2d..ad5bd1097974 100644 --- a/arch/mips/rb532/prom.c +++ b/arch/mips/rb532/prom.c @@ -69,7 +69,7 @@ static inline unsigned long tag2ul(char *arg, const char *tag) void __init prom_setup_cmdline(void) { - char cmd_line[CL_SIZE]; + static char cmd_line[CL_SIZE] __initdata; char *cp, *board; int prom_argc; char **prom_argv, **prom_envp; diff --git a/arch/mips/sgi-ip27/ip27-timer.c b/arch/mips/sgi-ip27/ip27-timer.c index 6d0e59ffba2e..d6802d6d1f82 100644 --- a/arch/mips/sgi-ip27/ip27-timer.c +++ b/arch/mips/sgi-ip27/ip27-timer.c @@ -105,7 +105,7 @@ static irqreturn_t hub_rt_counter_handler(int irq, void *dev_id) struct irqaction hub_rt_irqaction = { .handler = hub_rt_counter_handler, - .flags = IRQF_DISABLED | IRQF_PERCPU, + .flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER, .name = "hub-rt", }; diff --git a/arch/mips/sni/time.c b/arch/mips/sni/time.c index 62df6a598e0a..f3b60e671207 100644 --- a/arch/mips/sni/time.c +++ b/arch/mips/sni/time.c @@ -67,7 +67,7 @@ static irqreturn_t a20r_interrupt(int irq, void *dev_id) static struct irqaction a20r_irqaction = { .handler = a20r_interrupt, - .flags = IRQF_DISABLED | IRQF_PERCPU, + .flags = IRQF_DISABLED | IRQF_PERCPU | IRQF_TIMER, .name = "a20r-timer", }; diff --git a/arch/mips/txx9/generic/setup.c b/arch/mips/txx9/generic/setup.c index c860810722c0..d66802edebb2 100644 --- a/arch/mips/txx9/generic/setup.c +++ b/arch/mips/txx9/generic/setup.c @@ -85,7 +85,7 @@ int txx9_ccfg_toeon __initdata = 1; struct clk *clk_get(struct device *dev, const char *id) { if (!strcmp(id, "spi-baseclk")) - return (struct clk *)((unsigned long)txx9_gbus_clock / 2 / 4); + return (struct clk *)((unsigned long)txx9_gbus_clock / 2 / 2); if (!strcmp(id, "imbus_clk")) return (struct clk *)((unsigned long)txx9_gbus_clock / 2); return ERR_PTR(-ENOENT); @@ -160,7 +160,7 @@ static void __init prom_init_cmdline(void) int argc; int *argv32; int i; /* Always ignore the "-c" at argv[0] */ - char builtin[CL_SIZE]; + static char builtin[CL_SIZE] __initdata; if (fw_arg0 >= CKSEG0 || fw_arg1 < CKSEG0) { /* @@ -315,7 +315,7 @@ static inline void txx9_cache_fixup(void) static void __init preprocess_cmdline(void) { - char cmdline[CL_SIZE]; + static char cmdline[CL_SIZE] __initdata; char *s; strcpy(cmdline, arcs_cmdline); @@ -817,7 +817,8 @@ void __init txx9_iocled_init(unsigned long baseaddr, out_pdev: platform_device_put(pdev); out_gpio: - gpio_remove(&iocled->chip); + if (gpiochip_remove(&iocled->chip)) + return; out_unmap: iounmap(iocled->mmioaddr); out_free: diff --git a/arch/parisc/Kconfig b/arch/parisc/Kconfig index f388dc68f605..524d9352f17e 100644 --- a/arch/parisc/Kconfig +++ b/arch/parisc/Kconfig @@ -18,6 +18,7 @@ config PARISC select BUG select HAVE_PERF_EVENTS select GENERIC_ATOMIC64 if !64BIT + select HAVE_ARCH_TRACEHOOK help The PA-RISC microprocessor is designed by Hewlett-Packard and used in many of their workstations & servers (HP9000 700 and 800 series, diff --git a/arch/parisc/include/asm/fcntl.h b/arch/parisc/include/asm/fcntl.h index 5f39d5597ced..1e1c824764ee 100644 --- a/arch/parisc/include/asm/fcntl.h +++ b/arch/parisc/include/asm/fcntl.h @@ -28,8 +28,6 @@ #define F_SETOWN 12 /* for sockets. */ #define F_SETSIG 13 /* for sockets. */ #define F_GETSIG 14 /* for sockets. */ -#define F_GETOWN_EX 15 -#define F_SETOWN_EX 16 /* for posix fcntl() and lockf() */ #define F_RDLCK 01 diff --git a/arch/parisc/include/asm/fixmap.h b/arch/parisc/include/asm/fixmap.h index de3fe3a18229..6fec4d4a1a18 100644 --- a/arch/parisc/include/asm/fixmap.h +++ b/arch/parisc/include/asm/fixmap.h @@ -21,9 +21,9 @@ #define KERNEL_MAP_END (TMPALIAS_MAP_START) #ifndef __ASSEMBLY__ -extern void *vmalloc_start; +extern void *parisc_vmalloc_start; #define PCXL_DMA_MAP_SIZE (8*1024*1024) -#define VMALLOC_START ((unsigned long)vmalloc_start) +#define VMALLOC_START ((unsigned long)parisc_vmalloc_start) #define VMALLOC_END (KERNEL_MAP_END) #endif /*__ASSEMBLY__*/ diff --git a/arch/parisc/include/asm/hardirq.h b/arch/parisc/include/asm/hardirq.h index ce93133d5112..0d68184a76cb 100644 --- a/arch/parisc/include/asm/hardirq.h +++ b/arch/parisc/include/asm/hardirq.h @@ -1,29 +1,11 @@ /* hardirq.h: PA-RISC hard IRQ support. * * Copyright (C) 2001 Matthew Wilcox <matthew@wil.cx> - * - * The locking is really quite interesting. There's a cpu-local - * count of how many interrupts are being handled, and a global - * lock. An interrupt can only be serviced if the global lock - * is free. You can't be sure no more interrupts are being - * serviced until you've acquired the lock and then checked - * all the per-cpu interrupt counts are all zero. It's a specialised - * br_lock, and that's exactly how Sparc does it. We don't because - * it's more locking for us. This way is lock-free in the interrupt path. */ #ifndef _PARISC_HARDIRQ_H #define _PARISC_HARDIRQ_H -#include <linux/threads.h> -#include <linux/irq.h> - -typedef struct { - unsigned long __softirq_pending; /* set_bit is used on this */ -} ____cacheline_aligned irq_cpustat_t; - -#include <linux/irq_cpustat.h> /* Standard mappings for irq_cpustat_t above */ - -void ack_bad_irq(unsigned int irq); +#include <asm-generic/hardirq.h> #endif /* _PARISC_HARDIRQ_H */ diff --git a/arch/parisc/include/asm/ptrace.h b/arch/parisc/include/asm/ptrace.h index 302f68dc889c..aead40b16dd8 100644 --- a/arch/parisc/include/asm/ptrace.h +++ b/arch/parisc/include/asm/ptrace.h @@ -59,8 +59,11 @@ void user_enable_block_step(struct task_struct *task); #define user_mode(regs) (((regs)->iaoq[0] & 3) ? 1 : 0) #define user_space(regs) (((regs)->iasq[1] != 0) ? 1 : 0) #define instruction_pointer(regs) ((regs)->iaoq[0] & ~3) +#define user_stack_pointer(regs) ((regs)->gr[30]) unsigned long profile_pc(struct pt_regs *); extern void show_regs(struct pt_regs *); -#endif + + +#endif /* __KERNEL__ */ #endif diff --git a/arch/parisc/include/asm/syscall.h b/arch/parisc/include/asm/syscall.h new file mode 100644 index 000000000000..8bdfd2c8c39f --- /dev/null +++ b/arch/parisc/include/asm/syscall.h @@ -0,0 +1,40 @@ +/* syscall.h */ + +#ifndef _ASM_PARISC_SYSCALL_H_ +#define _ASM_PARISC_SYSCALL_H_ + +#include <linux/err.h> +#include <asm/ptrace.h> + +static inline long syscall_get_nr(struct task_struct *tsk, + struct pt_regs *regs) +{ + return regs->gr[20]; +} + +static inline void syscall_get_arguments(struct task_struct *tsk, + struct pt_regs *regs, unsigned int i, + unsigned int n, unsigned long *args) +{ + BUG_ON(i); + + switch (n) { + case 6: + args[5] = regs->gr[21]; + case 5: + args[4] = regs->gr[22]; + case 4: + args[3] = regs->gr[23]; + case 3: + args[2] = regs->gr[24]; + case 2: + args[1] = regs->gr[25]; + case 1: + args[0] = regs->gr[26]; + break; + default: + BUG(); + } +} + +#endif /*_ASM_PARISC_SYSCALL_H_*/ diff --git a/arch/parisc/include/asm/thread_info.h b/arch/parisc/include/asm/thread_info.h index ac775a76bff7..7ecc1039cfed 100644 --- a/arch/parisc/include/asm/thread_info.h +++ b/arch/parisc/include/asm/thread_info.h @@ -32,6 +32,11 @@ struct thread_info { #define init_thread_info (init_thread_union.thread_info) #define init_stack (init_thread_union.stack) +/* how to get the thread information struct from C */ +#define current_thread_info() ((struct thread_info *)mfctl(30)) + +#endif /* !__ASSEMBLY */ + /* thread information allocation */ #define THREAD_SIZE_ORDER 2 @@ -40,11 +45,6 @@ struct thread_info { #define THREAD_SIZE (PAGE_SIZE << THREAD_SIZE_ORDER) #define THREAD_SHIFT (PAGE_SHIFT + THREAD_SIZE_ORDER) -/* how to get the thread information struct from C */ -#define current_thread_info() ((struct thread_info *)mfctl(30)) - -#endif /* !__ASSEMBLY */ - #define PREEMPT_ACTIVE_BIT 28 #define PREEMPT_ACTIVE (1 << PREEMPT_ACTIVE_BIT) @@ -60,6 +60,8 @@ struct thread_info { #define TIF_RESTORE_SIGMASK 6 /* restore saved signal mask */ #define TIF_FREEZE 7 /* is freezing for suspend */ #define TIF_NOTIFY_RESUME 8 /* callback before returning to user */ +#define TIF_SINGLESTEP 9 /* single stepping? */ +#define TIF_BLOCKSTEP 10 /* branch stepping? */ #define _TIF_SYSCALL_TRACE (1 << TIF_SYSCALL_TRACE) #define _TIF_SIGPENDING (1 << TIF_SIGPENDING) @@ -69,6 +71,8 @@ struct thread_info { #define _TIF_RESTORE_SIGMASK (1 << TIF_RESTORE_SIGMASK) #define _TIF_FREEZE (1 << TIF_FREEZE) #define _TIF_NOTIFY_RESUME (1 << TIF_NOTIFY_RESUME) +#define _TIF_SINGLESTEP (1 << TIF_SINGLESTEP) +#define _TIF_BLOCKSTEP (1 << TIF_BLOCKSTEP) #define _TIF_USER_WORK_MASK (_TIF_SIGPENDING | _TIF_NOTIFY_RESUME | \ _TIF_NEED_RESCHED | _TIF_RESTORE_SIGMASK) diff --git a/arch/parisc/kernel/asm-offsets.c b/arch/parisc/kernel/asm-offsets.c index 699cf8ef2118..fcd3c707bf12 100644 --- a/arch/parisc/kernel/asm-offsets.c +++ b/arch/parisc/kernel/asm-offsets.c @@ -270,8 +270,8 @@ int main(void) DEFINE(DTLB_OFF_COUNT, offsetof(struct pdc_cache_info, dt_off_count)); DEFINE(DTLB_LOOP, offsetof(struct pdc_cache_info, dt_loop)); BLANK(); - DEFINE(PA_BLOCKSTEP_BIT, 31-PT_BLOCKSTEP_BIT); - DEFINE(PA_SINGLESTEP_BIT, 31-PT_SINGLESTEP_BIT); + DEFINE(TIF_BLOCKSTEP_PA_BIT, 31-TIF_BLOCKSTEP); + DEFINE(TIF_SINGLESTEP_PA_BIT, 31-TIF_SINGLESTEP); BLANK(); DEFINE(ASM_PMD_SHIFT, PMD_SHIFT); DEFINE(ASM_PGDIR_SHIFT, PGDIR_SHIFT); diff --git a/arch/parisc/kernel/entry.S b/arch/parisc/kernel/entry.S index 8c4712b74dc1..3a44f7f704fa 100644 --- a/arch/parisc/kernel/entry.S +++ b/arch/parisc/kernel/entry.S @@ -2047,12 +2047,13 @@ syscall_do_signal: b,n syscall_check_sig syscall_restore: - /* Are we being ptraced? */ LDREG TI_TASK-THREAD_SZ_ALGN-FRAME_SIZE(%r30),%r1 - ldw TASK_PTRACE(%r1), %r19 - bb,< %r19,31,syscall_restore_rfi - nop + /* Are we being ptraced? */ + ldw TASK_FLAGS(%r1),%r19 + ldi (_TIF_SINGLESTEP|_TIF_BLOCKSTEP),%r2 + and,COND(=) %r19,%r2,%r0 + b,n syscall_restore_rfi ldo TASK_PT_FR31(%r1),%r19 /* reload fpregs */ rest_fp %r19 @@ -2113,16 +2114,16 @@ syscall_restore_rfi: ldi 0x0b,%r20 /* Create new PSW */ depi -1,13,1,%r20 /* C, Q, D, and I bits */ - /* The values of PA_SINGLESTEP_BIT and PA_BLOCKSTEP_BIT are - * set in include/linux/ptrace.h and converted to PA bitmap + /* The values of SINGLESTEP_BIT and BLOCKSTEP_BIT are + * set in thread_info.h and converted to PA bitmap * numbers in asm-offsets.c */ - /* if ((%r19.PA_SINGLESTEP_BIT)) { %r20.27=1} */ - extru,= %r19,PA_SINGLESTEP_BIT,1,%r0 + /* if ((%r19.SINGLESTEP_BIT)) { %r20.27=1} */ + extru,= %r19,TIF_SINGLESTEP_PA_BIT,1,%r0 depi -1,27,1,%r20 /* R bit */ - /* if ((%r19.PA_BLOCKSTEP_BIT)) { %r20.7=1} */ - extru,= %r19,PA_BLOCKSTEP_BIT,1,%r0 + /* if ((%r19.BLOCKSTEP_BIT)) { %r20.7=1} */ + extru,= %r19,TIF_BLOCKSTEP_PA_BIT,1,%r0 depi -1,7,1,%r20 /* T bit */ STREG %r20,TASK_PT_PSW(%r1) diff --git a/arch/parisc/kernel/irq.c b/arch/parisc/kernel/irq.c index 330f536a9324..2e7610cb33d5 100644 --- a/arch/parisc/kernel/irq.c +++ b/arch/parisc/kernel/irq.c @@ -423,8 +423,3 @@ void __init init_IRQ(void) set_eiem(cpu_eiem); /* EIEM : enable all external intr */ } - -void ack_bad_irq(unsigned int irq) -{ - printk(KERN_WARNING "unexpected IRQ %d\n", irq); -} diff --git a/arch/parisc/kernel/module.c b/arch/parisc/kernel/module.c index 61ee0eec4e69..212074653df7 100644 --- a/arch/parisc/kernel/module.c +++ b/arch/parisc/kernel/module.c @@ -893,7 +893,7 @@ int module_finalize(const Elf_Ehdr *hdr, * ourselves */ for (i = 1; i < hdr->e_shnum; i++) { if(sechdrs[i].sh_type == SHT_SYMTAB - && (sechdrs[i].sh_type & SHF_ALLOC)) { + && (sechdrs[i].sh_flags & SHF_ALLOC)) { int strindex = sechdrs[i].sh_link; /* FIXME: AWFUL HACK * The cast is to drop the const from diff --git a/arch/parisc/kernel/ptrace.c b/arch/parisc/kernel/ptrace.c index 927db3668b6f..c4f49e45129d 100644 --- a/arch/parisc/kernel/ptrace.c +++ b/arch/parisc/kernel/ptrace.c @@ -13,6 +13,7 @@ #include <linux/smp.h> #include <linux/errno.h> #include <linux/ptrace.h> +#include <linux/tracehook.h> #include <linux/user.h> #include <linux/personality.h> #include <linux/security.h> @@ -35,7 +36,8 @@ */ void ptrace_disable(struct task_struct *task) { - task->ptrace &= ~(PT_SINGLESTEP|PT_BLOCKSTEP); + clear_tsk_thread_flag(task, TIF_SINGLESTEP); + clear_tsk_thread_flag(task, TIF_BLOCKSTEP); /* make sure the trap bits are not set */ pa_psw(task)->r = 0; @@ -55,8 +57,8 @@ void user_disable_single_step(struct task_struct *task) void user_enable_single_step(struct task_struct *task) { - task->ptrace &= ~PT_BLOCKSTEP; - task->ptrace |= PT_SINGLESTEP; + clear_tsk_thread_flag(task, TIF_BLOCKSTEP); + set_tsk_thread_flag(task, TIF_SINGLESTEP); if (pa_psw(task)->n) { struct siginfo si; @@ -98,8 +100,8 @@ void user_enable_single_step(struct task_struct *task) void user_enable_block_step(struct task_struct *task) { - task->ptrace &= ~PT_SINGLESTEP; - task->ptrace |= PT_BLOCKSTEP; + clear_tsk_thread_flag(task, TIF_SINGLESTEP); + set_tsk_thread_flag(task, TIF_BLOCKSTEP); /* Enable taken branch trap. */ pa_psw(task)->r = 0; @@ -263,22 +265,20 @@ long compat_arch_ptrace(struct task_struct *child, compat_long_t request, } #endif +long do_syscall_trace_enter(struct pt_regs *regs) +{ + if (test_thread_flag(TIF_SYSCALL_TRACE) && + tracehook_report_syscall_entry(regs)) + return -1L; + + return regs->gr[20]; +} -void syscall_trace(void) +void do_syscall_trace_exit(struct pt_regs *regs) { - if (!test_thread_flag(TIF_SYSCALL_TRACE)) - return; - if (!(current->ptrace & PT_PTRACED)) - return; - ptrace_notify(SIGTRAP | ((current->ptrace & PT_TRACESYSGOOD) - ? 0x80 : 0)); - /* - * this isn't the same as continuing with a signal, but it will do - * for normal use. strace only continues with a signal if the - * stopping signal is not SIGTRAP. -brl - */ - if (current->exit_code) { - send_sig(current->exit_code, current, 1); - current->exit_code = 0; - } + int stepping = test_thread_flag(TIF_SINGLESTEP) || + test_thread_flag(TIF_BLOCKSTEP); + + if (stepping || test_thread_flag(TIF_SYSCALL_TRACE)) + tracehook_report_syscall_exit(regs, stepping); } diff --git a/arch/parisc/kernel/signal.c b/arch/parisc/kernel/signal.c index 8eb3c63c407a..e8467e4aa8d1 100644 --- a/arch/parisc/kernel/signal.c +++ b/arch/parisc/kernel/signal.c @@ -21,6 +21,7 @@ #include <linux/errno.h> #include <linux/wait.h> #include <linux/ptrace.h> +#include <linux/tracehook.h> #include <linux/unistd.h> #include <linux/stddef.h> #include <linux/compat.h> @@ -34,7 +35,6 @@ #include <asm/asm-offsets.h> #ifdef CONFIG_COMPAT -#include <linux/compat.h> #include "signal32.h" #endif @@ -468,6 +468,9 @@ handle_signal(unsigned long sig, siginfo_t *info, struct k_sigaction *ka, sigaddset(¤t->blocked,sig); recalc_sigpending(); spin_unlock_irq(¤t->sighand->siglock); + + tracehook_signal_handler(sig, info, ka, regs, 0); + return 1; } diff --git a/arch/parisc/kernel/syscall.S b/arch/parisc/kernel/syscall.S index 59fc1a43ec3e..f5f96021caa0 100644 --- a/arch/parisc/kernel/syscall.S +++ b/arch/parisc/kernel/syscall.S @@ -288,18 +288,23 @@ tracesys: STREG %r18,PT_GR18(%r2) /* Finished saving things for the debugger */ - ldil L%syscall_trace,%r1 + copy %r2,%r26 + ldil L%do_syscall_trace_enter,%r1 ldil L%tracesys_next,%r2 - be R%syscall_trace(%sr7,%r1) + be R%do_syscall_trace_enter(%sr7,%r1) ldo R%tracesys_next(%r2),%r2 -tracesys_next: +tracesys_next: + /* do_syscall_trace_enter either returned the syscallno, or -1L, + * so we skip restoring the PT_GR20 below, since we pulled it from + * task->thread.regs.gr[20] above. + */ + copy %ret0,%r20 ldil L%sys_call_table,%r1 ldo R%sys_call_table(%r1), %r19 ldo -THREAD_SZ_ALGN-FRAME_SIZE(%r30),%r1 /* get task ptr */ LDREG TI_TASK(%r1), %r1 - LDREG TASK_PT_GR20(%r1), %r20 LDREG TASK_PT_GR26(%r1), %r26 /* Restore the users args */ LDREG TASK_PT_GR25(%r1), %r25 LDREG TASK_PT_GR24(%r1), %r24 @@ -336,7 +341,8 @@ tracesys_exit: #ifdef CONFIG_64BIT ldo -16(%r30),%r29 /* Reference param save area */ #endif - bl syscall_trace, %r2 + ldo TASK_REGS(%r1),%r26 + bl do_syscall_trace_exit,%r2 STREG %r28,TASK_PT_GR28(%r1) /* save return value now */ ldo -THREAD_SZ_ALGN-FRAME_SIZE(%r30),%r1 /* get task ptr */ LDREG TI_TASK(%r1), %r1 @@ -353,12 +359,12 @@ tracesys_exit: tracesys_sigexit: ldo -THREAD_SZ_ALGN-FRAME_SIZE(%r30),%r1 /* get task ptr */ - LDREG 0(%r1), %r1 + LDREG TI_TASK(%r1), %r1 #ifdef CONFIG_64BIT ldo -16(%r30),%r29 /* Reference param save area */ #endif - bl syscall_trace, %r2 - nop + bl do_syscall_trace_exit,%r2 + ldo TASK_REGS(%r1),%r26 ldil L%syscall_exit_rfi,%r1 be,n R%syscall_exit_rfi(%sr7,%r1) diff --git a/arch/parisc/kernel/vmlinux.lds.S b/arch/parisc/kernel/vmlinux.lds.S index 775be2791bc2..fda4baa059b5 100644 --- a/arch/parisc/kernel/vmlinux.lds.S +++ b/arch/parisc/kernel/vmlinux.lds.S @@ -28,6 +28,7 @@ #include <asm/cache.h> #include <asm/page.h> #include <asm/asm-offsets.h> +#include <asm/thread_info.h> /* ld script to make hppa Linux kernel */ #ifndef CONFIG_64BIT @@ -134,6 +135,15 @@ SECTIONS __init_begin = .; INIT_TEXT_SECTION(16384) INIT_DATA_SECTION(16) + /* we have to discard exit text and such at runtime, not link time */ + .exit.text : + { + EXIT_TEXT + } + .exit.data : + { + EXIT_DATA + } PERCPU(PAGE_SIZE) . = ALIGN(PAGE_SIZE); diff --git a/arch/parisc/mm/init.c b/arch/parisc/mm/init.c index d5aca31fddbb..13b6e3e59b99 100644 --- a/arch/parisc/mm/init.c +++ b/arch/parisc/mm/init.c @@ -434,8 +434,8 @@ void mark_rodata_ro(void) #define SET_MAP_OFFSET(x) ((void *)(((unsigned long)(x) + VM_MAP_OFFSET) \ & ~(VM_MAP_OFFSET-1))) -void *vmalloc_start __read_mostly; -EXPORT_SYMBOL(vmalloc_start); +void *parisc_vmalloc_start __read_mostly; +EXPORT_SYMBOL(parisc_vmalloc_start); #ifdef CONFIG_PA11 unsigned long pcxl_dma_start __read_mostly; @@ -496,13 +496,14 @@ void __init mem_init(void) #ifdef CONFIG_PA11 if (hppa_dma_ops == &pcxl_dma_ops) { pcxl_dma_start = (unsigned long)SET_MAP_OFFSET(MAP_START); - vmalloc_start = SET_MAP_OFFSET(pcxl_dma_start + PCXL_DMA_MAP_SIZE); + parisc_vmalloc_start = SET_MAP_OFFSET(pcxl_dma_start + + PCXL_DMA_MAP_SIZE); } else { pcxl_dma_start = 0; - vmalloc_start = SET_MAP_OFFSET(MAP_START); + parisc_vmalloc_start = SET_MAP_OFFSET(MAP_START); } #else - vmalloc_start = SET_MAP_OFFSET(MAP_START); + parisc_vmalloc_start = SET_MAP_OFFSET(MAP_START); #endif printk(KERN_INFO "Memory: %luk/%luk available (%dk kernel code, %dk reserved, %dk data, %dk init)\n", diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 10a0a5488a44..2ba14e77296c 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -414,6 +414,10 @@ config ARCH_SPARSEMEM_DEFAULT config ARCH_POPULATES_NODE_MAP def_bool y +config SYS_SUPPORTS_HUGETLBFS + def_bool y + depends on PPC_BOOK3S_64 + source "mm/Kconfig" config ARCH_MEMORY_PROBE diff --git a/arch/powerpc/boot/addRamDisk.c b/arch/powerpc/boot/addRamDisk.c index c02a99952be7..893f446cbd22 100644 --- a/arch/powerpc/boot/addRamDisk.c +++ b/arch/powerpc/boot/addRamDisk.c @@ -58,7 +58,7 @@ static int check_elf64(void *p, int size, struct addr_range *r) return 64; } -void get4k(FILE *file, char *buf ) +static void get4k(FILE *file, char *buf ) { unsigned j; unsigned num = fread(buf, 1, 4096, file); @@ -66,12 +66,12 @@ void get4k(FILE *file, char *buf ) buf[j] = 0; } -void put4k(FILE *file, char *buf ) +static void put4k(FILE *file, char *buf ) { fwrite(buf, 1, 4096, file); } -void death(const char *msg, FILE *fdesc, const char *fname) +static void death(const char *msg, FILE *fdesc, const char *fname) { fprintf(stderr, msg); fclose(fdesc); diff --git a/arch/powerpc/boot/dts/cm5200.dts b/arch/powerpc/boot/dts/cm5200.dts index cee8080aa245..dd3860846f15 100644 --- a/arch/powerpc/boot/dts/cm5200.dts +++ b/arch/powerpc/boot/dts/cm5200.dts @@ -210,7 +210,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; }; sram@8000 { diff --git a/arch/powerpc/boot/dts/digsy_mtc.dts b/arch/powerpc/boot/dts/digsy_mtc.dts index 4c36186ef946..8e9be6bfe23e 100644 --- a/arch/powerpc/boot/dts/digsy_mtc.dts +++ b/arch/powerpc/boot/dts/digsy_mtc.dts @@ -199,7 +199,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d00 0x40>; interrupts = <2 15 0>; - fsl5200-clocking; rtc@50 { compatible = "at,24c08"; diff --git a/arch/powerpc/boot/dts/lite5200.dts b/arch/powerpc/boot/dts/lite5200.dts index de30b3f9eb26..82ff2b13bc37 100644 --- a/arch/powerpc/boot/dts/lite5200.dts +++ b/arch/powerpc/boot/dts/lite5200.dts @@ -247,7 +247,6 @@ compatible = "fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d00 0x40>; interrupts = <2 15 0>; - fsl5200-clocking; }; i2c@3d40 { @@ -256,7 +255,6 @@ compatible = "fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; }; sram@8000 { compatible = "fsl,mpc5200-sram"; diff --git a/arch/powerpc/boot/dts/lite5200b.dts b/arch/powerpc/boot/dts/lite5200b.dts index d13cb11ce623..e45a63be3a86 100644 --- a/arch/powerpc/boot/dts/lite5200b.dts +++ b/arch/powerpc/boot/dts/lite5200b.dts @@ -251,7 +251,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d00 0x40>; interrupts = <2 15 0>; - fsl5200-clocking; }; i2c@3d40 { @@ -260,7 +259,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; }; sram@8000 { diff --git a/arch/powerpc/boot/dts/media5200.dts b/arch/powerpc/boot/dts/media5200.dts index e297d8b41875..0c3902bc5b6a 100644 --- a/arch/powerpc/boot/dts/media5200.dts +++ b/arch/powerpc/boot/dts/media5200.dts @@ -223,7 +223,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d00 0x40>; interrupts = <2 15 0>; - fsl5200-clocking; }; i2c@3d40 { @@ -232,7 +231,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; }; sram@8000 { diff --git a/arch/powerpc/boot/dts/motionpro.dts b/arch/powerpc/boot/dts/motionpro.dts index 7be8ca038676..6ca4fc144a33 100644 --- a/arch/powerpc/boot/dts/motionpro.dts +++ b/arch/powerpc/boot/dts/motionpro.dts @@ -222,7 +222,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; rtc@68 { compatible = "dallas,ds1339"; diff --git a/arch/powerpc/boot/dts/mpc5121ads.dts b/arch/powerpc/boot/dts/mpc5121ads.dts index c2b8dbfab79e..c353dac33416 100644 --- a/arch/powerpc/boot/dts/mpc5121ads.dts +++ b/arch/powerpc/boot/dts/mpc5121ads.dts @@ -209,7 +209,6 @@ reg = <0x1700 0x20>; interrupts = <9 0x8>; interrupt-parent = < &ipic >; - fsl5200-clocking; }; i2c@1720 { @@ -220,7 +219,6 @@ reg = <0x1720 0x20>; interrupts = <10 0x8>; interrupt-parent = < &ipic >; - fsl5200-clocking; }; i2c@1740 { @@ -231,7 +229,6 @@ reg = <0x1740 0x20>; interrupts = <11 0x8>; interrupt-parent = < &ipic >; - fsl5200-clocking; }; i2ccontrol@1760 { diff --git a/arch/powerpc/boot/dts/mpc8377_wlan.dts b/arch/powerpc/boot/dts/mpc8377_wlan.dts index 9a603695723b..9ea783056969 100644 --- a/arch/powerpc/boot/dts/mpc8377_wlan.dts +++ b/arch/powerpc/boot/dts/mpc8377_wlan.dts @@ -67,7 +67,7 @@ device-width = <1>; partition@0 { - reg = <0 0x8000>; + reg = <0 0x80000>; label = "u-boot"; read-only; }; diff --git a/arch/powerpc/boot/dts/mpc8569mds.dts b/arch/powerpc/boot/dts/mpc8569mds.dts index 06332d61830a..1e3ec8f059bf 100644 --- a/arch/powerpc/boot/dts/mpc8569mds.dts +++ b/arch/powerpc/boot/dts/mpc8569mds.dts @@ -487,8 +487,8 @@ &qe_pio_f 5 0 /* USBTN */ &qe_pio_f 6 0 /* USBRP */ &qe_pio_f 8 0 /* USBRN */ - &bcsr17 6 0 /* SPEED */ - &bcsr17 5 1>; /* POWER */ + &bcsr17 1 0 /* SPEED */ + &bcsr17 2 0>; /* POWER */ }; enet0: ucc@2000 { diff --git a/arch/powerpc/boot/dts/mucmc52.dts b/arch/powerpc/boot/dts/mucmc52.dts new file mode 100644 index 000000000000..b72a7581d798 --- /dev/null +++ b/arch/powerpc/boot/dts/mucmc52.dts @@ -0,0 +1,332 @@ +/* + * Manroland mucmc52 board Device Tree Source + * + * Copyright (C) 2009 DENX Software Engineering GmbH + * Heiko Schocher <hs@denx.de> + * Copyright 2006-2007 Secret Lab Technologies Ltd. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + */ + +/dts-v1/; + +/ { + model = "manroland,mucmc52"; + compatible = "manroland,mucmc52"; + #address-cells = <1>; + #size-cells = <1>; + interrupt-parent = <&mpc5200_pic>; + + cpus { + #address-cells = <1>; + #size-cells = <0>; + + PowerPC,5200@0 { + device_type = "cpu"; + reg = <0>; + d-cache-line-size = <32>; + i-cache-line-size = <32>; + d-cache-size = <0x4000>; // L1, 16K + i-cache-size = <0x4000>; // L1, 16K + timebase-frequency = <0>; // from bootloader + bus-frequency = <0>; // from bootloader + clock-frequency = <0>; // from bootloader + }; + }; + + memory { + device_type = "memory"; + reg = <0x00000000 0x04000000>; // 64MB + }; + + soc5200@f0000000 { + #address-cells = <1>; + #size-cells = <1>; + compatible = "fsl,mpc5200b-immr"; + ranges = <0 0xf0000000 0x0000c000>; + reg = <0xf0000000 0x00000100>; + bus-frequency = <0>; // from bootloader + system-frequency = <0>; // from bootloader + + cdm@200 { + compatible = "fsl,mpc5200b-cdm","fsl,mpc5200-cdm"; + reg = <0x200 0x38>; + }; + + mpc5200_pic: interrupt-controller@500 { + // 5200 interrupts are encoded into two levels; + interrupt-controller; + #interrupt-cells = <3>; + compatible = "fsl,mpc5200b-pic","fsl,mpc5200-pic"; + reg = <0x500 0x80>; + }; + + gpt0: timer@600 { // GPT 0 in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x600 0x10>; + interrupts = <1 9 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt1: timer@610 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x610 0x10>; + interrupts = <1 10 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt2: timer@620 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x620 0x10>; + interrupts = <1 11 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt3: timer@630 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x630 0x10>; + interrupts = <1 12 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpio_simple: gpio@b00 { + compatible = "fsl,mpc5200b-gpio","fsl,mpc5200-gpio"; + reg = <0xb00 0x40>; + interrupts = <1 7 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpio_wkup: gpio@c00 { + compatible = "fsl,mpc5200b-gpio-wkup","fsl,mpc5200-gpio-wkup"; + reg = <0xc00 0x40>; + interrupts = <1 8 0 0 3 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + dma-controller@1200 { + compatible = "fsl,mpc5200b-bestcomm","fsl,mpc5200-bestcomm"; + reg = <0x1200 0x80>; + interrupts = <3 0 0 3 1 0 3 2 0 3 3 0 + 3 4 0 3 5 0 3 6 0 3 7 0 + 3 8 0 3 9 0 3 10 0 3 11 0 + 3 12 0 3 13 0 3 14 0 3 15 0>; + }; + + xlb@1f00 { + compatible = "fsl,mpc5200b-xlb","fsl,mpc5200-xlb"; + reg = <0x1f00 0x100>; + }; + + serial@2000 { /* PSC1 in UART mode */ + compatible = "fsl,mpc5200b-psc-uart","fsl,mpc5200-psc-uart"; + reg = <0x2000 0x100>; + interrupts = <2 1 0>; + }; + + serial@2200 { /* PSC2 in UART mode */ + compatible = "fsl,mpc5200b-psc-uart","fsl,mpc5200-psc-uart"; + reg = <0x2200 0x100>; + interrupts = <2 2 0>; + }; + + serial@2c00 { /* PSC6 in UART mode */ + compatible = "fsl,mpc5200b-psc-uart","fsl,mpc5200-psc-uart"; + reg = <0x2c00 0x100>; + interrupts = <2 4 0>; + }; + + ethernet@3000 { + compatible = "fsl,mpc5200b-fec","fsl,mpc5200-fec"; + reg = <0x3000 0x400>; + local-mac-address = [ 00 00 00 00 00 00 ]; + interrupts = <2 5 0>; + phy-handle = <&phy0>; + }; + + mdio@3000 { + #address-cells = <1>; + #size-cells = <0>; + compatible = "fsl,mpc5200b-mdio","fsl,mpc5200-mdio"; + reg = <0x3000 0x400>; // fec range, since we need to setup fec interrupts + interrupts = <2 5 0>; // these are for "mii command finished", not link changes & co. + + phy0: ethernet-phy@0 { + compatible = "intel,lxt971"; + reg = <0>; + }; + }; + + ata@3a00 { + compatible = "fsl,mpc5200b-ata","fsl,mpc5200-ata"; + reg = <0x3a00 0x100>; + interrupts = <2 7 0>; + }; + + i2c@3d40 { + #address-cells = <1>; + #size-cells = <0>; + compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; + reg = <0x3d40 0x40>; + interrupts = <2 16 0>; + hwmon@2c { + compatible = "ad,adm9240"; + reg = <0x2c>; + }; + rtc@51 { + compatible = "nxp,pcf8563"; + reg = <0x51>; + }; + }; + + sram@8000 { + compatible = "fsl,mpc5200b-sram","fsl,mpc5200-sram"; + reg = <0x8000 0x4000>; + }; + }; + + pci@f0000d00 { + #interrupt-cells = <1>; + #size-cells = <2>; + #address-cells = <3>; + device_type = "pci"; + compatible = "fsl,mpc5200b-pci","fsl,mpc5200-pci"; + reg = <0xf0000d00 0x100>; + interrupt-map-mask = <0xf800 0 0 7>; + interrupt-map = < + /* IDSEL 0x10 */ + 0x8000 0 0 1 &mpc5200_pic 0 3 3 + 0x8000 0 0 2 &mpc5200_pic 0 3 3 + 0x8000 0 0 3 &mpc5200_pic 0 2 3 + 0x8000 0 0 4 &mpc5200_pic 0 1 3 + >; + clock-frequency = <0>; // From boot loader + interrupts = <2 8 0 2 9 0 2 10 0>; + bus-range = <0 0>; + ranges = <0x42000000 0 0x60000000 0x60000000 0 0x10000000 + 0x02000000 0 0x90000000 0x90000000 0 0x10000000 + 0x01000000 0 0x00000000 0xa0000000 0 0x01000000>; + }; + + localbus { + compatible = "fsl,mpc5200b-lpb","fsl,mpc5200-lpb","simple-bus"; + + #address-cells = <2>; + #size-cells = <1>; + + ranges = <0 0 0xff800000 0x00800000 + 1 0 0x80000000 0x00800000 + 3 0 0x80000000 0x00800000>; + + flash@0,0 { + compatible = "cfi-flash"; + reg = <0 0 0x00800000>; + bank-width = <4>; + device-width = <2>; + #size-cells = <1>; + #address-cells = <1>; + partition@0 { + label = "DTS"; + reg = <0x0 0x00100000>; + }; + partition@100000 { + label = "Kernel"; + reg = <0x100000 0x00200000>; + }; + partition@300000 { + label = "RootFS"; + reg = <0x00300000 0x00200000>; + }; + partition@500000 { + label = "user"; + reg = <0x00500000 0x00200000>; + }; + partition@700000 { + label = "U-Boot"; + reg = <0x00700000 0x00040000>; + }; + partition@740000 { + label = "Env"; + reg = <0x00740000 0x00020000>; + }; + partition@760000 { + label = "red. Env"; + reg = <0x00760000 0x00020000>; + }; + partition@780000 { + label = "reserve"; + reg = <0x00780000 0x00080000>; + }; + }; + + simple100: gpio-controller-100@3,600100 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600100 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple104: gpio-controller-104@3,600104 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600104 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple200: gpio-controller-200@3,600200 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600200 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple201: gpio-controller-201@3,600201 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600201 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple202: gpio-controller-202@3,600202 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600202 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple203: gpio-controller-203@3,600203 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600203 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple204: gpio-controller-204@3,600204 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600204 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple206: gpio-controller-206@3,600206 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600206 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple207: gpio-controller-207@3,600207 { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x00600207 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + simple20f: gpio-controller-20f@3,60020f { + compatible = "manroland,mucmc52-aux-gpio"; + reg = <3 0x0060020f 0x1>; + gpio-controller; + #gpio-cells = <2>; + }; + + }; +}; diff --git a/arch/powerpc/boot/dts/pcm030.dts b/arch/powerpc/boot/dts/pcm030.dts index 30bfdc04c6df..8a4ec30b21ae 100644 --- a/arch/powerpc/boot/dts/pcm030.dts +++ b/arch/powerpc/boot/dts/pcm030.dts @@ -244,7 +244,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d00 0x40>; interrupts = <2 15 0>; - fsl5200-clocking; }; i2c@3d40 { @@ -253,7 +252,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; rtc@51 { compatible = "nxp,pcf8563"; reg = <0x51>; diff --git a/arch/powerpc/boot/dts/pcm032.dts b/arch/powerpc/boot/dts/pcm032.dts index 030042678392..85d857a5d46e 100644 --- a/arch/powerpc/boot/dts/pcm032.dts +++ b/arch/powerpc/boot/dts/pcm032.dts @@ -244,7 +244,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d00 0x40>; interrupts = <2 15 0>; - fsl5200-clocking; }; i2c@3d40 { @@ -253,7 +252,6 @@ compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; rtc@51 { compatible = "nxp,pcf8563"; reg = <0x51>; diff --git a/arch/powerpc/boot/dts/sbc8548.dts b/arch/powerpc/boot/dts/sbc8548.dts index 9eefe00ed253..94a332251710 100644 --- a/arch/powerpc/boot/dts/sbc8548.dts +++ b/arch/powerpc/boot/dts/sbc8548.dts @@ -26,8 +26,7 @@ serial0 = &serial0; serial1 = &serial1; pci0 = &pci0; - /* pci1 doesn't have a corresponding physical connector */ - pci2 = &pci2; + pci1 = &pci1; }; cpus { @@ -381,7 +380,7 @@ bus-range = <0 0>; ranges = <0x02000000 0x0 0x80000000 0x80000000 0x0 0x10000000 0x01000000 0x0 0x00000000 0xe2000000 0x0 0x00800000>; - clock-frequency = <66666666>; + clock-frequency = <66000000>; #interrupt-cells = <1>; #size-cells = <2>; #address-cells = <3>; @@ -390,7 +389,7 @@ device_type = "pci"; }; - pci2: pcie@e000a000 { + pci1: pcie@e000a000 { interrupt-map-mask = <0xf800 0x0 0x0 0x7>; interrupt-map = < @@ -403,9 +402,9 @@ interrupt-parent = <&mpic>; interrupts = <0x1a 0x2>; bus-range = <0x0 0xff>; - ranges = <0x02000000 0x0 0xa0000000 0xa0000000 0x0 0x20000000 - 0x01000000 0x0 0x00000000 0xe3000000 0x0 0x08000000>; - clock-frequency = <33333333>; + ranges = <0x02000000 0x0 0xa0000000 0xa0000000 0x0 0x10000000 + 0x01000000 0x0 0x00000000 0xe2800000 0x0 0x08000000>; + clock-frequency = <33000000>; #interrupt-cells = <1>; #size-cells = <2>; #address-cells = <3>; @@ -419,11 +418,11 @@ device_type = "pci"; ranges = <0x02000000 0x0 0xa0000000 0x02000000 0x0 0xa0000000 - 0x0 0x20000000 + 0x0 0x10000000 0x01000000 0x0 0x00000000 0x01000000 0x0 0x00000000 - 0x0 0x08000000>; + 0x0 0x00800000>; }; }; }; diff --git a/arch/powerpc/boot/dts/tqm5200.dts b/arch/powerpc/boot/dts/tqm5200.dts index c9590b58b7b0..1db07f6cf133 100644 --- a/arch/powerpc/boot/dts/tqm5200.dts +++ b/arch/powerpc/boot/dts/tqm5200.dts @@ -160,7 +160,6 @@ compatible = "fsl,mpc5200-i2c","fsl-i2c"; reg = <0x3d40 0x40>; interrupts = <2 16 0>; - fsl5200-clocking; rtc@68 { compatible = "dallas,ds1307"; diff --git a/arch/powerpc/boot/dts/uc101.dts b/arch/powerpc/boot/dts/uc101.dts new file mode 100644 index 000000000000..019264c62904 --- /dev/null +++ b/arch/powerpc/boot/dts/uc101.dts @@ -0,0 +1,284 @@ +/* + * Manroland uc101 board Device Tree Source + * + * Copyright (C) 2009 DENX Software Engineering GmbH + * Heiko Schocher <hs@denx.de> + * Copyright 2006-2007 Secret Lab Technologies Ltd. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + */ + +/dts-v1/; + +/ { + model = "manroland,uc101"; + compatible = "manroland,uc101"; + #address-cells = <1>; + #size-cells = <1>; + interrupt-parent = <&mpc5200_pic>; + + cpus { + #address-cells = <1>; + #size-cells = <0>; + + PowerPC,5200@0 { + device_type = "cpu"; + reg = <0>; + d-cache-line-size = <32>; + i-cache-line-size = <32>; + d-cache-size = <0x4000>; // L1, 16K + i-cache-size = <0x4000>; // L1, 16K + timebase-frequency = <0>; // from bootloader + bus-frequency = <0>; // from bootloader + clock-frequency = <0>; // from bootloader + }; + }; + + memory { + device_type = "memory"; + reg = <0x00000000 0x04000000>; // 64MB + }; + + soc5200@f0000000 { + #address-cells = <1>; + #size-cells = <1>; + compatible = "fsl,mpc5200b-immr"; + ranges = <0 0xf0000000 0x0000c000>; + reg = <0xf0000000 0x00000100>; + bus-frequency = <0>; // from bootloader + system-frequency = <0>; // from bootloader + + cdm@200 { + compatible = "fsl,mpc5200b-cdm","fsl,mpc5200-cdm"; + reg = <0x200 0x38>; + }; + + mpc5200_pic: interrupt-controller@500 { + // 5200 interrupts are encoded into two levels; + interrupt-controller; + #interrupt-cells = <3>; + compatible = "fsl,mpc5200b-pic","fsl,mpc5200-pic"; + reg = <0x500 0x80>; + }; + + gpt0: timer@600 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x600 0x10>; + interrupts = <1 9 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt1: timer@610 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x610 0x10>; + interrupts = <1 10 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt2: timer@620 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x620 0x10>; + interrupts = <1 11 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt3: timer@630 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x630 0x10>; + interrupts = <1 12 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt4: timer@640 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x640 0x10>; + interrupts = <1 13 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt5: timer@650 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x650 0x10>; + interrupts = <1 14 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt6: timer@660 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x660 0x10>; + interrupts = <1 15 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpt7: timer@670 { // General Purpose Timer in GPIO mode + compatible = "fsl,mpc5200b-gpt","fsl,mpc5200-gpt"; + reg = <0x670 0x10>; + interrupts = <1 16 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpio_simple: gpio@b00 { + compatible = "fsl,mpc5200b-gpio","fsl,mpc5200-gpio"; + reg = <0xb00 0x40>; + interrupts = <1 7 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + gpio_wkup: gpio@c00 { + compatible = "fsl,mpc5200b-gpio-wkup","fsl,mpc5200-gpio-wkup"; + reg = <0xc00 0x40>; + interrupts = <1 8 0 0 3 0>; + gpio-controller; + #gpio-cells = <2>; + }; + + dma-controller@1200 { + compatible = "fsl,mpc5200b-bestcomm","fsl,mpc5200-bestcomm"; + reg = <0x1200 0x80>; + interrupts = <3 0 0 3 1 0 3 2 0 3 3 0 + 3 4 0 3 5 0 3 6 0 3 7 0 + 3 8 0 3 9 0 3 10 0 3 11 0 + 3 12 0 3 13 0 3 14 0 3 15 0>; + }; + + xlb@1f00 { + compatible = "fsl,mpc5200b-xlb","fsl,mpc5200-xlb"; + reg = <0x1f00 0x100>; + }; + + serial@2000 { /* PSC1 in UART mode */ + compatible = "fsl,mpc5200b-psc-uart","fsl,mpc5200-psc-uart"; + reg = <0x2000 0x100>; + interrupts = <2 1 0>; + }; + + serial@2200 { /* PSC2 in UART mode */ + compatible = "fsl,mpc5200b-psc-uart","fsl,mpc5200-psc-uart"; + reg = <0x2200 0x100>; + interrupts = <2 2 0>; + }; + + serial@2c00 { /* PSC6 in UART mode */ + compatible = "fsl,mpc5200b-psc-uart","fsl,mpc5200-psc-uart"; + reg = <0x2c00 0x100>; + interrupts = <2 4 0>; + }; + + ethernet@3000 { + compatible = "fsl,mpc5200b-fec","fsl,mpc5200-fec"; + reg = <0x3000 0x400>; + local-mac-address = [ 00 00 00 00 00 00 ]; + interrupts = <2 5 0>; + phy-handle = <&phy0>; + }; + + mdio@3000 { + #address-cells = <1>; + #size-cells = <0>; + compatible = "fsl,mpc5200b-mdio","fsl,mpc5200-mdio"; + reg = <0x3000 0x400>; // fec range, since we need to setup fec interrupts + interrupts = <2 5 0>; // these are for "mii command finished", not link changes & co. + + phy0: ethernet-phy@0 { + compatible = "intel,lxt971"; + reg = <0>; + }; + }; + + ata@3a00 { + compatible = "fsl,mpc5200b-ata","fsl,mpc5200-ata"; + reg = <0x3a00 0x100>; + interrupts = <2 7 0>; + }; + + i2c@3d40 { + #address-cells = <1>; + #size-cells = <0>; + compatible = "fsl,mpc5200b-i2c","fsl,mpc5200-i2c","fsl-i2c"; + reg = <0x3d40 0x40>; + interrupts = <2 16 0>; + fsl,preserve-clocking; + clock-frequency = <400000>; + + hwmon@2c { + compatible = "ad,adm9240"; + reg = <0x2c>; + }; + rtc@51 { + compatible = "nxp,pcf8563"; + reg = <0x51>; + }; + }; + + sram@8000 { + compatible = "fsl,mpc5200b-sram","fsl,mpc5200-sram"; + reg = <0x8000 0x4000>; + }; + }; + + localbus { + compatible = "fsl,mpc5200b-lpb","fsl,mpc5200-lpb","simple-bus"; + + #address-cells = <2>; + #size-cells = <1>; + + ranges = <0 0 0xff800000 0x00800000 + 1 0 0x80000000 0x00800000 + 3 0 0x80000000 0x00800000>; + + flash@0,0 { + compatible = "cfi-flash"; + reg = <0 0 0x00800000>; + bank-width = <2>; + device-width = <2>; + #size-cells = <1>; + #address-cells = <1>; + + partition@0 { + label = "DTS"; + reg = <0x0 0x00100000>; + }; + partition@100000 { + label = "Kernel"; + reg = <0x100000 0x00200000>; + }; + partition@300000 { + label = "RootFS"; + reg = <0x00300000 0x00200000>; + }; + partition@500000 { + label = "user"; + reg = <0x00500000 0x00200000>; + }; + partition@700000 { + label = "U-Boot"; + reg = <0x00700000 0x00040000>; + }; + partition@740000 { + label = "Env"; + reg = <0x00740000 0x00010000>; + }; + partition@750000 { + label = "red. Env"; + reg = <0x00750000 0x00010000>; + }; + partition@760000 { + label = "reserve"; + reg = <0x00760000 0x000a0000>; + }; + }; + + }; +}; diff --git a/arch/powerpc/configs/52xx/cm5200_defconfig b/arch/powerpc/configs/52xx/cm5200_defconfig index 3838b77b8116..0396ce7bffc6 100644 --- a/arch/powerpc/configs/52xx/cm5200_defconfig +++ b/arch/powerpc/configs/52xx/cm5200_defconfig @@ -1,25 +1,27 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc2 -# Sat Apr 18 00:47:44 2009 +# Linux kernel version: 2.6.32-rc4 +# Thu Oct 15 10:33:22 2009 # # CONFIG_PPC64 is not set # # Processor support # -CONFIG_6xx=y +CONFIG_PPC_BOOK3S_32=y # CONFIG_PPC_85xx is not set # CONFIG_PPC_8xx is not set # CONFIG_40x is not set # CONFIG_44x is not set # CONFIG_E200 is not set CONFIG_PPC_BOOK3S=y +CONFIG_6xx=y CONFIG_PPC_FPU=y # CONFIG_ALTIVEC is not set CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set +CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set CONFIG_PPC32=y CONFIG_WORD_SIZE=32 @@ -30,15 +32,17 @@ CONFIG_GENERIC_TIME=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y +CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_GENERIC_HWEIGHT=y -CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_FIND_NEXT_BIT=y # CONFIG_ARCH_NO_VIRT_TO_BUS is not set CONFIG_PPC=y @@ -52,11 +56,13 @@ CONFIG_OF=y # CONFIG_GENERIC_TBSYNC is not set CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y +CONFIG_DTC=y CONFIG_DEFAULT_UIMAGE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -77,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -105,7 +112,6 @@ CONFIG_ANON_INODES=y CONFIG_EMBEDDED=y # CONFIG_SYSCTL_SYSCALL is not set # CONFIG_KALLSYMS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -118,6 +124,13 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +# CONFIG_PERF_EVENTS is not set +# CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_SLUB_DEBUG=y CONFIG_COMPAT_BRK=y @@ -125,14 +138,19 @@ CONFIG_COMPAT_BRK=y CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# # CONFIG_SLOW_WORK is not set # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y @@ -140,7 +158,7 @@ CONFIG_RT_MUTEXES=y CONFIG_BASE_SMALL=0 # CONFIG_MODULES is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -219,11 +237,13 @@ CONFIG_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set # CONFIG_IOMMU_HELPER is not set +# CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -239,9 +259,10 @@ CONFIG_MIGRATION=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set # CONFIG_PPC_64K_PAGES is not set @@ -252,6 +273,7 @@ CONFIG_PROC_DEVICETREE=y CONFIG_EXTRA_TARGETS="" CONFIG_PM=y # CONFIG_PM_DEBUG is not set +# CONFIG_PM_RUNTIME is not set CONFIG_SECCOMP=y CONFIG_ISA_DMA_API=y @@ -328,6 +350,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -342,6 +365,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -367,6 +391,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -457,6 +482,7 @@ CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_UBI is not set CONFIG_OF_DEVICE=y CONFIG_OF_I2C=y +CONFIG_OF_MDIO=y # CONFIG_PARPORT is not set CONFIG_BLK_DEV=y # CONFIG_BLK_DEV_FD is not set @@ -495,10 +521,6 @@ CONFIG_BLK_DEV_SD=y # CONFIG_BLK_DEV_SR is not set CONFIG_CHR_DEV_SG=y # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -519,7 +541,6 @@ CONFIG_CHR_DEV_SG=y # CONFIG_MD is not set # CONFIG_MACINTOSH_DRIVERS is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -558,14 +579,14 @@ CONFIG_NET_ETHERNET=y # CONFIG_IBM_NEW_EMAC_MAL_CLR_ICINTSTAT is not set # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set CONFIG_FEC_MPC52xx=y CONFIG_FEC_MPC52xx_MDIO=y +# CONFIG_XILINX_EMACLITE is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -636,6 +657,7 @@ CONFIG_LEGACY_PTY_COUNT=256 # CONFIG_TCG_TPM is not set CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -646,6 +668,7 @@ CONFIG_I2C_HELPER_AUTO=y # # I2C system bus drivers (mostly embedded / system-on-chip) # +# CONFIG_I2C_DESIGNWARE is not set CONFIG_I2C_MPC=y # CONFIG_I2C_OCORES is not set # CONFIG_I2C_SIMTEC is not set @@ -666,23 +689,23 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set # CONFIG_I2C_DEBUG_CHIP is not set # CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -713,25 +736,12 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_AB3100_CORE is not set # CONFIG_REGULATOR is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -# CONFIG_DAB is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support @@ -775,11 +785,12 @@ CONFIG_USB_DEVICEFS=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_SOC=y -CONFIG_USB_OHCI_HCD_PPC_OF=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set +CONFIG_USB_OHCI_HCD_PPC_OF=y CONFIG_USB_OHCI_BIG_ENDIAN_DESC=y CONFIG_USB_OHCI_BIG_ENDIAN_MMIO=y # CONFIG_USB_OHCI_LITTLE_ENDIAN is not set @@ -866,6 +877,10 @@ CONFIG_USB_STORAGE=y # CONFIG_DMADEVICES is not set # CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -885,10 +900,13 @@ CONFIG_FS_MBCACHE=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -959,12 +977,12 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y # CONFIG_NFS_V3_ACL is not set CONFIG_NFS_V4=y +# CONFIG_NFS_V4_1 is not set CONFIG_ROOT_NFS=y # CONFIG_NFSD is not set CONFIG_LOCKD=y @@ -1064,6 +1082,7 @@ CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y CONFIG_NLATTR=y +CONFIG_GENERIC_ATOMIC64=y # # Kernel hacking @@ -1073,6 +1092,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1090,10 +1110,14 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set +# CONFIG_DEBUG_LOCK_ALLOC is not set +# CONFIG_PROVE_LOCKING is not set +# CONFIG_LOCK_STAT is not set # CONFIG_DEBUG_SPINLOCK_SLEEP is not set # CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set # CONFIG_DEBUG_KOBJECT is not set @@ -1105,11 +1129,12 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set -# CONFIG_BOOT_PRINTK_DELAY is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -1118,23 +1143,25 @@ CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# +CONFIG_FTRACE=y # CONFIG_FUNCTION_TRACER is not set +# CONFIG_IRQSOFF_TRACER is not set # CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set +# CONFIG_ENABLE_DEFAULT_TRACERS is not set # CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set +CONFIG_BRANCH_PROFILE_NONE=y +# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set +# CONFIG_PROFILE_ALL_BRANCHES is not set # CONFIG_STACK_TRACER is not set # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_DEBUG_STACKOVERFLOW is not set # CONFIG_DEBUG_STACK_USAGE is not set @@ -1159,7 +1186,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1200,11 +1226,13 @@ CONFIG_CRYPTO_PCBC=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/52xx/lite5200b_defconfig b/arch/powerpc/configs/52xx/lite5200b_defconfig index 29b0f34488f5..f5c07fd72239 100644 --- a/arch/powerpc/configs/52xx/lite5200b_defconfig +++ b/arch/powerpc/configs/52xx/lite5200b_defconfig @@ -1,25 +1,27 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc2 -# Sat Apr 18 00:48:04 2009 +# Linux kernel version: 2.6.32-rc4 +# Thu Oct 15 10:33:24 2009 # # CONFIG_PPC64 is not set # # Processor support # -CONFIG_6xx=y +CONFIG_PPC_BOOK3S_32=y # CONFIG_PPC_85xx is not set # CONFIG_PPC_8xx is not set # CONFIG_40x is not set # CONFIG_44x is not set # CONFIG_E200 is not set CONFIG_PPC_BOOK3S=y +CONFIG_6xx=y CONFIG_PPC_FPU=y # CONFIG_ALTIVEC is not set CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set +CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set CONFIG_PPC32=y CONFIG_WORD_SIZE=32 @@ -30,15 +32,17 @@ CONFIG_GENERIC_TIME=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y +CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_GENERIC_HWEIGHT=y -CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_FIND_NEXT_BIT=y # CONFIG_ARCH_NO_VIRT_TO_BUS is not set CONFIG_PPC=y @@ -52,12 +56,14 @@ CONFIG_OF=y # CONFIG_GENERIC_TBSYNC is not set CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y +CONFIG_DTC=y CONFIG_DEFAULT_UIMAGE=y CONFIG_ARCH_SUSPEND_POSSIBLE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -78,11 +84,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -106,7 +113,6 @@ CONFIG_ANON_INODES=y CONFIG_EMBEDDED=y # CONFIG_SYSCTL_SYSCALL is not set # CONFIG_KALLSYMS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -119,6 +125,13 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +# CONFIG_PERF_EVENTS is not set +# CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y @@ -127,14 +140,19 @@ CONFIG_COMPAT_BRK=y CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# # CONFIG_SLOW_WORK is not set # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y @@ -147,7 +165,7 @@ CONFIG_MODULE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -228,11 +246,13 @@ CONFIG_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set # CONFIG_IOMMU_HELPER is not set +# CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -248,9 +268,10 @@ CONFIG_MIGRATION=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set # CONFIG_PPC_64K_PAGES is not set @@ -264,6 +285,7 @@ CONFIG_PM=y CONFIG_PM_SLEEP=y CONFIG_SUSPEND=y CONFIG_SUSPEND_FREEZER=y +# CONFIG_PM_RUNTIME is not set CONFIG_SECCOMP=y CONFIG_ISA_DMA_API=y @@ -348,6 +370,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -362,6 +385,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -387,6 +411,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -397,6 +422,7 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_MTD is not set CONFIG_OF_DEVICE=y CONFIG_OF_I2C=y +CONFIG_OF_MDIO=y # CONFIG_PARPORT is not set CONFIG_BLK_DEV=y # CONFIG_BLK_DEV_FD is not set @@ -431,7 +457,9 @@ CONFIG_MISC_DEVICES=y # # CONFIG_EEPROM_AT24 is not set # CONFIG_EEPROM_LEGACY is not set +# CONFIG_EEPROM_MAX6875 is not set # CONFIG_EEPROM_93CX6 is not set +# CONFIG_CB710_CORE is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -454,10 +482,6 @@ CONFIG_BLK_DEV_SD=y # CONFIG_BLK_DEV_SR is not set # CONFIG_CHR_DEV_SG is not set # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -475,6 +499,8 @@ CONFIG_SCSI_WAIT_SCAN=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set +# CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -483,6 +509,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_AIC7XXX_OLD is not set # CONFIG_SCSI_AIC79XX is not set # CONFIG_SCSI_AIC94XX is not set +# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_DPT_I2O is not set # CONFIG_SCSI_ADVANSYS is not set # CONFIG_SCSI_ARCMSR is not set @@ -502,7 +529,6 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_IPS is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set -# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_STEX is not set # CONFIG_SCSI_SYM53C8XX_2 is not set # CONFIG_SCSI_IPR is not set @@ -514,11 +540,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -540,6 +569,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -568,6 +598,7 @@ CONFIG_PATA_MPC52xx=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -586,14 +617,17 @@ CONFIG_PATA_MPC52xx=y # # -# Enable only one of the two stacks, unless you know what you are doing +# You can enable one or both FireWire driver stacks. +# + +# +# See the help texts for more information. # # CONFIG_FIREWIRE is not set # CONFIG_IEEE1394 is not set # CONFIG_I2O is not set # CONFIG_MACINTOSH_DRIVERS is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -640,9 +674,12 @@ CONFIG_NET_ETHERNET=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_NET_PCI is not set # CONFIG_B44 is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set CONFIG_FEC_MPC52xx=y CONFIG_FEC_MPC52xx_MDIO=y # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -661,6 +698,8 @@ CONFIG_NETDEV_1000=y # CONFIG_VIA_VELOCITY is not set # CONFIG_TIGON3 is not set # CONFIG_BNX2 is not set +# CONFIG_CNIC is not set +# CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set # CONFIG_ATL1 is not set # CONFIG_ATL1E is not set @@ -686,10 +725,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -759,6 +795,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -787,6 +824,7 @@ CONFIG_I2C_HELPER_AUTO=y # # I2C system bus drivers (mostly embedded / system-on-chip) # +# CONFIG_I2C_DESIGNWARE is not set CONFIG_I2C_MPC=y # CONFIG_I2C_OCORES is not set # CONFIG_I2C_SIMTEC is not set @@ -812,23 +850,23 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set # CONFIG_I2C_DEBUG_CHIP is not set # CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -847,30 +885,18 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_AB3100_CORE is not set # CONFIG_REGULATOR is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -# CONFIG_DAB is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -913,6 +939,10 @@ CONFIG_USB_ARCH_HAS_EHCI=y # CONFIG_DMADEVICES is not set # CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -932,10 +962,13 @@ CONFIG_FS_MBCACHE=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -992,12 +1025,12 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y # CONFIG_NFS_V3_ACL is not set CONFIG_NFS_V4=y +# CONFIG_NFS_V4_1 is not set CONFIG_ROOT_NFS=y # CONFIG_NFSD is not set CONFIG_LOCKD=y @@ -1041,6 +1074,7 @@ CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y CONFIG_NLATTR=y +CONFIG_GENERIC_ATOMIC64=y # # Kernel hacking @@ -1050,6 +1084,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1067,10 +1102,14 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set +# CONFIG_DEBUG_LOCK_ALLOC is not set +# CONFIG_PROVE_LOCKING is not set +# CONFIG_LOCK_STAT is not set # CONFIG_DEBUG_SPINLOCK_SLEEP is not set # CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set # CONFIG_DEBUG_KOBJECT is not set @@ -1082,11 +1121,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set -# CONFIG_BOOT_PRINTK_DELAY is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -1095,23 +1135,25 @@ CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# +CONFIG_FTRACE=y # CONFIG_FUNCTION_TRACER is not set +# CONFIG_IRQSOFF_TRACER is not set # CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set +# CONFIG_ENABLE_DEFAULT_TRACERS is not set # CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set +CONFIG_BRANCH_PROFILE_NONE=y +# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set +# CONFIG_PROFILE_ALL_BRANCHES is not set # CONFIG_STACK_TRACER is not set # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_DEBUG_STACKOVERFLOW is not set # CONFIG_DEBUG_STACK_USAGE is not set @@ -1136,7 +1178,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1178,11 +1219,13 @@ CONFIG_CRYPTO_CBC=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/52xx/motionpro_defconfig b/arch/powerpc/configs/52xx/motionpro_defconfig index 07b6b266ea95..4f77a1bdc8f9 100644 --- a/arch/powerpc/configs/52xx/motionpro_defconfig +++ b/arch/powerpc/configs/52xx/motionpro_defconfig @@ -1,25 +1,27 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc2 -# Sat Apr 18 00:48:22 2009 +# Linux kernel version: 2.6.32-rc4 +# Thu Oct 15 10:33:22 2009 # # CONFIG_PPC64 is not set # # Processor support # -CONFIG_6xx=y +CONFIG_PPC_BOOK3S_32=y # CONFIG_PPC_85xx is not set # CONFIG_PPC_8xx is not set # CONFIG_40x is not set # CONFIG_44x is not set # CONFIG_E200 is not set CONFIG_PPC_BOOK3S=y +CONFIG_6xx=y CONFIG_PPC_FPU=y # CONFIG_ALTIVEC is not set CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set +CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set CONFIG_PPC32=y CONFIG_WORD_SIZE=32 @@ -30,15 +32,17 @@ CONFIG_GENERIC_TIME=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y +CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_GENERIC_HWEIGHT=y -CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_FIND_NEXT_BIT=y # CONFIG_ARCH_NO_VIRT_TO_BUS is not set CONFIG_PPC=y @@ -52,11 +56,13 @@ CONFIG_OF=y # CONFIG_GENERIC_TBSYNC is not set CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y +CONFIG_DTC=y CONFIG_DEFAULT_UIMAGE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -77,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -105,7 +112,6 @@ CONFIG_ANON_INODES=y CONFIG_EMBEDDED=y # CONFIG_SYSCTL_SYSCALL is not set # CONFIG_KALLSYMS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -118,6 +124,13 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +# CONFIG_PERF_EVENTS is not set +# CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_SLUB_DEBUG=y CONFIG_COMPAT_BRK=y @@ -125,14 +138,19 @@ CONFIG_COMPAT_BRK=y CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# # CONFIG_SLOW_WORK is not set # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y @@ -140,7 +158,7 @@ CONFIG_RT_MUTEXES=y CONFIG_BASE_SMALL=0 # CONFIG_MODULES is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -220,11 +238,13 @@ CONFIG_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set # CONFIG_IOMMU_HELPER is not set +# CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -240,9 +260,10 @@ CONFIG_MIGRATION=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set # CONFIG_PPC_64K_PAGES is not set @@ -253,6 +274,7 @@ CONFIG_PROC_DEVICETREE=y CONFIG_EXTRA_TARGETS="" CONFIG_PM=y # CONFIG_PM_DEBUG is not set +# CONFIG_PM_RUNTIME is not set CONFIG_SECCOMP=y CONFIG_ISA_DMA_API=y @@ -329,6 +351,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -343,6 +366,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -368,6 +392,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -458,6 +483,7 @@ CONFIG_MTD_ROM=y # CONFIG_MTD_UBI is not set CONFIG_OF_DEVICE=y CONFIG_OF_I2C=y +CONFIG_OF_MDIO=y # CONFIG_PARPORT is not set CONFIG_BLK_DEV=y # CONFIG_BLK_DEV_FD is not set @@ -483,6 +509,7 @@ CONFIG_MISC_DEVICES=y # # CONFIG_EEPROM_AT24 is not set CONFIG_EEPROM_LEGACY=y +# CONFIG_EEPROM_MAX6875 is not set # CONFIG_EEPROM_93CX6 is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -506,10 +533,6 @@ CONFIG_BLK_DEV_SD=y # CONFIG_BLK_DEV_SR is not set CONFIG_CHR_DEV_SG=y # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -532,6 +555,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_ATA_SFF=y # CONFIG_SATA_MV is not set @@ -540,7 +564,6 @@ CONFIG_PATA_MPC52xx=y # CONFIG_MD is not set # CONFIG_MACINTOSH_DRIVERS is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -579,14 +602,14 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_CLR_ICINTSTAT is not set # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set CONFIG_FEC_MPC52xx=y CONFIG_FEC_MPC52xx_MDIO=y +# CONFIG_XILINX_EMACLITE is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -647,6 +670,7 @@ CONFIG_LEGACY_PTY_COUNT=256 # CONFIG_TCG_TPM is not set CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -657,6 +681,7 @@ CONFIG_I2C_HELPER_AUTO=y # # I2C system bus drivers (mostly embedded / system-on-chip) # +# CONFIG_I2C_DESIGNWARE is not set CONFIG_I2C_MPC=y # CONFIG_I2C_OCORES is not set # CONFIG_I2C_SIMTEC is not set @@ -676,22 +701,28 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set # CONFIG_I2C_DEBUG_CHIP is not set # CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -738,6 +769,8 @@ CONFIG_HWMON=y # CONFIG_SENSORS_SMSC47B397 is not set # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set +# CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_W83781D is not set # CONFIG_SENSORS_W83791D is not set @@ -747,9 +780,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -775,25 +806,12 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_AB3100_CORE is not set # CONFIG_REGULATOR is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -CONFIG_DAB=y +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support @@ -817,7 +835,7 @@ CONFIG_LEDS_CLASS=y # # LED drivers # -# CONFIG_LEDS_LP5521 is not set +# CONFIG_LEDS_LP3944 is not set # CONFIG_LEDS_PCA955X is not set # CONFIG_LEDS_BD2802 is not set @@ -866,6 +884,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_S35390A is not set # CONFIG_RTC_DRV_FM3130 is not set # CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set # # SPI RTC drivers @@ -893,6 +912,10 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_DMADEVICES is not set # CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -912,10 +935,13 @@ CONFIG_FS_MBCACHE=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -986,12 +1012,12 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y # CONFIG_NFS_V3_ACL is not set CONFIG_NFS_V4=y +# CONFIG_NFS_V4_1 is not set CONFIG_ROOT_NFS=y # CONFIG_NFSD is not set CONFIG_LOCKD=y @@ -1091,6 +1117,7 @@ CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y CONFIG_NLATTR=y +CONFIG_GENERIC_ATOMIC64=y # # Kernel hacking @@ -1100,6 +1127,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1117,10 +1145,14 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set +# CONFIG_DEBUG_LOCK_ALLOC is not set +# CONFIG_PROVE_LOCKING is not set +# CONFIG_LOCK_STAT is not set # CONFIG_DEBUG_SPINLOCK_SLEEP is not set # CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set # CONFIG_DEBUG_KOBJECT is not set @@ -1132,11 +1164,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set -# CONFIG_BOOT_PRINTK_DELAY is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -1145,23 +1178,25 @@ CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# +CONFIG_FTRACE=y # CONFIG_FUNCTION_TRACER is not set +# CONFIG_IRQSOFF_TRACER is not set # CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set +# CONFIG_ENABLE_DEFAULT_TRACERS is not set # CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set +CONFIG_BRANCH_PROFILE_NONE=y +# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set +# CONFIG_PROFILE_ALL_BRANCHES is not set # CONFIG_STACK_TRACER is not set # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_DEBUG_STACKOVERFLOW is not set # CONFIG_DEBUG_STACK_USAGE is not set @@ -1186,7 +1221,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1227,11 +1261,13 @@ CONFIG_CRYPTO_PCBC=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/52xx/pcm030_defconfig b/arch/powerpc/configs/52xx/pcm030_defconfig index afb1a3d1ef0a..f9168c1a2fa5 100644 --- a/arch/powerpc/configs/52xx/pcm030_defconfig +++ b/arch/powerpc/configs/52xx/pcm030_defconfig @@ -1,25 +1,27 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc2 -# Sat Apr 18 00:48:42 2009 +# Linux kernel version: 2.6.32-rc4 +# Thu Oct 15 10:33:25 2009 # # CONFIG_PPC64 is not set # # Processor support # -CONFIG_6xx=y +CONFIG_PPC_BOOK3S_32=y # CONFIG_PPC_85xx is not set # CONFIG_PPC_8xx is not set # CONFIG_40x is not set # CONFIG_44x is not set # CONFIG_E200 is not set CONFIG_PPC_BOOK3S=y +CONFIG_6xx=y CONFIG_PPC_FPU=y # CONFIG_ALTIVEC is not set CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set +CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set CONFIG_PPC32=y CONFIG_WORD_SIZE=32 @@ -30,15 +32,17 @@ CONFIG_GENERIC_TIME=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y +CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_GENERIC_HWEIGHT=y -CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_FIND_NEXT_BIT=y # CONFIG_ARCH_NO_VIRT_TO_BUS is not set CONFIG_PPC=y @@ -52,11 +56,13 @@ CONFIG_OF=y # CONFIG_GENERIC_TBSYNC is not set CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y +CONFIG_DTC=y CONFIG_DEFAULT_UIMAGE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -79,11 +85,12 @@ CONFIG_POSIX_MQUEUE_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -105,7 +112,6 @@ CONFIG_EMBEDDED=y # CONFIG_SYSCTL_SYSCALL is not set CONFIG_KALLSYMS=y # CONFIG_KALLSYMS_EXTRA_PASS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -118,6 +124,13 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +# CONFIG_PERF_EVENTS is not set +# CONFIG_PERF_COUNTERS is not set # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_PCI_QUIRKS=y CONFIG_COMPAT_BRK=y @@ -125,7 +138,6 @@ CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -133,7 +145,13 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# # CONFIG_SLOW_WORK is not set # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y @@ -146,7 +164,7 @@ CONFIG_MODULE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -227,11 +245,13 @@ CONFIG_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set # CONFIG_IOMMU_HELPER is not set +# CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -247,9 +267,10 @@ CONFIG_MIGRATION=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set # CONFIG_PPC_64K_PAGES is not set @@ -336,6 +357,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -350,6 +372,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -375,6 +398,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -382,9 +406,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_OF_PARTS is not set @@ -467,6 +491,7 @@ CONFIG_MTD_PHYSMAP=y # CONFIG_MTD_UBI is not set CONFIG_OF_DEVICE=y CONFIG_OF_I2C=y +CONFIG_OF_MDIO=y # CONFIG_PARPORT is not set # CONFIG_BLK_DEV is not set # CONFIG_MISC_DEVICES is not set @@ -492,10 +517,6 @@ CONFIG_BLK_DEV_SD=m # CONFIG_BLK_DEV_SR is not set # CONFIG_CHR_DEV_SG is not set # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -515,6 +536,7 @@ CONFIG_SCSI_WAIT_SCAN=m # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=m # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -536,6 +558,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -564,6 +587,7 @@ CONFIG_PATA_MPC52xx=m # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -582,14 +606,17 @@ CONFIG_PATA_MPC52xx=m # # -# Enable only one of the two stacks, unless you know what you are doing +# You can enable one or both FireWire driver stacks. +# + +# +# See the help texts for more information. # # CONFIG_FIREWIRE is not set # CONFIG_IEEE1394 is not set # CONFIG_I2O is not set # CONFIG_MACINTOSH_DRIVERS is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -636,16 +663,16 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_NET_PCI is not set # CONFIG_B44 is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set CONFIG_FEC_MPC52xx=y CONFIG_FEC_MPC52xx_MDIO=y # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -722,6 +749,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -750,6 +778,7 @@ CONFIG_I2C_HELPER_AUTO=y # # I2C system bus drivers (mostly embedded / system-on-chip) # +# CONFIG_I2C_DESIGNWARE is not set CONFIG_I2C_MPC=y # CONFIG_I2C_OCORES is not set # CONFIG_I2C_SIMTEC is not set @@ -776,23 +805,23 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set # CONFIG_I2C_DEBUG_CHIP is not set # CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -811,30 +840,18 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_AB3100_CORE is not set # CONFIG_REGULATOR is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -# CONFIG_DAB is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -871,15 +888,17 @@ CONFIG_USB_DEVICEFS=y # USB Host Controller Drivers # # CONFIG_USB_C67X00_HCD is not set +# CONFIG_USB_XHCI_HCD is not set # CONFIG_USB_EHCI_HCD is not set # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=m # CONFIG_USB_OHCI_HCD_PPC_SOC is not set -CONFIG_USB_OHCI_HCD_PPC_OF=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set +CONFIG_USB_OHCI_HCD_PPC_OF=y # CONFIG_USB_OHCI_HCD_PCI is not set CONFIG_USB_OHCI_BIG_ENDIAN_DESC=y CONFIG_USB_OHCI_BIG_ENDIAN_MMIO=y @@ -995,6 +1014,7 @@ CONFIG_RTC_DRV_PCF8563=m # CONFIG_RTC_DRV_S35390A is not set # CONFIG_RTC_DRV_FM3130 is not set # CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set # # SPI RTC drivers @@ -1022,6 +1042,10 @@ CONFIG_RTC_DRV_PCF8563=m # CONFIG_DMADEVICES is not set # CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -1041,12 +1065,16 @@ CONFIG_FS_MBCACHE=m # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY is not set +CONFIG_INOTIFY_USER=y # CONFIG_QUOTA is not set # CONFIG_AUTOFS_FS is not set # CONFIG_AUTOFS4_FS is not set @@ -1114,7 +1142,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1201,6 +1228,7 @@ CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y CONFIG_NLATTR=y +CONFIG_GENERIC_ATOMIC64=y # # Kernel hacking @@ -1210,6 +1238,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1223,23 +1252,12 @@ CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# -# CONFIG_FUNCTION_TRACER is not set -# CONFIG_PREEMPT_TRACER is not set -# CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set -# CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set -# CONFIG_STACK_TRACER is not set -# CONFIG_KMEMTRACE is not set -# CONFIG_WORKQUEUE_TRACER is not set -# CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_IRQSTACKS is not set # CONFIG_BOOTX_TEXT is not set diff --git a/arch/powerpc/configs/52xx/tqm5200_defconfig b/arch/powerpc/configs/52xx/tqm5200_defconfig index 8585c7c12861..75c835c2ae66 100644 --- a/arch/powerpc/configs/52xx/tqm5200_defconfig +++ b/arch/powerpc/configs/52xx/tqm5200_defconfig @@ -1,25 +1,27 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc2 -# Sat Apr 18 00:48:57 2009 +# Linux kernel version: 2.6.32-rc4 +# Thu Oct 15 10:33:23 2009 # # CONFIG_PPC64 is not set # # Processor support # -CONFIG_6xx=y +CONFIG_PPC_BOOK3S_32=y # CONFIG_PPC_85xx is not set # CONFIG_PPC_8xx is not set # CONFIG_40x is not set # CONFIG_44x is not set # CONFIG_E200 is not set CONFIG_PPC_BOOK3S=y +CONFIG_6xx=y CONFIG_PPC_FPU=y # CONFIG_ALTIVEC is not set CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set +CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set CONFIG_PPC32=y CONFIG_WORD_SIZE=32 @@ -30,15 +32,17 @@ CONFIG_GENERIC_TIME=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y +CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_GENERIC_HWEIGHT=y -CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_FIND_NEXT_BIT=y # CONFIG_ARCH_NO_VIRT_TO_BUS is not set CONFIG_PPC=y @@ -52,11 +56,13 @@ CONFIG_OF=y # CONFIG_GENERIC_TBSYNC is not set CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y +CONFIG_DTC=y CONFIG_DEFAULT_UIMAGE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -77,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -105,7 +112,6 @@ CONFIG_ANON_INODES=y CONFIG_EMBEDDED=y # CONFIG_SYSCTL_SYSCALL is not set # CONFIG_KALLSYMS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -118,6 +124,13 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +# CONFIG_PERF_EVENTS is not set +# CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_SLUB_DEBUG=y CONFIG_COMPAT_BRK=y @@ -125,14 +138,19 @@ CONFIG_COMPAT_BRK=y CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# # CONFIG_SLOW_WORK is not set # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y @@ -145,7 +163,7 @@ CONFIG_MODULE_UNLOAD=y CONFIG_MODVERSIONS=y # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -225,11 +243,13 @@ CONFIG_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set # CONFIG_IOMMU_HELPER is not set +# CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -245,9 +265,10 @@ CONFIG_MIGRATION=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set # CONFIG_PPC_64K_PAGES is not set @@ -258,6 +279,7 @@ CONFIG_PROC_DEVICETREE=y CONFIG_EXTRA_TARGETS="" CONFIG_PM=y # CONFIG_PM_DEBUG is not set +# CONFIG_PM_RUNTIME is not set CONFIG_SECCOMP=y CONFIG_ISA_DMA_API=y @@ -334,6 +356,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -348,6 +371,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -373,6 +397,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -382,9 +407,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_OF_PARTS is not set @@ -464,6 +489,7 @@ CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_UBI is not set CONFIG_OF_DEVICE=y CONFIG_OF_I2C=y +CONFIG_OF_MDIO=y # CONFIG_PARPORT is not set CONFIG_BLK_DEV=y # CONFIG_BLK_DEV_FD is not set @@ -502,10 +528,6 @@ CONFIG_BLK_DEV_SD=y # CONFIG_BLK_DEV_SR is not set CONFIG_CHR_DEV_SG=y # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -529,6 +551,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_ATA_SFF=y # CONFIG_SATA_MV is not set @@ -538,7 +561,6 @@ CONFIG_PATA_PLATFORM=y # CONFIG_MD is not set # CONFIG_MACINTOSH_DRIVERS is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -577,14 +599,14 @@ CONFIG_NET_ETHERNET=y # CONFIG_IBM_NEW_EMAC_MAL_CLR_ICINTSTAT is not set # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set CONFIG_FEC_MPC52xx=y CONFIG_FEC_MPC52xx_MDIO=y +# CONFIG_XILINX_EMACLITE is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -654,6 +676,7 @@ CONFIG_LEGACY_PTY_COUNT=256 # CONFIG_TCG_TPM is not set CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -664,6 +687,7 @@ CONFIG_I2C_HELPER_AUTO=y # # I2C system bus drivers (mostly embedded / system-on-chip) # +# CONFIG_I2C_DESIGNWARE is not set CONFIG_I2C_MPC=y # CONFIG_I2C_OCORES is not set # CONFIG_I2C_SIMTEC is not set @@ -685,22 +709,28 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set # CONFIG_I2C_DEBUG_CHIP is not set # CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -747,6 +777,8 @@ CONFIG_HWMON=y # CONFIG_SENSORS_SMSC47B397 is not set # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set +# CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_W83781D is not set # CONFIG_SENSORS_W83791D is not set @@ -756,9 +788,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -789,25 +819,12 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_AB3100_CORE is not set # CONFIG_REGULATOR is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -# CONFIG_DAB is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support @@ -851,11 +868,12 @@ CONFIG_USB_MON=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_SOC=y -CONFIG_USB_OHCI_HCD_PPC_OF=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set +CONFIG_USB_OHCI_HCD_PPC_OF=y CONFIG_USB_OHCI_BIG_ENDIAN_DESC=y CONFIG_USB_OHCI_BIG_ENDIAN_MMIO=y # CONFIG_USB_OHCI_LITTLE_ENDIAN is not set @@ -969,6 +987,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_S35390A is not set # CONFIG_RTC_DRV_FM3130 is not set # CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set # # SPI RTC drivers @@ -996,6 +1015,10 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_DMADEVICES is not set # CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -1015,10 +1038,13 @@ CONFIG_FS_MBCACHE=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -1089,12 +1115,12 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y # CONFIG_NFS_V3_ACL is not set CONFIG_NFS_V4=y +# CONFIG_NFS_V4_1 is not set CONFIG_ROOT_NFS=y # CONFIG_NFSD is not set CONFIG_LOCKD=y @@ -1194,6 +1220,7 @@ CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y CONFIG_NLATTR=y +CONFIG_GENERIC_ATOMIC64=y # # Kernel hacking @@ -1203,6 +1230,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1220,10 +1248,14 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set +# CONFIG_DEBUG_LOCK_ALLOC is not set +# CONFIG_PROVE_LOCKING is not set +# CONFIG_LOCK_STAT is not set # CONFIG_DEBUG_SPINLOCK_SLEEP is not set # CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set # CONFIG_DEBUG_KOBJECT is not set @@ -1235,11 +1267,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set -# CONFIG_BOOT_PRINTK_DELAY is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -1248,23 +1281,25 @@ CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# +CONFIG_FTRACE=y # CONFIG_FUNCTION_TRACER is not set +# CONFIG_IRQSOFF_TRACER is not set # CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set +# CONFIG_ENABLE_DEFAULT_TRACERS is not set # CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set +CONFIG_BRANCH_PROFILE_NONE=y +# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set +# CONFIG_PROFILE_ALL_BRANCHES is not set # CONFIG_STACK_TRACER is not set # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_DEBUG_STACKOVERFLOW is not set # CONFIG_DEBUG_STACK_USAGE is not set @@ -1289,7 +1324,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1331,11 +1365,13 @@ CONFIG_CRYPTO_PCBC=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/asp8347_defconfig b/arch/powerpc/configs/83xx/asp8347_defconfig index a2df0635b6de..466f09ac3153 100644 --- a/arch/powerpc/configs/83xx/asp8347_defconfig +++ b/arch/powerpc/configs/83xx/asp8347_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:02 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:20 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,28 +127,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -257,6 +260,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -274,6 +278,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -369,6 +374,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -398,6 +404,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -405,7 +412,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -418,6 +424,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -425,9 +432,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set CONFIG_MTD_REDBOOT_PARTS=y CONFIG_MTD_REDBOOT_DIRECTORY_BLOCK=-1 CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED=y @@ -628,7 +635,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -658,10 +667,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -760,6 +766,7 @@ CONFIG_LEGACY_PTY_COUNT=256 CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -814,9 +821,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -834,6 +838,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -883,6 +892,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -894,7 +904,6 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set CONFIG_THERMAL=y # CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y @@ -934,6 +943,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -944,6 +954,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -990,6 +1001,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set # CONFIG_USB_UHCI_HCD is not set # CONFIG_USB_SL811_HCD is not set @@ -1045,6 +1057,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_LD is not set # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set @@ -1146,6 +1159,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1215,7 +1229,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1327,6 +1340,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1344,6 +1358,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1365,7 +1380,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1407,11 +1421,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/kmeter1_defconfig b/arch/powerpc/configs/83xx/kmeter1_defconfig index 93ebd443a18f..6694fb73cd99 100644 --- a/arch/powerpc/configs/83xx/kmeter1_defconfig +++ b/arch/powerpc/configs/83xx/kmeter1_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:03 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:21 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -86,11 +87,12 @@ CONFIG_POSIX_MQUEUE_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 # CONFIG_GROUP_SCHED is not set @@ -119,20 +121,19 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -140,6 +141,8 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -250,6 +253,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -267,6 +271,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -348,6 +353,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set CONFIG_STP=m @@ -396,9 +402,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y CONFIG_MTD_OF_PARTS=y @@ -565,18 +571,16 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y # CONFIG_GIANFAR is not set CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -663,6 +667,7 @@ CONFIG_HW_RANDOM=y # CONFIG_TCG_TPM is not set CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -693,9 +698,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -713,7 +715,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -732,6 +733,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -784,6 +786,7 @@ CONFIG_UIO=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set @@ -854,7 +857,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -926,6 +928,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -942,6 +945,7 @@ CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set diff --git a/arch/powerpc/configs/83xx/mpc8313_rdb_defconfig b/arch/powerpc/configs/83xx/mpc8313_rdb_defconfig index ff33a7db2eab..86df19f041a4 100644 --- a/arch/powerpc/configs/83xx/mpc8313_rdb_defconfig +++ b/arch/powerpc/configs/83xx/mpc8313_rdb_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:04 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:22 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -256,6 +259,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -369,6 +374,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -398,6 +404,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -405,7 +412,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -418,6 +424,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -427,9 +434,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set CONFIG_MTD_OF_PARTS=y @@ -488,6 +495,7 @@ CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_PMC551 is not set # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -605,6 +613,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -643,7 +652,9 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -741,9 +752,11 @@ CONFIG_E100=y # CONFIG_TLAN is not set # CONFIG_KS8842 is not set # CONFIG_KS8851 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -791,10 +804,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -896,6 +906,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -950,9 +961,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -984,6 +992,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADCXX is not set @@ -1036,6 +1049,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1048,9 +1062,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set # CONFIG_SENSORS_LIS3_SPI is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1088,8 +1100,10 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set # CONFIG_AB3100_CORE is not set # CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set @@ -1099,6 +1113,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1112,7 +1127,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1164,6 +1178,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1255,6 +1270,7 @@ CONFIG_USB_GADGET_SELECTED=y # CONFIG_USB_GADGET_LH7A40X is not set # CONFIG_USB_GADGET_OMAP is not set # CONFIG_USB_GADGET_PXA25X is not set +# CONFIG_USB_GADGET_R8A66597 is not set # CONFIG_USB_GADGET_PXA27X is not set # CONFIG_USB_GADGET_S3C_HSOTG is not set # CONFIG_USB_GADGET_IMX is not set @@ -1273,6 +1289,7 @@ CONFIG_USB_GADGET_DUALSPEED=y # CONFIG_USB_AUDIO is not set CONFIG_USB_ETH=y CONFIG_USB_ETH_RNDIS=y +# CONFIG_USB_ETH_EEM is not set # CONFIG_USB_GADGETFS is not set # CONFIG_USB_FILE_STORAGE is not set # CONFIG_USB_G_SERIAL is not set @@ -1334,6 +1351,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -1384,6 +1402,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1453,7 +1472,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1569,6 +1587,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1586,6 +1605,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1604,10 +1624,12 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1630,10 +1652,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1660,7 +1682,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1702,11 +1723,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc8315_rdb_defconfig b/arch/powerpc/configs/83xx/mpc8315_rdb_defconfig index 76237d466702..7bf71d577033 100644 --- a/arch/powerpc/configs/83xx/mpc8315_rdb_defconfig +++ b/arch/powerpc/configs/83xx/mpc8315_rdb_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:05 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:23 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -256,6 +259,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -369,6 +374,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -398,6 +404,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -405,7 +412,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -418,6 +424,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -427,9 +434,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set # CONFIG_MTD_OF_PARTS is not set @@ -488,6 +495,7 @@ CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_PMC551 is not set # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -605,6 +613,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -644,11 +653,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -671,6 +683,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -698,6 +711,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -802,9 +816,11 @@ CONFIG_E100=y # CONFIG_TLAN is not set # CONFIG_KS8842 is not set # CONFIG_KS8851 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -852,10 +868,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -957,6 +970,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1011,9 +1025,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1045,6 +1056,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADCXX is not set @@ -1097,6 +1113,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1109,9 +1126,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set # CONFIG_SENSORS_LIS3_SPI is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1149,8 +1164,10 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set # CONFIG_AB3100_CORE is not set # CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set @@ -1160,6 +1177,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1173,7 +1191,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1225,6 +1242,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1316,6 +1334,7 @@ CONFIG_USB_GADGET_SELECTED=y # CONFIG_USB_GADGET_LH7A40X is not set # CONFIG_USB_GADGET_OMAP is not set # CONFIG_USB_GADGET_PXA25X is not set +# CONFIG_USB_GADGET_R8A66597 is not set # CONFIG_USB_GADGET_PXA27X is not set # CONFIG_USB_GADGET_S3C_HSOTG is not set # CONFIG_USB_GADGET_IMX is not set @@ -1334,6 +1353,7 @@ CONFIG_USB_GADGET_DUALSPEED=y # CONFIG_USB_AUDIO is not set CONFIG_USB_ETH=y CONFIG_USB_ETH_RNDIS=y +# CONFIG_USB_ETH_EEM is not set # CONFIG_USB_GADGETFS is not set # CONFIG_USB_FILE_STORAGE is not set # CONFIG_USB_G_SERIAL is not set @@ -1395,6 +1415,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -1445,6 +1466,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1514,7 +1536,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1630,6 +1651,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1647,6 +1669,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1665,10 +1688,12 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1691,10 +1716,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1721,7 +1746,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1763,11 +1787,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc832x_mds_defconfig b/arch/powerpc/configs/83xx/mpc832x_mds_defconfig index e0e36a113409..7def83518a6c 100644 --- a/arch/powerpc/configs/83xx/mpc832x_mds_defconfig +++ b/arch/powerpc/configs/83xx/mpc832x_mds_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:06 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:24 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -257,6 +260,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -274,6 +278,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -369,6 +374,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -398,6 +404,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -405,7 +412,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -418,6 +424,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -504,6 +511,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -542,7 +550,9 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -612,7 +622,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -635,7 +647,6 @@ CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y # CONFIG_GIANFAR is not set CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set @@ -663,10 +674,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -759,6 +767,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -812,9 +821,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -832,6 +838,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -881,6 +892,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -892,9 +904,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -927,6 +937,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -937,6 +948,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -950,7 +962,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1070,6 +1081,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1128,7 +1140,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1202,6 +1213,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1219,6 +1231,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1240,7 +1253,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1282,11 +1294,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc832x_rdb_defconfig b/arch/powerpc/configs/83xx/mpc832x_rdb_defconfig index 4f27d4548223..b398b9b2b635 100644 --- a/arch/powerpc/configs/83xx/mpc832x_rdb_defconfig +++ b/arch/powerpc/configs/83xx/mpc832x_rdb_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:07 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:24 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -257,6 +260,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -274,6 +278,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -369,6 +374,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -398,6 +404,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -405,7 +412,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -418,6 +424,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -507,6 +514,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -545,7 +553,9 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -617,7 +627,9 @@ CONFIG_MII=y # CONFIG_B44 is not set # CONFIG_KS8842 is not set # CONFIG_KS8851 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -640,7 +652,6 @@ CONFIG_E1000=y CONFIG_FSL_PQ_MDIO=y # CONFIG_GIANFAR is not set CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set @@ -668,10 +679,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -776,6 +784,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -830,9 +839,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -863,6 +869,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADCXX is not set @@ -915,6 +926,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -927,9 +939,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set # CONFIG_SENSORS_LIS3_SPI is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -967,8 +977,10 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set # CONFIG_AB3100_CORE is not set # CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set @@ -978,6 +990,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -991,7 +1004,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1043,6 +1055,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1146,6 +1159,8 @@ CONFIG_MMC_BLOCK_BOUNCE=y # # CONFIG_MMC_SDHCI is not set # CONFIG_MMC_WBSD is not set +# CONFIG_MMC_AT91 is not set +# CONFIG_MMC_ATMELMCI is not set # CONFIG_MMC_TIFM_SD is not set CONFIG_MMC_SPI=y # CONFIG_MMC_CB710 is not set @@ -1186,6 +1201,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1247,7 +1263,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1365,6 +1380,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1382,6 +1398,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1403,7 +1420,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1445,11 +1461,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc834x_itx_defconfig b/arch/powerpc/configs/83xx/mpc834x_itx_defconfig index 648dac0c9d8d..f67317e1934c 100644 --- a/arch/powerpc/configs/83xx/mpc834x_itx_defconfig +++ b/arch/powerpc/configs/83xx/mpc834x_itx_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:07 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:25 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -256,6 +259,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -368,6 +373,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -397,6 +403,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -404,7 +411,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -417,6 +423,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -424,9 +431,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set # CONFIG_MTD_PARTITIONS is not set -# CONFIG_MTD_TESTS is not set # # User Modules And Translation Layers @@ -483,6 +490,7 @@ CONFIG_MTD_PHYSMAP=y # CONFIG_MTD_PMC551 is not set # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -637,6 +645,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -676,11 +685,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -703,6 +715,7 @@ CONFIG_SATA_SIL=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -730,6 +743,7 @@ CONFIG_SATA_SIL=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -845,10 +859,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -930,6 +941,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -984,9 +996,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -CONFIG_SENSORS_PCF8574=y -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1017,7 +1026,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1055,8 +1063,10 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set # CONFIG_AB3100_CORE is not set # CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set @@ -1066,6 +1076,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1111,6 +1122,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set CONFIG_USB_UHCI_HCD=y # CONFIG_USB_SL811_HCD is not set @@ -1238,6 +1250,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -1288,6 +1301,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1350,7 +1364,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1465,6 +1478,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1482,6 +1496,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1503,7 +1518,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1545,11 +1559,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc834x_itxgp_defconfig b/arch/powerpc/configs/83xx/mpc834x_itxgp_defconfig index bf6deb831dc3..a668110c10f6 100644 --- a/arch/powerpc/configs/83xx/mpc834x_itxgp_defconfig +++ b/arch/powerpc/configs/83xx/mpc834x_itxgp_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:08 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:26 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -256,6 +259,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -368,6 +373,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -397,6 +403,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -404,7 +411,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -417,6 +423,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -424,9 +431,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set # CONFIG_MTD_PARTITIONS is not set -# CONFIG_MTD_TESTS is not set # # User Modules And Translation Layers @@ -483,6 +490,7 @@ CONFIG_MTD_PHYSMAP=y # CONFIG_MTD_PMC551 is not set # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -589,6 +597,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -627,7 +636,9 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -725,10 +736,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -810,6 +818,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -864,9 +873,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -CONFIG_SENSORS_PCF8574=y -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -897,7 +903,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -935,8 +940,10 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set # CONFIG_AB3100_CORE is not set # CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set @@ -946,6 +953,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -991,6 +999,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set CONFIG_USB_UHCI_HCD=y # CONFIG_USB_SL811_HCD is not set @@ -1059,6 +1068,7 @@ CONFIG_USB_STORAGE=y # CONFIG_USB_LD is not set # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set @@ -1117,6 +1127,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -1167,6 +1178,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1229,7 +1241,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1344,6 +1355,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1361,6 +1373,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1382,7 +1395,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1424,11 +1436,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc834x_mds_defconfig b/arch/powerpc/configs/83xx/mpc834x_mds_defconfig index 3236c47712c2..c4e92ba5c38b 100644 --- a/arch/powerpc/configs/83xx/mpc834x_mds_defconfig +++ b/arch/powerpc/configs/83xx/mpc834x_mds_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:09 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:27 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -256,6 +259,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -368,6 +373,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -397,6 +403,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -404,7 +411,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -417,6 +423,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -556,9 +563,11 @@ CONFIG_E100=y # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -606,10 +615,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -699,6 +705,7 @@ CONFIG_LEGACY_PTY_COUNT=256 CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -752,9 +759,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -772,6 +776,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -821,6 +830,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -832,9 +842,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -867,6 +875,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -877,6 +886,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -890,7 +900,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1010,6 +1019,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1068,7 +1078,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1140,6 +1149,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1157,6 +1167,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1178,7 +1189,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1220,11 +1230,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc836x_mds_defconfig b/arch/powerpc/configs/83xx/mpc836x_mds_defconfig index 8c5299d74813..4f434b1492fa 100644 --- a/arch/powerpc/configs/83xx/mpc836x_mds_defconfig +++ b/arch/powerpc/configs/83xx/mpc836x_mds_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:10 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:28 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -255,6 +258,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -272,6 +276,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -367,6 +372,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -396,6 +402,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -403,7 +410,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -416,6 +422,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -423,9 +430,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_OF_PARTS is not set @@ -585,6 +592,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -623,7 +631,9 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -693,7 +703,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -716,7 +728,6 @@ CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y # CONFIG_GIANFAR is not set CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set @@ -744,10 +755,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -840,6 +848,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -893,9 +902,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -913,6 +919,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -962,6 +973,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -973,9 +985,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1008,6 +1018,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1018,6 +1029,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1031,7 +1043,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1151,6 +1162,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1210,7 +1222,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1284,6 +1295,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1301,6 +1313,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1322,7 +1335,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1364,11 +1376,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc836x_rdk_defconfig b/arch/powerpc/configs/83xx/mpc836x_rdk_defconfig index ff31667a890b..b52ec0861679 100644 --- a/arch/powerpc/configs/83xx/mpc836x_rdk_defconfig +++ b/arch/powerpc/configs/83xx/mpc836x_rdk_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:12 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:30 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,28 +127,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -255,6 +258,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -272,6 +276,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -369,6 +374,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -398,6 +404,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -405,7 +412,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -418,6 +424,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -427,9 +434,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_OF_PARTS is not set @@ -493,6 +500,7 @@ CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_PMC551 is not set # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -639,7 +647,6 @@ CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y # CONFIG_GIANFAR is not set CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set @@ -649,10 +656,7 @@ CONFIG_UCC_GETH=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -750,6 +754,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -804,9 +809,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -853,17 +855,22 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # # CONFIG_GPIO_MAX7301 is not set # CONFIG_GPIO_MCP23S08 is not set +# CONFIG_GPIO_MC33880 is not set + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -897,8 +904,10 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set # CONFIG_AB3100_CORE is not set # CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set @@ -908,6 +917,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -992,7 +1002,6 @@ CONFIG_LOGO_LINUX_CLUT224=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1038,6 +1047,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1107,7 +1117,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1183,6 +1192,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1200,6 +1210,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1232,7 +1243,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1274,11 +1284,13 @@ CONFIG_CRYPTO_CBC=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc837x_mds_defconfig b/arch/powerpc/configs/83xx/mpc837x_mds_defconfig index e285ec0fe958..730061574f96 100644 --- a/arch/powerpc/configs/83xx/mpc837x_mds_defconfig +++ b/arch/powerpc/configs/83xx/mpc837x_mds_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:11 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:29 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,21 +127,20 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -147,6 +148,8 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -256,6 +259,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -368,6 +373,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -397,6 +403,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -404,7 +411,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -417,6 +423,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -503,6 +510,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -542,11 +550,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -569,6 +580,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -596,6 +608,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -672,7 +685,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -720,10 +735,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -816,6 +828,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -869,9 +882,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -889,6 +899,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -938,6 +953,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -949,9 +965,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -984,6 +998,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -994,6 +1009,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1007,7 +1023,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1072,6 +1087,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1130,7 +1146,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1206,6 +1221,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1221,6 +1237,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1242,7 +1259,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1284,11 +1300,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/mpc837x_rdb_defconfig b/arch/powerpc/configs/83xx/mpc837x_rdb_defconfig index 1ab3e4cd3018..9e9158a5b190 100644 --- a/arch/powerpc/configs/83xx/mpc837x_rdb_defconfig +++ b/arch/powerpc/configs/83xx/mpc837x_rdb_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:13 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:30 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,21 +127,20 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -147,6 +148,8 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -256,6 +259,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -363,6 +368,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -392,6 +398,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -399,7 +406,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -412,6 +418,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -498,6 +505,7 @@ CONFIG_SCSI_WAIT_SCAN=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -537,11 +545,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -564,6 +575,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -591,6 +603,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -610,6 +623,7 @@ CONFIG_MD_RAID1=y # CONFIG_MD_RAID10 is not set CONFIG_MD_RAID456=y CONFIG_MD_RAID6_PQ=y +# CONFIG_ASYNC_RAID6_TEST is not set # CONFIG_MD_MULTIPATH is not set # CONFIG_MD_FAULTY is not set # CONFIG_BLK_DEV_DM is not set @@ -678,7 +692,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -708,10 +724,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -813,6 +826,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -867,9 +881,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -887,6 +898,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -936,6 +952,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -947,9 +964,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -987,6 +1002,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -997,6 +1013,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1010,7 +1027,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1033,6 +1049,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1085,6 +1102,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set # CONFIG_USB_UHCI_HCD is not set # CONFIG_USB_SL811_HCD is not set @@ -1142,6 +1160,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_LD is not set # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set @@ -1188,6 +1207,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1246,7 +1266,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1361,6 +1380,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1376,6 +1396,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1396,12 +1417,13 @@ CONFIG_XOR_BLOCKS=y CONFIG_ASYNC_CORE=y CONFIG_ASYNC_MEMCPY=y CONFIG_ASYNC_XOR=y +CONFIG_ASYNC_PQ=y +CONFIG_ASYNC_RAID6_RECOV=y CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1443,11 +1465,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/83xx/sbc834x_defconfig b/arch/powerpc/configs/83xx/sbc834x_defconfig index 3a68f861b1bd..6b399154970f 100644 --- a/arch/powerpc/configs/83xx/sbc834x_defconfig +++ b/arch/powerpc/configs/83xx/sbc834x_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc5 -# Tue Aug 11 19:57:51 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:31 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,27 +126,28 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -254,6 +257,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -271,6 +275,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -366,6 +371,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -395,6 +401,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -402,7 +409,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -415,6 +421,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -422,9 +429,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y CONFIG_MTD_OF_PARTS=y @@ -651,7 +658,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -681,10 +690,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -786,6 +792,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -840,9 +847,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -860,6 +864,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -909,6 +918,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -920,9 +930,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -960,6 +968,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -970,6 +979,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -983,7 +993,6 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1035,6 +1044,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set # CONFIG_USB_UHCI_HCD is not set # CONFIG_USB_SL811_HCD is not set @@ -1148,6 +1158,7 @@ CONFIG_JBD=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1207,7 +1218,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1306,6 +1316,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1321,6 +1332,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1342,7 +1354,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1384,11 +1395,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/ksi8560_defconfig b/arch/powerpc/configs/85xx/ksi8560_defconfig index ff04e1028f5e..a5bde8da462c 100644 --- a/arch/powerpc/configs/85xx/ksi8560_defconfig +++ b/arch/powerpc/configs/85xx/ksi8560_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:14 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:32 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +87,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 # CONFIG_GROUP_SCHED is not set @@ -123,28 +126,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -188,6 +192,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set CONFIG_KSI8560=y # CONFIG_XES_MPC85xx is not set @@ -243,6 +248,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -260,6 +266,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -348,6 +355,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -377,6 +385,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -384,7 +393,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -397,6 +405,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -582,6 +591,8 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FCC=y @@ -591,10 +602,7 @@ CONFIG_FSL_PQ_MDIO=y CONFIG_GIANFAR=y # CONFIG_MV643XX_ETH is not set CONFIG_NETDEV_10000=y - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -704,10 +712,19 @@ CONFIG_GPIOLIB=y # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set # CONFIG_SENSORS_IT87 is not set @@ -719,9 +736,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -755,7 +770,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -818,6 +832,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -877,7 +892,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -945,6 +959,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -962,6 +977,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -981,10 +997,12 @@ CONFIG_DEBUG_MUTEXES=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1008,10 +1026,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1039,7 +1057,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1070,11 +1087,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/mpc8540_ads_defconfig b/arch/powerpc/configs/85xx/mpc8540_ads_defconfig index fb10cc83702e..c10e26f8763f 100644 --- a/arch/powerpc/configs/85xx/mpc8540_ads_defconfig +++ b/arch/powerpc/configs/85xx/mpc8540_ads_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:15 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:33 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -126,27 +129,28 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -189,6 +193,7 @@ CONFIG_MPC8540_ADS=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -244,6 +249,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -261,6 +267,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -349,6 +356,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -378,6 +386,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -385,7 +394,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -398,6 +406,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -483,15 +492,14 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y CONFIG_GIANFAR=y # CONFIG_MV643XX_ETH is not set CONFIG_NETDEV_10000=y - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -588,6 +596,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set # CONFIG_SENSORS_IT87 is not set @@ -598,9 +611,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -634,7 +645,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -696,6 +706,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -754,7 +765,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -822,6 +832,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -839,6 +850,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -857,10 +869,12 @@ CONFIG_DEBUG_MUTEXES=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -883,10 +897,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -912,7 +926,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -943,11 +956,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/mpc8560_ads_defconfig b/arch/powerpc/configs/85xx/mpc8560_ads_defconfig index 5c8ce6978825..8d9f0a4b5205 100644 --- a/arch/powerpc/configs/85xx/mpc8560_ads_defconfig +++ b/arch/powerpc/configs/85xx/mpc8560_ads_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:16 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:34 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +87,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -127,29 +130,30 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -192,6 +196,7 @@ CONFIG_MPC8560_ADS=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -247,6 +252,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -264,6 +270,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -361,6 +368,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -390,6 +398,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -397,7 +406,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -410,6 +418,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -530,7 +539,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FCC=y @@ -582,10 +593,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -698,14 +706,24 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_I5K_AMB is not set # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set @@ -721,9 +739,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT8231 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -746,6 +762,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -759,7 +776,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -824,6 +840,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -882,7 +899,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -950,6 +966,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -967,6 +984,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -985,10 +1003,12 @@ CONFIG_DEBUG_MUTEXES=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1011,10 +1031,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1040,7 +1060,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1071,11 +1090,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/mpc85xx_cds_defconfig b/arch/powerpc/configs/85xx/mpc85xx_cds_defconfig index 158e63e8607f..9b63e258dac6 100644 --- a/arch/powerpc/configs/85xx/mpc85xx_cds_defconfig +++ b/arch/powerpc/configs/85xx/mpc85xx_cds_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:17 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:35 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -126,28 +129,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -190,6 +194,7 @@ CONFIG_MPC85xx_CDS=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -245,6 +250,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -262,6 +268,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -359,6 +366,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -388,6 +396,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -395,7 +404,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -408,6 +416,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -582,7 +591,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -630,10 +641,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -737,6 +745,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_I5K_AMB is not set # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set @@ -751,9 +764,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT8231 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -776,6 +787,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -789,7 +801,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -854,6 +865,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -912,7 +924,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -980,6 +991,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -997,6 +1009,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1015,10 +1028,12 @@ CONFIG_DEBUG_MUTEXES=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1041,10 +1056,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1070,7 +1085,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1101,11 +1115,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/sbc8548_defconfig b/arch/powerpc/configs/85xx/sbc8548_defconfig index 2726fca1d694..1b2356830173 100644 --- a/arch/powerpc/configs/85xx/sbc8548_defconfig +++ b/arch/powerpc/configs/85xx/sbc8548_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:18 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:36 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,27 +128,28 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -188,6 +192,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -242,6 +247,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -259,6 +265,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -355,6 +362,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -384,6 +392,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -391,7 +400,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -404,6 +412,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -521,7 +530,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -569,10 +580,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -676,6 +684,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_I5K_AMB is not set # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set @@ -690,9 +703,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT8231 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -715,6 +726,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -758,6 +770,7 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -816,7 +829,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -872,6 +884,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -887,6 +900,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -907,7 +921,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -938,11 +951,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/sbc8560_defconfig b/arch/powerpc/configs/85xx/sbc8560_defconfig index b0c469823b02..959d0281431b 100644 --- a/arch/powerpc/configs/85xx/sbc8560_defconfig +++ b/arch/powerpc/configs/85xx/sbc8560_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:19 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:37 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -126,26 +129,27 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -188,6 +192,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -242,6 +247,7 @@ CONFIG_BINFMT_MISC=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -259,6 +265,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -347,6 +354,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -376,6 +384,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -383,7 +392,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -396,6 +404,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -481,15 +490,14 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y CONFIG_GIANFAR=y # CONFIG_MV643XX_ETH is not set CONFIG_NETDEV_10000=y - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -584,6 +592,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set # CONFIG_SENSORS_IT87 is not set @@ -594,9 +607,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -630,7 +641,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -721,6 +731,7 @@ CONFIG_RTC_DRV_M48T59=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -779,7 +790,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -847,6 +857,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -863,6 +874,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_TIMER_STATS is not set # CONFIG_DEBUG_OBJECTS is not set # CONFIG_DEBUG_SLAB is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -881,10 +893,12 @@ CONFIG_DEBUG_MUTEXES=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -907,10 +921,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -947,7 +961,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -978,11 +991,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/socrates_defconfig b/arch/powerpc/configs/85xx/socrates_defconfig index 04c85dada845..7f5ec35bf199 100644 --- a/arch/powerpc/configs/85xx/socrates_defconfig +++ b/arch/powerpc/configs/85xx/socrates_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:19 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:37 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=16 CONFIG_GROUP_SCHED=y @@ -124,28 +127,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -193,6 +197,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set CONFIG_SOCRATES=y # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -247,6 +252,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -264,6 +270,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -358,6 +365,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -396,6 +404,7 @@ CONFIG_CAN_BCM=y # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 # CONFIG_WIRELESS_OLD_REGULATORY is not set # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -403,7 +412,6 @@ CONFIG_WIRELESS=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -421,9 +429,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y CONFIG_MTD_OF_PARTS=y @@ -482,6 +490,7 @@ CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_PMC551 is not set # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -668,7 +677,9 @@ CONFIG_MII=y # CONFIG_B44 is not set # CONFIG_KS8842 is not set # CONFIG_KS8851 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -698,10 +709,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -765,6 +773,7 @@ CONFIG_INPUT_TOUCHSCREEN=y # CONFIG_TOUCHSCREEN_GUNZE is not set # CONFIG_TOUCHSCREEN_ELO is not set # CONFIG_TOUCHSCREEN_WACOM_W8001 is not set +# CONFIG_TOUCHSCREEN_MCS5000 is not set # CONFIG_TOUCHSCREEN_MTOUCH is not set # CONFIG_TOUCHSCREEN_INEXIO is not set # CONFIG_TOUCHSCREEN_MK712 is not set @@ -774,7 +783,6 @@ CONFIG_INPUT_TOUCHSCREEN=y # CONFIG_TOUCHSCREEN_USB_COMPOSITE is not set # CONFIG_TOUCHSCREEN_TOUCHIT213 is not set # CONFIG_TOUCHSCREEN_TSC2007 is not set -# CONFIG_TOUCHSCREEN_W90X900 is not set # CONFIG_INPUT_MISC is not set # @@ -834,6 +842,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -888,9 +897,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -921,6 +927,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y CONFIG_HWMON_VID=y +CONFIG_HWMON_DEBUG_CHIP=y + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADCXX is not set @@ -973,6 +984,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -985,9 +997,7 @@ CONFIG_SENSORS_W83781D=y # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set # CONFIG_SENSORS_LIS3_SPI is not set -CONFIG_HWMON_DEBUG_CHIP=y # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1006,8 +1016,10 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set # CONFIG_AB3100_CORE is not set # CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set @@ -1017,6 +1029,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1112,7 +1125,6 @@ CONFIG_FONT_8x16=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1135,6 +1147,7 @@ CONFIG_USB_HID=y # CONFIG_HID_EZKEY is not set # CONFIG_HID_KYE is not set # CONFIG_HID_GYRATION is not set +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set # CONFIG_HID_LOGITECH is not set # CONFIG_HID_MICROSOFT is not set @@ -1184,6 +1197,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1319,6 +1333,7 @@ CONFIG_RTC_INTF_DEV=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -1369,6 +1384,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1438,7 +1454,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1552,6 +1567,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1569,6 +1585,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1589,7 +1606,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1621,11 +1637,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/stx_gp3_defconfig b/arch/powerpc/configs/85xx/stx_gp3_defconfig index e7e81d6769fe..c8327e88a987 100644 --- a/arch/powerpc/configs/85xx/stx_gp3_defconfig +++ b/arch/powerpc/configs/85xx/stx_gp3_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:20 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:38 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +87,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -127,22 +130,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -150,7 +152,9 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -197,6 +201,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -252,6 +257,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -269,6 +275,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -426,6 +433,7 @@ CONFIG_IP_NF_FILTER=m # CONFIG_IP_NF_ARPTABLES is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -455,6 +463,7 @@ CONFIG_NET_PKTGEN=y # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -462,7 +471,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -475,6 +483,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -622,6 +631,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -662,7 +672,9 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -732,8 +744,10 @@ CONFIG_NET_ETHERNET=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_NET_POCKET is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set # CONFIG_FS_ENET is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set @@ -782,10 +796,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -827,11 +838,15 @@ CONFIG_INPUT_EVDEV=m # Input Device Drivers # CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ADP5588 is not set CONFIG_KEYBOARD_ATKBD=y +# CONFIG_QT2160 is not set # CONFIG_KEYBOARD_LKKBD is not set # CONFIG_KEYBOARD_GPIO is not set # CONFIG_KEYBOARD_MATRIX is not set +# CONFIG_KEYBOARD_MAX7359 is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set # CONFIG_KEYBOARD_SUNKBD is not set # CONFIG_KEYBOARD_XTKBD is not set @@ -842,6 +857,7 @@ CONFIG_MOUSE_PS2_LOGIPS2PP=y CONFIG_MOUSE_PS2_SYNAPTICS=y CONFIG_MOUSE_PS2_TRACKPOINT=y # CONFIG_MOUSE_PS2_ELANTECH is not set +# CONFIG_MOUSE_PS2_SENTELIC is not set # CONFIG_MOUSE_PS2_TOUCHKIT is not set # CONFIG_MOUSE_SERIAL is not set # CONFIG_MOUSE_APPLETOUCH is not set @@ -909,6 +925,7 @@ CONFIG_HW_RANDOM=m CONFIG_DEVPORT=y CONFIG_I2C=m CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=m CONFIG_I2C_HELPER_AUTO=y CONFIG_I2C_ALGOBIT=m @@ -967,9 +984,6 @@ CONFIG_I2C_ALGOBIT=m # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1003,14 +1017,24 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1061,6 +1085,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1072,9 +1097,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1092,6 +1115,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_TPS65010 is not set # CONFIG_MFD_TMIO is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1102,6 +1126,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # CONFIG_AGP=m +CONFIG_VGA_ARB=y CONFIG_DRM=m # CONFIG_DRM_TDFX is not set # CONFIG_DRM_R128 is not set @@ -1125,7 +1150,6 @@ CONFIG_SOUND=m # CONFIG_SOUND_PRIME is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1190,6 +1214,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1254,7 +1279,6 @@ CONFIG_CRAMFS=m # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1352,6 +1376,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1369,6 +1394,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1388,10 +1414,12 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1414,10 +1442,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1443,7 +1471,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1475,11 +1502,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/tqm8540_defconfig b/arch/powerpc/configs/85xx/tqm8540_defconfig index 2c407523aad2..82563703d5e3 100644 --- a/arch/powerpc/configs/85xx/tqm8540_defconfig +++ b/arch/powerpc/configs/85xx/tqm8540_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:21 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:39 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -124,28 +127,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -188,6 +192,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -243,6 +248,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -260,6 +266,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -354,6 +361,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -383,6 +391,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -390,7 +399,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -677,9 +685,11 @@ CONFIG_E100=y # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -727,10 +737,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -824,6 +831,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -876,9 +884,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -896,6 +901,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +CONFIG_HWMON_DEBUG_CHIP=y + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -945,6 +955,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -956,9 +967,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -CONFIG_HWMON_DEBUG_CHIP=y # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -977,6 +986,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -987,6 +997,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1000,7 +1011,6 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1065,6 +1075,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1134,7 +1145,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -1203,6 +1213,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1220,6 +1231,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1240,7 +1252,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1271,11 +1282,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/tqm8541_defconfig b/arch/powerpc/configs/85xx/tqm8541_defconfig index 845731dc51c6..91d85d733827 100644 --- a/arch/powerpc/configs/85xx/tqm8541_defconfig +++ b/arch/powerpc/configs/85xx/tqm8541_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:22 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:40 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +87,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,29 +128,30 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -190,6 +194,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -246,6 +251,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -263,6 +269,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -357,6 +364,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -386,6 +394,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -393,7 +402,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -681,9 +689,11 @@ CONFIG_E100=y # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set # CONFIG_FS_ENET is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set @@ -732,10 +742,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -831,6 +838,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -886,9 +894,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -921,14 +926,24 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +CONFIG_HWMON_DEBUG_CHIP=y + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -979,6 +994,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -990,9 +1006,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -CONFIG_HWMON_DEBUG_CHIP=y # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1012,6 +1026,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1022,6 +1037,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1035,7 +1051,6 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1100,6 +1115,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1169,7 +1185,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -1238,6 +1253,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1255,6 +1271,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1275,7 +1292,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1306,11 +1322,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/tqm8548_defconfig b/arch/powerpc/configs/85xx/tqm8548_defconfig index 4f228a905274..debe268f43d1 100644 --- a/arch/powerpc/configs/85xx/tqm8548_defconfig +++ b/arch/powerpc/configs/85xx/tqm8548_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:23 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:41 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +86,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -126,22 +129,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -149,6 +151,8 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -196,6 +200,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -252,6 +257,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -269,6 +275,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -371,6 +378,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -411,6 +419,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -420,9 +429,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set CONFIG_MTD_OF_PARTS=y @@ -630,7 +639,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -678,10 +689,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -772,6 +780,7 @@ CONFIG_LEGACY_PTY_COUNT=256 CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -825,9 +834,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -845,6 +851,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -894,6 +905,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -905,9 +917,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -926,6 +936,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -936,6 +947,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -949,7 +961,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1042,6 +1053,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1111,7 +1123,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -1180,6 +1191,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1197,6 +1209,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1216,10 +1229,12 @@ CONFIG_DEBUG_MUTEXES=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1242,10 +1257,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1271,7 +1286,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1303,11 +1317,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/tqm8555_defconfig b/arch/powerpc/configs/85xx/tqm8555_defconfig index 9196724bebc7..74515501f5b7 100644 --- a/arch/powerpc/configs/85xx/tqm8555_defconfig +++ b/arch/powerpc/configs/85xx/tqm8555_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:24 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:42 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +87,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,29 +128,30 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -190,6 +194,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -246,6 +251,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -263,6 +269,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -357,6 +364,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -386,6 +394,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -393,7 +402,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -681,9 +689,11 @@ CONFIG_E100=y # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set # CONFIG_FS_ENET is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set @@ -732,10 +742,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -831,6 +838,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -886,9 +894,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -921,14 +926,24 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +CONFIG_HWMON_DEBUG_CHIP=y + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -979,6 +994,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -990,9 +1006,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -CONFIG_HWMON_DEBUG_CHIP=y # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1012,6 +1026,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1022,6 +1037,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1035,7 +1051,6 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1100,6 +1115,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1169,7 +1185,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -1238,6 +1253,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1255,6 +1271,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1275,7 +1292,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1306,11 +1322,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/tqm8560_defconfig b/arch/powerpc/configs/85xx/tqm8560_defconfig index 2e49a6e9faf2..631d92b4d4e6 100644 --- a/arch/powerpc/configs/85xx/tqm8560_defconfig +++ b/arch/powerpc/configs/85xx/tqm8560_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:25 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:43 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +87,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -125,29 +128,30 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -190,6 +194,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set # CONFIG_XES_MPC85xx is not set @@ -246,6 +251,7 @@ CONFIG_MATH_EMULATION=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -263,6 +269,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -357,6 +364,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -386,6 +394,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -393,7 +402,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -681,9 +689,11 @@ CONFIG_E100=y # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set # CONFIG_FS_ENET is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set @@ -732,10 +742,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -831,6 +838,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -886,9 +894,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -921,14 +926,24 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +CONFIG_HWMON_DEBUG_CHIP=y + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -979,6 +994,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -990,9 +1006,7 @@ CONFIG_SENSORS_LM75=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -CONFIG_HWMON_DEBUG_CHIP=y # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1012,6 +1026,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1022,6 +1037,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1035,7 +1051,6 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1100,6 +1115,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1169,7 +1185,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -1238,6 +1253,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1255,6 +1271,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1275,7 +1292,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1306,11 +1322,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/85xx/xes_mpc85xx_defconfig b/arch/powerpc/configs/85xx/xes_mpc85xx_defconfig index 1025da2bf069..52acbac0c4fe 100644 --- a/arch/powerpc/configs/85xx/xes_mpc85xx_defconfig +++ b/arch/powerpc/configs/85xx/xes_mpc85xx_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:25 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:44 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set CONFIG_SMP=y @@ -37,6 +38,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -89,11 +91,12 @@ CONFIG_AUDIT=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -128,22 +131,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -151,7 +153,9 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -201,6 +205,7 @@ CONFIG_MPC85xx=y # CONFIG_MPC85xx_MDS is not set # CONFIG_MPC8536_DS is not set # CONFIG_MPC85xx_DS is not set +# CONFIG_MPC85xx_RDB is not set # CONFIG_SOCRATES is not set # CONFIG_KSI8560 is not set CONFIG_XES_MPC85xx=y @@ -256,6 +261,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_IRQ_ALL_CPUS is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +279,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -405,6 +412,7 @@ CONFIG_IPV6_NDISC_NODETYPE=y # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -446,6 +454,7 @@ CONFIG_FIB_RULES=y # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -457,9 +466,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set CONFIG_MTD_REDBOOT_PARTS=y CONFIG_MTD_REDBOOT_DIRECTORY_BLOCK=-1 # CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set @@ -635,6 +644,7 @@ CONFIG_SCSI_WAIT_SCAN=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -674,11 +684,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_SATA_AHCI=y # CONFIG_SATA_SIL24 is not set @@ -701,6 +714,7 @@ CONFIG_ATA_SFF=y CONFIG_PATA_ALI=y # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -728,6 +742,7 @@ CONFIG_PATA_ALI=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -804,7 +819,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -834,10 +851,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -951,6 +965,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1006,8 +1021,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1041,14 +1054,24 @@ CONFIG_GPIO_PCA953X=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1099,6 +1122,7 @@ CONFIG_SENSORS_LM90=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1110,9 +1134,7 @@ CONFIG_SENSORS_LM90=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1151,6 +1173,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1161,6 +1184,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -1181,7 +1205,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1204,6 +1227,7 @@ CONFIG_USB_HID=y # CONFIG_HID_EZKEY is not set # CONFIG_HID_KYE is not set # CONFIG_HID_GYRATION is not set +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set # CONFIG_HID_LOGITECH is not set # CONFIG_HID_MICROSOFT is not set @@ -1249,6 +1273,7 @@ CONFIG_USB_MON=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set CONFIG_USB_ISP1760_HCD=y +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set # CONFIG_USB_UHCI_HCD is not set # CONFIG_USB_SL811_HCD is not set @@ -1466,6 +1491,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1541,7 +1567,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1658,6 +1683,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1675,6 +1701,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1694,10 +1721,12 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set @@ -1720,10 +1749,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1749,7 +1778,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1790,11 +1818,13 @@ CONFIG_CRYPTO_WORKQUEUE=y # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/86xx/gef_ppc9a_defconfig b/arch/powerpc/configs/86xx/gef_ppc9a_defconfig index 527ad1a5e802..28980738776c 100644 --- a/arch/powerpc/configs/86xx/gef_ppc9a_defconfig +++ b/arch/powerpc/configs/86xx/gef_ppc9a_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:31 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:49 2009 # # CONFIG_PPC64 is not set @@ -36,6 +36,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -88,11 +89,12 @@ CONFIG_BSD_PROCESS_ACCT_V3=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -130,21 +132,20 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -152,12 +153,14 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling # -# CONFIG_SLOW_WORK is not set +CONFIG_SLOW_WORK=y # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y @@ -256,6 +259,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set CONFIG_IRQ_ALL_CPUS=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -417,6 +422,7 @@ CONFIG_IPV6_TUNNEL=m # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -458,6 +464,7 @@ CONFIG_FIB_RULES=y # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -467,9 +474,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set CONFIG_MTD_OF_PARTS=y @@ -680,6 +687,7 @@ CONFIG_SCSI_WAIT_SCAN=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -719,12 +727,15 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_LOWLEVEL_PCMCIA is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -747,6 +758,7 @@ CONFIG_SATA_SIL=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -775,6 +787,7 @@ CONFIG_SATA_SIL=y # CONFIG_PATA_PCMCIA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -851,7 +864,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -881,10 +896,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -1016,6 +1028,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1071,9 +1084,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # CONFIG_DS1682=y -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1106,14 +1116,24 @@ CONFIG_GPIO_SYSFS=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1164,6 +1184,7 @@ CONFIG_SENSORS_LM92=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1175,9 +1196,7 @@ CONFIG_SENSORS_LM92=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1217,6 +1236,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1227,6 +1247,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1247,7 +1268,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1270,6 +1290,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1322,6 +1343,7 @@ CONFIG_USB_EHCI_HCD=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y # CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1397,6 +1419,7 @@ CONFIG_USB_STORAGE=y # CONFIG_USB_LD is not set # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set @@ -1501,6 +1524,7 @@ CONFIG_FS_POSIX_ACL=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1576,7 +1600,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1682,6 +1705,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1697,6 +1721,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1718,7 +1743,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=m @@ -1761,11 +1785,13 @@ CONFIG_CRYPTO_CBC=y # CONFIG_CRYPTO_HMAC=m # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=y +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/86xx/gef_sbc310_defconfig b/arch/powerpc/configs/86xx/gef_sbc310_defconfig index cd338d493bed..e199d1cacbaf 100644 --- a/arch/powerpc/configs/86xx/gef_sbc310_defconfig +++ b/arch/powerpc/configs/86xx/gef_sbc310_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:29 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:47 2009 # # CONFIG_PPC64 is not set @@ -36,6 +36,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -88,11 +89,12 @@ CONFIG_BSD_PROCESS_ACCT_V3=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -130,21 +132,20 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -152,12 +153,14 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling # -# CONFIG_SLOW_WORK is not set +CONFIG_SLOW_WORK=y # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y @@ -256,6 +259,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set CONFIG_IRQ_ALL_CPUS=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -273,6 +277,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -417,6 +422,7 @@ CONFIG_IPV6_TUNNEL=m # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -458,6 +464,7 @@ CONFIG_FIB_RULES=y # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -467,9 +474,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set CONFIG_MTD_OF_PARTS=y @@ -680,6 +687,7 @@ CONFIG_SCSI_WAIT_SCAN=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -719,12 +727,15 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_LOWLEVEL_PCMCIA is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set CONFIG_SATA_SIL24=y @@ -796,7 +807,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -826,10 +839,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -961,6 +971,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1016,9 +1027,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # CONFIG_DS1682=y -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1051,14 +1059,24 @@ CONFIG_GPIO_SYSFS=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1109,6 +1127,7 @@ CONFIG_SENSORS_LM92=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1120,9 +1139,7 @@ CONFIG_SENSORS_LM92=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1162,6 +1179,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1172,6 +1190,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1192,7 +1211,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1215,6 +1233,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1267,6 +1286,7 @@ CONFIG_USB_EHCI_HCD=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y # CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1342,6 +1362,7 @@ CONFIG_USB_STORAGE=y # CONFIG_USB_LD is not set # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set @@ -1446,6 +1467,7 @@ CONFIG_FS_POSIX_ACL=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1521,7 +1543,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1627,6 +1648,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1642,6 +1664,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1663,7 +1686,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=m @@ -1706,11 +1728,13 @@ CONFIG_CRYPTO_CBC=y # CONFIG_CRYPTO_HMAC=m # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=y +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/86xx/gef_sbc610_defconfig b/arch/powerpc/configs/86xx/gef_sbc610_defconfig index ba47883f4aa0..3b0fbfb28efd 100644 --- a/arch/powerpc/configs/86xx/gef_sbc610_defconfig +++ b/arch/powerpc/configs/86xx/gef_sbc610_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:30 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:48 2009 # # CONFIG_PPC64 is not set @@ -36,6 +36,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -88,11 +89,12 @@ CONFIG_BSD_PROCESS_ACCT_V3=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -131,21 +133,20 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -153,12 +154,14 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling # -# CONFIG_SLOW_WORK is not set +CONFIG_SLOW_WORK=y # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y @@ -257,6 +260,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set CONFIG_IRQ_ALL_CPUS=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -274,6 +278,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -503,6 +508,7 @@ CONFIG_IP_SCTP=m # CONFIG_SCTP_HMAC_NONE is not set # CONFIG_SCTP_HMAC_SHA1 is not set CONFIG_SCTP_HMAC_MD5=y +# CONFIG_RDS is not set CONFIG_TIPC=m # CONFIG_TIPC_ADVANCED is not set # CONFIG_TIPC_DEBUG is not set @@ -582,6 +588,7 @@ CONFIG_NET_PKTGEN=m CONFIG_FIB_RULES=y CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -589,7 +596,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -602,6 +608,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -611,9 +618,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set # CONFIG_MTD_OF_PARTS is not set @@ -780,6 +787,7 @@ CONFIG_SCSI_WAIT_SCAN=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -819,11 +827,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -846,6 +857,7 @@ CONFIG_SATA_SIL=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -873,6 +885,7 @@ CONFIG_SATA_SIL=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -949,7 +962,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -979,10 +994,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -1120,6 +1132,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1175,9 +1188,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # CONFIG_DS1682=y -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1211,14 +1221,24 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1269,6 +1289,7 @@ CONFIG_SENSORS_LM92=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1280,9 +1301,7 @@ CONFIG_SENSORS_LM92=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1322,6 +1341,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1332,6 +1352,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1352,7 +1373,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1375,6 +1395,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1427,6 +1448,7 @@ CONFIG_USB_EHCI_HCD=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y # CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1502,6 +1524,7 @@ CONFIG_USB_STORAGE=y # CONFIG_USB_LD is not set # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_ATM is not set @@ -1607,6 +1630,7 @@ CONFIG_FS_POSIX_ACL=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1669,7 +1693,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1775,6 +1798,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1791,6 +1815,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_TIMER_STATS is not set # CONFIG_DEBUG_OBJECTS is not set # CONFIG_DEBUG_SLAB is not set +# CONFIG_DEBUG_KMEMLEAK is not set CONFIG_DEBUG_PREEMPT=y # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set @@ -1810,10 +1835,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1837,10 +1864,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1872,7 +1899,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=m @@ -1915,11 +1941,13 @@ CONFIG_CRYPTO_PCBC=m # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set CONFIG_CRYPTO_MD4=m CONFIG_CRYPTO_MD5=y CONFIG_CRYPTO_MICHAEL_MIC=m diff --git a/arch/powerpc/configs/86xx/mpc8610_hpcd_defconfig b/arch/powerpc/configs/86xx/mpc8610_hpcd_defconfig index a61f183f7186..de4d52504fe4 100644 --- a/arch/powerpc/configs/86xx/mpc8610_hpcd_defconfig +++ b/arch/powerpc/configs/86xx/mpc8610_hpcd_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:27 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:45 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -83,11 +84,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -126,22 +128,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -149,6 +150,8 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -251,6 +254,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -268,6 +272,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -385,6 +390,7 @@ CONFIG_IPV6_NDISC_NODETYPE=y # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -414,6 +420,7 @@ CONFIG_IPV6_NDISC_NODETYPE=y # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -421,7 +428,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -434,6 +440,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -445,9 +452,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y # CONFIG_MTD_OF_PARTS is not set @@ -662,6 +669,7 @@ CONFIG_SCSI_WAIT_SCAN=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -701,11 +709,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_SATA_AHCI=y # CONFIG_SATA_SIL24 is not set @@ -728,6 +739,7 @@ CONFIG_ATA_SFF=y CONFIG_PATA_ALI=y # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -755,6 +767,7 @@ CONFIG_PATA_ALI=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -818,14 +831,13 @@ CONFIG_ULI526X=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -929,6 +941,7 @@ CONFIG_UNIX98_PTYS=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y # CONFIG_I2C_CHARDEV is not set CONFIG_I2C_HELPER_AUTO=y @@ -982,9 +995,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1002,7 +1012,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1021,6 +1030,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1031,6 +1041,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -1107,6 +1118,7 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_LOGO is not set CONFIG_SOUND=y CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y CONFIG_SND=y CONFIG_SND_TIMER=y CONFIG_SND_PCM=y @@ -1209,7 +1221,6 @@ CONFIG_SND_SOC_CS4270_VD33_ERRATA=y # CONFIG_SOUND_PRIME is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1329,6 +1340,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set @@ -1388,7 +1400,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1505,6 +1516,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1522,6 +1534,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1541,10 +1554,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1567,10 +1582,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1597,7 +1612,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1629,11 +1643,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/86xx/mpc8641_hpcn_defconfig b/arch/powerpc/configs/86xx/mpc8641_hpcn_defconfig index 7016ce732605..754a79ba74a9 100644 --- a/arch/powerpc/configs/86xx/mpc8641_hpcn_defconfig +++ b/arch/powerpc/configs/86xx/mpc8641_hpcn_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:28 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:46 2009 # # CONFIG_PPC64 is not set @@ -36,6 +36,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -87,11 +88,12 @@ CONFIG_AUDIT=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -130,22 +132,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -153,7 +154,9 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -251,13 +254,13 @@ CONFIG_BINFMT_ELF=y CONFIG_BINFMT_MISC=m CONFIG_IOMMU_HELPER=y CONFIG_SWIOTLB=y -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set # CONFIG_IRQ_ALL_CPUS is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -275,6 +278,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -404,6 +408,7 @@ CONFIG_IP_SCTP=m # CONFIG_SCTP_HMAC_NONE is not set # CONFIG_SCTP_HMAC_SHA1 is not set CONFIG_SCTP_HMAC_MD5=y +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -434,6 +439,7 @@ CONFIG_SCTP_HMAC_MD5=y CONFIG_FIB_RULES=y CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -441,7 +447,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -454,6 +459,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -546,6 +552,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -585,11 +592,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_SATA_AHCI=y # CONFIG_SATA_SIL24 is not set @@ -612,6 +622,7 @@ CONFIG_ATA_SFF=y CONFIG_PATA_ALI=y # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -639,6 +650,7 @@ CONFIG_PATA_ALI=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -715,7 +727,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -763,10 +777,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -880,6 +891,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y # CONFIG_I2C_CHARDEV is not set CONFIG_I2C_HELPER_AUTO=y @@ -934,9 +946,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -954,7 +963,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -973,6 +981,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -983,6 +992,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -1002,6 +1012,7 @@ CONFIG_VGA_CONSOLE=y CONFIG_DUMMY_CONSOLE=y CONFIG_SOUND=y CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y CONFIG_SND=y CONFIG_SND_TIMER=y CONFIG_SND_PCM=y @@ -1105,7 +1116,6 @@ CONFIG_SND_USB=y CONFIG_AC97_BUS=y CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1128,6 +1138,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1180,6 +1191,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y CONFIG_USB_OHCI_HCD_PPC_OF_LE=y @@ -1358,6 +1370,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1428,7 +1441,6 @@ CONFIG_SYSV_FS=m CONFIG_UFS_FS=m # CONFIG_UFS_FS_WRITE is not set # CONFIG_UFS_DEBUG is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1546,6 +1558,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1563,6 +1576,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1582,10 +1596,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1608,10 +1624,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1638,7 +1654,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1680,11 +1695,13 @@ CONFIG_CRYPTO_PCBC=m # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/86xx/sbc8641d_defconfig b/arch/powerpc/configs/86xx/sbc8641d_defconfig index f5ca2e0cd402..89991f157ae8 100644 --- a/arch/powerpc/configs/86xx/sbc8641d_defconfig +++ b/arch/powerpc/configs/86xx/sbc8641d_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:26 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:45 2009 # # CONFIG_PPC64 is not set @@ -36,6 +36,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -87,11 +88,12 @@ CONFIG_BSD_PROCESS_ACCT_V3=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -130,21 +132,20 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -152,13 +153,15 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling # # CONFIG_GCOV_KERNEL is not set -# CONFIG_SLOW_WORK is not set +CONFIG_SLOW_WORK=y # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y @@ -257,6 +260,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set CONFIG_IRQ_ALL_CPUS=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -274,6 +278,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -502,6 +507,7 @@ CONFIG_IP_SCTP=m # CONFIG_SCTP_HMAC_NONE is not set # CONFIG_SCTP_HMAC_SHA1 is not set CONFIG_SCTP_HMAC_MD5=y +# CONFIG_RDS is not set CONFIG_TIPC=m # CONFIG_TIPC_ADVANCED is not set # CONFIG_TIPC_DEBUG is not set @@ -581,6 +587,7 @@ CONFIG_NET_PKTGEN=m CONFIG_FIB_RULES=y CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -588,7 +595,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -601,6 +607,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -610,9 +617,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set # CONFIG_MTD_OF_PARTS is not set @@ -833,7 +840,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -863,10 +872,7 @@ CONFIG_GIANFAR=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -996,6 +1002,7 @@ CONFIG_HW_RANDOM=m CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1049,9 +1056,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1069,6 +1073,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1118,6 +1127,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1129,9 +1139,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1164,6 +1172,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1174,6 +1183,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1194,7 +1204,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -1274,6 +1283,7 @@ CONFIG_OCFS2_DEBUG_MASKLOG=y # CONFIG_OCFS2_DEBUG_FS is not set # CONFIG_OCFS2_FS_POSIX_ACL is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1343,7 +1353,6 @@ CONFIG_ROMFS_BACKED_BY_BLOCK=y CONFIG_ROMFS_ON_BLOCK=y # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1451,6 +1460,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -1467,6 +1477,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_TIMER_STATS is not set # CONFIG_DEBUG_OBJECTS is not set # CONFIG_DEBUG_SLAB is not set +# CONFIG_DEBUG_KMEMLEAK is not set CONFIG_DEBUG_PREEMPT=y # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set @@ -1486,10 +1497,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1514,10 +1527,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1550,7 +1563,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=m @@ -1593,11 +1605,13 @@ CONFIG_CRYPTO_PCBC=m # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set CONFIG_CRYPTO_MD4=m CONFIG_CRYPTO_MD5=y CONFIG_CRYPTO_MICHAEL_MIC=m diff --git a/arch/powerpc/configs/adder875_defconfig b/arch/powerpc/configs/adder875_defconfig index aece6bb5f733..052cf134e018 100644 --- a/arch/powerpc/configs/adder875_defconfig +++ b/arch/powerpc/configs/adder875_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:47 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:04 2009 # # CONFIG_PPC64 is not set @@ -16,6 +16,7 @@ CONFIG_PPC_8xx=y # CONFIG_E200 is not set CONFIG_8xx=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y # CONFIG_PPC_MM_SLICES is not set CONFIG_NOT_COHERENT_CACHE=y CONFIG_PPC32=y @@ -29,6 +30,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -78,11 +80,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -116,28 +119,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -235,10 +239,10 @@ CONFIG_BINFMT_ELF=y # CONFIG_8XX_MINIMAL_FPEMU is not set # CONFIG_IOMMU_HELPER is not set # CONFIG_SWIOTLB is not set -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -256,6 +260,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -338,6 +343,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -367,6 +373,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -374,7 +381,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -387,6 +393,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -530,16 +537,15 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FEC=y CONFIG_FS_ENET_MDIO_FEC=y # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -580,6 +586,7 @@ CONFIG_INPUT_KEYBOARD=y CONFIG_KEYBOARD_ATKBD=y # CONFIG_KEYBOARD_LKKBD is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set # CONFIG_KEYBOARD_SUNKBD is not set # CONFIG_KEYBOARD_XTKBD is not set @@ -590,6 +597,7 @@ CONFIG_MOUSE_PS2_LOGIPS2PP=y CONFIG_MOUSE_PS2_SYNAPTICS=y CONFIG_MOUSE_PS2_TRACKPOINT=y # CONFIG_MOUSE_PS2_ELANTECH is not set +# CONFIG_MOUSE_PS2_SENTELIC is not set # CONFIG_MOUSE_PS2_TOUCHKIT is not set # CONFIG_MOUSE_SERIAL is not set # CONFIG_MOUSE_VSXXXAA is not set @@ -716,6 +724,7 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set @@ -775,7 +784,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -847,6 +855,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -864,6 +873,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set # CONFIG_DEBUG_LOCK_ALLOC is not set @@ -880,10 +890,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -906,10 +918,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 diff --git a/arch/powerpc/configs/c2k_defconfig b/arch/powerpc/configs/c2k_defconfig index 8105360d53f4..0fb65a85dfdf 100644 --- a/arch/powerpc/configs/c2k_defconfig +++ b/arch/powerpc/configs/c2k_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:48 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:05 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set CONFIG_PPC_HAVE_PMU_SUPPORT=y +CONFIG_PPC_PERF_CTRS=y # CONFIG_SMP is not set CONFIG_NOT_COHERENT_CACHE=y CONFIG_CHECK_CACHE_COHERENCY=y @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -88,11 +90,12 @@ CONFIG_AUDIT_TREE=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=17 CONFIG_GROUP_SCHED=y @@ -135,23 +138,24 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +CONFIG_PERF_EVENTS=y +CONFIG_EVENT_PROFILE=y # CONFIG_PERF_COUNTERS is not set +# CONFIG_DEBUG_PERF_USE_VMALLOC is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set CONFIG_PROFILING=y CONFIG_TRACEPOINTS=y -CONFIG_MARKERS=y CONFIG_OPROFILE=m CONFIG_HAVE_OPROFILE=y CONFIG_KPROBES=y @@ -161,12 +165,14 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling # # CONFIG_GCOV_KERNEL is not set -# CONFIG_SLOW_WORK is not set +CONFIG_SLOW_WORK=y # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y @@ -275,12 +281,12 @@ CONFIG_BINFMT_ELF=y CONFIG_BINFMT_MISC=y # CONFIG_IOMMU_HELPER is not set # CONFIG_SWIOTLB is not set -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -298,6 +304,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -309,6 +316,7 @@ CONFIG_FORCE_MAX_ZONEORDER=11 CONFIG_EXTRA_TARGETS="" CONFIG_PM=y # CONFIG_PM_DEBUG is not set +# CONFIG_PM_RUNTIME is not set CONFIG_SECCOMP=y CONFIG_ISA_DMA_API=y @@ -674,10 +682,12 @@ CONFIG_BT_HCIBCM203X=m # CONFIG_BT_HCIBPA10X is not set CONFIG_BT_HCIBFUSB=m CONFIG_BT_HCIVHCI=m +# CONFIG_BT_MRVL is not set # CONFIG_AF_RXRPC is not set CONFIG_FIB_RULES=y CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y CONFIG_WIRELESS_EXT=y CONFIG_WIRELESS_EXT_SYSFS=y @@ -686,7 +696,6 @@ CONFIG_WIRELESS_EXT_SYSFS=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -699,6 +708,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -710,9 +720,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=m CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set CONFIG_MTD_OF_PARTS=y @@ -763,6 +773,7 @@ CONFIG_MTD_COMPLEX_MAPPINGS=y # CONFIG_MTD_PHYSMAP is not set CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_PCI is not set +# CONFIG_MTD_GPIO_ADDR is not set # CONFIG_MTD_INTEL_VR_NOR is not set # CONFIG_MTD_PLATRAM is not set @@ -857,6 +868,7 @@ CONFIG_SCSI_SRP_ATTRS=m CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set CONFIG_BLK_DEV_3W_XXXX_RAID=m CONFIG_SCSI_3W_9XXX=m CONFIG_SCSI_ACARD=m @@ -912,7 +924,9 @@ CONFIG_SCSI_LPFC=m # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -982,7 +996,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -1010,10 +1026,7 @@ CONFIG_MV643XX_ETH=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -1145,6 +1158,7 @@ CONFIG_MAX_RAW_DEVS=8192 CONFIG_DEVPORT=y CONFIG_I2C=m CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=m CONFIG_I2C_HELPER_AUTO=y @@ -1200,9 +1214,6 @@ CONFIG_I2C_MV64XXX=m # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -CONFIG_SENSORS_PCF8574=m -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1220,6 +1231,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=m CONFIG_HWMON_VID=m +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set CONFIG_SENSORS_ADM1021=m @@ -1269,6 +1285,7 @@ CONFIG_SENSORS_SMSC47B397=m # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set CONFIG_SENSORS_VIA686A=m # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1280,7 +1297,6 @@ CONFIG_SENSORS_W83L785TS=m # CONFIG_SENSORS_W83L786NG is not set CONFIG_SENSORS_W83627HF=m # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1317,6 +1333,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_HTC_PASIC3 is not set # CONFIG_MFD_TMIO is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1327,6 +1344,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1378,6 +1396,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=m CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1588,6 +1607,7 @@ CONFIG_FS_POSIX_ACL=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1668,7 +1688,6 @@ CONFIG_VXFS_FS=m # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1770,7 +1789,7 @@ CONFIG_BINARY_PRINTF=y CONFIG_BITREVERSE=y CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC_CCITT=m -# CONFIG_CRC16 is not set +CONFIG_CRC16=m CONFIG_CRC_T10DIF=m CONFIG_CRC_ITU_T=m CONFIG_CRC32=y @@ -1797,6 +1816,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -1814,6 +1834,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set CONFIG_DEBUG_SPINLOCK=y @@ -1834,11 +1855,13 @@ CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_KPROBES_SANITY_TEST is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_LKDTM is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set @@ -1852,6 +1875,7 @@ CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_RING_BUFFER=y CONFIG_EVENT_TRACING=y CONFIG_CONTEXT_SWITCH_TRACER=y +CONFIG_RING_BUFFER_ALLOW_SWAP=y CONFIG_TRACING=y CONFIG_TRACING_SUPPORT=y CONFIG_FTRACE=y @@ -1869,6 +1893,7 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_RING_BUFFER_BENCHMARK is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set @@ -1899,6 +1924,7 @@ CONFIG_SECURITY_NETWORK=y # CONFIG_SECURITY_NETWORK_XFRM is not set # CONFIG_SECURITY_PATH is not set # CONFIG_SECURITY_FILE_CAPABILITIES is not set +CONFIG_LSM_MMAP_MIN_ADDR=65536 CONFIG_SECURITY_SELINUX=y CONFIG_SECURITY_SELINUX_BOOTPARAM=y CONFIG_SECURITY_SELINUX_BOOTPARAM_VALUE=1 @@ -1913,7 +1939,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=m @@ -1956,11 +1981,13 @@ CONFIG_CRYPTO_ECB=m # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set CONFIG_CRYPTO_MD4=m CONFIG_CRYPTO_MD5=y CONFIG_CRYPTO_MICHAEL_MIC=m diff --git a/arch/powerpc/configs/ep8248e_defconfig b/arch/powerpc/configs/ep8248e_defconfig index 0aa5b43ffeb2..ef5edc7203f5 100644 --- a/arch/powerpc/configs/ep8248e_defconfig +++ b/arch/powerpc/configs/ep8248e_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:49 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:06 2009 # # CONFIG_PPC64 is not set @@ -34,6 +34,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -82,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -116,28 +118,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -150,6 +153,7 @@ CONFIG_BASE_SMALL=0 # CONFIG_MODULES is not set CONFIG_BLOCK=y CONFIG_LBDAF=y +CONFIG_BLK_DEV_BSG=y # CONFIG_BLK_DEV_INTEGRITY is not set # @@ -233,6 +237,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_FLATMEM=y @@ -246,6 +251,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -394,6 +400,7 @@ CONFIG_NETFILTER_ADVANCED=y # CONFIG_BT is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -401,7 +408,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set @@ -413,6 +419,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -600,7 +607,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FCC=y @@ -648,10 +657,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -736,15 +742,19 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -767,6 +777,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -968,6 +979,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -998,10 +1010,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1024,6 +1038,7 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1052,7 +1067,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1094,6 +1108,7 @@ CONFIG_CRYPTO_PCBC=y # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/ep88xc_defconfig b/arch/powerpc/configs/ep88xc_defconfig index 2c292e25cc01..73ef9be41280 100644 --- a/arch/powerpc/configs/ep88xc_defconfig +++ b/arch/powerpc/configs/ep88xc_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:49 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:07 2009 # # CONFIG_PPC64 is not set @@ -16,6 +16,7 @@ CONFIG_PPC_8xx=y # CONFIG_E200 is not set CONFIG_8xx=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y # CONFIG_PPC_MM_SLICES is not set CONFIG_NOT_COHERENT_CACHE=y CONFIG_PPC32=y @@ -29,6 +30,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -77,11 +79,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -115,28 +118,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -234,10 +238,10 @@ CONFIG_BINFMT_ELF=y CONFIG_8XX_MINIMAL_FPEMU=y # CONFIG_IOMMU_HELPER is not set # CONFIG_SWIOTLB is not set -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -255,6 +259,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -337,6 +342,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -366,6 +372,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -373,7 +380,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -386,6 +392,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -529,16 +536,15 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FEC=y CONFIG_FS_ENET_MDIO_FEC=y # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -611,7 +617,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -672,6 +677,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set @@ -731,7 +737,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -803,6 +808,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -820,6 +826,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set # CONFIG_DEBUG_LOCK_ALLOC is not set @@ -836,10 +843,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -861,10 +870,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 diff --git a/arch/powerpc/configs/linkstation_defconfig b/arch/powerpc/configs/linkstation_defconfig index 45671e7dd2c7..63c3e8de8f16 100644 --- a/arch/powerpc/configs/linkstation_defconfig +++ b/arch/powerpc/configs/linkstation_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:50 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:08 2009 # # CONFIG_PPC64 is not set @@ -34,6 +34,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -83,11 +84,12 @@ CONFIG_POSIX_MQUEUE_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -131,22 +133,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_COMPAT_BRK is not set # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -154,11 +155,13 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling # -# CONFIG_SLOW_WORK is not set +CONFIG_SLOW_WORK=y # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y @@ -258,6 +261,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -275,6 +279,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -482,6 +487,7 @@ CONFIG_IP_NF_ARPFILTER=m CONFIG_IP_NF_ARP_MANGLE=m # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -511,6 +517,7 @@ CONFIG_IP_NF_ARP_MANGLE=m # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y CONFIG_WIRELESS_EXT=y CONFIG_WIRELESS_EXT_SYSFS=y @@ -519,7 +526,6 @@ CONFIG_WIRELESS_EXT_SYSFS=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -532,6 +538,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -543,9 +550,9 @@ CONFIG_EXTRA_FIRMWARE="" # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y CONFIG_MTD_OF_PARTS=y @@ -711,6 +718,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -750,11 +758,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -777,6 +788,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -804,6 +816,7 @@ CONFIG_PATA_IT821X=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -870,7 +883,9 @@ CONFIG_TULIP_MMIO=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -918,10 +933,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -1043,6 +1055,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1097,9 +1110,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1117,6 +1127,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1166,6 +1181,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1177,9 +1193,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1198,6 +1212,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1208,6 +1223,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1227,7 +1243,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=m -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1271,6 +1286,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1500,6 +1516,7 @@ CONFIG_XFS_FS=m # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1567,7 +1584,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1681,6 +1697,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1698,6 +1715,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1716,10 +1734,12 @@ CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1742,6 +1762,7 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set @@ -1771,7 +1792,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1813,11 +1833,13 @@ CONFIG_CRYPTO_PCBC=m # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set CONFIG_CRYPTO_MD4=m CONFIG_CRYPTO_MD5=y CONFIG_CRYPTO_MICHAEL_MIC=m diff --git a/arch/powerpc/configs/mgcoge_defconfig b/arch/powerpc/configs/mgcoge_defconfig index 30b68bfacebf..520b04a0def9 100644 --- a/arch/powerpc/configs/mgcoge_defconfig +++ b/arch/powerpc/configs/mgcoge_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc5 -# Fri Aug 7 08:19:15 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:09 2009 # # CONFIG_PPC64 is not set @@ -34,6 +34,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -84,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -123,28 +125,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -247,6 +250,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_FLATMEM=y @@ -260,6 +264,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -390,6 +395,7 @@ CONFIG_NETFILTER_ADVANCED=y # CONFIG_BT is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -397,7 +403,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set @@ -409,6 +414,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -608,7 +614,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y CONFIG_FS_ENET_HAS_SCC=y CONFIG_FS_ENET_HAS_FCC=y @@ -616,10 +624,7 @@ CONFIG_FS_ENET_MDIO_FCC=y # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -685,6 +690,7 @@ CONFIG_HW_RANDOM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -740,7 +746,6 @@ CONFIG_I2C_CPM=y # # Miscellaneous I2C Chip support # -# CONFIG_PCF8575 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set @@ -771,15 +776,19 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -799,6 +808,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -809,6 +819,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1022,6 +1033,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -1052,10 +1064,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1079,6 +1093,7 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1109,7 +1124,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1151,6 +1165,7 @@ CONFIG_CRYPTO_PCBC=y # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/mgsuvd_defconfig b/arch/powerpc/configs/mgsuvd_defconfig index 1ae85a3b2942..43c3c4fcdce3 100644 --- a/arch/powerpc/configs/mgsuvd_defconfig +++ b/arch/powerpc/configs/mgsuvd_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:52 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:10 2009 # # CONFIG_PPC64 is not set @@ -16,6 +16,7 @@ CONFIG_PPC_8xx=y # CONFIG_E200 is not set CONFIG_8xx=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y # CONFIG_PPC_MM_SLICES is not set CONFIG_NOT_COHERENT_CACHE=y CONFIG_PPC32=y @@ -29,6 +30,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -76,11 +78,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=17 CONFIG_GROUP_SCHED=y @@ -117,27 +120,28 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set # CONFIG_VM_EVENT_COUNTERS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -237,10 +241,10 @@ CONFIG_BINFMT_ELF=y CONFIG_MATH_EMULATION=y # CONFIG_IOMMU_HELPER is not set # CONFIG_SWIOTLB is not set -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -258,6 +262,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -344,6 +349,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -373,6 +379,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -380,7 +387,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -553,16 +559,15 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y CONFIG_FS_ENET_HAS_SCC=y # CONFIG_FS_ENET_HAS_FEC is not set # CONFIG_FS_ENET_MDIO_FEC is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -635,7 +640,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -707,6 +711,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -776,7 +781,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -851,6 +855,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -865,6 +870,7 @@ CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -887,7 +893,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -918,11 +923,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/mpc5200_defconfig b/arch/powerpc/configs/mpc5200_defconfig index aaa4416660e9..523d5fe18c0e 100644 --- a/arch/powerpc/configs/mpc5200_defconfig +++ b/arch/powerpc/configs/mpc5200_defconfig @@ -1,25 +1,27 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc2 -# Mon Apr 20 11:06:25 2009 +# Linux kernel version: 2.6.32-rc4 +# Thu Oct 15 10:33:21 2009 # # CONFIG_PPC64 is not set # # Processor support # -CONFIG_6xx=y +CONFIG_PPC_BOOK3S_32=y # CONFIG_PPC_85xx is not set # CONFIG_PPC_8xx is not set # CONFIG_40x is not set # CONFIG_44x is not set # CONFIG_E200 is not set CONFIG_PPC_BOOK3S=y +CONFIG_6xx=y CONFIG_PPC_FPU=y # CONFIG_ALTIVEC is not set CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set +CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set CONFIG_PPC32=y CONFIG_WORD_SIZE=32 @@ -30,15 +32,17 @@ CONFIG_GENERIC_TIME=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y +CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_GENERIC_HWEIGHT=y -CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_FIND_NEXT_BIT=y CONFIG_GENERIC_GPIO=y # CONFIG_ARCH_NO_VIRT_TO_BUS is not set @@ -53,12 +57,14 @@ CONFIG_OF=y # CONFIG_GENERIC_TBSYNC is not set CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y +CONFIG_DTC=y CONFIG_DEFAULT_UIMAGE=y CONFIG_ARCH_SUSPEND_POSSIBLE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -79,11 +85,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 # CONFIG_GROUP_SCHED is not set @@ -103,7 +110,6 @@ CONFIG_ANON_INODES=y CONFIG_EMBEDDED=y # CONFIG_SYSCTL_SYSCALL is not set # CONFIG_KALLSYMS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y @@ -116,6 +122,13 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +# CONFIG_PERF_EVENTS is not set +# CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y @@ -124,14 +137,19 @@ CONFIG_COMPAT_BRK=y CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# # CONFIG_SLOW_WORK is not set # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y @@ -144,7 +162,7 @@ CONFIG_MODULE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBD is not set +CONFIG_LBDAF=y # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set @@ -205,7 +223,7 @@ CONFIG_RTAS_PROC=y CONFIG_PPC_BESTCOMM=y CONFIG_PPC_BESTCOMM_ATA=y CONFIG_PPC_BESTCOMM_FEC=y -# CONFIG_SIMPLE_GPIO is not set +CONFIG_SIMPLE_GPIO=y # # Kernel options @@ -229,11 +247,13 @@ CONFIG_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set # CONFIG_IOMMU_HELPER is not set +# CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -249,9 +269,10 @@ CONFIG_MIGRATION=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y -CONFIG_UNEVICTABLE_LRU=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set # CONFIG_PPC_64K_PAGES is not set @@ -265,6 +286,7 @@ CONFIG_PM=y CONFIG_PM_SLEEP=y CONFIG_SUSPEND=y CONFIG_SUSPEND_FREEZER=y +# CONFIG_PM_RUNTIME is not set CONFIG_SECCOMP=y CONFIG_ISA_DMA_API=y @@ -349,6 +371,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -363,6 +386,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set # CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set @@ -388,6 +412,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -397,9 +422,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y CONFIG_MTD_OF_PARTS=y @@ -458,6 +483,7 @@ CONFIG_MTD_PHYSMAP_OF=y # CONFIG_MTD_PMC551 is not set # CONFIG_MTD_DATAFLASH is not set # CONFIG_MTD_M25P80 is not set +# CONFIG_MTD_SST25L is not set # CONFIG_MTD_SLRAM is not set # CONFIG_MTD_PHRAM is not set # CONFIG_MTD_MTDRAM is not set @@ -493,6 +519,7 @@ CONFIG_OF_DEVICE=y CONFIG_OF_GPIO=y CONFIG_OF_I2C=y CONFIG_OF_SPI=y +CONFIG_OF_MDIO=y # CONFIG_PARPORT is not set CONFIG_BLK_DEV=y # CONFIG_BLK_DEV_FD is not set @@ -529,7 +556,9 @@ CONFIG_MISC_DEVICES=y CONFIG_EEPROM_AT24=y # CONFIG_EEPROM_AT25 is not set # CONFIG_EEPROM_LEGACY is not set +# CONFIG_EEPROM_MAX6875 is not set # CONFIG_EEPROM_93CX6 is not set +# CONFIG_CB710_CORE is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -552,10 +581,6 @@ CONFIG_BLK_DEV_SD=y # CONFIG_BLK_DEV_SR is not set CONFIG_CHR_DEV_SG=y # CONFIG_CHR_DEV_SCH is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set # CONFIG_SCSI_CONSTANTS is not set # CONFIG_SCSI_LOGGING is not set @@ -572,6 +597,8 @@ CONFIG_SCSI_WAIT_SCAN=m # CONFIG_SCSI_SRP_ATTRS is not set CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set +# CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -580,6 +607,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_AIC7XXX_OLD is not set # CONFIG_SCSI_AIC79XX is not set # CONFIG_SCSI_AIC94XX is not set +# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_DPT_I2O is not set # CONFIG_SCSI_ADVANSYS is not set # CONFIG_SCSI_ARCMSR is not set @@ -599,7 +627,6 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_IPS is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set -# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_STEX is not set # CONFIG_SCSI_SYM53C8XX_2 is not set # CONFIG_SCSI_IPR is not set @@ -611,11 +638,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -637,6 +667,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -665,6 +696,7 @@ CONFIG_PATA_MPC52xx=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -684,14 +716,17 @@ CONFIG_PATA_PLATFORM=y # # -# Enable only one of the two stacks, unless you know what you are doing +# You can enable one or both FireWire driver stacks. +# + +# +# See the help texts for more information. # # CONFIG_FIREWIRE is not set # CONFIG_IEEE1394 is not set # CONFIG_I2O is not set # CONFIG_MACINTOSH_DRIVERS is not set CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -739,16 +774,17 @@ CONFIG_NET_ETHERNET=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_NET_PCI is not set # CONFIG_B44 is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851 is not set +# CONFIG_KS8851_MLL is not set CONFIG_FEC_MPC52xx=y CONFIG_FEC_MPC52xx_MDIO=y # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -854,6 +890,7 @@ CONFIG_LEGACY_PTY_COUNT=256 CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y CONFIG_I2C_ALGOBIT=y @@ -883,6 +920,7 @@ CONFIG_I2C_ALGOBIT=y # # I2C system bus drivers (mostly embedded / system-on-chip) # +# CONFIG_I2C_DESIGNWARE is not set # CONFIG_I2C_GPIO is not set CONFIG_I2C_MPC=y # CONFIG_I2C_OCORES is not set @@ -910,10 +948,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -935,6 +969,11 @@ CONFIG_SPI_MPC52xx_PSC=m # CONFIG_SPI_SPIDEV=m # CONFIG_SPI_TLE62X0 is not set + +# +# PPS support +# +# CONFIG_PPS is not set CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y CONFIG_ARCH_REQUIRE_GPIOLIB=y CONFIG_GPIOLIB=y @@ -957,16 +996,27 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # # CONFIG_GPIO_MAX7301 is not set # CONFIG_GPIO_MCP23S08 is not set +# CONFIG_GPIO_MC33880 is not set + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADCXX is not set @@ -1019,6 +1069,8 @@ CONFIG_HWMON=y # CONFIG_SENSORS_SMSC47B397 is not set # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set +# CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1031,9 +1083,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set # CONFIG_SENSORS_LIS3_SPI is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1073,31 +1123,20 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set +# CONFIG_MFD_MC13783 is not set +# CONFIG_AB3100_CORE is not set +# CONFIG_EZX_PCAP is not set # CONFIG_REGULATOR is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -CONFIG_DAB=y -# CONFIG_USB_DABUSB is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y CONFIG_DRM=y # CONFIG_DRM_TDFX is not set # CONFIG_DRM_R128 is not set @@ -1167,6 +1206,7 @@ CONFIG_FB_RADEON_BACKLIGHT=y # CONFIG_FB_BROADSHEET is not set CONFIG_BACKLIGHT_LCD_SUPPORT=y CONFIG_LCD_CLASS_DEVICE=m +# CONFIG_LCD_LMS283GF05 is not set # CONFIG_LCD_LTV350QV is not set # CONFIG_LCD_ILI9320 is not set # CONFIG_LCD_TDO24M is not set @@ -1198,7 +1238,6 @@ CONFIG_LOGO_LINUX_CLUT224=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1217,10 +1256,11 @@ CONFIG_HID_BELKIN=y CONFIG_HID_CHERRY=y # CONFIG_HID_CHICONY is not set CONFIG_HID_CYPRESS=y -# CONFIG_DRAGONRISE_FF is not set +# CONFIG_HID_DRAGONRISE is not set CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set # CONFIG_HID_GYRATION is not set +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set # CONFIG_HID_LOGITECH is not set # CONFIG_HID_MICROSOFT is not set @@ -1231,10 +1271,11 @@ CONFIG_HID_EZKEY=y # CONFIG_HID_SAMSUNG is not set # CONFIG_HID_SONY is not set # CONFIG_HID_SUNPLUS is not set -# CONFIG_GREENASIA_FF is not set +# CONFIG_HID_GREENASIA is not set +# CONFIG_HID_SMARTJOYPLUS is not set # CONFIG_HID_TOPSEED is not set -# CONFIG_THRUSTMASTER_FF is not set -# CONFIG_ZEROPLUS_FF is not set +# CONFIG_HID_THRUSTMASTER is not set +# CONFIG_HID_ZEROPLUS is not set CONFIG_USB_SUPPORT=y CONFIG_USB_ARCH_HAS_HCD=y CONFIG_USB_ARCH_HAS_OHCI=y @@ -1261,15 +1302,17 @@ CONFIG_USB_MON=y # USB Host Controller Drivers # # CONFIG_USB_C67X00_HCD is not set +# CONFIG_USB_XHCI_HCD is not set # CONFIG_USB_EHCI_HCD is not set # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_SOC=y -CONFIG_USB_OHCI_HCD_PPC_OF=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set +CONFIG_USB_OHCI_HCD_PPC_OF=y CONFIG_USB_OHCI_HCD_PCI=y CONFIG_USB_OHCI_BIG_ENDIAN_DESC=y CONFIG_USB_OHCI_BIG_ENDIAN_MMIO=y @@ -1400,6 +1443,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_S35390A is not set # CONFIG_RTC_DRV_FM3130 is not set # CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set # # SPI RTC drivers @@ -1411,6 +1455,7 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_R9701 is not set # CONFIG_RTC_DRV_RS5C348 is not set # CONFIG_RTC_DRV_DS3234 is not set +# CONFIG_RTC_DRV_PCF2123 is not set # # Platform RTC drivers @@ -1434,6 +1479,10 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_DMADEVICES is not set # CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set + +# +# TI VLYNQ +# # CONFIG_STAGING is not set # @@ -1453,10 +1502,13 @@ CONFIG_FS_MBCACHE=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set # CONFIG_FS_POSIX_ACL is not set -CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -1533,12 +1585,12 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y # CONFIG_NFS_V3_ACL is not set CONFIG_NFS_V4=y +# CONFIG_NFS_V4_1 is not set CONFIG_ROOT_NFS=y # CONFIG_NFSD is not set CONFIG_LOCKD=y @@ -1624,6 +1676,7 @@ CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y CONFIG_NLATTR=y +CONFIG_GENERIC_ATOMIC64=y # # Kernel hacking @@ -1633,6 +1686,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1650,10 +1704,14 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set +# CONFIG_DEBUG_LOCK_ALLOC is not set +# CONFIG_PROVE_LOCKING is not set +# CONFIG_LOCK_STAT is not set # CONFIG_DEBUG_SPINLOCK_SLEEP is not set # CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set # CONFIG_DEBUG_KOBJECT is not set @@ -1665,11 +1723,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set -# CONFIG_BOOT_PRINTK_DELAY is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -1678,23 +1737,25 @@ CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y - -# -# Tracers -# +CONFIG_FTRACE=y # CONFIG_FUNCTION_TRACER is not set +# CONFIG_IRQSOFF_TRACER is not set # CONFIG_SCHED_TRACER is not set -# CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set +# CONFIG_ENABLE_DEFAULT_TRACERS is not set # CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set +CONFIG_BRANCH_PROFILE_NONE=y +# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set +# CONFIG_PROFILE_ALL_BRANCHES is not set # CONFIG_STACK_TRACER is not set # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_DEBUG_STACKOVERFLOW is not set # CONFIG_DEBUG_STACK_USAGE is not set @@ -1719,7 +1780,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1761,11 +1821,13 @@ CONFIG_CRYPTO_CBC=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/mpc7448_hpc2_defconfig b/arch/powerpc/configs/mpc7448_hpc2_defconfig index f23428c3b34e..d8b364a45944 100644 --- a/arch/powerpc/configs/mpc7448_hpc2_defconfig +++ b/arch/powerpc/configs/mpc7448_hpc2_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:53 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:10 2009 # # CONFIG_PPC64 is not set @@ -34,6 +34,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -82,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -123,28 +125,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -241,6 +244,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -258,6 +262,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -350,6 +355,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -379,6 +385,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -386,7 +393,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -399,6 +405,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -478,6 +485,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -517,11 +525,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -543,6 +554,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -570,6 +582,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -666,9 +679,11 @@ CONFIG_8139TOO=y # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -715,10 +730,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -822,6 +834,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_I5K_AMB is not set # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set @@ -836,9 +853,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT8231 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -861,6 +876,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -874,7 +890,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -939,6 +954,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -997,7 +1013,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -1069,6 +1084,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1086,6 +1102,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1107,7 +1124,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1138,11 +1154,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/mpc8272_ads_defconfig b/arch/powerpc/configs/mpc8272_ads_defconfig index 02716f72db6f..00fad81b6fce 100644 --- a/arch/powerpc/configs/mpc8272_ads_defconfig +++ b/arch/powerpc/configs/mpc8272_ads_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:54 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:11 2009 # # CONFIG_PPC64 is not set @@ -34,6 +34,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -82,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -116,29 +118,30 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -151,6 +154,7 @@ CONFIG_BASE_SMALL=0 # CONFIG_MODULES is not set CONFIG_BLOCK=y CONFIG_LBDAF=y +CONFIG_BLK_DEV_BSG=y # CONFIG_BLK_DEV_INTEGRITY is not set # @@ -236,6 +240,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_FLATMEM=y @@ -249,6 +254,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -397,6 +403,7 @@ CONFIG_NETFILTER_ADVANCED=y # CONFIG_BT is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -404,7 +411,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set @@ -416,6 +422,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -477,7 +484,6 @@ CONFIG_MTD_CFI_UTIL=y # CONFIG_MTD_COMPLEX_MAPPINGS is not set # CONFIG_MTD_PHYSMAP is not set CONFIG_MTD_PHYSMAP_OF=y -# CONFIG_MTD_SBC8240 is not set # CONFIG_MTD_INTEL_VR_NOR is not set # CONFIG_MTD_PLATRAM is not set @@ -604,7 +610,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FCC=y @@ -652,10 +660,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -704,6 +709,7 @@ CONFIG_KEYBOARD_ATKBD=y # CONFIG_KEYBOARD_GPIO is not set # CONFIG_KEYBOARD_MATRIX is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set # CONFIG_KEYBOARD_SUNKBD is not set # CONFIG_KEYBOARD_XTKBD is not set @@ -714,6 +720,7 @@ CONFIG_MOUSE_PS2_LOGIPS2PP=y CONFIG_MOUSE_PS2_SYNAPTICS=y CONFIG_MOUSE_PS2_TRACKPOINT=y # CONFIG_MOUSE_PS2_ELANTECH is not set +# CONFIG_MOUSE_PS2_SENTELIC is not set # CONFIG_MOUSE_PS2_TOUCHKIT is not set # CONFIG_MOUSE_SERIAL is not set # CONFIG_MOUSE_VSXXXAA is not set @@ -793,15 +800,19 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -824,6 +835,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -1032,6 +1044,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1067,10 +1080,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1093,6 +1108,7 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1121,7 +1137,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1163,6 +1178,7 @@ CONFIG_CRYPTO_PCBC=y # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/mpc83xx_defconfig b/arch/powerpc/configs/mpc83xx_defconfig index 4a96cb6925b4..64dff21516cb 100644 --- a/arch/powerpc/configs/mpc83xx_defconfig +++ b/arch/powerpc/configs/mpc83xx_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:55 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:12 2009 # # CONFIG_PPC64 is not set @@ -35,6 +35,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -86,11 +87,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -127,21 +129,20 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y CONFIG_SLAB=y # CONFIG_SLUB is not set # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -149,6 +150,8 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -263,6 +266,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -280,6 +284,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -343,7 +348,8 @@ CONFIG_XFRM_USER=m # CONFIG_XFRM_SUB_POLICY is not set # CONFIG_XFRM_MIGRATE is not set # CONFIG_XFRM_STATISTICS is not set -# CONFIG_NET_KEY is not set +CONFIG_NET_KEY=y +# CONFIG_NET_KEY_MIGRATE is not set CONFIG_INET=y CONFIG_IP_MULTICAST=y # CONFIG_IP_ADVANCED_ROUTER is not set @@ -358,7 +364,7 @@ CONFIG_IP_PNP_BOOTP=y # CONFIG_ARPD is not set CONFIG_SYN_COOKIES=y # CONFIG_INET_AH is not set -# CONFIG_INET_ESP is not set +CONFIG_INET_ESP=y # CONFIG_INET_IPCOMP is not set # CONFIG_INET_XFRM_TUNNEL is not set # CONFIG_INET_TUNNEL is not set @@ -377,6 +383,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -406,6 +413,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -413,7 +421,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -426,6 +433,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -433,9 +441,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set CONFIG_MTD_OF_PARTS=y @@ -608,6 +616,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -647,11 +656,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -674,6 +686,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -701,6 +714,7 @@ CONFIG_ATA_SFF=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -777,7 +791,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -800,7 +816,6 @@ CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y CONFIG_GIANFAR=y CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set @@ -828,10 +843,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -935,6 +947,7 @@ CONFIG_GEN_RTC=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -990,9 +1003,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1025,14 +1035,24 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1083,6 +1103,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1094,9 +1115,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set CONFIG_WATCHDOG=y # CONFIG_WATCHDOG_NOWAYOUT is not set @@ -1135,6 +1154,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1145,6 +1165,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=m @@ -1158,7 +1179,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=m # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1181,6 +1201,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1233,6 +1254,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set # CONFIG_USB_OHCI_HCD is not set # CONFIG_USB_UHCI_HCD is not set # CONFIG_USB_FHCI_HCD is not set @@ -1291,6 +1313,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_LD is not set # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set @@ -1338,6 +1361,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1397,7 +1421,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1514,6 +1537,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1529,6 +1553,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1550,7 +1575,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=y @@ -1591,13 +1615,15 @@ CONFIG_CRYPTO_PCBC=m # # Hash modes # -# CONFIG_CRYPTO_HMAC is not set +CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set @@ -1605,16 +1631,16 @@ CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_RMD160 is not set # CONFIG_CRYPTO_RMD256 is not set # CONFIG_CRYPTO_RMD320 is not set -# CONFIG_CRYPTO_SHA1 is not set -# CONFIG_CRYPTO_SHA256 is not set -# CONFIG_CRYPTO_SHA512 is not set +CONFIG_CRYPTO_SHA1=y +CONFIG_CRYPTO_SHA256=y +CONFIG_CRYPTO_SHA512=y # CONFIG_CRYPTO_TGR192 is not set # CONFIG_CRYPTO_WP512 is not set # # Ciphers # -# CONFIG_CRYPTO_AES is not set +CONFIG_CRYPTO_AES=y # CONFIG_CRYPTO_ANUBIS is not set # CONFIG_CRYPTO_ARC4 is not set # CONFIG_CRYPTO_BLOWFISH is not set diff --git a/arch/powerpc/configs/mpc85xx_defconfig b/arch/powerpc/configs/mpc85xx_defconfig index ee6acc6557f8..a12e7ba87a43 100644 --- a/arch/powerpc/configs/mpc85xx_defconfig +++ b/arch/powerpc/configs/mpc85xx_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:55 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:25:20 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set # CONFIG_SMP is not set @@ -36,6 +37,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -88,11 +90,12 @@ CONFIG_AUDIT=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -131,22 +134,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -154,7 +156,9 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -189,6 +193,7 @@ CONFIG_DEFAULT_CFQ=y # CONFIG_DEFAULT_NOOP is not set CONFIG_DEFAULT_IOSCHED="cfq" # CONFIG_FREEZER is not set +CONFIG_PPC_MSI_BITMAP=y # # Platform support @@ -206,7 +211,7 @@ CONFIG_MPC85xx_DS=y CONFIG_MPC85xx_RDB=y CONFIG_SOCRATES=y CONFIG_KSI8560=y -# CONFIG_XES_MPC85xx is not set +CONFIG_XES_MPC85xx=y CONFIG_STX_GP3=y CONFIG_TQM8540=y CONFIG_TQM8541=y @@ -259,10 +264,10 @@ CONFIG_BINFMT_MISC=m CONFIG_MATH_EMULATION=y CONFIG_IOMMU_HELPER=y CONFIG_SWIOTLB=y -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -280,6 +285,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -307,7 +313,7 @@ CONFIG_PCI_DOMAINS=y CONFIG_PCI_SYSCALL=y # CONFIG_PCIEPORTBUS is not set CONFIG_ARCH_SUPPORTS_MSI=y -# CONFIG_PCI_MSI is not set +CONFIG_PCI_MSI=y # CONFIG_PCI_LEGACY is not set # CONFIG_PCI_DEBUG is not set # CONFIG_PCI_STUB is not set @@ -315,7 +321,8 @@ CONFIG_ARCH_SUPPORTS_MSI=y # CONFIG_PCCARD is not set # CONFIG_HOTPLUG_PCI is not set CONFIG_HAS_RAPIDIO=y -# CONFIG_RAPIDIO is not set +CONFIG_RAPIDIO=y +CONFIG_RAPIDIO_DISC_TIMEOUT=30 # # Advanced setup @@ -345,7 +352,7 @@ CONFIG_XFRM_USER=y # CONFIG_XFRM_SUB_POLICY is not set # CONFIG_XFRM_MIGRATE is not set # CONFIG_XFRM_STATISTICS is not set -CONFIG_NET_KEY=m +CONFIG_NET_KEY=y # CONFIG_NET_KEY_MIGRATE is not set CONFIG_INET=y CONFIG_IP_MULTICAST=y @@ -369,12 +376,12 @@ CONFIG_IP_PIMSM_V2=y CONFIG_ARPD=y # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set -# CONFIG_INET_ESP is not set +CONFIG_INET_ESP=y # CONFIG_INET_IPCOMP is not set # CONFIG_INET_XFRM_TUNNEL is not set CONFIG_INET_TUNNEL=y -# CONFIG_INET_XFRM_MODE_TRANSPORT is not set -# CONFIG_INET_XFRM_MODE_TUNNEL is not set +CONFIG_INET_XFRM_MODE_TRANSPORT=y +CONFIG_INET_XFRM_MODE_TUNNEL=y # CONFIG_INET_XFRM_MODE_BEET is not set # CONFIG_INET_LRO is not set CONFIG_INET_DIAG=y @@ -411,6 +418,7 @@ CONFIG_IP_SCTP=m # CONFIG_SCTP_HMAC_NONE is not set # CONFIG_SCTP_HMAC_SHA1 is not set CONFIG_SCTP_HMAC_MD5=y +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -441,6 +449,7 @@ CONFIG_SCTP_HMAC_MD5=y CONFIG_FIB_RULES=y CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -448,7 +457,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -461,6 +469,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -554,6 +563,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -593,11 +603,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_SATA_AHCI=y # CONFIG_SATA_SIL24 is not set @@ -620,6 +633,7 @@ CONFIG_ATA_SFF=y CONFIG_PATA_ALI=y # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -647,6 +661,7 @@ CONFIG_PATA_ALI=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -723,7 +738,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y CONFIG_FS_ENET_HAS_SCC=y CONFIG_FS_ENET_HAS_FCC=y @@ -750,7 +767,6 @@ CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y CONFIG_GIANFAR=y CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set @@ -778,10 +794,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -798,6 +811,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_USB_RTL8150 is not set # CONFIG_USB_USBNET is not set # CONFIG_WAN is not set +# CONFIG_RIONET is not set # CONFIG_FDDI is not set # CONFIG_HIPPI is not set # CONFIG_PPP is not set @@ -898,6 +912,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y # CONFIG_I2C_CHARDEV is not set CONFIG_I2C_HELPER_AUTO=y @@ -955,9 +970,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -991,15 +1003,19 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1020,6 +1036,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1030,6 +1047,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -1049,6 +1067,7 @@ CONFIG_VGA_CONSOLE=y CONFIG_DUMMY_CONSOLE=y CONFIG_SOUND=y CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y CONFIG_SND=y CONFIG_SND_TIMER=y CONFIG_SND_PCM=y @@ -1152,7 +1171,6 @@ CONFIG_SND_USB=y CONFIG_AC97_BUS=y CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1175,6 +1193,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1227,6 +1246,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y CONFIG_USB_OHCI_HCD_PPC_OF_LE=y @@ -1241,7 +1261,6 @@ CONFIG_USB_OHCI_LITTLE_ENDIAN=y # CONFIG_USB_R8A66597_HCD is not set # CONFIG_USB_WHCI_HCD is not set # CONFIG_USB_HWA_HCD is not set -# CONFIG_USB_MUSB_HDRC is not set # # USB Device Class drivers @@ -1429,6 +1448,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1499,7 +1519,6 @@ CONFIG_SYSV_FS=m CONFIG_UFS_FS=m # CONFIG_UFS_FS_WRITE is not set # CONFIG_UFS_DEBUG is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1620,6 +1639,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -1637,6 +1657,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1656,10 +1677,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1683,10 +1706,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1714,7 +1737,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=y @@ -1757,11 +1779,13 @@ CONFIG_CRYPTO_PCBC=m # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set @@ -1769,16 +1793,16 @@ CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_RMD160 is not set # CONFIG_CRYPTO_RMD256 is not set # CONFIG_CRYPTO_RMD320 is not set -CONFIG_CRYPTO_SHA1=m -# CONFIG_CRYPTO_SHA256 is not set -# CONFIG_CRYPTO_SHA512 is not set +CONFIG_CRYPTO_SHA1=y +CONFIG_CRYPTO_SHA256=y +CONFIG_CRYPTO_SHA512=y # CONFIG_CRYPTO_TGR192 is not set # CONFIG_CRYPTO_WP512 is not set # # Ciphers # -# CONFIG_CRYPTO_AES is not set +CONFIG_CRYPTO_AES=y # CONFIG_CRYPTO_ANUBIS is not set # CONFIG_CRYPTO_ARC4 is not set # CONFIG_CRYPTO_BLOWFISH is not set diff --git a/arch/powerpc/configs/mpc85xx_smp_defconfig b/arch/powerpc/configs/mpc85xx_smp_defconfig index db082ce5a1c5..cd70b4a4ce01 100644 --- a/arch/powerpc/configs/mpc85xx_smp_defconfig +++ b/arch/powerpc/configs/mpc85xx_smp_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:56 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:26:01 2009 # # CONFIG_PPC64 is not set @@ -22,6 +22,7 @@ CONFIG_FSL_EMB_PERFMON=y # CONFIG_PHYS_64BIT is not set CONFIG_SPE=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y CONFIG_PPC_BOOK3E_MMU=y # CONFIG_PPC_MM_SLICES is not set CONFIG_SMP=y @@ -37,6 +38,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -89,11 +91,12 @@ CONFIG_AUDIT=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -132,22 +135,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -155,8 +157,10 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -192,6 +196,7 @@ CONFIG_DEFAULT_CFQ=y # CONFIG_DEFAULT_NOOP is not set CONFIG_DEFAULT_IOSCHED="cfq" # CONFIG_FREEZER is not set +CONFIG_PPC_MSI_BITMAP=y # # Platform support @@ -206,9 +211,10 @@ CONFIG_MPC85xx_CDS=y CONFIG_MPC85xx_MDS=y CONFIG_MPC8536_DS=y CONFIG_MPC85xx_DS=y +CONFIG_MPC85xx_RDB=y CONFIG_SOCRATES=y CONFIG_KSI8560=y -# CONFIG_XES_MPC85xx is not set +CONFIG_XES_MPC85xx=y CONFIG_STX_GP3=y CONFIG_TQM8540=y CONFIG_TQM8541=y @@ -261,11 +267,11 @@ CONFIG_BINFMT_MISC=m CONFIG_MATH_EMULATION=y CONFIG_IOMMU_HELPER=y CONFIG_SWIOTLB=y -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_IRQ_ALL_CPUS is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -283,6 +289,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -310,7 +317,7 @@ CONFIG_PCI_DOMAINS=y CONFIG_PCI_SYSCALL=y # CONFIG_PCIEPORTBUS is not set CONFIG_ARCH_SUPPORTS_MSI=y -# CONFIG_PCI_MSI is not set +CONFIG_PCI_MSI=y # CONFIG_PCI_LEGACY is not set # CONFIG_PCI_DEBUG is not set # CONFIG_PCI_STUB is not set @@ -318,7 +325,8 @@ CONFIG_ARCH_SUPPORTS_MSI=y # CONFIG_PCCARD is not set # CONFIG_HOTPLUG_PCI is not set CONFIG_HAS_RAPIDIO=y -# CONFIG_RAPIDIO is not set +CONFIG_RAPIDIO=y +CONFIG_RAPIDIO_DISC_TIMEOUT=30 # # Advanced setup @@ -348,7 +356,7 @@ CONFIG_XFRM_USER=y # CONFIG_XFRM_SUB_POLICY is not set # CONFIG_XFRM_MIGRATE is not set # CONFIG_XFRM_STATISTICS is not set -CONFIG_NET_KEY=m +CONFIG_NET_KEY=y # CONFIG_NET_KEY_MIGRATE is not set CONFIG_INET=y CONFIG_IP_MULTICAST=y @@ -372,12 +380,12 @@ CONFIG_IP_PIMSM_V2=y CONFIG_ARPD=y # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set -# CONFIG_INET_ESP is not set +CONFIG_INET_ESP=y # CONFIG_INET_IPCOMP is not set # CONFIG_INET_XFRM_TUNNEL is not set CONFIG_INET_TUNNEL=y -# CONFIG_INET_XFRM_MODE_TRANSPORT is not set -# CONFIG_INET_XFRM_MODE_TUNNEL is not set +CONFIG_INET_XFRM_MODE_TRANSPORT=y +CONFIG_INET_XFRM_MODE_TUNNEL=y # CONFIG_INET_XFRM_MODE_BEET is not set # CONFIG_INET_LRO is not set CONFIG_INET_DIAG=y @@ -414,6 +422,7 @@ CONFIG_IP_SCTP=m # CONFIG_SCTP_HMAC_NONE is not set # CONFIG_SCTP_HMAC_SHA1 is not set CONFIG_SCTP_HMAC_MD5=y +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -444,6 +453,7 @@ CONFIG_SCTP_HMAC_MD5=y CONFIG_FIB_RULES=y CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -451,7 +461,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -464,6 +473,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -557,6 +567,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -596,11 +607,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_SATA_AHCI=y # CONFIG_SATA_SIL24 is not set @@ -623,6 +637,7 @@ CONFIG_ATA_SFF=y CONFIG_PATA_ALI=y # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -650,6 +665,7 @@ CONFIG_PATA_ALI=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -726,7 +742,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y CONFIG_FS_ENET_HAS_SCC=y CONFIG_FS_ENET_HAS_FCC=y @@ -753,7 +771,6 @@ CONFIG_NETDEV_1000=y CONFIG_FSL_PQ_MDIO=y CONFIG_GIANFAR=y CONFIG_UCC_GETH=y -# CONFIG_UGETH_MAGIC_PACKET is not set # CONFIG_UGETH_TX_ON_DEMAND is not set # CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set @@ -781,10 +798,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -801,6 +815,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_USB_RTL8150 is not set # CONFIG_USB_USBNET is not set # CONFIG_WAN is not set +# CONFIG_RIONET is not set # CONFIG_FDDI is not set # CONFIG_HIPPI is not set # CONFIG_PPP is not set @@ -901,6 +916,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y # CONFIG_I2C_CHARDEV is not set CONFIG_I2C_HELPER_AUTO=y @@ -958,9 +974,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -994,15 +1007,19 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1023,6 +1040,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1033,6 +1051,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -1052,6 +1071,7 @@ CONFIG_VGA_CONSOLE=y CONFIG_DUMMY_CONSOLE=y CONFIG_SOUND=y CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y CONFIG_SND=y CONFIG_SND_TIMER=y CONFIG_SND_PCM=y @@ -1155,7 +1175,6 @@ CONFIG_SND_USB=y CONFIG_AC97_BUS=y CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1178,6 +1197,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1230,6 +1250,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y CONFIG_USB_OHCI_HCD_PPC_OF_LE=y @@ -1244,7 +1265,6 @@ CONFIG_USB_OHCI_LITTLE_ENDIAN=y # CONFIG_USB_R8A66597_HCD is not set # CONFIG_USB_WHCI_HCD is not set # CONFIG_USB_HWA_HCD is not set -# CONFIG_USB_MUSB_HDRC is not set # # USB Device Class drivers @@ -1432,6 +1452,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1502,7 +1523,6 @@ CONFIG_SYSV_FS=m CONFIG_UFS_FS=m # CONFIG_UFS_FS_WRITE is not set # CONFIG_UFS_DEBUG is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1623,6 +1643,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set @@ -1640,6 +1661,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1659,10 +1681,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1686,10 +1710,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1717,7 +1741,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=y @@ -1760,11 +1783,13 @@ CONFIG_CRYPTO_PCBC=m # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set @@ -1772,16 +1797,16 @@ CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_RMD160 is not set # CONFIG_CRYPTO_RMD256 is not set # CONFIG_CRYPTO_RMD320 is not set -CONFIG_CRYPTO_SHA1=m -# CONFIG_CRYPTO_SHA256 is not set -# CONFIG_CRYPTO_SHA512 is not set +CONFIG_CRYPTO_SHA1=y +CONFIG_CRYPTO_SHA256=y +CONFIG_CRYPTO_SHA512=y # CONFIG_CRYPTO_TGR192 is not set # CONFIG_CRYPTO_WP512 is not set # # Ciphers # -# CONFIG_CRYPTO_AES is not set +CONFIG_CRYPTO_AES=y # CONFIG_CRYPTO_ANUBIS is not set # CONFIG_CRYPTO_ARC4 is not set # CONFIG_CRYPTO_BLOWFISH is not set diff --git a/arch/powerpc/configs/mpc866_ads_defconfig b/arch/powerpc/configs/mpc866_ads_defconfig index 6809b61ed3de..40d6f0568ca5 100644 --- a/arch/powerpc/configs/mpc866_ads_defconfig +++ b/arch/powerpc/configs/mpc866_ads_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:57 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:15 2009 # # CONFIG_PPC64 is not set @@ -16,6 +16,7 @@ CONFIG_PPC_8xx=y # CONFIG_E200 is not set CONFIG_8xx=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y # CONFIG_PPC_MM_SLICES is not set CONFIG_NOT_COHERENT_CACHE=y CONFIG_PPC32=y @@ -29,6 +30,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -76,11 +78,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -113,28 +116,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -233,10 +237,10 @@ CONFIG_BINFMT_ELF=y CONFIG_MATH_EMULATION=y # CONFIG_IOMMU_HELPER is not set # CONFIG_SWIOTLB is not set -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -254,6 +258,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -340,6 +345,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -369,6 +375,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -376,7 +383,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -467,6 +473,8 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y CONFIG_FS_ENET_HAS_SCC=y CONFIG_FS_ENET_HAS_FEC=y @@ -476,10 +484,7 @@ CONFIG_NETDEV_1000=y # CONFIG_GIANFAR is not set # CONFIG_MV643XX_ETH is not set CONFIG_NETDEV_10000=y - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -520,6 +525,7 @@ CONFIG_INPUT_KEYBOARD=y CONFIG_KEYBOARD_ATKBD=y # CONFIG_KEYBOARD_LKKBD is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set # CONFIG_KEYBOARD_SUNKBD is not set # CONFIG_KEYBOARD_XTKBD is not set @@ -530,6 +536,7 @@ CONFIG_MOUSE_PS2_LOGIPS2PP=y CONFIG_MOUSE_PS2_SYNAPTICS=y CONFIG_MOUSE_PS2_TRACKPOINT=y # CONFIG_MOUSE_PS2_ELANTECH is not set +# CONFIG_MOUSE_PS2_SENTELIC is not set # CONFIG_MOUSE_PS2_TOUCHKIT is not set # CONFIG_MOUSE_SERIAL is not set # CONFIG_MOUSE_VSXXXAA is not set @@ -595,6 +602,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set # CONFIG_SENSORS_IT87 is not set @@ -605,9 +617,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -641,7 +651,6 @@ CONFIG_VIDEO_OUTPUT_CONTROL=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # CONFIG_HID_PID is not set @@ -705,6 +714,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -763,7 +773,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -836,6 +845,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -851,6 +861,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -871,7 +882,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -902,11 +912,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/mpc86xx_defconfig b/arch/powerpc/configs/mpc86xx_defconfig index 0e8684a3138d..5b3abb42ae30 100644 --- a/arch/powerpc/configs/mpc86xx_defconfig +++ b/arch/powerpc/configs/mpc86xx_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:58 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:16 2009 # # CONFIG_PPC64 is not set @@ -36,6 +36,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -88,11 +89,12 @@ CONFIG_AUDIT=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -131,22 +133,21 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y @@ -154,7 +155,9 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -253,13 +256,13 @@ CONFIG_BINFMT_ELF=y CONFIG_BINFMT_MISC=m CONFIG_IOMMU_HELPER=y CONFIG_SWIOTLB=y -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set # CONFIG_IRQ_ALL_CPUS is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -277,6 +280,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -406,6 +410,7 @@ CONFIG_IP_SCTP=m # CONFIG_SCTP_HMAC_NONE is not set # CONFIG_SCTP_HMAC_SHA1 is not set CONFIG_SCTP_HMAC_MD5=y +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -436,6 +441,7 @@ CONFIG_SCTP_HMAC_MD5=y CONFIG_FIB_RULES=y CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -443,7 +449,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -456,6 +461,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -549,6 +555,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -588,11 +595,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y CONFIG_SATA_AHCI=y # CONFIG_SATA_SIL24 is not set @@ -615,6 +625,7 @@ CONFIG_ATA_SFF=y CONFIG_PATA_ALI=y # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -642,6 +653,7 @@ CONFIG_PATA_ALI=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -718,7 +730,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -766,10 +780,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -883,6 +894,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y # CONFIG_I2C_CHARDEV is not set CONFIG_I2C_HELPER_AUTO=y @@ -938,9 +950,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -974,15 +983,19 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1003,6 +1016,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1013,6 +1027,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -1032,6 +1047,7 @@ CONFIG_VGA_CONSOLE=y CONFIG_DUMMY_CONSOLE=y CONFIG_SOUND=y CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y CONFIG_SND=y CONFIG_SND_TIMER=y CONFIG_SND_PCM=y @@ -1135,7 +1151,6 @@ CONFIG_SND_USB=y CONFIG_AC97_BUS=y CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1158,6 +1173,7 @@ CONFIG_HID_CYPRESS=y CONFIG_HID_EZKEY=y # CONFIG_HID_KYE is not set CONFIG_HID_GYRATION=y +# CONFIG_HID_TWINHAN is not set # CONFIG_HID_KENSINGTON is not set CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1210,6 +1226,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y CONFIG_USB_OHCI_HCD_PPC_OF_BE=y CONFIG_USB_OHCI_HCD_PPC_OF_LE=y @@ -1389,6 +1406,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1459,7 +1477,6 @@ CONFIG_SYSV_FS=m CONFIG_UFS_FS=m # CONFIG_UFS_FS_WRITE is not set # CONFIG_UFS_DEBUG is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1577,6 +1594,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1594,6 +1612,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1613,10 +1632,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1639,10 +1660,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 @@ -1669,7 +1690,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1711,11 +1731,13 @@ CONFIG_CRYPTO_PCBC=m # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # CONFIG_CRYPTO_CRC32C=m +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/mpc885_ads_defconfig b/arch/powerpc/configs/mpc885_ads_defconfig index dbe8e869a827..1da3488a603d 100644 --- a/arch/powerpc/configs/mpc885_ads_defconfig +++ b/arch/powerpc/configs/mpc885_ads_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:31:59 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:17 2009 # # CONFIG_PPC64 is not set @@ -16,6 +16,7 @@ CONFIG_PPC_8xx=y # CONFIG_E200 is not set CONFIG_8xx=y CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_32=y # CONFIG_PPC_MM_SLICES is not set CONFIG_NOT_COHERENT_CACHE=y CONFIG_PPC32=y @@ -29,6 +30,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -77,11 +79,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -115,28 +118,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -241,10 +245,10 @@ CONFIG_BINFMT_ELF=y CONFIG_8XX_MINIMAL_FPEMU=y # CONFIG_IOMMU_HELPER is not set # CONFIG_SWIOTLB is not set -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -262,6 +266,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -344,6 +349,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -373,6 +379,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -380,7 +387,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -393,6 +399,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -540,16 +547,15 @@ CONFIG_MII=y # CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FEC=y CONFIG_FS_ENET_MDIO_FEC=y # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -622,7 +628,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -683,6 +688,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set @@ -742,7 +748,6 @@ CONFIG_CRAMFS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -814,6 +819,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -831,6 +837,7 @@ CONFIG_SCHED_DEBUG=y # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_SPINLOCK is not set # CONFIG_DEBUG_MUTEXES is not set # CONFIG_DEBUG_LOCK_ALLOC is not set @@ -847,10 +854,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set # CONFIG_DEBUG_PAGEALLOC is not set @@ -872,10 +881,10 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -# CONFIG_KMEMCHECK is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 diff --git a/arch/powerpc/configs/pasemi_defconfig b/arch/powerpc/configs/pasemi_defconfig index 4f8681cc8d77..20ba0cfff8ba 100644 --- a/arch/powerpc/configs/pasemi_defconfig +++ b/arch/powerpc/configs/pasemi_defconfig @@ -1,49 +1,58 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.26-rc3 -# Tue May 27 16:08:06 2008 +# Linux kernel version: 2.6.32-rc3 +# Tue Oct 6 10:27:18 2009 # CONFIG_PPC64=y # # Processor support # +CONFIG_PPC_BOOK3S_64=y +# CONFIG_PPC_BOOK3E_64 is not set +CONFIG_PPC_BOOK3S=y CONFIG_POWER4_ONLY=y CONFIG_POWER4=y # CONFIG_TUNE_CELL is not set CONFIG_PPC_FPU=y CONFIG_ALTIVEC=y +# CONFIG_VSX is not set CONFIG_PPC_STD_MMU=y +CONFIG_PPC_STD_MMU_64=y CONFIG_PPC_MM_SLICES=y # CONFIG_VIRT_CPU_ACCOUNTING is not set +CONFIG_PPC_HAVE_PMU_SUPPORT=y +CONFIG_PPC_PERF_CTRS=y CONFIG_SMP=y CONFIG_NR_CPUS=2 CONFIG_64BIT=y CONFIG_WORD_SIZE=64 -CONFIG_PPC_MERGE=y +CONFIG_ARCH_PHYS_ADDR_T_64BIT=y CONFIG_MMU=y CONFIG_GENERIC_CMOS_UPDATE=y CONFIG_GENERIC_TIME=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y CONFIG_HAVE_SETUP_PER_CPU_AREA=y +CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK=y CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y +CONFIG_HAVE_LATENCYTOP_SUPPORT=y CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_ARCH_HAS_ILOG2_U64=y CONFIG_GENERIC_HWEIGHT=y -CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_FIND_NEXT_BIT=y CONFIG_ARCH_NO_VIRT_TO_BUS=y CONFIG_PPC=y CONFIG_EARLY_PRINTK=y CONFIG_COMPAT=y CONFIG_SYSVIPC_COMPAT=y -CONFIG_SCHED_NO_NO_OMIT_FRAME_POINTER=y +CONFIG_SCHED_OMIT_FRAME_POINTER=y CONFIG_ARCH_MAY_HAVE_PC_FDC=y CONFIG_PPC_OF=y CONFIG_OF=y @@ -51,11 +60,14 @@ CONFIG_PPC_UDBG_16550=y # CONFIG_GENERIC_TBSYNC is not set CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y +CONFIG_DTC=y # CONFIG_DEFAULT_UIMAGE is not set # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set # CONFIG_PPC_OF_PLATFORM_PCI is not set +CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y # # General setup @@ -72,10 +84,20 @@ CONFIG_SYSVIPC_SYSCTL=y # CONFIG_BSD_PROCESS_ACCT is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set + +# +# RCU Subsystem +# +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=64 +# CONFIG_RCU_FANOUT_EXACT is not set +# CONFIG_TREE_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=17 -# CONFIG_CGROUPS is not set # CONFIG_GROUP_SCHED is not set +# CONFIG_CGROUPS is not set CONFIG_SYSFS_DEPRECATED=y CONFIG_SYSFS_DEPRECATED_V2=y # CONFIG_RELAY is not set @@ -84,13 +106,17 @@ CONFIG_NAMESPACES=y # CONFIG_IPC_NS is not set # CONFIG_USER_NS is not set # CONFIG_PID_NS is not set +# CONFIG_NET_NS is not set CONFIG_BLK_DEV_INITRD=y CONFIG_INITRAMFS_SOURCE="" +CONFIG_RD_GZIP=y +CONFIG_RD_BZIP2=y +CONFIG_RD_LZMA=y # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set CONFIG_SYSCTL=y +CONFIG_ANON_INODES=y # CONFIG_EMBEDDED is not set CONFIG_SYSCTL_SYSCALL=y -CONFIG_SYSCTL_SYSCALL_CHECK=y CONFIG_KALLSYMS=y # CONFIG_KALLSYMS_ALL is not set # CONFIG_KALLSYMS_EXTRA_PASS is not set @@ -98,32 +124,52 @@ CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y CONFIG_ELF_CORE=y -CONFIG_COMPAT_BRK=y CONFIG_BASE_FULL=y CONFIG_FUTEX=y -CONFIG_ANON_INODES=y CONFIG_EPOLL=y CONFIG_SIGNALFD=y CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y +CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +CONFIG_PERF_EVENTS=y +CONFIG_EVENT_PROFILE=y +# CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y +CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y +CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set CONFIG_PROFILING=y -# CONFIG_MARKERS is not set +CONFIG_TRACEPOINTS=y CONFIG_OPROFILE=y CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set +CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y +CONFIG_HAVE_SYSCALL_WRAPPERS=y +CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y -# CONFIG_HAVE_DMA_ATTRS is not set -CONFIG_PROC_PAGE_MONITOR=y +CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# +# CONFIG_GCOV_KERNEL is not set +# CONFIG_SLOW_WORK is not set +# CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y -# CONFIG_TINY_SHMEM is not set CONFIG_BASE_SMALL=0 CONFIG_MODULES=y # CONFIG_MODULE_FORCE_LOAD is not set @@ -131,11 +177,10 @@ CONFIG_MODULE_UNLOAD=y # CONFIG_MODULE_FORCE_UNLOAD is not set # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set -# CONFIG_KMOD is not set CONFIG_STOP_MACHINE=y CONFIG_BLOCK=y -# CONFIG_BLK_DEV_IO_TRACE is not set # CONFIG_BLK_DEV_BSG is not set +# CONFIG_BLK_DEV_INTEGRITY is not set CONFIG_BLOCK_COMPAT=y # @@ -150,19 +195,14 @@ CONFIG_DEFAULT_AS=y # CONFIG_DEFAULT_CFQ is not set # CONFIG_DEFAULT_NOOP is not set CONFIG_DEFAULT_IOSCHED="anticipatory" -CONFIG_CLASSIC_RCU=y +# CONFIG_FREEZER is not set +CONFIG_PPC_MSI_BITMAP=y # # Platform support # -CONFIG_PPC_MULTIPLATFORM=y -# CONFIG_PPC_82xx is not set -# CONFIG_PPC_83xx is not set -# CONFIG_PPC_86xx is not set # CONFIG_PPC_PSERIES is not set # CONFIG_PPC_ISERIES is not set -# CONFIG_PPC_MPC512x is not set -# CONFIG_PPC_MPC5121 is not set # CONFIG_PPC_PMAC is not set # CONFIG_PPC_MAPLE is not set CONFIG_PPC_PASEMI=y @@ -178,8 +218,10 @@ CONFIG_PPC_PASEMI_MDIO=y # CONFIG_PPC_CELL_NATIVE is not set # CONFIG_PPC_IBM_CELL_BLADE is not set # CONFIG_PPC_CELLEB is not set +# CONFIG_PPC_CELL_QPACE is not set # CONFIG_PQ2ADS is not set CONFIG_PPC_NATIVE=y +CONFIG_PPC_OF_BOOT_TRAMPOLINE=y # CONFIG_IPIC is not set CONFIG_MPIC=y # CONFIG_MPIC_WEIRD is not set @@ -213,6 +255,7 @@ CONFIG_CPU_FREQ_GOV_ONDEMAND=y # CONFIG_PPC_PASEMI_CPUFREQ=y # CONFIG_FSL_ULI1575 is not set +# CONFIG_SIMPLE_GPIO is not set # # Kernel options @@ -226,16 +269,19 @@ CONFIG_GENERIC_CLOCKEVENTS_BUILD=y # CONFIG_HZ_300 is not set CONFIG_HZ_1000=y CONFIG_HZ=1000 -# CONFIG_SCHED_HRTICK is not set +CONFIG_SCHED_HRTICK=y CONFIG_PREEMPT_NONE=y # CONFIG_PREEMPT_VOLUNTARY is not set # CONFIG_PREEMPT is not set CONFIG_BINFMT_ELF=y CONFIG_COMPAT_BINFMT_ELF=y +# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set +# CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set CONFIG_HUGETLB_PAGE_SIZE_VARIABLE=y CONFIG_IOMMU_VMERGE=y CONFIG_IOMMU_HELPER=y +# CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y @@ -243,6 +289,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_CRASH_DUMP is not set # CONFIG_IRQ_ALL_CPUS is not set # CONFIG_NUMA is not set +CONFIG_MAX_ACTIVE_REGIONS=256 CONFIG_ARCH_SELECT_MEMORY_MODEL=y CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_SPARSEMEM_ENABLE=y @@ -253,20 +300,28 @@ CONFIG_FLATMEM_MANUAL=y # CONFIG_SPARSEMEM_MANUAL is not set CONFIG_FLATMEM=y CONFIG_FLAT_NODE_MEM_MAP=y -# CONFIG_SPARSEMEM_STATIC is not set CONFIG_SPARSEMEM_VMEMMAP_ENABLE=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 -CONFIG_RESOURCES_64BIT=y +CONFIG_MIGRATION=y +CONFIG_PHYS_ADDR_T_64BIT=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y +CONFIG_HAVE_MLOCK=y +CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_HAS_HASH_64K=y +# CONFIG_PPC_4K_PAGES is not set +# CONFIG_PPC_16K_PAGES is not set CONFIG_PPC_64K_PAGES=y +# CONFIG_PPC_256K_PAGES is not set CONFIG_FORCE_MAX_ZONEORDER=9 # CONFIG_PPC_SUBPAGE_PROT is not set # CONFIG_SCHED_SMT is not set CONFIG_PROC_DEVICETREE=y # CONFIG_CMDLINE_BOOL is not set +CONFIG_EXTRA_TARGETS="" # CONFIG_PM is not set # CONFIG_SECCOMP is not set CONFIG_ISA_DMA_API=y @@ -285,6 +340,8 @@ CONFIG_ARCH_SUPPORTS_MSI=y CONFIG_PCI_MSI=y CONFIG_PCI_LEGACY=y # CONFIG_PCI_DEBUG is not set +# CONFIG_PCI_STUB is not set +# CONFIG_PCI_IOV is not set CONFIG_PCCARD=y CONFIG_PCMCIA_DEBUG=y CONFIG_PCMCIA=y @@ -301,13 +358,10 @@ CONFIG_CARDBUS=y CONFIG_ELECTRA_CF=y # CONFIG_HOTPLUG_PCI is not set # CONFIG_HAS_RAPIDIO is not set +# CONFIG_RELOCATABLE is not set CONFIG_PAGE_OFFSET=0xc000000000000000 CONFIG_KERNEL_START=0xc000000000000000 CONFIG_PHYSICAL_START=0x00000000 - -# -# Networking -# CONFIG_NET=y # @@ -356,9 +410,11 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set +# CONFIG_NET_DSA is not set # CONFIG_VLAN_8021Q is not set # CONFIG_DECNET is not set # CONFIG_LLC2 is not set @@ -368,25 +424,32 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_LAPB is not set # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set +# CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set +# CONFIG_DCB is not set # # Network testing # # CONFIG_NET_PKTGEN is not set +# CONFIG_NET_DROP_MONITOR is not set # CONFIG_HAMRADIO is not set # CONFIG_CAN is not set # CONFIG_IRDA is not set # CONFIG_BT is not set # CONFIG_AF_RXRPC is not set +CONFIG_WIRELESS=y +# CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 +# CONFIG_WIRELESS_OLD_REGULATORY is not set +# CONFIG_WIRELESS_EXT is not set +# CONFIG_LIB80211 is not set # -# Wireless +# CFG80211 needs to be enabled for MAC80211 # -# CONFIG_CFG80211 is not set -# CONFIG_WIRELESS_EXT is not set -# CONFIG_MAC80211 is not set -# CONFIG_IEEE80211 is not set +# CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -398,15 +461,19 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y +CONFIG_FIRMWARE_IN_KERNEL=y +CONFIG_EXTRA_FIRMWARE="" # CONFIG_DEBUG_DRIVER is not set # CONFIG_DEBUG_DEVRES is not set # CONFIG_SYS_HYPERVISOR is not set # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set CONFIG_MTD_CONCAT=y # CONFIG_MTD_PARTITIONS is not set @@ -478,11 +545,17 @@ CONFIG_MTD_NAND_PASEMI=y # CONFIG_MTD_ONENAND is not set # +# LPDDR flash memory drivers +# +# CONFIG_MTD_LPDDR is not set + +# # UBI - Unsorted block images # # CONFIG_MTD_UBI is not set CONFIG_OF_DEVICE=y CONFIG_OF_I2C=y +CONFIG_OF_MDIO=y # CONFIG_PARPORT is not set CONFIG_BLK_DEV=y # CONFIG_BLK_DEV_FD is not set @@ -501,29 +574,41 @@ CONFIG_BLK_DEV_RAM_SIZE=16384 # CONFIG_BLK_DEV_XIP is not set # CONFIG_CDROM_PKTCDVD is not set # CONFIG_ATA_OVER_ETH is not set +# CONFIG_BLK_DEV_HD is not set CONFIG_MISC_DEVICES=y # CONFIG_PHANTOM is not set -# CONFIG_EEPROM_93CX6 is not set # CONFIG_SGI_IOC4 is not set # CONFIG_TIFM_CORE is not set +# CONFIG_ICS932S401 is not set # CONFIG_ENCLOSURE_SERVICES is not set +# CONFIG_HP_ILO is not set +# CONFIG_ISL29003 is not set +# CONFIG_C2PORT is not set + +# +# EEPROM support +# +# CONFIG_EEPROM_AT24 is not set +CONFIG_EEPROM_LEGACY=y +# CONFIG_EEPROM_MAX6875 is not set +# CONFIG_EEPROM_93CX6 is not set +# CONFIG_CB710_CORE is not set CONFIG_HAVE_IDE=y CONFIG_IDE=y -CONFIG_BLK_DEV_IDE=y # # Please see Documentation/ide/ide.txt for help/info on IDE drives # +CONFIG_IDE_ATAPI=y # CONFIG_BLK_DEV_IDE_SATA is not set -CONFIG_BLK_DEV_IDEDISK=y -CONFIG_IDEDISK_MULTI_MODE=y +CONFIG_IDE_GD=y +CONFIG_IDE_GD_ATA=y +# CONFIG_IDE_GD_ATAPI is not set # CONFIG_BLK_DEV_IDECS is not set # CONFIG_BLK_DEV_DELKIN is not set CONFIG_BLK_DEV_IDECD=y CONFIG_BLK_DEV_IDECD_VERBOSE_ERRORS=y # CONFIG_BLK_DEV_IDETAPE is not set -# CONFIG_BLK_DEV_IDEFLOPPY is not set -CONFIG_BLK_DEV_IDESCSI=y CONFIG_IDE_TASK_IOCTL=y CONFIG_IDE_PROC_FS=y @@ -542,14 +627,13 @@ CONFIG_IDE_PROC_FS=y # CONFIG_BLK_DEV_AMD74XX is not set # CONFIG_BLK_DEV_CMD64X is not set # CONFIG_BLK_DEV_TRIFLEX is not set -# CONFIG_BLK_DEV_CY82C693 is not set # CONFIG_BLK_DEV_CS5520 is not set # CONFIG_BLK_DEV_CS5530 is not set -# CONFIG_BLK_DEV_HPT34X is not set # CONFIG_BLK_DEV_HPT366 is not set # CONFIG_BLK_DEV_JMICRON is not set # CONFIG_BLK_DEV_SC1200 is not set # CONFIG_BLK_DEV_PIIX is not set +# CONFIG_BLK_DEV_IT8172 is not set # CONFIG_BLK_DEV_IT8213 is not set # CONFIG_BLK_DEV_IT821X is not set # CONFIG_BLK_DEV_NS87415 is not set @@ -563,8 +647,6 @@ CONFIG_IDE_PROC_FS=y # CONFIG_BLK_DEV_VIA82CXXX is not set # CONFIG_BLK_DEV_TC86C001 is not set # CONFIG_BLK_DEV_IDEDMA is not set -# CONFIG_BLK_DEV_HD_ONLY is not set -# CONFIG_BLK_DEV_HD is not set # # SCSI device support @@ -586,10 +668,6 @@ CONFIG_BLK_DEV_SR=y CONFIG_BLK_DEV_SR_VENDOR=y CONFIG_CHR_DEV_SG=y CONFIG_CHR_DEV_SCH=y - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# CONFIG_SCSI_MULTI_LUN=y CONFIG_SCSI_CONSTANTS=y CONFIG_SCSI_LOGGING=y @@ -606,6 +684,8 @@ CONFIG_SCSI_WAIT_SCAN=m # CONFIG_SCSI_SRP_ATTRS is not set CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set +# CONFIG_SCSI_CXGB3_ISCSI is not set +# CONFIG_SCSI_BNX2_ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -614,11 +694,16 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_AIC7XXX_OLD is not set # CONFIG_SCSI_AIC79XX is not set # CONFIG_SCSI_AIC94XX is not set +# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_ARCMSR is not set # CONFIG_MEGARAID_NEWGEN is not set # CONFIG_MEGARAID_LEGACY is not set # CONFIG_MEGARAID_SAS is not set +# CONFIG_SCSI_MPT2SAS is not set # CONFIG_SCSI_HPTIOP is not set +# CONFIG_LIBFC is not set +# CONFIG_LIBFCOE is not set +# CONFIG_FCOE is not set # CONFIG_SCSI_DMX3191D is not set # CONFIG_SCSI_EATA is not set # CONFIG_SCSI_FUTURE_DOMAIN is not set @@ -626,7 +711,6 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_IPS is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set -# CONFIG_SCSI_MVSAS is not set # CONFIG_SCSI_STEX is not set # CONFIG_SCSI_SYM53C8XX_2 is not set # CONFIG_SCSI_IPR is not set @@ -637,10 +721,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC395x is not set # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set # CONFIG_SCSI_LOWLEVEL_PCMCIA is not set +# CONFIG_SCSI_DH is not set +# CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set CONFIG_SATA_SIL24=y @@ -662,6 +750,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -690,6 +779,7 @@ CONFIG_ATA_GENERIC=y CONFIG_PATA_PCMCIA=y # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -703,12 +793,15 @@ CONFIG_PATA_OF_PLATFORM=y # CONFIG_PATA_SCH is not set CONFIG_MD=y CONFIG_BLK_DEV_MD=y +CONFIG_MD_AUTODETECT=y CONFIG_MD_LINEAR=y CONFIG_MD_RAID0=y CONFIG_MD_RAID1=y CONFIG_MD_RAID10=y CONFIG_MD_RAID456=y -CONFIG_MD_RAID5_RESHAPE=y +# CONFIG_MULTICORE_RAID456 is not set +CONFIG_MD_RAID6_PQ=y +# CONFIG_ASYNC_RAID6_TEST is not set # CONFIG_MD_MULTIPATH is not set # CONFIG_MD_FAULTY is not set CONFIG_BLK_DEV_DM=y @@ -725,12 +818,19 @@ CONFIG_DM_CRYPT=y # # IEEE 1394 (FireWire) support # + +# +# You can enable one or both FireWire driver stacks. +# + +# +# See the help texts for more information. +# # CONFIG_FIREWIRE is not set # CONFIG_IEEE1394 is not set # CONFIG_I2O is not set # CONFIG_MACINTOSH_DRIVERS is not set CONFIG_NETDEVICES=y -# CONFIG_NETDEVICES_MULTIQUEUE is not set CONFIG_DUMMY=y # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -753,6 +853,9 @@ CONFIG_MARVELL_PHY=y # CONFIG_BROADCOM_PHY is not set # CONFIG_ICPLUS_PHY is not set # CONFIG_REALTEK_PHY is not set +# CONFIG_NATIONAL_PHY is not set +# CONFIG_STE10XP is not set +# CONFIG_LSI_ET1011C_PHY is not set # CONFIG_FIXED_PHY is not set # CONFIG_MDIO_BITBANG is not set CONFIG_NET_ETHERNET=y @@ -761,19 +864,23 @@ CONFIG_MII=y # CONFIG_SUNGEM is not set # CONFIG_CASSINI is not set # CONFIG_NET_VENDOR_3COM is not set +# CONFIG_ETHOC is not set +# CONFIG_DNET is not set # CONFIG_NET_TULIP is not set # CONFIG_HP100 is not set # CONFIG_IBM_NEW_EMAC_ZMII is not set # CONFIG_IBM_NEW_EMAC_RGMII is not set # CONFIG_IBM_NEW_EMAC_TAH is not set # CONFIG_IBM_NEW_EMAC_EMAC4 is not set +# CONFIG_IBM_NEW_EMAC_NO_FLOW_CTRL is not set +# CONFIG_IBM_NEW_EMAC_MAL_CLR_ICINTSTAT is not set +# CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set CONFIG_NET_PCI=y # CONFIG_PCNET32 is not set # CONFIG_AMD8111_ETH is not set # CONFIG_ADAPTEC_STARFIRE is not set # CONFIG_B44 is not set # CONFIG_FORCEDETH is not set -# CONFIG_EEPRO100 is not set # CONFIG_E100 is not set # CONFIG_FEALNX is not set # CONFIG_NATSEMI is not set @@ -783,19 +890,22 @@ CONFIG_NET_PCI=y # CONFIG_R6040 is not set # CONFIG_SIS900 is not set # CONFIG_EPIC100 is not set +# CONFIG_SMSC9420 is not set # CONFIG_SUNDANCE is not set +# CONFIG_TLAN is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set +# CONFIG_ATL2 is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set CONFIG_E1000=y -CONFIG_E1000_NAPI=y -# CONFIG_E1000_DISABLE_PACKET_SPLIT is not set # CONFIG_E1000E is not set -# CONFIG_E1000E_ENABLED is not set # CONFIG_IP1000 is not set # CONFIG_IGB is not set +# CONFIG_IGBVF is not set # CONFIG_NS83820 is not set # CONFIG_HAMACHI is not set # CONFIG_YELLOWFIN is not set @@ -806,30 +916,40 @@ CONFIG_E1000_NAPI=y # CONFIG_VIA_VELOCITY is not set CONFIG_TIGON3=y # CONFIG_BNX2 is not set +# CONFIG_CNIC is not set # CONFIG_QLA3XXX is not set # CONFIG_ATL1 is not set +# CONFIG_ATL1E is not set +# CONFIG_ATL1C is not set +# CONFIG_JME is not set CONFIG_NETDEV_10000=y # CONFIG_CHELSIO_T1 is not set +CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_CHELSIO_T3 is not set +# CONFIG_ENIC is not set # CONFIG_IXGBE is not set # CONFIG_IXGB is not set # CONFIG_S2IO is not set +# CONFIG_VXGE is not set # CONFIG_MYRI10GE is not set # CONFIG_NETXEN_NIC is not set # CONFIG_NIU is not set CONFIG_PASEMI_MAC=y +# CONFIG_MLX4_EN is not set # CONFIG_MLX4_CORE is not set # CONFIG_TEHUTI is not set # CONFIG_BNX2X is not set +# CONFIG_QLGE is not set # CONFIG_SFC is not set +# CONFIG_BE2NET is not set # CONFIG_TR is not set +CONFIG_WLAN=y +# CONFIG_WLAN_PRE80211 is not set +# CONFIG_WLAN_80211 is not set # -# Wireless LAN +# Enable WiMAX (Networking options) to see the WiMAX drivers # -# CONFIG_WLAN_PRE80211 is not set -# CONFIG_WLAN_80211 is not set -# CONFIG_IWLWIFI_LEDS is not set # # USB Network Adapters @@ -874,17 +994,23 @@ CONFIG_INPUT_EVDEV=y # Input Device Drivers # CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ADP5588 is not set # CONFIG_KEYBOARD_ATKBD is not set -# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_QT2160 is not set # CONFIG_KEYBOARD_LKKBD is not set -# CONFIG_KEYBOARD_XTKBD is not set +# CONFIG_KEYBOARD_MAX7359 is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_XTKBD is not set CONFIG_INPUT_MOUSE=y # CONFIG_MOUSE_PS2 is not set # CONFIG_MOUSE_SERIAL is not set # CONFIG_MOUSE_APPLETOUCH is not set +# CONFIG_MOUSE_BCM5974 is not set # CONFIG_MOUSE_VSXXXAA is not set +# CONFIG_MOUSE_SYNAPTICS_I2C is not set # CONFIG_INPUT_JOYSTICK is not set # CONFIG_INPUT_TABLET is not set # CONFIG_INPUT_TOUCHSCREEN is not set @@ -900,6 +1026,7 @@ CONFIG_INPUT_MOUSE=y # Character devices # CONFIG_VT=y +CONFIG_CONSOLE_TRANSLATIONS=y CONFIG_VT_CONSOLE=y CONFIG_HW_CONSOLE=y # CONFIG_VT_HW_CONSOLE_BINDING is not set @@ -926,10 +1053,13 @@ CONFIG_SERIAL_CORE_CONSOLE=y # CONFIG_SERIAL_JSM is not set # CONFIG_SERIAL_OF_PLATFORM is not set CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set CONFIG_LEGACY_PTYS=y CONFIG_LEGACY_PTY_COUNT=4 +# CONFIG_HVC_UDBG is not set # CONFIG_IPMI_HANDLER is not set CONFIG_HW_RANDOM=y +# CONFIG_HW_RANDOM_TIMERIOMEM is not set CONFIG_HW_RANDOM_PASEMI=y # CONFIG_R3964 is not set # CONFIG_APPLICOM is not set @@ -948,57 +1078,85 @@ CONFIG_MAX_RAW_DEVS=256 CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y +CONFIG_I2C_HELPER_AUTO=y CONFIG_I2C_ALGOBIT=y # # I2C Hardware Bus support # + +# +# PC SMBus host controller drivers +# # CONFIG_I2C_ALI1535 is not set # CONFIG_I2C_ALI1563 is not set # CONFIG_I2C_ALI15X3 is not set # CONFIG_I2C_AMD756 is not set # CONFIG_I2C_AMD8111 is not set # CONFIG_I2C_I801 is not set -# CONFIG_I2C_I810 is not set +# CONFIG_I2C_ISCH is not set # CONFIG_I2C_PIIX4 is not set # CONFIG_I2C_NFORCE2 is not set -# CONFIG_I2C_OCORES is not set -# CONFIG_I2C_PARPORT_LIGHT is not set -CONFIG_I2C_PASEMI=y -# CONFIG_I2C_PROSAVAGE is not set -# CONFIG_I2C_SAVAGE4 is not set -# CONFIG_I2C_SIMTEC is not set # CONFIG_I2C_SIS5595 is not set # CONFIG_I2C_SIS630 is not set # CONFIG_I2C_SIS96X is not set -# CONFIG_I2C_TAOS_EVM is not set -# CONFIG_I2C_STUB is not set -# CONFIG_I2C_TINY_USB is not set # CONFIG_I2C_VIA is not set # CONFIG_I2C_VIAPRO is not set + +# +# I2C system bus drivers (mostly embedded / system-on-chip) +# +# CONFIG_I2C_OCORES is not set +CONFIG_I2C_PASEMI=y +# CONFIG_I2C_SIMTEC is not set + +# +# External I2C/SMBus adapter drivers +# +# CONFIG_I2C_PARPORT_LIGHT is not set +# CONFIG_I2C_TAOS_EVM is not set +# CONFIG_I2C_TINY_USB is not set + +# +# Graphics adapter I2C/DDC channel drivers +# # CONFIG_I2C_VOODOO3 is not set + +# +# Other I2C/SMBus bus drivers +# # CONFIG_I2C_PCA_PLATFORM is not set +# CONFIG_I2C_STUB is not set # # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -CONFIG_EEPROM_LEGACY=y -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCF8591 is not set -# CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set # CONFIG_I2C_DEBUG_BUS is not set # CONFIG_I2C_DEBUG_CHIP is not set # CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set +CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y +# CONFIG_GPIOLIB is not set # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y CONFIG_HWMON_VID=y +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# +# CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set # CONFIG_SENSORS_ADM1025 is not set @@ -1006,14 +1164,17 @@ CONFIG_HWMON_VID=y # CONFIG_SENSORS_ADM1029 is not set # CONFIG_SENSORS_ADM1031 is not set # CONFIG_SENSORS_ADM9240 is not set +# CONFIG_SENSORS_ADT7462 is not set # CONFIG_SENSORS_ADT7470 is not set # CONFIG_SENSORS_ADT7473 is not set +# CONFIG_SENSORS_ADT7475 is not set # CONFIG_SENSORS_ATXP1 is not set # CONFIG_SENSORS_DS1621 is not set # CONFIG_SENSORS_I5K_AMB is not set # CONFIG_SENSORS_F71805F is not set # CONFIG_SENSORS_F71882FG is not set # CONFIG_SENSORS_F75375S is not set +# CONFIG_SENSORS_G760A is not set # CONFIG_SENSORS_GL518SM is not set # CONFIG_SENSORS_GL520SM is not set # CONFIG_SENSORS_IT87 is not set @@ -1028,10 +1189,14 @@ CONFIG_SENSORS_LM85=y CONFIG_SENSORS_LM90=y # CONFIG_SENSORS_LM92 is not set # CONFIG_SENSORS_LM93 is not set +# CONFIG_SENSORS_LTC4215 is not set +# CONFIG_SENSORS_LTC4245 is not set +# CONFIG_SENSORS_LM95241 is not set # CONFIG_SENSORS_MAX1619 is not set # CONFIG_SENSORS_MAX6650 is not set # CONFIG_SENSORS_PC87360 is not set # CONFIG_SENSORS_PC87427 is not set +# CONFIG_SENSORS_PCF8591 is not set # CONFIG_SENSORS_SIS5595 is not set # CONFIG_SENSORS_DME1737 is not set # CONFIG_SENSORS_SMSC47M1 is not set @@ -1039,6 +1204,8 @@ CONFIG_SENSORS_LM90=y # CONFIG_SENSORS_SMSC47B397 is not set # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set +# CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1050,44 +1217,40 @@ CONFIG_SENSORS_LM90=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set # CONFIG_WATCHDOG is not set +CONFIG_SSB_POSSIBLE=y # # Sonics Silicon Backplane # -CONFIG_SSB_POSSIBLE=y # CONFIG_SSB is not set # # Multifunction device drivers # +# CONFIG_MFD_CORE is not set # CONFIG_MFD_SM501 is not set # CONFIG_HTC_PASIC3 is not set - -# -# Multimedia devices -# - -# -# Multimedia core support -# -# CONFIG_VIDEO_DEV is not set -# CONFIG_DVB_CORE is not set -# CONFIG_VIDEO_MEDIA is not set - -# -# Multimedia drivers -# -CONFIG_DAB=y -# CONFIG_USB_DABUSB is not set +# CONFIG_TWL4030_CORE is not set +# CONFIG_MFD_TMIO is not set +# CONFIG_PMIC_DA903X is not set +# CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set +# CONFIG_MFD_WM8350_I2C is not set +# CONFIG_MFD_PCF50633 is not set +# CONFIG_AB3100_CORE is not set +# CONFIG_REGULATOR is not set +# CONFIG_MEDIA_SUPPORT is not set # # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y CONFIG_DRM=y +CONFIG_DRM_KMS_HELPER=y +CONFIG_DRM_TTM=y # CONFIG_DRM_TDFX is not set # CONFIG_DRM_R128 is not set CONFIG_DRM_RADEON=y @@ -1099,6 +1262,7 @@ CONFIG_VGASTATE=y CONFIG_FB=y CONFIG_FIRMWARE_EDID=y CONFIG_FB_DDC=y +# CONFIG_FB_BOOT_VESA_SUPPORT is not set CONFIG_FB_CFB_FILLRECT=y CONFIG_FB_CFB_COPYAREA=y CONFIG_FB_CFB_IMAGEBLIT=y @@ -1140,6 +1304,7 @@ CONFIG_FB_RADEON_BACKLIGHT=y # CONFIG_FB_S3 is not set # CONFIG_FB_SAVAGE is not set # CONFIG_FB_SIS is not set +# CONFIG_FB_VIA is not set # CONFIG_FB_NEOMAGIC is not set # CONFIG_FB_KYRO is not set # CONFIG_FB_3DFX is not set @@ -1148,12 +1313,16 @@ CONFIG_FB_RADEON_BACKLIGHT=y # CONFIG_FB_TRIDENT is not set # CONFIG_FB_ARK is not set # CONFIG_FB_PM3 is not set +# CONFIG_FB_CARMINE is not set # CONFIG_FB_IBM_GXT4500 is not set # CONFIG_FB_VIRTUAL is not set +# CONFIG_FB_METRONOME is not set +# CONFIG_FB_MB862XX is not set +# CONFIG_FB_BROADSHEET is not set CONFIG_BACKLIGHT_LCD_SUPPORT=y # CONFIG_LCD_CLASS_DEVICE is not set CONFIG_BACKLIGHT_CLASS_DEVICE=y -# CONFIG_BACKLIGHT_CORGI is not set +CONFIG_BACKLIGHT_GENERIC=y # # Display device support @@ -1177,15 +1346,9 @@ CONFIG_LOGO=y CONFIG_LOGO_LINUX_MONO=y CONFIG_LOGO_LINUX_VGA16=y CONFIG_LOGO_LINUX_CLUT224=y - -# -# Sound -# CONFIG_SOUND=y - -# -# Advanced Linux Sound Architecture -# +CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y CONFIG_SND=y CONFIG_SND_TIMER=y CONFIG_SND_PCM=y @@ -1198,24 +1361,24 @@ CONFIG_SND_MIXER_OSS=y CONFIG_SND_PCM_OSS=y CONFIG_SND_PCM_OSS_PLUGINS=y CONFIG_SND_SEQUENCER_OSS=y +# CONFIG_SND_HRTIMER is not set # CONFIG_SND_DYNAMIC_MINORS is not set CONFIG_SND_SUPPORT_OLD_API=y CONFIG_SND_VERBOSE_PROCFS=y # CONFIG_SND_VERBOSE_PRINTK is not set # CONFIG_SND_DEBUG is not set - -# -# Generic devices -# +CONFIG_SND_RAWMIDI_SEQ=y +# CONFIG_SND_OPL3_LIB_SEQ is not set +# CONFIG_SND_OPL4_LIB_SEQ is not set +# CONFIG_SND_SBAWE_SEQ is not set +# CONFIG_SND_EMU10K1_SEQ is not set +CONFIG_SND_DRIVERS=y # CONFIG_SND_DUMMY is not set # CONFIG_SND_VIRMIDI is not set # CONFIG_SND_MTPAV is not set # CONFIG_SND_SERIAL_U16550 is not set # CONFIG_SND_MPU401 is not set - -# -# PCI devices -# +CONFIG_SND_PCI=y # CONFIG_SND_AD1889 is not set # CONFIG_SND_ALS300 is not set # CONFIG_SND_ALS4000 is not set @@ -1234,6 +1397,7 @@ CONFIG_SND_VERBOSE_PROCFS=y # CONFIG_SND_CS4281 is not set # CONFIG_SND_CS46XX is not set # CONFIG_SND_CS5530 is not set +# CONFIG_SND_CTXFI is not set # CONFIG_SND_DARLA20 is not set # CONFIG_SND_GINA20 is not set # CONFIG_SND_LAYLA20 is not set @@ -1246,6 +1410,8 @@ CONFIG_SND_VERBOSE_PROCFS=y # CONFIG_SND_INDIGO is not set # CONFIG_SND_INDIGOIO is not set # CONFIG_SND_INDIGODJ is not set +# CONFIG_SND_INDIGOIOX is not set +# CONFIG_SND_INDIGODJX is not set # CONFIG_SND_EMU10K1 is not set # CONFIG_SND_EMU10K1X is not set # CONFIG_SND_ENS1370 is not set @@ -1262,6 +1428,7 @@ CONFIG_SND_VERBOSE_PROCFS=y # CONFIG_SND_INTEL8X0 is not set # CONFIG_SND_INTEL8X0M is not set # CONFIG_SND_KORG1212 is not set +# CONFIG_SND_LX6464ES is not set # CONFIG_SND_MAESTRO3 is not set # CONFIG_SND_MIXART is not set # CONFIG_SND_NM256 is not set @@ -1277,57 +1444,64 @@ CONFIG_SND_VERBOSE_PROCFS=y # CONFIG_SND_VIRTUOSO is not set # CONFIG_SND_VX222 is not set # CONFIG_SND_YMFPCI is not set - -# -# ALSA PowerMac devices -# - -# -# ALSA PowerPC devices -# - -# -# USB devices -# +CONFIG_SND_PPC=y +CONFIG_SND_USB=y CONFIG_SND_USB_AUDIO=y CONFIG_SND_USB_USX2Y=y # CONFIG_SND_USB_CAIAQ is not set - -# -# PCMCIA devices -# +CONFIG_SND_PCMCIA=y # CONFIG_SND_VXPOCKET is not set # CONFIG_SND_PDAUDIOCF is not set - -# -# System on Chip audio support -# # CONFIG_SND_SOC is not set - -# -# ALSA SoC audio for Freescale SOCs -# - -# -# SoC Audio for the Texas Instruments OMAP -# - -# -# Open Sound System -# # CONFIG_SOUND_PRIME is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # # USB Input Devices # CONFIG_USB_HID=y -# CONFIG_USB_HIDINPUT_POWERBOOK is not set -# CONFIG_HID_FF is not set +# CONFIG_HID_PID is not set # CONFIG_USB_HIDDEV is not set + +# +# Special HID drivers +# +CONFIG_HID_A4TECH=y +CONFIG_HID_APPLE=y +CONFIG_HID_BELKIN=y +CONFIG_HID_CHERRY=y +CONFIG_HID_CHICONY=y +CONFIG_HID_CYPRESS=y +CONFIG_HID_DRAGONRISE=y +# CONFIG_DRAGONRISE_FF is not set +CONFIG_HID_EZKEY=y +CONFIG_HID_KYE=y +CONFIG_HID_GYRATION=y +CONFIG_HID_TWINHAN=y +CONFIG_HID_KENSINGTON=y +CONFIG_HID_LOGITECH=y +# CONFIG_LOGITECH_FF is not set +# CONFIG_LOGIRUMBLEPAD2_FF is not set +CONFIG_HID_MICROSOFT=y +CONFIG_HID_MONTEREY=y +CONFIG_HID_NTRIG=y +CONFIG_HID_PANTHERLORD=y +# CONFIG_PANTHERLORD_FF is not set +CONFIG_HID_PETALYNX=y +CONFIG_HID_SAMSUNG=y +CONFIG_HID_SONY=y +CONFIG_HID_SUNPLUS=y +CONFIG_HID_GREENASIA=y +# CONFIG_GREENASIA_FF is not set +CONFIG_HID_SMARTJOYPLUS=y +# CONFIG_SMARTJOYPLUS_FF is not set +CONFIG_HID_TOPSEED=y +CONFIG_HID_THRUSTMASTER=y +# CONFIG_THRUSTMASTER_FF is not set +CONFIG_HID_ZEROPLUS=y +# CONFIG_ZEROPLUS_FF is not set CONFIG_USB_SUPPORT=y CONFIG_USB_ARCH_HAS_HCD=y CONFIG_USB_ARCH_HAS_OHCI=y @@ -1343,18 +1517,26 @@ CONFIG_USB_DEVICEFS=y # CONFIG_USB_DEVICE_CLASS is not set # CONFIG_USB_DYNAMIC_MINORS is not set # CONFIG_USB_OTG is not set +# CONFIG_USB_MON is not set +# CONFIG_USB_WUSB is not set +# CONFIG_USB_WUSB_CBAF is not set # # USB Host Controller Drivers # # CONFIG_USB_C67X00_HCD is not set +# CONFIG_USB_XHCI_HCD is not set CONFIG_USB_EHCI_HCD=y # CONFIG_USB_EHCI_ROOT_HUB_TT is not set # CONFIG_USB_EHCI_TT_NEWSCHED is not set CONFIG_USB_EHCI_HCD_PPC_OF=y +# CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y +# CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set +# CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set # CONFIG_USB_OHCI_HCD_PPC_OF is not set # CONFIG_USB_OHCI_BIG_ENDIAN_DESC is not set # CONFIG_USB_OHCI_BIG_ENDIAN_MMIO is not set @@ -1363,6 +1545,8 @@ CONFIG_USB_UHCI_HCD=y CONFIG_USB_SL811_HCD=y # CONFIG_USB_SL811_CS is not set # CONFIG_USB_R8A66597_HCD is not set +# CONFIG_USB_WHCI_HCD is not set +# CONFIG_USB_HWA_HCD is not set # # USB Device Class drivers @@ -1370,20 +1554,20 @@ CONFIG_USB_SL811_HCD=y # CONFIG_USB_ACM is not set # CONFIG_USB_PRINTER is not set # CONFIG_USB_WDM is not set +# CONFIG_USB_TMC is not set # -# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' +# NOTE: USB_STORAGE depends on SCSI but BLK_DEV_SD may # # -# may also be needed; see USB_STORAGE Help for more information +# also be needed; see USB_STORAGE Help for more info # CONFIG_USB_STORAGE=y # CONFIG_USB_STORAGE_DEBUG is not set # CONFIG_USB_STORAGE_DATAFAB is not set # CONFIG_USB_STORAGE_FREECOM is not set # CONFIG_USB_STORAGE_ISD200 is not set -# CONFIG_USB_STORAGE_DPCM is not set # CONFIG_USB_STORAGE_USBAT is not set # CONFIG_USB_STORAGE_SDDR09 is not set # CONFIG_USB_STORAGE_SDDR55 is not set @@ -1399,7 +1583,6 @@ CONFIG_USB_LIBUSUAL=y # # CONFIG_USB_MDC800 is not set # CONFIG_USB_MICROTEK is not set -# CONFIG_USB_MON is not set # # USB port drivers @@ -1412,7 +1595,7 @@ CONFIG_USB_LIBUSUAL=y # CONFIG_USB_EMI62 is not set # CONFIG_USB_EMI26 is not set # CONFIG_USB_ADUTUX is not set -# CONFIG_USB_AUERSWALD is not set +# CONFIG_USB_SEVSEG is not set # CONFIG_USB_RIO500 is not set # CONFIG_USB_LEGOTOWER is not set # CONFIG_USB_LCD is not set @@ -1420,7 +1603,6 @@ CONFIG_USB_LIBUSUAL=y # CONFIG_USB_LED is not set # CONFIG_USB_CYPRESS_CY7C63 is not set # CONFIG_USB_CYTHERM is not set -# CONFIG_USB_PHIDGET is not set # CONFIG_USB_IDMOUSE is not set # CONFIG_USB_FTDI_ELAN is not set # CONFIG_USB_APPLEDISPLAY is not set @@ -1429,7 +1611,15 @@ CONFIG_USB_LIBUSUAL=y # CONFIG_USB_TRANCEVIBRATOR is not set # CONFIG_USB_IOWARRIOR is not set # CONFIG_USB_TEST is not set +# CONFIG_USB_ISIGHTFW is not set +# CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set + +# +# OTG and related infrastructure +# +# CONFIG_NOP_USB_XCEIV is not set +# CONFIG_UWB is not set # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set # CONFIG_NEW_LEDS is not set @@ -1443,6 +1633,7 @@ CONFIG_EDAC=y # CONFIG_EDAC_DEBUG is not set CONFIG_EDAC_MM_EDAC=y CONFIG_EDAC_PASEMI=y +# CONFIG_EDAC_CPC925 is not set CONFIG_RTC_LIB=y CONFIG_RTC_CLASS=y CONFIG_RTC_HCTOSYS=y @@ -1472,6 +1663,9 @@ CONFIG_RTC_DRV_DS1307=y # CONFIG_RTC_DRV_PCF8583 is not set # CONFIG_RTC_DRV_M41T80 is not set # CONFIG_RTC_DRV_S35390A is not set +# CONFIG_RTC_DRV_FM3130 is not set +# CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set # # SPI RTC drivers @@ -1481,21 +1675,31 @@ CONFIG_RTC_DRV_DS1307=y # Platform RTC drivers # # CONFIG_RTC_DRV_CMOS is not set +# CONFIG_RTC_DRV_DS1286 is not set # CONFIG_RTC_DRV_DS1511 is not set # CONFIG_RTC_DRV_DS1553 is not set # CONFIG_RTC_DRV_DS1742 is not set # CONFIG_RTC_DRV_STK17TA8 is not set # CONFIG_RTC_DRV_M48T86 is not set +# CONFIG_RTC_DRV_M48T35 is not set # CONFIG_RTC_DRV_M48T59 is not set +# CONFIG_RTC_DRV_BQ4802 is not set # CONFIG_RTC_DRV_V3020 is not set # # on-CPU RTC drivers # +# CONFIG_RTC_DRV_GENERIC is not set # CONFIG_DMADEVICES is not set +# CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set # +# TI VLYNQ +# +# CONFIG_STAGING is not set + +# # File systems # CONFIG_EXT2_FS=y @@ -1504,11 +1708,13 @@ CONFIG_EXT2_FS_POSIX_ACL=y # CONFIG_EXT2_FS_SECURITY is not set # CONFIG_EXT2_FS_XIP is not set CONFIG_EXT3_FS=y +# CONFIG_EXT3_DEFAULTS_TO_ORDERED is not set CONFIG_EXT3_FS_XATTR=y # CONFIG_EXT3_FS_POSIX_ACL is not set # CONFIG_EXT3_FS_SECURITY is not set -# CONFIG_EXT4DEV_FS is not set +# CONFIG_EXT4_FS is not set CONFIG_JBD=y +# CONFIG_JBD_DEBUG is not set CONFIG_FS_MBCACHE=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set @@ -1516,6 +1722,10 @@ CONFIG_FS_POSIX_ACL=y # CONFIG_XFS_FS is not set # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set +# CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -1525,6 +1735,11 @@ CONFIG_AUTOFS4_FS=y # CONFIG_FUSE_FS is not set # +# Caches +# +# CONFIG_FSCACHE is not set + +# # CD-ROM/DVD Filesystems # CONFIG_ISO9660_FS=y @@ -1549,16 +1764,14 @@ CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1" CONFIG_PROC_FS=y CONFIG_PROC_KCORE=y CONFIG_PROC_SYSCTL=y +CONFIG_PROC_PAGE_MONITOR=y CONFIG_SYSFS=y CONFIG_TMPFS=y # CONFIG_TMPFS_POSIX_ACL is not set CONFIG_HUGETLBFS=y CONFIG_HUGETLB_PAGE=y CONFIG_CONFIGFS_FS=y - -# -# Miscellaneous filesystems -# +CONFIG_MISC_FILESYSTEMS=y # CONFIG_ADFS_FS is not set # CONFIG_AFFS_FS is not set # CONFIG_HFS_FS is not set @@ -1578,8 +1791,10 @@ CONFIG_JFFS2_ZLIB=y CONFIG_JFFS2_RTIME=y # CONFIG_JFFS2_RUBIN is not set # CONFIG_CRAMFS is not set +# CONFIG_SQUASHFS is not set # CONFIG_VXFS_FS is not set # CONFIG_MINIX_FS is not set +# CONFIG_OMFS_FS is not set # CONFIG_HPFS_FS is not set # CONFIG_QNX4FS_FS is not set # CONFIG_ROMFS_FS is not set @@ -1590,18 +1805,17 @@ CONFIG_NFS_FS=y CONFIG_NFS_V3=y # CONFIG_NFS_V3_ACL is not set # CONFIG_NFS_V4 is not set +CONFIG_ROOT_NFS=y CONFIG_NFSD=y CONFIG_NFSD_V3=y # CONFIG_NFSD_V3_ACL is not set CONFIG_NFSD_V4=y -CONFIG_ROOT_NFS=y CONFIG_LOCKD=y CONFIG_LOCKD_V4=y CONFIG_EXPORTFS=y CONFIG_NFS_COMMON=y CONFIG_SUNRPC=y CONFIG_SUNRPC_GSS=y -# CONFIG_SUNRPC_BIND34 is not set CONFIG_RPCSEC_GSS_KRB5=y # CONFIG_RPCSEC_GSS_SPKM3 is not set # CONFIG_SMB_FS is not set @@ -1672,25 +1886,30 @@ CONFIG_NLS_ISO8859_1=y # CONFIG_NLS_KOI8_U is not set # CONFIG_NLS_UTF8 is not set # CONFIG_DLM is not set +CONFIG_BINARY_PRINTF=y # # Library routines # CONFIG_BITREVERSE=y -# CONFIG_GENERIC_FIND_FIRST_BIT is not set +CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC_CCITT=y # CONFIG_CRC16 is not set +# CONFIG_CRC_T10DIF is not set CONFIG_CRC_ITU_T=y CONFIG_CRC32=y # CONFIG_CRC7 is not set -CONFIG_LIBCRC32C=m +# CONFIG_LIBCRC32C is not set CONFIG_ZLIB_INFLATE=y CONFIG_ZLIB_DEFLATE=y -CONFIG_PLIST=y +CONFIG_DECOMPRESS_GZIP=y +CONFIG_DECOMPRESS_BZIP2=y +CONFIG_DECOMPRESS_LZMA=y CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y +CONFIG_NLATTR=y # # Kernel hacking @@ -1700,18 +1919,25 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=2048 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set -# CONFIG_DEBUG_FS is not set +CONFIG_DEBUG_FS=y # CONFIG_HEADERS_CHECK is not set CONFIG_DEBUG_KERNEL=y # CONFIG_DEBUG_SHIRQ is not set CONFIG_DETECT_SOFTLOCKUP=y +# CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC is not set +CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC_VALUE=0 +CONFIG_DETECT_HUNG_TASK=y +# CONFIG_BOOTPARAM_HUNG_TASK_PANIC is not set +CONFIG_BOOTPARAM_HUNG_TASK_PANIC_VALUE=0 # CONFIG_SCHED_DEBUG is not set # CONFIG_SCHEDSTATS is not set # CONFIG_TIMER_STATS is not set # CONFIG_DEBUG_OBJECTS is not set # CONFIG_SLUB_DEBUG_ON is not set # CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set # CONFIG_DEBUG_RT_MUTEXES is not set # CONFIG_RT_MUTEX_TESTER is not set # CONFIG_DEBUG_SPINLOCK is not set @@ -1721,26 +1947,71 @@ CONFIG_DETECT_SOFTLOCKUP=y # CONFIG_LOCK_STAT is not set # CONFIG_DEBUG_SPINLOCK_SLEEP is not set # CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set +CONFIG_STACKTRACE=y # CONFIG_DEBUG_KOBJECT is not set CONFIG_DEBUG_BUGVERBOSE=y # CONFIG_DEBUG_INFO is not set # CONFIG_DEBUG_VM is not set # CONFIG_DEBUG_WRITECOUNT is not set +CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set -# CONFIG_BOOT_PRINTK_DELAY is not set +# CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set +# CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set +# CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set +# CONFIG_LATENCYTOP is not set +CONFIG_SYSCTL_SYSCALL_CHECK=y +# CONFIG_DEBUG_PAGEALLOC is not set +CONFIG_NOP_TRACER=y +CONFIG_HAVE_FUNCTION_TRACER=y +CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y +CONFIG_HAVE_DYNAMIC_FTRACE=y +CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y +CONFIG_RING_BUFFER=y +CONFIG_EVENT_TRACING=y +CONFIG_CONTEXT_SWITCH_TRACER=y +CONFIG_RING_BUFFER_ALLOW_SWAP=y +CONFIG_TRACING=y +CONFIG_TRACING_SUPPORT=y +CONFIG_FTRACE=y +# CONFIG_FUNCTION_TRACER is not set +# CONFIG_IRQSOFF_TRACER is not set +# CONFIG_SCHED_TRACER is not set +# CONFIG_ENABLE_DEFAULT_TRACERS is not set +# CONFIG_BOOT_TRACER is not set +CONFIG_BRANCH_PROFILE_NONE=y +# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set +# CONFIG_PROFILE_ALL_BRANCHES is not set +# CONFIG_STACK_TRACER is not set +# CONFIG_KMEMTRACE is not set +# CONFIG_WORKQUEUE_TRACER is not set +# CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_RING_BUFFER_BENCHMARK is not set +# CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set +CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_KGDB is not set +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y +CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_DEBUG_STACKOVERFLOW is not set # CONFIG_DEBUG_STACK_USAGE is not set -# CONFIG_DEBUG_PAGEALLOC is not set -CONFIG_DEBUGGER=y +# CONFIG_PPC_EMULATED_STATS is not set +# CONFIG_CODE_PATCHING_SELFTEST is not set +# CONFIG_FTR_FIXUP_SELFTEST is not set +# CONFIG_MSI_BITMAP_SELFTEST is not set CONFIG_XMON=y CONFIG_XMON_DEFAULT=y CONFIG_XMON_DISASSEMBLY=y +CONFIG_DEBUGGER=y # CONFIG_IRQSTACKS is not set +# CONFIG_VIRQ_DEBUG is not set # CONFIG_BOOTX_TEXT is not set # CONFIG_PPC_EARLY_DEBUG is not set @@ -1749,23 +2020,34 @@ CONFIG_XMON_DISASSEMBLY=y # # CONFIG_KEYS is not set # CONFIG_SECURITY is not set +# CONFIG_SECURITYFS is not set # CONFIG_SECURITY_FILE_CAPABILITIES is not set CONFIG_XOR_BLOCKS=y CONFIG_ASYNC_CORE=y CONFIG_ASYNC_MEMCPY=y CONFIG_ASYNC_XOR=y +CONFIG_ASYNC_PQ=y +CONFIG_ASYNC_RAID6_RECOV=y CONFIG_CRYPTO=y # # Crypto core or helper # CONFIG_CRYPTO_ALGAPI=y +CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=y +CONFIG_CRYPTO_AEAD2=y CONFIG_CRYPTO_BLKCIPHER=y +CONFIG_CRYPTO_BLKCIPHER2=y CONFIG_CRYPTO_HASH=y +CONFIG_CRYPTO_HASH2=y +CONFIG_CRYPTO_RNG2=y +CONFIG_CRYPTO_PCOMP=y CONFIG_CRYPTO_MANAGER=y +CONFIG_CRYPTO_MANAGER2=y # CONFIG_CRYPTO_GF128MUL is not set # CONFIG_CRYPTO_NULL is not set +CONFIG_CRYPTO_WORKQUEUE=y # CONFIG_CRYPTO_CRYPTD is not set CONFIG_CRYPTO_AUTHENC=y # CONFIG_CRYPTO_TEST is not set @@ -1793,14 +2075,20 @@ CONFIG_CRYPTO_CBC=y # CONFIG_CRYPTO_HMAC=y # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set CONFIG_CRYPTO_MD4=y CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set +# CONFIG_CRYPTO_RMD128 is not set +# CONFIG_CRYPTO_RMD160 is not set +# CONFIG_CRYPTO_RMD256 is not set +# CONFIG_CRYPTO_RMD320 is not set CONFIG_CRYPTO_SHA1=y CONFIG_CRYPTO_SHA256=y CONFIG_CRYPTO_SHA512=y @@ -1830,7 +2118,13 @@ CONFIG_CRYPTO_DES=y # Compression # # CONFIG_CRYPTO_DEFLATE is not set +# CONFIG_CRYPTO_ZLIB is not set # CONFIG_CRYPTO_LZO is not set + +# +# Random Number Generation +# +# CONFIG_CRYPTO_ANSI_CPRNG is not set CONFIG_CRYPTO_HW=y # CONFIG_CRYPTO_DEV_HIFN_795X is not set # CONFIG_PPC_CLOCK is not set diff --git a/arch/powerpc/configs/ppc64e_defconfig b/arch/powerpc/configs/ppc64e_defconfig new file mode 100644 index 000000000000..18af46036258 --- /dev/null +++ b/arch/powerpc/configs/ppc64e_defconfig @@ -0,0 +1,2199 @@ +# +# Automatically generated make config: don't edit +# Linux kernel version: 2.6.32-rc5 +# Fri Oct 16 11:37:15 2009 +# +CONFIG_PPC64=y + +# +# Processor support +# +# CONFIG_PPC_BOOK3S_64 is not set +CONFIG_PPC_BOOK3E_64=y +CONFIG_PPC_BOOK3E=y +CONFIG_PPC_FPU=y +CONFIG_BOOKE=y +CONFIG_PPC_MMU_NOHASH=y +CONFIG_PPC_MMU_NOHASH_64=y +CONFIG_PPC_BOOK3E_MMU=y +# CONFIG_PPC_MM_SLICES is not set +CONFIG_VIRT_CPU_ACCOUNTING=y +CONFIG_PPC_HAVE_PMU_SUPPORT=y +CONFIG_PPC_PERF_CTRS=y +CONFIG_SMP=y +CONFIG_NR_CPUS=32 +CONFIG_64BIT=y +CONFIG_WORD_SIZE=64 +CONFIG_ARCH_PHYS_ADDR_T_64BIT=y +CONFIG_MMU=y +CONFIG_GENERIC_CMOS_UPDATE=y +CONFIG_GENERIC_TIME=y +CONFIG_GENERIC_TIME_VSYSCALL=y +CONFIG_GENERIC_CLOCKEVENTS=y +CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y +CONFIG_HAVE_SETUP_PER_CPU_AREA=y +CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK=y +CONFIG_IRQ_PER_CPU=y +CONFIG_STACKTRACE_SUPPORT=y +CONFIG_HAVE_LATENCYTOP_SUPPORT=y +CONFIG_TRACE_IRQFLAGS_SUPPORT=y +CONFIG_LOCKDEP_SUPPORT=y +CONFIG_RWSEM_XCHGADD_ALGORITHM=y +CONFIG_ARCH_HAS_ILOG2_U32=y +CONFIG_ARCH_HAS_ILOG2_U64=y +CONFIG_GENERIC_HWEIGHT=y +CONFIG_GENERIC_FIND_NEXT_BIT=y +CONFIG_ARCH_NO_VIRT_TO_BUS=y +CONFIG_PPC=y +CONFIG_EARLY_PRINTK=y +CONFIG_COMPAT=y +CONFIG_SYSVIPC_COMPAT=y +CONFIG_SCHED_OMIT_FRAME_POINTER=y +CONFIG_ARCH_MAY_HAVE_PC_FDC=y +CONFIG_PPC_OF=y +CONFIG_OF=y +# CONFIG_PPC_UDBG_16550 is not set +# CONFIG_GENERIC_TBSYNC is not set +CONFIG_AUDIT_ARCH=y +CONFIG_GENERIC_BUG=y +CONFIG_DTC=y +# CONFIG_DEFAULT_UIMAGE is not set +# CONFIG_PPC_DCR_NATIVE is not set +# CONFIG_PPC_DCR_MMIO is not set +# CONFIG_PPC_OF_PLATFORM_PCI is not set +CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y +CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" +CONFIG_CONSTRUCTORS=y + +# +# General setup +# +CONFIG_EXPERIMENTAL=y +CONFIG_LOCK_KERNEL=y +CONFIG_INIT_ENV_ARG_LIMIT=32 +CONFIG_LOCALVERSION="" +CONFIG_LOCALVERSION_AUTO=y +CONFIG_SWAP=y +CONFIG_SYSVIPC=y +CONFIG_SYSVIPC_SYSCTL=y +CONFIG_POSIX_MQUEUE=y +CONFIG_POSIX_MQUEUE_SYSCTL=y +# CONFIG_BSD_PROCESS_ACCT is not set +CONFIG_TASKSTATS=y +CONFIG_TASK_DELAY_ACCT=y +# CONFIG_TASK_XACCT is not set +# CONFIG_AUDIT is not set + +# +# RCU Subsystem +# +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=64 +# CONFIG_RCU_FANOUT_EXACT is not set +# CONFIG_TREE_RCU_TRACE is not set +CONFIG_IKCONFIG=y +CONFIG_IKCONFIG_PROC=y +CONFIG_LOG_BUF_SHIFT=17 +# CONFIG_GROUP_SCHED is not set +CONFIG_CGROUPS=y +# CONFIG_CGROUP_DEBUG is not set +# CONFIG_CGROUP_NS is not set +# CONFIG_CGROUP_FREEZER is not set +# CONFIG_CGROUP_DEVICE is not set +CONFIG_CPUSETS=y +CONFIG_PROC_PID_CPUSET=y +# CONFIG_CGROUP_CPUACCT is not set +# CONFIG_RESOURCE_COUNTERS is not set +CONFIG_SYSFS_DEPRECATED=y +CONFIG_SYSFS_DEPRECATED_V2=y +CONFIG_RELAY=y +CONFIG_NAMESPACES=y +# CONFIG_UTS_NS is not set +# CONFIG_IPC_NS is not set +# CONFIG_USER_NS is not set +# CONFIG_PID_NS is not set +# CONFIG_NET_NS is not set +CONFIG_BLK_DEV_INITRD=y +CONFIG_INITRAMFS_SOURCE="" +CONFIG_RD_GZIP=y +CONFIG_RD_BZIP2=y +CONFIG_RD_LZMA=y +CONFIG_CC_OPTIMIZE_FOR_SIZE=y +CONFIG_SYSCTL=y +CONFIG_ANON_INODES=y +# CONFIG_EMBEDDED is not set +CONFIG_SYSCTL_SYSCALL=y +CONFIG_KALLSYMS=y +CONFIG_KALLSYMS_ALL=y +# CONFIG_KALLSYMS_EXTRA_PASS is not set +CONFIG_HOTPLUG=y +CONFIG_PRINTK=y +CONFIG_BUG=y +CONFIG_ELF_CORE=y +CONFIG_BASE_FULL=y +CONFIG_FUTEX=y +CONFIG_EPOLL=y +CONFIG_SIGNALFD=y +CONFIG_TIMERFD=y +CONFIG_EVENTFD=y +CONFIG_SHMEM=y +CONFIG_AIO=y +CONFIG_HAVE_PERF_EVENTS=y + +# +# Kernel Performance Events And Counters +# +CONFIG_PERF_EVENTS=y +CONFIG_EVENT_PROFILE=y +# CONFIG_PERF_COUNTERS is not set +# CONFIG_DEBUG_PERF_USE_VMALLOC is not set +CONFIG_VM_EVENT_COUNTERS=y +CONFIG_PCI_QUIRKS=y +CONFIG_SLUB_DEBUG=y +# CONFIG_COMPAT_BRK is not set +# CONFIG_SLAB is not set +CONFIG_SLUB=y +# CONFIG_SLOB is not set +CONFIG_PROFILING=y +CONFIG_TRACEPOINTS=y +CONFIG_OPROFILE=y +CONFIG_HAVE_OPROFILE=y +# CONFIG_KPROBES is not set +CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y +CONFIG_HAVE_SYSCALL_WRAPPERS=y +CONFIG_HAVE_IOREMAP_PROT=y +CONFIG_HAVE_KPROBES=y +CONFIG_HAVE_KRETPROBES=y +CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_USE_GENERIC_SMP_HELPERS=y +CONFIG_HAVE_DMA_API_DEBUG=y + +# +# GCOV-based kernel profiling +# +# CONFIG_GCOV_KERNEL is not set +CONFIG_SLOW_WORK=y +# CONFIG_HAVE_GENERIC_DMA_COHERENT is not set +CONFIG_SLABINFO=y +CONFIG_RT_MUTEXES=y +CONFIG_BASE_SMALL=0 +CONFIG_MODULES=y +# CONFIG_MODULE_FORCE_LOAD is not set +CONFIG_MODULE_UNLOAD=y +# CONFIG_MODULE_FORCE_UNLOAD is not set +CONFIG_MODVERSIONS=y +CONFIG_MODULE_SRCVERSION_ALL=y +CONFIG_STOP_MACHINE=y +CONFIG_BLOCK=y +CONFIG_BLK_DEV_BSG=y +# CONFIG_BLK_DEV_INTEGRITY is not set +CONFIG_BLOCK_COMPAT=y + +# +# IO Schedulers +# +CONFIG_IOSCHED_NOOP=y +CONFIG_IOSCHED_AS=y +CONFIG_IOSCHED_DEADLINE=y +CONFIG_IOSCHED_CFQ=y +CONFIG_DEFAULT_AS=y +# CONFIG_DEFAULT_DEADLINE is not set +# CONFIG_DEFAULT_CFQ is not set +# CONFIG_DEFAULT_NOOP is not set +CONFIG_DEFAULT_IOSCHED="anticipatory" +# CONFIG_FREEZER is not set + +# +# Platform support +# +# CONFIG_PPC_CELL is not set +# CONFIG_PPC_CELL_NATIVE is not set +# CONFIG_PQ2ADS is not set +CONFIG_PPC_OF_BOOT_TRAMPOLINE=y +# CONFIG_IPIC is not set +# CONFIG_MPIC is not set +# CONFIG_MPIC_WEIRD is not set +# CONFIG_PPC_I8259 is not set +# CONFIG_U3_DART is not set +# CONFIG_PPC_RTAS is not set +# CONFIG_MMIO_NVRAM is not set +# CONFIG_PPC_MPC106 is not set +# CONFIG_PPC_970_NAP is not set +# CONFIG_PPC_INDIRECT_IO is not set +# CONFIG_GENERIC_IOMAP is not set +CONFIG_CPU_FREQ=y +CONFIG_CPU_FREQ_TABLE=y +# CONFIG_CPU_FREQ_DEBUG is not set +CONFIG_CPU_FREQ_STAT=y +# CONFIG_CPU_FREQ_STAT_DETAILS is not set +CONFIG_CPU_FREQ_DEFAULT_GOV_PERFORMANCE=y +# CONFIG_CPU_FREQ_DEFAULT_GOV_POWERSAVE is not set +# CONFIG_CPU_FREQ_DEFAULT_GOV_USERSPACE is not set +# CONFIG_CPU_FREQ_DEFAULT_GOV_ONDEMAND is not set +# CONFIG_CPU_FREQ_DEFAULT_GOV_CONSERVATIVE is not set +CONFIG_CPU_FREQ_GOV_PERFORMANCE=y +CONFIG_CPU_FREQ_GOV_POWERSAVE=y +CONFIG_CPU_FREQ_GOV_USERSPACE=y +# CONFIG_CPU_FREQ_GOV_ONDEMAND is not set +# CONFIG_CPU_FREQ_GOV_CONSERVATIVE is not set + +# +# CPU Frequency drivers +# +# CONFIG_FSL_ULI1575 is not set +# CONFIG_SIMPLE_GPIO is not set + +# +# Kernel options +# +CONFIG_TICK_ONESHOT=y +CONFIG_NO_HZ=y +CONFIG_HIGH_RES_TIMERS=y +CONFIG_GENERIC_CLOCKEVENTS_BUILD=y +# CONFIG_HZ_100 is not set +CONFIG_HZ_250=y +# CONFIG_HZ_300 is not set +# CONFIG_HZ_1000 is not set +CONFIG_HZ=250 +CONFIG_SCHED_HRTICK=y +CONFIG_PREEMPT_NONE=y +# CONFIG_PREEMPT_VOLUNTARY is not set +# CONFIG_PREEMPT is not set +CONFIG_BINFMT_ELF=y +CONFIG_COMPAT_BINFMT_ELF=y +# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set +# CONFIG_HAVE_AOUT is not set +CONFIG_BINFMT_MISC=m +CONFIG_IOMMU_VMERGE=y +CONFIG_IOMMU_HELPER=y +# CONFIG_SWIOTLB is not set +CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y +CONFIG_ARCH_HAS_WALK_MEMORY=y +CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y +# CONFIG_CRASH_DUMP is not set +CONFIG_IRQ_ALL_CPUS=y +# CONFIG_NUMA is not set +CONFIG_MAX_ACTIVE_REGIONS=256 +CONFIG_ARCH_SELECT_MEMORY_MODEL=y +CONFIG_ARCH_FLATMEM_ENABLE=y +CONFIG_ARCH_SPARSEMEM_ENABLE=y +CONFIG_ARCH_POPULATES_NODE_MAP=y +CONFIG_SELECT_MEMORY_MODEL=y +# CONFIG_FLATMEM_MANUAL is not set +# CONFIG_DISCONTIGMEM_MANUAL is not set +CONFIG_SPARSEMEM_MANUAL=y +CONFIG_SPARSEMEM=y +CONFIG_HAVE_MEMORY_PRESENT=y +CONFIG_SPARSEMEM_EXTREME=y +CONFIG_SPARSEMEM_VMEMMAP_ENABLE=y +CONFIG_SPARSEMEM_VMEMMAP=y +# CONFIG_MEMORY_HOTPLUG is not set +CONFIG_PAGEFLAGS_EXTENDED=y +CONFIG_SPLIT_PTLOCK_CPUS=4 +CONFIG_MIGRATION=y +CONFIG_PHYS_ADDR_T_64BIT=y +CONFIG_ZONE_DMA_FLAG=1 +CONFIG_BOUNCE=y +CONFIG_HAVE_MLOCK=y +CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set +CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 +# CONFIG_PPC_HAS_HASH_64K is not set +CONFIG_PPC_4K_PAGES=y +# CONFIG_PPC_16K_PAGES is not set +# CONFIG_PPC_64K_PAGES is not set +# CONFIG_PPC_256K_PAGES is not set +CONFIG_FORCE_MAX_ZONEORDER=13 +# CONFIG_SCHED_SMT is not set +CONFIG_PROC_DEVICETREE=y +# CONFIG_CMDLINE_BOOL is not set +CONFIG_EXTRA_TARGETS="" +# CONFIG_PM is not set +CONFIG_SECCOMP=y +CONFIG_ISA_DMA_API=y + +# +# Bus options +# +CONFIG_ZONE_DMA=y +CONFIG_GENERIC_ISA_DMA=y +# CONFIG_PPC_INDIRECT_PCI is not set +CONFIG_PCI=y +CONFIG_PCI_DOMAINS=y +CONFIG_PCI_SYSCALL=y +# CONFIG_PCIEPORTBUS is not set +CONFIG_ARCH_SUPPORTS_MSI=y +CONFIG_PCI_MSI=y +# CONFIG_PCI_LEGACY is not set +# CONFIG_PCI_DEBUG is not set +# CONFIG_PCI_STUB is not set +# CONFIG_PCI_IOV is not set +CONFIG_PCCARD=y +# CONFIG_PCMCIA_DEBUG is not set +CONFIG_PCMCIA=y +CONFIG_PCMCIA_LOAD_CIS=y +CONFIG_PCMCIA_IOCTL=y +CONFIG_CARDBUS=y + +# +# PC-card bridges +# +# CONFIG_YENTA is not set +# CONFIG_PD6729 is not set +# CONFIG_I82092 is not set +CONFIG_HOTPLUG_PCI=m +# CONFIG_HOTPLUG_PCI_FAKE is not set +# CONFIG_HOTPLUG_PCI_CPCI is not set +# CONFIG_HOTPLUG_PCI_SHPC is not set +# CONFIG_HAS_RAPIDIO is not set +# CONFIG_RELOCATABLE is not set +CONFIG_PAGE_OFFSET=0xc000000000000000 +CONFIG_KERNEL_START=0xc000000000000000 +CONFIG_PHYSICAL_START=0x00000000 +CONFIG_NET=y +CONFIG_COMPAT_NETLINK_MESSAGES=y + +# +# Networking options +# +CONFIG_PACKET=y +# CONFIG_PACKET_MMAP is not set +CONFIG_UNIX=y +CONFIG_XFRM=y +CONFIG_XFRM_USER=m +# CONFIG_XFRM_SUB_POLICY is not set +# CONFIG_XFRM_MIGRATE is not set +# CONFIG_XFRM_STATISTICS is not set +CONFIG_XFRM_IPCOMP=m +CONFIG_NET_KEY=m +# CONFIG_NET_KEY_MIGRATE is not set +CONFIG_INET=y +CONFIG_IP_MULTICAST=y +# CONFIG_IP_ADVANCED_ROUTER is not set +CONFIG_IP_FIB_HASH=y +CONFIG_IP_PNP=y +CONFIG_IP_PNP_DHCP=y +CONFIG_IP_PNP_BOOTP=y +# CONFIG_IP_PNP_RARP is not set +CONFIG_NET_IPIP=y +# CONFIG_NET_IPGRE is not set +# CONFIG_IP_MROUTE is not set +# CONFIG_ARPD is not set +CONFIG_SYN_COOKIES=y +CONFIG_INET_AH=m +CONFIG_INET_ESP=m +CONFIG_INET_IPCOMP=m +CONFIG_INET_XFRM_TUNNEL=m +CONFIG_INET_TUNNEL=y +CONFIG_INET_XFRM_MODE_TRANSPORT=y +CONFIG_INET_XFRM_MODE_TUNNEL=y +CONFIG_INET_XFRM_MODE_BEET=y +CONFIG_INET_LRO=y +CONFIG_INET_DIAG=y +CONFIG_INET_TCP_DIAG=y +# CONFIG_TCP_CONG_ADVANCED is not set +CONFIG_TCP_CONG_CUBIC=y +CONFIG_DEFAULT_TCP_CONG="cubic" +# CONFIG_TCP_MD5SIG is not set +# CONFIG_IPV6 is not set +# CONFIG_NETWORK_SECMARK is not set +CONFIG_NETFILTER=y +# CONFIG_NETFILTER_DEBUG is not set +CONFIG_NETFILTER_ADVANCED=y + +# +# Core Netfilter Configuration +# +CONFIG_NETFILTER_NETLINK=m +CONFIG_NETFILTER_NETLINK_QUEUE=m +CONFIG_NETFILTER_NETLINK_LOG=m +CONFIG_NF_CONNTRACK=m +CONFIG_NF_CT_ACCT=y +CONFIG_NF_CONNTRACK_MARK=y +CONFIG_NF_CONNTRACK_EVENTS=y +# CONFIG_NF_CT_PROTO_DCCP is not set +CONFIG_NF_CT_PROTO_GRE=m +CONFIG_NF_CT_PROTO_SCTP=m +# CONFIG_NF_CT_PROTO_UDPLITE is not set +CONFIG_NF_CONNTRACK_AMANDA=m +CONFIG_NF_CONNTRACK_FTP=m +CONFIG_NF_CONNTRACK_H323=m +CONFIG_NF_CONNTRACK_IRC=m +CONFIG_NF_CONNTRACK_NETBIOS_NS=m +CONFIG_NF_CONNTRACK_PPTP=m +# CONFIG_NF_CONNTRACK_SANE is not set +CONFIG_NF_CONNTRACK_SIP=m +CONFIG_NF_CONNTRACK_TFTP=m +CONFIG_NF_CT_NETLINK=m +CONFIG_NETFILTER_TPROXY=m +CONFIG_NETFILTER_XTABLES=m +CONFIG_NETFILTER_XT_TARGET_CLASSIFY=m +CONFIG_NETFILTER_XT_TARGET_CONNMARK=m +CONFIG_NETFILTER_XT_TARGET_DSCP=m +CONFIG_NETFILTER_XT_TARGET_HL=m +CONFIG_NETFILTER_XT_TARGET_MARK=m +CONFIG_NETFILTER_XT_TARGET_NFLOG=m +CONFIG_NETFILTER_XT_TARGET_NFQUEUE=m +CONFIG_NETFILTER_XT_TARGET_NOTRACK=m +CONFIG_NETFILTER_XT_TARGET_RATEEST=m +CONFIG_NETFILTER_XT_TARGET_TPROXY=m +CONFIG_NETFILTER_XT_TARGET_TRACE=m +CONFIG_NETFILTER_XT_TARGET_TCPMSS=m +CONFIG_NETFILTER_XT_TARGET_TCPOPTSTRIP=m +# CONFIG_NETFILTER_XT_MATCH_CLUSTER is not set +CONFIG_NETFILTER_XT_MATCH_COMMENT=m +CONFIG_NETFILTER_XT_MATCH_CONNBYTES=m +CONFIG_NETFILTER_XT_MATCH_CONNLIMIT=m +CONFIG_NETFILTER_XT_MATCH_CONNMARK=m +CONFIG_NETFILTER_XT_MATCH_CONNTRACK=m +CONFIG_NETFILTER_XT_MATCH_DCCP=m +CONFIG_NETFILTER_XT_MATCH_DSCP=m +CONFIG_NETFILTER_XT_MATCH_ESP=m +CONFIG_NETFILTER_XT_MATCH_HASHLIMIT=m +CONFIG_NETFILTER_XT_MATCH_HELPER=m +CONFIG_NETFILTER_XT_MATCH_HL=m +CONFIG_NETFILTER_XT_MATCH_IPRANGE=m +CONFIG_NETFILTER_XT_MATCH_LENGTH=m +CONFIG_NETFILTER_XT_MATCH_LIMIT=m +CONFIG_NETFILTER_XT_MATCH_MAC=m +CONFIG_NETFILTER_XT_MATCH_MARK=m +CONFIG_NETFILTER_XT_MATCH_MULTIPORT=m +CONFIG_NETFILTER_XT_MATCH_OWNER=m +CONFIG_NETFILTER_XT_MATCH_POLICY=m +CONFIG_NETFILTER_XT_MATCH_PKTTYPE=m +CONFIG_NETFILTER_XT_MATCH_QUOTA=m +CONFIG_NETFILTER_XT_MATCH_RATEEST=m +CONFIG_NETFILTER_XT_MATCH_REALM=m +CONFIG_NETFILTER_XT_MATCH_RECENT=m +# CONFIG_NETFILTER_XT_MATCH_RECENT_PROC_COMPAT is not set +CONFIG_NETFILTER_XT_MATCH_SCTP=m +CONFIG_NETFILTER_XT_MATCH_SOCKET=m +CONFIG_NETFILTER_XT_MATCH_STATE=m +CONFIG_NETFILTER_XT_MATCH_STATISTIC=m +CONFIG_NETFILTER_XT_MATCH_STRING=m +CONFIG_NETFILTER_XT_MATCH_TCPMSS=m +# CONFIG_NETFILTER_XT_MATCH_TIME is not set +CONFIG_NETFILTER_XT_MATCH_U32=m +# CONFIG_NETFILTER_XT_MATCH_OSF is not set +# CONFIG_IP_VS is not set + +# +# IP: Netfilter Configuration +# +CONFIG_NF_DEFRAG_IPV4=m +CONFIG_NF_CONNTRACK_IPV4=m +CONFIG_NF_CONNTRACK_PROC_COMPAT=y +CONFIG_IP_NF_QUEUE=m +CONFIG_IP_NF_IPTABLES=m +CONFIG_IP_NF_MATCH_ADDRTYPE=m +CONFIG_IP_NF_MATCH_AH=m +CONFIG_IP_NF_MATCH_ECN=m +CONFIG_IP_NF_MATCH_TTL=m +CONFIG_IP_NF_FILTER=m +CONFIG_IP_NF_TARGET_REJECT=m +CONFIG_IP_NF_TARGET_LOG=m +CONFIG_IP_NF_TARGET_ULOG=m +CONFIG_NF_NAT=m +CONFIG_NF_NAT_NEEDED=y +CONFIG_IP_NF_TARGET_MASQUERADE=m +CONFIG_IP_NF_TARGET_NETMAP=m +CONFIG_IP_NF_TARGET_REDIRECT=m +CONFIG_NF_NAT_SNMP_BASIC=m +CONFIG_NF_NAT_PROTO_GRE=m +CONFIG_NF_NAT_PROTO_SCTP=m +CONFIG_NF_NAT_FTP=m +CONFIG_NF_NAT_IRC=m +CONFIG_NF_NAT_TFTP=m +CONFIG_NF_NAT_AMANDA=m +CONFIG_NF_NAT_PPTP=m +CONFIG_NF_NAT_H323=m +CONFIG_NF_NAT_SIP=m +CONFIG_IP_NF_MANGLE=m +CONFIG_IP_NF_TARGET_CLUSTERIP=m +CONFIG_IP_NF_TARGET_ECN=m +CONFIG_IP_NF_TARGET_TTL=m +CONFIG_IP_NF_RAW=m +CONFIG_IP_NF_ARPTABLES=m +CONFIG_IP_NF_ARPFILTER=m +CONFIG_IP_NF_ARP_MANGLE=m +# CONFIG_IP_DCCP is not set +# CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set +# CONFIG_TIPC is not set +# CONFIG_ATM is not set +# CONFIG_BRIDGE is not set +# CONFIG_NET_DSA is not set +# CONFIG_VLAN_8021Q is not set +# CONFIG_DECNET is not set +CONFIG_LLC=y +# CONFIG_LLC2 is not set +# CONFIG_IPX is not set +# CONFIG_ATALK is not set +# CONFIG_X25 is not set +# CONFIG_LAPB is not set +# CONFIG_ECONET is not set +# CONFIG_WAN_ROUTER is not set +# CONFIG_PHONET is not set +# CONFIG_IEEE802154 is not set +# CONFIG_NET_SCHED is not set +CONFIG_NET_CLS_ROUTE=y +# CONFIG_DCB is not set + +# +# Network testing +# +# CONFIG_NET_PKTGEN is not set +# CONFIG_NET_DROP_MONITOR is not set +# CONFIG_HAMRADIO is not set +# CONFIG_CAN is not set +# CONFIG_IRDA is not set +# CONFIG_BT is not set +# CONFIG_AF_RXRPC is not set +CONFIG_WIRELESS=y +# CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 +CONFIG_WIRELESS_OLD_REGULATORY=y +CONFIG_WIRELESS_EXT=y +CONFIG_WIRELESS_EXT_SYSFS=y +# CONFIG_LIB80211 is not set + +# +# CFG80211 needs to be enabled for MAC80211 +# +# CONFIG_WIMAX is not set +# CONFIG_RFKILL is not set +# CONFIG_NET_9P is not set + +# +# Device Drivers +# + +# +# Generic Driver Options +# +CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set +CONFIG_STANDALONE=y +CONFIG_PREVENT_FIRMWARE_BUILD=y +CONFIG_FW_LOADER=y +CONFIG_FIRMWARE_IN_KERNEL=y +CONFIG_EXTRA_FIRMWARE="" +# CONFIG_DEBUG_DRIVER is not set +# CONFIG_DEBUG_DEVRES is not set +# CONFIG_SYS_HYPERVISOR is not set +# CONFIG_CONNECTOR is not set +# CONFIG_MTD is not set +CONFIG_OF_DEVICE=y +CONFIG_OF_I2C=y +CONFIG_OF_MDIO=y +# CONFIG_PARPORT is not set +CONFIG_BLK_DEV=y +CONFIG_BLK_DEV_FD=y +# CONFIG_BLK_CPQ_CISS_DA is not set +# CONFIG_BLK_DEV_DAC960 is not set +# CONFIG_BLK_DEV_UMEM is not set +# CONFIG_BLK_DEV_COW_COMMON is not set +CONFIG_BLK_DEV_LOOP=y +# CONFIG_BLK_DEV_CRYPTOLOOP is not set +CONFIG_BLK_DEV_NBD=m +# CONFIG_BLK_DEV_SX8 is not set +# CONFIG_BLK_DEV_UB is not set +CONFIG_BLK_DEV_RAM=y +CONFIG_BLK_DEV_RAM_COUNT=16 +CONFIG_BLK_DEV_RAM_SIZE=65536 +# CONFIG_BLK_DEV_XIP is not set +# CONFIG_CDROM_PKTCDVD is not set +# CONFIG_ATA_OVER_ETH is not set +# CONFIG_BLK_DEV_HD is not set +CONFIG_MISC_DEVICES=y +# CONFIG_PHANTOM is not set +# CONFIG_SGI_IOC4 is not set +# CONFIG_TIFM_CORE is not set +# CONFIG_ICS932S401 is not set +# CONFIG_ENCLOSURE_SERVICES is not set +# CONFIG_HP_ILO is not set +# CONFIG_ISL29003 is not set +# CONFIG_C2PORT is not set + +# +# EEPROM support +# +# CONFIG_EEPROM_AT24 is not set +# CONFIG_EEPROM_LEGACY is not set +# CONFIG_EEPROM_MAX6875 is not set +# CONFIG_EEPROM_93CX6 is not set +# CONFIG_CB710_CORE is not set +CONFIG_HAVE_IDE=y +CONFIG_IDE=y + +# +# Please see Documentation/ide/ide.txt for help/info on IDE drives +# +CONFIG_IDE_XFER_MODE=y +CONFIG_IDE_TIMINGS=y +CONFIG_IDE_ATAPI=y +# CONFIG_BLK_DEV_IDE_SATA is not set +CONFIG_IDE_GD=y +CONFIG_IDE_GD_ATA=y +# CONFIG_IDE_GD_ATAPI is not set +# CONFIG_BLK_DEV_IDECS is not set +# CONFIG_BLK_DEV_DELKIN is not set +CONFIG_BLK_DEV_IDECD=y +CONFIG_BLK_DEV_IDECD_VERBOSE_ERRORS=y +# CONFIG_BLK_DEV_IDETAPE is not set +# CONFIG_IDE_TASK_IOCTL is not set +CONFIG_IDE_PROC_FS=y + +# +# IDE chipset support/bugfixes +# +# CONFIG_BLK_DEV_PLATFORM is not set +CONFIG_BLK_DEV_IDEDMA_SFF=y + +# +# PCI IDE chipsets support +# +CONFIG_BLK_DEV_IDEPCI=y +CONFIG_IDEPCI_PCIBUS_ORDER=y +# CONFIG_BLK_DEV_OFFBOARD is not set +CONFIG_BLK_DEV_GENERIC=y +# CONFIG_BLK_DEV_OPTI621 is not set +CONFIG_BLK_DEV_IDEDMA_PCI=y +# CONFIG_BLK_DEV_AEC62XX is not set +# CONFIG_BLK_DEV_ALI15X3 is not set +CONFIG_BLK_DEV_AMD74XX=y +# CONFIG_BLK_DEV_CMD64X is not set +# CONFIG_BLK_DEV_TRIFLEX is not set +# CONFIG_BLK_DEV_CS5520 is not set +# CONFIG_BLK_DEV_CS5530 is not set +# CONFIG_BLK_DEV_HPT366 is not set +# CONFIG_BLK_DEV_JMICRON is not set +# CONFIG_BLK_DEV_SC1200 is not set +# CONFIG_BLK_DEV_PIIX is not set +# CONFIG_BLK_DEV_IT8172 is not set +# CONFIG_BLK_DEV_IT8213 is not set +# CONFIG_BLK_DEV_IT821X is not set +# CONFIG_BLK_DEV_NS87415 is not set +# CONFIG_BLK_DEV_PDC202XX_OLD is not set +# CONFIG_BLK_DEV_PDC202XX_NEW is not set +# CONFIG_BLK_DEV_SVWKS is not set +# CONFIG_BLK_DEV_SIIMAGE is not set +# CONFIG_BLK_DEV_SL82C105 is not set +# CONFIG_BLK_DEV_SLC90E66 is not set +# CONFIG_BLK_DEV_TRM290 is not set +# CONFIG_BLK_DEV_VIA82CXXX is not set +# CONFIG_BLK_DEV_TC86C001 is not set +CONFIG_BLK_DEV_IDEDMA=y + +# +# SCSI device support +# +# CONFIG_RAID_ATTRS is not set +CONFIG_SCSI=y +CONFIG_SCSI_DMA=y +# CONFIG_SCSI_TGT is not set +CONFIG_SCSI_NETLINK=y +CONFIG_SCSI_PROC_FS=y + +# +# SCSI support type (disk, tape, CD-ROM) +# +CONFIG_BLK_DEV_SD=y +CONFIG_CHR_DEV_ST=y +# CONFIG_CHR_DEV_OSST is not set +CONFIG_BLK_DEV_SR=y +CONFIG_BLK_DEV_SR_VENDOR=y +CONFIG_CHR_DEV_SG=y +# CONFIG_CHR_DEV_SCH is not set +CONFIG_SCSI_MULTI_LUN=y +CONFIG_SCSI_CONSTANTS=y +# CONFIG_SCSI_LOGGING is not set +# CONFIG_SCSI_SCAN_ASYNC is not set +CONFIG_SCSI_WAIT_SCAN=m + +# +# SCSI Transports +# +CONFIG_SCSI_SPI_ATTRS=y +CONFIG_SCSI_FC_ATTRS=y +CONFIG_SCSI_ISCSI_ATTRS=m +# CONFIG_SCSI_SAS_ATTRS is not set +# CONFIG_SCSI_SAS_LIBSAS is not set +CONFIG_SCSI_SRP_ATTRS=y +CONFIG_SCSI_LOWLEVEL=y +# CONFIG_ISCSI_TCP is not set +# CONFIG_SCSI_CXGB3_ISCSI is not set +# CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set +# CONFIG_BLK_DEV_3W_XXXX_RAID is not set +# CONFIG_SCSI_3W_9XXX is not set +# CONFIG_SCSI_ACARD is not set +# CONFIG_SCSI_AACRAID is not set +# CONFIG_SCSI_AIC7XXX is not set +# CONFIG_SCSI_AIC7XXX_OLD is not set +# CONFIG_SCSI_AIC79XX is not set +# CONFIG_SCSI_AIC94XX is not set +# CONFIG_SCSI_MVSAS is not set +# CONFIG_SCSI_ARCMSR is not set +# CONFIG_MEGARAID_NEWGEN is not set +# CONFIG_MEGARAID_LEGACY is not set +# CONFIG_MEGARAID_SAS is not set +# CONFIG_SCSI_MPT2SAS is not set +# CONFIG_SCSI_HPTIOP is not set +# CONFIG_LIBFC is not set +# CONFIG_LIBFCOE is not set +# CONFIG_FCOE is not set +# CONFIG_SCSI_DMX3191D is not set +# CONFIG_SCSI_EATA is not set +# CONFIG_SCSI_FUTURE_DOMAIN is not set +# CONFIG_SCSI_GDTH is not set +# CONFIG_SCSI_IPS is not set +# CONFIG_SCSI_INITIO is not set +# CONFIG_SCSI_INIA100 is not set +# CONFIG_SCSI_STEX is not set +CONFIG_SCSI_SYM53C8XX_2=y +CONFIG_SCSI_SYM53C8XX_DMA_ADDRESSING_MODE=0 +CONFIG_SCSI_SYM53C8XX_DEFAULT_TAGS=16 +CONFIG_SCSI_SYM53C8XX_MAX_TAGS=64 +CONFIG_SCSI_SYM53C8XX_MMIO=y +CONFIG_SCSI_IPR=y +CONFIG_SCSI_IPR_TRACE=y +CONFIG_SCSI_IPR_DUMP=y +# CONFIG_SCSI_QLOGIC_1280 is not set +# CONFIG_SCSI_QLA_FC is not set +# CONFIG_SCSI_QLA_ISCSI is not set +CONFIG_SCSI_LPFC=m +# CONFIG_SCSI_LPFC_DEBUG_FS is not set +# CONFIG_SCSI_DC395x is not set +# CONFIG_SCSI_DC390T is not set +CONFIG_SCSI_DEBUG=m +# CONFIG_SCSI_PMCRAID is not set +# CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set +# CONFIG_SCSI_LOWLEVEL_PCMCIA is not set +# CONFIG_SCSI_DH is not set +# CONFIG_SCSI_OSD_INITIATOR is not set +CONFIG_ATA=y +# CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y +CONFIG_SATA_PMP=y +# CONFIG_SATA_AHCI is not set +CONFIG_SATA_SIL24=y +CONFIG_ATA_SFF=y +CONFIG_SATA_SVW=y +# CONFIG_ATA_PIIX is not set +# CONFIG_SATA_MV is not set +# CONFIG_SATA_NV is not set +# CONFIG_PDC_ADMA is not set +# CONFIG_SATA_QSTOR is not set +# CONFIG_SATA_PROMISE is not set +# CONFIG_SATA_SX4 is not set +# CONFIG_SATA_SIL is not set +# CONFIG_SATA_SIS is not set +# CONFIG_SATA_ULI is not set +# CONFIG_SATA_VIA is not set +# CONFIG_SATA_VITESSE is not set +# CONFIG_SATA_INIC162X is not set +# CONFIG_PATA_ALI is not set +# CONFIG_PATA_AMD is not set +# CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set +# CONFIG_PATA_ATIIXP is not set +# CONFIG_PATA_CMD640_PCI is not set +# CONFIG_PATA_CMD64X is not set +# CONFIG_PATA_CS5520 is not set +# CONFIG_PATA_CS5530 is not set +# CONFIG_PATA_CYPRESS is not set +# CONFIG_PATA_EFAR is not set +# CONFIG_ATA_GENERIC is not set +# CONFIG_PATA_HPT366 is not set +# CONFIG_PATA_HPT37X is not set +# CONFIG_PATA_HPT3X2N is not set +# CONFIG_PATA_HPT3X3 is not set +# CONFIG_PATA_IT821X is not set +# CONFIG_PATA_IT8213 is not set +# CONFIG_PATA_JMICRON is not set +# CONFIG_PATA_TRIFLEX is not set +# CONFIG_PATA_MARVELL is not set +# CONFIG_PATA_MPIIX is not set +# CONFIG_PATA_OLDPIIX is not set +# CONFIG_PATA_NETCELL is not set +# CONFIG_PATA_NINJA32 is not set +# CONFIG_PATA_NS87410 is not set +# CONFIG_PATA_NS87415 is not set +# CONFIG_PATA_OPTI is not set +# CONFIG_PATA_OPTIDMA is not set +# CONFIG_PATA_PCMCIA is not set +# CONFIG_PATA_PDC_OLD is not set +# CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set +# CONFIG_PATA_RZ1000 is not set +# CONFIG_PATA_SC1200 is not set +# CONFIG_PATA_SERVERWORKS is not set +# CONFIG_PATA_PDC2027X is not set +# CONFIG_PATA_SIL680 is not set +# CONFIG_PATA_SIS is not set +# CONFIG_PATA_VIA is not set +# CONFIG_PATA_WINBOND is not set +# CONFIG_PATA_PLATFORM is not set +# CONFIG_PATA_SCH is not set +CONFIG_MD=y +CONFIG_BLK_DEV_MD=y +CONFIG_MD_AUTODETECT=y +CONFIG_MD_LINEAR=y +CONFIG_MD_RAID0=y +CONFIG_MD_RAID1=y +CONFIG_MD_RAID10=y +CONFIG_MD_RAID456=y +# CONFIG_MULTICORE_RAID456 is not set +CONFIG_MD_RAID6_PQ=y +# CONFIG_ASYNC_RAID6_TEST is not set +CONFIG_MD_MULTIPATH=m +CONFIG_MD_FAULTY=m +CONFIG_BLK_DEV_DM=y +# CONFIG_DM_DEBUG is not set +CONFIG_DM_CRYPT=m +CONFIG_DM_SNAPSHOT=m +CONFIG_DM_MIRROR=m +# CONFIG_DM_LOG_USERSPACE is not set +CONFIG_DM_ZERO=m +CONFIG_DM_MULTIPATH=m +# CONFIG_DM_MULTIPATH_QL is not set +# CONFIG_DM_MULTIPATH_ST is not set +# CONFIG_DM_DELAY is not set +# CONFIG_DM_UEVENT is not set +# CONFIG_FUSION is not set + +# +# IEEE 1394 (FireWire) support +# + +# +# You can enable one or both FireWire driver stacks. +# + +# +# See the help texts for more information. +# +# CONFIG_FIREWIRE is not set +CONFIG_IEEE1394=y +CONFIG_IEEE1394_OHCI1394=y +# CONFIG_IEEE1394_PCILYNX is not set +CONFIG_IEEE1394_SBP2=m +CONFIG_IEEE1394_ETH1394_ROM_ENTRY=y +CONFIG_IEEE1394_ETH1394=m +CONFIG_IEEE1394_RAWIO=y +CONFIG_IEEE1394_VIDEO1394=m +CONFIG_IEEE1394_DV1394=m +# CONFIG_IEEE1394_VERBOSEDEBUG is not set +# CONFIG_I2O is not set +CONFIG_MACINTOSH_DRIVERS=y +# CONFIG_MAC_EMUMOUSEBTN is not set +CONFIG_WINDFARM=y +CONFIG_NETDEVICES=y +CONFIG_DUMMY=m +CONFIG_BONDING=m +# CONFIG_MACVLAN is not set +# CONFIG_EQUALIZER is not set +CONFIG_TUN=m +# CONFIG_VETH is not set +# CONFIG_ARCNET is not set +CONFIG_PHYLIB=y + +# +# MII PHY device drivers +# +CONFIG_MARVELL_PHY=y +# CONFIG_DAVICOM_PHY is not set +# CONFIG_QSEMI_PHY is not set +# CONFIG_LXT_PHY is not set +# CONFIG_CICADA_PHY is not set +# CONFIG_VITESSE_PHY is not set +# CONFIG_SMSC_PHY is not set +CONFIG_BROADCOM_PHY=m +# CONFIG_ICPLUS_PHY is not set +# CONFIG_REALTEK_PHY is not set +# CONFIG_NATIONAL_PHY is not set +# CONFIG_STE10XP is not set +# CONFIG_LSI_ET1011C_PHY is not set +# CONFIG_FIXED_PHY is not set +# CONFIG_MDIO_BITBANG is not set +CONFIG_NET_ETHERNET=y +CONFIG_MII=y +# CONFIG_HAPPYMEAL is not set +CONFIG_SUNGEM=y +# CONFIG_CASSINI is not set +CONFIG_NET_VENDOR_3COM=y +CONFIG_VORTEX=y +# CONFIG_TYPHOON is not set +# CONFIG_ETHOC is not set +# CONFIG_DNET is not set +# CONFIG_NET_TULIP is not set +# CONFIG_HP100 is not set +# CONFIG_IBM_NEW_EMAC_ZMII is not set +# CONFIG_IBM_NEW_EMAC_RGMII is not set +# CONFIG_IBM_NEW_EMAC_TAH is not set +# CONFIG_IBM_NEW_EMAC_EMAC4 is not set +# CONFIG_IBM_NEW_EMAC_NO_FLOW_CTRL is not set +# CONFIG_IBM_NEW_EMAC_MAL_CLR_ICINTSTAT is not set +# CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set +CONFIG_NET_PCI=y +CONFIG_PCNET32=y +# CONFIG_AMD8111_ETH is not set +# CONFIG_ADAPTEC_STARFIRE is not set +# CONFIG_B44 is not set +# CONFIG_FORCEDETH is not set +CONFIG_E100=y +# CONFIG_FEALNX is not set +# CONFIG_NATSEMI is not set +# CONFIG_NE2K_PCI is not set +# CONFIG_8139CP is not set +# CONFIG_8139TOO is not set +# CONFIG_R6040 is not set +# CONFIG_SIS900 is not set +# CONFIG_EPIC100 is not set +# CONFIG_SMSC9420 is not set +# CONFIG_SUNDANCE is not set +# CONFIG_TLAN is not set +# CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_VIA_RHINE is not set +# CONFIG_SC92031 is not set +# CONFIG_ATL2 is not set +CONFIG_NETDEV_1000=y +CONFIG_ACENIC=y +CONFIG_ACENIC_OMIT_TIGON_I=y +# CONFIG_DL2K is not set +CONFIG_E1000=y +# CONFIG_E1000E is not set +# CONFIG_IP1000 is not set +# CONFIG_IGB is not set +# CONFIG_IGBVF is not set +# CONFIG_NS83820 is not set +# CONFIG_HAMACHI is not set +# CONFIG_YELLOWFIN is not set +# CONFIG_R8169 is not set +# CONFIG_SIS190 is not set +# CONFIG_SKGE is not set +# CONFIG_SKY2 is not set +# CONFIG_VIA_VELOCITY is not set +CONFIG_TIGON3=y +# CONFIG_BNX2 is not set +# CONFIG_CNIC is not set +# CONFIG_QLA3XXX is not set +# CONFIG_ATL1 is not set +# CONFIG_ATL1E is not set +# CONFIG_ATL1C is not set +# CONFIG_JME is not set +CONFIG_NETDEV_10000=y +# CONFIG_CHELSIO_T1 is not set +CONFIG_CHELSIO_T3_DEPENDS=y +# CONFIG_CHELSIO_T3 is not set +# CONFIG_ENIC is not set +# CONFIG_IXGBE is not set +CONFIG_IXGB=m +# CONFIG_S2IO is not set +# CONFIG_VXGE is not set +# CONFIG_MYRI10GE is not set +# CONFIG_NETXEN_NIC is not set +# CONFIG_NIU is not set +# CONFIG_MLX4_EN is not set +# CONFIG_MLX4_CORE is not set +# CONFIG_TEHUTI is not set +# CONFIG_BNX2X is not set +# CONFIG_QLGE is not set +# CONFIG_SFC is not set +# CONFIG_BE2NET is not set +CONFIG_TR=y +CONFIG_IBMOL=y +# CONFIG_3C359 is not set +# CONFIG_TMS380TR is not set +CONFIG_WLAN=y +# CONFIG_WLAN_PRE80211 is not set +# CONFIG_WLAN_80211 is not set + +# +# Enable WiMAX (Networking options) to see the WiMAX drivers +# + +# +# USB Network Adapters +# +# CONFIG_USB_CATC is not set +# CONFIG_USB_KAWETH is not set +# CONFIG_USB_PEGASUS is not set +# CONFIG_USB_RTL8150 is not set +# CONFIG_USB_USBNET is not set +# CONFIG_NET_PCMCIA is not set +# CONFIG_WAN is not set +# CONFIG_FDDI is not set +# CONFIG_HIPPI is not set +CONFIG_PPP=m +# CONFIG_PPP_MULTILINK is not set +# CONFIG_PPP_FILTER is not set +CONFIG_PPP_ASYNC=m +CONFIG_PPP_SYNC_TTY=m +CONFIG_PPP_DEFLATE=m +CONFIG_PPP_BSDCOMP=m +# CONFIG_PPP_MPPE is not set +CONFIG_PPPOE=m +# CONFIG_PPPOL2TP is not set +# CONFIG_SLIP is not set +CONFIG_SLHC=m +# CONFIG_NET_FC is not set +CONFIG_NETCONSOLE=y +# CONFIG_NETCONSOLE_DYNAMIC is not set +CONFIG_NETPOLL=y +CONFIG_NETPOLL_TRAP=y +CONFIG_NET_POLL_CONTROLLER=y +# CONFIG_ISDN is not set +# CONFIG_PHONE is not set + +# +# Input device support +# +CONFIG_INPUT=y +# CONFIG_INPUT_FF_MEMLESS is not set +# CONFIG_INPUT_POLLDEV is not set + +# +# Userland interfaces +# +CONFIG_INPUT_MOUSEDEV=y +# CONFIG_INPUT_MOUSEDEV_PSAUX is not set +CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024 +CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768 +# CONFIG_INPUT_JOYDEV is not set +CONFIG_INPUT_EVDEV=m +# CONFIG_INPUT_EVBUG is not set + +# +# Input Device Drivers +# +CONFIG_INPUT_KEYBOARD=y +# CONFIG_KEYBOARD_ADP5588 is not set +CONFIG_KEYBOARD_ATKBD=y +# CONFIG_QT2160 is not set +# CONFIG_KEYBOARD_LKKBD is not set +# CONFIG_KEYBOARD_MAX7359 is not set +# CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set +# CONFIG_KEYBOARD_STOWAWAY is not set +# CONFIG_KEYBOARD_SUNKBD is not set +# CONFIG_KEYBOARD_XTKBD is not set +CONFIG_INPUT_MOUSE=y +CONFIG_MOUSE_PS2=y +CONFIG_MOUSE_PS2_ALPS=y +CONFIG_MOUSE_PS2_LOGIPS2PP=y +CONFIG_MOUSE_PS2_SYNAPTICS=y +CONFIG_MOUSE_PS2_TRACKPOINT=y +# CONFIG_MOUSE_PS2_ELANTECH is not set +# CONFIG_MOUSE_PS2_SENTELIC is not set +# CONFIG_MOUSE_PS2_TOUCHKIT is not set +# CONFIG_MOUSE_SERIAL is not set +# CONFIG_MOUSE_APPLETOUCH is not set +# CONFIG_MOUSE_BCM5974 is not set +# CONFIG_MOUSE_VSXXXAA is not set +# CONFIG_MOUSE_SYNAPTICS_I2C is not set +# CONFIG_INPUT_JOYSTICK is not set +# CONFIG_INPUT_TABLET is not set +# CONFIG_INPUT_TOUCHSCREEN is not set +CONFIG_INPUT_MISC=y +# CONFIG_INPUT_ATI_REMOTE is not set +# CONFIG_INPUT_ATI_REMOTE2 is not set +# CONFIG_INPUT_KEYSPAN_REMOTE is not set +# CONFIG_INPUT_POWERMATE is not set +# CONFIG_INPUT_YEALINK is not set +# CONFIG_INPUT_CM109 is not set +# CONFIG_INPUT_UINPUT is not set + +# +# Hardware I/O ports +# +CONFIG_SERIO=y +CONFIG_SERIO_I8042=y +# CONFIG_SERIO_SERPORT is not set +# CONFIG_SERIO_PCIPS2 is not set +CONFIG_SERIO_LIBPS2=y +# CONFIG_SERIO_RAW is not set +# CONFIG_SERIO_XILINX_XPS_PS2 is not set +# CONFIG_GAMEPORT is not set + +# +# Character devices +# +CONFIG_VT=y +CONFIG_CONSOLE_TRANSLATIONS=y +CONFIG_VT_CONSOLE=y +CONFIG_HW_CONSOLE=y +CONFIG_VT_HW_CONSOLE_BINDING=y +CONFIG_DEVKMEM=y +# CONFIG_SERIAL_NONSTANDARD is not set +# CONFIG_NOZOMI is not set + +# +# Serial drivers +# +CONFIG_SERIAL_8250=y +CONFIG_SERIAL_8250_CONSOLE=y +CONFIG_SERIAL_8250_PCI=y +# CONFIG_SERIAL_8250_CS is not set +CONFIG_SERIAL_8250_NR_UARTS=4 +CONFIG_SERIAL_8250_RUNTIME_UARTS=4 +# CONFIG_SERIAL_8250_EXTENDED is not set + +# +# Non-8250 serial port support +# +CONFIG_SERIAL_CORE=y +CONFIG_SERIAL_CORE_CONSOLE=y +# CONFIG_SERIAL_JSM is not set +# CONFIG_SERIAL_OF_PLATFORM is not set +CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set +CONFIG_LEGACY_PTYS=y +CONFIG_LEGACY_PTY_COUNT=256 +# CONFIG_HVC_UDBG is not set +# CONFIG_IPMI_HANDLER is not set +# CONFIG_HW_RANDOM is not set +# CONFIG_R3964 is not set +# CONFIG_APPLICOM is not set + +# +# PCMCIA character devices +# +# CONFIG_SYNCLINK_CS is not set +# CONFIG_CARDMAN_4000 is not set +# CONFIG_CARDMAN_4040 is not set +# CONFIG_IPWIRELESS is not set +CONFIG_RAW_DRIVER=y +CONFIG_MAX_RAW_DEVS=256 +# CONFIG_HANGCHECK_TIMER is not set +# CONFIG_TCG_TPM is not set +CONFIG_DEVPORT=y +CONFIG_I2C=y +CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y +CONFIG_I2C_CHARDEV=y +CONFIG_I2C_HELPER_AUTO=y +CONFIG_I2C_ALGOBIT=y + +# +# I2C Hardware Bus support +# + +# +# PC SMBus host controller drivers +# +# CONFIG_I2C_ALI1535 is not set +# CONFIG_I2C_ALI1563 is not set +# CONFIG_I2C_ALI15X3 is not set +# CONFIG_I2C_AMD756 is not set +CONFIG_I2C_AMD8111=y +# CONFIG_I2C_I801 is not set +# CONFIG_I2C_ISCH is not set +# CONFIG_I2C_PIIX4 is not set +# CONFIG_I2C_NFORCE2 is not set +# CONFIG_I2C_SIS5595 is not set +# CONFIG_I2C_SIS630 is not set +# CONFIG_I2C_SIS96X is not set +# CONFIG_I2C_VIA is not set +# CONFIG_I2C_VIAPRO is not set + +# +# I2C system bus drivers (mostly embedded / system-on-chip) +# +# CONFIG_I2C_OCORES is not set +# CONFIG_I2C_SIMTEC is not set + +# +# External I2C/SMBus adapter drivers +# +# CONFIG_I2C_PARPORT_LIGHT is not set +# CONFIG_I2C_TAOS_EVM is not set +# CONFIG_I2C_TINY_USB is not set + +# +# Graphics adapter I2C/DDC channel drivers +# +# CONFIG_I2C_VOODOO3 is not set + +# +# Other I2C/SMBus bus drivers +# +# CONFIG_I2C_PCA_PLATFORM is not set +# CONFIG_I2C_STUB is not set + +# +# Miscellaneous I2C Chip support +# +# CONFIG_DS1682 is not set +# CONFIG_SENSORS_TSL2550 is not set +# CONFIG_I2C_DEBUG_CORE is not set +# CONFIG_I2C_DEBUG_ALGO is not set +# CONFIG_I2C_DEBUG_BUS is not set +# CONFIG_I2C_DEBUG_CHIP is not set +# CONFIG_SPI is not set + +# +# PPS support +# +# CONFIG_PPS is not set +CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y +# CONFIG_GPIOLIB is not set +# CONFIG_W1 is not set +# CONFIG_POWER_SUPPLY is not set +# CONFIG_HWMON is not set +# CONFIG_THERMAL is not set +# CONFIG_WATCHDOG is not set +CONFIG_SSB_POSSIBLE=y + +# +# Sonics Silicon Backplane +# +# CONFIG_SSB is not set + +# +# Multifunction device drivers +# +# CONFIG_MFD_CORE is not set +# CONFIG_MFD_SM501 is not set +# CONFIG_HTC_PASIC3 is not set +# CONFIG_TWL4030_CORE is not set +# CONFIG_MFD_TMIO is not set +# CONFIG_PMIC_DA903X is not set +# CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set +# CONFIG_MFD_WM8350_I2C is not set +# CONFIG_MFD_PCF50633 is not set +# CONFIG_AB3100_CORE is not set +# CONFIG_REGULATOR is not set +# CONFIG_MEDIA_SUPPORT is not set + +# +# Graphics support +# +# CONFIG_AGP is not set +CONFIG_VGA_ARB=y +# CONFIG_DRM is not set +# CONFIG_VGASTATE is not set +CONFIG_VIDEO_OUTPUT_CONTROL=m +CONFIG_FB=y +CONFIG_FIRMWARE_EDID=y +CONFIG_FB_DDC=y +# CONFIG_FB_BOOT_VESA_SUPPORT is not set +CONFIG_FB_CFB_FILLRECT=y +CONFIG_FB_CFB_COPYAREA=y +CONFIG_FB_CFB_IMAGEBLIT=y +# CONFIG_FB_CFB_REV_PIXELS_IN_BYTE is not set +# CONFIG_FB_SYS_FILLRECT is not set +# CONFIG_FB_SYS_COPYAREA is not set +# CONFIG_FB_SYS_IMAGEBLIT is not set +# CONFIG_FB_FOREIGN_ENDIAN is not set +# CONFIG_FB_SYS_FOPS is not set +# CONFIG_FB_SVGALIB is not set +CONFIG_FB_MACMODES=y +CONFIG_FB_BACKLIGHT=y +CONFIG_FB_MODE_HELPERS=y +CONFIG_FB_TILEBLITTING=y + +# +# Frame buffer hardware drivers +# +# CONFIG_FB_CIRRUS is not set +# CONFIG_FB_PM2 is not set +# CONFIG_FB_CYBER2000 is not set +CONFIG_FB_OF=y +# CONFIG_FB_ASILIANT is not set +# CONFIG_FB_IMSTT is not set +# CONFIG_FB_VGA16 is not set +# CONFIG_FB_S1D13XXX is not set +# CONFIG_FB_NVIDIA is not set +# CONFIG_FB_RIVA is not set +CONFIG_FB_MATROX=y +CONFIG_FB_MATROX_MILLENIUM=y +CONFIG_FB_MATROX_MYSTIQUE=y +CONFIG_FB_MATROX_G=y +CONFIG_FB_MATROX_I2C=m +CONFIG_FB_MATROX_MAVEN=m +CONFIG_FB_RADEON=y +CONFIG_FB_RADEON_I2C=y +CONFIG_FB_RADEON_BACKLIGHT=y +# CONFIG_FB_RADEON_DEBUG is not set +# CONFIG_FB_ATY128 is not set +# CONFIG_FB_ATY is not set +# CONFIG_FB_S3 is not set +# CONFIG_FB_SAVAGE is not set +# CONFIG_FB_SIS is not set +# CONFIG_FB_VIA is not set +# CONFIG_FB_NEOMAGIC is not set +# CONFIG_FB_KYRO is not set +# CONFIG_FB_3DFX is not set +# CONFIG_FB_VOODOO1 is not set +# CONFIG_FB_VT8623 is not set +# CONFIG_FB_TRIDENT is not set +# CONFIG_FB_ARK is not set +# CONFIG_FB_PM3 is not set +# CONFIG_FB_CARMINE is not set +CONFIG_FB_IBM_GXT4500=y +# CONFIG_FB_VIRTUAL is not set +# CONFIG_FB_METRONOME is not set +# CONFIG_FB_MB862XX is not set +# CONFIG_FB_BROADSHEET is not set +CONFIG_BACKLIGHT_LCD_SUPPORT=y +CONFIG_LCD_CLASS_DEVICE=y +# CONFIG_LCD_ILI9320 is not set +# CONFIG_LCD_PLATFORM is not set +CONFIG_BACKLIGHT_CLASS_DEVICE=y +CONFIG_BACKLIGHT_GENERIC=y + +# +# Display device support +# +CONFIG_DISPLAY_SUPPORT=y + +# +# Display hardware drivers +# + +# +# Console display driver support +# +# CONFIG_VGA_CONSOLE is not set +CONFIG_DUMMY_CONSOLE=y +CONFIG_FRAMEBUFFER_CONSOLE=y +# CONFIG_FRAMEBUFFER_CONSOLE_DETECT_PRIMARY is not set +# CONFIG_FRAMEBUFFER_CONSOLE_ROTATION is not set +# CONFIG_FONTS is not set +CONFIG_FONT_8x8=y +CONFIG_FONT_8x16=y +CONFIG_LOGO=y +CONFIG_LOGO_LINUX_MONO=y +CONFIG_LOGO_LINUX_VGA16=y +CONFIG_LOGO_LINUX_CLUT224=y +CONFIG_SOUND=m +CONFIG_SOUND_OSS_CORE=y +CONFIG_SOUND_OSS_CORE_PRECLAIM=y +CONFIG_SND=m +CONFIG_SND_TIMER=m +CONFIG_SND_PCM=m +CONFIG_SND_SEQUENCER=m +CONFIG_SND_SEQ_DUMMY=m +CONFIG_SND_OSSEMUL=y +CONFIG_SND_MIXER_OSS=m +CONFIG_SND_PCM_OSS=m +CONFIG_SND_PCM_OSS_PLUGINS=y +CONFIG_SND_SEQUENCER_OSS=y +# CONFIG_SND_HRTIMER is not set +# CONFIG_SND_DYNAMIC_MINORS is not set +CONFIG_SND_SUPPORT_OLD_API=y +CONFIG_SND_VERBOSE_PROCFS=y +# CONFIG_SND_VERBOSE_PRINTK is not set +# CONFIG_SND_DEBUG is not set +# CONFIG_SND_RAWMIDI_SEQ is not set +# CONFIG_SND_OPL3_LIB_SEQ is not set +# CONFIG_SND_OPL4_LIB_SEQ is not set +# CONFIG_SND_SBAWE_SEQ is not set +# CONFIG_SND_EMU10K1_SEQ is not set +CONFIG_SND_DRIVERS=y +# CONFIG_SND_DUMMY is not set +# CONFIG_SND_VIRMIDI is not set +# CONFIG_SND_MTPAV is not set +# CONFIG_SND_SERIAL_U16550 is not set +# CONFIG_SND_MPU401 is not set +CONFIG_SND_PCI=y +# CONFIG_SND_AD1889 is not set +# CONFIG_SND_ALS300 is not set +# CONFIG_SND_ALS4000 is not set +# CONFIG_SND_ALI5451 is not set +# CONFIG_SND_ATIIXP is not set +# CONFIG_SND_ATIIXP_MODEM is not set +# CONFIG_SND_AU8810 is not set +# CONFIG_SND_AU8820 is not set +# CONFIG_SND_AU8830 is not set +# CONFIG_SND_AW2 is not set +# CONFIG_SND_AZT3328 is not set +# CONFIG_SND_BT87X is not set +# CONFIG_SND_CA0106 is not set +# CONFIG_SND_CMIPCI is not set +# CONFIG_SND_OXYGEN is not set +# CONFIG_SND_CS4281 is not set +# CONFIG_SND_CS46XX is not set +# CONFIG_SND_CS5530 is not set +# CONFIG_SND_CTXFI is not set +# CONFIG_SND_DARLA20 is not set +# CONFIG_SND_GINA20 is not set +# CONFIG_SND_LAYLA20 is not set +# CONFIG_SND_DARLA24 is not set +# CONFIG_SND_GINA24 is not set +# CONFIG_SND_LAYLA24 is not set +# CONFIG_SND_MONA is not set +# CONFIG_SND_MIA is not set +# CONFIG_SND_ECHO3G is not set +# CONFIG_SND_INDIGO is not set +# CONFIG_SND_INDIGOIO is not set +# CONFIG_SND_INDIGODJ is not set +# CONFIG_SND_INDIGOIOX is not set +# CONFIG_SND_INDIGODJX is not set +# CONFIG_SND_EMU10K1 is not set +# CONFIG_SND_EMU10K1X is not set +# CONFIG_SND_ENS1370 is not set +# CONFIG_SND_ENS1371 is not set +# CONFIG_SND_ES1938 is not set +# CONFIG_SND_ES1968 is not set +# CONFIG_SND_FM801 is not set +# CONFIG_SND_HDA_INTEL is not set +# CONFIG_SND_HDSP is not set +# CONFIG_SND_HDSPM is not set +# CONFIG_SND_HIFIER is not set +# CONFIG_SND_ICE1712 is not set +# CONFIG_SND_ICE1724 is not set +# CONFIG_SND_INTEL8X0 is not set +# CONFIG_SND_INTEL8X0M is not set +# CONFIG_SND_KORG1212 is not set +# CONFIG_SND_LX6464ES is not set +# CONFIG_SND_MAESTRO3 is not set +# CONFIG_SND_MIXART is not set +# CONFIG_SND_NM256 is not set +# CONFIG_SND_PCXHR is not set +# CONFIG_SND_RIPTIDE is not set +# CONFIG_SND_RME32 is not set +# CONFIG_SND_RME96 is not set +# CONFIG_SND_RME9652 is not set +# CONFIG_SND_SONICVIBES is not set +# CONFIG_SND_TRIDENT is not set +# CONFIG_SND_VIA82XX is not set +# CONFIG_SND_VIA82XX_MODEM is not set +# CONFIG_SND_VIRTUOSO is not set +# CONFIG_SND_VX222 is not set +# CONFIG_SND_YMFPCI is not set +CONFIG_SND_PPC=y +CONFIG_SND_USB=y +# CONFIG_SND_USB_AUDIO is not set +# CONFIG_SND_USB_USX2Y is not set +# CONFIG_SND_USB_CAIAQ is not set +CONFIG_SND_PCMCIA=y +# CONFIG_SND_VXPOCKET is not set +# CONFIG_SND_PDAUDIOCF is not set +# CONFIG_SND_SOC is not set +# CONFIG_SOUND_PRIME is not set +CONFIG_HID_SUPPORT=y +CONFIG_HID=y +# CONFIG_HIDRAW is not set + +# +# USB Input Devices +# +CONFIG_USB_HID=y +# CONFIG_HID_PID is not set +CONFIG_USB_HIDDEV=y + +# +# Special HID drivers +# +CONFIG_HID_A4TECH=y +CONFIG_HID_APPLE=y +CONFIG_HID_BELKIN=y +CONFIG_HID_CHERRY=y +CONFIG_HID_CHICONY=y +CONFIG_HID_CYPRESS=y +CONFIG_HID_DRAGONRISE=y +# CONFIG_DRAGONRISE_FF is not set +CONFIG_HID_EZKEY=y +CONFIG_HID_KYE=y +CONFIG_HID_GYRATION=y +CONFIG_HID_TWINHAN=y +CONFIG_HID_KENSINGTON=y +CONFIG_HID_LOGITECH=y +# CONFIG_LOGITECH_FF is not set +# CONFIG_LOGIRUMBLEPAD2_FF is not set +CONFIG_HID_MICROSOFT=y +CONFIG_HID_MONTEREY=y +CONFIG_HID_NTRIG=y +CONFIG_HID_PANTHERLORD=y +# CONFIG_PANTHERLORD_FF is not set +CONFIG_HID_PETALYNX=y +CONFIG_HID_SAMSUNG=y +CONFIG_HID_SONY=y +CONFIG_HID_SUNPLUS=y +CONFIG_HID_GREENASIA=y +# CONFIG_GREENASIA_FF is not set +CONFIG_HID_SMARTJOYPLUS=y +# CONFIG_SMARTJOYPLUS_FF is not set +CONFIG_HID_TOPSEED=y +CONFIG_HID_THRUSTMASTER=y +# CONFIG_THRUSTMASTER_FF is not set +CONFIG_HID_ZEROPLUS=y +# CONFIG_ZEROPLUS_FF is not set +CONFIG_USB_SUPPORT=y +CONFIG_USB_ARCH_HAS_HCD=y +CONFIG_USB_ARCH_HAS_OHCI=y +CONFIG_USB_ARCH_HAS_EHCI=y +CONFIG_USB=y +# CONFIG_USB_DEBUG is not set +# CONFIG_USB_ANNOUNCE_NEW_DEVICES is not set + +# +# Miscellaneous USB options +# +CONFIG_USB_DEVICEFS=y +CONFIG_USB_DEVICE_CLASS=y +# CONFIG_USB_DYNAMIC_MINORS is not set +# CONFIG_USB_OTG is not set +# CONFIG_USB_MON is not set +# CONFIG_USB_WUSB is not set +# CONFIG_USB_WUSB_CBAF is not set + +# +# USB Host Controller Drivers +# +# CONFIG_USB_C67X00_HCD is not set +# CONFIG_USB_XHCI_HCD is not set +CONFIG_USB_EHCI_HCD=y +# CONFIG_USB_EHCI_ROOT_HUB_TT is not set +CONFIG_USB_EHCI_TT_NEWSCHED=y +# CONFIG_USB_EHCI_HCD_PPC_OF is not set +# CONFIG_USB_OXU210HP_HCD is not set +# CONFIG_USB_ISP116X_HCD is not set +# CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set +CONFIG_USB_OHCI_HCD=y +# CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set +# CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set +# CONFIG_USB_OHCI_HCD_PPC_OF is not set +# CONFIG_USB_OHCI_BIG_ENDIAN_DESC is not set +# CONFIG_USB_OHCI_BIG_ENDIAN_MMIO is not set +CONFIG_USB_OHCI_LITTLE_ENDIAN=y +# CONFIG_USB_UHCI_HCD is not set +# CONFIG_USB_SL811_HCD is not set +# CONFIG_USB_R8A66597_HCD is not set +# CONFIG_USB_WHCI_HCD is not set +# CONFIG_USB_HWA_HCD is not set + +# +# USB Device Class drivers +# +# CONFIG_USB_ACM is not set +# CONFIG_USB_PRINTER is not set +# CONFIG_USB_WDM is not set +# CONFIG_USB_TMC is not set + +# +# NOTE: USB_STORAGE depends on SCSI but BLK_DEV_SD may +# + +# +# also be needed; see USB_STORAGE Help for more info +# +CONFIG_USB_STORAGE=m +# CONFIG_USB_STORAGE_DEBUG is not set +# CONFIG_USB_STORAGE_DATAFAB is not set +# CONFIG_USB_STORAGE_FREECOM is not set +# CONFIG_USB_STORAGE_ISD200 is not set +# CONFIG_USB_STORAGE_USBAT is not set +# CONFIG_USB_STORAGE_SDDR09 is not set +# CONFIG_USB_STORAGE_SDDR55 is not set +# CONFIG_USB_STORAGE_JUMPSHOT is not set +# CONFIG_USB_STORAGE_ALAUDA is not set +# CONFIG_USB_STORAGE_ONETOUCH is not set +# CONFIG_USB_STORAGE_KARMA is not set +# CONFIG_USB_STORAGE_CYPRESS_ATACB is not set +# CONFIG_USB_LIBUSUAL is not set + +# +# USB Imaging devices +# +# CONFIG_USB_MDC800 is not set +# CONFIG_USB_MICROTEK is not set + +# +# USB port drivers +# +# CONFIG_USB_SERIAL is not set + +# +# USB Miscellaneous drivers +# +# CONFIG_USB_EMI62 is not set +# CONFIG_USB_EMI26 is not set +# CONFIG_USB_ADUTUX is not set +# CONFIG_USB_SEVSEG is not set +# CONFIG_USB_RIO500 is not set +# CONFIG_USB_LEGOTOWER is not set +# CONFIG_USB_LCD is not set +# CONFIG_USB_BERRY_CHARGE is not set +# CONFIG_USB_LED is not set +# CONFIG_USB_CYPRESS_CY7C63 is not set +# CONFIG_USB_CYTHERM is not set +# CONFIG_USB_IDMOUSE is not set +# CONFIG_USB_FTDI_ELAN is not set +CONFIG_USB_APPLEDISPLAY=m +# CONFIG_USB_SISUSBVGA is not set +# CONFIG_USB_LD is not set +# CONFIG_USB_TRANCEVIBRATOR is not set +# CONFIG_USB_IOWARRIOR is not set +# CONFIG_USB_TEST is not set +# CONFIG_USB_ISIGHTFW is not set +# CONFIG_USB_VST is not set +# CONFIG_USB_GADGET is not set + +# +# OTG and related infrastructure +# +# CONFIG_NOP_USB_XCEIV is not set +# CONFIG_UWB is not set +# CONFIG_MMC is not set +# CONFIG_MEMSTICK is not set +# CONFIG_NEW_LEDS is not set +# CONFIG_ACCESSIBILITY is not set +CONFIG_INFINIBAND=m +# CONFIG_INFINIBAND_USER_MAD is not set +# CONFIG_INFINIBAND_USER_ACCESS is not set +CONFIG_INFINIBAND_ADDR_TRANS=y +CONFIG_INFINIBAND_MTHCA=m +CONFIG_INFINIBAND_MTHCA_DEBUG=y +# CONFIG_INFINIBAND_IPATH is not set +# CONFIG_INFINIBAND_AMSO1100 is not set +# CONFIG_MLX4_INFINIBAND is not set +# CONFIG_INFINIBAND_NES is not set +CONFIG_INFINIBAND_IPOIB=m +# CONFIG_INFINIBAND_IPOIB_CM is not set +CONFIG_INFINIBAND_IPOIB_DEBUG=y +# CONFIG_INFINIBAND_IPOIB_DEBUG_DATA is not set +# CONFIG_INFINIBAND_SRP is not set +CONFIG_INFINIBAND_ISER=m +CONFIG_EDAC=y + +# +# Reporting subsystems +# +# CONFIG_EDAC_DEBUG is not set +CONFIG_EDAC_MM_EDAC=y +# CONFIG_EDAC_CPC925 is not set +CONFIG_RTC_LIB=y +CONFIG_RTC_CLASS=y +CONFIG_RTC_HCTOSYS=y +CONFIG_RTC_HCTOSYS_DEVICE="rtc0" +# CONFIG_RTC_DEBUG is not set + +# +# RTC interfaces +# +CONFIG_RTC_INTF_SYSFS=y +CONFIG_RTC_INTF_PROC=y +CONFIG_RTC_INTF_DEV=y +# CONFIG_RTC_INTF_DEV_UIE_EMUL is not set +# CONFIG_RTC_DRV_TEST is not set + +# +# I2C RTC drivers +# +CONFIG_RTC_DRV_DS1307=y +# CONFIG_RTC_DRV_DS1374 is not set +# CONFIG_RTC_DRV_DS1672 is not set +# CONFIG_RTC_DRV_MAX6900 is not set +# CONFIG_RTC_DRV_RS5C372 is not set +# CONFIG_RTC_DRV_ISL1208 is not set +# CONFIG_RTC_DRV_X1205 is not set +# CONFIG_RTC_DRV_PCF8563 is not set +# CONFIG_RTC_DRV_PCF8583 is not set +# CONFIG_RTC_DRV_M41T80 is not set +# CONFIG_RTC_DRV_S35390A is not set +# CONFIG_RTC_DRV_FM3130 is not set +# CONFIG_RTC_DRV_RX8581 is not set +# CONFIG_RTC_DRV_RX8025 is not set + +# +# SPI RTC drivers +# + +# +# Platform RTC drivers +# +# CONFIG_RTC_DRV_CMOS is not set +# CONFIG_RTC_DRV_DS1286 is not set +# CONFIG_RTC_DRV_DS1511 is not set +# CONFIG_RTC_DRV_DS1553 is not set +# CONFIG_RTC_DRV_DS1742 is not set +# CONFIG_RTC_DRV_STK17TA8 is not set +# CONFIG_RTC_DRV_M48T86 is not set +# CONFIG_RTC_DRV_M48T35 is not set +# CONFIG_RTC_DRV_M48T59 is not set +# CONFIG_RTC_DRV_BQ4802 is not set +# CONFIG_RTC_DRV_V3020 is not set + +# +# on-CPU RTC drivers +# +# CONFIG_RTC_DRV_GENERIC is not set +# CONFIG_DMADEVICES is not set +# CONFIG_AUXDISPLAY is not set +# CONFIG_UIO is not set + +# +# TI VLYNQ +# +# CONFIG_STAGING is not set + +# +# File systems +# +CONFIG_EXT2_FS=y +CONFIG_EXT2_FS_XATTR=y +CONFIG_EXT2_FS_POSIX_ACL=y +CONFIG_EXT2_FS_SECURITY=y +CONFIG_EXT2_FS_XIP=y +CONFIG_EXT3_FS=y +# CONFIG_EXT3_DEFAULTS_TO_ORDERED is not set +CONFIG_EXT3_FS_XATTR=y +CONFIG_EXT3_FS_POSIX_ACL=y +CONFIG_EXT3_FS_SECURITY=y +CONFIG_EXT4_FS=y +CONFIG_EXT4_FS_XATTR=y +CONFIG_EXT4_FS_POSIX_ACL=y +CONFIG_EXT4_FS_SECURITY=y +# CONFIG_EXT4_DEBUG is not set +CONFIG_FS_XIP=y +CONFIG_JBD=y +# CONFIG_JBD_DEBUG is not set +CONFIG_JBD2=y +# CONFIG_JBD2_DEBUG is not set +CONFIG_FS_MBCACHE=y +CONFIG_REISERFS_FS=y +# CONFIG_REISERFS_CHECK is not set +# CONFIG_REISERFS_PROC_INFO is not set +CONFIG_REISERFS_FS_XATTR=y +CONFIG_REISERFS_FS_POSIX_ACL=y +CONFIG_REISERFS_FS_SECURITY=y +CONFIG_JFS_FS=y +CONFIG_JFS_POSIX_ACL=y +CONFIG_JFS_SECURITY=y +# CONFIG_JFS_DEBUG is not set +# CONFIG_JFS_STATISTICS is not set +CONFIG_FS_POSIX_ACL=y +CONFIG_XFS_FS=m +# CONFIG_XFS_QUOTA is not set +CONFIG_XFS_POSIX_ACL=y +# CONFIG_XFS_RT is not set +# CONFIG_XFS_DEBUG is not set +# CONFIG_GFS2_FS is not set +# CONFIG_OCFS2_FS is not set +# CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set +CONFIG_FILE_LOCKING=y +CONFIG_FSNOTIFY=y +CONFIG_DNOTIFY=y +CONFIG_INOTIFY=y +CONFIG_INOTIFY_USER=y +# CONFIG_QUOTA is not set +# CONFIG_AUTOFS_FS is not set +CONFIG_AUTOFS4_FS=m +# CONFIG_FUSE_FS is not set + +# +# Caches +# +# CONFIG_FSCACHE is not set + +# +# CD-ROM/DVD Filesystems +# +CONFIG_ISO9660_FS=y +# CONFIG_JOLIET is not set +# CONFIG_ZISOFS is not set +CONFIG_UDF_FS=m +CONFIG_UDF_NLS=y + +# +# DOS/FAT/NT Filesystems +# +CONFIG_FAT_FS=y +CONFIG_MSDOS_FS=y +CONFIG_VFAT_FS=y +CONFIG_FAT_DEFAULT_CODEPAGE=437 +CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1" +# CONFIG_NTFS_FS is not set + +# +# Pseudo filesystems +# +CONFIG_PROC_FS=y +CONFIG_PROC_KCORE=y +CONFIG_PROC_SYSCTL=y +CONFIG_PROC_PAGE_MONITOR=y +CONFIG_SYSFS=y +CONFIG_TMPFS=y +# CONFIG_TMPFS_POSIX_ACL is not set +# CONFIG_HUGETLBFS is not set +# CONFIG_HUGETLB_PAGE is not set +# CONFIG_CONFIGFS_FS is not set +CONFIG_MISC_FILESYSTEMS=y +# CONFIG_ADFS_FS is not set +# CONFIG_AFFS_FS is not set +CONFIG_HFS_FS=m +CONFIG_HFSPLUS_FS=m +# CONFIG_BEFS_FS is not set +# CONFIG_BFS_FS is not set +# CONFIG_EFS_FS is not set +CONFIG_CRAMFS=y +# CONFIG_SQUASHFS is not set +# CONFIG_VXFS_FS is not set +# CONFIG_MINIX_FS is not set +# CONFIG_OMFS_FS is not set +# CONFIG_HPFS_FS is not set +# CONFIG_QNX4FS_FS is not set +# CONFIG_ROMFS_FS is not set +# CONFIG_SYSV_FS is not set +# CONFIG_UFS_FS is not set +CONFIG_NETWORK_FILESYSTEMS=y +CONFIG_NFS_FS=y +CONFIG_NFS_V3=y +CONFIG_NFS_V3_ACL=y +CONFIG_NFS_V4=y +# CONFIG_NFS_V4_1 is not set +CONFIG_ROOT_NFS=y +CONFIG_NFSD=m +CONFIG_NFSD_V2_ACL=y +CONFIG_NFSD_V3=y +CONFIG_NFSD_V3_ACL=y +CONFIG_NFSD_V4=y +CONFIG_LOCKD=y +CONFIG_LOCKD_V4=y +CONFIG_EXPORTFS=m +CONFIG_NFS_ACL_SUPPORT=y +CONFIG_NFS_COMMON=y +CONFIG_SUNRPC=y +CONFIG_SUNRPC_GSS=y +CONFIG_SUNRPC_XPRT_RDMA=m +CONFIG_RPCSEC_GSS_KRB5=y +CONFIG_RPCSEC_GSS_SPKM3=m +# CONFIG_SMB_FS is not set +CONFIG_CIFS=m +# CONFIG_CIFS_STATS is not set +# CONFIG_CIFS_WEAK_PW_HASH is not set +CONFIG_CIFS_XATTR=y +CONFIG_CIFS_POSIX=y +# CONFIG_CIFS_DEBUG2 is not set +# CONFIG_CIFS_EXPERIMENTAL is not set +# CONFIG_NCP_FS is not set +# CONFIG_CODA_FS is not set +# CONFIG_AFS_FS is not set + +# +# Partition Types +# +CONFIG_PARTITION_ADVANCED=y +# CONFIG_ACORN_PARTITION is not set +# CONFIG_OSF_PARTITION is not set +# CONFIG_AMIGA_PARTITION is not set +# CONFIG_ATARI_PARTITION is not set +CONFIG_MAC_PARTITION=y +CONFIG_MSDOS_PARTITION=y +# CONFIG_BSD_DISKLABEL is not set +# CONFIG_MINIX_SUBPARTITION is not set +# CONFIG_SOLARIS_X86_PARTITION is not set +# CONFIG_UNIXWARE_DISKLABEL is not set +# CONFIG_LDM_PARTITION is not set +# CONFIG_SGI_PARTITION is not set +# CONFIG_ULTRIX_PARTITION is not set +# CONFIG_SUN_PARTITION is not set +# CONFIG_KARMA_PARTITION is not set +# CONFIG_EFI_PARTITION is not set +# CONFIG_SYSV68_PARTITION is not set +CONFIG_NLS=y +CONFIG_NLS_DEFAULT="iso8859-1" +CONFIG_NLS_CODEPAGE_437=y +CONFIG_NLS_CODEPAGE_737=m +CONFIG_NLS_CODEPAGE_775=m +CONFIG_NLS_CODEPAGE_850=m +CONFIG_NLS_CODEPAGE_852=m +CONFIG_NLS_CODEPAGE_855=m +CONFIG_NLS_CODEPAGE_857=m +CONFIG_NLS_CODEPAGE_860=m +CONFIG_NLS_CODEPAGE_861=m +CONFIG_NLS_CODEPAGE_862=m +CONFIG_NLS_CODEPAGE_863=m +CONFIG_NLS_CODEPAGE_864=m +CONFIG_NLS_CODEPAGE_865=m +CONFIG_NLS_CODEPAGE_866=m +CONFIG_NLS_CODEPAGE_869=m +CONFIG_NLS_CODEPAGE_936=m +CONFIG_NLS_CODEPAGE_950=m +CONFIG_NLS_CODEPAGE_932=m +CONFIG_NLS_CODEPAGE_949=m +CONFIG_NLS_CODEPAGE_874=m +CONFIG_NLS_ISO8859_8=m +CONFIG_NLS_CODEPAGE_1250=m +CONFIG_NLS_CODEPAGE_1251=m +CONFIG_NLS_ASCII=m +CONFIG_NLS_ISO8859_1=y +CONFIG_NLS_ISO8859_2=m +CONFIG_NLS_ISO8859_3=m +CONFIG_NLS_ISO8859_4=m +CONFIG_NLS_ISO8859_5=m +CONFIG_NLS_ISO8859_6=m +CONFIG_NLS_ISO8859_7=m +CONFIG_NLS_ISO8859_9=m +CONFIG_NLS_ISO8859_13=m +CONFIG_NLS_ISO8859_14=m +CONFIG_NLS_ISO8859_15=m +CONFIG_NLS_KOI8_R=m +CONFIG_NLS_KOI8_U=m +CONFIG_NLS_UTF8=m +# CONFIG_DLM is not set +CONFIG_BINARY_PRINTF=y + +# +# Library routines +# +CONFIG_BITREVERSE=y +CONFIG_GENERIC_FIND_LAST_BIT=y +CONFIG_CRC_CCITT=m +CONFIG_CRC16=y +CONFIG_CRC_T10DIF=y +CONFIG_CRC_ITU_T=m +CONFIG_CRC32=y +# CONFIG_CRC7 is not set +CONFIG_LIBCRC32C=m +CONFIG_ZLIB_INFLATE=y +CONFIG_ZLIB_DEFLATE=m +CONFIG_LZO_COMPRESS=m +CONFIG_LZO_DECOMPRESS=m +CONFIG_DECOMPRESS_GZIP=y +CONFIG_DECOMPRESS_BZIP2=y +CONFIG_DECOMPRESS_LZMA=y +CONFIG_TEXTSEARCH=y +CONFIG_TEXTSEARCH_KMP=m +CONFIG_TEXTSEARCH_BM=m +CONFIG_TEXTSEARCH_FSM=m +CONFIG_HAS_IOMEM=y +CONFIG_HAS_IOPORT=y +CONFIG_HAS_DMA=y +CONFIG_HAVE_LMB=y +CONFIG_NLATTR=y + +# +# Kernel hacking +# +# CONFIG_PRINTK_TIME is not set +CONFIG_ENABLE_WARN_DEPRECATED=y +CONFIG_ENABLE_MUST_CHECK=y +CONFIG_FRAME_WARN=2048 +CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set +# CONFIG_UNUSED_SYMBOLS is not set +CONFIG_DEBUG_FS=y +# CONFIG_HEADERS_CHECK is not set +CONFIG_DEBUG_KERNEL=y +# CONFIG_DEBUG_SHIRQ is not set +CONFIG_DETECT_SOFTLOCKUP=y +# CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC is not set +CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC_VALUE=0 +CONFIG_DETECT_HUNG_TASK=y +# CONFIG_BOOTPARAM_HUNG_TASK_PANIC is not set +CONFIG_BOOTPARAM_HUNG_TASK_PANIC_VALUE=0 +CONFIG_SCHED_DEBUG=y +CONFIG_SCHEDSTATS=y +# CONFIG_TIMER_STATS is not set +# CONFIG_DEBUG_OBJECTS is not set +# CONFIG_SLUB_DEBUG_ON is not set +# CONFIG_SLUB_STATS is not set +# CONFIG_DEBUG_KMEMLEAK is not set +# CONFIG_DEBUG_RT_MUTEXES is not set +# CONFIG_RT_MUTEX_TESTER is not set +# CONFIG_DEBUG_SPINLOCK is not set +CONFIG_DEBUG_MUTEXES=y +# CONFIG_DEBUG_LOCK_ALLOC is not set +# CONFIG_PROVE_LOCKING is not set +# CONFIG_LOCK_STAT is not set +CONFIG_TRACE_IRQFLAGS=y +# CONFIG_DEBUG_SPINLOCK_SLEEP is not set +# CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set +CONFIG_STACKTRACE=y +# CONFIG_DEBUG_KOBJECT is not set +CONFIG_DEBUG_BUGVERBOSE=y +# CONFIG_DEBUG_INFO is not set +# CONFIG_DEBUG_VM is not set +# CONFIG_DEBUG_WRITECOUNT is not set +CONFIG_DEBUG_MEMORY_INIT=y +# CONFIG_DEBUG_LIST is not set +# CONFIG_DEBUG_SG is not set +# CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set +# CONFIG_RCU_TORTURE_TEST is not set +# CONFIG_RCU_CPU_STALL_DETECTOR is not set +# CONFIG_BACKTRACE_SELF_TEST is not set +# CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set +# CONFIG_FAULT_INJECTION is not set +CONFIG_LATENCYTOP=y +CONFIG_SYSCTL_SYSCALL_CHECK=y +# CONFIG_DEBUG_PAGEALLOC is not set +CONFIG_NOP_TRACER=y +CONFIG_HAVE_FUNCTION_TRACER=y +CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y +CONFIG_HAVE_DYNAMIC_FTRACE=y +CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y +CONFIG_TRACER_MAX_TRACE=y +CONFIG_RING_BUFFER=y +CONFIG_EVENT_TRACING=y +CONFIG_CONTEXT_SWITCH_TRACER=y +CONFIG_RING_BUFFER_ALLOW_SWAP=y +CONFIG_TRACING=y +CONFIG_GENERIC_TRACER=y +CONFIG_TRACING_SUPPORT=y +CONFIG_FTRACE=y +# CONFIG_FUNCTION_TRACER is not set +CONFIG_IRQSOFF_TRACER=y +CONFIG_SCHED_TRACER=y +# CONFIG_BOOT_TRACER is not set +CONFIG_BRANCH_PROFILE_NONE=y +# CONFIG_PROFILE_ANNOTATED_BRANCHES is not set +# CONFIG_PROFILE_ALL_BRANCHES is not set +# CONFIG_STACK_TRACER is not set +# CONFIG_KMEMTRACE is not set +# CONFIG_WORKQUEUE_TRACER is not set +CONFIG_BLK_DEV_IO_TRACE=y +# CONFIG_FTRACE_STARTUP_TEST is not set +# CONFIG_RING_BUFFER_BENCHMARK is not set +# CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DMA_API_DEBUG is not set +# CONFIG_SAMPLES is not set +CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_KGDB is not set +# CONFIG_PPC_DISABLE_WERROR is not set +CONFIG_PPC_WERROR=y +CONFIG_PRINT_STACK_DEPTH=64 +CONFIG_DEBUG_STACKOVERFLOW=y +CONFIG_DEBUG_STACK_USAGE=y +# CONFIG_PPC_EMULATED_STATS is not set +CONFIG_CODE_PATCHING_SELFTEST=y +CONFIG_FTR_FIXUP_SELFTEST=y +CONFIG_MSI_BITMAP_SELFTEST=y +CONFIG_XMON=y +# CONFIG_XMON_DEFAULT is not set +CONFIG_XMON_DISASSEMBLY=y +CONFIG_DEBUGGER=y +CONFIG_IRQSTACKS=y +# CONFIG_VIRQ_DEBUG is not set +# CONFIG_PPC_EARLY_DEBUG is not set + +# +# Security options +# +# CONFIG_KEYS is not set +# CONFIG_SECURITY is not set +# CONFIG_SECURITYFS is not set +# CONFIG_SECURITY_FILE_CAPABILITIES is not set +CONFIG_XOR_BLOCKS=y +CONFIG_ASYNC_CORE=y +CONFIG_ASYNC_MEMCPY=y +CONFIG_ASYNC_XOR=y +CONFIG_ASYNC_PQ=y +CONFIG_ASYNC_RAID6_RECOV=y +CONFIG_CRYPTO=y + +# +# Crypto core or helper +# +CONFIG_CRYPTO_ALGAPI=y +CONFIG_CRYPTO_ALGAPI2=y +CONFIG_CRYPTO_AEAD=m +CONFIG_CRYPTO_AEAD2=y +CONFIG_CRYPTO_BLKCIPHER=y +CONFIG_CRYPTO_BLKCIPHER2=y +CONFIG_CRYPTO_HASH=y +CONFIG_CRYPTO_HASH2=y +CONFIG_CRYPTO_RNG=m +CONFIG_CRYPTO_RNG2=y +CONFIG_CRYPTO_PCOMP=y +CONFIG_CRYPTO_MANAGER=y +CONFIG_CRYPTO_MANAGER2=y +CONFIG_CRYPTO_GF128MUL=m +CONFIG_CRYPTO_NULL=m +CONFIG_CRYPTO_WORKQUEUE=y +# CONFIG_CRYPTO_CRYPTD is not set +CONFIG_CRYPTO_AUTHENC=m +CONFIG_CRYPTO_TEST=m + +# +# Authenticated Encryption with Associated Data +# +CONFIG_CRYPTO_CCM=m +CONFIG_CRYPTO_GCM=m +CONFIG_CRYPTO_SEQIV=m + +# +# Block modes +# +CONFIG_CRYPTO_CBC=y +CONFIG_CRYPTO_CTR=m +# CONFIG_CRYPTO_CTS is not set +CONFIG_CRYPTO_ECB=m +# CONFIG_CRYPTO_LRW is not set +CONFIG_CRYPTO_PCBC=m +# CONFIG_CRYPTO_XTS is not set + +# +# Hash modes +# +CONFIG_CRYPTO_HMAC=y +# CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set + +# +# Digest +# +CONFIG_CRYPTO_CRC32C=m +CONFIG_CRYPTO_GHASH=m +CONFIG_CRYPTO_MD4=m +CONFIG_CRYPTO_MD5=y +CONFIG_CRYPTO_MICHAEL_MIC=m +# CONFIG_CRYPTO_RMD128 is not set +# CONFIG_CRYPTO_RMD160 is not set +# CONFIG_CRYPTO_RMD256 is not set +# CONFIG_CRYPTO_RMD320 is not set +CONFIG_CRYPTO_SHA1=m +CONFIG_CRYPTO_SHA256=m +CONFIG_CRYPTO_SHA512=m +CONFIG_CRYPTO_TGR192=m +CONFIG_CRYPTO_WP512=m + +# +# Ciphers +# +CONFIG_CRYPTO_AES=m +CONFIG_CRYPTO_ANUBIS=m +CONFIG_CRYPTO_ARC4=m +CONFIG_CRYPTO_BLOWFISH=m +# CONFIG_CRYPTO_CAMELLIA is not set +CONFIG_CRYPTO_CAST5=m +CONFIG_CRYPTO_CAST6=m +CONFIG_CRYPTO_DES=y +# CONFIG_CRYPTO_FCRYPT is not set +CONFIG_CRYPTO_KHAZAD=m +CONFIG_CRYPTO_SALSA20=m +# CONFIG_CRYPTO_SEED is not set +CONFIG_CRYPTO_SERPENT=m +CONFIG_CRYPTO_TEA=m +CONFIG_CRYPTO_TWOFISH=m +CONFIG_CRYPTO_TWOFISH_COMMON=m + +# +# Compression +# +CONFIG_CRYPTO_DEFLATE=m +# CONFIG_CRYPTO_ZLIB is not set +CONFIG_CRYPTO_LZO=m + +# +# Random Number Generation +# +# CONFIG_CRYPTO_ANSI_CPRNG is not set +# CONFIG_CRYPTO_HW is not set +# CONFIG_PPC_CLOCK is not set +# CONFIG_VIRTUALIZATION is not set diff --git a/arch/powerpc/configs/pq2fads_defconfig b/arch/powerpc/configs/pq2fads_defconfig index ff96bb43c32d..b7911216af78 100644 --- a/arch/powerpc/configs/pq2fads_defconfig +++ b/arch/powerpc/configs/pq2fads_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:00 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:17 2009 # # CONFIG_PPC64 is not set @@ -34,6 +34,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -82,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 @@ -120,29 +122,30 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -155,6 +158,7 @@ CONFIG_BASE_SMALL=0 # CONFIG_MODULES is not set CONFIG_BLOCK=y CONFIG_LBDAF=y +CONFIG_BLK_DEV_BSG=y # CONFIG_BLK_DEV_INTEGRITY is not set # @@ -239,6 +243,7 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_FLATMEM=y @@ -252,6 +257,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -401,6 +407,7 @@ CONFIG_NETFILTER_ADVANCED=y # CONFIG_BT is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -408,7 +415,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set @@ -420,6 +426,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -481,7 +488,6 @@ CONFIG_MTD_CFI_UTIL=y # CONFIG_MTD_COMPLEX_MAPPINGS is not set # CONFIG_MTD_PHYSMAP is not set CONFIG_MTD_PHYSMAP_OF=y -# CONFIG_MTD_SBC8240 is not set # CONFIG_MTD_INTEL_VR_NOR is not set # CONFIG_MTD_PLATRAM is not set @@ -664,7 +670,9 @@ CONFIG_MII=y # CONFIG_NET_PCI is not set # CONFIG_B44 is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_FS_ENET=y # CONFIG_FS_ENET_HAS_SCC is not set CONFIG_FS_ENET_HAS_FCC=y @@ -712,10 +720,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -764,6 +769,7 @@ CONFIG_KEYBOARD_ATKBD=y # CONFIG_KEYBOARD_GPIO is not set # CONFIG_KEYBOARD_MATRIX is not set # CONFIG_KEYBOARD_NEWTON is not set +# CONFIG_KEYBOARD_OPENCORES is not set # CONFIG_KEYBOARD_STOWAWAY is not set # CONFIG_KEYBOARD_SUNKBD is not set # CONFIG_KEYBOARD_XTKBD is not set @@ -774,6 +780,7 @@ CONFIG_MOUSE_PS2_LOGIPS2PP=y CONFIG_MOUSE_PS2_SYNAPTICS=y CONFIG_MOUSE_PS2_TRACKPOINT=y # CONFIG_MOUSE_PS2_ELANTECH is not set +# CONFIG_MOUSE_PS2_SENTELIC is not set # CONFIG_MOUSE_PS2_TOUCHKIT is not set # CONFIG_MOUSE_SERIAL is not set # CONFIG_MOUSE_APPLETOUCH is not set @@ -855,15 +862,19 @@ CONFIG_GPIOLIB=y # PCI GPIO expanders: # # CONFIG_GPIO_BT8XX is not set +# CONFIG_GPIO_LANGWELL is not set # # SPI GPIO expanders: # + +# +# AC97 GPIO expanders: +# # CONFIG_W1 is not set # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -886,6 +897,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -905,7 +917,6 @@ CONFIG_USB_ARCH_HAS_EHCI=y # CONFIG_USB is not set # CONFIG_USB_OTG_WHITELIST is not set # CONFIG_USB_OTG_BLACKLIST_HUB is not set -# CONFIG_USB_MUSB_HDRC is not set # CONFIG_USB_GADGET_MUSB_HDRC is not set # @@ -922,6 +933,7 @@ CONFIG_USB_GADGET_SELECTED=y # CONFIG_USB_GADGET_LH7A40X is not set # CONFIG_USB_GADGET_OMAP is not set # CONFIG_USB_GADGET_PXA25X is not set +# CONFIG_USB_GADGET_R8A66597 is not set # CONFIG_USB_GADGET_PXA27X is not set # CONFIG_USB_GADGET_S3C_HSOTG is not set # CONFIG_USB_GADGET_IMX is not set @@ -940,6 +952,7 @@ CONFIG_USB_GADGET_DUALSPEED=y # CONFIG_USB_AUDIO is not set CONFIG_USB_ETH=y CONFIG_USB_ETH_RNDIS=y +# CONFIG_USB_ETH_EEM is not set # CONFIG_USB_GADGETFS is not set # CONFIG_USB_FILE_STORAGE is not set # CONFIG_USB_G_SERIAL is not set @@ -1148,6 +1161,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1183,10 +1197,12 @@ CONFIG_DEBUG_INFO=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set # CONFIG_DEBUG_NOTIFIERS is not set +# CONFIG_DEBUG_CREDENTIALS is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_BACKTRACE_SELF_TEST is not set # CONFIG_DEBUG_BLOCK_EXT_DEVT is not set +# CONFIG_DEBUG_FORCE_WEAK_PER_CPU is not set # CONFIG_FAULT_INJECTION is not set # CONFIG_LATENCYTOP is not set CONFIG_SYSCTL_SYSCALL_CHECK=y @@ -1209,6 +1225,7 @@ CONFIG_BRANCH_PROFILE_NONE=y # CONFIG_KMEMTRACE is not set # CONFIG_WORKQUEUE_TRACER is not set # CONFIG_BLK_DEV_IO_TRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1237,7 +1254,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD2=y @@ -1279,6 +1295,7 @@ CONFIG_CRYPTO_PCBC=y # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set CONFIG_CRYPTO_MD5=y # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/prpmc2800_defconfig b/arch/powerpc/configs/prpmc2800_defconfig index 1293c465d7fa..ef50ce45d50b 100644 --- a/arch/powerpc/configs/prpmc2800_defconfig +++ b/arch/powerpc/configs/prpmc2800_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:01 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:18 2009 # # CONFIG_PPC64 is not set @@ -36,6 +36,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -85,11 +86,12 @@ CONFIG_POSIX_MQUEUE_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -131,28 +133,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -244,12 +247,12 @@ CONFIG_BINFMT_ELF=y CONFIG_BINFMT_MISC=y # CONFIG_IOMMU_HELPER is not set # CONFIG_SWIOTLB is not set -CONFIG_PPC_NEED_DMA_SYNC_OPS=y CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -267,6 +270,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -360,6 +364,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -389,6 +394,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -396,7 +402,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -409,6 +414,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y CONFIG_FW_LOADER=y @@ -633,6 +639,7 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -672,11 +679,14 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set CONFIG_ATA=y # CONFIG_ATA_NONSTANDARD is not set +CONFIG_ATA_VERBOSE_ERROR=y CONFIG_SATA_PMP=y # CONFIG_SATA_AHCI is not set # CONFIG_SATA_SIL24 is not set @@ -698,6 +708,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_ALI is not set # CONFIG_PATA_AMD is not set # CONFIG_PATA_ARTOP is not set +# CONFIG_PATA_ATP867X is not set # CONFIG_PATA_ATIIXP is not set # CONFIG_PATA_CMD640_PCI is not set # CONFIG_PATA_CMD64X is not set @@ -725,6 +736,7 @@ CONFIG_SATA_MV=y # CONFIG_PATA_OPTIDMA is not set # CONFIG_PATA_PDC_OLD is not set # CONFIG_PATA_RADISYS is not set +# CONFIG_PATA_RDC is not set # CONFIG_PATA_RZ1000 is not set # CONFIG_PATA_SC1200 is not set # CONFIG_PATA_SERVERWORKS is not set @@ -823,9 +835,11 @@ CONFIG_8139TOO=y # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_KS8842 is not set +# CONFIG_KS8851_MLL is not set # CONFIG_VIA_RHINE is not set # CONFIG_SC92031 is not set # CONFIG_ATL2 is not set +# CONFIG_XILINX_EMACLITE is not set CONFIG_NETDEV_1000=y # CONFIG_ACENIC is not set # CONFIG_DL2K is not set @@ -871,10 +885,7 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_SFC is not set # CONFIG_BE2NET is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -977,6 +988,7 @@ CONFIG_LEGACY_PTY_COUNT=256 CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -1031,9 +1043,6 @@ CONFIG_I2C_MV64XXX=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -1051,6 +1060,11 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set CONFIG_HWMON=y # CONFIG_HWMON_VID is not set +# CONFIG_HWMON_DEBUG_CHIP is not set + +# +# Native drivers +# # CONFIG_SENSORS_AD7414 is not set # CONFIG_SENSORS_AD7418 is not set # CONFIG_SENSORS_ADM1021 is not set @@ -1100,6 +1114,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_ADS7828 is not set # CONFIG_SENSORS_THMC50 is not set # CONFIG_SENSORS_TMP401 is not set +# CONFIG_SENSORS_TMP421 is not set # CONFIG_SENSORS_VIA686A is not set # CONFIG_SENSORS_VT1211 is not set # CONFIG_SENSORS_VT8231 is not set @@ -1111,9 +1126,7 @@ CONFIG_HWMON=y # CONFIG_SENSORS_W83L786NG is not set # CONFIG_SENSORS_W83627HF is not set # CONFIG_SENSORS_W83627EHF is not set -# CONFIG_HWMON_DEBUG_CHIP is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -1132,6 +1145,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -1142,6 +1156,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set CONFIG_VIDEO_OUTPUT_CONTROL=y @@ -1162,7 +1177,6 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_SOUND is not set CONFIG_HID_SUPPORT=y CONFIG_HID=y -# CONFIG_HID_DEBUG is not set # CONFIG_HIDRAW is not set # @@ -1186,6 +1200,7 @@ CONFIG_HID_DRAGONRISE=y CONFIG_HID_EZKEY=y CONFIG_HID_KYE=y CONFIG_HID_GYRATION=y +CONFIG_HID_TWINHAN=y CONFIG_HID_KENSINGTON=y CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set @@ -1239,6 +1254,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y # CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1404,6 +1420,7 @@ CONFIG_FS_MBCACHE=y # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1463,7 +1480,6 @@ CONFIG_MISC_FILESYSTEMS=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y # CONFIG_NFS_V3 is not set @@ -1576,6 +1592,7 @@ CONFIG_ENABLE_WARN_DEPRECATED=y CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1593,6 +1610,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1614,7 +1632,6 @@ CONFIG_CRYPTO=y # # Crypto core or helper # -# CONFIG_CRYPTO_FIPS is not set # CONFIG_CRYPTO_MANAGER is not set # CONFIG_CRYPTO_MANAGER2 is not set # CONFIG_CRYPTO_GF128MUL is not set @@ -1645,11 +1662,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_HMAC is not set # CONFIG_CRYPTO_XCBC is not set +# CONFIG_CRYPTO_VMAC is not set # # Digest # # CONFIG_CRYPTO_CRC32C is not set +# CONFIG_CRYPTO_GHASH is not set # CONFIG_CRYPTO_MD4 is not set # CONFIG_CRYPTO_MD5 is not set # CONFIG_CRYPTO_MICHAEL_MIC is not set diff --git a/arch/powerpc/configs/storcenter_defconfig b/arch/powerpc/configs/storcenter_defconfig index 28384dc01003..524263158fc0 100644 --- a/arch/powerpc/configs/storcenter_defconfig +++ b/arch/powerpc/configs/storcenter_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.31-rc4 -# Wed Jul 29 23:32:01 2009 +# Linux kernel version: 2.6.32-rc5 +# Thu Nov 5 08:20:19 2009 # # CONFIG_PPC64 is not set @@ -34,6 +34,7 @@ CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_HARDIRQS=y CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set +# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set CONFIG_IRQ_PER_CPU=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -82,11 +83,12 @@ CONFIG_SYSVIPC_SYSCTL=y # # RCU Subsystem # -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set +CONFIG_TREE_RCU=y +# CONFIG_TREE_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set +CONFIG_RCU_FANOUT=32 +# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 CONFIG_GROUP_SCHED=y @@ -118,28 +120,29 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y -CONFIG_HAVE_PERF_COUNTERS=y +CONFIG_HAVE_PERF_EVENTS=y # -# Performance Counters +# Kernel Performance Events And Counters # +# CONFIG_PERF_EVENTS is not set # CONFIG_PERF_COUNTERS is not set CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_COMPAT_BRK=y # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set -# CONFIG_MARKERS is not set CONFIG_HAVE_OPROFILE=y CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y +CONFIG_HAVE_DMA_ATTRS=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -243,6 +246,7 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set +CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -260,6 +264,7 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_HAVE_MLOCK=y CONFIG_HAVE_MLOCKED_PAGE_BIT=y +# CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 CONFIG_PPC_4K_PAGES=y # CONFIG_PPC_16K_PAGES is not set @@ -349,6 +354,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_NETFILTER is not set # CONFIG_IP_DCCP is not set # CONFIG_IP_SCTP is not set +# CONFIG_RDS is not set # CONFIG_TIPC is not set # CONFIG_ATM is not set # CONFIG_BRIDGE is not set @@ -378,6 +384,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_AF_RXRPC is not set CONFIG_WIRELESS=y # CONFIG_CFG80211 is not set +CONFIG_CFG80211_DEFAULT_PS_VALUE=0 CONFIG_WIRELESS_OLD_REGULATORY=y # CONFIG_WIRELESS_EXT is not set # CONFIG_LIB80211 is not set @@ -385,7 +392,6 @@ CONFIG_WIRELESS_OLD_REGULATORY=y # # CFG80211 needs to be enabled for MAC80211 # -CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -398,6 +404,7 @@ CONFIG_MAC80211_DEFAULT_PS_VALUE=0 # Generic Driver Options # CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug" +# CONFIG_DEVTMPFS is not set CONFIG_STANDALONE=y CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_FW_LOADER is not set @@ -405,9 +412,9 @@ CONFIG_PREVENT_FIRMWARE_BUILD=y # CONFIG_CONNECTOR is not set CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set +# CONFIG_MTD_TESTS is not set # CONFIG_MTD_CONCAT is not set CONFIG_MTD_PARTITIONS=y -# CONFIG_MTD_TESTS is not set # CONFIG_MTD_REDBOOT_PARTS is not set CONFIG_MTD_CMDLINE_PARTS=y CONFIG_MTD_OF_PARTS=y @@ -619,6 +626,7 @@ CONFIG_SCSI_SPI_ATTRS=y CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set # CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_BE2ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -657,7 +665,9 @@ CONFIG_SCSI_LOWLEVEL=y # CONFIG_SCSI_DC390T is not set # CONFIG_SCSI_NSP32 is not set # CONFIG_SCSI_DEBUG is not set +# CONFIG_SCSI_PMCRAID is not set # CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set # CONFIG_SCSI_DH is not set # CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set @@ -670,6 +680,7 @@ CONFIG_MD_RAID1=y # CONFIG_MD_RAID10 is not set CONFIG_MD_RAID456=y CONFIG_MD_RAID6_PQ=y +# CONFIG_ASYNC_RAID6_TEST is not set # CONFIG_MD_MULTIPATH is not set # CONFIG_MD_FAULTY is not set # CONFIG_BLK_DEV_DM is not set @@ -729,10 +740,7 @@ CONFIG_R8169=y # CONFIG_JME is not set # CONFIG_NETDEV_10000 is not set # CONFIG_TR is not set - -# -# Wireless LAN -# +CONFIG_WLAN=y # CONFIG_WLAN_PRE80211 is not set # CONFIG_WLAN_80211 is not set @@ -813,6 +821,7 @@ CONFIG_NVRAM=y CONFIG_DEVPORT=y CONFIG_I2C=y CONFIG_I2C_BOARDINFO=y +CONFIG_I2C_COMPAT=y CONFIG_I2C_CHARDEV=y CONFIG_I2C_HELPER_AUTO=y @@ -867,9 +876,6 @@ CONFIG_I2C_MPC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set -# CONFIG_SENSORS_PCF8574 is not set -# CONFIG_PCF8575 is not set -# CONFIG_SENSORS_PCA9539 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set # CONFIG_I2C_DEBUG_ALGO is not set @@ -887,7 +893,6 @@ CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_POWER_SUPPLY is not set # CONFIG_HWMON is not set # CONFIG_THERMAL is not set -# CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set CONFIG_SSB_POSSIBLE=y @@ -906,6 +911,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set +# CONFIG_MFD_WM831X is not set # CONFIG_MFD_WM8350_I2C is not set # CONFIG_MFD_PCF50633 is not set # CONFIG_AB3100_CORE is not set @@ -916,6 +922,7 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_AGP is not set +CONFIG_VGA_ARB=y # CONFIG_DRM is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set @@ -961,6 +968,7 @@ CONFIG_USB_EHCI_HCD_PPC_OF=y # CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set +# CONFIG_USB_ISP1362_HCD is not set CONFIG_USB_OHCI_HCD=y # CONFIG_USB_OHCI_HCD_PPC_OF_BE is not set # CONFIG_USB_OHCI_HCD_PPC_OF_LE is not set @@ -1141,6 +1149,7 @@ CONFIG_XFS_FS=m # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set +# CONFIG_NILFS2_FS is not set CONFIG_FILE_LOCKING=y CONFIG_FSNOTIFY=y CONFIG_DNOTIFY=y @@ -1210,7 +1219,6 @@ CONFIG_JFFS2_RTIME=y # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set # CONFIG_NETWORK_FILESYSTEMS is not set CONFIG_EXPORTFS=m @@ -1307,6 +1315,7 @@ CONFIG_GENERIC_ATOMIC64=y # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 # CONFIG_MAGIC_SYSRQ is not set +# CONFIG_STRIP_ASM_SYMS is not set # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set @@ -1324,6 +1333,7 @@ CONFIG_HAVE_DYNAMIC_FTRACE=y CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_PPC_DISABLE_WERROR is not set @@ -1344,6 +1354,8 @@ CONFIG_XOR_BLOCKS=y CONFIG_ASYNC_CORE=y CONFIG_ASYNC_MEMCPY=y CONFIG_ASYNC_XOR=y +CONFIG_ASYNC_PQ=y +CONFIG_ASYNC_RAID6_RECOV=y # CONFIG_CRYPTO is not set # CONFIG_PPC_CLOCK is not set # CONFIG_VIRTUALIZATION is not set diff --git a/arch/powerpc/include/asm/firmware.h b/arch/powerpc/include/asm/firmware.h index 3a179827528d..20778a405d7a 100644 --- a/arch/powerpc/include/asm/firmware.h +++ b/arch/powerpc/include/asm/firmware.h @@ -37,7 +37,7 @@ #define FW_FEATURE_VIO ASM_CONST(0x0000000000004000) #define FW_FEATURE_RDMA ASM_CONST(0x0000000000008000) #define FW_FEATURE_LLAN ASM_CONST(0x0000000000010000) -#define FW_FEATURE_BULK ASM_CONST(0x0000000000020000) +#define FW_FEATURE_BULK_REMOVE ASM_CONST(0x0000000000020000) #define FW_FEATURE_XDABR ASM_CONST(0x0000000000040000) #define FW_FEATURE_MULTITCE ASM_CONST(0x0000000000080000) #define FW_FEATURE_SPLPAR ASM_CONST(0x0000000000100000) @@ -45,8 +45,7 @@ #define FW_FEATURE_LPAR ASM_CONST(0x0000000000400000) #define FW_FEATURE_PS3_LV1 ASM_CONST(0x0000000000800000) #define FW_FEATURE_BEAT ASM_CONST(0x0000000001000000) -#define FW_FEATURE_BULK_REMOVE ASM_CONST(0x0000000002000000) -#define FW_FEATURE_CMO ASM_CONST(0x0000000004000000) +#define FW_FEATURE_CMO ASM_CONST(0x0000000002000000) #ifndef __ASSEMBLY__ @@ -58,8 +57,9 @@ enum { FW_FEATURE_PERF | FW_FEATURE_DUMP | FW_FEATURE_INTERRUPT | FW_FEATURE_MIGRATE | FW_FEATURE_PERFMON | FW_FEATURE_CRQ | FW_FEATURE_VIO | FW_FEATURE_RDMA | FW_FEATURE_LLAN | - FW_FEATURE_BULK | FW_FEATURE_XDABR | FW_FEATURE_MULTITCE | - FW_FEATURE_SPLPAR | FW_FEATURE_LPAR | FW_FEATURE_CMO, + FW_FEATURE_BULK_REMOVE | FW_FEATURE_XDABR | + FW_FEATURE_MULTITCE | FW_FEATURE_SPLPAR | FW_FEATURE_LPAR | + FW_FEATURE_CMO, FW_FEATURE_PSERIES_ALWAYS = 0, FW_FEATURE_ISERIES_POSSIBLE = FW_FEATURE_ISERIES | FW_FEATURE_LPAR, FW_FEATURE_ISERIES_ALWAYS = FW_FEATURE_ISERIES | FW_FEATURE_LPAR, diff --git a/arch/powerpc/kernel/cputable.c b/arch/powerpc/kernel/cputable.c index 0b9c9135922e..03c862b6a9c4 100644 --- a/arch/powerpc/kernel/cputable.c +++ b/arch/powerpc/kernel/cputable.c @@ -711,6 +711,8 @@ static struct cpu_spec __initdata cpu_specs[] = { .cpu_setup = __setup_cpu_750, .machine_check = machine_check_generic, .platform = "ppc750", + .oprofile_cpu_type = "ppc/750", + .oprofile_type = PPC_OPROFILE_G4, }, { /* 745/755 */ .pvr_mask = 0xfffff000, diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S index 900e0eea0099..9763267e38b4 100644 --- a/arch/powerpc/kernel/entry_64.S +++ b/arch/powerpc/kernel/entry_64.S @@ -658,42 +658,43 @@ do_work: cmpdi r0,0 crandc eq,cr1*4+eq,eq bne restore - /* here we are preempting the current task */ -1: -#ifdef CONFIG_TRACE_IRQFLAGS - bl .trace_hardirqs_on - /* Note: we just clobbered r10 which used to contain the previous - * MSR before the hard-disabling done by the caller of do_work. - * We don't have that value anymore, but it doesn't matter as - * we will hard-enable unconditionally, we can just reload the - * current MSR into r10 + + /* Here we are preempting the current task. + * + * Ensure interrupts are soft-disabled. We also properly mark + * the PACA to reflect the fact that they are hard-disabled + * and trace the change */ - mfmsr r10 -#endif /* CONFIG_TRACE_IRQFLAGS */ - li r0,1 + li r0,0 stb r0,PACASOFTIRQEN(r13) stb r0,PACAHARDIRQEN(r13) + TRACE_DISABLE_INTS + + /* Call the scheduler with soft IRQs off */ +1: bl .preempt_schedule_irq + + /* Hard-disable interrupts again (and update PACA) */ #ifdef CONFIG_PPC_BOOK3E - wrteei 1 - bl .preempt_schedule wrteei 0 #else - ori r10,r10,MSR_EE - mtmsrd r10,1 /* reenable interrupts */ - bl .preempt_schedule mfmsr r10 - clrrdi r9,r1,THREAD_SHIFT - rldicl r10,r10,48,1 /* disable interrupts again */ + rldicl r10,r10,48,1 rotldi r10,r10,16 mtmsrd r10,1 #endif /* CONFIG_PPC_BOOK3E */ + li r0,0 + stb r0,PACAHARDIRQEN(r13) + + /* Re-test flags and eventually loop */ + clrrdi r9,r1,THREAD_SHIFT ld r4,TI_FLAGS(r9) andi. r0,r4,_TIF_NEED_RESCHED bne 1b b restore user_work: -#endif +#endif /* CONFIG_PREEMPT */ + /* Enable interrupts */ #ifdef CONFIG_PPC_BOOK3E wrteei 1 @@ -1038,8 +1039,7 @@ _GLOBAL(mod_return_to_handler) * We are in a module using the module's TOC. * Switch to our TOC to run inside the core kernel. */ - LOAD_REG_IMMEDIATE(r4,ftrace_return_to_handler) - ld r2, 8(r4) + ld r2, PACATOC(r13) bl .ftrace_return_to_handler nop diff --git a/arch/powerpc/kernel/kgdb.c b/arch/powerpc/kernel/kgdb.c index fe8f71dd0b3f..641c74bb8e27 100644 --- a/arch/powerpc/kernel/kgdb.c +++ b/arch/powerpc/kernel/kgdb.c @@ -282,12 +282,6 @@ void gdb_regs_to_pt_regs(unsigned long *gdb_regs, struct pt_regs *regs) { unsigned long *ptr = gdb_regs; int reg; -#ifdef CONFIG_SPE - union { - u32 v32[2]; - u64 v64; - } acc; -#endif for (reg = 0; reg < 32; reg++) UNPACK64(regs->gpr[reg], ptr); diff --git a/arch/powerpc/kernel/pci-common.c b/arch/powerpc/kernel/pci-common.c index bb8209e34931..e8dfdbd9327a 100644 --- a/arch/powerpc/kernel/pci-common.c +++ b/arch/powerpc/kernel/pci-common.c @@ -1190,7 +1190,7 @@ EXPORT_SYMBOL(pcibios_align_resource); * Reparent resource children of pr that conflict with res * under res, and make res replace those children. */ -static int __init reparent_resources(struct resource *parent, +static int reparent_resources(struct resource *parent, struct resource *res) { struct resource *p, **pp; diff --git a/arch/powerpc/kernel/pci_64.c b/arch/powerpc/kernel/pci_64.c index ba949a2c93ac..ccf56ac92de5 100644 --- a/arch/powerpc/kernel/pci_64.c +++ b/arch/powerpc/kernel/pci_64.c @@ -97,7 +97,9 @@ int pcibios_unmap_io_space(struct pci_bus *bus) * to do an appropriate TLB flush here too */ if (bus->self) { +#ifdef CONFIG_PPC_STD_MMU_64 struct resource *res = bus->resource[0]; +#endif pr_debug("IO unmapping for PCI-PCI bridge %s\n", pci_name(bus->self)); diff --git a/arch/powerpc/kernel/perf_event.c b/arch/powerpc/kernel/perf_event.c index bbcbae183e92..87f1663584b0 100644 --- a/arch/powerpc/kernel/perf_event.c +++ b/arch/powerpc/kernel/perf_event.c @@ -116,20 +116,23 @@ static inline void perf_get_data_addr(struct pt_regs *regs, u64 *addrp) static inline u32 perf_get_misc_flags(struct pt_regs *regs) { unsigned long mmcra = regs->dsisr; + unsigned long sihv = MMCRA_SIHV; + unsigned long sipr = MMCRA_SIPR; if (TRAP(regs) != 0xf00) return 0; /* not a PMU interrupt */ if (ppmu->flags & PPMU_ALT_SIPR) { - if (mmcra & POWER6_MMCRA_SIHV) - return PERF_RECORD_MISC_HYPERVISOR; - return (mmcra & POWER6_MMCRA_SIPR) ? - PERF_RECORD_MISC_USER : PERF_RECORD_MISC_KERNEL; + sihv = POWER6_MMCRA_SIHV; + sipr = POWER6_MMCRA_SIPR; } - if (mmcra & MMCRA_SIHV) + + /* PR has priority over HV, so order below is important */ + if (mmcra & sipr) + return PERF_RECORD_MISC_USER; + if ((mmcra & sihv) && (freeze_events_kernel != MMCR0_FCHV)) return PERF_RECORD_MISC_HYPERVISOR; - return (mmcra & MMCRA_SIPR) ? PERF_RECORD_MISC_USER : - PERF_RECORD_MISC_KERNEL; + return PERF_RECORD_MISC_KERNEL; } /* diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c index 1168c5f440ab..c930ac38e59f 100644 --- a/arch/powerpc/kernel/process.c +++ b/arch/powerpc/kernel/process.c @@ -1016,9 +1016,13 @@ void show_stack(struct task_struct *tsk, unsigned long *stack) #ifdef CONFIG_FUNCTION_GRAPH_TRACER int curr_frame = current->curr_ret_stack; extern void return_to_handler(void); - unsigned long addr = (unsigned long)return_to_handler; + unsigned long rth = (unsigned long)return_to_handler; + unsigned long mrth = -1; #ifdef CONFIG_PPC64 - addr = *(unsigned long*)addr; + extern void mod_return_to_handler(void); + rth = *(unsigned long *)rth; + mrth = (unsigned long)mod_return_to_handler; + mrth = *(unsigned long *)mrth; #endif #endif @@ -1044,7 +1048,7 @@ void show_stack(struct task_struct *tsk, unsigned long *stack) if (!firstframe || ip != lr) { printk("["REG"] ["REG"] %pS", sp, ip, (void *)ip); #ifdef CONFIG_FUNCTION_GRAPH_TRACER - if (ip == addr && curr_frame >= 0) { + if ((ip == rth || ip == mrth) && curr_frame >= 0) { printk(" (%pS)", (void *)current->ret_stack[curr_frame].ret); curr_frame--; @@ -1168,7 +1172,7 @@ unsigned long arch_randomize_brk(struct mm_struct *mm) unsigned long base = mm->brk; unsigned long ret; -#ifdef CONFIG_PPC64 +#ifdef CONFIG_PPC_STD_MMU_64 /* * If we are using 1TB segments and we are allowed to randomise * the heap, we can put it above 1TB so it is backed by a 1TB diff --git a/arch/powerpc/kernel/setup_64.c b/arch/powerpc/kernel/setup_64.c index 797ea95aae2e..04f638d82fb3 100644 --- a/arch/powerpc/kernel/setup_64.c +++ b/arch/powerpc/kernel/setup_64.c @@ -57,7 +57,6 @@ #include <asm/cache.h> #include <asm/page.h> #include <asm/mmu.h> -#include <asm/mmu-hash64.h> #include <asm/firmware.h> #include <asm/xmon.h> #include <asm/udbg.h> diff --git a/arch/powerpc/kernel/time.c b/arch/powerpc/kernel/time.c index 92dc844299b6..a136a11c490d 100644 --- a/arch/powerpc/kernel/time.c +++ b/arch/powerpc/kernel/time.c @@ -777,7 +777,7 @@ int update_persistent_clock(struct timespec now) return ppc_md.set_rtc_time(&tm); } -void read_persistent_clock(struct timespec *ts) +static void __read_persistent_clock(struct timespec *ts) { struct rtc_time tm; static int first = 1; @@ -800,10 +800,23 @@ void read_persistent_clock(struct timespec *ts) return; } ppc_md.get_rtc_time(&tm); + ts->tv_sec = mktime(tm.tm_year+1900, tm.tm_mon+1, tm.tm_mday, tm.tm_hour, tm.tm_min, tm.tm_sec); } +void read_persistent_clock(struct timespec *ts) +{ + __read_persistent_clock(ts); + + /* Sanitize it in case real time clock is set below EPOCH */ + if (ts->tv_sec < 0) { + ts->tv_sec = 0; + ts->tv_nsec = 0; + } + +} + /* clocksource code */ static cycle_t rtc_read(struct clocksource *cs) { diff --git a/arch/powerpc/kernel/vdso.c b/arch/powerpc/kernel/vdso.c index 94e2df3cae07..137dc22afa42 100644 --- a/arch/powerpc/kernel/vdso.c +++ b/arch/powerpc/kernel/vdso.c @@ -50,6 +50,9 @@ /* Max supported size for symbol names */ #define MAX_SYMNAME 64 +/* The alignment of the vDSO */ +#define VDSO_ALIGNMENT (1 << 16) + extern char vdso32_start, vdso32_end; static void *vdso32_kbase = &vdso32_start; static unsigned int vdso32_pages; @@ -231,15 +234,21 @@ int arch_setup_additional_pages(struct linux_binprm *bprm, int uses_interp) * pick a base address for the vDSO in process space. We try to put it * at vdso_base which is the "natural" base for it, but we might fail * and end up putting it elsewhere. + * Add enough to the size so that the result can be aligned. */ down_write(&mm->mmap_sem); vdso_base = get_unmapped_area(NULL, vdso_base, - vdso_pages << PAGE_SHIFT, 0, 0); + (vdso_pages << PAGE_SHIFT) + + ((VDSO_ALIGNMENT - 1) & PAGE_MASK), + 0, 0); if (IS_ERR_VALUE(vdso_base)) { rc = vdso_base; goto fail_mmapsem; } + /* Add required alignment. */ + vdso_base = ALIGN(vdso_base, VDSO_ALIGNMENT); + /* * Put vDSO base into mm struct. We need to do this before calling * install_special_mapping or the perf counter mmap tracking code diff --git a/arch/powerpc/kernel/vdso32/vdso32.lds.S b/arch/powerpc/kernel/vdso32/vdso32.lds.S index 904ef1360dd7..0546bcd49cd0 100644 --- a/arch/powerpc/kernel/vdso32/vdso32.lds.S +++ b/arch/powerpc/kernel/vdso32/vdso32.lds.S @@ -25,7 +25,7 @@ SECTIONS . = ALIGN(16); .text : { *(.text .stub .text.* .gnu.linkonce.t.* __ftr_alt_*) - } + } :text PROVIDE(__etext = .); PROVIDE(_etext = .); PROVIDE(etext = .); @@ -56,7 +56,7 @@ SECTIONS .fixup : { *(.fixup) } .dynamic : { *(.dynamic) } :text :dynamic - .got : { *(.got) } + .got : { *(.got) } :text .plt : { *(.plt) } _end = .; diff --git a/arch/powerpc/kernel/vmlinux.lds.S b/arch/powerpc/kernel/vmlinux.lds.S index f56429362a12..27735a7ac12b 100644 --- a/arch/powerpc/kernel/vmlinux.lds.S +++ b/arch/powerpc/kernel/vmlinux.lds.S @@ -236,6 +236,7 @@ SECTIONS READ_MOSTLY_DATA(L1_CACHE_BYTES) } + . = ALIGN(PAGE_SIZE); .data_nosave : AT(ADDR(.data_nosave) - LOAD_OFFSET) { NOSAVE_DATA } diff --git a/arch/powerpc/kvm/timing.h b/arch/powerpc/kvm/timing.h index bb13b1f3cd5a..806ef67868bd 100644 --- a/arch/powerpc/kvm/timing.h +++ b/arch/powerpc/kvm/timing.h @@ -48,7 +48,11 @@ static inline void kvmppc_set_exit_type(struct kvm_vcpu *vcpu, int type) {} static inline void kvmppc_account_exit_stat(struct kvm_vcpu *vcpu, int type) { /* type has to be known at build time for optimization */ + + /* The BUILD_BUG_ON below breaks in funny ways, commented out + * for now ... -BenH BUILD_BUG_ON(__builtin_constant_p(type)); + */ switch (type) { case EXT_INTR_EXITS: vcpu->stat.ext_intr_exits++; diff --git a/arch/powerpc/mm/mmu_context_nohash.c b/arch/powerpc/mm/mmu_context_nohash.c index c2f93dc470e6..be4f34c30a0b 100644 --- a/arch/powerpc/mm/mmu_context_nohash.c +++ b/arch/powerpc/mm/mmu_context_nohash.c @@ -25,8 +25,8 @@ * also clear mm->cpu_vm_mask bits when processes are migrated */ -#define DEBUG_MAP_CONSISTENCY -#define DEBUG_CLAMP_LAST_CONTEXT 31 +//#define DEBUG_MAP_CONSISTENCY +//#define DEBUG_CLAMP_LAST_CONTEXT 31 //#define DEBUG_HARDER /* We don't use DEBUG because it tends to be compiled in always nowadays diff --git a/arch/powerpc/mm/slb_low.S b/arch/powerpc/mm/slb_low.S index bc44dc4b5c67..95ce35581696 100644 --- a/arch/powerpc/mm/slb_low.S +++ b/arch/powerpc/mm/slb_low.S @@ -72,19 +72,17 @@ _GLOBAL(slb_miss_kernel_load_vmemmap) 1: #endif /* CONFIG_SPARSEMEM_VMEMMAP */ - /* vmalloc/ioremap mapping encoding bits, the "li" instructions below - * will be patched by the kernel at boot + /* vmalloc mapping gets the encoding from the PACA as the mapping + * can be demoted from 64K -> 4K dynamically on some machines */ -BEGIN_FTR_SECTION - /* check whether this is in vmalloc or ioremap space */ clrldi r11,r10,48 cmpldi r11,(VMALLOC_SIZE >> 28) - 1 bgt 5f lhz r11,PACAVMALLOCSLLP(r13) b 6f 5: -END_FTR_SECTION_IFCLR(CPU_FTR_CI_LARGE_PAGE) -_GLOBAL(slb_miss_kernel_load_io) + /* IO mapping */ + _GLOBAL(slb_miss_kernel_load_io) li r11,0 6: BEGIN_FTR_SECTION diff --git a/arch/powerpc/platforms/52xx/mpc5200_simple.c b/arch/powerpc/platforms/52xx/mpc5200_simple.c index c31e5b534f0a..d45be5b5ad49 100644 --- a/arch/powerpc/platforms/52xx/mpc5200_simple.c +++ b/arch/powerpc/platforms/52xx/mpc5200_simple.c @@ -51,6 +51,8 @@ static void __init mpc5200_simple_setup_arch(void) /* list of the supported boards */ static char *board[] __initdata = { "intercontrol,digsy-mtc", + "manroland,mucmc52", + "manroland,uc101", "phytec,pcm030", "phytec,pcm032", "promess,motionpro", diff --git a/arch/powerpc/platforms/82xx/ep8248e.c b/arch/powerpc/platforms/82xx/ep8248e.c index 51fcae41f08a..f9aee182e6f7 100644 --- a/arch/powerpc/platforms/82xx/ep8248e.c +++ b/arch/powerpc/platforms/82xx/ep8248e.c @@ -132,12 +132,25 @@ static int __devinit ep8248e_mdio_probe(struct of_device *ofdev, return -ENOMEM; bus->irq = kmalloc(sizeof(int) * PHY_MAX_ADDR, GFP_KERNEL); + if (bus->irq == NULL) { + ret = -ENOMEM; + goto err_free_bus; + } bus->name = "ep8248e-mdio-bitbang"; bus->parent = &ofdev->dev; snprintf(bus->id, MII_BUS_ID_SIZE, "%x", res.start); - return of_mdiobus_register(bus, ofdev->node); + ret = of_mdiobus_register(bus, ofdev->node); + if (ret) + goto err_free_irq; + + return 0; +err_free_irq: + kfree(bus->irq); +err_free_bus: + free_mdio_bitbang(bus); + return ret; } static int ep8248e_mdio_remove(struct of_device *ofdev) diff --git a/arch/powerpc/platforms/cell/axon_msi.c b/arch/powerpc/platforms/cell/axon_msi.c index aca5741ddc67..a86c34b3bb84 100644 --- a/arch/powerpc/platforms/cell/axon_msi.c +++ b/arch/powerpc/platforms/cell/axon_msi.c @@ -365,7 +365,7 @@ static int axon_msi_probe(struct of_device *device, printk(KERN_ERR "axon_msi: couldn't parse dcr properties on %s\n", dn->full_name); - goto out; + goto out_free_msic; } msic->dcr_host = dcr_map(dn, dcr_base, dcr_len); diff --git a/arch/powerpc/platforms/iseries/Makefile b/arch/powerpc/platforms/iseries/Makefile index cc7161ff1666..ce014928d460 100644 --- a/arch/powerpc/platforms/iseries/Makefile +++ b/arch/powerpc/platforms/iseries/Makefile @@ -1,18 +1,9 @@ EXTRA_CFLAGS += -mno-minimal-toc -extra-y += dt.o - obj-y += exception.o -obj-y += hvlog.o hvlpconfig.o lpardata.o setup.o dt_mod.o mf.o lpevents.o \ +obj-y += hvlog.o hvlpconfig.o lpardata.o setup.o dt.o mf.o lpevents.o \ hvcall.o proc.o htab.o iommu.o misc.o irq.o obj-$(CONFIG_PCI) += pci.o obj-$(CONFIG_SMP) += smp.o obj-$(CONFIG_VIOPATH) += viopath.o vio.o obj-$(CONFIG_MODULES) += ksyms.o - -quiet_cmd_dt_strings = DT_STR $@ - cmd_dt_strings = $(OBJCOPY) --rename-section .rodata.str1.8=.dt_strings \ - $< $@ - -$(obj)/dt_mod.o: $(obj)/dt.o - $(call if_changed,dt_strings) diff --git a/arch/powerpc/platforms/iseries/dt.c b/arch/powerpc/platforms/iseries/dt.c index c5a87a72057b..7f45a51fe793 100644 --- a/arch/powerpc/platforms/iseries/dt.c +++ b/arch/powerpc/platforms/iseries/dt.c @@ -51,11 +51,16 @@ /* * These are created by the linker script at the start and end - * of the section containing all the strings from this file. + * of the section containing all the strings marked with the DS macro. */ extern char __dt_strings_start[]; extern char __dt_strings_end[]; +#define DS(s) ({ \ + static const char __s[] __attribute__((section(".dt_strings"))) = s; \ + __s; \ +}) + struct iseries_flat_dt { struct boot_param_header header; u64 reserve_map[2]; @@ -64,9 +69,8 @@ struct iseries_flat_dt { static void * __initdata dt_data; /* - * Putting these strings here keeps them out of the section - * that we rename to .dt_strings using objcopy and capture - * for the strings blob of the flattened device tree. + * Putting these strings here keeps them out of the .dt_strings section + * that we capture for the strings blob of the flattened device tree. */ static char __initdata device_type_cpu[] = "cpu"; static char __initdata device_type_memory[] = "memory"; @@ -173,7 +177,7 @@ static void __init dt_start_node(struct iseries_flat_dt *dt, const char *name) #define dt_end_node(dt) dt_push_u32(dt, OF_DT_END_NODE) -static void __init dt_prop(struct iseries_flat_dt *dt, const char *name, +static void __init __dt_prop(struct iseries_flat_dt *dt, const char *name, const void *data, int len) { unsigned long offset; @@ -191,44 +195,32 @@ static void __init dt_prop(struct iseries_flat_dt *dt, const char *name, /* The actual data. */ dt_push_bytes(dt, data, len); } +#define dt_prop(dt, name, data, len) __dt_prop((dt), DS(name), (data), (len)) -static void __init dt_prop_str(struct iseries_flat_dt *dt, const char *name, - const char *data) -{ - dt_prop(dt, name, data, strlen(data) + 1); /* + 1 for NULL */ -} +#define dt_prop_str(dt, name, data) \ + dt_prop((dt), name, (data), strlen((data)) + 1); /* + 1 for NULL */ -static void __init dt_prop_u32(struct iseries_flat_dt *dt, const char *name, +static void __init __dt_prop_u32(struct iseries_flat_dt *dt, const char *name, u32 data) { - dt_prop(dt, name, &data, sizeof(u32)); + __dt_prop(dt, name, &data, sizeof(u32)); } +#define dt_prop_u32(dt, name, data) __dt_prop_u32((dt), DS(name), (data)) -static void __init __maybe_unused dt_prop_u64(struct iseries_flat_dt *dt, - const char *name, - u64 data) +static void __init __maybe_unused __dt_prop_u64(struct iseries_flat_dt *dt, + const char *name, u64 data) { - dt_prop(dt, name, &data, sizeof(u64)); + __dt_prop(dt, name, &data, sizeof(u64)); } +#define dt_prop_u64(dt, name, data) __dt_prop_u64((dt), DS(name), (data)) -static void __init dt_prop_u64_list(struct iseries_flat_dt *dt, - const char *name, u64 *data, int n) -{ - dt_prop(dt, name, data, sizeof(u64) * n); -} +#define dt_prop_u64_list(dt, name, data, n) \ + dt_prop((dt), name, (data), sizeof(u64) * (n)) -static void __init dt_prop_u32_list(struct iseries_flat_dt *dt, - const char *name, u32 *data, int n) -{ - dt_prop(dt, name, data, sizeof(u32) * n); -} +#define dt_prop_u32_list(dt, name, data, n) \ + dt_prop((dt), name, (data), sizeof(u32) * (n)) -#ifdef notyet -static void __init dt_prop_empty(struct iseries_flat_dt *dt, const char *name) -{ - dt_prop(dt, name, NULL, 0); -} -#endif +#define dt_prop_empty(dt, name) dt_prop((dt), name, NULL, 0) static void __init dt_cpus(struct iseries_flat_dt *dt) { diff --git a/arch/powerpc/platforms/powermac/low_i2c.c b/arch/powerpc/platforms/powermac/low_i2c.c index 21226b74c9b2..414ca9849f23 100644 --- a/arch/powerpc/platforms/powermac/low_i2c.c +++ b/arch/powerpc/platforms/powermac/low_i2c.c @@ -540,8 +540,11 @@ static struct pmac_i2c_host_kw *__init kw_i2c_host_init(struct device_node *np) /* Make sure IRQ is disabled */ kw_write_reg(reg_ier, 0); - /* Request chip interrupt */ - if (request_irq(host->irq, kw_i2c_irq, 0, "keywest i2c", host)) + /* Request chip interrupt. We set IRQF_TIMER because we don't + * want that interrupt disabled between the 2 passes of driver + * suspend or we'll have issues running the pfuncs + */ + if (request_irq(host->irq, kw_i2c_irq, IRQF_TIMER, "keywest i2c", host)) host->irq = NO_IRQ; printk(KERN_INFO "KeyWest i2c @0x%08x irq %d %s\n", diff --git a/arch/powerpc/platforms/pseries/firmware.c b/arch/powerpc/platforms/pseries/firmware.c index 5a707da3f5c2..0a14d8cd314f 100644 --- a/arch/powerpc/platforms/pseries/firmware.c +++ b/arch/powerpc/platforms/pseries/firmware.c @@ -51,11 +51,10 @@ firmware_features_table[FIRMWARE_MAX_FEATURES] = { {FW_FEATURE_VIO, "hcall-vio"}, {FW_FEATURE_RDMA, "hcall-rdma"}, {FW_FEATURE_LLAN, "hcall-lLAN"}, - {FW_FEATURE_BULK, "hcall-bulk"}, + {FW_FEATURE_BULK_REMOVE, "hcall-bulk"}, {FW_FEATURE_XDABR, "hcall-xdabr"}, {FW_FEATURE_MULTITCE, "hcall-multi-tce"}, {FW_FEATURE_SPLPAR, "hcall-splpar"}, - {FW_FEATURE_BULK_REMOVE, "hcall-bulk"}, }; /* Build up the firmware features bitmask using the contents of diff --git a/arch/powerpc/platforms/pseries/msi.c b/arch/powerpc/platforms/pseries/msi.c index bf2e1ac41308..1164c3430f2c 100644 --- a/arch/powerpc/platforms/pseries/msi.c +++ b/arch/powerpc/platforms/pseries/msi.c @@ -432,8 +432,6 @@ static int rtas_setup_msi_irqs(struct pci_dev *pdev, int nvec, int type) /* Read config space back so we can restore after reset */ read_msi_msg(virq, &msg); entry->msg = msg; - - unmask_msi_irq(virq); } return 0; diff --git a/arch/powerpc/platforms/pseries/xics.c b/arch/powerpc/platforms/pseries/xics.c index 419f8a637ffe..b9bf0eedccf2 100644 --- a/arch/powerpc/platforms/pseries/xics.c +++ b/arch/powerpc/platforms/pseries/xics.c @@ -18,6 +18,7 @@ #include <linux/init.h> #include <linux/radix-tree.h> #include <linux/cpu.h> +#include <linux/msi.h> #include <linux/of.h> #include <asm/firmware.h> @@ -219,6 +220,14 @@ static void xics_unmask_irq(unsigned int virq) static unsigned int xics_startup(unsigned int virq) { + /* + * The generic MSI code returns with the interrupt disabled on the + * card, using the MSI mask bits. Firmware doesn't appear to unmask + * at that level, so we do it here by hand. + */ + if (irq_to_desc(virq)->msi_desc) + unmask_msi_irq(virq); + /* unmask it */ xics_unmask_irq(virq); return 0; diff --git a/arch/powerpc/xmon/xmon.c b/arch/powerpc/xmon/xmon.c index c6f0a71b405e..bdbe96c8a7e4 100644 --- a/arch/powerpc/xmon/xmon.c +++ b/arch/powerpc/xmon/xmon.c @@ -517,6 +517,15 @@ static int xmon_core(struct pt_regs *regs, int fromipi) in_xmon = 0; #endif +#ifdef CONFIG_BOOKE + if (regs->msr & MSR_DE) { + bp = at_breakpoint(regs->nip); + if (bp != NULL) { + regs->nip = (unsigned long) &bp->instr[0]; + atomic_inc(&bp->ref_count); + } + } +#else if ((regs->msr & (MSR_IR|MSR_PR|MSR_SF)) == (MSR_IR|MSR_SF)) { bp = at_breakpoint(regs->nip); if (bp != NULL) { @@ -530,7 +539,7 @@ static int xmon_core(struct pt_regs *regs, int fromipi) } } } - +#endif insert_cpu_bpts(); local_irq_restore(flags); @@ -894,6 +903,14 @@ cmds(struct pt_regs *excp) } } +#ifdef CONFIG_BOOKE +static int do_step(struct pt_regs *regs) +{ + regs->msr |= MSR_DE; + mtspr(SPRN_DBCR0, mfspr(SPRN_DBCR0) | DBCR0_IC | DBCR0_IDM); + return 1; +} +#else /* * Step a single instruction. * Some instructions we emulate, others we execute with MSR_SE set. @@ -924,6 +941,7 @@ static int do_step(struct pt_regs *regs) regs->msr |= MSR_SE; return 1; } +#endif static void bootcmds(void) { diff --git a/arch/s390/hypfs/hypfs_diag.c b/arch/s390/hypfs/hypfs_diag.c index 704dd396257b..77df726180ba 100644 --- a/arch/s390/hypfs/hypfs_diag.c +++ b/arch/s390/hypfs/hypfs_diag.c @@ -438,7 +438,7 @@ static int diag204_probe(void) } if (diag204((unsigned long)SUBC_STIB6 | (unsigned long)INFO_EXT, pages, buf) >= 0) { - diag204_store_sc = SUBC_STIB7; + diag204_store_sc = SUBC_STIB6; diag204_info_type = INFO_EXT; goto out; } diff --git a/arch/s390/include/asm/cputime.h b/arch/s390/include/asm/cputime.h index 24b1244aadb9..f23961ada7fb 100644 --- a/arch/s390/include/asm/cputime.h +++ b/arch/s390/include/asm/cputime.h @@ -78,7 +78,7 @@ cputime64_to_jiffies64(cputime64_t cputime) static inline unsigned int cputime_to_msecs(const cputime_t cputime) { - return __div(cputime, 4096000); + return cputime_div(cputime, 4096000); } static inline cputime_t @@ -160,7 +160,7 @@ cputime_to_timeval(const cputime_t cputime, struct timeval *value) static inline clock_t cputime_to_clock_t(cputime_t cputime) { - return __div(cputime, 4096000000ULL / USER_HZ); + return cputime_div(cputime, 4096000000ULL / USER_HZ); } static inline cputime_t @@ -175,7 +175,7 @@ clock_t_to_cputime(unsigned long x) static inline clock_t cputime64_to_clock_t(cputime64_t cputime) { - return __div(cputime, 4096000000ULL / USER_HZ); + return cputime_div(cputime, 4096000000ULL / USER_HZ); } struct s390_idle_data { diff --git a/arch/s390/include/asm/delay.h b/arch/s390/include/asm/delay.h index a356c958e260..8a096b83f51f 100644 --- a/arch/s390/include/asm/delay.h +++ b/arch/s390/include/asm/delay.h @@ -14,10 +14,11 @@ #ifndef _S390_DELAY_H #define _S390_DELAY_H -extern void __udelay(unsigned long usecs); -extern void udelay_simple(unsigned long usecs); +extern void __udelay(unsigned long long usecs); +extern void udelay_simple(unsigned long long usecs); extern void __delay(unsigned long loops); -#define udelay(n) __udelay(n) +#define udelay(n) __udelay((unsigned long long) (n)) +#define mdelay(n) __udelay((unsigned long long) (n) * 1000) #endif /* defined(_S390_DELAY_H) */ diff --git a/arch/s390/include/asm/elf.h b/arch/s390/include/asm/elf.h index 74d0bbb7d955..e885442c1dfe 100644 --- a/arch/s390/include/asm/elf.h +++ b/arch/s390/include/asm/elf.h @@ -92,6 +92,18 @@ /* Keep this the last entry. */ #define R_390_NUM 61 +/* Bits present in AT_HWCAP. */ +#define HWCAP_S390_ESAN3 1 +#define HWCAP_S390_ZARCH 2 +#define HWCAP_S390_STFLE 4 +#define HWCAP_S390_MSA 8 +#define HWCAP_S390_LDISP 16 +#define HWCAP_S390_EIMM 32 +#define HWCAP_S390_DFP 64 +#define HWCAP_S390_HPAGE 128 +#define HWCAP_S390_ETF3EH 256 +#define HWCAP_S390_HIGH_GPRS 512 + /* * These are used to set parameters in the core dumps. */ diff --git a/arch/s390/include/asm/ptrace.h b/arch/s390/include/asm/ptrace.h index 539263fc9ab9..95dcf183a28d 100644 --- a/arch/s390/include/asm/ptrace.h +++ b/arch/s390/include/asm/ptrace.h @@ -311,6 +311,10 @@ typedef struct __u32 orig_gpr2; } s390_compat_regs; +typedef struct +{ + __u32 gprs_high[NUM_GPRS]; +} s390_compat_regs_high; #ifdef __KERNEL__ diff --git a/arch/s390/include/asm/ucontext.h b/arch/s390/include/asm/ucontext.h index d69bec0b03f5..cfb874e66c9a 100644 --- a/arch/s390/include/asm/ucontext.h +++ b/arch/s390/include/asm/ucontext.h @@ -9,6 +9,21 @@ #ifndef _ASM_S390_UCONTEXT_H #define _ASM_S390_UCONTEXT_H +#define UC_EXTENDED 0x00000001 + +#ifndef __s390x__ + +struct ucontext_extended { + unsigned long uc_flags; + struct ucontext *uc_link; + stack_t uc_stack; + _sigregs uc_mcontext; + unsigned long uc_sigmask[2]; + unsigned long uc_gprs_high[16]; +}; + +#endif + struct ucontext { unsigned long uc_flags; struct ucontext *uc_link; diff --git a/arch/s390/kernel/compat_signal.c b/arch/s390/kernel/compat_signal.c index b537cb0e9b55..eee999853a7c 100644 --- a/arch/s390/kernel/compat_signal.c +++ b/arch/s390/kernel/compat_signal.c @@ -39,6 +39,7 @@ typedef struct struct sigcontext32 sc; _sigregs32 sregs; int signo; + __u32 gprs_high[NUM_GPRS]; __u8 retcode[S390_SYSCALL_SIZE]; } sigframe32; @@ -48,6 +49,7 @@ typedef struct __u8 retcode[S390_SYSCALL_SIZE]; compat_siginfo_t info; struct ucontext32 uc; + __u32 gprs_high[NUM_GPRS]; } rt_sigframe32; int copy_siginfo_to_user32(compat_siginfo_t __user *to, siginfo_t *from) @@ -344,6 +346,30 @@ static int restore_sigregs32(struct pt_regs *regs,_sigregs32 __user *sregs) return 0; } +static int save_sigregs_gprs_high(struct pt_regs *regs, __u32 __user *uregs) +{ + __u32 gprs_high[NUM_GPRS]; + int i; + + for (i = 0; i < NUM_GPRS; i++) + gprs_high[i] = regs->gprs[i] >> 32; + + return __copy_to_user(uregs, &gprs_high, sizeof(gprs_high)); +} + +static int restore_sigregs_gprs_high(struct pt_regs *regs, __u32 __user *uregs) +{ + __u32 gprs_high[NUM_GPRS]; + int err, i; + + err = __copy_from_user(&gprs_high, uregs, sizeof(gprs_high)); + if (err) + return err; + for (i = 0; i < NUM_GPRS; i++) + *(__u32 *)®s->gprs[i] = gprs_high[i]; + return 0; +} + asmlinkage long sys32_sigreturn(void) { struct pt_regs *regs = task_pt_regs(current); @@ -363,6 +389,8 @@ asmlinkage long sys32_sigreturn(void) if (restore_sigregs32(regs, &frame->sregs)) goto badframe; + if (restore_sigregs_gprs_high(regs, frame->gprs_high)) + goto badframe; return regs->gprs[2]; @@ -394,6 +422,8 @@ asmlinkage long sys32_rt_sigreturn(void) if (restore_sigregs32(regs, &frame->uc.uc_mcontext)) goto badframe; + if (restore_sigregs_gprs_high(regs, frame->gprs_high)) + goto badframe; err = __get_user(ss_sp, &frame->uc.uc_stack.ss_sp); st.ss_sp = compat_ptr(ss_sp); @@ -474,6 +504,8 @@ static int setup_frame32(int sig, struct k_sigaction *ka, if (save_sigregs32(regs, &frame->sregs)) goto give_sigsegv; + if (save_sigregs_gprs_high(regs, frame->gprs_high)) + goto give_sigsegv; if (__put_user((unsigned long) &frame->sregs, &frame->sc.sregs)) goto give_sigsegv; @@ -529,13 +561,14 @@ static int setup_rt_frame32(int sig, struct k_sigaction *ka, siginfo_t *info, goto give_sigsegv; /* Create the ucontext. */ - err |= __put_user(0, &frame->uc.uc_flags); + err |= __put_user(UC_EXTENDED, &frame->uc.uc_flags); err |= __put_user(0, &frame->uc.uc_link); err |= __put_user(current->sas_ss_sp, &frame->uc.uc_stack.ss_sp); err |= __put_user(sas_ss_flags(regs->gprs[15]), &frame->uc.uc_stack.ss_flags); err |= __put_user(current->sas_ss_size, &frame->uc.uc_stack.ss_size); err |= save_sigregs32(regs, &frame->uc.uc_mcontext); + err |= save_sigregs_gprs_high(regs, frame->gprs_high); err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set)); if (err) goto give_sigsegv; diff --git a/arch/s390/kernel/compat_wrapper.S b/arch/s390/kernel/compat_wrapper.S index 682fb69dba21..cbd9901dc0f8 100644 --- a/arch/s390/kernel/compat_wrapper.S +++ b/arch/s390/kernel/compat_wrapper.S @@ -409,7 +409,7 @@ sys32_munmap_wrapper: .globl sys32_truncate_wrapper sys32_truncate_wrapper: llgtr %r2,%r2 # const char * - llgfr %r3,%r3 # unsigned long + lgfr %r3,%r3 # long jg sys_truncate # branch to system call .globl sys32_ftruncate_wrapper diff --git a/arch/s390/kernel/early.c b/arch/s390/kernel/early.c index bf8b4ae7ff2d..e49e9e0c69fd 100644 --- a/arch/s390/kernel/early.c +++ b/arch/s390/kernel/early.c @@ -55,6 +55,7 @@ static void __init reset_tod_clock(void) disabled_wait(0); sched_clock_base_cc = TOD_UNIX_EPOCH; + S390_lowcore.last_update_clock = sched_clock_base_cc; } #ifdef CONFIG_SHARED_KERNEL @@ -167,6 +168,14 @@ static noinline __init void create_kernel_nss(void) return; } + /* re-initialize cputime accounting. */ + sched_clock_base_cc = get_clock(); + S390_lowcore.last_update_clock = sched_clock_base_cc; + S390_lowcore.last_update_timer = 0x7fffffffffffffffULL; + S390_lowcore.user_timer = 0; + S390_lowcore.system_timer = 0; + asm volatile("SPT 0(%0)" : : "a" (&S390_lowcore.last_update_timer)); + /* re-setup boot command line with new ipl vm parms */ ipl_update_parameters(); setup_boot_command_line(); diff --git a/arch/s390/kernel/entry.S b/arch/s390/kernel/entry.S index f43d2ee54464..48215d15762b 100644 --- a/arch/s390/kernel/entry.S +++ b/arch/s390/kernel/entry.S @@ -565,10 +565,10 @@ pgm_svcper: lh %r7,0x8a # get svc number from lowcore l %r9,__LC_THREAD_INFO # load pointer to thread_info struct TRACE_IRQS_OFF - l %r1,__TI_task(%r9) - mvc __THREAD_per+__PER_atmid(2,%r1),__LC_PER_ATMID - mvc __THREAD_per+__PER_address(4,%r1),__LC_PER_ADDRESS - mvc __THREAD_per+__PER_access_id(1,%r1),__LC_PER_ACCESS_ID + l %r8,__TI_task(%r9) + mvc __THREAD_per+__PER_atmid(2,%r8),__LC_PER_ATMID + mvc __THREAD_per+__PER_address(4,%r8),__LC_PER_ADDRESS + mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID oi __TI_flags+3(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP TRACE_IRQS_ON stosm __SF_EMPTY(%r15),0x03 # reenable interrupts diff --git a/arch/s390/kernel/entry64.S b/arch/s390/kernel/entry64.S index a6f7b20df616..9aff1d449b6e 100644 --- a/arch/s390/kernel/entry64.S +++ b/arch/s390/kernel/entry64.S @@ -543,10 +543,10 @@ pgm_svcper: mvc __LC_LAST_UPDATE_TIMER(8),__LC_SYNC_ENTER_TIMER llgh %r7,__LC_SVC_INT_CODE # get svc number from lowcore lg %r9,__LC_THREAD_INFO # load pointer to thread_info struct - lg %r1,__TI_task(%r9) - mvc __THREAD_per+__PER_atmid(2,%r1),__LC_PER_ATMID - mvc __THREAD_per+__PER_address(8,%r1),__LC_PER_ADDRESS - mvc __THREAD_per+__PER_access_id(1,%r1),__LC_PER_ACCESS_ID + lg %r8,__TI_task(%r9) + mvc __THREAD_per+__PER_atmid(2,%r8),__LC_PER_ATMID + mvc __THREAD_per+__PER_address(8,%r8),__LC_PER_ADDRESS + mvc __THREAD_per+__PER_access_id(1,%r8),__LC_PER_ACCESS_ID oi __TI_flags+7(%r9),_TIF_SINGLE_STEP # set TIF_SINGLE_STEP TRACE_IRQS_ON stosm __SF_EMPTY(%r15),0x03 # reenable interrupts diff --git a/arch/s390/kernel/ftrace.c b/arch/s390/kernel/ftrace.c index 57bdcb1e3cdf..f5fe34dd821b 100644 --- a/arch/s390/kernel/ftrace.c +++ b/arch/s390/kernel/ftrace.c @@ -185,9 +185,6 @@ unsigned long prepare_ftrace_return(unsigned long ip, unsigned long parent) { struct ftrace_graph_ent trace; - /* Nmi's are currently unsupported. */ - if (unlikely(in_nmi())) - goto out; if (unlikely(atomic_read(¤t->tracing_graph_pause))) goto out; if (ftrace_push_return_trace(parent, ip, &trace.depth, 0) == -EBUSY) diff --git a/arch/s390/kernel/ipl.c b/arch/s390/kernel/ipl.c index ee57a42e6e93..4890ac6d7faa 100644 --- a/arch/s390/kernel/ipl.c +++ b/arch/s390/kernel/ipl.c @@ -1595,10 +1595,9 @@ static void stop_run(struct shutdown_trigger *trigger) { if (strcmp(trigger->name, ON_PANIC_STR) == 0) disabled_wait((unsigned long) __builtin_return_address(0)); - else { - signal_processor(smp_processor_id(), sigp_stop); - for (;;); - } + while (signal_processor(smp_processor_id(), sigp_stop) == sigp_busy) + cpu_relax(); + for (;;); } static struct shutdown_action stop_action = {SHUTDOWN_ACTION_STOP_STR, diff --git a/arch/s390/kernel/module.c b/arch/s390/kernel/module.c index ab2e3ed28abc..639380a0c45c 100644 --- a/arch/s390/kernel/module.c +++ b/arch/s390/kernel/module.c @@ -55,6 +55,8 @@ void *module_alloc(unsigned long size) /* Free memory returned from module_alloc */ void module_free(struct module *mod, void *module_region) { + vfree(mod->arch.syminfo); + mod->arch.syminfo = NULL; vfree(module_region); } @@ -402,6 +404,7 @@ int module_finalize(const Elf_Ehdr *hdr, struct module *me) { vfree(me->arch.syminfo); + me->arch.syminfo = NULL; return module_bug_finalize(hdr, sechdrs, me); } diff --git a/arch/s390/kernel/processor.c b/arch/s390/kernel/processor.c index 802c8ab247f3..0729f36c2fe3 100644 --- a/arch/s390/kernel/processor.c +++ b/arch/s390/kernel/processor.c @@ -31,9 +31,9 @@ void __cpuinit print_cpu_info(void) static int show_cpuinfo(struct seq_file *m, void *v) { - static const char *hwcap_str[9] = { + static const char *hwcap_str[10] = { "esan3", "zarch", "stfle", "msa", "ldisp", "eimm", "dfp", - "edat", "etf3eh" + "edat", "etf3eh", "highgprs" }; struct _lowcore *lc; unsigned long n = (unsigned long) v - 1; @@ -48,7 +48,7 @@ static int show_cpuinfo(struct seq_file *m, void *v) num_online_cpus(), loops_per_jiffy/(500000/HZ), (loops_per_jiffy/(5000/HZ))%100); seq_puts(m, "features\t: "); - for (i = 0; i < 9; i++) + for (i = 0; i < 10; i++) if (hwcap_str[i] && (elf_hwcap & (1UL << i))) seq_printf(m, "%s ", hwcap_str[i]); seq_puts(m, "\n"); diff --git a/arch/s390/kernel/ptrace.c b/arch/s390/kernel/ptrace.c index a8738676b26c..653c6a178740 100644 --- a/arch/s390/kernel/ptrace.c +++ b/arch/s390/kernel/ptrace.c @@ -57,6 +57,7 @@ enum s390_regset { REGSET_GENERAL, REGSET_FP, + REGSET_GENERAL_EXTENDED, }; static void @@ -879,6 +880,67 @@ static int s390_compat_regs_set(struct task_struct *target, return rc; } +static int s390_compat_regs_high_get(struct task_struct *target, + const struct user_regset *regset, + unsigned int pos, unsigned int count, + void *kbuf, void __user *ubuf) +{ + compat_ulong_t *gprs_high; + + gprs_high = (compat_ulong_t *) + &task_pt_regs(target)->gprs[pos / sizeof(compat_ulong_t)]; + if (kbuf) { + compat_ulong_t *k = kbuf; + while (count > 0) { + *k++ = *gprs_high; + gprs_high += 2; + count -= sizeof(*k); + } + } else { + compat_ulong_t __user *u = ubuf; + while (count > 0) { + if (__put_user(*gprs_high, u++)) + return -EFAULT; + gprs_high += 2; + count -= sizeof(*u); + } + } + return 0; +} + +static int s390_compat_regs_high_set(struct task_struct *target, + const struct user_regset *regset, + unsigned int pos, unsigned int count, + const void *kbuf, const void __user *ubuf) +{ + compat_ulong_t *gprs_high; + int rc = 0; + + gprs_high = (compat_ulong_t *) + &task_pt_regs(target)->gprs[pos / sizeof(compat_ulong_t)]; + if (kbuf) { + const compat_ulong_t *k = kbuf; + while (count > 0) { + *gprs_high = *k++; + *gprs_high += 2; + count -= sizeof(*k); + } + } else { + const compat_ulong_t __user *u = ubuf; + while (count > 0 && !rc) { + unsigned long word; + rc = __get_user(word, u++); + if (rc) + break; + *gprs_high = word; + *gprs_high += 2; + count -= sizeof(*u); + } + } + + return rc; +} + static const struct user_regset s390_compat_regsets[] = { [REGSET_GENERAL] = { .core_note_type = NT_PRSTATUS, @@ -896,6 +958,14 @@ static const struct user_regset s390_compat_regsets[] = { .get = s390_fpregs_get, .set = s390_fpregs_set, }, + [REGSET_GENERAL_EXTENDED] = { + .core_note_type = NT_PRXSTATUS, + .n = sizeof(s390_compat_regs_high) / sizeof(compat_long_t), + .size = sizeof(compat_long_t), + .align = sizeof(compat_long_t), + .get = s390_compat_regs_high_get, + .set = s390_compat_regs_high_set, + }, }; static const struct user_regset_view user_s390_compat_view = { diff --git a/arch/s390/kernel/setup.c b/arch/s390/kernel/setup.c index 9ed13a1ed376..061479ff029f 100644 --- a/arch/s390/kernel/setup.c +++ b/arch/s390/kernel/setup.c @@ -729,7 +729,7 @@ static void __init setup_hwcaps(void) if ((facility_list & (1UL << (31 - 22))) && (facility_list & (1UL << (31 - 30)))) - elf_hwcap |= 1UL << 8; + elf_hwcap |= HWCAP_S390_ETF3EH; /* * Check for additional facilities with store-facility-list-extended. @@ -748,11 +748,20 @@ static void __init setup_hwcaps(void) __stfle(&facility_list_extended, 1) > 0) { if ((facility_list_extended & (1ULL << (63 - 42))) && (facility_list_extended & (1ULL << (63 - 44)))) - elf_hwcap |= 1UL << 6; + elf_hwcap |= HWCAP_S390_DFP; } + /* + * Huge page support HWCAP_S390_HPAGE is bit 7. + */ if (MACHINE_HAS_HPAGE) - elf_hwcap |= 1UL << 7; + elf_hwcap |= HWCAP_S390_HPAGE; + + /* + * 64-bit register support for 31-bit processes + * HWCAP_S390_HIGH_GPRS is bit 9. + */ + elf_hwcap |= HWCAP_S390_HIGH_GPRS; switch (S390_lowcore.cpu_id.machine) { case 0x9672: diff --git a/arch/s390/kernel/smp.c b/arch/s390/kernel/smp.c index c932caa5e850..93e52039321b 100644 --- a/arch/s390/kernel/smp.c +++ b/arch/s390/kernel/smp.c @@ -76,7 +76,6 @@ static int cpu_stopped(int cpu) __u32 status; switch (signal_processor_ps(&status, 0, cpu, sigp_sense)) { - case sigp_order_code_accepted: case sigp_status_stored: /* Check for stopped and check stop state */ if (status & 0x50) @@ -638,6 +637,8 @@ void __cpu_die(unsigned int cpu) /* Wait until target cpu is down */ while (!cpu_stopped(cpu)) cpu_relax(); + while (signal_processor_p(0, cpu, sigp_set_prefix) == sigp_busy) + udelay(10); smp_free_lowcore(cpu); pr_info("Processor %d stopped\n", cpu); } @@ -645,8 +646,8 @@ void __cpu_die(unsigned int cpu) void cpu_die(void) { idle_task_exit(); - signal_processor(smp_processor_id(), sigp_stop); - BUG(); + while (signal_processor(smp_processor_id(), sigp_stop) == sigp_busy) + cpu_relax(); for (;;); } diff --git a/arch/s390/kernel/swsusp_asm64.S b/arch/s390/kernel/swsusp_asm64.S index fe927d0bc20b..0c26cc1898ec 100644 --- a/arch/s390/kernel/swsusp_asm64.S +++ b/arch/s390/kernel/swsusp_asm64.S @@ -43,7 +43,7 @@ swsusp_arch_suspend: lghi %r1,0x1000 /* Save CPU address */ - stap __LC_CPU_ADDRESS(%r1) + stap __LC_CPU_ADDRESS(%r0) /* Store registers */ mvc 0x318(4,%r1),__SF_EMPTY(%r15) /* move prefix to lowcore */ @@ -69,8 +69,21 @@ swsusp_arch_suspend: stmg %r0,%r15,0x280(%r1) /* store general registers */ stpt 0x328(%r1) /* store timer */ + stck __SF_EMPTY(%r15) /* store clock */ stckc 0x330(%r1) /* store clock comparator */ + /* Update cputime accounting before going to sleep */ + lg %r0,__LC_LAST_UPDATE_TIMER + slg %r0,0x328(%r1) + alg %r0,__LC_SYSTEM_TIMER + stg %r0,__LC_SYSTEM_TIMER + mvc __LC_LAST_UPDATE_TIMER(8),0x328(%r1) + lg %r0,__LC_LAST_UPDATE_CLOCK + slg %r0,__SF_EMPTY(%r15) + alg %r0,__LC_STEAL_TIMER + stg %r0,__LC_STEAL_TIMER + mvc __LC_LAST_UPDATE_CLOCK(8),__SF_EMPTY(%r15) + /* Activate DAT */ stosm __SF_EMPTY(%r15),0x04 @@ -159,8 +172,7 @@ pgm_check_entry: larl %r1,.Lresume_cpu /* Resume CPU address: r2 */ stap 0(%r1) llgh %r2,0(%r1) - lghi %r3,0x1000 - llgh %r1,__LC_CPU_ADDRESS(%r3) /* Suspend CPU address: r1 */ + llgh %r1,__LC_CPU_ADDRESS(%r0) /* Suspend CPU address: r1 */ cgr %r1,%r2 je restore_registers /* r1 = r2 -> nothing to do */ larl %r4,.Lrestart_suspend_psw /* Set new restart PSW */ @@ -187,6 +199,7 @@ pgm_check_entry: brc 2,4b /* busy, try again */ 5: sigp %r9,%r2,__SIGP_STOP /* stop resume (current) CPU */ + brc 2,5b /* busy, try again */ 6: j 6b restart_suspend: @@ -194,14 +207,18 @@ restart_suspend: llgh %r2,0(%r1) 7: sigp %r9,%r2,__SIGP_SENSE /* Wait for resume CPU */ + brc 8,7b /* accepted, status 0, still running */ brc 2,7b /* busy, try again */ tmll %r9,0x40 /* Test if resume CPU is stopped */ jz 7b restore_registers: /* Restore registers */ - lghi %r13,0x1000 /* %r1 = pointer to save arae */ + lghi %r13,0x1000 /* %r1 = pointer to save area */ + /* Ignore time spent in suspended state. */ + llgf %r1,0x318(%r13) + stck __LC_LAST_UPDATE_CLOCK(%r1) spt 0x328(%r13) /* reprogram timer */ //sckc 0x330(%r13) /* set clock comparator */ @@ -229,9 +246,6 @@ restore_registers: /* Load old stack */ lg %r15,0x2f8(%r13) - /* Pointer to save area */ - lghi %r13,0x1000 - /* Restore prefix register */ spx 0x318(%r13) diff --git a/arch/s390/kernel/vdso.c b/arch/s390/kernel/vdso.c index 45a3e9a7ae21..adfb32aa6d59 100644 --- a/arch/s390/kernel/vdso.c +++ b/arch/s390/kernel/vdso.c @@ -247,6 +247,13 @@ int arch_setup_additional_pages(struct linux_binprm *bprm, int uses_interp) } /* + * Put vDSO base into mm struct. We need to do this before calling + * install_special_mapping or the perf counter mmap tracking code + * will fail to recognise it as a vDSO (since arch_vma_name fails). + */ + current->mm->context.vdso_base = vdso_base; + + /* * our vma flags don't have VM_WRITE so by default, the process * isn't allowed to write those pages. * gdb can break that with ptrace interface, and thus trigger COW @@ -267,14 +274,7 @@ int arch_setup_additional_pages(struct linux_binprm *bprm, int uses_interp) VM_ALWAYSDUMP, vdso_pagelist); if (rc) - goto out_up; - - /* Put vDSO base into mm struct */ - current->mm->context.vdso_base = vdso_base; - - up_write(&mm->mmap_sem); - return 0; - + current->mm->context.vdso_base = 0; out_up: up_write(&mm->mmap_sem); return rc; diff --git a/arch/s390/kernel/vmlinux.lds.S b/arch/s390/kernel/vmlinux.lds.S index bc15ef93e656..a68ac10213b2 100644 --- a/arch/s390/kernel/vmlinux.lds.S +++ b/arch/s390/kernel/vmlinux.lds.S @@ -51,6 +51,7 @@ SECTIONS . = ALIGN(PAGE_SIZE); _eshared = .; /* End of shareable data */ + _sdata = .; /* Start of data section */ EXCEPTION_TABLE(16) :data diff --git a/arch/s390/kvm/kvm-s390.h b/arch/s390/kvm/kvm-s390.h index ec5eee7c25d8..06cce8285ba0 100644 --- a/arch/s390/kvm/kvm-s390.h +++ b/arch/s390/kvm/kvm-s390.h @@ -58,7 +58,7 @@ int kvm_s390_inject_vcpu(struct kvm_vcpu *vcpu, int kvm_s390_inject_program_int(struct kvm_vcpu *vcpu, u16 code); int kvm_s390_inject_sigp_stop(struct kvm_vcpu *vcpu, int action); -static inline int kvm_s390_vcpu_get_memsize(struct kvm_vcpu *vcpu) +static inline long kvm_s390_vcpu_get_memsize(struct kvm_vcpu *vcpu) { return vcpu->arch.sie_block->gmslm - vcpu->arch.sie_block->gmsor diff --git a/arch/s390/lib/delay.c b/arch/s390/lib/delay.c index 97c1eca83cc2..752b362bf651 100644 --- a/arch/s390/lib/delay.c +++ b/arch/s390/lib/delay.c @@ -25,13 +25,13 @@ void __delay(unsigned long loops) asm volatile("0: brct %0,0b" : : "d" ((loops/2) + 1)); } -static void __udelay_disabled(unsigned long usecs) +static void __udelay_disabled(unsigned long long usecs) { unsigned long mask, cr0, cr0_saved; u64 clock_saved; clock_saved = local_tick_disable(); - set_clock_comparator(get_clock() + ((u64) usecs << 12)); + set_clock_comparator(get_clock() + (usecs << 12)); __ctl_store(cr0_saved, 0, 0); cr0 = (cr0_saved & 0xffff00e0) | 0x00000800; __ctl_load(cr0 , 0, 0); @@ -46,20 +46,25 @@ static void __udelay_disabled(unsigned long usecs) set_clock_comparator(S390_lowcore.clock_comparator); } -static void __udelay_enabled(unsigned long usecs) +static void __udelay_enabled(unsigned long long usecs) { unsigned long mask; - u64 end, time; + u64 clock_saved; + u64 end; mask = psw_kernel_bits | PSW_MASK_WAIT | PSW_MASK_EXT | PSW_MASK_IO; - end = get_clock() + ((u64) usecs << 12); + end = get_clock() + (usecs << 12); do { - time = end < S390_lowcore.clock_comparator ? - end : S390_lowcore.clock_comparator; - set_clock_comparator(time); + clock_saved = 0; + if (end < S390_lowcore.clock_comparator) { + clock_saved = local_tick_disable(); + set_clock_comparator(end); + } trace_hardirqs_on(); __load_psw_mask(mask); local_irq_disable(); + if (clock_saved) + local_tick_enable(clock_saved); } while (get_clock() < end); set_clock_comparator(S390_lowcore.clock_comparator); } @@ -67,7 +72,7 @@ static void __udelay_enabled(unsigned long usecs) /* * Waits for 'usecs' microseconds using the TOD clock comparator. */ -void __udelay(unsigned long usecs) +void __udelay(unsigned long long usecs) { unsigned long flags; @@ -101,11 +106,11 @@ EXPORT_SYMBOL(__udelay); * Simple udelay variant. To be used on startup and reboot * when the interrupt handler isn't working. */ -void udelay_simple(unsigned long usecs) +void udelay_simple(unsigned long long usecs) { u64 end; - end = get_clock() + ((u64) usecs << 12); + end = get_clock() + (usecs << 12); while (get_clock() < end) cpu_relax(); } diff --git a/arch/s390/lib/uaccess_mvcos.c b/arch/s390/lib/uaccess_mvcos.c index 3f15aaf54855..58da3f461214 100644 --- a/arch/s390/lib/uaccess_mvcos.c +++ b/arch/s390/lib/uaccess_mvcos.c @@ -36,7 +36,7 @@ static size_t copy_from_user_mvcos(size_t size, const void __user *ptr, void *x) tmp1 = -4096UL; asm volatile( "0: .insn ss,0xc80000000000,0(%0,%2),0(%1),0\n" - " jz 7f\n" + "9: jz 7f\n" "1:"ALR" %0,%3\n" " "SLR" %1,%3\n" " "SLR" %2,%3\n" @@ -47,7 +47,7 @@ static size_t copy_from_user_mvcos(size_t size, const void __user *ptr, void *x) " "CLR" %0,%4\n" /* copy crosses next page boundary? */ " jnh 4f\n" "3: .insn ss,0xc80000000000,0(%4,%2),0(%1),0\n" - " "SLR" %0,%4\n" + "10:"SLR" %0,%4\n" " "ALR" %2,%4\n" "4:"LHI" %4,-1\n" " "ALR" %4,%0\n" /* copy remaining size, subtract 1 */ @@ -61,7 +61,7 @@ static size_t copy_from_user_mvcos(size_t size, const void __user *ptr, void *x) " j 8f\n" "7:"SLR" %0,%0\n" "8: \n" - EX_TABLE(0b,2b) EX_TABLE(3b,4b) + EX_TABLE(0b,2b) EX_TABLE(3b,4b) EX_TABLE(9b,2b) EX_TABLE(10b,4b) : "+a" (size), "+a" (ptr), "+a" (x), "+a" (tmp1), "=a" (tmp2) : "d" (reg0) : "cc", "memory"); return size; @@ -82,7 +82,7 @@ static size_t copy_to_user_mvcos(size_t size, void __user *ptr, const void *x) tmp1 = -4096UL; asm volatile( "0: .insn ss,0xc80000000000,0(%0,%1),0(%2),0\n" - " jz 4f\n" + "6: jz 4f\n" "1:"ALR" %0,%3\n" " "SLR" %1,%3\n" " "SLR" %2,%3\n" @@ -93,11 +93,11 @@ static size_t copy_to_user_mvcos(size_t size, void __user *ptr, const void *x) " "CLR" %0,%4\n" /* copy crosses next page boundary? */ " jnh 5f\n" "3: .insn ss,0xc80000000000,0(%4,%1),0(%2),0\n" - " "SLR" %0,%4\n" + "7:"SLR" %0,%4\n" " j 5f\n" "4:"SLR" %0,%0\n" "5: \n" - EX_TABLE(0b,2b) EX_TABLE(3b,5b) + EX_TABLE(0b,2b) EX_TABLE(3b,5b) EX_TABLE(6b,2b) EX_TABLE(7b,5b) : "+a" (size), "+a" (ptr), "+a" (x), "+a" (tmp1), "=a" (tmp2) : "d" (reg0) : "cc", "memory"); return size; diff --git a/arch/s390/lib/uaccess_std.c b/arch/s390/lib/uaccess_std.c index d2ffbadb51a7..07deaeee14c8 100644 --- a/arch/s390/lib/uaccess_std.c +++ b/arch/s390/lib/uaccess_std.c @@ -36,12 +36,12 @@ size_t copy_from_user_std(size_t size, const void __user *ptr, void *x) tmp1 = -256UL; asm volatile( "0: mvcp 0(%0,%2),0(%1),%3\n" - " jz 8f\n" + "10:jz 8f\n" "1:"ALR" %0,%3\n" " la %1,256(%1)\n" " la %2,256(%2)\n" "2: mvcp 0(%0,%2),0(%1),%3\n" - " jnz 1b\n" + "11:jnz 1b\n" " j 8f\n" "3: la %4,255(%1)\n" /* %4 = ptr + 255 */ " "LHI" %3,-4096\n" @@ -50,7 +50,7 @@ size_t copy_from_user_std(size_t size, const void __user *ptr, void *x) " "CLR" %0,%4\n" /* copy crosses next page boundary? */ " jnh 5f\n" "4: mvcp 0(%4,%2),0(%1),%3\n" - " "SLR" %0,%4\n" + "12:"SLR" %0,%4\n" " "ALR" %2,%4\n" "5:"LHI" %4,-1\n" " "ALR" %4,%0\n" /* copy remaining size, subtract 1 */ @@ -65,6 +65,7 @@ size_t copy_from_user_std(size_t size, const void __user *ptr, void *x) "8:"SLR" %0,%0\n" "9: \n" EX_TABLE(0b,3b) EX_TABLE(2b,3b) EX_TABLE(4b,5b) + EX_TABLE(10b,3b) EX_TABLE(11b,3b) EX_TABLE(12b,5b) : "+a" (size), "+a" (ptr), "+a" (x), "+a" (tmp1), "=a" (tmp2) : : "cc", "memory"); return size; @@ -85,12 +86,12 @@ size_t copy_to_user_std(size_t size, void __user *ptr, const void *x) tmp1 = -256UL; asm volatile( "0: mvcs 0(%0,%1),0(%2),%3\n" - " jz 5f\n" + "7: jz 5f\n" "1:"ALR" %0,%3\n" " la %1,256(%1)\n" " la %2,256(%2)\n" "2: mvcs 0(%0,%1),0(%2),%3\n" - " jnz 1b\n" + "8: jnz 1b\n" " j 5f\n" "3: la %4,255(%1)\n" /* %4 = ptr + 255 */ " "LHI" %3,-4096\n" @@ -99,11 +100,12 @@ size_t copy_to_user_std(size_t size, void __user *ptr, const void *x) " "CLR" %0,%4\n" /* copy crosses next page boundary? */ " jnh 6f\n" "4: mvcs 0(%4,%1),0(%2),%3\n" - " "SLR" %0,%4\n" + "9:"SLR" %0,%4\n" " j 6f\n" "5:"SLR" %0,%0\n" "6: \n" EX_TABLE(0b,3b) EX_TABLE(2b,3b) EX_TABLE(4b,6b) + EX_TABLE(7b,3b) EX_TABLE(8b,3b) EX_TABLE(9b,6b) : "+a" (size), "+a" (ptr), "+a" (x), "+a" (tmp1), "=a" (tmp2) : : "cc", "memory"); return size; diff --git a/arch/s390/mm/pgtable.c b/arch/s390/mm/pgtable.c index c60bfb309ce6..2757c5616a07 100644 --- a/arch/s390/mm/pgtable.c +++ b/arch/s390/mm/pgtable.c @@ -279,7 +279,10 @@ int s390_enable_sie(void) /* lets check if we are allowed to replace the mm */ task_lock(tsk); if (!tsk->mm || atomic_read(&tsk->mm->mm_users) > 1 || - tsk->mm != tsk->active_mm || !hlist_empty(&tsk->mm->ioctx_list)) { +#ifdef CONFIG_AIO + !hlist_empty(&tsk->mm->ioctx_list) || +#endif + tsk->mm != tsk->active_mm) { task_unlock(tsk); return -EINVAL; } @@ -295,7 +298,10 @@ int s390_enable_sie(void) /* Now lets check again if something happened */ task_lock(tsk); if (!tsk->mm || atomic_read(&tsk->mm->mm_users) > 1 || - tsk->mm != tsk->active_mm || !hlist_empty(&tsk->mm->ioctx_list)) { +#ifdef CONFIG_AIO + !hlist_empty(&tsk->mm->ioctx_list) || +#endif + tsk->mm != tsk->active_mm) { mmput(mm); task_unlock(tsk); return -EINVAL; diff --git a/arch/sh/Kconfig b/arch/sh/Kconfig index b940424f8ccc..88cdeb9f72d9 100644 --- a/arch/sh/Kconfig +++ b/arch/sh/Kconfig @@ -37,7 +37,6 @@ config SUPERH32 select HAVE_FTRACE_MCOUNT_RECORD select HAVE_DYNAMIC_FTRACE select HAVE_FUNCTION_TRACE_MCOUNT_TEST - select HAVE_FTRACE_SYSCALLS select HAVE_FUNCTION_GRAPH_TRACER select HAVE_ARCH_KGDB select ARCH_HIBERNATION_POSSIBLE if MMU @@ -122,6 +121,9 @@ config SYS_SUPPORTS_APM_EMULATION bool select ARCH_SUSPEND_POSSIBLE +config SYS_SUPPORTS_HUGETLBFS + bool + config SYS_SUPPORTS_SMP bool @@ -196,6 +198,7 @@ config CPU_SH4 select CPU_HAS_SR_RB select CPU_HAS_FPU if !CPU_SH4AL_DSP select SYS_SUPPORTS_TMU + select SYS_SUPPORTS_HUGETLBFS if MMU config CPU_SH4A bool @@ -210,6 +213,7 @@ config CPU_SH5 bool select CPU_HAS_FPU select SYS_SUPPORTS_TMU + select SYS_SUPPORTS_HUGETLBFS if MMU config CPU_SHX2 bool diff --git a/arch/sh/Makefile b/arch/sh/Makefile index fc51a918b31a..66e40aabc600 100644 --- a/arch/sh/Makefile +++ b/arch/sh/Makefile @@ -199,7 +199,7 @@ endif libs-$(CONFIG_SUPERH32) := arch/sh/lib/ $(libs-y) libs-$(CONFIG_SUPERH64) := arch/sh/lib64/ $(libs-y) -BOOT_TARGETS = uImage uImage.bz2 uImage.gz uImage.lzma uImage.srec \ +BOOT_TARGETS = uImage uImage.bz2 uImage.gz uImage.lzma uImage.srec uImage.bin \ zImage vmlinux.srec romImage PHONY += maketools $(BOOT_TARGETS) FORCE @@ -225,6 +225,7 @@ define archhelp @echo ' vmlinux.srec - Create an ELF S-record' @echo '* uImage - Alias to bootable U-Boot image' @echo ' uImage.srec - Create an S-record for U-Boot' + @echo ' uImage.bin - Kernel-only image for U-Boot (bin)' @echo '* uImage.gz - Kernel-only image for U-Boot (gzip)' @echo ' uImage.bz2 - Kernel-only image for U-Boot (bzip2)' @echo ' uImage.lzma - Kernel-only image for U-Boot (lzma)' diff --git a/arch/sh/boards/board-magicpanelr2.c b/arch/sh/boards/board-magicpanelr2.c index 0a37c8bfc959..99ffc5f1c0dd 100644 --- a/arch/sh/boards/board-magicpanelr2.c +++ b/arch/sh/boards/board-magicpanelr2.c @@ -205,8 +205,6 @@ static void __init setup_port_multiplexing(void) static void __init mpr2_setup(char **cmdline_p) { - __set_io_port_base(0xa0000000); - /* set Pin Select Register A: * /PCC_CD1, /PCC_CD2, PCC_BVD1, PCC_BVD2, * /IOIS16, IRQ4, IRQ5, USB1d_SUSPEND diff --git a/arch/sh/boards/mach-dreamcast/setup.c b/arch/sh/boards/mach-dreamcast/setup.c index ebe99227d4e6..a4b7402d6176 100644 --- a/arch/sh/boards/mach-dreamcast/setup.c +++ b/arch/sh/boards/mach-dreamcast/setup.c @@ -42,8 +42,6 @@ static void __init dreamcast_setup(char **cmdline_p) /* Acknowledge any previous events */ /* XXX */ - __set_io_port_base(0xa0000000); - /* Assign all virtual IRQs to the System ASIC int. handler */ for (i = HW_EVENT_IRQ_BASE; i < HW_EVENT_IRQ_MAX; i++) set_irq_chip_and_handler(i, &systemasic_int, diff --git a/arch/sh/boards/mach-ecovec24/setup.c b/arch/sh/boards/mach-ecovec24/setup.c index 5f9881e16e2f..3b1ceb46fa54 100644 --- a/arch/sh/boards/mach-ecovec24/setup.c +++ b/arch/sh/boards/mach-ecovec24/setup.c @@ -18,6 +18,7 @@ #include <linux/delay.h> #include <linux/usb/r8a66597.h> #include <linux/i2c.h> +#include <linux/i2c/tsc2007.h> #include <linux/input.h> #include <video/sh_mobile_lcdc.h> #include <media/sh_mobile_ceu.h> @@ -38,6 +39,20 @@ * 0x1800_0000 MFI 16bit */ +/* SWITCH + *------------------------------ + * DS2[1] = FlashROM write protect ON : write protect + * OFF : No write protect + * DS2[2] = RMII / TS, SCIF ON : RMII + * OFF : TS, SCIF3 + * DS2[3] = Camera / Video ON : Camera + * OFF : NTSC/PAL (IN) + * DS2[5] = NTSC_OUT Clock ON : On board OSC + * OFF : SH7724 DV_CLK + * DS2[6-7] = MMC / SD ON-OFF : SD + * OFF-ON : MMC + */ + /* Heartbeat */ static unsigned char led_pos[] = { 0, 1, 2, 3 }; static struct heartbeat_data heartbeat_data = { @@ -70,7 +85,7 @@ static struct mtd_partition nor_flash_partitions[] = { .name = "boot loader", .offset = 0, .size = (5 * 1024 * 1024), - .mask_flags = MTD_CAP_ROM, + .mask_flags = MTD_WRITEABLE, /* force read-only */ }, { .name = "free-area", .offset = MTDPART_OFS_APPEND, @@ -376,6 +391,43 @@ static struct platform_device keysc_device = { }, }; +/* TouchScreen */ +#define IRQ0 32 +static int ts_get_pendown_state(void) +{ + int val = 0; + gpio_free(GPIO_FN_INTC_IRQ0); + gpio_request(GPIO_PTZ0, NULL); + gpio_direction_input(GPIO_PTZ0); + + val = gpio_get_value(GPIO_PTZ0); + + gpio_free(GPIO_PTZ0); + gpio_request(GPIO_FN_INTC_IRQ0, NULL); + + return val ? 0 : 1; +} + +static int ts_init(void) +{ + gpio_request(GPIO_FN_INTC_IRQ0, NULL); + return 0; +} + +struct tsc2007_platform_data tsc2007_info = { + .model = 2007, + .x_plate_ohms = 180, + .get_pendown_state = ts_get_pendown_state, + .init_platform_hw = ts_init, +}; + +static struct i2c_board_info ts_i2c_clients = { + I2C_BOARD_INFO("tsc2007", 0x48), + .type = "tsc2007", + .platform_data = &tsc2007_info, + .irq = IRQ0, +}; + static struct platform_device *ecovec_devices[] __initdata = { &heartbeat_device, &nor_flash_device, @@ -460,6 +512,11 @@ static void __init sh_eth_init(void) #define IODRIVEA 0xA405018A static int __init arch_setup(void) { + /* enable STATUS0, STATUS2 and PDSTATUS */ + gpio_request(GPIO_FN_STATUS0, NULL); + gpio_request(GPIO_FN_STATUS2, NULL); + gpio_request(GPIO_FN_PDSTATUS, NULL); + /* enable SCIFA0 */ gpio_request(GPIO_FN_SCIF0_TXD, NULL); gpio_request(GPIO_FN_SCIF0_RXD, NULL); @@ -590,6 +647,10 @@ static int __init arch_setup(void) */ gpio_request(GPIO_PTF4, NULL); gpio_direction_output(GPIO_PTF4, 1); + + /* enable TouchScreen */ + i2c_register_board_info(0, &ts_i2c_clients, 1); + set_irq_type(IRQ0, IRQ_TYPE_LEVEL_LOW); } /* enable CEU0 */ diff --git a/arch/sh/boards/mach-landisk/gio.c b/arch/sh/boards/mach-landisk/gio.c index 25cdf7358000..528013188196 100644 --- a/arch/sh/boards/mach-landisk/gio.c +++ b/arch/sh/boards/mach-landisk/gio.c @@ -14,7 +14,6 @@ */ #include <linux/module.h> #include <linux/init.h> -#include <linux/smp_lock.h> #include <linux/kdev_t.h> #include <linux/cdev.h> #include <linux/fs.h> @@ -35,7 +34,7 @@ static int gio_open(struct inode *inode, struct file *filp) int minor; int ret = -ENOENT; - lock_kernel(); + preempt_disable(); minor = MINOR(inode->i_rdev); if (minor < DEVCOUNT) { if (openCnt > 0) { @@ -45,7 +44,7 @@ static int gio_open(struct inode *inode, struct file *filp) ret = 0; } } - unlock_kernel(); + preempt_enable(); return ret; } @@ -60,8 +59,7 @@ static int gio_close(struct inode *inode, struct file *filp) return 0; } -static int gio_ioctl(struct inode *inode, struct file *filp, - unsigned int cmd, unsigned long arg) +static long gio_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) { unsigned int data; static unsigned int addr = 0; @@ -129,7 +127,7 @@ static const struct file_operations gio_fops = { .owner = THIS_MODULE, .open = gio_open, /* open */ .release = gio_close, /* release */ - .ioctl = gio_ioctl, /* ioctl */ + .unlocked_ioctl = gio_ioctl, }; static int __init gio_init(void) diff --git a/arch/sh/boards/mach-rsk/devices-rsk7203.c b/arch/sh/boards/mach-rsk/devices-rsk7203.c index 4af3a771c058..c37617e63220 100644 --- a/arch/sh/boards/mach-rsk/devices-rsk7203.c +++ b/arch/sh/boards/mach-rsk/devices-rsk7203.c @@ -11,10 +11,6 @@ #include <linux/types.h> #include <linux/platform_device.h> #include <linux/interrupt.h> -#include <linux/mtd/mtd.h> -#include <linux/mtd/partitions.h> -#include <linux/mtd/physmap.h> -#include <linux/mtd/map.h> #include <linux/smsc911x.h> #include <linux/gpio.h> #include <linux/leds.h> diff --git a/arch/sh/boards/mach-rsk/setup.c b/arch/sh/boards/mach-rsk/setup.c index af64d030a5c7..a5c0df785bfe 100644 --- a/arch/sh/boards/mach-rsk/setup.c +++ b/arch/sh/boards/mach-rsk/setup.c @@ -15,14 +15,12 @@ #include <linux/mtd/mtd.h> #include <linux/mtd/partitions.h> #include <linux/mtd/physmap.h> +#ifdef CONFIG_MTD #include <linux/mtd/map.h> +#endif #include <asm/machvec.h> #include <asm/io.h> -static const char *probes[] = { "cmdlinepart", NULL }; - -static struct mtd_partition *parsed_partitions; - static struct mtd_partition rsk_partitions[] = { { .name = "Bootloader", @@ -41,6 +39,8 @@ static struct mtd_partition rsk_partitions[] = { }; static struct physmap_flash_data flash_data = { + .parts = rsk_partitions, + .nr_parts = ARRAY_SIZE(rsk_partitions), .width = 2, }; @@ -60,7 +60,8 @@ static struct platform_device flash_device = { }, }; -static struct mtd_info *flash_mtd; +#ifdef CONFIG_MTD +static const char *probes[] = { "cmdlinepart", NULL }; static struct map_info rsk_flash_map = { .name = "RSK+ Flash", @@ -68,6 +69,10 @@ static struct map_info rsk_flash_map = { .bankwidth = 2, }; +static struct mtd_info *flash_mtd; + +static struct mtd_partition *parsed_partitions; + static void __init set_mtd_partitions(void) { int nr_parts = 0; @@ -77,14 +82,14 @@ static void __init set_mtd_partitions(void) nr_parts = parse_mtd_partitions(flash_mtd, probes, &parsed_partitions, 0); /* If there is no partition table, used the hard coded table */ - if (nr_parts <= 0) { - flash_data.parts = rsk_partitions; - flash_data.nr_parts = ARRAY_SIZE(rsk_partitions); - } else { + if (nr_parts > 0) { flash_data.nr_parts = nr_parts; flash_data.parts = parsed_partitions; } } +#else +static inline void set_mtd_partitions(void) {} +#endif static struct platform_device *rsk_devices[] __initdata = { &flash_device, diff --git a/arch/sh/boot/Makefile b/arch/sh/boot/Makefile index a1316872be6f..cb8cf5572e79 100644 --- a/arch/sh/boot/Makefile +++ b/arch/sh/boot/Makefile @@ -20,11 +20,12 @@ CONFIG_BOOT_LINK_OFFSET ?= 0x00800000 CONFIG_ZERO_PAGE_OFFSET ?= 0x00001000 CONFIG_ENTRY_OFFSET ?= 0x00001000 +suffix-y := bin suffix-$(CONFIG_KERNEL_GZIP) := gz suffix-$(CONFIG_KERNEL_BZIP2) := bz2 suffix-$(CONFIG_KERNEL_LZMA) := lzma -targets := zImage vmlinux.srec romImage uImage uImage.srec uImage.gz uImage.bz2 uImage.lzma +targets := zImage vmlinux.srec romImage uImage uImage.srec uImage.gz uImage.bz2 uImage.lzma uImage.bin extra-y += vmlinux.bin vmlinux.bin.gz vmlinux.bin.bz2 vmlinux.bin.lzma subdir- := compressed romimage @@ -88,6 +89,9 @@ $(obj)/uImage.gz: $(obj)/vmlinux.bin.gz $(obj)/uImage.lzma: $(obj)/vmlinux.bin.lzma $(call if_changed,uimage,lzma) +$(obj)/uImage.bin: $(obj)/vmlinux.bin + $(call if_changed,uimage,none) + OBJCOPYFLAGS_vmlinux.srec := -I binary -O srec $(obj)/vmlinux.srec: $(obj)/compressed/vmlinux $(call if_changed,objcopy) diff --git a/arch/sh/include/asm/rwsem.h b/arch/sh/include/asm/rwsem.h index 1987f3ea7f1b..06e2251a5e48 100644 --- a/arch/sh/include/asm/rwsem.h +++ b/arch/sh/include/asm/rwsem.h @@ -41,7 +41,7 @@ struct rw_semaphore { #endif #define __RWSEM_INITIALIZER(name) \ - { RWSEM_UNLOCKED_VALUE, SPIN_LOCK_UNLOCKED, \ + { RWSEM_UNLOCKED_VALUE, __SPIN_LOCK_UNLOCKED((name).wait_lock), \ LIST_HEAD_INIT((name).wait_list) \ __RWSEM_DEP_MAP_INIT(name) } diff --git a/arch/sh/kernel/cpu/irq/imask.c b/arch/sh/kernel/cpu/irq/imask.c index 6b5d191eec3a..a351ed84eec5 100644 --- a/arch/sh/kernel/cpu/irq/imask.c +++ b/arch/sh/kernel/cpu/irq/imask.c @@ -68,7 +68,7 @@ static void unmask_imask_irq(unsigned int irq) } static struct irq_chip imask_irq_chip = { - .typename = "SR.IMASK", + .name = "SR.IMASK", .mask = mask_imask_irq, .unmask = unmask_imask_irq, .mask_ack = mask_imask_irq, diff --git a/arch/sh/kernel/cpu/irq/intc-sh5.c b/arch/sh/kernel/cpu/irq/intc-sh5.c index 6c092f1f5557..06e7e2959b54 100644 --- a/arch/sh/kernel/cpu/irq/intc-sh5.c +++ b/arch/sh/kernel/cpu/irq/intc-sh5.c @@ -85,7 +85,7 @@ static void mask_and_ack_intc(unsigned int); static void end_intc_irq(unsigned int irq); static struct irq_chip intc_irq_type = { - .typename = "INTC", + .name = "INTC", .startup = startup_intc_irq, .shutdown = shutdown_intc_irq, .enable = enable_intc_irq, diff --git a/arch/sh/kernel/cpu/sh3/entry.S b/arch/sh/kernel/cpu/sh3/entry.S index 0151933e5253..bb407ef0b91e 100644 --- a/arch/sh/kernel/cpu/sh3/entry.S +++ b/arch/sh/kernel/cpu/sh3/entry.S @@ -152,8 +152,6 @@ call_do_page_fault: mov.l 1f, r0 mov.l @r0, r6 - sti - mov.l 3f, r0 mov.l 4f, r1 mov r15, r4 diff --git a/arch/sh/kernel/dwarf.c b/arch/sh/kernel/dwarf.c index 03b3616c80a5..d76a23170dbb 100644 --- a/arch/sh/kernel/dwarf.c +++ b/arch/sh/kernel/dwarf.c @@ -20,6 +20,7 @@ #include <linux/list.h> #include <linux/mempool.h> #include <linux/mm.h> +#include <linux/ftrace.h> #include <asm/dwarf.h> #include <asm/unwinder.h> #include <asm/sections.h> @@ -554,9 +555,30 @@ struct dwarf_frame * dwarf_unwind_stack(unsigned long pc, * NOTE: the return address is guaranteed to be setup by the * time this function makes its first function call. */ - if (!pc && !prev) + if (!pc || !prev) pc = (unsigned long)current_text_addr(); +#ifdef CONFIG_FUNCTION_GRAPH_TRACER + /* + * If our stack has been patched by the function graph tracer + * then we might see the address of return_to_handler() where we + * expected to find the real return address. + */ + if (pc == (unsigned long)&return_to_handler) { + int index = current->curr_ret_stack; + + /* + * We currently have no way of tracking how many + * return_to_handler()'s we've seen. If there is more + * than one patched return address on our stack, + * complain loudly. + */ + WARN_ON(index > 0); + + pc = current->ret_stack[index].ret; + } +#endif + frame = mempool_alloc(dwarf_frame_pool, GFP_ATOMIC); if (!frame) { printk(KERN_ERR "Unable to allocate a dwarf frame\n"); diff --git a/arch/sh/kernel/entry-common.S b/arch/sh/kernel/entry-common.S index 68d9223b145e..3eb84931d2aa 100644 --- a/arch/sh/kernel/entry-common.S +++ b/arch/sh/kernel/entry-common.S @@ -121,7 +121,7 @@ noresched: ENTRY(resume_userspace) ! r8: current_thread_info cli - TRACE_IRQS_OfF + TRACE_IRQS_OFF mov.l @(TI_FLAGS,r8), r0 ! current_thread_info->flags tst #(_TIF_WORK_MASK & 0xff), r0 bt/s __restore_all diff --git a/arch/sh/kernel/ftrace.c b/arch/sh/kernel/ftrace.c index a3dcc6d5d253..2c48e267256e 100644 --- a/arch/sh/kernel/ftrace.c +++ b/arch/sh/kernel/ftrace.c @@ -291,31 +291,48 @@ struct syscall_metadata *syscall_nr_to_meta(int nr) return syscalls_metadata[nr]; } -void arch_init_ftrace_syscalls(void) +int syscall_name_to_nr(char *name) +{ + int i; + + if (!syscalls_metadata) + return -1; + for (i = 0; i < NR_syscalls; i++) + if (syscalls_metadata[i]) + if (!strcmp(syscalls_metadata[i]->name, name)) + return i; + return -1; +} + +void set_syscall_enter_id(int num, int id) +{ + syscalls_metadata[num]->enter_id = id; +} + +void set_syscall_exit_id(int num, int id) +{ + syscalls_metadata[num]->exit_id = id; +} + +static int __init arch_init_ftrace_syscalls(void) { int i; struct syscall_metadata *meta; unsigned long **psys_syscall_table = &sys_call_table; - static atomic_t refs; - - if (atomic_inc_return(&refs) != 1) - goto end; syscalls_metadata = kzalloc(sizeof(*syscalls_metadata) * FTRACE_SYSCALL_MAX, GFP_KERNEL); if (!syscalls_metadata) { WARN_ON(1); - return; + return -ENOMEM; } for (i = 0; i < FTRACE_SYSCALL_MAX; i++) { meta = find_syscall_meta(psys_syscall_table[i]); syscalls_metadata[i] = meta; } - return; - /* Paranoid: avoid overflow */ -end: - atomic_dec(&refs); + return 0; } +arch_initcall(arch_init_ftrace_syscalls); #endif /* CONFIG_FTRACE_SYSCALLS */ diff --git a/arch/sh/kernel/io_generic.c b/arch/sh/kernel/io_generic.c index 4ff507239286..b8fa6524760a 100644 --- a/arch/sh/kernel/io_generic.c +++ b/arch/sh/kernel/io_generic.c @@ -147,6 +147,9 @@ void generic_outsl(unsigned long port, const void *src, unsigned long count) void __iomem *generic_ioport_map(unsigned long addr, unsigned int size) { + if (PXSEG(addr) >= P1SEG) + return (void __iomem *)addr; + return (void __iomem *)(addr + generic_io_base); } diff --git a/arch/sh/kernel/irq.c b/arch/sh/kernel/irq.c index 7cb933ba4957..eac7da772fc2 100644 --- a/arch/sh/kernel/irq.c +++ b/arch/sh/kernel/irq.c @@ -11,6 +11,7 @@ #include <linux/module.h> #include <linux/kernel_stat.h> #include <linux/seq_file.h> +#include <linux/ftrace.h> #include <asm/processor.h> #include <asm/machvec.h> #include <asm/uaccess.h> @@ -106,7 +107,7 @@ static union irq_ctx *hardirq_ctx[NR_CPUS] __read_mostly; static union irq_ctx *softirq_ctx[NR_CPUS] __read_mostly; #endif -asmlinkage int do_IRQ(unsigned int irq, struct pt_regs *regs) +asmlinkage __irq_entry int do_IRQ(unsigned int irq, struct pt_regs *regs) { struct pt_regs *old_regs = set_irq_regs(regs); #ifdef CONFIG_IRQSTACKS diff --git a/arch/sh/kernel/machvec.c b/arch/sh/kernel/machvec.c index 548f6607fd0f..cbce639b108a 100644 --- a/arch/sh/kernel/machvec.c +++ b/arch/sh/kernel/machvec.c @@ -14,6 +14,7 @@ #include <linux/string.h> #include <asm/machvec.h> #include <asm/sections.h> +#include <asm/addrspace.h> #include <asm/setup.h> #include <asm/io.h> #include <asm/irq.h> @@ -133,4 +134,6 @@ void __init sh_mv_setup(void) if (!sh_mv.mv_nr_irqs) sh_mv.mv_nr_irqs = NR_IRQS; + + __set_io_port_base(P2SEG); } diff --git a/arch/sh/kernel/setup.c b/arch/sh/kernel/setup.c index f9d44f8e0df6..99b4fb553bf1 100644 --- a/arch/sh/kernel/setup.c +++ b/arch/sh/kernel/setup.c @@ -549,6 +549,8 @@ static int show_cpuinfo(struct seq_file *m, void *v) if (cpu == 0) seq_printf(m, "machine\t\t: %s\n", get_system_type()); + else + seq_printf(m, "\n"); seq_printf(m, "processor\t: %d\n", cpu); seq_printf(m, "cpu family\t: %s\n", init_utsname()->machine); diff --git a/arch/sh/kernel/sh_ksyms_32.c b/arch/sh/kernel/sh_ksyms_32.c index 8dbe26b17c44..444cce3ae921 100644 --- a/arch/sh/kernel/sh_ksyms_32.c +++ b/arch/sh/kernel/sh_ksyms_32.c @@ -84,6 +84,21 @@ DECLARE_EXPORT(__movstrSI60); DECLARE_EXPORT(__movstr_i4_even); DECLARE_EXPORT(__movstr_i4_odd); DECLARE_EXPORT(__movstrSI12_i4); +DECLARE_EXPORT(__movmem); +DECLARE_EXPORT(__movmemSI8); +DECLARE_EXPORT(__movmemSI12); +DECLARE_EXPORT(__movmemSI16); +DECLARE_EXPORT(__movmemSI20); +DECLARE_EXPORT(__movmemSI24); +DECLARE_EXPORT(__movmemSI28); +DECLARE_EXPORT(__movmemSI32); +DECLARE_EXPORT(__movmemSI36); +DECLARE_EXPORT(__movmemSI40); +DECLARE_EXPORT(__movmemSI44); +DECLARE_EXPORT(__movmemSI48); +DECLARE_EXPORT(__movmemSI52); +DECLARE_EXPORT(__movmemSI56); +DECLARE_EXPORT(__movmemSI60); DECLARE_EXPORT(__movmem_i4_even); DECLARE_EXPORT(__movmem_i4_odd); DECLARE_EXPORT(__movmemSI12_i4); diff --git a/arch/sh/kernel/signal_32.c b/arch/sh/kernel/signal_32.c index 6729703547a1..3db37425210d 100644 --- a/arch/sh/kernel/signal_32.c +++ b/arch/sh/kernel/signal_32.c @@ -145,7 +145,7 @@ static inline int restore_sigcontext_fpu(struct sigcontext __user *sc) { struct task_struct *tsk = current; - if (!(current_cpu_data.flags & CPU_HAS_FPU)) + if (!(boot_cpu_data.flags & CPU_HAS_FPU)) return 0; set_used_math(); @@ -158,7 +158,7 @@ static inline int save_sigcontext_fpu(struct sigcontext __user *sc, { struct task_struct *tsk = current; - if (!(current_cpu_data.flags & CPU_HAS_FPU)) + if (!(boot_cpu_data.flags & CPU_HAS_FPU)) return 0; if (!used_math()) { @@ -199,7 +199,7 @@ restore_sigcontext(struct pt_regs *regs, struct sigcontext __user *sc, int *r0_p #undef COPY #ifdef CONFIG_SH_FPU - if (current_cpu_data.flags & CPU_HAS_FPU) { + if (boot_cpu_data.flags & CPU_HAS_FPU) { int owned_fp; struct task_struct *tsk = current; @@ -472,6 +472,7 @@ static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, err |= __put_user(OR_R0_R0, &frame->retcode[6]); err |= __put_user((__NR_rt_sigreturn), &frame->retcode[7]); regs->pr = (unsigned long) frame->retcode; + flush_icache_range(regs->pr, regs->pr + sizeof(frame->retcode)); } if (err) @@ -497,8 +498,6 @@ static int setup_rt_frame(int sig, struct k_sigaction *ka, siginfo_t *info, pr_debug("SIG deliver (%s:%d): sp=%p pc=%08lx pr=%08lx\n", current->comm, task_pid_nr(current), frame, regs->pc, regs->pr); - flush_icache_range(regs->pr, regs->pr + sizeof(frame->retcode)); - return 0; give_sigsegv: diff --git a/arch/sh/kernel/smp.c b/arch/sh/kernel/smp.c index 442d8d47a41e..160db1003cfb 100644 --- a/arch/sh/kernel/smp.c +++ b/arch/sh/kernel/smp.c @@ -35,6 +35,8 @@ static inline void __init smp_store_cpu_info(unsigned int cpu) { struct sh_cpuinfo *c = cpu_data + cpu; + memcpy(c, &boot_cpu_data, sizeof(struct sh_cpuinfo)); + c->loops_per_jiffy = loops_per_jiffy; } diff --git a/arch/sh/kernel/traps_32.c b/arch/sh/kernel/traps_32.c index 69bb1652eccd..7a2ee3a6b8e7 100644 --- a/arch/sh/kernel/traps_32.c +++ b/arch/sh/kernel/traps_32.c @@ -25,6 +25,7 @@ #include <linux/kexec.h> #include <linux/limits.h> #include <linux/proc_fs.h> +#include <linux/sysfs.h> #include <asm/system.h> #include <asm/uaccess.h> #include <asm/fpu.h> @@ -54,8 +55,8 @@ static unsigned long se_multi; /* bitfield: 1: warn 2: fixup 4: signal -> combinations 2|4 && 1|2|4 are not valid! */ static int se_usermode = 3; -/* 0: no warning 1: print a warning message */ -static int se_kernmode_warn = 1; +/* 0: no warning 1: print a warning message, disabled by default */ +static int se_kernmode_warn; #ifdef CONFIG_PROC_FS static const char *se_usermode_action[] = { @@ -159,12 +160,12 @@ void die(const char * str, struct pt_regs * regs, long err) oops_enter(); - console_verbose(); spin_lock_irq(&die_lock); + console_verbose(); bust_spinlocks(1); printk("%s: %04lx [#%d]\n", str, err & 0xffff, ++die_counter); - + sysfs_printk_last_file(); print_modules(); show_regs(regs); @@ -180,6 +181,7 @@ void die(const char * str, struct pt_regs * regs, long err) bust_spinlocks(0); add_taint(TAINT_DIE); spin_unlock_irq(&die_lock); + oops_exit(); if (kexec_should_crash(current)) crash_kexec(regs); @@ -190,7 +192,6 @@ void die(const char * str, struct pt_regs * regs, long err) if (panic_on_oops) panic("Fatal exception"); - oops_exit(); do_exit(SIGSEGV); } diff --git a/arch/sh/mm/Kconfig b/arch/sh/mm/Kconfig index 64dc1ad59801..7f7b52f9beba 100644 --- a/arch/sh/mm/Kconfig +++ b/arch/sh/mm/Kconfig @@ -227,7 +227,7 @@ endchoice choice prompt "HugeTLB page size" - depends on HUGETLB_PAGE && (CPU_SH4 || CPU_SH5) && MMU + depends on HUGETLB_PAGE default HUGETLB_PAGE_SIZE_1MB if PAGE_SIZE_64KB default HUGETLB_PAGE_SIZE_64K diff --git a/arch/sh/mm/cache-sh4.c b/arch/sh/mm/cache-sh4.c index b2453bbef4cd..b7f235c74d66 100644 --- a/arch/sh/mm/cache-sh4.c +++ b/arch/sh/mm/cache-sh4.c @@ -26,7 +26,7 @@ #define MAX_DCACHE_PAGES 64 /* XXX: Tune for ways */ #define MAX_ICACHE_PAGES 32 -static void __flush_cache_4096(unsigned long addr, unsigned long phys, +static void __flush_cache_one(unsigned long addr, unsigned long phys, unsigned long exec_offset); /* @@ -43,7 +43,7 @@ static void (*__flush_dcache_segment_fn)(unsigned long, unsigned long) = * Called from kernel/module.c:sys_init_module and routine for a.out format, * signal handler code and kprobes code */ -static void sh4_flush_icache_range(void *args) +static void __uses_jump_to_uncached sh4_flush_icache_range(void *args) { struct flusher_data *data = args; unsigned long start, end; @@ -72,6 +72,7 @@ static void sh4_flush_icache_range(void *args) for (v = start; v < end; v += L1_CACHE_BYTES) { unsigned long icacheaddr; + int j, n; __ocbwb(v); @@ -79,8 +80,10 @@ static void sh4_flush_icache_range(void *args) cpu_data->icache.entry_mask); /* Clear i-cache line valid-bit */ + n = boot_cpu_data.icache.n_aliases; for (i = 0; i < cpu_data->icache.ways; i++) { - __raw_writel(0, icacheaddr); + for (j = 0; j < n; j++) + __raw_writel(0, icacheaddr + (j * PAGE_SIZE)); icacheaddr += cpu_data->icache.way_incr; } } @@ -89,8 +92,7 @@ static void sh4_flush_icache_range(void *args) local_irq_restore(flags); } -static inline void flush_cache_4096(unsigned long start, - unsigned long phys) +static inline void flush_cache_one(unsigned long start, unsigned long phys) { unsigned long flags, exec_offset = 0; @@ -103,8 +105,7 @@ static inline void flush_cache_4096(unsigned long start, exec_offset = 0x20000000; local_irq_save(flags); - __flush_cache_4096(start | SH_CACHE_ASSOC, - P1SEGADDR(phys), exec_offset); + __flush_cache_one(start | SH_CACHE_ASSOC, P1SEGADDR(phys), exec_offset); local_irq_restore(flags); } @@ -129,8 +130,8 @@ static void sh4_flush_dcache_page(void *arg) /* Loop all the D-cache */ n = boot_cpu_data.dcache.n_aliases; - for (i = 0; i < n; i++, addr += 4096) - flush_cache_4096(addr, phys); + for (i = 0; i < n; i++, addr += PAGE_SIZE) + flush_cache_one(addr, phys); } wmb(); @@ -318,11 +319,11 @@ static void sh4_flush_cache_page(void *args) /* We only need to flush D-cache when we have alias */ if ((address^phys) & alias_mask) { /* Loop 4K of the D-cache */ - flush_cache_4096( + flush_cache_one( CACHE_OC_ADDRESS_ARRAY | (address & alias_mask), phys); /* Loop another 4K of the D-cache */ - flush_cache_4096( + flush_cache_one( CACHE_OC_ADDRESS_ARRAY | (phys & alias_mask), phys); } @@ -337,7 +338,7 @@ static void sh4_flush_cache_page(void *args) * kernel has never executed the code through its identity * translation. */ - flush_cache_4096( + flush_cache_one( CACHE_IC_ADDRESS_ARRAY | (address & alias_mask), phys); } @@ -393,7 +394,7 @@ static void sh4_flush_cache_range(void *args) } /** - * __flush_cache_4096 + * __flush_cache_one * * @addr: address in memory mapped cache array * @phys: P1 address to flush (has to match tags if addr has 'A' bit @@ -406,7 +407,7 @@ static void sh4_flush_cache_range(void *args) * operation (purge/write-back) is selected by the lower 2 bits of * 'phys'. */ -static void __flush_cache_4096(unsigned long addr, unsigned long phys, +static void __flush_cache_one(unsigned long addr, unsigned long phys, unsigned long exec_offset) { int way_count; diff --git a/arch/sh/mm/cache-sh7705.c b/arch/sh/mm/cache-sh7705.c index 2cadee2037ac..2601935eb589 100644 --- a/arch/sh/mm/cache-sh7705.c +++ b/arch/sh/mm/cache-sh7705.c @@ -78,7 +78,7 @@ static void sh7705_flush_icache_range(void *args) /* * Writeback&Invalidate the D-cache of the page */ -static void __flush_dcache_page(unsigned long phys) +static void __uses_jump_to_uncached __flush_dcache_page(unsigned long phys) { unsigned long ways, waysize, addrstart; unsigned long flags; @@ -144,7 +144,7 @@ static void sh7705_flush_dcache_page(void *arg) __flush_dcache_page(PHYSADDR(page_address(page))); } -static void sh7705_flush_cache_all(void *args) +static void __uses_jump_to_uncached sh7705_flush_cache_all(void *args) { unsigned long flags; diff --git a/arch/sh/mm/cache.c b/arch/sh/mm/cache.c index 35c37b7f717a..a2dc7f9ecc51 100644 --- a/arch/sh/mm/cache.c +++ b/arch/sh/mm/cache.c @@ -128,7 +128,7 @@ void __update_cache(struct vm_area_struct *vma, return; page = pfn_to_page(pfn); - if (pfn_valid(pfn) && page_mapping(page)) { + if (pfn_valid(pfn)) { int dirty = test_and_clear_bit(PG_dcache_dirty, &page->flags); if (dirty) { unsigned long addr = (unsigned long)page_address(page); @@ -265,6 +265,8 @@ static void __init emit_cache_params(void) void __init cpu_cache_init(void) { + unsigned int cache_disabled = !(__raw_readl(CCR) & CCR_CACHE_ENABLE); + compute_alias(&boot_cpu_data.icache); compute_alias(&boot_cpu_data.dcache); compute_alias(&boot_cpu_data.scache); @@ -273,6 +275,13 @@ void __init cpu_cache_init(void) __flush_purge_region = noop__flush_region; __flush_invalidate_region = noop__flush_region; + /* + * No flushing is necessary in the disabled cache case so we can + * just keep the noop functions in local_flush_..() and __flush_..() + */ + if (unlikely(cache_disabled)) + goto skip; + if (boot_cpu_data.family == CPU_FAMILY_SH2) { extern void __weak sh2_cache_init(void); @@ -312,5 +321,6 @@ void __init cpu_cache_init(void) sh5_cache_init(); } +skip: emit_cache_params(); } diff --git a/arch/sh/mm/ioremap_32.c b/arch/sh/mm/ioremap_32.c index c3250614e3ae..a86eaa9d75a5 100644 --- a/arch/sh/mm/ioremap_32.c +++ b/arch/sh/mm/ioremap_32.c @@ -83,7 +83,7 @@ void __iomem *__ioremap(unsigned long phys_addr, unsigned long size, * * PMB entries are all pre-faulted. */ - if (unlikely(size >= 0x1000000)) { + if (unlikely(phys_addr >= P1SEG)) { unsigned long mapped = pmb_remap(addr, phys_addr, size, flags); if (likely(mapped)) { diff --git a/arch/sh/mm/pmb.c b/arch/sh/mm/pmb.c index b1a714a92b14..aade31102112 100644 --- a/arch/sh/mm/pmb.c +++ b/arch/sh/mm/pmb.c @@ -33,6 +33,8 @@ #define NR_PMB_ENTRIES 16 +static void __pmb_unmap(struct pmb_entry *); + static struct kmem_cache *pmb_cache; static unsigned long pmb_map; @@ -218,9 +220,10 @@ static struct { long pmb_remap(unsigned long vaddr, unsigned long phys, unsigned long size, unsigned long flags) { - struct pmb_entry *pmbp; + struct pmb_entry *pmbp, *pmbe; unsigned long wanted; int pmb_flags, i; + long err; /* Convert typical pgprot value to the PMB equivalent */ if (flags & _PAGE_CACHABLE) { @@ -236,20 +239,22 @@ long pmb_remap(unsigned long vaddr, unsigned long phys, again: for (i = 0; i < ARRAY_SIZE(pmb_sizes); i++) { - struct pmb_entry *pmbe; int ret; if (size < pmb_sizes[i].size) continue; pmbe = pmb_alloc(vaddr, phys, pmb_flags | pmb_sizes[i].flag); - if (IS_ERR(pmbe)) - return PTR_ERR(pmbe); + if (IS_ERR(pmbe)) { + err = PTR_ERR(pmbe); + goto out; + } ret = set_pmb_entry(pmbe); if (ret != 0) { pmb_free(pmbe); - return -EBUSY; + err = -EBUSY; + goto out; } phys += pmb_sizes[i].size; @@ -264,12 +269,25 @@ again: pmbp->link = pmbe; pmbp = pmbe; + + /* + * Instead of trying smaller sizes on every iteration + * (even if we succeed in allocating space), try using + * pmb_sizes[i].size again. + */ + i--; } if (size >= 0x1000000) goto again; return wanted - size; + +out: + if (pmbp) + __pmb_unmap(pmbp); + + return err; } void pmb_unmap(unsigned long addr) @@ -283,12 +301,19 @@ void pmb_unmap(unsigned long addr) if (unlikely(!pmbe)) return; + __pmb_unmap(pmbe); +} + +static void __pmb_unmap(struct pmb_entry *pmbe) +{ WARN_ON(!test_bit(pmbe->entry, &pmb_map)); do { struct pmb_entry *pmblink = pmbe; - clear_pmb_entry(pmbe); + if (pmbe->entry != PMB_NO_ENTRY) + clear_pmb_entry(pmbe); + pmbe = pmblink->link; pmb_free(pmblink); diff --git a/arch/sparc/Kconfig b/arch/sparc/Kconfig index ac45aab741a5..05ef5380a687 100644 --- a/arch/sparc/Kconfig +++ b/arch/sparc/Kconfig @@ -26,6 +26,7 @@ config SPARC select RTC_CLASS select RTC_DRV_M48T59 select HAVE_PERF_EVENTS + select PERF_USE_VMALLOC select HAVE_DMA_ATTRS select HAVE_DMA_API_DEBUG @@ -48,6 +49,7 @@ config SPARC64 select RTC_DRV_SUN4V select RTC_DRV_STARFIRE select HAVE_PERF_EVENTS + select PERF_USE_VMALLOC config ARCH_DEFCONFIG string diff --git a/arch/sparc/boot/btfixupprep.c b/arch/sparc/boot/btfixupprep.c index 52a4208fe4f0..bbf91b9c3d39 100644 --- a/arch/sparc/boot/btfixupprep.c +++ b/arch/sparc/boot/btfixupprep.c @@ -61,14 +61,14 @@ unsigned long lastfoffset = -1; unsigned long lastfrelno; btfixup *lastf; -void fatal(void) __attribute__((noreturn)); -void fatal(void) +static void fatal(void) __attribute__((noreturn)); +static void fatal(void) { fprintf(stderr, "Malformed output from objdump\n%s\n", buffer); exit(1); } -btfixup *find(int type, char *name) +static btfixup *find(int type, char *name) { int i; for (i = 0; i < last; i++) { @@ -88,7 +88,7 @@ btfixup *find(int type, char *name) return array + last - 1; } -void set_mode (char *buffer) +static void set_mode (char *buffer) { for (mode = 0;; mode++) if (buffer[mode] < '0' || buffer[mode] > '9') diff --git a/arch/sparc/boot/piggyback_32.c b/arch/sparc/boot/piggyback_32.c index e8dc9adfcd61..ac944aec7301 100644 --- a/arch/sparc/boot/piggyback_32.c +++ b/arch/sparc/boot/piggyback_32.c @@ -35,17 +35,17 @@ * as PROM looks for a.out image only. */ -unsigned short ld2(char *p) +static unsigned short ld2(char *p) { return (p[0] << 8) | p[1]; } -unsigned int ld4(char *p) +static unsigned int ld4(char *p) { return (p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3]; } -void st4(char *p, unsigned int x) +static void st4(char *p, unsigned int x) { p[0] = x >> 24; p[1] = x >> 16; @@ -53,7 +53,7 @@ void st4(char *p, unsigned int x) p[3] = x; } -void usage(void) +static void usage(void) { /* fs_img.gz is an image of initial ramdisk. */ fprintf(stderr, "Usage: piggyback vmlinux.aout System.map fs_img.gz\n"); @@ -61,7 +61,7 @@ void usage(void) exit(1); } -void die(char *str) +static void die(char *str) { perror (str); exit(1); diff --git a/arch/sparc/boot/piggyback_64.c b/arch/sparc/boot/piggyback_64.c index c63fd1b6bdd4..a26a686cb5aa 100644 --- a/arch/sparc/boot/piggyback_64.c +++ b/arch/sparc/boot/piggyback_64.c @@ -32,7 +32,7 @@ /* Note: run this on an a.out kernel (use elftoaout for it), as PROM looks for a.out image onlly usage: piggyback vmlinux System.map tail, where tail is gzipped fs of the initial ramdisk */ -void die(char *str) +static void die(char *str) { perror (str); exit(1); diff --git a/arch/sparc/include/asm/hardirq_32.h b/arch/sparc/include/asm/hardirq_32.h index 4f63ed8df551..162007643cdc 100644 --- a/arch/sparc/include/asm/hardirq_32.h +++ b/arch/sparc/include/asm/hardirq_32.h @@ -7,17 +7,7 @@ #ifndef __SPARC_HARDIRQ_H #define __SPARC_HARDIRQ_H -#include <linux/threads.h> -#include <linux/spinlock.h> -#include <linux/cache.h> - -/* entry.S is sensitive to the offsets of these fields */ /* XXX P3 Is it? */ -typedef struct { - unsigned int __softirq_pending; -} ____cacheline_aligned irq_cpustat_t; - -#include <linux/irq_cpustat.h> /* Standard mappings for irq_cpustat_t above */ - #define HARDIRQ_BITS 8 +#include <asm-generic/hardirq.h> #endif /* __SPARC_HARDIRQ_H */ diff --git a/arch/sparc/include/asm/irq_32.h b/arch/sparc/include/asm/irq_32.h index ea43057d4763..cbf4801deaaf 100644 --- a/arch/sparc/include/asm/irq_32.h +++ b/arch/sparc/include/asm/irq_32.h @@ -6,10 +6,10 @@ #ifndef _SPARC_IRQ_H #define _SPARC_IRQ_H -#include <linux/interrupt.h> - #define NR_IRQS 16 +#include <linux/interrupt.h> + #define irq_canonicalize(irq) (irq) extern void __init init_IRQ(void); diff --git a/arch/sparc/include/asm/pgtable_64.h b/arch/sparc/include/asm/pgtable_64.h index 0ff92fa22064..f3cb790fa2ae 100644 --- a/arch/sparc/include/asm/pgtable_64.h +++ b/arch/sparc/include/asm/pgtable_64.h @@ -41,8 +41,8 @@ #define LOW_OBP_ADDRESS _AC(0x00000000f0000000,UL) #define HI_OBP_ADDRESS _AC(0x0000000100000000,UL) #define VMALLOC_START _AC(0x0000000100000000,UL) -#define VMALLOC_END _AC(0x0000000200000000,UL) -#define VMEMMAP_BASE _AC(0x0000000200000000,UL) +#define VMALLOC_END _AC(0x0000010000000000,UL) +#define VMEMMAP_BASE _AC(0x0000010000000000,UL) #define vmemmap ((struct page *)VMEMMAP_BASE) diff --git a/arch/sparc/include/asm/system_64.h b/arch/sparc/include/asm/system_64.h index 25e848f0cad7..d47a98e66972 100644 --- a/arch/sparc/include/asm/system_64.h +++ b/arch/sparc/include/asm/system_64.h @@ -63,6 +63,10 @@ do { __asm__ __volatile__("ba,pt %%xcc, 1f\n\t" \ : : : "memory"); \ } while (0) +/* The kernel always executes in TSO memory model these days, + * and furthermore most sparc64 chips implement more stringent + * memory ordering than required by the specifications. + */ #define mb() membar_safe("#StoreLoad") #define rmb() __asm__ __volatile__("":::"memory") #define wmb() __asm__ __volatile__("":::"memory") diff --git a/arch/sparc/kernel/ktlb.S b/arch/sparc/kernel/ktlb.S index 3ea6e8cde8c5..1d361477d7d6 100644 --- a/arch/sparc/kernel/ktlb.S +++ b/arch/sparc/kernel/ktlb.S @@ -280,8 +280,8 @@ kvmap_dtlb_nonlinear: #ifdef CONFIG_SPARSEMEM_VMEMMAP /* Do not use the TSB for vmemmap. */ - mov (VMEMMAP_BASE >> 24), %g5 - sllx %g5, 24, %g5 + mov (VMEMMAP_BASE >> 40), %g5 + sllx %g5, 40, %g5 cmp %g4,%g5 bgeu,pn %xcc, kvmap_vmemmap nop @@ -293,8 +293,8 @@ kvmap_dtlb_tsbmiss: sethi %hi(MODULES_VADDR), %g5 cmp %g4, %g5 blu,pn %xcc, kvmap_dtlb_longpath - mov (VMALLOC_END >> 24), %g5 - sllx %g5, 24, %g5 + mov (VMALLOC_END >> 40), %g5 + sllx %g5, 40, %g5 cmp %g4, %g5 bgeu,pn %xcc, kvmap_dtlb_longpath nop diff --git a/arch/sparc/kernel/ldc.c b/arch/sparc/kernel/ldc.c index adf5f273868a..cb3c72c45aab 100644 --- a/arch/sparc/kernel/ldc.c +++ b/arch/sparc/kernel/ldc.c @@ -1242,13 +1242,13 @@ int ldc_bind(struct ldc_channel *lp, const char *name) snprintf(lp->tx_irq_name, LDC_IRQ_NAME_MAX, "%s TX", name); err = request_irq(lp->cfg.rx_irq, ldc_rx, - IRQF_SAMPLE_RANDOM | IRQF_SHARED, + IRQF_SAMPLE_RANDOM | IRQF_DISABLED | IRQF_SHARED, lp->rx_irq_name, lp); if (err) return err; err = request_irq(lp->cfg.tx_irq, ldc_tx, - IRQF_SAMPLE_RANDOM | IRQF_SHARED, + IRQF_SAMPLE_RANDOM | IRQF_DISABLED | IRQF_SHARED, lp->tx_irq_name, lp); if (err) { free_irq(lp->cfg.rx_irq, lp); diff --git a/arch/sparc/kernel/perf_event.c b/arch/sparc/kernel/perf_event.c index 2d6a1b10c81d..fa5936e1c3b9 100644 --- a/arch/sparc/kernel/perf_event.c +++ b/arch/sparc/kernel/perf_event.c @@ -56,7 +56,8 @@ struct cpu_hw_events { struct perf_event *events[MAX_HWEVENTS]; unsigned long used_mask[BITS_TO_LONGS(MAX_HWEVENTS)]; unsigned long active_mask[BITS_TO_LONGS(MAX_HWEVENTS)]; - int enabled; + u64 pcr; + int enabled; }; DEFINE_PER_CPU(struct cpu_hw_events, cpu_hw_events) = { .enabled = 1, }; @@ -68,8 +69,30 @@ struct perf_event_map { #define PIC_LOWER 0x02 }; +static unsigned long perf_event_encode(const struct perf_event_map *pmap) +{ + return ((unsigned long) pmap->encoding << 16) | pmap->pic_mask; +} + +static void perf_event_decode(unsigned long val, u16 *enc, u8 *msk) +{ + *msk = val & 0xff; + *enc = val >> 16; +} + +#define C(x) PERF_COUNT_HW_CACHE_##x + +#define CACHE_OP_UNSUPPORTED 0xfffe +#define CACHE_OP_NONSENSE 0xffff + +typedef struct perf_event_map cache_map_t + [PERF_COUNT_HW_CACHE_MAX] + [PERF_COUNT_HW_CACHE_OP_MAX] + [PERF_COUNT_HW_CACHE_RESULT_MAX]; + struct sparc_pmu { const struct perf_event_map *(*event_map)(int); + const cache_map_t *cache_map; int max_events; int upper_shift; int lower_shift; @@ -80,21 +103,109 @@ struct sparc_pmu { int lower_nop; }; -static const struct perf_event_map ultra3i_perfmon_event_map[] = { +static const struct perf_event_map ultra3_perfmon_event_map[] = { [PERF_COUNT_HW_CPU_CYCLES] = { 0x0000, PIC_UPPER | PIC_LOWER }, [PERF_COUNT_HW_INSTRUCTIONS] = { 0x0001, PIC_UPPER | PIC_LOWER }, [PERF_COUNT_HW_CACHE_REFERENCES] = { 0x0009, PIC_LOWER }, [PERF_COUNT_HW_CACHE_MISSES] = { 0x0009, PIC_UPPER }, }; -static const struct perf_event_map *ultra3i_event_map(int event_id) +static const struct perf_event_map *ultra3_event_map(int event_id) { - return &ultra3i_perfmon_event_map[event_id]; + return &ultra3_perfmon_event_map[event_id]; } -static const struct sparc_pmu ultra3i_pmu = { - .event_map = ultra3i_event_map, - .max_events = ARRAY_SIZE(ultra3i_perfmon_event_map), +static const cache_map_t ultra3_cache_map = { +[C(L1D)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { 0x09, PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x09, PIC_UPPER, }, + }, + [C(OP_WRITE)] = { + [C(RESULT_ACCESS)] = { 0x0a, PIC_LOWER }, + [C(RESULT_MISS)] = { 0x0a, PIC_UPPER }, + }, + [C(OP_PREFETCH)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(L1I)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { 0x09, PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x09, PIC_UPPER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_NONSENSE }, + [ C(RESULT_MISS) ] = { CACHE_OP_NONSENSE }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(LL)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { 0x0c, PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x0c, PIC_UPPER, }, + }, + [C(OP_WRITE)] = { + [C(RESULT_ACCESS)] = { 0x0c, PIC_LOWER }, + [C(RESULT_MISS)] = { 0x0c, PIC_UPPER }, + }, + [C(OP_PREFETCH)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(DTLB)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x12, PIC_UPPER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(ITLB)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x11, PIC_UPPER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(BPU)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +}; + +static const struct sparc_pmu ultra3_pmu = { + .event_map = ultra3_event_map, + .cache_map = &ultra3_cache_map, + .max_events = ARRAY_SIZE(ultra3_perfmon_event_map), .upper_shift = 11, .lower_shift = 4, .event_mask = 0x3f, @@ -102,6 +213,121 @@ static const struct sparc_pmu ultra3i_pmu = { .lower_nop = 0x14, }; +/* Niagara1 is very limited. The upper PIC is hard-locked to count + * only instructions, so it is free running which creates all kinds of + * problems. Some hardware designs make one wonder if the creator + * even looked at how this stuff gets used by software. + */ +static const struct perf_event_map niagara1_perfmon_event_map[] = { + [PERF_COUNT_HW_CPU_CYCLES] = { 0x00, PIC_UPPER }, + [PERF_COUNT_HW_INSTRUCTIONS] = { 0x00, PIC_UPPER }, + [PERF_COUNT_HW_CACHE_REFERENCES] = { 0, PIC_NONE }, + [PERF_COUNT_HW_CACHE_MISSES] = { 0x03, PIC_LOWER }, +}; + +static const struct perf_event_map *niagara1_event_map(int event_id) +{ + return &niagara1_perfmon_event_map[event_id]; +} + +static const cache_map_t niagara1_cache_map = { +[C(L1D)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x03, PIC_LOWER, }, + }, + [C(OP_WRITE)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x03, PIC_LOWER, }, + }, + [C(OP_PREFETCH)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(L1I)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { 0x00, PIC_UPPER }, + [C(RESULT_MISS)] = { 0x02, PIC_LOWER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_NONSENSE }, + [ C(RESULT_MISS) ] = { CACHE_OP_NONSENSE }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(LL)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x07, PIC_LOWER, }, + }, + [C(OP_WRITE)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x07, PIC_LOWER, }, + }, + [C(OP_PREFETCH)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(DTLB)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x05, PIC_LOWER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(ITLB)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x04, PIC_LOWER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(BPU)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +}; + +static const struct sparc_pmu niagara1_pmu = { + .event_map = niagara1_event_map, + .cache_map = &niagara1_cache_map, + .max_events = ARRAY_SIZE(niagara1_perfmon_event_map), + .upper_shift = 0, + .lower_shift = 4, + .event_mask = 0x7, + .upper_nop = 0x0, + .lower_nop = 0x0, +}; + static const struct perf_event_map niagara2_perfmon_event_map[] = { [PERF_COUNT_HW_CPU_CYCLES] = { 0x02ff, PIC_UPPER | PIC_LOWER }, [PERF_COUNT_HW_INSTRUCTIONS] = { 0x02ff, PIC_UPPER | PIC_LOWER }, @@ -116,14 +342,102 @@ static const struct perf_event_map *niagara2_event_map(int event_id) return &niagara2_perfmon_event_map[event_id]; } +static const cache_map_t niagara2_cache_map = { +[C(L1D)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { 0x0208, PIC_UPPER | PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x0302, PIC_UPPER | PIC_LOWER, }, + }, + [C(OP_WRITE)] = { + [C(RESULT_ACCESS)] = { 0x0210, PIC_UPPER | PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x0302, PIC_UPPER | PIC_LOWER, }, + }, + [C(OP_PREFETCH)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(L1I)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { 0x02ff, PIC_UPPER | PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x0301, PIC_UPPER | PIC_LOWER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_NONSENSE }, + [ C(RESULT_MISS) ] = { CACHE_OP_NONSENSE }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(LL)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { 0x0208, PIC_UPPER | PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x0330, PIC_UPPER | PIC_LOWER, }, + }, + [C(OP_WRITE)] = { + [C(RESULT_ACCESS)] = { 0x0210, PIC_UPPER | PIC_LOWER, }, + [C(RESULT_MISS)] = { 0x0320, PIC_UPPER | PIC_LOWER, }, + }, + [C(OP_PREFETCH)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(DTLB)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0x0b08, PIC_UPPER | PIC_LOWER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(ITLB)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { 0xb04, PIC_UPPER | PIC_LOWER, }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +[C(BPU)] = { + [C(OP_READ)] = { + [C(RESULT_ACCESS)] = { CACHE_OP_UNSUPPORTED }, + [C(RESULT_MISS)] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_WRITE) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, + [ C(OP_PREFETCH) ] = { + [ C(RESULT_ACCESS) ] = { CACHE_OP_UNSUPPORTED }, + [ C(RESULT_MISS) ] = { CACHE_OP_UNSUPPORTED }, + }, +}, +}; + static const struct sparc_pmu niagara2_pmu = { .event_map = niagara2_event_map, + .cache_map = &niagara2_cache_map, .max_events = ARRAY_SIZE(niagara2_perfmon_event_map), .upper_shift = 19, .lower_shift = 6, .event_mask = 0xfff, .hv_bit = 0x8, - .irq_bit = 0x03, + .irq_bit = 0x30, .upper_nop = 0x220, .lower_nop = 0x220, }; @@ -151,23 +465,30 @@ static u64 nop_for_index(int idx) sparc_pmu->lower_nop, idx); } -static inline void sparc_pmu_enable_event(struct hw_perf_event *hwc, - int idx) +static inline void sparc_pmu_enable_event(struct cpu_hw_events *cpuc, struct hw_perf_event *hwc, int idx) { u64 val, mask = mask_for_index(idx); - val = pcr_ops->read(); - pcr_ops->write((val & ~mask) | hwc->config); + val = cpuc->pcr; + val &= ~mask; + val |= hwc->config; + cpuc->pcr = val; + + pcr_ops->write(cpuc->pcr); } -static inline void sparc_pmu_disable_event(struct hw_perf_event *hwc, - int idx) +static inline void sparc_pmu_disable_event(struct cpu_hw_events *cpuc, struct hw_perf_event *hwc, int idx) { u64 mask = mask_for_index(idx); u64 nop = nop_for_index(idx); - u64 val = pcr_ops->read(); + u64 val; - pcr_ops->write((val & ~mask) | nop); + val = cpuc->pcr; + val &= ~mask; + val |= nop; + cpuc->pcr = val; + + pcr_ops->write(cpuc->pcr); } void hw_perf_enable(void) @@ -182,7 +503,7 @@ void hw_perf_enable(void) cpuc->enabled = 1; barrier(); - val = pcr_ops->read(); + val = cpuc->pcr; for (i = 0; i < MAX_HWEVENTS; i++) { struct perf_event *cp = cpuc->events[i]; @@ -194,7 +515,9 @@ void hw_perf_enable(void) val |= hwc->config_base; } - pcr_ops->write(val); + cpuc->pcr = val; + + pcr_ops->write(cpuc->pcr); } void hw_perf_disable(void) @@ -207,10 +530,12 @@ void hw_perf_disable(void) cpuc->enabled = 0; - val = pcr_ops->read(); + val = cpuc->pcr; val &= ~(PCR_UTRACE | PCR_STRACE | sparc_pmu->hv_bit | sparc_pmu->irq_bit); - pcr_ops->write(val); + cpuc->pcr = val; + + pcr_ops->write(cpuc->pcr); } static u32 read_pmc(int idx) @@ -242,7 +567,7 @@ static void write_pmc(int idx, u64 val) } static int sparc_perf_event_set_period(struct perf_event *event, - struct hw_perf_event *hwc, int idx) + struct hw_perf_event *hwc, int idx) { s64 left = atomic64_read(&hwc->period_left); s64 period = hwc->sample_period; @@ -282,19 +607,19 @@ static int sparc_pmu_enable(struct perf_event *event) if (test_and_set_bit(idx, cpuc->used_mask)) return -EAGAIN; - sparc_pmu_disable_event(hwc, idx); + sparc_pmu_disable_event(cpuc, hwc, idx); cpuc->events[idx] = event; set_bit(idx, cpuc->active_mask); sparc_perf_event_set_period(event, hwc, idx); - sparc_pmu_enable_event(hwc, idx); + sparc_pmu_enable_event(cpuc, hwc, idx); perf_event_update_userpage(event); return 0; } static u64 sparc_perf_event_update(struct perf_event *event, - struct hw_perf_event *hwc, int idx) + struct hw_perf_event *hwc, int idx) { int shift = 64 - 32; u64 prev_raw_count, new_raw_count; @@ -324,7 +649,7 @@ static void sparc_pmu_disable(struct perf_event *event) int idx = hwc->idx; clear_bit(idx, cpuc->active_mask); - sparc_pmu_disable_event(hwc, idx); + sparc_pmu_disable_event(cpuc, hwc, idx); barrier(); @@ -338,18 +663,29 @@ static void sparc_pmu_disable(struct perf_event *event) static void sparc_pmu_read(struct perf_event *event) { struct hw_perf_event *hwc = &event->hw; + sparc_perf_event_update(event, hwc, hwc->idx); } static void sparc_pmu_unthrottle(struct perf_event *event) { + struct cpu_hw_events *cpuc = &__get_cpu_var(cpu_hw_events); struct hw_perf_event *hwc = &event->hw; - sparc_pmu_enable_event(hwc, hwc->idx); + + sparc_pmu_enable_event(cpuc, hwc, hwc->idx); } static atomic_t active_events = ATOMIC_INIT(0); static DEFINE_MUTEX(pmc_grab_mutex); +static void perf_stop_nmi_watchdog(void *unused) +{ + struct cpu_hw_events *cpuc = &__get_cpu_var(cpu_hw_events); + + stop_nmi_watchdog(NULL); + cpuc->pcr = pcr_ops->read(); +} + void perf_event_grab_pmc(void) { if (atomic_inc_not_zero(&active_events)) @@ -358,7 +694,7 @@ void perf_event_grab_pmc(void) mutex_lock(&pmc_grab_mutex); if (atomic_read(&active_events) == 0) { if (atomic_read(&nmi_active) > 0) { - on_each_cpu(stop_nmi_watchdog, NULL, 1); + on_each_cpu(perf_stop_nmi_watchdog, NULL, 1); BUG_ON(atomic_read(&nmi_active) != 0); } atomic_inc(&active_events); @@ -375,30 +711,160 @@ void perf_event_release_pmc(void) } } +static const struct perf_event_map *sparc_map_cache_event(u64 config) +{ + unsigned int cache_type, cache_op, cache_result; + const struct perf_event_map *pmap; + + if (!sparc_pmu->cache_map) + return ERR_PTR(-ENOENT); + + cache_type = (config >> 0) & 0xff; + if (cache_type >= PERF_COUNT_HW_CACHE_MAX) + return ERR_PTR(-EINVAL); + + cache_op = (config >> 8) & 0xff; + if (cache_op >= PERF_COUNT_HW_CACHE_OP_MAX) + return ERR_PTR(-EINVAL); + + cache_result = (config >> 16) & 0xff; + if (cache_result >= PERF_COUNT_HW_CACHE_RESULT_MAX) + return ERR_PTR(-EINVAL); + + pmap = &((*sparc_pmu->cache_map)[cache_type][cache_op][cache_result]); + + if (pmap->encoding == CACHE_OP_UNSUPPORTED) + return ERR_PTR(-ENOENT); + + if (pmap->encoding == CACHE_OP_NONSENSE) + return ERR_PTR(-EINVAL); + + return pmap; +} + static void hw_perf_event_destroy(struct perf_event *event) { perf_event_release_pmc(); } +/* Make sure all events can be scheduled into the hardware at + * the same time. This is simplified by the fact that we only + * need to support 2 simultaneous HW events. + */ +static int sparc_check_constraints(unsigned long *events, int n_ev) +{ + if (n_ev <= perf_max_events) { + u8 msk1, msk2; + u16 dummy; + + if (n_ev == 1) + return 0; + BUG_ON(n_ev != 2); + perf_event_decode(events[0], &dummy, &msk1); + perf_event_decode(events[1], &dummy, &msk2); + + /* If both events can go on any counter, OK. */ + if (msk1 == (PIC_UPPER | PIC_LOWER) && + msk2 == (PIC_UPPER | PIC_LOWER)) + return 0; + + /* If one event is limited to a specific counter, + * and the other can go on both, OK. + */ + if ((msk1 == PIC_UPPER || msk1 == PIC_LOWER) && + msk2 == (PIC_UPPER | PIC_LOWER)) + return 0; + if ((msk2 == PIC_UPPER || msk2 == PIC_LOWER) && + msk1 == (PIC_UPPER | PIC_LOWER)) + return 0; + + /* If the events are fixed to different counters, OK. */ + if ((msk1 == PIC_UPPER && msk2 == PIC_LOWER) || + (msk1 == PIC_LOWER && msk2 == PIC_UPPER)) + return 0; + + /* Otherwise, there is a conflict. */ + } + + return -1; +} + +static int check_excludes(struct perf_event **evts, int n_prev, int n_new) +{ + int eu = 0, ek = 0, eh = 0; + struct perf_event *event; + int i, n, first; + + n = n_prev + n_new; + if (n <= 1) + return 0; + + first = 1; + for (i = 0; i < n; i++) { + event = evts[i]; + if (first) { + eu = event->attr.exclude_user; + ek = event->attr.exclude_kernel; + eh = event->attr.exclude_hv; + first = 0; + } else if (event->attr.exclude_user != eu || + event->attr.exclude_kernel != ek || + event->attr.exclude_hv != eh) { + return -EAGAIN; + } + } + + return 0; +} + +static int collect_events(struct perf_event *group, int max_count, + struct perf_event *evts[], unsigned long *events) +{ + struct perf_event *event; + int n = 0; + + if (!is_software_event(group)) { + if (n >= max_count) + return -1; + evts[n] = group; + events[n++] = group->hw.event_base; + } + list_for_each_entry(event, &group->sibling_list, group_entry) { + if (!is_software_event(event) && + event->state != PERF_EVENT_STATE_OFF) { + if (n >= max_count) + return -1; + evts[n] = event; + events[n++] = event->hw.event_base; + } + } + return n; +} + static int __hw_perf_event_init(struct perf_event *event) { struct perf_event_attr *attr = &event->attr; + struct perf_event *evts[MAX_HWEVENTS]; struct hw_perf_event *hwc = &event->hw; + unsigned long events[MAX_HWEVENTS]; const struct perf_event_map *pmap; u64 enc; + int n; if (atomic_read(&nmi_active) < 0) return -ENODEV; - if (attr->type != PERF_TYPE_HARDWARE) + if (attr->type == PERF_TYPE_HARDWARE) { + if (attr->config >= sparc_pmu->max_events) + return -EINVAL; + pmap = sparc_pmu->event_map(attr->config); + } else if (attr->type == PERF_TYPE_HW_CACHE) { + pmap = sparc_map_cache_event(attr->config); + if (IS_ERR(pmap)) + return PTR_ERR(pmap); + } else return -EOPNOTSUPP; - if (attr->config >= sparc_pmu->max_events) - return -EINVAL; - - perf_event_grab_pmc(); - event->destroy = hw_perf_event_destroy; - /* We save the enable bits in the config_base. So to * turn off sampling just write 'config', and to enable * things write 'config | config_base'. @@ -411,15 +877,39 @@ static int __hw_perf_event_init(struct perf_event *event) if (!attr->exclude_hv) hwc->config_base |= sparc_pmu->hv_bit; + hwc->event_base = perf_event_encode(pmap); + + enc = pmap->encoding; + + n = 0; + if (event->group_leader != event) { + n = collect_events(event->group_leader, + perf_max_events - 1, + evts, events); + if (n < 0) + return -EINVAL; + } + events[n] = hwc->event_base; + evts[n] = event; + + if (check_excludes(evts, n, 1)) + return -EINVAL; + + if (sparc_check_constraints(events, n + 1)) + return -EINVAL; + + /* Try to do all error checking before this point, as unwinding + * state after grabbing the PMC is difficult. + */ + perf_event_grab_pmc(); + event->destroy = hw_perf_event_destroy; + if (!hwc->sample_period) { hwc->sample_period = MAX_PERIOD; hwc->last_period = hwc->sample_period; atomic64_set(&hwc->period_left, hwc->sample_period); } - pmap = sparc_pmu->event_map(attr->config); - - enc = pmap->encoding; if (pmap->pic_mask & PIC_UPPER) { hwc->idx = PIC_UPPER_INDEX; enc <<= sparc_pmu->upper_shift; @@ -472,7 +962,7 @@ void perf_event_print_debug(void) } static int __kprobes perf_event_nmi_handler(struct notifier_block *self, - unsigned long cmd, void *__args) + unsigned long cmd, void *__args) { struct die_args *args = __args; struct perf_sample_data data; @@ -513,7 +1003,7 @@ static int __kprobes perf_event_nmi_handler(struct notifier_block *self, continue; if (perf_event_overflow(event, 1, &data, regs)) - sparc_pmu_disable_event(hwc, idx); + sparc_pmu_disable_event(cpuc, hwc, idx); } return NOTIFY_STOP; @@ -525,8 +1015,15 @@ static __read_mostly struct notifier_block perf_event_nmi_notifier = { static bool __init supported_pmu(void) { - if (!strcmp(sparc_pmu_type, "ultra3i")) { - sparc_pmu = &ultra3i_pmu; + if (!strcmp(sparc_pmu_type, "ultra3") || + !strcmp(sparc_pmu_type, "ultra3+") || + !strcmp(sparc_pmu_type, "ultra3i") || + !strcmp(sparc_pmu_type, "ultra4+")) { + sparc_pmu = &ultra3_pmu; + return true; + } + if (!strcmp(sparc_pmu_type, "niagara")) { + sparc_pmu = &niagara1_pmu; return true; } if (!strcmp(sparc_pmu_type, "niagara2")) { diff --git a/arch/sparc/kernel/prom_common.c b/arch/sparc/kernel/prom_common.c index 138910c67206..d80a65d9e893 100644 --- a/arch/sparc/kernel/prom_common.c +++ b/arch/sparc/kernel/prom_common.c @@ -79,6 +79,7 @@ int of_set_property(struct device_node *dp, const char *name, void *val, int len err = -ENODEV; + mutex_lock(&of_set_property_mutex); write_lock(&devtree_lock); prevp = &dp->properties; while (*prevp) { @@ -88,9 +89,7 @@ int of_set_property(struct device_node *dp, const char *name, void *val, int len void *old_val = prop->value; int ret; - mutex_lock(&of_set_property_mutex); ret = prom_setprop(dp->node, name, val, len); - mutex_unlock(&of_set_property_mutex); err = -EINVAL; if (ret >= 0) { @@ -109,6 +108,7 @@ int of_set_property(struct device_node *dp, const char *name, void *val, int len prevp = &(*prevp)->next; } write_unlock(&devtree_lock); + mutex_unlock(&of_set_property_mutex); /* XXX Upate procfs if necessary... */ diff --git a/arch/sparc/kernel/visemul.c b/arch/sparc/kernel/visemul.c index b956fd71c131..d231cbd5c526 100644 --- a/arch/sparc/kernel/visemul.c +++ b/arch/sparc/kernel/visemul.c @@ -617,7 +617,7 @@ static void pmul(struct pt_regs *regs, unsigned int insn, unsigned int opf) rs2 = fps_regval(f, RS2(insn)); rd_val = 0; - src2 = (rs2 >> (opf == FMUL8x16AU_OPF) ? 16 : 0); + src2 = rs2 >> (opf == FMUL8x16AU_OPF ? 16 : 0); for (byte = 0; byte < 4; byte++) { u16 src1 = (rs1 >> (byte * 8)) & 0x00ff; u32 prod = src1 * src2; diff --git a/arch/sparc/mm/init_64.c b/arch/sparc/mm/init_64.c index a70a5e1904d9..1886d37d411b 100644 --- a/arch/sparc/mm/init_64.c +++ b/arch/sparc/mm/init_64.c @@ -265,7 +265,7 @@ static void flush_dcache(unsigned long pfn) struct page *page; page = pfn_to_page(pfn); - if (page && page_mapping(page)) { + if (page) { unsigned long pg_flags; pg_flags = page->flags; diff --git a/arch/sparc/oprofile/init.c b/arch/sparc/oprofile/init.c index f97cb8b6ee5f..f9024bccff16 100644 --- a/arch/sparc/oprofile/init.c +++ b/arch/sparc/oprofile/init.c @@ -11,6 +11,7 @@ #include <linux/oprofile.h> #include <linux/errno.h> #include <linux/init.h> +#include <linux/param.h> /* for HZ */ #ifdef CONFIG_SPARC64 #include <linux/notifier.h> diff --git a/arch/um/drivers/line.c b/arch/um/drivers/line.c index 14a102e877d6..cf8a97f34518 100644 --- a/arch/um/drivers/line.c +++ b/arch/um/drivers/line.c @@ -5,6 +5,7 @@ #include "linux/irqreturn.h" #include "linux/kd.h" +#include "linux/sched.h" #include "chan_kern.h" #include "irq_kern.h" #include "irq_user.h" diff --git a/arch/um/drivers/port_kern.c b/arch/um/drivers/port_kern.c index 19930081d3d8..4ebc8a34738f 100644 --- a/arch/um/drivers/port_kern.c +++ b/arch/um/drivers/port_kern.c @@ -7,6 +7,7 @@ #include "linux/interrupt.h" #include "linux/list.h" #include "linux/mutex.h" +#include "linux/workqueue.h" #include "asm/atomic.h" #include "init.h" #include "irq_kern.h" diff --git a/arch/um/kernel/irq.c b/arch/um/kernel/irq.c index 454cdb43e351..039270b9b73b 100644 --- a/arch/um/kernel/irq.c +++ b/arch/um/kernel/irq.c @@ -10,6 +10,7 @@ #include "linux/interrupt.h" #include "linux/kernel_stat.h" #include "linux/module.h" +#include "linux/sched.h" #include "linux/seq_file.h" #include "as-layout.h" #include "kern_util.h" diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig index 8da93745c087..72ace9515a07 100644 --- a/arch/x86/Kconfig +++ b/arch/x86/Kconfig @@ -86,10 +86,6 @@ config STACKTRACE_SUPPORT config HAVE_LATENCYTOP_SUPPORT def_bool y -config FAST_CMPXCHG_LOCAL - bool - default y - config MMU def_bool y @@ -495,7 +491,7 @@ if PARAVIRT_GUEST source "arch/x86/xen/Kconfig" config VMI - bool "VMI Guest support" + bool "VMI Guest support (DEPRECATED)" select PARAVIRT depends on X86_32 ---help--- @@ -504,6 +500,15 @@ config VMI at the moment), by linking the kernel to a GPL-ed ROM module provided by the hypervisor. + As of September 2009, VMware has started a phased retirement + of this feature from VMware's products. Please see + feature-removal-schedule.txt for details. If you are + planning to enable this option, please note that you cannot + live migrate a VMI enabled VM to a future VMware product, + which doesn't support VMI. So if you expect your kernel to + seamlessly migrate to newer VMware products, keep this + disabled. + config KVM_CLOCK bool "KVM paravirtualized clock" select PARAVIRT @@ -1438,12 +1443,8 @@ config SECCOMP If unsure, say Y. Only embedded should say N here. -config CC_STACKPROTECTOR_ALL - bool - config CC_STACKPROTECTOR bool "Enable -fstack-protector buffer overflow detection (EXPERIMENTAL)" - select CC_STACKPROTECTOR_ALL ---help--- This option turns on the -fstack-protector GCC feature. This feature puts, at the beginning of functions, a canary value on diff --git a/arch/x86/Kconfig.cpu b/arch/x86/Kconfig.cpu index 527519b8a9f9..2649840d888f 100644 --- a/arch/x86/Kconfig.cpu +++ b/arch/x86/Kconfig.cpu @@ -400,7 +400,7 @@ config X86_TSC config X86_CMPXCHG64 def_bool y - depends on X86_PAE || X86_64 + depends on !M386 && !M486 # this should be set for all -march=.. options where the compiler # generates cmov. @@ -412,6 +412,7 @@ config X86_MINIMUM_CPU_FAMILY int default "64" if X86_64 default "6" if X86_32 && X86_P6_NOP + default "5" if X86_32 && X86_CMPXCHG64 default "4" if X86_32 && (X86_XADD || X86_CMPXCHG || X86_BSWAP || X86_WP_WORKS_OK) default "3" diff --git a/arch/x86/Makefile b/arch/x86/Makefile index a012ee8ef803..d2d24c9ee64d 100644 --- a/arch/x86/Makefile +++ b/arch/x86/Makefile @@ -76,7 +76,6 @@ ifdef CONFIG_CC_STACKPROTECTOR cc_has_sp := $(srctree)/scripts/gcc-x86_$(BITS)-has-stack-protector.sh ifeq ($(shell $(CONFIG_SHELL) $(cc_has_sp) $(CC) $(biarch)),y) stackp-y := -fstack-protector - stackp-$(CONFIG_CC_STACKPROTECTOR_ALL) += -fstack-protector-all KBUILD_CFLAGS += $(stackp-y) else $(warning stack protector enabled but no compiler support) diff --git a/arch/x86/boot/setup.ld b/arch/x86/boot/setup.ld index 0f6ec455a2b1..03c0683636b6 100644 --- a/arch/x86/boot/setup.ld +++ b/arch/x86/boot/setup.ld @@ -53,6 +53,9 @@ SECTIONS /DISCARD/ : { *(.note*) } + /* + * The ASSERT() sink to . is intentional, for binutils 2.14 compatibility: + */ . = ASSERT(_end <= 0x8000, "Setup too big!"); . = ASSERT(hdr == 0x1f1, "The setup header has the wrong offset!"); /* Necessary for the very-old-loader check to work... */ diff --git a/arch/x86/crypto/aesni-intel_glue.c b/arch/x86/crypto/aesni-intel_glue.c index 585edebe12cf..49c552c060e9 100644 --- a/arch/x86/crypto/aesni-intel_glue.c +++ b/arch/x86/crypto/aesni-intel_glue.c @@ -82,7 +82,7 @@ static int aes_set_key_common(struct crypto_tfm *tfm, void *raw_ctx, return -EINVAL; } - if (irq_fpu_usable()) + if (!irq_fpu_usable()) err = crypto_aes_expand_key(ctx, in_key, key_len); else { kernel_fpu_begin(); @@ -103,7 +103,7 @@ static void aes_encrypt(struct crypto_tfm *tfm, u8 *dst, const u8 *src) { struct crypto_aes_ctx *ctx = aes_ctx(crypto_tfm_ctx(tfm)); - if (irq_fpu_usable()) + if (!irq_fpu_usable()) crypto_aes_encrypt_x86(ctx, dst, src); else { kernel_fpu_begin(); @@ -116,7 +116,7 @@ static void aes_decrypt(struct crypto_tfm *tfm, u8 *dst, const u8 *src) { struct crypto_aes_ctx *ctx = aes_ctx(crypto_tfm_ctx(tfm)); - if (irq_fpu_usable()) + if (!irq_fpu_usable()) crypto_aes_decrypt_x86(ctx, dst, src); else { kernel_fpu_begin(); @@ -342,7 +342,7 @@ static int ablk_encrypt(struct ablkcipher_request *req) struct crypto_ablkcipher *tfm = crypto_ablkcipher_reqtfm(req); struct async_aes_ctx *ctx = crypto_ablkcipher_ctx(tfm); - if (irq_fpu_usable()) { + if (!irq_fpu_usable()) { struct ablkcipher_request *cryptd_req = ablkcipher_request_ctx(req); memcpy(cryptd_req, req, sizeof(*req)); @@ -363,7 +363,7 @@ static int ablk_decrypt(struct ablkcipher_request *req) struct crypto_ablkcipher *tfm = crypto_ablkcipher_reqtfm(req); struct async_aes_ctx *ctx = crypto_ablkcipher_ctx(tfm); - if (irq_fpu_usable()) { + if (!irq_fpu_usable()) { struct ablkcipher_request *cryptd_req = ablkcipher_request_ctx(req); memcpy(cryptd_req, req, sizeof(*req)); diff --git a/arch/x86/ia32/ia32entry.S b/arch/x86/ia32/ia32entry.S index 11a6c79d5f46..d23b98782653 100644 --- a/arch/x86/ia32/ia32entry.S +++ b/arch/x86/ia32/ia32entry.S @@ -21,8 +21,8 @@ #define __AUDIT_ARCH_LE 0x40000000 #ifndef CONFIG_AUDITSYSCALL -#define sysexit_audit int_ret_from_sys_call -#define sysretl_audit int_ret_from_sys_call +#define sysexit_audit ia32_ret_from_sys_call +#define sysretl_audit ia32_ret_from_sys_call #endif #define IA32_NR_syscalls ((ia32_syscall_end - ia32_sys_call_table)/8) @@ -39,12 +39,12 @@ .endm /* clobbers %eax */ - .macro CLEAR_RREGS _r9=rax + .macro CLEAR_RREGS offset=0, _r9=rax xorl %eax,%eax - movq %rax,R11(%rsp) - movq %rax,R10(%rsp) - movq %\_r9,R9(%rsp) - movq %rax,R8(%rsp) + movq %rax,\offset+R11(%rsp) + movq %rax,\offset+R10(%rsp) + movq %\_r9,\offset+R9(%rsp) + movq %rax,\offset+R8(%rsp) .endm /* @@ -172,6 +172,10 @@ sysexit_from_sys_call: movl RIP-R11(%rsp),%edx /* User %eip */ CFI_REGISTER rip,rdx RESTORE_ARGS 1,24,1,1,1,1 + xorq %r8,%r8 + xorq %r9,%r9 + xorq %r10,%r10 + xorq %r11,%r11 popfq CFI_ADJUST_CFA_OFFSET -8 /*CFI_RESTORE rflags*/ @@ -200,9 +204,9 @@ sysexit_from_sys_call: movl RDI-ARGOFFSET(%rsp),%r8d /* reload 5th syscall arg */ .endm - .macro auditsys_exit exit,ebpsave=RBP + .macro auditsys_exit exit testl $(_TIF_ALLWORK_MASK & ~_TIF_SYSCALL_AUDIT),TI_flags(%r10) - jnz int_ret_from_sys_call + jnz ia32_ret_from_sys_call TRACE_IRQS_ON sti movl %eax,%esi /* second arg, syscall return value */ @@ -213,13 +217,13 @@ sysexit_from_sys_call: call audit_syscall_exit GET_THREAD_INFO(%r10) movl RAX-ARGOFFSET(%rsp),%eax /* reload syscall return value */ - movl \ebpsave-ARGOFFSET(%rsp),%ebp /* reload user register value */ movl $(_TIF_ALLWORK_MASK & ~_TIF_SYSCALL_AUDIT),%edi cli TRACE_IRQS_OFF testl %edi,TI_flags(%r10) - jnz int_with_check - jmp \exit + jz \exit + CLEAR_RREGS -ARGOFFSET + jmp int_with_check .endm sysenter_auditsys: @@ -329,6 +333,9 @@ sysretl_from_sys_call: CFI_REGISTER rip,rcx movl EFLAGS-ARGOFFSET(%rsp),%r11d /*CFI_REGISTER rflags,r11*/ + xorq %r10,%r10 + xorq %r9,%r9 + xorq %r8,%r8 TRACE_IRQS_ON movl RSP-ARGOFFSET(%rsp),%esp CFI_RESTORE rsp @@ -343,7 +350,7 @@ cstar_auditsys: jmp cstar_dispatch sysretl_audit: - auditsys_exit sysretl_from_sys_call, RCX /* user %ebp in RCX slot */ + auditsys_exit sysretl_from_sys_call #endif cstar_tracesys: @@ -353,7 +360,7 @@ cstar_tracesys: #endif xchgl %r9d,%ebp SAVE_REST - CLEAR_RREGS r9 + CLEAR_RREGS 0, r9 movq $-ENOSYS,RAX(%rsp) /* ptrace can change this for a bad syscall */ movq %rsp,%rdi /* &pt_regs -> arg1 */ call syscall_trace_enter @@ -425,6 +432,8 @@ ia32_do_call: call *ia32_sys_call_table(,%rax,8) # xxx: rip relative ia32_sysret: movq %rax,RAX-ARGOFFSET(%rsp) +ia32_ret_from_sys_call: + CLEAR_RREGS -ARGOFFSET jmp int_ret_from_sys_call ia32_tracesys: @@ -442,8 +451,8 @@ END(ia32_syscall) ia32_badsys: movq $0,ORIG_RAX-ARGOFFSET(%rsp) - movq $-ENOSYS,RAX-ARGOFFSET(%rsp) - jmp int_ret_from_sys_call + movq $-ENOSYS,%rax + jmp ia32_sysret quiet_ni_syscall: movq $-ENOSYS,%rax diff --git a/arch/x86/include/asm/amd_iommu.h b/arch/x86/include/asm/amd_iommu.h index ac95995b7bad..4b180897e6b5 100644 --- a/arch/x86/include/asm/amd_iommu.h +++ b/arch/x86/include/asm/amd_iommu.h @@ -31,6 +31,7 @@ extern irqreturn_t amd_iommu_int_handler(int irq, void *data); extern void amd_iommu_flush_all_domains(void); extern void amd_iommu_flush_all_devices(void); extern void amd_iommu_shutdown(void); +extern void amd_iommu_apply_erratum_63(u16 devid); #else static inline int amd_iommu_init(void) { return -ENODEV; } static inline void amd_iommu_detect(void) { } diff --git a/arch/x86/include/asm/desc.h b/arch/x86/include/asm/desc.h index e8de2f6f5ca5..617bd56b3070 100644 --- a/arch/x86/include/asm/desc.h +++ b/arch/x86/include/asm/desc.h @@ -288,7 +288,7 @@ static inline void load_LDT(mm_context_t *pc) static inline unsigned long get_desc_base(const struct desc_struct *desc) { - return desc->base0 | ((desc->base1) << 16) | ((desc->base2) << 24); + return (unsigned)(desc->base0 | ((desc->base1) << 16) | ((desc->base2) << 24)); } static inline void set_desc_base(struct desc_struct *desc, unsigned long base) diff --git a/arch/x86/include/asm/dma-mapping.h b/arch/x86/include/asm/dma-mapping.h index 0ee770d23d0e..6a25d5d42836 100644 --- a/arch/x86/include/asm/dma-mapping.h +++ b/arch/x86/include/asm/dma-mapping.h @@ -14,6 +14,12 @@ #include <asm/swiotlb.h> #include <asm-generic/dma-coherent.h> +#ifdef CONFIG_ISA +# define ISA_DMA_BIT_MASK DMA_BIT_MASK(24) +#else +# define ISA_DMA_BIT_MASK DMA_BIT_MASK(32) +#endif + extern dma_addr_t bad_dma_address; extern int iommu_merge; extern struct device x86_dma_fallback_dev; @@ -124,10 +130,8 @@ dma_alloc_coherent(struct device *dev, size_t size, dma_addr_t *dma_handle, if (dma_alloc_from_coherent(dev, size, dma_handle, &memory)) return memory; - if (!dev) { + if (!dev) dev = &x86_dma_fallback_dev; - gfp |= GFP_DMA; - } if (!is_device_dma_capable(dev)) return NULL; diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h index 3be000435fad..d83892226f73 100644 --- a/arch/x86/include/asm/kvm_host.h +++ b/arch/x86/include/asm/kvm_host.h @@ -796,6 +796,7 @@ asmlinkage void kvm_handle_fault_on_reboot(void); #define KVM_ARCH_WANT_MMU_NOTIFIER int kvm_unmap_hva(struct kvm *kvm, unsigned long hva); int kvm_age_hva(struct kvm *kvm, unsigned long hva); +void kvm_set_spte_hva(struct kvm *kvm, unsigned long hva, pte_t pte); int cpuid_maxphyaddr(struct kvm_vcpu *vcpu); int kvm_cpu_has_interrupt(struct kvm_vcpu *vcpu); int kvm_arch_interrupt_allowed(struct kvm_vcpu *vcpu); diff --git a/arch/x86/include/asm/mce.h b/arch/x86/include/asm/mce.h index b608a64c5814..f1363b72364f 100644 --- a/arch/x86/include/asm/mce.h +++ b/arch/x86/include/asm/mce.h @@ -133,6 +133,8 @@ static inline void winchip_mcheck_init(struct cpuinfo_x86 *c) {} static inline void enable_p5_mce(void) {} #endif +extern void (*x86_mce_decode_callback)(struct mce *m); + void mce_setup(struct mce *m); void mce_log(struct mce *m); DECLARE_PER_CPU(struct sys_device, mce_dev); diff --git a/arch/x86/include/asm/paravirt.h b/arch/x86/include/asm/paravirt.h index 8aebcc41041d..efb38994859c 100644 --- a/arch/x86/include/asm/paravirt.h +++ b/arch/x86/include/asm/paravirt.h @@ -840,42 +840,22 @@ static __always_inline void __raw_spin_unlock(struct raw_spinlock *lock) static inline unsigned long __raw_local_save_flags(void) { - unsigned long f; - - asm volatile(paravirt_alt(PARAVIRT_CALL) - : "=a"(f) - : paravirt_type(pv_irq_ops.save_fl), - paravirt_clobber(CLBR_EAX) - : "memory", "cc"); - return f; + return PVOP_CALLEE0(unsigned long, pv_irq_ops.save_fl); } static inline void raw_local_irq_restore(unsigned long f) { - asm volatile(paravirt_alt(PARAVIRT_CALL) - : "=a"(f) - : PV_FLAGS_ARG(f), - paravirt_type(pv_irq_ops.restore_fl), - paravirt_clobber(CLBR_EAX) - : "memory", "cc"); + PVOP_VCALLEE1(pv_irq_ops.restore_fl, f); } static inline void raw_local_irq_disable(void) { - asm volatile(paravirt_alt(PARAVIRT_CALL) - : - : paravirt_type(pv_irq_ops.irq_disable), - paravirt_clobber(CLBR_EAX) - : "memory", "eax", "cc"); + PVOP_VCALLEE0(pv_irq_ops.irq_disable); } static inline void raw_local_irq_enable(void) { - asm volatile(paravirt_alt(PARAVIRT_CALL) - : - : paravirt_type(pv_irq_ops.irq_enable), - paravirt_clobber(CLBR_EAX) - : "memory", "eax", "cc"); + PVOP_VCALLEE0(pv_irq_ops.irq_enable); } static inline unsigned long __raw_local_irq_save(void) diff --git a/arch/x86/include/asm/paravirt_types.h b/arch/x86/include/asm/paravirt_types.h index dd0f5b32489d..9357473c8da0 100644 --- a/arch/x86/include/asm/paravirt_types.h +++ b/arch/x86/include/asm/paravirt_types.h @@ -494,10 +494,11 @@ int paravirt_disable_iospace(void); #define EXTRA_CLOBBERS #define VEXTRA_CLOBBERS #else /* CONFIG_X86_64 */ +/* [re]ax isn't an arg, but the return val */ #define PVOP_VCALL_ARGS \ unsigned long __edi = __edi, __esi = __esi, \ - __edx = __edx, __ecx = __ecx -#define PVOP_CALL_ARGS PVOP_VCALL_ARGS, __eax + __edx = __edx, __ecx = __ecx, __eax = __eax +#define PVOP_CALL_ARGS PVOP_VCALL_ARGS #define PVOP_CALL_ARG1(x) "D" ((unsigned long)(x)) #define PVOP_CALL_ARG2(x) "S" ((unsigned long)(x)) @@ -509,6 +510,7 @@ int paravirt_disable_iospace(void); "=c" (__ecx) #define PVOP_CALL_CLOBBERS PVOP_VCALL_CLOBBERS, "=a" (__eax) +/* void functions are still allowed [re]ax for scratch */ #define PVOP_VCALLEE_CLOBBERS "=a" (__eax) #define PVOP_CALLEE_CLOBBERS PVOP_VCALLEE_CLOBBERS @@ -583,8 +585,8 @@ int paravirt_disable_iospace(void); VEXTRA_CLOBBERS, \ pre, post, ##__VA_ARGS__) -#define __PVOP_VCALLEESAVE(rettype, op, pre, post, ...) \ - ____PVOP_CALL(rettype, op.func, CLBR_RET_REG, \ +#define __PVOP_VCALLEESAVE(op, pre, post, ...) \ + ____PVOP_VCALL(op.func, CLBR_RET_REG, \ PVOP_VCALLEE_CLOBBERS, , \ pre, post, ##__VA_ARGS__) diff --git a/arch/x86/include/asm/processor.h b/arch/x86/include/asm/processor.h index c3429e8b2424..c9786480f0fe 100644 --- a/arch/x86/include/asm/processor.h +++ b/arch/x86/include/asm/processor.h @@ -1000,7 +1000,7 @@ extern unsigned long thread_saved_pc(struct task_struct *tsk); #define thread_saved_pc(t) (*(unsigned long *)((t)->thread.sp - 8)) #define task_pt_regs(tsk) ((struct pt_regs *)(tsk)->thread.sp0 - 1) -#define KSTK_ESP(tsk) -1 /* sorry. doesn't work for syscall. */ +extern unsigned long KSTK_ESP(struct task_struct *task); #endif /* CONFIG_X86_64 */ extern void start_thread(struct pt_regs *regs, unsigned long new_ip, diff --git a/arch/x86/include/asm/topology.h b/arch/x86/include/asm/topology.h index 25a92842dd99..40e37b10c6c0 100644 --- a/arch/x86/include/asm/topology.h +++ b/arch/x86/include/asm/topology.h @@ -143,6 +143,7 @@ extern unsigned long node_remap_size[]; | 1*SD_BALANCE_FORK \ | 0*SD_BALANCE_WAKE \ | 1*SD_WAKE_AFFINE \ + | 0*SD_PREFER_LOCAL \ | 0*SD_SHARE_CPUPOWER \ | 0*SD_POWERSAVINGS_BALANCE \ | 0*SD_SHARE_PKG_RESOURCES \ diff --git a/arch/x86/include/asm/uv/uv_hub.h b/arch/x86/include/asm/uv/uv_hub.h index 04eb6c958b9d..d1414af98559 100644 --- a/arch/x86/include/asm/uv/uv_hub.h +++ b/arch/x86/include/asm/uv/uv_hub.h @@ -19,6 +19,8 @@ #include <asm/types.h> #include <asm/percpu.h> #include <asm/uv/uv_mmrs.h> +#include <asm/irq_vectors.h> +#include <asm/io_apic.h> /* @@ -114,7 +116,7 @@ /* * The largest possible NASID of a C or M brick (+ 2) */ -#define UV_MAX_NASID_VALUE (UV_MAX_NUMALINK_NODES * 2) +#define UV_MAX_NASID_VALUE (UV_MAX_NUMALINK_BLADES * 2) struct uv_scir_s { struct timer_list timer; @@ -230,6 +232,20 @@ static inline unsigned long uv_gpa(void *v) return uv_soc_phys_ram_to_gpa(__pa(v)); } +/* gnode -> pnode */ +static inline unsigned long uv_gpa_to_gnode(unsigned long gpa) +{ + return gpa >> uv_hub_info->m_val; +} + +/* gpa -> pnode */ +static inline int uv_gpa_to_pnode(unsigned long gpa) +{ + unsigned long n_mask = (1UL << uv_hub_info->n_val) - 1; + + return uv_gpa_to_gnode(gpa) & n_mask; +} + /* pnode, offset --> socket virtual */ static inline void *uv_pnode_offset_to_vaddr(int pnode, unsigned long offset) { @@ -421,9 +437,14 @@ static inline void uv_set_cpu_scir_bits(int cpu, unsigned char value) static inline void uv_hub_send_ipi(int pnode, int apicid, int vector) { unsigned long val; + unsigned long dmode = dest_Fixed; + + if (vector == NMI_VECTOR) + dmode = dest_NMI; val = (1UL << UVH_IPI_INT_SEND_SHFT) | ((apicid) << UVH_IPI_INT_APIC_ID_SHFT) | + (dmode << UVH_IPI_INT_DELIVERY_MODE_SHFT) | (vector << UVH_IPI_INT_VECTOR_SHFT); uv_write_global_mmr64(pnode, UVH_IPI_INT, val); } diff --git a/arch/x86/kernel/acpi/realmode/wakeup.lds.S b/arch/x86/kernel/acpi/realmode/wakeup.lds.S index 7da00b799cda..060fff8f5c5b 100644 --- a/arch/x86/kernel/acpi/realmode/wakeup.lds.S +++ b/arch/x86/kernel/acpi/realmode/wakeup.lds.S @@ -57,5 +57,8 @@ SECTIONS *(.note*) } + /* + * The ASSERT() sink to . is intentional, for binutils 2.14 compatibility: + */ . = ASSERT(_end <= WAKEUP_SIZE, "Wakeup too big!"); } diff --git a/arch/x86/kernel/amd_iommu.c b/arch/x86/kernel/amd_iommu.c index 98f230f6a28d..0285521e0a99 100644 --- a/arch/x86/kernel/amd_iommu.c +++ b/arch/x86/kernel/amd_iommu.c @@ -1220,6 +1220,8 @@ static void __detach_device(struct protection_domain *domain, u16 devid) amd_iommu_dev_table[devid].data[1] = 0; amd_iommu_dev_table[devid].data[2] = 0; + amd_iommu_apply_erratum_63(devid); + /* decrease reference counter */ domain->dev_cnt -= 1; diff --git a/arch/x86/kernel/amd_iommu_init.c b/arch/x86/kernel/amd_iommu_init.c index b4b61d462dcc..c20001e4f556 100644 --- a/arch/x86/kernel/amd_iommu_init.c +++ b/arch/x86/kernel/amd_iommu_init.c @@ -240,7 +240,7 @@ static void iommu_feature_enable(struct amd_iommu *iommu, u8 bit) writel(ctrl, iommu->mmio_base + MMIO_CONTROL_OFFSET); } -static void __init iommu_feature_disable(struct amd_iommu *iommu, u8 bit) +static void iommu_feature_disable(struct amd_iommu *iommu, u8 bit) { u32 ctrl; @@ -519,6 +519,26 @@ static void set_dev_entry_bit(u16 devid, u8 bit) amd_iommu_dev_table[devid].data[i] |= (1 << _bit); } +static int get_dev_entry_bit(u16 devid, u8 bit) +{ + int i = (bit >> 5) & 0x07; + int _bit = bit & 0x1f; + + return (amd_iommu_dev_table[devid].data[i] & (1 << _bit)) >> _bit; +} + + +void amd_iommu_apply_erratum_63(u16 devid) +{ + int sysmgt; + + sysmgt = get_dev_entry_bit(devid, DEV_ENTRY_SYSMGT1) | + (get_dev_entry_bit(devid, DEV_ENTRY_SYSMGT2) << 1); + + if (sysmgt == 0x01) + set_dev_entry_bit(devid, DEV_ENTRY_IW); +} + /* Writes the specific IOMMU for a device into the rlookup table */ static void __init set_iommu_for_device(struct amd_iommu *iommu, u16 devid) { @@ -547,6 +567,8 @@ static void __init set_dev_entry_from_acpi(struct amd_iommu *iommu, if (flags & ACPI_DEVFLAG_LINT1) set_dev_entry_bit(devid, DEV_ENTRY_LINT1_PASS); + amd_iommu_apply_erratum_63(devid); + set_iommu_for_device(iommu, devid); } diff --git a/arch/x86/kernel/apic/x2apic_uv_x.c b/arch/x86/kernel/apic/x2apic_uv_x.c index f5f5886a6b53..326c25477d3d 100644 --- a/arch/x86/kernel/apic/x2apic_uv_x.c +++ b/arch/x86/kernel/apic/x2apic_uv_x.c @@ -352,14 +352,14 @@ static __init void get_lowmem_redirect(unsigned long *base, unsigned long *size) for (i = 0; i < ARRAY_SIZE(redir_addrs); i++) { alias.v = uv_read_local_mmr(redir_addrs[i].alias); - if (alias.s.base == 0) { + if (alias.s.enable && alias.s.base == 0) { *size = (1UL << alias.s.m_alias); redirect.v = uv_read_local_mmr(redir_addrs[i].redirect); *base = (unsigned long)redirect.s.dest_base << DEST_SHIFT; return; } } - BUG(); + *base = *size = 0; } enum map_type {map_wb, map_uc}; @@ -619,12 +619,12 @@ void __init uv_system_init(void) uv_cpu_hub_info(cpu)->lowmem_remap_base = lowmem_redir_base; uv_cpu_hub_info(cpu)->lowmem_remap_top = lowmem_redir_size; uv_cpu_hub_info(cpu)->m_val = m_val; - uv_cpu_hub_info(cpu)->n_val = m_val; + uv_cpu_hub_info(cpu)->n_val = n_val; uv_cpu_hub_info(cpu)->numa_blade_id = blade; uv_cpu_hub_info(cpu)->blade_processor_id = lcpu; uv_cpu_hub_info(cpu)->pnode = pnode; uv_cpu_hub_info(cpu)->pnode_mask = pnode_mask; - uv_cpu_hub_info(cpu)->gpa_mask = (1 << (m_val + n_val)) - 1; + uv_cpu_hub_info(cpu)->gpa_mask = (1UL << (m_val + n_val)) - 1; uv_cpu_hub_info(cpu)->gnode_upper = gnode_upper; uv_cpu_hub_info(cpu)->gnode_extra = gnode_extra; uv_cpu_hub_info(cpu)->global_mmr_base = mmr_base; diff --git a/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c b/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c index 7d5c3b0ea8da..8b581d3905cb 100644 --- a/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c +++ b/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c @@ -526,15 +526,21 @@ static const struct dmi_system_id sw_any_bug_dmi_table[] = { static int acpi_cpufreq_blacklist(struct cpuinfo_x86 *c) { - /* http://www.intel.com/Assets/PDF/specupdate/314554.pdf + /* Intel Xeon Processor 7100 Series Specification Update + * http://www.intel.com/Assets/PDF/specupdate/314554.pdf * AL30: A Machine Check Exception (MCE) Occurring during an * Enhanced Intel SpeedStep Technology Ratio Change May Cause - * Both Processor Cores to Lock Up when HT is enabled*/ + * Both Processor Cores to Lock Up. */ if (c->x86_vendor == X86_VENDOR_INTEL) { if ((c->x86 == 15) && (c->x86_model == 6) && - (c->x86_mask == 8) && smt_capable()) + (c->x86_mask == 8)) { + printk(KERN_INFO "acpi-cpufreq: Intel(R) " + "Xeon(R) 7100 Errata AL30, processors may " + "lock up on frequency changes: disabling " + "acpi-cpufreq.\n"); return -ENODEV; + } } return 0; } @@ -549,13 +555,18 @@ static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy) unsigned int result = 0; struct cpuinfo_x86 *c = &cpu_data(policy->cpu); struct acpi_processor_performance *perf; +#ifdef CONFIG_SMP + static int blacklisted; +#endif dprintk("acpi_cpufreq_cpu_init\n"); #ifdef CONFIG_SMP - result = acpi_cpufreq_blacklist(c); - if (result) - return result; + if (blacklisted) + return blacklisted; + blacklisted = acpi_cpufreq_blacklist(c); + if (blacklisted) + return blacklisted; #endif data = kzalloc(sizeof(struct acpi_cpufreq_data), GFP_KERNEL); diff --git a/arch/x86/kernel/cpu/cpufreq/longhaul.c b/arch/x86/kernel/cpu/cpufreq/longhaul.c index ce2ed3e4aad9..cabd2fa3fc93 100644 --- a/arch/x86/kernel/cpu/cpufreq/longhaul.c +++ b/arch/x86/kernel/cpu/cpufreq/longhaul.c @@ -813,7 +813,7 @@ static int __init longhaul_cpu_init(struct cpufreq_policy *policy) memcpy(eblcr, samuel2_eblcr, sizeof(samuel2_eblcr)); break; case 1 ... 15: - longhaul_version = TYPE_LONGHAUL_V1; + longhaul_version = TYPE_LONGHAUL_V2; if (c->x86_mask < 8) { cpu_model = CPU_SAMUEL2; cpuname = "C3 'Samuel 2' [C5B]"; diff --git a/arch/x86/kernel/cpu/cpufreq/powernow-k8.c b/arch/x86/kernel/cpu/cpufreq/powernow-k8.c index 6394aa5c7985..3f12dabeab52 100644 --- a/arch/x86/kernel/cpu/cpufreq/powernow-k8.c +++ b/arch/x86/kernel/cpu/cpufreq/powernow-k8.c @@ -1022,7 +1022,7 @@ static int get_transition_latency(struct powernow_k8_data *data) * set it to 1 to avoid problems in the future. * For all others it's a BIOS bug. */ - if (!boot_cpu_data.x86 == 0x11) + if (boot_cpu_data.x86 != 0x11) printk(KERN_ERR FW_WARN PFX "Invalid zero transition " "latency\n"); max_latency = 1; diff --git a/arch/x86/kernel/cpu/cpufreq/speedstep-ich.c b/arch/x86/kernel/cpu/cpufreq/speedstep-ich.c index 6911e91fb4f6..3ae5a7a3a500 100644 --- a/arch/x86/kernel/cpu/cpufreq/speedstep-ich.c +++ b/arch/x86/kernel/cpu/cpufreq/speedstep-ich.c @@ -232,28 +232,23 @@ static unsigned int speedstep_detect_chipset(void) return 0; } -struct get_freq_data { - unsigned int speed; - unsigned int processor; -}; - -static void get_freq_data(void *_data) +static void get_freq_data(void *_speed) { - struct get_freq_data *data = _data; + unsigned int *speed = _speed; - data->speed = speedstep_get_frequency(data->processor); + *speed = speedstep_get_frequency(speedstep_processor); } static unsigned int speedstep_get(unsigned int cpu) { - struct get_freq_data data = { .processor = cpu }; + unsigned int speed; /* You're supposed to ensure CPU is online. */ - if (smp_call_function_single(cpu, get_freq_data, &data, 1) != 0) + if (smp_call_function_single(cpu, get_freq_data, &speed, 1) != 0) BUG(); - dprintk("detected %u kHz as current frequency\n", data.speed); - return data.speed; + dprintk("detected %u kHz as current frequency\n", speed); + return speed; } /** diff --git a/arch/x86/kernel/cpu/mcheck/mce.c b/arch/x86/kernel/cpu/mcheck/mce.c index 183c3457d2f4..721a77ca8115 100644 --- a/arch/x86/kernel/cpu/mcheck/mce.c +++ b/arch/x86/kernel/cpu/mcheck/mce.c @@ -85,6 +85,18 @@ static DECLARE_WAIT_QUEUE_HEAD(mce_wait); static DEFINE_PER_CPU(struct mce, mces_seen); static int cpu_missing; +static void default_decode_mce(struct mce *m) +{ + pr_emerg("No human readable MCE decoding support on this CPU type.\n"); + pr_emerg("Run the message through 'mcelog --ascii' to decode.\n"); +} + +/* + * CPU/chipset specific EDAC code can register a callback here to print + * MCE errors in a human-readable form: + */ +void (*x86_mce_decode_callback)(struct mce *m) = default_decode_mce; +EXPORT_SYMBOL(x86_mce_decode_callback); /* MCA banks polled by the period polling timer for corrected events */ DEFINE_PER_CPU(mce_banks_t, mce_poll_banks) = { @@ -165,46 +177,46 @@ void mce_log(struct mce *mce) set_bit(0, &mce_need_notify); } -void __weak decode_mce(struct mce *m) -{ - return; -} - static void print_mce(struct mce *m) { - printk(KERN_EMERG - "CPU %d: Machine Check Exception: %16Lx Bank %d: %016Lx\n", + pr_emerg("CPU %d: Machine Check Exception: %16Lx Bank %d: %016Lx\n", m->extcpu, m->mcgstatus, m->bank, m->status); + if (m->ip) { - printk(KERN_EMERG "RIP%s %02x:<%016Lx> ", - !(m->mcgstatus & MCG_STATUS_EIPV) ? " !INEXACT!" : "", - m->cs, m->ip); + pr_emerg("RIP%s %02x:<%016Lx> ", + !(m->mcgstatus & MCG_STATUS_EIPV) ? " !INEXACT!" : "", + m->cs, m->ip); + if (m->cs == __KERNEL_CS) print_symbol("{%s}", m->ip); - printk(KERN_CONT "\n"); + pr_cont("\n"); } - printk(KERN_EMERG "TSC %llx ", m->tsc); + + pr_emerg("TSC %llx ", m->tsc); if (m->addr) - printk(KERN_CONT "ADDR %llx ", m->addr); + pr_cont("ADDR %llx ", m->addr); if (m->misc) - printk(KERN_CONT "MISC %llx ", m->misc); - printk(KERN_CONT "\n"); - printk(KERN_EMERG "PROCESSOR %u:%x TIME %llu SOCKET %u APIC %x\n", - m->cpuvendor, m->cpuid, m->time, m->socketid, - m->apicid); + pr_cont("MISC %llx ", m->misc); - decode_mce(m); + pr_cont("\n"); + pr_emerg("PROCESSOR %u:%x TIME %llu SOCKET %u APIC %x\n", + m->cpuvendor, m->cpuid, m->time, m->socketid, m->apicid); + + /* + * Print out human-readable details about the MCE error, + * (if the CPU has an implementation for that): + */ + x86_mce_decode_callback(m); } static void print_mce_head(void) { - printk(KERN_EMERG "\nHARDWARE ERROR\n"); + pr_emerg("\nHARDWARE ERROR\n"); } static void print_mce_tail(void) { - printk(KERN_EMERG "This is not a software problem!\n" - "Run through mcelog --ascii to decode and contact your hardware vendor\n"); + pr_emerg("This is not a software problem!\n"); } #define PANIC_TIMEOUT 5 /* 5 seconds */ @@ -218,6 +230,7 @@ static atomic_t mce_fake_paniced; static void wait_for_panic(void) { long timeout = PANIC_TIMEOUT*USEC_PER_SEC; + preempt_disable(); local_irq_enable(); while (timeout-- > 0) @@ -285,6 +298,7 @@ static void mce_panic(char *msg, struct mce *final, char *exp) static int msr_to_offset(u32 msr) { unsigned bank = __get_cpu_var(injectm.bank); + if (msr == rip_msr) return offsetof(struct mce, ip); if (msr == MSR_IA32_MCx_STATUS(bank)) @@ -1200,7 +1214,8 @@ static int __cpuinit mce_cap_init(void) rdmsrl(MSR_IA32_MCG_CAP, cap); b = cap & MCG_BANKCNT_MASK; - printk(KERN_INFO "mce: CPU supports %d MCE banks\n", b); + if (!banks) + printk(KERN_INFO "mce: CPU supports %d MCE banks\n", b); if (b > MAX_NR_BANKS) { printk(KERN_WARNING diff --git a/arch/x86/kernel/cpu/mcheck/mce_intel.c b/arch/x86/kernel/cpu/mcheck/mce_intel.c index 889f665fe93d..7c785634af2b 100644 --- a/arch/x86/kernel/cpu/mcheck/mce_intel.c +++ b/arch/x86/kernel/cpu/mcheck/mce_intel.c @@ -8,6 +8,7 @@ #include <linux/init.h> #include <linux/interrupt.h> #include <linux/percpu.h> +#include <linux/sched.h> #include <asm/apic.h> #include <asm/processor.h> #include <asm/msr.h> diff --git a/arch/x86/kernel/cpu/mtrr/cleanup.c b/arch/x86/kernel/cpu/mtrr/cleanup.c index 315738c74aad..73c86db5acbe 100644 --- a/arch/x86/kernel/cpu/mtrr/cleanup.c +++ b/arch/x86/kernel/cpu/mtrr/cleanup.c @@ -846,7 +846,7 @@ int __init mtrr_cleanup(unsigned address_bits) sort(range, nr_range, sizeof(struct res_range), cmp_range, NULL); range_sums = sum_ranges(range, nr_range); - printk(KERN_INFO "total RAM coverred: %ldM\n", + printk(KERN_INFO "total RAM covered: %ldM\n", range_sums >> (20 - PAGE_SHIFT)); if (mtrr_chunk_size && mtrr_gran_size) { diff --git a/arch/x86/kernel/cpu/mtrr/if.c b/arch/x86/kernel/cpu/mtrr/if.c index f04e72527604..3c1b12d461d1 100644 --- a/arch/x86/kernel/cpu/mtrr/if.c +++ b/arch/x86/kernel/cpu/mtrr/if.c @@ -96,17 +96,24 @@ mtrr_write(struct file *file, const char __user *buf, size_t len, loff_t * ppos) unsigned long long base, size; char *ptr; char line[LINE_SIZE]; + int length; size_t linelen; if (!capable(CAP_SYS_ADMIN)) return -EPERM; - if (!len) - return -EINVAL; memset(line, 0, LINE_SIZE); - if (len > LINE_SIZE) - len = LINE_SIZE; - if (copy_from_user(line, buf, len - 1)) + + length = len; + length--; + + if (length > LINE_SIZE - 1) + length = LINE_SIZE - 1; + + if (length < 0) + return -EINVAL; + + if (copy_from_user(line, buf, length)) return -EFAULT; linelen = strlen(line); diff --git a/arch/x86/kernel/crash_dump_32.c b/arch/x86/kernel/crash_dump_32.c index f7cdb3b457aa..cd97ce18c29d 100644 --- a/arch/x86/kernel/crash_dump_32.c +++ b/arch/x86/kernel/crash_dump_32.c @@ -16,6 +16,22 @@ static void *kdump_buf_page; /* Stores the physical address of elf header of crash image. */ unsigned long long elfcorehdr_addr = ELFCORE_ADDR_MAX; +static inline bool is_crashed_pfn_valid(unsigned long pfn) +{ +#ifndef CONFIG_X86_PAE + /* + * non-PAE kdump kernel executed from a PAE one will crop high pte + * bits and poke unwanted space counting again from address 0, we + * don't want that. pte must fit into unsigned long. In fact the + * test checks high 12 bits for being zero (pfn will be shifted left + * by PAGE_SHIFT). + */ + return pte_pfn(pfn_pte(pfn, __pgprot(0))) == pfn; +#else + return true; +#endif +} + /** * copy_oldmem_page - copy one page from "oldmem" * @pfn: page frame number to be copied @@ -41,6 +57,9 @@ ssize_t copy_oldmem_page(unsigned long pfn, char *buf, if (!csize) return 0; + if (!is_crashed_pfn_valid(pfn)) + return -EFAULT; + vaddr = kmap_atomic_pfn(pfn, KM_PTE0); if (!userbuf) { diff --git a/arch/x86/kernel/e820.c b/arch/x86/kernel/e820.c index 85419bb7d4ab..d17d482a04f4 100644 --- a/arch/x86/kernel/e820.c +++ b/arch/x86/kernel/e820.c @@ -1378,8 +1378,8 @@ static unsigned long ram_alignment(resource_size_t pos) if (mb < 16) return 1024*1024; - /* To 32MB for anything above that */ - return 32*1024*1024; + /* To 64MB for anything above that */ + return 64*1024*1024; } #define MAX_RESOURCE_SIZE ((resource_size_t)-1) diff --git a/arch/x86/kernel/early_printk.c b/arch/x86/kernel/early_printk.c index 41fd965c80c6..b9c830c12b4a 100644 --- a/arch/x86/kernel/early_printk.c +++ b/arch/x86/kernel/early_printk.c @@ -206,8 +206,11 @@ static int __init setup_early_printk(char *buf) while (*buf != '\0') { if (!strncmp(buf, "serial", 6)) { - early_serial_init(buf + 6); + buf += 6; + early_serial_init(buf); early_console_register(&early_serial_console, keep); + if (!strncmp(buf, ",ttyS", 5)) + buf += 5; } if (!strncmp(buf, "ttyS", 4)) { early_serial_init(buf + 4); diff --git a/arch/x86/kernel/efi.c b/arch/x86/kernel/efi.c index ad5bd988fb79..cdcfb122f256 100644 --- a/arch/x86/kernel/efi.c +++ b/arch/x86/kernel/efi.c @@ -454,8 +454,10 @@ void __init efi_init(void) if (add_efi_memmap) do_add_efi_memmap(); +#ifdef CONFIG_X86_32 x86_platform.get_wallclock = efi_get_time; x86_platform.set_wallclock = efi_set_rtc_mmss; +#endif /* Setup for EFI runtime service */ reboot_type = BOOT_EFI; diff --git a/arch/x86/kernel/i386_ksyms_32.c b/arch/x86/kernel/i386_ksyms_32.c index 1736c5a725aa..9c3bd4a2050e 100644 --- a/arch/x86/kernel/i386_ksyms_32.c +++ b/arch/x86/kernel/i386_ksyms_32.c @@ -15,8 +15,10 @@ EXPORT_SYMBOL(mcount); * the export, but dont use it from C code, it is used * by assembly code and is not using C calling convention! */ +#ifndef CONFIG_X86_CMPXCHG64 extern void cmpxchg8b_emu(void); EXPORT_SYMBOL(cmpxchg8b_emu); +#endif /* Networking helper routines. */ EXPORT_SYMBOL(csum_partial_copy_generic); diff --git a/arch/x86/kernel/irq.c b/arch/x86/kernel/irq.c index 74656d1d4e30..04bbd5278568 100644 --- a/arch/x86/kernel/irq.c +++ b/arch/x86/kernel/irq.c @@ -63,10 +63,10 @@ static int show_other_interrupts(struct seq_file *p, int prec) for_each_online_cpu(j) seq_printf(p, "%10u ", irq_stats(j)->irq_spurious_count); seq_printf(p, " Spurious interrupts\n"); - seq_printf(p, "%*s: ", prec, "CNT"); + seq_printf(p, "%*s: ", prec, "PMI"); for_each_online_cpu(j) seq_printf(p, "%10u ", irq_stats(j)->apic_perf_irqs); - seq_printf(p, " Performance counter interrupts\n"); + seq_printf(p, " Performance monitoring interrupts\n"); seq_printf(p, "%*s: ", prec, "PND"); for_each_online_cpu(j) seq_printf(p, "%10u ", irq_stats(j)->apic_pending_irqs); diff --git a/arch/x86/kernel/microcode_amd.c b/arch/x86/kernel/microcode_amd.c index 366baa179913..f4c538b681ca 100644 --- a/arch/x86/kernel/microcode_amd.c +++ b/arch/x86/kernel/microcode_amd.c @@ -317,6 +317,12 @@ static enum ucode_state request_microcode_fw(int cpu, struct device *device) return UCODE_NFOUND; } + if (*(u32 *)firmware->data != UCODE_MAGIC) { + printk(KERN_ERR "microcode: invalid UCODE_MAGIC (0x%08x)\n", + *(u32 *)firmware->data); + return UCODE_ERROR; + } + ret = generic_load_microcode(cpu, firmware->data, firmware->size); release_firmware(firmware); diff --git a/arch/x86/kernel/pci-dma.c b/arch/x86/kernel/pci-dma.c index 64b838eac18c..a6e804d16c35 100644 --- a/arch/x86/kernel/pci-dma.c +++ b/arch/x86/kernel/pci-dma.c @@ -35,7 +35,7 @@ int iommu_detected __read_mostly = 0; /* * This variable becomes 1 if iommu=pt is passed on the kernel command line. - * If this variable is 1, IOMMU implementations do no DMA ranslation for + * If this variable is 1, IOMMU implementations do no DMA translation for * devices and allow every device to access to whole physical memory. This is * useful if a user want to use an IOMMU only for KVM device assignment to * guests and not for driver dma translation. @@ -45,12 +45,10 @@ int iommu_pass_through __read_mostly; dma_addr_t bad_dma_address __read_mostly = 0; EXPORT_SYMBOL(bad_dma_address); -/* Dummy device used for NULL arguments (normally ISA). Better would - be probably a smaller DMA mask, but this is bug-to-bug compatible - to older i386. */ +/* Dummy device used for NULL arguments (normally ISA). */ struct device x86_dma_fallback_dev = { .init_name = "fallback device", - .coherent_dma_mask = DMA_BIT_MASK(32), + .coherent_dma_mask = ISA_DMA_BIT_MASK, .dma_mask = &x86_dma_fallback_dev.coherent_dma_mask, }; EXPORT_SYMBOL(x86_dma_fallback_dev); @@ -311,7 +309,7 @@ void pci_iommu_shutdown(void) amd_iommu_shutdown(); } /* Must execute after PCI subsystem */ -fs_initcall(pci_iommu_init); +rootfs_initcall(pci_iommu_init); #ifdef CONFIG_PCI /* Many VIA bridges seem to corrupt data for DAC. Disable it here */ diff --git a/arch/x86/kernel/pci-gart_64.c b/arch/x86/kernel/pci-gart_64.c index 98a827ee9ed7..a7f1b64f86e0 100644 --- a/arch/x86/kernel/pci-gart_64.c +++ b/arch/x86/kernel/pci-gart_64.c @@ -16,6 +16,7 @@ #include <linux/agp_backend.h> #include <linux/init.h> #include <linux/mm.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/spinlock.h> #include <linux/pci.h> diff --git a/arch/x86/kernel/process_64.c b/arch/x86/kernel/process_64.c index ad535b683170..eb62cbcaa490 100644 --- a/arch/x86/kernel/process_64.c +++ b/arch/x86/kernel/process_64.c @@ -664,3 +664,8 @@ long sys_arch_prctl(int code, unsigned long addr) return do_arch_prctl(current, code, addr); } +unsigned long KSTK_ESP(struct task_struct *task) +{ + return (test_tsk_thread_flag(task, TIF_IA32)) ? + (task_pt_regs(task)->sp) : ((task)->thread.usersp); +} diff --git a/arch/x86/kernel/reboot.c b/arch/x86/kernel/reboot.c index 27349f92a6d7..f93078746e00 100644 --- a/arch/x86/kernel/reboot.c +++ b/arch/x86/kernel/reboot.c @@ -4,6 +4,7 @@ #include <linux/pm.h> #include <linux/efi.h> #include <linux/dmi.h> +#include <linux/sched.h> #include <linux/tboot.h> #include <acpi/reboot.h> #include <asm/io.h> @@ -435,6 +436,14 @@ static struct dmi_system_id __initdata pci_reboot_dmi_table[] = { DMI_MATCH(DMI_PRODUCT_NAME, "MacBookPro5"), }, }, + { /* Handle problems with rebooting on Apple Macmini3,1 */ + .callback = set_pci_reboot, + .ident = "Apple Macmini3,1", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Apple Inc."), + DMI_MATCH(DMI_PRODUCT_NAME, "Macmini3,1"), + }, + }, { } }; diff --git a/arch/x86/kernel/setup.c b/arch/x86/kernel/setup.c index e09f0e2c14b5..2a34f9c5be21 100644 --- a/arch/x86/kernel/setup.c +++ b/arch/x86/kernel/setup.c @@ -660,6 +660,13 @@ static struct dmi_system_id __initdata bad_bios_dmi_table[] = { }, }, { + .callback = dmi_low_memory_corruption, + .ident = "Phoenix/MSC BIOS", + .matches = { + DMI_MATCH(DMI_BIOS_VENDOR, "Phoenix/MSC"), + }, + }, + { /* * AMI BIOS with low memory corruption was found on Intel DG45ID board. * It hase different DMI_BIOS_VENDOR = "Intel Corp.", for now we will diff --git a/arch/x86/kernel/time.c b/arch/x86/kernel/time.c index dcb00d278512..be2573448ed9 100644 --- a/arch/x86/kernel/time.c +++ b/arch/x86/kernel/time.c @@ -38,7 +38,8 @@ unsigned long profile_pc(struct pt_regs *regs) #ifdef CONFIG_FRAME_POINTER return *(unsigned long *)(regs->bp + sizeof(long)); #else - unsigned long *sp = (unsigned long *)regs->sp; + unsigned long *sp = + (unsigned long *)kernel_stack_pointer(regs); /* * Return address is either directly at stack pointer * or above a saved flags. Eflags has bits 22-31 zero, diff --git a/arch/x86/kernel/tlb_uv.c b/arch/x86/kernel/tlb_uv.c index 503c1f2e8835..1740c85e24bb 100644 --- a/arch/x86/kernel/tlb_uv.c +++ b/arch/x86/kernel/tlb_uv.c @@ -23,8 +23,6 @@ static struct bau_control **uv_bau_table_bases __read_mostly; static int uv_bau_retry_limit __read_mostly; -/* position of pnode (which is nasid>>1): */ -static int uv_nshift __read_mostly; /* base pnode in this partition */ static int uv_partition_base_pnode __read_mostly; @@ -723,7 +721,7 @@ uv_activation_descriptor_init(int node, int pnode) BUG_ON(!adp); pa = uv_gpa(adp); /* need the real nasid*/ - n = pa >> uv_nshift; + n = uv_gpa_to_pnode(pa); m = pa & uv_mmask; uv_write_global_mmr64(pnode, UVH_LB_BAU_SB_DESCRIPTOR_BASE, @@ -778,7 +776,7 @@ uv_payload_queue_init(int node, int pnode, struct bau_control *bau_tablesp) * need the pnode of where the memory was really allocated */ pa = uv_gpa(pqp); - pn = pa >> uv_nshift; + pn = uv_gpa_to_pnode(pa); uv_write_global_mmr64(pnode, UVH_LB_BAU_INTD_PAYLOAD_QUEUE_FIRST, ((unsigned long)pn << UV_PAYLOADQ_PNODE_SHIFT) | @@ -843,8 +841,7 @@ static int __init uv_bau_init(void) GFP_KERNEL, cpu_to_node(cur_cpu)); uv_bau_retry_limit = 1; - uv_nshift = uv_hub_info->n_val; - uv_mmask = (1UL << uv_hub_info->n_val) - 1; + uv_mmask = (1UL << uv_hub_info->m_val) - 1; nblades = uv_num_possible_blades(); uv_bau_table_bases = (struct bau_control **) diff --git a/arch/x86/kernel/trampoline.c b/arch/x86/kernel/trampoline.c index 699f7eeb896a..cd022121cab6 100644 --- a/arch/x86/kernel/trampoline.c +++ b/arch/x86/kernel/trampoline.c @@ -3,8 +3,16 @@ #include <asm/trampoline.h> #include <asm/e820.h> +#if defined(CONFIG_X86_64) && defined(CONFIG_ACPI_SLEEP) +#define __trampinit +#define __trampinitdata +#else +#define __trampinit __cpuinit +#define __trampinitdata __cpuinitdata +#endif + /* ready for x86_64 and x86 */ -unsigned char *__cpuinitdata trampoline_base = __va(TRAMPOLINE_BASE); +unsigned char *__trampinitdata trampoline_base = __va(TRAMPOLINE_BASE); void __init reserve_trampoline_memory(void) { @@ -26,7 +34,7 @@ void __init reserve_trampoline_memory(void) * bootstrap into the page concerned. The caller * has made sure it's suitably aligned. */ -unsigned long __cpuinit setup_trampoline(void) +unsigned long __trampinit setup_trampoline(void) { memcpy(trampoline_base, trampoline_data, TRAMPOLINE_SIZE); return virt_to_phys(trampoline_base); diff --git a/arch/x86/kernel/trampoline_64.S b/arch/x86/kernel/trampoline_64.S index 596d54c660a5..3af2dff58b21 100644 --- a/arch/x86/kernel/trampoline_64.S +++ b/arch/x86/kernel/trampoline_64.S @@ -32,8 +32,12 @@ #include <asm/segment.h> #include <asm/processor-flags.h> +#ifdef CONFIG_ACPI_SLEEP +.section .rodata, "a", @progbits +#else /* We can free up the trampoline after bootup if cpu hotplug is not supported. */ __CPUINITRODATA +#endif .code16 ENTRY(trampoline_data) diff --git a/arch/x86/kernel/vmi_32.c b/arch/x86/kernel/vmi_32.c index 31e6f6cfe53e..d430e4c30193 100644 --- a/arch/x86/kernel/vmi_32.c +++ b/arch/x86/kernel/vmi_32.c @@ -648,7 +648,7 @@ static inline int __init activate_vmi(void) pv_info.paravirt_enabled = 1; pv_info.kernel_rpl = kernel_cs & SEGMENT_RPL_MASK; - pv_info.name = "vmi"; + pv_info.name = "vmi [deprecated]"; pv_init_ops.patch = vmi_patch; diff --git a/arch/x86/kernel/vmlinux.lds.S b/arch/x86/kernel/vmlinux.lds.S index 92929fb3f9fa..3c68fe2d46cf 100644 --- a/arch/x86/kernel/vmlinux.lds.S +++ b/arch/x86/kernel/vmlinux.lds.S @@ -305,6 +305,9 @@ SECTIONS #ifdef CONFIG_X86_32 +/* + * The ASSERT() sink to . is intentional, for binutils 2.14 compatibility: + */ . = ASSERT((_end - LOAD_OFFSET <= KERNEL_IMAGE_SIZE), "kernel image bigger than KERNEL_IMAGE_SIZE"); #else diff --git a/arch/x86/kvm/i8254.c b/arch/x86/kvm/i8254.c index 82ad523b4901..144e7f60b5e2 100644 --- a/arch/x86/kvm/i8254.c +++ b/arch/x86/kvm/i8254.c @@ -116,7 +116,7 @@ static s64 __kpit_elapsed(struct kvm *kvm) * itself with the initial count and continues counting * from there. */ - remaining = hrtimer_expires_remaining(&ps->pit_timer.timer); + remaining = hrtimer_get_remaining(&ps->pit_timer.timer); elapsed = ps->pit_timer.period - ktime_to_ns(remaining); elapsed = mod_64(elapsed, ps->pit_timer.period); diff --git a/arch/x86/kvm/lapic.c b/arch/x86/kvm/lapic.c index 1ae5ceba7eb2..23c217692ea9 100644 --- a/arch/x86/kvm/lapic.c +++ b/arch/x86/kvm/lapic.c @@ -521,7 +521,7 @@ static u32 apic_get_tmcct(struct kvm_lapic *apic) if (apic_get_reg(apic, APIC_TMICT) == 0) return 0; - remaining = hrtimer_expires_remaining(&apic->lapic_timer.timer); + remaining = hrtimer_get_remaining(&apic->lapic_timer.timer); if (ktime_to_ns(remaining) < 0) remaining = ktime_set(0, 0); @@ -664,7 +664,7 @@ static void start_apic_timer(struct kvm_lapic *apic) { ktime_t now = apic->lapic_timer.timer.base->get_time(); - apic->lapic_timer.period = apic_get_reg(apic, APIC_TMICT) * + apic->lapic_timer.period = (u64)apic_get_reg(apic, APIC_TMICT) * APIC_BUS_CYCLE_NS * apic->divide_count; atomic_set(&apic->lapic_timer.pending, 0); diff --git a/arch/x86/kvm/mmu.c b/arch/x86/kvm/mmu.c index eca41ae9f453..818b92ad82cf 100644 --- a/arch/x86/kvm/mmu.c +++ b/arch/x86/kvm/mmu.c @@ -156,6 +156,8 @@ module_param(oos_shadow, bool, 0644); #define CREATE_TRACE_POINTS #include "mmutrace.h" +#define SPTE_HOST_WRITEABLE (1ULL << PT_FIRST_AVAIL_BITS_SHIFT) + #define SHADOW_PT_INDEX(addr, level) PT64_INDEX(addr, level) struct kvm_rmap_desc { @@ -634,9 +636,7 @@ static void rmap_remove(struct kvm *kvm, u64 *spte) if (*spte & shadow_accessed_mask) kvm_set_pfn_accessed(pfn); if (is_writeble_pte(*spte)) - kvm_release_pfn_dirty(pfn); - else - kvm_release_pfn_clean(pfn); + kvm_set_pfn_dirty(pfn); rmapp = gfn_to_rmap(kvm, sp->gfns[spte - sp->spt], sp->role.level); if (!*rmapp) { printk(KERN_ERR "rmap_remove: %p %llx 0->BUG\n", spte, *spte); @@ -748,7 +748,8 @@ static int rmap_write_protect(struct kvm *kvm, u64 gfn) return write_protected; } -static int kvm_unmap_rmapp(struct kvm *kvm, unsigned long *rmapp) +static int kvm_unmap_rmapp(struct kvm *kvm, unsigned long *rmapp, + unsigned long data) { u64 *spte; int need_tlb_flush = 0; @@ -763,8 +764,47 @@ static int kvm_unmap_rmapp(struct kvm *kvm, unsigned long *rmapp) return need_tlb_flush; } +static int kvm_set_pte_rmapp(struct kvm *kvm, unsigned long *rmapp, + unsigned long data) +{ + int need_flush = 0; + u64 *spte, new_spte; + pte_t *ptep = (pte_t *)data; + pfn_t new_pfn; + + WARN_ON(pte_huge(*ptep)); + new_pfn = pte_pfn(*ptep); + spte = rmap_next(kvm, rmapp, NULL); + while (spte) { + BUG_ON(!is_shadow_present_pte(*spte)); + rmap_printk("kvm_set_pte_rmapp: spte %p %llx\n", spte, *spte); + need_flush = 1; + if (pte_write(*ptep)) { + rmap_remove(kvm, spte); + __set_spte(spte, shadow_trap_nonpresent_pte); + spte = rmap_next(kvm, rmapp, NULL); + } else { + new_spte = *spte &~ (PT64_BASE_ADDR_MASK); + new_spte |= (u64)new_pfn << PAGE_SHIFT; + + new_spte &= ~PT_WRITABLE_MASK; + new_spte &= ~SPTE_HOST_WRITEABLE; + if (is_writeble_pte(*spte)) + kvm_set_pfn_dirty(spte_to_pfn(*spte)); + __set_spte(spte, new_spte); + spte = rmap_next(kvm, rmapp, spte); + } + } + if (need_flush) + kvm_flush_remote_tlbs(kvm); + + return 0; +} + static int kvm_handle_hva(struct kvm *kvm, unsigned long hva, - int (*handler)(struct kvm *kvm, unsigned long *rmapp)) + unsigned long data, + int (*handler)(struct kvm *kvm, unsigned long *rmapp, + unsigned long data)) { int i, j; int retval = 0; @@ -786,13 +826,15 @@ static int kvm_handle_hva(struct kvm *kvm, unsigned long hva, if (hva >= start && hva < end) { gfn_t gfn_offset = (hva - start) >> PAGE_SHIFT; - retval |= handler(kvm, &memslot->rmap[gfn_offset]); + retval |= handler(kvm, &memslot->rmap[gfn_offset], + data); for (j = 0; j < KVM_NR_PAGE_SIZES - 1; ++j) { int idx = gfn_offset; idx /= KVM_PAGES_PER_HPAGE(PT_DIRECTORY_LEVEL + j); retval |= handler(kvm, - &memslot->lpage_info[j][idx].rmap_pde); + &memslot->lpage_info[j][idx].rmap_pde, + data); } } } @@ -802,10 +844,16 @@ static int kvm_handle_hva(struct kvm *kvm, unsigned long hva, int kvm_unmap_hva(struct kvm *kvm, unsigned long hva) { - return kvm_handle_hva(kvm, hva, kvm_unmap_rmapp); + return kvm_handle_hva(kvm, hva, 0, kvm_unmap_rmapp); } -static int kvm_age_rmapp(struct kvm *kvm, unsigned long *rmapp) +void kvm_set_spte_hva(struct kvm *kvm, unsigned long hva, pte_t pte) +{ + kvm_handle_hva(kvm, hva, (unsigned long)&pte, kvm_set_pte_rmapp); +} + +static int kvm_age_rmapp(struct kvm *kvm, unsigned long *rmapp, + unsigned long data) { u64 *spte; int young = 0; @@ -841,13 +889,13 @@ static void rmap_recycle(struct kvm_vcpu *vcpu, u64 *spte, gfn_t gfn) gfn = unalias_gfn(vcpu->kvm, gfn); rmapp = gfn_to_rmap(vcpu->kvm, gfn, sp->role.level); - kvm_unmap_rmapp(vcpu->kvm, rmapp); + kvm_unmap_rmapp(vcpu->kvm, rmapp, 0); kvm_flush_remote_tlbs(vcpu->kvm); } int kvm_age_hva(struct kvm *kvm, unsigned long hva) { - return kvm_handle_hva(kvm, hva, kvm_age_rmapp); + return kvm_handle_hva(kvm, hva, 0, kvm_age_rmapp); } #ifdef MMU_DEBUG @@ -1756,7 +1804,7 @@ static int set_spte(struct kvm_vcpu *vcpu, u64 *sptep, unsigned pte_access, int user_fault, int write_fault, int dirty, int level, gfn_t gfn, pfn_t pfn, bool speculative, - bool can_unsync) + bool can_unsync, bool reset_host_protection) { u64 spte; int ret = 0; @@ -1783,6 +1831,9 @@ static int set_spte(struct kvm_vcpu *vcpu, u64 *sptep, spte |= kvm_x86_ops->get_mt_mask(vcpu, gfn, kvm_is_mmio_pfn(pfn)); + if (reset_host_protection) + spte |= SPTE_HOST_WRITEABLE; + spte |= (u64)pfn << PAGE_SHIFT; if ((pte_access & ACC_WRITE_MASK) @@ -1828,7 +1879,8 @@ static void mmu_set_spte(struct kvm_vcpu *vcpu, u64 *sptep, unsigned pt_access, unsigned pte_access, int user_fault, int write_fault, int dirty, int *ptwrite, int level, gfn_t gfn, - pfn_t pfn, bool speculative) + pfn_t pfn, bool speculative, + bool reset_host_protection) { int was_rmapped = 0; int was_writeble = is_writeble_pte(*sptep); @@ -1860,7 +1912,8 @@ static void mmu_set_spte(struct kvm_vcpu *vcpu, u64 *sptep, } if (set_spte(vcpu, sptep, pte_access, user_fault, write_fault, - dirty, level, gfn, pfn, speculative, true)) { + dirty, level, gfn, pfn, speculative, true, + reset_host_protection)) { if (write_fault) *ptwrite = 1; kvm_x86_ops->tlb_flush(vcpu); @@ -1877,8 +1930,7 @@ static void mmu_set_spte(struct kvm_vcpu *vcpu, u64 *sptep, page_header_update_slot(vcpu->kvm, sptep, gfn); if (!was_rmapped) { rmap_count = rmap_add(vcpu, sptep, gfn); - if (!is_rmap_spte(*sptep)) - kvm_release_pfn_clean(pfn); + kvm_release_pfn_clean(pfn); if (rmap_count > RMAP_RECYCLE_THRESHOLD) rmap_recycle(vcpu, sptep, gfn); } else { @@ -1909,7 +1961,7 @@ static int __direct_map(struct kvm_vcpu *vcpu, gpa_t v, int write, if (iterator.level == level) { mmu_set_spte(vcpu, iterator.sptep, ACC_ALL, ACC_ALL, 0, write, 1, &pt_write, - level, gfn, pfn, false); + level, gfn, pfn, false, true); ++vcpu->stat.pf_fixed; break; } diff --git a/arch/x86/kvm/paging_tmpl.h b/arch/x86/kvm/paging_tmpl.h index d2fec9c12d22..72558f8ff3f5 100644 --- a/arch/x86/kvm/paging_tmpl.h +++ b/arch/x86/kvm/paging_tmpl.h @@ -273,9 +273,13 @@ static void FNAME(update_pte)(struct kvm_vcpu *vcpu, struct kvm_mmu_page *page, if (mmu_notifier_retry(vcpu, vcpu->arch.update_pte.mmu_seq)) return; kvm_get_pfn(pfn); + /* + * we call mmu_set_spte() with reset_host_protection = true beacuse that + * vcpu->arch.update_pte.pfn was fetched from get_user_pages(write = 1). + */ mmu_set_spte(vcpu, spte, page->role.access, pte_access, 0, 0, gpte & PT_DIRTY_MASK, NULL, PT_PAGE_TABLE_LEVEL, - gpte_to_gfn(gpte), pfn, true); + gpte_to_gfn(gpte), pfn, true, true); } /* @@ -308,7 +312,7 @@ static u64 *FNAME(fetch)(struct kvm_vcpu *vcpu, gva_t addr, user_fault, write_fault, gw->ptes[gw->level-1] & PT_DIRTY_MASK, ptwrite, level, - gw->gfn, pfn, false); + gw->gfn, pfn, false, true); break; } @@ -558,6 +562,7 @@ static void FNAME(prefetch_page)(struct kvm_vcpu *vcpu, static int FNAME(sync_page)(struct kvm_vcpu *vcpu, struct kvm_mmu_page *sp) { int i, offset, nr_present; + bool reset_host_protection; offset = nr_present = 0; @@ -595,9 +600,16 @@ static int FNAME(sync_page)(struct kvm_vcpu *vcpu, struct kvm_mmu_page *sp) nr_present++; pte_access = sp->role.access & FNAME(gpte_access)(vcpu, gpte); + if (!(sp->spt[i] & SPTE_HOST_WRITEABLE)) { + pte_access &= ~ACC_WRITE_MASK; + reset_host_protection = 0; + } else { + reset_host_protection = 1; + } set_spte(vcpu, &sp->spt[i], pte_access, 0, 0, is_dirty_gpte(gpte), PT_PAGE_TABLE_LEVEL, gfn, - spte_to_pfn(sp->spt[i]), true, false); + spte_to_pfn(sp->spt[i]), true, false, + reset_host_protection); } return !nr_present; diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c index 944cc9c04b3c..c17404add91f 100644 --- a/arch/x86/kvm/svm.c +++ b/arch/x86/kvm/svm.c @@ -767,6 +767,8 @@ static void svm_vcpu_load(struct kvm_vcpu *vcpu, int cpu) rdtscll(tsc_this); delta = vcpu->arch.host_tsc - tsc_this; svm->vmcb->control.tsc_offset += delta; + if (is_nested(svm)) + svm->nested.hsave->control.tsc_offset += delta; vcpu->cpu = cpu; kvm_migrate_timers(vcpu); svm->asid_generation = 0; @@ -2057,10 +2059,14 @@ static int svm_get_msr(struct kvm_vcpu *vcpu, unsigned ecx, u64 *data) switch (ecx) { case MSR_IA32_TSC: { - u64 tsc; + u64 tsc_offset; + + if (is_nested(svm)) + tsc_offset = svm->nested.hsave->control.tsc_offset; + else + tsc_offset = svm->vmcb->control.tsc_offset; - rdtscll(tsc); - *data = svm->vmcb->control.tsc_offset + tsc; + *data = tsc_offset + native_read_tsc(); break; } case MSR_K6_STAR: @@ -2146,10 +2152,17 @@ static int svm_set_msr(struct kvm_vcpu *vcpu, unsigned ecx, u64 data) switch (ecx) { case MSR_IA32_TSC: { - u64 tsc; + u64 tsc_offset = data - native_read_tsc(); + u64 g_tsc_offset = 0; + + if (is_nested(svm)) { + g_tsc_offset = svm->vmcb->control.tsc_offset - + svm->nested.hsave->control.tsc_offset; + svm->nested.hsave->control.tsc_offset = tsc_offset; + } + + svm->vmcb->control.tsc_offset = tsc_offset + g_tsc_offset; - rdtscll(tsc); - svm->vmcb->control.tsc_offset = data - tsc; break; } case MSR_K6_STAR: diff --git a/arch/x86/kvm/vmx.c b/arch/x86/kvm/vmx.c index f3812014bd0b..ed53b42caba1 100644 --- a/arch/x86/kvm/vmx.c +++ b/arch/x86/kvm/vmx.c @@ -709,7 +709,7 @@ static void vmx_vcpu_load(struct kvm_vcpu *vcpu, int cpu) if (vcpu->cpu != cpu) { vcpu_clear(vmx); kvm_migrate_timers(vcpu); - vpid_sync_vcpu_all(vmx); + set_bit(KVM_REQ_TLB_FLUSH, &vcpu->requests); local_irq_disable(); list_add(&vmx->local_vcpus_link, &per_cpu(vcpus_on_cpu, cpu)); diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index be451ee44249..ae07d261527c 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -1591,6 +1591,8 @@ static int kvm_dev_ioctl_get_supported_cpuid(struct kvm_cpuid2 *cpuid, if (cpuid->nent < 1) goto out; + if (cpuid->nent > KVM_MAX_CPUID_ENTRIES) + cpuid->nent = KVM_MAX_CPUID_ENTRIES; r = -ENOMEM; cpuid_entries = vmalloc(sizeof(struct kvm_cpuid_entry2) * cpuid->nent); if (!cpuid_entries) @@ -1690,7 +1692,7 @@ static int kvm_vcpu_ioctl_x86_setup_mce(struct kvm_vcpu *vcpu, unsigned bank_num = mcg_cap & 0xff, bank; r = -EINVAL; - if (!bank_num) + if (!bank_num || bank_num >= KVM_MAX_MCE_BANKS) goto out; if (mcg_cap & ~(KVM_MCE_CAP_SUPPORTED | 0xff | 0xff0000)) goto out; @@ -4049,7 +4051,7 @@ static int save_guest_segment_descriptor(struct kvm_vcpu *vcpu, u16 selector, return kvm_write_guest_virt(dtable.base + index*8, seg_desc, sizeof(*seg_desc), vcpu); } -static u32 get_tss_base_addr(struct kvm_vcpu *vcpu, +static gpa_t get_tss_base_addr(struct kvm_vcpu *vcpu, struct desc_struct *seg_desc) { u32 base_addr = get_desc_base(seg_desc); diff --git a/arch/x86/lib/Makefile b/arch/x86/lib/Makefile index 3e549b8ec8c9..85f5db95c60f 100644 --- a/arch/x86/lib/Makefile +++ b/arch/x86/lib/Makefile @@ -15,8 +15,10 @@ ifeq ($(CONFIG_X86_32),y) obj-y += atomic64_32.o lib-y += checksum_32.o lib-y += strstr_32.o - lib-y += semaphore_32.o string_32.o cmpxchg8b_emu.o - + lib-y += semaphore_32.o string_32.o +ifneq ($(CONFIG_X86_CMPXCHG64),y) + lib-y += cmpxchg8b_emu.o +endif lib-$(CONFIG_X86_USE_3DNOW) += mmx_32.o else obj-y += io_64.o iomap_copy_64.o diff --git a/arch/x86/mm/ioremap.c b/arch/x86/mm/ioremap.c index 334e63ca7b2b..2feb9bdedaaf 100644 --- a/arch/x86/mm/ioremap.c +++ b/arch/x86/mm/ioremap.c @@ -170,8 +170,7 @@ static void __iomem *__ioremap_caller(resource_size_t phys_addr, (unsigned long long)phys_addr, (unsigned long long)(phys_addr + size), prot_val, new_prot_val); - free_memtype(phys_addr, phys_addr + size); - return NULL; + goto err_free_memtype; } prot_val = new_prot_val; } @@ -197,26 +196,25 @@ static void __iomem *__ioremap_caller(resource_size_t phys_addr, */ area = get_vm_area_caller(size, VM_IOREMAP, caller); if (!area) - return NULL; + goto err_free_memtype; area->phys_addr = phys_addr; vaddr = (unsigned long) area->addr; - if (kernel_map_sync_memtype(phys_addr, size, prot_val)) { - free_memtype(phys_addr, phys_addr + size); - free_vm_area(area); - return NULL; - } + if (kernel_map_sync_memtype(phys_addr, size, prot_val)) + goto err_free_area; - if (ioremap_page_range(vaddr, vaddr + size, phys_addr, prot)) { - free_memtype(phys_addr, phys_addr + size); - free_vm_area(area); - return NULL; - } + if (ioremap_page_range(vaddr, vaddr + size, phys_addr, prot)) + goto err_free_area; ret_addr = (void __iomem *) (vaddr + offset); mmiotrace_ioremap(unaligned_phys_addr, unaligned_size, ret_addr); return ret_addr; +err_free_area: + free_vm_area(area); +err_free_memtype: + free_memtype(phys_addr, phys_addr + size); + return NULL; } /** diff --git a/arch/x86/xen/enlighten.c b/arch/x86/xen/enlighten.c index 3439616d69f1..dfbf70e65860 100644 --- a/arch/x86/xen/enlighten.c +++ b/arch/x86/xen/enlighten.c @@ -178,6 +178,7 @@ static __read_mostly unsigned int cpuid_leaf1_ecx_mask = ~0; static void xen_cpuid(unsigned int *ax, unsigned int *bx, unsigned int *cx, unsigned int *dx) { + unsigned maskebx = ~0; unsigned maskecx = ~0; unsigned maskedx = ~0; @@ -185,9 +186,16 @@ static void xen_cpuid(unsigned int *ax, unsigned int *bx, * Mask out inconvenient features, to try and disable as many * unsupported kernel subsystems as possible. */ - if (*ax == 1) { + switch (*ax) { + case 1: maskecx = cpuid_leaf1_ecx_mask; maskedx = cpuid_leaf1_edx_mask; + break; + + case 0xb: + /* Suppress extended topology stuff */ + maskebx = 0; + break; } asm(XEN_EMULATE_PREFIX "cpuid" @@ -197,6 +205,7 @@ static void xen_cpuid(unsigned int *ax, unsigned int *bx, "=d" (*dx) : "0" (*ax), "2" (*cx)); + *bx &= maskebx; *cx &= maskecx; *dx &= maskedx; } @@ -1075,6 +1084,8 @@ asmlinkage void __init xen_start_kernel(void) * Set up some pagetable state before starting to set any ptes. */ + xen_init_mmu_ops(); + /* Prevent unwanted bits from being set in PTEs. */ __supported_pte_mask &= ~_PAGE_GLOBAL; if (!xen_initial_domain()) @@ -1099,7 +1110,6 @@ asmlinkage void __init xen_start_kernel(void) */ xen_setup_stackprotector(); - xen_init_mmu_ops(); xen_init_irq_ops(); xen_init_cpuid_mask(); diff --git a/arch/xtensa/kernel/time.c b/arch/xtensa/kernel/time.c index 19085ff0484a..19f7df30937f 100644 --- a/arch/xtensa/kernel/time.c +++ b/arch/xtensa/kernel/time.c @@ -13,6 +13,7 @@ */ #include <linux/errno.h> +#include <linux/sched.h> #include <linux/time.h> #include <linux/clocksource.h> #include <linux/interrupt.h> diff --git a/block/blk-core.c b/block/blk-core.c index 81f34311659a..71da5111120c 100644 --- a/block/blk-core.c +++ b/block/blk-core.c @@ -70,7 +70,7 @@ static void drive_stat_acct(struct request *rq, int new_io) part_stat_inc(cpu, part, merges[rw]); else { part_round_stats(cpu, part); - part_inc_in_flight(part); + part_inc_in_flight(part, rw); } part_stat_unlock(); @@ -1030,9 +1030,9 @@ static void part_round_stats_single(int cpu, struct hd_struct *part, if (now == part->stamp) return; - if (part->in_flight) { + if (part_in_flight(part)) { __part_stat_add(cpu, part, time_in_queue, - part->in_flight * (now - part->stamp)); + part_in_flight(part) * (now - part->stamp)); __part_stat_add(cpu, part, io_ticks, (now - part->stamp)); } part->stamp = now; @@ -1161,7 +1161,7 @@ static int __make_request(struct request_queue *q, struct bio *bio) const unsigned int ff = bio->bi_rw & REQ_FAILFAST_MASK; int rw_flags; - if (bio_rw_flagged(bio, BIO_RW_BARRIER) && bio_has_data(bio) && + if (bio_rw_flagged(bio, BIO_RW_BARRIER) && (q->next_ordered == QUEUE_ORDERED_NONE)) { bio_endio(bio, -EOPNOTSUPP); return 0; @@ -1739,7 +1739,7 @@ static void blk_account_io_done(struct request *req) part_stat_inc(cpu, part, ios[rw]); part_stat_add(cpu, part, ticks[rw], duration); part_round_stats(cpu, part); - part_dec_in_flight(part); + part_dec_in_flight(part, rw); part_stat_unlock(); } @@ -2492,14 +2492,6 @@ int kblockd_schedule_work(struct request_queue *q, struct work_struct *work) } EXPORT_SYMBOL(kblockd_schedule_work); -int kblockd_schedule_delayed_work(struct request_queue *q, - struct delayed_work *work, - unsigned long delay) -{ - return queue_delayed_work(kblockd_workqueue, work, delay); -} -EXPORT_SYMBOL(kblockd_schedule_delayed_work); - int __init blk_dev_init(void) { BUILD_BUG_ON(__REQ_NR_BITS > 8 * diff --git a/block/blk-merge.c b/block/blk-merge.c index b0de8574fdc8..99cb5cf1f447 100644 --- a/block/blk-merge.c +++ b/block/blk-merge.c @@ -351,7 +351,7 @@ static void blk_account_io_merge(struct request *req) part = disk_map_sector_rcu(req->rq_disk, blk_rq_pos(req)); part_round_stats(cpu, part); - part_dec_in_flight(part); + part_dec_in_flight(part, rq_data_dir(req)); part_stat_unlock(); } diff --git a/block/blk-settings.c b/block/blk-settings.c index e0695bca7027..66d4aa8799b7 100644 --- a/block/blk-settings.c +++ b/block/blk-settings.c @@ -242,7 +242,7 @@ EXPORT_SYMBOL(blk_queue_max_hw_sectors); /** * blk_queue_max_discard_sectors - set max sectors for a single discard * @q: the request queue for the device - * @max_discard: maximum number of sectors to discard + * @max_discard_sectors: maximum number of sectors to discard **/ void blk_queue_max_discard_sectors(struct request_queue *q, unsigned int max_discard_sectors) diff --git a/block/blk-tag.c b/block/blk-tag.c index 2e5cfeb59333..6b0f52c20964 100644 --- a/block/blk-tag.c +++ b/block/blk-tag.c @@ -359,7 +359,7 @@ int blk_queue_start_tag(struct request_queue *q, struct request *rq) max_depth -= 2; if (!max_depth) max_depth = 1; - if (q->in_flight[0] > max_depth) + if (q->in_flight[BLK_RW_ASYNC] > max_depth) return 1; } diff --git a/block/cfq-iosched.c b/block/cfq-iosched.c index 9c4b679908f4..aa1e9535e358 100644 --- a/block/cfq-iosched.c +++ b/block/cfq-iosched.c @@ -150,7 +150,7 @@ struct cfq_data { * idle window management */ struct timer_list idle_slice_timer; - struct delayed_work unplug_work; + struct work_struct unplug_work; struct cfq_queue *active_queue; struct cfq_io_context *active_cic; @@ -196,6 +196,7 @@ enum cfqq_state_flags { CFQ_CFQQ_FLAG_slice_new, /* no requests dispatched in slice */ CFQ_CFQQ_FLAG_sync, /* synchronous queue */ CFQ_CFQQ_FLAG_coop, /* has done a coop jump of the queue */ + CFQ_CFQQ_FLAG_coop_preempt, /* coop preempt */ }; #define CFQ_CFQQ_FNS(name) \ @@ -222,6 +223,7 @@ CFQ_CFQQ_FNS(prio_changed); CFQ_CFQQ_FNS(slice_new); CFQ_CFQQ_FNS(sync); CFQ_CFQQ_FNS(coop); +CFQ_CFQQ_FNS(coop_preempt); #undef CFQ_CFQQ_FNS #define cfq_log_cfqq(cfqd, cfqq, fmt, args...) \ @@ -230,7 +232,7 @@ CFQ_CFQQ_FNS(coop); blk_add_trace_msg((cfqd)->queue, "cfq " fmt, ##args) static void cfq_dispatch_insert(struct request_queue *, struct request *); -static struct cfq_queue *cfq_get_queue(struct cfq_data *, int, +static struct cfq_queue *cfq_get_queue(struct cfq_data *, bool, struct io_context *, gfp_t); static struct cfq_io_context *cfq_cic_lookup(struct cfq_data *, struct io_context *); @@ -241,40 +243,35 @@ static inline int rq_in_driver(struct cfq_data *cfqd) } static inline struct cfq_queue *cic_to_cfqq(struct cfq_io_context *cic, - int is_sync) + bool is_sync) { - return cic->cfqq[!!is_sync]; + return cic->cfqq[is_sync]; } static inline void cic_set_cfqq(struct cfq_io_context *cic, - struct cfq_queue *cfqq, int is_sync) + struct cfq_queue *cfqq, bool is_sync) { - cic->cfqq[!!is_sync] = cfqq; + cic->cfqq[is_sync] = cfqq; } /* * We regard a request as SYNC, if it's either a read or has the SYNC bit * set (in which case it could also be direct WRITE). */ -static inline int cfq_bio_sync(struct bio *bio) +static inline bool cfq_bio_sync(struct bio *bio) { - if (bio_data_dir(bio) == READ || bio_rw_flagged(bio, BIO_RW_SYNCIO)) - return 1; - - return 0; + return bio_data_dir(bio) == READ || bio_rw_flagged(bio, BIO_RW_SYNCIO); } /* * scheduler run of queue, if there are requests pending and no one in the * driver that will restart queueing */ -static inline void cfq_schedule_dispatch(struct cfq_data *cfqd, - unsigned long delay) +static inline void cfq_schedule_dispatch(struct cfq_data *cfqd) { if (cfqd->busy_queues) { cfq_log(cfqd, "schedule dispatch"); - kblockd_schedule_delayed_work(cfqd->queue, &cfqd->unplug_work, - delay); + kblockd_schedule_work(cfqd->queue, &cfqd->unplug_work); } } @@ -290,7 +287,7 @@ static int cfq_queue_empty(struct request_queue *q) * if a queue is marked sync and has sync io queued. A sync queue with async * io only, should not get full sync slice length. */ -static inline int cfq_prio_slice(struct cfq_data *cfqd, int sync, +static inline int cfq_prio_slice(struct cfq_data *cfqd, bool sync, unsigned short prio) { const int base_slice = cfqd->cfq_slice[sync]; @@ -318,7 +315,7 @@ cfq_set_prio_slice(struct cfq_data *cfqd, struct cfq_queue *cfqq) * isn't valid until the first request from the dispatch is activated * and the slice time set. */ -static inline int cfq_slice_used(struct cfq_queue *cfqq) +static inline bool cfq_slice_used(struct cfq_queue *cfqq) { if (cfq_cfqq_slice_new(cfqq)) return 0; @@ -493,7 +490,7 @@ static unsigned long cfq_slice_offset(struct cfq_data *cfqd, * we will service the queues. */ static void cfq_service_tree_add(struct cfq_data *cfqd, struct cfq_queue *cfqq, - int add_front) + bool add_front) { struct rb_node **p, *parent; struct cfq_queue *__cfqq; @@ -509,11 +506,20 @@ static void cfq_service_tree_add(struct cfq_data *cfqd, struct cfq_queue *cfqq, } else rb_key += jiffies; } else if (!add_front) { + /* + * Get our rb key offset. Subtract any residual slice + * value carried from last service. A negative resid + * count indicates slice overrun, and this should position + * the next service time further away in the tree. + */ rb_key = cfq_slice_offset(cfqd, cfqq) + jiffies; - rb_key += cfqq->slice_resid; + rb_key -= cfqq->slice_resid; cfqq->slice_resid = 0; - } else - rb_key = 0; + } else { + rb_key = -HZ; + __cfqq = cfq_rb_first(&cfqd->service_tree); + rb_key += __cfqq ? __cfqq->rb_key : jiffies; + } if (!RB_EMPTY_NODE(&cfqq->rb_node)) { /* @@ -547,7 +553,7 @@ static void cfq_service_tree_add(struct cfq_data *cfqd, struct cfq_queue *cfqq, n = &(*p)->rb_left; else if (cfq_class_idle(cfqq) > cfq_class_idle(__cfqq)) n = &(*p)->rb_right; - else if (rb_key < __cfqq->rb_key) + else if (time_before(rb_key, __cfqq->rb_key)) n = &(*p)->rb_left; else n = &(*p)->rb_right; @@ -827,8 +833,10 @@ cfq_merged_requests(struct request_queue *q, struct request *rq, * reposition in fifo if next is older than rq */ if (!list_empty(&rq->queuelist) && !list_empty(&next->queuelist) && - time_before(next->start_time, rq->start_time)) + time_before(rq_fifo_time(next), rq_fifo_time(rq))) { list_move(&rq->queuelist, &next->queuelist); + rq_set_fifo_time(rq, rq_fifo_time(next)); + } cfq_remove_request(next); } @@ -844,7 +852,7 @@ static int cfq_allow_merge(struct request_queue *q, struct request *rq, * Disallow merge of a sync bio into an async request. */ if (cfq_bio_sync(bio) && !rq_is_sync(rq)) - return 0; + return false; /* * Lookup the cfqq that this bio will be queued with. Allow @@ -852,13 +860,10 @@ static int cfq_allow_merge(struct request_queue *q, struct request *rq, */ cic = cfq_cic_lookup(cfqd, current->io_context); if (!cic) - return 0; + return false; cfqq = cic_to_cfqq(cic, cfq_bio_sync(bio)); - if (cfqq == RQ_CFQQ(rq)) - return 1; - - return 0; + return cfqq == RQ_CFQQ(rq); } static void __cfq_set_active_queue(struct cfq_data *cfqd, @@ -886,7 +891,7 @@ static void __cfq_set_active_queue(struct cfq_data *cfqd, */ static void __cfq_slice_expired(struct cfq_data *cfqd, struct cfq_queue *cfqq, - int timed_out) + bool timed_out) { cfq_log_cfqq(cfqd, cfqq, "slice expired t=%d", timed_out); @@ -914,7 +919,7 @@ __cfq_slice_expired(struct cfq_data *cfqd, struct cfq_queue *cfqq, } } -static inline void cfq_slice_expired(struct cfq_data *cfqd, int timed_out) +static inline void cfq_slice_expired(struct cfq_data *cfqd, bool timed_out) { struct cfq_queue *cfqq = cfqd->active_queue; @@ -942,10 +947,13 @@ static struct cfq_queue *cfq_set_active_queue(struct cfq_data *cfqd, { if (!cfqq) { cfqq = cfq_get_next_queue(cfqd); - if (cfqq) + if (cfqq && !cfq_cfqq_coop_preempt(cfqq)) cfq_clear_cfqq_coop(cfqq); } + if (cfqq) + cfq_clear_cfqq_coop_preempt(cfqq); + __cfq_set_active_queue(cfqd, cfqq); return cfqq; } @@ -1026,7 +1034,7 @@ static struct cfq_queue *cfqq_close(struct cfq_data *cfqd, */ static struct cfq_queue *cfq_close_cooperator(struct cfq_data *cfqd, struct cfq_queue *cur_cfqq, - int probe) + bool probe) { struct cfq_queue *cfqq; @@ -1090,6 +1098,15 @@ static void cfq_arm_slice_timer(struct cfq_data *cfqd) if (!cic || !atomic_read(&cic->ioc->nr_tasks)) return; + /* + * If our average think time is larger than the remaining time + * slice, then don't idle. This avoids overrunning the allotted + * time slice. + */ + if (sample_valid(cic->ttime_samples) && + (cfqq->slice_end - jiffies < cic->ttime_mean)) + return; + cfq_mark_cfqq_wait_request(cfqq); /* @@ -1129,9 +1146,7 @@ static void cfq_dispatch_insert(struct request_queue *q, struct request *rq) */ static struct request *cfq_check_fifo(struct cfq_queue *cfqq) { - struct cfq_data *cfqd = cfqq->cfqd; - struct request *rq; - int fifo; + struct request *rq = NULL; if (cfq_cfqq_fifo_expire(cfqq)) return NULL; @@ -1141,13 +1156,11 @@ static struct request *cfq_check_fifo(struct cfq_queue *cfqq) if (list_empty(&cfqq->fifo)) return NULL; - fifo = cfq_cfqq_sync(cfqq); rq = rq_entry_fifo(cfqq->fifo.next); - - if (time_before(jiffies, rq->start_time + cfqd->cfq_fifo_expire[fifo])) + if (time_before(jiffies, rq_fifo_time(rq))) rq = NULL; - cfq_log_cfqq(cfqd, cfqq, "fifo=%p", rq); + cfq_log_cfqq(cfqq->cfqd, cfqq, "fifo=%p", rq); return rq; } @@ -1248,67 +1261,21 @@ static int cfq_forced_dispatch(struct cfq_data *cfqd) return dispatched; } -/* - * Dispatch a request from cfqq, moving them to the request queue - * dispatch list. - */ -static void cfq_dispatch_request(struct cfq_data *cfqd, struct cfq_queue *cfqq) -{ - struct request *rq; - - BUG_ON(RB_EMPTY_ROOT(&cfqq->sort_list)); - - /* - * follow expired path, else get first next available - */ - rq = cfq_check_fifo(cfqq); - if (!rq) - rq = cfqq->next_rq; - - /* - * insert request into driver dispatch list - */ - cfq_dispatch_insert(cfqd->queue, rq); - - if (!cfqd->active_cic) { - struct cfq_io_context *cic = RQ_CIC(rq); - - atomic_long_inc(&cic->ioc->refcount); - cfqd->active_cic = cic; - } -} - -/* - * Find the cfqq that we need to service and move a request from that to the - * dispatch list - */ -static int cfq_dispatch_requests(struct request_queue *q, int force) +static bool cfq_may_dispatch(struct cfq_data *cfqd, struct cfq_queue *cfqq) { - struct cfq_data *cfqd = q->elevator->elevator_data; - struct cfq_queue *cfqq; unsigned int max_dispatch; - if (!cfqd->busy_queues) - return 0; - - if (unlikely(force)) - return cfq_forced_dispatch(cfqd); - - cfqq = cfq_select_queue(cfqd); - if (!cfqq) - return 0; - /* * Drain async requests before we start sync IO */ if (cfq_cfqq_idle_window(cfqq) && cfqd->rq_in_driver[BLK_RW_ASYNC]) - return 0; + return false; /* * If this is an async queue and we have sync IO in flight, let it wait */ if (cfqd->sync_flight && !cfq_cfqq_sync(cfqq)) - return 0; + return false; max_dispatch = cfqd->cfq_quantum; if (cfq_class_idle(cfqq)) @@ -1322,13 +1289,13 @@ static int cfq_dispatch_requests(struct request_queue *q, int force) * idle queue must always only have a single IO in flight */ if (cfq_class_idle(cfqq)) - return 0; + return false; /* * We have other queues, don't allow more IO from this one */ if (cfqd->busy_queues > 1) - return 0; + return false; /* * Sole queue user, allow bigger slice @@ -1352,13 +1319,72 @@ static int cfq_dispatch_requests(struct request_queue *q, int force) max_dispatch = depth; } - if (cfqq->dispatched >= max_dispatch) + /* + * If we're below the current max, allow a dispatch + */ + return cfqq->dispatched < max_dispatch; +} + +/* + * Dispatch a request from cfqq, moving them to the request queue + * dispatch list. + */ +static bool cfq_dispatch_request(struct cfq_data *cfqd, struct cfq_queue *cfqq) +{ + struct request *rq; + + BUG_ON(RB_EMPTY_ROOT(&cfqq->sort_list)); + + if (!cfq_may_dispatch(cfqd, cfqq)) + return false; + + /* + * follow expired path, else get first next available + */ + rq = cfq_check_fifo(cfqq); + if (!rq) + rq = cfqq->next_rq; + + /* + * insert request into driver dispatch list + */ + cfq_dispatch_insert(cfqd->queue, rq); + + if (!cfqd->active_cic) { + struct cfq_io_context *cic = RQ_CIC(rq); + + atomic_long_inc(&cic->ioc->refcount); + cfqd->active_cic = cic; + } + + return true; +} + +/* + * Find the cfqq that we need to service and move a request from that to the + * dispatch list + */ +static int cfq_dispatch_requests(struct request_queue *q, int force) +{ + struct cfq_data *cfqd = q->elevator->elevator_data; + struct cfq_queue *cfqq; + + if (!cfqd->busy_queues) + return 0; + + if (unlikely(force)) + return cfq_forced_dispatch(cfqd); + + cfqq = cfq_select_queue(cfqd); + if (!cfqq) return 0; /* - * Dispatch a request from this cfqq + * Dispatch a request from this cfqq, if it is allowed */ - cfq_dispatch_request(cfqd, cfqq); + if (!cfq_dispatch_request(cfqd, cfqq)) + return 0; + cfqq->slice_dispatch++; cfq_clear_cfqq_must_dispatch(cfqq); @@ -1399,7 +1425,7 @@ static void cfq_put_queue(struct cfq_queue *cfqq) if (unlikely(cfqd->active_queue == cfqq)) { __cfq_slice_expired(cfqd, cfqq, 0); - cfq_schedule_dispatch(cfqd, 0); + cfq_schedule_dispatch(cfqd); } kmem_cache_free(cfq_pool, cfqq); @@ -1494,7 +1520,7 @@ static void cfq_exit_cfqq(struct cfq_data *cfqd, struct cfq_queue *cfqq) { if (unlikely(cfqq == cfqd->active_queue)) { __cfq_slice_expired(cfqd, cfqq, 0); - cfq_schedule_dispatch(cfqd, 0); + cfq_schedule_dispatch(cfqd); } cfq_put_queue(cfqq); @@ -1658,7 +1684,7 @@ static void cfq_ioc_set_ioprio(struct io_context *ioc) } static void cfq_init_cfqq(struct cfq_data *cfqd, struct cfq_queue *cfqq, - pid_t pid, int is_sync) + pid_t pid, bool is_sync) { RB_CLEAR_NODE(&cfqq->rb_node); RB_CLEAR_NODE(&cfqq->p_node); @@ -1678,7 +1704,7 @@ static void cfq_init_cfqq(struct cfq_data *cfqd, struct cfq_queue *cfqq, } static struct cfq_queue * -cfq_find_alloc_queue(struct cfq_data *cfqd, int is_sync, +cfq_find_alloc_queue(struct cfq_data *cfqd, bool is_sync, struct io_context *ioc, gfp_t gfp_mask) { struct cfq_queue *cfqq, *new_cfqq = NULL; @@ -1742,7 +1768,7 @@ cfq_async_queue_prio(struct cfq_data *cfqd, int ioprio_class, int ioprio) } static struct cfq_queue * -cfq_get_queue(struct cfq_data *cfqd, int is_sync, struct io_context *ioc, +cfq_get_queue(struct cfq_data *cfqd, bool is_sync, struct io_context *ioc, gfp_t gfp_mask) { const int ioprio = task_ioprio(ioc); @@ -1977,7 +2003,10 @@ cfq_update_idle_window(struct cfq_data *cfqd, struct cfq_queue *cfqq, (!cfqd->cfq_latency && cfqd->hw_tag && CIC_SEEKY(cic))) enable_idle = 0; else if (sample_valid(cic->ttime_samples)) { - if (cic->ttime_mean > cfqd->cfq_slice_idle) + unsigned int slice_idle = cfqd->cfq_slice_idle; + if (sample_valid(cic->seek_samples) && CIC_SEEKY(cic)) + slice_idle = msecs_to_jiffies(CFQ_MIN_TT); + if (cic->ttime_mean > slice_idle) enable_idle = 0; else enable_idle = 1; @@ -1996,7 +2025,7 @@ cfq_update_idle_window(struct cfq_data *cfqd, struct cfq_queue *cfqq, * Check if new_cfqq should preempt the currently active queue. Return 0 for * no or if we aren't sure, a 1 will cause a preempt. */ -static int +static bool cfq_should_preempt(struct cfq_data *cfqd, struct cfq_queue *new_cfqq, struct request *rq) { @@ -2004,48 +2033,56 @@ cfq_should_preempt(struct cfq_data *cfqd, struct cfq_queue *new_cfqq, cfqq = cfqd->active_queue; if (!cfqq) - return 0; + return false; if (cfq_slice_used(cfqq)) - return 1; + return true; if (cfq_class_idle(new_cfqq)) - return 0; + return false; if (cfq_class_idle(cfqq)) - return 1; + return true; /* * if the new request is sync, but the currently running queue is * not, let the sync request have priority. */ if (rq_is_sync(rq) && !cfq_cfqq_sync(cfqq)) - return 1; + return true; /* * So both queues are sync. Let the new request get disk time if * it's a metadata request and the current queue is doing regular IO. */ if (rq_is_meta(rq) && !cfqq->meta_pending) - return 1; + return true; /* * Allow an RT request to pre-empt an ongoing non-RT cfqq timeslice. */ if (cfq_class_rt(new_cfqq) && !cfq_class_rt(cfqq)) - return 1; + return true; if (!cfqd->active_cic || !cfq_cfqq_wait_request(cfqq)) - return 0; + return false; /* * if this request is as-good as one we would expect from the * current cfqq, let it preempt */ - if (cfq_rq_close(cfqd, rq)) - return 1; + if (cfq_rq_close(cfqd, rq) && (!cfq_cfqq_coop(new_cfqq) || + cfqd->busy_queues == 1)) { + /* + * Mark new queue coop_preempt, so its coop flag will not be + * cleared when new queue gets scheduled at the very first time + */ + cfq_mark_cfqq_coop_preempt(new_cfqq); + cfq_mark_cfqq_coop(new_cfqq); + return true; + } - return 0; + return false; } /* @@ -2130,6 +2167,7 @@ static void cfq_insert_request(struct request_queue *q, struct request *rq) cfq_add_rq_rb(rq); + rq_set_fifo_time(rq, jiffies + cfqd->cfq_fifo_expire[rq_is_sync(rq)]); list_add_tail(&rq->queuelist, &cfqq->fifo); cfq_rq_enqueued(cfqd, cfqq, rq); @@ -2211,7 +2249,7 @@ static void cfq_completed_request(struct request_queue *q, struct request *rq) } if (!rq_in_driver(cfqd)) - cfq_schedule_dispatch(cfqd, 0); + cfq_schedule_dispatch(cfqd); } /* @@ -2309,7 +2347,7 @@ cfq_set_request(struct request_queue *q, struct request *rq, gfp_t gfp_mask) struct cfq_data *cfqd = q->elevator->elevator_data; struct cfq_io_context *cic; const int rw = rq_data_dir(rq); - const int is_sync = rq_is_sync(rq); + const bool is_sync = rq_is_sync(rq); struct cfq_queue *cfqq; unsigned long flags; @@ -2341,7 +2379,7 @@ queue_fail: if (cic) put_io_context(cic->ioc); - cfq_schedule_dispatch(cfqd, 0); + cfq_schedule_dispatch(cfqd); spin_unlock_irqrestore(q->queue_lock, flags); cfq_log(cfqd, "set_request fail"); return 1; @@ -2350,7 +2388,7 @@ queue_fail: static void cfq_kick_queue(struct work_struct *work) { struct cfq_data *cfqd = - container_of(work, struct cfq_data, unplug_work.work); + container_of(work, struct cfq_data, unplug_work); struct request_queue *q = cfqd->queue; spin_lock_irq(q->queue_lock); @@ -2404,7 +2442,7 @@ static void cfq_idle_slice_timer(unsigned long data) expire: cfq_slice_expired(cfqd, timed_out); out_kick: - cfq_schedule_dispatch(cfqd, 0); + cfq_schedule_dispatch(cfqd); out_cont: spin_unlock_irqrestore(cfqd->queue->queue_lock, flags); } @@ -2412,7 +2450,7 @@ out_cont: static void cfq_shutdown_timer_wq(struct cfq_data *cfqd) { del_timer_sync(&cfqd->idle_slice_timer); - cancel_delayed_work_sync(&cfqd->unplug_work); + cancel_work_sync(&cfqd->unplug_work); } static void cfq_put_async_queues(struct cfq_data *cfqd) @@ -2494,7 +2532,7 @@ static void *cfq_init_queue(struct request_queue *q) cfqd->idle_slice_timer.function = cfq_idle_slice_timer; cfqd->idle_slice_timer.data = (unsigned long) cfqd; - INIT_DELAYED_WORK(&cfqd->unplug_work, cfq_kick_queue); + INIT_WORK(&cfqd->unplug_work, cfq_kick_queue); cfqd->cfq_quantum = cfq_quantum; cfqd->cfq_fifo_expire[0] = cfq_fifo_expire[0]; diff --git a/block/elevator.c b/block/elevator.c index 1975b619c86d..a847046c6e53 100644 --- a/block/elevator.c +++ b/block/elevator.c @@ -1059,9 +1059,7 @@ ssize_t elv_iosched_store(struct request_queue *q, const char *name, return count; strlcpy(elevator_name, name, sizeof(elevator_name)); - strstrip(elevator_name); - - e = elevator_get(elevator_name); + e = elevator_get(strstrip(elevator_name)); if (!e) { printk(KERN_ERR "elevator: type %s not found\n", elevator_name); return -EINVAL; diff --git a/block/genhd.c b/block/genhd.c index 5a0861da324d..517e4332cb37 100644 --- a/block/genhd.c +++ b/block/genhd.c @@ -869,6 +869,7 @@ static DEVICE_ATTR(size, S_IRUGO, part_size_show, NULL); static DEVICE_ATTR(alignment_offset, S_IRUGO, disk_alignment_offset_show, NULL); static DEVICE_ATTR(capability, S_IRUGO, disk_capability_show, NULL); static DEVICE_ATTR(stat, S_IRUGO, part_stat_show, NULL); +static DEVICE_ATTR(inflight, S_IRUGO, part_inflight_show, NULL); #ifdef CONFIG_FAIL_MAKE_REQUEST static struct device_attribute dev_attr_fail = __ATTR(make-it-fail, S_IRUGO|S_IWUSR, part_fail_show, part_fail_store); @@ -888,6 +889,7 @@ static struct attribute *disk_attrs[] = { &dev_attr_alignment_offset.attr, &dev_attr_capability.attr, &dev_attr_stat.attr, + &dev_attr_inflight.attr, #ifdef CONFIG_FAIL_MAKE_REQUEST &dev_attr_fail.attr, #endif @@ -1053,7 +1055,7 @@ static int diskstats_show(struct seq_file *seqf, void *v) part_stat_read(hd, merges[1]), (unsigned long long)part_stat_read(hd, sectors[1]), jiffies_to_msecs(part_stat_read(hd, ticks[1])), - hd->in_flight, + part_in_flight(hd), jiffies_to_msecs(part_stat_read(hd, io_ticks)), jiffies_to_msecs(part_stat_read(hd, time_in_queue)) ); diff --git a/crypto/aead.c b/crypto/aead.c index d9aa733db164..0a55da70845e 100644 --- a/crypto/aead.c +++ b/crypto/aead.c @@ -18,6 +18,7 @@ #include <linux/kernel.h> #include <linux/module.h> #include <linux/rtnetlink.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/seq_file.h> diff --git a/crypto/async_tx/async_pq.c b/crypto/async_tx/async_pq.c index b88db6d1dc65..6b5cc4fba59f 100644 --- a/crypto/async_tx/async_pq.c +++ b/crypto/async_tx/async_pq.c @@ -26,14 +26,10 @@ #include <linux/async_tx.h> /** - * scribble - space to hold throwaway P buffer for synchronous gen_syndrome + * pq_scribble_page - space to hold throwaway P or Q buffer for + * synchronous gen_syndrome */ -static struct page *scribble; - -static bool is_raid6_zero_block(struct page *p) -{ - return p == (void *) raid6_empty_zero_page; -} +static struct page *pq_scribble_page; /* the struct page *blocks[] parameter passed to async_gen_syndrome() * and async_syndrome_val() contains the 'P' destination address at @@ -83,7 +79,7 @@ do_async_gen_syndrome(struct dma_chan *chan, struct page **blocks, * sources and update the coefficients accordingly */ for (i = 0, idx = 0; i < src_cnt; i++) { - if (is_raid6_zero_block(blocks[i])) + if (blocks[i] == NULL) continue; dma_src[idx] = dma_map_page(dma->dev, blocks[i], offset, len, DMA_TO_DEVICE); @@ -160,9 +156,9 @@ do_sync_gen_syndrome(struct page **blocks, unsigned int offset, int disks, srcs = (void **) blocks; for (i = 0; i < disks; i++) { - if (is_raid6_zero_block(blocks[i])) { + if (blocks[i] == NULL) { BUG_ON(i > disks - 3); /* P or Q can't be zero */ - srcs[i] = blocks[i]; + srcs[i] = (void*)raid6_empty_zero_page; } else srcs[i] = page_address(blocks[i]) + offset; } @@ -186,10 +182,14 @@ do_sync_gen_syndrome(struct page **blocks, unsigned int offset, int disks, * blocks[disks-1] to NULL. When P or Q is omitted 'len' must be <= * PAGE_SIZE as a temporary buffer of this size is used in the * synchronous path. 'disks' always accounts for both destination - * buffers. + * buffers. If any source buffers (blocks[i] where i < disks - 2) are + * set to NULL those buffers will be replaced with the raid6_zero_page + * in the synchronous path and omitted in the hardware-asynchronous + * path. * * 'blocks' note: if submit->scribble is NULL then the contents of - * 'blocks' may be overridden + * 'blocks' may be overwritten to perform address conversions + * (dma_map_page() or page_address()). */ struct dma_async_tx_descriptor * async_gen_syndrome(struct page **blocks, unsigned int offset, int disks, @@ -227,11 +227,11 @@ async_gen_syndrome(struct page **blocks, unsigned int offset, int disks, async_tx_quiesce(&submit->depend_tx); if (!P(blocks, disks)) { - P(blocks, disks) = scribble; + P(blocks, disks) = pq_scribble_page; BUG_ON(len + offset > PAGE_SIZE); } if (!Q(blocks, disks)) { - Q(blocks, disks) = scribble; + Q(blocks, disks) = pq_scribble_page; BUG_ON(len + offset > PAGE_SIZE); } do_sync_gen_syndrome(blocks, offset, disks, len, submit); @@ -265,8 +265,10 @@ async_syndrome_val(struct page **blocks, unsigned int offset, int disks, len); struct dma_device *device = chan ? chan->device : NULL; struct dma_async_tx_descriptor *tx; + unsigned char coefs[disks-2]; enum dma_ctrl_flags dma_flags = submit->cb_fn ? DMA_PREP_INTERRUPT : 0; dma_addr_t *dma_src = NULL; + int src_cnt = 0; BUG_ON(disks < 4); @@ -285,22 +287,32 @@ async_syndrome_val(struct page **blocks, unsigned int offset, int disks, __func__, disks, len); if (!P(blocks, disks)) dma_flags |= DMA_PREP_PQ_DISABLE_P; + else + pq[0] = dma_map_page(dev, P(blocks, disks), + offset, len, + DMA_TO_DEVICE); if (!Q(blocks, disks)) dma_flags |= DMA_PREP_PQ_DISABLE_Q; + else + pq[1] = dma_map_page(dev, Q(blocks, disks), + offset, len, + DMA_TO_DEVICE); + if (submit->flags & ASYNC_TX_FENCE) dma_flags |= DMA_PREP_FENCE; - for (i = 0; i < disks; i++) + for (i = 0; i < disks-2; i++) if (likely(blocks[i])) { - BUG_ON(is_raid6_zero_block(blocks[i])); - dma_src[i] = dma_map_page(dev, blocks[i], - offset, len, - DMA_TO_DEVICE); + dma_src[src_cnt] = dma_map_page(dev, blocks[i], + offset, len, + DMA_TO_DEVICE); + coefs[src_cnt] = raid6_gfexp[i]; + src_cnt++; } for (;;) { tx = device->device_prep_dma_pq_val(chan, pq, dma_src, - disks - 2, - raid6_gfexp, + src_cnt, + coefs, len, pqres, dma_flags); if (likely(tx)) @@ -373,9 +385,9 @@ EXPORT_SYMBOL_GPL(async_syndrome_val); static int __init async_pq_init(void) { - scribble = alloc_page(GFP_KERNEL); + pq_scribble_page = alloc_page(GFP_KERNEL); - if (scribble) + if (pq_scribble_page) return 0; pr_err("%s: failed to allocate required spare page\n", __func__); @@ -385,7 +397,7 @@ static int __init async_pq_init(void) static void __exit async_pq_exit(void) { - put_page(scribble); + put_page(pq_scribble_page); } module_init(async_pq_init); diff --git a/crypto/async_tx/async_raid6_recov.c b/crypto/async_tx/async_raid6_recov.c index 6d73dde4786d..943f2abac9b4 100644 --- a/crypto/async_tx/async_raid6_recov.c +++ b/crypto/async_tx/async_raid6_recov.c @@ -131,8 +131,8 @@ async_mult(struct page *dest, struct page *src, u8 coef, size_t len, } static struct dma_async_tx_descriptor * -__2data_recov_4(size_t bytes, int faila, int failb, struct page **blocks, - struct async_submit_ctl *submit) +__2data_recov_4(int disks, size_t bytes, int faila, int failb, + struct page **blocks, struct async_submit_ctl *submit) { struct dma_async_tx_descriptor *tx = NULL; struct page *p, *q, *a, *b; @@ -143,8 +143,8 @@ __2data_recov_4(size_t bytes, int faila, int failb, struct page **blocks, void *cb_param = submit->cb_param; void *scribble = submit->scribble; - p = blocks[4-2]; - q = blocks[4-1]; + p = blocks[disks-2]; + q = blocks[disks-1]; a = blocks[faila]; b = blocks[failb]; @@ -170,8 +170,8 @@ __2data_recov_4(size_t bytes, int faila, int failb, struct page **blocks, } static struct dma_async_tx_descriptor * -__2data_recov_5(size_t bytes, int faila, int failb, struct page **blocks, - struct async_submit_ctl *submit) +__2data_recov_5(int disks, size_t bytes, int faila, int failb, + struct page **blocks, struct async_submit_ctl *submit) { struct dma_async_tx_descriptor *tx = NULL; struct page *p, *q, *g, *dp, *dq; @@ -181,21 +181,22 @@ __2data_recov_5(size_t bytes, int faila, int failb, struct page **blocks, dma_async_tx_callback cb_fn = submit->cb_fn; void *cb_param = submit->cb_param; void *scribble = submit->scribble; - int uninitialized_var(good); - int i; + int good_srcs, good, i; - for (i = 0; i < 3; i++) { + good_srcs = 0; + good = -1; + for (i = 0; i < disks-2; i++) { + if (blocks[i] == NULL) + continue; if (i == faila || i == failb) continue; - else { - good = i; - break; - } + good = i; + good_srcs++; } - BUG_ON(i >= 3); + BUG_ON(good_srcs > 1); - p = blocks[5-2]; - q = blocks[5-1]; + p = blocks[disks-2]; + q = blocks[disks-1]; g = blocks[good]; /* Compute syndrome with zero for the missing data pages @@ -263,10 +264,10 @@ __2data_recov_n(int disks, size_t bytes, int faila, int failb, * delta p and delta q */ dp = blocks[faila]; - blocks[faila] = (void *)raid6_empty_zero_page; + blocks[faila] = NULL; blocks[disks-2] = dp; dq = blocks[failb]; - blocks[failb] = (void *)raid6_empty_zero_page; + blocks[failb] = NULL; blocks[disks-1] = dq; init_async_submit(submit, ASYNC_TX_FENCE, tx, NULL, NULL, scribble); @@ -323,6 +324,8 @@ struct dma_async_tx_descriptor * async_raid6_2data_recov(int disks, size_t bytes, int faila, int failb, struct page **blocks, struct async_submit_ctl *submit) { + int non_zero_srcs, i; + BUG_ON(faila == failb); if (failb < faila) swap(faila, failb); @@ -334,11 +337,13 @@ async_raid6_2data_recov(int disks, size_t bytes, int faila, int failb, */ if (!submit->scribble) { void **ptrs = (void **) blocks; - int i; async_tx_quiesce(&submit->depend_tx); for (i = 0; i < disks; i++) - ptrs[i] = page_address(blocks[i]); + if (blocks[i] == NULL) + ptrs[i] = (void *) raid6_empty_zero_page; + else + ptrs[i] = page_address(blocks[i]); raid6_2data_recov(disks, bytes, faila, failb, ptrs); @@ -347,19 +352,30 @@ async_raid6_2data_recov(int disks, size_t bytes, int faila, int failb, return NULL; } - switch (disks) { - case 4: + non_zero_srcs = 0; + for (i = 0; i < disks-2 && non_zero_srcs < 4; i++) + if (blocks[i]) + non_zero_srcs++; + switch (non_zero_srcs) { + case 0: + case 1: + /* There must be at least 2 sources - the failed devices. */ + BUG(); + + case 2: /* dma devices do not uniformly understand a zero source pq * operation (in contrast to the synchronous case), so - * explicitly handle the 4 disk special case + * explicitly handle the special case of a 4 disk array with + * both data disks missing. */ - return __2data_recov_4(bytes, faila, failb, blocks, submit); - case 5: + return __2data_recov_4(disks, bytes, faila, failb, blocks, submit); + case 3: /* dma devices do not uniformly understand a single * source pq operation (in contrast to the synchronous - * case), so explicitly handle the 5 disk special case + * case), so explicitly handle the special case of a 5 disk + * array with 2 of 3 data disks missing. */ - return __2data_recov_5(bytes, faila, failb, blocks, submit); + return __2data_recov_5(disks, bytes, faila, failb, blocks, submit); default: return __2data_recov_n(disks, bytes, faila, failb, blocks, submit); } @@ -385,6 +401,7 @@ async_raid6_datap_recov(int disks, size_t bytes, int faila, dma_async_tx_callback cb_fn = submit->cb_fn; void *cb_param = submit->cb_param; void *scribble = submit->scribble; + int good_srcs, good, i; struct page *srcs[2]; pr_debug("%s: disks: %d len: %zu\n", __func__, disks, bytes); @@ -394,11 +411,13 @@ async_raid6_datap_recov(int disks, size_t bytes, int faila, */ if (!scribble) { void **ptrs = (void **) blocks; - int i; async_tx_quiesce(&submit->depend_tx); for (i = 0; i < disks; i++) - ptrs[i] = page_address(blocks[i]); + if (blocks[i] == NULL) + ptrs[i] = (void*)raid6_empty_zero_page; + else + ptrs[i] = page_address(blocks[i]); raid6_datap_recov(disks, bytes, faila, ptrs); @@ -407,6 +426,20 @@ async_raid6_datap_recov(int disks, size_t bytes, int faila, return NULL; } + good_srcs = 0; + good = -1; + for (i = 0; i < disks-2; i++) { + if (i == faila) + continue; + if (blocks[i]) { + good = i; + good_srcs++; + if (good_srcs > 1) + break; + } + } + BUG_ON(good_srcs == 0); + p = blocks[disks-2]; q = blocks[disks-1]; @@ -414,14 +447,13 @@ async_raid6_datap_recov(int disks, size_t bytes, int faila, * Use the dead data page as temporary storage for delta q */ dq = blocks[faila]; - blocks[faila] = (void *)raid6_empty_zero_page; + blocks[faila] = NULL; blocks[disks-1] = dq; - /* in the 4 disk case we only need to perform a single source - * multiplication + /* in the 4-disk case we only need to perform a single source + * multiplication with the one good data block. */ - if (disks == 4) { - int good = faila == 0 ? 1 : 0; + if (good_srcs == 1) { struct page *g = blocks[good]; init_async_submit(submit, ASYNC_TX_FENCE, tx, NULL, NULL, diff --git a/crypto/async_tx/async_xor.c b/crypto/async_tx/async_xor.c index b459a9034aac..79182dcb91b7 100644 --- a/crypto/async_tx/async_xor.c +++ b/crypto/async_tx/async_xor.c @@ -44,20 +44,23 @@ do_async_xor(struct dma_chan *chan, struct page *dest, struct page **src_list, void *cb_param_orig = submit->cb_param; enum async_tx_flags flags_orig = submit->flags; enum dma_ctrl_flags dma_flags; - int xor_src_cnt; + int xor_src_cnt = 0; dma_addr_t dma_dest; /* map the dest bidrectional in case it is re-used as a source */ dma_dest = dma_map_page(dma->dev, dest, offset, len, DMA_BIDIRECTIONAL); for (i = 0; i < src_cnt; i++) { /* only map the dest once */ + if (!src_list[i]) + continue; if (unlikely(src_list[i] == dest)) { - dma_src[i] = dma_dest; + dma_src[xor_src_cnt++] = dma_dest; continue; } - dma_src[i] = dma_map_page(dma->dev, src_list[i], offset, - len, DMA_TO_DEVICE); + dma_src[xor_src_cnt++] = dma_map_page(dma->dev, src_list[i], offset, + len, DMA_TO_DEVICE); } + src_cnt = xor_src_cnt; while (src_cnt) { submit->flags = flags_orig; @@ -123,7 +126,7 @@ do_sync_xor(struct page *dest, struct page **src_list, unsigned int offset, int src_cnt, size_t len, struct async_submit_ctl *submit) { int i; - int xor_src_cnt; + int xor_src_cnt = 0; int src_off = 0; void *dest_buf; void **srcs; @@ -135,8 +138,9 @@ do_sync_xor(struct page *dest, struct page **src_list, unsigned int offset, /* convert to buffer pointers */ for (i = 0; i < src_cnt; i++) - srcs[i] = page_address(src_list[i]) + offset; - + if (src_list[i]) + srcs[xor_src_cnt++] = page_address(src_list[i]) + offset; + src_cnt = xor_src_cnt; /* set destination address */ dest_buf = page_address(dest) + offset; diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index 0ed42d8870c7..93d2c7971df6 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -218,10 +218,10 @@ config ACPI_PROCESSOR_AGGREGATOR depends on X86 help ACPI 4.0 defines processor Aggregator, which enables OS to perform - specfic processor configuration and control that applies to all + specific processor configuration and control that applies to all processors in the platform. Currently only logical processor idling is defined, which is to reduce power consumption. This driver - support the new device. + supports the new device. config ACPI_THERMAL tristate "Thermal Zone" diff --git a/drivers/acpi/ac.c b/drivers/acpi/ac.c index 98b9690b0159..b6ed60b57b0d 100644 --- a/drivers/acpi/ac.c +++ b/drivers/acpi/ac.c @@ -245,6 +245,7 @@ static void acpi_ac_notify(struct acpi_device *device, u32 event) acpi_bus_generate_netlink_event(device->pnp.device_class, dev_name(&device->dev), event, (u32) ac->state); + acpi_notifier_call_chain(device, event, (u32) ac->state); #ifdef CONFIG_ACPI_SYSFS_POWER kobject_uevent(&ac->charger.dev->kobj, KOBJ_CHANGE); #endif diff --git a/drivers/acpi/acpica/acconfig.h b/drivers/acpi/acpica/acconfig.h index 8e679ef5b231..a4471e3d3853 100644 --- a/drivers/acpi/acpica/acconfig.h +++ b/drivers/acpi/acpica/acconfig.h @@ -103,9 +103,9 @@ #define ACPI_MAX_REFERENCE_COUNT 0x1000 -/* Size of cached memory mapping for system memory operation region */ +/* Default page size for use in mapping memory for operation regions */ -#define ACPI_SYSMEM_REGION_WINDOW_SIZE 4096 +#define ACPI_DEFAULT_PAGE_SIZE 4096 /* Must be power of 2 */ /* owner_id tracking. 8 entries allows for 255 owner_ids */ diff --git a/drivers/acpi/acpica/exregion.c b/drivers/acpi/acpica/exregion.c index 3a54b737d2da..2bd83ac57c3a 100644 --- a/drivers/acpi/acpica/exregion.c +++ b/drivers/acpi/acpica/exregion.c @@ -77,7 +77,8 @@ acpi_ex_system_memory_space_handler(u32 function, void *logical_addr_ptr = NULL; struct acpi_mem_space_context *mem_info = region_context; u32 length; - acpi_size window_size; + acpi_size map_length; + acpi_size page_boundary_map_length; #ifdef ACPI_MISALIGNMENT_NOT_SUPPORTED u32 remainder; #endif @@ -144,25 +145,39 @@ acpi_ex_system_memory_space_handler(u32 function, } /* - * Don't attempt to map memory beyond the end of the region, and - * constrain the maximum mapping size to something reasonable. + * Attempt to map from the requested address to the end of the region. + * However, we will never map more than one page, nor will we cross + * a page boundary. */ - window_size = (acpi_size) + map_length = (acpi_size) ((mem_info->address + mem_info->length) - address); - if (window_size > ACPI_SYSMEM_REGION_WINDOW_SIZE) { - window_size = ACPI_SYSMEM_REGION_WINDOW_SIZE; + /* + * If mapping the entire remaining portion of the region will cross + * a page boundary, just map up to the page boundary, do not cross. + * On some systems, crossing a page boundary while mapping regions + * can cause warnings if the pages have different attributes + * due to resource management + */ + page_boundary_map_length = + ACPI_ROUND_UP(address, ACPI_DEFAULT_PAGE_SIZE) - address; + + if (!page_boundary_map_length) { + page_boundary_map_length = ACPI_DEFAULT_PAGE_SIZE; + } + + if (map_length > page_boundary_map_length) { + map_length = page_boundary_map_length; } /* Create a new mapping starting at the address given */ - mem_info->mapped_logical_address = - acpi_os_map_memory((acpi_physical_address) address, window_size); + mem_info->mapped_logical_address = acpi_os_map_memory((acpi_physical_address) address, map_length); if (!mem_info->mapped_logical_address) { ACPI_ERROR((AE_INFO, "Could not map memory at %8.8X%8.8X, size %X", ACPI_FORMAT_NATIVE_UINT(address), - (u32) window_size)); + (u32) map_length)); mem_info->mapped_length = 0; return_ACPI_STATUS(AE_NO_MEMORY); } @@ -170,7 +185,7 @@ acpi_ex_system_memory_space_handler(u32 function, /* Save the physical address and mapping size */ mem_info->mapped_physical_address = address; - mem_info->mapped_length = window_size; + mem_info->mapped_length = map_length; } /* diff --git a/drivers/acpi/button.c b/drivers/acpi/button.c index 9335b87c5174..0c9c6a9a002c 100644 --- a/drivers/acpi/button.c +++ b/drivers/acpi/button.c @@ -251,6 +251,9 @@ int acpi_lid_open(void) acpi_status status; unsigned long long state; + if (!lid_device) + return -ENODEV; + status = acpi_evaluate_integer(lid_device->handle, "_LID", NULL, &state); if (ACPI_FAILURE(status)) diff --git a/drivers/acpi/pci_root.c b/drivers/acpi/pci_root.c index 31122214e0ec..1af808171d46 100644 --- a/drivers/acpi/pci_root.c +++ b/drivers/acpi/pci_root.c @@ -389,6 +389,17 @@ struct pci_dev *acpi_get_pci_dev(acpi_handle handle) pbus = pdev->subordinate; pci_dev_put(pdev); + + /* + * This function may be called for a non-PCI device that has a + * PCI parent (eg. a disk under a PCI SATA controller). In that + * case pdev->subordinate will be NULL for the parent. + */ + if (!pbus) { + dev_dbg(&pdev->dev, "Not a PCI-to-PCI bridge\n"); + pdev = NULL; + break; + } } out: list_for_each_entry_safe(node, tmp, &device_list, node) diff --git a/drivers/acpi/power_meter.c b/drivers/acpi/power_meter.c index e6bfd77986b8..2ef7030a0c28 100644 --- a/drivers/acpi/power_meter.c +++ b/drivers/acpi/power_meter.c @@ -294,7 +294,11 @@ static int set_acpi_trip(struct acpi_power_meter_resource *resource) return -EINVAL; } - return data; + /* _PTP returns 0 on success, nonzero otherwise */ + if (data) + return -EINVAL; + + return 0; } static ssize_t set_trip(struct device *dev, struct device_attribute *devattr, diff --git a/drivers/acpi/proc.c b/drivers/acpi/proc.c index f8b6f555ba52..d0d25e2e1ced 100644 --- a/drivers/acpi/proc.c +++ b/drivers/acpi/proc.c @@ -393,7 +393,7 @@ acpi_system_write_wakeup_device(struct file *file, struct list_head *node, *next; char strbuf[5]; char str[5] = ""; - int len = count; + unsigned int len = count; struct acpi_device *found_dev = NULL; if (len > 4) diff --git a/drivers/acpi/processor_core.c b/drivers/acpi/processor_core.c index c567b46dfa0f..ec742a4e5635 100644 --- a/drivers/acpi/processor_core.c +++ b/drivers/acpi/processor_core.c @@ -770,7 +770,7 @@ static struct notifier_block acpi_cpu_notifier = .notifier_call = acpi_cpu_soft_notify, }; -static int acpi_processor_add(struct acpi_device *device) +static int __cpuinit acpi_processor_add(struct acpi_device *device) { struct acpi_processor *pr = NULL; int result = 0; diff --git a/drivers/acpi/processor_throttling.c b/drivers/acpi/processor_throttling.c index 4c6c14c1e307..1c5d7a8b2fdf 100644 --- a/drivers/acpi/processor_throttling.c +++ b/drivers/acpi/processor_throttling.c @@ -1133,15 +1133,15 @@ int acpi_processor_get_throttling_info(struct acpi_processor *pr) int result = 0; struct acpi_processor_throttling *pthrottling; + if (!pr) + return -EINVAL; + ACPI_DEBUG_PRINT((ACPI_DB_INFO, "pblk_address[0x%08x] duty_offset[%d] duty_width[%d]\n", pr->throttling.address, pr->throttling.duty_offset, pr->throttling.duty_width)); - if (!pr) - return -EINVAL; - /* * Evaluate _PTC, _TSS and _TPC * They must all be present or none of them can be used. diff --git a/drivers/acpi/sleep.c b/drivers/acpi/sleep.c index a90afcc723ab..4cc1b8116e76 100644 --- a/drivers/acpi/sleep.c +++ b/drivers/acpi/sleep.c @@ -413,6 +413,30 @@ static struct dmi_system_id __initdata acpisleep_dmi_table[] = { }, }, { + .callback = init_set_sci_en_on_resume, + .ident = "Hewlett-Packard Pavilion dv4", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), + DMI_MATCH(DMI_PRODUCT_NAME, "HP Pavilion dv4"), + }, + }, + { + .callback = init_set_sci_en_on_resume, + .ident = "Hewlett-Packard Pavilion dv7", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), + DMI_MATCH(DMI_PRODUCT_NAME, "HP Pavilion dv7"), + }, + }, + { + .callback = init_set_sci_en_on_resume, + .ident = "Hewlett-Packard Compaq Presario CQ40 Notebook PC", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), + DMI_MATCH(DMI_PRODUCT_NAME, "Compaq Presario CQ40 Notebook PC"), + }, + }, + { .callback = init_old_suspend_ordering, .ident = "Panasonic CF51-2L", .matches = { diff --git a/drivers/acpi/video.c b/drivers/acpi/video.c index f6e54bf8dd96..05dff631591c 100644 --- a/drivers/acpi/video.c +++ b/drivers/acpi/video.c @@ -1109,7 +1109,12 @@ static int acpi_video_bus_check(struct acpi_video_bus *video) */ /* Does this device support video switching? */ - if (video->cap._DOS) { + if (video->cap._DOS || video->cap._DOD) { + if (!video->cap._DOS) { + printk(KERN_WARNING FW_BUG + "ACPI(%s) defines _DOD but not _DOS\n", + acpi_device_bid(video->device)); + } video->flags.multihead = 1; status = 0; } @@ -1218,7 +1223,7 @@ acpi_video_device_write_state(struct file *file, u32 state = 0; - if (!dev || count + 1 > sizeof str) + if (!dev || count >= sizeof(str)) return -EINVAL; if (copy_from_user(str, buffer, count)) @@ -1275,7 +1280,7 @@ acpi_video_device_write_brightness(struct file *file, int i; - if (!dev || !dev->brightness || count + 1 > sizeof str) + if (!dev || !dev->brightness || count >= sizeof(str)) return -EINVAL; if (copy_from_user(str, buffer, count)) @@ -1557,7 +1562,7 @@ acpi_video_bus_write_POST(struct file *file, unsigned long long opt, options; - if (!video || count + 1 > sizeof str) + if (!video || count >= sizeof(str)) return -EINVAL; status = acpi_video_bus_POST_options(video, &options); @@ -1597,7 +1602,7 @@ acpi_video_bus_write_DOS(struct file *file, unsigned long opt; - if (!video || count + 1 > sizeof str) + if (!video || count >= sizeof(str)) return -EINVAL; if (copy_from_user(str, buffer, count)) diff --git a/drivers/acpi/video_detect.c b/drivers/acpi/video_detect.c index 7032f25da9b5..575593a8b4e6 100644 --- a/drivers/acpi/video_detect.c +++ b/drivers/acpi/video_detect.c @@ -84,7 +84,7 @@ long acpi_is_video_device(struct acpi_device *device) return 0; /* Does this device able to support video switching ? */ - if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOD", &h_dummy)) && + if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOD", &h_dummy)) || ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOS", &h_dummy))) video_caps |= ACPI_VIDEO_OUTPUT_SWITCHING; diff --git a/drivers/ata/ahci.c b/drivers/ata/ahci.c index acd1162712b1..a3241a1a710b 100644 --- a/drivers/ata/ahci.c +++ b/drivers/ata/ahci.c @@ -122,6 +122,7 @@ enum { HOST_VERSION = 0x10, /* AHCI spec. version compliancy */ HOST_EM_LOC = 0x1c, /* Enclosure Management location */ HOST_EM_CTL = 0x20, /* Enclosure Management Control */ + HOST_CAP2 = 0x24, /* host capabilities, extended */ /* HOST_CTL bits */ HOST_RESET = (1 << 0), /* reset controller; self-clear */ @@ -129,16 +130,29 @@ enum { HOST_AHCI_EN = (1 << 31), /* AHCI enabled */ /* HOST_CAP bits */ + HOST_CAP_SXS = (1 << 5), /* Supports External SATA */ HOST_CAP_EMS = (1 << 6), /* Enclosure Management support */ - HOST_CAP_SSC = (1 << 14), /* Slumber capable */ + HOST_CAP_CCC = (1 << 7), /* Command Completion Coalescing */ + HOST_CAP_PART = (1 << 13), /* Partial state capable */ + HOST_CAP_SSC = (1 << 14), /* Slumber state capable */ + HOST_CAP_PIO_MULTI = (1 << 15), /* PIO multiple DRQ support */ + HOST_CAP_FBS = (1 << 16), /* FIS-based switching support */ HOST_CAP_PMP = (1 << 17), /* Port Multiplier support */ + HOST_CAP_ONLY = (1 << 18), /* Supports AHCI mode only */ HOST_CAP_CLO = (1 << 24), /* Command List Override support */ + HOST_CAP_LED = (1 << 25), /* Supports activity LED */ HOST_CAP_ALPM = (1 << 26), /* Aggressive Link PM support */ HOST_CAP_SSS = (1 << 27), /* Staggered Spin-up */ + HOST_CAP_MPS = (1 << 28), /* Mechanical presence switch */ HOST_CAP_SNTF = (1 << 29), /* SNotification register */ HOST_CAP_NCQ = (1 << 30), /* Native Command Queueing */ HOST_CAP_64 = (1 << 31), /* PCI DAC (64-bit DMA) support */ + /* HOST_CAP2 bits */ + HOST_CAP2_BOH = (1 << 0), /* BIOS/OS handoff supported */ + HOST_CAP2_NVMHCI = (1 << 1), /* NVMHCI supported */ + HOST_CAP2_APST = (1 << 2), /* Automatic partial to slumber */ + /* registers for each SATA port */ PORT_LST_ADDR = 0x00, /* command list DMA addr */ PORT_LST_ADDR_HI = 0x04, /* command list DMA addr hi */ @@ -267,8 +281,10 @@ struct ahci_em_priv { struct ahci_host_priv { unsigned int flags; /* AHCI_HFLAG_* */ u32 cap; /* cap to use */ + u32 cap2; /* cap2 to use */ u32 port_map; /* port map to use */ u32 saved_cap; /* saved initial cap */ + u32 saved_cap2; /* saved initial cap2 */ u32 saved_port_map; /* saved initial port_map */ u32 em_loc; /* enclosure management location */ }; @@ -331,12 +347,15 @@ static void ahci_init_sw_activity(struct ata_link *link); static ssize_t ahci_show_host_caps(struct device *dev, struct device_attribute *attr, char *buf); +static ssize_t ahci_show_host_cap2(struct device *dev, + struct device_attribute *attr, char *buf); static ssize_t ahci_show_host_version(struct device *dev, struct device_attribute *attr, char *buf); static ssize_t ahci_show_port_cmd(struct device *dev, struct device_attribute *attr, char *buf); DEVICE_ATTR(ahci_host_caps, S_IRUGO, ahci_show_host_caps, NULL); +DEVICE_ATTR(ahci_host_cap2, S_IRUGO, ahci_show_host_cap2, NULL); DEVICE_ATTR(ahci_host_version, S_IRUGO, ahci_show_host_version, NULL); DEVICE_ATTR(ahci_port_cmd, S_IRUGO, ahci_show_port_cmd, NULL); @@ -345,6 +364,7 @@ static struct device_attribute *ahci_shost_attrs[] = { &dev_attr_em_message_type, &dev_attr_em_message, &dev_attr_ahci_host_caps, + &dev_attr_ahci_host_cap2, &dev_attr_ahci_host_version, &dev_attr_ahci_port_cmd, NULL @@ -447,7 +467,8 @@ static const struct ata_port_info ahci_port_info[] = { [board_ahci_sb600] = { AHCI_HFLAGS (AHCI_HFLAG_IGN_SERR_INTERNAL | - AHCI_HFLAG_NO_MSI | AHCI_HFLAG_SECT255), + AHCI_HFLAG_NO_MSI | AHCI_HFLAG_SECT255 | + AHCI_HFLAG_32BIT_ONLY), .flags = AHCI_FLAG_COMMON, .pio_mask = ATA_PIO4, .udma_mask = ATA_UDMA6, @@ -554,7 +575,7 @@ static const struct pci_device_id ahci_pci_tbl[] = { { PCI_VDEVICE(ATI, 0x4395), board_ahci_sb700 }, /* ATI SB700/800 */ /* AMD */ - { PCI_VDEVICE(AMD, 0x7800), board_ahci }, /* AMD SB900 */ + { PCI_VDEVICE(AMD, 0x7800), board_ahci }, /* AMD Hudson-2 */ /* AMD is using RAID class only for ahci controllers */ { PCI_VENDOR_ID_AMD, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, PCI_CLASS_STORAGE_RAID << 8, 0xffffff, board_ahci }, @@ -584,6 +605,7 @@ static const struct pci_device_id ahci_pci_tbl[] = { { PCI_VDEVICE(NVIDIA, 0x0559), board_ahci_yesncq }, /* MCP67 */ { PCI_VDEVICE(NVIDIA, 0x055a), board_ahci_yesncq }, /* MCP67 */ { PCI_VDEVICE(NVIDIA, 0x055b), board_ahci_yesncq }, /* MCP67 */ + { PCI_VDEVICE(NVIDIA, 0x0580), board_ahci_yesncq }, /* Linux ID */ { PCI_VDEVICE(NVIDIA, 0x07f0), board_ahci_yesncq }, /* MCP73 */ { PCI_VDEVICE(NVIDIA, 0x07f1), board_ahci_yesncq }, /* MCP73 */ { PCI_VDEVICE(NVIDIA, 0x07f2), board_ahci_yesncq }, /* MCP73 */ @@ -732,6 +754,16 @@ static ssize_t ahci_show_host_caps(struct device *dev, return sprintf(buf, "%x\n", hpriv->cap); } +static ssize_t ahci_show_host_cap2(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct ata_port *ap = ata_shost_to_port(shost); + struct ahci_host_priv *hpriv = ap->host->private_data; + + return sprintf(buf, "%x\n", hpriv->cap2); +} + static ssize_t ahci_show_host_version(struct device *dev, struct device_attribute *attr, char *buf) { @@ -771,7 +803,7 @@ static void ahci_save_initial_config(struct pci_dev *pdev, struct ahci_host_priv *hpriv) { void __iomem *mmio = pcim_iomap_table(pdev)[AHCI_PCI_BAR]; - u32 cap, port_map; + u32 cap, cap2, vers, port_map; int i; int mv; @@ -784,6 +816,14 @@ static void ahci_save_initial_config(struct pci_dev *pdev, hpriv->saved_cap = cap = readl(mmio + HOST_CAP); hpriv->saved_port_map = port_map = readl(mmio + HOST_PORTS_IMPL); + /* CAP2 register is only defined for AHCI 1.2 and later */ + vers = readl(mmio + HOST_VERSION); + if ((vers >> 16) > 1 || + ((vers >> 16) == 1 && (vers & 0xFFFF) >= 0x200)) + hpriv->saved_cap2 = cap2 = readl(mmio + HOST_CAP2); + else + hpriv->saved_cap2 = cap2 = 0; + /* some chips have errata preventing 64bit use */ if ((cap & HOST_CAP_64) && (hpriv->flags & AHCI_HFLAG_32BIT_ONLY)) { dev_printk(KERN_INFO, &pdev->dev, @@ -869,6 +909,7 @@ static void ahci_save_initial_config(struct pci_dev *pdev, /* record values to use during operation */ hpriv->cap = cap; + hpriv->cap2 = cap2; hpriv->port_map = port_map; } @@ -887,6 +928,8 @@ static void ahci_restore_initial_config(struct ata_host *host) void __iomem *mmio = host->iomap[AHCI_PCI_BAR]; writel(hpriv->saved_cap, mmio + HOST_CAP); + if (hpriv->saved_cap2) + writel(hpriv->saved_cap2, mmio + HOST_CAP2); writel(hpriv->saved_port_map, mmio + HOST_PORTS_IMPL); (void) readl(mmio + HOST_PORTS_IMPL); /* flush */ } @@ -2534,13 +2577,14 @@ static void ahci_print_info(struct ata_host *host) struct ahci_host_priv *hpriv = host->private_data; struct pci_dev *pdev = to_pci_dev(host->dev); void __iomem *mmio = host->iomap[AHCI_PCI_BAR]; - u32 vers, cap, impl, speed; + u32 vers, cap, cap2, impl, speed; const char *speed_s; u16 cc; const char *scc_s; vers = readl(mmio + HOST_VERSION); cap = hpriv->cap; + cap2 = hpriv->cap2; impl = hpriv->port_map; speed = (cap >> 20) & 0xf; @@ -2583,25 +2627,29 @@ static void ahci_print_info(struct ata_host *host) "flags: " "%s%s%s%s%s%s%s" "%s%s%s%s%s%s%s" - "%s\n" + "%s%s%s%s%s%s\n" , - cap & (1 << 31) ? "64bit " : "", - cap & (1 << 30) ? "ncq " : "", - cap & (1 << 29) ? "sntf " : "", - cap & (1 << 28) ? "ilck " : "", - cap & (1 << 27) ? "stag " : "", - cap & (1 << 26) ? "pm " : "", - cap & (1 << 25) ? "led " : "", - - cap & (1 << 24) ? "clo " : "", - cap & (1 << 19) ? "nz " : "", - cap & (1 << 18) ? "only " : "", - cap & (1 << 17) ? "pmp " : "", - cap & (1 << 15) ? "pio " : "", - cap & (1 << 14) ? "slum " : "", - cap & (1 << 13) ? "part " : "", - cap & (1 << 6) ? "ems ": "" + cap & HOST_CAP_64 ? "64bit " : "", + cap & HOST_CAP_NCQ ? "ncq " : "", + cap & HOST_CAP_SNTF ? "sntf " : "", + cap & HOST_CAP_MPS ? "ilck " : "", + cap & HOST_CAP_SSS ? "stag " : "", + cap & HOST_CAP_ALPM ? "pm " : "", + cap & HOST_CAP_LED ? "led " : "", + cap & HOST_CAP_CLO ? "clo " : "", + cap & HOST_CAP_ONLY ? "only " : "", + cap & HOST_CAP_PMP ? "pmp " : "", + cap & HOST_CAP_FBS ? "fbs " : "", + cap & HOST_CAP_PIO_MULTI ? "pio " : "", + cap & HOST_CAP_SSC ? "slum " : "", + cap & HOST_CAP_PART ? "part " : "", + cap & HOST_CAP_CCC ? "ccc " : "", + cap & HOST_CAP_EMS ? "ems " : "", + cap & HOST_CAP_SXS ? "sxs " : "", + cap2 & HOST_CAP2_APST ? "apst " : "", + cap2 & HOST_CAP2_NVMHCI ? "nvmp " : "", + cap2 & HOST_CAP2_BOH ? "boh " : "" ); } @@ -2650,17 +2698,15 @@ static void ahci_p5wdh_workaround(struct ata_host *host) } } -/* - * SB600 ahci controller on certain boards can't do 64bit DMA with - * older BIOS. - */ -static bool ahci_sb600_32bit_only(struct pci_dev *pdev) +/* only some SB600 ahci controllers can do 64bit DMA */ +static bool ahci_sb600_enable_64bit(struct pci_dev *pdev) { static const struct dmi_system_id sysids[] = { /* * The oldest version known to be broken is 0901 and * working is 1501 which was released on 2007-10-26. - * Force 32bit DMA on anything older than 1501. + * Enable 64bit DMA on 1501 and anything newer. + * * Please read bko#9412 for more info. */ { @@ -2673,46 +2719,57 @@ static bool ahci_sb600_32bit_only(struct pci_dev *pdev) .driver_data = "20071026", /* yyyymmdd */ }, /* - * It's yet unknown whether more recent BIOS fixes the - * problem. Blacklist the whole board for the time - * being. Please read the following thread for more - * info. + * All BIOS versions for the MSI K9A2 Platinum (MS-7376) + * support 64bit DMA. * - * http://thread.gmane.org/gmane.linux.ide/42326 + * BIOS versions earlier than 1.5 had the Manufacturer DMI + * fields as "MICRO-STAR INTERANTIONAL CO.,LTD". + * This spelling mistake was fixed in BIOS version 1.5, so + * 1.5 and later have the Manufacturer as + * "MICRO-STAR INTERNATIONAL CO.,LTD". + * So try to match on DMI_BOARD_VENDOR of "MICRO-STAR INTER". + * + * BIOS versions earlier than 1.9 had a Board Product Name + * DMI field of "MS-7376". This was changed to be + * "K9A2 Platinum (MS-7376)" in version 1.9, but we can still + * match on DMI_BOARD_NAME of "MS-7376". */ { - .ident = "Gigabyte GA-MA69VM-S2", + .ident = "MSI K9A2 Platinum", .matches = { DMI_MATCH(DMI_BOARD_VENDOR, - "Gigabyte Technology Co., Ltd."), - DMI_MATCH(DMI_BOARD_NAME, "GA-MA69VM-S2"), + "MICRO-STAR INTER"), + DMI_MATCH(DMI_BOARD_NAME, "MS-7376"), }, }, { } }; const struct dmi_system_id *match; + int year, month, date; + char buf[9]; match = dmi_first_match(sysids); if (pdev->bus->number != 0 || pdev->devfn != PCI_DEVFN(0x12, 0) || !match) return false; - if (match->driver_data) { - int year, month, date; - char buf[9]; - - dmi_get_date(DMI_BIOS_DATE, &year, &month, &date); - snprintf(buf, sizeof(buf), "%04d%02d%02d", year, month, date); + if (!match->driver_data) + goto enable_64bit; - if (strcmp(buf, match->driver_data) >= 0) - return false; + dmi_get_date(DMI_BIOS_DATE, &year, &month, &date); + snprintf(buf, sizeof(buf), "%04d%02d%02d", year, month, date); + if (strcmp(buf, match->driver_data) >= 0) + goto enable_64bit; + else { dev_printk(KERN_WARNING, &pdev->dev, "%s: BIOS too old, " "forcing 32bit DMA, update BIOS\n", match->ident); - } else - dev_printk(KERN_WARNING, &pdev->dev, "%s: this board can't " - "do 64bit DMA, forcing 32bit\n", match->ident); + return false; + } +enable_64bit: + dev_printk(KERN_WARNING, &pdev->dev, "%s: enabling 64bit DMA\n", + match->ident); return true; } @@ -2858,6 +2915,55 @@ static bool ahci_broken_online(struct pci_dev *pdev) return pdev->bus->number == (val >> 8) && pdev->devfn == (val & 0xff); } +#ifdef CONFIG_ATA_ACPI +static void ahci_gtf_filter_workaround(struct ata_host *host) +{ + static const struct dmi_system_id sysids[] = { + /* + * Aspire 3810T issues a bunch of SATA enable commands + * via _GTF including an invalid one and one which is + * rejected by the device. Among the successful ones + * is FPDMA non-zero offset enable which when enabled + * only on the drive side leads to NCQ command + * failures. Filter it out. + */ + { + .ident = "Aspire 3810T", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Acer"), + DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 3810T"), + }, + .driver_data = (void *)ATA_ACPI_FILTER_FPDMA_OFFSET, + }, + { } + }; + const struct dmi_system_id *dmi = dmi_first_match(sysids); + unsigned int filter; + int i; + + if (!dmi) + return; + + filter = (unsigned long)dmi->driver_data; + dev_printk(KERN_INFO, host->dev, + "applying extra ACPI _GTF filter 0x%x for %s\n", + filter, dmi->ident); + + for (i = 0; i < host->n_ports; i++) { + struct ata_port *ap = host->ports[i]; + struct ata_link *link; + struct ata_device *dev; + + ata_for_each_link(link, ap, EDGE) + ata_for_each_dev(dev, link, ALL) + dev->gtf_filter |= filter; + } +} +#else +static inline void ahci_gtf_filter_workaround(struct ata_host *host) +{} +#endif + static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) { static int printed_version; @@ -2926,9 +3032,9 @@ static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) if (board_id == board_ahci_sb700 && pdev->revision >= 0x40) hpriv->flags &= ~AHCI_HFLAG_IGN_SERR_INTERNAL; - /* apply sb600 32bit only quirk */ - if (ahci_sb600_32bit_only(pdev)) - hpriv->flags |= AHCI_HFLAG_32BIT_ONLY; + /* only some SB600s can do 64bit DMA */ + if (ahci_sb600_enable_64bit(pdev)) + hpriv->flags &= ~AHCI_HFLAG_32BIT_ONLY; if ((hpriv->flags & AHCI_HFLAG_NO_MSI) || pci_enable_msi(pdev)) pci_intx(pdev, 1); @@ -3023,6 +3129,9 @@ static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) /* apply workaround for ASUS P5W DH Deluxe mainboard */ ahci_p5wdh_workaround(host); + /* apply gtf filter quirk */ + ahci_gtf_filter_workaround(host); + /* initialize adapter */ rc = ahci_configure_dma_masks(pdev, hpriv->cap & HOST_CAP_64); if (rc) diff --git a/drivers/ata/libata-acpi.c b/drivers/ata/libata-acpi.c index 01964b6e6f6b..b0882cddfd4c 100644 --- a/drivers/ata/libata-acpi.c +++ b/drivers/ata/libata-acpi.c @@ -20,19 +20,9 @@ #include <acpi/acpi_bus.h> -enum { - ATA_ACPI_FILTER_SETXFER = 1 << 0, - ATA_ACPI_FILTER_LOCK = 1 << 1, - ATA_ACPI_FILTER_DIPM = 1 << 2, - - ATA_ACPI_FILTER_DEFAULT = ATA_ACPI_FILTER_SETXFER | - ATA_ACPI_FILTER_LOCK | - ATA_ACPI_FILTER_DIPM, -}; - -static unsigned int ata_acpi_gtf_filter = ATA_ACPI_FILTER_DEFAULT; +unsigned int ata_acpi_gtf_filter = ATA_ACPI_FILTER_DEFAULT; module_param_named(acpi_gtf_filter, ata_acpi_gtf_filter, int, 0644); -MODULE_PARM_DESC(acpi_gtf_filter, "filter mask for ACPI _GTF commands, set to filter out (0x1=set xfermode, 0x2=lock/freeze lock, 0x4=DIPM)"); +MODULE_PARM_DESC(acpi_gtf_filter, "filter mask for ACPI _GTF commands, set to filter out (0x1=set xfermode, 0x2=lock/freeze lock, 0x4=DIPM, 0x8=FPDMA non-zero offset, 0x10=FPDMA DMA Setup FIS auto-activate)"); #define NO_PORT_MULT 0xffff #define SATA_ADR(root, pmp) (((root) << 16) | (pmp)) @@ -613,10 +603,11 @@ static void ata_acpi_gtf_to_tf(struct ata_device *dev, tf->command = gtf->tf[6]; /* 0x1f7 */ } -static int ata_acpi_filter_tf(const struct ata_taskfile *tf, +static int ata_acpi_filter_tf(struct ata_device *dev, + const struct ata_taskfile *tf, const struct ata_taskfile *ptf) { - if (ata_acpi_gtf_filter & ATA_ACPI_FILTER_SETXFER) { + if (dev->gtf_filter & ATA_ACPI_FILTER_SETXFER) { /* libata doesn't use ACPI to configure transfer mode. * It will only confuse device configuration. Skip. */ @@ -625,7 +616,7 @@ static int ata_acpi_filter_tf(const struct ata_taskfile *tf, return 1; } - if (ata_acpi_gtf_filter & ATA_ACPI_FILTER_LOCK) { + if (dev->gtf_filter & ATA_ACPI_FILTER_LOCK) { /* BIOS writers, sorry but we don't wanna lock * features unless the user explicitly said so. */ @@ -647,12 +638,23 @@ static int ata_acpi_filter_tf(const struct ata_taskfile *tf, return 1; } - if (ata_acpi_gtf_filter & ATA_ACPI_FILTER_DIPM) { + if (tf->command == ATA_CMD_SET_FEATURES && + tf->feature == SETFEATURES_SATA_ENABLE) { /* inhibit enabling DIPM */ - if (tf->command == ATA_CMD_SET_FEATURES && - tf->feature == SETFEATURES_SATA_ENABLE && + if (dev->gtf_filter & ATA_ACPI_FILTER_DIPM && tf->nsect == SATA_DIPM) return 1; + + /* inhibit FPDMA non-zero offset */ + if (dev->gtf_filter & ATA_ACPI_FILTER_FPDMA_OFFSET && + (tf->nsect == SATA_FPDMA_OFFSET || + tf->nsect == SATA_FPDMA_IN_ORDER)) + return 1; + + /* inhibit FPDMA auto activation */ + if (dev->gtf_filter & ATA_ACPI_FILTER_FPDMA_AA && + tf->nsect == SATA_FPDMA_AA) + return 1; } return 0; @@ -704,7 +706,7 @@ static int ata_acpi_run_tf(struct ata_device *dev, pptf = &ptf; } - if (!ata_acpi_filter_tf(&tf, pptf)) { + if (!ata_acpi_filter_tf(dev, &tf, pptf)) { rtf = tf; err_mask = ata_exec_internal(dev, &rtf, NULL, DMA_NONE, NULL, 0, 0); diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c index 0ddaf43d68c6..dc72690ed5db 100644 --- a/drivers/ata/libata-core.c +++ b/drivers/ata/libata-core.c @@ -4919,10 +4919,11 @@ struct ata_queued_cmd *ata_qc_new_init(struct ata_device *dev) */ void ata_qc_free(struct ata_queued_cmd *qc) { - struct ata_port *ap = qc->ap; + struct ata_port *ap; unsigned int tag; WARN_ON_ONCE(qc == NULL); /* ata_qc_from_tag _might_ return NULL */ + ap = qc->ap; qc->flags = 0; tag = qc->tag; @@ -4934,11 +4935,13 @@ void ata_qc_free(struct ata_queued_cmd *qc) void __ata_qc_complete(struct ata_queued_cmd *qc) { - struct ata_port *ap = qc->ap; - struct ata_link *link = qc->dev->link; + struct ata_port *ap; + struct ata_link *link; WARN_ON_ONCE(qc == NULL); /* ata_qc_from_tag _might_ return NULL */ WARN_ON_ONCE(!(qc->flags & ATA_QCFLAG_ACTIVE)); + ap = qc->ap; + link = qc->dev->link; if (likely(qc->flags & ATA_QCFLAG_DMAMAP)) ata_sg_clean(qc); @@ -5028,12 +5031,14 @@ void ata_qc_complete(struct ata_queued_cmd *qc) qc->flags |= ATA_QCFLAG_FAILED; if (unlikely(qc->flags & ATA_QCFLAG_FAILED)) { - if (!ata_tag_internal(qc->tag)) { - /* always fill result TF for failed qc */ - fill_result_tf(qc); + /* always fill result TF for failed qc */ + fill_result_tf(qc); + + if (!ata_tag_internal(qc->tag)) ata_qc_schedule_eh(qc); - return; - } + else + __ata_qc_complete(qc); + return; } WARN_ON_ONCE(ap->pflags & ATA_PFLAG_FROZEN); @@ -5591,6 +5596,9 @@ void ata_link_init(struct ata_port *ap, struct ata_link *link, int pmp) dev->link = link; dev->devno = dev - link->device; +#ifdef CONFIG_ATA_ACPI + dev->gtf_filter = ata_acpi_gtf_filter; +#endif ata_dev_init(dev); } } diff --git a/drivers/ata/libata-eh.c b/drivers/ata/libata-eh.c index a04488f0de88..bba2ae5df1c2 100644 --- a/drivers/ata/libata-eh.c +++ b/drivers/ata/libata-eh.c @@ -2667,14 +2667,14 @@ int ata_eh_reset(struct ata_link *link, int classify, dev->pio_mode = XFER_PIO_0; dev->flags &= ~ATA_DFLAG_SLEEPING; - if (!ata_phys_link_offline(ata_dev_phys_link(dev))) { - /* apply class override */ - if (lflags & ATA_LFLAG_ASSUME_ATA) - classes[dev->devno] = ATA_DEV_ATA; - else if (lflags & ATA_LFLAG_ASSUME_SEMB) - classes[dev->devno] = ATA_DEV_SEMB_UNSUP; - } else - classes[dev->devno] = ATA_DEV_NONE; + if (ata_phys_link_offline(ata_dev_phys_link(dev))) + continue; + + /* apply class override */ + if (lflags & ATA_LFLAG_ASSUME_ATA) + classes[dev->devno] = ATA_DEV_ATA; + else if (lflags & ATA_LFLAG_ASSUME_SEMB) + classes[dev->devno] = ATA_DEV_SEMB_UNSUP; } /* record current link speed */ @@ -2713,34 +2713,48 @@ int ata_eh_reset(struct ata_link *link, int classify, ap->pflags &= ~ATA_PFLAG_EH_PENDING; spin_unlock_irqrestore(link->ap->lock, flags); - /* Make sure onlineness and classification result correspond. + /* + * Make sure onlineness and classification result correspond. * Hotplug could have happened during reset and some * controllers fail to wait while a drive is spinning up after * being hotplugged causing misdetection. By cross checking - * link onlineness and classification result, those conditions - * can be reliably detected and retried. + * link on/offlineness and classification result, those + * conditions can be reliably detected and retried. */ nr_unknown = 0; ata_for_each_dev(dev, link, ALL) { - /* convert all ATA_DEV_UNKNOWN to ATA_DEV_NONE */ - if (classes[dev->devno] == ATA_DEV_UNKNOWN) { - classes[dev->devno] = ATA_DEV_NONE; - if (ata_phys_link_online(ata_dev_phys_link(dev))) + if (ata_phys_link_online(ata_dev_phys_link(dev))) { + if (classes[dev->devno] == ATA_DEV_UNKNOWN) { + ata_dev_printk(dev, KERN_DEBUG, "link online " + "but device misclassifed\n"); + classes[dev->devno] = ATA_DEV_NONE; nr_unknown++; + } + } else if (ata_phys_link_offline(ata_dev_phys_link(dev))) { + if (ata_class_enabled(classes[dev->devno])) + ata_dev_printk(dev, KERN_DEBUG, "link offline, " + "clearing class %d to NONE\n", + classes[dev->devno]); + classes[dev->devno] = ATA_DEV_NONE; + } else if (classes[dev->devno] == ATA_DEV_UNKNOWN) { + ata_dev_printk(dev, KERN_DEBUG, "link status unknown, " + "clearing UNKNOWN to NONE\n"); + classes[dev->devno] = ATA_DEV_NONE; } } if (classify && nr_unknown) { if (try < max_tries) { ata_link_printk(link, KERN_WARNING, "link online but " - "device misclassified, retrying\n"); + "%d devices misclassified, retrying\n", + nr_unknown); failed_link = link; rc = -EAGAIN; goto fail; } ata_link_printk(link, KERN_WARNING, - "link online but device misclassified, " - "device detection might fail\n"); + "link online but %d devices misclassified, " + "device detection might fail\n", nr_unknown); } /* reset successful, schedule revalidation */ @@ -2967,12 +2981,14 @@ static int ata_eh_revalidate_and_attach(struct ata_link *link, * device detection messages backwards. */ ata_for_each_dev(dev, link, ALL) { - if (!(new_mask & (1 << dev->devno)) || - dev->class == ATA_DEV_PMP) + if (!(new_mask & (1 << dev->devno))) continue; dev->class = ehc->classes[dev->devno]; + if (dev->class == ATA_DEV_PMP) + continue; + ehc->i.flags |= ATA_EHI_PRINTINFO; rc = ata_dev_configure(dev); ehc->i.flags &= ~ATA_EHI_PRINTINFO; diff --git a/drivers/ata/libata.h b/drivers/ata/libata.h index be8e2628f82c..823e63096362 100644 --- a/drivers/ata/libata.h +++ b/drivers/ata/libata.h @@ -118,6 +118,8 @@ extern void ata_lpm_schedule(struct ata_port *ap, enum link_pm); /* libata-acpi.c */ #ifdef CONFIG_ATA_ACPI +extern unsigned int ata_acpi_gtf_filter; + extern void ata_acpi_associate_sata_port(struct ata_port *ap); extern void ata_acpi_associate(struct ata_host *host); extern void ata_acpi_dissociate(struct ata_host *host); diff --git a/drivers/ata/pata_ali.c b/drivers/ata/pata_ali.c index fc9c5d6d7d80..1432dc9d0ab8 100644 --- a/drivers/ata/pata_ali.c +++ b/drivers/ata/pata_ali.c @@ -290,7 +290,7 @@ static void ali_warn_atapi_dma(struct ata_device *adev) if (print_info && adev->class == ATA_DEV_ATAPI && !ali_atapi_dma) { ata_dev_printk(adev, KERN_WARNING, - "WARNING: ATAPI DMA disabled for reliablity issues. It can be enabled\n"); + "WARNING: ATAPI DMA disabled for reliability issues. It can be enabled\n"); ata_dev_printk(adev, KERN_WARNING, "WARNING: via pata_ali.atapi_dma modparam or corresponding sysfs node.\n"); } diff --git a/drivers/ata/pata_atiixp.c b/drivers/ata/pata_atiixp.c index aa4b3f6ae771..ae4454d4e955 100644 --- a/drivers/ata/pata_atiixp.c +++ b/drivers/ata/pata_atiixp.c @@ -246,7 +246,7 @@ static const struct pci_device_id atiixp[] = { { PCI_VDEVICE(ATI, PCI_DEVICE_ID_ATI_IXP400_IDE), }, { PCI_VDEVICE(ATI, PCI_DEVICE_ID_ATI_IXP600_IDE), }, { PCI_VDEVICE(ATI, PCI_DEVICE_ID_ATI_IXP700_IDE), }, - { PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_SB900_IDE), }, + { PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_HUDSON2_IDE), }, { }, }; diff --git a/drivers/ata/pata_atp867x.c b/drivers/ata/pata_atp867x.c index 7990de925d2e..6fe7ded40c6a 100644 --- a/drivers/ata/pata_atp867x.c +++ b/drivers/ata/pata_atp867x.c @@ -118,20 +118,13 @@ struct atp867x_priv { int pci66mhz; }; -static inline u8 atp867x_speed_to_mode(u8 speed) -{ - return speed - XFER_UDMA_0 + 1; -} - static void atp867x_set_dmamode(struct ata_port *ap, struct ata_device *adev) { struct pci_dev *pdev = to_pci_dev(ap->host->dev); struct atp867x_priv *dp = ap->private_data; u8 speed = adev->dma_mode; u8 b; - u8 mode; - - mode = atp867x_speed_to_mode(speed); + u8 mode = speed - XFER_UDMA_0 + 1; /* * Doc 6.6.9: decrease the udma mode value by 1 for safer UDMA speed @@ -156,25 +149,38 @@ static void atp867x_set_dmamode(struct ata_port *ap, struct ata_device *adev) iowrite8(b, dp->dma_mode); } -static int atp867x_get_active_clocks_shifted(unsigned int clk) +static int atp867x_get_active_clocks_shifted(struct ata_port *ap, + unsigned int clk) { + struct atp867x_priv *dp = ap->private_data; unsigned char clocks = clk; + /* + * Doc 6.6.9: increase the clock value by 1 for safer PIO speed + * on 66MHz bus + */ + if (dp->pci66mhz) + clocks++; + switch (clocks) { case 0: clocks = 1; break; - case 1 ... 7: - break; - case 8 ... 12: - clocks = 7; + case 1 ... 6: break; default: printk(KERN_WARNING "ATP867X: active %dclk is invalid. " - "Using default 8clk.\n", clk); - clocks = 0; /* 8 clk */ + "Using 12clk.\n", clk); + case 9 ... 12: + clocks = 7; /* 12 clk */ break; + case 7: + case 8: /* default 8 clk */ + clocks = 0; + goto active_clock_shift_done; } + +active_clock_shift_done: return clocks << ATP867X_IO_PIOSPD_ACTIVE_SHIFT; } @@ -188,20 +194,20 @@ static int atp867x_get_recover_clocks_shifted(unsigned int clk) break; case 1 ... 11: break; - case 12: - clocks = 0; - break; - case 13: case 14: - --clocks; + case 13: + case 14: + --clocks; /* by the spec */ break; case 15: break; default: printk(KERN_WARNING "ATP867X: recover %dclk is invalid. " - "Using default 15clk.\n", clk); - clocks = 0; /* 12 clk */ + "Using default 12clk.\n", clk); + case 12: /* default 12 clk */ + clocks = 0; break; } + return clocks << ATP867X_IO_PIOSPD_RECOVER_SHIFT; } @@ -230,25 +236,38 @@ static void atp867x_set_piomode(struct ata_port *ap, struct ata_device *adev) b = (b & ~ATP867X_IO_DMAMODE_MSTR_MASK); iowrite8(b, dp->dma_mode); - b = atp867x_get_active_clocks_shifted(t.active) | - atp867x_get_recover_clocks_shifted(t.recover); - if (dp->pci66mhz) - b += 0x10; + b = atp867x_get_active_clocks_shifted(ap, t.active) | + atp867x_get_recover_clocks_shifted(t.recover); if (adev->devno & 1) iowrite8(b, dp->slave_piospd); else iowrite8(b, dp->mstr_piospd); - /* - * use the same value for comand timing as for PIO timimg - */ + b = atp867x_get_active_clocks_shifted(ap, t.act8b) | + atp867x_get_recover_clocks_shifted(t.rec8b); + iowrite8(b, dp->eightb_piospd); } +static int atp867x_cable_override(struct pci_dev *pdev) +{ + if (pdev->subsystem_vendor == PCI_VENDOR_ID_ARTOP && + (pdev->subsystem_device == PCI_DEVICE_ID_ARTOP_ATP867A || + pdev->subsystem_device == PCI_DEVICE_ID_ARTOP_ATP867B)) { + return 1; + } + return 0; +} + static int atp867x_cable_detect(struct ata_port *ap) { - return ATA_CBL_PATA40_SHORT; + struct pci_dev *pdev = to_pci_dev(ap->host->dev); + + if (atp867x_cable_override(pdev)) + return ATA_CBL_PATA40_SHORT; + + return ATA_CBL_PATA_UNK; } static struct scsi_host_template atp867x_sht = { @@ -471,7 +490,6 @@ static int atp867x_init_one(struct pci_dev *pdev, static const struct ata_port_info info_867x = { .flags = ATA_FLAG_SLAVE_POSS, .pio_mask = ATA_PIO4, - .mwdma_mask = ATA_MWDMA2, .udma_mask = ATA_UDMA6, .port_ops = &atp867x_ops, }; @@ -515,6 +533,23 @@ err_out: return rc; } +#ifdef CONFIG_PM +static int atp867x_reinit_one(struct pci_dev *pdev) +{ + struct ata_host *host = dev_get_drvdata(&pdev->dev); + int rc; + + rc = ata_pci_device_do_resume(pdev); + if (rc) + return rc; + + atp867x_fixup(host); + + ata_host_resume(host); + return 0; +} +#endif + static struct pci_device_id atp867x_pci_tbl[] = { { PCI_VDEVICE(ARTOP, PCI_DEVICE_ID_ARTOP_ATP867A), 0 }, { PCI_VDEVICE(ARTOP, PCI_DEVICE_ID_ARTOP_ATP867B), 0 }, @@ -526,6 +561,10 @@ static struct pci_driver atp867x_driver = { .id_table = atp867x_pci_tbl, .probe = atp867x_init_one, .remove = ata_pci_remove_one, +#ifdef CONFIG_PM + .suspend = ata_pci_device_suspend, + .resume = atp867x_reinit_one, +#endif }; static int __init atp867x_init(void) diff --git a/drivers/ata/pata_sc1200.c b/drivers/ata/pata_sc1200.c index f49814d6fd2e..3bbed8322ecf 100644 --- a/drivers/ata/pata_sc1200.c +++ b/drivers/ata/pata_sc1200.c @@ -235,8 +235,7 @@ static int sc1200_init_one(struct pci_dev *dev, const struct pci_device_id *id) .udma_mask = ATA_UDMA2, .port_ops = &sc1200_port_ops }; - /* Can't enable port 2 yet, see top comments */ - const struct ata_port_info *ppi[] = { &info, }; + const struct ata_port_info *ppi[] = { &info, NULL }; return ata_pci_sff_init_one(dev, ppi, &sc1200_sht, NULL); } diff --git a/drivers/ata/pata_via.c b/drivers/ata/pata_via.c index 45657cacec43..88984b803d6d 100644 --- a/drivers/ata/pata_via.c +++ b/drivers/ata/pata_via.c @@ -111,7 +111,7 @@ static const struct via_isa_bridge { { "vt8251", PCI_DEVICE_ID_VIA_8251, 0x00, 0x2f, VIA_UDMA_133 | VIA_BAD_AST }, { "cx700", PCI_DEVICE_ID_VIA_CX700, 0x00, 0x2f, VIA_UDMA_133 | VIA_BAD_AST | VIA_SATA_PATA }, { "vt6410", PCI_DEVICE_ID_VIA_6410, 0x00, 0x2f, VIA_UDMA_133 | VIA_BAD_AST | VIA_NO_ENABLES }, - { "vt6415", PCI_DEVICE_ID_VIA_6415, 0x00, 0x2f, VIA_UDMA_133 | VIA_BAD_AST | VIA_NO_ENABLES }, + { "vt6415", PCI_DEVICE_ID_VIA_6415, 0x00, 0xff, VIA_UDMA_133 | VIA_BAD_AST | VIA_NO_ENABLES }, { "vt8237a", PCI_DEVICE_ID_VIA_8237A, 0x00, 0x2f, VIA_UDMA_133 | VIA_BAD_AST }, { "vt8237", PCI_DEVICE_ID_VIA_8237, 0x00, 0x2f, VIA_UDMA_133 | VIA_BAD_AST }, { "vt8235", PCI_DEVICE_ID_VIA_8235, 0x00, 0x2f, VIA_UDMA_133 | VIA_BAD_AST }, diff --git a/drivers/ata/sata_mv.c b/drivers/ata/sata_mv.c index 17f9ff9067a2..6f5093b7c8c5 100644 --- a/drivers/ata/sata_mv.c +++ b/drivers/ata/sata_mv.c @@ -1382,6 +1382,25 @@ static int mv_qc_defer(struct ata_queued_cmd *qc) */ if (pp->pp_flags & MV_PP_FLAG_DELAYED_EH) return ATA_DEFER_PORT; + + /* PIO commands need exclusive link: no other commands [DMA or PIO] + * can run concurrently. + * set excl_link when we want to send a PIO command in DMA mode + * or a non-NCQ command in NCQ mode. + * When we receive a command from that link, and there are no + * outstanding commands, mark a flag to clear excl_link and let + * the command go through. + */ + if (unlikely(ap->excl_link)) { + if (link == ap->excl_link) { + if (ap->nr_active_links) + return ATA_DEFER_PORT; + qc->flags |= ATA_QCFLAG_CLEAR_EXCL; + return 0; + } else + return ATA_DEFER_PORT; + } + /* * If the port is completely idle, then allow the new qc. */ @@ -1395,8 +1414,14 @@ static int mv_qc_defer(struct ata_queued_cmd *qc) * doesn't allow it. */ if ((pp->pp_flags & MV_PP_FLAG_EDMA_EN) && - (pp->pp_flags & MV_PP_FLAG_NCQ_EN) && ata_is_ncq(qc->tf.protocol)) - return 0; + (pp->pp_flags & MV_PP_FLAG_NCQ_EN)) { + if (ata_is_ncq(qc->tf.protocol)) + return 0; + else { + ap->excl_link = link; + return ATA_DEFER_PORT; + } + } return ATA_DEFER_PORT; } diff --git a/drivers/ata/sata_nv.c b/drivers/ata/sata_nv.c index 86a40582999c..1eb4e020eb5c 100644 --- a/drivers/ata/sata_nv.c +++ b/drivers/ata/sata_nv.c @@ -1594,9 +1594,21 @@ static int nv_hardreset(struct ata_link *link, unsigned int *class, !ata_dev_enabled(link->device)) sata_link_hardreset(link, sata_deb_timing_hotplug, deadline, NULL, NULL); - else if (!(ehc->i.flags & ATA_EHI_QUIET)) - ata_link_printk(link, KERN_INFO, - "nv: skipping hardreset on occupied port\n"); + else { + const unsigned long *timing = sata_ehc_deb_timing(ehc); + int rc; + + if (!(ehc->i.flags & ATA_EHI_QUIET)) + ata_link_printk(link, KERN_INFO, "nv: skipping " + "hardreset on occupied port\n"); + + /* make sure the link is online */ + rc = sata_link_resume(link, timing, deadline); + /* whine about phy resume failure but proceed */ + if (rc && rc != -EOPNOTSUPP) + ata_link_printk(link, KERN_WARNING, "failed to resume " + "link (errno=%d)\n", rc); + } /* device signature acquisition is unreliable */ return -EAGAIN; diff --git a/drivers/ata/sata_via.c b/drivers/ata/sata_via.c index bdd43c7f432e..02efd9a83d26 100644 --- a/drivers/ata/sata_via.c +++ b/drivers/ata/sata_via.c @@ -93,7 +93,6 @@ static const struct pci_device_id svia_pci_tbl[] = { { PCI_VDEVICE(VIA, 0x7372), vt6420 }, { PCI_VDEVICE(VIA, 0x5287), vt8251 }, /* 2 sata chnls (Master/Slave) */ { PCI_VDEVICE(VIA, 0x9000), vt8251 }, - { PCI_VDEVICE(VIA, 0x9040), vt8251 }, { } /* terminate list */ }; diff --git a/drivers/base/bus.c b/drivers/base/bus.c index 973bf2ad4e0d..63c143e54a57 100644 --- a/drivers/base/bus.c +++ b/drivers/base/bus.c @@ -689,15 +689,19 @@ int bus_add_driver(struct device_driver *drv) printk(KERN_ERR "%s: driver_add_attrs(%s) failed\n", __func__, drv->name); } - error = add_bind_files(drv); - if (error) { - /* Ditto */ - printk(KERN_ERR "%s: add_bind_files(%s) failed\n", - __func__, drv->name); + + if (!drv->suppress_bind_attrs) { + error = add_bind_files(drv); + if (error) { + /* Ditto */ + printk(KERN_ERR "%s: add_bind_files(%s) failed\n", + __func__, drv->name); + } } kobject_uevent(&priv->kobj, KOBJ_ADD); return 0; + out_unregister: kfree(drv->p); drv->p = NULL; @@ -720,7 +724,8 @@ void bus_remove_driver(struct device_driver *drv) if (!drv->bus) return; - remove_bind_files(drv); + if (!drv->suppress_bind_attrs) + remove_bind_files(drv); driver_remove_attrs(drv->bus, drv); driver_remove_file(drv, &driver_attr_uevent); klist_remove(&drv->p->knode_bus); diff --git a/drivers/base/driver.c b/drivers/base/driver.c index ed2ebd3c287d..f367885a7646 100644 --- a/drivers/base/driver.c +++ b/drivers/base/driver.c @@ -236,7 +236,7 @@ int driver_register(struct device_driver *drv) put_driver(other); printk(KERN_ERR "Error: Driver '%s' is already registered, " "aborting...\n", drv->name); - return -EEXIST; + return -EBUSY; } ret = bus_add_driver(drv); diff --git a/drivers/base/platform.c b/drivers/base/platform.c index ed156a13aa40..4fa954b07ac4 100644 --- a/drivers/base/platform.c +++ b/drivers/base/platform.c @@ -521,11 +521,15 @@ int __init_or_module platform_driver_probe(struct platform_driver *drv, { int retval, code; + /* make sure driver won't have bind/unbind attributes */ + drv->driver.suppress_bind_attrs = true; + /* temporary section violation during probe() */ drv->probe = probe; retval = code = platform_driver_register(drv); - /* Fixup that section violation, being paranoid about code scanning + /* + * Fixup that section violation, being paranoid about code scanning * the list of drivers in order to probe new devices. Check to see * if the probe was successful, and make sure any forced probes of * new devices fail. diff --git a/drivers/base/power/main.c b/drivers/base/power/main.c index e0dc4071e088..8aa2443182d5 100644 --- a/drivers/base/power/main.c +++ b/drivers/base/power/main.c @@ -511,6 +511,7 @@ static void dpm_complete(pm_message_t state) INIT_LIST_HEAD(&list); mutex_lock(&dpm_list_mtx); + transition_started = false; while (!list_empty(&dpm_list)) { struct device *dev = to_device(dpm_list.prev); diff --git a/drivers/base/power/runtime.c b/drivers/base/power/runtime.c index 38556f6cc22d..a770498a74ec 100644 --- a/drivers/base/power/runtime.c +++ b/drivers/base/power/runtime.c @@ -51,8 +51,6 @@ static int __pm_runtime_idle(struct device *dev) { int retval = 0; - dev_dbg(dev, "__pm_runtime_idle()!\n"); - if (dev->power.runtime_error) retval = -EINVAL; else if (dev->power.idle_notification) @@ -93,8 +91,6 @@ static int __pm_runtime_idle(struct device *dev) wake_up_all(&dev->power.wait_queue); out: - dev_dbg(dev, "__pm_runtime_idle() returns %d!\n", retval); - return retval; } diff --git a/drivers/block/cciss.c b/drivers/block/cciss.c index fb5be2d95d52..6399e5090df4 100644 --- a/drivers/block/cciss.c +++ b/drivers/block/cciss.c @@ -68,6 +68,12 @@ MODULE_SUPPORTED_DEVICE("HP SA5i SA5i+ SA532 SA5300 SA5312 SA641 SA642 SA6400" MODULE_VERSION("3.6.20"); MODULE_LICENSE("GPL"); +static int cciss_allow_hpsa; +module_param(cciss_allow_hpsa, int, S_IRUGO|S_IWUSR); +MODULE_PARM_DESC(cciss_allow_hpsa, + "Prevent cciss driver from accessing hardware known to be " + " supported by the hpsa driver"); + #include "cciss_cmd.h" #include "cciss.h" #include <linux/cciss_ioctl.h> @@ -101,8 +107,6 @@ static const struct pci_device_id cciss_pci_device_id[] = { {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x3249}, {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x324A}, {PCI_VENDOR_ID_HP, PCI_DEVICE_ID_HP_CISSE, 0x103C, 0x324B}, - {PCI_VENDOR_ID_HP, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, - PCI_CLASS_STORAGE_RAID << 8, 0xffff << 8, 0}, {0,} }; @@ -123,8 +127,6 @@ static struct board_type products[] = { {0x409D0E11, "Smart Array 6400 EM", &SA5_access}, {0x40910E11, "Smart Array 6i", &SA5_access}, {0x3225103C, "Smart Array P600", &SA5_access}, - {0x3223103C, "Smart Array P800", &SA5_access}, - {0x3234103C, "Smart Array P400", &SA5_access}, {0x3235103C, "Smart Array P400i", &SA5_access}, {0x3211103C, "Smart Array E200i", &SA5_access}, {0x3212103C, "Smart Array E200", &SA5_access}, @@ -132,6 +134,10 @@ static struct board_type products[] = { {0x3214103C, "Smart Array E200i", &SA5_access}, {0x3215103C, "Smart Array E200i", &SA5_access}, {0x3237103C, "Smart Array E500", &SA5_access}, +/* controllers below this line are also supported by the hpsa driver. */ +#define HPSA_BOUNDARY 0x3223103C + {0x3223103C, "Smart Array P800", &SA5_access}, + {0x3234103C, "Smart Array P400", &SA5_access}, {0x323D103C, "Smart Array P700m", &SA5_access}, {0x3241103C, "Smart Array P212", &SA5_access}, {0x3243103C, "Smart Array P410", &SA5_access}, @@ -140,7 +146,6 @@ static struct board_type products[] = { {0x3249103C, "Smart Array P812", &SA5_access}, {0x324A103C, "Smart Array P712m", &SA5_access}, {0x324B103C, "Smart Array P711m", &SA5_access}, - {0xFFFF103C, "Unknown Smart Array", &SA5_access}, }; /* How long to wait (in milliseconds) for board to go into simple mode */ @@ -3754,7 +3759,27 @@ static int __devinit cciss_pci_init(ctlr_info_t *c, struct pci_dev *pdev) __u64 cfg_offset; __u32 cfg_base_addr; __u64 cfg_base_addr_index; - int i, err; + int i, prod_index, err; + + subsystem_vendor_id = pdev->subsystem_vendor; + subsystem_device_id = pdev->subsystem_device; + board_id = (((__u32) (subsystem_device_id << 16) & 0xffff0000) | + subsystem_vendor_id); + + for (i = 0; i < ARRAY_SIZE(products); i++) { + /* Stand aside for hpsa driver on request */ + if (cciss_allow_hpsa && products[i].board_id == HPSA_BOUNDARY) + return -ENODEV; + if (board_id == products[i].board_id) + break; + } + prod_index = i; + if (prod_index == ARRAY_SIZE(products)) { + dev_warn(&pdev->dev, + "unrecognized board ID: 0x%08lx, ignoring.\n", + (unsigned long) board_id); + return -ENODEV; + } /* check to see if controller has been disabled */ /* BEFORE trying to enable it */ @@ -3778,11 +3803,6 @@ static int __devinit cciss_pci_init(ctlr_info_t *c, struct pci_dev *pdev) return err; } - subsystem_vendor_id = pdev->subsystem_vendor; - subsystem_device_id = pdev->subsystem_device; - board_id = (((__u32) (subsystem_device_id << 16) & 0xffff0000) | - subsystem_vendor_id); - #ifdef CCISS_DEBUG printk("command = %x\n", command); printk("irq = %x\n", pdev->irq); @@ -3868,14 +3888,9 @@ static int __devinit cciss_pci_init(ctlr_info_t *c, struct pci_dev *pdev) * leave a little room for ioctl calls. */ c->max_commands = readl(&(c->cfgtable->CmdsOutMax)); - for (i = 0; i < ARRAY_SIZE(products); i++) { - if (board_id == products[i].board_id) { - c->product_name = products[i].product_name; - c->access = *(products[i].access); - c->nr_cmds = c->max_commands - 4; - break; - } - } + c->product_name = products[prod_index].product_name; + c->access = *(products[prod_index].access); + c->nr_cmds = c->max_commands - 4; if ((readb(&c->cfgtable->Signature[0]) != 'C') || (readb(&c->cfgtable->Signature[1]) != 'I') || (readb(&c->cfgtable->Signature[2]) != 'S') || @@ -3884,27 +3899,6 @@ static int __devinit cciss_pci_init(ctlr_info_t *c, struct pci_dev *pdev) err = -ENODEV; goto err_out_free_res; } - /* We didn't find the controller in our list. We know the - * signature is valid. If it's an HP device let's try to - * bind to the device and fire it up. Otherwise we bail. - */ - if (i == ARRAY_SIZE(products)) { - if (subsystem_vendor_id == PCI_VENDOR_ID_HP) { - c->product_name = products[i-1].product_name; - c->access = *(products[i-1].access); - c->nr_cmds = c->max_commands - 4; - printk(KERN_WARNING "cciss: This is an unknown " - "Smart Array controller.\n" - "cciss: Please update to the latest driver " - "available from www.hp.com.\n"); - } else { - printk(KERN_WARNING "cciss: Sorry, I don't know how" - " to access the Smart Array controller %08lx\n" - , (unsigned long)board_id); - err = -ENODEV; - goto err_out_free_res; - } - } #ifdef CONFIG_X86 { /* Need to enable prefetch in the SCSI core for 6400 in x86 */ @@ -4254,7 +4248,7 @@ static int __devinit cciss_init_one(struct pci_dev *pdev, mutex_init(&hba[i]->busy_shutting_down); if (cciss_pci_init(hba[i], pdev) != 0) - goto clean0; + goto clean_no_release_regions; sprintf(hba[i]->devname, "cciss%d", i); hba[i]->ctlr = i; @@ -4391,13 +4385,14 @@ clean2: clean1: cciss_destroy_hba_sysfs_entry(hba[i]); clean0: + pci_release_regions(pdev); +clean_no_release_regions: hba[i]->busy_initializing = 0; /* * Deliberately omit pci_disable_device(): it does something nasty to * Smart Array controllers that pci_enable_device does not undo */ - pci_release_regions(pdev); pci_set_drvdata(pdev, NULL); free_hba(i); return -1; diff --git a/drivers/block/loop.c b/drivers/block/loop.c index edda9ea7c626..bd112c8c7bcd 100644 --- a/drivers/block/loop.c +++ b/drivers/block/loop.c @@ -949,7 +949,7 @@ static int loop_clr_fd(struct loop_device *lo, struct block_device *bdev) lo->lo_state = Lo_unbound; /* This is safe: open() is still holding a reference. */ module_put(THIS_MODULE); - if (max_part > 0) + if (max_part > 0 && bdev) ioctl_by_bdev(bdev, BLKRRPART, 0); mutex_unlock(&lo->lo_ctl_mutex); /* diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c index 43f19389647a..51042f0ba7e1 100644 --- a/drivers/block/virtio_blk.c +++ b/drivers/block/virtio_blk.c @@ -3,7 +3,6 @@ #include <linux/blkdev.h> #include <linux/hdreg.h> #include <linux/virtio.h> -#include <linux/virtio_ids.h> #include <linux/virtio_blk.h> #include <linux/scatterlist.h> @@ -183,34 +182,6 @@ static void do_virtblk_request(struct request_queue *q) vblk->vq->vq_ops->kick(vblk->vq); } -/* return ATA identify data - */ -static int virtblk_identify(struct gendisk *disk, void *argp) -{ - struct virtio_blk *vblk = disk->private_data; - void *opaque; - int err = -ENOMEM; - - opaque = kmalloc(VIRTIO_BLK_ID_BYTES, GFP_KERNEL); - if (!opaque) - goto out; - - err = virtio_config_buf(vblk->vdev, VIRTIO_BLK_F_IDENTIFY, - offsetof(struct virtio_blk_config, identify), opaque, - VIRTIO_BLK_ID_BYTES); - - if (err) - goto out_kfree; - - if (copy_to_user(argp, opaque, VIRTIO_BLK_ID_BYTES)) - err = -EFAULT; - -out_kfree: - kfree(opaque); -out: - return err; -} - static void virtblk_prepare_flush(struct request_queue *q, struct request *req) { req->cmd_type = REQ_TYPE_LINUX_BLOCK; @@ -222,10 +193,6 @@ static int virtblk_ioctl(struct block_device *bdev, fmode_t mode, { struct gendisk *disk = bdev->bd_disk; struct virtio_blk *vblk = disk->private_data; - void __user *argp = (void __user *)data; - - if (cmd == HDIO_GET_IDENTITY) - return virtblk_identify(disk, argp); /* * Only allow the generic SCSI ioctls if the host can support it. @@ -233,7 +200,8 @@ static int virtblk_ioctl(struct block_device *bdev, fmode_t mode, if (!virtio_has_feature(vblk->vdev, VIRTIO_BLK_F_SCSI)) return -ENOTTY; - return scsi_cmd_ioctl(disk->queue, disk, mode, cmd, argp); + return scsi_cmd_ioctl(disk->queue, disk, mode, cmd, + (void __user *)data); } /* We provide getgeo only to please some old bootloader/partitioning tools */ @@ -332,7 +300,6 @@ static int __devinit virtblk_probe(struct virtio_device *vdev) } vblk->disk->queue->queuedata = vblk; - queue_flag_set_unlocked(QUEUE_FLAG_VIRT, vblk->disk->queue); if (index < 26) { sprintf(vblk->disk->disk_name, "vd%c", 'a' + index % 26); @@ -445,7 +412,7 @@ static struct virtio_device_id id_table[] = { static unsigned int features[] = { VIRTIO_BLK_F_BARRIER, VIRTIO_BLK_F_SEG_MAX, VIRTIO_BLK_F_SIZE_MAX, VIRTIO_BLK_F_GEOMETRY, VIRTIO_BLK_F_RO, VIRTIO_BLK_F_BLK_SIZE, - VIRTIO_BLK_F_SCSI, VIRTIO_BLK_F_IDENTIFY, VIRTIO_BLK_F_FLUSH + VIRTIO_BLK_F_SCSI, VIRTIO_BLK_F_FLUSH }; /* diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index 7ba91aa3fe8b..44bc8bbabf54 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -591,6 +591,7 @@ static int btusb_close(struct hci_dev *hdev) return 0; cancel_work_sync(&data->work); + cancel_work_sync(&data->waker); clear_bit(BTUSB_ISOC_RUNNING, &data->flags); clear_bit(BTUSB_BULK_RUNNING, &data->flags); @@ -599,11 +600,13 @@ static int btusb_close(struct hci_dev *hdev) btusb_stop_traffic(data); err = usb_autopm_get_interface(data->intf); if (err < 0) - return 0; + goto failed; data->intf->needs_remote_wakeup = 0; usb_autopm_put_interface(data->intf); +failed: + usb_scuttle_anchored_urbs(&data->deferred); return 0; } diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig index 08a6f50ae791..6aad99ec4e0f 100644 --- a/drivers/char/Kconfig +++ b/drivers/char/Kconfig @@ -323,7 +323,7 @@ config SPECIALIX config SX tristate "Specialix SX (and SI) card support" - depends on SERIAL_NONSTANDARD && (PCI || EISA || ISA) + depends on SERIAL_NONSTANDARD && (PCI || EISA || ISA) && BROKEN help This is a driver for the SX and SI multiport serial cards. Please read the file <file:Documentation/serial/sx.txt> for details. @@ -334,7 +334,7 @@ config SX config RIO tristate "Specialix RIO system support" - depends on SERIAL_NONSTANDARD + depends on SERIAL_NONSTANDARD && BROKEN help This is a driver for the Specialix RIO, a smart serial card which drives an outboard box that can support up to 128 ports. Product @@ -395,7 +395,7 @@ config NOZOMI config A2232 tristate "Commodore A2232 serial support (EXPERIMENTAL)" - depends on EXPERIMENTAL && ZORRO && BROKEN_ON_SMP + depends on EXPERIMENTAL && ZORRO && BROKEN ---help--- This option supports the 2232 7-port serial card shipped with the Amiga 2000 and other Zorro-bus machines, dating from 1989. At diff --git a/drivers/char/agp/intel-agp.c b/drivers/char/agp/intel-agp.c index 4068467ce7b9..10e1f0390bbb 100644 --- a/drivers/char/agp/intel-agp.c +++ b/drivers/char/agp/intel-agp.c @@ -1161,12 +1161,6 @@ static int intel_i915_configure(void) intel_i9xx_setup_flush(); -#ifdef USE_PCI_DMA_API - if (pci_set_dma_mask(intel_private.pcidev, DMA_BIT_MASK(36))) - dev_err(&intel_private.pcidev->dev, - "set gfx device dma mask 36bit failed!\n"); -#endif - return 0; } @@ -2456,6 +2450,11 @@ static int __devinit agp_intel_probe(struct pci_dev *pdev, &bridge->mode); } + if (bridge->driver->mask_memory == intel_i965_mask_memory) + if (pci_set_dma_mask(intel_private.pcidev, DMA_BIT_MASK(36))) + dev_err(&intel_private.pcidev->dev, + "set gfx device dma mask 36bit failed!\n"); + pci_set_drvdata(pdev, bridge); return agp_add_bridge(bridge); } diff --git a/drivers/char/agp/parisc-agp.c b/drivers/char/agp/parisc-agp.c index 60ab75104da9..1c129211302d 100644 --- a/drivers/char/agp/parisc-agp.c +++ b/drivers/char/agp/parisc-agp.c @@ -217,7 +217,7 @@ static const struct agp_bridge_driver parisc_agp_driver = { .configure = parisc_agp_configure, .fetch_size = parisc_agp_fetch_size, .tlb_flush = parisc_agp_tlbflush, - .mask_memory = parisc_agp_page_mask_memory, + .mask_memory = parisc_agp_mask_memory, .masks = parisc_agp_masks, .agp_enable = parisc_agp_enable, .cache_flush = global_cache_flush, diff --git a/drivers/char/applicom.c b/drivers/char/applicom.c index 73a0765344b6..fe2cb2f5db17 100644 --- a/drivers/char/applicom.c +++ b/drivers/char/applicom.c @@ -23,6 +23,7 @@ #include <linux/kernel.h> #include <linux/module.h> #include <linux/interrupt.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/errno.h> #include <linux/miscdevice.h> diff --git a/drivers/char/epca.c b/drivers/char/epca.c index 9d589e3144de..dde5134713e2 100644 --- a/drivers/char/epca.c +++ b/drivers/char/epca.c @@ -30,6 +30,7 @@ #include <linux/kernel.h> #include <linux/types.h> #include <linux/init.h> +#include <linux/sched.h> #include <linux/serial.h> #include <linux/delay.h> #include <linux/ctype.h> diff --git a/drivers/char/generic_serial.c b/drivers/char/generic_serial.c index 9e4e569dc00d..d400cbd280f2 100644 --- a/drivers/char/generic_serial.c +++ b/drivers/char/generic_serial.c @@ -22,6 +22,7 @@ #include <linux/module.h> #include <linux/kernel.h> #include <linux/tty.h> +#include <linux/sched.h> #include <linux/serial.h> #include <linux/mm.h> #include <linux/generic_serial.h> diff --git a/drivers/char/genrtc.c b/drivers/char/genrtc.c index aac0985a572b..31e7c91c2d9d 100644 --- a/drivers/char/genrtc.c +++ b/drivers/char/genrtc.c @@ -43,6 +43,7 @@ #define RTC_VERSION "1.07" #include <linux/module.h> +#include <linux/sched.h> #include <linux/errno.h> #include <linux/miscdevice.h> #include <linux/fcntl.h> diff --git a/drivers/char/hvc_xen.c b/drivers/char/hvc_xen.c index eba999f8598d..a6ee32b599a8 100644 --- a/drivers/char/hvc_xen.c +++ b/drivers/char/hvc_xen.c @@ -55,7 +55,7 @@ static inline void notify_daemon(void) notify_remote_via_evtchn(xen_start_info->console.domU.evtchn); } -static int write_console(uint32_t vtermno, const char *data, int len) +static int __write_console(const char *data, int len) { struct xencons_interface *intf = xencons_interface(); XENCONS_RING_IDX cons, prod; @@ -76,6 +76,29 @@ static int write_console(uint32_t vtermno, const char *data, int len) return sent; } +static int write_console(uint32_t vtermno, const char *data, int len) +{ + int ret = len; + + /* + * Make sure the whole buffer is emitted, polling if + * necessary. We don't ever want to rely on the hvc daemon + * because the most interesting console output is when the + * kernel is crippled. + */ + while (len) { + int sent = __write_console(data, len); + + data += sent; + len -= sent; + + if (unlikely(len)) + HYPERVISOR_sched_op(SCHEDOP_yield, NULL); + } + + return ret; +} + static int read_console(uint32_t vtermno, char *buf, int len) { struct xencons_interface *intf = xencons_interface(); diff --git a/drivers/char/hw_random/virtio-rng.c b/drivers/char/hw_random/virtio-rng.c index 962968f05b94..915157fcff98 100644 --- a/drivers/char/hw_random/virtio-rng.c +++ b/drivers/char/hw_random/virtio-rng.c @@ -21,7 +21,6 @@ #include <linux/scatterlist.h> #include <linux/spinlock.h> #include <linux/virtio.h> -#include <linux/virtio_ids.h> #include <linux/virtio_rng.h> /* The host will fill any buffer we give it with sweet, sweet randomness. We @@ -117,7 +116,7 @@ static int virtrng_probe(struct virtio_device *vdev) return 0; } -static void virtrng_remove(struct virtio_device *vdev) +static void __devexit virtrng_remove(struct virtio_device *vdev) { vdev->config->reset(vdev); hwrng_unregister(&virtio_hwrng); diff --git a/drivers/char/istallion.c b/drivers/char/istallion.c index ab2f3349c5c4..402838f4083e 100644 --- a/drivers/char/istallion.c +++ b/drivers/char/istallion.c @@ -19,6 +19,7 @@ /*****************************************************************************/ #include <linux/module.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/smp_lock.h> #include <linux/interrupt.h> diff --git a/drivers/char/nozomi.c b/drivers/char/nozomi.c index ec58d8c387ff..d3400b20444f 100644 --- a/drivers/char/nozomi.c +++ b/drivers/char/nozomi.c @@ -48,6 +48,7 @@ #include <linux/tty.h> #include <linux/tty_driver.h> #include <linux/tty_flip.h> +#include <linux/sched.h> #include <linux/serial.h> #include <linux/interrupt.h> #include <linux/kmod.h> diff --git a/drivers/char/pty.c b/drivers/char/pty.c index e066c4fdf81b..62f282e67638 100644 --- a/drivers/char/pty.c +++ b/drivers/char/pty.c @@ -18,6 +18,7 @@ #include <linux/tty.h> #include <linux/tty_flip.h> #include <linux/fcntl.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/major.h> #include <linux/mm.h> diff --git a/drivers/char/rio/riocmd.c b/drivers/char/rio/riocmd.c index 01f2654d5a2e..f121357e5af0 100644 --- a/drivers/char/rio/riocmd.c +++ b/drivers/char/rio/riocmd.c @@ -32,6 +32,7 @@ */ #include <linux/module.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/errno.h> #include <linux/tty.h> diff --git a/drivers/char/rio/rioctrl.c b/drivers/char/rio/rioctrl.c index 74339559f0b9..780506326a73 100644 --- a/drivers/char/rio/rioctrl.c +++ b/drivers/char/rio/rioctrl.c @@ -31,6 +31,7 @@ */ #include <linux/module.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/errno.h> #include <asm/io.h> diff --git a/drivers/char/rio/riotty.c b/drivers/char/rio/riotty.c index 2fb49e89b324..47fab7c33073 100644 --- a/drivers/char/rio/riotty.c +++ b/drivers/char/rio/riotty.c @@ -33,6 +33,7 @@ #define __EXPLICIT_DEF_H__ #include <linux/module.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/errno.h> #include <linux/tty.h> diff --git a/drivers/char/rtc.c b/drivers/char/rtc.c index e0d0f8b2696b..bc4ab3e54550 100644 --- a/drivers/char/rtc.c +++ b/drivers/char/rtc.c @@ -74,6 +74,7 @@ #include <linux/proc_fs.h> #include <linux/seq_file.h> #include <linux/spinlock.h> +#include <linux/sched.h> #include <linux/sysctl.h> #include <linux/wait.h> #include <linux/bcd.h> diff --git a/drivers/char/ser_a2232.c b/drivers/char/ser_a2232.c index 33a2b531802e..9610861d1f5f 100644 --- a/drivers/char/ser_a2232.c +++ b/drivers/char/ser_a2232.c @@ -89,6 +89,7 @@ #include <linux/interrupt.h> #include <linux/kernel.h> #include <linux/errno.h> +#include <linux/sched.h> #include <linux/tty.h> #include <asm/setup.h> diff --git a/drivers/char/sonypi.c b/drivers/char/sonypi.c index fd3dced97776..8c262aaf7c26 100644 --- a/drivers/char/sonypi.c +++ b/drivers/char/sonypi.c @@ -36,6 +36,7 @@ */ #include <linux/module.h> +#include <linux/sched.h> #include <linux/input.h> #include <linux/pci.h> #include <linux/init.h> diff --git a/drivers/char/stallion.c b/drivers/char/stallion.c index 53e504f41b20..db6dcfa35ba0 100644 --- a/drivers/char/stallion.c +++ b/drivers/char/stallion.c @@ -27,6 +27,7 @@ /*****************************************************************************/ #include <linux/module.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/interrupt.h> #include <linux/tty.h> diff --git a/drivers/char/tlclk.c b/drivers/char/tlclk.c index 8f2284be68e1..80ea6bcfffdc 100644 --- a/drivers/char/tlclk.c +++ b/drivers/char/tlclk.c @@ -32,6 +32,7 @@ #include <linux/kernel.h> /* printk() */ #include <linux/fs.h> /* everything... */ #include <linux/errno.h> /* error codes */ +#include <linux/sched.h> #include <linux/slab.h> #include <linux/ioport.h> #include <linux/interrupt.h> diff --git a/drivers/char/tpm/tpm.c b/drivers/char/tpm/tpm.c index 45d58002b06c..47c2d2763456 100644 --- a/drivers/char/tpm/tpm.c +++ b/drivers/char/tpm/tpm.c @@ -696,8 +696,7 @@ int __tpm_pcr_read(struct tpm_chip *chip, int pcr_idx, u8 *res_buf) cmd.header.in = pcrread_header; cmd.params.pcrread_in.pcr_idx = cpu_to_be32(pcr_idx); - BUG_ON(cmd.header.in.length > READ_PCR_RESULT_SIZE); - rc = transmit_cmd(chip, &cmd, cmd.header.in.length, + rc = transmit_cmd(chip, &cmd, READ_PCR_RESULT_SIZE, "attempting to read a pcr value"); if (rc == 0) diff --git a/drivers/char/tty_buffer.c b/drivers/char/tty_buffer.c index 3108991c5c8b..66fa4e10d76b 100644 --- a/drivers/char/tty_buffer.c +++ b/drivers/char/tty_buffer.c @@ -402,28 +402,26 @@ static void flush_to_ldisc(struct work_struct *work) container_of(work, struct tty_struct, buf.work.work); unsigned long flags; struct tty_ldisc *disc; - struct tty_buffer *tbuf, *head; - char *char_buf; - unsigned char *flag_buf; disc = tty_ldisc_ref(tty); if (disc == NULL) /* !TTY_LDISC */ return; spin_lock_irqsave(&tty->buf.lock, flags); - /* So we know a flush is running */ - set_bit(TTY_FLUSHING, &tty->flags); - head = tty->buf.head; - if (head != NULL) { - tty->buf.head = NULL; - for (;;) { - int count = head->commit - head->read; + + if (!test_and_set_bit(TTY_FLUSHING, &tty->flags)) { + struct tty_buffer *head; + while ((head = tty->buf.head) != NULL) { + int count; + char *char_buf; + unsigned char *flag_buf; + + count = head->commit - head->read; if (!count) { if (head->next == NULL) break; - tbuf = head; - head = head->next; - tty_buffer_free(tty, tbuf); + tty->buf.head = head->next; + tty_buffer_free(tty, head); continue; } /* Ldisc or user is trying to flush the buffers @@ -445,9 +443,9 @@ static void flush_to_ldisc(struct work_struct *work) flag_buf, count); spin_lock_irqsave(&tty->buf.lock, flags); } - /* Restore the queue head */ - tty->buf.head = head; + clear_bit(TTY_FLUSHING, &tty->flags); } + /* We may have a deferred request to flush the input buffer, if so pull the chain under the lock and empty the queue */ if (test_bit(TTY_FLUSHPENDING, &tty->flags)) { @@ -455,7 +453,6 @@ static void flush_to_ldisc(struct work_struct *work) clear_bit(TTY_FLUSHPENDING, &tty->flags); wake_up(&tty->read_wait); } - clear_bit(TTY_FLUSHING, &tty->flags); spin_unlock_irqrestore(&tty->buf.lock, flags); tty_ldisc_deref(disc); @@ -471,7 +468,7 @@ static void flush_to_ldisc(struct work_struct *work) */ void tty_flush_to_ldisc(struct tty_struct *tty) { - flush_to_ldisc(&tty->buf.work.work); + flush_delayed_work(&tty->buf.work); } /** diff --git a/drivers/char/tty_port.c b/drivers/char/tty_port.c index a4bbb28f10be..2e8552dc5eda 100644 --- a/drivers/char/tty_port.c +++ b/drivers/char/tty_port.c @@ -221,6 +221,9 @@ int tty_port_block_til_ready(struct tty_port *port, the port has just hung up or is in another error state */ if ((filp->f_flags & O_NONBLOCK) || (tty->flags & (1 << TTY_IO_ERROR))) { + /* Indicate we are open */ + if (tty->termios->c_cflag & CBAUD) + tty_port_raise_dtr_rts(port); port->flags |= ASYNC_NORMAL_ACTIVE; return 0; } diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c index 0d328b59568d..a035ae39a359 100644 --- a/drivers/char/virtio_console.c +++ b/drivers/char/virtio_console.c @@ -31,7 +31,6 @@ #include <linux/err.h> #include <linux/init.h> #include <linux/virtio.h> -#include <linux/virtio_ids.h> #include <linux/virtio_console.h> #include "hvc_console.h" diff --git a/drivers/char/vt_ioctl.c b/drivers/char/vt_ioctl.c index 6b36ee56e6fe..ed86d3bf249a 100644 --- a/drivers/char/vt_ioctl.c +++ b/drivers/char/vt_ioctl.c @@ -1532,7 +1532,7 @@ long vt_compat_ioctl(struct tty_struct *tty, struct file * file, case PIO_UNIMAP: case GIO_UNIMAP: - ret = do_unimap_ioctl(cmd, up, perm, vc); + ret = compat_unimap_ioctl(cmd, up, perm, vc); break; /* diff --git a/drivers/cpufreq/cpufreq.c b/drivers/cpufreq/cpufreq.c index 3938c7817095..ff57c40e9b8b 100644 --- a/drivers/cpufreq/cpufreq.c +++ b/drivers/cpufreq/cpufreq.c @@ -41,7 +41,7 @@ static struct cpufreq_driver *cpufreq_driver; static DEFINE_PER_CPU(struct cpufreq_policy *, cpufreq_cpu_data); #ifdef CONFIG_HOTPLUG_CPU /* This one keeps track of the previously set governor of a removed CPU */ -static DEFINE_PER_CPU(struct cpufreq_governor *, cpufreq_cpu_governor); +static DEFINE_PER_CPU(char[CPUFREQ_NAME_LEN], cpufreq_cpu_governor); #endif static DEFINE_SPINLOCK(cpufreq_driver_lock); @@ -774,10 +774,12 @@ int cpufreq_add_dev_policy(unsigned int cpu, struct cpufreq_policy *policy, #ifdef CONFIG_SMP unsigned long flags; unsigned int j; - #ifdef CONFIG_HOTPLUG_CPU - if (per_cpu(cpufreq_cpu_governor, cpu)) { - policy->governor = per_cpu(cpufreq_cpu_governor, cpu); + struct cpufreq_governor *gov; + + gov = __find_governor(per_cpu(cpufreq_cpu_governor, cpu)); + if (gov) { + policy->governor = gov; dprintk("Restoring governor %s for cpu %d\n", policy->governor->name, cpu); } @@ -949,10 +951,13 @@ err_out_kobj_put: static int cpufreq_add_dev(struct sys_device *sys_dev) { unsigned int cpu = sys_dev->id; - int ret = 0; + int ret = 0, found = 0; struct cpufreq_policy *policy; unsigned long flags; unsigned int j; +#ifdef CONFIG_HOTPLUG_CPU + int sibling; +#endif if (cpu_is_offline(cpu)) return 0; @@ -999,7 +1004,19 @@ static int cpufreq_add_dev(struct sys_device *sys_dev) INIT_WORK(&policy->update, handle_update); /* Set governor before ->init, so that driver could check it */ - policy->governor = CPUFREQ_DEFAULT_GOVERNOR; +#ifdef CONFIG_HOTPLUG_CPU + for_each_online_cpu(sibling) { + struct cpufreq_policy *cp = per_cpu(cpufreq_cpu_data, sibling); + if (cp && cp->governor && + (cpumask_test_cpu(cpu, cp->related_cpus))) { + policy->governor = cp->governor; + found = 1; + break; + } + } +#endif + if (!found) + policy->governor = CPUFREQ_DEFAULT_GOVERNOR; /* call driver. From then on the cpufreq must be able * to accept all calls to ->verify and ->setpolicy for this CPU */ @@ -1111,7 +1128,8 @@ static int __cpufreq_remove_dev(struct sys_device *sys_dev) #ifdef CONFIG_SMP #ifdef CONFIG_HOTPLUG_CPU - per_cpu(cpufreq_cpu_governor, cpu) = data->governor; + strncpy(per_cpu(cpufreq_cpu_governor, cpu), data->governor->name, + CPUFREQ_NAME_LEN); #endif /* if we have other CPUs still registered, we need to unlink them, @@ -1135,7 +1153,8 @@ static int __cpufreq_remove_dev(struct sys_device *sys_dev) continue; dprintk("removing link for cpu %u\n", j); #ifdef CONFIG_HOTPLUG_CPU - per_cpu(cpufreq_cpu_governor, j) = data->governor; + strncpy(per_cpu(cpufreq_cpu_governor, j), + data->governor->name, CPUFREQ_NAME_LEN); #endif cpu_sys_dev = get_cpu_sysdev(j); sysfs_remove_link(&cpu_sys_dev->kobj, "cpufreq"); @@ -1606,9 +1625,22 @@ EXPORT_SYMBOL_GPL(cpufreq_register_governor); void cpufreq_unregister_governor(struct cpufreq_governor *governor) { +#ifdef CONFIG_HOTPLUG_CPU + int cpu; +#endif + if (!governor) return; +#ifdef CONFIG_HOTPLUG_CPU + for_each_present_cpu(cpu) { + if (cpu_online(cpu)) + continue; + if (!strcmp(per_cpu(cpufreq_cpu_governor, cpu), governor->name)) + strcpy(per_cpu(cpufreq_cpu_governor, cpu), "\0"); + } +#endif + mutex_lock(&cpufreq_governor_mutex); list_del(&governor->governor_list); mutex_unlock(&cpufreq_governor_mutex); diff --git a/drivers/cpufreq/cpufreq_conservative.c b/drivers/cpufreq/cpufreq_conservative.c index bc33ddc9c97c..c7b081b839ff 100644 --- a/drivers/cpufreq/cpufreq_conservative.c +++ b/drivers/cpufreq/cpufreq_conservative.c @@ -116,9 +116,9 @@ static inline cputime64_t get_cpu_idle_time_jiffy(unsigned int cpu, idle_time = cputime64_sub(cur_wall_time, busy_time); if (wall) - *wall = cur_wall_time; + *wall = (cputime64_t)jiffies_to_usecs(cur_wall_time); - return idle_time; + return (cputime64_t)jiffies_to_usecs(idle_time);; } static inline cputime64_t get_cpu_idle_time(unsigned int cpu, cputime64_t *wall) diff --git a/drivers/cpufreq/cpufreq_ondemand.c b/drivers/cpufreq/cpufreq_ondemand.c index 071699de50ee..4b34ade2332b 100644 --- a/drivers/cpufreq/cpufreq_ondemand.c +++ b/drivers/cpufreq/cpufreq_ondemand.c @@ -133,9 +133,9 @@ static inline cputime64_t get_cpu_idle_time_jiffy(unsigned int cpu, idle_time = cputime64_sub(cur_wall_time, busy_time); if (wall) - *wall = cur_wall_time; + *wall = (cputime64_t)jiffies_to_usecs(cur_wall_time); - return idle_time; + return (cputime64_t)jiffies_to_usecs(idle_time); } static inline cputime64_t get_cpu_idle_time(unsigned int cpu, cputime64_t *wall) diff --git a/drivers/cpuidle/cpuidle.c b/drivers/cpuidle/cpuidle.c index ad41f19b8e3f..12fdd3987a36 100644 --- a/drivers/cpuidle/cpuidle.c +++ b/drivers/cpuidle/cpuidle.c @@ -76,8 +76,11 @@ static void cpuidle_idle_call(void) #endif /* ask the governor for the next state */ next_state = cpuidle_curr_governor->select(dev); - if (need_resched()) + if (need_resched()) { + local_irq_enable(); return; + } + target_state = &dev->states[next_state]; /* enter the state and update stats */ diff --git a/drivers/crypto/padlock-sha.c b/drivers/crypto/padlock-sha.c index 76cb6b345e7b..0af80577dc7b 100644 --- a/drivers/crypto/padlock-sha.c +++ b/drivers/crypto/padlock-sha.c @@ -24,6 +24,12 @@ #include <asm/i387.h> #include "padlock.h" +#ifdef CONFIG_64BIT +#define STACK_ALIGN 16 +#else +#define STACK_ALIGN 4 +#endif + struct padlock_sha_desc { struct shash_desc fallback; }; @@ -64,7 +70,9 @@ static int padlock_sha1_finup(struct shash_desc *desc, const u8 *in, /* We can't store directly to *out as it may be unaligned. */ /* BTW Don't reduce the buffer size below 128 Bytes! * PadLock microcode needs it that big. */ - char result[128] __attribute__ ((aligned(PADLOCK_ALIGNMENT))); + char buf[128 + PADLOCK_ALIGNMENT - STACK_ALIGN] __attribute__ + ((aligned(STACK_ALIGN))); + char *result = PTR_ALIGN(&buf[0], PADLOCK_ALIGNMENT); struct padlock_sha_desc *dctx = shash_desc_ctx(desc); struct sha1_state state; unsigned int space; @@ -128,7 +136,9 @@ static int padlock_sha256_finup(struct shash_desc *desc, const u8 *in, /* We can't store directly to *out as it may be unaligned. */ /* BTW Don't reduce the buffer size below 128 Bytes! * PadLock microcode needs it that big. */ - char result[128] __attribute__ ((aligned(PADLOCK_ALIGNMENT))); + char buf[128 + PADLOCK_ALIGNMENT - STACK_ALIGN] __attribute__ + ((aligned(STACK_ALIGN))); + char *result = PTR_ALIGN(&buf[0], PADLOCK_ALIGNMENT); struct padlock_sha_desc *dctx = shash_desc_ctx(desc); struct sha256_state state; unsigned int space; diff --git a/drivers/edac/Kconfig b/drivers/edac/Kconfig index 02127e59fe8e..55c9c59b3f71 100644 --- a/drivers/edac/Kconfig +++ b/drivers/edac/Kconfig @@ -47,6 +47,18 @@ config EDAC_DEBUG_VERBOSE Source file name and line number where debugging message printed will be added to debugging message. + config EDAC_DECODE_MCE + tristate "Decode MCEs in human-readable form (only on AMD for now)" + depends on CPU_SUP_AMD && X86_MCE + default y + ---help--- + Enable this option if you want to decode Machine Check Exceptions + occuring on your machine in human-readable form. + + You should definitely say Y here in case you want to decode MCEs + which occur really early upon boot, before the module infrastructure + has been initialized. + config EDAC_MM_EDAC tristate "Main Memory EDAC (Error Detection And Correction) reporting" help @@ -59,7 +71,7 @@ config EDAC_MM_EDAC config EDAC_AMD64 tristate "AMD64 (Opteron, Athlon64) K8, F10h, F11h" - depends on EDAC_MM_EDAC && K8_NB && X86_64 && PCI && CPU_SUP_AMD + depends on EDAC_MM_EDAC && K8_NB && X86_64 && PCI && EDAC_DECODE_MCE help Support for error detection and correction on the AMD 64 Families of Memory Controllers (K8, F10h and F11h) diff --git a/drivers/edac/Makefile b/drivers/edac/Makefile index 7a473bbe8abd..bc5dc232a0fb 100644 --- a/drivers/edac/Makefile +++ b/drivers/edac/Makefile @@ -6,7 +6,6 @@ # GNU General Public License. # - obj-$(CONFIG_EDAC) := edac_stub.o obj-$(CONFIG_EDAC_MM_EDAC) += edac_core.o @@ -17,9 +16,7 @@ ifdef CONFIG_PCI edac_core-objs += edac_pci.o edac_pci_sysfs.o endif -ifdef CONFIG_CPU_SUP_AMD -edac_core-objs += edac_mce_amd.o -endif +obj-$(CONFIG_EDAC_DECODE_MCE) += edac_mce_amd.o obj-$(CONFIG_EDAC_AMD76X) += amd76x_edac.o obj-$(CONFIG_EDAC_CPC925) += cpc925_edac.o diff --git a/drivers/edac/amd64_edac.c b/drivers/edac/amd64_edac.c index 4e551e63b6dc..a38831c82649 100644 --- a/drivers/edac/amd64_edac.c +++ b/drivers/edac/amd64_edac.c @@ -15,8 +15,8 @@ module_param(ecc_enable_override, int, 0644); /* Lookup table for all possible MC control instances */ struct amd64_pvt; -static struct mem_ctl_info *mci_lookup[MAX_NUMNODES]; -static struct amd64_pvt *pvt_lookup[MAX_NUMNODES]; +static struct mem_ctl_info *mci_lookup[EDAC_MAX_NUMNODES]; +static struct amd64_pvt *pvt_lookup[EDAC_MAX_NUMNODES]; /* * See F2x80 for K8 and F2x[1,0]80 for Fam10 and later. The table below is only @@ -189,7 +189,10 @@ static int amd64_get_scrub_rate(struct mem_ctl_info *mci, u32 *bw) /* Map from a CSROW entry to the mask entry that operates on it */ static inline u32 amd64_map_to_dcs_mask(struct amd64_pvt *pvt, int csrow) { - return csrow >> (pvt->num_dcsm >> 3); + if (boot_cpu_data.x86 == 0xf && pvt->ext_model < OPTERON_CPU_REV_F) + return csrow; + else + return csrow >> 1; } /* return the 'base' address the i'th CS entry of the 'dct' DRAM controller */ @@ -279,29 +282,26 @@ static struct mem_ctl_info *find_mc_by_sys_addr(struct mem_ctl_info *mci, intlv_en = pvt->dram_IntlvEn[0]; if (intlv_en == 0) { - for (node_id = 0; ; ) { + for (node_id = 0; node_id < DRAM_REG_COUNT; node_id++) { if (amd64_base_limit_match(pvt, sys_addr, node_id)) - break; - - if (++node_id >= DRAM_REG_COUNT) - goto err_no_match; + goto found; } - goto found; + goto err_no_match; } - if (unlikely((intlv_en != (0x01 << 8)) && - (intlv_en != (0x03 << 8)) && - (intlv_en != (0x07 << 8)))) { + if (unlikely((intlv_en != 0x01) && + (intlv_en != 0x03) && + (intlv_en != 0x07))) { amd64_printk(KERN_WARNING, "junk value of 0x%x extracted from " "IntlvEn field of DRAM Base Register for node 0: " - "This probably indicates a BIOS bug.\n", intlv_en); + "this probably indicates a BIOS bug.\n", intlv_en); return NULL; } bits = (((u32) sys_addr) >> 12) & intlv_en; for (node_id = 0; ; ) { - if ((pvt->dram_limit[node_id] & intlv_en) == bits) + if ((pvt->dram_IntlvSel[node_id] & intlv_en) == bits) break; /* intlv_sel field matches */ if (++node_id >= DRAM_REG_COUNT) @@ -311,10 +311,10 @@ static struct mem_ctl_info *find_mc_by_sys_addr(struct mem_ctl_info *mci, /* sanity test for sys_addr */ if (unlikely(!amd64_base_limit_match(pvt, sys_addr, node_id))) { amd64_printk(KERN_WARNING, - "%s(): sys_addr 0x%lx falls outside base/limit " - "address range for node %d with node interleaving " - "enabled.\n", __func__, (unsigned long)sys_addr, - node_id); + "%s(): sys_addr 0x%llx falls outside base/limit " + "address range for node %d with node interleaving " + "enabled.\n", + __func__, sys_addr, node_id); return NULL; } @@ -377,7 +377,7 @@ static int input_addr_to_csrow(struct mem_ctl_info *mci, u64 input_addr) * base/mask register pair, test the condition shown near the start of * section 3.5.4 (p. 84, BKDG #26094, K8, revA-E). */ - for (csrow = 0; csrow < CHIPSELECT_COUNT; csrow++) { + for (csrow = 0; csrow < pvt->cs_count; csrow++) { /* This DRAM chip select is disabled on this node */ if ((pvt->dcsb0[csrow] & K8_DCSB_CS_ENABLE) == 0) @@ -734,7 +734,7 @@ static void find_csrow_limits(struct mem_ctl_info *mci, int csrow, u64 base, mask; pvt = mci->pvt_info; - BUG_ON((csrow < 0) || (csrow >= CHIPSELECT_COUNT)); + BUG_ON((csrow < 0) || (csrow >= pvt->cs_count)); base = base_from_dct_base(pvt, csrow); mask = mask_from_dct_mask(pvt, csrow); @@ -962,35 +962,27 @@ err_reg: */ static void amd64_set_dct_base_and_mask(struct amd64_pvt *pvt) { - if (pvt->ext_model >= OPTERON_CPU_REV_F) { + + if (boot_cpu_data.x86 == 0xf && pvt->ext_model < OPTERON_CPU_REV_F) { + pvt->dcsb_base = REV_E_DCSB_BASE_BITS; + pvt->dcsm_mask = REV_E_DCSM_MASK_BITS; + pvt->dcs_mask_notused = REV_E_DCS_NOTUSED_BITS; + pvt->dcs_shift = REV_E_DCS_SHIFT; + pvt->cs_count = 8; + pvt->num_dcsm = 8; + } else { pvt->dcsb_base = REV_F_F1Xh_DCSB_BASE_BITS; pvt->dcsm_mask = REV_F_F1Xh_DCSM_MASK_BITS; pvt->dcs_mask_notused = REV_F_F1Xh_DCS_NOTUSED_BITS; pvt->dcs_shift = REV_F_F1Xh_DCS_SHIFT; - switch (boot_cpu_data.x86) { - case 0xf: - pvt->num_dcsm = REV_F_DCSM_COUNT; - break; - - case 0x10: - pvt->num_dcsm = F10_DCSM_COUNT; - break; - - case 0x11: - pvt->num_dcsm = F11_DCSM_COUNT; - break; - - default: - amd64_printk(KERN_ERR, "Unsupported family!\n"); - break; + if (boot_cpu_data.x86 == 0x11) { + pvt->cs_count = 4; + pvt->num_dcsm = 2; + } else { + pvt->cs_count = 8; + pvt->num_dcsm = 4; } - } else { - pvt->dcsb_base = REV_E_DCSB_BASE_BITS; - pvt->dcsm_mask = REV_E_DCSM_MASK_BITS; - pvt->dcs_mask_notused = REV_E_DCS_NOTUSED_BITS; - pvt->dcs_shift = REV_E_DCS_SHIFT; - pvt->num_dcsm = REV_E_DCSM_COUNT; } } @@ -1003,7 +995,7 @@ static void amd64_read_dct_base_mask(struct amd64_pvt *pvt) amd64_set_dct_base_and_mask(pvt); - for (cs = 0; cs < CHIPSELECT_COUNT; cs++) { + for (cs = 0; cs < pvt->cs_count; cs++) { reg = K8_DCSB0 + (cs * 4); err = pci_read_config_dword(pvt->dram_f2_ctl, reg, &pvt->dcsb0[cs]); @@ -1193,7 +1185,7 @@ static void k8_map_sysaddr_to_csrow(struct mem_ctl_info *mci, * different from the node that detected the error. */ src_mci = find_mc_by_sys_addr(mci, SystemAddress); - if (src_mci) { + if (!src_mci) { amd64_mc_printk(mci, KERN_ERR, "failed to map error address 0x%lx to a node\n", (unsigned long)SystemAddress); @@ -1376,8 +1368,8 @@ static void f10_read_dram_base_limit(struct amd64_pvt *pvt, int dram) pvt->dram_IntlvEn[dram] = (low_base >> 8) & 0x7; - pvt->dram_base[dram] = (((((u64) high_base & 0x000000FF) << 32) | - ((u64) low_base & 0xFFFF0000))) << 8; + pvt->dram_base[dram] = (((u64)high_base & 0x000000FF) << 40) | + (((u64)low_base & 0xFFFF0000) << 8); low_offset = K8_DRAM_LIMIT_LOW + (dram << 3); high_offset = F10_DRAM_LIMIT_HIGH + (dram << 3); @@ -1398,9 +1390,9 @@ static void f10_read_dram_base_limit(struct amd64_pvt *pvt, int dram) * Extract address values and form a LIMIT address. Limit is the HIGHEST * memory location of the region, so low 24 bits need to be all ones. */ - low_limit |= 0x0000FFFF; - pvt->dram_limit[dram] = - ((((u64) high_limit << 32) + (u64) low_limit) << 8) | (0xFF); + pvt->dram_limit[dram] = (((u64)high_limit & 0x000000FF) << 40) | + (((u64) low_limit & 0xFFFF0000) << 8) | + 0x00FFFFFF; } static void f10_read_dram_ctl_register(struct amd64_pvt *pvt) @@ -1566,7 +1558,7 @@ static int f10_lookup_addr_in_dct(u32 in_addr, u32 nid, u32 cs) debugf1("InputAddr=0x%x channelselect=%d\n", in_addr, cs); - for (csrow = 0; csrow < CHIPSELECT_COUNT; csrow++) { + for (csrow = 0; csrow < pvt->cs_count; csrow++) { cs_base = amd64_get_dct_base(pvt, cs, csrow); if (!(cs_base & K8_DCSB_CS_ENABLE)) @@ -2262,7 +2254,7 @@ static inline void __amd64_decode_bus_error(struct mem_ctl_info *mci, { u32 ec = ERROR_CODE(info->nbsl); u32 xec = EXT_ERROR_CODE(info->nbsl); - int ecc_type = info->nbsh & (0x3 << 13); + int ecc_type = (info->nbsh >> 13) & 0x3; /* Bail early out if this was an 'observed' error */ if (PP(ec) == K8_NBSL_PP_OBS) @@ -2497,7 +2489,7 @@ err_reg: * NOTE: CPU Revision Dependent code * * Input: - * @csrow_nr ChipSelect Row Number (0..CHIPSELECT_COUNT-1) + * @csrow_nr ChipSelect Row Number (0..pvt->cs_count-1) * k8 private pointer to --> * DRAM Bank Address mapping register * node_id @@ -2577,7 +2569,7 @@ static int amd64_init_csrows(struct mem_ctl_info *mci) (pvt->nbcfg & K8_NBCFG_ECC_ENABLE) ? "Enabled" : "Disabled" ); - for (i = 0; i < CHIPSELECT_COUNT; i++) { + for (i = 0; i < pvt->cs_count; i++) { csrow = &mci->csrows[i]; if ((pvt->dcsb0[i] & K8_DCSB_CS_ENABLE) == 0) { @@ -2988,7 +2980,7 @@ static int amd64_init_2nd_stage(struct amd64_pvt *pvt) goto err_exit; ret = -ENOMEM; - mci = edac_mc_alloc(0, CHIPSELECT_COUNT, pvt->channel_count, node_id); + mci = edac_mc_alloc(0, pvt->cs_count, pvt->channel_count, node_id); if (!mci) goto err_exit; @@ -3171,7 +3163,7 @@ static int __init amd64_edac_init(void) opstate_init(); if (cache_k8_northbridges() < 0) - goto err_exit; + return err; err = pci_register_driver(&amd64_pci_driver); if (err) @@ -3197,8 +3189,6 @@ static int __init amd64_edac_init(void) err_2nd_stage: debugf0("2nd stage failed\n"); - -err_exit: pci_unregister_driver(&amd64_pci_driver); return err; diff --git a/drivers/edac/amd64_edac.h b/drivers/edac/amd64_edac.h index 8ea07e2715dc..c6f359a85207 100644 --- a/drivers/edac/amd64_edac.h +++ b/drivers/edac/amd64_edac.h @@ -132,6 +132,8 @@ #define EDAC_AMD64_VERSION " Ver: 3.2.0 " __DATE__ #define EDAC_MOD_STR "amd64_edac" +#define EDAC_MAX_NUMNODES 8 + /* Extended Model from CPUID, for CPU Revision numbers */ #define OPTERON_CPU_LE_REV_C 0 #define OPTERON_CPU_REV_D 1 @@ -142,7 +144,7 @@ #define OPTERON_CPU_REV_FA 5 /* Hardware limit on ChipSelect rows per MC and processors per system */ -#define CHIPSELECT_COUNT 8 +#define MAX_CS_COUNT 8 #define DRAM_REG_COUNT 8 @@ -193,7 +195,6 @@ */ #define REV_E_DCSB_BASE_BITS (0xFFE0FE00ULL) #define REV_E_DCS_SHIFT 4 -#define REV_E_DCSM_COUNT 8 #define REV_F_F1Xh_DCSB_BASE_BITS (0x1FF83FE0ULL) #define REV_F_F1Xh_DCS_SHIFT 8 @@ -204,9 +205,6 @@ */ #define REV_F_DCSB_BASE_BITS (0x1FF83FE0ULL) #define REV_F_DCS_SHIFT 8 -#define REV_F_DCSM_COUNT 4 -#define F10_DCSM_COUNT 4 -#define F11_DCSM_COUNT 2 /* DRAM CS Mask Registers */ #define K8_DCSM0 0x60 @@ -374,13 +372,11 @@ enum { #define SET_NB_DRAM_INJECTION_WRITE(word, bits) \ (BIT(((word) & 0xF) + 20) | \ - BIT(17) | \ - ((bits) & 0xF)) + BIT(17) | bits) #define SET_NB_DRAM_INJECTION_READ(word, bits) \ (BIT(((word) & 0xF) + 20) | \ - BIT(16) | \ - ((bits) & 0xF)) + BIT(16) | bits) #define K8_NBCAP 0xE8 #define K8_NBCAP_CORES (BIT(12)|BIT(13)) @@ -445,12 +441,12 @@ struct amd64_pvt { u32 dbam1; /* DRAM Base Address Mapping reg for DCT1 */ /* DRAM CS Base Address Registers F2x[1,0][5C:40] */ - u32 dcsb0[CHIPSELECT_COUNT]; - u32 dcsb1[CHIPSELECT_COUNT]; + u32 dcsb0[MAX_CS_COUNT]; + u32 dcsb1[MAX_CS_COUNT]; /* DRAM CS Mask Registers F2x[1,0][6C:60] */ - u32 dcsm0[CHIPSELECT_COUNT]; - u32 dcsm1[CHIPSELECT_COUNT]; + u32 dcsm0[MAX_CS_COUNT]; + u32 dcsm1[MAX_CS_COUNT]; /* * Decoded parts of DRAM BASE and LIMIT Registers @@ -470,6 +466,7 @@ struct amd64_pvt { */ u32 dcsb_base; /* DCSB base bits */ u32 dcsm_mask; /* DCSM mask bits */ + u32 cs_count; /* num chip selects (== num DCSB registers) */ u32 num_dcsm; /* Number of DCSM registers */ u32 dcs_mask_notused; /* DCSM notused mask bits */ u32 dcs_shift; /* DCSB and DCSM shift value */ diff --git a/drivers/edac/amd64_edac_inj.c b/drivers/edac/amd64_edac_inj.c index d3675b76b3a7..29f1f7a612d9 100644 --- a/drivers/edac/amd64_edac_inj.c +++ b/drivers/edac/amd64_edac_inj.c @@ -1,5 +1,11 @@ #include "amd64_edac.h" +static ssize_t amd64_inject_section_show(struct mem_ctl_info *mci, char *buf) +{ + struct amd64_pvt *pvt = mci->pvt_info; + return sprintf(buf, "0x%x\n", pvt->injection.section); +} + /* * store error injection section value which refers to one of 4 16-byte sections * within a 64-byte cacheline @@ -15,12 +21,26 @@ static ssize_t amd64_inject_section_store(struct mem_ctl_info *mci, ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { + + if (value > 3) { + amd64_printk(KERN_WARNING, + "%s: invalid section 0x%lx\n", + __func__, value); + return -EINVAL; + } + pvt->injection.section = (u32) value; return count; } return ret; } +static ssize_t amd64_inject_word_show(struct mem_ctl_info *mci, char *buf) +{ + struct amd64_pvt *pvt = mci->pvt_info; + return sprintf(buf, "0x%x\n", pvt->injection.word); +} + /* * store error injection word value which refers to one of 9 16-bit word of the * 16-byte (128-bit + ECC bits) section @@ -37,14 +57,25 @@ static ssize_t amd64_inject_word_store(struct mem_ctl_info *mci, ret = strict_strtoul(data, 10, &value); if (ret != -EINVAL) { - value = (value <= 8) ? value : 0; - pvt->injection.word = (u32) value; + if (value > 8) { + amd64_printk(KERN_WARNING, + "%s: invalid word 0x%lx\n", + __func__, value); + return -EINVAL; + } + pvt->injection.word = (u32) value; return count; } return ret; } +static ssize_t amd64_inject_ecc_vector_show(struct mem_ctl_info *mci, char *buf) +{ + struct amd64_pvt *pvt = mci->pvt_info; + return sprintf(buf, "0x%x\n", pvt->injection.bit_map); +} + /* * store 16 bit error injection vector which enables injecting errors to the * corresponding bit within the error injection word above. When used during a @@ -60,8 +91,14 @@ static ssize_t amd64_inject_ecc_vector_store(struct mem_ctl_info *mci, ret = strict_strtoul(data, 16, &value); if (ret != -EINVAL) { - pvt->injection.bit_map = (u32) value & 0xFFFF; + if (value & 0xFFFF0000) { + amd64_printk(KERN_WARNING, + "%s: invalid EccVector: 0x%lx\n", + __func__, value); + return -EINVAL; + } + pvt->injection.bit_map = (u32) value; return count; } return ret; @@ -147,7 +184,7 @@ struct mcidev_sysfs_attribute amd64_inj_attrs[] = { .name = "inject_section", .mode = (S_IRUGO | S_IWUSR) }, - .show = NULL, + .show = amd64_inject_section_show, .store = amd64_inject_section_store, }, { @@ -155,7 +192,7 @@ struct mcidev_sysfs_attribute amd64_inj_attrs[] = { .name = "inject_word", .mode = (S_IRUGO | S_IWUSR) }, - .show = NULL, + .show = amd64_inject_word_show, .store = amd64_inject_word_store, }, { @@ -163,7 +200,7 @@ struct mcidev_sysfs_attribute amd64_inj_attrs[] = { .name = "inject_ecc_vector", .mode = (S_IRUGO | S_IWUSR) }, - .show = NULL, + .show = amd64_inject_ecc_vector_show, .store = amd64_inject_ecc_vector_store, }, { diff --git a/drivers/edac/edac_mce_amd.c b/drivers/edac/edac_mce_amd.c index 0c21c370c9dd..713ed7d37247 100644 --- a/drivers/edac/edac_mce_amd.c +++ b/drivers/edac/edac_mce_amd.c @@ -3,6 +3,7 @@ static bool report_gart_errors; static void (*nb_bus_decoder)(int node_id, struct err_regs *regs); +static void (*orig_mce_callback)(struct mce *m); void amd_report_gart_errors(bool v) { @@ -362,7 +363,7 @@ static inline void amd_decode_err_code(unsigned int ec) pr_warning("Huh? Unknown MCE error 0x%x\n", ec); } -void decode_mce(struct mce *m) +static void amd_decode_mce(struct mce *m) { struct err_regs regs; int node, ecc; @@ -420,3 +421,32 @@ void decode_mce(struct mce *m) amd_decode_err_code(m->status & 0xffff); } + +static int __init mce_amd_init(void) +{ + /* + * We can decode MCEs for Opteron and later CPUs: + */ + if ((boot_cpu_data.x86_vendor == X86_VENDOR_AMD) && + (boot_cpu_data.x86 >= 0xf)) { + /* safe the default decode mce callback */ + orig_mce_callback = x86_mce_decode_callback; + + x86_mce_decode_callback = amd_decode_mce; + } + + return 0; +} +early_initcall(mce_amd_init); + +#ifdef MODULE +static void __exit mce_amd_exit(void) +{ + x86_mce_decode_callback = orig_mce_callback; +} + +MODULE_DESCRIPTION("AMD MCE decoder"); +MODULE_ALIAS("edac-mce-amd"); +MODULE_LICENSE("GPL"); +module_exit(mce_amd_exit); +#endif diff --git a/drivers/edac/i5000_edac.c b/drivers/edac/i5000_edac.c index d335086f4a26..77a9579d7167 100644 --- a/drivers/edac/i5000_edac.c +++ b/drivers/edac/i5000_edac.c @@ -1173,7 +1173,7 @@ static void i5000_get_mc_regs(struct mem_ctl_info *mci) pci_read_config_word(pvt->branch_1, where, &pvt->b1_mtr[slot_row]); debugf2("MTR%d where=0x%x B1 value=0x%x\n", slot_row, - where, pvt->b0_mtr[slot_row]); + where, pvt->b1_mtr[slot_row]); } else { pvt->b1_mtr[slot_row] = 0; } @@ -1232,7 +1232,7 @@ static int i5000_init_csrows(struct mem_ctl_info *mci) struct csrow_info *p_csrow; int empty, channel_count; int max_csrows; - int mtr; + int mtr, mtr1; int csrow_megs; int channel; int csrow; @@ -1251,9 +1251,10 @@ static int i5000_init_csrows(struct mem_ctl_info *mci) /* use branch 0 for the basis */ mtr = pvt->b0_mtr[csrow >> 1]; + mtr1 = pvt->b1_mtr[csrow >> 1]; /* if no DIMMS on this row, continue */ - if (!MTR_DIMMS_PRESENT(mtr)) + if (!MTR_DIMMS_PRESENT(mtr) && !MTR_DIMMS_PRESENT(mtr1)) continue; /* FAKE OUT VALUES, FIXME */ diff --git a/drivers/edac/i5400_edac.c b/drivers/edac/i5400_edac.c index b08b6d8e2dc7..f99d10655ed4 100644 --- a/drivers/edac/i5400_edac.c +++ b/drivers/edac/i5400_edac.c @@ -46,9 +46,10 @@ /* Limits for i5400 */ #define NUM_MTRS_PER_BRANCH 4 #define CHANNELS_PER_BRANCH 2 +#define MAX_DIMMS_PER_CHANNEL NUM_MTRS_PER_BRANCH #define MAX_CHANNELS 4 -#define MAX_DIMMS (MAX_CHANNELS * 4) /* Up to 4 DIMM's per channel */ -#define MAX_CSROWS (MAX_DIMMS * 2) /* max possible csrows per channel */ +/* max possible csrows per channel */ +#define MAX_CSROWS (MAX_DIMMS_PER_CHANNEL) /* Device 16, * Function 0: System Address @@ -331,7 +332,6 @@ static const struct i5400_dev_info i5400_devs[] = { struct i5400_dimm_info { int megabytes; /* size, 0 means not present */ - int dual_rank; }; /* driver private data structure */ @@ -849,11 +849,9 @@ static int determine_mtr(struct i5400_pvt *pvt, int csrow, int channel) int n; /* There is one MTR for each slot pair of FB-DIMMs, - Each slot may have one or two ranks (2 csrows), Each slot pair may be at branch 0 or branch 1. - So, csrow should be divided by eight */ - n = csrow >> 3; + n = csrow; if (n >= NUM_MTRS_PER_BRANCH) { debugf0("ERROR: trying to access an invalid csrow: %d\n", @@ -905,25 +903,22 @@ static void handle_channel(struct i5400_pvt *pvt, int csrow, int channel, amb_present_reg = determine_amb_present_reg(pvt, channel); /* Determine if there is a DIMM present in this DIMM slot */ - if (amb_present_reg & (1 << (csrow >> 1))) { - dinfo->dual_rank = MTR_DIMM_RANK(mtr); - - if (!((dinfo->dual_rank == 0) && - ((csrow & 0x1) == 0x1))) { - /* Start with the number of bits for a Bank - * on the DRAM */ - addrBits = MTR_DRAM_BANKS_ADDR_BITS(mtr); - /* Add thenumber of ROW bits */ - addrBits += MTR_DIMM_ROWS_ADDR_BITS(mtr); - /* add the number of COLUMN bits */ - addrBits += MTR_DIMM_COLS_ADDR_BITS(mtr); - - addrBits += 6; /* add 64 bits per DIMM */ - addrBits -= 20; /* divide by 2^^20 */ - addrBits -= 3; /* 8 bits per bytes */ - - dinfo->megabytes = 1 << addrBits; - } + if (amb_present_reg & (1 << csrow)) { + /* Start with the number of bits for a Bank + * on the DRAM */ + addrBits = MTR_DRAM_BANKS_ADDR_BITS(mtr); + /* Add thenumber of ROW bits */ + addrBits += MTR_DIMM_ROWS_ADDR_BITS(mtr); + /* add the number of COLUMN bits */ + addrBits += MTR_DIMM_COLS_ADDR_BITS(mtr); + /* add the number of RANK bits */ + addrBits += MTR_DIMM_RANK(mtr); + + addrBits += 6; /* add 64 bits per DIMM */ + addrBits -= 20; /* divide by 2^^20 */ + addrBits -= 3; /* 8 bits per bytes */ + + dinfo->megabytes = 1 << addrBits; } } } @@ -951,12 +946,12 @@ static void calculate_dimm_size(struct i5400_pvt *pvt) return; } - /* Scan all the actual CSROWS (which is # of DIMMS * 2) + /* Scan all the actual CSROWS * and calculate the information for each DIMM * Start with the highest csrow first, to display it first * and work toward the 0th csrow */ - max_csrows = pvt->maxdimmperch * 2; + max_csrows = pvt->maxdimmperch; for (csrow = max_csrows - 1; csrow >= 0; csrow--) { /* on an odd csrow, first output a 'boundary' marker, @@ -1064,7 +1059,7 @@ static void i5400_get_mc_regs(struct mem_ctl_info *mci) /* Get the set of MTR[0-3] regs by each branch */ for (slot_row = 0; slot_row < NUM_MTRS_PER_BRANCH; slot_row++) { - int where = MTR0 + (slot_row * sizeof(u32)); + int where = MTR0 + (slot_row * sizeof(u16)); /* Branch 0 set of MTR registers */ pci_read_config_word(pvt->branch_0, where, @@ -1146,7 +1141,7 @@ static int i5400_init_csrows(struct mem_ctl_info *mci) pvt = mci->pvt_info; channel_count = pvt->maxch; - max_csrows = pvt->maxdimmperch * 2; + max_csrows = pvt->maxdimmperch; empty = 1; /* Assume NO memory */ @@ -1215,28 +1210,6 @@ static void i5400_enable_error_reporting(struct mem_ctl_info *mci) } /* - * i5400_get_dimm_and_channel_counts(pdev, &num_csrows, &num_channels) - * - * ask the device how many channels are present and how many CSROWS - * as well - */ -static void i5400_get_dimm_and_channel_counts(struct pci_dev *pdev, - int *num_dimms_per_channel, - int *num_channels) -{ - u8 value; - - /* Need to retrieve just how many channels and dimms per channel are - * supported on this memory controller - */ - pci_read_config_byte(pdev, MAXDIMMPERCH, &value); - *num_dimms_per_channel = (int)value * 2; - - pci_read_config_byte(pdev, MAXCH, &value); - *num_channels = (int)value; -} - -/* * i5400_probe1 Probe for ONE instance of device to see if it is * present. * return: @@ -1263,22 +1236,16 @@ static int i5400_probe1(struct pci_dev *pdev, int dev_idx) if (PCI_FUNC(pdev->devfn) != 0) return -ENODEV; - /* Ask the devices for the number of CSROWS and CHANNELS so - * that we can calculate the memory resources, etc - * - * The Chipset will report what it can handle which will be greater - * or equal to what the motherboard manufacturer will implement. - * - * As we don't have a motherboard identification routine to determine + /* As we don't have a motherboard identification routine to determine * actual number of slots/dimms per channel, we thus utilize the * resource as specified by the chipset. Thus, we might have * have more DIMMs per channel than actually on the mobo, but this * allows the driver to support upto the chipset max, without * some fancy mobo determination. */ - i5400_get_dimm_and_channel_counts(pdev, &num_dimms_per_channel, - &num_channels); - num_csrows = num_dimms_per_channel * 2; + num_dimms_per_channel = MAX_DIMMS_PER_CHANNEL; + num_channels = MAX_CHANNELS; + num_csrows = num_dimms_per_channel; debugf0("MC: %s(): Number of - Channels= %d DIMMS= %d CSROWS= %d\n", __func__, num_channels, num_dimms_per_channel, num_csrows); diff --git a/drivers/edac/mpc85xx_edac.c b/drivers/edac/mpc85xx_edac.c index 157f6504f25e..cf27402af97b 100644 --- a/drivers/edac/mpc85xx_edac.c +++ b/drivers/edac/mpc85xx_edac.c @@ -26,7 +26,9 @@ #include "mpc85xx_edac.h" static int edac_dev_idx; +#ifdef CONFIG_PCI static int edac_pci_idx; +#endif static int edac_mc_idx; static u32 orig_ddr_err_disable; diff --git a/drivers/firewire/sbp2.c b/drivers/firewire/sbp2.c index 50f0176de615..98dbbda3ad41 100644 --- a/drivers/firewire/sbp2.c +++ b/drivers/firewire/sbp2.c @@ -188,14 +188,7 @@ static struct fw_device *target_device(struct sbp2_target *tgt) /* Impossible login_id, to detect logout attempt before successful login */ #define INVALID_LOGIN_ID 0x10000 -/* - * Per section 7.4.8 of the SBP-2 spec, a mgt_ORB_timeout value can be - * provided in the config rom. Most devices do provide a value, which - * we'll use for login management orbs, but with some sane limits. - */ -#define SBP2_MIN_LOGIN_ORB_TIMEOUT 5000U /* Timeout in ms */ -#define SBP2_MAX_LOGIN_ORB_TIMEOUT 40000U /* Timeout in ms */ -#define SBP2_ORB_TIMEOUT 2000U /* Timeout in ms */ +#define SBP2_ORB_TIMEOUT 2000U /* Timeout in ms */ #define SBP2_ORB_NULL 0x80000000 #define SBP2_RETRY_LIMIT 0xf /* 15 retries */ #define SBP2_CYCLE_LIMIT (0xc8 << 12) /* 200 125us cycles */ @@ -1034,7 +1027,6 @@ static int sbp2_scan_unit_dir(struct sbp2_target *tgt, u32 *directory, { struct fw_csr_iterator ci; int key, value; - unsigned int timeout; fw_csr_iterator_init(&ci, directory); while (fw_csr_iterator_next(&ci, &key, &value)) { @@ -1059,17 +1051,7 @@ static int sbp2_scan_unit_dir(struct sbp2_target *tgt, u32 *directory, case SBP2_CSR_UNIT_CHARACTERISTICS: /* the timeout value is stored in 500ms units */ - timeout = ((unsigned int) value >> 8 & 0xff) * 500; - timeout = max(timeout, SBP2_MIN_LOGIN_ORB_TIMEOUT); - tgt->mgt_orb_timeout = - min(timeout, SBP2_MAX_LOGIN_ORB_TIMEOUT); - - if (timeout > tgt->mgt_orb_timeout) - fw_notify("%s: config rom contains %ds " - "management ORB timeout, limiting " - "to %ds\n", tgt->bus_id, - timeout / 1000, - tgt->mgt_orb_timeout / 1000); + tgt->mgt_orb_timeout = (value >> 8 & 0xff) * 500; break; case SBP2_CSR_LOGICAL_UNIT_NUMBER: @@ -1087,6 +1069,22 @@ static int sbp2_scan_unit_dir(struct sbp2_target *tgt, u32 *directory, return 0; } +/* + * Per section 7.4.8 of the SBP-2 spec, a mgt_ORB_timeout value can be + * provided in the config rom. Most devices do provide a value, which + * we'll use for login management orbs, but with some sane limits. + */ +static void sbp2_clamp_management_orb_timeout(struct sbp2_target *tgt) +{ + unsigned int timeout = tgt->mgt_orb_timeout; + + if (timeout > 40000) + fw_notify("%s: %ds mgt_ORB_timeout limited to 40s\n", + tgt->bus_id, timeout / 1000); + + tgt->mgt_orb_timeout = clamp_val(timeout, 5000, 40000); +} + static void sbp2_init_workarounds(struct sbp2_target *tgt, u32 model, u32 firmware_revision) { @@ -1171,6 +1169,7 @@ static int sbp2_probe(struct device *dev) &firmware_revision) < 0) goto fail_tgt_put; + sbp2_clamp_management_orb_timeout(tgt); sbp2_init_workarounds(tgt, model, firmware_revision); /* diff --git a/drivers/firmware/iscsi_ibft.c b/drivers/firmware/iscsi_ibft.c index 420a96e7f2db..051d1ebbd287 100644 --- a/drivers/firmware/iscsi_ibft.c +++ b/drivers/firmware/iscsi_ibft.c @@ -939,7 +939,7 @@ static int __init ibft_init(void) if (ibft_addr) { printk(KERN_INFO "iBFT detected at 0x%llx.\n", - (u64)virt_to_phys((void *)ibft_addr)); + (u64)isa_virt_to_bus(ibft_addr)); rc = ibft_check_device(); if (rc) diff --git a/drivers/firmware/iscsi_ibft_find.c b/drivers/firmware/iscsi_ibft_find.c index d53fbbfefa3e..dfb15c06c88f 100644 --- a/drivers/firmware/iscsi_ibft_find.c +++ b/drivers/firmware/iscsi_ibft_find.c @@ -65,10 +65,10 @@ void __init reserve_ibft_region(void) * so skip that area */ if (pos == VGA_MEM) pos += VGA_SIZE; - virt = phys_to_virt(pos); + virt = isa_bus_to_virt(pos); if (memcmp(virt, IBFT_SIGN, IBFT_SIGN_LEN) == 0) { unsigned long *addr = - (unsigned long *)phys_to_virt(pos + 4); + (unsigned long *)isa_bus_to_virt(pos + 4); len = *addr; /* if the length of the table extends past 1M, * the table cannot be valid. */ diff --git a/drivers/gpio/gpiolib.c b/drivers/gpio/gpiolib.c index 662ed923d9eb..50de0f5750d8 100644 --- a/drivers/gpio/gpiolib.c +++ b/drivers/gpio/gpiolib.c @@ -661,7 +661,7 @@ int gpio_export(unsigned gpio, bool direction_may_change) dev = device_create(&gpio_class, desc->chip->dev, MKDEV(0, 0), desc, ioname ? ioname : "gpio%d", gpio); - if (dev) { + if (!IS_ERR(dev)) { if (direction_may_change) status = sysfs_create_group(&dev->kobj, &gpio_attr_group); @@ -679,7 +679,7 @@ int gpio_export(unsigned gpio, bool direction_may_change) if (status != 0) device_unregister(dev); } else - status = -ENODEV; + status = PTR_ERR(dev); if (status == 0) set_bit(FLAG_EXPORT, &desc->flags); } @@ -800,11 +800,11 @@ static int gpiochip_export(struct gpio_chip *chip) mutex_lock(&sysfs_lock); dev = device_create(&gpio_class, chip->dev, MKDEV(0, 0), chip, "gpiochip%d", chip->base); - if (dev) { + if (!IS_ERR(dev)) { status = sysfs_create_group(&dev->kobj, &gpiochip_attr_group); } else - status = -ENODEV; + status = PTR_ERR(dev); chip->exported = (status == 0); mutex_unlock(&sysfs_lock); diff --git a/drivers/gpio/twl4030-gpio.c b/drivers/gpio/twl4030-gpio.c index afad14792141..49384a7c5492 100644 --- a/drivers/gpio/twl4030-gpio.c +++ b/drivers/gpio/twl4030-gpio.c @@ -460,7 +460,8 @@ no_irqs: return ret; } -static int __devexit gpio_twl4030_remove(struct platform_device *pdev) +/* Cannot use __devexit as gpio_twl4030_probe() calls us */ +static int gpio_twl4030_remove(struct platform_device *pdev) { struct twl4030_gpio_platform_data *pdata = pdev->dev.platform_data; int status; @@ -493,7 +494,7 @@ static struct platform_driver gpio_twl4030_driver = { .driver.name = "twl4030_gpio", .driver.owner = THIS_MODULE, .probe = gpio_twl4030_probe, - .remove = __devexit_p(gpio_twl4030_remove), + .remove = gpio_twl4030_remove, }; static int __init gpio_twl4030_init(void) diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c index 8e7b0ebece0c..5cae0b3eee9b 100644 --- a/drivers/gpu/drm/drm_crtc.c +++ b/drivers/gpu/drm/drm_crtc.c @@ -1556,8 +1556,6 @@ int drm_mode_cursor_ioctl(struct drm_device *dev, struct drm_crtc *crtc; int ret = 0; - DRM_DEBUG_KMS("\n"); - if (!req->flags) { DRM_ERROR("no operation set\n"); return -EINVAL; diff --git a/drivers/gpu/drm/drm_crtc_helper.c b/drivers/gpu/drm/drm_crtc_helper.c index 1fe4e1d344fd..bbfd110a7168 100644 --- a/drivers/gpu/drm/drm_crtc_helper.c +++ b/drivers/gpu/drm/drm_crtc_helper.c @@ -331,6 +331,7 @@ create_mode: cmdline_mode->refresh_specified ? cmdline_mode->refresh : 60, cmdline_mode->rb, cmdline_mode->interlace, cmdline_mode->margins); + drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V); list_add(&mode->head, &connector->modes); return mode; } diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c index 3c0d2b3aed76..cea665d86dd3 100644 --- a/drivers/gpu/drm/drm_edid.c +++ b/drivers/gpu/drm/drm_edid.c @@ -626,6 +626,12 @@ static struct drm_display_mode *drm_mode_detailed(struct drm_device *dev, return NULL; } + /* it is incorrect if hsync/vsync width is zero */ + if (!hsync_pulse_width || !vsync_pulse_width) { + DRM_DEBUG_KMS("Incorrect Detailed timing. " + "Wrong Hsync/Vsync pulse width\n"); + return NULL; + } mode = drm_mode_create(dev); if (!mode) return NULL; @@ -647,6 +653,15 @@ static struct drm_display_mode *drm_mode_detailed(struct drm_device *dev, mode->vsync_end = mode->vsync_start + vsync_pulse_width; mode->vtotal = mode->vdisplay + vblank; + /* perform the basic check for the detailed timing */ + if (mode->hsync_end > mode->htotal || + mode->vsync_end > mode->vtotal) { + drm_mode_destroy(dev, mode); + DRM_DEBUG_KMS("Incorrect detailed timing. " + "Sync is beyond the blank.\n"); + return NULL; + } + drm_mode_set_name(mode); if (pt->misc & DRM_EDID_PT_INTERLACED) diff --git a/drivers/gpu/drm/drm_fb_helper.c b/drivers/gpu/drm/drm_fb_helper.c index 819ddcbfcce5..dc8e374a0b55 100644 --- a/drivers/gpu/drm/drm_fb_helper.c +++ b/drivers/gpu/drm/drm_fb_helper.c @@ -454,6 +454,109 @@ out_free: } EXPORT_SYMBOL(drm_fb_helper_init_crtc_count); +static int setcolreg(struct drm_crtc *crtc, u16 red, u16 green, + u16 blue, u16 regno, struct fb_info *info) +{ + struct drm_fb_helper *fb_helper = info->par; + struct drm_framebuffer *fb = fb_helper->fb; + int pindex; + + if (info->fix.visual == FB_VISUAL_TRUECOLOR) { + u32 *palette; + u32 value; + /* place color in psuedopalette */ + if (regno > 16) + return -EINVAL; + palette = (u32 *)info->pseudo_palette; + red >>= (16 - info->var.red.length); + green >>= (16 - info->var.green.length); + blue >>= (16 - info->var.blue.length); + value = (red << info->var.red.offset) | + (green << info->var.green.offset) | + (blue << info->var.blue.offset); + palette[regno] = value; + return 0; + } + + pindex = regno; + + if (fb->bits_per_pixel == 16) { + pindex = regno << 3; + + if (fb->depth == 16 && regno > 63) + return -EINVAL; + if (fb->depth == 15 && regno > 31) + return -EINVAL; + + if (fb->depth == 16) { + u16 r, g, b; + int i; + if (regno < 32) { + for (i = 0; i < 8; i++) + fb_helper->funcs->gamma_set(crtc, red, + green, blue, pindex + i); + } + + fb_helper->funcs->gamma_get(crtc, &r, + &g, &b, + pindex >> 1); + + for (i = 0; i < 4; i++) + fb_helper->funcs->gamma_set(crtc, r, + green, b, + (pindex >> 1) + i); + } + } + + if (fb->depth != 16) + fb_helper->funcs->gamma_set(crtc, red, green, blue, pindex); + return 0; +} + +int drm_fb_helper_setcmap(struct fb_cmap *cmap, struct fb_info *info) +{ + struct drm_fb_helper *fb_helper = info->par; + struct drm_device *dev = fb_helper->dev; + u16 *red, *green, *blue, *transp; + struct drm_crtc *crtc; + int i, rc = 0; + int start; + + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private; + for (i = 0; i < fb_helper->crtc_count; i++) { + if (crtc->base.id == fb_helper->crtc_info[i].crtc_id) + break; + } + if (i == fb_helper->crtc_count) + continue; + + red = cmap->red; + green = cmap->green; + blue = cmap->blue; + transp = cmap->transp; + start = cmap->start; + + for (i = 0; i < cmap->len; i++) { + u16 hred, hgreen, hblue, htransp = 0xffff; + + hred = *red++; + hgreen = *green++; + hblue = *blue++; + + if (transp) + htransp = *transp++; + + rc = setcolreg(crtc, hred, hgreen, hblue, start++, info); + if (rc) + return rc; + } + crtc_funcs->load_lut(crtc); + } + return rc; +} +EXPORT_SYMBOL(drm_fb_helper_setcmap); + int drm_fb_helper_setcolreg(unsigned regno, unsigned red, unsigned green, @@ -465,10 +568,13 @@ int drm_fb_helper_setcolreg(unsigned regno, struct drm_device *dev = fb_helper->dev; struct drm_crtc *crtc; int i; + int ret; - list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { - struct drm_framebuffer *fb = fb_helper->fb; + if (regno > 255) + return 1; + list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { + struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private; for (i = 0; i < fb_helper->crtc_count; i++) { if (crtc->base.id == fb_helper->crtc_info[i].crtc_id) break; @@ -476,35 +582,11 @@ int drm_fb_helper_setcolreg(unsigned regno, if (i == fb_helper->crtc_count) continue; - if (regno > 255) - return 1; - - if (fb->depth == 8) { - fb_helper->funcs->gamma_set(crtc, red, green, blue, regno); - return 0; - } + ret = setcolreg(crtc, red, green, blue, regno, info); + if (ret) + return ret; - if (regno < 16) { - switch (fb->depth) { - case 15: - fb->pseudo_palette[regno] = ((red & 0xf800) >> 1) | - ((green & 0xf800) >> 6) | - ((blue & 0xf800) >> 11); - break; - case 16: - fb->pseudo_palette[regno] = (red & 0xf800) | - ((green & 0xfc00) >> 5) | - ((blue & 0xf800) >> 11); - break; - case 24: - case 32: - fb->pseudo_palette[regno] = - (((red >> 8) & 0xff) << info->var.red.offset) | - (((green >> 8) & 0xff) << info->var.green.offset) | - (((blue >> 8) & 0xff) << info->var.blue.offset); - break; - } - } + crtc_funcs->load_lut(crtc); } return 0; } @@ -625,7 +707,7 @@ int drm_fb_helper_set_par(struct fb_info *info) if (crtc->fb == fb_helper->crtc_info[i].mode_set.fb) { mutex_lock(&dev->mode_config.mutex); - ret = crtc->funcs->set_config(&fb_helper->crtc_info->mode_set); + ret = crtc->funcs->set_config(&fb_helper->crtc_info[i].mode_set); mutex_unlock(&dev->mode_config.mutex); if (ret) return ret; @@ -674,6 +756,7 @@ int drm_fb_helper_pan_display(struct fb_var_screeninfo *var, EXPORT_SYMBOL(drm_fb_helper_pan_display); int drm_fb_helper_single_fb_probe(struct drm_device *dev, + int preferred_bpp, int (*fb_create)(struct drm_device *dev, uint32_t fb_width, uint32_t fb_height, @@ -696,6 +779,11 @@ int drm_fb_helper_single_fb_probe(struct drm_device *dev, struct drm_fb_helper *fb_helper; uint32_t surface_depth = 24, surface_bpp = 32; + /* if driver picks 8 or 16 by default use that + for both depth/bpp */ + if (preferred_bpp != surface_bpp) { + surface_depth = surface_bpp = preferred_bpp; + } /* first up get a count of crtcs now in use and new min/maxes width/heights */ list_for_each_entry(connector, &dev->mode_config.connector_list, head) { struct drm_fb_helper_connector *fb_help_conn = connector->fb_helper_private; @@ -851,10 +939,12 @@ void drm_fb_helper_free(struct drm_fb_helper *helper) } EXPORT_SYMBOL(drm_fb_helper_free); -void drm_fb_helper_fill_fix(struct fb_info *info, uint32_t pitch) +void drm_fb_helper_fill_fix(struct fb_info *info, uint32_t pitch, + uint32_t depth) { info->fix.type = FB_TYPE_PACKED_PIXELS; - info->fix.visual = FB_VISUAL_TRUECOLOR; + info->fix.visual = depth == 8 ? FB_VISUAL_PSEUDOCOLOR : + FB_VISUAL_TRUECOLOR; info->fix.type_aux = 0; info->fix.xpanstep = 1; /* doing it in hw */ info->fix.ypanstep = 1; /* doing it in hw */ diff --git a/drivers/gpu/drm/i915/i915_dma.c b/drivers/gpu/drm/i915/i915_dma.c index 45d507ebd3ff..e5b138be45fa 100644 --- a/drivers/gpu/drm/i915/i915_dma.c +++ b/drivers/gpu/drm/i915/i915_dma.c @@ -1227,8 +1227,7 @@ static int i915_load_modeset_init(struct drm_device *dev, goto out; /* Try to set up FBC with a reasonable compressed buffer size */ - if (IS_MOBILE(dev) && (IS_I9XX(dev) || IS_I965G(dev) || IS_GM45(dev)) && - i915_powersave) { + if (I915_HAS_FBC(dev) && i915_powersave) { int cfb_size; /* Try to get an 8M buffer... */ @@ -1468,6 +1467,7 @@ int i915_driver_load(struct drm_device *dev, unsigned long flags) spin_lock_init(&dev_priv->user_irq_lock); spin_lock_init(&dev_priv->error_lock); dev_priv->user_irq_refcount = 0; + dev_priv->trace_irq_seqno = 0; ret = drm_vblank_init(dev, I915_NUM_PIPE); diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index b93814c0d3e2..7f436ec075f6 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -89,7 +89,8 @@ static int i915_suspend(struct drm_device *dev, pm_message_t state) pci_set_power_state(dev->pdev, PCI_D3hot); } - dev_priv->suspended = 1; + /* Modeset on resume, not lid events */ + dev_priv->modeset_on_lid = 0; return 0; } @@ -124,7 +125,7 @@ static int i915_resume(struct drm_device *dev) drm_helper_resume_force_mode(dev); } - dev_priv->suspended = 0; + dev_priv->modeset_on_lid = 0; return ret; } diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index b24b2d145b75..57204e298975 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -202,6 +202,7 @@ typedef struct drm_i915_private { spinlock_t user_irq_lock; /** Refcount for i915_user_irq_get() versus i915_user_irq_put(). */ int user_irq_refcount; + u32 trace_irq_seqno; /** Cached value of IMR to avoid reads in updating the bitfield */ u32 irq_mask_reg; u32 pipestat[2]; @@ -273,7 +274,7 @@ typedef struct drm_i915_private { struct drm_i915_display_funcs display; /* Register state */ - bool suspended; + bool modeset_on_lid; u8 saveLBB; u32 saveDSPACNTR; u32 saveDSPBCNTR; @@ -295,6 +296,12 @@ typedef struct drm_i915_private { u32 saveVBLANK_A; u32 saveVSYNC_A; u32 saveBCLRPAT_A; + u32 saveTRANS_HTOTAL_A; + u32 saveTRANS_HBLANK_A; + u32 saveTRANS_HSYNC_A; + u32 saveTRANS_VTOTAL_A; + u32 saveTRANS_VBLANK_A; + u32 saveTRANS_VSYNC_A; u32 savePIPEASTAT; u32 saveDSPASTRIDE; u32 saveDSPASIZE; @@ -303,8 +310,11 @@ typedef struct drm_i915_private { u32 saveDSPASURF; u32 saveDSPATILEOFF; u32 savePFIT_PGM_RATIOS; + u32 saveBLC_HIST_CTL; u32 saveBLC_PWM_CTL; u32 saveBLC_PWM_CTL2; + u32 saveBLC_CPU_PWM_CTL; + u32 saveBLC_CPU_PWM_CTL2; u32 saveFPB0; u32 saveFPB1; u32 saveDPLL_B; @@ -316,6 +326,12 @@ typedef struct drm_i915_private { u32 saveVBLANK_B; u32 saveVSYNC_B; u32 saveBCLRPAT_B; + u32 saveTRANS_HTOTAL_B; + u32 saveTRANS_HBLANK_B; + u32 saveTRANS_HSYNC_B; + u32 saveTRANS_VTOTAL_B; + u32 saveTRANS_VBLANK_B; + u32 saveTRANS_VSYNC_B; u32 savePIPEBSTAT; u32 saveDSPBSTRIDE; u32 saveDSPBSIZE; @@ -341,6 +357,7 @@ typedef struct drm_i915_private { u32 savePFIT_CONTROL; u32 save_palette_a[256]; u32 save_palette_b[256]; + u32 saveDPFC_CB_BASE; u32 saveFBC_CFB_BASE; u32 saveFBC_LL_BASE; u32 saveFBC_CONTROL; @@ -348,6 +365,12 @@ typedef struct drm_i915_private { u32 saveIER; u32 saveIIR; u32 saveIMR; + u32 saveDEIER; + u32 saveDEIMR; + u32 saveGTIER; + u32 saveGTIMR; + u32 saveFDI_RXA_IMR; + u32 saveFDI_RXB_IMR; u32 saveCACHE_MODE_0; u32 saveD_STATE; u32 saveDSPCLK_GATE_D; @@ -381,6 +404,16 @@ typedef struct drm_i915_private { u32 savePIPEB_DP_LINK_M; u32 savePIPEA_DP_LINK_N; u32 savePIPEB_DP_LINK_N; + u32 saveFDI_RXA_CTL; + u32 saveFDI_TXA_CTL; + u32 saveFDI_RXB_CTL; + u32 saveFDI_TXB_CTL; + u32 savePFA_CTL_1; + u32 savePFB_CTL_1; + u32 savePFA_WIN_SZ; + u32 savePFB_WIN_SZ; + u32 savePFA_WIN_POS; + u32 savePFB_WIN_POS; struct { struct drm_mm gtt_space; @@ -491,6 +524,8 @@ typedef struct drm_i915_private { struct drm_i915_gem_phys_object *phys_objs[I915_MAX_PHYS_OBJECT]; } mm; struct sdvo_device_mapping sdvo_mappings[2]; + /* indicate whether the LVDS_BORDER should be enabled or not */ + unsigned int lvds_border_bits; /* Reclocking support */ bool render_reclock_avail; @@ -665,6 +700,7 @@ extern int i915_irq_emit(struct drm_device *dev, void *data, extern int i915_irq_wait(struct drm_device *dev, void *data, struct drm_file *file_priv); void i915_user_irq_get(struct drm_device *dev); +void i915_trace_irq_get(struct drm_device *dev, u32 seqno); void i915_user_irq_put(struct drm_device *dev); extern void i915_enable_interrupt (struct drm_device *dev); @@ -979,7 +1015,10 @@ extern int i915_wait_ring(struct drm_device * dev, int n, const char *caller); #define HAS_FW_BLC(dev) (IS_I9XX(dev) || IS_G4X(dev) || IS_IGDNG(dev)) #define HAS_PIPE_CXSR(dev) (IS_G4X(dev) || IS_IGDNG(dev)) -#define I915_HAS_FBC(dev) (IS_MOBILE(dev) && (IS_I9XX(dev) || IS_I965G(dev))) +#define I915_HAS_FBC(dev) (IS_MOBILE(dev) && \ + (IS_I9XX(dev) || IS_GM45(dev)) && \ + !IS_IGD(dev) && \ + !IS_IGDNG(dev)) #define PRIMARY_RINGBUFFER_SIZE (128*1024) diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index 40727d4c2919..abfc27b0c2ea 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -1770,7 +1770,7 @@ i915_gem_retire_requests(struct drm_device *dev) drm_i915_private_t *dev_priv = dev->dev_private; uint32_t seqno; - if (!dev_priv->hw_status_page) + if (!dev_priv->hw_status_page || list_empty(&dev_priv->mm.request_list)) return; seqno = i915_get_gem_seqno(dev); @@ -1794,6 +1794,12 @@ i915_gem_retire_requests(struct drm_device *dev) } else break; } + + if (unlikely (dev_priv->trace_irq_seqno && + i915_seqno_passed(dev_priv->trace_irq_seqno, seqno))) { + i915_user_irq_put(dev); + dev_priv->trace_irq_seqno = 0; + } } void @@ -3352,7 +3358,7 @@ i915_dispatch_gem_execbuffer(struct drm_device *dev, exec_start = (uint32_t) exec_offset + exec->batch_start_offset; exec_len = (uint32_t) exec->batch_len; - trace_i915_gem_request_submit(dev, dev_priv->mm.next_gem_seqno); + trace_i915_gem_request_submit(dev, dev_priv->mm.next_gem_seqno + 1); count = nbox ? nbox : 1; diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 4dfeec7cdd42..c3ceffa46ea0 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -725,6 +725,16 @@ void i915_user_irq_put(struct drm_device *dev) spin_unlock_irqrestore(&dev_priv->user_irq_lock, irqflags); } +void i915_trace_irq_get(struct drm_device *dev, u32 seqno) +{ + drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; + + if (dev_priv->trace_irq_seqno == 0) + i915_user_irq_get(dev); + + dev_priv->trace_irq_seqno = seqno; +} + static int i915_wait_irq(struct drm_device * dev, int irq_nr) { drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private; diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h index 0466ddbeba32..1687edf68795 100644 --- a/drivers/gpu/drm/i915/i915_reg.h +++ b/drivers/gpu/drm/i915/i915_reg.h @@ -968,6 +968,8 @@ #define LVDS_PORT_EN (1 << 31) /* Selects pipe B for LVDS data. Must be set on pre-965. */ #define LVDS_PIPEB_SELECT (1 << 30) +/* Enable border for unscaled (or aspect-scaled) display */ +#define LVDS_BORDER_ENABLE (1 << 15) /* * Enables the A0-A2 data pairs and CLKA, containing 18 bits of color data per * pixel. @@ -1078,6 +1080,8 @@ #define BACKLIGHT_DUTY_CYCLE_SHIFT (0) #define BACKLIGHT_DUTY_CYCLE_MASK (0xffff) +#define BLC_HIST_CTL 0x61260 + /* TV port control */ #define TV_CTL 0x68000 /** Enables the TV encoder */ @@ -1780,6 +1784,11 @@ #define PIPE_START_VBLANK_INTERRUPT_STATUS (1UL<<2) /* 965 or later */ #define PIPE_VBLANK_INTERRUPT_STATUS (1UL<<1) #define PIPE_OVERLAY_UPDATED_STATUS (1UL<<0) +#define PIPE_BPC_MASK (7 << 5) /* Ironlake */ +#define PIPE_8BPC (0 << 5) +#define PIPE_10BPC (1 << 5) +#define PIPE_6BPC (2 << 5) +#define PIPE_12BPC (3 << 5) #define DSPARB 0x70030 #define DSPARB_CSTART_MASK (0x7f << 7) @@ -1790,17 +1799,29 @@ #define DSPARB_AEND_SHIFT 0 #define DSPFW1 0x70034 +#define DSPFW_SR_SHIFT 23 +#define DSPFW_CURSORB_SHIFT 16 +#define DSPFW_PLANEB_SHIFT 8 #define DSPFW2 0x70038 +#define DSPFW_CURSORA_MASK 0x00003f00 +#define DSPFW_CURSORA_SHIFT 16 #define DSPFW3 0x7003c +#define DSPFW_HPLL_SR_EN (1<<31) +#define DSPFW_CURSOR_SR_SHIFT 24 #define IGD_SELF_REFRESH_EN (1<<30) /* FIFO watermark sizes etc */ +#define G4X_FIFO_LINE_SIZE 64 #define I915_FIFO_LINE_SIZE 64 #define I830_FIFO_LINE_SIZE 32 + +#define G4X_FIFO_SIZE 127 #define I945_FIFO_SIZE 127 /* 945 & 965 */ #define I915_FIFO_SIZE 95 #define I855GM_FIFO_SIZE 127 /* In cachelines */ #define I830_FIFO_SIZE 95 + +#define G4X_MAX_WM 0x3f #define I915_MAX_WM 0x3f #define IGD_DISPLAY_FIFO 512 /* in 64byte unit */ @@ -2030,6 +2051,11 @@ #define PFA_CTL_1 0x68080 #define PFB_CTL_1 0x68880 #define PF_ENABLE (1<<31) +#define PF_FILTER_MASK (3<<23) +#define PF_FILTER_PROGRAMMED (0<<23) +#define PF_FILTER_MED_3x3 (1<<23) +#define PF_FILTER_EDGE_ENHANCE (2<<23) +#define PF_FILTER_EDGE_SOFTEN (3<<23) #define PFA_WIN_SZ 0x68074 #define PFB_WIN_SZ 0x68874 #define PFA_WIN_POS 0x68070 @@ -2149,11 +2175,11 @@ #define DREF_CPU_SOURCE_OUTPUT_MASK (3<<13) #define DREF_SSC_SOURCE_DISABLE (0<<11) #define DREF_SSC_SOURCE_ENABLE (2<<11) -#define DREF_SSC_SOURCE_MASK (2<<11) +#define DREF_SSC_SOURCE_MASK (3<<11) #define DREF_NONSPREAD_SOURCE_DISABLE (0<<9) #define DREF_NONSPREAD_CK505_ENABLE (1<<9) #define DREF_NONSPREAD_SOURCE_ENABLE (2<<9) -#define DREF_NONSPREAD_SOURCE_MASK (2<<9) +#define DREF_NONSPREAD_SOURCE_MASK (3<<9) #define DREF_SUPERSPREAD_SOURCE_DISABLE (0<<7) #define DREF_SUPERSPREAD_SOURCE_ENABLE (2<<7) #define DREF_SSC4_DOWNSPREAD (0<<6) diff --git a/drivers/gpu/drm/i915/i915_suspend.c b/drivers/gpu/drm/i915/i915_suspend.c index bd6d8d91ca9f..992d5617e798 100644 --- a/drivers/gpu/drm/i915/i915_suspend.c +++ b/drivers/gpu/drm/i915/i915_suspend.c @@ -32,11 +32,15 @@ static bool i915_pipe_enabled(struct drm_device *dev, enum pipe pipe) { struct drm_i915_private *dev_priv = dev->dev_private; + u32 dpll_reg; - if (pipe == PIPE_A) - return (I915_READ(DPLL_A) & DPLL_VCO_ENABLE); - else - return (I915_READ(DPLL_B) & DPLL_VCO_ENABLE); + if (IS_IGDNG(dev)) { + dpll_reg = (pipe == PIPE_A) ? PCH_DPLL_A: PCH_DPLL_B; + } else { + dpll_reg = (pipe == PIPE_A) ? DPLL_A: DPLL_B; + } + + return (I915_READ(dpll_reg) & DPLL_VCO_ENABLE); } static void i915_save_palette(struct drm_device *dev, enum pipe pipe) @@ -49,6 +53,9 @@ static void i915_save_palette(struct drm_device *dev, enum pipe pipe) if (!i915_pipe_enabled(dev, pipe)) return; + if (IS_IGDNG(dev)) + reg = (pipe == PIPE_A) ? LGC_PALETTE_A : LGC_PALETTE_B; + if (pipe == PIPE_A) array = dev_priv->save_palette_a; else @@ -68,6 +75,9 @@ static void i915_restore_palette(struct drm_device *dev, enum pipe pipe) if (!i915_pipe_enabled(dev, pipe)) return; + if (IS_IGDNG(dev)) + reg = (pipe == PIPE_A) ? LGC_PALETTE_A : LGC_PALETTE_B; + if (pipe == PIPE_A) array = dev_priv->save_palette_a; else @@ -232,10 +242,16 @@ static void i915_save_modeset_reg(struct drm_device *dev) /* Pipe & plane A info */ dev_priv->savePIPEACONF = I915_READ(PIPEACONF); dev_priv->savePIPEASRC = I915_READ(PIPEASRC); - dev_priv->saveFPA0 = I915_READ(FPA0); - dev_priv->saveFPA1 = I915_READ(FPA1); - dev_priv->saveDPLL_A = I915_READ(DPLL_A); - if (IS_I965G(dev)) + if (IS_IGDNG(dev)) { + dev_priv->saveFPA0 = I915_READ(PCH_FPA0); + dev_priv->saveFPA1 = I915_READ(PCH_FPA1); + dev_priv->saveDPLL_A = I915_READ(PCH_DPLL_A); + } else { + dev_priv->saveFPA0 = I915_READ(FPA0); + dev_priv->saveFPA1 = I915_READ(FPA1); + dev_priv->saveDPLL_A = I915_READ(DPLL_A); + } + if (IS_I965G(dev) && !IS_IGDNG(dev)) dev_priv->saveDPLL_A_MD = I915_READ(DPLL_A_MD); dev_priv->saveHTOTAL_A = I915_READ(HTOTAL_A); dev_priv->saveHBLANK_A = I915_READ(HBLANK_A); @@ -243,7 +259,24 @@ static void i915_save_modeset_reg(struct drm_device *dev) dev_priv->saveVTOTAL_A = I915_READ(VTOTAL_A); dev_priv->saveVBLANK_A = I915_READ(VBLANK_A); dev_priv->saveVSYNC_A = I915_READ(VSYNC_A); - dev_priv->saveBCLRPAT_A = I915_READ(BCLRPAT_A); + if (!IS_IGDNG(dev)) + dev_priv->saveBCLRPAT_A = I915_READ(BCLRPAT_A); + + if (IS_IGDNG(dev)) { + dev_priv->saveFDI_TXA_CTL = I915_READ(FDI_TXA_CTL); + dev_priv->saveFDI_RXA_CTL = I915_READ(FDI_RXA_CTL); + + dev_priv->savePFA_CTL_1 = I915_READ(PFA_CTL_1); + dev_priv->savePFA_WIN_SZ = I915_READ(PFA_WIN_SZ); + dev_priv->savePFA_WIN_POS = I915_READ(PFA_WIN_POS); + + dev_priv->saveTRANS_HTOTAL_A = I915_READ(TRANS_HTOTAL_A); + dev_priv->saveTRANS_HBLANK_A = I915_READ(TRANS_HBLANK_A); + dev_priv->saveTRANS_HSYNC_A = I915_READ(TRANS_HSYNC_A); + dev_priv->saveTRANS_VTOTAL_A = I915_READ(TRANS_VTOTAL_A); + dev_priv->saveTRANS_VBLANK_A = I915_READ(TRANS_VBLANK_A); + dev_priv->saveTRANS_VSYNC_A = I915_READ(TRANS_VSYNC_A); + } dev_priv->saveDSPACNTR = I915_READ(DSPACNTR); dev_priv->saveDSPASTRIDE = I915_READ(DSPASTRIDE); @@ -260,10 +293,16 @@ static void i915_save_modeset_reg(struct drm_device *dev) /* Pipe & plane B info */ dev_priv->savePIPEBCONF = I915_READ(PIPEBCONF); dev_priv->savePIPEBSRC = I915_READ(PIPEBSRC); - dev_priv->saveFPB0 = I915_READ(FPB0); - dev_priv->saveFPB1 = I915_READ(FPB1); - dev_priv->saveDPLL_B = I915_READ(DPLL_B); - if (IS_I965G(dev)) + if (IS_IGDNG(dev)) { + dev_priv->saveFPB0 = I915_READ(PCH_FPB0); + dev_priv->saveFPB1 = I915_READ(PCH_FPB1); + dev_priv->saveDPLL_B = I915_READ(PCH_DPLL_B); + } else { + dev_priv->saveFPB0 = I915_READ(FPB0); + dev_priv->saveFPB1 = I915_READ(FPB1); + dev_priv->saveDPLL_B = I915_READ(DPLL_B); + } + if (IS_I965G(dev) && !IS_IGDNG(dev)) dev_priv->saveDPLL_B_MD = I915_READ(DPLL_B_MD); dev_priv->saveHTOTAL_B = I915_READ(HTOTAL_B); dev_priv->saveHBLANK_B = I915_READ(HBLANK_B); @@ -271,7 +310,24 @@ static void i915_save_modeset_reg(struct drm_device *dev) dev_priv->saveVTOTAL_B = I915_READ(VTOTAL_B); dev_priv->saveVBLANK_B = I915_READ(VBLANK_B); dev_priv->saveVSYNC_B = I915_READ(VSYNC_B); - dev_priv->saveBCLRPAT_A = I915_READ(BCLRPAT_A); + if (!IS_IGDNG(dev)) + dev_priv->saveBCLRPAT_B = I915_READ(BCLRPAT_B); + + if (IS_IGDNG(dev)) { + dev_priv->saveFDI_TXB_CTL = I915_READ(FDI_TXB_CTL); + dev_priv->saveFDI_RXB_CTL = I915_READ(FDI_RXB_CTL); + + dev_priv->savePFB_CTL_1 = I915_READ(PFB_CTL_1); + dev_priv->savePFB_WIN_SZ = I915_READ(PFB_WIN_SZ); + dev_priv->savePFB_WIN_POS = I915_READ(PFB_WIN_POS); + + dev_priv->saveTRANS_HTOTAL_B = I915_READ(TRANS_HTOTAL_B); + dev_priv->saveTRANS_HBLANK_B = I915_READ(TRANS_HBLANK_B); + dev_priv->saveTRANS_HSYNC_B = I915_READ(TRANS_HSYNC_B); + dev_priv->saveTRANS_VTOTAL_B = I915_READ(TRANS_VTOTAL_B); + dev_priv->saveTRANS_VBLANK_B = I915_READ(TRANS_VBLANK_B); + dev_priv->saveTRANS_VSYNC_B = I915_READ(TRANS_VSYNC_B); + } dev_priv->saveDSPBCNTR = I915_READ(DSPBCNTR); dev_priv->saveDSPBSTRIDE = I915_READ(DSPBSTRIDE); @@ -290,23 +346,41 @@ static void i915_save_modeset_reg(struct drm_device *dev) static void i915_restore_modeset_reg(struct drm_device *dev) { struct drm_i915_private *dev_priv = dev->dev_private; + int dpll_a_reg, fpa0_reg, fpa1_reg; + int dpll_b_reg, fpb0_reg, fpb1_reg; if (drm_core_check_feature(dev, DRIVER_MODESET)) return; + if (IS_IGDNG(dev)) { + dpll_a_reg = PCH_DPLL_A; + dpll_b_reg = PCH_DPLL_B; + fpa0_reg = PCH_FPA0; + fpb0_reg = PCH_FPB0; + fpa1_reg = PCH_FPA1; + fpb1_reg = PCH_FPB1; + } else { + dpll_a_reg = DPLL_A; + dpll_b_reg = DPLL_B; + fpa0_reg = FPA0; + fpb0_reg = FPB0; + fpa1_reg = FPA1; + fpb1_reg = FPB1; + } + /* Pipe & plane A info */ /* Prime the clock */ if (dev_priv->saveDPLL_A & DPLL_VCO_ENABLE) { - I915_WRITE(DPLL_A, dev_priv->saveDPLL_A & + I915_WRITE(dpll_a_reg, dev_priv->saveDPLL_A & ~DPLL_VCO_ENABLE); DRM_UDELAY(150); } - I915_WRITE(FPA0, dev_priv->saveFPA0); - I915_WRITE(FPA1, dev_priv->saveFPA1); + I915_WRITE(fpa0_reg, dev_priv->saveFPA0); + I915_WRITE(fpa1_reg, dev_priv->saveFPA1); /* Actually enable it */ - I915_WRITE(DPLL_A, dev_priv->saveDPLL_A); + I915_WRITE(dpll_a_reg, dev_priv->saveDPLL_A); DRM_UDELAY(150); - if (IS_I965G(dev)) + if (IS_I965G(dev) && !IS_IGDNG(dev)) I915_WRITE(DPLL_A_MD, dev_priv->saveDPLL_A_MD); DRM_UDELAY(150); @@ -317,7 +391,24 @@ static void i915_restore_modeset_reg(struct drm_device *dev) I915_WRITE(VTOTAL_A, dev_priv->saveVTOTAL_A); I915_WRITE(VBLANK_A, dev_priv->saveVBLANK_A); I915_WRITE(VSYNC_A, dev_priv->saveVSYNC_A); - I915_WRITE(BCLRPAT_A, dev_priv->saveBCLRPAT_A); + if (!IS_IGDNG(dev)) + I915_WRITE(BCLRPAT_A, dev_priv->saveBCLRPAT_A); + + if (IS_IGDNG(dev)) { + I915_WRITE(FDI_RXA_CTL, dev_priv->saveFDI_RXA_CTL); + I915_WRITE(FDI_TXA_CTL, dev_priv->saveFDI_TXA_CTL); + + I915_WRITE(PFA_CTL_1, dev_priv->savePFA_CTL_1); + I915_WRITE(PFA_WIN_SZ, dev_priv->savePFA_WIN_SZ); + I915_WRITE(PFA_WIN_POS, dev_priv->savePFA_WIN_POS); + + I915_WRITE(TRANS_HTOTAL_A, dev_priv->saveTRANS_HTOTAL_A); + I915_WRITE(TRANS_HBLANK_A, dev_priv->saveTRANS_HBLANK_A); + I915_WRITE(TRANS_HSYNC_A, dev_priv->saveTRANS_HSYNC_A); + I915_WRITE(TRANS_VTOTAL_A, dev_priv->saveTRANS_VTOTAL_A); + I915_WRITE(TRANS_VBLANK_A, dev_priv->saveTRANS_VBLANK_A); + I915_WRITE(TRANS_VSYNC_A, dev_priv->saveTRANS_VSYNC_A); + } /* Restore plane info */ I915_WRITE(DSPASIZE, dev_priv->saveDSPASIZE); @@ -339,14 +430,14 @@ static void i915_restore_modeset_reg(struct drm_device *dev) /* Pipe & plane B info */ if (dev_priv->saveDPLL_B & DPLL_VCO_ENABLE) { - I915_WRITE(DPLL_B, dev_priv->saveDPLL_B & + I915_WRITE(dpll_b_reg, dev_priv->saveDPLL_B & ~DPLL_VCO_ENABLE); DRM_UDELAY(150); } - I915_WRITE(FPB0, dev_priv->saveFPB0); - I915_WRITE(FPB1, dev_priv->saveFPB1); + I915_WRITE(fpb0_reg, dev_priv->saveFPB0); + I915_WRITE(fpb1_reg, dev_priv->saveFPB1); /* Actually enable it */ - I915_WRITE(DPLL_B, dev_priv->saveDPLL_B); + I915_WRITE(dpll_b_reg, dev_priv->saveDPLL_B); DRM_UDELAY(150); if (IS_I965G(dev)) I915_WRITE(DPLL_B_MD, dev_priv->saveDPLL_B_MD); @@ -359,7 +450,24 @@ static void i915_restore_modeset_reg(struct drm_device *dev) I915_WRITE(VTOTAL_B, dev_priv->saveVTOTAL_B); I915_WRITE(VBLANK_B, dev_priv->saveVBLANK_B); I915_WRITE(VSYNC_B, dev_priv->saveVSYNC_B); - I915_WRITE(BCLRPAT_B, dev_priv->saveBCLRPAT_B); + if (!IS_IGDNG(dev)) + I915_WRITE(BCLRPAT_B, dev_priv->saveBCLRPAT_B); + + if (IS_IGDNG(dev)) { + I915_WRITE(FDI_RXB_CTL, dev_priv->saveFDI_RXB_CTL); + I915_WRITE(FDI_TXB_CTL, dev_priv->saveFDI_TXB_CTL); + + I915_WRITE(PFB_CTL_1, dev_priv->savePFB_CTL_1); + I915_WRITE(PFB_WIN_SZ, dev_priv->savePFB_WIN_SZ); + I915_WRITE(PFB_WIN_POS, dev_priv->savePFB_WIN_POS); + + I915_WRITE(TRANS_HTOTAL_B, dev_priv->saveTRANS_HTOTAL_B); + I915_WRITE(TRANS_HBLANK_B, dev_priv->saveTRANS_HBLANK_B); + I915_WRITE(TRANS_HSYNC_B, dev_priv->saveTRANS_HSYNC_B); + I915_WRITE(TRANS_VTOTAL_B, dev_priv->saveTRANS_VTOTAL_B); + I915_WRITE(TRANS_VBLANK_B, dev_priv->saveTRANS_VBLANK_B); + I915_WRITE(TRANS_VSYNC_B, dev_priv->saveTRANS_VSYNC_B); + } /* Restore plane info */ I915_WRITE(DSPBSIZE, dev_priv->saveDSPBSIZE); @@ -404,21 +512,43 @@ void i915_save_display(struct drm_device *dev) dev_priv->saveCURSIZE = I915_READ(CURSIZE); /* CRT state */ - dev_priv->saveADPA = I915_READ(ADPA); + if (IS_IGDNG(dev)) { + dev_priv->saveADPA = I915_READ(PCH_ADPA); + } else { + dev_priv->saveADPA = I915_READ(ADPA); + } /* LVDS state */ - dev_priv->savePP_CONTROL = I915_READ(PP_CONTROL); - dev_priv->savePFIT_PGM_RATIOS = I915_READ(PFIT_PGM_RATIOS); - dev_priv->saveBLC_PWM_CTL = I915_READ(BLC_PWM_CTL); - if (IS_I965G(dev)) - dev_priv->saveBLC_PWM_CTL2 = I915_READ(BLC_PWM_CTL2); - if (IS_MOBILE(dev) && !IS_I830(dev)) - dev_priv->saveLVDS = I915_READ(LVDS); - if (!IS_I830(dev) && !IS_845G(dev)) + if (IS_IGDNG(dev)) { + dev_priv->savePP_CONTROL = I915_READ(PCH_PP_CONTROL); + dev_priv->saveBLC_PWM_CTL = I915_READ(BLC_PWM_PCH_CTL1); + dev_priv->saveBLC_PWM_CTL2 = I915_READ(BLC_PWM_PCH_CTL2); + dev_priv->saveBLC_CPU_PWM_CTL = I915_READ(BLC_PWM_CPU_CTL); + dev_priv->saveBLC_CPU_PWM_CTL2 = I915_READ(BLC_PWM_CPU_CTL2); + dev_priv->saveLVDS = I915_READ(PCH_LVDS); + } else { + dev_priv->savePP_CONTROL = I915_READ(PP_CONTROL); + dev_priv->savePFIT_PGM_RATIOS = I915_READ(PFIT_PGM_RATIOS); + dev_priv->saveBLC_PWM_CTL = I915_READ(BLC_PWM_CTL); + dev_priv->saveBLC_HIST_CTL = I915_READ(BLC_HIST_CTL); + if (IS_I965G(dev)) + dev_priv->saveBLC_PWM_CTL2 = I915_READ(BLC_PWM_CTL2); + if (IS_MOBILE(dev) && !IS_I830(dev)) + dev_priv->saveLVDS = I915_READ(LVDS); + } + + if (!IS_I830(dev) && !IS_845G(dev) && !IS_IGDNG(dev)) dev_priv->savePFIT_CONTROL = I915_READ(PFIT_CONTROL); - dev_priv->savePP_ON_DELAYS = I915_READ(PP_ON_DELAYS); - dev_priv->savePP_OFF_DELAYS = I915_READ(PP_OFF_DELAYS); - dev_priv->savePP_DIVISOR = I915_READ(PP_DIVISOR); + + if (IS_IGDNG(dev)) { + dev_priv->savePP_ON_DELAYS = I915_READ(PCH_PP_ON_DELAYS); + dev_priv->savePP_OFF_DELAYS = I915_READ(PCH_PP_OFF_DELAYS); + dev_priv->savePP_DIVISOR = I915_READ(PCH_PP_DIVISOR); + } else { + dev_priv->savePP_ON_DELAYS = I915_READ(PP_ON_DELAYS); + dev_priv->savePP_OFF_DELAYS = I915_READ(PP_OFF_DELAYS); + dev_priv->savePP_DIVISOR = I915_READ(PP_DIVISOR); + } /* Display Port state */ if (SUPPORTS_INTEGRATED_DP(dev)) { @@ -437,16 +567,23 @@ void i915_save_display(struct drm_device *dev) /* FIXME: save TV & SDVO state */ /* FBC state */ - dev_priv->saveFBC_CFB_BASE = I915_READ(FBC_CFB_BASE); - dev_priv->saveFBC_LL_BASE = I915_READ(FBC_LL_BASE); - dev_priv->saveFBC_CONTROL2 = I915_READ(FBC_CONTROL2); - dev_priv->saveFBC_CONTROL = I915_READ(FBC_CONTROL); + if (IS_GM45(dev)) { + dev_priv->saveDPFC_CB_BASE = I915_READ(DPFC_CB_BASE); + } else { + dev_priv->saveFBC_CFB_BASE = I915_READ(FBC_CFB_BASE); + dev_priv->saveFBC_LL_BASE = I915_READ(FBC_LL_BASE); + dev_priv->saveFBC_CONTROL2 = I915_READ(FBC_CONTROL2); + dev_priv->saveFBC_CONTROL = I915_READ(FBC_CONTROL); + } /* VGA state */ dev_priv->saveVGA0 = I915_READ(VGA0); dev_priv->saveVGA1 = I915_READ(VGA1); dev_priv->saveVGA_PD = I915_READ(VGA_PD); - dev_priv->saveVGACNTRL = I915_READ(VGACNTRL); + if (IS_IGDNG(dev)) + dev_priv->saveVGACNTRL = I915_READ(CPU_VGACNTRL); + else + dev_priv->saveVGACNTRL = I915_READ(VGACNTRL); i915_save_vga(dev); } @@ -485,22 +622,41 @@ void i915_restore_display(struct drm_device *dev) I915_WRITE(CURSIZE, dev_priv->saveCURSIZE); /* CRT state */ - I915_WRITE(ADPA, dev_priv->saveADPA); + if (IS_IGDNG(dev)) + I915_WRITE(PCH_ADPA, dev_priv->saveADPA); + else + I915_WRITE(ADPA, dev_priv->saveADPA); /* LVDS state */ - if (IS_I965G(dev)) + if (IS_I965G(dev) && !IS_IGDNG(dev)) I915_WRITE(BLC_PWM_CTL2, dev_priv->saveBLC_PWM_CTL2); - if (IS_MOBILE(dev) && !IS_I830(dev)) + + if (IS_IGDNG(dev)) { + I915_WRITE(PCH_LVDS, dev_priv->saveLVDS); + } else if (IS_MOBILE(dev) && !IS_I830(dev)) I915_WRITE(LVDS, dev_priv->saveLVDS); - if (!IS_I830(dev) && !IS_845G(dev)) + + if (!IS_I830(dev) && !IS_845G(dev) && !IS_IGDNG(dev)) I915_WRITE(PFIT_CONTROL, dev_priv->savePFIT_CONTROL); - I915_WRITE(PFIT_PGM_RATIOS, dev_priv->savePFIT_PGM_RATIOS); - I915_WRITE(BLC_PWM_CTL, dev_priv->saveBLC_PWM_CTL); - I915_WRITE(PP_ON_DELAYS, dev_priv->savePP_ON_DELAYS); - I915_WRITE(PP_OFF_DELAYS, dev_priv->savePP_OFF_DELAYS); - I915_WRITE(PP_DIVISOR, dev_priv->savePP_DIVISOR); - I915_WRITE(PP_CONTROL, dev_priv->savePP_CONTROL); + if (IS_IGDNG(dev)) { + I915_WRITE(BLC_PWM_PCH_CTL1, dev_priv->saveBLC_PWM_CTL); + I915_WRITE(BLC_PWM_PCH_CTL2, dev_priv->saveBLC_PWM_CTL2); + I915_WRITE(BLC_PWM_CPU_CTL, dev_priv->saveBLC_CPU_PWM_CTL); + I915_WRITE(BLC_PWM_CPU_CTL2, dev_priv->saveBLC_CPU_PWM_CTL2); + I915_WRITE(PCH_PP_ON_DELAYS, dev_priv->savePP_ON_DELAYS); + I915_WRITE(PCH_PP_OFF_DELAYS, dev_priv->savePP_OFF_DELAYS); + I915_WRITE(PCH_PP_DIVISOR, dev_priv->savePP_DIVISOR); + I915_WRITE(PCH_PP_CONTROL, dev_priv->savePP_CONTROL); + } else { + I915_WRITE(PFIT_PGM_RATIOS, dev_priv->savePFIT_PGM_RATIOS); + I915_WRITE(BLC_PWM_CTL, dev_priv->saveBLC_PWM_CTL); + I915_WRITE(BLC_HIST_CTL, dev_priv->saveBLC_HIST_CTL); + I915_WRITE(PP_ON_DELAYS, dev_priv->savePP_ON_DELAYS); + I915_WRITE(PP_OFF_DELAYS, dev_priv->savePP_OFF_DELAYS); + I915_WRITE(PP_DIVISOR, dev_priv->savePP_DIVISOR); + I915_WRITE(PP_CONTROL, dev_priv->savePP_CONTROL); + } /* Display Port state */ if (SUPPORTS_INTEGRATED_DP(dev)) { @@ -511,13 +667,22 @@ void i915_restore_display(struct drm_device *dev) /* FIXME: restore TV & SDVO state */ /* FBC info */ - I915_WRITE(FBC_CFB_BASE, dev_priv->saveFBC_CFB_BASE); - I915_WRITE(FBC_LL_BASE, dev_priv->saveFBC_LL_BASE); - I915_WRITE(FBC_CONTROL2, dev_priv->saveFBC_CONTROL2); - I915_WRITE(FBC_CONTROL, dev_priv->saveFBC_CONTROL); + if (IS_GM45(dev)) { + g4x_disable_fbc(dev); + I915_WRITE(DPFC_CB_BASE, dev_priv->saveDPFC_CB_BASE); + } else { + i8xx_disable_fbc(dev); + I915_WRITE(FBC_CFB_BASE, dev_priv->saveFBC_CFB_BASE); + I915_WRITE(FBC_LL_BASE, dev_priv->saveFBC_LL_BASE); + I915_WRITE(FBC_CONTROL2, dev_priv->saveFBC_CONTROL2); + I915_WRITE(FBC_CONTROL, dev_priv->saveFBC_CONTROL); + } /* VGA state */ - I915_WRITE(VGACNTRL, dev_priv->saveVGACNTRL); + if (IS_IGDNG(dev)) + I915_WRITE(CPU_VGACNTRL, dev_priv->saveVGACNTRL); + else + I915_WRITE(VGACNTRL, dev_priv->saveVGACNTRL); I915_WRITE(VGA0, dev_priv->saveVGA0); I915_WRITE(VGA1, dev_priv->saveVGA1); I915_WRITE(VGA_PD, dev_priv->saveVGA_PD); @@ -543,8 +708,17 @@ int i915_save_state(struct drm_device *dev) i915_save_display(dev); /* Interrupt state */ - dev_priv->saveIER = I915_READ(IER); - dev_priv->saveIMR = I915_READ(IMR); + if (IS_IGDNG(dev)) { + dev_priv->saveDEIER = I915_READ(DEIER); + dev_priv->saveDEIMR = I915_READ(DEIMR); + dev_priv->saveGTIER = I915_READ(GTIER); + dev_priv->saveGTIMR = I915_READ(GTIMR); + dev_priv->saveFDI_RXA_IMR = I915_READ(FDI_RXA_IMR); + dev_priv->saveFDI_RXB_IMR = I915_READ(FDI_RXB_IMR); + } else { + dev_priv->saveIER = I915_READ(IER); + dev_priv->saveIMR = I915_READ(IMR); + } /* Clock gating state */ dev_priv->saveD_STATE = I915_READ(D_STATE); @@ -609,8 +783,17 @@ int i915_restore_state(struct drm_device *dev) i915_restore_display(dev); /* Interrupt state */ - I915_WRITE (IER, dev_priv->saveIER); - I915_WRITE (IMR, dev_priv->saveIMR); + if (IS_IGDNG(dev)) { + I915_WRITE(DEIER, dev_priv->saveDEIER); + I915_WRITE(DEIMR, dev_priv->saveDEIMR); + I915_WRITE(GTIER, dev_priv->saveGTIER); + I915_WRITE(GTIMR, dev_priv->saveGTIMR); + I915_WRITE(FDI_RXA_IMR, dev_priv->saveFDI_RXA_IMR); + I915_WRITE(FDI_RXB_IMR, dev_priv->saveFDI_RXB_IMR); + } else { + I915_WRITE (IER, dev_priv->saveIER); + I915_WRITE (IMR, dev_priv->saveIMR); + } /* Clock gating state */ I915_WRITE (D_STATE, dev_priv->saveD_STATE); diff --git a/drivers/gpu/drm/i915/i915_trace.h b/drivers/gpu/drm/i915/i915_trace.h index 5567a40816f3..01840d9bc38f 100644 --- a/drivers/gpu/drm/i915/i915_trace.h +++ b/drivers/gpu/drm/i915/i915_trace.h @@ -158,16 +158,17 @@ TRACE_EVENT(i915_gem_request_submit, TP_ARGS(dev, seqno), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) __field(u32, seqno) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; __entry->seqno = seqno; + i915_trace_irq_get(dev, seqno); ), - TP_printk("dev=%p, seqno=%u", __entry->dev, __entry->seqno) + TP_printk("dev=%u, seqno=%u", __entry->dev, __entry->seqno) ); TRACE_EVENT(i915_gem_request_flush, @@ -178,20 +179,20 @@ TRACE_EVENT(i915_gem_request_flush, TP_ARGS(dev, seqno, flush_domains, invalidate_domains), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) __field(u32, seqno) __field(u32, flush_domains) __field(u32, invalidate_domains) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; __entry->seqno = seqno; __entry->flush_domains = flush_domains; __entry->invalidate_domains = invalidate_domains; ), - TP_printk("dev=%p, seqno=%u, flush=%04x, invalidate=%04x", + TP_printk("dev=%u, seqno=%u, flush=%04x, invalidate=%04x", __entry->dev, __entry->seqno, __entry->flush_domains, __entry->invalidate_domains) ); @@ -204,16 +205,16 @@ TRACE_EVENT(i915_gem_request_complete, TP_ARGS(dev, seqno), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) __field(u32, seqno) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; __entry->seqno = seqno; ), - TP_printk("dev=%p, seqno=%u", __entry->dev, __entry->seqno) + TP_printk("dev=%u, seqno=%u", __entry->dev, __entry->seqno) ); TRACE_EVENT(i915_gem_request_retire, @@ -223,16 +224,16 @@ TRACE_EVENT(i915_gem_request_retire, TP_ARGS(dev, seqno), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) __field(u32, seqno) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; __entry->seqno = seqno; ), - TP_printk("dev=%p, seqno=%u", __entry->dev, __entry->seqno) + TP_printk("dev=%u, seqno=%u", __entry->dev, __entry->seqno) ); TRACE_EVENT(i915_gem_request_wait_begin, @@ -242,16 +243,16 @@ TRACE_EVENT(i915_gem_request_wait_begin, TP_ARGS(dev, seqno), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) __field(u32, seqno) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; __entry->seqno = seqno; ), - TP_printk("dev=%p, seqno=%u", __entry->dev, __entry->seqno) + TP_printk("dev=%u, seqno=%u", __entry->dev, __entry->seqno) ); TRACE_EVENT(i915_gem_request_wait_end, @@ -261,16 +262,16 @@ TRACE_EVENT(i915_gem_request_wait_end, TP_ARGS(dev, seqno), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) __field(u32, seqno) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; __entry->seqno = seqno; ), - TP_printk("dev=%p, seqno=%u", __entry->dev, __entry->seqno) + TP_printk("dev=%u, seqno=%u", __entry->dev, __entry->seqno) ); TRACE_EVENT(i915_ring_wait_begin, @@ -280,14 +281,14 @@ TRACE_EVENT(i915_ring_wait_begin, TP_ARGS(dev), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; ), - TP_printk("dev=%p", __entry->dev) + TP_printk("dev=%u", __entry->dev) ); TRACE_EVENT(i915_ring_wait_end, @@ -297,14 +298,14 @@ TRACE_EVENT(i915_ring_wait_end, TP_ARGS(dev), TP_STRUCT__entry( - __field(struct drm_device *, dev) + __field(u32, dev) ), TP_fast_assign( - __entry->dev = dev; + __entry->dev = dev->primary->index; ), - TP_printk("dev=%p", __entry->dev) + TP_printk("dev=%u", __entry->dev) ); #endif /* _I915_TRACE_H_ */ diff --git a/drivers/gpu/drm/i915/intel_bios.c b/drivers/gpu/drm/i915/intel_bios.c index 4337414846b6..96cd256e60e6 100644 --- a/drivers/gpu/drm/i915/intel_bios.c +++ b/drivers/gpu/drm/i915/intel_bios.c @@ -351,20 +351,18 @@ parse_driver_features(struct drm_i915_private *dev_priv, struct drm_device *dev = dev_priv->dev; struct bdb_driver_features *driver; - /* set default for chips without eDP */ - if (!SUPPORTS_EDP(dev)) { - dev_priv->edp_support = 0; - return; - } - driver = find_section(bdb, BDB_DRIVER_FEATURES); if (!driver) return; - if (driver->lvds_config == BDB_DRIVER_FEATURE_EDP) + if (driver && SUPPORTS_EDP(dev) && + driver->lvds_config == BDB_DRIVER_FEATURE_EDP) { dev_priv->edp_support = 1; + } else { + dev_priv->edp_support = 0; + } - if (driver->dual_frequency) + if (driver && driver->dual_frequency) dev_priv->render_reclock_avail = true; } diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 93ff6c03733e..3ba6546b7c7f 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -943,6 +943,7 @@ intel_find_pll_g4x_dp(const intel_limit_t *limit, struct drm_crtc *crtc, clock.m = 5 * (clock.m1 + 2) + (clock.m2 + 2); clock.p = (clock.p1 * clock.p2); clock.dot = 96000 * clock.m / (clock.n + 2) / clock.p; + clock.vco = 0; memcpy(best_clock, &clock, sizeof(intel_clock_t)); return true; } @@ -1260,9 +1261,11 @@ intel_pipe_set_base(struct drm_crtc *crtc, int x, int y, return ret; } - /* Pre-i965 needs to install a fence for tiled scan-out */ - if (!IS_I965G(dev) && - obj_priv->fence_reg == I915_FENCE_REG_NONE && + /* Install a fence for tiled scan-out. Pre-i965 always needs a fence, + * whereas 965+ only requires a fence if using framebuffer compression. + * For simplicity, we always install a fence as the cost is not that onerous. + */ + if (obj_priv->fence_reg == I915_FENCE_REG_NONE && obj_priv->tiling_mode != I915_TILING_NONE) { ret = i915_gem_object_get_fence_reg(obj); if (ret != 0) { @@ -1513,7 +1516,7 @@ static void igdng_crtc_dpms(struct drm_crtc *crtc, int mode) /* Enable panel fitting for LVDS */ if (intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS)) { temp = I915_READ(pf_ctl_reg); - I915_WRITE(pf_ctl_reg, temp | PF_ENABLE); + I915_WRITE(pf_ctl_reg, temp | PF_ENABLE | PF_FILTER_MED_3x3); /* currently full aspect */ I915_WRITE(pf_win_pos, 0); @@ -1801,6 +1804,8 @@ static void i9xx_crtc_dpms(struct drm_crtc *crtc, int mode) case DRM_MODE_DPMS_ON: case DRM_MODE_DPMS_STANDBY: case DRM_MODE_DPMS_SUSPEND: + intel_update_watermarks(dev); + /* Enable the DPLL */ temp = I915_READ(dpll_reg); if ((temp & DPLL_VCO_ENABLE) == 0) { @@ -1838,7 +1843,6 @@ static void i9xx_crtc_dpms(struct drm_crtc *crtc, int mode) /* Give the overlay scaler a chance to enable if it's on this pipe */ //intel_crtc_dpms_video(crtc, true); TODO - intel_update_watermarks(dev); break; case DRM_MODE_DPMS_OFF: intel_update_watermarks(dev); @@ -2082,7 +2086,7 @@ fdi_reduce_ratio(u32 *num, u32 *den) #define LINK_N 0x80000 static void -igdng_compute_m_n(int bytes_per_pixel, int nlanes, +igdng_compute_m_n(int bits_per_pixel, int nlanes, int pixel_clock, int link_clock, struct fdi_m_n *m_n) { @@ -2092,7 +2096,8 @@ igdng_compute_m_n(int bytes_per_pixel, int nlanes, temp = (u64) DATA_N * pixel_clock; temp = div_u64(temp, link_clock); - m_n->gmch_m = div_u64(temp * bytes_per_pixel, nlanes); + m_n->gmch_m = div_u64(temp * bits_per_pixel, nlanes); + m_n->gmch_m >>= 3; /* convert to bytes_per_pixel */ m_n->gmch_n = DATA_N; fdi_reduce_ratio(&m_n->gmch_m, &m_n->gmch_n); @@ -2140,6 +2145,13 @@ static struct intel_watermark_params igd_cursor_hplloff_wm = { IGD_CURSOR_GUARD_WM, IGD_FIFO_LINE_SIZE }; +static struct intel_watermark_params g4x_wm_info = { + G4X_FIFO_SIZE, + G4X_MAX_WM, + G4X_MAX_WM, + 2, + G4X_FIFO_LINE_SIZE, +}; static struct intel_watermark_params i945_wm_info = { I945_FIFO_SIZE, I915_MAX_WM, @@ -2430,17 +2442,74 @@ static int i830_get_fifo_size(struct drm_device *dev, int plane) return size; } -static void g4x_update_wm(struct drm_device *dev, int unused, int unused2, - int unused3, int unused4) +static void g4x_update_wm(struct drm_device *dev, int planea_clock, + int planeb_clock, int sr_hdisplay, int pixel_size) { struct drm_i915_private *dev_priv = dev->dev_private; - u32 fw_blc_self = I915_READ(FW_BLC_SELF); + int total_size, cacheline_size; + int planea_wm, planeb_wm, cursora_wm, cursorb_wm, cursor_sr; + struct intel_watermark_params planea_params, planeb_params; + unsigned long line_time_us; + int sr_clock, sr_entries = 0, entries_required; - if (i915_powersave) - fw_blc_self |= FW_BLC_SELF_EN; - else - fw_blc_self &= ~FW_BLC_SELF_EN; - I915_WRITE(FW_BLC_SELF, fw_blc_self); + /* Create copies of the base settings for each pipe */ + planea_params = planeb_params = g4x_wm_info; + + /* Grab a couple of global values before we overwrite them */ + total_size = planea_params.fifo_size; + cacheline_size = planea_params.cacheline_size; + + /* + * Note: we need to make sure we don't overflow for various clock & + * latency values. + * clocks go from a few thousand to several hundred thousand. + * latency is usually a few thousand + */ + entries_required = ((planea_clock / 1000) * pixel_size * latency_ns) / + 1000; + entries_required /= G4X_FIFO_LINE_SIZE; + planea_wm = entries_required + planea_params.guard_size; + + entries_required = ((planeb_clock / 1000) * pixel_size * latency_ns) / + 1000; + entries_required /= G4X_FIFO_LINE_SIZE; + planeb_wm = entries_required + planeb_params.guard_size; + + cursora_wm = cursorb_wm = 16; + cursor_sr = 32; + + DRM_DEBUG("FIFO watermarks - A: %d, B: %d\n", planea_wm, planeb_wm); + + /* Calc sr entries for one plane configs */ + if (sr_hdisplay && (!planea_clock || !planeb_clock)) { + /* self-refresh has much higher latency */ + const static int sr_latency_ns = 12000; + + sr_clock = planea_clock ? planea_clock : planeb_clock; + line_time_us = ((sr_hdisplay * 1000) / sr_clock); + + /* Use ns/us then divide to preserve precision */ + sr_entries = (((sr_latency_ns / line_time_us) + 1) * + pixel_size * sr_hdisplay) / 1000; + sr_entries = roundup(sr_entries / cacheline_size, 1); + DRM_DEBUG("self-refresh entries: %d\n", sr_entries); + I915_WRITE(FW_BLC_SELF, FW_BLC_SELF_EN); + } + + DRM_DEBUG("Setting FIFO watermarks - A: %d, B: %d, SR %d\n", + planea_wm, planeb_wm, sr_entries); + + planea_wm &= 0x3f; + planeb_wm &= 0x3f; + + I915_WRITE(DSPFW1, (sr_entries << DSPFW_SR_SHIFT) | + (cursorb_wm << DSPFW_CURSORB_SHIFT) | + (planeb_wm << DSPFW_PLANEB_SHIFT) | planea_wm); + I915_WRITE(DSPFW2, (I915_READ(DSPFW2) & DSPFW_CURSORA_MASK) | + (cursora_wm << DSPFW_CURSORA_SHIFT)); + /* HPLL off in SR has some issues on G4x... disable it */ + I915_WRITE(DSPFW3, (I915_READ(DSPFW3) & ~DSPFW_HPLL_SR_EN) | + (cursor_sr << DSPFW_CURSOR_SR_SHIFT)); } static void i965_update_wm(struct drm_device *dev, int unused, int unused2, @@ -2586,6 +2655,9 @@ static void intel_update_watermarks(struct drm_device *dev) unsigned long planea_clock = 0, planeb_clock = 0, sr_clock = 0; int enabled = 0, pixel_size = 0; + if (!dev_priv->display.update_wm) + return; + /* Get the clock config from both planes */ list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { intel_crtc = to_intel_crtc(crtc); @@ -2763,7 +2835,7 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc, /* FDI link */ if (IS_IGDNG(dev)) { - int lane, link_bw; + int lane, link_bw, bpp; /* eDP doesn't require FDI link, so just set DP M/N according to current link config */ if (is_edp) { @@ -2782,10 +2854,72 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc, lane = 4; link_bw = 270000; } - igdng_compute_m_n(3, lane, target_clock, + + /* determine panel color depth */ + temp = I915_READ(pipeconf_reg); + + switch (temp & PIPE_BPC_MASK) { + case PIPE_8BPC: + bpp = 24; + break; + case PIPE_10BPC: + bpp = 30; + break; + case PIPE_6BPC: + bpp = 18; + break; + case PIPE_12BPC: + bpp = 36; + break; + default: + DRM_ERROR("unknown pipe bpc value\n"); + bpp = 24; + } + + igdng_compute_m_n(bpp, lane, target_clock, link_bw, &m_n); } + /* Ironlake: try to setup display ref clock before DPLL + * enabling. This is only under driver's control after + * PCH B stepping, previous chipset stepping should be + * ignoring this setting. + */ + if (IS_IGDNG(dev)) { + temp = I915_READ(PCH_DREF_CONTROL); + /* Always enable nonspread source */ + temp &= ~DREF_NONSPREAD_SOURCE_MASK; + temp |= DREF_NONSPREAD_SOURCE_ENABLE; + I915_WRITE(PCH_DREF_CONTROL, temp); + POSTING_READ(PCH_DREF_CONTROL); + + temp &= ~DREF_SSC_SOURCE_MASK; + temp |= DREF_SSC_SOURCE_ENABLE; + I915_WRITE(PCH_DREF_CONTROL, temp); + POSTING_READ(PCH_DREF_CONTROL); + + udelay(200); + + if (is_edp) { + if (dev_priv->lvds_use_ssc) { + temp |= DREF_SSC1_ENABLE; + I915_WRITE(PCH_DREF_CONTROL, temp); + POSTING_READ(PCH_DREF_CONTROL); + + udelay(200); + + temp &= ~DREF_CPU_SOURCE_OUTPUT_MASK; + temp |= DREF_CPU_SOURCE_OUTPUT_DOWNSPREAD; + I915_WRITE(PCH_DREF_CONTROL, temp); + POSTING_READ(PCH_DREF_CONTROL); + } else { + temp |= DREF_CPU_SOURCE_OUTPUT_NONSPREAD; + I915_WRITE(PCH_DREF_CONTROL, temp); + POSTING_READ(PCH_DREF_CONTROL); + } + } + } + if (IS_IGD(dev)) { fp = (1 << clock.n) << 16 | clock.m1 << 8 | clock.m2; if (has_reduced_clock) @@ -2936,6 +3070,8 @@ static int intel_crtc_mode_set(struct drm_crtc *crtc, lvds = I915_READ(lvds_reg); lvds |= LVDS_PORT_EN | LVDS_A0A2_CLKA_POWER_UP | LVDS_PIPEB_SELECT; + /* set the corresponsding LVDS_BORDER bit */ + lvds |= dev_priv->lvds_border_bits; /* Set the B0-B3 data pairs corresponding to whether we're going to * set the DPLLs for dual-channel mode or not. */ @@ -3095,7 +3231,6 @@ static int intel_crtc_cursor_set(struct drm_crtc *crtc, struct drm_gem_object *bo; struct drm_i915_gem_object *obj_priv; int pipe = intel_crtc->pipe; - int plane = intel_crtc->plane; uint32_t control = (pipe == 0) ? CURACNTR : CURBCNTR; uint32_t base = (pipe == 0) ? CURABASE : CURBBASE; uint32_t temp = I915_READ(control); @@ -3182,9 +3317,6 @@ static int intel_crtc_cursor_set(struct drm_crtc *crtc, drm_gem_object_unreference(intel_crtc->cursor_bo); } - if ((IS_I965G(dev) || plane == 0)) - intel_update_fbc(crtc, &crtc->mode); - mutex_unlock(&dev->struct_mutex); intel_crtc->cursor_addr = addr; @@ -3244,6 +3376,16 @@ void intel_crtc_fb_gamma_set(struct drm_crtc *crtc, u16 red, u16 green, intel_crtc->lut_b[regno] = blue >> 8; } +void intel_crtc_fb_gamma_get(struct drm_crtc *crtc, u16 *red, u16 *green, + u16 *blue, int regno) +{ + struct intel_crtc *intel_crtc = to_intel_crtc(crtc); + + *red = intel_crtc->lut_r[regno] << 8; + *green = intel_crtc->lut_g[regno] << 8; + *blue = intel_crtc->lut_b[regno] << 8; +} + static void intel_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, u16 *blue, uint32_t size) { @@ -3835,6 +3977,7 @@ static const struct drm_crtc_helper_funcs intel_helper_funcs = { .mode_set_base = intel_pipe_set_base, .prepare = intel_crtc_prepare, .commit = intel_crtc_commit, + .load_lut = intel_crtc_load_lut, }; static const struct drm_crtc_funcs intel_crtc_funcs = { @@ -4117,7 +4260,9 @@ void intel_init_clock_gating(struct drm_device *dev) * Disable clock gating reported to work incorrectly according to the * specs, but enable as much else as we can. */ - if (IS_G4X(dev)) { + if (IS_IGDNG(dev)) { + return; + } else if (IS_G4X(dev)) { uint32_t dspclk_gate; I915_WRITE(RENCLK_GATE_D1, 0); I915_WRITE(RENCLK_GATE_D2, VF_UNIT_CLOCK_GATE_DISABLE | @@ -4205,7 +4350,9 @@ static void intel_init_display(struct drm_device *dev) i830_get_display_clock_speed; /* For FIFO watermark updates */ - if (IS_G4X(dev)) + if (IS_IGDNG(dev)) + dev_priv->display.update_wm = NULL; + else if (IS_G4X(dev)) dev_priv->display.update_wm = g4x_update_wm; else if (IS_I965G(dev)) dev_priv->display.update_wm = i965_update_wm; diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index f4856a510476..d83447557f9b 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -400,7 +400,7 @@ intel_dp_i2c_init(struct intel_output *intel_output, const char *name) { struct intel_dp_priv *dp_priv = intel_output->dev_priv; - DRM_ERROR("i2c_init %s\n", name); + DRM_DEBUG_KMS("i2c_init %s\n", name); dp_priv->algo.running = false; dp_priv->algo.address = 0; dp_priv->algo.aux_ch = intel_dp_i2c_aux_ch; diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index 8aa4b7f30daa..ef61fe9507e2 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -175,6 +175,8 @@ extern int intelfb_resize(struct drm_device *dev, struct drm_crtc *crtc); extern void intelfb_restore(void); extern void intel_crtc_fb_gamma_set(struct drm_crtc *crtc, u16 red, u16 green, u16 blue, int regno); +extern void intel_crtc_fb_gamma_get(struct drm_crtc *crtc, u16 *red, u16 *green, + u16 *blue, int regno); extern int intel_framebuffer_create(struct drm_device *dev, struct drm_mode_fb_cmd *mode_cmd, diff --git a/drivers/gpu/drm/i915/intel_fb.c b/drivers/gpu/drm/i915/intel_fb.c index e85d7e9eed7d..2b0fe54cd92c 100644 --- a/drivers/gpu/drm/i915/intel_fb.c +++ b/drivers/gpu/drm/i915/intel_fb.c @@ -60,10 +60,12 @@ static struct fb_ops intelfb_ops = { .fb_imageblit = cfb_imageblit, .fb_pan_display = drm_fb_helper_pan_display, .fb_blank = drm_fb_helper_blank, + .fb_setcmap = drm_fb_helper_setcmap, }; static struct drm_fb_helper_funcs intel_fb_helper_funcs = { .gamma_set = intel_crtc_fb_gamma_set, + .gamma_get = intel_crtc_fb_gamma_get, }; @@ -123,6 +125,10 @@ static int intelfb_create(struct drm_device *dev, uint32_t fb_width, struct device *device = &dev->pdev->dev; int size, ret, mmio_bar = IS_I9XX(dev) ? 0 : 1; + /* we don't do packed 24bpp */ + if (surface_bpp == 24) + surface_bpp = 32; + mode_cmd.width = surface_width; mode_cmd.height = surface_height; @@ -206,7 +212,7 @@ static int intelfb_create(struct drm_device *dev, uint32_t fb_width, // memset(info->screen_base, 0, size); - drm_fb_helper_fill_fix(info, fb->pitch); + drm_fb_helper_fill_fix(info, fb->pitch, fb->depth); drm_fb_helper_fill_var(info, fb, fb_width, fb_height); /* FIXME: we really shouldn't expose mmio space at all */ @@ -244,7 +250,7 @@ int intelfb_probe(struct drm_device *dev) int ret; DRM_DEBUG("\n"); - ret = drm_fb_helper_single_fb_probe(dev, intelfb_create); + ret = drm_fb_helper_single_fb_probe(dev, 32, intelfb_create); return ret; } EXPORT_SYMBOL(intelfb_probe); diff --git a/drivers/gpu/drm/i915/intel_hdmi.c b/drivers/gpu/drm/i915/intel_hdmi.c index fa304e136010..663ab6de0b58 100644 --- a/drivers/gpu/drm/i915/intel_hdmi.c +++ b/drivers/gpu/drm/i915/intel_hdmi.c @@ -223,7 +223,7 @@ void intel_hdmi_init(struct drm_device *dev, int sdvox_reg) connector = &intel_output->base; drm_connector_init(dev, connector, &intel_hdmi_connector_funcs, - DRM_MODE_CONNECTOR_DVID); + DRM_MODE_CONNECTOR_HDMIA); drm_connector_helper_add(connector, &intel_hdmi_connector_helper_funcs); intel_output->type = INTEL_OUTPUT_HDMI; diff --git a/drivers/gpu/drm/i915/intel_lvds.c b/drivers/gpu/drm/i915/intel_lvds.c index 98ae3d73577e..05598ae10c4b 100644 --- a/drivers/gpu/drm/i915/intel_lvds.c +++ b/drivers/gpu/drm/i915/intel_lvds.c @@ -380,7 +380,7 @@ static bool intel_lvds_mode_fixup(struct drm_encoder *encoder, adjusted_mode->crtc_vblank_start + vsync_pos; /* keep the vsync width constant */ adjusted_mode->crtc_vsync_end = - adjusted_mode->crtc_vblank_start + vsync_width; + adjusted_mode->crtc_vsync_start + vsync_width; border = 1; break; case DRM_MODE_SCALE_ASPECT: @@ -526,6 +526,14 @@ out: lvds_priv->pfit_control = pfit_control; lvds_priv->pfit_pgm_ratios = pfit_pgm_ratios; /* + * When there exists the border, it means that the LVDS_BORDR + * should be enabled. + */ + if (border) + dev_priv->lvds_border_bits |= LVDS_BORDER_ENABLE; + else + dev_priv->lvds_border_bits &= ~(LVDS_BORDER_ENABLE); + /* * XXX: It would be nice to support lower refresh rates on the * panels to reduce power consumption, and perhaps match the * user's requested refresh rate. @@ -656,6 +664,15 @@ static int intel_lvds_get_modes(struct drm_connector *connector) return 0; } +/* + * Lid events. Note the use of 'modeset_on_lid': + * - we set it on lid close, and reset it on open + * - we use it as a "only once" bit (ie we ignore + * duplicate events where it was already properly + * set/reset) + * - the suspend/resume paths will also set it to + * zero, since they restore the mode ("lid open"). + */ static int intel_lid_notify(struct notifier_block *nb, unsigned long val, void *unused) { @@ -663,13 +680,19 @@ static int intel_lid_notify(struct notifier_block *nb, unsigned long val, container_of(nb, struct drm_i915_private, lid_notifier); struct drm_device *dev = dev_priv->dev; - if (acpi_lid_open() && !dev_priv->suspended) { - mutex_lock(&dev->mode_config.mutex); - drm_helper_resume_force_mode(dev); - mutex_unlock(&dev->mode_config.mutex); + if (!acpi_lid_open()) { + dev_priv->modeset_on_lid = 1; + return NOTIFY_OK; } - drm_sysfs_hotplug_event(dev_priv->dev); + if (!dev_priv->modeset_on_lid) + return NOTIFY_OK; + + dev_priv->modeset_on_lid = 0; + + mutex_lock(&dev->mode_config.mutex); + drm_helper_resume_force_mode(dev); + mutex_unlock(&dev->mode_config.mutex); return NOTIFY_OK; } diff --git a/drivers/gpu/drm/i915/intel_tv.c b/drivers/gpu/drm/i915/intel_tv.c index c64eab493fb0..9ca917931afb 100644 --- a/drivers/gpu/drm/i915/intel_tv.c +++ b/drivers/gpu/drm/i915/intel_tv.c @@ -1082,7 +1082,8 @@ intel_tv_mode_valid(struct drm_connector *connector, struct drm_display_mode *mo const struct tv_mode *tv_mode = intel_tv_mode_find(intel_output); /* Ensure TV refresh is close to desired refresh */ - if (tv_mode && abs(tv_mode->refresh - drm_mode_vrefresh(mode)) < 10) + if (tv_mode && abs(tv_mode->refresh - drm_mode_vrefresh(mode) * 1000) + < 1000) return MODE_OK; return MODE_CLOCK_RANGE; } diff --git a/drivers/gpu/drm/radeon/Makefile b/drivers/gpu/drm/radeon/Makefile index 09a28923f46e..b5713eedd6e1 100644 --- a/drivers/gpu/drm/radeon/Makefile +++ b/drivers/gpu/drm/radeon/Makefile @@ -49,7 +49,7 @@ radeon-y += radeon_device.o radeon_kms.o \ radeon_cs.o radeon_bios.o radeon_benchmark.o r100.o r300.o r420.o \ rs400.o rs600.o rs690.o rv515.o r520.o r600.o rv770.o radeon_test.o \ r200.o radeon_legacy_tv.o r600_cs.o r600_blit.o r600_blit_shaders.o \ - r600_blit_kms.o + r600_blit_kms.o radeon_pm.o radeon-$(CONFIG_COMPAT) += radeon_ioc32.o diff --git a/drivers/gpu/drm/radeon/atombios.h b/drivers/gpu/drm/radeon/atombios.h index 5d402086bc47..c11ddddfb3b6 100644 --- a/drivers/gpu/drm/radeon/atombios.h +++ b/drivers/gpu/drm/radeon/atombios.h @@ -2314,7 +2314,7 @@ typedef struct _ATOM_SPREAD_SPECTRUM_ASSIGNMENT { UCHAR ucSS_Step; UCHAR ucSS_Delay; UCHAR ucSS_Id; - UCHAR ucRecommandedRef_Div; + UCHAR ucRecommendedRef_Div; UCHAR ucSS_Range; /* it was reserved for V11 */ } ATOM_SPREAD_SPECTRUM_ASSIGNMENT; diff --git a/drivers/gpu/drm/radeon/atombios_crtc.c b/drivers/gpu/drm/radeon/atombios_crtc.c index 6a015929deee..c15287a590ff 100644 --- a/drivers/gpu/drm/radeon/atombios_crtc.c +++ b/drivers/gpu/drm/radeon/atombios_crtc.c @@ -31,10 +31,6 @@ #include "atom.h" #include "atom-bits.h" -/* evil but including atombios.h is much worse */ -bool radeon_atom_get_tv_timings(struct radeon_device *rdev, int index, - SET_CRTC_TIMING_PARAMETERS_PS_ALLOCATION *crtc_timing, - int32_t *pixel_clock); static void atombios_overscan_setup(struct drm_crtc *crtc, struct drm_display_mode *mode, struct drm_display_mode *adjusted_mode) @@ -248,18 +244,18 @@ void atombios_crtc_dpms(struct drm_crtc *crtc, int mode) switch (mode) { case DRM_MODE_DPMS_ON: + atombios_enable_crtc(crtc, 1); if (ASIC_IS_DCE3(rdev)) atombios_enable_crtc_memreq(crtc, 1); - atombios_enable_crtc(crtc, 1); atombios_blank_crtc(crtc, 0); break; case DRM_MODE_DPMS_STANDBY: case DRM_MODE_DPMS_SUSPEND: case DRM_MODE_DPMS_OFF: atombios_blank_crtc(crtc, 1); - atombios_enable_crtc(crtc, 0); if (ASIC_IS_DCE3(rdev)) atombios_enable_crtc_memreq(crtc, 0); + atombios_enable_crtc(crtc, 0); break; } @@ -270,59 +266,147 @@ void atombios_crtc_dpms(struct drm_crtc *crtc, int mode) static void atombios_set_crtc_dtd_timing(struct drm_crtc *crtc, - SET_CRTC_USING_DTD_TIMING_PARAMETERS * crtc_param) + struct drm_display_mode *mode) { + struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); struct drm_device *dev = crtc->dev; struct radeon_device *rdev = dev->dev_private; - SET_CRTC_USING_DTD_TIMING_PARAMETERS conv_param; + SET_CRTC_USING_DTD_TIMING_PARAMETERS args; int index = GetIndexIntoMasterTable(COMMAND, SetCRTC_UsingDTDTiming); + u16 misc = 0; - conv_param.usH_Size = cpu_to_le16(crtc_param->usH_Size); - conv_param.usH_Blanking_Time = - cpu_to_le16(crtc_param->usH_Blanking_Time); - conv_param.usV_Size = cpu_to_le16(crtc_param->usV_Size); - conv_param.usV_Blanking_Time = - cpu_to_le16(crtc_param->usV_Blanking_Time); - conv_param.usH_SyncOffset = cpu_to_le16(crtc_param->usH_SyncOffset); - conv_param.usH_SyncWidth = cpu_to_le16(crtc_param->usH_SyncWidth); - conv_param.usV_SyncOffset = cpu_to_le16(crtc_param->usV_SyncOffset); - conv_param.usV_SyncWidth = cpu_to_le16(crtc_param->usV_SyncWidth); - conv_param.susModeMiscInfo.usAccess = - cpu_to_le16(crtc_param->susModeMiscInfo.usAccess); - conv_param.ucCRTC = crtc_param->ucCRTC; + memset(&args, 0, sizeof(args)); + args.usH_Size = cpu_to_le16(mode->crtc_hdisplay); + args.usH_Blanking_Time = + cpu_to_le16(mode->crtc_hblank_end - mode->crtc_hdisplay); + args.usV_Size = cpu_to_le16(mode->crtc_vdisplay); + args.usV_Blanking_Time = + cpu_to_le16(mode->crtc_vblank_end - mode->crtc_vdisplay); + args.usH_SyncOffset = + cpu_to_le16(mode->crtc_hsync_start - mode->crtc_hdisplay); + args.usH_SyncWidth = + cpu_to_le16(mode->crtc_hsync_end - mode->crtc_hsync_start); + args.usV_SyncOffset = + cpu_to_le16(mode->crtc_vsync_start - mode->crtc_vdisplay); + args.usV_SyncWidth = + cpu_to_le16(mode->crtc_vsync_end - mode->crtc_vsync_start); + /*args.ucH_Border = mode->hborder;*/ + /*args.ucV_Border = mode->vborder;*/ + + if (mode->flags & DRM_MODE_FLAG_NVSYNC) + misc |= ATOM_VSYNC_POLARITY; + if (mode->flags & DRM_MODE_FLAG_NHSYNC) + misc |= ATOM_HSYNC_POLARITY; + if (mode->flags & DRM_MODE_FLAG_CSYNC) + misc |= ATOM_COMPOSITESYNC; + if (mode->flags & DRM_MODE_FLAG_INTERLACE) + misc |= ATOM_INTERLACE; + if (mode->flags & DRM_MODE_FLAG_DBLSCAN) + misc |= ATOM_DOUBLE_CLOCK_MODE; + + args.susModeMiscInfo.usAccess = cpu_to_le16(misc); + args.ucCRTC = radeon_crtc->crtc_id; printk("executing set crtc dtd timing\n"); - atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&conv_param); + atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); } -void atombios_crtc_set_timing(struct drm_crtc *crtc, - SET_CRTC_TIMING_PARAMETERS_PS_ALLOCATION * - crtc_param) +static void atombios_crtc_set_timing(struct drm_crtc *crtc, + struct drm_display_mode *mode) { + struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); struct drm_device *dev = crtc->dev; struct radeon_device *rdev = dev->dev_private; - SET_CRTC_TIMING_PARAMETERS_PS_ALLOCATION conv_param; + SET_CRTC_TIMING_PARAMETERS_PS_ALLOCATION args; int index = GetIndexIntoMasterTable(COMMAND, SetCRTC_Timing); + u16 misc = 0; - conv_param.usH_Total = cpu_to_le16(crtc_param->usH_Total); - conv_param.usH_Disp = cpu_to_le16(crtc_param->usH_Disp); - conv_param.usH_SyncStart = cpu_to_le16(crtc_param->usH_SyncStart); - conv_param.usH_SyncWidth = cpu_to_le16(crtc_param->usH_SyncWidth); - conv_param.usV_Total = cpu_to_le16(crtc_param->usV_Total); - conv_param.usV_Disp = cpu_to_le16(crtc_param->usV_Disp); - conv_param.usV_SyncStart = cpu_to_le16(crtc_param->usV_SyncStart); - conv_param.usV_SyncWidth = cpu_to_le16(crtc_param->usV_SyncWidth); - conv_param.susModeMiscInfo.usAccess = - cpu_to_le16(crtc_param->susModeMiscInfo.usAccess); - conv_param.ucCRTC = crtc_param->ucCRTC; - conv_param.ucOverscanRight = crtc_param->ucOverscanRight; - conv_param.ucOverscanLeft = crtc_param->ucOverscanLeft; - conv_param.ucOverscanBottom = crtc_param->ucOverscanBottom; - conv_param.ucOverscanTop = crtc_param->ucOverscanTop; - conv_param.ucReserved = crtc_param->ucReserved; + memset(&args, 0, sizeof(args)); + args.usH_Total = cpu_to_le16(mode->crtc_htotal); + args.usH_Disp = cpu_to_le16(mode->crtc_hdisplay); + args.usH_SyncStart = cpu_to_le16(mode->crtc_hsync_start); + args.usH_SyncWidth = + cpu_to_le16(mode->crtc_hsync_end - mode->crtc_hsync_start); + args.usV_Total = cpu_to_le16(mode->crtc_vtotal); + args.usV_Disp = cpu_to_le16(mode->crtc_vdisplay); + args.usV_SyncStart = cpu_to_le16(mode->crtc_vsync_start); + args.usV_SyncWidth = + cpu_to_le16(mode->crtc_vsync_end - mode->crtc_vsync_start); + + if (mode->flags & DRM_MODE_FLAG_NVSYNC) + misc |= ATOM_VSYNC_POLARITY; + if (mode->flags & DRM_MODE_FLAG_NHSYNC) + misc |= ATOM_HSYNC_POLARITY; + if (mode->flags & DRM_MODE_FLAG_CSYNC) + misc |= ATOM_COMPOSITESYNC; + if (mode->flags & DRM_MODE_FLAG_INTERLACE) + misc |= ATOM_INTERLACE; + if (mode->flags & DRM_MODE_FLAG_DBLSCAN) + misc |= ATOM_DOUBLE_CLOCK_MODE; + + args.susModeMiscInfo.usAccess = cpu_to_le16(misc); + args.ucCRTC = radeon_crtc->crtc_id; printk("executing set crtc timing\n"); - atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&conv_param); + atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); +} + +static void atombios_set_ss(struct drm_crtc *crtc, int enable) +{ + struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); + struct drm_device *dev = crtc->dev; + struct radeon_device *rdev = dev->dev_private; + struct drm_encoder *encoder = NULL; + struct radeon_encoder *radeon_encoder = NULL; + struct radeon_encoder_atom_dig *dig = NULL; + int index = GetIndexIntoMasterTable(COMMAND, EnableSpreadSpectrumOnPPLL); + ENABLE_SPREAD_SPECTRUM_ON_PPLL_PS_ALLOCATION args; + ENABLE_LVDS_SS_PARAMETERS legacy_args; + uint16_t percentage = 0; + uint8_t type = 0, step = 0, delay = 0, range = 0; + + list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { + if (encoder->crtc == crtc) { + radeon_encoder = to_radeon_encoder(encoder); + /* only enable spread spectrum on LVDS */ + if (radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT)) { + dig = radeon_encoder->enc_priv; + if (dig && dig->ss) { + percentage = dig->ss->percentage; + type = dig->ss->type; + step = dig->ss->step; + delay = dig->ss->delay; + range = dig->ss->range; + } else if (enable) + return; + } else if (enable) + return; + break; + } + } + + if (!radeon_encoder) + return; + + if (ASIC_IS_AVIVO(rdev)) { + memset(&args, 0, sizeof(args)); + args.usSpreadSpectrumPercentage = cpu_to_le16(percentage); + args.ucSpreadSpectrumType = type; + args.ucSpreadSpectrumStep = step; + args.ucSpreadSpectrumDelay = delay; + args.ucSpreadSpectrumRange = range; + args.ucPpll = radeon_crtc->crtc_id ? ATOM_PPLL2 : ATOM_PPLL1; + args.ucEnable = enable; + atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); + } else { + memset(&legacy_args, 0, sizeof(legacy_args)); + legacy_args.usSpreadSpectrumPercentage = cpu_to_le16(percentage); + legacy_args.ucSpreadSpectrumType = type; + legacy_args.ucSpreadSpectrumStepSize_Delay = (step & 3) << 2; + legacy_args.ucSpreadSpectrumStepSize_Delay |= (delay & 7) << 4; + legacy_args.ucEnable = enable; + atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&legacy_args); + } } void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) @@ -333,12 +417,13 @@ void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) struct drm_encoder *encoder = NULL; struct radeon_encoder *radeon_encoder = NULL; uint8_t frev, crev; - int index = GetIndexIntoMasterTable(COMMAND, SetPixelClock); + int index; SET_PIXEL_CLOCK_PS_ALLOCATION args; PIXEL_CLOCK_PARAMETERS *spc1_ptr; PIXEL_CLOCK_PARAMETERS_V2 *spc2_ptr; PIXEL_CLOCK_PARAMETERS_V3 *spc3_ptr; - uint32_t sclock = mode->clock; + uint32_t pll_clock = mode->clock; + uint32_t adjusted_clock; uint32_t ref_div = 0, fb_div = 0, frac_fb_div = 0, post_div = 0; struct radeon_pll *pll; int pll_flags = 0; @@ -346,8 +431,6 @@ void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) memset(&args, 0, sizeof(args)); if (ASIC_IS_AVIVO(rdev)) { - uint32_t ss_cntl; - if ((rdev->family == CHIP_RS600) || (rdev->family == CHIP_RS690) || (rdev->family == CHIP_RS740)) @@ -358,15 +441,6 @@ void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) pll_flags |= RADEON_PLL_PREFER_HIGH_FB_DIV; else pll_flags |= RADEON_PLL_PREFER_LOW_REF_DIV; - - /* disable spread spectrum clocking for now -- thanks Hedy Lamarr */ - if (radeon_crtc->crtc_id == 0) { - ss_cntl = RREG32(AVIVO_P1PLL_INT_SS_CNTL); - WREG32(AVIVO_P1PLL_INT_SS_CNTL, ss_cntl & ~1); - } else { - ss_cntl = RREG32(AVIVO_P2PLL_INT_SS_CNTL); - WREG32(AVIVO_P2PLL_INT_SS_CNTL, ss_cntl & ~1); - } } else { pll_flags |= RADEON_PLL_LEGACY; @@ -393,14 +467,43 @@ void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) } } + /* DCE3+ has an AdjustDisplayPll that will adjust the pixel clock + * accordingly based on the encoder/transmitter to work around + * special hw requirements. + */ + if (ASIC_IS_DCE3(rdev)) { + ADJUST_DISPLAY_PLL_PS_ALLOCATION adjust_pll_args; + + if (!encoder) + return; + + memset(&adjust_pll_args, 0, sizeof(adjust_pll_args)); + adjust_pll_args.usPixelClock = cpu_to_le16(mode->clock / 10); + adjust_pll_args.ucTransmitterID = radeon_encoder->encoder_id; + adjust_pll_args.ucEncodeMode = atombios_get_encoder_mode(encoder); + + index = GetIndexIntoMasterTable(COMMAND, AdjustDisplayPll); + atom_execute_table(rdev->mode_info.atom_context, + index, (uint32_t *)&adjust_pll_args); + adjusted_clock = le16_to_cpu(adjust_pll_args.usPixelClock) * 10; + } else { + /* DVO wants 2x pixel clock if the DVO chip is in 12 bit mode */ + if (ASIC_IS_AVIVO(rdev) && + (radeon_encoder->encoder_id == ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DVO1)) + adjusted_clock = mode->clock * 2; + else + adjusted_clock = mode->clock; + } + if (radeon_crtc->crtc_id == 0) pll = &rdev->clock.p1pll; else pll = &rdev->clock.p2pll; - radeon_compute_pll(pll, mode->clock, &sclock, &fb_div, &frac_fb_div, + radeon_compute_pll(pll, adjusted_clock, &pll_clock, &fb_div, &frac_fb_div, &ref_div, &post_div, pll_flags); + index = GetIndexIntoMasterTable(COMMAND, SetPixelClock); atom_parse_cmd_header(rdev->mode_info.atom_context, index, &frev, &crev); @@ -409,7 +512,7 @@ void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) switch (crev) { case 1: spc1_ptr = (PIXEL_CLOCK_PARAMETERS *) & args.sPCLKInput; - spc1_ptr->usPixelClock = cpu_to_le16(sclock); + spc1_ptr->usPixelClock = cpu_to_le16(mode->clock / 10); spc1_ptr->usRefDiv = cpu_to_le16(ref_div); spc1_ptr->usFbDiv = cpu_to_le16(fb_div); spc1_ptr->ucFracFbDiv = frac_fb_div; @@ -422,7 +525,7 @@ void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) case 2: spc2_ptr = (PIXEL_CLOCK_PARAMETERS_V2 *) & args.sPCLKInput; - spc2_ptr->usPixelClock = cpu_to_le16(sclock); + spc2_ptr->usPixelClock = cpu_to_le16(mode->clock / 10); spc2_ptr->usRefDiv = cpu_to_le16(ref_div); spc2_ptr->usFbDiv = cpu_to_le16(fb_div); spc2_ptr->ucFracFbDiv = frac_fb_div; @@ -437,7 +540,7 @@ void atombios_crtc_set_pll(struct drm_crtc *crtc, struct drm_display_mode *mode) return; spc3_ptr = (PIXEL_CLOCK_PARAMETERS_V3 *) & args.sPCLKInput; - spc3_ptr->usPixelClock = cpu_to_le16(sclock); + spc3_ptr->usPixelClock = cpu_to_le16(mode->clock / 10); spc3_ptr->usRefDiv = cpu_to_le16(ref_div); spc3_ptr->usFbDiv = cpu_to_le16(fb_div); spc3_ptr->ucFracFbDiv = frac_fb_div; @@ -527,6 +630,16 @@ int atombios_crtc_set_base(struct drm_crtc *crtc, int x, int y, WREG32(AVIVO_D1VGA_CONTROL, 0); else WREG32(AVIVO_D2VGA_CONTROL, 0); + + if (rdev->family >= CHIP_RV770) { + if (radeon_crtc->crtc_id) { + WREG32(R700_D2GRPH_PRIMARY_SURFACE_ADDRESS_HIGH, 0); + WREG32(R700_D2GRPH_SECONDARY_SURFACE_ADDRESS_HIGH, 0); + } else { + WREG32(R700_D1GRPH_PRIMARY_SURFACE_ADDRESS_HIGH, 0); + WREG32(R700_D1GRPH_SECONDARY_SURFACE_ADDRESS_HIGH, 0); + } + } WREG32(AVIVO_D1GRPH_PRIMARY_SURFACE_ADDRESS + radeon_crtc->crtc_offset, (u32) fb_location); WREG32(AVIVO_D1GRPH_SECONDARY_SURFACE_ADDRESS + @@ -563,6 +676,10 @@ int atombios_crtc_set_base(struct drm_crtc *crtc, int x, int y, radeon_fb = to_radeon_framebuffer(old_fb); radeon_gem_object_unpin(radeon_fb->obj); } + + /* Bytes per pixel may have changed */ + radeon_bandwidth_update(rdev); + return 0; } @@ -574,134 +691,24 @@ int atombios_crtc_mode_set(struct drm_crtc *crtc, struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); struct drm_device *dev = crtc->dev; struct radeon_device *rdev = dev->dev_private; - struct drm_encoder *encoder; - SET_CRTC_TIMING_PARAMETERS_PS_ALLOCATION crtc_timing; - int need_tv_timings = 0; - bool ret; /* TODO color tiling */ - memset(&crtc_timing, 0, sizeof(crtc_timing)); - - list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { - /* find tv std */ - if (encoder->crtc == crtc) { - struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); - - if (radeon_encoder->active_device & ATOM_DEVICE_TV_SUPPORT) { - struct radeon_encoder_atom_dac *tv_dac = radeon_encoder->enc_priv; - if (tv_dac) { - if (tv_dac->tv_std == TV_STD_NTSC || - tv_dac->tv_std == TV_STD_NTSC_J || - tv_dac->tv_std == TV_STD_PAL_M) - need_tv_timings = 1; - else - need_tv_timings = 2; - break; - } - } - } - } - - crtc_timing.ucCRTC = radeon_crtc->crtc_id; - if (need_tv_timings) { - ret = radeon_atom_get_tv_timings(rdev, need_tv_timings - 1, - &crtc_timing, &adjusted_mode->clock); - if (ret == false) - need_tv_timings = 0; - } - - if (!need_tv_timings) { - crtc_timing.usH_Total = adjusted_mode->crtc_htotal; - crtc_timing.usH_Disp = adjusted_mode->crtc_hdisplay; - crtc_timing.usH_SyncStart = adjusted_mode->crtc_hsync_start; - crtc_timing.usH_SyncWidth = - adjusted_mode->crtc_hsync_end - adjusted_mode->crtc_hsync_start; - - crtc_timing.usV_Total = adjusted_mode->crtc_vtotal; - crtc_timing.usV_Disp = adjusted_mode->crtc_vdisplay; - crtc_timing.usV_SyncStart = adjusted_mode->crtc_vsync_start; - crtc_timing.usV_SyncWidth = - adjusted_mode->crtc_vsync_end - adjusted_mode->crtc_vsync_start; - - if (adjusted_mode->flags & DRM_MODE_FLAG_NVSYNC) - crtc_timing.susModeMiscInfo.usAccess |= ATOM_VSYNC_POLARITY; - - if (adjusted_mode->flags & DRM_MODE_FLAG_NHSYNC) - crtc_timing.susModeMiscInfo.usAccess |= ATOM_HSYNC_POLARITY; - - if (adjusted_mode->flags & DRM_MODE_FLAG_CSYNC) - crtc_timing.susModeMiscInfo.usAccess |= ATOM_COMPOSITESYNC; - - if (adjusted_mode->flags & DRM_MODE_FLAG_INTERLACE) - crtc_timing.susModeMiscInfo.usAccess |= ATOM_INTERLACE; - - if (adjusted_mode->flags & DRM_MODE_FLAG_DBLSCAN) - crtc_timing.susModeMiscInfo.usAccess |= ATOM_DOUBLE_CLOCK_MODE; - } + atombios_set_ss(crtc, 0); atombios_crtc_set_pll(crtc, adjusted_mode); - atombios_crtc_set_timing(crtc, &crtc_timing); + atombios_set_ss(crtc, 1); + atombios_crtc_set_timing(crtc, adjusted_mode); if (ASIC_IS_AVIVO(rdev)) atombios_crtc_set_base(crtc, x, y, old_fb); else { - if (radeon_crtc->crtc_id == 0) { - SET_CRTC_USING_DTD_TIMING_PARAMETERS crtc_dtd_timing; - memset(&crtc_dtd_timing, 0, sizeof(crtc_dtd_timing)); - - /* setup FP shadow regs on R4xx */ - crtc_dtd_timing.ucCRTC = radeon_crtc->crtc_id; - crtc_dtd_timing.usH_Size = adjusted_mode->crtc_hdisplay; - crtc_dtd_timing.usV_Size = adjusted_mode->crtc_vdisplay; - crtc_dtd_timing.usH_Blanking_Time = - adjusted_mode->crtc_hblank_end - - adjusted_mode->crtc_hdisplay; - crtc_dtd_timing.usV_Blanking_Time = - adjusted_mode->crtc_vblank_end - - adjusted_mode->crtc_vdisplay; - crtc_dtd_timing.usH_SyncOffset = - adjusted_mode->crtc_hsync_start - - adjusted_mode->crtc_hdisplay; - crtc_dtd_timing.usV_SyncOffset = - adjusted_mode->crtc_vsync_start - - adjusted_mode->crtc_vdisplay; - crtc_dtd_timing.usH_SyncWidth = - adjusted_mode->crtc_hsync_end - - adjusted_mode->crtc_hsync_start; - crtc_dtd_timing.usV_SyncWidth = - adjusted_mode->crtc_vsync_end - - adjusted_mode->crtc_vsync_start; - /* crtc_dtd_timing.ucH_Border = adjusted_mode->crtc_hborder; */ - /* crtc_dtd_timing.ucV_Border = adjusted_mode->crtc_vborder; */ - - if (adjusted_mode->flags & DRM_MODE_FLAG_NVSYNC) - crtc_dtd_timing.susModeMiscInfo.usAccess |= - ATOM_VSYNC_POLARITY; - - if (adjusted_mode->flags & DRM_MODE_FLAG_NHSYNC) - crtc_dtd_timing.susModeMiscInfo.usAccess |= - ATOM_HSYNC_POLARITY; - - if (adjusted_mode->flags & DRM_MODE_FLAG_CSYNC) - crtc_dtd_timing.susModeMiscInfo.usAccess |= - ATOM_COMPOSITESYNC; - - if (adjusted_mode->flags & DRM_MODE_FLAG_INTERLACE) - crtc_dtd_timing.susModeMiscInfo.usAccess |= - ATOM_INTERLACE; - - if (adjusted_mode->flags & DRM_MODE_FLAG_DBLSCAN) - crtc_dtd_timing.susModeMiscInfo.usAccess |= - ATOM_DOUBLE_CLOCK_MODE; - - atombios_set_crtc_dtd_timing(crtc, &crtc_dtd_timing); - } + if (radeon_crtc->crtc_id == 0) + atombios_set_crtc_dtd_timing(crtc, adjusted_mode); radeon_crtc_set_base(crtc, x, y, old_fb); radeon_legacy_atom_set_surface(crtc); } atombios_overscan_setup(crtc, mode, adjusted_mode); atombios_scaler_setup(crtc); - radeon_bandwidth_update(rdev); return 0; } @@ -733,6 +740,7 @@ static const struct drm_crtc_helper_funcs atombios_helper_funcs = { .mode_set_base = atombios_crtc_set_base, .prepare = atombios_crtc_prepare, .commit = atombios_crtc_commit, + .load_lut = radeon_crtc_load_lut, }; void radeon_atombios_init_crtc(struct drm_device *dev, diff --git a/drivers/gpu/drm/radeon/mkregtable.c b/drivers/gpu/drm/radeon/mkregtable.c index fb211e585dea..0d79577c1576 100644 --- a/drivers/gpu/drm/radeon/mkregtable.c +++ b/drivers/gpu/drm/radeon/mkregtable.c @@ -561,7 +561,7 @@ struct table { char *gpu_prefix; }; -struct offset *offset_new(unsigned o) +static struct offset *offset_new(unsigned o) { struct offset *offset; @@ -573,12 +573,12 @@ struct offset *offset_new(unsigned o) return offset; } -void table_offset_add(struct table *t, struct offset *offset) +static void table_offset_add(struct table *t, struct offset *offset) { list_add_tail(&offset->list, &t->offsets); } -void table_init(struct table *t) +static void table_init(struct table *t) { INIT_LIST_HEAD(&t->offsets); t->offset_max = 0; @@ -586,7 +586,7 @@ void table_init(struct table *t) t->table = NULL; } -void table_print(struct table *t) +static void table_print(struct table *t) { unsigned nlloop, i, j, n, c, id; @@ -611,7 +611,7 @@ void table_print(struct table *t) printf("};\n"); } -int table_build(struct table *t) +static int table_build(struct table *t) { struct offset *offset; unsigned i, m; @@ -631,7 +631,7 @@ int table_build(struct table *t) } static char gpu_name[10]; -int parser_auth(struct table *t, const char *filename) +static int parser_auth(struct table *t, const char *filename) { FILE *file; regex_t mask_rex; diff --git a/drivers/gpu/drm/radeon/r100.c b/drivers/gpu/drm/radeon/r100.c index e6cce24de802..c9e93eabcf16 100644 --- a/drivers/gpu/drm/radeon/r100.c +++ b/drivers/gpu/drm/radeon/r100.c @@ -32,6 +32,9 @@ #include "radeon_reg.h" #include "radeon.h" #include "r100d.h" +#include "rs100d.h" +#include "rv200d.h" +#include "rv250d.h" #include <linux/firmware.h> #include <linux/platform_device.h> @@ -60,18 +63,7 @@ MODULE_FIRMWARE(FIRMWARE_R520); /* This files gather functions specifics to: * r100,rv100,rs100,rv200,rs200,r200,rv250,rs300,rv280 - * - * Some of these functions might be used by newer ASICs. */ -int r200_init(struct radeon_device *rdev); -void r100_hdp_reset(struct radeon_device *rdev); -void r100_gpu_init(struct radeon_device *rdev); -int r100_gui_wait_for_idle(struct radeon_device *rdev); -int r100_mc_wait_for_idle(struct radeon_device *rdev); -void r100_gpu_wait_for_vsync(struct radeon_device *rdev); -void r100_gpu_wait_for_vsync2(struct radeon_device *rdev); -int r100_debugfs_mc_info_init(struct radeon_device *rdev); - /* * PCI GART @@ -152,136 +144,6 @@ void r100_pci_gart_fini(struct radeon_device *rdev) radeon_gart_fini(rdev); } - -/* - * MC - */ -void r100_mc_disable_clients(struct radeon_device *rdev) -{ - uint32_t ov0_scale_cntl, crtc_ext_cntl, crtc_gen_cntl, crtc2_gen_cntl; - - /* FIXME: is this function correct for rs100,rs200,rs300 ? */ - if (r100_gui_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait GUI idle while " - "programming pipes. Bad things might happen.\n"); - } - - /* stop display and memory access */ - ov0_scale_cntl = RREG32(RADEON_OV0_SCALE_CNTL); - WREG32(RADEON_OV0_SCALE_CNTL, ov0_scale_cntl & ~RADEON_SCALER_ENABLE); - crtc_ext_cntl = RREG32(RADEON_CRTC_EXT_CNTL); - WREG32(RADEON_CRTC_EXT_CNTL, crtc_ext_cntl | RADEON_CRTC_DISPLAY_DIS); - crtc_gen_cntl = RREG32(RADEON_CRTC_GEN_CNTL); - - r100_gpu_wait_for_vsync(rdev); - - WREG32(RADEON_CRTC_GEN_CNTL, - (crtc_gen_cntl & ~(RADEON_CRTC_CUR_EN | RADEON_CRTC_ICON_EN)) | - RADEON_CRTC_DISP_REQ_EN_B | RADEON_CRTC_EXT_DISP_EN); - - if (!(rdev->flags & RADEON_SINGLE_CRTC)) { - crtc2_gen_cntl = RREG32(RADEON_CRTC2_GEN_CNTL); - - r100_gpu_wait_for_vsync2(rdev); - WREG32(RADEON_CRTC2_GEN_CNTL, - (crtc2_gen_cntl & - ~(RADEON_CRTC2_CUR_EN | RADEON_CRTC2_ICON_EN)) | - RADEON_CRTC2_DISP_REQ_EN_B); - } - - udelay(500); -} - -void r100_mc_setup(struct radeon_device *rdev) -{ - uint32_t tmp; - int r; - - r = r100_debugfs_mc_info_init(rdev); - if (r) { - DRM_ERROR("Failed to register debugfs file for R100 MC !\n"); - } - /* Write VRAM size in case we are limiting it */ - WREG32(RADEON_CONFIG_MEMSIZE, rdev->mc.real_vram_size); - /* Novell bug 204882 for RN50/M6/M7 with 8/16/32MB VRAM, - * if the aperture is 64MB but we have 32MB VRAM - * we report only 32MB VRAM but we have to set MC_FB_LOCATION - * to 64MB, otherwise the gpu accidentially dies */ - tmp = rdev->mc.vram_location + rdev->mc.mc_vram_size - 1; - tmp = REG_SET(RADEON_MC_FB_TOP, tmp >> 16); - tmp |= REG_SET(RADEON_MC_FB_START, rdev->mc.vram_location >> 16); - WREG32(RADEON_MC_FB_LOCATION, tmp); - - /* Enable bus mastering */ - tmp = RREG32(RADEON_BUS_CNTL) & ~RADEON_BUS_MASTER_DIS; - WREG32(RADEON_BUS_CNTL, tmp); - - if (rdev->flags & RADEON_IS_AGP) { - tmp = rdev->mc.gtt_location + rdev->mc.gtt_size - 1; - tmp = REG_SET(RADEON_MC_AGP_TOP, tmp >> 16); - tmp |= REG_SET(RADEON_MC_AGP_START, rdev->mc.gtt_location >> 16); - WREG32(RADEON_MC_AGP_LOCATION, tmp); - WREG32(RADEON_AGP_BASE, rdev->mc.agp_base); - } else { - WREG32(RADEON_MC_AGP_LOCATION, 0x0FFFFFFF); - WREG32(RADEON_AGP_BASE, 0); - } - - tmp = RREG32(RADEON_HOST_PATH_CNTL) & RADEON_HDP_APER_CNTL; - tmp |= (7 << 28); - WREG32(RADEON_HOST_PATH_CNTL, tmp | RADEON_HDP_SOFT_RESET | RADEON_HDP_READ_BUFFER_INVALIDATE); - (void)RREG32(RADEON_HOST_PATH_CNTL); - WREG32(RADEON_HOST_PATH_CNTL, tmp); - (void)RREG32(RADEON_HOST_PATH_CNTL); -} - -int r100_mc_init(struct radeon_device *rdev) -{ - int r; - - if (r100_debugfs_rbbm_init(rdev)) { - DRM_ERROR("Failed to register debugfs file for RBBM !\n"); - } - - r100_gpu_init(rdev); - /* Disable gart which also disable out of gart access */ - r100_pci_gart_disable(rdev); - - /* Setup GPU memory space */ - rdev->mc.gtt_location = 0xFFFFFFFFUL; - if (rdev->flags & RADEON_IS_AGP) { - r = radeon_agp_init(rdev); - if (r) { - printk(KERN_WARNING "[drm] Disabling AGP\n"); - rdev->flags &= ~RADEON_IS_AGP; - rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; - } else { - rdev->mc.gtt_location = rdev->mc.agp_base; - } - } - r = radeon_mc_setup(rdev); - if (r) { - return r; - } - - r100_mc_disable_clients(rdev); - if (r100_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait MC idle while " - "programming pipes. Bad things might happen.\n"); - } - - r100_mc_setup(rdev); - return 0; -} - -void r100_mc_fini(struct radeon_device *rdev) -{ -} - - -/* - * Interrupts - */ int r100_irq_set(struct radeon_device *rdev) { uint32_t tmp = 0; @@ -324,7 +186,7 @@ static inline uint32_t r100_irq_ack(struct radeon_device *rdev) int r100_irq_process(struct radeon_device *rdev) { - uint32_t status; + uint32_t status, msi_rearm; status = r100_irq_ack(rdev); if (!status) { @@ -347,6 +209,21 @@ int r100_irq_process(struct radeon_device *rdev) } status = r100_irq_ack(rdev); } + if (rdev->msi_enabled) { + switch (rdev->family) { + case CHIP_RS400: + case CHIP_RS480: + msi_rearm = RREG32(RADEON_AIC_CNTL) & ~RS400_MSI_REARM; + WREG32(RADEON_AIC_CNTL, msi_rearm); + WREG32(RADEON_AIC_CNTL, msi_rearm | RS400_MSI_REARM); + break; + default: + msi_rearm = RREG32(RADEON_MSI_REARM_EN) & ~RV370_MSI_REARM_EN; + WREG32(RADEON_MSI_REARM_EN, msi_rearm); + WREG32(RADEON_MSI_REARM_EN, msi_rearm | RV370_MSI_REARM_EN); + break; + } + } return IRQ_HANDLED; } @@ -358,10 +235,6 @@ u32 r100_get_vblank_counter(struct radeon_device *rdev, int crtc) return RREG32(RADEON_CRTC2_CRNT_FRAME); } - -/* - * Fence emission - */ void r100_fence_ring_emit(struct radeon_device *rdev, struct radeon_fence *fence) { @@ -377,16 +250,12 @@ void r100_fence_ring_emit(struct radeon_device *rdev, radeon_ring_write(rdev, RADEON_SW_INT_FIRE); } - -/* - * Writeback - */ int r100_wb_init(struct radeon_device *rdev) { int r; if (rdev->wb.wb_obj == NULL) { - r = radeon_object_create(rdev, NULL, 4096, + r = radeon_object_create(rdev, NULL, RADEON_GPU_PAGE_SIZE, true, RADEON_GEM_DOMAIN_GTT, false, &rdev->wb.wb_obj); @@ -504,10 +373,6 @@ int r100_copy_blit(struct radeon_device *rdev, return r; } - -/* - * CP - */ static int r100_cp_wait_for_idle(struct radeon_device *rdev) { unsigned i; @@ -612,6 +477,7 @@ static int r100_cp_init_microcode(struct radeon_device *rdev) } return err; } + static void r100_cp_load_microcode(struct radeon_device *rdev) { const __be32 *fw_data; @@ -712,19 +578,19 @@ int r100_cp_init(struct radeon_device *rdev, unsigned ring_size) indirect1_start = 16; /* cp setup */ WREG32(0x718, pre_write_timer | (pre_write_limit << 28)); - WREG32(RADEON_CP_RB_CNTL, -#ifdef __BIG_ENDIAN - RADEON_BUF_SWAP_32BIT | -#endif - REG_SET(RADEON_RB_BUFSZ, rb_bufsz) | + tmp = (REG_SET(RADEON_RB_BUFSZ, rb_bufsz) | REG_SET(RADEON_RB_BLKSZ, rb_blksz) | REG_SET(RADEON_MAX_FETCH, max_fetch) | RADEON_RB_NO_UPDATE); +#ifdef __BIG_ENDIAN + tmp |= RADEON_BUF_SWAP_32BIT; +#endif + WREG32(RADEON_CP_RB_CNTL, tmp); + /* Set ring address */ DRM_INFO("radeon: ring at 0x%016lX\n", (unsigned long)rdev->cp.gpu_addr); WREG32(RADEON_CP_RB_BASE, rdev->cp.gpu_addr); /* Force read & write ptr to 0 */ - tmp = RREG32(RADEON_CP_RB_CNTL); WREG32(RADEON_CP_RB_CNTL, tmp | RADEON_RB_RPTR_WR_ENA); WREG32(RADEON_CP_RB_RPTR_WR, 0); WREG32(RADEON_CP_RB_WPTR, 0); @@ -978,7 +844,7 @@ int r100_cs_packet_parse_vline(struct radeon_cs_parser *p) header = radeon_get_ib_value(p, h_idx); crtc_id = radeon_get_ib_value(p, h_idx + 5); - reg = header >> 2; + reg = CP_PACKET0_GET_REG(header); mutex_lock(&p->rdev->ddev->mode_config.mutex); obj = drm_mode_object_find(p->rdev->ddev, crtc_id, DRM_MODE_OBJECT_CRTC); if (!obj) { @@ -1990,7 +1856,7 @@ void r100_pll_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v) r100_pll_errata_after_data(rdev); } -int r100_init(struct radeon_device *rdev) +void r100_set_safe_registers(struct radeon_device *rdev) { if (ASIC_IS_RN50(rdev)) { rdev->config.r100.reg_safe_bm = rn50_reg_safe_bm; @@ -1999,9 +1865,8 @@ int r100_init(struct radeon_device *rdev) rdev->config.r100.reg_safe_bm = r100_reg_safe_bm; rdev->config.r100.reg_safe_bm_size = ARRAY_SIZE(r100_reg_safe_bm); } else { - return r200_init(rdev); + r200_set_safe_registers(rdev); } - return 0; } /* @@ -2299,9 +2164,11 @@ void r100_bandwidth_update(struct radeon_device *rdev) mode1 = &rdev->mode_info.crtcs[0]->base.mode; pixel_bytes1 = rdev->mode_info.crtcs[0]->base.fb->bits_per_pixel / 8; } - if (rdev->mode_info.crtcs[1]->base.enabled) { - mode2 = &rdev->mode_info.crtcs[1]->base.mode; - pixel_bytes2 = rdev->mode_info.crtcs[1]->base.fb->bits_per_pixel / 8; + if (!(rdev->flags & RADEON_SINGLE_CRTC)) { + if (rdev->mode_info.crtcs[1]->base.enabled) { + mode2 = &rdev->mode_info.crtcs[1]->base.mode; + pixel_bytes2 = rdev->mode_info.crtcs[1]->base.fb->bits_per_pixel / 8; + } } min_mem_eff.full = rfixed_const_8(0); @@ -2512,7 +2379,7 @@ void r100_bandwidth_update(struct radeon_device *rdev) /* Find the total latency for the display data. */ - disp_latency_overhead.full = rfixed_const(80); + disp_latency_overhead.full = rfixed_const(8); disp_latency_overhead.full = rfixed_div(disp_latency_overhead, sclk_ff); mc_latency_mclk.full += disp_latency_overhead.full + cur_latency_mclk.full; mc_latency_sclk.full += disp_latency_overhead.full + cur_latency_sclk.full; @@ -2710,8 +2577,11 @@ void r100_bandwidth_update(struct radeon_device *rdev) static inline void r100_cs_track_texture_print(struct r100_cs_track_texture *t) { DRM_ERROR("pitch %d\n", t->pitch); + DRM_ERROR("use_pitch %d\n", t->use_pitch); DRM_ERROR("width %d\n", t->width); + DRM_ERROR("width_11 %d\n", t->width_11); DRM_ERROR("height %d\n", t->height); + DRM_ERROR("height_11 %d\n", t->height_11); DRM_ERROR("num levels %d\n", t->num_levels); DRM_ERROR("depth %d\n", t->txdepth); DRM_ERROR("bpp %d\n", t->cpp); @@ -2771,15 +2641,17 @@ static int r100_cs_track_texture_check(struct radeon_device *rdev, else w = track->textures[u].pitch / (1 << i); } else { - w = track->textures[u].width / (1 << i); + w = track->textures[u].width; if (rdev->family >= CHIP_RV515) w |= track->textures[u].width_11; + w = w / (1 << i); if (track->textures[u].roundup_w) w = roundup_pow_of_two(w); } - h = track->textures[u].height / (1 << i); + h = track->textures[u].height; if (rdev->family >= CHIP_RV515) h |= track->textures[u].height_11; + h = h / (1 << i); if (track->textures[u].roundup_h) h = roundup_pow_of_two(h); size += w * h; @@ -3114,7 +2986,7 @@ void r100_mc_stop(struct radeon_device *rdev, struct r100_mc_save *save) WREG32(R_000740_CP_CSQ_CNTL, 0); /* Save few CRTC registers */ - save->GENMO_WT = RREG32(R_0003C0_GENMO_WT); + save->GENMO_WT = RREG8(R_0003C2_GENMO_WT); save->CRTC_EXT_CNTL = RREG32(R_000054_CRTC_EXT_CNTL); save->CRTC_GEN_CNTL = RREG32(R_000050_CRTC_GEN_CNTL); save->CUR_OFFSET = RREG32(R_000260_CUR_OFFSET); @@ -3124,7 +2996,7 @@ void r100_mc_stop(struct radeon_device *rdev, struct r100_mc_save *save) } /* Disable VGA aperture access */ - WREG32(R_0003C0_GENMO_WT, C_0003C0_VGA_RAM_EN & save->GENMO_WT); + WREG8(R_0003C2_GENMO_WT, C_0003C2_VGA_RAM_EN & save->GENMO_WT); /* Disable cursor, overlay, crtc */ WREG32(R_000260_CUR_OFFSET, save->CUR_OFFSET | S_000260_CUR_LOCK(1)); WREG32(R_000054_CRTC_EXT_CNTL, save->CRTC_EXT_CNTL | @@ -3156,10 +3028,264 @@ void r100_mc_resume(struct radeon_device *rdev, struct r100_mc_save *save) rdev->mc.vram_location); } /* Restore CRTC registers */ - WREG32(R_0003C0_GENMO_WT, save->GENMO_WT); + WREG8(R_0003C2_GENMO_WT, save->GENMO_WT); WREG32(R_000054_CRTC_EXT_CNTL, save->CRTC_EXT_CNTL); WREG32(R_000050_CRTC_GEN_CNTL, save->CRTC_GEN_CNTL); if (!(rdev->flags & RADEON_SINGLE_CRTC)) { WREG32(R_0003F8_CRTC2_GEN_CNTL, save->CRTC2_GEN_CNTL); } } + +void r100_vga_render_disable(struct radeon_device *rdev) +{ + u32 tmp; + + tmp = RREG8(R_0003C2_GENMO_WT); + WREG8(R_0003C2_GENMO_WT, C_0003C2_VGA_RAM_EN & tmp); +} + +static void r100_debugfs(struct radeon_device *rdev) +{ + int r; + + r = r100_debugfs_mc_info_init(rdev); + if (r) + dev_warn(rdev->dev, "Failed to create r100_mc debugfs file.\n"); +} + +static void r100_mc_program(struct radeon_device *rdev) +{ + struct r100_mc_save save; + + /* Stops all mc clients */ + r100_mc_stop(rdev, &save); + if (rdev->flags & RADEON_IS_AGP) { + WREG32(R_00014C_MC_AGP_LOCATION, + S_00014C_MC_AGP_START(rdev->mc.gtt_start >> 16) | + S_00014C_MC_AGP_TOP(rdev->mc.gtt_end >> 16)); + WREG32(R_000170_AGP_BASE, lower_32_bits(rdev->mc.agp_base)); + if (rdev->family > CHIP_RV200) + WREG32(R_00015C_AGP_BASE_2, + upper_32_bits(rdev->mc.agp_base) & 0xff); + } else { + WREG32(R_00014C_MC_AGP_LOCATION, 0x0FFFFFFF); + WREG32(R_000170_AGP_BASE, 0); + if (rdev->family > CHIP_RV200) + WREG32(R_00015C_AGP_BASE_2, 0); + } + /* Wait for mc idle */ + if (r100_mc_wait_for_idle(rdev)) + dev_warn(rdev->dev, "Wait for MC idle timeout.\n"); + /* Program MC, should be a 32bits limited address space */ + WREG32(R_000148_MC_FB_LOCATION, + S_000148_MC_FB_START(rdev->mc.vram_start >> 16) | + S_000148_MC_FB_TOP(rdev->mc.vram_end >> 16)); + r100_mc_resume(rdev, &save); +} + +void r100_clock_startup(struct radeon_device *rdev) +{ + u32 tmp; + + if (radeon_dynclks != -1 && radeon_dynclks) + radeon_legacy_set_clock_gating(rdev, 1); + /* We need to force on some of the block */ + tmp = RREG32_PLL(R_00000D_SCLK_CNTL); + tmp |= S_00000D_FORCE_CP(1) | S_00000D_FORCE_VIP(1); + if ((rdev->family == CHIP_RV250) || (rdev->family == CHIP_RV280)) + tmp |= S_00000D_FORCE_DISP1(1) | S_00000D_FORCE_DISP2(1); + WREG32_PLL(R_00000D_SCLK_CNTL, tmp); +} + +static int r100_startup(struct radeon_device *rdev) +{ + int r; + + r100_mc_program(rdev); + /* Resume clock */ + r100_clock_startup(rdev); + /* Initialize GPU configuration (# pipes, ...) */ + r100_gpu_init(rdev); + /* Initialize GART (initialize after TTM so we can allocate + * memory through TTM but finalize after TTM) */ + if (rdev->flags & RADEON_IS_PCI) { + r = r100_pci_gart_enable(rdev); + if (r) + return r; + } + /* Enable IRQ */ + rdev->irq.sw_int = true; + r100_irq_set(rdev); + /* 1M ring buffer */ + r = r100_cp_init(rdev, 1024 * 1024); + if (r) { + dev_err(rdev->dev, "failled initializing CP (%d).\n", r); + return r; + } + r = r100_wb_init(rdev); + if (r) + dev_err(rdev->dev, "failled initializing WB (%d).\n", r); + r = r100_ib_init(rdev); + if (r) { + dev_err(rdev->dev, "failled initializing IB (%d).\n", r); + return r; + } + return 0; +} + +int r100_resume(struct radeon_device *rdev) +{ + /* Make sur GART are not working */ + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_disable(rdev); + /* Resume clock before doing reset */ + r100_clock_startup(rdev); + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* post */ + radeon_combios_asic_init(rdev->ddev); + /* Resume clock after posting */ + r100_clock_startup(rdev); + return r100_startup(rdev); +} + +int r100_suspend(struct radeon_device *rdev) +{ + r100_cp_disable(rdev); + r100_wb_disable(rdev); + r100_irq_disable(rdev); + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_disable(rdev); + return 0; +} + +void r100_fini(struct radeon_device *rdev) +{ + r100_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + radeon_gem_fini(rdev); + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + radeon_fence_driver_fini(rdev); + radeon_object_fini(rdev); + radeon_atombios_fini(rdev); + kfree(rdev->bios); + rdev->bios = NULL; +} + +int r100_mc_init(struct radeon_device *rdev) +{ + int r; + u32 tmp; + + /* Setup GPU memory space */ + rdev->mc.vram_location = 0xFFFFFFFFUL; + rdev->mc.gtt_location = 0xFFFFFFFFUL; + if (rdev->flags & RADEON_IS_IGP) { + tmp = G_00015C_MC_FB_START(RREG32(R_00015C_NB_TOM)); + rdev->mc.vram_location = tmp << 16; + } + if (rdev->flags & RADEON_IS_AGP) { + r = radeon_agp_init(rdev); + if (r) { + printk(KERN_WARNING "[drm] Disabling AGP\n"); + rdev->flags &= ~RADEON_IS_AGP; + rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; + } else { + rdev->mc.gtt_location = rdev->mc.agp_base; + } + } + r = radeon_mc_setup(rdev); + if (r) + return r; + return 0; +} + +int r100_init(struct radeon_device *rdev) +{ + int r; + + /* Register debugfs file specific to this group of asics */ + r100_debugfs(rdev); + /* Disable VGA */ + r100_vga_render_disable(rdev); + /* Initialize scratch registers */ + radeon_scratch_init(rdev); + /* Initialize surface registers */ + radeon_surface_init(rdev); + /* TODO: disable VGA need to use VGA request */ + /* BIOS*/ + if (!radeon_get_bios(rdev)) { + if (ASIC_IS_AVIVO(rdev)) + return -EINVAL; + } + if (rdev->is_atom_bios) { + dev_err(rdev->dev, "Expecting combios for RS400/RS480 GPU\n"); + return -EINVAL; + } else { + r = radeon_combios_init(rdev); + if (r) + return r; + } + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, + "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* check if cards are posted or not */ + if (!radeon_card_posted(rdev) && rdev->bios) { + DRM_INFO("GPU not posted. posting now...\n"); + radeon_combios_asic_init(rdev->ddev); + } + /* Set asic errata */ + r100_errata(rdev); + /* Initialize clocks */ + radeon_get_clock_info(rdev->ddev); + /* Get vram informations */ + r100_vram_info(rdev); + /* Initialize memory controller (also test AGP) */ + r = r100_mc_init(rdev); + if (r) + return r; + /* Fence driver */ + r = radeon_fence_driver_init(rdev); + if (r) + return r; + r = radeon_irq_kms_init(rdev); + if (r) + return r; + /* Memory manager */ + r = radeon_object_init(rdev); + if (r) + return r; + if (rdev->flags & RADEON_IS_PCI) { + r = r100_pci_gart_init(rdev); + if (r) + return r; + } + r100_set_safe_registers(rdev); + rdev->accel_working = true; + r = r100_startup(rdev); + if (r) { + /* Somethings want wront with the accel init stop accel */ + dev_err(rdev->dev, "Disabling GPU acceleration\n"); + r100_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + rdev->accel_working = false; + } + return 0; +} diff --git a/drivers/gpu/drm/radeon/r100d.h b/drivers/gpu/drm/radeon/r100d.h index c4b257ec920e..df29a630c466 100644 --- a/drivers/gpu/drm/radeon/r100d.h +++ b/drivers/gpu/drm/radeon/r100d.h @@ -381,6 +381,24 @@ #define S_000054_VCRTC_IDX_MASTER(x) (((x) & 0x7F) << 24) #define G_000054_VCRTC_IDX_MASTER(x) (((x) >> 24) & 0x7F) #define C_000054_VCRTC_IDX_MASTER 0x80FFFFFF +#define R_000148_MC_FB_LOCATION 0x000148 +#define S_000148_MC_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_000148_MC_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_000148_MC_FB_START 0xFFFF0000 +#define S_000148_MC_FB_TOP(x) (((x) & 0xFFFF) << 16) +#define G_000148_MC_FB_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_000148_MC_FB_TOP 0x0000FFFF +#define R_00014C_MC_AGP_LOCATION 0x00014C +#define S_00014C_MC_AGP_START(x) (((x) & 0xFFFF) << 0) +#define G_00014C_MC_AGP_START(x) (((x) >> 0) & 0xFFFF) +#define C_00014C_MC_AGP_START 0xFFFF0000 +#define S_00014C_MC_AGP_TOP(x) (((x) & 0xFFFF) << 16) +#define G_00014C_MC_AGP_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_00014C_MC_AGP_TOP 0x0000FFFF +#define R_000170_AGP_BASE 0x000170 +#define S_000170_AGP_BASE_ADDR(x) (((x) & 0xFFFFFFFF) << 0) +#define G_000170_AGP_BASE_ADDR(x) (((x) >> 0) & 0xFFFFFFFF) +#define C_000170_AGP_BASE_ADDR 0x00000000 #define R_00023C_DISPLAY_BASE_ADDR 0x00023C #define S_00023C_DISPLAY_BASE_ADDR(x) (((x) & 0xFFFFFFFF) << 0) #define G_00023C_DISPLAY_BASE_ADDR(x) (((x) >> 0) & 0xFFFFFFFF) @@ -403,25 +421,25 @@ #define S_000360_CUR2_LOCK(x) (((x) & 0x1) << 31) #define G_000360_CUR2_LOCK(x) (((x) >> 31) & 0x1) #define C_000360_CUR2_LOCK 0x7FFFFFFF -#define R_0003C0_GENMO_WT 0x0003C0 -#define S_0003C0_GENMO_MONO_ADDRESS_B(x) (((x) & 0x1) << 0) -#define G_0003C0_GENMO_MONO_ADDRESS_B(x) (((x) >> 0) & 0x1) -#define C_0003C0_GENMO_MONO_ADDRESS_B 0xFFFFFFFE -#define S_0003C0_VGA_RAM_EN(x) (((x) & 0x1) << 1) -#define G_0003C0_VGA_RAM_EN(x) (((x) >> 1) & 0x1) -#define C_0003C0_VGA_RAM_EN 0xFFFFFFFD -#define S_0003C0_VGA_CKSEL(x) (((x) & 0x3) << 2) -#define G_0003C0_VGA_CKSEL(x) (((x) >> 2) & 0x3) -#define C_0003C0_VGA_CKSEL 0xFFFFFFF3 -#define S_0003C0_ODD_EVEN_MD_PGSEL(x) (((x) & 0x1) << 5) -#define G_0003C0_ODD_EVEN_MD_PGSEL(x) (((x) >> 5) & 0x1) -#define C_0003C0_ODD_EVEN_MD_PGSEL 0xFFFFFFDF -#define S_0003C0_VGA_HSYNC_POL(x) (((x) & 0x1) << 6) -#define G_0003C0_VGA_HSYNC_POL(x) (((x) >> 6) & 0x1) -#define C_0003C0_VGA_HSYNC_POL 0xFFFFFFBF -#define S_0003C0_VGA_VSYNC_POL(x) (((x) & 0x1) << 7) -#define G_0003C0_VGA_VSYNC_POL(x) (((x) >> 7) & 0x1) -#define C_0003C0_VGA_VSYNC_POL 0xFFFFFF7F +#define R_0003C2_GENMO_WT 0x0003C0 +#define S_0003C2_GENMO_MONO_ADDRESS_B(x) (((x) & 0x1) << 0) +#define G_0003C2_GENMO_MONO_ADDRESS_B(x) (((x) >> 0) & 0x1) +#define C_0003C2_GENMO_MONO_ADDRESS_B 0xFE +#define S_0003C2_VGA_RAM_EN(x) (((x) & 0x1) << 1) +#define G_0003C2_VGA_RAM_EN(x) (((x) >> 1) & 0x1) +#define C_0003C2_VGA_RAM_EN 0xFD +#define S_0003C2_VGA_CKSEL(x) (((x) & 0x3) << 2) +#define G_0003C2_VGA_CKSEL(x) (((x) >> 2) & 0x3) +#define C_0003C2_VGA_CKSEL 0xF3 +#define S_0003C2_ODD_EVEN_MD_PGSEL(x) (((x) & 0x1) << 5) +#define G_0003C2_ODD_EVEN_MD_PGSEL(x) (((x) >> 5) & 0x1) +#define C_0003C2_ODD_EVEN_MD_PGSEL 0xDF +#define S_0003C2_VGA_HSYNC_POL(x) (((x) & 0x1) << 6) +#define G_0003C2_VGA_HSYNC_POL(x) (((x) >> 6) & 0x1) +#define C_0003C2_VGA_HSYNC_POL 0xBF +#define S_0003C2_VGA_VSYNC_POL(x) (((x) & 0x1) << 7) +#define G_0003C2_VGA_VSYNC_POL(x) (((x) >> 7) & 0x1) +#define C_0003C2_VGA_VSYNC_POL 0x7F #define R_0003F8_CRTC2_GEN_CNTL 0x0003F8 #define S_0003F8_CRTC2_DBL_SCAN_EN(x) (((x) & 0x1) << 0) #define G_0003F8_CRTC2_DBL_SCAN_EN(x) (((x) >> 0) & 0x1) @@ -545,6 +563,46 @@ #define S_000774_SCRATCH_ADDR(x) (((x) & 0x7FFFFFF) << 5) #define G_000774_SCRATCH_ADDR(x) (((x) >> 5) & 0x7FFFFFF) #define C_000774_SCRATCH_ADDR 0x0000001F +#define R_0007C0_CP_STAT 0x0007C0 +#define S_0007C0_MRU_BUSY(x) (((x) & 0x1) << 0) +#define G_0007C0_MRU_BUSY(x) (((x) >> 0) & 0x1) +#define C_0007C0_MRU_BUSY 0xFFFFFFFE +#define S_0007C0_MWU_BUSY(x) (((x) & 0x1) << 1) +#define G_0007C0_MWU_BUSY(x) (((x) >> 1) & 0x1) +#define C_0007C0_MWU_BUSY 0xFFFFFFFD +#define S_0007C0_RSIU_BUSY(x) (((x) & 0x1) << 2) +#define G_0007C0_RSIU_BUSY(x) (((x) >> 2) & 0x1) +#define C_0007C0_RSIU_BUSY 0xFFFFFFFB +#define S_0007C0_RCIU_BUSY(x) (((x) & 0x1) << 3) +#define G_0007C0_RCIU_BUSY(x) (((x) >> 3) & 0x1) +#define C_0007C0_RCIU_BUSY 0xFFFFFFF7 +#define S_0007C0_CSF_PRIMARY_BUSY(x) (((x) & 0x1) << 9) +#define G_0007C0_CSF_PRIMARY_BUSY(x) (((x) >> 9) & 0x1) +#define C_0007C0_CSF_PRIMARY_BUSY 0xFFFFFDFF +#define S_0007C0_CSF_INDIRECT_BUSY(x) (((x) & 0x1) << 10) +#define G_0007C0_CSF_INDIRECT_BUSY(x) (((x) >> 10) & 0x1) +#define C_0007C0_CSF_INDIRECT_BUSY 0xFFFFFBFF +#define S_0007C0_CSQ_PRIMARY_BUSY(x) (((x) & 0x1) << 11) +#define G_0007C0_CSQ_PRIMARY_BUSY(x) (((x) >> 11) & 0x1) +#define C_0007C0_CSQ_PRIMARY_BUSY 0xFFFFF7FF +#define S_0007C0_CSQ_INDIRECT_BUSY(x) (((x) & 0x1) << 12) +#define G_0007C0_CSQ_INDIRECT_BUSY(x) (((x) >> 12) & 0x1) +#define C_0007C0_CSQ_INDIRECT_BUSY 0xFFFFEFFF +#define S_0007C0_CSI_BUSY(x) (((x) & 0x1) << 13) +#define G_0007C0_CSI_BUSY(x) (((x) >> 13) & 0x1) +#define C_0007C0_CSI_BUSY 0xFFFFDFFF +#define S_0007C0_GUIDMA_BUSY(x) (((x) & 0x1) << 28) +#define G_0007C0_GUIDMA_BUSY(x) (((x) >> 28) & 0x1) +#define C_0007C0_GUIDMA_BUSY 0xEFFFFFFF +#define S_0007C0_VIDDMA_BUSY(x) (((x) & 0x1) << 29) +#define G_0007C0_VIDDMA_BUSY(x) (((x) >> 29) & 0x1) +#define C_0007C0_VIDDMA_BUSY 0xDFFFFFFF +#define S_0007C0_CMDSTRM_BUSY(x) (((x) & 0x1) << 30) +#define G_0007C0_CMDSTRM_BUSY(x) (((x) >> 30) & 0x1) +#define C_0007C0_CMDSTRM_BUSY 0xBFFFFFFF +#define S_0007C0_CP_BUSY(x) (((x) & 0x1) << 31) +#define G_0007C0_CP_BUSY(x) (((x) >> 31) & 0x1) +#define C_0007C0_CP_BUSY 0x7FFFFFFF #define R_000E40_RBBM_STATUS 0x000E40 #define S_000E40_CMDFIFO_AVAIL(x) (((x) & 0x7F) << 0) #define G_000E40_CMDFIFO_AVAIL(x) (((x) >> 0) & 0x7F) @@ -604,4 +662,53 @@ #define G_000E40_GUI_ACTIVE(x) (((x) >> 31) & 0x1) #define C_000E40_GUI_ACTIVE 0x7FFFFFFF + +#define R_00000D_SCLK_CNTL 0x00000D +#define S_00000D_SCLK_SRC_SEL(x) (((x) & 0x7) << 0) +#define G_00000D_SCLK_SRC_SEL(x) (((x) >> 0) & 0x7) +#define C_00000D_SCLK_SRC_SEL 0xFFFFFFF8 +#define S_00000D_TCLK_SRC_SEL(x) (((x) & 0x7) << 8) +#define G_00000D_TCLK_SRC_SEL(x) (((x) >> 8) & 0x7) +#define C_00000D_TCLK_SRC_SEL 0xFFFFF8FF +#define S_00000D_FORCE_CP(x) (((x) & 0x1) << 16) +#define G_00000D_FORCE_CP(x) (((x) >> 16) & 0x1) +#define C_00000D_FORCE_CP 0xFFFEFFFF +#define S_00000D_FORCE_HDP(x) (((x) & 0x1) << 17) +#define G_00000D_FORCE_HDP(x) (((x) >> 17) & 0x1) +#define C_00000D_FORCE_HDP 0xFFFDFFFF +#define S_00000D_FORCE_DISP(x) (((x) & 0x1) << 18) +#define G_00000D_FORCE_DISP(x) (((x) >> 18) & 0x1) +#define C_00000D_FORCE_DISP 0xFFFBFFFF +#define S_00000D_FORCE_TOP(x) (((x) & 0x1) << 19) +#define G_00000D_FORCE_TOP(x) (((x) >> 19) & 0x1) +#define C_00000D_FORCE_TOP 0xFFF7FFFF +#define S_00000D_FORCE_E2(x) (((x) & 0x1) << 20) +#define G_00000D_FORCE_E2(x) (((x) >> 20) & 0x1) +#define C_00000D_FORCE_E2 0xFFEFFFFF +#define S_00000D_FORCE_SE(x) (((x) & 0x1) << 21) +#define G_00000D_FORCE_SE(x) (((x) >> 21) & 0x1) +#define C_00000D_FORCE_SE 0xFFDFFFFF +#define S_00000D_FORCE_IDCT(x) (((x) & 0x1) << 22) +#define G_00000D_FORCE_IDCT(x) (((x) >> 22) & 0x1) +#define C_00000D_FORCE_IDCT 0xFFBFFFFF +#define S_00000D_FORCE_VIP(x) (((x) & 0x1) << 23) +#define G_00000D_FORCE_VIP(x) (((x) >> 23) & 0x1) +#define C_00000D_FORCE_VIP 0xFF7FFFFF +#define S_00000D_FORCE_RE(x) (((x) & 0x1) << 24) +#define G_00000D_FORCE_RE(x) (((x) >> 24) & 0x1) +#define C_00000D_FORCE_RE 0xFEFFFFFF +#define S_00000D_FORCE_PB(x) (((x) & 0x1) << 25) +#define G_00000D_FORCE_PB(x) (((x) >> 25) & 0x1) +#define C_00000D_FORCE_PB 0xFDFFFFFF +#define S_00000D_FORCE_TAM(x) (((x) & 0x1) << 26) +#define G_00000D_FORCE_TAM(x) (((x) >> 26) & 0x1) +#define C_00000D_FORCE_TAM 0xFBFFFFFF +#define S_00000D_FORCE_TDM(x) (((x) & 0x1) << 27) +#define G_00000D_FORCE_TDM(x) (((x) >> 27) & 0x1) +#define C_00000D_FORCE_TDM 0xF7FFFFFF +#define S_00000D_FORCE_RB(x) (((x) & 0x1) << 28) +#define G_00000D_FORCE_RB(x) (((x) >> 28) & 0x1) +#define C_00000D_FORCE_RB 0xEFFFFFFF + + #endif diff --git a/drivers/gpu/drm/radeon/r200.c b/drivers/gpu/drm/radeon/r200.c index cf7fea5ff2e5..eb740fc3549f 100644 --- a/drivers/gpu/drm/radeon/r200.c +++ b/drivers/gpu/drm/radeon/r200.c @@ -447,9 +447,8 @@ int r200_packet0_check(struct radeon_cs_parser *p, return 0; } -int r200_init(struct radeon_device *rdev) +void r200_set_safe_registers(struct radeon_device *rdev) { rdev->config.r100.reg_safe_bm = r200_reg_safe_bm; rdev->config.r100.reg_safe_bm_size = ARRAY_SIZE(r200_reg_safe_bm); - return 0; } diff --git a/drivers/gpu/drm/radeon/r300.c b/drivers/gpu/drm/radeon/r300.c index 1ebea8cc8c93..2f43ee8e4048 100644 --- a/drivers/gpu/drm/radeon/r300.c +++ b/drivers/gpu/drm/radeon/r300.c @@ -33,43 +33,16 @@ #include "radeon_drm.h" #include "r100_track.h" #include "r300d.h" - +#include "rv350d.h" #include "r300_reg_safe.h" -/* r300,r350,rv350,rv370,rv380 depends on : */ -void r100_hdp_reset(struct radeon_device *rdev); -int r100_cp_reset(struct radeon_device *rdev); -int r100_rb2d_reset(struct radeon_device *rdev); -int r100_cp_init(struct radeon_device *rdev, unsigned ring_size); -int r100_pci_gart_enable(struct radeon_device *rdev); -void r100_mc_setup(struct radeon_device *rdev); -void r100_mc_disable_clients(struct radeon_device *rdev); -int r100_gui_wait_for_idle(struct radeon_device *rdev); -int r100_cs_packet_parse(struct radeon_cs_parser *p, - struct radeon_cs_packet *pkt, - unsigned idx); -int r100_cs_packet_parse_vline(struct radeon_cs_parser *p); -int r100_cs_parse_packet0(struct radeon_cs_parser *p, - struct radeon_cs_packet *pkt, - const unsigned *auth, unsigned n, - radeon_packet0_check_t check); -int r100_cs_track_check_pkt3_indx_buffer(struct radeon_cs_parser *p, - struct radeon_cs_packet *pkt, - struct radeon_object *robj); - -/* This files gather functions specifics to: - * r300,r350,rv350,rv370,rv380 - * - * Some of these functions might be used by newer ASICs. - */ -void r300_gpu_init(struct radeon_device *rdev); -int r300_mc_wait_for_idle(struct radeon_device *rdev); -int rv370_debugfs_pcie_gart_info_init(struct radeon_device *rdev); - +/* This files gather functions specifics to: r300,r350,rv350,rv370,rv380 */ /* * rv370,rv380 PCIE GART */ +static int rv370_debugfs_pcie_gart_info_init(struct radeon_device *rdev); + void rv370_pcie_gart_tlb_flush(struct radeon_device *rdev) { uint32_t tmp; @@ -140,7 +113,7 @@ int rv370_pcie_gart_enable(struct radeon_device *rdev) tmp = RADEON_PCIE_TX_GART_UNMAPPED_ACCESS_DISCARD; WREG32_PCIE(RADEON_PCIE_TX_GART_CNTL, tmp); WREG32_PCIE(RADEON_PCIE_TX_GART_START_LO, rdev->mc.gtt_location); - tmp = rdev->mc.gtt_location + rdev->mc.gtt_size - 4096; + tmp = rdev->mc.gtt_location + rdev->mc.gtt_size - RADEON_GPU_PAGE_SIZE; WREG32_PCIE(RADEON_PCIE_TX_GART_END_LO, tmp); WREG32_PCIE(RADEON_PCIE_TX_GART_START_HI, 0); WREG32_PCIE(RADEON_PCIE_TX_GART_END_HI, 0); @@ -182,59 +155,6 @@ void rv370_pcie_gart_fini(struct radeon_device *rdev) radeon_gart_fini(rdev); } -/* - * MC - */ -int r300_mc_init(struct radeon_device *rdev) -{ - int r; - - if (r100_debugfs_rbbm_init(rdev)) { - DRM_ERROR("Failed to register debugfs file for RBBM !\n"); - } - - r300_gpu_init(rdev); - r100_pci_gart_disable(rdev); - if (rdev->flags & RADEON_IS_PCIE) { - rv370_pcie_gart_disable(rdev); - } - - /* Setup GPU memory space */ - rdev->mc.vram_location = 0xFFFFFFFFUL; - rdev->mc.gtt_location = 0xFFFFFFFFUL; - if (rdev->flags & RADEON_IS_AGP) { - r = radeon_agp_init(rdev); - if (r) { - printk(KERN_WARNING "[drm] Disabling AGP\n"); - rdev->flags &= ~RADEON_IS_AGP; - rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; - } else { - rdev->mc.gtt_location = rdev->mc.agp_base; - } - } - r = radeon_mc_setup(rdev); - if (r) { - return r; - } - - /* Program GPU memory space */ - r100_mc_disable_clients(rdev); - if (r300_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait MC idle while " - "programming pipes. Bad things might happen.\n"); - } - r100_mc_setup(rdev); - return 0; -} - -void r300_mc_fini(struct radeon_device *rdev) -{ -} - - -/* - * Fence emission - */ void r300_fence_ring_emit(struct radeon_device *rdev, struct radeon_fence *fence) { @@ -260,10 +180,6 @@ void r300_fence_ring_emit(struct radeon_device *rdev, radeon_ring_write(rdev, RADEON_SW_INT_FIRE); } - -/* - * Global GPU functions - */ int r300_copy_dma(struct radeon_device *rdev, uint64_t src_offset, uint64_t dst_offset, @@ -582,11 +498,6 @@ void r300_vram_info(struct radeon_device *rdev) r100_vram_init_sizes(rdev); } - -/* - * PCIE Lanes - */ - void rv370_set_pcie_lanes(struct radeon_device *rdev, int lanes) { uint32_t link_width_cntl, mask; @@ -646,10 +557,6 @@ void rv370_set_pcie_lanes(struct radeon_device *rdev, int lanes) } - -/* - * Debugfs info - */ #if defined(CONFIG_DEBUG_FS) static int rv370_debugfs_pcie_gart_info(struct seq_file *m, void *data) { @@ -680,7 +587,7 @@ static struct drm_info_list rv370_pcie_gart_info_list[] = { }; #endif -int rv370_debugfs_pcie_gart_info_init(struct radeon_device *rdev) +static int rv370_debugfs_pcie_gart_info_init(struct radeon_device *rdev) { #if defined(CONFIG_DEBUG_FS) return radeon_debugfs_add_files(rdev, rv370_pcie_gart_info_list, 1); @@ -689,10 +596,6 @@ int rv370_debugfs_pcie_gart_info_init(struct radeon_device *rdev) #endif } - -/* - * CS functions - */ static int r300_packet0_check(struct radeon_cs_parser *p, struct radeon_cs_packet *pkt, unsigned idx, unsigned reg) @@ -1226,12 +1129,6 @@ void r300_set_reg_safe(struct radeon_device *rdev) rdev->config.r300.reg_safe_bm_size = ARRAY_SIZE(r300_reg_safe_bm); } -int r300_init(struct radeon_device *rdev) -{ - r300_set_reg_safe(rdev); - return 0; -} - void r300_mc_program(struct radeon_device *rdev) { struct r100_mc_save save; @@ -1265,3 +1162,198 @@ void r300_mc_program(struct radeon_device *rdev) S_000148_MC_FB_TOP(rdev->mc.vram_end >> 16)); r100_mc_resume(rdev, &save); } + +void r300_clock_startup(struct radeon_device *rdev) +{ + u32 tmp; + + if (radeon_dynclks != -1 && radeon_dynclks) + radeon_legacy_set_clock_gating(rdev, 1); + /* We need to force on some of the block */ + tmp = RREG32_PLL(R_00000D_SCLK_CNTL); + tmp |= S_00000D_FORCE_CP(1) | S_00000D_FORCE_VIP(1); + if ((rdev->family == CHIP_RV350) || (rdev->family == CHIP_RV380)) + tmp |= S_00000D_FORCE_VAP(1); + WREG32_PLL(R_00000D_SCLK_CNTL, tmp); +} + +static int r300_startup(struct radeon_device *rdev) +{ + int r; + + r300_mc_program(rdev); + /* Resume clock */ + r300_clock_startup(rdev); + /* Initialize GPU configuration (# pipes, ...) */ + r300_gpu_init(rdev); + /* Initialize GART (initialize after TTM so we can allocate + * memory through TTM but finalize after TTM) */ + if (rdev->flags & RADEON_IS_PCIE) { + r = rv370_pcie_gart_enable(rdev); + if (r) + return r; + } + if (rdev->flags & RADEON_IS_PCI) { + r = r100_pci_gart_enable(rdev); + if (r) + return r; + } + /* Enable IRQ */ + rdev->irq.sw_int = true; + r100_irq_set(rdev); + /* 1M ring buffer */ + r = r100_cp_init(rdev, 1024 * 1024); + if (r) { + dev_err(rdev->dev, "failled initializing CP (%d).\n", r); + return r; + } + r = r100_wb_init(rdev); + if (r) + dev_err(rdev->dev, "failled initializing WB (%d).\n", r); + r = r100_ib_init(rdev); + if (r) { + dev_err(rdev->dev, "failled initializing IB (%d).\n", r); + return r; + } + return 0; +} + +int r300_resume(struct radeon_device *rdev) +{ + /* Make sur GART are not working */ + if (rdev->flags & RADEON_IS_PCIE) + rv370_pcie_gart_disable(rdev); + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_disable(rdev); + /* Resume clock before doing reset */ + r300_clock_startup(rdev); + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* post */ + radeon_combios_asic_init(rdev->ddev); + /* Resume clock after posting */ + r300_clock_startup(rdev); + return r300_startup(rdev); +} + +int r300_suspend(struct radeon_device *rdev) +{ + r100_cp_disable(rdev); + r100_wb_disable(rdev); + r100_irq_disable(rdev); + if (rdev->flags & RADEON_IS_PCIE) + rv370_pcie_gart_disable(rdev); + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_disable(rdev); + return 0; +} + +void r300_fini(struct radeon_device *rdev) +{ + r300_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + radeon_gem_fini(rdev); + if (rdev->flags & RADEON_IS_PCIE) + rv370_pcie_gart_fini(rdev); + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + radeon_fence_driver_fini(rdev); + radeon_object_fini(rdev); + radeon_atombios_fini(rdev); + kfree(rdev->bios); + rdev->bios = NULL; +} + +int r300_init(struct radeon_device *rdev) +{ + int r; + + /* Disable VGA */ + r100_vga_render_disable(rdev); + /* Initialize scratch registers */ + radeon_scratch_init(rdev); + /* Initialize surface registers */ + radeon_surface_init(rdev); + /* TODO: disable VGA need to use VGA request */ + /* BIOS*/ + if (!radeon_get_bios(rdev)) { + if (ASIC_IS_AVIVO(rdev)) + return -EINVAL; + } + if (rdev->is_atom_bios) { + dev_err(rdev->dev, "Expecting combios for RS400/RS480 GPU\n"); + return -EINVAL; + } else { + r = radeon_combios_init(rdev); + if (r) + return r; + } + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, + "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* check if cards are posted or not */ + if (!radeon_card_posted(rdev) && rdev->bios) { + DRM_INFO("GPU not posted. posting now...\n"); + radeon_combios_asic_init(rdev->ddev); + } + /* Set asic errata */ + r300_errata(rdev); + /* Initialize clocks */ + radeon_get_clock_info(rdev->ddev); + /* Get vram informations */ + r300_vram_info(rdev); + /* Initialize memory controller (also test AGP) */ + r = r420_mc_init(rdev); + if (r) + return r; + /* Fence driver */ + r = radeon_fence_driver_init(rdev); + if (r) + return r; + r = radeon_irq_kms_init(rdev); + if (r) + return r; + /* Memory manager */ + r = radeon_object_init(rdev); + if (r) + return r; + if (rdev->flags & RADEON_IS_PCIE) { + r = rv370_pcie_gart_init(rdev); + if (r) + return r; + } + if (rdev->flags & RADEON_IS_PCI) { + r = r100_pci_gart_init(rdev); + if (r) + return r; + } + r300_set_reg_safe(rdev); + rdev->accel_working = true; + r = r300_startup(rdev); + if (r) { + /* Somethings want wront with the accel init stop accel */ + dev_err(rdev->dev, "Disabling GPU acceleration\n"); + r300_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + if (rdev->flags & RADEON_IS_PCIE) + rv370_pcie_gart_fini(rdev); + if (rdev->flags & RADEON_IS_PCI) + r100_pci_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + rdev->accel_working = false; + } + return 0; +} diff --git a/drivers/gpu/drm/radeon/r300d.h b/drivers/gpu/drm/radeon/r300d.h index d4fa3eb1074f..4c73114f0de9 100644 --- a/drivers/gpu/drm/radeon/r300d.h +++ b/drivers/gpu/drm/radeon/r300d.h @@ -96,6 +96,211 @@ #define S_000170_AGP_BASE_ADDR(x) (((x) & 0xFFFFFFFF) << 0) #define G_000170_AGP_BASE_ADDR(x) (((x) >> 0) & 0xFFFFFFFF) #define C_000170_AGP_BASE_ADDR 0x00000000 +#define R_0007C0_CP_STAT 0x0007C0 +#define S_0007C0_MRU_BUSY(x) (((x) & 0x1) << 0) +#define G_0007C0_MRU_BUSY(x) (((x) >> 0) & 0x1) +#define C_0007C0_MRU_BUSY 0xFFFFFFFE +#define S_0007C0_MWU_BUSY(x) (((x) & 0x1) << 1) +#define G_0007C0_MWU_BUSY(x) (((x) >> 1) & 0x1) +#define C_0007C0_MWU_BUSY 0xFFFFFFFD +#define S_0007C0_RSIU_BUSY(x) (((x) & 0x1) << 2) +#define G_0007C0_RSIU_BUSY(x) (((x) >> 2) & 0x1) +#define C_0007C0_RSIU_BUSY 0xFFFFFFFB +#define S_0007C0_RCIU_BUSY(x) (((x) & 0x1) << 3) +#define G_0007C0_RCIU_BUSY(x) (((x) >> 3) & 0x1) +#define C_0007C0_RCIU_BUSY 0xFFFFFFF7 +#define S_0007C0_CSF_PRIMARY_BUSY(x) (((x) & 0x1) << 9) +#define G_0007C0_CSF_PRIMARY_BUSY(x) (((x) >> 9) & 0x1) +#define C_0007C0_CSF_PRIMARY_BUSY 0xFFFFFDFF +#define S_0007C0_CSF_INDIRECT_BUSY(x) (((x) & 0x1) << 10) +#define G_0007C0_CSF_INDIRECT_BUSY(x) (((x) >> 10) & 0x1) +#define C_0007C0_CSF_INDIRECT_BUSY 0xFFFFFBFF +#define S_0007C0_CSQ_PRIMARY_BUSY(x) (((x) & 0x1) << 11) +#define G_0007C0_CSQ_PRIMARY_BUSY(x) (((x) >> 11) & 0x1) +#define C_0007C0_CSQ_PRIMARY_BUSY 0xFFFFF7FF +#define S_0007C0_CSQ_INDIRECT_BUSY(x) (((x) & 0x1) << 12) +#define G_0007C0_CSQ_INDIRECT_BUSY(x) (((x) >> 12) & 0x1) +#define C_0007C0_CSQ_INDIRECT_BUSY 0xFFFFEFFF +#define S_0007C0_CSI_BUSY(x) (((x) & 0x1) << 13) +#define G_0007C0_CSI_BUSY(x) (((x) >> 13) & 0x1) +#define C_0007C0_CSI_BUSY 0xFFFFDFFF +#define S_0007C0_CSF_INDIRECT2_BUSY(x) (((x) & 0x1) << 14) +#define G_0007C0_CSF_INDIRECT2_BUSY(x) (((x) >> 14) & 0x1) +#define C_0007C0_CSF_INDIRECT2_BUSY 0xFFFFBFFF +#define S_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) & 0x1) << 15) +#define G_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) >> 15) & 0x1) +#define C_0007C0_CSQ_INDIRECT2_BUSY 0xFFFF7FFF +#define S_0007C0_GUIDMA_BUSY(x) (((x) & 0x1) << 28) +#define G_0007C0_GUIDMA_BUSY(x) (((x) >> 28) & 0x1) +#define C_0007C0_GUIDMA_BUSY 0xEFFFFFFF +#define S_0007C0_VIDDMA_BUSY(x) (((x) & 0x1) << 29) +#define G_0007C0_VIDDMA_BUSY(x) (((x) >> 29) & 0x1) +#define C_0007C0_VIDDMA_BUSY 0xDFFFFFFF +#define S_0007C0_CMDSTRM_BUSY(x) (((x) & 0x1) << 30) +#define G_0007C0_CMDSTRM_BUSY(x) (((x) >> 30) & 0x1) +#define C_0007C0_CMDSTRM_BUSY 0xBFFFFFFF +#define S_0007C0_CP_BUSY(x) (((x) & 0x1) << 31) +#define G_0007C0_CP_BUSY(x) (((x) >> 31) & 0x1) +#define C_0007C0_CP_BUSY 0x7FFFFFFF +#define R_000E40_RBBM_STATUS 0x000E40 +#define S_000E40_CMDFIFO_AVAIL(x) (((x) & 0x7F) << 0) +#define G_000E40_CMDFIFO_AVAIL(x) (((x) >> 0) & 0x7F) +#define C_000E40_CMDFIFO_AVAIL 0xFFFFFF80 +#define S_000E40_HIRQ_ON_RBB(x) (((x) & 0x1) << 8) +#define G_000E40_HIRQ_ON_RBB(x) (((x) >> 8) & 0x1) +#define C_000E40_HIRQ_ON_RBB 0xFFFFFEFF +#define S_000E40_CPRQ_ON_RBB(x) (((x) & 0x1) << 9) +#define G_000E40_CPRQ_ON_RBB(x) (((x) >> 9) & 0x1) +#define C_000E40_CPRQ_ON_RBB 0xFFFFFDFF +#define S_000E40_CFRQ_ON_RBB(x) (((x) & 0x1) << 10) +#define G_000E40_CFRQ_ON_RBB(x) (((x) >> 10) & 0x1) +#define C_000E40_CFRQ_ON_RBB 0xFFFFFBFF +#define S_000E40_HIRQ_IN_RTBUF(x) (((x) & 0x1) << 11) +#define G_000E40_HIRQ_IN_RTBUF(x) (((x) >> 11) & 0x1) +#define C_000E40_HIRQ_IN_RTBUF 0xFFFFF7FF +#define S_000E40_CPRQ_IN_RTBUF(x) (((x) & 0x1) << 12) +#define G_000E40_CPRQ_IN_RTBUF(x) (((x) >> 12) & 0x1) +#define C_000E40_CPRQ_IN_RTBUF 0xFFFFEFFF +#define S_000E40_CFRQ_IN_RTBUF(x) (((x) & 0x1) << 13) +#define G_000E40_CFRQ_IN_RTBUF(x) (((x) >> 13) & 0x1) +#define C_000E40_CFRQ_IN_RTBUF 0xFFFFDFFF +#define S_000E40_CF_PIPE_BUSY(x) (((x) & 0x1) << 14) +#define G_000E40_CF_PIPE_BUSY(x) (((x) >> 14) & 0x1) +#define C_000E40_CF_PIPE_BUSY 0xFFFFBFFF +#define S_000E40_ENG_EV_BUSY(x) (((x) & 0x1) << 15) +#define G_000E40_ENG_EV_BUSY(x) (((x) >> 15) & 0x1) +#define C_000E40_ENG_EV_BUSY 0xFFFF7FFF +#define S_000E40_CP_CMDSTRM_BUSY(x) (((x) & 0x1) << 16) +#define G_000E40_CP_CMDSTRM_BUSY(x) (((x) >> 16) & 0x1) +#define C_000E40_CP_CMDSTRM_BUSY 0xFFFEFFFF +#define S_000E40_E2_BUSY(x) (((x) & 0x1) << 17) +#define G_000E40_E2_BUSY(x) (((x) >> 17) & 0x1) +#define C_000E40_E2_BUSY 0xFFFDFFFF +#define S_000E40_RB2D_BUSY(x) (((x) & 0x1) << 18) +#define G_000E40_RB2D_BUSY(x) (((x) >> 18) & 0x1) +#define C_000E40_RB2D_BUSY 0xFFFBFFFF +#define S_000E40_RB3D_BUSY(x) (((x) & 0x1) << 19) +#define G_000E40_RB3D_BUSY(x) (((x) >> 19) & 0x1) +#define C_000E40_RB3D_BUSY 0xFFF7FFFF +#define S_000E40_VAP_BUSY(x) (((x) & 0x1) << 20) +#define G_000E40_VAP_BUSY(x) (((x) >> 20) & 0x1) +#define C_000E40_VAP_BUSY 0xFFEFFFFF +#define S_000E40_RE_BUSY(x) (((x) & 0x1) << 21) +#define G_000E40_RE_BUSY(x) (((x) >> 21) & 0x1) +#define C_000E40_RE_BUSY 0xFFDFFFFF +#define S_000E40_TAM_BUSY(x) (((x) & 0x1) << 22) +#define G_000E40_TAM_BUSY(x) (((x) >> 22) & 0x1) +#define C_000E40_TAM_BUSY 0xFFBFFFFF +#define S_000E40_TDM_BUSY(x) (((x) & 0x1) << 23) +#define G_000E40_TDM_BUSY(x) (((x) >> 23) & 0x1) +#define C_000E40_TDM_BUSY 0xFF7FFFFF +#define S_000E40_PB_BUSY(x) (((x) & 0x1) << 24) +#define G_000E40_PB_BUSY(x) (((x) >> 24) & 0x1) +#define C_000E40_PB_BUSY 0xFEFFFFFF +#define S_000E40_TIM_BUSY(x) (((x) & 0x1) << 25) +#define G_000E40_TIM_BUSY(x) (((x) >> 25) & 0x1) +#define C_000E40_TIM_BUSY 0xFDFFFFFF +#define S_000E40_GA_BUSY(x) (((x) & 0x1) << 26) +#define G_000E40_GA_BUSY(x) (((x) >> 26) & 0x1) +#define C_000E40_GA_BUSY 0xFBFFFFFF +#define S_000E40_CBA2D_BUSY(x) (((x) & 0x1) << 27) +#define G_000E40_CBA2D_BUSY(x) (((x) >> 27) & 0x1) +#define C_000E40_CBA2D_BUSY 0xF7FFFFFF +#define S_000E40_GUI_ACTIVE(x) (((x) & 0x1) << 31) +#define G_000E40_GUI_ACTIVE(x) (((x) >> 31) & 0x1) +#define C_000E40_GUI_ACTIVE 0x7FFFFFFF +#define R_00000D_SCLK_CNTL 0x00000D +#define S_00000D_SCLK_SRC_SEL(x) (((x) & 0x7) << 0) +#define G_00000D_SCLK_SRC_SEL(x) (((x) >> 0) & 0x7) +#define C_00000D_SCLK_SRC_SEL 0xFFFFFFF8 +#define S_00000D_CP_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 3) +#define G_00000D_CP_MAX_DYN_STOP_LAT(x) (((x) >> 3) & 0x1) +#define C_00000D_CP_MAX_DYN_STOP_LAT 0xFFFFFFF7 +#define S_00000D_HDP_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 4) +#define G_00000D_HDP_MAX_DYN_STOP_LAT(x) (((x) >> 4) & 0x1) +#define C_00000D_HDP_MAX_DYN_STOP_LAT 0xFFFFFFEF +#define S_00000D_TV_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 5) +#define G_00000D_TV_MAX_DYN_STOP_LAT(x) (((x) >> 5) & 0x1) +#define C_00000D_TV_MAX_DYN_STOP_LAT 0xFFFFFFDF +#define S_00000D_E2_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 6) +#define G_00000D_E2_MAX_DYN_STOP_LAT(x) (((x) >> 6) & 0x1) +#define C_00000D_E2_MAX_DYN_STOP_LAT 0xFFFFFFBF +#define S_00000D_SE_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 7) +#define G_00000D_SE_MAX_DYN_STOP_LAT(x) (((x) >> 7) & 0x1) +#define C_00000D_SE_MAX_DYN_STOP_LAT 0xFFFFFF7F +#define S_00000D_IDCT_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 8) +#define G_00000D_IDCT_MAX_DYN_STOP_LAT(x) (((x) >> 8) & 0x1) +#define C_00000D_IDCT_MAX_DYN_STOP_LAT 0xFFFFFEFF +#define S_00000D_VIP_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 9) +#define G_00000D_VIP_MAX_DYN_STOP_LAT(x) (((x) >> 9) & 0x1) +#define C_00000D_VIP_MAX_DYN_STOP_LAT 0xFFFFFDFF +#define S_00000D_RE_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 10) +#define G_00000D_RE_MAX_DYN_STOP_LAT(x) (((x) >> 10) & 0x1) +#define C_00000D_RE_MAX_DYN_STOP_LAT 0xFFFFFBFF +#define S_00000D_PB_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 11) +#define G_00000D_PB_MAX_DYN_STOP_LAT(x) (((x) >> 11) & 0x1) +#define C_00000D_PB_MAX_DYN_STOP_LAT 0xFFFFF7FF +#define S_00000D_TAM_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 12) +#define G_00000D_TAM_MAX_DYN_STOP_LAT(x) (((x) >> 12) & 0x1) +#define C_00000D_TAM_MAX_DYN_STOP_LAT 0xFFFFEFFF +#define S_00000D_TDM_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 13) +#define G_00000D_TDM_MAX_DYN_STOP_LAT(x) (((x) >> 13) & 0x1) +#define C_00000D_TDM_MAX_DYN_STOP_LAT 0xFFFFDFFF +#define S_00000D_RB_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 14) +#define G_00000D_RB_MAX_DYN_STOP_LAT(x) (((x) >> 14) & 0x1) +#define C_00000D_RB_MAX_DYN_STOP_LAT 0xFFFFBFFF +#define S_00000D_FORCE_DISP2(x) (((x) & 0x1) << 15) +#define G_00000D_FORCE_DISP2(x) (((x) >> 15) & 0x1) +#define C_00000D_FORCE_DISP2 0xFFFF7FFF +#define S_00000D_FORCE_CP(x) (((x) & 0x1) << 16) +#define G_00000D_FORCE_CP(x) (((x) >> 16) & 0x1) +#define C_00000D_FORCE_CP 0xFFFEFFFF +#define S_00000D_FORCE_HDP(x) (((x) & 0x1) << 17) +#define G_00000D_FORCE_HDP(x) (((x) >> 17) & 0x1) +#define C_00000D_FORCE_HDP 0xFFFDFFFF +#define S_00000D_FORCE_DISP1(x) (((x) & 0x1) << 18) +#define G_00000D_FORCE_DISP1(x) (((x) >> 18) & 0x1) +#define C_00000D_FORCE_DISP1 0xFFFBFFFF +#define S_00000D_FORCE_TOP(x) (((x) & 0x1) << 19) +#define G_00000D_FORCE_TOP(x) (((x) >> 19) & 0x1) +#define C_00000D_FORCE_TOP 0xFFF7FFFF +#define S_00000D_FORCE_E2(x) (((x) & 0x1) << 20) +#define G_00000D_FORCE_E2(x) (((x) >> 20) & 0x1) +#define C_00000D_FORCE_E2 0xFFEFFFFF +#define S_00000D_FORCE_SE(x) (((x) & 0x1) << 21) +#define G_00000D_FORCE_SE(x) (((x) >> 21) & 0x1) +#define C_00000D_FORCE_SE 0xFFDFFFFF +#define S_00000D_FORCE_IDCT(x) (((x) & 0x1) << 22) +#define G_00000D_FORCE_IDCT(x) (((x) >> 22) & 0x1) +#define C_00000D_FORCE_IDCT 0xFFBFFFFF +#define S_00000D_FORCE_VIP(x) (((x) & 0x1) << 23) +#define G_00000D_FORCE_VIP(x) (((x) >> 23) & 0x1) +#define C_00000D_FORCE_VIP 0xFF7FFFFF +#define S_00000D_FORCE_RE(x) (((x) & 0x1) << 24) +#define G_00000D_FORCE_RE(x) (((x) >> 24) & 0x1) +#define C_00000D_FORCE_RE 0xFEFFFFFF +#define S_00000D_FORCE_PB(x) (((x) & 0x1) << 25) +#define G_00000D_FORCE_PB(x) (((x) >> 25) & 0x1) +#define C_00000D_FORCE_PB 0xFDFFFFFF +#define S_00000D_FORCE_TAM(x) (((x) & 0x1) << 26) +#define G_00000D_FORCE_TAM(x) (((x) >> 26) & 0x1) +#define C_00000D_FORCE_TAM 0xFBFFFFFF +#define S_00000D_FORCE_TDM(x) (((x) & 0x1) << 27) +#define G_00000D_FORCE_TDM(x) (((x) >> 27) & 0x1) +#define C_00000D_FORCE_TDM 0xF7FFFFFF +#define S_00000D_FORCE_RB(x) (((x) & 0x1) << 28) +#define G_00000D_FORCE_RB(x) (((x) >> 28) & 0x1) +#define C_00000D_FORCE_RB 0xEFFFFFFF +#define S_00000D_FORCE_TV_SCLK(x) (((x) & 0x1) << 29) +#define G_00000D_FORCE_TV_SCLK(x) (((x) >> 29) & 0x1) +#define C_00000D_FORCE_TV_SCLK 0xDFFFFFFF +#define S_00000D_FORCE_SUBPIC(x) (((x) & 0x1) << 30) +#define G_00000D_FORCE_SUBPIC(x) (((x) >> 30) & 0x1) +#define C_00000D_FORCE_SUBPIC 0xBFFFFFFF +#define S_00000D_FORCE_OV0(x) (((x) & 0x1) << 31) +#define G_00000D_FORCE_OV0(x) (((x) >> 31) & 0x1) +#define C_00000D_FORCE_OV0 0x7FFFFFFF + #endif diff --git a/drivers/gpu/drm/radeon/r420.c b/drivers/gpu/drm/radeon/r420.c index 49a2fdc57d27..1cefdbcc0850 100644 --- a/drivers/gpu/drm/radeon/r420.c +++ b/drivers/gpu/drm/radeon/r420.c @@ -155,6 +155,9 @@ static void r420_debugfs(struct radeon_device *rdev) static void r420_clock_resume(struct radeon_device *rdev) { u32 sclk_cntl; + + if (radeon_dynclks != -1 && radeon_dynclks) + radeon_atom_set_clock_gating(rdev, 1); sclk_cntl = RREG32_PLL(R_00000D_SCLK_CNTL); sclk_cntl |= S_00000D_FORCE_CP(1) | S_00000D_FORCE_VIP(1); if (rdev->family == CHIP_R420) @@ -167,6 +170,8 @@ static int r420_startup(struct radeon_device *rdev) int r; r300_mc_program(rdev); + /* Resume clock */ + r420_clock_resume(rdev); /* Initialize GART (initialize after TTM so we can allocate * memory through TTM but finalize after TTM) */ if (rdev->flags & RADEON_IS_PCIE) { @@ -267,7 +272,6 @@ int r420_init(struct radeon_device *rdev) { int r; - rdev->new_init_path = true; /* Initialize scratch registers */ radeon_scratch_init(rdev); /* Initialize surface registers */ @@ -307,6 +311,8 @@ int r420_init(struct radeon_device *rdev) } /* Initialize clocks */ radeon_get_clock_info(rdev->ddev); + /* Initialize power management */ + radeon_pm_init(rdev); /* Get vram informations */ r300_vram_info(rdev); /* Initialize memory controller (also test AGP) */ diff --git a/drivers/gpu/drm/radeon/r420d.h b/drivers/gpu/drm/radeon/r420d.h index a48a7db1e2aa..fc78d31a0b4a 100644 --- a/drivers/gpu/drm/radeon/r420d.h +++ b/drivers/gpu/drm/radeon/r420d.h @@ -212,9 +212,9 @@ #define S_00000D_FORCE_E2(x) (((x) & 0x1) << 20) #define G_00000D_FORCE_E2(x) (((x) >> 20) & 0x1) #define C_00000D_FORCE_E2 0xFFEFFFFF -#define S_00000D_FORCE_SE(x) (((x) & 0x1) << 21) -#define G_00000D_FORCE_SE(x) (((x) >> 21) & 0x1) -#define C_00000D_FORCE_SE 0xFFDFFFFF +#define S_00000D_FORCE_VAP(x) (((x) & 0x1) << 21) +#define G_00000D_FORCE_VAP(x) (((x) >> 21) & 0x1) +#define C_00000D_FORCE_VAP 0xFFDFFFFF #define S_00000D_FORCE_IDCT(x) (((x) & 0x1) << 22) #define G_00000D_FORCE_IDCT(x) (((x) >> 22) & 0x1) #define C_00000D_FORCE_IDCT 0xFFBFFFFF @@ -224,24 +224,24 @@ #define S_00000D_FORCE_RE(x) (((x) & 0x1) << 24) #define G_00000D_FORCE_RE(x) (((x) >> 24) & 0x1) #define C_00000D_FORCE_RE 0xFEFFFFFF -#define S_00000D_FORCE_PB(x) (((x) & 0x1) << 25) -#define G_00000D_FORCE_PB(x) (((x) >> 25) & 0x1) -#define C_00000D_FORCE_PB 0xFDFFFFFF +#define S_00000D_FORCE_SR(x) (((x) & 0x1) << 25) +#define G_00000D_FORCE_SR(x) (((x) >> 25) & 0x1) +#define C_00000D_FORCE_SR 0xFDFFFFFF #define S_00000D_FORCE_PX(x) (((x) & 0x1) << 26) #define G_00000D_FORCE_PX(x) (((x) >> 26) & 0x1) #define C_00000D_FORCE_PX 0xFBFFFFFF #define S_00000D_FORCE_TX(x) (((x) & 0x1) << 27) #define G_00000D_FORCE_TX(x) (((x) >> 27) & 0x1) #define C_00000D_FORCE_TX 0xF7FFFFFF -#define S_00000D_FORCE_RB(x) (((x) & 0x1) << 28) -#define G_00000D_FORCE_RB(x) (((x) >> 28) & 0x1) -#define C_00000D_FORCE_RB 0xEFFFFFFF +#define S_00000D_FORCE_US(x) (((x) & 0x1) << 28) +#define G_00000D_FORCE_US(x) (((x) >> 28) & 0x1) +#define C_00000D_FORCE_US 0xEFFFFFFF #define S_00000D_FORCE_TV_SCLK(x) (((x) & 0x1) << 29) #define G_00000D_FORCE_TV_SCLK(x) (((x) >> 29) & 0x1) #define C_00000D_FORCE_TV_SCLK 0xDFFFFFFF -#define S_00000D_FORCE_SUBPIC(x) (((x) & 0x1) << 30) -#define G_00000D_FORCE_SUBPIC(x) (((x) >> 30) & 0x1) -#define C_00000D_FORCE_SUBPIC 0xBFFFFFFF +#define S_00000D_FORCE_SU(x) (((x) & 0x1) << 30) +#define G_00000D_FORCE_SU(x) (((x) >> 30) & 0x1) +#define C_00000D_FORCE_SU 0xBFFFFFFF #define S_00000D_FORCE_OV0(x) (((x) & 0x1) << 31) #define G_00000D_FORCE_OV0(x) (((x) >> 31) & 0x1) #define C_00000D_FORCE_OV0 0x7FFFFFFF diff --git a/drivers/gpu/drm/radeon/r500_reg.h b/drivers/gpu/drm/radeon/r500_reg.h index 868add6e166d..7baa73955563 100644 --- a/drivers/gpu/drm/radeon/r500_reg.h +++ b/drivers/gpu/drm/radeon/r500_reg.h @@ -384,9 +384,16 @@ # define AVIVO_D1GRPH_TILED (1 << 20) # define AVIVO_D1GRPH_MACRO_ADDRESS_MODE (1 << 21) +/* The R7xx *_HIGH surface regs are backwards; the D1 regs are in the D2 + * block and vice versa. This applies to GRPH, CUR, etc. + */ #define AVIVO_D1GRPH_LUT_SEL 0x6108 #define AVIVO_D1GRPH_PRIMARY_SURFACE_ADDRESS 0x6110 +#define R700_D1GRPH_PRIMARY_SURFACE_ADDRESS_HIGH 0x6914 +#define R700_D2GRPH_PRIMARY_SURFACE_ADDRESS_HIGH 0x6114 #define AVIVO_D1GRPH_SECONDARY_SURFACE_ADDRESS 0x6118 +#define R700_D1GRPH_SECONDARY_SURFACE_ADDRESS_HIGH 0x691c +#define R700_D2GRPH_SECONDARY_SURFACE_ADDRESS_HIGH 0x611c #define AVIVO_D1GRPH_PITCH 0x6120 #define AVIVO_D1GRPH_SURFACE_OFFSET_X 0x6124 #define AVIVO_D1GRPH_SURFACE_OFFSET_Y 0x6128 @@ -404,6 +411,8 @@ # define AVIVO_D1CURSOR_MODE_MASK (3 << 8) # define AVIVO_D1CURSOR_MODE_24BPP 2 #define AVIVO_D1CUR_SURFACE_ADDRESS 0x6408 +#define R700_D1CUR_SURFACE_ADDRESS_HIGH 0x6c0c +#define R700_D2CUR_SURFACE_ADDRESS_HIGH 0x640c #define AVIVO_D1CUR_SIZE 0x6410 #define AVIVO_D1CUR_POSITION 0x6414 #define AVIVO_D1CUR_HOT_SPOT 0x6418 diff --git a/drivers/gpu/drm/radeon/r520.c b/drivers/gpu/drm/radeon/r520.c index 0bf13fccdaf2..f7435185c0a6 100644 --- a/drivers/gpu/drm/radeon/r520.c +++ b/drivers/gpu/drm/radeon/r520.c @@ -186,7 +186,7 @@ static int r520_startup(struct radeon_device *rdev) } /* Enable IRQ */ rdev->irq.sw_int = true; - r100_irq_set(rdev); + rs600_irq_set(rdev); /* 1M ring buffer */ r = r100_cp_init(rdev, 1024 * 1024); if (r) { @@ -228,7 +228,6 @@ int r520_init(struct radeon_device *rdev) { int r; - rdev->new_init_path = true; /* Initialize scratch registers */ radeon_scratch_init(rdev); /* Initialize surface registers */ @@ -261,6 +260,8 @@ int r520_init(struct radeon_device *rdev) } /* Initialize clocks */ radeon_get_clock_info(rdev->ddev); + /* Initialize power management */ + radeon_pm_init(rdev); /* Get vram informations */ r520_vram_info(rdev); /* Initialize memory controller (also test AGP) */ diff --git a/drivers/gpu/drm/radeon/r600.c b/drivers/gpu/drm/radeon/r600.c index 2e4e60edbff4..278f646bc18e 100644 --- a/drivers/gpu/drm/radeon/r600.c +++ b/drivers/gpu/drm/radeon/r600.c @@ -65,16 +65,11 @@ MODULE_FIRMWARE("radeon/RV710_me.bin"); int r600_debugfs_mc_info_init(struct radeon_device *rdev); -/* This files gather functions specifics to: - * r600,rv610,rv630,rv620,rv635,rv670 - * - * Some of these functions might be used by newer ASICs. - */ +/* r600,rv610,rv630,rv620,rv635,rv670 */ int r600_mc_wait_for_idle(struct radeon_device *rdev); void r600_gpu_init(struct radeon_device *rdev); void r600_fini(struct radeon_device *rdev); - /* * R600 PCIE GART */ @@ -168,7 +163,7 @@ int r600_pcie_gart_enable(struct radeon_device *rdev) WREG32(MC_VM_L1_TLB_MCB_RD_SEM_CNTL, tmp | ENABLE_SEMAPHORE_MODE); WREG32(MC_VM_L1_TLB_MCB_WR_SEM_CNTL, tmp | ENABLE_SEMAPHORE_MODE); WREG32(VM_CONTEXT0_PAGE_TABLE_START_ADDR, rdev->mc.gtt_start >> 12); - WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR, (rdev->mc.gtt_end - 1) >> 12); + WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR, rdev->mc.gtt_end >> 12); WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR, rdev->gart.table_addr >> 12); WREG32(VM_CONTEXT0_CNTL, ENABLE_CONTEXT | PAGE_TABLE_DEPTH(0) | RANGE_PROTECTION_FAULT_ENABLE_DEFAULT); @@ -225,6 +220,40 @@ void r600_pcie_gart_fini(struct radeon_device *rdev) radeon_gart_fini(rdev); } +void r600_agp_enable(struct radeon_device *rdev) +{ + u32 tmp; + int i; + + /* Setup L2 cache */ + WREG32(VM_L2_CNTL, ENABLE_L2_CACHE | ENABLE_L2_FRAGMENT_PROCESSING | + ENABLE_L2_PTE_CACHE_LRU_UPDATE_BY_WRITE | + EFFECTIVE_L2_QUEUE_SIZE(7)); + WREG32(VM_L2_CNTL2, 0); + WREG32(VM_L2_CNTL3, BANK_SELECT_0(0) | BANK_SELECT_1(1)); + /* Setup TLB control */ + tmp = ENABLE_L1_TLB | ENABLE_L1_FRAGMENT_PROCESSING | + SYSTEM_ACCESS_MODE_NOT_IN_SYS | + EFFECTIVE_L1_TLB_SIZE(5) | EFFECTIVE_L1_QUEUE_SIZE(5) | + ENABLE_WAIT_L2_QUERY; + WREG32(MC_VM_L1_TLB_MCB_RD_SYS_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCB_WR_SYS_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCB_RD_HDP_CNTL, tmp | ENABLE_L1_STRICT_ORDERING); + WREG32(MC_VM_L1_TLB_MCB_WR_HDP_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCD_RD_A_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCD_WR_A_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCD_RD_B_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCD_WR_B_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCB_RD_GFX_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCB_WR_GFX_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCB_RD_PDMA_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCB_WR_PDMA_CNTL, tmp); + WREG32(MC_VM_L1_TLB_MCB_RD_SEM_CNTL, tmp | ENABLE_SEMAPHORE_MODE); + WREG32(MC_VM_L1_TLB_MCB_WR_SEM_CNTL, tmp | ENABLE_SEMAPHORE_MODE); + for (i = 0; i < 7; i++) + WREG32(VM_CONTEXT0_CNTL + (i * 4), 0); +} + int r600_mc_wait_for_idle(struct radeon_device *rdev) { unsigned i; @@ -240,14 +269,9 @@ int r600_mc_wait_for_idle(struct radeon_device *rdev) return -1; } -static void r600_mc_resume(struct radeon_device *rdev) +static void r600_mc_program(struct radeon_device *rdev) { - u32 d1vga_control, d2vga_control; - u32 vga_render_control, vga_hdp_control; - u32 d1crtc_control, d2crtc_control; - u32 new_d1grph_primary, new_d1grph_secondary; - u32 new_d2grph_primary, new_d2grph_secondary; - u64 old_vram_start; + struct rv515_mc_save save; u32 tmp; int i, j; @@ -261,85 +285,51 @@ static void r600_mc_resume(struct radeon_device *rdev) } WREG32(HDP_REG_COHERENCY_FLUSH_CNTL, 0); - d1vga_control = RREG32(D1VGA_CONTROL); - d2vga_control = RREG32(D2VGA_CONTROL); - vga_render_control = RREG32(VGA_RENDER_CONTROL); - vga_hdp_control = RREG32(VGA_HDP_CONTROL); - d1crtc_control = RREG32(D1CRTC_CONTROL); - d2crtc_control = RREG32(D2CRTC_CONTROL); - old_vram_start = (u64)(RREG32(MC_VM_FB_LOCATION) & 0xFFFF) << 24; - new_d1grph_primary = RREG32(D1GRPH_PRIMARY_SURFACE_ADDRESS); - new_d1grph_secondary = RREG32(D1GRPH_SECONDARY_SURFACE_ADDRESS); - new_d1grph_primary += rdev->mc.vram_start - old_vram_start; - new_d1grph_secondary += rdev->mc.vram_start - old_vram_start; - new_d2grph_primary = RREG32(D2GRPH_PRIMARY_SURFACE_ADDRESS); - new_d2grph_secondary = RREG32(D2GRPH_SECONDARY_SURFACE_ADDRESS); - new_d2grph_primary += rdev->mc.vram_start - old_vram_start; - new_d2grph_secondary += rdev->mc.vram_start - old_vram_start; - - /* Stop all video */ - WREG32(D1VGA_CONTROL, 0); - WREG32(D2VGA_CONTROL, 0); - WREG32(VGA_RENDER_CONTROL, 0); - WREG32(D1CRTC_UPDATE_LOCK, 1); - WREG32(D2CRTC_UPDATE_LOCK, 1); - WREG32(D1CRTC_CONTROL, 0); - WREG32(D2CRTC_CONTROL, 0); - WREG32(D1CRTC_UPDATE_LOCK, 0); - WREG32(D2CRTC_UPDATE_LOCK, 0); - - mdelay(1); + rv515_mc_stop(rdev, &save); if (r600_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "[drm] MC not idle !\n"); + dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); } - - /* Lockout access through VGA aperture*/ + /* Lockout access through VGA aperture (doesn't exist before R600) */ WREG32(VGA_HDP_CONTROL, VGA_MEMORY_DISABLE); - /* Update configuration */ - WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, rdev->mc.vram_start >> 12); - WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, (rdev->mc.vram_end - 1) >> 12); + if (rdev->flags & RADEON_IS_AGP) { + if (rdev->mc.vram_start < rdev->mc.gtt_start) { + /* VRAM before AGP */ + WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, + rdev->mc.vram_start >> 12); + WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, + rdev->mc.gtt_end >> 12); + } else { + /* VRAM after AGP */ + WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, + rdev->mc.gtt_start >> 12); + WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, + rdev->mc.vram_end >> 12); + } + } else { + WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, rdev->mc.vram_start >> 12); + WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, rdev->mc.vram_end >> 12); + } WREG32(MC_VM_SYSTEM_APERTURE_DEFAULT_ADDR, 0); - tmp = (((rdev->mc.vram_end - 1) >> 24) & 0xFFFF) << 16; + tmp = ((rdev->mc.vram_end >> 24) & 0xFFFF) << 16; tmp |= ((rdev->mc.vram_start >> 24) & 0xFFFF); WREG32(MC_VM_FB_LOCATION, tmp); WREG32(HDP_NONSURFACE_BASE, (rdev->mc.vram_start >> 8)); WREG32(HDP_NONSURFACE_INFO, (2 << 7)); - WREG32(HDP_NONSURFACE_SIZE, (rdev->mc.mc_vram_size - 1) | 0x3FF); + WREG32(HDP_NONSURFACE_SIZE, rdev->mc.mc_vram_size | 0x3FF); if (rdev->flags & RADEON_IS_AGP) { - WREG32(MC_VM_AGP_TOP, (rdev->mc.gtt_end - 1) >> 16); - WREG32(MC_VM_AGP_BOT, rdev->mc.gtt_start >> 16); + WREG32(MC_VM_AGP_TOP, rdev->mc.gtt_end >> 22); + WREG32(MC_VM_AGP_BOT, rdev->mc.gtt_start >> 22); WREG32(MC_VM_AGP_BASE, rdev->mc.agp_base >> 22); } else { WREG32(MC_VM_AGP_BASE, 0); WREG32(MC_VM_AGP_TOP, 0x0FFFFFFF); WREG32(MC_VM_AGP_BOT, 0x0FFFFFFF); } - WREG32(D1GRPH_PRIMARY_SURFACE_ADDRESS, new_d1grph_primary); - WREG32(D1GRPH_SECONDARY_SURFACE_ADDRESS, new_d1grph_secondary); - WREG32(D2GRPH_PRIMARY_SURFACE_ADDRESS, new_d2grph_primary); - WREG32(D2GRPH_SECONDARY_SURFACE_ADDRESS, new_d2grph_secondary); - WREG32(VGA_MEMORY_BASE_ADDRESS, rdev->mc.vram_start); - - /* Unlock host access */ - WREG32(VGA_HDP_CONTROL, vga_hdp_control); - - mdelay(1); if (r600_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "[drm] MC not idle !\n"); + dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); } - - /* Restore video state */ - WREG32(D1CRTC_UPDATE_LOCK, 1); - WREG32(D2CRTC_UPDATE_LOCK, 1); - WREG32(D1CRTC_CONTROL, d1crtc_control); - WREG32(D2CRTC_CONTROL, d2crtc_control); - WREG32(D1CRTC_UPDATE_LOCK, 0); - WREG32(D2CRTC_UPDATE_LOCK, 0); - WREG32(D1VGA_CONTROL, d1vga_control); - WREG32(D2VGA_CONTROL, d2vga_control); - WREG32(VGA_RENDER_CONTROL, vga_render_control); - + rv515_mc_resume(rdev, &save); /* we need to own VRAM, so turn off the VGA renderer here * to stop it overwriting our objects */ rv515_vga_render_disable(rdev); @@ -349,11 +339,10 @@ int r600_mc_init(struct radeon_device *rdev) { fixed20_12 a; u32 tmp; - int chansize; + int chansize, numchan; int r; /* Get VRAM informations */ - rdev->mc.vram_width = 128; rdev->mc.vram_is_ddr = true; tmp = RREG32(RAMCFG); if (tmp & CHANSIZE_OVERRIDE) { @@ -363,17 +352,23 @@ int r600_mc_init(struct radeon_device *rdev) } else { chansize = 32; } - if (rdev->family == CHIP_R600) { - rdev->mc.vram_width = 8 * chansize; - } else if (rdev->family == CHIP_RV670) { - rdev->mc.vram_width = 4 * chansize; - } else if ((rdev->family == CHIP_RV610) || - (rdev->family == CHIP_RV620)) { - rdev->mc.vram_width = chansize; - } else if ((rdev->family == CHIP_RV630) || - (rdev->family == CHIP_RV635)) { - rdev->mc.vram_width = 2 * chansize; + tmp = RREG32(CHMAP); + switch ((tmp & NOOFCHAN_MASK) >> NOOFCHAN_SHIFT) { + case 0: + default: + numchan = 1; + break; + case 1: + numchan = 2; + break; + case 2: + numchan = 4; + break; + case 3: + numchan = 8; + break; } + rdev->mc.vram_width = numchan * chansize; /* Could aper size report 0 ? */ rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0); rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0); @@ -414,40 +409,34 @@ int r600_mc_init(struct radeon_device *rdev) rdev->mc.gtt_location = rdev->mc.mc_vram_size; } } else { - if (rdev->family == CHIP_RS780 || rdev->family == CHIP_RS880) { - rdev->mc.vram_location = (RREG32(MC_VM_FB_LOCATION) & - 0xFFFF) << 24; - rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; - tmp = rdev->mc.vram_location + rdev->mc.mc_vram_size; - if ((0xFFFFFFFFUL - tmp) >= rdev->mc.gtt_size) { - /* Enough place after vram */ - rdev->mc.gtt_location = tmp; - } else if (rdev->mc.vram_location >= rdev->mc.gtt_size) { - /* Enough place before vram */ + rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; + rdev->mc.vram_location = (RREG32(MC_VM_FB_LOCATION) & + 0xFFFF) << 24; + tmp = rdev->mc.vram_location + rdev->mc.mc_vram_size; + if ((0xFFFFFFFFUL - tmp) >= rdev->mc.gtt_size) { + /* Enough place after vram */ + rdev->mc.gtt_location = tmp; + } else if (rdev->mc.vram_location >= rdev->mc.gtt_size) { + /* Enough place before vram */ + rdev->mc.gtt_location = 0; + } else { + /* Not enough place after or before shrink + * gart size + */ + if (rdev->mc.vram_location > (0xFFFFFFFFUL - tmp)) { rdev->mc.gtt_location = 0; + rdev->mc.gtt_size = rdev->mc.vram_location; } else { - /* Not enough place after or before shrink - * gart size - */ - if (rdev->mc.vram_location > (0xFFFFFFFFUL - tmp)) { - rdev->mc.gtt_location = 0; - rdev->mc.gtt_size = rdev->mc.vram_location; - } else { - rdev->mc.gtt_location = tmp; - rdev->mc.gtt_size = 0xFFFFFFFFUL - tmp; - } + rdev->mc.gtt_location = tmp; + rdev->mc.gtt_size = 0xFFFFFFFFUL - tmp; } - rdev->mc.gtt_location = rdev->mc.mc_vram_size; - } else { - rdev->mc.vram_location = 0x00000000UL; - rdev->mc.gtt_location = rdev->mc.mc_vram_size; - rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; } + rdev->mc.gtt_location = rdev->mc.mc_vram_size; } rdev->mc.vram_start = rdev->mc.vram_location; - rdev->mc.vram_end = rdev->mc.vram_location + rdev->mc.mc_vram_size; + rdev->mc.vram_end = rdev->mc.vram_location + rdev->mc.mc_vram_size - 1; rdev->mc.gtt_start = rdev->mc.gtt_location; - rdev->mc.gtt_end = rdev->mc.gtt_location + rdev->mc.gtt_size; + rdev->mc.gtt_end = rdev->mc.gtt_location + rdev->mc.gtt_size - 1; /* FIXME: we should enforce default clock in case GPU is not in * default setup */ @@ -463,6 +452,7 @@ int r600_mc_init(struct radeon_device *rdev) */ int r600_gpu_soft_reset(struct radeon_device *rdev) { + struct rv515_mc_save save; u32 grbm_busy_mask = S_008010_VC_BUSY(1) | S_008010_VGT_BUSY_NO_DMA(1) | S_008010_VGT_BUSY(1) | S_008010_TA03_BUSY(1) | S_008010_TC_BUSY(1) | S_008010_SX_BUSY(1) | @@ -480,13 +470,25 @@ int r600_gpu_soft_reset(struct radeon_device *rdev) S_008014_CB0_BUSY(1) | S_008014_CB1_BUSY(1) | S_008014_CB2_BUSY(1) | S_008014_CB3_BUSY(1); u32 srbm_reset = 0; + u32 tmp; + dev_info(rdev->dev, "GPU softreset \n"); + dev_info(rdev->dev, " R_008010_GRBM_STATUS=0x%08X\n", + RREG32(R_008010_GRBM_STATUS)); + dev_info(rdev->dev, " R_008014_GRBM_STATUS2=0x%08X\n", + RREG32(R_008014_GRBM_STATUS2)); + dev_info(rdev->dev, " R_000E50_SRBM_STATUS=0x%08X\n", + RREG32(R_000E50_SRBM_STATUS)); + rv515_mc_stop(rdev, &save); + if (r600_mc_wait_for_idle(rdev)) { + dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); + } /* Disable CP parsing/prefetching */ WREG32(R_0086D8_CP_ME_CNTL, S_0086D8_CP_ME_HALT(0xff)); /* Check if any of the rendering block is busy and reset it */ if ((RREG32(R_008010_GRBM_STATUS) & grbm_busy_mask) || (RREG32(R_008014_GRBM_STATUS2) & grbm2_busy_mask)) { - WREG32(R_008020_GRBM_SOFT_RESET, S_008020_SOFT_RESET_CR(1) | + tmp = S_008020_SOFT_RESET_CR(1) | S_008020_SOFT_RESET_DB(1) | S_008020_SOFT_RESET_CB(1) | S_008020_SOFT_RESET_PA(1) | @@ -498,14 +500,18 @@ int r600_gpu_soft_reset(struct radeon_device *rdev) S_008020_SOFT_RESET_TC(1) | S_008020_SOFT_RESET_TA(1) | S_008020_SOFT_RESET_VC(1) | - S_008020_SOFT_RESET_VGT(1)); + S_008020_SOFT_RESET_VGT(1); + dev_info(rdev->dev, " R_008020_GRBM_SOFT_RESET=0x%08X\n", tmp); + WREG32(R_008020_GRBM_SOFT_RESET, tmp); (void)RREG32(R_008020_GRBM_SOFT_RESET); udelay(50); WREG32(R_008020_GRBM_SOFT_RESET, 0); (void)RREG32(R_008020_GRBM_SOFT_RESET); } /* Reset CP (we always reset CP) */ - WREG32(R_008020_GRBM_SOFT_RESET, S_008020_SOFT_RESET_CP(1)); + tmp = S_008020_SOFT_RESET_CP(1); + dev_info(rdev->dev, "R_008020_GRBM_SOFT_RESET=0x%08X\n", tmp); + WREG32(R_008020_GRBM_SOFT_RESET, tmp); (void)RREG32(R_008020_GRBM_SOFT_RESET); udelay(50); WREG32(R_008020_GRBM_SOFT_RESET, 0); @@ -533,6 +539,14 @@ int r600_gpu_soft_reset(struct radeon_device *rdev) srbm_reset |= S_000E60_SOFT_RESET_RLC(1); if (G_000E50_SEM_BUSY(RREG32(R_000E50_SRBM_STATUS))) srbm_reset |= S_000E60_SOFT_RESET_SEM(1); + if (G_000E50_BIF_BUSY(RREG32(R_000E50_SRBM_STATUS))) + srbm_reset |= S_000E60_SOFT_RESET_BIF(1); + dev_info(rdev->dev, " R_000E60_SRBM_SOFT_RESET=0x%08X\n", srbm_reset); + WREG32(R_000E60_SRBM_SOFT_RESET, srbm_reset); + (void)RREG32(R_000E60_SRBM_SOFT_RESET); + udelay(50); + WREG32(R_000E60_SRBM_SOFT_RESET, 0); + (void)RREG32(R_000E60_SRBM_SOFT_RESET); WREG32(R_000E60_SRBM_SOFT_RESET, srbm_reset); (void)RREG32(R_000E60_SRBM_SOFT_RESET); udelay(50); @@ -540,6 +554,17 @@ int r600_gpu_soft_reset(struct radeon_device *rdev) (void)RREG32(R_000E60_SRBM_SOFT_RESET); /* Wait a little for things to settle down */ udelay(50); + dev_info(rdev->dev, " R_008010_GRBM_STATUS=0x%08X\n", + RREG32(R_008010_GRBM_STATUS)); + dev_info(rdev->dev, " R_008014_GRBM_STATUS2=0x%08X\n", + RREG32(R_008014_GRBM_STATUS2)); + dev_info(rdev->dev, " R_000E50_SRBM_STATUS=0x%08X\n", + RREG32(R_000E50_SRBM_STATUS)); + /* After reset we need to reinit the asic as GPU often endup in an + * incoherent state. + */ + atom_asic_init(rdev->mode_info.atom_context); + rv515_mc_resume(rdev, &save); return 0; } @@ -833,7 +858,8 @@ void r600_gpu_init(struct radeon_device *rdev) ((rdev->family) == CHIP_RV630) || ((rdev->family) == CHIP_RV610) || ((rdev->family) == CHIP_RV620) || - ((rdev->family) == CHIP_RS780)) { + ((rdev->family) == CHIP_RS780) || + ((rdev->family) == CHIP_RS880)) { WREG32(DB_DEBUG, PREZ_MUST_WAIT_FOR_POSTZ_DONE); } else { WREG32(DB_DEBUG, 0); @@ -850,7 +876,8 @@ void r600_gpu_init(struct radeon_device *rdev) tmp = RREG32(SQ_MS_FIFO_SIZES); if (((rdev->family) == CHIP_RV610) || ((rdev->family) == CHIP_RV620) || - ((rdev->family) == CHIP_RS780)) { + ((rdev->family) == CHIP_RS780) || + ((rdev->family) == CHIP_RS880)) { tmp = (CACHE_FIFO_SIZE(0xa) | FETCH_FIFO_HIWATER(0xa) | DONE_FIFO_HIWATER(0xe0) | @@ -893,7 +920,8 @@ void r600_gpu_init(struct radeon_device *rdev) NUM_ES_STACK_ENTRIES(0)); } else if (((rdev->family) == CHIP_RV610) || ((rdev->family) == CHIP_RV620) || - ((rdev->family) == CHIP_RS780)) { + ((rdev->family) == CHIP_RS780) || + ((rdev->family) == CHIP_RS880)) { /* no vertex cache */ sq_config &= ~VC_ENABLE; @@ -950,7 +978,8 @@ void r600_gpu_init(struct radeon_device *rdev) if (((rdev->family) == CHIP_RV610) || ((rdev->family) == CHIP_RV620) || - ((rdev->family) == CHIP_RS780)) { + ((rdev->family) == CHIP_RS780) || + ((rdev->family) == CHIP_RS880)) { WREG32(VGT_CACHE_INVALIDATION, CACHE_INVALIDATION(TC_ONLY)); } else { WREG32(VGT_CACHE_INVALIDATION, CACHE_INVALIDATION(VC_AND_TC)); @@ -976,8 +1005,9 @@ void r600_gpu_init(struct radeon_device *rdev) tmp = rdev->config.r600.max_pipes * 16; switch (rdev->family) { case CHIP_RV610: - case CHIP_RS780: case CHIP_RV620: + case CHIP_RS780: + case CHIP_RS880: tmp += 32; break; case CHIP_RV670: @@ -1018,8 +1048,9 @@ void r600_gpu_init(struct radeon_device *rdev) switch (rdev->family) { case CHIP_RV610: - case CHIP_RS780: case CHIP_RV620: + case CHIP_RS780: + case CHIP_RS880: tmp = TC_L2_SIZE(8); break; case CHIP_RV630: @@ -1241,19 +1272,17 @@ int r600_cp_resume(struct radeon_device *rdev) /* Set ring buffer size */ rb_bufsz = drm_order(rdev->cp.ring_size / 8); + tmp = RB_NO_UPDATE | (drm_order(RADEON_GPU_PAGE_SIZE/8) << 8) | rb_bufsz; #ifdef __BIG_ENDIAN - WREG32(CP_RB_CNTL, BUF_SWAP_32BIT | RB_NO_UPDATE | - (drm_order(4096/8) << 8) | rb_bufsz); -#else - WREG32(CP_RB_CNTL, RB_NO_UPDATE | (drm_order(4096/8) << 8) | rb_bufsz); + tmp |= BUF_SWAP_32BIT; #endif + WREG32(CP_RB_CNTL, tmp); WREG32(CP_SEM_WAIT_TIMER, 0x4); /* Set the write pointer delay */ WREG32(CP_RB_WPTR_DELAY, 0); /* Initialize the ring buffer's read and write pointers */ - tmp = RREG32(CP_RB_CNTL); WREG32(CP_RB_CNTL, tmp | RB_RPTR_WR_ENA); WREG32(CP_RB_RPTR_WR, 0); WREG32(CP_RB_WPTR, 0); @@ -1350,32 +1379,47 @@ int r600_ring_test(struct radeon_device *rdev) return r; } -/* - * Writeback - */ -int r600_wb_init(struct radeon_device *rdev) +void r600_wb_disable(struct radeon_device *rdev) +{ + WREG32(SCRATCH_UMSK, 0); + if (rdev->wb.wb_obj) { + radeon_object_kunmap(rdev->wb.wb_obj); + radeon_object_unpin(rdev->wb.wb_obj); + } +} + +void r600_wb_fini(struct radeon_device *rdev) +{ + r600_wb_disable(rdev); + if (rdev->wb.wb_obj) { + radeon_object_unref(&rdev->wb.wb_obj); + rdev->wb.wb = NULL; + rdev->wb.wb_obj = NULL; + } +} + +int r600_wb_enable(struct radeon_device *rdev) { int r; if (rdev->wb.wb_obj == NULL) { - r = radeon_object_create(rdev, NULL, 4096, - true, - RADEON_GEM_DOMAIN_GTT, - false, &rdev->wb.wb_obj); + r = radeon_object_create(rdev, NULL, RADEON_GPU_PAGE_SIZE, true, + RADEON_GEM_DOMAIN_GTT, false, &rdev->wb.wb_obj); if (r) { - DRM_ERROR("radeon: failed to create WB buffer (%d).\n", r); + dev_warn(rdev->dev, "failed to create WB buffer (%d).\n", r); return r; } - r = radeon_object_pin(rdev->wb.wb_obj, - RADEON_GEM_DOMAIN_GTT, - &rdev->wb.gpu_addr); + r = radeon_object_pin(rdev->wb.wb_obj, RADEON_GEM_DOMAIN_GTT, + &rdev->wb.gpu_addr); if (r) { - DRM_ERROR("radeon: failed to pin WB buffer (%d).\n", r); + dev_warn(rdev->dev, "failed to pin WB buffer (%d).\n", r); + r600_wb_fini(rdev); return r; } r = radeon_object_kmap(rdev->wb.wb_obj, (void **)&rdev->wb.wb); if (r) { - DRM_ERROR("radeon: failed to map WB buffer (%d).\n", r); + dev_warn(rdev->dev, "failed to map WB buffer (%d).\n", r); + r600_wb_fini(rdev); return r; } } @@ -1386,21 +1430,6 @@ int r600_wb_init(struct radeon_device *rdev) return 0; } -void r600_wb_fini(struct radeon_device *rdev) -{ - if (rdev->wb.wb_obj) { - radeon_object_kunmap(rdev->wb.wb_obj); - radeon_object_unpin(rdev->wb.wb_obj); - radeon_object_unref(&rdev->wb.wb_obj); - rdev->wb.wb = NULL; - rdev->wb.wb_obj = NULL; - } -} - - -/* - * CS - */ void r600_fence_ring_emit(struct radeon_device *rdev, struct radeon_fence *fence) { @@ -1424,8 +1453,8 @@ int r600_copy_blit(struct radeon_device *rdev, uint64_t src_offset, uint64_t dst_offset, unsigned num_pages, struct radeon_fence *fence) { - r600_blit_prepare_copy(rdev, num_pages * 4096); - r600_kms_blit_copy(rdev, src_offset, dst_offset, num_pages * 4096); + r600_blit_prepare_copy(rdev, num_pages * RADEON_GPU_PAGE_SIZE); + r600_kms_blit_copy(rdev, src_offset, dst_offset, num_pages * RADEON_GPU_PAGE_SIZE); r600_blit_done_copy(rdev, fence); return 0; } @@ -1477,11 +1506,14 @@ int r600_startup(struct radeon_device *rdev) { int r; - r600_gpu_reset(rdev); - r600_mc_resume(rdev); - r = r600_pcie_gart_enable(rdev); - if (r) - return r; + r600_mc_program(rdev); + if (rdev->flags & RADEON_IS_AGP) { + r600_agp_enable(rdev); + } else { + r = r600_pcie_gart_enable(rdev); + if (r) + return r; + } r600_gpu_init(rdev); r = radeon_object_pin(rdev->r600_blit.shader_obj, RADEON_GEM_DOMAIN_VRAM, @@ -1500,9 +1532,8 @@ int r600_startup(struct radeon_device *rdev) r = r600_cp_resume(rdev); if (r) return r; - r = r600_wb_init(rdev); - if (r) - return r; + /* write back buffer are not vital so don't worry about failure */ + r600_wb_enable(rdev); return 0; } @@ -1524,15 +1555,12 @@ int r600_resume(struct radeon_device *rdev) { int r; - if (radeon_gpu_reset(rdev)) { - /* FIXME: what do we want to do here ? */ - } + /* Do not reset GPU before posting, on r600 hw unlike on r500 hw, + * posting will perform necessary task to bring back GPU into good + * shape. + */ /* post card */ - if (rdev->is_atom_bios) { - atom_asic_init(rdev->mode_info.atom_context); - } else { - radeon_combios_asic_init(rdev->ddev); - } + atom_asic_init(rdev->mode_info.atom_context); /* Initialize clocks */ r = radeon_clocks_init(rdev); if (r) { @@ -1545,7 +1573,7 @@ int r600_resume(struct radeon_device *rdev) return r; } - r = radeon_ib_test(rdev); + r = r600_ib_test(rdev); if (r) { DRM_ERROR("radeon: failled testing IB (%d).\n", r); return r; @@ -1553,13 +1581,12 @@ int r600_resume(struct radeon_device *rdev) return r; } - int r600_suspend(struct radeon_device *rdev) { /* FIXME: we should wait for ring to be empty */ r600_cp_stop(rdev); rdev->cp.ready = false; - + r600_wb_disable(rdev); r600_pcie_gart_disable(rdev); /* unpin shaders bo */ radeon_object_unpin(rdev->r600_blit.shader_obj); @@ -1576,7 +1603,6 @@ int r600_init(struct radeon_device *rdev) { int r; - rdev->new_init_path = true; r = radeon_dummy_page_init(rdev); if (r) return r; @@ -1593,8 +1619,10 @@ int r600_init(struct radeon_device *rdev) return -EINVAL; } /* Must be an ATOMBIOS */ - if (!rdev->is_atom_bios) + if (!rdev->is_atom_bios) { + dev_err(rdev->dev, "Expecting atombios for R600 GPU\n"); return -EINVAL; + } r = radeon_atombios_init(rdev); if (r) return r; @@ -1607,24 +1635,20 @@ int r600_init(struct radeon_device *rdev) r600_scratch_init(rdev); /* Initialize surface registers */ radeon_surface_init(rdev); + /* Initialize clocks */ radeon_get_clock_info(rdev->ddev); r = radeon_clocks_init(rdev); if (r) return r; + /* Initialize power management */ + radeon_pm_init(rdev); /* Fence driver */ r = radeon_fence_driver_init(rdev); if (r) return r; r = r600_mc_init(rdev); - if (r) { - if (rdev->flags & RADEON_IS_AGP) { - /* Retry with disabling AGP */ - r600_fini(rdev); - rdev->flags &= ~RADEON_IS_AGP; - return r600_init(rdev); - } + if (r) return r; - } /* Memory manager */ r = radeon_object_init(rdev); if (r) @@ -1653,12 +1677,10 @@ int r600_init(struct radeon_device *rdev) r = r600_startup(rdev); if (r) { - if (rdev->flags & RADEON_IS_AGP) { - /* Retry with disabling AGP */ - r600_fini(rdev); - rdev->flags &= ~RADEON_IS_AGP; - return r600_init(rdev); - } + r600_suspend(rdev); + r600_wb_fini(rdev); + radeon_ring_fini(rdev); + r600_pcie_gart_fini(rdev); rdev->accel_working = false; } if (rdev->accel_working) { @@ -1667,7 +1689,7 @@ int r600_init(struct radeon_device *rdev) DRM_ERROR("radeon: failled initializing IB pool (%d).\n", r); rdev->accel_working = false; } - r = radeon_ib_test(rdev); + r = r600_ib_test(rdev); if (r) { DRM_ERROR("radeon: failled testing IB (%d).\n", r); rdev->accel_working = false; @@ -1683,19 +1705,15 @@ void r600_fini(struct radeon_device *rdev) r600_blit_fini(rdev); radeon_ring_fini(rdev); + r600_wb_fini(rdev); r600_pcie_gart_fini(rdev); radeon_gem_fini(rdev); radeon_fence_driver_fini(rdev); radeon_clocks_fini(rdev); -#if __OS_HAS_AGP if (rdev->flags & RADEON_IS_AGP) radeon_agp_fini(rdev); -#endif radeon_object_fini(rdev); - if (rdev->is_atom_bios) - radeon_atombios_fini(rdev); - else - radeon_combios_fini(rdev); + radeon_atombios_fini(rdev); kfree(rdev->bios); rdev->bios = NULL; radeon_dummy_page_fini(rdev); diff --git a/drivers/gpu/drm/radeon/r600_blit.c b/drivers/gpu/drm/radeon/r600_blit.c index d988eece0187..5ea432347589 100644 --- a/drivers/gpu/drm/radeon/r600_blit.c +++ b/drivers/gpu/drm/radeon/r600_blit.c @@ -774,11 +774,10 @@ r600_blit_swap(struct drm_device *dev, { drm_radeon_private_t *dev_priv = dev->dev_private; int cb_format, tex_format; + int sx2, sy2, dx2, dy2; u64 vb_addr; u32 *vb; - vb = r600_nomm_get_vb_ptr(dev); - if ((dev_priv->blit_vb->used + 48) > dev_priv->blit_vb->total) { r600_nomm_put_vb(dev); @@ -787,19 +786,13 @@ r600_blit_swap(struct drm_device *dev, return; set_shaders(dev); - vb = r600_nomm_get_vb_ptr(dev); } + vb = r600_nomm_get_vb_ptr(dev); - if (cpp == 4) { - cb_format = COLOR_8_8_8_8; - tex_format = FMT_8_8_8_8; - } else if (cpp == 2) { - cb_format = COLOR_5_6_5; - tex_format = FMT_5_6_5; - } else { - cb_format = COLOR_8; - tex_format = FMT_8; - } + sx2 = sx + w; + sy2 = sy + h; + dx2 = dx + w; + dy2 = dy + h; vb[0] = i2f(dx); vb[1] = i2f(dy); @@ -807,31 +800,46 @@ r600_blit_swap(struct drm_device *dev, vb[3] = i2f(sy); vb[4] = i2f(dx); - vb[5] = i2f(dy + h); + vb[5] = i2f(dy2); vb[6] = i2f(sx); - vb[7] = i2f(sy + h); + vb[7] = i2f(sy2); + + vb[8] = i2f(dx2); + vb[9] = i2f(dy2); + vb[10] = i2f(sx2); + vb[11] = i2f(sy2); - vb[8] = i2f(dx + w); - vb[9] = i2f(dy + h); - vb[10] = i2f(sx + w); - vb[11] = i2f(sy + h); + switch(cpp) { + case 4: + cb_format = COLOR_8_8_8_8; + tex_format = FMT_8_8_8_8; + break; + case 2: + cb_format = COLOR_5_6_5; + tex_format = FMT_5_6_5; + break; + default: + cb_format = COLOR_8; + tex_format = FMT_8; + break; + } /* src */ set_tex_resource(dev_priv, tex_format, src_pitch / cpp, - sy + h, src_pitch / cpp, + sy2, src_pitch / cpp, src_gpu_addr); cp_set_surface_sync(dev_priv, - R600_TC_ACTION_ENA, (src_pitch * (sy + h)), src_gpu_addr); + R600_TC_ACTION_ENA, src_pitch * sy2, src_gpu_addr); /* dst */ set_render_target(dev_priv, cb_format, - dst_pitch / cpp, dy + h, + dst_pitch / cpp, dy2, dst_gpu_addr); /* scissors */ - set_scissors(dev_priv, dx, dy, dx + w, dy + h); + set_scissors(dev_priv, dx, dy, dx2, dy2); /* Vertex buffer setup */ vb_addr = dev_priv->gart_buffers_offset + @@ -844,7 +852,7 @@ r600_blit_swap(struct drm_device *dev, cp_set_surface_sync(dev_priv, R600_CB_ACTION_ENA | R600_CB0_DEST_BASE_ENA, - dst_pitch * (dy + h), dst_gpu_addr); + dst_pitch * dy2, dst_gpu_addr); dev_priv->blit_vb->used += 12 * 4; } diff --git a/drivers/gpu/drm/radeon/r600_blit_kms.c b/drivers/gpu/drm/radeon/r600_blit_kms.c index acae33e2ad51..dbf716e1fbf3 100644 --- a/drivers/gpu/drm/radeon/r600_blit_kms.c +++ b/drivers/gpu/drm/radeon/r600_blit_kms.c @@ -368,7 +368,7 @@ set_default_state(struct radeon_device *rdev) if ((rdev->family == CHIP_RV610) || (rdev->family == CHIP_RV620) || (rdev->family == CHIP_RS780) || - (rdev->family == CHIP_RS780) || + (rdev->family == CHIP_RS880) || (rdev->family == CHIP_RV710)) sq_config = 0; else diff --git a/drivers/gpu/drm/radeon/r600_cs.c b/drivers/gpu/drm/radeon/r600_cs.c index d28970db6a2d..0d820764f340 100644 --- a/drivers/gpu/drm/radeon/r600_cs.c +++ b/drivers/gpu/drm/radeon/r600_cs.c @@ -252,7 +252,7 @@ static int r600_cs_packet_parse_vline(struct radeon_cs_parser *p) header = radeon_get_ib_value(p, h_idx); crtc_id = radeon_get_ib_value(p, h_idx + 2 + 7 + 1); - reg = header >> 2; + reg = CP_PACKET0_GET_REG(header); mutex_lock(&p->rdev->ddev->mode_config.mutex); obj = drm_mode_object_find(p->rdev->ddev, crtc_id, DRM_MODE_OBJECT_CRTC); if (!obj) { @@ -466,6 +466,23 @@ static int r600_packet3_check(struct radeon_cs_parser *p, for (i = 0; i < pkt->count; i++) { reg = start_reg + (4 * i); switch (reg) { + case SQ_ESGS_RING_BASE: + case SQ_GSVS_RING_BASE: + case SQ_ESTMP_RING_BASE: + case SQ_GSTMP_RING_BASE: + case SQ_VSTMP_RING_BASE: + case SQ_PSTMP_RING_BASE: + case SQ_FBUF_RING_BASE: + case SQ_REDUC_RING_BASE: + case SX_MEMORY_EXPORT_BASE: + r = r600_cs_packet_next_reloc(p, &reloc); + if (r) { + DRM_ERROR("bad SET_CONFIG_REG " + "0x%04X\n", reg); + return -EINVAL; + } + ib[idx+1+i] += (u32)((reloc->lobj.gpu_offset >> 8) & 0xffffffff); + break; case CP_COHER_BASE: /* use PACKET3_SURFACE_SYNC */ return -EINVAL; @@ -487,6 +504,7 @@ static int r600_packet3_check(struct radeon_cs_parser *p, reg = start_reg + (4 * i); switch (reg) { case DB_DEPTH_BASE: + case DB_HTILE_DATA_BASE: case CB_COLOR0_BASE: case CB_COLOR1_BASE: case CB_COLOR2_BASE: diff --git a/drivers/gpu/drm/radeon/r600d.h b/drivers/gpu/drm/radeon/r600d.h index 4a9028a85c9b..27ab428b149b 100644 --- a/drivers/gpu/drm/radeon/r600d.h +++ b/drivers/gpu/drm/radeon/r600d.h @@ -119,6 +119,7 @@ #define DB_DEBUG 0x9830 #define PREZ_MUST_WAIT_FOR_POSTZ_DONE (1 << 31) #define DB_DEPTH_BASE 0x2800C +#define DB_HTILE_DATA_BASE 0x28014 #define DB_WATERMARKS 0x9838 #define DEPTH_FREE(x) ((x) << 0) #define DEPTH_FLUSH(x) ((x) << 5) @@ -171,6 +172,14 @@ #define SQ_STACK_RESOURCE_MGMT_2 0x8c14 # define NUM_GS_STACK_ENTRIES(x) ((x) << 0) # define NUM_ES_STACK_ENTRIES(x) ((x) << 16) +#define SQ_ESGS_RING_BASE 0x8c40 +#define SQ_GSVS_RING_BASE 0x8c48 +#define SQ_ESTMP_RING_BASE 0x8c50 +#define SQ_GSTMP_RING_BASE 0x8c58 +#define SQ_VSTMP_RING_BASE 0x8c60 +#define SQ_PSTMP_RING_BASE 0x8c68 +#define SQ_FBUF_RING_BASE 0x8c70 +#define SQ_REDUC_RING_BASE 0x8c78 #define GRBM_CNTL 0x8000 # define GRBM_READ_TIMEOUT(x) ((x) << 0) @@ -271,6 +280,10 @@ #define PCIE_PORT_INDEX 0x0038 #define PCIE_PORT_DATA 0x003C +#define CHMAP 0x2004 +#define NOOFCHAN_SHIFT 12 +#define NOOFCHAN_MASK 0x00003000 + #define RAMCFG 0x2408 #define NOOFBANK_SHIFT 0 #define NOOFBANK_MASK 0x00000001 @@ -352,6 +365,7 @@ #define SX_MISC 0x28350 +#define SX_MEMORY_EXPORT_BASE 0x9010 #define SX_DEBUG_1 0x9054 #define SMX_EVENT_RELEASE (1 << 0) #define ENABLE_NEW_SMX_ADDRESS (1 << 16) @@ -643,6 +657,7 @@ #define G_000E50_MCDW_BUSY(x) (((x) >> 13) & 1) #define G_000E50_SEM_BUSY(x) (((x) >> 14) & 1) #define G_000E50_RLC_BUSY(x) (((x) >> 15) & 1) +#define G_000E50_BIF_BUSY(x) (((x) >> 29) & 1) #define R_000E60_SRBM_SOFT_RESET 0x0E60 #define S_000E60_SOFT_RESET_BIF(x) (((x) & 1) << 1) #define S_000E60_SOFT_RESET_CG(x) (((x) & 1) << 2) diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h index 950b346e343f..757f5cd37744 100644 --- a/drivers/gpu/drm/radeon/radeon.h +++ b/drivers/gpu/drm/radeon/radeon.h @@ -139,6 +139,10 @@ struct radeon_clock { uint32_t default_sclk; }; +/* + * Power management + */ +int radeon_pm_init(struct radeon_device *rdev); /* * Fences. @@ -276,6 +280,8 @@ union radeon_gart_table { struct radeon_gart_table_vram vram; }; +#define RADEON_GPU_PAGE_SIZE 4096 + struct radeon_gart { dma_addr_t table_addr; unsigned num_gpu_pages; @@ -590,18 +596,8 @@ struct radeon_asic { void (*fini)(struct radeon_device *rdev); int (*resume)(struct radeon_device *rdev); int (*suspend)(struct radeon_device *rdev); - void (*errata)(struct radeon_device *rdev); - void (*vram_info)(struct radeon_device *rdev); void (*vga_set_state)(struct radeon_device *rdev, bool state); int (*gpu_reset)(struct radeon_device *rdev); - int (*mc_init)(struct radeon_device *rdev); - void (*mc_fini)(struct radeon_device *rdev); - int (*wb_init)(struct radeon_device *rdev); - void (*wb_fini)(struct radeon_device *rdev); - int (*gart_init)(struct radeon_device *rdev); - void (*gart_fini)(struct radeon_device *rdev); - int (*gart_enable)(struct radeon_device *rdev); - void (*gart_disable)(struct radeon_device *rdev); void (*gart_tlb_flush)(struct radeon_device *rdev); int (*gart_set_page)(struct radeon_device *rdev, int i, uint64_t addr); int (*cp_init)(struct radeon_device *rdev, unsigned ring_size); @@ -611,7 +607,6 @@ struct radeon_asic { void (*ring_start)(struct radeon_device *rdev); int (*ring_test)(struct radeon_device *rdev); void (*ring_ib_execute)(struct radeon_device *rdev, struct radeon_ib *ib); - int (*ib_test)(struct radeon_device *rdev); int (*irq_set)(struct radeon_device *rdev); int (*irq_process)(struct radeon_device *rdev); u32 (*get_vblank_counter)(struct radeon_device *rdev, int crtc); @@ -632,7 +627,9 @@ struct radeon_asic { uint64_t dst_offset, unsigned num_pages, struct radeon_fence *fence); + uint32_t (*get_engine_clock)(struct radeon_device *rdev); void (*set_engine_clock)(struct radeon_device *rdev, uint32_t eng_clock); + uint32_t (*get_memory_clock)(struct radeon_device *rdev); void (*set_memory_clock)(struct radeon_device *rdev, uint32_t mem_clock); void (*set_pcie_lanes)(struct radeon_device *rdev, int lanes); void (*set_clock_gating)(struct radeon_device *rdev, int enable); @@ -789,12 +786,12 @@ struct radeon_device { bool shutdown; bool suspend; bool need_dma32; - bool new_init_path; bool accel_working; struct radeon_surface_reg surface_regs[RADEON_GEM_MAX_SURFACES]; const struct firmware *me_fw; /* all family ME firmware */ const struct firmware *pfp_fw; /* r6/700 PFP firmware */ struct r600_blit r600_blit; + int msi_enabled; /* msi enabled */ }; int radeon_device_init(struct radeon_device *rdev, @@ -949,28 +946,14 @@ static inline void radeon_ring_write(struct radeon_device *rdev, uint32_t v) #define radeon_resume(rdev) (rdev)->asic->resume((rdev)) #define radeon_suspend(rdev) (rdev)->asic->suspend((rdev)) #define radeon_cs_parse(p) rdev->asic->cs_parse((p)) -#define radeon_errata(rdev) (rdev)->asic->errata((rdev)) -#define radeon_vram_info(rdev) (rdev)->asic->vram_info((rdev)) #define radeon_vga_set_state(rdev, state) (rdev)->asic->vga_set_state((rdev), (state)) #define radeon_gpu_reset(rdev) (rdev)->asic->gpu_reset((rdev)) -#define radeon_mc_init(rdev) (rdev)->asic->mc_init((rdev)) -#define radeon_mc_fini(rdev) (rdev)->asic->mc_fini((rdev)) -#define radeon_wb_init(rdev) (rdev)->asic->wb_init((rdev)) -#define radeon_wb_fini(rdev) (rdev)->asic->wb_fini((rdev)) -#define radeon_gpu_gart_init(rdev) (rdev)->asic->gart_init((rdev)) -#define radeon_gpu_gart_fini(rdev) (rdev)->asic->gart_fini((rdev)) -#define radeon_gart_enable(rdev) (rdev)->asic->gart_enable((rdev)) -#define radeon_gart_disable(rdev) (rdev)->asic->gart_disable((rdev)) #define radeon_gart_tlb_flush(rdev) (rdev)->asic->gart_tlb_flush((rdev)) #define radeon_gart_set_page(rdev, i, p) (rdev)->asic->gart_set_page((rdev), (i), (p)) -#define radeon_cp_init(rdev,rsize) (rdev)->asic->cp_init((rdev), (rsize)) -#define radeon_cp_fini(rdev) (rdev)->asic->cp_fini((rdev)) -#define radeon_cp_disable(rdev) (rdev)->asic->cp_disable((rdev)) #define radeon_cp_commit(rdev) (rdev)->asic->cp_commit((rdev)) #define radeon_ring_start(rdev) (rdev)->asic->ring_start((rdev)) #define radeon_ring_test(rdev) (rdev)->asic->ring_test((rdev)) #define radeon_ring_ib_execute(rdev, ib) (rdev)->asic->ring_ib_execute((rdev), (ib)) -#define radeon_ib_test(rdev) (rdev)->asic->ib_test((rdev)) #define radeon_irq_set(rdev) (rdev)->asic->irq_set((rdev)) #define radeon_irq_process(rdev) (rdev)->asic->irq_process((rdev)) #define radeon_get_vblank_counter(rdev, crtc) (rdev)->asic->get_vblank_counter((rdev), (crtc)) @@ -978,7 +961,9 @@ static inline void radeon_ring_write(struct radeon_device *rdev, uint32_t v) #define radeon_copy_blit(rdev, s, d, np, f) (rdev)->asic->copy_blit((rdev), (s), (d), (np), (f)) #define radeon_copy_dma(rdev, s, d, np, f) (rdev)->asic->copy_dma((rdev), (s), (d), (np), (f)) #define radeon_copy(rdev, s, d, np, f) (rdev)->asic->copy((rdev), (s), (d), (np), (f)) +#define radeon_get_engine_clock(rdev) (rdev)->asic->get_engine_clock((rdev)) #define radeon_set_engine_clock(rdev, e) (rdev)->asic->set_engine_clock((rdev), (e)) +#define radeon_get_memory_clock(rdev) (rdev)->asic->get_memory_clock((rdev)) #define radeon_set_memory_clock(rdev, e) (rdev)->asic->set_engine_clock((rdev), (e)) #define radeon_set_pcie_lanes(rdev, l) (rdev)->asic->set_pcie_lanes((rdev), (l)) #define radeon_set_clock_gating(rdev, e) (rdev)->asic->set_clock_gating((rdev), (e)) @@ -996,6 +981,7 @@ extern void radeon_clocks_fini(struct radeon_device *rdev); extern void radeon_scratch_init(struct radeon_device *rdev); extern void radeon_surface_init(struct radeon_device *rdev); extern int radeon_cs_parser_init(struct radeon_cs_parser *p, void *data); +extern void radeon_legacy_set_clock_gating(struct radeon_device *rdev, int enable); extern void radeon_atom_set_clock_gating(struct radeon_device *rdev, int enable); /* r100,rv100,rs100,rv200,rs200,r200,rv250,rs300,rv280 */ @@ -1031,11 +1017,27 @@ extern int r100_wb_init(struct radeon_device *rdev); extern void r100_hdp_reset(struct radeon_device *rdev); extern int r100_rb2d_reset(struct radeon_device *rdev); extern int r100_cp_reset(struct radeon_device *rdev); +extern void r100_vga_render_disable(struct radeon_device *rdev); +extern int r100_cs_track_check_pkt3_indx_buffer(struct radeon_cs_parser *p, + struct radeon_cs_packet *pkt, + struct radeon_object *robj); +extern int r100_cs_parse_packet0(struct radeon_cs_parser *p, + struct radeon_cs_packet *pkt, + const unsigned *auth, unsigned n, + radeon_packet0_check_t check); +extern int r100_cs_packet_parse(struct radeon_cs_parser *p, + struct radeon_cs_packet *pkt, + unsigned idx); + +/* rv200,rv250,rv280 */ +extern void r200_set_safe_registers(struct radeon_device *rdev); /* r300,r350,rv350,rv370,rv380 */ extern void r300_set_reg_safe(struct radeon_device *rdev); extern void r300_mc_program(struct radeon_device *rdev); extern void r300_vram_info(struct radeon_device *rdev); +extern void r300_clock_startup(struct radeon_device *rdev); +extern int r300_mc_wait_for_idle(struct radeon_device *rdev); extern int rv370_pcie_gart_init(struct radeon_device *rdev); extern void rv370_pcie_gart_fini(struct radeon_device *rdev); extern int rv370_pcie_gart_enable(struct radeon_device *rdev); @@ -1066,6 +1068,18 @@ extern void rv515_clock_startup(struct radeon_device *rdev); extern void rv515_debugfs(struct radeon_device *rdev); extern int rv515_suspend(struct radeon_device *rdev); +/* rs400 */ +extern int rs400_gart_init(struct radeon_device *rdev); +extern int rs400_gart_enable(struct radeon_device *rdev); +extern void rs400_gart_adjust_size(struct radeon_device *rdev); +extern void rs400_gart_disable(struct radeon_device *rdev); +extern void rs400_gart_fini(struct radeon_device *rdev); + +/* rs600 */ +extern void rs600_set_safe_registers(struct radeon_device *rdev); +extern int rs600_irq_set(struct radeon_device *rdev); +extern void rs600_irq_disable(struct radeon_device *rdev); + /* rs690, rs740 */ extern void rs690_line_buffer_adjust(struct radeon_device *rdev, struct drm_display_mode *mode1, @@ -1083,8 +1097,9 @@ extern int r600_pcie_gart_init(struct radeon_device *rdev); extern void r600_pcie_gart_tlb_flush(struct radeon_device *rdev); extern int r600_ib_test(struct radeon_device *rdev); extern int r600_ring_test(struct radeon_device *rdev); -extern int r600_wb_init(struct radeon_device *rdev); extern void r600_wb_fini(struct radeon_device *rdev); +extern int r600_wb_enable(struct radeon_device *rdev); +extern void r600_wb_disable(struct radeon_device *rdev); extern void r600_scratch_init(struct radeon_device *rdev); extern int r600_blit_init(struct radeon_device *rdev); extern void r600_blit_fini(struct radeon_device *rdev); diff --git a/drivers/gpu/drm/radeon/radeon_asic.h b/drivers/gpu/drm/radeon/radeon_asic.h index c8a4e7b5663d..c18fbee387d7 100644 --- a/drivers/gpu/drm/radeon/radeon_asic.h +++ b/drivers/gpu/drm/radeon/radeon_asic.h @@ -31,38 +31,30 @@ /* * common functions */ +uint32_t radeon_legacy_get_engine_clock(struct radeon_device *rdev); void radeon_legacy_set_engine_clock(struct radeon_device *rdev, uint32_t eng_clock); void radeon_legacy_set_clock_gating(struct radeon_device *rdev, int enable); +uint32_t radeon_atom_get_engine_clock(struct radeon_device *rdev); void radeon_atom_set_engine_clock(struct radeon_device *rdev, uint32_t eng_clock); +uint32_t radeon_atom_get_memory_clock(struct radeon_device *rdev); void radeon_atom_set_memory_clock(struct radeon_device *rdev, uint32_t mem_clock); void radeon_atom_set_clock_gating(struct radeon_device *rdev, int enable); /* * r100,rv100,rs100,rv200,rs200,r200,rv250,rs300,rv280 */ -int r100_init(struct radeon_device *rdev); -int r200_init(struct radeon_device *rdev); +extern int r100_init(struct radeon_device *rdev); +extern void r100_fini(struct radeon_device *rdev); +extern int r100_suspend(struct radeon_device *rdev); +extern int r100_resume(struct radeon_device *rdev); uint32_t r100_mm_rreg(struct radeon_device *rdev, uint32_t reg); void r100_mm_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v); -void r100_errata(struct radeon_device *rdev); -void r100_vram_info(struct radeon_device *rdev); void r100_vga_set_state(struct radeon_device *rdev, bool state); int r100_gpu_reset(struct radeon_device *rdev); -int r100_mc_init(struct radeon_device *rdev); -void r100_mc_fini(struct radeon_device *rdev); u32 r100_get_vblank_counter(struct radeon_device *rdev, int crtc); -int r100_wb_init(struct radeon_device *rdev); -void r100_wb_fini(struct radeon_device *rdev); -int r100_pci_gart_init(struct radeon_device *rdev); -void r100_pci_gart_fini(struct radeon_device *rdev); -int r100_pci_gart_enable(struct radeon_device *rdev); -void r100_pci_gart_disable(struct radeon_device *rdev); void r100_pci_gart_tlb_flush(struct radeon_device *rdev); int r100_pci_gart_set_page(struct radeon_device *rdev, int i, uint64_t addr); -int r100_cp_init(struct radeon_device *rdev, unsigned ring_size); -void r100_cp_fini(struct radeon_device *rdev); -void r100_cp_disable(struct radeon_device *rdev); void r100_cp_commit(struct radeon_device *rdev); void r100_ring_start(struct radeon_device *rdev); int r100_irq_set(struct radeon_device *rdev); @@ -83,33 +75,21 @@ int r100_set_surface_reg(struct radeon_device *rdev, int reg, int r100_clear_surface_reg(struct radeon_device *rdev, int reg); void r100_bandwidth_update(struct radeon_device *rdev); void r100_ring_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib); -int r100_ib_test(struct radeon_device *rdev); int r100_ring_test(struct radeon_device *rdev); static struct radeon_asic r100_asic = { .init = &r100_init, - .errata = &r100_errata, - .vram_info = &r100_vram_info, + .fini = &r100_fini, + .suspend = &r100_suspend, + .resume = &r100_resume, .vga_set_state = &r100_vga_set_state, .gpu_reset = &r100_gpu_reset, - .mc_init = &r100_mc_init, - .mc_fini = &r100_mc_fini, - .wb_init = &r100_wb_init, - .wb_fini = &r100_wb_fini, - .gart_init = &r100_pci_gart_init, - .gart_fini = &r100_pci_gart_fini, - .gart_enable = &r100_pci_gart_enable, - .gart_disable = &r100_pci_gart_disable, .gart_tlb_flush = &r100_pci_gart_tlb_flush, .gart_set_page = &r100_pci_gart_set_page, - .cp_init = &r100_cp_init, - .cp_fini = &r100_cp_fini, - .cp_disable = &r100_cp_disable, .cp_commit = &r100_cp_commit, .ring_start = &r100_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = &r100_ib_test, .irq_set = &r100_irq_set, .irq_process = &r100_irq_process, .get_vblank_counter = &r100_get_vblank_counter, @@ -118,7 +98,9 @@ static struct radeon_asic r100_asic = { .copy_blit = &r100_copy_blit, .copy_dma = NULL, .copy = &r100_copy_blit, + .get_engine_clock = &radeon_legacy_get_engine_clock, .set_engine_clock = &radeon_legacy_set_engine_clock, + .get_memory_clock = NULL, .set_memory_clock = NULL, .set_pcie_lanes = NULL, .set_clock_gating = &radeon_legacy_set_clock_gating, @@ -131,55 +113,38 @@ static struct radeon_asic r100_asic = { /* * r300,r350,rv350,rv380 */ -int r300_init(struct radeon_device *rdev); -void r300_errata(struct radeon_device *rdev); -void r300_vram_info(struct radeon_device *rdev); -int r300_gpu_reset(struct radeon_device *rdev); -int r300_mc_init(struct radeon_device *rdev); -void r300_mc_fini(struct radeon_device *rdev); -void r300_ring_start(struct radeon_device *rdev); -void r300_fence_ring_emit(struct radeon_device *rdev, - struct radeon_fence *fence); -int r300_cs_parse(struct radeon_cs_parser *p); -int rv370_pcie_gart_init(struct radeon_device *rdev); -void rv370_pcie_gart_fini(struct radeon_device *rdev); -int rv370_pcie_gart_enable(struct radeon_device *rdev); -void rv370_pcie_gart_disable(struct radeon_device *rdev); -void rv370_pcie_gart_tlb_flush(struct radeon_device *rdev); -int rv370_pcie_gart_set_page(struct radeon_device *rdev, int i, uint64_t addr); -uint32_t rv370_pcie_rreg(struct radeon_device *rdev, uint32_t reg); -void rv370_pcie_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v); -void rv370_set_pcie_lanes(struct radeon_device *rdev, int lanes); -int r300_copy_dma(struct radeon_device *rdev, - uint64_t src_offset, - uint64_t dst_offset, - unsigned num_pages, - struct radeon_fence *fence); - +extern int r300_init(struct radeon_device *rdev); +extern void r300_fini(struct radeon_device *rdev); +extern int r300_suspend(struct radeon_device *rdev); +extern int r300_resume(struct radeon_device *rdev); +extern int r300_gpu_reset(struct radeon_device *rdev); +extern void r300_ring_start(struct radeon_device *rdev); +extern void r300_fence_ring_emit(struct radeon_device *rdev, + struct radeon_fence *fence); +extern int r300_cs_parse(struct radeon_cs_parser *p); +extern void rv370_pcie_gart_tlb_flush(struct radeon_device *rdev); +extern int rv370_pcie_gart_set_page(struct radeon_device *rdev, int i, uint64_t addr); +extern uint32_t rv370_pcie_rreg(struct radeon_device *rdev, uint32_t reg); +extern void rv370_pcie_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v); +extern void rv370_set_pcie_lanes(struct radeon_device *rdev, int lanes); +extern int r300_copy_dma(struct radeon_device *rdev, + uint64_t src_offset, + uint64_t dst_offset, + unsigned num_pages, + struct radeon_fence *fence); static struct radeon_asic r300_asic = { .init = &r300_init, - .errata = &r300_errata, - .vram_info = &r300_vram_info, + .fini = &r300_fini, + .suspend = &r300_suspend, + .resume = &r300_resume, .vga_set_state = &r100_vga_set_state, .gpu_reset = &r300_gpu_reset, - .mc_init = &r300_mc_init, - .mc_fini = &r300_mc_fini, - .wb_init = &r100_wb_init, - .wb_fini = &r100_wb_fini, - .gart_init = &r100_pci_gart_init, - .gart_fini = &r100_pci_gart_fini, - .gart_enable = &r100_pci_gart_enable, - .gart_disable = &r100_pci_gart_disable, .gart_tlb_flush = &r100_pci_gart_tlb_flush, .gart_set_page = &r100_pci_gart_set_page, - .cp_init = &r100_cp_init, - .cp_fini = &r100_cp_fini, - .cp_disable = &r100_cp_disable, .cp_commit = &r100_cp_commit, .ring_start = &r300_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = &r100_ib_test, .irq_set = &r100_irq_set, .irq_process = &r100_irq_process, .get_vblank_counter = &r100_get_vblank_counter, @@ -188,7 +153,9 @@ static struct radeon_asic r300_asic = { .copy_blit = &r100_copy_blit, .copy_dma = &r300_copy_dma, .copy = &r100_copy_blit, + .get_engine_clock = &radeon_legacy_get_engine_clock, .set_engine_clock = &radeon_legacy_set_engine_clock, + .get_memory_clock = NULL, .set_memory_clock = NULL, .set_pcie_lanes = &rv370_set_pcie_lanes, .set_clock_gating = &radeon_legacy_set_clock_gating, @@ -209,26 +176,14 @@ static struct radeon_asic r420_asic = { .fini = &r420_fini, .suspend = &r420_suspend, .resume = &r420_resume, - .errata = NULL, - .vram_info = NULL, .vga_set_state = &r100_vga_set_state, .gpu_reset = &r300_gpu_reset, - .mc_init = NULL, - .mc_fini = NULL, - .wb_init = NULL, - .wb_fini = NULL, - .gart_enable = NULL, - .gart_disable = NULL, .gart_tlb_flush = &rv370_pcie_gart_tlb_flush, .gart_set_page = &rv370_pcie_gart_set_page, - .cp_init = NULL, - .cp_fini = NULL, - .cp_disable = NULL, .cp_commit = &r100_cp_commit, .ring_start = &r300_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = NULL, .irq_set = &r100_irq_set, .irq_process = &r100_irq_process, .get_vblank_counter = &r100_get_vblank_counter, @@ -237,7 +192,9 @@ static struct radeon_asic r420_asic = { .copy_blit = &r100_copy_blit, .copy_dma = &r300_copy_dma, .copy = &r100_copy_blit, + .get_engine_clock = &radeon_atom_get_engine_clock, .set_engine_clock = &radeon_atom_set_engine_clock, + .get_memory_clock = &radeon_atom_get_memory_clock, .set_memory_clock = &radeon_atom_set_memory_clock, .set_pcie_lanes = &rv370_set_pcie_lanes, .set_clock_gating = &radeon_atom_set_clock_gating, @@ -250,42 +207,27 @@ static struct radeon_asic r420_asic = { /* * rs400,rs480 */ -void rs400_errata(struct radeon_device *rdev); -void rs400_vram_info(struct radeon_device *rdev); -int rs400_mc_init(struct radeon_device *rdev); -void rs400_mc_fini(struct radeon_device *rdev); -int rs400_gart_init(struct radeon_device *rdev); -void rs400_gart_fini(struct radeon_device *rdev); -int rs400_gart_enable(struct radeon_device *rdev); -void rs400_gart_disable(struct radeon_device *rdev); +extern int rs400_init(struct radeon_device *rdev); +extern void rs400_fini(struct radeon_device *rdev); +extern int rs400_suspend(struct radeon_device *rdev); +extern int rs400_resume(struct radeon_device *rdev); void rs400_gart_tlb_flush(struct radeon_device *rdev); int rs400_gart_set_page(struct radeon_device *rdev, int i, uint64_t addr); uint32_t rs400_mc_rreg(struct radeon_device *rdev, uint32_t reg); void rs400_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v); static struct radeon_asic rs400_asic = { - .init = &r300_init, - .errata = &rs400_errata, - .vram_info = &rs400_vram_info, + .init = &rs400_init, + .fini = &rs400_fini, + .suspend = &rs400_suspend, + .resume = &rs400_resume, .vga_set_state = &r100_vga_set_state, .gpu_reset = &r300_gpu_reset, - .mc_init = &rs400_mc_init, - .mc_fini = &rs400_mc_fini, - .wb_init = &r100_wb_init, - .wb_fini = &r100_wb_fini, - .gart_init = &rs400_gart_init, - .gart_fini = &rs400_gart_fini, - .gart_enable = &rs400_gart_enable, - .gart_disable = &rs400_gart_disable, .gart_tlb_flush = &rs400_gart_tlb_flush, .gart_set_page = &rs400_gart_set_page, - .cp_init = &r100_cp_init, - .cp_fini = &r100_cp_fini, - .cp_disable = &r100_cp_disable, .cp_commit = &r100_cp_commit, .ring_start = &r300_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = &r100_ib_test, .irq_set = &r100_irq_set, .irq_process = &r100_irq_process, .get_vblank_counter = &r100_get_vblank_counter, @@ -294,7 +236,9 @@ static struct radeon_asic rs400_asic = { .copy_blit = &r100_copy_blit, .copy_dma = &r300_copy_dma, .copy = &r100_copy_blit, + .get_engine_clock = &radeon_legacy_get_engine_clock, .set_engine_clock = &radeon_legacy_set_engine_clock, + .get_memory_clock = NULL, .set_memory_clock = NULL, .set_pcie_lanes = NULL, .set_clock_gating = &radeon_legacy_set_clock_gating, @@ -307,18 +251,13 @@ static struct radeon_asic rs400_asic = { /* * rs600. */ -int rs600_init(struct radeon_device *rdev); -void rs600_errata(struct radeon_device *rdev); -void rs600_vram_info(struct radeon_device *rdev); -int rs600_mc_init(struct radeon_device *rdev); -void rs600_mc_fini(struct radeon_device *rdev); +extern int rs600_init(struct radeon_device *rdev); +extern void rs600_fini(struct radeon_device *rdev); +extern int rs600_suspend(struct radeon_device *rdev); +extern int rs600_resume(struct radeon_device *rdev); int rs600_irq_set(struct radeon_device *rdev); int rs600_irq_process(struct radeon_device *rdev); u32 rs600_get_vblank_counter(struct radeon_device *rdev, int crtc); -int rs600_gart_init(struct radeon_device *rdev); -void rs600_gart_fini(struct radeon_device *rdev); -int rs600_gart_enable(struct radeon_device *rdev); -void rs600_gart_disable(struct radeon_device *rdev); void rs600_gart_tlb_flush(struct radeon_device *rdev); int rs600_gart_set_page(struct radeon_device *rdev, int i, uint64_t addr); uint32_t rs600_mc_rreg(struct radeon_device *rdev, uint32_t reg); @@ -326,28 +265,17 @@ void rs600_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v); void rs600_bandwidth_update(struct radeon_device *rdev); static struct radeon_asic rs600_asic = { .init = &rs600_init, - .errata = &rs600_errata, - .vram_info = &rs600_vram_info, + .fini = &rs600_fini, + .suspend = &rs600_suspend, + .resume = &rs600_resume, .vga_set_state = &r100_vga_set_state, .gpu_reset = &r300_gpu_reset, - .mc_init = &rs600_mc_init, - .mc_fini = &rs600_mc_fini, - .wb_init = &r100_wb_init, - .wb_fini = &r100_wb_fini, - .gart_init = &rs600_gart_init, - .gart_fini = &rs600_gart_fini, - .gart_enable = &rs600_gart_enable, - .gart_disable = &rs600_gart_disable, .gart_tlb_flush = &rs600_gart_tlb_flush, .gart_set_page = &rs600_gart_set_page, - .cp_init = &r100_cp_init, - .cp_fini = &r100_cp_fini, - .cp_disable = &r100_cp_disable, .cp_commit = &r100_cp_commit, .ring_start = &r300_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = &r100_ib_test, .irq_set = &rs600_irq_set, .irq_process = &rs600_irq_process, .get_vblank_counter = &rs600_get_vblank_counter, @@ -356,7 +284,9 @@ static struct radeon_asic rs600_asic = { .copy_blit = &r100_copy_blit, .copy_dma = &r300_copy_dma, .copy = &r100_copy_blit, + .get_engine_clock = &radeon_atom_get_engine_clock, .set_engine_clock = &radeon_atom_set_engine_clock, + .get_memory_clock = &radeon_atom_get_memory_clock, .set_memory_clock = &radeon_atom_set_memory_clock, .set_pcie_lanes = NULL, .set_clock_gating = &radeon_atom_set_clock_gating, @@ -367,37 +297,26 @@ static struct radeon_asic rs600_asic = { /* * rs690,rs740 */ -void rs690_errata(struct radeon_device *rdev); -void rs690_vram_info(struct radeon_device *rdev); -int rs690_mc_init(struct radeon_device *rdev); -void rs690_mc_fini(struct radeon_device *rdev); +int rs690_init(struct radeon_device *rdev); +void rs690_fini(struct radeon_device *rdev); +int rs690_resume(struct radeon_device *rdev); +int rs690_suspend(struct radeon_device *rdev); uint32_t rs690_mc_rreg(struct radeon_device *rdev, uint32_t reg); void rs690_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v); void rs690_bandwidth_update(struct radeon_device *rdev); static struct radeon_asic rs690_asic = { - .init = &rs600_init, - .errata = &rs690_errata, - .vram_info = &rs690_vram_info, + .init = &rs690_init, + .fini = &rs690_fini, + .suspend = &rs690_suspend, + .resume = &rs690_resume, .vga_set_state = &r100_vga_set_state, .gpu_reset = &r300_gpu_reset, - .mc_init = &rs690_mc_init, - .mc_fini = &rs690_mc_fini, - .wb_init = &r100_wb_init, - .wb_fini = &r100_wb_fini, - .gart_init = &rs400_gart_init, - .gart_fini = &rs400_gart_fini, - .gart_enable = &rs400_gart_enable, - .gart_disable = &rs400_gart_disable, .gart_tlb_flush = &rs400_gart_tlb_flush, .gart_set_page = &rs400_gart_set_page, - .cp_init = &r100_cp_init, - .cp_fini = &r100_cp_fini, - .cp_disable = &r100_cp_disable, .cp_commit = &r100_cp_commit, .ring_start = &r300_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = &r100_ib_test, .irq_set = &rs600_irq_set, .irq_process = &rs600_irq_process, .get_vblank_counter = &rs600_get_vblank_counter, @@ -406,7 +325,9 @@ static struct radeon_asic rs690_asic = { .copy_blit = &r100_copy_blit, .copy_dma = &r300_copy_dma, .copy = &r300_copy_dma, + .get_engine_clock = &radeon_atom_get_engine_clock, .set_engine_clock = &radeon_atom_set_engine_clock, + .get_memory_clock = &radeon_atom_get_memory_clock, .set_memory_clock = &radeon_atom_set_memory_clock, .set_pcie_lanes = NULL, .set_clock_gating = &radeon_atom_set_clock_gating, @@ -435,28 +356,14 @@ static struct radeon_asic rv515_asic = { .fini = &rv515_fini, .suspend = &rv515_suspend, .resume = &rv515_resume, - .errata = NULL, - .vram_info = NULL, .vga_set_state = &r100_vga_set_state, .gpu_reset = &rv515_gpu_reset, - .mc_init = NULL, - .mc_fini = NULL, - .wb_init = NULL, - .wb_fini = NULL, - .gart_init = &rv370_pcie_gart_init, - .gart_fini = &rv370_pcie_gart_fini, - .gart_enable = NULL, - .gart_disable = NULL, .gart_tlb_flush = &rv370_pcie_gart_tlb_flush, .gart_set_page = &rv370_pcie_gart_set_page, - .cp_init = NULL, - .cp_fini = NULL, - .cp_disable = NULL, .cp_commit = &r100_cp_commit, .ring_start = &rv515_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = NULL, .irq_set = &rs600_irq_set, .irq_process = &rs600_irq_process, .get_vblank_counter = &rs600_get_vblank_counter, @@ -465,7 +372,9 @@ static struct radeon_asic rv515_asic = { .copy_blit = &r100_copy_blit, .copy_dma = &r300_copy_dma, .copy = &r100_copy_blit, + .get_engine_clock = &radeon_atom_get_engine_clock, .set_engine_clock = &radeon_atom_set_engine_clock, + .get_memory_clock = &radeon_atom_get_memory_clock, .set_memory_clock = &radeon_atom_set_memory_clock, .set_pcie_lanes = &rv370_set_pcie_lanes, .set_clock_gating = &radeon_atom_set_clock_gating, @@ -485,28 +394,14 @@ static struct radeon_asic r520_asic = { .fini = &rv515_fini, .suspend = &rv515_suspend, .resume = &r520_resume, - .errata = NULL, - .vram_info = NULL, .vga_set_state = &r100_vga_set_state, .gpu_reset = &rv515_gpu_reset, - .mc_init = NULL, - .mc_fini = NULL, - .wb_init = NULL, - .wb_fini = NULL, - .gart_init = NULL, - .gart_fini = NULL, - .gart_enable = NULL, - .gart_disable = NULL, .gart_tlb_flush = &rv370_pcie_gart_tlb_flush, .gart_set_page = &rv370_pcie_gart_set_page, - .cp_init = NULL, - .cp_fini = NULL, - .cp_disable = NULL, .cp_commit = &r100_cp_commit, .ring_start = &rv515_ring_start, .ring_test = &r100_ring_test, .ring_ib_execute = &r100_ring_ib_execute, - .ib_test = NULL, .irq_set = &rs600_irq_set, .irq_process = &rs600_irq_process, .get_vblank_counter = &rs600_get_vblank_counter, @@ -515,7 +410,9 @@ static struct radeon_asic r520_asic = { .copy_blit = &r100_copy_blit, .copy_dma = &r300_copy_dma, .copy = &r100_copy_blit, + .get_engine_clock = &radeon_atom_get_engine_clock, .set_engine_clock = &radeon_atom_set_engine_clock, + .get_memory_clock = &radeon_atom_get_memory_clock, .set_memory_clock = &radeon_atom_set_memory_clock, .set_pcie_lanes = &rv370_set_pcie_lanes, .set_clock_gating = &radeon_atom_set_clock_gating, @@ -554,37 +451,23 @@ int r600_set_surface_reg(struct radeon_device *rdev, int reg, uint32_t offset, uint32_t obj_size); int r600_clear_surface_reg(struct radeon_device *rdev, int reg); void r600_ring_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib); -int r600_ib_test(struct radeon_device *rdev); int r600_ring_test(struct radeon_device *rdev); int r600_copy_blit(struct radeon_device *rdev, uint64_t src_offset, uint64_t dst_offset, unsigned num_pages, struct radeon_fence *fence); static struct radeon_asic r600_asic = { - .errata = NULL, .init = &r600_init, .fini = &r600_fini, .suspend = &r600_suspend, .resume = &r600_resume, .cp_commit = &r600_cp_commit, - .vram_info = NULL, .vga_set_state = &r600_vga_set_state, .gpu_reset = &r600_gpu_reset, - .mc_init = NULL, - .mc_fini = NULL, - .wb_init = &r600_wb_init, - .wb_fini = &r600_wb_fini, - .gart_enable = NULL, - .gart_disable = NULL, .gart_tlb_flush = &r600_pcie_gart_tlb_flush, .gart_set_page = &rs600_gart_set_page, - .cp_init = NULL, - .cp_fini = NULL, - .cp_disable = NULL, - .ring_start = NULL, .ring_test = &r600_ring_test, .ring_ib_execute = &r600_ring_ib_execute, - .ib_test = &r600_ib_test, .irq_set = &r600_irq_set, .irq_process = &r600_irq_process, .fence_ring_emit = &r600_fence_ring_emit, @@ -592,7 +475,9 @@ static struct radeon_asic r600_asic = { .copy_blit = &r600_copy_blit, .copy_dma = &r600_copy_blit, .copy = &r600_copy_blit, + .get_engine_clock = &radeon_atom_get_engine_clock, .set_engine_clock = &radeon_atom_set_engine_clock, + .get_memory_clock = &radeon_atom_get_memory_clock, .set_memory_clock = &radeon_atom_set_memory_clock, .set_pcie_lanes = NULL, .set_clock_gating = &radeon_atom_set_clock_gating, @@ -611,30 +496,17 @@ int rv770_resume(struct radeon_device *rdev); int rv770_gpu_reset(struct radeon_device *rdev); static struct radeon_asic rv770_asic = { - .errata = NULL, .init = &rv770_init, .fini = &rv770_fini, .suspend = &rv770_suspend, .resume = &rv770_resume, .cp_commit = &r600_cp_commit, - .vram_info = NULL, .gpu_reset = &rv770_gpu_reset, .vga_set_state = &r600_vga_set_state, - .mc_init = NULL, - .mc_fini = NULL, - .wb_init = &r600_wb_init, - .wb_fini = &r600_wb_fini, - .gart_enable = NULL, - .gart_disable = NULL, .gart_tlb_flush = &r600_pcie_gart_tlb_flush, .gart_set_page = &rs600_gart_set_page, - .cp_init = NULL, - .cp_fini = NULL, - .cp_disable = NULL, - .ring_start = NULL, .ring_test = &r600_ring_test, .ring_ib_execute = &r600_ring_ib_execute, - .ib_test = &r600_ib_test, .irq_set = &r600_irq_set, .irq_process = &r600_irq_process, .fence_ring_emit = &r600_fence_ring_emit, @@ -642,7 +514,9 @@ static struct radeon_asic rv770_asic = { .copy_blit = &r600_copy_blit, .copy_dma = &r600_copy_blit, .copy = &r600_copy_blit, + .get_engine_clock = &radeon_atom_get_engine_clock, .set_engine_clock = &radeon_atom_set_engine_clock, + .get_memory_clock = &radeon_atom_get_memory_clock, .set_memory_clock = &radeon_atom_set_memory_clock, .set_pcie_lanes = NULL, .set_clock_gating = &radeon_atom_set_clock_gating, diff --git a/drivers/gpu/drm/radeon/radeon_atombios.c b/drivers/gpu/drm/radeon/radeon_atombios.c index 5b6c08cee40e..2ed88a820935 100644 --- a/drivers/gpu/drm/radeon/radeon_atombios.c +++ b/drivers/gpu/drm/radeon/radeon_atombios.c @@ -46,7 +46,8 @@ radeon_add_atom_connector(struct drm_device *dev, uint32_t supported_device, int connector_type, struct radeon_i2c_bus_rec *i2c_bus, - bool linkb, uint32_t igp_lane_info); + bool linkb, uint32_t igp_lane_info, + uint16_t connector_object_id); /* from radeon_legacy_encoder.c */ extern void @@ -193,6 +194,23 @@ const int supported_devices_connector_convert[] = { DRM_MODE_CONNECTOR_DisplayPort }; +const uint16_t supported_devices_connector_object_id_convert[] = { + CONNECTOR_OBJECT_ID_NONE, + CONNECTOR_OBJECT_ID_VGA, + CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_I, /* not all boards support DL */ + CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_D, /* not all boards support DL */ + CONNECTOR_OBJECT_ID_VGA, /* technically DVI-A */ + CONNECTOR_OBJECT_ID_COMPOSITE, + CONNECTOR_OBJECT_ID_SVIDEO, + CONNECTOR_OBJECT_ID_LVDS, + CONNECTOR_OBJECT_ID_9PIN_DIN, + CONNECTOR_OBJECT_ID_9PIN_DIN, + CONNECTOR_OBJECT_ID_DISPLAYPORT, + CONNECTOR_OBJECT_ID_HDMI_TYPE_A, + CONNECTOR_OBJECT_ID_HDMI_TYPE_B, + CONNECTOR_OBJECT_ID_SVIDEO +}; + const int object_connector_convert[] = { DRM_MODE_CONNECTOR_Unknown, DRM_MODE_CONNECTOR_DVII, @@ -229,7 +247,7 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev) ATOM_OBJECT_HEADER *obj_header; int i, j, path_size, device_support; int connector_type; - uint16_t igp_lane_info, conn_id; + uint16_t igp_lane_info, conn_id, connector_object_id; bool linkb; struct radeon_i2c_bus_rec ddc_bus; @@ -277,7 +295,8 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev) ATOM_DEVICE_CV_SUPPORT) continue; - if ((rdev->family == CHIP_RS780) && + /* IGP chips */ + if ((rdev->flags & RADEON_IS_IGP) && (con_obj_id == CONNECTOR_OBJECT_ID_PCIE_CONNECTOR)) { uint16_t igp_offset = 0; @@ -311,6 +330,7 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev) connector_type = object_connector_convert [ct]; + connector_object_id = ct; igp_lane_info = slot_config & 0xffff; } else @@ -321,6 +341,7 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev) igp_lane_info = 0; connector_type = object_connector_convert[con_obj_id]; + connector_object_id = con_obj_id; } if (connector_type == DRM_MODE_CONNECTOR_Unknown) @@ -425,7 +446,8 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev) le16_to_cpu(path-> usDeviceTag), connector_type, &ddc_bus, - linkb, igp_lane_info); + linkb, igp_lane_info, + connector_object_id); } } @@ -435,6 +457,45 @@ bool radeon_get_atom_connector_info_from_object_table(struct drm_device *dev) return true; } +static uint16_t atombios_get_connector_object_id(struct drm_device *dev, + int connector_type, + uint16_t devices) +{ + struct radeon_device *rdev = dev->dev_private; + + if (rdev->flags & RADEON_IS_IGP) { + return supported_devices_connector_object_id_convert + [connector_type]; + } else if (((connector_type == DRM_MODE_CONNECTOR_DVII) || + (connector_type == DRM_MODE_CONNECTOR_DVID)) && + (devices & ATOM_DEVICE_DFP2_SUPPORT)) { + struct radeon_mode_info *mode_info = &rdev->mode_info; + struct atom_context *ctx = mode_info->atom_context; + int index = GetIndexIntoMasterTable(DATA, XTMDS_Info); + uint16_t size, data_offset; + uint8_t frev, crev; + ATOM_XTMDS_INFO *xtmds; + + atom_parse_data_header(ctx, index, &size, &frev, &crev, &data_offset); + xtmds = (ATOM_XTMDS_INFO *)(ctx->bios + data_offset); + + if (xtmds->ucSupportedLink & ATOM_XTMDS_SUPPORTED_DUALLINK) { + if (connector_type == DRM_MODE_CONNECTOR_DVII) + return CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_I; + else + return CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_D; + } else { + if (connector_type == DRM_MODE_CONNECTOR_DVII) + return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I; + else + return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_D; + } + } else { + return supported_devices_connector_object_id_convert + [connector_type]; + } +} + struct bios_connector { bool valid; uint16_t line_mux; @@ -593,14 +654,20 @@ bool radeon_get_atom_connector_info_from_supported_devices_table(struct /* add the connectors */ for (i = 0; i < ATOM_MAX_SUPPORTED_DEVICE; i++) { - if (bios_connectors[i].valid) + if (bios_connectors[i].valid) { + uint16_t connector_object_id = + atombios_get_connector_object_id(dev, + bios_connectors[i].connector_type, + bios_connectors[i].devices); radeon_add_atom_connector(dev, bios_connectors[i].line_mux, bios_connectors[i].devices, bios_connectors[i]. connector_type, &bios_connectors[i].ddc_bus, - false, 0); + false, 0, + connector_object_id); + } } radeon_link_encoder_connector(dev); @@ -641,8 +708,12 @@ bool radeon_atom_get_clock_info(struct drm_device *dev) le16_to_cpu(firmware_info->info.usReferenceClock); p1pll->reference_div = 0; - p1pll->pll_out_min = - le16_to_cpu(firmware_info->info.usMinPixelClockPLL_Output); + if (crev < 2) + p1pll->pll_out_min = + le16_to_cpu(firmware_info->info.usMinPixelClockPLL_Output); + else + p1pll->pll_out_min = + le32_to_cpu(firmware_info->info_12.ulMinPixelClockPLL_Output); p1pll->pll_out_max = le32_to_cpu(firmware_info->info.ulMaxPixelClockPLL_Output); @@ -651,6 +722,16 @@ bool radeon_atom_get_clock_info(struct drm_device *dev) p1pll->pll_out_min = 64800; else p1pll->pll_out_min = 20000; + } else if (p1pll->pll_out_min > 64800) { + /* Limiting the pll output range is a good thing generally as + * it limits the number of possible pll combinations for a given + * frequency presumably to the ones that work best on each card. + * However, certain duallink DVI monitors seem to like + * pll combinations that would be limited by this at least on + * pre-DCE 3.0 r6xx hardware. This might need to be adjusted per + * family. + */ + p1pll->pll_out_min = 64800; } p1pll->pll_in_min = @@ -767,6 +848,46 @@ bool radeon_atombios_get_tmds_info(struct radeon_encoder *encoder, return false; } +static struct radeon_atom_ss *radeon_atombios_get_ss_info(struct + radeon_encoder + *encoder, + int id) +{ + struct drm_device *dev = encoder->base.dev; + struct radeon_device *rdev = dev->dev_private; + struct radeon_mode_info *mode_info = &rdev->mode_info; + int index = GetIndexIntoMasterTable(DATA, PPLL_SS_Info); + uint16_t data_offset; + struct _ATOM_SPREAD_SPECTRUM_INFO *ss_info; + uint8_t frev, crev; + struct radeon_atom_ss *ss = NULL; + + if (id > ATOM_MAX_SS_ENTRY) + return NULL; + + atom_parse_data_header(mode_info->atom_context, index, NULL, &frev, + &crev, &data_offset); + + ss_info = + (struct _ATOM_SPREAD_SPECTRUM_INFO *)(mode_info->atom_context->bios + data_offset); + + if (ss_info) { + ss = + kzalloc(sizeof(struct radeon_atom_ss), GFP_KERNEL); + + if (!ss) + return NULL; + + ss->percentage = le16_to_cpu(ss_info->asSS_Info[id].usSpreadSpectrumPercentage); + ss->type = ss_info->asSS_Info[id].ucSpreadSpectrumType; + ss->step = ss_info->asSS_Info[id].ucSS_Step; + ss->delay = ss_info->asSS_Info[id].ucSS_Delay; + ss->range = ss_info->asSS_Info[id].ucSS_Range; + ss->refdiv = ss_info->asSS_Info[id].ucRecommendedRef_Div; + } + return ss; +} + union lvds_info { struct _ATOM_LVDS_INFO info; struct _ATOM_LVDS_INFO_V12 info_12; @@ -798,27 +919,31 @@ struct radeon_encoder_atom_dig *radeon_atombios_get_lvds_info(struct if (!lvds) return NULL; - lvds->native_mode.dotclock = + lvds->native_mode.clock = le16_to_cpu(lvds_info->info.sLCDTiming.usPixClk) * 10; - lvds->native_mode.panel_xres = + lvds->native_mode.hdisplay = le16_to_cpu(lvds_info->info.sLCDTiming.usHActive); - lvds->native_mode.panel_yres = + lvds->native_mode.vdisplay = le16_to_cpu(lvds_info->info.sLCDTiming.usVActive); - lvds->native_mode.hblank = - le16_to_cpu(lvds_info->info.sLCDTiming.usHBlanking_Time); - lvds->native_mode.hoverplus = - le16_to_cpu(lvds_info->info.sLCDTiming.usHSyncOffset); - lvds->native_mode.hsync_width = - le16_to_cpu(lvds_info->info.sLCDTiming.usHSyncWidth); - lvds->native_mode.vblank = - le16_to_cpu(lvds_info->info.sLCDTiming.usVBlanking_Time); - lvds->native_mode.voverplus = - le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncOffset); - lvds->native_mode.vsync_width = - le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncWidth); + lvds->native_mode.htotal = lvds->native_mode.hdisplay + + le16_to_cpu(lvds_info->info.sLCDTiming.usHBlanking_Time); + lvds->native_mode.hsync_start = lvds->native_mode.hdisplay + + le16_to_cpu(lvds_info->info.sLCDTiming.usHSyncOffset); + lvds->native_mode.hsync_end = lvds->native_mode.hsync_start + + le16_to_cpu(lvds_info->info.sLCDTiming.usHSyncWidth); + lvds->native_mode.vtotal = lvds->native_mode.vdisplay + + le16_to_cpu(lvds_info->info.sLCDTiming.usVBlanking_Time); + lvds->native_mode.vsync_start = lvds->native_mode.vdisplay + + le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncWidth); + lvds->native_mode.vsync_end = lvds->native_mode.vsync_start + + le16_to_cpu(lvds_info->info.sLCDTiming.usVSyncWidth); lvds->panel_pwr_delay = le16_to_cpu(lvds_info->info.usOffDelayInMs); lvds->lvds_misc = lvds_info->info.ucLVDS_Misc; + /* set crtc values */ + drm_mode_set_crtcinfo(&lvds->native_mode, CRTC_INTERLACE_HALVE_V); + + lvds->ss = radeon_atombios_get_ss_info(encoder, lvds_info->info.ucSS_Id); encoder->native_mode = lvds->native_mode; } @@ -857,8 +982,7 @@ radeon_atombios_get_primary_dac_info(struct radeon_encoder *encoder) } bool radeon_atom_get_tv_timings(struct radeon_device *rdev, int index, - SET_CRTC_TIMING_PARAMETERS_PS_ALLOCATION *crtc_timing, - int32_t *pixel_clock) + struct drm_display_mode *mode) { struct radeon_mode_info *mode_info = &rdev->mode_info; ATOM_ANALOG_TV_INFO *tv_info; @@ -866,7 +990,7 @@ bool radeon_atom_get_tv_timings(struct radeon_device *rdev, int index, ATOM_DTD_FORMAT *dtd_timings; int data_index = GetIndexIntoMasterTable(DATA, AnalogTV_Info); u8 frev, crev; - uint16_t data_offset; + u16 data_offset, misc; atom_parse_data_header(mode_info->atom_context, data_index, NULL, &frev, &crev, &data_offset); @@ -876,28 +1000,37 @@ bool radeon_atom_get_tv_timings(struct radeon_device *rdev, int index, if (index > MAX_SUPPORTED_TV_TIMING) return false; - crtc_timing->usH_Total = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_Total); - crtc_timing->usH_Disp = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_Disp); - crtc_timing->usH_SyncStart = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_SyncStart); - crtc_timing->usH_SyncWidth = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_SyncWidth); - - crtc_timing->usV_Total = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_Total); - crtc_timing->usV_Disp = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_Disp); - crtc_timing->usV_SyncStart = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_SyncStart); - crtc_timing->usV_SyncWidth = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_SyncWidth); - - crtc_timing->susModeMiscInfo = tv_info->aModeTimings[index].susModeMiscInfo; - - crtc_timing->ucOverscanRight = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_OverscanRight); - crtc_timing->ucOverscanLeft = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_OverscanLeft); - crtc_timing->ucOverscanBottom = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_OverscanBottom); - crtc_timing->ucOverscanTop = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_OverscanTop); - *pixel_clock = le16_to_cpu(tv_info->aModeTimings[index].usPixelClock) * 10; + mode->crtc_htotal = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_Total); + mode->crtc_hdisplay = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_Disp); + mode->crtc_hsync_start = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_SyncStart); + mode->crtc_hsync_end = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_SyncStart) + + le16_to_cpu(tv_info->aModeTimings[index].usCRTC_H_SyncWidth); + + mode->crtc_vtotal = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_Total); + mode->crtc_vdisplay = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_Disp); + mode->crtc_vsync_start = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_SyncStart); + mode->crtc_vsync_end = le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_SyncStart) + + le16_to_cpu(tv_info->aModeTimings[index].usCRTC_V_SyncWidth); + + mode->flags = 0; + misc = le16_to_cpu(tv_info->aModeTimings[index].susModeMiscInfo.usAccess); + if (misc & ATOM_VSYNC_POLARITY) + mode->flags |= DRM_MODE_FLAG_NVSYNC; + if (misc & ATOM_HSYNC_POLARITY) + mode->flags |= DRM_MODE_FLAG_NHSYNC; + if (misc & ATOM_COMPOSITESYNC) + mode->flags |= DRM_MODE_FLAG_CSYNC; + if (misc & ATOM_INTERLACE) + mode->flags |= DRM_MODE_FLAG_INTERLACE; + if (misc & ATOM_DOUBLE_CLOCK_MODE) + mode->flags |= DRM_MODE_FLAG_DBLSCAN; + + mode->clock = le16_to_cpu(tv_info->aModeTimings[index].usPixelClock) * 10; if (index == 1) { /* PAL timings appear to have wrong values for totals */ - crtc_timing->usH_Total -= 1; - crtc_timing->usV_Total -= 1; + mode->crtc_htotal -= 1; + mode->crtc_vtotal -= 1; } break; case 2: @@ -906,17 +1039,36 @@ bool radeon_atom_get_tv_timings(struct radeon_device *rdev, int index, return false; dtd_timings = &tv_info_v1_2->aModeTimings[index]; - crtc_timing->usH_Total = le16_to_cpu(dtd_timings->usHActive) + le16_to_cpu(dtd_timings->usHBlanking_Time); - crtc_timing->usH_Disp = le16_to_cpu(dtd_timings->usHActive); - crtc_timing->usH_SyncStart = le16_to_cpu(dtd_timings->usHActive) + le16_to_cpu(dtd_timings->usHSyncOffset); - crtc_timing->usH_SyncWidth = le16_to_cpu(dtd_timings->usHSyncWidth); - crtc_timing->usV_Total = le16_to_cpu(dtd_timings->usVActive) + le16_to_cpu(dtd_timings->usVBlanking_Time); - crtc_timing->usV_Disp = le16_to_cpu(dtd_timings->usVActive); - crtc_timing->usV_SyncStart = le16_to_cpu(dtd_timings->usVActive) + le16_to_cpu(dtd_timings->usVSyncOffset); - crtc_timing->usV_SyncWidth = le16_to_cpu(dtd_timings->usVSyncWidth); - - crtc_timing->susModeMiscInfo.usAccess = le16_to_cpu(dtd_timings->susModeMiscInfo.usAccess); - *pixel_clock = le16_to_cpu(dtd_timings->usPixClk) * 10; + mode->crtc_htotal = le16_to_cpu(dtd_timings->usHActive) + + le16_to_cpu(dtd_timings->usHBlanking_Time); + mode->crtc_hdisplay = le16_to_cpu(dtd_timings->usHActive); + mode->crtc_hsync_start = le16_to_cpu(dtd_timings->usHActive) + + le16_to_cpu(dtd_timings->usHSyncOffset); + mode->crtc_hsync_end = mode->crtc_hsync_start + + le16_to_cpu(dtd_timings->usHSyncWidth); + + mode->crtc_vtotal = le16_to_cpu(dtd_timings->usVActive) + + le16_to_cpu(dtd_timings->usVBlanking_Time); + mode->crtc_vdisplay = le16_to_cpu(dtd_timings->usVActive); + mode->crtc_vsync_start = le16_to_cpu(dtd_timings->usVActive) + + le16_to_cpu(dtd_timings->usVSyncOffset); + mode->crtc_vsync_end = mode->crtc_vsync_start + + le16_to_cpu(dtd_timings->usVSyncWidth); + + mode->flags = 0; + misc = le16_to_cpu(dtd_timings->susModeMiscInfo.usAccess); + if (misc & ATOM_VSYNC_POLARITY) + mode->flags |= DRM_MODE_FLAG_NVSYNC; + if (misc & ATOM_HSYNC_POLARITY) + mode->flags |= DRM_MODE_FLAG_NHSYNC; + if (misc & ATOM_COMPOSITESYNC) + mode->flags |= DRM_MODE_FLAG_CSYNC; + if (misc & ATOM_INTERLACE) + mode->flags |= DRM_MODE_FLAG_INTERLACE; + if (misc & ATOM_DOUBLE_CLOCK_MODE) + mode->flags |= DRM_MODE_FLAG_DBLSCAN; + + mode->clock = le16_to_cpu(dtd_timings->usPixClk) * 10; break; } return true; @@ -981,6 +1133,24 @@ void radeon_atom_static_pwrmgt_setup(struct radeon_device *rdev, int enable) atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); } +uint32_t radeon_atom_get_engine_clock(struct radeon_device *rdev) +{ + GET_ENGINE_CLOCK_PS_ALLOCATION args; + int index = GetIndexIntoMasterTable(COMMAND, GetEngineClock); + + atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); + return args.ulReturnEngineClock; +} + +uint32_t radeon_atom_get_memory_clock(struct radeon_device *rdev) +{ + GET_MEMORY_CLOCK_PS_ALLOCATION args; + int index = GetIndexIntoMasterTable(COMMAND, GetMemoryClock); + + atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); + return args.ulReturnMemoryClock; +} + void radeon_atom_set_engine_clock(struct radeon_device *rdev, uint32_t eng_clock) { diff --git a/drivers/gpu/drm/radeon/radeon_benchmark.c b/drivers/gpu/drm/radeon/radeon_benchmark.c index 2e938f7496fb..10bd50a7db87 100644 --- a/drivers/gpu/drm/radeon/radeon_benchmark.c +++ b/drivers/gpu/drm/radeon/radeon_benchmark.c @@ -63,7 +63,7 @@ void radeon_benchmark_move(struct radeon_device *rdev, unsigned bsize, if (r) { goto out_cleanup; } - r = radeon_copy_dma(rdev, saddr, daddr, size / 4096, fence); + r = radeon_copy_dma(rdev, saddr, daddr, size / RADEON_GPU_PAGE_SIZE, fence); if (r) { goto out_cleanup; } @@ -88,7 +88,7 @@ void radeon_benchmark_move(struct radeon_device *rdev, unsigned bsize, if (r) { goto out_cleanup; } - r = radeon_copy_blit(rdev, saddr, daddr, size / 4096, fence); + r = radeon_copy_blit(rdev, saddr, daddr, size / RADEON_GPU_PAGE_SIZE, fence); if (r) { goto out_cleanup; } diff --git a/drivers/gpu/drm/radeon/radeon_bios.c b/drivers/gpu/drm/radeon/radeon_bios.c index 96e37a6e7ce4..906921740c60 100644 --- a/drivers/gpu/drm/radeon/radeon_bios.c +++ b/drivers/gpu/drm/radeon/radeon_bios.c @@ -33,12 +33,47 @@ /* * BIOS. */ + +/* If you boot an IGP board with a discrete card as the primary, + * the IGP rom is not accessible via the rom bar as the IGP rom is + * part of the system bios. On boot, the system bios puts a + * copy of the igp rom at the start of vram if a discrete card is + * present. + */ +static bool igp_read_bios_from_vram(struct radeon_device *rdev) +{ + uint8_t __iomem *bios; + resource_size_t vram_base; + resource_size_t size = 256 * 1024; /* ??? */ + + rdev->bios = NULL; + vram_base = drm_get_resource_start(rdev->ddev, 0); + bios = ioremap(vram_base, size); + if (!bios) { + return false; + } + + if (size == 0 || bios[0] != 0x55 || bios[1] != 0xaa) { + iounmap(bios); + return false; + } + rdev->bios = kmalloc(size, GFP_KERNEL); + if (rdev->bios == NULL) { + iounmap(bios); + return false; + } + memcpy(rdev->bios, bios, size); + iounmap(bios); + return true; +} + static bool radeon_read_bios(struct radeon_device *rdev) { uint8_t __iomem *bios; size_t size; rdev->bios = NULL; + /* XXX: some cards may return 0 for rom size? ddx has a workaround */ bios = pci_map_rom(rdev->pdev, &size); if (!bios) { return false; @@ -341,7 +376,9 @@ static bool legacy_read_disabled_bios(struct radeon_device *rdev) static bool radeon_read_disabled_bios(struct radeon_device *rdev) { - if (rdev->family >= CHIP_RV770) + if (rdev->flags & RADEON_IS_IGP) + return igp_read_bios_from_vram(rdev); + else if (rdev->family >= CHIP_RV770) return r700_read_disabled_bios(rdev); else if (rdev->family >= CHIP_R600) return r600_read_disabled_bios(rdev); @@ -356,7 +393,12 @@ bool radeon_get_bios(struct radeon_device *rdev) bool r; uint16_t tmp; - r = radeon_read_bios(rdev); + if (rdev->flags & RADEON_IS_IGP) { + r = igp_read_bios_from_vram(rdev); + if (r == false) + r = radeon_read_bios(rdev); + } else + r = radeon_read_bios(rdev); if (r == false) { r = radeon_read_disabled_bios(rdev); } diff --git a/drivers/gpu/drm/radeon/radeon_clocks.c b/drivers/gpu/drm/radeon/radeon_clocks.c index 152eef13197a..a81354167621 100644 --- a/drivers/gpu/drm/radeon/radeon_clocks.c +++ b/drivers/gpu/drm/radeon/radeon_clocks.c @@ -32,7 +32,7 @@ #include "atom.h" /* 10 khz */ -static uint32_t radeon_legacy_get_engine_clock(struct radeon_device *rdev) +uint32_t radeon_legacy_get_engine_clock(struct radeon_device *rdev) { struct radeon_pll *spll = &rdev->clock.spll; uint32_t fb_div, ref_div, post_div, sclk; @@ -411,7 +411,7 @@ void radeon_legacy_set_clock_gating(struct radeon_device *rdev, int enable) R300_PIXCLK_TRANS_ALWAYS_ONb | R300_PIXCLK_TVO_ALWAYS_ONb | R300_P2G2CLK_ALWAYS_ONb | - R300_P2G2CLK_ALWAYS_ONb); + R300_P2G2CLK_DAC_ALWAYS_ONb); WREG32_PLL(RADEON_PIXCLKS_CNTL, tmp); } else if (rdev->family >= CHIP_RV350) { tmp = RREG32_PLL(R300_SCLK_CNTL2); @@ -464,7 +464,7 @@ void radeon_legacy_set_clock_gating(struct radeon_device *rdev, int enable) R300_PIXCLK_TRANS_ALWAYS_ONb | R300_PIXCLK_TVO_ALWAYS_ONb | R300_P2G2CLK_ALWAYS_ONb | - R300_P2G2CLK_ALWAYS_ONb); + R300_P2G2CLK_DAC_ALWAYS_ONb); WREG32_PLL(RADEON_PIXCLKS_CNTL, tmp); tmp = RREG32_PLL(RADEON_MCLK_MISC); @@ -654,7 +654,7 @@ void radeon_legacy_set_clock_gating(struct radeon_device *rdev, int enable) R300_PIXCLK_TRANS_ALWAYS_ONb | R300_PIXCLK_TVO_ALWAYS_ONb | R300_P2G2CLK_ALWAYS_ONb | - R300_P2G2CLK_ALWAYS_ONb | + R300_P2G2CLK_DAC_ALWAYS_ONb | R300_DISP_DAC_PIXCLK_DAC2_BLANK_OFF); WREG32_PLL(RADEON_PIXCLKS_CNTL, tmp); } else if (rdev->family >= CHIP_RV350) { @@ -705,7 +705,7 @@ void radeon_legacy_set_clock_gating(struct radeon_device *rdev, int enable) R300_PIXCLK_TRANS_ALWAYS_ONb | R300_PIXCLK_TVO_ALWAYS_ONb | R300_P2G2CLK_ALWAYS_ONb | - R300_P2G2CLK_ALWAYS_ONb | + R300_P2G2CLK_DAC_ALWAYS_ONb | R300_DISP_DAC_PIXCLK_DAC2_BLANK_OFF); WREG32_PLL(RADEON_PIXCLKS_CNTL, tmp); } else { diff --git a/drivers/gpu/drm/radeon/radeon_combios.c b/drivers/gpu/drm/radeon/radeon_combios.c index 748265a105b3..5253cbf6db1f 100644 --- a/drivers/gpu/drm/radeon/radeon_combios.c +++ b/drivers/gpu/drm/radeon/radeon_combios.c @@ -49,7 +49,8 @@ radeon_add_legacy_connector(struct drm_device *dev, uint32_t connector_id, uint32_t supported_device, int connector_type, - struct radeon_i2c_bus_rec *i2c_bus); + struct radeon_i2c_bus_rec *i2c_bus, + uint16_t connector_object_id); /* from radeon_legacy_encoder.c */ extern void @@ -808,25 +809,25 @@ static struct radeon_encoder_lvds *radeon_legacy_get_lvds_info_from_regs(struct lvds->panel_blon_delay = (lvds_ss_gen_cntl >> RADEON_LVDS_PWRSEQ_DELAY2_SHIFT) & 0xf; if (fp_vert_stretch & RADEON_VERT_STRETCH_ENABLE) - lvds->native_mode.panel_yres = + lvds->native_mode.vdisplay = ((fp_vert_stretch & RADEON_VERT_PANEL_SIZE) >> RADEON_VERT_PANEL_SHIFT) + 1; else - lvds->native_mode.panel_yres = + lvds->native_mode.vdisplay = (RREG32(RADEON_CRTC_V_TOTAL_DISP) >> 16) + 1; if (fp_horz_stretch & RADEON_HORZ_STRETCH_ENABLE) - lvds->native_mode.panel_xres = + lvds->native_mode.hdisplay = (((fp_horz_stretch & RADEON_HORZ_PANEL_SIZE) >> RADEON_HORZ_PANEL_SHIFT) + 1) * 8; else - lvds->native_mode.panel_xres = + lvds->native_mode.hdisplay = ((RREG32(RADEON_CRTC_H_TOTAL_DISP) >> 16) + 1) * 8; - if ((lvds->native_mode.panel_xres < 640) || - (lvds->native_mode.panel_yres < 480)) { - lvds->native_mode.panel_xres = 640; - lvds->native_mode.panel_yres = 480; + if ((lvds->native_mode.hdisplay < 640) || + (lvds->native_mode.vdisplay < 480)) { + lvds->native_mode.hdisplay = 640; + lvds->native_mode.vdisplay = 480; } ppll_div_sel = RREG8(RADEON_CLOCK_CNTL_INDEX + 1) & 0x3; @@ -846,8 +847,8 @@ static struct radeon_encoder_lvds *radeon_legacy_get_lvds_info_from_regs(struct lvds->panel_vcc_delay = 200; DRM_INFO("Panel info derived from registers\n"); - DRM_INFO("Panel Size %dx%d\n", lvds->native_mode.panel_xres, - lvds->native_mode.panel_yres); + DRM_INFO("Panel Size %dx%d\n", lvds->native_mode.hdisplay, + lvds->native_mode.vdisplay); return lvds; } @@ -882,11 +883,11 @@ struct radeon_encoder_lvds *radeon_combios_get_lvds_info(struct radeon_encoder DRM_INFO("Panel ID String: %s\n", stmp); - lvds->native_mode.panel_xres = RBIOS16(lcd_info + 0x19); - lvds->native_mode.panel_yres = RBIOS16(lcd_info + 0x1b); + lvds->native_mode.hdisplay = RBIOS16(lcd_info + 0x19); + lvds->native_mode.vdisplay = RBIOS16(lcd_info + 0x1b); - DRM_INFO("Panel Size %dx%d\n", lvds->native_mode.panel_xres, - lvds->native_mode.panel_yres); + DRM_INFO("Panel Size %dx%d\n", lvds->native_mode.hdisplay, + lvds->native_mode.vdisplay); lvds->panel_vcc_delay = RBIOS16(lcd_info + 0x2c); if (lvds->panel_vcc_delay > 2000 || lvds->panel_vcc_delay < 0) @@ -944,27 +945,25 @@ struct radeon_encoder_lvds *radeon_combios_get_lvds_info(struct radeon_encoder if (tmp == 0) break; - if ((RBIOS16(tmp) == lvds->native_mode.panel_xres) && + if ((RBIOS16(tmp) == lvds->native_mode.hdisplay) && (RBIOS16(tmp + 2) == - lvds->native_mode.panel_yres)) { - lvds->native_mode.hblank = - (RBIOS16(tmp + 17) - RBIOS16(tmp + 19)) * 8; - lvds->native_mode.hoverplus = - (RBIOS16(tmp + 21) - RBIOS16(tmp + 19) - - 1) * 8; - lvds->native_mode.hsync_width = - RBIOS8(tmp + 23) * 8; - - lvds->native_mode.vblank = (RBIOS16(tmp + 24) - - RBIOS16(tmp + 26)); - lvds->native_mode.voverplus = - ((RBIOS16(tmp + 28) & 0x7ff) - - RBIOS16(tmp + 26)); - lvds->native_mode.vsync_width = - ((RBIOS16(tmp + 28) & 0xf800) >> 11); - lvds->native_mode.dotclock = - RBIOS16(tmp + 9) * 10; + lvds->native_mode.vdisplay)) { + lvds->native_mode.htotal = RBIOS16(tmp + 17) * 8; + lvds->native_mode.hsync_start = RBIOS16(tmp + 21) * 8; + lvds->native_mode.hsync_end = (RBIOS8(tmp + 23) + + RBIOS16(tmp + 21)) * 8; + + lvds->native_mode.vtotal = RBIOS16(tmp + 24); + lvds->native_mode.vsync_start = RBIOS16(tmp + 28) & 0x7ff; + lvds->native_mode.vsync_end = + ((RBIOS16(tmp + 28) & 0xf800) >> 11) + + (RBIOS16(tmp + 28) & 0x7ff); + + lvds->native_mode.clock = RBIOS16(tmp + 9) * 10; lvds->native_mode.flags = 0; + /* set crtc values */ + drm_mode_set_crtcinfo(&lvds->native_mode, CRTC_INTERLACE_HALVE_V); + } } } else { @@ -1178,7 +1177,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_CRT1_SUPPORT, DRM_MODE_CONNECTOR_VGA, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); } else if (rdev->flags & RADEON_IS_MOBILITY) { /* LVDS */ ddc_i2c = combios_setup_i2c_bus(RADEON_LCD_GPIO_MASK); @@ -1190,7 +1190,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_LCD1_SUPPORT, DRM_MODE_CONNECTOR_LVDS, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_LVDS); /* VGA - primary dac */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_VGA_DDC); @@ -1202,7 +1203,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_CRT1_SUPPORT, DRM_MODE_CONNECTOR_VGA, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); } else { /* DVI-I - tv dac, int tmds */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_DVI_DDC); @@ -1220,7 +1222,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_DFP1_SUPPORT | ATOM_DEVICE_CRT2_SUPPORT, DRM_MODE_CONNECTOR_DVII, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I); /* VGA - primary dac */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_VGA_DDC); @@ -1232,7 +1235,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_CRT1_SUPPORT, DRM_MODE_CONNECTOR_VGA, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); } if (rdev->family != CHIP_R100 && rdev->family != CHIP_R200) { @@ -1245,7 +1249,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) radeon_add_legacy_connector(dev, 2, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); } break; case CT_IBOOK: @@ -1259,7 +1264,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 0), ATOM_DEVICE_LCD1_SUPPORT); radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_LCD1_SUPPORT, - DRM_MODE_CONNECTOR_LVDS, &ddc_i2c); + DRM_MODE_CONNECTOR_LVDS, &ddc_i2c, + CONNECTOR_OBJECT_ID_LVDS); /* VGA - TV DAC */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_VGA_DDC); radeon_add_legacy_encoder(dev, @@ -1268,7 +1274,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 2), ATOM_DEVICE_CRT2_SUPPORT); radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_CRT2_SUPPORT, - DRM_MODE_CONNECTOR_VGA, &ddc_i2c); + DRM_MODE_CONNECTOR_VGA, &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1277,7 +1284,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 2, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; case CT_POWERBOOK_EXTERNAL: DRM_INFO("Connector Table: %d (powerbook external tmds)\n", @@ -1290,7 +1298,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 0), ATOM_DEVICE_LCD1_SUPPORT); radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_LCD1_SUPPORT, - DRM_MODE_CONNECTOR_LVDS, &ddc_i2c); + DRM_MODE_CONNECTOR_LVDS, &ddc_i2c, + CONNECTOR_OBJECT_ID_LVDS); /* DVI-I - primary dac, ext tmds */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_VGA_DDC); radeon_add_legacy_encoder(dev, @@ -1303,10 +1312,12 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_CRT1_SUPPORT, 1), ATOM_DEVICE_CRT1_SUPPORT); + /* XXX some are SL */ radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_DFP2_SUPPORT | ATOM_DEVICE_CRT1_SUPPORT, - DRM_MODE_CONNECTOR_DVII, &ddc_i2c); + DRM_MODE_CONNECTOR_DVII, &ddc_i2c, + CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_I); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1315,7 +1326,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 2, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; case CT_POWERBOOK_INTERNAL: DRM_INFO("Connector Table: %d (powerbook internal tmds)\n", @@ -1328,7 +1340,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 0), ATOM_DEVICE_LCD1_SUPPORT); radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_LCD1_SUPPORT, - DRM_MODE_CONNECTOR_LVDS, &ddc_i2c); + DRM_MODE_CONNECTOR_LVDS, &ddc_i2c, + CONNECTOR_OBJECT_ID_LVDS); /* DVI-I - primary dac, int tmds */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_VGA_DDC); radeon_add_legacy_encoder(dev, @@ -1344,7 +1357,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_DFP1_SUPPORT | ATOM_DEVICE_CRT1_SUPPORT, - DRM_MODE_CONNECTOR_DVII, &ddc_i2c); + DRM_MODE_CONNECTOR_DVII, &ddc_i2c, + CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1353,7 +1367,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 2, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; case CT_POWERBOOK_VGA: DRM_INFO("Connector Table: %d (powerbook vga)\n", @@ -1366,7 +1381,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 0), ATOM_DEVICE_LCD1_SUPPORT); radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_LCD1_SUPPORT, - DRM_MODE_CONNECTOR_LVDS, &ddc_i2c); + DRM_MODE_CONNECTOR_LVDS, &ddc_i2c, + CONNECTOR_OBJECT_ID_LVDS); /* VGA - primary dac */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_VGA_DDC); radeon_add_legacy_encoder(dev, @@ -1375,7 +1391,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 1), ATOM_DEVICE_CRT1_SUPPORT); radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_CRT1_SUPPORT, - DRM_MODE_CONNECTOR_VGA, &ddc_i2c); + DRM_MODE_CONNECTOR_VGA, &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1384,7 +1401,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 2, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; case CT_MINI_EXTERNAL: DRM_INFO("Connector Table: %d (mini external tmds)\n", @@ -1401,10 +1419,12 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_CRT2_SUPPORT, 2), ATOM_DEVICE_CRT2_SUPPORT); + /* XXX are any DL? */ radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_DFP2_SUPPORT | ATOM_DEVICE_CRT2_SUPPORT, - DRM_MODE_CONNECTOR_DVII, &ddc_i2c); + DRM_MODE_CONNECTOR_DVII, &ddc_i2c, + CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1413,7 +1433,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; case CT_MINI_INTERNAL: DRM_INFO("Connector Table: %d (mini internal tmds)\n", @@ -1433,7 +1454,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_DFP1_SUPPORT | ATOM_DEVICE_CRT2_SUPPORT, - DRM_MODE_CONNECTOR_DVII, &ddc_i2c); + DRM_MODE_CONNECTOR_DVII, &ddc_i2c, + CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1442,7 +1464,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; case CT_IMAC_G5_ISIGHT: DRM_INFO("Connector Table: %d (imac g5 isight)\n", @@ -1455,7 +1478,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 0), ATOM_DEVICE_DFP1_SUPPORT); radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_DFP1_SUPPORT, - DRM_MODE_CONNECTOR_DVID, &ddc_i2c); + DRM_MODE_CONNECTOR_DVID, &ddc_i2c, + CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_D); /* VGA - tv dac */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_DVI_DDC); radeon_add_legacy_encoder(dev, @@ -1464,7 +1488,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 2), ATOM_DEVICE_CRT2_SUPPORT); radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_CRT2_SUPPORT, - DRM_MODE_CONNECTOR_VGA, &ddc_i2c); + DRM_MODE_CONNECTOR_VGA, &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1473,7 +1498,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 2, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; case CT_EMAC: DRM_INFO("Connector Table: %d (emac)\n", @@ -1486,7 +1512,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 1), ATOM_DEVICE_CRT1_SUPPORT); radeon_add_legacy_connector(dev, 0, ATOM_DEVICE_CRT1_SUPPORT, - DRM_MODE_CONNECTOR_VGA, &ddc_i2c); + DRM_MODE_CONNECTOR_VGA, &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); /* VGA - tv dac */ ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_CRT2_DDC); radeon_add_legacy_encoder(dev, @@ -1495,7 +1522,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) 2), ATOM_DEVICE_CRT2_SUPPORT); radeon_add_legacy_connector(dev, 1, ATOM_DEVICE_CRT2_SUPPORT, - DRM_MODE_CONNECTOR_VGA, &ddc_i2c); + DRM_MODE_CONNECTOR_VGA, &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); /* TV - TV DAC */ radeon_add_legacy_encoder(dev, radeon_get_encoder_id(dev, @@ -1504,7 +1532,8 @@ bool radeon_get_legacy_connector_info_from_table(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT); radeon_add_legacy_connector(dev, 2, ATOM_DEVICE_TV1_SUPPORT, DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; default: DRM_INFO("Connector table: %d (invalid)\n", @@ -1581,11 +1610,63 @@ static bool radeon_apply_legacy_quirks(struct drm_device *dev, return true; } +static bool radeon_apply_legacy_tv_quirks(struct drm_device *dev) +{ + /* Acer 5102 has non-existent TV port */ + if (dev->pdev->device == 0x5975 && + dev->pdev->subsystem_vendor == 0x1025 && + dev->pdev->subsystem_device == 0x009f) + return false; + + /* HP dc5750 has non-existent TV port */ + if (dev->pdev->device == 0x5974 && + dev->pdev->subsystem_vendor == 0x103c && + dev->pdev->subsystem_device == 0x280a) + return false; + + return true; +} + +static uint16_t combios_check_dl_dvi(struct drm_device *dev, int is_dvi_d) +{ + struct radeon_device *rdev = dev->dev_private; + uint32_t ext_tmds_info; + + if (rdev->flags & RADEON_IS_IGP) { + if (is_dvi_d) + return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_D; + else + return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I; + } + ext_tmds_info = combios_get_table_offset(dev, COMBIOS_EXT_TMDS_INFO_TABLE); + if (ext_tmds_info) { + uint8_t rev = RBIOS8(ext_tmds_info); + uint8_t flags = RBIOS8(ext_tmds_info + 4 + 5); + if (rev >= 3) { + if (is_dvi_d) + return CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_D; + else + return CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_I; + } else { + if (flags & 1) { + if (is_dvi_d) + return CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_D; + else + return CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_I; + } + } + } + if (is_dvi_d) + return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_D; + else + return CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I; +} + bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) { struct radeon_device *rdev = dev->dev_private; uint32_t conn_info, entry, devices; - uint16_t tmp; + uint16_t tmp, connector_object_id; enum radeon_combios_ddc ddc_type; enum radeon_combios_connector connector; int i = 0; @@ -1628,8 +1709,9 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) break; } - radeon_apply_legacy_quirks(dev, i, &connector, - &ddc_i2c); + if (!radeon_apply_legacy_quirks(dev, i, &connector, + &ddc_i2c)) + continue; switch (connector) { case CONNECTOR_PROPRIETARY_LEGACY: @@ -1644,7 +1726,8 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) radeon_add_legacy_connector(dev, i, devices, legacy_connector_convert [connector], - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_D); break; case CONNECTOR_CRT_LEGACY: if (tmp & 0x1) { @@ -1669,7 +1752,8 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) devices, legacy_connector_convert [connector], - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); break; case CONNECTOR_DVI_I_LEGACY: devices = 0; @@ -1698,6 +1782,7 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) ATOM_DEVICE_DFP2_SUPPORT, 0), ATOM_DEVICE_DFP2_SUPPORT); + connector_object_id = combios_check_dl_dvi(dev, 0); } else { devices |= ATOM_DEVICE_DFP1_SUPPORT; radeon_add_legacy_encoder(dev, @@ -1706,19 +1791,24 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) ATOM_DEVICE_DFP1_SUPPORT, 0), ATOM_DEVICE_DFP1_SUPPORT); + connector_object_id = CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I; } radeon_add_legacy_connector(dev, i, devices, legacy_connector_convert [connector], - &ddc_i2c); + &ddc_i2c, + connector_object_id); break; case CONNECTOR_DVI_D_LEGACY: - if ((tmp >> 4) & 0x1) + if ((tmp >> 4) & 0x1) { devices = ATOM_DEVICE_DFP2_SUPPORT; - else + connector_object_id = combios_check_dl_dvi(dev, 1); + } else { devices = ATOM_DEVICE_DFP1_SUPPORT; + connector_object_id = CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I; + } radeon_add_legacy_encoder(dev, radeon_get_encoder_id (dev, devices, 0), @@ -1726,7 +1816,8 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) radeon_add_legacy_connector(dev, i, devices, legacy_connector_convert [connector], - &ddc_i2c); + &ddc_i2c, + connector_object_id); break; case CONNECTOR_CTV_LEGACY: case CONNECTOR_STV_LEGACY: @@ -1740,7 +1831,8 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) ATOM_DEVICE_TV1_SUPPORT, legacy_connector_convert [connector], - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); break; default: DRM_ERROR("Unknown connector type: %d\n", @@ -1772,10 +1864,29 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) ATOM_DEVICE_CRT1_SUPPORT | ATOM_DEVICE_DFP1_SUPPORT, DRM_MODE_CONNECTOR_DVII, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_SINGLE_LINK_DVI_I); } else { - DRM_DEBUG("No connector info found\n"); - return false; + uint16_t crt_info = + combios_get_table_offset(dev, COMBIOS_CRT_INFO_TABLE); + DRM_DEBUG("Found CRT table, assuming VGA connector\n"); + if (crt_info) { + radeon_add_legacy_encoder(dev, + radeon_get_encoder_id(dev, + ATOM_DEVICE_CRT1_SUPPORT, + 1), + ATOM_DEVICE_CRT1_SUPPORT); + ddc_i2c = combios_setup_i2c_bus(RADEON_GPIO_VGA_DDC); + radeon_add_legacy_connector(dev, + 0, + ATOM_DEVICE_CRT1_SUPPORT, + DRM_MODE_CONNECTOR_VGA, + &ddc_i2c, + CONNECTOR_OBJECT_ID_VGA); + } else { + DRM_DEBUG("No connector info found\n"); + return false; + } } } @@ -1870,7 +1981,8 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) 5, ATOM_DEVICE_LCD1_SUPPORT, DRM_MODE_CONNECTOR_LVDS, - &ddc_i2c); + &ddc_i2c, + CONNECTOR_OBJECT_ID_LVDS); } } @@ -1880,16 +1992,19 @@ bool radeon_get_legacy_connector_info_from_bios(struct drm_device *dev) combios_get_table_offset(dev, COMBIOS_TV_INFO_TABLE); if (tv_info) { if (RBIOS8(tv_info + 6) == 'T') { - radeon_add_legacy_encoder(dev, - radeon_get_encoder_id - (dev, - ATOM_DEVICE_TV1_SUPPORT, - 2), - ATOM_DEVICE_TV1_SUPPORT); - radeon_add_legacy_connector(dev, 6, - ATOM_DEVICE_TV1_SUPPORT, - DRM_MODE_CONNECTOR_SVIDEO, - &ddc_i2c); + if (radeon_apply_legacy_tv_quirks(dev)) { + radeon_add_legacy_encoder(dev, + radeon_get_encoder_id + (dev, + ATOM_DEVICE_TV1_SUPPORT, + 2), + ATOM_DEVICE_TV1_SUPPORT); + radeon_add_legacy_connector(dev, 6, + ATOM_DEVICE_TV1_SUPPORT, + DRM_MODE_CONNECTOR_SVIDEO, + &ddc_i2c, + CONNECTOR_OBJECT_ID_SVIDEO); + } } } } diff --git a/drivers/gpu/drm/radeon/radeon_connectors.c b/drivers/gpu/drm/radeon/radeon_connectors.c index e376be47a4a0..fce4c4087fda 100644 --- a/drivers/gpu/drm/radeon/radeon_connectors.c +++ b/drivers/gpu/drm/radeon/radeon_connectors.c @@ -178,25 +178,12 @@ static struct drm_display_mode *radeon_fp_native_mode(struct drm_encoder *encode struct drm_device *dev = encoder->dev; struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); struct drm_display_mode *mode = NULL; - struct radeon_native_mode *native_mode = &radeon_encoder->native_mode; - - if (native_mode->panel_xres != 0 && - native_mode->panel_yres != 0 && - native_mode->dotclock != 0) { - mode = drm_mode_create(dev); - - mode->hdisplay = native_mode->panel_xres; - mode->vdisplay = native_mode->panel_yres; - - mode->htotal = mode->hdisplay + native_mode->hblank; - mode->hsync_start = mode->hdisplay + native_mode->hoverplus; - mode->hsync_end = mode->hsync_start + native_mode->hsync_width; - mode->vtotal = mode->vdisplay + native_mode->vblank; - mode->vsync_start = mode->vdisplay + native_mode->voverplus; - mode->vsync_end = mode->vsync_start + native_mode->vsync_width; - mode->clock = native_mode->dotclock; - mode->flags = 0; + struct drm_display_mode *native_mode = &radeon_encoder->native_mode; + if (native_mode->hdisplay != 0 && + native_mode->vdisplay != 0 && + native_mode->clock != 0) { + mode = drm_mode_duplicate(dev, native_mode); mode->type = DRM_MODE_TYPE_PREFERRED | DRM_MODE_TYPE_DRIVER; drm_mode_set_name(mode); @@ -210,7 +197,7 @@ static void radeon_add_common_modes(struct drm_encoder *encoder, struct drm_conn struct drm_device *dev = encoder->dev; struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); struct drm_display_mode *mode = NULL; - struct radeon_native_mode *native_mode = &radeon_encoder->native_mode; + struct drm_display_mode *native_mode = &radeon_encoder->native_mode; int i; struct mode_size { int w; @@ -236,11 +223,16 @@ static void radeon_add_common_modes(struct drm_encoder *encoder, struct drm_conn }; for (i = 0; i < 17; i++) { + if (radeon_encoder->devices & (ATOM_DEVICE_TV_SUPPORT)) { + if (common_modes[i].w > 1024 || + common_modes[i].h > 768) + continue; + } if (radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT)) { - if (common_modes[i].w > native_mode->panel_xres || - common_modes[i].h > native_mode->panel_yres || - (common_modes[i].w == native_mode->panel_xres && - common_modes[i].h == native_mode->panel_yres)) + if (common_modes[i].w > native_mode->hdisplay || + common_modes[i].h > native_mode->vdisplay || + (common_modes[i].w == native_mode->hdisplay && + common_modes[i].h == native_mode->vdisplay)) continue; } if (common_modes[i].w < 320 || common_modes[i].h < 200) @@ -344,28 +336,23 @@ static void radeon_fixup_lvds_native_mode(struct drm_encoder *encoder, struct drm_connector *connector) { struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); - struct radeon_native_mode *native_mode = &radeon_encoder->native_mode; + struct drm_display_mode *native_mode = &radeon_encoder->native_mode; /* Try to get native mode details from EDID if necessary */ - if (!native_mode->dotclock) { + if (!native_mode->clock) { struct drm_display_mode *t, *mode; list_for_each_entry_safe(mode, t, &connector->probed_modes, head) { - if (mode->hdisplay == native_mode->panel_xres && - mode->vdisplay == native_mode->panel_yres) { - native_mode->hblank = mode->htotal - mode->hdisplay; - native_mode->hoverplus = mode->hsync_start - mode->hdisplay; - native_mode->hsync_width = mode->hsync_end - mode->hsync_start; - native_mode->vblank = mode->vtotal - mode->vdisplay; - native_mode->voverplus = mode->vsync_start - mode->vdisplay; - native_mode->vsync_width = mode->vsync_end - mode->vsync_start; - native_mode->dotclock = mode->clock; + if (mode->hdisplay == native_mode->hdisplay && + mode->vdisplay == native_mode->vdisplay) { + *native_mode = *mode; + drm_mode_set_crtcinfo(native_mode, CRTC_INTERLACE_HALVE_V); DRM_INFO("Determined LVDS native mode details from EDID\n"); break; } } } - if (!native_mode->dotclock) { + if (!native_mode->clock) { DRM_INFO("No LVDS native mode details, disabling RMX\n"); radeon_encoder->rmx_type = RMX_OFF; } @@ -410,13 +397,64 @@ static int radeon_lvds_get_modes(struct drm_connector *connector) static int radeon_lvds_mode_valid(struct drm_connector *connector, struct drm_display_mode *mode) { + struct drm_encoder *encoder = radeon_best_single_encoder(connector); + + if ((mode->hdisplay < 320) || (mode->vdisplay < 240)) + return MODE_PANEL; + + if (encoder) { + struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); + struct drm_display_mode *native_mode = &radeon_encoder->native_mode; + + /* AVIVO hardware supports downscaling modes larger than the panel + * to the panel size, but I'm not sure this is desirable. + */ + if ((mode->hdisplay > native_mode->hdisplay) || + (mode->vdisplay > native_mode->vdisplay)) + return MODE_PANEL; + + /* if scaling is disabled, block non-native modes */ + if (radeon_encoder->rmx_type == RMX_OFF) { + if ((mode->hdisplay != native_mode->hdisplay) || + (mode->vdisplay != native_mode->vdisplay)) + return MODE_PANEL; + } + } + return MODE_OK; } static enum drm_connector_status radeon_lvds_detect(struct drm_connector *connector) { - enum drm_connector_status ret = connector_status_connected; + struct radeon_connector *radeon_connector = to_radeon_connector(connector); + struct drm_encoder *encoder = radeon_best_single_encoder(connector); + enum drm_connector_status ret = connector_status_disconnected; + + if (encoder) { + struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); + struct drm_display_mode *native_mode = &radeon_encoder->native_mode; + + /* check if panel is valid */ + if (native_mode->hdisplay >= 320 && native_mode->vdisplay >= 240) + ret = connector_status_connected; + + } + + /* check for edid as well */ + if (radeon_connector->edid) + ret = connector_status_connected; + else { + if (radeon_connector->ddc_bus) { + radeon_i2c_do_lock(radeon_connector, 1); + radeon_connector->edid = drm_get_edid(&radeon_connector->base, + &radeon_connector->ddc_bus->adapter); + radeon_i2c_do_lock(radeon_connector, 0); + if (radeon_connector->edid) + ret = connector_status_connected; + } + } /* check acpi lid status ??? */ + radeon_connector_update_scratch_regs(connector, ret); return ret; } @@ -427,6 +465,8 @@ static void radeon_connector_destroy(struct drm_connector *connector) if (radeon_connector->ddc_bus) radeon_i2c_destroy(radeon_connector->ddc_bus); + if (radeon_connector->edid) + kfree(radeon_connector->edid); kfree(radeon_connector->con_priv); drm_sysfs_connector_remove(connector); drm_connector_cleanup(connector); @@ -496,6 +536,8 @@ static int radeon_vga_get_modes(struct drm_connector *connector) static int radeon_vga_mode_valid(struct drm_connector *connector, struct drm_display_mode *mode) { + /* XXX check mode bandwidth */ + /* XXX verify against max DAC output frequency */ return MODE_OK; } @@ -514,9 +556,32 @@ static enum drm_connector_status radeon_vga_detect(struct drm_connector *connect radeon_i2c_do_lock(radeon_connector, 1); dret = radeon_ddc_probe(radeon_connector); radeon_i2c_do_lock(radeon_connector, 0); - if (dret) - ret = connector_status_connected; - else { + if (dret) { + if (radeon_connector->edid) { + kfree(radeon_connector->edid); + radeon_connector->edid = NULL; + } + radeon_i2c_do_lock(radeon_connector, 1); + radeon_connector->edid = drm_get_edid(&radeon_connector->base, &radeon_connector->ddc_bus->adapter); + radeon_i2c_do_lock(radeon_connector, 0); + + if (!radeon_connector->edid) { + DRM_ERROR("DDC responded but not EDID found for %s\n", + drm_get_connector_name(connector)); + } else { + radeon_connector->use_digital = !!(radeon_connector->edid->input & DRM_EDID_INPUT_DIGITAL); + + /* some oems have boards with separate digital and analog connectors + * with a shared ddc line (often vga + hdmi) + */ + if (radeon_connector->use_digital && radeon_connector->shared_ddc) { + kfree(radeon_connector->edid); + radeon_connector->edid = NULL; + ret = connector_status_disconnected; + } else + ret = connector_status_connected; + } + } else { if (radeon_connector->dac_load_detect) { encoder_funcs = encoder->helper_private; ret = encoder_funcs->detect(encoder, connector); @@ -570,6 +635,8 @@ static int radeon_tv_get_modes(struct drm_connector *connector) static int radeon_tv_mode_valid(struct drm_connector *connector, struct drm_display_mode *mode) { + if ((mode->hdisplay > 1024) || (mode->vdisplay > 768)) + return MODE_CLOCK_RANGE; return MODE_OK; } @@ -644,6 +711,10 @@ static enum drm_connector_status radeon_dvi_detect(struct drm_connector *connect dret = radeon_ddc_probe(radeon_connector); radeon_i2c_do_lock(radeon_connector, 0); if (dret) { + if (radeon_connector->edid) { + kfree(radeon_connector->edid); + radeon_connector->edid = NULL; + } radeon_i2c_do_lock(radeon_connector, 1); radeon_connector->edid = drm_get_edid(&radeon_connector->base, &radeon_connector->ddc_bus->adapter); radeon_i2c_do_lock(radeon_connector, 0); @@ -654,10 +725,15 @@ static enum drm_connector_status radeon_dvi_detect(struct drm_connector *connect } else { radeon_connector->use_digital = !!(radeon_connector->edid->input & DRM_EDID_INPUT_DIGITAL); - /* if this isn't a digital monitor - then we need to make sure we don't have any - TV conflicts */ - ret = connector_status_connected; + /* some oems have boards with separate digital and analog connectors + * with a shared ddc line (often vga + hdmi) + */ + if ((!radeon_connector->use_digital) && radeon_connector->shared_ddc) { + kfree(radeon_connector->edid); + radeon_connector->edid = NULL; + ret = connector_status_disconnected; + } else + ret = connector_status_connected; } } @@ -753,9 +829,27 @@ static void radeon_dvi_force(struct drm_connector *connector) radeon_connector->use_digital = true; } +static int radeon_dvi_mode_valid(struct drm_connector *connector, + struct drm_display_mode *mode) +{ + struct radeon_connector *radeon_connector = to_radeon_connector(connector); + + /* XXX check mode bandwidth */ + + if (radeon_connector->use_digital && (mode->clock > 165000)) { + if ((radeon_connector->connector_object_id == CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_I) || + (radeon_connector->connector_object_id == CONNECTOR_OBJECT_ID_DUAL_LINK_DVI_D) || + (radeon_connector->connector_object_id == CONNECTOR_OBJECT_ID_HDMI_TYPE_B)) + return MODE_OK; + else + return MODE_CLOCK_HIGH; + } + return MODE_OK; +} + struct drm_connector_helper_funcs radeon_dvi_connector_helper_funcs = { .get_modes = radeon_dvi_get_modes, - .mode_valid = radeon_vga_mode_valid, + .mode_valid = radeon_dvi_mode_valid, .best_encoder = radeon_dvi_encoder, }; @@ -775,13 +869,15 @@ radeon_add_atom_connector(struct drm_device *dev, int connector_type, struct radeon_i2c_bus_rec *i2c_bus, bool linkb, - uint32_t igp_lane_info) + uint32_t igp_lane_info, + uint16_t connector_object_id) { struct radeon_device *rdev = dev->dev_private; struct drm_connector *connector; struct radeon_connector *radeon_connector; struct radeon_connector_atom_dig *radeon_dig_connector; uint32_t subpixel_order = SubPixelNone; + bool shared_ddc = false; int ret; /* fixme - tv/cv/din */ @@ -795,6 +891,13 @@ radeon_add_atom_connector(struct drm_device *dev, radeon_connector->devices |= supported_device; return; } + if (radeon_connector->ddc_bus && i2c_bus->valid) { + if (memcmp(&radeon_connector->ddc_bus->rec, i2c_bus, + sizeof(struct radeon_i2c_bus_rec)) == 0) { + radeon_connector->shared_ddc = true; + shared_ddc = true; + } + } } radeon_connector = kzalloc(sizeof(struct radeon_connector), GFP_KERNEL); @@ -805,6 +908,8 @@ radeon_add_atom_connector(struct drm_device *dev, radeon_connector->connector_id = connector_id; radeon_connector->devices = supported_device; + radeon_connector->shared_ddc = shared_ddc; + radeon_connector->connector_object_id = connector_object_id; switch (connector_type) { case DRM_MODE_CONNECTOR_VGA: drm_connector_init(dev, &radeon_connector->base, &radeon_vga_connector_funcs, connector_type); @@ -956,7 +1061,8 @@ radeon_add_legacy_connector(struct drm_device *dev, uint32_t connector_id, uint32_t supported_device, int connector_type, - struct radeon_i2c_bus_rec *i2c_bus) + struct radeon_i2c_bus_rec *i2c_bus, + uint16_t connector_object_id) { struct radeon_device *rdev = dev->dev_private; struct drm_connector *connector; @@ -985,6 +1091,7 @@ radeon_add_legacy_connector(struct drm_device *dev, radeon_connector->connector_id = connector_id; radeon_connector->devices = supported_device; + radeon_connector->connector_object_id = connector_object_id; switch (connector_type) { case DRM_MODE_CONNECTOR_VGA: drm_connector_init(dev, &radeon_connector->base, &radeon_vga_connector_funcs, connector_type); diff --git a/drivers/gpu/drm/radeon/radeon_cursor.c b/drivers/gpu/drm/radeon/radeon_cursor.c index b13c79e38bc0..28772a37009c 100644 --- a/drivers/gpu/drm/radeon/radeon_cursor.c +++ b/drivers/gpu/drm/radeon/radeon_cursor.c @@ -109,9 +109,15 @@ static void radeon_set_cursor(struct drm_crtc *crtc, struct drm_gem_object *obj, struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); struct radeon_device *rdev = crtc->dev->dev_private; - if (ASIC_IS_AVIVO(rdev)) + if (ASIC_IS_AVIVO(rdev)) { + if (rdev->family >= CHIP_RV770) { + if (radeon_crtc->crtc_id) + WREG32(R700_D2CUR_SURFACE_ADDRESS_HIGH, 0); + else + WREG32(R700_D1CUR_SURFACE_ADDRESS_HIGH, 0); + } WREG32(AVIVO_D1CUR_SURFACE_ADDRESS + radeon_crtc->crtc_offset, gpu_addr); - else { + } else { radeon_crtc->legacy_cursor_offset = gpu_addr - radeon_crtc->legacy_display_base_addr; /* offset is from DISP(2)_BASE_ADDRESS */ WREG32(RADEON_CUR_OFFSET + radeon_crtc->crtc_offset, radeon_crtc->legacy_cursor_offset); diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c index ec835d56d30a..e3f9edfa40fe 100644 --- a/drivers/gpu/drm/radeon/radeon_device.c +++ b/drivers/gpu/drm/radeon/radeon_device.c @@ -322,10 +322,6 @@ int radeon_asic_init(struct radeon_device *rdev) case CHIP_RV380: rdev->asic = &r300_asic; if (rdev->flags & RADEON_IS_PCIE) { - rdev->asic->gart_init = &rv370_pcie_gart_init; - rdev->asic->gart_fini = &rv370_pcie_gart_fini; - rdev->asic->gart_enable = &rv370_pcie_gart_enable; - rdev->asic->gart_disable = &rv370_pcie_gart_disable; rdev->asic->gart_tlb_flush = &rv370_pcie_gart_tlb_flush; rdev->asic->gart_set_page = &rv370_pcie_gart_set_page; } @@ -448,20 +444,24 @@ static uint32_t cail_reg_read(struct card_info *info, uint32_t reg) return r; } -static struct card_info atom_card_info = { - .dev = NULL, - .reg_read = cail_reg_read, - .reg_write = cail_reg_write, - .mc_read = cail_mc_read, - .mc_write = cail_mc_write, - .pll_read = cail_pll_read, - .pll_write = cail_pll_write, -}; - int radeon_atombios_init(struct radeon_device *rdev) { - atom_card_info.dev = rdev->ddev; - rdev->mode_info.atom_context = atom_parse(&atom_card_info, rdev->bios); + struct card_info *atom_card_info = + kzalloc(sizeof(struct card_info), GFP_KERNEL); + + if (!atom_card_info) + return -ENOMEM; + + rdev->mode_info.atom_card_info = atom_card_info; + atom_card_info->dev = rdev->ddev; + atom_card_info->reg_read = cail_reg_read; + atom_card_info->reg_write = cail_reg_write; + atom_card_info->mc_read = cail_mc_read; + atom_card_info->mc_write = cail_mc_write; + atom_card_info->pll_read = cail_pll_read; + atom_card_info->pll_write = cail_pll_write; + + rdev->mode_info.atom_context = atom_parse(atom_card_info, rdev->bios); radeon_atom_initialize_bios_scratch_regs(rdev->ddev); return 0; } @@ -469,6 +469,7 @@ int radeon_atombios_init(struct radeon_device *rdev) void radeon_atombios_fini(struct radeon_device *rdev) { kfree(rdev->mode_info.atom_context); + kfree(rdev->mode_info.atom_card_info); } int radeon_combios_init(struct radeon_device *rdev) @@ -485,7 +486,6 @@ void radeon_combios_fini(struct radeon_device *rdev) static unsigned int radeon_vga_set_decode(void *cookie, bool state) { struct radeon_device *rdev = cookie; - radeon_vga_set_state(rdev, state); if (state) return VGA_RSRC_LEGACY_IO | VGA_RSRC_LEGACY_MEM | @@ -493,6 +493,29 @@ static unsigned int radeon_vga_set_decode(void *cookie, bool state) else return VGA_RSRC_NORMAL_IO | VGA_RSRC_NORMAL_MEM; } + +void radeon_agp_disable(struct radeon_device *rdev) +{ + rdev->flags &= ~RADEON_IS_AGP; + if (rdev->family >= CHIP_R600) { + DRM_INFO("Forcing AGP to PCIE mode\n"); + rdev->flags |= RADEON_IS_PCIE; + } else if (rdev->family >= CHIP_RV515 || + rdev->family == CHIP_RV380 || + rdev->family == CHIP_RV410 || + rdev->family == CHIP_R423) { + DRM_INFO("Forcing AGP to PCIE mode\n"); + rdev->flags |= RADEON_IS_PCIE; + rdev->asic->gart_tlb_flush = &rv370_pcie_gart_tlb_flush; + rdev->asic->gart_set_page = &rv370_pcie_gart_set_page; + } else { + DRM_INFO("Forcing AGP to PCI mode\n"); + rdev->flags |= RADEON_IS_PCI; + rdev->asic->gart_tlb_flush = &r100_pci_gart_tlb_flush; + rdev->asic->gart_set_page = &r100_pci_gart_set_page; + } +} + /* * Radeon device. */ @@ -531,32 +554,7 @@ int radeon_device_init(struct radeon_device *rdev, } if (radeon_agpmode == -1) { - rdev->flags &= ~RADEON_IS_AGP; - if (rdev->family >= CHIP_R600) { - DRM_INFO("Forcing AGP to PCIE mode\n"); - rdev->flags |= RADEON_IS_PCIE; - } else if (rdev->family >= CHIP_RV515 || - rdev->family == CHIP_RV380 || - rdev->family == CHIP_RV410 || - rdev->family == CHIP_R423) { - DRM_INFO("Forcing AGP to PCIE mode\n"); - rdev->flags |= RADEON_IS_PCIE; - rdev->asic->gart_init = &rv370_pcie_gart_init; - rdev->asic->gart_fini = &rv370_pcie_gart_fini; - rdev->asic->gart_enable = &rv370_pcie_gart_enable; - rdev->asic->gart_disable = &rv370_pcie_gart_disable; - rdev->asic->gart_tlb_flush = &rv370_pcie_gart_tlb_flush; - rdev->asic->gart_set_page = &rv370_pcie_gart_set_page; - } else { - DRM_INFO("Forcing AGP to PCI mode\n"); - rdev->flags |= RADEON_IS_PCI; - rdev->asic->gart_init = &r100_pci_gart_init; - rdev->asic->gart_fini = &r100_pci_gart_fini; - rdev->asic->gart_enable = &r100_pci_gart_enable; - rdev->asic->gart_disable = &r100_pci_gart_disable; - rdev->asic->gart_tlb_flush = &r100_pci_gart_tlb_flush; - rdev->asic->gart_set_page = &r100_pci_gart_set_page; - } + radeon_agp_disable(rdev); } /* set DMA mask + need_dma32 flags. @@ -588,111 +586,26 @@ int radeon_device_init(struct radeon_device *rdev, DRM_INFO("register mmio base: 0x%08X\n", (uint32_t)rdev->rmmio_base); DRM_INFO("register mmio size: %u\n", (unsigned)rdev->rmmio_size); - rdev->new_init_path = false; - r = radeon_init(rdev); - if (r) { - return r; - } - /* if we have > 1 VGA cards, then disable the radeon VGA resources */ - r = vga_client_register(rdev->pdev, rdev, NULL, radeon_vga_set_decode); - if (r) { - return -EINVAL; - } + /* this will fail for cards that aren't VGA class devices, just + * ignore it */ + vga_client_register(rdev->pdev, rdev, NULL, radeon_vga_set_decode); - if (!rdev->new_init_path) { - /* Setup errata flags */ - radeon_errata(rdev); - /* Initialize scratch registers */ - radeon_scratch_init(rdev); - /* Initialize surface registers */ - radeon_surface_init(rdev); - - /* BIOS*/ - if (!radeon_get_bios(rdev)) { - if (ASIC_IS_AVIVO(rdev)) - return -EINVAL; - } - if (rdev->is_atom_bios) { - r = radeon_atombios_init(rdev); - if (r) { - return r; - } - } else { - r = radeon_combios_init(rdev); - if (r) { - return r; - } - } - /* Reset gpu before posting otherwise ATOM will enter infinite loop */ - if (radeon_gpu_reset(rdev)) { - /* FIXME: what do we want to do here ? */ - } - /* check if cards are posted or not */ - if (!radeon_card_posted(rdev) && rdev->bios) { - DRM_INFO("GPU not posted. posting now...\n"); - if (rdev->is_atom_bios) { - atom_asic_init(rdev->mode_info.atom_context); - } else { - radeon_combios_asic_init(rdev->ddev); - } - } - /* Get clock & vram information */ - radeon_get_clock_info(rdev->ddev); - radeon_vram_info(rdev); - /* Initialize clocks */ - r = radeon_clocks_init(rdev); - if (r) { - return r; - } + r = radeon_init(rdev); + if (r) + return r; - /* Initialize memory controller (also test AGP) */ - r = radeon_mc_init(rdev); - if (r) { - return r; - } - /* Fence driver */ - r = radeon_fence_driver_init(rdev); - if (r) { - return r; - } - r = radeon_irq_kms_init(rdev); - if (r) { - return r; - } - /* Memory manager */ - r = radeon_object_init(rdev); - if (r) { - return r; - } - r = radeon_gpu_gart_init(rdev); + if (rdev->flags & RADEON_IS_AGP && !rdev->accel_working) { + /* Acceleration not working on AGP card try again + * with fallback to PCI or PCIE GART + */ + radeon_gpu_reset(rdev); + radeon_fini(rdev); + radeon_agp_disable(rdev); + r = radeon_init(rdev); if (r) return r; - /* Initialize GART (initialize after TTM so we can allocate - * memory through TTM but finalize after TTM) */ - r = radeon_gart_enable(rdev); - if (r) - return 0; - r = radeon_gem_init(rdev); - if (r) - return 0; - - /* 1M ring buffer */ - r = radeon_cp_init(rdev, 1024 * 1024); - if (r) - return 0; - r = radeon_wb_init(rdev); - if (r) - DRM_ERROR("radeon: failled initializing WB (%d).\n", r); - r = radeon_ib_pool_init(rdev); - if (r) - return 0; - r = radeon_ib_test(rdev); - if (r) - return 0; - rdev->accel_working = true; } - DRM_INFO("radeon: kernel modesetting successfully initialized.\n"); if (radeon_testing) { radeon_test_moves(rdev); } @@ -706,32 +619,8 @@ void radeon_device_fini(struct radeon_device *rdev) { DRM_INFO("radeon: finishing device.\n"); rdev->shutdown = true; - /* Order matter so becarefull if you rearrange anythings */ - if (!rdev->new_init_path) { - radeon_ib_pool_fini(rdev); - radeon_cp_fini(rdev); - radeon_wb_fini(rdev); - radeon_gpu_gart_fini(rdev); - radeon_gem_fini(rdev); - radeon_mc_fini(rdev); -#if __OS_HAS_AGP - radeon_agp_fini(rdev); -#endif - radeon_irq_kms_fini(rdev); - vga_client_register(rdev->pdev, NULL, NULL, NULL); - radeon_fence_driver_fini(rdev); - radeon_clocks_fini(rdev); - radeon_object_fini(rdev); - if (rdev->is_atom_bios) { - radeon_atombios_fini(rdev); - } else { - radeon_combios_fini(rdev); - } - kfree(rdev->bios); - rdev->bios = NULL; - } else { - radeon_fini(rdev); - } + radeon_fini(rdev); + vga_client_register(rdev->pdev, NULL, NULL, NULL); iounmap(rdev->rmmio); rdev->rmmio = NULL; } @@ -771,14 +660,7 @@ int radeon_suspend_kms(struct drm_device *dev, pm_message_t state) radeon_save_bios_scratch_regs(rdev); - if (!rdev->new_init_path) { - radeon_cp_disable(rdev); - radeon_gart_disable(rdev); - rdev->irq.sw_int = false; - radeon_irq_set(rdev); - } else { - radeon_suspend(rdev); - } + radeon_suspend(rdev); /* evict remaining vram memory */ radeon_object_evict_vram(rdev); @@ -797,7 +679,6 @@ int radeon_suspend_kms(struct drm_device *dev, pm_message_t state) int radeon_resume_kms(struct drm_device *dev) { struct radeon_device *rdev = dev->dev_private; - int r; acquire_console_sem(); pci_set_power_state(dev->pdev, PCI_D0); @@ -807,43 +688,7 @@ int radeon_resume_kms(struct drm_device *dev) return -1; } pci_set_master(dev->pdev); - /* Reset gpu before posting otherwise ATOM will enter infinite loop */ - if (!rdev->new_init_path) { - if (radeon_gpu_reset(rdev)) { - /* FIXME: what do we want to do here ? */ - } - /* post card */ - if (rdev->is_atom_bios) { - atom_asic_init(rdev->mode_info.atom_context); - } else { - radeon_combios_asic_init(rdev->ddev); - } - /* Initialize clocks */ - r = radeon_clocks_init(rdev); - if (r) { - release_console_sem(); - return r; - } - /* Enable IRQ */ - rdev->irq.sw_int = true; - radeon_irq_set(rdev); - /* Initialize GPU Memory Controller */ - r = radeon_mc_init(rdev); - if (r) { - goto out; - } - r = radeon_gart_enable(rdev); - if (r) { - goto out; - } - r = radeon_cp_init(rdev, rdev->cp.ring_size); - if (r) { - goto out; - } - } else { - radeon_resume(rdev); - } -out: + radeon_resume(rdev); radeon_restore_bios_scratch_regs(rdev); fb_set_suspend(rdev->fbdev_info, 0); release_console_sem(); diff --git a/drivers/gpu/drm/radeon/radeon_display.c b/drivers/gpu/drm/radeon/radeon_display.c index 5d8141b13765..c85df4afcb7a 100644 --- a/drivers/gpu/drm/radeon/radeon_display.c +++ b/drivers/gpu/drm/radeon/radeon_display.c @@ -106,51 +106,44 @@ void radeon_crtc_load_lut(struct drm_crtc *crtc) legacy_crtc_load_lut(crtc); } -/** Sets the color ramps on behalf of RandR */ +/** Sets the color ramps on behalf of fbcon */ void radeon_crtc_fb_gamma_set(struct drm_crtc *crtc, u16 red, u16 green, u16 blue, int regno) { struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); - if (regno == 0) - DRM_DEBUG("gamma set %d\n", radeon_crtc->crtc_id); radeon_crtc->lut_r[regno] = red >> 6; radeon_crtc->lut_g[regno] = green >> 6; radeon_crtc->lut_b[regno] = blue >> 6; } +/** Gets the color ramps on behalf of fbcon */ +void radeon_crtc_fb_gamma_get(struct drm_crtc *crtc, u16 *red, u16 *green, + u16 *blue, int regno) +{ + struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); + + *red = radeon_crtc->lut_r[regno] << 6; + *green = radeon_crtc->lut_g[regno] << 6; + *blue = radeon_crtc->lut_b[regno] << 6; +} + static void radeon_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, u16 *blue, uint32_t size) { struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); - int i, j; + int i; if (size != 256) { return; } - if (crtc->fb == NULL) { - return; - } - if (crtc->fb->depth == 16) { - for (i = 0; i < 64; i++) { - if (i <= 31) { - for (j = 0; j < 8; j++) { - radeon_crtc->lut_r[i * 8 + j] = red[i] >> 6; - radeon_crtc->lut_b[i * 8 + j] = blue[i] >> 6; - } - } - for (j = 0; j < 4; j++) - radeon_crtc->lut_g[i * 4 + j] = green[i] >> 6; - } - } else { - for (i = 0; i < 256; i++) { - radeon_crtc->lut_r[i] = red[i] >> 6; - radeon_crtc->lut_g[i] = green[i] >> 6; - radeon_crtc->lut_b[i] = blue[i] >> 6; - } + /* userspace palettes are always correct as is */ + for (i = 0; i < 256; i++) { + radeon_crtc->lut_r[i] = red[i] >> 6; + radeon_crtc->lut_g[i] = green[i] >> 6; + radeon_crtc->lut_b[i] = blue[i] >> 6; } - radeon_crtc_load_lut(crtc); } @@ -341,27 +334,19 @@ static bool radeon_setup_enc_conn(struct drm_device *dev) int radeon_ddc_get_modes(struct radeon_connector *radeon_connector) { - struct edid *edid; int ret = 0; if (!radeon_connector->ddc_bus) return -1; if (!radeon_connector->edid) { radeon_i2c_do_lock(radeon_connector, 1); - edid = drm_get_edid(&radeon_connector->base, &radeon_connector->ddc_bus->adapter); + radeon_connector->edid = drm_get_edid(&radeon_connector->base, &radeon_connector->ddc_bus->adapter); radeon_i2c_do_lock(radeon_connector, 0); - } else - edid = radeon_connector->edid; + } - if (edid) { - /* update digital bits here */ - if (edid->input & DRM_EDID_INPUT_DIGITAL) - radeon_connector->use_digital = 1; - else - radeon_connector->use_digital = 0; - drm_mode_connector_update_edid_property(&radeon_connector->base, edid); - ret = drm_add_edid_modes(&radeon_connector->base, edid); - kfree(edid); + if (radeon_connector->edid) { + drm_mode_connector_update_edid_property(&radeon_connector->base, radeon_connector->edid); + ret = drm_add_edid_modes(&radeon_connector->base, radeon_connector->edid); return ret; } drm_mode_connector_update_edid_property(&radeon_connector->base, NULL); @@ -724,7 +709,11 @@ int radeon_modeset_init(struct radeon_device *rdev) if (ret) { return ret; } - /* allocate crtcs - TODO single crtc */ + + if (rdev->flags & RADEON_SINGLE_CRTC) + num_crtc = 1; + + /* allocate crtcs */ for (i = 0; i < num_crtc; i++) { radeon_crtc_init(rdev->ddev, i); } @@ -764,7 +753,7 @@ bool radeon_crtc_scaling_mode_fixup(struct drm_crtc *crtc, radeon_crtc->rmx_type = radeon_encoder->rmx_type; memcpy(&radeon_crtc->native_mode, &radeon_encoder->native_mode, - sizeof(struct radeon_native_mode)); + sizeof(struct drm_display_mode)); first = false; } else { if (radeon_crtc->rmx_type != radeon_encoder->rmx_type) { @@ -782,10 +771,10 @@ bool radeon_crtc_scaling_mode_fixup(struct drm_crtc *crtc, if (radeon_crtc->rmx_type != RMX_OFF) { fixed20_12 a, b; a.full = rfixed_const(crtc->mode.vdisplay); - b.full = rfixed_const(radeon_crtc->native_mode.panel_xres); + b.full = rfixed_const(radeon_crtc->native_mode.hdisplay); radeon_crtc->vsc.full = rfixed_div(a, b); a.full = rfixed_const(crtc->mode.hdisplay); - b.full = rfixed_const(radeon_crtc->native_mode.panel_yres); + b.full = rfixed_const(radeon_crtc->native_mode.vdisplay); radeon_crtc->hsc.full = rfixed_div(a, b); } else { radeon_crtc->vsc.full = rfixed_const(1); diff --git a/drivers/gpu/drm/radeon/radeon_encoders.c b/drivers/gpu/drm/radeon/radeon_encoders.c index 621646752cd2..d42bc512d75a 100644 --- a/drivers/gpu/drm/radeon/radeon_encoders.c +++ b/drivers/gpu/drm/radeon/radeon_encoders.c @@ -31,6 +31,10 @@ extern int atom_debug; +/* evil but including atombios.h is much worse */ +bool radeon_atom_get_tv_timings(struct radeon_device *rdev, int index, + struct drm_display_mode *mode); + uint32_t radeon_get_encoder_id(struct drm_device *dev, uint32_t supported_device, uint8_t dac) { @@ -167,49 +171,17 @@ void radeon_rmx_mode_fixup(struct drm_encoder *encoder, struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); struct drm_device *dev = encoder->dev; struct radeon_device *rdev = dev->dev_private; - struct radeon_native_mode *native_mode = &radeon_encoder->native_mode; - - if (mode->hdisplay < native_mode->panel_xres || - mode->vdisplay < native_mode->panel_yres) { - if (ASIC_IS_AVIVO(rdev)) { - adjusted_mode->hdisplay = native_mode->panel_xres; - adjusted_mode->vdisplay = native_mode->panel_yres; - adjusted_mode->htotal = native_mode->panel_xres + native_mode->hblank; - adjusted_mode->hsync_start = native_mode->panel_xres + native_mode->hoverplus; - adjusted_mode->hsync_end = adjusted_mode->hsync_start + native_mode->hsync_width; - adjusted_mode->vtotal = native_mode->panel_yres + native_mode->vblank; - adjusted_mode->vsync_start = native_mode->panel_yres + native_mode->voverplus; - adjusted_mode->vsync_end = adjusted_mode->vsync_start + native_mode->vsync_width; - /* update crtc values */ - drm_mode_set_crtcinfo(adjusted_mode, CRTC_INTERLACE_HALVE_V); - /* adjust crtc values */ - adjusted_mode->crtc_hdisplay = native_mode->panel_xres; - adjusted_mode->crtc_vdisplay = native_mode->panel_yres; - adjusted_mode->crtc_htotal = adjusted_mode->crtc_hdisplay + native_mode->hblank; - adjusted_mode->crtc_hsync_start = adjusted_mode->crtc_hdisplay + native_mode->hoverplus; - adjusted_mode->crtc_hsync_end = adjusted_mode->crtc_hsync_start + native_mode->hsync_width; - adjusted_mode->crtc_vtotal = adjusted_mode->crtc_vdisplay + native_mode->vblank; - adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vdisplay + native_mode->voverplus; - adjusted_mode->crtc_vsync_end = adjusted_mode->crtc_vsync_start + native_mode->vsync_width; - } else { - adjusted_mode->htotal = native_mode->panel_xres + native_mode->hblank; - adjusted_mode->hsync_start = native_mode->panel_xres + native_mode->hoverplus; - adjusted_mode->hsync_end = adjusted_mode->hsync_start + native_mode->hsync_width; - adjusted_mode->vtotal = native_mode->panel_yres + native_mode->vblank; - adjusted_mode->vsync_start = native_mode->panel_yres + native_mode->voverplus; - adjusted_mode->vsync_end = adjusted_mode->vsync_start + native_mode->vsync_width; - /* update crtc values */ - drm_mode_set_crtcinfo(adjusted_mode, CRTC_INTERLACE_HALVE_V); - /* adjust crtc values */ - adjusted_mode->crtc_htotal = adjusted_mode->crtc_hdisplay + native_mode->hblank; - adjusted_mode->crtc_hsync_start = adjusted_mode->crtc_hdisplay + native_mode->hoverplus; - adjusted_mode->crtc_hsync_end = adjusted_mode->crtc_hsync_start + native_mode->hsync_width; - adjusted_mode->crtc_vtotal = adjusted_mode->crtc_vdisplay + native_mode->vblank; - adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vdisplay + native_mode->voverplus; - adjusted_mode->crtc_vsync_end = adjusted_mode->crtc_vsync_start + native_mode->vsync_width; + struct drm_display_mode *native_mode = &radeon_encoder->native_mode; + + if (mode->hdisplay < native_mode->hdisplay || + mode->vdisplay < native_mode->vdisplay) { + int mode_id = adjusted_mode->base.id; + *adjusted_mode = *native_mode; + if (!ASIC_IS_AVIVO(rdev)) { + adjusted_mode->hdisplay = mode->hdisplay; + adjusted_mode->vdisplay = mode->vdisplay; } - adjusted_mode->flags = native_mode->flags; - adjusted_mode->clock = native_mode->dotclock; + adjusted_mode->base.id = mode_id; } } @@ -219,7 +191,11 @@ static bool radeon_atom_mode_fixup(struct drm_encoder *encoder, struct drm_display_mode *adjusted_mode) { struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); + struct drm_device *dev = encoder->dev; + struct radeon_device *rdev = dev->dev_private; + /* set the active encoder to connector routing */ + radeon_encoder_set_active_device(encoder); drm_mode_set_crtcinfo(adjusted_mode, 0); if (radeon_encoder->rmx_type != RMX_OFF) @@ -230,6 +206,18 @@ static bool radeon_atom_mode_fixup(struct drm_encoder *encoder, && (mode->crtc_vsync_start < (mode->crtc_vdisplay + 2))) adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vdisplay + 2; + if (radeon_encoder->active_device & (ATOM_DEVICE_TV_SUPPORT)) { + struct radeon_encoder_atom_dac *tv_dac = radeon_encoder->enc_priv; + if (tv_dac) { + if (tv_dac->tv_std == TV_STD_NTSC || + tv_dac->tv_std == TV_STD_NTSC_J || + tv_dac->tv_std == TV_STD_PAL_M) + radeon_atom_get_tv_timings(rdev, 0, adjusted_mode); + else + radeon_atom_get_tv_timings(rdev, 1, adjusted_mode); + } + } + return true; } @@ -461,7 +449,7 @@ atombios_digital_setup(struct drm_encoder *encoder, int action) case 1: args.v1.ucMisc = 0; args.v1.ucAction = action; - if (drm_detect_hdmi_monitor((struct edid *)connector->edid_blob_ptr)) + if (drm_detect_hdmi_monitor(radeon_connector->edid)) args.v1.ucMisc |= PANEL_ENCODER_MISC_HDMI_TYPE; args.v1.usPixelClock = cpu_to_le16(radeon_encoder->pixel_clock / 10); if (radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT)) { @@ -486,7 +474,7 @@ atombios_digital_setup(struct drm_encoder *encoder, int action) if (dig->coherent_mode) args.v2.ucMisc |= PANEL_ENCODER_MISC_COHERENT; } - if (drm_detect_hdmi_monitor((struct edid *)connector->edid_blob_ptr)) + if (drm_detect_hdmi_monitor(radeon_connector->edid)) args.v2.ucMisc |= PANEL_ENCODER_MISC_HDMI_TYPE; args.v2.usPixelClock = cpu_to_le16(radeon_encoder->pixel_clock / 10); args.v2.ucTruncate = 0; @@ -544,7 +532,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder) switch (connector->connector_type) { case DRM_MODE_CONNECTOR_DVII: case DRM_MODE_CONNECTOR_HDMIB: /* HDMI-B is basically DL-DVI; analog works fine */ - if (drm_detect_hdmi_monitor((struct edid *)connector->edid_blob_ptr)) + if (drm_detect_hdmi_monitor(radeon_connector->edid)) return ATOM_ENCODER_MODE_HDMI; else if (radeon_connector->use_digital) return ATOM_ENCODER_MODE_DVI; @@ -554,7 +542,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder) case DRM_MODE_CONNECTOR_DVID: case DRM_MODE_CONNECTOR_HDMIA: default: - if (drm_detect_hdmi_monitor((struct edid *)connector->edid_blob_ptr)) + if (drm_detect_hdmi_monitor(radeon_connector->edid)) return ATOM_ENCODER_MODE_HDMI; else return ATOM_ENCODER_MODE_DVI; @@ -566,7 +554,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder) /*if (radeon_output->MonType == MT_DP) return ATOM_ENCODER_MODE_DP; else*/ - if (drm_detect_hdmi_monitor((struct edid *)connector->edid_blob_ptr)) + if (drm_detect_hdmi_monitor(radeon_connector->edid)) return ATOM_ENCODER_MODE_HDMI; else return ATOM_ENCODER_MODE_DVI; @@ -734,14 +722,17 @@ atombios_dig_transmitter_setup(struct drm_encoder *encoder, int action) atom_parse_cmd_header(rdev->mode_info.atom_context, index, &frev, &crev); args.v1.ucAction = action; - + if (action == ATOM_TRANSMITTER_ACTION_INIT) { + args.v1.usInitInfo = radeon_connector->connector_object_id; + } else { + if (radeon_encoder->pixel_clock > 165000) + args.v1.usPixelClock = cpu_to_le16((radeon_encoder->pixel_clock / 2) / 10); + else + args.v1.usPixelClock = cpu_to_le16(radeon_encoder->pixel_clock / 10); + } if (ASIC_IS_DCE32(rdev)) { - if (radeon_encoder->pixel_clock > 165000) { - args.v2.usPixelClock = cpu_to_le16((radeon_encoder->pixel_clock * 10 * 2) / 100); - args.v2.acConfig.fDualLinkConnector = 1; - } else { - args.v2.usPixelClock = cpu_to_le16((radeon_encoder->pixel_clock * 10 * 4) / 100); - } + if (radeon_encoder->pixel_clock > 165000) + args.v2.usPixelClock = cpu_to_le16((radeon_encoder->pixel_clock / 2) / 10); if (dig->dig_block) args.v2.acConfig.ucEncoderSel = 1; @@ -766,7 +757,6 @@ atombios_dig_transmitter_setup(struct drm_encoder *encoder, int action) } } else { args.v1.ucConfig = ATOM_TRANSMITTER_CONFIG_CLKSRC_PPLL; - args.v1.usPixelClock = cpu_to_le16((radeon_encoder->pixel_clock) / 10); switch (radeon_encoder->encoder_id) { case ENCODER_OBJECT_ID_INTERNAL_UNIPHY: @@ -874,16 +864,9 @@ radeon_atom_encoder_dpms(struct drm_encoder *encoder, int mode) DISPLAY_DEVICE_OUTPUT_CONTROL_PS_ALLOCATION args; int index = 0; bool is_dig = false; - int devices; memset(&args, 0, sizeof(args)); - /* on DPMS off we have no idea if active device is meaningful */ - if (mode != DRM_MODE_DPMS_ON && !radeon_encoder->active_device) - devices = radeon_encoder->devices; - else - devices = radeon_encoder->active_device; - DRM_DEBUG("encoder dpms %d to mode %d, devices %08x, active_devices %08x\n", radeon_encoder->encoder_id, mode, radeon_encoder->devices, radeon_encoder->active_device); @@ -914,18 +897,18 @@ radeon_atom_encoder_dpms(struct drm_encoder *encoder, int mode) break; case ENCODER_OBJECT_ID_INTERNAL_DAC1: case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DAC1: - if (devices & (ATOM_DEVICE_TV_SUPPORT)) + if (radeon_encoder->active_device & (ATOM_DEVICE_TV_SUPPORT)) index = GetIndexIntoMasterTable(COMMAND, TV1OutputControl); - else if (devices & (ATOM_DEVICE_CV_SUPPORT)) + else if (radeon_encoder->active_device & (ATOM_DEVICE_CV_SUPPORT)) index = GetIndexIntoMasterTable(COMMAND, CV1OutputControl); else index = GetIndexIntoMasterTable(COMMAND, DAC1OutputControl); break; case ENCODER_OBJECT_ID_INTERNAL_DAC2: case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DAC2: - if (devices & (ATOM_DEVICE_TV_SUPPORT)) + if (radeon_encoder->active_device & (ATOM_DEVICE_TV_SUPPORT)) index = GetIndexIntoMasterTable(COMMAND, TV1OutputControl); - else if (devices & (ATOM_DEVICE_CV_SUPPORT)) + else if (radeon_encoder->active_device & (ATOM_DEVICE_CV_SUPPORT)) index = GetIndexIntoMasterTable(COMMAND, CV1OutputControl); else index = GetIndexIntoMasterTable(COMMAND, DAC2OutputControl); @@ -1104,8 +1087,11 @@ atombios_apply_encoder_quirks(struct drm_encoder *encoder, } /* set scaler clears this on some chips */ - if (ASIC_IS_AVIVO(rdev) && (mode->flags & DRM_MODE_FLAG_INTERLACE)) - WREG32(AVIVO_D1MODE_DATA_FORMAT + radeon_crtc->crtc_offset, AVIVO_D1MODE_INTERLEAVE_EN); + if (!(radeon_encoder->active_device & (ATOM_DEVICE_TV_SUPPORT))) { + if (ASIC_IS_AVIVO(rdev) && (mode->flags & DRM_MODE_FLAG_INTERLACE)) + WREG32(AVIVO_D1MODE_DATA_FORMAT + radeon_crtc->crtc_offset, + AVIVO_D1MODE_INTERLEAVE_EN); + } } static void @@ -1153,6 +1139,7 @@ radeon_atom_encoder_mode_set(struct drm_encoder *encoder, /* setup and enable the encoder and transmitter */ atombios_dig_encoder_setup(encoder, ATOM_ENABLE); + atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_INIT); atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_SETUP); atombios_dig_transmitter_setup(encoder, ATOM_TRANSMITTER_ACTION_ENABLE); break; @@ -1268,8 +1255,6 @@ static void radeon_atom_encoder_prepare(struct drm_encoder *encoder) { radeon_atom_output_lock(encoder, true); radeon_atom_encoder_dpms(encoder, DRM_MODE_DPMS_OFF); - - radeon_encoder_set_active_device(encoder); } static void radeon_atom_encoder_commit(struct drm_encoder *encoder) @@ -1345,6 +1330,7 @@ radeon_atombios_set_dig_info(struct radeon_encoder *radeon_encoder) void radeon_add_atom_encoder(struct drm_device *dev, uint32_t encoder_id, uint32_t supported_device) { + struct radeon_device *rdev = dev->dev_private; struct drm_encoder *encoder; struct radeon_encoder *radeon_encoder; @@ -1364,7 +1350,10 @@ radeon_add_atom_encoder(struct drm_device *dev, uint32_t encoder_id, uint32_t su return; encoder = &radeon_encoder->base; - encoder->possible_crtcs = 0x3; + if (rdev->flags & RADEON_SINGLE_CRTC) + encoder->possible_crtcs = 0x1; + else + encoder->possible_crtcs = 0x3; encoder->possible_clones = 0; radeon_encoder->enc_priv = NULL; diff --git a/drivers/gpu/drm/radeon/radeon_fb.c b/drivers/gpu/drm/radeon/radeon_fb.c index 1ba704eedefb..b38c4c8e2c61 100644 --- a/drivers/gpu/drm/radeon/radeon_fb.c +++ b/drivers/gpu/drm/radeon/radeon_fb.c @@ -55,6 +55,7 @@ static struct fb_ops radeonfb_ops = { .fb_imageblit = cfb_imageblit, .fb_pan_display = drm_fb_helper_pan_display, .fb_blank = drm_fb_helper_blank, + .fb_setcmap = drm_fb_helper_setcmap, }; /** @@ -123,6 +124,7 @@ static int radeon_align_pitch(struct radeon_device *rdev, int width, int bpp, bo static struct drm_fb_helper_funcs radeon_fb_helper_funcs = { .gamma_set = radeon_crtc_fb_gamma_set, + .gamma_get = radeon_crtc_fb_gamma_get, }; int radeonfb_create(struct drm_device *dev, @@ -146,9 +148,15 @@ int radeonfb_create(struct drm_device *dev, unsigned long tmp; bool fb_tiled = false; /* useful for testing */ u32 tiling_flags = 0; + int crtc_count; mode_cmd.width = surface_width; mode_cmd.height = surface_height; + + /* avivo can't scanout real 24bpp */ + if ((surface_bpp == 24) && ASIC_IS_AVIVO(rdev)) + surface_bpp = 32; + mode_cmd.bpp = surface_bpp; /* need to align pitch with crtc limits */ mode_cmd.pitch = radeon_align_pitch(rdev, mode_cmd.width, mode_cmd.bpp, fb_tiled) * ((mode_cmd.bpp + 1) / 8); @@ -217,7 +225,11 @@ int radeonfb_create(struct drm_device *dev, rfbdev = info->par; rfbdev->helper.funcs = &radeon_fb_helper_funcs; rfbdev->helper.dev = dev; - ret = drm_fb_helper_init_crtc_count(&rfbdev->helper, 2, + if (rdev->flags & RADEON_SINGLE_CRTC) + crtc_count = 1; + else + crtc_count = 2; + ret = drm_fb_helper_init_crtc_count(&rfbdev->helper, crtc_count, RADEONFB_CONN_LIMIT); if (ret) goto out_unref; @@ -234,7 +246,7 @@ int radeonfb_create(struct drm_device *dev, strcpy(info->fix.id, "radeondrmfb"); - drm_fb_helper_fill_fix(info, fb->pitch); + drm_fb_helper_fill_fix(info, fb->pitch, fb->depth); info->flags = FBINFO_DEFAULT; info->fbops = &radeonfb_ops; @@ -309,7 +321,7 @@ int radeon_parse_options(char *options) int radeonfb_probe(struct drm_device *dev) { - return drm_fb_helper_single_fb_probe(dev, &radeonfb_create); + return drm_fb_helper_single_fb_probe(dev, 32, &radeonfb_create); } int radeonfb_remove(struct drm_device *dev, struct drm_framebuffer *fb) diff --git a/drivers/gpu/drm/radeon/radeon_gart.c b/drivers/gpu/drm/radeon/radeon_gart.c index a931af065dd4..a68d7566178c 100644 --- a/drivers/gpu/drm/radeon/radeon_gart.c +++ b/drivers/gpu/drm/radeon/radeon_gart.c @@ -140,15 +140,15 @@ void radeon_gart_unbind(struct radeon_device *rdev, unsigned offset, WARN(1, "trying to unbind memory to unitialized GART !\n"); return; } - t = offset / 4096; - p = t / (PAGE_SIZE / 4096); + t = offset / RADEON_GPU_PAGE_SIZE; + p = t / (PAGE_SIZE / RADEON_GPU_PAGE_SIZE); for (i = 0; i < pages; i++, p++) { if (rdev->gart.pages[p]) { pci_unmap_page(rdev->pdev, rdev->gart.pages_addr[p], PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); rdev->gart.pages[p] = NULL; rdev->gart.pages_addr[p] = 0; - for (j = 0; j < (PAGE_SIZE / 4096); j++, t++) { + for (j = 0; j < (PAGE_SIZE / RADEON_GPU_PAGE_SIZE); j++, t++) { radeon_gart_set_page(rdev, t, 0); } } @@ -169,8 +169,8 @@ int radeon_gart_bind(struct radeon_device *rdev, unsigned offset, DRM_ERROR("trying to bind memory to unitialized GART !\n"); return -EINVAL; } - t = offset / 4096; - p = t / (PAGE_SIZE / 4096); + t = offset / RADEON_GPU_PAGE_SIZE; + p = t / (PAGE_SIZE / RADEON_GPU_PAGE_SIZE); for (i = 0; i < pages; i++, p++) { /* we need to support large memory configurations */ @@ -185,9 +185,9 @@ int radeon_gart_bind(struct radeon_device *rdev, unsigned offset, } rdev->gart.pages[p] = pagelist[i]; page_base = rdev->gart.pages_addr[p]; - for (j = 0; j < (PAGE_SIZE / 4096); j++, t++) { + for (j = 0; j < (PAGE_SIZE / RADEON_GPU_PAGE_SIZE); j++, t++) { radeon_gart_set_page(rdev, t, page_base); - page_base += 4096; + page_base += RADEON_GPU_PAGE_SIZE; } } mb(); @@ -200,14 +200,14 @@ int radeon_gart_init(struct radeon_device *rdev) if (rdev->gart.pages) { return 0; } - /* We need PAGE_SIZE >= 4096 */ - if (PAGE_SIZE < 4096) { + /* We need PAGE_SIZE >= RADEON_GPU_PAGE_SIZE */ + if (PAGE_SIZE < RADEON_GPU_PAGE_SIZE) { DRM_ERROR("Page size is smaller than GPU page size!\n"); return -EINVAL; } /* Compute table size */ rdev->gart.num_cpu_pages = rdev->mc.gtt_size / PAGE_SIZE; - rdev->gart.num_gpu_pages = rdev->mc.gtt_size / 4096; + rdev->gart.num_gpu_pages = rdev->mc.gtt_size / RADEON_GPU_PAGE_SIZE; DRM_INFO("GART: num cpu pages %u, num gpu pages %u\n", rdev->gart.num_cpu_pages, rdev->gart.num_gpu_pages); /* Allocate pages table */ diff --git a/drivers/gpu/drm/radeon/radeon_irq_kms.c b/drivers/gpu/drm/radeon/radeon_irq_kms.c index 1841145a7c4f..a0fe6232dcb6 100644 --- a/drivers/gpu/drm/radeon/radeon_irq_kms.c +++ b/drivers/gpu/drm/radeon/radeon_irq_kms.c @@ -83,11 +83,22 @@ void radeon_driver_irq_uninstall_kms(struct drm_device *dev) int radeon_irq_kms_init(struct radeon_device *rdev) { int r = 0; + int num_crtc = 2; - r = drm_vblank_init(rdev->ddev, 2); + if (rdev->flags & RADEON_SINGLE_CRTC) + num_crtc = 1; + + r = drm_vblank_init(rdev->ddev, num_crtc); if (r) { return r; } + /* enable msi */ + rdev->msi_enabled = 0; + if (rdev->family >= CHIP_RV380) { + int ret = pci_enable_msi(rdev->pdev); + if (!ret) + rdev->msi_enabled = 1; + } drm_irq_install(rdev->ddev); rdev->irq.installed = true; DRM_INFO("radeon: irq initialized.\n"); @@ -99,5 +110,7 @@ void radeon_irq_kms_fini(struct radeon_device *rdev) if (rdev->irq.installed) { rdev->irq.installed = false; drm_irq_uninstall(rdev->ddev); + if (rdev->msi_enabled) + pci_disable_msi(rdev->pdev); } } diff --git a/drivers/gpu/drm/radeon/radeon_legacy_crtc.c b/drivers/gpu/drm/radeon/radeon_legacy_crtc.c index 2b997a15fb1f..8d0b7aa87fa4 100644 --- a/drivers/gpu/drm/radeon/radeon_legacy_crtc.c +++ b/drivers/gpu/drm/radeon/radeon_legacy_crtc.c @@ -48,7 +48,7 @@ static void radeon_legacy_rmx_mode_set(struct drm_crtc *crtc, u32 fp_horz_stretch, fp_vert_stretch, fp_horz_vert_active; u32 fp_h_sync_strt_wid, fp_crtc_h_total_disp; u32 fp_v_sync_strt_wid, fp_crtc_v_total_disp; - struct radeon_native_mode *native_mode = &radeon_crtc->native_mode; + struct drm_display_mode *native_mode = &radeon_crtc->native_mode; fp_vert_stretch = RREG32(RADEON_FP_VERT_STRETCH) & (RADEON_VERT_STRETCH_RESERVED | @@ -95,19 +95,19 @@ static void radeon_legacy_rmx_mode_set(struct drm_crtc *crtc, fp_horz_vert_active = 0; - if (native_mode->panel_xres == 0 || - native_mode->panel_yres == 0) { + if (native_mode->hdisplay == 0 || + native_mode->vdisplay == 0) { hscale = false; vscale = false; } else { - if (xres > native_mode->panel_xres) - xres = native_mode->panel_xres; - if (yres > native_mode->panel_yres) - yres = native_mode->panel_yres; + if (xres > native_mode->hdisplay) + xres = native_mode->hdisplay; + if (yres > native_mode->vdisplay) + yres = native_mode->vdisplay; - if (xres == native_mode->panel_xres) + if (xres == native_mode->hdisplay) hscale = false; - if (yres == native_mode->panel_yres) + if (yres == native_mode->vdisplay) vscale = false; } @@ -119,11 +119,11 @@ static void radeon_legacy_rmx_mode_set(struct drm_crtc *crtc, else { inc = (fp_horz_stretch & RADEON_HORZ_AUTO_RATIO_INC) ? 1 : 0; scale = ((xres + inc) * RADEON_HORZ_STRETCH_RATIO_MAX) - / native_mode->panel_xres + 1; + / native_mode->hdisplay + 1; fp_horz_stretch |= (((scale) & RADEON_HORZ_STRETCH_RATIO_MASK) | RADEON_HORZ_STRETCH_BLEND | RADEON_HORZ_STRETCH_ENABLE | - ((native_mode->panel_xres/8-1) << 16)); + ((native_mode->hdisplay/8-1) << 16)); } if (!vscale) @@ -131,11 +131,11 @@ static void radeon_legacy_rmx_mode_set(struct drm_crtc *crtc, else { inc = (fp_vert_stretch & RADEON_VERT_AUTO_RATIO_INC) ? 1 : 0; scale = ((yres + inc) * RADEON_VERT_STRETCH_RATIO_MAX) - / native_mode->panel_yres + 1; + / native_mode->vdisplay + 1; fp_vert_stretch |= (((scale) & RADEON_VERT_STRETCH_RATIO_MASK) | RADEON_VERT_STRETCH_ENABLE | RADEON_VERT_STRETCH_BLEND | - ((native_mode->panel_yres-1) << 12)); + ((native_mode->vdisplay-1) << 12)); } break; case RMX_CENTER: @@ -175,8 +175,8 @@ static void radeon_legacy_rmx_mode_set(struct drm_crtc *crtc, ? RADEON_CRTC_V_SYNC_POL : 0))); - fp_horz_vert_active = (((native_mode->panel_yres) & 0xfff) | - (((native_mode->panel_xres / 8) & 0x1ff) << 16)); + fp_horz_vert_active = (((native_mode->vdisplay) & 0xfff) | + (((native_mode->hdisplay / 8) & 0x1ff) << 16)); break; case RMX_OFF: default: @@ -532,6 +532,10 @@ int radeon_crtc_set_base(struct drm_crtc *crtc, int x, int y, radeon_fb = to_radeon_framebuffer(old_fb); radeon_gem_object_unpin(radeon_fb->obj); } + + /* Bytes per pixel may have changed */ + radeon_bandwidth_update(rdev); + return 0; } @@ -664,6 +668,9 @@ static bool radeon_set_crtc_timing(struct drm_crtc *crtc, struct drm_display_mod WREG32(RADEON_DISP2_MERGE_CNTL, disp2_merge_cntl); WREG32(RADEON_CRTC2_GEN_CNTL, crtc2_gen_cntl); + + WREG32(RADEON_FP_H2_SYNC_STRT_WID, crtc_h_sync_strt_wid); + WREG32(RADEON_FP_V2_SYNC_STRT_WID, crtc_v_sync_strt_wid); } else { uint32_t crtc_gen_cntl; uint32_t crtc_ext_cntl; @@ -1015,14 +1022,11 @@ static int radeon_crtc_mode_set(struct drm_crtc *crtc, int x, int y, struct drm_framebuffer *old_fb) { struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); - struct drm_device *dev = crtc->dev; - struct radeon_device *rdev = dev->dev_private; /* TODO TV */ radeon_crtc_set_base(crtc, x, y, old_fb); radeon_set_crtc_timing(crtc, adjusted_mode); radeon_set_pll(crtc, adjusted_mode); - radeon_bandwidth_update(rdev); if (radeon_crtc->crtc_id == 0) { radeon_legacy_rmx_mode_set(crtc, mode, adjusted_mode); } else { @@ -1053,6 +1057,7 @@ static const struct drm_crtc_helper_funcs legacy_helper_funcs = { .mode_set_base = radeon_crtc_set_base, .prepare = radeon_crtc_prepare, .commit = radeon_crtc_commit, + .load_lut = radeon_crtc_load_lut, }; diff --git a/drivers/gpu/drm/radeon/radeon_legacy_encoders.c b/drivers/gpu/drm/radeon/radeon_legacy_encoders.c index b1547f700d73..00382122869b 100644 --- a/drivers/gpu/drm/radeon/radeon_legacy_encoders.c +++ b/drivers/gpu/drm/radeon/radeon_legacy_encoders.c @@ -107,8 +107,6 @@ static void radeon_legacy_lvds_prepare(struct drm_encoder *encoder) else radeon_combios_output_lock(encoder, true); radeon_legacy_lvds_dpms(encoder, DRM_MODE_DPMS_OFF); - - radeon_encoder_set_active_device(encoder); } static void radeon_legacy_lvds_commit(struct drm_encoder *encoder) @@ -192,6 +190,8 @@ static bool radeon_legacy_lvds_mode_fixup(struct drm_encoder *encoder, { struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); + /* set the active encoder to connector routing */ + radeon_encoder_set_active_device(encoder); drm_mode_set_crtcinfo(adjusted_mode, 0); if (radeon_encoder->rmx_type != RMX_OFF) @@ -218,7 +218,8 @@ static bool radeon_legacy_primary_dac_mode_fixup(struct drm_encoder *encoder, struct drm_display_mode *mode, struct drm_display_mode *adjusted_mode) { - + /* set the active encoder to connector routing */ + radeon_encoder_set_active_device(encoder); drm_mode_set_crtcinfo(adjusted_mode, 0); return true; @@ -272,7 +273,6 @@ static void radeon_legacy_primary_dac_prepare(struct drm_encoder *encoder) else radeon_combios_output_lock(encoder, true); radeon_legacy_primary_dac_dpms(encoder, DRM_MODE_DPMS_OFF); - radeon_encoder_set_active_device(encoder); } static void radeon_legacy_primary_dac_commit(struct drm_encoder *encoder) @@ -468,7 +468,6 @@ static void radeon_legacy_tmds_int_prepare(struct drm_encoder *encoder) else radeon_combios_output_lock(encoder, true); radeon_legacy_tmds_int_dpms(encoder, DRM_MODE_DPMS_OFF); - radeon_encoder_set_active_device(encoder); } static void radeon_legacy_tmds_int_commit(struct drm_encoder *encoder) @@ -543,6 +542,14 @@ static void radeon_legacy_tmds_int_mode_set(struct drm_encoder *encoder, fp_gen_cntl &= ~(RADEON_FP_FPON | RADEON_FP_TMDS_EN); + fp_gen_cntl &= ~(RADEON_FP_RMX_HVSYNC_CONTROL_EN | + RADEON_FP_DFP_SYNC_SEL | + RADEON_FP_CRT_SYNC_SEL | + RADEON_FP_CRTC_LOCK_8DOT | + RADEON_FP_USE_SHADOW_EN | + RADEON_FP_CRTC_USE_SHADOW_VEND | + RADEON_FP_CRT_SYNC_ALT); + if (1) /* FIXME rgbBits == 8 */ fp_gen_cntl |= RADEON_FP_PANEL_FORMAT; /* 24 bit format */ else @@ -556,7 +563,7 @@ static void radeon_legacy_tmds_int_mode_set(struct drm_encoder *encoder, else fp_gen_cntl |= R200_FP_SOURCE_SEL_CRTC1; } else - fp_gen_cntl |= RADEON_FP_SEL_CRTC1; + fp_gen_cntl &= ~RADEON_FP_SEL_CRTC2; } else { if (ASIC_IS_R300(rdev) || rdev->family == CHIP_R200) { fp_gen_cntl &= ~R200_FP_SOURCE_SEL_MASK; @@ -593,7 +600,8 @@ static bool radeon_legacy_tmds_ext_mode_fixup(struct drm_encoder *encoder, struct drm_display_mode *mode, struct drm_display_mode *adjusted_mode) { - + /* set the active encoder to connector routing */ + radeon_encoder_set_active_device(encoder); drm_mode_set_crtcinfo(adjusted_mode, 0); return true; @@ -636,7 +644,6 @@ static void radeon_legacy_tmds_ext_prepare(struct drm_encoder *encoder) else radeon_combios_output_lock(encoder, true); radeon_legacy_tmds_ext_dpms(encoder, DRM_MODE_DPMS_OFF); - radeon_encoder_set_active_device(encoder); } static void radeon_legacy_tmds_ext_commit(struct drm_encoder *encoder) @@ -735,7 +742,8 @@ static bool radeon_legacy_tv_dac_mode_fixup(struct drm_encoder *encoder, struct drm_display_mode *mode, struct drm_display_mode *adjusted_mode) { - + /* set the active encoder to connector routing */ + radeon_encoder_set_active_device(encoder); drm_mode_set_crtcinfo(adjusted_mode, 0); return true; @@ -839,7 +847,6 @@ static void radeon_legacy_tv_dac_prepare(struct drm_encoder *encoder) else radeon_combios_output_lock(encoder, true); radeon_legacy_tv_dac_dpms(encoder, DRM_MODE_DPMS_OFF); - radeon_encoder_set_active_device(encoder); } static void radeon_legacy_tv_dac_commit(struct drm_encoder *encoder) @@ -881,7 +888,7 @@ static void radeon_legacy_tv_dac_mode_set(struct drm_encoder *encoder, R420_TV_DAC_DACADJ_MASK | R420_TV_DAC_RDACPD | R420_TV_DAC_GDACPD | - R420_TV_DAC_GDACPD | + R420_TV_DAC_BDACPD | R420_TV_DAC_TVENABLE); } else { tv_dac_cntl &= ~(RADEON_TV_DAC_STD_MASK | @@ -889,7 +896,7 @@ static void radeon_legacy_tv_dac_mode_set(struct drm_encoder *encoder, RADEON_TV_DAC_DACADJ_MASK | RADEON_TV_DAC_RDACPD | RADEON_TV_DAC_GDACPD | - RADEON_TV_DAC_GDACPD); + RADEON_TV_DAC_BDACPD); } /* FIXME TV */ @@ -1318,7 +1325,10 @@ radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_id, uint32_t return; encoder = &radeon_encoder->base; - encoder->possible_crtcs = 0x3; + if (rdev->flags & RADEON_SINGLE_CRTC) + encoder->possible_crtcs = 0x1; + else + encoder->possible_crtcs = 0x3; encoder->possible_clones = 0; radeon_encoder->enc_priv = NULL; diff --git a/drivers/gpu/drm/radeon/radeon_mode.h b/drivers/gpu/drm/radeon/radeon_mode.h index 570a58729daf..ace726aa0d76 100644 --- a/drivers/gpu/drm/radeon/radeon_mode.h +++ b/drivers/gpu/drm/radeon/radeon_mode.h @@ -172,6 +172,7 @@ enum radeon_connector_table { struct radeon_mode_info { struct atom_context *atom_context; + struct card_info *atom_card_info; enum radeon_connector_table connector_table; bool mode_config_initialized; struct radeon_crtc *crtcs[2]; @@ -186,17 +187,6 @@ struct radeon_mode_info { }; -struct radeon_native_mode { - /* preferred mode */ - uint32_t panel_xres, panel_yres; - uint32_t hoverplus, hsync_width; - uint32_t hblank; - uint32_t voverplus, vsync_width; - uint32_t vblank; - uint32_t dotclock; - uint32_t flags; -}; - #define MAX_H_CODE_TIMING_LEN 32 #define MAX_V_CODE_TIMING_LEN 32 @@ -228,7 +218,7 @@ struct radeon_crtc { enum radeon_rmx_type rmx_type; fixed20_12 vsc; fixed20_12 hsc; - struct radeon_native_mode native_mode; + struct drm_display_mode native_mode; }; struct radeon_encoder_primary_dac { @@ -248,7 +238,7 @@ struct radeon_encoder_lvds { bool use_bios_dividers; uint32_t lvds_gen_cntl; /* panel mode */ - struct radeon_native_mode native_mode; + struct drm_display_mode native_mode; }; struct radeon_encoder_tv_dac { @@ -271,6 +261,16 @@ struct radeon_encoder_int_tmds { struct radeon_tmds_pll tmds_pll[4]; }; +/* spread spectrum */ +struct radeon_atom_ss { + uint16_t percentage; + uint8_t type; + uint8_t step; + uint8_t delay; + uint8_t range; + uint8_t refdiv; +}; + struct radeon_encoder_atom_dig { /* atom dig */ bool coherent_mode; @@ -278,8 +278,9 @@ struct radeon_encoder_atom_dig { /* atom lvds */ uint32_t lvds_misc; uint16_t panel_pwr_delay; + struct radeon_atom_ss *ss; /* panel mode */ - struct radeon_native_mode native_mode; + struct drm_display_mode native_mode; }; struct radeon_encoder_atom_dac { @@ -294,7 +295,7 @@ struct radeon_encoder { uint32_t flags; uint32_t pixel_clock; enum radeon_rmx_type rmx_type; - struct radeon_native_mode native_mode; + struct drm_display_mode native_mode; void *enc_priv; }; @@ -308,12 +309,15 @@ struct radeon_connector { uint32_t connector_id; uint32_t devices; struct radeon_i2c_chan *ddc_bus; + /* some systems have a an hdmi and vga port with a shared ddc line */ + bool shared_ddc; bool use_digital; /* we need to mind the EDID between detect and get modes due to analog/digital/tvencoder */ struct edid *edid; void *con_priv; bool dac_load_detect; + uint16_t connector_object_id; }; struct radeon_framebuffer { @@ -407,6 +411,8 @@ extern void radeon_combios_encoder_dpms_scratch_regs(struct drm_encoder *encoder, bool on); extern void radeon_crtc_fb_gamma_set(struct drm_crtc *crtc, u16 red, u16 green, u16 blue, int regno); +extern void radeon_crtc_fb_gamma_get(struct drm_crtc *crtc, u16 *red, u16 *green, + u16 *blue, int regno); struct drm_framebuffer *radeon_framebuffer_create(struct drm_device *dev, struct drm_mode_fb_cmd *mode_cmd, struct drm_gem_object *obj); diff --git a/drivers/gpu/drm/radeon/radeon_object.c b/drivers/gpu/drm/radeon/radeon_object.c index 73af463b7a59..1f056dadc5c2 100644 --- a/drivers/gpu/drm/radeon/radeon_object.c +++ b/drivers/gpu/drm/radeon/radeon_object.c @@ -400,11 +400,9 @@ void radeon_object_list_add_object(struct radeon_object_list *lobj, int radeon_object_list_reserve(struct list_head *head) { struct radeon_object_list *lobj; - struct list_head *i; int r; - list_for_each(i, head) { - lobj = list_entry(i, struct radeon_object_list, list); + list_for_each_entry(lobj, head, list){ if (!lobj->robj->pin_count) { r = radeon_object_reserve(lobj->robj, true); if (unlikely(r != 0)) { @@ -420,13 +418,10 @@ int radeon_object_list_reserve(struct list_head *head) void radeon_object_list_unreserve(struct list_head *head) { struct radeon_object_list *lobj; - struct list_head *i; - list_for_each(i, head) { - lobj = list_entry(i, struct radeon_object_list, list); + list_for_each_entry(lobj, head, list) { if (!lobj->robj->pin_count) { radeon_object_unreserve(lobj->robj); - } else { } } } @@ -436,7 +431,6 @@ int radeon_object_list_validate(struct list_head *head, void *fence) struct radeon_object_list *lobj; struct radeon_object *robj; struct radeon_fence *old_fence = NULL; - struct list_head *i; int r; r = radeon_object_list_reserve(head); @@ -444,8 +438,7 @@ int radeon_object_list_validate(struct list_head *head, void *fence) radeon_object_list_unreserve(head); return r; } - list_for_each(i, head) { - lobj = list_entry(i, struct radeon_object_list, list); + list_for_each_entry(lobj, head, list) { robj = lobj->robj; if (!robj->pin_count) { if (lobj->wdomain) { @@ -482,10 +475,8 @@ void radeon_object_list_unvalidate(struct list_head *head) { struct radeon_object_list *lobj; struct radeon_fence *old_fence = NULL; - struct list_head *i; - list_for_each(i, head) { - lobj = list_entry(i, struct radeon_object_list, list); + list_for_each_entry(lobj, head, list) { old_fence = (struct radeon_fence *)lobj->robj->tobj.sync_obj; lobj->robj->tobj.sync_obj = NULL; if (old_fence) { diff --git a/drivers/gpu/drm/radeon/radeon_pm.c b/drivers/gpu/drm/radeon/radeon_pm.c new file mode 100644 index 000000000000..46146c6a2a06 --- /dev/null +++ b/drivers/gpu/drm/radeon/radeon_pm.c @@ -0,0 +1,65 @@ +/* + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Rafał Miłecki <zajec5@gmail.com> + */ +#include "drmP.h" +#include "radeon.h" + +int radeon_debugfs_pm_init(struct radeon_device *rdev); + +int radeon_pm_init(struct radeon_device *rdev) +{ + if (radeon_debugfs_pm_init(rdev)) { + DRM_ERROR("Failed to register debugfs file for CP !\n"); + } + + return 0; +} + +/* + * Debugfs info + */ +#if defined(CONFIG_DEBUG_FS) + +static int radeon_debugfs_pm_info(struct seq_file *m, void *data) +{ + struct drm_info_node *node = (struct drm_info_node *) m->private; + struct drm_device *dev = node->minor->dev; + struct radeon_device *rdev = dev->dev_private; + + seq_printf(m, "engine clock: %u0 Hz\n", radeon_get_engine_clock(rdev)); + seq_printf(m, "memory clock: %u0 Hz\n", radeon_get_memory_clock(rdev)); + + return 0; +} + +static struct drm_info_list radeon_pm_info_list[] = { + {"radeon_pm_info", radeon_debugfs_pm_info, 0, NULL}, +}; +#endif + +int radeon_debugfs_pm_init(struct radeon_device *rdev) +{ +#if defined(CONFIG_DEBUG_FS) + return radeon_debugfs_add_files(rdev, radeon_pm_info_list, ARRAY_SIZE(radeon_pm_info_list)); +#else + return 0; +#endif +} diff --git a/drivers/gpu/drm/radeon/radeon_reg.h b/drivers/gpu/drm/radeon/radeon_reg.h index bfa1ab9c93e1..29ab75903ec1 100644 --- a/drivers/gpu/drm/radeon/radeon_reg.h +++ b/drivers/gpu/drm/radeon/radeon_reg.h @@ -290,6 +290,8 @@ #define RADEON_BUS_CNTL 0x0030 # define RADEON_BUS_MASTER_DIS (1 << 6) # define RADEON_BUS_BIOS_DIS_ROM (1 << 12) +# define RS600_BUS_MASTER_DIS (1 << 14) +# define RS600_MSI_REARM (1 << 20) /* rs600/rs690/rs740 */ # define RADEON_BUS_RD_DISCARD_EN (1 << 24) # define RADEON_BUS_RD_ABORT_EN (1 << 25) # define RADEON_BUS_MSTR_DISCONNECT_EN (1 << 28) @@ -297,6 +299,9 @@ # define RADEON_BUS_READ_BURST (1 << 30) #define RADEON_BUS_CNTL1 0x0034 # define RADEON_BUS_WAIT_ON_LOCK_EN (1 << 4) +/* rv370/rv380, rv410, r423/r430/r480, r5xx */ +#define RADEON_MSI_REARM_EN 0x0160 +# define RV370_MSI_REARM_EN (1 << 0) /* #define RADEON_PCIE_INDEX 0x0030 */ /* #define RADEON_PCIE_DATA 0x0034 */ @@ -3311,6 +3316,7 @@ #define RADEON_AIC_CNTL 0x01d0 # define RADEON_PCIGART_TRANSLATE_EN (1 << 0) # define RADEON_DIS_OUT_OF_PCI_GART_ACCESS (1 << 1) +# define RS400_MSI_REARM (1 << 3) /* rs400/rs480 */ #define RADEON_AIC_LO_ADDR 0x01dc #define RADEON_AIC_PT_BASE 0x01d8 #define RADEON_AIC_HI_ADDR 0x01e0 diff --git a/drivers/gpu/drm/radeon/radeon_test.c b/drivers/gpu/drm/radeon/radeon_test.c index 03c33cf4e14c..f8a465d9a1cf 100644 --- a/drivers/gpu/drm/radeon/radeon_test.c +++ b/drivers/gpu/drm/radeon/radeon_test.c @@ -42,7 +42,7 @@ void radeon_test_moves(struct radeon_device *rdev) /* Number of tests = * (Total GTT - IB pool - writeback page - ring buffer) / test size */ - n = (rdev->mc.gtt_size - RADEON_IB_POOL_SIZE*64*1024 - 4096 - + n = (rdev->mc.gtt_size - RADEON_IB_POOL_SIZE*64*1024 - RADEON_GPU_PAGE_SIZE - rdev->cp.ring_size) / size; gtt_obj = kzalloc(n * sizeof(*gtt_obj), GFP_KERNEL); @@ -102,7 +102,7 @@ void radeon_test_moves(struct radeon_device *rdev) goto out_cleanup; } - r = radeon_copy(rdev, gtt_addr, vram_addr, size / 4096, fence); + r = radeon_copy(rdev, gtt_addr, vram_addr, size / RADEON_GPU_PAGE_SIZE, fence); if (r) { DRM_ERROR("Failed GTT->VRAM copy %d\n", i); goto out_cleanup; @@ -145,7 +145,7 @@ void radeon_test_moves(struct radeon_device *rdev) goto out_cleanup; } - r = radeon_copy(rdev, vram_addr, gtt_addr, size / 4096, fence); + r = radeon_copy(rdev, vram_addr, gtt_addr, size / RADEON_GPU_PAGE_SIZE, fence); if (r) { DRM_ERROR("Failed VRAM->GTT copy %d\n", i); goto out_cleanup; diff --git a/drivers/gpu/drm/radeon/radeon_ttm.c b/drivers/gpu/drm/radeon/radeon_ttm.c index 765bd184b6fc..1381e06d6af3 100644 --- a/drivers/gpu/drm/radeon/radeon_ttm.c +++ b/drivers/gpu/drm/radeon/radeon_ttm.c @@ -295,6 +295,12 @@ static int radeon_move_vram_ram(struct ttm_buffer_object *bo, if (unlikely(r)) { return r; } + + r = ttm_tt_set_placement_caching(bo->ttm, tmp_mem.placement); + if (unlikely(r)) { + goto out_cleanup; + } + r = ttm_tt_bind(bo->ttm, &tmp_mem); if (unlikely(r)) { goto out_cleanup; diff --git a/drivers/gpu/drm/radeon/rs100d.h b/drivers/gpu/drm/radeon/rs100d.h new file mode 100644 index 000000000000..48a913a06cfd --- /dev/null +++ b/drivers/gpu/drm/radeon/rs100d.h @@ -0,0 +1,40 @@ +/* + * Copyright 2008 Advanced Micro Devices, Inc. + * Copyright 2008 Red Hat Inc. + * Copyright 2009 Jerome Glisse. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Alex Deucher + * Jerome Glisse + */ +#ifndef __RS100D_H__ +#define __RS100D_H__ + +/* Registers */ +#define R_00015C_NB_TOM 0x00015C +#define S_00015C_MC_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_00015C_MC_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_00015C_MC_FB_START 0xFFFF0000 +#define S_00015C_MC_FB_TOP(x) (((x) & 0xFFFF) << 16) +#define G_00015C_MC_FB_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_00015C_MC_FB_TOP 0x0000FFFF + +#endif diff --git a/drivers/gpu/drm/radeon/rs400.c b/drivers/gpu/drm/radeon/rs400.c index a3fbdad938c7..ca037160a582 100644 --- a/drivers/gpu/drm/radeon/rs400.c +++ b/drivers/gpu/drm/radeon/rs400.c @@ -27,27 +27,12 @@ */ #include <linux/seq_file.h> #include <drm/drmP.h> -#include "radeon_reg.h" #include "radeon.h" +#include "rs400d.h" -/* rs400,rs480 depends on : */ -void r100_hdp_reset(struct radeon_device *rdev); -void r100_mc_disable_clients(struct radeon_device *rdev); -int r300_mc_wait_for_idle(struct radeon_device *rdev); -void r420_pipes_init(struct radeon_device *rdev); +/* This files gather functions specifics to : rs400,rs480 */ +static int rs400_debugfs_pcie_gart_info_init(struct radeon_device *rdev); -/* This files gather functions specifics to : - * rs400,rs480 - * - * Some of these functions might be used by newer ASICs. - */ -void rs400_gpu_init(struct radeon_device *rdev); -int rs400_debugfs_pcie_gart_info_init(struct radeon_device *rdev); - - -/* - * GART functions. - */ void rs400_gart_adjust_size(struct radeon_device *rdev) { /* Check gart size */ @@ -238,61 +223,6 @@ int rs400_gart_set_page(struct radeon_device *rdev, int i, uint64_t addr) return 0; } - -/* - * MC functions. - */ -int rs400_mc_init(struct radeon_device *rdev) -{ - uint32_t tmp; - int r; - - if (r100_debugfs_rbbm_init(rdev)) { - DRM_ERROR("Failed to register debugfs file for RBBM !\n"); - } - - rs400_gpu_init(rdev); - rs400_gart_disable(rdev); - rdev->mc.gtt_location = rdev->mc.mc_vram_size; - rdev->mc.gtt_location += (rdev->mc.gtt_size - 1); - rdev->mc.gtt_location &= ~(rdev->mc.gtt_size - 1); - r = radeon_mc_setup(rdev); - if (r) { - return r; - } - - r100_mc_disable_clients(rdev); - if (r300_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait MC idle while " - "programming pipes. Bad things might happen.\n"); - } - - tmp = rdev->mc.vram_location + rdev->mc.mc_vram_size - 1; - tmp = REG_SET(RADEON_MC_FB_TOP, tmp >> 16); - tmp |= REG_SET(RADEON_MC_FB_START, rdev->mc.vram_location >> 16); - WREG32(RADEON_MC_FB_LOCATION, tmp); - tmp = RREG32(RADEON_HOST_PATH_CNTL) | RADEON_HP_LIN_RD_CACHE_DIS; - WREG32(RADEON_HOST_PATH_CNTL, tmp | RADEON_HDP_SOFT_RESET | RADEON_HDP_READ_BUFFER_INVALIDATE); - (void)RREG32(RADEON_HOST_PATH_CNTL); - WREG32(RADEON_HOST_PATH_CNTL, tmp); - (void)RREG32(RADEON_HOST_PATH_CNTL); - - return 0; -} - -void rs400_mc_fini(struct radeon_device *rdev) -{ -} - - -/* - * Global GPU functions - */ -void rs400_errata(struct radeon_device *rdev) -{ - rdev->pll_errata = 0; -} - void rs400_gpu_init(struct radeon_device *rdev) { /* FIXME: HDP same place on rs400 ? */ @@ -305,10 +235,6 @@ void rs400_gpu_init(struct radeon_device *rdev) } } - -/* - * VRAM info. - */ void rs400_vram_info(struct radeon_device *rdev) { rs400_gart_adjust_size(rdev); @@ -319,10 +245,6 @@ void rs400_vram_info(struct radeon_device *rdev) r100_vram_init_sizes(rdev); } - -/* - * Indirect registers accessor - */ uint32_t rs400_mc_rreg(struct radeon_device *rdev, uint32_t reg) { uint32_t r; @@ -340,10 +262,6 @@ void rs400_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v) WREG32(RS480_NB_MC_INDEX, 0xff); } - -/* - * Debugfs info - */ #if defined(CONFIG_DEBUG_FS) static int rs400_debugfs_gart_info(struct seq_file *m, void *data) { @@ -419,7 +337,7 @@ static struct drm_info_list rs400_gart_info_list[] = { }; #endif -int rs400_debugfs_pcie_gart_info_init(struct radeon_device *rdev) +static int rs400_debugfs_pcie_gart_info_init(struct radeon_device *rdev) { #if defined(CONFIG_DEBUG_FS) return radeon_debugfs_add_files(rdev, rs400_gart_info_list, 1); @@ -427,3 +345,190 @@ int rs400_debugfs_pcie_gart_info_init(struct radeon_device *rdev) return 0; #endif } + +static int rs400_mc_init(struct radeon_device *rdev) +{ + int r; + u32 tmp; + + /* Setup GPU memory space */ + tmp = G_00015C_MC_FB_START(RREG32(R_00015C_NB_TOM)); + rdev->mc.vram_location = G_00015C_MC_FB_START(tmp) << 16; + rdev->mc.gtt_location = 0xFFFFFFFFUL; + r = radeon_mc_setup(rdev); + if (r) + return r; + return 0; +} + +void rs400_mc_program(struct radeon_device *rdev) +{ + struct r100_mc_save save; + + /* Stops all mc clients */ + r100_mc_stop(rdev, &save); + + /* Wait for mc idle */ + if (r300_mc_wait_for_idle(rdev)) + dev_warn(rdev->dev, "Wait MC idle timeout before updating MC.\n"); + WREG32(R_000148_MC_FB_LOCATION, + S_000148_MC_FB_START(rdev->mc.vram_start >> 16) | + S_000148_MC_FB_TOP(rdev->mc.vram_end >> 16)); + + r100_mc_resume(rdev, &save); +} + +static int rs400_startup(struct radeon_device *rdev) +{ + int r; + + rs400_mc_program(rdev); + /* Resume clock */ + r300_clock_startup(rdev); + /* Initialize GPU configuration (# pipes, ...) */ + rs400_gpu_init(rdev); + /* Initialize GART (initialize after TTM so we can allocate + * memory through TTM but finalize after TTM) */ + r = rs400_gart_enable(rdev); + if (r) + return r; + /* Enable IRQ */ + rdev->irq.sw_int = true; + r100_irq_set(rdev); + /* 1M ring buffer */ + r = r100_cp_init(rdev, 1024 * 1024); + if (r) { + dev_err(rdev->dev, "failled initializing CP (%d).\n", r); + return r; + } + r = r100_wb_init(rdev); + if (r) + dev_err(rdev->dev, "failled initializing WB (%d).\n", r); + r = r100_ib_init(rdev); + if (r) { + dev_err(rdev->dev, "failled initializing IB (%d).\n", r); + return r; + } + return 0; +} + +int rs400_resume(struct radeon_device *rdev) +{ + /* Make sur GART are not working */ + rs400_gart_disable(rdev); + /* Resume clock before doing reset */ + r300_clock_startup(rdev); + /* setup MC before calling post tables */ + rs400_mc_program(rdev); + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* post */ + radeon_combios_asic_init(rdev->ddev); + /* Resume clock after posting */ + r300_clock_startup(rdev); + return rs400_startup(rdev); +} + +int rs400_suspend(struct radeon_device *rdev) +{ + r100_cp_disable(rdev); + r100_wb_disable(rdev); + r100_irq_disable(rdev); + rs400_gart_disable(rdev); + return 0; +} + +void rs400_fini(struct radeon_device *rdev) +{ + rs400_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + radeon_gem_fini(rdev); + rs400_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + radeon_fence_driver_fini(rdev); + radeon_object_fini(rdev); + radeon_atombios_fini(rdev); + kfree(rdev->bios); + rdev->bios = NULL; +} + +int rs400_init(struct radeon_device *rdev) +{ + int r; + + /* Disable VGA */ + r100_vga_render_disable(rdev); + /* Initialize scratch registers */ + radeon_scratch_init(rdev); + /* Initialize surface registers */ + radeon_surface_init(rdev); + /* TODO: disable VGA need to use VGA request */ + /* BIOS*/ + if (!radeon_get_bios(rdev)) { + if (ASIC_IS_AVIVO(rdev)) + return -EINVAL; + } + if (rdev->is_atom_bios) { + dev_err(rdev->dev, "Expecting combios for RS400/RS480 GPU\n"); + return -EINVAL; + } else { + r = radeon_combios_init(rdev); + if (r) + return r; + } + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, + "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* check if cards are posted or not */ + if (!radeon_card_posted(rdev) && rdev->bios) { + DRM_INFO("GPU not posted. posting now...\n"); + radeon_combios_asic_init(rdev->ddev); + } + /* Initialize clocks */ + radeon_get_clock_info(rdev->ddev); + /* Get vram informations */ + rs400_vram_info(rdev); + /* Initialize memory controller (also test AGP) */ + r = rs400_mc_init(rdev); + if (r) + return r; + /* Fence driver */ + r = radeon_fence_driver_init(rdev); + if (r) + return r; + r = radeon_irq_kms_init(rdev); + if (r) + return r; + /* Memory manager */ + r = radeon_object_init(rdev); + if (r) + return r; + r = rs400_gart_init(rdev); + if (r) + return r; + r300_set_reg_safe(rdev); + rdev->accel_working = true; + r = rs400_startup(rdev); + if (r) { + /* Somethings want wront with the accel init stop accel */ + dev_err(rdev->dev, "Disabling GPU acceleration\n"); + rs400_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + rs400_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + rdev->accel_working = false; + } + return 0; +} diff --git a/drivers/gpu/drm/radeon/rs400d.h b/drivers/gpu/drm/radeon/rs400d.h new file mode 100644 index 000000000000..6d8bac58ced9 --- /dev/null +++ b/drivers/gpu/drm/radeon/rs400d.h @@ -0,0 +1,160 @@ +/* + * Copyright 2008 Advanced Micro Devices, Inc. + * Copyright 2008 Red Hat Inc. + * Copyright 2009 Jerome Glisse. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Alex Deucher + * Jerome Glisse + */ +#ifndef __RS400D_H__ +#define __RS400D_H__ + +/* Registers */ +#define R_000148_MC_FB_LOCATION 0x000148 +#define S_000148_MC_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_000148_MC_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_000148_MC_FB_START 0xFFFF0000 +#define S_000148_MC_FB_TOP(x) (((x) & 0xFFFF) << 16) +#define G_000148_MC_FB_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_000148_MC_FB_TOP 0x0000FFFF +#define R_00015C_NB_TOM 0x00015C +#define S_00015C_MC_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_00015C_MC_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_00015C_MC_FB_START 0xFFFF0000 +#define S_00015C_MC_FB_TOP(x) (((x) & 0xFFFF) << 16) +#define G_00015C_MC_FB_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_00015C_MC_FB_TOP 0x0000FFFF +#define R_0007C0_CP_STAT 0x0007C0 +#define S_0007C0_MRU_BUSY(x) (((x) & 0x1) << 0) +#define G_0007C0_MRU_BUSY(x) (((x) >> 0) & 0x1) +#define C_0007C0_MRU_BUSY 0xFFFFFFFE +#define S_0007C0_MWU_BUSY(x) (((x) & 0x1) << 1) +#define G_0007C0_MWU_BUSY(x) (((x) >> 1) & 0x1) +#define C_0007C0_MWU_BUSY 0xFFFFFFFD +#define S_0007C0_RSIU_BUSY(x) (((x) & 0x1) << 2) +#define G_0007C0_RSIU_BUSY(x) (((x) >> 2) & 0x1) +#define C_0007C0_RSIU_BUSY 0xFFFFFFFB +#define S_0007C0_RCIU_BUSY(x) (((x) & 0x1) << 3) +#define G_0007C0_RCIU_BUSY(x) (((x) >> 3) & 0x1) +#define C_0007C0_RCIU_BUSY 0xFFFFFFF7 +#define S_0007C0_CSF_PRIMARY_BUSY(x) (((x) & 0x1) << 9) +#define G_0007C0_CSF_PRIMARY_BUSY(x) (((x) >> 9) & 0x1) +#define C_0007C0_CSF_PRIMARY_BUSY 0xFFFFFDFF +#define S_0007C0_CSF_INDIRECT_BUSY(x) (((x) & 0x1) << 10) +#define G_0007C0_CSF_INDIRECT_BUSY(x) (((x) >> 10) & 0x1) +#define C_0007C0_CSF_INDIRECT_BUSY 0xFFFFFBFF +#define S_0007C0_CSQ_PRIMARY_BUSY(x) (((x) & 0x1) << 11) +#define G_0007C0_CSQ_PRIMARY_BUSY(x) (((x) >> 11) & 0x1) +#define C_0007C0_CSQ_PRIMARY_BUSY 0xFFFFF7FF +#define S_0007C0_CSQ_INDIRECT_BUSY(x) (((x) & 0x1) << 12) +#define G_0007C0_CSQ_INDIRECT_BUSY(x) (((x) >> 12) & 0x1) +#define C_0007C0_CSQ_INDIRECT_BUSY 0xFFFFEFFF +#define S_0007C0_CSI_BUSY(x) (((x) & 0x1) << 13) +#define G_0007C0_CSI_BUSY(x) (((x) >> 13) & 0x1) +#define C_0007C0_CSI_BUSY 0xFFFFDFFF +#define S_0007C0_CSF_INDIRECT2_BUSY(x) (((x) & 0x1) << 14) +#define G_0007C0_CSF_INDIRECT2_BUSY(x) (((x) >> 14) & 0x1) +#define C_0007C0_CSF_INDIRECT2_BUSY 0xFFFFBFFF +#define S_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) & 0x1) << 15) +#define G_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) >> 15) & 0x1) +#define C_0007C0_CSQ_INDIRECT2_BUSY 0xFFFF7FFF +#define S_0007C0_GUIDMA_BUSY(x) (((x) & 0x1) << 28) +#define G_0007C0_GUIDMA_BUSY(x) (((x) >> 28) & 0x1) +#define C_0007C0_GUIDMA_BUSY 0xEFFFFFFF +#define S_0007C0_VIDDMA_BUSY(x) (((x) & 0x1) << 29) +#define G_0007C0_VIDDMA_BUSY(x) (((x) >> 29) & 0x1) +#define C_0007C0_VIDDMA_BUSY 0xDFFFFFFF +#define S_0007C0_CMDSTRM_BUSY(x) (((x) & 0x1) << 30) +#define G_0007C0_CMDSTRM_BUSY(x) (((x) >> 30) & 0x1) +#define C_0007C0_CMDSTRM_BUSY 0xBFFFFFFF +#define S_0007C0_CP_BUSY(x) (((x) & 0x1) << 31) +#define G_0007C0_CP_BUSY(x) (((x) >> 31) & 0x1) +#define C_0007C0_CP_BUSY 0x7FFFFFFF +#define R_000E40_RBBM_STATUS 0x000E40 +#define S_000E40_CMDFIFO_AVAIL(x) (((x) & 0x7F) << 0) +#define G_000E40_CMDFIFO_AVAIL(x) (((x) >> 0) & 0x7F) +#define C_000E40_CMDFIFO_AVAIL 0xFFFFFF80 +#define S_000E40_HIRQ_ON_RBB(x) (((x) & 0x1) << 8) +#define G_000E40_HIRQ_ON_RBB(x) (((x) >> 8) & 0x1) +#define C_000E40_HIRQ_ON_RBB 0xFFFFFEFF +#define S_000E40_CPRQ_ON_RBB(x) (((x) & 0x1) << 9) +#define G_000E40_CPRQ_ON_RBB(x) (((x) >> 9) & 0x1) +#define C_000E40_CPRQ_ON_RBB 0xFFFFFDFF +#define S_000E40_CFRQ_ON_RBB(x) (((x) & 0x1) << 10) +#define G_000E40_CFRQ_ON_RBB(x) (((x) >> 10) & 0x1) +#define C_000E40_CFRQ_ON_RBB 0xFFFFFBFF +#define S_000E40_HIRQ_IN_RTBUF(x) (((x) & 0x1) << 11) +#define G_000E40_HIRQ_IN_RTBUF(x) (((x) >> 11) & 0x1) +#define C_000E40_HIRQ_IN_RTBUF 0xFFFFF7FF +#define S_000E40_CPRQ_IN_RTBUF(x) (((x) & 0x1) << 12) +#define G_000E40_CPRQ_IN_RTBUF(x) (((x) >> 12) & 0x1) +#define C_000E40_CPRQ_IN_RTBUF 0xFFFFEFFF +#define S_000E40_CFRQ_IN_RTBUF(x) (((x) & 0x1) << 13) +#define G_000E40_CFRQ_IN_RTBUF(x) (((x) >> 13) & 0x1) +#define C_000E40_CFRQ_IN_RTBUF 0xFFFFDFFF +#define S_000E40_CF_PIPE_BUSY(x) (((x) & 0x1) << 14) +#define G_000E40_CF_PIPE_BUSY(x) (((x) >> 14) & 0x1) +#define C_000E40_CF_PIPE_BUSY 0xFFFFBFFF +#define S_000E40_ENG_EV_BUSY(x) (((x) & 0x1) << 15) +#define G_000E40_ENG_EV_BUSY(x) (((x) >> 15) & 0x1) +#define C_000E40_ENG_EV_BUSY 0xFFFF7FFF +#define S_000E40_CP_CMDSTRM_BUSY(x) (((x) & 0x1) << 16) +#define G_000E40_CP_CMDSTRM_BUSY(x) (((x) >> 16) & 0x1) +#define C_000E40_CP_CMDSTRM_BUSY 0xFFFEFFFF +#define S_000E40_E2_BUSY(x) (((x) & 0x1) << 17) +#define G_000E40_E2_BUSY(x) (((x) >> 17) & 0x1) +#define C_000E40_E2_BUSY 0xFFFDFFFF +#define S_000E40_RB2D_BUSY(x) (((x) & 0x1) << 18) +#define G_000E40_RB2D_BUSY(x) (((x) >> 18) & 0x1) +#define C_000E40_RB2D_BUSY 0xFFFBFFFF +#define S_000E40_RB3D_BUSY(x) (((x) & 0x1) << 19) +#define G_000E40_RB3D_BUSY(x) (((x) >> 19) & 0x1) +#define C_000E40_RB3D_BUSY 0xFFF7FFFF +#define S_000E40_VAP_BUSY(x) (((x) & 0x1) << 20) +#define G_000E40_VAP_BUSY(x) (((x) >> 20) & 0x1) +#define C_000E40_VAP_BUSY 0xFFEFFFFF +#define S_000E40_RE_BUSY(x) (((x) & 0x1) << 21) +#define G_000E40_RE_BUSY(x) (((x) >> 21) & 0x1) +#define C_000E40_RE_BUSY 0xFFDFFFFF +#define S_000E40_TAM_BUSY(x) (((x) & 0x1) << 22) +#define G_000E40_TAM_BUSY(x) (((x) >> 22) & 0x1) +#define C_000E40_TAM_BUSY 0xFFBFFFFF +#define S_000E40_TDM_BUSY(x) (((x) & 0x1) << 23) +#define G_000E40_TDM_BUSY(x) (((x) >> 23) & 0x1) +#define C_000E40_TDM_BUSY 0xFF7FFFFF +#define S_000E40_PB_BUSY(x) (((x) & 0x1) << 24) +#define G_000E40_PB_BUSY(x) (((x) >> 24) & 0x1) +#define C_000E40_PB_BUSY 0xFEFFFFFF +#define S_000E40_TIM_BUSY(x) (((x) & 0x1) << 25) +#define G_000E40_TIM_BUSY(x) (((x) >> 25) & 0x1) +#define C_000E40_TIM_BUSY 0xFDFFFFFF +#define S_000E40_GA_BUSY(x) (((x) & 0x1) << 26) +#define G_000E40_GA_BUSY(x) (((x) >> 26) & 0x1) +#define C_000E40_GA_BUSY 0xFBFFFFFF +#define S_000E40_CBA2D_BUSY(x) (((x) & 0x1) << 27) +#define G_000E40_CBA2D_BUSY(x) (((x) >> 27) & 0x1) +#define C_000E40_CBA2D_BUSY 0xF7FFFFFF +#define S_000E40_GUI_ACTIVE(x) (((x) & 0x1) << 31) +#define G_000E40_GUI_ACTIVE(x) (((x) >> 31) & 0x1) +#define C_000E40_GUI_ACTIVE 0x7FFFFFFF + +#endif diff --git a/drivers/gpu/drm/radeon/rs600.c b/drivers/gpu/drm/radeon/rs600.c index 4a4fe1cb131c..5f117cd8736a 100644 --- a/drivers/gpu/drm/radeon/rs600.c +++ b/drivers/gpu/drm/radeon/rs600.c @@ -25,27 +25,26 @@ * Alex Deucher * Jerome Glisse */ +/* RS600 / Radeon X1250/X1270 integrated GPU + * + * This file gather function specific to RS600 which is the IGP of + * the X1250/X1270 family supporting intel CPU (while RS690/RS740 + * is the X1250/X1270 supporting AMD CPU). The display engine are + * the avivo one, bios is an atombios, 3D block are the one of the + * R4XX family. The GART is different from the RS400 one and is very + * close to the one of the R600 family (R600 likely being an evolution + * of the RS600 GART block). + */ #include "drmP.h" -#include "radeon_reg.h" #include "radeon.h" +#include "atom.h" +#include "rs600d.h" #include "rs600_reg_safe.h" -/* rs600 depends on : */ -void r100_hdp_reset(struct radeon_device *rdev); -int r100_gui_wait_for_idle(struct radeon_device *rdev); -int r300_mc_wait_for_idle(struct radeon_device *rdev); -void r420_pipes_init(struct radeon_device *rdev); - -/* This files gather functions specifics to : - * rs600 - * - * Some of these functions might be used by newer ASICs. - */ void rs600_gpu_init(struct radeon_device *rdev); int rs600_mc_wait_for_idle(struct radeon_device *rdev); - /* * GART. */ @@ -53,18 +52,18 @@ void rs600_gart_tlb_flush(struct radeon_device *rdev) { uint32_t tmp; - tmp = RREG32_MC(RS600_MC_PT0_CNTL); - tmp &= ~(RS600_INVALIDATE_ALL_L1_TLBS | RS600_INVALIDATE_L2_CACHE); - WREG32_MC(RS600_MC_PT0_CNTL, tmp); + tmp = RREG32_MC(R_000100_MC_PT0_CNTL); + tmp &= C_000100_INVALIDATE_ALL_L1_TLBS & C_000100_INVALIDATE_L2_CACHE; + WREG32_MC(R_000100_MC_PT0_CNTL, tmp); - tmp = RREG32_MC(RS600_MC_PT0_CNTL); - tmp |= RS600_INVALIDATE_ALL_L1_TLBS | RS600_INVALIDATE_L2_CACHE; - WREG32_MC(RS600_MC_PT0_CNTL, tmp); + tmp = RREG32_MC(R_000100_MC_PT0_CNTL); + tmp |= S_000100_INVALIDATE_ALL_L1_TLBS(1) & S_000100_INVALIDATE_L2_CACHE(1); + WREG32_MC(R_000100_MC_PT0_CNTL, tmp); - tmp = RREG32_MC(RS600_MC_PT0_CNTL); - tmp &= ~(RS600_INVALIDATE_ALL_L1_TLBS | RS600_INVALIDATE_L2_CACHE); - WREG32_MC(RS600_MC_PT0_CNTL, tmp); - tmp = RREG32_MC(RS600_MC_PT0_CNTL); + tmp = RREG32_MC(R_000100_MC_PT0_CNTL); + tmp &= C_000100_INVALIDATE_ALL_L1_TLBS & C_000100_INVALIDATE_L2_CACHE; + WREG32_MC(R_000100_MC_PT0_CNTL, tmp); + tmp = RREG32_MC(R_000100_MC_PT0_CNTL); } int rs600_gart_init(struct radeon_device *rdev) @@ -86,7 +85,7 @@ int rs600_gart_init(struct radeon_device *rdev) int rs600_gart_enable(struct radeon_device *rdev) { - uint32_t tmp; + u32 tmp; int r, i; if (rdev->gart.table.vram.robj == NULL) { @@ -96,46 +95,50 @@ int rs600_gart_enable(struct radeon_device *rdev) r = radeon_gart_table_vram_pin(rdev); if (r) return r; + /* Enable bus master */ + tmp = RREG32(R_00004C_BUS_CNTL) & C_00004C_BUS_MASTER_DIS; + WREG32(R_00004C_BUS_CNTL, tmp); /* FIXME: setup default page */ - WREG32_MC(RS600_MC_PT0_CNTL, - (RS600_EFFECTIVE_L2_CACHE_SIZE(6) | - RS600_EFFECTIVE_L2_QUEUE_SIZE(6))); + WREG32_MC(R_000100_MC_PT0_CNTL, + (S_000100_EFFECTIVE_L2_CACHE_SIZE(6) | + S_000100_EFFECTIVE_L2_QUEUE_SIZE(6))); for (i = 0; i < 19; i++) { - WREG32_MC(RS600_MC_PT0_CLIENT0_CNTL + i, - (RS600_ENABLE_TRANSLATION_MODE_OVERRIDE | - RS600_SYSTEM_ACCESS_MODE_IN_SYS | - RS600_SYSTEM_APERTURE_UNMAPPED_ACCESS_DEFAULT_PAGE | - RS600_EFFECTIVE_L1_CACHE_SIZE(3) | - RS600_ENABLE_FRAGMENT_PROCESSING | - RS600_EFFECTIVE_L1_QUEUE_SIZE(3))); + WREG32_MC(R_00016C_MC_PT0_CLIENT0_CNTL + i, + S_00016C_ENABLE_TRANSLATION_MODE_OVERRIDE(1) | + S_00016C_SYSTEM_ACCESS_MODE_MASK( + V_00016C_SYSTEM_ACCESS_MODE_IN_SYS) | + S_00016C_SYSTEM_APERTURE_UNMAPPED_ACCESS( + V_00016C_SYSTEM_APERTURE_UNMAPPED_DEFAULT_PAGE) | + S_00016C_EFFECTIVE_L1_CACHE_SIZE(1) | + S_00016C_ENABLE_FRAGMENT_PROCESSING(1) | + S_00016C_EFFECTIVE_L1_QUEUE_SIZE(1)); } /* System context map to GART space */ - WREG32_MC(RS600_MC_PT0_SYSTEM_APERTURE_LOW_ADDR, rdev->mc.gtt_location); - tmp = rdev->mc.gtt_location + rdev->mc.gtt_size - 1; - WREG32_MC(RS600_MC_PT0_SYSTEM_APERTURE_HIGH_ADDR, tmp); + WREG32_MC(R_000112_MC_PT0_SYSTEM_APERTURE_LOW_ADDR, rdev->mc.gtt_start); + WREG32_MC(R_000114_MC_PT0_SYSTEM_APERTURE_HIGH_ADDR, rdev->mc.gtt_end); /* enable first context */ - WREG32_MC(RS600_MC_PT0_CONTEXT0_FLAT_START_ADDR, rdev->mc.gtt_location); - tmp = rdev->mc.gtt_location + rdev->mc.gtt_size - 1; - WREG32_MC(RS600_MC_PT0_CONTEXT0_FLAT_END_ADDR, tmp); - WREG32_MC(RS600_MC_PT0_CONTEXT0_CNTL, - (RS600_ENABLE_PAGE_TABLE | RS600_PAGE_TABLE_TYPE_FLAT)); + WREG32_MC(R_00013C_MC_PT0_CONTEXT0_FLAT_START_ADDR, rdev->mc.gtt_start); + WREG32_MC(R_00014C_MC_PT0_CONTEXT0_FLAT_END_ADDR, rdev->mc.gtt_end); + WREG32_MC(R_000102_MC_PT0_CONTEXT0_CNTL, + S_000102_ENABLE_PAGE_TABLE(1) | + S_000102_PAGE_TABLE_DEPTH(V_000102_PAGE_TABLE_FLAT)); /* disable all other contexts */ for (i = 1; i < 8; i++) { - WREG32_MC(RS600_MC_PT0_CONTEXT0_CNTL + i, 0); + WREG32_MC(R_000102_MC_PT0_CONTEXT0_CNTL + i, 0); } /* setup the page table */ - WREG32_MC(RS600_MC_PT0_CONTEXT0_FLAT_BASE_ADDR, - rdev->gart.table_addr); - WREG32_MC(RS600_MC_PT0_CONTEXT0_DEFAULT_READ_ADDR, 0); + WREG32_MC(R_00012C_MC_PT0_CONTEXT0_FLAT_BASE_ADDR, + rdev->gart.table_addr); + WREG32_MC(R_00011C_MC_PT0_CONTEXT0_DEFAULT_READ_ADDR, 0); /* enable page tables */ - tmp = RREG32_MC(RS600_MC_PT0_CNTL); - WREG32_MC(RS600_MC_PT0_CNTL, (tmp | RS600_ENABLE_PT)); - tmp = RREG32_MC(RS600_MC_CNTL1); - WREG32_MC(RS600_MC_CNTL1, (tmp | RS600_ENABLE_PAGE_TABLES)); + tmp = RREG32_MC(R_000100_MC_PT0_CNTL); + WREG32_MC(R_000100_MC_PT0_CNTL, (tmp | S_000100_ENABLE_PT(1))); + tmp = RREG32_MC(R_000009_MC_CNTL1); + WREG32_MC(R_000009_MC_CNTL1, (tmp | S_000009_ENABLE_PAGE_TABLES(1))); rs600_gart_tlb_flush(rdev); rdev->gart.ready = true; return 0; @@ -146,10 +149,9 @@ void rs600_gart_disable(struct radeon_device *rdev) uint32_t tmp; /* FIXME: disable out of gart access */ - WREG32_MC(RS600_MC_PT0_CNTL, 0); - tmp = RREG32_MC(RS600_MC_CNTL1); - tmp &= ~RS600_ENABLE_PAGE_TABLES; - WREG32_MC(RS600_MC_CNTL1, tmp); + WREG32_MC(R_000100_MC_PT0_CNTL, 0); + tmp = RREG32_MC(R_000009_MC_CNTL1); + WREG32_MC(R_000009_MC_CNTL1, tmp & C_000009_ENABLE_PAGE_TABLES); if (rdev->gart.table.vram.robj) { radeon_object_kunmap(rdev->gart.table.vram.robj); radeon_object_unpin(rdev->gart.table.vram.robj); @@ -183,132 +185,64 @@ int rs600_gart_set_page(struct radeon_device *rdev, int i, uint64_t addr) return 0; } - -/* - * MC. - */ -void rs600_mc_disable_clients(struct radeon_device *rdev) -{ - unsigned tmp; - - if (r100_gui_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait GUI idle while " - "programming pipes. Bad things might happen.\n"); - } - - rv515_vga_render_disable(rdev); - - tmp = RREG32(AVIVO_D1VGA_CONTROL); - WREG32(AVIVO_D1VGA_CONTROL, tmp & ~AVIVO_DVGA_CONTROL_MODE_ENABLE); - tmp = RREG32(AVIVO_D2VGA_CONTROL); - WREG32(AVIVO_D2VGA_CONTROL, tmp & ~AVIVO_DVGA_CONTROL_MODE_ENABLE); - - tmp = RREG32(AVIVO_D1CRTC_CONTROL); - WREG32(AVIVO_D1CRTC_CONTROL, tmp & ~AVIVO_CRTC_EN); - tmp = RREG32(AVIVO_D2CRTC_CONTROL); - WREG32(AVIVO_D2CRTC_CONTROL, tmp & ~AVIVO_CRTC_EN); - - /* make sure all previous write got through */ - tmp = RREG32(AVIVO_D2CRTC_CONTROL); - - mdelay(1); -} - -int rs600_mc_init(struct radeon_device *rdev) -{ - uint32_t tmp; - int r; - - if (r100_debugfs_rbbm_init(rdev)) { - DRM_ERROR("Failed to register debugfs file for RBBM !\n"); - } - - rs600_gpu_init(rdev); - rs600_gart_disable(rdev); - - /* Setup GPU memory space */ - rdev->mc.vram_location = 0xFFFFFFFFUL; - rdev->mc.gtt_location = 0xFFFFFFFFUL; - r = radeon_mc_setup(rdev); - if (r) { - return r; - } - - /* Program GPU memory space */ - /* Enable bus master */ - tmp = RREG32(RADEON_BUS_CNTL) & ~RS600_BUS_MASTER_DIS; - WREG32(RADEON_BUS_CNTL, tmp); - /* FIXME: What does AGP means for such chipset ? */ - WREG32_MC(RS600_MC_AGP_LOCATION, 0x0FFFFFFF); - /* FIXME: are this AGP reg in indirect MC range ? */ - WREG32_MC(RS600_MC_AGP_BASE, 0); - WREG32_MC(RS600_MC_AGP_BASE_2, 0); - rs600_mc_disable_clients(rdev); - if (rs600_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait MC idle while " - "programming pipes. Bad things might happen.\n"); - } - tmp = rdev->mc.vram_location + rdev->mc.mc_vram_size - 1; - tmp = REG_SET(RS600_MC_FB_TOP, tmp >> 16); - tmp |= REG_SET(RS600_MC_FB_START, rdev->mc.vram_location >> 16); - WREG32_MC(RS600_MC_FB_LOCATION, tmp); - WREG32(RS690_HDP_FB_LOCATION, rdev->mc.vram_location >> 16); - return 0; -} - -void rs600_mc_fini(struct radeon_device *rdev) -{ -} - - -/* - * Interrupts - */ int rs600_irq_set(struct radeon_device *rdev) { uint32_t tmp = 0; uint32_t mode_int = 0; if (rdev->irq.sw_int) { - tmp |= RADEON_SW_INT_ENABLE; + tmp |= S_000040_SW_INT_EN(1); } if (rdev->irq.crtc_vblank_int[0]) { - mode_int |= AVIVO_D1MODE_INT_MASK; + mode_int |= S_006540_D1MODE_VBLANK_INT_MASK(1); } if (rdev->irq.crtc_vblank_int[1]) { - mode_int |= AVIVO_D2MODE_INT_MASK; + mode_int |= S_006540_D2MODE_VBLANK_INT_MASK(1); } - WREG32(RADEON_GEN_INT_CNTL, tmp); - WREG32(AVIVO_DxMODE_INT_MASK, mode_int); + WREG32(R_000040_GEN_INT_CNTL, tmp); + WREG32(R_006540_DxMODE_INT_MASK, mode_int); return 0; } static inline uint32_t rs600_irq_ack(struct radeon_device *rdev, u32 *r500_disp_int) { - uint32_t irqs = RREG32(RADEON_GEN_INT_STATUS); - uint32_t irq_mask = RADEON_SW_INT_TEST; - - if (irqs & AVIVO_DISPLAY_INT_STATUS) { - *r500_disp_int = RREG32(AVIVO_DISP_INTERRUPT_STATUS); - if (*r500_disp_int & AVIVO_D1_VBLANK_INTERRUPT) { - WREG32(AVIVO_D1MODE_VBLANK_STATUS, AVIVO_VBLANK_ACK); + uint32_t irqs = RREG32(R_000044_GEN_INT_STATUS); + uint32_t irq_mask = ~C_000044_SW_INT; + + if (G_000044_DISPLAY_INT_STAT(irqs)) { + *r500_disp_int = RREG32(R_007EDC_DISP_INTERRUPT_STATUS); + if (G_007EDC_LB_D1_VBLANK_INTERRUPT(*r500_disp_int)) { + WREG32(R_006534_D1MODE_VBLANK_STATUS, + S_006534_D1MODE_VBLANK_ACK(1)); } - if (*r500_disp_int & AVIVO_D2_VBLANK_INTERRUPT) { - WREG32(AVIVO_D2MODE_VBLANK_STATUS, AVIVO_VBLANK_ACK); + if (G_007EDC_LB_D2_VBLANK_INTERRUPT(*r500_disp_int)) { + WREG32(R_006D34_D2MODE_VBLANK_STATUS, + S_006D34_D2MODE_VBLANK_ACK(1)); } } else { *r500_disp_int = 0; } if (irqs) { - WREG32(RADEON_GEN_INT_STATUS, irqs); + WREG32(R_000044_GEN_INT_STATUS, irqs); } return irqs & irq_mask; } +void rs600_irq_disable(struct radeon_device *rdev) +{ + u32 tmp; + + WREG32(R_000040_GEN_INT_CNTL, 0); + WREG32(R_006540_DxMODE_INT_MASK, 0); + /* Wait and acknowledge irq */ + mdelay(1); + rs600_irq_ack(rdev, &tmp); +} + int rs600_irq_process(struct radeon_device *rdev) { - uint32_t status; + uint32_t status, msi_rearm; uint32_t r500_disp_int; status = rs600_irq_ack(rdev, &r500_disp_int); @@ -317,71 +251,65 @@ int rs600_irq_process(struct radeon_device *rdev) } while (status || r500_disp_int) { /* SW interrupt */ - if (status & RADEON_SW_INT_TEST) { + if (G_000040_SW_INT_EN(status)) radeon_fence_process(rdev); - } /* Vertical blank interrupts */ - if (r500_disp_int & AVIVO_D1_VBLANK_INTERRUPT) { + if (G_007EDC_LB_D1_VBLANK_INTERRUPT(r500_disp_int)) drm_handle_vblank(rdev->ddev, 0); - } - if (r500_disp_int & AVIVO_D2_VBLANK_INTERRUPT) { + if (G_007EDC_LB_D2_VBLANK_INTERRUPT(r500_disp_int)) drm_handle_vblank(rdev->ddev, 1); - } status = rs600_irq_ack(rdev, &r500_disp_int); } + if (rdev->msi_enabled) { + switch (rdev->family) { + case CHIP_RS600: + case CHIP_RS690: + case CHIP_RS740: + msi_rearm = RREG32(RADEON_BUS_CNTL) & ~RS600_MSI_REARM; + WREG32(RADEON_BUS_CNTL, msi_rearm); + WREG32(RADEON_BUS_CNTL, msi_rearm | RS600_MSI_REARM); + break; + default: + msi_rearm = RREG32(RADEON_MSI_REARM_EN) & ~RV370_MSI_REARM_EN; + WREG32(RADEON_MSI_REARM_EN, msi_rearm); + WREG32(RADEON_MSI_REARM_EN, msi_rearm | RV370_MSI_REARM_EN); + break; + } + } return IRQ_HANDLED; } u32 rs600_get_vblank_counter(struct radeon_device *rdev, int crtc) { if (crtc == 0) - return RREG32(AVIVO_D1CRTC_FRAME_COUNT); + return RREG32(R_0060A4_D1CRTC_STATUS_FRAME_COUNT); else - return RREG32(AVIVO_D2CRTC_FRAME_COUNT); + return RREG32(R_0068A4_D2CRTC_STATUS_FRAME_COUNT); } - -/* - * Global GPU functions - */ int rs600_mc_wait_for_idle(struct radeon_device *rdev) { unsigned i; - uint32_t tmp; for (i = 0; i < rdev->usec_timeout; i++) { - /* read MC_STATUS */ - tmp = RREG32_MC(RS600_MC_STATUS); - if (tmp & RS600_MC_STATUS_IDLE) { + if (G_000000_MC_IDLE(RREG32_MC(R_000000_MC_STATUS))) return 0; - } - DRM_UDELAY(1); + udelay(1); } return -1; } -void rs600_errata(struct radeon_device *rdev) -{ - rdev->pll_errata = 0; -} - void rs600_gpu_init(struct radeon_device *rdev) { /* FIXME: HDP same place on rs600 ? */ r100_hdp_reset(rdev); - rv515_vga_render_disable(rdev); /* FIXME: is this correct ? */ r420_pipes_init(rdev); - if (rs600_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait MC idle while " - "programming pipes. Bad things might happen.\n"); - } + /* Wait for mc idle */ + if (rs600_mc_wait_for_idle(rdev)) + dev_warn(rdev->dev, "Wait MC idle timeout before updating MC.\n"); } - -/* - * VRAM info. - */ void rs600_vram_info(struct radeon_device *rdev) { /* FIXME: to do or is these values sane ? */ @@ -394,31 +322,208 @@ void rs600_bandwidth_update(struct radeon_device *rdev) /* FIXME: implement, should this be like rs690 ? */ } - -/* - * Indirect registers accessor - */ uint32_t rs600_mc_rreg(struct radeon_device *rdev, uint32_t reg) { - uint32_t r; - - WREG32(RS600_MC_INDEX, - ((reg & RS600_MC_ADDR_MASK) | RS600_MC_IND_CITF_ARB0)); - r = RREG32(RS600_MC_DATA); - return r; + WREG32(R_000070_MC_IND_INDEX, S_000070_MC_IND_ADDR(reg) | + S_000070_MC_IND_CITF_ARB0(1)); + return RREG32(R_000074_MC_IND_DATA); } void rs600_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v) { - WREG32(RS600_MC_INDEX, - RS600_MC_IND_WR_EN | RS600_MC_IND_CITF_ARB0 | - ((reg) & RS600_MC_ADDR_MASK)); - WREG32(RS600_MC_DATA, v); + WREG32(R_000070_MC_IND_INDEX, S_000070_MC_IND_ADDR(reg) | + S_000070_MC_IND_CITF_ARB0(1) | S_000070_MC_IND_WR_EN(1)); + WREG32(R_000074_MC_IND_DATA, v); } -int rs600_init(struct radeon_device *rdev) +void rs600_debugfs(struct radeon_device *rdev) +{ + if (r100_debugfs_rbbm_init(rdev)) + DRM_ERROR("Failed to register debugfs file for RBBM !\n"); +} + +void rs600_set_safe_registers(struct radeon_device *rdev) { rdev->config.r300.reg_safe_bm = rs600_reg_safe_bm; rdev->config.r300.reg_safe_bm_size = ARRAY_SIZE(rs600_reg_safe_bm); +} + +static void rs600_mc_program(struct radeon_device *rdev) +{ + struct rv515_mc_save save; + + /* Stops all mc clients */ + rv515_mc_stop(rdev, &save); + + /* Wait for mc idle */ + if (rs600_mc_wait_for_idle(rdev)) + dev_warn(rdev->dev, "Wait MC idle timeout before updating MC.\n"); + + /* FIXME: What does AGP means for such chipset ? */ + WREG32_MC(R_000005_MC_AGP_LOCATION, 0x0FFFFFFF); + WREG32_MC(R_000006_AGP_BASE, 0); + WREG32_MC(R_000007_AGP_BASE_2, 0); + /* Program MC */ + WREG32_MC(R_000004_MC_FB_LOCATION, + S_000004_MC_FB_START(rdev->mc.vram_start >> 16) | + S_000004_MC_FB_TOP(rdev->mc.vram_end >> 16)); + WREG32(R_000134_HDP_FB_LOCATION, + S_000134_HDP_FB_START(rdev->mc.vram_start >> 16)); + + rv515_mc_resume(rdev, &save); +} + +static int rs600_startup(struct radeon_device *rdev) +{ + int r; + + rs600_mc_program(rdev); + /* Resume clock */ + rv515_clock_startup(rdev); + /* Initialize GPU configuration (# pipes, ...) */ + rs600_gpu_init(rdev); + /* Initialize GART (initialize after TTM so we can allocate + * memory through TTM but finalize after TTM) */ + r = rs600_gart_enable(rdev); + if (r) + return r; + /* Enable IRQ */ + rdev->irq.sw_int = true; + rs600_irq_set(rdev); + /* 1M ring buffer */ + r = r100_cp_init(rdev, 1024 * 1024); + if (r) { + dev_err(rdev->dev, "failled initializing CP (%d).\n", r); + return r; + } + r = r100_wb_init(rdev); + if (r) + dev_err(rdev->dev, "failled initializing WB (%d).\n", r); + r = r100_ib_init(rdev); + if (r) { + dev_err(rdev->dev, "failled initializing IB (%d).\n", r); + return r; + } + return 0; +} + +int rs600_resume(struct radeon_device *rdev) +{ + /* Make sur GART are not working */ + rs600_gart_disable(rdev); + /* Resume clock before doing reset */ + rv515_clock_startup(rdev); + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* post */ + atom_asic_init(rdev->mode_info.atom_context); + /* Resume clock after posting */ + rv515_clock_startup(rdev); + return rs600_startup(rdev); +} + +int rs600_suspend(struct radeon_device *rdev) +{ + r100_cp_disable(rdev); + r100_wb_disable(rdev); + rs600_irq_disable(rdev); + rs600_gart_disable(rdev); + return 0; +} + +void rs600_fini(struct radeon_device *rdev) +{ + rs600_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + radeon_gem_fini(rdev); + rs600_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + radeon_fence_driver_fini(rdev); + radeon_object_fini(rdev); + radeon_atombios_fini(rdev); + kfree(rdev->bios); + rdev->bios = NULL; +} + +int rs600_init(struct radeon_device *rdev) +{ + int r; + + /* Disable VGA */ + rv515_vga_render_disable(rdev); + /* Initialize scratch registers */ + radeon_scratch_init(rdev); + /* Initialize surface registers */ + radeon_surface_init(rdev); + /* BIOS */ + if (!radeon_get_bios(rdev)) { + if (ASIC_IS_AVIVO(rdev)) + return -EINVAL; + } + if (rdev->is_atom_bios) { + r = radeon_atombios_init(rdev); + if (r) + return r; + } else { + dev_err(rdev->dev, "Expecting atombios for RS600 GPU\n"); + return -EINVAL; + } + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, + "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* check if cards are posted or not */ + if (!radeon_card_posted(rdev) && rdev->bios) { + DRM_INFO("GPU not posted. posting now...\n"); + atom_asic_init(rdev->mode_info.atom_context); + } + /* Initialize clocks */ + radeon_get_clock_info(rdev->ddev); + /* Initialize power management */ + radeon_pm_init(rdev); + /* Get vram informations */ + rs600_vram_info(rdev); + /* Initialize memory controller (also test AGP) */ + r = r420_mc_init(rdev); + if (r) + return r; + rs600_debugfs(rdev); + /* Fence driver */ + r = radeon_fence_driver_init(rdev); + if (r) + return r; + r = radeon_irq_kms_init(rdev); + if (r) + return r; + /* Memory manager */ + r = radeon_object_init(rdev); + if (r) + return r; + r = rs600_gart_init(rdev); + if (r) + return r; + rs600_set_safe_registers(rdev); + rdev->accel_working = true; + r = rs600_startup(rdev); + if (r) { + /* Somethings want wront with the accel init stop accel */ + dev_err(rdev->dev, "Disabling GPU acceleration\n"); + rs600_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + rs600_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + rdev->accel_working = false; + } return 0; } diff --git a/drivers/gpu/drm/radeon/rs600d.h b/drivers/gpu/drm/radeon/rs600d.h new file mode 100644 index 000000000000..81308924859a --- /dev/null +++ b/drivers/gpu/drm/radeon/rs600d.h @@ -0,0 +1,470 @@ +/* + * Copyright 2008 Advanced Micro Devices, Inc. + * Copyright 2008 Red Hat Inc. + * Copyright 2009 Jerome Glisse. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Alex Deucher + * Jerome Glisse + */ +#ifndef __RS600D_H__ +#define __RS600D_H__ + +/* Registers */ +#define R_000040_GEN_INT_CNTL 0x000040 +#define S_000040_DISPLAY_INT_STATUS(x) (((x) & 0x1) << 0) +#define G_000040_DISPLAY_INT_STATUS(x) (((x) >> 0) & 0x1) +#define C_000040_DISPLAY_INT_STATUS 0xFFFFFFFE +#define S_000040_DMA_VIPH0_INT_EN(x) (((x) & 0x1) << 12) +#define G_000040_DMA_VIPH0_INT_EN(x) (((x) >> 12) & 0x1) +#define C_000040_DMA_VIPH0_INT_EN 0xFFFFEFFF +#define S_000040_CRTC2_VSYNC(x) (((x) & 0x1) << 6) +#define G_000040_CRTC2_VSYNC(x) (((x) >> 6) & 0x1) +#define C_000040_CRTC2_VSYNC 0xFFFFFFBF +#define S_000040_SNAPSHOT2(x) (((x) & 0x1) << 7) +#define G_000040_SNAPSHOT2(x) (((x) >> 7) & 0x1) +#define C_000040_SNAPSHOT2 0xFFFFFF7F +#define S_000040_CRTC2_VBLANK(x) (((x) & 0x1) << 9) +#define G_000040_CRTC2_VBLANK(x) (((x) >> 9) & 0x1) +#define C_000040_CRTC2_VBLANK 0xFFFFFDFF +#define S_000040_FP2_DETECT(x) (((x) & 0x1) << 10) +#define G_000040_FP2_DETECT(x) (((x) >> 10) & 0x1) +#define C_000040_FP2_DETECT 0xFFFFFBFF +#define S_000040_VSYNC_DIFF_OVER_LIMIT(x) (((x) & 0x1) << 11) +#define G_000040_VSYNC_DIFF_OVER_LIMIT(x) (((x) >> 11) & 0x1) +#define C_000040_VSYNC_DIFF_OVER_LIMIT 0xFFFFF7FF +#define S_000040_DMA_VIPH1_INT_EN(x) (((x) & 0x1) << 13) +#define G_000040_DMA_VIPH1_INT_EN(x) (((x) >> 13) & 0x1) +#define C_000040_DMA_VIPH1_INT_EN 0xFFFFDFFF +#define S_000040_DMA_VIPH2_INT_EN(x) (((x) & 0x1) << 14) +#define G_000040_DMA_VIPH2_INT_EN(x) (((x) >> 14) & 0x1) +#define C_000040_DMA_VIPH2_INT_EN 0xFFFFBFFF +#define S_000040_DMA_VIPH3_INT_EN(x) (((x) & 0x1) << 15) +#define G_000040_DMA_VIPH3_INT_EN(x) (((x) >> 15) & 0x1) +#define C_000040_DMA_VIPH3_INT_EN 0xFFFF7FFF +#define S_000040_I2C_INT_EN(x) (((x) & 0x1) << 17) +#define G_000040_I2C_INT_EN(x) (((x) >> 17) & 0x1) +#define C_000040_I2C_INT_EN 0xFFFDFFFF +#define S_000040_GUI_IDLE(x) (((x) & 0x1) << 19) +#define G_000040_GUI_IDLE(x) (((x) >> 19) & 0x1) +#define C_000040_GUI_IDLE 0xFFF7FFFF +#define S_000040_VIPH_INT_EN(x) (((x) & 0x1) << 24) +#define G_000040_VIPH_INT_EN(x) (((x) >> 24) & 0x1) +#define C_000040_VIPH_INT_EN 0xFEFFFFFF +#define S_000040_SW_INT_EN(x) (((x) & 0x1) << 25) +#define G_000040_SW_INT_EN(x) (((x) >> 25) & 0x1) +#define C_000040_SW_INT_EN 0xFDFFFFFF +#define S_000040_GEYSERVILLE(x) (((x) & 0x1) << 27) +#define G_000040_GEYSERVILLE(x) (((x) >> 27) & 0x1) +#define C_000040_GEYSERVILLE 0xF7FFFFFF +#define S_000040_HDCP_AUTHORIZED_INT(x) (((x) & 0x1) << 28) +#define G_000040_HDCP_AUTHORIZED_INT(x) (((x) >> 28) & 0x1) +#define C_000040_HDCP_AUTHORIZED_INT 0xEFFFFFFF +#define S_000040_DVI_I2C_INT(x) (((x) & 0x1) << 29) +#define G_000040_DVI_I2C_INT(x) (((x) >> 29) & 0x1) +#define C_000040_DVI_I2C_INT 0xDFFFFFFF +#define S_000040_GUIDMA(x) (((x) & 0x1) << 30) +#define G_000040_GUIDMA(x) (((x) >> 30) & 0x1) +#define C_000040_GUIDMA 0xBFFFFFFF +#define S_000040_VIDDMA(x) (((x) & 0x1) << 31) +#define G_000040_VIDDMA(x) (((x) >> 31) & 0x1) +#define C_000040_VIDDMA 0x7FFFFFFF +#define R_000044_GEN_INT_STATUS 0x000044 +#define S_000044_DISPLAY_INT_STAT(x) (((x) & 0x1) << 0) +#define G_000044_DISPLAY_INT_STAT(x) (((x) >> 0) & 0x1) +#define C_000044_DISPLAY_INT_STAT 0xFFFFFFFE +#define S_000044_VGA_INT_STAT(x) (((x) & 0x1) << 1) +#define G_000044_VGA_INT_STAT(x) (((x) >> 1) & 0x1) +#define C_000044_VGA_INT_STAT 0xFFFFFFFD +#define S_000044_CAP0_INT_ACTIVE(x) (((x) & 0x1) << 8) +#define G_000044_CAP0_INT_ACTIVE(x) (((x) >> 8) & 0x1) +#define C_000044_CAP0_INT_ACTIVE 0xFFFFFEFF +#define S_000044_DMA_VIPH0_INT(x) (((x) & 0x1) << 12) +#define G_000044_DMA_VIPH0_INT(x) (((x) >> 12) & 0x1) +#define C_000044_DMA_VIPH0_INT 0xFFFFEFFF +#define S_000044_DMA_VIPH1_INT(x) (((x) & 0x1) << 13) +#define G_000044_DMA_VIPH1_INT(x) (((x) >> 13) & 0x1) +#define C_000044_DMA_VIPH1_INT 0xFFFFDFFF +#define S_000044_DMA_VIPH2_INT(x) (((x) & 0x1) << 14) +#define G_000044_DMA_VIPH2_INT(x) (((x) >> 14) & 0x1) +#define C_000044_DMA_VIPH2_INT 0xFFFFBFFF +#define S_000044_DMA_VIPH3_INT(x) (((x) & 0x1) << 15) +#define G_000044_DMA_VIPH3_INT(x) (((x) >> 15) & 0x1) +#define C_000044_DMA_VIPH3_INT 0xFFFF7FFF +#define S_000044_MC_PROBE_FAULT_STAT(x) (((x) & 0x1) << 16) +#define G_000044_MC_PROBE_FAULT_STAT(x) (((x) >> 16) & 0x1) +#define C_000044_MC_PROBE_FAULT_STAT 0xFFFEFFFF +#define S_000044_I2C_INT(x) (((x) & 0x1) << 17) +#define G_000044_I2C_INT(x) (((x) >> 17) & 0x1) +#define C_000044_I2C_INT 0xFFFDFFFF +#define S_000044_SCRATCH_INT_STAT(x) (((x) & 0x1) << 18) +#define G_000044_SCRATCH_INT_STAT(x) (((x) >> 18) & 0x1) +#define C_000044_SCRATCH_INT_STAT 0xFFFBFFFF +#define S_000044_GUI_IDLE_STAT(x) (((x) & 0x1) << 19) +#define G_000044_GUI_IDLE_STAT(x) (((x) >> 19) & 0x1) +#define C_000044_GUI_IDLE_STAT 0xFFF7FFFF +#define S_000044_ATI_OVERDRIVE_INT_STAT(x) (((x) & 0x1) << 20) +#define G_000044_ATI_OVERDRIVE_INT_STAT(x) (((x) >> 20) & 0x1) +#define C_000044_ATI_OVERDRIVE_INT_STAT 0xFFEFFFFF +#define S_000044_MC_PROTECTION_FAULT_STAT(x) (((x) & 0x1) << 21) +#define G_000044_MC_PROTECTION_FAULT_STAT(x) (((x) >> 21) & 0x1) +#define C_000044_MC_PROTECTION_FAULT_STAT 0xFFDFFFFF +#define S_000044_RBBM_READ_INT_STAT(x) (((x) & 0x1) << 22) +#define G_000044_RBBM_READ_INT_STAT(x) (((x) >> 22) & 0x1) +#define C_000044_RBBM_READ_INT_STAT 0xFFBFFFFF +#define S_000044_CB_CONTEXT_SWITCH_STAT(x) (((x) & 0x1) << 23) +#define G_000044_CB_CONTEXT_SWITCH_STAT(x) (((x) >> 23) & 0x1) +#define C_000044_CB_CONTEXT_SWITCH_STAT 0xFF7FFFFF +#define S_000044_VIPH_INT(x) (((x) & 0x1) << 24) +#define G_000044_VIPH_INT(x) (((x) >> 24) & 0x1) +#define C_000044_VIPH_INT 0xFEFFFFFF +#define S_000044_SW_INT(x) (((x) & 0x1) << 25) +#define G_000044_SW_INT(x) (((x) >> 25) & 0x1) +#define C_000044_SW_INT 0xFDFFFFFF +#define S_000044_SW_INT_SET(x) (((x) & 0x1) << 26) +#define G_000044_SW_INT_SET(x) (((x) >> 26) & 0x1) +#define C_000044_SW_INT_SET 0xFBFFFFFF +#define S_000044_IDCT_INT_STAT(x) (((x) & 0x1) << 27) +#define G_000044_IDCT_INT_STAT(x) (((x) >> 27) & 0x1) +#define C_000044_IDCT_INT_STAT 0xF7FFFFFF +#define S_000044_GUIDMA_STAT(x) (((x) & 0x1) << 30) +#define G_000044_GUIDMA_STAT(x) (((x) >> 30) & 0x1) +#define C_000044_GUIDMA_STAT 0xBFFFFFFF +#define S_000044_VIDDMA_STAT(x) (((x) & 0x1) << 31) +#define G_000044_VIDDMA_STAT(x) (((x) >> 31) & 0x1) +#define C_000044_VIDDMA_STAT 0x7FFFFFFF +#define R_00004C_BUS_CNTL 0x00004C +#define S_00004C_BUS_MASTER_DIS(x) (((x) & 0x1) << 14) +#define G_00004C_BUS_MASTER_DIS(x) (((x) >> 14) & 0x1) +#define C_00004C_BUS_MASTER_DIS 0xFFFFBFFF +#define S_00004C_BUS_MSI_REARM(x) (((x) & 0x1) << 20) +#define G_00004C_BUS_MSI_REARM(x) (((x) >> 20) & 0x1) +#define C_00004C_BUS_MSI_REARM 0xFFEFFFFF +#define R_000070_MC_IND_INDEX 0x000070 +#define S_000070_MC_IND_ADDR(x) (((x) & 0xFFFF) << 0) +#define G_000070_MC_IND_ADDR(x) (((x) >> 0) & 0xFFFF) +#define C_000070_MC_IND_ADDR 0xFFFF0000 +#define S_000070_MC_IND_SEQ_RBS_0(x) (((x) & 0x1) << 16) +#define G_000070_MC_IND_SEQ_RBS_0(x) (((x) >> 16) & 0x1) +#define C_000070_MC_IND_SEQ_RBS_0 0xFFFEFFFF +#define S_000070_MC_IND_SEQ_RBS_1(x) (((x) & 0x1) << 17) +#define G_000070_MC_IND_SEQ_RBS_1(x) (((x) >> 17) & 0x1) +#define C_000070_MC_IND_SEQ_RBS_1 0xFFFDFFFF +#define S_000070_MC_IND_SEQ_RBS_2(x) (((x) & 0x1) << 18) +#define G_000070_MC_IND_SEQ_RBS_2(x) (((x) >> 18) & 0x1) +#define C_000070_MC_IND_SEQ_RBS_2 0xFFFBFFFF +#define S_000070_MC_IND_SEQ_RBS_3(x) (((x) & 0x1) << 19) +#define G_000070_MC_IND_SEQ_RBS_3(x) (((x) >> 19) & 0x1) +#define C_000070_MC_IND_SEQ_RBS_3 0xFFF7FFFF +#define S_000070_MC_IND_AIC_RBS(x) (((x) & 0x1) << 20) +#define G_000070_MC_IND_AIC_RBS(x) (((x) >> 20) & 0x1) +#define C_000070_MC_IND_AIC_RBS 0xFFEFFFFF +#define S_000070_MC_IND_CITF_ARB0(x) (((x) & 0x1) << 21) +#define G_000070_MC_IND_CITF_ARB0(x) (((x) >> 21) & 0x1) +#define C_000070_MC_IND_CITF_ARB0 0xFFDFFFFF +#define S_000070_MC_IND_CITF_ARB1(x) (((x) & 0x1) << 22) +#define G_000070_MC_IND_CITF_ARB1(x) (((x) >> 22) & 0x1) +#define C_000070_MC_IND_CITF_ARB1 0xFFBFFFFF +#define S_000070_MC_IND_WR_EN(x) (((x) & 0x1) << 23) +#define G_000070_MC_IND_WR_EN(x) (((x) >> 23) & 0x1) +#define C_000070_MC_IND_WR_EN 0xFF7FFFFF +#define S_000070_MC_IND_RD_INV(x) (((x) & 0x1) << 24) +#define G_000070_MC_IND_RD_INV(x) (((x) >> 24) & 0x1) +#define C_000070_MC_IND_RD_INV 0xFEFFFFFF +#define R_000074_MC_IND_DATA 0x000074 +#define S_000074_MC_IND_DATA(x) (((x) & 0xFFFFFFFF) << 0) +#define G_000074_MC_IND_DATA(x) (((x) >> 0) & 0xFFFFFFFF) +#define C_000074_MC_IND_DATA 0x00000000 +#define R_000134_HDP_FB_LOCATION 0x000134 +#define S_000134_HDP_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_000134_HDP_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_000134_HDP_FB_START 0xFFFF0000 +#define R_0007C0_CP_STAT 0x0007C0 +#define S_0007C0_MRU_BUSY(x) (((x) & 0x1) << 0) +#define G_0007C0_MRU_BUSY(x) (((x) >> 0) & 0x1) +#define C_0007C0_MRU_BUSY 0xFFFFFFFE +#define S_0007C0_MWU_BUSY(x) (((x) & 0x1) << 1) +#define G_0007C0_MWU_BUSY(x) (((x) >> 1) & 0x1) +#define C_0007C0_MWU_BUSY 0xFFFFFFFD +#define S_0007C0_RSIU_BUSY(x) (((x) & 0x1) << 2) +#define G_0007C0_RSIU_BUSY(x) (((x) >> 2) & 0x1) +#define C_0007C0_RSIU_BUSY 0xFFFFFFFB +#define S_0007C0_RCIU_BUSY(x) (((x) & 0x1) << 3) +#define G_0007C0_RCIU_BUSY(x) (((x) >> 3) & 0x1) +#define C_0007C0_RCIU_BUSY 0xFFFFFFF7 +#define S_0007C0_CSF_PRIMARY_BUSY(x) (((x) & 0x1) << 9) +#define G_0007C0_CSF_PRIMARY_BUSY(x) (((x) >> 9) & 0x1) +#define C_0007C0_CSF_PRIMARY_BUSY 0xFFFFFDFF +#define S_0007C0_CSF_INDIRECT_BUSY(x) (((x) & 0x1) << 10) +#define G_0007C0_CSF_INDIRECT_BUSY(x) (((x) >> 10) & 0x1) +#define C_0007C0_CSF_INDIRECT_BUSY 0xFFFFFBFF +#define S_0007C0_CSQ_PRIMARY_BUSY(x) (((x) & 0x1) << 11) +#define G_0007C0_CSQ_PRIMARY_BUSY(x) (((x) >> 11) & 0x1) +#define C_0007C0_CSQ_PRIMARY_BUSY 0xFFFFF7FF +#define S_0007C0_CSQ_INDIRECT_BUSY(x) (((x) & 0x1) << 12) +#define G_0007C0_CSQ_INDIRECT_BUSY(x) (((x) >> 12) & 0x1) +#define C_0007C0_CSQ_INDIRECT_BUSY 0xFFFFEFFF +#define S_0007C0_CSI_BUSY(x) (((x) & 0x1) << 13) +#define G_0007C0_CSI_BUSY(x) (((x) >> 13) & 0x1) +#define C_0007C0_CSI_BUSY 0xFFFFDFFF +#define S_0007C0_CSF_INDIRECT2_BUSY(x) (((x) & 0x1) << 14) +#define G_0007C0_CSF_INDIRECT2_BUSY(x) (((x) >> 14) & 0x1) +#define C_0007C0_CSF_INDIRECT2_BUSY 0xFFFFBFFF +#define S_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) & 0x1) << 15) +#define G_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) >> 15) & 0x1) +#define C_0007C0_CSQ_INDIRECT2_BUSY 0xFFFF7FFF +#define S_0007C0_GUIDMA_BUSY(x) (((x) & 0x1) << 28) +#define G_0007C0_GUIDMA_BUSY(x) (((x) >> 28) & 0x1) +#define C_0007C0_GUIDMA_BUSY 0xEFFFFFFF +#define S_0007C0_VIDDMA_BUSY(x) (((x) & 0x1) << 29) +#define G_0007C0_VIDDMA_BUSY(x) (((x) >> 29) & 0x1) +#define C_0007C0_VIDDMA_BUSY 0xDFFFFFFF +#define S_0007C0_CMDSTRM_BUSY(x) (((x) & 0x1) << 30) +#define G_0007C0_CMDSTRM_BUSY(x) (((x) >> 30) & 0x1) +#define C_0007C0_CMDSTRM_BUSY 0xBFFFFFFF +#define S_0007C0_CP_BUSY(x) (((x) & 0x1) << 31) +#define G_0007C0_CP_BUSY(x) (((x) >> 31) & 0x1) +#define C_0007C0_CP_BUSY 0x7FFFFFFF +#define R_000E40_RBBM_STATUS 0x000E40 +#define S_000E40_CMDFIFO_AVAIL(x) (((x) & 0x7F) << 0) +#define G_000E40_CMDFIFO_AVAIL(x) (((x) >> 0) & 0x7F) +#define C_000E40_CMDFIFO_AVAIL 0xFFFFFF80 +#define S_000E40_HIRQ_ON_RBB(x) (((x) & 0x1) << 8) +#define G_000E40_HIRQ_ON_RBB(x) (((x) >> 8) & 0x1) +#define C_000E40_HIRQ_ON_RBB 0xFFFFFEFF +#define S_000E40_CPRQ_ON_RBB(x) (((x) & 0x1) << 9) +#define G_000E40_CPRQ_ON_RBB(x) (((x) >> 9) & 0x1) +#define C_000E40_CPRQ_ON_RBB 0xFFFFFDFF +#define S_000E40_CFRQ_ON_RBB(x) (((x) & 0x1) << 10) +#define G_000E40_CFRQ_ON_RBB(x) (((x) >> 10) & 0x1) +#define C_000E40_CFRQ_ON_RBB 0xFFFFFBFF +#define S_000E40_HIRQ_IN_RTBUF(x) (((x) & 0x1) << 11) +#define G_000E40_HIRQ_IN_RTBUF(x) (((x) >> 11) & 0x1) +#define C_000E40_HIRQ_IN_RTBUF 0xFFFFF7FF +#define S_000E40_CPRQ_IN_RTBUF(x) (((x) & 0x1) << 12) +#define G_000E40_CPRQ_IN_RTBUF(x) (((x) >> 12) & 0x1) +#define C_000E40_CPRQ_IN_RTBUF 0xFFFFEFFF +#define S_000E40_CFRQ_IN_RTBUF(x) (((x) & 0x1) << 13) +#define G_000E40_CFRQ_IN_RTBUF(x) (((x) >> 13) & 0x1) +#define C_000E40_CFRQ_IN_RTBUF 0xFFFFDFFF +#define S_000E40_CF_PIPE_BUSY(x) (((x) & 0x1) << 14) +#define G_000E40_CF_PIPE_BUSY(x) (((x) >> 14) & 0x1) +#define C_000E40_CF_PIPE_BUSY 0xFFFFBFFF +#define S_000E40_ENG_EV_BUSY(x) (((x) & 0x1) << 15) +#define G_000E40_ENG_EV_BUSY(x) (((x) >> 15) & 0x1) +#define C_000E40_ENG_EV_BUSY 0xFFFF7FFF +#define S_000E40_CP_CMDSTRM_BUSY(x) (((x) & 0x1) << 16) +#define G_000E40_CP_CMDSTRM_BUSY(x) (((x) >> 16) & 0x1) +#define C_000E40_CP_CMDSTRM_BUSY 0xFFFEFFFF +#define S_000E40_E2_BUSY(x) (((x) & 0x1) << 17) +#define G_000E40_E2_BUSY(x) (((x) >> 17) & 0x1) +#define C_000E40_E2_BUSY 0xFFFDFFFF +#define S_000E40_RB2D_BUSY(x) (((x) & 0x1) << 18) +#define G_000E40_RB2D_BUSY(x) (((x) >> 18) & 0x1) +#define C_000E40_RB2D_BUSY 0xFFFBFFFF +#define S_000E40_RB3D_BUSY(x) (((x) & 0x1) << 19) +#define G_000E40_RB3D_BUSY(x) (((x) >> 19) & 0x1) +#define C_000E40_RB3D_BUSY 0xFFF7FFFF +#define S_000E40_VAP_BUSY(x) (((x) & 0x1) << 20) +#define G_000E40_VAP_BUSY(x) (((x) >> 20) & 0x1) +#define C_000E40_VAP_BUSY 0xFFEFFFFF +#define S_000E40_RE_BUSY(x) (((x) & 0x1) << 21) +#define G_000E40_RE_BUSY(x) (((x) >> 21) & 0x1) +#define C_000E40_RE_BUSY 0xFFDFFFFF +#define S_000E40_TAM_BUSY(x) (((x) & 0x1) << 22) +#define G_000E40_TAM_BUSY(x) (((x) >> 22) & 0x1) +#define C_000E40_TAM_BUSY 0xFFBFFFFF +#define S_000E40_TDM_BUSY(x) (((x) & 0x1) << 23) +#define G_000E40_TDM_BUSY(x) (((x) >> 23) & 0x1) +#define C_000E40_TDM_BUSY 0xFF7FFFFF +#define S_000E40_PB_BUSY(x) (((x) & 0x1) << 24) +#define G_000E40_PB_BUSY(x) (((x) >> 24) & 0x1) +#define C_000E40_PB_BUSY 0xFEFFFFFF +#define S_000E40_TIM_BUSY(x) (((x) & 0x1) << 25) +#define G_000E40_TIM_BUSY(x) (((x) >> 25) & 0x1) +#define C_000E40_TIM_BUSY 0xFDFFFFFF +#define S_000E40_GA_BUSY(x) (((x) & 0x1) << 26) +#define G_000E40_GA_BUSY(x) (((x) >> 26) & 0x1) +#define C_000E40_GA_BUSY 0xFBFFFFFF +#define S_000E40_CBA2D_BUSY(x) (((x) & 0x1) << 27) +#define G_000E40_CBA2D_BUSY(x) (((x) >> 27) & 0x1) +#define C_000E40_CBA2D_BUSY 0xF7FFFFFF +#define S_000E40_GUI_ACTIVE(x) (((x) & 0x1) << 31) +#define G_000E40_GUI_ACTIVE(x) (((x) >> 31) & 0x1) +#define C_000E40_GUI_ACTIVE 0x7FFFFFFF +#define R_0060A4_D1CRTC_STATUS_FRAME_COUNT 0x0060A4 +#define S_0060A4_D1CRTC_FRAME_COUNT(x) (((x) & 0xFFFFFF) << 0) +#define G_0060A4_D1CRTC_FRAME_COUNT(x) (((x) >> 0) & 0xFFFFFF) +#define C_0060A4_D1CRTC_FRAME_COUNT 0xFF000000 +#define R_006534_D1MODE_VBLANK_STATUS 0x006534 +#define S_006534_D1MODE_VBLANK_OCCURRED(x) (((x) & 0x1) << 0) +#define G_006534_D1MODE_VBLANK_OCCURRED(x) (((x) >> 0) & 0x1) +#define C_006534_D1MODE_VBLANK_OCCURRED 0xFFFFFFFE +#define S_006534_D1MODE_VBLANK_ACK(x) (((x) & 0x1) << 4) +#define G_006534_D1MODE_VBLANK_ACK(x) (((x) >> 4) & 0x1) +#define C_006534_D1MODE_VBLANK_ACK 0xFFFFFFEF +#define S_006534_D1MODE_VBLANK_STAT(x) (((x) & 0x1) << 12) +#define G_006534_D1MODE_VBLANK_STAT(x) (((x) >> 12) & 0x1) +#define C_006534_D1MODE_VBLANK_STAT 0xFFFFEFFF +#define S_006534_D1MODE_VBLANK_INTERRUPT(x) (((x) & 0x1) << 16) +#define G_006534_D1MODE_VBLANK_INTERRUPT(x) (((x) >> 16) & 0x1) +#define C_006534_D1MODE_VBLANK_INTERRUPT 0xFFFEFFFF +#define R_006540_DxMODE_INT_MASK 0x006540 +#define S_006540_D1MODE_VBLANK_INT_MASK(x) (((x) & 0x1) << 0) +#define G_006540_D1MODE_VBLANK_INT_MASK(x) (((x) >> 0) & 0x1) +#define C_006540_D1MODE_VBLANK_INT_MASK 0xFFFFFFFE +#define S_006540_D1MODE_VLINE_INT_MASK(x) (((x) & 0x1) << 4) +#define G_006540_D1MODE_VLINE_INT_MASK(x) (((x) >> 4) & 0x1) +#define C_006540_D1MODE_VLINE_INT_MASK 0xFFFFFFEF +#define S_006540_D2MODE_VBLANK_INT_MASK(x) (((x) & 0x1) << 8) +#define G_006540_D2MODE_VBLANK_INT_MASK(x) (((x) >> 8) & 0x1) +#define C_006540_D2MODE_VBLANK_INT_MASK 0xFFFFFEFF +#define S_006540_D2MODE_VLINE_INT_MASK(x) (((x) & 0x1) << 12) +#define G_006540_D2MODE_VLINE_INT_MASK(x) (((x) >> 12) & 0x1) +#define C_006540_D2MODE_VLINE_INT_MASK 0xFFFFEFFF +#define S_006540_D1MODE_VBLANK_CP_SEL(x) (((x) & 0x1) << 30) +#define G_006540_D1MODE_VBLANK_CP_SEL(x) (((x) >> 30) & 0x1) +#define C_006540_D1MODE_VBLANK_CP_SEL 0xBFFFFFFF +#define S_006540_D2MODE_VBLANK_CP_SEL(x) (((x) & 0x1) << 31) +#define G_006540_D2MODE_VBLANK_CP_SEL(x) (((x) >> 31) & 0x1) +#define C_006540_D2MODE_VBLANK_CP_SEL 0x7FFFFFFF +#define R_0068A4_D2CRTC_STATUS_FRAME_COUNT 0x0068A4 +#define S_0068A4_D2CRTC_FRAME_COUNT(x) (((x) & 0xFFFFFF) << 0) +#define G_0068A4_D2CRTC_FRAME_COUNT(x) (((x) >> 0) & 0xFFFFFF) +#define C_0068A4_D2CRTC_FRAME_COUNT 0xFF000000 +#define R_006D34_D2MODE_VBLANK_STATUS 0x006D34 +#define S_006D34_D2MODE_VBLANK_OCCURRED(x) (((x) & 0x1) << 0) +#define G_006D34_D2MODE_VBLANK_OCCURRED(x) (((x) >> 0) & 0x1) +#define C_006D34_D2MODE_VBLANK_OCCURRED 0xFFFFFFFE +#define S_006D34_D2MODE_VBLANK_ACK(x) (((x) & 0x1) << 4) +#define G_006D34_D2MODE_VBLANK_ACK(x) (((x) >> 4) & 0x1) +#define C_006D34_D2MODE_VBLANK_ACK 0xFFFFFFEF +#define S_006D34_D2MODE_VBLANK_STAT(x) (((x) & 0x1) << 12) +#define G_006D34_D2MODE_VBLANK_STAT(x) (((x) >> 12) & 0x1) +#define C_006D34_D2MODE_VBLANK_STAT 0xFFFFEFFF +#define S_006D34_D2MODE_VBLANK_INTERRUPT(x) (((x) & 0x1) << 16) +#define G_006D34_D2MODE_VBLANK_INTERRUPT(x) (((x) >> 16) & 0x1) +#define C_006D34_D2MODE_VBLANK_INTERRUPT 0xFFFEFFFF +#define R_007EDC_DISP_INTERRUPT_STATUS 0x007EDC +#define S_007EDC_LB_D1_VBLANK_INTERRUPT(x) (((x) & 0x1) << 4) +#define G_007EDC_LB_D1_VBLANK_INTERRUPT(x) (((x) >> 4) & 0x1) +#define C_007EDC_LB_D1_VBLANK_INTERRUPT 0xFFFFFFEF +#define S_007EDC_LB_D2_VBLANK_INTERRUPT(x) (((x) & 0x1) << 5) +#define G_007EDC_LB_D2_VBLANK_INTERRUPT(x) (((x) >> 5) & 0x1) +#define C_007EDC_LB_D2_VBLANK_INTERRUPT 0xFFFFFFDF + + +/* MC registers */ +#define R_000000_MC_STATUS 0x000000 +#define S_000000_MC_IDLE(x) (((x) & 0x1) << 0) +#define G_000000_MC_IDLE(x) (((x) >> 0) & 0x1) +#define C_000000_MC_IDLE 0xFFFFFFFE +#define R_000004_MC_FB_LOCATION 0x000004 +#define S_000004_MC_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_000004_MC_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_000004_MC_FB_START 0xFFFF0000 +#define S_000004_MC_FB_TOP(x) (((x) & 0xFFFF) << 16) +#define G_000004_MC_FB_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_000004_MC_FB_TOP 0x0000FFFF +#define R_000005_MC_AGP_LOCATION 0x000005 +#define S_000005_MC_AGP_START(x) (((x) & 0xFFFF) << 0) +#define G_000005_MC_AGP_START(x) (((x) >> 0) & 0xFFFF) +#define C_000005_MC_AGP_START 0xFFFF0000 +#define S_000005_MC_AGP_TOP(x) (((x) & 0xFFFF) << 16) +#define G_000005_MC_AGP_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_000005_MC_AGP_TOP 0x0000FFFF +#define R_000006_AGP_BASE 0x000006 +#define S_000006_AGP_BASE_ADDR(x) (((x) & 0xFFFFFFFF) << 0) +#define G_000006_AGP_BASE_ADDR(x) (((x) >> 0) & 0xFFFFFFFF) +#define C_000006_AGP_BASE_ADDR 0x00000000 +#define R_000007_AGP_BASE_2 0x000007 +#define S_000007_AGP_BASE_ADDR_2(x) (((x) & 0xF) << 0) +#define G_000007_AGP_BASE_ADDR_2(x) (((x) >> 0) & 0xF) +#define C_000007_AGP_BASE_ADDR_2 0xFFFFFFF0 +#define R_000009_MC_CNTL1 0x000009 +#define S_000009_ENABLE_PAGE_TABLES(x) (((x) & 0x1) << 26) +#define G_000009_ENABLE_PAGE_TABLES(x) (((x) >> 26) & 0x1) +#define C_000009_ENABLE_PAGE_TABLES 0xFBFFFFFF +/* FIXME don't know the various field size need feedback from AMD */ +#define R_000100_MC_PT0_CNTL 0x000100 +#define S_000100_ENABLE_PT(x) (((x) & 0x1) << 0) +#define G_000100_ENABLE_PT(x) (((x) >> 0) & 0x1) +#define C_000100_ENABLE_PT 0xFFFFFFFE +#define S_000100_EFFECTIVE_L2_CACHE_SIZE(x) (((x) & 0x7) << 15) +#define G_000100_EFFECTIVE_L2_CACHE_SIZE(x) (((x) >> 15) & 0x7) +#define C_000100_EFFECTIVE_L2_CACHE_SIZE 0xFFFC7FFF +#define S_000100_EFFECTIVE_L2_QUEUE_SIZE(x) (((x) & 0x7) << 21) +#define G_000100_EFFECTIVE_L2_QUEUE_SIZE(x) (((x) >> 21) & 0x7) +#define C_000100_EFFECTIVE_L2_QUEUE_SIZE 0xFF1FFFFF +#define S_000100_INVALIDATE_ALL_L1_TLBS(x) (((x) & 0x1) << 28) +#define G_000100_INVALIDATE_ALL_L1_TLBS(x) (((x) >> 28) & 0x1) +#define C_000100_INVALIDATE_ALL_L1_TLBS 0xEFFFFFFF +#define S_000100_INVALIDATE_L2_CACHE(x) (((x) & 0x1) << 29) +#define G_000100_INVALIDATE_L2_CACHE(x) (((x) >> 29) & 0x1) +#define C_000100_INVALIDATE_L2_CACHE 0xDFFFFFFF +#define R_000102_MC_PT0_CONTEXT0_CNTL 0x000102 +#define S_000102_ENABLE_PAGE_TABLE(x) (((x) & 0x1) << 0) +#define G_000102_ENABLE_PAGE_TABLE(x) (((x) >> 0) & 0x1) +#define C_000102_ENABLE_PAGE_TABLE 0xFFFFFFFE +#define S_000102_PAGE_TABLE_DEPTH(x) (((x) & 0x3) << 1) +#define G_000102_PAGE_TABLE_DEPTH(x) (((x) >> 1) & 0x3) +#define C_000102_PAGE_TABLE_DEPTH 0xFFFFFFF9 +#define V_000102_PAGE_TABLE_FLAT 0 +/* R600 documentation suggest that this should be a number of pages */ +#define R_000112_MC_PT0_SYSTEM_APERTURE_LOW_ADDR 0x000112 +#define R_000114_MC_PT0_SYSTEM_APERTURE_HIGH_ADDR 0x000114 +#define R_00011C_MC_PT0_CONTEXT0_DEFAULT_READ_ADDR 0x00011C +#define R_00012C_MC_PT0_CONTEXT0_FLAT_BASE_ADDR 0x00012C +#define R_00013C_MC_PT0_CONTEXT0_FLAT_START_ADDR 0x00013C +#define R_00014C_MC_PT0_CONTEXT0_FLAT_END_ADDR 0x00014C +#define R_00016C_MC_PT0_CLIENT0_CNTL 0x00016C +#define S_00016C_ENABLE_TRANSLATION_MODE_OVERRIDE(x) (((x) & 0x1) << 0) +#define G_00016C_ENABLE_TRANSLATION_MODE_OVERRIDE(x) (((x) >> 0) & 0x1) +#define C_00016C_ENABLE_TRANSLATION_MODE_OVERRIDE 0xFFFFFFFE +#define S_00016C_TRANSLATION_MODE_OVERRIDE(x) (((x) & 0x1) << 1) +#define G_00016C_TRANSLATION_MODE_OVERRIDE(x) (((x) >> 1) & 0x1) +#define C_00016C_TRANSLATION_MODE_OVERRIDE 0xFFFFFFFD +#define S_00016C_SYSTEM_ACCESS_MODE_MASK(x) (((x) & 0x3) << 8) +#define G_00016C_SYSTEM_ACCESS_MODE_MASK(x) (((x) >> 8) & 0x3) +#define C_00016C_SYSTEM_ACCESS_MODE_MASK 0xFFFFFCFF +#define V_00016C_SYSTEM_ACCESS_MODE_PA_ONLY 0 +#define V_00016C_SYSTEM_ACCESS_MODE_USE_SYS_MAP 1 +#define V_00016C_SYSTEM_ACCESS_MODE_IN_SYS 2 +#define V_00016C_SYSTEM_ACCESS_MODE_NOT_IN_SYS 3 +#define S_00016C_SYSTEM_APERTURE_UNMAPPED_ACCESS(x) (((x) & 0x1) << 10) +#define G_00016C_SYSTEM_APERTURE_UNMAPPED_ACCESS(x) (((x) >> 10) & 0x1) +#define C_00016C_SYSTEM_APERTURE_UNMAPPED_ACCESS 0xFFFFFBFF +#define V_00016C_SYSTEM_APERTURE_UNMAPPED_PASSTHROUGH 0 +#define V_00016C_SYSTEM_APERTURE_UNMAPPED_DEFAULT_PAGE 1 +#define S_00016C_EFFECTIVE_L1_CACHE_SIZE(x) (((x) & 0x7) << 11) +#define G_00016C_EFFECTIVE_L1_CACHE_SIZE(x) (((x) >> 11) & 0x7) +#define C_00016C_EFFECTIVE_L1_CACHE_SIZE 0xFFFFC7FF +#define S_00016C_ENABLE_FRAGMENT_PROCESSING(x) (((x) & 0x1) << 14) +#define G_00016C_ENABLE_FRAGMENT_PROCESSING(x) (((x) >> 14) & 0x1) +#define C_00016C_ENABLE_FRAGMENT_PROCESSING 0xFFFFBFFF +#define S_00016C_EFFECTIVE_L1_QUEUE_SIZE(x) (((x) & 0x7) << 15) +#define G_00016C_EFFECTIVE_L1_QUEUE_SIZE(x) (((x) >> 15) & 0x7) +#define C_00016C_EFFECTIVE_L1_QUEUE_SIZE 0xFFFC7FFF +#define S_00016C_INVALIDATE_L1_TLB(x) (((x) & 0x1) << 20) +#define G_00016C_INVALIDATE_L1_TLB(x) (((x) >> 20) & 0x1) +#define C_00016C_INVALIDATE_L1_TLB 0xFFEFFFFF + +#endif diff --git a/drivers/gpu/drm/radeon/rs690.c b/drivers/gpu/drm/radeon/rs690.c index 7a0098ddf977..27547175cf93 100644 --- a/drivers/gpu/drm/radeon/rs690.c +++ b/drivers/gpu/drm/radeon/rs690.c @@ -26,105 +26,29 @@ * Jerome Glisse */ #include "drmP.h" -#include "radeon_reg.h" #include "radeon.h" -#include "rs690r.h" #include "atom.h" -#include "atom-bits.h" - -/* rs690,rs740 depends on : */ -void r100_hdp_reset(struct radeon_device *rdev); -int r300_mc_wait_for_idle(struct radeon_device *rdev); -void r420_pipes_init(struct radeon_device *rdev); -void rs400_gart_disable(struct radeon_device *rdev); -int rs400_gart_enable(struct radeon_device *rdev); -void rs400_gart_adjust_size(struct radeon_device *rdev); -void rs600_mc_disable_clients(struct radeon_device *rdev); - -/* This files gather functions specifics to : - * rs690,rs740 - * - * Some of these functions might be used by newer ASICs. - */ -void rs690_gpu_init(struct radeon_device *rdev); -int rs690_mc_wait_for_idle(struct radeon_device *rdev); - - -/* - * MC functions. - */ -int rs690_mc_init(struct radeon_device *rdev) -{ - uint32_t tmp; - int r; - - if (r100_debugfs_rbbm_init(rdev)) { - DRM_ERROR("Failed to register debugfs file for RBBM !\n"); - } - - rs690_gpu_init(rdev); - rs400_gart_disable(rdev); - - /* Setup GPU memory space */ - rdev->mc.gtt_location = rdev->mc.mc_vram_size; - rdev->mc.gtt_location += (rdev->mc.gtt_size - 1); - rdev->mc.gtt_location &= ~(rdev->mc.gtt_size - 1); - rdev->mc.vram_location = 0xFFFFFFFFUL; - r = radeon_mc_setup(rdev); - if (r) { - return r; - } - - /* Program GPU memory space */ - rs600_mc_disable_clients(rdev); - if (rs690_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "Failed to wait MC idle while " - "programming pipes. Bad things might happen.\n"); - } - tmp = rdev->mc.vram_location + rdev->mc.mc_vram_size - 1; - tmp = REG_SET(RS690_MC_FB_TOP, tmp >> 16); - tmp |= REG_SET(RS690_MC_FB_START, rdev->mc.vram_location >> 16); - WREG32_MC(RS690_MCCFG_FB_LOCATION, tmp); - /* FIXME: Does this reg exist on RS480,RS740 ? */ - WREG32(0x310, rdev->mc.vram_location); - WREG32(RS690_HDP_FB_LOCATION, rdev->mc.vram_location >> 16); - return 0; -} - -void rs690_mc_fini(struct radeon_device *rdev) -{ -} - +#include "rs690d.h" -/* - * Global GPU functions - */ -int rs690_mc_wait_for_idle(struct radeon_device *rdev) +static int rs690_mc_wait_for_idle(struct radeon_device *rdev) { unsigned i; uint32_t tmp; for (i = 0; i < rdev->usec_timeout; i++) { /* read MC_STATUS */ - tmp = RREG32_MC(RS690_MC_STATUS); - if (tmp & RS690_MC_STATUS_IDLE) { + tmp = RREG32_MC(R_000090_MC_SYSTEM_STATUS); + if (G_000090_MC_SYSTEM_IDLE(tmp)) return 0; - } - DRM_UDELAY(1); + udelay(1); } return -1; } -void rs690_errata(struct radeon_device *rdev) -{ - rdev->pll_errata = 0; -} - -void rs690_gpu_init(struct radeon_device *rdev) +static void rs690_gpu_init(struct radeon_device *rdev) { /* FIXME: HDP same place on rs690 ? */ r100_hdp_reset(rdev); - rv515_vga_render_disable(rdev); /* FIXME: is this correct ? */ r420_pipes_init(rdev); if (rs690_mc_wait_for_idle(rdev)) { @@ -133,10 +57,6 @@ void rs690_gpu_init(struct radeon_device *rdev) } } - -/* - * VRAM info. - */ void rs690_pm_info(struct radeon_device *rdev) { int index = GetIndexIntoMasterTable(DATA, IntegratedSystemInfo); @@ -250,39 +170,39 @@ void rs690_line_buffer_adjust(struct radeon_device *rdev, /* * Line Buffer Setup * There is a single line buffer shared by both display controllers. - * DC_LB_MEMORY_SPLIT controls how that line buffer is shared between + * R_006520_DC_LB_MEMORY_SPLIT controls how that line buffer is shared between * the display controllers. The paritioning can either be done * manually or via one of four preset allocations specified in bits 1:0: * 0 - line buffer is divided in half and shared between crtc * 1 - D1 gets 3/4 of the line buffer, D2 gets 1/4 * 2 - D1 gets the whole buffer * 3 - D1 gets 1/4 of the line buffer, D2 gets 3/4 - * Setting bit 2 of DC_LB_MEMORY_SPLIT controls switches to manual + * Setting bit 2 of R_006520_DC_LB_MEMORY_SPLIT controls switches to manual * allocation mode. In manual allocation mode, D1 always starts at 0, * D1 end/2 is specified in bits 14:4; D2 allocation follows D1. */ - tmp = RREG32(DC_LB_MEMORY_SPLIT) & ~DC_LB_MEMORY_SPLIT_MASK; - tmp &= ~DC_LB_MEMORY_SPLIT_SHIFT_MODE; + tmp = RREG32(R_006520_DC_LB_MEMORY_SPLIT) & C_006520_DC_LB_MEMORY_SPLIT; + tmp &= ~C_006520_DC_LB_MEMORY_SPLIT_MODE; /* auto */ if (mode1 && mode2) { if (mode1->hdisplay > mode2->hdisplay) { if (mode1->hdisplay > 2560) - tmp |= DC_LB_MEMORY_SPLIT_D1_3Q_D2_1Q; + tmp |= V_006520_DC_LB_MEMORY_SPLIT_D1_3Q_D2_1Q; else - tmp |= DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; + tmp |= V_006520_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; } else if (mode2->hdisplay > mode1->hdisplay) { if (mode2->hdisplay > 2560) - tmp |= DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q; + tmp |= V_006520_DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q; else - tmp |= DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; + tmp |= V_006520_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; } else - tmp |= AVIVO_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; + tmp |= V_006520_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; } else if (mode1) { - tmp |= DC_LB_MEMORY_SPLIT_D1_ONLY; + tmp |= V_006520_DC_LB_MEMORY_SPLIT_D1_ONLY; } else if (mode2) { - tmp |= DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q; + tmp |= V_006520_DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q; } - WREG32(DC_LB_MEMORY_SPLIT, tmp); + WREG32(R_006520_DC_LB_MEMORY_SPLIT, tmp); } struct rs690_watermark { @@ -487,28 +407,28 @@ void rs690_bandwidth_update(struct radeon_device *rdev) * option. */ if (rdev->disp_priority == 2) { - tmp = RREG32_MC(MC_INIT_MISC_LAT_TIMER); - tmp &= ~MC_DISP1R_INIT_LAT_MASK; - tmp &= ~MC_DISP0R_INIT_LAT_MASK; - if (mode1) - tmp |= (1 << MC_DISP1R_INIT_LAT_SHIFT); + tmp = RREG32_MC(R_000104_MC_INIT_MISC_LAT_TIMER); + tmp &= C_000104_MC_DISP0R_INIT_LAT; + tmp &= C_000104_MC_DISP1R_INIT_LAT; if (mode0) - tmp |= (1 << MC_DISP0R_INIT_LAT_SHIFT); - WREG32_MC(MC_INIT_MISC_LAT_TIMER, tmp); + tmp |= S_000104_MC_DISP0R_INIT_LAT(1); + if (mode1) + tmp |= S_000104_MC_DISP1R_INIT_LAT(1); + WREG32_MC(R_000104_MC_INIT_MISC_LAT_TIMER, tmp); } rs690_line_buffer_adjust(rdev, mode0, mode1); if ((rdev->family == CHIP_RS690) || (rdev->family == CHIP_RS740)) - WREG32(DCP_CONTROL, 0); + WREG32(R_006C9C_DCP_CONTROL, 0); if ((rdev->family == CHIP_RS780) || (rdev->family == CHIP_RS880)) - WREG32(DCP_CONTROL, 2); + WREG32(R_006C9C_DCP_CONTROL, 2); rs690_crtc_bandwidth_compute(rdev, rdev->mode_info.crtcs[0], &wm0); rs690_crtc_bandwidth_compute(rdev, rdev->mode_info.crtcs[1], &wm1); tmp = (wm0.lb_request_fifo_depth - 1); tmp |= (wm1.lb_request_fifo_depth - 1) << 16; - WREG32(LB_MAX_REQ_OUTSTANDING, tmp); + WREG32(R_006D58_LB_MAX_REQ_OUTSTANDING, tmp); if (mode0 && mode1) { if (rfixed_trunc(wm0.dbpp) > 64) @@ -561,10 +481,10 @@ void rs690_bandwidth_update(struct radeon_device *rdev) priority_mark12.full = 0; if (wm1.priority_mark_max.full > priority_mark12.full) priority_mark12.full = wm1.priority_mark_max.full; - WREG32(D1MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark02)); - WREG32(D1MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark02)); - WREG32(D2MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark12)); - WREG32(D2MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark12)); + WREG32(R_006548_D1MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark02)); + WREG32(R_00654C_D1MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark02)); + WREG32(R_006D48_D2MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark12)); + WREG32(R_006D4C_D2MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark12)); } else if (mode0) { if (rfixed_trunc(wm0.dbpp) > 64) a.full = rfixed_mul(wm0.dbpp, wm0.num_line_pair); @@ -591,10 +511,12 @@ void rs690_bandwidth_update(struct radeon_device *rdev) priority_mark02.full = 0; if (wm0.priority_mark_max.full > priority_mark02.full) priority_mark02.full = wm0.priority_mark_max.full; - WREG32(D1MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark02)); - WREG32(D1MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark02)); - WREG32(D2MODE_PRIORITY_A_CNT, MODE_PRIORITY_OFF); - WREG32(D2MODE_PRIORITY_B_CNT, MODE_PRIORITY_OFF); + WREG32(R_006548_D1MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark02)); + WREG32(R_00654C_D1MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark02)); + WREG32(R_006D48_D2MODE_PRIORITY_A_CNT, + S_006D48_D2MODE_PRIORITY_A_OFF(1)); + WREG32(R_006D4C_D2MODE_PRIORITY_B_CNT, + S_006D4C_D2MODE_PRIORITY_B_OFF(1)); } else { if (rfixed_trunc(wm1.dbpp) > 64) a.full = rfixed_mul(wm1.dbpp, wm1.num_line_pair); @@ -621,30 +543,205 @@ void rs690_bandwidth_update(struct radeon_device *rdev) priority_mark12.full = 0; if (wm1.priority_mark_max.full > priority_mark12.full) priority_mark12.full = wm1.priority_mark_max.full; - WREG32(D1MODE_PRIORITY_A_CNT, MODE_PRIORITY_OFF); - WREG32(D1MODE_PRIORITY_B_CNT, MODE_PRIORITY_OFF); - WREG32(D2MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark12)); - WREG32(D2MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark12)); + WREG32(R_006548_D1MODE_PRIORITY_A_CNT, + S_006548_D1MODE_PRIORITY_A_OFF(1)); + WREG32(R_00654C_D1MODE_PRIORITY_B_CNT, + S_00654C_D1MODE_PRIORITY_B_OFF(1)); + WREG32(R_006D48_D2MODE_PRIORITY_A_CNT, rfixed_trunc(priority_mark12)); + WREG32(R_006D4C_D2MODE_PRIORITY_B_CNT, rfixed_trunc(priority_mark12)); } } -/* - * Indirect registers accessor - */ uint32_t rs690_mc_rreg(struct radeon_device *rdev, uint32_t reg) { uint32_t r; - WREG32(RS690_MC_INDEX, (reg & RS690_MC_INDEX_MASK)); - r = RREG32(RS690_MC_DATA); - WREG32(RS690_MC_INDEX, RS690_MC_INDEX_MASK); + WREG32(R_000078_MC_INDEX, S_000078_MC_IND_ADDR(reg)); + r = RREG32(R_00007C_MC_DATA); + WREG32(R_000078_MC_INDEX, ~C_000078_MC_IND_ADDR); return r; } void rs690_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v) { - WREG32(RS690_MC_INDEX, - RS690_MC_INDEX_WR_EN | ((reg) & RS690_MC_INDEX_MASK)); - WREG32(RS690_MC_DATA, v); - WREG32(RS690_MC_INDEX, RS690_MC_INDEX_WR_ACK); + WREG32(R_000078_MC_INDEX, S_000078_MC_IND_ADDR(reg) | + S_000078_MC_IND_WR_EN(1)); + WREG32(R_00007C_MC_DATA, v); + WREG32(R_000078_MC_INDEX, 0x7F); +} + +void rs690_mc_program(struct radeon_device *rdev) +{ + struct rv515_mc_save save; + + /* Stops all mc clients */ + rv515_mc_stop(rdev, &save); + + /* Wait for mc idle */ + if (rs690_mc_wait_for_idle(rdev)) + dev_warn(rdev->dev, "Wait MC idle timeout before updating MC.\n"); + /* Program MC, should be a 32bits limited address space */ + WREG32_MC(R_000100_MCCFG_FB_LOCATION, + S_000100_MC_FB_START(rdev->mc.vram_start >> 16) | + S_000100_MC_FB_TOP(rdev->mc.vram_end >> 16)); + WREG32(R_000134_HDP_FB_LOCATION, + S_000134_HDP_FB_START(rdev->mc.vram_start >> 16)); + + rv515_mc_resume(rdev, &save); +} + +static int rs690_startup(struct radeon_device *rdev) +{ + int r; + + rs690_mc_program(rdev); + /* Resume clock */ + rv515_clock_startup(rdev); + /* Initialize GPU configuration (# pipes, ...) */ + rs690_gpu_init(rdev); + /* Initialize GART (initialize after TTM so we can allocate + * memory through TTM but finalize after TTM) */ + r = rs400_gart_enable(rdev); + if (r) + return r; + /* Enable IRQ */ + rdev->irq.sw_int = true; + rs600_irq_set(rdev); + /* 1M ring buffer */ + r = r100_cp_init(rdev, 1024 * 1024); + if (r) { + dev_err(rdev->dev, "failled initializing CP (%d).\n", r); + return r; + } + r = r100_wb_init(rdev); + if (r) + dev_err(rdev->dev, "failled initializing WB (%d).\n", r); + r = r100_ib_init(rdev); + if (r) { + dev_err(rdev->dev, "failled initializing IB (%d).\n", r); + return r; + } + return 0; +} + +int rs690_resume(struct radeon_device *rdev) +{ + /* Make sur GART are not working */ + rs400_gart_disable(rdev); + /* Resume clock before doing reset */ + rv515_clock_startup(rdev); + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* post */ + atom_asic_init(rdev->mode_info.atom_context); + /* Resume clock after posting */ + rv515_clock_startup(rdev); + return rs690_startup(rdev); +} + +int rs690_suspend(struct radeon_device *rdev) +{ + r100_cp_disable(rdev); + r100_wb_disable(rdev); + rs600_irq_disable(rdev); + rs400_gart_disable(rdev); + return 0; +} + +void rs690_fini(struct radeon_device *rdev) +{ + rs690_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + radeon_gem_fini(rdev); + rs400_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + radeon_fence_driver_fini(rdev); + radeon_object_fini(rdev); + radeon_atombios_fini(rdev); + kfree(rdev->bios); + rdev->bios = NULL; +} + +int rs690_init(struct radeon_device *rdev) +{ + int r; + + /* Disable VGA */ + rv515_vga_render_disable(rdev); + /* Initialize scratch registers */ + radeon_scratch_init(rdev); + /* Initialize surface registers */ + radeon_surface_init(rdev); + /* TODO: disable VGA need to use VGA request */ + /* BIOS*/ + if (!radeon_get_bios(rdev)) { + if (ASIC_IS_AVIVO(rdev)) + return -EINVAL; + } + if (rdev->is_atom_bios) { + r = radeon_atombios_init(rdev); + if (r) + return r; + } else { + dev_err(rdev->dev, "Expecting atombios for RV515 GPU\n"); + return -EINVAL; + } + /* Reset gpu before posting otherwise ATOM will enter infinite loop */ + if (radeon_gpu_reset(rdev)) { + dev_warn(rdev->dev, + "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n", + RREG32(R_000E40_RBBM_STATUS), + RREG32(R_0007C0_CP_STAT)); + } + /* check if cards are posted or not */ + if (!radeon_card_posted(rdev) && rdev->bios) { + DRM_INFO("GPU not posted. posting now...\n"); + atom_asic_init(rdev->mode_info.atom_context); + } + /* Initialize clocks */ + radeon_get_clock_info(rdev->ddev); + /* Initialize power management */ + radeon_pm_init(rdev); + /* Get vram informations */ + rs690_vram_info(rdev); + /* Initialize memory controller (also test AGP) */ + r = r420_mc_init(rdev); + if (r) + return r; + rv515_debugfs(rdev); + /* Fence driver */ + r = radeon_fence_driver_init(rdev); + if (r) + return r; + r = radeon_irq_kms_init(rdev); + if (r) + return r; + /* Memory manager */ + r = radeon_object_init(rdev); + if (r) + return r; + r = rs400_gart_init(rdev); + if (r) + return r; + rs600_set_safe_registers(rdev); + rdev->accel_working = true; + r = rs690_startup(rdev); + if (r) { + /* Somethings want wront with the accel init stop accel */ + dev_err(rdev->dev, "Disabling GPU acceleration\n"); + rs690_suspend(rdev); + r100_cp_fini(rdev); + r100_wb_fini(rdev); + r100_ib_fini(rdev); + rs400_gart_fini(rdev); + radeon_irq_kms_fini(rdev); + rdev->accel_working = false; + } + return 0; } diff --git a/drivers/gpu/drm/radeon/rs690d.h b/drivers/gpu/drm/radeon/rs690d.h new file mode 100644 index 000000000000..62d31e7a897f --- /dev/null +++ b/drivers/gpu/drm/radeon/rs690d.h @@ -0,0 +1,307 @@ +/* + * Copyright 2008 Advanced Micro Devices, Inc. + * Copyright 2008 Red Hat Inc. + * Copyright 2009 Jerome Glisse. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Alex Deucher + * Jerome Glisse + */ +#ifndef __RS690D_H__ +#define __RS690D_H__ + +/* Registers */ +#define R_000078_MC_INDEX 0x000078 +#define S_000078_MC_IND_ADDR(x) (((x) & 0x1FF) << 0) +#define G_000078_MC_IND_ADDR(x) (((x) >> 0) & 0x1FF) +#define C_000078_MC_IND_ADDR 0xFFFFFE00 +#define S_000078_MC_IND_WR_EN(x) (((x) & 0x1) << 9) +#define G_000078_MC_IND_WR_EN(x) (((x) >> 9) & 0x1) +#define C_000078_MC_IND_WR_EN 0xFFFFFDFF +#define R_00007C_MC_DATA 0x00007C +#define S_00007C_MC_DATA(x) (((x) & 0xFFFFFFFF) << 0) +#define G_00007C_MC_DATA(x) (((x) >> 0) & 0xFFFFFFFF) +#define C_00007C_MC_DATA 0x00000000 +#define R_0000F8_CONFIG_MEMSIZE 0x0000F8 +#define S_0000F8_CONFIG_MEMSIZE(x) (((x) & 0xFFFFFFFF) << 0) +#define G_0000F8_CONFIG_MEMSIZE(x) (((x) >> 0) & 0xFFFFFFFF) +#define C_0000F8_CONFIG_MEMSIZE 0x00000000 +#define R_000134_HDP_FB_LOCATION 0x000134 +#define S_000134_HDP_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_000134_HDP_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_000134_HDP_FB_START 0xFFFF0000 +#define R_0007C0_CP_STAT 0x0007C0 +#define S_0007C0_MRU_BUSY(x) (((x) & 0x1) << 0) +#define G_0007C0_MRU_BUSY(x) (((x) >> 0) & 0x1) +#define C_0007C0_MRU_BUSY 0xFFFFFFFE +#define S_0007C0_MWU_BUSY(x) (((x) & 0x1) << 1) +#define G_0007C0_MWU_BUSY(x) (((x) >> 1) & 0x1) +#define C_0007C0_MWU_BUSY 0xFFFFFFFD +#define S_0007C0_RSIU_BUSY(x) (((x) & 0x1) << 2) +#define G_0007C0_RSIU_BUSY(x) (((x) >> 2) & 0x1) +#define C_0007C0_RSIU_BUSY 0xFFFFFFFB +#define S_0007C0_RCIU_BUSY(x) (((x) & 0x1) << 3) +#define G_0007C0_RCIU_BUSY(x) (((x) >> 3) & 0x1) +#define C_0007C0_RCIU_BUSY 0xFFFFFFF7 +#define S_0007C0_CSF_PRIMARY_BUSY(x) (((x) & 0x1) << 9) +#define G_0007C0_CSF_PRIMARY_BUSY(x) (((x) >> 9) & 0x1) +#define C_0007C0_CSF_PRIMARY_BUSY 0xFFFFFDFF +#define S_0007C0_CSF_INDIRECT_BUSY(x) (((x) & 0x1) << 10) +#define G_0007C0_CSF_INDIRECT_BUSY(x) (((x) >> 10) & 0x1) +#define C_0007C0_CSF_INDIRECT_BUSY 0xFFFFFBFF +#define S_0007C0_CSQ_PRIMARY_BUSY(x) (((x) & 0x1) << 11) +#define G_0007C0_CSQ_PRIMARY_BUSY(x) (((x) >> 11) & 0x1) +#define C_0007C0_CSQ_PRIMARY_BUSY 0xFFFFF7FF +#define S_0007C0_CSQ_INDIRECT_BUSY(x) (((x) & 0x1) << 12) +#define G_0007C0_CSQ_INDIRECT_BUSY(x) (((x) >> 12) & 0x1) +#define C_0007C0_CSQ_INDIRECT_BUSY 0xFFFFEFFF +#define S_0007C0_CSI_BUSY(x) (((x) & 0x1) << 13) +#define G_0007C0_CSI_BUSY(x) (((x) >> 13) & 0x1) +#define C_0007C0_CSI_BUSY 0xFFFFDFFF +#define S_0007C0_CSF_INDIRECT2_BUSY(x) (((x) & 0x1) << 14) +#define G_0007C0_CSF_INDIRECT2_BUSY(x) (((x) >> 14) & 0x1) +#define C_0007C0_CSF_INDIRECT2_BUSY 0xFFFFBFFF +#define S_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) & 0x1) << 15) +#define G_0007C0_CSQ_INDIRECT2_BUSY(x) (((x) >> 15) & 0x1) +#define C_0007C0_CSQ_INDIRECT2_BUSY 0xFFFF7FFF +#define S_0007C0_GUIDMA_BUSY(x) (((x) & 0x1) << 28) +#define G_0007C0_GUIDMA_BUSY(x) (((x) >> 28) & 0x1) +#define C_0007C0_GUIDMA_BUSY 0xEFFFFFFF +#define S_0007C0_VIDDMA_BUSY(x) (((x) & 0x1) << 29) +#define G_0007C0_VIDDMA_BUSY(x) (((x) >> 29) & 0x1) +#define C_0007C0_VIDDMA_BUSY 0xDFFFFFFF +#define S_0007C0_CMDSTRM_BUSY(x) (((x) & 0x1) << 30) +#define G_0007C0_CMDSTRM_BUSY(x) (((x) >> 30) & 0x1) +#define C_0007C0_CMDSTRM_BUSY 0xBFFFFFFF +#define S_0007C0_CP_BUSY(x) (((x) & 0x1) << 31) +#define G_0007C0_CP_BUSY(x) (((x) >> 31) & 0x1) +#define C_0007C0_CP_BUSY 0x7FFFFFFF +#define R_000E40_RBBM_STATUS 0x000E40 +#define S_000E40_CMDFIFO_AVAIL(x) (((x) & 0x7F) << 0) +#define G_000E40_CMDFIFO_AVAIL(x) (((x) >> 0) & 0x7F) +#define C_000E40_CMDFIFO_AVAIL 0xFFFFFF80 +#define S_000E40_HIRQ_ON_RBB(x) (((x) & 0x1) << 8) +#define G_000E40_HIRQ_ON_RBB(x) (((x) >> 8) & 0x1) +#define C_000E40_HIRQ_ON_RBB 0xFFFFFEFF +#define S_000E40_CPRQ_ON_RBB(x) (((x) & 0x1) << 9) +#define G_000E40_CPRQ_ON_RBB(x) (((x) >> 9) & 0x1) +#define C_000E40_CPRQ_ON_RBB 0xFFFFFDFF +#define S_000E40_CFRQ_ON_RBB(x) (((x) & 0x1) << 10) +#define G_000E40_CFRQ_ON_RBB(x) (((x) >> 10) & 0x1) +#define C_000E40_CFRQ_ON_RBB 0xFFFFFBFF +#define S_000E40_HIRQ_IN_RTBUF(x) (((x) & 0x1) << 11) +#define G_000E40_HIRQ_IN_RTBUF(x) (((x) >> 11) & 0x1) +#define C_000E40_HIRQ_IN_RTBUF 0xFFFFF7FF +#define S_000E40_CPRQ_IN_RTBUF(x) (((x) & 0x1) << 12) +#define G_000E40_CPRQ_IN_RTBUF(x) (((x) >> 12) & 0x1) +#define C_000E40_CPRQ_IN_RTBUF 0xFFFFEFFF +#define S_000E40_CFRQ_IN_RTBUF(x) (((x) & 0x1) << 13) +#define G_000E40_CFRQ_IN_RTBUF(x) (((x) >> 13) & 0x1) +#define C_000E40_CFRQ_IN_RTBUF 0xFFFFDFFF +#define S_000E40_CF_PIPE_BUSY(x) (((x) & 0x1) << 14) +#define G_000E40_CF_PIPE_BUSY(x) (((x) >> 14) & 0x1) +#define C_000E40_CF_PIPE_BUSY 0xFFFFBFFF +#define S_000E40_ENG_EV_BUSY(x) (((x) & 0x1) << 15) +#define G_000E40_ENG_EV_BUSY(x) (((x) >> 15) & 0x1) +#define C_000E40_ENG_EV_BUSY 0xFFFF7FFF +#define S_000E40_CP_CMDSTRM_BUSY(x) (((x) & 0x1) << 16) +#define G_000E40_CP_CMDSTRM_BUSY(x) (((x) >> 16) & 0x1) +#define C_000E40_CP_CMDSTRM_BUSY 0xFFFEFFFF +#define S_000E40_E2_BUSY(x) (((x) & 0x1) << 17) +#define G_000E40_E2_BUSY(x) (((x) >> 17) & 0x1) +#define C_000E40_E2_BUSY 0xFFFDFFFF +#define S_000E40_RB2D_BUSY(x) (((x) & 0x1) << 18) +#define G_000E40_RB2D_BUSY(x) (((x) >> 18) & 0x1) +#define C_000E40_RB2D_BUSY 0xFFFBFFFF +#define S_000E40_RB3D_BUSY(x) (((x) & 0x1) << 19) +#define G_000E40_RB3D_BUSY(x) (((x) >> 19) & 0x1) +#define C_000E40_RB3D_BUSY 0xFFF7FFFF +#define S_000E40_VAP_BUSY(x) (((x) & 0x1) << 20) +#define G_000E40_VAP_BUSY(x) (((x) >> 20) & 0x1) +#define C_000E40_VAP_BUSY 0xFFEFFFFF +#define S_000E40_RE_BUSY(x) (((x) & 0x1) << 21) +#define G_000E40_RE_BUSY(x) (((x) >> 21) & 0x1) +#define C_000E40_RE_BUSY 0xFFDFFFFF +#define S_000E40_TAM_BUSY(x) (((x) & 0x1) << 22) +#define G_000E40_TAM_BUSY(x) (((x) >> 22) & 0x1) +#define C_000E40_TAM_BUSY 0xFFBFFFFF +#define S_000E40_TDM_BUSY(x) (((x) & 0x1) << 23) +#define G_000E40_TDM_BUSY(x) (((x) >> 23) & 0x1) +#define C_000E40_TDM_BUSY 0xFF7FFFFF +#define S_000E40_PB_BUSY(x) (((x) & 0x1) << 24) +#define G_000E40_PB_BUSY(x) (((x) >> 24) & 0x1) +#define C_000E40_PB_BUSY 0xFEFFFFFF +#define S_000E40_TIM_BUSY(x) (((x) & 0x1) << 25) +#define G_000E40_TIM_BUSY(x) (((x) >> 25) & 0x1) +#define C_000E40_TIM_BUSY 0xFDFFFFFF +#define S_000E40_GA_BUSY(x) (((x) & 0x1) << 26) +#define G_000E40_GA_BUSY(x) (((x) >> 26) & 0x1) +#define C_000E40_GA_BUSY 0xFBFFFFFF +#define S_000E40_CBA2D_BUSY(x) (((x) & 0x1) << 27) +#define G_000E40_CBA2D_BUSY(x) (((x) >> 27) & 0x1) +#define C_000E40_CBA2D_BUSY 0xF7FFFFFF +#define S_000E40_GUI_ACTIVE(x) (((x) & 0x1) << 31) +#define G_000E40_GUI_ACTIVE(x) (((x) >> 31) & 0x1) +#define C_000E40_GUI_ACTIVE 0x7FFFFFFF +#define R_006520_DC_LB_MEMORY_SPLIT 0x006520 +#define S_006520_DC_LB_MEMORY_SPLIT(x) (((x) & 0x3) << 0) +#define G_006520_DC_LB_MEMORY_SPLIT(x) (((x) >> 0) & 0x3) +#define C_006520_DC_LB_MEMORY_SPLIT 0xFFFFFFFC +#define S_006520_DC_LB_MEMORY_SPLIT_MODE(x) (((x) & 0x1) << 2) +#define G_006520_DC_LB_MEMORY_SPLIT_MODE(x) (((x) >> 2) & 0x1) +#define C_006520_DC_LB_MEMORY_SPLIT_MODE 0xFFFFFFFB +#define V_006520_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF 0 +#define V_006520_DC_LB_MEMORY_SPLIT_D1_3Q_D2_1Q 1 +#define V_006520_DC_LB_MEMORY_SPLIT_D1_ONLY 2 +#define V_006520_DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q 3 +#define S_006520_DC_LB_DISP1_END_ADR(x) (((x) & 0x7FF) << 4) +#define G_006520_DC_LB_DISP1_END_ADR(x) (((x) >> 4) & 0x7FF) +#define C_006520_DC_LB_DISP1_END_ADR 0xFFFF800F +#define R_006548_D1MODE_PRIORITY_A_CNT 0x006548 +#define S_006548_D1MODE_PRIORITY_MARK_A(x) (((x) & 0x7FFF) << 0) +#define G_006548_D1MODE_PRIORITY_MARK_A(x) (((x) >> 0) & 0x7FFF) +#define C_006548_D1MODE_PRIORITY_MARK_A 0xFFFF8000 +#define S_006548_D1MODE_PRIORITY_A_OFF(x) (((x) & 0x1) << 16) +#define G_006548_D1MODE_PRIORITY_A_OFF(x) (((x) >> 16) & 0x1) +#define C_006548_D1MODE_PRIORITY_A_OFF 0xFFFEFFFF +#define S_006548_D1MODE_PRIORITY_A_FORCE_MASK(x) (((x) & 0x1) << 24) +#define G_006548_D1MODE_PRIORITY_A_FORCE_MASK(x) (((x) >> 24) & 0x1) +#define C_006548_D1MODE_PRIORITY_A_FORCE_MASK 0xFEFFFFFF +#define R_00654C_D1MODE_PRIORITY_B_CNT 0x00654C +#define S_00654C_D1MODE_PRIORITY_MARK_B(x) (((x) & 0x7FFF) << 0) +#define G_00654C_D1MODE_PRIORITY_MARK_B(x) (((x) >> 0) & 0x7FFF) +#define C_00654C_D1MODE_PRIORITY_MARK_B 0xFFFF8000 +#define S_00654C_D1MODE_PRIORITY_B_OFF(x) (((x) & 0x1) << 16) +#define G_00654C_D1MODE_PRIORITY_B_OFF(x) (((x) >> 16) & 0x1) +#define C_00654C_D1MODE_PRIORITY_B_OFF 0xFFFEFFFF +#define S_00654C_D1MODE_PRIORITY_B_ALWAYS_ON(x) (((x) & 0x1) << 20) +#define G_00654C_D1MODE_PRIORITY_B_ALWAYS_ON(x) (((x) >> 20) & 0x1) +#define C_00654C_D1MODE_PRIORITY_B_ALWAYS_ON 0xFFEFFFFF +#define S_00654C_D1MODE_PRIORITY_B_FORCE_MASK(x) (((x) & 0x1) << 24) +#define G_00654C_D1MODE_PRIORITY_B_FORCE_MASK(x) (((x) >> 24) & 0x1) +#define C_00654C_D1MODE_PRIORITY_B_FORCE_MASK 0xFEFFFFFF +#define R_006C9C_DCP_CONTROL 0x006C9C +#define R_006D48_D2MODE_PRIORITY_A_CNT 0x006D48 +#define S_006D48_D2MODE_PRIORITY_MARK_A(x) (((x) & 0x7FFF) << 0) +#define G_006D48_D2MODE_PRIORITY_MARK_A(x) (((x) >> 0) & 0x7FFF) +#define C_006D48_D2MODE_PRIORITY_MARK_A 0xFFFF8000 +#define S_006D48_D2MODE_PRIORITY_A_OFF(x) (((x) & 0x1) << 16) +#define G_006D48_D2MODE_PRIORITY_A_OFF(x) (((x) >> 16) & 0x1) +#define C_006D48_D2MODE_PRIORITY_A_OFF 0xFFFEFFFF +#define S_006D48_D2MODE_PRIORITY_A_ALWAYS_ON(x) (((x) & 0x1) << 20) +#define G_006D48_D2MODE_PRIORITY_A_ALWAYS_ON(x) (((x) >> 20) & 0x1) +#define C_006D48_D2MODE_PRIORITY_A_ALWAYS_ON 0xFFEFFFFF +#define S_006D48_D2MODE_PRIORITY_A_FORCE_MASK(x) (((x) & 0x1) << 24) +#define G_006D48_D2MODE_PRIORITY_A_FORCE_MASK(x) (((x) >> 24) & 0x1) +#define C_006D48_D2MODE_PRIORITY_A_FORCE_MASK 0xFEFFFFFF +#define R_006D4C_D2MODE_PRIORITY_B_CNT 0x006D4C +#define S_006D4C_D2MODE_PRIORITY_MARK_B(x) (((x) & 0x7FFF) << 0) +#define G_006D4C_D2MODE_PRIORITY_MARK_B(x) (((x) >> 0) & 0x7FFF) +#define C_006D4C_D2MODE_PRIORITY_MARK_B 0xFFFF8000 +#define S_006D4C_D2MODE_PRIORITY_B_OFF(x) (((x) & 0x1) << 16) +#define G_006D4C_D2MODE_PRIORITY_B_OFF(x) (((x) >> 16) & 0x1) +#define C_006D4C_D2MODE_PRIORITY_B_OFF 0xFFFEFFFF +#define S_006D4C_D2MODE_PRIORITY_B_ALWAYS_ON(x) (((x) & 0x1) << 20) +#define G_006D4C_D2MODE_PRIORITY_B_ALWAYS_ON(x) (((x) >> 20) & 0x1) +#define C_006D4C_D2MODE_PRIORITY_B_ALWAYS_ON 0xFFEFFFFF +#define S_006D4C_D2MODE_PRIORITY_B_FORCE_MASK(x) (((x) & 0x1) << 24) +#define G_006D4C_D2MODE_PRIORITY_B_FORCE_MASK(x) (((x) >> 24) & 0x1) +#define C_006D4C_D2MODE_PRIORITY_B_FORCE_MASK 0xFEFFFFFF +#define R_006D58_LB_MAX_REQ_OUTSTANDING 0x006D58 +#define S_006D58_LB_D1_MAX_REQ_OUTSTANDING(x) (((x) & 0xF) << 0) +#define G_006D58_LB_D1_MAX_REQ_OUTSTANDING(x) (((x) >> 0) & 0xF) +#define C_006D58_LB_D1_MAX_REQ_OUTSTANDING 0xFFFFFFF0 +#define S_006D58_LB_D2_MAX_REQ_OUTSTANDING(x) (((x) & 0xF) << 16) +#define G_006D58_LB_D2_MAX_REQ_OUTSTANDING(x) (((x) >> 16) & 0xF) +#define C_006D58_LB_D2_MAX_REQ_OUTSTANDING 0xFFF0FFFF + + +#define R_000090_MC_SYSTEM_STATUS 0x000090 +#define S_000090_MC_SYSTEM_IDLE(x) (((x) & 0x1) << 0) +#define G_000090_MC_SYSTEM_IDLE(x) (((x) >> 0) & 0x1) +#define C_000090_MC_SYSTEM_IDLE 0xFFFFFFFE +#define S_000090_MC_SEQUENCER_IDLE(x) (((x) & 0x1) << 1) +#define G_000090_MC_SEQUENCER_IDLE(x) (((x) >> 1) & 0x1) +#define C_000090_MC_SEQUENCER_IDLE 0xFFFFFFFD +#define S_000090_MC_ARBITER_IDLE(x) (((x) & 0x1) << 2) +#define G_000090_MC_ARBITER_IDLE(x) (((x) >> 2) & 0x1) +#define C_000090_MC_ARBITER_IDLE 0xFFFFFFFB +#define S_000090_MC_SELECT_PM(x) (((x) & 0x1) << 3) +#define G_000090_MC_SELECT_PM(x) (((x) >> 3) & 0x1) +#define C_000090_MC_SELECT_PM 0xFFFFFFF7 +#define S_000090_RESERVED4(x) (((x) & 0xF) << 4) +#define G_000090_RESERVED4(x) (((x) >> 4) & 0xF) +#define C_000090_RESERVED4 0xFFFFFF0F +#define S_000090_RESERVED8(x) (((x) & 0xF) << 8) +#define G_000090_RESERVED8(x) (((x) >> 8) & 0xF) +#define C_000090_RESERVED8 0xFFFFF0FF +#define S_000090_RESERVED12(x) (((x) & 0xF) << 12) +#define G_000090_RESERVED12(x) (((x) >> 12) & 0xF) +#define C_000090_RESERVED12 0xFFFF0FFF +#define S_000090_MCA_INIT_EXECUTED(x) (((x) & 0x1) << 16) +#define G_000090_MCA_INIT_EXECUTED(x) (((x) >> 16) & 0x1) +#define C_000090_MCA_INIT_EXECUTED 0xFFFEFFFF +#define S_000090_MCA_IDLE(x) (((x) & 0x1) << 17) +#define G_000090_MCA_IDLE(x) (((x) >> 17) & 0x1) +#define C_000090_MCA_IDLE 0xFFFDFFFF +#define S_000090_MCA_SEQ_IDLE(x) (((x) & 0x1) << 18) +#define G_000090_MCA_SEQ_IDLE(x) (((x) >> 18) & 0x1) +#define C_000090_MCA_SEQ_IDLE 0xFFFBFFFF +#define S_000090_MCA_ARB_IDLE(x) (((x) & 0x1) << 19) +#define G_000090_MCA_ARB_IDLE(x) (((x) >> 19) & 0x1) +#define C_000090_MCA_ARB_IDLE 0xFFF7FFFF +#define S_000090_RESERVED20(x) (((x) & 0xFFF) << 20) +#define G_000090_RESERVED20(x) (((x) >> 20) & 0xFFF) +#define C_000090_RESERVED20 0x000FFFFF +#define R_000100_MCCFG_FB_LOCATION 0x000100 +#define S_000100_MC_FB_START(x) (((x) & 0xFFFF) << 0) +#define G_000100_MC_FB_START(x) (((x) >> 0) & 0xFFFF) +#define C_000100_MC_FB_START 0xFFFF0000 +#define S_000100_MC_FB_TOP(x) (((x) & 0xFFFF) << 16) +#define G_000100_MC_FB_TOP(x) (((x) >> 16) & 0xFFFF) +#define C_000100_MC_FB_TOP 0x0000FFFF +#define R_000104_MC_INIT_MISC_LAT_TIMER 0x000104 +#define S_000104_MC_CPR_INIT_LAT(x) (((x) & 0xF) << 0) +#define G_000104_MC_CPR_INIT_LAT(x) (((x) >> 0) & 0xF) +#define C_000104_MC_CPR_INIT_LAT 0xFFFFFFF0 +#define S_000104_MC_VF_INIT_LAT(x) (((x) & 0xF) << 4) +#define G_000104_MC_VF_INIT_LAT(x) (((x) >> 4) & 0xF) +#define C_000104_MC_VF_INIT_LAT 0xFFFFFF0F +#define S_000104_MC_DISP0R_INIT_LAT(x) (((x) & 0xF) << 8) +#define G_000104_MC_DISP0R_INIT_LAT(x) (((x) >> 8) & 0xF) +#define C_000104_MC_DISP0R_INIT_LAT 0xFFFFF0FF +#define S_000104_MC_DISP1R_INIT_LAT(x) (((x) & 0xF) << 12) +#define G_000104_MC_DISP1R_INIT_LAT(x) (((x) >> 12) & 0xF) +#define C_000104_MC_DISP1R_INIT_LAT 0xFFFF0FFF +#define S_000104_MC_FIXED_INIT_LAT(x) (((x) & 0xF) << 16) +#define G_000104_MC_FIXED_INIT_LAT(x) (((x) >> 16) & 0xF) +#define C_000104_MC_FIXED_INIT_LAT 0xFFF0FFFF +#define S_000104_MC_E2R_INIT_LAT(x) (((x) & 0xF) << 20) +#define G_000104_MC_E2R_INIT_LAT(x) (((x) >> 20) & 0xF) +#define C_000104_MC_E2R_INIT_LAT 0xFF0FFFFF +#define S_000104_SAME_PAGE_PRIO(x) (((x) & 0xF) << 24) +#define G_000104_SAME_PAGE_PRIO(x) (((x) >> 24) & 0xF) +#define C_000104_SAME_PAGE_PRIO 0xF0FFFFFF +#define S_000104_MC_GLOBW_INIT_LAT(x) (((x) & 0xF) << 28) +#define G_000104_MC_GLOBW_INIT_LAT(x) (((x) >> 28) & 0xF) +#define C_000104_MC_GLOBW_INIT_LAT 0x0FFFFFFF + +#endif diff --git a/drivers/gpu/drm/radeon/rs690r.h b/drivers/gpu/drm/radeon/rs690r.h deleted file mode 100644 index c0d9faa2175b..000000000000 --- a/drivers/gpu/drm/radeon/rs690r.h +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright 2008 Advanced Micro Devices, Inc. - * Copyright 2008 Red Hat Inc. - * Copyright 2009 Jerome Glisse. - * - * Permission is hereby granted, free of charge, to any person obtaining a - * copy of this software and associated documentation files (the "Software"), - * to deal in the Software without restriction, including without limitation - * the rights to use, copy, modify, merge, publish, distribute, sublicense, - * and/or sell copies of the Software, and to permit persons to whom the - * Software is furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL - * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR - * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, - * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR - * OTHER DEALINGS IN THE SOFTWARE. - * - * Authors: Dave Airlie - * Alex Deucher - * Jerome Glisse - */ -#ifndef RS690R_H -#define RS690R_H - -/* RS690/RS740 registers */ -#define MC_INDEX 0x0078 -# define MC_INDEX_MASK 0x1FF -# define MC_INDEX_WR_EN (1 << 9) -# define MC_INDEX_WR_ACK 0x7F -#define MC_DATA 0x007C -#define HDP_FB_LOCATION 0x0134 -#define DC_LB_MEMORY_SPLIT 0x6520 -#define DC_LB_MEMORY_SPLIT_MASK 0x00000003 -#define DC_LB_MEMORY_SPLIT_SHIFT 0 -#define DC_LB_MEMORY_SPLIT_D1HALF_D2HALF 0 -#define DC_LB_MEMORY_SPLIT_D1_3Q_D2_1Q 1 -#define DC_LB_MEMORY_SPLIT_D1_ONLY 2 -#define DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q 3 -#define DC_LB_MEMORY_SPLIT_SHIFT_MODE (1 << 2) -#define DC_LB_DISP1_END_ADR_SHIFT 4 -#define DC_LB_DISP1_END_ADR_MASK 0x00007FF0 -#define D1MODE_PRIORITY_A_CNT 0x6548 -#define MODE_PRIORITY_MARK_MASK 0x00007FFF -#define MODE_PRIORITY_OFF (1 << 16) -#define MODE_PRIORITY_ALWAYS_ON (1 << 20) -#define MODE_PRIORITY_FORCE_MASK (1 << 24) -#define D1MODE_PRIORITY_B_CNT 0x654C -#define LB_MAX_REQ_OUTSTANDING 0x6D58 -#define LB_D1_MAX_REQ_OUTSTANDING_MASK 0x0000000F -#define LB_D1_MAX_REQ_OUTSTANDING_SHIFT 0 -#define LB_D2_MAX_REQ_OUTSTANDING_MASK 0x000F0000 -#define LB_D2_MAX_REQ_OUTSTANDING_SHIFT 16 -#define DCP_CONTROL 0x6C9C -#define D2MODE_PRIORITY_A_CNT 0x6D48 -#define D2MODE_PRIORITY_B_CNT 0x6D4C - -/* MC indirect registers */ -#define MC_STATUS_IDLE (1 << 0) -#define MC_MISC_CNTL 0x18 -#define DISABLE_GTW (1 << 1) -#define GART_INDEX_REG_EN (1 << 12) -#define BLOCK_GFX_D3_EN (1 << 14) -#define GART_FEATURE_ID 0x2B -#define HANG_EN (1 << 11) -#define TLB_ENABLE (1 << 18) -#define P2P_ENABLE (1 << 19) -#define GTW_LAC_EN (1 << 25) -#define LEVEL2_GART (0 << 30) -#define LEVEL1_GART (1 << 30) -#define PDC_EN (1 << 31) -#define GART_BASE 0x2C -#define GART_CACHE_CNTRL 0x2E -# define GART_CACHE_INVALIDATE (1 << 0) -#define MC_STATUS 0x90 -#define MCCFG_FB_LOCATION 0x100 -#define MC_FB_START_MASK 0x0000FFFF -#define MC_FB_START_SHIFT 0 -#define MC_FB_TOP_MASK 0xFFFF0000 -#define MC_FB_TOP_SHIFT 16 -#define MCCFG_AGP_LOCATION 0x101 -#define MC_AGP_START_MASK 0x0000FFFF -#define MC_AGP_START_SHIFT 0 -#define MC_AGP_TOP_MASK 0xFFFF0000 -#define MC_AGP_TOP_SHIFT 16 -#define MCCFG_AGP_BASE 0x102 -#define MCCFG_AGP_BASE_2 0x103 -#define MC_INIT_MISC_LAT_TIMER 0x104 -#define MC_DISP0R_INIT_LAT_SHIFT 8 -#define MC_DISP0R_INIT_LAT_MASK 0x00000F00 -#define MC_DISP1R_INIT_LAT_SHIFT 12 -#define MC_DISP1R_INIT_LAT_MASK 0x0000F000 - -#endif diff --git a/drivers/gpu/drm/radeon/rv200d.h b/drivers/gpu/drm/radeon/rv200d.h new file mode 100644 index 000000000000..c5b398330c26 --- /dev/null +++ b/drivers/gpu/drm/radeon/rv200d.h @@ -0,0 +1,36 @@ +/* + * Copyright 2008 Advanced Micro Devices, Inc. + * Copyright 2008 Red Hat Inc. + * Copyright 2009 Jerome Glisse. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Alex Deucher + * Jerome Glisse + */ +#ifndef __RV200D_H__ +#define __RV200D_H__ + +#define R_00015C_AGP_BASE_2 0x00015C +#define S_00015C_AGP_BASE_ADDR_2(x) (((x) & 0xF) << 0) +#define G_00015C_AGP_BASE_ADDR_2(x) (((x) >> 0) & 0xF) +#define C_00015C_AGP_BASE_ADDR_2 0xFFFFFFF0 + +#endif diff --git a/drivers/gpu/drm/radeon/rv250d.h b/drivers/gpu/drm/radeon/rv250d.h new file mode 100644 index 000000000000..e5a70b06fe1f --- /dev/null +++ b/drivers/gpu/drm/radeon/rv250d.h @@ -0,0 +1,123 @@ +/* + * Copyright 2008 Advanced Micro Devices, Inc. + * Copyright 2008 Red Hat Inc. + * Copyright 2009 Jerome Glisse. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Alex Deucher + * Jerome Glisse + */ +#ifndef __RV250D_H__ +#define __RV250D_H__ + +#define R_00000D_SCLK_CNTL_M6 0x00000D +#define S_00000D_SCLK_SRC_SEL(x) (((x) & 0x7) << 0) +#define G_00000D_SCLK_SRC_SEL(x) (((x) >> 0) & 0x7) +#define C_00000D_SCLK_SRC_SEL 0xFFFFFFF8 +#define S_00000D_CP_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 3) +#define G_00000D_CP_MAX_DYN_STOP_LAT(x) (((x) >> 3) & 0x1) +#define C_00000D_CP_MAX_DYN_STOP_LAT 0xFFFFFFF7 +#define S_00000D_HDP_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 4) +#define G_00000D_HDP_MAX_DYN_STOP_LAT(x) (((x) >> 4) & 0x1) +#define C_00000D_HDP_MAX_DYN_STOP_LAT 0xFFFFFFEF +#define S_00000D_TV_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 5) +#define G_00000D_TV_MAX_DYN_STOP_LAT(x) (((x) >> 5) & 0x1) +#define C_00000D_TV_MAX_DYN_STOP_LAT 0xFFFFFFDF +#define S_00000D_E2_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 6) +#define G_00000D_E2_MAX_DYN_STOP_LAT(x) (((x) >> 6) & 0x1) +#define C_00000D_E2_MAX_DYN_STOP_LAT 0xFFFFFFBF +#define S_00000D_SE_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 7) +#define G_00000D_SE_MAX_DYN_STOP_LAT(x) (((x) >> 7) & 0x1) +#define C_00000D_SE_MAX_DYN_STOP_LAT 0xFFFFFF7F +#define S_00000D_IDCT_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 8) +#define G_00000D_IDCT_MAX_DYN_STOP_LAT(x) (((x) >> 8) & 0x1) +#define C_00000D_IDCT_MAX_DYN_STOP_LAT 0xFFFFFEFF +#define S_00000D_VIP_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 9) +#define G_00000D_VIP_MAX_DYN_STOP_LAT(x) (((x) >> 9) & 0x1) +#define C_00000D_VIP_MAX_DYN_STOP_LAT 0xFFFFFDFF +#define S_00000D_RE_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 10) +#define G_00000D_RE_MAX_DYN_STOP_LAT(x) (((x) >> 10) & 0x1) +#define C_00000D_RE_MAX_DYN_STOP_LAT 0xFFFFFBFF +#define S_00000D_PB_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 11) +#define G_00000D_PB_MAX_DYN_STOP_LAT(x) (((x) >> 11) & 0x1) +#define C_00000D_PB_MAX_DYN_STOP_LAT 0xFFFFF7FF +#define S_00000D_TAM_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 12) +#define G_00000D_TAM_MAX_DYN_STOP_LAT(x) (((x) >> 12) & 0x1) +#define C_00000D_TAM_MAX_DYN_STOP_LAT 0xFFFFEFFF +#define S_00000D_TDM_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 13) +#define G_00000D_TDM_MAX_DYN_STOP_LAT(x) (((x) >> 13) & 0x1) +#define C_00000D_TDM_MAX_DYN_STOP_LAT 0xFFFFDFFF +#define S_00000D_RB_MAX_DYN_STOP_LAT(x) (((x) & 0x1) << 14) +#define G_00000D_RB_MAX_DYN_STOP_LAT(x) (((x) >> 14) & 0x1) +#define C_00000D_RB_MAX_DYN_STOP_LAT 0xFFFFBFFF +#define S_00000D_FORCE_DISP2(x) (((x) & 0x1) << 15) +#define G_00000D_FORCE_DISP2(x) (((x) >> 15) & 0x1) +#define C_00000D_FORCE_DISP2 0xFFFF7FFF +#define S_00000D_FORCE_CP(x) (((x) & 0x1) << 16) +#define G_00000D_FORCE_CP(x) (((x) >> 16) & 0x1) +#define C_00000D_FORCE_CP 0xFFFEFFFF +#define S_00000D_FORCE_HDP(x) (((x) & 0x1) << 17) +#define G_00000D_FORCE_HDP(x) (((x) >> 17) & 0x1) +#define C_00000D_FORCE_HDP 0xFFFDFFFF +#define S_00000D_FORCE_DISP1(x) (((x) & 0x1) << 18) +#define G_00000D_FORCE_DISP1(x) (((x) >> 18) & 0x1) +#define C_00000D_FORCE_DISP1 0xFFFBFFFF +#define S_00000D_FORCE_TOP(x) (((x) & 0x1) << 19) +#define G_00000D_FORCE_TOP(x) (((x) >> 19) & 0x1) +#define C_00000D_FORCE_TOP 0xFFF7FFFF +#define S_00000D_FORCE_E2(x) (((x) & 0x1) << 20) +#define G_00000D_FORCE_E2(x) (((x) >> 20) & 0x1) +#define C_00000D_FORCE_E2 0xFFEFFFFF +#define S_00000D_FORCE_SE(x) (((x) & 0x1) << 21) +#define G_00000D_FORCE_SE(x) (((x) >> 21) & 0x1) +#define C_00000D_FORCE_SE 0xFFDFFFFF +#define S_00000D_FORCE_IDCT(x) (((x) & 0x1) << 22) +#define G_00000D_FORCE_IDCT(x) (((x) >> 22) & 0x1) +#define C_00000D_FORCE_IDCT 0xFFBFFFFF +#define S_00000D_FORCE_VIP(x) (((x) & 0x1) << 23) +#define G_00000D_FORCE_VIP(x) (((x) >> 23) & 0x1) +#define C_00000D_FORCE_VIP 0xFF7FFFFF +#define S_00000D_FORCE_RE(x) (((x) & 0x1) << 24) +#define G_00000D_FORCE_RE(x) (((x) >> 24) & 0x1) +#define C_00000D_FORCE_RE 0xFEFFFFFF +#define S_00000D_FORCE_PB(x) (((x) & 0x1) << 25) +#define G_00000D_FORCE_PB(x) (((x) >> 25) & 0x1) +#define C_00000D_FORCE_PB 0xFDFFFFFF +#define S_00000D_FORCE_TAM(x) (((x) & 0x1) << 26) +#define G_00000D_FORCE_TAM(x) (((x) >> 26) & 0x1) +#define C_00000D_FORCE_TAM 0xFBFFFFFF +#define S_00000D_FORCE_TDM(x) (((x) & 0x1) << 27) +#define G_00000D_FORCE_TDM(x) (((x) >> 27) & 0x1) +#define C_00000D_FORCE_TDM 0xF7FFFFFF +#define S_00000D_FORCE_RB(x) (((x) & 0x1) << 28) +#define G_00000D_FORCE_RB(x) (((x) >> 28) & 0x1) +#define C_00000D_FORCE_RB 0xEFFFFFFF +#define S_00000D_FORCE_TV_SCLK(x) (((x) & 0x1) << 29) +#define G_00000D_FORCE_TV_SCLK(x) (((x) >> 29) & 0x1) +#define C_00000D_FORCE_TV_SCLK 0xDFFFFFFF +#define S_00000D_FORCE_SUBPIC(x) (((x) & 0x1) << 30) +#define G_00000D_FORCE_SUBPIC(x) (((x) >> 30) & 0x1) +#define C_00000D_FORCE_SUBPIC 0xBFFFFFFF +#define S_00000D_FORCE_OV0(x) (((x) & 0x1) << 31) +#define G_00000D_FORCE_OV0(x) (((x) >> 31) & 0x1) +#define C_00000D_FORCE_OV0 0x7FFFFFFF + +#endif diff --git a/drivers/gpu/drm/radeon/rv350d.h b/drivers/gpu/drm/radeon/rv350d.h new file mode 100644 index 000000000000..c75c5ed9e654 --- /dev/null +++ b/drivers/gpu/drm/radeon/rv350d.h @@ -0,0 +1,52 @@ +/* + * Copyright 2008 Advanced Micro Devices, Inc. + * Copyright 2008 Red Hat Inc. + * Copyright 2009 Jerome Glisse. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: Dave Airlie + * Alex Deucher + * Jerome Glisse + */ +#ifndef __RV350D_H__ +#define __RV350D_H__ + +/* RV350, RV380 registers */ +/* #define R_00000D_SCLK_CNTL 0x00000D */ +#define S_00000D_FORCE_VAP(x) (((x) & 0x1) << 21) +#define G_00000D_FORCE_VAP(x) (((x) >> 21) & 0x1) +#define C_00000D_FORCE_VAP 0xFFDFFFFF +#define S_00000D_FORCE_SR(x) (((x) & 0x1) << 25) +#define G_00000D_FORCE_SR(x) (((x) >> 25) & 0x1) +#define C_00000D_FORCE_SR 0xFDFFFFFF +#define S_00000D_FORCE_PX(x) (((x) & 0x1) << 26) +#define G_00000D_FORCE_PX(x) (((x) >> 26) & 0x1) +#define C_00000D_FORCE_PX 0xFBFFFFFF +#define S_00000D_FORCE_TX(x) (((x) & 0x1) << 27) +#define G_00000D_FORCE_TX(x) (((x) >> 27) & 0x1) +#define C_00000D_FORCE_TX 0xF7FFFFFF +#define S_00000D_FORCE_US(x) (((x) & 0x1) << 28) +#define G_00000D_FORCE_US(x) (((x) >> 28) & 0x1) +#define C_00000D_FORCE_US 0xEFFFFFFF +#define S_00000D_FORCE_SU(x) (((x) & 0x1) << 30) +#define G_00000D_FORCE_SU(x) (((x) >> 30) & 0x1) +#define C_00000D_FORCE_SU 0xBFFFFFFF + +#endif diff --git a/drivers/gpu/drm/radeon/rv515.c b/drivers/gpu/drm/radeon/rv515.c index e53b5ca7a253..7935f793bf62 100644 --- a/drivers/gpu/drm/radeon/rv515.c +++ b/drivers/gpu/drm/radeon/rv515.c @@ -137,6 +137,8 @@ int rv515_mc_wait_for_idle(struct radeon_device *rdev) void rv515_vga_render_disable(struct radeon_device *rdev) { + WREG32(R_000330_D1VGA_CONTROL, 0); + WREG32(R_000338_D2VGA_CONTROL, 0); WREG32(R_000300_VGA_RENDER_CONTROL, RREG32(R_000300_VGA_RENDER_CONTROL) & C_000300_VGA_VSTATUS_CNTL); } @@ -478,7 +480,7 @@ static int rv515_startup(struct radeon_device *rdev) } /* Enable IRQ */ rdev->irq.sw_int = true; - r100_irq_set(rdev); + rs600_irq_set(rdev); /* 1M ring buffer */ r = r100_cp_init(rdev, 1024 * 1024); if (r) { @@ -520,7 +522,7 @@ int rv515_suspend(struct radeon_device *rdev) { r100_cp_disable(rdev); r100_wb_disable(rdev); - r100_irq_disable(rdev); + rs600_irq_disable(rdev); if (rdev->flags & RADEON_IS_PCIE) rv370_pcie_gart_disable(rdev); return 0; @@ -553,7 +555,6 @@ int rv515_init(struct radeon_device *rdev) { int r; - rdev->new_init_path = true; /* Initialize scratch registers */ radeon_scratch_init(rdev); /* Initialize surface registers */ @@ -586,6 +587,8 @@ int rv515_init(struct radeon_device *rdev) } /* Initialize clocks */ radeon_get_clock_info(rdev->ddev); + /* Initialize power management */ + radeon_pm_init(rdev); /* Get vram informations */ rv515_vram_info(rdev); /* Initialize memory controller (also test AGP) */ diff --git a/drivers/gpu/drm/radeon/rv770.c b/drivers/gpu/drm/radeon/rv770.c index e0b97d161397..b0efd0ddae7a 100644 --- a/drivers/gpu/drm/radeon/rv770.c +++ b/drivers/gpu/drm/radeon/rv770.c @@ -75,7 +75,7 @@ int rv770_pcie_gart_enable(struct radeon_device *rdev) WREG32(MC_VM_MB_L1_TLB2_CNTL, tmp); WREG32(MC_VM_MB_L1_TLB3_CNTL, tmp); WREG32(VM_CONTEXT0_PAGE_TABLE_START_ADDR, rdev->mc.gtt_start >> 12); - WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR, (rdev->mc.gtt_end - 1) >> 12); + WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR, rdev->mc.gtt_end >> 12); WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR, rdev->gart.table_addr >> 12); WREG32(VM_CONTEXT0_CNTL, ENABLE_CONTEXT | PAGE_TABLE_DEPTH(0) | RANGE_PROTECTION_FAULT_ENABLE_DEFAULT); @@ -126,17 +126,36 @@ void rv770_pcie_gart_fini(struct radeon_device *rdev) } -/* - * MC - */ -static void rv770_mc_resume(struct radeon_device *rdev) +void rv770_agp_enable(struct radeon_device *rdev) +{ + u32 tmp; + int i; + + /* Setup L2 cache */ + WREG32(VM_L2_CNTL, ENABLE_L2_CACHE | ENABLE_L2_FRAGMENT_PROCESSING | + ENABLE_L2_PTE_CACHE_LRU_UPDATE_BY_WRITE | + EFFECTIVE_L2_QUEUE_SIZE(7)); + WREG32(VM_L2_CNTL2, 0); + WREG32(VM_L2_CNTL3, BANK_SELECT(0) | CACHE_UPDATE_MODE(2)); + /* Setup TLB control */ + tmp = ENABLE_L1_TLB | ENABLE_L1_FRAGMENT_PROCESSING | + SYSTEM_ACCESS_MODE_NOT_IN_SYS | + SYSTEM_APERTURE_UNMAPPED_ACCESS_PASS_THRU | + EFFECTIVE_L1_TLB_SIZE(5) | EFFECTIVE_L1_QUEUE_SIZE(5); + WREG32(MC_VM_MD_L1_TLB0_CNTL, tmp); + WREG32(MC_VM_MD_L1_TLB1_CNTL, tmp); + WREG32(MC_VM_MD_L1_TLB2_CNTL, tmp); + WREG32(MC_VM_MB_L1_TLB0_CNTL, tmp); + WREG32(MC_VM_MB_L1_TLB1_CNTL, tmp); + WREG32(MC_VM_MB_L1_TLB2_CNTL, tmp); + WREG32(MC_VM_MB_L1_TLB3_CNTL, tmp); + for (i = 0; i < 7; i++) + WREG32(VM_CONTEXT0_CNTL + (i * 4), 0); +} + +static void rv770_mc_program(struct radeon_device *rdev) { - u32 d1vga_control, d2vga_control; - u32 vga_render_control, vga_hdp_control; - u32 d1crtc_control, d2crtc_control; - u32 new_d1grph_primary, new_d1grph_secondary; - u32 new_d2grph_primary, new_d2grph_secondary; - u64 old_vram_start; + struct rv515_mc_save save; u32 tmp; int i, j; @@ -150,53 +169,42 @@ static void rv770_mc_resume(struct radeon_device *rdev) } WREG32(HDP_REG_COHERENCY_FLUSH_CNTL, 0); - d1vga_control = RREG32(D1VGA_CONTROL); - d2vga_control = RREG32(D2VGA_CONTROL); - vga_render_control = RREG32(VGA_RENDER_CONTROL); - vga_hdp_control = RREG32(VGA_HDP_CONTROL); - d1crtc_control = RREG32(D1CRTC_CONTROL); - d2crtc_control = RREG32(D2CRTC_CONTROL); - old_vram_start = (u64)(RREG32(MC_VM_FB_LOCATION) & 0xFFFF) << 24; - new_d1grph_primary = RREG32(D1GRPH_PRIMARY_SURFACE_ADDRESS); - new_d1grph_secondary = RREG32(D1GRPH_SECONDARY_SURFACE_ADDRESS); - new_d1grph_primary += rdev->mc.vram_start - old_vram_start; - new_d1grph_secondary += rdev->mc.vram_start - old_vram_start; - new_d2grph_primary = RREG32(D2GRPH_PRIMARY_SURFACE_ADDRESS); - new_d2grph_secondary = RREG32(D2GRPH_SECONDARY_SURFACE_ADDRESS); - new_d2grph_primary += rdev->mc.vram_start - old_vram_start; - new_d2grph_secondary += rdev->mc.vram_start - old_vram_start; - - /* Stop all video */ - WREG32(D1VGA_CONTROL, 0); - WREG32(D2VGA_CONTROL, 0); - WREG32(VGA_RENDER_CONTROL, 0); - WREG32(D1CRTC_UPDATE_LOCK, 1); - WREG32(D2CRTC_UPDATE_LOCK, 1); - WREG32(D1CRTC_CONTROL, 0); - WREG32(D2CRTC_CONTROL, 0); - WREG32(D1CRTC_UPDATE_LOCK, 0); - WREG32(D2CRTC_UPDATE_LOCK, 0); - - mdelay(1); + rv515_mc_stop(rdev, &save); if (r600_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "[drm] MC not idle !\n"); + dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); } - /* Lockout access through VGA aperture*/ WREG32(VGA_HDP_CONTROL, VGA_MEMORY_DISABLE); - /* Update configuration */ - WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, rdev->mc.vram_start >> 12); - WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, (rdev->mc.vram_end - 1) >> 12); + if (rdev->flags & RADEON_IS_AGP) { + if (rdev->mc.vram_start < rdev->mc.gtt_start) { + /* VRAM before AGP */ + WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, + rdev->mc.vram_start >> 12); + WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, + rdev->mc.gtt_end >> 12); + } else { + /* VRAM after AGP */ + WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, + rdev->mc.gtt_start >> 12); + WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, + rdev->mc.vram_end >> 12); + } + } else { + WREG32(MC_VM_SYSTEM_APERTURE_LOW_ADDR, + rdev->mc.vram_start >> 12); + WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR, + rdev->mc.vram_end >> 12); + } WREG32(MC_VM_SYSTEM_APERTURE_DEFAULT_ADDR, 0); - tmp = (((rdev->mc.vram_end - 1) >> 24) & 0xFFFF) << 16; + tmp = ((rdev->mc.vram_end >> 24) & 0xFFFF) << 16; tmp |= ((rdev->mc.vram_start >> 24) & 0xFFFF); WREG32(MC_VM_FB_LOCATION, tmp); WREG32(HDP_NONSURFACE_BASE, (rdev->mc.vram_start >> 8)); WREG32(HDP_NONSURFACE_INFO, (2 << 7)); WREG32(HDP_NONSURFACE_SIZE, (rdev->mc.mc_vram_size - 1) | 0x3FF); if (rdev->flags & RADEON_IS_AGP) { - WREG32(MC_VM_AGP_TOP, (rdev->mc.gtt_end - 1) >> 16); + WREG32(MC_VM_AGP_TOP, rdev->mc.gtt_end >> 16); WREG32(MC_VM_AGP_BOT, rdev->mc.gtt_start >> 16); WREG32(MC_VM_AGP_BASE, rdev->mc.agp_base >> 22); } else { @@ -204,31 +212,10 @@ static void rv770_mc_resume(struct radeon_device *rdev) WREG32(MC_VM_AGP_TOP, 0x0FFFFFFF); WREG32(MC_VM_AGP_BOT, 0x0FFFFFFF); } - WREG32(D1GRPH_PRIMARY_SURFACE_ADDRESS, new_d1grph_primary); - WREG32(D1GRPH_SECONDARY_SURFACE_ADDRESS, new_d1grph_secondary); - WREG32(D2GRPH_PRIMARY_SURFACE_ADDRESS, new_d2grph_primary); - WREG32(D2GRPH_SECONDARY_SURFACE_ADDRESS, new_d2grph_secondary); - WREG32(VGA_MEMORY_BASE_ADDRESS, rdev->mc.vram_start); - - /* Unlock host access */ - WREG32(VGA_HDP_CONTROL, vga_hdp_control); - - mdelay(1); if (r600_mc_wait_for_idle(rdev)) { - printk(KERN_WARNING "[drm] MC not idle !\n"); + dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); } - - /* Restore video state */ - WREG32(D1CRTC_UPDATE_LOCK, 1); - WREG32(D2CRTC_UPDATE_LOCK, 1); - WREG32(D1CRTC_CONTROL, d1crtc_control); - WREG32(D2CRTC_CONTROL, d2crtc_control); - WREG32(D1CRTC_UPDATE_LOCK, 0); - WREG32(D2CRTC_UPDATE_LOCK, 0); - WREG32(D1VGA_CONTROL, d1vga_control); - WREG32(D2VGA_CONTROL, d2vga_control); - WREG32(VGA_RENDER_CONTROL, vga_render_control); - + rv515_mc_resume(rdev, &save); /* we need to own VRAM, so turn off the VGA renderer here * to stop it overwriting our objects */ rv515_vga_render_disable(rdev); @@ -542,11 +529,11 @@ static void rv770_gpu_init(struct radeon_device *rdev) if (rdev->family == CHIP_RV770) gb_tiling_config |= BANK_TILING(1); else - gb_tiling_config |= BANK_TILING((mc_arb_ramcfg & NOOFBANK_SHIFT) >> NOOFBANK_MASK); + gb_tiling_config |= BANK_TILING((mc_arb_ramcfg & NOOFBANK_MASK) >> NOOFBANK_SHIFT); gb_tiling_config |= GROUP_SIZE(0); - if (((mc_arb_ramcfg & NOOFROWS_MASK) & NOOFROWS_SHIFT) > 3) { + if (((mc_arb_ramcfg & NOOFROWS_MASK) >> NOOFROWS_SHIFT) > 3) { gb_tiling_config |= ROW_TILING(3); gb_tiling_config |= SAMPLE_SPLIT(3); } else { @@ -592,14 +579,14 @@ static void rv770_gpu_init(struct radeon_device *rdev) /* set HW defaults for 3D engine */ WREG32(CP_QUEUE_THRESHOLDS, (ROQ_IB1_START(0x16) | - ROQ_IB2_START(0x2b))); + ROQ_IB2_START(0x2b))); WREG32(CP_MEQ_THRESHOLDS, STQ_SPLIT(0x30)); WREG32(TA_CNTL_AUX, (DISABLE_CUBE_ANISO | - SYNC_GRADIENT | - SYNC_WALKER | - SYNC_ALIGNER)); + SYNC_GRADIENT | + SYNC_WALKER | + SYNC_ALIGNER)); sx_debug_1 = RREG32(SX_DEBUG_1); sx_debug_1 |= ENABLE_NEW_SMX_ADDRESS; @@ -611,9 +598,9 @@ static void rv770_gpu_init(struct radeon_device *rdev) WREG32(SMX_DC_CTL0, smx_dc_ctl0); WREG32(SMX_EVENT_CTL, (ES_FLUSH_CTL(4) | - GS_FLUSH_CTL(4) | - ACK_FLUSH_CTL(3) | - SYNC_FLUSH_CTL)); + GS_FLUSH_CTL(4) | + ACK_FLUSH_CTL(3) | + SYNC_FLUSH_CTL)); if (rdev->family == CHIP_RV770) WREG32(DB_DEBUG3, DB_CLK_OFF_DELAY(0x1f)); @@ -624,12 +611,12 @@ static void rv770_gpu_init(struct radeon_device *rdev) } WREG32(SX_EXPORT_BUFFER_SIZES, (COLOR_BUFFER_SIZE((rdev->config.rv770.sx_max_export_size / 4) - 1) | - POSITION_BUFFER_SIZE((rdev->config.rv770.sx_max_export_pos_size / 4) - 1) | - SMX_BUFFER_SIZE((rdev->config.rv770.sx_max_export_smx_size / 4) - 1))); + POSITION_BUFFER_SIZE((rdev->config.rv770.sx_max_export_pos_size / 4) - 1) | + SMX_BUFFER_SIZE((rdev->config.rv770.sx_max_export_smx_size / 4) - 1))); WREG32(PA_SC_FIFO_SIZE, (SC_PRIM_FIFO_SIZE(rdev->config.rv770.sc_prim_fifo_size) | - SC_HIZ_TILE_FIFO_SIZE(rdev->config.rv770.sc_hiz_tile_fifo_size) | - SC_EARLYZ_TILE_FIFO_SIZE(rdev->config.rv770.sc_earlyz_tile_fifo_fize))); + SC_HIZ_TILE_FIFO_SIZE(rdev->config.rv770.sc_hiz_tile_fifo_size) | + SC_EARLYZ_TILE_FIFO_SIZE(rdev->config.rv770.sc_earlyz_tile_fifo_fize))); WREG32(PA_SC_MULTI_CHIP_CNTL, 0); @@ -787,14 +774,36 @@ int rv770_mc_init(struct radeon_device *rdev) { fixed20_12 a; u32 tmp; + int chansize, numchan; int r; /* Get VRAM informations */ - /* FIXME: Don't know how to determine vram width, need to check - * vram_width usage - */ - rdev->mc.vram_width = 128; rdev->mc.vram_is_ddr = true; + tmp = RREG32(MC_ARB_RAMCFG); + if (tmp & CHANSIZE_OVERRIDE) { + chansize = 16; + } else if (tmp & CHANSIZE_MASK) { + chansize = 64; + } else { + chansize = 32; + } + tmp = RREG32(MC_SHARED_CHMAP); + switch ((tmp & NOOFCHAN_MASK) >> NOOFCHAN_SHIFT) { + case 0: + default: + numchan = 1; + break; + case 1: + numchan = 2; + break; + case 2: + numchan = 4; + break; + case 3: + numchan = 8; + break; + } + rdev->mc.vram_width = numchan * chansize; /* Could aper size report 0 ? */ rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0); rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0); @@ -840,9 +849,9 @@ int rv770_mc_init(struct radeon_device *rdev) rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024; } rdev->mc.vram_start = rdev->mc.vram_location; - rdev->mc.vram_end = rdev->mc.vram_location + rdev->mc.mc_vram_size; + rdev->mc.vram_end = rdev->mc.vram_location + rdev->mc.mc_vram_size - 1; rdev->mc.gtt_start = rdev->mc.gtt_location; - rdev->mc.gtt_end = rdev->mc.gtt_location + rdev->mc.gtt_size; + rdev->mc.gtt_end = rdev->mc.gtt_location + rdev->mc.gtt_size - 1; /* FIXME: we should enforce default clock in case GPU is not in * default setup */ @@ -861,11 +870,14 @@ static int rv770_startup(struct radeon_device *rdev) { int r; - radeon_gpu_reset(rdev); - rv770_mc_resume(rdev); - r = rv770_pcie_gart_enable(rdev); - if (r) - return r; + rv770_mc_program(rdev); + if (rdev->flags & RADEON_IS_AGP) { + rv770_agp_enable(rdev); + } else { + r = rv770_pcie_gart_enable(rdev); + if (r) + return r; + } rv770_gpu_init(rdev); r = radeon_object_pin(rdev->r600_blit.shader_obj, RADEON_GEM_DOMAIN_VRAM, @@ -884,9 +896,8 @@ static int rv770_startup(struct radeon_device *rdev) r = r600_cp_resume(rdev); if (r) return r; - r = r600_wb_init(rdev); - if (r) - return r; + /* write back buffer are not vital so don't worry about failure */ + r600_wb_enable(rdev); return 0; } @@ -894,15 +905,12 @@ int rv770_resume(struct radeon_device *rdev) { int r; - if (radeon_gpu_reset(rdev)) { - /* FIXME: what do we want to do here ? */ - } + /* Do not reset GPU before posting, on rv770 hw unlike on r500 hw, + * posting will perform necessary task to bring back GPU into good + * shape. + */ /* post card */ - if (rdev->is_atom_bios) { - atom_asic_init(rdev->mode_info.atom_context); - } else { - radeon_combios_asic_init(rdev->ddev); - } + atom_asic_init(rdev->mode_info.atom_context); /* Initialize clocks */ r = radeon_clocks_init(rdev); if (r) { @@ -915,7 +923,7 @@ int rv770_resume(struct radeon_device *rdev) return r; } - r = radeon_ib_test(rdev); + r = r600_ib_test(rdev); if (r) { DRM_ERROR("radeon: failled testing IB (%d).\n", r); return r; @@ -929,8 +937,8 @@ int rv770_suspend(struct radeon_device *rdev) /* FIXME: we should wait for ring to be empty */ r700_cp_stop(rdev); rdev->cp.ready = false; + r600_wb_disable(rdev); rv770_pcie_gart_disable(rdev); - /* unpin shaders bo */ radeon_object_unpin(rdev->r600_blit.shader_obj); return 0; @@ -946,7 +954,6 @@ int rv770_init(struct radeon_device *rdev) { int r; - rdev->new_init_path = true; r = radeon_dummy_page_init(rdev); if (r) return r; @@ -960,8 +967,10 @@ int rv770_init(struct radeon_device *rdev) return -EINVAL; } /* Must be an ATOMBIOS */ - if (!rdev->is_atom_bios) + if (!rdev->is_atom_bios) { + dev_err(rdev->dev, "Expecting atombios for R600 GPU\n"); return -EINVAL; + } r = radeon_atombios_init(rdev); if (r) return r; @@ -974,24 +983,20 @@ int rv770_init(struct radeon_device *rdev) r600_scratch_init(rdev); /* Initialize surface registers */ radeon_surface_init(rdev); + /* Initialize clocks */ radeon_get_clock_info(rdev->ddev); r = radeon_clocks_init(rdev); if (r) return r; + /* Initialize power management */ + radeon_pm_init(rdev); /* Fence driver */ r = radeon_fence_driver_init(rdev); if (r) return r; r = rv770_mc_init(rdev); - if (r) { - if (rdev->flags & RADEON_IS_AGP) { - /* Retry with disabling AGP */ - rv770_fini(rdev); - rdev->flags &= ~RADEON_IS_AGP; - return rv770_init(rdev); - } + if (r) return r; - } /* Memory manager */ r = radeon_object_init(rdev); if (r) @@ -1020,12 +1025,10 @@ int rv770_init(struct radeon_device *rdev) r = rv770_startup(rdev); if (r) { - if (rdev->flags & RADEON_IS_AGP) { - /* Retry with disabling AGP */ - rv770_fini(rdev); - rdev->flags &= ~RADEON_IS_AGP; - return rv770_init(rdev); - } + rv770_suspend(rdev); + r600_wb_fini(rdev); + radeon_ring_fini(rdev); + rv770_pcie_gart_fini(rdev); rdev->accel_working = false; } if (rdev->accel_working) { @@ -1034,7 +1037,7 @@ int rv770_init(struct radeon_device *rdev) DRM_ERROR("radeon: failled initializing IB pool (%d).\n", r); rdev->accel_working = false; } - r = radeon_ib_test(rdev); + r = r600_ib_test(rdev); if (r) { DRM_ERROR("radeon: failled testing IB (%d).\n", r); rdev->accel_working = false; @@ -1049,20 +1052,15 @@ void rv770_fini(struct radeon_device *rdev) r600_blit_fini(rdev); radeon_ring_fini(rdev); + r600_wb_fini(rdev); rv770_pcie_gart_fini(rdev); radeon_gem_fini(rdev); radeon_fence_driver_fini(rdev); radeon_clocks_fini(rdev); -#if __OS_HAS_AGP if (rdev->flags & RADEON_IS_AGP) radeon_agp_fini(rdev); -#endif radeon_object_fini(rdev); - if (rdev->is_atom_bios) { - radeon_atombios_fini(rdev); - } else { - radeon_combios_fini(rdev); - } + radeon_atombios_fini(rdev); kfree(rdev->bios); rdev->bios = NULL; radeon_dummy_page_fini(rdev); diff --git a/drivers/gpu/drm/radeon/rv770d.h b/drivers/gpu/drm/radeon/rv770d.h index 4b9c3d6396ff..a1367ab6f261 100644 --- a/drivers/gpu/drm/radeon/rv770d.h +++ b/drivers/gpu/drm/radeon/rv770d.h @@ -129,6 +129,10 @@ #define HDP_REG_COHERENCY_FLUSH_CNTL 0x54A0 #define HDP_TILING_CONFIG 0x2F3C +#define MC_SHARED_CHMAP 0x2004 +#define NOOFCHAN_SHIFT 12 +#define NOOFCHAN_MASK 0x00003000 + #define MC_ARB_RAMCFG 0x2760 #define NOOFBANK_SHIFT 0 #define NOOFBANK_MASK 0x00000003 @@ -142,6 +146,7 @@ #define CHANSIZE_MASK 0x00000100 #define BURSTLENGTH_SHIFT 9 #define BURSTLENGTH_MASK 0x00000200 +#define CHANSIZE_OVERRIDE (1 << 11) #define MC_VM_AGP_TOP 0x2028 #define MC_VM_AGP_BOT 0x202C #define MC_VM_AGP_BASE 0x2030 diff --git a/drivers/gpu/drm/ttm/ttm_global.c b/drivers/gpu/drm/ttm/ttm_global.c index 541744d00d3e..b17007178a36 100644 --- a/drivers/gpu/drm/ttm/ttm_global.c +++ b/drivers/gpu/drm/ttm/ttm_global.c @@ -82,8 +82,8 @@ int ttm_global_item_ref(struct ttm_global_reference *ref) if (unlikely(ret != 0)) goto out_err; - ++item->refcount; } + ++item->refcount; ref->object = item->object; object = item->object; mutex_unlock(&item->mutex); diff --git a/drivers/gpu/drm/ttm/ttm_tt.c b/drivers/gpu/drm/ttm/ttm_tt.c index a55ee1a56c16..7bcb89f39ce8 100644 --- a/drivers/gpu/drm/ttm/ttm_tt.c +++ b/drivers/gpu/drm/ttm/ttm_tt.c @@ -279,6 +279,7 @@ int ttm_tt_set_placement_caching(struct ttm_tt *ttm, uint32_t placement) return ttm_tt_set_caching(ttm, state); } +EXPORT_SYMBOL(ttm_tt_set_placement_caching); static void ttm_tt_free_alloced_pages(struct ttm_tt *ttm) { diff --git a/drivers/hid/hid-core.c b/drivers/hid/hid-core.c index be34d32906bd..7d05c4bb201e 100644 --- a/drivers/hid/hid-core.c +++ b/drivers/hid/hid-core.c @@ -1066,7 +1066,7 @@ EXPORT_SYMBOL_GPL(hid_report_raw_event); * @type: HID report type (HID_*_REPORT) * @data: report contents * @size: size of data parameter - * @interrupt: called from atomic? + * @interrupt: distinguish between interrupt and control transfers * * This is data entry for lower layers. */ diff --git a/drivers/hid/hid-twinhan.c b/drivers/hid/hid-twinhan.c index b05f602c051e..c40afc57fc8f 100644 --- a/drivers/hid/hid-twinhan.c +++ b/drivers/hid/hid-twinhan.c @@ -132,12 +132,12 @@ static struct hid_driver twinhan_driver = { .input_mapping = twinhan_input_mapping, }; -static int twinhan_init(void) +static int __init twinhan_init(void) { return hid_register_driver(&twinhan_driver); } -static void twinhan_exit(void) +static void __exit twinhan_exit(void) { hid_unregister_driver(&twinhan_driver); } diff --git a/drivers/hid/hidraw.c b/drivers/hid/hidraw.c index ba05275e5104..cdd136942bca 100644 --- a/drivers/hid/hidraw.c +++ b/drivers/hid/hidraw.c @@ -48,10 +48,9 @@ static ssize_t hidraw_read(struct file *file, char __user *buffer, size_t count, char *report; DECLARE_WAITQUEUE(wait, current); - while (ret == 0) { - - mutex_lock(&list->read_mutex); + mutex_lock(&list->read_mutex); + while (ret == 0) { if (list->head == list->tail) { add_wait_queue(&list->hidraw->wait, &wait); set_current_state(TASK_INTERRUPTIBLE); diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig index 6857560144bd..700e93adeb33 100644 --- a/drivers/hwmon/Kconfig +++ b/drivers/hwmon/Kconfig @@ -675,7 +675,7 @@ config SENSORS_SHT15 config SENSORS_S3C tristate "S3C24XX/S3C64XX Inbuilt ADC" - depends on ARCH_S3C2410 || ARCH_S3C64XX + depends on ARCH_S3C2410 help If you say yes here you get support for the on-board ADCs of the Samsung S3C24XX or S3C64XX series of SoC diff --git a/drivers/hwmon/adt7475.c b/drivers/hwmon/adt7475.c index d39877a7da63..b5a95193c694 100644 --- a/drivers/hwmon/adt7475.c +++ b/drivers/hwmon/adt7475.c @@ -350,8 +350,7 @@ static ssize_t show_temp(struct device *dev, struct device_attribute *attr, case FAULT: /* Note - only for remote1 and remote2 */ - out = data->alarms & (sattr->index ? 0x8000 : 0x4000); - out = out ? 0 : 1; + out = !!(data->alarms & (sattr->index ? 0x8000 : 0x4000)); break; default: @@ -863,7 +862,7 @@ static SENSOR_DEVICE_ATTR_2(pwm1_freq, S_IRUGO | S_IWUSR, show_pwmfreq, set_pwmfreq, INPUT, 0); static SENSOR_DEVICE_ATTR_2(pwm1_enable, S_IRUGO | S_IWUSR, show_pwmctrl, set_pwmctrl, INPUT, 0); -static SENSOR_DEVICE_ATTR_2(pwm1_auto_channel_temp, S_IRUGO | S_IWUSR, +static SENSOR_DEVICE_ATTR_2(pwm1_auto_channels_temp, S_IRUGO | S_IWUSR, show_pwmchan, set_pwmchan, INPUT, 0); static SENSOR_DEVICE_ATTR_2(pwm1_auto_point1_pwm, S_IRUGO | S_IWUSR, show_pwm, set_pwm, MIN, 0); @@ -875,7 +874,7 @@ static SENSOR_DEVICE_ATTR_2(pwm2_freq, S_IRUGO | S_IWUSR, show_pwmfreq, set_pwmfreq, INPUT, 1); static SENSOR_DEVICE_ATTR_2(pwm2_enable, S_IRUGO | S_IWUSR, show_pwmctrl, set_pwmctrl, INPUT, 1); -static SENSOR_DEVICE_ATTR_2(pwm2_auto_channel_temp, S_IRUGO | S_IWUSR, +static SENSOR_DEVICE_ATTR_2(pwm2_auto_channels_temp, S_IRUGO | S_IWUSR, show_pwmchan, set_pwmchan, INPUT, 1); static SENSOR_DEVICE_ATTR_2(pwm2_auto_point1_pwm, S_IRUGO | S_IWUSR, show_pwm, set_pwm, MIN, 1); @@ -887,7 +886,7 @@ static SENSOR_DEVICE_ATTR_2(pwm3_freq, S_IRUGO | S_IWUSR, show_pwmfreq, set_pwmfreq, INPUT, 2); static SENSOR_DEVICE_ATTR_2(pwm3_enable, S_IRUGO | S_IWUSR, show_pwmctrl, set_pwmctrl, INPUT, 2); -static SENSOR_DEVICE_ATTR_2(pwm3_auto_channel_temp, S_IRUGO | S_IWUSR, +static SENSOR_DEVICE_ATTR_2(pwm3_auto_channels_temp, S_IRUGO | S_IWUSR, show_pwmchan, set_pwmchan, INPUT, 2); static SENSOR_DEVICE_ATTR_2(pwm3_auto_point1_pwm, S_IRUGO | S_IWUSR, show_pwm, set_pwm, MIN, 2); @@ -947,19 +946,19 @@ static struct attribute *adt7475_attrs[] = { &sensor_dev_attr_pwm1.dev_attr.attr, &sensor_dev_attr_pwm1_freq.dev_attr.attr, &sensor_dev_attr_pwm1_enable.dev_attr.attr, - &sensor_dev_attr_pwm1_auto_channel_temp.dev_attr.attr, + &sensor_dev_attr_pwm1_auto_channels_temp.dev_attr.attr, &sensor_dev_attr_pwm1_auto_point1_pwm.dev_attr.attr, &sensor_dev_attr_pwm1_auto_point2_pwm.dev_attr.attr, &sensor_dev_attr_pwm2.dev_attr.attr, &sensor_dev_attr_pwm2_freq.dev_attr.attr, &sensor_dev_attr_pwm2_enable.dev_attr.attr, - &sensor_dev_attr_pwm2_auto_channel_temp.dev_attr.attr, + &sensor_dev_attr_pwm2_auto_channels_temp.dev_attr.attr, &sensor_dev_attr_pwm2_auto_point1_pwm.dev_attr.attr, &sensor_dev_attr_pwm2_auto_point2_pwm.dev_attr.attr, &sensor_dev_attr_pwm3.dev_attr.attr, &sensor_dev_attr_pwm3_freq.dev_attr.attr, &sensor_dev_attr_pwm3_enable.dev_attr.attr, - &sensor_dev_attr_pwm3_auto_channel_temp.dev_attr.attr, + &sensor_dev_attr_pwm3_auto_channels_temp.dev_attr.attr, &sensor_dev_attr_pwm3_auto_point1_pwm.dev_attr.attr, &sensor_dev_attr_pwm3_auto_point2_pwm.dev_attr.attr, NULL, @@ -1152,7 +1151,7 @@ static struct adt7475_data *adt7475_update_device(struct device *dev) } /* Limits and settings, should never change update every 60 seconds */ - if (time_after(jiffies, data->limits_updated + HZ * 2) || + if (time_after(jiffies, data->limits_updated + HZ * 60) || !data->valid) { data->config5 = adt7475_read(REG_CONFIG5); diff --git a/drivers/hwmon/asus_atk0110.c b/drivers/hwmon/asus_atk0110.c index fe4fa29c9219..5a3ee00c0e7d 100644 --- a/drivers/hwmon/asus_atk0110.c +++ b/drivers/hwmon/asus_atk0110.c @@ -35,18 +35,22 @@ #define METHOD_OLD_ENUM_FAN "FSIF" #define ATK_MUX_HWMON 0x00000006ULL +#define ATK_MUX_MGMT 0x00000011ULL #define ATK_CLASS_MASK 0xff000000ULL #define ATK_CLASS_FREQ_CTL 0x03000000ULL #define ATK_CLASS_FAN_CTL 0x04000000ULL #define ATK_CLASS_HWMON 0x06000000ULL +#define ATK_CLASS_MGMT 0x11000000ULL #define ATK_TYPE_MASK 0x00ff0000ULL #define HWMON_TYPE_VOLT 0x00020000ULL #define HWMON_TYPE_TEMP 0x00030000ULL #define HWMON_TYPE_FAN 0x00040000ULL -#define HWMON_SENSOR_ID_MASK 0x0000ffffULL +#define ATK_ELEMENT_ID_MASK 0x0000ffffULL + +#define ATK_EC_ID 0x11060004ULL enum atk_pack_member { HWMON_PACK_FLAGS, @@ -89,6 +93,9 @@ struct atk_data { /* new inteface */ acpi_handle enumerate_handle; acpi_handle read_handle; + acpi_handle write_handle; + + bool disable_ec; int voltage_count; int temperature_count; @@ -129,9 +136,22 @@ struct atk_sensor_data { char const *acpi_name; }; -struct atk_acpi_buffer_u64 { - union acpi_object buf; - u64 value; +/* Return buffer format: + * [0-3] "value" is valid flag + * [4-7] value + * [8- ] unknown stuff on newer mobos + */ +struct atk_acpi_ret_buffer { + u32 flags; + u32 value; + u8 data[]; +}; + +/* Input buffer used for GITM and SITM methods */ +struct atk_acpi_input_buf { + u32 id; + u32 param1; + u32 param2; }; static int atk_add(struct acpi_device *device); @@ -439,52 +459,147 @@ static int atk_read_value_old(struct atk_sensor_data *sensor, u64 *value) return 0; } -static int atk_read_value_new(struct atk_sensor_data *sensor, u64 *value) +static union acpi_object *atk_ggrp(struct atk_data *data, u16 mux) { - struct atk_data *data = sensor->data; struct device *dev = &data->acpi_dev->dev; + struct acpi_buffer buf; + acpi_status ret; struct acpi_object_list params; - struct acpi_buffer ret; union acpi_object id; - struct atk_acpi_buffer_u64 tmp; - acpi_status status; + union acpi_object *pack; id.type = ACPI_TYPE_INTEGER; - id.integer.value = sensor->id; - + id.integer.value = mux; params.count = 1; params.pointer = &id; - tmp.buf.type = ACPI_TYPE_BUFFER; - tmp.buf.buffer.pointer = (u8 *)&tmp.value; - tmp.buf.buffer.length = sizeof(u64); - ret.length = sizeof(tmp); - ret.pointer = &tmp; + buf.length = ACPI_ALLOCATE_BUFFER; + ret = acpi_evaluate_object(data->enumerate_handle, NULL, ¶ms, &buf); + if (ret != AE_OK) { + dev_err(dev, "GGRP[%#x] ACPI exception: %s\n", mux, + acpi_format_exception(ret)); + return ERR_PTR(-EIO); + } + pack = buf.pointer; + if (pack->type != ACPI_TYPE_PACKAGE) { + /* Execution was successful, but the id was not found */ + ACPI_FREE(pack); + return ERR_PTR(-ENOENT); + } + + if (pack->package.count < 1) { + dev_err(dev, "GGRP[%#x] package is too small\n", mux); + ACPI_FREE(pack); + return ERR_PTR(-EIO); + } + return pack; +} + +static union acpi_object *atk_gitm(struct atk_data *data, u64 id) +{ + struct device *dev = &data->acpi_dev->dev; + struct atk_acpi_input_buf buf; + union acpi_object tmp; + struct acpi_object_list params; + struct acpi_buffer ret; + union acpi_object *obj; + acpi_status status; + + buf.id = id; + buf.param1 = 0; + buf.param2 = 0; + tmp.type = ACPI_TYPE_BUFFER; + tmp.buffer.pointer = (u8 *)&buf; + tmp.buffer.length = sizeof(buf); + + params.count = 1; + params.pointer = (void *)&tmp; + + ret.length = ACPI_ALLOCATE_BUFFER; status = acpi_evaluate_object_typed(data->read_handle, NULL, ¶ms, &ret, ACPI_TYPE_BUFFER); if (status != AE_OK) { - dev_warn(dev, "%s: ACPI exception: %s\n", __func__, + dev_warn(dev, "GITM[%#llx] ACPI exception: %s\n", id, acpi_format_exception(status)); - return -EIO; + return ERR_PTR(-EIO); + } + obj = ret.pointer; + + /* Sanity check */ + if (obj->buffer.length < 8) { + dev_warn(dev, "Unexpected ASBF length: %u\n", + obj->buffer.length); + ACPI_FREE(obj); + return ERR_PTR(-EIO); } + return obj; +} - /* Return buffer format: - * [0-3] "value" is valid flag - * [4-7] value - */ - if (!(tmp.value & 0xffffffff)) { +static union acpi_object *atk_sitm(struct atk_data *data, + struct atk_acpi_input_buf *buf) +{ + struct device *dev = &data->acpi_dev->dev; + struct acpi_object_list params; + union acpi_object tmp; + struct acpi_buffer ret; + union acpi_object *obj; + acpi_status status; + + tmp.type = ACPI_TYPE_BUFFER; + tmp.buffer.pointer = (u8 *)buf; + tmp.buffer.length = sizeof(*buf); + + params.count = 1; + params.pointer = &tmp; + + ret.length = ACPI_ALLOCATE_BUFFER; + status = acpi_evaluate_object_typed(data->write_handle, NULL, ¶ms, + &ret, ACPI_TYPE_BUFFER); + if (status != AE_OK) { + dev_warn(dev, "SITM[%#x] ACPI exception: %s\n", buf->id, + acpi_format_exception(status)); + return ERR_PTR(-EIO); + } + obj = ret.pointer; + + /* Sanity check */ + if (obj->buffer.length < 8) { + dev_warn(dev, "Unexpected ASBF length: %u\n", + obj->buffer.length); + ACPI_FREE(obj); + return ERR_PTR(-EIO); + } + return obj; +} + +static int atk_read_value_new(struct atk_sensor_data *sensor, u64 *value) +{ + struct atk_data *data = sensor->data; + struct device *dev = &data->acpi_dev->dev; + union acpi_object *obj; + struct atk_acpi_ret_buffer *buf; + int err = 0; + + obj = atk_gitm(data, sensor->id); + if (IS_ERR(obj)) + return PTR_ERR(obj); + + buf = (struct atk_acpi_ret_buffer *)obj->buffer.pointer; + if (buf->flags == 0) { /* The reading is not valid, possible causes: * - sensor failure * - enumeration was FUBAR (and we didn't notice) */ - dev_info(dev, "Failure: %#llx\n", tmp.value); - return -EIO; + dev_warn(dev, "Read failed, sensor = %#llx\n", sensor->id); + err = -EIO; + goto out; } - *value = (tmp.value & 0xffffffff00000000ULL) >> 32; - - return 0; + *value = buf->value; +out: + ACPI_FREE(obj); + return err; } static int atk_read_value(struct atk_sensor_data *sensor, u64 *value) @@ -713,43 +828,141 @@ cleanup: return ret; } -static int atk_enumerate_new_hwmon(struct atk_data *data) +static int atk_ec_present(struct atk_data *data) { struct device *dev = &data->acpi_dev->dev; - struct acpi_buffer buf; - acpi_status ret; - struct acpi_object_list params; - union acpi_object id; union acpi_object *pack; - int err; + union acpi_object *ec; + int ret; int i; - dev_dbg(dev, "Enumerating hwmon sensors\n"); + pack = atk_ggrp(data, ATK_MUX_MGMT); + if (IS_ERR(pack)) { + if (PTR_ERR(pack) == -ENOENT) { + /* The MGMT class does not exists - that's ok */ + dev_dbg(dev, "Class %#llx not found\n", ATK_MUX_MGMT); + return 0; + } + return PTR_ERR(pack); + } - id.type = ACPI_TYPE_INTEGER; - id.integer.value = ATK_MUX_HWMON; - params.count = 1; - params.pointer = &id; + /* Search the EC */ + ec = NULL; + for (i = 0; i < pack->package.count; i++) { + union acpi_object *obj = &pack->package.elements[i]; + union acpi_object *id; - buf.length = ACPI_ALLOCATE_BUFFER; - ret = acpi_evaluate_object_typed(data->enumerate_handle, NULL, ¶ms, - &buf, ACPI_TYPE_PACKAGE); - if (ret != AE_OK) { - dev_warn(dev, METHOD_ENUMERATE ": ACPI exception: %s\n", - acpi_format_exception(ret)); - return -ENODEV; + if (obj->type != ACPI_TYPE_PACKAGE) + continue; + + id = &obj->package.elements[0]; + if (id->type != ACPI_TYPE_INTEGER) + continue; + + if (id->integer.value == ATK_EC_ID) { + ec = obj; + break; + } } - /* Result must be a package */ - pack = buf.pointer; + ret = (ec != NULL); + if (!ret) + /* The system has no EC */ + dev_dbg(dev, "EC not found\n"); - if (pack->package.count < 1) { - dev_dbg(dev, "%s: hwmon package is too small: %d\n", __func__, - pack->package.count); - err = -EINVAL; - goto out; + ACPI_FREE(pack); + return ret; +} + +static int atk_ec_enabled(struct atk_data *data) +{ + struct device *dev = &data->acpi_dev->dev; + union acpi_object *obj; + struct atk_acpi_ret_buffer *buf; + int err; + + obj = atk_gitm(data, ATK_EC_ID); + if (IS_ERR(obj)) { + dev_err(dev, "Unable to query EC status\n"); + return PTR_ERR(obj); + } + buf = (struct atk_acpi_ret_buffer *)obj->buffer.pointer; + + if (buf->flags == 0) { + dev_err(dev, "Unable to query EC status\n"); + err = -EIO; + } else { + err = (buf->value != 0); + dev_dbg(dev, "EC is %sabled\n", + err ? "en" : "dis"); + } + + ACPI_FREE(obj); + return err; +} + +static int atk_ec_ctl(struct atk_data *data, int enable) +{ + struct device *dev = &data->acpi_dev->dev; + union acpi_object *obj; + struct atk_acpi_input_buf sitm; + struct atk_acpi_ret_buffer *ec_ret; + int err = 0; + + sitm.id = ATK_EC_ID; + sitm.param1 = enable; + sitm.param2 = 0; + + obj = atk_sitm(data, &sitm); + if (IS_ERR(obj)) { + dev_err(dev, "Failed to %sable the EC\n", + enable ? "en" : "dis"); + return PTR_ERR(obj); + } + ec_ret = (struct atk_acpi_ret_buffer *)obj->buffer.pointer; + if (ec_ret->flags == 0) { + dev_err(dev, "Failed to %sable the EC\n", + enable ? "en" : "dis"); + err = -EIO; + } else { + dev_info(dev, "EC %sabled\n", + enable ? "en" : "dis"); + } + + ACPI_FREE(obj); + return err; +} + +static int atk_enumerate_new_hwmon(struct atk_data *data) +{ + struct device *dev = &data->acpi_dev->dev; + union acpi_object *pack; + int err; + int i; + + err = atk_ec_present(data); + if (err < 0) + return err; + if (err) { + err = atk_ec_enabled(data); + if (err < 0) + return err; + /* If the EC was disabled we will disable it again on unload */ + data->disable_ec = err; + + err = atk_ec_ctl(data, 1); + if (err) { + data->disable_ec = false; + return err; + } } + dev_dbg(dev, "Enumerating hwmon sensors\n"); + + pack = atk_ggrp(data, ATK_MUX_HWMON); + if (IS_ERR(pack)) + return PTR_ERR(pack); + for (i = 0; i < pack->package.count; i++) { union acpi_object *obj = &pack->package.elements[i]; @@ -758,8 +971,7 @@ static int atk_enumerate_new_hwmon(struct atk_data *data) err = data->voltage_count + data->temperature_count + data->fan_count; -out: - ACPI_FREE(buf.pointer); + ACPI_FREE(pack); return err; } @@ -895,6 +1107,15 @@ static int atk_check_new_if(struct atk_data *data) } data->read_handle = ret; + /* De-multiplexer (write) */ + status = acpi_get_handle(data->atk_handle, METHOD_WRITE, &ret); + if (status != AE_OK) { + dev_dbg(dev, "method " METHOD_READ " not found: %s\n", + acpi_format_exception(status)); + return -ENODEV; + } + data->write_handle = ret; + return 0; } @@ -915,6 +1136,7 @@ static int atk_add(struct acpi_device *device) data->acpi_dev = device; data->atk_handle = device->handle; INIT_LIST_HEAD(&data->sensor_list); + data->disable_ec = false; buf.length = ACPI_ALLOCATE_BUFFER; ret = acpi_evaluate_object_typed(data->atk_handle, BOARD_ID, NULL, @@ -973,6 +1195,8 @@ static int atk_add(struct acpi_device *device) cleanup: atk_free_sensors(data); out: + if (data->disable_ec) + atk_ec_ctl(data, 0); kfree(data); return err; } @@ -988,6 +1212,11 @@ static int atk_remove(struct acpi_device *device, int type) atk_free_sensors(data); hwmon_device_unregister(data->hwmon_dev); + if (data->disable_ec) { + if (atk_ec_ctl(data, 0)) + dev_err(&device->dev, "Failed to disable EC\n"); + } + kfree(data); return 0; diff --git a/drivers/hwmon/dme1737.c b/drivers/hwmon/dme1737.c index 2c2cb1ec94c5..27d62574284f 100644 --- a/drivers/hwmon/dme1737.c +++ b/drivers/hwmon/dme1737.c @@ -572,7 +572,7 @@ static struct dme1737_data *dme1737_update_device(struct device *dev) /* Sample register contents every 1 sec */ if (time_after(jiffies, data->last_update + HZ) || !data->valid) { - if (data->type != sch5027) { + if (data->type == dme1737) { data->vid = dme1737_read(data, DME1737_REG_VID) & 0x3f; } @@ -1621,9 +1621,6 @@ static struct attribute *dme1737_misc_attr[] = { &sensor_dev_attr_zone1_auto_point1_temp_hyst.dev_attr.attr, &sensor_dev_attr_zone2_auto_point1_temp_hyst.dev_attr.attr, &sensor_dev_attr_zone3_auto_point1_temp_hyst.dev_attr.attr, - /* Misc */ - &dev_attr_vrm.attr, - &dev_attr_cpu0_vid.attr, NULL }; @@ -1631,6 +1628,18 @@ static const struct attribute_group dme1737_misc_group = { .attrs = dme1737_misc_attr, }; +/* The following struct holds VID-related attributes. Their creation + depends on the chip type which is determined during module load. */ +static struct attribute *dme1737_vid_attr[] = { + &dev_attr_vrm.attr, + &dev_attr_cpu0_vid.attr, + NULL +}; + +static const struct attribute_group dme1737_vid_group = { + .attrs = dme1737_vid_attr, +}; + /* The following structs hold the PWM attributes, some of which are optional. * Their creation depends on the chip configuration which is determined during * module load. */ @@ -1902,6 +1911,9 @@ static void dme1737_remove_files(struct device *dev) if (data->type != sch5027) { sysfs_remove_group(&dev->kobj, &dme1737_misc_group); } + if (data->type == dme1737) { + sysfs_remove_group(&dev->kobj, &dme1737_vid_group); + } sysfs_remove_group(&dev->kobj, &dme1737_group); @@ -1933,6 +1945,13 @@ static int dme1737_create_files(struct device *dev) goto exit_remove; } + /* Create VID-related sysfs attributes */ + if ((data->type == dme1737) && + (err = sysfs_create_group(&dev->kobj, + &dme1737_vid_group))) { + goto exit_remove; + } + /* Create fan sysfs attributes */ for (ix = 0; ix < ARRAY_SIZE(dme1737_fan_group); ix++) { if (data->has_fan & (1 << ix)) { @@ -2127,7 +2146,7 @@ static int dme1737_init_device(struct device *dev) data->pwm_acz[2] = 4; /* pwm3 -> zone3 */ /* Set VRM */ - if (data->type != sch5027) { + if (data->type == dme1737) { data->vrm = vid_which_vrm(); } diff --git a/drivers/hwmon/fschmd.c b/drivers/hwmon/fschmd.c index 2a7a85a6dc36..da1b1f9488af 100644 --- a/drivers/hwmon/fschmd.c +++ b/drivers/hwmon/fschmd.c @@ -819,7 +819,7 @@ static int watchdog_release(struct inode *inode, struct file *filp) static ssize_t watchdog_write(struct file *filp, const char __user *buf, size_t count, loff_t *offset) { - size_t ret; + int ret; struct fschmd_data *data = filp->private_data; if (count) { diff --git a/drivers/hwmon/hp_accel.c b/drivers/hwmon/hp_accel.c index 6679854c85b0..be475e844c2a 100644 --- a/drivers/hwmon/hp_accel.c +++ b/drivers/hwmon/hp_accel.c @@ -197,11 +197,13 @@ static struct dmi_system_id lis3lv02d_dmi_ids[] = { AXIS_DMI_MATCH("HP2133", "HP 2133", xy_rotated_left), AXIS_DMI_MATCH("HP2140", "HP 2140", xy_swap_inverted), AXIS_DMI_MATCH("NC653x", "HP Compaq 653", xy_rotated_left_usd), - AXIS_DMI_MATCH("NC673x", "HP Compaq 673", xy_rotated_left_usd), + AXIS_DMI_MATCH("NC6730b", "HP Compaq 6730b", xy_rotated_left_usd), + AXIS_DMI_MATCH("NC6730s", "HP Compaq 6730s", xy_swap), AXIS_DMI_MATCH("NC651xx", "HP Compaq 651", xy_rotated_right), AXIS_DMI_MATCH("NC6710x", "HP Compaq 6710", xy_swap_yz_inverted), AXIS_DMI_MATCH("NC6715x", "HP Compaq 6715", y_inverted), AXIS_DMI_MATCH("NC693xx", "HP EliteBook 693", xy_rotated_right), + AXIS_DMI_MATCH("NC693xx", "HP EliteBook 853", xy_swap), /* Intel-based HP Pavilion dv5 */ AXIS_DMI_MATCH2("HPDV5_I", PRODUCT_NAME, "HP Pavilion dv5", @@ -214,6 +216,7 @@ static struct dmi_system_id lis3lv02d_dmi_ids[] = { y_inverted), AXIS_DMI_MATCH("DV7", "HP Pavilion dv7", x_inverted), AXIS_DMI_MATCH("HP8710", "HP Compaq 8710", y_inverted), + AXIS_DMI_MATCH("HDX18", "HP HDX 18", x_inverted), { NULL, } /* Laptop models without axis info (yet): * "NC6910" "HP Compaq 6910" diff --git a/drivers/hwmon/it87.c b/drivers/hwmon/it87.c index ffeb2a10e1a7..a3749cb0f181 100644 --- a/drivers/hwmon/it87.c +++ b/drivers/hwmon/it87.c @@ -1028,12 +1028,11 @@ static int __init it87_find(unsigned short *address, chip_type, *address, sio_data->revision); /* Read GPIO config and VID value from LDN 7 (GPIO) */ - if (chip_type != IT8705F_DEVID) { + if (sio_data->type != it87) { int reg; superio_select(GPIO); - if ((chip_type == it8718) || - (chip_type == it8720)) + if (sio_data->type == it8718 || sio_data->type == it8720) sio_data->vid_value = superio_inb(IT87_SIO_VID_REG); reg = superio_inb(IT87_SIO_PINX2_REG); diff --git a/drivers/hwmon/lis3lv02d_spi.c b/drivers/hwmon/lis3lv02d_spi.c index ecd739534f6a..82b16808a274 100644 --- a/drivers/hwmon/lis3lv02d_spi.c +++ b/drivers/hwmon/lis3lv02d_spi.c @@ -83,7 +83,8 @@ static int __devexit lis302dl_spi_remove(struct spi_device *spi) struct lis3lv02d *lis3 = spi_get_drvdata(spi); lis3lv02d_joystick_disable(); lis3lv02d_poweroff(lis3); - return 0; + + return lis3lv02d_remove_fs(&lis3_dev); } #ifdef CONFIG_PM diff --git a/drivers/hwmon/s3c-hwmon.c b/drivers/hwmon/s3c-hwmon.c index 3a524f2fe493..71835412529f 100644 --- a/drivers/hwmon/s3c-hwmon.c +++ b/drivers/hwmon/s3c-hwmon.c @@ -323,14 +323,21 @@ static int __devinit s3c_hwmon_probe(struct platform_device *dev) } for (i = 0; i < ARRAY_SIZE(pdata->in); i++) { - if (!pdata->in[i]) + struct s3c24xx_adc_hwmon_incfg *cfg = pdata->in[i]; + + if (!cfg) continue; - if (pdata->in[i]->mult >= 0x10000) + if (cfg->mult >= 0x10000) dev_warn(&dev->dev, "channel %d multiplier too large\n", i); + if (cfg->divider == 0) { + dev_err(&dev->dev, "channel %d divider zero\n", i); + continue; + } + ret = s3c_hwmon_create_attr(&dev->dev, pdata->in[i], &hwmon->attrs[i], i); if (ret) { diff --git a/drivers/hwmon/sht15.c b/drivers/hwmon/sht15.c index 303c02694c3c..ebe38b680ee3 100644 --- a/drivers/hwmon/sht15.c +++ b/drivers/hwmon/sht15.c @@ -30,6 +30,7 @@ #include <linux/hwmon-sysfs.h> #include <linux/mutex.h> #include <linux/platform_device.h> +#include <linux/sched.h> #include <linux/delay.h> #include <linux/jiffies.h> #include <linux/err.h> @@ -622,7 +623,12 @@ static int __devexit sht15_remove(struct platform_device *pdev) } -static struct platform_driver sht_drivers[] = { +/* + * sht_drivers simultaneously refers to __devinit and __devexit function + * which causes spurious section mismatch warning. So use __refdata to + * get rid from this. + */ +static struct platform_driver __refdata sht_drivers[] = { { .driver = { .name = "sht10", diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index 737335ff2b21..e8fe7f169e25 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -128,7 +128,7 @@ config I2C_PIIX4 ATI SB600 ATI SB700 ATI SB800 - AMD SB900 + AMD Hudson-2 Serverworks OSB4 Serverworks CSB5 Serverworks CSB6 diff --git a/drivers/i2c/busses/i2c-imx.c b/drivers/i2c/busses/i2c-imx.c index 4afba3ec2a61..e3654d683e15 100644 --- a/drivers/i2c/busses/i2c-imx.c +++ b/drivers/i2c/busses/i2c-imx.c @@ -120,19 +120,26 @@ struct imx_i2c_struct { wait_queue_head_t queue; unsigned long i2csr; unsigned int disable_delay; + int stopped; + unsigned int ifdr; /* IMX_I2C_IFDR */ }; /** Functions for IMX I2C adapter driver *************************************** *******************************************************************************/ -static int i2c_imx_bus_busy(struct imx_i2c_struct *i2c_imx) +static int i2c_imx_bus_busy(struct imx_i2c_struct *i2c_imx, int for_busy) { unsigned long orig_jiffies = jiffies; + unsigned int temp; dev_dbg(&i2c_imx->adapter.dev, "<%s>\n", __func__); - /* wait for bus not busy */ - while (readb(i2c_imx->base + IMX_I2C_I2SR) & I2SR_IBB) { + while (1) { + temp = readb(i2c_imx->base + IMX_I2C_I2SR); + if (for_busy && (temp & I2SR_IBB)) + break; + if (!for_busy && !(temp & I2SR_IBB)) + break; if (signal_pending(current)) { dev_dbg(&i2c_imx->adapter.dev, "<%s> I2C Interrupted\n", __func__); @@ -179,41 +186,62 @@ static int i2c_imx_acked(struct imx_i2c_struct *i2c_imx) return 0; } -static void i2c_imx_start(struct imx_i2c_struct *i2c_imx) +static int i2c_imx_start(struct imx_i2c_struct *i2c_imx) { unsigned int temp = 0; + int result; dev_dbg(&i2c_imx->adapter.dev, "<%s>\n", __func__); + clk_enable(i2c_imx->clk); + writeb(i2c_imx->ifdr, i2c_imx->base + IMX_I2C_IFDR); /* Enable I2C controller */ + writeb(0, i2c_imx->base + IMX_I2C_I2SR); writeb(I2CR_IEN, i2c_imx->base + IMX_I2C_I2CR); + + /* Wait controller to be stable */ + udelay(50); + /* Start I2C transaction */ temp = readb(i2c_imx->base + IMX_I2C_I2CR); temp |= I2CR_MSTA; writeb(temp, i2c_imx->base + IMX_I2C_I2CR); + result = i2c_imx_bus_busy(i2c_imx, 1); + if (result) + return result; + i2c_imx->stopped = 0; + temp |= I2CR_IIEN | I2CR_MTX | I2CR_TXAK; writeb(temp, i2c_imx->base + IMX_I2C_I2CR); + return result; } static void i2c_imx_stop(struct imx_i2c_struct *i2c_imx) { unsigned int temp = 0; - /* Stop I2C transaction */ - dev_dbg(&i2c_imx->adapter.dev, "<%s>\n", __func__); - temp = readb(i2c_imx->base + IMX_I2C_I2CR); - temp &= ~I2CR_MSTA; - writeb(temp, i2c_imx->base + IMX_I2C_I2CR); - /* setup chip registers to defaults */ - writeb(I2CR_IEN, i2c_imx->base + IMX_I2C_I2CR); - writeb(0, i2c_imx->base + IMX_I2C_I2SR); - /* - * This delay caused by an i.MXL hardware bug. - * If no (or too short) delay, no "STOP" bit will be generated. - */ - udelay(i2c_imx->disable_delay); + if (!i2c_imx->stopped) { + /* Stop I2C transaction */ + dev_dbg(&i2c_imx->adapter.dev, "<%s>\n", __func__); + temp = readb(i2c_imx->base + IMX_I2C_I2CR); + temp &= ~(I2CR_MSTA | I2CR_MTX); + writeb(temp, i2c_imx->base + IMX_I2C_I2CR); + i2c_imx->stopped = 1; + } + if (cpu_is_mx1()) { + /* + * This delay caused by an i.MXL hardware bug. + * If no (or too short) delay, no "STOP" bit will be generated. + */ + udelay(i2c_imx->disable_delay); + } + + if (!i2c_imx->stopped) + i2c_imx_bus_busy(i2c_imx, 0); + /* Disable I2C controller */ writeb(0, i2c_imx->base + IMX_I2C_I2CR); + clk_disable(i2c_imx->clk); } static void __init i2c_imx_set_clk(struct imx_i2c_struct *i2c_imx, @@ -233,8 +261,8 @@ static void __init i2c_imx_set_clk(struct imx_i2c_struct *i2c_imx, else for (i = 0; i2c_clk_div[i][0] < div; i++); - /* Write divider value to register */ - writeb(i2c_clk_div[i][1], i2c_imx->base + IMX_I2C_IFDR); + /* Store divider value */ + i2c_imx->ifdr = i2c_clk_div[i][1]; /* * There dummy delay is calculated. @@ -341,11 +369,15 @@ static int i2c_imx_read(struct imx_i2c_struct *i2c_imx, struct i2c_msg *msgs) if (result) return result; if (i == (msgs->len - 1)) { + /* It must generate STOP before read I2DR to prevent + controller from generating another clock cycle */ dev_dbg(&i2c_imx->adapter.dev, "<%s> clear MSTA\n", __func__); temp = readb(i2c_imx->base + IMX_I2C_I2CR); - temp &= ~I2CR_MSTA; + temp &= ~(I2CR_MSTA | I2CR_MTX); writeb(temp, i2c_imx->base + IMX_I2C_I2CR); + i2c_imx_bus_busy(i2c_imx, 0); + i2c_imx->stopped = 1; } else if (i == (msgs->len - 2)) { dev_dbg(&i2c_imx->adapter.dev, "<%s> set TXAK\n", __func__); @@ -370,14 +402,11 @@ static int i2c_imx_xfer(struct i2c_adapter *adapter, dev_dbg(&i2c_imx->adapter.dev, "<%s>\n", __func__); - /* Check if i2c bus is not busy */ - result = i2c_imx_bus_busy(i2c_imx); + /* Start I2C transfer */ + result = i2c_imx_start(i2c_imx); if (result) goto fail0; - /* Start I2C transfer */ - i2c_imx_start(i2c_imx); - /* read/write data */ for (i = 0; i < num; i++) { if (i) { @@ -386,6 +415,9 @@ static int i2c_imx_xfer(struct i2c_adapter *adapter, temp = readb(i2c_imx->base + IMX_I2C_I2CR); temp |= I2CR_RSTA; writeb(temp, i2c_imx->base + IMX_I2C_I2CR); + result = i2c_imx_bus_busy(i2c_imx, 1); + if (result) + goto fail0; } dev_dbg(&i2c_imx->adapter.dev, "<%s> transfer message: %d\n", __func__, i); @@ -500,7 +532,6 @@ static int __init i2c_imx_probe(struct platform_device *pdev) dev_err(&pdev->dev, "can't get I2C clock\n"); goto fail3; } - clk_enable(i2c_imx->clk); /* Request IRQ */ ret = request_irq(i2c_imx->irq, i2c_imx_isr, 0, pdev->name, i2c_imx); @@ -549,7 +580,6 @@ static int __init i2c_imx_probe(struct platform_device *pdev) fail5: free_irq(i2c_imx->irq, i2c_imx); fail4: - clk_disable(i2c_imx->clk); clk_put(i2c_imx->clk); fail3: release_mem_region(i2c_imx->res->start, resource_size(res)); @@ -586,8 +616,6 @@ static int __exit i2c_imx_remove(struct platform_device *pdev) if (pdata && pdata->exit) pdata->exit(&pdev->dev); - /* Disable I2C clock */ - clk_disable(i2c_imx->clk); clk_put(i2c_imx->clk); release_mem_region(i2c_imx->res->start, resource_size(i2c_imx->res)); diff --git a/drivers/i2c/busses/i2c-mpc.c b/drivers/i2c/busses/i2c-mpc.c index d325e86e3103..f627001108b8 100644 --- a/drivers/i2c/busses/i2c-mpc.c +++ b/drivers/i2c/busses/i2c-mpc.c @@ -365,9 +365,6 @@ static int mpc_write(struct mpc_i2c *i2c, int target, unsigned timeout = i2c->adap.timeout; u32 flags = restart ? CCR_RSTA : 0; - /* Start with MEN */ - if (!restart) - writeccr(i2c, CCR_MEN); /* Start as master */ writeccr(i2c, CCR_MIEN | CCR_MEN | CCR_MSTA | CCR_MTX | flags); /* Write target byte */ @@ -396,9 +393,6 @@ static int mpc_read(struct mpc_i2c *i2c, int target, int i, result; u32 flags = restart ? CCR_RSTA : 0; - /* Start with MEN */ - if (!restart) - writeccr(i2c, CCR_MEN); /* Switch to read - restart */ writeccr(i2c, CCR_MIEN | CCR_MEN | CCR_MSTA | CCR_MTX | flags); /* Write target address byte - this time with the read flag set */ @@ -425,9 +419,9 @@ static int mpc_read(struct mpc_i2c *i2c, int target, /* Generate txack on next to last byte */ if (i == length - 2) writeccr(i2c, CCR_MIEN | CCR_MEN | CCR_MSTA | CCR_TXAK); - /* Generate stop on last byte */ + /* Do not generate stop on last byte */ if (i == length - 1) - writeccr(i2c, CCR_MIEN | CCR_MEN | CCR_TXAK); + writeccr(i2c, CCR_MIEN | CCR_MEN | CCR_MSTA | CCR_MTX); data[i] = readb(i2c->base + MPC_I2C_DR); } diff --git a/drivers/i2c/busses/i2c-piix4.c b/drivers/i2c/busses/i2c-piix4.c index d26a972aacaa..1e245e9cad31 100644 --- a/drivers/i2c/busses/i2c-piix4.c +++ b/drivers/i2c/busses/i2c-piix4.c @@ -22,7 +22,7 @@ Intel PIIX4, 440MX Serverworks OSB4, CSB5, CSB6, HT-1000, HT-1100 ATI IXP200, IXP300, IXP400, SB600, SB700, SB800 - AMD SB900 + AMD Hudson-2 SMSC Victory66 Note: we assume there can only be one device, with one SMBus interface. @@ -233,9 +233,9 @@ static int __devinit piix4_setup_sb800(struct pci_dev *PIIX4_dev, unsigned short smba_idx = 0xcd6; u8 smba_en_lo, smba_en_hi, i2ccfg, i2ccfg_offset = 0x10, smb_en = 0x2c; - /* SB800 SMBus does not support forcing address */ + /* SB800 and later SMBus does not support forcing address */ if (force || force_addr) { - dev_err(&PIIX4_dev->dev, "SB800 SMBus does not support " + dev_err(&PIIX4_dev->dev, "SMBus does not support " "forcing address!\n"); return -EINVAL; } @@ -480,7 +480,7 @@ static struct pci_device_id piix4_ids[] = { { PCI_DEVICE(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP300_SMBUS) }, { PCI_DEVICE(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP400_SMBUS) }, { PCI_DEVICE(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_SBX00_SMBUS) }, - { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_SB900_SMBUS) }, + { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_HUDSON2_SMBUS) }, { PCI_DEVICE(PCI_VENDOR_ID_SERVERWORKS, PCI_DEVICE_ID_SERVERWORKS_OSB4) }, { PCI_DEVICE(PCI_VENDOR_ID_SERVERWORKS, diff --git a/drivers/ide/atiixp.c b/drivers/ide/atiixp.c index 6396c3ad3252..837322b10a4c 100644 --- a/drivers/ide/atiixp.c +++ b/drivers/ide/atiixp.c @@ -177,7 +177,7 @@ static const struct pci_device_id atiixp_pci_tbl[] = { { PCI_VDEVICE(ATI, PCI_DEVICE_ID_ATI_IXP400_IDE), 0 }, { PCI_VDEVICE(ATI, PCI_DEVICE_ID_ATI_IXP600_IDE), 1 }, { PCI_VDEVICE(ATI, PCI_DEVICE_ID_ATI_IXP700_IDE), 0 }, - { PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_SB900_IDE), 0 }, + { PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_HUDSON2_IDE), 0 }, { 0, }, }; MODULE_DEVICE_TABLE(pci, atiixp_pci_tbl); diff --git a/drivers/ide/cmd64x.c b/drivers/ide/cmd64x.c index 680e5975217f..ca0c46f6580a 100644 --- a/drivers/ide/cmd64x.c +++ b/drivers/ide/cmd64x.c @@ -379,7 +379,8 @@ static const struct ide_port_info cmd64x_chipsets[] __devinitdata = { .enablebits = {{0x00,0x00,0x00}, {0x51,0x08,0x08}}, .port_ops = &cmd64x_port_ops, .host_flags = IDE_HFLAG_CLEAR_SIMPLEX | - IDE_HFLAG_ABUSE_PREFETCH, + IDE_HFLAG_ABUSE_PREFETCH | + IDE_HFLAG_SERIALIZE, .pio_mask = ATA_PIO5, .mwdma_mask = ATA_MWDMA2, .udma_mask = 0x00, /* no udma */ @@ -389,7 +390,8 @@ static const struct ide_port_info cmd64x_chipsets[] __devinitdata = { .init_chipset = init_chipset_cmd64x, .enablebits = {{0x51,0x04,0x04}, {0x51,0x08,0x08}}, .port_ops = &cmd648_port_ops, - .host_flags = IDE_HFLAG_ABUSE_PREFETCH, + .host_flags = IDE_HFLAG_ABUSE_PREFETCH | + IDE_HFLAG_SERIALIZE, .pio_mask = ATA_PIO5, .mwdma_mask = ATA_MWDMA2, .udma_mask = ATA_UDMA2, diff --git a/drivers/ide/ide-probe.c b/drivers/ide/ide-probe.c index 63c53d65e875..4d76ba473097 100644 --- a/drivers/ide/ide-probe.c +++ b/drivers/ide/ide-probe.c @@ -1046,15 +1046,6 @@ static void ide_port_init_devices(ide_hwif_t *hwif) if (port_ops && port_ops->init_dev) port_ops->init_dev(drive); } - - ide_port_for_each_dev(i, drive, hwif) { - /* - * default to PIO Mode 0 before we figure out - * the most suited mode for the attached device - */ - if (port_ops && port_ops->set_pio_mode) - port_ops->set_pio_mode(drive, 0); - } } static void ide_init_port(ide_hwif_t *hwif, unsigned int port, diff --git a/drivers/ide/ide-proc.c b/drivers/ide/ide-proc.c index 28d09a5d8450..017c09540c2f 100644 --- a/drivers/ide/ide-proc.c +++ b/drivers/ide/ide-proc.c @@ -273,14 +273,8 @@ static const struct ide_proc_devset ide_generic_settings[] = { static void proc_ide_settings_warn(void) { - static int warned; - - if (warned) - return; - - printk(KERN_WARNING "Warning: /proc/ide/hd?/settings interface is " + printk_once(KERN_WARNING "Warning: /proc/ide/hd?/settings interface is " "obsolete, and will be removed soon!\n"); - warned = 1; } static int ide_settings_proc_show(struct seq_file *m, void *v) diff --git a/drivers/ide/sis5513.c b/drivers/ide/sis5513.c index afca22beaadf..3b88eba04c9c 100644 --- a/drivers/ide/sis5513.c +++ b/drivers/ide/sis5513.c @@ -2,7 +2,7 @@ * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org> * Copyright (C) 2002 Lionel Bouton <Lionel.Bouton@inet6.fr>, Maintainer * Copyright (C) 2003 Vojtech Pavlik <vojtech@suse.cz> - * Copyright (C) 2007 Bartlomiej Zolnierkiewicz + * Copyright (C) 2007-2009 Bartlomiej Zolnierkiewicz * * May be copied or modified under the terms of the GNU General Public License * @@ -281,11 +281,13 @@ static void config_drive_art_rwp(ide_drive_t *drive) pci_read_config_byte(dev, 0x4b, ®4bh); + rw_prefetch = reg4bh & ~(0x11 << drive->dn); + if (drive->media == ide_disk) - rw_prefetch = 0x11 << drive->dn; + rw_prefetch |= 0x11 << drive->dn; - if ((reg4bh & (0x11 << drive->dn)) != rw_prefetch) - pci_write_config_byte(dev, 0x4b, reg4bh|rw_prefetch); + if (reg4bh != rw_prefetch) + pci_write_config_byte(dev, 0x4b, rw_prefetch); } static void sis_set_pio_mode(ide_drive_t *drive, const u8 pio) diff --git a/drivers/ieee1394/raw1394.c b/drivers/ieee1394/raw1394.c index 0bc3d78ce7b1..8aa56ac07e29 100644 --- a/drivers/ieee1394/raw1394.c +++ b/drivers/ieee1394/raw1394.c @@ -29,6 +29,7 @@ #include <linux/kernel.h> #include <linux/list.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/slab.h> #include <linux/fs.h> diff --git a/drivers/ieee1394/video1394.c b/drivers/ieee1394/video1394.c index d287ba79821d..949064a05675 100644 --- a/drivers/ieee1394/video1394.c +++ b/drivers/ieee1394/video1394.c @@ -30,6 +30,7 @@ */ #include <linux/kernel.h> #include <linux/list.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/interrupt.h> #include <linux/wait.h> diff --git a/drivers/infiniband/core/addr.c b/drivers/infiniband/core/addr.c index 5be1bd4fc7ed..bd07803e9183 100644 --- a/drivers/infiniband/core/addr.c +++ b/drivers/infiniband/core/addr.c @@ -393,7 +393,7 @@ static int addr_resolve_local(struct sockaddr *src_in, for_each_netdev(&init_net, dev) if (ipv6_chk_addr(&init_net, - &((struct sockaddr_in6 *) addr)->sin6_addr, + &((struct sockaddr_in6 *) dst_in)->sin6_addr, dev, 1)) break; diff --git a/drivers/infiniband/core/iwcm.c b/drivers/infiniband/core/iwcm.c index 55d093a36ae4..0f89909abce9 100644 --- a/drivers/infiniband/core/iwcm.c +++ b/drivers/infiniband/core/iwcm.c @@ -40,6 +40,7 @@ #include <linux/idr.h> #include <linux/interrupt.h> #include <linux/rbtree.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/workqueue.h> #include <linux/completion.h> @@ -362,7 +363,9 @@ static void destroy_cm_id(struct iw_cm_id *cm_id) * In either case, must tell the provider to reject. */ cm_id_priv->state = IW_CM_STATE_DESTROYING; + spin_unlock_irqrestore(&cm_id_priv->lock, flags); cm_id->device->iwcm->reject(cm_id, NULL, 0); + spin_lock_irqsave(&cm_id_priv->lock, flags); break; case IW_CM_STATE_CONN_SENT: case IW_CM_STATE_DESTROYING: diff --git a/drivers/infiniband/core/ucma.c b/drivers/infiniband/core/ucma.c index 4346a24568fb..bb96d3c4b0f4 100644 --- a/drivers/infiniband/core/ucma.c +++ b/drivers/infiniband/core/ucma.c @@ -34,6 +34,7 @@ #include <linux/file.h> #include <linux/mutex.h> #include <linux/poll.h> +#include <linux/sched.h> #include <linux/idr.h> #include <linux/in.h> #include <linux/in6.h> diff --git a/drivers/infiniband/hw/cxgb3/iwch_provider.c b/drivers/infiniband/hw/cxgb3/iwch_provider.c index 6895523779d0..ed7175549ebd 100644 --- a/drivers/infiniband/hw/cxgb3/iwch_provider.c +++ b/drivers/infiniband/hw/cxgb3/iwch_provider.c @@ -37,6 +37,7 @@ #include <linux/delay.h> #include <linux/errno.h> #include <linux/list.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/ethtool.h> #include <linux/rtnetlink.h> @@ -1199,11 +1200,14 @@ static int iwch_query_port(struct ib_device *ibdev, props->state = IB_PORT_DOWN; else { inetdev = in_dev_get(netdev); - if (inetdev->ifa_list) - props->state = IB_PORT_ACTIVE; - else + if (inetdev) { + if (inetdev->ifa_list) + props->state = IB_PORT_ACTIVE; + else + props->state = IB_PORT_INIT; + in_dev_put(inetdev); + } else props->state = IB_PORT_INIT; - in_dev_put(inetdev); } props->port_cap_flags = diff --git a/drivers/infiniband/hw/cxgb3/iwch_qp.c b/drivers/infiniband/hw/cxgb3/iwch_qp.c index 6e8653471941..1cecf98829ac 100644 --- a/drivers/infiniband/hw/cxgb3/iwch_qp.c +++ b/drivers/infiniband/hw/cxgb3/iwch_qp.c @@ -29,6 +29,7 @@ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE * SOFTWARE. */ +#include <linux/sched.h> #include "iwch_provider.h" #include "iwch.h" #include "iwch_cm.h" diff --git a/drivers/infiniband/hw/ipath/ipath_driver.c b/drivers/infiniband/hw/ipath/ipath_driver.c index 04e88b600558..013d1380e77c 100644 --- a/drivers/infiniband/hw/ipath/ipath_driver.c +++ b/drivers/infiniband/hw/ipath/ipath_driver.c @@ -31,6 +31,7 @@ * SOFTWARE. */ +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/idr.h> #include <linux/pci.h> diff --git a/drivers/infiniband/hw/ipath/ipath_iba7220.c b/drivers/infiniband/hw/ipath/ipath_iba7220.c index b2a9d4c155d1..a805402dd4ae 100644 --- a/drivers/infiniband/hw/ipath/ipath_iba7220.c +++ b/drivers/infiniband/hw/ipath/ipath_iba7220.c @@ -37,6 +37,7 @@ #include <linux/interrupt.h> #include <linux/pci.h> +#include <linux/sched.h> #include <linux/delay.h> #include <linux/io.h> #include <rdma/ib_verbs.h> diff --git a/drivers/infiniband/hw/ipath/ipath_intr.c b/drivers/infiniband/hw/ipath/ipath_intr.c index 6c21b4b5ec71..c0a03ac03ee7 100644 --- a/drivers/infiniband/hw/ipath/ipath_intr.c +++ b/drivers/infiniband/hw/ipath/ipath_intr.c @@ -33,6 +33,7 @@ #include <linux/pci.h> #include <linux/delay.h> +#include <linux/sched.h> #include "ipath_kernel.h" #include "ipath_verbs.h" diff --git a/drivers/infiniband/hw/ipath/ipath_qp.c b/drivers/infiniband/hw/ipath/ipath_qp.c index 3a5a89b609c4..cb2d3ef2ae12 100644 --- a/drivers/infiniband/hw/ipath/ipath_qp.c +++ b/drivers/infiniband/hw/ipath/ipath_qp.c @@ -32,6 +32,7 @@ */ #include <linux/err.h> +#include <linux/sched.h> #include <linux/vmalloc.h> #include "ipath_verbs.h" diff --git a/drivers/infiniband/hw/ipath/ipath_ruc.c b/drivers/infiniband/hw/ipath/ipath_ruc.c index 2296832f94da..1f95bbaf7602 100644 --- a/drivers/infiniband/hw/ipath/ipath_ruc.c +++ b/drivers/infiniband/hw/ipath/ipath_ruc.c @@ -31,6 +31,7 @@ * SOFTWARE. */ +#include <linux/sched.h> #include <linux/spinlock.h> #include "ipath_verbs.h" diff --git a/drivers/infiniband/hw/ipath/ipath_ud.c b/drivers/infiniband/hw/ipath/ipath_ud.c index 6076cb61bf6a..7420715256a9 100644 --- a/drivers/infiniband/hw/ipath/ipath_ud.c +++ b/drivers/infiniband/hw/ipath/ipath_ud.c @@ -31,6 +31,7 @@ * SOFTWARE. */ +#include <linux/sched.h> #include <rdma/ib_smi.h> #include "ipath_verbs.h" diff --git a/drivers/infiniband/hw/ipath/ipath_user_pages.c b/drivers/infiniband/hw/ipath/ipath_user_pages.c index 855911e7396d..82878e348627 100644 --- a/drivers/infiniband/hw/ipath/ipath_user_pages.c +++ b/drivers/infiniband/hw/ipath/ipath_user_pages.c @@ -33,6 +33,7 @@ #include <linux/mm.h> #include <linux/device.h> +#include <linux/sched.h> #include "ipath_kernel.h" diff --git a/drivers/infiniband/hw/ipath/ipath_user_sdma.c b/drivers/infiniband/hw/ipath/ipath_user_sdma.c index 7bff4b9baa0a..be78f6643c06 100644 --- a/drivers/infiniband/hw/ipath/ipath_user_sdma.c +++ b/drivers/infiniband/hw/ipath/ipath_user_sdma.c @@ -33,6 +33,7 @@ #include <linux/types.h> #include <linux/device.h> #include <linux/dmapool.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/list.h> #include <linux/highmem.h> diff --git a/drivers/infiniband/hw/ipath/ipath_verbs_mcast.c b/drivers/infiniband/hw/ipath/ipath_verbs_mcast.c index d73e32232879..6923e1d986da 100644 --- a/drivers/infiniband/hw/ipath/ipath_verbs_mcast.c +++ b/drivers/infiniband/hw/ipath/ipath_verbs_mcast.c @@ -32,6 +32,7 @@ */ #include <linux/rculist.h> +#include <linux/sched.h> #include "ipath_verbs.h" diff --git a/drivers/infiniband/ulp/iser/iscsi_iser.c b/drivers/infiniband/ulp/iser/iscsi_iser.c index 0ba6ec876296..add9188663ff 100644 --- a/drivers/infiniband/ulp/iser/iscsi_iser.c +++ b/drivers/infiniband/ulp/iser/iscsi_iser.c @@ -426,7 +426,7 @@ iscsi_iser_session_create(struct iscsi_endpoint *ep, * because we preallocate so many resources */ cls_session = iscsi_session_setup(&iscsi_iser_transport, shost, - ISCSI_DEF_XMIT_CMDS_MAX, + ISCSI_DEF_XMIT_CMDS_MAX, 0, sizeof(struct iscsi_iser_task), initial_cmdsn, 0); if (!cls_session) diff --git a/drivers/input/ff-core.c b/drivers/input/ff-core.c index 72c63e5dd630..38df81fcdc3a 100644 --- a/drivers/input/ff-core.c +++ b/drivers/input/ff-core.c @@ -337,16 +337,16 @@ int input_ff_create(struct input_dev *dev, int max_effects) dev->ff = ff; dev->flush = flush_effects; dev->event = input_ff_event; - set_bit(EV_FF, dev->evbit); + __set_bit(EV_FF, dev->evbit); /* Copy "true" bits into ff device bitmap */ for (i = 0; i <= FF_MAX; i++) if (test_bit(i, dev->ffbit)) - set_bit(i, ff->ffbit); + __set_bit(i, ff->ffbit); /* we can emulate RUMBLE with periodic effects */ if (test_bit(FF_PERIODIC, ff->ffbit)) - set_bit(FF_RUMBLE, dev->ffbit); + __set_bit(FF_RUMBLE, dev->ffbit); return 0; } @@ -362,12 +362,14 @@ EXPORT_SYMBOL_GPL(input_ff_create); */ void input_ff_destroy(struct input_dev *dev) { - clear_bit(EV_FF, dev->evbit); - if (dev->ff) { - if (dev->ff->destroy) - dev->ff->destroy(dev->ff); - kfree(dev->ff->private); - kfree(dev->ff); + struct ff_device *ff = dev->ff; + + __clear_bit(EV_FF, dev->evbit); + if (ff) { + if (ff->destroy) + ff->destroy(ff); + kfree(ff->private); + kfree(ff); dev->ff = NULL; } } diff --git a/drivers/input/ff-memless.c b/drivers/input/ff-memless.c index 2d1415e16834..b483b2995fa9 100644 --- a/drivers/input/ff-memless.c +++ b/drivers/input/ff-memless.c @@ -61,7 +61,6 @@ struct ml_device { struct ml_effect_state states[FF_MEMLESS_EFFECTS]; int gain; struct timer_list timer; - spinlock_t timer_lock; struct input_dev *dev; int (*play_effect)(struct input_dev *dev, void *data, @@ -368,38 +367,38 @@ static void ml_effect_timer(unsigned long timer_data) { struct input_dev *dev = (struct input_dev *)timer_data; struct ml_device *ml = dev->ff->private; + unsigned long flags; debug("timer: updating effects"); - spin_lock(&ml->timer_lock); + spin_lock_irqsave(&dev->event_lock, flags); ml_play_effects(ml); - spin_unlock(&ml->timer_lock); + spin_unlock_irqrestore(&dev->event_lock, flags); } +/* + * Sets requested gain for FF effects. Called with dev->event_lock held. + */ static void ml_ff_set_gain(struct input_dev *dev, u16 gain) { struct ml_device *ml = dev->ff->private; int i; - spin_lock_bh(&ml->timer_lock); - ml->gain = gain; for (i = 0; i < FF_MEMLESS_EFFECTS; i++) __clear_bit(FF_EFFECT_PLAYING, &ml->states[i].flags); ml_play_effects(ml); - - spin_unlock_bh(&ml->timer_lock); } +/* + * Start/stop specified FF effect. Called with dev->event_lock held. + */ static int ml_ff_playback(struct input_dev *dev, int effect_id, int value) { struct ml_device *ml = dev->ff->private; struct ml_effect_state *state = &ml->states[effect_id]; - unsigned long flags; - - spin_lock_irqsave(&ml->timer_lock, flags); if (value > 0) { debug("initiated play"); @@ -425,8 +424,6 @@ static int ml_ff_playback(struct input_dev *dev, int effect_id, int value) ml_play_effects(ml); } - spin_unlock_irqrestore(&ml->timer_lock, flags); - return 0; } @@ -436,7 +433,7 @@ static int ml_ff_upload(struct input_dev *dev, struct ml_device *ml = dev->ff->private; struct ml_effect_state *state = &ml->states[effect->id]; - spin_lock_bh(&ml->timer_lock); + spin_lock_irq(&dev->event_lock); if (test_bit(FF_EFFECT_STARTED, &state->flags)) { __clear_bit(FF_EFFECT_PLAYING, &state->flags); @@ -448,7 +445,7 @@ static int ml_ff_upload(struct input_dev *dev, ml_schedule_timer(ml); } - spin_unlock_bh(&ml->timer_lock); + spin_unlock_irq(&dev->event_lock); return 0; } @@ -482,7 +479,6 @@ int input_ff_create_memless(struct input_dev *dev, void *data, ml->private = data; ml->play_effect = play_effect; ml->gain = 0xffff; - spin_lock_init(&ml->timer_lock); setup_timer(&ml->timer, ml_effect_timer, (unsigned long)dev); set_bit(FF_GAIN, dev->ffbit); diff --git a/drivers/input/input.c b/drivers/input/input.c index c6f88ebb40c7..2266ecbfbc01 100644 --- a/drivers/input/input.c +++ b/drivers/input/input.c @@ -782,10 +782,29 @@ static unsigned int input_proc_devices_poll(struct file *file, poll_table *wait) return 0; } +union input_seq_state { + struct { + unsigned short pos; + bool mutex_acquired; + }; + void *p; +}; + static void *input_devices_seq_start(struct seq_file *seq, loff_t *pos) { - if (mutex_lock_interruptible(&input_mutex)) - return NULL; + union input_seq_state *state = (union input_seq_state *)&seq->private; + int error; + + /* We need to fit into seq->private pointer */ + BUILD_BUG_ON(sizeof(union input_seq_state) != sizeof(seq->private)); + + error = mutex_lock_interruptible(&input_mutex); + if (error) { + state->mutex_acquired = false; + return ERR_PTR(error); + } + + state->mutex_acquired = true; return seq_list_start(&input_dev_list, *pos); } @@ -795,9 +814,12 @@ static void *input_devices_seq_next(struct seq_file *seq, void *v, loff_t *pos) return seq_list_next(v, &input_dev_list, pos); } -static void input_devices_seq_stop(struct seq_file *seq, void *v) +static void input_seq_stop(struct seq_file *seq, void *v) { - mutex_unlock(&input_mutex); + union input_seq_state *state = (union input_seq_state *)&seq->private; + + if (state->mutex_acquired) + mutex_unlock(&input_mutex); } static void input_seq_print_bitmap(struct seq_file *seq, const char *name, @@ -861,7 +883,7 @@ static int input_devices_seq_show(struct seq_file *seq, void *v) static const struct seq_operations input_devices_seq_ops = { .start = input_devices_seq_start, .next = input_devices_seq_next, - .stop = input_devices_seq_stop, + .stop = input_seq_stop, .show = input_devices_seq_show, }; @@ -881,40 +903,49 @@ static const struct file_operations input_devices_fileops = { static void *input_handlers_seq_start(struct seq_file *seq, loff_t *pos) { - if (mutex_lock_interruptible(&input_mutex)) - return NULL; + union input_seq_state *state = (union input_seq_state *)&seq->private; + int error; + + /* We need to fit into seq->private pointer */ + BUILD_BUG_ON(sizeof(union input_seq_state) != sizeof(seq->private)); + + error = mutex_lock_interruptible(&input_mutex); + if (error) { + state->mutex_acquired = false; + return ERR_PTR(error); + } + + state->mutex_acquired = true; + state->pos = *pos; - seq->private = (void *)(unsigned long)*pos; return seq_list_start(&input_handler_list, *pos); } static void *input_handlers_seq_next(struct seq_file *seq, void *v, loff_t *pos) { - seq->private = (void *)(unsigned long)(*pos + 1); - return seq_list_next(v, &input_handler_list, pos); -} + union input_seq_state *state = (union input_seq_state *)&seq->private; -static void input_handlers_seq_stop(struct seq_file *seq, void *v) -{ - mutex_unlock(&input_mutex); + state->pos = *pos + 1; + return seq_list_next(v, &input_handler_list, pos); } static int input_handlers_seq_show(struct seq_file *seq, void *v) { struct input_handler *handler = container_of(v, struct input_handler, node); + union input_seq_state *state = (union input_seq_state *)&seq->private; - seq_printf(seq, "N: Number=%ld Name=%s", - (unsigned long)seq->private, handler->name); + seq_printf(seq, "N: Number=%u Name=%s", state->pos, handler->name); if (handler->fops) seq_printf(seq, " Minor=%d", handler->minor); seq_putc(seq, '\n'); return 0; } + static const struct seq_operations input_handlers_seq_ops = { .start = input_handlers_seq_start, .next = input_handlers_seq_next, - .stop = input_handlers_seq_stop, + .stop = input_seq_stop, .show = input_handlers_seq_show, }; @@ -1261,17 +1292,24 @@ static int input_dev_uevent(struct device *device, struct kobj_uevent_env *env) return 0; } -#define INPUT_DO_TOGGLE(dev, type, bits, on) \ - do { \ - int i; \ - if (!test_bit(EV_##type, dev->evbit)) \ - break; \ - for (i = 0; i < type##_MAX; i++) { \ - if (!test_bit(i, dev->bits##bit) || \ - !test_bit(i, dev->bits)) \ - continue; \ - dev->event(dev, EV_##type, i, on); \ - } \ +#define INPUT_DO_TOGGLE(dev, type, bits, on) \ + do { \ + int i; \ + bool active; \ + \ + if (!test_bit(EV_##type, dev->evbit)) \ + break; \ + \ + for (i = 0; i < type##_MAX; i++) { \ + if (!test_bit(i, dev->bits##bit)) \ + continue; \ + \ + active = test_bit(i, dev->bits); \ + if (!active && !on) \ + continue; \ + \ + dev->event(dev, EV_##type, i, on ? active : 0); \ + } \ } while (0) #ifdef CONFIG_PM diff --git a/drivers/input/joystick/xpad.c b/drivers/input/joystick/xpad.c index 2388cf578a62..79e3edcced1a 100644 --- a/drivers/input/joystick/xpad.c +++ b/drivers/input/joystick/xpad.c @@ -143,6 +143,7 @@ static const struct xpad_device { { 0x12ab, 0x8809, "Xbox DDR dancepad", MAP_DPAD_TO_BUTTONS, XTYPE_XBOX }, { 0x1430, 0x4748, "RedOctane Guitar Hero X-plorer", MAP_DPAD_TO_AXES, XTYPE_XBOX360 }, { 0x1430, 0x8888, "TX6500+ Dance Pad (first generation)", MAP_DPAD_TO_BUTTONS, XTYPE_XBOX }, + { 0x146b, 0x0601, "BigBen Interactive XBOX 360 Controller", MAP_DPAD_TO_AXES, XTYPE_XBOX360 }, { 0x045e, 0x028e, "Microsoft X-Box 360 pad", MAP_DPAD_TO_AXES, XTYPE_XBOX360 }, { 0x1bad, 0x0003, "Harmonix Rock Band Drumkit", MAP_DPAD_TO_BUTTONS, XTYPE_XBOX360 }, { 0xffff, 0xffff, "Chinese-made Xbox Controller", MAP_DPAD_TO_AXES, XTYPE_XBOX }, @@ -209,6 +210,7 @@ static struct usb_device_id xpad_table [] = { XPAD_XBOX360_VENDOR(0x0738), /* Mad Catz X-Box 360 controllers */ XPAD_XBOX360_VENDOR(0x0e6f), /* 0x0e6f X-Box 360 controllers */ XPAD_XBOX360_VENDOR(0x1430), /* RedOctane X-Box 360 controllers */ + XPAD_XBOX360_VENDOR(0x146b), /* BigBen Interactive Controllers */ XPAD_XBOX360_VENDOR(0x1bad), /* Rock Band Drums */ { } }; diff --git a/drivers/input/keyboard/atkbd.c b/drivers/input/keyboard/atkbd.c index 4709e15af607..28e6110d1ff8 100644 --- a/drivers/input/keyboard/atkbd.c +++ b/drivers/input/keyboard/atkbd.c @@ -233,6 +233,7 @@ struct atkbd { */ static void (*atkbd_platform_fixup)(struct atkbd *, const void *data); static void *atkbd_platform_fixup_data; +static unsigned int (*atkbd_platform_scancode_fixup)(struct atkbd *, unsigned int); static ssize_t atkbd_attr_show_helper(struct device *dev, char *buf, ssize_t (*handler)(struct atkbd *, char *)); @@ -393,6 +394,9 @@ static irqreturn_t atkbd_interrupt(struct serio *serio, unsigned char data, input_event(dev, EV_MSC, MSC_RAW, code); + if (atkbd_platform_scancode_fixup) + code = atkbd_platform_scancode_fixup(atkbd, code); + if (atkbd->translated) { if (atkbd->emul || atkbd_need_xlate(atkbd->xl_bit, code)) { @@ -574,11 +578,22 @@ static void atkbd_event_work(struct work_struct *work) mutex_lock(&atkbd->event_mutex); - if (test_and_clear_bit(ATKBD_LED_EVENT_BIT, &atkbd->event_mask)) - atkbd_set_leds(atkbd); + if (!atkbd->enabled) { + /* + * Serio ports are resumed asynchronously so while driver core + * thinks that device is already fully operational in reality + * it may not be ready yet. In this case we need to keep + * rescheduling till reconnect completes. + */ + schedule_delayed_work(&atkbd->event_work, + msecs_to_jiffies(100)); + } else { + if (test_and_clear_bit(ATKBD_LED_EVENT_BIT, &atkbd->event_mask)) + atkbd_set_leds(atkbd); - if (test_and_clear_bit(ATKBD_REP_EVENT_BIT, &atkbd->event_mask)) - atkbd_set_repeat_rate(atkbd); + if (test_and_clear_bit(ATKBD_REP_EVENT_BIT, &atkbd->event_mask)) + atkbd_set_repeat_rate(atkbd); + } mutex_unlock(&atkbd->event_mutex); } @@ -770,6 +785,30 @@ static int atkbd_select_set(struct atkbd *atkbd, int target_set, int allow_extra return 3; } +static int atkbd_reset_state(struct atkbd *atkbd) +{ + struct ps2dev *ps2dev = &atkbd->ps2dev; + unsigned char param[1]; + +/* + * Set the LEDs to a predefined state (all off). + */ + + param[0] = 0; + if (ps2_command(ps2dev, param, ATKBD_CMD_SETLEDS)) + return -1; + +/* + * Set autorepeat to fastest possible. + */ + + param[0] = 0; + if (ps2_command(ps2dev, param, ATKBD_CMD_SETREP)) + return -1; + + return 0; +} + static int atkbd_activate(struct atkbd *atkbd) { struct ps2dev *ps2dev = &atkbd->ps2dev; @@ -852,29 +891,6 @@ static unsigned int atkbd_hp_forced_release_keys[] = { }; /* - * Inventec system with broken key release on volume keys - */ -static unsigned int atkbd_inventec_forced_release_keys[] = { - 0xae, 0xb0, -1U -}; - -/* - * Perform fixup for HP Pavilion ZV6100 laptop that doesn't generate release - * for its volume buttons - */ -static unsigned int atkbd_hp_zv6100_forced_release_keys[] = { - 0xae, 0xb0, -1U -}; - -/* - * Perform fixup for HP (Compaq) Presario R4000 R4100 R4200 that don't generate - * release for their volume buttons - */ -static unsigned int atkbd_hp_r4000_forced_release_keys[] = { - 0xae, 0xb0, -1U -}; - -/* * Samsung NC10,NC20 with Fn+F? key release not working */ static unsigned int atkbd_samsung_forced_release_keys[] = { @@ -882,14 +898,6 @@ static unsigned int atkbd_samsung_forced_release_keys[] = { }; /* - * The volume up and volume down special keys on a Fujitsu Amilo PA 1510 laptop - * do not generate release events so we have to do it ourselves. - */ -static unsigned int atkbd_amilo_pa1510_forced_release_keys[] = { - 0xb0, 0xae, -1U -}; - -/* * Amilo Pi 3525 key release for Fn+Volume keys not working */ static unsigned int atkbd_amilo_pi3525_forced_release_keys[] = { @@ -911,6 +919,30 @@ static unsigned int atkdb_soltech_ta12_forced_release_keys[] = { }; /* + * Many notebooks don't send key release event for volume up/down + * keys, with key list below common among them + */ +static unsigned int atkbd_volume_forced_release_keys[] = { + 0xae, 0xb0, -1U +}; + +/* + * OQO 01+ multimedia keys (64--66) generate e0 6x upon release whereas + * they should be generating e4-e6 (0x80 | code). + */ +static unsigned int atkbd_oqo_01plus_scancode_fixup(struct atkbd *atkbd, + unsigned int code) +{ + if (atkbd->translated && atkbd->emul == 1 && + (code == 0x64 || code == 0x65 || code == 0x66)) { + atkbd->emul = 0; + code |= 0x80; + } + + return code; +} + +/* * atkbd_set_keycode_table() initializes keyboard's keycode table * according to the selected scancode set */ @@ -1087,6 +1119,7 @@ static int atkbd_connect(struct serio *serio, struct serio_driver *drv) } atkbd->set = atkbd_select_set(atkbd, atkbd_set, atkbd_extra); + atkbd_reset_state(atkbd); atkbd_activate(atkbd); } else { @@ -1141,6 +1174,18 @@ static int atkbd_reconnect(struct serio *serio) return -1; atkbd_activate(atkbd); + + /* + * Restore LED state and repeat rate. While input core + * will do this for us at resume time reconnect may happen + * because user requested it via sysfs or simply because + * keyboard was unplugged and plugged in again so we need + * to do it ourselves here. + */ + atkbd_set_leds(atkbd); + if (!atkbd->softrepeat) + atkbd_set_repeat_rate(atkbd); + } atkbd_enable(atkbd); @@ -1267,6 +1312,7 @@ static ssize_t atkbd_set_extra(struct atkbd *atkbd, const char *buf, size_t coun atkbd->dev = new_dev; atkbd->set = atkbd_select_set(atkbd, atkbd->set, value); + atkbd_reset_state(atkbd); atkbd_activate(atkbd); atkbd_set_keycode_table(atkbd); atkbd_set_device_attrs(atkbd); @@ -1388,6 +1434,7 @@ static ssize_t atkbd_set_set(struct atkbd *atkbd, const char *buf, size_t count) atkbd->dev = new_dev; atkbd->set = atkbd_select_set(atkbd, value, atkbd->extra); + atkbd_reset_state(atkbd); atkbd_activate(atkbd); atkbd_set_keycode_table(atkbd); atkbd_set_device_attrs(atkbd); @@ -1513,6 +1560,13 @@ static int __init atkbd_setup_forced_release(const struct dmi_system_id *id) return 0; } +static int __init atkbd_setup_scancode_fixup(const struct dmi_system_id *id) +{ + atkbd_platform_scancode_fixup = id->driver_data; + + return 0; +} + static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { { .ident = "Dell Laptop", @@ -1548,7 +1602,7 @@ static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { DMI_MATCH(DMI_PRODUCT_NAME, "Pavilion ZV6100"), }, .callback = atkbd_setup_forced_release, - .driver_data = atkbd_hp_zv6100_forced_release_keys, + .driver_data = atkbd_volume_forced_release_keys, }, { .ident = "HP Presario R4000", @@ -1557,7 +1611,7 @@ static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { DMI_MATCH(DMI_PRODUCT_NAME, "Presario R4000"), }, .callback = atkbd_setup_forced_release, - .driver_data = atkbd_hp_r4000_forced_release_keys, + .driver_data = atkbd_volume_forced_release_keys, }, { .ident = "HP Presario R4100", @@ -1566,7 +1620,7 @@ static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { DMI_MATCH(DMI_PRODUCT_NAME, "Presario R4100"), }, .callback = atkbd_setup_forced_release, - .driver_data = atkbd_hp_r4000_forced_release_keys, + .driver_data = atkbd_volume_forced_release_keys, }, { .ident = "HP Presario R4200", @@ -1575,7 +1629,7 @@ static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { DMI_MATCH(DMI_PRODUCT_NAME, "Presario R4200"), }, .callback = atkbd_setup_forced_release, - .driver_data = atkbd_hp_r4000_forced_release_keys, + .driver_data = atkbd_volume_forced_release_keys, }, { .ident = "Inventec Symphony", @@ -1584,7 +1638,7 @@ static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { DMI_MATCH(DMI_PRODUCT_NAME, "SYMPHONY 6.0/7.0"), }, .callback = atkbd_setup_forced_release, - .driver_data = atkbd_inventec_forced_release_keys, + .driver_data = atkbd_volume_forced_release_keys, }, { .ident = "Samsung NC10", @@ -1620,7 +1674,7 @@ static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { DMI_MATCH(DMI_PRODUCT_NAME, "AMILO Pa 1510"), }, .callback = atkbd_setup_forced_release, - .driver_data = atkbd_amilo_pa1510_forced_release_keys, + .driver_data = atkbd_volume_forced_release_keys, }, { .ident = "Fujitsu Amilo Pi 3525", @@ -1649,6 +1703,15 @@ static struct dmi_system_id atkbd_dmi_quirk_table[] __initdata = { .callback = atkbd_setup_forced_release, .driver_data = atkdb_soltech_ta12_forced_release_keys, }, + { + .ident = "OQO Model 01+", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "OQO"), + DMI_MATCH(DMI_PRODUCT_NAME, "ZEPTO"), + }, + .callback = atkbd_setup_scancode_fixup, + .driver_data = atkbd_oqo_01plus_scancode_fixup, + }, { } }; diff --git a/drivers/input/keyboard/gpio_keys.c b/drivers/input/keyboard/gpio_keys.c index a88aff3816a0..77d130914259 100644 --- a/drivers/input/keyboard/gpio_keys.c +++ b/drivers/input/keyboard/gpio_keys.c @@ -147,6 +147,7 @@ static int __devinit gpio_keys_probe(struct platform_device *pdev) } error = request_irq(irq, gpio_keys_isr, + IRQF_SHARED | IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, button->desc ? button->desc : "gpio_keys", bdata); diff --git a/drivers/input/keyboard/hilkbd.c b/drivers/input/keyboard/hilkbd.c index e9d639ec283d..5f72440b50c8 100644 --- a/drivers/input/keyboard/hilkbd.c +++ b/drivers/input/keyboard/hilkbd.c @@ -24,6 +24,7 @@ #include <linux/interrupt.h> #include <linux/hil.h> #include <linux/io.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <asm/irq.h> #ifdef CONFIG_HP300 diff --git a/drivers/input/keyboard/sunkbd.c b/drivers/input/keyboard/sunkbd.c index 472b56639cdb..a99a04b03ee4 100644 --- a/drivers/input/keyboard/sunkbd.c +++ b/drivers/input/keyboard/sunkbd.c @@ -27,6 +27,7 @@ */ #include <linux/delay.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/module.h> #include <linux/interrupt.h> diff --git a/drivers/input/misc/Kconfig b/drivers/input/misc/Kconfig index 02f4f8f1db6f..a9bb2544b2de 100644 --- a/drivers/input/misc/Kconfig +++ b/drivers/input/misc/Kconfig @@ -227,6 +227,7 @@ config INPUT_WINBOND_CIR depends on X86 && PNP select NEW_LEDS select LEDS_CLASS + select LEDS_TRIGGERS select BITREVERSE help Say Y here if you want to use the IR remote functionality found diff --git a/drivers/input/misc/hp_sdc_rtc.c b/drivers/input/misc/hp_sdc_rtc.c index 216a559f55ea..ea821b546969 100644 --- a/drivers/input/misc/hp_sdc_rtc.c +++ b/drivers/input/misc/hp_sdc_rtc.c @@ -209,7 +209,7 @@ static inline int hp_sdc_rtc_read_rt(struct timeval *res) { /* Read the i8042 fast handshake timer */ static inline int hp_sdc_rtc_read_fhs(struct timeval *res) { - uint64_t raw; + int64_t raw; unsigned int tenms; raw = hp_sdc_rtc_read_i8042timer(HP_SDC_CMD_LOAD_FHS, 2); diff --git a/drivers/input/misc/rotary_encoder.c b/drivers/input/misc/rotary_encoder.c index c806fbf1e174..3b9f588fc747 100644 --- a/drivers/input/misc/rotary_encoder.c +++ b/drivers/input/misc/rotary_encoder.c @@ -106,8 +106,8 @@ static int __devinit rotary_encoder_probe(struct platform_device *pdev) struct input_dev *input; int err; - if (!pdata || !pdata->steps) { - dev_err(&pdev->dev, "invalid platform data\n"); + if (!pdata) { + dev_err(&pdev->dev, "missing platform data\n"); return -ENOENT; } diff --git a/drivers/input/misc/sparcspkr.c b/drivers/input/misc/sparcspkr.c index c4f42311fdec..b064419b90a2 100644 --- a/drivers/input/misc/sparcspkr.c +++ b/drivers/input/misc/sparcspkr.c @@ -230,7 +230,7 @@ out_err: return err; } -static int bbc_remove(struct of_device *op) +static int __devexit bbc_remove(struct of_device *op) { struct sparcspkr_state *state = dev_get_drvdata(&op->dev); struct input_dev *input_dev = state->input_dev; @@ -308,7 +308,7 @@ out_err: return err; } -static int grover_remove(struct of_device *op) +static int __devexit grover_remove(struct of_device *op) { struct sparcspkr_state *state = dev_get_drvdata(&op->dev); struct grover_beep_info *info = &state->u.grover; diff --git a/drivers/input/misc/wistron_btns.c b/drivers/input/misc/wistron_btns.c index 11fd038a078f..a932179c4c9e 100644 --- a/drivers/input/misc/wistron_btns.c +++ b/drivers/input/misc/wistron_btns.c @@ -936,6 +936,15 @@ static struct dmi_system_id dmi_ids[] __initdata = { }, { .callback = dmi_matched, + .ident = "Medion MD 42200", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Medion"), + DMI_MATCH(DMI_PRODUCT_NAME, "WIM 2030"), + }, + .driver_data = keymap_fs_amilo_pro_v2000 + }, + { + .callback = dmi_matched, .ident = "Medion MD 96500", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "MEDIONPC"), diff --git a/drivers/input/mouse/lifebook.c b/drivers/input/mouse/lifebook.c index 5e6308694408..82811558ec33 100644 --- a/drivers/input/mouse/lifebook.c +++ b/drivers/input/mouse/lifebook.c @@ -107,8 +107,7 @@ static const struct dmi_system_id lifebook_dmi_table[] = { .matches = { DMI_MATCH(DMI_PRODUCT_NAME, "CF-72"), }, - .callback = lifebook_set_serio_phys, - .driver_data = "isa0060/serio3", + .callback = lifebook_set_6byte_proto, }, { .ident = "Lifebook B142", diff --git a/drivers/input/mouse/logips2pp.c b/drivers/input/mouse/logips2pp.c index de745d751162..ab5dc5f5fd83 100644 --- a/drivers/input/mouse/logips2pp.c +++ b/drivers/input/mouse/logips2pp.c @@ -219,7 +219,7 @@ static const struct ps2pp_info *get_model_info(unsigned char model) PS2PP_WHEEL | PS2PP_SIDE_BTN | PS2PP_TASK_BTN | PS2PP_EXTRA_BTN | PS2PP_NAV_BTN | PS2PP_HWHEEL }, { 72, PS2PP_KIND_TRACKMAN, 0 }, /* T-CH11: TrackMan Marble */ - { 73, 0, PS2PP_SIDE_BTN }, + { 73, PS2PP_KIND_TRACKMAN, PS2PP_SIDE_BTN }, /* TrackMan FX */ { 75, PS2PP_KIND_WHEEL, PS2PP_WHEEL }, { 76, PS2PP_KIND_WHEEL, PS2PP_WHEEL }, { 79, PS2PP_KIND_TRACKMAN, PS2PP_WHEEL }, /* TrackMan with wheel */ diff --git a/drivers/input/mouse/psmouse-base.c b/drivers/input/mouse/psmouse-base.c index 690aed905436..07c53798301a 100644 --- a/drivers/input/mouse/psmouse-base.c +++ b/drivers/input/mouse/psmouse-base.c @@ -581,7 +581,7 @@ static int cortron_detect(struct psmouse *psmouse, bool set_properties) static int psmouse_extensions(struct psmouse *psmouse, unsigned int max_proto, bool set_properties) { - bool synaptics_hardware = true; + bool synaptics_hardware = false; /* * We always check for lifebook because it does not disturb mouse @@ -1673,7 +1673,7 @@ static int psmouse_get_maxproto(char *buffer, struct kernel_param *kp) { int type = *((unsigned int *)kp->arg); - return sprintf(buffer, "%s\n", psmouse_protocol_by_type(type)->name); + return sprintf(buffer, "%s", psmouse_protocol_by_type(type)->name); } static int __init psmouse_init(void) diff --git a/drivers/input/mouse/synaptics.c b/drivers/input/mouse/synaptics.c index b66ff1ac7dea..f4a61252bcc9 100644 --- a/drivers/input/mouse/synaptics.c +++ b/drivers/input/mouse/synaptics.c @@ -652,6 +652,16 @@ static const struct dmi_system_id toshiba_dmi_table[] = { DMI_MATCH(DMI_SYS_VENDOR, "TOSHIBA"), DMI_MATCH(DMI_PRODUCT_NAME, "PORTEGE M300"), }, + + }, + { + .ident = "Toshiba Portege M300", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "TOSHIBA"), + DMI_MATCH(DMI_PRODUCT_NAME, "Portable PC"), + DMI_MATCH(DMI_PRODUCT_VERSION, "Version 1.0"), + }, + }, { } }; diff --git a/drivers/input/serio/Kconfig b/drivers/input/serio/Kconfig index c4b3fbd1a80f..aa533ceffe34 100644 --- a/drivers/input/serio/Kconfig +++ b/drivers/input/serio/Kconfig @@ -4,7 +4,7 @@ config SERIO tristate "Serial I/O support" if EMBEDDED || !X86 default y - ---help--- + help Say Yes here if you have any input device that uses serial I/O to communicate with the system. This includes the * standard AT keyboard and PS/2 mouse * @@ -22,7 +22,7 @@ config SERIO_I8042 tristate "i8042 PC Keyboard controller" if EMBEDDED || !X86 default y depends on !PARISC && (!ARM || ARCH_SHARK || FOOTBRIDGE_HOST) && !M68K && !BLACKFIN - ---help--- + help i8042 is the chip over which the standard AT keyboard and PS/2 mouse are connected to the computer. If you use these devices, you'll need to say Y here. @@ -35,7 +35,7 @@ config SERIO_I8042 config SERIO_SERPORT tristate "Serial port line discipline" default y - ---help--- + help Say Y here if you plan to use an input device (mouse, joystick, tablet, 6dof) that communicates over the RS232 serial (COM) port. @@ -49,7 +49,7 @@ config SERIO_SERPORT config SERIO_CT82C710 tristate "ct82c710 Aux port controller" depends on X86 - ---help--- + help Say Y here if you have a Texas Instruments TravelMate notebook equipped with the ct82c710 chip and want to use a mouse connected to the "QuickPort". @@ -66,7 +66,7 @@ config SERIO_Q40KBD config SERIO_PARKBD tristate "Parallel port keyboard adapter" depends on PARPORT - ---help--- + help Say Y here if you built a simple parallel port adapter to attach an additional AT keyboard, XT keyboard or PS/2 mouse. @@ -124,7 +124,7 @@ config HP_SDC tristate "HP System Device Controller i8042 Support" depends on (GSC || HP300) && SERIO default y - ---help--- + help This option enables support for the "System Device Controller", an i8042 carrying microcode to manage a few miscellaneous devices on some Hewlett Packard systems. @@ -168,6 +168,7 @@ config SERIO_MACEPS2 config SERIO_LIBPS2 tristate "PS/2 driver library" if EMBEDDED + depends on SERIO_I8042 || SERIO_I8042=n help Say Y here if you are using a driver for device connected to a PS/2 port, such as PS/2 mouse or standard AT keyboard. diff --git a/drivers/input/serio/i8042-x86ia64io.h b/drivers/input/serio/i8042-x86ia64io.h index a39bc4eb902b..a537925f7651 100644 --- a/drivers/input/serio/i8042-x86ia64io.h +++ b/drivers/input/serio/i8042-x86ia64io.h @@ -327,6 +327,17 @@ static struct dmi_system_id __initdata i8042_dmi_nomux_table[] = { }, }, { + /* + * Reset and GET ID commands issued via KBD port are + * sometimes being delivered to AUX3. + */ + .ident = "Sony Vaio FZ-240E", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Sony Corporation"), + DMI_MATCH(DMI_PRODUCT_NAME, "VGN-FZ240E"), + }, + }, + { .ident = "Amoi M636/A737", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Amoi Electronics CO.,LTD."), @@ -661,7 +672,7 @@ static void i8042_pnp_exit(void) static int __init i8042_pnp_init(void) { char kbd_irq_str[4] = { 0 }, aux_irq_str[4] = { 0 }; - int pnp_data_busted = false; + bool pnp_data_busted = false; int err; #ifdef CONFIG_X86 diff --git a/drivers/input/serio/i8042.c b/drivers/input/serio/i8042.c index bc56e52b945f..1df02d25aca5 100644 --- a/drivers/input/serio/i8042.c +++ b/drivers/input/serio/i8042.c @@ -609,6 +609,8 @@ static irqreturn_t __init i8042_aux_test_irq(int irq, void *dev_id) str = i8042_read_status(); if (str & I8042_STR_OBF) { data = i8042_read_data(); + dbg("%02x <- i8042 (aux_test_irq, %s)", + data, str & I8042_STR_AUXDATA ? "aux" : "kbd"); if (i8042_irq_being_tested && data == 0xa5 && (str & I8042_STR_AUXDATA)) complete(&i8042_aux_irq_delivered); @@ -750,6 +752,7 @@ static int __init i8042_check_aux(void) * AUX IRQ was never delivered so we need to flush the controller to * get rid of the byte we put there; otherwise keyboard may not work. */ + dbg(" -- i8042 (aux irq test timeout)"); i8042_flush(); retval = -1; } @@ -833,17 +836,32 @@ static int i8042_controller_selftest(void) static int i8042_controller_init(void) { unsigned long flags; + int n = 0; + unsigned char ctr[2]; /* - * Save the CTR for restoral on unload / reboot. + * Save the CTR for restore on unload / reboot. */ - if (i8042_command(&i8042_ctr, I8042_CMD_CTL_RCTR)) { - printk(KERN_ERR "i8042.c: Can't read CTR while initializing i8042.\n"); - return -EIO; - } + do { + if (n >= 10) { + printk(KERN_ERR + "i8042.c: Unable to get stable CTR read.\n"); + return -EIO; + } + + if (n != 0) + udelay(50); + + if (i8042_command(&ctr[n++ % 2], I8042_CMD_CTL_RCTR)) { + printk(KERN_ERR + "i8042.c: Can't read CTR while initializing i8042.\n"); + return -EIO; + } - i8042_initial_ctr = i8042_ctr; + } while (n < 2 || ctr[0] != ctr[1]); + + i8042_initial_ctr = i8042_ctr = ctr[0]; /* * Disable the keyboard interface and interrupt. @@ -892,6 +910,12 @@ static int i8042_controller_init(void) return -EIO; } +/* + * Flush whatever accumulated while we were disabling keyboard port. + */ + + i8042_flush(); + return 0; } @@ -911,7 +935,7 @@ static void i8042_controller_reset(void) i8042_ctr |= I8042_CTR_KBDDIS | I8042_CTR_AUXDIS; i8042_ctr &= ~(I8042_CTR_KBDINT | I8042_CTR_AUXINT); - if (i8042_command(&i8042_initial_ctr, I8042_CMD_CTL_WCTR)) + if (i8042_command(&i8042_ctr, I8042_CMD_CTL_WCTR)) printk(KERN_WARNING "i8042.c: Can't write CTR while resetting.\n"); /* diff --git a/drivers/input/serio/libps2.c b/drivers/input/serio/libps2.c index 769ba65a585a..f3876acc3e83 100644 --- a/drivers/input/serio/libps2.c +++ b/drivers/input/serio/libps2.c @@ -13,6 +13,7 @@ #include <linux/delay.h> #include <linux/module.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/interrupt.h> #include <linux/input.h> diff --git a/drivers/input/serio/serio_raw.c b/drivers/input/serio/serio_raw.c index b03009bb7468..27fdaaffbb40 100644 --- a/drivers/input/serio/serio_raw.c +++ b/drivers/input/serio/serio_raw.c @@ -9,6 +9,7 @@ * the Free Software Foundation. */ +#include <linux/sched.h> #include <linux/slab.h> #include <linux/smp_lock.h> #include <linux/poll.h> diff --git a/drivers/input/serio/serport.c b/drivers/input/serio/serport.c index b9694b6445d0..6d345112bcb7 100644 --- a/drivers/input/serio/serport.c +++ b/drivers/input/serio/serport.c @@ -15,6 +15,7 @@ #include <asm/uaccess.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/module.h> #include <linux/init.h> diff --git a/drivers/input/touchscreen/ad7879.c b/drivers/input/touchscreen/ad7879.c index f06332c9e21b..c21e6d3a8844 100644 --- a/drivers/input/touchscreen/ad7879.c +++ b/drivers/input/touchscreen/ad7879.c @@ -645,7 +645,7 @@ static int __devinit ad7879_probe(struct spi_device *spi) kfree(ts); } - return 0; + return error; } static int __devexit ad7879_remove(struct spi_device *spi) @@ -732,7 +732,7 @@ static int __devinit ad7879_probe(struct i2c_client *client, kfree(ts); } - return 0; + return error; } static int __devexit ad7879_remove(struct i2c_client *client) diff --git a/drivers/isdn/capi/kcapi.c b/drivers/isdn/capi/kcapi.c index 57d26360f64e..dc506ab99cac 100644 --- a/drivers/isdn/capi/kcapi.c +++ b/drivers/isdn/capi/kcapi.c @@ -18,6 +18,7 @@ #include <linux/interrupt.h> #include <linux/ioport.h> #include <linux/proc_fs.h> +#include <linux/sched.h> #include <linux/seq_file.h> #include <linux/skbuff.h> #include <linux/workqueue.h> diff --git a/drivers/isdn/hisax/arcofi.c b/drivers/isdn/hisax/arcofi.c index d30ce5b978c2..85a8fd8dd0b7 100644 --- a/drivers/isdn/hisax/arcofi.c +++ b/drivers/isdn/hisax/arcofi.c @@ -10,6 +10,7 @@ * */ +#include <linux/sched.h> #include "hisax.h" #include "isdnl1.h" #include "isac.h" diff --git a/drivers/isdn/hisax/hfc_2bds0.c b/drivers/isdn/hisax/hfc_2bds0.c index 5c46a7130e06..8d22f50760eb 100644 --- a/drivers/isdn/hisax/hfc_2bds0.c +++ b/drivers/isdn/hisax/hfc_2bds0.c @@ -11,6 +11,7 @@ */ #include <linux/init.h> +#include <linux/sched.h> #include "hisax.h" #include "hfc_2bds0.h" #include "isdnl1.h" diff --git a/drivers/isdn/hisax/hfc_pci.c b/drivers/isdn/hisax/hfc_pci.c index d110a77940a4..10914731b304 100644 --- a/drivers/isdn/hisax/hfc_pci.c +++ b/drivers/isdn/hisax/hfc_pci.c @@ -20,6 +20,7 @@ #include "hfc_pci.h" #include "isdnl1.h" #include <linux/pci.h> +#include <linux/sched.h> #include <linux/interrupt.h> static const char *hfcpci_revision = "$Revision: 1.48.2.4 $"; diff --git a/drivers/isdn/hysdn/hysdn_procconf.c b/drivers/isdn/hysdn/hysdn_procconf.c index 8f9f4912de32..90b35e1a4b7e 100644 --- a/drivers/isdn/hysdn/hysdn_procconf.c +++ b/drivers/isdn/hysdn/hysdn_procconf.c @@ -11,6 +11,7 @@ * */ +#include <linux/cred.h> #include <linux/module.h> #include <linux/poll.h> #include <linux/proc_fs.h> diff --git a/drivers/isdn/hysdn/hysdn_proclog.c b/drivers/isdn/hysdn/hysdn_proclog.c index 8991d2c8ee4a..8bcae28c4409 100644 --- a/drivers/isdn/hysdn/hysdn_proclog.c +++ b/drivers/isdn/hysdn/hysdn_proclog.c @@ -13,6 +13,7 @@ #include <linux/module.h> #include <linux/poll.h> #include <linux/proc_fs.h> +#include <linux/sched.h> #include <linux/smp_lock.h> #include "hysdn_defs.h" diff --git a/drivers/isdn/pcbit/drv.c b/drivers/isdn/pcbit/drv.c index 8c66bcb953a1..123c1d6c43b4 100644 --- a/drivers/isdn/pcbit/drv.c +++ b/drivers/isdn/pcbit/drv.c @@ -23,6 +23,7 @@ #include <linux/kernel.h> #include <linux/types.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/mm.h> #include <linux/interrupt.h> diff --git a/drivers/isdn/pcbit/layer2.c b/drivers/isdn/pcbit/layer2.c index e075e8d2fce0..30f0f45e3139 100644 --- a/drivers/isdn/pcbit/layer2.c +++ b/drivers/isdn/pcbit/layer2.c @@ -27,6 +27,7 @@ #include <linux/string.h> #include <linux/kernel.h> #include <linux/types.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/interrupt.h> #include <linux/workqueue.h> diff --git a/drivers/isdn/sc/init.c b/drivers/isdn/sc/init.c index dd0acd06750b..5a0774880d56 100644 --- a/drivers/isdn/sc/init.c +++ b/drivers/isdn/sc/init.c @@ -8,6 +8,7 @@ #include <linux/init.h> #include <linux/interrupt.h> #include <linux/delay.h> +#include <linux/sched.h> #include "includes.h" #include "hardware.h" #include "card.h" diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c index 7467980b8cf9..e5225d28f392 100644 --- a/drivers/leds/leds-gpio.c +++ b/drivers/leds/leds-gpio.c @@ -78,6 +78,8 @@ static int __devinit create_gpio_led(const struct gpio_led *template, { int ret, state; + led_dat->gpio = -1; + /* skip leds that aren't available */ if (!gpio_is_valid(template->gpio)) { printk(KERN_INFO "Skipping unavailable LED gpio %d (%s)\n", diff --git a/drivers/lguest/interrupts_and_traps.c b/drivers/lguest/interrupts_and_traps.c index 18648180db02..daaf86631647 100644 --- a/drivers/lguest/interrupts_and_traps.c +++ b/drivers/lguest/interrupts_and_traps.c @@ -16,6 +16,7 @@ #include <linux/uaccess.h> #include <linux/interrupt.h> #include <linux/module.h> +#include <linux/sched.h> #include "lg.h" /* Allow Guests to use a non-128 (ie. non-Linux) syscall trap. */ diff --git a/drivers/macintosh/via-pmu.c b/drivers/macintosh/via-pmu.c index b40fb9b6c862..6f308a4757ee 100644 --- a/drivers/macintosh/via-pmu.c +++ b/drivers/macintosh/via-pmu.c @@ -405,7 +405,11 @@ static int __init via_pmu_start(void) printk(KERN_ERR "via-pmu: can't map interrupt\n"); return -ENODEV; } - if (request_irq(irq, via_pmu_interrupt, 0, "VIA-PMU", (void *)0)) { + /* We set IRQF_TIMER because we don't want the interrupt to be disabled + * between the 2 passes of driver suspend, we control our own disabling + * for that one + */ + if (request_irq(irq, via_pmu_interrupt, IRQF_TIMER, "VIA-PMU", (void *)0)) { printk(KERN_ERR "via-pmu: can't request irq %d\n", irq); return -ENODEV; } @@ -419,7 +423,7 @@ static int __init via_pmu_start(void) gpio_irq = irq_of_parse_and_map(gpio_node, 0); if (gpio_irq != NO_IRQ) { - if (request_irq(gpio_irq, gpio1_interrupt, 0, + if (request_irq(gpio_irq, gpio1_interrupt, IRQF_TIMER, "GPIO1 ADB", (void *)0)) printk(KERN_ERR "pmu: can't get irq %d" " (GPIO1)\n", gpio_irq); @@ -925,8 +929,7 @@ proc_write_options(struct file *file, const char __user *buffer, #ifdef CONFIG_ADB /* Send an ADB command */ -static int -pmu_send_request(struct adb_request *req, int sync) +static int pmu_send_request(struct adb_request *req, int sync) { int i, ret; @@ -1005,16 +1008,11 @@ pmu_send_request(struct adb_request *req, int sync) } /* Enable/disable autopolling */ -static int -pmu_adb_autopoll(int devs) +static int __pmu_adb_autopoll(int devs) { struct adb_request req; - if ((vias == NULL) || (!pmu_fully_inited) || !pmu_has_adb) - return -ENXIO; - if (devs) { - adb_dev_map = devs; pmu_request(&req, NULL, 5, PMU_ADB_CMD, 0, 0x86, adb_dev_map >> 8, adb_dev_map); pmu_adb_flags = 2; @@ -1027,9 +1025,17 @@ pmu_adb_autopoll(int devs) return 0; } +static int pmu_adb_autopoll(int devs) +{ + if ((vias == NULL) || (!pmu_fully_inited) || !pmu_has_adb) + return -ENXIO; + + adb_dev_map = devs; + return __pmu_adb_autopoll(devs); +} + /* Reset the ADB bus */ -static int -pmu_adb_reset_bus(void) +static int pmu_adb_reset_bus(void) { struct adb_request req; int save_autopoll = adb_dev_map; @@ -1038,13 +1044,13 @@ pmu_adb_reset_bus(void) return -ENXIO; /* anyone got a better idea?? */ - pmu_adb_autopoll(0); + __pmu_adb_autopoll(0); - req.nbytes = 5; + req.nbytes = 4; req.done = NULL; req.data[0] = PMU_ADB_CMD; - req.data[1] = 0; - req.data[2] = ADB_BUSRESET; + req.data[1] = ADB_BUSRESET; + req.data[2] = 0; req.data[3] = 0; req.data[4] = 0; req.reply_len = 0; @@ -1056,7 +1062,7 @@ pmu_adb_reset_bus(void) pmu_wait_complete(&req); if (save_autopoll != 0) - pmu_adb_autopoll(save_autopoll); + __pmu_adb_autopoll(save_autopoll); return 0; } diff --git a/drivers/md/Makefile b/drivers/md/Makefile index 1dc4185bd781..e355e7f6a536 100644 --- a/drivers/md/Makefile +++ b/drivers/md/Makefile @@ -46,7 +46,7 @@ obj-$(CONFIG_DM_LOG_USERSPACE) += dm-log-userspace.o obj-$(CONFIG_DM_ZERO) += dm-zero.o quiet_cmd_unroll = UNROLL $@ - cmd_unroll = $(PERL) $(srctree)/$(src)/unroll.pl $(UNROLL) \ + cmd_unroll = $(AWK) -f$(srctree)/$(src)/unroll.awk -vN=$(UNROLL) \ < $< > $@ || ( rm -f $@ && exit 1 ) ifeq ($(CONFIG_ALTIVEC),y) @@ -59,56 +59,56 @@ endif targets += raid6int1.c $(obj)/raid6int1.c: UNROLL := 1 -$(obj)/raid6int1.c: $(src)/raid6int.uc $(src)/unroll.pl FORCE +$(obj)/raid6int1.c: $(src)/raid6int.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) targets += raid6int2.c $(obj)/raid6int2.c: UNROLL := 2 -$(obj)/raid6int2.c: $(src)/raid6int.uc $(src)/unroll.pl FORCE +$(obj)/raid6int2.c: $(src)/raid6int.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) targets += raid6int4.c $(obj)/raid6int4.c: UNROLL := 4 -$(obj)/raid6int4.c: $(src)/raid6int.uc $(src)/unroll.pl FORCE +$(obj)/raid6int4.c: $(src)/raid6int.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) targets += raid6int8.c $(obj)/raid6int8.c: UNROLL := 8 -$(obj)/raid6int8.c: $(src)/raid6int.uc $(src)/unroll.pl FORCE +$(obj)/raid6int8.c: $(src)/raid6int.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) targets += raid6int16.c $(obj)/raid6int16.c: UNROLL := 16 -$(obj)/raid6int16.c: $(src)/raid6int.uc $(src)/unroll.pl FORCE +$(obj)/raid6int16.c: $(src)/raid6int.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) targets += raid6int32.c $(obj)/raid6int32.c: UNROLL := 32 -$(obj)/raid6int32.c: $(src)/raid6int.uc $(src)/unroll.pl FORCE +$(obj)/raid6int32.c: $(src)/raid6int.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) CFLAGS_raid6altivec1.o += $(altivec_flags) targets += raid6altivec1.c $(obj)/raid6altivec1.c: UNROLL := 1 -$(obj)/raid6altivec1.c: $(src)/raid6altivec.uc $(src)/unroll.pl FORCE +$(obj)/raid6altivec1.c: $(src)/raid6altivec.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) CFLAGS_raid6altivec2.o += $(altivec_flags) targets += raid6altivec2.c $(obj)/raid6altivec2.c: UNROLL := 2 -$(obj)/raid6altivec2.c: $(src)/raid6altivec.uc $(src)/unroll.pl FORCE +$(obj)/raid6altivec2.c: $(src)/raid6altivec.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) CFLAGS_raid6altivec4.o += $(altivec_flags) targets += raid6altivec4.c $(obj)/raid6altivec4.c: UNROLL := 4 -$(obj)/raid6altivec4.c: $(src)/raid6altivec.uc $(src)/unroll.pl FORCE +$(obj)/raid6altivec4.c: $(src)/raid6altivec.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) CFLAGS_raid6altivec8.o += $(altivec_flags) targets += raid6altivec8.c $(obj)/raid6altivec8.c: UNROLL := 8 -$(obj)/raid6altivec8.c: $(src)/raid6altivec.uc $(src)/unroll.pl FORCE +$(obj)/raid6altivec8.c: $(src)/raid6altivec.uc $(src)/unroll.awk FORCE $(call if_changed,unroll) quiet_cmd_mktable = TABLE $@ diff --git a/drivers/md/bitmap.c b/drivers/md/bitmap.c index 6986b0059d23..60e2b322db11 100644 --- a/drivers/md/bitmap.c +++ b/drivers/md/bitmap.c @@ -1624,10 +1624,11 @@ int bitmap_create(mddev_t *mddev) bitmap->offset = mddev->bitmap_offset; if (file) { get_file(file); - do_sync_mapping_range(file->f_mapping, 0, LLONG_MAX, - SYNC_FILE_RANGE_WAIT_BEFORE | - SYNC_FILE_RANGE_WRITE | - SYNC_FILE_RANGE_WAIT_AFTER); + /* As future accesses to this file will use bmap, + * and bypass the page cache, we must sync the file + * first. + */ + vfs_fsync(file, file->f_dentry, 1); } /* read superblock from bitmap file (this sets bitmap->chunksize) */ err = bitmap_read_sb(bitmap); diff --git a/drivers/md/dm-exception-store.c b/drivers/md/dm-exception-store.c index 556acff3952f..7dbe652efb5a 100644 --- a/drivers/md/dm-exception-store.c +++ b/drivers/md/dm-exception-store.c @@ -138,16 +138,6 @@ int dm_exception_store_type_unregister(struct dm_exception_store_type *type) } EXPORT_SYMBOL(dm_exception_store_type_unregister); -/* - * Round a number up to the nearest 'size' boundary. size must - * be a power of 2. - */ -static ulong round_up(ulong n, ulong size) -{ - size--; - return (n + size) & ~size; -} - static int set_chunk_size(struct dm_exception_store *store, const char *chunk_size_arg, char **error) { @@ -155,7 +145,8 @@ static int set_chunk_size(struct dm_exception_store *store, char *value; chunk_size_ulong = simple_strtoul(chunk_size_arg, &value, 10); - if (*chunk_size_arg == '\0' || *value != '\0') { + if (*chunk_size_arg == '\0' || *value != '\0' || + chunk_size_ulong > UINT_MAX) { *error = "Invalid chunk size"; return -EINVAL; } @@ -165,40 +156,35 @@ static int set_chunk_size(struct dm_exception_store *store, return 0; } - /* - * Chunk size must be multiple of page size. Silently - * round up if it's not. - */ - chunk_size_ulong = round_up(chunk_size_ulong, PAGE_SIZE >> 9); - - return dm_exception_store_set_chunk_size(store, chunk_size_ulong, + return dm_exception_store_set_chunk_size(store, + (unsigned) chunk_size_ulong, error); } int dm_exception_store_set_chunk_size(struct dm_exception_store *store, - unsigned long chunk_size_ulong, + unsigned chunk_size, char **error) { /* Check chunk_size is a power of 2 */ - if (!is_power_of_2(chunk_size_ulong)) { + if (!is_power_of_2(chunk_size)) { *error = "Chunk size is not a power of 2"; return -EINVAL; } /* Validate the chunk size against the device block size */ - if (chunk_size_ulong % (bdev_logical_block_size(store->cow->bdev) >> 9)) { + if (chunk_size % (bdev_logical_block_size(store->cow->bdev) >> 9)) { *error = "Chunk size is not a multiple of device blocksize"; return -EINVAL; } - if (chunk_size_ulong > INT_MAX >> SECTOR_SHIFT) { + if (chunk_size > INT_MAX >> SECTOR_SHIFT) { *error = "Chunk size is too high"; return -EINVAL; } - store->chunk_size = chunk_size_ulong; - store->chunk_mask = chunk_size_ulong - 1; - store->chunk_shift = ffs(chunk_size_ulong) - 1; + store->chunk_size = chunk_size; + store->chunk_mask = chunk_size - 1; + store->chunk_shift = ffs(chunk_size) - 1; return 0; } @@ -251,7 +237,7 @@ int dm_exception_store_create(struct dm_target *ti, int argc, char **argv, r = set_chunk_size(tmp_store, argv[2], &ti->error); if (r) - goto bad_cow; + goto bad_ctr; r = type->ctr(tmp_store, 0, NULL); if (r) { diff --git a/drivers/md/dm-exception-store.h b/drivers/md/dm-exception-store.h index 812c71872ba0..8a223a48802c 100644 --- a/drivers/md/dm-exception-store.h +++ b/drivers/md/dm-exception-store.h @@ -101,9 +101,9 @@ struct dm_exception_store { struct dm_dev *cow; /* Size of data blocks saved - must be a power of 2 */ - chunk_t chunk_size; - chunk_t chunk_mask; - chunk_t chunk_shift; + unsigned chunk_size; + unsigned chunk_mask; + unsigned chunk_shift; void *context; }; @@ -169,7 +169,7 @@ int dm_exception_store_type_register(struct dm_exception_store_type *type); int dm_exception_store_type_unregister(struct dm_exception_store_type *type); int dm_exception_store_set_chunk_size(struct dm_exception_store *store, - unsigned long chunk_size_ulong, + unsigned chunk_size, char **error); int dm_exception_store_create(struct dm_target *ti, int argc, char **argv, diff --git a/drivers/md/dm-log-userspace-base.c b/drivers/md/dm-log-userspace-base.c index 652bd33109e3..7ac2c1450d10 100644 --- a/drivers/md/dm-log-userspace-base.c +++ b/drivers/md/dm-log-userspace-base.c @@ -156,7 +156,7 @@ static int userspace_ctr(struct dm_dirty_log *log, struct dm_target *ti, } /* The ptr value is sufficient for local unique id */ - lc->luid = (uint64_t)lc; + lc->luid = (unsigned long)lc; lc->ti = ti; diff --git a/drivers/md/dm-snap-persistent.c b/drivers/md/dm-snap-persistent.c index d5b2e08750d5..0c746420c008 100644 --- a/drivers/md/dm-snap-persistent.c +++ b/drivers/md/dm-snap-persistent.c @@ -284,12 +284,13 @@ static int read_header(struct pstore *ps, int *new_snapshot) { int r; struct disk_header *dh; - chunk_t chunk_size; + unsigned chunk_size; int chunk_size_supplied = 1; char *chunk_err; /* - * Use default chunk size (or hardsect_size, if larger) if none supplied + * Use default chunk size (or logical_block_size, if larger) + * if none supplied */ if (!ps->store->chunk_size) { ps->store->chunk_size = max(DM_CHUNK_SIZE_DEFAULT_SECTORS, @@ -334,10 +335,9 @@ static int read_header(struct pstore *ps, int *new_snapshot) return 0; if (chunk_size_supplied) - DMWARN("chunk size %llu in device metadata overrides " - "table chunk size of %llu.", - (unsigned long long)chunk_size, - (unsigned long long)ps->store->chunk_size); + DMWARN("chunk size %u in device metadata overrides " + "table chunk size of %u.", + chunk_size, ps->store->chunk_size); /* We had a bogus chunk_size. Fix stuff up. */ free_area(ps); @@ -345,8 +345,8 @@ static int read_header(struct pstore *ps, int *new_snapshot) r = dm_exception_store_set_chunk_size(ps->store, chunk_size, &chunk_err); if (r) { - DMERR("invalid on-disk chunk size %llu: %s.", - (unsigned long long)chunk_size, chunk_err); + DMERR("invalid on-disk chunk size %u: %s.", + chunk_size, chunk_err); return r; } diff --git a/drivers/md/dm-snap.c b/drivers/md/dm-snap.c index 57f1bf7f3b7a..3a3ba46e6d4b 100644 --- a/drivers/md/dm-snap.c +++ b/drivers/md/dm-snap.c @@ -296,6 +296,7 @@ static void __insert_origin(struct origin *o) */ static int register_snapshot(struct dm_snapshot *snap) { + struct dm_snapshot *l; struct origin *o, *new_o; struct block_device *bdev = snap->origin->bdev; @@ -319,7 +320,11 @@ static int register_snapshot(struct dm_snapshot *snap) __insert_origin(o); } - list_add_tail(&snap->list, &o->snapshots); + /* Sort the list according to chunk size, largest-first smallest-last */ + list_for_each_entry(l, &o->snapshots, list) + if (l->store->chunk_size < snap->store->chunk_size) + break; + list_add_tail(&snap->list, &l->list); up_write(&_origins_lock); return 0; @@ -668,6 +673,11 @@ static int snapshot_ctr(struct dm_target *ti, unsigned int argc, char **argv) bio_list_init(&s->queued_bios); INIT_WORK(&s->queued_bios_work, flush_queued_bios); + if (!s->store->chunk_size) { + ti->error = "Chunk size not set"; + goto bad_load_and_register; + } + /* Add snapshot to the list of snapshots for this origin */ /* Exceptions aren't triggered till snapshot_resume() is called */ if (register_snapshot(s)) { @@ -951,7 +961,7 @@ static void start_copy(struct dm_snap_pending_exception *pe) src.bdev = bdev; src.sector = chunk_to_sector(s->store, pe->e.old_chunk); - src.count = min(s->store->chunk_size, dev_size - src.sector); + src.count = min((sector_t)s->store->chunk_size, dev_size - src.sector); dest.bdev = s->store->cow->bdev; dest.sector = chunk_to_sector(s->store, pe->e.new_chunk); @@ -1142,6 +1152,8 @@ static int snapshot_status(struct dm_target *ti, status_type_t type, unsigned sz = 0; struct dm_snapshot *snap = ti->private; + down_write(&snap->lock); + switch (type) { case STATUSTYPE_INFO: if (!snap->valid) @@ -1173,6 +1185,8 @@ static int snapshot_status(struct dm_target *ti, status_type_t type, break; } + up_write(&snap->lock); + return 0; } @@ -1388,7 +1402,7 @@ static void origin_resume(struct dm_target *ti) struct dm_dev *dev = ti->private; struct dm_snapshot *snap; struct origin *o; - chunk_t chunk_size = 0; + unsigned chunk_size = 0; down_read(&_origins_lock); o = __lookup_origin(dev->bdev); @@ -1465,7 +1479,7 @@ static int __init dm_snapshot_init(void) r = dm_register_target(&snapshot_target); if (r) { DMERR("snapshot target register failed %d", r); - return r; + goto bad_register_snapshot_target; } r = dm_register_target(&origin_target); @@ -1522,6 +1536,9 @@ bad2: dm_unregister_target(&origin_target); bad1: dm_unregister_target(&snapshot_target); + +bad_register_snapshot_target: + dm_exception_store_exit(); return r; } diff --git a/drivers/md/dm.c b/drivers/md/dm.c index 23e76fe0d359..724efc63904d 100644 --- a/drivers/md/dm.c +++ b/drivers/md/dm.c @@ -47,6 +47,7 @@ struct dm_io { atomic_t io_count; struct bio *bio; unsigned long start_time; + spinlock_t endio_lock; }; /* @@ -130,7 +131,7 @@ struct mapped_device { /* * A list of ios that arrived while we were suspended. */ - atomic_t pending; + atomic_t pending[2]; wait_queue_head_t wait; struct work_struct work; struct bio_list deferred; @@ -453,13 +454,14 @@ static void start_io_acct(struct dm_io *io) { struct mapped_device *md = io->md; int cpu; + int rw = bio_data_dir(io->bio); io->start_time = jiffies; cpu = part_stat_lock(); part_round_stats(cpu, &dm_disk(md)->part0); part_stat_unlock(); - dm_disk(md)->part0.in_flight = atomic_inc_return(&md->pending); + dm_disk(md)->part0.in_flight[rw] = atomic_inc_return(&md->pending[rw]); } static void end_io_acct(struct dm_io *io) @@ -479,8 +481,9 @@ static void end_io_acct(struct dm_io *io) * After this is decremented the bio must not be touched if it is * a barrier. */ - dm_disk(md)->part0.in_flight = pending = - atomic_dec_return(&md->pending); + dm_disk(md)->part0.in_flight[rw] = pending = + atomic_dec_return(&md->pending[rw]); + pending += atomic_read(&md->pending[rw^0x1]); /* nudge anyone waiting on suspend queue */ if (!pending) @@ -576,8 +579,12 @@ static void dec_pending(struct dm_io *io, int error) struct mapped_device *md = io->md; /* Push-back supersedes any I/O errors */ - if (error && !(io->error > 0 && __noflush_suspending(md))) - io->error = error; + if (unlikely(error)) { + spin_lock_irqsave(&io->endio_lock, flags); + if (!(io->error > 0 && __noflush_suspending(md))) + io->error = error; + spin_unlock_irqrestore(&io->endio_lock, flags); + } if (atomic_dec_and_test(&io->io_count)) { if (io->error == DM_ENDIO_REQUEUE) { @@ -1224,6 +1231,7 @@ static void __split_and_process_bio(struct mapped_device *md, struct bio *bio) atomic_set(&ci.io->io_count, 1); ci.io->bio = bio; ci.io->md = md; + spin_lock_init(&ci.io->endio_lock); ci.sector = bio->bi_sector; ci.sector_count = bio_sectors(bio); if (unlikely(bio_empty_barrier(bio))) @@ -1785,7 +1793,8 @@ static struct mapped_device *alloc_dev(int minor) if (!md->disk) goto bad_disk; - atomic_set(&md->pending, 0); + atomic_set(&md->pending[0], 0); + atomic_set(&md->pending[1], 0); init_waitqueue_head(&md->wait); INIT_WORK(&md->work, dm_wq_work); init_waitqueue_head(&md->eventq); @@ -1819,6 +1828,7 @@ static struct mapped_device *alloc_dev(int minor) bad_bdev: destroy_workqueue(md->wq); bad_thread: + del_gendisk(md->disk); put_disk(md->disk); bad_disk: blk_cleanup_queue(md->queue); @@ -2088,7 +2098,8 @@ static int dm_wait_for_completion(struct mapped_device *md, int interruptible) break; } spin_unlock_irqrestore(q->queue_lock, flags); - } else if (!atomic_read(&md->pending)) + } else if (!atomic_read(&md->pending[0]) && + !atomic_read(&md->pending[1])) break; if (interruptible == TASK_INTERRUPTIBLE && diff --git a/drivers/md/md.c b/drivers/md/md.c index 26ba42a79129..b182f86a19dd 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c @@ -944,6 +944,14 @@ static int super_90_validate(mddev_t *mddev, mdk_rdev_t *rdev) desc->raid_disk < mddev->raid_disks */) { set_bit(In_sync, &rdev->flags); rdev->raid_disk = desc->raid_disk; + } else if (desc->state & (1<<MD_DISK_ACTIVE)) { + /* active but not in sync implies recovery up to + * reshape position. We don't know exactly where + * that is, so set to zero for now */ + if (mddev->minor_version >= 91) { + rdev->recovery_offset = 0; + rdev->raid_disk = desc->raid_disk; + } } if (desc->state & (1<<MD_DISK_WRITEMOSTLY)) set_bit(WriteMostly, &rdev->flags); @@ -1032,8 +1040,19 @@ static void super_90_sync(mddev_t *mddev, mdk_rdev_t *rdev) list_for_each_entry(rdev2, &mddev->disks, same_set) { mdp_disk_t *d; int desc_nr; - if (rdev2->raid_disk >= 0 && test_bit(In_sync, &rdev2->flags) - && !test_bit(Faulty, &rdev2->flags)) + int is_active = test_bit(In_sync, &rdev2->flags); + + if (rdev2->raid_disk >= 0 && + sb->minor_version >= 91) + /* we have nowhere to store the recovery_offset, + * but if it is not below the reshape_position, + * we can piggy-back on that. + */ + is_active = 1; + if (rdev2->raid_disk < 0 || + test_bit(Faulty, &rdev2->flags)) + is_active = 0; + if (is_active) desc_nr = rdev2->raid_disk; else desc_nr = next_spare++; @@ -1043,16 +1062,16 @@ static void super_90_sync(mddev_t *mddev, mdk_rdev_t *rdev) d->number = rdev2->desc_nr; d->major = MAJOR(rdev2->bdev->bd_dev); d->minor = MINOR(rdev2->bdev->bd_dev); - if (rdev2->raid_disk >= 0 && test_bit(In_sync, &rdev2->flags) - && !test_bit(Faulty, &rdev2->flags)) + if (is_active) d->raid_disk = rdev2->raid_disk; else d->raid_disk = rdev2->desc_nr; /* compatibility */ if (test_bit(Faulty, &rdev2->flags)) d->state = (1<<MD_DISK_FAULTY); - else if (test_bit(In_sync, &rdev2->flags)) { + else if (is_active) { d->state = (1<<MD_DISK_ACTIVE); - d->state |= (1<<MD_DISK_SYNC); + if (test_bit(In_sync, &rdev2->flags)) + d->state |= (1<<MD_DISK_SYNC); active++; working++; } else { @@ -1382,8 +1401,6 @@ static void super_1_sync(mddev_t *mddev, mdk_rdev_t *rdev) if (rdev->raid_disk >= 0 && !test_bit(In_sync, &rdev->flags)) { - if (mddev->curr_resync_completed > rdev->recovery_offset) - rdev->recovery_offset = mddev->curr_resync_completed; if (rdev->recovery_offset > 0) { sb->feature_map |= cpu_to_le32(MD_FEATURE_RECOVERY_OFFSET); @@ -1917,6 +1934,14 @@ static void sync_sbs(mddev_t * mddev, int nospares) */ mdk_rdev_t *rdev; + /* First make sure individual recovery_offsets are correct */ + list_for_each_entry(rdev, &mddev->disks, same_set) { + if (rdev->raid_disk >= 0 && + !test_bit(In_sync, &rdev->flags) && + mddev->curr_resync_completed > rdev->recovery_offset) + rdev->recovery_offset = mddev->curr_resync_completed; + + } list_for_each_entry(rdev, &mddev->disks, same_set) { if (rdev->sb_events == mddev->events || (nospares && @@ -2631,7 +2656,7 @@ static void analyze_sbs(mddev_t * mddev) rdev->desc_nr = i++; rdev->raid_disk = rdev->desc_nr; set_bit(In_sync, &rdev->flags); - } else if (rdev->raid_disk >= mddev->raid_disks) { + } else if (rdev->raid_disk >= (mddev->raid_disks - min(0, mddev->delta_disks))) { rdev->raid_disk = -1; clear_bit(In_sync, &rdev->flags); } @@ -6504,8 +6529,9 @@ void md_do_sync(mddev_t *mddev) skip: mddev->curr_resync = 0; mddev->curr_resync_completed = 0; - mddev->resync_min = 0; - mddev->resync_max = MaxSector; + if (!test_bit(MD_RECOVERY_INTR, &mddev->recovery)) + /* We completed so max setting can be forgotten. */ + mddev->resync_max = MaxSector; sysfs_notify(&mddev->kobj, NULL, "sync_completed"); wake_up(&resync_wait); set_bit(MD_RECOVERY_DONE, &mddev->recovery); diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c index d1b9bd5fd4f6..a053423785c9 100644 --- a/drivers/md/raid1.c +++ b/drivers/md/raid1.c @@ -64,7 +64,7 @@ static void * r1bio_pool_alloc(gfp_t gfp_flags, void *data) /* allocate a r1bio with room for raid_disks entries in the bios array */ r1_bio = kzalloc(size, gfp_flags); - if (!r1_bio) + if (!r1_bio && pi->mddev) unplug_slaves(pi->mddev); return r1_bio; @@ -1683,6 +1683,7 @@ static void raid1d(mddev_t *mddev) generic_make_request(bio); } } + cond_resched(); } if (unplug) unplug_slaves(mddev); @@ -1978,13 +1979,14 @@ static int run(mddev_t *mddev) conf->poolinfo = kmalloc(sizeof(*conf->poolinfo), GFP_KERNEL); if (!conf->poolinfo) goto out_no_mem; - conf->poolinfo->mddev = mddev; + conf->poolinfo->mddev = NULL; conf->poolinfo->raid_disks = mddev->raid_disks; conf->r1bio_pool = mempool_create(NR_RAID1_BIOS, r1bio_pool_alloc, r1bio_pool_free, conf->poolinfo); if (!conf->r1bio_pool) goto out_no_mem; + conf->poolinfo->mddev = mddev; spin_lock_init(&conf->device_lock); mddev->queue->queue_lock = &conf->device_lock; diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c index 51c4c5c4d87a..c2cb7b87b440 100644 --- a/drivers/md/raid10.c +++ b/drivers/md/raid10.c @@ -68,7 +68,7 @@ static void * r10bio_pool_alloc(gfp_t gfp_flags, void *data) /* allocate a r10bio with room for raid_disks entries in the bios array */ r10_bio = kzalloc(size, gfp_flags); - if (!r10_bio) + if (!r10_bio && conf->mddev) unplug_slaves(conf->mddev); return r10_bio; @@ -1632,6 +1632,7 @@ static void raid10d(mddev_t *mddev) generic_make_request(bio); } } + cond_resched(); } if (unplug) unplug_slaves(mddev); @@ -2095,7 +2096,6 @@ static int run(mddev_t *mddev) if (!conf->tmppage) goto out_free_conf; - conf->mddev = mddev; conf->raid_disks = mddev->raid_disks; conf->near_copies = nc; conf->far_copies = fc; @@ -2132,6 +2132,7 @@ static int run(mddev_t *mddev) goto out_free_conf; } + conf->mddev = mddev; spin_lock_init(&conf->device_lock); mddev->queue->queue_lock = &conf->device_lock; diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c index 94829804ab7f..d29215d966da 100644 --- a/drivers/md/raid5.c +++ b/drivers/md/raid5.c @@ -156,13 +156,16 @@ static inline int raid6_next_disk(int disk, int raid_disks) static int raid6_idx_to_slot(int idx, struct stripe_head *sh, int *count, int syndrome_disks) { - int slot; + int slot = *count; + if (sh->ddf_layout) + (*count)++; if (idx == sh->pd_idx) return syndrome_disks; if (idx == sh->qd_idx) return syndrome_disks + 1; - slot = (*count)++; + if (!sh->ddf_layout) + (*count)++; return slot; } @@ -717,7 +720,7 @@ static int set_syndrome_sources(struct page **srcs, struct stripe_head *sh) int i; for (i = 0; i < disks; i++) - srcs[i] = (void *)raid6_empty_zero_page; + srcs[i] = NULL; count = 0; i = d0_idx; @@ -727,9 +730,8 @@ static int set_syndrome_sources(struct page **srcs, struct stripe_head *sh) srcs[slot] = sh->dev[i].page; i = raid6_next_disk(i, disks); } while (i != d0_idx); - BUG_ON(count != syndrome_disks); - return count; + return syndrome_disks; } static struct dma_async_tx_descriptor * @@ -814,7 +816,7 @@ ops_run_compute6_2(struct stripe_head *sh, struct raid5_percpu *percpu) * slot number conversion for 'faila' and 'failb' */ for (i = 0; i < disks ; i++) - blocks[i] = (void *)raid6_empty_zero_page; + blocks[i] = NULL; count = 0; i = d0_idx; do { @@ -828,7 +830,6 @@ ops_run_compute6_2(struct stripe_head *sh, struct raid5_percpu *percpu) failb = slot; i = raid6_next_disk(i, disks); } while (i != d0_idx); - BUG_ON(count != syndrome_disks); BUG_ON(faila == failb); if (failb < faila) @@ -845,7 +846,7 @@ ops_run_compute6_2(struct stripe_head *sh, struct raid5_percpu *percpu) init_async_submit(&submit, ASYNC_TX_FENCE, NULL, ops_complete_compute, sh, to_addr_conv(sh, percpu)); - return async_gen_syndrome(blocks, 0, count+2, + return async_gen_syndrome(blocks, 0, syndrome_disks+2, STRIPE_SIZE, &submit); } else { struct page *dest; @@ -1139,7 +1140,7 @@ static void ops_run_check_pq(struct stripe_head *sh, struct raid5_percpu *percpu &sh->ops.zero_sum_result, percpu->spare_page, &submit); } -static void raid_run_ops(struct stripe_head *sh, unsigned long ops_request) +static void __raid_run_ops(struct stripe_head *sh, unsigned long ops_request) { int overlap_clear = 0, i, disks = sh->disks; struct dma_async_tx_descriptor *tx = NULL; @@ -1204,22 +1205,55 @@ static void raid_run_ops(struct stripe_head *sh, unsigned long ops_request) put_cpu(); } +#ifdef CONFIG_MULTICORE_RAID456 +static void async_run_ops(void *param, async_cookie_t cookie) +{ + struct stripe_head *sh = param; + unsigned long ops_request = sh->ops.request; + + clear_bit_unlock(STRIPE_OPS_REQ_PENDING, &sh->state); + wake_up(&sh->ops.wait_for_ops); + + __raid_run_ops(sh, ops_request); + release_stripe(sh); +} + +static void raid_run_ops(struct stripe_head *sh, unsigned long ops_request) +{ + /* since handle_stripe can be called outside of raid5d context + * we need to ensure sh->ops.request is de-staged before another + * request arrives + */ + wait_event(sh->ops.wait_for_ops, + !test_and_set_bit_lock(STRIPE_OPS_REQ_PENDING, &sh->state)); + sh->ops.request = ops_request; + + atomic_inc(&sh->count); + async_schedule(async_run_ops, sh); +} +#else +#define raid_run_ops __raid_run_ops +#endif + static int grow_one_stripe(raid5_conf_t *conf) { struct stripe_head *sh; + int disks = max(conf->raid_disks, conf->previous_raid_disks); sh = kmem_cache_alloc(conf->slab_cache, GFP_KERNEL); if (!sh) return 0; - memset(sh, 0, sizeof(*sh) + (conf->raid_disks-1)*sizeof(struct r5dev)); + memset(sh, 0, sizeof(*sh) + (disks-1)*sizeof(struct r5dev)); sh->raid_conf = conf; spin_lock_init(&sh->lock); + #ifdef CONFIG_MULTICORE_RAID456 + init_waitqueue_head(&sh->ops.wait_for_ops); + #endif - if (grow_buffers(sh, conf->raid_disks)) { - shrink_buffers(sh, conf->raid_disks); + if (grow_buffers(sh, disks)) { + shrink_buffers(sh, disks); kmem_cache_free(conf->slab_cache, sh); return 0; } - sh->disks = conf->raid_disks; /* we just created an active stripe so... */ atomic_set(&sh->count, 1); atomic_inc(&conf->active_stripes); @@ -1231,7 +1265,7 @@ static int grow_one_stripe(raid5_conf_t *conf) static int grow_stripes(raid5_conf_t *conf, int num) { struct kmem_cache *sc; - int devs = conf->raid_disks; + int devs = max(conf->raid_disks, conf->previous_raid_disks); sprintf(conf->cache_name[0], "raid%d-%s", conf->level, mdname(conf->mddev)); @@ -1329,6 +1363,9 @@ static int resize_stripes(raid5_conf_t *conf, int newsize) nsh->raid_conf = conf; spin_lock_init(&nsh->lock); + #ifdef CONFIG_MULTICORE_RAID456 + init_waitqueue_head(&nsh->ops.wait_for_ops); + #endif list_add(&nsh->lru, &newstripes); } @@ -1899,10 +1936,15 @@ static sector_t compute_blocknr(struct stripe_head *sh, int i, int previous) case ALGORITHM_PARITY_N: break; case ALGORITHM_ROTATING_N_CONTINUE: + /* Like left_symmetric, but P is before Q */ if (sh->pd_idx == 0) i--; /* P D D D Q */ - else if (i > sh->pd_idx) - i -= 2; /* D D Q P D */ + else { + /* D D Q P D */ + if (i < sh->pd_idx) + i += raid_disks; + i -= (sh->pd_idx + 1); + } break; case ALGORITHM_LEFT_ASYMMETRIC_6: case ALGORITHM_RIGHT_ASYMMETRIC_6: @@ -2896,7 +2938,7 @@ static void handle_stripe_expansion(raid5_conf_t *conf, struct stripe_head *sh, * */ -static bool handle_stripe5(struct stripe_head *sh) +static void handle_stripe5(struct stripe_head *sh) { raid5_conf_t *conf = sh->raid_conf; int disks = sh->disks, i; @@ -3167,11 +3209,9 @@ static bool handle_stripe5(struct stripe_head *sh) ops_run_io(sh, &s); return_io(return_bi); - - return blocked_rdev == NULL; } -static bool handle_stripe6(struct stripe_head *sh) +static void handle_stripe6(struct stripe_head *sh) { raid5_conf_t *conf = sh->raid_conf; int disks = sh->disks; @@ -3455,17 +3495,14 @@ static bool handle_stripe6(struct stripe_head *sh) ops_run_io(sh, &s); return_io(return_bi); - - return blocked_rdev == NULL; } -/* returns true if the stripe was handled */ -static bool handle_stripe(struct stripe_head *sh) +static void handle_stripe(struct stripe_head *sh) { if (sh->raid_conf->level == 6) - return handle_stripe6(sh); + handle_stripe6(sh); else - return handle_stripe5(sh); + handle_stripe5(sh); } static void raid5_activate_delayed(raid5_conf_t *conf) @@ -3503,9 +3540,10 @@ static void unplug_slaves(mddev_t *mddev) { raid5_conf_t *conf = mddev->private; int i; + int devs = max(conf->raid_disks, conf->previous_raid_disks); rcu_read_lock(); - for (i = 0; i < conf->raid_disks; i++) { + for (i = 0; i < devs; i++) { mdk_rdev_t *rdev = rcu_dereference(conf->disks[i].rdev); if (rdev && !test_bit(Faulty, &rdev->flags) && atomic_read(&rdev->nr_pending)) { struct request_queue *r_queue = bdev_get_queue(rdev->bdev); @@ -4011,6 +4049,8 @@ static sector_t reshape_request(mddev_t *mddev, sector_t sector_nr, int *skipped sector_nr = conf->reshape_progress; sector_div(sector_nr, new_data_disks); if (sector_nr) { + mddev->curr_resync_completed = sector_nr; + sysfs_notify(&mddev->kobj, NULL, "sync_completed"); *skipped = 1; return sector_nr; } @@ -4277,9 +4317,7 @@ static inline sector_t sync_request(mddev_t *mddev, sector_t sector_nr, int *ski clear_bit(STRIPE_INSYNC, &sh->state); spin_unlock(&sh->lock); - /* wait for any blocked device to be handled */ - while (unlikely(!handle_stripe(sh))) - ; + handle_stripe(sh); release_stripe(sh); return STRIPE_SECTORS; @@ -4349,37 +4387,6 @@ static int retry_aligned_read(raid5_conf_t *conf, struct bio *raid_bio) return handled; } -#ifdef CONFIG_MULTICORE_RAID456 -static void __process_stripe(void *param, async_cookie_t cookie) -{ - struct stripe_head *sh = param; - - handle_stripe(sh); - release_stripe(sh); -} - -static void process_stripe(struct stripe_head *sh, struct list_head *domain) -{ - async_schedule_domain(__process_stripe, sh, domain); -} - -static void synchronize_stripe_processing(struct list_head *domain) -{ - async_synchronize_full_domain(domain); -} -#else -static void process_stripe(struct stripe_head *sh, struct list_head *domain) -{ - handle_stripe(sh); - release_stripe(sh); - cond_resched(); -} - -static void synchronize_stripe_processing(struct list_head *domain) -{ -} -#endif - /* * This is our raid5 kernel thread. @@ -4393,7 +4400,6 @@ static void raid5d(mddev_t *mddev) struct stripe_head *sh; raid5_conf_t *conf = mddev->private; int handled; - LIST_HEAD(raid_domain); pr_debug("+++ raid5d active\n"); @@ -4430,7 +4436,9 @@ static void raid5d(mddev_t *mddev) spin_unlock_irq(&conf->device_lock); handled++; - process_stripe(sh, &raid_domain); + handle_stripe(sh); + release_stripe(sh); + cond_resched(); spin_lock_irq(&conf->device_lock); } @@ -4438,7 +4446,6 @@ static void raid5d(mddev_t *mddev) spin_unlock_irq(&conf->device_lock); - synchronize_stripe_processing(&raid_domain); async_tx_issue_pending_all(); unplug_slaves(mddev); @@ -4558,13 +4565,9 @@ raid5_size(mddev_t *mddev, sector_t sectors, int raid_disks) if (!sectors) sectors = mddev->dev_sectors; - if (!raid_disks) { + if (!raid_disks) /* size is defined by the smallest of previous and new size */ - if (conf->raid_disks < conf->previous_raid_disks) - raid_disks = conf->raid_disks; - else - raid_disks = conf->previous_raid_disks; - } + raid_disks = min(conf->raid_disks, conf->previous_raid_disks); sectors &= ~((sector_t)mddev->chunk_sectors - 1); sectors &= ~((sector_t)mddev->new_chunk_sectors - 1); @@ -4665,7 +4668,7 @@ static int raid5_alloc_percpu(raid5_conf_t *conf) } per_cpu_ptr(conf->percpu, cpu)->spare_page = spare_page; } - scribble = kmalloc(scribble_len(conf->raid_disks), GFP_KERNEL); + scribble = kmalloc(conf->scribble_len, GFP_KERNEL); if (!scribble) { err = -ENOMEM; break; @@ -4686,7 +4689,7 @@ static int raid5_alloc_percpu(raid5_conf_t *conf) static raid5_conf_t *setup_conf(mddev_t *mddev) { raid5_conf_t *conf; - int raid_disk, memory; + int raid_disk, memory, max_disks; mdk_rdev_t *rdev; struct disk_info *disk; @@ -4722,15 +4725,28 @@ static raid5_conf_t *setup_conf(mddev_t *mddev) conf = kzalloc(sizeof(raid5_conf_t), GFP_KERNEL); if (conf == NULL) goto abort; + spin_lock_init(&conf->device_lock); + init_waitqueue_head(&conf->wait_for_stripe); + init_waitqueue_head(&conf->wait_for_overlap); + INIT_LIST_HEAD(&conf->handle_list); + INIT_LIST_HEAD(&conf->hold_list); + INIT_LIST_HEAD(&conf->delayed_list); + INIT_LIST_HEAD(&conf->bitmap_list); + INIT_LIST_HEAD(&conf->inactive_list); + atomic_set(&conf->active_stripes, 0); + atomic_set(&conf->preread_active_stripes, 0); + atomic_set(&conf->active_aligned_reads, 0); + conf->bypass_threshold = BYPASS_THRESHOLD; conf->raid_disks = mddev->raid_disks; - conf->scribble_len = scribble_len(conf->raid_disks); if (mddev->reshape_position == MaxSector) conf->previous_raid_disks = mddev->raid_disks; else conf->previous_raid_disks = mddev->raid_disks - mddev->delta_disks; + max_disks = max(conf->raid_disks, conf->previous_raid_disks); + conf->scribble_len = scribble_len(max_disks); - conf->disks = kzalloc(conf->raid_disks * sizeof(struct disk_info), + conf->disks = kzalloc(max_disks * sizeof(struct disk_info), GFP_KERNEL); if (!conf->disks) goto abort; @@ -4744,24 +4760,11 @@ static raid5_conf_t *setup_conf(mddev_t *mddev) if (raid5_alloc_percpu(conf) != 0) goto abort; - spin_lock_init(&conf->device_lock); - init_waitqueue_head(&conf->wait_for_stripe); - init_waitqueue_head(&conf->wait_for_overlap); - INIT_LIST_HEAD(&conf->handle_list); - INIT_LIST_HEAD(&conf->hold_list); - INIT_LIST_HEAD(&conf->delayed_list); - INIT_LIST_HEAD(&conf->bitmap_list); - INIT_LIST_HEAD(&conf->inactive_list); - atomic_set(&conf->active_stripes, 0); - atomic_set(&conf->preread_active_stripes, 0); - atomic_set(&conf->active_aligned_reads, 0); - conf->bypass_threshold = BYPASS_THRESHOLD; - pr_debug("raid5: run(%s) called.\n", mdname(mddev)); list_for_each_entry(rdev, &mddev->disks, same_set) { raid_disk = rdev->raid_disk; - if (raid_disk >= conf->raid_disks + if (raid_disk >= max_disks || raid_disk < 0) continue; disk = conf->disks + raid_disk; @@ -4793,7 +4796,7 @@ static raid5_conf_t *setup_conf(mddev_t *mddev) } memory = conf->max_nr_stripes * (sizeof(struct stripe_head) + - conf->raid_disks * ((sizeof(struct bio) + PAGE_SIZE))) / 1024; + max_disks * ((sizeof(struct bio) + PAGE_SIZE))) / 1024; if (grow_stripes(conf, conf->max_nr_stripes)) { printk(KERN_ERR "raid5: couldn't allocate %dkB for buffers\n", memory); @@ -4820,11 +4823,40 @@ static raid5_conf_t *setup_conf(mddev_t *mddev) return ERR_PTR(-ENOMEM); } + +static int only_parity(int raid_disk, int algo, int raid_disks, int max_degraded) +{ + switch (algo) { + case ALGORITHM_PARITY_0: + if (raid_disk < max_degraded) + return 1; + break; + case ALGORITHM_PARITY_N: + if (raid_disk >= raid_disks - max_degraded) + return 1; + break; + case ALGORITHM_PARITY_0_6: + if (raid_disk == 0 || + raid_disk == raid_disks - 1) + return 1; + break; + case ALGORITHM_LEFT_ASYMMETRIC_6: + case ALGORITHM_RIGHT_ASYMMETRIC_6: + case ALGORITHM_LEFT_SYMMETRIC_6: + case ALGORITHM_RIGHT_SYMMETRIC_6: + if (raid_disk == raid_disks - 1) + return 1; + } + return 0; +} + static int run(mddev_t *mddev) { raid5_conf_t *conf; int working_disks = 0, chunk_size; + int dirty_parity_disks = 0; mdk_rdev_t *rdev; + sector_t reshape_offset = 0; if (mddev->recovery_cp != MaxSector) printk(KERN_NOTICE "raid5: %s is not clean" @@ -4858,6 +4890,7 @@ static int run(mddev_t *mddev) "on a stripe boundary\n"); return -EINVAL; } + reshape_offset = here_new * mddev->new_chunk_sectors; /* here_new is the stripe we will write to */ here_old = mddev->reshape_position; sector_div(here_old, mddev->chunk_sectors * @@ -4913,12 +4946,54 @@ static int run(mddev_t *mddev) /* * 0 for a fully functional array, 1 or 2 for a degraded array. */ - list_for_each_entry(rdev, &mddev->disks, same_set) - if (rdev->raid_disk >= 0 && - test_bit(In_sync, &rdev->flags)) + list_for_each_entry(rdev, &mddev->disks, same_set) { + if (rdev->raid_disk < 0) + continue; + if (test_bit(In_sync, &rdev->flags)) working_disks++; + /* This disc is not fully in-sync. However if it + * just stored parity (beyond the recovery_offset), + * when we don't need to be concerned about the + * array being dirty. + * When reshape goes 'backwards', we never have + * partially completed devices, so we only need + * to worry about reshape going forwards. + */ + /* Hack because v0.91 doesn't store recovery_offset properly. */ + if (mddev->major_version == 0 && + mddev->minor_version > 90) + rdev->recovery_offset = reshape_offset; + + printk("%d: w=%d pa=%d pr=%d m=%d a=%d r=%d op1=%d op2=%d\n", + rdev->raid_disk, working_disks, conf->prev_algo, + conf->previous_raid_disks, conf->max_degraded, + conf->algorithm, conf->raid_disks, + only_parity(rdev->raid_disk, + conf->prev_algo, + conf->previous_raid_disks, + conf->max_degraded), + only_parity(rdev->raid_disk, + conf->algorithm, + conf->raid_disks, + conf->max_degraded)); + if (rdev->recovery_offset < reshape_offset) { + /* We need to check old and new layout */ + if (!only_parity(rdev->raid_disk, + conf->algorithm, + conf->raid_disks, + conf->max_degraded)) + continue; + } + if (!only_parity(rdev->raid_disk, + conf->prev_algo, + conf->previous_raid_disks, + conf->max_degraded)) + continue; + dirty_parity_disks++; + } - mddev->degraded = conf->raid_disks - working_disks; + mddev->degraded = (max(conf->raid_disks, conf->previous_raid_disks) + - working_disks); if (mddev->degraded > conf->max_degraded) { printk(KERN_ERR "raid5: not enough operational devices for %s" @@ -4931,7 +5006,7 @@ static int run(mddev_t *mddev) mddev->dev_sectors &= ~(mddev->chunk_sectors - 1); mddev->resync_max_sectors = mddev->dev_sectors; - if (mddev->degraded > 0 && + if (mddev->degraded > dirty_parity_disks && mddev->recovery_cp != MaxSector) { if (mddev->ok_start_degraded) printk(KERN_WARNING @@ -5357,9 +5432,11 @@ static int raid5_start_reshape(mddev_t *mddev) !test_bit(Faulty, &rdev->flags)) { if (raid5_add_disk(mddev, rdev) == 0) { char nm[20]; - set_bit(In_sync, &rdev->flags); + if (rdev->raid_disk >= conf->previous_raid_disks) + set_bit(In_sync, &rdev->flags); + else + rdev->recovery_offset = 0; added_devices++; - rdev->recovery_offset = 0; sprintf(nm, "rd%d", rdev->raid_disk); if (sysfs_create_link(&mddev->kobj, &rdev->kobj, nm)) diff --git a/drivers/md/raid5.h b/drivers/md/raid5.h index 2390e0e83daf..dd708359b451 100644 --- a/drivers/md/raid5.h +++ b/drivers/md/raid5.h @@ -214,12 +214,20 @@ struct stripe_head { int disks; /* disks in stripe */ enum check_states check_state; enum reconstruct_states reconstruct_state; - /* stripe_operations + /** + * struct stripe_operations * @target - STRIPE_OP_COMPUTE_BLK target + * @target2 - 2nd compute target in the raid6 case + * @zero_sum_result - P and Q verification flags + * @request - async service request flags for raid_run_ops */ struct stripe_operations { int target, target2; enum sum_check_flags zero_sum_result; + #ifdef CONFIG_MULTICORE_RAID456 + unsigned long request; + wait_queue_head_t wait_for_ops; + #endif } ops; struct r5dev { struct bio req; @@ -294,6 +302,8 @@ struct r6_state { #define STRIPE_FULL_WRITE 13 /* all blocks are set to be overwritten */ #define STRIPE_BIOFILL_RUN 14 #define STRIPE_COMPUTE_RUN 15 +#define STRIPE_OPS_REQ_PENDING 16 + /* * Operation request flags */ @@ -478,7 +488,7 @@ static inline int algorithm_valid_raid6(int layout) { return (layout >= 0 && layout <= 5) || - (layout == 8 || layout == 10) + (layout >= 8 && layout <= 10) || (layout >= 16 && layout <= 20); } diff --git a/drivers/md/raid6altivec.uc b/drivers/md/raid6altivec.uc index 699dfeee4944..2654d5c854be 100644 --- a/drivers/md/raid6altivec.uc +++ b/drivers/md/raid6altivec.uc @@ -15,7 +15,7 @@ * * $#-way unrolled portable integer math RAID-6 instruction set * - * This file is postprocessed using unroll.pl + * This file is postprocessed using unroll.awk * * <benh> hpa: in process, * you can just "steal" the vec unit with enable_kernel_altivec() (but diff --git a/drivers/md/raid6int.uc b/drivers/md/raid6int.uc index f9bf9cba357f..d1e276a14fab 100644 --- a/drivers/md/raid6int.uc +++ b/drivers/md/raid6int.uc @@ -15,7 +15,7 @@ * * $#-way unrolled portable integer math RAID-6 instruction set * - * This file is postprocessed using unroll.pl + * This file is postprocessed using unroll.awk */ #include <linux/raid/pq.h> diff --git a/drivers/md/raid6test/Makefile b/drivers/md/raid6test/Makefile index 58ffdf4f5161..2874cbef529d 100644 --- a/drivers/md/raid6test/Makefile +++ b/drivers/md/raid6test/Makefile @@ -7,7 +7,7 @@ CC = gcc OPTFLAGS = -O2 # Adjust as desired CFLAGS = -I.. -I ../../../include -g $(OPTFLAGS) LD = ld -PERL = perl +AWK = awk AR = ar RANLIB = ranlib @@ -35,35 +35,35 @@ raid6.a: raid6int1.o raid6int2.o raid6int4.o raid6int8.o raid6int16.o \ raid6test: test.c raid6.a $(CC) $(CFLAGS) -o raid6test $^ -raid6altivec1.c: raid6altivec.uc ../unroll.pl - $(PERL) ../unroll.pl 1 < raid6altivec.uc > $@ +raid6altivec1.c: raid6altivec.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=1 < raid6altivec.uc > $@ -raid6altivec2.c: raid6altivec.uc ../unroll.pl - $(PERL) ../unroll.pl 2 < raid6altivec.uc > $@ +raid6altivec2.c: raid6altivec.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=2 < raid6altivec.uc > $@ -raid6altivec4.c: raid6altivec.uc ../unroll.pl - $(PERL) ../unroll.pl 4 < raid6altivec.uc > $@ +raid6altivec4.c: raid6altivec.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=4 < raid6altivec.uc > $@ -raid6altivec8.c: raid6altivec.uc ../unroll.pl - $(PERL) ../unroll.pl 8 < raid6altivec.uc > $@ +raid6altivec8.c: raid6altivec.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=8 < raid6altivec.uc > $@ -raid6int1.c: raid6int.uc ../unroll.pl - $(PERL) ../unroll.pl 1 < raid6int.uc > $@ +raid6int1.c: raid6int.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=1 < raid6int.uc > $@ -raid6int2.c: raid6int.uc ../unroll.pl - $(PERL) ../unroll.pl 2 < raid6int.uc > $@ +raid6int2.c: raid6int.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=2 < raid6int.uc > $@ -raid6int4.c: raid6int.uc ../unroll.pl - $(PERL) ../unroll.pl 4 < raid6int.uc > $@ +raid6int4.c: raid6int.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=4 < raid6int.uc > $@ -raid6int8.c: raid6int.uc ../unroll.pl - $(PERL) ../unroll.pl 8 < raid6int.uc > $@ +raid6int8.c: raid6int.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=8 < raid6int.uc > $@ -raid6int16.c: raid6int.uc ../unroll.pl - $(PERL) ../unroll.pl 16 < raid6int.uc > $@ +raid6int16.c: raid6int.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=16 < raid6int.uc > $@ -raid6int32.c: raid6int.uc ../unroll.pl - $(PERL) ../unroll.pl 32 < raid6int.uc > $@ +raid6int32.c: raid6int.uc ../unroll.awk + $(AWK) ../unroll.awk -vN=32 < raid6int.uc > $@ raid6tables.c: mktables ./mktables > raid6tables.c diff --git a/drivers/md/unroll.awk b/drivers/md/unroll.awk new file mode 100644 index 000000000000..c6aa03631df8 --- /dev/null +++ b/drivers/md/unroll.awk @@ -0,0 +1,20 @@ + +# This filter requires one command line option of form -vN=n +# where n must be a decimal number. +# +# Repeat each input line containing $$ n times, replacing $$ with 0...n-1. +# Replace each $# with n, and each $* with a single $. + +BEGIN { + n = N + 0 +} +{ + if (/\$\$/) { rep = n } else { rep = 1 } + for (i = 0; i < rep; ++i) { + tmp = $0 + gsub(/\$\$/, i, tmp) + gsub(/\$\#/, n, tmp) + gsub(/\$\*/, "$", tmp) + print tmp + } +} diff --git a/drivers/md/unroll.pl b/drivers/md/unroll.pl deleted file mode 100644 index 3acc710a20ea..000000000000 --- a/drivers/md/unroll.pl +++ /dev/null @@ -1,24 +0,0 @@ -#!/usr/bin/perl -# -# Take a piece of C code and for each line which contains the sequence $$ -# repeat n times with $ replaced by 0...n-1; the sequence $# is replaced -# by the unrolling factor, and $* with a single $ -# - -($n) = @ARGV; -$n += 0; - -while ( defined($line = <STDIN>) ) { - if ( $line =~ /\$\$/ ) { - $rep = $n; - } else { - $rep = 1; - } - for ( $i = 0 ; $i < $rep ; $i++ ) { - $tmp = $line; - $tmp =~ s/\$\$/$i/g; - $tmp =~ s/\$\#/$n/g; - $tmp =~ s/\$\*/\$/g; - print $tmp; - } -} diff --git a/drivers/media/common/tuners/tda18271-fe.c b/drivers/media/common/tuners/tda18271-fe.c index 64595112000d..3a50ce96fcb9 100644 --- a/drivers/media/common/tuners/tda18271-fe.c +++ b/drivers/media/common/tuners/tda18271-fe.c @@ -616,13 +616,13 @@ static int tda18271_rf_tracking_filters_init(struct dvb_frontend *fe, u32 freq) case RF2: map[i].rf_a1 = (prog_cal[RF2] - prog_tab[RF2] - prog_cal[RF1] + prog_tab[RF1]) / - ((rf_freq[RF2] - rf_freq[RF1]) / 1000); + (s32)((rf_freq[RF2] - rf_freq[RF1]) / 1000); map[i].rf2 = rf_freq[RF2] / 1000; break; case RF3: map[i].rf_a2 = (prog_cal[RF3] - prog_tab[RF3] - prog_cal[RF2] + prog_tab[RF2]) / - ((rf_freq[RF3] - rf_freq[RF2]) / 1000); + (s32)((rf_freq[RF3] - rf_freq[RF2]) / 1000); map[i].rf_b2 = prog_cal[RF2] - prog_tab[RF2]; map[i].rf3 = rf_freq[RF3] / 1000; break; @@ -1000,12 +1000,12 @@ static int tda18271_set_analog_params(struct dvb_frontend *fe, struct tda18271_std_map_item *map; char *mode; int ret; - u32 freq = params->frequency * 62500; + u32 freq = params->frequency * 125 * + ((params->mode == V4L2_TUNER_RADIO) ? 1 : 1000) / 2; priv->mode = TDA18271_ANALOG; if (params->mode == V4L2_TUNER_RADIO) { - freq = freq / 1000; map = &std_map->fm_radio; mode = "fm"; } else if (params->std & V4L2_STD_MN) { diff --git a/drivers/media/dvb/dvb-core/dvb_net.c b/drivers/media/dvb/dvb-core/dvb_net.c index 8c9ae0a3a272..0241a7c5c34a 100644 --- a/drivers/media/dvb/dvb-core/dvb_net.c +++ b/drivers/media/dvb/dvb-core/dvb_net.c @@ -63,6 +63,7 @@ #include <asm/uaccess.h> #include <linux/crc32.h> #include <linux/mutex.h> +#include <linux/sched.h> #include "dvb_demux.h" #include "dvb_net.h" diff --git a/drivers/media/dvb/dvb-usb/Kconfig b/drivers/media/dvb/dvb-usb/Kconfig index 9744b0692417..0e4b97fba384 100644 --- a/drivers/media/dvb/dvb-usb/Kconfig +++ b/drivers/media/dvb/dvb-usb/Kconfig @@ -75,7 +75,7 @@ config DVB_USB_DIB0700 select DVB_DIB3000MC if !DVB_FE_CUSTOMISE select DVB_S5H1411 if !DVB_FE_CUSTOMISE select DVB_LGDT3305 if !DVB_FE_CUSTOMISE - select DVB_TUNER_DIB0070 + select DVB_TUNER_DIB0070 if !DVB_FE_CUSTOMISE select MEDIA_TUNER_MT2060 if !MEDIA_TUNER_CUSTOMISE select MEDIA_TUNER_MT2266 if !MEDIA_TUNER_CUSTOMISE select MEDIA_TUNER_XC2028 if !MEDIA_TUNER_CUSTOMISE diff --git a/drivers/media/dvb/dvb-usb/ce6230.c b/drivers/media/dvb/dvb-usb/ce6230.c index 0737c6377892..3df2045b7d2d 100644 --- a/drivers/media/dvb/dvb-usb/ce6230.c +++ b/drivers/media/dvb/dvb-usb/ce6230.c @@ -105,7 +105,7 @@ static int ce6230_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msg[], int i = 0; struct req_t req; int ret = 0; - memset(&req, 0, sizeof(&req)); + memset(&req, 0, sizeof(req)); if (num > 2) return -EINVAL; diff --git a/drivers/media/dvb/dvb-usb/dib0700_devices.c b/drivers/media/dvb/dvb-usb/dib0700_devices.c index 0b2812aa30a4..6bd8951ea02b 100644 --- a/drivers/media/dvb/dvb-usb/dib0700_devices.c +++ b/drivers/media/dvb/dvb-usb/dib0700_devices.c @@ -1925,7 +1925,7 @@ struct dvb_usb_device_properties dib0700_devices[] = { { NULL }, }, { "Leadtek Winfast DTV Dongle (STK7700P based)", - { &dib0700_usb_id_table[8] }, + { &dib0700_usb_id_table[8], &dib0700_usb_id_table[34] }, { NULL }, }, { "AVerMedia AVerTV DVB-T Express", @@ -2064,7 +2064,7 @@ struct dvb_usb_device_properties dib0700_devices[] = { }, }, - .num_device_descs = 12, + .num_device_descs = 11, .devices = { { "DiBcom STK7070P reference design", { &dib0700_usb_id_table[15], NULL }, @@ -2098,11 +2098,6 @@ struct dvb_usb_device_properties dib0700_devices[] = { { &dib0700_usb_id_table[30], NULL }, { NULL }, }, - { "Terratec Cinergy T USB XXS/ T3", - { &dib0700_usb_id_table[33], - &dib0700_usb_id_table[52], NULL }, - { NULL }, - }, { "Elgato EyeTV DTT", { &dib0700_usb_id_table[49], NULL }, { NULL }, @@ -2343,8 +2338,10 @@ struct dvb_usb_device_properties dib0700_devices[] = { { &dib0700_usb_id_table[59], NULL }, { NULL }, }, - { "Terratec Cinergy T USB XXS (HD)", - { &dib0700_usb_id_table[34], &dib0700_usb_id_table[60] }, + { "Terratec Cinergy T USB XXS (HD)/ T3", + { &dib0700_usb_id_table[33], + &dib0700_usb_id_table[52], + &dib0700_usb_id_table[60], NULL}, { NULL }, }, }, diff --git a/drivers/media/dvb/firewire/firedtv-avc.c b/drivers/media/dvb/firewire/firedtv-avc.c index d1b67fe0f011..485d061319ab 100644 --- a/drivers/media/dvb/firewire/firedtv-avc.c +++ b/drivers/media/dvb/firewire/firedtv-avc.c @@ -1050,28 +1050,28 @@ int avc_ca_pmt(struct firedtv *fdtv, char *msg, int length) c->operand[4] = 0; /* slot */ c->operand[5] = SFE_VENDOR_TAG_CA_PMT; /* ca tag */ c->operand[6] = 0; /* more/last */ - /* c->operand[7] = XXXprogram_info_length + 17; */ /* length */ - c->operand[8] = list_management; - c->operand[9] = 0x01; /* pmt_cmd=OK_descramble */ + /* Use three bytes for length field in case length > 127 */ + c->operand[10] = list_management; + c->operand[11] = 0x01; /* pmt_cmd=OK_descramble */ /* TS program map table */ - c->operand[10] = 0x02; /* Table id=2 */ - c->operand[11] = 0x80; /* Section syntax + length */ - /* c->operand[12] = XXXprogram_info_length + 12; */ - c->operand[13] = msg[1]; /* Program number */ - c->operand[14] = msg[2]; - c->operand[15] = 0x01; /* Version number=0 + current/next=1 */ - c->operand[16] = 0x00; /* Section number=0 */ - c->operand[17] = 0x00; /* Last section number=0 */ - c->operand[18] = 0x1f; /* PCR_PID=1FFF */ - c->operand[19] = 0xff; - c->operand[20] = (program_info_length >> 8); /* Program info length */ - c->operand[21] = (program_info_length & 0xff); + c->operand[12] = 0x02; /* Table id=2 */ + c->operand[13] = 0x80; /* Section syntax + length */ + /* c->operand[14] = XXXprogram_info_length + 12; */ + c->operand[15] = msg[1]; /* Program number */ + c->operand[16] = msg[2]; + c->operand[17] = 0x01; /* Version number=0 + current/next=1 */ + c->operand[18] = 0x00; /* Section number=0 */ + c->operand[19] = 0x00; /* Last section number=0 */ + c->operand[20] = 0x1f; /* PCR_PID=1FFF */ + c->operand[21] = 0xff; + c->operand[22] = (program_info_length >> 8); /* Program info length */ + c->operand[23] = (program_info_length & 0xff); /* CA descriptors at programme level */ read_pos = 6; - write_pos = 22; + write_pos = 24; if (program_info_length > 0) { pmt_cmd_id = msg[read_pos++]; if (pmt_cmd_id != 1 && pmt_cmd_id != 4) @@ -1113,8 +1113,10 @@ int avc_ca_pmt(struct firedtv *fdtv, char *msg, int length) c->operand[write_pos++] = 0x00; c->operand[write_pos++] = 0x00; - c->operand[7] = write_pos - 8; - c->operand[12] = write_pos - 13; + c->operand[7] = 0x82; + c->operand[8] = (write_pos - 10) >> 8; + c->operand[9] = (write_pos - 10) & 0xff; + c->operand[14] = write_pos - 15; crc32_csum = crc32_be(0, &c->operand[10], c->operand[12] - 1); c->operand[write_pos - 4] = (crc32_csum >> 24) & 0xff; diff --git a/drivers/media/dvb/firewire/firedtv-fe.c b/drivers/media/dvb/firewire/firedtv-fe.c index 7ba43630a25d..e49cdc88b0c7 100644 --- a/drivers/media/dvb/firewire/firedtv-fe.c +++ b/drivers/media/dvb/firewire/firedtv-fe.c @@ -141,18 +141,12 @@ static int fdtv_read_uncorrected_blocks(struct dvb_frontend *fe, u32 *ucblocks) return -EOPNOTSUPP; } -#define ACCEPTED 0x9 - static int fdtv_set_frontend(struct dvb_frontend *fe, struct dvb_frontend_parameters *params) { struct firedtv *fdtv = fe->sec_priv; - /* FIXME: avc_tuner_dsd never returns ACCEPTED. Check status? */ - if (avc_tuner_dsd(fdtv, params) != ACCEPTED) - return -EINVAL; - else - return 0; /* not sure of this... */ + return avc_tuner_dsd(fdtv, params); } static int fdtv_get_frontend(struct dvb_frontend *fe, diff --git a/drivers/media/dvb/frontends/dib0070.h b/drivers/media/dvb/frontends/dib0070.h index 8a2e1e710adb..eec9e52ffa75 100644 --- a/drivers/media/dvb/frontends/dib0070.h +++ b/drivers/media/dvb/frontends/dib0070.h @@ -51,6 +51,7 @@ struct dib0070_config { #if defined(CONFIG_DVB_TUNER_DIB0070) || (defined(CONFIG_DVB_TUNER_DIB0070_MODULE) && defined(MODULE)) extern struct dvb_frontend *dib0070_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct dib0070_config *cfg); extern u16 dib0070_wbd_offset(struct dvb_frontend *); +extern void dib0070_ctrl_agc_filter(struct dvb_frontend *, u8 open); #else static inline struct dvb_frontend *dib0070_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct dib0070_config *cfg) { @@ -63,7 +64,11 @@ static inline u16 dib0070_wbd_offset(struct dvb_frontend *fe) printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__); return -ENODEV; } + +static inline void dib0070_ctrl_agc_filter(struct dvb_frontend *fe, u8 open) +{ + printk(KERN_WARNING "%s: driver disabled by Kconfig\n", __func__); +} #endif -extern void dib0070_ctrl_agc_filter(struct dvb_frontend *, u8 open); #endif diff --git a/drivers/media/dvb/frontends/dib7000p.c b/drivers/media/dvb/frontends/dib7000p.c index 55ef6eeb0769..0781f94e05d2 100644 --- a/drivers/media/dvb/frontends/dib7000p.c +++ b/drivers/media/dvb/frontends/dib7000p.c @@ -1375,6 +1375,11 @@ struct dvb_frontend * dib7000p_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, if (dib7000p_identify(st) != 0) goto error; + /* FIXME: make sure the dev.parent field is initialized, or else + request_firmware() will hit an OOPS (this should be moved somewhere + more common) */ + st->i2c_master.gated_tuner_i2c_adap.dev.parent = i2c_adap->dev.parent; + dibx000_init_i2c_master(&st->i2c_master, DIB7000P, st->i2c_adap, st->i2c_addr); dib7000p_demod_reset(st); diff --git a/drivers/media/dvb/pt1/pt1.c b/drivers/media/dvb/pt1/pt1.c index 81e623a90f09..1fd8306371e2 100644 --- a/drivers/media/dvb/pt1/pt1.c +++ b/drivers/media/dvb/pt1/pt1.c @@ -27,6 +27,7 @@ #include <linux/pci.h> #include <linux/kthread.h> #include <linux/freezer.h> +#include <linux/vmalloc.h> #include "dvbdev.h" #include "dvb_demux.h" diff --git a/drivers/media/dvb/siano/smsusb.c b/drivers/media/dvb/siano/smsusb.c index cb8a358b7310..8f88a586b0dd 100644 --- a/drivers/media/dvb/siano/smsusb.c +++ b/drivers/media/dvb/siano/smsusb.c @@ -529,6 +529,12 @@ struct usb_device_id smsusb_id_table[] = { .driver_info = SMS1XXX_BOARD_SIANO_NICE }, { USB_DEVICE(0x187f, 0x0301), .driver_info = SMS1XXX_BOARD_SIANO_VENICE }, + { USB_DEVICE(0x2040, 0xb900), + .driver_info = SMS1XXX_BOARD_HAUPPAUGE_WINDHAM }, + { USB_DEVICE(0x2040, 0xb910), + .driver_info = SMS1XXX_BOARD_HAUPPAUGE_WINDHAM }, + { USB_DEVICE(0x2040, 0xc000), + .driver_info = SMS1XXX_BOARD_HAUPPAUGE_WINDHAM }, { } /* Terminating entry */ }; diff --git a/drivers/media/video/bt8xx/bttv-driver.c b/drivers/media/video/bt8xx/bttv-driver.c index 939d1e512974..a6724019c66f 100644 --- a/drivers/media/video/bt8xx/bttv-driver.c +++ b/drivers/media/video/bt8xx/bttv-driver.c @@ -1299,7 +1299,7 @@ set_tvnorm(struct bttv *btv, unsigned int norm) tvnorm = &bttv_tvnorms[norm]; - if (!memcmp(&bttv_tvnorms[btv->tvnorm].cropcap, &tvnorm->cropcap, + if (memcmp(&bttv_tvnorms[btv->tvnorm].cropcap, &tvnorm->cropcap, sizeof (tvnorm->cropcap))) { bttv_crop_reset(&btv->crop[0], norm); btv->crop[1] = btv->crop[0]; /* current = default */ @@ -3800,11 +3800,34 @@ bttv_irq_next_video(struct bttv *btv, struct bttv_buffer_set *set) if (!V4L2_FIELD_HAS_BOTH(item->vb.field) && (item->vb.queue.next != &btv->capture)) { item = list_entry(item->vb.queue.next, struct bttv_buffer, vb.queue); + /* Mike Isely <isely@pobox.com> - Only check + * and set up the bottom field in the logic + * below. Don't ever do the top field. This + * of course means that if we set up the + * bottom field in the above code that we'll + * actually skip a field. But that's OK. + * Having processed only a single buffer this + * time, then the next time around the first + * available buffer should be for a top field. + * That will then cause us here to set up a + * top then a bottom field in the normal way. + * The alternative to this understanding is + * that we set up the second available buffer + * as a top field, but that's out of order + * since this driver always processes the top + * field first - the effect will be the two + * buffers being returned in the wrong order, + * with the second buffer also being delayed + * by one field time (owing to the fifo nature + * of videobuf). Worse still, we'll be stuck + * doing fields out of order now every time + * until something else causes a field to be + * dropped. By effectively forcing a field to + * drop this way then we always get back into + * sync within a single frame time. (Out of + * order fields can screw up deinterlacing + * algorithms.) */ if (!V4L2_FIELD_HAS_BOTH(item->vb.field)) { - if (NULL == set->top && - V4L2_FIELD_TOP == item->vb.field) { - set->top = item; - } if (NULL == set->bottom && V4L2_FIELD_BOTTOM == item->vb.field) { set->bottom = item; diff --git a/drivers/media/video/em28xx/em28xx-audio.c b/drivers/media/video/em28xx/em28xx-audio.c index 7bd8a70f0a0b..ac947aecb9c3 100644 --- a/drivers/media/video/em28xx/em28xx-audio.c +++ b/drivers/media/video/em28xx/em28xx-audio.c @@ -383,6 +383,11 @@ static int snd_em28xx_hw_capture_free(struct snd_pcm_substream *substream) static int snd_em28xx_prepare(struct snd_pcm_substream *substream) { + struct em28xx *dev = snd_pcm_substream_chip(substream); + + dev->adev.hwptr_done_capture = 0; + dev->adev.capture_transfer_done = 0; + return 0; } diff --git a/drivers/media/video/gspca/m5602/m5602_s5k4aa.c b/drivers/media/video/gspca/m5602/m5602_s5k4aa.c index 59400e858965..a27afeb6f39b 100644 --- a/drivers/media/video/gspca/m5602/m5602_s5k4aa.c +++ b/drivers/media/video/gspca/m5602/m5602_s5k4aa.c @@ -35,12 +35,25 @@ static const struct dmi_system_id s5k4aa_vflip_dmi_table[] = { { + .ident = "BRUNEINIT", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "BRUNENIT"), + DMI_MATCH(DMI_PRODUCT_NAME, "BRUNENIT"), + DMI_MATCH(DMI_BOARD_VERSION, "00030D0000000001") + } + }, { .ident = "Fujitsu-Siemens Amilo Xa 2528", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "FUJITSU SIEMENS"), DMI_MATCH(DMI_PRODUCT_NAME, "AMILO Xa 2528") } }, { + .ident = "Fujitsu-Siemens Amilo Xi 2528", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "FUJITSU SIEMENS"), + DMI_MATCH(DMI_PRODUCT_NAME, "AMILO Xi 2528") + } + }, { .ident = "Fujitsu-Siemens Amilo Xi 2550", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "FUJITSU SIEMENS"), @@ -57,6 +70,13 @@ static .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Micro-Star International"), DMI_MATCH(DMI_PRODUCT_NAME, "GX700"), + DMI_MATCH(DMI_BIOS_DATE, "12/02/2008") + } + }, { + .ident = "MSI GX700", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Micro-Star International"), + DMI_MATCH(DMI_PRODUCT_NAME, "GX700"), DMI_MATCH(DMI_BIOS_DATE, "07/26/2007") } }, { diff --git a/drivers/media/video/gspca/mr97310a.c b/drivers/media/video/gspca/mr97310a.c index 140c8f320e47..f8328b9efae5 100644 --- a/drivers/media/video/gspca/mr97310a.c +++ b/drivers/media/video/gspca/mr97310a.c @@ -483,7 +483,7 @@ static int start_cif_cam(struct gspca_dev *gspca_dev) data[3] = 0x2c; /* reg 2, H size/8 */ data[4] = 0x48; /* reg 3, V size/4 */ data[6] = 0x06; /* reg 5, H start */ - data[8] = 0x06 + sd->sensor_type; /* reg 7, V start */ + data[8] = 0x06 - sd->sensor_type; /* reg 7, V start */ break; } err_code = mr_write(gspca_dev, 11); diff --git a/drivers/media/video/gspca/ov519.c b/drivers/media/video/gspca/ov519.c index 2f6e135d94bc..a5c190e93799 100644 --- a/drivers/media/video/gspca/ov519.c +++ b/drivers/media/video/gspca/ov519.c @@ -2919,7 +2919,7 @@ static void ov518_pkt_scan(struct gspca_dev *gspca_dev, /* A false positive here is likely, until OVT gives me * the definitive SOF/EOF format */ if ((!(data[0] | data[1] | data[2] | data[3] | data[5])) && data[6]) { - gspca_frame_add(gspca_dev, LAST_PACKET, frame, data, 0); + frame = gspca_frame_add(gspca_dev, LAST_PACKET, frame, data, 0); gspca_frame_add(gspca_dev, FIRST_PACKET, frame, data, 0); sd->packet_nr = 0; } diff --git a/drivers/media/video/gspca/stv06xx/stv06xx.c b/drivers/media/video/gspca/stv06xx/stv06xx.c index 65489d6b0d89..bfae63f5584c 100644 --- a/drivers/media/video/gspca/stv06xx/stv06xx.c +++ b/drivers/media/video/gspca/stv06xx/stv06xx.c @@ -394,7 +394,8 @@ frame_data: PDEBUG(D_PACK, "End of frame detected"); /* Complete the last frame (if any) */ - gspca_frame_add(gspca_dev, LAST_PACKET, frame, data, 0); + frame = gspca_frame_add(gspca_dev, LAST_PACKET, + frame, data, 0); if (chunk_len) PDEBUG(D_ERR, "Chunk length is " diff --git a/drivers/media/video/meye.c b/drivers/media/video/meye.c index 4b1bc05a462c..01e1eefcf1eb 100644 --- a/drivers/media/video/meye.c +++ b/drivers/media/video/meye.c @@ -28,6 +28,7 @@ */ #include <linux/module.h> #include <linux/pci.h> +#include <linux/sched.h> #include <linux/init.h> #include <linux/videodev.h> #include <media/v4l2-common.h> diff --git a/drivers/media/video/pxa_camera.c b/drivers/media/video/pxa_camera.c index 6952e9602d5d..51b683c63b70 100644 --- a/drivers/media/video/pxa_camera.c +++ b/drivers/media/video/pxa_camera.c @@ -26,6 +26,7 @@ #include <linux/device.h> #include <linux/platform_device.h> #include <linux/clk.h> +#include <linux/sched.h> #include <media/v4l2-common.h> #include <media/v4l2-dev.h> @@ -1432,7 +1433,9 @@ static int pxa_camera_set_fmt(struct soc_camera_device *icd, icd->sense = &sense; cam_f.fmt.pix.pixelformat = cam_fmt->fourcc; - ret = v4l2_subdev_call(sd, video, s_fmt, f); + ret = v4l2_subdev_call(sd, video, s_fmt, &cam_f); + cam_f.fmt.pix.pixelformat = pix->pixelformat; + *pix = cam_f.fmt.pix; icd->sense = NULL; diff --git a/drivers/media/video/s2255drv.c b/drivers/media/video/s2255drv.c index 9e3262c0ba37..2c0bb06cab3b 100644 --- a/drivers/media/video/s2255drv.c +++ b/drivers/media/video/s2255drv.c @@ -598,11 +598,6 @@ static int s2255_got_frame(struct s2255_dev *dev, int chn, int jpgsize) buf = list_entry(dma_q->active.next, struct s2255_buffer, vb.queue); - if (!waitqueue_active(&buf->vb.done)) { - /* no one active */ - rc = -1; - goto unlock; - } list_del(&buf->vb.queue); do_gettimeofday(&buf->vb.ts); dprintk(100, "[%p/%d] wakeup\n", buf, buf->vb.i); diff --git a/drivers/media/video/saa7134/saa7134-cards.c b/drivers/media/video/saa7134/saa7134-cards.c index 71145bff94fa..09013229d4aa 100644 --- a/drivers/media/video/saa7134/saa7134-cards.c +++ b/drivers/media/video/saa7134/saa7134-cards.c @@ -3428,6 +3428,7 @@ struct saa7134_board saa7134_boards[] = { .tuner_config = 3, .mpeg = SAA7134_MPEG_DVB, .ts_type = SAA7134_MPEG_TS_SERIAL, + .ts_force_val = 1, .gpiomask = 0x0800100, /* GPIO 21 is an INPUT */ .inputs = {{ .name = name_tv, diff --git a/drivers/media/video/saa7134/saa7134-ts.c b/drivers/media/video/saa7134/saa7134-ts.c index 3fa652279ac0..03488ba4c99c 100644 --- a/drivers/media/video/saa7134/saa7134-ts.c +++ b/drivers/media/video/saa7134/saa7134-ts.c @@ -262,11 +262,13 @@ int saa7134_ts_start(struct saa7134_dev *dev) switch (saa7134_boards[dev->board].ts_type) { case SAA7134_MPEG_TS_PARALLEL: saa_writeb(SAA7134_TS_SERIAL0, 0x40); - saa_writeb(SAA7134_TS_PARALLEL, 0xec); + saa_writeb(SAA7134_TS_PARALLEL, 0xec | + (saa7134_boards[dev->board].ts_force_val << 4)); break; case SAA7134_MPEG_TS_SERIAL: saa_writeb(SAA7134_TS_SERIAL0, 0xd8); - saa_writeb(SAA7134_TS_PARALLEL, 0x6c); + saa_writeb(SAA7134_TS_PARALLEL, 0x6c | + (saa7134_boards[dev->board].ts_force_val << 4)); saa_writeb(SAA7134_TS_PARALLEL_SERIAL, 0xbc); saa_writeb(SAA7134_TS_SERIAL1, 0x02); break; diff --git a/drivers/media/video/saa7134/saa7134.h b/drivers/media/video/saa7134/saa7134.h index 6ee3e9b7769e..f8697d46ff5f 100644 --- a/drivers/media/video/saa7134/saa7134.h +++ b/drivers/media/video/saa7134/saa7134.h @@ -360,6 +360,7 @@ struct saa7134_board { enum saa7134_mpeg_type mpeg; enum saa7134_mpeg_ts_type ts_type; unsigned int vid_port_opts; + unsigned int ts_force_val:1; }; #define card_has_radio(dev) (NULL != saa7134_boards[dev->board].radio.name) diff --git a/drivers/media/video/saa7164/saa7164-cmd.c b/drivers/media/video/saa7164/saa7164-cmd.c index c45966edc0cf..9c1d3ac43869 100644 --- a/drivers/media/video/saa7164/saa7164-cmd.c +++ b/drivers/media/video/saa7164/saa7164-cmd.c @@ -347,7 +347,7 @@ int saa7164_cmd_send(struct saa7164_dev *dev, u8 id, tmComResCmd_t command, /* Prepare some basic command/response structures */ memset(&command_t, 0, sizeof(command_t)); - memset(&response_t, 0, sizeof(&response_t)); + memset(&response_t, 0, sizeof(response_t)); pcommand_t = &command_t; presponse_t = &response_t; command_t.id = id; diff --git a/drivers/media/video/sh_mobile_ceu_camera.c b/drivers/media/video/sh_mobile_ceu_camera.c index 65ac474c517a..2f78b4f263f5 100644 --- a/drivers/media/video/sh_mobile_ceu_camera.c +++ b/drivers/media/video/sh_mobile_ceu_camera.c @@ -1173,8 +1173,8 @@ static int get_scales(struct soc_camera_device *icd, width_in = scale_up(cam->ceu_rect.width, *scale_h); height_in = scale_up(cam->ceu_rect.height, *scale_v); - *scale_h = calc_generic_scale(cam->ceu_rect.width, icd->user_width); - *scale_v = calc_generic_scale(cam->ceu_rect.height, icd->user_height); + *scale_h = calc_generic_scale(width_in, icd->user_width); + *scale_v = calc_generic_scale(height_in, icd->user_height); return 0; } diff --git a/drivers/media/video/soc_camera.c b/drivers/media/video/soc_camera.c index 59aa7a3694c2..36e617bd13c7 100644 --- a/drivers/media/video/soc_camera.c +++ b/drivers/media/video/soc_camera.c @@ -1160,13 +1160,15 @@ void soc_camera_host_unregister(struct soc_camera_host *ici) if (icd->iface == ici->nr) { /* The bus->remove will be called */ device_unregister(&icd->dev); - /* Not before device_unregister(), .remove - * needs parent to call ici->ops->remove() */ - icd->dev.parent = NULL; - - /* If the host module is loaded again, device_register() - * would complain "already initialised" */ - memset(&icd->dev.kobj, 0, sizeof(icd->dev.kobj)); + /* + * Not before device_unregister(), .remove + * needs parent to call ici->ops->remove(). + * If the host module is loaded again, device_register() + * would complain "already initialised," since 2.6.32 + * this is also needed to prevent use-after-free of the + * device private data. + */ + memset(&icd->dev, 0, sizeof(icd->dev)); } } diff --git a/drivers/media/video/uvc/uvc_ctrl.c b/drivers/media/video/uvc/uvc_ctrl.c index c3225a561748..1b89735e62fd 100644 --- a/drivers/media/video/uvc/uvc_ctrl.c +++ b/drivers/media/video/uvc/uvc_ctrl.c @@ -348,7 +348,7 @@ static void uvc_ctrl_set_zoom(struct uvc_control_mapping *mapping, __s32 value, __u8 *data) { data[0] = value == 0 ? 0 : (value > 0) ? 1 : 0xff; - data[2] = min(abs(value), 0xff); + data[2] = min((int)abs(value), 0xff); } static struct uvc_control_mapping uvc_ctrl_mappings[] = { diff --git a/drivers/media/video/uvc/uvc_video.c b/drivers/media/video/uvc/uvc_video.c index f960e8ea4f17..a6e41d12b221 100644 --- a/drivers/media/video/uvc/uvc_video.c +++ b/drivers/media/video/uvc/uvc_video.c @@ -90,7 +90,8 @@ static void uvc_fixup_video_ctrl(struct uvc_streaming *stream, ctrl->dwMaxVideoFrameSize = frame->dwMaxVideoFrameBufferSize; - if (stream->dev->quirks & UVC_QUIRK_FIX_BANDWIDTH && + if (!(format->flags & UVC_FMT_FLAG_COMPRESSED) && + stream->dev->quirks & UVC_QUIRK_FIX_BANDWIDTH && stream->intf->num_altsetting > 1) { u32 interval; u32 bandwidth; diff --git a/drivers/media/video/videobuf-core.c b/drivers/media/video/videobuf-core.c index f1ccf98c0a6f..8e93c6f25c83 100644 --- a/drivers/media/video/videobuf-core.c +++ b/drivers/media/video/videobuf-core.c @@ -17,6 +17,7 @@ #include <linux/module.h> #include <linux/moduleparam.h> #include <linux/mm.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/interrupt.h> diff --git a/drivers/media/video/videobuf-dma-sg.c b/drivers/media/video/videobuf-dma-sg.c index 53cdd67cebe1..032ebae0134a 100644 --- a/drivers/media/video/videobuf-dma-sg.c +++ b/drivers/media/video/videobuf-dma-sg.c @@ -21,6 +21,7 @@ #include <linux/init.h> #include <linux/module.h> #include <linux/moduleparam.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/interrupt.h> diff --git a/drivers/message/fusion/mptlan.c b/drivers/message/fusion/mptlan.c index bc2ec2182c00..34f3f36f819b 100644 --- a/drivers/message/fusion/mptlan.c +++ b/drivers/message/fusion/mptlan.c @@ -56,6 +56,7 @@ #include <linux/init.h> #include <linux/module.h> #include <linux/fs.h> +#include <linux/sched.h> #define my_VERSION MPT_LINUX_VERSION_COMMON #define MYNAM "mptlan" diff --git a/drivers/mfd/twl4030-core.c b/drivers/mfd/twl4030-core.c index e424cf6d8e9e..a1c47ee95c0e 100644 --- a/drivers/mfd/twl4030-core.c +++ b/drivers/mfd/twl4030-core.c @@ -480,7 +480,6 @@ static int add_children(struct twl4030_platform_data *pdata, unsigned long features) { struct device *child; - struct device *usb_transceiver = NULL; if (twl_has_bci() && pdata->bci && !(features & TPS_SUBSET)) { child = add_child(3, "twl4030_bci", @@ -532,16 +531,61 @@ add_children(struct twl4030_platform_data *pdata, unsigned long features) } if (twl_has_usb() && pdata->usb) { + + static struct regulator_consumer_supply usb1v5 = { + .supply = "usb1v5", + }; + static struct regulator_consumer_supply usb1v8 = { + .supply = "usb1v8", + }; + static struct regulator_consumer_supply usb3v1 = { + .supply = "usb3v1", + }; + + /* First add the regulators so that they can be used by transceiver */ + if (twl_has_regulator()) { + /* this is a template that gets copied */ + struct regulator_init_data usb_fixed = { + .constraints.valid_modes_mask = + REGULATOR_MODE_NORMAL + | REGULATOR_MODE_STANDBY, + .constraints.valid_ops_mask = + REGULATOR_CHANGE_MODE + | REGULATOR_CHANGE_STATUS, + }; + + child = add_regulator_linked(TWL4030_REG_VUSB1V5, + &usb_fixed, &usb1v5, 1); + if (IS_ERR(child)) + return PTR_ERR(child); + + child = add_regulator_linked(TWL4030_REG_VUSB1V8, + &usb_fixed, &usb1v8, 1); + if (IS_ERR(child)) + return PTR_ERR(child); + + child = add_regulator_linked(TWL4030_REG_VUSB3V1, + &usb_fixed, &usb3v1, 1); + if (IS_ERR(child)) + return PTR_ERR(child); + + } + child = add_child(0, "twl4030_usb", pdata->usb, sizeof(*pdata->usb), true, /* irq0 = USB_PRES, irq1 = USB */ pdata->irq_base + 8 + 2, pdata->irq_base + 4); + if (IS_ERR(child)) return PTR_ERR(child); /* we need to connect regulators to this transceiver */ - usb_transceiver = child; + if (twl_has_regulator() && child) { + usb1v5.dev = child; + usb1v8.dev = child; + usb3v1.dev = child; + } } if (twl_has_watchdog()) { @@ -580,47 +624,6 @@ add_children(struct twl4030_platform_data *pdata, unsigned long features) return PTR_ERR(child); } - if (twl_has_regulator() && usb_transceiver) { - static struct regulator_consumer_supply usb1v5 = { - .supply = "usb1v5", - }; - static struct regulator_consumer_supply usb1v8 = { - .supply = "usb1v8", - }; - static struct regulator_consumer_supply usb3v1 = { - .supply = "usb3v1", - }; - - /* this is a template that gets copied */ - struct regulator_init_data usb_fixed = { - .constraints.valid_modes_mask = - REGULATOR_MODE_NORMAL - | REGULATOR_MODE_STANDBY, - .constraints.valid_ops_mask = - REGULATOR_CHANGE_MODE - | REGULATOR_CHANGE_STATUS, - }; - - usb1v5.dev = usb_transceiver; - usb1v8.dev = usb_transceiver; - usb3v1.dev = usb_transceiver; - - child = add_regulator_linked(TWL4030_REG_VUSB1V5, &usb_fixed, - &usb1v5, 1); - if (IS_ERR(child)) - return PTR_ERR(child); - - child = add_regulator_linked(TWL4030_REG_VUSB1V8, &usb_fixed, - &usb1v8, 1); - if (IS_ERR(child)) - return PTR_ERR(child); - - child = add_regulator_linked(TWL4030_REG_VUSB3V1, &usb_fixed, - &usb3v1, 1); - if (IS_ERR(child)) - return PTR_ERR(child); - } - /* maybe add LDOs that are omitted on cost-reduced parts */ if (twl_has_regulator() && !(features & TPS_SUBSET)) { child = add_regulator(TWL4030_REG_VPLL2, pdata->vpll2); @@ -792,7 +795,7 @@ twl4030_probe(struct i2c_client *client, const struct i2c_device_id *id) twl->client = i2c_new_dummy(client->adapter, twl->address); if (!twl->client) { - dev_err(&twl->client->dev, + dev_err(&client->dev, "can't attach client %d\n", i); status = -ENOMEM; goto fail; diff --git a/drivers/mfd/ucb1x00-core.c b/drivers/mfd/ucb1x00-core.c index fea9085fe52c..60c3988f3cf3 100644 --- a/drivers/mfd/ucb1x00-core.c +++ b/drivers/mfd/ucb1x00-core.c @@ -18,6 +18,7 @@ */ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/init.h> #include <linux/errno.h> diff --git a/drivers/mfd/wm831x-irq.c b/drivers/mfd/wm831x-irq.c index d3015dfb9134..ac056ea6b66e 100644 --- a/drivers/mfd/wm831x-irq.c +++ b/drivers/mfd/wm831x-irq.c @@ -507,6 +507,8 @@ int wm831x_irq_init(struct wm831x *wm831x, int irq) { int i, ret; + mutex_init(&wm831x->irq_lock); + if (!irq) { dev_warn(wm831x->dev, "No interrupt specified - functionality limited\n"); @@ -521,7 +523,6 @@ int wm831x_irq_init(struct wm831x *wm831x, int irq) } wm831x->irq = irq; - mutex_init(&wm831x->irq_lock); INIT_WORK(&wm831x->irq_work, wm831x_irq_worker); /* Mask the individual interrupt sources */ diff --git a/drivers/misc/hpilo.c b/drivers/misc/hpilo.c index 1ad27c6abcca..a92a3a742b43 100644 --- a/drivers/misc/hpilo.c +++ b/drivers/misc/hpilo.c @@ -18,6 +18,7 @@ #include <linux/device.h> #include <linux/file.h> #include <linux/cdev.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/delay.h> #include <linux/uaccess.h> diff --git a/drivers/misc/ibmasm/command.c b/drivers/misc/ibmasm/command.c index 276d3fb68094..e2031739aa29 100644 --- a/drivers/misc/ibmasm/command.c +++ b/drivers/misc/ibmasm/command.c @@ -22,6 +22,7 @@ * */ +#include <linux/sched.h> #include "ibmasm.h" #include "lowlevel.h" diff --git a/drivers/misc/ibmasm/event.c b/drivers/misc/ibmasm/event.c index 68a0a5b94795..572d41ffc186 100644 --- a/drivers/misc/ibmasm/event.c +++ b/drivers/misc/ibmasm/event.c @@ -22,6 +22,7 @@ * */ +#include <linux/sched.h> #include "ibmasm.h" #include "lowlevel.h" diff --git a/drivers/misc/ibmasm/r_heartbeat.c b/drivers/misc/ibmasm/r_heartbeat.c index bec9e2c44bef..2de487ac788c 100644 --- a/drivers/misc/ibmasm/r_heartbeat.c +++ b/drivers/misc/ibmasm/r_heartbeat.c @@ -20,6 +20,7 @@ * */ +#include <linux/sched.h> #include "ibmasm.h" #include "dot_command.h" diff --git a/drivers/misc/phantom.c b/drivers/misc/phantom.c index 90a95ce8dc34..04c27266f567 100644 --- a/drivers/misc/phantom.c +++ b/drivers/misc/phantom.c @@ -22,6 +22,7 @@ #include <linux/interrupt.h> #include <linux/cdev.h> #include <linux/phantom.h> +#include <linux/sched.h> #include <linux/smp_lock.h> #include <asm/atomic.h> diff --git a/drivers/misc/sgi-gru/gruprocfs.c b/drivers/misc/sgi-gru/gruprocfs.c index ccd4408a26c7..3f2375c5ba5b 100644 --- a/drivers/misc/sgi-gru/gruprocfs.c +++ b/drivers/misc/sgi-gru/gruprocfs.c @@ -161,14 +161,15 @@ static int options_show(struct seq_file *s, void *p) static ssize_t options_write(struct file *file, const char __user *userbuf, size_t count, loff_t *data) { - unsigned long val; - char buf[80]; + char buf[20]; - if (strncpy_from_user(buf, userbuf, sizeof(buf) - 1) < 0) + if (count >= sizeof(buf)) + return -EINVAL; + if (copy_from_user(buf, userbuf, count)) return -EFAULT; - buf[count - 1] = '\0'; - if (!strict_strtoul(buf, 10, &val)) - gru_options = val; + buf[count] = '\0'; + if (strict_strtoul(buf, 0, &gru_options)) + return -EINVAL; return count; } diff --git a/drivers/mmc/core/sdio_cis.c b/drivers/mmc/core/sdio_cis.c index e1035c895808..f85dcd536508 100644 --- a/drivers/mmc/core/sdio_cis.c +++ b/drivers/mmc/core/sdio_cis.c @@ -29,6 +29,8 @@ static int cistpl_vers_1(struct mmc_card *card, struct sdio_func *func, unsigned i, nr_strings; char **buffer, *string; + /* Find all null-terminated (including zero length) strings in + the TPLLV1_INFO field. Trailing garbage is ignored. */ buf += 2; size -= 2; @@ -39,11 +41,8 @@ static int cistpl_vers_1(struct mmc_card *card, struct sdio_func *func, if (buf[i] == 0) nr_strings++; } - - if (nr_strings < 4) { - printk(KERN_WARNING "SDIO: ignoring broken CISTPL_VERS_1\n"); + if (nr_strings == 0) return 0; - } size = i; diff --git a/drivers/mmc/host/at91_mci.c b/drivers/mmc/host/at91_mci.c index e556d42cc45a..63924e0c7ea9 100644 --- a/drivers/mmc/host/at91_mci.c +++ b/drivers/mmc/host/at91_mci.c @@ -72,7 +72,6 @@ #include <asm/irq.h> #include <asm/gpio.h> -#include <asm/mach/mmc.h> #include <mach/board.h> #include <mach/cpu.h> #include <mach/at91_mci.h> diff --git a/drivers/mmc/host/omap.c b/drivers/mmc/host/omap.c index e7a331de5733..b8fd7af1ceeb 100644 --- a/drivers/mmc/host/omap.c +++ b/drivers/mmc/host/omap.c @@ -1529,6 +1529,7 @@ static int mmc_omap_remove(struct platform_device *pdev) host->pdata->cleanup(&pdev->dev); mmc_omap_fclk_enable(host, 0); + free_irq(host->irq, host); clk_put(host->fclk); clk_disable(host->iclk); clk_put(host->iclk); diff --git a/drivers/mmc/host/omap_hsmmc.c b/drivers/mmc/host/omap_hsmmc.c index 4487cc097911..0aecaaebef3d 100644 --- a/drivers/mmc/host/omap_hsmmc.c +++ b/drivers/mmc/host/omap_hsmmc.c @@ -2013,7 +2013,7 @@ static struct platform_driver omap_hsmmc_driver = { static int __init omap_hsmmc_init(void) { /* Register the MMC driver */ - return platform_driver_register(&omap_hsmmc_driver); + return platform_driver_probe(&omap_hsmmc_driver, omap_hsmmc_probe); } static void __exit omap_hsmmc_cleanup(void) diff --git a/drivers/mmc/host/pxamci.c b/drivers/mmc/host/pxamci.c index 5e0b1529964d..b00d67319058 100644 --- a/drivers/mmc/host/pxamci.c +++ b/drivers/mmc/host/pxamci.c @@ -693,7 +693,7 @@ static int pxamci_probe(struct platform_device *pdev) if (gpio_is_valid(gpio_ro)) { ret = gpio_request(gpio_ro, "mmc card read only"); if (ret) { - dev_err(&pdev->dev, "Failed requesting gpio_ro %d\n", gpio_power); + dev_err(&pdev->dev, "Failed requesting gpio_ro %d\n", gpio_ro); goto err_gpio_ro; } gpio_direction_input(gpio_ro); @@ -701,7 +701,7 @@ static int pxamci_probe(struct platform_device *pdev) if (gpio_is_valid(gpio_cd)) { ret = gpio_request(gpio_cd, "mmc card detect"); if (ret) { - dev_err(&pdev->dev, "Failed requesting gpio_cd %d\n", gpio_power); + dev_err(&pdev->dev, "Failed requesting gpio_cd %d\n", gpio_cd); goto err_gpio_cd; } gpio_direction_input(gpio_cd); diff --git a/drivers/mtd/devices/m25p80.c b/drivers/mtd/devices/m25p80.c index 379c316f329e..4c19269de91a 100644 --- a/drivers/mtd/devices/m25p80.c +++ b/drivers/mtd/devices/m25p80.c @@ -21,6 +21,7 @@ #include <linux/interrupt.h> #include <linux/mutex.h> #include <linux/math64.h> +#include <linux/sched.h> #include <linux/mtd/mtd.h> #include <linux/mtd/partitions.h> diff --git a/drivers/mtd/devices/sst25l.c b/drivers/mtd/devices/sst25l.c index c2baf3353f84..0a11721f146e 100644 --- a/drivers/mtd/devices/sst25l.c +++ b/drivers/mtd/devices/sst25l.c @@ -20,6 +20,7 @@ #include <linux/device.h> #include <linux/mutex.h> #include <linux/interrupt.h> +#include <linux/sched.h> #include <linux/mtd/mtd.h> #include <linux/mtd/partitions.h> diff --git a/drivers/mtd/maps/Kconfig b/drivers/mtd/maps/Kconfig index 841e085ab74a..14be0755d7cd 100644 --- a/drivers/mtd/maps/Kconfig +++ b/drivers/mtd/maps/Kconfig @@ -486,6 +486,7 @@ config MTD_BFIN_ASYNC config MTD_GPIO_ADDR tristate "GPIO-assisted Flash Chip Support" + depends on GENERIC_GPIO || GPIOLIB depends on MTD_COMPLEX_MAPPINGS select MTD_PARTITIONS help diff --git a/drivers/mtd/maps/Makefile b/drivers/mtd/maps/Makefile index 1d5cf8636723..ae2f6dbe43c3 100644 --- a/drivers/mtd/maps/Makefile +++ b/drivers/mtd/maps/Makefile @@ -58,4 +58,6 @@ obj-$(CONFIG_MTD_PLATRAM) += plat-ram.o obj-$(CONFIG_MTD_OMAP_NOR) += omap_nor.o obj-$(CONFIG_MTD_INTEL_VR_NOR) += intel_vr_nor.o obj-$(CONFIG_MTD_BFIN_ASYNC) += bfin-async-flash.o +obj-$(CONFIG_MTD_RBTX4939) += rbtx4939-flash.o +obj-$(CONFIG_MTD_VMU) += vmu-flash.o obj-$(CONFIG_MTD_GPIO_ADDR) += gpio-addr-flash.o diff --git a/drivers/mtd/maps/gpio-addr-flash.c b/drivers/mtd/maps/gpio-addr-flash.c index 44ef9a49a860..1ad5caf9fe69 100644 --- a/drivers/mtd/maps/gpio-addr-flash.c +++ b/drivers/mtd/maps/gpio-addr-flash.c @@ -13,7 +13,9 @@ * Licensed under the GPL-2 or later. */ +#include <linux/gpio.h> #include <linux/init.h> +#include <linux/io.h> #include <linux/kernel.h> #include <linux/module.h> #include <linux/mtd/mtd.h> @@ -23,9 +25,6 @@ #include <linux/platform_device.h> #include <linux/types.h> -#include <asm/gpio.h> -#include <asm/io.h> - #define pr_devinit(fmt, args...) ({ static const __devinitconst char __fmt[] = fmt; printk(__fmt, ## args); }) #define DRIVER_NAME "gpio-addr-flash" diff --git a/drivers/mtd/maps/sa1100-flash.c b/drivers/mtd/maps/sa1100-flash.c index fdb97f3d30e9..d7a47574d21e 100644 --- a/drivers/mtd/maps/sa1100-flash.c +++ b/drivers/mtd/maps/sa1100-flash.c @@ -209,8 +209,8 @@ static int sa1100_probe_subdev(struct sa_subdev_info *subdev, struct resource *r } subdev->mtd->owner = THIS_MODULE; - printk(KERN_INFO "SA1100 flash: CFI device at 0x%08lx, %dMiB, " - "%d-bit\n", phys, subdev->mtd->size >> 20, + printk(KERN_INFO "SA1100 flash: CFI device at 0x%08lx, %uMiB, %d-bit\n", + phys, (unsigned)(subdev->mtd->size >> 20), subdev->map.bankwidth * 8); return 0; diff --git a/drivers/mtd/nand/nand_base.c b/drivers/mtd/nand/nand_base.c index 22113865438b..2957cc70da3d 100644 --- a/drivers/mtd/nand/nand_base.c +++ b/drivers/mtd/nand/nand_base.c @@ -761,6 +761,7 @@ static int nand_wait(struct mtd_info *mtd, struct nand_chip *chip) * @mtd: mtd info structure * @chip: nand chip info structure * @buf: buffer to store read data + * @page: page number to read * * Not for syndrome calculating ecc controllers, which use a special oob layout */ @@ -777,6 +778,7 @@ static int nand_read_page_raw(struct mtd_info *mtd, struct nand_chip *chip, * @mtd: mtd info structure * @chip: nand chip info structure * @buf: buffer to store read data + * @page: page number to read * * We need a special oob layout and handling even when OOB isn't used. */ @@ -818,6 +820,7 @@ static int nand_read_page_raw_syndrome(struct mtd_info *mtd, struct nand_chip *c * @mtd: mtd info structure * @chip: nand chip info structure * @buf: buffer to store read data + * @page: page number to read */ static int nand_read_page_swecc(struct mtd_info *mtd, struct nand_chip *chip, uint8_t *buf, int page) @@ -939,6 +942,7 @@ static int nand_read_subpage(struct mtd_info *mtd, struct nand_chip *chip, uint3 * @mtd: mtd info structure * @chip: nand chip info structure * @buf: buffer to store read data + * @page: page number to read * * Not for syndrome calculating ecc controllers which need a special oob layout */ @@ -983,6 +987,7 @@ static int nand_read_page_hwecc(struct mtd_info *mtd, struct nand_chip *chip, * @mtd: mtd info structure * @chip: nand chip info structure * @buf: buffer to store read data + * @page: page number to read * * Hardware ECC for large page chips, require OOB to be read first. * For this ECC mode, the write_page method is re-used from ECC_HW. @@ -1031,6 +1036,7 @@ static int nand_read_page_hwecc_oob_first(struct mtd_info *mtd, * @mtd: mtd info structure * @chip: nand chip info structure * @buf: buffer to store read data + * @page: page number to read * * The hw generator calculates the error syndrome automatically. Therefor * we need a special oob layout and handling. diff --git a/drivers/mtd/ubi/build.c b/drivers/mtd/ubi/build.c index e1f7d0a78b9d..14cec04c34f9 100644 --- a/drivers/mtd/ubi/build.c +++ b/drivers/mtd/ubi/build.c @@ -42,6 +42,7 @@ #include <linux/log2.h> #include <linux/kthread.h> #include <linux/reboot.h> +#include <linux/kernel.h> #include "ubi.h" /* Maximum length of the 'mtd=' parameter */ @@ -1257,7 +1258,7 @@ static int __init bytes_str_to_int(const char *str) unsigned long result; result = simple_strtoul(str, &endp, 0); - if (str == endp || result < 0) { + if (str == endp || result >= INT_MAX) { printk(KERN_ERR "UBI error: incorrect bytes count: \"%s\"\n", str); return -EINVAL; diff --git a/drivers/mtd/ubi/scan.c b/drivers/mtd/ubi/scan.c index e7161adc419d..90af61a2c3e4 100644 --- a/drivers/mtd/ubi/scan.c +++ b/drivers/mtd/ubi/scan.c @@ -794,16 +794,15 @@ static int process_eb(struct ubi_device *ubi, struct ubi_scan_info *si, * number. */ image_seq = be32_to_cpu(ech->image_seq); - if (!si->image_seq_set) { + if (!ubi->image_seq && image_seq) ubi->image_seq = image_seq; - si->image_seq_set = 1; - } else if (ubi->image_seq && ubi->image_seq != image_seq) { + if (ubi->image_seq && image_seq && + ubi->image_seq != image_seq) { ubi_err("bad image sequence number %d in PEB %d, " "expected %d", image_seq, pnum, ubi->image_seq); ubi_dbg_dump_ec_hdr(ech); return -EINVAL; } - } /* OK, we've done with the EC header, let's look at the VID header */ diff --git a/drivers/mtd/ubi/scan.h b/drivers/mtd/ubi/scan.h index bab31695dace..ff179ad7ca55 100644 --- a/drivers/mtd/ubi/scan.h +++ b/drivers/mtd/ubi/scan.h @@ -103,7 +103,6 @@ struct ubi_scan_volume { * @ec_sum: a temporary variable used when calculating @mean_ec * @ec_count: a temporary variable used when calculating @mean_ec * @corr_count: count of corrupted PEBs - * @image_seq_set: indicates @ubi->image_seq is known * * This data structure contains the result of scanning and may be used by other * UBI sub-systems to build final UBI data structures, further error-recovery @@ -127,7 +126,6 @@ struct ubi_scan_info { uint64_t ec_sum; int ec_count; int corr_count; - int image_seq_set; }; struct ubi_device; diff --git a/drivers/net/bonding/bond_sysfs.c b/drivers/net/bonding/bond_sysfs.c index a59094f8bb6b..4e00b4f83641 100644 --- a/drivers/net/bonding/bond_sysfs.c +++ b/drivers/net/bonding/bond_sysfs.c @@ -22,6 +22,7 @@ #include <linux/kernel.h> #include <linux/module.h> #include <linux/device.h> +#include <linux/sched.h> #include <linux/sysdev.h> #include <linux/fs.h> #include <linux/types.h> diff --git a/drivers/net/cxgb3/sge.c b/drivers/net/cxgb3/sge.c index cf2e1d3c0d8d..49f3de79118c 100644 --- a/drivers/net/cxgb3/sge.c +++ b/drivers/net/cxgb3/sge.c @@ -879,7 +879,7 @@ recycle: pci_dma_sync_single_for_cpu(adap->pdev, dma_addr, len, PCI_DMA_FROMDEVICE); (*sd->pg_chunk.p_cnt)--; - if (!*sd->pg_chunk.p_cnt) + if (!*sd->pg_chunk.p_cnt && sd->pg_chunk.page != fl->pg_chunk.page) pci_unmap_page(adap->pdev, sd->pg_chunk.mapping, fl->alloc_size, @@ -2098,7 +2098,7 @@ static void lro_add_page(struct adapter *adap, struct sge_qset *qs, PCI_DMA_FROMDEVICE); (*sd->pg_chunk.p_cnt)--; - if (!*sd->pg_chunk.p_cnt) + if (!*sd->pg_chunk.p_cnt && sd->pg_chunk.page != fl->pg_chunk.page) pci_unmap_page(adap->pdev, sd->pg_chunk.mapping, fl->alloc_size, diff --git a/drivers/net/depca.c b/drivers/net/depca.c index 9686c1fa28f1..7a3bdac84abe 100644 --- a/drivers/net/depca.c +++ b/drivers/net/depca.c @@ -237,6 +237,7 @@ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/errno.h> #include <linux/ioport.h> diff --git a/drivers/net/e100.c b/drivers/net/e100.c index 7462fdfd7f92..a81c7b0c41b0 100644 --- a/drivers/net/e100.c +++ b/drivers/net/e100.c @@ -151,6 +151,7 @@ #include <linux/moduleparam.h> #include <linux/kernel.h> #include <linux/types.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/delay.h> #include <linux/init.h> diff --git a/drivers/net/eql.c b/drivers/net/eql.c index d4d9a3eda695..f5b96cadeb25 100644 --- a/drivers/net/eql.c +++ b/drivers/net/eql.c @@ -111,6 +111,7 @@ * Sorry, I had to rewrite most of this for 2.5.x -DaveM */ +#include <linux/capability.h> #include <linux/module.h> #include <linux/kernel.h> #include <linux/init.h> diff --git a/drivers/net/ethoc.c b/drivers/net/ethoc.c index 96b6dc42fc74..bd1db92aec1b 100644 --- a/drivers/net/ethoc.c +++ b/drivers/net/ethoc.c @@ -17,6 +17,7 @@ #include <linux/mii.h> #include <linux/phy.h> #include <linux/platform_device.h> +#include <linux/sched.h> #include <net/ethoc.h> static int buffer_size = 0x8000; /* 32 KBytes */ diff --git a/drivers/net/ewrk3.c b/drivers/net/ewrk3.c index b2a5ec8f3721..dd4ba01fd92d 100644 --- a/drivers/net/ewrk3.c +++ b/drivers/net/ewrk3.c @@ -145,6 +145,7 @@ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/errno.h> #include <linux/ioport.h> diff --git a/drivers/net/forcedeth.c b/drivers/net/forcedeth.c index 73fe97777201..3116601dbfea 100644 --- a/drivers/net/forcedeth.c +++ b/drivers/net/forcedeth.c @@ -49,6 +49,7 @@ #include <linux/netdevice.h> #include <linux/etherdevice.h> #include <linux/delay.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/ethtool.h> #include <linux/timer.h> diff --git a/drivers/net/hamachi.c b/drivers/net/hamachi.c index 18bd9fe20d77..c9ac46118e6f 100644 --- a/drivers/net/hamachi.c +++ b/drivers/net/hamachi.c @@ -145,6 +145,7 @@ static int tx_params[MAX_UNITS] = {-1, -1, -1, -1, -1, -1, -1, -1}; /* Time in jiffies before concluding the transmitter is hung. */ #define TX_TIMEOUT (5*HZ) +#include <linux/capability.h> #include <linux/module.h> #include <linux/kernel.h> #include <linux/string.h> diff --git a/drivers/net/hamradio/baycom_epp.c b/drivers/net/hamradio/baycom_epp.c index b3cf95d76040..a3c0dc9d8b98 100644 --- a/drivers/net/hamradio/baycom_epp.c +++ b/drivers/net/hamradio/baycom_epp.c @@ -44,6 +44,7 @@ #include <linux/module.h> #include <linux/kernel.h> #include <linux/init.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/workqueue.h> #include <linux/fs.h> diff --git a/drivers/net/hamradio/baycom_ser_fdx.c b/drivers/net/hamradio/baycom_ser_fdx.c index aa4488e871b2..ed60fd664273 100644 --- a/drivers/net/hamradio/baycom_ser_fdx.c +++ b/drivers/net/hamradio/baycom_ser_fdx.c @@ -71,6 +71,7 @@ /*****************************************************************************/ +#include <linux/capability.h> #include <linux/module.h> #include <linux/ioport.h> #include <linux/string.h> diff --git a/drivers/net/hamradio/baycom_ser_hdx.c b/drivers/net/hamradio/baycom_ser_hdx.c index 88c593596020..1686f6dcbbce 100644 --- a/drivers/net/hamradio/baycom_ser_hdx.c +++ b/drivers/net/hamradio/baycom_ser_hdx.c @@ -61,6 +61,7 @@ /*****************************************************************************/ +#include <linux/capability.h> #include <linux/module.h> #include <linux/ioport.h> #include <linux/string.h> diff --git a/drivers/net/hamradio/hdlcdrv.c b/drivers/net/hamradio/hdlcdrv.c index 0013c409782c..91c5790c9581 100644 --- a/drivers/net/hamradio/hdlcdrv.c +++ b/drivers/net/hamradio/hdlcdrv.c @@ -42,6 +42,7 @@ /*****************************************************************************/ +#include <linux/capability.h> #include <linux/module.h> #include <linux/types.h> #include <linux/net.h> diff --git a/drivers/net/hp100.c b/drivers/net/hp100.c index a9a1a99f02dd..dd8665138062 100644 --- a/drivers/net/hp100.c +++ b/drivers/net/hp100.c @@ -98,6 +98,7 @@ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/errno.h> #include <linux/ioport.h> diff --git a/drivers/net/ibm_newemac/emac.h b/drivers/net/ibm_newemac/emac.h index d34adf99fc6a..8a61b597a169 100644 --- a/drivers/net/ibm_newemac/emac.h +++ b/drivers/net/ibm_newemac/emac.h @@ -263,8 +263,8 @@ struct emac_regs { /* EMACx_TRTR */ -#define EMAC_TRTR_SHIFT_EMAC4 27 -#define EMAC_TRTR_SHIFT 24 +#define EMAC_TRTR_SHIFT_EMAC4 24 +#define EMAC_TRTR_SHIFT 27 /* EMAC specific TX descriptor control fields (write access) */ #define EMAC_TX_CTRL_GFCS 0x0200 diff --git a/drivers/net/igb/igb_ethtool.c b/drivers/net/igb/igb_ethtool.c index c1cde5b44906..88e13f7e566f 100644 --- a/drivers/net/igb/igb_ethtool.c +++ b/drivers/net/igb/igb_ethtool.c @@ -34,6 +34,7 @@ #include <linux/interrupt.h> #include <linux/if_ether.h> #include <linux/ethtool.h> +#include <linux/sched.h> #include "igb.h" diff --git a/drivers/net/irda/toim3232-sir.c b/drivers/net/irda/toim3232-sir.c index fcf287b749db..99e1ec02a011 100644 --- a/drivers/net/irda/toim3232-sir.c +++ b/drivers/net/irda/toim3232-sir.c @@ -120,6 +120,7 @@ #include <linux/module.h> #include <linux/delay.h> #include <linux/init.h> +#include <linux/sched.h> #include <net/irda/irda.h> diff --git a/drivers/net/mlx4/main.c b/drivers/net/mlx4/main.c index 3dd481e77f92..291a505fd4fc 100644 --- a/drivers/net/mlx4/main.c +++ b/drivers/net/mlx4/main.c @@ -1282,6 +1282,8 @@ static struct pci_device_id mlx4_pci_table[] = { { PCI_VDEVICE(MELLANOX, 0x6372) }, /* MT25458 ConnectX EN 10GBASE-T 10GigE */ { PCI_VDEVICE(MELLANOX, 0x675a) }, /* MT25458 ConnectX EN 10GBASE-T+Gen2 10GigE */ { PCI_VDEVICE(MELLANOX, 0x6764) }, /* MT26468 ConnectX EN 10GigE PCIe gen2*/ + { PCI_VDEVICE(MELLANOX, 0x6746) }, /* MT26438 ConnectX EN 40GigE PCIe gen2 5GT/s */ + { PCI_VDEVICE(MELLANOX, 0x676e) }, /* MT26478 ConnectX2 40GigE PCIe gen2 */ { 0, } }; diff --git a/drivers/net/ns83820.c b/drivers/net/ns83820.c index c594e1946476..57fd483dbb1f 100644 --- a/drivers/net/ns83820.c +++ b/drivers/net/ns83820.c @@ -111,6 +111,7 @@ #include <linux/compiler.h> #include <linux/prefetch.h> #include <linux/ethtool.h> +#include <linux/sched.h> #include <linux/timer.h> #include <linux/if_vlan.h> #include <linux/rtnetlink.h> diff --git a/drivers/net/pcnet32.c b/drivers/net/pcnet32.c index 6d28b18e7e28..c1b3f09f452c 100644 --- a/drivers/net/pcnet32.c +++ b/drivers/net/pcnet32.c @@ -31,6 +31,7 @@ static const char *const version = #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/errno.h> #include <linux/ioport.h> diff --git a/drivers/net/phy/mdio-gpio.c b/drivers/net/phy/mdio-gpio.c index 8659d341e769..35897134a5dd 100644 --- a/drivers/net/phy/mdio-gpio.c +++ b/drivers/net/phy/mdio-gpio.c @@ -139,7 +139,7 @@ out: return NULL; } -static void __devinit mdio_gpio_bus_deinit(struct device *dev) +static void mdio_gpio_bus_deinit(struct device *dev) { struct mii_bus *bus = dev_get_drvdata(dev); struct mdio_gpio_info *bitbang = bus->priv; diff --git a/drivers/net/sb1000.c b/drivers/net/sb1000.c index ee366c5a8fa3..c9c70ab0cce0 100644 --- a/drivers/net/sb1000.c +++ b/drivers/net/sb1000.c @@ -36,6 +36,7 @@ static char version[] = "sb1000.c:v1.1.2 6/01/98 (fventuri@mediaone.net)\n"; #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/interrupt.h> #include <linux/errno.h> diff --git a/drivers/net/sfc/falcon_boards.c b/drivers/net/sfc/falcon_boards.c index 99f737223b10..d31c134981fd 100644 --- a/drivers/net/sfc/falcon_boards.c +++ b/drivers/net/sfc/falcon_boards.c @@ -327,7 +327,7 @@ static int sfn4111t_reset(struct efx_nic *efx) efx_oword_t reg; /* GPIO 3 and the GPIO register are shared with I2C, so block that */ - mutex_lock(&efx->i2c_adap.bus_lock); + i2c_lock_adapter(&efx->i2c_adap); /* Pull RST_N (GPIO 2) low then let it up again, setting the * FLASH_CFG_1 strap (GPIO 3) appropriately. Only change the @@ -343,7 +343,7 @@ static int sfn4111t_reset(struct efx_nic *efx) efx_writeo(efx, ®, FR_AB_GPIO_CTL); msleep(1); - mutex_unlock(&efx->i2c_adap.bus_lock); + i2c_unlock_adapter(&efx->i2c_adap); ssleep(1); return 0; diff --git a/drivers/net/sis900.c b/drivers/net/sis900.c index 97949d0a699b..c072f7f36acf 100644 --- a/drivers/net/sis900.c +++ b/drivers/net/sis900.c @@ -52,6 +52,7 @@ #include <linux/module.h> #include <linux/moduleparam.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/timer.h> #include <linux/errno.h> diff --git a/drivers/net/skfp/skfddi.c b/drivers/net/skfp/skfddi.c index 38a508b4aad9..b27156eaf267 100644 --- a/drivers/net/skfp/skfddi.c +++ b/drivers/net/skfp/skfddi.c @@ -73,6 +73,7 @@ static const char * const boot_msg = /* Include files */ +#include <linux/capability.h> #include <linux/module.h> #include <linux/kernel.h> #include <linux/errno.h> diff --git a/drivers/net/skge.c b/drivers/net/skge.c index be28ebb3811c..ba5eb14094ef 100644 --- a/drivers/net/skge.c +++ b/drivers/net/skge.c @@ -37,6 +37,7 @@ #include <linux/crc32.h> #include <linux/dma-mapping.h> #include <linux/debugfs.h> +#include <linux/sched.h> #include <linux/seq_file.h> #include <linux/mii.h> #include <asm/irq.h> diff --git a/drivers/net/slip.c b/drivers/net/slip.c index ccfe45924fd9..6640469b5d3b 100644 --- a/drivers/net/slip.c +++ b/drivers/net/slip.c @@ -67,6 +67,7 @@ #include <asm/system.h> #include <asm/uaccess.h> #include <linux/bitops.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/mm.h> #include <linux/interrupt.h> diff --git a/drivers/net/sungem.c b/drivers/net/sungem.c index d6f4faf5bbcb..b571a1babab9 100644 --- a/drivers/net/sungem.c +++ b/drivers/net/sungem.c @@ -38,6 +38,7 @@ #include <linux/interrupt.h> #include <linux/ioport.h> #include <linux/in.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/string.h> #include <linux/delay.h> @@ -2060,7 +2061,15 @@ static int gem_check_invariants(struct gem *gp) mif_cfg &= ~MIF_CFG_PSELECT; writel(mif_cfg, gp->regs + MIF_CFG); } else { - gp->phy_type = phy_serialink; +#ifdef CONFIG_SPARC + const char *p; + + p = of_get_property(gp->of_node, "shared-pins", NULL); + if (p && !strcmp(p, "serdes")) + gp->phy_type = phy_serdes; + else +#endif + gp->phy_type = phy_serialink; } if (gp->phy_type == phy_mii_mdio1 || gp->phy_type == phy_mii_mdio0) { diff --git a/drivers/net/tokenring/ibmtr.c b/drivers/net/tokenring/ibmtr.c index 6a3c7510afd9..75fa32e34fd0 100644 --- a/drivers/net/tokenring/ibmtr.c +++ b/drivers/net/tokenring/ibmtr.c @@ -108,6 +108,7 @@ in the event that chatty debug messages are desired - jjs 12/30/98 */ #define IBMTR_DEBUG_MESSAGES 0 #include <linux/module.h> +#include <linux/sched.h> #ifdef PCMCIA /* required for ibmtr_cs.c to build */ #undef MODULE /* yes, really */ diff --git a/drivers/net/typhoon.c b/drivers/net/typhoon.c index 4b7541024424..079a97000e5b 100644 --- a/drivers/net/typhoon.c +++ b/drivers/net/typhoon.c @@ -108,6 +108,7 @@ static const int multicast_filter_limit = 32; #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/timer.h> #include <linux/errno.h> diff --git a/drivers/net/usb/rndis_host.c b/drivers/net/usb/rndis_host.c index 0caa8008c51c..f56dec6119c3 100644 --- a/drivers/net/usb/rndis_host.c +++ b/drivers/net/usb/rndis_host.c @@ -362,12 +362,12 @@ generic_rndis_bind(struct usbnet *dev, struct usb_interface *intf, int flags) retval = -EINVAL; goto halt_fail_and_release; } - dev->hard_mtu = tmp; - net->mtu = dev->hard_mtu - net->hard_header_len; dev_warn(&intf->dev, "dev can't take %u byte packets (max %u), " "adjusting MTU to %u\n", - dev->hard_mtu, tmp, net->mtu); + dev->hard_mtu, tmp, tmp - net->hard_header_len); + dev->hard_mtu = tmp; + net->mtu = dev->hard_mtu - net->hard_header_len; } /* REVISIT: peripheral "alignment" request is ignored ... */ diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c index 22a8ca5d67d5..74636c5c41f0 100644 --- a/drivers/net/virtio_net.c +++ b/drivers/net/virtio_net.c @@ -22,7 +22,6 @@ #include <linux/ethtool.h> #include <linux/module.h> #include <linux/virtio.h> -#include <linux/virtio_ids.h> #include <linux/virtio_net.h> #include <linux/scatterlist.h> #include <linux/if_vlan.h> diff --git a/drivers/net/wan/c101.c b/drivers/net/wan/c101.c index 9693b0fd323d..0bd898c94759 100644 --- a/drivers/net/wan/c101.c +++ b/drivers/net/wan/c101.c @@ -16,6 +16,7 @@ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/capability.h> #include <linux/slab.h> #include <linux/types.h> #include <linux/string.h> diff --git a/drivers/net/wan/cosa.c b/drivers/net/wan/cosa.c index 2eceb1a24df2..cd8f04afed8f 100644 --- a/drivers/net/wan/cosa.c +++ b/drivers/net/wan/cosa.c @@ -76,6 +76,7 @@ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/poll.h> #include <linux/fs.h> diff --git a/drivers/net/wan/cycx_x25.c b/drivers/net/wan/cycx_x25.c index 2573c18b6aa5..cd8cb95c5bd7 100644 --- a/drivers/net/wan/cycx_x25.c +++ b/drivers/net/wan/cycx_x25.c @@ -84,6 +84,7 @@ #include <linux/kernel.h> /* printk(), and other useful stuff */ #include <linux/module.h> #include <linux/string.h> /* inline memset(), etc. */ +#include <linux/sched.h> #include <linux/slab.h> /* kmalloc(), kfree() */ #include <linux/stddef.h> /* offsetof(), etc. */ #include <linux/wanrouter.h> /* WAN router definitions */ diff --git a/drivers/net/wan/dscc4.c b/drivers/net/wan/dscc4.c index 63a010252a37..3f759daf3ca4 100644 --- a/drivers/net/wan/dscc4.c +++ b/drivers/net/wan/dscc4.c @@ -81,6 +81,7 @@ */ #include <linux/module.h> +#include <linux/sched.h> #include <linux/types.h> #include <linux/errno.h> #include <linux/list.h> diff --git a/drivers/net/wan/farsync.c b/drivers/net/wan/farsync.c index 3e90eb816181..beda387f2fc7 100644 --- a/drivers/net/wan/farsync.c +++ b/drivers/net/wan/farsync.c @@ -19,6 +19,7 @@ #include <linux/kernel.h> #include <linux/version.h> #include <linux/pci.h> +#include <linux/sched.h> #include <linux/ioport.h> #include <linux/init.h> #include <linux/if.h> diff --git a/drivers/net/wan/n2.c b/drivers/net/wan/n2.c index 83da596e2052..58c66819f39b 100644 --- a/drivers/net/wan/n2.c +++ b/drivers/net/wan/n2.c @@ -18,6 +18,7 @@ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/capability.h> #include <linux/slab.h> #include <linux/types.h> #include <linux/fcntl.h> diff --git a/drivers/net/wan/pci200syn.c b/drivers/net/wan/pci200syn.c index a52f29c72c33..f1340faaf022 100644 --- a/drivers/net/wan/pci200syn.c +++ b/drivers/net/wan/pci200syn.c @@ -16,6 +16,7 @@ #include <linux/module.h> #include <linux/kernel.h> +#include <linux/capability.h> #include <linux/slab.h> #include <linux/types.h> #include <linux/fcntl.h> diff --git a/drivers/net/wireless/b43/pio.c b/drivers/net/wireless/b43/pio.c index 7d2550269ede..c01b8e02412f 100644 --- a/drivers/net/wireless/b43/pio.c +++ b/drivers/net/wireless/b43/pio.c @@ -30,6 +30,7 @@ #include "xmit.h" #include <linux/delay.h> +#include <linux/sched.h> static u16 generate_cookie(struct b43_pio_txqueue *q, diff --git a/drivers/net/wireless/b43legacy/main.c b/drivers/net/wireless/b43legacy/main.c index d579bb9035c4..ab6a18c2e9d9 100644 --- a/drivers/net/wireless/b43legacy/main.c +++ b/drivers/net/wireless/b43legacy/main.c @@ -37,6 +37,7 @@ #include <linux/firmware.h> #include <linux/wireless.h> #include <linux/workqueue.h> +#include <linux/sched.h> #include <linux/skbuff.h> #include <linux/dma-mapping.h> #include <net/dst.h> diff --git a/drivers/net/wireless/b43legacy/phy.c b/drivers/net/wireless/b43legacy/phy.c index 11319ec2d64a..aaf227203a98 100644 --- a/drivers/net/wireless/b43legacy/phy.c +++ b/drivers/net/wireless/b43legacy/phy.c @@ -31,6 +31,7 @@ #include <linux/delay.h> #include <linux/pci.h> +#include <linux/sched.h> #include <linux/types.h> #include "b43legacy.h" diff --git a/drivers/net/wireless/hostap/hostap_info.c b/drivers/net/wireless/hostap/hostap_info.c index 6fa14a4e4b53..4dfb40a84c96 100644 --- a/drivers/net/wireless/hostap/hostap_info.c +++ b/drivers/net/wireless/hostap/hostap_info.c @@ -1,6 +1,7 @@ /* Host AP driver Info Frame processing (part of hostap.o module) */ #include <linux/if_arp.h> +#include <linux/sched.h> #include "hostap_wlan.h" #include "hostap.h" #include "hostap_ap.h" diff --git a/drivers/net/wireless/hostap/hostap_ioctl.c b/drivers/net/wireless/hostap/hostap_ioctl.c index 3f2bda881a4f..9419cebca8a5 100644 --- a/drivers/net/wireless/hostap/hostap_ioctl.c +++ b/drivers/net/wireless/hostap/hostap_ioctl.c @@ -1,6 +1,7 @@ /* ioctl() (mostly Linux Wireless Extensions) routines for Host AP driver */ #include <linux/types.h> +#include <linux/sched.h> #include <linux/ethtool.h> #include <linux/if_arp.h> #include <net/lib80211.h> diff --git a/drivers/net/wireless/ipw2x00/ipw2200.c b/drivers/net/wireless/ipw2x00/ipw2200.c index 9b398db2d740..9fe0e8078a88 100644 --- a/drivers/net/wireless/ipw2x00/ipw2200.c +++ b/drivers/net/wireless/ipw2x00/ipw2200.c @@ -30,6 +30,7 @@ ******************************************************************************/ +#include <linux/sched.h> #include "ipw2200.h" diff --git a/drivers/net/wireless/iwlwifi/iwl-3945.c b/drivers/net/wireless/iwlwifi/iwl-3945.c index 26a1134f84a2..7da1dab933d9 100644 --- a/drivers/net/wireless/iwlwifi/iwl-3945.c +++ b/drivers/net/wireless/iwlwifi/iwl-3945.c @@ -30,6 +30,7 @@ #include <linux/pci.h> #include <linux/dma-mapping.h> #include <linux/delay.h> +#include <linux/sched.h> #include <linux/skbuff.h> #include <linux/netdevice.h> #include <linux/wireless.h> diff --git a/drivers/net/wireless/iwlwifi/iwl-4965.c b/drivers/net/wireless/iwlwifi/iwl-4965.c index 1d22ea390c00..cc3942448703 100644 --- a/drivers/net/wireless/iwlwifi/iwl-4965.c +++ b/drivers/net/wireless/iwlwifi/iwl-4965.c @@ -30,6 +30,7 @@ #include <linux/pci.h> #include <linux/dma-mapping.h> #include <linux/delay.h> +#include <linux/sched.h> #include <linux/skbuff.h> #include <linux/netdevice.h> #include <linux/wireless.h> diff --git a/drivers/net/wireless/iwlwifi/iwl-5000.c b/drivers/net/wireless/iwlwifi/iwl-5000.c index 6eaf26b07636..e23d301e816f 100644 --- a/drivers/net/wireless/iwlwifi/iwl-5000.c +++ b/drivers/net/wireless/iwlwifi/iwl-5000.c @@ -29,6 +29,7 @@ #include <linux/pci.h> #include <linux/dma-mapping.h> #include <linux/delay.h> +#include <linux/sched.h> #include <linux/skbuff.h> #include <linux/netdevice.h> #include <linux/wireless.h> diff --git a/drivers/net/wireless/iwlwifi/iwl-agn.c b/drivers/net/wireless/iwlwifi/iwl-agn.c index da0b38e866ba..29f7510ecdd7 100644 --- a/drivers/net/wireless/iwlwifi/iwl-agn.c +++ b/drivers/net/wireless/iwlwifi/iwl-agn.c @@ -33,6 +33,7 @@ #include <linux/pci.h> #include <linux/dma-mapping.h> #include <linux/delay.h> +#include <linux/sched.h> #include <linux/skbuff.h> #include <linux/netdevice.h> #include <linux/wireless.h> diff --git a/drivers/net/wireless/iwlwifi/iwl-core.c b/drivers/net/wireless/iwlwifi/iwl-core.c index d09e74815323..6b18aab8fa9b 100644 --- a/drivers/net/wireless/iwlwifi/iwl-core.c +++ b/drivers/net/wireless/iwlwifi/iwl-core.c @@ -29,6 +29,7 @@ #include <linux/kernel.h> #include <linux/module.h> #include <linux/etherdevice.h> +#include <linux/sched.h> #include <net/mac80211.h> #include "iwl-eeprom.h" diff --git a/drivers/net/wireless/iwlwifi/iwl-hcmd.c b/drivers/net/wireless/iwlwifi/iwl-hcmd.c index e8002c1d3eba..a23165948202 100644 --- a/drivers/net/wireless/iwlwifi/iwl-hcmd.c +++ b/drivers/net/wireless/iwlwifi/iwl-hcmd.c @@ -28,6 +28,7 @@ #include <linux/kernel.h> #include <linux/module.h> +#include <linux/sched.h> #include <net/mac80211.h> #include "iwl-dev.h" /* FIXME: remove */ diff --git a/drivers/net/wireless/iwlwifi/iwl-tx.c b/drivers/net/wireless/iwlwifi/iwl-tx.c index 9370e062000d..6199bf60d313 100644 --- a/drivers/net/wireless/iwlwifi/iwl-tx.c +++ b/drivers/net/wireless/iwlwifi/iwl-tx.c @@ -28,6 +28,7 @@ *****************************************************************************/ #include <linux/etherdevice.h> +#include <linux/sched.h> #include <net/mac80211.h> #include "iwl-eeprom.h" #include "iwl-dev.h" diff --git a/drivers/net/wireless/iwlwifi/iwl3945-base.c b/drivers/net/wireless/iwlwifi/iwl3945-base.c index 05f118529fea..5d26330b43e8 100644 --- a/drivers/net/wireless/iwlwifi/iwl3945-base.c +++ b/drivers/net/wireless/iwlwifi/iwl3945-base.c @@ -33,6 +33,7 @@ #include <linux/pci.h> #include <linux/dma-mapping.h> #include <linux/delay.h> +#include <linux/sched.h> #include <linux/skbuff.h> #include <linux/netdevice.h> #include <linux/wireless.h> diff --git a/drivers/net/wireless/iwmc3200wifi/cfg80211.c b/drivers/net/wireless/iwmc3200wifi/cfg80211.c index af72cc746f15..2e00a4b389e6 100644 --- a/drivers/net/wireless/iwmc3200wifi/cfg80211.c +++ b/drivers/net/wireless/iwmc3200wifi/cfg80211.c @@ -23,6 +23,7 @@ #include <linux/kernel.h> #include <linux/netdevice.h> +#include <linux/sched.h> #include <linux/etherdevice.h> #include <linux/wireless.h> #include <linux/ieee80211.h> diff --git a/drivers/net/wireless/iwmc3200wifi/commands.c b/drivers/net/wireless/iwmc3200wifi/commands.c index cad511afd907..7e12438551ba 100644 --- a/drivers/net/wireless/iwmc3200wifi/commands.c +++ b/drivers/net/wireless/iwmc3200wifi/commands.c @@ -40,6 +40,7 @@ #include <linux/wireless.h> #include <linux/etherdevice.h> #include <linux/ieee80211.h> +#include <linux/sched.h> #include "iwm.h" #include "bus.h" diff --git a/drivers/net/wireless/iwmc3200wifi/main.c b/drivers/net/wireless/iwmc3200wifi/main.c index f93e9139b0f2..75f105a59543 100644 --- a/drivers/net/wireless/iwmc3200wifi/main.c +++ b/drivers/net/wireless/iwmc3200wifi/main.c @@ -38,6 +38,7 @@ #include <linux/kernel.h> #include <linux/netdevice.h> +#include <linux/sched.h> #include <linux/ieee80211.h> #include <linux/wireless.h> diff --git a/drivers/net/wireless/iwmc3200wifi/rx.c b/drivers/net/wireless/iwmc3200wifi/rx.c index 3ad95dc0dd8d..bdb1d7e7979d 100644 --- a/drivers/net/wireless/iwmc3200wifi/rx.c +++ b/drivers/net/wireless/iwmc3200wifi/rx.c @@ -38,6 +38,7 @@ #include <linux/kernel.h> #include <linux/netdevice.h> +#include <linux/sched.h> #include <linux/etherdevice.h> #include <linux/wireless.h> #include <linux/ieee80211.h> diff --git a/drivers/net/wireless/libertas/tx.c b/drivers/net/wireless/libertas/tx.c index 5d7c011fe296..eb856adbf8ea 100644 --- a/drivers/net/wireless/libertas/tx.c +++ b/drivers/net/wireless/libertas/tx.c @@ -3,6 +3,7 @@ */ #include <linux/netdevice.h> #include <linux/etherdevice.h> +#include <linux/sched.h> #include "host.h" #include "radiotap.h" diff --git a/drivers/net/wireless/prism54/isl_ioctl.c b/drivers/net/wireless/prism54/isl_ioctl.c index 4c97c6ad6f5d..bc08464d8323 100644 --- a/drivers/net/wireless/prism54/isl_ioctl.c +++ b/drivers/net/wireless/prism54/isl_ioctl.c @@ -19,6 +19,7 @@ * */ +#include <linux/capability.h> #include <linux/module.h> #include <linux/kernel.h> #include <linux/if_arp.h> diff --git a/drivers/net/wireless/prism54/islpci_dev.c b/drivers/net/wireless/prism54/islpci_dev.c index 3e6a71ce5b54..a3ba3539db02 100644 --- a/drivers/net/wireless/prism54/islpci_dev.c +++ b/drivers/net/wireless/prism54/islpci_dev.c @@ -23,6 +23,7 @@ #include <linux/netdevice.h> #include <linux/ethtool.h> #include <linux/pci.h> +#include <linux/sched.h> #include <linux/etherdevice.h> #include <linux/delay.h> #include <linux/if_arp.h> diff --git a/drivers/net/wireless/prism54/islpci_mgt.c b/drivers/net/wireless/prism54/islpci_mgt.c index f7c677e2094d..69d2f882fd06 100644 --- a/drivers/net/wireless/prism54/islpci_mgt.c +++ b/drivers/net/wireless/prism54/islpci_mgt.c @@ -20,6 +20,7 @@ #include <linux/netdevice.h> #include <linux/module.h> #include <linux/pci.h> +#include <linux/sched.h> #include <asm/io.h> #include <asm/system.h> diff --git a/drivers/net/wireless/ray_cs.c b/drivers/net/wireless/ray_cs.c index 595e4414d770..5ee9d2a19360 100644 --- a/drivers/net/wireless/ray_cs.c +++ b/drivers/net/wireless/ray_cs.c @@ -2879,7 +2879,7 @@ static int write_essid(struct file *file, const char __user *buffer, unsigned long count, void *data) { static char proc_essid[33]; - int len = count; + unsigned int len = count; if (len > 32) len = 32; diff --git a/drivers/net/wireless/rt2x00/rt2x00debug.c b/drivers/net/wireless/rt2x00/rt2x00debug.c index e6b0fbbc3fc7..7d323a763b54 100644 --- a/drivers/net/wireless/rt2x00/rt2x00debug.c +++ b/drivers/net/wireless/rt2x00/rt2x00debug.c @@ -27,6 +27,7 @@ #include <linux/kernel.h> #include <linux/module.h> #include <linux/poll.h> +#include <linux/sched.h> #include <linux/uaccess.h> #include "rt2x00.h" diff --git a/drivers/of/of_mdio.c b/drivers/of/of_mdio.c index bacaa536fd51..4b22ba568b19 100644 --- a/drivers/of/of_mdio.c +++ b/drivers/of/of_mdio.c @@ -97,6 +97,12 @@ int of_mdiobus_register(struct mii_bus *mdio, struct device_node *np) } EXPORT_SYMBOL(of_mdiobus_register); +/* Helper function for of_phy_find_device */ +static int of_phy_match(struct device *dev, void *phy_np) +{ + return dev_archdata_get_node(&dev->archdata) == phy_np; +} + /** * of_phy_find_device - Give a PHY node, find the phy_device * @phy_np: Pointer to the phy's device tree node @@ -106,15 +112,10 @@ EXPORT_SYMBOL(of_mdiobus_register); struct phy_device *of_phy_find_device(struct device_node *phy_np) { struct device *d; - int match(struct device *dev, void *phy_np) - { - return dev_archdata_get_node(&dev->archdata) == phy_np; - } - if (!phy_np) return NULL; - d = bus_find_device(&mdio_bus_type, NULL, phy_np, match); + d = bus_find_device(&mdio_bus_type, NULL, phy_np, of_phy_match); return d ? to_phy_device(d) : NULL; } EXPORT_SYMBOL(of_phy_find_device); diff --git a/drivers/oprofile/event_buffer.c b/drivers/oprofile/event_buffer.c index 2b7ae366ceb1..5df60a6b6776 100644 --- a/drivers/oprofile/event_buffer.c +++ b/drivers/oprofile/event_buffer.c @@ -35,12 +35,23 @@ static size_t buffer_pos; /* atomic_t because wait_event checks it outside of buffer_mutex */ static atomic_t buffer_ready = ATOMIC_INIT(0); -/* Add an entry to the event buffer. When we - * get near to the end we wake up the process - * sleeping on the read() of the file. +/* + * Add an entry to the event buffer. When we get near to the end we + * wake up the process sleeping on the read() of the file. To protect + * the event_buffer this function may only be called when buffer_mutex + * is set. */ void add_event_entry(unsigned long value) { + /* + * This shouldn't happen since all workqueues or handlers are + * canceled or flushed before the event buffer is freed. + */ + if (!event_buffer) { + WARN_ON_ONCE(1); + return; + } + if (buffer_pos == buffer_size) { atomic_inc(&oprofile_stats.event_lost_overflow); return; @@ -69,7 +80,6 @@ void wake_up_buffer_waiter(void) int alloc_event_buffer(void) { - int err = -ENOMEM; unsigned long flags; spin_lock_irqsave(&oprofilefs_lock, flags); @@ -80,21 +90,22 @@ int alloc_event_buffer(void) if (buffer_watershed >= buffer_size) return -EINVAL; + buffer_pos = 0; event_buffer = vmalloc(sizeof(unsigned long) * buffer_size); if (!event_buffer) - goto out; + return -ENOMEM; - err = 0; -out: - return err; + return 0; } void free_event_buffer(void) { + mutex_lock(&buffer_mutex); vfree(event_buffer); - + buffer_pos = 0; event_buffer = NULL; + mutex_unlock(&buffer_mutex); } @@ -167,6 +178,12 @@ static ssize_t event_buffer_read(struct file *file, char __user *buf, mutex_lock(&buffer_mutex); + /* May happen if the buffer is freed during pending reads. */ + if (!event_buffer) { + retval = -EINTR; + goto out; + } + atomic_set(&buffer_ready, 0); retval = -EFAULT; diff --git a/drivers/pci/dmar.c b/drivers/pci/dmar.c index 14bbaa17e2ca..e5f8fc164fd3 100644 --- a/drivers/pci/dmar.c +++ b/drivers/pci/dmar.c @@ -175,15 +175,6 @@ dmar_parse_one_drhd(struct acpi_dmar_header *header) int ret = 0; drhd = (struct acpi_dmar_hardware_unit *)header; - if (!drhd->address) { - /* Promote an attitude of violence to a BIOS engineer today */ - WARN(1, "Your BIOS is broken; DMAR reported at address zero!\n" - "BIOS vendor: %s; Ver: %s; Product Version: %s\n", - dmi_get_system_info(DMI_BIOS_VENDOR), - dmi_get_system_info(DMI_BIOS_VERSION), - dmi_get_system_info(DMI_PRODUCT_VERSION)); - return -ENODEV; - } dmaru = kzalloc(sizeof(*dmaru), GFP_KERNEL); if (!dmaru) return -ENOMEM; @@ -354,6 +345,7 @@ dmar_table_print_dmar_entry(struct acpi_dmar_header *header) struct acpi_dmar_hardware_unit *drhd; struct acpi_dmar_reserved_memory *rmrr; struct acpi_dmar_atsr *atsr; + struct acpi_dmar_rhsa *rhsa; switch (header->type) { case ACPI_DMAR_TYPE_HARDWARE_UNIT: @@ -375,6 +367,12 @@ dmar_table_print_dmar_entry(struct acpi_dmar_header *header) atsr = container_of(header, struct acpi_dmar_atsr, header); printk(KERN_INFO PREFIX "ATSR flags: %#x\n", atsr->flags); break; + case ACPI_DMAR_HARDWARE_AFFINITY: + rhsa = container_of(header, struct acpi_dmar_rhsa, header); + printk(KERN_INFO PREFIX "RHSA base: %#016Lx proximity domain: %#x\n", + (unsigned long long)rhsa->base_address, + rhsa->proximity_domain); + break; } } @@ -459,9 +457,13 @@ parse_dmar_table(void) ret = dmar_parse_one_atsr(entry_header); #endif break; + case ACPI_DMAR_HARDWARE_AFFINITY: + /* We don't do anything with RHSA (yet?) */ + break; default: printk(KERN_WARNING PREFIX - "Unknown DMAR structure type\n"); + "Unknown DMAR structure type %d\n", + entry_header->type); ret = 0; /* for forward compatibility */ break; } @@ -580,12 +582,50 @@ int __init dmar_table_init(void) return 0; } +int __init check_zero_address(void) +{ + struct acpi_table_dmar *dmar; + struct acpi_dmar_header *entry_header; + struct acpi_dmar_hardware_unit *drhd; + + dmar = (struct acpi_table_dmar *)dmar_tbl; + entry_header = (struct acpi_dmar_header *)(dmar + 1); + + while (((unsigned long)entry_header) < + (((unsigned long)dmar) + dmar_tbl->length)) { + /* Avoid looping forever on bad ACPI tables */ + if (entry_header->length == 0) { + printk(KERN_WARNING PREFIX + "Invalid 0-length structure\n"); + return 0; + } + + if (entry_header->type == ACPI_DMAR_TYPE_HARDWARE_UNIT) { + drhd = (void *)entry_header; + if (!drhd->address) { + /* Promote an attitude of violence to a BIOS engineer today */ + WARN(1, "Your BIOS is broken; DMAR reported at address zero!\n" + "BIOS vendor: %s; Ver: %s; Product Version: %s\n", + dmi_get_system_info(DMI_BIOS_VENDOR), + dmi_get_system_info(DMI_BIOS_VERSION), + dmi_get_system_info(DMI_PRODUCT_VERSION)); + return 0; + } + break; + } + + entry_header = ((void *)entry_header + entry_header->length); + } + return 1; +} + void __init detect_intel_iommu(void) { int ret; ret = dmar_table_detect(); - + if (ret) + ret = check_zero_address(); { #ifdef CONFIG_INTR_REMAP struct acpi_table_dmar *dmar; diff --git a/drivers/pci/hotplug/cpqphp.h b/drivers/pci/hotplug/cpqphp.h index 53836001d511..9c6a9fd26812 100644 --- a/drivers/pci/hotplug/cpqphp.h +++ b/drivers/pci/hotplug/cpqphp.h @@ -32,6 +32,7 @@ #include <asm/io.h> /* for read? and write? functions */ #include <linux/delay.h> /* for delays */ #include <linux/mutex.h> +#include <linux/sched.h> /* for signal_pending() */ #define MY_NAME "cpqphp" diff --git a/drivers/pci/intel-iommu.c b/drivers/pci/intel-iommu.c index 855dd7ca47f3..1840a0578a42 100644 --- a/drivers/pci/intel-iommu.c +++ b/drivers/pci/intel-iommu.c @@ -48,6 +48,7 @@ #define IS_GFX_DEVICE(pdev) ((pdev->class >> 16) == PCI_BASE_CLASS_DISPLAY) #define IS_ISA_DEVICE(pdev) ((pdev->class >> 8) == PCI_CLASS_BRIDGE_ISA) +#define IS_AZALIA(pdev) ((pdev)->vendor == 0x8086 && (pdev)->device == 0x3a3e) #define IOAPIC_RANGE_START (0xfee00000) #define IOAPIC_RANGE_END (0xfeefffff) @@ -94,6 +95,7 @@ static inline unsigned long virt_to_dma_pfn(void *p) /* global iommu list, set NULL for ignored DMAR units */ static struct intel_iommu **g_iommus; +static void __init check_tylersburg_isoch(void); static int rwbf_quirk; /* @@ -1934,6 +1936,9 @@ error: } static int iommu_identity_mapping; +#define IDENTMAP_ALL 1 +#define IDENTMAP_GFX 2 +#define IDENTMAP_AZALIA 4 static int iommu_domain_identity_map(struct dmar_domain *domain, unsigned long long start, @@ -2151,8 +2156,14 @@ static int domain_add_dev_info(struct dmar_domain *domain, static int iommu_should_identity_map(struct pci_dev *pdev, int startup) { - if (iommu_identity_mapping == 2) - return IS_GFX_DEVICE(pdev); + if ((iommu_identity_mapping & IDENTMAP_AZALIA) && IS_AZALIA(pdev)) + return 1; + + if ((iommu_identity_mapping & IDENTMAP_GFX) && IS_GFX_DEVICE(pdev)) + return 1; + + if (!(iommu_identity_mapping & IDENTMAP_ALL)) + return 0; /* * We want to start off with all devices in the 1:1 domain, and @@ -2332,11 +2343,14 @@ int __init init_dmars(void) } if (iommu_pass_through) - iommu_identity_mapping = 1; + iommu_identity_mapping |= IDENTMAP_ALL; + #ifdef CONFIG_DMAR_BROKEN_GFX_WA - else - iommu_identity_mapping = 2; + iommu_identity_mapping |= IDENTMAP_GFX; #endif + + check_tylersburg_isoch(); + /* * If pass through is not set or not enabled, setup context entries for * identity mappings for rmrr, gfx, and isa and may fall back to static @@ -2753,7 +2767,15 @@ static void *intel_alloc_coherent(struct device *hwdev, size_t size, size = PAGE_ALIGN(size); order = get_order(size); - flags &= ~(GFP_DMA | GFP_DMA32); + + if (!iommu_no_mapping(hwdev)) + flags &= ~(GFP_DMA | GFP_DMA32); + else if (hwdev->coherent_dma_mask < dma_get_required_mask(hwdev)) { + if (hwdev->coherent_dma_mask < DMA_BIT_MASK(32)) + flags |= GFP_DMA; + else + flags |= GFP_DMA32; + } vaddr = (void *)__get_free_pages(flags, order); if (!vaddr) @@ -3193,6 +3215,33 @@ static int __init init_iommu_sysfs(void) } #endif /* CONFIG_PM */ +/* + * Here we only respond to action of unbound device from driver. + * + * Added device is not attached to its DMAR domain here yet. That will happen + * when mapping the device to iova. + */ +static int device_notifier(struct notifier_block *nb, + unsigned long action, void *data) +{ + struct device *dev = data; + struct pci_dev *pdev = to_pci_dev(dev); + struct dmar_domain *domain; + + domain = find_domain(pdev); + if (!domain) + return 0; + + if (action == BUS_NOTIFY_UNBOUND_DRIVER && !iommu_pass_through) + domain_remove_one_dev_info(domain, pdev); + + return 0; +} + +static struct notifier_block device_nb = { + .notifier_call = device_notifier, +}; + int __init intel_iommu_init(void) { int ret = 0; @@ -3245,6 +3294,8 @@ int __init intel_iommu_init(void) register_iommu(&intel_iommu_ops); + bus_register_notifier(&pci_bus_type, &device_nb); + return 0; } @@ -3670,3 +3721,61 @@ static void __devinit quirk_iommu_rwbf(struct pci_dev *dev) } DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_INTEL, 0x2a40, quirk_iommu_rwbf); + +/* On Tylersburg chipsets, some BIOSes have been known to enable the + ISOCH DMAR unit for the Azalia sound device, but not give it any + TLB entries, which causes it to deadlock. Check for that. We do + this in a function called from init_dmars(), instead of in a PCI + quirk, because we don't want to print the obnoxious "BIOS broken" + message if VT-d is actually disabled. +*/ +static void __init check_tylersburg_isoch(void) +{ + struct pci_dev *pdev; + uint32_t vtisochctrl; + + /* If there's no Azalia in the system anyway, forget it. */ + pdev = pci_get_device(PCI_VENDOR_ID_INTEL, 0x3a3e, NULL); + if (!pdev) + return; + pci_dev_put(pdev); + + /* System Management Registers. Might be hidden, in which case + we can't do the sanity check. But that's OK, because the + known-broken BIOSes _don't_ actually hide it, so far. */ + pdev = pci_get_device(PCI_VENDOR_ID_INTEL, 0x342e, NULL); + if (!pdev) + return; + + if (pci_read_config_dword(pdev, 0x188, &vtisochctrl)) { + pci_dev_put(pdev); + return; + } + + pci_dev_put(pdev); + + /* If Azalia DMA is routed to the non-isoch DMAR unit, fine. */ + if (vtisochctrl & 1) + return; + + /* Drop all bits other than the number of TLB entries */ + vtisochctrl &= 0x1c; + + /* If we have the recommended number of TLB entries (16), fine. */ + if (vtisochctrl == 0x10) + return; + + /* Zero TLB entries? You get to ride the short bus to school. */ + if (!vtisochctrl) { + WARN(1, "Your BIOS is broken; DMA routed to ISOCH DMAR unit but no TLB space.\n" + "BIOS vendor: %s; Ver: %s; Product Version: %s\n", + dmi_get_system_info(DMI_BIOS_VENDOR), + dmi_get_system_info(DMI_BIOS_VERSION), + dmi_get_system_info(DMI_PRODUCT_VERSION)); + iommu_identity_mapping |= IDENTMAP_AZALIA; + return; + } + + printk(KERN_WARNING "DMAR: Recommended TLB entries for ISOCH unit is 16; your BIOS set %d\n", + vtisochctrl); +} diff --git a/drivers/pci/pci.c b/drivers/pci/pci.c index 6edecff0b419..4e4c295a049f 100644 --- a/drivers/pci/pci.c +++ b/drivers/pci/pci.c @@ -513,7 +513,11 @@ static int pci_raw_set_power_state(struct pci_dev *dev, pci_power_t state) else if (state == PCI_D2 || dev->current_state == PCI_D2) udelay(PCI_PM_D2_DELAY); - dev->current_state = state; + pci_read_config_word(dev, dev->pm_cap + PCI_PM_CTRL, &pmcsr); + dev->current_state = (pmcsr & PCI_PM_CTRL_STATE_MASK); + if (dev->current_state != state && printk_ratelimit()) + dev_info(&dev->dev, "Refused to change power state, " + "currently in D%d\n", dev->current_state); /* According to section 5.4.1 of the "PCI BUS POWER MANAGEMENT * INTERFACE SPECIFICATION, REV. 1.2", a device transitioning @@ -2542,10 +2546,10 @@ int pci_resource_bar(struct pci_dev *dev, int resno, enum pci_bar_type *type) /** * pci_set_vga_state - set VGA decode state on device and parents if requested - * @dev the PCI device - * @decode - true = enable decoding, false = disable decoding - * @command_bits PCI_COMMAND_IO and/or PCI_COMMAND_MEMORY - * @change_bridge - traverse ancestors and change bridges + * @dev: the PCI device + * @decode: true = enable decoding, false = disable decoding + * @command_bits: PCI_COMMAND_IO and/or PCI_COMMAND_MEMORY + * @change_bridge: traverse ancestors and change bridges */ int pci_set_vga_state(struct pci_dev *dev, bool decode, unsigned int command_bits, bool change_bridge) @@ -2719,17 +2723,6 @@ int __attribute__ ((weak)) pci_ext_cfg_avail(struct pci_dev *dev) return 1; } -static int __devinit pci_init(void) -{ - struct pci_dev *dev = NULL; - - while ((dev = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, dev)) != NULL) { - pci_fixup_device(pci_fixup_final, dev); - } - - return 0; -} - static int __init pci_setup(char *str) { while (str) { @@ -2767,8 +2760,6 @@ static int __init pci_setup(char *str) } early_param("pci", pci_setup); -device_initcall(pci_init); - EXPORT_SYMBOL(pci_reenable_device); EXPORT_SYMBOL(pci_enable_device_io); EXPORT_SYMBOL(pci_enable_device_mem); diff --git a/drivers/pci/pcie/aer/aerdrv.c b/drivers/pci/pcie/aer/aerdrv.c index 2ce8f9ccc66e..40c3cc5d1caf 100644 --- a/drivers/pci/pcie/aer/aerdrv.c +++ b/drivers/pci/pcie/aer/aerdrv.c @@ -17,6 +17,7 @@ #include <linux/module.h> #include <linux/pci.h> +#include <linux/sched.h> #include <linux/kernel.h> #include <linux/errno.h> #include <linux/pm.h> @@ -52,7 +53,7 @@ static struct pci_error_handlers aer_error_handlers = { static struct pcie_port_service_driver aerdriver = { .name = "aer", - .port_type = PCIE_ANY_PORT, + .port_type = PCIE_RC_PORT, .service = PCIE_PORT_SERVICE_AER, .probe = aer_probe, diff --git a/drivers/pci/pcie/aspm.c b/drivers/pci/pcie/aspm.c index 745402e8e498..5b7056cec00c 100644 --- a/drivers/pci/pcie/aspm.c +++ b/drivers/pci/pcie/aspm.c @@ -656,8 +656,10 @@ void pcie_aspm_exit_link_state(struct pci_dev *pdev) free_link_state(link); /* Recheck latencies and configure upstream links */ - pcie_update_aspm_capable(root); - pcie_config_aspm_path(parent_link); + if (parent_link) { + pcie_update_aspm_capable(root); + pcie_config_aspm_path(parent_link); + } out: mutex_unlock(&aspm_lock); up_read(&pci_bus_sem); diff --git a/drivers/pci/pcie/portdrv_pci.c b/drivers/pci/pcie/portdrv_pci.c index 6df5c984a791..f635e476d632 100644 --- a/drivers/pci/pcie/portdrv_pci.c +++ b/drivers/pci/pcie/portdrv_pci.c @@ -30,7 +30,6 @@ MODULE_DESCRIPTION(DRIVER_DESC); MODULE_LICENSE("GPL"); /* global data */ -static const char device_name[] = "pcieport-driver"; static int pcie_portdrv_restore_config(struct pci_dev *dev) { @@ -262,7 +261,7 @@ static struct pci_error_handlers pcie_portdrv_err_handler = { }; static struct pci_driver pcie_portdriver = { - .name = (char *)device_name, + .name = "pcieport", .id_table = &port_pci_ids[0], .probe = pcie_portdrv_probe, diff --git a/drivers/pci/quirks.c b/drivers/pci/quirks.c index 6099facecd79..245d2cdb4765 100644 --- a/drivers/pci/quirks.c +++ b/drivers/pci/quirks.c @@ -670,6 +670,25 @@ static void __devinit quirk_vt8235_acpi(struct pci_dev *dev) } DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_8235, quirk_vt8235_acpi); +/* + * TI XIO2000a PCIe-PCI Bridge erroneously reports it supports fast back-to-back: + * Disable fast back-to-back on the secondary bus segment + */ +static void __devinit quirk_xio2000a(struct pci_dev *dev) +{ + struct pci_dev *pdev; + u16 command; + + dev_warn(&dev->dev, "TI XIO2000a quirk detected; " + "secondary bus fast back-to-back transfers disabled\n"); + list_for_each_entry(pdev, &dev->subordinate->devices, bus_list) { + pci_read_config_word(pdev, PCI_COMMAND, &command); + if (command & PCI_COMMAND_FAST_BACK) + pci_write_config_word(pdev, PCI_COMMAND, command & ~PCI_COMMAND_FAST_BACK); + } +} +DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_TI, PCI_DEVICE_ID_TI_XIO2000A, + quirk_xio2000a); #ifdef CONFIG_X86_IO_APIC @@ -990,7 +1009,7 @@ DECLARE_PCI_FIXUP_RESUME_EARLY(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82454NX, static void __devinit quirk_amd_ide_mode(struct pci_dev *pdev) { - /* set SBX00 SATA in IDE mode to AHCI mode */ + /* set SBX00/Hudson-2 SATA in IDE mode to AHCI mode */ u8 tmp; pci_read_config_byte(pdev, PCI_CLASS_DEVICE, &tmp); @@ -1009,8 +1028,8 @@ DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP600_SATA, quirk DECLARE_PCI_FIXUP_RESUME_EARLY(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP600_SATA, quirk_amd_ide_mode); DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP700_SATA, quirk_amd_ide_mode); DECLARE_PCI_FIXUP_RESUME_EARLY(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_IXP700_SATA, quirk_amd_ide_mode); -DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_SB900_SATA_IDE, quirk_amd_ide_mode); -DECLARE_PCI_FIXUP_RESUME_EARLY(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_SB900_SATA_IDE, quirk_amd_ide_mode); +DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_HUDSON2_SATA_IDE, quirk_amd_ide_mode); +DECLARE_PCI_FIXUP_RESUME_EARLY(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_HUDSON2_SATA_IDE, quirk_amd_ide_mode); /* * Serverworks CSB5 IDE does not fully support native mode @@ -2572,6 +2591,19 @@ void pci_fixup_device(enum pci_fixup_pass pass, struct pci_dev *dev) } pci_do_fixups(dev, start, end); } + +static int __init pci_apply_final_quirks(void) +{ + struct pci_dev *dev = NULL; + + while ((dev = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, dev)) != NULL) { + pci_fixup_device(pci_fixup_final, dev); + } + + return 0; +} + +fs_initcall_sync(pci_apply_final_quirks); #else void pci_fixup_device(enum pci_fixup_pass pass, struct pci_dev *dev) {} #endif diff --git a/drivers/pci/setup-res.c b/drivers/pci/setup-res.c index 706f82d8111f..c54526b206b5 100644 --- a/drivers/pci/setup-res.c +++ b/drivers/pci/setup-res.c @@ -205,43 +205,6 @@ int pci_assign_resource(struct pci_dev *dev, int resno) return ret; } -#if 0 -int pci_assign_resource_fixed(struct pci_dev *dev, int resno) -{ - struct pci_bus *bus = dev->bus; - struct resource *res = dev->resource + resno; - unsigned int type_mask; - int i, ret = -EBUSY; - - type_mask = IORESOURCE_IO | IORESOURCE_MEM | IORESOURCE_PREFETCH; - - for (i = 0; i < PCI_BUS_NUM_RESOURCES; i++) { - struct resource *r = bus->resource[i]; - if (!r) - continue; - - /* type_mask must match */ - if ((res->flags ^ r->flags) & type_mask) - continue; - - ret = request_resource(r, res); - - if (ret == 0) - break; - } - - if (ret) { - dev_err(&dev->dev, "BAR %d: can't allocate %s resource %pR\n", - resno, res->flags & IORESOURCE_IO ? "I/O" : "mem", res); - } else if (resno < PCI_BRIDGE_RESOURCES) { - pci_update_resource(dev, resno); - } - - return ret; -} -EXPORT_SYMBOL_GPL(pci_assign_resource_fixed); -#endif - /* Sort resources by alignment */ void pdev_sort_resources(struct pci_dev *dev, struct resource_list *head) { diff --git a/drivers/pcmcia/cistpl.c b/drivers/pcmcia/cistpl.c index 4a110b7b2673..6c4a4fc83630 100644 --- a/drivers/pcmcia/cistpl.c +++ b/drivers/pcmcia/cistpl.c @@ -1463,7 +1463,9 @@ int pccard_read_tuple(struct pcmcia_socket *s, unsigned int function, cisdata_t return -ENOMEM; } tuple.DesiredTuple = code; - tuple.Attributes = TUPLE_RETURN_COMMON; + tuple.Attributes = 0; + if (function == BIND_FN_ALL) + tuple.Attributes = TUPLE_RETURN_COMMON; ret = pccard_get_first_tuple(s, function, &tuple); if (ret != 0) goto done; @@ -1490,7 +1492,7 @@ EXPORT_SYMBOL(pccard_read_tuple); ======================================================================*/ -int pccard_validate_cis(struct pcmcia_socket *s, unsigned int function, unsigned int *info) +int pccard_validate_cis(struct pcmcia_socket *s, unsigned int *info) { tuple_t *tuple; cisparse_t *p; @@ -1515,30 +1517,30 @@ int pccard_validate_cis(struct pcmcia_socket *s, unsigned int function, unsigned count = reserved = 0; tuple->DesiredTuple = RETURN_FIRST_TUPLE; tuple->Attributes = TUPLE_RETURN_COMMON; - ret = pccard_get_first_tuple(s, function, tuple); + ret = pccard_get_first_tuple(s, BIND_FN_ALL, tuple); if (ret != 0) goto done; /* First tuple should be DEVICE; we should really have either that or a CFTABLE_ENTRY of some sort */ if ((tuple->TupleCode == CISTPL_DEVICE) || - (pccard_read_tuple(s, function, CISTPL_CFTABLE_ENTRY, p) == 0) || - (pccard_read_tuple(s, function, CISTPL_CFTABLE_ENTRY_CB, p) == 0)) + (pccard_read_tuple(s, BIND_FN_ALL, CISTPL_CFTABLE_ENTRY, p) == 0) || + (pccard_read_tuple(s, BIND_FN_ALL, CISTPL_CFTABLE_ENTRY_CB, p) == 0)) dev_ok++; /* All cards should have a MANFID tuple, and/or a VERS_1 or VERS_2 tuple, for card identification. Certain old D-Link and Linksys cards have only a broken VERS_2 tuple; hence the bogus test. */ - if ((pccard_read_tuple(s, function, CISTPL_MANFID, p) == 0) || - (pccard_read_tuple(s, function, CISTPL_VERS_1, p) == 0) || - (pccard_read_tuple(s, function, CISTPL_VERS_2, p) != -ENOSPC)) + if ((pccard_read_tuple(s, BIND_FN_ALL, CISTPL_MANFID, p) == 0) || + (pccard_read_tuple(s, BIND_FN_ALL, CISTPL_VERS_1, p) == 0) || + (pccard_read_tuple(s, BIND_FN_ALL, CISTPL_VERS_2, p) != -ENOSPC)) ident_ok++; if (!dev_ok && !ident_ok) goto done; for (count = 1; count < MAX_TUPLES; count++) { - ret = pccard_get_next_tuple(s, function, tuple); + ret = pccard_get_next_tuple(s, BIND_FN_ALL, tuple); if (ret != 0) break; if (((tuple->TupleCode > 0x23) && (tuple->TupleCode < 0x40)) || diff --git a/drivers/pcmcia/cs.c b/drivers/pcmcia/cs.c index 934d4bee39a0..698d75cda084 100644 --- a/drivers/pcmcia/cs.c +++ b/drivers/pcmcia/cs.c @@ -98,10 +98,13 @@ EXPORT_SYMBOL(pcmcia_socket_list_rwsem); * These functions check for the appropriate struct pcmcia_soket arrays, * and pass them to the low-level functions pcmcia_{suspend,resume}_socket */ +static int socket_early_resume(struct pcmcia_socket *skt); +static int socket_late_resume(struct pcmcia_socket *skt); static int socket_resume(struct pcmcia_socket *skt); static int socket_suspend(struct pcmcia_socket *skt); -int pcmcia_socket_dev_suspend(struct device *dev) +static void pcmcia_socket_dev_run(struct device *dev, + int (*cb)(struct pcmcia_socket *)) { struct pcmcia_socket *socket; @@ -110,29 +113,34 @@ int pcmcia_socket_dev_suspend(struct device *dev) if (socket->dev.parent != dev) continue; mutex_lock(&socket->skt_mutex); - socket_suspend(socket); + cb(socket); mutex_unlock(&socket->skt_mutex); } up_read(&pcmcia_socket_list_rwsem); +} +int pcmcia_socket_dev_suspend(struct device *dev) +{ + pcmcia_socket_dev_run(dev, socket_suspend); return 0; } EXPORT_SYMBOL(pcmcia_socket_dev_suspend); -int pcmcia_socket_dev_resume(struct device *dev) +void pcmcia_socket_dev_early_resume(struct device *dev) { - struct pcmcia_socket *socket; + pcmcia_socket_dev_run(dev, socket_early_resume); +} +EXPORT_SYMBOL(pcmcia_socket_dev_early_resume); - down_read(&pcmcia_socket_list_rwsem); - list_for_each_entry(socket, &pcmcia_socket_list, socket_list) { - if (socket->dev.parent != dev) - continue; - mutex_lock(&socket->skt_mutex); - socket_resume(socket); - mutex_unlock(&socket->skt_mutex); - } - up_read(&pcmcia_socket_list_rwsem); +void pcmcia_socket_dev_late_resume(struct device *dev) +{ + pcmcia_socket_dev_run(dev, socket_late_resume); +} +EXPORT_SYMBOL(pcmcia_socket_dev_late_resume); +int pcmcia_socket_dev_resume(struct device *dev) +{ + pcmcia_socket_dev_run(dev, socket_resume); return 0; } EXPORT_SYMBOL(pcmcia_socket_dev_resume); @@ -546,29 +554,24 @@ static int socket_suspend(struct pcmcia_socket *skt) return 0; } -/* - * Resume a socket. If a card is present, verify its CIS against - * our cached copy. If they are different, the card has been - * replaced, and we need to tell the drivers. - */ -static int socket_resume(struct pcmcia_socket *skt) +static int socket_early_resume(struct pcmcia_socket *skt) { - int ret; - - if (!(skt->state & SOCKET_SUSPEND)) - return -EBUSY; - skt->socket = dead_socket; skt->ops->init(skt); skt->ops->set_socket(skt, &skt->socket); + if (skt->state & SOCKET_PRESENT) + skt->resume_status = socket_setup(skt, resume_delay); + return 0; +} +static int socket_late_resume(struct pcmcia_socket *skt) +{ if (!(skt->state & SOCKET_PRESENT)) { skt->state &= ~SOCKET_SUSPEND; return socket_insert(skt); } - ret = socket_setup(skt, resume_delay); - if (ret == 0) { + if (skt->resume_status == 0) { /* * FIXME: need a better check here for cardbus cards. */ @@ -596,6 +599,20 @@ static int socket_resume(struct pcmcia_socket *skt) return 0; } +/* + * Resume a socket. If a card is present, verify its CIS against + * our cached copy. If they are different, the card has been + * replaced, and we need to tell the drivers. + */ +static int socket_resume(struct pcmcia_socket *skt) +{ + if (!(skt->state & SOCKET_SUSPEND)) + return -EBUSY; + + socket_early_resume(skt); + return socket_late_resume(skt); +} + static void socket_remove(struct pcmcia_socket *skt) { dev_printk(KERN_NOTICE, &skt->dev, diff --git a/drivers/pcmcia/cs_internal.h b/drivers/pcmcia/cs_internal.h index 79615e6d540b..1f4098f1354d 100644 --- a/drivers/pcmcia/cs_internal.h +++ b/drivers/pcmcia/cs_internal.h @@ -197,8 +197,7 @@ int pccard_read_tuple(struct pcmcia_socket *s, unsigned int function, cisdata_t code, void *parse); int pcmcia_replace_cis(struct pcmcia_socket *s, const u8 *data, const size_t len); -int pccard_validate_cis(struct pcmcia_socket *s, unsigned int function, - unsigned int *count); +int pccard_validate_cis(struct pcmcia_socket *s, unsigned int *count); /* rsrc_mgr.c */ int pcmcia_validate_mem(struct pcmcia_socket *s); diff --git a/drivers/pcmcia/ds.c b/drivers/pcmcia/ds.c index 9f300d3cb125..f5b7079f13d3 100644 --- a/drivers/pcmcia/ds.c +++ b/drivers/pcmcia/ds.c @@ -547,7 +547,7 @@ static int pcmcia_device_query(struct pcmcia_device *p_dev) if (!vers1) return -ENOMEM; - if (!pccard_read_tuple(p_dev->socket, p_dev->func, + if (!pccard_read_tuple(p_dev->socket, BIND_FN_ALL, CISTPL_MANFID, &manf_id)) { p_dev->manf_id = manf_id.manf; p_dev->card_id = manf_id.card; @@ -581,9 +581,9 @@ static int pcmcia_device_query(struct pcmcia_device *p_dev) kfree(devgeo); } - if (!pccard_read_tuple(p_dev->socket, p_dev->func, CISTPL_VERS_1, + if (!pccard_read_tuple(p_dev->socket, BIND_FN_ALL, CISTPL_VERS_1, vers1)) { - for (i=0; i < vers1->ns; i++) { + for (i = 0; i < min_t(unsigned int, 4, vers1->ns); i++) { char *tmp; unsigned int length; @@ -733,7 +733,7 @@ static int pcmcia_card_add(struct pcmcia_socket *s) return -EAGAIN; /* try again, but later... */ } - ret = pccard_validate_cis(s, BIND_FN_ALL, &no_chains); + ret = pccard_validate_cis(s, &no_chains); if (ret || !no_chains) { ds_dev_dbg(0, &s->dev, "invalid CIS or invalid resources\n"); return -ENODEV; diff --git a/drivers/pcmcia/i82365.c b/drivers/pcmcia/i82365.c index b906abe26ad0..a4aacb830b80 100644 --- a/drivers/pcmcia/i82365.c +++ b/drivers/pcmcia/i82365.c @@ -1053,8 +1053,8 @@ static int i365_set_io_map(u_short sock, struct pccard_io_map *io) u_char map, ioctl; debug(1, "SetIOMap(%d, %d, %#2.2x, %d ns, " - "%#x-%#x)\n", sock, io->map, io->flags, - io->speed, io->start, io->stop); + "%#llx-%#llx)\n", sock, io->map, io->flags, io->speed, + (unsigned long long)io->start, (unsigned long long)io->stop); map = io->map; if ((map > 1) || (io->start > 0xffff) || (io->stop > 0xffff) || (io->stop < io->start)) return -EINVAL; diff --git a/drivers/pcmcia/m32r_cfc.c b/drivers/pcmcia/m32r_cfc.c index d1d89c4491ad..7dfbee1dcd76 100644 --- a/drivers/pcmcia/m32r_cfc.c +++ b/drivers/pcmcia/m32r_cfc.c @@ -537,8 +537,9 @@ static int _pcc_set_io_map(u_short sock, struct pccard_io_map *io) u_char map; debug(3, "m32r_cfc: SetIOMap(%d, %d, %#2.2x, %d ns, " - "%#lx-%#lx)\n", sock, io->map, io->flags, - io->speed, io->start, io->stop); + "%#llx-%#llx)\n", sock, io->map, io->flags, + io->speed, (unsigned long long)io->start, + (unsigned long long)io->stop); map = io->map; return 0; @@ -554,8 +555,9 @@ static int _pcc_set_mem_map(u_short sock, struct pccard_mem_map *mem) pcc_socket_t *t = &socket[sock]; debug(3, "m32r_cfc: SetMemMap(%d, %d, %#2.2x, %d ns, " - "%#lx, %#x)\n", sock, map, mem->flags, - mem->speed, mem->static_start, mem->card_start); + "%#llx, %#x)\n", sock, map, mem->flags, + mem->speed, (unsigned long long)mem->static_start, + mem->card_start); /* * sanity check diff --git a/drivers/pcmcia/m32r_pcc.c b/drivers/pcmcia/m32r_pcc.c index a0655839c8d3..c6524f99ccc3 100644 --- a/drivers/pcmcia/m32r_pcc.c +++ b/drivers/pcmcia/m32r_pcc.c @@ -492,8 +492,9 @@ static int _pcc_set_io_map(u_short sock, struct pccard_io_map *io) u_char map; debug(3, "m32r-pcc: SetIOMap(%d, %d, %#2.2x, %d ns, " - "%#x-%#x)\n", sock, io->map, io->flags, - io->speed, io->start, io->stop); + "%#llx-%#llx)\n", sock, io->map, io->flags, + io->speed, (unsigned long long)io->start, + (unsigned long long)io->stop); map = io->map; return 0; @@ -515,8 +516,9 @@ static int _pcc_set_mem_map(u_short sock, struct pccard_mem_map *mem) #endif debug(3, "m32r-pcc: SetMemMap(%d, %d, %#2.2x, %d ns, " - "%#lx, %#x)\n", sock, map, mem->flags, - mem->speed, mem->static_start, mem->card_start); + "%#llx, %#x)\n", sock, map, mem->flags, + mem->speed, (unsigned long long)mem->static_start, + mem->card_start); /* * sanity check diff --git a/drivers/pcmcia/m8xx_pcmcia.c b/drivers/pcmcia/m8xx_pcmcia.c index c69f2c4fe520..403559ba49dd 100644 --- a/drivers/pcmcia/m8xx_pcmcia.c +++ b/drivers/pcmcia/m8xx_pcmcia.c @@ -975,8 +975,9 @@ static int m8xx_set_io_map(struct pcmcia_socket *sock, struct pccard_io_map *io) #define M8XX_BASE (PCMCIA_IO_WIN_BASE + io->start) dprintk("SetIOMap(%d, %d, %#2.2x, %d ns, " - "%#4.4x-%#4.4x)\n", lsock, io->map, io->flags, - io->speed, io->start, io->stop); + "%#4.4llx-%#4.4llx)\n", lsock, io->map, io->flags, + io->speed, (unsigned long long)io->start, + (unsigned long long)io->stop); if ((io->map >= PCMCIA_IO_WIN_NO) || (io->start > 0xffff) || (io->stop > 0xffff) || (io->stop < io->start)) @@ -1055,8 +1056,9 @@ static int m8xx_set_mem_map(struct pcmcia_socket *sock, pcmconf8xx_t *pcmcia = s->pcmcia; dprintk("SetMemMap(%d, %d, %#2.2x, %d ns, " - "%#5.5lx, %#5.5x)\n", lsock, mem->map, mem->flags, - mem->speed, mem->static_start, mem->card_start); + "%#5.5llx, %#5.5x)\n", lsock, mem->map, mem->flags, + mem->speed, (unsigned long long)mem->static_start, + mem->card_start); if ((mem->map >= PCMCIA_MEM_WIN_NO) // || ((mem->s) >= PCMCIA_MEM_WIN_SIZE) @@ -1107,8 +1109,9 @@ static int m8xx_set_mem_map(struct pcmcia_socket *sock, } dprintk("SetMemMap(%d, %d, %#2.2x, %d ns, " - "%#5.5lx, %#5.5x)\n", lsock, mem->map, mem->flags, - mem->speed, mem->static_start, mem->card_start); + "%#5.5llx, %#5.5x)\n", lsock, mem->map, mem->flags, + mem->speed, (unsigned long long)mem->static_start, + mem->card_start); /* copy the struct and modify the copy */ diff --git a/drivers/pcmcia/pcmcia_ioctl.c b/drivers/pcmcia/pcmcia_ioctl.c index 32c44040c1e8..30cf71d2ee23 100644 --- a/drivers/pcmcia/pcmcia_ioctl.c +++ b/drivers/pcmcia/pcmcia_ioctl.c @@ -881,7 +881,7 @@ static int ds_ioctl(struct inode * inode, struct file * file, mutex_lock(&s->skt_mutex); pcmcia_validate_mem(s); mutex_unlock(&s->skt_mutex); - ret = pccard_validate_cis(s, BIND_FN_ALL, &buf->cisinfo.Chains); + ret = pccard_validate_cis(s, &buf->cisinfo.Chains); break; case DS_SUSPEND_CARD: ret = pcmcia_suspend_card(s); diff --git a/drivers/pcmcia/pd6729.c b/drivers/pcmcia/pd6729.c index 1c39d3438f20..70a33468bcd0 100644 --- a/drivers/pcmcia/pd6729.c +++ b/drivers/pcmcia/pd6729.c @@ -641,6 +641,12 @@ static int __devinit pd6729_pci_probe(struct pci_dev *dev, if ((ret = pci_enable_device(dev))) goto err_out_free_mem; + if (!pci_resource_start(dev, 0)) { + printk(KERN_INFO "pd6729: refusing to load the driver " + "as the io_base is 0.\n"); + goto err_out_free_mem; + } + printk(KERN_INFO "pd6729: Cirrus PD6729 PCI to PCMCIA Bridge " "at 0x%llx on irq %d\n", (unsigned long long)pci_resource_start(dev, 0), dev->irq); diff --git a/drivers/pcmcia/rsrc_nonstatic.c b/drivers/pcmcia/rsrc_nonstatic.c index 9ca22c7aafb2..7039f3cf5b77 100644 --- a/drivers/pcmcia/rsrc_nonstatic.c +++ b/drivers/pcmcia/rsrc_nonstatic.c @@ -206,6 +206,7 @@ static void do_io_probe(struct pcmcia_socket *s, unsigned int base, /* First, what does a floating port look like? */ b = kzalloc(256, GFP_KERNEL); if (!b) { + printk("\n"); dev_printk(KERN_ERR, &s->dev, "do_io_probe: unable to kmalloc 256 bytes"); return; @@ -275,7 +276,7 @@ static int readable(struct pcmcia_socket *s, struct resource *res, s->cis_mem.res = res; s->cis_virt = ioremap(res->start, s->map_size); if (s->cis_virt) { - ret = pccard_validate_cis(s, BIND_FN_ALL, count); + ret = pccard_validate_cis(s, count); /* invalidate mapping and CIS cache */ iounmap(s->cis_virt); s->cis_virt = NULL; diff --git a/drivers/pcmcia/soc_common.c b/drivers/pcmcia/soc_common.c index 163cf98e2386..ef7e9e58782b 100644 --- a/drivers/pcmcia/soc_common.c +++ b/drivers/pcmcia/soc_common.c @@ -336,8 +336,9 @@ soc_common_pcmcia_set_io_map(struct pcmcia_socket *sock, struct pccard_io_map *m struct soc_pcmcia_socket *skt = to_soc_pcmcia_socket(sock); unsigned short speed = map->speed; - debug(skt, 2, "map %u speed %u start 0x%08x stop 0x%08x\n", - map->map, map->speed, map->start, map->stop); + debug(skt, 2, "map %u speed %u start 0x%08llx stop 0x%08llx\n", + map->map, map->speed, (unsigned long long)map->start, + (unsigned long long)map->stop); debug(skt, 2, "flags: %s%s%s%s%s%s%s%s\n", (map->flags==0)?"<NONE>":"", (map->flags&MAP_ACTIVE)?"ACTIVE ":"", diff --git a/drivers/pcmcia/socket_sysfs.c b/drivers/pcmcia/socket_sysfs.c index ff9a3bb3c88d..78d5aab542f7 100644 --- a/drivers/pcmcia/socket_sysfs.c +++ b/drivers/pcmcia/socket_sysfs.c @@ -300,7 +300,7 @@ static ssize_t pccard_show_cis(struct kobject *kobj, if (!(s->state & SOCKET_PRESENT)) return -ENODEV; - if (pccard_validate_cis(s, BIND_FN_ALL, &chains)) + if (pccard_validate_cis(s, &chains)) return -EIO; if (!chains) return -ENODATA; diff --git a/drivers/pcmcia/tcic.c b/drivers/pcmcia/tcic.c index 582413fcb62f..6918849d511e 100644 --- a/drivers/pcmcia/tcic.c +++ b/drivers/pcmcia/tcic.c @@ -732,8 +732,8 @@ static int tcic_set_io_map(struct pcmcia_socket *sock, struct pccard_io_map *io) u_short base, len, ioctl; debug(1, "SetIOMap(%d, %d, %#2.2x, %d ns, " - "%#x-%#x)\n", psock, io->map, io->flags, - io->speed, io->start, io->stop); + "%#llx-%#llx)\n", psock, io->map, io->flags, io->speed, + (unsigned long long)io->start, (unsigned long long)io->stop); if ((io->map > 1) || (io->start > 0xffff) || (io->stop > 0xffff) || (io->stop < io->start)) return -EINVAL; tcic_setw(TCIC_ADDR+2, TCIC_ADR2_INDREG | (psock << TCIC_SS_SHFT)); diff --git a/drivers/pcmcia/yenta_socket.c b/drivers/pcmcia/yenta_socket.c index abe0e44c6e9e..8be4cc447a17 100644 --- a/drivers/pcmcia/yenta_socket.c +++ b/drivers/pcmcia/yenta_socket.c @@ -1275,16 +1275,26 @@ static int yenta_dev_resume_noirq(struct device *dev) if (socket->type && socket->type->restore_state) socket->type->restore_state(socket); - return pcmcia_socket_dev_resume(dev); + pcmcia_socket_dev_early_resume(dev); + return 0; +} + +static int yenta_dev_resume(struct device *dev) +{ + pcmcia_socket_dev_late_resume(dev); + return 0; } static struct dev_pm_ops yenta_pm_ops = { .suspend_noirq = yenta_dev_suspend_noirq, .resume_noirq = yenta_dev_resume_noirq, + .resume = yenta_dev_resume, .freeze_noirq = yenta_dev_suspend_noirq, .thaw_noirq = yenta_dev_resume_noirq, + .thaw = yenta_dev_resume, .poweroff_noirq = yenta_dev_suspend_noirq, .restore_noirq = yenta_dev_resume_noirq, + .restore = yenta_dev_resume, }; #define YENTA_PM_OPS (¥ta_pm_ops) diff --git a/drivers/platform/x86/eeepc-laptop.c b/drivers/platform/x86/eeepc-laptop.c index 749e2102b2be..4226e5352738 100644 --- a/drivers/platform/x86/eeepc-laptop.c +++ b/drivers/platform/x86/eeepc-laptop.c @@ -350,13 +350,14 @@ static const struct rfkill_ops eeepc_rfkill_ops = { .set_block = eeepc_rfkill_set, }; -static void __init eeepc_enable_camera(void) +static void __devinit eeepc_enable_camera(void) { /* * If the following call to set_acpi() fails, it's because there's no * camera so we can ignore the error. */ - set_acpi(CM_ASL_CAMERA, 1); + if (get_acpi(CM_ASL_CAMERA) == 0) + set_acpi(CM_ASL_CAMERA, 1); } /* @@ -1189,7 +1190,7 @@ static int eeepc_input_init(struct device *dev) return 0; } -static int eeepc_hotk_add(struct acpi_device *device) +static int __devinit eeepc_hotk_add(struct acpi_device *device) { struct device *dev; int result; diff --git a/drivers/platform/x86/fujitsu-laptop.c b/drivers/platform/x86/fujitsu-laptop.c index f35aee5c2149..bcd4ba8be7db 100644 --- a/drivers/platform/x86/fujitsu-laptop.c +++ b/drivers/platform/x86/fujitsu-laptop.c @@ -944,7 +944,7 @@ static int acpi_fujitsu_hotkey_remove(struct acpi_device *device, int type) struct fujitsu_hotkey_t *fujitsu_hotkey = acpi_driver_data(device); struct input_dev *input = fujitsu_hotkey->input; -#ifdef CONFIG_LEDS_CLASS +#if defined(CONFIG_LEDS_CLASS) || defined(CONFIG_LEDS_CLASS_MODULE) if (fujitsu_hotkey->logolamp_registered) led_classdev_unregister(&logolamp_led); diff --git a/drivers/pps/kapi.c b/drivers/pps/kapi.c index 35a0b192d768..2d414e23d390 100644 --- a/drivers/pps/kapi.c +++ b/drivers/pps/kapi.c @@ -271,6 +271,7 @@ void pps_event(int source, struct pps_ktime *ts, int event, void *data) { struct pps_device *pps; unsigned long flags; + int captured = 0; if ((event & (PPS_CAPTUREASSERT | PPS_CAPTURECLEAR)) == 0) { printk(KERN_ERR "pps: unknown event (%x) for source %d\n", @@ -293,7 +294,8 @@ void pps_event(int source, struct pps_ktime *ts, int event, void *data) /* Check the event */ pps->current_mode = pps->params.mode; - if (event & PPS_CAPTUREASSERT) { + if ((event & PPS_CAPTUREASSERT) & + (pps->params.mode & PPS_CAPTUREASSERT)) { /* We have to add an offset? */ if (pps->params.mode & PPS_OFFSETASSERT) pps_add_offset(ts, &pps->params.assert_off_tu); @@ -303,8 +305,11 @@ void pps_event(int source, struct pps_ktime *ts, int event, void *data) pps->assert_sequence++; pr_debug("capture assert seq #%u for source %d\n", pps->assert_sequence, source); + + captured = ~0; } - if (event & PPS_CAPTURECLEAR) { + if ((event & PPS_CAPTURECLEAR) & + (pps->params.mode & PPS_CAPTURECLEAR)) { /* We have to add an offset? */ if (pps->params.mode & PPS_OFFSETCLEAR) pps_add_offset(ts, &pps->params.clear_off_tu); @@ -314,12 +319,17 @@ void pps_event(int source, struct pps_ktime *ts, int event, void *data) pps->clear_sequence++; pr_debug("capture clear seq #%u for source %d\n", pps->clear_sequence, source); + + captured = ~0; } - pps->go = ~0; - wake_up_interruptible(&pps->queue); + /* Wake up iif captured somthing */ + if (captured) { + pps->go = ~0; + wake_up_interruptible(&pps->queue); - kill_fasync(&pps->async_queue, SIGIO, POLL_IN); + kill_fasync(&pps->async_queue, SIGIO, POLL_IN); + } spin_unlock_irqrestore(&pps->lock, flags); diff --git a/drivers/pps/pps.c b/drivers/pps/pps.c index fea17e7805e9..ca5183bdad85 100644 --- a/drivers/pps/pps.c +++ b/drivers/pps/pps.c @@ -71,9 +71,14 @@ static long pps_cdev_ioctl(struct file *file, case PPS_GETPARAMS: pr_debug("PPS_GETPARAMS: source %d\n", pps->id); - /* Return current parameters */ - err = copy_to_user(uarg, &pps->params, - sizeof(struct pps_kparams)); + spin_lock_irq(&pps->lock); + + /* Get the current parameters */ + params = pps->params; + + spin_unlock_irq(&pps->lock); + + err = copy_to_user(uarg, ¶ms, sizeof(struct pps_kparams)); if (err) return -EFAULT; diff --git a/drivers/regulator/core.c b/drivers/regulator/core.c index 744ea1d0b59b..efe568deda12 100644 --- a/drivers/regulator/core.c +++ b/drivers/regulator/core.c @@ -1283,7 +1283,8 @@ static int _regulator_disable(struct regulator_dev *rdev) return -EIO; /* are we the last user and permitted to disable ? */ - if (rdev->use_count == 1 && !rdev->constraints->always_on) { + if (rdev->use_count == 1 && + (rdev->constraints && !rdev->constraints->always_on)) { /* we are last user */ if (_regulator_can_change_status(rdev) && diff --git a/drivers/regulator/fixed.c b/drivers/regulator/fixed.c index f8b295700d7d..f9f516a3028a 100644 --- a/drivers/regulator/fixed.c +++ b/drivers/regulator/fixed.c @@ -196,11 +196,10 @@ static int regulator_fixed_voltage_remove(struct platform_device *pdev) struct fixed_voltage_data *drvdata = platform_get_drvdata(pdev); regulator_unregister(drvdata->dev); - kfree(drvdata->desc.name); - kfree(drvdata); - if (gpio_is_valid(drvdata->gpio)) gpio_free(drvdata->gpio); + kfree(drvdata->desc.name); + kfree(drvdata); return 0; } diff --git a/drivers/regulator/wm831x-ldo.c b/drivers/regulator/wm831x-ldo.c index bb61aede4801..902db56ce099 100644 --- a/drivers/regulator/wm831x-ldo.c +++ b/drivers/regulator/wm831x-ldo.c @@ -175,18 +175,18 @@ static unsigned int wm831x_gp_ldo_get_mode(struct regulator_dev *rdev) struct wm831x *wm831x = ldo->wm831x; int ctrl_reg = ldo->base + WM831X_LDO_CONTROL; int on_reg = ldo->base + WM831X_LDO_ON_CONTROL; - unsigned int ret; + int ret; ret = wm831x_reg_read(wm831x, on_reg); if (ret < 0) - return 0; + return ret; if (!(ret & WM831X_LDO1_ON_MODE)) return REGULATOR_MODE_NORMAL; ret = wm831x_reg_read(wm831x, ctrl_reg); if (ret < 0) - return 0; + return ret; if (ret & WM831X_LDO1_LP_MODE) return REGULATOR_MODE_STANDBY; diff --git a/drivers/rtc/interface.c b/drivers/rtc/interface.c index 4cdb31a362ca..a0c816238aa9 100644 --- a/drivers/rtc/interface.c +++ b/drivers/rtc/interface.c @@ -12,6 +12,7 @@ */ #include <linux/rtc.h> +#include <linux/sched.h> #include <linux/log2.h> int rtc_read_time(struct rtc_device *rtc, struct rtc_time *tm) diff --git a/drivers/rtc/rtc-coh901331.c b/drivers/rtc/rtc-coh901331.c index 7fe1fa26c52c..03ea530981d1 100644 --- a/drivers/rtc/rtc-coh901331.c +++ b/drivers/rtc/rtc-coh901331.c @@ -58,7 +58,16 @@ static irqreturn_t coh901331_interrupt(int irq, void *data) clk_enable(rtap->clk); /* Ack IRQ */ writel(1, rtap->virtbase + COH901331_IRQ_EVENT); + /* + * Disable the interrupt. This is necessary because + * the RTC lives on a lower-clocked line and will + * not release the IRQ line until after a few (slower) + * clock cycles. The interrupt will be re-enabled when + * a new alarm is set anyway. + */ + writel(0, rtap->virtbase + COH901331_IRQ_MASK); clk_disable(rtap->clk); + /* Set alarm flag */ rtc_update_irq(rtap->rtc, 1, RTC_AF); @@ -128,6 +137,8 @@ static int coh901331_alarm_irq_enable(struct device *dev, unsigned int enabled) else writel(0, rtap->virtbase + COH901331_IRQ_MASK); clk_disable(rtap->clk); + + return 0; } static struct rtc_class_ops coh901331_ops = { diff --git a/drivers/rtc/rtc-dev.c b/drivers/rtc/rtc-dev.c index 8a11de9552cd..62227cd52410 100644 --- a/drivers/rtc/rtc-dev.c +++ b/drivers/rtc/rtc-dev.c @@ -13,6 +13,7 @@ #include <linux/module.h> #include <linux/rtc.h> +#include <linux/sched.h> #include "rtc-core.h" static dev_t rtc_devt; diff --git a/drivers/rtc/rtc-pcf50633.c b/drivers/rtc/rtc-pcf50633.c index f4dd87e29075..33a10c47260e 100644 --- a/drivers/rtc/rtc-pcf50633.c +++ b/drivers/rtc/rtc-pcf50633.c @@ -70,7 +70,7 @@ static void pcf2rtc_time(struct rtc_time *rtc, struct pcf50633_time *pcf) rtc->tm_hour = bcd2bin(pcf->time[PCF50633_TI_HOUR]); rtc->tm_wday = bcd2bin(pcf->time[PCF50633_TI_WKDAY]); rtc->tm_mday = bcd2bin(pcf->time[PCF50633_TI_DAY]); - rtc->tm_mon = bcd2bin(pcf->time[PCF50633_TI_MONTH]); + rtc->tm_mon = bcd2bin(pcf->time[PCF50633_TI_MONTH]) - 1; rtc->tm_year = bcd2bin(pcf->time[PCF50633_TI_YEAR]) + 100; } @@ -81,7 +81,7 @@ static void rtc2pcf_time(struct pcf50633_time *pcf, struct rtc_time *rtc) pcf->time[PCF50633_TI_HOUR] = bin2bcd(rtc->tm_hour); pcf->time[PCF50633_TI_WKDAY] = bin2bcd(rtc->tm_wday); pcf->time[PCF50633_TI_DAY] = bin2bcd(rtc->tm_mday); - pcf->time[PCF50633_TI_MONTH] = bin2bcd(rtc->tm_mon); + pcf->time[PCF50633_TI_MONTH] = bin2bcd(rtc->tm_mon + 1); pcf->time[PCF50633_TI_YEAR] = bin2bcd(rtc->tm_year % 100); } @@ -245,8 +245,9 @@ static int pcf50633_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *alrm) ret = pcf50633_write_block(rtc->pcf, PCF50633_REG_RTCSCA, PCF50633_TI_EXTENT, &pcf_tm.time[0]); - if (!alarm_masked) + if (!alarm_masked || alrm->enabled) pcf50633_irq_unmask(rtc->pcf, PCF50633_IRQ_ALARM); + rtc->alarm_enabled = alrm->enabled; return ret; } diff --git a/drivers/rtc/rtc-v3020.c b/drivers/rtc/rtc-v3020.c index ad164056feb6..423cd5a30b10 100644 --- a/drivers/rtc/rtc-v3020.c +++ b/drivers/rtc/rtc-v3020.c @@ -96,7 +96,7 @@ static void v3020_mmio_write_bit(struct v3020 *chip, unsigned char bit) static unsigned char v3020_mmio_read_bit(struct v3020 *chip) { - return readl(chip->ioaddress) & (1 << chip->leftshift); + return !!(readl(chip->ioaddress) & (1 << chip->leftshift)); } static struct v3020_chip_ops v3020_mmio_ops = { diff --git a/drivers/rtc/rtc-vr41xx.c b/drivers/rtc/rtc-vr41xx.c index 2c839d0d21bd..fadddac1e5a4 100644 --- a/drivers/rtc/rtc-vr41xx.c +++ b/drivers/rtc/rtc-vr41xx.c @@ -209,19 +209,18 @@ static int vr41xx_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *wkalrm) static int vr41xx_rtc_irq_set_freq(struct device *dev, int freq) { - unsigned long count; + u64 count; if (!is_power_of_2(freq)) return -EINVAL; count = RTC_FREQUENCY; do_div(count, freq); - periodic_count = count; - spin_lock_irq(&rtc_lock); - rtc1_write(RTCL1LREG, count); - rtc1_write(RTCL1HREG, count >> 16); + periodic_count = count; + rtc1_write(RTCL1LREG, periodic_count); + rtc1_write(RTCL1HREG, periodic_count >> 16); spin_unlock_irq(&rtc_lock); diff --git a/drivers/s390/block/dasd.c b/drivers/s390/block/dasd.c index dad0449475b6..aaccc8ecfa8f 100644 --- a/drivers/s390/block/dasd.c +++ b/drivers/s390/block/dasd.c @@ -2508,8 +2508,6 @@ int dasd_generic_restore_device(struct ccw_device *cdev) device->stopped &= ~DASD_UNRESUMED_PM; dasd_schedule_device_bh(device); - if (device->block) - dasd_schedule_block_bh(device->block); if (device->discipline->restore) rc = device->discipline->restore(device); @@ -2520,6 +2518,9 @@ int dasd_generic_restore_device(struct ccw_device *cdev) */ device->stopped |= DASD_UNRESUMED_PM; + if (device->block) + dasd_schedule_block_bh(device->block); + dasd_put_device(device); return 0; } @@ -2532,6 +2533,7 @@ static struct dasd_ccw_req *dasd_generic_build_rdc(struct dasd_device *device, { struct dasd_ccw_req *cqr; struct ccw1 *ccw; + unsigned long *idaw; cqr = dasd_smalloc_request(magic, 1 /* RDC */, rdc_buffer_size, device); @@ -2545,9 +2547,17 @@ static struct dasd_ccw_req *dasd_generic_build_rdc(struct dasd_device *device, ccw = cqr->cpaddr; ccw->cmd_code = CCW_CMD_RDC; - ccw->cda = (__u32)(addr_t)rdc_buffer; - ccw->count = rdc_buffer_size; + if (idal_is_needed(rdc_buffer, rdc_buffer_size)) { + idaw = (unsigned long *) (cqr->data); + ccw->cda = (__u32)(addr_t) idaw; + ccw->flags = CCW_FLAG_IDA; + idaw = idal_create_words(idaw, rdc_buffer, rdc_buffer_size); + } else { + ccw->cda = (__u32)(addr_t) rdc_buffer; + ccw->flags = 0; + } + ccw->count = rdc_buffer_size; cqr->startdev = device; cqr->memdev = device; cqr->expires = 10*HZ; diff --git a/drivers/s390/block/dasd_eckd.c b/drivers/s390/block/dasd_eckd.c index ab3521755588..417b97cd3f94 100644 --- a/drivers/s390/block/dasd_eckd.c +++ b/drivers/s390/block/dasd_eckd.c @@ -2338,6 +2338,8 @@ static struct dasd_ccw_req *dasd_eckd_build_cp(struct dasd_device *startdev, /* Calculate number of blocks/records per track. */ blksize = block->bp_block; blk_per_trk = recs_per_track(&private->rdc_data, 0, blksize); + if (blk_per_trk == 0) + return ERR_PTR(-EINVAL); /* Calculate record id of first and last block. */ first_rec = first_trk = blk_rq_pos(req) >> block->s2b_shift; first_offs = sector_div(first_trk, blk_per_trk); @@ -3211,8 +3213,10 @@ int dasd_eckd_pm_freeze(struct dasd_device *device) int dasd_eckd_restore_device(struct dasd_device *device) { struct dasd_eckd_private *private; + struct dasd_eckd_characteristics temp_rdc_data; int is_known, rc; struct dasd_uid temp_uid; + unsigned long flags; private = (struct dasd_eckd_private *) device->private; @@ -3225,7 +3229,8 @@ int dasd_eckd_restore_device(struct dasd_device *device) rc = dasd_eckd_generate_uid(device, &private->uid); dasd_get_uid(device->cdev, &temp_uid); if (memcmp(&private->uid, &temp_uid, sizeof(struct dasd_uid)) != 0) - dev_err(&device->cdev->dev, "The UID of the DASD has changed\n"); + dev_err(&device->cdev->dev, "The UID of the DASD has " + "changed\n"); if (rc) goto out_err; dasd_set_uid(device->cdev, &private->uid); @@ -3245,15 +3250,17 @@ int dasd_eckd_restore_device(struct dasd_device *device) dasd_eckd_read_features(device); /* Read Device Characteristics */ - memset(&private->rdc_data, 0, sizeof(private->rdc_data)); rc = dasd_generic_read_dev_chars(device, DASD_ECKD_MAGIC, - &private->rdc_data, 64); + &temp_rdc_data, 64); if (rc) { DBF_EVENT(DBF_WARNING, "Read device characteristics failed, rc=%d for " "device: %s", rc, dev_name(&device->cdev->dev)); goto out_err; } + spin_lock_irqsave(get_ccwdev_lock(device->cdev), flags); + memcpy(&private->rdc_data, &temp_rdc_data, sizeof(temp_rdc_data)); + spin_unlock_irqrestore(get_ccwdev_lock(device->cdev), flags); /* add device to alias management */ dasd_alias_add_device(device); diff --git a/drivers/s390/char/monreader.c b/drivers/s390/char/monreader.c index 89ece1c235aa..66e21dd23154 100644 --- a/drivers/s390/char/monreader.c +++ b/drivers/s390/char/monreader.c @@ -357,6 +357,7 @@ static int mon_close(struct inode *inode, struct file *filp) atomic_set(&monpriv->msglim_count, 0); monpriv->write_index = 0; monpriv->read_index = 0; + dev_set_drvdata(monreader_device, NULL); for (i = 0; i < MON_MSGLIM; i++) kfree(monpriv->msg_array[i]); diff --git a/drivers/s390/char/raw3270.c b/drivers/s390/char/raw3270.c index d6a022f55e92..62ddf5202b79 100644 --- a/drivers/s390/char/raw3270.c +++ b/drivers/s390/char/raw3270.c @@ -1361,11 +1361,13 @@ static int raw3270_pm_start(struct ccw_device *cdev) void raw3270_pm_unfreeze(struct raw3270_view *view) { +#ifdef CONFIG_TN3270_CONSOLE struct raw3270 *rp; rp = view->dev; if (rp && test_bit(RAW3270_FLAGS_FROZEN, &rp->flags)) ccw_device_force_console(); +#endif } static struct ccw_device_id raw3270_id[] = { diff --git a/drivers/s390/char/sclp_async.c b/drivers/s390/char/sclp_async.c index daaec185ed36..b44462a6c6d3 100644 --- a/drivers/s390/char/sclp_async.c +++ b/drivers/s390/char/sclp_async.c @@ -26,7 +26,6 @@ static struct sclp_async_sccb *sccb; static int sclp_async_send_wait(char *message); static struct ctl_table_header *callhome_sysctl_header; static DEFINE_SPINLOCK(sclp_async_lock); -static char nodename[64]; #define SCLP_NORMAL_WRITE 0x00 struct async_evbuf { @@ -52,9 +51,10 @@ static struct sclp_register sclp_async_register = { static int call_home_on_panic(struct notifier_block *self, unsigned long event, void *data) { - strncat(data, nodename, strlen(nodename)); - sclp_async_send_wait(data); - return NOTIFY_DONE; + strncat(data, init_utsname()->nodename, + sizeof(init_utsname()->nodename)); + sclp_async_send_wait(data); + return NOTIFY_DONE; } static struct notifier_block call_home_panic_nb = { @@ -62,21 +62,20 @@ static struct notifier_block call_home_panic_nb = { .priority = INT_MAX, }; -static int proc_handler_callhome(ctl_table *ctl, int write, struct file *filp, +static int proc_handler_callhome(struct ctl_table *ctl, int write, void __user *buffer, size_t *count, loff_t *ppos) { unsigned long val; int len, rc; - char buf[2]; + char buf[3]; - if (!*count | (*ppos && !write)) { + if (!*count || (*ppos && !write)) { *count = 0; return 0; } if (!write) { - len = sprintf(buf, "%d\n", callhome_enabled); - buf[len] = '\0'; + len = snprintf(buf, sizeof(buf), "%d\n", callhome_enabled); rc = copy_to_user(buffer, buf, sizeof(buf)); if (rc != 0) return -EFAULT; @@ -100,7 +99,7 @@ static struct ctl_table callhome_table[] = { { .procname = "callhome", .mode = 0644, - .proc_handler = &proc_handler_callhome, + .proc_handler = proc_handler_callhome, }, { .ctl_name = 0 } }; @@ -171,39 +170,29 @@ static int __init sclp_async_init(void) rc = sclp_register(&sclp_async_register); if (rc) return rc; - callhome_sysctl_header = register_sysctl_table(kern_dir_table); - if (!callhome_sysctl_header) { - rc = -ENOMEM; - goto out_sclp; - } - if (!(sclp_async_register.sclp_receive_mask & EVTYP_ASYNC_MASK)) { - rc = -EOPNOTSUPP; + rc = -EOPNOTSUPP; + if (!(sclp_async_register.sclp_receive_mask & EVTYP_ASYNC_MASK)) goto out_sclp; - } rc = -ENOMEM; + callhome_sysctl_header = register_sysctl_table(kern_dir_table); + if (!callhome_sysctl_header) + goto out_sclp; request = kzalloc(sizeof(struct sclp_req), GFP_KERNEL); - if (!request) - goto out_sys; sccb = (struct sclp_async_sccb *) get_zeroed_page(GFP_KERNEL | GFP_DMA); - if (!sccb) + if (!request || !sccb) goto out_mem; - rc = atomic_notifier_chain_register(&panic_notifier_list, - &call_home_panic_nb); - if (rc) - goto out_mem; - - strncpy(nodename, init_utsname()->nodename, 64); - return 0; - + rc = atomic_notifier_chain_register(&panic_notifier_list, + &call_home_panic_nb); + if (!rc) + goto out; out_mem: kfree(request); free_page((unsigned long) sccb); -out_sys: unregister_sysctl_table(callhome_sysctl_header); out_sclp: sclp_unregister(&sclp_async_register); +out: return rc; - } module_init(sclp_async_init); diff --git a/drivers/s390/char/sclp_quiesce.c b/drivers/s390/char/sclp_quiesce.c index 84c191c1cd62..05909a7df8b3 100644 --- a/drivers/s390/char/sclp_quiesce.c +++ b/drivers/s390/char/sclp_quiesce.c @@ -20,9 +20,12 @@ #include "sclp.h" +static void (*old_machine_restart)(char *); +static void (*old_machine_halt)(void); +static void (*old_machine_power_off)(void); + /* Shutdown handler. Signal completion of shutdown by loading special PSW. */ -static void -do_machine_quiesce(void) +static void do_machine_quiesce(void) { psw_t quiesce_psw; @@ -33,23 +36,48 @@ do_machine_quiesce(void) } /* Handler for quiesce event. Start shutdown procedure. */ -static void -sclp_quiesce_handler(struct evbuf_header *evbuf) +static void sclp_quiesce_handler(struct evbuf_header *evbuf) { - _machine_restart = (void *) do_machine_quiesce; - _machine_halt = do_machine_quiesce; - _machine_power_off = do_machine_quiesce; + if (_machine_restart != (void *) do_machine_quiesce) { + old_machine_restart = _machine_restart; + old_machine_halt = _machine_halt; + old_machine_power_off = _machine_power_off; + _machine_restart = (void *) do_machine_quiesce; + _machine_halt = do_machine_quiesce; + _machine_power_off = do_machine_quiesce; + } ctrl_alt_del(); } +/* Undo machine restart/halt/power_off modification on resume */ +static void sclp_quiesce_pm_event(struct sclp_register *reg, + enum sclp_pm_event sclp_pm_event) +{ + switch (sclp_pm_event) { + case SCLP_PM_EVENT_RESTORE: + if (old_machine_restart) { + _machine_restart = old_machine_restart; + _machine_halt = old_machine_halt; + _machine_power_off = old_machine_power_off; + old_machine_restart = NULL; + old_machine_halt = NULL; + old_machine_power_off = NULL; + } + break; + case SCLP_PM_EVENT_FREEZE: + case SCLP_PM_EVENT_THAW: + break; + } +} + static struct sclp_register sclp_quiesce_event = { .receive_mask = EVTYP_SIGQUIESCE_MASK, - .receiver_fn = sclp_quiesce_handler + .receiver_fn = sclp_quiesce_handler, + .pm_event_fn = sclp_quiesce_pm_event }; /* Initialize quiesce driver. */ -static int __init -sclp_quiesce_init(void) +static int __init sclp_quiesce_init(void) { return sclp_register(&sclp_quiesce_event); } diff --git a/drivers/s390/char/sclp_vt220.c b/drivers/s390/char/sclp_vt220.c index 178724f2a4c3..b9d2a007e93b 100644 --- a/drivers/s390/char/sclp_vt220.c +++ b/drivers/s390/char/sclp_vt220.c @@ -705,21 +705,6 @@ out_driver: } __initcall(sclp_vt220_tty_init); -#ifdef CONFIG_SCLP_VT220_CONSOLE - -static void -sclp_vt220_con_write(struct console *con, const char *buf, unsigned int count) -{ - __sclp_vt220_write((const unsigned char *) buf, count, 1, 1, 0); -} - -static struct tty_driver * -sclp_vt220_con_device(struct console *c, int *index) -{ - *index = 0; - return sclp_vt220_driver; -} - static void __sclp_vt220_flush_buffer(void) { unsigned long flags; @@ -776,6 +761,21 @@ static void sclp_vt220_pm_event_fn(struct sclp_register *reg, } } +#ifdef CONFIG_SCLP_VT220_CONSOLE + +static void +sclp_vt220_con_write(struct console *con, const char *buf, unsigned int count) +{ + __sclp_vt220_write((const unsigned char *) buf, count, 1, 1, 0); +} + +static struct tty_driver * +sclp_vt220_con_device(struct console *c, int *index) +{ + *index = 0; + return sclp_vt220_driver; +} + static int sclp_vt220_notify(struct notifier_block *self, unsigned long event, void *data) diff --git a/drivers/s390/char/tape_block.c b/drivers/s390/char/tape_block.c index 64f57ef2763c..0c0705b91c28 100644 --- a/drivers/s390/char/tape_block.c +++ b/drivers/s390/char/tape_block.c @@ -162,9 +162,10 @@ tapeblock_requeue(struct work_struct *work) { spin_lock_irq(&device->blk_data.request_queue_lock); while ( !blk_queue_plugged(queue) && - (req = blk_fetch_request(queue)) && + blk_peek_request(queue) && nr_queued < TAPEBLOCK_MIN_REQUEUE ) { + req = blk_fetch_request(queue); if (rq_data_dir(req) == WRITE) { DBF_EVENT(1, "TBLOCK: Rejecting write request\n"); spin_unlock_irq(&device->blk_data.request_queue_lock); diff --git a/drivers/s390/cio/blacklist.c b/drivers/s390/cio/blacklist.c index 6565f027791e..7eab9ab9f406 100644 --- a/drivers/s390/cio/blacklist.c +++ b/drivers/s390/cio/blacklist.c @@ -265,13 +265,11 @@ struct ccwdev_iter { static void * cio_ignore_proc_seq_start(struct seq_file *s, loff_t *offset) { - struct ccwdev_iter *iter; + struct ccwdev_iter *iter = s->private; if (*offset >= (__MAX_SUBCHANNEL + 1) * (__MAX_SSID + 1)) return NULL; - iter = kzalloc(sizeof(struct ccwdev_iter), GFP_KERNEL); - if (!iter) - return ERR_PTR(-ENOMEM); + memset(iter, 0, sizeof(*iter)); iter->ssid = *offset / (__MAX_SUBCHANNEL + 1); iter->devno = *offset % (__MAX_SUBCHANNEL + 1); return iter; @@ -280,8 +278,6 @@ cio_ignore_proc_seq_start(struct seq_file *s, loff_t *offset) static void cio_ignore_proc_seq_stop(struct seq_file *s, void *it) { - if (!IS_ERR(it)) - kfree(it); } static void * @@ -378,14 +374,15 @@ static const struct seq_operations cio_ignore_proc_seq_ops = { static int cio_ignore_proc_open(struct inode *inode, struct file *file) { - return seq_open(file, &cio_ignore_proc_seq_ops); + return seq_open_private(file, &cio_ignore_proc_seq_ops, + sizeof(struct ccwdev_iter)); } static const struct file_operations cio_ignore_proc_fops = { .open = cio_ignore_proc_open, .read = seq_read, .llseek = seq_lseek, - .release = seq_release, + .release = seq_release_private, .write = cio_ignore_write, }; diff --git a/drivers/s390/cio/chp.c b/drivers/s390/cio/chp.c index 40002830d48a..8ab51608da55 100644 --- a/drivers/s390/cio/chp.c +++ b/drivers/s390/cio/chp.c @@ -393,7 +393,6 @@ int chp_new(struct chp_id chpid) chp->state = 1; chp->dev.parent = &channel_subsystems[chpid.cssid]->device; chp->dev.release = chp_release; - dev_set_name(&chp->dev, "chp%x.%02x", chpid.cssid, chpid.id); /* Obtain channel path description and fill it in. */ ret = chsc_determine_base_channel_path_desc(chpid, &chp->desc); @@ -411,6 +410,7 @@ int chp_new(struct chp_id chpid) } else { chp->cmg = -1; } + dev_set_name(&chp->dev, "chp%x.%02x", chpid.cssid, chpid.id); /* make it known to the system */ ret = device_register(&chp->dev); diff --git a/drivers/s390/cio/device.c b/drivers/s390/cio/device.c index f780bdd3a04e..2490b741e16a 100644 --- a/drivers/s390/cio/device.c +++ b/drivers/s390/cio/device.c @@ -1250,8 +1250,7 @@ static int io_subchannel_probe(struct subchannel *sch) unsigned long flags; struct ccw_dev_id dev_id; - cdev = sch_get_cdev(sch); - if (cdev) { + if (cio_is_console(sch->schid)) { rc = sysfs_create_group(&sch->dev.kobj, &io_subchannel_attr_group); if (rc) @@ -1260,13 +1259,13 @@ static int io_subchannel_probe(struct subchannel *sch) "0.%x.%04x (rc=%d)\n", sch->schid.ssid, sch->schid.sch_no, rc); /* - * This subchannel already has an associated ccw_device. + * The console subchannel already has an associated ccw_device. * Throw the delayed uevent for the subchannel, register - * the ccw_device and exit. This happens for all early - * devices, e.g. the console. + * the ccw_device and exit. */ dev_set_uevent_suppress(&sch->dev, 0); kobject_uevent(&sch->dev.kobj, KOBJ_ADD); + cdev = sch_get_cdev(sch); cdev->dev.groups = ccwdev_attr_groups; device_initialize(&cdev->dev); ccw_device_register(cdev); @@ -1609,7 +1608,7 @@ int ccw_purge_blacklisted(void) return 0; } -static void device_set_disconnected(struct ccw_device *cdev) +void ccw_device_set_disconnected(struct ccw_device *cdev) { if (!cdev) return; @@ -1705,7 +1704,7 @@ static int io_subchannel_sch_event(struct subchannel *sch, int slow) ccw_device_trigger_reprobe(cdev); break; case DISC: - device_set_disconnected(cdev); + ccw_device_set_disconnected(cdev); break; default: break; diff --git a/drivers/s390/cio/device.h b/drivers/s390/cio/device.h index ed39a2caaf47..246c6482842c 100644 --- a/drivers/s390/cio/device.h +++ b/drivers/s390/cio/device.h @@ -125,6 +125,7 @@ int ccw_device_stlck(struct ccw_device *); void ccw_device_trigger_reprobe(struct ccw_device *); void ccw_device_kill_io(struct ccw_device *); int ccw_device_notify(struct ccw_device *, int); +void ccw_device_set_disconnected(struct ccw_device *cdev); void ccw_device_set_notoper(struct ccw_device *cdev); /* qdio needs this. */ diff --git a/drivers/s390/cio/device_fsm.c b/drivers/s390/cio/device_fsm.c index e728ce447f6e..b9613d7df9ef 100644 --- a/drivers/s390/cio/device_fsm.c +++ b/drivers/s390/cio/device_fsm.c @@ -387,19 +387,35 @@ ccw_device_done(struct ccw_device *cdev, int state) cdev->private->state = state; - if (state == DEV_STATE_BOXED) { + switch (state) { + case DEV_STATE_BOXED: CIO_MSG_EVENT(0, "Boxed device %04x on subchannel %04x\n", cdev->private->dev_id.devno, sch->schid.sch_no); if (cdev->online && !ccw_device_notify(cdev, CIO_BOXED)) ccw_device_schedule_sch_unregister(cdev); cdev->private->flags.donotify = 0; - } - if (state == DEV_STATE_NOT_OPER) { + break; + case DEV_STATE_NOT_OPER: CIO_MSG_EVENT(0, "Device %04x gone on subchannel %04x\n", cdev->private->dev_id.devno, sch->schid.sch_no); if (!ccw_device_notify(cdev, CIO_GONE)) ccw_device_schedule_sch_unregister(cdev); + else + ccw_device_set_disconnected(cdev); cdev->private->flags.donotify = 0; + break; + case DEV_STATE_DISCONNECTED: + CIO_MSG_EVENT(0, "Disconnected device %04x on subchannel " + "%04x\n", cdev->private->dev_id.devno, + sch->schid.sch_no); + if (!ccw_device_notify(cdev, CIO_NO_PATH)) + ccw_device_schedule_sch_unregister(cdev); + else + ccw_device_set_disconnected(cdev); + cdev->private->flags.donotify = 0; + break; + default: + break; } if (cdev->private->flags.donotify) { @@ -671,6 +687,10 @@ ccw_device_offline(struct ccw_device *cdev) ccw_device_done(cdev, DEV_STATE_NOT_OPER); return 0; } + if (cdev->private->state == DEV_STATE_BOXED) { + ccw_device_done(cdev, DEV_STATE_BOXED); + return 0; + } if (ccw_device_is_orphan(cdev)) { ccw_device_done(cdev, DEV_STATE_OFFLINE); return 0; @@ -730,11 +750,10 @@ ccw_device_recog_notoper(struct ccw_device *cdev, enum dev_event dev_event) static void ccw_device_generic_notoper(struct ccw_device *cdev, enum dev_event dev_event) { - struct subchannel *sch; - - ccw_device_set_notoper(cdev); - sch = to_subchannel(cdev->dev.parent); - css_schedule_eval(sch->schid); + if (!ccw_device_notify(cdev, CIO_GONE)) + ccw_device_schedule_sch_unregister(cdev); + else + ccw_device_set_disconnected(cdev); } /* diff --git a/drivers/s390/crypto/zcrypt_pcixcc.c b/drivers/s390/crypto/zcrypt_pcixcc.c index c20d4790258e..5677b40e4ac0 100644 --- a/drivers/s390/crypto/zcrypt_pcixcc.c +++ b/drivers/s390/crypto/zcrypt_pcixcc.c @@ -361,7 +361,7 @@ static void rng_type6CPRB_msgX(struct ap_device *ap_dev, .ToCardLen1 = sizeof *msg - sizeof(msg->hdr), .FromCardLen1 = sizeof *msg - sizeof(msg->hdr), }; - static struct CPRBX static_cprbx = { + static struct CPRBX local_cprbx = { .cprb_len = 0x00dc, .cprb_ver_id = 0x02, .func_id = {0x54, 0x32}, @@ -372,7 +372,7 @@ static void rng_type6CPRB_msgX(struct ap_device *ap_dev, msg->hdr = static_type6_hdrX; msg->hdr.FromCardLen2 = random_number_length, - msg->cprbx = static_cprbx; + msg->cprbx = local_cprbx; msg->cprbx.rpl_datal = random_number_length, msg->cprbx.domain = AP_QID_QUEUE(ap_dev->qid); memcpy(msg->function_code, msg->hdr.function_code, 0x02); @@ -561,7 +561,8 @@ static int convert_response_ica(struct zcrypt_device *zdev, if (msg->cprbx.cprb_ver_id == 0x02) return convert_type86_ica(zdev, reply, outputdata, outputdatalength); - /* no break, incorrect cprb version is an unknown response */ + /* Fall through, no break, incorrect cprb version is an unknown + * response */ default: /* Unknown response type, this should NEVER EVER happen */ zdev->online = 0; return -EAGAIN; /* repeat the request on a different device. */ @@ -587,7 +588,8 @@ static int convert_response_xcrb(struct zcrypt_device *zdev, } if (msg->cprbx.cprb_ver_id == 0x02) return convert_type86_xcrb(zdev, reply, xcRB); - /* no break, incorrect cprb version is an unknown response */ + /* Fall through, no break, incorrect cprb version is an unknown + * response */ default: /* Unknown response type, this should NEVER EVER happen */ xcRB->status = 0x0008044DL; /* HDD_InvalidParm */ zdev->online = 0; @@ -610,7 +612,8 @@ static int convert_response_rng(struct zcrypt_device *zdev, return -EINVAL; if (msg->cprbx.cprb_ver_id == 0x02) return convert_type86_rng(zdev, reply, data); - /* no break, incorrect cprb version is an unknown response */ + /* Fall through, no break, incorrect cprb version is an unknown + * response */ default: /* Unknown response type, this should NEVER EVER happen */ zdev->online = 0; return -EAGAIN; /* repeat the request on a different device. */ diff --git a/drivers/s390/net/smsgiucv.c b/drivers/s390/net/smsgiucv.c index 102000d1af6f..3012355f8304 100644 --- a/drivers/s390/net/smsgiucv.c +++ b/drivers/s390/net/smsgiucv.c @@ -158,7 +158,12 @@ static int smsg_pm_restore_thaw(struct device *dev) smsg_path->flags = 0; rc = iucv_path_connect(smsg_path, &smsg_handler, "*MSG ", NULL, NULL, NULL); - printk(KERN_ERR "iucv_path_connect returned with rc %i\n", rc); +#ifdef CONFIG_PM_DEBUG + if (rc) + printk(KERN_ERR + "iucv_path_connect returned with rc %i\n", rc); +#endif + cpcmd("SET SMSG IUCV", NULL, 0, NULL); } return 0; } diff --git a/drivers/s390/scsi/zfcp_aux.c b/drivers/s390/scsi/zfcp_aux.c index 1be6bf7e8ce6..2889e5f2dfd3 100644 --- a/drivers/s390/scsi/zfcp_aux.c +++ b/drivers/s390/scsi/zfcp_aux.c @@ -80,28 +80,35 @@ int zfcp_reqlist_isempty(struct zfcp_adapter *adapter) static void __init zfcp_init_device_configure(char *busid, u64 wwpn, u64 lun) { + struct ccw_device *ccwdev; struct zfcp_adapter *adapter; struct zfcp_port *port; struct zfcp_unit *unit; - mutex_lock(&zfcp_data.config_mutex); - read_lock_irq(&zfcp_data.config_lock); - adapter = zfcp_get_adapter_by_busid(busid); - if (adapter) - zfcp_adapter_get(adapter); - read_unlock_irq(&zfcp_data.config_lock); + ccwdev = get_ccwdev_by_busid(&zfcp_ccw_driver, busid); + if (!ccwdev) + return; + + if (ccw_device_set_online(ccwdev)) + goto out_ccwdev; + mutex_lock(&zfcp_data.config_mutex); + adapter = dev_get_drvdata(&ccwdev->dev); if (!adapter) - goto out_adapter; - port = zfcp_port_enqueue(adapter, wwpn, 0, 0); - if (IS_ERR(port)) + goto out_unlock; + zfcp_adapter_get(adapter); + + port = zfcp_get_port_by_wwpn(adapter, wwpn); + if (!port) goto out_port; + + zfcp_port_get(port); unit = zfcp_unit_enqueue(port, lun); if (IS_ERR(unit)) goto out_unit; mutex_unlock(&zfcp_data.config_mutex); - ccw_device_set_online(adapter->ccw_device); + zfcp_erp_unit_reopen(unit, 0, "auidc_1", NULL); zfcp_erp_wait(adapter); flush_work(&unit->scsi_work); @@ -111,20 +118,23 @@ out_unit: zfcp_port_put(port); out_port: zfcp_adapter_put(adapter); -out_adapter: +out_unlock: mutex_unlock(&zfcp_data.config_mutex); +out_ccwdev: + put_device(&ccwdev->dev); return; } static void __init zfcp_init_device_setup(char *devstr) { char *token; - char *str; + char *str, *str_saved; char busid[ZFCP_BUS_ID_SIZE]; u64 wwpn, lun; /* duplicate devstr and keep the original for sysfs presentation*/ - str = kmalloc(strlen(devstr) + 1, GFP_KERNEL); + str_saved = kmalloc(strlen(devstr) + 1, GFP_KERNEL); + str = str_saved; if (!str) return; @@ -143,12 +153,12 @@ static void __init zfcp_init_device_setup(char *devstr) if (!token || strict_strtoull(token, 0, (unsigned long long *) &lun)) goto err_out; - kfree(str); + kfree(str_saved); zfcp_init_device_configure(busid, wwpn, lun); return; - err_out: - kfree(str); +err_out: + kfree(str_saved); pr_err("%s is not a valid SCSI device\n", devstr); } @@ -593,10 +603,8 @@ void zfcp_adapter_dequeue(struct zfcp_adapter *adapter) int retval = 0; unsigned long flags; - cancel_work_sync(&adapter->scan_work); cancel_work_sync(&adapter->stat_work); zfcp_fc_wka_ports_force_offline(adapter->gs); - zfcp_adapter_scsi_unregister(adapter); sysfs_remove_group(&adapter->ccw_device->dev.kobj, &zfcp_sysfs_adapter_attrs); dev_set_drvdata(&adapter->ccw_device->dev, NULL); diff --git a/drivers/s390/scsi/zfcp_ccw.c b/drivers/s390/scsi/zfcp_ccw.c index 0c90f8e71605..e08339428ecf 100644 --- a/drivers/s390/scsi/zfcp_ccw.c +++ b/drivers/s390/scsi/zfcp_ccw.c @@ -102,6 +102,14 @@ static void zfcp_ccw_remove(struct ccw_device *ccw_device) adapter = dev_get_drvdata(&ccw_device->dev); if (!adapter) goto out; + mutex_unlock(&zfcp_data.config_mutex); + + cancel_work_sync(&adapter->scan_work); + + mutex_lock(&zfcp_data.config_mutex); + + /* this also removes the scsi devices, so call it first */ + zfcp_adapter_scsi_unregister(adapter); write_lock_irq(&zfcp_data.config_lock); list_for_each_entry_safe(port, p, &adapter->port_list_head, list) { @@ -117,11 +125,8 @@ static void zfcp_ccw_remove(struct ccw_device *ccw_device) write_unlock_irq(&zfcp_data.config_lock); list_for_each_entry_safe(port, p, &port_remove_lh, list) { - list_for_each_entry_safe(unit, u, &unit_remove_lh, list) { - if (unit->device) - scsi_remove_device(unit->device); + list_for_each_entry_safe(unit, u, &unit_remove_lh, list) zfcp_unit_dequeue(unit); - } zfcp_port_dequeue(port); } wait_event(adapter->remove_wq, atomic_read(&adapter->refcount) == 0); @@ -192,13 +197,9 @@ static int zfcp_ccw_set_offline(struct ccw_device *ccw_device) mutex_lock(&zfcp_data.config_mutex); adapter = dev_get_drvdata(&ccw_device->dev); - if (!adapter) - goto out; - zfcp_erp_adapter_shutdown(adapter, 0, "ccsoff1", NULL); zfcp_erp_wait(adapter); mutex_unlock(&zfcp_data.config_mutex); -out: return 0; } @@ -253,13 +254,17 @@ static void zfcp_ccw_shutdown(struct ccw_device *cdev) mutex_lock(&zfcp_data.config_mutex); adapter = dev_get_drvdata(&cdev->dev); + if (!adapter) + goto out; + zfcp_erp_adapter_shutdown(adapter, 0, "ccshut1", NULL); zfcp_erp_wait(adapter); zfcp_erp_thread_kill(adapter); +out: mutex_unlock(&zfcp_data.config_mutex); } -static struct ccw_driver zfcp_ccw_driver = { +struct ccw_driver zfcp_ccw_driver = { .owner = THIS_MODULE, .name = "zfcp", .ids = zfcp_ccw_device_id, @@ -284,20 +289,3 @@ int __init zfcp_ccw_register(void) { return ccw_driver_register(&zfcp_ccw_driver); } - -/** - * zfcp_get_adapter_by_busid - find zfcp_adapter struct - * @busid: bus id string of zfcp adapter to find - */ -struct zfcp_adapter *zfcp_get_adapter_by_busid(char *busid) -{ - struct ccw_device *ccw_device; - struct zfcp_adapter *adapter = NULL; - - ccw_device = get_ccwdev_by_busid(&zfcp_ccw_driver, busid); - if (ccw_device) { - adapter = dev_get_drvdata(&ccw_device->dev); - put_device(&ccw_device->dev); - } - return adapter; -} diff --git a/drivers/s390/scsi/zfcp_cfdc.c b/drivers/s390/scsi/zfcp_cfdc.c index 8305c874e86f..ef681dfed0cc 100644 --- a/drivers/s390/scsi/zfcp_cfdc.c +++ b/drivers/s390/scsi/zfcp_cfdc.c @@ -86,8 +86,23 @@ static int zfcp_cfdc_copy_to_user(void __user *user_buffer, static struct zfcp_adapter *zfcp_cfdc_get_adapter(u32 devno) { char busid[9]; + struct ccw_device *ccwdev; + struct zfcp_adapter *adapter = NULL; + snprintf(busid, sizeof(busid), "0.0.%04x", devno); - return zfcp_get_adapter_by_busid(busid); + ccwdev = get_ccwdev_by_busid(&zfcp_ccw_driver, busid); + if (!ccwdev) + goto out; + + adapter = dev_get_drvdata(&ccwdev->dev); + if (!adapter) + goto out_put; + + zfcp_adapter_get(adapter); +out_put: + put_device(&ccwdev->dev); +out: + return adapter; } static int zfcp_cfdc_set_fsf(struct zfcp_fsf_cfdc *fsf_cfdc, int command) diff --git a/drivers/s390/scsi/zfcp_erp.c b/drivers/s390/scsi/zfcp_erp.c index 73d366ba31e5..f73e2180f333 100644 --- a/drivers/s390/scsi/zfcp_erp.c +++ b/drivers/s390/scsi/zfcp_erp.c @@ -858,10 +858,7 @@ static int zfcp_erp_port_strategy_open_common(struct zfcp_erp_action *act) if (fc_host_port_type(adapter->scsi_host) == FC_PORTTYPE_PTP) return zfcp_erp_open_ptp_port(act); if (!port->d_id) { - zfcp_port_get(port); - if (!queue_work(adapter->work_queue, - &port->gid_pn_work)) - zfcp_port_put(port); + zfcp_fc_trigger_did_lookup(port); return ZFCP_ERP_EXIT; } return zfcp_erp_port_strategy_open_port(act); @@ -869,12 +866,11 @@ static int zfcp_erp_port_strategy_open_common(struct zfcp_erp_action *act) case ZFCP_ERP_STEP_PORT_OPENING: /* D_ID might have changed during open */ if (p_status & ZFCP_STATUS_COMMON_OPEN) { - if (port->d_id) - return ZFCP_ERP_SUCCEEDED; - else { - act->step = ZFCP_ERP_STEP_PORT_CLOSING; - return ZFCP_ERP_CONTINUES; + if (!port->d_id) { + zfcp_fc_trigger_did_lookup(port); + return ZFCP_ERP_EXIT; } + return ZFCP_ERP_SUCCEEDED; } if (port->d_id && !(p_status & ZFCP_STATUS_COMMON_NOESC)) { port->d_id = 0; @@ -889,19 +885,21 @@ static int zfcp_erp_port_strategy_open_common(struct zfcp_erp_action *act) static int zfcp_erp_port_strategy(struct zfcp_erp_action *erp_action) { struct zfcp_port *port = erp_action->port; + int p_status = atomic_read(&port->status); - if (atomic_read(&port->status) & ZFCP_STATUS_COMMON_NOESC) + if ((p_status & ZFCP_STATUS_COMMON_NOESC) && + !(p_status & ZFCP_STATUS_COMMON_OPEN)) goto close_init_done; switch (erp_action->step) { case ZFCP_ERP_STEP_UNINITIALIZED: zfcp_erp_port_strategy_clearstati(port); - if (atomic_read(&port->status) & ZFCP_STATUS_COMMON_OPEN) + if (p_status & ZFCP_STATUS_COMMON_OPEN) return zfcp_erp_port_strategy_close(erp_action); break; case ZFCP_ERP_STEP_PORT_CLOSING: - if (atomic_read(&port->status) & ZFCP_STATUS_COMMON_OPEN) + if (p_status & ZFCP_STATUS_COMMON_OPEN) return ZFCP_ERP_FAILED; break; } diff --git a/drivers/s390/scsi/zfcp_ext.h b/drivers/s390/scsi/zfcp_ext.h index 36935bc0818f..b3f28deb4505 100644 --- a/drivers/s390/scsi/zfcp_ext.h +++ b/drivers/s390/scsi/zfcp_ext.h @@ -28,7 +28,7 @@ extern int zfcp_sg_setup_table(struct scatterlist *, int); /* zfcp_ccw.c */ extern int zfcp_ccw_register(void); extern int zfcp_ccw_priv_sch(struct zfcp_adapter *); -extern struct zfcp_adapter *zfcp_get_adapter_by_busid(char *); +extern struct ccw_driver zfcp_ccw_driver; /* zfcp_cfdc.c */ extern struct miscdevice zfcp_cfdc_misc; @@ -96,6 +96,7 @@ extern int zfcp_fc_scan_ports(struct zfcp_adapter *); extern void _zfcp_fc_scan_ports_later(struct work_struct *); extern void zfcp_fc_incoming_els(struct zfcp_fsf_req *); extern void zfcp_fc_port_did_lookup(struct work_struct *); +extern void zfcp_fc_trigger_did_lookup(struct zfcp_port *); extern void zfcp_fc_plogi_evaluate(struct zfcp_port *, struct fsf_plogi *); extern void zfcp_fc_test_link(struct zfcp_port *); extern void zfcp_fc_link_test_work(struct work_struct *); diff --git a/drivers/s390/scsi/zfcp_fc.c b/drivers/s390/scsi/zfcp_fc.c index 722f22de8753..df23bcead23d 100644 --- a/drivers/s390/scsi/zfcp_fc.c +++ b/drivers/s390/scsi/zfcp_fc.c @@ -361,6 +361,17 @@ out: } /** + * zfcp_fc_trigger_did_lookup - trigger the d_id lookup using a GID_PN request + * @port: The zfcp_port to lookup the d_id for. + */ +void zfcp_fc_trigger_did_lookup(struct zfcp_port *port) +{ + zfcp_port_get(port); + if (!queue_work(port->adapter->work_queue, &port->gid_pn_work)) + zfcp_port_put(port); +} + +/** * zfcp_fc_plogi_evaluate - evaluate PLOGI playload * @port: zfcp_port structure * @plogi: plogi payload diff --git a/drivers/s390/scsi/zfcp_fsf.c b/drivers/s390/scsi/zfcp_fsf.c index f09c863dc6bd..4e41baa0c141 100644 --- a/drivers/s390/scsi/zfcp_fsf.c +++ b/drivers/s390/scsi/zfcp_fsf.c @@ -1058,14 +1058,28 @@ static int zfcp_fsf_setup_ct_els_sbals(struct zfcp_fsf_req *req, bytes = zfcp_qdio_sbals_from_sg(adapter->qdio, &req->queue_req, SBAL_FLAGS0_TYPE_WRITE_READ, sg_resp, max_sbals); + req->qtcb->bottom.support.resp_buf_length = bytes; if (bytes <= 0) return -EIO; + return 0; +} + +static int zfcp_fsf_setup_ct_els(struct zfcp_fsf_req *req, + struct scatterlist *sg_req, + struct scatterlist *sg_resp, + int max_sbals) +{ + int ret; + + ret = zfcp_fsf_setup_ct_els_sbals(req, sg_req, sg_resp, max_sbals); + if (ret) + return ret; + /* common settings for ct/gs and els requests */ - req->qtcb->bottom.support.resp_buf_length = bytes; req->qtcb->bottom.support.service_class = FSF_CLASS_3; req->qtcb->bottom.support.timeout = 2 * R_A_TOV; - zfcp_fsf_start_timer(req, 2 * R_A_TOV + 10); + zfcp_fsf_start_timer(req, (2 * R_A_TOV + 10) * HZ); return 0; } @@ -1094,8 +1108,8 @@ int zfcp_fsf_send_ct(struct zfcp_send_ct *ct, mempool_t *pool) } req->status |= ZFCP_STATUS_FSFREQ_CLEANUP; - ret = zfcp_fsf_setup_ct_els_sbals(req, ct->req, ct->resp, - FSF_MAX_SBALS_PER_REQ); + ret = zfcp_fsf_setup_ct_els(req, ct->req, ct->resp, + FSF_MAX_SBALS_PER_REQ); if (ret) goto failed_send; @@ -1192,7 +1206,7 @@ int zfcp_fsf_send_els(struct zfcp_send_els *els) } req->status |= ZFCP_STATUS_FSFREQ_CLEANUP; - ret = zfcp_fsf_setup_ct_els_sbals(req, els->req, els->resp, 2); + ret = zfcp_fsf_setup_ct_els(req, els->req, els->resp, 2); if (ret) goto failed_send; @@ -1461,9 +1475,16 @@ static void zfcp_fsf_open_port_handler(struct zfcp_fsf_req *req) plogi = (struct fsf_plogi *) req->qtcb->bottom.support.els; if (req->qtcb->bottom.support.els1_length >= FSF_PLOGI_MIN_LEN) { - if (plogi->serv_param.wwpn != port->wwpn) + if (plogi->serv_param.wwpn != port->wwpn) { port->d_id = 0; - else { + dev_warn(&port->adapter->ccw_device->dev, + "A port opened with WWPN 0x%016Lx " + "returned data that identifies it as " + "WWPN 0x%016Lx\n", + (unsigned long long) port->wwpn, + (unsigned long long) + plogi->serv_param.wwpn); + } else { port->wwnn = plogi->serv_param.wwnn; zfcp_fc_plogi_evaluate(port, plogi); } diff --git a/drivers/s390/scsi/zfcp_sysfs.c b/drivers/s390/scsi/zfcp_sysfs.c index 079a8cf518a3..d31000886ca8 100644 --- a/drivers/s390/scsi/zfcp_sysfs.c +++ b/drivers/s390/scsi/zfcp_sysfs.c @@ -224,6 +224,7 @@ static ssize_t zfcp_sysfs_unit_add_store(struct device *dev, zfcp_erp_unit_reopen(unit, 0, "syuas_1", NULL); zfcp_erp_wait(unit->port->adapter); + flush_work(&unit->scsi_work); zfcp_unit_put(unit); out: mutex_unlock(&zfcp_data.config_mutex); diff --git a/drivers/scsi/Kconfig b/drivers/scsi/Kconfig index 82bb3b2d207a..e11cca4c784c 100644 --- a/drivers/scsi/Kconfig +++ b/drivers/scsi/Kconfig @@ -366,6 +366,7 @@ config ISCSI_TCP source "drivers/scsi/cxgb3i/Kconfig" source "drivers/scsi/bnx2i/Kconfig" +source "drivers/scsi/be2iscsi/Kconfig" config SGIWD93_SCSI tristate "SGI WD93C93 SCSI Driver" @@ -1827,6 +1828,16 @@ config SCSI_SRP To compile this driver as a module, choose M here: the module will be called libsrp. +config SCSI_BFA_FC + tristate "Brocade BFA Fibre Channel Support" + depends on PCI && SCSI + select SCSI_FC_ATTRS + help + This bfa driver supports all Brocade PCIe FC/FCOE host adapters. + + To compile this driver as a module, choose M here. The module will + be called bfa. + endif # SCSI_LOWLEVEL source "drivers/scsi/pcmcia/Kconfig" diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile index 61a94af3cee7..3ad61db5e3fa 100644 --- a/drivers/scsi/Makefile +++ b/drivers/scsi/Makefile @@ -86,6 +86,7 @@ obj-$(CONFIG_SCSI_QLOGIC_1280) += qla1280.o obj-$(CONFIG_SCSI_QLA_FC) += qla2xxx/ obj-$(CONFIG_SCSI_QLA_ISCSI) += qla4xxx/ obj-$(CONFIG_SCSI_LPFC) += lpfc/ +obj-$(CONFIG_SCSI_BFA_FC) += bfa/ obj-$(CONFIG_SCSI_PAS16) += pas16.o obj-$(CONFIG_SCSI_T128) += t128.o obj-$(CONFIG_SCSI_DMX3191D) += dmx3191d.o @@ -130,6 +131,7 @@ obj-$(CONFIG_SCSI_MVSAS) += mvsas/ obj-$(CONFIG_PS3_ROM) += ps3rom.o obj-$(CONFIG_SCSI_CXGB3_ISCSI) += libiscsi.o libiscsi_tcp.o cxgb3i/ obj-$(CONFIG_SCSI_BNX2_ISCSI) += libiscsi.o bnx2i/ +obj-$(CONFIG_BE2ISCSI) += libiscsi.o be2iscsi/ obj-$(CONFIG_SCSI_PMCRAID) += pmcraid.o obj-$(CONFIG_ARM) += arm/ diff --git a/drivers/scsi/be2iscsi/Kconfig b/drivers/scsi/be2iscsi/Kconfig new file mode 100644 index 000000000000..2952fcd008ea --- /dev/null +++ b/drivers/scsi/be2iscsi/Kconfig @@ -0,0 +1,8 @@ +config BE2ISCSI + tristate "ServerEngines' 10Gbps iSCSI - BladeEngine 2" + depends on PCI && SCSI + select SCSI_ISCSI_ATTRS + + help + This driver implements the iSCSI functionality for ServerEngines' + 10Gbps Storage adapter - BladeEngine 2. diff --git a/drivers/scsi/be2iscsi/Makefile b/drivers/scsi/be2iscsi/Makefile new file mode 100644 index 000000000000..c11f443e3f83 --- /dev/null +++ b/drivers/scsi/be2iscsi/Makefile @@ -0,0 +1,8 @@ +# +# Makefile to build the iSCSI driver for ServerEngine's BladeEngine. +# +# + +obj-$(CONFIG_BE2ISCSI) += be2iscsi.o + +be2iscsi-y := be_iscsi.o be_main.o be_mgmt.o be_cmds.o diff --git a/drivers/scsi/be2iscsi/be.h b/drivers/scsi/be2iscsi/be.h new file mode 100644 index 000000000000..b36020dcf012 --- /dev/null +++ b/drivers/scsi/be2iscsi/be.h @@ -0,0 +1,183 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + */ + +#ifndef BEISCSI_H +#define BEISCSI_H + +#include <linux/pci.h> +#include <linux/if_vlan.h> + +#define FW_VER_LEN 32 + +struct be_dma_mem { + void *va; + dma_addr_t dma; + u32 size; +}; + +struct be_queue_info { + struct be_dma_mem dma_mem; + u16 len; + u16 entry_size; /* Size of an element in the queue */ + u16 id; + u16 tail, head; + bool created; + atomic_t used; /* Number of valid elements in the queue */ +}; + +static inline u32 MODULO(u16 val, u16 limit) +{ + WARN_ON(limit & (limit - 1)); + return val & (limit - 1); +} + +static inline void index_inc(u16 *index, u16 limit) +{ + *index = MODULO((*index + 1), limit); +} + +static inline void *queue_head_node(struct be_queue_info *q) +{ + return q->dma_mem.va + q->head * q->entry_size; +} + +static inline void *queue_tail_node(struct be_queue_info *q) +{ + return q->dma_mem.va + q->tail * q->entry_size; +} + +static inline void queue_head_inc(struct be_queue_info *q) +{ + index_inc(&q->head, q->len); +} + +static inline void queue_tail_inc(struct be_queue_info *q) +{ + index_inc(&q->tail, q->len); +} + +/*ISCSI */ + +struct be_eq_obj { + struct be_queue_info q; + char desc[32]; + + /* Adaptive interrupt coalescing (AIC) info */ + bool enable_aic; + u16 min_eqd; /* in usecs */ + u16 max_eqd; /* in usecs */ + u16 cur_eqd; /* in usecs */ +}; + +struct be_mcc_obj { + struct be_queue_info *q; + struct be_queue_info *cq; +}; + +struct be_ctrl_info { + u8 __iomem *csr; + u8 __iomem *db; /* Door Bell */ + u8 __iomem *pcicfg; /* PCI config space */ + struct pci_dev *pdev; + + /* Mbox used for cmd request/response */ + spinlock_t mbox_lock; /* For serializing mbox cmds to BE card */ + struct be_dma_mem mbox_mem; + /* Mbox mem is adjusted to align to 16 bytes. The allocated addr + * is stored for freeing purpose */ + struct be_dma_mem mbox_mem_alloced; + + /* MCC Rings */ + struct be_mcc_obj mcc_obj; + spinlock_t mcc_lock; /* For serializing mcc cmds to BE card */ + spinlock_t mcc_cq_lock; + + /* MCC Async callback */ + void (*async_cb) (void *adapter, bool link_up); + void *adapter_ctxt; +}; + +#include "be_cmds.h" + +#define PAGE_SHIFT_4K 12 +#define PAGE_SIZE_4K (1 << PAGE_SHIFT_4K) + +/* Returns number of pages spanned by the data starting at the given addr */ +#define PAGES_4K_SPANNED(_address, size) \ + ((u32)((((size_t)(_address) & (PAGE_SIZE_4K - 1)) + \ + (size) + (PAGE_SIZE_4K - 1)) >> PAGE_SHIFT_4K)) + +/* Byte offset into the page corresponding to given address */ +#define OFFSET_IN_PAGE(addr) \ + ((size_t)(addr) & (PAGE_SIZE_4K-1)) + +/* Returns bit offset within a DWORD of a bitfield */ +#define AMAP_BIT_OFFSET(_struct, field) \ + (((size_t)&(((_struct *)0)->field))%32) + +/* Returns the bit mask of the field that is NOT shifted into location. */ +static inline u32 amap_mask(u32 bitsize) +{ + return (bitsize == 32 ? 0xFFFFFFFF : (1 << bitsize) - 1); +} + +static inline void amap_set(void *ptr, u32 dw_offset, u32 mask, + u32 offset, u32 value) +{ + u32 *dw = (u32 *) ptr + dw_offset; + *dw &= ~(mask << offset); + *dw |= (mask & value) << offset; +} + +#define AMAP_SET_BITS(_struct, field, ptr, val) \ + amap_set(ptr, \ + offsetof(_struct, field)/32, \ + amap_mask(sizeof(((_struct *)0)->field)), \ + AMAP_BIT_OFFSET(_struct, field), \ + val) + +static inline u32 amap_get(void *ptr, u32 dw_offset, u32 mask, u32 offset) +{ + u32 *dw = ptr; + return mask & (*(dw + dw_offset) >> offset); +} + +#define AMAP_GET_BITS(_struct, field, ptr) \ + amap_get(ptr, \ + offsetof(_struct, field)/32, \ + amap_mask(sizeof(((_struct *)0)->field)), \ + AMAP_BIT_OFFSET(_struct, field)) + +#define be_dws_cpu_to_le(wrb, len) swap_dws(wrb, len) +#define be_dws_le_to_cpu(wrb, len) swap_dws(wrb, len) +static inline void swap_dws(void *wrb, int len) +{ +#ifdef __BIG_ENDIAN + u32 *dw = wrb; + WARN_ON(len % 4); + do { + *dw = cpu_to_le32(*dw); + dw++; + len -= 4; + } while (len); +#endif /* __BIG_ENDIAN */ +} + +extern void beiscsi_cq_notify(struct be_ctrl_info *ctrl, u16 qid, bool arm, + u16 num_popped); + +#endif /* BEISCSI_H */ diff --git a/drivers/scsi/be2iscsi/be_cmds.c b/drivers/scsi/be2iscsi/be_cmds.c new file mode 100644 index 000000000000..08007b6e42df --- /dev/null +++ b/drivers/scsi/be2iscsi/be_cmds.c @@ -0,0 +1,523 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + */ + +#include "be.h" +#include "be_mgmt.h" +#include "be_main.h" + +static inline bool be_mcc_compl_is_new(struct be_mcc_compl *compl) +{ + if (compl->flags != 0) { + compl->flags = le32_to_cpu(compl->flags); + WARN_ON((compl->flags & CQE_FLAGS_VALID_MASK) == 0); + return true; + } else + return false; +} + +static inline void be_mcc_compl_use(struct be_mcc_compl *compl) +{ + compl->flags = 0; +} + +static int be_mcc_compl_process(struct be_ctrl_info *ctrl, + struct be_mcc_compl *compl) +{ + u16 compl_status, extd_status; + + be_dws_le_to_cpu(compl, 4); + + compl_status = (compl->status >> CQE_STATUS_COMPL_SHIFT) & + CQE_STATUS_COMPL_MASK; + if (compl_status != MCC_STATUS_SUCCESS) { + extd_status = (compl->status >> CQE_STATUS_EXTD_SHIFT) & + CQE_STATUS_EXTD_MASK; + dev_err(&ctrl->pdev->dev, + "error in cmd completion: status(compl/extd)=%d/%d\n", + compl_status, extd_status); + return -1; + } + return 0; +} + +static inline bool is_link_state_evt(u32 trailer) +{ + return (((trailer >> ASYNC_TRAILER_EVENT_CODE_SHIFT) & + ASYNC_TRAILER_EVENT_CODE_MASK) == ASYNC_EVENT_CODE_LINK_STATE); +} + +void beiscsi_cq_notify(struct be_ctrl_info *ctrl, u16 qid, bool arm, + u16 num_popped) +{ + u32 val = 0; + val |= qid & DB_CQ_RING_ID_MASK; + if (arm) + val |= 1 << DB_CQ_REARM_SHIFT; + val |= num_popped << DB_CQ_NUM_POPPED_SHIFT; + iowrite32(val, ctrl->db + DB_CQ_OFFSET); +} + +static int be_mbox_db_ready_wait(struct be_ctrl_info *ctrl) +{ +#define long_delay 2000 + void __iomem *db = ctrl->db + MPU_MAILBOX_DB_OFFSET; + int cnt = 0, wait = 5; /* in usecs */ + u32 ready; + + do { + ready = ioread32(db) & MPU_MAILBOX_DB_RDY_MASK; + if (ready) + break; + + if (cnt > 6000000) { + dev_err(&ctrl->pdev->dev, "mbox_db poll timed out\n"); + return -1; + } + + if (cnt > 50) { + wait = long_delay; + mdelay(long_delay / 1000); + } else + udelay(wait); + cnt += wait; + } while (true); + return 0; +} + +int be_mbox_notify(struct be_ctrl_info *ctrl) +{ + int status; + u32 val = 0; + void __iomem *db = ctrl->db + MPU_MAILBOX_DB_OFFSET; + struct be_dma_mem *mbox_mem = &ctrl->mbox_mem; + struct be_mcc_mailbox *mbox = mbox_mem->va; + struct be_mcc_compl *compl = &mbox->compl; + + val &= ~MPU_MAILBOX_DB_RDY_MASK; + val |= MPU_MAILBOX_DB_HI_MASK; + val |= (upper_32_bits(mbox_mem->dma) >> 2) << 2; + iowrite32(val, db); + + status = be_mbox_db_ready_wait(ctrl); + if (status != 0) { + SE_DEBUG(DBG_LVL_1, " be_mbox_db_ready_wait failed 1\n"); + return status; + } + val = 0; + val &= ~MPU_MAILBOX_DB_RDY_MASK; + val &= ~MPU_MAILBOX_DB_HI_MASK; + val |= (u32) (mbox_mem->dma >> 4) << 2; + iowrite32(val, db); + + status = be_mbox_db_ready_wait(ctrl); + if (status != 0) { + SE_DEBUG(DBG_LVL_1, " be_mbox_db_ready_wait failed 2\n"); + return status; + } + if (be_mcc_compl_is_new(compl)) { + status = be_mcc_compl_process(ctrl, &mbox->compl); + be_mcc_compl_use(compl); + if (status) { + SE_DEBUG(DBG_LVL_1, "After be_mcc_compl_process \n"); + return status; + } + } else { + dev_err(&ctrl->pdev->dev, "invalid mailbox completion\n"); + return -1; + } + return 0; +} + +void be_wrb_hdr_prepare(struct be_mcc_wrb *wrb, int payload_len, + bool embedded, u8 sge_cnt) +{ + if (embedded) + wrb->embedded |= MCC_WRB_EMBEDDED_MASK; + else + wrb->embedded |= (sge_cnt & MCC_WRB_SGE_CNT_MASK) << + MCC_WRB_SGE_CNT_SHIFT; + wrb->payload_length = payload_len; + be_dws_cpu_to_le(wrb, 8); +} + +void be_cmd_hdr_prepare(struct be_cmd_req_hdr *req_hdr, + u8 subsystem, u8 opcode, int cmd_len) +{ + req_hdr->opcode = opcode; + req_hdr->subsystem = subsystem; + req_hdr->request_length = cpu_to_le32(cmd_len - sizeof(*req_hdr)); +} + +static void be_cmd_page_addrs_prepare(struct phys_addr *pages, u32 max_pages, + struct be_dma_mem *mem) +{ + int i, buf_pages; + u64 dma = (u64) mem->dma; + + buf_pages = min(PAGES_4K_SPANNED(mem->va, mem->size), max_pages); + for (i = 0; i < buf_pages; i++) { + pages[i].lo = cpu_to_le32(dma & 0xFFFFFFFF); + pages[i].hi = cpu_to_le32(upper_32_bits(dma)); + dma += PAGE_SIZE_4K; + } +} + +static u32 eq_delay_to_mult(u32 usec_delay) +{ +#define MAX_INTR_RATE 651042 + const u32 round = 10; + u32 multiplier; + + if (usec_delay == 0) + multiplier = 0; + else { + u32 interrupt_rate = 1000000 / usec_delay; + if (interrupt_rate == 0) + multiplier = 1023; + else { + multiplier = (MAX_INTR_RATE - interrupt_rate) * round; + multiplier /= interrupt_rate; + multiplier = (multiplier + round / 2) / round; + multiplier = min(multiplier, (u32) 1023); + } + } + return multiplier; +} + +struct be_mcc_wrb *wrb_from_mbox(struct be_dma_mem *mbox_mem) +{ + return &((struct be_mcc_mailbox *)(mbox_mem->va))->wrb; +} + +int beiscsi_cmd_eq_create(struct be_ctrl_info *ctrl, + struct be_queue_info *eq, int eq_delay) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_cmd_req_eq_create *req = embedded_payload(wrb); + struct be_cmd_resp_eq_create *resp = embedded_payload(wrb); + struct be_dma_mem *q_mem = &eq->dma_mem; + int status; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON, + OPCODE_COMMON_EQ_CREATE, sizeof(*req)); + + req->num_pages = cpu_to_le16(PAGES_4K_SPANNED(q_mem->va, q_mem->size)); + + AMAP_SET_BITS(struct amap_eq_context, func, req->context, + PCI_FUNC(ctrl->pdev->devfn)); + AMAP_SET_BITS(struct amap_eq_context, valid, req->context, 1); + AMAP_SET_BITS(struct amap_eq_context, size, req->context, 0); + AMAP_SET_BITS(struct amap_eq_context, count, req->context, + __ilog2_u32(eq->len / 256)); + AMAP_SET_BITS(struct amap_eq_context, delaymult, req->context, + eq_delay_to_mult(eq_delay)); + be_dws_cpu_to_le(req->context, sizeof(req->context)); + + be_cmd_page_addrs_prepare(req->pages, ARRAY_SIZE(req->pages), q_mem); + + status = be_mbox_notify(ctrl); + if (!status) { + eq->id = le16_to_cpu(resp->eq_id); + eq->created = true; + } + spin_unlock(&ctrl->mbox_lock); + return status; +} + +int be_cmd_fw_initialize(struct be_ctrl_info *ctrl) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + int status; + u8 *endian_check; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + endian_check = (u8 *) wrb; + *endian_check++ = 0xFF; + *endian_check++ = 0x12; + *endian_check++ = 0x34; + *endian_check++ = 0xFF; + *endian_check++ = 0xFF; + *endian_check++ = 0x56; + *endian_check++ = 0x78; + *endian_check++ = 0xFF; + be_dws_cpu_to_le(wrb, sizeof(*wrb)); + + status = be_mbox_notify(ctrl); + if (status) + SE_DEBUG(DBG_LVL_1, "be_cmd_fw_initialize Failed \n"); + + spin_unlock(&ctrl->mbox_lock); + return status; +} + +int beiscsi_cmd_cq_create(struct be_ctrl_info *ctrl, + struct be_queue_info *cq, struct be_queue_info *eq, + bool sol_evts, bool no_delay, int coalesce_wm) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_cmd_req_cq_create *req = embedded_payload(wrb); + struct be_cmd_resp_cq_create *resp = embedded_payload(wrb); + struct be_dma_mem *q_mem = &cq->dma_mem; + void *ctxt = &req->context; + int status; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON, + OPCODE_COMMON_CQ_CREATE, sizeof(*req)); + + if (!q_mem->va) + SE_DEBUG(DBG_LVL_1, "uninitialized q_mem->va\n"); + + req->num_pages = cpu_to_le16(PAGES_4K_SPANNED(q_mem->va, q_mem->size)); + + AMAP_SET_BITS(struct amap_cq_context, coalescwm, ctxt, coalesce_wm); + AMAP_SET_BITS(struct amap_cq_context, nodelay, ctxt, no_delay); + AMAP_SET_BITS(struct amap_cq_context, count, ctxt, + __ilog2_u32(cq->len / 256)); + AMAP_SET_BITS(struct amap_cq_context, valid, ctxt, 1); + AMAP_SET_BITS(struct amap_cq_context, solevent, ctxt, sol_evts); + AMAP_SET_BITS(struct amap_cq_context, eventable, ctxt, 1); + AMAP_SET_BITS(struct amap_cq_context, eqid, ctxt, eq->id); + AMAP_SET_BITS(struct amap_cq_context, armed, ctxt, 1); + AMAP_SET_BITS(struct amap_cq_context, func, ctxt, + PCI_FUNC(ctrl->pdev->devfn)); + be_dws_cpu_to_le(ctxt, sizeof(req->context)); + + be_cmd_page_addrs_prepare(req->pages, ARRAY_SIZE(req->pages), q_mem); + + status = be_mbox_notify(ctrl); + if (!status) { + cq->id = le16_to_cpu(resp->cq_id); + cq->created = true; + } else + SE_DEBUG(DBG_LVL_1, "In be_cmd_cq_create, status=ox%08x \n", + status); + spin_unlock(&ctrl->mbox_lock); + + return status; +} + +static u32 be_encoded_q_len(int q_len) +{ + u32 len_encoded = fls(q_len); /* log2(len) + 1 */ + if (len_encoded == 16) + len_encoded = 0; + return len_encoded; +} +int beiscsi_cmd_q_destroy(struct be_ctrl_info *ctrl, struct be_queue_info *q, + int queue_type) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_cmd_req_q_destroy *req = embedded_payload(wrb); + u8 subsys = 0, opcode = 0; + int status; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + + switch (queue_type) { + case QTYPE_EQ: + subsys = CMD_SUBSYSTEM_COMMON; + opcode = OPCODE_COMMON_EQ_DESTROY; + break; + case QTYPE_CQ: + subsys = CMD_SUBSYSTEM_COMMON; + opcode = OPCODE_COMMON_CQ_DESTROY; + break; + case QTYPE_WRBQ: + subsys = CMD_SUBSYSTEM_ISCSI; + opcode = OPCODE_COMMON_ISCSI_WRBQ_DESTROY; + break; + case QTYPE_DPDUQ: + subsys = CMD_SUBSYSTEM_ISCSI; + opcode = OPCODE_COMMON_ISCSI_DEFQ_DESTROY; + break; + case QTYPE_SGL: + subsys = CMD_SUBSYSTEM_ISCSI; + opcode = OPCODE_COMMON_ISCSI_CFG_REMOVE_SGL_PAGES; + break; + default: + spin_unlock(&ctrl->mbox_lock); + BUG(); + return -1; + } + be_cmd_hdr_prepare(&req->hdr, subsys, opcode, sizeof(*req)); + if (queue_type != QTYPE_SGL) + req->id = cpu_to_le16(q->id); + + status = be_mbox_notify(ctrl); + + spin_unlock(&ctrl->mbox_lock); + return status; +} + +int be_cmd_get_mac_addr(struct be_ctrl_info *ctrl, u8 *mac_addr) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_cmd_req_get_mac_addr *req = embedded_payload(wrb); + int status; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI, + OPCODE_COMMON_ISCSI_NTWK_GET_NIC_CONFIG, + sizeof(*req)); + + status = be_mbox_notify(ctrl); + if (!status) { + struct be_cmd_resp_get_mac_addr *resp = embedded_payload(wrb); + + memcpy(mac_addr, resp->mac_address, ETH_ALEN); + } + + spin_unlock(&ctrl->mbox_lock); + return status; +} + +int be_cmd_create_default_pdu_queue(struct be_ctrl_info *ctrl, + struct be_queue_info *cq, + struct be_queue_info *dq, int length, + int entry_size) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_defq_create_req *req = embedded_payload(wrb); + struct be_dma_mem *q_mem = &dq->dma_mem; + void *ctxt = &req->context; + int status; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI, + OPCODE_COMMON_ISCSI_DEFQ_CREATE, sizeof(*req)); + + req->num_pages = PAGES_4K_SPANNED(q_mem->va, q_mem->size); + AMAP_SET_BITS(struct amap_be_default_pdu_context, rx_pdid, ctxt, 0); + AMAP_SET_BITS(struct amap_be_default_pdu_context, rx_pdid_valid, ctxt, + 1); + AMAP_SET_BITS(struct amap_be_default_pdu_context, pci_func_id, ctxt, + PCI_FUNC(ctrl->pdev->devfn)); + AMAP_SET_BITS(struct amap_be_default_pdu_context, ring_size, ctxt, + be_encoded_q_len(length / sizeof(struct phys_addr))); + AMAP_SET_BITS(struct amap_be_default_pdu_context, default_buffer_size, + ctxt, entry_size); + AMAP_SET_BITS(struct amap_be_default_pdu_context, cq_id_recv, ctxt, + cq->id); + + be_dws_cpu_to_le(ctxt, sizeof(req->context)); + + be_cmd_page_addrs_prepare(req->pages, ARRAY_SIZE(req->pages), q_mem); + + status = be_mbox_notify(ctrl); + if (!status) { + struct be_defq_create_resp *resp = embedded_payload(wrb); + + dq->id = le16_to_cpu(resp->id); + dq->created = true; + } + spin_unlock(&ctrl->mbox_lock); + + return status; +} + +int be_cmd_wrbq_create(struct be_ctrl_info *ctrl, struct be_dma_mem *q_mem, + struct be_queue_info *wrbq) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_wrbq_create_req *req = embedded_payload(wrb); + struct be_wrbq_create_resp *resp = embedded_payload(wrb); + int status; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI, + OPCODE_COMMON_ISCSI_WRBQ_CREATE, sizeof(*req)); + req->num_pages = PAGES_4K_SPANNED(q_mem->va, q_mem->size); + be_cmd_page_addrs_prepare(req->pages, ARRAY_SIZE(req->pages), q_mem); + + status = be_mbox_notify(ctrl); + if (!status) + wrbq->id = le16_to_cpu(resp->cid); + spin_unlock(&ctrl->mbox_lock); + return status; +} + +int be_cmd_iscsi_post_sgl_pages(struct be_ctrl_info *ctrl, + struct be_dma_mem *q_mem, + u32 page_offset, u32 num_pages) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_post_sgl_pages_req *req = embedded_payload(wrb); + int status; + unsigned int curr_pages; + u32 internal_page_offset = 0; + u32 temp_num_pages = num_pages; + + if (num_pages == 0xff) + num_pages = 1; + + spin_lock(&ctrl->mbox_lock); + do { + memset(wrb, 0, sizeof(*wrb)); + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI, + OPCODE_COMMON_ISCSI_CFG_POST_SGL_PAGES, + sizeof(*req)); + curr_pages = BE_NUMBER_OF_FIELD(struct be_post_sgl_pages_req, + pages); + req->num_pages = min(num_pages, curr_pages); + req->page_offset = page_offset; + be_cmd_page_addrs_prepare(req->pages, req->num_pages, q_mem); + q_mem->dma = q_mem->dma + (req->num_pages * PAGE_SIZE); + internal_page_offset += req->num_pages; + page_offset += req->num_pages; + num_pages -= req->num_pages; + + if (temp_num_pages == 0xff) + req->num_pages = temp_num_pages; + + status = be_mbox_notify(ctrl); + if (status) { + SE_DEBUG(DBG_LVL_1, + "FW CMD to map iscsi frags failed.\n"); + goto error; + } + } while (num_pages > 0); +error: + spin_unlock(&ctrl->mbox_lock); + if (status != 0) + beiscsi_cmd_q_destroy(ctrl, NULL, QTYPE_SGL); + return status; +} diff --git a/drivers/scsi/be2iscsi/be_cmds.h b/drivers/scsi/be2iscsi/be_cmds.h new file mode 100644 index 000000000000..c20d686cbb43 --- /dev/null +++ b/drivers/scsi/be2iscsi/be_cmds.h @@ -0,0 +1,877 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + */ + +#ifndef BEISCSI_CMDS_H +#define BEISCSI_CMDS_H + +/** + * The driver sends configuration and managements command requests to the + * firmware in the BE. These requests are communicated to the processor + * using Work Request Blocks (WRBs) submitted to the MCC-WRB ring or via one + * WRB inside a MAILBOX. + * The commands are serviced by the ARM processor in the BladeEngine's MPU. + */ +struct be_sge { + u32 pa_lo; + u32 pa_hi; + u32 len; +}; + +#define MCC_WRB_SGE_CNT_SHIFT 3 /* bits 3 - 7 of dword 0 */ +#define MCC_WRB_SGE_CNT_MASK 0x1F /* bits 3 - 7 of dword 0 */ +struct be_mcc_wrb { + u32 embedded; /* dword 0 */ + u32 payload_length; /* dword 1 */ + u32 tag0; /* dword 2 */ + u32 tag1; /* dword 3 */ + u32 rsvd; /* dword 4 */ + union { + u8 embedded_payload[236]; /* used by embedded cmds */ + struct be_sge sgl[19]; /* used by non-embedded cmds */ + } payload; +}; + +#define CQE_FLAGS_VALID_MASK (1 << 31) +#define CQE_FLAGS_ASYNC_MASK (1 << 30) + +/* Completion Status */ +#define MCC_STATUS_SUCCESS 0x0 + +#define CQE_STATUS_COMPL_MASK 0xFFFF +#define CQE_STATUS_COMPL_SHIFT 0 /* bits 0 - 15 */ +#define CQE_STATUS_EXTD_MASK 0xFFFF +#define CQE_STATUS_EXTD_SHIFT 0 /* bits 0 - 15 */ + +struct be_mcc_compl { + u32 status; /* dword 0 */ + u32 tag0; /* dword 1 */ + u32 tag1; /* dword 2 */ + u32 flags; /* dword 3 */ +}; + +/********* Mailbox door bell *************/ +/** + * Used for driver communication with the FW. + * The software must write this register twice to post any command. First, + * it writes the register with hi=1 and the upper bits of the physical address + * for the MAILBOX structure. Software must poll the ready bit until this + * is acknowledged. Then, sotware writes the register with hi=0 with the lower + * bits in the address. It must poll the ready bit until the command is + * complete. Upon completion, the MAILBOX will contain a valid completion + * queue entry. + */ +#define MPU_MAILBOX_DB_OFFSET 0x160 +#define MPU_MAILBOX_DB_RDY_MASK 0x1 /* bit 0 */ +#define MPU_MAILBOX_DB_HI_MASK 0x2 /* bit 1 */ + +/********** MPU semphore ******************/ +#define MPU_EP_SEMAPHORE_OFFSET 0xac +#define EP_SEMAPHORE_POST_STAGE_MASK 0x0000FFFF +#define EP_SEMAPHORE_POST_ERR_MASK 0x1 +#define EP_SEMAPHORE_POST_ERR_SHIFT 31 + +/********** MCC door bell ************/ +#define DB_MCCQ_OFFSET 0x140 +#define DB_MCCQ_RING_ID_MASK 0x7FF /* bits 0 - 10 */ +/* Number of entries posted */ +#define DB_MCCQ_NUM_POSTED_SHIFT 16 /* bits 16 - 29 */ + +/* MPU semphore POST stage values */ +#define POST_STAGE_ARMFW_RDY 0xc000 /* FW is done with POST */ + +/** + * When the async bit of mcc_compl is set, the last 4 bytes of + * mcc_compl is interpreted as follows: + */ +#define ASYNC_TRAILER_EVENT_CODE_SHIFT 8 /* bits 8 - 15 */ +#define ASYNC_TRAILER_EVENT_CODE_MASK 0xFF +#define ASYNC_EVENT_CODE_LINK_STATE 0x1 +struct be_async_event_trailer { + u32 code; +}; + +enum { + ASYNC_EVENT_LINK_DOWN = 0x0, + ASYNC_EVENT_LINK_UP = 0x1 +}; + +/** + * When the event code of an async trailer is link-state, the mcc_compl + * must be interpreted as follows + */ +struct be_async_event_link_state { + u8 physical_port; + u8 port_link_status; + u8 port_duplex; + u8 port_speed; + u8 port_fault; + u8 rsvd0[7]; + struct be_async_event_trailer trailer; +} __packed; + +struct be_mcc_mailbox { + struct be_mcc_wrb wrb; + struct be_mcc_compl compl; +}; + +/* Type of subsystems supported by FW */ +#define CMD_SUBSYSTEM_COMMON 0x1 +#define CMD_SUBSYSTEM_ISCSI 0x2 +#define CMD_SUBSYSTEM_ETH 0x3 +#define CMD_SUBSYSTEM_ISCSI_INI 0x6 +#define CMD_COMMON_TCP_UPLOAD 0x1 + +/** + * List of common opcodes subsystem CMD_SUBSYSTEM_COMMON + * These opcodes are unique for each subsystem defined above + */ +#define OPCODE_COMMON_CQ_CREATE 12 +#define OPCODE_COMMON_EQ_CREATE 13 +#define OPCODE_COMMON_MCC_CREATE 21 +#define OPCODE_COMMON_GET_CNTL_ATTRIBUTES 32 +#define OPCODE_COMMON_GET_FW_VERSION 35 +#define OPCODE_COMMON_MODIFY_EQ_DELAY 41 +#define OPCODE_COMMON_FIRMWARE_CONFIG 42 +#define OPCODE_COMMON_MCC_DESTROY 53 +#define OPCODE_COMMON_CQ_DESTROY 54 +#define OPCODE_COMMON_EQ_DESTROY 55 +#define OPCODE_COMMON_QUERY_FIRMWARE_CONFIG 58 +#define OPCODE_COMMON_FUNCTION_RESET 61 + +/** + * LIST of opcodes that are common between Initiator and Target + * used by CMD_SUBSYSTEM_ISCSI + * These opcodes are unique for each subsystem defined above + */ +#define OPCODE_COMMON_ISCSI_CFG_POST_SGL_PAGES 2 +#define OPCODE_COMMON_ISCSI_CFG_REMOVE_SGL_PAGES 3 +#define OPCODE_COMMON_ISCSI_NTWK_GET_NIC_CONFIG 7 +#define OPCODE_COMMON_ISCSI_SET_FRAGNUM_BITS_FOR_SGL_CRA 61 +#define OPCODE_COMMON_ISCSI_DEFQ_CREATE 64 +#define OPCODE_COMMON_ISCSI_DEFQ_DESTROY 65 +#define OPCODE_COMMON_ISCSI_WRBQ_CREATE 66 +#define OPCODE_COMMON_ISCSI_WRBQ_DESTROY 67 + +struct be_cmd_req_hdr { + u8 opcode; /* dword 0 */ + u8 subsystem; /* dword 0 */ + u8 port_number; /* dword 0 */ + u8 domain; /* dword 0 */ + u32 timeout; /* dword 1 */ + u32 request_length; /* dword 2 */ + u32 rsvd; /* dword 3 */ +}; + +struct be_cmd_resp_hdr { + u32 info; /* dword 0 */ + u32 status; /* dword 1 */ + u32 response_length; /* dword 2 */ + u32 actual_resp_len; /* dword 3 */ +}; + +struct phys_addr { + u32 lo; + u32 hi; +}; + +/************************** + * BE Command definitions * + **************************/ + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte - used to calculate offset/shift/mask of each field + */ +struct amap_eq_context { + u8 cidx[13]; /* dword 0 */ + u8 rsvd0[3]; /* dword 0 */ + u8 epidx[13]; /* dword 0 */ + u8 valid; /* dword 0 */ + u8 rsvd1; /* dword 0 */ + u8 size; /* dword 0 */ + u8 pidx[13]; /* dword 1 */ + u8 rsvd2[3]; /* dword 1 */ + u8 pd[10]; /* dword 1 */ + u8 count[3]; /* dword 1 */ + u8 solevent; /* dword 1 */ + u8 stalled; /* dword 1 */ + u8 armed; /* dword 1 */ + u8 rsvd3[4]; /* dword 2 */ + u8 func[8]; /* dword 2 */ + u8 rsvd4; /* dword 2 */ + u8 delaymult[10]; /* dword 2 */ + u8 rsvd5[2]; /* dword 2 */ + u8 phase[2]; /* dword 2 */ + u8 nodelay; /* dword 2 */ + u8 rsvd6[4]; /* dword 2 */ + u8 rsvd7[32]; /* dword 3 */ +} __packed; + +struct be_cmd_req_eq_create { + struct be_cmd_req_hdr hdr; /* dw[4] */ + u16 num_pages; /* sword */ + u16 rsvd0; /* sword */ + u8 context[sizeof(struct amap_eq_context) / 8]; /* dw[4] */ + struct phys_addr pages[8]; +} __packed; + +struct be_cmd_resp_eq_create { + struct be_cmd_resp_hdr resp_hdr; + u16 eq_id; /* sword */ + u16 rsvd0; /* sword */ +} __packed; + +struct mac_addr { + u16 size_of_struct; + u8 addr[ETH_ALEN]; +} __packed; + +struct be_cmd_req_mac_query { + struct be_cmd_req_hdr hdr; + u8 type; + u8 permanent; + u16 if_id; +} __packed; + +struct be_cmd_resp_mac_query { + struct be_cmd_resp_hdr hdr; + struct mac_addr mac; +}; + +/******************** Create CQ ***************************/ +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte - used to calculate offset/shift/mask of each field + */ +struct amap_cq_context { + u8 cidx[11]; /* dword 0 */ + u8 rsvd0; /* dword 0 */ + u8 coalescwm[2]; /* dword 0 */ + u8 nodelay; /* dword 0 */ + u8 epidx[11]; /* dword 0 */ + u8 rsvd1; /* dword 0 */ + u8 count[2]; /* dword 0 */ + u8 valid; /* dword 0 */ + u8 solevent; /* dword 0 */ + u8 eventable; /* dword 0 */ + u8 pidx[11]; /* dword 1 */ + u8 rsvd2; /* dword 1 */ + u8 pd[10]; /* dword 1 */ + u8 eqid[8]; /* dword 1 */ + u8 stalled; /* dword 1 */ + u8 armed; /* dword 1 */ + u8 rsvd3[4]; /* dword 2 */ + u8 func[8]; /* dword 2 */ + u8 rsvd4[20]; /* dword 2 */ + u8 rsvd5[32]; /* dword 3 */ +} __packed; + +struct be_cmd_req_cq_create { + struct be_cmd_req_hdr hdr; + u16 num_pages; + u16 rsvd0; + u8 context[sizeof(struct amap_cq_context) / 8]; + struct phys_addr pages[4]; +} __packed; + +struct be_cmd_resp_cq_create { + struct be_cmd_resp_hdr hdr; + u16 cq_id; + u16 rsvd0; +} __packed; + +/******************** Create MCCQ ***************************/ +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte - used to calculate offset/shift/mask of each field + */ +struct amap_mcc_context { + u8 con_index[14]; + u8 rsvd0[2]; + u8 ring_size[4]; + u8 fetch_wrb; + u8 fetch_r2t; + u8 cq_id[10]; + u8 prod_index[14]; + u8 fid[8]; + u8 pdid[9]; + u8 valid; + u8 rsvd1[32]; + u8 rsvd2[32]; +} __packed; + +struct be_cmd_req_mcc_create { + struct be_cmd_req_hdr hdr; + u16 num_pages; + u16 rsvd0; + u8 context[sizeof(struct amap_mcc_context) / 8]; + struct phys_addr pages[8]; +} __packed; + +struct be_cmd_resp_mcc_create { + struct be_cmd_resp_hdr hdr; + u16 id; + u16 rsvd0; +} __packed; + +/******************** Q Destroy ***************************/ +/* Type of Queue to be destroyed */ +enum { + QTYPE_EQ = 1, + QTYPE_CQ, + QTYPE_MCCQ, + QTYPE_WRBQ, + QTYPE_DPDUQ, + QTYPE_SGL +}; + +struct be_cmd_req_q_destroy { + struct be_cmd_req_hdr hdr; + u16 id; + u16 bypass_flush; /* valid only for rx q destroy */ +} __packed; + +struct macaddr { + u8 byte[ETH_ALEN]; +}; + +struct be_cmd_req_mcast_mac_config { + struct be_cmd_req_hdr hdr; + u16 num_mac; + u8 promiscuous; + u8 interface_id; + struct macaddr mac[32]; +} __packed; + +static inline void *embedded_payload(struct be_mcc_wrb *wrb) +{ + return wrb->payload.embedded_payload; +} + +static inline struct be_sge *nonembedded_sgl(struct be_mcc_wrb *wrb) +{ + return &wrb->payload.sgl[0]; +} + +/******************** Modify EQ Delay *******************/ +struct be_cmd_req_modify_eq_delay { + struct be_cmd_req_hdr hdr; + u32 num_eq; + struct { + u32 eq_id; + u32 phase; + u32 delay_multiplier; + } delay[8]; +} __packed; + +/******************** Get MAC ADDR *******************/ + +#define ETH_ALEN 6 + + +struct be_cmd_req_get_mac_addr { + struct be_cmd_req_hdr hdr; + u32 nic_port_count; + u32 speed; + u32 max_speed; + u32 link_state; + u32 max_frame_size; + u16 size_of_structure; + u8 mac_address[ETH_ALEN]; + u32 rsvd[23]; +}; + +struct be_cmd_resp_get_mac_addr { + struct be_cmd_resp_hdr hdr; + u32 nic_port_count; + u32 speed; + u32 max_speed; + u32 link_state; + u32 max_frame_size; + u16 size_of_structure; + u8 mac_address[6]; + u32 rsvd[23]; +}; + +int beiscsi_cmd_eq_create(struct be_ctrl_info *ctrl, + struct be_queue_info *eq, int eq_delay); + +int beiscsi_cmd_cq_create(struct be_ctrl_info *ctrl, + struct be_queue_info *cq, struct be_queue_info *eq, + bool sol_evts, bool no_delay, + int num_cqe_dma_coalesce); + +int beiscsi_cmd_q_destroy(struct be_ctrl_info *ctrl, struct be_queue_info *q, + int type); +int be_poll_mcc(struct be_ctrl_info *ctrl); +unsigned char mgmt_check_supported_fw(struct be_ctrl_info *ctrl); +int be_cmd_get_mac_addr(struct be_ctrl_info *ctrl, u8 *mac_addr); + +/*ISCSI Functuions */ +int be_cmd_fw_initialize(struct be_ctrl_info *ctrl); + +struct be_mcc_wrb *wrb_from_mbox(struct be_dma_mem *mbox_mem); + +int be_mbox_notify(struct be_ctrl_info *ctrl); + +int be_cmd_create_default_pdu_queue(struct be_ctrl_info *ctrl, + struct be_queue_info *cq, + struct be_queue_info *dq, int length, + int entry_size); + +int be_cmd_iscsi_post_sgl_pages(struct be_ctrl_info *ctrl, + struct be_dma_mem *q_mem, u32 page_offset, + u32 num_pages); + +int be_cmd_wrbq_create(struct be_ctrl_info *ctrl, struct be_dma_mem *q_mem, + struct be_queue_info *wrbq); + +struct be_default_pdu_context { + u32 dw[4]; +} __packed; + +struct amap_be_default_pdu_context { + u8 dbuf_cindex[13]; /* dword 0 */ + u8 rsvd0[3]; /* dword 0 */ + u8 ring_size[4]; /* dword 0 */ + u8 ring_state[4]; /* dword 0 */ + u8 rsvd1[8]; /* dword 0 */ + u8 dbuf_pindex[13]; /* dword 1 */ + u8 rsvd2; /* dword 1 */ + u8 pci_func_id[8]; /* dword 1 */ + u8 rx_pdid[9]; /* dword 1 */ + u8 rx_pdid_valid; /* dword 1 */ + u8 default_buffer_size[16]; /* dword 2 */ + u8 cq_id_recv[10]; /* dword 2 */ + u8 rx_pdid_not_valid; /* dword 2 */ + u8 rsvd3[5]; /* dword 2 */ + u8 rsvd4[32]; /* dword 3 */ +} __packed; + +struct be_defq_create_req { + struct be_cmd_req_hdr hdr; + u16 num_pages; + u8 ulp_num; + u8 rsvd0; + struct be_default_pdu_context context; + struct phys_addr pages[8]; +} __packed; + +struct be_defq_create_resp { + struct be_cmd_req_hdr hdr; + u16 id; + u16 rsvd0; +} __packed; + +struct be_post_sgl_pages_req { + struct be_cmd_req_hdr hdr; + u16 num_pages; + u16 page_offset; + u32 rsvd0; + struct phys_addr pages[26]; + u32 rsvd1; +} __packed; + +struct be_wrbq_create_req { + struct be_cmd_req_hdr hdr; + u16 num_pages; + u8 ulp_num; + u8 rsvd0; + struct phys_addr pages[8]; +} __packed; + +struct be_wrbq_create_resp { + struct be_cmd_resp_hdr resp_hdr; + u16 cid; + u16 rsvd0; +} __packed; + +#define SOL_CID_MASK 0x0000FFC0 +#define SOL_CODE_MASK 0x0000003F +#define SOL_WRB_INDEX_MASK 0x00FF0000 +#define SOL_CMD_WND_MASK 0xFF000000 +#define SOL_RES_CNT_MASK 0x7FFFFFFF +#define SOL_EXP_CMD_SN_MASK 0xFFFFFFFF +#define SOL_HW_STS_MASK 0x000000FF +#define SOL_STS_MASK 0x0000FF00 +#define SOL_RESP_MASK 0x00FF0000 +#define SOL_FLAGS_MASK 0x7F000000 +#define SOL_S_MASK 0x80000000 + +struct sol_cqe { + u32 dw[4]; +}; + +struct amap_sol_cqe { + u8 hw_sts[8]; /* dword 0 */ + u8 i_sts[8]; /* dword 0 */ + u8 i_resp[8]; /* dword 0 */ + u8 i_flags[7]; /* dword 0 */ + u8 s; /* dword 0 */ + u8 i_exp_cmd_sn[32]; /* dword 1 */ + u8 code[6]; /* dword 2 */ + u8 cid[10]; /* dword 2 */ + u8 wrb_index[8]; /* dword 2 */ + u8 i_cmd_wnd[8]; /* dword 2 */ + u8 i_res_cnt[31]; /* dword 3 */ + u8 valid; /* dword 3 */ +} __packed; + + +/** + * Post WRB Queue Doorbell Register used by the host Storage + * stack to notify the + * controller of a posted Work Request Block + */ +#define DB_WRB_POST_CID_MASK 0x3FF /* bits 0 - 9 */ +#define DB_DEF_PDU_WRB_INDEX_MASK 0xFF /* bits 0 - 9 */ + +#define DB_DEF_PDU_WRB_INDEX_SHIFT 16 +#define DB_DEF_PDU_NUM_POSTED_SHIFT 24 + +struct fragnum_bits_for_sgl_cra_in { + struct be_cmd_req_hdr hdr; + u32 num_bits; +} __packed; + +struct iscsi_cleanup_req { + struct be_cmd_req_hdr hdr; + u16 chute; + u8 hdr_ring_id; + u8 data_ring_id; + +} __packed; + +struct eq_delay { + u32 eq_id; + u32 phase; + u32 delay_multiplier; +} __packed; + +struct be_eq_delay_params_in { + struct be_cmd_req_hdr hdr; + u32 num_eq; + struct eq_delay delay[8]; +} __packed; + +struct ip_address_format { + u16 size_of_structure; + u8 reserved; + u8 ip_type; + u8 ip_address[16]; + u32 rsvd0; +} __packed; + +struct tcp_connect_and_offload_in { + struct be_cmd_req_hdr hdr; + struct ip_address_format ip_address; + u16 tcp_port; + u16 cid; + u16 cq_id; + u16 defq_id; + struct phys_addr dataout_template_pa; + u16 hdr_ring_id; + u16 data_ring_id; + u8 do_offload; + u8 rsvd0[3]; +} __packed; + +struct tcp_connect_and_offload_out { + struct be_cmd_resp_hdr hdr; + u32 connection_handle; + u16 cid; + u16 rsvd0; + +} __packed; + +struct be_mcc_wrb_context { + struct MCC_WRB *wrb; + int *users_final_status; +} __packed; + +#define DB_DEF_PDU_RING_ID_MASK 0x3FF /* bits 0 - 9 */ +#define DB_DEF_PDU_CQPROC_MASK 0x3FFF /* bits 0 - 9 */ +#define DB_DEF_PDU_REARM_SHIFT 14 +#define DB_DEF_PDU_EVENT_SHIFT 15 +#define DB_DEF_PDU_CQPROC_SHIFT 16 + +struct dmsg_cqe { + u32 dw[4]; +} __packed; + +struct tcp_upload_params_in { + struct be_cmd_req_hdr hdr; + u16 id; + u16 upload_type; + u32 reset_seq; +} __packed; + +struct tcp_upload_params_out { + u32 dw[32]; +} __packed; + +union tcp_upload_params { + struct tcp_upload_params_in request; + struct tcp_upload_params_out response; +} __packed; + +struct be_ulp_fw_cfg { + u32 ulp_mode; + u32 etx_base; + u32 etx_count; + u32 sq_base; + u32 sq_count; + u32 rq_base; + u32 rq_count; + u32 dq_base; + u32 dq_count; + u32 lro_base; + u32 lro_count; + u32 icd_base; + u32 icd_count; +}; + +struct be_fw_cfg { + struct be_cmd_req_hdr hdr; + u32 be_config_number; + u32 asic_revision; + u32 phys_port; + u32 function_mode; + struct be_ulp_fw_cfg ulp[2]; + u32 function_caps; +} __packed; + +#define CMD_ISCSI_COMMAND_INVALIDATE 1 +#define ISCSI_OPCODE_SCSI_DATA_OUT 5 +#define OPCODE_COMMON_ISCSI_TCP_CONNECT_AND_OFFLOAD 70 +#define OPCODE_ISCSI_INI_DRIVER_OFFLOAD_SESSION 41 +#define OPCODE_COMMON_MODIFY_EQ_DELAY 41 +#define OPCODE_COMMON_ISCSI_CLEANUP 59 +#define OPCODE_COMMON_TCP_UPLOAD 56 +#define OPCODE_COMMON_ISCSI_ERROR_RECOVERY_INVALIDATE_COMMANDS 1 +/* --- CMD_ISCSI_INVALIDATE_CONNECTION_TYPE --- */ +#define CMD_ISCSI_CONNECTION_INVALIDATE 1 +#define CMD_ISCSI_CONNECTION_ISSUE_TCP_RST 2 +#define OPCODE_ISCSI_INI_DRIVER_INVALIDATE_CONNECTION 42 + +#define INI_WR_CMD 1 /* Initiator write command */ +#define INI_TMF_CMD 2 /* Initiator TMF command */ +#define INI_NOPOUT_CMD 3 /* Initiator; Send a NOP-OUT */ +#define INI_RD_CMD 5 /* Initiator requesting to send + * a read command + */ +#define TGT_CTX_UPDT_CMD 7 /* Target context update */ +#define TGT_STS_CMD 8 /* Target R2T and other BHS + * where only the status number + * need to be updated + */ +#define TGT_DATAIN_CMD 9 /* Target Data-Ins in response + * to read command + */ +#define TGT_SOS_PDU 10 /* Target:standalone status + * response + */ +#define TGT_DM_CMD 11 /* Indicates that the bhs + * preparedby + * driver should not be touched + */ +/* --- CMD_CHUTE_TYPE --- */ +#define CMD_CONNECTION_CHUTE_0 1 +#define CMD_CONNECTION_CHUTE_1 2 +#define CMD_CONNECTION_CHUTE_2 3 + +#define EQ_MAJOR_CODE_COMPLETION 0 + +#define CMD_ISCSI_SESSION_DEL_CFG_FROM_FLASH 0 +#define CMD_ISCSI_SESSION_SAVE_CFG_ON_FLASH 1 + +/* --- CONNECTION_UPLOAD_PARAMS --- */ +/* These parameters are used to define the type of upload desired. */ +#define CONNECTION_UPLOAD_GRACEFUL 1 /* Graceful upload */ +#define CONNECTION_UPLOAD_ABORT_RESET 2 /* Abortive upload with + * reset + */ +#define CONNECTION_UPLOAD_ABORT 3 /* Abortive upload without + * reset + */ +#define CONNECTION_UPLOAD_ABORT_WITH_SEQ 4 /* Abortive upload with reset, + * sequence number by driver */ + +/* Returns byte size of given field with a structure. */ + +/* Returns the number of items in the field array. */ +#define BE_NUMBER_OF_FIELD(_type_, _field_) \ + (FIELD_SIZEOF(_type_, _field_)/sizeof((((_type_ *)0)->_field_[0])))\ + +/** + * Different types of iSCSI completions to host driver for both initiator + * and taget mode + * of operation. + */ +#define SOL_CMD_COMPLETE 1 /* Solicited command completed + * normally + */ +#define SOL_CMD_KILLED_DATA_DIGEST_ERR 2 /* Solicited command got + * invalidated internally due + * to Data Digest error + */ +#define CXN_KILLED_PDU_SIZE_EXCEEDS_DSL 3 /* Connection got invalidated + * internally + * due to a recieved PDU + * size > DSL + */ +#define CXN_KILLED_BURST_LEN_MISMATCH 4 /* Connection got invalidated + * internally due ti received + * PDU sequence size > + * FBL/MBL. + */ +#define CXN_KILLED_AHS_RCVD 5 /* Connection got invalidated + * internally due to a recieved + * PDU Hdr that has + * AHS */ +#define CXN_KILLED_HDR_DIGEST_ERR 6 /* Connection got invalidated + * internally due to Hdr Digest + * error + */ +#define CXN_KILLED_UNKNOWN_HDR 7 /* Connection got invalidated + * internally + * due to a bad opcode in the + * pdu hdr + */ +#define CXN_KILLED_STALE_ITT_TTT_RCVD 8 /* Connection got invalidated + * internally due to a recieved + * ITT/TTT that does not belong + * to this Connection + */ +#define CXN_KILLED_INVALID_ITT_TTT_RCVD 9 /* Connection got invalidated + * internally due to recieved + * ITT/TTT value > Max + * Supported ITTs/TTTs + */ +#define CXN_KILLED_RST_RCVD 10 /* Connection got invalidated + * internally due to an + * incoming TCP RST + */ +#define CXN_KILLED_TIMED_OUT 11 /* Connection got invalidated + * internally due to timeout on + * tcp segment 12 retransmit + * attempts failed + */ +#define CXN_KILLED_RST_SENT 12 /* Connection got invalidated + * internally due to TCP RST + * sent by the Tx side + */ +#define CXN_KILLED_FIN_RCVD 13 /* Connection got invalidated + * internally due to an + * incoming TCP FIN. + */ +#define CXN_KILLED_BAD_UNSOL_PDU_RCVD 14 /* Connection got invalidated + * internally due to bad + * unsolicited PDU Unsolicited + * PDUs are PDUs with + * ITT=0xffffffff + */ +#define CXN_KILLED_BAD_WRB_INDEX_ERROR 15 /* Connection got invalidated + * internally due to bad WRB + * index. + */ +#define CXN_KILLED_OVER_RUN_RESIDUAL 16 /* Command got invalidated + * internally due to recived + * command has residual + * over run bytes. + */ +#define CXN_KILLED_UNDER_RUN_RESIDUAL 17 /* Command got invalidated + * internally due to recived + * command has residual under + * run bytes. + */ +#define CMD_KILLED_INVALID_STATSN_RCVD 18 /* Command got invalidated + * internally due to a recieved + * PDU has an invalid StatusSN + */ +#define CMD_KILLED_INVALID_R2T_RCVD 19 /* Command got invalidated + * internally due to a recieved + * an R2T with some invalid + * fields in it + */ +#define CMD_CXN_KILLED_LUN_INVALID 20 /* Command got invalidated + * internally due to received + * PDU has an invalid LUN. + */ +#define CMD_CXN_KILLED_ICD_INVALID 21 /* Command got invalidated + * internally due to the + * corresponding ICD not in a + * valid state + */ +#define CMD_CXN_KILLED_ITT_INVALID 22 /* Command got invalidated due + * to received PDU has an + * invalid ITT. + */ +#define CMD_CXN_KILLED_SEQ_OUTOFORDER 23 /* Command got invalidated due + * to received sequence buffer + * offset is out of order. + */ +#define CMD_CXN_KILLED_INVALID_DATASN_RCVD 24 /* Command got invalidated + * internally due to a + * recieved PDU has an invalid + * DataSN + */ +#define CXN_INVALIDATE_NOTIFY 25 /* Connection invalidation + * completion notify. + */ +#define CXN_INVALIDATE_INDEX_NOTIFY 26 /* Connection invalidation + * completion + * with data PDU index. + */ +#define CMD_INVALIDATED_NOTIFY 27 /* Command invalidation + * completionnotifify. + */ +#define UNSOL_HDR_NOTIFY 28 /* Unsolicited header notify.*/ +#define UNSOL_DATA_NOTIFY 29 /* Unsolicited data notify.*/ +#define UNSOL_DATA_DIGEST_ERROR_NOTIFY 30 /* Unsolicited data digest + * error notify. + */ +#define DRIVERMSG_NOTIFY 31 /* TCP acknowledge based + * notification. + */ +#define CXN_KILLED_CMND_DATA_NOT_ON_SAME_CONN 32 /* Connection got invalidated + * internally due to command + * and data are not on same + * connection. + */ +#define SOL_CMD_KILLED_DIF_ERR 33 /* Solicited command got + * invalidated internally due + * to DIF error + */ +#define CXN_KILLED_SYN_RCVD 34 /* Connection got invalidated + * internally due to incoming + * TCP SYN + */ +#define CXN_KILLED_IMM_DATA_RCVD 35 /* Connection got invalidated + * internally due to an + * incoming Unsolicited PDU + * that has immediate data on + * the cxn + */ + +void be_wrb_hdr_prepare(struct be_mcc_wrb *wrb, int payload_len, + bool embedded, u8 sge_cnt); + +void be_cmd_hdr_prepare(struct be_cmd_req_hdr *req_hdr, + u8 subsystem, u8 opcode, int cmd_len); + +#endif /* !BEISCSI_CMDS_H */ diff --git a/drivers/scsi/be2iscsi/be_iscsi.c b/drivers/scsi/be2iscsi/be_iscsi.c new file mode 100644 index 000000000000..2fd25442cfaf --- /dev/null +++ b/drivers/scsi/be2iscsi/be_iscsi.c @@ -0,0 +1,638 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Written by: Jayamohan Kallickal (jayamohank@serverengines.com) + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + * + */ + +#include <scsi/libiscsi.h> +#include <scsi/scsi_transport_iscsi.h> +#include <scsi/scsi_transport.h> +#include <scsi/scsi_cmnd.h> +#include <scsi/scsi_device.h> +#include <scsi/scsi_host.h> +#include <scsi/scsi.h> + +#include "be_iscsi.h" + +extern struct iscsi_transport beiscsi_iscsi_transport; + +/** + * beiscsi_session_create - creates a new iscsi session + * @cmds_max: max commands supported + * @qdepth: max queue depth supported + * @initial_cmdsn: initial iscsi CMDSN + */ +struct iscsi_cls_session *beiscsi_session_create(struct iscsi_endpoint *ep, + u16 cmds_max, + u16 qdepth, + u32 initial_cmdsn) +{ + struct Scsi_Host *shost; + struct beiscsi_endpoint *beiscsi_ep; + struct iscsi_cls_session *cls_session; + struct beiscsi_hba *phba; + struct iscsi_session *sess; + struct beiscsi_session *beiscsi_sess; + struct beiscsi_io_task *io_task; + + SE_DEBUG(DBG_LVL_8, "In beiscsi_session_create\n"); + + if (!ep) { + SE_DEBUG(DBG_LVL_1, "beiscsi_session_create: invalid ep \n"); + return NULL; + } + beiscsi_ep = ep->dd_data; + phba = beiscsi_ep->phba; + shost = phba->shost; + if (cmds_max > beiscsi_ep->phba->params.wrbs_per_cxn) { + shost_printk(KERN_ERR, shost, "Cannot handle %d cmds." + "Max cmds per session supported is %d. Using %d. " + "\n", cmds_max, + beiscsi_ep->phba->params.wrbs_per_cxn, + beiscsi_ep->phba->params.wrbs_per_cxn); + cmds_max = beiscsi_ep->phba->params.wrbs_per_cxn; + } + + cls_session = iscsi_session_setup(&beiscsi_iscsi_transport, + shost, cmds_max, + sizeof(*beiscsi_sess), + sizeof(*io_task), + initial_cmdsn, ISCSI_MAX_TARGET); + if (!cls_session) + return NULL; + sess = cls_session->dd_data; + beiscsi_sess = sess->dd_data; + beiscsi_sess->bhs_pool = pci_pool_create("beiscsi_bhs_pool", + phba->pcidev, + sizeof(struct be_cmd_bhs), + 64, 0); + if (!beiscsi_sess->bhs_pool) + goto destroy_sess; + + return cls_session; +destroy_sess: + iscsi_session_teardown(cls_session); + return NULL; +} + +/** + * beiscsi_session_destroy - destroys iscsi session + * @cls_session: pointer to iscsi cls session + * + * Destroys iSCSI session instance and releases + * resources allocated for it. + */ +void beiscsi_session_destroy(struct iscsi_cls_session *cls_session) +{ + struct iscsi_session *sess = cls_session->dd_data; + struct beiscsi_session *beiscsi_sess = sess->dd_data; + + pci_pool_destroy(beiscsi_sess->bhs_pool); + iscsi_session_teardown(cls_session); +} + +/** + * beiscsi_conn_create - create an instance of iscsi connection + * @cls_session: ptr to iscsi_cls_session + * @cid: iscsi cid + */ +struct iscsi_cls_conn * +beiscsi_conn_create(struct iscsi_cls_session *cls_session, u32 cid) +{ + struct beiscsi_hba *phba; + struct Scsi_Host *shost; + struct iscsi_cls_conn *cls_conn; + struct beiscsi_conn *beiscsi_conn; + struct iscsi_conn *conn; + struct iscsi_session *sess; + struct beiscsi_session *beiscsi_sess; + + SE_DEBUG(DBG_LVL_8, "In beiscsi_conn_create ,cid" + "from iscsi layer=%d\n", cid); + shost = iscsi_session_to_shost(cls_session); + phba = iscsi_host_priv(shost); + + cls_conn = iscsi_conn_setup(cls_session, sizeof(*beiscsi_conn), cid); + if (!cls_conn) + return NULL; + + conn = cls_conn->dd_data; + beiscsi_conn = conn->dd_data; + beiscsi_conn->ep = NULL; + beiscsi_conn->phba = phba; + beiscsi_conn->conn = conn; + sess = cls_session->dd_data; + beiscsi_sess = sess->dd_data; + beiscsi_conn->beiscsi_sess = beiscsi_sess; + return cls_conn; +} + +/** + * beiscsi_bindconn_cid - Bind the beiscsi_conn with phba connection table + * @beiscsi_conn: The pointer to beiscsi_conn structure + * @phba: The phba instance + * @cid: The cid to free + */ +static int beiscsi_bindconn_cid(struct beiscsi_hba *phba, + struct beiscsi_conn *beiscsi_conn, + unsigned int cid) +{ + if (phba->conn_table[cid]) { + SE_DEBUG(DBG_LVL_1, + "Connection table already occupied. Detected clash\n"); + return -EINVAL; + } else { + SE_DEBUG(DBG_LVL_8, "phba->conn_table[%d]=%p(beiscsi_conn) \n", + cid, beiscsi_conn); + phba->conn_table[cid] = beiscsi_conn; + } + return 0; +} + +/** + * beiscsi_conn_bind - Binds iscsi session/connection with TCP connection + * @cls_session: pointer to iscsi cls session + * @cls_conn: pointer to iscsi cls conn + * @transport_fd: EP handle(64 bit) + * + * This function binds the TCP Conn with iSCSI Connection and Session. + */ +int beiscsi_conn_bind(struct iscsi_cls_session *cls_session, + struct iscsi_cls_conn *cls_conn, + u64 transport_fd, int is_leading) +{ + struct iscsi_conn *conn = cls_conn->dd_data; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct Scsi_Host *shost = + (struct Scsi_Host *)iscsi_session_to_shost(cls_session); + struct beiscsi_hba *phba = (struct beiscsi_hba *)iscsi_host_priv(shost); + struct beiscsi_endpoint *beiscsi_ep; + struct iscsi_endpoint *ep; + + SE_DEBUG(DBG_LVL_8, "In beiscsi_conn_bind\n"); + ep = iscsi_lookup_endpoint(transport_fd); + if (!ep) + return -EINVAL; + + beiscsi_ep = ep->dd_data; + + if (iscsi_conn_bind(cls_session, cls_conn, is_leading)) + return -EINVAL; + + if (beiscsi_ep->phba != phba) { + SE_DEBUG(DBG_LVL_8, + "beiscsi_ep->hba=%p not equal to phba=%p \n", + beiscsi_ep->phba, phba); + return -EEXIST; + } + + beiscsi_conn->beiscsi_conn_cid = beiscsi_ep->ep_cid; + beiscsi_conn->ep = beiscsi_ep; + beiscsi_ep->conn = beiscsi_conn; + SE_DEBUG(DBG_LVL_8, "beiscsi_conn=%p conn=%p ep_cid=%d \n", + beiscsi_conn, conn, beiscsi_ep->ep_cid); + return beiscsi_bindconn_cid(phba, beiscsi_conn, beiscsi_ep->ep_cid); +} + +/** + * beiscsi_conn_get_param - get the iscsi parameter + * @cls_conn: pointer to iscsi cls conn + * @param: parameter type identifier + * @buf: buffer pointer + * + * returns iscsi parameter + */ +int beiscsi_conn_get_param(struct iscsi_cls_conn *cls_conn, + enum iscsi_param param, char *buf) +{ + struct beiscsi_endpoint *beiscsi_ep; + struct iscsi_conn *conn = cls_conn->dd_data; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + int len = 0; + + beiscsi_ep = beiscsi_conn->ep; + if (!beiscsi_ep) { + SE_DEBUG(DBG_LVL_1, + "In beiscsi_conn_get_param , no beiscsi_ep\n"); + return -1; + } + + switch (param) { + case ISCSI_PARAM_CONN_PORT: + len = sprintf(buf, "%hu\n", beiscsi_ep->dst_tcpport); + break; + case ISCSI_PARAM_CONN_ADDRESS: + if (beiscsi_ep->ip_type == BE2_IPV4) + len = sprintf(buf, "%pI4\n", &beiscsi_ep->dst_addr); + else + len = sprintf(buf, "%pI6\n", &beiscsi_ep->dst6_addr); + break; + default: + return iscsi_conn_get_param(cls_conn, param, buf); + } + return len; +} + +int beiscsi_set_param(struct iscsi_cls_conn *cls_conn, + enum iscsi_param param, char *buf, int buflen) +{ + struct iscsi_conn *conn = cls_conn->dd_data; + struct iscsi_session *session = conn->session; + int ret; + + ret = iscsi_set_param(cls_conn, param, buf, buflen); + if (ret) + return ret; + /* + * If userspace tried to set the value to higher than we can + * support override here. + */ + switch (param) { + case ISCSI_PARAM_FIRST_BURST: + if (session->first_burst > 8192) + session->first_burst = 8192; + break; + case ISCSI_PARAM_MAX_RECV_DLENGTH: + if (conn->max_recv_dlength > 65536) + conn->max_recv_dlength = 65536; + break; + case ISCSI_PARAM_MAX_BURST: + if (session->first_burst > 262144) + session->first_burst = 262144; + break; + default: + return 0; + } + + return 0; +} + +/** + * beiscsi_get_host_param - get the iscsi parameter + * @shost: pointer to scsi_host structure + * @param: parameter type identifier + * @buf: buffer pointer + * + * returns host parameter + */ +int beiscsi_get_host_param(struct Scsi_Host *shost, + enum iscsi_host_param param, char *buf) +{ + struct beiscsi_hba *phba = (struct beiscsi_hba *)iscsi_host_priv(shost); + int len = 0; + + switch (param) { + case ISCSI_HOST_PARAM_HWADDRESS: + be_cmd_get_mac_addr(&phba->ctrl, phba->mac_address); + len = sysfs_format_mac(buf, phba->mac_address, ETH_ALEN); + break; + default: + return iscsi_host_get_param(shost, param, buf); + } + return len; +} + +/** + * beiscsi_conn_get_stats - get the iscsi stats + * @cls_conn: pointer to iscsi cls conn + * @stats: pointer to iscsi_stats structure + * + * returns iscsi stats + */ +void beiscsi_conn_get_stats(struct iscsi_cls_conn *cls_conn, + struct iscsi_stats *stats) +{ + struct iscsi_conn *conn = cls_conn->dd_data; + + SE_DEBUG(DBG_LVL_8, "In beiscsi_conn_get_stats\n"); + stats->txdata_octets = conn->txdata_octets; + stats->rxdata_octets = conn->rxdata_octets; + stats->dataout_pdus = conn->dataout_pdus_cnt; + stats->scsirsp_pdus = conn->scsirsp_pdus_cnt; + stats->scsicmd_pdus = conn->scsicmd_pdus_cnt; + stats->datain_pdus = conn->datain_pdus_cnt; + stats->tmfrsp_pdus = conn->tmfrsp_pdus_cnt; + stats->tmfcmd_pdus = conn->tmfcmd_pdus_cnt; + stats->r2t_pdus = conn->r2t_pdus_cnt; + stats->digest_err = 0; + stats->timeout_err = 0; + stats->custom_length = 0; + strcpy(stats->custom[0].desc, "eh_abort_cnt"); + stats->custom[0].value = conn->eh_abort_cnt; +} + +/** + * beiscsi_set_params_for_offld - get the parameters for offload + * @beiscsi_conn: pointer to beiscsi_conn + * @params: pointer to offload_params structure + */ +static void beiscsi_set_params_for_offld(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_offload_params *params) +{ + struct iscsi_conn *conn = beiscsi_conn->conn; + struct iscsi_session *session = conn->session; + + AMAP_SET_BITS(struct amap_beiscsi_offload_params, max_burst_length, + params, session->max_burst); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, + max_send_data_segment_length, params, + conn->max_xmit_dlength); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, first_burst_length, + params, session->first_burst); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, erl, params, + session->erl); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, dde, params, + conn->datadgst_en); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, hde, params, + conn->hdrdgst_en); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, ir2t, params, + session->initial_r2t_en); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, imd, params, + session->imm_data_en); + AMAP_SET_BITS(struct amap_beiscsi_offload_params, exp_statsn, params, + (conn->exp_statsn - 1)); +} + +/** + * beiscsi_conn_start - offload of session to chip + * @cls_conn: pointer to beiscsi_conn + */ +int beiscsi_conn_start(struct iscsi_cls_conn *cls_conn) +{ + struct iscsi_conn *conn = cls_conn->dd_data; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct beiscsi_endpoint *beiscsi_ep; + struct beiscsi_offload_params params; + struct iscsi_session *session = conn->session; + struct Scsi_Host *shost = iscsi_session_to_shost(session->cls_session); + struct beiscsi_hba *phba = iscsi_host_priv(shost); + + memset(¶ms, 0, sizeof(struct beiscsi_offload_params)); + beiscsi_ep = beiscsi_conn->ep; + if (!beiscsi_ep) + SE_DEBUG(DBG_LVL_1, "In beiscsi_conn_start , no beiscsi_ep\n"); + + free_mgmt_sgl_handle(phba, beiscsi_conn->plogin_sgl_handle); + beiscsi_conn->login_in_progress = 0; + beiscsi_set_params_for_offld(beiscsi_conn, ¶ms); + beiscsi_offload_connection(beiscsi_conn, ¶ms); + iscsi_conn_start(cls_conn); + return 0; +} + +/** + * beiscsi_get_cid - Allocate a cid + * @phba: The phba instance + */ +static int beiscsi_get_cid(struct beiscsi_hba *phba) +{ + unsigned short cid = 0xFFFF; + + if (!phba->avlbl_cids) + return cid; + + cid = phba->cid_array[phba->cid_alloc++]; + if (phba->cid_alloc == phba->params.cxns_per_ctrl) + phba->cid_alloc = 0; + phba->avlbl_cids--; + return cid; +} + +/** + * beiscsi_open_conn - Ask FW to open a TCP connection + * @ep: endpoint to be used + * @src_addr: The source IP address + * @dst_addr: The Destination IP address + * + * Asks the FW to open a TCP connection + */ +static int beiscsi_open_conn(struct iscsi_endpoint *ep, + struct sockaddr *src_addr, + struct sockaddr *dst_addr, int non_blocking) +{ + struct beiscsi_endpoint *beiscsi_ep = ep->dd_data; + struct beiscsi_hba *phba = beiscsi_ep->phba; + int ret = -1; + + beiscsi_ep->ep_cid = beiscsi_get_cid(phba); + if (beiscsi_ep->ep_cid == 0xFFFF) { + SE_DEBUG(DBG_LVL_1, "No free cid available\n"); + return ret; + } + SE_DEBUG(DBG_LVL_8, "In beiscsi_open_conn, ep_cid=%d ", + beiscsi_ep->ep_cid); + phba->ep_array[beiscsi_ep->ep_cid] = ep; + if (beiscsi_ep->ep_cid > + (phba->fw_config.iscsi_cid_start + phba->params.cxns_per_ctrl)) { + SE_DEBUG(DBG_LVL_1, "Failed in allocate iscsi cid\n"); + return ret; + } + + beiscsi_ep->cid_vld = 0; + return mgmt_open_connection(phba, dst_addr, beiscsi_ep); +} + +/** + * beiscsi_put_cid - Free the cid + * @phba: The phba for which the cid is being freed + * @cid: The cid to free + */ +static void beiscsi_put_cid(struct beiscsi_hba *phba, unsigned short cid) +{ + phba->avlbl_cids++; + phba->cid_array[phba->cid_free++] = cid; + if (phba->cid_free == phba->params.cxns_per_ctrl) + phba->cid_free = 0; +} + +/** + * beiscsi_free_ep - free endpoint + * @ep: pointer to iscsi endpoint structure + */ +static void beiscsi_free_ep(struct iscsi_endpoint *ep) +{ + struct beiscsi_endpoint *beiscsi_ep = ep->dd_data; + struct beiscsi_hba *phba = beiscsi_ep->phba; + + beiscsi_put_cid(phba, beiscsi_ep->ep_cid); + beiscsi_ep->phba = NULL; + iscsi_destroy_endpoint(ep); +} + +/** + * beiscsi_ep_connect - Ask chip to create TCP Conn + * @scsi_host: Pointer to scsi_host structure + * @dst_addr: The IP address of Target + * @non_blocking: blocking or non-blocking call + * + * This routines first asks chip to create a connection and then allocates an EP + */ +struct iscsi_endpoint * +beiscsi_ep_connect(struct Scsi_Host *shost, struct sockaddr *dst_addr, + int non_blocking) +{ + struct beiscsi_hba *phba; + struct beiscsi_endpoint *beiscsi_ep; + struct iscsi_endpoint *ep; + int ret; + + SE_DEBUG(DBG_LVL_8, "In beiscsi_ep_connect \n"); + if (shost) + phba = iscsi_host_priv(shost); + else { + ret = -ENXIO; + SE_DEBUG(DBG_LVL_1, "shost is NULL \n"); + return ERR_PTR(ret); + } + ep = iscsi_create_endpoint(sizeof(struct beiscsi_endpoint)); + if (!ep) { + ret = -ENOMEM; + return ERR_PTR(ret); + } + + beiscsi_ep = ep->dd_data; + beiscsi_ep->phba = phba; + + if (beiscsi_open_conn(ep, NULL, dst_addr, non_blocking)) { + SE_DEBUG(DBG_LVL_1, "Failed in allocate iscsi cid\n"); + ret = -ENOMEM; + goto free_ep; + } + + return ep; + +free_ep: + beiscsi_free_ep(ep); + return ERR_PTR(ret); +} + +/** + * beiscsi_ep_poll - Poll to see if connection is established + * @ep: endpoint to be used + * @timeout_ms: timeout specified in millisecs + * + * Poll to see if TCP connection established + */ +int beiscsi_ep_poll(struct iscsi_endpoint *ep, int timeout_ms) +{ + struct beiscsi_endpoint *beiscsi_ep = ep->dd_data; + + SE_DEBUG(DBG_LVL_8, "In beiscsi_ep_poll\n"); + if (beiscsi_ep->cid_vld == 1) + return 1; + else + return 0; +} + +/** + * beiscsi_close_conn - Upload the connection + * @ep: The iscsi endpoint + * @flag: The type of connection closure + */ +static int beiscsi_close_conn(struct iscsi_endpoint *ep, int flag) +{ + int ret = 0; + struct beiscsi_endpoint *beiscsi_ep = ep->dd_data; + struct beiscsi_hba *phba = beiscsi_ep->phba; + + if (MGMT_STATUS_SUCCESS != + mgmt_upload_connection(phba, beiscsi_ep->ep_cid, + CONNECTION_UPLOAD_GRACEFUL)) { + SE_DEBUG(DBG_LVL_8, "upload failed for cid 0x%x", + beiscsi_ep->ep_cid); + ret = -1; + } + + return ret; +} + +/** + * beiscsi_ep_disconnect - Tears down the TCP connection + * @ep: endpoint to be used + * + * Tears down the TCP connection + */ +void beiscsi_ep_disconnect(struct iscsi_endpoint *ep) +{ + struct beiscsi_conn *beiscsi_conn; + struct beiscsi_endpoint *beiscsi_ep; + struct beiscsi_hba *phba; + int flag = 0; + + beiscsi_ep = ep->dd_data; + phba = beiscsi_ep->phba; + SE_DEBUG(DBG_LVL_8, "In beiscsi_ep_disconnect\n"); + + if (beiscsi_ep->conn) { + beiscsi_conn = beiscsi_ep->conn; + iscsi_suspend_queue(beiscsi_conn->conn); + beiscsi_close_conn(ep, flag); + } + + beiscsi_free_ep(ep); +} + +/** + * beiscsi_unbind_conn_to_cid - Unbind the beiscsi_conn from phba conn table + * @phba: The phba instance + * @cid: The cid to free + */ +static int beiscsi_unbind_conn_to_cid(struct beiscsi_hba *phba, + unsigned int cid) +{ + if (phba->conn_table[cid]) + phba->conn_table[cid] = NULL; + else { + SE_DEBUG(DBG_LVL_8, "Connection table Not occupied. \n"); + return -EINVAL; + } + return 0; +} + +/** + * beiscsi_conn_stop - Invalidate and stop the connection + * @cls_conn: pointer to get iscsi_conn + * @flag: The type of connection closure + */ +void beiscsi_conn_stop(struct iscsi_cls_conn *cls_conn, int flag) +{ + struct iscsi_conn *conn = cls_conn->dd_data; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct beiscsi_endpoint *beiscsi_ep; + struct iscsi_session *session = conn->session; + struct Scsi_Host *shost = iscsi_session_to_shost(session->cls_session); + struct beiscsi_hba *phba = iscsi_host_priv(shost); + unsigned int status; + unsigned short savecfg_flag = CMD_ISCSI_SESSION_SAVE_CFG_ON_FLASH; + + SE_DEBUG(DBG_LVL_8, "In beiscsi_conn_stop\n"); + beiscsi_ep = beiscsi_conn->ep; + if (!beiscsi_ep) { + SE_DEBUG(DBG_LVL_8, "In beiscsi_conn_stop , no beiscsi_ep\n"); + return; + } + status = mgmt_invalidate_connection(phba, beiscsi_ep, + beiscsi_ep->ep_cid, 1, + savecfg_flag); + if (status != MGMT_STATUS_SUCCESS) { + SE_DEBUG(DBG_LVL_1, + "mgmt_invalidate_connection Failed for cid=%d \n", + beiscsi_ep->ep_cid); + } + beiscsi_unbind_conn_to_cid(phba, beiscsi_ep->ep_cid); + iscsi_conn_stop(cls_conn, flag); +} diff --git a/drivers/scsi/be2iscsi/be_iscsi.h b/drivers/scsi/be2iscsi/be_iscsi.h new file mode 100644 index 000000000000..f92ffc5349fb --- /dev/null +++ b/drivers/scsi/be2iscsi/be_iscsi.h @@ -0,0 +1,75 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Written by: Jayamohan Kallickal (jayamohank@serverengines.com) + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + * + */ + +#ifndef _BE_ISCSI_ +#define _BE_ISCSI_ + +#include "be_main.h" +#include "be_mgmt.h" + +#define BE2_IPV4 0x1 +#define BE2_IPV6 0x10 + +void beiscsi_offload_connection(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_offload_params *params); + +void beiscsi_offload_iscsi(struct beiscsi_hba *phba, struct iscsi_conn *conn, + struct beiscsi_conn *beiscsi_conn, + unsigned int fw_handle); + +struct iscsi_cls_session *beiscsi_session_create(struct iscsi_endpoint *ep, + uint16_t cmds_max, + uint16_t qdepth, + uint32_t initial_cmdsn); + +void beiscsi_session_destroy(struct iscsi_cls_session *cls_session); + +struct iscsi_cls_conn *beiscsi_conn_create(struct iscsi_cls_session + *cls_session, uint32_t cid); + +int beiscsi_conn_bind(struct iscsi_cls_session *cls_session, + struct iscsi_cls_conn *cls_conn, + uint64_t transport_fd, int is_leading); + +int beiscsi_conn_get_param(struct iscsi_cls_conn *cls_conn, + enum iscsi_param param, char *buf); + +int beiscsi_get_host_param(struct Scsi_Host *shost, + enum iscsi_host_param param, char *buf); + +int beiscsi_set_param(struct iscsi_cls_conn *cls_conn, + enum iscsi_param param, char *buf, int buflen); + +int beiscsi_conn_start(struct iscsi_cls_conn *cls_conn); + +void beiscsi_conn_stop(struct iscsi_cls_conn *cls_conn, int flag); + +struct iscsi_endpoint *beiscsi_ep_connect(struct Scsi_Host *shost, + struct sockaddr *dst_addr, + int non_blocking); + +int beiscsi_ep_poll(struct iscsi_endpoint *ep, int timeout_ms); + +void beiscsi_ep_disconnect(struct iscsi_endpoint *ep); + +void beiscsi_conn_get_stats(struct iscsi_cls_conn *cls_conn, + struct iscsi_stats *stats); + +#endif diff --git a/drivers/scsi/be2iscsi/be_main.c b/drivers/scsi/be2iscsi/be_main.c new file mode 100644 index 000000000000..4f1aca346e38 --- /dev/null +++ b/drivers/scsi/be2iscsi/be_main.c @@ -0,0 +1,3390 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Written by: Jayamohan Kallickal (jayamohank@serverengines.com) + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + * + */ +#include <linux/reboot.h> +#include <linux/delay.h> +#include <linux/interrupt.h> +#include <linux/blkdev.h> +#include <linux/pci.h> +#include <linux/string.h> +#include <linux/kernel.h> +#include <linux/semaphore.h> + +#include <scsi/libiscsi.h> +#include <scsi/scsi_transport_iscsi.h> +#include <scsi/scsi_transport.h> +#include <scsi/scsi_cmnd.h> +#include <scsi/scsi_device.h> +#include <scsi/scsi_host.h> +#include <scsi/scsi.h> +#include "be_main.h" +#include "be_iscsi.h" +#include "be_mgmt.h" + +static unsigned int be_iopoll_budget = 10; +static unsigned int be_max_phys_size = 64; +static unsigned int enable_msix; + +MODULE_DEVICE_TABLE(pci, beiscsi_pci_id_table); +MODULE_DESCRIPTION(DRV_DESC " " BUILD_STR); +MODULE_AUTHOR("ServerEngines Corporation"); +MODULE_LICENSE("GPL"); +module_param(be_iopoll_budget, int, 0); +module_param(enable_msix, int, 0); +module_param(be_max_phys_size, uint, S_IRUGO); +MODULE_PARM_DESC(be_max_phys_size, "Maximum Size (In Kilobytes) of physically" + "contiguous memory that can be allocated." + "Range is 16 - 128"); + +static int beiscsi_slave_configure(struct scsi_device *sdev) +{ + blk_queue_max_segment_size(sdev->request_queue, 65536); + return 0; +} + +static struct scsi_host_template beiscsi_sht = { + .module = THIS_MODULE, + .name = "ServerEngines 10Gbe open-iscsi Initiator Driver", + .proc_name = DRV_NAME, + .queuecommand = iscsi_queuecommand, + .eh_abort_handler = iscsi_eh_abort, + .change_queue_depth = iscsi_change_queue_depth, + .slave_configure = beiscsi_slave_configure, + .target_alloc = iscsi_target_alloc, + .eh_device_reset_handler = iscsi_eh_device_reset, + .eh_target_reset_handler = iscsi_eh_target_reset, + .sg_tablesize = BEISCSI_SGLIST_ELEMENTS, + .can_queue = BE2_IO_DEPTH, + .this_id = -1, + .max_sectors = BEISCSI_MAX_SECTORS, + .cmd_per_lun = BEISCSI_CMD_PER_LUN, + .use_clustering = ENABLE_CLUSTERING, +}; +static struct scsi_transport_template *beiscsi_scsi_transport; + +/*------------------- PCI Driver operations and data ----------------- */ +static DEFINE_PCI_DEVICE_TABLE(beiscsi_pci_id_table) = { + { PCI_DEVICE(BE_VENDOR_ID, BE_DEVICE_ID1) }, + { PCI_DEVICE(BE_VENDOR_ID, OC_DEVICE_ID1) }, + { PCI_DEVICE(BE_VENDOR_ID, OC_DEVICE_ID2) }, + { 0 } +}; +MODULE_DEVICE_TABLE(pci, beiscsi_pci_id_table); + +static struct beiscsi_hba *beiscsi_hba_alloc(struct pci_dev *pcidev) +{ + struct beiscsi_hba *phba; + struct Scsi_Host *shost; + + shost = iscsi_host_alloc(&beiscsi_sht, sizeof(*phba), 0); + if (!shost) { + dev_err(&pcidev->dev, "beiscsi_hba_alloc -" + "iscsi_host_alloc failed \n"); + return NULL; + } + shost->dma_boundary = pcidev->dma_mask; + shost->max_id = BE2_MAX_SESSIONS; + shost->max_channel = 0; + shost->max_cmd_len = BEISCSI_MAX_CMD_LEN; + shost->max_lun = BEISCSI_NUM_MAX_LUN; + shost->transportt = beiscsi_scsi_transport; + + phba = iscsi_host_priv(shost); + memset(phba, 0, sizeof(*phba)); + phba->shost = shost; + phba->pcidev = pci_dev_get(pcidev); + + if (iscsi_host_add(shost, &phba->pcidev->dev)) + goto free_devices; + return phba; + +free_devices: + pci_dev_put(phba->pcidev); + iscsi_host_free(phba->shost); + return NULL; +} + +static void beiscsi_unmap_pci_function(struct beiscsi_hba *phba) +{ + if (phba->csr_va) { + iounmap(phba->csr_va); + phba->csr_va = NULL; + } + if (phba->db_va) { + iounmap(phba->db_va); + phba->db_va = NULL; + } + if (phba->pci_va) { + iounmap(phba->pci_va); + phba->pci_va = NULL; + } +} + +static int beiscsi_map_pci_bars(struct beiscsi_hba *phba, + struct pci_dev *pcidev) +{ + u8 __iomem *addr; + + addr = ioremap_nocache(pci_resource_start(pcidev, 2), + pci_resource_len(pcidev, 2)); + if (addr == NULL) + return -ENOMEM; + phba->ctrl.csr = addr; + phba->csr_va = addr; + phba->csr_pa.u.a64.address = pci_resource_start(pcidev, 2); + + addr = ioremap_nocache(pci_resource_start(pcidev, 4), 128 * 1024); + if (addr == NULL) + goto pci_map_err; + phba->ctrl.db = addr; + phba->db_va = addr; + phba->db_pa.u.a64.address = pci_resource_start(pcidev, 4); + + addr = ioremap_nocache(pci_resource_start(pcidev, 1), + pci_resource_len(pcidev, 1)); + if (addr == NULL) + goto pci_map_err; + phba->ctrl.pcicfg = addr; + phba->pci_va = addr; + phba->pci_pa.u.a64.address = pci_resource_start(pcidev, 1); + return 0; + +pci_map_err: + beiscsi_unmap_pci_function(phba); + return -ENOMEM; +} + +static int beiscsi_enable_pci(struct pci_dev *pcidev) +{ + int ret; + + ret = pci_enable_device(pcidev); + if (ret) { + dev_err(&pcidev->dev, "beiscsi_enable_pci - enable device " + "failed. Returning -ENODEV\n"); + return ret; + } + + if (pci_set_consistent_dma_mask(pcidev, DMA_BIT_MASK(64))) { + ret = pci_set_consistent_dma_mask(pcidev, DMA_BIT_MASK(32)); + if (ret) { + dev_err(&pcidev->dev, "Could not set PCI DMA Mask\n"); + pci_disable_device(pcidev); + return ret; + } + } + return 0; +} + +static int be_ctrl_init(struct beiscsi_hba *phba, struct pci_dev *pdev) +{ + struct be_ctrl_info *ctrl = &phba->ctrl; + struct be_dma_mem *mbox_mem_alloc = &ctrl->mbox_mem_alloced; + struct be_dma_mem *mbox_mem_align = &ctrl->mbox_mem; + int status = 0; + + ctrl->pdev = pdev; + status = beiscsi_map_pci_bars(phba, pdev); + if (status) + return status; + + mbox_mem_alloc->size = sizeof(struct be_mcc_mailbox) + 16; + mbox_mem_alloc->va = pci_alloc_consistent(pdev, + mbox_mem_alloc->size, + &mbox_mem_alloc->dma); + if (!mbox_mem_alloc->va) { + beiscsi_unmap_pci_function(phba); + status = -ENOMEM; + return status; + } + + mbox_mem_align->size = sizeof(struct be_mcc_mailbox); + mbox_mem_align->va = PTR_ALIGN(mbox_mem_alloc->va, 16); + mbox_mem_align->dma = PTR_ALIGN(mbox_mem_alloc->dma, 16); + memset(mbox_mem_align->va, 0, sizeof(struct be_mcc_mailbox)); + spin_lock_init(&ctrl->mbox_lock); + return status; +} + +static void beiscsi_get_params(struct beiscsi_hba *phba) +{ + phba->params.ios_per_ctrl = BE2_IO_DEPTH; + phba->params.cxns_per_ctrl = BE2_MAX_SESSIONS; + phba->params.asyncpdus_per_ctrl = BE2_ASYNCPDUS; + phba->params.icds_per_ctrl = BE2_MAX_ICDS / 2; + phba->params.num_sge_per_io = BE2_SGE; + phba->params.defpdu_hdr_sz = BE2_DEFPDU_HDR_SZ; + phba->params.defpdu_data_sz = BE2_DEFPDU_DATA_SZ; + phba->params.eq_timer = 64; + phba->params.num_eq_entries = + (((BE2_CMDS_PER_CXN * 2 + BE2_LOGOUTS + BE2_TMFS + BE2_ASYNCPDUS) / + 512) + 1) * 512; + phba->params.num_eq_entries = (phba->params.num_eq_entries < 1024) + ? 1024 : phba->params.num_eq_entries; + SE_DEBUG(DBG_LVL_8, "phba->params.num_eq_entries=%d \n", + phba->params.num_eq_entries); + phba->params.num_cq_entries = + (((BE2_CMDS_PER_CXN * 2 + BE2_LOGOUTS + BE2_TMFS + BE2_ASYNCPDUS) / + 512) + 1) * 512; + SE_DEBUG(DBG_LVL_8, + "phba->params.num_cq_entries=%d BE2_CMDS_PER_CXN=%d" + "BE2_LOGOUTS=%d BE2_TMFS=%d BE2_ASYNCPDUS=%d \n", + phba->params.num_cq_entries, BE2_CMDS_PER_CXN, + BE2_LOGOUTS, BE2_TMFS, BE2_ASYNCPDUS); + phba->params.wrbs_per_cxn = 256; +} + +static void hwi_ring_eq_db(struct beiscsi_hba *phba, + unsigned int id, unsigned int clr_interrupt, + unsigned int num_processed, + unsigned char rearm, unsigned char event) +{ + u32 val = 0; + val |= id & DB_EQ_RING_ID_MASK; + if (rearm) + val |= 1 << DB_EQ_REARM_SHIFT; + if (clr_interrupt) + val |= 1 << DB_EQ_CLR_SHIFT; + if (event) + val |= 1 << DB_EQ_EVNT_SHIFT; + val |= num_processed << DB_EQ_NUM_POPPED_SHIFT; + iowrite32(val, phba->db_va + DB_EQ_OFFSET); +} + +/** + * be_isr - The isr routine of the driver. + * @irq: Not used + * @dev_id: Pointer to host adapter structure + */ +static irqreturn_t be_isr(int irq, void *dev_id) +{ + struct beiscsi_hba *phba; + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + struct be_eq_entry *eqe = NULL; + struct be_queue_info *eq; + struct be_queue_info *cq; + unsigned long flags, index; + unsigned int num_eq_processed; + struct be_ctrl_info *ctrl; + int isr; + + phba = dev_id; + if (!enable_msix) { + ctrl = &phba->ctrl;; + isr = ioread32(ctrl->csr + CEV_ISR0_OFFSET + + (PCI_FUNC(ctrl->pdev->devfn) * CEV_ISR_SIZE)); + if (!isr) + return IRQ_NONE; + } + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_context = phwi_ctrlr->phwi_ctxt; + eq = &phwi_context->be_eq.q; + cq = &phwi_context->be_cq; + index = 0; + eqe = queue_tail_node(eq); + if (!eqe) + SE_DEBUG(DBG_LVL_1, "eqe is NULL\n"); + + num_eq_processed = 0; + if (blk_iopoll_enabled) { + while (eqe->dw[offsetof(struct amap_eq_entry, valid) / 32] + & EQE_VALID_MASK) { + if (!blk_iopoll_sched_prep(&phba->iopoll)) + blk_iopoll_sched(&phba->iopoll); + + AMAP_SET_BITS(struct amap_eq_entry, valid, eqe, 0); + queue_tail_inc(eq); + eqe = queue_tail_node(eq); + num_eq_processed++; + SE_DEBUG(DBG_LVL_8, "Valid EQE\n"); + } + if (num_eq_processed) { + hwi_ring_eq_db(phba, eq->id, 0, num_eq_processed, 0, 1); + return IRQ_HANDLED; + } else + return IRQ_NONE; + } else { + while (eqe->dw[offsetof(struct amap_eq_entry, valid) / 32] + & EQE_VALID_MASK) { + + if (((eqe->dw[offsetof(struct amap_eq_entry, + resource_id) / 32] & + EQE_RESID_MASK) >> 16) != cq->id) { + spin_lock_irqsave(&phba->isr_lock, flags); + phba->todo_mcc_cq = 1; + spin_unlock_irqrestore(&phba->isr_lock, flags); + } else { + spin_lock_irqsave(&phba->isr_lock, flags); + phba->todo_cq = 1; + spin_unlock_irqrestore(&phba->isr_lock, flags); + } + AMAP_SET_BITS(struct amap_eq_entry, valid, eqe, 0); + queue_tail_inc(eq); + eqe = queue_tail_node(eq); + num_eq_processed++; + } + if (phba->todo_cq || phba->todo_mcc_cq) + queue_work(phba->wq, &phba->work_cqs); + + if (num_eq_processed) { + hwi_ring_eq_db(phba, eq->id, 0, num_eq_processed, 1, 1); + return IRQ_HANDLED; + } else + return IRQ_NONE; + } +} + +static int beiscsi_init_irqs(struct beiscsi_hba *phba) +{ + struct pci_dev *pcidev = phba->pcidev; + int ret; + + ret = request_irq(pcidev->irq, be_isr, IRQF_SHARED, "beiscsi", phba); + if (ret) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_init_irqs-" + "Failed to register irq\\n"); + return ret; + } + return 0; +} + +static void hwi_ring_cq_db(struct beiscsi_hba *phba, + unsigned int id, unsigned int num_processed, + unsigned char rearm, unsigned char event) +{ + u32 val = 0; + val |= id & DB_CQ_RING_ID_MASK; + if (rearm) + val |= 1 << DB_CQ_REARM_SHIFT; + val |= num_processed << DB_CQ_NUM_POPPED_SHIFT; + iowrite32(val, phba->db_va + DB_CQ_OFFSET); +} + +/* + * async pdus include + * a. unsolicited NOP-In (target initiated NOP-In) + * b. Async Messages + * c. Reject PDU + * d. Login response + * These headers arrive unprocessed by the EP firmware and iSCSI layer + * process them + */ +static unsigned int +beiscsi_process_async_pdu(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_hba *phba, + unsigned short cid, + struct pdu_base *ppdu, + unsigned long pdu_len, + void *pbuffer, unsigned long buf_len) +{ + struct iscsi_conn *conn = beiscsi_conn->conn; + struct iscsi_session *session = conn->session; + + switch (ppdu->dw[offsetof(struct amap_pdu_base, opcode) / 32] & + PDUBASE_OPCODE_MASK) { + case ISCSI_OP_NOOP_IN: + pbuffer = NULL; + buf_len = 0; + break; + case ISCSI_OP_ASYNC_EVENT: + break; + case ISCSI_OP_REJECT: + WARN_ON(!pbuffer); + WARN_ON(!(buf_len == 48)); + SE_DEBUG(DBG_LVL_1, "In ISCSI_OP_REJECT\n"); + break; + case ISCSI_OP_LOGIN_RSP: + break; + default: + shost_printk(KERN_WARNING, phba->shost, + "Unrecognized opcode 0x%x in async msg \n", + (ppdu-> + dw[offsetof(struct amap_pdu_base, opcode) / 32] + & PDUBASE_OPCODE_MASK)); + return 1; + } + + spin_lock_bh(&session->lock); + __iscsi_complete_pdu(conn, (struct iscsi_hdr *)ppdu, pbuffer, buf_len); + spin_unlock_bh(&session->lock); + return 0; +} + +static struct sgl_handle *alloc_io_sgl_handle(struct beiscsi_hba *phba) +{ + struct sgl_handle *psgl_handle; + + if (phba->io_sgl_hndl_avbl) { + SE_DEBUG(DBG_LVL_8, + "In alloc_io_sgl_handle,io_sgl_alloc_index=%d \n", + phba->io_sgl_alloc_index); + psgl_handle = phba->io_sgl_hndl_base[phba-> + io_sgl_alloc_index]; + phba->io_sgl_hndl_base[phba->io_sgl_alloc_index] = NULL; + phba->io_sgl_hndl_avbl--; + if (phba->io_sgl_alloc_index == (phba->params.ios_per_ctrl - 1)) + phba->io_sgl_alloc_index = 0; + else + phba->io_sgl_alloc_index++; + } else + psgl_handle = NULL; + return psgl_handle; +} + +static void +free_io_sgl_handle(struct beiscsi_hba *phba, struct sgl_handle *psgl_handle) +{ + SE_DEBUG(DBG_LVL_8, "In free_,io_sgl_free_index=%d \n", + phba->io_sgl_free_index); + if (phba->io_sgl_hndl_base[phba->io_sgl_free_index]) { + /* + * this can happen if clean_task is called on a task that + * failed in xmit_task or alloc_pdu. + */ + SE_DEBUG(DBG_LVL_8, + "Double Free in IO SGL io_sgl_free_index=%d," + "value there=%p \n", phba->io_sgl_free_index, + phba->io_sgl_hndl_base[phba->io_sgl_free_index]); + return; + } + phba->io_sgl_hndl_base[phba->io_sgl_free_index] = psgl_handle; + phba->io_sgl_hndl_avbl++; + if (phba->io_sgl_free_index == (phba->params.ios_per_ctrl - 1)) + phba->io_sgl_free_index = 0; + else + phba->io_sgl_free_index++; +} + +/** + * alloc_wrb_handle - To allocate a wrb handle + * @phba: The hba pointer + * @cid: The cid to use for allocation + * @index: index allocation and wrb index + * + * This happens under session_lock until submission to chip + */ +struct wrb_handle *alloc_wrb_handle(struct beiscsi_hba *phba, unsigned int cid, + int index) +{ + struct hwi_wrb_context *pwrb_context; + struct hwi_controller *phwi_ctrlr; + struct wrb_handle *pwrb_handle; + + phwi_ctrlr = phba->phwi_ctrlr; + pwrb_context = &phwi_ctrlr->wrb_context[cid]; + pwrb_handle = pwrb_context->pwrb_handle_base[index]; + pwrb_handle->wrb_index = index; + pwrb_handle->nxt_wrb_index = index; + return pwrb_handle; +} + +/** + * free_wrb_handle - To free the wrb handle back to pool + * @phba: The hba pointer + * @pwrb_context: The context to free from + * @pwrb_handle: The wrb_handle to free + * + * This happens under session_lock until submission to chip + */ +static void +free_wrb_handle(struct beiscsi_hba *phba, struct hwi_wrb_context *pwrb_context, + struct wrb_handle *pwrb_handle) +{ + SE_DEBUG(DBG_LVL_8, + "FREE WRB: pwrb_handle=%p free_index=%d=0x%x" + "wrb_handles_available=%d \n", + pwrb_handle, pwrb_context->free_index, + pwrb_context->free_index, pwrb_context->wrb_handles_available); +} + +static struct sgl_handle *alloc_mgmt_sgl_handle(struct beiscsi_hba *phba) +{ + struct sgl_handle *psgl_handle; + + if (phba->eh_sgl_hndl_avbl) { + psgl_handle = phba->eh_sgl_hndl_base[phba->eh_sgl_alloc_index]; + phba->eh_sgl_hndl_base[phba->eh_sgl_alloc_index] = NULL; + SE_DEBUG(DBG_LVL_8, "mgmt_sgl_alloc_index=%d=0x%x \n", + phba->eh_sgl_alloc_index, phba->eh_sgl_alloc_index); + phba->eh_sgl_hndl_avbl--; + if (phba->eh_sgl_alloc_index == + (phba->params.icds_per_ctrl - phba->params.ios_per_ctrl - + 1)) + phba->eh_sgl_alloc_index = 0; + else + phba->eh_sgl_alloc_index++; + } else + psgl_handle = NULL; + return psgl_handle; +} + +void +free_mgmt_sgl_handle(struct beiscsi_hba *phba, struct sgl_handle *psgl_handle) +{ + + if (phba->eh_sgl_hndl_base[phba->eh_sgl_free_index]) { + /* + * this can happen if clean_task is called on a task that + * failed in xmit_task or alloc_pdu. + */ + SE_DEBUG(DBG_LVL_8, + "Double Free in eh SGL ,eh_sgl_free_index=%d \n", + phba->eh_sgl_free_index); + return; + } + phba->eh_sgl_hndl_base[phba->eh_sgl_free_index] = psgl_handle; + phba->eh_sgl_hndl_avbl++; + if (phba->eh_sgl_free_index == + (phba->params.icds_per_ctrl - phba->params.ios_per_ctrl - 1)) + phba->eh_sgl_free_index = 0; + else + phba->eh_sgl_free_index++; +} + +static void +be_complete_io(struct beiscsi_conn *beiscsi_conn, + struct iscsi_task *task, struct sol_cqe *psol) +{ + struct beiscsi_io_task *io_task = task->dd_data; + struct be_status_bhs *sts_bhs = + (struct be_status_bhs *)io_task->cmd_bhs; + struct iscsi_conn *conn = beiscsi_conn->conn; + unsigned int sense_len; + unsigned char *sense; + u32 resid = 0, exp_cmdsn, max_cmdsn; + u8 rsp, status, flags; + + exp_cmdsn = be32_to_cpu(psol-> + dw[offsetof(struct amap_sol_cqe, i_exp_cmd_sn) / 32] + & SOL_EXP_CMD_SN_MASK); + max_cmdsn = be32_to_cpu((psol-> + dw[offsetof(struct amap_sol_cqe, i_exp_cmd_sn) / 32] + & SOL_EXP_CMD_SN_MASK) + + ((psol->dw[offsetof(struct amap_sol_cqe, i_cmd_wnd) + / 32] & SOL_CMD_WND_MASK) >> 24) - 1); + rsp = ((psol->dw[offsetof(struct amap_sol_cqe, i_resp) / 32] + & SOL_RESP_MASK) >> 16); + status = ((psol->dw[offsetof(struct amap_sol_cqe, i_sts) / 32] + & SOL_STS_MASK) >> 8); + flags = ((psol->dw[offsetof(struct amap_sol_cqe, i_flags) / 32] + & SOL_FLAGS_MASK) >> 24) | 0x80; + + task->sc->result = (DID_OK << 16) | status; + if (rsp != ISCSI_STATUS_CMD_COMPLETED) { + task->sc->result = DID_ERROR << 16; + goto unmap; + } + + /* bidi not initially supported */ + if (flags & (ISCSI_FLAG_CMD_UNDERFLOW | ISCSI_FLAG_CMD_OVERFLOW)) { + resid = (psol->dw[offsetof(struct amap_sol_cqe, i_res_cnt) / + 32] & SOL_RES_CNT_MASK); + + if (!status && (flags & ISCSI_FLAG_CMD_OVERFLOW)) + task->sc->result = DID_ERROR << 16; + + if (flags & ISCSI_FLAG_CMD_UNDERFLOW) { + scsi_set_resid(task->sc, resid); + if (!status && (scsi_bufflen(task->sc) - resid < + task->sc->underflow)) + task->sc->result = DID_ERROR << 16; + } + } + + if (status == SAM_STAT_CHECK_CONDITION) { + sense = sts_bhs->sense_info + sizeof(unsigned short); + sense_len = + cpu_to_be16((unsigned short)(sts_bhs->sense_info[0])); + memcpy(task->sc->sense_buffer, sense, + min_t(u16, sense_len, SCSI_SENSE_BUFFERSIZE)); + } + if (io_task->cmd_bhs->iscsi_hdr.flags & ISCSI_FLAG_CMD_READ) { + if (psol->dw[offsetof(struct amap_sol_cqe, i_res_cnt) / 32] + & SOL_RES_CNT_MASK) + conn->rxdata_octets += (psol-> + dw[offsetof(struct amap_sol_cqe, i_res_cnt) / 32] + & SOL_RES_CNT_MASK); + } +unmap: + scsi_dma_unmap(io_task->scsi_cmnd); + iscsi_complete_scsi_task(task, exp_cmdsn, max_cmdsn); +} + +static void +be_complete_logout(struct beiscsi_conn *beiscsi_conn, + struct iscsi_task *task, struct sol_cqe *psol) +{ + struct iscsi_logout_rsp *hdr; + struct iscsi_conn *conn = beiscsi_conn->conn; + + hdr = (struct iscsi_logout_rsp *)task->hdr; + hdr->t2wait = 5; + hdr->t2retain = 0; + hdr->flags = ((psol->dw[offsetof(struct amap_sol_cqe, i_flags) / 32] + & SOL_FLAGS_MASK) >> 24) | 0x80; + hdr->response = (psol->dw[offsetof(struct amap_sol_cqe, i_resp) / + 32] & SOL_RESP_MASK); + hdr->exp_cmdsn = cpu_to_be32(psol-> + dw[offsetof(struct amap_sol_cqe, i_exp_cmd_sn) / 32] + & SOL_EXP_CMD_SN_MASK); + hdr->max_cmdsn = be32_to_cpu((psol-> + dw[offsetof(struct amap_sol_cqe, i_exp_cmd_sn) / 32] + & SOL_EXP_CMD_SN_MASK) + + ((psol->dw[offsetof(struct amap_sol_cqe, i_cmd_wnd) + / 32] & SOL_CMD_WND_MASK) >> 24) - 1); + hdr->hlength = 0; + + __iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0); +} + +static void +be_complete_tmf(struct beiscsi_conn *beiscsi_conn, + struct iscsi_task *task, struct sol_cqe *psol) +{ + struct iscsi_tm_rsp *hdr; + struct iscsi_conn *conn = beiscsi_conn->conn; + + hdr = (struct iscsi_tm_rsp *)task->hdr; + hdr->flags = ((psol->dw[offsetof(struct amap_sol_cqe, i_flags) / 32] + & SOL_FLAGS_MASK) >> 24) | 0x80; + hdr->response = (psol->dw[offsetof(struct amap_sol_cqe, i_resp) / + 32] & SOL_RESP_MASK); + hdr->exp_cmdsn = cpu_to_be32(psol->dw[offsetof(struct amap_sol_cqe, + i_exp_cmd_sn) / 32] & SOL_EXP_CMD_SN_MASK); + hdr->max_cmdsn = be32_to_cpu((psol->dw[offsetof(struct amap_sol_cqe, + i_exp_cmd_sn) / 32] & SOL_EXP_CMD_SN_MASK) + + ((psol->dw[offsetof(struct amap_sol_cqe, i_cmd_wnd) + / 32] & SOL_CMD_WND_MASK) >> 24) - 1); + __iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0); +} + +static void +hwi_complete_drvr_msgs(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_hba *phba, struct sol_cqe *psol) +{ + struct hwi_wrb_context *pwrb_context; + struct wrb_handle *pwrb_handle; + struct hwi_controller *phwi_ctrlr; + struct iscsi_conn *conn = beiscsi_conn->conn; + struct iscsi_session *session = conn->session; + + phwi_ctrlr = phba->phwi_ctrlr; + pwrb_context = &phwi_ctrlr->wrb_context[((psol-> + dw[offsetof(struct amap_sol_cqe, cid) / 32] & + SOL_CID_MASK) >> 6)]; + pwrb_handle = pwrb_context->pwrb_handle_basestd[((psol-> + dw[offsetof(struct amap_sol_cqe, wrb_index) / + 32] & SOL_WRB_INDEX_MASK) >> 16)]; + spin_lock_bh(&session->lock); + free_wrb_handle(phba, pwrb_context, pwrb_handle); + spin_unlock_bh(&session->lock); +} + +static void +be_complete_nopin_resp(struct beiscsi_conn *beiscsi_conn, + struct iscsi_task *task, struct sol_cqe *psol) +{ + struct iscsi_nopin *hdr; + struct iscsi_conn *conn = beiscsi_conn->conn; + + hdr = (struct iscsi_nopin *)task->hdr; + hdr->flags = ((psol->dw[offsetof(struct amap_sol_cqe, i_flags) / 32] + & SOL_FLAGS_MASK) >> 24) | 0x80; + hdr->exp_cmdsn = cpu_to_be32(psol->dw[offsetof(struct amap_sol_cqe, + i_exp_cmd_sn) / 32] & SOL_EXP_CMD_SN_MASK); + hdr->max_cmdsn = be32_to_cpu((psol->dw[offsetof(struct amap_sol_cqe, + i_exp_cmd_sn) / 32] & SOL_EXP_CMD_SN_MASK) + + ((psol->dw[offsetof(struct amap_sol_cqe, i_cmd_wnd) + / 32] & SOL_CMD_WND_MASK) >> 24) - 1); + hdr->opcode = ISCSI_OP_NOOP_IN; + __iscsi_complete_pdu(conn, (struct iscsi_hdr *)hdr, NULL, 0); +} + +static void hwi_complete_cmd(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_hba *phba, struct sol_cqe *psol) +{ + struct hwi_wrb_context *pwrb_context; + struct wrb_handle *pwrb_handle; + struct iscsi_wrb *pwrb = NULL; + struct hwi_controller *phwi_ctrlr; + struct iscsi_task *task; + struct beiscsi_io_task *io_task; + struct iscsi_conn *conn = beiscsi_conn->conn; + struct iscsi_session *session = conn->session; + + phwi_ctrlr = phba->phwi_ctrlr; + + pwrb_context = &phwi_ctrlr-> + wrb_context[((psol->dw[offsetof(struct amap_sol_cqe, cid) / 32] + & SOL_CID_MASK) >> 6)]; + pwrb_handle = pwrb_context->pwrb_handle_basestd[((psol-> + dw[offsetof(struct amap_sol_cqe, wrb_index) / + 32] & SOL_WRB_INDEX_MASK) >> 16)]; + + task = pwrb_handle->pio_handle; + io_task = task->dd_data; + spin_lock_bh(&session->lock); + pwrb = pwrb_handle->pwrb; + switch ((pwrb->dw[offsetof(struct amap_iscsi_wrb, type) / 32] & + WRB_TYPE_MASK) >> 28) { + case HWH_TYPE_IO: + case HWH_TYPE_IO_RD: + if ((task->hdr->opcode & ISCSI_OPCODE_MASK) == + ISCSI_OP_NOOP_OUT) { + be_complete_nopin_resp(beiscsi_conn, task, psol); + } else + be_complete_io(beiscsi_conn, task, psol); + break; + + case HWH_TYPE_LOGOUT: + be_complete_logout(beiscsi_conn, task, psol); + break; + + case HWH_TYPE_LOGIN: + SE_DEBUG(DBG_LVL_1, + "\t\t No HWH_TYPE_LOGIN Expected in hwi_complete_cmd" + "- Solicited path \n"); + break; + + case HWH_TYPE_TMF: + be_complete_tmf(beiscsi_conn, task, psol); + break; + + case HWH_TYPE_NOP: + be_complete_nopin_resp(beiscsi_conn, task, psol); + break; + + default: + shost_printk(KERN_WARNING, phba->shost, + "wrb_index 0x%x CID 0x%x\n", + ((psol->dw[offsetof(struct amap_iscsi_wrb, type) / + 32] & SOL_WRB_INDEX_MASK) >> 16), + ((psol->dw[offsetof(struct amap_sol_cqe, cid) / 32] + & SOL_CID_MASK) >> 6)); + break; + } + + spin_unlock_bh(&session->lock); +} + +static struct list_head *hwi_get_async_busy_list(struct hwi_async_pdu_context + *pasync_ctx, unsigned int is_header, + unsigned int host_write_ptr) +{ + if (is_header) + return &pasync_ctx->async_entry[host_write_ptr]. + header_busy_list; + else + return &pasync_ctx->async_entry[host_write_ptr].data_busy_list; +} + +static struct async_pdu_handle * +hwi_get_async_handle(struct beiscsi_hba *phba, + struct beiscsi_conn *beiscsi_conn, + struct hwi_async_pdu_context *pasync_ctx, + struct i_t_dpdu_cqe *pdpdu_cqe, unsigned int *pcq_index) +{ + struct be_bus_address phys_addr; + struct list_head *pbusy_list; + struct async_pdu_handle *pasync_handle = NULL; + int buffer_len = 0; + unsigned char buffer_index = -1; + unsigned char is_header = 0; + + phys_addr.u.a32.address_lo = + pdpdu_cqe->dw[offsetof(struct amap_i_t_dpdu_cqe, db_addr_lo) / 32] - + ((pdpdu_cqe->dw[offsetof(struct amap_i_t_dpdu_cqe, dpl) / 32] + & PDUCQE_DPL_MASK) >> 16); + phys_addr.u.a32.address_hi = + pdpdu_cqe->dw[offsetof(struct amap_i_t_dpdu_cqe, db_addr_hi) / 32]; + + phys_addr.u.a64.address = + *((unsigned long long *)(&phys_addr.u.a64.address)); + + switch (pdpdu_cqe->dw[offsetof(struct amap_i_t_dpdu_cqe, code) / 32] + & PDUCQE_CODE_MASK) { + case UNSOL_HDR_NOTIFY: + is_header = 1; + + pbusy_list = hwi_get_async_busy_list(pasync_ctx, 1, + (pdpdu_cqe->dw[offsetof(struct amap_i_t_dpdu_cqe, + index) / 32] & PDUCQE_INDEX_MASK)); + + buffer_len = (unsigned int)(phys_addr.u.a64.address - + pasync_ctx->async_header.pa_base.u.a64.address); + + buffer_index = buffer_len / + pasync_ctx->async_header.buffer_size; + + break; + case UNSOL_DATA_NOTIFY: + pbusy_list = hwi_get_async_busy_list(pasync_ctx, 0, (pdpdu_cqe-> + dw[offsetof(struct amap_i_t_dpdu_cqe, + index) / 32] & PDUCQE_INDEX_MASK)); + buffer_len = (unsigned long)(phys_addr.u.a64.address - + pasync_ctx->async_data.pa_base.u. + a64.address); + buffer_index = buffer_len / pasync_ctx->async_data.buffer_size; + break; + default: + pbusy_list = NULL; + shost_printk(KERN_WARNING, phba->shost, + "Unexpected code=%d \n", + pdpdu_cqe->dw[offsetof(struct amap_i_t_dpdu_cqe, + code) / 32] & PDUCQE_CODE_MASK); + return NULL; + } + + WARN_ON(!(buffer_index <= pasync_ctx->async_data.num_entries)); + WARN_ON(list_empty(pbusy_list)); + list_for_each_entry(pasync_handle, pbusy_list, link) { + WARN_ON(pasync_handle->consumed); + if (pasync_handle->index == buffer_index) + break; + } + + WARN_ON(!pasync_handle); + + pasync_handle->cri = (unsigned short)beiscsi_conn->beiscsi_conn_cid; + pasync_handle->is_header = is_header; + pasync_handle->buffer_len = ((pdpdu_cqe-> + dw[offsetof(struct amap_i_t_dpdu_cqe, dpl) / 32] + & PDUCQE_DPL_MASK) >> 16); + + *pcq_index = (pdpdu_cqe->dw[offsetof(struct amap_i_t_dpdu_cqe, + index) / 32] & PDUCQE_INDEX_MASK); + return pasync_handle; +} + +static unsigned int +hwi_update_async_writables(struct hwi_async_pdu_context *pasync_ctx, + unsigned int is_header, unsigned int cq_index) +{ + struct list_head *pbusy_list; + struct async_pdu_handle *pasync_handle; + unsigned int num_entries, writables = 0; + unsigned int *pep_read_ptr, *pwritables; + + + if (is_header) { + pep_read_ptr = &pasync_ctx->async_header.ep_read_ptr; + pwritables = &pasync_ctx->async_header.writables; + num_entries = pasync_ctx->async_header.num_entries; + } else { + pep_read_ptr = &pasync_ctx->async_data.ep_read_ptr; + pwritables = &pasync_ctx->async_data.writables; + num_entries = pasync_ctx->async_data.num_entries; + } + + while ((*pep_read_ptr) != cq_index) { + (*pep_read_ptr)++; + *pep_read_ptr = (*pep_read_ptr) % num_entries; + + pbusy_list = hwi_get_async_busy_list(pasync_ctx, is_header, + *pep_read_ptr); + if (writables == 0) + WARN_ON(list_empty(pbusy_list)); + + if (!list_empty(pbusy_list)) { + pasync_handle = list_entry(pbusy_list->next, + struct async_pdu_handle, + link); + WARN_ON(!pasync_handle); + pasync_handle->consumed = 1; + } + + writables++; + } + + if (!writables) { + SE_DEBUG(DBG_LVL_1, + "Duplicate notification received - index 0x%x!!\n", + cq_index); + WARN_ON(1); + } + + *pwritables = *pwritables + writables; + return 0; +} + +static unsigned int hwi_free_async_msg(struct beiscsi_hba *phba, + unsigned int cri) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_async_pdu_context *pasync_ctx; + struct async_pdu_handle *pasync_handle, *tmp_handle; + struct list_head *plist; + unsigned int i = 0; + + phwi_ctrlr = phba->phwi_ctrlr; + pasync_ctx = HWI_GET_ASYNC_PDU_CTX(phwi_ctrlr); + + plist = &pasync_ctx->async_entry[cri].wait_queue.list; + + list_for_each_entry_safe(pasync_handle, tmp_handle, plist, link) { + list_del(&pasync_handle->link); + + if (i == 0) { + list_add_tail(&pasync_handle->link, + &pasync_ctx->async_header.free_list); + pasync_ctx->async_header.free_entries++; + i++; + } else { + list_add_tail(&pasync_handle->link, + &pasync_ctx->async_data.free_list); + pasync_ctx->async_data.free_entries++; + i++; + } + } + + INIT_LIST_HEAD(&pasync_ctx->async_entry[cri].wait_queue.list); + pasync_ctx->async_entry[cri].wait_queue.hdr_received = 0; + pasync_ctx->async_entry[cri].wait_queue.bytes_received = 0; + return 0; +} + +static struct phys_addr * +hwi_get_ring_address(struct hwi_async_pdu_context *pasync_ctx, + unsigned int is_header, unsigned int host_write_ptr) +{ + struct phys_addr *pasync_sge = NULL; + + if (is_header) + pasync_sge = pasync_ctx->async_header.ring_base; + else + pasync_sge = pasync_ctx->async_data.ring_base; + + return pasync_sge + host_write_ptr; +} + +static void hwi_post_async_buffers(struct beiscsi_hba *phba, + unsigned int is_header) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_async_pdu_context *pasync_ctx; + struct async_pdu_handle *pasync_handle; + struct list_head *pfree_link, *pbusy_list; + struct phys_addr *pasync_sge; + unsigned int ring_id, num_entries; + unsigned int host_write_num; + unsigned int writables; + unsigned int i = 0; + u32 doorbell = 0; + + phwi_ctrlr = phba->phwi_ctrlr; + pasync_ctx = HWI_GET_ASYNC_PDU_CTX(phwi_ctrlr); + + if (is_header) { + num_entries = pasync_ctx->async_header.num_entries; + writables = min(pasync_ctx->async_header.writables, + pasync_ctx->async_header.free_entries); + pfree_link = pasync_ctx->async_header.free_list.next; + host_write_num = pasync_ctx->async_header.host_write_ptr; + ring_id = phwi_ctrlr->default_pdu_hdr.id; + } else { + num_entries = pasync_ctx->async_data.num_entries; + writables = min(pasync_ctx->async_data.writables, + pasync_ctx->async_data.free_entries); + pfree_link = pasync_ctx->async_data.free_list.next; + host_write_num = pasync_ctx->async_data.host_write_ptr; + ring_id = phwi_ctrlr->default_pdu_data.id; + } + + writables = (writables / 8) * 8; + if (writables) { + for (i = 0; i < writables; i++) { + pbusy_list = + hwi_get_async_busy_list(pasync_ctx, is_header, + host_write_num); + pasync_handle = + list_entry(pfree_link, struct async_pdu_handle, + link); + WARN_ON(!pasync_handle); + pasync_handle->consumed = 0; + + pfree_link = pfree_link->next; + + pasync_sge = hwi_get_ring_address(pasync_ctx, + is_header, host_write_num); + + pasync_sge->hi = pasync_handle->pa.u.a32.address_lo; + pasync_sge->lo = pasync_handle->pa.u.a32.address_hi; + + list_move(&pasync_handle->link, pbusy_list); + + host_write_num++; + host_write_num = host_write_num % num_entries; + } + + if (is_header) { + pasync_ctx->async_header.host_write_ptr = + host_write_num; + pasync_ctx->async_header.free_entries -= writables; + pasync_ctx->async_header.writables -= writables; + pasync_ctx->async_header.busy_entries += writables; + } else { + pasync_ctx->async_data.host_write_ptr = host_write_num; + pasync_ctx->async_data.free_entries -= writables; + pasync_ctx->async_data.writables -= writables; + pasync_ctx->async_data.busy_entries += writables; + } + + doorbell |= ring_id & DB_DEF_PDU_RING_ID_MASK; + doorbell |= 1 << DB_DEF_PDU_REARM_SHIFT; + doorbell |= 0 << DB_DEF_PDU_EVENT_SHIFT; + doorbell |= (writables & DB_DEF_PDU_CQPROC_MASK) + << DB_DEF_PDU_CQPROC_SHIFT; + + iowrite32(doorbell, phba->db_va + DB_RXULP0_OFFSET); + } +} + +static void hwi_flush_default_pdu_buffer(struct beiscsi_hba *phba, + struct beiscsi_conn *beiscsi_conn, + struct i_t_dpdu_cqe *pdpdu_cqe) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_async_pdu_context *pasync_ctx; + struct async_pdu_handle *pasync_handle = NULL; + unsigned int cq_index = -1; + + phwi_ctrlr = phba->phwi_ctrlr; + pasync_ctx = HWI_GET_ASYNC_PDU_CTX(phwi_ctrlr); + + pasync_handle = hwi_get_async_handle(phba, beiscsi_conn, pasync_ctx, + pdpdu_cqe, &cq_index); + BUG_ON(pasync_handle->is_header != 0); + if (pasync_handle->consumed == 0) + hwi_update_async_writables(pasync_ctx, pasync_handle->is_header, + cq_index); + + hwi_free_async_msg(phba, pasync_handle->cri); + hwi_post_async_buffers(phba, pasync_handle->is_header); +} + +static unsigned int +hwi_fwd_async_msg(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_hba *phba, + struct hwi_async_pdu_context *pasync_ctx, unsigned short cri) +{ + struct list_head *plist; + struct async_pdu_handle *pasync_handle; + void *phdr = NULL; + unsigned int hdr_len = 0, buf_len = 0; + unsigned int status, index = 0, offset = 0; + void *pfirst_buffer = NULL; + unsigned int num_buf = 0; + + plist = &pasync_ctx->async_entry[cri].wait_queue.list; + + list_for_each_entry(pasync_handle, plist, link) { + if (index == 0) { + phdr = pasync_handle->pbuffer; + hdr_len = pasync_handle->buffer_len; + } else { + buf_len = pasync_handle->buffer_len; + if (!num_buf) { + pfirst_buffer = pasync_handle->pbuffer; + num_buf++; + } + memcpy(pfirst_buffer + offset, + pasync_handle->pbuffer, buf_len); + offset = buf_len; + } + index++; + } + + status = beiscsi_process_async_pdu(beiscsi_conn, phba, + beiscsi_conn->beiscsi_conn_cid, + phdr, hdr_len, pfirst_buffer, + buf_len); + + if (status == 0) + hwi_free_async_msg(phba, cri); + return 0; +} + +static unsigned int +hwi_gather_async_pdu(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_hba *phba, + struct async_pdu_handle *pasync_handle) +{ + struct hwi_async_pdu_context *pasync_ctx; + struct hwi_controller *phwi_ctrlr; + unsigned int bytes_needed = 0, status = 0; + unsigned short cri = pasync_handle->cri; + struct pdu_base *ppdu; + + phwi_ctrlr = phba->phwi_ctrlr; + pasync_ctx = HWI_GET_ASYNC_PDU_CTX(phwi_ctrlr); + + list_del(&pasync_handle->link); + if (pasync_handle->is_header) { + pasync_ctx->async_header.busy_entries--; + if (pasync_ctx->async_entry[cri].wait_queue.hdr_received) { + hwi_free_async_msg(phba, cri); + BUG(); + } + + pasync_ctx->async_entry[cri].wait_queue.bytes_received = 0; + pasync_ctx->async_entry[cri].wait_queue.hdr_received = 1; + pasync_ctx->async_entry[cri].wait_queue.hdr_len = + (unsigned short)pasync_handle->buffer_len; + list_add_tail(&pasync_handle->link, + &pasync_ctx->async_entry[cri].wait_queue.list); + + ppdu = pasync_handle->pbuffer; + bytes_needed = ((((ppdu->dw[offsetof(struct amap_pdu_base, + data_len_hi) / 32] & PDUBASE_DATALENHI_MASK) << 8) & + 0xFFFF0000) | ((be16_to_cpu((ppdu-> + dw[offsetof(struct amap_pdu_base, data_len_lo) / 32] + & PDUBASE_DATALENLO_MASK) >> 16)) & 0x0000FFFF)); + + if (status == 0) { + pasync_ctx->async_entry[cri].wait_queue.bytes_needed = + bytes_needed; + + if (bytes_needed == 0) + status = hwi_fwd_async_msg(beiscsi_conn, phba, + pasync_ctx, cri); + } + } else { + pasync_ctx->async_data.busy_entries--; + if (pasync_ctx->async_entry[cri].wait_queue.hdr_received) { + list_add_tail(&pasync_handle->link, + &pasync_ctx->async_entry[cri].wait_queue. + list); + pasync_ctx->async_entry[cri].wait_queue. + bytes_received += + (unsigned short)pasync_handle->buffer_len; + + if (pasync_ctx->async_entry[cri].wait_queue. + bytes_received >= + pasync_ctx->async_entry[cri].wait_queue. + bytes_needed) + status = hwi_fwd_async_msg(beiscsi_conn, phba, + pasync_ctx, cri); + } + } + return status; +} + +static void hwi_process_default_pdu_ring(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_hba *phba, + struct i_t_dpdu_cqe *pdpdu_cqe) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_async_pdu_context *pasync_ctx; + struct async_pdu_handle *pasync_handle = NULL; + unsigned int cq_index = -1; + + phwi_ctrlr = phba->phwi_ctrlr; + pasync_ctx = HWI_GET_ASYNC_PDU_CTX(phwi_ctrlr); + pasync_handle = hwi_get_async_handle(phba, beiscsi_conn, pasync_ctx, + pdpdu_cqe, &cq_index); + + if (pasync_handle->consumed == 0) + hwi_update_async_writables(pasync_ctx, pasync_handle->is_header, + cq_index); + hwi_gather_async_pdu(beiscsi_conn, phba, pasync_handle); + hwi_post_async_buffers(phba, pasync_handle->is_header); +} + +static unsigned int beiscsi_process_cq(struct beiscsi_hba *phba) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + struct be_queue_info *cq; + struct sol_cqe *sol; + struct dmsg_cqe *dmsg; + unsigned int num_processed = 0; + unsigned int tot_nump = 0; + struct beiscsi_conn *beiscsi_conn; + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_context = phwi_ctrlr->phwi_ctxt; + cq = &phwi_context->be_cq; + sol = queue_tail_node(cq); + + while (sol->dw[offsetof(struct amap_sol_cqe, valid) / 32] & + CQE_VALID_MASK) { + be_dws_le_to_cpu(sol, sizeof(struct sol_cqe)); + + beiscsi_conn = phba->conn_table[(u32) (sol-> + dw[offsetof(struct amap_sol_cqe, cid) / 32] & + SOL_CID_MASK) >> 6]; + + if (!beiscsi_conn || !beiscsi_conn->ep) { + shost_printk(KERN_WARNING, phba->shost, + "Connection table empty for cid = %d\n", + (u32)(sol->dw[offsetof(struct amap_sol_cqe, + cid) / 32] & SOL_CID_MASK) >> 6); + return 0; + } + + if (num_processed >= 32) { + hwi_ring_cq_db(phba, phwi_context->be_cq.id, + num_processed, 0, 0); + tot_nump += num_processed; + num_processed = 0; + } + + switch ((u32) sol->dw[offsetof(struct amap_sol_cqe, code) / + 32] & CQE_CODE_MASK) { + case SOL_CMD_COMPLETE: + hwi_complete_cmd(beiscsi_conn, phba, sol); + break; + case DRIVERMSG_NOTIFY: + SE_DEBUG(DBG_LVL_8, "Received DRIVERMSG_NOTIFY \n"); + dmsg = (struct dmsg_cqe *)sol; + hwi_complete_drvr_msgs(beiscsi_conn, phba, sol); + break; + case UNSOL_HDR_NOTIFY: + case UNSOL_DATA_NOTIFY: + SE_DEBUG(DBG_LVL_8, "Received UNSOL_HDR/DATA_NOTIFY\n"); + hwi_process_default_pdu_ring(beiscsi_conn, phba, + (struct i_t_dpdu_cqe *)sol); + break; + case CXN_INVALIDATE_INDEX_NOTIFY: + case CMD_INVALIDATED_NOTIFY: + case CXN_INVALIDATE_NOTIFY: + SE_DEBUG(DBG_LVL_1, + "Ignoring CQ Error notification for cmd/cxn" + "invalidate\n"); + break; + case SOL_CMD_KILLED_DATA_DIGEST_ERR: + case CMD_KILLED_INVALID_STATSN_RCVD: + case CMD_KILLED_INVALID_R2T_RCVD: + case CMD_CXN_KILLED_LUN_INVALID: + case CMD_CXN_KILLED_ICD_INVALID: + case CMD_CXN_KILLED_ITT_INVALID: + case CMD_CXN_KILLED_SEQ_OUTOFORDER: + case CMD_CXN_KILLED_INVALID_DATASN_RCVD: + SE_DEBUG(DBG_LVL_1, + "CQ Error notification for cmd.. " + "code %d cid 0x%x\n", + sol->dw[offsetof(struct amap_sol_cqe, code) / + 32] & CQE_CODE_MASK, + (sol->dw[offsetof(struct amap_sol_cqe, cid) / + 32] & SOL_CID_MASK)); + break; + case UNSOL_DATA_DIGEST_ERROR_NOTIFY: + SE_DEBUG(DBG_LVL_1, + "Digest error on def pdu ring, dropping..\n"); + hwi_flush_default_pdu_buffer(phba, beiscsi_conn, + (struct i_t_dpdu_cqe *) sol); + break; + case CXN_KILLED_PDU_SIZE_EXCEEDS_DSL: + case CXN_KILLED_BURST_LEN_MISMATCH: + case CXN_KILLED_AHS_RCVD: + case CXN_KILLED_HDR_DIGEST_ERR: + case CXN_KILLED_UNKNOWN_HDR: + case CXN_KILLED_STALE_ITT_TTT_RCVD: + case CXN_KILLED_INVALID_ITT_TTT_RCVD: + case CXN_KILLED_TIMED_OUT: + case CXN_KILLED_FIN_RCVD: + case CXN_KILLED_BAD_UNSOL_PDU_RCVD: + case CXN_KILLED_BAD_WRB_INDEX_ERROR: + case CXN_KILLED_OVER_RUN_RESIDUAL: + case CXN_KILLED_UNDER_RUN_RESIDUAL: + case CXN_KILLED_CMND_DATA_NOT_ON_SAME_CONN: + SE_DEBUG(DBG_LVL_1, "CQ Error %d, resetting CID " + "0x%x...\n", + sol->dw[offsetof(struct amap_sol_cqe, code) / + 32] & CQE_CODE_MASK, + sol->dw[offsetof(struct amap_sol_cqe, cid) / + 32] & CQE_CID_MASK); + iscsi_conn_failure(beiscsi_conn->conn, + ISCSI_ERR_CONN_FAILED); + break; + case CXN_KILLED_RST_SENT: + case CXN_KILLED_RST_RCVD: + SE_DEBUG(DBG_LVL_1, "CQ Error %d, reset received/sent " + "on CID 0x%x...\n", + sol->dw[offsetof(struct amap_sol_cqe, code) / + 32] & CQE_CODE_MASK, + sol->dw[offsetof(struct amap_sol_cqe, cid) / + 32] & CQE_CID_MASK); + iscsi_conn_failure(beiscsi_conn->conn, + ISCSI_ERR_CONN_FAILED); + break; + default: + SE_DEBUG(DBG_LVL_1, "CQ Error Invalid code= %d " + "received on CID 0x%x...\n", + sol->dw[offsetof(struct amap_sol_cqe, code) / + 32] & CQE_CODE_MASK, + sol->dw[offsetof(struct amap_sol_cqe, cid) / + 32] & CQE_CID_MASK); + break; + } + + AMAP_SET_BITS(struct amap_sol_cqe, valid, sol, 0); + queue_tail_inc(cq); + sol = queue_tail_node(cq); + num_processed++; + } + + if (num_processed > 0) { + tot_nump += num_processed; + hwi_ring_cq_db(phba, phwi_context->be_cq.id, num_processed, + 1, 0); + } + return tot_nump; +} + +static void beiscsi_process_all_cqs(struct work_struct *work) +{ + unsigned long flags; + struct beiscsi_hba *phba = + container_of(work, struct beiscsi_hba, work_cqs); + + if (phba->todo_mcc_cq) { + spin_lock_irqsave(&phba->isr_lock, flags); + phba->todo_mcc_cq = 0; + spin_unlock_irqrestore(&phba->isr_lock, flags); + SE_DEBUG(DBG_LVL_1, "MCC Interrupt Not expected \n"); + } + + if (phba->todo_cq) { + spin_lock_irqsave(&phba->isr_lock, flags); + phba->todo_cq = 0; + spin_unlock_irqrestore(&phba->isr_lock, flags); + beiscsi_process_cq(phba); + } +} + +static int be_iopoll(struct blk_iopoll *iop, int budget) +{ + static unsigned int ret; + struct beiscsi_hba *phba; + + phba = container_of(iop, struct beiscsi_hba, iopoll); + + ret = beiscsi_process_cq(phba); + if (ret < budget) { + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_context = phwi_ctrlr->phwi_ctxt; + blk_iopoll_complete(iop); + hwi_ring_eq_db(phba, phwi_context->be_eq.q.id, 0, + 0, 1, 1); + } + return ret; +} + +static void +hwi_write_sgl(struct iscsi_wrb *pwrb, struct scatterlist *sg, + unsigned int num_sg, struct beiscsi_io_task *io_task) +{ + struct iscsi_sge *psgl; + unsigned short sg_len, index; + unsigned int sge_len = 0; + unsigned long long addr; + struct scatterlist *l_sg; + unsigned int offset; + + AMAP_SET_BITS(struct amap_iscsi_wrb, iscsi_bhs_addr_lo, pwrb, + io_task->bhs_pa.u.a32.address_lo); + AMAP_SET_BITS(struct amap_iscsi_wrb, iscsi_bhs_addr_hi, pwrb, + io_task->bhs_pa.u.a32.address_hi); + + l_sg = sg; + for (index = 0; (index < num_sg) && (index < 2); index++, sg_next(sg)) { + if (index == 0) { + sg_len = sg_dma_len(sg); + addr = (u64) sg_dma_address(sg); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_addr_lo, pwrb, + (addr & 0xFFFFFFFF)); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_addr_hi, pwrb, + (addr >> 32)); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_len, pwrb, + sg_len); + sge_len = sg_len; + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_last, pwrb, + 1); + } else { + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_last, pwrb, + 0); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge1_r2t_offset, + pwrb, sge_len); + sg_len = sg_dma_len(sg); + addr = (u64) sg_dma_address(sg); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge1_addr_lo, pwrb, + (addr & 0xFFFFFFFF)); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge1_addr_hi, pwrb, + (addr >> 32)); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge1_len, pwrb, + sg_len); + } + } + psgl = (struct iscsi_sge *)io_task->psgl_handle->pfrag; + memset(psgl, 0, sizeof(*psgl) * BE2_SGE); + + AMAP_SET_BITS(struct amap_iscsi_sge, len, psgl, io_task->bhs_len - 2); + + AMAP_SET_BITS(struct amap_iscsi_sge, addr_hi, psgl, + io_task->bhs_pa.u.a32.address_hi); + AMAP_SET_BITS(struct amap_iscsi_sge, addr_lo, psgl, + io_task->bhs_pa.u.a32.address_lo); + + if (num_sg == 2) + AMAP_SET_BITS(struct amap_iscsi_wrb, sge1_last, pwrb, 1); + sg = l_sg; + psgl++; + psgl++; + offset = 0; + for (index = 0; index < num_sg; index++, sg_next(sg), psgl++) { + sg_len = sg_dma_len(sg); + addr = (u64) sg_dma_address(sg); + AMAP_SET_BITS(struct amap_iscsi_sge, addr_lo, psgl, + (addr & 0xFFFFFFFF)); + AMAP_SET_BITS(struct amap_iscsi_sge, addr_hi, psgl, + (addr >> 32)); + AMAP_SET_BITS(struct amap_iscsi_sge, len, psgl, sg_len); + AMAP_SET_BITS(struct amap_iscsi_sge, sge_offset, psgl, offset); + AMAP_SET_BITS(struct amap_iscsi_sge, last_sge, psgl, 0); + offset += sg_len; + } + psgl--; + AMAP_SET_BITS(struct amap_iscsi_sge, last_sge, psgl, 1); +} + +static void hwi_write_buffer(struct iscsi_wrb *pwrb, struct iscsi_task *task) +{ + struct iscsi_sge *psgl; + unsigned long long addr; + struct beiscsi_io_task *io_task = task->dd_data; + struct beiscsi_conn *beiscsi_conn = io_task->conn; + struct beiscsi_hba *phba = beiscsi_conn->phba; + + io_task->bhs_len = sizeof(struct be_nonio_bhs) - 2; + AMAP_SET_BITS(struct amap_iscsi_wrb, iscsi_bhs_addr_lo, pwrb, + io_task->bhs_pa.u.a32.address_lo); + AMAP_SET_BITS(struct amap_iscsi_wrb, iscsi_bhs_addr_hi, pwrb, + io_task->bhs_pa.u.a32.address_hi); + + if (task->data) { + if (task->data_count) { + AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 1); + addr = (u64) pci_map_single(phba->pcidev, + task->data, + task->data_count, 1); + } else { + AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 0); + addr = 0; + } + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_addr_lo, pwrb, + (addr & 0xFFFFFFFF)); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_addr_hi, pwrb, + (addr >> 32)); + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_len, pwrb, + task->data_count); + + AMAP_SET_BITS(struct amap_iscsi_wrb, sge0_last, pwrb, 1); + } else { + AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 0); + addr = 0; + } + + psgl = (struct iscsi_sge *)io_task->psgl_handle->pfrag; + + AMAP_SET_BITS(struct amap_iscsi_sge, len, psgl, io_task->bhs_len); + + AMAP_SET_BITS(struct amap_iscsi_sge, addr_hi, psgl, + io_task->bhs_pa.u.a32.address_hi); + AMAP_SET_BITS(struct amap_iscsi_sge, addr_lo, psgl, + io_task->bhs_pa.u.a32.address_lo); + if (task->data) { + psgl++; + AMAP_SET_BITS(struct amap_iscsi_sge, addr_hi, psgl, 0); + AMAP_SET_BITS(struct amap_iscsi_sge, addr_lo, psgl, 0); + AMAP_SET_BITS(struct amap_iscsi_sge, len, psgl, 0); + AMAP_SET_BITS(struct amap_iscsi_sge, sge_offset, psgl, 0); + AMAP_SET_BITS(struct amap_iscsi_sge, rsvd0, psgl, 0); + AMAP_SET_BITS(struct amap_iscsi_sge, last_sge, psgl, 0); + + psgl++; + if (task->data) { + AMAP_SET_BITS(struct amap_iscsi_sge, addr_lo, psgl, + (addr & 0xFFFFFFFF)); + AMAP_SET_BITS(struct amap_iscsi_sge, addr_hi, psgl, + (addr >> 32)); + } + AMAP_SET_BITS(struct amap_iscsi_sge, len, psgl, 0x106); + } + AMAP_SET_BITS(struct amap_iscsi_sge, last_sge, psgl, 1); +} + +static void beiscsi_find_mem_req(struct beiscsi_hba *phba) +{ + unsigned int num_cq_pages, num_eq_pages, num_async_pdu_buf_pages; + unsigned int num_async_pdu_data_pages, wrb_sz_per_cxn; + unsigned int num_async_pdu_buf_sgl_pages, num_async_pdu_data_sgl_pages; + + num_cq_pages = PAGES_REQUIRED(phba->params.num_cq_entries * \ + sizeof(struct sol_cqe)); + num_eq_pages = PAGES_REQUIRED(phba->params.num_eq_entries * \ + sizeof(struct be_eq_entry)); + num_async_pdu_buf_pages = + PAGES_REQUIRED(phba->params.asyncpdus_per_ctrl * \ + phba->params.defpdu_hdr_sz); + num_async_pdu_buf_sgl_pages = + PAGES_REQUIRED(phba->params.asyncpdus_per_ctrl * \ + sizeof(struct phys_addr)); + num_async_pdu_data_pages = + PAGES_REQUIRED(phba->params.asyncpdus_per_ctrl * \ + phba->params.defpdu_data_sz); + num_async_pdu_data_sgl_pages = + PAGES_REQUIRED(phba->params.asyncpdus_per_ctrl * \ + sizeof(struct phys_addr)); + + phba->params.hwi_ws_sz = sizeof(struct hwi_controller); + + phba->mem_req[ISCSI_MEM_GLOBAL_HEADER] = 2 * + BE_ISCSI_PDU_HEADER_SIZE; + phba->mem_req[HWI_MEM_ADDN_CONTEXT] = + sizeof(struct hwi_context_memory); + + phba->mem_req[HWI_MEM_CQ] = num_cq_pages * PAGE_SIZE; + phba->mem_req[HWI_MEM_EQ] = num_eq_pages * PAGE_SIZE; + + phba->mem_req[HWI_MEM_WRB] = sizeof(struct iscsi_wrb) + * (phba->params.wrbs_per_cxn) + * phba->params.cxns_per_ctrl; + wrb_sz_per_cxn = sizeof(struct wrb_handle) * + (phba->params.wrbs_per_cxn); + phba->mem_req[HWI_MEM_WRBH] = roundup_pow_of_two((wrb_sz_per_cxn) * + phba->params.cxns_per_ctrl); + + phba->mem_req[HWI_MEM_SGLH] = sizeof(struct sgl_handle) * + phba->params.icds_per_ctrl; + phba->mem_req[HWI_MEM_SGE] = sizeof(struct iscsi_sge) * + phba->params.num_sge_per_io * phba->params.icds_per_ctrl; + + phba->mem_req[HWI_MEM_ASYNC_HEADER_BUF] = + num_async_pdu_buf_pages * PAGE_SIZE; + phba->mem_req[HWI_MEM_ASYNC_DATA_BUF] = + num_async_pdu_data_pages * PAGE_SIZE; + phba->mem_req[HWI_MEM_ASYNC_HEADER_RING] = + num_async_pdu_buf_sgl_pages * PAGE_SIZE; + phba->mem_req[HWI_MEM_ASYNC_DATA_RING] = + num_async_pdu_data_sgl_pages * PAGE_SIZE; + phba->mem_req[HWI_MEM_ASYNC_HEADER_HANDLE] = + phba->params.asyncpdus_per_ctrl * + sizeof(struct async_pdu_handle); + phba->mem_req[HWI_MEM_ASYNC_DATA_HANDLE] = + phba->params.asyncpdus_per_ctrl * + sizeof(struct async_pdu_handle); + phba->mem_req[HWI_MEM_ASYNC_PDU_CONTEXT] = + sizeof(struct hwi_async_pdu_context) + + (phba->params.cxns_per_ctrl * sizeof(struct hwi_async_entry)); +} + +static int beiscsi_alloc_mem(struct beiscsi_hba *phba) +{ + struct be_mem_descriptor *mem_descr; + dma_addr_t bus_add; + struct mem_array *mem_arr, *mem_arr_orig; + unsigned int i, j, alloc_size, curr_alloc_size; + + phba->phwi_ctrlr = kmalloc(phba->params.hwi_ws_sz, GFP_KERNEL); + if (!phba->phwi_ctrlr) + return -ENOMEM; + + phba->init_mem = kcalloc(SE_MEM_MAX, sizeof(*mem_descr), + GFP_KERNEL); + if (!phba->init_mem) { + kfree(phba->phwi_ctrlr); + return -ENOMEM; + } + + mem_arr_orig = kmalloc(sizeof(*mem_arr_orig) * BEISCSI_MAX_FRAGS_INIT, + GFP_KERNEL); + if (!mem_arr_orig) { + kfree(phba->init_mem); + kfree(phba->phwi_ctrlr); + return -ENOMEM; + } + + mem_descr = phba->init_mem; + for (i = 0; i < SE_MEM_MAX; i++) { + j = 0; + mem_arr = mem_arr_orig; + alloc_size = phba->mem_req[i]; + memset(mem_arr, 0, sizeof(struct mem_array) * + BEISCSI_MAX_FRAGS_INIT); + curr_alloc_size = min(be_max_phys_size * 1024, alloc_size); + do { + mem_arr->virtual_address = pci_alloc_consistent( + phba->pcidev, + curr_alloc_size, + &bus_add); + if (!mem_arr->virtual_address) { + if (curr_alloc_size <= BE_MIN_MEM_SIZE) + goto free_mem; + if (curr_alloc_size - + rounddown_pow_of_two(curr_alloc_size)) + curr_alloc_size = rounddown_pow_of_two + (curr_alloc_size); + else + curr_alloc_size = curr_alloc_size / 2; + } else { + mem_arr->bus_address.u. + a64.address = (__u64) bus_add; + mem_arr->size = curr_alloc_size; + alloc_size -= curr_alloc_size; + curr_alloc_size = min(be_max_phys_size * + 1024, alloc_size); + j++; + mem_arr++; + } + } while (alloc_size); + mem_descr->num_elements = j; + mem_descr->size_in_bytes = phba->mem_req[i]; + mem_descr->mem_array = kmalloc(sizeof(*mem_arr) * j, + GFP_KERNEL); + if (!mem_descr->mem_array) + goto free_mem; + + memcpy(mem_descr->mem_array, mem_arr_orig, + sizeof(struct mem_array) * j); + mem_descr++; + } + kfree(mem_arr_orig); + return 0; +free_mem: + mem_descr->num_elements = j; + while ((i) || (j)) { + for (j = mem_descr->num_elements; j > 0; j--) { + pci_free_consistent(phba->pcidev, + mem_descr->mem_array[j - 1].size, + mem_descr->mem_array[j - 1]. + virtual_address, + mem_descr->mem_array[j - 1]. + bus_address.u.a64.address); + } + if (i) { + i--; + kfree(mem_descr->mem_array); + mem_descr--; + } + } + kfree(mem_arr_orig); + kfree(phba->init_mem); + kfree(phba->phwi_ctrlr); + return -ENOMEM; +} + +static int beiscsi_get_memory(struct beiscsi_hba *phba) +{ + beiscsi_find_mem_req(phba); + return beiscsi_alloc_mem(phba); +} + +static void iscsi_init_global_templates(struct beiscsi_hba *phba) +{ + struct pdu_data_out *pdata_out; + struct pdu_nop_out *pnop_out; + struct be_mem_descriptor *mem_descr; + + mem_descr = phba->init_mem; + mem_descr += ISCSI_MEM_GLOBAL_HEADER; + pdata_out = + (struct pdu_data_out *)mem_descr->mem_array[0].virtual_address; + memset(pdata_out, 0, BE_ISCSI_PDU_HEADER_SIZE); + + AMAP_SET_BITS(struct amap_pdu_data_out, opcode, pdata_out, + IIOC_SCSI_DATA); + + pnop_out = + (struct pdu_nop_out *)((unsigned char *)mem_descr->mem_array[0]. + virtual_address + BE_ISCSI_PDU_HEADER_SIZE); + + memset(pnop_out, 0, BE_ISCSI_PDU_HEADER_SIZE); + AMAP_SET_BITS(struct amap_pdu_nop_out, ttt, pnop_out, 0xFFFFFFFF); + AMAP_SET_BITS(struct amap_pdu_nop_out, f_bit, pnop_out, 1); + AMAP_SET_BITS(struct amap_pdu_nop_out, i_bit, pnop_out, 0); +} + +static void beiscsi_init_wrb_handle(struct beiscsi_hba *phba) +{ + struct be_mem_descriptor *mem_descr_wrbh, *mem_descr_wrb; + struct wrb_handle *pwrb_handle; + struct hwi_controller *phwi_ctrlr; + struct hwi_wrb_context *pwrb_context; + struct iscsi_wrb *pwrb; + unsigned int num_cxn_wrbh; + unsigned int num_cxn_wrb, j, idx, index; + + mem_descr_wrbh = phba->init_mem; + mem_descr_wrbh += HWI_MEM_WRBH; + + mem_descr_wrb = phba->init_mem; + mem_descr_wrb += HWI_MEM_WRB; + + idx = 0; + pwrb_handle = mem_descr_wrbh->mem_array[idx].virtual_address; + num_cxn_wrbh = ((mem_descr_wrbh->mem_array[idx].size) / + ((sizeof(struct wrb_handle)) * + phba->params.wrbs_per_cxn)); + phwi_ctrlr = phba->phwi_ctrlr; + + for (index = 0; index < phba->params.cxns_per_ctrl * 2; index += 2) { + pwrb_context = &phwi_ctrlr->wrb_context[index]; + SE_DEBUG(DBG_LVL_8, "cid=%d pwrb_context=%p \n", index, + pwrb_context); + pwrb_context->pwrb_handle_base = + kzalloc(sizeof(struct wrb_handle *) * + phba->params.wrbs_per_cxn, GFP_KERNEL); + pwrb_context->pwrb_handle_basestd = + kzalloc(sizeof(struct wrb_handle *) * + phba->params.wrbs_per_cxn, GFP_KERNEL); + if (num_cxn_wrbh) { + pwrb_context->alloc_index = 0; + pwrb_context->wrb_handles_available = 0; + for (j = 0; j < phba->params.wrbs_per_cxn; j++) { + pwrb_context->pwrb_handle_base[j] = pwrb_handle; + pwrb_context->pwrb_handle_basestd[j] = + pwrb_handle; + pwrb_context->wrb_handles_available++; + pwrb_handle++; + } + pwrb_context->free_index = 0; + num_cxn_wrbh--; + } else { + idx++; + pwrb_handle = + mem_descr_wrbh->mem_array[idx].virtual_address; + num_cxn_wrbh = + ((mem_descr_wrbh->mem_array[idx].size) / + ((sizeof(struct wrb_handle)) * + phba->params.wrbs_per_cxn)); + pwrb_context->alloc_index = 0; + for (j = 0; j < phba->params.wrbs_per_cxn; j++) { + pwrb_context->pwrb_handle_base[j] = pwrb_handle; + pwrb_context->pwrb_handle_basestd[j] = + pwrb_handle; + pwrb_context->wrb_handles_available++; + pwrb_handle++; + } + pwrb_context->free_index = 0; + num_cxn_wrbh--; + } + } + idx = 0; + pwrb = mem_descr_wrb->mem_array[idx].virtual_address; + num_cxn_wrb = + ((mem_descr_wrb->mem_array[idx].size) / (sizeof(struct iscsi_wrb)) * + phba->params.wrbs_per_cxn); + + for (index = 0; index < phba->params.cxns_per_ctrl; index += 2) { + pwrb_context = &phwi_ctrlr->wrb_context[index]; + if (num_cxn_wrb) { + for (j = 0; j < phba->params.wrbs_per_cxn; j++) { + pwrb_handle = pwrb_context->pwrb_handle_base[j]; + pwrb_handle->pwrb = pwrb; + pwrb++; + } + num_cxn_wrb--; + } else { + idx++; + pwrb = mem_descr_wrb->mem_array[idx].virtual_address; + num_cxn_wrb = ((mem_descr_wrb->mem_array[idx].size) / + (sizeof(struct iscsi_wrb)) * + phba->params.wrbs_per_cxn); + for (j = 0; j < phba->params.wrbs_per_cxn; j++) { + pwrb_handle = pwrb_context->pwrb_handle_base[j]; + pwrb_handle->pwrb = pwrb; + pwrb++; + } + num_cxn_wrb--; + } + } +} + +static void hwi_init_async_pdu_ctx(struct beiscsi_hba *phba) +{ + struct hwi_controller *phwi_ctrlr; + struct hba_parameters *p = &phba->params; + struct hwi_async_pdu_context *pasync_ctx; + struct async_pdu_handle *pasync_header_h, *pasync_data_h; + unsigned int index; + struct be_mem_descriptor *mem_descr; + + mem_descr = (struct be_mem_descriptor *)phba->init_mem; + mem_descr += HWI_MEM_ASYNC_PDU_CONTEXT; + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_ctrlr->phwi_ctxt->pasync_ctx = (struct hwi_async_pdu_context *) + mem_descr->mem_array[0].virtual_address; + pasync_ctx = phwi_ctrlr->phwi_ctxt->pasync_ctx; + memset(pasync_ctx, 0, sizeof(*pasync_ctx)); + + pasync_ctx->async_header.num_entries = p->asyncpdus_per_ctrl; + pasync_ctx->async_header.buffer_size = p->defpdu_hdr_sz; + pasync_ctx->async_data.buffer_size = p->defpdu_data_sz; + pasync_ctx->async_data.num_entries = p->asyncpdus_per_ctrl; + + mem_descr = (struct be_mem_descriptor *)phba->init_mem; + mem_descr += HWI_MEM_ASYNC_HEADER_BUF; + if (mem_descr->mem_array[0].virtual_address) { + SE_DEBUG(DBG_LVL_8, + "hwi_init_async_pdu_ctx HWI_MEM_ASYNC_HEADER_BUF" + "va=%p \n", mem_descr->mem_array[0].virtual_address); + } else + shost_printk(KERN_WARNING, phba->shost, + "No Virtual address \n"); + + pasync_ctx->async_header.va_base = + mem_descr->mem_array[0].virtual_address; + + pasync_ctx->async_header.pa_base.u.a64.address = + mem_descr->mem_array[0].bus_address.u.a64.address; + + mem_descr = (struct be_mem_descriptor *)phba->init_mem; + mem_descr += HWI_MEM_ASYNC_HEADER_RING; + if (mem_descr->mem_array[0].virtual_address) { + SE_DEBUG(DBG_LVL_8, + "hwi_init_async_pdu_ctx HWI_MEM_ASYNC_HEADER_RING" + "va=%p \n", mem_descr->mem_array[0].virtual_address); + } else + shost_printk(KERN_WARNING, phba->shost, + "No Virtual address \n"); + pasync_ctx->async_header.ring_base = + mem_descr->mem_array[0].virtual_address; + + mem_descr = (struct be_mem_descriptor *)phba->init_mem; + mem_descr += HWI_MEM_ASYNC_HEADER_HANDLE; + if (mem_descr->mem_array[0].virtual_address) { + SE_DEBUG(DBG_LVL_8, + "hwi_init_async_pdu_ctx HWI_MEM_ASYNC_HEADER_HANDLE" + "va=%p \n", mem_descr->mem_array[0].virtual_address); + } else + shost_printk(KERN_WARNING, phba->shost, + "No Virtual address \n"); + + pasync_ctx->async_header.handle_base = + mem_descr->mem_array[0].virtual_address; + pasync_ctx->async_header.writables = 0; + INIT_LIST_HEAD(&pasync_ctx->async_header.free_list); + + mem_descr = (struct be_mem_descriptor *)phba->init_mem; + mem_descr += HWI_MEM_ASYNC_DATA_BUF; + if (mem_descr->mem_array[0].virtual_address) { + SE_DEBUG(DBG_LVL_8, + "hwi_init_async_pdu_ctx HWI_MEM_ASYNC_DATA_BUF" + "va=%p \n", mem_descr->mem_array[0].virtual_address); + } else + shost_printk(KERN_WARNING, phba->shost, + "No Virtual address \n"); + pasync_ctx->async_data.va_base = + mem_descr->mem_array[0].virtual_address; + pasync_ctx->async_data.pa_base.u.a64.address = + mem_descr->mem_array[0].bus_address.u.a64.address; + + mem_descr = (struct be_mem_descriptor *)phba->init_mem; + mem_descr += HWI_MEM_ASYNC_DATA_RING; + if (mem_descr->mem_array[0].virtual_address) { + SE_DEBUG(DBG_LVL_8, + "hwi_init_async_pdu_ctx HWI_MEM_ASYNC_DATA_RING" + "va=%p \n", mem_descr->mem_array[0].virtual_address); + } else + shost_printk(KERN_WARNING, phba->shost, + "No Virtual address \n"); + + pasync_ctx->async_data.ring_base = + mem_descr->mem_array[0].virtual_address; + + mem_descr = (struct be_mem_descriptor *)phba->init_mem; + mem_descr += HWI_MEM_ASYNC_DATA_HANDLE; + if (!mem_descr->mem_array[0].virtual_address) + shost_printk(KERN_WARNING, phba->shost, + "No Virtual address \n"); + + pasync_ctx->async_data.handle_base = + mem_descr->mem_array[0].virtual_address; + pasync_ctx->async_data.writables = 0; + INIT_LIST_HEAD(&pasync_ctx->async_data.free_list); + + pasync_header_h = + (struct async_pdu_handle *)pasync_ctx->async_header.handle_base; + pasync_data_h = + (struct async_pdu_handle *)pasync_ctx->async_data.handle_base; + + for (index = 0; index < p->asyncpdus_per_ctrl; index++) { + pasync_header_h->cri = -1; + pasync_header_h->index = (char)index; + INIT_LIST_HEAD(&pasync_header_h->link); + pasync_header_h->pbuffer = + (void *)((unsigned long) + (pasync_ctx->async_header.va_base) + + (p->defpdu_hdr_sz * index)); + + pasync_header_h->pa.u.a64.address = + pasync_ctx->async_header.pa_base.u.a64.address + + (p->defpdu_hdr_sz * index); + + list_add_tail(&pasync_header_h->link, + &pasync_ctx->async_header.free_list); + pasync_header_h++; + pasync_ctx->async_header.free_entries++; + pasync_ctx->async_header.writables++; + + INIT_LIST_HEAD(&pasync_ctx->async_entry[index].wait_queue.list); + INIT_LIST_HEAD(&pasync_ctx->async_entry[index]. + header_busy_list); + pasync_data_h->cri = -1; + pasync_data_h->index = (char)index; + INIT_LIST_HEAD(&pasync_data_h->link); + pasync_data_h->pbuffer = + (void *)((unsigned long) + (pasync_ctx->async_data.va_base) + + (p->defpdu_data_sz * index)); + + pasync_data_h->pa.u.a64.address = + pasync_ctx->async_data.pa_base.u.a64.address + + (p->defpdu_data_sz * index); + + list_add_tail(&pasync_data_h->link, + &pasync_ctx->async_data.free_list); + pasync_data_h++; + pasync_ctx->async_data.free_entries++; + pasync_ctx->async_data.writables++; + + INIT_LIST_HEAD(&pasync_ctx->async_entry[index].data_busy_list); + } + + pasync_ctx->async_header.host_write_ptr = 0; + pasync_ctx->async_header.ep_read_ptr = -1; + pasync_ctx->async_data.host_write_ptr = 0; + pasync_ctx->async_data.ep_read_ptr = -1; +} + +static int +be_sgl_create_contiguous(void *virtual_address, + u64 physical_address, u32 length, + struct be_dma_mem *sgl) +{ + WARN_ON(!virtual_address); + WARN_ON(!physical_address); + WARN_ON(!length > 0); + WARN_ON(!sgl); + + sgl->va = virtual_address; + sgl->dma = physical_address; + sgl->size = length; + + return 0; +} + +static void be_sgl_destroy_contiguous(struct be_dma_mem *sgl) +{ + memset(sgl, 0, sizeof(*sgl)); +} + +static void +hwi_build_be_sgl_arr(struct beiscsi_hba *phba, + struct mem_array *pmem, struct be_dma_mem *sgl) +{ + if (sgl->va) + be_sgl_destroy_contiguous(sgl); + + be_sgl_create_contiguous(pmem->virtual_address, + pmem->bus_address.u.a64.address, + pmem->size, sgl); +} + +static void +hwi_build_be_sgl_by_offset(struct beiscsi_hba *phba, + struct mem_array *pmem, struct be_dma_mem *sgl) +{ + if (sgl->va) + be_sgl_destroy_contiguous(sgl); + + be_sgl_create_contiguous((unsigned char *)pmem->virtual_address, + pmem->bus_address.u.a64.address, + pmem->size, sgl); +} + +static int be_fill_queue(struct be_queue_info *q, + u16 len, u16 entry_size, void *vaddress) +{ + struct be_dma_mem *mem = &q->dma_mem; + + memset(q, 0, sizeof(*q)); + q->len = len; + q->entry_size = entry_size; + mem->size = len * entry_size; + mem->va = vaddress; + if (!mem->va) + return -ENOMEM; + memset(mem->va, 0, mem->size); + return 0; +} + +static int beiscsi_create_eq(struct beiscsi_hba *phba, + struct hwi_context_memory *phwi_context) +{ + unsigned int idx; + int ret; + struct be_queue_info *eq; + struct be_dma_mem *mem; + struct be_mem_descriptor *mem_descr; + void *eq_vaddress; + + idx = 0; + eq = &phwi_context->be_eq.q; + mem = &eq->dma_mem; + mem_descr = phba->init_mem; + mem_descr += HWI_MEM_EQ; + eq_vaddress = mem_descr->mem_array[idx].virtual_address; + + ret = be_fill_queue(eq, phba->params.num_eq_entries, + sizeof(struct be_eq_entry), eq_vaddress); + if (ret) { + shost_printk(KERN_ERR, phba->shost, + "be_fill_queue Failed for EQ \n"); + return ret; + } + + mem->dma = mem_descr->mem_array[idx].bus_address.u.a64.address; + + ret = beiscsi_cmd_eq_create(&phba->ctrl, eq, + phwi_context->be_eq.cur_eqd); + if (ret) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_cmd_eq_create" + "Failedfor EQ \n"); + return ret; + } + SE_DEBUG(DBG_LVL_8, "eq id is %d\n", phwi_context->be_eq.q.id); + return 0; +} + +static int beiscsi_create_cq(struct beiscsi_hba *phba, + struct hwi_context_memory *phwi_context) +{ + unsigned int idx; + int ret; + struct be_queue_info *cq, *eq; + struct be_dma_mem *mem; + struct be_mem_descriptor *mem_descr; + void *cq_vaddress; + + idx = 0; + cq = &phwi_context->be_cq; + eq = &phwi_context->be_eq.q; + mem = &cq->dma_mem; + mem_descr = phba->init_mem; + mem_descr += HWI_MEM_CQ; + cq_vaddress = mem_descr->mem_array[idx].virtual_address; + ret = be_fill_queue(cq, phba->params.icds_per_ctrl / 2, + sizeof(struct sol_cqe), cq_vaddress); + if (ret) { + shost_printk(KERN_ERR, phba->shost, + "be_fill_queue Failed for ISCSI CQ \n"); + return ret; + } + + mem->dma = mem_descr->mem_array[idx].bus_address.u.a64.address; + ret = beiscsi_cmd_cq_create(&phba->ctrl, cq, eq, false, false, 0); + if (ret) { + shost_printk(KERN_ERR, phba->shost, + "beiscsi_cmd_eq_create Failed for ISCSI CQ \n"); + return ret; + } + SE_DEBUG(DBG_LVL_8, "iscsi cq id is %d\n", phwi_context->be_cq.id); + SE_DEBUG(DBG_LVL_8, "ISCSI CQ CREATED\n"); + return 0; +} + +static int +beiscsi_create_def_hdr(struct beiscsi_hba *phba, + struct hwi_context_memory *phwi_context, + struct hwi_controller *phwi_ctrlr, + unsigned int def_pdu_ring_sz) +{ + unsigned int idx; + int ret; + struct be_queue_info *dq, *cq; + struct be_dma_mem *mem; + struct be_mem_descriptor *mem_descr; + void *dq_vaddress; + + idx = 0; + dq = &phwi_context->be_def_hdrq; + cq = &phwi_context->be_cq; + mem = &dq->dma_mem; + mem_descr = phba->init_mem; + mem_descr += HWI_MEM_ASYNC_HEADER_RING; + dq_vaddress = mem_descr->mem_array[idx].virtual_address; + ret = be_fill_queue(dq, mem_descr->mem_array[0].size / + sizeof(struct phys_addr), + sizeof(struct phys_addr), dq_vaddress); + if (ret) { + shost_printk(KERN_ERR, phba->shost, + "be_fill_queue Failed for DEF PDU HDR\n"); + return ret; + } + mem->dma = mem_descr->mem_array[idx].bus_address.u.a64.address; + ret = be_cmd_create_default_pdu_queue(&phba->ctrl, cq, dq, + def_pdu_ring_sz, + phba->params.defpdu_hdr_sz); + if (ret) { + shost_printk(KERN_ERR, phba->shost, + "be_cmd_create_default_pdu_queue Failed DEFHDR\n"); + return ret; + } + phwi_ctrlr->default_pdu_hdr.id = phwi_context->be_def_hdrq.id; + SE_DEBUG(DBG_LVL_8, "iscsi def pdu id is %d\n", + phwi_context->be_def_hdrq.id); + hwi_post_async_buffers(phba, 1); + return 0; +} + +static int +beiscsi_create_def_data(struct beiscsi_hba *phba, + struct hwi_context_memory *phwi_context, + struct hwi_controller *phwi_ctrlr, + unsigned int def_pdu_ring_sz) +{ + unsigned int idx; + int ret; + struct be_queue_info *dataq, *cq; + struct be_dma_mem *mem; + struct be_mem_descriptor *mem_descr; + void *dq_vaddress; + + idx = 0; + dataq = &phwi_context->be_def_dataq; + cq = &phwi_context->be_cq; + mem = &dataq->dma_mem; + mem_descr = phba->init_mem; + mem_descr += HWI_MEM_ASYNC_DATA_RING; + dq_vaddress = mem_descr->mem_array[idx].virtual_address; + ret = be_fill_queue(dataq, mem_descr->mem_array[0].size / + sizeof(struct phys_addr), + sizeof(struct phys_addr), dq_vaddress); + if (ret) { + shost_printk(KERN_ERR, phba->shost, + "be_fill_queue Failed for DEF PDU DATA\n"); + return ret; + } + mem->dma = mem_descr->mem_array[idx].bus_address.u.a64.address; + ret = be_cmd_create_default_pdu_queue(&phba->ctrl, cq, dataq, + def_pdu_ring_sz, + phba->params.defpdu_data_sz); + if (ret) { + shost_printk(KERN_ERR, phba->shost, + "be_cmd_create_default_pdu_queue Failed" + " for DEF PDU DATA\n"); + return ret; + } + phwi_ctrlr->default_pdu_data.id = phwi_context->be_def_dataq.id; + SE_DEBUG(DBG_LVL_8, "iscsi def data id is %d\n", + phwi_context->be_def_dataq.id); + hwi_post_async_buffers(phba, 0); + SE_DEBUG(DBG_LVL_8, "DEFAULT PDU DATA RING CREATED \n"); + return 0; +} + +static int +beiscsi_post_pages(struct beiscsi_hba *phba) +{ + struct be_mem_descriptor *mem_descr; + struct mem_array *pm_arr; + unsigned int page_offset, i; + struct be_dma_mem sgl; + int status; + + mem_descr = phba->init_mem; + mem_descr += HWI_MEM_SGE; + pm_arr = mem_descr->mem_array; + + page_offset = (sizeof(struct iscsi_sge) * phba->params.num_sge_per_io * + phba->fw_config.iscsi_icd_start) / PAGE_SIZE; + for (i = 0; i < mem_descr->num_elements; i++) { + hwi_build_be_sgl_arr(phba, pm_arr, &sgl); + status = be_cmd_iscsi_post_sgl_pages(&phba->ctrl, &sgl, + page_offset, + (pm_arr->size / PAGE_SIZE)); + page_offset += pm_arr->size / PAGE_SIZE; + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, + "post sgl failed.\n"); + return status; + } + pm_arr++; + } + SE_DEBUG(DBG_LVL_8, "POSTED PAGES \n"); + return 0; +} + +static int +beiscsi_create_wrb_rings(struct beiscsi_hba *phba, + struct hwi_context_memory *phwi_context, + struct hwi_controller *phwi_ctrlr) +{ + unsigned int wrb_mem_index, offset, size, num_wrb_rings; + u64 pa_addr_lo; + unsigned int idx, num, i; + struct mem_array *pwrb_arr; + void *wrb_vaddr; + struct be_dma_mem sgl; + struct be_mem_descriptor *mem_descr; + int status; + + idx = 0; + mem_descr = phba->init_mem; + mem_descr += HWI_MEM_WRB; + pwrb_arr = kmalloc(sizeof(*pwrb_arr) * phba->params.cxns_per_ctrl, + GFP_KERNEL); + if (!pwrb_arr) { + shost_printk(KERN_ERR, phba->shost, + "Memory alloc failed in create wrb ring.\n"); + return -ENOMEM; + } + wrb_vaddr = mem_descr->mem_array[idx].virtual_address; + pa_addr_lo = mem_descr->mem_array[idx].bus_address.u.a64.address; + num_wrb_rings = mem_descr->mem_array[idx].size / + (phba->params.wrbs_per_cxn * sizeof(struct iscsi_wrb)); + + for (num = 0; num < phba->params.cxns_per_ctrl; num++) { + if (num_wrb_rings) { + pwrb_arr[num].virtual_address = wrb_vaddr; + pwrb_arr[num].bus_address.u.a64.address = pa_addr_lo; + pwrb_arr[num].size = phba->params.wrbs_per_cxn * + sizeof(struct iscsi_wrb); + wrb_vaddr += pwrb_arr[num].size; + pa_addr_lo += pwrb_arr[num].size; + num_wrb_rings--; + } else { + idx++; + wrb_vaddr = mem_descr->mem_array[idx].virtual_address; + pa_addr_lo = mem_descr->mem_array[idx].\ + bus_address.u.a64.address; + num_wrb_rings = mem_descr->mem_array[idx].size / + (phba->params.wrbs_per_cxn * + sizeof(struct iscsi_wrb)); + pwrb_arr[num].virtual_address = wrb_vaddr; + pwrb_arr[num].bus_address.u.a64.address\ + = pa_addr_lo; + pwrb_arr[num].size = phba->params.wrbs_per_cxn * + sizeof(struct iscsi_wrb); + wrb_vaddr += pwrb_arr[num].size; + pa_addr_lo += pwrb_arr[num].size; + num_wrb_rings--; + } + } + for (i = 0; i < phba->params.cxns_per_ctrl; i++) { + wrb_mem_index = 0; + offset = 0; + size = 0; + + hwi_build_be_sgl_by_offset(phba, &pwrb_arr[i], &sgl); + status = be_cmd_wrbq_create(&phba->ctrl, &sgl, + &phwi_context->be_wrbq[i]); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, + "wrbq create failed."); + return status; + } + phwi_ctrlr->wrb_context[i].cid = phwi_context->be_wrbq[i].id; + } + kfree(pwrb_arr); + return 0; +} + +static void free_wrb_handles(struct beiscsi_hba *phba) +{ + unsigned int index; + struct hwi_controller *phwi_ctrlr; + struct hwi_wrb_context *pwrb_context; + + phwi_ctrlr = phba->phwi_ctrlr; + for (index = 0; index < phba->params.cxns_per_ctrl * 2; index += 2) { + pwrb_context = &phwi_ctrlr->wrb_context[index]; + kfree(pwrb_context->pwrb_handle_base); + kfree(pwrb_context->pwrb_handle_basestd); + } +} + +static void hwi_cleanup(struct beiscsi_hba *phba) +{ + struct be_queue_info *q; + struct be_ctrl_info *ctrl = &phba->ctrl; + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + int i; + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_context = phwi_ctrlr->phwi_ctxt; + for (i = 0; i < phba->params.cxns_per_ctrl; i++) { + q = &phwi_context->be_wrbq[i]; + if (q->created) + beiscsi_cmd_q_destroy(ctrl, q, QTYPE_WRBQ); + } + + free_wrb_handles(phba); + + q = &phwi_context->be_def_hdrq; + if (q->created) + beiscsi_cmd_q_destroy(ctrl, q, QTYPE_DPDUQ); + + q = &phwi_context->be_def_dataq; + if (q->created) + beiscsi_cmd_q_destroy(ctrl, q, QTYPE_DPDUQ); + + beiscsi_cmd_q_destroy(ctrl, NULL, QTYPE_SGL); + + q = &phwi_context->be_cq; + if (q->created) + beiscsi_cmd_q_destroy(ctrl, q, QTYPE_CQ); + + q = &phwi_context->be_eq.q; + if (q->created) + beiscsi_cmd_q_destroy(ctrl, q, QTYPE_EQ); +} + +static int hwi_init_port(struct beiscsi_hba *phba) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + unsigned int def_pdu_ring_sz; + struct be_ctrl_info *ctrl = &phba->ctrl; + int status; + + def_pdu_ring_sz = + phba->params.asyncpdus_per_ctrl * sizeof(struct phys_addr); + phwi_ctrlr = phba->phwi_ctrlr; + + phwi_context = phwi_ctrlr->phwi_ctxt; + phwi_context->be_eq.max_eqd = 0; + phwi_context->be_eq.min_eqd = 0; + phwi_context->be_eq.cur_eqd = 64; + phwi_context->be_eq.enable_aic = false; + be_cmd_fw_initialize(&phba->ctrl); + status = beiscsi_create_eq(phba, phwi_context); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, "EQ not created \n"); + goto error; + } + + status = mgmt_check_supported_fw(ctrl); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, + "Unsupported fw version \n"); + goto error; + } + + status = mgmt_get_fw_config(ctrl, phba); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, + "Error getting fw config\n"); + goto error; + } + + status = beiscsi_create_cq(phba, phwi_context); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, "CQ not created\n"); + goto error; + } + + status = beiscsi_create_def_hdr(phba, phwi_context, phwi_ctrlr, + def_pdu_ring_sz); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, + "Default Header not created\n"); + goto error; + } + + status = beiscsi_create_def_data(phba, phwi_context, + phwi_ctrlr, def_pdu_ring_sz); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, + "Default Data not created\n"); + goto error; + } + + status = beiscsi_post_pages(phba); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, "Post SGL Pages Failed\n"); + goto error; + } + + status = beiscsi_create_wrb_rings(phba, phwi_context, phwi_ctrlr); + if (status != 0) { + shost_printk(KERN_ERR, phba->shost, + "WRB Rings not created\n"); + goto error; + } + + SE_DEBUG(DBG_LVL_8, "hwi_init_port success\n"); + return 0; + +error: + shost_printk(KERN_ERR, phba->shost, "hwi_init_port failed"); + hwi_cleanup(phba); + return -ENOMEM; +} + + +static int hwi_init_controller(struct beiscsi_hba *phba) +{ + struct hwi_controller *phwi_ctrlr; + + phwi_ctrlr = phba->phwi_ctrlr; + if (1 == phba->init_mem[HWI_MEM_ADDN_CONTEXT].num_elements) { + phwi_ctrlr->phwi_ctxt = (struct hwi_context_memory *)phba-> + init_mem[HWI_MEM_ADDN_CONTEXT].mem_array[0].virtual_address; + SE_DEBUG(DBG_LVL_8, " phwi_ctrlr->phwi_ctxt=%p \n", + phwi_ctrlr->phwi_ctxt); + } else { + shost_printk(KERN_ERR, phba->shost, + "HWI_MEM_ADDN_CONTEXT is more than one element." + "Failing to load\n"); + return -ENOMEM; + } + + iscsi_init_global_templates(phba); + beiscsi_init_wrb_handle(phba); + hwi_init_async_pdu_ctx(phba); + if (hwi_init_port(phba) != 0) { + shost_printk(KERN_ERR, phba->shost, + "hwi_init_controller failed\n"); + return -ENOMEM; + } + return 0; +} + +static void beiscsi_free_mem(struct beiscsi_hba *phba) +{ + struct be_mem_descriptor *mem_descr; + int i, j; + + mem_descr = phba->init_mem; + i = 0; + j = 0; + for (i = 0; i < SE_MEM_MAX; i++) { + for (j = mem_descr->num_elements; j > 0; j--) { + pci_free_consistent(phba->pcidev, + mem_descr->mem_array[j - 1].size, + mem_descr->mem_array[j - 1].virtual_address, + mem_descr->mem_array[j - 1].bus_address. + u.a64.address); + } + kfree(mem_descr->mem_array); + mem_descr++; + } + kfree(phba->init_mem); + kfree(phba->phwi_ctrlr); +} + +static int beiscsi_init_controller(struct beiscsi_hba *phba) +{ + int ret = -ENOMEM; + + ret = beiscsi_get_memory(phba); + if (ret < 0) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_dev_probe -" + "Failed in beiscsi_alloc_memory \n"); + return ret; + } + + ret = hwi_init_controller(phba); + if (ret) + goto free_init; + SE_DEBUG(DBG_LVL_8, "Return success from beiscsi_init_controller"); + return 0; + +free_init: + beiscsi_free_mem(phba); + return -ENOMEM; +} + +static int beiscsi_init_sgl_handle(struct beiscsi_hba *phba) +{ + struct be_mem_descriptor *mem_descr_sglh, *mem_descr_sg; + struct sgl_handle *psgl_handle; + struct iscsi_sge *pfrag; + unsigned int arr_index, i, idx; + + phba->io_sgl_hndl_avbl = 0; + phba->eh_sgl_hndl_avbl = 0; + mem_descr_sglh = phba->init_mem; + mem_descr_sglh += HWI_MEM_SGLH; + if (1 == mem_descr_sglh->num_elements) { + phba->io_sgl_hndl_base = kzalloc(sizeof(struct sgl_handle *) * + phba->params.ios_per_ctrl, + GFP_KERNEL); + if (!phba->io_sgl_hndl_base) { + shost_printk(KERN_ERR, phba->shost, + "Mem Alloc Failed. Failing to load\n"); + return -ENOMEM; + } + phba->eh_sgl_hndl_base = kzalloc(sizeof(struct sgl_handle *) * + (phba->params.icds_per_ctrl - + phba->params.ios_per_ctrl), + GFP_KERNEL); + if (!phba->eh_sgl_hndl_base) { + kfree(phba->io_sgl_hndl_base); + shost_printk(KERN_ERR, phba->shost, + "Mem Alloc Failed. Failing to load\n"); + return -ENOMEM; + } + } else { + shost_printk(KERN_ERR, phba->shost, + "HWI_MEM_SGLH is more than one element." + "Failing to load\n"); + return -ENOMEM; + } + + arr_index = 0; + idx = 0; + while (idx < mem_descr_sglh->num_elements) { + psgl_handle = mem_descr_sglh->mem_array[idx].virtual_address; + + for (i = 0; i < (mem_descr_sglh->mem_array[idx].size / + sizeof(struct sgl_handle)); i++) { + if (arr_index < phba->params.ios_per_ctrl) { + phba->io_sgl_hndl_base[arr_index] = psgl_handle; + phba->io_sgl_hndl_avbl++; + arr_index++; + } else { + phba->eh_sgl_hndl_base[arr_index - + phba->params.ios_per_ctrl] = + psgl_handle; + arr_index++; + phba->eh_sgl_hndl_avbl++; + } + psgl_handle++; + } + idx++; + } + SE_DEBUG(DBG_LVL_8, + "phba->io_sgl_hndl_avbl=%d" + "phba->eh_sgl_hndl_avbl=%d \n", + phba->io_sgl_hndl_avbl, + phba->eh_sgl_hndl_avbl); + mem_descr_sg = phba->init_mem; + mem_descr_sg += HWI_MEM_SGE; + SE_DEBUG(DBG_LVL_8, "\n mem_descr_sg->num_elements=%d \n", + mem_descr_sg->num_elements); + arr_index = 0; + idx = 0; + while (idx < mem_descr_sg->num_elements) { + pfrag = mem_descr_sg->mem_array[idx].virtual_address; + + for (i = 0; + i < (mem_descr_sg->mem_array[idx].size) / + (sizeof(struct iscsi_sge) * phba->params.num_sge_per_io); + i++) { + if (arr_index < phba->params.ios_per_ctrl) + psgl_handle = phba->io_sgl_hndl_base[arr_index]; + else + psgl_handle = phba->eh_sgl_hndl_base[arr_index - + phba->params.ios_per_ctrl]; + psgl_handle->pfrag = pfrag; + AMAP_SET_BITS(struct amap_iscsi_sge, addr_hi, pfrag, 0); + AMAP_SET_BITS(struct amap_iscsi_sge, addr_lo, pfrag, 0); + pfrag += phba->params.num_sge_per_io; + psgl_handle->sgl_index = + phba->fw_config.iscsi_cid_start + arr_index++; + } + idx++; + } + phba->io_sgl_free_index = 0; + phba->io_sgl_alloc_index = 0; + phba->eh_sgl_free_index = 0; + phba->eh_sgl_alloc_index = 0; + return 0; +} + +static int hba_setup_cid_tbls(struct beiscsi_hba *phba) +{ + int i, new_cid; + + phba->cid_array = kmalloc(sizeof(void *) * phba->params.cxns_per_ctrl, + GFP_KERNEL); + if (!phba->cid_array) { + shost_printk(KERN_ERR, phba->shost, + "Failed to allocate memory in " + "hba_setup_cid_tbls\n"); + return -ENOMEM; + } + phba->ep_array = kmalloc(sizeof(struct iscsi_endpoint *) * + phba->params.cxns_per_ctrl * 2, GFP_KERNEL); + if (!phba->ep_array) { + shost_printk(KERN_ERR, phba->shost, + "Failed to allocate memory in " + "hba_setup_cid_tbls \n"); + kfree(phba->cid_array); + return -ENOMEM; + } + new_cid = phba->fw_config.iscsi_icd_start; + for (i = 0; i < phba->params.cxns_per_ctrl; i++) { + phba->cid_array[i] = new_cid; + new_cid += 2; + } + phba->avlbl_cids = phba->params.cxns_per_ctrl; + return 0; +} + +static unsigned char hwi_enable_intr(struct beiscsi_hba *phba) +{ + struct be_ctrl_info *ctrl = &phba->ctrl; + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + struct be_queue_info *eq; + u8 __iomem *addr; + u32 reg; + u32 enabled; + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_context = phwi_ctrlr->phwi_ctxt; + + eq = &phwi_context->be_eq.q; + addr = (u8 __iomem *) ((u8 __iomem *) ctrl->pcicfg + + PCICFG_MEMBAR_CTRL_INT_CTRL_OFFSET); + reg = ioread32(addr); + SE_DEBUG(DBG_LVL_8, "reg =x%08x \n", reg); + + enabled = reg & MEMBAR_CTRL_INT_CTRL_HOSTINTR_MASK; + if (!enabled) { + reg |= MEMBAR_CTRL_INT_CTRL_HOSTINTR_MASK; + SE_DEBUG(DBG_LVL_8, "reg =x%08x addr=%p \n", reg, addr); + iowrite32(reg, addr); + SE_DEBUG(DBG_LVL_8, "eq->id=%d \n", eq->id); + + hwi_ring_eq_db(phba, eq->id, 0, 0, 1, 1); + } else + shost_printk(KERN_WARNING, phba->shost, + "In hwi_enable_intr, Not Enabled \n"); + return true; +} + +static void hwi_disable_intr(struct beiscsi_hba *phba) +{ + struct be_ctrl_info *ctrl = &phba->ctrl; + + u8 __iomem *addr = ctrl->pcicfg + PCICFG_MEMBAR_CTRL_INT_CTRL_OFFSET; + u32 reg = ioread32(addr); + + u32 enabled = reg & MEMBAR_CTRL_INT_CTRL_HOSTINTR_MASK; + if (enabled) { + reg &= ~MEMBAR_CTRL_INT_CTRL_HOSTINTR_MASK; + iowrite32(reg, addr); + } else + shost_printk(KERN_WARNING, phba->shost, + "In hwi_disable_intr, Already Disabled \n"); +} + +static int beiscsi_init_port(struct beiscsi_hba *phba) +{ + int ret; + + ret = beiscsi_init_controller(phba); + if (ret < 0) { + shost_printk(KERN_ERR, phba->shost, + "beiscsi_dev_probe - Failed in" + "beiscsi_init_controller \n"); + return ret; + } + ret = beiscsi_init_sgl_handle(phba); + if (ret < 0) { + shost_printk(KERN_ERR, phba->shost, + "beiscsi_dev_probe - Failed in" + "beiscsi_init_sgl_handle \n"); + goto do_cleanup_ctrlr; + } + + if (hba_setup_cid_tbls(phba)) { + shost_printk(KERN_ERR, phba->shost, + "Failed in hba_setup_cid_tbls\n"); + kfree(phba->io_sgl_hndl_base); + kfree(phba->eh_sgl_hndl_base); + goto do_cleanup_ctrlr; + } + + return ret; + +do_cleanup_ctrlr: + hwi_cleanup(phba); + return ret; +} + +static void hwi_purge_eq(struct beiscsi_hba *phba) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + struct be_queue_info *eq; + struct be_eq_entry *eqe = NULL; + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_context = phwi_ctrlr->phwi_ctxt; + eq = &phwi_context->be_eq.q; + eqe = queue_tail_node(eq); + + while (eqe->dw[offsetof(struct amap_eq_entry, valid) / 32] + & EQE_VALID_MASK) { + AMAP_SET_BITS(struct amap_eq_entry, valid, eqe, 0); + queue_tail_inc(eq); + eqe = queue_tail_node(eq); + } +} + +static void beiscsi_clean_port(struct beiscsi_hba *phba) +{ + unsigned char mgmt_status; + + mgmt_status = mgmt_epfw_cleanup(phba, CMD_CONNECTION_CHUTE_0); + if (mgmt_status) + shost_printk(KERN_WARNING, phba->shost, + "mgmt_epfw_cleanup FAILED \n"); + hwi_cleanup(phba); + hwi_purge_eq(phba); + kfree(phba->io_sgl_hndl_base); + kfree(phba->eh_sgl_hndl_base); + kfree(phba->cid_array); + kfree(phba->ep_array); +} + +void +beiscsi_offload_connection(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_offload_params *params) +{ + struct wrb_handle *pwrb_handle; + struct iscsi_target_context_update_wrb *pwrb = NULL; + struct be_mem_descriptor *mem_descr; + struct beiscsi_hba *phba = beiscsi_conn->phba; + u32 doorbell = 0; + + /* + * We can always use 0 here because it is reserved by libiscsi for + * login/startup related tasks. + */ + pwrb_handle = alloc_wrb_handle(phba, beiscsi_conn->beiscsi_conn_cid, 0); + pwrb = (struct iscsi_target_context_update_wrb *)pwrb_handle->pwrb; + memset(pwrb, 0, sizeof(*pwrb)); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, + max_burst_length, pwrb, params->dw[offsetof + (struct amap_beiscsi_offload_params, + max_burst_length) / 32]); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, + max_send_data_segment_length, pwrb, + params->dw[offsetof(struct amap_beiscsi_offload_params, + max_send_data_segment_length) / 32]); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, + first_burst_length, + pwrb, + params->dw[offsetof(struct amap_beiscsi_offload_params, + first_burst_length) / 32]); + + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, erl, pwrb, + (params->dw[offsetof(struct amap_beiscsi_offload_params, + erl) / 32] & OFFLD_PARAMS_ERL)); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, dde, pwrb, + (params->dw[offsetof(struct amap_beiscsi_offload_params, + dde) / 32] & OFFLD_PARAMS_DDE) >> 2); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, hde, pwrb, + (params->dw[offsetof(struct amap_beiscsi_offload_params, + hde) / 32] & OFFLD_PARAMS_HDE) >> 3); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, ir2t, pwrb, + (params->dw[offsetof(struct amap_beiscsi_offload_params, + ir2t) / 32] & OFFLD_PARAMS_IR2T) >> 4); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, imd, pwrb, + (params->dw[offsetof(struct amap_beiscsi_offload_params, + imd) / 32] & OFFLD_PARAMS_IMD) >> 5); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, stat_sn, + pwrb, + (params->dw[offsetof(struct amap_beiscsi_offload_params, + exp_statsn) / 32] + 1)); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, type, pwrb, + 0x7); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, wrb_idx, + pwrb, pwrb_handle->wrb_index); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, ptr2nextwrb, + pwrb, pwrb_handle->nxt_wrb_index); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, + session_state, pwrb, 0); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, compltonack, + pwrb, 1); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, notpredblq, + pwrb, 0); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, mode, pwrb, + 0); + + mem_descr = phba->init_mem; + mem_descr += ISCSI_MEM_GLOBAL_HEADER; + + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, + pad_buffer_addr_hi, pwrb, + mem_descr->mem_array[0].bus_address.u.a32.address_hi); + AMAP_SET_BITS(struct amap_iscsi_target_context_update_wrb, + pad_buffer_addr_lo, pwrb, + mem_descr->mem_array[0].bus_address.u.a32.address_lo); + + be_dws_le_to_cpu(pwrb, sizeof(struct iscsi_target_context_update_wrb)); + + doorbell |= beiscsi_conn->beiscsi_conn_cid & DB_WRB_POST_CID_MASK; + doorbell |= (pwrb_handle->wrb_index & DB_DEF_PDU_WRB_INDEX_MASK) << + DB_DEF_PDU_WRB_INDEX_SHIFT; + doorbell |= 1 << DB_DEF_PDU_NUM_POSTED_SHIFT; + + iowrite32(doorbell, phba->db_va + DB_TXULP0_OFFSET); +} + +static void beiscsi_parse_pdu(struct iscsi_conn *conn, itt_t itt, + int *index, int *age) +{ + *index = be32_to_cpu(itt) >> 16; + if (age) + *age = conn->session->age; +} + +/** + * beiscsi_alloc_pdu - allocates pdu and related resources + * @task: libiscsi task + * @opcode: opcode of pdu for task + * + * This is called with the session lock held. It will allocate + * the wrb and sgl if needed for the command. And it will prep + * the pdu's itt. beiscsi_parse_pdu will later translate + * the pdu itt to the libiscsi task itt. + */ +static int beiscsi_alloc_pdu(struct iscsi_task *task, uint8_t opcode) +{ + struct beiscsi_io_task *io_task = task->dd_data; + struct iscsi_conn *conn = task->conn; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct beiscsi_hba *phba = beiscsi_conn->phba; + struct hwi_wrb_context *pwrb_context; + struct hwi_controller *phwi_ctrlr; + itt_t itt; + struct beiscsi_session *beiscsi_sess = beiscsi_conn->beiscsi_sess; + dma_addr_t paddr; + + io_task->cmd_bhs = pci_pool_alloc(beiscsi_sess->bhs_pool, + GFP_KERNEL, &paddr); + + if (!io_task->cmd_bhs) + return -ENOMEM; + + io_task->bhs_pa.u.a64.address = paddr; + io_task->pwrb_handle = alloc_wrb_handle(phba, + beiscsi_conn->beiscsi_conn_cid, + task->itt); + io_task->pwrb_handle->pio_handle = task; + io_task->conn = beiscsi_conn; + + task->hdr = (struct iscsi_hdr *)&io_task->cmd_bhs->iscsi_hdr; + task->hdr_max = sizeof(struct be_cmd_bhs); + + if (task->sc) { + spin_lock(&phba->io_sgl_lock); + io_task->psgl_handle = alloc_io_sgl_handle(phba); + spin_unlock(&phba->io_sgl_lock); + if (!io_task->psgl_handle) + goto free_hndls; + + } else { + io_task->scsi_cmnd = NULL; + if ((task->hdr->opcode & ISCSI_OPCODE_MASK) == ISCSI_OP_LOGIN) { + if (!beiscsi_conn->login_in_progress) { + spin_lock(&phba->mgmt_sgl_lock); + io_task->psgl_handle = (struct sgl_handle *) + alloc_mgmt_sgl_handle(phba); + spin_unlock(&phba->mgmt_sgl_lock); + if (!io_task->psgl_handle) + goto free_hndls; + + beiscsi_conn->login_in_progress = 1; + beiscsi_conn->plogin_sgl_handle = + io_task->psgl_handle; + } else { + io_task->psgl_handle = + beiscsi_conn->plogin_sgl_handle; + } + } else { + spin_lock(&phba->mgmt_sgl_lock); + io_task->psgl_handle = alloc_mgmt_sgl_handle(phba); + spin_unlock(&phba->mgmt_sgl_lock); + if (!io_task->psgl_handle) + goto free_hndls; + } + } + itt = (itt_t) cpu_to_be32(((unsigned int)task->itt << 16) | + (unsigned int)(io_task->psgl_handle->sgl_index)); + io_task->cmd_bhs->iscsi_hdr.itt = itt; + return 0; + +free_hndls: + phwi_ctrlr = phba->phwi_ctrlr; + pwrb_context = &phwi_ctrlr->wrb_context[beiscsi_conn->beiscsi_conn_cid]; + free_wrb_handle(phba, pwrb_context, io_task->pwrb_handle); + io_task->pwrb_handle = NULL; + pci_pool_free(beiscsi_sess->bhs_pool, io_task->cmd_bhs, + io_task->bhs_pa.u.a64.address); + SE_DEBUG(DBG_LVL_1, "Alloc of SGL_ICD Failed \n"); + return -ENOMEM; +} + +static void beiscsi_cleanup_task(struct iscsi_task *task) +{ + struct beiscsi_io_task *io_task = task->dd_data; + struct iscsi_conn *conn = task->conn; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct beiscsi_hba *phba = beiscsi_conn->phba; + struct beiscsi_session *beiscsi_sess = beiscsi_conn->beiscsi_sess; + struct hwi_wrb_context *pwrb_context; + struct hwi_controller *phwi_ctrlr; + + phwi_ctrlr = phba->phwi_ctrlr; + pwrb_context = &phwi_ctrlr->wrb_context[beiscsi_conn->beiscsi_conn_cid]; + if (io_task->pwrb_handle) { + free_wrb_handle(phba, pwrb_context, io_task->pwrb_handle); + io_task->pwrb_handle = NULL; + } + + if (io_task->cmd_bhs) { + pci_pool_free(beiscsi_sess->bhs_pool, io_task->cmd_bhs, + io_task->bhs_pa.u.a64.address); + } + + if (task->sc) { + if (io_task->psgl_handle) { + spin_lock(&phba->io_sgl_lock); + free_io_sgl_handle(phba, io_task->psgl_handle); + spin_unlock(&phba->io_sgl_lock); + io_task->psgl_handle = NULL; + } + } else { + if ((task->hdr->opcode & ISCSI_OPCODE_MASK) == ISCSI_OP_LOGIN) + return; + if (io_task->psgl_handle) { + spin_lock(&phba->mgmt_sgl_lock); + free_mgmt_sgl_handle(phba, io_task->psgl_handle); + spin_unlock(&phba->mgmt_sgl_lock); + io_task->psgl_handle = NULL; + } + } +} + +static int beiscsi_iotask(struct iscsi_task *task, struct scatterlist *sg, + unsigned int num_sg, unsigned int xferlen, + unsigned int writedir) +{ + + struct beiscsi_io_task *io_task = task->dd_data; + struct iscsi_conn *conn = task->conn; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct beiscsi_hba *phba = beiscsi_conn->phba; + struct iscsi_wrb *pwrb = NULL; + unsigned int doorbell = 0; + + pwrb = io_task->pwrb_handle->pwrb; + io_task->cmd_bhs->iscsi_hdr.exp_statsn = 0; + io_task->bhs_len = sizeof(struct be_cmd_bhs); + + if (writedir) { + SE_DEBUG(DBG_LVL_4, " WRITE Command \t"); + memset(&io_task->cmd_bhs->iscsi_data_pdu, 0, 48); + AMAP_SET_BITS(struct amap_pdu_data_out, itt, + &io_task->cmd_bhs->iscsi_data_pdu, + (unsigned int)io_task->cmd_bhs->iscsi_hdr.itt); + AMAP_SET_BITS(struct amap_pdu_data_out, opcode, + &io_task->cmd_bhs->iscsi_data_pdu, + ISCSI_OPCODE_SCSI_DATA_OUT); + AMAP_SET_BITS(struct amap_pdu_data_out, final_bit, + &io_task->cmd_bhs->iscsi_data_pdu, 1); + AMAP_SET_BITS(struct amap_iscsi_wrb, type, pwrb, INI_WR_CMD); + AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 1); + } else { + SE_DEBUG(DBG_LVL_4, "READ Command \t"); + AMAP_SET_BITS(struct amap_iscsi_wrb, type, pwrb, INI_RD_CMD); + AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 0); + } + memcpy(&io_task->cmd_bhs->iscsi_data_pdu. + dw[offsetof(struct amap_pdu_data_out, lun) / 32], + io_task->cmd_bhs->iscsi_hdr.lun, sizeof(struct scsi_lun)); + + AMAP_SET_BITS(struct amap_iscsi_wrb, lun, pwrb, + cpu_to_be16((unsigned short)io_task->cmd_bhs->iscsi_hdr. + lun[0])); + AMAP_SET_BITS(struct amap_iscsi_wrb, r2t_exp_dtl, pwrb, xferlen); + AMAP_SET_BITS(struct amap_iscsi_wrb, wrb_idx, pwrb, + io_task->pwrb_handle->wrb_index); + AMAP_SET_BITS(struct amap_iscsi_wrb, cmdsn_itt, pwrb, + be32_to_cpu(task->cmdsn)); + AMAP_SET_BITS(struct amap_iscsi_wrb, sgl_icd_idx, pwrb, + io_task->psgl_handle->sgl_index); + + hwi_write_sgl(pwrb, sg, num_sg, io_task); + + AMAP_SET_BITS(struct amap_iscsi_wrb, ptr2nextwrb, pwrb, + io_task->pwrb_handle->nxt_wrb_index); + be_dws_le_to_cpu(pwrb, sizeof(struct iscsi_wrb)); + + doorbell |= beiscsi_conn->beiscsi_conn_cid & DB_WRB_POST_CID_MASK; + doorbell |= (io_task->pwrb_handle->wrb_index & + DB_DEF_PDU_WRB_INDEX_MASK) << DB_DEF_PDU_WRB_INDEX_SHIFT; + doorbell |= 1 << DB_DEF_PDU_NUM_POSTED_SHIFT; + + iowrite32(doorbell, phba->db_va + DB_TXULP0_OFFSET); + return 0; +} + +static int beiscsi_mtask(struct iscsi_task *task) +{ + struct beiscsi_io_task *aborted_io_task, *io_task = task->dd_data; + struct iscsi_conn *conn = task->conn; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct beiscsi_hba *phba = beiscsi_conn->phba; + struct iscsi_wrb *pwrb = NULL; + unsigned int doorbell = 0; + struct iscsi_task *aborted_task; + + pwrb = io_task->pwrb_handle->pwrb; + AMAP_SET_BITS(struct amap_iscsi_wrb, cmdsn_itt, pwrb, + be32_to_cpu(task->cmdsn)); + AMAP_SET_BITS(struct amap_iscsi_wrb, wrb_idx, pwrb, + io_task->pwrb_handle->wrb_index); + AMAP_SET_BITS(struct amap_iscsi_wrb, sgl_icd_idx, pwrb, + io_task->psgl_handle->sgl_index); + + switch (task->hdr->opcode & ISCSI_OPCODE_MASK) { + case ISCSI_OP_LOGIN: + AMAP_SET_BITS(struct amap_iscsi_wrb, type, pwrb, TGT_DM_CMD); + AMAP_SET_BITS(struct amap_iscsi_wrb, dmsg, pwrb, 0); + AMAP_SET_BITS(struct amap_iscsi_wrb, cmdsn_itt, pwrb, 1); + hwi_write_buffer(pwrb, task); + break; + case ISCSI_OP_NOOP_OUT: + AMAP_SET_BITS(struct amap_iscsi_wrb, type, pwrb, INI_RD_CMD); + hwi_write_buffer(pwrb, task); + break; + case ISCSI_OP_TEXT: + AMAP_SET_BITS(struct amap_iscsi_wrb, type, pwrb, INI_WR_CMD); + AMAP_SET_BITS(struct amap_iscsi_wrb, dsp, pwrb, 1); + hwi_write_buffer(pwrb, task); + break; + case ISCSI_OP_SCSI_TMFUNC: + aborted_task = iscsi_itt_to_task(conn, + ((struct iscsi_tm *)task->hdr)->rtt); + if (!aborted_task) + return 0; + aborted_io_task = aborted_task->dd_data; + if (!aborted_io_task->scsi_cmnd) + return 0; + + mgmt_invalidate_icds(phba, + aborted_io_task->psgl_handle->sgl_index, + beiscsi_conn->beiscsi_conn_cid); + AMAP_SET_BITS(struct amap_iscsi_wrb, type, pwrb, INI_TMF_CMD); + AMAP_SET_BITS(struct amap_iscsi_wrb, dmsg, pwrb, 0); + hwi_write_buffer(pwrb, task); + break; + case ISCSI_OP_LOGOUT: + AMAP_SET_BITS(struct amap_iscsi_wrb, dmsg, pwrb, 0); + AMAP_SET_BITS(struct amap_iscsi_wrb, type, pwrb, + HWH_TYPE_LOGOUT); + hwi_write_buffer(pwrb, task); + break; + + default: + SE_DEBUG(DBG_LVL_1, "opcode =%d Not supported \n", + task->hdr->opcode & ISCSI_OPCODE_MASK); + return -EINVAL; + } + + AMAP_SET_BITS(struct amap_iscsi_wrb, r2t_exp_dtl, pwrb, + be32_to_cpu(task->data_count)); + AMAP_SET_BITS(struct amap_iscsi_wrb, ptr2nextwrb, pwrb, + io_task->pwrb_handle->nxt_wrb_index); + be_dws_le_to_cpu(pwrb, sizeof(struct iscsi_wrb)); + + doorbell |= beiscsi_conn->beiscsi_conn_cid & DB_WRB_POST_CID_MASK; + doorbell |= (io_task->pwrb_handle->wrb_index & + DB_DEF_PDU_WRB_INDEX_MASK) << DB_DEF_PDU_WRB_INDEX_SHIFT; + doorbell |= 1 << DB_DEF_PDU_NUM_POSTED_SHIFT; + iowrite32(doorbell, phba->db_va + DB_TXULP0_OFFSET); + return 0; +} + +static int beiscsi_task_xmit(struct iscsi_task *task) +{ + struct iscsi_conn *conn = task->conn; + struct beiscsi_io_task *io_task = task->dd_data; + struct scsi_cmnd *sc = task->sc; + struct beiscsi_conn *beiscsi_conn = conn->dd_data; + struct scatterlist *sg; + int num_sg; + unsigned int writedir = 0, xferlen = 0; + + SE_DEBUG(DBG_LVL_4, "\n cid=%d In beiscsi_task_xmit task=%p conn=%p \t" + "beiscsi_conn=%p \n", beiscsi_conn->beiscsi_conn_cid, + task, conn, beiscsi_conn); + if (!sc) + return beiscsi_mtask(task); + + io_task->scsi_cmnd = sc; + num_sg = scsi_dma_map(sc); + if (num_sg < 0) { + SE_DEBUG(DBG_LVL_1, " scsi_dma_map Failed\n") + return num_sg; + } + SE_DEBUG(DBG_LVL_4, "xferlen=0x%08x scmd=%p num_sg=%d sernum=%lu\n", + (scsi_bufflen(sc)), sc, num_sg, sc->serial_number); + xferlen = scsi_bufflen(sc); + sg = scsi_sglist(sc); + if (sc->sc_data_direction == DMA_TO_DEVICE) { + writedir = 1; + SE_DEBUG(DBG_LVL_4, "task->imm_count=0x%08x \n", + task->imm_count); + } else + writedir = 0; + return beiscsi_iotask(task, sg, num_sg, xferlen, writedir); +} + +static void beiscsi_remove(struct pci_dev *pcidev) +{ + struct beiscsi_hba *phba = NULL; + + phba = (struct beiscsi_hba *)pci_get_drvdata(pcidev); + if (!phba) { + dev_err(&pcidev->dev, "beiscsi_remove called with no phba \n"); + return; + } + + hwi_disable_intr(phba); + if (phba->pcidev->irq) + free_irq(phba->pcidev->irq, phba); + destroy_workqueue(phba->wq); + if (blk_iopoll_enabled) + blk_iopoll_disable(&phba->iopoll); + + beiscsi_clean_port(phba); + beiscsi_free_mem(phba); + beiscsi_unmap_pci_function(phba); + pci_free_consistent(phba->pcidev, + phba->ctrl.mbox_mem_alloced.size, + phba->ctrl.mbox_mem_alloced.va, + phba->ctrl.mbox_mem_alloced.dma); + iscsi_host_remove(phba->shost); + pci_dev_put(phba->pcidev); + iscsi_host_free(phba->shost); +} + +static int __devinit beiscsi_dev_probe(struct pci_dev *pcidev, + const struct pci_device_id *id) +{ + struct beiscsi_hba *phba = NULL; + int ret; + + ret = beiscsi_enable_pci(pcidev); + if (ret < 0) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_dev_probe-" + "Failed to enable pci device \n"); + return ret; + } + + phba = beiscsi_hba_alloc(pcidev); + if (!phba) { + dev_err(&pcidev->dev, "beiscsi_dev_probe-" + " Failed in beiscsi_hba_alloc \n"); + goto disable_pci; + } + + pci_set_drvdata(pcidev, phba); + ret = be_ctrl_init(phba, pcidev); + if (ret) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_dev_probe-" + "Failed in be_ctrl_init\n"); + goto hba_free; + } + + spin_lock_init(&phba->io_sgl_lock); + spin_lock_init(&phba->mgmt_sgl_lock); + spin_lock_init(&phba->isr_lock); + beiscsi_get_params(phba); + ret = beiscsi_init_port(phba); + if (ret < 0) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_dev_probe-" + "Failed in beiscsi_init_port\n"); + goto free_port; + } + + snprintf(phba->wq_name, sizeof(phba->wq_name), "beiscsi_q_irq%u", + phba->shost->host_no); + phba->wq = create_singlethread_workqueue(phba->wq_name); + if (!phba->wq) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_dev_probe-" + "Failed to allocate work queue\n"); + goto free_twq; + } + + INIT_WORK(&phba->work_cqs, beiscsi_process_all_cqs); + + if (blk_iopoll_enabled) { + blk_iopoll_init(&phba->iopoll, be_iopoll_budget, be_iopoll); + blk_iopoll_enable(&phba->iopoll); + } + + ret = beiscsi_init_irqs(phba); + if (ret < 0) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_dev_probe-" + "Failed to beiscsi_init_irqs\n"); + goto free_blkenbld; + } + ret = hwi_enable_intr(phba); + if (ret < 0) { + shost_printk(KERN_ERR, phba->shost, "beiscsi_dev_probe-" + "Failed to hwi_enable_intr\n"); + goto free_ctrlr; + } + + SE_DEBUG(DBG_LVL_8, "\n\n\n SUCCESS - DRIVER LOADED \n\n\n"); + return 0; + +free_ctrlr: + if (phba->pcidev->irq) + free_irq(phba->pcidev->irq, phba); +free_blkenbld: + destroy_workqueue(phba->wq); + if (blk_iopoll_enabled) + blk_iopoll_disable(&phba->iopoll); +free_twq: + beiscsi_clean_port(phba); + beiscsi_free_mem(phba); +free_port: + pci_free_consistent(phba->pcidev, + phba->ctrl.mbox_mem_alloced.size, + phba->ctrl.mbox_mem_alloced.va, + phba->ctrl.mbox_mem_alloced.dma); + beiscsi_unmap_pci_function(phba); +hba_free: + iscsi_host_remove(phba->shost); + pci_dev_put(phba->pcidev); + iscsi_host_free(phba->shost); +disable_pci: + pci_disable_device(pcidev); + return ret; +} + +struct iscsi_transport beiscsi_iscsi_transport = { + .owner = THIS_MODULE, + .name = DRV_NAME, + .caps = CAP_RECOVERY_L0 | CAP_HDRDGST | + CAP_MULTI_R2T | CAP_DATADGST | CAP_DATA_PATH_OFFLOAD, + .param_mask = ISCSI_MAX_RECV_DLENGTH | + ISCSI_MAX_XMIT_DLENGTH | + ISCSI_HDRDGST_EN | + ISCSI_DATADGST_EN | + ISCSI_INITIAL_R2T_EN | + ISCSI_MAX_R2T | + ISCSI_IMM_DATA_EN | + ISCSI_FIRST_BURST | + ISCSI_MAX_BURST | + ISCSI_PDU_INORDER_EN | + ISCSI_DATASEQ_INORDER_EN | + ISCSI_ERL | + ISCSI_CONN_PORT | + ISCSI_CONN_ADDRESS | + ISCSI_EXP_STATSN | + ISCSI_PERSISTENT_PORT | + ISCSI_PERSISTENT_ADDRESS | + ISCSI_TARGET_NAME | ISCSI_TPGT | + ISCSI_USERNAME | ISCSI_PASSWORD | + ISCSI_USERNAME_IN | ISCSI_PASSWORD_IN | + ISCSI_FAST_ABORT | ISCSI_ABORT_TMO | + ISCSI_LU_RESET_TMO | + ISCSI_PING_TMO | ISCSI_RECV_TMO | + ISCSI_IFACE_NAME | ISCSI_INITIATOR_NAME, + .host_param_mask = ISCSI_HOST_HWADDRESS | ISCSI_HOST_IPADDRESS | + ISCSI_HOST_INITIATOR_NAME, + .create_session = beiscsi_session_create, + .destroy_session = beiscsi_session_destroy, + .create_conn = beiscsi_conn_create, + .bind_conn = beiscsi_conn_bind, + .destroy_conn = iscsi_conn_teardown, + .set_param = beiscsi_set_param, + .get_conn_param = beiscsi_conn_get_param, + .get_session_param = iscsi_session_get_param, + .get_host_param = beiscsi_get_host_param, + .start_conn = beiscsi_conn_start, + .stop_conn = beiscsi_conn_stop, + .send_pdu = iscsi_conn_send_pdu, + .xmit_task = beiscsi_task_xmit, + .cleanup_task = beiscsi_cleanup_task, + .alloc_pdu = beiscsi_alloc_pdu, + .parse_pdu_itt = beiscsi_parse_pdu, + .get_stats = beiscsi_conn_get_stats, + .ep_connect = beiscsi_ep_connect, + .ep_poll = beiscsi_ep_poll, + .ep_disconnect = beiscsi_ep_disconnect, + .session_recovery_timedout = iscsi_session_recovery_timedout, +}; + +static struct pci_driver beiscsi_pci_driver = { + .name = DRV_NAME, + .probe = beiscsi_dev_probe, + .remove = beiscsi_remove, + .id_table = beiscsi_pci_id_table +}; + +static int __init beiscsi_module_init(void) +{ + int ret; + + beiscsi_scsi_transport = + iscsi_register_transport(&beiscsi_iscsi_transport); + if (!beiscsi_scsi_transport) { + SE_DEBUG(DBG_LVL_1, + "beiscsi_module_init - Unable to register beiscsi" + "transport.\n"); + ret = -ENOMEM; + } + SE_DEBUG(DBG_LVL_8, "In beiscsi_module_init, tt=%p \n", + &beiscsi_iscsi_transport); + + ret = pci_register_driver(&beiscsi_pci_driver); + if (ret) { + SE_DEBUG(DBG_LVL_1, + "beiscsi_module_init - Unable to register" + "beiscsi pci driver.\n"); + goto unregister_iscsi_transport; + } + return 0; + +unregister_iscsi_transport: + iscsi_unregister_transport(&beiscsi_iscsi_transport); + return ret; +} + +static void __exit beiscsi_module_exit(void) +{ + pci_unregister_driver(&beiscsi_pci_driver); + iscsi_unregister_transport(&beiscsi_iscsi_transport); +} + +module_init(beiscsi_module_init); +module_exit(beiscsi_module_exit); diff --git a/drivers/scsi/be2iscsi/be_main.h b/drivers/scsi/be2iscsi/be_main.h new file mode 100644 index 000000000000..53c9b70ac7ac --- /dev/null +++ b/drivers/scsi/be2iscsi/be_main.h @@ -0,0 +1,837 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Written by: Jayamohan Kallickal (jayamohank@serverengines.com) + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + * + */ + +#ifndef _BEISCSI_MAIN_ +#define _BEISCSI_MAIN_ + + +#include <linux/kernel.h> +#include <linux/pci.h> +#include <linux/in.h> +#include <linux/blk-iopoll.h> +#include <scsi/scsi.h> +#include <scsi/scsi_cmnd.h> +#include <scsi/scsi_device.h> +#include <scsi/scsi_host.h> +#include <scsi/iscsi_proto.h> +#include <scsi/libiscsi.h> +#include <scsi/scsi_transport_iscsi.h> + +#include "be.h" + + + +#define DRV_NAME "be2iscsi" +#define BUILD_STR "2.0.527.0" + +#define BE_NAME "ServerEngines BladeEngine2" \ + "Linux iSCSI Driver version" BUILD_STR +#define DRV_DESC BE_NAME " " "Driver" + +#define BE_VENDOR_ID 0x19A2 +#define BE_DEVICE_ID1 0x212 +#define OC_DEVICE_ID1 0x702 +#define OC_DEVICE_ID2 0x703 + +#define BE2_MAX_SESSIONS 64 +#define BE2_CMDS_PER_CXN 128 +#define BE2_LOGOUTS BE2_MAX_SESSIONS +#define BE2_TMFS 16 +#define BE2_NOPOUT_REQ 16 +#define BE2_ASYNCPDUS BE2_MAX_SESSIONS +#define BE2_MAX_ICDS 2048 +#define BE2_SGE 32 +#define BE2_DEFPDU_HDR_SZ 64 +#define BE2_DEFPDU_DATA_SZ 8192 +#define BE2_IO_DEPTH \ + (BE2_MAX_ICDS / 2 - (BE2_LOGOUTS + BE2_TMFS + BE2_NOPOUT_REQ)) + +#define BEISCSI_SGLIST_ELEMENTS BE2_SGE + +#define BEISCSI_MAX_CMNDS 1024 /* Max IO's per Ctrlr sht->can_queue */ +#define BEISCSI_CMD_PER_LUN 128 /* scsi_host->cmd_per_lun */ +#define BEISCSI_MAX_SECTORS 2048 /* scsi_host->max_sectors */ + +#define BEISCSI_MAX_CMD_LEN 16 /* scsi_host->max_cmd_len */ +#define BEISCSI_NUM_MAX_LUN 256 /* scsi_host->max_lun */ +#define BEISCSI_NUM_DEVICES_SUPPORTED 0x01 +#define BEISCSI_MAX_FRAGS_INIT 192 +#define BE_NUM_MSIX_ENTRIES 1 +#define MPU_EP_SEMAPHORE 0xac + +#define BE_SENSE_INFO_SIZE 258 +#define BE_ISCSI_PDU_HEADER_SIZE 64 +#define BE_MIN_MEM_SIZE 16384 + +#define IIOC_SCSI_DATA 0x05 /* Write Operation */ + +#define DBG_LVL 0x00000001 +#define DBG_LVL_1 0x00000001 +#define DBG_LVL_2 0x00000002 +#define DBG_LVL_3 0x00000004 +#define DBG_LVL_4 0x00000008 +#define DBG_LVL_5 0x00000010 +#define DBG_LVL_6 0x00000020 +#define DBG_LVL_7 0x00000040 +#define DBG_LVL_8 0x00000080 + +#define SE_DEBUG(debug_mask, fmt, args...) \ +do { \ + if (debug_mask & DBG_LVL) { \ + printk(KERN_ERR "(%s():%d):", __func__, __LINE__);\ + printk(fmt, ##args); \ + } \ +} while (0); + +/** + * hardware needs the async PDU buffers to be posted in multiples of 8 + * So have atleast 8 of them by default + */ + +#define HWI_GET_ASYNC_PDU_CTX(phwi) (phwi->phwi_ctxt->pasync_ctx) + +/********* Memory BAR register ************/ +#define PCICFG_MEMBAR_CTRL_INT_CTRL_OFFSET 0xfc +/** + * Host Interrupt Enable, if set interrupts are enabled although "PCI Interrupt + * Disable" may still globally block interrupts in addition to individual + * interrupt masks; a mechanism for the device driver to block all interrupts + * atomically without having to arbitrate for the PCI Interrupt Disable bit + * with the OS. + */ +#define MEMBAR_CTRL_INT_CTRL_HOSTINTR_MASK (1 << 29) /* bit 29 */ + +/********* ISR0 Register offset **********/ +#define CEV_ISR0_OFFSET 0xC18 +#define CEV_ISR_SIZE 4 + +/** + * Macros for reading/writing a protection domain or CSR registers + * in BladeEngine. + */ + +#define DB_TXULP0_OFFSET 0x40 +#define DB_RXULP0_OFFSET 0xA0 +/********* Event Q door bell *************/ +#define DB_EQ_OFFSET DB_CQ_OFFSET +#define DB_EQ_RING_ID_MASK 0x1FF /* bits 0 - 8 */ +/* Clear the interrupt for this eq */ +#define DB_EQ_CLR_SHIFT (9) /* bit 9 */ +/* Must be 1 */ +#define DB_EQ_EVNT_SHIFT (10) /* bit 10 */ +/* Number of event entries processed */ +#define DB_EQ_NUM_POPPED_SHIFT (16) /* bits 16 - 28 */ +/* Rearm bit */ +#define DB_EQ_REARM_SHIFT (29) /* bit 29 */ + +/********* Compl Q door bell *************/ +#define DB_CQ_OFFSET 0x120 +#define DB_CQ_RING_ID_MASK 0x3FF /* bits 0 - 9 */ +/* Number of event entries processed */ +#define DB_CQ_NUM_POPPED_SHIFT (16) /* bits 16 - 28 */ +/* Rearm bit */ +#define DB_CQ_REARM_SHIFT (29) /* bit 29 */ + +#define GET_HWI_CONTROLLER_WS(pc) (pc->phwi_ctrlr) +#define HWI_GET_DEF_BUFQ_ID(pc) (((struct hwi_controller *)\ + (GET_HWI_CONTROLLER_WS(pc)))->default_pdu_data.id) +#define HWI_GET_DEF_HDRQ_ID(pc) (((struct hwi_controller *)\ + (GET_HWI_CONTROLLER_WS(pc)))->default_pdu_hdr.id) + +#define PAGES_REQUIRED(x) \ + ((x < PAGE_SIZE) ? 1 : ((x + PAGE_SIZE - 1) / PAGE_SIZE)) + +enum be_mem_enum { + HWI_MEM_ADDN_CONTEXT, + HWI_MEM_CQ, + HWI_MEM_EQ, + HWI_MEM_WRB, + HWI_MEM_WRBH, + HWI_MEM_SGLH, /* 5 */ + HWI_MEM_SGE, + HWI_MEM_ASYNC_HEADER_BUF, + HWI_MEM_ASYNC_DATA_BUF, + HWI_MEM_ASYNC_HEADER_RING, + HWI_MEM_ASYNC_DATA_RING, /* 10 */ + HWI_MEM_ASYNC_HEADER_HANDLE, + HWI_MEM_ASYNC_DATA_HANDLE, + HWI_MEM_ASYNC_PDU_CONTEXT, + ISCSI_MEM_GLOBAL_HEADER, + SE_MEM_MAX /* 15 */ +}; + +struct be_bus_address32 { + unsigned int address_lo; + unsigned int address_hi; +}; + +struct be_bus_address64 { + unsigned long long address; +}; + +struct be_bus_address { + union { + struct be_bus_address32 a32; + struct be_bus_address64 a64; + } u; +}; + +struct mem_array { + struct be_bus_address bus_address; /* Bus address of location */ + void *virtual_address; /* virtual address to the location */ + unsigned int size; /* Size required by memory block */ +}; + +struct be_mem_descriptor { + unsigned int index; /* Index of this memory parameter */ + unsigned int category; /* type indicates cached/non-cached */ + unsigned int num_elements; /* number of elements in this + * descriptor + */ + unsigned int alignment_mask; /* Alignment mask for this block */ + unsigned int size_in_bytes; /* Size required by memory block */ + struct mem_array *mem_array; +}; + +struct sgl_handle { + unsigned int sgl_index; + struct iscsi_sge *pfrag; +}; + +struct hba_parameters { + unsigned int ios_per_ctrl; + unsigned int cxns_per_ctrl; + unsigned int asyncpdus_per_ctrl; + unsigned int icds_per_ctrl; + unsigned int num_sge_per_io; + unsigned int defpdu_hdr_sz; + unsigned int defpdu_data_sz; + unsigned int num_cq_entries; + unsigned int num_eq_entries; + unsigned int wrbs_per_cxn; + unsigned int crashmode; + unsigned int hba_num; + + unsigned int mgmt_ws_sz; + unsigned int hwi_ws_sz; + + unsigned int eto; + unsigned int ldto; + + unsigned int dbg_flags; + unsigned int num_cxn; + + unsigned int eq_timer; + /** + * These are calculated from other params. They're here + * for debug purposes + */ + unsigned int num_mcc_pages; + unsigned int num_mcc_cq_pages; + unsigned int num_cq_pages; + unsigned int num_eq_pages; + + unsigned int num_async_pdu_buf_pages; + unsigned int num_async_pdu_buf_sgl_pages; + unsigned int num_async_pdu_buf_cq_pages; + + unsigned int num_async_pdu_hdr_pages; + unsigned int num_async_pdu_hdr_sgl_pages; + unsigned int num_async_pdu_hdr_cq_pages; + + unsigned int num_sge; +}; + +struct beiscsi_hba { + struct hba_parameters params; + struct hwi_controller *phwi_ctrlr; + unsigned int mem_req[SE_MEM_MAX]; + /* PCI BAR mapped addresses */ + u8 __iomem *csr_va; /* CSR */ + u8 __iomem *db_va; /* Door Bell */ + u8 __iomem *pci_va; /* PCI Config */ + struct be_bus_address csr_pa; /* CSR */ + struct be_bus_address db_pa; /* CSR */ + struct be_bus_address pci_pa; /* CSR */ + /* PCI representation of our HBA */ + struct pci_dev *pcidev; + unsigned int state; + unsigned short asic_revision; + struct blk_iopoll iopoll; + struct be_mem_descriptor *init_mem; + + unsigned short io_sgl_alloc_index; + unsigned short io_sgl_free_index; + unsigned short io_sgl_hndl_avbl; + struct sgl_handle **io_sgl_hndl_base; + + unsigned short eh_sgl_alloc_index; + unsigned short eh_sgl_free_index; + unsigned short eh_sgl_hndl_avbl; + struct sgl_handle **eh_sgl_hndl_base; + spinlock_t io_sgl_lock; + spinlock_t mgmt_sgl_lock; + spinlock_t isr_lock; + unsigned int age; + unsigned short avlbl_cids; + unsigned short cid_alloc; + unsigned short cid_free; + struct beiscsi_conn *conn_table[BE2_MAX_SESSIONS * 2]; + struct list_head hba_queue; + unsigned short *cid_array; + struct iscsi_endpoint **ep_array; + struct Scsi_Host *shost; + struct { + /** + * group together since they are used most frequently + * for cid to cri conversion + */ + unsigned int iscsi_cid_start; + unsigned int phys_port; + + unsigned int isr_offset; + unsigned int iscsi_icd_start; + unsigned int iscsi_cid_count; + unsigned int iscsi_icd_count; + unsigned int pci_function; + + unsigned short cid_alloc; + unsigned short cid_free; + unsigned short avlbl_cids; + spinlock_t cid_lock; + } fw_config; + + u8 mac_address[ETH_ALEN]; + unsigned short todo_cq; + unsigned short todo_mcc_cq; + char wq_name[20]; + struct workqueue_struct *wq; /* The actuak work queue */ + struct work_struct work_cqs; /* The work being queued */ + struct be_ctrl_info ctrl; +}; + +struct beiscsi_session { + struct pci_pool *bhs_pool; +}; + +/** + * struct beiscsi_conn - iscsi connection structure + */ +struct beiscsi_conn { + struct iscsi_conn *conn; + struct beiscsi_hba *phba; + u32 exp_statsn; + u32 beiscsi_conn_cid; + struct beiscsi_endpoint *ep; + unsigned short login_in_progress; + struct sgl_handle *plogin_sgl_handle; + struct beiscsi_session *beiscsi_sess; +}; + +/* This structure is used by the chip */ +struct pdu_data_out { + u32 dw[12]; +}; +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_pdu_data_out { + u8 opcode[6]; /* opcode */ + u8 rsvd0[2]; /* should be 0 */ + u8 rsvd1[7]; + u8 final_bit; /* F bit */ + u8 rsvd2[16]; + u8 ahs_length[8]; /* no AHS */ + u8 data_len_hi[8]; + u8 data_len_lo[16]; /* DataSegmentLength */ + u8 lun[64]; + u8 itt[32]; /* ITT; initiator task tag */ + u8 ttt[32]; /* TTT; valid for R2T or 0xffffffff */ + u8 rsvd3[32]; + u8 exp_stat_sn[32]; + u8 rsvd4[32]; + u8 data_sn[32]; + u8 buffer_offset[32]; + u8 rsvd5[32]; +}; + +struct be_cmd_bhs { + struct iscsi_cmd iscsi_hdr; + unsigned char pad1[16]; + struct pdu_data_out iscsi_data_pdu; + unsigned char pad2[BE_SENSE_INFO_SIZE - + sizeof(struct pdu_data_out)]; +}; + +struct beiscsi_io_task { + struct wrb_handle *pwrb_handle; + struct sgl_handle *psgl_handle; + struct beiscsi_conn *conn; + struct scsi_cmnd *scsi_cmnd; + unsigned int cmd_sn; + unsigned int flags; + unsigned short cid; + unsigned short header_len; + + struct be_cmd_bhs *cmd_bhs; + struct be_bus_address bhs_pa; + unsigned short bhs_len; +}; + +struct be_nonio_bhs { + struct iscsi_hdr iscsi_hdr; + unsigned char pad1[16]; + struct pdu_data_out iscsi_data_pdu; + unsigned char pad2[BE_SENSE_INFO_SIZE - + sizeof(struct pdu_data_out)]; +}; + +struct be_status_bhs { + struct iscsi_cmd iscsi_hdr; + unsigned char pad1[16]; + /** + * The plus 2 below is to hold the sense info length that gets + * DMA'ed by RxULP + */ + unsigned char sense_info[BE_SENSE_INFO_SIZE]; +}; + +struct iscsi_sge { + u32 dw[4]; +}; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_iscsi_sge { + u8 addr_hi[32]; + u8 addr_lo[32]; + u8 sge_offset[22]; /* DWORD 2 */ + u8 rsvd0[9]; /* DWORD 2 */ + u8 last_sge; /* DWORD 2 */ + u8 len[17]; /* DWORD 3 */ + u8 rsvd1[15]; /* DWORD 3 */ +}; + +struct beiscsi_offload_params { + u32 dw[5]; +}; + +#define OFFLD_PARAMS_ERL 0x00000003 +#define OFFLD_PARAMS_DDE 0x00000004 +#define OFFLD_PARAMS_HDE 0x00000008 +#define OFFLD_PARAMS_IR2T 0x00000010 +#define OFFLD_PARAMS_IMD 0x00000020 + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_beiscsi_offload_params { + u8 max_burst_length[32]; + u8 max_send_data_segment_length[32]; + u8 first_burst_length[32]; + u8 erl[2]; + u8 dde[1]; + u8 hde[1]; + u8 ir2t[1]; + u8 imd[1]; + u8 pad[26]; + u8 exp_statsn[32]; +}; + +/* void hwi_complete_drvr_msgs(struct beiscsi_conn *beiscsi_conn, + struct beiscsi_hba *phba, struct sol_cqe *psol);*/ + +struct async_pdu_handle { + struct list_head link; + struct be_bus_address pa; + void *pbuffer; + unsigned int consumed; + unsigned char index; + unsigned char is_header; + unsigned short cri; + unsigned long buffer_len; +}; + +struct hwi_async_entry { + struct { + unsigned char hdr_received; + unsigned char hdr_len; + unsigned short bytes_received; + unsigned int bytes_needed; + struct list_head list; + } wait_queue; + + struct list_head header_busy_list; + struct list_head data_busy_list; +}; + +#define BE_MIN_ASYNC_ENTRIES 128 + +struct hwi_async_pdu_context { + struct { + struct be_bus_address pa_base; + void *va_base; + void *ring_base; + struct async_pdu_handle *handle_base; + + unsigned int host_write_ptr; + unsigned int ep_read_ptr; + unsigned int writables; + + unsigned int free_entries; + unsigned int busy_entries; + unsigned int buffer_size; + unsigned int num_entries; + + struct list_head free_list; + } async_header; + + struct { + struct be_bus_address pa_base; + void *va_base; + void *ring_base; + struct async_pdu_handle *handle_base; + + unsigned int host_write_ptr; + unsigned int ep_read_ptr; + unsigned int writables; + + unsigned int free_entries; + unsigned int busy_entries; + unsigned int buffer_size; + struct list_head free_list; + unsigned int num_entries; + } async_data; + + /** + * This is a varying size list! Do not add anything + * after this entry!! + */ + struct hwi_async_entry async_entry[BE_MIN_ASYNC_ENTRIES]; +}; + +#define PDUCQE_CODE_MASK 0x0000003F +#define PDUCQE_DPL_MASK 0xFFFF0000 +#define PDUCQE_INDEX_MASK 0x0000FFFF + +struct i_t_dpdu_cqe { + u32 dw[4]; +} __packed; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_i_t_dpdu_cqe { + u8 db_addr_hi[32]; + u8 db_addr_lo[32]; + u8 code[6]; + u8 cid[10]; + u8 dpl[16]; + u8 index[16]; + u8 num_cons[10]; + u8 rsvd0[4]; + u8 final; + u8 valid; +} __packed; + +#define CQE_VALID_MASK 0x80000000 +#define CQE_CODE_MASK 0x0000003F +#define CQE_CID_MASK 0x0000FFC0 + +#define EQE_VALID_MASK 0x00000001 +#define EQE_MAJORCODE_MASK 0x0000000E +#define EQE_RESID_MASK 0xFFFF0000 + +struct be_eq_entry { + u32 dw[1]; +} __packed; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_eq_entry { + u8 valid; /* DWORD 0 */ + u8 major_code[3]; /* DWORD 0 */ + u8 minor_code[12]; /* DWORD 0 */ + u8 resource_id[16]; /* DWORD 0 */ + +} __packed; + +struct cq_db { + u32 dw[1]; +} __packed; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_cq_db { + u8 qid[10]; + u8 event[1]; + u8 rsvd0[5]; + u8 num_popped[13]; + u8 rearm[1]; + u8 rsvd1[2]; +} __packed; + +void beiscsi_process_eq(struct beiscsi_hba *phba); + + +struct iscsi_wrb { + u32 dw[16]; +} __packed; + +#define WRB_TYPE_MASK 0xF0000000 + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_iscsi_wrb { + u8 lun[14]; /* DWORD 0 */ + u8 lt; /* DWORD 0 */ + u8 invld; /* DWORD 0 */ + u8 wrb_idx[8]; /* DWORD 0 */ + u8 dsp; /* DWORD 0 */ + u8 dmsg; /* DWORD 0 */ + u8 undr_run; /* DWORD 0 */ + u8 over_run; /* DWORD 0 */ + u8 type[4]; /* DWORD 0 */ + u8 ptr2nextwrb[8]; /* DWORD 1 */ + u8 r2t_exp_dtl[24]; /* DWORD 1 */ + u8 sgl_icd_idx[12]; /* DWORD 2 */ + u8 rsvd0[20]; /* DWORD 2 */ + u8 exp_data_sn[32]; /* DWORD 3 */ + u8 iscsi_bhs_addr_hi[32]; /* DWORD 4 */ + u8 iscsi_bhs_addr_lo[32]; /* DWORD 5 */ + u8 cmdsn_itt[32]; /* DWORD 6 */ + u8 dif_ref_tag[32]; /* DWORD 7 */ + u8 sge0_addr_hi[32]; /* DWORD 8 */ + u8 sge0_addr_lo[32]; /* DWORD 9 */ + u8 sge0_offset[22]; /* DWORD 10 */ + u8 pbs; /* DWORD 10 */ + u8 dif_mode[2]; /* DWORD 10 */ + u8 rsvd1[6]; /* DWORD 10 */ + u8 sge0_last; /* DWORD 10 */ + u8 sge0_len[17]; /* DWORD 11 */ + u8 dif_meta_tag[14]; /* DWORD 11 */ + u8 sge0_in_ddr; /* DWORD 11 */ + u8 sge1_addr_hi[32]; /* DWORD 12 */ + u8 sge1_addr_lo[32]; /* DWORD 13 */ + u8 sge1_r2t_offset[22]; /* DWORD 14 */ + u8 rsvd2[9]; /* DWORD 14 */ + u8 sge1_last; /* DWORD 14 */ + u8 sge1_len[17]; /* DWORD 15 */ + u8 ref_sgl_icd_idx[12]; /* DWORD 15 */ + u8 rsvd3[2]; /* DWORD 15 */ + u8 sge1_in_ddr; /* DWORD 15 */ + +} __packed; + +struct wrb_handle *alloc_wrb_handle(struct beiscsi_hba *phba, unsigned int cid, + int index); +void +free_mgmt_sgl_handle(struct beiscsi_hba *phba, struct sgl_handle *psgl_handle); + +struct pdu_nop_out { + u32 dw[12]; +}; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_pdu_nop_out { + u8 opcode[6]; /* opcode 0x00 */ + u8 i_bit; /* I Bit */ + u8 x_bit; /* reserved; should be 0 */ + u8 fp_bit_filler1[7]; + u8 f_bit; /* always 1 */ + u8 reserved1[16]; + u8 ahs_length[8]; /* no AHS */ + u8 data_len_hi[8]; + u8 data_len_lo[16]; /* DataSegmentLength */ + u8 lun[64]; + u8 itt[32]; /* initiator id for ping or 0xffffffff */ + u8 ttt[32]; /* target id for ping or 0xffffffff */ + u8 cmd_sn[32]; + u8 exp_stat_sn[32]; + u8 reserved5[128]; +}; + +#define PDUBASE_OPCODE_MASK 0x0000003F +#define PDUBASE_DATALENHI_MASK 0x0000FF00 +#define PDUBASE_DATALENLO_MASK 0xFFFF0000 + +struct pdu_base { + u32 dw[16]; +} __packed; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_pdu_base { + u8 opcode[6]; + u8 i_bit; /* immediate bit */ + u8 x_bit; /* reserved, always 0 */ + u8 reserved1[24]; /* opcode-specific fields */ + u8 ahs_length[8]; /* length units is 4 byte words */ + u8 data_len_hi[8]; + u8 data_len_lo[16]; /* DatasegmentLength */ + u8 lun[64]; /* lun or opcode-specific fields */ + u8 itt[32]; /* initiator task tag */ + u8 reserved4[224]; +}; + +struct iscsi_target_context_update_wrb { + u32 dw[16]; +} __packed; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_iscsi_target_context_update_wrb { + u8 lun[14]; /* DWORD 0 */ + u8 lt; /* DWORD 0 */ + u8 invld; /* DWORD 0 */ + u8 wrb_idx[8]; /* DWORD 0 */ + u8 dsp; /* DWORD 0 */ + u8 dmsg; /* DWORD 0 */ + u8 undr_run; /* DWORD 0 */ + u8 over_run; /* DWORD 0 */ + u8 type[4]; /* DWORD 0 */ + u8 ptr2nextwrb[8]; /* DWORD 1 */ + u8 max_burst_length[19]; /* DWORD 1 */ + u8 rsvd0[5]; /* DWORD 1 */ + u8 rsvd1[15]; /* DWORD 2 */ + u8 max_send_data_segment_length[17]; /* DWORD 2 */ + u8 first_burst_length[14]; /* DWORD 3 */ + u8 rsvd2[2]; /* DWORD 3 */ + u8 tx_wrbindex_drv_msg[8]; /* DWORD 3 */ + u8 rsvd3[5]; /* DWORD 3 */ + u8 session_state[3]; /* DWORD 3 */ + u8 rsvd4[16]; /* DWORD 4 */ + u8 tx_jumbo; /* DWORD 4 */ + u8 hde; /* DWORD 4 */ + u8 dde; /* DWORD 4 */ + u8 erl[2]; /* DWORD 4 */ + u8 domain_id[5]; /* DWORD 4 */ + u8 mode; /* DWORD 4 */ + u8 imd; /* DWORD 4 */ + u8 ir2t; /* DWORD 4 */ + u8 notpredblq[2]; /* DWORD 4 */ + u8 compltonack; /* DWORD 4 */ + u8 stat_sn[32]; /* DWORD 5 */ + u8 pad_buffer_addr_hi[32]; /* DWORD 6 */ + u8 pad_buffer_addr_lo[32]; /* DWORD 7 */ + u8 pad_addr_hi[32]; /* DWORD 8 */ + u8 pad_addr_lo[32]; /* DWORD 9 */ + u8 rsvd5[32]; /* DWORD 10 */ + u8 rsvd6[32]; /* DWORD 11 */ + u8 rsvd7[32]; /* DWORD 12 */ + u8 rsvd8[32]; /* DWORD 13 */ + u8 rsvd9[32]; /* DWORD 14 */ + u8 rsvd10[32]; /* DWORD 15 */ + +} __packed; + +struct be_ring { + u32 pages; /* queue size in pages */ + u32 id; /* queue id assigned by beklib */ + u32 num; /* number of elements in queue */ + u32 cidx; /* consumer index */ + u32 pidx; /* producer index -- not used by most rings */ + u32 item_size; /* size in bytes of one object */ + + void *va; /* The virtual address of the ring. This + * should be last to allow 32 & 64 bit debugger + * extensions to work. + */ +}; + +struct hwi_wrb_context { + struct list_head wrb_handle_list; + struct list_head wrb_handle_drvr_list; + struct wrb_handle **pwrb_handle_base; + struct wrb_handle **pwrb_handle_basestd; + struct iscsi_wrb *plast_wrb; + unsigned short alloc_index; + unsigned short free_index; + unsigned short wrb_handles_available; + unsigned short cid; +}; + +struct hwi_controller { + struct list_head io_sgl_list; + struct list_head eh_sgl_list; + struct sgl_handle *psgl_handle_base; + unsigned int wrb_mem_index; + + struct hwi_wrb_context wrb_context[BE2_MAX_SESSIONS * 2]; + struct mcc_wrb *pmcc_wrb_base; + struct be_ring default_pdu_hdr; + struct be_ring default_pdu_data; + struct hwi_context_memory *phwi_ctxt; + unsigned short cq_errors[CXN_KILLED_CMND_DATA_NOT_ON_SAME_CONN]; +}; + +enum hwh_type_enum { + HWH_TYPE_IO = 1, + HWH_TYPE_LOGOUT = 2, + HWH_TYPE_TMF = 3, + HWH_TYPE_NOP = 4, + HWH_TYPE_IO_RD = 5, + HWH_TYPE_LOGIN = 11, + HWH_TYPE_INVALID = 0xFFFFFFFF +}; + +struct wrb_handle { + enum hwh_type_enum type; + unsigned short wrb_index; + unsigned short nxt_wrb_index; + + struct iscsi_task *pio_handle; + struct iscsi_wrb *pwrb; +}; + +struct hwi_context_memory { + struct be_eq_obj be_eq; + struct be_queue_info be_cq; + struct be_queue_info be_mcc_cq; + struct be_queue_info be_mcc; + + struct be_queue_info be_def_hdrq; + struct be_queue_info be_def_dataq; + + struct be_queue_info be_wrbq[BE2_MAX_SESSIONS]; + struct be_mcc_wrb_context *pbe_mcc_context; + + struct hwi_async_pdu_context *pasync_ctx; +}; + +#endif diff --git a/drivers/scsi/be2iscsi/be_mgmt.c b/drivers/scsi/be2iscsi/be_mgmt.c new file mode 100644 index 000000000000..12e644fc746e --- /dev/null +++ b/drivers/scsi/be2iscsi/be_mgmt.c @@ -0,0 +1,321 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Written by: Jayamohan Kallickal (jayamohank@serverengines.com) + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + * + */ + +#include "be_mgmt.h" +#include "be_iscsi.h" + +unsigned char mgmt_get_fw_config(struct be_ctrl_info *ctrl, + struct beiscsi_hba *phba) +{ + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_fw_cfg *req = embedded_payload(wrb); + int status = 0; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON, + OPCODE_COMMON_QUERY_FIRMWARE_CONFIG, sizeof(*req)); + + status = be_mbox_notify(ctrl); + if (!status) { + struct be_fw_cfg *pfw_cfg; + pfw_cfg = req; + phba->fw_config.phys_port = pfw_cfg->phys_port; + phba->fw_config.iscsi_icd_start = + pfw_cfg->ulp[0].icd_base; + phba->fw_config.iscsi_icd_count = + pfw_cfg->ulp[0].icd_count; + phba->fw_config.iscsi_cid_start = + pfw_cfg->ulp[0].sq_base; + phba->fw_config.iscsi_cid_count = + pfw_cfg->ulp[0].sq_count; + } else { + shost_printk(KERN_WARNING, phba->shost, + "Failed in mgmt_get_fw_config \n"); + } + + spin_unlock(&ctrl->mbox_lock); + return status; +} + +unsigned char mgmt_check_supported_fw(struct be_ctrl_info *ctrl) +{ + struct be_dma_mem nonemb_cmd; + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_mgmt_controller_attributes *req; + struct be_sge *sge = nonembedded_sgl(wrb); + int status = 0; + + nonemb_cmd.va = pci_alloc_consistent(ctrl->pdev, + sizeof(struct be_mgmt_controller_attributes), + &nonemb_cmd.dma); + if (nonemb_cmd.va == NULL) { + SE_DEBUG(DBG_LVL_1, + "Failed to allocate memory for mgmt_check_supported_fw" + "\n"); + return -1; + } + nonemb_cmd.size = sizeof(struct be_mgmt_controller_attributes); + req = nonemb_cmd.va; + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + be_wrb_hdr_prepare(wrb, sizeof(*req), false, 1); + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_COMMON, + OPCODE_COMMON_GET_CNTL_ATTRIBUTES, sizeof(*req)); + sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd.dma)); + sge->pa_lo = cpu_to_le32(nonemb_cmd.dma & 0xFFFFFFFF); + sge->len = cpu_to_le32(nonemb_cmd.size); + + status = be_mbox_notify(ctrl); + if (!status) { + struct be_mgmt_controller_attributes_resp *resp = nonemb_cmd.va; + SE_DEBUG(DBG_LVL_8, "Firmware version of CMD: %s\n", + resp->params.hba_attribs.flashrom_version_string); + SE_DEBUG(DBG_LVL_8, "Firmware version is : %s\n", + resp->params.hba_attribs.firmware_version_string); + SE_DEBUG(DBG_LVL_8, + "Developer Build, not performing version check...\n"); + + } else + SE_DEBUG(DBG_LVL_1, " Failed in mgmt_check_supported_fw\n"); + if (nonemb_cmd.va) + pci_free_consistent(ctrl->pdev, nonemb_cmd.size, + nonemb_cmd.va, nonemb_cmd.dma); + + spin_unlock(&ctrl->mbox_lock); + return status; +} + +unsigned char mgmt_epfw_cleanup(struct beiscsi_hba *phba, unsigned short chute) +{ + struct be_ctrl_info *ctrl = &phba->ctrl; + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct iscsi_cleanup_req *req = embedded_payload(wrb); + int status = 0; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI, + OPCODE_COMMON_ISCSI_CLEANUP, sizeof(*req)); + + req->chute = chute; + req->hdr_ring_id = 0; + req->data_ring_id = 0; + + status = be_mbox_notify(ctrl); + if (status) + shost_printk(KERN_WARNING, phba->shost, + " mgmt_epfw_cleanup , FAILED\n"); + spin_unlock(&ctrl->mbox_lock); + return status; +} + +unsigned char mgmt_invalidate_icds(struct beiscsi_hba *phba, + unsigned int icd, unsigned int cid) +{ + struct be_dma_mem nonemb_cmd; + struct be_ctrl_info *ctrl = &phba->ctrl; + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct be_sge *sge = nonembedded_sgl(wrb); + struct invalidate_commands_params_in *req; + int status = 0; + + nonemb_cmd.va = pci_alloc_consistent(ctrl->pdev, + sizeof(struct invalidate_commands_params_in), + &nonemb_cmd.dma); + if (nonemb_cmd.va == NULL) { + SE_DEBUG(DBG_LVL_1, + "Failed to allocate memory for" + "mgmt_invalidate_icds \n"); + return -1; + } + nonemb_cmd.size = sizeof(struct invalidate_commands_params_in); + req = nonemb_cmd.va; + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), false, 1); + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI, + OPCODE_COMMON_ISCSI_ERROR_RECOVERY_INVALIDATE_COMMANDS, + sizeof(*req)); + req->ref_handle = 0; + req->cleanup_type = CMD_ISCSI_COMMAND_INVALIDATE; + req->icd_count = 0; + req->table[req->icd_count].icd = icd; + req->table[req->icd_count].cid = cid; + sge->pa_hi = cpu_to_le32(upper_32_bits(nonemb_cmd.dma)); + sge->pa_lo = cpu_to_le32(nonemb_cmd.dma & 0xFFFFFFFF); + sge->len = cpu_to_le32(nonemb_cmd.size); + + status = be_mbox_notify(ctrl); + if (status) + SE_DEBUG(DBG_LVL_1, "ICDS Invalidation Failed\n"); + spin_unlock(&ctrl->mbox_lock); + if (nonemb_cmd.va) + pci_free_consistent(ctrl->pdev, nonemb_cmd.size, + nonemb_cmd.va, nonemb_cmd.dma); + return status; +} + +unsigned char mgmt_invalidate_connection(struct beiscsi_hba *phba, + struct beiscsi_endpoint *beiscsi_ep, + unsigned short cid, + unsigned short issue_reset, + unsigned short savecfg_flag) +{ + struct be_ctrl_info *ctrl = &phba->ctrl; + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct iscsi_invalidate_connection_params_in *req = + embedded_payload(wrb); + int status = 0; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI_INI, + OPCODE_ISCSI_INI_DRIVER_INVALIDATE_CONNECTION, + sizeof(*req)); + req->session_handle = beiscsi_ep->fw_handle; + req->cid = cid; + if (issue_reset) + req->cleanup_type = CMD_ISCSI_CONNECTION_ISSUE_TCP_RST; + else + req->cleanup_type = CMD_ISCSI_CONNECTION_INVALIDATE; + req->save_cfg = savecfg_flag; + status = be_mbox_notify(ctrl); + if (status) + SE_DEBUG(DBG_LVL_1, "Invalidation Failed\n"); + + spin_unlock(&ctrl->mbox_lock); + return status; +} + +unsigned char mgmt_upload_connection(struct beiscsi_hba *phba, + unsigned short cid, unsigned int upload_flag) +{ + struct be_ctrl_info *ctrl = &phba->ctrl; + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct tcp_upload_params_in *req = embedded_payload(wrb); + int status = 0; + + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + be_cmd_hdr_prepare(&req->hdr, CMD_COMMON_TCP_UPLOAD, + OPCODE_COMMON_TCP_UPLOAD, sizeof(*req)); + req->id = (unsigned short)cid; + req->upload_type = (unsigned char)upload_flag; + status = be_mbox_notify(ctrl); + if (status) + SE_DEBUG(DBG_LVL_1, "mgmt_upload_connection Failed\n"); + spin_unlock(&ctrl->mbox_lock); + return status; +} + +int mgmt_open_connection(struct beiscsi_hba *phba, + struct sockaddr *dst_addr, + struct beiscsi_endpoint *beiscsi_ep) +{ + struct hwi_controller *phwi_ctrlr; + struct hwi_context_memory *phwi_context; + struct sockaddr_in *daddr_in = (struct sockaddr_in *)dst_addr; + struct sockaddr_in6 *daddr_in6 = (struct sockaddr_in6 *)dst_addr; + struct be_ctrl_info *ctrl = &phba->ctrl; + struct be_mcc_wrb *wrb = wrb_from_mbox(&ctrl->mbox_mem); + struct tcp_connect_and_offload_in *req = embedded_payload(wrb); + unsigned short def_hdr_id; + unsigned short def_data_id; + struct phys_addr template_address = { 0, 0 }; + struct phys_addr *ptemplate_address; + int status = 0; + unsigned short cid = beiscsi_ep->ep_cid; + + phwi_ctrlr = phba->phwi_ctrlr; + phwi_context = phwi_ctrlr->phwi_ctxt; + def_hdr_id = (unsigned short)HWI_GET_DEF_HDRQ_ID(phba); + def_data_id = (unsigned short)HWI_GET_DEF_BUFQ_ID(phba); + + ptemplate_address = &template_address; + ISCSI_GET_PDU_TEMPLATE_ADDRESS(phba, ptemplate_address); + spin_lock(&ctrl->mbox_lock); + memset(wrb, 0, sizeof(*wrb)); + + be_wrb_hdr_prepare(wrb, sizeof(*req), true, 0); + be_cmd_hdr_prepare(&req->hdr, CMD_SUBSYSTEM_ISCSI, + OPCODE_COMMON_ISCSI_TCP_CONNECT_AND_OFFLOAD, + sizeof(*req)); + if (dst_addr->sa_family == PF_INET) { + __be32 s_addr = daddr_in->sin_addr.s_addr; + req->ip_address.ip_type = BE2_IPV4; + req->ip_address.ip_address[0] = s_addr & 0x000000ff; + req->ip_address.ip_address[1] = (s_addr & 0x0000ff00) >> 8; + req->ip_address.ip_address[2] = (s_addr & 0x00ff0000) >> 16; + req->ip_address.ip_address[3] = (s_addr & 0xff000000) >> 24; + req->tcp_port = ntohs(daddr_in->sin_port); + beiscsi_ep->dst_addr = daddr_in->sin_addr.s_addr; + beiscsi_ep->dst_tcpport = ntohs(daddr_in->sin_port); + beiscsi_ep->ip_type = BE2_IPV4; + } else if (dst_addr->sa_family == PF_INET6) { + req->ip_address.ip_type = BE2_IPV6; + memcpy(&req->ip_address.ip_address, + &daddr_in6->sin6_addr.in6_u.u6_addr8, 16); + req->tcp_port = ntohs(daddr_in6->sin6_port); + beiscsi_ep->dst_tcpport = ntohs(daddr_in6->sin6_port); + memcpy(&beiscsi_ep->dst6_addr, + &daddr_in6->sin6_addr.in6_u.u6_addr8, 16); + beiscsi_ep->ip_type = BE2_IPV6; + } else{ + shost_printk(KERN_ERR, phba->shost, "unknown addr family %d\n", + dst_addr->sa_family); + spin_unlock(&ctrl->mbox_lock); + return -EINVAL; + + } + req->cid = cid; + req->cq_id = phwi_context->be_cq.id; + req->defq_id = def_hdr_id; + req->hdr_ring_id = def_hdr_id; + req->data_ring_id = def_data_id; + req->do_offload = 1; + req->dataout_template_pa.lo = ptemplate_address->lo; + req->dataout_template_pa.hi = ptemplate_address->hi; + status = be_mbox_notify(ctrl); + if (!status) { + struct iscsi_endpoint *ep; + struct tcp_connect_and_offload_out *ptcpcnct_out = + embedded_payload(wrb); + + ep = phba->ep_array[ptcpcnct_out->cid]; + beiscsi_ep = ep->dd_data; + beiscsi_ep->fw_handle = 0; + beiscsi_ep->cid_vld = 1; + SE_DEBUG(DBG_LVL_8, "mgmt_open_connection Success\n"); + } else + SE_DEBUG(DBG_LVL_1, "mgmt_open_connection Failed\n"); + spin_unlock(&ctrl->mbox_lock); + return status; +} diff --git a/drivers/scsi/be2iscsi/be_mgmt.h b/drivers/scsi/be2iscsi/be_mgmt.h new file mode 100644 index 000000000000..00e816ee8070 --- /dev/null +++ b/drivers/scsi/be2iscsi/be_mgmt.h @@ -0,0 +1,249 @@ +/** + * Copyright (C) 2005 - 2009 ServerEngines + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License version 2 + * as published by the Free Software Foundation. The full GNU General + * Public License is included in this distribution in the file called COPYING. + * + * Written by: Jayamohan Kallickal (jayamohank@serverengines.com) + * + * Contact Information: + * linux-drivers@serverengines.com + * + * ServerEngines + * 209 N. Fair Oaks Ave + * Sunnyvale, CA 94085 + * + */ + +#ifndef _BEISCSI_MGMT_ +#define _BEISCSI_MGMT_ + +#include <linux/types.h> +#include <linux/list.h> +#include "be_iscsi.h" +#include "be_main.h" + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_mcc_sge { + u8 pa_lo[32]; /* dword 0 */ + u8 pa_hi[32]; /* dword 1 */ + u8 length[32]; /* DWORD 2 */ +} __packed; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_mcc_wrb_payload { + union { + struct amap_mcc_sge sgl[19]; + u8 embedded[59 * 32]; /* DWORDS 57 to 115 */ + } u; +} __packed; + +/** + * Pseudo amap definition in which each bit of the actual structure is defined + * as a byte: used to calculate offset/shift/mask of each field + */ +struct amap_mcc_wrb { + u8 embedded; /* DWORD 0 */ + u8 rsvd0[2]; /* DWORD 0 */ + u8 sge_count[5]; /* DWORD 0 */ + u8 rsvd1[16]; /* DWORD 0 */ + u8 special[8]; /* DWORD 0 */ + u8 payload_length[32]; + u8 tag[64]; /* DWORD 2 */ + u8 rsvd2[32]; /* DWORD 4 */ + struct amap_mcc_wrb_payload payload; +}; + +struct mcc_sge { + u32 pa_lo; /* dword 0 */ + u32 pa_hi; /* dword 1 */ + u32 length; /* DWORD 2 */ +} __packed; + +struct mcc_wrb_payload { + union { + struct mcc_sge sgl[19]; + u32 embedded[59]; /* DWORDS 57 to 115 */ + } u; +} __packed; + +#define MCC_WRB_EMBEDDED_MASK 0x00000001 + +struct mcc_wrb { + u32 dw[0]; /* DWORD 0 */ + u32 payload_length; + u32 tag[2]; /* DWORD 2 */ + u32 rsvd2[1]; /* DWORD 4 */ + struct mcc_wrb_payload payload; +}; + +unsigned char mgmt_epfw_cleanup(struct beiscsi_hba *phba, unsigned short chute); +int mgmt_open_connection(struct beiscsi_hba *phba, struct sockaddr *dst_addr, + struct beiscsi_endpoint *beiscsi_ep); + +unsigned char mgmt_upload_connection(struct beiscsi_hba *phba, + unsigned short cid, + unsigned int upload_flag); +unsigned char mgmt_invalidate_icds(struct beiscsi_hba *phba, + unsigned int icd, unsigned int cid); + +struct iscsi_invalidate_connection_params_in { + struct be_cmd_req_hdr hdr; + unsigned int session_handle; + unsigned short cid; + unsigned short unused; + unsigned short cleanup_type; + unsigned short save_cfg; +} __packed; + +struct iscsi_invalidate_connection_params_out { + unsigned int session_handle; + unsigned short cid; + unsigned short unused; +} __packed; + +union iscsi_invalidate_connection_params { + struct iscsi_invalidate_connection_params_in request; + struct iscsi_invalidate_connection_params_out response; +} __packed; + +struct invalidate_command_table { + unsigned short icd; + unsigned short cid; +} __packed; + +struct invalidate_commands_params_in { + struct be_cmd_req_hdr hdr; + unsigned int ref_handle; + unsigned int icd_count; + struct invalidate_command_table table[128]; + unsigned short cleanup_type; + unsigned short unused; +} __packed; + +struct invalidate_commands_params_out { + unsigned int ref_handle; + unsigned int icd_count; + unsigned int icd_status[128]; +} __packed; + +union invalidate_commands_params { + struct invalidate_commands_params_in request; + struct invalidate_commands_params_out response; +} __packed; + +struct mgmt_hba_attributes { + u8 flashrom_version_string[32]; + u8 manufacturer_name[32]; + u32 supported_modes; + u8 seeprom_version_lo; + u8 seeprom_version_hi; + u8 rsvd0[2]; + u32 fw_cmd_data_struct_version; + u32 ep_fw_data_struct_version; + u32 future_reserved[12]; + u32 default_extended_timeout; + u8 controller_model_number[32]; + u8 controller_description[64]; + u8 controller_serial_number[32]; + u8 ip_version_string[32]; + u8 firmware_version_string[32]; + u8 bios_version_string[32]; + u8 redboot_version_string[32]; + u8 driver_version_string[32]; + u8 fw_on_flash_version_string[32]; + u32 functionalities_supported; + u16 max_cdblength; + u8 asic_revision; + u8 generational_guid[16]; + u8 hba_port_count; + u16 default_link_down_timeout; + u8 iscsi_ver_min_max; + u8 multifunction_device; + u8 cache_valid; + u8 hba_status; + u8 max_domains_supported; + u8 phy_port; + u32 firmware_post_status; + u32 hba_mtu[8]; + u32 future_u32[4]; +} __packed; + +struct mgmt_controller_attributes { + struct mgmt_hba_attributes hba_attribs; + u16 pci_vendor_id; + u16 pci_device_id; + u16 pci_sub_vendor_id; + u16 pci_sub_system_id; + u8 pci_bus_number; + u8 pci_device_number; + u8 pci_function_number; + u8 interface_type; + u64 unique_identifier; + u8 netfilters; + u8 rsvd0[3]; + u8 future_u32[4]; +} __packed; + +struct be_mgmt_controller_attributes { + struct be_cmd_req_hdr hdr; + struct mgmt_controller_attributes params; +} __packed; + +struct be_mgmt_controller_attributes_resp { + struct be_cmd_resp_hdr hdr; + struct mgmt_controller_attributes params; +} __packed; + +/* configuration management */ + +#define GET_MGMT_CONTROLLER_WS(phba) (phba->pmgmt_ws) + +/* MGMT CMD flags */ + +#define MGMT_CMDH_FREE (1<<0) + +/* --- MGMT_ERROR_CODES --- */ +/* Error Codes returned in the status field of the CMD response header */ +#define MGMT_STATUS_SUCCESS 0 /* The CMD completed without errors */ +#define MGMT_STATUS_FAILED 1 /* Error status in the Status field of */ + /* the CMD_RESPONSE_HEADER */ + +#define ISCSI_GET_PDU_TEMPLATE_ADDRESS(pc, pa) {\ + pa->lo = phba->init_mem[ISCSI_MEM_GLOBAL_HEADER].mem_array[0].\ + bus_address.u.a32.address_lo; \ + pa->hi = phba->init_mem[ISCSI_MEM_GLOBAL_HEADER].mem_array[0].\ + bus_address.u.a32.address_hi; \ +} + +struct beiscsi_endpoint { + struct beiscsi_hba *phba; + struct beiscsi_sess *sess; + struct beiscsi_conn *conn; + unsigned short ip_type; + char dst6_addr[ISCSI_ADDRESS_BUF_LEN]; + unsigned long dst_addr; + unsigned short ep_cid; + unsigned int fw_handle; + u16 dst_tcpport; + u16 cid_vld; +}; + +unsigned char mgmt_get_fw_config(struct be_ctrl_info *ctrl, + struct beiscsi_hba *phba); + +unsigned char mgmt_invalidate_connection(struct beiscsi_hba *phba, + struct beiscsi_endpoint *beiscsi_ep, + unsigned short cid, + unsigned short issue_reset, + unsigned short savecfg_flag); +#endif diff --git a/drivers/scsi/bfa/Makefile b/drivers/scsi/bfa/Makefile new file mode 100644 index 000000000000..1d6009490d1c --- /dev/null +++ b/drivers/scsi/bfa/Makefile @@ -0,0 +1,15 @@ +obj-$(CONFIG_SCSI_BFA_FC) := bfa.o + +bfa-y := bfad.o bfad_intr.o bfad_os.o bfad_im.o bfad_attr.o bfad_fwimg.o + +bfa-y += bfa_core.o bfa_ioc.o bfa_iocfc.o bfa_fcxp.o bfa_lps.o +bfa-y += bfa_hw_cb.o bfa_hw_ct.o bfa_intr.o bfa_timer.o bfa_rport.o +bfa-y += bfa_fcport.o bfa_port.o bfa_uf.o bfa_sgpg.o bfa_module.o bfa_ioim.o +bfa-y += bfa_itnim.o bfa_fcpim.o bfa_tskim.o bfa_log.o bfa_log_module.o +bfa-y += bfa_csdebug.o bfa_sm.o plog.o + +bfa-y += fcbuild.o fabric.o fcpim.o vfapi.o fcptm.o bfa_fcs.o bfa_fcs_port.o +bfa-y += bfa_fcs_uf.o bfa_fcs_lport.o fab.o fdmi.o ms.o ns.o scn.o loop.o +bfa-y += lport_api.o n2n.o rport.o rport_api.o rport_ftrs.o vport.o + +ccflags-y := -I$(obj) -I$(obj)/include -I$(obj)/include/cna diff --git a/drivers/scsi/bfa/bfa_callback_priv.h b/drivers/scsi/bfa/bfa_callback_priv.h new file mode 100644 index 000000000000..1e3265c9f7d4 --- /dev/null +++ b/drivers/scsi/bfa/bfa_callback_priv.h @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_CALLBACK_PRIV_H__ +#define __BFA_CALLBACK_PRIV_H__ + +#include <cs/bfa_q.h> + +typedef void (*bfa_cb_cbfn_t) (void *cbarg, bfa_boolean_t complete); + +/** + * Generic BFA callback element. + */ +struct bfa_cb_qe_s { + struct list_head qe; + bfa_cb_cbfn_t cbfn; + bfa_boolean_t once; + u32 rsvd; + void *cbarg; +}; + +#define bfa_cb_queue(__bfa, __hcb_qe, __cbfn, __cbarg) do { \ + (__hcb_qe)->cbfn = (__cbfn); \ + (__hcb_qe)->cbarg = (__cbarg); \ + list_add_tail(&(__hcb_qe)->qe, &(__bfa)->comp_q); \ +} while (0) + +#define bfa_cb_dequeue(__hcb_qe) list_del(&(__hcb_qe)->qe) + +#define bfa_cb_queue_once(__bfa, __hcb_qe, __cbfn, __cbarg) do { \ + (__hcb_qe)->cbfn = (__cbfn); \ + (__hcb_qe)->cbarg = (__cbarg); \ + if (!(__hcb_qe)->once) { \ + list_add_tail((__hcb_qe), &(__bfa)->comp_q); \ + (__hcb_qe)->once = BFA_TRUE; \ + } \ +} while (0) + +#define bfa_cb_queue_done(__hcb_qe) do { \ + (__hcb_qe)->once = BFA_FALSE; \ +} while (0) + +#endif /* __BFA_CALLBACK_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_cb_ioim_macros.h b/drivers/scsi/bfa/bfa_cb_ioim_macros.h new file mode 100644 index 000000000000..0050c838c358 --- /dev/null +++ b/drivers/scsi/bfa/bfa_cb_ioim_macros.h @@ -0,0 +1,205 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_cb_ioim_macros.h BFA IOIM driver interface macros. + */ + +#ifndef __BFA_HCB_IOIM_MACROS_H__ +#define __BFA_HCB_IOIM_MACROS_H__ + +#include <bfa_os_inc.h> +/* + * #include <linux/dma-mapping.h> + * + * #include <scsi/scsi.h> #include <scsi/scsi_cmnd.h> #include + * <scsi/scsi_device.h> #include <scsi/scsi_host.h> + */ +#include "bfad_im_compat.h" + +/* + * task attribute values in FCP-2 FCP_CMND IU + */ +#define SIMPLE_Q 0 +#define HEAD_OF_Q 1 +#define ORDERED_Q 2 +#define ACA_Q 4 +#define UNTAGGED 5 + +static inline lun_t +bfad_int_to_lun(u32 luno) +{ + union { + u16 scsi_lun[4]; + lun_t bfa_lun; + } lun; + + lun.bfa_lun = 0; + lun.scsi_lun[0] = bfa_os_htons(luno); + + return (lun.bfa_lun); +} + +/** + * Get LUN for the I/O request + */ +#define bfa_cb_ioim_get_lun(__dio) \ + bfad_int_to_lun(((struct scsi_cmnd *)__dio)->device->lun) + +/** + * Get CDB for the I/O request + */ +static inline u8 * +bfa_cb_ioim_get_cdb(struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + + return ((u8 *) cmnd->cmnd); +} + +/** + * Get I/O direction (read/write) for the I/O request + */ +static inline enum fcp_iodir +bfa_cb_ioim_get_iodir(struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + enum dma_data_direction dmadir; + + dmadir = cmnd->sc_data_direction; + if (dmadir == DMA_TO_DEVICE) + return FCP_IODIR_WRITE; + else if (dmadir == DMA_FROM_DEVICE) + return FCP_IODIR_READ; + else + return FCP_IODIR_NONE; +} + +/** + * Get IO size in bytes for the I/O request + */ +static inline u32 +bfa_cb_ioim_get_size(struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + + return (scsi_bufflen(cmnd)); +} + +/** + * Get timeout for the I/O request + */ +static inline u8 +bfa_cb_ioim_get_timeout(struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + /* + * TBD: need a timeout for scsi passthru + */ + if (cmnd->device->host == NULL) + return 4; + + return 0; +} + +/** + * Get SG element for the I/O request given the SG element index + */ +static inline union bfi_addr_u +bfa_cb_ioim_get_sgaddr(struct bfad_ioim_s *dio, int sgeid) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + struct scatterlist *sge; + u64 addr; + + sge = (struct scatterlist *)scsi_sglist(cmnd) + sgeid; + addr = (u64) sg_dma_address(sge); + + return (*(union bfi_addr_u *) &addr); +} + +static inline u32 +bfa_cb_ioim_get_sglen(struct bfad_ioim_s *dio, int sgeid) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + struct scatterlist *sge; + u32 len; + + sge = (struct scatterlist *)scsi_sglist(cmnd) + sgeid; + len = sg_dma_len(sge); + + return len; +} + +/** + * Get Command Reference Number for the I/O request. 0 if none. + */ +static inline u8 +bfa_cb_ioim_get_crn(struct bfad_ioim_s *dio) +{ + return 0; +} + +/** + * Get SAM-3 priority for the I/O request. 0 is default. + */ +static inline u8 +bfa_cb_ioim_get_priority(struct bfad_ioim_s *dio) +{ + return 0; +} + +/** + * Get task attributes for the I/O request. Default is FCP_TASK_ATTR_SIMPLE(0). + */ +static inline u8 +bfa_cb_ioim_get_taskattr(struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + u8 task_attr = UNTAGGED; + + if (cmnd->device->tagged_supported) { + switch (cmnd->tag) { + case HEAD_OF_QUEUE_TAG: + task_attr = HEAD_OF_Q; + break; + case ORDERED_QUEUE_TAG: + task_attr = ORDERED_Q; + break; + default: + task_attr = SIMPLE_Q; + break; + } + } + + return task_attr; +} + +/** + * Get CDB length in bytes for the I/O request. Default is FCP_CMND_CDB_LEN(16). + */ +static inline u8 +bfa_cb_ioim_get_cdblen(struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + + return (cmnd->cmd_len); +} + + + +#endif /* __BFA_HCB_IOIM_MACROS_H__ */ diff --git a/drivers/scsi/bfa/bfa_cee.c b/drivers/scsi/bfa/bfa_cee.c new file mode 100644 index 000000000000..7a959c34e789 --- /dev/null +++ b/drivers/scsi/bfa/bfa_cee.c @@ -0,0 +1,492 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <defs/bfa_defs_cee.h> +#include <cs/bfa_trc.h> +#include <cs/bfa_log.h> +#include <cs/bfa_debug.h> +#include <cee/bfa_cee.h> +#include <bfi/bfi_cee.h> +#include <bfi/bfi.h> +#include <bfa_ioc.h> +#include <cna/bfa_cna_trcmod.h> + +BFA_TRC_FILE(CNA, CEE); + +#define bfa_ioc_portid(__ioc) ((__ioc)->port_id) +#define bfa_lpuid(__arg) bfa_ioc_portid(&(__arg)->ioc) + +static void bfa_cee_format_lldp_cfg(struct bfa_cee_lldp_cfg_s *lldp_cfg); +static void bfa_cee_format_dcbcx_stats(struct bfa_cee_dcbx_stats_s + *dcbcx_stats); +static void bfa_cee_format_lldp_stats(struct bfa_cee_lldp_stats_s + *lldp_stats); +static void bfa_cee_format_cfg_stats(struct bfa_cee_cfg_stats_s *cfg_stats); +static void bfa_cee_format_cee_cfg(void *buffer); +static void bfa_cee_format_cee_stats(void *buffer); + +static void +bfa_cee_format_cee_stats(void *buffer) +{ + struct bfa_cee_stats_s *cee_stats = buffer; + bfa_cee_format_dcbcx_stats(&cee_stats->dcbx_stats); + bfa_cee_format_lldp_stats(&cee_stats->lldp_stats); + bfa_cee_format_cfg_stats(&cee_stats->cfg_stats); +} + +static void +bfa_cee_format_cee_cfg(void *buffer) +{ + struct bfa_cee_attr_s *cee_cfg = buffer; + bfa_cee_format_lldp_cfg(&cee_cfg->lldp_remote); +} + +static void +bfa_cee_format_dcbcx_stats(struct bfa_cee_dcbx_stats_s *dcbcx_stats) +{ + dcbcx_stats->subtlvs_unrecognized = + bfa_os_ntohl(dcbcx_stats->subtlvs_unrecognized); + dcbcx_stats->negotiation_failed = + bfa_os_ntohl(dcbcx_stats->negotiation_failed); + dcbcx_stats->remote_cfg_changed = + bfa_os_ntohl(dcbcx_stats->remote_cfg_changed); + dcbcx_stats->tlvs_received = bfa_os_ntohl(dcbcx_stats->tlvs_received); + dcbcx_stats->tlvs_invalid = bfa_os_ntohl(dcbcx_stats->tlvs_invalid); + dcbcx_stats->seqno = bfa_os_ntohl(dcbcx_stats->seqno); + dcbcx_stats->ackno = bfa_os_ntohl(dcbcx_stats->ackno); + dcbcx_stats->recvd_seqno = bfa_os_ntohl(dcbcx_stats->recvd_seqno); + dcbcx_stats->recvd_ackno = bfa_os_ntohl(dcbcx_stats->recvd_ackno); +} + +static void +bfa_cee_format_lldp_stats(struct bfa_cee_lldp_stats_s *lldp_stats) +{ + lldp_stats->frames_transmitted = + bfa_os_ntohl(lldp_stats->frames_transmitted); + lldp_stats->frames_aged_out = bfa_os_ntohl(lldp_stats->frames_aged_out); + lldp_stats->frames_discarded = + bfa_os_ntohl(lldp_stats->frames_discarded); + lldp_stats->frames_in_error = bfa_os_ntohl(lldp_stats->frames_in_error); + lldp_stats->frames_rcvd = bfa_os_ntohl(lldp_stats->frames_rcvd); + lldp_stats->tlvs_discarded = bfa_os_ntohl(lldp_stats->tlvs_discarded); + lldp_stats->tlvs_unrecognized = + bfa_os_ntohl(lldp_stats->tlvs_unrecognized); +} + +static void +bfa_cee_format_cfg_stats(struct bfa_cee_cfg_stats_s *cfg_stats) +{ + cfg_stats->cee_status_down = bfa_os_ntohl(cfg_stats->cee_status_down); + cfg_stats->cee_status_up = bfa_os_ntohl(cfg_stats->cee_status_up); + cfg_stats->cee_hw_cfg_changed = + bfa_os_ntohl(cfg_stats->cee_hw_cfg_changed); + cfg_stats->recvd_invalid_cfg = + bfa_os_ntohl(cfg_stats->recvd_invalid_cfg); +} + +static void +bfa_cee_format_lldp_cfg(struct bfa_cee_lldp_cfg_s *lldp_cfg) +{ + lldp_cfg->time_to_interval = bfa_os_ntohs(lldp_cfg->time_to_interval); + lldp_cfg->enabled_system_cap = + bfa_os_ntohs(lldp_cfg->enabled_system_cap); +} + +/** + * bfa_cee_attr_meminfo() + * + * + * @param[in] void + * + * @return Size of DMA region + */ +static u32 +bfa_cee_attr_meminfo(void) +{ + return BFA_ROUNDUP(sizeof(struct bfa_cee_attr_s), BFA_DMA_ALIGN_SZ); +} + +/** + * bfa_cee_stats_meminfo() + * + * + * @param[in] void + * + * @return Size of DMA region + */ +static u32 +bfa_cee_stats_meminfo(void) +{ + return BFA_ROUNDUP(sizeof(struct bfa_cee_stats_s), BFA_DMA_ALIGN_SZ); +} + +/** + * bfa_cee_get_attr_isr() + * + * + * @param[in] cee - Pointer to the CEE module + * status - Return status from the f/w + * + * @return void + */ +static void +bfa_cee_get_attr_isr(struct bfa_cee_s *cee, bfa_status_t status) +{ + cee->get_attr_status = status; + bfa_trc(cee, 0); + if (status == BFA_STATUS_OK) { + bfa_trc(cee, 0); + /* + * The requested data has been copied to the DMA area, *process + * it. + */ + memcpy(cee->attr, cee->attr_dma.kva, + sizeof(struct bfa_cee_attr_s)); + bfa_cee_format_cee_cfg(cee->attr); + } + cee->get_attr_pending = BFA_FALSE; + if (cee->cbfn.get_attr_cbfn) { + bfa_trc(cee, 0); + cee->cbfn.get_attr_cbfn(cee->cbfn.get_attr_cbarg, status); + } + bfa_trc(cee, 0); +} + +/** + * bfa_cee_get_attr_isr() + * + * + * @param[in] cee - Pointer to the CEE module + * status - Return status from the f/w + * + * @return void + */ +static void +bfa_cee_get_stats_isr(struct bfa_cee_s *cee, bfa_status_t status) +{ + cee->get_stats_status = status; + bfa_trc(cee, 0); + if (status == BFA_STATUS_OK) { + bfa_trc(cee, 0); + /* + * The requested data has been copied to the DMA area, process + * it. + */ + memcpy(cee->stats, cee->stats_dma.kva, + sizeof(struct bfa_cee_stats_s)); + bfa_cee_format_cee_stats(cee->stats); + } + cee->get_stats_pending = BFA_FALSE; + bfa_trc(cee, 0); + if (cee->cbfn.get_stats_cbfn) { + bfa_trc(cee, 0); + cee->cbfn.get_stats_cbfn(cee->cbfn.get_stats_cbarg, status); + } + bfa_trc(cee, 0); +} + +/** + * bfa_cee_get_attr_isr() + * + * + * @param[in] cee - Pointer to the CEE module + * status - Return status from the f/w + * + * @return void + */ +static void +bfa_cee_reset_stats_isr(struct bfa_cee_s *cee, bfa_status_t status) +{ + cee->reset_stats_status = status; + cee->reset_stats_pending = BFA_FALSE; + if (cee->cbfn.reset_stats_cbfn) + cee->cbfn.reset_stats_cbfn(cee->cbfn.reset_stats_cbarg, status); +} + +/** + * bfa_cee_meminfo() + * + * + * @param[in] void + * + * @return Size of DMA region + */ +u32 +bfa_cee_meminfo(void) +{ + return (bfa_cee_attr_meminfo() + bfa_cee_stats_meminfo()); +} + +/** + * bfa_cee_mem_claim() + * + * + * @param[in] cee CEE module pointer + * dma_kva Kernel Virtual Address of CEE DMA Memory + * dma_pa Physical Address of CEE DMA Memory + * + * @return void + */ +void +bfa_cee_mem_claim(struct bfa_cee_s *cee, u8 *dma_kva, u64 dma_pa) +{ + cee->attr_dma.kva = dma_kva; + cee->attr_dma.pa = dma_pa; + cee->stats_dma.kva = dma_kva + bfa_cee_attr_meminfo(); + cee->stats_dma.pa = dma_pa + bfa_cee_attr_meminfo(); + cee->attr = (struct bfa_cee_attr_s *)dma_kva; + cee->stats = + (struct bfa_cee_stats_s *)(dma_kva + bfa_cee_attr_meminfo()); +} + +/** + * bfa_cee_get_attr() + * + * Send the request to the f/w to fetch CEE attributes. + * + * @param[in] Pointer to the CEE module data structure. + * + * @return Status + */ + +bfa_status_t +bfa_cee_get_attr(struct bfa_cee_s *cee, struct bfa_cee_attr_s *attr, + bfa_cee_get_attr_cbfn_t cbfn, void *cbarg) +{ + struct bfi_cee_get_req_s *cmd; + + bfa_assert((cee != NULL) && (cee->ioc != NULL)); + bfa_trc(cee, 0); + if (!bfa_ioc_is_operational(cee->ioc)) { + bfa_trc(cee, 0); + return BFA_STATUS_IOC_FAILURE; + } + if (cee->get_attr_pending == BFA_TRUE) { + bfa_trc(cee, 0); + return BFA_STATUS_DEVBUSY; + } + cee->get_attr_pending = BFA_TRUE; + cmd = (struct bfi_cee_get_req_s *)cee->get_cfg_mb.msg; + cee->attr = attr; + cee->cbfn.get_attr_cbfn = cbfn; + cee->cbfn.get_attr_cbarg = cbarg; + bfi_h2i_set(cmd->mh, BFI_MC_CEE, BFI_CEE_H2I_GET_CFG_REQ, + bfa_ioc_portid(cee->ioc)); + bfa_dma_be_addr_set(cmd->dma_addr, cee->attr_dma.pa); + bfa_ioc_mbox_queue(cee->ioc, &cee->get_cfg_mb); + bfa_trc(cee, 0); + + return BFA_STATUS_OK; +} + +/** + * bfa_cee_get_stats() + * + * Send the request to the f/w to fetch CEE statistics. + * + * @param[in] Pointer to the CEE module data structure. + * + * @return Status + */ + +bfa_status_t +bfa_cee_get_stats(struct bfa_cee_s *cee, struct bfa_cee_stats_s *stats, + bfa_cee_get_stats_cbfn_t cbfn, void *cbarg) +{ + struct bfi_cee_get_req_s *cmd; + + bfa_assert((cee != NULL) && (cee->ioc != NULL)); + + if (!bfa_ioc_is_operational(cee->ioc)) { + bfa_trc(cee, 0); + return BFA_STATUS_IOC_FAILURE; + } + if (cee->get_stats_pending == BFA_TRUE) { + bfa_trc(cee, 0); + return BFA_STATUS_DEVBUSY; + } + cee->get_stats_pending = BFA_TRUE; + cmd = (struct bfi_cee_get_req_s *)cee->get_stats_mb.msg; + cee->stats = stats; + cee->cbfn.get_stats_cbfn = cbfn; + cee->cbfn.get_stats_cbarg = cbarg; + bfi_h2i_set(cmd->mh, BFI_MC_CEE, BFI_CEE_H2I_GET_STATS_REQ, + bfa_ioc_portid(cee->ioc)); + bfa_dma_be_addr_set(cmd->dma_addr, cee->stats_dma.pa); + bfa_ioc_mbox_queue(cee->ioc, &cee->get_stats_mb); + bfa_trc(cee, 0); + + return BFA_STATUS_OK; +} + +/** + * bfa_cee_reset_stats() + * + * + * @param[in] Pointer to the CEE module data structure. + * + * @return Status + */ + +bfa_status_t +bfa_cee_reset_stats(struct bfa_cee_s *cee, bfa_cee_reset_stats_cbfn_t cbfn, + void *cbarg) +{ + struct bfi_cee_reset_stats_s *cmd; + + bfa_assert((cee != NULL) && (cee->ioc != NULL)); + if (!bfa_ioc_is_operational(cee->ioc)) { + bfa_trc(cee, 0); + return BFA_STATUS_IOC_FAILURE; + } + if (cee->reset_stats_pending == BFA_TRUE) { + bfa_trc(cee, 0); + return BFA_STATUS_DEVBUSY; + } + cee->reset_stats_pending = BFA_TRUE; + cmd = (struct bfi_cee_reset_stats_s *)cee->reset_stats_mb.msg; + cee->cbfn.reset_stats_cbfn = cbfn; + cee->cbfn.reset_stats_cbarg = cbarg; + bfi_h2i_set(cmd->mh, BFI_MC_CEE, BFI_CEE_H2I_RESET_STATS, + bfa_ioc_portid(cee->ioc)); + bfa_ioc_mbox_queue(cee->ioc, &cee->reset_stats_mb); + bfa_trc(cee, 0); + return BFA_STATUS_OK; +} + +/** + * bfa_cee_isrs() + * + * + * @param[in] Pointer to the CEE module data structure. + * + * @return void + */ + +void +bfa_cee_isr(void *cbarg, struct bfi_mbmsg_s *m) +{ + union bfi_cee_i2h_msg_u *msg; + struct bfi_cee_get_rsp_s *get_rsp; + struct bfa_cee_s *cee = (struct bfa_cee_s *)cbarg; + msg = (union bfi_cee_i2h_msg_u *)m; + get_rsp = (struct bfi_cee_get_rsp_s *)m; + bfa_trc(cee, msg->mh.msg_id); + switch (msg->mh.msg_id) { + case BFI_CEE_I2H_GET_CFG_RSP: + bfa_trc(cee, get_rsp->cmd_status); + bfa_cee_get_attr_isr(cee, get_rsp->cmd_status); + break; + case BFI_CEE_I2H_GET_STATS_RSP: + bfa_cee_get_stats_isr(cee, get_rsp->cmd_status); + break; + case BFI_CEE_I2H_RESET_STATS_RSP: + bfa_cee_reset_stats_isr(cee, get_rsp->cmd_status); + break; + default: + bfa_assert(0); + } +} + +/** + * bfa_cee_hbfail() + * + * + * @param[in] Pointer to the CEE module data structure. + * + * @return void + */ + +void +bfa_cee_hbfail(void *arg) +{ + struct bfa_cee_s *cee; + cee = (struct bfa_cee_s *)arg; + + if (cee->get_attr_pending == BFA_TRUE) { + cee->get_attr_status = BFA_STATUS_FAILED; + cee->get_attr_pending = BFA_FALSE; + if (cee->cbfn.get_attr_cbfn) { + cee->cbfn.get_attr_cbfn(cee->cbfn.get_attr_cbarg, + BFA_STATUS_FAILED); + } + } + if (cee->get_stats_pending == BFA_TRUE) { + cee->get_stats_status = BFA_STATUS_FAILED; + cee->get_stats_pending = BFA_FALSE; + if (cee->cbfn.get_stats_cbfn) { + cee->cbfn.get_stats_cbfn(cee->cbfn.get_stats_cbarg, + BFA_STATUS_FAILED); + } + } + if (cee->reset_stats_pending == BFA_TRUE) { + cee->reset_stats_status = BFA_STATUS_FAILED; + cee->reset_stats_pending = BFA_FALSE; + if (cee->cbfn.reset_stats_cbfn) { + cee->cbfn.reset_stats_cbfn(cee->cbfn.reset_stats_cbarg, + BFA_STATUS_FAILED); + } + } +} + +/** + * bfa_cee_attach() + * + * + * @param[in] cee - Pointer to the CEE module data structure + * ioc - Pointer to the ioc module data structure + * dev - Pointer to the device driver module data structure + * The device driver specific mbox ISR functions have + * this pointer as one of the parameters. + * trcmod - + * logmod - + * + * @return void + */ +void +bfa_cee_attach(struct bfa_cee_s *cee, struct bfa_ioc_s *ioc, void *dev, + struct bfa_trc_mod_s *trcmod, struct bfa_log_mod_s *logmod) +{ + bfa_assert(cee != NULL); + cee->dev = dev; + cee->trcmod = trcmod; + cee->logmod = logmod; + cee->ioc = ioc; + + bfa_ioc_mbox_regisr(cee->ioc, BFI_MC_CEE, bfa_cee_isr, cee); + bfa_ioc_hbfail_init(&cee->hbfail, bfa_cee_hbfail, cee); + bfa_ioc_hbfail_register(cee->ioc, &cee->hbfail); + bfa_trc(cee, 0); +} + +/** + * bfa_cee_detach() + * + * + * @param[in] cee - Pointer to the CEE module data structure + * + * @return void + */ +void +bfa_cee_detach(struct bfa_cee_s *cee) +{ + /* + * For now, just check if there is some ioctl pending and mark that as + * failed? + */ + /* bfa_cee_hbfail(cee); */ +} diff --git a/drivers/scsi/bfa/bfa_core.c b/drivers/scsi/bfa/bfa_core.c new file mode 100644 index 000000000000..44e2d1155c51 --- /dev/null +++ b/drivers/scsi/bfa/bfa_core.c @@ -0,0 +1,402 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <defs/bfa_defs_pci.h> +#include <cs/bfa_debug.h> +#include <bfa_iocfc.h> + +#define DEF_CFG_NUM_FABRICS 1 +#define DEF_CFG_NUM_LPORTS 256 +#define DEF_CFG_NUM_CQS 4 +#define DEF_CFG_NUM_IOIM_REQS (BFA_IOIM_MAX) +#define DEF_CFG_NUM_TSKIM_REQS 128 +#define DEF_CFG_NUM_FCXP_REQS 64 +#define DEF_CFG_NUM_UF_BUFS 64 +#define DEF_CFG_NUM_RPORTS 1024 +#define DEF_CFG_NUM_ITNIMS (DEF_CFG_NUM_RPORTS) +#define DEF_CFG_NUM_TINS 256 + +#define DEF_CFG_NUM_SGPGS 2048 +#define DEF_CFG_NUM_REQQ_ELEMS 256 +#define DEF_CFG_NUM_RSPQ_ELEMS 64 +#define DEF_CFG_NUM_SBOOT_TGTS 16 +#define DEF_CFG_NUM_SBOOT_LUNS 16 + +/** + * Use this function query the memory requirement of the BFA library. + * This function needs to be called before bfa_attach() to get the + * memory required of the BFA layer for a given driver configuration. + * + * This call will fail, if the cap is out of range compared to pre-defined + * values within the BFA library + * + * @param[in] cfg - pointer to bfa_ioc_cfg_t. Driver layer should indicate + * its configuration in this structure. + * The default values for struct bfa_iocfc_cfg_s can be + * fetched using bfa_cfg_get_default() API. + * + * If cap's boundary check fails, the library will use + * the default bfa_cap_t values (and log a warning msg). + * + * @param[out] meminfo - pointer to bfa_meminfo_t. This content + * indicates the memory type (see bfa_mem_type_t) and + * amount of memory required. + * + * Driver should allocate the memory, populate the + * starting address for each block and provide the same + * structure as input parameter to bfa_attach() call. + * + * @return void + * + * Special Considerations: @note + */ +void +bfa_cfg_get_meminfo(struct bfa_iocfc_cfg_s *cfg, struct bfa_meminfo_s *meminfo) +{ + int i; + u32 km_len = 0, dm_len = 0; + + bfa_assert((cfg != NULL) && (meminfo != NULL)); + + bfa_os_memset((void *)meminfo, 0, sizeof(struct bfa_meminfo_s)); + meminfo->meminfo[BFA_MEM_TYPE_KVA - 1].mem_type = + BFA_MEM_TYPE_KVA; + meminfo->meminfo[BFA_MEM_TYPE_DMA - 1].mem_type = + BFA_MEM_TYPE_DMA; + + bfa_iocfc_meminfo(cfg, &km_len, &dm_len); + + for (i = 0; hal_mods[i]; i++) + hal_mods[i]->meminfo(cfg, &km_len, &dm_len); + + + meminfo->meminfo[BFA_MEM_TYPE_KVA - 1].mem_len = km_len; + meminfo->meminfo[BFA_MEM_TYPE_DMA - 1].mem_len = dm_len; +} + +/** + * Use this function to do attach the driver instance with the BFA + * library. This function will not trigger any HW initialization + * process (which will be done in bfa_init() call) + * + * This call will fail, if the cap is out of range compared to + * pre-defined values within the BFA library + * + * @param[out] bfa Pointer to bfa_t. + * @param[in] bfad Opaque handle back to the driver's IOC structure + * @param[in] cfg Pointer to bfa_ioc_cfg_t. Should be same structure + * that was used in bfa_cfg_get_meminfo(). + * @param[in] meminfo Pointer to bfa_meminfo_t. The driver should + * use the bfa_cfg_get_meminfo() call to + * find the memory blocks required, allocate the + * required memory and provide the starting addresses. + * @param[in] pcidev pointer to struct bfa_pcidev_s + * + * @return + * void + * + * Special Considerations: + * + * @note + * + */ +void +bfa_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + int i; + struct bfa_mem_elem_s *melem; + + bfa->fcs = BFA_FALSE; + + bfa_assert((cfg != NULL) && (meminfo != NULL)); + + /** + * initialize all memory pointers for iterative allocation + */ + for (i = 0; i < BFA_MEM_TYPE_MAX; i++) { + melem = meminfo->meminfo + i; + melem->kva_curp = melem->kva; + melem->dma_curp = melem->dma; + } + + bfa_iocfc_attach(bfa, bfad, cfg, meminfo, pcidev); + + for (i = 0; hal_mods[i]; i++) + hal_mods[i]->attach(bfa, bfad, cfg, meminfo, pcidev); + +} + +/** + * Use this function to delete a BFA IOC. IOC should be stopped (by + * calling bfa_stop()) before this function call. + * + * @param[in] bfa - pointer to bfa_t. + * + * @return + * void + * + * Special Considerations: + * + * @note + */ +void +bfa_detach(struct bfa_s *bfa) +{ + int i; + + for (i = 0; hal_mods[i]; i++) + hal_mods[i]->detach(bfa); + + bfa_iocfc_detach(bfa); +} + + +void +bfa_init_trc(struct bfa_s *bfa, struct bfa_trc_mod_s *trcmod) +{ + bfa->trcmod = trcmod; +} + + +void +bfa_init_log(struct bfa_s *bfa, struct bfa_log_mod_s *logmod) +{ + bfa->logm = logmod; +} + + +void +bfa_init_aen(struct bfa_s *bfa, struct bfa_aen_s *aen) +{ + bfa->aen = aen; +} + +void +bfa_init_plog(struct bfa_s *bfa, struct bfa_plog_s *plog) +{ + bfa->plog = plog; +} + +/** + * Initialize IOC. + * + * This function will return immediately, when the IOC initialization is + * completed, the bfa_cb_init() will be called. + * + * @param[in] bfa instance + * + * @return void + * + * Special Considerations: + * + * @note + * When this function returns, the driver should register the interrupt service + * routine(s) and enable the device interrupts. If this is not done, + * bfa_cb_init() will never get called + */ +void +bfa_init(struct bfa_s *bfa) +{ + bfa_iocfc_init(bfa); +} + +/** + * Use this function initiate the IOC configuration setup. This function + * will return immediately. + * + * @param[in] bfa instance + * + * @return None + */ +void +bfa_start(struct bfa_s *bfa) +{ + bfa_iocfc_start(bfa); +} + +/** + * Use this function quiese the IOC. This function will return immediately, + * when the IOC is actually stopped, the bfa_cb_stop() will be called. + * + * @param[in] bfa - pointer to bfa_t. + * + * @return None + * + * Special Considerations: + * bfa_cb_stop() could be called before or after bfa_stop() returns. + * + * @note + * In case of any failure, we could handle it automatically by doing a + * reset and then succeed the bfa_stop() call. + */ +void +bfa_stop(struct bfa_s *bfa) +{ + bfa_iocfc_stop(bfa); +} + +void +bfa_comp_deq(struct bfa_s *bfa, struct list_head *comp_q) +{ + INIT_LIST_HEAD(comp_q); + list_splice_tail_init(&bfa->comp_q, comp_q); +} + +void +bfa_comp_process(struct bfa_s *bfa, struct list_head *comp_q) +{ + struct list_head *qe; + struct list_head *qen; + struct bfa_cb_qe_s *hcb_qe; + + list_for_each_safe(qe, qen, comp_q) { + hcb_qe = (struct bfa_cb_qe_s *) qe; + hcb_qe->cbfn(hcb_qe->cbarg, BFA_TRUE); + } +} + +void +bfa_comp_free(struct bfa_s *bfa, struct list_head *comp_q) +{ + struct list_head *qe; + struct bfa_cb_qe_s *hcb_qe; + + while (!list_empty(comp_q)) { + bfa_q_deq(comp_q, &qe); + hcb_qe = (struct bfa_cb_qe_s *) qe; + hcb_qe->cbfn(hcb_qe->cbarg, BFA_FALSE); + } +} + +void +bfa_attach_fcs(struct bfa_s *bfa) +{ + bfa->fcs = BFA_TRUE; +} + +/** + * Periodic timer heart beat from driver + */ +void +bfa_timer_tick(struct bfa_s *bfa) +{ + bfa_timer_beat(&bfa->timer_mod); +} + +#ifndef BFA_BIOS_BUILD +/** + * Return the list of PCI vendor/device id lists supported by this + * BFA instance. + */ +void +bfa_get_pciids(struct bfa_pciid_s **pciids, int *npciids) +{ + static struct bfa_pciid_s __pciids[] = { + {BFA_PCI_VENDOR_ID_BROCADE, BFA_PCI_DEVICE_ID_FC_8G2P}, + {BFA_PCI_VENDOR_ID_BROCADE, BFA_PCI_DEVICE_ID_FC_8G1P}, + {BFA_PCI_VENDOR_ID_BROCADE, BFA_PCI_DEVICE_ID_CT}, + }; + + *npciids = sizeof(__pciids) / sizeof(__pciids[0]); + *pciids = __pciids; +} + +/** + * Use this function query the default struct bfa_iocfc_cfg_s value (compiled + * into BFA layer). The OS driver can then turn back and overwrite entries that + * have been configured by the user. + * + * @param[in] cfg - pointer to bfa_ioc_cfg_t + * + * @return + * void + * + * Special Considerations: + * note + */ +void +bfa_cfg_get_default(struct bfa_iocfc_cfg_s *cfg) +{ + cfg->fwcfg.num_fabrics = DEF_CFG_NUM_FABRICS; + cfg->fwcfg.num_lports = DEF_CFG_NUM_LPORTS; + cfg->fwcfg.num_rports = DEF_CFG_NUM_RPORTS; + cfg->fwcfg.num_ioim_reqs = DEF_CFG_NUM_IOIM_REQS; + cfg->fwcfg.num_tskim_reqs = DEF_CFG_NUM_TSKIM_REQS; + cfg->fwcfg.num_fcxp_reqs = DEF_CFG_NUM_FCXP_REQS; + cfg->fwcfg.num_uf_bufs = DEF_CFG_NUM_UF_BUFS; + cfg->fwcfg.num_cqs = DEF_CFG_NUM_CQS; + + cfg->drvcfg.num_reqq_elems = DEF_CFG_NUM_REQQ_ELEMS; + cfg->drvcfg.num_rspq_elems = DEF_CFG_NUM_RSPQ_ELEMS; + cfg->drvcfg.num_sgpgs = DEF_CFG_NUM_SGPGS; + cfg->drvcfg.num_sboot_tgts = DEF_CFG_NUM_SBOOT_TGTS; + cfg->drvcfg.num_sboot_luns = DEF_CFG_NUM_SBOOT_LUNS; + cfg->drvcfg.path_tov = BFA_FCPIM_PATHTOV_DEF; + cfg->drvcfg.ioc_recover = BFA_FALSE; + cfg->drvcfg.delay_comp = BFA_FALSE; + +} + +void +bfa_cfg_get_min(struct bfa_iocfc_cfg_s *cfg) +{ + bfa_cfg_get_default(cfg); + cfg->fwcfg.num_ioim_reqs = BFA_IOIM_MIN; + cfg->fwcfg.num_tskim_reqs = BFA_TSKIM_MIN; + cfg->fwcfg.num_fcxp_reqs = BFA_FCXP_MIN; + cfg->fwcfg.num_uf_bufs = BFA_UF_MIN; + cfg->fwcfg.num_rports = BFA_RPORT_MIN; + + cfg->drvcfg.num_sgpgs = BFA_SGPG_MIN; + cfg->drvcfg.num_reqq_elems = BFA_REQQ_NELEMS_MIN; + cfg->drvcfg.num_rspq_elems = BFA_RSPQ_NELEMS_MIN; + cfg->drvcfg.min_cfg = BFA_TRUE; +} + +void +bfa_get_attr(struct bfa_s *bfa, struct bfa_ioc_attr_s *ioc_attr) +{ + bfa_ioc_get_attr(&bfa->ioc, ioc_attr); +} + +/** + * Retrieve firmware trace information on IOC failure. + */ +bfa_status_t +bfa_debug_fwsave(struct bfa_s *bfa, void *trcdata, int *trclen) +{ + return bfa_ioc_debug_fwsave(&bfa->ioc, trcdata, trclen); +} + +/** + * Fetch firmware trace data. + * + * @param[in] bfa BFA instance + * @param[out] trcdata Firmware trace buffer + * @param[in,out] trclen Firmware trace buffer len + * + * @retval BFA_STATUS_OK Firmware trace is fetched. + * @retval BFA_STATUS_INPROGRESS Firmware trace fetch is in progress. + */ +bfa_status_t +bfa_debug_fwtrc(struct bfa_s *bfa, void *trcdata, int *trclen) +{ + return bfa_ioc_debug_fwtrc(&bfa->ioc, trcdata, trclen); +} +#endif diff --git a/drivers/scsi/bfa/bfa_csdebug.c b/drivers/scsi/bfa/bfa_csdebug.c new file mode 100644 index 000000000000..1b71d349451a --- /dev/null +++ b/drivers/scsi/bfa/bfa_csdebug.c @@ -0,0 +1,58 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <cs/bfa_debug.h> +#include <bfa_os_inc.h> +#include <cs/bfa_q.h> +#include <log/bfa_log_hal.h> + +/** + * cs_debug_api + */ + + +void +bfa_panic(int line, char *file, char *panicstr) +{ + bfa_log(NULL, BFA_LOG_HAL_ASSERT, file, line, panicstr); + bfa_os_panic(); +} + +void +bfa_sm_panic(struct bfa_log_mod_s *logm, int line, char *file, int event) +{ + bfa_log(logm, BFA_LOG_HAL_SM_ASSERT, file, line, event); + bfa_os_panic(); +} + +int +bfa_q_is_on_q_func(struct list_head *q, struct list_head *qe) +{ + struct list_head *tqe; + + tqe = bfa_q_next(q); + while (tqe != q) { + if (tqe == qe) + return (1); + tqe = bfa_q_next(tqe); + if (tqe == NULL) + break; + } + return (0); +} + + diff --git a/drivers/scsi/bfa/bfa_fcpim.c b/drivers/scsi/bfa/bfa_fcpim.c new file mode 100644 index 000000000000..401babe3494e --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcpim.c @@ -0,0 +1,175 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <log/bfa_log_hal.h> + +BFA_TRC_FILE(HAL, FCPIM); +BFA_MODULE(fcpim); + +/** + * hal_fcpim_mod BFA FCP Initiator Mode module + */ + +/** + * Compute and return memory needed by FCP(im) module. + */ +static void +bfa_fcpim_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len) +{ + bfa_itnim_meminfo(cfg, km_len, dm_len); + + /** + * IO memory + */ + if (cfg->fwcfg.num_ioim_reqs < BFA_IOIM_MIN) + cfg->fwcfg.num_ioim_reqs = BFA_IOIM_MIN; + else if (cfg->fwcfg.num_ioim_reqs > BFA_IOIM_MAX) + cfg->fwcfg.num_ioim_reqs = BFA_IOIM_MAX; + + *km_len += cfg->fwcfg.num_ioim_reqs * + (sizeof(struct bfa_ioim_s) + sizeof(struct bfa_ioim_sp_s)); + + *dm_len += cfg->fwcfg.num_ioim_reqs * BFI_IOIM_SNSLEN; + + /** + * task management command memory + */ + if (cfg->fwcfg.num_tskim_reqs < BFA_TSKIM_MIN) + cfg->fwcfg.num_tskim_reqs = BFA_TSKIM_MIN; + *km_len += cfg->fwcfg.num_tskim_reqs * sizeof(struct bfa_tskim_s); +} + + +static void +bfa_fcpim_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + bfa_trc(bfa, cfg->drvcfg.path_tov); + bfa_trc(bfa, cfg->fwcfg.num_rports); + bfa_trc(bfa, cfg->fwcfg.num_ioim_reqs); + bfa_trc(bfa, cfg->fwcfg.num_tskim_reqs); + + fcpim->bfa = bfa; + fcpim->num_itnims = cfg->fwcfg.num_rports; + fcpim->num_ioim_reqs = cfg->fwcfg.num_ioim_reqs; + fcpim->num_tskim_reqs = cfg->fwcfg.num_tskim_reqs; + fcpim->path_tov = cfg->drvcfg.path_tov; + fcpim->delay_comp = cfg->drvcfg.delay_comp; + + bfa_itnim_attach(fcpim, meminfo); + bfa_tskim_attach(fcpim, meminfo); + bfa_ioim_attach(fcpim, meminfo); +} + +static void +bfa_fcpim_initdone(struct bfa_s *bfa) +{ +} + +static void +bfa_fcpim_detach(struct bfa_s *bfa) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + bfa_ioim_detach(fcpim); + bfa_tskim_detach(fcpim); +} + +static void +bfa_fcpim_start(struct bfa_s *bfa) +{ +} + +static void +bfa_fcpim_stop(struct bfa_s *bfa) +{ +} + +static void +bfa_fcpim_iocdisable(struct bfa_s *bfa) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + struct bfa_itnim_s *itnim; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &fcpim->itnim_q) { + itnim = (struct bfa_itnim_s *) qe; + bfa_itnim_iocdisable(itnim); + } +} + +void +bfa_fcpim_path_tov_set(struct bfa_s *bfa, u16 path_tov) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + fcpim->path_tov = path_tov * 1000; + if (fcpim->path_tov > BFA_FCPIM_PATHTOV_MAX) + fcpim->path_tov = BFA_FCPIM_PATHTOV_MAX; +} + +u16 +bfa_fcpim_path_tov_get(struct bfa_s *bfa) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + return (fcpim->path_tov / 1000); +} + +bfa_status_t +bfa_fcpim_get_modstats(struct bfa_s *bfa, struct bfa_fcpim_stats_s *modstats) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + *modstats = fcpim->stats; + + return BFA_STATUS_OK; +} + +bfa_status_t +bfa_fcpim_clr_modstats(struct bfa_s *bfa) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + memset(&fcpim->stats, 0, sizeof(struct bfa_fcpim_stats_s)); + + return BFA_STATUS_OK; +} + +void +bfa_fcpim_qdepth_set(struct bfa_s *bfa, u16 q_depth) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + bfa_assert(q_depth <= BFA_IOCFC_QDEPTH_MAX); + + fcpim->q_depth = q_depth; +} + +u16 +bfa_fcpim_qdepth_get(struct bfa_s *bfa) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + + return (fcpim->q_depth); +} + + diff --git a/drivers/scsi/bfa/bfa_fcpim_priv.h b/drivers/scsi/bfa/bfa_fcpim_priv.h new file mode 100644 index 000000000000..153206cfb37a --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcpim_priv.h @@ -0,0 +1,188 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCPIM_PRIV_H__ +#define __BFA_FCPIM_PRIV_H__ + +#include <bfa_fcpim.h> +#include <defs/bfa_defs_fcpim.h> +#include <cs/bfa_wc.h> +#include "bfa_sgpg_priv.h" + +#define BFA_ITNIM_MIN 32 +#define BFA_ITNIM_MAX 1024 + +#define BFA_IOIM_MIN 8 +#define BFA_IOIM_MAX 2000 + +#define BFA_TSKIM_MIN 4 +#define BFA_TSKIM_MAX 512 +#define BFA_FCPIM_PATHTOV_DEF (30 * 1000) /* in millisecs */ +#define BFA_FCPIM_PATHTOV_MAX (90 * 1000) /* in millisecs */ + +#define bfa_fcpim_stats(__fcpim, __stats) \ + (__fcpim)->stats.__stats ++ + +struct bfa_fcpim_mod_s { + struct bfa_s *bfa; + struct bfa_itnim_s *itnim_arr; + struct bfa_ioim_s *ioim_arr; + struct bfa_ioim_sp_s *ioim_sp_arr; + struct bfa_tskim_s *tskim_arr; + struct bfa_dma_s snsbase; + int num_itnims; + int num_ioim_reqs; + int num_tskim_reqs; + u32 path_tov; + u16 q_depth; + u16 rsvd; + struct list_head itnim_q; /* queue of active itnim */ + struct list_head ioim_free_q; /* free IO resources */ + struct list_head ioim_resfree_q; /* IOs waiting for f/w */ + struct list_head ioim_comp_q; /* IO global comp Q */ + struct list_head tskim_free_q; + u32 ios_active; /* current active IOs */ + u32 delay_comp; + struct bfa_fcpim_stats_s stats; +}; + +struct bfa_ioim_s; +struct bfa_tskim_s; + +/** + * BFA IO (initiator mode) + */ +struct bfa_ioim_s { + struct list_head qe; /* queue elememt */ + bfa_sm_t sm; /* BFA ioim state machine */ + struct bfa_s *bfa; /* BFA module */ + struct bfa_fcpim_mod_s *fcpim; /* parent fcpim module */ + struct bfa_itnim_s *itnim; /* i-t-n nexus for this IO */ + struct bfad_ioim_s *dio; /* driver IO handle */ + u16 iotag; /* FWI IO tag */ + u16 abort_tag; /* unqiue abort request tag */ + u16 nsges; /* number of SG elements */ + u16 nsgpgs; /* number of SG pages */ + struct bfa_sgpg_s *sgpg; /* first SG page */ + struct list_head sgpg_q; /* allocated SG pages */ + struct bfa_cb_qe_s hcb_qe; /* bfa callback qelem */ + bfa_cb_cbfn_t io_cbfn; /* IO completion handler */ + struct bfa_ioim_sp_s *iosp; /* slow-path IO handling */ +}; + +struct bfa_ioim_sp_s { + struct bfi_msg_s comp_rspmsg; /* IO comp f/w response */ + u8 *snsinfo; /* sense info for this IO */ + struct bfa_sgpg_wqe_s sgpg_wqe; /* waitq elem for sgpg */ + struct bfa_reqq_wait_s reqq_wait; /* to wait for room in reqq */ + bfa_boolean_t abort_explicit; /* aborted by OS */ + struct bfa_tskim_s *tskim; /* Relevant TM cmd */ +}; + +/** + * BFA Task management command (initiator mode) + */ +struct bfa_tskim_s { + struct list_head qe; + bfa_sm_t sm; + struct bfa_s *bfa; /* BFA module */ + struct bfa_fcpim_mod_s *fcpim; /* parent fcpim module */ + struct bfa_itnim_s *itnim; /* i-t-n nexus for this IO */ + struct bfad_tskim_s *dtsk; /* driver task mgmt cmnd */ + bfa_boolean_t notify; /* notify itnim on TM comp */ + lun_t lun; /* lun if applicable */ + enum fcp_tm_cmnd tm_cmnd; /* task management command */ + u16 tsk_tag; /* FWI IO tag */ + u8 tsecs; /* timeout in seconds */ + struct bfa_reqq_wait_s reqq_wait; /* to wait for room in reqq */ + struct list_head io_q; /* queue of affected IOs */ + struct bfa_wc_s wc; /* waiting counter */ + struct bfa_cb_qe_s hcb_qe; /* bfa callback qelem */ + enum bfi_tskim_status tsk_status; /* TM status */ +}; + +/** + * BFA i-t-n (initiator mode) + */ +struct bfa_itnim_s { + struct list_head qe; /* queue element */ + bfa_sm_t sm; /* i-t-n im BFA state machine */ + struct bfa_s *bfa; /* bfa instance */ + struct bfa_rport_s *rport; /* bfa rport */ + void *ditn; /* driver i-t-n structure */ + struct bfi_mhdr_s mhdr; /* pre-built mhdr */ + u8 msg_no; /* itnim/rport firmware handle */ + u8 reqq; /* CQ for requests */ + struct bfa_cb_qe_s hcb_qe; /* bfa callback qelem */ + struct list_head pending_q; /* queue of pending IO requests*/ + struct list_head io_q; /* queue of active IO requests */ + struct list_head io_cleanup_q; /* IO being cleaned up */ + struct list_head tsk_q; /* queue of active TM commands */ + struct list_head delay_comp_q;/* queue of failed inflight cmds */ + bfa_boolean_t seq_rec; /* SQER supported */ + bfa_boolean_t is_online; /* itnim is ONLINE for IO */ + bfa_boolean_t iotov_active; /* IO TOV timer is active */ + struct bfa_wc_s wc; /* waiting counter */ + struct bfa_timer_s timer; /* pending IO TOV */ + struct bfa_reqq_wait_s reqq_wait; /* to wait for room in reqq */ + struct bfa_fcpim_mod_s *fcpim; /* fcpim module */ + struct bfa_itnim_hal_stats_s stats; +}; + +#define bfa_itnim_is_online(_itnim) (_itnim)->is_online +#define BFA_FCPIM_MOD(_hal) (&(_hal)->modules.fcpim_mod) +#define BFA_IOIM_FROM_TAG(_fcpim, _iotag) \ + (&fcpim->ioim_arr[_iotag]) +#define BFA_TSKIM_FROM_TAG(_fcpim, _tmtag) \ + (&fcpim->tskim_arr[_tmtag & (fcpim->num_tskim_reqs - 1)]) + +/* + * function prototypes + */ +void bfa_ioim_attach(struct bfa_fcpim_mod_s *fcpim, + struct bfa_meminfo_s *minfo); +void bfa_ioim_detach(struct bfa_fcpim_mod_s *fcpim); +void bfa_ioim_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); +void bfa_ioim_good_comp_isr(struct bfa_s *bfa, + struct bfi_msg_s *msg); +void bfa_ioim_cleanup(struct bfa_ioim_s *ioim); +void bfa_ioim_cleanup_tm(struct bfa_ioim_s *ioim, + struct bfa_tskim_s *tskim); +void bfa_ioim_iocdisable(struct bfa_ioim_s *ioim); +void bfa_ioim_tov(struct bfa_ioim_s *ioim); + +void bfa_tskim_attach(struct bfa_fcpim_mod_s *fcpim, + struct bfa_meminfo_s *minfo); +void bfa_tskim_detach(struct bfa_fcpim_mod_s *fcpim); +void bfa_tskim_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); +void bfa_tskim_iodone(struct bfa_tskim_s *tskim); +void bfa_tskim_iocdisable(struct bfa_tskim_s *tskim); +void bfa_tskim_cleanup(struct bfa_tskim_s *tskim); + +void bfa_itnim_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len); +void bfa_itnim_attach(struct bfa_fcpim_mod_s *fcpim, + struct bfa_meminfo_s *minfo); +void bfa_itnim_detach(struct bfa_fcpim_mod_s *fcpim); +void bfa_itnim_iocdisable(struct bfa_itnim_s *itnim); +void bfa_itnim_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); +void bfa_itnim_iodone(struct bfa_itnim_s *itnim); +void bfa_itnim_tskdone(struct bfa_itnim_s *itnim); +bfa_boolean_t bfa_itnim_hold_io(struct bfa_itnim_s *itnim); + +#endif /* __BFA_FCPIM_PRIV_H__ */ + diff --git a/drivers/scsi/bfa/bfa_fcport.c b/drivers/scsi/bfa/bfa_fcport.c new file mode 100644 index 000000000000..992435987deb --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcport.c @@ -0,0 +1,1671 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include <bfi/bfi_pport.h> +#include <cs/bfa_debug.h> +#include <aen/bfa_aen.h> +#include <cs/bfa_plog.h> +#include <aen/bfa_aen_port.h> + +BFA_TRC_FILE(HAL, PPORT); +BFA_MODULE(pport); + +#define bfa_pport_callback(__pport, __event) do { \ + if ((__pport)->bfa->fcs) { \ + (__pport)->event_cbfn((__pport)->event_cbarg, (__event)); \ + } else { \ + (__pport)->hcb_event = (__event); \ + bfa_cb_queue((__pport)->bfa, &(__pport)->hcb_qe, \ + __bfa_cb_port_event, (__pport)); \ + } \ +} while (0) + +/* + * The port is considered disabled if corresponding physical port or IOC are + * disabled explicitly + */ +#define BFA_PORT_IS_DISABLED(bfa) \ + ((bfa_pport_is_disabled(bfa) == BFA_TRUE) || \ + (bfa_ioc_is_disabled(&bfa->ioc) == BFA_TRUE)) + +/* + * forward declarations + */ +static bfa_boolean_t bfa_pport_send_enable(struct bfa_pport_s *port); +static bfa_boolean_t bfa_pport_send_disable(struct bfa_pport_s *port); +static void bfa_pport_update_linkinfo(struct bfa_pport_s *pport); +static void bfa_pport_reset_linkinfo(struct bfa_pport_s *pport); +static void bfa_pport_set_wwns(struct bfa_pport_s *port); +static void __bfa_cb_port_event(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_port_stats(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_port_stats_clr(void *cbarg, bfa_boolean_t complete); +static void bfa_port_stats_timeout(void *cbarg); +static void bfa_port_stats_clr_timeout(void *cbarg); + +/** + * bfa_pport_private + */ + +/** + * BFA port state machine events + */ +enum bfa_pport_sm_event { + BFA_PPORT_SM_START = 1, /* start port state machine */ + BFA_PPORT_SM_STOP = 2, /* stop port state machine */ + BFA_PPORT_SM_ENABLE = 3, /* enable port */ + BFA_PPORT_SM_DISABLE = 4, /* disable port state machine */ + BFA_PPORT_SM_FWRSP = 5, /* firmware enable/disable rsp */ + BFA_PPORT_SM_LINKUP = 6, /* firmware linkup event */ + BFA_PPORT_SM_LINKDOWN = 7, /* firmware linkup down */ + BFA_PPORT_SM_QRESUME = 8, /* CQ space available */ + BFA_PPORT_SM_HWFAIL = 9, /* IOC h/w failure */ +}; + +static void bfa_pport_sm_uninit(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_enabling_qwait(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_enabling(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_linkdown(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_linkup(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_disabling(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_disabling_qwait(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_disabled(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_stopped(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_iocdown(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); +static void bfa_pport_sm_iocfail(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event); + +static struct bfa_sm_table_s hal_pport_sm_table[] = { + {BFA_SM(bfa_pport_sm_uninit), BFA_PPORT_ST_UNINIT}, + {BFA_SM(bfa_pport_sm_enabling_qwait), BFA_PPORT_ST_ENABLING_QWAIT}, + {BFA_SM(bfa_pport_sm_enabling), BFA_PPORT_ST_ENABLING}, + {BFA_SM(bfa_pport_sm_linkdown), BFA_PPORT_ST_LINKDOWN}, + {BFA_SM(bfa_pport_sm_linkup), BFA_PPORT_ST_LINKUP}, + {BFA_SM(bfa_pport_sm_disabling_qwait), + BFA_PPORT_ST_DISABLING_QWAIT}, + {BFA_SM(bfa_pport_sm_disabling), BFA_PPORT_ST_DISABLING}, + {BFA_SM(bfa_pport_sm_disabled), BFA_PPORT_ST_DISABLED}, + {BFA_SM(bfa_pport_sm_stopped), BFA_PPORT_ST_STOPPED}, + {BFA_SM(bfa_pport_sm_iocdown), BFA_PPORT_ST_IOCDOWN}, + {BFA_SM(bfa_pport_sm_iocfail), BFA_PPORT_ST_IOCDOWN}, +}; + +static void +bfa_pport_aen_post(struct bfa_pport_s *pport, enum bfa_port_aen_event event) +{ + union bfa_aen_data_u aen_data; + struct bfa_log_mod_s *logmod = pport->bfa->logm; + wwn_t pwwn = pport->pwwn; + char pwwn_ptr[BFA_STRING_32]; + struct bfa_ioc_attr_s ioc_attr; + + wwn2str(pwwn_ptr, pwwn); + switch (event) { + case BFA_PORT_AEN_ONLINE: + bfa_log(logmod, BFA_AEN_PORT_ONLINE, pwwn_ptr); + break; + case BFA_PORT_AEN_OFFLINE: + bfa_log(logmod, BFA_AEN_PORT_OFFLINE, pwwn_ptr); + break; + case BFA_PORT_AEN_ENABLE: + bfa_log(logmod, BFA_AEN_PORT_ENABLE, pwwn_ptr); + break; + case BFA_PORT_AEN_DISABLE: + bfa_log(logmod, BFA_AEN_PORT_DISABLE, pwwn_ptr); + break; + case BFA_PORT_AEN_DISCONNECT: + bfa_log(logmod, BFA_AEN_PORT_DISCONNECT, pwwn_ptr); + break; + case BFA_PORT_AEN_QOS_NEG: + bfa_log(logmod, BFA_AEN_PORT_QOS_NEG, pwwn_ptr); + break; + default: + break; + } + + bfa_ioc_get_attr(&pport->bfa->ioc, &ioc_attr); + aen_data.port.ioc_type = ioc_attr.ioc_type; + aen_data.port.pwwn = pwwn; +} + +static void +bfa_pport_sm_uninit(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_START: + /** + * Start event after IOC is configured and BFA is started. + */ + if (bfa_pport_send_enable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_enabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_enabling_qwait); + break; + + case BFA_PPORT_SM_ENABLE: + /** + * Port is persistently configured to be in enabled state. Do + * not change state. Port enabling is done when START event is + * received. + */ + break; + + case BFA_PPORT_SM_DISABLE: + /** + * If a port is persistently configured to be disabled, the + * first event will a port disable request. + */ + bfa_sm_set_state(pport, bfa_pport_sm_disabled); + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_sm_set_state(pport, bfa_pport_sm_iocdown); + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_enabling_qwait(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_QRESUME: + bfa_sm_set_state(pport, bfa_pport_sm_enabling); + bfa_pport_send_enable(pport); + break; + + case BFA_PPORT_SM_STOP: + bfa_reqq_wcancel(&pport->reqq_wait); + bfa_sm_set_state(pport, bfa_pport_sm_stopped); + break; + + case BFA_PPORT_SM_ENABLE: + /** + * Already enable is in progress. + */ + break; + + case BFA_PPORT_SM_DISABLE: + /** + * Just send disable request to firmware when room becomes + * available in request queue. + */ + bfa_sm_set_state(pport, bfa_pport_sm_disabled); + bfa_reqq_wcancel(&pport->reqq_wait); + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_DISABLE, 0, "Port Disable"); + bfa_pport_aen_post(pport, BFA_PORT_AEN_DISABLE); + break; + + case BFA_PPORT_SM_LINKUP: + case BFA_PPORT_SM_LINKDOWN: + /** + * Possible to get link events when doing back-to-back + * enable/disables. + */ + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_reqq_wcancel(&pport->reqq_wait); + bfa_sm_set_state(pport, bfa_pport_sm_iocdown); + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_enabling(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_FWRSP: + case BFA_PPORT_SM_LINKDOWN: + bfa_sm_set_state(pport, bfa_pport_sm_linkdown); + break; + + case BFA_PPORT_SM_LINKUP: + bfa_pport_update_linkinfo(pport); + bfa_sm_set_state(pport, bfa_pport_sm_linkup); + + bfa_assert(pport->event_cbfn); + bfa_pport_callback(pport, BFA_PPORT_LINKUP); + break; + + case BFA_PPORT_SM_ENABLE: + /** + * Already being enabled. + */ + break; + + case BFA_PPORT_SM_DISABLE: + if (bfa_pport_send_disable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_disabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_disabling_qwait); + + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_DISABLE, 0, "Port Disable"); + bfa_pport_aen_post(pport, BFA_PORT_AEN_DISABLE); + break; + + case BFA_PPORT_SM_STOP: + bfa_sm_set_state(pport, bfa_pport_sm_stopped); + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_sm_set_state(pport, bfa_pport_sm_iocdown); + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_linkdown(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_LINKUP: + bfa_pport_update_linkinfo(pport); + bfa_sm_set_state(pport, bfa_pport_sm_linkup); + bfa_assert(pport->event_cbfn); + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_ST_CHANGE, 0, "Port Linkup"); + bfa_pport_callback(pport, BFA_PPORT_LINKUP); + bfa_pport_aen_post(pport, BFA_PORT_AEN_ONLINE); + /** + * If QoS is enabled and it is not online, + * Send a separate event. + */ + if ((pport->cfg.qos_enabled) + && (bfa_os_ntohl(pport->qos_attr.state) != BFA_QOS_ONLINE)) + bfa_pport_aen_post(pport, BFA_PORT_AEN_QOS_NEG); + + break; + + case BFA_PPORT_SM_LINKDOWN: + /** + * Possible to get link down event. + */ + break; + + case BFA_PPORT_SM_ENABLE: + /** + * Already enabled. + */ + break; + + case BFA_PPORT_SM_DISABLE: + if (bfa_pport_send_disable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_disabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_disabling_qwait); + + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_DISABLE, 0, "Port Disable"); + bfa_pport_aen_post(pport, BFA_PORT_AEN_DISABLE); + break; + + case BFA_PPORT_SM_STOP: + bfa_sm_set_state(pport, bfa_pport_sm_stopped); + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_sm_set_state(pport, bfa_pport_sm_iocdown); + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_linkup(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_ENABLE: + /** + * Already enabled. + */ + break; + + case BFA_PPORT_SM_DISABLE: + if (bfa_pport_send_disable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_disabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_disabling_qwait); + + bfa_pport_reset_linkinfo(pport); + bfa_pport_callback(pport, BFA_PPORT_LINKDOWN); + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_DISABLE, 0, "Port Disable"); + bfa_pport_aen_post(pport, BFA_PORT_AEN_OFFLINE); + bfa_pport_aen_post(pport, BFA_PORT_AEN_DISABLE); + break; + + case BFA_PPORT_SM_LINKDOWN: + bfa_sm_set_state(pport, bfa_pport_sm_linkdown); + bfa_pport_reset_linkinfo(pport); + bfa_pport_callback(pport, BFA_PPORT_LINKDOWN); + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_ST_CHANGE, 0, "Port Linkdown"); + if (BFA_PORT_IS_DISABLED(pport->bfa)) { + bfa_pport_aen_post(pport, BFA_PORT_AEN_OFFLINE); + } else { + bfa_pport_aen_post(pport, BFA_PORT_AEN_DISCONNECT); + } + break; + + case BFA_PPORT_SM_STOP: + bfa_sm_set_state(pport, bfa_pport_sm_stopped); + bfa_pport_reset_linkinfo(pport); + if (BFA_PORT_IS_DISABLED(pport->bfa)) { + bfa_pport_aen_post(pport, BFA_PORT_AEN_OFFLINE); + } else { + bfa_pport_aen_post(pport, BFA_PORT_AEN_DISCONNECT); + } + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_sm_set_state(pport, bfa_pport_sm_iocdown); + bfa_pport_reset_linkinfo(pport); + bfa_pport_callback(pport, BFA_PPORT_LINKDOWN); + if (BFA_PORT_IS_DISABLED(pport->bfa)) { + bfa_pport_aen_post(pport, BFA_PORT_AEN_OFFLINE); + } else { + bfa_pport_aen_post(pport, BFA_PORT_AEN_DISCONNECT); + } + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_disabling_qwait(struct bfa_pport_s *pport, + enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_QRESUME: + bfa_sm_set_state(pport, bfa_pport_sm_disabling); + bfa_pport_send_disable(pport); + break; + + case BFA_PPORT_SM_STOP: + bfa_sm_set_state(pport, bfa_pport_sm_stopped); + bfa_reqq_wcancel(&pport->reqq_wait); + break; + + case BFA_PPORT_SM_DISABLE: + /** + * Already being disabled. + */ + break; + + case BFA_PPORT_SM_LINKUP: + case BFA_PPORT_SM_LINKDOWN: + /** + * Possible to get link events when doing back-to-back + * enable/disables. + */ + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_sm_set_state(pport, bfa_pport_sm_iocfail); + bfa_reqq_wcancel(&pport->reqq_wait); + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_disabling(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_FWRSP: + bfa_sm_set_state(pport, bfa_pport_sm_disabled); + break; + + case BFA_PPORT_SM_DISABLE: + /** + * Already being disabled. + */ + break; + + case BFA_PPORT_SM_ENABLE: + if (bfa_pport_send_enable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_enabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_enabling_qwait); + + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_ENABLE, 0, "Port Enable"); + bfa_pport_aen_post(pport, BFA_PORT_AEN_ENABLE); + break; + + case BFA_PPORT_SM_STOP: + bfa_sm_set_state(pport, bfa_pport_sm_stopped); + break; + + case BFA_PPORT_SM_LINKUP: + case BFA_PPORT_SM_LINKDOWN: + /** + * Possible to get link events when doing back-to-back + * enable/disables. + */ + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_sm_set_state(pport, bfa_pport_sm_iocfail); + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_disabled(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_START: + /** + * Ignore start event for a port that is disabled. + */ + break; + + case BFA_PPORT_SM_STOP: + bfa_sm_set_state(pport, bfa_pport_sm_stopped); + break; + + case BFA_PPORT_SM_ENABLE: + if (bfa_pport_send_enable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_enabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_enabling_qwait); + + bfa_plog_str(pport->bfa->plog, BFA_PL_MID_HAL, + BFA_PL_EID_PORT_ENABLE, 0, "Port Enable"); + bfa_pport_aen_post(pport, BFA_PORT_AEN_ENABLE); + break; + + case BFA_PPORT_SM_DISABLE: + /** + * Already disabled. + */ + break; + + case BFA_PPORT_SM_HWFAIL: + bfa_sm_set_state(pport, bfa_pport_sm_iocfail); + break; + + default: + bfa_sm_fault(pport->bfa, event); + } +} + +static void +bfa_pport_sm_stopped(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_START: + if (bfa_pport_send_enable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_enabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_enabling_qwait); + break; + + default: + /** + * Ignore all other events. + */ + ; + } +} + +/** + * Port is enabled. IOC is down/failed. + */ +static void +bfa_pport_sm_iocdown(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_START: + if (bfa_pport_send_enable(pport)) + bfa_sm_set_state(pport, bfa_pport_sm_enabling); + else + bfa_sm_set_state(pport, bfa_pport_sm_enabling_qwait); + break; + + default: + /** + * Ignore all events. + */ + ; + } +} + +/** + * Port is disabled. IOC is down/failed. + */ +static void +bfa_pport_sm_iocfail(struct bfa_pport_s *pport, enum bfa_pport_sm_event event) +{ + bfa_trc(pport->bfa, event); + + switch (event) { + case BFA_PPORT_SM_START: + bfa_sm_set_state(pport, bfa_pport_sm_disabled); + break; + + case BFA_PPORT_SM_ENABLE: + bfa_sm_set_state(pport, bfa_pport_sm_iocdown); + break; + + default: + /** + * Ignore all events. + */ + ; + } +} + + + +/** + * bfa_pport_private + */ + +static void +__bfa_cb_port_event(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_pport_s *pport = cbarg; + + if (complete) + pport->event_cbfn(pport->event_cbarg, pport->hcb_event); +} + +#define PPORT_STATS_DMA_SZ (BFA_ROUNDUP(sizeof(union bfa_pport_stats_u), \ + BFA_CACHELINE_SZ)) + +static void +bfa_pport_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *ndm_len, + u32 *dm_len) +{ + *dm_len += PPORT_STATS_DMA_SZ; +} + +static void +bfa_pport_qresume(void *cbarg) +{ + struct bfa_pport_s *port = cbarg; + + bfa_sm_send_event(port, BFA_PPORT_SM_QRESUME); +} + +static void +bfa_pport_mem_claim(struct bfa_pport_s *pport, struct bfa_meminfo_s *meminfo) +{ + u8 *dm_kva; + u64 dm_pa; + + dm_kva = bfa_meminfo_dma_virt(meminfo); + dm_pa = bfa_meminfo_dma_phys(meminfo); + + pport->stats_kva = dm_kva; + pport->stats_pa = dm_pa; + pport->stats = (union bfa_pport_stats_u *)dm_kva; + + dm_kva += PPORT_STATS_DMA_SZ; + dm_pa += PPORT_STATS_DMA_SZ; + + bfa_meminfo_dma_virt(meminfo) = dm_kva; + bfa_meminfo_dma_phys(meminfo) = dm_pa; +} + +/** + * Memory initialization. + */ +static void +bfa_pport_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + struct bfa_pport_cfg_s *port_cfg = &pport->cfg; + + bfa_os_memset(pport, 0, sizeof(struct bfa_pport_s)); + pport->bfa = bfa; + + bfa_pport_mem_claim(pport, meminfo); + + bfa_sm_set_state(pport, bfa_pport_sm_uninit); + + /** + * initialize and set default configuration + */ + port_cfg->topology = BFA_PPORT_TOPOLOGY_P2P; + port_cfg->speed = BFA_PPORT_SPEED_AUTO; + port_cfg->trunked = BFA_FALSE; + port_cfg->maxfrsize = 0; + + port_cfg->trl_def_speed = BFA_PPORT_SPEED_1GBPS; + + bfa_reqq_winit(&pport->reqq_wait, bfa_pport_qresume, pport); +} + +static void +bfa_pport_initdone(struct bfa_s *bfa) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + /** + * Initialize port attributes from IOC hardware data. + */ + bfa_pport_set_wwns(pport); + if (pport->cfg.maxfrsize == 0) + pport->cfg.maxfrsize = bfa_ioc_maxfrsize(&bfa->ioc); + pport->cfg.rx_bbcredit = bfa_ioc_rx_bbcredit(&bfa->ioc); + pport->speed_sup = bfa_ioc_speed_sup(&bfa->ioc); + + bfa_assert(pport->cfg.maxfrsize); + bfa_assert(pport->cfg.rx_bbcredit); + bfa_assert(pport->speed_sup); +} + +static void +bfa_pport_detach(struct bfa_s *bfa) +{ +} + +/** + * Called when IOC is ready. + */ +static void +bfa_pport_start(struct bfa_s *bfa) +{ + bfa_sm_send_event(BFA_PORT_MOD(bfa), BFA_PPORT_SM_START); +} + +/** + * Called before IOC is stopped. + */ +static void +bfa_pport_stop(struct bfa_s *bfa) +{ + bfa_sm_send_event(BFA_PORT_MOD(bfa), BFA_PPORT_SM_STOP); +} + +/** + * Called when IOC failure is detected. + */ +static void +bfa_pport_iocdisable(struct bfa_s *bfa) +{ + bfa_sm_send_event(BFA_PORT_MOD(bfa), BFA_PPORT_SM_HWFAIL); +} + +static void +bfa_pport_update_linkinfo(struct bfa_pport_s *pport) +{ + struct bfi_pport_event_s *pevent = pport->event_arg.i2hmsg.event; + + pport->speed = pevent->link_state.speed; + pport->topology = pevent->link_state.topology; + + if (pport->topology == BFA_PPORT_TOPOLOGY_LOOP) + pport->myalpa = pevent->link_state.tl.loop_info.myalpa; + + /* + * QoS Details + */ + bfa_os_assign(pport->qos_attr, pevent->link_state.qos_attr); + bfa_os_assign(pport->qos_vc_attr, pevent->link_state.qos_vc_attr); + + bfa_trc(pport->bfa, pport->speed); + bfa_trc(pport->bfa, pport->topology); +} + +static void +bfa_pport_reset_linkinfo(struct bfa_pport_s *pport) +{ + pport->speed = BFA_PPORT_SPEED_UNKNOWN; + pport->topology = BFA_PPORT_TOPOLOGY_NONE; +} + +/** + * Send port enable message to firmware. + */ +static bfa_boolean_t +bfa_pport_send_enable(struct bfa_pport_s *port) +{ + struct bfi_pport_enable_req_s *m; + + /** + * Increment message tag before queue check, so that responses to old + * requests are discarded. + */ + port->msgtag++; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(port->bfa, BFA_REQQ_PORT); + if (!m) { + bfa_reqq_wait(port->bfa, BFA_REQQ_PORT, &port->reqq_wait); + return BFA_FALSE; + } + + bfi_h2i_set(m->mh, BFI_MC_FC_PORT, BFI_PPORT_H2I_ENABLE_REQ, + bfa_lpuid(port->bfa)); + m->nwwn = port->nwwn; + m->pwwn = port->pwwn; + m->port_cfg = port->cfg; + m->msgtag = port->msgtag; + m->port_cfg.maxfrsize = bfa_os_htons(port->cfg.maxfrsize); + bfa_dma_be_addr_set(m->stats_dma_addr, port->stats_pa); + bfa_trc(port->bfa, m->stats_dma_addr.a32.addr_lo); + bfa_trc(port->bfa, m->stats_dma_addr.a32.addr_hi); + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(port->bfa, BFA_REQQ_PORT); + return BFA_TRUE; +} + +/** + * Send port disable message to firmware. + */ +static bfa_boolean_t +bfa_pport_send_disable(struct bfa_pport_s *port) +{ + bfi_pport_disable_req_t *m; + + /** + * Increment message tag before queue check, so that responses to old + * requests are discarded. + */ + port->msgtag++; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(port->bfa, BFA_REQQ_PORT); + if (!m) { + bfa_reqq_wait(port->bfa, BFA_REQQ_PORT, &port->reqq_wait); + return BFA_FALSE; + } + + bfi_h2i_set(m->mh, BFI_MC_FC_PORT, BFI_PPORT_H2I_DISABLE_REQ, + bfa_lpuid(port->bfa)); + m->msgtag = port->msgtag; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(port->bfa, BFA_REQQ_PORT); + + return BFA_TRUE; +} + +static void +bfa_pport_set_wwns(struct bfa_pport_s *port) +{ + port->pwwn = bfa_ioc_get_pwwn(&port->bfa->ioc); + port->nwwn = bfa_ioc_get_nwwn(&port->bfa->ioc); + + bfa_trc(port->bfa, port->pwwn); + bfa_trc(port->bfa, port->nwwn); +} + +static void +bfa_port_send_txcredit(void *port_cbarg) +{ + + struct bfa_pport_s *port = port_cbarg; + struct bfi_pport_set_svc_params_req_s *m; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(port->bfa, BFA_REQQ_PORT); + if (!m) { + bfa_trc(port->bfa, port->cfg.tx_bbcredit); + return; + } + + bfi_h2i_set(m->mh, BFI_MC_FC_PORT, BFI_PPORT_H2I_SET_SVC_PARAMS_REQ, + bfa_lpuid(port->bfa)); + m->tx_bbcredit = bfa_os_htons((u16) port->cfg.tx_bbcredit); + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(port->bfa, BFA_REQQ_PORT); +} + + + +/** + * bfa_pport_public + */ + +/** + * Firmware message handler. + */ +void +bfa_pport_isr(struct bfa_s *bfa, struct bfi_msg_s *msg) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + union bfi_pport_i2h_msg_u i2hmsg; + + i2hmsg.msg = msg; + pport->event_arg.i2hmsg = i2hmsg; + + switch (msg->mhdr.msg_id) { + case BFI_PPORT_I2H_ENABLE_RSP: + if (pport->msgtag == i2hmsg.enable_rsp->msgtag) + bfa_sm_send_event(pport, BFA_PPORT_SM_FWRSP); + break; + + case BFI_PPORT_I2H_DISABLE_RSP: + if (pport->msgtag == i2hmsg.enable_rsp->msgtag) + bfa_sm_send_event(pport, BFA_PPORT_SM_FWRSP); + break; + + case BFI_PPORT_I2H_EVENT: + switch (i2hmsg.event->link_state.linkstate) { + case BFA_PPORT_LINKUP: + bfa_sm_send_event(pport, BFA_PPORT_SM_LINKUP); + break; + case BFA_PPORT_LINKDOWN: + bfa_sm_send_event(pport, BFA_PPORT_SM_LINKDOWN); + break; + case BFA_PPORT_TRUNK_LINKDOWN: + /** todo: event notification */ + break; + } + break; + + case BFI_PPORT_I2H_GET_STATS_RSP: + case BFI_PPORT_I2H_GET_QOS_STATS_RSP: + /* + * check for timer pop before processing the rsp + */ + if (pport->stats_busy == BFA_FALSE + || pport->stats_status == BFA_STATUS_ETIMER) + break; + + bfa_timer_stop(&pport->timer); + pport->stats_status = i2hmsg.getstats_rsp->status; + bfa_cb_queue(pport->bfa, &pport->hcb_qe, __bfa_cb_port_stats, + pport); + break; + case BFI_PPORT_I2H_CLEAR_STATS_RSP: + case BFI_PPORT_I2H_CLEAR_QOS_STATS_RSP: + /* + * check for timer pop before processing the rsp + */ + if (pport->stats_busy == BFA_FALSE + || pport->stats_status == BFA_STATUS_ETIMER) + break; + + bfa_timer_stop(&pport->timer); + pport->stats_status = BFA_STATUS_OK; + bfa_cb_queue(pport->bfa, &pport->hcb_qe, + __bfa_cb_port_stats_clr, pport); + break; + + default: + bfa_assert(0); + } +} + + + +/** + * bfa_pport_api + */ + +/** + * Registered callback for port events. + */ +void +bfa_pport_event_register(struct bfa_s *bfa, + void (*cbfn) (void *cbarg, bfa_pport_event_t event), + void *cbarg) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + pport->event_cbfn = cbfn; + pport->event_cbarg = cbarg; +} + +bfa_status_t +bfa_pport_enable(struct bfa_s *bfa) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + if (pport->diag_busy) + return (BFA_STATUS_DIAG_BUSY); + else if (bfa_sm_cmp_state + (BFA_PORT_MOD(bfa), bfa_pport_sm_disabling_qwait)) + return (BFA_STATUS_DEVBUSY); + + bfa_sm_send_event(BFA_PORT_MOD(bfa), BFA_PPORT_SM_ENABLE); + return BFA_STATUS_OK; +} + +bfa_status_t +bfa_pport_disable(struct bfa_s *bfa) +{ + bfa_sm_send_event(BFA_PORT_MOD(bfa), BFA_PPORT_SM_DISABLE); + return BFA_STATUS_OK; +} + +/** + * Configure port speed. + */ +bfa_status_t +bfa_pport_cfg_speed(struct bfa_s *bfa, enum bfa_pport_speed speed) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, speed); + + if ((speed != BFA_PPORT_SPEED_AUTO) && (speed > pport->speed_sup)) { + bfa_trc(bfa, pport->speed_sup); + return BFA_STATUS_UNSUPP_SPEED; + } + + pport->cfg.speed = speed; + + return (BFA_STATUS_OK); +} + +/** + * Get current speed. + */ +enum bfa_pport_speed +bfa_pport_get_speed(struct bfa_s *bfa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + return port->speed; +} + +/** + * Configure port topology. + */ +bfa_status_t +bfa_pport_cfg_topology(struct bfa_s *bfa, enum bfa_pport_topology topology) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, topology); + bfa_trc(bfa, pport->cfg.topology); + + switch (topology) { + case BFA_PPORT_TOPOLOGY_P2P: + case BFA_PPORT_TOPOLOGY_LOOP: + case BFA_PPORT_TOPOLOGY_AUTO: + break; + + default: + return BFA_STATUS_EINVAL; + } + + pport->cfg.topology = topology; + return (BFA_STATUS_OK); +} + +/** + * Get current topology. + */ +enum bfa_pport_topology +bfa_pport_get_topology(struct bfa_s *bfa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + return port->topology; +} + +bfa_status_t +bfa_pport_cfg_hardalpa(struct bfa_s *bfa, u8 alpa) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, alpa); + bfa_trc(bfa, pport->cfg.cfg_hardalpa); + bfa_trc(bfa, pport->cfg.hardalpa); + + pport->cfg.cfg_hardalpa = BFA_TRUE; + pport->cfg.hardalpa = alpa; + + return (BFA_STATUS_OK); +} + +bfa_status_t +bfa_pport_clr_hardalpa(struct bfa_s *bfa) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, pport->cfg.cfg_hardalpa); + bfa_trc(bfa, pport->cfg.hardalpa); + + pport->cfg.cfg_hardalpa = BFA_FALSE; + return (BFA_STATUS_OK); +} + +bfa_boolean_t +bfa_pport_get_hardalpa(struct bfa_s *bfa, u8 *alpa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + *alpa = port->cfg.hardalpa; + return port->cfg.cfg_hardalpa; +} + +u8 +bfa_pport_get_myalpa(struct bfa_s *bfa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + return port->myalpa; +} + +bfa_status_t +bfa_pport_cfg_maxfrsize(struct bfa_s *bfa, u16 maxfrsize) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, maxfrsize); + bfa_trc(bfa, pport->cfg.maxfrsize); + + /* + * with in range + */ + if ((maxfrsize > FC_MAX_PDUSZ) || (maxfrsize < FC_MIN_PDUSZ)) + return (BFA_STATUS_INVLD_DFSZ); + + /* + * power of 2, if not the max frame size of 2112 + */ + if ((maxfrsize != FC_MAX_PDUSZ) && (maxfrsize & (maxfrsize - 1))) + return (BFA_STATUS_INVLD_DFSZ); + + pport->cfg.maxfrsize = maxfrsize; + return (BFA_STATUS_OK); +} + +u16 +bfa_pport_get_maxfrsize(struct bfa_s *bfa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + return port->cfg.maxfrsize; +} + +u32 +bfa_pport_mypid(struct bfa_s *bfa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + return port->mypid; +} + +u8 +bfa_pport_get_rx_bbcredit(struct bfa_s *bfa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + return port->cfg.rx_bbcredit; +} + +void +bfa_pport_set_tx_bbcredit(struct bfa_s *bfa, u16 tx_bbcredit) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + port->cfg.tx_bbcredit = (u8) tx_bbcredit; + bfa_port_send_txcredit(port); +} + +/** + * Get port attributes. + */ + +wwn_t +bfa_pport_get_wwn(struct bfa_s *bfa, bfa_boolean_t node) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + if (node) + return pport->nwwn; + else + return pport->pwwn; +} + +void +bfa_pport_get_attr(struct bfa_s *bfa, struct bfa_pport_attr_s *attr) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_os_memset(attr, 0, sizeof(struct bfa_pport_attr_s)); + + attr->nwwn = pport->nwwn; + attr->pwwn = pport->pwwn; + + bfa_os_memcpy(&attr->pport_cfg, &pport->cfg, + sizeof(struct bfa_pport_cfg_s)); + /* + * speed attributes + */ + attr->pport_cfg.speed = pport->cfg.speed; + attr->speed_supported = pport->speed_sup; + attr->speed = pport->speed; + attr->cos_supported = FC_CLASS_3; + + /* + * topology attributes + */ + attr->pport_cfg.topology = pport->cfg.topology; + attr->topology = pport->topology; + + /* + * beacon attributes + */ + attr->beacon = pport->beacon; + attr->link_e2e_beacon = pport->link_e2e_beacon; + attr->plog_enabled = bfa_plog_get_setting(pport->bfa->plog); + + attr->pport_cfg.path_tov = bfa_fcpim_path_tov_get(bfa); + attr->pport_cfg.q_depth = bfa_fcpim_qdepth_get(bfa); + attr->port_state = bfa_sm_to_state(hal_pport_sm_table, pport->sm); + if (bfa_ioc_is_disabled(&pport->bfa->ioc)) + attr->port_state = BFA_PPORT_ST_IOCDIS; + else if (bfa_ioc_fw_mismatch(&pport->bfa->ioc)) + attr->port_state = BFA_PPORT_ST_FWMISMATCH; +} + +static void +bfa_port_stats_query(void *cbarg) +{ + struct bfa_pport_s *port = (struct bfa_pport_s *)cbarg; + bfi_pport_get_stats_req_t *msg; + + msg = bfa_reqq_next(port->bfa, BFA_REQQ_PORT); + + if (!msg) { + port->stats_qfull = BFA_TRUE; + bfa_reqq_winit(&port->stats_reqq_wait, bfa_port_stats_query, + port); + bfa_reqq_wait(port->bfa, BFA_REQQ_PORT, &port->stats_reqq_wait); + return; + } + port->stats_qfull = BFA_FALSE; + + bfa_os_memset(msg, 0, sizeof(bfi_pport_get_stats_req_t)); + bfi_h2i_set(msg->mh, BFI_MC_FC_PORT, BFI_PPORT_H2I_GET_STATS_REQ, + bfa_lpuid(port->bfa)); + bfa_reqq_produce(port->bfa, BFA_REQQ_PORT); + + return; +} + +static void +bfa_port_stats_clear(void *cbarg) +{ + struct bfa_pport_s *port = (struct bfa_pport_s *)cbarg; + bfi_pport_clear_stats_req_t *msg; + + msg = bfa_reqq_next(port->bfa, BFA_REQQ_PORT); + + if (!msg) { + port->stats_qfull = BFA_TRUE; + bfa_reqq_winit(&port->stats_reqq_wait, bfa_port_stats_clear, + port); + bfa_reqq_wait(port->bfa, BFA_REQQ_PORT, &port->stats_reqq_wait); + return; + } + port->stats_qfull = BFA_FALSE; + + bfa_os_memset(msg, 0, sizeof(bfi_pport_clear_stats_req_t)); + bfi_h2i_set(msg->mh, BFI_MC_FC_PORT, BFI_PPORT_H2I_CLEAR_STATS_REQ, + bfa_lpuid(port->bfa)); + bfa_reqq_produce(port->bfa, BFA_REQQ_PORT); + return; +} + +static void +bfa_port_qos_stats_clear(void *cbarg) +{ + struct bfa_pport_s *port = (struct bfa_pport_s *)cbarg; + bfi_pport_clear_qos_stats_req_t *msg; + + msg = bfa_reqq_next(port->bfa, BFA_REQQ_PORT); + + if (!msg) { + port->stats_qfull = BFA_TRUE; + bfa_reqq_winit(&port->stats_reqq_wait, bfa_port_qos_stats_clear, + port); + bfa_reqq_wait(port->bfa, BFA_REQQ_PORT, &port->stats_reqq_wait); + return; + } + port->stats_qfull = BFA_FALSE; + + bfa_os_memset(msg, 0, sizeof(bfi_pport_clear_qos_stats_req_t)); + bfi_h2i_set(msg->mh, BFI_MC_FC_PORT, BFI_PPORT_H2I_CLEAR_QOS_STATS_REQ, + bfa_lpuid(port->bfa)); + bfa_reqq_produce(port->bfa, BFA_REQQ_PORT); + return; +} + +static void +bfa_pport_stats_swap(union bfa_pport_stats_u *d, union bfa_pport_stats_u *s) +{ + u32 *dip = (u32 *) d; + u32 *sip = (u32 *) s; + int i; + + /* + * Do 64 bit fields swap first + */ + for (i = 0; + i < + ((sizeof(union bfa_pport_stats_u) - + sizeof(struct bfa_qos_stats_s)) / sizeof(u32)); i = i + 2) { +#ifdef __BIGENDIAN + dip[i] = bfa_os_ntohl(sip[i]); + dip[i + 1] = bfa_os_ntohl(sip[i + 1]); +#else + dip[i] = bfa_os_ntohl(sip[i + 1]); + dip[i + 1] = bfa_os_ntohl(sip[i]); +#endif + } + + /* + * Now swap the 32 bit fields + */ + for (; i < (sizeof(union bfa_pport_stats_u) / sizeof(u32)); ++i) + dip[i] = bfa_os_ntohl(sip[i]); +} + +static void +__bfa_cb_port_stats_clr(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_pport_s *port = cbarg; + + if (complete) { + port->stats_cbfn(port->stats_cbarg, port->stats_status); + } else { + port->stats_busy = BFA_FALSE; + port->stats_status = BFA_STATUS_OK; + } +} + +static void +bfa_port_stats_clr_timeout(void *cbarg) +{ + struct bfa_pport_s *port = (struct bfa_pport_s *)cbarg; + + bfa_trc(port->bfa, port->stats_qfull); + + if (port->stats_qfull) { + bfa_reqq_wcancel(&port->stats_reqq_wait); + port->stats_qfull = BFA_FALSE; + } + + port->stats_status = BFA_STATUS_ETIMER; + bfa_cb_queue(port->bfa, &port->hcb_qe, __bfa_cb_port_stats_clr, port); +} + +static void +__bfa_cb_port_stats(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_pport_s *port = cbarg; + + if (complete) { + if (port->stats_status == BFA_STATUS_OK) + bfa_pport_stats_swap(port->stats_ret, port->stats); + port->stats_cbfn(port->stats_cbarg, port->stats_status); + } else { + port->stats_busy = BFA_FALSE; + port->stats_status = BFA_STATUS_OK; + } +} + +static void +bfa_port_stats_timeout(void *cbarg) +{ + struct bfa_pport_s *port = (struct bfa_pport_s *)cbarg; + + bfa_trc(port->bfa, port->stats_qfull); + + if (port->stats_qfull) { + bfa_reqq_wcancel(&port->stats_reqq_wait); + port->stats_qfull = BFA_FALSE; + } + + port->stats_status = BFA_STATUS_ETIMER; + bfa_cb_queue(port->bfa, &port->hcb_qe, __bfa_cb_port_stats, port); +} + +#define BFA_PORT_STATS_TOV 1000 + +/** + * Fetch port attributes. + */ +bfa_status_t +bfa_pport_get_stats(struct bfa_s *bfa, union bfa_pport_stats_u *stats, + bfa_cb_pport_t cbfn, void *cbarg) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + if (port->stats_busy) { + bfa_trc(bfa, port->stats_busy); + return (BFA_STATUS_DEVBUSY); + } + + port->stats_busy = BFA_TRUE; + port->stats_ret = stats; + port->stats_cbfn = cbfn; + port->stats_cbarg = cbarg; + + bfa_port_stats_query(port); + + bfa_timer_start(bfa, &port->timer, bfa_port_stats_timeout, port, + BFA_PORT_STATS_TOV); + return (BFA_STATUS_OK); +} + +bfa_status_t +bfa_pport_clear_stats(struct bfa_s *bfa, bfa_cb_pport_t cbfn, void *cbarg) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + if (port->stats_busy) { + bfa_trc(bfa, port->stats_busy); + return (BFA_STATUS_DEVBUSY); + } + + port->stats_busy = BFA_TRUE; + port->stats_cbfn = cbfn; + port->stats_cbarg = cbarg; + + bfa_port_stats_clear(port); + + bfa_timer_start(bfa, &port->timer, bfa_port_stats_clr_timeout, port, + BFA_PORT_STATS_TOV); + return (BFA_STATUS_OK); +} + +bfa_status_t +bfa_pport_trunk_enable(struct bfa_s *bfa, u8 bitmap) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, bitmap); + bfa_trc(bfa, pport->cfg.trunked); + bfa_trc(bfa, pport->cfg.trunk_ports); + + if (!bitmap || (bitmap & (bitmap - 1))) + return BFA_STATUS_EINVAL; + + pport->cfg.trunked = BFA_TRUE; + pport->cfg.trunk_ports = bitmap; + + return BFA_STATUS_OK; +} + +void +bfa_pport_qos_get_attr(struct bfa_s *bfa, struct bfa_qos_attr_s *qos_attr) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + qos_attr->state = bfa_os_ntohl(pport->qos_attr.state); + qos_attr->total_bb_cr = bfa_os_ntohl(pport->qos_attr.total_bb_cr); +} + +void +bfa_pport_qos_get_vc_attr(struct bfa_s *bfa, + struct bfa_qos_vc_attr_s *qos_vc_attr) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + struct bfa_qos_vc_attr_s *bfa_vc_attr = &pport->qos_vc_attr; + u32 i = 0; + + qos_vc_attr->total_vc_count = bfa_os_ntohs(bfa_vc_attr->total_vc_count); + qos_vc_attr->shared_credit = bfa_os_ntohs(bfa_vc_attr->shared_credit); + qos_vc_attr->elp_opmode_flags = + bfa_os_ntohl(bfa_vc_attr->elp_opmode_flags); + + /* + * Individual VC info + */ + while (i < qos_vc_attr->total_vc_count) { + qos_vc_attr->vc_info[i].vc_credit = + bfa_vc_attr->vc_info[i].vc_credit; + qos_vc_attr->vc_info[i].borrow_credit = + bfa_vc_attr->vc_info[i].borrow_credit; + qos_vc_attr->vc_info[i].priority = + bfa_vc_attr->vc_info[i].priority; + ++i; + } +} + +/** + * Fetch QoS Stats. + */ +bfa_status_t +bfa_pport_get_qos_stats(struct bfa_s *bfa, union bfa_pport_stats_u *stats, + bfa_cb_pport_t cbfn, void *cbarg) +{ + /* + * QoS stats is embedded in port stats + */ + return (bfa_pport_get_stats(bfa, stats, cbfn, cbarg)); +} + +bfa_status_t +bfa_pport_clear_qos_stats(struct bfa_s *bfa, bfa_cb_pport_t cbfn, void *cbarg) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + if (port->stats_busy) { + bfa_trc(bfa, port->stats_busy); + return (BFA_STATUS_DEVBUSY); + } + + port->stats_busy = BFA_TRUE; + port->stats_cbfn = cbfn; + port->stats_cbarg = cbarg; + + bfa_port_qos_stats_clear(port); + + bfa_timer_start(bfa, &port->timer, bfa_port_stats_clr_timeout, port, + BFA_PORT_STATS_TOV); + return (BFA_STATUS_OK); +} + +/** + * Fetch port attributes. + */ +bfa_status_t +bfa_pport_trunk_disable(struct bfa_s *bfa) +{ + return (BFA_STATUS_OK); +} + +bfa_boolean_t +bfa_pport_trunk_query(struct bfa_s *bfa, u32 *bitmap) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + *bitmap = port->cfg.trunk_ports; + return port->cfg.trunked; +} + +bfa_boolean_t +bfa_pport_is_disabled(struct bfa_s *bfa) +{ + struct bfa_pport_s *port = BFA_PORT_MOD(bfa); + + return (bfa_sm_to_state(hal_pport_sm_table, port->sm) == + BFA_PPORT_ST_DISABLED); + +} + +bfa_boolean_t +bfa_pport_is_ratelim(struct bfa_s *bfa) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + +return (pport->cfg.ratelimit ? BFA_TRUE : BFA_FALSE); + +} + +void +bfa_pport_cfg_qos(struct bfa_s *bfa, bfa_boolean_t on_off) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, on_off); + bfa_trc(bfa, pport->cfg.qos_enabled); + + pport->cfg.qos_enabled = on_off; +} + +void +bfa_pport_cfg_ratelim(struct bfa_s *bfa, bfa_boolean_t on_off) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, on_off); + bfa_trc(bfa, pport->cfg.ratelimit); + + pport->cfg.ratelimit = on_off; + if (pport->cfg.trl_def_speed == BFA_PPORT_SPEED_UNKNOWN) + pport->cfg.trl_def_speed = BFA_PPORT_SPEED_1GBPS; +} + +/** + * Configure default minimum ratelim speed + */ +bfa_status_t +bfa_pport_cfg_ratelim_speed(struct bfa_s *bfa, enum bfa_pport_speed speed) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, speed); + + /* + * Auto and speeds greater than the supported speed, are invalid + */ + if ((speed == BFA_PPORT_SPEED_AUTO) || (speed > pport->speed_sup)) { + bfa_trc(bfa, pport->speed_sup); + return BFA_STATUS_UNSUPP_SPEED; + } + + pport->cfg.trl_def_speed = speed; + + return (BFA_STATUS_OK); +} + +/** + * Get default minimum ratelim speed + */ +enum bfa_pport_speed +bfa_pport_get_ratelim_speed(struct bfa_s *bfa) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, pport->cfg.trl_def_speed); + return (pport->cfg.trl_def_speed); + +} + +void +bfa_pport_busy(struct bfa_s *bfa, bfa_boolean_t status) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, status); + bfa_trc(bfa, pport->diag_busy); + + pport->diag_busy = status; +} + +void +bfa_pport_beacon(struct bfa_s *bfa, bfa_boolean_t beacon, + bfa_boolean_t link_e2e_beacon) +{ + struct bfa_pport_s *pport = BFA_PORT_MOD(bfa); + + bfa_trc(bfa, beacon); + bfa_trc(bfa, link_e2e_beacon); + bfa_trc(bfa, pport->beacon); + bfa_trc(bfa, pport->link_e2e_beacon); + + pport->beacon = beacon; + pport->link_e2e_beacon = link_e2e_beacon; +} + +bfa_boolean_t +bfa_pport_is_linkup(struct bfa_s *bfa) +{ + return bfa_sm_cmp_state(BFA_PORT_MOD(bfa), bfa_pport_sm_linkup); +} + + diff --git a/drivers/scsi/bfa/bfa_fcs.c b/drivers/scsi/bfa/bfa_fcs.c new file mode 100644 index 000000000000..7cb39a306ea9 --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcs.c @@ -0,0 +1,182 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs.c BFA FCS main + */ + +#include <fcs/bfa_fcs.h> +#include "fcs_port.h" +#include "fcs_uf.h" +#include "fcs_vport.h" +#include "fcs_rport.h" +#include "fcs_fabric.h" +#include "fcs_fcpim.h" +#include "fcs_fcptm.h" +#include "fcbuild.h" +#include "fcs.h" +#include "bfad_drv.h" +#include <fcb/bfa_fcb.h> + +/** + * FCS sub-modules + */ +struct bfa_fcs_mod_s { + void (*modinit) (struct bfa_fcs_s *fcs); + void (*modexit) (struct bfa_fcs_s *fcs); +}; + +#define BFA_FCS_MODULE(_mod) { _mod ## _modinit, _mod ## _modexit } + +static struct bfa_fcs_mod_s fcs_modules[] = { + BFA_FCS_MODULE(bfa_fcs_pport), + BFA_FCS_MODULE(bfa_fcs_uf), + BFA_FCS_MODULE(bfa_fcs_fabric), + BFA_FCS_MODULE(bfa_fcs_vport), + BFA_FCS_MODULE(bfa_fcs_rport), + BFA_FCS_MODULE(bfa_fcs_fcpim), +}; + +/** + * fcs_api BFA FCS API + */ + +static void +bfa_fcs_exit_comp(void *fcs_cbarg) +{ + struct bfa_fcs_s *fcs = fcs_cbarg; + struct bfad_s *bfad = fcs->bfad; + + complete(&bfad->comp); +} + + + +/** + * fcs_api BFA FCS API + */ + +/** + * FCS instance initialization. + * + * param[in] fcs FCS instance + * param[in] bfa BFA instance + * param[in] bfad BFA driver instance + * + * return None + */ +void +bfa_fcs_init(struct bfa_fcs_s *fcs, struct bfa_s *bfa, struct bfad_s *bfad, + bfa_boolean_t min_cfg) +{ + int i; + struct bfa_fcs_mod_s *mod; + + fcs->bfa = bfa; + fcs->bfad = bfad; + fcs->min_cfg = min_cfg; + + bfa_attach_fcs(bfa); + fcbuild_init(); + + for (i = 0; i < sizeof(fcs_modules) / sizeof(fcs_modules[0]); i++) { + mod = &fcs_modules[i]; + mod->modinit(fcs); + } +} + +/** + * Start FCS operations. + */ +void +bfa_fcs_start(struct bfa_fcs_s *fcs) +{ + bfa_fcs_fabric_modstart(fcs); +} + +/** + * FCS driver details initialization. + * + * param[in] fcs FCS instance + * param[in] driver_info Driver Details + * + * return None + */ +void +bfa_fcs_driver_info_init(struct bfa_fcs_s *fcs, + struct bfa_fcs_driver_info_s *driver_info) +{ + + fcs->driver_info = *driver_info; + + bfa_fcs_fabric_psymb_init(&fcs->fabric); +} + +/** + * FCS instance cleanup and exit. + * + * param[in] fcs FCS instance + * return None + */ +void +bfa_fcs_exit(struct bfa_fcs_s *fcs) +{ + struct bfa_fcs_mod_s *mod; + int nmods, i; + + bfa_wc_init(&fcs->wc, bfa_fcs_exit_comp, fcs); + + nmods = sizeof(fcs_modules) / sizeof(fcs_modules[0]); + + for (i = 0; i < nmods; i++) { + bfa_wc_up(&fcs->wc); + + mod = &fcs_modules[i]; + mod->modexit(fcs); + } + + bfa_wc_wait(&fcs->wc); +} + + +void +bfa_fcs_trc_init(struct bfa_fcs_s *fcs, struct bfa_trc_mod_s *trcmod) +{ + fcs->trcmod = trcmod; +} + + +void +bfa_fcs_log_init(struct bfa_fcs_s *fcs, struct bfa_log_mod_s *logmod) +{ + fcs->logm = logmod; +} + + +void +bfa_fcs_aen_init(struct bfa_fcs_s *fcs, struct bfa_aen_s *aen) +{ + fcs->aen = aen; +} + +void +bfa_fcs_modexit_comp(struct bfa_fcs_s *fcs) +{ + bfa_wc_down(&fcs->wc); +} + + diff --git a/drivers/scsi/bfa/bfa_fcs_lport.c b/drivers/scsi/bfa/bfa_fcs_lport.c new file mode 100644 index 000000000000..8975ed041dc0 --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcs_lport.c @@ -0,0 +1,940 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_port.c BFA FCS port + */ + +#include <fcs/bfa_fcs.h> +#include <fcs/bfa_fcs_lport.h> +#include <fcs/bfa_fcs_rport.h> +#include <fcb/bfa_fcb_port.h> +#include <bfa_svc.h> +#include <log/bfa_log_fcs.h> +#include "fcs.h" +#include "fcs_lport.h" +#include "fcs_vport.h" +#include "fcs_rport.h" +#include "fcs_fcxp.h" +#include "fcs_trcmod.h" +#include "lport_priv.h" +#include <aen/bfa_aen_lport.h> + +BFA_TRC_FILE(FCS, PORT); + +/** + * Forward declarations + */ + +static void bfa_fcs_port_aen_post(struct bfa_fcs_port_s *port, + enum bfa_lport_aen_event event); +static void bfa_fcs_port_send_ls_rjt(struct bfa_fcs_port_s *port, + struct fchs_s *rx_fchs, u8 reason_code, + u8 reason_code_expl); +static void bfa_fcs_port_plogi(struct bfa_fcs_port_s *port, + struct fchs_s *rx_fchs, + struct fc_logi_s *plogi); +static void bfa_fcs_port_online_actions(struct bfa_fcs_port_s *port); +static void bfa_fcs_port_offline_actions(struct bfa_fcs_port_s *port); +static void bfa_fcs_port_unknown_init(struct bfa_fcs_port_s *port); +static void bfa_fcs_port_unknown_online(struct bfa_fcs_port_s *port); +static void bfa_fcs_port_unknown_offline(struct bfa_fcs_port_s *port); +static void bfa_fcs_port_deleted(struct bfa_fcs_port_s *port); +static void bfa_fcs_port_echo(struct bfa_fcs_port_s *port, + struct fchs_s *rx_fchs, + struct fc_echo_s *echo, u16 len); +static void bfa_fcs_port_rnid(struct bfa_fcs_port_s *port, + struct fchs_s *rx_fchs, + struct fc_rnid_cmd_s *rnid, u16 len); +static void bfa_fs_port_get_gen_topo_data(struct bfa_fcs_port_s *port, + struct fc_rnid_general_topology_data_s *gen_topo_data); + +static struct { + void (*init) (struct bfa_fcs_port_s *port); + void (*online) (struct bfa_fcs_port_s *port); + void (*offline) (struct bfa_fcs_port_s *port); +} __port_action[] = { + { + bfa_fcs_port_unknown_init, bfa_fcs_port_unknown_online, + bfa_fcs_port_unknown_offline}, { + bfa_fcs_port_fab_init, bfa_fcs_port_fab_online, + bfa_fcs_port_fab_offline}, { + bfa_fcs_port_loop_init, bfa_fcs_port_loop_online, + bfa_fcs_port_loop_offline}, { +bfa_fcs_port_n2n_init, bfa_fcs_port_n2n_online, + bfa_fcs_port_n2n_offline},}; + +/** + * fcs_port_sm FCS logical port state machine + */ + +enum bfa_fcs_port_event { + BFA_FCS_PORT_SM_CREATE = 1, + BFA_FCS_PORT_SM_ONLINE = 2, + BFA_FCS_PORT_SM_OFFLINE = 3, + BFA_FCS_PORT_SM_DELETE = 4, + BFA_FCS_PORT_SM_DELRPORT = 5, +}; + +static void bfa_fcs_port_sm_uninit(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event); +static void bfa_fcs_port_sm_init(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event); +static void bfa_fcs_port_sm_online(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event); +static void bfa_fcs_port_sm_offline(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event); +static void bfa_fcs_port_sm_deleting(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event); + +static void +bfa_fcs_port_sm_uninit(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event) +{ + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case BFA_FCS_PORT_SM_CREATE: + bfa_sm_set_state(port, bfa_fcs_port_sm_init); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_sm_init(struct bfa_fcs_port_s *port, enum bfa_fcs_port_event event) +{ + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case BFA_FCS_PORT_SM_ONLINE: + bfa_sm_set_state(port, bfa_fcs_port_sm_online); + bfa_fcs_port_online_actions(port); + break; + + case BFA_FCS_PORT_SM_DELETE: + bfa_sm_set_state(port, bfa_fcs_port_sm_uninit); + bfa_fcs_port_deleted(port); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_sm_online(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event) +{ + struct bfa_fcs_rport_s *rport; + struct list_head *qe, *qen; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case BFA_FCS_PORT_SM_OFFLINE: + bfa_sm_set_state(port, bfa_fcs_port_sm_offline); + bfa_fcs_port_offline_actions(port); + break; + + case BFA_FCS_PORT_SM_DELETE: + + __port_action[port->fabric->fab_type].offline(port); + + if (port->num_rports == 0) { + bfa_sm_set_state(port, bfa_fcs_port_sm_uninit); + bfa_fcs_port_deleted(port); + } else { + bfa_sm_set_state(port, bfa_fcs_port_sm_deleting); + list_for_each_safe(qe, qen, &port->rport_q) { + rport = (struct bfa_fcs_rport_s *)qe; + bfa_fcs_rport_delete(rport); + } + } + break; + + case BFA_FCS_PORT_SM_DELRPORT: + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_sm_offline(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event) +{ + struct bfa_fcs_rport_s *rport; + struct list_head *qe, *qen; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case BFA_FCS_PORT_SM_ONLINE: + bfa_sm_set_state(port, bfa_fcs_port_sm_online); + bfa_fcs_port_online_actions(port); + break; + + case BFA_FCS_PORT_SM_DELETE: + if (port->num_rports == 0) { + bfa_sm_set_state(port, bfa_fcs_port_sm_uninit); + bfa_fcs_port_deleted(port); + } else { + bfa_sm_set_state(port, bfa_fcs_port_sm_deleting); + list_for_each_safe(qe, qen, &port->rport_q) { + rport = (struct bfa_fcs_rport_s *)qe; + bfa_fcs_rport_delete(rport); + } + } + break; + + case BFA_FCS_PORT_SM_DELRPORT: + case BFA_FCS_PORT_SM_OFFLINE: + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_sm_deleting(struct bfa_fcs_port_s *port, + enum bfa_fcs_port_event event) +{ + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case BFA_FCS_PORT_SM_DELRPORT: + if (port->num_rports == 0) { + bfa_sm_set_state(port, bfa_fcs_port_sm_uninit); + bfa_fcs_port_deleted(port); + } + break; + + default: + bfa_assert(0); + } +} + + + +/** + * fcs_port_pvt + */ + +/** + * Send AEN notification + */ +static void +bfa_fcs_port_aen_post(struct bfa_fcs_port_s *port, + enum bfa_lport_aen_event event) +{ + union bfa_aen_data_u aen_data; + struct bfa_log_mod_s *logmod = port->fcs->logm; + enum bfa_port_role role = port->port_cfg.roles; + wwn_t lpwwn = bfa_fcs_port_get_pwwn(port); + char lpwwn_ptr[BFA_STRING_32]; + char *role_str[BFA_PORT_ROLE_FCP_MAX / 2 + 1] = + { "Initiator", "Target", "IPFC" }; + + wwn2str(lpwwn_ptr, lpwwn); + + bfa_assert(role <= BFA_PORT_ROLE_FCP_MAX); + + switch (event) { + case BFA_LPORT_AEN_ONLINE: + bfa_log(logmod, BFA_AEN_LPORT_ONLINE, lpwwn_ptr, + role_str[role / 2]); + break; + case BFA_LPORT_AEN_OFFLINE: + bfa_log(logmod, BFA_AEN_LPORT_OFFLINE, lpwwn_ptr, + role_str[role / 2]); + break; + case BFA_LPORT_AEN_NEW: + bfa_log(logmod, BFA_AEN_LPORT_NEW, lpwwn_ptr, + role_str[role / 2]); + break; + case BFA_LPORT_AEN_DELETE: + bfa_log(logmod, BFA_AEN_LPORT_DELETE, lpwwn_ptr, + role_str[role / 2]); + break; + case BFA_LPORT_AEN_DISCONNECT: + bfa_log(logmod, BFA_AEN_LPORT_DISCONNECT, lpwwn_ptr, + role_str[role / 2]); + break; + default: + break; + } + + aen_data.lport.vf_id = port->fabric->vf_id; + aen_data.lport.roles = role; + aen_data.lport.ppwwn = + bfa_fcs_port_get_pwwn(bfa_fcs_get_base_port(port->fcs)); + aen_data.lport.lpwwn = lpwwn; +} + +/* + * Send a LS reject + */ +static void +bfa_fcs_port_send_ls_rjt(struct bfa_fcs_port_s *port, struct fchs_s *rx_fchs, + u8 reason_code, u8 reason_code_expl) +{ + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + struct bfa_rport_s *bfa_rport = NULL; + int len; + + bfa_trc(port->fcs, rx_fchs->s_id); + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + len = fc_ls_rjt_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), rx_fchs->ox_id, + reason_code, reason_code_expl); + + bfa_fcxp_send(fcxp, bfa_rport, port->fabric->vf_id, port->lp_tag, + BFA_FALSE, FC_CLASS_3, len, &fchs, NULL, NULL, + FC_MAX_PDUSZ, 0); +} + +/** + * Process incoming plogi from a remote port. + */ +static void +bfa_fcs_port_plogi(struct bfa_fcs_port_s *port, struct fchs_s *rx_fchs, + struct fc_logi_s *plogi) +{ + struct bfa_fcs_rport_s *rport; + + bfa_trc(port->fcs, rx_fchs->d_id); + bfa_trc(port->fcs, rx_fchs->s_id); + + /* + * If min cfg mode is enabled, drop any incoming PLOGIs + */ + if (__fcs_min_cfg(port->fcs)) { + bfa_trc(port->fcs, rx_fchs->s_id); + return; + } + + if (fc_plogi_parse(rx_fchs) != FC_PARSE_OK) { + bfa_trc(port->fcs, rx_fchs->s_id); + /* + * send a LS reject + */ + bfa_fcs_port_send_ls_rjt(port, rx_fchs, + FC_LS_RJT_RSN_PROTOCOL_ERROR, + FC_LS_RJT_EXP_SPARMS_ERR_OPTIONS); + return; + } + + /** +* Direct Attach P2P mode : verify address assigned by the r-port. + */ + if ((!bfa_fcs_fabric_is_switched(port->fabric)) + && + (memcmp + ((void *)&bfa_fcs_port_get_pwwn(port), (void *)&plogi->port_name, + sizeof(wwn_t)) < 0)) { + if (BFA_FCS_PID_IS_WKA(rx_fchs->d_id)) { + /* + * Address assigned to us cannot be a WKA + */ + bfa_fcs_port_send_ls_rjt(port, rx_fchs, + FC_LS_RJT_RSN_PROTOCOL_ERROR, + FC_LS_RJT_EXP_INVALID_NPORT_ID); + return; + } + port->pid = rx_fchs->d_id; + } + + /** + * First, check if we know the device by pwwn. + */ + rport = bfa_fcs_port_get_rport_by_pwwn(port, plogi->port_name); + if (rport) { + /** + * Direct Attach P2P mode: handle address assigned by the rport. + */ + if ((!bfa_fcs_fabric_is_switched(port->fabric)) + && + (memcmp + ((void *)&bfa_fcs_port_get_pwwn(port), + (void *)&plogi->port_name, sizeof(wwn_t)) < 0)) { + port->pid = rx_fchs->d_id; + rport->pid = rx_fchs->s_id; + } + bfa_fcs_rport_plogi(rport, rx_fchs, plogi); + return; + } + + /** + * Next, lookup rport by PID. + */ + rport = bfa_fcs_port_get_rport_by_pid(port, rx_fchs->s_id); + if (!rport) { + /** + * Inbound PLOGI from a new device. + */ + bfa_fcs_rport_plogi_create(port, rx_fchs, plogi); + return; + } + + /** + * Rport is known only by PID. + */ + if (rport->pwwn) { + /** + * This is a different device with the same pid. Old device + * disappeared. Send implicit LOGO to old device. + */ + bfa_assert(rport->pwwn != plogi->port_name); + bfa_fcs_rport_logo_imp(rport); + + /** + * Inbound PLOGI from a new device (with old PID). + */ + bfa_fcs_rport_plogi_create(port, rx_fchs, plogi); + return; + } + + /** + * PLOGI crossing each other. + */ + bfa_assert(rport->pwwn == WWN_NULL); + bfa_fcs_rport_plogi(rport, rx_fchs, plogi); +} + +/* + * Process incoming ECHO. + * Since it does not require a login, it is processed here. + */ +static void +bfa_fcs_port_echo(struct bfa_fcs_port_s *port, struct fchs_s *rx_fchs, + struct fc_echo_s *echo, u16 rx_len) +{ + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + struct bfa_rport_s *bfa_rport = NULL; + int len, pyld_len; + + bfa_trc(port->fcs, rx_fchs->s_id); + bfa_trc(port->fcs, rx_fchs->d_id); + bfa_trc(port->fcs, rx_len); + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + len = fc_ls_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), rx_fchs->ox_id); + + /* + * Copy the payload (if any) from the echo frame + */ + pyld_len = rx_len - sizeof(struct fchs_s); + bfa_trc(port->fcs, pyld_len); + + if (pyld_len > len) + memcpy(((u8 *) bfa_fcxp_get_reqbuf(fcxp)) + + sizeof(struct fc_echo_s), (echo + 1), + (pyld_len - sizeof(struct fc_echo_s))); + + bfa_fcxp_send(fcxp, bfa_rport, port->fabric->vf_id, port->lp_tag, + BFA_FALSE, FC_CLASS_3, pyld_len, &fchs, NULL, NULL, + FC_MAX_PDUSZ, 0); +} + +/* + * Process incoming RNID. + * Since it does not require a login, it is processed here. + */ +static void +bfa_fcs_port_rnid(struct bfa_fcs_port_s *port, struct fchs_s *rx_fchs, + struct fc_rnid_cmd_s *rnid, u16 rx_len) +{ + struct fc_rnid_common_id_data_s common_id_data; + struct fc_rnid_general_topology_data_s gen_topo_data; + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + struct bfa_rport_s *bfa_rport = NULL; + u16 len; + u32 data_format; + + bfa_trc(port->fcs, rx_fchs->s_id); + bfa_trc(port->fcs, rx_fchs->d_id); + bfa_trc(port->fcs, rx_len); + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + /* + * Check Node Indentification Data Format + * We only support General Topology Discovery Format. + * For any other requested Data Formats, we return Common Node Id Data + * only, as per FC-LS. + */ + bfa_trc(port->fcs, rnid->node_id_data_format); + if (rnid->node_id_data_format == RNID_NODEID_DATA_FORMAT_DISCOVERY) { + data_format = RNID_NODEID_DATA_FORMAT_DISCOVERY; + /* + * Get General topology data for this port + */ + bfa_fs_port_get_gen_topo_data(port, &gen_topo_data); + } else { + data_format = RNID_NODEID_DATA_FORMAT_COMMON; + } + + /* + * Copy the Node Id Info + */ + common_id_data.port_name = bfa_fcs_port_get_pwwn(port); + common_id_data.node_name = bfa_fcs_port_get_nwwn(port); + + len = fc_rnid_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), rx_fchs->ox_id, + data_format, &common_id_data, &gen_topo_data); + + bfa_fcxp_send(fcxp, bfa_rport, port->fabric->vf_id, port->lp_tag, + BFA_FALSE, FC_CLASS_3, len, &fchs, NULL, NULL, + FC_MAX_PDUSZ, 0); + + return; +} + +/* + * Fill out General Topolpgy Discovery Data for RNID ELS. + */ +static void +bfa_fs_port_get_gen_topo_data(struct bfa_fcs_port_s *port, + struct fc_rnid_general_topology_data_s *gen_topo_data) +{ + + bfa_os_memset(gen_topo_data, 0, + sizeof(struct fc_rnid_general_topology_data_s)); + + gen_topo_data->asso_type = bfa_os_htonl(RNID_ASSOCIATED_TYPE_HOST); + gen_topo_data->phy_port_num = 0; /* @todo */ + gen_topo_data->num_attached_nodes = bfa_os_htonl(1); +} + +static void +bfa_fcs_port_online_actions(struct bfa_fcs_port_s *port) +{ + bfa_trc(port->fcs, port->fabric->oper_type); + + __port_action[port->fabric->fab_type].init(port); + __port_action[port->fabric->fab_type].online(port); + + bfa_fcs_port_aen_post(port, BFA_LPORT_AEN_ONLINE); + bfa_fcb_port_online(port->fcs->bfad, port->port_cfg.roles, + port->fabric->vf_drv, (port->vport == NULL) ? + NULL : port->vport->vport_drv); +} + +static void +bfa_fcs_port_offline_actions(struct bfa_fcs_port_s *port) +{ + struct list_head *qe, *qen; + struct bfa_fcs_rport_s *rport; + + bfa_trc(port->fcs, port->fabric->oper_type); + + __port_action[port->fabric->fab_type].offline(port); + + if (bfa_fcs_fabric_is_online(port->fabric) == BFA_TRUE) { + bfa_fcs_port_aen_post(port, BFA_LPORT_AEN_DISCONNECT); + } else { + bfa_fcs_port_aen_post(port, BFA_LPORT_AEN_OFFLINE); + } + bfa_fcb_port_offline(port->fcs->bfad, port->port_cfg.roles, + port->fabric->vf_drv, + (port->vport == NULL) ? NULL : port->vport->vport_drv); + + list_for_each_safe(qe, qen, &port->rport_q) { + rport = (struct bfa_fcs_rport_s *)qe; + bfa_fcs_rport_offline(rport); + } +} + +static void +bfa_fcs_port_unknown_init(struct bfa_fcs_port_s *port) +{ + bfa_assert(0); +} + +static void +bfa_fcs_port_unknown_online(struct bfa_fcs_port_s *port) +{ + bfa_assert(0); +} + +static void +bfa_fcs_port_unknown_offline(struct bfa_fcs_port_s *port) +{ + bfa_assert(0); +} + +static void +bfa_fcs_port_deleted(struct bfa_fcs_port_s *port) +{ + bfa_fcs_port_aen_post(port, BFA_LPORT_AEN_DELETE); + + /* + * Base port will be deleted by the OS driver + */ + if (port->vport) { + bfa_fcb_port_delete(port->fcs->bfad, port->port_cfg.roles, + port->fabric->vf_drv, + port->vport ? port->vport->vport_drv : NULL); + bfa_fcs_vport_delete_comp(port->vport); + } else { + bfa_fcs_fabric_port_delete_comp(port->fabric); + } +} + + + +/** + * fcs_lport_api BFA FCS port API + */ +/** + * Module initialization + */ +void +bfa_fcs_port_modinit(struct bfa_fcs_s *fcs) +{ + +} + +/** + * Module cleanup + */ +void +bfa_fcs_port_modexit(struct bfa_fcs_s *fcs) +{ + bfa_fcs_modexit_comp(fcs); +} + +/** + * Unsolicited frame receive handling. + */ +void +bfa_fcs_port_uf_recv(struct bfa_fcs_port_s *lport, struct fchs_s *fchs, + u16 len) +{ + u32 pid = fchs->s_id; + struct bfa_fcs_rport_s *rport = NULL; + struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + + bfa_stats(lport, uf_recvs); + + if (!bfa_fcs_port_is_online(lport)) { + bfa_stats(lport, uf_recv_drops); + return; + } + + /** + * First, handle ELSs that donot require a login. + */ + /* + * Handle PLOGI first + */ + if ((fchs->type == FC_TYPE_ELS) && + (els_cmd->els_code == FC_ELS_PLOGI)) { + bfa_fcs_port_plogi(lport, fchs, (struct fc_logi_s *) els_cmd); + return; + } + + /* + * Handle ECHO separately. + */ + if ((fchs->type == FC_TYPE_ELS) && (els_cmd->els_code == FC_ELS_ECHO)) { + bfa_fcs_port_echo(lport, fchs, + (struct fc_echo_s *) els_cmd, len); + return; + } + + /* + * Handle RNID separately. + */ + if ((fchs->type == FC_TYPE_ELS) && (els_cmd->els_code == FC_ELS_RNID)) { + bfa_fcs_port_rnid(lport, fchs, + (struct fc_rnid_cmd_s *) els_cmd, len); + return; + } + + /** + * look for a matching remote port ID + */ + rport = bfa_fcs_port_get_rport_by_pid(lport, pid); + if (rport) { + bfa_trc(rport->fcs, fchs->s_id); + bfa_trc(rport->fcs, fchs->d_id); + bfa_trc(rport->fcs, fchs->type); + + bfa_fcs_rport_uf_recv(rport, fchs, len); + return; + } + + /** + * Only handles ELS frames for now. + */ + if (fchs->type != FC_TYPE_ELS) { + bfa_trc(lport->fcs, fchs->type); + bfa_assert(0); + return; + } + + bfa_trc(lport->fcs, els_cmd->els_code); + if (els_cmd->els_code == FC_ELS_RSCN) { + bfa_fcs_port_scn_process_rscn(lport, fchs, len); + return; + } + + if (els_cmd->els_code == FC_ELS_LOGO) { + /** + * @todo Handle LOGO frames received. + */ + bfa_trc(lport->fcs, els_cmd->els_code); + return; + } + + if (els_cmd->els_code == FC_ELS_PRLI) { + /** + * @todo Handle PRLI frames received. + */ + bfa_trc(lport->fcs, els_cmd->els_code); + return; + } + + /** + * Unhandled ELS frames. Send a LS_RJT. + */ + bfa_fcs_port_send_ls_rjt(lport, fchs, FC_LS_RJT_RSN_CMD_NOT_SUPP, + FC_LS_RJT_EXP_NO_ADDL_INFO); + +} + +/** + * PID based Lookup for a R-Port in the Port R-Port Queue + */ +struct bfa_fcs_rport_s * +bfa_fcs_port_get_rport_by_pid(struct bfa_fcs_port_s *port, u32 pid) +{ + struct bfa_fcs_rport_s *rport; + struct list_head *qe; + + list_for_each(qe, &port->rport_q) { + rport = (struct bfa_fcs_rport_s *)qe; + if (rport->pid == pid) + return rport; + } + + bfa_trc(port->fcs, pid); + return NULL; +} + +/** + * PWWN based Lookup for a R-Port in the Port R-Port Queue + */ +struct bfa_fcs_rport_s * +bfa_fcs_port_get_rport_by_pwwn(struct bfa_fcs_port_s *port, wwn_t pwwn) +{ + struct bfa_fcs_rport_s *rport; + struct list_head *qe; + + list_for_each(qe, &port->rport_q) { + rport = (struct bfa_fcs_rport_s *)qe; + if (wwn_is_equal(rport->pwwn, pwwn)) + return rport; + } + + bfa_trc(port->fcs, pwwn); + return (NULL); +} + +/** + * NWWN based Lookup for a R-Port in the Port R-Port Queue + */ +struct bfa_fcs_rport_s * +bfa_fcs_port_get_rport_by_nwwn(struct bfa_fcs_port_s *port, wwn_t nwwn) +{ + struct bfa_fcs_rport_s *rport; + struct list_head *qe; + + list_for_each(qe, &port->rport_q) { + rport = (struct bfa_fcs_rport_s *)qe; + if (wwn_is_equal(rport->nwwn, nwwn)) + return rport; + } + + bfa_trc(port->fcs, nwwn); + return (NULL); +} + +/** + * Called by rport module when new rports are discovered. + */ +void +bfa_fcs_port_add_rport(struct bfa_fcs_port_s *port, + struct bfa_fcs_rport_s *rport) +{ + list_add_tail(&rport->qe, &port->rport_q); + port->num_rports++; +} + +/** + * Called by rport module to when rports are deleted. + */ +void +bfa_fcs_port_del_rport(struct bfa_fcs_port_s *port, + struct bfa_fcs_rport_s *rport) +{ + bfa_assert(bfa_q_is_on_q(&port->rport_q, rport)); + list_del(&rport->qe); + port->num_rports--; + + bfa_sm_send_event(port, BFA_FCS_PORT_SM_DELRPORT); +} + +/** + * Called by fabric for base port when fabric login is complete. + * Called by vport for virtual ports when FDISC is complete. + */ +void +bfa_fcs_port_online(struct bfa_fcs_port_s *port) +{ + bfa_sm_send_event(port, BFA_FCS_PORT_SM_ONLINE); +} + +/** + * Called by fabric for base port when fabric goes offline. + * Called by vport for virtual ports when virtual port becomes offline. + */ +void +bfa_fcs_port_offline(struct bfa_fcs_port_s *port) +{ + bfa_sm_send_event(port, BFA_FCS_PORT_SM_OFFLINE); +} + +/** + * Called by fabric to delete base lport and associated resources. + * + * Called by vport to delete lport and associated resources. Should call + * bfa_fcs_vport_delete_comp() for vports on completion. + */ +void +bfa_fcs_port_delete(struct bfa_fcs_port_s *port) +{ + bfa_sm_send_event(port, BFA_FCS_PORT_SM_DELETE); +} + +/** + * Called by fabric in private loop topology to process LIP event. + */ +void +bfa_fcs_port_lip(struct bfa_fcs_port_s *port) +{ +} + +/** + * Return TRUE if port is online, else return FALSE + */ +bfa_boolean_t +bfa_fcs_port_is_online(struct bfa_fcs_port_s *port) +{ + return (bfa_sm_cmp_state(port, bfa_fcs_port_sm_online)); +} + +/** + * Logical port initialization of base or virtual port. + * Called by fabric for base port or by vport for virtual ports. + */ +void +bfa_fcs_lport_init(struct bfa_fcs_port_s *lport, struct bfa_fcs_s *fcs, + u16 vf_id, struct bfa_port_cfg_s *port_cfg, + struct bfa_fcs_vport_s *vport) +{ + lport->fcs = fcs; + lport->fabric = bfa_fcs_vf_lookup(fcs, vf_id); + bfa_os_assign(lport->port_cfg, *port_cfg); + lport->vport = vport; + lport->lp_tag = (vport) ? bfa_lps_get_tag(vport->lps) : + bfa_lps_get_tag(lport->fabric->lps); + + INIT_LIST_HEAD(&lport->rport_q); + lport->num_rports = 0; + + lport->bfad_port = + bfa_fcb_port_new(fcs->bfad, lport, lport->port_cfg.roles, + lport->fabric->vf_drv, + vport ? vport->vport_drv : NULL); + bfa_fcs_port_aen_post(lport, BFA_LPORT_AEN_NEW); + + bfa_sm_set_state(lport, bfa_fcs_port_sm_uninit); + bfa_sm_send_event(lport, BFA_FCS_PORT_SM_CREATE); +} + + + +/** + * fcs_lport_api + */ + +void +bfa_fcs_port_get_attr(struct bfa_fcs_port_s *port, + struct bfa_port_attr_s *port_attr) +{ + if (bfa_sm_cmp_state(port, bfa_fcs_port_sm_online)) + port_attr->pid = port->pid; + else + port_attr->pid = 0; + + port_attr->port_cfg = port->port_cfg; + + if (port->fabric) { + port_attr->port_type = bfa_fcs_fabric_port_type(port->fabric); + port_attr->loopback = bfa_fcs_fabric_is_loopback(port->fabric); + port_attr->fabric_name = bfa_fcs_port_get_fabric_name(port); + memcpy(port_attr->fabric_ip_addr, + bfa_fcs_port_get_fabric_ipaddr(port), + BFA_FCS_FABRIC_IPADDR_SZ); + + if (port->vport != NULL) + port_attr->port_type = BFA_PPORT_TYPE_VPORT; + + } else { + port_attr->port_type = BFA_PPORT_TYPE_UNKNOWN; + port_attr->state = BFA_PORT_UNINIT; + } + +} + + diff --git a/drivers/scsi/bfa/bfa_fcs_port.c b/drivers/scsi/bfa/bfa_fcs_port.c new file mode 100644 index 000000000000..9c4b24e62de1 --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcs_port.c @@ -0,0 +1,68 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_pport.c BFA FCS PPORT ( physical port) + */ + +#include <fcs/bfa_fcs.h> +#include <bfa_svc.h> +#include <fcs/bfa_fcs_fabric.h> +#include "fcs_trcmod.h" +#include "fcs.h" +#include "fcs_fabric.h" +#include "fcs_port.h" + +BFA_TRC_FILE(FCS, PPORT); + +static void +bfa_fcs_pport_event_handler(void *cbarg, bfa_pport_event_t event) +{ + struct bfa_fcs_s *fcs = cbarg; + + bfa_trc(fcs, event); + + switch (event) { + case BFA_PPORT_LINKUP: + bfa_fcs_fabric_link_up(&fcs->fabric); + break; + + case BFA_PPORT_LINKDOWN: + bfa_fcs_fabric_link_down(&fcs->fabric); + break; + + case BFA_PPORT_TRUNK_LINKDOWN: + bfa_assert(0); + break; + + default: + bfa_assert(0); + } +} + +void +bfa_fcs_pport_modinit(struct bfa_fcs_s *fcs) +{ + bfa_pport_event_register(fcs->bfa, bfa_fcs_pport_event_handler, + fcs); +} + +void +bfa_fcs_pport_modexit(struct bfa_fcs_s *fcs) +{ + bfa_fcs_modexit_comp(fcs); +} diff --git a/drivers/scsi/bfa/bfa_fcs_uf.c b/drivers/scsi/bfa/bfa_fcs_uf.c new file mode 100644 index 000000000000..ad01db6444b2 --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcs_uf.c @@ -0,0 +1,105 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_uf.c BFA FCS UF ( Unsolicited Frames) + */ + +#include <fcs/bfa_fcs.h> +#include <bfa_svc.h> +#include <fcs/bfa_fcs_fabric.h> +#include "fcs.h" +#include "fcs_trcmod.h" +#include "fcs_fabric.h" +#include "fcs_uf.h" + +BFA_TRC_FILE(FCS, UF); + +/** + * BFA callback for unsolicited frame receive handler. + * + * @param[in] cbarg callback arg for receive handler + * @param[in] uf unsolicited frame descriptor + * + * @return None + */ +static void +bfa_fcs_uf_recv(void *cbarg, struct bfa_uf_s *uf) +{ + struct bfa_fcs_s *fcs = (struct bfa_fcs_s *) cbarg; + struct fchs_s *fchs = bfa_uf_get_frmbuf(uf); + u16 len = bfa_uf_get_frmlen(uf); + struct fc_vft_s *vft; + struct bfa_fcs_fabric_s *fabric; + + /** + * check for VFT header + */ + if (fchs->routing == FC_RTG_EXT_HDR && + fchs->cat_info == FC_CAT_VFT_HDR) { + bfa_stats(fcs, uf.tagged); + vft = bfa_uf_get_frmbuf(uf); + if (fcs->port_vfid == vft->vf_id) + fabric = &fcs->fabric; + else + fabric = bfa_fcs_vf_lookup(fcs, (u16) vft->vf_id); + + /** + * drop frame if vfid is unknown + */ + if (!fabric) { + bfa_assert(0); + bfa_stats(fcs, uf.vfid_unknown); + bfa_uf_free(uf); + return; + } + + /** + * skip vft header + */ + fchs = (struct fchs_s *) (vft + 1); + len -= sizeof(struct fc_vft_s); + + bfa_trc(fcs, vft->vf_id); + } else { + bfa_stats(fcs, uf.untagged); + fabric = &fcs->fabric; + } + + bfa_trc(fcs, ((u32 *) fchs)[0]); + bfa_trc(fcs, ((u32 *) fchs)[1]); + bfa_trc(fcs, ((u32 *) fchs)[2]); + bfa_trc(fcs, ((u32 *) fchs)[3]); + bfa_trc(fcs, ((u32 *) fchs)[4]); + bfa_trc(fcs, ((u32 *) fchs)[5]); + bfa_trc(fcs, len); + + bfa_fcs_fabric_uf_recv(fabric, fchs, len); + bfa_uf_free(uf); +} + +void +bfa_fcs_uf_modinit(struct bfa_fcs_s *fcs) +{ + bfa_uf_recv_register(fcs->bfa, bfa_fcs_uf_recv, fcs); +} + +void +bfa_fcs_uf_modexit(struct bfa_fcs_s *fcs) +{ + bfa_fcs_modexit_comp(fcs); +} diff --git a/drivers/scsi/bfa/bfa_fcxp.c b/drivers/scsi/bfa/bfa_fcxp.c new file mode 100644 index 000000000000..4754a0e9006a --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcxp.c @@ -0,0 +1,782 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfi/bfi_uf.h> +#include <cs/bfa_debug.h> + +BFA_TRC_FILE(HAL, FCXP); +BFA_MODULE(fcxp); + +/** + * forward declarations + */ +static void __bfa_fcxp_send_cbfn(void *cbarg, bfa_boolean_t complete); +static void hal_fcxp_rx_plog(struct bfa_s *bfa, struct bfa_fcxp_s *fcxp, + struct bfi_fcxp_send_rsp_s *fcxp_rsp); +static void hal_fcxp_tx_plog(struct bfa_s *bfa, u32 reqlen, + struct bfa_fcxp_s *fcxp, struct fchs_s *fchs); +static void bfa_fcxp_qresume(void *cbarg); +static void bfa_fcxp_queue(struct bfa_fcxp_s *fcxp, + struct bfi_fcxp_send_req_s *send_req); + +/** + * fcxp_pvt BFA FCXP private functions + */ + +static void +claim_fcxp_req_rsp_mem(struct bfa_fcxp_mod_s *mod, struct bfa_meminfo_s *mi) +{ + u8 *dm_kva = NULL; + u64 dm_pa; + u32 buf_pool_sz; + + dm_kva = bfa_meminfo_dma_virt(mi); + dm_pa = bfa_meminfo_dma_phys(mi); + + buf_pool_sz = mod->req_pld_sz * mod->num_fcxps; + + /* + * Initialize the fcxp req payload list + */ + mod->req_pld_list_kva = dm_kva; + mod->req_pld_list_pa = dm_pa; + dm_kva += buf_pool_sz; + dm_pa += buf_pool_sz; + bfa_os_memset(mod->req_pld_list_kva, 0, buf_pool_sz); + + /* + * Initialize the fcxp rsp payload list + */ + buf_pool_sz = mod->rsp_pld_sz * mod->num_fcxps; + mod->rsp_pld_list_kva = dm_kva; + mod->rsp_pld_list_pa = dm_pa; + dm_kva += buf_pool_sz; + dm_pa += buf_pool_sz; + bfa_os_memset(mod->rsp_pld_list_kva, 0, buf_pool_sz); + + bfa_meminfo_dma_virt(mi) = dm_kva; + bfa_meminfo_dma_phys(mi) = dm_pa; +} + +static void +claim_fcxps_mem(struct bfa_fcxp_mod_s *mod, struct bfa_meminfo_s *mi) +{ + u16 i; + struct bfa_fcxp_s *fcxp; + + fcxp = (struct bfa_fcxp_s *) bfa_meminfo_kva(mi); + bfa_os_memset(fcxp, 0, sizeof(struct bfa_fcxp_s) * mod->num_fcxps); + + INIT_LIST_HEAD(&mod->fcxp_free_q); + INIT_LIST_HEAD(&mod->fcxp_active_q); + + mod->fcxp_list = fcxp; + + for (i = 0; i < mod->num_fcxps; i++) { + fcxp->fcxp_mod = mod; + fcxp->fcxp_tag = i; + + list_add_tail(&fcxp->qe, &mod->fcxp_free_q); + bfa_reqq_winit(&fcxp->reqq_wqe, bfa_fcxp_qresume, fcxp); + fcxp->reqq_waiting = BFA_FALSE; + + fcxp = fcxp + 1; + } + + bfa_meminfo_kva(mi) = (void *)fcxp; +} + +static void +bfa_fcxp_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *ndm_len, + u32 *dm_len) +{ + u16 num_fcxp_reqs = cfg->fwcfg.num_fcxp_reqs; + + if (num_fcxp_reqs == 0) + return; + + /* + * Account for req/rsp payload + */ + *dm_len += BFA_FCXP_MAX_IBUF_SZ * num_fcxp_reqs; + if (cfg->drvcfg.min_cfg) + *dm_len += BFA_FCXP_MAX_IBUF_SZ * num_fcxp_reqs; + else + *dm_len += BFA_FCXP_MAX_LBUF_SZ * num_fcxp_reqs; + + /* + * Account for fcxp structs + */ + *ndm_len += sizeof(struct bfa_fcxp_s) * num_fcxp_reqs; +} + +static void +bfa_fcxp_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + struct bfa_fcxp_mod_s *mod = BFA_FCXP_MOD(bfa); + + bfa_os_memset(mod, 0, sizeof(struct bfa_fcxp_mod_s)); + mod->bfa = bfa; + mod->num_fcxps = cfg->fwcfg.num_fcxp_reqs; + + /** + * Initialize FCXP request and response payload sizes. + */ + mod->req_pld_sz = mod->rsp_pld_sz = BFA_FCXP_MAX_IBUF_SZ; + if (!cfg->drvcfg.min_cfg) + mod->rsp_pld_sz = BFA_FCXP_MAX_LBUF_SZ; + + INIT_LIST_HEAD(&mod->wait_q); + + claim_fcxp_req_rsp_mem(mod, meminfo); + claim_fcxps_mem(mod, meminfo); +} + +static void +bfa_fcxp_initdone(struct bfa_s *bfa) +{ +} + +static void +bfa_fcxp_detach(struct bfa_s *bfa) +{ +} + +static void +bfa_fcxp_start(struct bfa_s *bfa) +{ +} + +static void +bfa_fcxp_stop(struct bfa_s *bfa) +{ +} + +static void +bfa_fcxp_iocdisable(struct bfa_s *bfa) +{ + struct bfa_fcxp_mod_s *mod = BFA_FCXP_MOD(bfa); + struct bfa_fcxp_s *fcxp; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &mod->fcxp_active_q) { + fcxp = (struct bfa_fcxp_s *) qe; + if (fcxp->caller == NULL) { + fcxp->send_cbfn(fcxp->caller, fcxp, fcxp->send_cbarg, + BFA_STATUS_IOC_FAILURE, 0, 0, NULL); + bfa_fcxp_free(fcxp); + } else { + fcxp->rsp_status = BFA_STATUS_IOC_FAILURE; + bfa_cb_queue(bfa, &fcxp->hcb_qe, + __bfa_fcxp_send_cbfn, fcxp); + } + } +} + +static struct bfa_fcxp_s * +bfa_fcxp_get(struct bfa_fcxp_mod_s *fm) +{ + struct bfa_fcxp_s *fcxp; + + bfa_q_deq(&fm->fcxp_free_q, &fcxp); + + if (fcxp) + list_add_tail(&fcxp->qe, &fm->fcxp_active_q); + + return (fcxp); +} + +static void +bfa_fcxp_put(struct bfa_fcxp_s *fcxp) +{ + struct bfa_fcxp_mod_s *mod = fcxp->fcxp_mod; + struct bfa_fcxp_wqe_s *wqe; + + bfa_q_deq(&mod->wait_q, &wqe); + if (wqe) { + bfa_trc(mod->bfa, fcxp->fcxp_tag); + wqe->alloc_cbfn(wqe->alloc_cbarg, fcxp); + return; + } + + bfa_assert(bfa_q_is_on_q(&mod->fcxp_active_q, fcxp)); + list_del(&fcxp->qe); + list_add_tail(&fcxp->qe, &mod->fcxp_free_q); +} + +static void +bfa_fcxp_null_comp(void *bfad_fcxp, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, struct fchs_s *rsp_fchs) +{ + /**discarded fcxp completion */ +} + +static void +__bfa_fcxp_send_cbfn(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_fcxp_s *fcxp = cbarg; + + if (complete) { + fcxp->send_cbfn(fcxp->caller, fcxp, fcxp->send_cbarg, + fcxp->rsp_status, fcxp->rsp_len, + fcxp->residue_len, &fcxp->rsp_fchs); + } else { + bfa_fcxp_free(fcxp); + } +} + +static void +hal_fcxp_send_comp(struct bfa_s *bfa, struct bfi_fcxp_send_rsp_s *fcxp_rsp) +{ + struct bfa_fcxp_mod_s *mod = BFA_FCXP_MOD(bfa); + struct bfa_fcxp_s *fcxp; + u16 fcxp_tag = bfa_os_ntohs(fcxp_rsp->fcxp_tag); + + bfa_trc(bfa, fcxp_tag); + + fcxp_rsp->rsp_len = bfa_os_ntohl(fcxp_rsp->rsp_len); + + /** + * @todo f/w should not set residue to non-0 when everything + * is received. + */ + if (fcxp_rsp->req_status == BFA_STATUS_OK) + fcxp_rsp->residue_len = 0; + else + fcxp_rsp->residue_len = bfa_os_ntohl(fcxp_rsp->residue_len); + + fcxp = BFA_FCXP_FROM_TAG(mod, fcxp_tag); + + bfa_assert(fcxp->send_cbfn != NULL); + + hal_fcxp_rx_plog(mod->bfa, fcxp, fcxp_rsp); + + if (fcxp->send_cbfn != NULL) { + if (fcxp->caller == NULL) { + bfa_trc(mod->bfa, fcxp->fcxp_tag); + + fcxp->send_cbfn(fcxp->caller, fcxp, fcxp->send_cbarg, + fcxp_rsp->req_status, fcxp_rsp->rsp_len, + fcxp_rsp->residue_len, &fcxp_rsp->fchs); + /* + * fcxp automatically freed on return from the callback + */ + bfa_fcxp_free(fcxp); + } else { + bfa_trc(mod->bfa, fcxp->fcxp_tag); + fcxp->rsp_status = fcxp_rsp->req_status; + fcxp->rsp_len = fcxp_rsp->rsp_len; + fcxp->residue_len = fcxp_rsp->residue_len; + fcxp->rsp_fchs = fcxp_rsp->fchs; + + bfa_cb_queue(bfa, &fcxp->hcb_qe, + __bfa_fcxp_send_cbfn, fcxp); + } + } else { + bfa_trc(bfa, fcxp_tag); + } +} + +static void +hal_fcxp_set_local_sges(struct bfi_sge_s *sge, u32 reqlen, u64 req_pa) +{ + union bfi_addr_u sga_zero = { {0} }; + + sge->sg_len = reqlen; + sge->flags = BFI_SGE_DATA_LAST; + bfa_dma_addr_set(sge[0].sga, req_pa); + bfa_sge_to_be(sge); + sge++; + + sge->sga = sga_zero; + sge->sg_len = reqlen; + sge->flags = BFI_SGE_PGDLEN; + bfa_sge_to_be(sge); +} + +static void +hal_fcxp_tx_plog(struct bfa_s *bfa, u32 reqlen, struct bfa_fcxp_s *fcxp, + struct fchs_s *fchs) +{ + /* + * TODO: TX ox_id + */ + if (reqlen > 0) { + if (fcxp->use_ireqbuf) { + u32 pld_w0 = + *((u32 *) BFA_FCXP_REQ_PLD(fcxp)); + + bfa_plog_fchdr_and_pl(bfa->plog, BFA_PL_MID_HAL_FCXP, + BFA_PL_EID_TX, + reqlen + sizeof(struct fchs_s), fchs, pld_w0); + } else { + bfa_plog_fchdr(bfa->plog, BFA_PL_MID_HAL_FCXP, + BFA_PL_EID_TX, reqlen + sizeof(struct fchs_s), + fchs); + } + } else { + bfa_plog_fchdr(bfa->plog, BFA_PL_MID_HAL_FCXP, BFA_PL_EID_TX, + reqlen + sizeof(struct fchs_s), fchs); + } +} + +static void +hal_fcxp_rx_plog(struct bfa_s *bfa, struct bfa_fcxp_s *fcxp, + struct bfi_fcxp_send_rsp_s *fcxp_rsp) +{ + if (fcxp_rsp->rsp_len > 0) { + if (fcxp->use_irspbuf) { + u32 pld_w0 = + *((u32 *) BFA_FCXP_RSP_PLD(fcxp)); + + bfa_plog_fchdr_and_pl(bfa->plog, BFA_PL_MID_HAL_FCXP, + BFA_PL_EID_RX, + (u16) fcxp_rsp->rsp_len, + &fcxp_rsp->fchs, pld_w0); + } else { + bfa_plog_fchdr(bfa->plog, BFA_PL_MID_HAL_FCXP, + BFA_PL_EID_RX, + (u16) fcxp_rsp->rsp_len, + &fcxp_rsp->fchs); + } + } else { + bfa_plog_fchdr(bfa->plog, BFA_PL_MID_HAL_FCXP, BFA_PL_EID_RX, + (u16) fcxp_rsp->rsp_len, &fcxp_rsp->fchs); + } +} + +/** + * Handler to resume sending fcxp when space in available in cpe queue. + */ +static void +bfa_fcxp_qresume(void *cbarg) +{ + struct bfa_fcxp_s *fcxp = cbarg; + struct bfa_s *bfa = fcxp->fcxp_mod->bfa; + struct bfi_fcxp_send_req_s *send_req; + + fcxp->reqq_waiting = BFA_FALSE; + send_req = bfa_reqq_next(bfa, BFA_REQQ_FCXP); + bfa_fcxp_queue(fcxp, send_req); +} + +/** + * Queue fcxp send request to foimrware. + */ +static void +bfa_fcxp_queue(struct bfa_fcxp_s *fcxp, struct bfi_fcxp_send_req_s *send_req) +{ + struct bfa_s *bfa = fcxp->fcxp_mod->bfa; + struct bfa_fcxp_req_info_s *reqi = &fcxp->req_info; + struct bfa_fcxp_rsp_info_s *rspi = &fcxp->rsp_info; + struct bfa_rport_s *rport = reqi->bfa_rport; + + bfi_h2i_set(send_req->mh, BFI_MC_FCXP, BFI_FCXP_H2I_SEND_REQ, + bfa_lpuid(bfa)); + + send_req->fcxp_tag = bfa_os_htons(fcxp->fcxp_tag); + if (rport) { + send_req->rport_fw_hndl = rport->fw_handle; + send_req->max_frmsz = bfa_os_htons(rport->rport_info.max_frmsz); + if (send_req->max_frmsz == 0) + send_req->max_frmsz = bfa_os_htons(FC_MAX_PDUSZ); + } else { + send_req->rport_fw_hndl = 0; + send_req->max_frmsz = bfa_os_htons(FC_MAX_PDUSZ); + } + + send_req->vf_id = bfa_os_htons(reqi->vf_id); + send_req->lp_tag = reqi->lp_tag; + send_req->class = reqi->class; + send_req->rsp_timeout = rspi->rsp_timeout; + send_req->cts = reqi->cts; + send_req->fchs = reqi->fchs; + + send_req->req_len = bfa_os_htonl(reqi->req_tot_len); + send_req->rsp_maxlen = bfa_os_htonl(rspi->rsp_maxlen); + + /* + * setup req sgles + */ + if (fcxp->use_ireqbuf == 1) { + hal_fcxp_set_local_sges(send_req->req_sge, reqi->req_tot_len, + BFA_FCXP_REQ_PLD_PA(fcxp)); + } else { + if (fcxp->nreq_sgles > 0) { + bfa_assert(fcxp->nreq_sgles == 1); + hal_fcxp_set_local_sges(send_req->req_sge, + reqi->req_tot_len, + fcxp->req_sga_cbfn(fcxp->caller, + 0)); + } else { + bfa_assert(reqi->req_tot_len == 0); + hal_fcxp_set_local_sges(send_req->rsp_sge, 0, 0); + } + } + + /* + * setup rsp sgles + */ + if (fcxp->use_irspbuf == 1) { + bfa_assert(rspi->rsp_maxlen <= BFA_FCXP_MAX_LBUF_SZ); + + hal_fcxp_set_local_sges(send_req->rsp_sge, rspi->rsp_maxlen, + BFA_FCXP_RSP_PLD_PA(fcxp)); + + } else { + if (fcxp->nrsp_sgles > 0) { + bfa_assert(fcxp->nrsp_sgles == 1); + hal_fcxp_set_local_sges(send_req->rsp_sge, + rspi->rsp_maxlen, + fcxp->rsp_sga_cbfn(fcxp->caller, + 0)); + } else { + bfa_assert(rspi->rsp_maxlen == 0); + hal_fcxp_set_local_sges(send_req->rsp_sge, 0, 0); + } + } + + hal_fcxp_tx_plog(bfa, reqi->req_tot_len, fcxp, &reqi->fchs); + + bfa_reqq_produce(bfa, BFA_REQQ_FCXP); + + bfa_trc(bfa, bfa_reqq_pi(bfa, BFA_REQQ_FCXP)); + bfa_trc(bfa, bfa_reqq_ci(bfa, BFA_REQQ_FCXP)); +} + + +/** + * hal_fcxp_api BFA FCXP API + */ + +/** + * Allocate an FCXP instance to send a response or to send a request + * that has a response. Request/response buffers are allocated by caller. + * + * @param[in] bfa BFA bfa instance + * @param[in] nreq_sgles Number of SG elements required for request + * buffer. 0, if fcxp internal buffers are used. + * Use bfa_fcxp_get_reqbuf() to get the + * internal req buffer. + * @param[in] req_sgles SG elements describing request buffer. Will be + * copied in by BFA and hence can be freed on + * return from this function. + * @param[in] get_req_sga function ptr to be called to get a request SG + * Address (given the sge index). + * @param[in] get_req_sglen function ptr to be called to get a request SG + * len (given the sge index). + * @param[in] get_rsp_sga function ptr to be called to get a response SG + * Address (given the sge index). + * @param[in] get_rsp_sglen function ptr to be called to get a response SG + * len (given the sge index). + * + * @return FCXP instance. NULL on failure. + */ +struct bfa_fcxp_s * +bfa_fcxp_alloc(void *caller, struct bfa_s *bfa, int nreq_sgles, + int nrsp_sgles, bfa_fcxp_get_sgaddr_t req_sga_cbfn, + bfa_fcxp_get_sglen_t req_sglen_cbfn, + bfa_fcxp_get_sgaddr_t rsp_sga_cbfn, + bfa_fcxp_get_sglen_t rsp_sglen_cbfn) +{ + struct bfa_fcxp_s *fcxp = NULL; + u32 nreq_sgpg, nrsp_sgpg; + + bfa_assert(bfa != NULL); + + fcxp = bfa_fcxp_get(BFA_FCXP_MOD(bfa)); + if (fcxp == NULL) + return (NULL); + + bfa_trc(bfa, fcxp->fcxp_tag); + + fcxp->caller = caller; + + if (nreq_sgles == 0) { + fcxp->use_ireqbuf = 1; + } else { + bfa_assert(req_sga_cbfn != NULL); + bfa_assert(req_sglen_cbfn != NULL); + + fcxp->use_ireqbuf = 0; + fcxp->req_sga_cbfn = req_sga_cbfn; + fcxp->req_sglen_cbfn = req_sglen_cbfn; + + fcxp->nreq_sgles = nreq_sgles; + + /* + * alloc required sgpgs + */ + if (nreq_sgles > BFI_SGE_INLINE) { + nreq_sgpg = BFA_SGPG_NPAGE(nreq_sgles); + + if (bfa_sgpg_malloc + (bfa, &fcxp->req_sgpg_q, nreq_sgpg) + != BFA_STATUS_OK) { + /* bfa_sgpg_wait(bfa, &fcxp->req_sgpg_wqe, + nreq_sgpg); */ + /* + * TODO + */ + } + } + } + + if (nrsp_sgles == 0) { + fcxp->use_irspbuf = 1; + } else { + bfa_assert(rsp_sga_cbfn != NULL); + bfa_assert(rsp_sglen_cbfn != NULL); + + fcxp->use_irspbuf = 0; + fcxp->rsp_sga_cbfn = rsp_sga_cbfn; + fcxp->rsp_sglen_cbfn = rsp_sglen_cbfn; + + fcxp->nrsp_sgles = nrsp_sgles; + /* + * alloc required sgpgs + */ + if (nrsp_sgles > BFI_SGE_INLINE) { + nrsp_sgpg = BFA_SGPG_NPAGE(nreq_sgles); + + if (bfa_sgpg_malloc + (bfa, &fcxp->rsp_sgpg_q, nrsp_sgpg) + != BFA_STATUS_OK) { + /* bfa_sgpg_wait(bfa, &fcxp->rsp_sgpg_wqe, + nrsp_sgpg); */ + /* + * TODO + */ + } + } + } + + return (fcxp); +} + +/** + * Get the internal request buffer pointer + * + * @param[in] fcxp BFA fcxp pointer + * + * @return pointer to the internal request buffer + */ +void * +bfa_fcxp_get_reqbuf(struct bfa_fcxp_s *fcxp) +{ + struct bfa_fcxp_mod_s *mod = fcxp->fcxp_mod; + void *reqbuf; + + bfa_assert(fcxp->use_ireqbuf == 1); + reqbuf = ((u8 *)mod->req_pld_list_kva) + + fcxp->fcxp_tag * mod->req_pld_sz; + return reqbuf; +} + +u32 +bfa_fcxp_get_reqbufsz(struct bfa_fcxp_s *fcxp) +{ + struct bfa_fcxp_mod_s *mod = fcxp->fcxp_mod; + + return mod->req_pld_sz; +} + +/** + * Get the internal response buffer pointer + * + * @param[in] fcxp BFA fcxp pointer + * + * @return pointer to the internal request buffer + */ +void * +bfa_fcxp_get_rspbuf(struct bfa_fcxp_s *fcxp) +{ + struct bfa_fcxp_mod_s *mod = fcxp->fcxp_mod; + void *rspbuf; + + bfa_assert(fcxp->use_irspbuf == 1); + + rspbuf = ((u8 *)mod->rsp_pld_list_kva) + + fcxp->fcxp_tag * mod->rsp_pld_sz; + return rspbuf; +} + +/** + * Free the BFA FCXP + * + * @param[in] fcxp BFA fcxp pointer + * + * @return void + */ +void +bfa_fcxp_free(struct bfa_fcxp_s *fcxp) +{ + struct bfa_fcxp_mod_s *mod = fcxp->fcxp_mod; + + bfa_assert(fcxp != NULL); + bfa_trc(mod->bfa, fcxp->fcxp_tag); + bfa_fcxp_put(fcxp); +} + +/** + * Send a FCXP request + * + * @param[in] fcxp BFA fcxp pointer + * @param[in] rport BFA rport pointer. Could be left NULL for WKA rports + * @param[in] vf_id virtual Fabric ID + * @param[in] lp_tag lport tag + * @param[in] cts use Continous sequence + * @param[in] cos fc Class of Service + * @param[in] reqlen request length, does not include FCHS length + * @param[in] fchs fc Header Pointer. The header content will be copied + * in by BFA. + * + * @param[in] cbfn call back function to be called on receiving + * the response + * @param[in] cbarg arg for cbfn + * @param[in] rsp_timeout + * response timeout + * + * @return bfa_status_t + */ +void +bfa_fcxp_send(struct bfa_fcxp_s *fcxp, struct bfa_rport_s *rport, + u16 vf_id, u8 lp_tag, bfa_boolean_t cts, enum fc_cos cos, + u32 reqlen, struct fchs_s *fchs, bfa_cb_fcxp_send_t cbfn, + void *cbarg, u32 rsp_maxlen, u8 rsp_timeout) +{ + struct bfa_s *bfa = fcxp->fcxp_mod->bfa; + struct bfa_fcxp_req_info_s *reqi = &fcxp->req_info; + struct bfa_fcxp_rsp_info_s *rspi = &fcxp->rsp_info; + struct bfi_fcxp_send_req_s *send_req; + + bfa_trc(bfa, fcxp->fcxp_tag); + + /** + * setup request/response info + */ + reqi->bfa_rport = rport; + reqi->vf_id = vf_id; + reqi->lp_tag = lp_tag; + reqi->class = cos; + rspi->rsp_timeout = rsp_timeout; + reqi->cts = cts; + reqi->fchs = *fchs; + reqi->req_tot_len = reqlen; + rspi->rsp_maxlen = rsp_maxlen; + fcxp->send_cbfn = cbfn ? cbfn : bfa_fcxp_null_comp; + fcxp->send_cbarg = cbarg; + + /** + * If no room in CPE queue, wait for + */ + send_req = bfa_reqq_next(bfa, BFA_REQQ_FCXP); + if (!send_req) { + bfa_trc(bfa, fcxp->fcxp_tag); + fcxp->reqq_waiting = BFA_TRUE; + bfa_reqq_wait(bfa, BFA_REQQ_FCXP, &fcxp->reqq_wqe); + return; + } + + bfa_fcxp_queue(fcxp, send_req); +} + +/** + * Abort a BFA FCXP + * + * @param[in] fcxp BFA fcxp pointer + * + * @return void + */ +bfa_status_t +bfa_fcxp_abort(struct bfa_fcxp_s *fcxp) +{ + bfa_assert(0); + return (BFA_STATUS_OK); +} + +void +bfa_fcxp_alloc_wait(struct bfa_s *bfa, struct bfa_fcxp_wqe_s *wqe, + bfa_fcxp_alloc_cbfn_t alloc_cbfn, void *alloc_cbarg) +{ + struct bfa_fcxp_mod_s *mod = BFA_FCXP_MOD(bfa); + + bfa_assert(list_empty(&mod->fcxp_free_q)); + + wqe->alloc_cbfn = alloc_cbfn; + wqe->alloc_cbarg = alloc_cbarg; + list_add_tail(&wqe->qe, &mod->wait_q); +} + +void +bfa_fcxp_walloc_cancel(struct bfa_s *bfa, struct bfa_fcxp_wqe_s *wqe) +{ + struct bfa_fcxp_mod_s *mod = BFA_FCXP_MOD(bfa); + + bfa_assert(bfa_q_is_on_q(&mod->wait_q, wqe)); + list_del(&wqe->qe); +} + +void +bfa_fcxp_discard(struct bfa_fcxp_s *fcxp) +{ + /** + * If waiting for room in request queue, cancel reqq wait + * and free fcxp. + */ + if (fcxp->reqq_waiting) { + fcxp->reqq_waiting = BFA_FALSE; + bfa_reqq_wcancel(&fcxp->reqq_wqe); + bfa_fcxp_free(fcxp); + return; + } + + fcxp->send_cbfn = bfa_fcxp_null_comp; +} + + + +/** + * hal_fcxp_public BFA FCXP public functions + */ + +void +bfa_fcxp_isr(struct bfa_s *bfa, struct bfi_msg_s *msg) +{ + switch (msg->mhdr.msg_id) { + case BFI_FCXP_I2H_SEND_RSP: + hal_fcxp_send_comp(bfa, (struct bfi_fcxp_send_rsp_s *) msg); + break; + + default: + bfa_trc(bfa, msg->mhdr.msg_id); + bfa_assert(0); + } +} + +u32 +bfa_fcxp_get_maxrsp(struct bfa_s *bfa) +{ + struct bfa_fcxp_mod_s *mod = BFA_FCXP_MOD(bfa); + + return mod->rsp_pld_sz; +} + + diff --git a/drivers/scsi/bfa/bfa_fcxp_priv.h b/drivers/scsi/bfa/bfa_fcxp_priv.h new file mode 100644 index 000000000000..4cda49397da0 --- /dev/null +++ b/drivers/scsi/bfa/bfa_fcxp_priv.h @@ -0,0 +1,138 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCXP_PRIV_H__ +#define __BFA_FCXP_PRIV_H__ + +#include <cs/bfa_sm.h> +#include <protocol/fc.h> +#include <bfa_svc.h> +#include <bfi/bfi_fcxp.h> + +#define BFA_FCXP_MIN (1) +#define BFA_FCXP_MAX_IBUF_SZ (2 * 1024 + 256) +#define BFA_FCXP_MAX_LBUF_SZ (4 * 1024 + 256) + +struct bfa_fcxp_mod_s { + struct bfa_s *bfa; /* backpointer to BFA */ + struct bfa_fcxp_s *fcxp_list; /* array of FCXPs */ + u16 num_fcxps; /* max num FCXP requests */ + struct list_head fcxp_free_q; /* free FCXPs */ + struct list_head fcxp_active_q; /* active FCXPs */ + void *req_pld_list_kva; /* list of FCXP req pld */ + u64 req_pld_list_pa; /* list of FCXP req pld */ + void *rsp_pld_list_kva; /* list of FCXP resp pld */ + u64 rsp_pld_list_pa; /* list of FCXP resp pld */ + struct list_head wait_q; /* wait queue for free fcxp */ + u32 req_pld_sz; + u32 rsp_pld_sz; +}; + +#define BFA_FCXP_MOD(__bfa) (&(__bfa)->modules.fcxp_mod) +#define BFA_FCXP_FROM_TAG(__mod, __tag) (&(__mod)->fcxp_list[__tag]) + +typedef void (*fcxp_send_cb_t) (struct bfa_s *ioc, struct bfa_fcxp_s *fcxp, + void *cb_arg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs); + +/** + * Information needed for a FCXP request + */ +struct bfa_fcxp_req_info_s { + struct bfa_rport_s *bfa_rport; /* Pointer to the bfa rport that was + *returned from bfa_rport_create(). + *This could be left NULL for WKA or for + *FCXP interactions before the rport + *nexus is established + */ + struct fchs_s fchs; /* request FC header structure */ + u8 cts; /* continous sequence */ + u8 class; /* FC class for the request/response */ + u16 max_frmsz; /* max send frame size */ + u16 vf_id; /* vsan tag if applicable */ + u8 lp_tag; /* lport tag */ + u32 req_tot_len; /* request payload total length */ +}; + +struct bfa_fcxp_rsp_info_s { + struct fchs_s rsp_fchs; /* Response frame's FC header will + * be *sent back in this field */ + u8 rsp_timeout; /* timeout in seconds, 0-no response + */ + u8 rsvd2[3]; + u32 rsp_maxlen; /* max response length expected */ +}; + +struct bfa_fcxp_s { + struct list_head qe; /* fcxp queue element */ + bfa_sm_t sm; /* state machine */ + void *caller; /* driver or fcs */ + struct bfa_fcxp_mod_s *fcxp_mod; + /* back pointer to fcxp mod */ + u16 fcxp_tag; /* internal tag */ + struct bfa_fcxp_req_info_s req_info; + /* request info */ + struct bfa_fcxp_rsp_info_s rsp_info; + /* response info */ + u8 use_ireqbuf; /* use internal req buf */ + u8 use_irspbuf; /* use internal rsp buf */ + u32 nreq_sgles; /* num request SGLEs */ + u32 nrsp_sgles; /* num response SGLEs */ + struct list_head req_sgpg_q; /* SG pages for request buf */ + struct list_head req_sgpg_wqe; /* wait queue for req SG page */ + struct list_head rsp_sgpg_q; /* SG pages for response buf */ + struct list_head rsp_sgpg_wqe; /* wait queue for rsp SG page */ + + bfa_fcxp_get_sgaddr_t req_sga_cbfn; + /* SG elem addr user function */ + bfa_fcxp_get_sglen_t req_sglen_cbfn; + /* SG elem len user function */ + bfa_fcxp_get_sgaddr_t rsp_sga_cbfn; + /* SG elem addr user function */ + bfa_fcxp_get_sglen_t rsp_sglen_cbfn; + /* SG elem len user function */ + bfa_cb_fcxp_send_t send_cbfn; /* send completion callback */ + void *send_cbarg; /* callback arg */ + struct bfa_sge_s req_sge[BFA_FCXP_MAX_SGES]; + /* req SG elems */ + struct bfa_sge_s rsp_sge[BFA_FCXP_MAX_SGES]; + /* rsp SG elems */ + u8 rsp_status; /* comp: rsp status */ + u32 rsp_len; /* comp: actual response len */ + u32 residue_len; /* comp: residual rsp length */ + struct fchs_s rsp_fchs; /* comp: response fchs */ + struct bfa_cb_qe_s hcb_qe; /* comp: callback qelem */ + struct bfa_reqq_wait_s reqq_wqe; + bfa_boolean_t reqq_waiting; +}; + +#define BFA_FCXP_REQ_PLD(_fcxp) (bfa_fcxp_get_reqbuf(_fcxp)) + +#define BFA_FCXP_RSP_FCHS(_fcxp) (&((_fcxp)->rsp_info.fchs)) +#define BFA_FCXP_RSP_PLD(_fcxp) (bfa_fcxp_get_rspbuf(_fcxp)) + +#define BFA_FCXP_REQ_PLD_PA(_fcxp) \ + ((_fcxp)->fcxp_mod->req_pld_list_pa + \ + ((_fcxp)->fcxp_mod->req_pld_sz * (_fcxp)->fcxp_tag)) + +#define BFA_FCXP_RSP_PLD_PA(_fcxp) \ + ((_fcxp)->fcxp_mod->rsp_pld_list_pa + \ + ((_fcxp)->fcxp_mod->rsp_pld_sz * (_fcxp)->fcxp_tag)) + +void bfa_fcxp_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); +#endif /* __BFA_FCXP_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_fwimg_priv.h b/drivers/scsi/bfa/bfa_fwimg_priv.h new file mode 100644 index 000000000000..1ec1355924d9 --- /dev/null +++ b/drivers/scsi/bfa/bfa_fwimg_priv.h @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FWIMG_PRIV_H__ +#define __BFA_FWIMG_PRIV_H__ + +#define BFI_FLASH_CHUNK_SZ 256 /* Flash chunk size */ +#define BFI_FLASH_CHUNK_SZ_WORDS (BFI_FLASH_CHUNK_SZ/sizeof(u32)) + +extern u32 *bfi_image_ct_get_chunk(u32 off); +extern u32 bfi_image_ct_size; +extern u32 *bfi_image_cb_get_chunk(u32 off); +extern u32 bfi_image_cb_size; +extern u32 *bfi_image_cb; +extern u32 *bfi_image_ct; + +#endif /* __BFA_FWIMG_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_hw_cb.c b/drivers/scsi/bfa/bfa_hw_cb.c new file mode 100644 index 000000000000..ede1438619e2 --- /dev/null +++ b/drivers/scsi/bfa/bfa_hw_cb.c @@ -0,0 +1,142 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa_priv.h> +#include <bfi/bfi_cbreg.h> + +void +bfa_hwcb_reginit(struct bfa_s *bfa) +{ + struct bfa_iocfc_regs_s *bfa_regs = &bfa->iocfc.bfa_regs; + bfa_os_addr_t kva = bfa_ioc_bar0(&bfa->ioc); + int i, q, fn = bfa_ioc_pcifn(&bfa->ioc); + + if (fn == 0) { + bfa_regs->intr_status = (kva + HOSTFN0_INT_STATUS); + bfa_regs->intr_mask = (kva + HOSTFN0_INT_MSK); + } else { + bfa_regs->intr_status = (kva + HOSTFN1_INT_STATUS); + bfa_regs->intr_mask = (kva + HOSTFN1_INT_MSK); + } + + for (i = 0; i < BFI_IOC_MAX_CQS; i++) { + /* + * CPE registers + */ + q = CPE_Q_NUM(fn, i); + bfa_regs->cpe_q_pi[i] = (kva + CPE_Q_PI(q)); + bfa_regs->cpe_q_ci[i] = (kva + CPE_Q_CI(q)); + bfa_regs->cpe_q_depth[i] = (kva + CPE_Q_DEPTH(q)); + + /* + * RME registers + */ + q = CPE_Q_NUM(fn, i); + bfa_regs->rme_q_pi[i] = (kva + RME_Q_PI(q)); + bfa_regs->rme_q_ci[i] = (kva + RME_Q_CI(q)); + bfa_regs->rme_q_depth[i] = (kva + RME_Q_DEPTH(q)); + } +} + +void +bfa_hwcb_rspq_ack(struct bfa_s *bfa, int rspq) +{ +} + +static void +bfa_hwcb_rspq_ack_msix(struct bfa_s *bfa, int rspq) +{ + bfa_reg_write(bfa->iocfc.bfa_regs.intr_status, + __HFN_INT_RME_Q0 << RME_Q_NUM(bfa_ioc_pcifn(&bfa->ioc), rspq)); +} + +void +bfa_hwcb_msix_getvecs(struct bfa_s *bfa, u32 *msix_vecs_bmap, + u32 *num_vecs, u32 *max_vec_bit) +{ +#define __HFN_NUMINTS 13 + if (bfa_ioc_pcifn(&bfa->ioc) == 0) { + *msix_vecs_bmap = (__HFN_INT_CPE_Q0 | __HFN_INT_CPE_Q1 | + __HFN_INT_CPE_Q2 | __HFN_INT_CPE_Q3 | + __HFN_INT_RME_Q0 | __HFN_INT_RME_Q1 | + __HFN_INT_RME_Q2 | __HFN_INT_RME_Q3 | + __HFN_INT_MBOX_LPU0); + *max_vec_bit = __HFN_INT_MBOX_LPU0; + } else { + *msix_vecs_bmap = (__HFN_INT_CPE_Q4 | __HFN_INT_CPE_Q5 | + __HFN_INT_CPE_Q6 | __HFN_INT_CPE_Q7 | + __HFN_INT_RME_Q4 | __HFN_INT_RME_Q5 | + __HFN_INT_RME_Q6 | __HFN_INT_RME_Q7 | + __HFN_INT_MBOX_LPU1); + *max_vec_bit = __HFN_INT_MBOX_LPU1; + } + + *msix_vecs_bmap |= (__HFN_INT_ERR_EMC | __HFN_INT_ERR_LPU0 | + __HFN_INT_ERR_LPU1 | __HFN_INT_ERR_PSS); + *num_vecs = __HFN_NUMINTS; +} + +/** + * No special setup required for crossbow -- vector assignments are implicit. + */ +void +bfa_hwcb_msix_init(struct bfa_s *bfa, int nvecs) +{ + int i; + + bfa_assert((nvecs == 1) || (nvecs == __HFN_NUMINTS)); + + bfa->msix.nvecs = nvecs; + if (nvecs == 1) { + for (i = 0; i < BFA_MSIX_CB_MAX; i++) + bfa->msix.handler[i] = bfa_msix_all; + return; + } + + for (i = BFA_MSIX_CPE_Q0; i <= BFA_MSIX_CPE_Q7; i++) + bfa->msix.handler[i] = bfa_msix_reqq; + + for (i = BFA_MSIX_RME_Q0; i <= BFA_MSIX_RME_Q7; i++) + bfa->msix.handler[i] = bfa_msix_rspq; + + for (; i < BFA_MSIX_CB_MAX; i++) + bfa->msix.handler[i] = bfa_msix_lpu_err; +} + +/** + * Crossbow -- dummy, interrupts are masked + */ +void +bfa_hwcb_msix_install(struct bfa_s *bfa) +{ +} + +void +bfa_hwcb_msix_uninstall(struct bfa_s *bfa) +{ +} + +/** + * No special enable/disable -- vector assignments are implicit. + */ +void +bfa_hwcb_isr_mode_set(struct bfa_s *bfa, bfa_boolean_t msix) +{ + bfa->iocfc.hwif.hw_rspq_ack = bfa_hwcb_rspq_ack_msix; +} + + diff --git a/drivers/scsi/bfa/bfa_hw_ct.c b/drivers/scsi/bfa/bfa_hw_ct.c new file mode 100644 index 000000000000..51ae5740e6e9 --- /dev/null +++ b/drivers/scsi/bfa/bfa_hw_ct.c @@ -0,0 +1,162 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa_priv.h> +#include <bfi/bfi_ctreg.h> +#include <bfa_ioc.h> + +BFA_TRC_FILE(HAL, IOCFC_CT); + +static u32 __ct_msix_err_vec_reg[] = { + HOST_MSIX_ERR_INDEX_FN0, + HOST_MSIX_ERR_INDEX_FN1, + HOST_MSIX_ERR_INDEX_FN2, + HOST_MSIX_ERR_INDEX_FN3, +}; + +static void +bfa_hwct_msix_lpu_err_set(struct bfa_s *bfa, bfa_boolean_t msix, int vec) +{ + int fn = bfa_ioc_pcifn(&bfa->ioc); + bfa_os_addr_t kva = bfa_ioc_bar0(&bfa->ioc); + + if (msix) + bfa_reg_write(kva + __ct_msix_err_vec_reg[fn], vec); + else + bfa_reg_write(kva + __ct_msix_err_vec_reg[fn], 0); +} + +/** + * Dummy interrupt handler for handling spurious interrupt during chip-reinit. + */ +static void +bfa_hwct_msix_dummy(struct bfa_s *bfa, int vec) +{ +} + +void +bfa_hwct_reginit(struct bfa_s *bfa) +{ + struct bfa_iocfc_regs_s *bfa_regs = &bfa->iocfc.bfa_regs; + bfa_os_addr_t kva = bfa_ioc_bar0(&bfa->ioc); + int i, q, fn = bfa_ioc_pcifn(&bfa->ioc); + + if (fn == 0) { + bfa_regs->intr_status = (kva + HOSTFN0_INT_STATUS); + bfa_regs->intr_mask = (kva + HOSTFN0_INT_MSK); + } else { + bfa_regs->intr_status = (kva + HOSTFN1_INT_STATUS); + bfa_regs->intr_mask = (kva + HOSTFN1_INT_MSK); + } + + for (i = 0; i < BFI_IOC_MAX_CQS; i++) { + /* + * CPE registers + */ + q = CPE_Q_NUM(fn, i); + bfa_regs->cpe_q_pi[i] = (kva + CPE_PI_PTR_Q(q << 5)); + bfa_regs->cpe_q_ci[i] = (kva + CPE_CI_PTR_Q(q << 5)); + bfa_regs->cpe_q_depth[i] = (kva + CPE_DEPTH_Q(q << 5)); + bfa_regs->cpe_q_ctrl[i] = (kva + CPE_QCTRL_Q(q << 5)); + + /* + * RME registers + */ + q = CPE_Q_NUM(fn, i); + bfa_regs->rme_q_pi[i] = (kva + RME_PI_PTR_Q(q << 5)); + bfa_regs->rme_q_ci[i] = (kva + RME_CI_PTR_Q(q << 5)); + bfa_regs->rme_q_depth[i] = (kva + RME_DEPTH_Q(q << 5)); + bfa_regs->rme_q_ctrl[i] = (kva + RME_QCTRL_Q(q << 5)); + } +} + +void +bfa_hwct_rspq_ack(struct bfa_s *bfa, int rspq) +{ + u32 r32; + + r32 = bfa_reg_read(bfa->iocfc.bfa_regs.rme_q_ctrl[rspq]); + bfa_reg_write(bfa->iocfc.bfa_regs.rme_q_ctrl[rspq], r32); +} + +void +bfa_hwct_msix_getvecs(struct bfa_s *bfa, u32 *msix_vecs_bmap, + u32 *num_vecs, u32 *max_vec_bit) +{ + *msix_vecs_bmap = (1 << BFA_MSIX_CT_MAX) - 1; + *max_vec_bit = (1 << (BFA_MSIX_CT_MAX - 1)); + *num_vecs = BFA_MSIX_CT_MAX; +} + +/** + * Setup MSI-X vector for catapult + */ +void +bfa_hwct_msix_init(struct bfa_s *bfa, int nvecs) +{ + bfa_assert((nvecs == 1) || (nvecs == BFA_MSIX_CT_MAX)); + bfa_trc(bfa, nvecs); + + bfa->msix.nvecs = nvecs; + bfa_hwct_msix_uninstall(bfa); +} + +void +bfa_hwct_msix_install(struct bfa_s *bfa) +{ + int i; + + if (bfa->msix.nvecs == 0) + return; + + if (bfa->msix.nvecs == 1) { + for (i = 0; i < BFA_MSIX_CT_MAX; i++) + bfa->msix.handler[i] = bfa_msix_all; + return; + } + + for (i = BFA_MSIX_CPE_Q0; i <= BFA_MSIX_CPE_Q3; i++) + bfa->msix.handler[i] = bfa_msix_reqq; + + for (; i <= BFA_MSIX_RME_Q3; i++) + bfa->msix.handler[i] = bfa_msix_rspq; + + bfa_assert(i == BFA_MSIX_LPU_ERR); + bfa->msix.handler[BFA_MSIX_LPU_ERR] = bfa_msix_lpu_err; +} + +void +bfa_hwct_msix_uninstall(struct bfa_s *bfa) +{ + int i; + + for (i = 0; i < BFA_MSIX_CT_MAX; i++) + bfa->msix.handler[i] = bfa_hwct_msix_dummy; +} + +/** + * Enable MSI-X vectors + */ +void +bfa_hwct_isr_mode_set(struct bfa_s *bfa, bfa_boolean_t msix) +{ + bfa_trc(bfa, 0); + bfa_hwct_msix_lpu_err_set(bfa, msix, BFA_MSIX_LPU_ERR); + bfa_ioc_isr_mode_set(&bfa->ioc, msix); +} + + diff --git a/drivers/scsi/bfa/bfa_intr.c b/drivers/scsi/bfa/bfa_intr.c new file mode 100644 index 000000000000..0ca125712a04 --- /dev/null +++ b/drivers/scsi/bfa/bfa_intr.c @@ -0,0 +1,218 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#include <bfa.h> +#include <bfi/bfi_cbreg.h> +#include <bfa_port_priv.h> +#include <bfa_intr_priv.h> +#include <cs/bfa_debug.h> + +BFA_TRC_FILE(HAL, INTR); + +static void +bfa_msix_errint(struct bfa_s *bfa, u32 intr) +{ + bfa_ioc_error_isr(&bfa->ioc); +} + +static void +bfa_msix_lpu(struct bfa_s *bfa) +{ + bfa_ioc_mbox_isr(&bfa->ioc); +} + +void +bfa_msix_all(struct bfa_s *bfa, int vec) +{ + bfa_intx(bfa); +} + +/** + * hal_intr_api + */ +bfa_boolean_t +bfa_intx(struct bfa_s *bfa) +{ + u32 intr, qintr; + int queue; + + intr = bfa_reg_read(bfa->iocfc.bfa_regs.intr_status); + if (!intr) + return BFA_FALSE; + + /** + * RME completion queue interrupt + */ + qintr = intr & __HFN_INT_RME_MASK; + bfa_reg_write(bfa->iocfc.bfa_regs.intr_status, qintr); + + for (queue = 0; queue < BFI_IOC_MAX_CQS_ASIC; queue ++) { + if (intr & (__HFN_INT_RME_Q0 << queue)) + bfa_msix_rspq(bfa, queue & (BFI_IOC_MAX_CQS - 1)); + } + intr &= ~qintr; + if (!intr) + return BFA_TRUE; + + /** + * CPE completion queue interrupt + */ + qintr = intr & __HFN_INT_CPE_MASK; + bfa_reg_write(bfa->iocfc.bfa_regs.intr_status, qintr); + + for (queue = 0; queue < BFI_IOC_MAX_CQS_ASIC; queue++) { + if (intr & (__HFN_INT_CPE_Q0 << queue)) + bfa_msix_reqq(bfa, queue & (BFI_IOC_MAX_CQS - 1)); + } + intr &= ~qintr; + if (!intr) + return BFA_TRUE; + + bfa_msix_lpu_err(bfa, intr); + + return BFA_TRUE; +} + +void +bfa_isr_enable(struct bfa_s *bfa) +{ + u32 intr_unmask; + int pci_func = bfa_ioc_pcifn(&bfa->ioc); + + bfa_trc(bfa, pci_func); + + bfa_msix_install(bfa); + intr_unmask = (__HFN_INT_ERR_EMC | __HFN_INT_ERR_LPU0 | + __HFN_INT_ERR_LPU1 | __HFN_INT_ERR_PSS); + + if (pci_func == 0) + intr_unmask |= (__HFN_INT_CPE_Q0 | __HFN_INT_CPE_Q1 | + __HFN_INT_CPE_Q2 | __HFN_INT_CPE_Q3 | + __HFN_INT_RME_Q0 | __HFN_INT_RME_Q1 | + __HFN_INT_RME_Q2 | __HFN_INT_RME_Q3 | + __HFN_INT_MBOX_LPU0); + else + intr_unmask |= (__HFN_INT_CPE_Q4 | __HFN_INT_CPE_Q5 | + __HFN_INT_CPE_Q6 | __HFN_INT_CPE_Q7 | + __HFN_INT_RME_Q4 | __HFN_INT_RME_Q5 | + __HFN_INT_RME_Q6 | __HFN_INT_RME_Q7 | + __HFN_INT_MBOX_LPU1); + + bfa_reg_write(bfa->iocfc.bfa_regs.intr_status, intr_unmask); + bfa_reg_write(bfa->iocfc.bfa_regs.intr_mask, ~intr_unmask); + bfa_isr_mode_set(bfa, bfa->msix.nvecs != 0); +} + +void +bfa_isr_disable(struct bfa_s *bfa) +{ + bfa_isr_mode_set(bfa, BFA_FALSE); + bfa_reg_write(bfa->iocfc.bfa_regs.intr_mask, -1L); + bfa_msix_uninstall(bfa); +} + +void +bfa_msix_reqq(struct bfa_s *bfa, int qid) +{ + struct list_head *waitq, *qe, *qen; + struct bfa_reqq_wait_s *wqe; + + qid &= (BFI_IOC_MAX_CQS - 1); + + waitq = bfa_reqq(bfa, qid); + list_for_each_safe(qe, qen, waitq) { + /** + * Callback only as long as there is room in request queue + */ + if (bfa_reqq_full(bfa, qid)) + break; + + list_del(qe); + wqe = (struct bfa_reqq_wait_s *) qe; + wqe->qresume(wqe->cbarg); + } +} + +void +bfa_isr_unhandled(struct bfa_s *bfa, struct bfi_msg_s *m) +{ + bfa_trc(bfa, m->mhdr.msg_class); + bfa_trc(bfa, m->mhdr.msg_id); + bfa_trc(bfa, m->mhdr.mtag.i2htok); + bfa_assert(0); + bfa_trc_stop(bfa->trcmod); +} + +void +bfa_msix_rspq(struct bfa_s *bfa, int rsp_qid) +{ + struct bfi_msg_s *m; + u32 pi, ci; + + bfa_trc_fp(bfa, rsp_qid); + + rsp_qid &= (BFI_IOC_MAX_CQS - 1); + + bfa->iocfc.hwif.hw_rspq_ack(bfa, rsp_qid); + + ci = bfa_rspq_ci(bfa, rsp_qid); + pi = bfa_rspq_pi(bfa, rsp_qid); + + bfa_trc_fp(bfa, ci); + bfa_trc_fp(bfa, pi); + + if (bfa->rme_process) { + while (ci != pi) { + m = bfa_rspq_elem(bfa, rsp_qid, ci); + bfa_assert_fp(m->mhdr.msg_class < BFI_MC_MAX); + + bfa_isrs[m->mhdr.msg_class] (bfa, m); + + CQ_INCR(ci, bfa->iocfc.cfg.drvcfg.num_rspq_elems); + } + } + + /** + * update CI + */ + bfa_rspq_ci(bfa, rsp_qid) = pi; + bfa_reg_write(bfa->iocfc.bfa_regs.rme_q_ci[rsp_qid], pi); + bfa_os_mmiowb(); +} + +void +bfa_msix_lpu_err(struct bfa_s *bfa, int vec) +{ + u32 intr; + + intr = bfa_reg_read(bfa->iocfc.bfa_regs.intr_status); + + if (intr & (__HFN_INT_MBOX_LPU0 | __HFN_INT_MBOX_LPU1)) + bfa_msix_lpu(bfa); + + if (intr & (__HFN_INT_ERR_EMC | + __HFN_INT_ERR_LPU0 | __HFN_INT_ERR_LPU1 | + __HFN_INT_ERR_PSS)) + bfa_msix_errint(bfa, intr); +} + +void +bfa_isr_bind(enum bfi_mclass mc, bfa_isr_func_t isr_func) +{ + bfa_isrs[mc] = isr_func; +} + + diff --git a/drivers/scsi/bfa/bfa_intr_priv.h b/drivers/scsi/bfa/bfa_intr_priv.h new file mode 100644 index 000000000000..8ce6e6b105c8 --- /dev/null +++ b/drivers/scsi/bfa/bfa_intr_priv.h @@ -0,0 +1,115 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_INTR_PRIV_H__ +#define __BFA_INTR_PRIV_H__ + +/** + * Message handler + */ +typedef void (*bfa_isr_func_t) (struct bfa_s *bfa, struct bfi_msg_s *m); +void bfa_isr_unhandled(struct bfa_s *bfa, struct bfi_msg_s *m); +void bfa_isr_bind(enum bfi_mclass mc, bfa_isr_func_t isr_func); + + +#define bfa_reqq_pi(__bfa, __reqq) (__bfa)->iocfc.req_cq_pi[__reqq] +#define bfa_reqq_ci(__bfa, __reqq) \ + *(u32 *)((__bfa)->iocfc.req_cq_shadow_ci[__reqq].kva) + +#define bfa_reqq_full(__bfa, __reqq) \ + (((bfa_reqq_pi(__bfa, __reqq) + 1) & \ + ((__bfa)->iocfc.cfg.drvcfg.num_reqq_elems - 1)) == \ + bfa_reqq_ci(__bfa, __reqq)) + +#define bfa_reqq_next(__bfa, __reqq) \ + (bfa_reqq_full(__bfa, __reqq) ? NULL : \ + ((void *)((struct bfi_msg_s *)((__bfa)->iocfc.req_cq_ba[__reqq].kva) \ + + bfa_reqq_pi((__bfa), (__reqq))))) + +#define bfa_reqq_produce(__bfa, __reqq) do { \ + (__bfa)->iocfc.req_cq_pi[__reqq]++; \ + (__bfa)->iocfc.req_cq_pi[__reqq] &= \ + ((__bfa)->iocfc.cfg.drvcfg.num_reqq_elems - 1); \ + bfa_reg_write((__bfa)->iocfc.bfa_regs.cpe_q_pi[__reqq], \ + (__bfa)->iocfc.req_cq_pi[__reqq]); \ + bfa_os_mmiowb(); \ +} while (0) + +#define bfa_rspq_pi(__bfa, __rspq) \ + *(u32 *)((__bfa)->iocfc.rsp_cq_shadow_pi[__rspq].kva) + +#define bfa_rspq_ci(__bfa, __rspq) (__bfa)->iocfc.rsp_cq_ci[__rspq] +#define bfa_rspq_elem(__bfa, __rspq, __ci) \ + &((struct bfi_msg_s *)((__bfa)->iocfc.rsp_cq_ba[__rspq].kva))[__ci] + +#define CQ_INCR(__index, __size) \ + (__index)++; (__index) &= ((__size) - 1) + +/** + * Queue element to wait for room in request queue. FIFO order is + * maintained when fullfilling requests. + */ +struct bfa_reqq_wait_s { + struct list_head qe; + void (*qresume) (void *cbarg); + void *cbarg; +}; + +/** + * Circular queue usage assignments + */ +enum { + BFA_REQQ_IOC = 0, /* all low-priority IOC msgs */ + BFA_REQQ_FCXP = 0, /* all FCXP messages */ + BFA_REQQ_LPS = 0, /* all lport service msgs */ + BFA_REQQ_PORT = 0, /* all port messages */ + BFA_REQQ_FLASH = 0, /* for flash module */ + BFA_REQQ_DIAG = 0, /* for diag module */ + BFA_REQQ_RPORT = 0, /* all port messages */ + BFA_REQQ_SBOOT = 0, /* all san boot messages */ + BFA_REQQ_QOS_LO = 1, /* all low priority IO */ + BFA_REQQ_QOS_MD = 2, /* all medium priority IO */ + BFA_REQQ_QOS_HI = 3, /* all high priority IO */ +}; + +static inline void +bfa_reqq_winit(struct bfa_reqq_wait_s *wqe, void (*qresume) (void *cbarg), + void *cbarg) +{ + wqe->qresume = qresume; + wqe->cbarg = cbarg; +} + +#define bfa_reqq(__bfa, __reqq) &(__bfa)->reqq_waitq[__reqq] + +/** + * static inline void + * bfa_reqq_wait(struct bfa_s *bfa, int reqq, struct bfa_reqq_wait_s *wqe) + */ +#define bfa_reqq_wait(__bfa, __reqq, __wqe) do { \ + \ + struct list_head *waitq = bfa_reqq(__bfa, __reqq); \ + \ + bfa_assert(((__reqq) < BFI_IOC_MAX_CQS)); \ + bfa_assert((__wqe)->qresume && (__wqe)->cbarg); \ + \ + list_add_tail(&(__wqe)->qe, waitq); \ +} while (0) + +#define bfa_reqq_wcancel(__wqe) list_del(&(__wqe)->qe) + +#endif /* __BFA_INTR_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_ioc.c b/drivers/scsi/bfa/bfa_ioc.c new file mode 100644 index 000000000000..149348934ce3 --- /dev/null +++ b/drivers/scsi/bfa/bfa_ioc.c @@ -0,0 +1,2382 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfa_ioc.h> +#include <bfa_fwimg_priv.h> +#include <bfa_trcmod_priv.h> +#include <cs/bfa_debug.h> +#include <bfi/bfi_ioc.h> +#include <bfi/bfi_ctreg.h> +#include <aen/bfa_aen_ioc.h> +#include <aen/bfa_aen.h> +#include <log/bfa_log_hal.h> +#include <defs/bfa_defs_pci.h> + +BFA_TRC_FILE(HAL, IOC); + +/** + * IOC local definitions + */ +#define BFA_IOC_TOV 2000 /* msecs */ +#define BFA_IOC_HB_TOV 1000 /* msecs */ +#define BFA_IOC_HB_FAIL_MAX 4 +#define BFA_IOC_HWINIT_MAX 2 +#define BFA_IOC_FWIMG_MINSZ (16 * 1024) +#define BFA_IOC_TOV_RECOVER (BFA_IOC_HB_FAIL_MAX * BFA_IOC_HB_TOV \ + + BFA_IOC_TOV) + +#define bfa_ioc_timer_start(__ioc) \ + bfa_timer_begin((__ioc)->timer_mod, &(__ioc)->ioc_timer, \ + bfa_ioc_timeout, (__ioc), BFA_IOC_TOV) +#define bfa_ioc_timer_stop(__ioc) bfa_timer_stop(&(__ioc)->ioc_timer) + +#define BFA_DBG_FWTRC_ENTS (BFI_IOC_TRC_ENTS) +#define BFA_DBG_FWTRC_LEN \ + (BFA_DBG_FWTRC_ENTS * sizeof(struct bfa_trc_s) + \ + (sizeof(struct bfa_trc_mod_s) - \ + BFA_TRC_MAX * sizeof(struct bfa_trc_s))) +#define BFA_DBG_FWTRC_OFF(_fn) (BFI_IOC_TRC_OFF + BFA_DBG_FWTRC_LEN * (_fn)) +#define bfa_ioc_stats(_ioc, _stats) (_ioc)->stats._stats ++ + +#define BFA_FLASH_CHUNK_NO(off) (off / BFI_FLASH_CHUNK_SZ_WORDS) +#define BFA_FLASH_OFFSET_IN_CHUNK(off) (off % BFI_FLASH_CHUNK_SZ_WORDS) +#define BFA_FLASH_CHUNK_ADDR(chunkno) (chunkno * BFI_FLASH_CHUNK_SZ_WORDS) +bfa_boolean_t bfa_auto_recover = BFA_FALSE; + +/* + * forward declarations + */ +static void bfa_ioc_aen_post(struct bfa_ioc_s *bfa, + enum bfa_ioc_aen_event event); +static void bfa_ioc_hw_sem_get(struct bfa_ioc_s *ioc); +static void bfa_ioc_hw_sem_release(struct bfa_ioc_s *ioc); +static void bfa_ioc_hw_sem_get_cancel(struct bfa_ioc_s *ioc); +static void bfa_ioc_hwinit(struct bfa_ioc_s *ioc, bfa_boolean_t force); +static void bfa_ioc_timeout(void *ioc); +static void bfa_ioc_send_enable(struct bfa_ioc_s *ioc); +static void bfa_ioc_send_disable(struct bfa_ioc_s *ioc); +static void bfa_ioc_send_getattr(struct bfa_ioc_s *ioc); +static void bfa_ioc_hb_monitor(struct bfa_ioc_s *ioc); +static void bfa_ioc_hb_stop(struct bfa_ioc_s *ioc); +static void bfa_ioc_reset(struct bfa_ioc_s *ioc, bfa_boolean_t force); +static void bfa_ioc_mbox_poll(struct bfa_ioc_s *ioc); +static void bfa_ioc_mbox_hbfail(struct bfa_ioc_s *ioc); +static void bfa_ioc_recover(struct bfa_ioc_s *ioc); +static bfa_boolean_t bfa_ioc_firmware_lock(struct bfa_ioc_s *ioc); +static void bfa_ioc_firmware_unlock(struct bfa_ioc_s *ioc); +static void bfa_ioc_disable_comp(struct bfa_ioc_s *ioc); +static void bfa_ioc_lpu_stop(struct bfa_ioc_s *ioc); + +/** + * bfa_ioc_sm + */ + +/** + * IOC state machine events + */ +enum ioc_event { + IOC_E_ENABLE = 1, /* IOC enable request */ + IOC_E_DISABLE = 2, /* IOC disable request */ + IOC_E_TIMEOUT = 3, /* f/w response timeout */ + IOC_E_FWREADY = 4, /* f/w initialization done */ + IOC_E_FWRSP_GETATTR = 5, /* IOC get attribute response */ + IOC_E_FWRSP_ENABLE = 6, /* enable f/w response */ + IOC_E_FWRSP_DISABLE = 7, /* disable f/w response */ + IOC_E_HBFAIL = 8, /* heartbeat failure */ + IOC_E_HWERROR = 9, /* hardware error interrupt */ + IOC_E_SEMLOCKED = 10, /* h/w semaphore is locked */ + IOC_E_DETACH = 11, /* driver detach cleanup */ +}; + +bfa_fsm_state_decl(bfa_ioc, reset, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, fwcheck, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, mismatch, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, semwait, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, hwinit, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, enabling, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, getattr, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, op, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, initfail, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, hbfail, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, disabling, struct bfa_ioc_s, enum ioc_event); +bfa_fsm_state_decl(bfa_ioc, disabled, struct bfa_ioc_s, enum ioc_event); + +static struct bfa_sm_table_s ioc_sm_table[] = { + {BFA_SM(bfa_ioc_sm_reset), BFA_IOC_RESET}, + {BFA_SM(bfa_ioc_sm_fwcheck), BFA_IOC_FWMISMATCH}, + {BFA_SM(bfa_ioc_sm_mismatch), BFA_IOC_FWMISMATCH}, + {BFA_SM(bfa_ioc_sm_semwait), BFA_IOC_SEMWAIT}, + {BFA_SM(bfa_ioc_sm_hwinit), BFA_IOC_HWINIT}, + {BFA_SM(bfa_ioc_sm_enabling), BFA_IOC_HWINIT}, + {BFA_SM(bfa_ioc_sm_getattr), BFA_IOC_GETATTR}, + {BFA_SM(bfa_ioc_sm_op), BFA_IOC_OPERATIONAL}, + {BFA_SM(bfa_ioc_sm_initfail), BFA_IOC_INITFAIL}, + {BFA_SM(bfa_ioc_sm_hbfail), BFA_IOC_HBFAIL}, + {BFA_SM(bfa_ioc_sm_disabling), BFA_IOC_DISABLING}, + {BFA_SM(bfa_ioc_sm_disabled), BFA_IOC_DISABLED}, +}; + +/** + * Reset entry actions -- initialize state machine + */ +static void +bfa_ioc_sm_reset_entry(struct bfa_ioc_s *ioc) +{ + ioc->retry_count = 0; + ioc->auto_recover = bfa_auto_recover; +} + +/** + * Beginning state. IOC is in reset state. + */ +static void +bfa_ioc_sm_reset(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_ENABLE: + bfa_fsm_set_state(ioc, bfa_ioc_sm_fwcheck); + break; + + case IOC_E_DISABLE: + bfa_ioc_disable_comp(ioc); + break; + + case IOC_E_DETACH: + break; + + default: + bfa_sm_fault(ioc, event); + } +} + +/** + * Semaphore should be acquired for version check. + */ +static void +bfa_ioc_sm_fwcheck_entry(struct bfa_ioc_s *ioc) +{ + bfa_ioc_hw_sem_get(ioc); +} + +/** + * Awaiting h/w semaphore to continue with version check. + */ +static void +bfa_ioc_sm_fwcheck(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_SEMLOCKED: + if (bfa_ioc_firmware_lock(ioc)) { + ioc->retry_count = 0; + bfa_fsm_set_state(ioc, bfa_ioc_sm_hwinit); + } else { + bfa_ioc_hw_sem_release(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_mismatch); + } + break; + + case IOC_E_DISABLE: + bfa_ioc_disable_comp(ioc); + /* + * fall through + */ + + case IOC_E_DETACH: + bfa_ioc_hw_sem_get_cancel(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_reset); + break; + + case IOC_E_FWREADY: + break; + + default: + bfa_sm_fault(ioc, event); + } +} + +/** + * Notify enable completion callback and generate mismatch AEN. + */ +static void +bfa_ioc_sm_mismatch_entry(struct bfa_ioc_s *ioc) +{ + /** + * Provide enable completion callback and AEN notification only once. + */ + if (ioc->retry_count == 0) { + ioc->cbfn->enable_cbfn(ioc->bfa, BFA_STATUS_IOC_FAILURE); + bfa_ioc_aen_post(ioc, BFA_IOC_AEN_FWMISMATCH); + } + ioc->retry_count++; + bfa_ioc_timer_start(ioc); +} + +/** + * Awaiting firmware version match. + */ +static void +bfa_ioc_sm_mismatch(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_TIMEOUT: + bfa_fsm_set_state(ioc, bfa_ioc_sm_fwcheck); + break; + + case IOC_E_DISABLE: + bfa_ioc_disable_comp(ioc); + /* + * fall through + */ + + case IOC_E_DETACH: + bfa_ioc_timer_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_reset); + break; + + case IOC_E_FWREADY: + break; + + default: + bfa_sm_fault(ioc, event); + } +} + +/** + * Request for semaphore. + */ +static void +bfa_ioc_sm_semwait_entry(struct bfa_ioc_s *ioc) +{ + bfa_ioc_hw_sem_get(ioc); +} + +/** + * Awaiting semaphore for h/w initialzation. + */ +static void +bfa_ioc_sm_semwait(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_SEMLOCKED: + ioc->retry_count = 0; + bfa_fsm_set_state(ioc, bfa_ioc_sm_hwinit); + break; + + case IOC_E_DISABLE: + bfa_ioc_hw_sem_get_cancel(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabled); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + +static void +bfa_ioc_sm_hwinit_entry(struct bfa_ioc_s *ioc) +{ + bfa_ioc_timer_start(ioc); + bfa_ioc_reset(ioc, BFA_FALSE); +} + +/** + * Hardware is being initialized. Interrupts are enabled. + * Holding hardware semaphore lock. + */ +static void +bfa_ioc_sm_hwinit(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_FWREADY: + bfa_ioc_timer_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_enabling); + break; + + case IOC_E_HWERROR: + bfa_ioc_timer_stop(ioc); + /* + * fall through + */ + + case IOC_E_TIMEOUT: + ioc->retry_count++; + if (ioc->retry_count < BFA_IOC_HWINIT_MAX) { + bfa_ioc_timer_start(ioc); + bfa_ioc_reset(ioc, BFA_TRUE); + break; + } + + bfa_ioc_hw_sem_release(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_initfail); + break; + + case IOC_E_DISABLE: + bfa_ioc_hw_sem_release(ioc); + bfa_ioc_timer_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabled); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + +static void +bfa_ioc_sm_enabling_entry(struct bfa_ioc_s *ioc) +{ + bfa_ioc_timer_start(ioc); + bfa_ioc_send_enable(ioc); +} + +/** + * Host IOC function is being enabled, awaiting response from firmware. + * Semaphore is acquired. + */ +static void +bfa_ioc_sm_enabling(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_FWRSP_ENABLE: + bfa_ioc_timer_stop(ioc); + bfa_ioc_hw_sem_release(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_getattr); + break; + + case IOC_E_HWERROR: + bfa_ioc_timer_stop(ioc); + /* + * fall through + */ + + case IOC_E_TIMEOUT: + ioc->retry_count++; + if (ioc->retry_count < BFA_IOC_HWINIT_MAX) { + bfa_reg_write(ioc->ioc_regs.ioc_fwstate, + BFI_IOC_UNINIT); + bfa_fsm_set_state(ioc, bfa_ioc_sm_hwinit); + break; + } + + bfa_ioc_hw_sem_release(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_initfail); + break; + + case IOC_E_DISABLE: + bfa_ioc_timer_stop(ioc); + bfa_ioc_hw_sem_release(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabled); + break; + + case IOC_E_FWREADY: + bfa_ioc_send_enable(ioc); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + +static void +bfa_ioc_sm_getattr_entry(struct bfa_ioc_s *ioc) +{ + bfa_ioc_timer_start(ioc); + bfa_ioc_send_getattr(ioc); +} + +/** + * IOC configuration in progress. Timer is active. + */ +static void +bfa_ioc_sm_getattr(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_FWRSP_GETATTR: + bfa_ioc_timer_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_op); + break; + + case IOC_E_HWERROR: + bfa_ioc_timer_stop(ioc); + /* + * fall through + */ + + case IOC_E_TIMEOUT: + bfa_fsm_set_state(ioc, bfa_ioc_sm_initfail); + break; + + case IOC_E_DISABLE: + bfa_ioc_timer_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabled); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + +static void +bfa_ioc_sm_op_entry(struct bfa_ioc_s *ioc) +{ + ioc->cbfn->enable_cbfn(ioc->bfa, BFA_STATUS_OK); + bfa_ioc_hb_monitor(ioc); + bfa_ioc_aen_post(ioc, BFA_IOC_AEN_ENABLE); +} + +static void +bfa_ioc_sm_op(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_ENABLE: + break; + + case IOC_E_DISABLE: + bfa_ioc_hb_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabling); + break; + + case IOC_E_HWERROR: + case IOC_E_FWREADY: + /** + * Hard error or IOC recovery by other function. + * Treat it same as heartbeat failure. + */ + bfa_ioc_hb_stop(ioc); + /* + * !!! fall through !!! + */ + + case IOC_E_HBFAIL: + bfa_fsm_set_state(ioc, bfa_ioc_sm_hbfail); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + +static void +bfa_ioc_sm_disabling_entry(struct bfa_ioc_s *ioc) +{ + bfa_ioc_aen_post(ioc, BFA_IOC_AEN_DISABLE); + bfa_ioc_timer_start(ioc); + bfa_ioc_send_disable(ioc); +} + +/** + * IOC is being disabled + */ +static void +bfa_ioc_sm_disabling(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_HWERROR: + case IOC_E_FWRSP_DISABLE: + bfa_ioc_timer_stop(ioc); + /* + * !!! fall through !!! + */ + + case IOC_E_TIMEOUT: + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabled); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + +/** + * IOC disable completion entry. + */ +static void +bfa_ioc_sm_disabled_entry(struct bfa_ioc_s *ioc) +{ + bfa_ioc_disable_comp(ioc); +} + +static void +bfa_ioc_sm_disabled(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_ENABLE: + bfa_fsm_set_state(ioc, bfa_ioc_sm_semwait); + break; + + case IOC_E_DISABLE: + ioc->cbfn->disable_cbfn(ioc->bfa); + break; + + case IOC_E_FWREADY: + break; + + case IOC_E_DETACH: + bfa_ioc_firmware_unlock(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_reset); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + +static void +bfa_ioc_sm_initfail_entry(struct bfa_ioc_s *ioc) +{ + ioc->cbfn->enable_cbfn(ioc->bfa, BFA_STATUS_IOC_FAILURE); + bfa_ioc_timer_start(ioc); +} + +/** + * Hardware initialization failed. + */ +static void +bfa_ioc_sm_initfail(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + case IOC_E_DISABLE: + bfa_ioc_timer_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabled); + break; + + case IOC_E_DETACH: + bfa_ioc_timer_stop(ioc); + bfa_ioc_firmware_unlock(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_reset); + break; + + case IOC_E_TIMEOUT: + bfa_fsm_set_state(ioc, bfa_ioc_sm_semwait); + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + +static void +bfa_ioc_sm_hbfail_entry(struct bfa_ioc_s *ioc) +{ + struct list_head *qe; + struct bfa_ioc_hbfail_notify_s *notify; + + /** + * Mark IOC as failed in hardware and stop firmware. + */ + bfa_ioc_lpu_stop(ioc); + bfa_reg_write(ioc->ioc_regs.ioc_fwstate, BFI_IOC_HBFAIL); + + if (ioc->pcidev.device_id == BFA_PCI_DEVICE_ID_CT) { + bfa_reg_write(ioc->ioc_regs.ll_halt, __FW_INIT_HALT_P); + /* + * Wait for halt to take effect + */ + bfa_reg_read(ioc->ioc_regs.ll_halt); + } + + /** + * Notify driver and common modules registered for notification. + */ + ioc->cbfn->hbfail_cbfn(ioc->bfa); + list_for_each(qe, &ioc->hb_notify_q) { + notify = (struct bfa_ioc_hbfail_notify_s *)qe; + notify->cbfn(notify->cbarg); + } + + /** + * Flush any queued up mailbox requests. + */ + bfa_ioc_mbox_hbfail(ioc); + bfa_ioc_aen_post(ioc, BFA_IOC_AEN_HBFAIL); + + /** + * Trigger auto-recovery after a delay. + */ + if (ioc->auto_recover) { + bfa_timer_begin(ioc->timer_mod, &ioc->ioc_timer, + bfa_ioc_timeout, ioc, BFA_IOC_TOV_RECOVER); + } +} + +/** + * IOC heartbeat failure. + */ +static void +bfa_ioc_sm_hbfail(struct bfa_ioc_s *ioc, enum ioc_event event) +{ + bfa_trc(ioc, event); + + switch (event) { + + case IOC_E_ENABLE: + ioc->cbfn->enable_cbfn(ioc->bfa, BFA_STATUS_IOC_FAILURE); + break; + + case IOC_E_DISABLE: + if (ioc->auto_recover) + bfa_ioc_timer_stop(ioc); + bfa_fsm_set_state(ioc, bfa_ioc_sm_disabled); + break; + + case IOC_E_TIMEOUT: + bfa_fsm_set_state(ioc, bfa_ioc_sm_semwait); + break; + + case IOC_E_FWREADY: + /** + * Recovery is already initiated by other function. + */ + break; + + default: + bfa_sm_fault(ioc, event); + } +} + + + +/** + * bfa_ioc_pvt BFA IOC private functions + */ + +static void +bfa_ioc_disable_comp(struct bfa_ioc_s *ioc) +{ + struct list_head *qe; + struct bfa_ioc_hbfail_notify_s *notify; + + ioc->cbfn->disable_cbfn(ioc->bfa); + + /** + * Notify common modules registered for notification. + */ + list_for_each(qe, &ioc->hb_notify_q) { + notify = (struct bfa_ioc_hbfail_notify_s *)qe; + notify->cbfn(notify->cbarg); + } +} + +static void +bfa_ioc_sem_timeout(void *ioc_arg) +{ + struct bfa_ioc_s *ioc = (struct bfa_ioc_s *)ioc_arg; + + bfa_ioc_hw_sem_get(ioc); +} + +static void +bfa_ioc_usage_sem_get(struct bfa_ioc_s *ioc) +{ + u32 r32; + int cnt = 0; +#define BFA_SEM_SPINCNT 1000 + + do { + r32 = bfa_reg_read(ioc->ioc_regs.ioc_usage_sem_reg); + cnt++; + if (cnt > BFA_SEM_SPINCNT) + break; + } while (r32 != 0); + bfa_assert(cnt < BFA_SEM_SPINCNT); +} + +static void +bfa_ioc_usage_sem_release(struct bfa_ioc_s *ioc) +{ + bfa_reg_write(ioc->ioc_regs.ioc_usage_sem_reg, 1); +} + +static void +bfa_ioc_hw_sem_get(struct bfa_ioc_s *ioc) +{ + u32 r32; + + /** + * First read to the semaphore register will return 0, subsequent reads + * will return 1. Semaphore is released by writing 0 to the register + */ + r32 = bfa_reg_read(ioc->ioc_regs.ioc_sem_reg); + if (r32 == 0) { + bfa_fsm_send_event(ioc, IOC_E_SEMLOCKED); + return; + } + + bfa_timer_begin(ioc->timer_mod, &ioc->sem_timer, bfa_ioc_sem_timeout, + ioc, BFA_IOC_TOV); +} + +static void +bfa_ioc_hw_sem_release(struct bfa_ioc_s *ioc) +{ + bfa_reg_write(ioc->ioc_regs.ioc_sem_reg, 1); +} + +static void +bfa_ioc_hw_sem_get_cancel(struct bfa_ioc_s *ioc) +{ + bfa_timer_stop(&ioc->sem_timer); +} + +/** + * Initialize LPU local memory (aka secondary memory / SRAM) + */ +static void +bfa_ioc_lmem_init(struct bfa_ioc_s *ioc) +{ + u32 pss_ctl; + int i; +#define PSS_LMEM_INIT_TIME 10000 + + pss_ctl = bfa_reg_read(ioc->ioc_regs.pss_ctl_reg); + pss_ctl &= ~__PSS_LMEM_RESET; + pss_ctl |= __PSS_LMEM_INIT_EN; + pss_ctl |= __PSS_I2C_CLK_DIV(3UL); /* i2c workaround 12.5khz clock */ + bfa_reg_write(ioc->ioc_regs.pss_ctl_reg, pss_ctl); + + /** + * wait for memory initialization to be complete + */ + i = 0; + do { + pss_ctl = bfa_reg_read(ioc->ioc_regs.pss_ctl_reg); + i++; + } while (!(pss_ctl & __PSS_LMEM_INIT_DONE) && (i < PSS_LMEM_INIT_TIME)); + + /** + * If memory initialization is not successful, IOC timeout will catch + * such failures. + */ + bfa_assert(pss_ctl & __PSS_LMEM_INIT_DONE); + bfa_trc(ioc, pss_ctl); + + pss_ctl &= ~(__PSS_LMEM_INIT_DONE | __PSS_LMEM_INIT_EN); + bfa_reg_write(ioc->ioc_regs.pss_ctl_reg, pss_ctl); +} + +static void +bfa_ioc_lpu_start(struct bfa_ioc_s *ioc) +{ + u32 pss_ctl; + + /** + * Take processor out of reset. + */ + pss_ctl = bfa_reg_read(ioc->ioc_regs.pss_ctl_reg); + pss_ctl &= ~__PSS_LPU0_RESET; + + bfa_reg_write(ioc->ioc_regs.pss_ctl_reg, pss_ctl); +} + +static void +bfa_ioc_lpu_stop(struct bfa_ioc_s *ioc) +{ + u32 pss_ctl; + + /** + * Put processors in reset. + */ + pss_ctl = bfa_reg_read(ioc->ioc_regs.pss_ctl_reg); + pss_ctl |= (__PSS_LPU0_RESET | __PSS_LPU1_RESET); + + bfa_reg_write(ioc->ioc_regs.pss_ctl_reg, pss_ctl); +} + +/** + * Get driver and firmware versions. + */ +static void +bfa_ioc_fwver_get(struct bfa_ioc_s *ioc, struct bfi_ioc_image_hdr_s *fwhdr) +{ + u32 pgnum, pgoff; + u32 loff = 0; + int i; + u32 *fwsig = (u32 *) fwhdr; + + pgnum = bfa_ioc_smem_pgnum(ioc, loff); + pgoff = bfa_ioc_smem_pgoff(ioc, loff); + bfa_reg_write(ioc->ioc_regs.host_page_num_fn, pgnum); + + for (i = 0; i < (sizeof(struct bfi_ioc_image_hdr_s) / sizeof(u32)); + i++) { + fwsig[i] = bfa_mem_read(ioc->ioc_regs.smem_page_start, loff); + loff += sizeof(u32); + } +} + +static u32 * +bfa_ioc_fwimg_get_chunk(struct bfa_ioc_s *ioc, u32 off) +{ + if (ioc->ctdev) + return bfi_image_ct_get_chunk(off); + return bfi_image_cb_get_chunk(off); +} + +static u32 +bfa_ioc_fwimg_get_size(struct bfa_ioc_s *ioc) +{ +return (ioc->ctdev) ? bfi_image_ct_size : bfi_image_cb_size; +} + +/** + * Returns TRUE if same. + */ +static bfa_boolean_t +bfa_ioc_fwver_cmp(struct bfa_ioc_s *ioc, struct bfi_ioc_image_hdr_s *fwhdr) +{ + struct bfi_ioc_image_hdr_s *drv_fwhdr; + int i; + + drv_fwhdr = + (struct bfi_ioc_image_hdr_s *)bfa_ioc_fwimg_get_chunk(ioc, 0); + + for (i = 0; i < BFI_IOC_MD5SUM_SZ; i++) { + if (fwhdr->md5sum[i] != drv_fwhdr->md5sum[i]) { + bfa_trc(ioc, i); + bfa_trc(ioc, fwhdr->md5sum[i]); + bfa_trc(ioc, drv_fwhdr->md5sum[i]); + return BFA_FALSE; + } + } + + bfa_trc(ioc, fwhdr->md5sum[0]); + return BFA_TRUE; +} + +/** + * Return true if current running version is valid. Firmware signature and + * execution context (driver/bios) must match. + */ +static bfa_boolean_t +bfa_ioc_fwver_valid(struct bfa_ioc_s *ioc) +{ + struct bfi_ioc_image_hdr_s fwhdr, *drv_fwhdr; + + /** + * If bios/efi boot (flash based) -- return true + */ + if (bfa_ioc_fwimg_get_size(ioc) < BFA_IOC_FWIMG_MINSZ) + return BFA_TRUE; + + bfa_ioc_fwver_get(ioc, &fwhdr); + drv_fwhdr = + (struct bfi_ioc_image_hdr_s *)bfa_ioc_fwimg_get_chunk(ioc, 0); + + if (fwhdr.signature != drv_fwhdr->signature) { + bfa_trc(ioc, fwhdr.signature); + bfa_trc(ioc, drv_fwhdr->signature); + return BFA_FALSE; + } + + if (fwhdr.exec != drv_fwhdr->exec) { + bfa_trc(ioc, fwhdr.exec); + bfa_trc(ioc, drv_fwhdr->exec); + return BFA_FALSE; + } + + return bfa_ioc_fwver_cmp(ioc, &fwhdr); +} + +/** + * Return true if firmware of current driver matches the running firmware. + */ +static bfa_boolean_t +bfa_ioc_firmware_lock(struct bfa_ioc_s *ioc) +{ + enum bfi_ioc_state ioc_fwstate; + u32 usecnt; + struct bfi_ioc_image_hdr_s fwhdr; + + /** + * Firmware match check is relevant only for CNA. + */ + if (!ioc->cna) + return BFA_TRUE; + + /** + * If bios boot (flash based) -- do not increment usage count + */ + if (bfa_ioc_fwimg_get_size(ioc) < BFA_IOC_FWIMG_MINSZ) + return BFA_TRUE; + + bfa_ioc_usage_sem_get(ioc); + usecnt = bfa_reg_read(ioc->ioc_regs.ioc_usage_reg); + + /** + * If usage count is 0, always return TRUE. + */ + if (usecnt == 0) { + bfa_reg_write(ioc->ioc_regs.ioc_usage_reg, 1); + bfa_ioc_usage_sem_release(ioc); + bfa_trc(ioc, usecnt); + return BFA_TRUE; + } + + ioc_fwstate = bfa_reg_read(ioc->ioc_regs.ioc_fwstate); + bfa_trc(ioc, ioc_fwstate); + + /** + * Use count cannot be non-zero and chip in uninitialized state. + */ + bfa_assert(ioc_fwstate != BFI_IOC_UNINIT); + + /** + * Check if another driver with a different firmware is active + */ + bfa_ioc_fwver_get(ioc, &fwhdr); + if (!bfa_ioc_fwver_cmp(ioc, &fwhdr)) { + bfa_ioc_usage_sem_release(ioc); + bfa_trc(ioc, usecnt); + return BFA_FALSE; + } + + /** + * Same firmware version. Increment the reference count. + */ + usecnt++; + bfa_reg_write(ioc->ioc_regs.ioc_usage_reg, usecnt); + bfa_ioc_usage_sem_release(ioc); + bfa_trc(ioc, usecnt); + return BFA_TRUE; +} + +static void +bfa_ioc_firmware_unlock(struct bfa_ioc_s *ioc) +{ + u32 usecnt; + + /** + * Firmware lock is relevant only for CNA. + * If bios boot (flash based) -- do not decrement usage count + */ + if (!ioc->cna || (bfa_ioc_fwimg_get_size(ioc) < BFA_IOC_FWIMG_MINSZ)) + return; + + /** + * decrement usage count + */ + bfa_ioc_usage_sem_get(ioc); + usecnt = bfa_reg_read(ioc->ioc_regs.ioc_usage_reg); + bfa_assert(usecnt > 0); + + usecnt--; + bfa_reg_write(ioc->ioc_regs.ioc_usage_reg, usecnt); + bfa_trc(ioc, usecnt); + + bfa_ioc_usage_sem_release(ioc); +} + +/** + * Conditionally flush any pending message from firmware at start. + */ +static void +bfa_ioc_msgflush(struct bfa_ioc_s *ioc) +{ + u32 r32; + + r32 = bfa_reg_read(ioc->ioc_regs.lpu_mbox_cmd); + if (r32) + bfa_reg_write(ioc->ioc_regs.lpu_mbox_cmd, 1); +} + + +static void +bfa_ioc_hwinit(struct bfa_ioc_s *ioc, bfa_boolean_t force) +{ + enum bfi_ioc_state ioc_fwstate; + bfa_boolean_t fwvalid; + + ioc_fwstate = bfa_reg_read(ioc->ioc_regs.ioc_fwstate); + + if (force) + ioc_fwstate = BFI_IOC_UNINIT; + + bfa_trc(ioc, ioc_fwstate); + + /** + * check if firmware is valid + */ + fwvalid = (ioc_fwstate == BFI_IOC_UNINIT) ? + BFA_FALSE : bfa_ioc_fwver_valid(ioc); + + if (!fwvalid) { + bfa_ioc_boot(ioc, BFI_BOOT_TYPE_NORMAL, ioc->pcidev.device_id); + return; + } + + /** + * If hardware initialization is in progress (initialized by other IOC), + * just wait for an initialization completion interrupt. + */ + if (ioc_fwstate == BFI_IOC_INITING) { + bfa_trc(ioc, ioc_fwstate); + ioc->cbfn->reset_cbfn(ioc->bfa); + return; + } + + /** + * If IOC function is disabled and firmware version is same, + * just re-enable IOC. + */ + if (ioc_fwstate == BFI_IOC_DISABLED || ioc_fwstate == BFI_IOC_OP) { + bfa_trc(ioc, ioc_fwstate); + + /** + * When using MSI-X any pending firmware ready event should + * be flushed. Otherwise MSI-X interrupts are not delivered. + */ + bfa_ioc_msgflush(ioc); + ioc->cbfn->reset_cbfn(ioc->bfa); + bfa_fsm_send_event(ioc, IOC_E_FWREADY); + return; + } + + /** + * Initialize the h/w for any other states. + */ + bfa_ioc_boot(ioc, BFI_BOOT_TYPE_NORMAL, ioc->pcidev.device_id); +} + +static void +bfa_ioc_timeout(void *ioc_arg) +{ + struct bfa_ioc_s *ioc = (struct bfa_ioc_s *)ioc_arg; + + bfa_trc(ioc, 0); + bfa_fsm_send_event(ioc, IOC_E_TIMEOUT); +} + +void +bfa_ioc_mbox_send(struct bfa_ioc_s *ioc, void *ioc_msg, int len) +{ + u32 *msgp = (u32 *) ioc_msg; + u32 i; + + bfa_trc(ioc, msgp[0]); + bfa_trc(ioc, len); + + bfa_assert(len <= BFI_IOC_MSGLEN_MAX); + + /* + * first write msg to mailbox registers + */ + for (i = 0; i < len / sizeof(u32); i++) + bfa_reg_write(ioc->ioc_regs.hfn_mbox + i * sizeof(u32), + bfa_os_wtole(msgp[i])); + + for (; i < BFI_IOC_MSGLEN_MAX / sizeof(u32); i++) + bfa_reg_write(ioc->ioc_regs.hfn_mbox + i * sizeof(u32), 0); + + /* + * write 1 to mailbox CMD to trigger LPU event + */ + bfa_reg_write(ioc->ioc_regs.hfn_mbox_cmd, 1); + (void)bfa_reg_read(ioc->ioc_regs.hfn_mbox_cmd); +} + +static void +bfa_ioc_send_enable(struct bfa_ioc_s *ioc) +{ + struct bfi_ioc_ctrl_req_s enable_req; + + bfi_h2i_set(enable_req.mh, BFI_MC_IOC, BFI_IOC_H2I_ENABLE_REQ, + bfa_ioc_portid(ioc)); + enable_req.ioc_class = ioc->ioc_mc; + bfa_ioc_mbox_send(ioc, &enable_req, sizeof(struct bfi_ioc_ctrl_req_s)); +} + +static void +bfa_ioc_send_disable(struct bfa_ioc_s *ioc) +{ + struct bfi_ioc_ctrl_req_s disable_req; + + bfi_h2i_set(disable_req.mh, BFI_MC_IOC, BFI_IOC_H2I_DISABLE_REQ, + bfa_ioc_portid(ioc)); + bfa_ioc_mbox_send(ioc, &disable_req, sizeof(struct bfi_ioc_ctrl_req_s)); +} + +static void +bfa_ioc_send_getattr(struct bfa_ioc_s *ioc) +{ + struct bfi_ioc_getattr_req_s attr_req; + + bfi_h2i_set(attr_req.mh, BFI_MC_IOC, BFI_IOC_H2I_GETATTR_REQ, + bfa_ioc_portid(ioc)); + bfa_dma_be_addr_set(attr_req.attr_addr, ioc->attr_dma.pa); + bfa_ioc_mbox_send(ioc, &attr_req, sizeof(attr_req)); +} + +static void +bfa_ioc_hb_check(void *cbarg) +{ + struct bfa_ioc_s *ioc = cbarg; + u32 hb_count; + + hb_count = bfa_reg_read(ioc->ioc_regs.heartbeat); + if (ioc->hb_count == hb_count) { + ioc->hb_fail++; + } else { + ioc->hb_count = hb_count; + ioc->hb_fail = 0; + } + + if (ioc->hb_fail >= BFA_IOC_HB_FAIL_MAX) { + bfa_log(ioc->logm, BFA_LOG_HAL_HEARTBEAT_FAILURE, hb_count); + ioc->hb_fail = 0; + bfa_ioc_recover(ioc); + return; + } + + bfa_ioc_mbox_poll(ioc); + bfa_timer_begin(ioc->timer_mod, &ioc->ioc_timer, bfa_ioc_hb_check, ioc, + BFA_IOC_HB_TOV); +} + +static void +bfa_ioc_hb_monitor(struct bfa_ioc_s *ioc) +{ + ioc->hb_fail = 0; + ioc->hb_count = bfa_reg_read(ioc->ioc_regs.heartbeat); + bfa_timer_begin(ioc->timer_mod, &ioc->ioc_timer, bfa_ioc_hb_check, ioc, + BFA_IOC_HB_TOV); +} + +static void +bfa_ioc_hb_stop(struct bfa_ioc_s *ioc) +{ + bfa_timer_stop(&ioc->ioc_timer); +} + +/** + * Host to LPU mailbox message addresses + */ +static struct { + u32 hfn_mbox, lpu_mbox, hfn_pgn; +} iocreg_fnreg[] = { + { + HOSTFN0_LPU_MBOX0_0, LPU_HOSTFN0_MBOX0_0, HOST_PAGE_NUM_FN0}, { + HOSTFN1_LPU_MBOX0_8, LPU_HOSTFN1_MBOX0_8, HOST_PAGE_NUM_FN1}, { + HOSTFN2_LPU_MBOX0_0, LPU_HOSTFN2_MBOX0_0, HOST_PAGE_NUM_FN2}, { + HOSTFN3_LPU_MBOX0_8, LPU_HOSTFN3_MBOX0_8, HOST_PAGE_NUM_FN3} +}; + +/** + * Host <-> LPU mailbox command/status registers - port 0 + */ +static struct { + u32 hfn, lpu; +} iocreg_mbcmd_p0[] = { + { + HOSTFN0_LPU0_MBOX0_CMD_STAT, LPU0_HOSTFN0_MBOX0_CMD_STAT}, { + HOSTFN1_LPU0_MBOX0_CMD_STAT, LPU0_HOSTFN1_MBOX0_CMD_STAT}, { + HOSTFN2_LPU0_MBOX0_CMD_STAT, LPU0_HOSTFN2_MBOX0_CMD_STAT}, { + HOSTFN3_LPU0_MBOX0_CMD_STAT, LPU0_HOSTFN3_MBOX0_CMD_STAT} +}; + +/** + * Host <-> LPU mailbox command/status registers - port 1 + */ +static struct { + u32 hfn, lpu; +} iocreg_mbcmd_p1[] = { + { + HOSTFN0_LPU1_MBOX0_CMD_STAT, LPU1_HOSTFN0_MBOX0_CMD_STAT}, { + HOSTFN1_LPU1_MBOX0_CMD_STAT, LPU1_HOSTFN1_MBOX0_CMD_STAT}, { + HOSTFN2_LPU1_MBOX0_CMD_STAT, LPU1_HOSTFN2_MBOX0_CMD_STAT}, { + HOSTFN3_LPU1_MBOX0_CMD_STAT, LPU1_HOSTFN3_MBOX0_CMD_STAT} +}; + +/** + * Shared IRQ handling in INTX mode + */ +static struct { + u32 isr, msk; +} iocreg_shirq_next[] = { + { + HOSTFN1_INT_STATUS, HOSTFN1_INT_MSK}, { + HOSTFN2_INT_STATUS, HOSTFN2_INT_MSK}, { + HOSTFN3_INT_STATUS, HOSTFN3_INT_MSK}, { +HOSTFN0_INT_STATUS, HOSTFN0_INT_MSK},}; + +static void +bfa_ioc_reg_init(struct bfa_ioc_s *ioc) +{ + bfa_os_addr_t rb; + int pcifn = bfa_ioc_pcifn(ioc); + + rb = bfa_ioc_bar0(ioc); + + ioc->ioc_regs.hfn_mbox = rb + iocreg_fnreg[pcifn].hfn_mbox; + ioc->ioc_regs.lpu_mbox = rb + iocreg_fnreg[pcifn].lpu_mbox; + ioc->ioc_regs.host_page_num_fn = rb + iocreg_fnreg[pcifn].hfn_pgn; + + if (ioc->port_id == 0) { + ioc->ioc_regs.heartbeat = rb + BFA_IOC0_HBEAT_REG; + ioc->ioc_regs.ioc_fwstate = rb + BFA_IOC0_STATE_REG; + ioc->ioc_regs.hfn_mbox_cmd = rb + iocreg_mbcmd_p0[pcifn].hfn; + ioc->ioc_regs.lpu_mbox_cmd = rb + iocreg_mbcmd_p0[pcifn].lpu; + ioc->ioc_regs.ll_halt = rb + FW_INIT_HALT_P0; + } else { + ioc->ioc_regs.heartbeat = (rb + BFA_IOC1_HBEAT_REG); + ioc->ioc_regs.ioc_fwstate = (rb + BFA_IOC1_STATE_REG); + ioc->ioc_regs.hfn_mbox_cmd = rb + iocreg_mbcmd_p1[pcifn].hfn; + ioc->ioc_regs.lpu_mbox_cmd = rb + iocreg_mbcmd_p1[pcifn].lpu; + ioc->ioc_regs.ll_halt = rb + FW_INIT_HALT_P1; + } + + /** + * Shared IRQ handling in INTX mode + */ + ioc->ioc_regs.shirq_isr_next = rb + iocreg_shirq_next[pcifn].isr; + ioc->ioc_regs.shirq_msk_next = rb + iocreg_shirq_next[pcifn].msk; + + /* + * PSS control registers + */ + ioc->ioc_regs.pss_ctl_reg = (rb + PSS_CTL_REG); + ioc->ioc_regs.app_pll_fast_ctl_reg = (rb + APP_PLL_425_CTL_REG); + ioc->ioc_regs.app_pll_slow_ctl_reg = (rb + APP_PLL_312_CTL_REG); + + /* + * IOC semaphore registers and serialization + */ + ioc->ioc_regs.ioc_sem_reg = (rb + HOST_SEM0_REG); + ioc->ioc_regs.ioc_usage_sem_reg = (rb + HOST_SEM1_REG); + ioc->ioc_regs.ioc_usage_reg = (rb + BFA_FW_USE_COUNT); + + /** + * sram memory access + */ + ioc->ioc_regs.smem_page_start = (rb + PSS_SMEM_PAGE_START); + ioc->ioc_regs.smem_pg0 = BFI_IOC_SMEM_PG0_CB; + if (ioc->pcidev.device_id == BFA_PCI_DEVICE_ID_CT) + ioc->ioc_regs.smem_pg0 = BFI_IOC_SMEM_PG0_CT; +} + +/** + * Initiate a full firmware download. + */ +static void +bfa_ioc_download_fw(struct bfa_ioc_s *ioc, u32 boot_type, + u32 boot_param) +{ + u32 *fwimg; + u32 pgnum, pgoff; + u32 loff = 0; + u32 chunkno = 0; + u32 i; + + /** + * Initialize LMEM first before code download + */ + bfa_ioc_lmem_init(ioc); + + /** + * Flash based firmware boot + */ + bfa_trc(ioc, bfa_ioc_fwimg_get_size(ioc)); + if (bfa_ioc_fwimg_get_size(ioc) < BFA_IOC_FWIMG_MINSZ) + boot_type = BFI_BOOT_TYPE_FLASH; + fwimg = bfa_ioc_fwimg_get_chunk(ioc, chunkno); + fwimg[BFI_BOOT_TYPE_OFF / sizeof(u32)] = bfa_os_swap32(boot_type); + fwimg[BFI_BOOT_PARAM_OFF / sizeof(u32)] = + bfa_os_swap32(boot_param); + + pgnum = bfa_ioc_smem_pgnum(ioc, loff); + pgoff = bfa_ioc_smem_pgoff(ioc, loff); + + bfa_reg_write(ioc->ioc_regs.host_page_num_fn, pgnum); + + for (i = 0; i < bfa_ioc_fwimg_get_size(ioc); i++) { + + if (BFA_FLASH_CHUNK_NO(i) != chunkno) { + chunkno = BFA_FLASH_CHUNK_NO(i); + fwimg = bfa_ioc_fwimg_get_chunk(ioc, + BFA_FLASH_CHUNK_ADDR(chunkno)); + } + + /** + * write smem + */ + bfa_mem_write(ioc->ioc_regs.smem_page_start, loff, + fwimg[BFA_FLASH_OFFSET_IN_CHUNK(i)]); + + loff += sizeof(u32); + + /** + * handle page offset wrap around + */ + loff = PSS_SMEM_PGOFF(loff); + if (loff == 0) { + pgnum++; + bfa_reg_write(ioc->ioc_regs.host_page_num_fn, pgnum); + } + } + + bfa_reg_write(ioc->ioc_regs.host_page_num_fn, + bfa_ioc_smem_pgnum(ioc, 0)); +} + +static void +bfa_ioc_reset(struct bfa_ioc_s *ioc, bfa_boolean_t force) +{ + bfa_ioc_hwinit(ioc, force); +} + +/** + * Update BFA configuration from firmware configuration. + */ +static void +bfa_ioc_getattr_reply(struct bfa_ioc_s *ioc) +{ + struct bfi_ioc_attr_s *attr = ioc->attr; + + attr->adapter_prop = bfa_os_ntohl(attr->adapter_prop); + attr->maxfrsize = bfa_os_ntohs(attr->maxfrsize); + + bfa_fsm_send_event(ioc, IOC_E_FWRSP_GETATTR); +} + +/** + * Attach time initialization of mbox logic. + */ +static void +bfa_ioc_mbox_attach(struct bfa_ioc_s *ioc) +{ + struct bfa_ioc_mbox_mod_s *mod = &ioc->mbox_mod; + int mc; + + INIT_LIST_HEAD(&mod->cmd_q); + for (mc = 0; mc < BFI_MC_MAX; mc++) { + mod->mbhdlr[mc].cbfn = NULL; + mod->mbhdlr[mc].cbarg = ioc->bfa; + } +} + +/** + * Mbox poll timer -- restarts any pending mailbox requests. + */ +static void +bfa_ioc_mbox_poll(struct bfa_ioc_s *ioc) +{ + struct bfa_ioc_mbox_mod_s *mod = &ioc->mbox_mod; + struct bfa_mbox_cmd_s *cmd; + u32 stat; + + /** + * If no command pending, do nothing + */ + if (list_empty(&mod->cmd_q)) + return; + + /** + * If previous command is not yet fetched by firmware, do nothing + */ + stat = bfa_reg_read(ioc->ioc_regs.hfn_mbox_cmd); + if (stat) + return; + + /** + * Enqueue command to firmware. + */ + bfa_q_deq(&mod->cmd_q, &cmd); + bfa_ioc_mbox_send(ioc, cmd->msg, sizeof(cmd->msg)); +} + +/** + * Cleanup any pending requests. + */ +static void +bfa_ioc_mbox_hbfail(struct bfa_ioc_s *ioc) +{ + struct bfa_ioc_mbox_mod_s *mod = &ioc->mbox_mod; + struct bfa_mbox_cmd_s *cmd; + + while (!list_empty(&mod->cmd_q)) + bfa_q_deq(&mod->cmd_q, &cmd); +} + +/** + * Initialize IOC to port mapping. + */ + +#define FNC_PERS_FN_SHIFT(__fn) ((__fn) * 8) +static void +bfa_ioc_map_port(struct bfa_ioc_s *ioc) +{ + bfa_os_addr_t rb = ioc->pcidev.pci_bar_kva; + u32 r32; + + /** + * For crossbow, port id is same as pci function. + */ + if (ioc->pcidev.device_id != BFA_PCI_DEVICE_ID_CT) { + ioc->port_id = bfa_ioc_pcifn(ioc); + return; + } + + /** + * For catapult, base port id on personality register and IOC type + */ + r32 = bfa_reg_read(rb + FNC_PERS_REG); + r32 >>= FNC_PERS_FN_SHIFT(bfa_ioc_pcifn(ioc)); + ioc->port_id = (r32 & __F0_PORT_MAP_MK) >> __F0_PORT_MAP_SH; + + bfa_trc(ioc, bfa_ioc_pcifn(ioc)); + bfa_trc(ioc, ioc->port_id); +} + + + +/** + * bfa_ioc_public + */ + +/** +* Set interrupt mode for a function: INTX or MSIX + */ +void +bfa_ioc_isr_mode_set(struct bfa_ioc_s *ioc, bfa_boolean_t msix) +{ + bfa_os_addr_t rb = ioc->pcidev.pci_bar_kva; + u32 r32, mode; + + r32 = bfa_reg_read(rb + FNC_PERS_REG); + bfa_trc(ioc, r32); + + mode = (r32 >> FNC_PERS_FN_SHIFT(bfa_ioc_pcifn(ioc))) & + __F0_INTX_STATUS; + + /** + * If already in desired mode, do not change anything + */ + if (!msix && mode) + return; + + if (msix) + mode = __F0_INTX_STATUS_MSIX; + else + mode = __F0_INTX_STATUS_INTA; + + r32 &= ~(__F0_INTX_STATUS << FNC_PERS_FN_SHIFT(bfa_ioc_pcifn(ioc))); + r32 |= (mode << FNC_PERS_FN_SHIFT(bfa_ioc_pcifn(ioc))); + bfa_trc(ioc, r32); + + bfa_reg_write(rb + FNC_PERS_REG, r32); +} + +bfa_status_t +bfa_ioc_pll_init(struct bfa_ioc_s *ioc) +{ + bfa_os_addr_t rb = ioc->pcidev.pci_bar_kva; + u32 pll_sclk, pll_fclk, r32; + + if (ioc->pcidev.device_id == BFA_PCI_DEVICE_ID_CT) { + pll_sclk = + __APP_PLL_312_ENABLE | __APP_PLL_312_LRESETN | + __APP_PLL_312_RSEL200500 | __APP_PLL_312_P0_1(0U) | + __APP_PLL_312_JITLMT0_1(3U) | + __APP_PLL_312_CNTLMT0_1(1U); + pll_fclk = + __APP_PLL_425_ENABLE | __APP_PLL_425_LRESETN | + __APP_PLL_425_RSEL200500 | __APP_PLL_425_P0_1(0U) | + __APP_PLL_425_JITLMT0_1(3U) | + __APP_PLL_425_CNTLMT0_1(1U); + + /** + * For catapult, choose operational mode FC/FCoE + */ + if (ioc->fcmode) { + bfa_reg_write((rb + OP_MODE), 0); + bfa_reg_write((rb + ETH_MAC_SER_REG), + __APP_EMS_CMLCKSEL | __APP_EMS_REFCKBUFEN2 + | __APP_EMS_CHANNEL_SEL); + } else { + ioc->pllinit = BFA_TRUE; + bfa_reg_write((rb + OP_MODE), __GLOBAL_FCOE_MODE); + bfa_reg_write((rb + ETH_MAC_SER_REG), + __APP_EMS_REFCKBUFEN1); + } + } else { + pll_sclk = + __APP_PLL_312_ENABLE | __APP_PLL_312_LRESETN | + __APP_PLL_312_P0_1(3U) | __APP_PLL_312_JITLMT0_1(3U) | + __APP_PLL_312_CNTLMT0_1(3U); + pll_fclk = + __APP_PLL_425_ENABLE | __APP_PLL_425_LRESETN | + __APP_PLL_425_RSEL200500 | __APP_PLL_425_P0_1(3U) | + __APP_PLL_425_JITLMT0_1(3U) | + __APP_PLL_425_CNTLMT0_1(3U); + } + + bfa_reg_write((rb + BFA_IOC0_STATE_REG), BFI_IOC_UNINIT); + bfa_reg_write((rb + BFA_IOC1_STATE_REG), BFI_IOC_UNINIT); + + bfa_reg_write((rb + HOSTFN0_INT_MSK), 0xffffffffU); + bfa_reg_write((rb + HOSTFN1_INT_MSK), 0xffffffffU); + bfa_reg_write((rb + HOSTFN0_INT_STATUS), 0xffffffffU); + bfa_reg_write((rb + HOSTFN1_INT_STATUS), 0xffffffffU); + bfa_reg_write((rb + HOSTFN0_INT_MSK), 0xffffffffU); + bfa_reg_write((rb + HOSTFN1_INT_MSK), 0xffffffffU); + + bfa_reg_write(ioc->ioc_regs.app_pll_slow_ctl_reg, + __APP_PLL_312_LOGIC_SOFT_RESET); + bfa_reg_write(ioc->ioc_regs.app_pll_slow_ctl_reg, + __APP_PLL_312_BYPASS | __APP_PLL_312_LOGIC_SOFT_RESET); + bfa_reg_write(ioc->ioc_regs.app_pll_fast_ctl_reg, + __APP_PLL_425_LOGIC_SOFT_RESET); + bfa_reg_write(ioc->ioc_regs.app_pll_fast_ctl_reg, + __APP_PLL_425_BYPASS | __APP_PLL_425_LOGIC_SOFT_RESET); + bfa_os_udelay(2); + bfa_reg_write(ioc->ioc_regs.app_pll_slow_ctl_reg, + __APP_PLL_312_LOGIC_SOFT_RESET); + bfa_reg_write(ioc->ioc_regs.app_pll_fast_ctl_reg, + __APP_PLL_425_LOGIC_SOFT_RESET); + + bfa_reg_write(ioc->ioc_regs.app_pll_slow_ctl_reg, + pll_sclk | __APP_PLL_312_LOGIC_SOFT_RESET); + bfa_reg_write(ioc->ioc_regs.app_pll_fast_ctl_reg, + pll_fclk | __APP_PLL_425_LOGIC_SOFT_RESET); + + /** + * Wait for PLLs to lock. + */ + bfa_os_udelay(2000); + bfa_reg_write((rb + HOSTFN0_INT_STATUS), 0xffffffffU); + bfa_reg_write((rb + HOSTFN1_INT_STATUS), 0xffffffffU); + + bfa_reg_write(ioc->ioc_regs.app_pll_slow_ctl_reg, pll_sclk); + bfa_reg_write(ioc->ioc_regs.app_pll_fast_ctl_reg, pll_fclk); + + if (ioc->pcidev.device_id == BFA_PCI_DEVICE_ID_CT) { + bfa_reg_write((rb + MBIST_CTL_REG), __EDRAM_BISTR_START); + bfa_os_udelay(1000); + r32 = bfa_reg_read((rb + MBIST_STAT_REG)); + bfa_trc(ioc, r32); + } + + return BFA_STATUS_OK; +} + +/** + * Interface used by diag module to do firmware boot with memory test + * as the entry vector. + */ +void +bfa_ioc_boot(struct bfa_ioc_s *ioc, u32 boot_type, u32 boot_param) +{ + bfa_os_addr_t rb; + + bfa_ioc_stats(ioc, ioc_boots); + + if (bfa_ioc_pll_init(ioc) != BFA_STATUS_OK) + return; + + /** + * Initialize IOC state of all functions on a chip reset. + */ + rb = ioc->pcidev.pci_bar_kva; + if (boot_param == BFI_BOOT_TYPE_MEMTEST) { + bfa_reg_write((rb + BFA_IOC0_STATE_REG), BFI_IOC_MEMTEST); + bfa_reg_write((rb + BFA_IOC1_STATE_REG), BFI_IOC_MEMTEST); + } else { + bfa_reg_write((rb + BFA_IOC0_STATE_REG), BFI_IOC_INITING); + bfa_reg_write((rb + BFA_IOC1_STATE_REG), BFI_IOC_INITING); + } + + bfa_ioc_download_fw(ioc, boot_type, boot_param); + + /** + * Enable interrupts just before starting LPU + */ + ioc->cbfn->reset_cbfn(ioc->bfa); + bfa_ioc_lpu_start(ioc); +} + +/** + * Enable/disable IOC failure auto recovery. + */ +void +bfa_ioc_auto_recover(bfa_boolean_t auto_recover) +{ + bfa_auto_recover = BFA_FALSE; +} + + +bfa_boolean_t +bfa_ioc_is_operational(struct bfa_ioc_s *ioc) +{ + return bfa_fsm_cmp_state(ioc, bfa_ioc_sm_op); +} + +void +bfa_ioc_msgget(struct bfa_ioc_s *ioc, void *mbmsg) +{ + u32 *msgp = mbmsg; + u32 r32; + int i; + + /** + * read the MBOX msg + */ + for (i = 0; i < (sizeof(union bfi_ioc_i2h_msg_u) / sizeof(u32)); + i++) { + r32 = bfa_reg_read(ioc->ioc_regs.lpu_mbox + + i * sizeof(u32)); + msgp[i] = bfa_os_htonl(r32); + } + + /** + * turn off mailbox interrupt by clearing mailbox status + */ + bfa_reg_write(ioc->ioc_regs.lpu_mbox_cmd, 1); + bfa_reg_read(ioc->ioc_regs.lpu_mbox_cmd); +} + +void +bfa_ioc_isr(struct bfa_ioc_s *ioc, struct bfi_mbmsg_s *m) +{ + union bfi_ioc_i2h_msg_u *msg; + + msg = (union bfi_ioc_i2h_msg_u *)m; + + bfa_ioc_stats(ioc, ioc_isrs); + + switch (msg->mh.msg_id) { + case BFI_IOC_I2H_HBEAT: + break; + + case BFI_IOC_I2H_READY_EVENT: + bfa_fsm_send_event(ioc, IOC_E_FWREADY); + break; + + case BFI_IOC_I2H_ENABLE_REPLY: + bfa_fsm_send_event(ioc, IOC_E_FWRSP_ENABLE); + break; + + case BFI_IOC_I2H_DISABLE_REPLY: + bfa_fsm_send_event(ioc, IOC_E_FWRSP_DISABLE); + break; + + case BFI_IOC_I2H_GETATTR_REPLY: + bfa_ioc_getattr_reply(ioc); + break; + + default: + bfa_trc(ioc, msg->mh.msg_id); + bfa_assert(0); + } +} + +/** + * IOC attach time initialization and setup. + * + * @param[in] ioc memory for IOC + * @param[in] bfa driver instance structure + * @param[in] trcmod kernel trace module + * @param[in] aen kernel aen event module + * @param[in] logm kernel logging module + */ +void +bfa_ioc_attach(struct bfa_ioc_s *ioc, void *bfa, struct bfa_ioc_cbfn_s *cbfn, + struct bfa_timer_mod_s *timer_mod, struct bfa_trc_mod_s *trcmod, + struct bfa_aen_s *aen, struct bfa_log_mod_s *logm) +{ + ioc->bfa = bfa; + ioc->cbfn = cbfn; + ioc->timer_mod = timer_mod; + ioc->trcmod = trcmod; + ioc->aen = aen; + ioc->logm = logm; + ioc->fcmode = BFA_FALSE; + ioc->pllinit = BFA_FALSE; + ioc->dbg_fwsave_once = BFA_TRUE; + + bfa_ioc_mbox_attach(ioc); + INIT_LIST_HEAD(&ioc->hb_notify_q); + + bfa_fsm_set_state(ioc, bfa_ioc_sm_reset); +} + +/** + * Driver detach time IOC cleanup. + */ +void +bfa_ioc_detach(struct bfa_ioc_s *ioc) +{ + bfa_fsm_send_event(ioc, IOC_E_DETACH); +} + +/** + * Setup IOC PCI properties. + * + * @param[in] pcidev PCI device information for this IOC + */ +void +bfa_ioc_pci_init(struct bfa_ioc_s *ioc, struct bfa_pcidev_s *pcidev, + enum bfi_mclass mc) +{ + ioc->ioc_mc = mc; + ioc->pcidev = *pcidev; + ioc->ctdev = (ioc->pcidev.device_id == BFA_PCI_DEVICE_ID_CT); + ioc->cna = ioc->ctdev && !ioc->fcmode; + + bfa_ioc_map_port(ioc); + bfa_ioc_reg_init(ioc); +} + +/** + * Initialize IOC dma memory + * + * @param[in] dm_kva kernel virtual address of IOC dma memory + * @param[in] dm_pa physical address of IOC dma memory + */ +void +bfa_ioc_mem_claim(struct bfa_ioc_s *ioc, u8 *dm_kva, u64 dm_pa) +{ + /** + * dma memory for firmware attribute + */ + ioc->attr_dma.kva = dm_kva; + ioc->attr_dma.pa = dm_pa; + ioc->attr = (struct bfi_ioc_attr_s *)dm_kva; +} + +/** + * Return size of dma memory required. + */ +u32 +bfa_ioc_meminfo(void) +{ + return BFA_ROUNDUP(sizeof(struct bfi_ioc_attr_s), BFA_DMA_ALIGN_SZ); +} + +void +bfa_ioc_enable(struct bfa_ioc_s *ioc) +{ + bfa_ioc_stats(ioc, ioc_enables); + ioc->dbg_fwsave_once = BFA_TRUE; + + bfa_fsm_send_event(ioc, IOC_E_ENABLE); +} + +void +bfa_ioc_disable(struct bfa_ioc_s *ioc) +{ + bfa_ioc_stats(ioc, ioc_disables); + bfa_fsm_send_event(ioc, IOC_E_DISABLE); +} + +/** + * Returns memory required for saving firmware trace in case of crash. + * Driver must call this interface to allocate memory required for + * automatic saving of firmware trace. Driver should call + * bfa_ioc_debug_memclaim() right after bfa_ioc_attach() to setup this + * trace memory. + */ +int +bfa_ioc_debug_trcsz(bfa_boolean_t auto_recover) +{ +return (auto_recover) ? BFA_DBG_FWTRC_LEN : 0; +} + +/** + * Initialize memory for saving firmware trace. Driver must initialize + * trace memory before call bfa_ioc_enable(). + */ +void +bfa_ioc_debug_memclaim(struct bfa_ioc_s *ioc, void *dbg_fwsave) +{ + bfa_assert(ioc->auto_recover); + ioc->dbg_fwsave = dbg_fwsave; + ioc->dbg_fwsave_len = bfa_ioc_debug_trcsz(ioc->auto_recover); +} + +u32 +bfa_ioc_smem_pgnum(struct bfa_ioc_s *ioc, u32 fmaddr) +{ + return PSS_SMEM_PGNUM(ioc->ioc_regs.smem_pg0, fmaddr); +} + +u32 +bfa_ioc_smem_pgoff(struct bfa_ioc_s *ioc, u32 fmaddr) +{ + return PSS_SMEM_PGOFF(fmaddr); +} + +/** + * Register mailbox message handler functions + * + * @param[in] ioc IOC instance + * @param[in] mcfuncs message class handler functions + */ +void +bfa_ioc_mbox_register(struct bfa_ioc_s *ioc, bfa_ioc_mbox_mcfunc_t *mcfuncs) +{ + struct bfa_ioc_mbox_mod_s *mod = &ioc->mbox_mod; + int mc; + + for (mc = 0; mc < BFI_MC_MAX; mc++) + mod->mbhdlr[mc].cbfn = mcfuncs[mc]; +} + +/** + * Register mailbox message handler function, to be called by common modules + */ +void +bfa_ioc_mbox_regisr(struct bfa_ioc_s *ioc, enum bfi_mclass mc, + bfa_ioc_mbox_mcfunc_t cbfn, void *cbarg) +{ + struct bfa_ioc_mbox_mod_s *mod = &ioc->mbox_mod; + + mod->mbhdlr[mc].cbfn = cbfn; + mod->mbhdlr[mc].cbarg = cbarg; +} + +/** + * Queue a mailbox command request to firmware. Waits if mailbox is busy. + * Responsibility of caller to serialize + * + * @param[in] ioc IOC instance + * @param[i] cmd Mailbox command + */ +void +bfa_ioc_mbox_queue(struct bfa_ioc_s *ioc, struct bfa_mbox_cmd_s *cmd) +{ + struct bfa_ioc_mbox_mod_s *mod = &ioc->mbox_mod; + u32 stat; + + /** + * If a previous command is pending, queue new command + */ + if (!list_empty(&mod->cmd_q)) { + list_add_tail(&cmd->qe, &mod->cmd_q); + return; + } + + /** + * If mailbox is busy, queue command for poll timer + */ + stat = bfa_reg_read(ioc->ioc_regs.hfn_mbox_cmd); + if (stat) { + list_add_tail(&cmd->qe, &mod->cmd_q); + return; + } + + /** + * mailbox is free -- queue command to firmware + */ + bfa_ioc_mbox_send(ioc, cmd->msg, sizeof(cmd->msg)); +} + +/** + * Handle mailbox interrupts + */ +void +bfa_ioc_mbox_isr(struct bfa_ioc_s *ioc) +{ + struct bfa_ioc_mbox_mod_s *mod = &ioc->mbox_mod; + struct bfi_mbmsg_s m; + int mc; + + bfa_ioc_msgget(ioc, &m); + + /** + * Treat IOC message class as special. + */ + mc = m.mh.msg_class; + if (mc == BFI_MC_IOC) { + bfa_ioc_isr(ioc, &m); + return; + } + + if ((mc > BFI_MC_MAX) || (mod->mbhdlr[mc].cbfn == NULL)) + return; + + mod->mbhdlr[mc].cbfn(mod->mbhdlr[mc].cbarg, &m); +} + +void +bfa_ioc_error_isr(struct bfa_ioc_s *ioc) +{ + bfa_fsm_send_event(ioc, IOC_E_HWERROR); +} + +#ifndef BFA_BIOS_BUILD + +/** + * return true if IOC is disabled + */ +bfa_boolean_t +bfa_ioc_is_disabled(struct bfa_ioc_s *ioc) +{ + return (bfa_fsm_cmp_state(ioc, bfa_ioc_sm_disabling) + || bfa_fsm_cmp_state(ioc, bfa_ioc_sm_disabled)); +} + +/** + * return true if IOC firmware is different. + */ +bfa_boolean_t +bfa_ioc_fw_mismatch(struct bfa_ioc_s *ioc) +{ + return (bfa_fsm_cmp_state(ioc, bfa_ioc_sm_reset) + || bfa_fsm_cmp_state(ioc, bfa_ioc_sm_fwcheck) + || bfa_fsm_cmp_state(ioc, bfa_ioc_sm_mismatch)); +} + +#define bfa_ioc_state_disabled(__sm) \ + (((__sm) == BFI_IOC_UNINIT) || \ + ((__sm) == BFI_IOC_INITING) || \ + ((__sm) == BFI_IOC_HWINIT) || \ + ((__sm) == BFI_IOC_DISABLED) || \ + ((__sm) == BFI_IOC_HBFAIL) || \ + ((__sm) == BFI_IOC_CFG_DISABLED)) + +/** + * Check if adapter is disabled -- both IOCs should be in a disabled + * state. + */ +bfa_boolean_t +bfa_ioc_adapter_is_disabled(struct bfa_ioc_s *ioc) +{ + u32 ioc_state; + bfa_os_addr_t rb = ioc->pcidev.pci_bar_kva; + + if (!bfa_fsm_cmp_state(ioc, bfa_ioc_sm_disabled)) + return BFA_FALSE; + + ioc_state = bfa_reg_read(rb + BFA_IOC0_STATE_REG); + if (!bfa_ioc_state_disabled(ioc_state)) + return BFA_FALSE; + + ioc_state = bfa_reg_read(rb + BFA_IOC1_STATE_REG); + if (!bfa_ioc_state_disabled(ioc_state)) + return BFA_FALSE; + + return BFA_TRUE; +} + +/** + * Add to IOC heartbeat failure notification queue. To be used by common + * modules such as + */ +void +bfa_ioc_hbfail_register(struct bfa_ioc_s *ioc, + struct bfa_ioc_hbfail_notify_s *notify) +{ + list_add_tail(¬ify->qe, &ioc->hb_notify_q); +} + +#define BFA_MFG_NAME "Brocade" +void +bfa_ioc_get_adapter_attr(struct bfa_ioc_s *ioc, + struct bfa_adapter_attr_s *ad_attr) +{ + struct bfi_ioc_attr_s *ioc_attr; + char model[BFA_ADAPTER_MODEL_NAME_LEN]; + + ioc_attr = ioc->attr; + bfa_os_memcpy((void *)&ad_attr->serial_num, + (void *)ioc_attr->brcd_serialnum, + BFA_ADAPTER_SERIAL_NUM_LEN); + + bfa_os_memcpy(&ad_attr->fw_ver, ioc_attr->fw_version, BFA_VERSION_LEN); + bfa_os_memcpy(&ad_attr->optrom_ver, ioc_attr->optrom_version, + BFA_VERSION_LEN); + bfa_os_memcpy(&ad_attr->manufacturer, BFA_MFG_NAME, + BFA_ADAPTER_MFG_NAME_LEN); + bfa_os_memcpy(&ad_attr->vpd, &ioc_attr->vpd, + sizeof(struct bfa_mfg_vpd_s)); + + ad_attr->nports = BFI_ADAPTER_GETP(NPORTS, ioc_attr->adapter_prop); + ad_attr->max_speed = BFI_ADAPTER_GETP(SPEED, ioc_attr->adapter_prop); + + /** + * model name + */ + if (BFI_ADAPTER_GETP(SPEED, ioc_attr->adapter_prop) == 10) { + strcpy(model, "BR-10?0"); + model[5] = '0' + ad_attr->nports; + } else { + strcpy(model, "Brocade-??5"); + model[8] = + '0' + BFI_ADAPTER_GETP(SPEED, ioc_attr->adapter_prop); + model[9] = '0' + ad_attr->nports; + } + + if (BFI_ADAPTER_IS_SPECIAL(ioc_attr->adapter_prop)) + ad_attr->prototype = 1; + else + ad_attr->prototype = 0; + + bfa_os_memcpy(&ad_attr->model, model, BFA_ADAPTER_MODEL_NAME_LEN); + bfa_os_memcpy(&ad_attr->model_descr, &ad_attr->model, + BFA_ADAPTER_MODEL_NAME_LEN); + + ad_attr->pwwn = bfa_ioc_get_pwwn(ioc); + ad_attr->mac = bfa_ioc_get_mac(ioc); + + ad_attr->pcie_gen = ioc_attr->pcie_gen; + ad_attr->pcie_lanes = ioc_attr->pcie_lanes; + ad_attr->pcie_lanes_orig = ioc_attr->pcie_lanes_orig; + ad_attr->asic_rev = ioc_attr->asic_rev; + ad_attr->hw_ver[0] = 'R'; + ad_attr->hw_ver[1] = 'e'; + ad_attr->hw_ver[2] = 'v'; + ad_attr->hw_ver[3] = '-'; + ad_attr->hw_ver[4] = ioc_attr->asic_rev; + ad_attr->hw_ver[5] = '\0'; + + ad_attr->cna_capable = ioc->cna; +} + +void +bfa_ioc_get_attr(struct bfa_ioc_s *ioc, struct bfa_ioc_attr_s *ioc_attr) +{ + bfa_os_memset((void *)ioc_attr, 0, sizeof(struct bfa_ioc_attr_s)); + + ioc_attr->state = bfa_sm_to_state(ioc_sm_table, ioc->fsm); + ioc_attr->port_id = ioc->port_id; + + if (!ioc->ctdev) + ioc_attr->ioc_type = BFA_IOC_TYPE_FC; + else if (ioc->ioc_mc == BFI_MC_IOCFC) + ioc_attr->ioc_type = BFA_IOC_TYPE_FCoE; + else if (ioc->ioc_mc == BFI_MC_LL) + ioc_attr->ioc_type = BFA_IOC_TYPE_LL; + + bfa_ioc_get_adapter_attr(ioc, &ioc_attr->adapter_attr); + + ioc_attr->pci_attr.device_id = ioc->pcidev.device_id; + ioc_attr->pci_attr.pcifn = ioc->pcidev.pci_func; + ioc_attr->pci_attr.chip_rev[0] = 'R'; + ioc_attr->pci_attr.chip_rev[1] = 'e'; + ioc_attr->pci_attr.chip_rev[2] = 'v'; + ioc_attr->pci_attr.chip_rev[3] = '-'; + ioc_attr->pci_attr.chip_rev[4] = ioc_attr->adapter_attr.asic_rev; + ioc_attr->pci_attr.chip_rev[5] = '\0'; +} + +/** + * hal_wwn_public + */ +wwn_t +bfa_ioc_get_pwwn(struct bfa_ioc_s *ioc) +{ + union { + wwn_t wwn; + u8 byte[sizeof(wwn_t)]; + } + w; + + w.wwn = ioc->attr->mfg_wwn; + + if (bfa_ioc_portid(ioc) == 1) + w.byte[7]++; + + return w.wwn; +} + +wwn_t +bfa_ioc_get_nwwn(struct bfa_ioc_s *ioc) +{ + union { + wwn_t wwn; + u8 byte[sizeof(wwn_t)]; + } + w; + + w.wwn = ioc->attr->mfg_wwn; + + if (bfa_ioc_portid(ioc) == 1) + w.byte[7]++; + + w.byte[0] = 0x20; + + return w.wwn; +} + +wwn_t +bfa_ioc_get_wwn_naa5(struct bfa_ioc_s *ioc, u16 inst) +{ + union { + wwn_t wwn; + u8 byte[sizeof(wwn_t)]; + } + w , w5; + + bfa_trc(ioc, inst); + + w.wwn = ioc->attr->mfg_wwn; + w5.byte[0] = 0x50 | w.byte[2] >> 4; + w5.byte[1] = w.byte[2] << 4 | w.byte[3] >> 4; + w5.byte[2] = w.byte[3] << 4 | w.byte[4] >> 4; + w5.byte[3] = w.byte[4] << 4 | w.byte[5] >> 4; + w5.byte[4] = w.byte[5] << 4 | w.byte[6] >> 4; + w5.byte[5] = w.byte[6] << 4 | w.byte[7] >> 4; + w5.byte[6] = w.byte[7] << 4 | (inst & 0x0f00) >> 8; + w5.byte[7] = (inst & 0xff); + + return w5.wwn; +} + +u64 +bfa_ioc_get_adid(struct bfa_ioc_s *ioc) +{ + return ioc->attr->mfg_wwn; +} + +mac_t +bfa_ioc_get_mac(struct bfa_ioc_s *ioc) +{ + mac_t mac; + + mac = ioc->attr->mfg_mac; + mac.mac[MAC_ADDRLEN - 1] += bfa_ioc_pcifn(ioc); + + return mac; +} + +void +bfa_ioc_set_fcmode(struct bfa_ioc_s *ioc) +{ + ioc->fcmode = BFA_TRUE; + ioc->port_id = bfa_ioc_pcifn(ioc); +} + +bfa_boolean_t +bfa_ioc_get_fcmode(struct bfa_ioc_s *ioc) +{ + return ioc->fcmode || (ioc->pcidev.device_id != BFA_PCI_DEVICE_ID_CT); +} + +/** + * Return true if interrupt should be claimed. + */ +bfa_boolean_t +bfa_ioc_intx_claim(struct bfa_ioc_s *ioc) +{ + u32 isr, msk; + + /** + * Always claim if not catapult. + */ + if (!ioc->ctdev) + return BFA_TRUE; + + /** + * FALSE if next device is claiming interrupt. + * TRUE if next device is not interrupting or not present. + */ + msk = bfa_reg_read(ioc->ioc_regs.shirq_msk_next); + isr = bfa_reg_read(ioc->ioc_regs.shirq_isr_next); + return !(isr & ~msk); +} + +/** + * Send AEN notification + */ +static void +bfa_ioc_aen_post(struct bfa_ioc_s *ioc, enum bfa_ioc_aen_event event) +{ + union bfa_aen_data_u aen_data; + struct bfa_log_mod_s *logmod = ioc->logm; + s32 inst_num = 0; + struct bfa_ioc_attr_s ioc_attr; + + switch (event) { + case BFA_IOC_AEN_HBGOOD: + bfa_log(logmod, BFA_AEN_IOC_HBGOOD, inst_num); + break; + case BFA_IOC_AEN_HBFAIL: + bfa_log(logmod, BFA_AEN_IOC_HBFAIL, inst_num); + break; + case BFA_IOC_AEN_ENABLE: + bfa_log(logmod, BFA_AEN_IOC_ENABLE, inst_num); + break; + case BFA_IOC_AEN_DISABLE: + bfa_log(logmod, BFA_AEN_IOC_DISABLE, inst_num); + break; + case BFA_IOC_AEN_FWMISMATCH: + bfa_log(logmod, BFA_AEN_IOC_FWMISMATCH, inst_num); + break; + default: + break; + } + + memset(&aen_data.ioc.pwwn, 0, sizeof(aen_data.ioc.pwwn)); + memset(&aen_data.ioc.mac, 0, sizeof(aen_data.ioc.mac)); + bfa_ioc_get_attr(ioc, &ioc_attr); + switch (ioc_attr.ioc_type) { + case BFA_IOC_TYPE_FC: + aen_data.ioc.pwwn = bfa_ioc_get_pwwn(ioc); + break; + case BFA_IOC_TYPE_FCoE: + aen_data.ioc.pwwn = bfa_ioc_get_pwwn(ioc); + aen_data.ioc.mac = bfa_ioc_get_mac(ioc); + break; + case BFA_IOC_TYPE_LL: + aen_data.ioc.mac = bfa_ioc_get_mac(ioc); + break; + default: + bfa_assert(ioc_attr.ioc_type == BFA_IOC_TYPE_FC); + break; + } + aen_data.ioc.ioc_type = ioc_attr.ioc_type; +} + +/** + * Retrieve saved firmware trace from a prior IOC failure. + */ +bfa_status_t +bfa_ioc_debug_fwsave(struct bfa_ioc_s *ioc, void *trcdata, int *trclen) +{ + int tlen; + + if (ioc->dbg_fwsave_len == 0) + return BFA_STATUS_ENOFSAVE; + + tlen = *trclen; + if (tlen > ioc->dbg_fwsave_len) + tlen = ioc->dbg_fwsave_len; + + bfa_os_memcpy(trcdata, ioc->dbg_fwsave, tlen); + *trclen = tlen; + return BFA_STATUS_OK; +} + +/** + * Retrieve saved firmware trace from a prior IOC failure. + */ +bfa_status_t +bfa_ioc_debug_fwtrc(struct bfa_ioc_s *ioc, void *trcdata, int *trclen) +{ + u32 pgnum; + u32 loff = BFA_DBG_FWTRC_OFF(bfa_ioc_portid(ioc)); + int i, tlen; + u32 *tbuf = trcdata, r32; + + bfa_trc(ioc, *trclen); + + pgnum = bfa_ioc_smem_pgnum(ioc, loff); + loff = bfa_ioc_smem_pgoff(ioc, loff); + bfa_reg_write(ioc->ioc_regs.host_page_num_fn, pgnum); + + tlen = *trclen; + if (tlen > BFA_DBG_FWTRC_LEN) + tlen = BFA_DBG_FWTRC_LEN; + tlen /= sizeof(u32); + + bfa_trc(ioc, tlen); + + for (i = 0; i < tlen; i++) { + r32 = bfa_mem_read(ioc->ioc_regs.smem_page_start, loff); + tbuf[i] = bfa_os_ntohl(r32); + loff += sizeof(u32); + + /** + * handle page offset wrap around + */ + loff = PSS_SMEM_PGOFF(loff); + if (loff == 0) { + pgnum++; + bfa_reg_write(ioc->ioc_regs.host_page_num_fn, pgnum); + } + } + bfa_reg_write(ioc->ioc_regs.host_page_num_fn, + bfa_ioc_smem_pgnum(ioc, 0)); + bfa_trc(ioc, pgnum); + + *trclen = tlen * sizeof(u32); + return BFA_STATUS_OK; +} + +/** + * Save firmware trace if configured. + */ +static void +bfa_ioc_debug_save(struct bfa_ioc_s *ioc) +{ + int tlen; + + if (ioc->dbg_fwsave_len) { + tlen = ioc->dbg_fwsave_len; + bfa_ioc_debug_fwtrc(ioc, ioc->dbg_fwsave, &tlen); + } +} + +/** + * Firmware failure detected. Start recovery actions. + */ +static void +bfa_ioc_recover(struct bfa_ioc_s *ioc) +{ + if (ioc->dbg_fwsave_once) { + ioc->dbg_fwsave_once = BFA_FALSE; + bfa_ioc_debug_save(ioc); + } + + bfa_ioc_stats(ioc, ioc_hbfails); + bfa_fsm_send_event(ioc, IOC_E_HBFAIL); +} + +#else + +static void +bfa_ioc_aen_post(struct bfa_ioc_s *ioc, enum bfa_ioc_aen_event event) +{ +} + +static void +bfa_ioc_recover(struct bfa_ioc_s *ioc) +{ + bfa_assert(0); +} + +#endif + + diff --git a/drivers/scsi/bfa/bfa_ioc.h b/drivers/scsi/bfa/bfa_ioc.h new file mode 100644 index 000000000000..58efd4b13143 --- /dev/null +++ b/drivers/scsi/bfa/bfa_ioc.h @@ -0,0 +1,259 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_IOC_H__ +#define __BFA_IOC_H__ + +#include <cs/bfa_sm.h> +#include <bfi/bfi.h> +#include <bfi/bfi_ioc.h> +#include <bfi/bfi_boot.h> +#include <bfa_timer.h> + +/** + * PCI device information required by IOC + */ +struct bfa_pcidev_s { + int pci_slot; + u8 pci_func; + u16 device_id; + bfa_os_addr_t pci_bar_kva; +}; + +/** + * Structure used to remember the DMA-able memory block's KVA and Physical + * Address + */ +struct bfa_dma_s { + void *kva; /*! Kernel virtual address */ + u64 pa; /*! Physical address */ +}; + +#define BFA_DMA_ALIGN_SZ 256 +#define BFA_ROUNDUP(_l, _s) (((_l) + ((_s) - 1)) & ~((_s) - 1)) + + + +#define bfa_dma_addr_set(dma_addr, pa) \ + __bfa_dma_addr_set(&dma_addr, (u64)pa) + +static inline void +__bfa_dma_addr_set(union bfi_addr_u *dma_addr, u64 pa) +{ + dma_addr->a32.addr_lo = (u32) pa; + dma_addr->a32.addr_hi = (u32) (bfa_os_u32(pa)); +} + + +#define bfa_dma_be_addr_set(dma_addr, pa) \ + __bfa_dma_be_addr_set(&dma_addr, (u64)pa) +static inline void +__bfa_dma_be_addr_set(union bfi_addr_u *dma_addr, u64 pa) +{ + dma_addr->a32.addr_lo = (u32) bfa_os_htonl(pa); + dma_addr->a32.addr_hi = (u32) bfa_os_htonl(bfa_os_u32(pa)); +} + +struct bfa_ioc_regs_s { + bfa_os_addr_t hfn_mbox_cmd; + bfa_os_addr_t hfn_mbox; + bfa_os_addr_t lpu_mbox_cmd; + bfa_os_addr_t lpu_mbox; + bfa_os_addr_t pss_ctl_reg; + bfa_os_addr_t app_pll_fast_ctl_reg; + bfa_os_addr_t app_pll_slow_ctl_reg; + bfa_os_addr_t ioc_sem_reg; + bfa_os_addr_t ioc_usage_sem_reg; + bfa_os_addr_t ioc_usage_reg; + bfa_os_addr_t host_page_num_fn; + bfa_os_addr_t heartbeat; + bfa_os_addr_t ioc_fwstate; + bfa_os_addr_t ll_halt; + bfa_os_addr_t shirq_isr_next; + bfa_os_addr_t shirq_msk_next; + bfa_os_addr_t smem_page_start; + u32 smem_pg0; +}; + +#define bfa_reg_read(_raddr) bfa_os_reg_read(_raddr) +#define bfa_reg_write(_raddr, _val) bfa_os_reg_write(_raddr, _val) +#define bfa_mem_read(_raddr, _off) bfa_os_mem_read(_raddr, _off) +#define bfa_mem_write(_raddr, _off, _val) \ + bfa_os_mem_write(_raddr, _off, _val) +/** + * IOC Mailbox structures + */ +struct bfa_mbox_cmd_s { + struct list_head qe; + u32 msg[BFI_IOC_MSGSZ]; +}; + +/** + * IOC mailbox module + */ +typedef void (*bfa_ioc_mbox_mcfunc_t)(void *cbarg, struct bfi_mbmsg_s *m); +struct bfa_ioc_mbox_mod_s { + struct list_head cmd_q; /* pending mbox queue */ + int nmclass; /* number of handlers */ + struct { + bfa_ioc_mbox_mcfunc_t cbfn; /* message handlers */ + void *cbarg; + } mbhdlr[BFI_MC_MAX]; +}; + +/** + * IOC callback function interfaces + */ +typedef void (*bfa_ioc_enable_cbfn_t)(void *bfa, enum bfa_status status); +typedef void (*bfa_ioc_disable_cbfn_t)(void *bfa); +typedef void (*bfa_ioc_hbfail_cbfn_t)(void *bfa); +typedef void (*bfa_ioc_reset_cbfn_t)(void *bfa); +struct bfa_ioc_cbfn_s { + bfa_ioc_enable_cbfn_t enable_cbfn; + bfa_ioc_disable_cbfn_t disable_cbfn; + bfa_ioc_hbfail_cbfn_t hbfail_cbfn; + bfa_ioc_reset_cbfn_t reset_cbfn; +}; + +/** + * Heartbeat failure notification queue element. + */ +struct bfa_ioc_hbfail_notify_s { + struct list_head qe; + bfa_ioc_hbfail_cbfn_t cbfn; + void *cbarg; +}; + +/** + * Initialize a heartbeat failure notification structure + */ +#define bfa_ioc_hbfail_init(__notify, __cbfn, __cbarg) do { \ + (__notify)->cbfn = (__cbfn); \ + (__notify)->cbarg = (__cbarg); \ +} while (0) + +struct bfa_ioc_s { + bfa_fsm_t fsm; + struct bfa_s *bfa; + struct bfa_pcidev_s pcidev; + struct bfa_timer_mod_s *timer_mod; + struct bfa_timer_s ioc_timer; + struct bfa_timer_s sem_timer; + u32 hb_count; + u32 hb_fail; + u32 retry_count; + struct list_head hb_notify_q; + void *dbg_fwsave; + int dbg_fwsave_len; + bfa_boolean_t dbg_fwsave_once; + enum bfi_mclass ioc_mc; + struct bfa_ioc_regs_s ioc_regs; + struct bfa_trc_mod_s *trcmod; + struct bfa_aen_s *aen; + struct bfa_log_mod_s *logm; + struct bfa_ioc_drv_stats_s stats; + bfa_boolean_t auto_recover; + bfa_boolean_t fcmode; + bfa_boolean_t ctdev; + bfa_boolean_t cna; + bfa_boolean_t pllinit; + u8 port_id; + + struct bfa_dma_s attr_dma; + struct bfi_ioc_attr_s *attr; + struct bfa_ioc_cbfn_s *cbfn; + struct bfa_ioc_mbox_mod_s mbox_mod; +}; + +#define bfa_ioc_pcifn(__ioc) (__ioc)->pcidev.pci_func +#define bfa_ioc_devid(__ioc) (__ioc)->pcidev.device_id +#define bfa_ioc_bar0(__ioc) (__ioc)->pcidev.pci_bar_kva +#define bfa_ioc_portid(__ioc) ((__ioc)->port_id) +#define bfa_ioc_fetch_stats(__ioc, __stats) \ + ((__stats)->drv_stats) = (__ioc)->stats +#define bfa_ioc_clr_stats(__ioc) \ + bfa_os_memset(&(__ioc)->stats, 0, sizeof((__ioc)->stats)) +#define bfa_ioc_maxfrsize(__ioc) (__ioc)->attr->maxfrsize +#define bfa_ioc_rx_bbcredit(__ioc) (__ioc)->attr->rx_bbcredit +#define bfa_ioc_speed_sup(__ioc) \ + BFI_ADAPTER_GETP(SPEED, (__ioc)->attr->adapter_prop) + +/** + * IOC mailbox interface + */ +void bfa_ioc_mbox_queue(struct bfa_ioc_s *ioc, struct bfa_mbox_cmd_s *cmd); +void bfa_ioc_mbox_register(struct bfa_ioc_s *ioc, + bfa_ioc_mbox_mcfunc_t *mcfuncs); +void bfa_ioc_mbox_isr(struct bfa_ioc_s *ioc); +void bfa_ioc_mbox_send(struct bfa_ioc_s *ioc, void *ioc_msg, int len); +void bfa_ioc_msgget(struct bfa_ioc_s *ioc, void *mbmsg); +void bfa_ioc_mbox_regisr(struct bfa_ioc_s *ioc, enum bfi_mclass mc, + bfa_ioc_mbox_mcfunc_t cbfn, void *cbarg); + +/** + * IOC interfaces + */ +void bfa_ioc_attach(struct bfa_ioc_s *ioc, void *bfa, + struct bfa_ioc_cbfn_s *cbfn, struct bfa_timer_mod_s *timer_mod, + struct bfa_trc_mod_s *trcmod, + struct bfa_aen_s *aen, struct bfa_log_mod_s *logm); +void bfa_ioc_detach(struct bfa_ioc_s *ioc); +void bfa_ioc_pci_init(struct bfa_ioc_s *ioc, struct bfa_pcidev_s *pcidev, + enum bfi_mclass mc); +u32 bfa_ioc_meminfo(void); +void bfa_ioc_mem_claim(struct bfa_ioc_s *ioc, u8 *dm_kva, u64 dm_pa); +void bfa_ioc_enable(struct bfa_ioc_s *ioc); +void bfa_ioc_disable(struct bfa_ioc_s *ioc); +bfa_boolean_t bfa_ioc_intx_claim(struct bfa_ioc_s *ioc); + +void bfa_ioc_boot(struct bfa_ioc_s *ioc, u32 boot_type, u32 boot_param); +void bfa_ioc_isr(struct bfa_ioc_s *ioc, struct bfi_mbmsg_s *msg); +void bfa_ioc_error_isr(struct bfa_ioc_s *ioc); +void bfa_ioc_isr_mode_set(struct bfa_ioc_s *ioc, bfa_boolean_t intx); +bfa_status_t bfa_ioc_pll_init(struct bfa_ioc_s *ioc); +bfa_boolean_t bfa_ioc_is_operational(struct bfa_ioc_s *ioc); +bfa_boolean_t bfa_ioc_is_disabled(struct bfa_ioc_s *ioc); +bfa_boolean_t bfa_ioc_fw_mismatch(struct bfa_ioc_s *ioc); +bfa_boolean_t bfa_ioc_adapter_is_disabled(struct bfa_ioc_s *ioc); +void bfa_ioc_cfg_complete(struct bfa_ioc_s *ioc); +void bfa_ioc_get_attr(struct bfa_ioc_s *ioc, struct bfa_ioc_attr_s *ioc_attr); +void bfa_ioc_get_adapter_attr(struct bfa_ioc_s *ioc, + struct bfa_adapter_attr_s *ad_attr); +int bfa_ioc_debug_trcsz(bfa_boolean_t auto_recover); +void bfa_ioc_debug_memclaim(struct bfa_ioc_s *ioc, void *dbg_fwsave); +bfa_status_t bfa_ioc_debug_fwsave(struct bfa_ioc_s *ioc, void *trcdata, + int *trclen); +bfa_status_t bfa_ioc_debug_fwtrc(struct bfa_ioc_s *ioc, void *trcdata, + int *trclen); +u32 bfa_ioc_smem_pgnum(struct bfa_ioc_s *ioc, u32 fmaddr); +u32 bfa_ioc_smem_pgoff(struct bfa_ioc_s *ioc, u32 fmaddr); +void bfa_ioc_set_fcmode(struct bfa_ioc_s *ioc); +bfa_boolean_t bfa_ioc_get_fcmode(struct bfa_ioc_s *ioc); +void bfa_ioc_hbfail_register(struct bfa_ioc_s *ioc, + struct bfa_ioc_hbfail_notify_s *notify); + +/* + * bfa mfg wwn API functions + */ +wwn_t bfa_ioc_get_pwwn(struct bfa_ioc_s *ioc); +wwn_t bfa_ioc_get_nwwn(struct bfa_ioc_s *ioc); +wwn_t bfa_ioc_get_wwn_naa5(struct bfa_ioc_s *ioc, u16 inst); +mac_t bfa_ioc_get_mac(struct bfa_ioc_s *ioc); +u64 bfa_ioc_get_adid(struct bfa_ioc_s *ioc); + +#endif /* __BFA_IOC_H__ */ + diff --git a/drivers/scsi/bfa/bfa_iocfc.c b/drivers/scsi/bfa/bfa_iocfc.c new file mode 100644 index 000000000000..12350b022d63 --- /dev/null +++ b/drivers/scsi/bfa/bfa_iocfc.c @@ -0,0 +1,872 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <cs/bfa_debug.h> +#include <bfa_priv.h> +#include <log/bfa_log_hal.h> +#include <bfi/bfi_boot.h> +#include <bfi/bfi_cbreg.h> +#include <aen/bfa_aen_ioc.h> +#include <defs/bfa_defs_iocfc.h> +#include <defs/bfa_defs_pci.h> +#include "bfa_callback_priv.h" +#include "bfad_drv.h" + +BFA_TRC_FILE(HAL, IOCFC); + +/** + * IOC local definitions + */ +#define BFA_IOCFC_TOV 5000 /* msecs */ + +enum { + BFA_IOCFC_ACT_NONE = 0, + BFA_IOCFC_ACT_INIT = 1, + BFA_IOCFC_ACT_STOP = 2, + BFA_IOCFC_ACT_DISABLE = 3, +}; + +/* + * forward declarations + */ +static void bfa_iocfc_enable_cbfn(void *bfa_arg, enum bfa_status status); +static void bfa_iocfc_disable_cbfn(void *bfa_arg); +static void bfa_iocfc_hbfail_cbfn(void *bfa_arg); +static void bfa_iocfc_reset_cbfn(void *bfa_arg); +static void bfa_iocfc_stats_clear(void *bfa_arg); +static void bfa_iocfc_stats_swap(struct bfa_fw_stats_s *d, + struct bfa_fw_stats_s *s); +static void bfa_iocfc_stats_clr_cb(void *bfa_arg, bfa_boolean_t complete); +static void bfa_iocfc_stats_clr_timeout(void *bfa_arg); +static void bfa_iocfc_stats_cb(void *bfa_arg, bfa_boolean_t complete); +static void bfa_iocfc_stats_timeout(void *bfa_arg); + +static struct bfa_ioc_cbfn_s bfa_iocfc_cbfn; + +/** + * bfa_ioc_pvt BFA IOC private functions + */ + +static void +bfa_iocfc_cqs_sz(struct bfa_iocfc_cfg_s *cfg, u32 *dm_len) +{ + int i, per_reqq_sz, per_rspq_sz; + + per_reqq_sz = BFA_ROUNDUP((cfg->drvcfg.num_reqq_elems * BFI_LMSG_SZ), + BFA_DMA_ALIGN_SZ); + per_rspq_sz = BFA_ROUNDUP((cfg->drvcfg.num_rspq_elems * BFI_LMSG_SZ), + BFA_DMA_ALIGN_SZ); + + /* + * Calculate CQ size + */ + for (i = 0; i < cfg->fwcfg.num_cqs; i++) { + *dm_len = *dm_len + per_reqq_sz; + *dm_len = *dm_len + per_rspq_sz; + } + + /* + * Calculate Shadow CI/PI size + */ + for (i = 0; i < cfg->fwcfg.num_cqs; i++) + *dm_len += (2 * BFA_CACHELINE_SZ); +} + +static void +bfa_iocfc_fw_cfg_sz(struct bfa_iocfc_cfg_s *cfg, u32 *dm_len) +{ + *dm_len += + BFA_ROUNDUP(sizeof(struct bfi_iocfc_cfg_s), BFA_CACHELINE_SZ); + *dm_len += + BFA_ROUNDUP(sizeof(struct bfi_iocfc_cfgrsp_s), + BFA_CACHELINE_SZ); + *dm_len += BFA_ROUNDUP(sizeof(struct bfa_fw_stats_s), BFA_CACHELINE_SZ); +} + +/** + * Use the Mailbox interface to send BFI_IOCFC_H2I_CFG_REQ + */ +static void +bfa_iocfc_send_cfg(void *bfa_arg) +{ + struct bfa_s *bfa = bfa_arg; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + struct bfi_iocfc_cfg_req_s cfg_req; + struct bfi_iocfc_cfg_s *cfg_info = iocfc->cfginfo; + struct bfa_iocfc_cfg_s *cfg = &iocfc->cfg; + int i; + + bfa_assert(cfg->fwcfg.num_cqs <= BFI_IOC_MAX_CQS); + bfa_trc(bfa, cfg->fwcfg.num_cqs); + + iocfc->cfgdone = BFA_FALSE; + bfa_iocfc_reset_queues(bfa); + + /** + * initialize IOC configuration info + */ + cfg_info->endian_sig = BFI_IOC_ENDIAN_SIG; + cfg_info->num_cqs = cfg->fwcfg.num_cqs; + + bfa_dma_be_addr_set(cfg_info->cfgrsp_addr, iocfc->cfgrsp_dma.pa); + bfa_dma_be_addr_set(cfg_info->stats_addr, iocfc->stats_pa); + + /** + * dma map REQ and RSP circular queues and shadow pointers + */ + for (i = 0; i < cfg->fwcfg.num_cqs; i++) { + bfa_dma_be_addr_set(cfg_info->req_cq_ba[i], + iocfc->req_cq_ba[i].pa); + bfa_dma_be_addr_set(cfg_info->req_shadow_ci[i], + iocfc->req_cq_shadow_ci[i].pa); + cfg_info->req_cq_elems[i] = + bfa_os_htons(cfg->drvcfg.num_reqq_elems); + + bfa_dma_be_addr_set(cfg_info->rsp_cq_ba[i], + iocfc->rsp_cq_ba[i].pa); + bfa_dma_be_addr_set(cfg_info->rsp_shadow_pi[i], + iocfc->rsp_cq_shadow_pi[i].pa); + cfg_info->rsp_cq_elems[i] = + bfa_os_htons(cfg->drvcfg.num_rspq_elems); + } + + /** + * dma map IOC configuration itself + */ + bfi_h2i_set(cfg_req.mh, BFI_MC_IOCFC, BFI_IOCFC_H2I_CFG_REQ, + bfa_lpuid(bfa)); + bfa_dma_be_addr_set(cfg_req.ioc_cfg_dma_addr, iocfc->cfg_info.pa); + + bfa_ioc_mbox_send(&bfa->ioc, &cfg_req, + sizeof(struct bfi_iocfc_cfg_req_s)); +} + +static void +bfa_iocfc_init_mem(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_pcidev_s *pcidev) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + bfa->bfad = bfad; + iocfc->bfa = bfa; + iocfc->action = BFA_IOCFC_ACT_NONE; + + bfa_os_assign(iocfc->cfg, *cfg); + + /** + * Initialize chip specific handlers. + */ + if (bfa_ioc_devid(&bfa->ioc) == BFA_PCI_DEVICE_ID_CT) { + iocfc->hwif.hw_reginit = bfa_hwct_reginit; + iocfc->hwif.hw_rspq_ack = bfa_hwct_rspq_ack; + iocfc->hwif.hw_msix_init = bfa_hwct_msix_init; + iocfc->hwif.hw_msix_install = bfa_hwct_msix_install; + iocfc->hwif.hw_msix_uninstall = bfa_hwct_msix_uninstall; + iocfc->hwif.hw_isr_mode_set = bfa_hwct_isr_mode_set; + iocfc->hwif.hw_msix_getvecs = bfa_hwct_msix_getvecs; + } else { + iocfc->hwif.hw_reginit = bfa_hwcb_reginit; + iocfc->hwif.hw_rspq_ack = bfa_hwcb_rspq_ack; + iocfc->hwif.hw_msix_init = bfa_hwcb_msix_init; + iocfc->hwif.hw_msix_install = bfa_hwcb_msix_install; + iocfc->hwif.hw_msix_uninstall = bfa_hwcb_msix_uninstall; + iocfc->hwif.hw_isr_mode_set = bfa_hwcb_isr_mode_set; + iocfc->hwif.hw_msix_getvecs = bfa_hwcb_msix_getvecs; + } + + iocfc->hwif.hw_reginit(bfa); + bfa->msix.nvecs = 0; +} + +static void +bfa_iocfc_mem_claim(struct bfa_s *bfa, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo) +{ + u8 *dm_kva; + u64 dm_pa; + int i, per_reqq_sz, per_rspq_sz; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + int dbgsz; + + dm_kva = bfa_meminfo_dma_virt(meminfo); + dm_pa = bfa_meminfo_dma_phys(meminfo); + + /* + * First allocate dma memory for IOC. + */ + bfa_ioc_mem_claim(&bfa->ioc, dm_kva, dm_pa); + dm_kva += bfa_ioc_meminfo(); + dm_pa += bfa_ioc_meminfo(); + + /* + * Claim DMA-able memory for the request/response queues and for shadow + * ci/pi registers + */ + per_reqq_sz = BFA_ROUNDUP((cfg->drvcfg.num_reqq_elems * BFI_LMSG_SZ), + BFA_DMA_ALIGN_SZ); + per_rspq_sz = BFA_ROUNDUP((cfg->drvcfg.num_rspq_elems * BFI_LMSG_SZ), + BFA_DMA_ALIGN_SZ); + + for (i = 0; i < cfg->fwcfg.num_cqs; i++) { + iocfc->req_cq_ba[i].kva = dm_kva; + iocfc->req_cq_ba[i].pa = dm_pa; + bfa_os_memset(dm_kva, 0, per_reqq_sz); + dm_kva += per_reqq_sz; + dm_pa += per_reqq_sz; + + iocfc->rsp_cq_ba[i].kva = dm_kva; + iocfc->rsp_cq_ba[i].pa = dm_pa; + bfa_os_memset(dm_kva, 0, per_rspq_sz); + dm_kva += per_rspq_sz; + dm_pa += per_rspq_sz; + } + + for (i = 0; i < cfg->fwcfg.num_cqs; i++) { + iocfc->req_cq_shadow_ci[i].kva = dm_kva; + iocfc->req_cq_shadow_ci[i].pa = dm_pa; + dm_kva += BFA_CACHELINE_SZ; + dm_pa += BFA_CACHELINE_SZ; + + iocfc->rsp_cq_shadow_pi[i].kva = dm_kva; + iocfc->rsp_cq_shadow_pi[i].pa = dm_pa; + dm_kva += BFA_CACHELINE_SZ; + dm_pa += BFA_CACHELINE_SZ; + } + + /* + * Claim DMA-able memory for the config info page + */ + bfa->iocfc.cfg_info.kva = dm_kva; + bfa->iocfc.cfg_info.pa = dm_pa; + bfa->iocfc.cfginfo = (struct bfi_iocfc_cfg_s *) dm_kva; + dm_kva += BFA_ROUNDUP(sizeof(struct bfi_iocfc_cfg_s), BFA_CACHELINE_SZ); + dm_pa += BFA_ROUNDUP(sizeof(struct bfi_iocfc_cfg_s), BFA_CACHELINE_SZ); + + /* + * Claim DMA-able memory for the config response + */ + bfa->iocfc.cfgrsp_dma.kva = dm_kva; + bfa->iocfc.cfgrsp_dma.pa = dm_pa; + bfa->iocfc.cfgrsp = (struct bfi_iocfc_cfgrsp_s *) dm_kva; + + dm_kva += + BFA_ROUNDUP(sizeof(struct bfi_iocfc_cfgrsp_s), + BFA_CACHELINE_SZ); + dm_pa += BFA_ROUNDUP(sizeof(struct bfi_iocfc_cfgrsp_s), + BFA_CACHELINE_SZ); + + /* + * Claim DMA-able memory for iocfc stats + */ + bfa->iocfc.stats_kva = dm_kva; + bfa->iocfc.stats_pa = dm_pa; + bfa->iocfc.fw_stats = (struct bfa_fw_stats_s *) dm_kva; + dm_kva += BFA_ROUNDUP(sizeof(struct bfa_fw_stats_s), BFA_CACHELINE_SZ); + dm_pa += BFA_ROUNDUP(sizeof(struct bfa_fw_stats_s), BFA_CACHELINE_SZ); + + bfa_meminfo_dma_virt(meminfo) = dm_kva; + bfa_meminfo_dma_phys(meminfo) = dm_pa; + + dbgsz = bfa_ioc_debug_trcsz(bfa_auto_recover); + if (dbgsz > 0) { + bfa_ioc_debug_memclaim(&bfa->ioc, bfa_meminfo_kva(meminfo)); + bfa_meminfo_kva(meminfo) += dbgsz; + } +} + +/** + * BFA submodules initialization completion notification. + */ +static void +bfa_iocfc_initdone_submod(struct bfa_s *bfa) +{ + int i; + + for (i = 0; hal_mods[i]; i++) + hal_mods[i]->initdone(bfa); +} + +/** + * Start BFA submodules. + */ +static void +bfa_iocfc_start_submod(struct bfa_s *bfa) +{ + int i; + + bfa->rme_process = BFA_TRUE; + + for (i = 0; hal_mods[i]; i++) + hal_mods[i]->start(bfa); +} + +/** + * Disable BFA submodules. + */ +static void +bfa_iocfc_disable_submod(struct bfa_s *bfa) +{ + int i; + + for (i = 0; hal_mods[i]; i++) + hal_mods[i]->iocdisable(bfa); +} + +static void +bfa_iocfc_init_cb(void *bfa_arg, bfa_boolean_t complete) +{ + struct bfa_s *bfa = bfa_arg; + + if (complete) { + if (bfa->iocfc.cfgdone) + bfa_cb_init(bfa->bfad, BFA_STATUS_OK); + else + bfa_cb_init(bfa->bfad, BFA_STATUS_FAILED); + } else + bfa->iocfc.action = BFA_IOCFC_ACT_NONE; +} + +static void +bfa_iocfc_stop_cb(void *bfa_arg, bfa_boolean_t compl) +{ + struct bfa_s *bfa = bfa_arg; + struct bfad_s *bfad = bfa->bfad; + + if (compl) + complete(&bfad->comp); + + else + bfa->iocfc.action = BFA_IOCFC_ACT_NONE; +} + +static void +bfa_iocfc_disable_cb(void *bfa_arg, bfa_boolean_t compl) +{ + struct bfa_s *bfa = bfa_arg; + struct bfad_s *bfad = bfa->bfad; + + if (compl) + complete(&bfad->disable_comp); +} + +/** + * Update BFA configuration from firmware configuration. + */ +static void +bfa_iocfc_cfgrsp(struct bfa_s *bfa) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + struct bfi_iocfc_cfgrsp_s *cfgrsp = iocfc->cfgrsp; + struct bfa_iocfc_fwcfg_s *fwcfg = &cfgrsp->fwcfg; + struct bfi_iocfc_cfg_s *cfginfo = iocfc->cfginfo; + + fwcfg->num_cqs = fwcfg->num_cqs; + fwcfg->num_ioim_reqs = bfa_os_ntohs(fwcfg->num_ioim_reqs); + fwcfg->num_tskim_reqs = bfa_os_ntohs(fwcfg->num_tskim_reqs); + fwcfg->num_fcxp_reqs = bfa_os_ntohs(fwcfg->num_fcxp_reqs); + fwcfg->num_uf_bufs = bfa_os_ntohs(fwcfg->num_uf_bufs); + fwcfg->num_rports = bfa_os_ntohs(fwcfg->num_rports); + + cfginfo->intr_attr.coalesce = cfgrsp->intr_attr.coalesce; + cfginfo->intr_attr.delay = bfa_os_ntohs(cfgrsp->intr_attr.delay); + cfginfo->intr_attr.latency = bfa_os_ntohs(cfgrsp->intr_attr.latency); + + iocfc->cfgdone = BFA_TRUE; + + /** + * Configuration is complete - initialize/start submodules + */ + if (iocfc->action == BFA_IOCFC_ACT_INIT) + bfa_cb_queue(bfa, &iocfc->init_hcb_qe, bfa_iocfc_init_cb, bfa); + else + bfa_iocfc_start_submod(bfa); +} + +static void +bfa_iocfc_stats_clear(void *bfa_arg) +{ + struct bfa_s *bfa = bfa_arg; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + struct bfi_iocfc_stats_req_s stats_req; + + bfa_timer_start(bfa, &iocfc->stats_timer, + bfa_iocfc_stats_clr_timeout, bfa, + BFA_IOCFC_TOV); + + bfi_h2i_set(stats_req.mh, BFI_MC_IOCFC, BFI_IOCFC_H2I_CLEAR_STATS_REQ, + bfa_lpuid(bfa)); + bfa_ioc_mbox_send(&bfa->ioc, &stats_req, + sizeof(struct bfi_iocfc_stats_req_s)); +} + +static void +bfa_iocfc_stats_swap(struct bfa_fw_stats_s *d, struct bfa_fw_stats_s *s) +{ + u32 *dip = (u32 *) d; + u32 *sip = (u32 *) s; + int i; + + for (i = 0; i < (sizeof(struct bfa_fw_stats_s) / sizeof(u32)); i++) + dip[i] = bfa_os_ntohl(sip[i]); +} + +static void +bfa_iocfc_stats_clr_cb(void *bfa_arg, bfa_boolean_t complete) +{ + struct bfa_s *bfa = bfa_arg; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + if (complete) { + bfa_ioc_clr_stats(&bfa->ioc); + iocfc->stats_cbfn(iocfc->stats_cbarg, iocfc->stats_status); + } else { + iocfc->stats_busy = BFA_FALSE; + iocfc->stats_status = BFA_STATUS_OK; + } +} + +static void +bfa_iocfc_stats_clr_timeout(void *bfa_arg) +{ + struct bfa_s *bfa = bfa_arg; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + bfa_trc(bfa, 0); + + iocfc->stats_status = BFA_STATUS_ETIMER; + bfa_cb_queue(bfa, &iocfc->stats_hcb_qe, bfa_iocfc_stats_clr_cb, bfa); +} + +static void +bfa_iocfc_stats_cb(void *bfa_arg, bfa_boolean_t complete) +{ + struct bfa_s *bfa = bfa_arg; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + if (complete) { + if (iocfc->stats_status == BFA_STATUS_OK) { + bfa_os_memset(iocfc->stats_ret, 0, + sizeof(*iocfc->stats_ret)); + bfa_iocfc_stats_swap(&iocfc->stats_ret->fw_stats, + iocfc->fw_stats); + } + iocfc->stats_cbfn(iocfc->stats_cbarg, iocfc->stats_status); + } else { + iocfc->stats_busy = BFA_FALSE; + iocfc->stats_status = BFA_STATUS_OK; + } +} + +static void +bfa_iocfc_stats_timeout(void *bfa_arg) +{ + struct bfa_s *bfa = bfa_arg; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + bfa_trc(bfa, 0); + + iocfc->stats_status = BFA_STATUS_ETIMER; + bfa_cb_queue(bfa, &iocfc->stats_hcb_qe, bfa_iocfc_stats_cb, bfa); +} + +static void +bfa_iocfc_stats_query(struct bfa_s *bfa) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + struct bfi_iocfc_stats_req_s stats_req; + + bfa_timer_start(bfa, &iocfc->stats_timer, + bfa_iocfc_stats_timeout, bfa, BFA_IOCFC_TOV); + + bfi_h2i_set(stats_req.mh, BFI_MC_IOCFC, BFI_IOCFC_H2I_GET_STATS_REQ, + bfa_lpuid(bfa)); + bfa_ioc_mbox_send(&bfa->ioc, &stats_req, + sizeof(struct bfi_iocfc_stats_req_s)); +} + +void +bfa_iocfc_reset_queues(struct bfa_s *bfa) +{ + int q; + + for (q = 0; q < BFI_IOC_MAX_CQS; q++) { + bfa_reqq_ci(bfa, q) = 0; + bfa_reqq_pi(bfa, q) = 0; + bfa_rspq_ci(bfa, q) = 0; + bfa_rspq_pi(bfa, q) = 0; + } +} + +/** + * IOC enable request is complete + */ +static void +bfa_iocfc_enable_cbfn(void *bfa_arg, enum bfa_status status) +{ + struct bfa_s *bfa = bfa_arg; + + if (status != BFA_STATUS_OK) { + bfa_isr_disable(bfa); + if (bfa->iocfc.action == BFA_IOCFC_ACT_INIT) + bfa_cb_queue(bfa, &bfa->iocfc.init_hcb_qe, + bfa_iocfc_init_cb, bfa); + return; + } + + bfa_iocfc_initdone_submod(bfa); + bfa_iocfc_send_cfg(bfa); +} + +/** + * IOC disable request is complete + */ +static void +bfa_iocfc_disable_cbfn(void *bfa_arg) +{ + struct bfa_s *bfa = bfa_arg; + + bfa_isr_disable(bfa); + bfa_iocfc_disable_submod(bfa); + + if (bfa->iocfc.action == BFA_IOCFC_ACT_STOP) + bfa_cb_queue(bfa, &bfa->iocfc.stop_hcb_qe, bfa_iocfc_stop_cb, + bfa); + else { + bfa_assert(bfa->iocfc.action == BFA_IOCFC_ACT_DISABLE); + bfa_cb_queue(bfa, &bfa->iocfc.dis_hcb_qe, bfa_iocfc_disable_cb, + bfa); + } +} + +/** + * Notify sub-modules of hardware failure. + */ +static void +bfa_iocfc_hbfail_cbfn(void *bfa_arg) +{ + struct bfa_s *bfa = bfa_arg; + + bfa->rme_process = BFA_FALSE; + + bfa_isr_disable(bfa); + bfa_iocfc_disable_submod(bfa); + + if (bfa->iocfc.action == BFA_IOCFC_ACT_INIT) + bfa_cb_queue(bfa, &bfa->iocfc.init_hcb_qe, bfa_iocfc_init_cb, + bfa); +} + +/** + * Actions on chip-reset completion. + */ +static void +bfa_iocfc_reset_cbfn(void *bfa_arg) +{ + struct bfa_s *bfa = bfa_arg; + + bfa_iocfc_reset_queues(bfa); + bfa_isr_enable(bfa); +} + + + +/** + * bfa_ioc_public + */ + +/** + * Query IOC memory requirement information. + */ +void +bfa_iocfc_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len) +{ + /* dma memory for IOC */ + *dm_len += bfa_ioc_meminfo(); + + bfa_iocfc_fw_cfg_sz(cfg, dm_len); + bfa_iocfc_cqs_sz(cfg, dm_len); + *km_len += bfa_ioc_debug_trcsz(bfa_auto_recover); +} + +/** + * Query IOC memory requirement information. + */ +void +bfa_iocfc_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + int i; + + bfa_iocfc_cbfn.enable_cbfn = bfa_iocfc_enable_cbfn; + bfa_iocfc_cbfn.disable_cbfn = bfa_iocfc_disable_cbfn; + bfa_iocfc_cbfn.hbfail_cbfn = bfa_iocfc_hbfail_cbfn; + bfa_iocfc_cbfn.reset_cbfn = bfa_iocfc_reset_cbfn; + + bfa_ioc_attach(&bfa->ioc, bfa, &bfa_iocfc_cbfn, &bfa->timer_mod, + bfa->trcmod, bfa->aen, bfa->logm); + bfa_ioc_pci_init(&bfa->ioc, pcidev, BFI_MC_IOCFC); + bfa_ioc_mbox_register(&bfa->ioc, bfa_mbox_isrs); + + /** + * Choose FC (ssid: 0x1C) v/s FCoE (ssid: 0x14) mode. + */ + if (0) + bfa_ioc_set_fcmode(&bfa->ioc); + + bfa_iocfc_init_mem(bfa, bfad, cfg, pcidev); + bfa_iocfc_mem_claim(bfa, cfg, meminfo); + bfa_timer_init(&bfa->timer_mod); + + INIT_LIST_HEAD(&bfa->comp_q); + for (i = 0; i < BFI_IOC_MAX_CQS; i++) + INIT_LIST_HEAD(&bfa->reqq_waitq[i]); +} + +/** + * Query IOC memory requirement information. + */ +void +bfa_iocfc_detach(struct bfa_s *bfa) +{ + bfa_ioc_detach(&bfa->ioc); +} + +/** + * Query IOC memory requirement information. + */ +void +bfa_iocfc_init(struct bfa_s *bfa) +{ + bfa->iocfc.action = BFA_IOCFC_ACT_INIT; + bfa_ioc_enable(&bfa->ioc); + bfa_msix_install(bfa); +} + +/** + * IOC start called from bfa_start(). Called to start IOC operations + * at driver instantiation for this instance. + */ +void +bfa_iocfc_start(struct bfa_s *bfa) +{ + if (bfa->iocfc.cfgdone) + bfa_iocfc_start_submod(bfa); +} + +/** + * IOC stop called from bfa_stop(). Called only when driver is unloaded + * for this instance. + */ +void +bfa_iocfc_stop(struct bfa_s *bfa) +{ + bfa->iocfc.action = BFA_IOCFC_ACT_STOP; + + bfa->rme_process = BFA_FALSE; + bfa_ioc_disable(&bfa->ioc); +} + +void +bfa_iocfc_isr(void *bfaarg, struct bfi_mbmsg_s *m) +{ + struct bfa_s *bfa = bfaarg; + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + union bfi_iocfc_i2h_msg_u *msg; + + msg = (union bfi_iocfc_i2h_msg_u *) m; + bfa_trc(bfa, msg->mh.msg_id); + + switch (msg->mh.msg_id) { + case BFI_IOCFC_I2H_CFG_REPLY: + iocfc->cfg_reply = &msg->cfg_reply; + bfa_iocfc_cfgrsp(bfa); + break; + + case BFI_IOCFC_I2H_GET_STATS_RSP: + if (iocfc->stats_busy == BFA_FALSE + || iocfc->stats_status == BFA_STATUS_ETIMER) + break; + + bfa_timer_stop(&iocfc->stats_timer); + iocfc->stats_status = BFA_STATUS_OK; + bfa_cb_queue(bfa, &iocfc->stats_hcb_qe, bfa_iocfc_stats_cb, + bfa); + break; + case BFI_IOCFC_I2H_CLEAR_STATS_RSP: + /* + * check for timer pop before processing the rsp + */ + if (iocfc->stats_busy == BFA_FALSE + || iocfc->stats_status == BFA_STATUS_ETIMER) + break; + + bfa_timer_stop(&iocfc->stats_timer); + iocfc->stats_status = BFA_STATUS_OK; + bfa_cb_queue(bfa, &iocfc->stats_hcb_qe, + bfa_iocfc_stats_clr_cb, bfa); + break; + case BFI_IOCFC_I2H_UPDATEQ_RSP: + iocfc->updateq_cbfn(iocfc->updateq_cbarg, BFA_STATUS_OK); + break; + default: + bfa_assert(0); + } +} + +#ifndef BFA_BIOS_BUILD +void +bfa_adapter_get_attr(struct bfa_s *bfa, struct bfa_adapter_attr_s *ad_attr) +{ + bfa_ioc_get_adapter_attr(&bfa->ioc, ad_attr); +} + +u64 +bfa_adapter_get_id(struct bfa_s *bfa) +{ + return bfa_ioc_get_adid(&bfa->ioc); +} + +void +bfa_iocfc_get_attr(struct bfa_s *bfa, struct bfa_iocfc_attr_s *attr) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + attr->intr_attr = iocfc->cfginfo->intr_attr; + attr->config = iocfc->cfg; +} + +bfa_status_t +bfa_iocfc_israttr_set(struct bfa_s *bfa, struct bfa_iocfc_intr_attr_s *attr) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + struct bfi_iocfc_set_intr_req_s *m; + + iocfc->cfginfo->intr_attr = *attr; + if (!bfa_iocfc_is_operational(bfa)) + return BFA_STATUS_OK; + + m = bfa_reqq_next(bfa, BFA_REQQ_IOC); + if (!m) + return BFA_STATUS_DEVBUSY; + + bfi_h2i_set(m->mh, BFI_MC_IOCFC, BFI_IOCFC_H2I_SET_INTR_REQ, + bfa_lpuid(bfa)); + m->coalesce = attr->coalesce; + m->delay = bfa_os_htons(attr->delay); + m->latency = bfa_os_htons(attr->latency); + + bfa_trc(bfa, attr->delay); + bfa_trc(bfa, attr->latency); + + bfa_reqq_produce(bfa, BFA_REQQ_IOC); + return BFA_STATUS_OK; +} + +void +bfa_iocfc_set_snsbase(struct bfa_s *bfa, u64 snsbase_pa) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + iocfc->cfginfo->sense_buf_len = (BFI_IOIM_SNSLEN - 1); + bfa_dma_be_addr_set(iocfc->cfginfo->ioim_snsbase, snsbase_pa); +} + +bfa_status_t +bfa_iocfc_get_stats(struct bfa_s *bfa, struct bfa_iocfc_stats_s *stats, + bfa_cb_ioc_t cbfn, void *cbarg) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + if (iocfc->stats_busy) { + bfa_trc(bfa, iocfc->stats_busy); + return (BFA_STATUS_DEVBUSY); + } + + iocfc->stats_busy = BFA_TRUE; + iocfc->stats_ret = stats; + iocfc->stats_cbfn = cbfn; + iocfc->stats_cbarg = cbarg; + + bfa_iocfc_stats_query(bfa); + + return (BFA_STATUS_OK); +} + +bfa_status_t +bfa_iocfc_clear_stats(struct bfa_s *bfa, bfa_cb_ioc_t cbfn, void *cbarg) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + + if (iocfc->stats_busy) { + bfa_trc(bfa, iocfc->stats_busy); + return (BFA_STATUS_DEVBUSY); + } + + iocfc->stats_busy = BFA_TRUE; + iocfc->stats_cbfn = cbfn; + iocfc->stats_cbarg = cbarg; + + bfa_iocfc_stats_clear(bfa); + return (BFA_STATUS_OK); +} + +/** + * Enable IOC after it is disabled. + */ +void +bfa_iocfc_enable(struct bfa_s *bfa) +{ + bfa_plog_str(bfa->plog, BFA_PL_MID_HAL, BFA_PL_EID_MISC, 0, + "IOC Enable"); + bfa_ioc_enable(&bfa->ioc); +} + +void +bfa_iocfc_disable(struct bfa_s *bfa) +{ + bfa_plog_str(bfa->plog, BFA_PL_MID_HAL, BFA_PL_EID_MISC, 0, + "IOC Disable"); + bfa->iocfc.action = BFA_IOCFC_ACT_DISABLE; + + bfa->rme_process = BFA_FALSE; + bfa_ioc_disable(&bfa->ioc); +} + + +bfa_boolean_t +bfa_iocfc_is_operational(struct bfa_s *bfa) +{ + return bfa_ioc_is_operational(&bfa->ioc) && bfa->iocfc.cfgdone; +} + +/** + * Return boot target port wwns -- read from boot information in flash. + */ +void +bfa_iocfc_get_bootwwns(struct bfa_s *bfa, u8 *nwwns, wwn_t **wwns) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + struct bfi_iocfc_cfgrsp_s *cfgrsp = iocfc->cfgrsp; + + *nwwns = cfgrsp->bootwwns.nwwns; + *wwns = cfgrsp->bootwwns.wwn; +} + +#endif + + diff --git a/drivers/scsi/bfa/bfa_iocfc.h b/drivers/scsi/bfa/bfa_iocfc.h new file mode 100644 index 000000000000..7ad177ed4cfc --- /dev/null +++ b/drivers/scsi/bfa/bfa_iocfc.h @@ -0,0 +1,168 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_IOCFC_H__ +#define __BFA_IOCFC_H__ + +#include <bfa_ioc.h> +#include <bfa.h> +#include <bfi/bfi_iocfc.h> +#include <bfa_callback_priv.h> + +#define BFA_REQQ_NELEMS_MIN (4) +#define BFA_RSPQ_NELEMS_MIN (4) + +struct bfa_iocfc_regs_s { + bfa_os_addr_t intr_status; + bfa_os_addr_t intr_mask; + bfa_os_addr_t cpe_q_pi[BFI_IOC_MAX_CQS]; + bfa_os_addr_t cpe_q_ci[BFI_IOC_MAX_CQS]; + bfa_os_addr_t cpe_q_depth[BFI_IOC_MAX_CQS]; + bfa_os_addr_t cpe_q_ctrl[BFI_IOC_MAX_CQS]; + bfa_os_addr_t rme_q_ci[BFI_IOC_MAX_CQS]; + bfa_os_addr_t rme_q_pi[BFI_IOC_MAX_CQS]; + bfa_os_addr_t rme_q_depth[BFI_IOC_MAX_CQS]; + bfa_os_addr_t rme_q_ctrl[BFI_IOC_MAX_CQS]; +}; + +/** + * MSIX vector handlers + */ +#define BFA_MSIX_MAX_VECTORS 22 +typedef void (*bfa_msix_handler_t)(struct bfa_s *bfa, int vec); +struct bfa_msix_s { + int nvecs; + bfa_msix_handler_t handler[BFA_MSIX_MAX_VECTORS]; +}; + +/** + * Chip specific interfaces + */ +struct bfa_hwif_s { + void (*hw_reginit)(struct bfa_s *bfa); + void (*hw_rspq_ack)(struct bfa_s *bfa, int rspq); + void (*hw_msix_init)(struct bfa_s *bfa, int nvecs); + void (*hw_msix_install)(struct bfa_s *bfa); + void (*hw_msix_uninstall)(struct bfa_s *bfa); + void (*hw_isr_mode_set)(struct bfa_s *bfa, bfa_boolean_t msix); + void (*hw_msix_getvecs)(struct bfa_s *bfa, u32 *vecmap, + u32 *nvecs, u32 *maxvec); +}; +typedef void (*bfa_cb_iocfc_t) (void *cbarg, enum bfa_status status); + +struct bfa_iocfc_s { + struct bfa_s *bfa; + struct bfa_iocfc_cfg_s cfg; + int action; + + u32 req_cq_pi[BFI_IOC_MAX_CQS]; + u32 rsp_cq_ci[BFI_IOC_MAX_CQS]; + + struct bfa_cb_qe_s init_hcb_qe; + struct bfa_cb_qe_s stop_hcb_qe; + struct bfa_cb_qe_s dis_hcb_qe; + struct bfa_cb_qe_s stats_hcb_qe; + bfa_boolean_t cfgdone; + + struct bfa_dma_s cfg_info; + struct bfi_iocfc_cfg_s *cfginfo; + struct bfa_dma_s cfgrsp_dma; + struct bfi_iocfc_cfgrsp_s *cfgrsp; + struct bfi_iocfc_cfg_reply_s *cfg_reply; + + u8 *stats_kva; + u64 stats_pa; + struct bfa_fw_stats_s *fw_stats; + struct bfa_timer_s stats_timer; /* timer */ + struct bfa_iocfc_stats_s *stats_ret; /* driver stats location */ + bfa_status_t stats_status; /* stats/statsclr status */ + bfa_boolean_t stats_busy; /* outstanding stats */ + bfa_cb_ioc_t stats_cbfn; /* driver callback function */ + void *stats_cbarg; /* user callback arg */ + + struct bfa_dma_s req_cq_ba[BFI_IOC_MAX_CQS]; + struct bfa_dma_s req_cq_shadow_ci[BFI_IOC_MAX_CQS]; + struct bfa_dma_s rsp_cq_ba[BFI_IOC_MAX_CQS]; + struct bfa_dma_s rsp_cq_shadow_pi[BFI_IOC_MAX_CQS]; + struct bfa_iocfc_regs_s bfa_regs; /* BFA device registers */ + struct bfa_hwif_s hwif; + + bfa_cb_iocfc_t updateq_cbfn; /* bios callback function */ + void *updateq_cbarg; /* bios callback arg */ +}; + +#define bfa_lpuid(__bfa) bfa_ioc_portid(&(__bfa)->ioc) +#define bfa_msix_init(__bfa, __nvecs) \ + (__bfa)->iocfc.hwif.hw_msix_init(__bfa, __nvecs) +#define bfa_msix_install(__bfa) \ + (__bfa)->iocfc.hwif.hw_msix_install(__bfa) +#define bfa_msix_uninstall(__bfa) \ + (__bfa)->iocfc.hwif.hw_msix_uninstall(__bfa) +#define bfa_isr_mode_set(__bfa, __msix) \ + (__bfa)->iocfc.hwif.hw_isr_mode_set(__bfa, __msix) +#define bfa_msix_getvecs(__bfa, __vecmap, __nvecs, __maxvec) \ + (__bfa)->iocfc.hwif.hw_msix_getvecs(__bfa, __vecmap, __nvecs, __maxvec) + +/* + * FC specific IOC functions. + */ +void bfa_iocfc_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len); +void bfa_iocfc_attach(struct bfa_s *bfa, void *bfad, + struct bfa_iocfc_cfg_s *cfg, struct bfa_meminfo_s *meminfo, + struct bfa_pcidev_s *pcidev); +void bfa_iocfc_detach(struct bfa_s *bfa); +void bfa_iocfc_init(struct bfa_s *bfa); +void bfa_iocfc_start(struct bfa_s *bfa); +void bfa_iocfc_stop(struct bfa_s *bfa); +void bfa_iocfc_isr(void *bfa, struct bfi_mbmsg_s *msg); +void bfa_iocfc_set_snsbase(struct bfa_s *bfa, u64 snsbase_pa); +bfa_boolean_t bfa_iocfc_is_operational(struct bfa_s *bfa); +void bfa_iocfc_reset_queues(struct bfa_s *bfa); +void bfa_iocfc_updateq(struct bfa_s *bfa, u32 reqq_ba, u32 rspq_ba, + u32 reqq_sci, u32 rspq_spi, + bfa_cb_iocfc_t cbfn, void *cbarg); + +void bfa_msix_all(struct bfa_s *bfa, int vec); +void bfa_msix_reqq(struct bfa_s *bfa, int vec); +void bfa_msix_rspq(struct bfa_s *bfa, int vec); +void bfa_msix_lpu_err(struct bfa_s *bfa, int vec); + +void bfa_hwcb_reginit(struct bfa_s *bfa); +void bfa_hwcb_rspq_ack(struct bfa_s *bfa, int rspq); +void bfa_hwcb_msix_init(struct bfa_s *bfa, int nvecs); +void bfa_hwcb_msix_install(struct bfa_s *bfa); +void bfa_hwcb_msix_uninstall(struct bfa_s *bfa); +void bfa_hwcb_isr_mode_set(struct bfa_s *bfa, bfa_boolean_t msix); +void bfa_hwcb_msix_getvecs(struct bfa_s *bfa, u32 *vecmap, + u32 *nvecs, u32 *maxvec); +void bfa_hwct_reginit(struct bfa_s *bfa); +void bfa_hwct_rspq_ack(struct bfa_s *bfa, int rspq); +void bfa_hwct_msix_init(struct bfa_s *bfa, int nvecs); +void bfa_hwct_msix_install(struct bfa_s *bfa); +void bfa_hwct_msix_uninstall(struct bfa_s *bfa); +void bfa_hwct_isr_mode_set(struct bfa_s *bfa, bfa_boolean_t msix); +void bfa_hwct_msix_getvecs(struct bfa_s *bfa, u32 *vecmap, + u32 *nvecs, u32 *maxvec); + +void bfa_com_meminfo(bfa_boolean_t mincfg, u32 *dm_len); +void bfa_com_attach(struct bfa_s *bfa, struct bfa_meminfo_s *mi, + bfa_boolean_t mincfg); +void bfa_iocfc_get_bootwwns(struct bfa_s *bfa, u8 *nwwns, wwn_t **wwns); + +#endif /* __BFA_IOCFC_H__ */ + diff --git a/drivers/scsi/bfa/bfa_iocfc_q.c b/drivers/scsi/bfa/bfa_iocfc_q.c new file mode 100644 index 000000000000..500a17df40b2 --- /dev/null +++ b/drivers/scsi/bfa/bfa_iocfc_q.c @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include "bfa_intr_priv.h" + +BFA_TRC_FILE(HAL, IOCFC_Q); + +void +bfa_iocfc_updateq(struct bfa_s *bfa, u32 reqq_ba, u32 rspq_ba, + u32 reqq_sci, u32 rspq_spi, bfa_cb_iocfc_t cbfn, + void *cbarg) +{ + struct bfa_iocfc_s *iocfc = &bfa->iocfc; + struct bfi_iocfc_updateq_req_s updateq_req; + + iocfc->updateq_cbfn = cbfn; + iocfc->updateq_cbarg = cbarg; + + bfi_h2i_set(updateq_req.mh, BFI_MC_IOCFC, BFI_IOCFC_H2I_UPDATEQ_REQ, + bfa_lpuid(bfa)); + + updateq_req.reqq_ba = bfa_os_htonl(reqq_ba); + updateq_req.rspq_ba = bfa_os_htonl(rspq_ba); + updateq_req.reqq_sci = bfa_os_htonl(reqq_sci); + updateq_req.rspq_spi = bfa_os_htonl(rspq_spi); + + bfa_ioc_mbox_send(&bfa->ioc, &updateq_req, + sizeof(struct bfi_iocfc_updateq_req_s)); +} diff --git a/drivers/scsi/bfa/bfa_ioim.c b/drivers/scsi/bfa/bfa_ioim.c new file mode 100644 index 000000000000..7ae2552e1e14 --- /dev/null +++ b/drivers/scsi/bfa/bfa_ioim.c @@ -0,0 +1,1311 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <cs/bfa_debug.h> +#include <bfa_cb_ioim_macros.h> + +BFA_TRC_FILE(HAL, IOIM); + +/* + * forward declarations. + */ +static bfa_boolean_t bfa_ioim_send_ioreq(struct bfa_ioim_s *ioim); +static bfa_boolean_t bfa_ioim_sge_setup(struct bfa_ioim_s *ioim); +static void bfa_ioim_sgpg_setup(struct bfa_ioim_s *ioim); +static bfa_boolean_t bfa_ioim_send_abort(struct bfa_ioim_s *ioim); +static void bfa_ioim_notify_cleanup(struct bfa_ioim_s *ioim); +static void __bfa_cb_ioim_good_comp(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_ioim_comp(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_ioim_abort(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_ioim_failed(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_ioim_pathtov(void *cbarg, bfa_boolean_t complete); + +/** + * bfa_ioim_sm + */ + +/** + * IO state machine events + */ +enum bfa_ioim_event { + BFA_IOIM_SM_START = 1, /* io start request from host */ + BFA_IOIM_SM_COMP_GOOD = 2, /* io good comp, resource free */ + BFA_IOIM_SM_COMP = 3, /* io comp, resource is free */ + BFA_IOIM_SM_COMP_UTAG = 4, /* io comp, resource is free */ + BFA_IOIM_SM_DONE = 5, /* io comp, resource not free */ + BFA_IOIM_SM_FREE = 6, /* io resource is freed */ + BFA_IOIM_SM_ABORT = 7, /* abort request from scsi stack */ + BFA_IOIM_SM_ABORT_COMP = 8, /* abort from f/w */ + BFA_IOIM_SM_ABORT_DONE = 9, /* abort completion from f/w */ + BFA_IOIM_SM_QRESUME = 10, /* CQ space available to queue IO */ + BFA_IOIM_SM_SGALLOCED = 11, /* SG page allocation successful */ + BFA_IOIM_SM_SQRETRY = 12, /* sequence recovery retry */ + BFA_IOIM_SM_HCB = 13, /* bfa callback complete */ + BFA_IOIM_SM_CLEANUP = 14, /* IO cleanup from itnim */ + BFA_IOIM_SM_TMSTART = 15, /* IO cleanup from tskim */ + BFA_IOIM_SM_TMDONE = 16, /* IO cleanup from tskim */ + BFA_IOIM_SM_HWFAIL = 17, /* IOC h/w failure event */ + BFA_IOIM_SM_IOTOV = 18, /* ITN offline TOV */ +}; + +/* + * forward declaration of IO state machine + */ +static void bfa_ioim_sm_uninit(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_sgalloc(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_active(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_abort(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_cleanup(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_qfull(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_abort_qfull(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_cleanup_qfull(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_hcb(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_hcb_free(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); +static void bfa_ioim_sm_resfree(struct bfa_ioim_s *ioim, + enum bfa_ioim_event event); + +/** + * IO is not started (unallocated). + */ +static void +bfa_ioim_sm_uninit(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc_fp(ioim->bfa, ioim->iotag); + bfa_trc_fp(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_START: + if (!bfa_itnim_is_online(ioim->itnim)) { + if (!bfa_itnim_hold_io(ioim->itnim)) { + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + list_del(&ioim->qe); + list_add_tail(&ioim->qe, + &ioim->fcpim->ioim_comp_q); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, + __bfa_cb_ioim_pathtov, ioim); + } else { + list_del(&ioim->qe); + list_add_tail(&ioim->qe, + &ioim->itnim->pending_q); + } + break; + } + + if (ioim->nsges > BFI_SGE_INLINE) { + if (!bfa_ioim_sge_setup(ioim)) { + bfa_sm_set_state(ioim, bfa_ioim_sm_sgalloc); + return; + } + } + + if (!bfa_ioim_send_ioreq(ioim)) { + bfa_sm_set_state(ioim, bfa_ioim_sm_qfull); + break; + } + + bfa_sm_set_state(ioim, bfa_ioim_sm_active); + break; + + case BFA_IOIM_SM_IOTOV: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, + __bfa_cb_ioim_pathtov, ioim); + break; + + case BFA_IOIM_SM_ABORT: + /** + * IO in pending queue can get abort requests. Complete abort + * requests immediately. + */ + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_assert(bfa_q_is_on_q(&ioim->itnim->pending_q, ioim)); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + default: + bfa_assert(0); + } +} + +/** + * IO is waiting for SG pages. + */ +static void +bfa_ioim_sm_sgalloc(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_SGALLOCED: + if (!bfa_ioim_send_ioreq(ioim)) { + bfa_sm_set_state(ioim, bfa_ioim_sm_qfull); + break; + } + bfa_sm_set_state(ioim, bfa_ioim_sm_active); + break; + + case BFA_IOIM_SM_CLEANUP: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_sgpg_wcancel(ioim->bfa, &ioim->iosp->sgpg_wqe); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_ABORT: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_sgpg_wcancel(ioim->bfa, &ioim->iosp->sgpg_wqe); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_sgpg_wcancel(ioim->bfa, &ioim->iosp->sgpg_wqe); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + break; + + default: + bfa_assert(0); + } +} + +/** + * IO is active. + */ +static void +bfa_ioim_sm_active(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc_fp(ioim->bfa, ioim->iotag); + bfa_trc_fp(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_COMP_GOOD: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, + __bfa_cb_ioim_good_comp, ioim); + break; + + case BFA_IOIM_SM_COMP: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_comp, + ioim); + break; + + case BFA_IOIM_SM_DONE: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb_free); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_comp, + ioim); + break; + + case BFA_IOIM_SM_ABORT: + ioim->iosp->abort_explicit = BFA_TRUE; + ioim->io_cbfn = __bfa_cb_ioim_abort; + + if (bfa_ioim_send_abort(ioim)) + bfa_sm_set_state(ioim, bfa_ioim_sm_abort); + else { + bfa_sm_set_state(ioim, bfa_ioim_sm_abort_qfull); + bfa_reqq_wait(ioim->bfa, ioim->itnim->reqq, + &ioim->iosp->reqq_wait); + } + break; + + case BFA_IOIM_SM_CLEANUP: + ioim->iosp->abort_explicit = BFA_FALSE; + ioim->io_cbfn = __bfa_cb_ioim_failed; + + if (bfa_ioim_send_abort(ioim)) + bfa_sm_set_state(ioim, bfa_ioim_sm_cleanup); + else { + bfa_sm_set_state(ioim, bfa_ioim_sm_cleanup_qfull); + bfa_reqq_wait(ioim->bfa, ioim->itnim->reqq, + &ioim->iosp->reqq_wait); + } + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + break; + + default: + bfa_assert(0); + } +} + +/** + * IO is being aborted, waiting for completion from firmware. + */ +static void +bfa_ioim_sm_abort(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_COMP_GOOD: + case BFA_IOIM_SM_COMP: + case BFA_IOIM_SM_DONE: + case BFA_IOIM_SM_FREE: + break; + + case BFA_IOIM_SM_ABORT_DONE: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb_free); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + case BFA_IOIM_SM_ABORT_COMP: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + case BFA_IOIM_SM_COMP_UTAG: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + case BFA_IOIM_SM_CLEANUP: + bfa_assert(ioim->iosp->abort_explicit == BFA_TRUE); + ioim->iosp->abort_explicit = BFA_FALSE; + + if (bfa_ioim_send_abort(ioim)) + bfa_sm_set_state(ioim, bfa_ioim_sm_cleanup); + else { + bfa_sm_set_state(ioim, bfa_ioim_sm_cleanup_qfull); + bfa_reqq_wait(ioim->bfa, ioim->itnim->reqq, + &ioim->iosp->reqq_wait); + } + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + break; + + default: + bfa_assert(0); + } +} + +/** + * IO is being cleaned up (implicit abort), waiting for completion from + * firmware. + */ +static void +bfa_ioim_sm_cleanup(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_COMP_GOOD: + case BFA_IOIM_SM_COMP: + case BFA_IOIM_SM_DONE: + case BFA_IOIM_SM_FREE: + break; + + case BFA_IOIM_SM_ABORT: + /** + * IO is already being aborted implicitly + */ + ioim->io_cbfn = __bfa_cb_ioim_abort; + break; + + case BFA_IOIM_SM_ABORT_DONE: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb_free); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, ioim->io_cbfn, ioim); + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_ABORT_COMP: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, ioim->io_cbfn, ioim); + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_COMP_UTAG: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, ioim->io_cbfn, ioim); + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + break; + + case BFA_IOIM_SM_CLEANUP: + /** + * IO can be in cleanup state already due to TM command. 2nd cleanup + * request comes from ITN offline event. + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * IO is waiting for room in request CQ + */ +static void +bfa_ioim_sm_qfull(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_QRESUME: + bfa_sm_set_state(ioim, bfa_ioim_sm_active); + bfa_ioim_send_ioreq(ioim); + break; + + case BFA_IOIM_SM_ABORT: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + case BFA_IOIM_SM_CLEANUP: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Active IO is being aborted, waiting for room in request CQ. + */ +static void +bfa_ioim_sm_abort_qfull(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_QRESUME: + bfa_sm_set_state(ioim, bfa_ioim_sm_abort); + bfa_ioim_send_abort(ioim); + break; + + case BFA_IOIM_SM_CLEANUP: + bfa_assert(ioim->iosp->abort_explicit == BFA_TRUE); + ioim->iosp->abort_explicit = BFA_FALSE; + bfa_sm_set_state(ioim, bfa_ioim_sm_cleanup_qfull); + break; + + case BFA_IOIM_SM_COMP_GOOD: + case BFA_IOIM_SM_COMP: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + case BFA_IOIM_SM_DONE: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb_free); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_abort, + ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Active IO is being cleaned up, waiting for room in request CQ. + */ +static void +bfa_ioim_sm_cleanup_qfull(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_QRESUME: + bfa_sm_set_state(ioim, bfa_ioim_sm_cleanup); + bfa_ioim_send_abort(ioim); + break; + + case BFA_IOIM_SM_ABORT: + /** + * IO is alraedy being cleaned up implicitly + */ + ioim->io_cbfn = __bfa_cb_ioim_abort; + break; + + case BFA_IOIM_SM_COMP_GOOD: + case BFA_IOIM_SM_COMP: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, ioim->io_cbfn, ioim); + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_DONE: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb_free); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, ioim->io_cbfn, ioim); + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + bfa_reqq_wcancel(&ioim->iosp->reqq_wait); + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, __bfa_cb_ioim_failed, + ioim); + break; + + default: + bfa_assert(0); + } +} + +/** + * IO bfa callback is pending. + */ +static void +bfa_ioim_sm_hcb(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc_fp(ioim->bfa, ioim->iotag); + bfa_trc_fp(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_HCB: + bfa_sm_set_state(ioim, bfa_ioim_sm_uninit); + bfa_ioim_free(ioim); + bfa_cb_ioim_resfree(ioim->bfa->bfad); + break; + + case BFA_IOIM_SM_CLEANUP: + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + break; + + default: + bfa_assert(0); + } +} + +/** + * IO bfa callback is pending. IO resource cannot be freed. + */ +static void +bfa_ioim_sm_hcb_free(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_HCB: + bfa_sm_set_state(ioim, bfa_ioim_sm_resfree); + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &ioim->fcpim->ioim_resfree_q); + break; + + case BFA_IOIM_SM_FREE: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + break; + + case BFA_IOIM_SM_CLEANUP: + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + bfa_sm_set_state(ioim, bfa_ioim_sm_hcb); + break; + + default: + bfa_assert(0); + } +} + +/** + * IO is completed, waiting resource free from firmware. + */ +static void +bfa_ioim_sm_resfree(struct bfa_ioim_s *ioim, enum bfa_ioim_event event) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, event); + + switch (event) { + case BFA_IOIM_SM_FREE: + bfa_sm_set_state(ioim, bfa_ioim_sm_uninit); + bfa_ioim_free(ioim); + bfa_cb_ioim_resfree(ioim->bfa->bfad); + break; + + case BFA_IOIM_SM_CLEANUP: + bfa_ioim_notify_cleanup(ioim); + break; + + case BFA_IOIM_SM_HWFAIL: + break; + + default: + bfa_assert(0); + } +} + + + +/** + * bfa_ioim_private + */ + +static void +__bfa_cb_ioim_good_comp(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_ioim_s *ioim = cbarg; + + if (!complete) { + bfa_sm_send_event(ioim, BFA_IOIM_SM_HCB); + return; + } + + bfa_cb_ioim_good_comp(ioim->bfa->bfad, ioim->dio); +} + +static void +__bfa_cb_ioim_comp(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_ioim_s *ioim = cbarg; + struct bfi_ioim_rsp_s *m; + u8 *snsinfo = NULL; + u8 sns_len = 0; + s32 residue = 0; + + if (!complete) { + bfa_sm_send_event(ioim, BFA_IOIM_SM_HCB); + return; + } + + m = (struct bfi_ioim_rsp_s *) &ioim->iosp->comp_rspmsg; + if (m->io_status == BFI_IOIM_STS_OK) { + /** + * setup sense information, if present + */ + if (m->scsi_status == SCSI_STATUS_CHECK_CONDITION + && m->sns_len) { + sns_len = m->sns_len; + snsinfo = ioim->iosp->snsinfo; + } + + /** + * setup residue value correctly for normal completions + */ + if (m->resid_flags == FCP_RESID_UNDER) + residue = bfa_os_ntohl(m->residue); + if (m->resid_flags == FCP_RESID_OVER) { + residue = bfa_os_ntohl(m->residue); + residue = -residue; + } + } + + bfa_cb_ioim_done(ioim->bfa->bfad, ioim->dio, m->io_status, + m->scsi_status, sns_len, snsinfo, residue); +} + +static void +__bfa_cb_ioim_failed(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_ioim_s *ioim = cbarg; + + if (!complete) { + bfa_sm_send_event(ioim, BFA_IOIM_SM_HCB); + return; + } + + bfa_cb_ioim_done(ioim->bfa->bfad, ioim->dio, BFI_IOIM_STS_ABORTED, + 0, 0, NULL, 0); +} + +static void +__bfa_cb_ioim_pathtov(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_ioim_s *ioim = cbarg; + + if (!complete) { + bfa_sm_send_event(ioim, BFA_IOIM_SM_HCB); + return; + } + + bfa_cb_ioim_done(ioim->bfa->bfad, ioim->dio, BFI_IOIM_STS_PATHTOV, + 0, 0, NULL, 0); +} + +static void +__bfa_cb_ioim_abort(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_ioim_s *ioim = cbarg; + + if (!complete) { + bfa_sm_send_event(ioim, BFA_IOIM_SM_HCB); + return; + } + + bfa_cb_ioim_abort(ioim->bfa->bfad, ioim->dio); +} + +static void +bfa_ioim_sgpg_alloced(void *cbarg) +{ + struct bfa_ioim_s *ioim = cbarg; + + ioim->nsgpgs = BFA_SGPG_NPAGE(ioim->nsges); + list_splice_tail_init(&ioim->iosp->sgpg_wqe.sgpg_q, &ioim->sgpg_q); + bfa_ioim_sgpg_setup(ioim); + bfa_sm_send_event(ioim, BFA_IOIM_SM_SGALLOCED); +} + +/** + * Send I/O request to firmware. + */ +static bfa_boolean_t +bfa_ioim_send_ioreq(struct bfa_ioim_s *ioim) +{ + struct bfa_itnim_s *itnim = ioim->itnim; + struct bfi_ioim_req_s *m; + static struct fcp_cmnd_s cmnd_z0 = { 0 }; + struct bfi_sge_s *sge; + u32 pgdlen = 0; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(ioim->bfa, itnim->reqq); + if (!m) { + bfa_reqq_wait(ioim->bfa, ioim->itnim->reqq, + &ioim->iosp->reqq_wait); + return BFA_FALSE; + } + + /** + * build i/o request message next + */ + m->io_tag = bfa_os_htons(ioim->iotag); + m->rport_hdl = ioim->itnim->rport->fw_handle; + m->io_timeout = bfa_cb_ioim_get_timeout(ioim->dio); + + /** + * build inline IO SG element here + */ + sge = &m->sges[0]; + if (ioim->nsges) { + sge->sga = bfa_cb_ioim_get_sgaddr(ioim->dio, 0); + pgdlen = bfa_cb_ioim_get_sglen(ioim->dio, 0); + sge->sg_len = pgdlen; + sge->flags = (ioim->nsges > BFI_SGE_INLINE) ? + BFI_SGE_DATA_CPL : BFI_SGE_DATA_LAST; + bfa_sge_to_be(sge); + sge++; + } + + if (ioim->nsges > BFI_SGE_INLINE) { + sge->sga = ioim->sgpg->sgpg_pa; + } else { + sge->sga.a32.addr_lo = 0; + sge->sga.a32.addr_hi = 0; + } + sge->sg_len = pgdlen; + sge->flags = BFI_SGE_PGDLEN; + bfa_sge_to_be(sge); + + /** + * set up I/O command parameters + */ + bfa_os_assign(m->cmnd, cmnd_z0); + m->cmnd.lun = bfa_cb_ioim_get_lun(ioim->dio); + m->cmnd.iodir = bfa_cb_ioim_get_iodir(ioim->dio); + bfa_os_assign(m->cmnd.cdb, + *(struct scsi_cdb_s *)bfa_cb_ioim_get_cdb(ioim->dio)); + m->cmnd.fcp_dl = bfa_os_htonl(bfa_cb_ioim_get_size(ioim->dio)); + + /** + * set up I/O message header + */ + switch (m->cmnd.iodir) { + case FCP_IODIR_READ: + bfi_h2i_set(m->mh, BFI_MC_IOIM_READ, 0, bfa_lpuid(ioim->bfa)); + bfa_stats(itnim, input_reqs); + break; + case FCP_IODIR_WRITE: + bfi_h2i_set(m->mh, BFI_MC_IOIM_WRITE, 0, bfa_lpuid(ioim->bfa)); + bfa_stats(itnim, output_reqs); + break; + case FCP_IODIR_RW: + bfa_stats(itnim, input_reqs); + bfa_stats(itnim, output_reqs); + default: + bfi_h2i_set(m->mh, BFI_MC_IOIM_IO, 0, bfa_lpuid(ioim->bfa)); + } + if (itnim->seq_rec || + (bfa_cb_ioim_get_size(ioim->dio) & (sizeof(u32) - 1))) + bfi_h2i_set(m->mh, BFI_MC_IOIM_IO, 0, bfa_lpuid(ioim->bfa)); + +#ifdef IOIM_ADVANCED + m->cmnd.crn = bfa_cb_ioim_get_crn(ioim->dio); + m->cmnd.priority = bfa_cb_ioim_get_priority(ioim->dio); + m->cmnd.taskattr = bfa_cb_ioim_get_taskattr(ioim->dio); + + /** + * Handle large CDB (>16 bytes). + */ + m->cmnd.addl_cdb_len = (bfa_cb_ioim_get_cdblen(ioim->dio) - + FCP_CMND_CDB_LEN) / sizeof(u32); + if (m->cmnd.addl_cdb_len) { + bfa_os_memcpy(&m->cmnd.cdb + 1, (struct scsi_cdb_s *) + bfa_cb_ioim_get_cdb(ioim->dio) + 1, + m->cmnd.addl_cdb_len * sizeof(u32)); + fcp_cmnd_fcpdl(&m->cmnd) = + bfa_os_htonl(bfa_cb_ioim_get_size(ioim->dio)); + } +#endif + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(ioim->bfa, itnim->reqq); + return BFA_TRUE; +} + +/** + * Setup any additional SG pages needed.Inline SG element is setup + * at queuing time. + */ +static bfa_boolean_t +bfa_ioim_sge_setup(struct bfa_ioim_s *ioim) +{ + u16 nsgpgs; + + bfa_assert(ioim->nsges > BFI_SGE_INLINE); + + /** + * allocate SG pages needed + */ + nsgpgs = BFA_SGPG_NPAGE(ioim->nsges); + if (!nsgpgs) + return BFA_TRUE; + + if (bfa_sgpg_malloc(ioim->bfa, &ioim->sgpg_q, nsgpgs) + != BFA_STATUS_OK) { + bfa_sgpg_wait(ioim->bfa, &ioim->iosp->sgpg_wqe, nsgpgs); + return BFA_FALSE; + } + + ioim->nsgpgs = nsgpgs; + bfa_ioim_sgpg_setup(ioim); + + return BFA_TRUE; +} + +static void +bfa_ioim_sgpg_setup(struct bfa_ioim_s *ioim) +{ + int sgeid, nsges, i; + struct bfi_sge_s *sge; + struct bfa_sgpg_s *sgpg; + u32 pgcumsz; + + sgeid = BFI_SGE_INLINE; + ioim->sgpg = sgpg = bfa_q_first(&ioim->sgpg_q); + + do { + sge = sgpg->sgpg->sges; + nsges = ioim->nsges - sgeid; + if (nsges > BFI_SGPG_DATA_SGES) + nsges = BFI_SGPG_DATA_SGES; + + pgcumsz = 0; + for (i = 0; i < nsges; i++, sge++, sgeid++) { + sge->sga = bfa_cb_ioim_get_sgaddr(ioim->dio, sgeid); + sge->sg_len = bfa_cb_ioim_get_sglen(ioim->dio, sgeid); + pgcumsz += sge->sg_len; + + /** + * set flags + */ + if (i < (nsges - 1)) + sge->flags = BFI_SGE_DATA; + else if (sgeid < (ioim->nsges - 1)) + sge->flags = BFI_SGE_DATA_CPL; + else + sge->flags = BFI_SGE_DATA_LAST; + } + + sgpg = (struct bfa_sgpg_s *) bfa_q_next(sgpg); + + /** + * set the link element of each page + */ + if (sgeid == ioim->nsges) { + sge->flags = BFI_SGE_PGDLEN; + sge->sga.a32.addr_lo = 0; + sge->sga.a32.addr_hi = 0; + } else { + sge->flags = BFI_SGE_LINK; + sge->sga = sgpg->sgpg_pa; + } + sge->sg_len = pgcumsz; + } while (sgeid < ioim->nsges); +} + +/** + * Send I/O abort request to firmware. + */ +static bfa_boolean_t +bfa_ioim_send_abort(struct bfa_ioim_s *ioim) +{ + struct bfa_itnim_s *itnim = ioim->itnim; + struct bfi_ioim_abort_req_s *m; + enum bfi_ioim_h2i msgop; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(ioim->bfa, itnim->reqq); + if (!m) + return BFA_FALSE; + + /** + * build i/o request message next + */ + if (ioim->iosp->abort_explicit) + msgop = BFI_IOIM_H2I_IOABORT_REQ; + else + msgop = BFI_IOIM_H2I_IOCLEANUP_REQ; + + bfi_h2i_set(m->mh, BFI_MC_IOIM, msgop, bfa_lpuid(ioim->bfa)); + m->io_tag = bfa_os_htons(ioim->iotag); + m->abort_tag = ++ioim->abort_tag; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(ioim->bfa, itnim->reqq); + return BFA_TRUE; +} + +/** + * Call to resume any I/O requests waiting for room in request queue. + */ +static void +bfa_ioim_qresume(void *cbarg) +{ + struct bfa_ioim_s *ioim = cbarg; + + bfa_fcpim_stats(ioim->fcpim, qresumes); + bfa_sm_send_event(ioim, BFA_IOIM_SM_QRESUME); +} + + +static void +bfa_ioim_notify_cleanup(struct bfa_ioim_s *ioim) +{ + /** + * Move IO from itnim queue to fcpim global queue since itnim will be + * freed. + */ + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &ioim->fcpim->ioim_comp_q); + + if (!ioim->iosp->tskim) { + if (ioim->fcpim->delay_comp && ioim->itnim->iotov_active) { + bfa_cb_dequeue(&ioim->hcb_qe); + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &ioim->itnim->delay_comp_q); + } + bfa_itnim_iodone(ioim->itnim); + } else + bfa_tskim_iodone(ioim->iosp->tskim); +} + +/** + * or after the link comes back. + */ +void +bfa_ioim_delayed_comp(struct bfa_ioim_s *ioim, bfa_boolean_t iotov) +{ + /** + * If path tov timer expired, failback with PATHTOV status - these + * IO requests are not normally retried by IO stack. + * + * Otherwise device cameback online and fail it with normal failed + * status so that IO stack retries these failed IO requests. + */ + if (iotov) + ioim->io_cbfn = __bfa_cb_ioim_pathtov; + else + ioim->io_cbfn = __bfa_cb_ioim_failed; + + bfa_cb_queue(ioim->bfa, &ioim->hcb_qe, ioim->io_cbfn, ioim); + + /** + * Move IO to fcpim global queue since itnim will be + * freed. + */ + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &ioim->fcpim->ioim_comp_q); +} + + + +/** + * bfa_ioim_friend + */ + +/** + * Memory allocation and initialization. + */ +void +bfa_ioim_attach(struct bfa_fcpim_mod_s *fcpim, struct bfa_meminfo_s *minfo) +{ + struct bfa_ioim_s *ioim; + struct bfa_ioim_sp_s *iosp; + u16 i; + u8 *snsinfo; + u32 snsbufsz; + + /** + * claim memory first + */ + ioim = (struct bfa_ioim_s *) bfa_meminfo_kva(minfo); + fcpim->ioim_arr = ioim; + bfa_meminfo_kva(minfo) = (u8 *) (ioim + fcpim->num_ioim_reqs); + + iosp = (struct bfa_ioim_sp_s *) bfa_meminfo_kva(minfo); + fcpim->ioim_sp_arr = iosp; + bfa_meminfo_kva(minfo) = (u8 *) (iosp + fcpim->num_ioim_reqs); + + /** + * Claim DMA memory for per IO sense data. + */ + snsbufsz = fcpim->num_ioim_reqs * BFI_IOIM_SNSLEN; + fcpim->snsbase.pa = bfa_meminfo_dma_phys(minfo); + bfa_meminfo_dma_phys(minfo) += snsbufsz; + + fcpim->snsbase.kva = bfa_meminfo_dma_virt(minfo); + bfa_meminfo_dma_virt(minfo) += snsbufsz; + snsinfo = fcpim->snsbase.kva; + bfa_iocfc_set_snsbase(fcpim->bfa, fcpim->snsbase.pa); + + /** + * Initialize ioim free queues + */ + INIT_LIST_HEAD(&fcpim->ioim_free_q); + INIT_LIST_HEAD(&fcpim->ioim_resfree_q); + INIT_LIST_HEAD(&fcpim->ioim_comp_q); + + for (i = 0; i < fcpim->num_ioim_reqs; + i++, ioim++, iosp++, snsinfo += BFI_IOIM_SNSLEN) { + /* + * initialize IOIM + */ + bfa_os_memset(ioim, 0, sizeof(struct bfa_ioim_s)); + ioim->iotag = i; + ioim->bfa = fcpim->bfa; + ioim->fcpim = fcpim; + ioim->iosp = iosp; + iosp->snsinfo = snsinfo; + INIT_LIST_HEAD(&ioim->sgpg_q); + bfa_reqq_winit(&ioim->iosp->reqq_wait, + bfa_ioim_qresume, ioim); + bfa_sgpg_winit(&ioim->iosp->sgpg_wqe, + bfa_ioim_sgpg_alloced, ioim); + bfa_sm_set_state(ioim, bfa_ioim_sm_uninit); + + list_add_tail(&ioim->qe, &fcpim->ioim_free_q); + } +} + +/** + * Driver detach time call. + */ +void +bfa_ioim_detach(struct bfa_fcpim_mod_s *fcpim) +{ +} + +void +bfa_ioim_isr(struct bfa_s *bfa, struct bfi_msg_s *m) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + struct bfi_ioim_rsp_s *rsp = (struct bfi_ioim_rsp_s *) m; + struct bfa_ioim_s *ioim; + u16 iotag; + enum bfa_ioim_event evt = BFA_IOIM_SM_COMP; + + iotag = bfa_os_ntohs(rsp->io_tag); + + ioim = BFA_IOIM_FROM_TAG(fcpim, iotag); + bfa_assert(ioim->iotag == iotag); + + bfa_trc(ioim->bfa, ioim->iotag); + bfa_trc(ioim->bfa, rsp->io_status); + bfa_trc(ioim->bfa, rsp->reuse_io_tag); + + if (bfa_sm_cmp_state(ioim, bfa_ioim_sm_active)) + bfa_os_assign(ioim->iosp->comp_rspmsg, *m); + + switch (rsp->io_status) { + case BFI_IOIM_STS_OK: + bfa_fcpim_stats(fcpim, iocomp_ok); + if (rsp->reuse_io_tag == 0) + evt = BFA_IOIM_SM_DONE; + else + evt = BFA_IOIM_SM_COMP; + break; + + case BFI_IOIM_STS_TIMEDOUT: + case BFI_IOIM_STS_ABORTED: + rsp->io_status = BFI_IOIM_STS_ABORTED; + bfa_fcpim_stats(fcpim, iocomp_aborted); + if (rsp->reuse_io_tag == 0) + evt = BFA_IOIM_SM_DONE; + else + evt = BFA_IOIM_SM_COMP; + break; + + case BFI_IOIM_STS_PROTO_ERR: + bfa_fcpim_stats(fcpim, iocom_proto_err); + bfa_assert(rsp->reuse_io_tag); + evt = BFA_IOIM_SM_COMP; + break; + + case BFI_IOIM_STS_SQER_NEEDED: + bfa_fcpim_stats(fcpim, iocom_sqer_needed); + bfa_assert(rsp->reuse_io_tag == 0); + evt = BFA_IOIM_SM_SQRETRY; + break; + + case BFI_IOIM_STS_RES_FREE: + bfa_fcpim_stats(fcpim, iocom_res_free); + evt = BFA_IOIM_SM_FREE; + break; + + case BFI_IOIM_STS_HOST_ABORTED: + bfa_fcpim_stats(fcpim, iocom_hostabrts); + if (rsp->abort_tag != ioim->abort_tag) { + bfa_trc(ioim->bfa, rsp->abort_tag); + bfa_trc(ioim->bfa, ioim->abort_tag); + return; + } + + if (rsp->reuse_io_tag) + evt = BFA_IOIM_SM_ABORT_COMP; + else + evt = BFA_IOIM_SM_ABORT_DONE; + break; + + case BFI_IOIM_STS_UTAG: + bfa_fcpim_stats(fcpim, iocom_utags); + evt = BFA_IOIM_SM_COMP_UTAG; + break; + + default: + bfa_assert(0); + } + + bfa_sm_send_event(ioim, evt); +} + +void +bfa_ioim_good_comp_isr(struct bfa_s *bfa, struct bfi_msg_s *m) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + struct bfi_ioim_rsp_s *rsp = (struct bfi_ioim_rsp_s *) m; + struct bfa_ioim_s *ioim; + u16 iotag; + + iotag = bfa_os_ntohs(rsp->io_tag); + + ioim = BFA_IOIM_FROM_TAG(fcpim, iotag); + bfa_assert(ioim->iotag == iotag); + + bfa_trc_fp(ioim->bfa, ioim->iotag); + bfa_sm_send_event(ioim, BFA_IOIM_SM_COMP_GOOD); +} + +/** + * Called by itnim to clean up IO while going offline. + */ +void +bfa_ioim_cleanup(struct bfa_ioim_s *ioim) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_fcpim_stats(ioim->fcpim, io_cleanups); + + ioim->iosp->tskim = NULL; + bfa_sm_send_event(ioim, BFA_IOIM_SM_CLEANUP); +} + +void +bfa_ioim_cleanup_tm(struct bfa_ioim_s *ioim, struct bfa_tskim_s *tskim) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_fcpim_stats(ioim->fcpim, io_tmaborts); + + ioim->iosp->tskim = tskim; + bfa_sm_send_event(ioim, BFA_IOIM_SM_CLEANUP); +} + +/** + * IOC failure handling. + */ +void +bfa_ioim_iocdisable(struct bfa_ioim_s *ioim) +{ + bfa_sm_send_event(ioim, BFA_IOIM_SM_HWFAIL); +} + +/** + * IO offline TOV popped. Fail the pending IO. + */ +void +bfa_ioim_tov(struct bfa_ioim_s *ioim) +{ + bfa_sm_send_event(ioim, BFA_IOIM_SM_IOTOV); +} + + + +/** + * bfa_ioim_api + */ + +/** + * Allocate IOIM resource for initiator mode I/O request. + */ +struct bfa_ioim_s * +bfa_ioim_alloc(struct bfa_s *bfa, struct bfad_ioim_s *dio, + struct bfa_itnim_s *itnim, u16 nsges) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + struct bfa_ioim_s *ioim; + + /** + * alocate IOIM resource + */ + bfa_q_deq(&fcpim->ioim_free_q, &ioim); + if (!ioim) { + bfa_fcpim_stats(fcpim, no_iotags); + return NULL; + } + + ioim->dio = dio; + ioim->itnim = itnim; + ioim->nsges = nsges; + ioim->nsgpgs = 0; + + bfa_stats(fcpim, total_ios); + bfa_stats(itnim, ios); + fcpim->ios_active++; + + list_add_tail(&ioim->qe, &itnim->io_q); + bfa_trc_fp(ioim->bfa, ioim->iotag); + + return ioim; +} + +void +bfa_ioim_free(struct bfa_ioim_s *ioim) +{ + struct bfa_fcpim_mod_s *fcpim = ioim->fcpim; + + bfa_trc_fp(ioim->bfa, ioim->iotag); + bfa_assert_fp(bfa_sm_cmp_state(ioim, bfa_ioim_sm_uninit)); + + bfa_assert_fp(list_empty(&ioim->sgpg_q) + || (ioim->nsges > BFI_SGE_INLINE)); + + if (ioim->nsgpgs > 0) + bfa_sgpg_mfree(ioim->bfa, &ioim->sgpg_q, ioim->nsgpgs); + + bfa_stats(ioim->itnim, io_comps); + fcpim->ios_active--; + + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &fcpim->ioim_free_q); +} + +void +bfa_ioim_start(struct bfa_ioim_s *ioim) +{ + bfa_trc_fp(ioim->bfa, ioim->iotag); + bfa_sm_send_event(ioim, BFA_IOIM_SM_START); +} + +/** + * Driver I/O abort request. + */ +void +bfa_ioim_abort(struct bfa_ioim_s *ioim) +{ + bfa_trc(ioim->bfa, ioim->iotag); + bfa_fcpim_stats(ioim->fcpim, io_aborts); + bfa_sm_send_event(ioim, BFA_IOIM_SM_ABORT); +} + + diff --git a/drivers/scsi/bfa/bfa_itnim.c b/drivers/scsi/bfa/bfa_itnim.c new file mode 100644 index 000000000000..4d5c61a4f85c --- /dev/null +++ b/drivers/scsi/bfa/bfa_itnim.c @@ -0,0 +1,1088 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfa_fcpim.h> +#include "bfa_fcpim_priv.h" + +BFA_TRC_FILE(HAL, ITNIM); + +#define BFA_ITNIM_FROM_TAG(_fcpim, _tag) \ + ((_fcpim)->itnim_arr + ((_tag) & ((_fcpim)->num_itnims - 1))) + +#define bfa_fcpim_additn(__itnim) \ + list_add_tail(&(__itnim)->qe, &(__itnim)->fcpim->itnim_q) +#define bfa_fcpim_delitn(__itnim) do { \ + bfa_assert(bfa_q_is_on_q(&(__itnim)->fcpim->itnim_q, __itnim)); \ + list_del(&(__itnim)->qe); \ + bfa_assert(list_empty(&(__itnim)->io_q)); \ + bfa_assert(list_empty(&(__itnim)->io_cleanup_q)); \ + bfa_assert(list_empty(&(__itnim)->pending_q)); \ +} while (0) + +#define bfa_itnim_online_cb(__itnim) do { \ + if ((__itnim)->bfa->fcs) \ + bfa_cb_itnim_online((__itnim)->ditn); \ + else { \ + bfa_cb_queue((__itnim)->bfa, &(__itnim)->hcb_qe, \ + __bfa_cb_itnim_online, (__itnim)); \ + } \ +} while (0) + +#define bfa_itnim_offline_cb(__itnim) do { \ + if ((__itnim)->bfa->fcs) \ + bfa_cb_itnim_offline((__itnim)->ditn); \ + else { \ + bfa_cb_queue((__itnim)->bfa, &(__itnim)->hcb_qe, \ + __bfa_cb_itnim_offline, (__itnim)); \ + } \ +} while (0) + +#define bfa_itnim_sler_cb(__itnim) do { \ + if ((__itnim)->bfa->fcs) \ + bfa_cb_itnim_sler((__itnim)->ditn); \ + else { \ + bfa_cb_queue((__itnim)->bfa, &(__itnim)->hcb_qe, \ + __bfa_cb_itnim_sler, (__itnim)); \ + } \ +} while (0) + +/* + * forward declarations + */ +static void bfa_itnim_iocdisable_cleanup(struct bfa_itnim_s *itnim); +static bfa_boolean_t bfa_itnim_send_fwcreate(struct bfa_itnim_s *itnim); +static bfa_boolean_t bfa_itnim_send_fwdelete(struct bfa_itnim_s *itnim); +static void bfa_itnim_cleanp_comp(void *itnim_cbarg); +static void bfa_itnim_cleanup(struct bfa_itnim_s *itnim); +static void __bfa_cb_itnim_online(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_itnim_offline(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_itnim_sler(void *cbarg, bfa_boolean_t complete); +static void bfa_itnim_iotov_online(struct bfa_itnim_s *itnim); +static void bfa_itnim_iotov_cleanup(struct bfa_itnim_s *itnim); +static void bfa_itnim_iotov(void *itnim_arg); +static void bfa_itnim_iotov_start(struct bfa_itnim_s *itnim); +static void bfa_itnim_iotov_stop(struct bfa_itnim_s *itnim); +static void bfa_itnim_iotov_delete(struct bfa_itnim_s *itnim); + +/** + * bfa_itnim_sm BFA itnim state machine + */ + + +enum bfa_itnim_event { + BFA_ITNIM_SM_CREATE = 1, /* itnim is created */ + BFA_ITNIM_SM_ONLINE = 2, /* itnim is online */ + BFA_ITNIM_SM_OFFLINE = 3, /* itnim is offline */ + BFA_ITNIM_SM_FWRSP = 4, /* firmware response */ + BFA_ITNIM_SM_DELETE = 5, /* deleting an existing itnim */ + BFA_ITNIM_SM_CLEANUP = 6, /* IO cleanup completion */ + BFA_ITNIM_SM_SLER = 7, /* second level error recovery */ + BFA_ITNIM_SM_HWFAIL = 8, /* IOC h/w failure event */ + BFA_ITNIM_SM_QRESUME = 9, /* queue space available */ +}; + +static void bfa_itnim_sm_uninit(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_created(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_fwcreate(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_delete_pending(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_online(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_sler(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_cleanup_offline(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_cleanup_delete(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_fwdelete(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_offline(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_iocdisable(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_deleting(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_fwcreate_qfull(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_fwdelete_qfull(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); +static void bfa_itnim_sm_deleting_qfull(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event); + +/** + * Beginning/unallocated state - no events expected. + */ +static void +bfa_itnim_sm_uninit(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_CREATE: + bfa_sm_set_state(itnim, bfa_itnim_sm_created); + itnim->is_online = BFA_FALSE; + bfa_fcpim_additn(itnim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Beginning state, only online event expected. + */ +static void +bfa_itnim_sm_created(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_ONLINE: + if (bfa_itnim_send_fwcreate(itnim)) + bfa_sm_set_state(itnim, bfa_itnim_sm_fwcreate); + else + bfa_sm_set_state(itnim, bfa_itnim_sm_fwcreate_qfull); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + bfa_fcpim_delitn(itnim); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + break; + + default: + bfa_assert(0); + } +} + +/** + * Waiting for itnim create response from firmware. + */ +static void +bfa_itnim_sm_fwcreate(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_FWRSP: + bfa_sm_set_state(itnim, bfa_itnim_sm_online); + itnim->is_online = BFA_TRUE; + bfa_itnim_iotov_online(itnim); + bfa_itnim_online_cb(itnim); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_delete_pending); + break; + + case BFA_ITNIM_SM_OFFLINE: + if (bfa_itnim_send_fwdelete(itnim)) + bfa_sm_set_state(itnim, bfa_itnim_sm_fwdelete); + else + bfa_sm_set_state(itnim, bfa_itnim_sm_fwdelete_qfull); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_itnim_sm_fwcreate_qfull(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_QRESUME: + bfa_sm_set_state(itnim, bfa_itnim_sm_fwcreate); + bfa_itnim_send_fwcreate(itnim); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + bfa_reqq_wcancel(&itnim->reqq_wait); + bfa_fcpim_delitn(itnim); + break; + + case BFA_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_itnim_sm_offline); + bfa_reqq_wcancel(&itnim->reqq_wait); + bfa_itnim_offline_cb(itnim); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + bfa_reqq_wcancel(&itnim->reqq_wait); + break; + + default: + bfa_assert(0); + } +} + +/** + * Waiting for itnim create response from firmware, a delete is pending. + */ +static void +bfa_itnim_sm_delete_pending(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_FWRSP: + if (bfa_itnim_send_fwdelete(itnim)) + bfa_sm_set_state(itnim, bfa_itnim_sm_deleting); + else + bfa_sm_set_state(itnim, bfa_itnim_sm_deleting_qfull); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + bfa_fcpim_delitn(itnim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Online state - normal parking state. + */ +static void +bfa_itnim_sm_online(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_itnim_sm_cleanup_offline); + itnim->is_online = BFA_FALSE; + bfa_itnim_iotov_start(itnim); + bfa_itnim_cleanup(itnim); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_cleanup_delete); + itnim->is_online = BFA_FALSE; + bfa_itnim_cleanup(itnim); + break; + + case BFA_ITNIM_SM_SLER: + bfa_sm_set_state(itnim, bfa_itnim_sm_sler); + itnim->is_online = BFA_FALSE; + bfa_itnim_iotov_start(itnim); + bfa_itnim_sler_cb(itnim); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + itnim->is_online = BFA_FALSE; + bfa_itnim_iotov_start(itnim); + bfa_itnim_iocdisable_cleanup(itnim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Second level error recovery need. + */ +static void +bfa_itnim_sm_sler(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_itnim_sm_cleanup_offline); + bfa_itnim_cleanup(itnim); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_cleanup_delete); + bfa_itnim_cleanup(itnim); + bfa_itnim_iotov_delete(itnim); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + bfa_itnim_iocdisable_cleanup(itnim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Going offline. Waiting for active IO cleanup. + */ +static void +bfa_itnim_sm_cleanup_offline(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_CLEANUP: + if (bfa_itnim_send_fwdelete(itnim)) + bfa_sm_set_state(itnim, bfa_itnim_sm_fwdelete); + else + bfa_sm_set_state(itnim, bfa_itnim_sm_fwdelete_qfull); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_cleanup_delete); + bfa_itnim_iotov_delete(itnim); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + bfa_itnim_iocdisable_cleanup(itnim); + bfa_itnim_offline_cb(itnim); + break; + + case BFA_ITNIM_SM_SLER: + break; + + default: + bfa_assert(0); + } +} + +/** + * Deleting itnim. Waiting for active IO cleanup. + */ +static void +bfa_itnim_sm_cleanup_delete(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_CLEANUP: + if (bfa_itnim_send_fwdelete(itnim)) + bfa_sm_set_state(itnim, bfa_itnim_sm_deleting); + else + bfa_sm_set_state(itnim, bfa_itnim_sm_deleting_qfull); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + bfa_itnim_iocdisable_cleanup(itnim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport offline. Fimrware itnim is being deleted - awaiting f/w response. + */ +static void +bfa_itnim_sm_fwdelete(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_FWRSP: + bfa_sm_set_state(itnim, bfa_itnim_sm_offline); + bfa_itnim_offline_cb(itnim); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_deleting); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + bfa_itnim_offline_cb(itnim); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_itnim_sm_fwdelete_qfull(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_QRESUME: + bfa_sm_set_state(itnim, bfa_itnim_sm_fwdelete); + bfa_itnim_send_fwdelete(itnim); + break; + + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_deleting_qfull); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + bfa_reqq_wcancel(&itnim->reqq_wait); + bfa_itnim_offline_cb(itnim); + break; + + default: + bfa_assert(0); + } +} + +/** + * Offline state. + */ +static void +bfa_itnim_sm_offline(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + bfa_itnim_iotov_delete(itnim); + bfa_fcpim_delitn(itnim); + break; + + case BFA_ITNIM_SM_ONLINE: + if (bfa_itnim_send_fwcreate(itnim)) + bfa_sm_set_state(itnim, bfa_itnim_sm_fwcreate); + else + bfa_sm_set_state(itnim, bfa_itnim_sm_fwcreate_qfull); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_iocdisable); + break; + + default: + bfa_assert(0); + } +} + +/** + * IOC h/w failed state. + */ +static void +bfa_itnim_sm_iocdisable(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + bfa_itnim_iotov_delete(itnim); + bfa_fcpim_delitn(itnim); + break; + + case BFA_ITNIM_SM_OFFLINE: + bfa_itnim_offline_cb(itnim); + break; + + case BFA_ITNIM_SM_ONLINE: + if (bfa_itnim_send_fwcreate(itnim)) + bfa_sm_set_state(itnim, bfa_itnim_sm_fwcreate); + else + bfa_sm_set_state(itnim, bfa_itnim_sm_fwcreate_qfull); + break; + + case BFA_ITNIM_SM_HWFAIL: + break; + + default: + bfa_assert(0); + } +} + +/** + * Itnim is deleted, waiting for firmware response to delete. + */ +static void +bfa_itnim_sm_deleting(struct bfa_itnim_s *itnim, enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_FWRSP: + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + bfa_fcpim_delitn(itnim); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_itnim_sm_deleting_qfull(struct bfa_itnim_s *itnim, + enum bfa_itnim_event event) +{ + bfa_trc(itnim->bfa, itnim->rport->rport_tag); + bfa_trc(itnim->bfa, event); + + switch (event) { + case BFA_ITNIM_SM_QRESUME: + bfa_sm_set_state(itnim, bfa_itnim_sm_deleting); + bfa_itnim_send_fwdelete(itnim); + break; + + case BFA_ITNIM_SM_HWFAIL: + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + bfa_reqq_wcancel(&itnim->reqq_wait); + bfa_fcpim_delitn(itnim); + break; + + default: + bfa_assert(0); + } +} + + + +/** + * bfa_itnim_private + */ + +/** + * Initiate cleanup of all IOs on an IOC failure. + */ +static void +bfa_itnim_iocdisable_cleanup(struct bfa_itnim_s *itnim) +{ + struct bfa_tskim_s *tskim; + struct bfa_ioim_s *ioim; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &itnim->tsk_q) { + tskim = (struct bfa_tskim_s *) qe; + bfa_tskim_iocdisable(tskim); + } + + list_for_each_safe(qe, qen, &itnim->io_q) { + ioim = (struct bfa_ioim_s *) qe; + bfa_ioim_iocdisable(ioim); + } + + /** + * For IO request in pending queue, we pretend an early timeout. + */ + list_for_each_safe(qe, qen, &itnim->pending_q) { + ioim = (struct bfa_ioim_s *) qe; + bfa_ioim_tov(ioim); + } + + list_for_each_safe(qe, qen, &itnim->io_cleanup_q) { + ioim = (struct bfa_ioim_s *) qe; + bfa_ioim_iocdisable(ioim); + } +} + +/** + * IO cleanup completion + */ +static void +bfa_itnim_cleanp_comp(void *itnim_cbarg) +{ + struct bfa_itnim_s *itnim = itnim_cbarg; + + bfa_stats(itnim, cleanup_comps); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_CLEANUP); +} + +/** + * Initiate cleanup of all IOs. + */ +static void +bfa_itnim_cleanup(struct bfa_itnim_s *itnim) +{ + struct bfa_ioim_s *ioim; + struct bfa_tskim_s *tskim; + struct list_head *qe, *qen; + + bfa_wc_init(&itnim->wc, bfa_itnim_cleanp_comp, itnim); + + list_for_each_safe(qe, qen, &itnim->io_q) { + ioim = (struct bfa_ioim_s *) qe; + + /** + * Move IO to a cleanup queue from active queue so that a later + * TM will not pickup this IO. + */ + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &itnim->io_cleanup_q); + + bfa_wc_up(&itnim->wc); + bfa_ioim_cleanup(ioim); + } + + list_for_each_safe(qe, qen, &itnim->tsk_q) { + tskim = (struct bfa_tskim_s *) qe; + bfa_wc_up(&itnim->wc); + bfa_tskim_cleanup(tskim); + } + + bfa_wc_wait(&itnim->wc); +} + +static void +__bfa_cb_itnim_online(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_itnim_s *itnim = cbarg; + + if (complete) + bfa_cb_itnim_online(itnim->ditn); +} + +static void +__bfa_cb_itnim_offline(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_itnim_s *itnim = cbarg; + + if (complete) + bfa_cb_itnim_offline(itnim->ditn); +} + +static void +__bfa_cb_itnim_sler(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_itnim_s *itnim = cbarg; + + if (complete) + bfa_cb_itnim_sler(itnim->ditn); +} + +/** + * Call to resume any I/O requests waiting for room in request queue. + */ +static void +bfa_itnim_qresume(void *cbarg) +{ + struct bfa_itnim_s *itnim = cbarg; + + bfa_sm_send_event(itnim, BFA_ITNIM_SM_QRESUME); +} + + + + +/** + * bfa_itnim_public + */ + +void +bfa_itnim_iodone(struct bfa_itnim_s *itnim) +{ + bfa_wc_down(&itnim->wc); +} + +void +bfa_itnim_tskdone(struct bfa_itnim_s *itnim) +{ + bfa_wc_down(&itnim->wc); +} + +void +bfa_itnim_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len) +{ + /** + * ITN memory + */ + *km_len += cfg->fwcfg.num_rports * sizeof(struct bfa_itnim_s); +} + +void +bfa_itnim_attach(struct bfa_fcpim_mod_s *fcpim, struct bfa_meminfo_s *minfo) +{ + struct bfa_s *bfa = fcpim->bfa; + struct bfa_itnim_s *itnim; + int i; + + INIT_LIST_HEAD(&fcpim->itnim_q); + + itnim = (struct bfa_itnim_s *) bfa_meminfo_kva(minfo); + fcpim->itnim_arr = itnim; + + for (i = 0; i < fcpim->num_itnims; i++, itnim++) { + bfa_os_memset(itnim, 0, sizeof(struct bfa_itnim_s)); + itnim->bfa = bfa; + itnim->fcpim = fcpim; + itnim->reqq = BFA_REQQ_QOS_LO; + itnim->rport = BFA_RPORT_FROM_TAG(bfa, i); + itnim->iotov_active = BFA_FALSE; + bfa_reqq_winit(&itnim->reqq_wait, bfa_itnim_qresume, itnim); + + INIT_LIST_HEAD(&itnim->io_q); + INIT_LIST_HEAD(&itnim->io_cleanup_q); + INIT_LIST_HEAD(&itnim->pending_q); + INIT_LIST_HEAD(&itnim->tsk_q); + INIT_LIST_HEAD(&itnim->delay_comp_q); + bfa_sm_set_state(itnim, bfa_itnim_sm_uninit); + } + + bfa_meminfo_kva(minfo) = (u8 *) itnim; +} + +void +bfa_itnim_iocdisable(struct bfa_itnim_s *itnim) +{ + bfa_stats(itnim, ioc_disabled); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_HWFAIL); +} + +static bfa_boolean_t +bfa_itnim_send_fwcreate(struct bfa_itnim_s *itnim) +{ + struct bfi_itnim_create_req_s *m; + + itnim->msg_no++; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(itnim->bfa, itnim->reqq); + if (!m) { + bfa_reqq_wait(itnim->bfa, itnim->reqq, &itnim->reqq_wait); + return BFA_FALSE; + } + + bfi_h2i_set(m->mh, BFI_MC_ITNIM, BFI_ITNIM_H2I_CREATE_REQ, + bfa_lpuid(itnim->bfa)); + m->fw_handle = itnim->rport->fw_handle; + m->class = FC_CLASS_3; + m->seq_rec = itnim->seq_rec; + m->msg_no = itnim->msg_no; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(itnim->bfa, itnim->reqq); + return BFA_TRUE; +} + +static bfa_boolean_t +bfa_itnim_send_fwdelete(struct bfa_itnim_s *itnim) +{ + struct bfi_itnim_delete_req_s *m; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(itnim->bfa, itnim->reqq); + if (!m) { + bfa_reqq_wait(itnim->bfa, itnim->reqq, &itnim->reqq_wait); + return BFA_FALSE; + } + + bfi_h2i_set(m->mh, BFI_MC_ITNIM, BFI_ITNIM_H2I_DELETE_REQ, + bfa_lpuid(itnim->bfa)); + m->fw_handle = itnim->rport->fw_handle; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(itnim->bfa, itnim->reqq); + return BFA_TRUE; +} + +/** + * Cleanup all pending failed inflight requests. + */ +static void +bfa_itnim_delayed_comp(struct bfa_itnim_s *itnim, bfa_boolean_t iotov) +{ + struct bfa_ioim_s *ioim; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &itnim->delay_comp_q) { + ioim = (struct bfa_ioim_s *)qe; + bfa_ioim_delayed_comp(ioim, iotov); + } +} + +/** + * Start all pending IO requests. + */ +static void +bfa_itnim_iotov_online(struct bfa_itnim_s *itnim) +{ + struct bfa_ioim_s *ioim; + + bfa_itnim_iotov_stop(itnim); + + /** + * Abort all inflight IO requests in the queue + */ + bfa_itnim_delayed_comp(itnim, BFA_FALSE); + + /** + * Start all pending IO requests. + */ + while (!list_empty(&itnim->pending_q)) { + bfa_q_deq(&itnim->pending_q, &ioim); + list_add_tail(&ioim->qe, &itnim->io_q); + bfa_ioim_start(ioim); + } +} + +/** + * Fail all pending IO requests + */ +static void +bfa_itnim_iotov_cleanup(struct bfa_itnim_s *itnim) +{ + struct bfa_ioim_s *ioim; + + /** + * Fail all inflight IO requests in the queue + */ + bfa_itnim_delayed_comp(itnim, BFA_TRUE); + + /** + * Fail any pending IO requests. + */ + while (!list_empty(&itnim->pending_q)) { + bfa_q_deq(&itnim->pending_q, &ioim); + list_add_tail(&ioim->qe, &ioim->fcpim->ioim_comp_q); + bfa_ioim_tov(ioim); + } +} + +/** + * IO TOV timer callback. Fail any pending IO requests. + */ +static void +bfa_itnim_iotov(void *itnim_arg) +{ + struct bfa_itnim_s *itnim = itnim_arg; + + itnim->iotov_active = BFA_FALSE; + + bfa_cb_itnim_tov_begin(itnim->ditn); + bfa_itnim_iotov_cleanup(itnim); + bfa_cb_itnim_tov(itnim->ditn); +} + +/** + * Start IO TOV timer for failing back pending IO requests in offline state. + */ +static void +bfa_itnim_iotov_start(struct bfa_itnim_s *itnim) +{ + if (itnim->fcpim->path_tov > 0) { + + itnim->iotov_active = BFA_TRUE; + bfa_assert(bfa_itnim_hold_io(itnim)); + bfa_timer_start(itnim->bfa, &itnim->timer, + bfa_itnim_iotov, itnim, itnim->fcpim->path_tov); + } +} + +/** + * Stop IO TOV timer. + */ +static void +bfa_itnim_iotov_stop(struct bfa_itnim_s *itnim) +{ + if (itnim->iotov_active) { + itnim->iotov_active = BFA_FALSE; + bfa_timer_stop(&itnim->timer); + } +} + +/** + * Stop IO TOV timer. + */ +static void +bfa_itnim_iotov_delete(struct bfa_itnim_s *itnim) +{ + bfa_boolean_t pathtov_active = BFA_FALSE; + + if (itnim->iotov_active) + pathtov_active = BFA_TRUE; + + bfa_itnim_iotov_stop(itnim); + if (pathtov_active) + bfa_cb_itnim_tov_begin(itnim->ditn); + bfa_itnim_iotov_cleanup(itnim); + if (pathtov_active) + bfa_cb_itnim_tov(itnim->ditn); +} + + + +/** + * bfa_itnim_public + */ + +/** + * Itnim interrupt processing. + */ +void +bfa_itnim_isr(struct bfa_s *bfa, struct bfi_msg_s *m) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + union bfi_itnim_i2h_msg_u msg; + struct bfa_itnim_s *itnim; + + bfa_trc(bfa, m->mhdr.msg_id); + + msg.msg = m; + + switch (m->mhdr.msg_id) { + case BFI_ITNIM_I2H_CREATE_RSP: + itnim = BFA_ITNIM_FROM_TAG(fcpim, + msg.create_rsp->bfa_handle); + bfa_assert(msg.create_rsp->status == BFA_STATUS_OK); + bfa_stats(itnim, create_comps); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_FWRSP); + break; + + case BFI_ITNIM_I2H_DELETE_RSP: + itnim = BFA_ITNIM_FROM_TAG(fcpim, + msg.delete_rsp->bfa_handle); + bfa_assert(msg.delete_rsp->status == BFA_STATUS_OK); + bfa_stats(itnim, delete_comps); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_FWRSP); + break; + + case BFI_ITNIM_I2H_SLER_EVENT: + itnim = BFA_ITNIM_FROM_TAG(fcpim, + msg.sler_event->bfa_handle); + bfa_stats(itnim, sler_events); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_SLER); + break; + + default: + bfa_trc(bfa, m->mhdr.msg_id); + bfa_assert(0); + } +} + + + +/** + * bfa_itnim_api + */ + +struct bfa_itnim_s * +bfa_itnim_create(struct bfa_s *bfa, struct bfa_rport_s *rport, void *ditn) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + struct bfa_itnim_s *itnim; + + itnim = BFA_ITNIM_FROM_TAG(fcpim, rport->rport_tag); + bfa_assert(itnim->rport == rport); + + itnim->ditn = ditn; + + bfa_stats(itnim, creates); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_CREATE); + + return (itnim); +} + +void +bfa_itnim_delete(struct bfa_itnim_s *itnim) +{ + bfa_stats(itnim, deletes); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_DELETE); +} + +void +bfa_itnim_online(struct bfa_itnim_s *itnim, bfa_boolean_t seq_rec) +{ + itnim->seq_rec = seq_rec; + bfa_stats(itnim, onlines); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_ONLINE); +} + +void +bfa_itnim_offline(struct bfa_itnim_s *itnim) +{ + bfa_stats(itnim, offlines); + bfa_sm_send_event(itnim, BFA_ITNIM_SM_OFFLINE); +} + +/** + * Return true if itnim is considered offline for holding off IO request. + * IO is not held if itnim is being deleted. + */ +bfa_boolean_t +bfa_itnim_hold_io(struct bfa_itnim_s *itnim) +{ + return ( + itnim->fcpim->path_tov && itnim->iotov_active && + (bfa_sm_cmp_state(itnim, bfa_itnim_sm_fwcreate) || + bfa_sm_cmp_state(itnim, bfa_itnim_sm_sler) || + bfa_sm_cmp_state(itnim, bfa_itnim_sm_cleanup_offline) || + bfa_sm_cmp_state(itnim, bfa_itnim_sm_fwdelete) || + bfa_sm_cmp_state(itnim, bfa_itnim_sm_offline) || + bfa_sm_cmp_state(itnim, bfa_itnim_sm_iocdisable)) +); +} + +void +bfa_itnim_get_stats(struct bfa_itnim_s *itnim, + struct bfa_itnim_hal_stats_s *stats) +{ + *stats = itnim->stats; +} + +void +bfa_itnim_clear_stats(struct bfa_itnim_s *itnim) +{ + bfa_os_memset(&itnim->stats, 0, sizeof(itnim->stats)); +} + + diff --git a/drivers/scsi/bfa/bfa_log.c b/drivers/scsi/bfa/bfa_log.c new file mode 100644 index 000000000000..c2735e55cf03 --- /dev/null +++ b/drivers/scsi/bfa/bfa_log.c @@ -0,0 +1,346 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_log.c BFA log library + */ + +#include <bfa_os_inc.h> +#include <cs/bfa_log.h> + +/* + * global log info structure + */ +struct bfa_log_info_s { + u32 start_idx; /* start index for a module */ + u32 total_count; /* total count for a module */ + enum bfa_log_severity level; /* global log level */ + bfa_log_cb_t cbfn; /* callback function */ +}; + +static struct bfa_log_info_s bfa_log_info[BFA_LOG_MODULE_ID_MAX + 1]; +static u32 bfa_log_msg_total_count; +static int bfa_log_initialized; + +static char *bfa_log_severity[] = + { "[none]", "[critical]", "[error]", "[warn]", "[info]", "" }; + +/** + * BFA log library initialization + * + * The log library initialization includes the following, + * - set log instance name and callback function + * - read the message array generated from xml files + * - calculate start index for each module + * - calculate message count for each module + * - perform error checking + * + * @param[in] log_mod - log module info + * @param[in] instance_name - instance name + * @param[in] cbfn - callback function + * + * It return 0 on success, or -1 on failure + */ +int +bfa_log_init(struct bfa_log_mod_s *log_mod, char *instance_name, + bfa_log_cb_t cbfn) +{ + struct bfa_log_msgdef_s *msg; + u32 pre_mod_id = 0; + u32 cur_mod_id = 0; + u32 i, pre_idx, idx, msg_id; + + /* + * set instance name + */ + if (log_mod) { + strncpy(log_mod->instance_info, instance_name, + sizeof(log_mod->instance_info)); + log_mod->cbfn = cbfn; + for (i = 0; i <= BFA_LOG_MODULE_ID_MAX; i++) + log_mod->log_level[i] = BFA_LOG_WARNING; + } + + if (bfa_log_initialized) + return 0; + + for (i = 0; i <= BFA_LOG_MODULE_ID_MAX; i++) { + bfa_log_info[i].start_idx = 0; + bfa_log_info[i].total_count = 0; + bfa_log_info[i].level = BFA_LOG_WARNING; + bfa_log_info[i].cbfn = cbfn; + } + + pre_idx = 0; + idx = 0; + msg = bfa_log_msg_array; + msg_id = BFA_LOG_GET_MSG_ID(msg); + pre_mod_id = BFA_LOG_GET_MOD_ID(msg_id); + while (msg_id != 0) { + cur_mod_id = BFA_LOG_GET_MOD_ID(msg_id); + + if (cur_mod_id > BFA_LOG_MODULE_ID_MAX) { + cbfn(log_mod, msg_id, + "%s%s log: module id %u out of range\n", + BFA_LOG_CAT_NAME, + bfa_log_severity[BFA_LOG_ERROR], + cur_mod_id); + return -1; + } + + if (pre_mod_id > BFA_LOG_MODULE_ID_MAX) { + cbfn(log_mod, msg_id, + "%s%s log: module id %u out of range\n", + BFA_LOG_CAT_NAME, + bfa_log_severity[BFA_LOG_ERROR], + pre_mod_id); + return -1; + } + + if (cur_mod_id != pre_mod_id) { + bfa_log_info[pre_mod_id].start_idx = pre_idx; + bfa_log_info[pre_mod_id].total_count = idx - pre_idx; + pre_mod_id = cur_mod_id; + pre_idx = idx; + } + + idx++; + msg++; + msg_id = BFA_LOG_GET_MSG_ID(msg); + } + + bfa_log_info[cur_mod_id].start_idx = pre_idx; + bfa_log_info[cur_mod_id].total_count = idx - pre_idx; + bfa_log_msg_total_count = idx; + + cbfn(log_mod, msg_id, "%s%s log: init OK, msg total count %u\n", + BFA_LOG_CAT_NAME, + bfa_log_severity[BFA_LOG_INFO], bfa_log_msg_total_count); + + bfa_log_initialized = 1; + + return 0; +} + +/** + * BFA log set log level for a module + * + * @param[in] log_mod - log module info + * @param[in] mod_id - module id + * @param[in] log_level - log severity level + * + * It return BFA_STATUS_OK on success, or > 0 on failure + */ +bfa_status_t +bfa_log_set_level(struct bfa_log_mod_s *log_mod, int mod_id, + enum bfa_log_severity log_level) +{ + if (mod_id <= BFA_LOG_UNUSED_ID || mod_id > BFA_LOG_MODULE_ID_MAX) + return BFA_STATUS_EINVAL; + + if (log_level <= BFA_LOG_INVALID || log_level > BFA_LOG_LEVEL_MAX) + return BFA_STATUS_EINVAL; + + if (log_mod) + log_mod->log_level[mod_id] = log_level; + else + bfa_log_info[mod_id].level = log_level; + + return BFA_STATUS_OK; +} + +/** + * BFA log set log level for all modules + * + * @param[in] log_mod - log module info + * @param[in] log_level - log severity level + * + * It return BFA_STATUS_OK on success, or > 0 on failure + */ +bfa_status_t +bfa_log_set_level_all(struct bfa_log_mod_s *log_mod, + enum bfa_log_severity log_level) +{ + int mod_id = BFA_LOG_UNUSED_ID + 1; + + if (log_level <= BFA_LOG_INVALID || log_level > BFA_LOG_LEVEL_MAX) + return BFA_STATUS_EINVAL; + + if (log_mod) { + for (; mod_id <= BFA_LOG_MODULE_ID_MAX; mod_id++) + log_mod->log_level[mod_id] = log_level; + } else { + for (; mod_id <= BFA_LOG_MODULE_ID_MAX; mod_id++) + bfa_log_info[mod_id].level = log_level; + } + + return BFA_STATUS_OK; +} + +/** + * BFA log set log level for all aen sub-modules + * + * @param[in] log_mod - log module info + * @param[in] log_level - log severity level + * + * It return BFA_STATUS_OK on success, or > 0 on failure + */ +bfa_status_t +bfa_log_set_level_aen(struct bfa_log_mod_s *log_mod, + enum bfa_log_severity log_level) +{ + int mod_id = BFA_LOG_AEN_MIN + 1; + + if (log_mod) { + for (; mod_id <= BFA_LOG_AEN_MAX; mod_id++) + log_mod->log_level[mod_id] = log_level; + } else { + for (; mod_id <= BFA_LOG_AEN_MAX; mod_id++) + bfa_log_info[mod_id].level = log_level; + } + + return BFA_STATUS_OK; +} + +/** + * BFA log get log level for a module + * + * @param[in] log_mod - log module info + * @param[in] mod_id - module id + * + * It returns log level or -1 on error + */ +enum bfa_log_severity +bfa_log_get_level(struct bfa_log_mod_s *log_mod, int mod_id) +{ + if (mod_id <= BFA_LOG_UNUSED_ID || mod_id > BFA_LOG_MODULE_ID_MAX) + return BFA_LOG_INVALID; + + if (log_mod) + return (log_mod->log_level[mod_id]); + else + return (bfa_log_info[mod_id].level); +} + +enum bfa_log_severity +bfa_log_get_msg_level(struct bfa_log_mod_s *log_mod, u32 msg_id) +{ + struct bfa_log_msgdef_s *msg; + u32 mod = BFA_LOG_GET_MOD_ID(msg_id); + u32 idx = BFA_LOG_GET_MSG_IDX(msg_id) - 1; + + if (!bfa_log_initialized) + return BFA_LOG_INVALID; + + if (mod > BFA_LOG_MODULE_ID_MAX) + return BFA_LOG_INVALID; + + if (idx >= bfa_log_info[mod].total_count) { + bfa_log_info[mod].cbfn(log_mod, msg_id, + "%s%s log: inconsistent idx %u vs. total count %u\n", + BFA_LOG_CAT_NAME, bfa_log_severity[BFA_LOG_ERROR], idx, + bfa_log_info[mod].total_count); + return BFA_LOG_INVALID; + } + + msg = bfa_log_msg_array + bfa_log_info[mod].start_idx + idx; + if (msg_id != BFA_LOG_GET_MSG_ID(msg)) { + bfa_log_info[mod].cbfn(log_mod, msg_id, + "%s%s log: inconsistent msg id %u array msg id %u\n", + BFA_LOG_CAT_NAME, bfa_log_severity[BFA_LOG_ERROR], + msg_id, BFA_LOG_GET_MSG_ID(msg)); + return BFA_LOG_INVALID; + } + + return BFA_LOG_GET_SEVERITY(msg); +} + +/** + * BFA log message handling + * + * BFA log message handling finds the message based on message id and prints + * out the message based on its format and arguments. It also does prefix + * the severity etc. + * + * @param[in] log_mod - log module info + * @param[in] msg_id - message id + * @param[in] ... - message arguments + * + * It return 0 on success, or -1 on errors + */ +int +bfa_log(struct bfa_log_mod_s *log_mod, u32 msg_id, ...) +{ + va_list ap; + char buf[256]; + struct bfa_log_msgdef_s *msg; + int log_level; + u32 mod = BFA_LOG_GET_MOD_ID(msg_id); + u32 idx = BFA_LOG_GET_MSG_IDX(msg_id) - 1; + + if (!bfa_log_initialized) + return -1; + + if (mod > BFA_LOG_MODULE_ID_MAX) + return -1; + + if (idx >= bfa_log_info[mod].total_count) { + bfa_log_info[mod]. + cbfn + (log_mod, msg_id, + "%s%s log: inconsistent idx %u vs. total count %u\n", + BFA_LOG_CAT_NAME, bfa_log_severity[BFA_LOG_ERROR], idx, + bfa_log_info[mod].total_count); + return -1; + } + + msg = bfa_log_msg_array + bfa_log_info[mod].start_idx + idx; + if (msg_id != BFA_LOG_GET_MSG_ID(msg)) { + bfa_log_info[mod]. + cbfn + (log_mod, msg_id, + "%s%s log: inconsistent msg id %u array msg id %u\n", + BFA_LOG_CAT_NAME, bfa_log_severity[BFA_LOG_ERROR], + msg_id, BFA_LOG_GET_MSG_ID(msg)); + return -1; + } + + log_level = log_mod ? log_mod->log_level[mod] : bfa_log_info[mod].level; + if ((BFA_LOG_GET_SEVERITY(msg) > log_level) && + (msg->attributes != BFA_LOG_ATTR_NONE)) + return 0; + + va_start(ap, msg_id); + bfa_os_vsprintf(buf, BFA_LOG_GET_MSG_FMT_STRING(msg), ap); + va_end(ap); + + if (log_mod) + log_mod->cbfn(log_mod, msg_id, "%s[%s]%s%s %s: %s\n", + BFA_LOG_CAT_NAME, log_mod->instance_info, + bfa_log_severity[BFA_LOG_GET_SEVERITY(msg)], + (msg->attributes & BFA_LOG_ATTR_AUDIT) + ? " (audit) " : "", msg->msg_value, buf); + else + bfa_log_info[mod].cbfn(log_mod, msg_id, "%s%s%s %s: %s\n", + BFA_LOG_CAT_NAME, + bfa_log_severity[BFA_LOG_GET_SEVERITY(msg)], + (msg->attributes & BFA_LOG_ATTR_AUDIT) ? + " (audit) " : "", msg->msg_value, buf); + + return 0; +} + diff --git a/drivers/scsi/bfa/bfa_log_module.c b/drivers/scsi/bfa/bfa_log_module.c new file mode 100644 index 000000000000..5c154d341d69 --- /dev/null +++ b/drivers/scsi/bfa/bfa_log_module.c @@ -0,0 +1,451 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <cs/bfa_log.h> +#include <aen/bfa_aen_adapter.h> +#include <aen/bfa_aen_audit.h> +#include <aen/bfa_aen_ethport.h> +#include <aen/bfa_aen_ioc.h> +#include <aen/bfa_aen_itnim.h> +#include <aen/bfa_aen_lport.h> +#include <aen/bfa_aen_port.h> +#include <aen/bfa_aen_rport.h> +#include <log/bfa_log_fcs.h> +#include <log/bfa_log_hal.h> +#include <log/bfa_log_linux.h> +#include <log/bfa_log_wdrv.h> + +struct bfa_log_msgdef_s bfa_log_msg_array[] = { + + +/* messages define for BFA_AEN_CAT_ADAPTER Module */ +{BFA_AEN_ADAPTER_ADD, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_ADAPTER_ADD", + "New adapter found: SN = %s, base port WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_ADAPTER_REMOVE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_ADAPTER_REMOVE", + "Adapter removed: SN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + + + + +/* messages define for BFA_AEN_CAT_AUDIT Module */ +{BFA_AEN_AUDIT_AUTH_ENABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "BFA_AEN_AUDIT_AUTH_ENABLE", + "Authentication enabled for base port: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_AUDIT_AUTH_DISABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "BFA_AEN_AUDIT_AUTH_DISABLE", + "Authentication disabled for base port: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + + + + +/* messages define for BFA_AEN_CAT_ETHPORT Module */ +{BFA_AEN_ETHPORT_LINKUP, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_ETHPORT_LINKUP", + "Base port ethernet linkup: mac = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_ETHPORT_LINKDOWN, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_ETHPORT_LINKDOWN", + "Base port ethernet linkdown: mac = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_ETHPORT_ENABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_ETHPORT_ENABLE", + "Base port ethernet interface enabled: mac = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_ETHPORT_DISABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_ETHPORT_DISABLE", + "Base port ethernet interface disabled: mac = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + + + + +/* messages define for BFA_AEN_CAT_IOC Module */ +{BFA_AEN_IOC_HBGOOD, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_IOC_HBGOOD", + "Heart Beat of IOC %d is good.", + ((BFA_LOG_D << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_IOC_HBFAIL, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_CRITICAL, + "BFA_AEN_IOC_HBFAIL", + "Heart Beat of IOC %d has failed.", + ((BFA_LOG_D << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_IOC_ENABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_IOC_ENABLE", + "IOC %d is enabled.", + ((BFA_LOG_D << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_IOC_DISABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_IOC_DISABLE", + "IOC %d is disabled.", + ((BFA_LOG_D << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_IOC_FWMISMATCH, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_CRITICAL, "BFA_AEN_IOC_FWMISMATCH", + "Running firmware version is incompatible with the driver version.", + (0), 0}, + + + + +/* messages define for BFA_AEN_CAT_ITNIM Module */ +{BFA_AEN_ITNIM_ONLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_ITNIM_ONLINE", + "Target (WWN = %s) is online for initiator (WWN = %s).", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_ITNIM_OFFLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_ITNIM_OFFLINE", + "Target (WWN = %s) offlined by initiator (WWN = %s).", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_ITNIM_DISCONNECT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_ERROR, "BFA_AEN_ITNIM_DISCONNECT", + "Target (WWN = %s) connectivity lost for initiator (WWN = %s).", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + + + + +/* messages define for BFA_AEN_CAT_LPORT Module */ +{BFA_AEN_LPORT_NEW, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_LPORT_NEW", + "New logical port created: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_DELETE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_LPORT_DELETE", + "Logical port deleted: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_ONLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_LPORT_ONLINE", + "Logical port online: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_OFFLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_LPORT_OFFLINE", + "Logical port taken offline: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_DISCONNECT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_ERROR, "BFA_AEN_LPORT_DISCONNECT", + "Logical port lost fabric connectivity: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_NEW_PROP, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_LPORT_NEW_PROP", + "New virtual port created using proprietary interface: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_DELETE_PROP, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "BFA_AEN_LPORT_DELETE_PROP", + "Virtual port deleted using proprietary interface: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_NEW_STANDARD, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "BFA_AEN_LPORT_NEW_STANDARD", + "New virtual port created using standard interface: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_DELETE_STANDARD, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "BFA_AEN_LPORT_DELETE_STANDARD", + "Virtual port deleted using standard interface: WWN = %s, Role = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_LPORT_NPIV_DUP_WWN, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_LPORT_NPIV_DUP_WWN", + "Virtual port login failed. Duplicate WWN = %s reported by fabric.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_LPORT_NPIV_FABRIC_MAX, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_LPORT_NPIV_FABRIC_MAX", + "Virtual port (WWN = %s) login failed. Max NPIV ports already exist in" + " fabric/fport.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_LPORT_NPIV_UNKNOWN, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_LPORT_NPIV_UNKNOWN", + "Virtual port (WWN = %s) login failed.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + + + + +/* messages define for BFA_AEN_CAT_PORT Module */ +{BFA_AEN_PORT_ONLINE, BFA_LOG_ATTR_NONE, BFA_LOG_INFO, "BFA_AEN_PORT_ONLINE", + "Base port online: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_OFFLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_WARNING, + "BFA_AEN_PORT_OFFLINE", + "Base port offline: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_RLIR, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_PORT_RLIR", + "RLIR event not supported.", + (0), 0}, + +{BFA_AEN_PORT_SFP_INSERT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_PORT_SFP_INSERT", + "New SFP found: WWN/MAC = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_SFP_REMOVE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_PORT_SFP_REMOVE", + "SFP removed: WWN/MAC = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_SFP_POM, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_WARNING, + "BFA_AEN_PORT_SFP_POM", + "SFP POM level to %s: WWN/MAC = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_PORT_ENABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_PORT_ENABLE", + "Base port enabled: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_DISABLE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_PORT_DISABLE", + "Base port disabled: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_AUTH_ON, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_PORT_AUTH_ON", + "Authentication successful for base port: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_AUTH_OFF, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_ERROR, + "BFA_AEN_PORT_AUTH_OFF", + "Authentication unsuccessful for base port: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_DISCONNECT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_ERROR, + "BFA_AEN_PORT_DISCONNECT", + "Base port (WWN = %s) lost fabric connectivity.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_QOS_NEG, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_WARNING, + "BFA_AEN_PORT_QOS_NEG", + "QOS negotiation failed for base port: WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_FABRIC_NAME_CHANGE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_PORT_FABRIC_NAME_CHANGE", + "Base port WWN = %s, Fabric WWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_PORT_SFP_ACCESS_ERROR, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_PORT_SFP_ACCESS_ERROR", + "SFP access error: WWN/MAC = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_AEN_PORT_SFP_UNSUPPORT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_WARNING, "BFA_AEN_PORT_SFP_UNSUPPORT", + "Unsupported SFP found: WWN/MAC = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + + + + +/* messages define for BFA_AEN_CAT_RPORT Module */ +{BFA_AEN_RPORT_ONLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_RPORT_ONLINE", + "Remote port (WWN = %s) online for logical port (WWN = %s).", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_RPORT_OFFLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_RPORT_OFFLINE", + "Remote port (WWN = %s) offlined by logical port (WWN = %s).", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_RPORT_DISCONNECT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_ERROR, "BFA_AEN_RPORT_DISCONNECT", + "Remote port (WWN = %s) connectivity lost for logical port (WWN = %s).", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | 0), 2}, + +{BFA_AEN_RPORT_QOS_PRIO, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_RPORT_QOS_PRIO", + "QOS priority changed to %s: RPWWN = %s and LPWWN = %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | + (BFA_LOG_S << BFA_LOG_ARG2) | 0), 3}, + +{BFA_AEN_RPORT_QOS_FLOWID, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "BFA_AEN_RPORT_QOS_FLOWID", + "QOS flow ID changed to %d: RPWWN = %s and LPWWN = %s.", + ((BFA_LOG_D << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | + (BFA_LOG_S << BFA_LOG_ARG2) | 0), 3}, + + + + +/* messages define for FCS Module */ +{BFA_LOG_FCS_FABRIC_NOSWITCH, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "FCS_FABRIC_NOSWITCH", + "No switched fabric presence is detected.", + (0), 0}, + +{BFA_LOG_FCS_FABRIC_ISOLATED, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "FCS_FABRIC_ISOLATED", + "Port is isolated due to VF_ID mismatch. PWWN: %s, Port VF_ID: %04x and" + " switch port VF_ID: %04x.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_X << BFA_LOG_ARG1) | + (BFA_LOG_X << BFA_LOG_ARG2) | 0), 3}, + + + + +/* messages define for HAL Module */ +{BFA_LOG_HAL_ASSERT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_ERROR, + "HAL_ASSERT", + "Assertion failure: %s:%d: %s", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_D << BFA_LOG_ARG1) | + (BFA_LOG_S << BFA_LOG_ARG2) | 0), 3}, + +{BFA_LOG_HAL_HEARTBEAT_FAILURE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_CRITICAL, "HAL_HEARTBEAT_FAILURE", + "Firmware heartbeat failure at %d", + ((BFA_LOG_D << BFA_LOG_ARG0) | 0), 1}, + +{BFA_LOG_HAL_FCPIM_PARM_INVALID, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "HAL_FCPIM_PARM_INVALID", + "Driver configuration %s value %d is invalid. Value should be within" + " %d and %d.", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_D << BFA_LOG_ARG1) | + (BFA_LOG_D << BFA_LOG_ARG2) | (BFA_LOG_D << BFA_LOG_ARG3) | 0), 4}, + +{BFA_LOG_HAL_SM_ASSERT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_ERROR, + "HAL_SM_ASSERT", + "SM Assertion failure: %s:%d: event = %d", + ((BFA_LOG_S << BFA_LOG_ARG0) | (BFA_LOG_D << BFA_LOG_ARG1) | + (BFA_LOG_D << BFA_LOG_ARG2) | 0), 3}, + + + + +/* messages define for LINUX Module */ +{BFA_LOG_LINUX_DEVICE_CLAIMED, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_DEVICE_CLAIMED", + "bfa device at %s claimed.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_LOG_LINUX_HASH_INIT_FAILED, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_HASH_INIT_FAILED", + "Hash table initialization failure for the port %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_LOG_LINUX_SYSFS_FAILED, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_SYSFS_FAILED", + "sysfs file creation failure for the port %s.", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_LOG_LINUX_MEM_ALLOC_FAILED, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_MEM_ALLOC_FAILED", + "Memory allocation failed: %s. ", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_LOG_LINUX_DRIVER_REGISTRATION_FAILED, + BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "LINUX_DRIVER_REGISTRATION_FAILED", + "%s. ", + ((BFA_LOG_S << BFA_LOG_ARG0) | 0), 1}, + +{BFA_LOG_LINUX_ITNIM_FREE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "LINUX_ITNIM_FREE", + "scsi%d: FCID: %s WWPN: %s", + ((BFA_LOG_D << BFA_LOG_ARG0) | (BFA_LOG_S << BFA_LOG_ARG1) | + (BFA_LOG_S << BFA_LOG_ARG2) | 0), 3}, + +{BFA_LOG_LINUX_ITNIM_ONLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_ITNIM_ONLINE", + "Target: %d:0:%d FCID: %s WWPN: %s", + ((BFA_LOG_D << BFA_LOG_ARG0) | (BFA_LOG_D << BFA_LOG_ARG1) | + (BFA_LOG_S << BFA_LOG_ARG2) | (BFA_LOG_S << BFA_LOG_ARG3) | 0), 4}, + +{BFA_LOG_LINUX_ITNIM_OFFLINE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_ITNIM_OFFLINE", + "Target: %d:0:%d FCID: %s WWPN: %s", + ((BFA_LOG_D << BFA_LOG_ARG0) | (BFA_LOG_D << BFA_LOG_ARG1) | + (BFA_LOG_S << BFA_LOG_ARG2) | (BFA_LOG_S << BFA_LOG_ARG3) | 0), 4}, + +{BFA_LOG_LINUX_SCSI_HOST_FREE, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_SCSI_HOST_FREE", + "Free scsi%d", + ((BFA_LOG_D << BFA_LOG_ARG0) | 0), 1}, + +{BFA_LOG_LINUX_SCSI_ABORT, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, BFA_LOG_INFO, + "LINUX_SCSI_ABORT", + "scsi%d: abort cmnd %p, iotag %x", + ((BFA_LOG_D << BFA_LOG_ARG0) | (BFA_LOG_P << BFA_LOG_ARG1) | + (BFA_LOG_X << BFA_LOG_ARG2) | 0), 3}, + +{BFA_LOG_LINUX_SCSI_ABORT_COMP, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "LINUX_SCSI_ABORT_COMP", + "scsi%d: complete abort 0x%p, iotag 0x%x", + ((BFA_LOG_D << BFA_LOG_ARG0) | (BFA_LOG_P << BFA_LOG_ARG1) | + (BFA_LOG_X << BFA_LOG_ARG2) | 0), 3}, + + + + +/* messages define for WDRV Module */ +{BFA_LOG_WDRV_IOC_INIT_ERROR, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "WDRV_IOC_INIT_ERROR", + "IOC initialization has failed.", + (0), 0}, + +{BFA_LOG_WDRV_IOC_INTERNAL_ERROR, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "WDRV_IOC_INTERNAL_ERROR", + "IOC internal error. ", + (0), 0}, + +{BFA_LOG_WDRV_IOC_START_ERROR, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "WDRV_IOC_START_ERROR", + "IOC could not be started. ", + (0), 0}, + +{BFA_LOG_WDRV_IOC_STOP_ERROR, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "WDRV_IOC_STOP_ERROR", + "IOC could not be stopped. ", + (0), 0}, + +{BFA_LOG_WDRV_INSUFFICIENT_RESOURCES, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "WDRV_INSUFFICIENT_RESOURCES", + "Insufficient memory. ", + (0), 0}, + +{BFA_LOG_WDRV_BASE_ADDRESS_MAP_ERROR, BFA_LOG_ATTR_NONE | BFA_LOG_ATTR_LOG, + BFA_LOG_INFO, "WDRV_BASE_ADDRESS_MAP_ERROR", + "Unable to map the IOC onto the system address space. ", + (0), 0}, + + +{0, 0, 0, "", "", 0, 0}, +}; diff --git a/drivers/scsi/bfa/bfa_lps.c b/drivers/scsi/bfa/bfa_lps.c new file mode 100644 index 000000000000..9844b45412b6 --- /dev/null +++ b/drivers/scsi/bfa/bfa_lps.c @@ -0,0 +1,782 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfi/bfi_lps.h> +#include <cs/bfa_debug.h> + +BFA_TRC_FILE(HAL, LPS); +BFA_MODULE(lps); + +#define BFA_LPS_MIN_LPORTS (1) +#define BFA_LPS_MAX_LPORTS (256) + +/** + * forward declarations + */ +static void bfa_lps_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *ndm_len, + u32 *dm_len); +static void bfa_lps_attach(struct bfa_s *bfa, void *bfad, + struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, + struct bfa_pcidev_s *pcidev); +static void bfa_lps_initdone(struct bfa_s *bfa); +static void bfa_lps_detach(struct bfa_s *bfa); +static void bfa_lps_start(struct bfa_s *bfa); +static void bfa_lps_stop(struct bfa_s *bfa); +static void bfa_lps_iocdisable(struct bfa_s *bfa); +static void bfa_lps_login_rsp(struct bfa_s *bfa, + struct bfi_lps_login_rsp_s *rsp); +static void bfa_lps_logout_rsp(struct bfa_s *bfa, + struct bfi_lps_logout_rsp_s *rsp); +static void bfa_lps_reqq_resume(void *lps_arg); +static void bfa_lps_free(struct bfa_lps_s *lps); +static void bfa_lps_send_login(struct bfa_lps_s *lps); +static void bfa_lps_send_logout(struct bfa_lps_s *lps); +static void bfa_lps_login_comp(struct bfa_lps_s *lps); +static void bfa_lps_logout_comp(struct bfa_lps_s *lps); + + +/** + * lps_pvt BFA LPS private functions + */ + +enum bfa_lps_event { + BFA_LPS_SM_LOGIN = 1, /* login request from user */ + BFA_LPS_SM_LOGOUT = 2, /* logout request from user */ + BFA_LPS_SM_FWRSP = 3, /* f/w response to login/logout */ + BFA_LPS_SM_RESUME = 4, /* space present in reqq queue */ + BFA_LPS_SM_DELETE = 5, /* lps delete from user */ + BFA_LPS_SM_OFFLINE = 6, /* Link is offline */ +}; + +static void bfa_lps_sm_init(struct bfa_lps_s *lps, enum bfa_lps_event event); +static void bfa_lps_sm_login(struct bfa_lps_s *lps, enum bfa_lps_event event); +static void bfa_lps_sm_loginwait(struct bfa_lps_s *lps, + enum bfa_lps_event event); +static void bfa_lps_sm_online(struct bfa_lps_s *lps, enum bfa_lps_event event); +static void bfa_lps_sm_logout(struct bfa_lps_s *lps, enum bfa_lps_event event); +static void bfa_lps_sm_logowait(struct bfa_lps_s *lps, + enum bfa_lps_event event); + +/** + * Init state -- no login + */ +static void +bfa_lps_sm_init(struct bfa_lps_s *lps, enum bfa_lps_event event) +{ + bfa_trc(lps->bfa, lps->lp_tag); + bfa_trc(lps->bfa, event); + + switch (event) { + case BFA_LPS_SM_LOGIN: + if (bfa_reqq_full(lps->bfa, lps->reqq)) { + bfa_sm_set_state(lps, bfa_lps_sm_loginwait); + bfa_reqq_wait(lps->bfa, lps->reqq, &lps->wqe); + } else { + bfa_sm_set_state(lps, bfa_lps_sm_login); + bfa_lps_send_login(lps); + } + break; + + case BFA_LPS_SM_LOGOUT: + bfa_lps_logout_comp(lps); + break; + + case BFA_LPS_SM_DELETE: + bfa_lps_free(lps); + break; + + case BFA_LPS_SM_OFFLINE: + break; + + case BFA_LPS_SM_FWRSP: + /* Could happen when fabric detects loopback and discards + * the lps request. Fw will eventually sent out the timeout + * Just ignore + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * login is in progress -- awaiting response from firmware + */ +static void +bfa_lps_sm_login(struct bfa_lps_s *lps, enum bfa_lps_event event) +{ + bfa_trc(lps->bfa, lps->lp_tag); + bfa_trc(lps->bfa, event); + + switch (event) { + case BFA_LPS_SM_FWRSP: + if (lps->status == BFA_STATUS_OK) + bfa_sm_set_state(lps, bfa_lps_sm_online); + else + bfa_sm_set_state(lps, bfa_lps_sm_init); + bfa_lps_login_comp(lps); + break; + + case BFA_LPS_SM_OFFLINE: + bfa_sm_set_state(lps, bfa_lps_sm_init); + break; + + default: + bfa_assert(0); + } +} + +/** + * login pending - awaiting space in request queue + */ +static void +bfa_lps_sm_loginwait(struct bfa_lps_s *lps, enum bfa_lps_event event) +{ + bfa_trc(lps->bfa, lps->lp_tag); + bfa_trc(lps->bfa, event); + + switch (event) { + case BFA_LPS_SM_RESUME: + bfa_sm_set_state(lps, bfa_lps_sm_login); + break; + + case BFA_LPS_SM_OFFLINE: + bfa_sm_set_state(lps, bfa_lps_sm_init); + bfa_reqq_wcancel(&lps->wqe); + break; + + default: + bfa_assert(0); + } +} + +/** + * login complete + */ +static void +bfa_lps_sm_online(struct bfa_lps_s *lps, enum bfa_lps_event event) +{ + bfa_trc(lps->bfa, lps->lp_tag); + bfa_trc(lps->bfa, event); + + switch (event) { + case BFA_LPS_SM_LOGOUT: + if (bfa_reqq_full(lps->bfa, lps->reqq)) { + bfa_sm_set_state(lps, bfa_lps_sm_logowait); + bfa_reqq_wait(lps->bfa, lps->reqq, &lps->wqe); + } else { + bfa_sm_set_state(lps, bfa_lps_sm_logout); + bfa_lps_send_logout(lps); + } + break; + + case BFA_LPS_SM_OFFLINE: + case BFA_LPS_SM_DELETE: + bfa_sm_set_state(lps, bfa_lps_sm_init); + break; + + default: + bfa_assert(0); + } +} + +/** + * logout in progress - awaiting firmware response + */ +static void +bfa_lps_sm_logout(struct bfa_lps_s *lps, enum bfa_lps_event event) +{ + bfa_trc(lps->bfa, lps->lp_tag); + bfa_trc(lps->bfa, event); + + switch (event) { + case BFA_LPS_SM_FWRSP: + bfa_sm_set_state(lps, bfa_lps_sm_init); + bfa_lps_logout_comp(lps); + break; + + case BFA_LPS_SM_OFFLINE: + bfa_sm_set_state(lps, bfa_lps_sm_init); + break; + + default: + bfa_assert(0); + } +} + +/** + * logout pending -- awaiting space in request queue + */ +static void +bfa_lps_sm_logowait(struct bfa_lps_s *lps, enum bfa_lps_event event) +{ + bfa_trc(lps->bfa, lps->lp_tag); + bfa_trc(lps->bfa, event); + + switch (event) { + case BFA_LPS_SM_RESUME: + bfa_sm_set_state(lps, bfa_lps_sm_logout); + bfa_lps_send_logout(lps); + break; + + case BFA_LPS_SM_OFFLINE: + bfa_sm_set_state(lps, bfa_lps_sm_init); + bfa_reqq_wcancel(&lps->wqe); + break; + + default: + bfa_assert(0); + } +} + + + +/** + * lps_pvt BFA LPS private functions + */ + +/** + * return memory requirement + */ +static void +bfa_lps_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *ndm_len, u32 *dm_len) +{ + if (cfg->drvcfg.min_cfg) + *ndm_len += sizeof(struct bfa_lps_s) * BFA_LPS_MIN_LPORTS; + else + *ndm_len += sizeof(struct bfa_lps_s) * BFA_LPS_MAX_LPORTS; +} + +/** + * bfa module attach at initialization time + */ +static void +bfa_lps_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + struct bfa_lps_mod_s *mod = BFA_LPS_MOD(bfa); + struct bfa_lps_s *lps; + int i; + + bfa_os_memset(mod, 0, sizeof(struct bfa_lps_mod_s)); + mod->num_lps = BFA_LPS_MAX_LPORTS; + if (cfg->drvcfg.min_cfg) + mod->num_lps = BFA_LPS_MIN_LPORTS; + else + mod->num_lps = BFA_LPS_MAX_LPORTS; + mod->lps_arr = lps = (struct bfa_lps_s *) bfa_meminfo_kva(meminfo); + + bfa_meminfo_kva(meminfo) += mod->num_lps * sizeof(struct bfa_lps_s); + + INIT_LIST_HEAD(&mod->lps_free_q); + INIT_LIST_HEAD(&mod->lps_active_q); + + for (i = 0; i < mod->num_lps; i++, lps++) { + lps->bfa = bfa; + lps->lp_tag = (u8) i; + lps->reqq = BFA_REQQ_LPS; + bfa_reqq_winit(&lps->wqe, bfa_lps_reqq_resume, lps); + list_add_tail(&lps->qe, &mod->lps_free_q); + } +} + +static void +bfa_lps_initdone(struct bfa_s *bfa) +{ +} + +static void +bfa_lps_detach(struct bfa_s *bfa) +{ +} + +static void +bfa_lps_start(struct bfa_s *bfa) +{ +} + +static void +bfa_lps_stop(struct bfa_s *bfa) +{ +} + +/** + * IOC in disabled state -- consider all lps offline + */ +static void +bfa_lps_iocdisable(struct bfa_s *bfa) +{ + struct bfa_lps_mod_s *mod = BFA_LPS_MOD(bfa); + struct bfa_lps_s *lps; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &mod->lps_active_q) { + lps = (struct bfa_lps_s *) qe; + bfa_sm_send_event(lps, BFA_LPS_SM_OFFLINE); + } +} + +/** + * Firmware login response + */ +static void +bfa_lps_login_rsp(struct bfa_s *bfa, struct bfi_lps_login_rsp_s *rsp) +{ + struct bfa_lps_mod_s *mod = BFA_LPS_MOD(bfa); + struct bfa_lps_s *lps; + + bfa_assert(rsp->lp_tag < mod->num_lps); + lps = BFA_LPS_FROM_TAG(mod, rsp->lp_tag); + + lps->status = rsp->status; + switch (rsp->status) { + case BFA_STATUS_OK: + lps->fport = rsp->f_port; + lps->npiv_en = rsp->npiv_en; + lps->lp_pid = rsp->lp_pid; + lps->pr_bbcred = bfa_os_ntohs(rsp->bb_credit); + lps->pr_pwwn = rsp->port_name; + lps->pr_nwwn = rsp->node_name; + lps->auth_req = rsp->auth_req; + lps->lp_mac = rsp->lp_mac; + lps->brcd_switch = rsp->brcd_switch; + lps->fcf_mac = rsp->fcf_mac; + + break; + + case BFA_STATUS_FABRIC_RJT: + lps->lsrjt_rsn = rsp->lsrjt_rsn; + lps->lsrjt_expl = rsp->lsrjt_expl; + + break; + + case BFA_STATUS_EPROTOCOL: + lps->ext_status = rsp->ext_status; + + break; + + default: + /* Nothing to do with other status */ + break; + } + + bfa_sm_send_event(lps, BFA_LPS_SM_FWRSP); +} + +/** + * Firmware logout response + */ +static void +bfa_lps_logout_rsp(struct bfa_s *bfa, struct bfi_lps_logout_rsp_s *rsp) +{ + struct bfa_lps_mod_s *mod = BFA_LPS_MOD(bfa); + struct bfa_lps_s *lps; + + bfa_assert(rsp->lp_tag < mod->num_lps); + lps = BFA_LPS_FROM_TAG(mod, rsp->lp_tag); + + bfa_sm_send_event(lps, BFA_LPS_SM_FWRSP); +} + +/** + * Space is available in request queue, resume queueing request to firmware. + */ +static void +bfa_lps_reqq_resume(void *lps_arg) +{ + struct bfa_lps_s *lps = lps_arg; + + bfa_sm_send_event(lps, BFA_LPS_SM_RESUME); +} + +/** + * lps is freed -- triggered by vport delete + */ +static void +bfa_lps_free(struct bfa_lps_s *lps) +{ + struct bfa_lps_mod_s *mod = BFA_LPS_MOD(lps->bfa); + + list_del(&lps->qe); + list_add_tail(&lps->qe, &mod->lps_free_q); +} + +/** + * send login request to firmware + */ +static void +bfa_lps_send_login(struct bfa_lps_s *lps) +{ + struct bfi_lps_login_req_s *m; + + m = bfa_reqq_next(lps->bfa, lps->reqq); + bfa_assert(m); + + bfi_h2i_set(m->mh, BFI_MC_LPS, BFI_LPS_H2I_LOGIN_REQ, + bfa_lpuid(lps->bfa)); + + m->lp_tag = lps->lp_tag; + m->alpa = lps->alpa; + m->pdu_size = bfa_os_htons(lps->pdusz); + m->pwwn = lps->pwwn; + m->nwwn = lps->nwwn; + m->fdisc = lps->fdisc; + m->auth_en = lps->auth_en; + + bfa_reqq_produce(lps->bfa, lps->reqq); +} + +/** + * send logout request to firmware + */ +static void +bfa_lps_send_logout(struct bfa_lps_s *lps) +{ + struct bfi_lps_logout_req_s *m; + + m = bfa_reqq_next(lps->bfa, lps->reqq); + bfa_assert(m); + + bfi_h2i_set(m->mh, BFI_MC_LPS, BFI_LPS_H2I_LOGOUT_REQ, + bfa_lpuid(lps->bfa)); + + m->lp_tag = lps->lp_tag; + m->port_name = lps->pwwn; + bfa_reqq_produce(lps->bfa, lps->reqq); +} + +/** + * Indirect login completion handler for non-fcs + */ +static void +bfa_lps_login_comp_cb(void *arg, bfa_boolean_t complete) +{ + struct bfa_lps_s *lps = arg; + + if (!complete) + return; + + if (lps->fdisc) + bfa_cb_lps_fdisc_comp(lps->bfa->bfad, lps->uarg, lps->status); + else + bfa_cb_lps_flogi_comp(lps->bfa->bfad, lps->uarg, lps->status); +} + +/** + * Login completion handler -- direct call for fcs, queue for others + */ +static void +bfa_lps_login_comp(struct bfa_lps_s *lps) +{ + if (!lps->bfa->fcs) { + bfa_cb_queue(lps->bfa, &lps->hcb_qe, + bfa_lps_login_comp_cb, lps); + return; + } + + if (lps->fdisc) + bfa_cb_lps_fdisc_comp(lps->bfa->bfad, lps->uarg, lps->status); + else + bfa_cb_lps_flogi_comp(lps->bfa->bfad, lps->uarg, lps->status); +} + +/** + * Indirect logout completion handler for non-fcs + */ +static void +bfa_lps_logout_comp_cb(void *arg, bfa_boolean_t complete) +{ + struct bfa_lps_s *lps = arg; + + if (!complete) + return; + + if (lps->fdisc) + bfa_cb_lps_fdisclogo_comp(lps->bfa->bfad, lps->uarg); + else + bfa_cb_lps_flogo_comp(lps->bfa->bfad, lps->uarg); +} + +/** + * Logout completion handler -- direct call for fcs, queue for others + */ +static void +bfa_lps_logout_comp(struct bfa_lps_s *lps) +{ + if (!lps->bfa->fcs) { + bfa_cb_queue(lps->bfa, &lps->hcb_qe, + bfa_lps_logout_comp_cb, lps); + return; + } + if (lps->fdisc) + bfa_cb_lps_fdisclogo_comp(lps->bfa->bfad, lps->uarg); + else + bfa_cb_lps_flogo_comp(lps->bfa->bfad, lps->uarg); +} + + + +/** + * lps_public BFA LPS public functions + */ + +/** + * Allocate a lport srvice tag. + */ +struct bfa_lps_s * +bfa_lps_alloc(struct bfa_s *bfa) +{ + struct bfa_lps_mod_s *mod = BFA_LPS_MOD(bfa); + struct bfa_lps_s *lps = NULL; + + bfa_q_deq(&mod->lps_free_q, &lps); + + if (lps == NULL) + return NULL; + + list_add_tail(&lps->qe, &mod->lps_active_q); + + bfa_sm_set_state(lps, bfa_lps_sm_init); + return lps; +} + +/** + * Free lport service tag. This can be called anytime after an alloc. + * No need to wait for any pending login/logout completions. + */ +void +bfa_lps_delete(struct bfa_lps_s *lps) +{ + bfa_sm_send_event(lps, BFA_LPS_SM_DELETE); +} + +/** + * Initiate a lport login. + */ +void +bfa_lps_flogi(struct bfa_lps_s *lps, void *uarg, u8 alpa, u16 pdusz, + wwn_t pwwn, wwn_t nwwn, bfa_boolean_t auth_en) +{ + lps->uarg = uarg; + lps->alpa = alpa; + lps->pdusz = pdusz; + lps->pwwn = pwwn; + lps->nwwn = nwwn; + lps->fdisc = BFA_FALSE; + lps->auth_en = auth_en; + bfa_sm_send_event(lps, BFA_LPS_SM_LOGIN); +} + +/** + * Initiate a lport fdisc login. + */ +void +bfa_lps_fdisc(struct bfa_lps_s *lps, void *uarg, u16 pdusz, wwn_t pwwn, + wwn_t nwwn) +{ + lps->uarg = uarg; + lps->alpa = 0; + lps->pdusz = pdusz; + lps->pwwn = pwwn; + lps->nwwn = nwwn; + lps->fdisc = BFA_TRUE; + lps->auth_en = BFA_FALSE; + bfa_sm_send_event(lps, BFA_LPS_SM_LOGIN); +} + +/** + * Initiate a lport logout (flogi). + */ +void +bfa_lps_flogo(struct bfa_lps_s *lps) +{ + bfa_sm_send_event(lps, BFA_LPS_SM_LOGOUT); +} + +/** + * Initiate a lport FDSIC logout. + */ +void +bfa_lps_fdisclogo(struct bfa_lps_s *lps) +{ + bfa_sm_send_event(lps, BFA_LPS_SM_LOGOUT); +} + +/** + * Discard a pending login request -- should be called only for + * link down handling. + */ +void +bfa_lps_discard(struct bfa_lps_s *lps) +{ + bfa_sm_send_event(lps, BFA_LPS_SM_OFFLINE); +} + +/** + * Return lport services tag + */ +u8 +bfa_lps_get_tag(struct bfa_lps_s *lps) +{ + return lps->lp_tag; +} + +/** + * Return lport services tag given the pid + */ +u8 +bfa_lps_get_tag_from_pid(struct bfa_s *bfa, u32 pid) +{ + struct bfa_lps_mod_s *mod = BFA_LPS_MOD(bfa); + struct bfa_lps_s *lps; + int i; + + for (i = 0, lps = mod->lps_arr; i < mod->num_lps; i++, lps++) { + if (lps->lp_pid == pid) + return lps->lp_tag; + } + + /* Return base port tag anyway */ + return 0; +} + +/** + * return if fabric login indicates support for NPIV + */ +bfa_boolean_t +bfa_lps_is_npiv_en(struct bfa_lps_s *lps) +{ + return lps->npiv_en; +} + +/** + * Return TRUE if attached to F-Port, else return FALSE + */ +bfa_boolean_t +bfa_lps_is_fport(struct bfa_lps_s *lps) +{ + return lps->fport; +} + +/** + * Return TRUE if attached to a Brocade Fabric + */ +bfa_boolean_t +bfa_lps_is_brcd_fabric(struct bfa_lps_s *lps) +{ + return lps->brcd_switch; +} +/** + * return TRUE if authentication is required + */ +bfa_boolean_t +bfa_lps_is_authreq(struct bfa_lps_s *lps) +{ + return lps->auth_req; +} + +bfa_eproto_status_t +bfa_lps_get_extstatus(struct bfa_lps_s *lps) +{ + return lps->ext_status; +} + +/** + * return port id assigned to the lport + */ +u32 +bfa_lps_get_pid(struct bfa_lps_s *lps) +{ + return lps->lp_pid; +} + +/** + * Return bb_credit assigned in FLOGI response + */ +u16 +bfa_lps_get_peer_bbcredit(struct bfa_lps_s *lps) +{ + return lps->pr_bbcred; +} + +/** + * Return peer port name + */ +wwn_t +bfa_lps_get_peer_pwwn(struct bfa_lps_s *lps) +{ + return lps->pr_pwwn; +} + +/** + * Return peer node name + */ +wwn_t +bfa_lps_get_peer_nwwn(struct bfa_lps_s *lps) +{ + return lps->pr_nwwn; +} + +/** + * return reason code if login request is rejected + */ +u8 +bfa_lps_get_lsrjt_rsn(struct bfa_lps_s *lps) +{ + return lps->lsrjt_rsn; +} + +/** + * return explanation code if login request is rejected + */ +u8 +bfa_lps_get_lsrjt_expl(struct bfa_lps_s *lps) +{ + return lps->lsrjt_expl; +} + + +/** + * LPS firmware message class handler. + */ +void +bfa_lps_isr(struct bfa_s *bfa, struct bfi_msg_s *m) +{ + union bfi_lps_i2h_msg_u msg; + + bfa_trc(bfa, m->mhdr.msg_id); + msg.msg = m; + + switch (m->mhdr.msg_id) { + case BFI_LPS_H2I_LOGIN_RSP: + bfa_lps_login_rsp(bfa, msg.login_rsp); + break; + + case BFI_LPS_H2I_LOGOUT_RSP: + bfa_lps_logout_rsp(bfa, msg.logout_rsp); + break; + + default: + bfa_trc(bfa, m->mhdr.msg_id); + bfa_assert(0); + } +} + + diff --git a/drivers/scsi/bfa/bfa_lps_priv.h b/drivers/scsi/bfa/bfa_lps_priv.h new file mode 100644 index 000000000000..d16c6ce995df --- /dev/null +++ b/drivers/scsi/bfa/bfa_lps_priv.h @@ -0,0 +1,38 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_LPS_PRIV_H__ +#define __BFA_LPS_PRIV_H__ + +#include <bfa_svc.h> + +struct bfa_lps_mod_s { + struct list_head lps_free_q; + struct list_head lps_active_q; + struct bfa_lps_s *lps_arr; + int num_lps; +}; + +#define BFA_LPS_MOD(__bfa) (&(__bfa)->modules.lps_mod) +#define BFA_LPS_FROM_TAG(__mod, __tag) (&(__mod)->lps_arr[__tag]) + +/* + * external functions + */ +void bfa_lps_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); + +#endif /* __BFA_LPS_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_module.c b/drivers/scsi/bfa/bfa_module.c new file mode 100644 index 000000000000..32eda8e1ec65 --- /dev/null +++ b/drivers/scsi/bfa/bfa_module.c @@ -0,0 +1,90 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#include <bfa.h> +#include <defs/bfa_defs_pci.h> +#include <cs/bfa_debug.h> +#include <bfa_iocfc.h> + +/** + * BFA module list terminated by NULL + */ +struct bfa_module_s *hal_mods[] = { + &hal_mod_sgpg, + &hal_mod_pport, + &hal_mod_fcxp, + &hal_mod_lps, + &hal_mod_uf, + &hal_mod_rport, + &hal_mod_fcpim, +#ifdef BFA_CFG_PBIND + &hal_mod_pbind, +#endif + NULL +}; + +/** + * Message handlers for various modules. + */ +bfa_isr_func_t bfa_isrs[BFI_MC_MAX] = { + bfa_isr_unhandled, /* NONE */ + bfa_isr_unhandled, /* BFI_MC_IOC */ + bfa_isr_unhandled, /* BFI_MC_DIAG */ + bfa_isr_unhandled, /* BFI_MC_FLASH */ + bfa_isr_unhandled, /* BFI_MC_CEE */ + bfa_pport_isr, /* BFI_MC_PORT */ + bfa_isr_unhandled, /* BFI_MC_IOCFC */ + bfa_isr_unhandled, /* BFI_MC_LL */ + bfa_uf_isr, /* BFI_MC_UF */ + bfa_fcxp_isr, /* BFI_MC_FCXP */ + bfa_lps_isr, /* BFI_MC_LPS */ + bfa_rport_isr, /* BFI_MC_RPORT */ + bfa_itnim_isr, /* BFI_MC_ITNIM */ + bfa_isr_unhandled, /* BFI_MC_IOIM_READ */ + bfa_isr_unhandled, /* BFI_MC_IOIM_WRITE */ + bfa_isr_unhandled, /* BFI_MC_IOIM_IO */ + bfa_ioim_isr, /* BFI_MC_IOIM */ + bfa_ioim_good_comp_isr, /* BFI_MC_IOIM_IOCOM */ + bfa_tskim_isr, /* BFI_MC_TSKIM */ + bfa_isr_unhandled, /* BFI_MC_SBOOT */ + bfa_isr_unhandled, /* BFI_MC_IPFC */ + bfa_isr_unhandled, /* BFI_MC_PORT */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ + bfa_isr_unhandled, /* --------- */ +}; + +/** + * Message handlers for mailbox command classes + */ +bfa_ioc_mbox_mcfunc_t bfa_mbox_isrs[BFI_MC_MAX] = { + NULL, + NULL, /* BFI_MC_IOC */ + NULL, /* BFI_MC_DIAG */ + NULL, /* BFI_MC_FLASH */ + NULL, /* BFI_MC_CEE */ + NULL, /* BFI_MC_PORT */ + bfa_iocfc_isr, /* BFI_MC_IOCFC */ + NULL, +}; + diff --git a/drivers/scsi/bfa/bfa_modules_priv.h b/drivers/scsi/bfa/bfa_modules_priv.h new file mode 100644 index 000000000000..96f70534593c --- /dev/null +++ b/drivers/scsi/bfa/bfa_modules_priv.h @@ -0,0 +1,43 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_MODULES_PRIV_H__ +#define __BFA_MODULES_PRIV_H__ + +#include "bfa_uf_priv.h" +#include "bfa_port_priv.h" +#include "bfa_rport_priv.h" +#include "bfa_fcxp_priv.h" +#include "bfa_lps_priv.h" +#include "bfa_fcpim_priv.h" +#include <cee/bfa_cee.h> +#include <port/bfa_port.h> + + +struct bfa_modules_s { + struct bfa_pport_s pport; /* physical port module */ + struct bfa_fcxp_mod_s fcxp_mod; /* fcxp module */ + struct bfa_lps_mod_s lps_mod; /* fcxp module */ + struct bfa_uf_mod_s uf_mod; /* unsolicited frame module */ + struct bfa_rport_mod_s rport_mod; /* remote port module */ + struct bfa_fcpim_mod_s fcpim_mod; /* FCP initiator module */ + struct bfa_sgpg_mod_s sgpg_mod; /* SG page module */ + struct bfa_cee_s cee; /* CEE Module */ + struct bfa_port_s port; /* Physical port module */ +}; + +#endif /* __BFA_MODULES_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_os_inc.h b/drivers/scsi/bfa/bfa_os_inc.h new file mode 100644 index 000000000000..10a89f75fa94 --- /dev/null +++ b/drivers/scsi/bfa/bfa_os_inc.h @@ -0,0 +1,222 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * Contains declarations all OS Specific files needed for BFA layer + */ + +#ifndef __BFA_OS_INC_H__ +#define __BFA_OS_INC_H__ + +#ifndef __KERNEL__ +#include <stdint.h> +#else +#include <linux/types.h> + +#include <linux/version.h> +#include <linux/pci.h> + +#include <linux/dma-mapping.h> +#define SET_MODULE_VERSION(VER) + +#include <linux/idr.h> + +#include <linux/interrupt.h> +#include <linux/cdev.h> +#include <linux/fs.h> +#include <linux/delay.h> +#include <linux/vmalloc.h> + +#include <linux/workqueue.h> + +#include <scsi/scsi.h> +#include <scsi/scsi_host.h> + +#include <scsi/scsi_tcq.h> +#include <scsi/scsi_transport_fc.h> +#include <scsi/scsi_transport.h> + +#define BFA_ERR KERN_ERR +#define BFA_WARNING KERN_WARNING +#define BFA_NOTICE KERN_NOTICE +#define BFA_INFO KERN_INFO +#define BFA_DEBUG KERN_DEBUG + +#define LOG_BFAD_INIT 0x00000001 +#define LOG_FCP_IO 0x00000002 + +#ifdef DEBUG +#define BFA_LOG_TRACE(bfad, level, mask, fmt, arg...) \ + BFA_LOG(bfad, level, mask, fmt, ## arg) +#define BFA_DEV_TRACE(bfad, level, fmt, arg...) \ + BFA_DEV_PRINTF(bfad, level, fmt, ## arg) +#define BFA_TRACE(level, fmt, arg...) \ + BFA_PRINTF(level, fmt, ## arg) +#else +#define BFA_LOG_TRACE(bfad, level, mask, fmt, arg...) +#define BFA_DEV_TRACE(bfad, level, fmt, arg...) +#define BFA_TRACE(level, fmt, arg...) +#endif + +#define BFA_ASSERT(p) do { \ + if (!(p)) { \ + printk(KERN_ERR "assert(%s) failed at %s:%d\n", \ + #p, __FILE__, __LINE__); \ + BUG(); \ + } \ +} while (0) + + +#define BFA_LOG(bfad, level, mask, fmt, arg...) \ +do { \ + if (((mask) & (((struct bfad_s *)(bfad))-> \ + cfg_data[cfg_log_mask])) || (level[1] <= '3')) \ + dev_printk(level, &(((struct bfad_s *) \ + (bfad))->pcidev->dev), fmt, ##arg); \ +} while (0) + +#ifndef BFA_DEV_PRINTF +#define BFA_DEV_PRINTF(bfad, level, fmt, arg...) \ + dev_printk(level, &(((struct bfad_s *) \ + (bfad))->pcidev->dev), fmt, ##arg); +#endif + +#define BFA_PRINTF(level, fmt, arg...) \ + printk(level fmt, ##arg); + +int bfa_os_MWB(void *); + +#define bfa_os_mmiowb() mmiowb() + +#define bfa_swap_3b(_x) \ + ((((_x) & 0xff) << 16) | \ + ((_x) & 0x00ff00) | \ + (((_x) & 0xff0000) >> 16)) + +#define bfa_swap_8b(_x) \ + ((((_x) & 0xff00000000000000ull) >> 56) \ + | (((_x) & 0x00ff000000000000ull) >> 40) \ + | (((_x) & 0x0000ff0000000000ull) >> 24) \ + | (((_x) & 0x000000ff00000000ull) >> 8) \ + | (((_x) & 0x00000000ff000000ull) << 8) \ + | (((_x) & 0x0000000000ff0000ull) << 24) \ + | (((_x) & 0x000000000000ff00ull) << 40) \ + | (((_x) & 0x00000000000000ffull) << 56)) + +#define bfa_os_swap32(_x) \ + ((((_x) & 0xff) << 24) | \ + (((_x) & 0x0000ff00) << 8) | \ + (((_x) & 0x00ff0000) >> 8) | \ + (((_x) & 0xff000000) >> 24)) + + +#ifndef __BIGENDIAN +#define bfa_os_htons(_x) ((u16)((((_x) & 0xff00) >> 8) | \ + (((_x) & 0x00ff) << 8))) + +#define bfa_os_htonl(_x) bfa_os_swap32(_x) +#define bfa_os_htonll(_x) bfa_swap_8b(_x) +#define bfa_os_hton3b(_x) bfa_swap_3b(_x) + +#define bfa_os_wtole(_x) (_x) + +#else + +#define bfa_os_htons(_x) (_x) +#define bfa_os_htonl(_x) (_x) +#define bfa_os_hton3b(_x) (_x) +#define bfa_os_htonll(_x) (_x) +#define bfa_os_wtole(_x) bfa_os_swap32(_x) + +#endif + +#define bfa_os_ntohs(_x) bfa_os_htons(_x) +#define bfa_os_ntohl(_x) bfa_os_htonl(_x) +#define bfa_os_ntohll(_x) bfa_os_htonll(_x) +#define bfa_os_ntoh3b(_x) bfa_os_hton3b(_x) + +#define bfa_os_u32(__pa64) ((__pa64) >> 32) + +#define bfa_os_memset memset +#define bfa_os_memcpy memcpy +#define bfa_os_udelay udelay +#define bfa_os_vsprintf vsprintf + +#define bfa_os_assign(__t, __s) __t = __s + +#define bfa_os_addr_t char __iomem * +#define bfa_os_panic() + +#define bfa_os_reg_read(_raddr) bfa_os_wtole(readl(_raddr)) +#define bfa_os_reg_write(_raddr, _val) writel(bfa_os_wtole((_val)), (_raddr)) +#define bfa_os_mem_read(_raddr, _off) \ + bfa_os_ntohl(readl(((_raddr) + (_off)))) +#define bfa_os_mem_write(_raddr, _off, _val) \ + writel(bfa_os_htonl((_val)), ((_raddr) + (_off))) + +#define BFA_TRC_TS(_trcm) \ + ({ \ + struct timeval tv; \ + \ + do_gettimeofday(&tv); \ + (tv.tv_sec*1000000+tv.tv_usec); \ + }) + +struct bfa_log_mod_s; +void bfa_os_printf(struct bfa_log_mod_s *log_mod, u32 msg_id, + const char *fmt, ...); +#endif + +#define boolean_t int + +/** + * For current time stamp, OS API will fill-in + */ +struct bfa_timeval_s { + u32 tv_sec; /* seconds */ + u32 tv_usec; /* microseconds */ +}; + +void bfa_os_gettimeofday(struct bfa_timeval_s *tv); + +static inline void +wwn2str(char *wwn_str, u64 wwn) +{ + union { + u64 wwn; + u8 byte[8]; + } w; + + w.wwn = wwn; + sprintf(wwn_str, "%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x", w.byte[0], + w.byte[1], w.byte[2], w.byte[3], w.byte[4], w.byte[5], + w.byte[6], w.byte[7]); +} + +static inline void +fcid2str(char *fcid_str, u32 fcid) +{ + union { + u32 fcid; + u8 byte[4]; + } f; + + f.fcid = fcid; + sprintf(fcid_str, "%02x:%02x:%02x", f.byte[1], f.byte[2], f.byte[3]); +} + +#endif /* __BFA_OS_INC_H__ */ diff --git a/drivers/scsi/bfa/bfa_port.c b/drivers/scsi/bfa/bfa_port.c new file mode 100644 index 000000000000..cab19028361a --- /dev/null +++ b/drivers/scsi/bfa/bfa_port.c @@ -0,0 +1,460 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <defs/bfa_defs_port.h> +#include <cs/bfa_trc.h> +#include <cs/bfa_log.h> +#include <cs/bfa_debug.h> +#include <port/bfa_port.h> +#include <bfi/bfi.h> +#include <bfi/bfi_port.h> +#include <bfa_ioc.h> +#include <cna/bfa_cna_trcmod.h> + +BFA_TRC_FILE(CNA, PORT); + +#define bfa_ioc_portid(__ioc) ((__ioc)->port_id) +#define bfa_lpuid(__arg) bfa_ioc_portid(&(__arg)->ioc) + +static void +bfa_port_stats_swap(struct bfa_port_s *port, union bfa_pport_stats_u *stats) +{ + u32 *dip = (u32 *) stats; + u32 t0, t1; + int i; + + for (i = 0; i < sizeof(union bfa_pport_stats_u) / sizeof(u32); + i += 2) { + t0 = dip[i]; + t1 = dip[i + 1]; +#ifdef __BIGENDIAN + dip[i] = bfa_os_ntohl(t0); + dip[i + 1] = bfa_os_ntohl(t1); +#else + dip[i] = bfa_os_ntohl(t1); + dip[i + 1] = bfa_os_ntohl(t0); +#endif + } + + /** todo + * QoS stats r also swapped as 64bit; that structure also + * has to use 64 bit counters + */ +} + +/** + * bfa_port_enable_isr() + * + * + * @param[in] port - Pointer to the port module + * status - Return status from the f/w + * + * @return void + */ +static void +bfa_port_enable_isr(struct bfa_port_s *port, bfa_status_t status) +{ + bfa_assert(0); +} + +/** + * bfa_port_disable_isr() + * + * + * @param[in] port - Pointer to the port module + * status - Return status from the f/w + * + * @return void + */ +static void +bfa_port_disable_isr(struct bfa_port_s *port, bfa_status_t status) +{ + bfa_assert(0); +} + +/** + * bfa_port_get_stats_isr() + * + * + * @param[in] port - Pointer to the Port module + * status - Return status from the f/w + * + * @return void + */ +static void +bfa_port_get_stats_isr(struct bfa_port_s *port, bfa_status_t status) +{ + port->stats_status = status; + port->stats_busy = BFA_FALSE; + + if (status == BFA_STATUS_OK) { + memcpy(port->stats, port->stats_dma.kva, + sizeof(union bfa_pport_stats_u)); + bfa_port_stats_swap(port, port->stats); + } + + if (port->stats_cbfn) { + port->stats_cbfn(port->stats_cbarg, status); + port->stats_cbfn = NULL; + } +} + +/** + * bfa_port_clear_stats_isr() + * + * + * @param[in] port - Pointer to the Port module + * status - Return status from the f/w + * + * @return void + */ +static void +bfa_port_clear_stats_isr(struct bfa_port_s *port, bfa_status_t status) +{ + port->stats_status = status; + port->stats_busy = BFA_FALSE; + + if (port->stats_cbfn) { + port->stats_cbfn(port->stats_cbarg, status); + port->stats_cbfn = NULL; + } +} + +/** + * bfa_port_isr() + * + * + * @param[in] Pointer to the Port module data structure. + * + * @return void + */ +static void +bfa_port_isr(void *cbarg, struct bfi_mbmsg_s *m) +{ + struct bfa_port_s *port = (struct bfa_port_s *)cbarg; + union bfi_port_i2h_msg_u *i2hmsg; + + i2hmsg = (union bfi_port_i2h_msg_u *)m; + bfa_trc(port, m->mh.msg_id); + + switch (m->mh.msg_id) { + case BFI_PORT_I2H_ENABLE_RSP: + if (port->endis_pending == BFA_FALSE) + break; + bfa_port_enable_isr(port, i2hmsg->enable_rsp.status); + break; + + case BFI_PORT_I2H_DISABLE_RSP: + if (port->endis_pending == BFA_FALSE) + break; + bfa_port_disable_isr(port, i2hmsg->disable_rsp.status); + break; + + case BFI_PORT_I2H_GET_STATS_RSP: + /* + * Stats busy flag is still set? (may be cmd timed out) + */ + if (port->stats_busy == BFA_FALSE) + break; + bfa_port_get_stats_isr(port, i2hmsg->getstats_rsp.status); + break; + + case BFI_PORT_I2H_CLEAR_STATS_RSP: + if (port->stats_busy == BFA_FALSE) + break; + bfa_port_clear_stats_isr(port, i2hmsg->clearstats_rsp.status); + break; + + default: + bfa_assert(0); + } +} + +/** + * bfa_port_meminfo() + * + * + * @param[in] void + * + * @return Size of DMA region + */ +u32 +bfa_port_meminfo(void) +{ + return BFA_ROUNDUP(sizeof(union bfa_pport_stats_u), BFA_DMA_ALIGN_SZ); +} + +/** + * bfa_port_mem_claim() + * + * + * @param[in] port Port module pointer + * dma_kva Kernel Virtual Address of Port DMA Memory + * dma_pa Physical Address of Port DMA Memory + * + * @return void + */ +void +bfa_port_mem_claim(struct bfa_port_s *port, u8 *dma_kva, u64 dma_pa) +{ + port->stats_dma.kva = dma_kva; + port->stats_dma.pa = dma_pa; +} + +/** + * bfa_port_enable() + * + * Send the Port enable request to the f/w + * + * @param[in] Pointer to the Port module data structure. + * + * @return Status + */ +bfa_status_t +bfa_port_enable(struct bfa_port_s *port, bfa_port_endis_cbfn_t cbfn, + void *cbarg) +{ + struct bfi_port_generic_req_s *m; + + /** todo Not implemented */ + bfa_assert(0); + + if (!bfa_ioc_is_operational(port->ioc)) { + bfa_trc(port, BFA_STATUS_IOC_FAILURE); + return BFA_STATUS_IOC_FAILURE; + } + + if (port->endis_pending) { + bfa_trc(port, BFA_STATUS_DEVBUSY); + return BFA_STATUS_DEVBUSY; + } + + m = (struct bfi_port_generic_req_s *)port->endis_mb.msg; + + port->msgtag++; + port->endis_cbfn = cbfn; + port->endis_cbarg = cbarg; + port->endis_pending = BFA_TRUE; + + bfi_h2i_set(m->mh, BFI_MC_PORT, BFI_PORT_H2I_ENABLE_REQ, + bfa_ioc_portid(port->ioc)); + bfa_ioc_mbox_queue(port->ioc, &port->endis_mb); + + return BFA_STATUS_OK; +} + +/** + * bfa_port_disable() + * + * Send the Port disable request to the f/w + * + * @param[in] Pointer to the Port module data structure. + * + * @return Status + */ +bfa_status_t +bfa_port_disable(struct bfa_port_s *port, bfa_port_endis_cbfn_t cbfn, + void *cbarg) +{ + struct bfi_port_generic_req_s *m; + + /** todo Not implemented */ + bfa_assert(0); + + if (!bfa_ioc_is_operational(port->ioc)) { + bfa_trc(port, BFA_STATUS_IOC_FAILURE); + return BFA_STATUS_IOC_FAILURE; + } + + if (port->endis_pending) { + bfa_trc(port, BFA_STATUS_DEVBUSY); + return BFA_STATUS_DEVBUSY; + } + + m = (struct bfi_port_generic_req_s *)port->endis_mb.msg; + + port->msgtag++; + port->endis_cbfn = cbfn; + port->endis_cbarg = cbarg; + port->endis_pending = BFA_TRUE; + + bfi_h2i_set(m->mh, BFI_MC_PORT, BFI_PORT_H2I_DISABLE_REQ, + bfa_ioc_portid(port->ioc)); + bfa_ioc_mbox_queue(port->ioc, &port->endis_mb); + + return BFA_STATUS_OK; +} + +/** + * bfa_port_get_stats() + * + * Send the request to the f/w to fetch Port statistics. + * + * @param[in] Pointer to the Port module data structure. + * + * @return Status + */ +bfa_status_t +bfa_port_get_stats(struct bfa_port_s *port, union bfa_pport_stats_u *stats, + bfa_port_stats_cbfn_t cbfn, void *cbarg) +{ + struct bfi_port_get_stats_req_s *m; + + if (!bfa_ioc_is_operational(port->ioc)) { + bfa_trc(port, BFA_STATUS_IOC_FAILURE); + return BFA_STATUS_IOC_FAILURE; + } + + if (port->stats_busy) { + bfa_trc(port, BFA_STATUS_DEVBUSY); + return BFA_STATUS_DEVBUSY; + } + + m = (struct bfi_port_get_stats_req_s *)port->stats_mb.msg; + + port->stats = stats; + port->stats_cbfn = cbfn; + port->stats_cbarg = cbarg; + port->stats_busy = BFA_TRUE; + bfa_dma_be_addr_set(m->dma_addr, port->stats_dma.pa); + + bfi_h2i_set(m->mh, BFI_MC_PORT, BFI_PORT_H2I_GET_STATS_REQ, + bfa_ioc_portid(port->ioc)); + bfa_ioc_mbox_queue(port->ioc, &port->stats_mb); + + return BFA_STATUS_OK; +} + +/** + * bfa_port_clear_stats() + * + * + * @param[in] Pointer to the Port module data structure. + * + * @return Status + */ +bfa_status_t +bfa_port_clear_stats(struct bfa_port_s *port, bfa_port_stats_cbfn_t cbfn, + void *cbarg) +{ + struct bfi_port_generic_req_s *m; + + if (!bfa_ioc_is_operational(port->ioc)) { + bfa_trc(port, BFA_STATUS_IOC_FAILURE); + return BFA_STATUS_IOC_FAILURE; + } + + if (port->stats_busy) { + bfa_trc(port, BFA_STATUS_DEVBUSY); + return BFA_STATUS_DEVBUSY; + } + + m = (struct bfi_port_generic_req_s *)port->stats_mb.msg; + + port->stats_cbfn = cbfn; + port->stats_cbarg = cbarg; + port->stats_busy = BFA_TRUE; + + bfi_h2i_set(m->mh, BFI_MC_PORT, BFI_PORT_H2I_CLEAR_STATS_REQ, + bfa_ioc_portid(port->ioc)); + bfa_ioc_mbox_queue(port->ioc, &port->stats_mb); + + return BFA_STATUS_OK; +} + +/** + * bfa_port_hbfail() + * + * + * @param[in] Pointer to the Port module data structure. + * + * @return void + */ +void +bfa_port_hbfail(void *arg) +{ + struct bfa_port_s *port = (struct bfa_port_s *)arg; + + /* + * Fail any pending get_stats/clear_stats requests + */ + if (port->stats_busy) { + if (port->stats_cbfn) + port->stats_cbfn(port->dev, BFA_STATUS_FAILED); + port->stats_cbfn = NULL; + port->stats_busy = BFA_FALSE; + } + + /* + * Clear any enable/disable is pending + */ + if (port->endis_pending) { + if (port->endis_cbfn) + port->endis_cbfn(port->dev, BFA_STATUS_FAILED); + port->endis_cbfn = NULL; + port->endis_pending = BFA_FALSE; + } +} + +/** + * bfa_port_attach() + * + * + * @param[in] port - Pointer to the Port module data structure + * ioc - Pointer to the ioc module data structure + * dev - Pointer to the device driver module data structure + * The device driver specific mbox ISR functions have + * this pointer as one of the parameters. + * trcmod - + * logmod - + * + * @return void + */ +void +bfa_port_attach(struct bfa_port_s *port, struct bfa_ioc_s *ioc, void *dev, + struct bfa_trc_mod_s *trcmod, struct bfa_log_mod_s *logmod) +{ + bfa_assert(port); + + port->dev = dev; + port->ioc = ioc; + port->trcmod = trcmod; + port->logmod = logmod; + + port->stats_busy = port->endis_pending = BFA_FALSE; + port->stats_cbfn = port->endis_cbfn = NULL; + + bfa_ioc_mbox_regisr(port->ioc, BFI_MC_PORT, bfa_port_isr, port); + bfa_ioc_hbfail_init(&port->hbfail, bfa_port_hbfail, port); + bfa_ioc_hbfail_register(port->ioc, &port->hbfail); + + bfa_trc(port, 0); +} + +/** + * bfa_port_detach() + * + * + * @param[in] port - Pointer to the Port module data structure + * + * @return void + */ +void +bfa_port_detach(struct bfa_port_s *port) +{ + bfa_trc(port, 0); +} diff --git a/drivers/scsi/bfa/bfa_port_priv.h b/drivers/scsi/bfa/bfa_port_priv.h new file mode 100644 index 000000000000..4b97e2759908 --- /dev/null +++ b/drivers/scsi/bfa/bfa_port_priv.h @@ -0,0 +1,90 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_PORT_PRIV_H__ +#define __BFA_PORT_PRIV_H__ + +#include <defs/bfa_defs_pport.h> +#include <bfi/bfi_pport.h> +#include "bfa_intr_priv.h" + +/** + * BFA physical port data structure + */ +struct bfa_pport_s { + struct bfa_s *bfa; /* parent BFA instance */ + bfa_sm_t sm; /* port state machine */ + wwn_t nwwn; /* node wwn of physical port */ + wwn_t pwwn; /* port wwn of physical oprt */ + enum bfa_pport_speed speed_sup; + /* supported speeds */ + enum bfa_pport_speed speed; /* current speed */ + enum bfa_pport_topology topology; /* current topology */ + u8 myalpa; /* my ALPA in LOOP topology */ + u8 rsvd[3]; + struct bfa_pport_cfg_s cfg; /* current port configuration */ + struct bfa_qos_attr_s qos_attr; /* QoS Attributes */ + struct bfa_qos_vc_attr_s qos_vc_attr; /* VC info from ELP */ + struct bfa_reqq_wait_s reqq_wait; + /* to wait for room in reqq */ + struct bfa_reqq_wait_s svcreq_wait; + /* to wait for room in reqq */ + struct bfa_reqq_wait_s stats_reqq_wait; + /* to wait for room in reqq (stats) */ + void *event_cbarg; + void (*event_cbfn) (void *cbarg, + bfa_pport_event_t event); + union { + union bfi_pport_i2h_msg_u i2hmsg; + } event_arg; + void *bfad; /* BFA driver handle */ + struct bfa_cb_qe_s hcb_qe; /* BFA callback queue elem */ + enum bfa_pport_linkstate hcb_event; + /* link event for callback */ + u32 msgtag; /* fimrware msg tag for reply */ + u8 *stats_kva; + u64 stats_pa; + union bfa_pport_stats_u *stats; /* pport stats */ + u32 mypid : 24; + u32 rsvd_b : 8; + struct bfa_timer_s timer; /* timer */ + union bfa_pport_stats_u *stats_ret; + /* driver stats location */ + bfa_status_t stats_status; + /* stats/statsclr status */ + bfa_boolean_t stats_busy; + /* outstanding stats/statsclr */ + bfa_boolean_t stats_qfull; + bfa_boolean_t diag_busy; + /* diag busy status */ + bfa_boolean_t beacon; + /* port beacon status */ + bfa_boolean_t link_e2e_beacon; + /* link beacon status */ + bfa_cb_pport_t stats_cbfn; + /* driver callback function */ + void *stats_cbarg; + /* *!< user callback arg */ +}; + +#define BFA_PORT_MOD(__bfa) (&(__bfa)->modules.pport) + +/* + * public functions + */ +void bfa_pport_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); +#endif /* __BFA_PORT_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_priv.h b/drivers/scsi/bfa/bfa_priv.h new file mode 100644 index 000000000000..0747a6b26f7b --- /dev/null +++ b/drivers/scsi/bfa/bfa_priv.h @@ -0,0 +1,113 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_PRIV_H__ +#define __BFA_PRIV_H__ + +#include "bfa_iocfc.h" +#include "bfa_intr_priv.h" +#include "bfa_trcmod_priv.h" +#include "bfa_modules_priv.h" +#include "bfa_fwimg_priv.h" +#include <cs/bfa_log.h> +#include <bfa_timer.h> + +/** + * Macro to define a new BFA module + */ +#define BFA_MODULE(__mod) \ + static void bfa_ ## __mod ## _meminfo( \ + struct bfa_iocfc_cfg_s *cfg, u32 *ndm_len, \ + u32 *dm_len); \ + static void bfa_ ## __mod ## _attach(struct bfa_s *bfa, \ + void *bfad, struct bfa_iocfc_cfg_s *cfg, \ + struct bfa_meminfo_s *meminfo, \ + struct bfa_pcidev_s *pcidev); \ + static void bfa_ ## __mod ## _initdone(struct bfa_s *bfa); \ + static void bfa_ ## __mod ## _detach(struct bfa_s *bfa); \ + static void bfa_ ## __mod ## _start(struct bfa_s *bfa); \ + static void bfa_ ## __mod ## _stop(struct bfa_s *bfa); \ + static void bfa_ ## __mod ## _iocdisable(struct bfa_s *bfa); \ + \ + extern struct bfa_module_s hal_mod_ ## __mod; \ + struct bfa_module_s hal_mod_ ## __mod = { \ + bfa_ ## __mod ## _meminfo, \ + bfa_ ## __mod ## _attach, \ + bfa_ ## __mod ## _initdone, \ + bfa_ ## __mod ## _detach, \ + bfa_ ## __mod ## _start, \ + bfa_ ## __mod ## _stop, \ + bfa_ ## __mod ## _iocdisable, \ + } + +#define BFA_CACHELINE_SZ (256) + +/** + * Structure used to interact between different BFA sub modules + * + * Each sub module needs to implement only the entry points relevant to it (and + * can leave entry points as NULL) + */ +struct bfa_module_s { + void (*meminfo) (struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len); + void (*attach) (struct bfa_s *bfa, void *bfad, + struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, + struct bfa_pcidev_s *pcidev); + void (*initdone) (struct bfa_s *bfa); + void (*detach) (struct bfa_s *bfa); + void (*start) (struct bfa_s *bfa); + void (*stop) (struct bfa_s *bfa); + void (*iocdisable) (struct bfa_s *bfa); +}; + +extern struct bfa_module_s *hal_mods[]; + +struct bfa_s { + void *bfad; /* BFA driver instance */ + struct bfa_aen_s *aen; /* AEN module */ + struct bfa_plog_s *plog; /* portlog buffer */ + struct bfa_log_mod_s *logm; /* driver logging modulen */ + struct bfa_trc_mod_s *trcmod; /* driver tracing */ + struct bfa_ioc_s ioc; /* IOC module */ + struct bfa_iocfc_s iocfc; /* IOCFC module */ + struct bfa_timer_mod_s timer_mod; /* timer module */ + struct bfa_modules_s modules; /* BFA modules */ + struct list_head comp_q; /* pending completions */ + bfa_boolean_t rme_process; /* RME processing enabled */ + struct list_head reqq_waitq[BFI_IOC_MAX_CQS]; + bfa_boolean_t fcs; /* FCS is attached to BFA */ + struct bfa_msix_s msix; +}; + +extern bfa_isr_func_t bfa_isrs[BFI_MC_MAX]; +extern bfa_ioc_mbox_mcfunc_t bfa_mbox_isrs[]; +extern bfa_boolean_t bfa_auto_recover; +extern struct bfa_module_s hal_mod_flash; +extern struct bfa_module_s hal_mod_fcdiag; +extern struct bfa_module_s hal_mod_sgpg; +extern struct bfa_module_s hal_mod_pport; +extern struct bfa_module_s hal_mod_fcxp; +extern struct bfa_module_s hal_mod_lps; +extern struct bfa_module_s hal_mod_uf; +extern struct bfa_module_s hal_mod_rport; +extern struct bfa_module_s hal_mod_fcpim; +extern struct bfa_module_s hal_mod_pbind; + +#endif /* __BFA_PRIV_H__ */ + diff --git a/drivers/scsi/bfa/bfa_rport.c b/drivers/scsi/bfa/bfa_rport.c new file mode 100644 index 000000000000..16da77a8db28 --- /dev/null +++ b/drivers/scsi/bfa/bfa_rport.c @@ -0,0 +1,911 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include <cs/bfa_debug.h> +#include <bfi/bfi_rport.h> +#include "bfa_intr_priv.h" + +BFA_TRC_FILE(HAL, RPORT); +BFA_MODULE(rport); + +#define bfa_rport_offline_cb(__rp) do { \ + if ((__rp)->bfa->fcs) \ + bfa_cb_rport_offline((__rp)->rport_drv); \ + else { \ + bfa_cb_queue((__rp)->bfa, &(__rp)->hcb_qe, \ + __bfa_cb_rport_offline, (__rp)); \ + } \ +} while (0) + +#define bfa_rport_online_cb(__rp) do { \ + if ((__rp)->bfa->fcs) \ + bfa_cb_rport_online((__rp)->rport_drv); \ + else { \ + bfa_cb_queue((__rp)->bfa, &(__rp)->hcb_qe, \ + __bfa_cb_rport_online, (__rp)); \ + } \ +} while (0) + +/* + * forward declarations + */ +static struct bfa_rport_s *bfa_rport_alloc(struct bfa_rport_mod_s *rp_mod); +static void bfa_rport_free(struct bfa_rport_s *rport); +static bfa_boolean_t bfa_rport_send_fwcreate(struct bfa_rport_s *rp); +static bfa_boolean_t bfa_rport_send_fwdelete(struct bfa_rport_s *rp); +static bfa_boolean_t bfa_rport_send_fwspeed(struct bfa_rport_s *rp); +static void __bfa_cb_rport_online(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_rport_offline(void *cbarg, bfa_boolean_t complete); + +/** + * bfa_rport_sm BFA rport state machine + */ + + +enum bfa_rport_event { + BFA_RPORT_SM_CREATE = 1, /* rport create event */ + BFA_RPORT_SM_DELETE = 2, /* deleting an existing rport */ + BFA_RPORT_SM_ONLINE = 3, /* rport is online */ + BFA_RPORT_SM_OFFLINE = 4, /* rport is offline */ + BFA_RPORT_SM_FWRSP = 5, /* firmware response */ + BFA_RPORT_SM_HWFAIL = 6, /* IOC h/w failure */ + BFA_RPORT_SM_QOS_SCN = 7, /* QoS SCN from firmware */ + BFA_RPORT_SM_SET_SPEED = 8, /* Set Rport Speed */ + BFA_RPORT_SM_QRESUME = 9, /* space in requeue queue */ +}; + +static void bfa_rport_sm_uninit(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_created(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_fwcreate(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_online(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_fwdelete(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_offline(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_deleting(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_offline_pending(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_delete_pending(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_iocdisable(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_fwcreate_qfull(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_fwdelete_qfull(struct bfa_rport_s *rp, + enum bfa_rport_event event); +static void bfa_rport_sm_deleting_qfull(struct bfa_rport_s *rp, + enum bfa_rport_event event); + +/** + * Beginning state, only online event expected. + */ +static void +bfa_rport_sm_uninit(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_CREATE: + bfa_stats(rp, sm_un_cr); + bfa_sm_set_state(rp, bfa_rport_sm_created); + break; + + default: + bfa_stats(rp, sm_un_unexp); + bfa_assert(0); + } +} + +static void +bfa_rport_sm_created(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_ONLINE: + bfa_stats(rp, sm_cr_on); + if (bfa_rport_send_fwcreate(rp)) + bfa_sm_set_state(rp, bfa_rport_sm_fwcreate); + else + bfa_sm_set_state(rp, bfa_rport_sm_fwcreate_qfull); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_cr_del); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_rport_free(rp); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_cr_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + break; + + default: + bfa_stats(rp, sm_cr_unexp); + bfa_assert(0); + } +} + +/** + * Waiting for rport create response from firmware. + */ +static void +bfa_rport_sm_fwcreate(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_FWRSP: + bfa_stats(rp, sm_fwc_rsp); + bfa_sm_set_state(rp, bfa_rport_sm_online); + bfa_rport_online_cb(rp); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_fwc_del); + bfa_sm_set_state(rp, bfa_rport_sm_delete_pending); + break; + + case BFA_RPORT_SM_OFFLINE: + bfa_stats(rp, sm_fwc_off); + bfa_sm_set_state(rp, bfa_rport_sm_offline_pending); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_fwc_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + break; + + default: + bfa_stats(rp, sm_fwc_unexp); + bfa_assert(0); + } +} + +/** + * Request queue is full, awaiting queue resume to send create request. + */ +static void +bfa_rport_sm_fwcreate_qfull(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_QRESUME: + bfa_sm_set_state(rp, bfa_rport_sm_fwcreate); + bfa_rport_send_fwcreate(rp); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_fwc_del); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_reqq_wcancel(&rp->reqq_wait); + bfa_rport_free(rp); + break; + + case BFA_RPORT_SM_OFFLINE: + bfa_stats(rp, sm_fwc_off); + bfa_sm_set_state(rp, bfa_rport_sm_offline); + bfa_reqq_wcancel(&rp->reqq_wait); + bfa_rport_offline_cb(rp); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_fwc_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + bfa_reqq_wcancel(&rp->reqq_wait); + break; + + default: + bfa_stats(rp, sm_fwc_unexp); + bfa_assert(0); + } +} + +/** + * Online state - normal parking state. + */ +static void +bfa_rport_sm_online(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + struct bfi_rport_qos_scn_s *qos_scn; + + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_OFFLINE: + bfa_stats(rp, sm_on_off); + if (bfa_rport_send_fwdelete(rp)) + bfa_sm_set_state(rp, bfa_rport_sm_fwdelete); + else + bfa_sm_set_state(rp, bfa_rport_sm_fwdelete_qfull); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_on_del); + if (bfa_rport_send_fwdelete(rp)) + bfa_sm_set_state(rp, bfa_rport_sm_deleting); + else + bfa_sm_set_state(rp, bfa_rport_sm_deleting_qfull); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_on_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + break; + + case BFA_RPORT_SM_SET_SPEED: + bfa_rport_send_fwspeed(rp); + break; + + case BFA_RPORT_SM_QOS_SCN: + qos_scn = (struct bfi_rport_qos_scn_s *) rp->event_arg.fw_msg; + rp->qos_attr = qos_scn->new_qos_attr; + bfa_trc(rp->bfa, qos_scn->old_qos_attr.qos_flow_id); + bfa_trc(rp->bfa, qos_scn->new_qos_attr.qos_flow_id); + bfa_trc(rp->bfa, qos_scn->old_qos_attr.qos_priority); + bfa_trc(rp->bfa, qos_scn->new_qos_attr.qos_priority); + + qos_scn->old_qos_attr.qos_flow_id = + bfa_os_ntohl(qos_scn->old_qos_attr.qos_flow_id); + qos_scn->new_qos_attr.qos_flow_id = + bfa_os_ntohl(qos_scn->new_qos_attr.qos_flow_id); + qos_scn->old_qos_attr.qos_priority = + bfa_os_ntohl(qos_scn->old_qos_attr.qos_priority); + qos_scn->new_qos_attr.qos_priority = + bfa_os_ntohl(qos_scn->new_qos_attr.qos_priority); + + if (qos_scn->old_qos_attr.qos_flow_id != + qos_scn->new_qos_attr.qos_flow_id) + bfa_cb_rport_qos_scn_flowid(rp->rport_drv, + qos_scn->old_qos_attr, + qos_scn->new_qos_attr); + if (qos_scn->old_qos_attr.qos_priority != + qos_scn->new_qos_attr.qos_priority) + bfa_cb_rport_qos_scn_prio(rp->rport_drv, + qos_scn->old_qos_attr, + qos_scn->new_qos_attr); + break; + + default: + bfa_stats(rp, sm_on_unexp); + bfa_assert(0); + } +} + +/** + * Firmware rport is being deleted - awaiting f/w response. + */ +static void +bfa_rport_sm_fwdelete(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_FWRSP: + bfa_stats(rp, sm_fwd_rsp); + bfa_sm_set_state(rp, bfa_rport_sm_offline); + bfa_rport_offline_cb(rp); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_fwd_del); + bfa_sm_set_state(rp, bfa_rport_sm_deleting); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_fwd_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + bfa_rport_offline_cb(rp); + break; + + default: + bfa_stats(rp, sm_fwd_unexp); + bfa_assert(0); + } +} + +static void +bfa_rport_sm_fwdelete_qfull(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_QRESUME: + bfa_sm_set_state(rp, bfa_rport_sm_fwdelete); + bfa_rport_send_fwdelete(rp); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_fwd_del); + bfa_sm_set_state(rp, bfa_rport_sm_deleting_qfull); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_fwd_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + bfa_reqq_wcancel(&rp->reqq_wait); + bfa_rport_offline_cb(rp); + break; + + default: + bfa_stats(rp, sm_fwd_unexp); + bfa_assert(0); + } +} + +/** + * Offline state. + */ +static void +bfa_rport_sm_offline(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_off_del); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_rport_free(rp); + break; + + case BFA_RPORT_SM_ONLINE: + bfa_stats(rp, sm_off_on); + if (bfa_rport_send_fwcreate(rp)) + bfa_sm_set_state(rp, bfa_rport_sm_fwcreate); + else + bfa_sm_set_state(rp, bfa_rport_sm_fwcreate_qfull); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_off_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + break; + + default: + bfa_stats(rp, sm_off_unexp); + bfa_assert(0); + } +} + +/** + * Rport is deleted, waiting for firmware response to delete. + */ +static void +bfa_rport_sm_deleting(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_FWRSP: + bfa_stats(rp, sm_del_fwrsp); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_rport_free(rp); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_del_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_rport_free(rp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_rport_sm_deleting_qfull(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_QRESUME: + bfa_stats(rp, sm_del_fwrsp); + bfa_sm_set_state(rp, bfa_rport_sm_deleting); + bfa_rport_send_fwdelete(rp); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_del_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_reqq_wcancel(&rp->reqq_wait); + bfa_rport_free(rp); + break; + + default: + bfa_assert(0); + } +} + +/** + * Waiting for rport create response from firmware. A delete is pending. + */ +static void +bfa_rport_sm_delete_pending(struct bfa_rport_s *rp, + enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_FWRSP: + bfa_stats(rp, sm_delp_fwrsp); + if (bfa_rport_send_fwdelete(rp)) + bfa_sm_set_state(rp, bfa_rport_sm_deleting); + else + bfa_sm_set_state(rp, bfa_rport_sm_deleting_qfull); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_delp_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_rport_free(rp); + break; + + default: + bfa_stats(rp, sm_delp_unexp); + bfa_assert(0); + } +} + +/** + * Waiting for rport create response from firmware. Rport offline is pending. + */ +static void +bfa_rport_sm_offline_pending(struct bfa_rport_s *rp, + enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_FWRSP: + bfa_stats(rp, sm_offp_fwrsp); + if (bfa_rport_send_fwdelete(rp)) + bfa_sm_set_state(rp, bfa_rport_sm_fwdelete); + else + bfa_sm_set_state(rp, bfa_rport_sm_fwdelete_qfull); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_offp_del); + bfa_sm_set_state(rp, bfa_rport_sm_delete_pending); + break; + + case BFA_RPORT_SM_HWFAIL: + bfa_stats(rp, sm_offp_hwf); + bfa_sm_set_state(rp, bfa_rport_sm_iocdisable); + break; + + default: + bfa_stats(rp, sm_offp_unexp); + bfa_assert(0); + } +} + +/** + * IOC h/w failed. + */ +static void +bfa_rport_sm_iocdisable(struct bfa_rport_s *rp, enum bfa_rport_event event) +{ + bfa_trc(rp->bfa, rp->rport_tag); + bfa_trc(rp->bfa, event); + + switch (event) { + case BFA_RPORT_SM_OFFLINE: + bfa_stats(rp, sm_iocd_off); + bfa_rport_offline_cb(rp); + break; + + case BFA_RPORT_SM_DELETE: + bfa_stats(rp, sm_iocd_del); + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + bfa_rport_free(rp); + break; + + case BFA_RPORT_SM_ONLINE: + bfa_stats(rp, sm_iocd_on); + if (bfa_rport_send_fwcreate(rp)) + bfa_sm_set_state(rp, bfa_rport_sm_fwcreate); + else + bfa_sm_set_state(rp, bfa_rport_sm_fwcreate_qfull); + break; + + case BFA_RPORT_SM_HWFAIL: + break; + + default: + bfa_stats(rp, sm_iocd_unexp); + bfa_assert(0); + } +} + + + +/** + * bfa_rport_private BFA rport private functions + */ + +static void +__bfa_cb_rport_online(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_rport_s *rp = cbarg; + + if (complete) + bfa_cb_rport_online(rp->rport_drv); +} + +static void +__bfa_cb_rport_offline(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_rport_s *rp = cbarg; + + if (complete) + bfa_cb_rport_offline(rp->rport_drv); +} + +static void +bfa_rport_qresume(void *cbarg) +{ + struct bfa_rport_s *rp = cbarg; + + bfa_sm_send_event(rp, BFA_RPORT_SM_QRESUME); +} + +static void +bfa_rport_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len) +{ + if (cfg->fwcfg.num_rports < BFA_RPORT_MIN) + cfg->fwcfg.num_rports = BFA_RPORT_MIN; + + *km_len += cfg->fwcfg.num_rports * sizeof(struct bfa_rport_s); +} + +static void +bfa_rport_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + struct bfa_rport_mod_s *mod = BFA_RPORT_MOD(bfa); + struct bfa_rport_s *rp; + u16 i; + + INIT_LIST_HEAD(&mod->rp_free_q); + INIT_LIST_HEAD(&mod->rp_active_q); + + rp = (struct bfa_rport_s *) bfa_meminfo_kva(meminfo); + mod->rps_list = rp; + mod->num_rports = cfg->fwcfg.num_rports; + + bfa_assert(mod->num_rports + && !(mod->num_rports & (mod->num_rports - 1))); + + for (i = 0; i < mod->num_rports; i++, rp++) { + bfa_os_memset(rp, 0, sizeof(struct bfa_rport_s)); + rp->bfa = bfa; + rp->rport_tag = i; + bfa_sm_set_state(rp, bfa_rport_sm_uninit); + + /** + * - is unused + */ + if (i) + list_add_tail(&rp->qe, &mod->rp_free_q); + + bfa_reqq_winit(&rp->reqq_wait, bfa_rport_qresume, rp); + } + + /** + * consume memory + */ + bfa_meminfo_kva(meminfo) = (u8 *) rp; +} + +static void +bfa_rport_initdone(struct bfa_s *bfa) +{ +} + +static void +bfa_rport_detach(struct bfa_s *bfa) +{ +} + +static void +bfa_rport_start(struct bfa_s *bfa) +{ +} + +static void +bfa_rport_stop(struct bfa_s *bfa) +{ +} + +static void +bfa_rport_iocdisable(struct bfa_s *bfa) +{ + struct bfa_rport_mod_s *mod = BFA_RPORT_MOD(bfa); + struct bfa_rport_s *rport; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &mod->rp_active_q) { + rport = (struct bfa_rport_s *) qe; + bfa_sm_send_event(rport, BFA_RPORT_SM_HWFAIL); + } +} + +static struct bfa_rport_s * +bfa_rport_alloc(struct bfa_rport_mod_s *mod) +{ + struct bfa_rport_s *rport; + + bfa_q_deq(&mod->rp_free_q, &rport); + if (rport) + list_add_tail(&rport->qe, &mod->rp_active_q); + + return (rport); +} + +static void +bfa_rport_free(struct bfa_rport_s *rport) +{ + struct bfa_rport_mod_s *mod = BFA_RPORT_MOD(rport->bfa); + + bfa_assert(bfa_q_is_on_q(&mod->rp_active_q, rport)); + list_del(&rport->qe); + list_add_tail(&rport->qe, &mod->rp_free_q); +} + +static bfa_boolean_t +bfa_rport_send_fwcreate(struct bfa_rport_s *rp) +{ + struct bfi_rport_create_req_s *m; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(rp->bfa, BFA_REQQ_RPORT); + if (!m) { + bfa_reqq_wait(rp->bfa, BFA_REQQ_RPORT, &rp->reqq_wait); + return BFA_FALSE; + } + + bfi_h2i_set(m->mh, BFI_MC_RPORT, BFI_RPORT_H2I_CREATE_REQ, + bfa_lpuid(rp->bfa)); + m->bfa_handle = rp->rport_tag; + m->max_frmsz = bfa_os_htons(rp->rport_info.max_frmsz); + m->pid = rp->rport_info.pid; + m->lp_tag = rp->rport_info.lp_tag; + m->local_pid = rp->rport_info.local_pid; + m->fc_class = rp->rport_info.fc_class; + m->vf_en = rp->rport_info.vf_en; + m->vf_id = rp->rport_info.vf_id; + m->cisc = rp->rport_info.cisc; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(rp->bfa, BFA_REQQ_RPORT); + return BFA_TRUE; +} + +static bfa_boolean_t +bfa_rport_send_fwdelete(struct bfa_rport_s *rp) +{ + struct bfi_rport_delete_req_s *m; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(rp->bfa, BFA_REQQ_RPORT); + if (!m) { + bfa_reqq_wait(rp->bfa, BFA_REQQ_RPORT, &rp->reqq_wait); + return BFA_FALSE; + } + + bfi_h2i_set(m->mh, BFI_MC_RPORT, BFI_RPORT_H2I_DELETE_REQ, + bfa_lpuid(rp->bfa)); + m->fw_handle = rp->fw_handle; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(rp->bfa, BFA_REQQ_RPORT); + return BFA_TRUE; +} + +static bfa_boolean_t +bfa_rport_send_fwspeed(struct bfa_rport_s *rp) +{ + struct bfa_rport_speed_req_s *m; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(rp->bfa, BFA_REQQ_RPORT); + if (!m) { + bfa_trc(rp->bfa, rp->rport_info.speed); + return BFA_FALSE; + } + + bfi_h2i_set(m->mh, BFI_MC_RPORT, BFI_RPORT_H2I_SET_SPEED_REQ, + bfa_lpuid(rp->bfa)); + m->fw_handle = rp->fw_handle; + m->speed = (u8)rp->rport_info.speed; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(rp->bfa, BFA_REQQ_RPORT); + return BFA_TRUE; +} + + + +/** + * bfa_rport_public + */ + +/** + * Rport interrupt processing. + */ +void +bfa_rport_isr(struct bfa_s *bfa, struct bfi_msg_s *m) +{ + union bfi_rport_i2h_msg_u msg; + struct bfa_rport_s *rp; + + bfa_trc(bfa, m->mhdr.msg_id); + + msg.msg = m; + + switch (m->mhdr.msg_id) { + case BFI_RPORT_I2H_CREATE_RSP: + rp = BFA_RPORT_FROM_TAG(bfa, msg.create_rsp->bfa_handle); + rp->fw_handle = msg.create_rsp->fw_handle; + rp->qos_attr = msg.create_rsp->qos_attr; + bfa_assert(msg.create_rsp->status == BFA_STATUS_OK); + bfa_sm_send_event(rp, BFA_RPORT_SM_FWRSP); + break; + + case BFI_RPORT_I2H_DELETE_RSP: + rp = BFA_RPORT_FROM_TAG(bfa, msg.delete_rsp->bfa_handle); + bfa_assert(msg.delete_rsp->status == BFA_STATUS_OK); + bfa_sm_send_event(rp, BFA_RPORT_SM_FWRSP); + break; + + case BFI_RPORT_I2H_QOS_SCN: + rp = BFA_RPORT_FROM_TAG(bfa, msg.qos_scn_evt->bfa_handle); + rp->event_arg.fw_msg = msg.qos_scn_evt; + bfa_sm_send_event(rp, BFA_RPORT_SM_QOS_SCN); + break; + + default: + bfa_trc(bfa, m->mhdr.msg_id); + bfa_assert(0); + } +} + + + +/** + * bfa_rport_api + */ + +struct bfa_rport_s * +bfa_rport_create(struct bfa_s *bfa, void *rport_drv) +{ + struct bfa_rport_s *rp; + + rp = bfa_rport_alloc(BFA_RPORT_MOD(bfa)); + + if (rp == NULL) + return (NULL); + + rp->bfa = bfa; + rp->rport_drv = rport_drv; + bfa_rport_clear_stats(rp); + + bfa_assert(bfa_sm_cmp_state(rp, bfa_rport_sm_uninit)); + bfa_sm_send_event(rp, BFA_RPORT_SM_CREATE); + + return (rp); +} + +void +bfa_rport_delete(struct bfa_rport_s *rport) +{ + bfa_sm_send_event(rport, BFA_RPORT_SM_DELETE); +} + +void +bfa_rport_online(struct bfa_rport_s *rport, struct bfa_rport_info_s *rport_info) +{ + bfa_assert(rport_info->max_frmsz != 0); + + /** + * Some JBODs are seen to be not setting PDU size correctly in PLOGI + * responses. Default to minimum size. + */ + if (rport_info->max_frmsz == 0) { + bfa_trc(rport->bfa, rport->rport_tag); + rport_info->max_frmsz = FC_MIN_PDUSZ; + } + + bfa_os_assign(rport->rport_info, *rport_info); + bfa_sm_send_event(rport, BFA_RPORT_SM_ONLINE); +} + +void +bfa_rport_offline(struct bfa_rport_s *rport) +{ + bfa_sm_send_event(rport, BFA_RPORT_SM_OFFLINE); +} + +void +bfa_rport_speed(struct bfa_rport_s *rport, enum bfa_pport_speed speed) +{ + bfa_assert(speed != 0); + bfa_assert(speed != BFA_PPORT_SPEED_AUTO); + + rport->rport_info.speed = speed; + bfa_sm_send_event(rport, BFA_RPORT_SM_SET_SPEED); +} + +void +bfa_rport_get_stats(struct bfa_rport_s *rport, + struct bfa_rport_hal_stats_s *stats) +{ + *stats = rport->stats; +} + +void +bfa_rport_get_qos_attr(struct bfa_rport_s *rport, + struct bfa_rport_qos_attr_s *qos_attr) +{ + qos_attr->qos_priority = bfa_os_ntohl(rport->qos_attr.qos_priority); + qos_attr->qos_flow_id = bfa_os_ntohl(rport->qos_attr.qos_flow_id); + +} + +void +bfa_rport_clear_stats(struct bfa_rport_s *rport) +{ + bfa_os_memset(&rport->stats, 0, sizeof(rport->stats)); +} + + diff --git a/drivers/scsi/bfa/bfa_rport_priv.h b/drivers/scsi/bfa/bfa_rport_priv.h new file mode 100644 index 000000000000..6490ce2e990d --- /dev/null +++ b/drivers/scsi/bfa/bfa_rport_priv.h @@ -0,0 +1,45 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_RPORT_PRIV_H__ +#define __BFA_RPORT_PRIV_H__ + +#include <bfa_svc.h> + +#define BFA_RPORT_MIN 4 + +struct bfa_rport_mod_s { + struct bfa_rport_s *rps_list; /* list of rports */ + struct list_head rp_free_q; /* free bfa_rports */ + struct list_head rp_active_q; /* free bfa_rports */ + u16 num_rports; /* number of rports */ +}; + +#define BFA_RPORT_MOD(__bfa) (&(__bfa)->modules.rport_mod) + +/** + * Convert rport tag to RPORT + */ +#define BFA_RPORT_FROM_TAG(__bfa, _tag) \ + (BFA_RPORT_MOD(__bfa)->rps_list + \ + ((_tag) & (BFA_RPORT_MOD(__bfa)->num_rports - 1))) + +/* + * external functions + */ +void bfa_rport_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); +#endif /* __BFA_RPORT_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_sgpg.c b/drivers/scsi/bfa/bfa_sgpg.c new file mode 100644 index 000000000000..279d8f9b8907 --- /dev/null +++ b/drivers/scsi/bfa/bfa_sgpg.c @@ -0,0 +1,231 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> + +BFA_TRC_FILE(HAL, SGPG); +BFA_MODULE(sgpg); + +/** + * bfa_sgpg_mod BFA SGPG Mode module + */ + +/** + * Compute and return memory needed by FCP(im) module. + */ +static void +bfa_sgpg_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *km_len, + u32 *dm_len) +{ + if (cfg->drvcfg.num_sgpgs < BFA_SGPG_MIN) + cfg->drvcfg.num_sgpgs = BFA_SGPG_MIN; + + *km_len += (cfg->drvcfg.num_sgpgs + 1) * sizeof(struct bfa_sgpg_s); + *dm_len += (cfg->drvcfg.num_sgpgs + 1) * sizeof(struct bfi_sgpg_s); +} + + +static void +bfa_sgpg_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *minfo, struct bfa_pcidev_s *pcidev) +{ + struct bfa_sgpg_mod_s *mod = BFA_SGPG_MOD(bfa); + int i; + struct bfa_sgpg_s *hsgpg; + struct bfi_sgpg_s *sgpg; + u64 align_len; + + union { + u64 pa; + union bfi_addr_u addr; + } sgpg_pa; + + INIT_LIST_HEAD(&mod->sgpg_q); + INIT_LIST_HEAD(&mod->sgpg_wait_q); + + bfa_trc(bfa, cfg->drvcfg.num_sgpgs); + + mod->num_sgpgs = cfg->drvcfg.num_sgpgs; + mod->sgpg_arr_pa = bfa_meminfo_dma_phys(minfo); + align_len = (BFA_SGPG_ROUNDUP(mod->sgpg_arr_pa) - mod->sgpg_arr_pa); + mod->sgpg_arr_pa += align_len; + mod->hsgpg_arr = (struct bfa_sgpg_s *) (bfa_meminfo_kva(minfo) + + align_len); + mod->sgpg_arr = (struct bfi_sgpg_s *) (bfa_meminfo_dma_virt(minfo) + + align_len); + + hsgpg = mod->hsgpg_arr; + sgpg = mod->sgpg_arr; + sgpg_pa.pa = mod->sgpg_arr_pa; + mod->free_sgpgs = mod->num_sgpgs; + + bfa_assert(!(sgpg_pa.pa & (sizeof(struct bfi_sgpg_s) - 1))); + + for (i = 0; i < mod->num_sgpgs; i++) { + bfa_os_memset(hsgpg, 0, sizeof(*hsgpg)); + bfa_os_memset(sgpg, 0, sizeof(*sgpg)); + + hsgpg->sgpg = sgpg; + hsgpg->sgpg_pa = sgpg_pa.addr; + list_add_tail(&hsgpg->qe, &mod->sgpg_q); + + hsgpg++; + sgpg++; + sgpg_pa.pa += sizeof(struct bfi_sgpg_s); + } + + bfa_meminfo_kva(minfo) = (u8 *) hsgpg; + bfa_meminfo_dma_virt(minfo) = (u8 *) sgpg; + bfa_meminfo_dma_phys(minfo) = sgpg_pa.pa; +} + +static void +bfa_sgpg_initdone(struct bfa_s *bfa) +{ +} + +static void +bfa_sgpg_detach(struct bfa_s *bfa) +{ +} + +static void +bfa_sgpg_start(struct bfa_s *bfa) +{ +} + +static void +bfa_sgpg_stop(struct bfa_s *bfa) +{ +} + +static void +bfa_sgpg_iocdisable(struct bfa_s *bfa) +{ +} + + + +/** + * bfa_sgpg_public BFA SGPG public functions + */ + +bfa_status_t +bfa_sgpg_malloc(struct bfa_s *bfa, struct list_head *sgpg_q, int nsgpgs) +{ + struct bfa_sgpg_mod_s *mod = BFA_SGPG_MOD(bfa); + struct bfa_sgpg_s *hsgpg; + int i; + + bfa_trc_fp(bfa, nsgpgs); + + if (mod->free_sgpgs < nsgpgs) + return BFA_STATUS_ENOMEM; + + for (i = 0; i < nsgpgs; i++) { + bfa_q_deq(&mod->sgpg_q, &hsgpg); + bfa_assert(hsgpg); + list_add_tail(&hsgpg->qe, sgpg_q); + } + + mod->free_sgpgs -= nsgpgs; + return BFA_STATUS_OK; +} + +void +bfa_sgpg_mfree(struct bfa_s *bfa, struct list_head *sgpg_q, int nsgpg) +{ + struct bfa_sgpg_mod_s *mod = BFA_SGPG_MOD(bfa); + struct bfa_sgpg_wqe_s *wqe; + + bfa_trc_fp(bfa, nsgpg); + + mod->free_sgpgs += nsgpg; + bfa_assert(mod->free_sgpgs <= mod->num_sgpgs); + + list_splice_tail_init(sgpg_q, &mod->sgpg_q); + + if (list_empty(&mod->sgpg_wait_q)) + return; + + /** + * satisfy as many waiting requests as possible + */ + do { + wqe = bfa_q_first(&mod->sgpg_wait_q); + if (mod->free_sgpgs < wqe->nsgpg) + nsgpg = mod->free_sgpgs; + else + nsgpg = wqe->nsgpg; + bfa_sgpg_malloc(bfa, &wqe->sgpg_q, nsgpg); + wqe->nsgpg -= nsgpg; + if (wqe->nsgpg == 0) { + list_del(&wqe->qe); + wqe->cbfn(wqe->cbarg); + } + } while (mod->free_sgpgs && !list_empty(&mod->sgpg_wait_q)); +} + +void +bfa_sgpg_wait(struct bfa_s *bfa, struct bfa_sgpg_wqe_s *wqe, int nsgpg) +{ + struct bfa_sgpg_mod_s *mod = BFA_SGPG_MOD(bfa); + + bfa_assert(nsgpg > 0); + bfa_assert(nsgpg > mod->free_sgpgs); + + wqe->nsgpg_total = wqe->nsgpg = nsgpg; + + /** + * allocate any left to this one first + */ + if (mod->free_sgpgs) { + /** + * no one else is waiting for SGPG + */ + bfa_assert(list_empty(&mod->sgpg_wait_q)); + list_splice_tail_init(&mod->sgpg_q, &wqe->sgpg_q); + wqe->nsgpg -= mod->free_sgpgs; + mod->free_sgpgs = 0; + } + + list_add_tail(&wqe->qe, &mod->sgpg_wait_q); +} + +void +bfa_sgpg_wcancel(struct bfa_s *bfa, struct bfa_sgpg_wqe_s *wqe) +{ + struct bfa_sgpg_mod_s *mod = BFA_SGPG_MOD(bfa); + + bfa_assert(bfa_q_is_on_q(&mod->sgpg_wait_q, wqe)); + list_del(&wqe->qe); + + if (wqe->nsgpg_total != wqe->nsgpg) + bfa_sgpg_mfree(bfa, &wqe->sgpg_q, + wqe->nsgpg_total - wqe->nsgpg); +} + +void +bfa_sgpg_winit(struct bfa_sgpg_wqe_s *wqe, void (*cbfn) (void *cbarg), + void *cbarg) +{ + INIT_LIST_HEAD(&wqe->sgpg_q); + wqe->cbfn = cbfn; + wqe->cbarg = cbarg; +} + + diff --git a/drivers/scsi/bfa/bfa_sgpg_priv.h b/drivers/scsi/bfa/bfa_sgpg_priv.h new file mode 100644 index 000000000000..9c2a8cbe7522 --- /dev/null +++ b/drivers/scsi/bfa/bfa_sgpg_priv.h @@ -0,0 +1,79 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * hal_sgpg.h BFA SG page module + */ + +#ifndef __BFA_SGPG_PRIV_H__ +#define __BFA_SGPG_PRIV_H__ + +#include <cs/bfa_q.h> + +#define BFA_SGPG_MIN (16) + +/** + * Alignment macro for SG page allocation + */ +#define BFA_SGPG_ROUNDUP(_l) (((_l) + (sizeof(struct bfi_sgpg_s) - 1)) \ + & ~(sizeof(struct bfi_sgpg_s) - 1)) + +struct bfa_sgpg_wqe_s { + struct list_head qe; /* queue sg page element */ + int nsgpg; /* pages to be allocated */ + int nsgpg_total; /* total pages required */ + void (*cbfn) (void *cbarg); + /* callback function */ + void *cbarg; /* callback arg */ + struct list_head sgpg_q; /* queue of alloced sgpgs */ +}; + +struct bfa_sgpg_s { + struct list_head qe; /* queue sg page element */ + struct bfi_sgpg_s *sgpg; /* va of SG page */ + union bfi_addr_u sgpg_pa;/* pa of SG page */ +}; + +/** + * Given number of SG elements, BFA_SGPG_NPAGE() returns the number of + * SG pages required. + */ +#define BFA_SGPG_NPAGE(_nsges) (((_nsges) / BFI_SGPG_DATA_SGES) + 1) + +struct bfa_sgpg_mod_s { + struct bfa_s *bfa; + int num_sgpgs; /* number of SG pages */ + int free_sgpgs; /* number of free SG pages */ + struct bfa_sgpg_s *hsgpg_arr; /* BFA SG page array */ + struct bfi_sgpg_s *sgpg_arr; /* actual SG page array */ + u64 sgpg_arr_pa; /* SG page array DMA addr */ + struct list_head sgpg_q; /* queue of free SG pages */ + struct list_head sgpg_wait_q; /* wait queue for SG pages */ +}; +#define BFA_SGPG_MOD(__bfa) (&(__bfa)->modules.sgpg_mod) + +bfa_status_t bfa_sgpg_malloc(struct bfa_s *bfa, struct list_head *sgpg_q, + int nsgpgs); +void bfa_sgpg_mfree(struct bfa_s *bfa, struct list_head *sgpg_q, + int nsgpgs); +void bfa_sgpg_winit(struct bfa_sgpg_wqe_s *wqe, + void (*cbfn) (void *cbarg), void *cbarg); +void bfa_sgpg_wait(struct bfa_s *bfa, struct bfa_sgpg_wqe_s *wqe, + int nsgpgs); +void bfa_sgpg_wcancel(struct bfa_s *bfa, struct bfa_sgpg_wqe_s *wqe); + +#endif /* __BFA_SGPG_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_sm.c b/drivers/scsi/bfa/bfa_sm.c new file mode 100644 index 000000000000..5420f4f45e58 --- /dev/null +++ b/drivers/scsi/bfa/bfa_sm.c @@ -0,0 +1,38 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfasm.c BFA State machine utility functions + */ + +#include <cs/bfa_sm.h> + +/** + * cs_sm_api + */ + +int +bfa_sm_to_state(struct bfa_sm_table_s *smt, bfa_sm_t sm) +{ + int i = 0; + + while (smt[i].sm && smt[i].sm != sm) + i++; + return smt[i].state; +} + + diff --git a/drivers/scsi/bfa/bfa_timer.c b/drivers/scsi/bfa/bfa_timer.c new file mode 100644 index 000000000000..cb76481f5cb1 --- /dev/null +++ b/drivers/scsi/bfa/bfa_timer.c @@ -0,0 +1,90 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa_timer.h> +#include <cs/bfa_debug.h> + +void +bfa_timer_init(struct bfa_timer_mod_s *mod) +{ + INIT_LIST_HEAD(&mod->timer_q); +} + +void +bfa_timer_beat(struct bfa_timer_mod_s *mod) +{ + struct list_head *qh = &mod->timer_q; + struct list_head *qe, *qe_next; + struct bfa_timer_s *elem; + struct list_head timedout_q; + + INIT_LIST_HEAD(&timedout_q); + + qe = bfa_q_next(qh); + + while (qe != qh) { + qe_next = bfa_q_next(qe); + + elem = (struct bfa_timer_s *) qe; + if (elem->timeout <= BFA_TIMER_FREQ) { + elem->timeout = 0; + list_del(&elem->qe); + list_add_tail(&elem->qe, &timedout_q); + } else { + elem->timeout -= BFA_TIMER_FREQ; + } + + qe = qe_next; /* go to next elem */ + } + + /* + * Pop all the timeout entries + */ + while (!list_empty(&timedout_q)) { + bfa_q_deq(&timedout_q, &elem); + elem->timercb(elem->arg); + } +} + +/** + * Should be called with lock protection + */ +void +bfa_timer_begin(struct bfa_timer_mod_s *mod, struct bfa_timer_s *timer, + void (*timercb) (void *), void *arg, unsigned int timeout) +{ + + bfa_assert(timercb != NULL); + bfa_assert(!bfa_q_is_on_q(&mod->timer_q, timer)); + + timer->timeout = timeout; + timer->timercb = timercb; + timer->arg = arg; + + list_add_tail(&timer->qe, &mod->timer_q); +} + +/** + * Should be called with lock protection + */ +void +bfa_timer_stop(struct bfa_timer_s *timer) +{ + bfa_assert(!list_empty(&timer->qe)); + + list_del(&timer->qe); +} diff --git a/drivers/scsi/bfa/bfa_trcmod_priv.h b/drivers/scsi/bfa/bfa_trcmod_priv.h new file mode 100644 index 000000000000..b3562dce7e9f --- /dev/null +++ b/drivers/scsi/bfa/bfa_trcmod_priv.h @@ -0,0 +1,66 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * hal_trcmod.h BFA trace modules + */ + +#ifndef __BFA_TRCMOD_PRIV_H__ +#define __BFA_TRCMOD_PRIV_H__ + +#include <cs/bfa_trc.h> + +/* + * !!! Only append to the enums defined here to avoid any versioning + * !!! needed between trace utility and driver version + */ +enum { + BFA_TRC_HAL_IOC = 1, + BFA_TRC_HAL_INTR = 2, + BFA_TRC_HAL_FCXP = 3, + BFA_TRC_HAL_UF = 4, + BFA_TRC_HAL_DIAG = 5, + BFA_TRC_HAL_RPORT = 6, + BFA_TRC_HAL_FCPIM = 7, + BFA_TRC_HAL_IOIM = 8, + BFA_TRC_HAL_TSKIM = 9, + BFA_TRC_HAL_ITNIM = 10, + BFA_TRC_HAL_PPORT = 11, + BFA_TRC_HAL_SGPG = 12, + BFA_TRC_HAL_FLASH = 13, + BFA_TRC_HAL_DEBUG = 14, + BFA_TRC_HAL_WWN = 15, + BFA_TRC_HAL_FLASH_RAW = 16, + BFA_TRC_HAL_SBOOT = 17, + BFA_TRC_HAL_SBOOT_IO = 18, + BFA_TRC_HAL_SBOOT_INTR = 19, + BFA_TRC_HAL_SBTEST = 20, + BFA_TRC_HAL_IPFC = 21, + BFA_TRC_HAL_IOCFC = 22, + BFA_TRC_HAL_FCPTM = 23, + BFA_TRC_HAL_IOTM = 24, + BFA_TRC_HAL_TSKTM = 25, + BFA_TRC_HAL_TIN = 26, + BFA_TRC_HAL_LPS = 27, + BFA_TRC_HAL_FCDIAG = 28, + BFA_TRC_HAL_PBIND = 29, + BFA_TRC_HAL_IOCFC_CT = 30, + BFA_TRC_HAL_IOCFC_CB = 31, + BFA_TRC_HAL_IOCFC_Q = 32, +}; + +#endif /* __BFA_TRCMOD_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfa_tskim.c b/drivers/scsi/bfa/bfa_tskim.c new file mode 100644 index 000000000000..010d40d1e5d3 --- /dev/null +++ b/drivers/scsi/bfa/bfa_tskim.c @@ -0,0 +1,689 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfa_cb_ioim_macros.h> + +BFA_TRC_FILE(HAL, TSKIM); + +/** + * task management completion handling + */ +#define bfa_tskim_qcomp(__tskim, __cbfn) do { \ + bfa_cb_queue((__tskim)->bfa, &(__tskim)->hcb_qe, __cbfn, (__tskim)); \ + bfa_tskim_notify_comp(__tskim); \ +} while (0) + +#define bfa_tskim_notify_comp(__tskim) do { \ + if ((__tskim)->notify) \ + bfa_itnim_tskdone((__tskim)->itnim); \ +} while (0) + +/* + * forward declarations + */ +static void __bfa_cb_tskim_done(void *cbarg, bfa_boolean_t complete); +static void __bfa_cb_tskim_failed(void *cbarg, bfa_boolean_t complete); +static bfa_boolean_t bfa_tskim_match_scope(struct bfa_tskim_s *tskim, + lun_t lun); +static void bfa_tskim_gather_ios(struct bfa_tskim_s *tskim); +static void bfa_tskim_cleanp_comp(void *tskim_cbarg); +static void bfa_tskim_cleanup_ios(struct bfa_tskim_s *tskim); +static bfa_boolean_t bfa_tskim_send(struct bfa_tskim_s *tskim); +static bfa_boolean_t bfa_tskim_send_abort(struct bfa_tskim_s *tskim); +static void bfa_tskim_iocdisable_ios(struct bfa_tskim_s *tskim); + +/** + * bfa_tskim_sm + */ + +enum bfa_tskim_event { + BFA_TSKIM_SM_START = 1, /* TM command start */ + BFA_TSKIM_SM_DONE = 2, /* TM completion */ + BFA_TSKIM_SM_QRESUME = 3, /* resume after qfull */ + BFA_TSKIM_SM_HWFAIL = 5, /* IOC h/w failure event */ + BFA_TSKIM_SM_HCB = 6, /* BFA callback completion */ + BFA_TSKIM_SM_IOS_DONE = 7, /* IO and sub TM completions */ + BFA_TSKIM_SM_CLEANUP = 8, /* TM cleanup on ITN offline */ + BFA_TSKIM_SM_CLEANUP_DONE = 9, /* TM abort completion */ +}; + +static void bfa_tskim_sm_uninit(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event); +static void bfa_tskim_sm_active(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event); +static void bfa_tskim_sm_cleanup(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event); +static void bfa_tskim_sm_iocleanup(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event); +static void bfa_tskim_sm_qfull(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event); +static void bfa_tskim_sm_cleanup_qfull(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event); +static void bfa_tskim_sm_hcb(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event); + +/** + * Task management command beginning state. + */ +static void +bfa_tskim_sm_uninit(struct bfa_tskim_s *tskim, enum bfa_tskim_event event) +{ + bfa_trc(tskim->bfa, event); + + switch (event) { + case BFA_TSKIM_SM_START: + bfa_sm_set_state(tskim, bfa_tskim_sm_active); + bfa_tskim_gather_ios(tskim); + + /** + * If device is offline, do not send TM on wire. Just cleanup + * any pending IO requests and complete TM request. + */ + if (!bfa_itnim_is_online(tskim->itnim)) { + bfa_sm_set_state(tskim, bfa_tskim_sm_iocleanup); + tskim->tsk_status = BFI_TSKIM_STS_OK; + bfa_tskim_cleanup_ios(tskim); + return; + } + + if (!bfa_tskim_send(tskim)) { + bfa_sm_set_state(tskim, bfa_tskim_sm_qfull); + bfa_reqq_wait(tskim->bfa, tskim->itnim->reqq, + &tskim->reqq_wait); + } + break; + + default: + bfa_assert(0); + } +} + +/** + * brief + * TM command is active, awaiting completion from firmware to + * cleanup IO requests in TM scope. + */ +static void +bfa_tskim_sm_active(struct bfa_tskim_s *tskim, enum bfa_tskim_event event) +{ + bfa_trc(tskim->bfa, event); + + switch (event) { + case BFA_TSKIM_SM_DONE: + bfa_sm_set_state(tskim, bfa_tskim_sm_iocleanup); + bfa_tskim_cleanup_ios(tskim); + break; + + case BFA_TSKIM_SM_CLEANUP: + bfa_sm_set_state(tskim, bfa_tskim_sm_cleanup); + if (!bfa_tskim_send_abort(tskim)) { + bfa_sm_set_state(tskim, bfa_tskim_sm_cleanup_qfull); + bfa_reqq_wait(tskim->bfa, tskim->itnim->reqq, + &tskim->reqq_wait); + } + break; + + case BFA_TSKIM_SM_HWFAIL: + bfa_sm_set_state(tskim, bfa_tskim_sm_hcb); + bfa_tskim_iocdisable_ios(tskim); + bfa_tskim_qcomp(tskim, __bfa_cb_tskim_failed); + break; + + default: + bfa_assert(0); + } +} + +/** + * An active TM is being cleaned up since ITN is offline. Awaiting cleanup + * completion event from firmware. + */ +static void +bfa_tskim_sm_cleanup(struct bfa_tskim_s *tskim, enum bfa_tskim_event event) +{ + bfa_trc(tskim->bfa, event); + + switch (event) { + case BFA_TSKIM_SM_DONE: + /** + * Ignore and wait for ABORT completion from firmware. + */ + break; + + case BFA_TSKIM_SM_CLEANUP_DONE: + bfa_sm_set_state(tskim, bfa_tskim_sm_iocleanup); + bfa_tskim_cleanup_ios(tskim); + break; + + case BFA_TSKIM_SM_HWFAIL: + bfa_sm_set_state(tskim, bfa_tskim_sm_hcb); + bfa_tskim_iocdisable_ios(tskim); + bfa_tskim_qcomp(tskim, __bfa_cb_tskim_failed); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_tskim_sm_iocleanup(struct bfa_tskim_s *tskim, enum bfa_tskim_event event) +{ + bfa_trc(tskim->bfa, event); + + switch (event) { + case BFA_TSKIM_SM_IOS_DONE: + bfa_sm_set_state(tskim, bfa_tskim_sm_hcb); + bfa_tskim_qcomp(tskim, __bfa_cb_tskim_done); + break; + + case BFA_TSKIM_SM_CLEANUP: + /** + * Ignore, TM command completed on wire. + * Notify TM conmpletion on IO cleanup completion. + */ + break; + + case BFA_TSKIM_SM_HWFAIL: + bfa_sm_set_state(tskim, bfa_tskim_sm_hcb); + bfa_tskim_iocdisable_ios(tskim); + bfa_tskim_qcomp(tskim, __bfa_cb_tskim_failed); + break; + + default: + bfa_assert(0); + } +} + +/** + * Task management command is waiting for room in request CQ + */ +static void +bfa_tskim_sm_qfull(struct bfa_tskim_s *tskim, enum bfa_tskim_event event) +{ + bfa_trc(tskim->bfa, event); + + switch (event) { + case BFA_TSKIM_SM_QRESUME: + bfa_sm_set_state(tskim, bfa_tskim_sm_active); + bfa_tskim_send(tskim); + break; + + case BFA_TSKIM_SM_CLEANUP: + /** + * No need to send TM on wire since ITN is offline. + */ + bfa_sm_set_state(tskim, bfa_tskim_sm_iocleanup); + bfa_reqq_wcancel(&tskim->reqq_wait); + bfa_tskim_cleanup_ios(tskim); + break; + + case BFA_TSKIM_SM_HWFAIL: + bfa_sm_set_state(tskim, bfa_tskim_sm_hcb); + bfa_reqq_wcancel(&tskim->reqq_wait); + bfa_tskim_iocdisable_ios(tskim); + bfa_tskim_qcomp(tskim, __bfa_cb_tskim_failed); + break; + + default: + bfa_assert(0); + } +} + +/** + * Task management command is active, awaiting for room in request CQ + * to send clean up request. + */ +static void +bfa_tskim_sm_cleanup_qfull(struct bfa_tskim_s *tskim, + enum bfa_tskim_event event) +{ + bfa_trc(tskim->bfa, event); + + switch (event) { + case BFA_TSKIM_SM_DONE: + bfa_reqq_wcancel(&tskim->reqq_wait); + /** + * + * Fall through !!! + */ + + case BFA_TSKIM_SM_QRESUME: + bfa_sm_set_state(tskim, bfa_tskim_sm_cleanup); + bfa_tskim_send_abort(tskim); + break; + + case BFA_TSKIM_SM_HWFAIL: + bfa_sm_set_state(tskim, bfa_tskim_sm_hcb); + bfa_reqq_wcancel(&tskim->reqq_wait); + bfa_tskim_iocdisable_ios(tskim); + bfa_tskim_qcomp(tskim, __bfa_cb_tskim_failed); + break; + + default: + bfa_assert(0); + } +} + +/** + * BFA callback is pending + */ +static void +bfa_tskim_sm_hcb(struct bfa_tskim_s *tskim, enum bfa_tskim_event event) +{ + bfa_trc(tskim->bfa, event); + + switch (event) { + case BFA_TSKIM_SM_HCB: + bfa_sm_set_state(tskim, bfa_tskim_sm_uninit); + bfa_tskim_free(tskim); + break; + + case BFA_TSKIM_SM_CLEANUP: + bfa_tskim_notify_comp(tskim); + break; + + case BFA_TSKIM_SM_HWFAIL: + break; + + default: + bfa_assert(0); + } +} + + + +/** + * bfa_tskim_private + */ + +static void +__bfa_cb_tskim_done(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_tskim_s *tskim = cbarg; + + if (!complete) { + bfa_sm_send_event(tskim, BFA_TSKIM_SM_HCB); + return; + } + + bfa_stats(tskim->itnim, tm_success); + bfa_cb_tskim_done(tskim->bfa->bfad, tskim->dtsk, tskim->tsk_status); +} + +static void +__bfa_cb_tskim_failed(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_tskim_s *tskim = cbarg; + + if (!complete) { + bfa_sm_send_event(tskim, BFA_TSKIM_SM_HCB); + return; + } + + bfa_stats(tskim->itnim, tm_failures); + bfa_cb_tskim_done(tskim->bfa->bfad, tskim->dtsk, + BFI_TSKIM_STS_FAILED); +} + +static bfa_boolean_t +bfa_tskim_match_scope(struct bfa_tskim_s *tskim, lun_t lun) +{ + switch (tskim->tm_cmnd) { + case FCP_TM_TARGET_RESET: + return BFA_TRUE; + + case FCP_TM_ABORT_TASK_SET: + case FCP_TM_CLEAR_TASK_SET: + case FCP_TM_LUN_RESET: + case FCP_TM_CLEAR_ACA: + return (tskim->lun == lun); + + default: + bfa_assert(0); + } + + return BFA_FALSE; +} + +/** + * Gather affected IO requests and task management commands. + */ +static void +bfa_tskim_gather_ios(struct bfa_tskim_s *tskim) +{ + struct bfa_itnim_s *itnim = tskim->itnim; + struct bfa_ioim_s *ioim; + struct list_head *qe, *qen; + + INIT_LIST_HEAD(&tskim->io_q); + + /** + * Gather any active IO requests first. + */ + list_for_each_safe(qe, qen, &itnim->io_q) { + ioim = (struct bfa_ioim_s *) qe; + if (bfa_tskim_match_scope + (tskim, bfa_cb_ioim_get_lun(ioim->dio))) { + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &tskim->io_q); + } + } + + /** + * Failback any pending IO requests immediately. + */ + list_for_each_safe(qe, qen, &itnim->pending_q) { + ioim = (struct bfa_ioim_s *) qe; + if (bfa_tskim_match_scope + (tskim, bfa_cb_ioim_get_lun(ioim->dio))) { + list_del(&ioim->qe); + list_add_tail(&ioim->qe, &ioim->fcpim->ioim_comp_q); + bfa_ioim_tov(ioim); + } + } +} + +/** + * IO cleanup completion + */ +static void +bfa_tskim_cleanp_comp(void *tskim_cbarg) +{ + struct bfa_tskim_s *tskim = tskim_cbarg; + + bfa_stats(tskim->itnim, tm_io_comps); + bfa_sm_send_event(tskim, BFA_TSKIM_SM_IOS_DONE); +} + +/** + * Gather affected IO requests and task management commands. + */ +static void +bfa_tskim_cleanup_ios(struct bfa_tskim_s *tskim) +{ + struct bfa_ioim_s *ioim; + struct list_head *qe, *qen; + + bfa_wc_init(&tskim->wc, bfa_tskim_cleanp_comp, tskim); + + list_for_each_safe(qe, qen, &tskim->io_q) { + ioim = (struct bfa_ioim_s *) qe; + bfa_wc_up(&tskim->wc); + bfa_ioim_cleanup_tm(ioim, tskim); + } + + bfa_wc_wait(&tskim->wc); +} + +/** + * Send task management request to firmware. + */ +static bfa_boolean_t +bfa_tskim_send(struct bfa_tskim_s *tskim) +{ + struct bfa_itnim_s *itnim = tskim->itnim; + struct bfi_tskim_req_s *m; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(tskim->bfa, itnim->reqq); + if (!m) + return BFA_FALSE; + + /** + * build i/o request message next + */ + bfi_h2i_set(m->mh, BFI_MC_TSKIM, BFI_TSKIM_H2I_TM_REQ, + bfa_lpuid(tskim->bfa)); + + m->tsk_tag = bfa_os_htons(tskim->tsk_tag); + m->itn_fhdl = tskim->itnim->rport->fw_handle; + m->t_secs = tskim->tsecs; + m->lun = tskim->lun; + m->tm_flags = tskim->tm_cmnd; + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(tskim->bfa, itnim->reqq); + return BFA_TRUE; +} + +/** + * Send abort request to cleanup an active TM to firmware. + */ +static bfa_boolean_t +bfa_tskim_send_abort(struct bfa_tskim_s *tskim) +{ + struct bfa_itnim_s *itnim = tskim->itnim; + struct bfi_tskim_abortreq_s *m; + + /** + * check for room in queue to send request now + */ + m = bfa_reqq_next(tskim->bfa, itnim->reqq); + if (!m) + return BFA_FALSE; + + /** + * build i/o request message next + */ + bfi_h2i_set(m->mh, BFI_MC_TSKIM, BFI_TSKIM_H2I_ABORT_REQ, + bfa_lpuid(tskim->bfa)); + + m->tsk_tag = bfa_os_htons(tskim->tsk_tag); + + /** + * queue I/O message to firmware + */ + bfa_reqq_produce(tskim->bfa, itnim->reqq); + return BFA_TRUE; +} + +/** + * Call to resume task management cmnd waiting for room in request queue. + */ +static void +bfa_tskim_qresume(void *cbarg) +{ + struct bfa_tskim_s *tskim = cbarg; + + bfa_fcpim_stats(tskim->fcpim, qresumes); + bfa_stats(tskim->itnim, tm_qresumes); + bfa_sm_send_event(tskim, BFA_TSKIM_SM_QRESUME); +} + +/** + * Cleanup IOs associated with a task mangement command on IOC failures. + */ +static void +bfa_tskim_iocdisable_ios(struct bfa_tskim_s *tskim) +{ + struct bfa_ioim_s *ioim; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &tskim->io_q) { + ioim = (struct bfa_ioim_s *) qe; + bfa_ioim_iocdisable(ioim); + } +} + + + +/** + * bfa_tskim_friend + */ + +/** + * Notification on completions from related ioim. + */ +void +bfa_tskim_iodone(struct bfa_tskim_s *tskim) +{ + bfa_wc_down(&tskim->wc); +} + +/** + * Handle IOC h/w failure notification from itnim. + */ +void +bfa_tskim_iocdisable(struct bfa_tskim_s *tskim) +{ + tskim->notify = BFA_FALSE; + bfa_stats(tskim->itnim, tm_iocdowns); + bfa_sm_send_event(tskim, BFA_TSKIM_SM_HWFAIL); +} + +/** + * Cleanup TM command and associated IOs as part of ITNIM offline. + */ +void +bfa_tskim_cleanup(struct bfa_tskim_s *tskim) +{ + tskim->notify = BFA_TRUE; + bfa_stats(tskim->itnim, tm_cleanups); + bfa_sm_send_event(tskim, BFA_TSKIM_SM_CLEANUP); +} + +/** + * Memory allocation and initialization. + */ +void +bfa_tskim_attach(struct bfa_fcpim_mod_s *fcpim, struct bfa_meminfo_s *minfo) +{ + struct bfa_tskim_s *tskim; + u16 i; + + INIT_LIST_HEAD(&fcpim->tskim_free_q); + + tskim = (struct bfa_tskim_s *) bfa_meminfo_kva(minfo); + fcpim->tskim_arr = tskim; + + for (i = 0; i < fcpim->num_tskim_reqs; i++, tskim++) { + /* + * initialize TSKIM + */ + bfa_os_memset(tskim, 0, sizeof(struct bfa_tskim_s)); + tskim->tsk_tag = i; + tskim->bfa = fcpim->bfa; + tskim->fcpim = fcpim; + tskim->notify = BFA_FALSE; + bfa_reqq_winit(&tskim->reqq_wait, bfa_tskim_qresume, + tskim); + bfa_sm_set_state(tskim, bfa_tskim_sm_uninit); + + list_add_tail(&tskim->qe, &fcpim->tskim_free_q); + } + + bfa_meminfo_kva(minfo) = (u8 *) tskim; +} + +void +bfa_tskim_detach(struct bfa_fcpim_mod_s *fcpim) +{ + /** + * @todo + */ +} + +void +bfa_tskim_isr(struct bfa_s *bfa, struct bfi_msg_s *m) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + struct bfi_tskim_rsp_s *rsp = (struct bfi_tskim_rsp_s *) m; + struct bfa_tskim_s *tskim; + u16 tsk_tag = bfa_os_ntohs(rsp->tsk_tag); + + tskim = BFA_TSKIM_FROM_TAG(fcpim, tsk_tag); + bfa_assert(tskim->tsk_tag == tsk_tag); + + tskim->tsk_status = rsp->tsk_status; + + /** + * Firmware sends BFI_TSKIM_STS_ABORTED status for abort + * requests. All other statuses are for normal completions. + */ + if (rsp->tsk_status == BFI_TSKIM_STS_ABORTED) { + bfa_stats(tskim->itnim, tm_cleanup_comps); + bfa_sm_send_event(tskim, BFA_TSKIM_SM_CLEANUP_DONE); + } else { + bfa_stats(tskim->itnim, tm_fw_rsps); + bfa_sm_send_event(tskim, BFA_TSKIM_SM_DONE); + } +} + + + +/** + * bfa_tskim_api + */ + + +struct bfa_tskim_s * +bfa_tskim_alloc(struct bfa_s *bfa, struct bfad_tskim_s *dtsk) +{ + struct bfa_fcpim_mod_s *fcpim = BFA_FCPIM_MOD(bfa); + struct bfa_tskim_s *tskim; + + bfa_q_deq(&fcpim->tskim_free_q, &tskim); + + if (!tskim) + bfa_fcpim_stats(fcpim, no_tskims); + else + tskim->dtsk = dtsk; + + return tskim; +} + +void +bfa_tskim_free(struct bfa_tskim_s *tskim) +{ + bfa_assert(bfa_q_is_on_q_func(&tskim->itnim->tsk_q, &tskim->qe)); + list_del(&tskim->qe); + list_add_tail(&tskim->qe, &tskim->fcpim->tskim_free_q); +} + +/** + * Start a task management command. + * + * @param[in] tskim BFA task management command instance + * @param[in] itnim i-t nexus for the task management command + * @param[in] lun lun, if applicable + * @param[in] tm_cmnd Task management command code. + * @param[in] t_secs Timeout in seconds + * + * @return None. + */ +void +bfa_tskim_start(struct bfa_tskim_s *tskim, struct bfa_itnim_s *itnim, lun_t lun, + enum fcp_tm_cmnd tm_cmnd, u8 tsecs) +{ + tskim->itnim = itnim; + tskim->lun = lun; + tskim->tm_cmnd = tm_cmnd; + tskim->tsecs = tsecs; + tskim->notify = BFA_FALSE; + bfa_stats(itnim, tm_cmnds); + + list_add_tail(&tskim->qe, &itnim->tsk_q); + bfa_sm_send_event(tskim, BFA_TSKIM_SM_START); +} + + diff --git a/drivers/scsi/bfa/bfa_uf.c b/drivers/scsi/bfa/bfa_uf.c new file mode 100644 index 000000000000..ff5f9deb1b22 --- /dev/null +++ b/drivers/scsi/bfa/bfa_uf.c @@ -0,0 +1,345 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_uf.c BFA unsolicited frame receive implementation + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include <bfi/bfi_uf.h> +#include <cs/bfa_debug.h> + +BFA_TRC_FILE(HAL, UF); +BFA_MODULE(uf); + +/* + ***************************************************************************** + * Internal functions + ***************************************************************************** + */ +static void +__bfa_cb_uf_recv(void *cbarg, bfa_boolean_t complete) +{ + struct bfa_uf_s *uf = cbarg; + struct bfa_uf_mod_s *ufm = BFA_UF_MOD(uf->bfa); + + if (complete) + ufm->ufrecv(ufm->cbarg, uf); +} + +static void +claim_uf_pbs(struct bfa_uf_mod_s *ufm, struct bfa_meminfo_s *mi) +{ + u32 uf_pb_tot_sz; + + ufm->uf_pbs_kva = (struct bfa_uf_buf_s *) bfa_meminfo_dma_virt(mi); + ufm->uf_pbs_pa = bfa_meminfo_dma_phys(mi); + uf_pb_tot_sz = BFA_ROUNDUP((sizeof(struct bfa_uf_buf_s) * ufm->num_ufs), + BFA_DMA_ALIGN_SZ); + + bfa_meminfo_dma_virt(mi) += uf_pb_tot_sz; + bfa_meminfo_dma_phys(mi) += uf_pb_tot_sz; + + bfa_os_memset((void *)ufm->uf_pbs_kva, 0, uf_pb_tot_sz); +} + +static void +claim_uf_post_msgs(struct bfa_uf_mod_s *ufm, struct bfa_meminfo_s *mi) +{ + struct bfi_uf_buf_post_s *uf_bp_msg; + struct bfi_sge_s *sge; + union bfi_addr_u sga_zero = { {0} }; + u16 i; + u16 buf_len; + + ufm->uf_buf_posts = (struct bfi_uf_buf_post_s *) bfa_meminfo_kva(mi); + uf_bp_msg = ufm->uf_buf_posts; + + for (i = 0, uf_bp_msg = ufm->uf_buf_posts; i < ufm->num_ufs; + i++, uf_bp_msg++) { + bfa_os_memset(uf_bp_msg, 0, sizeof(struct bfi_uf_buf_post_s)); + + uf_bp_msg->buf_tag = i; + buf_len = sizeof(struct bfa_uf_buf_s); + uf_bp_msg->buf_len = bfa_os_htons(buf_len); + bfi_h2i_set(uf_bp_msg->mh, BFI_MC_UF, BFI_UF_H2I_BUF_POST, + bfa_lpuid(ufm->bfa)); + + sge = uf_bp_msg->sge; + sge[0].sg_len = buf_len; + sge[0].flags = BFI_SGE_DATA_LAST; + bfa_dma_addr_set(sge[0].sga, ufm_pbs_pa(ufm, i)); + bfa_sge_to_be(sge); + + sge[1].sg_len = buf_len; + sge[1].flags = BFI_SGE_PGDLEN; + sge[1].sga = sga_zero; + bfa_sge_to_be(&sge[1]); + } + + /** + * advance pointer beyond consumed memory + */ + bfa_meminfo_kva(mi) = (u8 *) uf_bp_msg; +} + +static void +claim_ufs(struct bfa_uf_mod_s *ufm, struct bfa_meminfo_s *mi) +{ + u16 i; + struct bfa_uf_s *uf; + + /* + * Claim block of memory for UF list + */ + ufm->uf_list = (struct bfa_uf_s *) bfa_meminfo_kva(mi); + + /* + * Initialize UFs and queue it in UF free queue + */ + for (i = 0, uf = ufm->uf_list; i < ufm->num_ufs; i++, uf++) { + bfa_os_memset(uf, 0, sizeof(struct bfa_uf_s)); + uf->bfa = ufm->bfa; + uf->uf_tag = i; + uf->pb_len = sizeof(struct bfa_uf_buf_s); + uf->buf_kva = (void *)&ufm->uf_pbs_kva[i]; + uf->buf_pa = ufm_pbs_pa(ufm, i); + list_add_tail(&uf->qe, &ufm->uf_free_q); + } + + /** + * advance memory pointer + */ + bfa_meminfo_kva(mi) = (u8 *) uf; +} + +static void +uf_mem_claim(struct bfa_uf_mod_s *ufm, struct bfa_meminfo_s *mi) +{ + claim_uf_pbs(ufm, mi); + claim_ufs(ufm, mi); + claim_uf_post_msgs(ufm, mi); +} + +static void +bfa_uf_meminfo(struct bfa_iocfc_cfg_s *cfg, u32 *ndm_len, u32 *dm_len) +{ + u32 num_ufs = cfg->fwcfg.num_uf_bufs; + + /* + * dma-able memory for UF posted bufs + */ + *dm_len += BFA_ROUNDUP((sizeof(struct bfa_uf_buf_s) * num_ufs), + BFA_DMA_ALIGN_SZ); + + /* + * kernel Virtual memory for UFs and UF buf post msg copies + */ + *ndm_len += sizeof(struct bfa_uf_s) * num_ufs; + *ndm_len += sizeof(struct bfi_uf_buf_post_s) * num_ufs; +} + +static void +bfa_uf_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, struct bfa_pcidev_s *pcidev) +{ + struct bfa_uf_mod_s *ufm = BFA_UF_MOD(bfa); + + bfa_os_memset(ufm, 0, sizeof(struct bfa_uf_mod_s)); + ufm->bfa = bfa; + ufm->num_ufs = cfg->fwcfg.num_uf_bufs; + INIT_LIST_HEAD(&ufm->uf_free_q); + INIT_LIST_HEAD(&ufm->uf_posted_q); + + uf_mem_claim(ufm, meminfo); +} + +static void +bfa_uf_initdone(struct bfa_s *bfa) +{ +} + +static void +bfa_uf_detach(struct bfa_s *bfa) +{ +} + +static struct bfa_uf_s * +bfa_uf_get(struct bfa_uf_mod_s *uf_mod) +{ + struct bfa_uf_s *uf; + + bfa_q_deq(&uf_mod->uf_free_q, &uf); + return (uf); +} + +static void +bfa_uf_put(struct bfa_uf_mod_s *uf_mod, struct bfa_uf_s *uf) +{ + list_add_tail(&uf->qe, &uf_mod->uf_free_q); +} + +static bfa_status_t +bfa_uf_post(struct bfa_uf_mod_s *ufm, struct bfa_uf_s *uf) +{ + struct bfi_uf_buf_post_s *uf_post_msg; + + uf_post_msg = bfa_reqq_next(ufm->bfa, BFA_REQQ_FCXP); + if (!uf_post_msg) + return BFA_STATUS_FAILED; + + bfa_os_memcpy(uf_post_msg, &ufm->uf_buf_posts[uf->uf_tag], + sizeof(struct bfi_uf_buf_post_s)); + bfa_reqq_produce(ufm->bfa, BFA_REQQ_FCXP); + + bfa_trc(ufm->bfa, uf->uf_tag); + + list_add_tail(&uf->qe, &ufm->uf_posted_q); + return BFA_STATUS_OK; +} + +static void +bfa_uf_post_all(struct bfa_uf_mod_s *uf_mod) +{ + struct bfa_uf_s *uf; + + while ((uf = bfa_uf_get(uf_mod)) != NULL) { + if (bfa_uf_post(uf_mod, uf) != BFA_STATUS_OK) + break; + } +} + +static void +uf_recv(struct bfa_s *bfa, struct bfi_uf_frm_rcvd_s *m) +{ + struct bfa_uf_mod_s *ufm = BFA_UF_MOD(bfa); + u16 uf_tag = m->buf_tag; + struct bfa_uf_buf_s *uf_buf = &ufm->uf_pbs_kva[uf_tag]; + struct bfa_uf_s *uf = &ufm->uf_list[uf_tag]; + u8 *buf = &uf_buf->d[0]; + struct fchs_s *fchs; + + m->frm_len = bfa_os_ntohs(m->frm_len); + m->xfr_len = bfa_os_ntohs(m->xfr_len); + + fchs = (struct fchs_s *) uf_buf; + + list_del(&uf->qe); /* dequeue from posted queue */ + + uf->data_ptr = buf; + uf->data_len = m->xfr_len; + + bfa_assert(uf->data_len >= sizeof(struct fchs_s)); + + if (uf->data_len == sizeof(struct fchs_s)) { + bfa_plog_fchdr(bfa->plog, BFA_PL_MID_HAL_UF, BFA_PL_EID_RX, + uf->data_len, (struct fchs_s *) buf); + } else { + u32 pld_w0 = *((u32 *) (buf + sizeof(struct fchs_s))); + bfa_plog_fchdr_and_pl(bfa->plog, BFA_PL_MID_HAL_UF, + BFA_PL_EID_RX, uf->data_len, + (struct fchs_s *) buf, pld_w0); + } + + bfa_cb_queue(bfa, &uf->hcb_qe, __bfa_cb_uf_recv, uf); +} + +static void +bfa_uf_stop(struct bfa_s *bfa) +{ +} + +static void +bfa_uf_iocdisable(struct bfa_s *bfa) +{ + struct bfa_uf_mod_s *ufm = BFA_UF_MOD(bfa); + struct bfa_uf_s *uf; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &ufm->uf_posted_q) { + uf = (struct bfa_uf_s *) qe; + list_del(&uf->qe); + bfa_uf_put(ufm, uf); + } +} + +static void +bfa_uf_start(struct bfa_s *bfa) +{ + bfa_uf_post_all(BFA_UF_MOD(bfa)); +} + + + +/** + * bfa_uf_api + */ + +/** + * Register handler for all unsolicted recieve frames. + * + * @param[in] bfa BFA instance + * @param[in] ufrecv receive handler function + * @param[in] cbarg receive handler arg + */ +void +bfa_uf_recv_register(struct bfa_s *bfa, bfa_cb_uf_recv_t ufrecv, void *cbarg) +{ + struct bfa_uf_mod_s *ufm = BFA_UF_MOD(bfa); + + ufm->ufrecv = ufrecv; + ufm->cbarg = cbarg; +} + +/** + * Free an unsolicited frame back to BFA. + * + * @param[in] uf unsolicited frame to be freed + * + * @return None + */ +void +bfa_uf_free(struct bfa_uf_s *uf) +{ + bfa_uf_put(BFA_UF_MOD(uf->bfa), uf); + bfa_uf_post_all(BFA_UF_MOD(uf->bfa)); +} + + + +/** + * uf_pub BFA uf module public functions + */ + +void +bfa_uf_isr(struct bfa_s *bfa, struct bfi_msg_s *msg) +{ + bfa_trc(bfa, msg->mhdr.msg_id); + + switch (msg->mhdr.msg_id) { + case BFI_UF_I2H_FRM_RCVD: + uf_recv(bfa, (struct bfi_uf_frm_rcvd_s *) msg); + break; + + default: + bfa_trc(bfa, msg->mhdr.msg_id); + bfa_assert(0); + } +} + + diff --git a/drivers/scsi/bfa/bfa_uf_priv.h b/drivers/scsi/bfa/bfa_uf_priv.h new file mode 100644 index 000000000000..bcb490f834f3 --- /dev/null +++ b/drivers/scsi/bfa/bfa_uf_priv.h @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_UF_PRIV_H__ +#define __BFA_UF_PRIV_H__ + +#include <cs/bfa_sm.h> +#include <bfa_svc.h> +#include <bfi/bfi_uf.h> + +#define BFA_UF_MIN (4) + +struct bfa_uf_mod_s { + struct bfa_s *bfa; /* back pointer to BFA */ + struct bfa_uf_s *uf_list; /* array of UFs */ + u16 num_ufs; /* num unsolicited rx frames */ + struct list_head uf_free_q; /* free UFs */ + struct list_head uf_posted_q; /* UFs posted to IOC */ + struct bfa_uf_buf_s *uf_pbs_kva; /* list UF bufs request pld */ + u64 uf_pbs_pa; /* phy addr for UF bufs */ + struct bfi_uf_buf_post_s *uf_buf_posts; + /* pre-built UF post msgs */ + bfa_cb_uf_recv_t ufrecv; /* uf recv handler function */ + void *cbarg; /* uf receive handler arg */ +}; + +#define BFA_UF_MOD(__bfa) (&(__bfa)->modules.uf_mod) + +#define ufm_pbs_pa(_ufmod, _uftag) \ + ((_ufmod)->uf_pbs_pa + sizeof(struct bfa_uf_buf_s) * (_uftag)) + +void bfa_uf_isr(struct bfa_s *bfa, struct bfi_msg_s *msg); + +#endif /* __BFA_UF_PRIV_H__ */ diff --git a/drivers/scsi/bfa/bfad.c b/drivers/scsi/bfa/bfad.c new file mode 100644 index 000000000000..6f2be5abf561 --- /dev/null +++ b/drivers/scsi/bfa/bfad.c @@ -0,0 +1,1182 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfad.c Linux driver PCI interface module. + */ + +#include <linux/module.h> +#include "bfad_drv.h" +#include "bfad_im.h" +#include "bfad_tm.h" +#include "bfad_ipfc.h" +#include "bfad_trcmod.h" +#include <fcb/bfa_fcb_vf.h> +#include <fcb/bfa_fcb_rport.h> +#include <fcb/bfa_fcb_port.h> +#include <fcb/bfa_fcb.h> + +BFA_TRC_FILE(LDRV, BFAD); +static DEFINE_MUTEX(bfad_mutex); +LIST_HEAD(bfad_list); +static int bfad_inst; +int bfad_supported_fc4s; + +static char *host_name; +static char *os_name; +static char *os_patch; +static int num_rports; +static int num_ios; +static int num_tms; +static int num_fcxps; +static int num_ufbufs; +static int reqq_size; +static int rspq_size; +static int num_sgpgs; +static int rport_del_timeout = BFA_FCS_RPORT_DEF_DEL_TIMEOUT; +static int bfa_io_max_sge = BFAD_IO_MAX_SGE; +static int log_level = BFA_LOG_WARNING; +static int ioc_auto_recover = BFA_TRUE; +static int ipfc_enable = BFA_FALSE; +static int ipfc_mtu = -1; +int bfa_lun_queue_depth = BFAD_LUN_QUEUE_DEPTH; +int bfa_linkup_delay = -1; + +module_param(os_name, charp, S_IRUGO | S_IWUSR); +module_param(os_patch, charp, S_IRUGO | S_IWUSR); +module_param(host_name, charp, S_IRUGO | S_IWUSR); +module_param(num_rports, int, S_IRUGO | S_IWUSR); +module_param(num_ios, int, S_IRUGO | S_IWUSR); +module_param(num_tms, int, S_IRUGO | S_IWUSR); +module_param(num_fcxps, int, S_IRUGO | S_IWUSR); +module_param(num_ufbufs, int, S_IRUGO | S_IWUSR); +module_param(reqq_size, int, S_IRUGO | S_IWUSR); +module_param(rspq_size, int, S_IRUGO | S_IWUSR); +module_param(num_sgpgs, int, S_IRUGO | S_IWUSR); +module_param(rport_del_timeout, int, S_IRUGO | S_IWUSR); +module_param(bfa_lun_queue_depth, int, S_IRUGO | S_IWUSR); +module_param(bfa_io_max_sge, int, S_IRUGO | S_IWUSR); +module_param(log_level, int, S_IRUGO | S_IWUSR); +module_param(ioc_auto_recover, int, S_IRUGO | S_IWUSR); +module_param(ipfc_enable, int, S_IRUGO | S_IWUSR); +module_param(ipfc_mtu, int, S_IRUGO | S_IWUSR); +module_param(bfa_linkup_delay, int, S_IRUGO | S_IWUSR); + +/* + * Stores the module parm num_sgpgs value; + * used to reset for bfad next instance. + */ +static int num_sgpgs_parm; + +static bfa_status_t +bfad_fc4_probe(struct bfad_s *bfad) +{ + int rc; + + rc = bfad_im_probe(bfad); + if (rc != BFA_STATUS_OK) + goto ext; + + bfad_tm_probe(bfad); + + if (ipfc_enable) + bfad_ipfc_probe(bfad); +ext: + return rc; +} + +static void +bfad_fc4_probe_undo(struct bfad_s *bfad) +{ + bfad_im_probe_undo(bfad); + bfad_tm_probe_undo(bfad); + if (ipfc_enable) + bfad_ipfc_probe_undo(bfad); +} + +static void +bfad_fc4_probe_post(struct bfad_s *bfad) +{ + if (bfad->im) + bfad_im_probe_post(bfad->im); + + bfad_tm_probe_post(bfad); + if (ipfc_enable) + bfad_ipfc_probe_post(bfad); +} + +static bfa_status_t +bfad_fc4_port_new(struct bfad_s *bfad, struct bfad_port_s *port, int roles) +{ + int rc = BFA_STATUS_FAILED; + + if (roles & BFA_PORT_ROLE_FCP_IM) + rc = bfad_im_port_new(bfad, port); + if (rc != BFA_STATUS_OK) + goto ext; + + if (roles & BFA_PORT_ROLE_FCP_TM) + rc = bfad_tm_port_new(bfad, port); + if (rc != BFA_STATUS_OK) + goto ext; + + if ((roles & BFA_PORT_ROLE_FCP_IPFC) && ipfc_enable) + rc = bfad_ipfc_port_new(bfad, port, port->pvb_type); +ext: + return rc; +} + +static void +bfad_fc4_port_delete(struct bfad_s *bfad, struct bfad_port_s *port, int roles) +{ + if (roles & BFA_PORT_ROLE_FCP_IM) + bfad_im_port_delete(bfad, port); + + if (roles & BFA_PORT_ROLE_FCP_TM) + bfad_tm_port_delete(bfad, port); + + if ((roles & BFA_PORT_ROLE_FCP_IPFC) && ipfc_enable) + bfad_ipfc_port_delete(bfad, port); +} + +/** + * BFA callbacks + */ +void +bfad_hcb_comp(void *arg, bfa_status_t status) +{ + struct bfad_hal_comp *fcomp = (struct bfad_hal_comp *)arg; + + fcomp->status = status; + complete(&fcomp->comp); +} + +/** + * bfa_init callback + */ +void +bfa_cb_init(void *drv, bfa_status_t init_status) +{ + struct bfad_s *bfad = drv; + + if (init_status == BFA_STATUS_OK) + bfad->bfad_flags |= BFAD_HAL_INIT_DONE; + + complete(&bfad->comp); +} + + + +/** + * BFA_FCS callbacks + */ +static struct bfad_port_s * +bfad_get_drv_port(struct bfad_s *bfad, struct bfad_vf_s *vf_drv, + struct bfad_vport_s *vp_drv) +{ + return ((vp_drv) ? (&(vp_drv)->drv_port) + : ((vf_drv) ? (&(vf_drv)->base_port) : (&(bfad)->pport))); +} + +struct bfad_port_s * +bfa_fcb_port_new(struct bfad_s *bfad, struct bfa_fcs_port_s *port, + enum bfa_port_role roles, struct bfad_vf_s *vf_drv, + struct bfad_vport_s *vp_drv) +{ + bfa_status_t rc; + struct bfad_port_s *port_drv; + + if (!vp_drv && !vf_drv) { + port_drv = &bfad->pport; + port_drv->pvb_type = BFAD_PORT_PHYS_BASE; + } else if (!vp_drv && vf_drv) { + port_drv = &vf_drv->base_port; + port_drv->pvb_type = BFAD_PORT_VF_BASE; + } else if (vp_drv && !vf_drv) { + port_drv = &vp_drv->drv_port; + port_drv->pvb_type = BFAD_PORT_PHYS_VPORT; + } else { + port_drv = &vp_drv->drv_port; + port_drv->pvb_type = BFAD_PORT_VF_VPORT; + } + + port_drv->fcs_port = port; + port_drv->roles = roles; + rc = bfad_fc4_port_new(bfad, port_drv, roles); + if (rc != BFA_STATUS_OK) { + bfad_fc4_port_delete(bfad, port_drv, roles); + port_drv = NULL; + } + + return port_drv; +} + +void +bfa_fcb_port_delete(struct bfad_s *bfad, enum bfa_port_role roles, + struct bfad_vf_s *vf_drv, struct bfad_vport_s *vp_drv) +{ + struct bfad_port_s *port_drv; + + /* + * this will be only called from rmmod context + */ + if (vp_drv && !vp_drv->comp_del) { + port_drv = bfad_get_drv_port(bfad, vf_drv, vp_drv); + bfa_trc(bfad, roles); + bfad_fc4_port_delete(bfad, port_drv, roles); + } +} + +void +bfa_fcb_port_online(struct bfad_s *bfad, enum bfa_port_role roles, + struct bfad_vf_s *vf_drv, struct bfad_vport_s *vp_drv) +{ + struct bfad_port_s *port_drv = bfad_get_drv_port(bfad, vf_drv, vp_drv); + + if (roles & BFA_PORT_ROLE_FCP_IM) + bfad_im_port_online(bfad, port_drv); + + if (roles & BFA_PORT_ROLE_FCP_TM) + bfad_tm_port_online(bfad, port_drv); + + if ((roles & BFA_PORT_ROLE_FCP_IPFC) && ipfc_enable) + bfad_ipfc_port_online(bfad, port_drv); + + bfad->bfad_flags |= BFAD_PORT_ONLINE; +} + +void +bfa_fcb_port_offline(struct bfad_s *bfad, enum bfa_port_role roles, + struct bfad_vf_s *vf_drv, struct bfad_vport_s *vp_drv) +{ + struct bfad_port_s *port_drv = bfad_get_drv_port(bfad, vf_drv, vp_drv); + + if (roles & BFA_PORT_ROLE_FCP_IM) + bfad_im_port_offline(bfad, port_drv); + + if (roles & BFA_PORT_ROLE_FCP_TM) + bfad_tm_port_offline(bfad, port_drv); + + if ((roles & BFA_PORT_ROLE_FCP_IPFC) && ipfc_enable) + bfad_ipfc_port_offline(bfad, port_drv); +} + +void +bfa_fcb_vport_delete(struct bfad_vport_s *vport_drv) +{ + if (vport_drv->comp_del) { + complete(vport_drv->comp_del); + return; + } + + kfree(vport_drv); +} + +/** + * FCS RPORT alloc callback, after successful PLOGI by FCS + */ +bfa_status_t +bfa_fcb_rport_alloc(struct bfad_s *bfad, struct bfa_fcs_rport_s **rport, + struct bfad_rport_s **rport_drv) +{ + bfa_status_t rc = BFA_STATUS_OK; + + *rport_drv = kzalloc(sizeof(struct bfad_rport_s), GFP_ATOMIC); + if (*rport_drv == NULL) { + rc = BFA_STATUS_ENOMEM; + goto ext; + } + + *rport = &(*rport_drv)->fcs_rport; + +ext: + return rc; +} + + + +void +bfad_hal_mem_release(struct bfad_s *bfad) +{ + int i; + struct bfa_meminfo_s *hal_meminfo = &bfad->meminfo; + struct bfa_mem_elem_s *meminfo_elem; + + for (i = 0; i < BFA_MEM_TYPE_MAX; i++) { + meminfo_elem = &hal_meminfo->meminfo[i]; + if (meminfo_elem->kva != NULL) { + switch (meminfo_elem->mem_type) { + case BFA_MEM_TYPE_KVA: + vfree(meminfo_elem->kva); + break; + case BFA_MEM_TYPE_DMA: + dma_free_coherent(&bfad->pcidev->dev, + meminfo_elem->mem_len, + meminfo_elem->kva, + (dma_addr_t) meminfo_elem->dma); + break; + default: + bfa_assert(0); + break; + } + } + } + + memset(hal_meminfo, 0, sizeof(struct bfa_meminfo_s)); +} + +void +bfad_update_hal_cfg(struct bfa_iocfc_cfg_s *bfa_cfg) +{ + if (num_rports > 0) + bfa_cfg->fwcfg.num_rports = num_rports; + if (num_ios > 0) + bfa_cfg->fwcfg.num_ioim_reqs = num_ios; + if (num_tms > 0) + bfa_cfg->fwcfg.num_tskim_reqs = num_tms; + if (num_fcxps > 0) + bfa_cfg->fwcfg.num_fcxp_reqs = num_fcxps; + if (num_ufbufs > 0) + bfa_cfg->fwcfg.num_uf_bufs = num_ufbufs; + if (reqq_size > 0) + bfa_cfg->drvcfg.num_reqq_elems = reqq_size; + if (rspq_size > 0) + bfa_cfg->drvcfg.num_rspq_elems = rspq_size; + if (num_sgpgs > 0) + bfa_cfg->drvcfg.num_sgpgs = num_sgpgs; + + /* + * populate the hal values back to the driver for sysfs use. + * otherwise, the default values will be shown as 0 in sysfs + */ + num_rports = bfa_cfg->fwcfg.num_rports; + num_ios = bfa_cfg->fwcfg.num_ioim_reqs; + num_tms = bfa_cfg->fwcfg.num_tskim_reqs; + num_fcxps = bfa_cfg->fwcfg.num_fcxp_reqs; + num_ufbufs = bfa_cfg->fwcfg.num_uf_bufs; + reqq_size = bfa_cfg->drvcfg.num_reqq_elems; + rspq_size = bfa_cfg->drvcfg.num_rspq_elems; + num_sgpgs = bfa_cfg->drvcfg.num_sgpgs; +} + +bfa_status_t +bfad_hal_mem_alloc(struct bfad_s *bfad) +{ + struct bfa_meminfo_s *hal_meminfo = &bfad->meminfo; + struct bfa_mem_elem_s *meminfo_elem; + bfa_status_t rc = BFA_STATUS_OK; + dma_addr_t phys_addr; + int retry_count = 0; + int reset_value = 1; + int min_num_sgpgs = 512; + void *kva; + int i; + + bfa_cfg_get_default(&bfad->ioc_cfg); + +retry: + bfad_update_hal_cfg(&bfad->ioc_cfg); + bfad->cfg_data.ioc_queue_depth = bfad->ioc_cfg.fwcfg.num_ioim_reqs; + bfa_cfg_get_meminfo(&bfad->ioc_cfg, hal_meminfo); + + for (i = 0; i < BFA_MEM_TYPE_MAX; i++) { + meminfo_elem = &hal_meminfo->meminfo[i]; + switch (meminfo_elem->mem_type) { + case BFA_MEM_TYPE_KVA: + kva = vmalloc(meminfo_elem->mem_len); + if (kva == NULL) { + bfad_hal_mem_release(bfad); + rc = BFA_STATUS_ENOMEM; + goto ext; + } + memset(kva, 0, meminfo_elem->mem_len); + meminfo_elem->kva = kva; + break; + case BFA_MEM_TYPE_DMA: + kva = dma_alloc_coherent(&bfad->pcidev->dev, + meminfo_elem->mem_len, + &phys_addr, GFP_KERNEL); + if (kva == NULL) { + bfad_hal_mem_release(bfad); + /* + * If we cannot allocate with default + * num_sgpages try with half the value. + */ + if (num_sgpgs > min_num_sgpgs) { + printk(KERN_INFO "bfad[%d]: memory" + " allocation failed with" + " num_sgpgs: %d\n", + bfad->inst_no, num_sgpgs); + nextLowerInt(&num_sgpgs); + printk(KERN_INFO "bfad[%d]: trying to" + " allocate memory with" + " num_sgpgs: %d\n", + bfad->inst_no, num_sgpgs); + retry_count++; + goto retry; + } else { + if (num_sgpgs_parm > 0) + num_sgpgs = num_sgpgs_parm; + else { + reset_value = + (1 << retry_count); + num_sgpgs *= reset_value; + } + rc = BFA_STATUS_ENOMEM; + goto ext; + } + } + + if (num_sgpgs_parm > 0) + num_sgpgs = num_sgpgs_parm; + else { + reset_value = (1 << retry_count); + num_sgpgs *= reset_value; + } + + memset(kva, 0, meminfo_elem->mem_len); + meminfo_elem->kva = kva; + meminfo_elem->dma = phys_addr; + break; + default: + break; + + } + } +ext: + return rc; +} + +/** + * Create a vport under a vf. + */ +bfa_status_t +bfad_vport_create(struct bfad_s *bfad, u16 vf_id, + struct bfa_port_cfg_s *port_cfg) +{ + struct bfad_vport_s *vport; + int rc = BFA_STATUS_OK; + unsigned long flags; + struct completion fcomp; + + vport = kzalloc(sizeof(struct bfad_vport_s), GFP_KERNEL); + if (!vport) { + rc = BFA_STATUS_ENOMEM; + goto ext; + } + + vport->drv_port.bfad = bfad; + spin_lock_irqsave(&bfad->bfad_lock, flags); + rc = bfa_fcs_vport_create(&vport->fcs_vport, &bfad->bfa_fcs, vf_id, + port_cfg, vport); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + if (rc != BFA_STATUS_OK) + goto ext_free_vport; + + if (port_cfg->roles & BFA_PORT_ROLE_FCP_IM) { + rc = bfad_im_scsi_host_alloc(bfad, vport->drv_port.im_port); + if (rc != BFA_STATUS_OK) + goto ext_free_fcs_vport; + } + + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_fcs_vport_start(&vport->fcs_vport); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + return BFA_STATUS_OK; + +ext_free_fcs_vport: + spin_lock_irqsave(&bfad->bfad_lock, flags); + vport->comp_del = &fcomp; + init_completion(vport->comp_del); + bfa_fcs_vport_delete(&vport->fcs_vport); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + wait_for_completion(vport->comp_del); +ext_free_vport: + kfree(vport); +ext: + return rc; +} + +/** + * Create a vf and its base vport implicitely. + */ +bfa_status_t +bfad_vf_create(struct bfad_s *bfad, u16 vf_id, + struct bfa_port_cfg_s *port_cfg) +{ + struct bfad_vf_s *vf; + int rc = BFA_STATUS_OK; + + vf = kzalloc(sizeof(struct bfad_vf_s), GFP_KERNEL); + if (!vf) { + rc = BFA_STATUS_FAILED; + goto ext; + } + + rc = bfa_fcs_vf_create(&vf->fcs_vf, &bfad->bfa_fcs, vf_id, port_cfg, + vf); + if (rc != BFA_STATUS_OK) + kfree(vf); +ext: + return rc; +} + +void +bfad_bfa_tmo(unsigned long data) +{ + struct bfad_s *bfad = (struct bfad_s *)data; + unsigned long flags; + struct list_head doneq; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + + bfa_timer_tick(&bfad->bfa); + + bfa_comp_deq(&bfad->bfa, &doneq); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + if (!list_empty(&doneq)) { + bfa_comp_process(&bfad->bfa, &doneq); + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_comp_free(&bfad->bfa, &doneq); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + } + + mod_timer(&bfad->hal_tmo, jiffies + msecs_to_jiffies(BFA_TIMER_FREQ)); +} + +void +bfad_init_timer(struct bfad_s *bfad) +{ + init_timer(&bfad->hal_tmo); + bfad->hal_tmo.function = bfad_bfa_tmo; + bfad->hal_tmo.data = (unsigned long)bfad; + + mod_timer(&bfad->hal_tmo, jiffies + msecs_to_jiffies(BFA_TIMER_FREQ)); +} + +int +bfad_pci_init(struct pci_dev *pdev, struct bfad_s *bfad) +{ + unsigned long bar0_len; + int rc = -ENODEV; + + if (pci_enable_device(pdev)) { + BFA_PRINTF(BFA_ERR, "pci_enable_device fail %p\n", pdev); + goto out; + } + + if (pci_request_regions(pdev, BFAD_DRIVER_NAME)) + goto out_disable_device; + + pci_set_master(pdev); + + + if (pci_set_dma_mask(pdev, DMA_BIT_MASK(64)) != 0) + if (pci_set_dma_mask(pdev, DMA_BIT_MASK(32)) != 0) { + BFA_PRINTF(BFA_ERR, "pci_set_dma_mask fail %p\n", pdev); + goto out_release_region; + } + + bfad->pci_bar0_map = pci_resource_start(pdev, 0); + bar0_len = pci_resource_len(pdev, 0); + bfad->pci_bar0_kva = ioremap(bfad->pci_bar0_map, bar0_len); + + if (bfad->pci_bar0_kva == NULL) { + BFA_PRINTF(BFA_ERR, "Fail to map bar0\n"); + goto out_release_region; + } + + bfad->hal_pcidev.pci_slot = PCI_SLOT(pdev->devfn); + bfad->hal_pcidev.pci_func = PCI_FUNC(pdev->devfn); + bfad->hal_pcidev.pci_bar_kva = bfad->pci_bar0_kva; + bfad->hal_pcidev.device_id = pdev->device; + bfad->pci_name = pci_name(pdev); + + bfad->pci_attr.vendor_id = pdev->vendor; + bfad->pci_attr.device_id = pdev->device; + bfad->pci_attr.ssid = pdev->subsystem_device; + bfad->pci_attr.ssvid = pdev->subsystem_vendor; + bfad->pci_attr.pcifn = PCI_FUNC(pdev->devfn); + + bfad->pcidev = pdev; + return 0; + +out_release_region: + pci_release_regions(pdev); +out_disable_device: + pci_disable_device(pdev); +out: + return rc; +} + +void +bfad_pci_uninit(struct pci_dev *pdev, struct bfad_s *bfad) +{ +#if defined(__ia64__) + pci_iounmap(pdev, bfad->pci_bar0_kva); +#else + iounmap(bfad->pci_bar0_kva); +#endif + pci_release_regions(pdev); + pci_disable_device(pdev); + pci_set_drvdata(pdev, NULL); +} + +void +bfad_fcs_port_cfg(struct bfad_s *bfad) +{ + struct bfa_port_cfg_s port_cfg; + struct bfa_pport_attr_s attr; + char symname[BFA_SYMNAME_MAXLEN]; + + sprintf(symname, "%s-%d", BFAD_DRIVER_NAME, bfad->inst_no); + memcpy(port_cfg.sym_name.symname, symname, strlen(symname)); + bfa_pport_get_attr(&bfad->bfa, &attr); + port_cfg.nwwn = attr.nwwn; + port_cfg.pwwn = attr.pwwn; + + bfa_fcs_cfg_base_port(&bfad->bfa_fcs, &port_cfg); +} + +bfa_status_t +bfad_drv_init(struct bfad_s *bfad) +{ + bfa_status_t rc; + unsigned long flags; + struct bfa_fcs_driver_info_s driver_info; + int i; + + bfad->cfg_data.rport_del_timeout = rport_del_timeout; + bfad->cfg_data.lun_queue_depth = bfa_lun_queue_depth; + bfad->cfg_data.io_max_sge = bfa_io_max_sge; + bfad->cfg_data.binding_method = FCP_PWWN_BINDING; + + rc = bfad_hal_mem_alloc(bfad); + if (rc != BFA_STATUS_OK) { + printk(KERN_WARNING "bfad%d bfad_hal_mem_alloc failure\n", + bfad->inst_no); + printk(KERN_WARNING + "Not enough memory to attach all Brocade HBA ports," + " System may need more memory.\n"); + goto out_hal_mem_alloc_failure; + } + + bfa_init_log(&bfad->bfa, bfad->logmod); + bfa_init_trc(&bfad->bfa, bfad->trcmod); + bfa_init_aen(&bfad->bfa, bfad->aen); + INIT_LIST_HEAD(&bfad->file_q); + INIT_LIST_HEAD(&bfad->file_free_q); + for (i = 0; i < BFAD_AEN_MAX_APPS; i++) { + bfa_q_qe_init(&bfad->file_buf[i].qe); + list_add_tail(&bfad->file_buf[i].qe, &bfad->file_free_q); + } + bfa_init_plog(&bfad->bfa, &bfad->plog_buf); + bfa_plog_init(&bfad->plog_buf); + bfa_plog_str(&bfad->plog_buf, BFA_PL_MID_DRVR, BFA_PL_EID_DRIVER_START, + 0, "Driver Attach"); + + bfa_attach(&bfad->bfa, bfad, &bfad->ioc_cfg, &bfad->meminfo, + &bfad->hal_pcidev); + + init_completion(&bfad->comp); + + /* + * Enable Interrupt and wait bfa_init completion + */ + if (bfad_setup_intr(bfad)) { + printk(KERN_WARNING "bfad%d: bfad_setup_intr failed\n", + bfad->inst_no); + goto out_setup_intr_failure; + } + + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_init(&bfad->bfa); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + /* + * Set up interrupt handler for each vectors + */ + if ((bfad->bfad_flags & BFAD_MSIX_ON) + && bfad_install_msix_handler(bfad)) { + printk(KERN_WARNING "%s: install_msix failed, bfad%d\n", + __FUNCTION__, bfad->inst_no); + } + + bfad_init_timer(bfad); + + wait_for_completion(&bfad->comp); + + memset(&driver_info, 0, sizeof(driver_info)); + strncpy(driver_info.version, BFAD_DRIVER_VERSION, + sizeof(driver_info.version) - 1); + if (host_name) + strncpy(driver_info.host_machine_name, host_name, + sizeof(driver_info.host_machine_name) - 1); + if (os_name) + strncpy(driver_info.host_os_name, os_name, + sizeof(driver_info.host_os_name) - 1); + if (os_patch) + strncpy(driver_info.host_os_patch, os_patch, + sizeof(driver_info.host_os_patch) - 1); + + strncpy(driver_info.os_device_name, bfad->pci_name, + sizeof(driver_info.os_device_name - 1)); + + /* + * FCS INIT + */ + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_fcs_log_init(&bfad->bfa_fcs, bfad->logmod); + bfa_fcs_trc_init(&bfad->bfa_fcs, bfad->trcmod); + bfa_fcs_aen_init(&bfad->bfa_fcs, bfad->aen); + bfa_fcs_init(&bfad->bfa_fcs, &bfad->bfa, bfad, BFA_FALSE); + bfa_fcs_driver_info_init(&bfad->bfa_fcs, &driver_info); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + bfad->bfad_flags |= BFAD_DRV_INIT_DONE; + return BFA_STATUS_OK; + +out_setup_intr_failure: + bfa_detach(&bfad->bfa); + bfad_hal_mem_release(bfad); +out_hal_mem_alloc_failure: + return BFA_STATUS_FAILED; +} + +void +bfad_drv_uninit(struct bfad_s *bfad) +{ + del_timer_sync(&bfad->hal_tmo); + bfa_isr_disable(&bfad->bfa); + bfa_detach(&bfad->bfa); + bfad_remove_intr(bfad); + bfa_assert(list_empty(&bfad->file_q)); + bfad_hal_mem_release(bfad); +} + +void +bfad_drv_start(struct bfad_s *bfad) +{ + unsigned long flags; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_start(&bfad->bfa); + bfa_fcs_start(&bfad->bfa_fcs); + bfad->bfad_flags |= BFAD_HAL_START_DONE; + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + bfad_fc4_probe_post(bfad); +} + +void +bfad_drv_stop(struct bfad_s *bfad) +{ + unsigned long flags; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + init_completion(&bfad->comp); + bfad->pport.flags |= BFAD_PORT_DELETE; + bfa_fcs_exit(&bfad->bfa_fcs); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + wait_for_completion(&bfad->comp); + + spin_lock_irqsave(&bfad->bfad_lock, flags); + init_completion(&bfad->comp); + bfa_stop(&bfad->bfa); + bfad->bfad_flags &= ~BFAD_HAL_START_DONE; + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + wait_for_completion(&bfad->comp); +} + +bfa_status_t +bfad_cfg_pport(struct bfad_s *bfad, enum bfa_port_role role) +{ + int rc = BFA_STATUS_OK; + + /* + * Allocate scsi_host for the physical port + */ + if ((bfad_supported_fc4s & BFA_PORT_ROLE_FCP_IM) + && (role & BFA_PORT_ROLE_FCP_IM)) { + if (bfad->pport.im_port == NULL) { + rc = BFA_STATUS_FAILED; + goto out; + } + + rc = bfad_im_scsi_host_alloc(bfad, bfad->pport.im_port); + if (rc != BFA_STATUS_OK) + goto out; + + bfad->pport.roles |= BFA_PORT_ROLE_FCP_IM; + } + + bfad->bfad_flags |= BFAD_CFG_PPORT_DONE; + +out: + return rc; +} + +void +bfad_uncfg_pport(struct bfad_s *bfad) +{ + if ((bfad->pport.roles & BFA_PORT_ROLE_FCP_IPFC) && ipfc_enable) { + bfad_ipfc_port_delete(bfad, &bfad->pport); + bfad->pport.roles &= ~BFA_PORT_ROLE_FCP_IPFC; + } + + if ((bfad_supported_fc4s & BFA_PORT_ROLE_FCP_IM) + && (bfad->pport.roles & BFA_PORT_ROLE_FCP_IM)) { + bfad_im_scsi_host_free(bfad, bfad->pport.im_port); + bfad_im_port_clean(bfad->pport.im_port); + kfree(bfad->pport.im_port); + bfad->pport.roles &= ~BFA_PORT_ROLE_FCP_IM; + } + + bfad->bfad_flags &= ~BFAD_CFG_PPORT_DONE; +} + +void +bfad_drv_log_level_set(struct bfad_s *bfad) +{ + if (log_level > BFA_LOG_INVALID && log_level <= BFA_LOG_LEVEL_MAX) + bfa_log_set_level_all(&bfad->log_data, log_level); +} + + /* + * PCI_entry PCI driver entries * { + */ + +/** + * PCI probe entry. + */ +int +bfad_pci_probe(struct pci_dev *pdev, const struct pci_device_id *pid) +{ + struct bfad_s *bfad; + int error = -ENODEV, retval; + char buf[16]; + + /* + * For single port cards - only claim function 0 + */ + if ((pdev->device == BFA_PCI_DEVICE_ID_FC_8G1P) + && (PCI_FUNC(pdev->devfn) != 0)) + return -ENODEV; + + BFA_TRACE(BFA_INFO, "bfad_pci_probe entry"); + + bfad = kzalloc(sizeof(struct bfad_s), GFP_KERNEL); + if (!bfad) { + error = -ENOMEM; + goto out; + } + + bfad->trcmod = kzalloc(sizeof(struct bfa_trc_mod_s), GFP_KERNEL); + if (!bfad->trcmod) { + printk(KERN_WARNING "Error alloc trace buffer!\n"); + error = -ENOMEM; + goto out_alloc_trace_failure; + } + + /* + * LOG/TRACE INIT + */ + bfa_trc_init(bfad->trcmod); + bfa_trc(bfad, bfad_inst); + + bfad->logmod = &bfad->log_data; + sprintf(buf, "%d", bfad_inst); + bfa_log_init(bfad->logmod, buf, bfa_os_printf); + + bfad_drv_log_level_set(bfad); + + bfad->aen = &bfad->aen_buf; + + if (!(bfad_load_fwimg(pdev))) { + printk(KERN_WARNING "bfad_load_fwimg failure!\n"); + kfree(bfad->trcmod); + goto out_alloc_trace_failure; + } + + retval = bfad_pci_init(pdev, bfad); + if (retval) { + printk(KERN_WARNING "bfad_pci_init failure!\n"); + error = retval; + goto out_pci_init_failure; + } + + mutex_lock(&bfad_mutex); + bfad->inst_no = bfad_inst++; + list_add_tail(&bfad->list_entry, &bfad_list); + mutex_unlock(&bfad_mutex); + + spin_lock_init(&bfad->bfad_lock); + pci_set_drvdata(pdev, bfad); + + bfad->ref_count = 0; + bfad->pport.bfad = bfad; + + retval = bfad_drv_init(bfad); + if (retval != BFA_STATUS_OK) + goto out_drv_init_failure; + if (!(bfad->bfad_flags & BFAD_HAL_INIT_DONE)) { + printk(KERN_WARNING "bfad%d: hal init failed\n", bfad->inst_no); + goto ok; + } + + /* + * PPORT FCS config + */ + bfad_fcs_port_cfg(bfad); + + retval = bfad_cfg_pport(bfad, BFA_PORT_ROLE_FCP_IM); + if (retval != BFA_STATUS_OK) + goto out_cfg_pport_failure; + + /* + * BFAD level FC4 (IM/TM/IPFC) specific resource allocation + */ + retval = bfad_fc4_probe(bfad); + if (retval != BFA_STATUS_OK) { + printk(KERN_WARNING "bfad_fc4_probe failed\n"); + goto out_fc4_probe_failure; + } + + bfad_drv_start(bfad); + + /* + * If bfa_linkup_delay is set to -1 default; try to retrive the + * value using the bfad_os_get_linkup_delay(); else use the + * passed in module param value as the bfa_linkup_delay. + */ + if (bfa_linkup_delay < 0) { + bfa_linkup_delay = bfad_os_get_linkup_delay(bfad); + bfad_os_rport_online_wait(bfad); + bfa_linkup_delay = -1; + } else { + bfad_os_rport_online_wait(bfad); + } + + bfa_log(bfad->logmod, BFA_LOG_LINUX_DEVICE_CLAIMED, bfad->pci_name); +ok: + return 0; + +out_fc4_probe_failure: + bfad_fc4_probe_undo(bfad); + bfad_uncfg_pport(bfad); +out_cfg_pport_failure: + bfad_drv_uninit(bfad); +out_drv_init_failure: + mutex_lock(&bfad_mutex); + bfad_inst--; + list_del(&bfad->list_entry); + mutex_unlock(&bfad_mutex); + bfad_pci_uninit(pdev, bfad); +out_pci_init_failure: + kfree(bfad->trcmod); +out_alloc_trace_failure: + kfree(bfad); +out: + return error; +} + +/** + * PCI remove entry. + */ +void +bfad_pci_remove(struct pci_dev *pdev) +{ + struct bfad_s *bfad = pci_get_drvdata(pdev); + unsigned long flags; + + bfa_trc(bfad, bfad->inst_no); + + if ((bfad->bfad_flags & BFAD_DRV_INIT_DONE) + && !(bfad->bfad_flags & BFAD_HAL_INIT_DONE)) { + + spin_lock_irqsave(&bfad->bfad_lock, flags); + init_completion(&bfad->comp); + bfa_stop(&bfad->bfa); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + wait_for_completion(&bfad->comp); + + bfad_remove_intr(bfad); + del_timer_sync(&bfad->hal_tmo); + goto hal_detach; + } else if (!(bfad->bfad_flags & BFAD_DRV_INIT_DONE)) { + goto remove_sysfs; + } + + if (bfad->bfad_flags & BFAD_HAL_START_DONE) + bfad_drv_stop(bfad); + + bfad_remove_intr(bfad); + + del_timer_sync(&bfad->hal_tmo); + bfad_fc4_probe_undo(bfad); + + if (bfad->bfad_flags & BFAD_CFG_PPORT_DONE) + bfad_uncfg_pport(bfad); + +hal_detach: + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_detach(&bfad->bfa); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + bfad_hal_mem_release(bfad); +remove_sysfs: + + mutex_lock(&bfad_mutex); + bfad_inst--; + list_del(&bfad->list_entry); + mutex_unlock(&bfad_mutex); + bfad_pci_uninit(pdev, bfad); + + kfree(bfad->trcmod); + kfree(bfad); +} + + +static struct pci_device_id bfad_id_table[] = { + { + .vendor = BFA_PCI_VENDOR_ID_BROCADE, + .device = BFA_PCI_DEVICE_ID_FC_8G2P, + .subvendor = PCI_ANY_ID, + .subdevice = PCI_ANY_ID, + }, + { + .vendor = BFA_PCI_VENDOR_ID_BROCADE, + .device = BFA_PCI_DEVICE_ID_FC_8G1P, + .subvendor = PCI_ANY_ID, + .subdevice = PCI_ANY_ID, + }, + { + .vendor = BFA_PCI_VENDOR_ID_BROCADE, + .device = BFA_PCI_DEVICE_ID_CT, + .subvendor = PCI_ANY_ID, + .subdevice = PCI_ANY_ID, + .class = (PCI_CLASS_SERIAL_FIBER << 8), + .class_mask = ~0, + }, + + {0, 0}, +}; + +MODULE_DEVICE_TABLE(pci, bfad_id_table); + +static struct pci_driver bfad_pci_driver = { + .name = BFAD_DRIVER_NAME, + .id_table = bfad_id_table, + .probe = bfad_pci_probe, + .remove = __devexit_p(bfad_pci_remove), +}; + +/** + * Linux driver module functions + */ +bfa_status_t +bfad_fc4_module_init(void) +{ + int rc; + + rc = bfad_im_module_init(); + if (rc != BFA_STATUS_OK) + goto ext; + + bfad_tm_module_init(); + if (ipfc_enable) + bfad_ipfc_module_init(); +ext: + return rc; +} + +void +bfad_fc4_module_exit(void) +{ + if (ipfc_enable) + bfad_ipfc_module_exit(); + bfad_tm_module_exit(); + bfad_im_module_exit(); +} + +/** + * Driver module init. + */ +static int __init +bfad_init(void) +{ + int error = 0; + + printk(KERN_INFO "Brocade BFA FC/FCOE SCSI driver - version: %s\n", + BFAD_DRIVER_VERSION); + + if (num_sgpgs > 0) + num_sgpgs_parm = num_sgpgs; + + error = bfad_fc4_module_init(); + if (error) { + error = -ENOMEM; + printk(KERN_WARNING "bfad_fc4_module_init failure\n"); + goto ext; + } + + if (!strcmp(FCPI_NAME, " fcpim")) + bfad_supported_fc4s |= BFA_PORT_ROLE_FCP_IM; + if (!strcmp(FCPT_NAME, " fcptm")) + bfad_supported_fc4s |= BFA_PORT_ROLE_FCP_TM; + if (!strcmp(IPFC_NAME, " ipfc")) + bfad_supported_fc4s |= BFA_PORT_ROLE_FCP_IPFC; + + bfa_ioc_auto_recover(ioc_auto_recover); + bfa_fcs_rport_set_del_timeout(rport_del_timeout); + error = pci_register_driver(&bfad_pci_driver); + + if (error) { + printk(KERN_WARNING "bfad pci_register_driver failure\n"); + goto ext; + } + + return 0; + +ext: + bfad_fc4_module_exit(); + return error; +} + +/** + * Driver module exit. + */ +static void __exit +bfad_exit(void) +{ + pci_unregister_driver(&bfad_pci_driver); + bfad_fc4_module_exit(); + bfad_free_fwimg(); +} + +#define BFAD_PROTO_NAME FCPI_NAME FCPT_NAME IPFC_NAME + +module_init(bfad_init); +module_exit(bfad_exit); +MODULE_LICENSE("GPL"); +MODULE_DESCRIPTION("Brocade Fibre Channel HBA Driver" BFAD_PROTO_NAME); +MODULE_AUTHOR("Brocade Communications Systems, Inc."); +MODULE_VERSION(BFAD_DRIVER_VERSION); + + diff --git a/drivers/scsi/bfa/bfad_attr.c b/drivers/scsi/bfa/bfad_attr.c new file mode 100644 index 000000000000..9129ae3040ff --- /dev/null +++ b/drivers/scsi/bfa/bfad_attr.c @@ -0,0 +1,649 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_attr.c Linux driver configuration interface module. + */ + +#include "bfad_drv.h" +#include "bfad_im.h" +#include "bfad_trcmod.h" +#include "bfad_attr.h" + +/** + * FC_transport_template FC transport template + */ + +/** + * FC transport template entry, get SCSI target port ID. + */ +void +bfad_im_get_starget_port_id(struct scsi_target *starget) +{ + struct Scsi_Host *shost; + struct bfad_im_port_s *im_port; + struct bfad_s *bfad; + struct bfad_itnim_s *itnim = NULL; + u32 fc_id = -1; + unsigned long flags; + + shost = bfad_os_starget_to_shost(starget); + im_port = (struct bfad_im_port_s *) shost->hostdata[0]; + bfad = im_port->bfad; + spin_lock_irqsave(&bfad->bfad_lock, flags); + + itnim = bfad_os_get_itnim(im_port, starget->id); + if (itnim) + fc_id = bfa_fcs_itnim_get_fcid(&itnim->fcs_itnim); + + fc_starget_port_id(starget) = fc_id; + spin_unlock_irqrestore(&bfad->bfad_lock, flags); +} + +/** + * FC transport template entry, get SCSI target nwwn. + */ +void +bfad_im_get_starget_node_name(struct scsi_target *starget) +{ + struct Scsi_Host *shost; + struct bfad_im_port_s *im_port; + struct bfad_s *bfad; + struct bfad_itnim_s *itnim = NULL; + u64 node_name = 0; + unsigned long flags; + + shost = bfad_os_starget_to_shost(starget); + im_port = (struct bfad_im_port_s *) shost->hostdata[0]; + bfad = im_port->bfad; + spin_lock_irqsave(&bfad->bfad_lock, flags); + + itnim = bfad_os_get_itnim(im_port, starget->id); + if (itnim) + node_name = bfa_fcs_itnim_get_nwwn(&itnim->fcs_itnim); + + fc_starget_node_name(starget) = bfa_os_htonll(node_name); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); +} + +/** + * FC transport template entry, get SCSI target pwwn. + */ +void +bfad_im_get_starget_port_name(struct scsi_target *starget) +{ + struct Scsi_Host *shost; + struct bfad_im_port_s *im_port; + struct bfad_s *bfad; + struct bfad_itnim_s *itnim = NULL; + u64 port_name = 0; + unsigned long flags; + + shost = bfad_os_starget_to_shost(starget); + im_port = (struct bfad_im_port_s *) shost->hostdata[0]; + bfad = im_port->bfad; + spin_lock_irqsave(&bfad->bfad_lock, flags); + + itnim = bfad_os_get_itnim(im_port, starget->id); + if (itnim) + port_name = bfa_fcs_itnim_get_pwwn(&itnim->fcs_itnim); + + fc_starget_port_name(starget) = bfa_os_htonll(port_name); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); +} + +/** + * FC transport template entry, get SCSI host port ID. + */ +void +bfad_im_get_host_port_id(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_port_s *port = im_port->port; + + fc_host_port_id(shost) = + bfa_os_hton3b(bfa_fcs_port_get_fcid(port->fcs_port)); +} + + + + + +struct Scsi_Host * +bfad_os_starget_to_shost(struct scsi_target *starget) +{ + return dev_to_shost(starget->dev.parent); +} + +/** + * FC transport template entry, get SCSI host port type. + */ +static void +bfad_im_get_host_port_type(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_pport_attr_s attr; + + bfa_pport_get_attr(&bfad->bfa, &attr); + + switch (attr.port_type) { + case BFA_PPORT_TYPE_NPORT: + fc_host_port_type(shost) = FC_PORTTYPE_NPORT; + break; + case BFA_PPORT_TYPE_NLPORT: + fc_host_port_type(shost) = FC_PORTTYPE_NLPORT; + break; + case BFA_PPORT_TYPE_P2P: + fc_host_port_type(shost) = FC_PORTTYPE_PTP; + break; + case BFA_PPORT_TYPE_LPORT: + fc_host_port_type(shost) = FC_PORTTYPE_LPORT; + break; + default: + fc_host_port_type(shost) = FC_PORTTYPE_UNKNOWN; + break; + } +} + +/** + * FC transport template entry, get SCSI host port state. + */ +static void +bfad_im_get_host_port_state(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_pport_attr_s attr; + + bfa_pport_get_attr(&bfad->bfa, &attr); + + switch (attr.port_state) { + case BFA_PPORT_ST_LINKDOWN: + fc_host_port_state(shost) = FC_PORTSTATE_LINKDOWN; + break; + case BFA_PPORT_ST_LINKUP: + fc_host_port_state(shost) = FC_PORTSTATE_ONLINE; + break; + case BFA_PPORT_ST_UNINIT: + case BFA_PPORT_ST_ENABLING_QWAIT: + case BFA_PPORT_ST_ENABLING: + case BFA_PPORT_ST_DISABLING_QWAIT: + case BFA_PPORT_ST_DISABLING: + case BFA_PPORT_ST_DISABLED: + case BFA_PPORT_ST_STOPPED: + case BFA_PPORT_ST_IOCDOWN: + default: + fc_host_port_state(shost) = FC_PORTSTATE_UNKNOWN; + break; + } +} + +/** + * FC transport template entry, get SCSI host active fc4s. + */ +static void +bfad_im_get_host_active_fc4s(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_port_s *port = im_port->port; + + memset(fc_host_active_fc4s(shost), 0, + sizeof(fc_host_active_fc4s(shost))); + + if (port->supported_fc4s & + (BFA_PORT_ROLE_FCP_IM | BFA_PORT_ROLE_FCP_TM)) + fc_host_active_fc4s(shost)[2] = 1; + + if (port->supported_fc4s & BFA_PORT_ROLE_FCP_IPFC) + fc_host_active_fc4s(shost)[3] = 0x20; + + fc_host_active_fc4s(shost)[7] = 1; +} + +/** + * FC transport template entry, get SCSI host link speed. + */ +static void +bfad_im_get_host_speed(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_pport_attr_s attr; + + bfa_pport_get_attr(&bfad->bfa, &attr); + switch (attr.speed) { + case BFA_PPORT_SPEED_8GBPS: + fc_host_speed(shost) = FC_PORTSPEED_8GBIT; + break; + case BFA_PPORT_SPEED_4GBPS: + fc_host_speed(shost) = FC_PORTSPEED_4GBIT; + break; + case BFA_PPORT_SPEED_2GBPS: + fc_host_speed(shost) = FC_PORTSPEED_2GBIT; + break; + case BFA_PPORT_SPEED_1GBPS: + fc_host_speed(shost) = FC_PORTSPEED_1GBIT; + break; + default: + fc_host_speed(shost) = FC_PORTSPEED_UNKNOWN; + break; + } +} + +/** + * FC transport template entry, get SCSI host port type. + */ +static void +bfad_im_get_host_fabric_name(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_port_s *port = im_port->port; + wwn_t fabric_nwwn = 0; + + fabric_nwwn = bfa_fcs_port_get_fabric_name(port->fcs_port); + + fc_host_fabric_name(shost) = bfa_os_htonll(fabric_nwwn); + +} + +/** + * FC transport template entry, get BFAD statistics. + */ +static struct fc_host_statistics * +bfad_im_get_stats(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfad_hal_comp fcomp; + struct fc_host_statistics *hstats; + bfa_status_t rc; + unsigned long flags; + + hstats = &bfad->link_stats; + init_completion(&fcomp.comp); + spin_lock_irqsave(&bfad->bfad_lock, flags); + memset(hstats, 0, sizeof(struct fc_host_statistics)); + rc = bfa_pport_get_stats(&bfad->bfa, + (union bfa_pport_stats_u *) hstats, + bfad_hcb_comp, &fcomp); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + if (rc != BFA_STATUS_OK) + return NULL; + + wait_for_completion(&fcomp.comp); + + return hstats; +} + +/** + * FC transport template entry, reset BFAD statistics. + */ +static void +bfad_im_reset_stats(struct Scsi_Host *shost) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfad_hal_comp fcomp; + unsigned long flags; + bfa_status_t rc; + + init_completion(&fcomp.comp); + spin_lock_irqsave(&bfad->bfad_lock, flags); + rc = bfa_pport_clear_stats(&bfad->bfa, bfad_hcb_comp, &fcomp); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + if (rc != BFA_STATUS_OK) + return; + + wait_for_completion(&fcomp.comp); + + return; +} + +/** + * FC transport template entry, get rport loss timeout. + */ +static void +bfad_im_get_rport_loss_tmo(struct fc_rport *rport) +{ + struct bfad_itnim_data_s *itnim_data = rport->dd_data; + struct bfad_itnim_s *itnim = itnim_data->itnim; + struct bfad_s *bfad = itnim->im->bfad; + unsigned long flags; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + rport->dev_loss_tmo = bfa_fcpim_path_tov_get(&bfad->bfa); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); +} + +/** + * FC transport template entry, set rport loss timeout. + */ +static void +bfad_im_set_rport_loss_tmo(struct fc_rport *rport, u32 timeout) +{ + struct bfad_itnim_data_s *itnim_data = rport->dd_data; + struct bfad_itnim_s *itnim = itnim_data->itnim; + struct bfad_s *bfad = itnim->im->bfad; + unsigned long flags; + + if (timeout > 0) { + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_fcpim_path_tov_set(&bfad->bfa, timeout); + rport->dev_loss_tmo = bfa_fcpim_path_tov_get(&bfad->bfa); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + } + +} + +struct fc_function_template bfad_im_fc_function_template = { + + /* Target dynamic attributes */ + .get_starget_port_id = bfad_im_get_starget_port_id, + .show_starget_port_id = 1, + .get_starget_node_name = bfad_im_get_starget_node_name, + .show_starget_node_name = 1, + .get_starget_port_name = bfad_im_get_starget_port_name, + .show_starget_port_name = 1, + + /* Host dynamic attribute */ + .get_host_port_id = bfad_im_get_host_port_id, + .show_host_port_id = 1, + + /* Host fixed attributes */ + .show_host_node_name = 1, + .show_host_port_name = 1, + .show_host_supported_classes = 1, + .show_host_supported_fc4s = 1, + .show_host_supported_speeds = 1, + .show_host_maxframe_size = 1, + + /* More host dynamic attributes */ + .show_host_port_type = 1, + .get_host_port_type = bfad_im_get_host_port_type, + .show_host_port_state = 1, + .get_host_port_state = bfad_im_get_host_port_state, + .show_host_active_fc4s = 1, + .get_host_active_fc4s = bfad_im_get_host_active_fc4s, + .show_host_speed = 1, + .get_host_speed = bfad_im_get_host_speed, + .show_host_fabric_name = 1, + .get_host_fabric_name = bfad_im_get_host_fabric_name, + + .show_host_symbolic_name = 1, + + /* Statistics */ + .get_fc_host_stats = bfad_im_get_stats, + .reset_fc_host_stats = bfad_im_reset_stats, + + /* Allocation length for host specific data */ + .dd_fcrport_size = sizeof(struct bfad_itnim_data_s *), + + /* Remote port fixed attributes */ + .show_rport_maxframe_size = 1, + .show_rport_supported_classes = 1, + .show_rport_dev_loss_tmo = 1, + .get_rport_dev_loss_tmo = bfad_im_get_rport_loss_tmo, + .set_rport_dev_loss_tmo = bfad_im_set_rport_loss_tmo, +}; + +/** + * Scsi_Host_attrs SCSI host attributes + */ +static ssize_t +bfad_im_serial_num_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + return snprintf(buf, PAGE_SIZE, "%s\n", + ioc_attr.adapter_attr.serial_num); +} + +static ssize_t +bfad_im_model_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + return snprintf(buf, PAGE_SIZE, "%s\n", ioc_attr.adapter_attr.model); +} + +static ssize_t +bfad_im_model_desc_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + return snprintf(buf, PAGE_SIZE, "%s\n", + ioc_attr.adapter_attr.model_descr); +} + +static ssize_t +bfad_im_node_name_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_port_s *port = im_port->port; + u64 nwwn; + + nwwn = bfa_fcs_port_get_nwwn(port->fcs_port); + return snprintf(buf, PAGE_SIZE, "0x%llx\n", bfa_os_htonll(nwwn)); +} + +static ssize_t +bfad_im_symbolic_name_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + + return snprintf(buf, PAGE_SIZE, "Brocade %s FV%s DV%s\n", + ioc_attr.adapter_attr.model, + ioc_attr.adapter_attr.fw_ver, BFAD_DRIVER_VERSION); +} + +static ssize_t +bfad_im_hw_version_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + return snprintf(buf, PAGE_SIZE, "%s\n", ioc_attr.adapter_attr.hw_ver); +} + +static ssize_t +bfad_im_drv_version_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + return snprintf(buf, PAGE_SIZE, "%s\n", BFAD_DRIVER_VERSION); +} + +static ssize_t +bfad_im_optionrom_version_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + return snprintf(buf, PAGE_SIZE, "%s\n", + ioc_attr.adapter_attr.optrom_ver); +} + +static ssize_t +bfad_im_fw_version_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + return snprintf(buf, PAGE_SIZE, "%s\n", ioc_attr.adapter_attr.fw_ver); +} + +static ssize_t +bfad_im_num_of_ports_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioc_attr_s ioc_attr; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + return snprintf(buf, PAGE_SIZE, "%d\n", ioc_attr.adapter_attr.nports); +} + +static ssize_t +bfad_im_drv_name_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + return snprintf(buf, PAGE_SIZE, "%s\n", BFAD_DRIVER_NAME); +} + +static ssize_t +bfad_im_num_of_discovered_ports_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct Scsi_Host *shost = class_to_shost(dev); + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_port_s *port = im_port->port; + struct bfad_s *bfad = im_port->bfad; + int nrports = 2048; + wwn_t *rports = NULL; + unsigned long flags; + + rports = kzalloc(sizeof(wwn_t) * nrports , GFP_ATOMIC); + if (rports == NULL) + return -ENOMEM; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_fcs_port_get_rports(port->fcs_port, rports, &nrports); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + kfree(rports); + + return snprintf(buf, PAGE_SIZE, "%d\n", nrports); +} + +static DEVICE_ATTR(serial_number, S_IRUGO, + bfad_im_serial_num_show, NULL); +static DEVICE_ATTR(model, S_IRUGO, bfad_im_model_show, NULL); +static DEVICE_ATTR(model_description, S_IRUGO, + bfad_im_model_desc_show, NULL); +static DEVICE_ATTR(node_name, S_IRUGO, bfad_im_node_name_show, NULL); +static DEVICE_ATTR(symbolic_name, S_IRUGO, + bfad_im_symbolic_name_show, NULL); +static DEVICE_ATTR(hardware_version, S_IRUGO, + bfad_im_hw_version_show, NULL); +static DEVICE_ATTR(driver_version, S_IRUGO, + bfad_im_drv_version_show, NULL); +static DEVICE_ATTR(option_rom_version, S_IRUGO, + bfad_im_optionrom_version_show, NULL); +static DEVICE_ATTR(firmware_version, S_IRUGO, + bfad_im_fw_version_show, NULL); +static DEVICE_ATTR(number_of_ports, S_IRUGO, + bfad_im_num_of_ports_show, NULL); +static DEVICE_ATTR(driver_name, S_IRUGO, bfad_im_drv_name_show, NULL); +static DEVICE_ATTR(number_of_discovered_ports, S_IRUGO, + bfad_im_num_of_discovered_ports_show, NULL); + +struct device_attribute *bfad_im_host_attrs[] = { + &dev_attr_serial_number, + &dev_attr_model, + &dev_attr_model_description, + &dev_attr_node_name, + &dev_attr_symbolic_name, + &dev_attr_hardware_version, + &dev_attr_driver_version, + &dev_attr_option_rom_version, + &dev_attr_firmware_version, + &dev_attr_number_of_ports, + &dev_attr_driver_name, + &dev_attr_number_of_discovered_ports, + NULL, +}; + +struct device_attribute *bfad_im_vport_attrs[] = { + &dev_attr_serial_number, + &dev_attr_model, + &dev_attr_model_description, + &dev_attr_node_name, + &dev_attr_symbolic_name, + &dev_attr_hardware_version, + &dev_attr_driver_version, + &dev_attr_option_rom_version, + &dev_attr_firmware_version, + &dev_attr_number_of_ports, + &dev_attr_driver_name, + &dev_attr_number_of_discovered_ports, + NULL, +}; + + diff --git a/drivers/scsi/bfa/bfad_attr.h b/drivers/scsi/bfa/bfad_attr.h new file mode 100644 index 000000000000..4d3312da6a81 --- /dev/null +++ b/drivers/scsi/bfa/bfad_attr.h @@ -0,0 +1,65 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFAD_ATTR_H__ +#define __BFAD_ATTR_H__ +/** + * bfad_attr.h VMware driver configuration interface module. + */ + +/** + * FC_transport_template FC transport template + */ + +struct Scsi_Host* +bfad_os_dev_to_shost(struct scsi_target *starget); + +/** + * FC transport template entry, get SCSI target port ID. + */ +void +bfad_im_get_starget_port_id(struct scsi_target *starget); + +/** + * FC transport template entry, get SCSI target nwwn. + */ +void +bfad_im_get_starget_node_name(struct scsi_target *starget); + +/** + * FC transport template entry, get SCSI target pwwn. + */ +void +bfad_im_get_starget_port_name(struct scsi_target *starget); + +/** + * FC transport template entry, get SCSI host port ID. + */ +void +bfad_im_get_host_port_id(struct Scsi_Host *shost); + +/** + * FC transport template entry, issue a LIP. + */ +int +bfad_im_issue_fc_host_lip(struct Scsi_Host *shost); + +struct Scsi_Host* +bfad_os_starget_to_shost(struct scsi_target *starget); + + +#endif /* __BFAD_ATTR_H__ */ diff --git a/drivers/scsi/bfa/bfad_drv.h b/drivers/scsi/bfa/bfad_drv.h new file mode 100644 index 000000000000..172c81e25c1c --- /dev/null +++ b/drivers/scsi/bfa/bfad_drv.h @@ -0,0 +1,295 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * Contains base driver definitions. + */ + +/** + * bfa_drv.h Linux driver data structures. + */ + +#ifndef __BFAD_DRV_H__ +#define __BFAD_DRV_H__ + +#include "bfa_os_inc.h" + +#include <bfa.h> +#include <bfa_svc.h> +#include <fcs/bfa_fcs.h> +#include <defs/bfa_defs_pci.h> +#include <defs/bfa_defs_port.h> +#include <defs/bfa_defs_rport.h> +#include <fcs/bfa_fcs_rport.h> +#include <defs/bfa_defs_vport.h> +#include <fcs/bfa_fcs_vport.h> + +#include <cs/bfa_plog.h> +#include "aen/bfa_aen.h" +#include <log/bfa_log_linux.h> + +#define BFAD_DRIVER_NAME "bfa" +#ifdef BFA_DRIVER_VERSION +#define BFAD_DRIVER_VERSION BFA_DRIVER_VERSION +#else +#define BFAD_DRIVER_VERSION "2.0.0.0" +#endif + + +#define BFAD_IRQ_FLAGS IRQF_SHARED + +/* + * BFAD flags + */ +#define BFAD_MSIX_ON 0x00000001 +#define BFAD_HAL_INIT_DONE 0x00000002 +#define BFAD_DRV_INIT_DONE 0x00000004 +#define BFAD_CFG_PPORT_DONE 0x00000008 +#define BFAD_HAL_START_DONE 0x00000010 +#define BFAD_PORT_ONLINE 0x00000020 +#define BFAD_RPORT_ONLINE 0x00000040 + +#define BFAD_PORT_DELETE 0x00000001 + +/* + * BFAD related definition + */ +#define SCSI_SCAN_DELAY HZ +#define BFAD_STOP_TIMEOUT 30 +#define BFAD_SUSPEND_TIMEOUT BFAD_STOP_TIMEOUT + +/* + * BFAD configuration parameter default values + */ +#define BFAD_LUN_QUEUE_DEPTH 32 +#define BFAD_IO_MAX_SGE SG_ALL + +#define bfad_isr_t irq_handler_t + +#define MAX_MSIX_ENTRY 22 + +struct bfad_msix_s { + struct bfad_s *bfad; + struct msix_entry msix; +}; + +enum bfad_port_pvb_type { + BFAD_PORT_PHYS_BASE = 0, + BFAD_PORT_PHYS_VPORT = 1, + BFAD_PORT_VF_BASE = 2, + BFAD_PORT_VF_VPORT = 3, +}; + +/* + * PORT data structure + */ +struct bfad_port_s { + struct list_head list_entry; + struct bfad_s *bfad; + struct bfa_fcs_port_s *fcs_port; + u32 roles; + s32 flags; + u32 supported_fc4s; + u8 ipfc_flags; + enum bfad_port_pvb_type pvb_type; + struct bfad_im_port_s *im_port; /* IM specific data */ + struct bfad_tm_port_s *tm_port; /* TM specific data */ + struct bfad_ipfc_port_s *ipfc_port; /* IPFC specific data */ +}; + +/* + * VPORT data structure + */ +struct bfad_vport_s { + struct bfad_port_s drv_port; + struct bfa_fcs_vport_s fcs_vport; + struct completion *comp_del; +}; + +/* + * VF data structure + */ +struct bfad_vf_s { + bfa_fcs_vf_t fcs_vf; + struct bfad_port_s base_port; /* base port for vf */ + struct bfad_s *bfad; +}; + +struct bfad_cfg_param_s { + u32 rport_del_timeout; + u32 ioc_queue_depth; + u32 lun_queue_depth; + u32 io_max_sge; + u32 binding_method; +}; + +#define BFAD_AEN_MAX_APPS 8 +struct bfad_aen_file_s { + struct list_head qe; + struct bfad_s *bfad; + s32 ri; + s32 app_id; +}; + +/* + * BFAD (PCI function) data structure + */ +struct bfad_s { + struct list_head list_entry; + struct bfa_s bfa; + struct bfa_fcs_s bfa_fcs; + struct pci_dev *pcidev; + const char *pci_name; + struct bfa_pcidev_s hal_pcidev; + struct bfa_ioc_pci_attr_s pci_attr; + unsigned long pci_bar0_map; + void __iomem *pci_bar0_kva; + struct completion comp; + struct completion suspend; + struct completion disable_comp; + bfa_boolean_t disable_active; + struct bfad_port_s pport; /* physical port of the BFAD */ + struct bfa_meminfo_s meminfo; + struct bfa_iocfc_cfg_s ioc_cfg; + u32 inst_no; /* BFAD instance number */ + u32 bfad_flags; + spinlock_t bfad_lock; + struct bfad_cfg_param_s cfg_data; + struct bfad_msix_s msix_tab[MAX_MSIX_ENTRY]; + int nvec; + char adapter_name[BFA_ADAPTER_SYM_NAME_LEN]; + char port_name[BFA_ADAPTER_SYM_NAME_LEN]; + struct timer_list hal_tmo; + unsigned long hs_start; + struct bfad_im_s *im; /* IM specific data */ + struct bfad_tm_s *tm; /* TM specific data */ + struct bfad_ipfc_s *ipfc; /* IPFC specific data */ + struct bfa_log_mod_s log_data; + struct bfa_trc_mod_s *trcmod; + struct bfa_log_mod_s *logmod; + struct bfa_aen_s *aen; + struct bfa_aen_s aen_buf; + struct bfad_aen_file_s file_buf[BFAD_AEN_MAX_APPS]; + struct list_head file_q; + struct list_head file_free_q; + struct bfa_plog_s plog_buf; + int ref_count; + bfa_boolean_t ipfc_enabled; + struct fc_host_statistics link_stats; + + struct kobject *bfa_kobj; + struct kobject *ioc_kobj; + struct kobject *pport_kobj; + struct kobject *lport_kobj; +}; + +/* + * RPORT data structure + */ +struct bfad_rport_s { + struct bfa_fcs_rport_s fcs_rport; +}; + +struct bfad_buf_info { + void *virt; + dma_addr_t phys; + u32 size; +}; + +struct bfad_fcxp { + struct bfad_port_s *port; + struct bfa_rport_s *bfa_rport; + bfa_status_t req_status; + u16 tag; + u16 rsp_len; + u16 rsp_maxlen; + u8 use_ireqbuf; + u8 use_irspbuf; + u32 num_req_sgles; + u32 num_rsp_sgles; + struct fchs_s fchs; + void *reqbuf_info; + void *rspbuf_info; + struct bfa_sge_s *req_sge; + struct bfa_sge_s *rsp_sge; + fcxp_send_cb_t send_cbfn; + void *send_cbarg; + void *bfa_fcxp; + struct completion comp; +}; + +struct bfad_hal_comp { + bfa_status_t status; + struct completion comp; +}; + +/* + * Macro to obtain the immediate lower power + * of two for the integer. + */ +#define nextLowerInt(x) \ +do { \ + int j; \ + (*x)--; \ + for (j = 1; j < (sizeof(int) * 8); j <<= 1) \ + (*x) = (*x) | (*x) >> j; \ + (*x)++; \ + (*x) = (*x) >> 1; \ +} while (0) + + +bfa_status_t bfad_vport_create(struct bfad_s *bfad, u16 vf_id, + struct bfa_port_cfg_s *port_cfg); +bfa_status_t bfad_vf_create(struct bfad_s *bfad, u16 vf_id, + struct bfa_port_cfg_s *port_cfg); +bfa_status_t bfad_cfg_pport(struct bfad_s *bfad, enum bfa_port_role role); +bfa_status_t bfad_drv_init(struct bfad_s *bfad); +void bfad_drv_start(struct bfad_s *bfad); +void bfad_uncfg_pport(struct bfad_s *bfad); +void bfad_drv_stop(struct bfad_s *bfad); +void bfad_remove_intr(struct bfad_s *bfad); +void bfad_hal_mem_release(struct bfad_s *bfad); +void bfad_hcb_comp(void *arg, bfa_status_t status); + +int bfad_setup_intr(struct bfad_s *bfad); +void bfad_remove_intr(struct bfad_s *bfad); + +void bfad_update_hal_cfg(struct bfa_iocfc_cfg_s *bfa_cfg); +bfa_status_t bfad_hal_mem_alloc(struct bfad_s *bfad); +void bfad_bfa_tmo(unsigned long data); +void bfad_init_timer(struct bfad_s *bfad); +int bfad_pci_init(struct pci_dev *pdev, struct bfad_s *bfad); +void bfad_pci_uninit(struct pci_dev *pdev, struct bfad_s *bfad); +void bfad_fcs_port_cfg(struct bfad_s *bfad); +void bfad_drv_uninit(struct bfad_s *bfad); +void bfad_drv_log_level_set(struct bfad_s *bfad); +bfa_status_t bfad_fc4_module_init(void); +void bfad_fc4_module_exit(void); + +void bfad_pci_remove(struct pci_dev *pdev); +int bfad_pci_probe(struct pci_dev *pdev, const struct pci_device_id *pid); +void bfad_os_rport_online_wait(struct bfad_s *bfad); +int bfad_os_get_linkup_delay(struct bfad_s *bfad); +int bfad_install_msix_handler(struct bfad_s *bfad); + +extern struct idr bfad_im_port_index; +extern struct list_head bfad_list; +extern int bfa_lun_queue_depth; +extern int bfad_supported_fc4s; +extern int bfa_linkup_delay; + +#endif /* __BFAD_DRV_H__ */ diff --git a/drivers/scsi/bfa/bfad_fwimg.c b/drivers/scsi/bfa/bfad_fwimg.c new file mode 100644 index 000000000000..bd34b0db2d6b --- /dev/null +++ b/drivers/scsi/bfa/bfad_fwimg.c @@ -0,0 +1,97 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfad_fwimg.c Linux driver PCI interface module. + */ +#include <bfa_os_inc.h> +#include <bfad_drv.h> +#include <bfad_im_compat.h> +#include <defs/bfa_defs_version.h> +#include <linux/errno.h> +#include <linux/sched.h> +#include <linux/init.h> +#include <linux/fs.h> +#include <asm/uaccess.h> +#include <asm/fcntl.h> +#include <linux/pci.h> +#include <linux/firmware.h> +#include <bfa_fwimg_priv.h> +#include <bfa.h> + +u32 bfi_image_ct_size; +u32 bfi_image_cb_size; +u32 *bfi_image_ct; +u32 *bfi_image_cb; + + +#define BFAD_FW_FILE_CT "ctfw.bin" +#define BFAD_FW_FILE_CB "cbfw.bin" +MODULE_FIRMWARE(BFAD_FW_FILE_CT); +MODULE_FIRMWARE(BFAD_FW_FILE_CB); + +u32 * +bfad_read_firmware(struct pci_dev *pdev, u32 **bfi_image, + u32 *bfi_image_size, char *fw_name) +{ + const struct firmware *fw; + + if (request_firmware(&fw, fw_name, &pdev->dev)) { + printk(KERN_ALERT "Can't locate firmware %s\n", fw_name); + goto error; + } + + *bfi_image = vmalloc(fw->size); + if (NULL == *bfi_image) { + printk(KERN_ALERT "Fail to allocate buffer for fw image " + "size=%x!\n", (u32) fw->size); + goto error; + } + + memcpy(*bfi_image, fw->data, fw->size); + *bfi_image_size = fw->size/sizeof(u32); + + return(*bfi_image); + +error: + return(NULL); +} + +u32 * +bfad_get_firmware_buf(struct pci_dev *pdev) +{ + if (pdev->device == BFA_PCI_DEVICE_ID_CT) { + if (bfi_image_ct_size == 0) + bfad_read_firmware(pdev, &bfi_image_ct, + &bfi_image_ct_size, BFAD_FW_FILE_CT); + return(bfi_image_ct); + } else { + if (bfi_image_cb_size == 0) + bfad_read_firmware(pdev, &bfi_image_cb, + &bfi_image_cb_size, BFAD_FW_FILE_CB); + return(bfi_image_cb); + } +} + +u32 * +bfi_image_ct_get_chunk(u32 off) +{ return (u32 *)(bfi_image_ct + off); } + +u32 * +bfi_image_cb_get_chunk(u32 off) +{ return (u32 *)(bfi_image_cb + off); } + diff --git a/drivers/scsi/bfa/bfad_im.c b/drivers/scsi/bfa/bfad_im.c new file mode 100644 index 000000000000..55d012a9a668 --- /dev/null +++ b/drivers/scsi/bfa/bfad_im.c @@ -0,0 +1,1230 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfad_im.c Linux driver IM module. + */ + +#include "bfad_drv.h" +#include "bfad_im.h" +#include "bfad_trcmod.h" +#include "bfa_cb_ioim_macros.h" +#include <fcb/bfa_fcb_fcpim.h> + +BFA_TRC_FILE(LDRV, IM); + +DEFINE_IDR(bfad_im_port_index); +struct scsi_transport_template *bfad_im_scsi_transport_template; +static void bfad_im_itnim_work_handler(struct work_struct *work); +static int bfad_im_queuecommand(struct scsi_cmnd *cmnd, + void (*done)(struct scsi_cmnd *)); +static int bfad_im_slave_alloc(struct scsi_device *sdev); + +void +bfa_cb_ioim_done(void *drv, struct bfad_ioim_s *dio, + enum bfi_ioim_status io_status, u8 scsi_status, + int sns_len, u8 *sns_info, s32 residue) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + struct bfad_s *bfad = drv; + struct bfad_itnim_data_s *itnim_data; + struct bfad_itnim_s *itnim; + + switch (io_status) { + case BFI_IOIM_STS_OK: + bfa_trc(bfad, scsi_status); + cmnd->result = ScsiResult(DID_OK, scsi_status); + scsi_set_resid(cmnd, 0); + + if (sns_len > 0) { + bfa_trc(bfad, sns_len); + if (sns_len > SCSI_SENSE_BUFFERSIZE) + sns_len = SCSI_SENSE_BUFFERSIZE; + memcpy(cmnd->sense_buffer, sns_info, sns_len); + } + if (residue > 0) + scsi_set_resid(cmnd, residue); + break; + + case BFI_IOIM_STS_ABORTED: + case BFI_IOIM_STS_TIMEDOUT: + case BFI_IOIM_STS_PATHTOV: + default: + cmnd->result = ScsiResult(DID_ERROR, 0); + } + + /* Unmap DMA, if host is NULL, it means a scsi passthru cmd */ + if (cmnd->device->host != NULL) + scsi_dma_unmap(cmnd); + + cmnd->host_scribble = NULL; + bfa_trc(bfad, cmnd->result); + + itnim_data = cmnd->device->hostdata; + if (itnim_data) { + itnim = itnim_data->itnim; + if (!cmnd->result && itnim && + (bfa_lun_queue_depth > cmnd->device->queue_depth)) { + /* Queue depth adjustment for good status completion */ + bfad_os_ramp_up_qdepth(itnim, cmnd->device); + } else if (cmnd->result == SAM_STAT_TASK_SET_FULL && itnim) { + /* qfull handling */ + bfad_os_handle_qfull(itnim, cmnd->device); + } + } + + cmnd->scsi_done(cmnd); +} + +void +bfa_cb_ioim_good_comp(void *drv, struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + struct bfad_itnim_data_s *itnim_data; + struct bfad_itnim_s *itnim; + + cmnd->result = ScsiResult(DID_OK, SCSI_STATUS_GOOD); + + /* Unmap DMA, if host is NULL, it means a scsi passthru cmd */ + if (cmnd->device->host != NULL) + scsi_dma_unmap(cmnd); + + cmnd->host_scribble = NULL; + + /* Queue depth adjustment */ + if (bfa_lun_queue_depth > cmnd->device->queue_depth) { + itnim_data = cmnd->device->hostdata; + if (itnim_data) { + itnim = itnim_data->itnim; + if (itnim) + bfad_os_ramp_up_qdepth(itnim, cmnd->device); + } + } + + cmnd->scsi_done(cmnd); +} + +void +bfa_cb_ioim_abort(void *drv, struct bfad_ioim_s *dio) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dio; + struct bfad_s *bfad = drv; + + cmnd->result = ScsiResult(DID_ERROR, 0); + + /* Unmap DMA, if host is NULL, it means a scsi passthru cmd */ + if (cmnd->device->host != NULL) + scsi_dma_unmap(cmnd); + + bfa_trc(bfad, cmnd->result); + cmnd->host_scribble = NULL; +} + +void +bfa_cb_tskim_done(void *bfad, struct bfad_tskim_s *dtsk, + enum bfi_tskim_status tsk_status) +{ + struct scsi_cmnd *cmnd = (struct scsi_cmnd *)dtsk; + wait_queue_head_t *wq; + + cmnd->SCp.Status |= tsk_status << 1; + set_bit(IO_DONE_BIT, (unsigned long *)&cmnd->SCp.Status); + wq = (wait_queue_head_t *) cmnd->SCp.ptr; + cmnd->SCp.ptr = NULL; + + if (wq) + wake_up(wq); +} + +void +bfa_cb_ioim_resfree(void *drv) +{ +} + +/** + * Scsi_Host_template SCSI host template + */ +/** + * Scsi_Host template entry, returns BFAD PCI info. + */ +static const char * +bfad_im_info(struct Scsi_Host *shost) +{ + static char bfa_buf[256]; + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfa_ioc_attr_s ioc_attr; + struct bfad_s *bfad = im_port->bfad; + + memset(&ioc_attr, 0, sizeof(ioc_attr)); + bfa_get_attr(&bfad->bfa, &ioc_attr); + + memset(bfa_buf, 0, sizeof(bfa_buf)); + snprintf(bfa_buf, sizeof(bfa_buf), + "Brocade FC/FCOE Adapter, " "model: %s hwpath: %s driver: %s", + ioc_attr.adapter_attr.model, bfad->pci_name, + BFAD_DRIVER_VERSION); + return bfa_buf; +} + +/** + * Scsi_Host template entry, aborts the specified SCSI command. + * + * Returns: SUCCESS or FAILED. + */ +static int +bfad_im_abort_handler(struct scsi_cmnd *cmnd) +{ + struct Scsi_Host *shost = cmnd->device->host; + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfa_ioim_s *hal_io; + unsigned long flags; + u32 timeout; + int rc = FAILED; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + hal_io = (struct bfa_ioim_s *) cmnd->host_scribble; + if (!hal_io) { + /* IO has been completed, retrun success */ + rc = SUCCESS; + goto out; + } + if (hal_io->dio != (struct bfad_ioim_s *) cmnd) { + rc = FAILED; + goto out; + } + + bfa_trc(bfad, hal_io->iotag); + bfa_log(bfad->logmod, BFA_LOG_LINUX_SCSI_ABORT, + im_port->shost->host_no, cmnd, hal_io->iotag); + bfa_ioim_abort(hal_io); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + /* Need to wait until the command get aborted */ + timeout = 10; + while ((struct bfa_ioim_s *) cmnd->host_scribble == hal_io) { + set_current_state(TASK_UNINTERRUPTIBLE); + schedule_timeout(timeout); + if (timeout < 4 * HZ) + timeout *= 2; + } + + cmnd->scsi_done(cmnd); + bfa_trc(bfad, hal_io->iotag); + bfa_log(bfad->logmod, BFA_LOG_LINUX_SCSI_ABORT_COMP, + im_port->shost->host_no, cmnd, hal_io->iotag); + return SUCCESS; +out: + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + return rc; +} + +static bfa_status_t +bfad_im_target_reset_send(struct bfad_s *bfad, struct scsi_cmnd *cmnd, + struct bfad_itnim_s *itnim) +{ + struct bfa_tskim_s *tskim; + struct bfa_itnim_s *bfa_itnim; + bfa_status_t rc = BFA_STATUS_OK; + + bfa_itnim = bfa_fcs_itnim_get_halitn(&itnim->fcs_itnim); + tskim = bfa_tskim_alloc(&bfad->bfa, (struct bfad_tskim_s *) cmnd); + if (!tskim) { + BFA_DEV_PRINTF(bfad, BFA_ERR, + "target reset, fail to allocate tskim\n"); + rc = BFA_STATUS_FAILED; + goto out; + } + + /* + * Set host_scribble to NULL to avoid aborting a task command if + * happens. + */ + cmnd->host_scribble = NULL; + cmnd->SCp.Status = 0; + bfa_itnim = bfa_fcs_itnim_get_halitn(&itnim->fcs_itnim); + bfa_tskim_start(tskim, bfa_itnim, (lun_t)0, + FCP_TM_TARGET_RESET, BFAD_TARGET_RESET_TMO); +out: + return rc; +} + +/** + * Scsi_Host template entry, resets a LUN and abort its all commands. + * + * Returns: SUCCESS or FAILED. + * + */ +static int +bfad_im_reset_lun_handler(struct scsi_cmnd *cmnd) +{ + struct Scsi_Host *shost = cmnd->device->host; + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_itnim_data_s *itnim_data = cmnd->device->hostdata; + struct bfad_s *bfad = im_port->bfad; + struct bfa_tskim_s *tskim; + struct bfad_itnim_s *itnim; + struct bfa_itnim_s *bfa_itnim; + DECLARE_WAIT_QUEUE_HEAD(wq); + int rc = SUCCESS; + unsigned long flags; + enum bfi_tskim_status task_status; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + itnim = itnim_data->itnim; + if (!itnim) { + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + rc = FAILED; + goto out; + } + + tskim = bfa_tskim_alloc(&bfad->bfa, (struct bfad_tskim_s *) cmnd); + if (!tskim) { + BFA_DEV_PRINTF(bfad, BFA_ERR, + "LUN reset, fail to allocate tskim"); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + rc = FAILED; + goto out; + } + + /** + * Set host_scribble to NULL to avoid aborting a task command + * if happens. + */ + cmnd->host_scribble = NULL; + cmnd->SCp.ptr = (char *)&wq; + cmnd->SCp.Status = 0; + bfa_itnim = bfa_fcs_itnim_get_halitn(&itnim->fcs_itnim); + bfa_tskim_start(tskim, bfa_itnim, + bfad_int_to_lun(cmnd->device->lun), + FCP_TM_LUN_RESET, BFAD_LUN_RESET_TMO); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + wait_event(wq, test_bit(IO_DONE_BIT, + (unsigned long *)&cmnd->SCp.Status)); + + task_status = cmnd->SCp.Status >> 1; + if (task_status != BFI_TSKIM_STS_OK) { + BFA_DEV_PRINTF(bfad, BFA_ERR, "LUN reset failure, status: %d\n", + task_status); + rc = FAILED; + } + +out: + return rc; +} + +/** + * Scsi_Host template entry, resets the bus and abort all commands. + */ +static int +bfad_im_reset_bus_handler(struct scsi_cmnd *cmnd) +{ + struct Scsi_Host *shost = cmnd->device->host; + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) shost->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfad_itnim_s *itnim; + unsigned long flags; + u32 i, rc, err_cnt = 0; + DECLARE_WAIT_QUEUE_HEAD(wq); + enum bfi_tskim_status task_status; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + for (i = 0; i < MAX_FCP_TARGET; i++) { + itnim = bfad_os_get_itnim(im_port, i); + if (itnim) { + cmnd->SCp.ptr = (char *)&wq; + rc = bfad_im_target_reset_send(bfad, cmnd, itnim); + if (rc != BFA_STATUS_OK) { + err_cnt++; + continue; + } + + /* wait target reset to complete */ + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + wait_event(wq, test_bit(IO_DONE_BIT, + (unsigned long *)&cmnd->SCp.Status)); + spin_lock_irqsave(&bfad->bfad_lock, flags); + + task_status = cmnd->SCp.Status >> 1; + if (task_status != BFI_TSKIM_STS_OK) { + BFA_DEV_PRINTF(bfad, BFA_ERR, + "target reset failure," + " status: %d\n", task_status); + err_cnt++; + } + } + } + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + if (err_cnt) + return FAILED; + + return SUCCESS; +} + +/** + * Scsi_Host template entry slave_destroy. + */ +static void +bfad_im_slave_destroy(struct scsi_device *sdev) +{ + sdev->hostdata = NULL; + return; +} + +/** + * BFA FCS itnim callbacks + */ + +/** + * BFA FCS itnim alloc callback, after successful PRLI + * Context: Interrupt + */ +void +bfa_fcb_itnim_alloc(struct bfad_s *bfad, struct bfa_fcs_itnim_s **itnim, + struct bfad_itnim_s **itnim_drv) +{ + *itnim_drv = kzalloc(sizeof(struct bfad_itnim_s), GFP_ATOMIC); + if (*itnim_drv == NULL) + return; + + (*itnim_drv)->im = bfad->im; + *itnim = &(*itnim_drv)->fcs_itnim; + (*itnim_drv)->state = ITNIM_STATE_NONE; + + /* + * Initiaze the itnim_work + */ + INIT_WORK(&(*itnim_drv)->itnim_work, bfad_im_itnim_work_handler); + bfad->bfad_flags |= BFAD_RPORT_ONLINE; +} + +/** + * BFA FCS itnim free callback. + * Context: Interrupt. bfad_lock is held + */ +void +bfa_fcb_itnim_free(struct bfad_s *bfad, struct bfad_itnim_s *itnim_drv) +{ + struct bfad_port_s *port; + wwn_t wwpn; + u32 fcid; + char wwpn_str[32], fcid_str[16]; + + /* online to free state transtion should not happen */ + bfa_assert(itnim_drv->state != ITNIM_STATE_ONLINE); + + itnim_drv->queue_work = 1; + /* offline request is not yet done, use the same request to free */ + if (itnim_drv->state == ITNIM_STATE_OFFLINE_PENDING) + itnim_drv->queue_work = 0; + + itnim_drv->state = ITNIM_STATE_FREE; + port = bfa_fcs_itnim_get_drvport(&itnim_drv->fcs_itnim); + itnim_drv->im_port = port->im_port; + wwpn = bfa_fcs_itnim_get_pwwn(&itnim_drv->fcs_itnim); + fcid = bfa_fcs_itnim_get_fcid(&itnim_drv->fcs_itnim); + wwn2str(wwpn_str, wwpn); + fcid2str(fcid_str, fcid); + bfa_log(bfad->logmod, BFA_LOG_LINUX_ITNIM_FREE, + port->im_port->shost->host_no, + fcid_str, wwpn_str); + bfad_os_itnim_process(itnim_drv); +} + +/** + * BFA FCS itnim online callback. + * Context: Interrupt. bfad_lock is held + */ +void +bfa_fcb_itnim_online(struct bfad_itnim_s *itnim_drv) +{ + struct bfad_port_s *port; + + itnim_drv->bfa_itnim = bfa_fcs_itnim_get_halitn(&itnim_drv->fcs_itnim); + port = bfa_fcs_itnim_get_drvport(&itnim_drv->fcs_itnim); + itnim_drv->state = ITNIM_STATE_ONLINE; + itnim_drv->queue_work = 1; + itnim_drv->im_port = port->im_port; + bfad_os_itnim_process(itnim_drv); +} + +/** + * BFA FCS itnim offline callback. + * Context: Interrupt. bfad_lock is held + */ +void +bfa_fcb_itnim_offline(struct bfad_itnim_s *itnim_drv) +{ + struct bfad_port_s *port; + struct bfad_s *bfad; + + port = bfa_fcs_itnim_get_drvport(&itnim_drv->fcs_itnim); + bfad = port->bfad; + if ((bfad->pport.flags & BFAD_PORT_DELETE) || + (port->flags & BFAD_PORT_DELETE)) { + itnim_drv->state = ITNIM_STATE_OFFLINE; + return; + } + itnim_drv->im_port = port->im_port; + itnim_drv->state = ITNIM_STATE_OFFLINE_PENDING; + itnim_drv->queue_work = 1; + bfad_os_itnim_process(itnim_drv); +} + +/** + * BFA FCS itnim timeout callback. + * Context: Interrupt. bfad_lock is held + */ +void bfa_fcb_itnim_tov(struct bfad_itnim_s *itnim) +{ + itnim->state = ITNIM_STATE_TIMEOUT; +} + +/** + * Path TOV processing begin notification -- dummy for linux + */ +void +bfa_fcb_itnim_tov_begin(struct bfad_itnim_s *itnim) +{ +} + + + +/** + * Allocate a Scsi_Host for a port. + */ +int +bfad_im_scsi_host_alloc(struct bfad_s *bfad, struct bfad_im_port_s *im_port) +{ + int error = 1; + + if (!idr_pre_get(&bfad_im_port_index, GFP_KERNEL)) { + printk(KERN_WARNING "idr_pre_get failure\n"); + goto out; + } + + error = idr_get_new(&bfad_im_port_index, im_port, + &im_port->idr_id); + if (error) { + printk(KERN_WARNING "idr_get_new failure\n"); + goto out; + } + + im_port->shost = bfad_os_scsi_host_alloc(im_port, bfad); + if (!im_port->shost) { + error = 1; + goto out_free_idr; + } + + im_port->shost->hostdata[0] = (unsigned long)im_port; + im_port->shost->unique_id = im_port->idr_id; + im_port->shost->this_id = -1; + im_port->shost->max_id = MAX_FCP_TARGET; + im_port->shost->max_lun = MAX_FCP_LUN; + im_port->shost->max_cmd_len = 16; + im_port->shost->can_queue = bfad->cfg_data.ioc_queue_depth; + im_port->shost->transportt = bfad_im_scsi_transport_template; + + error = bfad_os_scsi_add_host(im_port->shost, im_port, bfad); + if (error) { + printk(KERN_WARNING "bfad_os_scsi_add_host failure %d\n", + error); + goto out_fc_rel; + } + + /* setup host fixed attribute if the lk supports */ + bfad_os_fc_host_init(im_port); + + return 0; + +out_fc_rel: + scsi_host_put(im_port->shost); +out_free_idr: + idr_remove(&bfad_im_port_index, im_port->idr_id); +out: + return error; +} + +void +bfad_im_scsi_host_free(struct bfad_s *bfad, struct bfad_im_port_s *im_port) +{ + unsigned long flags; + + bfa_trc(bfad, bfad->inst_no); + bfa_log(bfad->logmod, BFA_LOG_LINUX_SCSI_HOST_FREE, + im_port->shost->host_no); + + fc_remove_host(im_port->shost); + + scsi_remove_host(im_port->shost); + scsi_host_put(im_port->shost); + + spin_lock_irqsave(&bfad->bfad_lock, flags); + idr_remove(&bfad_im_port_index, im_port->idr_id); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); +} + +static void +bfad_im_port_delete_handler(struct work_struct *work) +{ + struct bfad_im_port_s *im_port = + container_of(work, struct bfad_im_port_s, port_delete_work); + + bfad_im_scsi_host_free(im_port->bfad, im_port); + bfad_im_port_clean(im_port); + kfree(im_port); +} + +bfa_status_t +bfad_im_port_new(struct bfad_s *bfad, struct bfad_port_s *port) +{ + int rc = BFA_STATUS_OK; + struct bfad_im_port_s *im_port; + + im_port = kzalloc(sizeof(struct bfad_im_port_s), GFP_ATOMIC); + if (im_port == NULL) { + rc = BFA_STATUS_ENOMEM; + goto ext; + } + port->im_port = im_port; + im_port->port = port; + im_port->bfad = bfad; + + INIT_WORK(&im_port->port_delete_work, bfad_im_port_delete_handler); + INIT_LIST_HEAD(&im_port->itnim_mapped_list); + INIT_LIST_HEAD(&im_port->binding_list); + +ext: + return rc; +} + +void +bfad_im_port_delete(struct bfad_s *bfad, struct bfad_port_s *port) +{ + struct bfad_im_port_s *im_port = port->im_port; + + queue_work(bfad->im->drv_workq, + &im_port->port_delete_work); +} + +void +bfad_im_port_clean(struct bfad_im_port_s *im_port) +{ + struct bfad_fcp_binding *bp, *bp_new; + unsigned long flags; + struct bfad_s *bfad = im_port->bfad; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + list_for_each_entry_safe(bp, bp_new, &im_port->binding_list, + list_entry) { + list_del(&bp->list_entry); + kfree(bp); + } + + /* the itnim_mapped_list must be empty at this time */ + bfa_assert(list_empty(&im_port->itnim_mapped_list)); + + spin_unlock_irqrestore(&bfad->bfad_lock, flags); +} + +void +bfad_im_port_online(struct bfad_s *bfad, struct bfad_port_s *port) +{ +} + +void +bfad_im_port_offline(struct bfad_s *bfad, struct bfad_port_s *port) +{ +} + +bfa_status_t +bfad_im_probe(struct bfad_s *bfad) +{ + struct bfad_im_s *im; + bfa_status_t rc = BFA_STATUS_OK; + + im = kzalloc(sizeof(struct bfad_im_s), GFP_KERNEL); + if (im == NULL) { + rc = BFA_STATUS_ENOMEM; + goto ext; + } + + bfad->im = im; + im->bfad = bfad; + + if (bfad_os_thread_workq(bfad) != BFA_STATUS_OK) { + kfree(im); + rc = BFA_STATUS_FAILED; + } + +ext: + return rc; +} + +void +bfad_im_probe_undo(struct bfad_s *bfad) +{ + if (bfad->im) { + bfad_os_destroy_workq(bfad->im); + kfree(bfad->im); + bfad->im = NULL; + } +} + + + + +int +bfad_os_scsi_add_host(struct Scsi_Host *shost, struct bfad_im_port_s *im_port, + struct bfad_s *bfad) +{ + struct device *dev; + + if (im_port->port->pvb_type == BFAD_PORT_PHYS_BASE) + dev = &bfad->pcidev->dev; + else + dev = &bfad->pport.im_port->shost->shost_gendev; + + return scsi_add_host(shost, dev); +} + +struct Scsi_Host * +bfad_os_scsi_host_alloc(struct bfad_im_port_s *im_port, struct bfad_s *bfad) +{ + struct scsi_host_template *sht; + + if (im_port->port->pvb_type == BFAD_PORT_PHYS_BASE) + sht = &bfad_im_scsi_host_template; + else + sht = &bfad_im_vport_template; + + sht->sg_tablesize = bfad->cfg_data.io_max_sge; + + return scsi_host_alloc(sht, sizeof(unsigned long)); +} + +void +bfad_os_scsi_host_free(struct bfad_s *bfad, struct bfad_im_port_s *im_port) +{ + flush_workqueue(bfad->im->drv_workq); + bfad_im_scsi_host_free(im_port->bfad, im_port); + bfad_im_port_clean(im_port); + kfree(im_port); +} + +void +bfad_os_destroy_workq(struct bfad_im_s *im) +{ + if (im && im->drv_workq) { + destroy_workqueue(im->drv_workq); + im->drv_workq = NULL; + } +} + +bfa_status_t +bfad_os_thread_workq(struct bfad_s *bfad) +{ + struct bfad_im_s *im = bfad->im; + + bfa_trc(bfad, 0); + snprintf(im->drv_workq_name, BFAD_KOBJ_NAME_LEN, "bfad_wq_%d", + bfad->inst_no); + im->drv_workq = create_singlethread_workqueue(im->drv_workq_name); + if (!im->drv_workq) + return BFA_STATUS_FAILED; + + return BFA_STATUS_OK; +} + +/** + * Scsi_Host template entry. + * + * Description: + * OS entry point to adjust the queue_depths on a per-device basis. + * Called once per device during the bus scan. + * Return non-zero if fails. + */ +static int +bfad_im_slave_configure(struct scsi_device *sdev) +{ + if (sdev->tagged_supported) + scsi_activate_tcq(sdev, bfa_lun_queue_depth); + else + scsi_deactivate_tcq(sdev, bfa_lun_queue_depth); + + return 0; +} + +struct scsi_host_template bfad_im_scsi_host_template = { + .module = THIS_MODULE, + .name = BFAD_DRIVER_NAME, + .info = bfad_im_info, + .queuecommand = bfad_im_queuecommand, + .eh_abort_handler = bfad_im_abort_handler, + .eh_device_reset_handler = bfad_im_reset_lun_handler, + .eh_bus_reset_handler = bfad_im_reset_bus_handler, + + .slave_alloc = bfad_im_slave_alloc, + .slave_configure = bfad_im_slave_configure, + .slave_destroy = bfad_im_slave_destroy, + + .this_id = -1, + .sg_tablesize = BFAD_IO_MAX_SGE, + .cmd_per_lun = 3, + .use_clustering = ENABLE_CLUSTERING, + .shost_attrs = bfad_im_host_attrs, + .max_sectors = 0xFFFF, +}; + +struct scsi_host_template bfad_im_vport_template = { + .module = THIS_MODULE, + .name = BFAD_DRIVER_NAME, + .info = bfad_im_info, + .queuecommand = bfad_im_queuecommand, + .eh_abort_handler = bfad_im_abort_handler, + .eh_device_reset_handler = bfad_im_reset_lun_handler, + .eh_bus_reset_handler = bfad_im_reset_bus_handler, + + .slave_alloc = bfad_im_slave_alloc, + .slave_configure = bfad_im_slave_configure, + .slave_destroy = bfad_im_slave_destroy, + + .this_id = -1, + .sg_tablesize = BFAD_IO_MAX_SGE, + .cmd_per_lun = 3, + .use_clustering = ENABLE_CLUSTERING, + .shost_attrs = bfad_im_vport_attrs, + .max_sectors = 0xFFFF, +}; + +void +bfad_im_probe_post(struct bfad_im_s *im) +{ + flush_workqueue(im->drv_workq); +} + +bfa_status_t +bfad_im_module_init(void) +{ + bfad_im_scsi_transport_template = + fc_attach_transport(&bfad_im_fc_function_template); + if (!bfad_im_scsi_transport_template) + return BFA_STATUS_ENOMEM; + + return BFA_STATUS_OK; +} + +void +bfad_im_module_exit(void) +{ + if (bfad_im_scsi_transport_template) + fc_release_transport(bfad_im_scsi_transport_template); +} + +void +bfad_os_itnim_process(struct bfad_itnim_s *itnim_drv) +{ + struct bfad_im_s *im = itnim_drv->im; + + if (itnim_drv->queue_work) + queue_work(im->drv_workq, &itnim_drv->itnim_work); +} + +void +bfad_os_ramp_up_qdepth(struct bfad_itnim_s *itnim, struct scsi_device *sdev) +{ + struct scsi_device *tmp_sdev; + + if (((jiffies - itnim->last_ramp_up_time) > + BFA_QUEUE_FULL_RAMP_UP_TIME * HZ) && + ((jiffies - itnim->last_queue_full_time) > + BFA_QUEUE_FULL_RAMP_UP_TIME * HZ)) { + shost_for_each_device(tmp_sdev, sdev->host) { + if (bfa_lun_queue_depth > tmp_sdev->queue_depth) { + if (tmp_sdev->id != sdev->id) + continue; + if (tmp_sdev->ordered_tags) + scsi_adjust_queue_depth(tmp_sdev, + MSG_ORDERED_TAG, + tmp_sdev->queue_depth + 1); + else + scsi_adjust_queue_depth(tmp_sdev, + MSG_SIMPLE_TAG, + tmp_sdev->queue_depth + 1); + + itnim->last_ramp_up_time = jiffies; + } + } + } +} + +void +bfad_os_handle_qfull(struct bfad_itnim_s *itnim, struct scsi_device *sdev) +{ + struct scsi_device *tmp_sdev; + + itnim->last_queue_full_time = jiffies; + + shost_for_each_device(tmp_sdev, sdev->host) { + if (tmp_sdev->id != sdev->id) + continue; + scsi_track_queue_full(tmp_sdev, tmp_sdev->queue_depth - 1); + } +} + + + + +struct bfad_itnim_s * +bfad_os_get_itnim(struct bfad_im_port_s *im_port, int id) +{ + struct bfad_itnim_s *itnim = NULL; + + /* Search the mapped list for this target ID */ + list_for_each_entry(itnim, &im_port->itnim_mapped_list, list_entry) { + if (id == itnim->scsi_tgt_id) + return itnim; + } + + return NULL; +} + +/** + * Scsi_Host template entry slave_alloc + */ +static int +bfad_im_slave_alloc(struct scsi_device *sdev) +{ + struct fc_rport *rport = starget_to_rport(scsi_target(sdev)); + + if (!rport || fc_remote_port_chkready(rport)) + return -ENXIO; + + sdev->hostdata = rport->dd_data; + + return 0; +} + +void +bfad_os_fc_host_init(struct bfad_im_port_s *im_port) +{ + struct Scsi_Host *host = im_port->shost; + struct bfad_s *bfad = im_port->bfad; + struct bfad_port_s *port = im_port->port; + union attr { + struct bfa_pport_attr_s pattr; + struct bfa_ioc_attr_s ioc_attr; + } attr; + + fc_host_node_name(host) = + bfa_os_htonll((bfa_fcs_port_get_nwwn(port->fcs_port))); + fc_host_port_name(host) = + bfa_os_htonll((bfa_fcs_port_get_pwwn(port->fcs_port))); + + fc_host_supported_classes(host) = FC_COS_CLASS3; + + memset(fc_host_supported_fc4s(host), 0, + sizeof(fc_host_supported_fc4s(host))); + if (bfad_supported_fc4s & (BFA_PORT_ROLE_FCP_IM | BFA_PORT_ROLE_FCP_TM)) + /* For FCP type 0x08 */ + fc_host_supported_fc4s(host)[2] = 1; + if (bfad_supported_fc4s & BFA_PORT_ROLE_FCP_IPFC) + /* For LLC/SNAP type 0x05 */ + fc_host_supported_fc4s(host)[3] = 0x20; + /* For fibre channel services type 0x20 */ + fc_host_supported_fc4s(host)[7] = 1; + + memset(&attr.ioc_attr, 0, sizeof(attr.ioc_attr)); + bfa_get_attr(&bfad->bfa, &attr.ioc_attr); + sprintf(fc_host_symbolic_name(host), "Brocade %s FV%s DV%s", + attr.ioc_attr.adapter_attr.model, + attr.ioc_attr.adapter_attr.fw_ver, BFAD_DRIVER_VERSION); + + fc_host_supported_speeds(host) = 0; + fc_host_supported_speeds(host) |= + FC_PORTSPEED_8GBIT | FC_PORTSPEED_4GBIT | FC_PORTSPEED_2GBIT | + FC_PORTSPEED_1GBIT; + + memset(&attr.pattr, 0, sizeof(attr.pattr)); + bfa_pport_get_attr(&bfad->bfa, &attr.pattr); + fc_host_maxframe_size(host) = attr.pattr.pport_cfg.maxfrsize; +} + +static void +bfad_im_fc_rport_add(struct bfad_im_port_s *im_port, struct bfad_itnim_s *itnim) +{ + struct fc_rport_identifiers rport_ids; + struct fc_rport *fc_rport; + struct bfad_itnim_data_s *itnim_data; + + rport_ids.node_name = + bfa_os_htonll(bfa_fcs_itnim_get_nwwn(&itnim->fcs_itnim)); + rport_ids.port_name = + bfa_os_htonll(bfa_fcs_itnim_get_pwwn(&itnim->fcs_itnim)); + rport_ids.port_id = + bfa_os_hton3b(bfa_fcs_itnim_get_fcid(&itnim->fcs_itnim)); + rport_ids.roles = FC_RPORT_ROLE_UNKNOWN; + + itnim->fc_rport = fc_rport = + fc_remote_port_add(im_port->shost, 0, &rport_ids); + + if (!fc_rport) + return; + + fc_rport->maxframe_size = + bfa_fcs_itnim_get_maxfrsize(&itnim->fcs_itnim); + fc_rport->supported_classes = bfa_fcs_itnim_get_cos(&itnim->fcs_itnim); + + itnim_data = fc_rport->dd_data; + itnim_data->itnim = itnim; + + rport_ids.roles |= FC_RPORT_ROLE_FCP_TARGET; + + if (rport_ids.roles != FC_RPORT_ROLE_UNKNOWN) + fc_remote_port_rolechg(fc_rport, rport_ids.roles); + + if ((fc_rport->scsi_target_id != -1) + && (fc_rport->scsi_target_id < MAX_FCP_TARGET)) + itnim->scsi_tgt_id = fc_rport->scsi_target_id; + + return; +} + +/** + * Work queue handler using FC transport service +* Context: kernel + */ +static void +bfad_im_itnim_work_handler(struct work_struct *work) +{ + struct bfad_itnim_s *itnim = container_of(work, struct bfad_itnim_s, + itnim_work); + struct bfad_im_s *im = itnim->im; + struct bfad_s *bfad = im->bfad; + struct bfad_im_port_s *im_port; + unsigned long flags; + struct fc_rport *fc_rport; + wwn_t wwpn; + u32 fcid; + char wwpn_str[32], fcid_str[16]; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + im_port = itnim->im_port; + bfa_trc(bfad, itnim->state); + switch (itnim->state) { + case ITNIM_STATE_ONLINE: + if (!itnim->fc_rport) { + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + bfad_im_fc_rport_add(im_port, itnim); + spin_lock_irqsave(&bfad->bfad_lock, flags); + wwpn = bfa_fcs_itnim_get_pwwn(&itnim->fcs_itnim); + fcid = bfa_fcs_itnim_get_fcid(&itnim->fcs_itnim); + wwn2str(wwpn_str, wwpn); + fcid2str(fcid_str, fcid); + list_add_tail(&itnim->list_entry, + &im_port->itnim_mapped_list); + bfa_log(bfad->logmod, BFA_LOG_LINUX_ITNIM_ONLINE, + im_port->shost->host_no, + itnim->scsi_tgt_id, + fcid_str, wwpn_str); + } else { + printk(KERN_WARNING + "%s: itnim %llx is already in online state\n", + __FUNCTION__, + bfa_fcs_itnim_get_pwwn(&itnim->fcs_itnim)); + } + + break; + case ITNIM_STATE_OFFLINE_PENDING: + itnim->state = ITNIM_STATE_OFFLINE; + if (itnim->fc_rport) { + fc_rport = itnim->fc_rport; + ((struct bfad_itnim_data_s *) + fc_rport->dd_data)->itnim = NULL; + itnim->fc_rport = NULL; + if (!(im_port->port->flags & BFAD_PORT_DELETE)) { + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + fc_rport->dev_loss_tmo = + bfa_fcpim_path_tov_get(&bfad->bfa) + 1; + fc_remote_port_delete(fc_rport); + spin_lock_irqsave(&bfad->bfad_lock, flags); + } + wwpn = bfa_fcs_itnim_get_pwwn(&itnim->fcs_itnim); + fcid = bfa_fcs_itnim_get_fcid(&itnim->fcs_itnim); + wwn2str(wwpn_str, wwpn); + fcid2str(fcid_str, fcid); + list_del(&itnim->list_entry); + bfa_log(bfad->logmod, BFA_LOG_LINUX_ITNIM_OFFLINE, + im_port->shost->host_no, + itnim->scsi_tgt_id, + fcid_str, wwpn_str); + } + break; + case ITNIM_STATE_FREE: + if (itnim->fc_rport) { + fc_rport = itnim->fc_rport; + ((struct bfad_itnim_data_s *) + fc_rport->dd_data)->itnim = NULL; + itnim->fc_rport = NULL; + if (!(im_port->port->flags & BFAD_PORT_DELETE)) { + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + fc_rport->dev_loss_tmo = + bfa_fcpim_path_tov_get(&bfad->bfa) + 1; + fc_remote_port_delete(fc_rport); + spin_lock_irqsave(&bfad->bfad_lock, flags); + } + list_del(&itnim->list_entry); + } + + kfree(itnim); + break; + default: + bfa_assert(0); + break; + } + + spin_unlock_irqrestore(&bfad->bfad_lock, flags); +} + +/** + * Scsi_Host template entry, queue a SCSI command to the BFAD. + */ +static int +bfad_im_queuecommand(struct scsi_cmnd *cmnd, void (*done) (struct scsi_cmnd *)) +{ + struct bfad_im_port_s *im_port = + (struct bfad_im_port_s *) cmnd->device->host->hostdata[0]; + struct bfad_s *bfad = im_port->bfad; + struct bfad_itnim_data_s *itnim_data = cmnd->device->hostdata; + struct bfad_itnim_s *itnim; + struct bfa_ioim_s *hal_io; + unsigned long flags; + int rc; + s16 sg_cnt = 0; + struct fc_rport *rport = starget_to_rport(scsi_target(cmnd->device)); + + rc = fc_remote_port_chkready(rport); + if (rc) { + cmnd->result = rc; + done(cmnd); + return 0; + } + + sg_cnt = scsi_dma_map(cmnd); + + if (sg_cnt < 0) + return SCSI_MLQUEUE_HOST_BUSY; + + cmnd->scsi_done = done; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + if (!(bfad->bfad_flags & BFAD_HAL_START_DONE)) { + printk(KERN_WARNING + "bfad%d, queuecommand %p %x failed, BFA stopped\n", + bfad->inst_no, cmnd, cmnd->cmnd[0]); + cmnd->result = ScsiResult(DID_NO_CONNECT, 0); + goto out_fail_cmd; + } + + itnim = itnim_data->itnim; + if (!itnim) { + cmnd->result = ScsiResult(DID_IMM_RETRY, 0); + goto out_fail_cmd; + } + + hal_io = bfa_ioim_alloc(&bfad->bfa, (struct bfad_ioim_s *) cmnd, + itnim->bfa_itnim, sg_cnt); + if (!hal_io) { + printk(KERN_WARNING "hal_io failure\n"); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + scsi_dma_unmap(cmnd); + return SCSI_MLQUEUE_HOST_BUSY; + } + + cmnd->host_scribble = (char *)hal_io; + bfa_trc_fp(bfad, hal_io->iotag); + bfa_ioim_start(hal_io); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + return 0; + +out_fail_cmd: + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + scsi_dma_unmap(cmnd); + if (done) + done(cmnd); + + return 0; +} + +void +bfad_os_rport_online_wait(struct bfad_s *bfad) +{ + int i; + int rport_delay = 10; + + for (i = 0; !(bfad->bfad_flags & BFAD_PORT_ONLINE) + && i < bfa_linkup_delay; i++) + schedule_timeout_uninterruptible(HZ); + + if (bfad->bfad_flags & BFAD_PORT_ONLINE) { + rport_delay = rport_delay < bfa_linkup_delay ? + rport_delay : bfa_linkup_delay; + for (i = 0; !(bfad->bfad_flags & BFAD_RPORT_ONLINE) + && i < rport_delay; i++) + schedule_timeout_uninterruptible(HZ); + + if (rport_delay > 0 && (bfad->bfad_flags & BFAD_RPORT_ONLINE)) + schedule_timeout_uninterruptible(rport_delay * HZ); + } +} + +int +bfad_os_get_linkup_delay(struct bfad_s *bfad) +{ + + u8 nwwns = 0; + wwn_t *wwns; + int ldelay; + + /* + * Querying for the boot target port wwns + * -- read from boot information in flash. + * If nwwns > 0 => boot over SAN and set bfa_linkup_delay = 30 + * else => local boot machine set bfa_linkup_delay = 10 + */ + + bfa_iocfc_get_bootwwns(&bfad->bfa, &nwwns, &wwns); + + if (nwwns > 0) { + /* If boot over SAN; linkup_delay = 30sec */ + ldelay = 30; + } else { + /* If local boot; linkup_delay = 10sec */ + ldelay = 0; + } + + return ldelay; +} + + diff --git a/drivers/scsi/bfa/bfad_im.h b/drivers/scsi/bfa/bfad_im.h new file mode 100644 index 000000000000..189a5b29e21a --- /dev/null +++ b/drivers/scsi/bfa/bfad_im.h @@ -0,0 +1,150 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFAD_IM_H__ +#define __BFAD_IM_H__ + +#include "fcs/bfa_fcs_fcpim.h" +#include "bfad_im_compat.h" + +#define FCPI_NAME " fcpim" + +void bfad_flags_set(struct bfad_s *bfad, u32 flags); +bfa_status_t bfad_im_module_init(void); +void bfad_im_module_exit(void); +bfa_status_t bfad_im_probe(struct bfad_s *bfad); +void bfad_im_probe_undo(struct bfad_s *bfad); +void bfad_im_probe_post(struct bfad_im_s *im); +bfa_status_t bfad_im_port_new(struct bfad_s *bfad, struct bfad_port_s *port); +void bfad_im_port_delete(struct bfad_s *bfad, struct bfad_port_s *port); +void bfad_im_port_online(struct bfad_s *bfad, struct bfad_port_s *port); +void bfad_im_port_offline(struct bfad_s *bfad, struct bfad_port_s *port); +void bfad_im_port_clean(struct bfad_im_port_s *im_port); +int bfad_im_scsi_host_alloc(struct bfad_s *bfad, + struct bfad_im_port_s *im_port); +void bfad_im_scsi_host_free(struct bfad_s *bfad, + struct bfad_im_port_s *im_port); + +#define MAX_FCP_TARGET 1024 +#define MAX_FCP_LUN 16384 +#define BFAD_TARGET_RESET_TMO 60 +#define BFAD_LUN_RESET_TMO 60 +#define ScsiResult(host_code, scsi_code) (((host_code) << 16) | scsi_code) +#define BFA_QUEUE_FULL_RAMP_UP_TIME 120 +#define BFAD_KOBJ_NAME_LEN 20 + +/* + * itnim flags + */ +#define ITNIM_MAPPED 0x00000001 + +#define SCSI_TASK_MGMT 0x00000001 +#define IO_DONE_BIT 0 + +struct bfad_itnim_data_s { + struct bfad_itnim_s *itnim; +}; + +struct bfad_im_port_s { + struct bfad_s *bfad; + struct bfad_port_s *port; + struct work_struct port_delete_work; + int idr_id; + u16 cur_scsi_id; + struct list_head binding_list; + struct Scsi_Host *shost; + struct list_head itnim_mapped_list; +}; + +enum bfad_itnim_state { + ITNIM_STATE_NONE, + ITNIM_STATE_ONLINE, + ITNIM_STATE_OFFLINE_PENDING, + ITNIM_STATE_OFFLINE, + ITNIM_STATE_TIMEOUT, + ITNIM_STATE_FREE, +}; + +/* + * Per itnim data structure + */ +struct bfad_itnim_s { + struct list_head list_entry; + struct bfa_fcs_itnim_s fcs_itnim; + struct work_struct itnim_work; + u32 flags; + enum bfad_itnim_state state; + struct bfad_im_s *im; + struct bfad_im_port_s *im_port; + struct bfad_rport_s *drv_rport; + struct fc_rport *fc_rport; + struct bfa_itnim_s *bfa_itnim; + u16 scsi_tgt_id; + u16 queue_work; + unsigned long last_ramp_up_time; + unsigned long last_queue_full_time; +}; + +enum bfad_binding_type { + FCP_PWWN_BINDING = 0x1, + FCP_NWWN_BINDING = 0x2, + FCP_FCID_BINDING = 0x3, +}; + +struct bfad_fcp_binding { + struct list_head list_entry; + enum bfad_binding_type binding_type; + u16 scsi_target_id; + u32 fc_id; + wwn_t nwwn; + wwn_t pwwn; +}; + +struct bfad_im_s { + struct bfad_s *bfad; + struct workqueue_struct *drv_workq; + char drv_workq_name[BFAD_KOBJ_NAME_LEN]; +}; + +struct Scsi_Host *bfad_os_scsi_host_alloc(struct bfad_im_port_s *im_port, + struct bfad_s *); +bfa_status_t bfad_os_thread_workq(struct bfad_s *bfad); +void bfad_os_destroy_workq(struct bfad_im_s *im); +void bfad_os_itnim_process(struct bfad_itnim_s *itnim_drv); +void bfad_os_fc_host_init(struct bfad_im_port_s *im_port); +void bfad_os_init_work(struct bfad_im_port_s *im_port); +void bfad_os_scsi_host_free(struct bfad_s *bfad, + struct bfad_im_port_s *im_port); +void bfad_os_ramp_up_qdepth(struct bfad_itnim_s *itnim, + struct scsi_device *sdev); +void bfad_os_handle_qfull(struct bfad_itnim_s *itnim, struct scsi_device *sdev); +struct bfad_itnim_s *bfad_os_get_itnim(struct bfad_im_port_s *im_port, int id); +int bfad_os_scsi_add_host(struct Scsi_Host *shost, + struct bfad_im_port_s *im_port, struct bfad_s *bfad); + +/* + * scsi_host_template entries + */ +void bfad_im_itnim_unmap(struct bfad_im_port_s *im_port, + struct bfad_itnim_s *itnim); + +extern struct scsi_host_template bfad_im_scsi_host_template; +extern struct scsi_host_template bfad_im_vport_template; +extern struct fc_function_template bfad_im_fc_function_template; +extern struct scsi_transport_template *bfad_im_scsi_transport_template; + +#endif diff --git a/drivers/scsi/bfa/bfad_im_compat.h b/drivers/scsi/bfa/bfad_im_compat.h new file mode 100644 index 000000000000..1d3e74ec338c --- /dev/null +++ b/drivers/scsi/bfa/bfad_im_compat.h @@ -0,0 +1,46 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFAD_IM_COMPAT_H__ +#define __BFAD_IM_COMPAT_H__ + +extern u32 *bfi_image_buf; +extern u32 bfi_image_size; + +extern struct device_attribute *bfad_im_host_attrs[]; +extern struct device_attribute *bfad_im_vport_attrs[]; + +u32 *bfad_get_firmware_buf(struct pci_dev *pdev); +u32 *bfad_read_firmware(struct pci_dev *pdev, u32 **bfi_image, + u32 *bfi_image_size, char *fw_name); + +static inline u32 * +bfad_load_fwimg(struct pci_dev *pdev) +{ + return(bfad_get_firmware_buf(pdev)); +} + +static inline void +bfad_free_fwimg(void) +{ + if (bfi_image_ct_size && bfi_image_ct) + vfree(bfi_image_ct); + if (bfi_image_cb_size && bfi_image_cb) + vfree(bfi_image_cb); +} + +#endif diff --git a/drivers/scsi/bfa/bfad_intr.c b/drivers/scsi/bfa/bfad_intr.c new file mode 100644 index 000000000000..f104e029cac9 --- /dev/null +++ b/drivers/scsi/bfa/bfad_intr.c @@ -0,0 +1,214 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include "bfad_drv.h" +#include "bfad_trcmod.h" + +BFA_TRC_FILE(LDRV, INTR); + +/** + * bfa_isr BFA driver interrupt functions + */ +irqreturn_t bfad_intx(int irq, void *dev_id); +static int msix_disable; +module_param(msix_disable, int, S_IRUGO | S_IWUSR); +/** + * Line based interrupt handler. + */ +irqreturn_t +bfad_intx(int irq, void *dev_id) +{ + struct bfad_s *bfad = dev_id; + struct list_head doneq; + unsigned long flags; + bfa_boolean_t rc; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + rc = bfa_intx(&bfad->bfa); + if (!rc) { + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + return IRQ_NONE; + } + + bfa_comp_deq(&bfad->bfa, &doneq); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + if (!list_empty(&doneq)) { + bfa_comp_process(&bfad->bfa, &doneq); + + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_comp_free(&bfad->bfa, &doneq); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + bfa_trc_fp(bfad, irq); + } + + return IRQ_HANDLED; + +} + +static irqreturn_t +bfad_msix(int irq, void *dev_id) +{ + struct bfad_msix_s *vec = dev_id; + struct bfad_s *bfad = vec->bfad; + struct list_head doneq; + unsigned long flags; + + spin_lock_irqsave(&bfad->bfad_lock, flags); + + bfa_msix(&bfad->bfa, vec->msix.entry); + bfa_comp_deq(&bfad->bfa, &doneq); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + + if (!list_empty(&doneq)) { + bfa_comp_process(&bfad->bfa, &doneq); + + spin_lock_irqsave(&bfad->bfad_lock, flags); + bfa_comp_free(&bfad->bfa, &doneq); + spin_unlock_irqrestore(&bfad->bfad_lock, flags); + } + + return IRQ_HANDLED; +} + +/** + * Initialize the MSIX entry table. + */ +static void +bfad_init_msix_entry(struct bfad_s *bfad, struct msix_entry *msix_entries, + int mask, int max_bit) +{ + int i; + int match = 0x00000001; + + for (i = 0, bfad->nvec = 0; i < MAX_MSIX_ENTRY; i++) { + if (mask & match) { + bfad->msix_tab[bfad->nvec].msix.entry = i; + bfad->msix_tab[bfad->nvec].bfad = bfad; + msix_entries[bfad->nvec].entry = i; + bfad->nvec++; + } + + match <<= 1; + } + +} + +int +bfad_install_msix_handler(struct bfad_s *bfad) +{ + int i, error = 0; + + for (i = 0; i < bfad->nvec; i++) { + error = request_irq(bfad->msix_tab[i].msix.vector, + (irq_handler_t) bfad_msix, 0, + BFAD_DRIVER_NAME, &bfad->msix_tab[i]); + bfa_trc(bfad, i); + bfa_trc(bfad, bfad->msix_tab[i].msix.vector); + if (error) { + int j; + + for (j = 0; j < i; j++) + free_irq(bfad->msix_tab[j].msix.vector, + &bfad->msix_tab[j]); + + return 1; + } + } + + return 0; +} + +/** + * Setup MSIX based interrupt. + */ +int +bfad_setup_intr(struct bfad_s *bfad) +{ + int error = 0; + u32 mask = 0, i, num_bit = 0, max_bit = 0; + struct msix_entry msix_entries[MAX_MSIX_ENTRY]; + + /* Call BFA to get the msix map for this PCI function. */ + bfa_msix_getvecs(&bfad->bfa, &mask, &num_bit, &max_bit); + + /* Set up the msix entry table */ + bfad_init_msix_entry(bfad, msix_entries, mask, max_bit); + + if (!msix_disable) { + error = pci_enable_msix(bfad->pcidev, msix_entries, bfad->nvec); + if (error) { + /* + * Only error number of vector is available. + * We don't have a mechanism to map multiple + * interrupts into one vector, so even if we + * can try to request less vectors, we don't + * know how to associate interrupt events to + * vectors. Linux doesn't dupicate vectors + * in the MSIX table for this case. + */ + + printk(KERN_WARNING "bfad%d: " + "pci_enable_msix failed (%d)," + " use line based.\n", bfad->inst_no, error); + + goto line_based; + } + + /* Save the vectors */ + for (i = 0; i < bfad->nvec; i++) { + bfa_trc(bfad, msix_entries[i].vector); + bfad->msix_tab[i].msix.vector = msix_entries[i].vector; + } + + bfa_msix_init(&bfad->bfa, bfad->nvec); + + bfad->bfad_flags |= BFAD_MSIX_ON; + + return error; + } + +line_based: + error = 0; + if (request_irq + (bfad->pcidev->irq, (irq_handler_t) bfad_intx, BFAD_IRQ_FLAGS, + BFAD_DRIVER_NAME, bfad) != 0) { + /* Enable interrupt handler failed */ + return 1; + } + + return error; +} + +void +bfad_remove_intr(struct bfad_s *bfad) +{ + int i; + + if (bfad->bfad_flags & BFAD_MSIX_ON) { + for (i = 0; i < bfad->nvec; i++) + free_irq(bfad->msix_tab[i].msix.vector, + &bfad->msix_tab[i]); + + pci_disable_msix(bfad->pcidev); + bfad->bfad_flags &= ~BFAD_MSIX_ON; + } else { + free_irq(bfad->pcidev->irq, bfad); + } +} + + diff --git a/drivers/scsi/bfa/bfad_ipfc.h b/drivers/scsi/bfa/bfad_ipfc.h new file mode 100644 index 000000000000..718bc5227671 --- /dev/null +++ b/drivers/scsi/bfa/bfad_ipfc.h @@ -0,0 +1,42 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DRV_IPFC_H__ +#define __BFA_DRV_IPFC_H__ + + +#define IPFC_NAME "" + +#define bfad_ipfc_module_init(x) do {} while (0) +#define bfad_ipfc_module_exit(x) do {} while (0) +#define bfad_ipfc_probe(x) do {} while (0) +#define bfad_ipfc_probe_undo(x) do {} while (0) +#define bfad_ipfc_port_config(x, y) BFA_STATUS_OK +#define bfad_ipfc_port_unconfig(x, y) do {} while (0) + +#define bfad_ipfc_probe_post(x) do {} while (0) +#define bfad_ipfc_port_new(x, y, z) BFA_STATUS_OK +#define bfad_ipfc_port_delete(x, y) do {} while (0) +#define bfad_ipfc_port_online(x, y) do {} while (0) +#define bfad_ipfc_port_offline(x, y) do {} while (0) + +#define bfad_ip_get_attr(x) BFA_STATUS_FAILED +#define bfad_ip_reset_drv_stats(x) BFA_STATUS_FAILED +#define bfad_ip_get_drv_stats(x, y) BFA_STATUS_FAILED +#define bfad_ip_enable_ipfc(x, y, z) BFA_STATUS_FAILED + + +#endif diff --git a/drivers/scsi/bfa/bfad_os.c b/drivers/scsi/bfa/bfad_os.c new file mode 100644 index 000000000000..faf47b4f1a38 --- /dev/null +++ b/drivers/scsi/bfa/bfad_os.c @@ -0,0 +1,50 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfad_os.c Linux driver OS specific calls. + */ + +#include "bfa_os_inc.h" +#include "bfad_drv.h" + +void +bfa_os_gettimeofday(struct bfa_timeval_s *tv) +{ + struct timeval tmp_tv; + + do_gettimeofday(&tmp_tv); + tv->tv_sec = (u32) tmp_tv.tv_sec; + tv->tv_usec = (u32) tmp_tv.tv_usec; +} + +void +bfa_os_printf(struct bfa_log_mod_s *log_mod, u32 msg_id, + const char *fmt, ...) +{ + va_list ap; + #define BFA_STRING_256 256 + char tmp[BFA_STRING_256]; + + va_start(ap, fmt); + vsprintf(tmp, fmt, ap); + va_end(ap); + + printk(tmp); +} + + diff --git a/drivers/scsi/bfa/bfad_tm.h b/drivers/scsi/bfa/bfad_tm.h new file mode 100644 index 000000000000..4901b1b7df02 --- /dev/null +++ b/drivers/scsi/bfa/bfad_tm.h @@ -0,0 +1,59 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* + * Brocade Fibre Channel HBA Linux Target Mode Driver + */ + +/** + * tm/dummy/bfad_tm.h BFA callback dummy header file for BFA Linux target mode PCI interface module. + */ + +#ifndef __BFAD_TM_H__ +#define __BFAD_TM_H__ + +#include <defs/bfa_defs_status.h> + +#define FCPT_NAME "" + +/* + * Called from base Linux driver on (De)Init events + */ + +/* attach tgt template with scst */ +#define bfad_tm_module_init() do {} while (0) + +/* detach/release tgt template */ +#define bfad_tm_module_exit() do {} while (0) + +#define bfad_tm_probe(x) do {} while (0) +#define bfad_tm_probe_undo(x) do {} while (0) +#define bfad_tm_probe_post(x) do {} while (0) + +/* + * Called by base Linux driver but triggered by BFA FCS on config events + */ +#define bfad_tm_port_new(x, y) BFA_STATUS_OK +#define bfad_tm_port_delete(x, y) do {} while (0) + +/* + * Called by base Linux driver but triggered by BFA FCS on PLOGI/O events + */ +#define bfad_tm_port_online(x, y) do {} while (0) +#define bfad_tm_port_offline(x, y) do {} while (0) + +#endif diff --git a/drivers/scsi/bfa/bfad_trcmod.h b/drivers/scsi/bfa/bfad_trcmod.h new file mode 100644 index 000000000000..2827b2acd041 --- /dev/null +++ b/drivers/scsi/bfa/bfad_trcmod.h @@ -0,0 +1,52 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfad_trcmod.h Linux driver trace modules + */ + + +#ifndef __BFAD_TRCMOD_H__ +#define __BFAD_TRCMOD_H__ + +#include <cs/bfa_trc.h> + +/* + * !!! Only append to the enums defined here to avoid any versioning + * !!! needed between trace utility and driver version + */ +enum { + /* 2.6 Driver */ + BFA_TRC_LDRV_BFAD = 1, + BFA_TRC_LDRV_BFAD_2_6 = 2, + BFA_TRC_LDRV_BFAD_2_6_9 = 3, + BFA_TRC_LDRV_BFAD_2_6_10 = 4, + BFA_TRC_LDRV_INTR = 5, + BFA_TRC_LDRV_IOCTL = 6, + BFA_TRC_LDRV_OS = 7, + BFA_TRC_LDRV_IM = 8, + BFA_TRC_LDRV_IM_2_6 = 9, + BFA_TRC_LDRV_IM_2_6_9 = 10, + BFA_TRC_LDRV_IM_2_6_10 = 11, + BFA_TRC_LDRV_TM = 12, + BFA_TRC_LDRV_IPFC = 13, + BFA_TRC_LDRV_IM_2_4 = 14, + BFA_TRC_LDRV_IM_VMW = 15, + BFA_TRC_LDRV_IM_LT_2_6_10 = 16, +}; + +#endif /* __BFAD_TRCMOD_H__ */ diff --git a/drivers/scsi/bfa/fab.c b/drivers/scsi/bfa/fab.c new file mode 100644 index 000000000000..7e3a4d5d7bb4 --- /dev/null +++ b/drivers/scsi/bfa/fab.c @@ -0,0 +1,62 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "lport_priv.h" + +/** + * fab.c port fab implementation. + */ + +/** + * bfa_fcs_port_fab_public port fab public functions + */ + +/** + * Called by port to initialize fabric services of the base port. + */ +void +bfa_fcs_port_fab_init(struct bfa_fcs_port_s *port) +{ + bfa_fcs_port_ns_init(port); + bfa_fcs_port_scn_init(port); + bfa_fcs_port_ms_init(port); +} + +/** + * Called by port to notify transition to online state. + */ +void +bfa_fcs_port_fab_online(struct bfa_fcs_port_s *port) +{ + bfa_fcs_port_ns_online(port); + bfa_fcs_port_scn_online(port); +} + +/** + * Called by port to notify transition to offline state. + */ +void +bfa_fcs_port_fab_offline(struct bfa_fcs_port_s *port) +{ + bfa_fcs_port_ns_offline(port); + bfa_fcs_port_scn_offline(port); + bfa_fcs_port_ms_offline(port); +} diff --git a/drivers/scsi/bfa/fabric.c b/drivers/scsi/bfa/fabric.c new file mode 100644 index 000000000000..a8b14c47b009 --- /dev/null +++ b/drivers/scsi/bfa/fabric.c @@ -0,0 +1,1278 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fabric.c Fabric module implementation. + */ + +#include "fcs_fabric.h" +#include "fcs_lport.h" +#include "fcs_vport.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include "fcs_auth.h" +#include "fcs.h" +#include "fcbuild.h" +#include <log/bfa_log_fcs.h> +#include <aen/bfa_aen_port.h> +#include <bfa_svc.h> + +BFA_TRC_FILE(FCS, FABRIC); + +#define BFA_FCS_FABRIC_RETRY_DELAY (2000) /* Milliseconds */ +#define BFA_FCS_FABRIC_CLEANUP_DELAY (10000) /* Milliseconds */ + +#define bfa_fcs_fabric_set_opertype(__fabric) do { \ + if (bfa_pport_get_topology((__fabric)->fcs->bfa) \ + == BFA_PPORT_TOPOLOGY_P2P) \ + (__fabric)->oper_type = BFA_PPORT_TYPE_NPORT; \ + else \ + (__fabric)->oper_type = BFA_PPORT_TYPE_NLPORT; \ +} while (0) + +/* + * forward declarations + */ +static void bfa_fcs_fabric_init(struct bfa_fcs_fabric_s *fabric); +static void bfa_fcs_fabric_login(struct bfa_fcs_fabric_s *fabric); +static void bfa_fcs_fabric_notify_online(struct bfa_fcs_fabric_s *fabric); +static void bfa_fcs_fabric_notify_offline(struct bfa_fcs_fabric_s *fabric); +static void bfa_fcs_fabric_delay(void *cbarg); +static void bfa_fcs_fabric_delete(struct bfa_fcs_fabric_s *fabric); +static void bfa_fcs_fabric_delete_comp(void *cbarg); +static void bfa_fcs_fabric_process_uf(struct bfa_fcs_fabric_s *fabric, + struct fchs_s *fchs, u16 len); +static void bfa_fcs_fabric_process_flogi(struct bfa_fcs_fabric_s *fabric, + struct fchs_s *fchs, u16 len); +static void bfa_fcs_fabric_send_flogi_acc(struct bfa_fcs_fabric_s *fabric); +static void bfa_fcs_fabric_flogiacc_comp(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rspfchs); +/** + * fcs_fabric_sm fabric state machine functions + */ + +/** + * Fabric state machine events + */ +enum bfa_fcs_fabric_event { + BFA_FCS_FABRIC_SM_CREATE = 1, /* fabric create from driver */ + BFA_FCS_FABRIC_SM_DELETE = 2, /* fabric delete from driver */ + BFA_FCS_FABRIC_SM_LINK_DOWN = 3, /* link down from port */ + BFA_FCS_FABRIC_SM_LINK_UP = 4, /* link up from port */ + BFA_FCS_FABRIC_SM_CONT_OP = 5, /* continue op from flogi/auth */ + BFA_FCS_FABRIC_SM_RETRY_OP = 6, /* continue op from flogi/auth */ + BFA_FCS_FABRIC_SM_NO_FABRIC = 7, /* no fabric from flogi/auth + */ + BFA_FCS_FABRIC_SM_PERF_EVFP = 8, /* perform EVFP from + *flogi/auth */ + BFA_FCS_FABRIC_SM_ISOLATE = 9, /* isolate from EVFP processing */ + BFA_FCS_FABRIC_SM_NO_TAGGING = 10,/* no VFT tagging from EVFP */ + BFA_FCS_FABRIC_SM_DELAYED = 11, /* timeout delay event */ + BFA_FCS_FABRIC_SM_AUTH_FAILED = 12, /* authentication failed */ + BFA_FCS_FABRIC_SM_AUTH_SUCCESS = 13, /* authentication successful + */ + BFA_FCS_FABRIC_SM_DELCOMP = 14, /* all vports deleted event */ + BFA_FCS_FABRIC_SM_LOOPBACK = 15, /* Received our own FLOGI */ + BFA_FCS_FABRIC_SM_START = 16, /* fabric delete from driver */ +}; + +static void bfa_fcs_fabric_sm_uninit(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_created(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_linkdown(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_flogi(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_flogi_retry(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_auth(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_auth_failed(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_loopback(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_nofabric(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_online(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_evfp(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_evfp_done(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_isolated(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +static void bfa_fcs_fabric_sm_deleting(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event); +/** + * Beginning state before fabric creation. + */ +static void +bfa_fcs_fabric_sm_uninit(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_CREATE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_created); + bfa_fcs_fabric_init(fabric); + bfa_fcs_lport_init(&fabric->bport, fabric->fcs, FC_VF_ID_NULL, + &fabric->bport.port_cfg, NULL); + break; + + case BFA_FCS_FABRIC_SM_LINK_UP: + case BFA_FCS_FABRIC_SM_LINK_DOWN: + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * Beginning state before fabric creation. + */ +static void +bfa_fcs_fabric_sm_created(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_START: + if (bfa_pport_is_linkup(fabric->fcs->bfa)) { + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_flogi); + bfa_fcs_fabric_login(fabric); + } else + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + break; + + case BFA_FCS_FABRIC_SM_LINK_UP: + case BFA_FCS_FABRIC_SM_LINK_DOWN: + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_uninit); + bfa_fcs_modexit_comp(fabric->fcs); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * Link is down, awaiting LINK UP event from port. This is also the + * first state at fabric creation. + */ +static void +bfa_fcs_fabric_sm_linkdown(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_LINK_UP: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_flogi); + bfa_fcs_fabric_login(fabric); + break; + + case BFA_FCS_FABRIC_SM_RETRY_OP: + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_fcs_fabric_delete(fabric); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * FLOGI is in progress, awaiting FLOGI reply. + */ +static void +bfa_fcs_fabric_sm_flogi(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_CONT_OP: + + bfa_pport_set_tx_bbcredit(fabric->fcs->bfa, fabric->bb_credit); + fabric->fab_type = BFA_FCS_FABRIC_SWITCHED; + + if (fabric->auth_reqd && fabric->is_auth) { + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_auth); + bfa_trc(fabric->fcs, event); + } else { + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_online); + bfa_fcs_fabric_notify_online(fabric); + } + break; + + case BFA_FCS_FABRIC_SM_RETRY_OP: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_flogi_retry); + bfa_timer_start(fabric->fcs->bfa, &fabric->delay_timer, + bfa_fcs_fabric_delay, fabric, + BFA_FCS_FABRIC_RETRY_DELAY); + break; + + case BFA_FCS_FABRIC_SM_LOOPBACK: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_loopback); + bfa_lps_discard(fabric->lps); + bfa_fcs_fabric_set_opertype(fabric); + break; + + case BFA_FCS_FABRIC_SM_NO_FABRIC: + fabric->fab_type = BFA_FCS_FABRIC_N2N; + bfa_pport_set_tx_bbcredit(fabric->fcs->bfa, fabric->bb_credit); + bfa_fcs_fabric_notify_online(fabric); + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_nofabric); + break; + + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + bfa_lps_discard(fabric->lps); + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_lps_discard(fabric->lps); + bfa_fcs_fabric_delete(fabric); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + + +static void +bfa_fcs_fabric_sm_flogi_retry(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_DELAYED: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_flogi); + bfa_fcs_fabric_login(fabric); + break; + + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + bfa_timer_stop(&fabric->delay_timer); + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_timer_stop(&fabric->delay_timer); + bfa_fcs_fabric_delete(fabric); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * Authentication is in progress, awaiting authentication results. + */ +static void +bfa_fcs_fabric_sm_auth(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_AUTH_FAILED: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_auth_failed); + bfa_lps_discard(fabric->lps); + break; + + case BFA_FCS_FABRIC_SM_AUTH_SUCCESS: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_online); + bfa_fcs_fabric_notify_online(fabric); + break; + + case BFA_FCS_FABRIC_SM_PERF_EVFP: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_evfp); + break; + + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + bfa_lps_discard(fabric->lps); + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_fcs_fabric_delete(fabric); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * Authentication failed + */ +static void +bfa_fcs_fabric_sm_auth_failed(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + bfa_fcs_fabric_notify_offline(fabric); + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_fcs_fabric_delete(fabric); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * Port is in loopback mode. + */ +static void +bfa_fcs_fabric_sm_loopback(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + bfa_fcs_fabric_notify_offline(fabric); + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_fcs_fabric_delete(fabric); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * There is no attached fabric - private loop or NPort-to-NPort topology. + */ +static void +bfa_fcs_fabric_sm_nofabric(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + bfa_lps_discard(fabric->lps); + bfa_fcs_fabric_notify_offline(fabric); + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_fcs_fabric_delete(fabric); + break; + + case BFA_FCS_FABRIC_SM_NO_FABRIC: + bfa_trc(fabric->fcs, fabric->bb_credit); + bfa_pport_set_tx_bbcredit(fabric->fcs->bfa, fabric->bb_credit); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * Fabric is online - normal operating state. + */ +static void +bfa_fcs_fabric_sm_online(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_linkdown); + bfa_lps_discard(fabric->lps); + bfa_fcs_fabric_notify_offline(fabric); + break; + + case BFA_FCS_FABRIC_SM_DELETE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_deleting); + bfa_fcs_fabric_delete(fabric); + break; + + case BFA_FCS_FABRIC_SM_AUTH_FAILED: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_auth_failed); + bfa_lps_discard(fabric->lps); + break; + + case BFA_FCS_FABRIC_SM_AUTH_SUCCESS: + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * Exchanging virtual fabric parameters. + */ +static void +bfa_fcs_fabric_sm_evfp(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_CONT_OP: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_evfp_done); + break; + + case BFA_FCS_FABRIC_SM_ISOLATE: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_isolated); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + +/** + * EVFP exchange complete and VFT tagging is enabled. + */ +static void +bfa_fcs_fabric_sm_evfp_done(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); +} + +/** + * Port is isolated after EVFP exchange due to VF_ID mismatch (N and F). + */ +static void +bfa_fcs_fabric_sm_isolated(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + bfa_log(fabric->fcs->logm, BFA_LOG_FCS_FABRIC_ISOLATED, + fabric->bport.port_cfg.pwwn, fabric->fcs->port_vfid, + fabric->event_arg.swp_vfid); +} + +/** + * Fabric is being deleted, awaiting vport delete completions. + */ +static void +bfa_fcs_fabric_sm_deleting(struct bfa_fcs_fabric_s *fabric, + enum bfa_fcs_fabric_event event) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, event); + + switch (event) { + case BFA_FCS_FABRIC_SM_DELCOMP: + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_uninit); + bfa_fcs_modexit_comp(fabric->fcs); + break; + + case BFA_FCS_FABRIC_SM_LINK_UP: + break; + + case BFA_FCS_FABRIC_SM_LINK_DOWN: + bfa_fcs_fabric_notify_offline(fabric); + break; + + default: + bfa_sm_fault(fabric->fcs, event); + } +} + + + +/** + * fcs_fabric_private fabric private functions + */ + +static void +bfa_fcs_fabric_init(struct bfa_fcs_fabric_s *fabric) +{ + struct bfa_port_cfg_s *port_cfg = &fabric->bport.port_cfg; + + port_cfg->roles = BFA_PORT_ROLE_FCP_IM; + port_cfg->nwwn = bfa_ioc_get_nwwn(&fabric->fcs->bfa->ioc); + port_cfg->pwwn = bfa_ioc_get_pwwn(&fabric->fcs->bfa->ioc); +} + +/** + * Port Symbolic Name Creation for base port. + */ +void +bfa_fcs_fabric_psymb_init(struct bfa_fcs_fabric_s *fabric) +{ + struct bfa_port_cfg_s *port_cfg = &fabric->bport.port_cfg; + struct bfa_adapter_attr_s adapter_attr; + struct bfa_fcs_driver_info_s *driver_info = &fabric->fcs->driver_info; + + bfa_os_memset((void *)&adapter_attr, 0, + sizeof(struct bfa_adapter_attr_s)); + bfa_ioc_get_adapter_attr(&fabric->fcs->bfa->ioc, &adapter_attr); + + /* + * Model name/number + */ + strncpy((char *)&port_cfg->sym_name, adapter_attr.model, + BFA_FCS_PORT_SYMBNAME_MODEL_SZ); + strncat((char *)&port_cfg->sym_name, BFA_FCS_PORT_SYMBNAME_SEPARATOR, + sizeof(BFA_FCS_PORT_SYMBNAME_SEPARATOR)); + + /* + * Driver Version + */ + strncat((char *)&port_cfg->sym_name, (char *)driver_info->version, + BFA_FCS_PORT_SYMBNAME_VERSION_SZ); + strncat((char *)&port_cfg->sym_name, BFA_FCS_PORT_SYMBNAME_SEPARATOR, + sizeof(BFA_FCS_PORT_SYMBNAME_SEPARATOR)); + + /* + * Host machine name + */ + strncat((char *)&port_cfg->sym_name, + (char *)driver_info->host_machine_name, + BFA_FCS_PORT_SYMBNAME_MACHINENAME_SZ); + strncat((char *)&port_cfg->sym_name, BFA_FCS_PORT_SYMBNAME_SEPARATOR, + sizeof(BFA_FCS_PORT_SYMBNAME_SEPARATOR)); + + /* + * Host OS Info : + * If OS Patch Info is not there, do not truncate any bytes from the + * OS name string and instead copy the entire OS info string (64 bytes). + */ + if (driver_info->host_os_patch[0] == '\0') { + strncat((char *)&port_cfg->sym_name, + (char *)driver_info->host_os_name, BFA_FCS_OS_STR_LEN); + strncat((char *)&port_cfg->sym_name, + BFA_FCS_PORT_SYMBNAME_SEPARATOR, + sizeof(BFA_FCS_PORT_SYMBNAME_SEPARATOR)); + } else { + strncat((char *)&port_cfg->sym_name, + (char *)driver_info->host_os_name, + BFA_FCS_PORT_SYMBNAME_OSINFO_SZ); + strncat((char *)&port_cfg->sym_name, + BFA_FCS_PORT_SYMBNAME_SEPARATOR, + sizeof(BFA_FCS_PORT_SYMBNAME_SEPARATOR)); + + /* + * Append host OS Patch Info + */ + strncat((char *)&port_cfg->sym_name, + (char *)driver_info->host_os_patch, + BFA_FCS_PORT_SYMBNAME_OSPATCH_SZ); + } + + /* + * null terminate + */ + port_cfg->sym_name.symname[BFA_SYMNAME_MAXLEN - 1] = 0; +} + +/** + * bfa lps login completion callback + */ +void +bfa_cb_lps_flogi_comp(void *bfad, void *uarg, bfa_status_t status) +{ + struct bfa_fcs_fabric_s *fabric = uarg; + + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_trc(fabric->fcs, status); + + switch (status) { + case BFA_STATUS_OK: + fabric->stats.flogi_accepts++; + break; + + case BFA_STATUS_INVALID_MAC: + /* + * Only for CNA + */ + fabric->stats.flogi_acc_err++; + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_RETRY_OP); + + return; + + case BFA_STATUS_EPROTOCOL: + switch (bfa_lps_get_extstatus(fabric->lps)) { + case BFA_EPROTO_BAD_ACCEPT: + fabric->stats.flogi_acc_err++; + break; + + case BFA_EPROTO_UNKNOWN_RSP: + fabric->stats.flogi_unknown_rsp++; + break; + + default: + break; + } + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_RETRY_OP); + + return; + + case BFA_STATUS_FABRIC_RJT: + fabric->stats.flogi_rejects++; + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_RETRY_OP); + return; + + default: + fabric->stats.flogi_rsp_err++; + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_RETRY_OP); + return; + } + + fabric->bb_credit = bfa_lps_get_peer_bbcredit(fabric->lps); + bfa_trc(fabric->fcs, fabric->bb_credit); + + if (!bfa_lps_is_brcd_fabric(fabric->lps)) + fabric->fabric_name = bfa_lps_get_peer_nwwn(fabric->lps); + + /* + * Check port type. It should be 1 = F-port. + */ + if (bfa_lps_is_fport(fabric->lps)) { + fabric->bport.pid = bfa_lps_get_pid(fabric->lps); + fabric->is_npiv = bfa_lps_is_npiv_en(fabric->lps); + fabric->is_auth = bfa_lps_is_authreq(fabric->lps); + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_CONT_OP); + } else { + /* + * Nport-2-Nport direct attached + */ + fabric->bport.port_topo.pn2n.rem_port_wwn = + bfa_lps_get_peer_pwwn(fabric->lps); + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_NO_FABRIC); + } + + bfa_trc(fabric->fcs, fabric->bport.pid); + bfa_trc(fabric->fcs, fabric->is_npiv); + bfa_trc(fabric->fcs, fabric->is_auth); +} + +/** + * Allocate and send FLOGI. + */ +static void +bfa_fcs_fabric_login(struct bfa_fcs_fabric_s *fabric) +{ + struct bfa_s *bfa = fabric->fcs->bfa; + struct bfa_port_cfg_s *pcfg = &fabric->bport.port_cfg; + u8 alpa = 0; + + if (bfa_pport_get_topology(bfa) == BFA_PPORT_TOPOLOGY_LOOP) + alpa = bfa_pport_get_myalpa(bfa); + + bfa_lps_flogi(fabric->lps, fabric, alpa, bfa_pport_get_maxfrsize(bfa), + pcfg->pwwn, pcfg->nwwn, fabric->auth_reqd); + + fabric->stats.flogi_sent++; +} + +static void +bfa_fcs_fabric_notify_online(struct bfa_fcs_fabric_s *fabric) +{ + struct bfa_fcs_vport_s *vport; + struct list_head *qe, *qen; + + bfa_trc(fabric->fcs, fabric->fabric_name); + + bfa_fcs_fabric_set_opertype(fabric); + fabric->stats.fabric_onlines++; + + /** + * notify online event to base and then virtual ports + */ + bfa_fcs_port_online(&fabric->bport); + + list_for_each_safe(qe, qen, &fabric->vport_q) { + vport = (struct bfa_fcs_vport_s *)qe; + bfa_fcs_vport_online(vport); + } +} + +static void +bfa_fcs_fabric_notify_offline(struct bfa_fcs_fabric_s *fabric) +{ + struct bfa_fcs_vport_s *vport; + struct list_head *qe, *qen; + + bfa_trc(fabric->fcs, fabric->fabric_name); + fabric->stats.fabric_offlines++; + + /** + * notify offline event first to vports and then base port. + */ + list_for_each_safe(qe, qen, &fabric->vport_q) { + vport = (struct bfa_fcs_vport_s *)qe; + bfa_fcs_vport_offline(vport); + } + + bfa_fcs_port_offline(&fabric->bport); + + fabric->fabric_name = 0; + fabric->fabric_ip_addr[0] = 0; +} + +static void +bfa_fcs_fabric_delay(void *cbarg) +{ + struct bfa_fcs_fabric_s *fabric = cbarg; + + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_DELAYED); +} + +/** + * Delete all vports and wait for vport delete completions. + */ +static void +bfa_fcs_fabric_delete(struct bfa_fcs_fabric_s *fabric) +{ + struct bfa_fcs_vport_s *vport; + struct list_head *qe, *qen; + + list_for_each_safe(qe, qen, &fabric->vport_q) { + vport = (struct bfa_fcs_vport_s *)qe; + bfa_fcs_vport_delete(vport); + } + + bfa_fcs_port_delete(&fabric->bport); + bfa_wc_wait(&fabric->wc); +} + +static void +bfa_fcs_fabric_delete_comp(void *cbarg) +{ + struct bfa_fcs_fabric_s *fabric = cbarg; + + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_DELCOMP); +} + + + +/** + * fcs_fabric_public fabric public functions + */ + +/** + * Module initialization + */ +void +bfa_fcs_fabric_modinit(struct bfa_fcs_s *fcs) +{ + struct bfa_fcs_fabric_s *fabric; + + fabric = &fcs->fabric; + bfa_os_memset(fabric, 0, sizeof(struct bfa_fcs_fabric_s)); + + /** + * Initialize base fabric. + */ + fabric->fcs = fcs; + INIT_LIST_HEAD(&fabric->vport_q); + INIT_LIST_HEAD(&fabric->vf_q); + fabric->lps = bfa_lps_alloc(fcs->bfa); + bfa_assert(fabric->lps); + + /** + * Initialize fabric delete completion handler. Fabric deletion is complete + * when the last vport delete is complete. + */ + bfa_wc_init(&fabric->wc, bfa_fcs_fabric_delete_comp, fabric); + bfa_wc_up(&fabric->wc); /* For the base port */ + + bfa_sm_set_state(fabric, bfa_fcs_fabric_sm_uninit); + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_CREATE); + bfa_trc(fcs, 0); +} + +/** + * Module cleanup + */ +void +bfa_fcs_fabric_modexit(struct bfa_fcs_s *fcs) +{ + struct bfa_fcs_fabric_s *fabric; + + bfa_trc(fcs, 0); + + /** + * Cleanup base fabric. + */ + fabric = &fcs->fabric; + bfa_lps_delete(fabric->lps); + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_DELETE); +} + +/** + * Fabric module start -- kick starts FCS actions + */ +void +bfa_fcs_fabric_modstart(struct bfa_fcs_s *fcs) +{ + struct bfa_fcs_fabric_s *fabric; + + bfa_trc(fcs, 0); + fabric = &fcs->fabric; + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_START); +} + +/** + * Suspend fabric activity as part of driver suspend. + */ +void +bfa_fcs_fabric_modsusp(struct bfa_fcs_s *fcs) +{ +} + +bfa_boolean_t +bfa_fcs_fabric_is_loopback(struct bfa_fcs_fabric_s *fabric) +{ + return (bfa_sm_cmp_state(fabric, bfa_fcs_fabric_sm_loopback)); +} + +enum bfa_pport_type +bfa_fcs_fabric_port_type(struct bfa_fcs_fabric_s *fabric) +{ + return fabric->oper_type; +} + +/** + * Link up notification from BFA physical port module. + */ +void +bfa_fcs_fabric_link_up(struct bfa_fcs_fabric_s *fabric) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_LINK_UP); +} + +/** + * Link down notification from BFA physical port module. + */ +void +bfa_fcs_fabric_link_down(struct bfa_fcs_fabric_s *fabric) +{ + bfa_trc(fabric->fcs, fabric->bport.port_cfg.pwwn); + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_LINK_DOWN); +} + +/** + * A child vport is being created in the fabric. + * + * Call from vport module at vport creation. A list of base port and vports + * belonging to a fabric is maintained to propagate link events. + * + * param[in] fabric - Fabric instance. This can be a base fabric or vf. + * param[in] vport - Vport being created. + * + * @return None (always succeeds) + */ +void +bfa_fcs_fabric_addvport(struct bfa_fcs_fabric_s *fabric, + struct bfa_fcs_vport_s *vport) +{ + /** + * - add vport to fabric's vport_q + */ + bfa_trc(fabric->fcs, fabric->vf_id); + + list_add_tail(&vport->qe, &fabric->vport_q); + fabric->num_vports++; + bfa_wc_up(&fabric->wc); +} + +/** + * A child vport is being deleted from fabric. + * + * Vport is being deleted. + */ +void +bfa_fcs_fabric_delvport(struct bfa_fcs_fabric_s *fabric, + struct bfa_fcs_vport_s *vport) +{ + list_del(&vport->qe); + fabric->num_vports--; + bfa_wc_down(&fabric->wc); +} + +/** + * Base port is deleted. + */ +void +bfa_fcs_fabric_port_delete_comp(struct bfa_fcs_fabric_s *fabric) +{ + bfa_wc_down(&fabric->wc); +} + +/** + * Check if fabric is online. + * + * param[in] fabric - Fabric instance. This can be a base fabric or vf. + * + * @return TRUE/FALSE + */ +int +bfa_fcs_fabric_is_online(struct bfa_fcs_fabric_s *fabric) +{ + return (bfa_sm_cmp_state(fabric, bfa_fcs_fabric_sm_online)); +} + + +bfa_status_t +bfa_fcs_fabric_addvf(struct bfa_fcs_fabric_s *vf, struct bfa_fcs_s *fcs, + struct bfa_port_cfg_s *port_cfg, + struct bfad_vf_s *vf_drv) +{ + bfa_sm_set_state(vf, bfa_fcs_fabric_sm_uninit); + return BFA_STATUS_OK; +} + +/** + * Lookup for a vport withing a fabric given its pwwn + */ +struct bfa_fcs_vport_s * +bfa_fcs_fabric_vport_lookup(struct bfa_fcs_fabric_s *fabric, wwn_t pwwn) +{ + struct bfa_fcs_vport_s *vport; + struct list_head *qe; + + list_for_each(qe, &fabric->vport_q) { + vport = (struct bfa_fcs_vport_s *)qe; + if (bfa_fcs_port_get_pwwn(&vport->lport) == pwwn) + return vport; + } + + return NULL; +} + +/** + * In a given fabric, return the number of lports. + * + * param[in] fabric - Fabric instance. This can be a base fabric or vf. + * +* @return : 1 or more. + */ +u16 +bfa_fcs_fabric_vport_count(struct bfa_fcs_fabric_s *fabric) +{ + return (fabric->num_vports); +} + +/** + * Unsolicited frame receive handling. + */ +void +bfa_fcs_fabric_uf_recv(struct bfa_fcs_fabric_s *fabric, struct fchs_s *fchs, + u16 len) +{ + u32 pid = fchs->d_id; + struct bfa_fcs_vport_s *vport; + struct list_head *qe; + struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + struct fc_logi_s *flogi = (struct fc_logi_s *) els_cmd; + + bfa_trc(fabric->fcs, len); + bfa_trc(fabric->fcs, pid); + + /** + * Look for our own FLOGI frames being looped back. This means an + * external loopback cable is in place. Our own FLOGI frames are + * sometimes looped back when switch port gets temporarily bypassed. + */ + if ((pid == bfa_os_ntoh3b(FC_FABRIC_PORT)) + && (els_cmd->els_code == FC_ELS_FLOGI) + && (flogi->port_name == bfa_fcs_port_get_pwwn(&fabric->bport))) { + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_LOOPBACK); + return; + } + + /** + * FLOGI/EVFP exchanges should be consumed by base fabric. + */ + if (fchs->d_id == bfa_os_hton3b(FC_FABRIC_PORT)) { + bfa_trc(fabric->fcs, pid); + bfa_fcs_fabric_process_uf(fabric, fchs, len); + return; + } + + if (fabric->bport.pid == pid) { + /** + * All authentication frames should be routed to auth + */ + bfa_trc(fabric->fcs, els_cmd->els_code); + if (els_cmd->els_code == FC_ELS_AUTH) { + bfa_trc(fabric->fcs, els_cmd->els_code); + fabric->auth.response = (u8 *) els_cmd; + return; + } + + bfa_trc(fabric->fcs, *(u8 *) ((u8 *) fchs)); + bfa_fcs_port_uf_recv(&fabric->bport, fchs, len); + return; + } + + /** + * look for a matching local port ID + */ + list_for_each(qe, &fabric->vport_q) { + vport = (struct bfa_fcs_vport_s *)qe; + if (vport->lport.pid == pid) { + bfa_fcs_port_uf_recv(&vport->lport, fchs, len); + return; + } + } + bfa_trc(fabric->fcs, els_cmd->els_code); + bfa_fcs_port_uf_recv(&fabric->bport, fchs, len); +} + +/** + * Unsolicited frames to be processed by fabric. + */ +static void +bfa_fcs_fabric_process_uf(struct bfa_fcs_fabric_s *fabric, struct fchs_s *fchs, + u16 len) +{ + struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + + bfa_trc(fabric->fcs, els_cmd->els_code); + + switch (els_cmd->els_code) { + case FC_ELS_FLOGI: + bfa_fcs_fabric_process_flogi(fabric, fchs, len); + break; + + default: + /* + * need to generate a LS_RJT + */ + break; + } +} + +/** + * Process incoming FLOGI + */ +static void +bfa_fcs_fabric_process_flogi(struct bfa_fcs_fabric_s *fabric, + struct fchs_s *fchs, u16 len) +{ + struct fc_logi_s *flogi = (struct fc_logi_s *) (fchs + 1); + struct bfa_fcs_port_s *bport = &fabric->bport; + + bfa_trc(fabric->fcs, fchs->s_id); + + fabric->stats.flogi_rcvd++; + /* + * Check port type. It should be 0 = n-port. + */ + if (flogi->csp.port_type) { + /* + * @todo: may need to send a LS_RJT + */ + bfa_trc(fabric->fcs, flogi->port_name); + fabric->stats.flogi_rejected++; + return; + } + + fabric->bb_credit = bfa_os_ntohs(flogi->csp.bbcred); + bport->port_topo.pn2n.rem_port_wwn = flogi->port_name; + bport->port_topo.pn2n.reply_oxid = fchs->ox_id; + + /* + * Send a Flogi Acc + */ + bfa_fcs_fabric_send_flogi_acc(fabric); + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_NO_FABRIC); +} + +static void +bfa_fcs_fabric_send_flogi_acc(struct bfa_fcs_fabric_s *fabric) +{ + struct bfa_port_cfg_s *pcfg = &fabric->bport.port_cfg; + struct bfa_fcs_port_n2n_s *n2n_port = &fabric->bport.port_topo.pn2n; + struct bfa_s *bfa = fabric->fcs->bfa; + struct bfa_fcxp_s *fcxp; + u16 reqlen; + struct fchs_s fchs; + + fcxp = bfa_fcs_fcxp_alloc(fabric->fcs); + /** + * Do not expect this failure -- expect remote node to retry + */ + if (!fcxp) + return; + + reqlen = fc_flogi_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_os_hton3b(FC_FABRIC_PORT), + n2n_port->reply_oxid, pcfg->pwwn, + pcfg->nwwn, bfa_pport_get_maxfrsize(bfa), + bfa_pport_get_rx_bbcredit(bfa)); + + bfa_fcxp_send(fcxp, NULL, fabric->vf_id, bfa_lps_get_tag(fabric->lps), + BFA_FALSE, FC_CLASS_3, reqlen, &fchs, + bfa_fcs_fabric_flogiacc_comp, fabric, + FC_MAX_PDUSZ, 0); /* Timeout 0 indicates no + * response expected + */ +} + +/** + * Flogi Acc completion callback. + */ +static void +bfa_fcs_fabric_flogiacc_comp(void *fcsarg, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t status, u32 rsp_len, + u32 resid_len, struct fchs_s *rspfchs) +{ + struct bfa_fcs_fabric_s *fabric = cbarg; + + bfa_trc(fabric->fcs, status); +} + +/* + * + * @param[in] fabric - fabric + * @param[in] result - 1 + * + * @return - none + */ +void +bfa_fcs_auth_finished(struct bfa_fcs_fabric_s *fabric, enum auth_status status) +{ + bfa_trc(fabric->fcs, status); + + if (status == FC_AUTH_STATE_SUCCESS) + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_AUTH_SUCCESS); + else + bfa_sm_send_event(fabric, BFA_FCS_FABRIC_SM_AUTH_FAILED); +} + +/** + * Send AEN notification + */ +static void +bfa_fcs_fabric_aen_post(struct bfa_fcs_port_s *port, + enum bfa_port_aen_event event) +{ + union bfa_aen_data_u aen_data; + struct bfa_log_mod_s *logmod = port->fcs->logm; + wwn_t pwwn = bfa_fcs_port_get_pwwn(port); + wwn_t fwwn = bfa_fcs_port_get_fabric_name(port); + char pwwn_ptr[BFA_STRING_32]; + char fwwn_ptr[BFA_STRING_32]; + + wwn2str(pwwn_ptr, pwwn); + wwn2str(fwwn_ptr, fwwn); + + switch (event) { + case BFA_PORT_AEN_FABRIC_NAME_CHANGE: + bfa_log(logmod, BFA_AEN_PORT_FABRIC_NAME_CHANGE, pwwn_ptr, + fwwn_ptr); + break; + default: + break; + } + + aen_data.port.pwwn = pwwn; + aen_data.port.fwwn = fwwn; +} + +/* + * + * @param[in] fabric - fabric + * @param[in] wwn_t - new fabric name + * + * @return - none + */ +void +bfa_fcs_fabric_set_fabric_name(struct bfa_fcs_fabric_s *fabric, + wwn_t fabric_name) +{ + bfa_trc(fabric->fcs, fabric_name); + + if (fabric->fabric_name == 0) { + /* + * With BRCD switches, we don't get Fabric Name in FLOGI. + * Don't generate a fabric name change event in this case. + */ + fabric->fabric_name = fabric_name; + } else { + fabric->fabric_name = fabric_name; + /* + * Generate a Event + */ + bfa_fcs_fabric_aen_post(&fabric->bport, + BFA_PORT_AEN_FABRIC_NAME_CHANGE); + } + +} + +/** + * Not used by FCS. + */ +void +bfa_cb_lps_flogo_comp(void *bfad, void *uarg) +{ +} + + diff --git a/drivers/scsi/bfa/fcbuild.c b/drivers/scsi/bfa/fcbuild.c new file mode 100644 index 000000000000..d174706b9caa --- /dev/null +++ b/drivers/scsi/bfa/fcbuild.c @@ -0,0 +1,1449 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +/* + * fcbuild.c - FC link service frame building and parsing routines + */ + +#include <bfa_os_inc.h> +#include "fcbuild.h" + +/* + * static build functions + */ +static void fc_els_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id); +static void fc_bls_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id); +static struct fchs_s fc_els_req_tmpl; +static struct fchs_s fc_els_rsp_tmpl; +static struct fchs_s fc_bls_req_tmpl; +static struct fchs_s fc_bls_rsp_tmpl; +static struct fc_ba_acc_s ba_acc_tmpl; +static struct fc_logi_s plogi_tmpl; +static struct fc_prli_s prli_tmpl; +static struct fc_rrq_s rrq_tmpl; +static struct fchs_s fcp_fchs_tmpl; + +void +fcbuild_init(void) +{ + /* + * fc_els_req_tmpl + */ + fc_els_req_tmpl.routing = FC_RTG_EXT_LINK; + fc_els_req_tmpl.cat_info = FC_CAT_LD_REQUEST; + fc_els_req_tmpl.type = FC_TYPE_ELS; + fc_els_req_tmpl.f_ctl = + bfa_os_hton3b(FCTL_SEQ_INI | FCTL_FS_EXCH | FCTL_END_SEQ | + FCTL_SI_XFER); + fc_els_req_tmpl.rx_id = FC_RXID_ANY; + + /* + * fc_els_rsp_tmpl + */ + fc_els_rsp_tmpl.routing = FC_RTG_EXT_LINK; + fc_els_rsp_tmpl.cat_info = FC_CAT_LD_REPLY; + fc_els_rsp_tmpl.type = FC_TYPE_ELS; + fc_els_rsp_tmpl.f_ctl = + bfa_os_hton3b(FCTL_EC_RESP | FCTL_SEQ_INI | FCTL_LS_EXCH | + FCTL_END_SEQ | FCTL_SI_XFER); + fc_els_rsp_tmpl.rx_id = FC_RXID_ANY; + + /* + * fc_bls_req_tmpl + */ + fc_bls_req_tmpl.routing = FC_RTG_BASIC_LINK; + fc_bls_req_tmpl.type = FC_TYPE_BLS; + fc_bls_req_tmpl.f_ctl = bfa_os_hton3b(FCTL_END_SEQ | FCTL_SI_XFER); + fc_bls_req_tmpl.rx_id = FC_RXID_ANY; + + /* + * fc_bls_rsp_tmpl + */ + fc_bls_rsp_tmpl.routing = FC_RTG_BASIC_LINK; + fc_bls_rsp_tmpl.cat_info = FC_CAT_BA_ACC; + fc_bls_rsp_tmpl.type = FC_TYPE_BLS; + fc_bls_rsp_tmpl.f_ctl = + bfa_os_hton3b(FCTL_EC_RESP | FCTL_SEQ_INI | FCTL_LS_EXCH | + FCTL_END_SEQ | FCTL_SI_XFER); + fc_bls_rsp_tmpl.rx_id = FC_RXID_ANY; + + /* + * ba_acc_tmpl + */ + ba_acc_tmpl.seq_id_valid = 0; + ba_acc_tmpl.low_seq_cnt = 0; + ba_acc_tmpl.high_seq_cnt = 0xFFFF; + + /* + * plogi_tmpl + */ + plogi_tmpl.csp.verhi = FC_PH_VER_PH_3; + plogi_tmpl.csp.verlo = FC_PH_VER_4_3; + plogi_tmpl.csp.bbcred = bfa_os_htons(0x0004); + plogi_tmpl.csp.ciro = 0x1; + plogi_tmpl.csp.cisc = 0x0; + plogi_tmpl.csp.altbbcred = 0x0; + plogi_tmpl.csp.conseq = bfa_os_htons(0x00FF); + plogi_tmpl.csp.ro_bitmap = bfa_os_htons(0x0002); + plogi_tmpl.csp.e_d_tov = bfa_os_htonl(2000); + + plogi_tmpl.class3.class_valid = 1; + plogi_tmpl.class3.sequential = 1; + plogi_tmpl.class3.conseq = 0xFF; + plogi_tmpl.class3.ospx = 1; + + /* + * prli_tmpl + */ + prli_tmpl.command = FC_ELS_PRLI; + prli_tmpl.pglen = 0x10; + prli_tmpl.pagebytes = bfa_os_htons(0x0014); + prli_tmpl.parampage.type = FC_TYPE_FCP; + prli_tmpl.parampage.imagepair = 1; + prli_tmpl.parampage.servparams.rxrdisab = 1; + + /* + * rrq_tmpl + */ + rrq_tmpl.els_cmd.els_code = FC_ELS_RRQ; + + /* + * fcp_fchs_tmpl + */ + fcp_fchs_tmpl.routing = FC_RTG_FC4_DEV_DATA; + fcp_fchs_tmpl.cat_info = FC_CAT_UNSOLICIT_CMD; + fcp_fchs_tmpl.type = FC_TYPE_FCP; + fcp_fchs_tmpl.f_ctl = + bfa_os_hton3b(FCTL_FS_EXCH | FCTL_END_SEQ | FCTL_SI_XFER); + fcp_fchs_tmpl.seq_id = 1; + fcp_fchs_tmpl.rx_id = FC_RXID_ANY; +} + +static void +fc_gs_fchdr_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u32 ox_id) +{ + bfa_os_memset(fchs, 0, sizeof(struct fchs_s)); + + fchs->routing = FC_RTG_FC4_DEV_DATA; + fchs->cat_info = FC_CAT_UNSOLICIT_CTRL; + fchs->type = FC_TYPE_SERVICES; + fchs->f_ctl = + bfa_os_hton3b(FCTL_SEQ_INI | FCTL_FS_EXCH | FCTL_END_SEQ | + FCTL_SI_XFER); + fchs->rx_id = FC_RXID_ANY; + fchs->d_id = (d_id); + fchs->s_id = (s_id); + fchs->ox_id = bfa_os_htons(ox_id); + + /** + * @todo no need to set ox_id for request + * no need to set rx_id for response + */ +} + +void +fc_els_req_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id) +{ + bfa_os_memcpy(fchs, &fc_els_req_tmpl, sizeof(struct fchs_s)); + fchs->d_id = (d_id); + fchs->s_id = (s_id); + fchs->ox_id = bfa_os_htons(ox_id); +} + +static void +fc_els_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id) +{ + bfa_os_memcpy(fchs, &fc_els_rsp_tmpl, sizeof(struct fchs_s)); + fchs->d_id = d_id; + fchs->s_id = s_id; + fchs->ox_id = ox_id; +} + +enum fc_parse_status +fc_els_rsp_parse(struct fchs_s *fchs, int len) +{ + struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + struct fc_ls_rjt_s *ls_rjt = (struct fc_ls_rjt_s *) els_cmd; + + len = len; + + switch (els_cmd->els_code) { + case FC_ELS_LS_RJT: + if (ls_rjt->reason_code == FC_LS_RJT_RSN_LOGICAL_BUSY) + return (FC_PARSE_BUSY); + else + return (FC_PARSE_FAILURE); + + case FC_ELS_ACC: + return (FC_PARSE_OK); + } + return (FC_PARSE_OK); +} + +static void +fc_bls_rsp_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id) +{ + bfa_os_memcpy(fchs, &fc_bls_rsp_tmpl, sizeof(struct fchs_s)); + fchs->d_id = d_id; + fchs->s_id = s_id; + fchs->ox_id = ox_id; +} + +static u16 +fc_plogi_x_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size, u8 els_code) +{ + struct fc_logi_s *plogi = (struct fc_logi_s *) (pld); + + bfa_os_memcpy(plogi, &plogi_tmpl, sizeof(struct fc_logi_s)); + + plogi->els_cmd.els_code = els_code; + if (els_code == FC_ELS_PLOGI) + fc_els_req_build(fchs, d_id, s_id, ox_id); + else + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + plogi->csp.rxsz = plogi->class3.rxsz = bfa_os_htons(pdu_size); + + bfa_os_memcpy(&plogi->port_name, &port_name, sizeof(wwn_t)); + bfa_os_memcpy(&plogi->node_name, &node_name, sizeof(wwn_t)); + + return (sizeof(struct fc_logi_s)); +} + +u16 +fc_flogi_build(struct fchs_s *fchs, struct fc_logi_s *flogi, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size, u8 set_npiv, u8 set_auth, + u16 local_bb_credits) +{ + u32 d_id = bfa_os_hton3b(FC_FABRIC_PORT); + u32 *vvl_info; + + bfa_os_memcpy(flogi, &plogi_tmpl, sizeof(struct fc_logi_s)); + + flogi->els_cmd.els_code = FC_ELS_FLOGI; + fc_els_req_build(fchs, d_id, s_id, ox_id); + + flogi->csp.rxsz = flogi->class3.rxsz = bfa_os_htons(pdu_size); + flogi->port_name = port_name; + flogi->node_name = node_name; + + /* + * Set the NPIV Capability Bit ( word 1, bit 31) of Common + * Service Parameters. + */ + flogi->csp.ciro = set_npiv; + + /* set AUTH capability */ + flogi->csp.security = set_auth; + + flogi->csp.bbcred = bfa_os_htons(local_bb_credits); + + /* Set brcd token in VVL */ + vvl_info = (u32 *)&flogi->vvl[0]; + + /* set the flag to indicate the presence of VVL */ + flogi->csp.npiv_supp = 1; /* @todo. field name is not correct */ + vvl_info[0] = bfa_os_htonl(FLOGI_VVL_BRCD); + + return (sizeof(struct fc_logi_s)); +} + +u16 +fc_flogi_acc_build(struct fchs_s *fchs, struct fc_logi_s *flogi, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size, u16 local_bb_credits) +{ + u32 d_id = 0; + + bfa_os_memcpy(flogi, &plogi_tmpl, sizeof(struct fc_logi_s)); + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + flogi->els_cmd.els_code = FC_ELS_ACC; + flogi->csp.rxsz = flogi->class3.rxsz = bfa_os_htons(pdu_size); + flogi->port_name = port_name; + flogi->node_name = node_name; + + flogi->csp.bbcred = bfa_os_htons(local_bb_credits); + + return (sizeof(struct fc_logi_s)); +} + +u16 +fc_fdisc_build(struct fchs_s *fchs, struct fc_logi_s *flogi, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size) +{ + u32 d_id = bfa_os_hton3b(FC_FABRIC_PORT); + + bfa_os_memcpy(flogi, &plogi_tmpl, sizeof(struct fc_logi_s)); + + flogi->els_cmd.els_code = FC_ELS_FDISC; + fc_els_req_build(fchs, d_id, s_id, ox_id); + + flogi->csp.rxsz = flogi->class3.rxsz = bfa_os_htons(pdu_size); + flogi->port_name = port_name; + flogi->node_name = node_name; + + return (sizeof(struct fc_logi_s)); +} + +u16 +fc_plogi_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size) +{ + return fc_plogi_x_build(fchs, pld, d_id, s_id, ox_id, port_name, + node_name, pdu_size, FC_ELS_PLOGI); +} + +u16 +fc_plogi_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size) +{ + return fc_plogi_x_build(fchs, pld, d_id, s_id, ox_id, port_name, + node_name, pdu_size, FC_ELS_ACC); +} + +enum fc_parse_status +fc_plogi_rsp_parse(struct fchs_s *fchs, int len, wwn_t port_name) +{ + struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + struct fc_logi_s *plogi; + struct fc_ls_rjt_s *ls_rjt; + + switch (els_cmd->els_code) { + case FC_ELS_LS_RJT: + ls_rjt = (struct fc_ls_rjt_s *) (fchs + 1); + if (ls_rjt->reason_code == FC_LS_RJT_RSN_LOGICAL_BUSY) + return (FC_PARSE_BUSY); + else + return (FC_PARSE_FAILURE); + case FC_ELS_ACC: + plogi = (struct fc_logi_s *) (fchs + 1); + if (len < sizeof(struct fc_logi_s)) + return (FC_PARSE_FAILURE); + + if (!wwn_is_equal(plogi->port_name, port_name)) + return (FC_PARSE_FAILURE); + + if (!plogi->class3.class_valid) + return (FC_PARSE_FAILURE); + + if (bfa_os_ntohs(plogi->class3.rxsz) < (FC_MIN_PDUSZ)) + return (FC_PARSE_FAILURE); + + return (FC_PARSE_OK); + default: + return (FC_PARSE_FAILURE); + } +} + +enum fc_parse_status +fc_plogi_parse(struct fchs_s *fchs) +{ + struct fc_logi_s *plogi = (struct fc_logi_s *) (fchs + 1); + + if (plogi->class3.class_valid != 1) + return FC_PARSE_FAILURE; + + if ((bfa_os_ntohs(plogi->class3.rxsz) < FC_MIN_PDUSZ) + || (bfa_os_ntohs(plogi->class3.rxsz) > FC_MAX_PDUSZ) + || (plogi->class3.rxsz == 0)) + return (FC_PARSE_FAILURE); + + return FC_PARSE_OK; +} + +u16 +fc_prli_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id, + u16 ox_id) +{ + struct fc_prli_s *prli = (struct fc_prli_s *) (pld); + + fc_els_req_build(fchs, d_id, s_id, ox_id); + bfa_os_memcpy(prli, &prli_tmpl, sizeof(struct fc_prli_s)); + + prli->command = FC_ELS_PRLI; + prli->parampage.servparams.initiator = 1; + prli->parampage.servparams.retry = 1; + prli->parampage.servparams.rec_support = 1; + prli->parampage.servparams.task_retry_id = 0; + prli->parampage.servparams.confirm = 1; + + return (sizeof(struct fc_prli_s)); +} + +u16 +fc_prli_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id, + u16 ox_id, enum bfa_port_role role) +{ + struct fc_prli_s *prli = (struct fc_prli_s *) (pld); + + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + bfa_os_memcpy(prli, &prli_tmpl, sizeof(struct fc_prli_s)); + + prli->command = FC_ELS_ACC; + + if ((role & BFA_PORT_ROLE_FCP_TM) == BFA_PORT_ROLE_FCP_TM) + prli->parampage.servparams.target = 1; + else + prli->parampage.servparams.initiator = 1; + + prli->parampage.rspcode = FC_PRLI_ACC_XQTD; + + return (sizeof(struct fc_prli_s)); +} + +enum fc_parse_status +fc_prli_rsp_parse(struct fc_prli_s *prli, int len) +{ + if (len < sizeof(struct fc_prli_s)) + return (FC_PARSE_FAILURE); + + if (prli->command != FC_ELS_ACC) + return (FC_PARSE_FAILURE); + + if ((prli->parampage.rspcode != FC_PRLI_ACC_XQTD) + && (prli->parampage.rspcode != FC_PRLI_ACC_PREDEF_IMG)) + return (FC_PARSE_FAILURE); + + if (prli->parampage.servparams.target != 1) + return (FC_PARSE_FAILURE); + + return (FC_PARSE_OK); +} + +enum fc_parse_status +fc_prli_parse(struct fc_prli_s *prli) +{ + if (prli->parampage.type != FC_TYPE_FCP) + return (FC_PARSE_FAILURE); + + if (!prli->parampage.imagepair) + return (FC_PARSE_FAILURE); + + if (!prli->parampage.servparams.initiator) + return (FC_PARSE_FAILURE); + + return (FC_PARSE_OK); +} + +u16 +fc_logo_build(struct fchs_s *fchs, struct fc_logo_s *logo, u32 d_id, + u32 s_id, u16 ox_id, wwn_t port_name) +{ + fc_els_req_build(fchs, d_id, s_id, ox_id); + + memset(logo, '\0', sizeof(struct fc_logo_s)); + logo->els_cmd.els_code = FC_ELS_LOGO; + logo->nport_id = (s_id); + logo->orig_port_name = port_name; + + return (sizeof(struct fc_logo_s)); +} + +static u16 +fc_adisc_x_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, u32 d_id, + u32 s_id, u16 ox_id, wwn_t port_name, + wwn_t node_name, u8 els_code) +{ + memset(adisc, '\0', sizeof(struct fc_adisc_s)); + + adisc->els_cmd.els_code = els_code; + + if (els_code == FC_ELS_ADISC) + fc_els_req_build(fchs, d_id, s_id, ox_id); + else + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + adisc->orig_HA = 0; + adisc->orig_port_name = port_name; + adisc->orig_node_name = node_name; + adisc->nport_id = (s_id); + + return (sizeof(struct fc_adisc_s)); +} + +u16 +fc_adisc_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, u32 d_id, + u32 s_id, u16 ox_id, wwn_t port_name, + wwn_t node_name) +{ + return fc_adisc_x_build(fchs, adisc, d_id, s_id, ox_id, port_name, + node_name, FC_ELS_ADISC); +} + +u16 +fc_adisc_acc_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, u32 d_id, + u32 s_id, u16 ox_id, wwn_t port_name, + wwn_t node_name) +{ + return fc_adisc_x_build(fchs, adisc, d_id, s_id, ox_id, port_name, + node_name, FC_ELS_ACC); +} + +enum fc_parse_status +fc_adisc_rsp_parse(struct fc_adisc_s *adisc, int len, wwn_t port_name, + wwn_t node_name) +{ + + if (len < sizeof(struct fc_adisc_s)) + return (FC_PARSE_FAILURE); + + if (adisc->els_cmd.els_code != FC_ELS_ACC) + return (FC_PARSE_FAILURE); + + if (!wwn_is_equal(adisc->orig_port_name, port_name)) + return (FC_PARSE_FAILURE); + + return (FC_PARSE_OK); +} + +enum fc_parse_status +fc_adisc_parse(struct fchs_s *fchs, void *pld, u32 host_dap, + wwn_t node_name, wwn_t port_name) +{ + struct fc_adisc_s *adisc = (struct fc_adisc_s *) pld; + + if (adisc->els_cmd.els_code != FC_ELS_ACC) + return (FC_PARSE_FAILURE); + + if ((adisc->nport_id == (host_dap)) + && wwn_is_equal(adisc->orig_port_name, port_name) + && wwn_is_equal(adisc->orig_node_name, node_name)) + return (FC_PARSE_OK); + + return (FC_PARSE_FAILURE); +} + +enum fc_parse_status +fc_pdisc_parse(struct fchs_s *fchs, wwn_t node_name, wwn_t port_name) +{ + struct fc_logi_s *pdisc = (struct fc_logi_s *) (fchs + 1); + + if (pdisc->class3.class_valid != 1) + return FC_PARSE_FAILURE; + + if ((bfa_os_ntohs(pdisc->class3.rxsz) < + (FC_MIN_PDUSZ - sizeof(struct fchs_s))) + || (pdisc->class3.rxsz == 0)) + return (FC_PARSE_FAILURE); + + if (!wwn_is_equal(pdisc->port_name, port_name)) + return (FC_PARSE_FAILURE); + + if (!wwn_is_equal(pdisc->node_name, node_name)) + return (FC_PARSE_FAILURE); + + return FC_PARSE_OK; +} + +u16 +fc_abts_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u16 ox_id) +{ + bfa_os_memcpy(fchs, &fc_bls_req_tmpl, sizeof(struct fchs_s)); + fchs->cat_info = FC_CAT_ABTS; + fchs->d_id = (d_id); + fchs->s_id = (s_id); + fchs->ox_id = bfa_os_htons(ox_id); + + return (sizeof(struct fchs_s)); +} + +enum fc_parse_status +fc_abts_rsp_parse(struct fchs_s *fchs, int len) +{ + if ((fchs->cat_info == FC_CAT_BA_ACC) + || (fchs->cat_info == FC_CAT_BA_RJT)) + return (FC_PARSE_OK); + + return (FC_PARSE_FAILURE); +} + +u16 +fc_rrq_build(struct fchs_s *fchs, struct fc_rrq_s *rrq, u32 d_id, + u32 s_id, u16 ox_id, u16 rrq_oxid) +{ + fc_els_req_build(fchs, d_id, s_id, ox_id); + + /* + * build rrq payload + */ + bfa_os_memcpy(rrq, &rrq_tmpl, sizeof(struct fc_rrq_s)); + rrq->s_id = (s_id); + rrq->ox_id = bfa_os_htons(rrq_oxid); + rrq->rx_id = FC_RXID_ANY; + + return (sizeof(struct fc_rrq_s)); +} + +u16 +fc_logo_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, u32 s_id, + u16 ox_id) +{ + struct fc_els_cmd_s *acc = pld; + + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + memset(acc, 0, sizeof(struct fc_els_cmd_s)); + acc->els_code = FC_ELS_ACC; + + return (sizeof(struct fc_els_cmd_s)); +} + +u16 +fc_ls_rjt_build(struct fchs_s *fchs, struct fc_ls_rjt_s *ls_rjt, u32 d_id, + u32 s_id, u16 ox_id, u8 reason_code, + u8 reason_code_expl) +{ + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + memset(ls_rjt, 0, sizeof(struct fc_ls_rjt_s)); + + ls_rjt->els_cmd.els_code = FC_ELS_LS_RJT; + ls_rjt->reason_code = reason_code; + ls_rjt->reason_code_expl = reason_code_expl; + ls_rjt->vendor_unique = 0x00; + + return (sizeof(struct fc_ls_rjt_s)); +} + +u16 +fc_ba_acc_build(struct fchs_s *fchs, struct fc_ba_acc_s *ba_acc, u32 d_id, + u32 s_id, u16 ox_id, u16 rx_id) +{ + fc_bls_rsp_build(fchs, d_id, s_id, ox_id); + + bfa_os_memcpy(ba_acc, &ba_acc_tmpl, sizeof(struct fc_ba_acc_s)); + + fchs->rx_id = rx_id; + + ba_acc->ox_id = fchs->ox_id; + ba_acc->rx_id = fchs->rx_id; + + return (sizeof(struct fc_ba_acc_s)); +} + +u16 +fc_ls_acc_build(struct fchs_s *fchs, struct fc_els_cmd_s *els_cmd, + u32 d_id, u32 s_id, u16 ox_id) +{ + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + memset(els_cmd, 0, sizeof(struct fc_els_cmd_s)); + els_cmd->els_code = FC_ELS_ACC; + + return (sizeof(struct fc_els_cmd_s)); +} + +int +fc_logout_params_pages(struct fchs_s *fc_frame, u8 els_code) +{ + int num_pages = 0; + struct fc_prlo_s *prlo; + struct fc_tprlo_s *tprlo; + + if (els_code == FC_ELS_PRLO) { + prlo = (struct fc_prlo_s *) (fc_frame + 1); + num_pages = (bfa_os_ntohs(prlo->payload_len) - 4) / 16; + } else { + tprlo = (struct fc_tprlo_s *) (fc_frame + 1); + num_pages = (bfa_os_ntohs(tprlo->payload_len) - 4) / 16; + } + return num_pages; +} + +u16 +fc_tprlo_acc_build(struct fchs_s *fchs, struct fc_tprlo_acc_s *tprlo_acc, + u32 d_id, u32 s_id, u16 ox_id, + int num_pages) +{ + int page; + + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + memset(tprlo_acc, 0, (num_pages * 16) + 4); + tprlo_acc->command = FC_ELS_ACC; + + tprlo_acc->page_len = 0x10; + tprlo_acc->payload_len = bfa_os_htons((num_pages * 16) + 4); + + for (page = 0; page < num_pages; page++) { + tprlo_acc->tprlo_acc_params[page].opa_valid = 0; + tprlo_acc->tprlo_acc_params[page].rpa_valid = 0; + tprlo_acc->tprlo_acc_params[page].fc4type_csp = FC_TYPE_FCP; + tprlo_acc->tprlo_acc_params[page].orig_process_assc = 0; + tprlo_acc->tprlo_acc_params[page].resp_process_assc = 0; + } + return (bfa_os_ntohs(tprlo_acc->payload_len)); +} + +u16 +fc_prlo_acc_build(struct fchs_s *fchs, struct fc_prlo_acc_s *prlo_acc, + u32 d_id, u32 s_id, u16 ox_id, + int num_pages) +{ + int page; + + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + memset(prlo_acc, 0, (num_pages * 16) + 4); + prlo_acc->command = FC_ELS_ACC; + prlo_acc->page_len = 0x10; + prlo_acc->payload_len = bfa_os_htons((num_pages * 16) + 4); + + for (page = 0; page < num_pages; page++) { + prlo_acc->prlo_acc_params[page].opa_valid = 0; + prlo_acc->prlo_acc_params[page].rpa_valid = 0; + prlo_acc->prlo_acc_params[page].fc4type_csp = FC_TYPE_FCP; + prlo_acc->prlo_acc_params[page].orig_process_assc = 0; + prlo_acc->prlo_acc_params[page].resp_process_assc = 0; + } + + return (bfa_os_ntohs(prlo_acc->payload_len)); +} + +u16 +fc_rnid_build(struct fchs_s *fchs, struct fc_rnid_cmd_s *rnid, u32 d_id, + u32 s_id, u16 ox_id, u32 data_format) +{ + fc_els_req_build(fchs, d_id, s_id, ox_id); + + memset(rnid, 0, sizeof(struct fc_rnid_cmd_s)); + + rnid->els_cmd.els_code = FC_ELS_RNID; + rnid->node_id_data_format = data_format; + + return (sizeof(struct fc_rnid_cmd_s)); +} + +u16 +fc_rnid_acc_build(struct fchs_s *fchs, struct fc_rnid_acc_s *rnid_acc, + u32 d_id, u32 s_id, u16 ox_id, + u32 data_format, + struct fc_rnid_common_id_data_s *common_id_data, + struct fc_rnid_general_topology_data_s *gen_topo_data) +{ + memset(rnid_acc, 0, sizeof(struct fc_rnid_acc_s)); + + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + rnid_acc->els_cmd.els_code = FC_ELS_ACC; + rnid_acc->node_id_data_format = data_format; + rnid_acc->common_id_data_length = + sizeof(struct fc_rnid_common_id_data_s); + rnid_acc->common_id_data = *common_id_data; + + if (data_format == RNID_NODEID_DATA_FORMAT_DISCOVERY) { + rnid_acc->specific_id_data_length = + sizeof(struct fc_rnid_general_topology_data_s); + bfa_os_assign(rnid_acc->gen_topology_data, *gen_topo_data); + return (sizeof(struct fc_rnid_acc_s)); + } else { + return (sizeof(struct fc_rnid_acc_s) - + sizeof(struct fc_rnid_general_topology_data_s)); + } + +} + +u16 +fc_rpsc_build(struct fchs_s *fchs, struct fc_rpsc_cmd_s *rpsc, u32 d_id, + u32 s_id, u16 ox_id) +{ + fc_els_req_build(fchs, d_id, s_id, ox_id); + + memset(rpsc, 0, sizeof(struct fc_rpsc_cmd_s)); + + rpsc->els_cmd.els_code = FC_ELS_RPSC; + return (sizeof(struct fc_rpsc_cmd_s)); +} + +u16 +fc_rpsc2_build(struct fchs_s *fchs, struct fc_rpsc2_cmd_s *rpsc2, + u32 d_id, u32 s_id, u32 *pid_list, + u16 npids) +{ + u32 dctlr_id = FC_DOMAIN_CTRLR(bfa_os_hton3b(d_id)); + int i = 0; + + fc_els_req_build(fchs, bfa_os_hton3b(dctlr_id), s_id, 0); + + memset(rpsc2, 0, sizeof(struct fc_rpsc2_cmd_s)); + + rpsc2->els_cmd.els_code = FC_ELS_RPSC; + rpsc2->token = bfa_os_htonl(FC_BRCD_TOKEN); + rpsc2->num_pids = bfa_os_htons(npids); + for (i = 0; i < npids; i++) + rpsc2->pid_list[i].pid = pid_list[i]; + + return (sizeof(struct fc_rpsc2_cmd_s) + ((npids - 1) * + (sizeof(u32)))); +} + +u16 +fc_rpsc_acc_build(struct fchs_s *fchs, struct fc_rpsc_acc_s *rpsc_acc, + u32 d_id, u32 s_id, u16 ox_id, + struct fc_rpsc_speed_info_s *oper_speed) +{ + memset(rpsc_acc, 0, sizeof(struct fc_rpsc_acc_s)); + + fc_els_rsp_build(fchs, d_id, s_id, ox_id); + + rpsc_acc->command = FC_ELS_ACC; + rpsc_acc->num_entries = bfa_os_htons(1); + + rpsc_acc->speed_info[0].port_speed_cap = + bfa_os_htons(oper_speed->port_speed_cap); + + rpsc_acc->speed_info[0].port_op_speed = + bfa_os_htons(oper_speed->port_op_speed); + + return (sizeof(struct fc_rpsc_acc_s)); + +} + +/* + * TBD - + * . get rid of unnecessary memsets + */ + +u16 +fc_logo_rsp_parse(struct fchs_s *fchs, int len) +{ + struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + + len = len; + if (els_cmd->els_code != FC_ELS_ACC) + return FC_PARSE_FAILURE; + + return FC_PARSE_OK; +} + +u16 +fc_pdisc_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size) +{ + struct fc_logi_s *pdisc = (struct fc_logi_s *) (fchs + 1); + + bfa_os_memcpy(pdisc, &plogi_tmpl, sizeof(struct fc_logi_s)); + + pdisc->els_cmd.els_code = FC_ELS_PDISC; + fc_els_req_build(fchs, d_id, s_id, ox_id); + + pdisc->csp.rxsz = pdisc->class3.rxsz = bfa_os_htons(pdu_size); + pdisc->port_name = port_name; + pdisc->node_name = node_name; + + return (sizeof(struct fc_logi_s)); +} + +u16 +fc_pdisc_rsp_parse(struct fchs_s *fchs, int len, wwn_t port_name) +{ + struct fc_logi_s *pdisc = (struct fc_logi_s *) (fchs + 1); + + if (len < sizeof(struct fc_logi_s)) + return (FC_PARSE_LEN_INVAL); + + if (pdisc->els_cmd.els_code != FC_ELS_ACC) + return (FC_PARSE_ACC_INVAL); + + if (!wwn_is_equal(pdisc->port_name, port_name)) + return (FC_PARSE_PWWN_NOT_EQUAL); + + if (!pdisc->class3.class_valid) + return (FC_PARSE_NWWN_NOT_EQUAL); + + if (bfa_os_ntohs(pdisc->class3.rxsz) < (FC_MIN_PDUSZ)) + return (FC_PARSE_RXSZ_INVAL); + + return (FC_PARSE_OK); +} + +u16 +fc_prlo_build(struct fchs_s *fchs, u32 d_id, u32 s_id, u16 ox_id, + int num_pages) +{ + struct fc_prlo_s *prlo = (struct fc_prlo_s *) (fchs + 1); + int page; + + fc_els_req_build(fchs, d_id, s_id, ox_id); + memset(prlo, 0, (num_pages * 16) + 4); + prlo->command = FC_ELS_PRLO; + prlo->page_len = 0x10; + prlo->payload_len = bfa_os_htons((num_pages * 16) + 4); + + for (page = 0; page < num_pages; page++) { + prlo->prlo_params[page].type = FC_TYPE_FCP; + prlo->prlo_params[page].opa_valid = 0; + prlo->prlo_params[page].rpa_valid = 0; + prlo->prlo_params[page].orig_process_assc = 0; + prlo->prlo_params[page].resp_process_assc = 0; + } + + return (bfa_os_ntohs(prlo->payload_len)); +} + +u16 +fc_prlo_rsp_parse(struct fchs_s *fchs, int len) +{ + struct fc_prlo_acc_s *prlo = (struct fc_prlo_acc_s *) (fchs + 1); + int num_pages = 0; + int page = 0; + + len = len; + + if (prlo->command != FC_ELS_ACC) + return (FC_PARSE_FAILURE); + + num_pages = ((bfa_os_ntohs(prlo->payload_len)) - 4) / 16; + + for (page = 0; page < num_pages; page++) { + if (prlo->prlo_acc_params[page].type != FC_TYPE_FCP) + return FC_PARSE_FAILURE; + + if (prlo->prlo_acc_params[page].opa_valid != 0) + return FC_PARSE_FAILURE; + + if (prlo->prlo_acc_params[page].rpa_valid != 0) + return FC_PARSE_FAILURE; + + if (prlo->prlo_acc_params[page].orig_process_assc != 0) + return FC_PARSE_FAILURE; + + if (prlo->prlo_acc_params[page].resp_process_assc != 0) + return FC_PARSE_FAILURE; + } + return (FC_PARSE_OK); + +} + +u16 +fc_tprlo_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id, int num_pages, + enum fc_tprlo_type tprlo_type, u32 tpr_id) +{ + struct fc_tprlo_s *tprlo = (struct fc_tprlo_s *) (fchs + 1); + int page; + + fc_els_req_build(fchs, d_id, s_id, ox_id); + memset(tprlo, 0, (num_pages * 16) + 4); + tprlo->command = FC_ELS_TPRLO; + tprlo->page_len = 0x10; + tprlo->payload_len = bfa_os_htons((num_pages * 16) + 4); + + for (page = 0; page < num_pages; page++) { + tprlo->tprlo_params[page].type = FC_TYPE_FCP; + tprlo->tprlo_params[page].opa_valid = 0; + tprlo->tprlo_params[page].rpa_valid = 0; + tprlo->tprlo_params[page].orig_process_assc = 0; + tprlo->tprlo_params[page].resp_process_assc = 0; + if (tprlo_type == FC_GLOBAL_LOGO) { + tprlo->tprlo_params[page].global_process_logout = 1; + } else if (tprlo_type == FC_TPR_LOGO) { + tprlo->tprlo_params[page].tpo_nport_valid = 1; + tprlo->tprlo_params[page].tpo_nport_id = (tpr_id); + } + } + + return (bfa_os_ntohs(tprlo->payload_len)); +} + +u16 +fc_tprlo_rsp_parse(struct fchs_s *fchs, int len) +{ + struct fc_tprlo_acc_s *tprlo = (struct fc_tprlo_acc_s *) (fchs + 1); + int num_pages = 0; + int page = 0; + + len = len; + + if (tprlo->command != FC_ELS_ACC) + return (FC_PARSE_ACC_INVAL); + + num_pages = (bfa_os_ntohs(tprlo->payload_len) - 4) / 16; + + for (page = 0; page < num_pages; page++) { + if (tprlo->tprlo_acc_params[page].type != FC_TYPE_FCP) + return (FC_PARSE_NOT_FCP); + if (tprlo->tprlo_acc_params[page].opa_valid != 0) + return (FC_PARSE_OPAFLAG_INVAL); + if (tprlo->tprlo_acc_params[page].rpa_valid != 0) + return (FC_PARSE_RPAFLAG_INVAL); + if (tprlo->tprlo_acc_params[page].orig_process_assc != 0) + return (FC_PARSE_OPA_INVAL); + if (tprlo->tprlo_acc_params[page].resp_process_assc != 0) + return (FC_PARSE_RPA_INVAL); + } + return (FC_PARSE_OK); +} + +enum fc_parse_status +fc_rrq_rsp_parse(struct fchs_s *fchs, int len) +{ + struct fc_els_cmd_s *els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + + len = len; + if (els_cmd->els_code != FC_ELS_ACC) + return FC_PARSE_FAILURE; + + return FC_PARSE_OK; +} + +u16 +fc_ba_rjt_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id, u32 reason_code, + u32 reason_expl) +{ + struct fc_ba_rjt_s *ba_rjt = (struct fc_ba_rjt_s *) (fchs + 1); + + fc_bls_rsp_build(fchs, d_id, s_id, ox_id); + + fchs->cat_info = FC_CAT_BA_RJT; + ba_rjt->reason_code = reason_code; + ba_rjt->reason_expl = reason_expl; + return (sizeof(struct fc_ba_rjt_s)); +} + +static void +fc_gs_cthdr_build(struct ct_hdr_s *cthdr, u32 s_id, u16 cmd_code) +{ + bfa_os_memset(cthdr, 0, sizeof(struct ct_hdr_s)); + cthdr->rev_id = CT_GS3_REVISION; + cthdr->gs_type = CT_GSTYPE_DIRSERVICE; + cthdr->gs_sub_type = CT_GSSUBTYPE_NAMESERVER; + cthdr->cmd_rsp_code = bfa_os_htons(cmd_code); +} + +static void +fc_gs_fdmi_cthdr_build(struct ct_hdr_s *cthdr, u32 s_id, u16 cmd_code) +{ + bfa_os_memset(cthdr, 0, sizeof(struct ct_hdr_s)); + cthdr->rev_id = CT_GS3_REVISION; + cthdr->gs_type = CT_GSTYPE_MGMTSERVICE; + cthdr->gs_sub_type = CT_GSSUBTYPE_HBA_MGMTSERVER; + cthdr->cmd_rsp_code = bfa_os_htons(cmd_code); +} + +static void +fc_gs_ms_cthdr_build(struct ct_hdr_s *cthdr, u32 s_id, u16 cmd_code, + u8 sub_type) +{ + bfa_os_memset(cthdr, 0, sizeof(struct ct_hdr_s)); + cthdr->rev_id = CT_GS3_REVISION; + cthdr->gs_type = CT_GSTYPE_MGMTSERVICE; + cthdr->gs_sub_type = sub_type; + cthdr->cmd_rsp_code = bfa_os_htons(cmd_code); +} + +u16 +fc_gidpn_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id, + wwn_t port_name) +{ + + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_gidpn_req_s *gidpn = + (struct fcgs_gidpn_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, ox_id); + fc_gs_cthdr_build(cthdr, s_id, GS_GID_PN); + + bfa_os_memset(gidpn, 0, sizeof(struct fcgs_gidpn_req_s)); + gidpn->port_name = port_name; + return (sizeof(struct fcgs_gidpn_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_gpnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id, + u32 port_id) +{ + + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + fcgs_gpnid_req_t *gpnid = (fcgs_gpnid_req_t *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, ox_id); + fc_gs_cthdr_build(cthdr, s_id, GS_GPN_ID); + + bfa_os_memset(gpnid, 0, sizeof(fcgs_gpnid_req_t)); + gpnid->dap = port_id; + return (sizeof(fcgs_gpnid_req_t) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_gnnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id, + u32 port_id) +{ + + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + fcgs_gnnid_req_t *gnnid = (fcgs_gnnid_req_t *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, ox_id); + fc_gs_cthdr_build(cthdr, s_id, GS_GNN_ID); + + bfa_os_memset(gnnid, 0, sizeof(fcgs_gnnid_req_t)); + gnnid->dap = port_id; + return (sizeof(fcgs_gnnid_req_t) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_ct_rsp_parse(struct ct_hdr_s *cthdr) +{ + if (bfa_os_ntohs(cthdr->cmd_rsp_code) != CT_RSP_ACCEPT) { + if (cthdr->reason_code == CT_RSN_LOGICAL_BUSY) + return FC_PARSE_BUSY; + else + return FC_PARSE_FAILURE; + } + + return FC_PARSE_OK; +} + +u16 +fc_scr_build(struct fchs_s *fchs, struct fc_scr_s *scr, u8 set_br_reg, + u32 s_id, u16 ox_id) +{ + u32 d_id = bfa_os_hton3b(FC_FABRIC_CONTROLLER); + + fc_els_req_build(fchs, d_id, s_id, ox_id); + + bfa_os_memset(scr, 0, sizeof(struct fc_scr_s)); + scr->command = FC_ELS_SCR; + scr->reg_func = FC_SCR_REG_FUNC_FULL; + if (set_br_reg) + scr->vu_reg_func = FC_VU_SCR_REG_FUNC_FABRIC_NAME_CHANGE; + + return (sizeof(struct fc_scr_s)); +} + +u16 +fc_rscn_build(struct fchs_s *fchs, struct fc_rscn_pl_s *rscn, u32 s_id, + u16 ox_id) +{ + u32 d_id = bfa_os_hton3b(FC_FABRIC_CONTROLLER); + u16 payldlen; + + fc_els_req_build(fchs, d_id, s_id, ox_id); + rscn->command = FC_ELS_RSCN; + rscn->pagelen = sizeof(rscn->event[0]); + + payldlen = sizeof(u32) + rscn->pagelen; + rscn->payldlen = bfa_os_htons(payldlen); + + rscn->event[0].format = FC_RSCN_FORMAT_PORTID; + rscn->event[0].portid = s_id; + + return (sizeof(struct fc_rscn_pl_s)); +} + +u16 +fc_rftid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id, + enum bfa_port_role roles) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rftid_req_s *rftid = + (struct fcgs_rftid_req_s *) (cthdr + 1); + u32 type_value, d_id = bfa_os_hton3b(FC_NAME_SERVER); + u8 index; + + fc_gs_fchdr_build(fchs, d_id, s_id, ox_id); + fc_gs_cthdr_build(cthdr, s_id, GS_RFT_ID); + + bfa_os_memset(rftid, 0, sizeof(struct fcgs_rftid_req_s)); + + rftid->dap = s_id; + + /* By default, FCP FC4 Type is registered */ + index = FC_TYPE_FCP >> 5; + type_value = 1 << (FC_TYPE_FCP % 32); + rftid->fc4_type[index] = bfa_os_htonl(type_value); + + if (roles & BFA_PORT_ROLE_FCP_IPFC) { + index = FC_TYPE_IP >> 5; + type_value = 1 << (FC_TYPE_IP % 32); + rftid->fc4_type[index] |= bfa_os_htonl(type_value); + } + + return (sizeof(struct fcgs_rftid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_rftid_build_sol(struct fchs_s *fchs, void *pyld, u32 s_id, + u16 ox_id, u8 *fc4_bitmap, + u32 bitmap_size) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rftid_req_s *rftid = + (struct fcgs_rftid_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, ox_id); + fc_gs_cthdr_build(cthdr, s_id, GS_RFT_ID); + + bfa_os_memset(rftid, 0, sizeof(struct fcgs_rftid_req_s)); + + rftid->dap = s_id; + bfa_os_memcpy((void *)rftid->fc4_type, (void *)fc4_bitmap, + (bitmap_size < 32 ? bitmap_size : 32)); + + return (sizeof(struct fcgs_rftid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_rffid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id, + u8 fc4_type, u8 fc4_ftrs) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rffid_req_s *rffid = + (struct fcgs_rffid_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, ox_id); + fc_gs_cthdr_build(cthdr, s_id, GS_RFF_ID); + + bfa_os_memset(rffid, 0, sizeof(struct fcgs_rffid_req_s)); + + rffid->dap = s_id; + rffid->fc4ftr_bits = fc4_ftrs; + rffid->fc4_type = fc4_type; + + return (sizeof(struct fcgs_rffid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_rspnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u16 ox_id, + u8 *name) +{ + + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rspnid_req_s *rspnid = + (struct fcgs_rspnid_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, ox_id); + fc_gs_cthdr_build(cthdr, s_id, GS_RSPN_ID); + + bfa_os_memset(rspnid, 0, sizeof(struct fcgs_rspnid_req_s)); + + rspnid->dap = s_id; + rspnid->spn_len = (u8) strlen((char *)name); + strncpy((char *)rspnid->spn, (char *)name, rspnid->spn_len); + + return (sizeof(struct fcgs_rspnid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_gid_ft_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u8 fc4_type) +{ + + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_gidft_req_s *gidft = + (struct fcgs_gidft_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + + fc_gs_cthdr_build(cthdr, s_id, GS_GID_FT); + + bfa_os_memset(gidft, 0, sizeof(struct fcgs_gidft_req_s)); + gidft->fc4_type = fc4_type; + gidft->domain_id = 0; + gidft->area_id = 0; + + return (sizeof(struct fcgs_gidft_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_rpnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id, + wwn_t port_name) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rpnid_req_s *rpnid = + (struct fcgs_rpnid_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_cthdr_build(cthdr, s_id, GS_RPN_ID); + + bfa_os_memset(rpnid, 0, sizeof(struct fcgs_rpnid_req_s)); + rpnid->port_id = port_id; + rpnid->port_name = port_name; + + return (sizeof(struct fcgs_rpnid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_rnnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id, + wwn_t node_name) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rnnid_req_s *rnnid = + (struct fcgs_rnnid_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_cthdr_build(cthdr, s_id, GS_RNN_ID); + + bfa_os_memset(rnnid, 0, sizeof(struct fcgs_rnnid_req_s)); + rnnid->port_id = port_id; + rnnid->node_name = node_name; + + return (sizeof(struct fcgs_rnnid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_rcsid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id, + u32 cos) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rcsid_req_s *rcsid = + (struct fcgs_rcsid_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_cthdr_build(cthdr, s_id, GS_RCS_ID); + + bfa_os_memset(rcsid, 0, sizeof(struct fcgs_rcsid_req_s)); + rcsid->port_id = port_id; + rcsid->cos = cos; + + return (sizeof(struct fcgs_rcsid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_rptid_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id, + u8 port_type) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_rptid_req_s *rptid = + (struct fcgs_rptid_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_cthdr_build(cthdr, s_id, GS_RPT_ID); + + bfa_os_memset(rptid, 0, sizeof(struct fcgs_rptid_req_s)); + rptid->port_id = port_id; + rptid->port_type = port_type; + + return (sizeof(struct fcgs_rptid_req_s) + sizeof(struct ct_hdr_s)); +} + +u16 +fc_ganxt_build(struct fchs_s *fchs, void *pyld, u32 s_id, u32 port_id) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + struct fcgs_ganxt_req_s *ganxt = + (struct fcgs_ganxt_req_s *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_NAME_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_cthdr_build(cthdr, s_id, GS_GA_NXT); + + bfa_os_memset(ganxt, 0, sizeof(struct fcgs_ganxt_req_s)); + ganxt->port_id = port_id; + + return (sizeof(struct ct_hdr_s) + sizeof(struct fcgs_ganxt_req_s)); +} + +/* + * Builds fc hdr and ct hdr for FDMI requests. + */ +u16 +fc_fdmi_reqhdr_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u16 cmd_code) +{ + + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + u32 d_id = bfa_os_hton3b(FC_MGMT_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_fdmi_cthdr_build(cthdr, s_id, cmd_code); + + return (sizeof(struct ct_hdr_s)); +} + +/* + * Given a FC4 Type, this function returns a fc4 type bitmask + */ +void +fc_get_fc4type_bitmask(u8 fc4_type, u8 *bit_mask) +{ + u8 index; + u32 *ptr = (u32 *) bit_mask; + u32 type_value; + + /* + * @todo : Check for bitmask size + */ + + index = fc4_type >> 5; + type_value = 1 << (fc4_type % 32); + ptr[index] = bfa_os_htonl(type_value); + +} + +/* + * GMAL Request + */ +u16 +fc_gmal_req_build(struct fchs_s *fchs, void *pyld, u32 s_id, wwn_t wwn) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + fcgs_gmal_req_t *gmal = (fcgs_gmal_req_t *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_MGMT_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_ms_cthdr_build(cthdr, s_id, GS_FC_GMAL_CMD, + CT_GSSUBTYPE_CFGSERVER); + + bfa_os_memset(gmal, 0, sizeof(fcgs_gmal_req_t)); + gmal->wwn = wwn; + + return (sizeof(struct ct_hdr_s) + sizeof(fcgs_gmal_req_t)); +} + +/* + * GFN (Get Fabric Name) Request + */ +u16 +fc_gfn_req_build(struct fchs_s *fchs, void *pyld, u32 s_id, wwn_t wwn) +{ + struct ct_hdr_s *cthdr = (struct ct_hdr_s *) pyld; + fcgs_gfn_req_t *gfn = (fcgs_gfn_req_t *) (cthdr + 1); + u32 d_id = bfa_os_hton3b(FC_MGMT_SERVER); + + fc_gs_fchdr_build(fchs, d_id, s_id, 0); + fc_gs_ms_cthdr_build(cthdr, s_id, GS_FC_GFN_CMD, + CT_GSSUBTYPE_CFGSERVER); + + bfa_os_memset(gfn, 0, sizeof(fcgs_gfn_req_t)); + gfn->wwn = wwn; + + return (sizeof(struct ct_hdr_s) + sizeof(fcgs_gfn_req_t)); +} diff --git a/drivers/scsi/bfa/fcbuild.h b/drivers/scsi/bfa/fcbuild.h new file mode 100644 index 000000000000..4d248424f7b3 --- /dev/null +++ b/drivers/scsi/bfa/fcbuild.h @@ -0,0 +1,273 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +/* + * fcbuild.h - FC link service frame building and parsing routines + */ + +#ifndef __FCBUILD_H__ +#define __FCBUILD_H__ + +#include <bfa_os_inc.h> +#include <protocol/fc.h> +#include <protocol/fcp.h> +#include <protocol/ct.h> +#include <defs/bfa_defs_port.h> +#include <defs/bfa_defs_pport.h> + +/* + * Utility Macros/functions + */ + +#define fcif_sof_set(_ifhdr, _sof) (_ifhdr)->sof = FC_ ## _sof +#define fcif_eof_set(_ifhdr, _eof) (_ifhdr)->eof = FC_ ## _eof + +#define wwn_is_equal(_wwn1, _wwn2) \ + (memcmp(&(_wwn1), &(_wwn2), sizeof(wwn_t)) == 0) + +#define fc_roundup(_l, _s) (((_l) + ((_s) - 1)) & ~((_s) - 1)) + +/* + * Given the fc response length, this routine will return + * the length of the actual payload bytes following the CT header. + * + * Assumes the input response length does not include the crc, eof, etc. + */ +static inline u32 +fc_get_ctresp_pyld_len(u32 resp_len) +{ + return (resp_len - sizeof(struct ct_hdr_s)); +} + +/* + * Convert bfa speed to rpsc speed value. + */ +static inline enum bfa_pport_speed +fc_rpsc_operspeed_to_bfa_speed(enum fc_rpsc_op_speed_s speed) +{ + switch (speed) { + + case RPSC_OP_SPEED_1G: + return BFA_PPORT_SPEED_1GBPS; + + case RPSC_OP_SPEED_2G: + return BFA_PPORT_SPEED_2GBPS; + + case RPSC_OP_SPEED_4G: + return BFA_PPORT_SPEED_4GBPS; + + case RPSC_OP_SPEED_8G: + return BFA_PPORT_SPEED_8GBPS; + + default: + return BFA_PPORT_SPEED_UNKNOWN; + } +} + +/* + * Convert RPSC speed to bfa speed value. + */ +static inline enum fc_rpsc_op_speed_s +fc_bfa_speed_to_rpsc_operspeed(enum bfa_pport_speed op_speed) +{ + switch (op_speed) { + + case BFA_PPORT_SPEED_1GBPS: + return RPSC_OP_SPEED_1G; + + case BFA_PPORT_SPEED_2GBPS: + return RPSC_OP_SPEED_2G; + + case BFA_PPORT_SPEED_4GBPS: + return RPSC_OP_SPEED_4G; + + case BFA_PPORT_SPEED_8GBPS: + return RPSC_OP_SPEED_8G; + + default: + return RPSC_OP_SPEED_NOT_EST; + } +} +enum fc_parse_status { + FC_PARSE_OK = 0, + FC_PARSE_FAILURE = 1, + FC_PARSE_BUSY = 2, + FC_PARSE_LEN_INVAL, + FC_PARSE_ACC_INVAL, + FC_PARSE_PWWN_NOT_EQUAL, + FC_PARSE_NWWN_NOT_EQUAL, + FC_PARSE_RXSZ_INVAL, + FC_PARSE_NOT_FCP, + FC_PARSE_OPAFLAG_INVAL, + FC_PARSE_RPAFLAG_INVAL, + FC_PARSE_OPA_INVAL, + FC_PARSE_RPA_INVAL, + +}; + +struct fc_templates_s { + struct fchs_s fc_els_req; + struct fchs_s fc_bls_req; + struct fc_logi_s plogi; + struct fc_rrq_s rrq; +}; + +void fcbuild_init(void); + +u16 fc_flogi_build(struct fchs_s *fchs, struct fc_logi_s *flogi, + u32 s_id, u16 ox_id, wwn_t port_name, + wwn_t node_name, u16 pdu_size, u8 set_npiv, + u8 set_auth, u16 local_bb_credits); +u16 fc_fdisc_build(struct fchs_s *buf, struct fc_logi_s *flogi, + u32 s_id, u16 ox_id, wwn_t port_name, + wwn_t node_name, u16 pdu_size); +u16 fc_flogi_acc_build(struct fchs_s *fchs, struct fc_logi_s *flogi, + u32 s_id, u16 ox_id, wwn_t port_name, + wwn_t node_name, u16 pdu_size, + u16 local_bb_credits); +u16 fc_plogi_build(struct fchs_s *fchs, void *pld, u32 d_id, + u32 s_id, u16 ox_id, wwn_t port_name, + wwn_t node_name, u16 pdu_size); +enum fc_parse_status fc_plogi_parse(struct fchs_s *fchs); +u16 fc_abts_build(struct fchs_s *buf, u32 d_id, u32 s_id, + u16 ox_id); +enum fc_parse_status fc_abts_rsp_parse(struct fchs_s *buf, int len); +u16 fc_rrq_build(struct fchs_s *buf, struct fc_rrq_s *rrq, u32 d_id, + u32 s_id, u16 ox_id, u16 rrq_oxid); +enum fc_parse_status fc_rrq_rsp_parse(struct fchs_s *buf, int len); +u16 fc_rspnid_build(struct fchs_s *fchs, void *pld, u32 s_id, + u16 ox_id, u8 *name); +u16 fc_rftid_build(struct fchs_s *fchs, void *pld, u32 s_id, + u16 ox_id, enum bfa_port_role role); +u16 fc_rftid_build_sol(struct fchs_s *fchs, void *pyld, u32 s_id, + u16 ox_id, u8 *fc4_bitmap, + u32 bitmap_size); +u16 fc_rffid_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u16 ox_id, u8 fc4_type, u8 fc4_ftrs); +u16 fc_gidpn_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u16 ox_id, wwn_t port_name); +u16 fc_gpnid_build(struct fchs_s *fchs, void *pld, u32 s_id, + u16 ox_id, u32 port_id); +u16 fc_scr_build(struct fchs_s *fchs, struct fc_scr_s *scr, + u8 set_br_reg, u32 s_id, u16 ox_id); +u16 fc_plogi_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, + u32 s_id, u16 ox_id, + wwn_t port_name, wwn_t node_name, u16 pdu_size); + +u16 fc_adisc_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, + u32 d_id, u32 s_id, u16 ox_id, + wwn_t port_name, wwn_t node_name); +enum fc_parse_status fc_adisc_parse(struct fchs_s *fchs, void *pld, + u32 host_dap, + wwn_t node_name, wwn_t port_name); +enum fc_parse_status fc_adisc_rsp_parse(struct fc_adisc_s *adisc, int len, + wwn_t port_name, wwn_t node_name); +u16 fc_adisc_acc_build(struct fchs_s *fchs, struct fc_adisc_s *adisc, + u32 d_id, u32 s_id, u16 ox_id, + wwn_t port_name, wwn_t node_name); +u16 fc_ls_rjt_build(struct fchs_s *fchs, struct fc_ls_rjt_s *ls_rjt, + u32 d_id, u32 s_id, u16 ox_id, + u8 reason_code, u8 reason_code_expl); +u16 fc_ls_acc_build(struct fchs_s *fchs, struct fc_els_cmd_s *els_cmd, + u32 d_id, u32 s_id, u16 ox_id); +u16 fc_prli_build(struct fchs_s *fchs, void *pld, u32 d_id, + u32 s_id, u16 ox_id); +enum fc_parse_status fc_prli_rsp_parse(struct fc_prli_s *prli, int len); + +u16 fc_prli_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, + u32 s_id, u16 ox_id, + enum bfa_port_role role); +u16 fc_rnid_build(struct fchs_s *fchs, struct fc_rnid_cmd_s *rnid, + u32 d_id, u32 s_id, u16 ox_id, + u32 data_format); +u16 fc_rnid_acc_build(struct fchs_s *fchs, struct fc_rnid_acc_s *rnid_acc, + u32 d_id, u32 s_id, u16 ox_id, + u32 data_format, + struct fc_rnid_common_id_data_s *common_id_data, + struct fc_rnid_general_topology_data_s * + gen_topo_data); +u16 fc_rpsc2_build(struct fchs_s *fchs, struct fc_rpsc2_cmd_s *rps2c, + u32 d_id, u32 s_id, + u32 *pid_list, u16 npids); +u16 fc_rpsc_build(struct fchs_s *fchs, struct fc_rpsc_cmd_s *rpsc, + u32 d_id, u32 s_id, u16 ox_id); +u16 fc_rpsc_acc_build(struct fchs_s *fchs, struct fc_rpsc_acc_s *rpsc_acc, + u32 d_id, u32 s_id, u16 ox_id, + struct fc_rpsc_speed_info_s *oper_speed); +u16 fc_gid_ft_build(struct fchs_s *fchs, void *pld, u32 s_id, + u8 fc4_type); +u16 fc_rpnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u32 port_id, wwn_t port_name); +u16 fc_rnnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u32 port_id, wwn_t node_name); +u16 fc_rcsid_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u32 port_id, u32 cos); +u16 fc_rptid_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u32 port_id, u8 port_type); +u16 fc_ganxt_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u32 port_id); +u16 fc_logo_build(struct fchs_s *fchs, struct fc_logo_s *logo, + u32 d_id, u32 s_id, u16 ox_id, + wwn_t port_name); +u16 fc_logo_acc_build(struct fchs_s *fchs, void *pld, u32 d_id, + u32 s_id, u16 ox_id); +u16 fc_fdmi_reqhdr_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u16 cmd_code); +u16 fc_gmal_req_build(struct fchs_s *fchs, void *pyld, u32 s_id, + wwn_t wwn); +u16 fc_gfn_req_build(struct fchs_s *fchs, void *pyld, u32 s_id, + wwn_t wwn); +void fc_get_fc4type_bitmask(u8 fc4_type, u8 *bit_mask); +void fc_els_req_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id); +enum fc_parse_status fc_els_rsp_parse(struct fchs_s *fchs, int len); +enum fc_parse_status fc_plogi_rsp_parse(struct fchs_s *fchs, int len, + wwn_t port_name); +enum fc_parse_status fc_prli_parse(struct fc_prli_s *prli); +enum fc_parse_status fc_pdisc_parse(struct fchs_s *fchs, wwn_t node_name, + wwn_t port_name); +u16 fc_ba_acc_build(struct fchs_s *fchs, struct fc_ba_acc_s *ba_acc, + u32 d_id, u32 s_id, u16 ox_id, + u16 rx_id); +int fc_logout_params_pages(struct fchs_s *fc_frame, u8 els_code); +u16 fc_tprlo_acc_build(struct fchs_s *fchs, + struct fc_tprlo_acc_s *tprlo_acc, + u32 d_id, u32 s_id, u16 ox_id, + int num_pages); +u16 fc_prlo_acc_build(struct fchs_s *fchs, struct fc_prlo_acc_s *prlo_acc, + u32 d_id, u32 s_id, u16 ox_id, + int num_pages); +u16 fc_logo_rsp_parse(struct fchs_s *fchs, int len); +u16 fc_pdisc_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id, wwn_t port_name, wwn_t node_name, + u16 pdu_size); +u16 fc_pdisc_rsp_parse(struct fchs_s *fchs, int len, wwn_t port_name); +u16 fc_prlo_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id, int num_pages); +u16 fc_prlo_rsp_parse(struct fchs_s *fchs, int len); +u16 fc_tprlo_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id, int num_pages, + enum fc_tprlo_type tprlo_type, u32 tpr_id); +u16 fc_tprlo_rsp_parse(struct fchs_s *fchs, int len); +u16 fc_ba_rjt_build(struct fchs_s *fchs, u32 d_id, u32 s_id, + u16 ox_id, u32 reason_code, + u32 reason_expl); +u16 fc_gnnid_build(struct fchs_s *fchs, void *pyld, u32 s_id, + u16 ox_id, u32 port_id); +u16 fc_ct_rsp_parse(struct ct_hdr_s *cthdr); +u16 fc_rscn_build(struct fchs_s *fchs, struct fc_rscn_pl_s *rscn, + u32 s_id, u16 ox_id); +#endif diff --git a/drivers/scsi/bfa/fcpim.c b/drivers/scsi/bfa/fcpim.c new file mode 100644 index 000000000000..8ce5d8934677 --- /dev/null +++ b/drivers/scsi/bfa/fcpim.c @@ -0,0 +1,844 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcpim.c - FCP initiator mode i-t nexus state machine + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_fcpim.h" +#include "fcs_rport.h" +#include "fcs_lport.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include "fcs.h" +#include <fcs/bfa_fcs_fcpim.h> +#include <fcb/bfa_fcb_fcpim.h> +#include <aen/bfa_aen_itnim.h> + +BFA_TRC_FILE(FCS, FCPIM); + +/* + * forward declarations + */ +static void bfa_fcs_itnim_timeout(void *arg); +static void bfa_fcs_itnim_free(struct bfa_fcs_itnim_s *itnim); +static void bfa_fcs_itnim_send_prli(void *itnim_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_itnim_prli_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_itnim_aen_post(struct bfa_fcs_itnim_s *itnim, + enum bfa_itnim_aen_event event); + +/** + * fcs_itnim_sm FCS itnim state machine events + */ + +enum bfa_fcs_itnim_event { + BFA_FCS_ITNIM_SM_ONLINE = 1, /* rport online event */ + BFA_FCS_ITNIM_SM_OFFLINE = 2, /* rport offline */ + BFA_FCS_ITNIM_SM_FRMSENT = 3, /* prli frame is sent */ + BFA_FCS_ITNIM_SM_RSP_OK = 4, /* good response */ + BFA_FCS_ITNIM_SM_RSP_ERROR = 5, /* error response */ + BFA_FCS_ITNIM_SM_TIMEOUT = 6, /* delay timeout */ + BFA_FCS_ITNIM_SM_HCB_OFFLINE = 7, /* BFA online callback */ + BFA_FCS_ITNIM_SM_HCB_ONLINE = 8, /* BFA offline callback */ + BFA_FCS_ITNIM_SM_INITIATOR = 9, /* rport is initiator */ + BFA_FCS_ITNIM_SM_DELETE = 10, /* delete event from rport */ + BFA_FCS_ITNIM_SM_PRLO = 11, /* delete event from rport */ +}; + +static void bfa_fcs_itnim_sm_offline(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); +static void bfa_fcs_itnim_sm_prli_send(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); +static void bfa_fcs_itnim_sm_prli(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); +static void bfa_fcs_itnim_sm_prli_retry(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); +static void bfa_fcs_itnim_sm_hcb_online(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); +static void bfa_fcs_itnim_sm_online(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); +static void bfa_fcs_itnim_sm_hcb_offline(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); +static void bfa_fcs_itnim_sm_initiator(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event); + +static struct bfa_sm_table_s itnim_sm_table[] = { + {BFA_SM(bfa_fcs_itnim_sm_offline), BFA_ITNIM_OFFLINE}, + {BFA_SM(bfa_fcs_itnim_sm_prli_send), BFA_ITNIM_PRLI_SEND}, + {BFA_SM(bfa_fcs_itnim_sm_prli), BFA_ITNIM_PRLI_SENT}, + {BFA_SM(bfa_fcs_itnim_sm_prli_retry), BFA_ITNIM_PRLI_RETRY}, + {BFA_SM(bfa_fcs_itnim_sm_hcb_online), BFA_ITNIM_HCB_ONLINE}, + {BFA_SM(bfa_fcs_itnim_sm_online), BFA_ITNIM_ONLINE}, + {BFA_SM(bfa_fcs_itnim_sm_hcb_offline), BFA_ITNIM_HCB_OFFLINE}, + {BFA_SM(bfa_fcs_itnim_sm_initiator), BFA_ITNIM_INITIATIOR}, +}; + +/** + * fcs_itnim_sm FCS itnim state machine + */ + +static void +bfa_fcs_itnim_sm_offline(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_ONLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_prli_send); + bfa_fcs_itnim_send_prli(itnim, NULL); + break; + + case BFA_FCS_ITNIM_SM_OFFLINE: + bfa_fcs_rport_itnim_ack(itnim->rport); + break; + + case BFA_FCS_ITNIM_SM_INITIATOR: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_initiator); + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } + +} + +static void +bfa_fcs_itnim_sm_prli_send(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_FRMSENT: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_prli); + break; + + case BFA_FCS_ITNIM_SM_INITIATOR: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_initiator); + bfa_fcxp_walloc_cancel(itnim->fcs->bfa, &itnim->fcxp_wqe); + break; + + case BFA_FCS_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcxp_walloc_cancel(itnim->fcs->bfa, &itnim->fcxp_wqe); + bfa_fcs_rport_itnim_ack(itnim->rport); + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcxp_walloc_cancel(itnim->fcs->bfa, &itnim->fcxp_wqe); + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_itnim_sm_prli(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_RSP_OK: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_hcb_online); + bfa_itnim_online(itnim->bfa_itnim, itnim->seq_rec); + break; + + case BFA_FCS_ITNIM_SM_RSP_ERROR: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_prli_retry); + bfa_timer_start(itnim->fcs->bfa, &itnim->timer, + bfa_fcs_itnim_timeout, itnim, + BFA_FCS_RETRY_TIMEOUT); + break; + + case BFA_FCS_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcxp_discard(itnim->fcxp); + bfa_fcs_rport_itnim_ack(itnim->rport); + break; + + case BFA_FCS_ITNIM_SM_INITIATOR: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_initiator); + /* + * dont discard fcxp. accept will reach same state + */ + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcxp_discard(itnim->fcxp); + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_itnim_sm_prli_retry(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_TIMEOUT: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_prli_send); + bfa_fcs_itnim_send_prli(itnim, NULL); + break; + + case BFA_FCS_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_timer_stop(&itnim->timer); + bfa_fcs_rport_itnim_ack(itnim->rport); + break; + + case BFA_FCS_ITNIM_SM_INITIATOR: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_initiator); + bfa_timer_stop(&itnim->timer); + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_timer_stop(&itnim->timer); + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_itnim_sm_hcb_online(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_HCB_ONLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_online); + bfa_fcb_itnim_online(itnim->itnim_drv); + bfa_fcs_itnim_aen_post(itnim, BFA_ITNIM_AEN_ONLINE); + break; + + case BFA_FCS_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_itnim_offline(itnim->bfa_itnim); + bfa_fcs_rport_itnim_ack(itnim->rport); + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_itnim_sm_online(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_hcb_offline); + bfa_fcb_itnim_offline(itnim->itnim_drv); + bfa_itnim_offline(itnim->bfa_itnim); + if (bfa_fcs_port_is_online(itnim->rport->port) == BFA_TRUE) { + bfa_fcs_itnim_aen_post(itnim, BFA_ITNIM_AEN_DISCONNECT); + } else { + bfa_fcs_itnim_aen_post(itnim, BFA_ITNIM_AEN_OFFLINE); + } + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_itnim_sm_hcb_offline(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_HCB_OFFLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcs_rport_itnim_ack(itnim->rport); + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } +} + +/* + * This state is set when a discovered rport is also in intiator mode. + * This ITN is marked as no_op and is not active and will not be truned into + * online state. + */ +static void +bfa_fcs_itnim_sm_initiator(struct bfa_fcs_itnim_s *itnim, + enum bfa_fcs_itnim_event event) +{ + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_trc(itnim->fcs, event); + + switch (event) { + case BFA_FCS_ITNIM_SM_OFFLINE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcs_rport_itnim_ack(itnim->rport); + break; + + case BFA_FCS_ITNIM_SM_RSP_ERROR: + case BFA_FCS_ITNIM_SM_ONLINE: + case BFA_FCS_ITNIM_SM_INITIATOR: + break; + + case BFA_FCS_ITNIM_SM_DELETE: + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + bfa_fcs_itnim_free(itnim); + break; + + default: + bfa_assert(0); + } +} + + + +/** + * itnim_private FCS ITNIM private interfaces + */ + +static void +bfa_fcs_itnim_aen_post(struct bfa_fcs_itnim_s *itnim, + enum bfa_itnim_aen_event event) +{ + struct bfa_fcs_rport_s *rport = itnim->rport; + union bfa_aen_data_u aen_data; + struct bfa_log_mod_s *logmod = rport->fcs->logm; + wwn_t lpwwn = bfa_fcs_port_get_pwwn(rport->port); + wwn_t rpwwn = rport->pwwn; + char lpwwn_ptr[BFA_STRING_32]; + char rpwwn_ptr[BFA_STRING_32]; + + /* + * Don't post events for well known addresses + */ + if (BFA_FCS_PID_IS_WKA(rport->pid)) + return; + + wwn2str(lpwwn_ptr, lpwwn); + wwn2str(rpwwn_ptr, rpwwn); + + switch (event) { + case BFA_ITNIM_AEN_ONLINE: + bfa_log(logmod, BFA_AEN_ITNIM_ONLINE, rpwwn_ptr, lpwwn_ptr); + break; + case BFA_ITNIM_AEN_OFFLINE: + bfa_log(logmod, BFA_AEN_ITNIM_OFFLINE, rpwwn_ptr, lpwwn_ptr); + break; + case BFA_ITNIM_AEN_DISCONNECT: + bfa_log(logmod, BFA_AEN_ITNIM_DISCONNECT, rpwwn_ptr, lpwwn_ptr); + break; + default: + break; + } + + aen_data.itnim.vf_id = rport->port->fabric->vf_id; + aen_data.itnim.ppwwn = + bfa_fcs_port_get_pwwn(bfa_fcs_get_base_port(itnim->fcs)); + aen_data.itnim.lpwwn = lpwwn; + aen_data.itnim.rpwwn = rpwwn; +} + +static void +bfa_fcs_itnim_send_prli(void *itnim_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_itnim_s *itnim = itnim_cbarg; + struct bfa_fcs_rport_s *rport = itnim->rport; + struct bfa_fcs_port_s *port = rport->port; + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + int len; + + bfa_trc(itnim->fcs, itnim->rport->pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + itnim->stats.fcxp_alloc_wait++; + bfa_fcxp_alloc_wait(port->fcs->bfa, &itnim->fcxp_wqe, + bfa_fcs_itnim_send_prli, itnim); + return; + } + itnim->fcxp = fcxp; + + len = fc_prli_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), itnim->rport->pid, + bfa_fcs_port_get_fcid(port), 0); + + bfa_fcxp_send(fcxp, rport->bfa_rport, port->fabric->vf_id, port->lp_tag, + BFA_FALSE, FC_CLASS_3, len, &fchs, + bfa_fcs_itnim_prli_response, (void *)itnim, FC_MAX_PDUSZ, + FC_RA_TOV); + + itnim->stats.prli_sent++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_FRMSENT); +} + +static void +bfa_fcs_itnim_prli_response(void *fcsarg, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_itnim_s *itnim = (struct bfa_fcs_itnim_s *)cbarg; + struct fc_els_cmd_s *els_cmd; + struct fc_prli_s *prli_resp; + struct fc_ls_rjt_s *ls_rjt; + struct fc_prli_params_s *sparams; + + bfa_trc(itnim->fcs, req_status); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + itnim->stats.prli_rsp_err++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_RSP_ERROR); + return; + } + + els_cmd = (struct fc_els_cmd_s *) BFA_FCXP_RSP_PLD(fcxp); + + if (els_cmd->els_code == FC_ELS_ACC) { + prli_resp = (struct fc_prli_s *) els_cmd; + + if (fc_prli_rsp_parse(prli_resp, rsp_len) != FC_PARSE_OK) { + bfa_trc(itnim->fcs, rsp_len); + /* + * Check if this r-port is also in Initiator mode. + * If so, we need to set this ITN as a no-op. + */ + if (prli_resp->parampage.servparams.initiator) { + bfa_trc(itnim->fcs, prli_resp->parampage.type); + itnim->rport->scsi_function = + BFA_RPORT_INITIATOR; + itnim->stats.prli_rsp_acc++; + bfa_sm_send_event(itnim, + BFA_FCS_ITNIM_SM_INITIATOR); + return; + } + + itnim->stats.prli_rsp_parse_err++; + return; + } + itnim->rport->scsi_function = BFA_RPORT_TARGET; + + sparams = &prli_resp->parampage.servparams; + itnim->seq_rec = sparams->retry; + itnim->rec_support = sparams->rec_support; + itnim->task_retry_id = sparams->task_retry_id; + itnim->conf_comp = sparams->confirm; + + itnim->stats.prli_rsp_acc++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_RSP_OK); + } else { + ls_rjt = (struct fc_ls_rjt_s *) BFA_FCXP_RSP_PLD(fcxp); + + bfa_trc(itnim->fcs, ls_rjt->reason_code); + bfa_trc(itnim->fcs, ls_rjt->reason_code_expl); + + itnim->stats.prli_rsp_rjt++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_RSP_ERROR); + } +} + +static void +bfa_fcs_itnim_timeout(void *arg) +{ + struct bfa_fcs_itnim_s *itnim = (struct bfa_fcs_itnim_s *)arg; + + itnim->stats.timeout++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_TIMEOUT); +} + +static void +bfa_fcs_itnim_free(struct bfa_fcs_itnim_s *itnim) +{ + bfa_itnim_delete(itnim->bfa_itnim); + bfa_fcb_itnim_free(itnim->fcs->bfad, itnim->itnim_drv); +} + + + +/** + * itnim_public FCS ITNIM public interfaces + */ + +/** + * Called by rport when a new rport is created. + * + * @param[in] rport - remote port. + */ +struct bfa_fcs_itnim_s * +bfa_fcs_itnim_create(struct bfa_fcs_rport_s *rport) +{ + struct bfa_fcs_port_s *port = rport->port; + struct bfa_fcs_itnim_s *itnim; + struct bfad_itnim_s *itnim_drv; + struct bfa_itnim_s *bfa_itnim; + + /* + * call bfad to allocate the itnim + */ + bfa_fcb_itnim_alloc(port->fcs->bfad, &itnim, &itnim_drv); + if (itnim == NULL) { + bfa_trc(port->fcs, rport->pwwn); + return NULL; + } + + /* + * Initialize itnim + */ + itnim->rport = rport; + itnim->fcs = rport->fcs; + itnim->itnim_drv = itnim_drv; + + /* + * call BFA to create the itnim + */ + bfa_itnim = bfa_itnim_create(port->fcs->bfa, rport->bfa_rport, itnim); + + if (bfa_itnim == NULL) { + bfa_trc(port->fcs, rport->pwwn); + bfa_fcb_itnim_free(port->fcs->bfad, itnim_drv); + bfa_assert(0); + return NULL; + } + + itnim->bfa_itnim = bfa_itnim; + itnim->seq_rec = BFA_FALSE; + itnim->rec_support = BFA_FALSE; + itnim->conf_comp = BFA_FALSE; + itnim->task_retry_id = BFA_FALSE; + + /* + * Set State machine + */ + bfa_sm_set_state(itnim, bfa_fcs_itnim_sm_offline); + + return itnim; +} + +/** + * Called by rport to delete the instance of FCPIM. + * + * @param[in] rport - remote port. + */ +void +bfa_fcs_itnim_delete(struct bfa_fcs_itnim_s *itnim) +{ + bfa_trc(itnim->fcs, itnim->rport->pid); + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_DELETE); +} + +/** + * Notification from rport that PLOGI is complete to initiate FC-4 session. + */ +void +bfa_fcs_itnim_rport_online(struct bfa_fcs_itnim_s *itnim) +{ + itnim->stats.onlines++; + + if (!BFA_FCS_PID_IS_WKA(itnim->rport->pid)) { + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_ONLINE); + } else { + /* + * For well known addresses, we set the itnim to initiator + * state + */ + itnim->stats.initiator++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_INITIATOR); + } +} + +/** + * Called by rport to handle a remote device offline. + */ +void +bfa_fcs_itnim_rport_offline(struct bfa_fcs_itnim_s *itnim) +{ + itnim->stats.offlines++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_OFFLINE); +} + +/** + * Called by rport when remote port is known to be an initiator from + * PRLI received. + */ +void +bfa_fcs_itnim_is_initiator(struct bfa_fcs_itnim_s *itnim) +{ + bfa_trc(itnim->fcs, itnim->rport->pid); + itnim->stats.initiator++; + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_INITIATOR); +} + +/** + * Called by rport to check if the itnim is online. + */ +bfa_status_t +bfa_fcs_itnim_get_online_state(struct bfa_fcs_itnim_s *itnim) +{ + bfa_trc(itnim->fcs, itnim->rport->pid); + switch (bfa_sm_to_state(itnim_sm_table, itnim->sm)) { + case BFA_ITNIM_ONLINE: + case BFA_ITNIM_INITIATIOR: + return BFA_STATUS_OK; + + default: + return BFA_STATUS_NO_FCPIM_NEXUS; + + } +} + +/** + * BFA completion callback for bfa_itnim_online(). + */ +void +bfa_cb_itnim_online(void *cbarg) +{ + struct bfa_fcs_itnim_s *itnim = (struct bfa_fcs_itnim_s *)cbarg; + + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_HCB_ONLINE); +} + +/** + * BFA completion callback for bfa_itnim_offline(). + */ +void +bfa_cb_itnim_offline(void *cb_arg) +{ + struct bfa_fcs_itnim_s *itnim = (struct bfa_fcs_itnim_s *)cb_arg; + + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_HCB_OFFLINE); +} + +/** + * Mark the beginning of PATH TOV handling. IO completion callbacks + * are still pending. + */ +void +bfa_cb_itnim_tov_begin(void *cb_arg) +{ + struct bfa_fcs_itnim_s *itnim = (struct bfa_fcs_itnim_s *)cb_arg; + + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_fcb_itnim_tov_begin(itnim->itnim_drv); +} + +/** + * Mark the end of PATH TOV handling. All pending IOs are already cleaned up. + */ +void +bfa_cb_itnim_tov(void *cb_arg) +{ + struct bfa_fcs_itnim_s *itnim = (struct bfa_fcs_itnim_s *)cb_arg; + + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_fcb_itnim_tov(itnim->itnim_drv); +} + +/** + * BFA notification to FCS/driver for second level error recovery. + * + * Atleast one I/O request has timedout and target is unresponsive to + * repeated abort requests. Second level error recovery should be initiated + * by starting implicit logout and recovery procedures. + */ +void +bfa_cb_itnim_sler(void *cb_arg) +{ + struct bfa_fcs_itnim_s *itnim = (struct bfa_fcs_itnim_s *)cb_arg; + + itnim->stats.sler++; + bfa_trc(itnim->fcs, itnim->rport->pwwn); + bfa_fcs_rport_logo_imp(itnim->rport); +} + +struct bfa_fcs_itnim_s * +bfa_fcs_itnim_lookup(struct bfa_fcs_port_s *port, wwn_t rpwwn) +{ + struct bfa_fcs_rport_s *rport; + rport = bfa_fcs_rport_lookup(port, rpwwn); + + if (!rport) + return NULL; + + bfa_assert(rport->itnim != NULL); + return (rport->itnim); +} + +bfa_status_t +bfa_fcs_itnim_attr_get(struct bfa_fcs_port_s *port, wwn_t rpwwn, + struct bfa_itnim_attr_s *attr) +{ + struct bfa_fcs_itnim_s *itnim = NULL; + + itnim = bfa_fcs_itnim_lookup(port, rpwwn); + + if (itnim == NULL) + return BFA_STATUS_NO_FCPIM_NEXUS; + + attr->state = bfa_sm_to_state(itnim_sm_table, itnim->sm); + attr->retry = itnim->seq_rec; + attr->rec_support = itnim->rec_support; + attr->conf_comp = itnim->conf_comp; + attr->task_retry_id = itnim->task_retry_id; + + return BFA_STATUS_OK; +} + +bfa_status_t +bfa_fcs_itnim_stats_get(struct bfa_fcs_port_s *port, wwn_t rpwwn, + struct bfa_itnim_stats_s *stats) +{ + struct bfa_fcs_itnim_s *itnim = NULL; + + bfa_assert(port != NULL); + + itnim = bfa_fcs_itnim_lookup(port, rpwwn); + + if (itnim == NULL) + return BFA_STATUS_NO_FCPIM_NEXUS; + + bfa_os_memcpy(stats, &itnim->stats, sizeof(struct bfa_itnim_stats_s)); + + return BFA_STATUS_OK; +} + +bfa_status_t +bfa_fcs_itnim_stats_clear(struct bfa_fcs_port_s *port, wwn_t rpwwn) +{ + struct bfa_fcs_itnim_s *itnim = NULL; + + bfa_assert(port != NULL); + + itnim = bfa_fcs_itnim_lookup(port, rpwwn); + + if (itnim == NULL) + return BFA_STATUS_NO_FCPIM_NEXUS; + + bfa_os_memset(&itnim->stats, 0, sizeof(struct bfa_itnim_stats_s)); + return BFA_STATUS_OK; +} + +void +bfa_fcs_fcpim_uf_recv(struct bfa_fcs_itnim_s *itnim, struct fchs_s *fchs, + u16 len) +{ + struct fc_els_cmd_s *els_cmd; + + bfa_trc(itnim->fcs, fchs->type); + + if (fchs->type != FC_TYPE_ELS) + return; + + els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + + bfa_trc(itnim->fcs, els_cmd->els_code); + + switch (els_cmd->els_code) { + case FC_ELS_PRLO: + /* bfa_sm_send_event(itnim, BFA_FCS_ITNIM_SM_PRLO); */ + break; + + default: + bfa_assert(0); + } +} + +void +bfa_fcs_itnim_pause(struct bfa_fcs_itnim_s *itnim) +{ +} + +void +bfa_fcs_itnim_resume(struct bfa_fcs_itnim_s *itnim) +{ +} + +/** + * Module initialization + */ +void +bfa_fcs_fcpim_modinit(struct bfa_fcs_s *fcs) +{ +} + +/** + * Module cleanup + */ +void +bfa_fcs_fcpim_modexit(struct bfa_fcs_s *fcs) +{ + bfa_fcs_modexit_comp(fcs); +} + + diff --git a/drivers/scsi/bfa/fcptm.c b/drivers/scsi/bfa/fcptm.c new file mode 100644 index 000000000000..8c8b08c72e7a --- /dev/null +++ b/drivers/scsi/bfa/fcptm.c @@ -0,0 +1,68 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * This file contains dummy FCPTM routines to aid in Initiator Mode only + * compilation of OS driver. + * + */ + +#include "bfa_os_inc.h" +#include "fcs_rport.h" +#include "fcs_fcptm.h" +#include "fcs/bfa_fcs_rport.h" + +struct bfa_fcs_tin_s * +bfa_fcs_tin_create(struct bfa_fcs_rport_s *rport) +{ + return NULL; +} + +void +bfa_fcs_tin_delete(struct bfa_fcs_tin_s *tin) +{ +} + +void +bfa_fcs_tin_rport_offline(struct bfa_fcs_tin_s *tin) +{ +} + +void +bfa_fcs_tin_rport_online(struct bfa_fcs_tin_s *tin) +{ +} + +void +bfa_fcs_tin_rx_prli(struct bfa_fcs_tin_s *tin, struct fchs_s *fchs, u16 len) +{ +} + +void +bfa_fcs_fcptm_uf_recv(struct bfa_fcs_tin_s *tin, struct fchs_s *fchs, u16 len) +{ +} + +void +bfa_fcs_tin_pause(struct bfa_fcs_tin_s *tin) +{ +} + +void +bfa_fcs_tin_resume(struct bfa_fcs_tin_s *tin) +{ +} diff --git a/drivers/scsi/bfa/fcs.h b/drivers/scsi/bfa/fcs.h new file mode 100644 index 000000000000..deee685e8478 --- /dev/null +++ b/drivers/scsi/bfa/fcs.h @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs.h FCS module functions + */ + + +#ifndef __FCS_H__ +#define __FCS_H__ + +#define __fcs_min_cfg(__fcs) (__fcs)->min_cfg + +void bfa_fcs_modexit_comp(struct bfa_fcs_s *fcs); + +#endif /* __FCS_H__ */ diff --git a/drivers/scsi/bfa/fcs_auth.h b/drivers/scsi/bfa/fcs_auth.h new file mode 100644 index 000000000000..65d155fea3d7 --- /dev/null +++ b/drivers/scsi/bfa/fcs_auth.h @@ -0,0 +1,37 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_uf.h FCS unsolicited frame receive + */ + + +#ifndef __FCS_AUTH_H__ +#define __FCS_AUTH_H__ + +#include <fcs/bfa_fcs.h> +#include <fcs/bfa_fcs_vport.h> +#include <fcs/bfa_fcs_lport.h> + +/* + * fcs friend functions: only between fcs modules + */ +void bfa_fcs_auth_uf_recv(struct bfa_fcs_fabric_s *fabric, int len); +void bfa_fcs_auth_start(struct bfa_fcs_fabric_s *fabric); +void bfa_fcs_auth_stop(struct bfa_fcs_fabric_s *fabric); + +#endif /* __FCS_UF_H__ */ diff --git a/drivers/scsi/bfa/fcs_fabric.h b/drivers/scsi/bfa/fcs_fabric.h new file mode 100644 index 000000000000..eee960820f86 --- /dev/null +++ b/drivers/scsi/bfa/fcs_fabric.h @@ -0,0 +1,61 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_lport.h FCS logical port interfaces + */ + +#ifndef __FCS_FABRIC_H__ +#define __FCS_FABRIC_H__ + +#include <fcs/bfa_fcs.h> +#include <fcs/bfa_fcs_vport.h> +#include <fcs/bfa_fcs_lport.h> + +/* +* fcs friend functions: only between fcs modules + */ +void bfa_fcs_fabric_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_fabric_modexit(struct bfa_fcs_s *fcs); +void bfa_fcs_fabric_modsusp(struct bfa_fcs_s *fcs); +void bfa_fcs_fabric_link_up(struct bfa_fcs_fabric_s *fabric); +void bfa_fcs_fabric_link_down(struct bfa_fcs_fabric_s *fabric); +void bfa_fcs_fabric_addvport(struct bfa_fcs_fabric_s *fabric, + struct bfa_fcs_vport_s *vport); +void bfa_fcs_fabric_delvport(struct bfa_fcs_fabric_s *fabric, + struct bfa_fcs_vport_s *vport); +int bfa_fcs_fabric_is_online(struct bfa_fcs_fabric_s *fabric); +struct bfa_fcs_vport_s *bfa_fcs_fabric_vport_lookup( + struct bfa_fcs_fabric_s *fabric, wwn_t pwwn); +void bfa_fcs_fabric_modstart(struct bfa_fcs_s *fcs); +void bfa_fcs_fabric_uf_recv(struct bfa_fcs_fabric_s *fabric, + struct fchs_s *fchs, u16 len); +u16 bfa_fcs_fabric_vport_count(struct bfa_fcs_fabric_s *fabric); +bfa_boolean_t bfa_fcs_fabric_is_loopback(struct bfa_fcs_fabric_s *fabric); +enum bfa_pport_type bfa_fcs_fabric_port_type(struct bfa_fcs_fabric_s *fabric); +void bfa_fcs_fabric_psymb_init(struct bfa_fcs_fabric_s *fabric); +void bfa_fcs_fabric_port_delete_comp(struct bfa_fcs_fabric_s *fabric); + +bfa_status_t bfa_fcs_fabric_addvf(struct bfa_fcs_fabric_s *vf, + struct bfa_fcs_s *fcs, struct bfa_port_cfg_s *port_cfg, + struct bfad_vf_s *vf_drv); +void bfa_fcs_auth_finished(struct bfa_fcs_fabric_s *fabric, + enum auth_status status); + +void bfa_fcs_fabric_set_fabric_name(struct bfa_fcs_fabric_s *fabric, + wwn_t fabric_name); +#endif /* __FCS_FABRIC_H__ */ diff --git a/drivers/scsi/bfa/fcs_fcpim.h b/drivers/scsi/bfa/fcs_fcpim.h new file mode 100644 index 000000000000..61e9e2687de3 --- /dev/null +++ b/drivers/scsi/bfa/fcs_fcpim.h @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __FCS_FCPIM_H__ +#define __FCS_FCPIM_H__ + +#include <defs/bfa_defs_port.h> +#include <fcs/bfa_fcs_lport.h> +#include <fcs/bfa_fcs_rport.h> + +/* + * Following routines are from FCPIM and will be called by rport. + */ +struct bfa_fcs_itnim_s *bfa_fcs_itnim_create(struct bfa_fcs_rport_s *rport); +void bfa_fcs_itnim_delete(struct bfa_fcs_itnim_s *itnim); +void bfa_fcs_itnim_rport_offline(struct bfa_fcs_itnim_s *itnim); +void bfa_fcs_itnim_rport_online(struct bfa_fcs_itnim_s *itnim); +bfa_status_t bfa_fcs_itnim_get_online_state(struct bfa_fcs_itnim_s *itnim); + +void bfa_fcs_itnim_is_initiator(struct bfa_fcs_itnim_s *itnim); +void bfa_fcs_itnim_pause(struct bfa_fcs_itnim_s *itnim); +void bfa_fcs_itnim_resume(struct bfa_fcs_itnim_s *itnim); + +/* + * Modudle init/cleanup routines. + */ +void bfa_fcs_fcpim_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_fcpim_modexit(struct bfa_fcs_s *fcs); +void bfa_fcs_fcpim_uf_recv(struct bfa_fcs_itnim_s *itnim, struct fchs_s *fchs, + u16 len); +#endif /* __FCS_FCPIM_H__ */ diff --git a/drivers/scsi/bfa/fcs_fcptm.h b/drivers/scsi/bfa/fcs_fcptm.h new file mode 100644 index 000000000000..ffff0829fd31 --- /dev/null +++ b/drivers/scsi/bfa/fcs_fcptm.h @@ -0,0 +1,45 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __FCS_FCPTM_H__ +#define __FCS_FCPTM_H__ + +#include <defs/bfa_defs_port.h> +#include <fcs/bfa_fcs_lport.h> +#include <fcs/bfa_fcs_rport.h> + +/* + * Following routines are from FCPTM and will be called by rport. + */ +struct bfa_fcs_tin_s *bfa_fcs_tin_create(struct bfa_fcs_rport_s *rport); +void bfa_fcs_tin_rport_offline(struct bfa_fcs_tin_s *tin); +void bfa_fcs_tin_rport_online(struct bfa_fcs_tin_s *tin); +void bfa_fcs_tin_delete(struct bfa_fcs_tin_s *tin); +void bfa_fcs_tin_rx_prli(struct bfa_fcs_tin_s *tin, struct fchs_s *fchs, + u16 len); +void bfa_fcs_tin_pause(struct bfa_fcs_tin_s *tin); +void bfa_fcs_tin_resume(struct bfa_fcs_tin_s *tin); + +/* + * Modudle init/cleanup routines. + */ +void bfa_fcs_fcptm_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_fcptm_modexit(struct bfa_fcs_s *fcs); +void bfa_fcs_fcptm_uf_recv(struct bfa_fcs_tin_s *tin, struct fchs_s *fchs, + u16 len); + +#endif /* __FCS_FCPTM_H__ */ diff --git a/drivers/scsi/bfa/fcs_fcxp.h b/drivers/scsi/bfa/fcs_fcxp.h new file mode 100644 index 000000000000..8277fe9c2b70 --- /dev/null +++ b/drivers/scsi/bfa/fcs_fcxp.h @@ -0,0 +1,29 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_fcxp.h FCXP helper macros for FCS + */ + + +#ifndef __FCS_FCXP_H__ +#define __FCS_FCXP_H__ + +#define bfa_fcs_fcxp_alloc(__fcs) \ + bfa_fcxp_alloc(NULL, (__fcs)->bfa, 0, 0, NULL, NULL, NULL, NULL) + +#endif /* __FCS_FCXP_H__ */ diff --git a/drivers/scsi/bfa/fcs_lport.h b/drivers/scsi/bfa/fcs_lport.h new file mode 100644 index 000000000000..ae744ba35671 --- /dev/null +++ b/drivers/scsi/bfa/fcs_lport.h @@ -0,0 +1,117 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_lport.h FCS logical port interfaces + */ + +#ifndef __FCS_LPORT_H__ +#define __FCS_LPORT_H__ + +#define __VPORT_H__ +#include <defs/bfa_defs_port.h> +#include <bfa_svc.h> +#include <fcs/bfa_fcs_lport.h> +#include <fcs/bfa_fcs_rport.h> +#include <fcs/bfa_fcs_vport.h> +#include <fcs_fabric.h> +#include <fcs_ms.h> +#include <cs/bfa_q.h> +#include <fcbuild.h> + +/* + * PID used in P2P/N2N ( In Big Endian) + */ +#define N2N_LOCAL_PID 0x010000 +#define N2N_REMOTE_PID 0x020000 + +/* + * Misc Timeouts + */ +/* + * To be used when spawning a timer before retrying a failed command. Milli + * Secs. + */ +#define BFA_FCS_RETRY_TIMEOUT 2000 + +/* + * Check for Port/Vport Mode/Role + */ +#define BFA_FCS_VPORT_IS_INITIATOR_MODE(port) \ + (port->port_cfg.roles & BFA_PORT_ROLE_FCP_IM) + +#define BFA_FCS_VPORT_IS_TARGET_MODE(port) \ + (port->port_cfg.roles & BFA_PORT_ROLE_FCP_TM) + +#define BFA_FCS_VPORT_IS_IPFC_MODE(port) \ + (port->port_cfg.roles & BFA_PORT_ROLE_FCP_IPFC) + +/* + * Is this a Well Known Address + */ +#define BFA_FCS_PID_IS_WKA(pid) ((bfa_os_ntoh3b(pid) > 0xFFF000) ? 1 : 0) + +/* + * Pointer to elements within Port + */ +#define BFA_FCS_GET_HAL_FROM_PORT(port) (port->fcs->bfa) +#define BFA_FCS_GET_NS_FROM_PORT(port) (&port->port_topo.pfab.ns) +#define BFA_FCS_GET_SCN_FROM_PORT(port) (&port->port_topo.pfab.scn) +#define BFA_FCS_GET_MS_FROM_PORT(port) (&port->port_topo.pfab.ms) +#define BFA_FCS_GET_FDMI_FROM_PORT(port) (&port->port_topo.pfab.ms.fdmi) + +/* + * handler for unsolicied frames + */ +void bfa_fcs_port_uf_recv(struct bfa_fcs_port_s *lport, struct fchs_s *fchs, + u16 len); + +/* + * Following routines will be called by Fabric to indicate port + * online/offline to vport. + */ +void bfa_fcs_lport_init(struct bfa_fcs_port_s *lport, struct bfa_fcs_s *fcs, + u16 vf_id, struct bfa_port_cfg_s *port_cfg, + struct bfa_fcs_vport_s *vport); +void bfa_fcs_port_online(struct bfa_fcs_port_s *port); +void bfa_fcs_port_offline(struct bfa_fcs_port_s *port); +void bfa_fcs_port_delete(struct bfa_fcs_port_s *port); +bfa_boolean_t bfa_fcs_port_is_online(struct bfa_fcs_port_s *port); + +/* + * Lookup rport based on PID + */ +struct bfa_fcs_rport_s *bfa_fcs_port_get_rport_by_pid( + struct bfa_fcs_port_s *port, u32 pid); + +/* + * Lookup rport based on PWWN + */ +struct bfa_fcs_rport_s *bfa_fcs_port_get_rport_by_pwwn( + struct bfa_fcs_port_s *port, wwn_t pwwn); +struct bfa_fcs_rport_s *bfa_fcs_port_get_rport_by_nwwn( + struct bfa_fcs_port_s *port, wwn_t nwwn); +void bfa_fcs_port_add_rport(struct bfa_fcs_port_s *port, + struct bfa_fcs_rport_s *rport); +void bfa_fcs_port_del_rport(struct bfa_fcs_port_s *port, + struct bfa_fcs_rport_s *rport); + +void bfa_fcs_port_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_port_modexit(struct bfa_fcs_s *fcs); +void bfa_fcs_port_lip(struct bfa_fcs_port_s *port); + +#endif /* __FCS_LPORT_H__ */ diff --git a/drivers/scsi/bfa/fcs_ms.h b/drivers/scsi/bfa/fcs_ms.h new file mode 100644 index 000000000000..b6a8c12876f4 --- /dev/null +++ b/drivers/scsi/bfa/fcs_ms.h @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_ms.h FCS ms interfaces + */ +#ifndef __FCS_MS_H__ +#define __FCS_MS_H__ + +/* MS FCS routines */ +void bfa_fcs_port_ms_init(struct bfa_fcs_port_s *port); +void bfa_fcs_port_ms_offline(struct bfa_fcs_port_s *port); +void bfa_fcs_port_ms_online(struct bfa_fcs_port_s *port); +void bfa_fcs_port_ms_fabric_rscn(struct bfa_fcs_port_s *port); + +/* FDMI FCS routines */ +void bfa_fcs_port_fdmi_init(struct bfa_fcs_port_ms_s *ms); +void bfa_fcs_port_fdmi_offline(struct bfa_fcs_port_ms_s *ms); +void bfa_fcs_port_fdmi_online(struct bfa_fcs_port_ms_s *ms); + +#endif diff --git a/drivers/scsi/bfa/fcs_port.h b/drivers/scsi/bfa/fcs_port.h new file mode 100644 index 000000000000..abb65191dd27 --- /dev/null +++ b/drivers/scsi/bfa/fcs_port.h @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_pport.h FCS physical port interfaces + */ + + +#ifndef __FCS_PPORT_H__ +#define __FCS_PPORT_H__ + +/* + * fcs friend functions: only between fcs modules + */ +void bfa_fcs_pport_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_pport_modexit(struct bfa_fcs_s *fcs); + +#endif /* __FCS_PPORT_H__ */ diff --git a/drivers/scsi/bfa/fcs_rport.h b/drivers/scsi/bfa/fcs_rport.h new file mode 100644 index 000000000000..f601e9d74236 --- /dev/null +++ b/drivers/scsi/bfa/fcs_rport.h @@ -0,0 +1,61 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_rport.h FCS rport interfaces and defines + */ + +#ifndef __FCS_RPORT_H__ +#define __FCS_RPORT_H__ + +#include <fcs/bfa_fcs_rport.h> + +void bfa_fcs_rport_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_rport_modexit(struct bfa_fcs_s *fcs); + +void bfa_fcs_rport_uf_recv(struct bfa_fcs_rport_s *rport, struct fchs_s *fchs, + u16 len); +void bfa_fcs_rport_scn(struct bfa_fcs_rport_s *rport); + +struct bfa_fcs_rport_s *bfa_fcs_rport_create(struct bfa_fcs_port_s *port, + u32 pid); +void bfa_fcs_rport_delete(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_online(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_offline(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_start(struct bfa_fcs_port_s *port, struct fchs_s *rx_fchs, + struct fc_logi_s *plogi_rsp); +void bfa_fcs_rport_plogi_create(struct bfa_fcs_port_s *port, + struct fchs_s *rx_fchs, + struct fc_logi_s *plogi); +void bfa_fcs_rport_plogi(struct bfa_fcs_rport_s *rport, struct fchs_s *fchs, + struct fc_logi_s *plogi); +void bfa_fcs_rport_logo_imp(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_itnim_ack(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_itntm_ack(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_tin_ack(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_fcptm_offline_done(struct bfa_fcs_rport_s *rport); +int bfa_fcs_rport_get_state(struct bfa_fcs_rport_s *rport); +struct bfa_fcs_rport_s *bfa_fcs_rport_create_by_wwn(struct bfa_fcs_port_s *port, + wwn_t wwn); + + +/* Rport Features */ +void bfa_fcs_rpf_init(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rpf_rport_online(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rpf_rport_offline(struct bfa_fcs_rport_s *rport); + +#endif /* __FCS_RPORT_H__ */ diff --git a/drivers/scsi/bfa/fcs_trcmod.h b/drivers/scsi/bfa/fcs_trcmod.h new file mode 100644 index 000000000000..41b5ae8d7644 --- /dev/null +++ b/drivers/scsi/bfa/fcs_trcmod.h @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_trcmod.h BFA FCS trace modules + */ + +#ifndef __FCS_TRCMOD_H__ +#define __FCS_TRCMOD_H__ + +#include <cs/bfa_trc.h> + +/* + * !!! Only append to the enums defined here to avoid any versioning + * !!! needed between trace utility and driver version + */ +enum { + BFA_TRC_FCS_FABRIC = 1, + BFA_TRC_FCS_VFAPI = 2, + BFA_TRC_FCS_PORT = 3, + BFA_TRC_FCS_VPORT = 4, + BFA_TRC_FCS_VP_API = 5, + BFA_TRC_FCS_VPS = 6, + BFA_TRC_FCS_RPORT = 7, + BFA_TRC_FCS_FCPIM = 8, + BFA_TRC_FCS_FCPTM = 9, + BFA_TRC_FCS_NS = 10, + BFA_TRC_FCS_SCN = 11, + BFA_TRC_FCS_LOOP = 12, + BFA_TRC_FCS_UF = 13, + BFA_TRC_FCS_PPORT = 14, + BFA_TRC_FCS_FCPIP = 15, + BFA_TRC_FCS_PORT_API = 16, + BFA_TRC_FCS_RPORT_API = 17, + BFA_TRC_FCS_AUTH = 18, + BFA_TRC_FCS_N2N = 19, + BFA_TRC_FCS_MS = 20, + BFA_TRC_FCS_FDMI = 21, + BFA_TRC_FCS_RPORT_FTRS = 22, +}; + +#endif /* __FCS_TRCMOD_H__ */ diff --git a/drivers/scsi/bfa/fcs_uf.h b/drivers/scsi/bfa/fcs_uf.h new file mode 100644 index 000000000000..96f1bdcb31ed --- /dev/null +++ b/drivers/scsi/bfa/fcs_uf.h @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * fcs_uf.h FCS unsolicited frame receive + */ + + +#ifndef __FCS_UF_H__ +#define __FCS_UF_H__ + +/* + * fcs friend functions: only between fcs modules + */ +void bfa_fcs_uf_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_uf_modexit(struct bfa_fcs_s *fcs); + +#endif /* __FCS_UF_H__ */ diff --git a/drivers/scsi/bfa/fcs_vport.h b/drivers/scsi/bfa/fcs_vport.h new file mode 100644 index 000000000000..9e80b6a97b7f --- /dev/null +++ b/drivers/scsi/bfa/fcs_vport.h @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __FCS_VPORT_H__ +#define __FCS_VPORT_H__ + +#include <fcs/bfa_fcs_lport.h> +#include <fcs/bfa_fcs_vport.h> +#include <defs/bfa_defs_pci.h> + +/* + * Modudle init/cleanup routines. + */ + +void bfa_fcs_vport_modinit(struct bfa_fcs_s *fcs); +void bfa_fcs_vport_modexit(struct bfa_fcs_s *fcs); + +void bfa_fcs_vport_cleanup(struct bfa_fcs_vport_s *vport); +void bfa_fcs_vport_online(struct bfa_fcs_vport_s *vport); +void bfa_fcs_vport_offline(struct bfa_fcs_vport_s *vport); +void bfa_fcs_vport_delete_comp(struct bfa_fcs_vport_s *vport); +u32 bfa_fcs_vport_get_max(struct bfa_fcs_s *fcs); + +#endif /* __FCS_VPORT_H__ */ + diff --git a/drivers/scsi/bfa/fdmi.c b/drivers/scsi/bfa/fdmi.c new file mode 100644 index 000000000000..b845eb272c78 --- /dev/null +++ b/drivers/scsi/bfa/fdmi.c @@ -0,0 +1,1223 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * port_api.c BFA FCS port + */ + + +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "lport_priv.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include <fcs/bfa_fcs_fdmi.h> + +BFA_TRC_FILE(FCS, FDMI); + +#define BFA_FCS_FDMI_CMD_MAX_RETRIES 2 + +/* + * forward declarations + */ +static void bfa_fcs_port_fdmi_send_rhba(void *fdmi_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_fdmi_send_rprt(void *fdmi_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_fdmi_send_rpa(void *fdmi_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_fdmi_rhba_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_fdmi_rprt_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_fdmi_rpa_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_fdmi_timeout(void *arg); +static u16 bfa_fcs_port_fdmi_build_rhba_pyld( + struct bfa_fcs_port_fdmi_s *fdmi, u8 *pyld); +static u16 bfa_fcs_port_fdmi_build_rprt_pyld( + struct bfa_fcs_port_fdmi_s *fdmi, u8 *pyld); +static u16 bfa_fcs_port_fdmi_build_rpa_pyld( + struct bfa_fcs_port_fdmi_s *fdmi, u8 *pyld); +static u16 bfa_fcs_port_fdmi_build_portattr_block( + struct bfa_fcs_port_fdmi_s *fdmi, u8 *pyld); +void bfa_fcs_fdmi_get_hbaattr(struct bfa_fcs_port_fdmi_s *fdmi, + struct bfa_fcs_fdmi_hba_attr_s *hba_attr); +void bfa_fcs_fdmi_get_portattr(struct bfa_fcs_port_fdmi_s *fdmi, + struct bfa_fcs_fdmi_port_attr_s *port_attr); +/** + * fcs_fdmi_sm FCS FDMI state machine + */ + +/** + * FDMI State Machine events + */ +enum port_fdmi_event { + FDMISM_EVENT_PORT_ONLINE = 1, + FDMISM_EVENT_PORT_OFFLINE = 2, + FDMISM_EVENT_RSP_OK = 4, + FDMISM_EVENT_RSP_ERROR = 5, + FDMISM_EVENT_TIMEOUT = 6, + FDMISM_EVENT_RHBA_SENT = 7, + FDMISM_EVENT_RPRT_SENT = 8, + FDMISM_EVENT_RPA_SENT = 9, +}; + +static void bfa_fcs_port_fdmi_sm_offline(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_sending_rhba(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_rhba(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_rhba_retry(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_sending_rprt(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_rprt(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_rprt_retry(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_sending_rpa(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_rpa(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_rpa_retry(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +static void bfa_fcs_port_fdmi_sm_online(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event); +/** + * Start in offline state - awaiting MS to send start. + */ +static void +bfa_fcs_port_fdmi_sm_offline(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + fdmi->retry_cnt = 0; + + switch (event) { + case FDMISM_EVENT_PORT_ONLINE: + if (port->vport) { + /* + * For Vports, register a new port. + */ + bfa_sm_set_state(fdmi, + bfa_fcs_port_fdmi_sm_sending_rprt); + bfa_fcs_port_fdmi_send_rprt(fdmi, NULL); + } else { + /* + * For a base port, we should first register the HBA + * atribute. The HBA attribute also contains the base + * port registration. + */ + bfa_sm_set_state(fdmi, + bfa_fcs_port_fdmi_sm_sending_rhba); + bfa_fcs_port_fdmi_send_rhba(fdmi, NULL); + } + break; + + case FDMISM_EVENT_PORT_OFFLINE: + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_sending_rhba(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_RHBA_SENT: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_rhba); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(port), + &fdmi->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_rhba(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_RSP_ERROR: + /* + * if max retries have not been reached, start timer for a + * delayed retry + */ + if (fdmi->retry_cnt++ < BFA_FCS_FDMI_CMD_MAX_RETRIES) { + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_rhba_retry); + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(port), + &fdmi->timer, bfa_fcs_port_fdmi_timeout, + fdmi, BFA_FCS_RETRY_TIMEOUT); + } else { + /* + * set state to offline + */ + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + } + break; + + case FDMISM_EVENT_RSP_OK: + /* + * Initiate Register Port Attributes + */ + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_sending_rpa); + fdmi->retry_cnt = 0; + bfa_fcs_port_fdmi_send_rpa(fdmi, NULL); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_fcxp_discard(fdmi->fcxp); + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_rhba_retry(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_sending_rhba); + bfa_fcs_port_fdmi_send_rhba(fdmi, NULL); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + bfa_timer_stop(&fdmi->timer); + break; + + default: + bfa_assert(0); + } +} + +/* +* RPRT : Register Port + */ +static void +bfa_fcs_port_fdmi_sm_sending_rprt(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_RPRT_SENT: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_rprt); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(port), + &fdmi->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_rprt(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_RSP_ERROR: + /* + * if max retries have not been reached, start timer for a + * delayed retry + */ + if (fdmi->retry_cnt++ < BFA_FCS_FDMI_CMD_MAX_RETRIES) { + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_rprt_retry); + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(port), + &fdmi->timer, bfa_fcs_port_fdmi_timeout, + fdmi, BFA_FCS_RETRY_TIMEOUT); + + } else { + /* + * set state to offline + */ + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + fdmi->retry_cnt = 0; + } + break; + + case FDMISM_EVENT_RSP_OK: + fdmi->retry_cnt = 0; + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_online); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_fcxp_discard(fdmi->fcxp); + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_rprt_retry(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_sending_rprt); + bfa_fcs_port_fdmi_send_rprt(fdmi, NULL); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + bfa_timer_stop(&fdmi->timer); + break; + + default: + bfa_assert(0); + } +} + +/* + * Register Port Attributes + */ +static void +bfa_fcs_port_fdmi_sm_sending_rpa(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_RPA_SENT: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_rpa); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(port), + &fdmi->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_rpa(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_RSP_ERROR: + /* + * if max retries have not been reached, start timer for a + * delayed retry + */ + if (fdmi->retry_cnt++ < BFA_FCS_FDMI_CMD_MAX_RETRIES) { + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_rpa_retry); + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(port), + &fdmi->timer, bfa_fcs_port_fdmi_timeout, + fdmi, BFA_FCS_RETRY_TIMEOUT); + } else { + /* + * set state to offline + */ + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + fdmi->retry_cnt = 0; + } + break; + + case FDMISM_EVENT_RSP_OK: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_online); + fdmi->retry_cnt = 0; + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_fcxp_discard(fdmi->fcxp); + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_rpa_retry(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_sending_rpa); + bfa_fcs_port_fdmi_send_rpa(fdmi, NULL); + break; + + case FDMISM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + bfa_timer_stop(&fdmi->timer); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_fdmi_sm_online(struct bfa_fcs_port_fdmi_s *fdmi, + enum port_fdmi_event event) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + bfa_trc(port->fcs, event); + + switch (event) { + case FDMISM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); + break; + + default: + bfa_assert(0); + } +} + + +/** +* RHBA : Register HBA Attributes. + */ +static void +bfa_fcs_port_fdmi_send_rhba(void *fdmi_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_fdmi_s *fdmi = fdmi_cbarg; + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct fchs_s fchs; + int len, attr_len; + struct bfa_fcxp_s *fcxp; + u8 *pyld; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &fdmi->fcxp_wqe, + bfa_fcs_port_fdmi_send_rhba, fdmi); + return; + } + fdmi->fcxp = fcxp; + + pyld = bfa_fcxp_get_reqbuf(fcxp); + bfa_os_memset(pyld, 0, FC_MAX_PDUSZ); + + len = fc_fdmi_reqhdr_build(&fchs, pyld, bfa_fcs_port_get_fcid(port), + FDMI_RHBA); + + attr_len = bfa_fcs_port_fdmi_build_rhba_pyld(fdmi, + (u8 *) ((struct ct_hdr_s *) pyld + 1)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, (len + attr_len), &fchs, + bfa_fcs_port_fdmi_rhba_response, (void *)fdmi, + FC_MAX_PDUSZ, FC_RA_TOV); + + bfa_sm_send_event(fdmi, FDMISM_EVENT_RHBA_SENT); +} + +static u16 +bfa_fcs_port_fdmi_build_rhba_pyld(struct bfa_fcs_port_fdmi_s *fdmi, + u8 *pyld) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct bfa_fcs_fdmi_hba_attr_s hba_attr; /* @todo */ + struct bfa_fcs_fdmi_hba_attr_s *fcs_hba_attr = &hba_attr; /* @todo */ + struct fdmi_rhba_s *rhba = (struct fdmi_rhba_s *) pyld; + struct fdmi_attr_s *attr; + u8 *curr_ptr; + u16 len, count; + + /* + * get hba attributes + */ + bfa_fcs_fdmi_get_hbaattr(fdmi, fcs_hba_attr); + + rhba->hba_id = bfa_fcs_port_get_pwwn(port); + rhba->port_list.num_ports = bfa_os_htonl(1); + rhba->port_list.port_entry = bfa_fcs_port_get_pwwn(port); + + len = sizeof(rhba->hba_id) + sizeof(rhba->port_list); + + count = 0; + len += sizeof(rhba->hba_attr_blk.attr_count); + + /* + * fill out the invididual entries of the HBA attrib Block + */ + curr_ptr = (u8 *) &rhba->hba_attr_blk.hba_attr; + + /* + * Node Name + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_NODENAME); + attr->len = sizeof(wwn_t); + memcpy(attr->value, &bfa_fcs_port_get_nwwn(port), attr->len); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * Manufacturer + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_MANUFACTURER); + attr->len = (u16) strlen(fcs_hba_attr->manufacturer); + memcpy(attr->value, fcs_hba_attr->manufacturer, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * Serial Number + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_SERIALNUM); + attr->len = (u16) strlen(fcs_hba_attr->serial_num); + memcpy(attr->value, fcs_hba_attr->serial_num, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * Model + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_MODEL); + attr->len = (u16) strlen(fcs_hba_attr->model); + memcpy(attr->value, fcs_hba_attr->model, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * Model Desc + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_MODEL_DESC); + attr->len = (u16) strlen(fcs_hba_attr->model_desc); + memcpy(attr->value, fcs_hba_attr->model_desc, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * H/W Version + */ + if (fcs_hba_attr->hw_version[0] != '\0') { + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_HW_VERSION); + attr->len = (u16) strlen(fcs_hba_attr->hw_version); + memcpy(attr->value, fcs_hba_attr->hw_version, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + } + + /* + * Driver Version + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_DRIVER_VERSION); + attr->len = (u16) strlen(fcs_hba_attr->driver_version); + memcpy(attr->value, fcs_hba_attr->driver_version, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len;; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * Option Rom Version + */ + if (fcs_hba_attr->option_rom_ver[0] != '\0') { + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_ROM_VERSION); + attr->len = (u16) strlen(fcs_hba_attr->option_rom_ver); + memcpy(attr->value, fcs_hba_attr->option_rom_ver, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + } + + /* + * f/w Version = driver version + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_FW_VERSION); + attr->len = (u16) strlen(fcs_hba_attr->driver_version); + memcpy(attr->value, fcs_hba_attr->driver_version, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * OS Name + */ + if (fcs_hba_attr->os_name[0] != '\0') { + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_OS_NAME); + attr->len = (u16) strlen(fcs_hba_attr->os_name); + memcpy(attr->value, fcs_hba_attr->os_name, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + } + + /* + * MAX_CT_PAYLOAD + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_HBA_ATTRIB_MAX_CT); + attr->len = sizeof(fcs_hba_attr->max_ct_pyld); + memcpy(attr->value, &fcs_hba_attr->max_ct_pyld, attr->len); + len += attr->len; + count++; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * Update size of payload + */ + len += ((sizeof(attr->type) + sizeof(attr->len)) * count); + + rhba->hba_attr_blk.attr_count = bfa_os_htonl(count); + return len; +} + +static void +bfa_fcs_port_fdmi_rhba_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_fdmi_s *fdmi = (struct bfa_fcs_port_fdmi_s *)cbarg; + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct ct_hdr_s *cthdr = NULL; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_OK); + return; + } + + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_ERROR); +} + +/** +* RPRT : Register Port + */ +static void +bfa_fcs_port_fdmi_send_rprt(void *fdmi_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_fdmi_s *fdmi = fdmi_cbarg; + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct fchs_s fchs; + u16 len, attr_len; + struct bfa_fcxp_s *fcxp; + u8 *pyld; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &fdmi->fcxp_wqe, + bfa_fcs_port_fdmi_send_rprt, fdmi); + return; + } + fdmi->fcxp = fcxp; + + pyld = bfa_fcxp_get_reqbuf(fcxp); + bfa_os_memset(pyld, 0, FC_MAX_PDUSZ); + + len = fc_fdmi_reqhdr_build(&fchs, pyld, bfa_fcs_port_get_fcid(port), + FDMI_RPRT); + + attr_len = bfa_fcs_port_fdmi_build_rprt_pyld(fdmi, + (u8 *) ((struct ct_hdr_s *) pyld + 1)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len + attr_len, &fchs, + bfa_fcs_port_fdmi_rprt_response, (void *)fdmi, + FC_MAX_PDUSZ, FC_RA_TOV); + + bfa_sm_send_event(fdmi, FDMISM_EVENT_RPRT_SENT); +} + +/** + * This routine builds Port Attribute Block that used in RPA, RPRT commands. + */ +static u16 +bfa_fcs_port_fdmi_build_portattr_block(struct bfa_fcs_port_fdmi_s *fdmi, + u8 *pyld) +{ + struct bfa_fcs_fdmi_port_attr_s fcs_port_attr; + struct fdmi_port_attr_s *port_attrib = (struct fdmi_port_attr_s *) pyld; + struct fdmi_attr_s *attr; + u8 *curr_ptr; + u16 len; + u8 count = 0; + + /* + * get port attributes + */ + bfa_fcs_fdmi_get_portattr(fdmi, &fcs_port_attr); + + len = sizeof(port_attrib->attr_count); + + /* + * fill out the invididual entries + */ + curr_ptr = (u8 *) &port_attrib->port_attr; + + /* + * FC4 Types + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_PORT_ATTRIB_FC4_TYPES); + attr->len = sizeof(fcs_port_attr.supp_fc4_types); + memcpy(attr->value, fcs_port_attr.supp_fc4_types, attr->len); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + ++count; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * Supported Speed + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_PORT_ATTRIB_SUPP_SPEED); + attr->len = sizeof(fcs_port_attr.supp_speed); + memcpy(attr->value, &fcs_port_attr.supp_speed, attr->len); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + ++count; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * current Port Speed + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_PORT_ATTRIB_PORT_SPEED); + attr->len = sizeof(fcs_port_attr.curr_speed); + memcpy(attr->value, &fcs_port_attr.curr_speed, attr->len); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + ++count; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * max frame size + */ + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_PORT_ATTRIB_FRAME_SIZE); + attr->len = sizeof(fcs_port_attr.max_frm_size); + memcpy(attr->value, &fcs_port_attr.max_frm_size, attr->len); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + ++count; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + /* + * OS Device Name + */ + if (fcs_port_attr.os_device_name[0] != '\0') { + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_PORT_ATTRIB_DEV_NAME); + attr->len = (u16) strlen(fcs_port_attr.os_device_name); + memcpy(attr->value, fcs_port_attr.os_device_name, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + ++count; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + } + /* + * Host Name + */ + if (fcs_port_attr.host_name[0] != '\0') { + attr = (struct fdmi_attr_s *) curr_ptr; + attr->type = bfa_os_htons(FDMI_PORT_ATTRIB_HOST_NAME); + attr->len = (u16) strlen(fcs_port_attr.host_name); + memcpy(attr->value, fcs_port_attr.host_name, attr->len); + /* variable fields need to be 4 byte aligned */ + attr->len = fc_roundup(attr->len, sizeof(u32)); + curr_ptr += sizeof(attr->type) + sizeof(attr->len) + attr->len; + len += attr->len; + ++count; + attr->len = + bfa_os_htons(attr->len + sizeof(attr->type) + + sizeof(attr->len)); + + } + + /* + * Update size of payload + */ + port_attrib->attr_count = bfa_os_htonl(count); + len += ((sizeof(attr->type) + sizeof(attr->len)) * count); + return len; +} + +static u16 +bfa_fcs_port_fdmi_build_rprt_pyld(struct bfa_fcs_port_fdmi_s *fdmi, + u8 *pyld) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct fdmi_rprt_s *rprt = (struct fdmi_rprt_s *) pyld; + u16 len; + + rprt->hba_id = bfa_fcs_port_get_pwwn(bfa_fcs_get_base_port(port->fcs)); + rprt->port_name = bfa_fcs_port_get_pwwn(port); + + len = bfa_fcs_port_fdmi_build_portattr_block(fdmi, + (u8 *) &rprt->port_attr_blk); + + len += sizeof(rprt->hba_id) + sizeof(rprt->port_name); + + return len; +} + +static void +bfa_fcs_port_fdmi_rprt_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_fdmi_s *fdmi = (struct bfa_fcs_port_fdmi_s *)cbarg; + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct ct_hdr_s *cthdr = NULL; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_OK); + return; + } + + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_ERROR); +} + +/** +* RPA : Register Port Attributes. + */ +static void +bfa_fcs_port_fdmi_send_rpa(void *fdmi_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_fdmi_s *fdmi = fdmi_cbarg; + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct fchs_s fchs; + u16 len, attr_len; + struct bfa_fcxp_s *fcxp; + u8 *pyld; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &fdmi->fcxp_wqe, + bfa_fcs_port_fdmi_send_rpa, fdmi); + return; + } + fdmi->fcxp = fcxp; + + pyld = bfa_fcxp_get_reqbuf(fcxp); + bfa_os_memset(pyld, 0, FC_MAX_PDUSZ); + + len = fc_fdmi_reqhdr_build(&fchs, pyld, bfa_fcs_port_get_fcid(port), + FDMI_RPA); + + attr_len = bfa_fcs_port_fdmi_build_rpa_pyld(fdmi, + (u8 *) ((struct ct_hdr_s *) pyld + 1)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len + attr_len, &fchs, + bfa_fcs_port_fdmi_rpa_response, (void *)fdmi, + FC_MAX_PDUSZ, FC_RA_TOV); + + bfa_sm_send_event(fdmi, FDMISM_EVENT_RPA_SENT); +} + +static u16 +bfa_fcs_port_fdmi_build_rpa_pyld(struct bfa_fcs_port_fdmi_s *fdmi, + u8 *pyld) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct fdmi_rpa_s *rpa = (struct fdmi_rpa_s *) pyld; + u16 len; + + rpa->port_name = bfa_fcs_port_get_pwwn(port); + + len = bfa_fcs_port_fdmi_build_portattr_block(fdmi, + (u8 *) &rpa->port_attr_blk); + + len += sizeof(rpa->port_name); + + return len; +} + +static void +bfa_fcs_port_fdmi_rpa_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_fdmi_s *fdmi = (struct bfa_fcs_port_fdmi_s *)cbarg; + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct ct_hdr_s *cthdr = NULL; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_OK); + return; + } + + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + bfa_sm_send_event(fdmi, FDMISM_EVENT_RSP_ERROR); +} + +static void +bfa_fcs_port_fdmi_timeout(void *arg) +{ + struct bfa_fcs_port_fdmi_s *fdmi = (struct bfa_fcs_port_fdmi_s *)arg; + + bfa_sm_send_event(fdmi, FDMISM_EVENT_TIMEOUT); +} + +void +bfa_fcs_fdmi_get_hbaattr(struct bfa_fcs_port_fdmi_s *fdmi, + struct bfa_fcs_fdmi_hba_attr_s *hba_attr) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct bfa_fcs_driver_info_s *driver_info = &port->fcs->driver_info; + struct bfa_adapter_attr_s adapter_attr; + + bfa_os_memset(hba_attr, 0, sizeof(struct bfa_fcs_fdmi_hba_attr_s)); + bfa_os_memset(&adapter_attr, 0, sizeof(struct bfa_adapter_attr_s)); + + bfa_ioc_get_adapter_attr(&port->fcs->bfa->ioc, &adapter_attr); + + strncpy(hba_attr->manufacturer, adapter_attr.manufacturer, + sizeof(adapter_attr.manufacturer)); + + strncpy(hba_attr->serial_num, adapter_attr.serial_num, + sizeof(adapter_attr.serial_num)); + + strncpy(hba_attr->model, adapter_attr.model, sizeof(hba_attr->model)); + + strncpy(hba_attr->model_desc, adapter_attr.model_descr, + sizeof(hba_attr->model_desc)); + + strncpy(hba_attr->hw_version, adapter_attr.hw_ver, + sizeof(hba_attr->hw_version)); + + strncpy(hba_attr->driver_version, (char *)driver_info->version, + sizeof(hba_attr->driver_version)); + + strncpy(hba_attr->option_rom_ver, adapter_attr.optrom_ver, + sizeof(hba_attr->option_rom_ver)); + + strncpy(hba_attr->fw_version, adapter_attr.fw_ver, + sizeof(hba_attr->fw_version)); + + strncpy(hba_attr->os_name, driver_info->host_os_name, + sizeof(hba_attr->os_name)); + + /* + * If there is a patch level, append it to the os name along with a + * separator + */ + if (driver_info->host_os_patch[0] != '\0') { + strncat(hba_attr->os_name, BFA_FCS_PORT_SYMBNAME_SEPARATOR, + sizeof(BFA_FCS_PORT_SYMBNAME_SEPARATOR)); + strncat(hba_attr->os_name, driver_info->host_os_patch, + sizeof(driver_info->host_os_patch)); + } + + hba_attr->max_ct_pyld = bfa_os_htonl(FC_MAX_PDUSZ); + +} + +void +bfa_fcs_fdmi_get_portattr(struct bfa_fcs_port_fdmi_s *fdmi, + struct bfa_fcs_fdmi_port_attr_s *port_attr) +{ + struct bfa_fcs_port_s *port = fdmi->ms->port; + struct bfa_fcs_driver_info_s *driver_info = &port->fcs->driver_info; + struct bfa_pport_attr_s pport_attr; + + bfa_os_memset(port_attr, 0, sizeof(struct bfa_fcs_fdmi_port_attr_s)); + + /* + * get pport attributes from hal + */ + bfa_pport_get_attr(port->fcs->bfa, &pport_attr); + + /* + * get FC4 type Bitmask + */ + fc_get_fc4type_bitmask(FC_TYPE_FCP, port_attr->supp_fc4_types); + + /* + * Supported Speeds + */ + port_attr->supp_speed = bfa_os_htonl(BFA_FCS_FDMI_SUPORTED_SPEEDS); + + /* + * Current Speed + */ + port_attr->curr_speed = bfa_os_htonl(pport_attr.speed); + + /* + * Max PDU Size. + */ + port_attr->max_frm_size = bfa_os_htonl(FC_MAX_PDUSZ); + + /* + * OS device Name + */ + strncpy(port_attr->os_device_name, (char *)driver_info->os_device_name, + sizeof(port_attr->os_device_name)); + + /* + * Host name + */ + strncpy(port_attr->host_name, (char *)driver_info->host_machine_name, + sizeof(port_attr->host_name)); + +} + + +void +bfa_fcs_port_fdmi_init(struct bfa_fcs_port_ms_s *ms) +{ + struct bfa_fcs_port_fdmi_s *fdmi = &ms->fdmi; + + fdmi->ms = ms; + bfa_sm_set_state(fdmi, bfa_fcs_port_fdmi_sm_offline); +} + +void +bfa_fcs_port_fdmi_offline(struct bfa_fcs_port_ms_s *ms) +{ + struct bfa_fcs_port_fdmi_s *fdmi = &ms->fdmi; + + fdmi->ms = ms; + bfa_sm_send_event(fdmi, FDMISM_EVENT_PORT_OFFLINE); +} + +void +bfa_fcs_port_fdmi_online(struct bfa_fcs_port_ms_s *ms) +{ + struct bfa_fcs_port_fdmi_s *fdmi = &ms->fdmi; + + fdmi->ms = ms; + bfa_sm_send_event(fdmi, FDMISM_EVENT_PORT_ONLINE); +} diff --git a/drivers/scsi/bfa/include/aen/bfa_aen.h b/drivers/scsi/bfa/include/aen/bfa_aen.h new file mode 100644 index 000000000000..da8cac093d3d --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen.h @@ -0,0 +1,92 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_AEN_H__ +#define __BFA_AEN_H__ + +#include "defs/bfa_defs_aen.h" + +#define BFA_AEN_MAX_ENTRY 512 + +extern s32 bfa_aen_max_cfg_entry; +struct bfa_aen_s { + void *bfad; + s32 max_entry; + s32 write_index; + s32 read_index; + u32 bfad_num; + u32 seq_num; + void (*aen_cb_notify)(void *bfad); + void (*gettimeofday)(struct bfa_timeval_s *tv); + struct bfa_trc_mod_s *trcmod; + struct bfa_aen_entry_s list[BFA_AEN_MAX_ENTRY]; /* Must be the last */ +}; + + +/** + * Public APIs + */ +static inline void +bfa_aen_set_max_cfg_entry(int max_entry) +{ + bfa_aen_max_cfg_entry = max_entry; +} + +static inline s32 +bfa_aen_get_max_cfg_entry(void) +{ + return bfa_aen_max_cfg_entry; +} + +static inline s32 +bfa_aen_get_meminfo(void) +{ + return (sizeof(struct bfa_aen_entry_s) * bfa_aen_get_max_cfg_entry()); +} + +static inline s32 +bfa_aen_get_wi(struct bfa_aen_s *aen) +{ + return aen->write_index; +} + +static inline s32 +bfa_aen_get_ri(struct bfa_aen_s *aen) +{ + return aen->read_index; +} + +static inline s32 +bfa_aen_fetch_count(struct bfa_aen_s *aen, s32 read_index) +{ + return ((aen->write_index + aen->max_entry) - read_index) + % aen->max_entry; +} + +s32 bfa_aen_init(struct bfa_aen_s *aen, struct bfa_trc_mod_s *trcmod, + void *bfad, u32 inst_id, void (*aen_cb_notify)(void *), + void (*gettimeofday)(struct bfa_timeval_s *)); + +s32 bfa_aen_post(struct bfa_aen_s *aen, enum bfa_aen_category aen_category, + int aen_type, union bfa_aen_data_u *aen_data); + +s32 bfa_aen_fetch(struct bfa_aen_s *aen, struct bfa_aen_entry_s *aen_entry, + s32 entry_space, s32 rii, s32 *ri_arr, + s32 ri_arr_cnt); + +s32 bfa_aen_get_inst(struct bfa_aen_s *aen); + +#endif /* __BFA_AEN_H__ */ diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_adapter.h b/drivers/scsi/bfa/include/aen/bfa_aen_adapter.h new file mode 100644 index 000000000000..260d3ea1cab3 --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_adapter.h @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_ADAPTER Module */ +#ifndef __bfa_aen_adapter_h__ +#define __bfa_aen_adapter_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_ADAPTER_ADD \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ADAPTER, BFA_ADAPTER_AEN_ADD) +#define BFA_AEN_ADAPTER_REMOVE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ADAPTER, BFA_ADAPTER_AEN_REMOVE) + +#endif + diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_audit.h b/drivers/scsi/bfa/include/aen/bfa_aen_audit.h new file mode 100644 index 000000000000..12cd7aab5d53 --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_audit.h @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_AUDIT Module */ +#ifndef __bfa_aen_audit_h__ +#define __bfa_aen_audit_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_AUDIT_AUTH_ENABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_AUDIT, BFA_AUDIT_AEN_AUTH_ENABLE) +#define BFA_AEN_AUDIT_AUTH_DISABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_AUDIT, BFA_AUDIT_AEN_AUTH_DISABLE) + +#endif + diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_ethport.h b/drivers/scsi/bfa/include/aen/bfa_aen_ethport.h new file mode 100644 index 000000000000..507d0b58d149 --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_ethport.h @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_ETHPORT Module */ +#ifndef __bfa_aen_ethport_h__ +#define __bfa_aen_ethport_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_ETHPORT_LINKUP \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ETHPORT, BFA_ETHPORT_AEN_LINKUP) +#define BFA_AEN_ETHPORT_LINKDOWN \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ETHPORT, BFA_ETHPORT_AEN_LINKDOWN) +#define BFA_AEN_ETHPORT_ENABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ETHPORT, BFA_ETHPORT_AEN_ENABLE) +#define BFA_AEN_ETHPORT_DISABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ETHPORT, BFA_ETHPORT_AEN_DISABLE) + +#endif + diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_ioc.h b/drivers/scsi/bfa/include/aen/bfa_aen_ioc.h new file mode 100644 index 000000000000..71378b446b69 --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_ioc.h @@ -0,0 +1,37 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_IOC Module */ +#ifndef __bfa_aen_ioc_h__ +#define __bfa_aen_ioc_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_IOC_HBGOOD \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_IOC, BFA_IOC_AEN_HBGOOD) +#define BFA_AEN_IOC_HBFAIL \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_IOC, BFA_IOC_AEN_HBFAIL) +#define BFA_AEN_IOC_ENABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_IOC, BFA_IOC_AEN_ENABLE) +#define BFA_AEN_IOC_DISABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_IOC, BFA_IOC_AEN_DISABLE) +#define BFA_AEN_IOC_FWMISMATCH \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_IOC, BFA_IOC_AEN_FWMISMATCH) + +#endif + diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_itnim.h b/drivers/scsi/bfa/include/aen/bfa_aen_itnim.h new file mode 100644 index 000000000000..a7d8ddcfef99 --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_itnim.h @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_ITNIM Module */ +#ifndef __bfa_aen_itnim_h__ +#define __bfa_aen_itnim_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_ITNIM_ONLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ITNIM, BFA_ITNIM_AEN_ONLINE) +#define BFA_AEN_ITNIM_OFFLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ITNIM, BFA_ITNIM_AEN_OFFLINE) +#define BFA_AEN_ITNIM_DISCONNECT \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_ITNIM, BFA_ITNIM_AEN_DISCONNECT) + +#endif + diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_lport.h b/drivers/scsi/bfa/include/aen/bfa_aen_lport.h new file mode 100644 index 000000000000..5a8ebb65193f --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_lport.h @@ -0,0 +1,51 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_LPORT Module */ +#ifndef __bfa_aen_lport_h__ +#define __bfa_aen_lport_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_LPORT_NEW \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_NEW) +#define BFA_AEN_LPORT_DELETE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_DELETE) +#define BFA_AEN_LPORT_ONLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_ONLINE) +#define BFA_AEN_LPORT_OFFLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_OFFLINE) +#define BFA_AEN_LPORT_DISCONNECT \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_DISCONNECT) +#define BFA_AEN_LPORT_NEW_PROP \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_NEW_PROP) +#define BFA_AEN_LPORT_DELETE_PROP \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_DELETE_PROP) +#define BFA_AEN_LPORT_NEW_STANDARD \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_NEW_STANDARD) +#define BFA_AEN_LPORT_DELETE_STANDARD \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_DELETE_STANDARD) +#define BFA_AEN_LPORT_NPIV_DUP_WWN \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_NPIV_DUP_WWN) +#define BFA_AEN_LPORT_NPIV_FABRIC_MAX \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_NPIV_FABRIC_MAX) +#define BFA_AEN_LPORT_NPIV_UNKNOWN \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_LPORT, BFA_LPORT_AEN_NPIV_UNKNOWN) + +#endif + diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_port.h b/drivers/scsi/bfa/include/aen/bfa_aen_port.h new file mode 100644 index 000000000000..9add905a622d --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_port.h @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_PORT Module */ +#ifndef __bfa_aen_port_h__ +#define __bfa_aen_port_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_PORT_ONLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_ONLINE) +#define BFA_AEN_PORT_OFFLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_OFFLINE) +#define BFA_AEN_PORT_RLIR \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_RLIR) +#define BFA_AEN_PORT_SFP_INSERT \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_SFP_INSERT) +#define BFA_AEN_PORT_SFP_REMOVE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_SFP_REMOVE) +#define BFA_AEN_PORT_SFP_POM \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_SFP_POM) +#define BFA_AEN_PORT_ENABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_ENABLE) +#define BFA_AEN_PORT_DISABLE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_DISABLE) +#define BFA_AEN_PORT_AUTH_ON \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_AUTH_ON) +#define BFA_AEN_PORT_AUTH_OFF \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_AUTH_OFF) +#define BFA_AEN_PORT_DISCONNECT \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_DISCONNECT) +#define BFA_AEN_PORT_QOS_NEG \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_QOS_NEG) +#define BFA_AEN_PORT_FABRIC_NAME_CHANGE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_FABRIC_NAME_CHANGE) +#define BFA_AEN_PORT_SFP_ACCESS_ERROR \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_SFP_ACCESS_ERROR) +#define BFA_AEN_PORT_SFP_UNSUPPORT \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_PORT, BFA_PORT_AEN_SFP_UNSUPPORT) + +#endif + diff --git a/drivers/scsi/bfa/include/aen/bfa_aen_rport.h b/drivers/scsi/bfa/include/aen/bfa_aen_rport.h new file mode 100644 index 000000000000..7e4be1fd5e15 --- /dev/null +++ b/drivers/scsi/bfa/include/aen/bfa_aen_rport.h @@ -0,0 +1,37 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for BFA_AEN_CAT_RPORT Module */ +#ifndef __bfa_aen_rport_h__ +#define __bfa_aen_rport_h__ + +#include <cs/bfa_log.h> +#include <defs/bfa_defs_aen.h> + +#define BFA_AEN_RPORT_ONLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_RPORT, BFA_RPORT_AEN_ONLINE) +#define BFA_AEN_RPORT_OFFLINE \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_RPORT, BFA_RPORT_AEN_OFFLINE) +#define BFA_AEN_RPORT_DISCONNECT \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_RPORT, BFA_RPORT_AEN_DISCONNECT) +#define BFA_AEN_RPORT_QOS_PRIO \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_RPORT, BFA_RPORT_AEN_QOS_PRIO) +#define BFA_AEN_RPORT_QOS_FLOWID \ + BFA_LOG_CREATE_ID(BFA_AEN_CAT_RPORT, BFA_RPORT_AEN_QOS_FLOWID) + +#endif + diff --git a/drivers/scsi/bfa/include/bfa.h b/drivers/scsi/bfa/include/bfa.h new file mode 100644 index 000000000000..64c1412c5703 --- /dev/null +++ b/drivers/scsi/bfa/include/bfa.h @@ -0,0 +1,177 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_H__ +#define __BFA_H__ + +#include <bfa_os_inc.h> +#include <cs/bfa_debug.h> +#include <cs/bfa_q.h> +#include <cs/bfa_trc.h> +#include <cs/bfa_log.h> +#include <cs/bfa_plog.h> +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_ioc.h> +#include <defs/bfa_defs_iocfc.h> +#include <aen/bfa_aen.h> +#include <bfi/bfi.h> + +struct bfa_s; +#include <bfa_intr_priv.h> + +struct bfa_pcidev_s; + +/** + * PCI devices supported by the current BFA + */ +struct bfa_pciid_s { + u16 device_id; + u16 vendor_id; +}; + +extern char bfa_version[]; + +/** + * BFA Power Mgmt Commands + */ +enum bfa_pm_cmd { + BFA_PM_CTL_D0 = 0, + BFA_PM_CTL_D1 = 1, + BFA_PM_CTL_D2 = 2, + BFA_PM_CTL_D3 = 3, +}; + +/** + * BFA memory resources + */ +enum bfa_mem_type { + BFA_MEM_TYPE_KVA = 1, /*! Kernel Virtual Memory *(non-dma-able) */ + BFA_MEM_TYPE_DMA = 2, /*! DMA-able memory */ + BFA_MEM_TYPE_MAX = BFA_MEM_TYPE_DMA, +}; + +struct bfa_mem_elem_s { + enum bfa_mem_type mem_type; /* see enum bfa_mem_type */ + u32 mem_len; /* Total Length in Bytes */ + u8 *kva; /* kernel virtual address */ + u64 dma; /* dma address if DMA memory */ + u8 *kva_curp; /* kva allocation cursor */ + u64 dma_curp; /* dma allocation cursor */ +}; + +struct bfa_meminfo_s { + struct bfa_mem_elem_s meminfo[BFA_MEM_TYPE_MAX]; +}; +#define bfa_meminfo_kva(_m) \ + (_m)->meminfo[BFA_MEM_TYPE_KVA - 1].kva_curp +#define bfa_meminfo_dma_virt(_m) \ + (_m)->meminfo[BFA_MEM_TYPE_DMA - 1].kva_curp +#define bfa_meminfo_dma_phys(_m) \ + (_m)->meminfo[BFA_MEM_TYPE_DMA - 1].dma_curp + +/** + * Generic Scatter Gather Element used by driver + */ +struct bfa_sge_s { + u32 sg_len; + void *sg_addr; +}; + +#define bfa_sge_to_be(__sge) do { \ + ((u32 *)(__sge))[0] = bfa_os_htonl(((u32 *)(__sge))[0]); \ + ((u32 *)(__sge))[1] = bfa_os_htonl(((u32 *)(__sge))[1]); \ + ((u32 *)(__sge))[2] = bfa_os_htonl(((u32 *)(__sge))[2]); \ +} while (0) + + +/* + * bfa stats interfaces + */ +#define bfa_stats(_mod, _stats) (_mod)->stats._stats ++ + +#define bfa_ioc_get_stats(__bfa, __ioc_stats) \ + bfa_ioc_fetch_stats(&(__bfa)->ioc, __ioc_stats) +#define bfa_ioc_clear_stats(__bfa) \ + bfa_ioc_clr_stats(&(__bfa)->ioc) + +/* + * bfa API functions + */ +void bfa_get_pciids(struct bfa_pciid_s **pciids, int *npciids); +void bfa_cfg_get_default(struct bfa_iocfc_cfg_s *cfg); +void bfa_cfg_get_min(struct bfa_iocfc_cfg_s *cfg); +void bfa_cfg_get_meminfo(struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo); +void bfa_attach(struct bfa_s *bfa, void *bfad, struct bfa_iocfc_cfg_s *cfg, + struct bfa_meminfo_s *meminfo, + struct bfa_pcidev_s *pcidev); +void bfa_init_trc(struct bfa_s *bfa, struct bfa_trc_mod_s *trcmod); +void bfa_init_log(struct bfa_s *bfa, struct bfa_log_mod_s *logmod); +void bfa_init_aen(struct bfa_s *bfa, struct bfa_aen_s *aen); +void bfa_init_plog(struct bfa_s *bfa, struct bfa_plog_s *plog); +void bfa_detach(struct bfa_s *bfa); +void bfa_init(struct bfa_s *bfa); +void bfa_start(struct bfa_s *bfa); +void bfa_stop(struct bfa_s *bfa); +void bfa_attach_fcs(struct bfa_s *bfa); +void bfa_cb_init(void *bfad, bfa_status_t status); +void bfa_cb_stop(void *bfad, bfa_status_t status); +void bfa_cb_updateq(void *bfad, bfa_status_t status); + +bfa_boolean_t bfa_intx(struct bfa_s *bfa); +void bfa_isr_enable(struct bfa_s *bfa); +void bfa_isr_disable(struct bfa_s *bfa); +void bfa_msix_getvecs(struct bfa_s *bfa, u32 *msix_vecs_bmap, + u32 *num_vecs, u32 *max_vec_bit); +#define bfa_msix(__bfa, __vec) (__bfa)->msix.handler[__vec](__bfa, __vec) + +void bfa_comp_deq(struct bfa_s *bfa, struct list_head *comp_q); +void bfa_comp_process(struct bfa_s *bfa, struct list_head *comp_q); +void bfa_comp_free(struct bfa_s *bfa, struct list_head *comp_q); + +typedef void (*bfa_cb_ioc_t) (void *cbarg, enum bfa_status status); +void bfa_iocfc_get_attr(struct bfa_s *bfa, struct bfa_iocfc_attr_s *attr); +bfa_status_t bfa_iocfc_get_stats(struct bfa_s *bfa, + struct bfa_iocfc_stats_s *stats, + bfa_cb_ioc_t cbfn, void *cbarg); +bfa_status_t bfa_iocfc_clear_stats(struct bfa_s *bfa, + bfa_cb_ioc_t cbfn, void *cbarg); +void bfa_get_attr(struct bfa_s *bfa, struct bfa_ioc_attr_s *ioc_attr); + +void bfa_adapter_get_attr(struct bfa_s *bfa, + struct bfa_adapter_attr_s *ad_attr); +u64 bfa_adapter_get_id(struct bfa_s *bfa); + +bfa_status_t bfa_iocfc_israttr_set(struct bfa_s *bfa, + struct bfa_iocfc_intr_attr_s *attr); + +void bfa_iocfc_enable(struct bfa_s *bfa); +void bfa_iocfc_disable(struct bfa_s *bfa); +void bfa_ioc_auto_recover(bfa_boolean_t auto_recover); +void bfa_cb_ioc_disable(void *bfad); +void bfa_timer_tick(struct bfa_s *bfa); +#define bfa_timer_start(_bfa, _timer, _timercb, _arg, _timeout) \ + bfa_timer_begin(&(_bfa)->timer_mod, _timer, _timercb, _arg, _timeout) + +/* + * BFA debug API functions + */ +bfa_status_t bfa_debug_fwtrc(struct bfa_s *bfa, void *trcdata, int *trclen); +bfa_status_t bfa_debug_fwsave(struct bfa_s *bfa, void *trcdata, int *trclen); + +#include "bfa_priv.h" + +#endif /* __BFA_H__ */ diff --git a/drivers/scsi/bfa/include/bfa_fcpim.h b/drivers/scsi/bfa/include/bfa_fcpim.h new file mode 100644 index 000000000000..04789795fa53 --- /dev/null +++ b/drivers/scsi/bfa/include/bfa_fcpim.h @@ -0,0 +1,159 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCPIM_H__ +#define __BFA_FCPIM_H__ + +#include <bfa.h> +#include <bfa_svc.h> +#include <bfi/bfi_fcpim.h> +#include <defs/bfa_defs_fcpim.h> + +/* + * forward declarations + */ +struct bfa_itnim_s; +struct bfa_ioim_s; +struct bfa_tskim_s; +struct bfad_ioim_s; +struct bfad_tskim_s; + +/* + * bfa fcpim module API functions + */ +void bfa_fcpim_path_tov_set(struct bfa_s *bfa, u16 path_tov); +u16 bfa_fcpim_path_tov_get(struct bfa_s *bfa); +void bfa_fcpim_qdepth_set(struct bfa_s *bfa, u16 q_depth); +u16 bfa_fcpim_qdepth_get(struct bfa_s *bfa); +bfa_status_t bfa_fcpim_get_modstats(struct bfa_s *bfa, + struct bfa_fcpim_stats_s *modstats); +bfa_status_t bfa_fcpim_clr_modstats(struct bfa_s *bfa); + +/* + * bfa itnim API functions + */ +struct bfa_itnim_s *bfa_itnim_create(struct bfa_s *bfa, + struct bfa_rport_s *rport, void *itnim); +void bfa_itnim_delete(struct bfa_itnim_s *itnim); +void bfa_itnim_online(struct bfa_itnim_s *itnim, + bfa_boolean_t seq_rec); +void bfa_itnim_offline(struct bfa_itnim_s *itnim); +void bfa_itnim_get_stats(struct bfa_itnim_s *itnim, + struct bfa_itnim_hal_stats_s *stats); +void bfa_itnim_clear_stats(struct bfa_itnim_s *itnim); + + +/** + * BFA completion callback for bfa_itnim_online(). + * + * @param[in] itnim FCS or driver itnim instance + * + * return None + */ +void bfa_cb_itnim_online(void *itnim); + +/** + * BFA completion callback for bfa_itnim_offline(). + * + * @param[in] itnim FCS or driver itnim instance + * + * return None + */ +void bfa_cb_itnim_offline(void *itnim); +void bfa_cb_itnim_tov_begin(void *itnim); +void bfa_cb_itnim_tov(void *itnim); + +/** + * BFA notification to FCS/driver for second level error recovery. + * + * Atleast one I/O request has timedout and target is unresponsive to + * repeated abort requests. Second level error recovery should be initiated + * by starting implicit logout and recovery procedures. + * + * @param[in] itnim FCS or driver itnim instance + * + * return None + */ +void bfa_cb_itnim_sler(void *itnim); + +/* + * bfa ioim API functions + */ +struct bfa_ioim_s *bfa_ioim_alloc(struct bfa_s *bfa, + struct bfad_ioim_s *dio, + struct bfa_itnim_s *itnim, + u16 nsgles); + +void bfa_ioim_free(struct bfa_ioim_s *ioim); +void bfa_ioim_start(struct bfa_ioim_s *ioim); +void bfa_ioim_abort(struct bfa_ioim_s *ioim); +void bfa_ioim_delayed_comp(struct bfa_ioim_s *ioim, + bfa_boolean_t iotov); + + +/** + * I/O completion notification. + * + * @param[in] dio driver IO structure + * @param[in] io_status IO completion status + * @param[in] scsi_status SCSI status returned by target + * @param[in] sns_len SCSI sense length, 0 if none + * @param[in] sns_info SCSI sense data, if any + * @param[in] residue Residual length + * + * @return None + */ +void bfa_cb_ioim_done(void *bfad, struct bfad_ioim_s *dio, + enum bfi_ioim_status io_status, + u8 scsi_status, int sns_len, + u8 *sns_info, s32 residue); + +/** + * I/O good completion notification. + * + * @param[in] dio driver IO structure + * + * @return None + */ +void bfa_cb_ioim_good_comp(void *bfad, struct bfad_ioim_s *dio); + +/** + * I/O abort completion notification + * + * @param[in] dio driver IO that was aborted + * + * @return None + */ +void bfa_cb_ioim_abort(void *bfad, struct bfad_ioim_s *dio); +void bfa_cb_ioim_resfree(void *hcb_bfad); + +void bfa_cb_ioim_resfree(void *hcb_bfad); + +/* + * bfa tskim API functions + */ +struct bfa_tskim_s *bfa_tskim_alloc(struct bfa_s *bfa, + struct bfad_tskim_s *dtsk); +void bfa_tskim_free(struct bfa_tskim_s *tskim); +void bfa_tskim_start(struct bfa_tskim_s *tskim, + struct bfa_itnim_s *itnim, lun_t lun, + enum fcp_tm_cmnd tm, u8 t_secs); +void bfa_cb_tskim_done(void *bfad, struct bfad_tskim_s *dtsk, + enum bfi_tskim_status tsk_status); + +#endif /* __BFA_FCPIM_H__ */ + diff --git a/drivers/scsi/bfa/include/bfa_fcptm.h b/drivers/scsi/bfa/include/bfa_fcptm.h new file mode 100644 index 000000000000..5f5ffe0bb1bb --- /dev/null +++ b/drivers/scsi/bfa/include/bfa_fcptm.h @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCPTM_H__ +#define __BFA_FCPTM_H__ + +#include <bfa.h> +#include <bfa_svc.h> +#include <bfi/bfi_fcptm.h> + +/* + * forward declarations + */ +struct bfa_tin_s; +struct bfa_iotm_s; +struct bfa_tsktm_s; + +/* + * bfa fcptm module API functions + */ +void bfa_fcptm_path_tov_set(struct bfa_s *bfa, u16 path_tov); +u16 bfa_fcptm_path_tov_get(struct bfa_s *bfa); +void bfa_fcptm_qdepth_set(struct bfa_s *bfa, u16 q_depth); +u16 bfa_fcptm_qdepth_get(struct bfa_s *bfa); + +/* + * bfa tin API functions + */ +void bfa_tin_get_stats(struct bfa_tin_s *tin, struct bfa_tin_stats_s *stats); +void bfa_tin_clear_stats(struct bfa_tin_s *tin); + +#endif /* __BFA_FCPTM_H__ */ + diff --git a/drivers/scsi/bfa/include/bfa_svc.h b/drivers/scsi/bfa/include/bfa_svc.h new file mode 100644 index 000000000000..0c80b74f72ef --- /dev/null +++ b/drivers/scsi/bfa/include/bfa_svc.h @@ -0,0 +1,324 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_SVC_H__ +#define __BFA_SVC_H__ + +/* + * forward declarations + */ +struct bfa_fcxp_s; + +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_pport.h> +#include <defs/bfa_defs_rport.h> +#include <defs/bfa_defs_qos.h> +#include <cs/bfa_sm.h> +#include <bfa.h> + +/** + * BFA rport information. + */ +struct bfa_rport_info_s { + u16 max_frmsz; /* max rcv pdu size */ + u32 pid : 24, /* remote port ID */ + lp_tag : 8; + u32 local_pid : 24, /* local port ID */ + cisc : 8; /* CIRO supported */ + u8 fc_class; /* supported FC classes. enum fc_cos */ + u8 vf_en; /* virtual fabric enable */ + u16 vf_id; /* virtual fabric ID */ + enum bfa_pport_speed speed; /* Rport's current speed */ +}; + +/** + * BFA rport data structure + */ +struct bfa_rport_s { + struct list_head qe; /* queue element */ + bfa_sm_t sm; /* state machine */ + struct bfa_s *bfa; /* backpointer to BFA */ + void *rport_drv; /* fcs/driver rport object */ + u16 fw_handle; /* firmware rport handle */ + u16 rport_tag; /* BFA rport tag */ + struct bfa_rport_info_s rport_info; /* rport info from *fcs/driver */ + struct bfa_reqq_wait_s reqq_wait; /* to wait for room in reqq */ + struct bfa_cb_qe_s hcb_qe; /* BFA callback qelem */ + struct bfa_rport_hal_stats_s stats; /* BFA rport statistics */ + struct bfa_rport_qos_attr_s qos_attr; + union a { + bfa_status_t status; /* f/w status */ + void *fw_msg; /* QoS scn event */ + } event_arg; +}; +#define BFA_RPORT_FC_COS(_rport) ((_rport)->rport_info.fc_class) + +/** + * Send completion callback. + */ +typedef void (*bfa_cb_fcxp_send_t) (void *bfad_fcxp, struct bfa_fcxp_s *fcxp, + void *cbarg, enum bfa_status req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs); + +/** + * BFA fcxp allocation (asynchronous) + */ +typedef void (*bfa_fcxp_alloc_cbfn_t) (void *cbarg, struct bfa_fcxp_s *fcxp); + +struct bfa_fcxp_wqe_s { + struct list_head qe; + bfa_fcxp_alloc_cbfn_t alloc_cbfn; + void *alloc_cbarg; +}; + +typedef u64 (*bfa_fcxp_get_sgaddr_t) (void *bfad_fcxp, int sgeid); +typedef u32 (*bfa_fcxp_get_sglen_t) (void *bfad_fcxp, int sgeid); + +#define BFA_UF_BUFSZ (2 * 1024 + 256) + +/** + * @todo private + */ +struct bfa_uf_buf_s { + u8 d[BFA_UF_BUFSZ]; +}; + + +struct bfa_uf_s { + struct list_head qe; /* queue element */ + struct bfa_s *bfa; /* bfa instance */ + u16 uf_tag; /* identifying tag f/w messages */ + u16 vf_id; + u16 src_rport_handle; + u16 rsvd; + u8 *data_ptr; + u16 data_len; /* actual receive length */ + u16 pb_len; /* posted buffer length */ + void *buf_kva; /* buffer virtual address */ + u64 buf_pa; /* buffer physical address */ + struct bfa_cb_qe_s hcb_qe; /* comp: BFA comp qelem */ + struct bfa_sge_s sges[BFI_SGE_INLINE_MAX]; +}; + +typedef void (*bfa_cb_pport_t) (void *cbarg, enum bfa_status status); + +/** + * bfa lport login/logout service interface + */ +struct bfa_lps_s { + struct list_head qe; /* queue element */ + struct bfa_s *bfa; /* parent bfa instance */ + bfa_sm_t sm; /* finite state machine */ + u8 lp_tag; /* lport tag */ + u8 reqq; /* lport request queue */ + u8 alpa; /* ALPA for loop topologies */ + u32 lp_pid; /* lport port ID */ + bfa_boolean_t fdisc; /* send FDISC instead of FLOGI*/ + bfa_boolean_t auth_en; /* enable authentication */ + bfa_boolean_t auth_req; /* authentication required */ + bfa_boolean_t npiv_en; /* NPIV is allowed by peer */ + bfa_boolean_t fport; /* attached peer is F_PORT */ + bfa_boolean_t brcd_switch;/* attached peer is brcd switch */ + bfa_status_t status; /* login status */ + u16 pdusz; /* max receive PDU size */ + u16 pr_bbcred; /* BB_CREDIT from peer */ + u8 lsrjt_rsn; /* LSRJT reason */ + u8 lsrjt_expl; /* LSRJT explanation */ + wwn_t pwwn; /* port wwn of lport */ + wwn_t nwwn; /* node wwn of lport */ + wwn_t pr_pwwn; /* port wwn of lport peer */ + wwn_t pr_nwwn; /* node wwn of lport peer */ + mac_t lp_mac; /* fpma/spma MAC for lport */ + mac_t fcf_mac; /* FCF MAC of lport */ + struct bfa_reqq_wait_s wqe; /* request wait queue element */ + void *uarg; /* user callback arg */ + struct bfa_cb_qe_s hcb_qe; /* comp: callback qelem */ + struct bfi_lps_login_rsp_s *loginrsp; + bfa_eproto_status_t ext_status; +}; + +/* + * bfa pport API functions + */ +bfa_status_t bfa_pport_enable(struct bfa_s *bfa); +bfa_status_t bfa_pport_disable(struct bfa_s *bfa); +bfa_status_t bfa_pport_cfg_speed(struct bfa_s *bfa, + enum bfa_pport_speed speed); +enum bfa_pport_speed bfa_pport_get_speed(struct bfa_s *bfa); +bfa_status_t bfa_pport_cfg_topology(struct bfa_s *bfa, + enum bfa_pport_topology topo); +enum bfa_pport_topology bfa_pport_get_topology(struct bfa_s *bfa); +bfa_status_t bfa_pport_cfg_hardalpa(struct bfa_s *bfa, u8 alpa); +bfa_boolean_t bfa_pport_get_hardalpa(struct bfa_s *bfa, u8 *alpa); +u8 bfa_pport_get_myalpa(struct bfa_s *bfa); +bfa_status_t bfa_pport_clr_hardalpa(struct bfa_s *bfa); +bfa_status_t bfa_pport_cfg_maxfrsize(struct bfa_s *bfa, u16 maxsize); +u16 bfa_pport_get_maxfrsize(struct bfa_s *bfa); +u32 bfa_pport_mypid(struct bfa_s *bfa); +u8 bfa_pport_get_rx_bbcredit(struct bfa_s *bfa); +bfa_status_t bfa_pport_trunk_enable(struct bfa_s *bfa, u8 bitmap); +bfa_status_t bfa_pport_trunk_disable(struct bfa_s *bfa); +bfa_boolean_t bfa_pport_trunk_query(struct bfa_s *bfa, u32 *bitmap); +void bfa_pport_get_attr(struct bfa_s *bfa, struct bfa_pport_attr_s *attr); +wwn_t bfa_pport_get_wwn(struct bfa_s *bfa, bfa_boolean_t node); +bfa_status_t bfa_pport_get_stats(struct bfa_s *bfa, + union bfa_pport_stats_u *stats, + bfa_cb_pport_t cbfn, void *cbarg); +bfa_status_t bfa_pport_clear_stats(struct bfa_s *bfa, bfa_cb_pport_t cbfn, + void *cbarg); +void bfa_pport_event_register(struct bfa_s *bfa, + void (*event_cbfn) (void *cbarg, + bfa_pport_event_t event), void *event_cbarg); +bfa_boolean_t bfa_pport_is_disabled(struct bfa_s *bfa); +void bfa_pport_cfg_qos(struct bfa_s *bfa, bfa_boolean_t on_off); +void bfa_pport_cfg_ratelim(struct bfa_s *bfa, bfa_boolean_t on_off); +bfa_status_t bfa_pport_cfg_ratelim_speed(struct bfa_s *bfa, + enum bfa_pport_speed speed); +enum bfa_pport_speed bfa_pport_get_ratelim_speed(struct bfa_s *bfa); + +void bfa_pport_set_tx_bbcredit(struct bfa_s *bfa, u16 tx_bbcredit); +void bfa_pport_busy(struct bfa_s *bfa, bfa_boolean_t status); +void bfa_pport_beacon(struct bfa_s *bfa, bfa_boolean_t beacon, + bfa_boolean_t link_e2e_beacon); +void bfa_cb_pport_event(void *cbarg, bfa_pport_event_t event); +void bfa_pport_qos_get_attr(struct bfa_s *bfa, struct bfa_qos_attr_s *qos_attr); +void bfa_pport_qos_get_vc_attr(struct bfa_s *bfa, + struct bfa_qos_vc_attr_s *qos_vc_attr); +bfa_status_t bfa_pport_get_qos_stats(struct bfa_s *bfa, + union bfa_pport_stats_u *stats, + bfa_cb_pport_t cbfn, void *cbarg); +bfa_status_t bfa_pport_clear_qos_stats(struct bfa_s *bfa, bfa_cb_pport_t cbfn, + void *cbarg); +bfa_boolean_t bfa_pport_is_ratelim(struct bfa_s *bfa); +bfa_boolean_t bfa_pport_is_linkup(struct bfa_s *bfa); + +/* + * bfa rport API functions + */ +struct bfa_rport_s *bfa_rport_create(struct bfa_s *bfa, void *rport_drv); +void bfa_rport_delete(struct bfa_rport_s *rport); +void bfa_rport_online(struct bfa_rport_s *rport, + struct bfa_rport_info_s *rport_info); +void bfa_rport_offline(struct bfa_rport_s *rport); +void bfa_rport_speed(struct bfa_rport_s *rport, enum bfa_pport_speed speed); +void bfa_rport_get_stats(struct bfa_rport_s *rport, + struct bfa_rport_hal_stats_s *stats); +void bfa_rport_clear_stats(struct bfa_rport_s *rport); +void bfa_cb_rport_online(void *rport); +void bfa_cb_rport_offline(void *rport); +void bfa_cb_rport_qos_scn_flowid(void *rport, + struct bfa_rport_qos_attr_s old_qos_attr, + struct bfa_rport_qos_attr_s new_qos_attr); +void bfa_cb_rport_qos_scn_prio(void *rport, + struct bfa_rport_qos_attr_s old_qos_attr, + struct bfa_rport_qos_attr_s new_qos_attr); +void bfa_rport_get_qos_attr(struct bfa_rport_s *rport, + struct bfa_rport_qos_attr_s *qos_attr); + +/* + * bfa fcxp API functions + */ +struct bfa_fcxp_s *bfa_fcxp_alloc(void *bfad_fcxp, struct bfa_s *bfa, + int nreq_sgles, int nrsp_sgles, + bfa_fcxp_get_sgaddr_t get_req_sga, + bfa_fcxp_get_sglen_t get_req_sglen, + bfa_fcxp_get_sgaddr_t get_rsp_sga, + bfa_fcxp_get_sglen_t get_rsp_sglen); +void bfa_fcxp_alloc_wait(struct bfa_s *bfa, struct bfa_fcxp_wqe_s *wqe, + bfa_fcxp_alloc_cbfn_t alloc_cbfn, void *cbarg); +void bfa_fcxp_walloc_cancel(struct bfa_s *bfa, + struct bfa_fcxp_wqe_s *wqe); +void bfa_fcxp_discard(struct bfa_fcxp_s *fcxp); + +void *bfa_fcxp_get_reqbuf(struct bfa_fcxp_s *fcxp); +void *bfa_fcxp_get_rspbuf(struct bfa_fcxp_s *fcxp); + +void bfa_fcxp_free(struct bfa_fcxp_s *fcxp); + +void bfa_fcxp_send(struct bfa_fcxp_s *fcxp, + struct bfa_rport_s *rport, u16 vf_id, u8 lp_tag, + bfa_boolean_t cts, enum fc_cos cos, + u32 reqlen, struct fchs_s *fchs, + bfa_cb_fcxp_send_t cbfn, + void *cbarg, + u32 rsp_maxlen, u8 rsp_timeout); +bfa_status_t bfa_fcxp_abort(struct bfa_fcxp_s *fcxp); +u32 bfa_fcxp_get_reqbufsz(struct bfa_fcxp_s *fcxp); +u32 bfa_fcxp_get_maxrsp(struct bfa_s *bfa); + +static inline void * +bfa_uf_get_frmbuf(struct bfa_uf_s *uf) +{ + return uf->data_ptr; +} + +static inline u16 +bfa_uf_get_frmlen(struct bfa_uf_s *uf) +{ + return uf->data_len; +} + +/** + * Callback prototype for unsolicited frame receive handler. + * + * @param[in] cbarg callback arg for receive handler + * @param[in] uf unsolicited frame descriptor + * + * @return None + */ +typedef void (*bfa_cb_uf_recv_t) (void *cbarg, struct bfa_uf_s *uf); + +/* + * bfa uf API functions + */ +void bfa_uf_recv_register(struct bfa_s *bfa, bfa_cb_uf_recv_t ufrecv, + void *cbarg); +void bfa_uf_free(struct bfa_uf_s *uf); + +/** + * bfa lport service api + */ + +struct bfa_lps_s *bfa_lps_alloc(struct bfa_s *bfa); +void bfa_lps_delete(struct bfa_lps_s *lps); +void bfa_lps_discard(struct bfa_lps_s *lps); +void bfa_lps_flogi(struct bfa_lps_s *lps, void *uarg, u8 alpa, u16 pdusz, + wwn_t pwwn, wwn_t nwwn, bfa_boolean_t auth_en); +void bfa_lps_fdisc(struct bfa_lps_s *lps, void *uarg, u16 pdusz, wwn_t pwwn, + wwn_t nwwn); +void bfa_lps_flogo(struct bfa_lps_s *lps); +void bfa_lps_fdisclogo(struct bfa_lps_s *lps); +u8 bfa_lps_get_tag(struct bfa_lps_s *lps); +bfa_boolean_t bfa_lps_is_npiv_en(struct bfa_lps_s *lps); +bfa_boolean_t bfa_lps_is_fport(struct bfa_lps_s *lps); +bfa_boolean_t bfa_lps_is_brcd_fabric(struct bfa_lps_s *lps); +bfa_boolean_t bfa_lps_is_authreq(struct bfa_lps_s *lps); +bfa_eproto_status_t bfa_lps_get_extstatus(struct bfa_lps_s *lps); +u32 bfa_lps_get_pid(struct bfa_lps_s *lps); +u8 bfa_lps_get_tag_from_pid(struct bfa_s *bfa, u32 pid); +u16 bfa_lps_get_peer_bbcredit(struct bfa_lps_s *lps); +wwn_t bfa_lps_get_peer_pwwn(struct bfa_lps_s *lps); +wwn_t bfa_lps_get_peer_nwwn(struct bfa_lps_s *lps); +u8 bfa_lps_get_lsrjt_rsn(struct bfa_lps_s *lps); +u8 bfa_lps_get_lsrjt_expl(struct bfa_lps_s *lps); +void bfa_cb_lps_flogi_comp(void *bfad, void *uarg, bfa_status_t status); +void bfa_cb_lps_flogo_comp(void *bfad, void *uarg); +void bfa_cb_lps_fdisc_comp(void *bfad, void *uarg, bfa_status_t status); +void bfa_cb_lps_fdisclogo_comp(void *bfad, void *uarg); + +#endif /* __BFA_SVC_H__ */ + diff --git a/drivers/scsi/bfa/include/bfa_timer.h b/drivers/scsi/bfa/include/bfa_timer.h new file mode 100644 index 000000000000..e407103fa565 --- /dev/null +++ b/drivers/scsi/bfa/include/bfa_timer.h @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_TIMER_H__ +#define __BFA_TIMER_H__ + +#include <bfa_os_inc.h> +#include <cs/bfa_q.h> + +struct bfa_s; + +typedef void (*bfa_timer_cbfn_t)(void *); + +/** + * BFA timer data structure + */ +struct bfa_timer_s { + struct list_head qe; + bfa_timer_cbfn_t timercb; + void *arg; + int timeout; /**< in millisecs. */ +}; + +/** + * Timer module structure + */ +struct bfa_timer_mod_s { + struct list_head timer_q; +}; + +#define BFA_TIMER_FREQ 500 /**< specified in millisecs */ + +void bfa_timer_beat(struct bfa_timer_mod_s *mod); +void bfa_timer_init(struct bfa_timer_mod_s *mod); +void bfa_timer_begin(struct bfa_timer_mod_s *mod, struct bfa_timer_s *timer, + bfa_timer_cbfn_t timercb, void *arg, + unsigned int timeout); +void bfa_timer_stop(struct bfa_timer_s *timer); + +#endif /* __BFA_TIMER_H__ */ diff --git a/drivers/scsi/bfa/include/bfi/bfi.h b/drivers/scsi/bfa/include/bfi/bfi.h new file mode 100644 index 000000000000..6cadfe0d4ba1 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi.h @@ -0,0 +1,174 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_H__ +#define __BFI_H__ + +#include <bfa_os_inc.h> +#include <defs/bfa_defs_status.h> + +#pragma pack(1) + +/** + * Msg header common to all msgs + */ +struct bfi_mhdr_s { + u8 msg_class; /* @ref bfi_mclass_t */ + u8 msg_id; /* msg opcode with in the class */ + union { + struct { + u8 rsvd; + u8 lpu_id; /* msg destination */ + } h2i; + u16 i2htok; /* token in msgs to host */ + } mtag; +}; + +#define bfi_h2i_set(_mh, _mc, _op, _lpuid) do { \ + (_mh).msg_class = (_mc); \ + (_mh).msg_id = (_op); \ + (_mh).mtag.h2i.lpu_id = (_lpuid); \ +} while (0) + +#define bfi_i2h_set(_mh, _mc, _op, _i2htok) do { \ + (_mh).msg_class = (_mc); \ + (_mh).msg_id = (_op); \ + (_mh).mtag.i2htok = (_i2htok); \ +} while (0) + +/* + * Message opcodes: 0-127 to firmware, 128-255 to host + */ +#define BFI_I2H_OPCODE_BASE 128 +#define BFA_I2HM(_x) ((_x) + BFI_I2H_OPCODE_BASE) + +/** + **************************************************************************** + * + * Scatter Gather Element and Page definition + * + **************************************************************************** + */ + +#define BFI_SGE_INLINE 1 +#define BFI_SGE_INLINE_MAX (BFI_SGE_INLINE + 1) + +/** + * SG Flags + */ +enum { + BFI_SGE_DATA = 0, /* data address, not last */ + BFI_SGE_DATA_CPL = 1, /* data addr, last in current page */ + BFI_SGE_DATA_LAST = 3, /* data address, last */ + BFI_SGE_LINK = 2, /* link address */ + BFI_SGE_PGDLEN = 2, /* cumulative data length for page */ +}; + +/** + * DMA addresses + */ +union bfi_addr_u { + struct { + u32 addr_lo; + u32 addr_hi; + } a32; +}; + +/** + * Scatter Gather Element + */ +struct bfi_sge_s { +#ifdef __BIGENDIAN + u32 flags : 2, + rsvd : 2, + sg_len : 28; +#else + u32 sg_len : 28, + rsvd : 2, + flags : 2; +#endif + union bfi_addr_u sga; +}; + +/** + * Scatter Gather Page + */ +#define BFI_SGPG_DATA_SGES 7 +#define BFI_SGPG_SGES_MAX (BFI_SGPG_DATA_SGES + 1) +#define BFI_SGPG_RSVD_WD_LEN 8 +struct bfi_sgpg_s { + struct bfi_sge_s sges[BFI_SGPG_SGES_MAX]; + u32 rsvd[BFI_SGPG_RSVD_WD_LEN]; +}; + +/* + * Large Message structure - 128 Bytes size Msgs + */ +#define BFI_LMSG_SZ 128 +#define BFI_LMSG_PL_WSZ \ + ((BFI_LMSG_SZ - sizeof(struct bfi_mhdr_s)) / 4) + +struct bfi_msg_s { + struct bfi_mhdr_s mhdr; + u32 pl[BFI_LMSG_PL_WSZ]; +}; + +/** + * Mailbox message structure + */ +#define BFI_MBMSG_SZ 7 +struct bfi_mbmsg_s { + struct bfi_mhdr_s mh; + u32 pl[BFI_MBMSG_SZ]; +}; + +/** + * Message Classes + */ +enum bfi_mclass { + BFI_MC_IOC = 1, /* IO Controller (IOC) */ + BFI_MC_DIAG = 2, /* Diagnostic Msgs */ + BFI_MC_FLASH = 3, /* Flash message class */ + BFI_MC_CEE = 4, + BFI_MC_FC_PORT = 5, /* FC port */ + BFI_MC_IOCFC = 6, /* FC - IO Controller (IOC) */ + BFI_MC_LL = 7, /* Link Layer */ + BFI_MC_UF = 8, /* Unsolicited frame receive */ + BFI_MC_FCXP = 9, /* FC Transport */ + BFI_MC_LPS = 10, /* lport fc login services */ + BFI_MC_RPORT = 11, /* Remote port */ + BFI_MC_ITNIM = 12, /* I-T nexus (Initiator mode) */ + BFI_MC_IOIM_READ = 13, /* read IO (Initiator mode) */ + BFI_MC_IOIM_WRITE = 14, /* write IO (Initiator mode) */ + BFI_MC_IOIM_IO = 15, /* IO (Initiator mode) */ + BFI_MC_IOIM = 16, /* IO (Initiator mode) */ + BFI_MC_IOIM_IOCOM = 17, /* good IO completion */ + BFI_MC_TSKIM = 18, /* Initiator Task management */ + BFI_MC_SBOOT = 19, /* SAN boot services */ + BFI_MC_IPFC = 20, /* IP over FC Msgs */ + BFI_MC_PORT = 21, /* Physical port */ + BFI_MC_MAX = 32 +}; + +#define BFI_IOC_MAX_CQS 4 +#define BFI_IOC_MAX_CQS_ASIC 8 +#define BFI_IOC_MSGLEN_MAX 32 /* 32 bytes */ + +#pragma pack() + +#endif /* __BFI_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_boot.h b/drivers/scsi/bfa/include/bfi/bfi_boot.h new file mode 100644 index 000000000000..5955afe7d108 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_boot.h @@ -0,0 +1,34 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +/* + * bfi_boot.h + */ + +#ifndef __BFI_BOOT_H__ +#define __BFI_BOOT_H__ + +#define BFI_BOOT_TYPE_OFF 8 +#define BFI_BOOT_PARAM_OFF 12 + +#define BFI_BOOT_TYPE_NORMAL 0 /* param is device id */ +#define BFI_BOOT_TYPE_FLASH 1 +#define BFI_BOOT_TYPE_MEMTEST 2 + +#define BFI_BOOT_MEMTEST_RES_ADDR 0x900 +#define BFI_BOOT_MEMTEST_RES_SIG 0xA0A1A2A3 + +#endif diff --git a/drivers/scsi/bfa/include/bfi/bfi_cbreg.h b/drivers/scsi/bfa/include/bfi/bfi_cbreg.h new file mode 100644 index 000000000000..b3bb52b565b1 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_cbreg.h @@ -0,0 +1,305 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* + * bfi_cbreg.h crossbow host block register definitions + * + * !!! Do not edit. Auto generated. !!! + */ + +#ifndef __BFI_CBREG_H__ +#define __BFI_CBREG_H__ + + +#define HOSTFN0_INT_STATUS 0x00014000 +#define __HOSTFN0_INT_STATUS_LVL_MK 0x00f00000 +#define __HOSTFN0_INT_STATUS_LVL_SH 20 +#define __HOSTFN0_INT_STATUS_LVL(_v) ((_v) << __HOSTFN0_INT_STATUS_LVL_SH) +#define __HOSTFN0_INT_STATUS_P 0x000fffff +#define HOSTFN0_INT_MSK 0x00014004 +#define HOST_PAGE_NUM_FN0 0x00014008 +#define __HOST_PAGE_NUM_FN 0x000001ff +#define HOSTFN1_INT_STATUS 0x00014100 +#define __HOSTFN1_INT_STAT_LVL_MK 0x00f00000 +#define __HOSTFN1_INT_STAT_LVL_SH 20 +#define __HOSTFN1_INT_STAT_LVL(_v) ((_v) << __HOSTFN1_INT_STAT_LVL_SH) +#define __HOSTFN1_INT_STAT_P 0x000fffff +#define HOSTFN1_INT_MSK 0x00014104 +#define HOST_PAGE_NUM_FN1 0x00014108 +#define APP_PLL_400_CTL_REG 0x00014204 +#define __P_400_PLL_LOCK 0x80000000 +#define __APP_PLL_400_SRAM_USE_100MHZ 0x00100000 +#define __APP_PLL_400_RESET_TIMER_MK 0x000e0000 +#define __APP_PLL_400_RESET_TIMER_SH 17 +#define __APP_PLL_400_RESET_TIMER(_v) ((_v) << __APP_PLL_400_RESET_TIMER_SH) +#define __APP_PLL_400_LOGIC_SOFT_RESET 0x00010000 +#define __APP_PLL_400_CNTLMT0_1_MK 0x0000c000 +#define __APP_PLL_400_CNTLMT0_1_SH 14 +#define __APP_PLL_400_CNTLMT0_1(_v) ((_v) << __APP_PLL_400_CNTLMT0_1_SH) +#define __APP_PLL_400_JITLMT0_1_MK 0x00003000 +#define __APP_PLL_400_JITLMT0_1_SH 12 +#define __APP_PLL_400_JITLMT0_1(_v) ((_v) << __APP_PLL_400_JITLMT0_1_SH) +#define __APP_PLL_400_HREF 0x00000800 +#define __APP_PLL_400_HDIV 0x00000400 +#define __APP_PLL_400_P0_1_MK 0x00000300 +#define __APP_PLL_400_P0_1_SH 8 +#define __APP_PLL_400_P0_1(_v) ((_v) << __APP_PLL_400_P0_1_SH) +#define __APP_PLL_400_Z0_2_MK 0x000000e0 +#define __APP_PLL_400_Z0_2_SH 5 +#define __APP_PLL_400_Z0_2(_v) ((_v) << __APP_PLL_400_Z0_2_SH) +#define __APP_PLL_400_RSEL200500 0x00000010 +#define __APP_PLL_400_ENARST 0x00000008 +#define __APP_PLL_400_BYPASS 0x00000004 +#define __APP_PLL_400_LRESETN 0x00000002 +#define __APP_PLL_400_ENABLE 0x00000001 +#define APP_PLL_212_CTL_REG 0x00014208 +#define __P_212_PLL_LOCK 0x80000000 +#define __APP_PLL_212_RESET_TIMER_MK 0x000e0000 +#define __APP_PLL_212_RESET_TIMER_SH 17 +#define __APP_PLL_212_RESET_TIMER(_v) ((_v) << __APP_PLL_212_RESET_TIMER_SH) +#define __APP_PLL_212_LOGIC_SOFT_RESET 0x00010000 +#define __APP_PLL_212_CNTLMT0_1_MK 0x0000c000 +#define __APP_PLL_212_CNTLMT0_1_SH 14 +#define __APP_PLL_212_CNTLMT0_1(_v) ((_v) << __APP_PLL_212_CNTLMT0_1_SH) +#define __APP_PLL_212_JITLMT0_1_MK 0x00003000 +#define __APP_PLL_212_JITLMT0_1_SH 12 +#define __APP_PLL_212_JITLMT0_1(_v) ((_v) << __APP_PLL_212_JITLMT0_1_SH) +#define __APP_PLL_212_HREF 0x00000800 +#define __APP_PLL_212_HDIV 0x00000400 +#define __APP_PLL_212_P0_1_MK 0x00000300 +#define __APP_PLL_212_P0_1_SH 8 +#define __APP_PLL_212_P0_1(_v) ((_v) << __APP_PLL_212_P0_1_SH) +#define __APP_PLL_212_Z0_2_MK 0x000000e0 +#define __APP_PLL_212_Z0_2_SH 5 +#define __APP_PLL_212_Z0_2(_v) ((_v) << __APP_PLL_212_Z0_2_SH) +#define __APP_PLL_212_RSEL200500 0x00000010 +#define __APP_PLL_212_ENARST 0x00000008 +#define __APP_PLL_212_BYPASS 0x00000004 +#define __APP_PLL_212_LRESETN 0x00000002 +#define __APP_PLL_212_ENABLE 0x00000001 +#define HOST_SEM0_REG 0x00014230 +#define __HOST_SEMAPHORE 0x00000001 +#define HOST_SEM1_REG 0x00014234 +#define HOST_SEM2_REG 0x00014238 +#define HOST_SEM3_REG 0x0001423c +#define HOST_SEM0_INFO_REG 0x00014240 +#define HOST_SEM1_INFO_REG 0x00014244 +#define HOST_SEM2_INFO_REG 0x00014248 +#define HOST_SEM3_INFO_REG 0x0001424c +#define HOSTFN0_LPU0_CMD_STAT 0x00019000 +#define __HOSTFN0_LPU0_MBOX_INFO_MK 0xfffffffe +#define __HOSTFN0_LPU0_MBOX_INFO_SH 1 +#define __HOSTFN0_LPU0_MBOX_INFO(_v) ((_v) << __HOSTFN0_LPU0_MBOX_INFO_SH) +#define __HOSTFN0_LPU0_MBOX_CMD_STATUS 0x00000001 +#define LPU0_HOSTFN0_CMD_STAT 0x00019008 +#define __LPU0_HOSTFN0_MBOX_INFO_MK 0xfffffffe +#define __LPU0_HOSTFN0_MBOX_INFO_SH 1 +#define __LPU0_HOSTFN0_MBOX_INFO(_v) ((_v) << __LPU0_HOSTFN0_MBOX_INFO_SH) +#define __LPU0_HOSTFN0_MBOX_CMD_STATUS 0x00000001 +#define HOSTFN1_LPU1_CMD_STAT 0x00019014 +#define __HOSTFN1_LPU1_MBOX_INFO_MK 0xfffffffe +#define __HOSTFN1_LPU1_MBOX_INFO_SH 1 +#define __HOSTFN1_LPU1_MBOX_INFO(_v) ((_v) << __HOSTFN1_LPU1_MBOX_INFO_SH) +#define __HOSTFN1_LPU1_MBOX_CMD_STATUS 0x00000001 +#define LPU1_HOSTFN1_CMD_STAT 0x0001901c +#define __LPU1_HOSTFN1_MBOX_INFO_MK 0xfffffffe +#define __LPU1_HOSTFN1_MBOX_INFO_SH 1 +#define __LPU1_HOSTFN1_MBOX_INFO(_v) ((_v) << __LPU1_HOSTFN1_MBOX_INFO_SH) +#define __LPU1_HOSTFN1_MBOX_CMD_STATUS 0x00000001 +#define CPE_Q0_DEPTH 0x00010014 +#define CPE_Q0_PI 0x0001001c +#define CPE_Q0_CI 0x00010020 +#define CPE_Q1_DEPTH 0x00010034 +#define CPE_Q1_PI 0x0001003c +#define CPE_Q1_CI 0x00010040 +#define CPE_Q2_DEPTH 0x00010054 +#define CPE_Q2_PI 0x0001005c +#define CPE_Q2_CI 0x00010060 +#define CPE_Q3_DEPTH 0x00010074 +#define CPE_Q3_PI 0x0001007c +#define CPE_Q3_CI 0x00010080 +#define CPE_Q4_DEPTH 0x00010094 +#define CPE_Q4_PI 0x0001009c +#define CPE_Q4_CI 0x000100a0 +#define CPE_Q5_DEPTH 0x000100b4 +#define CPE_Q5_PI 0x000100bc +#define CPE_Q5_CI 0x000100c0 +#define CPE_Q6_DEPTH 0x000100d4 +#define CPE_Q6_PI 0x000100dc +#define CPE_Q6_CI 0x000100e0 +#define CPE_Q7_DEPTH 0x000100f4 +#define CPE_Q7_PI 0x000100fc +#define CPE_Q7_CI 0x00010100 +#define RME_Q0_DEPTH 0x00011014 +#define RME_Q0_PI 0x0001101c +#define RME_Q0_CI 0x00011020 +#define RME_Q1_DEPTH 0x00011034 +#define RME_Q1_PI 0x0001103c +#define RME_Q1_CI 0x00011040 +#define RME_Q2_DEPTH 0x00011054 +#define RME_Q2_PI 0x0001105c +#define RME_Q2_CI 0x00011060 +#define RME_Q3_DEPTH 0x00011074 +#define RME_Q3_PI 0x0001107c +#define RME_Q3_CI 0x00011080 +#define RME_Q4_DEPTH 0x00011094 +#define RME_Q4_PI 0x0001109c +#define RME_Q4_CI 0x000110a0 +#define RME_Q5_DEPTH 0x000110b4 +#define RME_Q5_PI 0x000110bc +#define RME_Q5_CI 0x000110c0 +#define RME_Q6_DEPTH 0x000110d4 +#define RME_Q6_PI 0x000110dc +#define RME_Q6_CI 0x000110e0 +#define RME_Q7_DEPTH 0x000110f4 +#define RME_Q7_PI 0x000110fc +#define RME_Q7_CI 0x00011100 +#define PSS_CTL_REG 0x00018800 +#define __PSS_I2C_CLK_DIV_MK 0x00030000 +#define __PSS_I2C_CLK_DIV_SH 16 +#define __PSS_I2C_CLK_DIV(_v) ((_v) << __PSS_I2C_CLK_DIV_SH) +#define __PSS_LMEM_INIT_DONE 0x00001000 +#define __PSS_LMEM_RESET 0x00000200 +#define __PSS_LMEM_INIT_EN 0x00000100 +#define __PSS_LPU1_RESET 0x00000002 +#define __PSS_LPU0_RESET 0x00000001 + + +/* + * These definitions are either in error/missing in spec. Its auto-generated + * from hard coded values in regparse.pl. + */ +#define __EMPHPOST_AT_4G_MK_FIX 0x0000001c +#define __EMPHPOST_AT_4G_SH_FIX 0x00000002 +#define __EMPHPRE_AT_4G_FIX 0x00000003 +#define __SFP_TXRATE_EN_FIX 0x00000100 +#define __SFP_RXRATE_EN_FIX 0x00000080 + + +/* + * These register definitions are auto-generated from hard coded values + * in regparse.pl. + */ +#define HOSTFN0_LPU_MBOX0_0 0x00019200 +#define HOSTFN1_LPU_MBOX0_8 0x00019260 +#define LPU_HOSTFN0_MBOX0_0 0x00019280 +#define LPU_HOSTFN1_MBOX0_8 0x000192e0 + + +/* + * These register mapping definitions are auto-generated from mapping tables + * in regparse.pl. + */ +#define BFA_IOC0_HBEAT_REG HOST_SEM0_INFO_REG +#define BFA_IOC0_STATE_REG HOST_SEM1_INFO_REG +#define BFA_IOC1_HBEAT_REG HOST_SEM2_INFO_REG +#define BFA_IOC1_STATE_REG HOST_SEM3_INFO_REG +#define BFA_FW_USE_COUNT HOST_SEM4_INFO_REG + +#define CPE_Q_DEPTH(__n) \ + (CPE_Q0_DEPTH + (__n) * (CPE_Q1_DEPTH - CPE_Q0_DEPTH)) +#define CPE_Q_PI(__n) \ + (CPE_Q0_PI + (__n) * (CPE_Q1_PI - CPE_Q0_PI)) +#define CPE_Q_CI(__n) \ + (CPE_Q0_CI + (__n) * (CPE_Q1_CI - CPE_Q0_CI)) +#define RME_Q_DEPTH(__n) \ + (RME_Q0_DEPTH + (__n) * (RME_Q1_DEPTH - RME_Q0_DEPTH)) +#define RME_Q_PI(__n) \ + (RME_Q0_PI + (__n) * (RME_Q1_PI - RME_Q0_PI)) +#define RME_Q_CI(__n) \ + (RME_Q0_CI + (__n) * (RME_Q1_CI - RME_Q0_CI)) + +#define CPE_Q_NUM(__fn, __q) (((__fn) << 2) + (__q)) +#define RME_Q_NUM(__fn, __q) (((__fn) << 2) + (__q)) +#define CPE_Q_MASK(__q) ((__q) & 0x3) +#define RME_Q_MASK(__q) ((__q) & 0x3) + + +/* + * PCI MSI-X vector defines + */ +enum { + BFA_MSIX_CPE_Q0 = 0, + BFA_MSIX_CPE_Q1 = 1, + BFA_MSIX_CPE_Q2 = 2, + BFA_MSIX_CPE_Q3 = 3, + BFA_MSIX_CPE_Q4 = 4, + BFA_MSIX_CPE_Q5 = 5, + BFA_MSIX_CPE_Q6 = 6, + BFA_MSIX_CPE_Q7 = 7, + BFA_MSIX_RME_Q0 = 8, + BFA_MSIX_RME_Q1 = 9, + BFA_MSIX_RME_Q2 = 10, + BFA_MSIX_RME_Q3 = 11, + BFA_MSIX_RME_Q4 = 12, + BFA_MSIX_RME_Q5 = 13, + BFA_MSIX_RME_Q6 = 14, + BFA_MSIX_RME_Q7 = 15, + BFA_MSIX_ERR_EMC = 16, + BFA_MSIX_ERR_LPU0 = 17, + BFA_MSIX_ERR_LPU1 = 18, + BFA_MSIX_ERR_PSS = 19, + BFA_MSIX_MBOX_LPU0 = 20, + BFA_MSIX_MBOX_LPU1 = 21, + BFA_MSIX_CB_MAX = 22, +}; + +/* + * And corresponding host interrupt status bit field defines + */ +#define __HFN_INT_CPE_Q0 0x00000001U +#define __HFN_INT_CPE_Q1 0x00000002U +#define __HFN_INT_CPE_Q2 0x00000004U +#define __HFN_INT_CPE_Q3 0x00000008U +#define __HFN_INT_CPE_Q4 0x00000010U +#define __HFN_INT_CPE_Q5 0x00000020U +#define __HFN_INT_CPE_Q6 0x00000040U +#define __HFN_INT_CPE_Q7 0x00000080U +#define __HFN_INT_RME_Q0 0x00000100U +#define __HFN_INT_RME_Q1 0x00000200U +#define __HFN_INT_RME_Q2 0x00000400U +#define __HFN_INT_RME_Q3 0x00000800U +#define __HFN_INT_RME_Q4 0x00001000U +#define __HFN_INT_RME_Q5 0x00002000U +#define __HFN_INT_RME_Q6 0x00004000U +#define __HFN_INT_RME_Q7 0x00008000U +#define __HFN_INT_ERR_EMC 0x00010000U +#define __HFN_INT_ERR_LPU0 0x00020000U +#define __HFN_INT_ERR_LPU1 0x00040000U +#define __HFN_INT_ERR_PSS 0x00080000U +#define __HFN_INT_MBOX_LPU0 0x00100000U +#define __HFN_INT_MBOX_LPU1 0x00200000U +#define __HFN_INT_MBOX1_LPU0 0x00400000U +#define __HFN_INT_MBOX1_LPU1 0x00800000U +#define __HFN_INT_CPE_MASK 0x000000ffU +#define __HFN_INT_RME_MASK 0x0000ff00U + + +/* + * crossbow memory map. + */ +#define PSS_SMEM_PAGE_START 0x8000 +#define PSS_SMEM_PGNUM(_pg0, _ma) ((_pg0) + ((_ma) >> 15)) +#define PSS_SMEM_PGOFF(_ma) ((_ma) & 0x7fff) + +/* + * End of crossbow memory map + */ + + +#endif /* __BFI_CBREG_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_cee.h b/drivers/scsi/bfa/include/bfi/bfi_cee.h new file mode 100644 index 000000000000..0970596583ea --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_cee.h @@ -0,0 +1,119 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +/** + * Copyright (c) 2006-2009 Brocade Communications Systems, Inc. + * All rights reserved. + * + * bfi_dcbx.h BFI Interface (Mailbox commands and related structures) + * between host driver and DCBX/LLDP firmware module. + * +**/ + +#ifndef __BFI_CEE_H__ +#define __BFI_CEE_H__ + +#include <bfi/bfi.h> + +#pragma pack(1) + + +enum bfi_cee_h2i_msgs_e { + BFI_CEE_H2I_GET_CFG_REQ = 1, + BFI_CEE_H2I_RESET_STATS = 2, + BFI_CEE_H2I_GET_STATS_REQ = 3, +}; + + +enum bfi_cee_i2h_msgs_e { + BFI_CEE_I2H_GET_CFG_RSP = BFA_I2HM(1), + BFI_CEE_I2H_RESET_STATS_RSP = BFA_I2HM(2), + BFI_CEE_I2H_GET_STATS_RSP = BFA_I2HM(3), +}; + + +/* Data structures */ + +/* + * BFI_CEE_H2I_RESET_STATS + */ +struct bfi_lldp_reset_stats_s { + struct bfi_mhdr_s mh; +}; + +/* + * BFI_CEE_H2I_RESET_STATS + */ +struct bfi_cee_reset_stats_s { + struct bfi_mhdr_s mh; +}; + +/* + * BFI_CEE_H2I_GET_CFG_REQ + */ +struct bfi_cee_get_req_s { + struct bfi_mhdr_s mh; + union bfi_addr_u dma_addr; +}; + + +/* + * BFI_CEE_I2H_GET_CFG_RSP + */ +struct bfi_cee_get_rsp_s { + struct bfi_mhdr_s mh; + u8 cmd_status; + u8 rsvd[3]; +}; + +/* + * BFI_CEE_H2I_GET_STATS_REQ + */ +struct bfi_cee_stats_req_s { + struct bfi_mhdr_s mh; + union bfi_addr_u dma_addr; +}; + + +/* + * BFI_CEE_I2H_GET_STATS_RSP + */ +struct bfi_cee_stats_rsp_s { + struct bfi_mhdr_s mh; + u8 cmd_status; + u8 rsvd[3]; +}; + + + +union bfi_cee_h2i_msg_u { + struct bfi_mhdr_s mh; + struct bfi_cee_get_req_s get_req; + struct bfi_cee_stats_req_s stats_req; +}; + + +union bfi_cee_i2h_msg_u { + struct bfi_mhdr_s mh; + struct bfi_cee_get_rsp_s get_rsp; + struct bfi_cee_stats_rsp_s stats_rsp; +}; + +#pragma pack() + + +#endif /* __BFI_CEE_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_ctreg.h b/drivers/scsi/bfa/include/bfi/bfi_ctreg.h new file mode 100644 index 000000000000..d3caa58c0a0a --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_ctreg.h @@ -0,0 +1,611 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* + * bfi_ctreg.h catapult host block register definitions + * + * !!! Do not edit. Auto generated. !!! + */ + +#ifndef __BFI_CTREG_H__ +#define __BFI_CTREG_H__ + + +#define HOSTFN0_LPU_MBOX0_0 0x00019200 +#define HOSTFN1_LPU_MBOX0_8 0x00019260 +#define LPU_HOSTFN0_MBOX0_0 0x00019280 +#define LPU_HOSTFN1_MBOX0_8 0x000192e0 +#define HOSTFN2_LPU_MBOX0_0 0x00019400 +#define HOSTFN3_LPU_MBOX0_8 0x00019460 +#define LPU_HOSTFN2_MBOX0_0 0x00019480 +#define LPU_HOSTFN3_MBOX0_8 0x000194e0 +#define HOSTFN0_INT_STATUS 0x00014000 +#define __HOSTFN0_HALT_OCCURRED 0x01000000 +#define __HOSTFN0_INT_STATUS_LVL_MK 0x00f00000 +#define __HOSTFN0_INT_STATUS_LVL_SH 20 +#define __HOSTFN0_INT_STATUS_LVL(_v) ((_v) << __HOSTFN0_INT_STATUS_LVL_SH) +#define __HOSTFN0_INT_STATUS_P_MK 0x000f0000 +#define __HOSTFN0_INT_STATUS_P_SH 16 +#define __HOSTFN0_INT_STATUS_P(_v) ((_v) << __HOSTFN0_INT_STATUS_P_SH) +#define __HOSTFN0_INT_STATUS_F 0x0000ffff +#define HOSTFN0_INT_MSK 0x00014004 +#define HOST_PAGE_NUM_FN0 0x00014008 +#define __HOST_PAGE_NUM_FN 0x000001ff +#define HOST_MSIX_ERR_INDEX_FN0 0x0001400c +#define __MSIX_ERR_INDEX_FN 0x000001ff +#define HOSTFN1_INT_STATUS 0x00014100 +#define __HOSTFN1_HALT_OCCURRED 0x01000000 +#define __HOSTFN1_INT_STATUS_LVL_MK 0x00f00000 +#define __HOSTFN1_INT_STATUS_LVL_SH 20 +#define __HOSTFN1_INT_STATUS_LVL(_v) ((_v) << __HOSTFN1_INT_STATUS_LVL_SH) +#define __HOSTFN1_INT_STATUS_P_MK 0x000f0000 +#define __HOSTFN1_INT_STATUS_P_SH 16 +#define __HOSTFN1_INT_STATUS_P(_v) ((_v) << __HOSTFN1_INT_STATUS_P_SH) +#define __HOSTFN1_INT_STATUS_F 0x0000ffff +#define HOSTFN1_INT_MSK 0x00014104 +#define HOST_PAGE_NUM_FN1 0x00014108 +#define HOST_MSIX_ERR_INDEX_FN1 0x0001410c +#define APP_PLL_425_CTL_REG 0x00014204 +#define __P_425_PLL_LOCK 0x80000000 +#define __APP_PLL_425_SRAM_USE_100MHZ 0x00100000 +#define __APP_PLL_425_RESET_TIMER_MK 0x000e0000 +#define __APP_PLL_425_RESET_TIMER_SH 17 +#define __APP_PLL_425_RESET_TIMER(_v) ((_v) << __APP_PLL_425_RESET_TIMER_SH) +#define __APP_PLL_425_LOGIC_SOFT_RESET 0x00010000 +#define __APP_PLL_425_CNTLMT0_1_MK 0x0000c000 +#define __APP_PLL_425_CNTLMT0_1_SH 14 +#define __APP_PLL_425_CNTLMT0_1(_v) ((_v) << __APP_PLL_425_CNTLMT0_1_SH) +#define __APP_PLL_425_JITLMT0_1_MK 0x00003000 +#define __APP_PLL_425_JITLMT0_1_SH 12 +#define __APP_PLL_425_JITLMT0_1(_v) ((_v) << __APP_PLL_425_JITLMT0_1_SH) +#define __APP_PLL_425_HREF 0x00000800 +#define __APP_PLL_425_HDIV 0x00000400 +#define __APP_PLL_425_P0_1_MK 0x00000300 +#define __APP_PLL_425_P0_1_SH 8 +#define __APP_PLL_425_P0_1(_v) ((_v) << __APP_PLL_425_P0_1_SH) +#define __APP_PLL_425_Z0_2_MK 0x000000e0 +#define __APP_PLL_425_Z0_2_SH 5 +#define __APP_PLL_425_Z0_2(_v) ((_v) << __APP_PLL_425_Z0_2_SH) +#define __APP_PLL_425_RSEL200500 0x00000010 +#define __APP_PLL_425_ENARST 0x00000008 +#define __APP_PLL_425_BYPASS 0x00000004 +#define __APP_PLL_425_LRESETN 0x00000002 +#define __APP_PLL_425_ENABLE 0x00000001 +#define APP_PLL_312_CTL_REG 0x00014208 +#define __P_312_PLL_LOCK 0x80000000 +#define __ENABLE_MAC_AHB_1 0x00800000 +#define __ENABLE_MAC_AHB_0 0x00400000 +#define __ENABLE_MAC_1 0x00200000 +#define __ENABLE_MAC_0 0x00100000 +#define __APP_PLL_312_RESET_TIMER_MK 0x000e0000 +#define __APP_PLL_312_RESET_TIMER_SH 17 +#define __APP_PLL_312_RESET_TIMER(_v) ((_v) << __APP_PLL_312_RESET_TIMER_SH) +#define __APP_PLL_312_LOGIC_SOFT_RESET 0x00010000 +#define __APP_PLL_312_CNTLMT0_1_MK 0x0000c000 +#define __APP_PLL_312_CNTLMT0_1_SH 14 +#define __APP_PLL_312_CNTLMT0_1(_v) ((_v) << __APP_PLL_312_CNTLMT0_1_SH) +#define __APP_PLL_312_JITLMT0_1_MK 0x00003000 +#define __APP_PLL_312_JITLMT0_1_SH 12 +#define __APP_PLL_312_JITLMT0_1(_v) ((_v) << __APP_PLL_312_JITLMT0_1_SH) +#define __APP_PLL_312_HREF 0x00000800 +#define __APP_PLL_312_HDIV 0x00000400 +#define __APP_PLL_312_P0_1_MK 0x00000300 +#define __APP_PLL_312_P0_1_SH 8 +#define __APP_PLL_312_P0_1(_v) ((_v) << __APP_PLL_312_P0_1_SH) +#define __APP_PLL_312_Z0_2_MK 0x000000e0 +#define __APP_PLL_312_Z0_2_SH 5 +#define __APP_PLL_312_Z0_2(_v) ((_v) << __APP_PLL_312_Z0_2_SH) +#define __APP_PLL_312_RSEL200500 0x00000010 +#define __APP_PLL_312_ENARST 0x00000008 +#define __APP_PLL_312_BYPASS 0x00000004 +#define __APP_PLL_312_LRESETN 0x00000002 +#define __APP_PLL_312_ENABLE 0x00000001 +#define MBIST_CTL_REG 0x00014220 +#define __EDRAM_BISTR_START 0x00000004 +#define __MBIST_RESET 0x00000002 +#define __MBIST_START 0x00000001 +#define MBIST_STAT_REG 0x00014224 +#define __EDRAM_BISTR_STATUS 0x00000008 +#define __EDRAM_BISTR_DONE 0x00000004 +#define __MEM_BIT_STATUS 0x00000002 +#define __MBIST_DONE 0x00000001 +#define HOST_SEM0_REG 0x00014230 +#define __HOST_SEMAPHORE 0x00000001 +#define HOST_SEM1_REG 0x00014234 +#define HOST_SEM2_REG 0x00014238 +#define HOST_SEM3_REG 0x0001423c +#define HOST_SEM0_INFO_REG 0x00014240 +#define HOST_SEM1_INFO_REG 0x00014244 +#define HOST_SEM2_INFO_REG 0x00014248 +#define HOST_SEM3_INFO_REG 0x0001424c +#define ETH_MAC_SER_REG 0x00014288 +#define __APP_EMS_CKBUFAMPIN 0x00000020 +#define __APP_EMS_REFCLKSEL 0x00000010 +#define __APP_EMS_CMLCKSEL 0x00000008 +#define __APP_EMS_REFCKBUFEN2 0x00000004 +#define __APP_EMS_REFCKBUFEN1 0x00000002 +#define __APP_EMS_CHANNEL_SEL 0x00000001 +#define HOSTFN2_INT_STATUS 0x00014300 +#define __HOSTFN2_HALT_OCCURRED 0x01000000 +#define __HOSTFN2_INT_STATUS_LVL_MK 0x00f00000 +#define __HOSTFN2_INT_STATUS_LVL_SH 20 +#define __HOSTFN2_INT_STATUS_LVL(_v) ((_v) << __HOSTFN2_INT_STATUS_LVL_SH) +#define __HOSTFN2_INT_STATUS_P_MK 0x000f0000 +#define __HOSTFN2_INT_STATUS_P_SH 16 +#define __HOSTFN2_INT_STATUS_P(_v) ((_v) << __HOSTFN2_INT_STATUS_P_SH) +#define __HOSTFN2_INT_STATUS_F 0x0000ffff +#define HOSTFN2_INT_MSK 0x00014304 +#define HOST_PAGE_NUM_FN2 0x00014308 +#define HOST_MSIX_ERR_INDEX_FN2 0x0001430c +#define HOSTFN3_INT_STATUS 0x00014400 +#define __HALT_OCCURRED 0x01000000 +#define __HOSTFN3_INT_STATUS_LVL_MK 0x00f00000 +#define __HOSTFN3_INT_STATUS_LVL_SH 20 +#define __HOSTFN3_INT_STATUS_LVL(_v) ((_v) << __HOSTFN3_INT_STATUS_LVL_SH) +#define __HOSTFN3_INT_STATUS_P_MK 0x000f0000 +#define __HOSTFN3_INT_STATUS_P_SH 16 +#define __HOSTFN3_INT_STATUS_P(_v) ((_v) << __HOSTFN3_INT_STATUS_P_SH) +#define __HOSTFN3_INT_STATUS_F 0x0000ffff +#define HOSTFN3_INT_MSK 0x00014404 +#define HOST_PAGE_NUM_FN3 0x00014408 +#define HOST_MSIX_ERR_INDEX_FN3 0x0001440c +#define FNC_ID_REG 0x00014600 +#define __FUNCTION_NUMBER 0x00000007 +#define FNC_PERS_REG 0x00014604 +#define __F3_FUNCTION_ACTIVE 0x80000000 +#define __F3_FUNCTION_MODE 0x40000000 +#define __F3_PORT_MAP_MK 0x30000000 +#define __F3_PORT_MAP_SH 28 +#define __F3_PORT_MAP(_v) ((_v) << __F3_PORT_MAP_SH) +#define __F3_VM_MODE 0x08000000 +#define __F3_INTX_STATUS_MK 0x07000000 +#define __F3_INTX_STATUS_SH 24 +#define __F3_INTX_STATUS(_v) ((_v) << __F3_INTX_STATUS_SH) +#define __F2_FUNCTION_ACTIVE 0x00800000 +#define __F2_FUNCTION_MODE 0x00400000 +#define __F2_PORT_MAP_MK 0x00300000 +#define __F2_PORT_MAP_SH 20 +#define __F2_PORT_MAP(_v) ((_v) << __F2_PORT_MAP_SH) +#define __F2_VM_MODE 0x00080000 +#define __F2_INTX_STATUS_MK 0x00070000 +#define __F2_INTX_STATUS_SH 16 +#define __F2_INTX_STATUS(_v) ((_v) << __F2_INTX_STATUS_SH) +#define __F1_FUNCTION_ACTIVE 0x00008000 +#define __F1_FUNCTION_MODE 0x00004000 +#define __F1_PORT_MAP_MK 0x00003000 +#define __F1_PORT_MAP_SH 12 +#define __F1_PORT_MAP(_v) ((_v) << __F1_PORT_MAP_SH) +#define __F1_VM_MODE 0x00000800 +#define __F1_INTX_STATUS_MK 0x00000700 +#define __F1_INTX_STATUS_SH 8 +#define __F1_INTX_STATUS(_v) ((_v) << __F1_INTX_STATUS_SH) +#define __F0_FUNCTION_ACTIVE 0x00000080 +#define __F0_FUNCTION_MODE 0x00000040 +#define __F0_PORT_MAP_MK 0x00000030 +#define __F0_PORT_MAP_SH 4 +#define __F0_PORT_MAP(_v) ((_v) << __F0_PORT_MAP_SH) +#define __F0_VM_MODE 0x00000008 +#define __F0_INTX_STATUS 0x00000007 +enum { + __F0_INTX_STATUS_MSIX = 0x0, + __F0_INTX_STATUS_INTA = 0x1, + __F0_INTX_STATUS_INTB = 0x2, + __F0_INTX_STATUS_INTC = 0x3, + __F0_INTX_STATUS_INTD = 0x4, +}; +#define OP_MODE 0x0001460c +#define __APP_ETH_CLK_LOWSPEED 0x00000004 +#define __GLOBAL_CORECLK_HALFSPEED 0x00000002 +#define __GLOBAL_FCOE_MODE 0x00000001 +#define HOST_SEM4_REG 0x00014610 +#define HOST_SEM5_REG 0x00014614 +#define HOST_SEM6_REG 0x00014618 +#define HOST_SEM7_REG 0x0001461c +#define HOST_SEM4_INFO_REG 0x00014620 +#define HOST_SEM5_INFO_REG 0x00014624 +#define HOST_SEM6_INFO_REG 0x00014628 +#define HOST_SEM7_INFO_REG 0x0001462c +#define HOSTFN0_LPU0_MBOX0_CMD_STAT 0x00019000 +#define __HOSTFN0_LPU0_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN0_LPU0_MBOX0_INFO_SH 1 +#define __HOSTFN0_LPU0_MBOX0_INFO(_v) ((_v) << __HOSTFN0_LPU0_MBOX0_INFO_SH) +#define __HOSTFN0_LPU0_MBOX0_CMD_STATUS 0x00000001 +#define HOSTFN0_LPU1_MBOX0_CMD_STAT 0x00019004 +#define __HOSTFN0_LPU1_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN0_LPU1_MBOX0_INFO_SH 1 +#define __HOSTFN0_LPU1_MBOX0_INFO(_v) ((_v) << __HOSTFN0_LPU1_MBOX0_INFO_SH) +#define __HOSTFN0_LPU1_MBOX0_CMD_STATUS 0x00000001 +#define LPU0_HOSTFN0_MBOX0_CMD_STAT 0x00019008 +#define __LPU0_HOSTFN0_MBOX0_INFO_MK 0xfffffffe +#define __LPU0_HOSTFN0_MBOX0_INFO_SH 1 +#define __LPU0_HOSTFN0_MBOX0_INFO(_v) ((_v) << __LPU0_HOSTFN0_MBOX0_INFO_SH) +#define __LPU0_HOSTFN0_MBOX0_CMD_STATUS 0x00000001 +#define LPU1_HOSTFN0_MBOX0_CMD_STAT 0x0001900c +#define __LPU1_HOSTFN0_MBOX0_INFO_MK 0xfffffffe +#define __LPU1_HOSTFN0_MBOX0_INFO_SH 1 +#define __LPU1_HOSTFN0_MBOX0_INFO(_v) ((_v) << __LPU1_HOSTFN0_MBOX0_INFO_SH) +#define __LPU1_HOSTFN0_MBOX0_CMD_STATUS 0x00000001 +#define HOSTFN1_LPU0_MBOX0_CMD_STAT 0x00019010 +#define __HOSTFN1_LPU0_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN1_LPU0_MBOX0_INFO_SH 1 +#define __HOSTFN1_LPU0_MBOX0_INFO(_v) ((_v) << __HOSTFN1_LPU0_MBOX0_INFO_SH) +#define __HOSTFN1_LPU0_MBOX0_CMD_STATUS 0x00000001 +#define HOSTFN1_LPU1_MBOX0_CMD_STAT 0x00019014 +#define __HOSTFN1_LPU1_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN1_LPU1_MBOX0_INFO_SH 1 +#define __HOSTFN1_LPU1_MBOX0_INFO(_v) ((_v) << __HOSTFN1_LPU1_MBOX0_INFO_SH) +#define __HOSTFN1_LPU1_MBOX0_CMD_STATUS 0x00000001 +#define LPU0_HOSTFN1_MBOX0_CMD_STAT 0x00019018 +#define __LPU0_HOSTFN1_MBOX0_INFO_MK 0xfffffffe +#define __LPU0_HOSTFN1_MBOX0_INFO_SH 1 +#define __LPU0_HOSTFN1_MBOX0_INFO(_v) ((_v) << __LPU0_HOSTFN1_MBOX0_INFO_SH) +#define __LPU0_HOSTFN1_MBOX0_CMD_STATUS 0x00000001 +#define LPU1_HOSTFN1_MBOX0_CMD_STAT 0x0001901c +#define __LPU1_HOSTFN1_MBOX0_INFO_MK 0xfffffffe +#define __LPU1_HOSTFN1_MBOX0_INFO_SH 1 +#define __LPU1_HOSTFN1_MBOX0_INFO(_v) ((_v) << __LPU1_HOSTFN1_MBOX0_INFO_SH) +#define __LPU1_HOSTFN1_MBOX0_CMD_STATUS 0x00000001 +#define HOSTFN2_LPU0_MBOX0_CMD_STAT 0x00019150 +#define __HOSTFN2_LPU0_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN2_LPU0_MBOX0_INFO_SH 1 +#define __HOSTFN2_LPU0_MBOX0_INFO(_v) ((_v) << __HOSTFN2_LPU0_MBOX0_INFO_SH) +#define __HOSTFN2_LPU0_MBOX0_CMD_STATUS 0x00000001 +#define HOSTFN2_LPU1_MBOX0_CMD_STAT 0x00019154 +#define __HOSTFN2_LPU1_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN2_LPU1_MBOX0_INFO_SH 1 +#define __HOSTFN2_LPU1_MBOX0_INFO(_v) ((_v) << __HOSTFN2_LPU1_MBOX0_INFO_SH) +#define __HOSTFN2_LPU1_MBOX0BOX0_CMD_STATUS 0x00000001 +#define LPU0_HOSTFN2_MBOX0_CMD_STAT 0x00019158 +#define __LPU0_HOSTFN2_MBOX0_INFO_MK 0xfffffffe +#define __LPU0_HOSTFN2_MBOX0_INFO_SH 1 +#define __LPU0_HOSTFN2_MBOX0_INFO(_v) ((_v) << __LPU0_HOSTFN2_MBOX0_INFO_SH) +#define __LPU0_HOSTFN2_MBOX0_CMD_STATUS 0x00000001 +#define LPU1_HOSTFN2_MBOX0_CMD_STAT 0x0001915c +#define __LPU1_HOSTFN2_MBOX0_INFO_MK 0xfffffffe +#define __LPU1_HOSTFN2_MBOX0_INFO_SH 1 +#define __LPU1_HOSTFN2_MBOX0_INFO(_v) ((_v) << __LPU1_HOSTFN2_MBOX0_INFO_SH) +#define __LPU1_HOSTFN2_MBOX0_CMD_STATUS 0x00000001 +#define HOSTFN3_LPU0_MBOX0_CMD_STAT 0x00019160 +#define __HOSTFN3_LPU0_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN3_LPU0_MBOX0_INFO_SH 1 +#define __HOSTFN3_LPU0_MBOX0_INFO(_v) ((_v) << __HOSTFN3_LPU0_MBOX0_INFO_SH) +#define __HOSTFN3_LPU0_MBOX0_CMD_STATUS 0x00000001 +#define HOSTFN3_LPU1_MBOX0_CMD_STAT 0x00019164 +#define __HOSTFN3_LPU1_MBOX0_INFO_MK 0xfffffffe +#define __HOSTFN3_LPU1_MBOX0_INFO_SH 1 +#define __HOSTFN3_LPU1_MBOX0_INFO(_v) ((_v) << __HOSTFN3_LPU1_MBOX0_INFO_SH) +#define __HOSTFN3_LPU1_MBOX0_CMD_STATUS 0x00000001 +#define LPU0_HOSTFN3_MBOX0_CMD_STAT 0x00019168 +#define __LPU0_HOSTFN3_MBOX0_INFO_MK 0xfffffffe +#define __LPU0_HOSTFN3_MBOX0_INFO_SH 1 +#define __LPU0_HOSTFN3_MBOX0_INFO(_v) ((_v) << __LPU0_HOSTFN3_MBOX0_INFO_SH) +#define __LPU0_HOSTFN3_MBOX0_CMD_STATUS 0x00000001 +#define LPU1_HOSTFN3_MBOX0_CMD_STAT 0x0001916c +#define __LPU1_HOSTFN3_MBOX0_INFO_MK 0xfffffffe +#define __LPU1_HOSTFN3_MBOX0_INFO_SH 1 +#define __LPU1_HOSTFN3_MBOX0_INFO(_v) ((_v) << __LPU1_HOSTFN3_MBOX0_INFO_SH) +#define __LPU1_HOSTFN3_MBOX0_CMD_STATUS 0x00000001 +#define FW_INIT_HALT_P0 0x000191ac +#define __FW_INIT_HALT_P 0x00000001 +#define FW_INIT_HALT_P1 0x000191bc +#define CPE_PI_PTR_Q0 0x00038000 +#define __CPE_PI_UNUSED_MK 0xffff0000 +#define __CPE_PI_UNUSED_SH 16 +#define __CPE_PI_UNUSED(_v) ((_v) << __CPE_PI_UNUSED_SH) +#define __CPE_PI_PTR 0x0000ffff +#define CPE_PI_PTR_Q1 0x00038040 +#define CPE_CI_PTR_Q0 0x00038004 +#define __CPE_CI_UNUSED_MK 0xffff0000 +#define __CPE_CI_UNUSED_SH 16 +#define __CPE_CI_UNUSED(_v) ((_v) << __CPE_CI_UNUSED_SH) +#define __CPE_CI_PTR 0x0000ffff +#define CPE_CI_PTR_Q1 0x00038044 +#define CPE_DEPTH_Q0 0x00038008 +#define __CPE_DEPTH_UNUSED_MK 0xf8000000 +#define __CPE_DEPTH_UNUSED_SH 27 +#define __CPE_DEPTH_UNUSED(_v) ((_v) << __CPE_DEPTH_UNUSED_SH) +#define __CPE_MSIX_VEC_INDEX_MK 0x07ff0000 +#define __CPE_MSIX_VEC_INDEX_SH 16 +#define __CPE_MSIX_VEC_INDEX(_v) ((_v) << __CPE_MSIX_VEC_INDEX_SH) +#define __CPE_DEPTH 0x0000ffff +#define CPE_DEPTH_Q1 0x00038048 +#define CPE_QCTRL_Q0 0x0003800c +#define __CPE_CTRL_UNUSED30_MK 0xfc000000 +#define __CPE_CTRL_UNUSED30_SH 26 +#define __CPE_CTRL_UNUSED30(_v) ((_v) << __CPE_CTRL_UNUSED30_SH) +#define __CPE_FUNC_INT_CTRL_MK 0x03000000 +#define __CPE_FUNC_INT_CTRL_SH 24 +#define __CPE_FUNC_INT_CTRL(_v) ((_v) << __CPE_FUNC_INT_CTRL_SH) +enum { + __CPE_FUNC_INT_CTRL_DISABLE = 0x0, + __CPE_FUNC_INT_CTRL_F2NF = 0x1, + __CPE_FUNC_INT_CTRL_3QUART = 0x2, + __CPE_FUNC_INT_CTRL_HALF = 0x3, +}; +#define __CPE_CTRL_UNUSED20_MK 0x00f00000 +#define __CPE_CTRL_UNUSED20_SH 20 +#define __CPE_CTRL_UNUSED20(_v) ((_v) << __CPE_CTRL_UNUSED20_SH) +#define __CPE_SCI_TH_MK 0x000f0000 +#define __CPE_SCI_TH_SH 16 +#define __CPE_SCI_TH(_v) ((_v) << __CPE_SCI_TH_SH) +#define __CPE_CTRL_UNUSED10_MK 0x0000c000 +#define __CPE_CTRL_UNUSED10_SH 14 +#define __CPE_CTRL_UNUSED10(_v) ((_v) << __CPE_CTRL_UNUSED10_SH) +#define __CPE_ACK_PENDING 0x00002000 +#define __CPE_CTRL_UNUSED40_MK 0x00001c00 +#define __CPE_CTRL_UNUSED40_SH 10 +#define __CPE_CTRL_UNUSED40(_v) ((_v) << __CPE_CTRL_UNUSED40_SH) +#define __CPE_PCIEID_MK 0x00000300 +#define __CPE_PCIEID_SH 8 +#define __CPE_PCIEID(_v) ((_v) << __CPE_PCIEID_SH) +#define __CPE_CTRL_UNUSED00_MK 0x000000fe +#define __CPE_CTRL_UNUSED00_SH 1 +#define __CPE_CTRL_UNUSED00(_v) ((_v) << __CPE_CTRL_UNUSED00_SH) +#define __CPE_ESIZE 0x00000001 +#define CPE_QCTRL_Q1 0x0003804c +#define __CPE_CTRL_UNUSED31_MK 0xfc000000 +#define __CPE_CTRL_UNUSED31_SH 26 +#define __CPE_CTRL_UNUSED31(_v) ((_v) << __CPE_CTRL_UNUSED31_SH) +#define __CPE_CTRL_UNUSED21_MK 0x00f00000 +#define __CPE_CTRL_UNUSED21_SH 20 +#define __CPE_CTRL_UNUSED21(_v) ((_v) << __CPE_CTRL_UNUSED21_SH) +#define __CPE_CTRL_UNUSED11_MK 0x0000c000 +#define __CPE_CTRL_UNUSED11_SH 14 +#define __CPE_CTRL_UNUSED11(_v) ((_v) << __CPE_CTRL_UNUSED11_SH) +#define __CPE_CTRL_UNUSED41_MK 0x00001c00 +#define __CPE_CTRL_UNUSED41_SH 10 +#define __CPE_CTRL_UNUSED41(_v) ((_v) << __CPE_CTRL_UNUSED41_SH) +#define __CPE_CTRL_UNUSED01_MK 0x000000fe +#define __CPE_CTRL_UNUSED01_SH 1 +#define __CPE_CTRL_UNUSED01(_v) ((_v) << __CPE_CTRL_UNUSED01_SH) +#define RME_PI_PTR_Q0 0x00038020 +#define __LATENCY_TIME_STAMP_MK 0xffff0000 +#define __LATENCY_TIME_STAMP_SH 16 +#define __LATENCY_TIME_STAMP(_v) ((_v) << __LATENCY_TIME_STAMP_SH) +#define __RME_PI_PTR 0x0000ffff +#define RME_PI_PTR_Q1 0x00038060 +#define RME_CI_PTR_Q0 0x00038024 +#define __DELAY_TIME_STAMP_MK 0xffff0000 +#define __DELAY_TIME_STAMP_SH 16 +#define __DELAY_TIME_STAMP(_v) ((_v) << __DELAY_TIME_STAMP_SH) +#define __RME_CI_PTR 0x0000ffff +#define RME_CI_PTR_Q1 0x00038064 +#define RME_DEPTH_Q0 0x00038028 +#define __RME_DEPTH_UNUSED_MK 0xf8000000 +#define __RME_DEPTH_UNUSED_SH 27 +#define __RME_DEPTH_UNUSED(_v) ((_v) << __RME_DEPTH_UNUSED_SH) +#define __RME_MSIX_VEC_INDEX_MK 0x07ff0000 +#define __RME_MSIX_VEC_INDEX_SH 16 +#define __RME_MSIX_VEC_INDEX(_v) ((_v) << __RME_MSIX_VEC_INDEX_SH) +#define __RME_DEPTH 0x0000ffff +#define RME_DEPTH_Q1 0x00038068 +#define RME_QCTRL_Q0 0x0003802c +#define __RME_INT_LATENCY_TIMER_MK 0xff000000 +#define __RME_INT_LATENCY_TIMER_SH 24 +#define __RME_INT_LATENCY_TIMER(_v) ((_v) << __RME_INT_LATENCY_TIMER_SH) +#define __RME_INT_DELAY_TIMER_MK 0x00ff0000 +#define __RME_INT_DELAY_TIMER_SH 16 +#define __RME_INT_DELAY_TIMER(_v) ((_v) << __RME_INT_DELAY_TIMER_SH) +#define __RME_INT_DELAY_DISABLE 0x00008000 +#define __RME_DLY_DELAY_DISABLE 0x00004000 +#define __RME_ACK_PENDING 0x00002000 +#define __RME_FULL_INTERRUPT_DISABLE 0x00001000 +#define __RME_CTRL_UNUSED10_MK 0x00000c00 +#define __RME_CTRL_UNUSED10_SH 10 +#define __RME_CTRL_UNUSED10(_v) ((_v) << __RME_CTRL_UNUSED10_SH) +#define __RME_PCIEID_MK 0x00000300 +#define __RME_PCIEID_SH 8 +#define __RME_PCIEID(_v) ((_v) << __RME_PCIEID_SH) +#define __RME_CTRL_UNUSED00_MK 0x000000fe +#define __RME_CTRL_UNUSED00_SH 1 +#define __RME_CTRL_UNUSED00(_v) ((_v) << __RME_CTRL_UNUSED00_SH) +#define __RME_ESIZE 0x00000001 +#define RME_QCTRL_Q1 0x0003806c +#define __RME_CTRL_UNUSED11_MK 0x00000c00 +#define __RME_CTRL_UNUSED11_SH 10 +#define __RME_CTRL_UNUSED11(_v) ((_v) << __RME_CTRL_UNUSED11_SH) +#define __RME_CTRL_UNUSED01_MK 0x000000fe +#define __RME_CTRL_UNUSED01_SH 1 +#define __RME_CTRL_UNUSED01(_v) ((_v) << __RME_CTRL_UNUSED01_SH) +#define PSS_CTL_REG 0x00018800 +#define __PSS_I2C_CLK_DIV_MK 0x007f0000 +#define __PSS_I2C_CLK_DIV_SH 16 +#define __PSS_I2C_CLK_DIV(_v) ((_v) << __PSS_I2C_CLK_DIV_SH) +#define __PSS_LMEM_INIT_DONE 0x00001000 +#define __PSS_LMEM_RESET 0x00000200 +#define __PSS_LMEM_INIT_EN 0x00000100 +#define __PSS_LPU1_RESET 0x00000002 +#define __PSS_LPU0_RESET 0x00000001 +#define HQM_QSET0_RXQ_DRBL_P0 0x00038000 +#define __RXQ0_ADD_VECTORS_P 0x80000000 +#define __RXQ0_STOP_P 0x40000000 +#define __RXQ0_PRD_PTR_P 0x0000ffff +#define HQM_QSET1_RXQ_DRBL_P0 0x00038080 +#define __RXQ1_ADD_VECTORS_P 0x80000000 +#define __RXQ1_STOP_P 0x40000000 +#define __RXQ1_PRD_PTR_P 0x0000ffff +#define HQM_QSET0_RXQ_DRBL_P1 0x0003c000 +#define HQM_QSET1_RXQ_DRBL_P1 0x0003c080 +#define HQM_QSET0_TXQ_DRBL_P0 0x00038020 +#define __TXQ0_ADD_VECTORS_P 0x80000000 +#define __TXQ0_STOP_P 0x40000000 +#define __TXQ0_PRD_PTR_P 0x0000ffff +#define HQM_QSET1_TXQ_DRBL_P0 0x000380a0 +#define __TXQ1_ADD_VECTORS_P 0x80000000 +#define __TXQ1_STOP_P 0x40000000 +#define __TXQ1_PRD_PTR_P 0x0000ffff +#define HQM_QSET0_TXQ_DRBL_P1 0x0003c020 +#define HQM_QSET1_TXQ_DRBL_P1 0x0003c0a0 +#define HQM_QSET0_IB_DRBL_1_P0 0x00038040 +#define __IB1_0_ACK_P 0x80000000 +#define __IB1_0_DISABLE_P 0x40000000 +#define __IB1_0_NUM_OF_ACKED_EVENTS_P 0x0000ffff +#define HQM_QSET1_IB_DRBL_1_P0 0x000380c0 +#define __IB1_1_ACK_P 0x80000000 +#define __IB1_1_DISABLE_P 0x40000000 +#define __IB1_1_NUM_OF_ACKED_EVENTS_P 0x0000ffff +#define HQM_QSET0_IB_DRBL_1_P1 0x0003c040 +#define HQM_QSET1_IB_DRBL_1_P1 0x0003c0c0 +#define HQM_QSET0_IB_DRBL_2_P0 0x00038060 +#define __IB2_0_ACK_P 0x80000000 +#define __IB2_0_DISABLE_P 0x40000000 +#define __IB2_0_NUM_OF_ACKED_EVENTS_P 0x0000ffff +#define HQM_QSET1_IB_DRBL_2_P0 0x000380e0 +#define __IB2_1_ACK_P 0x80000000 +#define __IB2_1_DISABLE_P 0x40000000 +#define __IB2_1_NUM_OF_ACKED_EVENTS_P 0x0000ffff +#define HQM_QSET0_IB_DRBL_2_P1 0x0003c060 +#define HQM_QSET1_IB_DRBL_2_P1 0x0003c0e0 + + +/* + * These definitions are either in error/missing in spec. Its auto-generated + * from hard coded values in regparse.pl. + */ +#define __EMPHPOST_AT_4G_MK_FIX 0x0000001c +#define __EMPHPOST_AT_4G_SH_FIX 0x00000002 +#define __EMPHPRE_AT_4G_FIX 0x00000003 +#define __SFP_TXRATE_EN_FIX 0x00000100 +#define __SFP_RXRATE_EN_FIX 0x00000080 + + +/* + * These register definitions are auto-generated from hard coded values + * in regparse.pl. + */ + + +/* + * These register mapping definitions are auto-generated from mapping tables + * in regparse.pl. + */ +#define BFA_IOC0_HBEAT_REG HOST_SEM0_INFO_REG +#define BFA_IOC0_STATE_REG HOST_SEM1_INFO_REG +#define BFA_IOC1_HBEAT_REG HOST_SEM2_INFO_REG +#define BFA_IOC1_STATE_REG HOST_SEM3_INFO_REG +#define BFA_FW_USE_COUNT HOST_SEM4_INFO_REG + +#define CPE_DEPTH_Q(__n) \ + (CPE_DEPTH_Q0 + (__n) * (CPE_DEPTH_Q1 - CPE_DEPTH_Q0)) +#define CPE_QCTRL_Q(__n) \ + (CPE_QCTRL_Q0 + (__n) * (CPE_QCTRL_Q1 - CPE_QCTRL_Q0)) +#define CPE_PI_PTR_Q(__n) \ + (CPE_PI_PTR_Q0 + (__n) * (CPE_PI_PTR_Q1 - CPE_PI_PTR_Q0)) +#define CPE_CI_PTR_Q(__n) \ + (CPE_CI_PTR_Q0 + (__n) * (CPE_CI_PTR_Q1 - CPE_CI_PTR_Q0)) +#define RME_DEPTH_Q(__n) \ + (RME_DEPTH_Q0 + (__n) * (RME_DEPTH_Q1 - RME_DEPTH_Q0)) +#define RME_QCTRL_Q(__n) \ + (RME_QCTRL_Q0 + (__n) * (RME_QCTRL_Q1 - RME_QCTRL_Q0)) +#define RME_PI_PTR_Q(__n) \ + (RME_PI_PTR_Q0 + (__n) * (RME_PI_PTR_Q1 - RME_PI_PTR_Q0)) +#define RME_CI_PTR_Q(__n) \ + (RME_CI_PTR_Q0 + (__n) * (RME_CI_PTR_Q1 - RME_CI_PTR_Q0)) +#define HQM_QSET_RXQ_DRBL_P0(__n) \ + (HQM_QSET0_RXQ_DRBL_P0 + (__n) * (HQM_QSET1_RXQ_DRBL_P0 - \ + HQM_QSET0_RXQ_DRBL_P0)) +#define HQM_QSET_TXQ_DRBL_P0(__n) \ + (HQM_QSET0_TXQ_DRBL_P0 + (__n) * (HQM_QSET1_TXQ_DRBL_P0 - \ + HQM_QSET0_TXQ_DRBL_P0)) +#define HQM_QSET_IB_DRBL_1_P0(__n) \ + (HQM_QSET0_IB_DRBL_1_P0 + (__n) * (HQM_QSET1_IB_DRBL_1_P0 - \ + HQM_QSET0_IB_DRBL_1_P0)) +#define HQM_QSET_IB_DRBL_2_P0(__n) \ + (HQM_QSET0_IB_DRBL_2_P0 + (__n) * (HQM_QSET1_IB_DRBL_2_P0 - \ + HQM_QSET0_IB_DRBL_2_P0)) +#define HQM_QSET_RXQ_DRBL_P1(__n) \ + (HQM_QSET0_RXQ_DRBL_P1 + (__n) * (HQM_QSET1_RXQ_DRBL_P1 - \ + HQM_QSET0_RXQ_DRBL_P1)) +#define HQM_QSET_TXQ_DRBL_P1(__n) \ + (HQM_QSET0_TXQ_DRBL_P1 + (__n) * (HQM_QSET1_TXQ_DRBL_P1 - \ + HQM_QSET0_TXQ_DRBL_P1)) +#define HQM_QSET_IB_DRBL_1_P1(__n) \ + (HQM_QSET0_IB_DRBL_1_P1 + (__n) * (HQM_QSET1_IB_DRBL_1_P1 - \ + HQM_QSET0_IB_DRBL_1_P1)) +#define HQM_QSET_IB_DRBL_2_P1(__n) \ + (HQM_QSET0_IB_DRBL_2_P1 + (__n) * (HQM_QSET1_IB_DRBL_2_P1 - \ + HQM_QSET0_IB_DRBL_2_P1)) + +#define CPE_Q_NUM(__fn, __q) (((__fn) << 2) + (__q)) +#define RME_Q_NUM(__fn, __q) (((__fn) << 2) + (__q)) +#define CPE_Q_MASK(__q) ((__q) & 0x3) +#define RME_Q_MASK(__q) ((__q) & 0x3) + + +/* + * PCI MSI-X vector defines + */ +enum { + BFA_MSIX_CPE_Q0 = 0, + BFA_MSIX_CPE_Q1 = 1, + BFA_MSIX_CPE_Q2 = 2, + BFA_MSIX_CPE_Q3 = 3, + BFA_MSIX_RME_Q0 = 4, + BFA_MSIX_RME_Q1 = 5, + BFA_MSIX_RME_Q2 = 6, + BFA_MSIX_RME_Q3 = 7, + BFA_MSIX_LPU_ERR = 8, + BFA_MSIX_CT_MAX = 9, +}; + +/* + * And corresponding host interrupt status bit field defines + */ +#define __HFN_INT_CPE_Q0 0x00000001U +#define __HFN_INT_CPE_Q1 0x00000002U +#define __HFN_INT_CPE_Q2 0x00000004U +#define __HFN_INT_CPE_Q3 0x00000008U +#define __HFN_INT_CPE_Q4 0x00000010U +#define __HFN_INT_CPE_Q5 0x00000020U +#define __HFN_INT_CPE_Q6 0x00000040U +#define __HFN_INT_CPE_Q7 0x00000080U +#define __HFN_INT_RME_Q0 0x00000100U +#define __HFN_INT_RME_Q1 0x00000200U +#define __HFN_INT_RME_Q2 0x00000400U +#define __HFN_INT_RME_Q3 0x00000800U +#define __HFN_INT_RME_Q4 0x00001000U +#define __HFN_INT_RME_Q5 0x00002000U +#define __HFN_INT_RME_Q6 0x00004000U +#define __HFN_INT_RME_Q7 0x00008000U +#define __HFN_INT_ERR_EMC 0x00010000U +#define __HFN_INT_ERR_LPU0 0x00020000U +#define __HFN_INT_ERR_LPU1 0x00040000U +#define __HFN_INT_ERR_PSS 0x00080000U +#define __HFN_INT_MBOX_LPU0 0x00100000U +#define __HFN_INT_MBOX_LPU1 0x00200000U +#define __HFN_INT_MBOX1_LPU0 0x00400000U +#define __HFN_INT_MBOX1_LPU1 0x00800000U +#define __HFN_INT_CPE_MASK 0x000000ffU +#define __HFN_INT_RME_MASK 0x0000ff00U + + +/* + * catapult memory map. + */ +#define LL_PGN_HQM0 0x0096 +#define LL_PGN_HQM1 0x0097 +#define PSS_SMEM_PAGE_START 0x8000 +#define PSS_SMEM_PGNUM(_pg0, _ma) ((_pg0) + ((_ma) >> 15)) +#define PSS_SMEM_PGOFF(_ma) ((_ma) & 0x7fff) + +/* + * End of catapult memory map + */ + + +#endif /* __BFI_CTREG_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_fabric.h b/drivers/scsi/bfa/include/bfi/bfi_fabric.h new file mode 100644 index 000000000000..c0669ed41078 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_fabric.h @@ -0,0 +1,92 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_FABRIC_H__ +#define __BFI_FABRIC_H__ + +#include <bfi/bfi.h> + +#pragma pack(1) + +enum bfi_fabric_h2i_msgs { + BFI_FABRIC_H2I_CREATE_REQ = 1, + BFI_FABRIC_H2I_DELETE_REQ = 2, + BFI_FABRIC_H2I_SETAUTH = 3, +}; + +enum bfi_fabric_i2h_msgs { + BFI_FABRIC_I2H_CREATE_RSP = BFA_I2HM(1), + BFI_FABRIC_I2H_DELETE_RSP = BFA_I2HM(2), + BFI_FABRIC_I2H_SETAUTH_RSP = BFA_I2HM(3), + BFI_FABRIC_I2H_ONLINE = BFA_I2HM(4), + BFI_FABRIC_I2H_OFFLINE = BFA_I2HM(5), +}; + +struct bfi_fabric_create_req_s { + bfi_mhdr_t mh; /* common msg header */ + u8 vf_en; /* virtual fabric enable */ + u8 rsvd; + u16 vf_id; /* virtual fabric ID */ + wwn_t pwwn; /* port name */ + wwn_t nwwn; /* node name */ +}; + +struct bfi_fabric_create_rsp_s { + bfi_mhdr_t mh; /* common msg header */ + u16 bfa_handle; /* host fabric handle */ + u8 status; /* fabric create status */ + u8 rsvd; +}; + +struct bfi_fabric_delete_req_s { + bfi_mhdr_t mh; /* common msg header */ + u16 fw_handle; /* firmware fabric handle */ + u16 rsvd; +}; + +struct bfi_fabric_delete_rsp_s { + bfi_mhdr_t mh; /* common msg header */ + u16 bfa_handle; /* host fabric handle */ + u8 status; /* fabric deletion status */ + u8 rsvd; +}; + +#define BFI_FABRIC_AUTHSECRET_LEN 64 +struct bfi_fabric_setauth_req_s { + bfi_mhdr_t mh; /* common msg header */ + u16 fw_handle; /* f/w handle of fabric */ + u8 algorithm; + u8 group; + u8 secret[BFI_FABRIC_AUTHSECRET_LEN]; +}; + +union bfi_fabric_h2i_msg_u { + bfi_msg_t *msg; + struct bfi_fabric_create_req_s *create_req; + struct bfi_fabric_delete_req_s *delete_req; +}; + +union bfi_fabric_i2h_msg_u { + bfi_msg_t *msg; + struct bfi_fabric_create_rsp_s *create_rsp; + struct bfi_fabric_delete_rsp_s *delete_rsp; +}; + +#pragma pack() + +#endif /* __BFI_FABRIC_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_fcpim.h b/drivers/scsi/bfa/include/bfi/bfi_fcpim.h new file mode 100644 index 000000000000..52c059fb4c3a --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_fcpim.h @@ -0,0 +1,301 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_FCPIM_H__ +#define __BFI_FCPIM_H__ + +#include "bfi.h" +#include <protocol/fcp.h> + +#pragma pack(1) + +/* + * Initiator mode I-T nexus interface defines. + */ + +enum bfi_itnim_h2i { + BFI_ITNIM_H2I_CREATE_REQ = 1, /* i-t nexus creation */ + BFI_ITNIM_H2I_DELETE_REQ = 2, /* i-t nexus deletion */ +}; + +enum bfi_itnim_i2h { + BFI_ITNIM_I2H_CREATE_RSP = BFA_I2HM(1), + BFI_ITNIM_I2H_DELETE_RSP = BFA_I2HM(2), + BFI_ITNIM_I2H_SLER_EVENT = BFA_I2HM(3), +}; + +struct bfi_itnim_create_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 fw_handle; /* f/w handle for itnim */ + u8 class; /* FC class for IO */ + u8 seq_rec; /* sequence recovery support */ + u8 msg_no; /* seq id of the msg */ +}; + +struct bfi_itnim_create_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 bfa_handle; /* bfa handle for itnim */ + u8 status; /* fcp request status */ + u8 seq_id; /* seq id of the msg */ +}; + +struct bfi_itnim_delete_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 fw_handle; /* f/w itnim handle */ + u8 seq_id; /* seq id of the msg */ + u8 rsvd; +}; + +struct bfi_itnim_delete_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 bfa_handle; /* bfa handle for itnim */ + u8 status; /* fcp request status */ + u8 seq_id; /* seq id of the msg */ +}; + +struct bfi_itnim_sler_event_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 bfa_handle; /* bfa handle for itnim */ + u16 rsvd; +}; + +union bfi_itnim_h2i_msg_u { + struct bfi_itnim_create_req_s *create_req; + struct bfi_itnim_delete_req_s *delete_req; + struct bfi_msg_s *msg; +}; + +union bfi_itnim_i2h_msg_u { + struct bfi_itnim_create_rsp_s *create_rsp; + struct bfi_itnim_delete_rsp_s *delete_rsp; + struct bfi_itnim_sler_event_s *sler_event; + struct bfi_msg_s *msg; +}; + +/* + * Initiator mode IO interface defines. + */ + +enum bfi_ioim_h2i { + BFI_IOIM_H2I_IOABORT_REQ = 1, /* IO abort request */ + BFI_IOIM_H2I_IOCLEANUP_REQ = 2, /* IO cleanup request */ +}; + +enum bfi_ioim_i2h { + BFI_IOIM_I2H_IO_RSP = BFA_I2HM(1), /* non-fp IO response */ + BFI_IOIM_I2H_IOABORT_RSP = BFA_I2HM(2),/* ABORT rsp */ +}; + +/** + * IO command DIF info + */ +struct bfi_ioim_dif_s { + u32 dif_info[4]; +}; + +/** + * FCP IO messages overview + * + * @note + * - Max CDB length supported is 64 bytes. + * - SCSI Linked commands and SCSI bi-directional Commands not + * supported. + * + */ +struct bfi_ioim_req_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 io_tag; /* I/O tag */ + u16 rport_hdl; /* itnim/rport firmware handle */ + struct fcp_cmnd_s cmnd; /* IO request info */ + + /** + * SG elements array within the IO request must be double word + * aligned. This aligment is required to optimize SGM setup for the IO. + */ + struct bfi_sge_s sges[BFI_SGE_INLINE_MAX]; + u8 io_timeout; + u8 dif_en; + u8 rsvd_a[2]; + struct bfi_ioim_dif_s dif; +}; + +/** + * This table shows various IO status codes from firmware and their + * meaning. Host driver can use these status codes to further process + * IO completions. + * + * BFI_IOIM_STS_OK : IO completed with error free SCSI & + * transport status. + * - io-tag can be reused. + * + * BFA_IOIM_STS_SCSI_ERR : IO completed with scsi error. + * - io-tag can be reused. + * + * BFI_IOIM_STS_HOST_ABORTED : IO was aborted successfully due to + * host request. + * - io-tag cannot be reused yet. + * + * BFI_IOIM_STS_ABORTED : IO was aborted successfully + * internally by f/w. + * - io-tag cannot be reused yet. + * + * BFI_IOIM_STS_TIMEDOUT : IO timedout and ABTS/RRQ is happening + * in the firmware and + * - io-tag cannot be reused yet. + * + * BFI_IOIM_STS_SQER_NEEDED : Firmware could not recover the IO + * with sequence level error + * logic and hence host needs to retry + * this IO with a different IO tag + * - io-tag cannot be used yet. + * + * BFI_IOIM_STS_NEXUS_ABORT : Second Level Error Recovery from host + * is required because 2 consecutive ABTS + * timedout and host needs logout and + * re-login with the target + * - io-tag cannot be used yet. + * + * BFI_IOIM_STS_UNDERRUN : IO completed with SCSI status good, + * but the data tranferred is less than + * the fcp data length in the command. + * ex. SCSI INQUIRY where transferred + * data length and residue count in FCP + * response accounts for total fcp-dl + * - io-tag can be reused. + * + * BFI_IOIM_STS_OVERRUN : IO completed with SCSI status good, + * but the data transerred is more than + * fcp data length in the command. ex. + * TAPE IOs where blocks can of unequal + * lengths. + * - io-tag can be reused. + * + * BFI_IOIM_STS_RES_FREE : Firmware has completed using io-tag + * during abort process + * - io-tag can be reused. + * + * BFI_IOIM_STS_PROTO_ERR : Firmware detected a protocol error. + * ex target sent more data than + * requested, or there was data frame + * loss and other reasons + * - io-tag cannot be used yet. + * + * BFI_IOIM_STS_DIF_ERR : Firwmare detected DIF error. ex: DIF + * CRC err or Ref Tag err or App tag err. + * - io-tag can be reused. + * + * BFA_IOIM_STS_TSK_MGT_ABORT : IO was aborted because of Task + * Management command from the host + * - io-tag can be reused. + * + * BFI_IOIM_STS_UTAG : Firmware does not know about this + * io_tag. + * - io-tag can be reused. + */ +enum bfi_ioim_status { + BFI_IOIM_STS_OK = 0, + BFI_IOIM_STS_HOST_ABORTED = 1, + BFI_IOIM_STS_ABORTED = 2, + BFI_IOIM_STS_TIMEDOUT = 3, + BFI_IOIM_STS_RES_FREE = 4, + BFI_IOIM_STS_SQER_NEEDED = 5, + BFI_IOIM_STS_PROTO_ERR = 6, + BFI_IOIM_STS_UTAG = 7, + BFI_IOIM_STS_PATHTOV = 8, +}; + +#define BFI_IOIM_SNSLEN (256) +/** + * I/O response message + */ +struct bfi_ioim_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 io_tag; /* completed IO tag */ + u16 bfa_rport_hndl; /* releated rport handle */ + u8 io_status; /* IO completion status */ + u8 reuse_io_tag; /* IO tag can be reused */ + u16 abort_tag; /* host abort request tag */ + u8 scsi_status; /* scsi status from target */ + u8 sns_len; /* scsi sense length */ + u8 resid_flags; /* IO residue flags */ + u8 rsvd_a; + u32 residue; /* IO residual length in bytes */ + u32 rsvd_b[3]; +}; + +struct bfi_ioim_abort_req_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 io_tag; /* I/O tag */ + u16 abort_tag; /* unique request tag */ +}; + +/* + * Initiator mode task management command interface defines. + */ + +enum bfi_tskim_h2i { + BFI_TSKIM_H2I_TM_REQ = 1, /* task-mgmt command */ + BFI_TSKIM_H2I_ABORT_REQ = 2, /* task-mgmt command */ +}; + +enum bfi_tskim_i2h { + BFI_TSKIM_I2H_TM_RSP = BFA_I2HM(1), +}; + +struct bfi_tskim_req_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 tsk_tag; /* task management tag */ + u16 itn_fhdl; /* itn firmware handle */ + lun_t lun; /* LU number */ + u8 tm_flags; /* see fcp_tm_cmnd_t */ + u8 t_secs; /* Timeout value in seconds */ + u8 rsvd[2]; +}; + +struct bfi_tskim_abortreq_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 tsk_tag; /* task management tag */ + u16 rsvd; +}; + +enum bfi_tskim_status { + /* + * Following are FCP-4 spec defined status codes, + * **DO NOT CHANGE THEM ** + */ + BFI_TSKIM_STS_OK = 0, + BFI_TSKIM_STS_NOT_SUPP = 4, + BFI_TSKIM_STS_FAILED = 5, + + /** + * Defined by BFA + */ + BFI_TSKIM_STS_TIMEOUT = 10, /* TM request timedout */ + BFI_TSKIM_STS_ABORTED = 11, /* Aborted on host request */ +}; + +struct bfi_tskim_rsp_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 tsk_tag; /* task mgmt cmnd tag */ + u8 tsk_status; /* @ref bfi_tskim_status */ + u8 rsvd; +}; + +#pragma pack() + +#endif /* __BFI_FCPIM_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_fcxp.h b/drivers/scsi/bfa/include/bfi/bfi_fcxp.h new file mode 100644 index 000000000000..e0e995a32828 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_fcxp.h @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_FCXP_H__ +#define __BFI_FCXP_H__ + +#include "bfi.h" + +#pragma pack(1) + +enum bfi_fcxp_h2i { + BFI_FCXP_H2I_SEND_REQ = 1, +}; + +enum bfi_fcxp_i2h { + BFI_FCXP_I2H_SEND_RSP = BFA_I2HM(1), +}; + +#define BFA_FCXP_MAX_SGES 2 + +/** + * FCXP send request structure + */ +struct bfi_fcxp_send_req_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 fcxp_tag; /* driver request tag */ + u16 max_frmsz; /* max send frame size */ + u16 vf_id; /* vsan tag if applicable */ + u16 rport_fw_hndl; /* FW Handle for the remote port */ + u8 class; /* FC class used for req/rsp */ + u8 rsp_timeout; /* timeout in secs, 0-no response */ + u8 cts; /* continue sequence */ + u8 lp_tag; /* lport tag */ + struct fchs_s fchs; /* request FC header structure */ + u32 req_len; /* request payload length */ + u32 rsp_maxlen; /* max response length expected */ + struct bfi_sge_s req_sge[BFA_FCXP_MAX_SGES]; /* request buf */ + struct bfi_sge_s rsp_sge[BFA_FCXP_MAX_SGES]; /* response buf */ +}; + +/** + * FCXP send response structure + */ +struct bfi_fcxp_send_rsp_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 fcxp_tag; /* send request tag */ + u8 req_status; /* request status */ + u8 rsvd; + u32 rsp_len; /* actual response length */ + u32 residue_len; /* residual response length */ + struct fchs_s fchs; /* response FC header structure */ +}; + +#pragma pack() + +#endif /* __BFI_FCXP_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_ioc.h b/drivers/scsi/bfa/include/bfi/bfi_ioc.h new file mode 100644 index 000000000000..026e9c06ae97 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_ioc.h @@ -0,0 +1,202 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_IOC_H__ +#define __BFI_IOC_H__ + +#include "bfi.h" +#include <defs/bfa_defs_ioc.h> + +#pragma pack(1) + +enum bfi_ioc_h2i_msgs { + BFI_IOC_H2I_ENABLE_REQ = 1, + BFI_IOC_H2I_DISABLE_REQ = 2, + BFI_IOC_H2I_GETATTR_REQ = 3, + BFI_IOC_H2I_DBG_SYNC = 4, + BFI_IOC_H2I_DBG_DUMP = 5, +}; + +enum bfi_ioc_i2h_msgs { + BFI_IOC_I2H_ENABLE_REPLY = BFA_I2HM(1), + BFI_IOC_I2H_DISABLE_REPLY = BFA_I2HM(2), + BFI_IOC_I2H_GETATTR_REPLY = BFA_I2HM(3), + BFI_IOC_I2H_READY_EVENT = BFA_I2HM(4), + BFI_IOC_I2H_HBEAT = BFA_I2HM(5), +}; + +/** + * BFI_IOC_H2I_GETATTR_REQ message + */ +struct bfi_ioc_getattr_req_s { + struct bfi_mhdr_s mh; + union bfi_addr_u attr_addr; +}; + +struct bfi_ioc_attr_s { + wwn_t mfg_wwn; + mac_t mfg_mac; + u16 rsvd_a; + char brcd_serialnum[STRSZ(BFA_MFG_SERIALNUM_SIZE)]; + u8 pcie_gen; + u8 pcie_lanes_orig; + u8 pcie_lanes; + u8 rx_bbcredit; /* receive buffer credits */ + u32 adapter_prop; /* adapter properties */ + u16 maxfrsize; /* max receive frame size */ + char asic_rev; + u8 rsvd_b; + char fw_version[BFA_VERSION_LEN]; + char optrom_version[BFA_VERSION_LEN]; + struct bfa_mfg_vpd_s vpd; +}; + +/** + * BFI_IOC_I2H_GETATTR_REPLY message + */ +struct bfi_ioc_getattr_reply_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u8 status; /* cfg reply status */ + u8 rsvd[3]; +}; + +/** + * Firmware memory page offsets + */ +#define BFI_IOC_SMEM_PG0_CB (0x40) +#define BFI_IOC_SMEM_PG0_CT (0x180) + +/** + * Firmware trace offset + */ +#define BFI_IOC_TRC_OFF (0x4b00) +#define BFI_IOC_TRC_ENTS 256 + +#define BFI_IOC_FW_SIGNATURE (0xbfadbfad) +#define BFI_IOC_MD5SUM_SZ 4 +struct bfi_ioc_image_hdr_s { + u32 signature; /* constant signature */ + u32 rsvd_a; + u32 exec; /* exec vector */ + u32 param; /* parameters */ + u32 rsvd_b[4]; + u32 md5sum[BFI_IOC_MD5SUM_SZ]; +}; + +/** + * BFI_IOC_I2H_READY_EVENT message + */ +struct bfi_ioc_rdy_event_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 init_status; /* init event status */ + u8 rsvd[3]; +}; + +struct bfi_ioc_hbeat_s { + struct bfi_mhdr_s mh; /* common msg header */ + u32 hb_count; /* current heart beat count */ +}; + +/** + * IOC hardware/firmware state + */ +enum bfi_ioc_state { + BFI_IOC_UNINIT = 0, /* not initialized */ + BFI_IOC_INITING = 1, /* h/w is being initialized */ + BFI_IOC_HWINIT = 2, /* h/w is initialized */ + BFI_IOC_CFG = 3, /* IOC configuration in progress */ + BFI_IOC_OP = 4, /* IOC is operational */ + BFI_IOC_DISABLING = 5, /* IOC is being disabled */ + BFI_IOC_DISABLED = 6, /* IOC is disabled */ + BFI_IOC_CFG_DISABLED = 7, /* IOC is being disabled;transient */ + BFI_IOC_HBFAIL = 8, /* IOC heart-beat failure */ + BFI_IOC_MEMTEST = 9, /* IOC is doing memtest */ +}; + +#define BFI_IOC_ENDIAN_SIG 0x12345678 + +enum { + BFI_ADAPTER_TYPE_FC = 0x01, /* FC adapters */ + BFI_ADAPTER_TYPE_MK = 0x0f0000, /* adapter type mask */ + BFI_ADAPTER_TYPE_SH = 16, /* adapter type shift */ + BFI_ADAPTER_NPORTS_MK = 0xff00, /* number of ports mask */ + BFI_ADAPTER_NPORTS_SH = 8, /* number of ports shift */ + BFI_ADAPTER_SPEED_MK = 0xff, /* adapter speed mask */ + BFI_ADAPTER_SPEED_SH = 0, /* adapter speed shift */ + BFI_ADAPTER_PROTO = 0x100000, /* prototype adapaters */ + BFI_ADAPTER_TTV = 0x200000, /* TTV debug capable */ + BFI_ADAPTER_UNSUPP = 0x400000, /* unknown adapter type */ +}; + +#define BFI_ADAPTER_GETP(__prop,__adap_prop) \ + (((__adap_prop) & BFI_ADAPTER_ ## __prop ## _MK) >> \ + BFI_ADAPTER_ ## __prop ## _SH) +#define BFI_ADAPTER_SETP(__prop, __val) \ + ((__val) << BFI_ADAPTER_ ## __prop ## _SH) +#define BFI_ADAPTER_IS_PROTO(__adap_type) \ + ((__adap_type) & BFI_ADAPTER_PROTO) +#define BFI_ADAPTER_IS_TTV(__adap_type) \ + ((__adap_type) & BFI_ADAPTER_TTV) +#define BFI_ADAPTER_IS_UNSUPP(__adap_type) \ + ((__adap_type) & BFI_ADAPTER_UNSUPP) +#define BFI_ADAPTER_IS_SPECIAL(__adap_type) \ + ((__adap_type) & (BFI_ADAPTER_TTV | BFI_ADAPTER_PROTO | \ + BFI_ADAPTER_UNSUPP)) + +/** + * BFI_IOC_H2I_ENABLE_REQ & BFI_IOC_H2I_DISABLE_REQ messages + */ +struct bfi_ioc_ctrl_req_s { + struct bfi_mhdr_s mh; + u8 ioc_class; + u8 rsvd[3]; +}; + +/** + * BFI_IOC_I2H_ENABLE_REPLY & BFI_IOC_I2H_DISABLE_REPLY messages + */ +struct bfi_ioc_ctrl_reply_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u8 status; /* enable/disable status */ + u8 rsvd[3]; +}; + +#define BFI_IOC_MSGSZ 8 +/** + * H2I Messages + */ +union bfi_ioc_h2i_msg_u { + struct bfi_mhdr_s mh; + struct bfi_ioc_ctrl_req_s enable_req; + struct bfi_ioc_ctrl_req_s disable_req; + struct bfi_ioc_getattr_req_s getattr_req; + u32 mboxmsg[BFI_IOC_MSGSZ]; +}; + +/** + * I2H Messages + */ +union bfi_ioc_i2h_msg_u { + struct bfi_mhdr_s mh; + struct bfi_ioc_rdy_event_s rdy_event; + u32 mboxmsg[BFI_IOC_MSGSZ]; +}; + +#pragma pack() + +#endif /* __BFI_IOC_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_iocfc.h b/drivers/scsi/bfa/include/bfi/bfi_iocfc.h new file mode 100644 index 000000000000..c3760df72575 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_iocfc.h @@ -0,0 +1,177 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_IOCFC_H__ +#define __BFI_IOCFC_H__ + +#include "bfi.h" +#include <defs/bfa_defs_ioc.h> +#include <defs/bfa_defs_iocfc.h> +#include <defs/bfa_defs_boot.h> + +#pragma pack(1) + +enum bfi_iocfc_h2i_msgs { + BFI_IOCFC_H2I_CFG_REQ = 1, + BFI_IOCFC_H2I_GET_STATS_REQ = 2, + BFI_IOCFC_H2I_CLEAR_STATS_REQ = 3, + BFI_IOCFC_H2I_SET_INTR_REQ = 4, + BFI_IOCFC_H2I_UPDATEQ_REQ = 5, +}; + +enum bfi_iocfc_i2h_msgs { + BFI_IOCFC_I2H_CFG_REPLY = BFA_I2HM(1), + BFI_IOCFC_I2H_GET_STATS_RSP = BFA_I2HM(2), + BFI_IOCFC_I2H_CLEAR_STATS_RSP = BFA_I2HM(3), + BFI_IOCFC_I2H_UPDATEQ_RSP = BFA_I2HM(5), +}; + +struct bfi_iocfc_cfg_s { + u8 num_cqs; /* Number of CQs to be used */ + u8 sense_buf_len; /* SCSI sense length */ + u8 trunk_enabled; /* port trunking enabled */ + u8 trunk_ports; /* trunk ports bit map */ + u32 endian_sig; /* endian signature of host */ + + /** + * Request and response circular queue base addresses, size and + * shadow index pointers. + */ + union bfi_addr_u req_cq_ba[BFI_IOC_MAX_CQS]; + union bfi_addr_u req_shadow_ci[BFI_IOC_MAX_CQS]; + u16 req_cq_elems[BFI_IOC_MAX_CQS]; + union bfi_addr_u rsp_cq_ba[BFI_IOC_MAX_CQS]; + union bfi_addr_u rsp_shadow_pi[BFI_IOC_MAX_CQS]; + u16 rsp_cq_elems[BFI_IOC_MAX_CQS]; + + union bfi_addr_u stats_addr; /* DMA-able address for stats */ + union bfi_addr_u cfgrsp_addr; /* config response dma address */ + union bfi_addr_u ioim_snsbase; /* IO sense buffer base address */ + struct bfa_iocfc_intr_attr_s intr_attr; /* IOC interrupt attributes */ +}; + +/** + * Boot target wwn information for this port. This contains either the stored + * or discovered boot target port wwns for the port. + */ +struct bfi_iocfc_bootwwns { + wwn_t wwn[BFA_BOOT_BOOTLUN_MAX]; + u8 nwwns; + u8 rsvd[7]; +}; + +struct bfi_iocfc_cfgrsp_s { + struct bfa_iocfc_fwcfg_s fwcfg; + struct bfa_iocfc_intr_attr_s intr_attr; + struct bfi_iocfc_bootwwns bootwwns; +}; + +/** + * BFI_IOCFC_H2I_CFG_REQ message + */ +struct bfi_iocfc_cfg_req_s { + struct bfi_mhdr_s mh; + union bfi_addr_u ioc_cfg_dma_addr; +}; + +/** + * BFI_IOCFC_I2H_CFG_REPLY message + */ +struct bfi_iocfc_cfg_reply_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u8 cfg_success; /* cfg reply status */ + u8 lpu_bm; /* LPUs assigned for this IOC */ + u8 rsvd[2]; +}; + +/** + * BFI_IOCFC_H2I_GET_STATS_REQ & BFI_IOCFC_H2I_CLEAR_STATS_REQ messages + */ +struct bfi_iocfc_stats_req_s { + struct bfi_mhdr_s mh; /* msg header */ + u32 msgtag; /* msgtag for reply */ +}; + +/** + * BFI_IOCFC_I2H_GET_STATS_RSP & BFI_IOCFC_I2H_CLEAR_STATS_RSP messages + */ +struct bfi_iocfc_stats_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 status; /* reply status */ + u8 rsvd[3]; + u32 msgtag; /* msgtag for reply */ +}; + +/** + * BFI_IOCFC_H2I_SET_INTR_REQ message + */ +struct bfi_iocfc_set_intr_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 coalesce; /* enable intr coalescing*/ + u8 rsvd[3]; + u16 delay; /* delay timer 0..1125us */ + u16 latency; /* latency timer 0..225us */ +}; + +/** + * BFI_IOCFC_H2I_UPDATEQ_REQ message + */ +struct bfi_iocfc_updateq_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u32 reqq_ba; /* reqq base addr */ + u32 rspq_ba; /* rspq base addr */ + u32 reqq_sci; /* reqq shadow ci */ + u32 rspq_spi; /* rspq shadow pi */ +}; + +/** + * BFI_IOCFC_I2H_UPDATEQ_RSP message + */ +struct bfi_iocfc_updateq_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 status; /* updateq status */ + u8 rsvd[3]; +}; + +/** + * H2I Messages + */ +union bfi_iocfc_h2i_msg_u { + struct bfi_mhdr_s mh; + struct bfi_iocfc_cfg_req_s cfg_req; + struct bfi_iocfc_stats_req_s stats_get; + struct bfi_iocfc_stats_req_s stats_clr; + struct bfi_iocfc_updateq_req_s updateq_req; + u32 mboxmsg[BFI_IOC_MSGSZ]; +}; + +/** + * I2H Messages + */ +union bfi_iocfc_i2h_msg_u { + struct bfi_mhdr_s mh; + struct bfi_iocfc_cfg_reply_s cfg_reply; + struct bfi_iocfc_stats_rsp_s stats_get_rsp; + struct bfi_iocfc_stats_rsp_s stats_clr_rsp; + struct bfi_iocfc_updateq_rsp_s updateq_rsp; + u32 mboxmsg[BFI_IOC_MSGSZ]; +}; + +#pragma pack() + +#endif /* __BFI_IOCFC_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_lport.h b/drivers/scsi/bfa/include/bfi/bfi_lport.h new file mode 100644 index 000000000000..29010614bac9 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_lport.h @@ -0,0 +1,89 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_LPORT_H__ +#define __BFI_LPORT_H__ + +#include <bfi/bfi.h> + +#pragma pack(1) + +enum bfi_lport_h2i_msgs { + BFI_LPORT_H2I_CREATE_REQ = 1, + BFI_LPORT_H2I_DELETE_REQ = 2, +}; + +enum bfi_lport_i2h_msgs { + BFI_LPORT_I2H_CREATE_RSP = BFA_I2HM(1), + BFI_LPORT_I2H_DELETE_RSP = BFA_I2HM(2), + BFI_LPORT_I2H_ONLINE = BFA_I2HM(3), + BFI_LPORT_I2H_OFFLINE = BFA_I2HM(4), +}; + +#define BFI_LPORT_MAX_SYNNAME 64 + +enum bfi_lport_role_e { + BFI_LPORT_ROLE_FCPIM = 1, + BFI_LPORT_ROLE_FCPTM = 2, + BFI_LPORT_ROLE_IPFC = 4, +}; + +struct bfi_lport_create_req_s { + bfi_mhdr_t mh; /* common msg header */ + u16 fabric_fwhdl; /* parent fabric instance */ + u8 roles; /* lport FC-4 roles */ + u8 rsvd; + wwn_t pwwn; /* port name */ + wwn_t nwwn; /* node name */ + u8 symname[BFI_LPORT_MAX_SYNNAME]; +}; + +struct bfi_lport_create_rsp_s { + bfi_mhdr_t mh; /* common msg header */ + u8 status; /* lport creation status */ + u8 rsvd[3]; +}; + +struct bfi_lport_delete_req_s { + bfi_mhdr_t mh; /* common msg header */ + u16 fw_handle; /* firmware lport handle */ + u16 rsvd; +}; + +struct bfi_lport_delete_rsp_s { + bfi_mhdr_t mh; /* common msg header */ + u16 bfa_handle; /* host lport handle */ + u8 status; /* lport deletion status */ + u8 rsvd; +}; + +union bfi_lport_h2i_msg_u { + bfi_msg_t *msg; + struct bfi_lport_create_req_s *create_req; + struct bfi_lport_delete_req_s *delete_req; +}; + +union bfi_lport_i2h_msg_u { + bfi_msg_t *msg; + struct bfi_lport_create_rsp_s *create_rsp; + struct bfi_lport_delete_rsp_s *delete_rsp; +}; + +#pragma pack() + +#endif /* __BFI_LPORT_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_lps.h b/drivers/scsi/bfa/include/bfi/bfi_lps.h new file mode 100644 index 000000000000..414b0e30f6ef --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_lps.h @@ -0,0 +1,96 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_LPS_H__ +#define __BFI_LPS_H__ + +#include <bfi/bfi.h> + +#pragma pack(1) + +enum bfi_lps_h2i_msgs { + BFI_LPS_H2I_LOGIN_REQ = 1, + BFI_LPS_H2I_LOGOUT_REQ = 2, +}; + +enum bfi_lps_i2h_msgs { + BFI_LPS_H2I_LOGIN_RSP = BFA_I2HM(1), + BFI_LPS_H2I_LOGOUT_RSP = BFA_I2HM(2), +}; + +struct bfi_lps_login_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 lp_tag; + u8 alpa; + u16 pdu_size; + wwn_t pwwn; + wwn_t nwwn; + u8 fdisc; + u8 auth_en; + u8 rsvd[2]; +}; + +struct bfi_lps_login_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 lp_tag; + u8 status; + u8 lsrjt_rsn; + u8 lsrjt_expl; + wwn_t port_name; + wwn_t node_name; + u16 bb_credit; + u8 f_port; + u8 npiv_en; + u32 lp_pid : 24; + u32 auth_req : 8; + mac_t lp_mac; + mac_t fcf_mac; + u8 ext_status; + u8 brcd_switch;/* attached peer is brcd switch */ +}; + +struct bfi_lps_logout_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 lp_tag; + u8 rsvd[3]; + wwn_t port_name; +}; + +struct bfi_lps_logout_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 lp_tag; + u8 status; + u8 rsvd[2]; +}; + +union bfi_lps_h2i_msg_u { + struct bfi_mhdr_s *msg; + struct bfi_lps_login_req_s *login_req; + struct bfi_lps_logout_req_s *logout_req; +}; + +union bfi_lps_i2h_msg_u { + struct bfi_msg_s *msg; + struct bfi_lps_login_rsp_s *login_rsp; + struct bfi_lps_logout_rsp_s *logout_rsp; +}; + +#pragma pack() + +#endif /* __BFI_LPS_H__ */ + + diff --git a/drivers/scsi/bfa/include/bfi/bfi_port.h b/drivers/scsi/bfa/include/bfi/bfi_port.h new file mode 100644 index 000000000000..3ec3bea110ba --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_port.h @@ -0,0 +1,115 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFI_PORT_H__ +#define __BFI_PORT_H__ + +#include <bfi/bfi.h> +#include <defs/bfa_defs_pport.h> + +#pragma pack(1) + +enum bfi_port_h2i { + BFI_PORT_H2I_ENABLE_REQ = (1), + BFI_PORT_H2I_DISABLE_REQ = (2), + BFI_PORT_H2I_GET_STATS_REQ = (3), + BFI_PORT_H2I_CLEAR_STATS_REQ = (4), +}; + +enum bfi_port_i2h { + BFI_PORT_I2H_ENABLE_RSP = BFA_I2HM(1), + BFI_PORT_I2H_DISABLE_RSP = BFA_I2HM(2), + BFI_PORT_I2H_GET_STATS_RSP = BFA_I2HM(3), + BFI_PORT_I2H_CLEAR_STATS_RSP = BFA_I2HM(4), +}; + +/** + * Generic REQ type + */ +struct bfi_port_generic_req_s { + struct bfi_mhdr_s mh; /* msg header */ + u32 msgtag; /* msgtag for reply */ + u32 rsvd; +}; + +/** + * Generic RSP type + */ +struct bfi_port_generic_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 status; /* port enable status */ + u8 rsvd[3]; + u32 msgtag; /* msgtag for reply */ +}; + +/** + * @todo + * BFI_PORT_H2I_ENABLE_REQ + */ + +/** + * @todo + * BFI_PORT_I2H_ENABLE_RSP + */ + +/** + * BFI_PORT_H2I_DISABLE_REQ + */ + +/** + * BFI_PORT_I2H_DISABLE_RSP + */ + +/** + * BFI_PORT_H2I_GET_STATS_REQ + */ +struct bfi_port_get_stats_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + union bfi_addr_u dma_addr; +}; + +/** + * BFI_PORT_I2H_GET_STATS_RSP + */ + +/** + * BFI_PORT_H2I_CLEAR_STATS_REQ + */ + +/** + * BFI_PORT_I2H_CLEAR_STATS_RSP + */ + +union bfi_port_h2i_msg_u { + struct bfi_mhdr_s mh; + struct bfi_port_generic_req_s enable_req; + struct bfi_port_generic_req_s disable_req; + struct bfi_port_get_stats_req_s getstats_req; + struct bfi_port_generic_req_s clearstats_req; +}; + +union bfi_port_i2h_msg_u { + struct bfi_mhdr_s mh; + struct bfi_port_generic_rsp_s enable_rsp; + struct bfi_port_generic_rsp_s disable_rsp; + struct bfi_port_generic_rsp_s getstats_rsp; + struct bfi_port_generic_rsp_s clearstats_rsp; +}; + +#pragma pack() + +#endif /* __BFI_PORT_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_pport.h b/drivers/scsi/bfa/include/bfi/bfi_pport.h new file mode 100644 index 000000000000..c96d246851af --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_pport.h @@ -0,0 +1,184 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFI_PPORT_H__ +#define __BFI_PPORT_H__ + +#include <bfi/bfi.h> +#include <defs/bfa_defs_pport.h> + +#pragma pack(1) + +enum bfi_pport_h2i { + BFI_PPORT_H2I_ENABLE_REQ = (1), + BFI_PPORT_H2I_DISABLE_REQ = (2), + BFI_PPORT_H2I_GET_STATS_REQ = (3), + BFI_PPORT_H2I_CLEAR_STATS_REQ = (4), + BFI_PPORT_H2I_SET_SVC_PARAMS_REQ = (5), + BFI_PPORT_H2I_ENABLE_RX_VF_TAG_REQ = (6), + BFI_PPORT_H2I_ENABLE_TX_VF_TAG_REQ = (7), + BFI_PPORT_H2I_GET_QOS_STATS_REQ = (8), + BFI_PPORT_H2I_CLEAR_QOS_STATS_REQ = (9), +}; + +enum bfi_pport_i2h { + BFI_PPORT_I2H_ENABLE_RSP = BFA_I2HM(1), + BFI_PPORT_I2H_DISABLE_RSP = BFA_I2HM(2), + BFI_PPORT_I2H_GET_STATS_RSP = BFA_I2HM(3), + BFI_PPORT_I2H_CLEAR_STATS_RSP = BFA_I2HM(4), + BFI_PPORT_I2H_SET_SVC_PARAMS_RSP = BFA_I2HM(5), + BFI_PPORT_I2H_ENABLE_RX_VF_TAG_RSP = BFA_I2HM(6), + BFI_PPORT_I2H_ENABLE_TX_VF_TAG_RSP = BFA_I2HM(7), + BFI_PPORT_I2H_EVENT = BFA_I2HM(8), + BFI_PPORT_I2H_GET_QOS_STATS_RSP = BFA_I2HM(9), + BFI_PPORT_I2H_CLEAR_QOS_STATS_RSP = BFA_I2HM(10), +}; + +/** + * Generic REQ type + */ +struct bfi_pport_generic_req_s { + struct bfi_mhdr_s mh; /* msg header */ + u32 msgtag; /* msgtag for reply */ +}; + +/** + * Generic RSP type + */ +struct bfi_pport_generic_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 status; /* port enable status */ + u8 rsvd[3]; + u32 msgtag; /* msgtag for reply */ +}; + +/** + * BFI_PPORT_H2I_ENABLE_REQ + */ +struct bfi_pport_enable_req_s { + struct bfi_mhdr_s mh; /* msg header */ + u32 rsvd1; + wwn_t nwwn; /* node wwn of physical port */ + wwn_t pwwn; /* port wwn of physical port */ + struct bfa_pport_cfg_s port_cfg; /* port configuration */ + union bfi_addr_u stats_dma_addr; /* DMA address for stats */ + u32 msgtag; /* msgtag for reply */ + u32 rsvd2; +}; + +/** + * BFI_PPORT_I2H_ENABLE_RSP + */ +#define bfi_pport_enable_rsp_t struct bfi_pport_generic_rsp_s + +/** + * BFI_PPORT_H2I_DISABLE_REQ + */ +#define bfi_pport_disable_req_t struct bfi_pport_generic_req_s + +/** + * BFI_PPORT_I2H_DISABLE_RSP + */ +#define bfi_pport_disable_rsp_t struct bfi_pport_generic_rsp_s + +/** + * BFI_PPORT_H2I_GET_STATS_REQ + */ +#define bfi_pport_get_stats_req_t struct bfi_pport_generic_req_s + +/** + * BFI_PPORT_I2H_GET_STATS_RSP + */ +#define bfi_pport_get_stats_rsp_t struct bfi_pport_generic_rsp_s + +/** + * BFI_PPORT_H2I_CLEAR_STATS_REQ + */ +#define bfi_pport_clear_stats_req_t struct bfi_pport_generic_req_s + +/** + * BFI_PPORT_I2H_CLEAR_STATS_RSP + */ +#define bfi_pport_clear_stats_rsp_t struct bfi_pport_generic_rsp_s + +/** + * BFI_PPORT_H2I_GET_QOS_STATS_REQ + */ +#define bfi_pport_get_qos_stats_req_t struct bfi_pport_generic_req_s + +/** + * BFI_PPORT_H2I_GET_QOS_STATS_RSP + */ +#define bfi_pport_get_qos_stats_rsp_t struct bfi_pport_generic_rsp_s + +/** + * BFI_PPORT_H2I_CLEAR_QOS_STATS_REQ + */ +#define bfi_pport_clear_qos_stats_req_t struct bfi_pport_generic_req_s + +/** + * BFI_PPORT_H2I_CLEAR_QOS_STATS_RSP + */ +#define bfi_pport_clear_qos_stats_rsp_t struct bfi_pport_generic_rsp_s + +/** + * BFI_PPORT_H2I_SET_SVC_PARAMS_REQ + */ +struct bfi_pport_set_svc_params_req_s { + struct bfi_mhdr_s mh; /* msg header */ + u16 tx_bbcredit; /* Tx credits */ + u16 rsvd; +}; + +/** + * BFI_PPORT_I2H_SET_SVC_PARAMS_RSP + */ + +/** + * BFI_PPORT_I2H_EVENT + */ +struct bfi_pport_event_s { + struct bfi_mhdr_s mh; /* common msg header */ + struct bfa_pport_link_s link_state; +}; + +union bfi_pport_h2i_msg_u { + struct bfi_mhdr_s *mhdr; + struct bfi_pport_enable_req_s *penable; + struct bfi_pport_generic_req_s *pdisable; + struct bfi_pport_generic_req_s *pgetstats; + struct bfi_pport_generic_req_s *pclearstats; + struct bfi_pport_set_svc_params_req_s *psetsvcparams; + struct bfi_pport_get_qos_stats_req_s *pgetqosstats; + struct bfi_pport_generic_req_s *pclearqosstats; +}; + +union bfi_pport_i2h_msg_u { + struct bfi_msg_s *msg; + struct bfi_pport_generic_rsp_s *enable_rsp; + struct bfi_pport_disable_rsp_s *disable_rsp; + struct bfi_pport_generic_rsp_s *getstats_rsp; + struct bfi_pport_clear_stats_rsp_s *clearstats_rsp; + struct bfi_pport_set_svc_params_rsp_s *setsvcparasm_rsp; + struct bfi_pport_get_qos_stats_rsp_s *getqosstats_rsp; + struct bfi_pport_clear_qos_stats_rsp_s *clearqosstats_rsp; + struct bfi_pport_event_s *event; +}; + +#pragma pack() + +#endif /* __BFI_PPORT_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_rport.h b/drivers/scsi/bfa/include/bfi/bfi_rport.h new file mode 100644 index 000000000000..3520f55f09d7 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_rport.h @@ -0,0 +1,104 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_RPORT_H__ +#define __BFI_RPORT_H__ + +#include <bfi/bfi.h> + +#pragma pack(1) + +enum bfi_rport_h2i_msgs { + BFI_RPORT_H2I_CREATE_REQ = 1, + BFI_RPORT_H2I_DELETE_REQ = 2, + BFI_RPORT_H2I_SET_SPEED_REQ = 3, +}; + +enum bfi_rport_i2h_msgs { + BFI_RPORT_I2H_CREATE_RSP = BFA_I2HM(1), + BFI_RPORT_I2H_DELETE_RSP = BFA_I2HM(2), + BFI_RPORT_I2H_QOS_SCN = BFA_I2HM(3), +}; + +struct bfi_rport_create_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 bfa_handle; /* host rport handle */ + u16 max_frmsz; /* max rcv pdu size */ + u32 pid : 24, /* remote port ID */ + lp_tag : 8; /* local port tag */ + u32 local_pid : 24, /* local port ID */ + cisc : 8; + u8 fc_class; /* supported FC classes */ + u8 vf_en; /* virtual fabric enable */ + u16 vf_id; /* virtual fabric ID */ +}; + +struct bfi_rport_create_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u8 status; /* rport creation status */ + u8 rsvd[3]; + u16 bfa_handle; /* host rport handle */ + u16 fw_handle; /* firmware rport handle */ + struct bfa_rport_qos_attr_s qos_attr; /* QoS Attributes */ +}; + +struct bfa_rport_speed_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 fw_handle; /* firmware rport handle */ + u8 speed; /*! rport's speed via RPSC */ + u8 rsvd; +}; + +struct bfi_rport_delete_req_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 fw_handle; /* firmware rport handle */ + u16 rsvd; +}; + +struct bfi_rport_delete_rsp_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 bfa_handle; /* host rport handle */ + u8 status; /* rport deletion status */ + u8 rsvd; +}; + +struct bfi_rport_qos_scn_s { + struct bfi_mhdr_s mh; /* common msg header */ + u16 bfa_handle; /* host rport handle */ + u16 rsvd; + struct bfa_rport_qos_attr_s old_qos_attr; /* Old QoS Attributes */ + struct bfa_rport_qos_attr_s new_qos_attr; /* New QoS Attributes */ +}; + +union bfi_rport_h2i_msg_u { + struct bfi_msg_s *msg; + struct bfi_rport_create_req_s *create_req; + struct bfi_rport_delete_req_s *delete_req; + struct bfi_rport_speed_req_s *speed_req; +}; + +union bfi_rport_i2h_msg_u { + struct bfi_msg_s *msg; + struct bfi_rport_create_rsp_s *create_rsp; + struct bfi_rport_delete_rsp_s *delete_rsp; + struct bfi_rport_qos_scn_s *qos_scn_evt; +}; + +#pragma pack() + +#endif /* __BFI_RPORT_H__ */ + diff --git a/drivers/scsi/bfa/include/bfi/bfi_uf.h b/drivers/scsi/bfa/include/bfi/bfi_uf.h new file mode 100644 index 000000000000..f328a9e7e622 --- /dev/null +++ b/drivers/scsi/bfa/include/bfi/bfi_uf.h @@ -0,0 +1,52 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFI_UF_H__ +#define __BFI_UF_H__ + +#include "bfi.h" + +#pragma pack(1) + +enum bfi_uf_h2i { + BFI_UF_H2I_BUF_POST = 1, +}; + +enum bfi_uf_i2h { + BFI_UF_I2H_FRM_RCVD = BFA_I2HM(1), +}; + +#define BFA_UF_MAX_SGES 2 + +struct bfi_uf_buf_post_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 buf_tag; /* buffer tag */ + u16 buf_len; /* total buffer length */ + struct bfi_sge_s sge[BFA_UF_MAX_SGES]; /* buffer DMA SGEs */ +}; + +struct bfi_uf_frm_rcvd_s { + struct bfi_mhdr_s mh; /* Common msg header */ + u16 buf_tag; /* buffer tag */ + u16 rsvd; + u16 frm_len; /* received frame length */ + u16 xfr_len; /* tranferred length */ +}; + +#pragma pack() + +#endif /* __BFI_UF_H__ */ diff --git a/drivers/scsi/bfa/include/cna/bfa_cna_trcmod.h b/drivers/scsi/bfa/include/cna/bfa_cna_trcmod.h new file mode 100644 index 000000000000..43ba7064e81a --- /dev/null +++ b/drivers/scsi/bfa/include/cna/bfa_cna_trcmod.h @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_cna_trcmod.h CNA trace modules + */ + +#ifndef __BFA_CNA_TRCMOD_H__ +#define __BFA_CNA_TRCMOD_H__ + +#include <cs/bfa_trc.h> + +/* + * !!! Only append to the enums defined here to avoid any versioning + * !!! needed between trace utility and driver version + */ +enum { + BFA_TRC_CNA_CEE = 1, + BFA_TRC_CNA_PORT = 2, +}; + +#endif /* __BFA_CNA_TRCMOD_H__ */ diff --git a/drivers/scsi/bfa/include/cna/cee/bfa_cee.h b/drivers/scsi/bfa/include/cna/cee/bfa_cee.h new file mode 100644 index 000000000000..77f297f68046 --- /dev/null +++ b/drivers/scsi/bfa/include/cna/cee/bfa_cee.h @@ -0,0 +1,77 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_CEE_H__ +#define __BFA_CEE_H__ + +#include <defs/bfa_defs_cee.h> +#include <bfa_ioc.h> +#include <cs/bfa_trc.h> +#include <cs/bfa_log.h> + +typedef void (*bfa_cee_get_attr_cbfn_t) (void *dev, bfa_status_t status); +typedef void (*bfa_cee_get_stats_cbfn_t) (void *dev, bfa_status_t status); +typedef void (*bfa_cee_reset_stats_cbfn_t) (void *dev, bfa_status_t status); +typedef void (*bfa_cee_hbfail_cbfn_t) (void *dev, bfa_status_t status); + +struct bfa_cee_cbfn_s { + bfa_cee_get_attr_cbfn_t get_attr_cbfn; + void *get_attr_cbarg; + bfa_cee_get_stats_cbfn_t get_stats_cbfn; + void *get_stats_cbarg; + bfa_cee_reset_stats_cbfn_t reset_stats_cbfn; + void *reset_stats_cbarg; +}; + +struct bfa_cee_s { + void *dev; + bfa_boolean_t get_attr_pending; + bfa_boolean_t get_stats_pending; + bfa_boolean_t reset_stats_pending; + bfa_status_t get_attr_status; + bfa_status_t get_stats_status; + bfa_status_t reset_stats_status; + struct bfa_cee_cbfn_s cbfn; + struct bfa_ioc_hbfail_notify_s hbfail; + struct bfa_trc_mod_s *trcmod; + struct bfa_log_mod_s *logmod; + struct bfa_cee_attr_s *attr; + struct bfa_cee_stats_s *stats; + struct bfa_dma_s attr_dma; + struct bfa_dma_s stats_dma; + struct bfa_ioc_s *ioc; + struct bfa_mbox_cmd_s get_cfg_mb; + struct bfa_mbox_cmd_s get_stats_mb; + struct bfa_mbox_cmd_s reset_stats_mb; +}; + +u32 bfa_cee_meminfo(void); +void bfa_cee_mem_claim(struct bfa_cee_s *cee, u8 *dma_kva, + u64 dma_pa); +void bfa_cee_attach(struct bfa_cee_s *cee, struct bfa_ioc_s *ioc, void *dev, + struct bfa_trc_mod_s *trcmod, + struct bfa_log_mod_s *logmod); +void bfa_cee_detach(struct bfa_cee_s *cee); +bfa_status_t bfa_cee_get_attr(struct bfa_cee_s *cee, + struct bfa_cee_attr_s *attr, + bfa_cee_get_attr_cbfn_t cbfn, void *cbarg); +bfa_status_t bfa_cee_get_stats(struct bfa_cee_s *cee, + struct bfa_cee_stats_s *stats, + bfa_cee_get_stats_cbfn_t cbfn, void *cbarg); +bfa_status_t bfa_cee_reset_stats(struct bfa_cee_s *cee, + bfa_cee_reset_stats_cbfn_t cbfn, void *cbarg); +#endif /* __BFA_CEE_H__ */ diff --git a/drivers/scsi/bfa/include/cna/port/bfa_port.h b/drivers/scsi/bfa/include/cna/port/bfa_port.h new file mode 100644 index 000000000000..7cbf17d3141b --- /dev/null +++ b/drivers/scsi/bfa/include/cna/port/bfa_port.h @@ -0,0 +1,69 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_PORT_H__ +#define __BFA_PORT_H__ + +#include <defs/bfa_defs_port.h> +#include <bfa_ioc.h> +#include <cs/bfa_trc.h> +#include <cs/bfa_log.h> + +typedef void (*bfa_port_stats_cbfn_t) (void *dev, bfa_status_t status); +typedef void (*bfa_port_endis_cbfn_t) (void *dev, bfa_status_t status); + +struct bfa_port_s { + void *dev; + struct bfa_ioc_s *ioc; + struct bfa_trc_mod_s *trcmod; + struct bfa_log_mod_s *logmod; + u32 msgtag; + bfa_boolean_t stats_busy; + struct bfa_mbox_cmd_s stats_mb; + bfa_port_stats_cbfn_t stats_cbfn; + void *stats_cbarg; + bfa_status_t stats_status; + union bfa_pport_stats_u *stats; + struct bfa_dma_s stats_dma; + bfa_boolean_t endis_pending; + struct bfa_mbox_cmd_s endis_mb; + bfa_port_endis_cbfn_t endis_cbfn; + void *endis_cbarg; + bfa_status_t endis_status; + struct bfa_ioc_hbfail_notify_s hbfail; +}; + +void bfa_port_attach(struct bfa_port_s *port, struct bfa_ioc_s *ioc, + void *dev, struct bfa_trc_mod_s *trcmod, + struct bfa_log_mod_s *logmod); +void bfa_port_detach(struct bfa_port_s *port); +void bfa_port_hbfail(void *arg); + +bfa_status_t bfa_port_get_stats(struct bfa_port_s *port, + union bfa_pport_stats_u *stats, + bfa_port_stats_cbfn_t cbfn, void *cbarg); +bfa_status_t bfa_port_clear_stats(struct bfa_port_s *port, + bfa_port_stats_cbfn_t cbfn, void *cbarg); +bfa_status_t bfa_port_enable(struct bfa_port_s *port, + bfa_port_endis_cbfn_t cbfn, void *cbarg); +bfa_status_t bfa_port_disable(struct bfa_port_s *port, + bfa_port_endis_cbfn_t cbfn, void *cbarg); +u32 bfa_port_meminfo(void); +void bfa_port_mem_claim(struct bfa_port_s *port, u8 *dma_kva, + u64 dma_pa); + +#endif /* __BFA_PORT_H__ */ diff --git a/drivers/scsi/bfa/include/cna/pstats/ethport_defs.h b/drivers/scsi/bfa/include/cna/pstats/ethport_defs.h new file mode 100644 index 000000000000..1563ee512218 --- /dev/null +++ b/drivers/scsi/bfa/include/cna/pstats/ethport_defs.h @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved. + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __ETHPORT_DEFS_H__ +#define __ETHPORT_DEFS_H__ + +struct bnad_drv_stats { + u64 netif_queue_stop; + u64 netif_queue_wakeup; + u64 tso4; + u64 tso6; + u64 tso_err; + u64 tcpcsum_offload; + u64 udpcsum_offload; + u64 csum_help; + u64 csum_help_err; + + u64 hw_stats_updates; + u64 netif_rx_schedule; + u64 netif_rx_complete; + u64 netif_rx_dropped; +}; +#endif diff --git a/drivers/scsi/bfa/include/cna/pstats/phyport_defs.h b/drivers/scsi/bfa/include/cna/pstats/phyport_defs.h new file mode 100644 index 000000000000..eb7548030d0f --- /dev/null +++ b/drivers/scsi/bfa/include/cna/pstats/phyport_defs.h @@ -0,0 +1,218 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved. + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __PHYPORT_DEFS_H__ +#define __PHYPORT_DEFS_H__ + +#define BNA_TXF_ID_MAX 64 +#define BNA_RXF_ID_MAX 64 + +/* + * Statistics + */ + +/* + * TxF Frame Statistics + */ +struct bna_stats_txf { + u64 ucast_octets; + u64 ucast; + u64 ucast_vlan; + + u64 mcast_octets; + u64 mcast; + u64 mcast_vlan; + + u64 bcast_octets; + u64 bcast; + u64 bcast_vlan; + + u64 errors; + u64 filter_vlan; /* frames filtered due to VLAN */ + u64 filter_mac_sa; /* frames filtered due to SA check */ +}; + +/* + * RxF Frame Statistics + */ +struct bna_stats_rxf { + u64 ucast_octets; + u64 ucast; + u64 ucast_vlan; + + u64 mcast_octets; + u64 mcast; + u64 mcast_vlan; + + u64 bcast_octets; + u64 bcast; + u64 bcast_vlan; + u64 frame_drops; +}; + +/* + * FC Tx Frame Statistics + */ +struct bna_stats_fc_tx { + u64 txf_ucast_octets; + u64 txf_ucast; + u64 txf_ucast_vlan; + + u64 txf_mcast_octets; + u64 txf_mcast; + u64 txf_mcast_vlan; + + u64 txf_bcast_octets; + u64 txf_bcast; + u64 txf_bcast_vlan; + + u64 txf_parity_errors; + u64 txf_timeout; + u64 txf_fid_parity_errors; +}; + +/* + * FC Rx Frame Statistics + */ +struct bna_stats_fc_rx { + u64 rxf_ucast_octets; + u64 rxf_ucast; + u64 rxf_ucast_vlan; + + u64 rxf_mcast_octets; + u64 rxf_mcast; + u64 rxf_mcast_vlan; + + u64 rxf_bcast_octets; + u64 rxf_bcast; + u64 rxf_bcast_vlan; +}; + +/* + * RAD Frame Statistics + */ +struct cna_stats_rad { + u64 rx_frames; + u64 rx_octets; + u64 rx_vlan_frames; + + u64 rx_ucast; + u64 rx_ucast_octets; + u64 rx_ucast_vlan; + + u64 rx_mcast; + u64 rx_mcast_octets; + u64 rx_mcast_vlan; + + u64 rx_bcast; + u64 rx_bcast_octets; + u64 rx_bcast_vlan; + + u64 rx_drops; +}; + +/* + * BPC Tx Registers + */ +struct cna_stats_bpc_tx { + u64 tx_pause[8]; + u64 tx_zero_pause[8]; /* Pause cancellation */ + u64 tx_first_pause[8]; /* Pause initiation rather + *than retention */ +}; + +/* + * BPC Rx Registers + */ +struct cna_stats_bpc_rx { + u64 rx_pause[8]; + u64 rx_zero_pause[8]; /* Pause cancellation */ + u64 rx_first_pause[8]; /* Pause initiation rather + *than retention */ +}; + +/* + * MAC Rx Statistics + */ +struct cna_stats_mac_rx { + u64 frame_64; /* both rx and tx counter */ + u64 frame_65_127; /* both rx and tx counter */ + u64 frame_128_255; /* both rx and tx counter */ + u64 frame_256_511; /* both rx and tx counter */ + u64 frame_512_1023; /* both rx and tx counter */ + u64 frame_1024_1518; /* both rx and tx counter */ + u64 frame_1518_1522; /* both rx and tx counter */ + u64 rx_bytes; + u64 rx_packets; + u64 rx_fcs_error; + u64 rx_multicast; + u64 rx_broadcast; + u64 rx_control_frames; + u64 rx_pause; + u64 rx_unknown_opcode; + u64 rx_alignment_error; + u64 rx_frame_length_error; + u64 rx_code_error; + u64 rx_carrier_sense_error; + u64 rx_undersize; + u64 rx_oversize; + u64 rx_fragments; + u64 rx_jabber; + u64 rx_drop; +}; + +/* + * MAC Tx Statistics + */ +struct cna_stats_mac_tx { + u64 tx_bytes; + u64 tx_packets; + u64 tx_multicast; + u64 tx_broadcast; + u64 tx_pause; + u64 tx_deferral; + u64 tx_excessive_deferral; + u64 tx_single_collision; + u64 tx_muliple_collision; + u64 tx_late_collision; + u64 tx_excessive_collision; + u64 tx_total_collision; + u64 tx_pause_honored; + u64 tx_drop; + u64 tx_jabber; + u64 tx_fcs_error; + u64 tx_control_frame; + u64 tx_oversize; + u64 tx_undersize; + u64 tx_fragments; +}; + +/* + * Complete statistics + */ +struct bna_stats { + struct cna_stats_mac_rx mac_rx_stats; + struct cna_stats_bpc_rx bpc_rx_stats; + struct cna_stats_rad rad_stats; + struct bna_stats_fc_rx fc_rx_stats; + struct cna_stats_mac_tx mac_tx_stats; + struct cna_stats_bpc_tx bpc_tx_stats; + struct bna_stats_fc_tx fc_tx_stats; + struct bna_stats_rxf rxf_stats[BNA_TXF_ID_MAX]; + struct bna_stats_txf txf_stats[BNA_RXF_ID_MAX]; +}; + +#endif diff --git a/drivers/scsi/bfa/include/cs/bfa_checksum.h b/drivers/scsi/bfa/include/cs/bfa_checksum.h new file mode 100644 index 000000000000..af8c1d533ba8 --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_checksum.h @@ -0,0 +1,60 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_checksum.h BFA checksum utilities + */ + +#ifndef __BFA_CHECKSUM_H__ +#define __BFA_CHECKSUM_H__ + +static inline u32 +bfa_checksum_u32(u32 *buf, int sz) +{ + int i, m = sz >> 2; + u32 sum = 0; + + for (i = 0; i < m; i++) + sum ^= buf[i]; + + return (sum); +} + +static inline u16 +bfa_checksum_u16(u16 *buf, int sz) +{ + int i, m = sz >> 1; + u16 sum = 0; + + for (i = 0; i < m; i++) + sum ^= buf[i]; + + return (sum); +} + +static inline u8 +bfa_checksum_u8(u8 *buf, int sz) +{ + int i; + u8 sum = 0; + + for (i = 0; i < sz; i++) + sum ^= buf[i]; + + return (sum); +} +#endif diff --git a/drivers/scsi/bfa/include/cs/bfa_debug.h b/drivers/scsi/bfa/include/cs/bfa_debug.h new file mode 100644 index 000000000000..441be86b1b0f --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_debug.h @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_debug.h BFA debug interfaces + */ + +#ifndef __BFA_DEBUG_H__ +#define __BFA_DEBUG_H__ + +#define bfa_assert(__cond) do { \ + if (!(__cond)) \ + bfa_panic(__LINE__, __FILE__, #__cond); \ +} while (0) + +#define bfa_sm_fault(__mod, __event) do { \ + bfa_sm_panic((__mod)->logm, __LINE__, __FILE__, __event); \ +} while (0) + +#ifndef BFA_PERF_BUILD +#define bfa_assert_fp(__cond) bfa_assert(__cond) +#else +#define bfa_assert_fp(__cond) +#endif + +struct bfa_log_mod_s; +void bfa_panic(int line, char *file, char *panicstr); +void bfa_sm_panic(struct bfa_log_mod_s *logm, int line, char *file, int event); + +#endif /* __BFA_DEBUG_H__ */ diff --git a/drivers/scsi/bfa/include/cs/bfa_log.h b/drivers/scsi/bfa/include/cs/bfa_log.h new file mode 100644 index 000000000000..761cbe22130a --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_log.h @@ -0,0 +1,184 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_log.h BFA log library data structure and function definition + */ + +#ifndef __BFA_LOG_H__ +#define __BFA_LOG_H__ + +#include <bfa_os_inc.h> +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_aen.h> + +/* + * BFA log module definition + * + * To create a new module id: + * Add a #define at the end of the list below. Select a value for your + * definition so that it is one (1) greater than the previous + * definition. Modify the definition of BFA_LOG_MODULE_ID_MAX to become + * your new definition. + * Should have no gaps in between the values because this is used in arrays. + * IMPORTANT: AEN_IDs must be at the begining, otherwise update bfa_defs_aen.h + */ + +enum bfa_log_module_id { + BFA_LOG_UNUSED_ID = 0, + + /* AEN defs begin */ + BFA_LOG_AEN_MIN = BFA_LOG_UNUSED_ID, + + BFA_LOG_AEN_ID_ADAPTER = BFA_LOG_AEN_MIN + BFA_AEN_CAT_ADAPTER,/* 1 */ + BFA_LOG_AEN_ID_PORT = BFA_LOG_AEN_MIN + BFA_AEN_CAT_PORT, /* 2 */ + BFA_LOG_AEN_ID_LPORT = BFA_LOG_AEN_MIN + BFA_AEN_CAT_LPORT, /* 3 */ + BFA_LOG_AEN_ID_RPORT = BFA_LOG_AEN_MIN + BFA_AEN_CAT_RPORT, /* 4 */ + BFA_LOG_AEN_ID_ITNIM = BFA_LOG_AEN_MIN + BFA_AEN_CAT_ITNIM, /* 5 */ + BFA_LOG_AEN_ID_TIN = BFA_LOG_AEN_MIN + BFA_AEN_CAT_TIN, /* 6 */ + BFA_LOG_AEN_ID_IPFC = BFA_LOG_AEN_MIN + BFA_AEN_CAT_IPFC, /* 7 */ + BFA_LOG_AEN_ID_AUDIT = BFA_LOG_AEN_MIN + BFA_AEN_CAT_AUDIT, /* 8 */ + BFA_LOG_AEN_ID_IOC = BFA_LOG_AEN_MIN + BFA_AEN_CAT_IOC, /* 9 */ + BFA_LOG_AEN_ID_ETHPORT = BFA_LOG_AEN_MIN + BFA_AEN_CAT_ETHPORT,/* 10 */ + + BFA_LOG_AEN_MAX = BFA_LOG_AEN_ID_ETHPORT, + /* AEN defs end */ + + BFA_LOG_MODULE_ID_MIN = BFA_LOG_AEN_MAX, + + BFA_LOG_FW_ID = BFA_LOG_MODULE_ID_MIN + 1, + BFA_LOG_HAL_ID = BFA_LOG_MODULE_ID_MIN + 2, + BFA_LOG_FCS_ID = BFA_LOG_MODULE_ID_MIN + 3, + BFA_LOG_WDRV_ID = BFA_LOG_MODULE_ID_MIN + 4, + BFA_LOG_LINUX_ID = BFA_LOG_MODULE_ID_MIN + 5, + BFA_LOG_SOLARIS_ID = BFA_LOG_MODULE_ID_MIN + 6, + + BFA_LOG_MODULE_ID_MAX = BFA_LOG_SOLARIS_ID, + + /* Not part of any arrays */ + BFA_LOG_MODULE_ID_ALL = BFA_LOG_MODULE_ID_MAX + 1, + BFA_LOG_AEN_ALL = BFA_LOG_MODULE_ID_MAX + 2, + BFA_LOG_DRV_ALL = BFA_LOG_MODULE_ID_MAX + 3, +}; + +/* + * BFA log catalog name + */ +#define BFA_LOG_CAT_NAME "BFA" + +/* + * bfa log severity values + */ +enum bfa_log_severity { + BFA_LOG_INVALID = 0, + BFA_LOG_CRITICAL = 1, + BFA_LOG_ERROR = 2, + BFA_LOG_WARNING = 3, + BFA_LOG_INFO = 4, + BFA_LOG_NONE = 5, + BFA_LOG_LEVEL_MAX = BFA_LOG_NONE +}; + +#define BFA_LOG_MODID_OFFSET 16 + + +struct bfa_log_msgdef_s { + u32 msg_id; /* message id */ + int attributes; /* attributes */ + int severity; /* severity level */ + char *msg_value; + /* msg string */ + char *message; + /* msg format string */ + int arg_type; /* argument type */ + int arg_num; /* number of argument */ +}; + +/* + * supported argument type + */ +enum bfa_log_arg_type { + BFA_LOG_S = 0, /* string */ + BFA_LOG_D, /* decimal */ + BFA_LOG_I, /* integer */ + BFA_LOG_O, /* oct number */ + BFA_LOG_U, /* unsigned integer */ + BFA_LOG_X, /* hex number */ + BFA_LOG_F, /* floating */ + BFA_LOG_C, /* character */ + BFA_LOG_L, /* double */ + BFA_LOG_P /* pointer */ +}; + +#define BFA_LOG_ARG_TYPE 2 +#define BFA_LOG_ARG0 (0 * BFA_LOG_ARG_TYPE) +#define BFA_LOG_ARG1 (1 * BFA_LOG_ARG_TYPE) +#define BFA_LOG_ARG2 (2 * BFA_LOG_ARG_TYPE) +#define BFA_LOG_ARG3 (3 * BFA_LOG_ARG_TYPE) + +#define BFA_LOG_GET_MOD_ID(msgid) ((msgid >> BFA_LOG_MODID_OFFSET) & 0xff) +#define BFA_LOG_GET_MSG_IDX(msgid) (msgid & 0xffff) +#define BFA_LOG_GET_MSG_ID(msgdef) ((msgdef)->msg_id) +#define BFA_LOG_GET_MSG_FMT_STRING(msgdef) ((msgdef)->message) +#define BFA_LOG_GET_SEVERITY(msgdef) ((msgdef)->severity) + +/* + * Event attributes + */ +#define BFA_LOG_ATTR_NONE 0 +#define BFA_LOG_ATTR_AUDIT 1 +#define BFA_LOG_ATTR_LOG 2 +#define BFA_LOG_ATTR_FFDC 4 + +#define BFA_LOG_CREATE_ID(msw, lsw) \ + (((u32)msw << BFA_LOG_MODID_OFFSET) | lsw) + +struct bfa_log_mod_s; + +/** + * callback function + */ +typedef void (*bfa_log_cb_t)(struct bfa_log_mod_s *log_mod, u32 msg_id, + const char *format, ...); + + +struct bfa_log_mod_s { + char instance_info[16]; /* instance info */ + int log_level[BFA_LOG_MODULE_ID_MAX + 1]; + /* log level for modules */ + bfa_log_cb_t cbfn; /* callback function */ +}; + +extern int bfa_log_init(struct bfa_log_mod_s *log_mod, + char *instance_name, bfa_log_cb_t cbfn); +extern int bfa_log(struct bfa_log_mod_s *log_mod, u32 msg_id, ...); +extern bfa_status_t bfa_log_set_level(struct bfa_log_mod_s *log_mod, + int mod_id, enum bfa_log_severity log_level); +extern bfa_status_t bfa_log_set_level_all(struct bfa_log_mod_s *log_mod, + enum bfa_log_severity log_level); +extern bfa_status_t bfa_log_set_level_aen(struct bfa_log_mod_s *log_mod, + enum bfa_log_severity log_level); +extern enum bfa_log_severity bfa_log_get_level(struct bfa_log_mod_s *log_mod, + int mod_id); +extern enum bfa_log_severity bfa_log_get_msg_level( + struct bfa_log_mod_s *log_mod, u32 msg_id); +/* + * array of messages generated from xml files + */ +extern struct bfa_log_msgdef_s bfa_log_msg_array[]; + +#endif diff --git a/drivers/scsi/bfa/include/cs/bfa_perf.h b/drivers/scsi/bfa/include/cs/bfa_perf.h new file mode 100644 index 000000000000..45aa5f978ff5 --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_perf.h @@ -0,0 +1,34 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFAD_PERF_H__ +#define __BFAD_PERF_H__ + +#ifdef BFAD_PERF_BUILD + +#undef bfa_trc +#undef bfa_trc32 +#undef bfa_assert +#undef BFA_TRC_FILE + +#define bfa_trc(_trcp, _data) +#define bfa_trc32(_trcp, _data) +#define bfa_assert(__cond) +#define BFA_TRC_FILE(__mod, __submod) + +#endif + +#endif /* __BFAD_PERF_H__ */ diff --git a/drivers/scsi/bfa/include/cs/bfa_plog.h b/drivers/scsi/bfa/include/cs/bfa_plog.h new file mode 100644 index 000000000000..670f86e5fc6e --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_plog.h @@ -0,0 +1,162 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_PORTLOG_H__ +#define __BFA_PORTLOG_H__ + +#include "protocol/fc.h" +#include <defs/bfa_defs_types.h> + +#define BFA_PL_NLOG_ENTS 256 +#define BFA_PL_LOG_REC_INCR(_x) ((_x)++, (_x) %= BFA_PL_NLOG_ENTS) + +#define BFA_PL_STRING_LOG_SZ 32 /* number of chars in string log */ +#define BFA_PL_INT_LOG_SZ 8 /* number of integers in the integer log */ + +enum bfa_plog_log_type { + BFA_PL_LOG_TYPE_INVALID = 0, + BFA_PL_LOG_TYPE_INT = 1, + BFA_PL_LOG_TYPE_STRING = 2, +}; + +/* + * the (fixed size) record format for each entry in the portlog + */ +struct bfa_plog_rec_s { + u32 tv; /* Filled by the portlog driver when the * + * entry is added to the circular log. */ + u8 port; /* Source port that logged this entry. CM + * entities will use 0xFF */ + u8 mid; /* Integer value to be used by all entities * + * while logging. The module id to string * + * conversion will be done by BFAL. See + * enum bfa_plog_mid */ + u8 eid; /* indicates Rx, Tx, IOCTL, etc. See + * enum bfa_plog_eid */ + u8 log_type; /* indicates string log or integer log. + * see bfa_plog_log_type_t */ + u8 log_num_ints; + /* + * interpreted only if log_type is INT_LOG. indicates number of + * integers in the int_log[] (0-PL_INT_LOG_SZ). + */ + u8 rsvd; + u16 misc; /* can be used to indicate fc frame length, + *etc.. */ + union { + char string_log[BFA_PL_STRING_LOG_SZ]; + u32 int_log[BFA_PL_INT_LOG_SZ]; + } log_entry; + +}; + +/* + * the following #defines will be used by the logging entities to indicate + * their module id. BFAL will convert the integer value to string format + * +* process to be used while changing the following #defines: + * - Always add new entries at the end + * - define corresponding string in BFAL + * - Do not remove any entry or rearrange the order. + */ +enum bfa_plog_mid { + BFA_PL_MID_INVALID = 0, + BFA_PL_MID_DEBUG = 1, + BFA_PL_MID_DRVR = 2, + BFA_PL_MID_HAL = 3, + BFA_PL_MID_HAL_FCXP = 4, + BFA_PL_MID_HAL_UF = 5, + BFA_PL_MID_FCS = 6, + BFA_PL_MID_MAX = 7 +}; + +#define BFA_PL_MID_STRLEN 8 +struct bfa_plog_mid_strings_s { + char m_str[BFA_PL_MID_STRLEN]; +}; + +/* + * the following #defines will be used by the logging entities to indicate + * their event type. BFAL will convert the integer value to string format + * +* process to be used while changing the following #defines: + * - Always add new entries at the end + * - define corresponding string in BFAL + * - Do not remove any entry or rearrange the order. + */ +enum bfa_plog_eid { + BFA_PL_EID_INVALID = 0, + BFA_PL_EID_IOC_DISABLE = 1, + BFA_PL_EID_IOC_ENABLE = 2, + BFA_PL_EID_PORT_DISABLE = 3, + BFA_PL_EID_PORT_ENABLE = 4, + BFA_PL_EID_PORT_ST_CHANGE = 5, + BFA_PL_EID_TX = 6, + BFA_PL_EID_TX_ACK1 = 7, + BFA_PL_EID_TX_RJT = 8, + BFA_PL_EID_TX_BSY = 9, + BFA_PL_EID_RX = 10, + BFA_PL_EID_RX_ACK1 = 11, + BFA_PL_EID_RX_RJT = 12, + BFA_PL_EID_RX_BSY = 13, + BFA_PL_EID_CT_IN = 14, + BFA_PL_EID_CT_OUT = 15, + BFA_PL_EID_DRIVER_START = 16, + BFA_PL_EID_RSCN = 17, + BFA_PL_EID_DEBUG = 18, + BFA_PL_EID_MISC = 19, + BFA_PL_EID_MAX = 20 +}; + +#define BFA_PL_ENAME_STRLEN 8 +struct bfa_plog_eid_strings_s { + char e_str[BFA_PL_ENAME_STRLEN]; +}; + +#define BFA_PL_SIG_LEN 8 +#define BFA_PL_SIG_STR "12pl123" + +/* + * per port circular log buffer + */ +struct bfa_plog_s { + char plog_sig[BFA_PL_SIG_LEN]; /* Start signature */ + u8 plog_enabled; + u8 rsvd[7]; + u32 ticks; + u16 head; + u16 tail; + struct bfa_plog_rec_s plog_recs[BFA_PL_NLOG_ENTS]; +}; + +void bfa_plog_init(struct bfa_plog_s *plog); +void bfa_plog_str(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, u16 misc, char *log_str); +void bfa_plog_intarr(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, u16 misc, + u32 *intarr, u32 num_ints); +void bfa_plog_fchdr(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, u16 misc, + struct fchs_s *fchdr); +void bfa_plog_fchdr_and_pl(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, u16 misc, + struct fchs_s *fchdr, u32 pld_w0); +void bfa_plog_clear(struct bfa_plog_s *plog); +void bfa_plog_enable(struct bfa_plog_s *plog); +void bfa_plog_disable(struct bfa_plog_s *plog); +bfa_boolean_t bfa_plog_get_setting(struct bfa_plog_s *plog); + +#endif /* __BFA_PORTLOG_H__ */ diff --git a/drivers/scsi/bfa/include/cs/bfa_q.h b/drivers/scsi/bfa/include/cs/bfa_q.h new file mode 100644 index 000000000000..ea895facedbc --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_q.h @@ -0,0 +1,81 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_q.h Circular queue definitions. + */ + +#ifndef __BFA_Q_H__ +#define __BFA_Q_H__ + +#define bfa_q_first(_q) ((void *)(((struct list_head *) (_q))->next)) +#define bfa_q_next(_qe) (((struct list_head *) (_qe))->next) +#define bfa_q_prev(_qe) (((struct list_head *) (_qe))->prev) + +/* + * bfa_q_qe_init - to initialize a queue element + */ +#define bfa_q_qe_init(_qe) { \ + bfa_q_next(_qe) = (struct list_head *) NULL; \ + bfa_q_prev(_qe) = (struct list_head *) NULL; \ +} + +/* + * bfa_q_deq - dequeue an element from head of the queue + */ +#define bfa_q_deq(_q, _qe) { \ + if (!list_empty(_q)) { \ + (*((struct list_head **) (_qe))) = bfa_q_next(_q); \ + bfa_q_prev(bfa_q_next(*((struct list_head **) _qe))) = \ + (struct list_head *) (_q); \ + bfa_q_next(_q) = bfa_q_next(*((struct list_head **) _qe)); \ + BFA_Q_DBG_INIT(*((struct list_head **) _qe)); \ + } else { \ + *((struct list_head **) (_qe)) = (struct list_head *) NULL; \ + } \ +} + +/* + * bfa_q_deq_tail - dequeue an element from tail of the queue + */ +#define bfa_q_deq_tail(_q, _qe) { \ + if (!list_empty(_q)) { \ + *((struct list_head **) (_qe)) = bfa_q_prev(_q); \ + bfa_q_next(bfa_q_prev(*((struct list_head **) _qe))) = \ + (struct list_head *) (_q); \ + bfa_q_prev(_q) = bfa_q_prev(*(struct list_head **) _qe); \ + BFA_Q_DBG_INIT(*((struct list_head **) _qe)); \ + } else { \ + *((struct list_head **) (_qe)) = (struct list_head *) NULL; \ + } \ +} + +/* + * #ifdef BFA_DEBUG (Using bfa_assert to check for debug_build is not + * consistent across modules) + */ +#ifndef BFA_PERF_BUILD +#define BFA_Q_DBG_INIT(_qe) bfa_q_qe_init(_qe) +#else +#define BFA_Q_DBG_INIT(_qe) +#endif + +#define bfa_q_is_on_q(_q, _qe) \ + bfa_q_is_on_q_func(_q, (struct list_head *)(_qe)) +extern int bfa_q_is_on_q_func(struct list_head *q, struct list_head *qe); + +#endif diff --git a/drivers/scsi/bfa/include/cs/bfa_sm.h b/drivers/scsi/bfa/include/cs/bfa_sm.h new file mode 100644 index 000000000000..9877066680a6 --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_sm.h @@ -0,0 +1,69 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfasm.h State machine defines + */ + +#ifndef __BFA_SM_H__ +#define __BFA_SM_H__ + +typedef void (*bfa_sm_t)(void *sm, int event); + +#define bfa_sm_set_state(_sm, _state) (_sm)->sm = (bfa_sm_t)(_state) +#define bfa_sm_send_event(_sm, _event) (_sm)->sm((_sm), (_event)) +#define bfa_sm_get_state(_sm) ((_sm)->sm) +#define bfa_sm_cmp_state(_sm, _state) ((_sm)->sm == (bfa_sm_t)(_state)) + +/** + * For converting from state machine function to state encoding. + */ +struct bfa_sm_table_s { + bfa_sm_t sm; /* state machine function */ + int state; /* state machine encoding */ + char *name; /* state name for display */ +}; +#define BFA_SM(_sm) ((bfa_sm_t)(_sm)) + +int bfa_sm_to_state(struct bfa_sm_table_s *smt, bfa_sm_t sm); + +/** + * State machine with entry actions. + */ +typedef void (*bfa_fsm_t)(void *fsm, int event); + +/** + * oc - object class eg. bfa_ioc + * st - state, eg. reset + * otype - object type, eg. struct bfa_ioc_s + * etype - object type, eg. enum ioc_event + */ +#define bfa_fsm_state_decl(oc, st, otype, etype) \ + static void oc ## _sm_ ## st(otype * fsm, etype event); \ + static void oc ## _sm_ ## st ## _entry(otype * fsm) + +#define bfa_fsm_set_state(_fsm, _state) do { \ + (_fsm)->fsm = (bfa_fsm_t)(_state); \ + _state ## _entry(_fsm); \ +} while (0) + +#define bfa_fsm_send_event(_fsm, _event) \ + (_fsm)->fsm((_fsm), (_event)) +#define bfa_fsm_cmp_state(_fsm, _state) \ + ((_fsm)->fsm == (bfa_fsm_t)(_state)) + +#endif diff --git a/drivers/scsi/bfa/include/cs/bfa_trc.h b/drivers/scsi/bfa/include/cs/bfa_trc.h new file mode 100644 index 000000000000..3e743928c74c --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_trc.h @@ -0,0 +1,176 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_TRC_H__ +#define __BFA_TRC_H__ + +#include <bfa_os_inc.h> + +#ifndef BFA_TRC_MAX +#define BFA_TRC_MAX (4 * 1024) +#endif + +#ifndef BFA_TRC_TS +#define BFA_TRC_TS(_trcm) ((_trcm)->ticks ++) +#endif + +struct bfa_trc_s { +#ifdef __BIGENDIAN + u16 fileno; + u16 line; +#else + u16 line; + u16 fileno; +#endif + u32 timestamp; + union { + struct { + u32 rsvd; + u32 u32; + } u32; + u64 u64; + } data; +}; + + +struct bfa_trc_mod_s { + u32 head; + u32 tail; + u32 ntrc; + u32 stopped; + u32 ticks; + u32 rsvd[3]; + struct bfa_trc_s trc[BFA_TRC_MAX]; +}; + + +enum { + BFA_TRC_FW = 1, /* firmware modules */ + BFA_TRC_HAL = 2, /* BFA modules */ + BFA_TRC_FCS = 3, /* BFA FCS modules */ + BFA_TRC_LDRV = 4, /* Linux driver modules */ + BFA_TRC_SDRV = 5, /* Solaris driver modules */ + BFA_TRC_VDRV = 6, /* vmware driver modules */ + BFA_TRC_WDRV = 7, /* windows driver modules */ + BFA_TRC_AEN = 8, /* AEN module */ + BFA_TRC_BIOS = 9, /* bios driver modules */ + BFA_TRC_EFI = 10, /* EFI driver modules */ + BNA_TRC_WDRV = 11, /* BNA windows driver modules */ + BNA_TRC_VDRV = 12, /* BNA vmware driver modules */ + BNA_TRC_SDRV = 13, /* BNA Solaris driver modules */ + BNA_TRC_LDRV = 14, /* BNA Linux driver modules */ + BNA_TRC_HAL = 15, /* BNA modules */ + BFA_TRC_CNA = 16, /* Common modules */ + BNA_TRC_IMDRV = 17 /* BNA windows intermediate driver modules */ +}; +#define BFA_TRC_MOD_SH 10 +#define BFA_TRC_MOD(__mod) ((BFA_TRC_ ## __mod) << BFA_TRC_MOD_SH) + +/** + * Define a new tracing file (module). Module should match one defined above. + */ +#define BFA_TRC_FILE(__mod, __submod) \ + static int __trc_fileno = ((BFA_TRC_ ## __mod ## _ ## __submod) | \ + BFA_TRC_MOD(__mod)) + + +#define bfa_trc32(_trcp, _data) \ + __bfa_trc((_trcp)->trcmod, __trc_fileno, __LINE__, (u32)_data) + + +#ifndef BFA_BOOT_BUILD +#define bfa_trc(_trcp, _data) \ + __bfa_trc((_trcp)->trcmod, __trc_fileno, __LINE__, (u64)_data) +#else +void bfa_boot_trc(struct bfa_trc_mod_s *trcmod, u16 fileno, + u16 line, u32 data); +#define bfa_trc(_trcp, _data) \ + bfa_boot_trc((_trcp)->trcmod, __trc_fileno, __LINE__, (u32)_data) +#endif + + +static inline void +bfa_trc_init(struct bfa_trc_mod_s *trcm) +{ + trcm->head = trcm->tail = trcm->stopped = 0; + trcm->ntrc = BFA_TRC_MAX; +} + + +static inline void +bfa_trc_stop(struct bfa_trc_mod_s *trcm) +{ + trcm->stopped = 1; +} + +#ifdef FWTRC +extern void dc_flush(void *data); +#else +#define dc_flush(data) +#endif + + +static inline void +__bfa_trc(struct bfa_trc_mod_s *trcm, int fileno, int line, u64 data) +{ + int tail = trcm->tail; + struct bfa_trc_s *trc = &trcm->trc[tail]; + + if (trcm->stopped) + return; + + trc->fileno = (u16) fileno; + trc->line = (u16) line; + trc->data.u64 = data; + trc->timestamp = BFA_TRC_TS(trcm); + dc_flush(trc); + + trcm->tail = (trcm->tail + 1) & (BFA_TRC_MAX - 1); + if (trcm->tail == trcm->head) + trcm->head = (trcm->head + 1) & (BFA_TRC_MAX - 1); + dc_flush(trcm); +} + + +static inline void +__bfa_trc32(struct bfa_trc_mod_s *trcm, int fileno, int line, u32 data) +{ + int tail = trcm->tail; + struct bfa_trc_s *trc = &trcm->trc[tail]; + + if (trcm->stopped) + return; + + trc->fileno = (u16) fileno; + trc->line = (u16) line; + trc->data.u32.u32 = data; + trc->timestamp = BFA_TRC_TS(trcm); + dc_flush(trc); + + trcm->tail = (trcm->tail + 1) & (BFA_TRC_MAX - 1); + if (trcm->tail == trcm->head) + trcm->head = (trcm->head + 1) & (BFA_TRC_MAX - 1); + dc_flush(trcm); +} + +#ifndef BFA_PERF_BUILD +#define bfa_trc_fp(_trcp, _data) bfa_trc(_trcp, _data) +#else +#define bfa_trc_fp(_trcp, _data) +#endif + +#endif /* __BFA_TRC_H__ */ + diff --git a/drivers/scsi/bfa/include/cs/bfa_wc.h b/drivers/scsi/bfa/include/cs/bfa_wc.h new file mode 100644 index 000000000000..0460bd4fc7c4 --- /dev/null +++ b/drivers/scsi/bfa/include/cs/bfa_wc.h @@ -0,0 +1,68 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_wc.h Generic wait counter. + */ + +#ifndef __BFA_WC_H__ +#define __BFA_WC_H__ + +typedef void (*bfa_wc_resume_t) (void *cbarg); + +struct bfa_wc_s { + bfa_wc_resume_t wc_resume; + void *wc_cbarg; + int wc_count; +}; + +static inline void +bfa_wc_up(struct bfa_wc_s *wc) +{ + wc->wc_count++; +} + +static inline void +bfa_wc_down(struct bfa_wc_s *wc) +{ + wc->wc_count--; + if (wc->wc_count == 0) + wc->wc_resume(wc->wc_cbarg); +} + +/** + * Initialize a waiting counter. + */ +static inline void +bfa_wc_init(struct bfa_wc_s *wc, bfa_wc_resume_t wc_resume, void *wc_cbarg) +{ + wc->wc_resume = wc_resume; + wc->wc_cbarg = wc_cbarg; + wc->wc_count = 0; + bfa_wc_up(wc); +} + +/** + * Wait for counter to reach zero + */ +static inline void +bfa_wc_wait(struct bfa_wc_s *wc) +{ + bfa_wc_down(wc); +} + +#endif diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_adapter.h b/drivers/scsi/bfa/include/defs/bfa_defs_adapter.h new file mode 100644 index 000000000000..8c208fc8e329 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_adapter.h @@ -0,0 +1,82 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_ADAPTER_H__ +#define __BFA_DEFS_ADAPTER_H__ + +#include <protocol/types.h> +#include <defs/bfa_defs_version.h> +#include <defs/bfa_defs_mfg.h> + +/** + * BFA adapter level attributes. + */ +enum { + BFA_ADAPTER_SERIAL_NUM_LEN = STRSZ(BFA_MFG_SERIALNUM_SIZE), + /* + *!< adapter serial num length + */ + BFA_ADAPTER_MODEL_NAME_LEN = 16, /* model name length */ + BFA_ADAPTER_MODEL_DESCR_LEN = 128, /* model description length */ + BFA_ADAPTER_MFG_NAME_LEN = 8, /* manufacturer name length */ + BFA_ADAPTER_SYM_NAME_LEN = 64, /* adapter symbolic name length */ + BFA_ADAPTER_OS_TYPE_LEN = 64, /* adapter os type length */ +}; + +struct bfa_adapter_attr_s { + char manufacturer[BFA_ADAPTER_MFG_NAME_LEN]; + char serial_num[BFA_ADAPTER_SERIAL_NUM_LEN]; + u32 rsvd1; + char model[BFA_ADAPTER_MODEL_NAME_LEN]; + char model_descr[BFA_ADAPTER_MODEL_DESCR_LEN]; + wwn_t pwwn; + char node_symname[FC_SYMNAME_MAX]; + char hw_ver[BFA_VERSION_LEN]; + char fw_ver[BFA_VERSION_LEN]; + char optrom_ver[BFA_VERSION_LEN]; + char os_type[BFA_ADAPTER_OS_TYPE_LEN]; + struct bfa_mfg_vpd_s vpd; + struct mac_s mac; + + u8 nports; + u8 max_speed; + u8 prototype; + char asic_rev; + + u8 pcie_gen; + u8 pcie_lanes_orig; + u8 pcie_lanes; + u8 cna_capable; +}; + +/** + * BFA adapter level events + * Arguments below are in BFAL context from Mgmt + * BFA_PORT_AEN_ADD: [in]: None [out]: serial_num, pwwn, nports + * BFA_PORT_AEN_REMOVE: [in]: pwwn [out]: serial_num, pwwn, nports + */ +enum bfa_adapter_aen_event { + BFA_ADAPTER_AEN_ADD = 1, /* New Adapter found event */ + BFA_ADAPTER_AEN_REMOVE = 2, /* Adapter removed event */ +}; + +struct bfa_adapter_aen_data_s { + char serial_num[BFA_ADAPTER_SERIAL_NUM_LEN]; + u32 nports; /* Number of NPorts */ + wwn_t pwwn; /* WWN of one of its physical port */ +}; + +#endif /* __BFA_DEFS_ADAPTER_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_aen.h b/drivers/scsi/bfa/include/defs/bfa_defs_aen.h new file mode 100644 index 000000000000..4c81a613db3d --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_aen.h @@ -0,0 +1,73 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_AEN_H__ +#define __BFA_DEFS_AEN_H__ + +#include <defs/bfa_defs_types.h> +#include <defs/bfa_defs_ioc.h> +#include <defs/bfa_defs_adapter.h> +#include <defs/bfa_defs_port.h> +#include <defs/bfa_defs_lport.h> +#include <defs/bfa_defs_rport.h> +#include <defs/bfa_defs_itnim.h> +#include <defs/bfa_defs_tin.h> +#include <defs/bfa_defs_ipfc.h> +#include <defs/bfa_defs_audit.h> +#include <defs/bfa_defs_ethport.h> + +enum bfa_aen_category { + BFA_AEN_CAT_ADAPTER = 1, + BFA_AEN_CAT_PORT = 2, + BFA_AEN_CAT_LPORT = 3, + BFA_AEN_CAT_RPORT = 4, + BFA_AEN_CAT_ITNIM = 5, + BFA_AEN_CAT_TIN = 6, + BFA_AEN_CAT_IPFC = 7, + BFA_AEN_CAT_AUDIT = 8, + BFA_AEN_CAT_IOC = 9, + BFA_AEN_CAT_ETHPORT = 10, + BFA_AEN_MAX_CAT = 10 +}; + +#pragma pack(1) +union bfa_aen_data_u { + struct bfa_adapter_aen_data_s adapter; + struct bfa_port_aen_data_s port; + struct bfa_lport_aen_data_s lport; + struct bfa_rport_aen_data_s rport; + struct bfa_itnim_aen_data_s itnim; + struct bfa_audit_aen_data_s audit; + struct bfa_ioc_aen_data_s ioc; + struct bfa_ethport_aen_data_s ethport; +}; + +struct bfa_aen_entry_s { + enum bfa_aen_category aen_category; + int aen_type; + union bfa_aen_data_u aen_data; + struct bfa_timeval_s aen_tv; + s32 seq_num; + s32 bfad_num; + s32 rsvd[1]; +}; + +#pragma pack() + +#define bfa_aen_event_t int + +#endif /* __BFA_DEFS_AEN_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_audit.h b/drivers/scsi/bfa/include/defs/bfa_defs_audit.h new file mode 100644 index 000000000000..8e3a962bf20c --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_audit.h @@ -0,0 +1,38 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_AUDIT_H__ +#define __BFA_DEFS_AUDIT_H__ + +#include <bfa_os_inc.h> + +/** + * BFA audit events + */ +enum bfa_audit_aen_event { + BFA_AUDIT_AEN_AUTH_ENABLE = 1, + BFA_AUDIT_AEN_AUTH_DISABLE = 2, +}; + +/** + * audit event data + */ +struct bfa_audit_aen_data_s { + wwn_t pwwn; +}; + +#endif /* __BFA_DEFS_AUDIT_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_auth.h b/drivers/scsi/bfa/include/defs/bfa_defs_auth.h new file mode 100644 index 000000000000..dd19c83aba58 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_auth.h @@ -0,0 +1,112 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_AUTH_H__ +#define __BFA_DEFS_AUTH_H__ + +#include <defs/bfa_defs_types.h> + +#define PUBLIC_KEY 15409 +#define PRIVATE_KEY 19009 +#define KEY_LEN 32399 +#define BFA_AUTH_SECRET_STRING_LEN 256 +#define BFA_AUTH_FAIL_TIMEOUT 0xFF + +/** + * Authentication status + */ +enum bfa_auth_status { + BFA_AUTH_STATUS_NONE = 0, /* no authentication */ + BFA_AUTH_UNINIT = 1, /* state - uninit */ + BFA_AUTH_NEG_SEND = 2, /* state - negotiate send */ + BFA_AUTH_CHAL_WAIT = 3, /* state - challenge wait */ + BFA_AUTH_NEG_RETRY = 4, /* state - negotiate retry */ + BFA_AUTH_REPLY_SEND = 5, /* state - reply send */ + BFA_AUTH_STATUS_WAIT = 6, /* state - status wait */ + BFA_AUTH_SUCCESS = 7, /* state - success */ + BFA_AUTH_FAILED = 8, /* state - failed */ + BFA_AUTH_STATUS_UNKNOWN = 9, /* authentication status unknown */ +}; + +struct auth_proto_stats_s { + u32 auth_rjts; + u32 auth_negs; + u32 auth_dones; + + u32 dhchap_challenges; + u32 dhchap_replies; + u32 dhchap_successes; +}; + +/** + * Authentication related statistics + */ +struct bfa_auth_stats_s { + u32 auth_failures; /* authentication failures */ + u32 auth_successes; /* authentication successes*/ + struct auth_proto_stats_s auth_rx_stats; /* Rx protocol stats */ + struct auth_proto_stats_s auth_tx_stats; /* Tx protocol stats */ +}; + +/** + * Authentication hash function algorithms + */ +enum bfa_auth_algo { + BFA_AUTH_ALGO_MD5 = 1, /* Message-Digest algorithm 5 */ + BFA_AUTH_ALGO_SHA1 = 2, /* Secure Hash Algorithm 1 */ + BFA_AUTH_ALGO_MS = 3, /* MD5, then SHA-1 */ + BFA_AUTH_ALGO_SM = 4, /* SHA-1, then MD5 */ +}; + +/** + * DH Groups + * + * Current value could be combination of one or more of the following values + */ +enum bfa_auth_group { + BFA_AUTH_GROUP_DHNULL = 0, /* DH NULL (value == 0) */ + BFA_AUTH_GROUP_DH768 = 1, /* DH group 768 (value == 1) */ + BFA_AUTH_GROUP_DH1024 = 2, /* DH group 1024 (value == 2) */ + BFA_AUTH_GROUP_DH1280 = 4, /* DH group 1280 (value == 3) */ + BFA_AUTH_GROUP_DH1536 = 8, /* DH group 1536 (value == 4) */ + + BFA_AUTH_GROUP_ALL = 256 /* Use default DH group order + * 0, 1, 2, 3, 4 */ +}; + +/** + * Authentication secret sources + */ +enum bfa_auth_secretsource { + BFA_AUTH_SECSRC_LOCAL = 1, /* locally configured */ + BFA_AUTH_SECSRC_RADIUS = 2, /* use radius server */ + BFA_AUTH_SECSRC_TACACS = 3, /* TACACS server */ +}; + +/** + * Authentication attributes + */ +struct bfa_auth_attr_s { + enum bfa_auth_status status; + enum bfa_auth_algo algo; + enum bfa_auth_group dh_grp; + u16 rjt_code; + u16 rjt_code_exp; + u8 secret_set; + u8 resv[7]; +}; + +#endif /* __BFA_DEFS_AUTH_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_boot.h b/drivers/scsi/bfa/include/defs/bfa_defs_boot.h new file mode 100644 index 000000000000..6f4aa5283545 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_boot.h @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_BOOT_H__ +#define __BFA_DEFS_BOOT_H__ + +#include <protocol/types.h> +#include <defs/bfa_defs_types.h> +#include <defs/bfa_defs_pport.h> + +enum { + BFA_BOOT_BOOTLUN_MAX = 4, /* maximum boot lun per IOC */ +}; + +#define BOOT_CFG_REV1 1 + +/** + * Boot options setting. Boot options setting determines from where + * to get the boot lun information + */ +enum bfa_boot_bootopt { + BFA_BOOT_AUTO_DISCOVER = 0, /* Boot from blun provided by fabric */ + BFA_BOOT_STORED_BLUN = 1, /* Boot from bluns stored in flash */ + BFA_BOOT_FIRST_LUN = 2, /* Boot from first discovered blun */ +}; + +/** + * Boot lun information. + */ +struct bfa_boot_bootlun_s { + wwn_t pwwn; /* port wwn of target */ + lun_t lun; /* 64-bit lun */ +}; + +/** + * BOOT boot configuraton + */ +struct bfa_boot_cfg_s { + u8 version; + u8 rsvd1; + u16 chksum; + + u8 enable; /* enable/disable SAN boot */ + u8 speed; /* boot speed settings */ + u8 topology; /* boot topology setting */ + u8 bootopt; /* bfa_boot_bootopt_t */ + + u32 nbluns; /* number of boot luns */ + + u32 rsvd2; + + struct bfa_boot_bootlun_s blun[BFA_BOOT_BOOTLUN_MAX]; + struct bfa_boot_bootlun_s blun_disc[BFA_BOOT_BOOTLUN_MAX]; +}; + + +#endif /* __BFA_DEFS_BOOT_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_cee.h b/drivers/scsi/bfa/include/defs/bfa_defs_cee.h new file mode 100644 index 000000000000..520a22f52dd1 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_cee.h @@ -0,0 +1,159 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * bfa_defs_cee.h Interface declarations between host based + * BFAL and DCBX/LLDP module in Firmware + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_CEE_H__ +#define __BFA_DEFS_CEE_H__ + +#include <defs/bfa_defs_types.h> +#include <defs/bfa_defs_pport.h> +#include <protocol/types.h> + +#pragma pack(1) + +#define BFA_CEE_LLDP_MAX_STRING_LEN (128) + + +/* FIXME: this is coming from the protocol spec. Can the host & apps share the + protocol .h files ? + */ +#define BFA_CEE_LLDP_SYS_CAP_OTHER 0x0001 +#define BFA_CEE_LLDP_SYS_CAP_REPEATER 0x0002 +#define BFA_CEE_LLDP_SYS_CAP_MAC_BRIDGE 0x0004 +#define BFA_CEE_LLDP_SYS_CAP_WLAN_AP 0x0008 +#define BFA_CEE_LLDP_SYS_CAP_ROUTER 0x0010 +#define BFA_CEE_LLDP_SYS_CAP_TELEPHONE 0x0020 +#define BFA_CEE_LLDP_SYS_CAP_DOCSIS_CD 0x0040 +#define BFA_CEE_LLDP_SYS_CAP_STATION 0x0080 +#define BFA_CEE_LLDP_SYS_CAP_CVLAN 0x0100 +#define BFA_CEE_LLDP_SYS_CAP_SVLAN 0x0200 +#define BFA_CEE_LLDP_SYS_CAP_TPMR 0x0400 + + +/* LLDP string type */ +struct bfa_cee_lldp_str_s { + u8 sub_type; + u8 len; + u8 rsvd[2]; + u8 value[BFA_CEE_LLDP_MAX_STRING_LEN]; +}; + + +/* LLDP paramters */ +struct bfa_cee_lldp_cfg_s { + struct bfa_cee_lldp_str_s chassis_id; + struct bfa_cee_lldp_str_s port_id; + struct bfa_cee_lldp_str_s port_desc; + struct bfa_cee_lldp_str_s sys_name; + struct bfa_cee_lldp_str_s sys_desc; + struct bfa_cee_lldp_str_s mgmt_addr; + u16 time_to_interval; + u16 enabled_system_cap; +}; + +enum bfa_cee_dcbx_version_e { + DCBX_PROTOCOL_PRECEE = 1, + DCBX_PROTOCOL_CEE = 2, +}; + +enum bfa_cee_lls_e { + CEE_LLS_DOWN_NO_TLV = 0, /* LLS is down because the TLV not sent by + * the peer */ + CEE_LLS_DOWN = 1, /* LLS is down as advertised by the peer */ + CEE_LLS_UP = 2, +}; + +/* CEE/DCBX parameters */ +struct bfa_cee_dcbx_cfg_s { + u8 pgid[8]; + u8 pg_percentage[8]; + u8 pfc_enabled; /* bitmap of priorties with PFC enabled */ + u8 fcoe_user_priority; /* bitmap of priorities used for FcoE + * traffic */ + u8 dcbx_version; /* operating version:CEE or preCEE */ + u8 lls_fcoe; /* FCoE Logical Link Status */ + u8 lls_lan; /* LAN Logical Link Status */ + u8 rsvd[3]; +}; + +/* CEE status */ +/* Making this to tri-state for the benefit of port list command */ +enum bfa_cee_status_e { + CEE_PHY_DOWN = 0, + CEE_PHY_UP = 1, + CEE_UP = 2, +}; + +/* CEE Query */ +struct bfa_cee_attr_s { + u8 cee_status; + u8 error_reason; + struct bfa_cee_lldp_cfg_s lldp_remote; + struct bfa_cee_dcbx_cfg_s dcbx_remote; + mac_t src_mac; + u8 link_speed; + u8 filler[3]; +}; + + + + +/* LLDP/DCBX/CEE Statistics */ + +struct bfa_cee_lldp_stats_s { + u32 frames_transmitted; + u32 frames_aged_out; + u32 frames_discarded; + u32 frames_in_error; + u32 frames_rcvd; + u32 tlvs_discarded; + u32 tlvs_unrecognized; +}; + +struct bfa_cee_dcbx_stats_s { + u32 subtlvs_unrecognized; + u32 negotiation_failed; + u32 remote_cfg_changed; + u32 tlvs_received; + u32 tlvs_invalid; + u32 seqno; + u32 ackno; + u32 recvd_seqno; + u32 recvd_ackno; +}; + +struct bfa_cee_cfg_stats_s { + u32 cee_status_down; + u32 cee_status_up; + u32 cee_hw_cfg_changed; + u32 recvd_invalid_cfg; +}; + + +struct bfa_cee_stats_s { + struct bfa_cee_lldp_stats_s lldp_stats; + struct bfa_cee_dcbx_stats_s dcbx_stats; + struct bfa_cee_cfg_stats_s cfg_stats; +}; + +#pragma pack() + + +#endif /* __BFA_DEFS_CEE_H__ */ + + diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_driver.h b/drivers/scsi/bfa/include/defs/bfa_defs_driver.h new file mode 100644 index 000000000000..57049805762b --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_driver.h @@ -0,0 +1,40 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_DRIVER_H__ +#define __BFA_DEFS_DRIVER_H__ + +/** + * Driver statistics + */ + u16 tm_io_abort; + u16 tm_io_abort_comp; + u16 tm_lun_reset; + u16 tm_lun_reset_comp; + u16 tm_target_reset; + u16 tm_bus_reset; + u16 ioc_restart; /* IOC restart count */ + u16 io_pending; /* outstanding io count per-IOC */ + u64 control_req; + u64 input_req; + u64 output_req; + u64 input_words; + u64 output_words; +} bfa_driver_stats_t; + + +#endif /* __BFA_DEFS_DRIVER_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_ethport.h b/drivers/scsi/bfa/include/defs/bfa_defs_ethport.h new file mode 100644 index 000000000000..79f9b3e146f7 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_ethport.h @@ -0,0 +1,98 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_ETHPORT_H__ +#define __BFA_DEFS_ETHPORT_H__ + +#include <defs/bfa_defs_status.h> +#include <protocol/types.h> +#include <cna/pstats/phyport_defs.h> +#include <cna/pstats/ethport_defs.h> + +struct bna_tx_info_s { + u32 miniport_state; + u32 adapter_state; + u64 tx_count; + u64 tx_wi; + u64 tx_sg; + u64 tx_tcp_chksum; + u64 tx_udp_chksum; + u64 tx_ip_chksum; + u64 tx_lsov1; + u64 tx_lsov2; + u64 tx_max_sg_len ; +}; + +struct bna_rx_queue_info_s { + u16 q_id ; + u16 buf_size ; + u16 buf_count ; + u16 rsvd ; + u64 rx_count ; + u64 rx_dropped ; + u64 rx_unsupported ; + u64 rx_internal_err ; + u64 rss_count ; + u64 vlan_count ; + u64 rx_tcp_chksum ; + u64 rx_udp_chksum ; + u64 rx_ip_chksum ; + u64 rx_hds ; +}; + +struct bna_rx_q_set_s { + u16 q_set_type; + u32 miniport_state; + u32 adapter_state; + struct bna_rx_queue_info_s rx_queue[2]; +}; + +struct bna_port_stats_s { + struct bna_tx_info_s tx_stats; + u16 qset_count ; + struct bna_rx_q_set_s rx_qset[8]; +}; + +struct bfa_ethport_stats_s { + struct bna_stats_txf txf_stats[1]; + struct bna_stats_rxf rxf_stats[1]; + struct bnad_drv_stats drv_stats; +}; + +/** + * Ethernet port events + * Arguments below are in BFAL context from Mgmt + * BFA_PORT_AEN_ETH_LINKUP: [in]: mac [out]: mac + * BFA_PORT_AEN_ETH_LINKDOWN: [in]: mac [out]: mac + * BFA_PORT_AEN_ETH_ENABLE: [in]: mac [out]: mac + * BFA_PORT_AEN_ETH_DISABLE: [in]: mac [out]: mac + * + */ +enum bfa_ethport_aen_event { + BFA_ETHPORT_AEN_LINKUP = 1, /* Base Port Ethernet link up event */ + BFA_ETHPORT_AEN_LINKDOWN = 2, /* Base Port Ethernet link down event */ + BFA_ETHPORT_AEN_ENABLE = 3, /* Base Port Ethernet link enable event */ + BFA_ETHPORT_AEN_DISABLE = 4, /* Base Port Ethernet link disable + * event */ +}; + +struct bfa_ethport_aen_data_s { + mac_t mac; /* MAC address of the physical port */ +}; + + +#endif /* __BFA_DEFS_ETHPORT_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_fcpim.h b/drivers/scsi/bfa/include/defs/bfa_defs_fcpim.h new file mode 100644 index 000000000000..c08f4f5026ac --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_fcpim.h @@ -0,0 +1,45 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_FCPIM_H__ +#define __BFA_DEFS_FCPIM_H__ + +struct bfa_fcpim_stats_s { + u32 total_ios; /* Total IO count */ + u32 qresumes; /* IO waiting for CQ space */ + u32 no_iotags; /* NO IO contexts */ + u32 io_aborts; /* IO abort requests */ + u32 no_tskims; /* NO task management contexts */ + u32 iocomp_ok; /* IO completions with OK status */ + u32 iocomp_underrun; /* IO underrun (good) */ + u32 iocomp_overrun; /* IO overrun (good) */ + u32 iocomp_aborted; /* Aborted IO requests */ + u32 iocomp_timedout; /* IO timeouts */ + u32 iocom_nexus_abort; /* IO selection timeouts */ + u32 iocom_proto_err; /* IO protocol errors */ + u32 iocom_dif_err; /* IO SBC-3 protection errors */ + u32 iocom_tm_abort; /* IO aborted by TM requests */ + u32 iocom_sqer_needed; /* IO retry for SQ error + *recovery */ + u32 iocom_res_free; /* Delayed freeing of IO resources */ + u32 iocomp_scsierr; /* IO with non-good SCSI status */ + u32 iocom_hostabrts; /* Host IO abort requests */ + u32 iocom_utags; /* IO comp with unknown tags */ + u32 io_cleanups; /* IO implicitly aborted */ + u32 io_tmaborts; /* IO aborted due to TM commands */ + u32 rsvd; +}; +#endif /*__BFA_DEFS_FCPIM_H__*/ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_im_common.h b/drivers/scsi/bfa/include/defs/bfa_defs_im_common.h new file mode 100644 index 000000000000..9ccf53bef65a --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_im_common.h @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_IM_COMMON_H__ +#define __BFA_DEFS_IM_COMMON_H__ + +#define BFA_ADAPTER_NAME_LEN 256 +#define BFA_ADAPTER_GUID_LEN 256 +#define RESERVED_VLAN_NAME L"PORT VLAN" +#define PASSTHRU_VLAN_NAME L"PASSTHRU VLAN" + + u64 tx_pkt_cnt; + u64 rx_pkt_cnt; + u32 duration; + u8 status; +} bfa_im_stats_t, *pbfa_im_stats_t; + +#endif /* __BFA_DEFS_IM_COMMON_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_im_team.h b/drivers/scsi/bfa/include/defs/bfa_defs_im_team.h new file mode 100644 index 000000000000..a486a7eb81d6 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_im_team.h @@ -0,0 +1,72 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_IM_TEAM_H__ +#define __BFA_DEFS_IM_TEAM_H__ + +#include <protocol/types.h> + +#define BFA_TEAM_MAX_PORTS 8 +#define BFA_TEAM_NAME_LEN 256 +#define BFA_MAX_NUM_TEAMS 16 +#define BFA_TEAM_INVALID_DELAY -1 + + BFA_LACP_RATE_SLOW = 1, + BFA_LACP_RATE_FAST +} bfa_im_lacp_rate_t; + + BFA_TEAM_MODE_FAIL_OVER = 1, + BFA_TEAM_MODE_FAIL_BACK, + BFA_TEAM_MODE_LACP, + BFA_TEAM_MODE_NONE +} bfa_im_team_mode_t; + + BFA_XMIT_POLICY_L2 = 1, + BFA_XMIT_POLICY_L3_L4 +} bfa_im_xmit_policy_t; + + bfa_im_team_mode_t team_mode; + bfa_im_lacp_rate_t lacp_rate; + bfa_im_xmit_policy_t xmit_policy; + int delay; + wchar_t primary[BFA_ADAPTER_NAME_LEN]; + wchar_t preferred_primary[BFA_ADAPTER_NAME_LEN]; + mac_t mac; + u16 num_ports; + u16 num_vlans; + u16 vlan_list[BFA_MAX_VLANS_PER_PORT]; + wchar_t team_guid_list[BFA_TEAM_MAX_PORTS][BFA_ADAPTER_GUID_LEN]; + wchar_t ioc_name_list[BFA_TEAM_MAX_PORTS][BFA_ADAPTER_NAME_LEN]; +} bfa_im_team_attr_t; + + wchar_t team_name[BFA_TEAM_NAME_LEN]; + bfa_im_xmit_policy_t xmit_policy; + int delay; + wchar_t primary[BFA_ADAPTER_NAME_LEN]; + wchar_t preferred_primary[BFA_ADAPTER_NAME_LEN]; +} bfa_im_team_edit_t, *pbfa_im_team_edit_t; + + wchar_t team_name[BFA_TEAM_NAME_LEN]; + bfa_im_team_mode_t team_mode; + mac_t mac; +} bfa_im_team_info_t; + + bfa_im_team_info_t team_info[BFA_MAX_NUM_TEAMS]; + u16 num_teams; +} bfa_im_team_list_t, *pbfa_im_team_list_t; + +#endif /* __BFA_DEFS_IM_TEAM_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_ioc.h b/drivers/scsi/bfa/include/defs/bfa_defs_ioc.h new file mode 100644 index 000000000000..b1d532da3a9d --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_ioc.h @@ -0,0 +1,152 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_IOC_H__ +#define __BFA_DEFS_IOC_H__ + +#include <protocol/types.h> +#include <defs/bfa_defs_types.h> +#include <defs/bfa_defs_version.h> +#include <defs/bfa_defs_adapter.h> +#include <defs/bfa_defs_pm.h> + +enum { + BFA_IOC_DRIVER_LEN = 16, + BFA_IOC_CHIP_REV_LEN = 8, +}; + +/** + * Driver and firmware versions. + */ +struct bfa_ioc_driver_attr_s { + char driver[BFA_IOC_DRIVER_LEN]; /* driver name */ + char driver_ver[BFA_VERSION_LEN]; /* driver version */ + char fw_ver[BFA_VERSION_LEN]; /* firmware version*/ + char bios_ver[BFA_VERSION_LEN]; /* bios version */ + char efi_ver[BFA_VERSION_LEN]; /* EFI version */ + char ob_ver[BFA_VERSION_LEN]; /* openboot version*/ +}; + +/** + * IOC PCI device attributes + */ +struct bfa_ioc_pci_attr_s { + u16 vendor_id; /* PCI vendor ID */ + u16 device_id; /* PCI device ID */ + u16 ssid; /* subsystem ID */ + u16 ssvid; /* subsystem vendor ID */ + u32 pcifn; /* PCI device function */ + u32 rsvd; /* padding */ + u8 chip_rev[BFA_IOC_CHIP_REV_LEN]; /* chip revision */ +}; + +/** + * IOC states + */ +enum bfa_ioc_state { + BFA_IOC_RESET = 1, /* IOC is in reset state */ + BFA_IOC_SEMWAIT = 2, /* Waiting for IOC hardware semaphore */ + BFA_IOC_HWINIT = 3, /* IOC hardware is being initialized */ + BFA_IOC_GETATTR = 4, /* IOC is being configured */ + BFA_IOC_OPERATIONAL = 5, /* IOC is operational */ + BFA_IOC_INITFAIL = 6, /* IOC hardware failure */ + BFA_IOC_HBFAIL = 7, /* IOC heart-beat failure */ + BFA_IOC_DISABLING = 8, /* IOC is being disabled */ + BFA_IOC_DISABLED = 9, /* IOC is disabled */ + BFA_IOC_FWMISMATCH = 10, /* IOC firmware different from drivers */ +}; + +/** + * IOC firmware stats + */ +struct bfa_fw_ioc_stats_s { + u32 hb_count; + u32 cfg_reqs; + u32 enable_reqs; + u32 disable_reqs; + u32 stats_reqs; + u32 clrstats_reqs; + u32 unknown_reqs; + u32 ic_reqs; /* interrupt coalesce reqs */ +}; + +/** + * IOC driver stats + */ +struct bfa_ioc_drv_stats_s { + u32 ioc_isrs; + u32 ioc_enables; + u32 ioc_disables; + u32 ioc_hbfails; + u32 ioc_boots; + u32 stats_tmos; + u32 hb_count; + u32 disable_reqs; + u32 enable_reqs; + u32 disable_replies; + u32 enable_replies; +}; + +/** + * IOC statistics + */ +struct bfa_ioc_stats_s { + struct bfa_ioc_drv_stats_s drv_stats; /* driver IOC stats */ + struct bfa_fw_ioc_stats_s fw_stats; /* firmware IOC stats */ +}; + + +enum bfa_ioc_type_e { + BFA_IOC_TYPE_FC = 1, + BFA_IOC_TYPE_FCoE = 2, + BFA_IOC_TYPE_LL = 3, +}; + +/** + * IOC attributes returned in queries + */ +struct bfa_ioc_attr_s { + enum bfa_ioc_type_e ioc_type; + enum bfa_ioc_state state; /* IOC state */ + struct bfa_adapter_attr_s adapter_attr; /* HBA attributes */ + struct bfa_ioc_driver_attr_s driver_attr; /* driver attr */ + struct bfa_ioc_pci_attr_s pci_attr; + u8 port_id; /* port number */ +}; + +/** + * BFA IOC level events + */ +enum bfa_ioc_aen_event { + BFA_IOC_AEN_HBGOOD = 1, /* Heart Beat restore event */ + BFA_IOC_AEN_HBFAIL = 2, /* Heart Beat failure event */ + BFA_IOC_AEN_ENABLE = 3, /* IOC enabled event */ + BFA_IOC_AEN_DISABLE = 4, /* IOC disabled event */ + BFA_IOC_AEN_FWMISMATCH = 5, /* IOC firmware mismatch */ +}; + +/** + * BFA IOC level event data, now just a place holder + */ +struct bfa_ioc_aen_data_s { + enum bfa_ioc_type_e ioc_type; + wwn_t pwwn; + mac_t mac; +}; + +#endif /* __BFA_DEFS_IOC_H__ */ + diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_iocfc.h b/drivers/scsi/bfa/include/defs/bfa_defs_iocfc.h new file mode 100644 index 000000000000..d76bcbd9820f --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_iocfc.h @@ -0,0 +1,310 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_IOCFC_H__ +#define __BFA_DEFS_IOCFC_H__ + +#include <protocol/types.h> +#include <defs/bfa_defs_types.h> +#include <defs/bfa_defs_version.h> +#include <defs/bfa_defs_adapter.h> +#include <defs/bfa_defs_pm.h> + +#define BFA_IOCFC_INTR_DELAY 1125 +#define BFA_IOCFC_INTR_LATENCY 225 + +/** + * Interrupt coalescing configuration. + */ +struct bfa_iocfc_intr_attr_s { + bfa_boolean_t coalesce; /* enable/disable coalescing */ + u16 latency; /* latency in microseconds */ + u16 delay; /* delay in microseconds */ +}; + +/** + * IOC firmware configuraton + */ +struct bfa_iocfc_fwcfg_s { + u16 num_fabrics; /* number of fabrics */ + u16 num_lports; /* number of local lports */ + u16 num_rports; /* number of remote ports */ + u16 num_ioim_reqs; /* number of IO reqs */ + u16 num_tskim_reqs; /* task management requests */ + u16 num_iotm_reqs; /* number of TM IO reqs */ + u16 num_tsktm_reqs; /* TM task management requests*/ + u16 num_fcxp_reqs; /* unassisted FC exchanges */ + u16 num_uf_bufs; /* unsolicited recv buffers */ + u8 num_cqs; + u8 rsvd; +}; + +struct bfa_iocfc_drvcfg_s { + u16 num_reqq_elems; /* number of req queue elements */ + u16 num_rspq_elems; /* number of rsp queue elements */ + u16 num_sgpgs; /* number of total SG pages */ + u16 num_sboot_tgts; /* number of SAN boot targets */ + u16 num_sboot_luns; /* number of SAN boot luns */ + u16 ioc_recover; /* IOC recovery mode */ + u16 min_cfg; /* minimum configuration */ + u16 path_tov; /* device path timeout */ + bfa_boolean_t delay_comp; /* delay completion of + failed inflight IOs */ + u32 rsvd; +}; +/** + * IOC configuration + */ +struct bfa_iocfc_cfg_s { + struct bfa_iocfc_fwcfg_s fwcfg; /* firmware side config */ + struct bfa_iocfc_drvcfg_s drvcfg; /* driver side config */ +}; + +/** + * IOC firmware IO stats + */ +struct bfa_fw_io_stats_s { + u32 host_abort; /* IO aborted by host driver*/ + u32 host_cleanup; /* IO clean up by host driver */ + + u32 fw_io_timeout; /* IOs timedout */ + u32 fw_frm_parse; /* frame parsed by f/w */ + u32 fw_frm_data; /* fcp_data frame parsed by f/w */ + u32 fw_frm_rsp; /* fcp_rsp frame parsed by f/w */ + u32 fw_frm_xfer_rdy; /* xfer_rdy frame parsed by f/w */ + u32 fw_frm_bls_acc; /* BLS ACC frame parsed by f/w */ + u32 fw_frm_tgt_abort; /* target ABTS parsed by f/w */ + u32 fw_frm_unknown; /* unknown parsed by f/w */ + u32 fw_data_dma; /* f/w DMA'ed the data frame */ + u32 fw_frm_drop; /* f/w drop the frame */ + + u32 rec_timeout; /* FW rec timed out */ + u32 error_rec; /* FW sending rec on + * an error condition*/ + u32 wait_for_si; /* FW wait for SI */ + u32 rec_rsp_inval; /* REC rsp invalid */ + u32 seqr_io_abort; /* target does not know cmd so abort */ + u32 seqr_io_retry; /* SEQR failed so retry IO */ + + u32 itn_cisc_upd_rsp; /* ITN cisc updated on fcp_rsp */ + u32 itn_cisc_upd_data; /* ITN cisc updated on fcp_data */ + u32 itn_cisc_upd_xfer_rdy; /* ITN cisc updated on fcp_data */ + + u32 fcp_data_lost; /* fcp data lost */ + + u32 ro_set_in_xfer_rdy; /* Target set RO in Xfer_rdy frame */ + u32 xfer_rdy_ooo_err; /* Out of order Xfer_rdy received */ + u32 xfer_rdy_unknown_err; /* unknown error in xfer_rdy frame */ + + u32 io_abort_timeout; /* ABTS timedout */ + u32 sler_initiated; /* SLER initiated */ + + u32 unexp_fcp_rsp; /* fcp response in wrong state */ + + u32 fcp_rsp_under_run; /* fcp rsp IO underrun */ + u32 fcp_rsp_under_run_wr; /* fcp rsp IO underrun for write */ + u32 fcp_rsp_under_run_err; /* fcp rsp IO underrun error */ + u32 fcp_rsp_resid_inval; /* invalid residue */ + u32 fcp_rsp_over_run; /* fcp rsp IO overrun */ + u32 fcp_rsp_over_run_err; /* fcp rsp IO overrun error */ + u32 fcp_rsp_proto_err; /* protocol error in fcp rsp */ + u32 fcp_rsp_sense_err; /* error in sense info in fcp rsp */ + u32 fcp_conf_req; /* FCP conf requested */ + + u32 tgt_aborted_io; /* target initiated abort */ + + u32 ioh_edtov_timeout_event;/* IOH edtov timer popped */ + u32 ioh_fcp_rsp_excp_event; /* IOH FCP_RSP exception */ + u32 ioh_fcp_conf_event; /* IOH FCP_CONF */ + u32 ioh_mult_frm_rsp_event; /* IOH multi_frame FCP_RSP */ + u32 ioh_hit_class2_event; /* IOH hit class2 */ + u32 ioh_miss_other_event; /* IOH miss other */ + u32 ioh_seq_cnt_err_event; /* IOH seq cnt error */ + u32 ioh_len_err_event; /* IOH len error - fcp_dl != + * bytes xfered */ + u32 ioh_seq_len_err_event; /* IOH seq len error */ + u32 ioh_data_oor_event; /* Data out of range */ + u32 ioh_ro_ooo_event; /* Relative offset out of range */ + u32 ioh_cpu_owned_event; /* IOH hit -iost owned by f/w */ + u32 ioh_unexp_frame_event; /* unexpected frame recieved + * count */ + u32 ioh_err_int; /* IOH error int during data-phase + * for scsi write + */ +}; + +/** + * IOC port firmware stats + */ + +struct bfa_fw_port_fpg_stats_s { + u32 intr_evt; + u32 intr; + u32 intr_excess; + u32 intr_cause0; + u32 intr_other; + u32 intr_other_ign; + u32 sig_lost; + u32 sig_regained; + u32 sync_lost; + u32 sync_to; + u32 sync_regained; + u32 div2_overflow; + u32 div2_underflow; + u32 efifo_overflow; + u32 efifo_underflow; + u32 idle_rx; + u32 lrr_rx; + u32 lr_rx; + u32 ols_rx; + u32 nos_rx; + u32 lip_rx; + u32 arbf0_rx; + u32 mrk_rx; + u32 const_mrk_rx; + u32 prim_unknown; + u32 rsvd; +}; + + +struct bfa_fw_port_lksm_stats_s { + u32 hwsm_success; /* hwsm state machine success */ + u32 hwsm_fails; /* hwsm fails */ + u32 hwsm_wdtov; /* hwsm timed out */ + u32 swsm_success; /* swsm success */ + u32 swsm_fails; /* swsm fails */ + u32 swsm_wdtov; /* swsm timed out */ + u32 busybufs; /* link init failed due to busybuf */ + u32 buf_waits; /* bufwait state entries */ + u32 link_fails; /* link failures */ + u32 psp_errors; /* primitive sequence protocol errors */ + u32 lr_unexp; /* No. of times LR rx-ed unexpectedly */ + u32 lrr_unexp; /* No. of times LRR rx-ed unexpectedly */ + u32 lr_tx; /* No. of times LR tx started */ + u32 lrr_tx; /* No. of times LRR tx started */ + u32 ols_tx; /* No. of times OLS tx started */ + u32 nos_tx; /* No. of times NOS tx started */ +}; + + +struct bfa_fw_port_snsm_stats_s { + u32 hwsm_success; /* Successful hwsm terminations */ + u32 hwsm_fails; /* hwsm fail count */ + u32 hwsm_wdtov; /* hwsm timed out */ + u32 swsm_success; /* swsm success */ + u32 swsm_wdtov; /* swsm timed out */ + u32 error_resets; /* error resets initiated by upsm */ + u32 sync_lost; /* Sync loss count */ + u32 sig_lost; /* Signal loss count */ +}; + + +struct bfa_fw_port_physm_stats_s { + u32 module_inserts; /* Module insert count */ + u32 module_xtracts; /* Module extracts count */ + u32 module_invalids; /* Invalid module inserted count */ + u32 module_read_ign; /* Module validation status ignored */ + u32 laser_faults; /* Laser fault count */ + u32 rsvd; +}; + + +struct bfa_fw_fip_stats_s { + u32 disc_req; /* Discovery solicit requests */ + u32 disc_rsp; /* Discovery solicit response */ + u32 disc_err; /* Discovery advt. parse errors */ + u32 disc_unsol; /* Discovery unsolicited */ + u32 disc_timeouts; /* Discovery timeouts */ + u32 linksvc_unsupp; /* Unsupported link service req */ + u32 linksvc_err; /* Parse error in link service req */ + u32 logo_req; /* Number of FIP logos received */ + u32 clrvlink_req; /* Clear virtual link req */ + u32 op_unsupp; /* Unsupported FIP operation */ + u32 untagged; /* Untagged frames (ignored) */ + u32 rsvd; +}; + + +struct bfa_fw_lps_stats_s { + u32 mac_invalids; /* Invalid mac assigned */ + u32 rsvd; +}; + + +struct bfa_fw_fcoe_stats_s { + u32 cee_linkups; /* CEE link up count */ + u32 cee_linkdns; /* CEE link down count */ + u32 fip_linkups; /* FIP link up count */ + u32 fip_linkdns; /* FIP link up count */ + u32 fip_fails; /* FIP fail count */ + u32 mac_invalids; /* Invalid mac assigned */ +}; + +/** + * IOC firmware FCoE port stats + */ +struct bfa_fw_fcoe_port_stats_s { + struct bfa_fw_fcoe_stats_s fcoe_stats; + struct bfa_fw_fip_stats_s fip_stats; +}; + +/** + * IOC firmware FC port stats + */ +struct bfa_fw_fc_port_stats_s { + struct bfa_fw_port_fpg_stats_s fpg_stats; + struct bfa_fw_port_physm_stats_s physm_stats; + struct bfa_fw_port_snsm_stats_s snsm_stats; + struct bfa_fw_port_lksm_stats_s lksm_stats; +}; + +/** + * IOC firmware FC port stats + */ +union bfa_fw_port_stats_s { + struct bfa_fw_fc_port_stats_s fc_stats; + struct bfa_fw_fcoe_port_stats_s fcoe_stats; +}; + +/** + * IOC firmware stats + */ +struct bfa_fw_stats_s { + struct bfa_fw_ioc_stats_s ioc_stats; + struct bfa_fw_io_stats_s io_stats; + union bfa_fw_port_stats_s port_stats; +}; + +/** + * IOC statistics + */ +struct bfa_iocfc_stats_s { + struct bfa_fw_stats_s fw_stats; /* firmware IOC stats */ +}; + +/** + * IOC attributes returned in queries + */ +struct bfa_iocfc_attr_s { + struct bfa_iocfc_cfg_s config; /* IOCFC config */ + struct bfa_iocfc_intr_attr_s intr_attr; /* interrupt attr */ +}; + +#define BFA_IOCFC_PATHTOV_MAX 60 +#define BFA_IOCFC_QDEPTH_MAX 2000 + +#endif /* __BFA_DEFS_IOC_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_ipfc.h b/drivers/scsi/bfa/include/defs/bfa_defs_ipfc.h new file mode 100644 index 000000000000..7cb63ea98f38 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_ipfc.h @@ -0,0 +1,70 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_IPFC_H__ +#define __BFA_DEFS_IPFC_H__ + +#include <bfa_os_inc.h> +#include <protocol/types.h> +#include <defs/bfa_defs_types.h> + +/** + * FCS ip remote port states + */ +enum bfa_iprp_state { + BFA_IPRP_UNINIT = 0, /* PORT is not yet initialized */ + BFA_IPRP_ONLINE = 1, /* process login is complete */ + BFA_IPRP_OFFLINE = 2, /* iprp is offline */ +}; + +/** + * FCS remote port statistics + */ +struct bfa_iprp_stats_s { + u32 offlines; + u32 onlines; + u32 rscns; + u32 plogis; + u32 logos; + u32 plogi_timeouts; + u32 plogi_rejects; +}; + +/** + * FCS iprp attribute returned in queries + */ +struct bfa_iprp_attr_s { + enum bfa_iprp_state state; +}; + +struct bfa_ipfc_stats_s { + u32 arp_sent; + u32 arp_recv; + u32 arp_reply_sent; + u32 arp_reply_recv; + u32 farp_sent; + u32 farp_recv; + u32 farp_reply_sent; + u32 farp_reply_recv; + u32 farp_reject_sent; + u32 farp_reject_recv; +}; + +struct bfa_ipfc_attr_s { + bfa_boolean_t enabled; +}; + +#endif /* __BFA_DEFS_IPFC_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_itnim.h b/drivers/scsi/bfa/include/defs/bfa_defs_itnim.h new file mode 100644 index 000000000000..2ec769903d24 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_itnim.h @@ -0,0 +1,126 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_ITNIM_H__ +#define __BFA_DEFS_ITNIM_H__ + +#include <bfa_os_inc.h> +#include <protocol/types.h> + +/** + * FCS itnim states + */ +enum bfa_itnim_state { + BFA_ITNIM_OFFLINE = 0, /* offline */ + BFA_ITNIM_PRLI_SEND = 1, /* prli send */ + BFA_ITNIM_PRLI_SENT = 2, /* prli sent */ + BFA_ITNIM_PRLI_RETRY = 3, /* prli retry */ + BFA_ITNIM_HCB_ONLINE = 4, /* online callback */ + BFA_ITNIM_ONLINE = 5, /* online */ + BFA_ITNIM_HCB_OFFLINE = 6, /* offline callback */ + BFA_ITNIM_INITIATIOR = 7, /* initiator */ +}; + +struct bfa_itnim_hal_stats_s { + u32 onlines; /* ITN nexus onlines (PRLI done) */ + u32 offlines; /* ITN Nexus offlines */ + u32 creates; /* ITN create requests */ + u32 deletes; /* ITN delete requests */ + u32 create_comps; /* ITN create completions */ + u32 delete_comps; /* ITN delete completions */ + u32 sler_events; /* SLER (sequence level error + * recovery) events */ + u32 ioc_disabled; /* Num IOC disables */ + u32 cleanup_comps; /* ITN cleanup completions */ + u32 tm_cmnds; /* task management(TM) cmnds sent */ + u32 tm_fw_rsps; /* TM cmds firmware responses */ + u32 tm_success; /* TM successes */ + u32 tm_failures; /* TM failures */ + u32 tm_io_comps; /* TM IO completions */ + u32 tm_qresumes; /* TM queue resumes (after waiting + * for resources) + */ + u32 tm_iocdowns; /* TM cmnds affected by IOC down */ + u32 tm_cleanups; /* TM cleanups */ + u32 tm_cleanup_comps; + /* TM cleanup completions */ + u32 ios; /* IO requests */ + u32 io_comps; /* IO completions */ + u64 input_reqs; /* INPUT requests */ + u64 output_reqs; /* OUTPUT requests */ +}; + +/** + * FCS remote port statistics + */ +struct bfa_itnim_stats_s { + u32 onlines; /* num rport online */ + u32 offlines; /* num rport offline */ + u32 prli_sent; /* num prli sent out */ + u32 fcxp_alloc_wait;/* num fcxp alloc waits */ + u32 prli_rsp_err; /* num prli rsp errors */ + u32 prli_rsp_acc; /* num prli rsp accepts */ + u32 initiator; /* rport is an initiator */ + u32 prli_rsp_parse_err; /* prli rsp parsing errors */ + u32 prli_rsp_rjt; /* num prli rsp rejects */ + u32 timeout; /* num timeouts detected */ + u32 sler; /* num sler notification from BFA */ + u32 rsvd; + struct bfa_itnim_hal_stats_s hal_stats; +}; + +/** + * FCS itnim attributes returned in queries + */ +struct bfa_itnim_attr_s { + enum bfa_itnim_state state; /* FCS itnim state */ + u8 retry; /* data retransmision support */ + u8 task_retry_id; /* task retry ident support */ + u8 rec_support; /* REC supported */ + u8 conf_comp; /* confirmed completion supp */ +}; + +/** + * BFA ITNIM events. + * Arguments below are in BFAL context from Mgmt + * BFA_ITNIM_AEN_NEW: [in]: None [out]: vf_id, lpwwn + * BFA_ITNIM_AEN_DELETE: [in]: vf_id, lpwwn, rpwwn (0 = all fcp4 targets), + * [out]: vf_id, ppwwn, lpwwn, rpwwn + * BFA_ITNIM_AEN_ONLINE: [in]: vf_id, lpwwn, rpwwn (0 = all fcp4 targets), + * [out]: vf_id, ppwwn, lpwwn, rpwwn + * BFA_ITNIM_AEN_OFFLINE: [in]: vf_id, lpwwn, rpwwn (0 = all fcp4 targets), + * [out]: vf_id, ppwwn, lpwwn, rpwwn + * BFA_ITNIM_AEN_DISCONNECT:[in]: vf_id, lpwwn, rpwwn (0 = all fcp4 targets), + * [out]: vf_id, ppwwn, lpwwn, rpwwn + */ +enum bfa_itnim_aen_event { + BFA_ITNIM_AEN_ONLINE = 1, /* Target online */ + BFA_ITNIM_AEN_OFFLINE = 2, /* Target offline */ + BFA_ITNIM_AEN_DISCONNECT = 3, /* Target disconnected */ +}; + +/** + * BFA ITNIM event data structure. + */ +struct bfa_itnim_aen_data_s { + u16 vf_id; /* vf_id of the IT nexus */ + u16 rsvd[3]; + wwn_t ppwwn; /* WWN of its physical port */ + wwn_t lpwwn; /* WWN of logical port */ + wwn_t rpwwn; /* WWN of remote(target) port */ +}; + +#endif /* __BFA_DEFS_ITNIM_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_led.h b/drivers/scsi/bfa/include/defs/bfa_defs_led.h new file mode 100644 index 000000000000..62039273264e --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_led.h @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_LED_H__ +#define __BFA_DEFS_LED_H__ + +#define BFA_LED_MAX_NUM 3 + +enum bfa_led_op { + BFA_LED_OFF = 0, + BFA_LED_ON = 1, + BFA_LED_FLICK = 2, + BFA_LED_BLINK = 3, +}; + +enum bfa_led_color { + BFA_LED_GREEN = 0, + BFA_LED_AMBER = 1, +}; + +#endif /* __BFA_DEFS_LED_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_lport.h b/drivers/scsi/bfa/include/defs/bfa_defs_lport.h new file mode 100644 index 000000000000..7359f82aacfc --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_lport.h @@ -0,0 +1,68 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_LPORT_H__ +#define __BFA_DEFS_LPORT_H__ + +#include <defs/bfa_defs_types.h> +#include <defs/bfa_defs_port.h> + +/** + * BFA AEN logical port events. + * Arguments below are in BFAL context from Mgmt + * BFA_LPORT_AEN_NEW: [in]: None [out]: vf_id, ppwwn, lpwwn, roles + * BFA_LPORT_AEN_DELETE: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_ONLINE: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_OFFLINE: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_DISCONNECT:[in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_NEW_PROP: [in]: None [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_DELETE_PROP: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_NEW_STANDARD: [in]: None [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_DELETE_STANDARD: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_NPIV_DUP_WWN: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_NPIV_FABRIC_MAX: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + * BFA_LPORT_AEN_NPIV_UNKNOWN: [in]: lpwwn [out]: vf_id, ppwwn. lpwwn, roles + */ +enum bfa_lport_aen_event { + BFA_LPORT_AEN_NEW = 1, /* LPort created event */ + BFA_LPORT_AEN_DELETE = 2, /* LPort deleted event */ + BFA_LPORT_AEN_ONLINE = 3, /* LPort online event */ + BFA_LPORT_AEN_OFFLINE = 4, /* LPort offline event */ + BFA_LPORT_AEN_DISCONNECT = 5, /* LPort disconnect event */ + BFA_LPORT_AEN_NEW_PROP = 6, /* VPort created event */ + BFA_LPORT_AEN_DELETE_PROP = 7, /* VPort deleted event */ + BFA_LPORT_AEN_NEW_STANDARD = 8, /* VPort created event */ + BFA_LPORT_AEN_DELETE_STANDARD = 9, /* VPort deleted event */ + BFA_LPORT_AEN_NPIV_DUP_WWN = 10, /* VPort configured with + * duplicate WWN event + */ + BFA_LPORT_AEN_NPIV_FABRIC_MAX = 11, /* Max NPIV in fabric/fport */ + BFA_LPORT_AEN_NPIV_UNKNOWN = 12, /* Unknown NPIV Error code event */ +}; + +/** + * BFA AEN event data structure + */ +struct bfa_lport_aen_data_s { + u16 vf_id; /* vf_id of this logical port */ + u16 rsvd; + enum bfa_port_role roles; /* Logical port mode,IM/TM/IP etc */ + wwn_t ppwwn; /* WWN of its physical port */ + wwn_t lpwwn; /* WWN of this logical port */ +}; + +#endif /* __BFA_DEFS_LPORT_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_mfg.h b/drivers/scsi/bfa/include/defs/bfa_defs_mfg.h new file mode 100644 index 000000000000..13fd4ab6aae2 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_mfg.h @@ -0,0 +1,58 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_MFG_H__ +#define __BFA_DEFS_MFG_H__ + +#include <bfa_os_inc.h> + +/** + * Manufacturing block version + */ +#define BFA_MFG_VERSION 1 + +/** + * Manufacturing block format + */ +#define BFA_MFG_SERIALNUM_SIZE 11 +#define BFA_MFG_PARTNUM_SIZE 14 +#define BFA_MFG_SUPPLIER_ID_SIZE 10 +#define BFA_MFG_SUPPLIER_PARTNUM_SIZE 20 +#define BFA_MFG_SUPPLIER_SERIALNUM_SIZE 20 +#define BFA_MFG_SUPPLIER_REVISION_SIZE 4 +#define STRSZ(_n) (((_n) + 4) & ~3) + +/** + * VPD data length + */ +#define BFA_MFG_VPD_LEN 256 + +/** + * All numerical fields are in big-endian format. + */ +struct bfa_mfg_vpd_s { + u8 version; /* vpd data version */ + u8 vpd_sig[3]; /* characters 'V', 'P', 'D' */ + u8 chksum; /* u8 checksum */ + u8 vendor; /* vendor */ + u8 len; /* vpd data length excluding header */ + u8 rsv; + u8 data[BFA_MFG_VPD_LEN]; /* vpd data */ +}; + +#pragma pack(1) + +#endif /* __BFA_DEFS_MFG_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_pci.h b/drivers/scsi/bfa/include/defs/bfa_defs_pci.h new file mode 100644 index 000000000000..c9b83321694b --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_pci.h @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_PCI_H__ +#define __BFA_DEFS_PCI_H__ + +/** + * PCI device and vendor ID information + */ +enum { + BFA_PCI_VENDOR_ID_BROCADE = 0x1657, + BFA_PCI_DEVICE_ID_FC_8G2P = 0x13, + BFA_PCI_DEVICE_ID_FC_8G1P = 0x17, + BFA_PCI_DEVICE_ID_CT = 0x14, +}; + +/** + * PCI sub-system device and vendor ID information + */ +enum { + BFA_PCI_FCOE_SSDEVICE_ID = 0x14, +}; + +#define BFA_PCI_ACCESS_RANGES 1 /* Maximum number of device address ranges + * mapped through different BAR(s). */ + +#endif /* __BFA_DEFS_PCI_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_pm.h b/drivers/scsi/bfa/include/defs/bfa_defs_pm.h new file mode 100644 index 000000000000..e8d6d959006e --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_pm.h @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_PM_H__ +#define __BFA_DEFS_PM_H__ + +#include <bfa_os_inc.h> + +/** + * BFA power management device states + */ +enum bfa_pm_ds { + BFA_PM_DS_D0 = 0, /* full power mode */ + BFA_PM_DS_D1 = 1, /* power save state 1 */ + BFA_PM_DS_D2 = 2, /* power save state 2 */ + BFA_PM_DS_D3 = 3, /* power off state */ +}; + +#endif /* __BFA_DEFS_PM_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_pom.h b/drivers/scsi/bfa/include/defs/bfa_defs_pom.h new file mode 100644 index 000000000000..d9fa278472b7 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_pom.h @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_POM_H__ +#define __BFA_DEFS_POM_H__ + +#include <bfa_os_inc.h> +#include <defs/bfa_defs_types.h> + +/** + * POM health status levels for each attributes. + */ +enum bfa_pom_entry_health { + BFA_POM_HEALTH_NOINFO = 1, /* no information */ + BFA_POM_HEALTH_NORMAL = 2, /* health is normal */ + BFA_POM_HEALTH_WARNING = 3, /* warning level */ + BFA_POM_HEALTH_ALARM = 4, /* alarming level */ +}; + +/** + * Reading of temperature/voltage/current/power + */ +struct bfa_pom_entry_s { + enum bfa_pom_entry_health health; /* POM entry health */ + u32 curr_value; /* current value */ + u32 thr_warn_high; /* threshold warning high */ + u32 thr_warn_low; /* threshold warning low */ + u32 thr_alarm_low; /* threshold alaram low */ + u32 thr_alarm_high; /* threshold alarm high */ +}; + +/** + * POM attributes + */ +struct bfa_pom_attr_s { + struct bfa_pom_entry_s temperature; /* centigrade */ + struct bfa_pom_entry_s voltage; /* volts */ + struct bfa_pom_entry_s curr; /* milli amps */ + struct bfa_pom_entry_s txpower; /* micro watts */ + struct bfa_pom_entry_s rxpower; /* micro watts */ +}; + +#endif /* __BFA_DEFS_POM_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_port.h b/drivers/scsi/bfa/include/defs/bfa_defs_port.h new file mode 100644 index 000000000000..de0696c81bc4 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_port.h @@ -0,0 +1,245 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_PORT_H__ +#define __BFA_DEFS_PORT_H__ + +#include <bfa_os_inc.h> +#include <protocol/types.h> +#include <defs/bfa_defs_pport.h> +#include <defs/bfa_defs_ioc.h> + +#define BFA_FCS_FABRIC_IPADDR_SZ 16 + +/** + * symbolic names for base port/virtual port + */ +#define BFA_SYMNAME_MAXLEN 128 /* vmware/windows uses 128 bytes */ +struct bfa_port_symname_s { + char symname[BFA_SYMNAME_MAXLEN]; +}; + +/** +* Roles of FCS port: + * - FCP IM and FCP TM roles cannot be enabled together for a FCS port + * - Create multiple ports if both IM and TM functions required. + * - Atleast one role must be specified. + */ +enum bfa_port_role { + BFA_PORT_ROLE_FCP_IM = 0x01, /* FCP initiator role */ + BFA_PORT_ROLE_FCP_TM = 0x02, /* FCP target role */ + BFA_PORT_ROLE_FCP_IPFC = 0x04, /* IP over FC role */ + BFA_PORT_ROLE_FCP_MAX = BFA_PORT_ROLE_FCP_IPFC | BFA_PORT_ROLE_FCP_IM +}; + +/** + * FCS port configuration. + */ +struct bfa_port_cfg_s { + wwn_t pwwn; /* port wwn */ + wwn_t nwwn; /* node wwn */ + struct bfa_port_symname_s sym_name; /* vm port symbolic name */ + enum bfa_port_role roles; /* FCS port roles */ + u32 rsvd; + u8 tag[16]; /* opaque tag from application */ +}; + +/** + * FCS port states + */ +enum bfa_port_state { + BFA_PORT_UNINIT = 0, /* PORT is not yet initialized */ + BFA_PORT_FDISC = 1, /* FDISC is in progress */ + BFA_PORT_ONLINE = 2, /* login to fabric is complete */ + BFA_PORT_OFFLINE = 3, /* No login to fabric */ +}; + +/** + * FCS port type. Required for VmWare. + */ +enum bfa_port_type { + BFA_PORT_TYPE_PHYSICAL = 0, + BFA_PORT_TYPE_VIRTUAL, +}; + +/** + * FCS port offline reason. Required for VmWare. + */ +enum bfa_port_offline_reason { + BFA_PORT_OFFLINE_UNKNOWN = 0, + BFA_PORT_OFFLINE_LINKDOWN, + BFA_PORT_OFFLINE_FAB_UNSUPPORTED, /* NPIV not supported by the + * fabric */ + BFA_PORT_OFFLINE_FAB_NORESOURCES, + BFA_PORT_OFFLINE_FAB_LOGOUT, +}; + +/** + * FCS lport info. Required for VmWare. + */ +struct bfa_port_info_s { + u8 port_type; /* bfa_port_type_t : physical or + * virtual */ + u8 port_state; /* one of bfa_port_state values */ + u8 offline_reason; /* one of bfa_port_offline_reason_t + * values */ + wwn_t port_wwn; + wwn_t node_wwn; + + /* + * following 4 feilds are valid for Physical Ports only + */ + u32 max_vports_supp; /* Max supported vports */ + u32 num_vports_inuse; /* Num of in use vports */ + u32 max_rports_supp; /* Max supported rports */ + u32 num_rports_inuse; /* Num of doscovered rports */ + +}; + +/** + * FCS port statistics + */ +struct bfa_port_stats_s { + u32 ns_plogi_sent; + u32 ns_plogi_rsp_err; + u32 ns_plogi_acc_err; + u32 ns_plogi_accepts; + u32 ns_rejects; /* NS command rejects */ + u32 ns_plogi_unknown_rsp; + u32 ns_plogi_alloc_wait; + + u32 ns_retries; /* NS command retries */ + u32 ns_timeouts; /* NS command timeouts */ + + u32 ns_rspnid_sent; + u32 ns_rspnid_accepts; + u32 ns_rspnid_rsp_err; + u32 ns_rspnid_rejects; + u32 ns_rspnid_alloc_wait; + + u32 ns_rftid_sent; + u32 ns_rftid_accepts; + u32 ns_rftid_rsp_err; + u32 ns_rftid_rejects; + u32 ns_rftid_alloc_wait; + + u32 ns_rffid_sent; + u32 ns_rffid_accepts; + u32 ns_rffid_rsp_err; + u32 ns_rffid_rejects; + u32 ns_rffid_alloc_wait; + + u32 ns_gidft_sent; + u32 ns_gidft_accepts; + u32 ns_gidft_rsp_err; + u32 ns_gidft_rejects; + u32 ns_gidft_unknown_rsp; + u32 ns_gidft_alloc_wait; + + /* + * Mgmt Server stats + */ + u32 ms_retries; /* MS command retries */ + u32 ms_timeouts; /* MS command timeouts */ + u32 ms_plogi_sent; + u32 ms_plogi_rsp_err; + u32 ms_plogi_acc_err; + u32 ms_plogi_accepts; + u32 ms_rejects; /* NS command rejects */ + u32 ms_plogi_unknown_rsp; + u32 ms_plogi_alloc_wait; + + u32 num_rscn; /* Num of RSCN received */ + u32 num_portid_rscn;/* Num portid format RSCN + * received */ + + u32 uf_recvs; /* unsolicited recv frames */ + u32 uf_recv_drops; /* dropped received frames */ + + u32 rsvd; /* padding for 64 bit alignment */ +}; + +/** + * BFA port attribute returned in queries + */ +struct bfa_port_attr_s { + enum bfa_port_state state; /* port state */ + u32 pid; /* port ID */ + struct bfa_port_cfg_s port_cfg; /* port configuration */ + enum bfa_pport_type port_type; /* current topology */ + u32 loopback; /* cable is externally looped back */ + wwn_t fabric_name; /* attached switch's nwwn */ + u8 fabric_ip_addr[BFA_FCS_FABRIC_IPADDR_SZ]; /* attached + * fabric's ip addr */ +}; + +/** + * BFA physical port Level events + * Arguments below are in BFAL context from Mgmt + * BFA_PORT_AEN_ONLINE: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_OFFLINE: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_RLIR: [in]: None [out]: pwwn, rlir_data, rlir_len + * BFA_PORT_AEN_SFP_INSERT: [in]: pwwn [out]: port_id, pwwn + * BFA_PORT_AEN_SFP_REMOVE: [in]: pwwn [out]: port_id, pwwn + * BFA_PORT_AEN_SFP_POM: [in]: pwwn [out]: level, port_id, pwwn + * BFA_PORT_AEN_ENABLE: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_DISABLE: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_AUTH_ON: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_AUTH_OFF: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_DISCONNECT: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_QOS_NEG: [in]: pwwn [out]: pwwn + * BFA_PORT_AEN_FABRIC_NAME_CHANGE: [in]: pwwn, [out]: pwwn, fwwn + * + */ +enum bfa_port_aen_event { + BFA_PORT_AEN_ONLINE = 1, /* Physical Port online event */ + BFA_PORT_AEN_OFFLINE = 2, /* Physical Port offline event */ + BFA_PORT_AEN_RLIR = 3, /* RLIR event, not supported */ + BFA_PORT_AEN_SFP_INSERT = 4, /* SFP inserted event */ + BFA_PORT_AEN_SFP_REMOVE = 5, /* SFP removed event */ + BFA_PORT_AEN_SFP_POM = 6, /* SFP POM event */ + BFA_PORT_AEN_ENABLE = 7, /* Physical Port enable event */ + BFA_PORT_AEN_DISABLE = 8, /* Physical Port disable event */ + BFA_PORT_AEN_AUTH_ON = 9, /* Physical Port auth success event */ + BFA_PORT_AEN_AUTH_OFF = 10, /* Physical Port auth fail event */ + BFA_PORT_AEN_DISCONNECT = 11, /* Physical Port disconnect event */ + BFA_PORT_AEN_QOS_NEG = 12, /* Base Port QOS negotiation event */ + BFA_PORT_AEN_FABRIC_NAME_CHANGE = 13, /* Fabric Name/WWN change + * event */ + BFA_PORT_AEN_SFP_ACCESS_ERROR = 14, /* SFP read error event */ + BFA_PORT_AEN_SFP_UNSUPPORT = 15, /* Unsupported SFP event */ +}; + +enum bfa_port_aen_sfp_pom { + BFA_PORT_AEN_SFP_POM_GREEN = 1, /* Normal */ + BFA_PORT_AEN_SFP_POM_AMBER = 2, /* Warning */ + BFA_PORT_AEN_SFP_POM_RED = 3, /* Critical */ + BFA_PORT_AEN_SFP_POM_MAX = BFA_PORT_AEN_SFP_POM_RED +}; + +struct bfa_port_aen_data_s { + enum bfa_ioc_type_e ioc_type; + wwn_t pwwn; /* WWN of the physical port */ + wwn_t fwwn; /* WWN of the fabric port */ + mac_t mac; /* MAC addres of the ethernet port, + * applicable to CNA port only */ + int phy_port_num; /*! For SFP related events */ + enum bfa_port_aen_sfp_pom level; /* Only transitions will + * be informed */ +}; + +#endif /* __BFA_DEFS_PORT_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_pport.h b/drivers/scsi/bfa/include/defs/bfa_defs_pport.h new file mode 100644 index 000000000000..a000bc4e2d4a --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_pport.h @@ -0,0 +1,383 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_PPORT_H__ +#define __BFA_DEFS_PPORT_H__ + +#include <bfa_os_inc.h> +#include <protocol/fc.h> +#include <defs/bfa_defs_types.h> +#include <defs/bfa_defs_qos.h> +#include <cna/pstats/phyport_defs.h> + +/* Modify char* port_stt[] in bfal_port.c if a new state was added */ +enum bfa_pport_states { + BFA_PPORT_ST_UNINIT = 1, + BFA_PPORT_ST_ENABLING_QWAIT = 2, + BFA_PPORT_ST_ENABLING = 3, + BFA_PPORT_ST_LINKDOWN = 4, + BFA_PPORT_ST_LINKUP = 5, + BFA_PPORT_ST_DISABLING_QWAIT = 6, + BFA_PPORT_ST_DISABLING = 7, + BFA_PPORT_ST_DISABLED = 8, + BFA_PPORT_ST_STOPPED = 9, + BFA_PPORT_ST_IOCDOWN = 10, + BFA_PPORT_ST_IOCDIS = 11, + BFA_PPORT_ST_FWMISMATCH = 12, + BFA_PPORT_ST_MAX_STATE, +}; + +/** + * Port speed settings. Each specific speed is a bit field. Use multiple + * bits to specify speeds to be selected for auto-negotiation. + */ +enum bfa_pport_speed { + BFA_PPORT_SPEED_UNKNOWN = 0, + BFA_PPORT_SPEED_1GBPS = 1, + BFA_PPORT_SPEED_2GBPS = 2, + BFA_PPORT_SPEED_4GBPS = 4, + BFA_PPORT_SPEED_8GBPS = 8, + BFA_PPORT_SPEED_10GBPS = 10, + BFA_PPORT_SPEED_AUTO = + (BFA_PPORT_SPEED_1GBPS | BFA_PPORT_SPEED_2GBPS | + BFA_PPORT_SPEED_4GBPS | BFA_PPORT_SPEED_8GBPS), +}; + +/** + * Port operational type (in sync with SNIA port type). + */ +enum bfa_pport_type { + BFA_PPORT_TYPE_UNKNOWN = 1, /* port type is unkown */ + BFA_PPORT_TYPE_TRUNKED = 2, /* Trunked mode */ + BFA_PPORT_TYPE_NPORT = 5, /* P2P with switched fabric */ + BFA_PPORT_TYPE_NLPORT = 6, /* public loop */ + BFA_PPORT_TYPE_LPORT = 20, /* private loop */ + BFA_PPORT_TYPE_P2P = 21, /* P2P with no switched fabric */ + BFA_PPORT_TYPE_VPORT = 22, /* NPIV - virtual port */ +}; + +/** + * Port topology setting. A port's topology and fabric login status + * determine its operational type. + */ +enum bfa_pport_topology { + BFA_PPORT_TOPOLOGY_NONE = 0, /* No valid topology */ + BFA_PPORT_TOPOLOGY_P2P = 1, /* P2P only */ + BFA_PPORT_TOPOLOGY_LOOP = 2, /* LOOP topology */ + BFA_PPORT_TOPOLOGY_AUTO = 3, /* auto topology selection */ +}; + +/** + * Physical port loopback types. + */ +enum bfa_pport_opmode { + BFA_PPORT_OPMODE_NORMAL = 0x00, /* normal non-loopback mode */ + BFA_PPORT_OPMODE_LB_INT = 0x01, /* internal loop back */ + BFA_PPORT_OPMODE_LB_SLW = 0x02, /* serial link wrapback (serdes) */ + BFA_PPORT_OPMODE_LB_EXT = 0x04, /* external loop back (serdes) */ + BFA_PPORT_OPMODE_LB_CBL = 0x08, /* cabled loop back */ + BFA_PPORT_OPMODE_LB_NLINT = 0x20, /* NL_Port internal loopback */ +}; + +#define BFA_PPORT_OPMODE_LB_HARD(_mode) \ + ((_mode == BFA_PPORT_OPMODE_LB_INT) || \ + (_mode == BFA_PPORT_OPMODE_LB_SLW) || \ + (_mode == BFA_PPORT_OPMODE_LB_EXT)) + +/** + Port State (in sync with SNIA port state). + */ +enum bfa_pport_snia_state { + BFA_PPORT_STATE_UNKNOWN = 1, /* port is not initialized */ + BFA_PPORT_STATE_ONLINE = 2, /* port is ONLINE */ + BFA_PPORT_STATE_DISABLED = 3, /* port is disabled by user */ + BFA_PPORT_STATE_BYPASSED = 4, /* port is bypassed (in LOOP) */ + BFA_PPORT_STATE_DIAG = 5, /* port diagnostics is active */ + BFA_PPORT_STATE_LINKDOWN = 6, /* link is down */ + BFA_PPORT_STATE_LOOPBACK = 8, /* port is looped back */ +}; + +/** + * Port link state + */ +enum bfa_pport_linkstate { + BFA_PPORT_LINKUP = 1, /* Physical port/Trunk link up */ + BFA_PPORT_LINKDOWN = 2, /* Physical port/Trunk link down */ + BFA_PPORT_TRUNK_LINKDOWN = 3, /* Trunk link down (new tmaster) */ +}; + +/** + * Port link state event + */ +#define bfa_pport_event_t enum bfa_pport_linkstate + +/** + * Port link state reason code + */ +enum bfa_pport_linkstate_rsn { + BFA_PPORT_LINKSTATE_RSN_NONE = 0, + BFA_PPORT_LINKSTATE_RSN_DISABLED = 1, + BFA_PPORT_LINKSTATE_RSN_RX_NOS = 2, + BFA_PPORT_LINKSTATE_RSN_RX_OLS = 3, + BFA_PPORT_LINKSTATE_RSN_RX_LIP = 4, + BFA_PPORT_LINKSTATE_RSN_RX_LIPF7 = 5, + BFA_PPORT_LINKSTATE_RSN_SFP_REMOVED = 6, + BFA_PPORT_LINKSTATE_RSN_PORT_FAULT = 7, + BFA_PPORT_LINKSTATE_RSN_RX_LOS = 8, + BFA_PPORT_LINKSTATE_RSN_LOCAL_FAULT = 9, + BFA_PPORT_LINKSTATE_RSN_REMOTE_FAULT = 10, + BFA_PPORT_LINKSTATE_RSN_TIMEOUT = 11, + + + + /* CEE related reason codes/errors */ + CEE_LLDP_INFO_AGED_OUT = 20, + CEE_LLDP_SHUTDOWN_TLV_RCVD = 21, + CEE_PEER_NOT_ADVERTISE_DCBX = 22, + CEE_PEER_NOT_ADVERTISE_PG = 23, + CEE_PEER_NOT_ADVERTISE_PFC = 24, + CEE_PEER_NOT_ADVERTISE_FCOE = 25, + CEE_PG_NOT_COMPATIBLE = 26, + CEE_PFC_NOT_COMPATIBLE = 27, + CEE_FCOE_NOT_COMPATIBLE = 28, + CEE_BAD_PG_RCVD = 29, + CEE_BAD_BW_RCVD = 30, + CEE_BAD_PFC_RCVD = 31, + CEE_BAD_FCOE_PRI_RCVD = 32, + CEE_FCOE_PRI_PFC_OFF = 33, + CEE_DUP_CONTROL_TLV_RCVD = 34, + CEE_DUP_FEAT_TLV_RCVD = 35, + CEE_APPLY_NEW_CFG = 36, /* reason, not an error */ + CEE_PROTOCOL_INIT = 37, /* reason, not an error */ + CEE_PHY_LINK_DOWN = 38, + CEE_LLS_FCOE_ABSENT = 39, + CEE_LLS_FCOE_DOWN = 40 +}; + +/** + * Default Target Rate Limiting Speed. + */ +#define BFA_PPORT_DEF_TRL_SPEED BFA_PPORT_SPEED_1GBPS + +/** + * Physical port configuration + */ +struct bfa_pport_cfg_s { + u8 topology; /* bfa_pport_topology */ + u8 speed; /* enum bfa_pport_speed */ + u8 trunked; /* trunked or not */ + u8 qos_enabled; /* qos enabled or not */ + u8 trunk_ports; /* bitmap of trunked ports */ + u8 cfg_hardalpa; /* is hard alpa configured */ + u16 maxfrsize; /* maximum frame size */ + u8 hardalpa; /* configured hard alpa */ + u8 rx_bbcredit; /* receive buffer credits */ + u8 tx_bbcredit; /* transmit buffer credits */ + u8 ratelimit; /* ratelimit enabled or not */ + u8 trl_def_speed; /* ratelimit default speed */ + u8 rsvd[3]; + u16 path_tov; /* device path timeout */ + u16 q_depth; /* SCSI Queue depth */ +}; + +/** + * Port attribute values. + */ +struct bfa_pport_attr_s { + /* + * Static fields + */ + wwn_t nwwn; /* node wwn */ + wwn_t pwwn; /* port wwn */ + enum fc_cos cos_supported; /* supported class of services */ + u32 rsvd; + struct fc_symname_s port_symname; /* port symbolic name */ + enum bfa_pport_speed speed_supported; /* supported speeds */ + bfa_boolean_t pbind_enabled; /* Will be set if Persistent binding + * enabled. Relevant only in Windows + */ + + /* + * Configured values + */ + struct bfa_pport_cfg_s pport_cfg; /* pport cfg */ + + /* + * Dynamic field - info from BFA + */ + enum bfa_pport_states port_state; /* current port state */ + enum bfa_pport_speed speed; /* current speed */ + enum bfa_pport_topology topology; /* current topology */ + bfa_boolean_t beacon; /* current beacon status */ + bfa_boolean_t link_e2e_beacon;/* set if link beacon on */ + bfa_boolean_t plog_enabled; /* set if portlog is enabled*/ + + /* + * Dynamic field - info from FCS + */ + u32 pid; /* port ID */ + enum bfa_pport_type port_type; /* current topology */ + u32 loopback; /* external loopback */ + u32 rsvd1; + u32 rsvd2; /* padding for 64 bit */ +}; + +/** + * FC Port statistics. + */ +struct bfa_pport_fc_stats_s { + u64 secs_reset; /* seconds since stats is reset */ + u64 tx_frames; /* transmitted frames */ + u64 tx_words; /* transmitted words */ + u64 rx_frames; /* received frames */ + u64 rx_words; /* received words */ + u64 lip_count; /* LIPs seen */ + u64 nos_count; /* NOS count */ + u64 error_frames; /* errored frames (sent?) */ + u64 dropped_frames; /* dropped frames */ + u64 link_failures; /* link failure count */ + u64 loss_of_syncs; /* loss of sync count */ + u64 loss_of_signals;/* loss of signal count */ + u64 primseq_errs; /* primitive sequence protocol */ + u64 bad_os_count; /* invalid ordered set */ + u64 err_enc_out; /* Encoding error outside frame */ + u64 invalid_crcs; /* frames received with invalid CRC*/ + u64 undersized_frm; /* undersized frames */ + u64 oversized_frm; /* oversized frames */ + u64 bad_eof_frm; /* frames with bad EOF */ + struct bfa_qos_stats_s qos_stats; /* QoS statistics */ +}; + +/** + * Eth Port statistics. + */ +struct bfa_pport_eth_stats_s { + u64 secs_reset; /* seconds since stats is reset */ + u64 frame_64; /* both rx and tx counter */ + u64 frame_65_127; /* both rx and tx counter */ + u64 frame_128_255; /* both rx and tx counter */ + u64 frame_256_511; /* both rx and tx counter */ + u64 frame_512_1023; /* both rx and tx counter */ + u64 frame_1024_1518; /* both rx and tx counter */ + u64 frame_1519_1522; /* both rx and tx counter */ + + u64 tx_bytes; + u64 tx_packets; + u64 tx_mcast_packets; + u64 tx_bcast_packets; + u64 tx_control_frame; + u64 tx_drop; + u64 tx_jabber; + u64 tx_fcs_error; + u64 tx_fragments; + + u64 rx_bytes; + u64 rx_packets; + u64 rx_mcast_packets; + u64 rx_bcast_packets; + u64 rx_control_frames; + u64 rx_unknown_opcode; + u64 rx_drop; + u64 rx_jabber; + u64 rx_fcs_error; + u64 rx_alignment_error; + u64 rx_frame_length_error; + u64 rx_code_error; + u64 rx_fragments; + + u64 rx_pause; /* BPC */ + u64 rx_zero_pause; /* BPC Pause cancellation */ + u64 tx_pause; /* BPC */ + u64 tx_zero_pause; /* BPC Pause cancellation */ + u64 rx_fcoe_pause; /* BPC */ + u64 rx_fcoe_zero_pause; /* BPC Pause cancellation */ + u64 tx_fcoe_pause; /* BPC */ + u64 tx_fcoe_zero_pause; /* BPC Pause cancellation */ +}; + +/** + * Port statistics. + */ +union bfa_pport_stats_u { + struct bfa_pport_fc_stats_s fc; + struct bfa_pport_eth_stats_s eth; +}; + +/** + * Port FCP mappings. + */ +struct bfa_pport_fcpmap_s { + char osdevname[256]; + u32 bus; + u32 target; + u32 oslun; + u32 fcid; + wwn_t nwwn; + wwn_t pwwn; + u64 fcplun; + char luid[256]; +}; + +/** + * Port RNID info. + */ +struct bfa_pport_rnid_s { + wwn_t wwn; + u32 unittype; + u32 portid; + u32 attached_nodes_num; + u16 ip_version; + u16 udp_port; + u8 ipaddr[16]; + u16 rsvd; + u16 topologydiscoveryflags; +}; + +/** + * Link state information + */ +struct bfa_pport_link_s { + u8 linkstate; /* Link state bfa_pport_linkstate */ + u8 linkstate_rsn; /* bfa_pport_linkstate_rsn_t */ + u8 topology; /* P2P/LOOP bfa_pport_topology */ + u8 speed; /* Link speed (1/2/4/8 G) */ + u32 linkstate_opt; /* Linkstate optional data (debug) */ + u8 trunked; /* Trunked or not (1 or 0) */ + u8 resvd[3]; + struct bfa_qos_attr_s qos_attr; /* QoS Attributes */ + struct bfa_qos_vc_attr_s qos_vc_attr; /* VC info from ELP */ + union { + struct { + u8 tmaster;/* Trunk Master or + * not (1 or 0) */ + u8 tlinks; /* Trunk links bitmap + * (linkup) */ + u8 resv1; /* Reserved */ + } trunk_info; + + struct { + u8 myalpa; /* alpa claimed */ + u8 login_req; /* Login required or + * not (1 or 0) */ + u8 alpabm_val;/* alpa bitmap valid + * or not (1 or 0) */ + struct fc_alpabm_s alpabm; /* alpa bitmap */ + } loop_info; + } tl; +}; + +#endif /* __BFA_DEFS_PPORT_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_qos.h b/drivers/scsi/bfa/include/defs/bfa_defs_qos.h new file mode 100644 index 000000000000..aadbacd1d2d7 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_qos.h @@ -0,0 +1,99 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_QOS_H__ +#define __BFA_DEFS_QOS_H__ + +/** + * QoS states + */ +enum bfa_qos_state { + BFA_QOS_ONLINE = 1, /* QoS is online */ + BFA_QOS_OFFLINE = 2, /* QoS is offline */ +}; + + +/** + * QoS Priority levels. + */ +enum bfa_qos_priority { + BFA_QOS_UNKNOWN = 0, + BFA_QOS_HIGH = 1, /* QoS Priority Level High */ + BFA_QOS_MED = 2, /* QoS Priority Level Medium */ + BFA_QOS_LOW = 3, /* QoS Priority Level Low */ +}; + + +/** + * QoS bandwidth allocation for each priority level + */ +enum bfa_qos_bw_alloc { + BFA_QOS_BW_HIGH = 60, /* bandwidth allocation for High */ + BFA_QOS_BW_MED = 30, /* bandwidth allocation for Medium */ + BFA_QOS_BW_LOW = 10, /* bandwidth allocation for Low */ +}; + +/** + * QoS attribute returned in QoS Query + */ +struct bfa_qos_attr_s { + enum bfa_qos_state state; /* QoS current state */ + u32 total_bb_cr; /* Total BB Credits */ +}; + +/** + * These fields should be displayed only from the CLI. + * There will be a separate BFAL API (get_qos_vc_attr ?) + * to retrieve this. + * + */ +#define BFA_QOS_MAX_VC 16 + +struct bfa_qos_vc_info_s { + u8 vc_credit; + u8 borrow_credit; + u8 priority; + u8 resvd; +}; + +struct bfa_qos_vc_attr_s { + u16 total_vc_count; /* Total VC Count */ + u16 shared_credit; + u32 elp_opmode_flags; + struct bfa_qos_vc_info_s vc_info[BFA_QOS_MAX_VC]; /* as many as + * total_vc_count */ +}; + +/** + * QoS statistics + */ +struct bfa_qos_stats_s { + u32 flogi_sent; /* QoS Flogi sent */ + u32 flogi_acc_recvd; /* QoS Flogi Acc received */ + u32 flogi_rjt_recvd; /* QoS Flogi rejects received */ + u32 flogi_retries; /* QoS Flogi retries */ + + u32 elp_recvd; /* QoS ELP received */ + u32 elp_accepted; /* QoS ELP Accepted */ + u32 elp_rejected; /* QoS ELP rejected */ + u32 elp_dropped; /* QoS ELP dropped */ + + u32 qos_rscn_recvd; /* QoS RSCN received */ + u32 rsvd; /* padding for 64 bit alignment */ +}; + +#endif /* __BFA_DEFS_QOS_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_rport.h b/drivers/scsi/bfa/include/defs/bfa_defs_rport.h new file mode 100644 index 000000000000..e0af59d6d2f6 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_rport.h @@ -0,0 +1,199 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_RPORT_H__ +#define __BFA_DEFS_RPORT_H__ + +#include <bfa_os_inc.h> +#include <protocol/types.h> +#include <defs/bfa_defs_pport.h> +#include <defs/bfa_defs_port.h> +#include <defs/bfa_defs_qos.h> + +/** + * FCS remote port states + */ +enum bfa_rport_state { + BFA_RPORT_UNINIT = 0, /* PORT is not yet initialized */ + BFA_RPORT_OFFLINE = 1, /* rport is offline */ + BFA_RPORT_PLOGI = 2, /* PLOGI to rport is in progress */ + BFA_RPORT_ONLINE = 3, /* login to rport is complete */ + BFA_RPORT_PLOGI_RETRY = 4, /* retrying login to rport */ + BFA_RPORT_NSQUERY = 5, /* nameserver query */ + BFA_RPORT_ADISC = 6, /* ADISC authentication */ + BFA_RPORT_LOGO = 7, /* logging out with rport */ + BFA_RPORT_LOGORCV = 8, /* handling LOGO from rport */ + BFA_RPORT_NSDISC = 9, /* re-discover rport */ +}; + +/** + * Rport Scsi Function : Initiator/Target. + */ +enum bfa_rport_function { + BFA_RPORT_INITIATOR = 0x01, /* SCSI Initiator */ + BFA_RPORT_TARGET = 0x02, /* SCSI Target */ +}; + +/** + * port/node symbolic names for rport + */ +#define BFA_RPORT_SYMNAME_MAXLEN 255 +struct bfa_rport_symname_s { + char symname[BFA_RPORT_SYMNAME_MAXLEN]; +}; + +struct bfa_rport_hal_stats_s { + u32 sm_un_cr; /* uninit: create events */ + u32 sm_un_unexp; /* uninit: exception events */ + u32 sm_cr_on; /* created: online events */ + u32 sm_cr_del; /* created: delete events */ + u32 sm_cr_hwf; /* created: IOC down */ + u32 sm_cr_unexp; /* created: exception events */ + u32 sm_fwc_rsp; /* fw create: f/w responses */ + u32 sm_fwc_del; /* fw create: delete events */ + u32 sm_fwc_off; /* fw create: offline events */ + u32 sm_fwc_hwf; /* fw create: IOC down */ + u32 sm_fwc_unexp; /* fw create: exception events*/ + u32 sm_on_off; /* online: offline events */ + u32 sm_on_del; /* online: delete events */ + u32 sm_on_hwf; /* online: IOC down events */ + u32 sm_on_unexp; /* online: exception events */ + u32 sm_fwd_rsp; /* fw delete: fw responses */ + u32 sm_fwd_del; /* fw delete: delete events */ + u32 sm_fwd_hwf; /* fw delete: IOC down events */ + u32 sm_fwd_unexp; /* fw delete: exception events*/ + u32 sm_off_del; /* offline: delete events */ + u32 sm_off_on; /* offline: online events */ + u32 sm_off_hwf; /* offline: IOC down events */ + u32 sm_off_unexp; /* offline: exception events */ + u32 sm_del_fwrsp; /* delete: fw responses */ + u32 sm_del_hwf; /* delete: IOC down events */ + u32 sm_del_unexp; /* delete: exception events */ + u32 sm_delp_fwrsp; /* delete pend: fw responses */ + u32 sm_delp_hwf; /* delete pend: IOC downs */ + u32 sm_delp_unexp; /* delete pend: exceptions */ + u32 sm_offp_fwrsp; /* off-pending: fw responses */ + u32 sm_offp_del; /* off-pending: deletes */ + u32 sm_offp_hwf; /* off-pending: IOC downs */ + u32 sm_offp_unexp; /* off-pending: exceptions */ + u32 sm_iocd_off; /* IOC down: offline events */ + u32 sm_iocd_del; /* IOC down: delete events */ + u32 sm_iocd_on; /* IOC down: online events */ + u32 sm_iocd_unexp; /* IOC down: exceptions */ + u32 rsvd; +}; + +/** + * FCS remote port statistics + */ +struct bfa_rport_stats_s { + u32 offlines; /* remote port offline count */ + u32 onlines; /* remote port online count */ + u32 rscns; /* RSCN affecting rport */ + u32 plogis; /* plogis sent */ + u32 plogi_accs; /* plogi accepts */ + u32 plogi_timeouts; /* plogi timeouts */ + u32 plogi_rejects; /* rcvd plogi rejects */ + u32 plogi_failed; /* local failure */ + u32 plogi_rcvd; /* plogis rcvd */ + u32 prli_rcvd; /* inbound PRLIs */ + u32 adisc_rcvd; /* ADISCs received */ + u32 adisc_rejects; /* recvd ADISC rejects */ + u32 adisc_sent; /* ADISC requests sent */ + u32 adisc_accs; /* ADISC accepted by rport */ + u32 adisc_failed; /* ADISC failed (no response) */ + u32 adisc_rejected; /* ADISC rejected by us */ + u32 logos; /* logos sent */ + u32 logo_accs; /* LOGO accepts from rport */ + u32 logo_failed; /* LOGO failures */ + u32 logo_rejected; /* LOGO rejects from rport */ + u32 logo_rcvd; /* LOGO from remote port */ + + u32 rpsc_rcvd; /* RPSC received */ + u32 rpsc_rejects; /* recvd RPSC rejects */ + u32 rpsc_sent; /* RPSC requests sent */ + u32 rpsc_accs; /* RPSC accepted by rport */ + u32 rpsc_failed; /* RPSC failed (no response) */ + u32 rpsc_rejected; /* RPSC rejected by us */ + + u32 rsvd; + struct bfa_rport_hal_stats_s hal_stats; /* BFA rport stats */ +}; + +/** + * Rport's QoS attributes + */ +struct bfa_rport_qos_attr_s { + enum bfa_qos_priority qos_priority; /* rport's QoS priority */ + u32 qos_flow_id; /* QoS flow Id */ +}; + +/** + * FCS remote port attributes returned in queries + */ +struct bfa_rport_attr_s { + wwn_t nwwn; /* node wwn */ + wwn_t pwwn; /* port wwn */ + enum fc_cos cos_supported; /* supported class of services */ + u32 pid; /* port ID */ + u32 df_sz; /* Max payload size */ + enum bfa_rport_state state; /* Rport State machine state */ + enum fc_cos fc_cos; /* FC classes of services */ + bfa_boolean_t cisc; /* CISC capable device */ + struct bfa_rport_symname_s symname; /* Symbolic Name */ + enum bfa_rport_function scsi_function; /* Initiator/Target */ + struct bfa_rport_qos_attr_s qos_attr; /* qos attributes */ + enum bfa_pport_speed curr_speed; /* operating speed got from + * RPSC ELS. UNKNOWN, if RPSC + * is not supported */ + bfa_boolean_t trl_enforced; /* TRL enforced ? TRUE/FALSE */ + enum bfa_pport_speed assigned_speed; /* Speed assigned by the user. + * will be used if RPSC is not + * supported by the rport */ +}; + +#define bfa_rport_aen_qos_data_t struct bfa_rport_qos_attr_s + +/** + * BFA remote port events + * Arguments below are in BFAL context from Mgmt + * BFA_RPORT_AEN_ONLINE: [in]: lpwwn [out]: vf_id, lpwwn, rpwwn + * BFA_RPORT_AEN_OFFLINE: [in]: lpwwn [out]: vf_id, lpwwn, rpwwn + * BFA_RPORT_AEN_DISCONNECT:[in]: lpwwn [out]: vf_id, lpwwn, rpwwn + * BFA_RPORT_AEN_QOS_PRIO: [in]: lpwwn [out]: vf_id, lpwwn, rpwwn, prio + * BFA_RPORT_AEN_QOS_FLOWID:[in]: lpwwn [out]: vf_id, lpwwn, rpwwn, flow_id + */ +enum bfa_rport_aen_event { + BFA_RPORT_AEN_ONLINE = 1, /* RPort online event */ + BFA_RPORT_AEN_OFFLINE = 2, /* RPort offline event */ + BFA_RPORT_AEN_DISCONNECT = 3, /* RPort disconnect event */ + BFA_RPORT_AEN_QOS_PRIO = 4, /* QOS priority change event */ + BFA_RPORT_AEN_QOS_FLOWID = 5, /* QOS flow Id change event */ +}; + +struct bfa_rport_aen_data_s { + u16 vf_id; /* vf_id of this logical port */ + u16 rsvd[3]; + wwn_t ppwwn; /* WWN of its physical port */ + wwn_t lpwwn; /* WWN of this logical port */ + wwn_t rpwwn; /* WWN of this remote port */ + union { + bfa_rport_aen_qos_data_t qos; + } priv; +}; + +#endif /* __BFA_DEFS_RPORT_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_status.h b/drivers/scsi/bfa/include/defs/bfa_defs_status.h new file mode 100644 index 000000000000..cdceaeb9f4b8 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_status.h @@ -0,0 +1,255 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_STATUS_H__ +#define __BFA_DEFS_STATUS_H__ + +/** + * API status return values + * + * NOTE: The error msgs are auto generated from the comments. Only singe line + * comments are supported + */ +enum bfa_status { + BFA_STATUS_OK = 0, /* Success */ + BFA_STATUS_FAILED = 1, /* Operation failed */ + BFA_STATUS_EINVAL = 2, /* Invalid params Check input + * parameters */ + BFA_STATUS_ENOMEM = 3, /* Out of resources */ + BFA_STATUS_ENOSYS = 4, /* Function not implemented */ + BFA_STATUS_ETIMER = 5, /* Timer expired - Retry, if + * persists, contact support */ + BFA_STATUS_EPROTOCOL = 6, /* Protocol error */ + BFA_STATUS_ENOFCPORTS = 7, /* No FC ports resources */ + BFA_STATUS_NOFLASH = 8, /* Flash not present */ + BFA_STATUS_BADFLASH = 9, /* Flash is corrupted or bad */ + BFA_STATUS_SFP_UNSUPP = 10, /* Unsupported SFP - Replace SFP */ + BFA_STATUS_UNKNOWN_VFID = 11, /* VF_ID not found */ + BFA_STATUS_DATACORRUPTED = 12, /* Diag returned data corrupted + * contact support */ + BFA_STATUS_DEVBUSY = 13, /* Device busy - Retry operation */ + BFA_STATUS_ABORTED = 14, /* Operation aborted */ + BFA_STATUS_NODEV = 15, /* Dev is not present */ + BFA_STATUS_HDMA_FAILED = 16, /* Host dma failed contact support */ + BFA_STATUS_FLASH_BAD_LEN = 17, /* Flash bad length */ + BFA_STATUS_UNKNOWN_LWWN = 18, /* LPORT PWWN not found */ + BFA_STATUS_UNKNOWN_RWWN = 19, /* RPORT PWWN not found */ + BFA_STATUS_FCPT_LS_RJT = 20, /* Got LS_RJT for FC Pass + * through Req */ + BFA_STATUS_VPORT_EXISTS = 21, /* VPORT already exists */ + BFA_STATUS_VPORT_MAX = 22, /* Reached max VPORT supported + * limit */ + BFA_STATUS_UNSUPP_SPEED = 23, /* Invalid Speed Check speed + * setting */ + BFA_STATUS_INVLD_DFSZ = 24, /* Invalid Max data field size */ + BFA_STATUS_CNFG_FAILED = 25, /* Setting can not be persisted */ + BFA_STATUS_CMD_NOTSUPP = 26, /* Command/API not supported */ + BFA_STATUS_NO_ADAPTER = 27, /* No Brocade Adapter Found */ + BFA_STATUS_LINKDOWN = 28, /* Link is down - Check or replace + * SFP/cable */ + BFA_STATUS_FABRIC_RJT = 29, /* Reject from attached fabric */ + BFA_STATUS_UNKNOWN_VWWN = 30, /* VPORT PWWN not found */ + BFA_STATUS_NSLOGIN_FAILED = 31, /* Nameserver login failed */ + BFA_STATUS_NO_RPORTS = 32, /* No remote ports found */ + BFA_STATUS_NSQUERY_FAILED = 33, /* Nameserver query failed */ + BFA_STATUS_PORT_OFFLINE = 34, /* Port is not online */ + BFA_STATUS_RPORT_OFFLINE = 35, /* RPORT is not online */ + BFA_STATUS_TGTOPEN_FAILED = 36, /* Remote SCSI target open failed */ + BFA_STATUS_BAD_LUNS = 37, /* No valid LUNs found */ + BFA_STATUS_IO_FAILURE = 38, /* SCSI target IO failure */ + BFA_STATUS_NO_FABRIC = 39, /* No switched fabric present */ + BFA_STATUS_EBADF = 40, /* Bad file descriptor */ + BFA_STATUS_EINTR = 41, /* A signal was caught during ioctl */ + BFA_STATUS_EIO = 42, /* I/O error */ + BFA_STATUS_ENOTTY = 43, /* Inappropriate I/O control + * operation */ + BFA_STATUS_ENXIO = 44, /* No such device or address */ + BFA_STATUS_EFOPEN = 45, /* Failed to open file */ + BFA_STATUS_VPORT_WWN_BP = 46, /* WWN is same as base port's WWN */ + BFA_STATUS_PORT_NOT_DISABLED = 47, /* Port not disabled disable port + * first */ + BFA_STATUS_BADFRMHDR = 48, /* Bad frame header */ + BFA_STATUS_BADFRMSZ = 49, /* Bad frame size check and replace + * SFP/cable */ + BFA_STATUS_MISSINGFRM = 50, /* Missing frame check and replace + * SFP/cable */ + BFA_STATUS_LINKTIMEOUT = 51, /* Link timeout check and replace + * SFP/cable */ + BFA_STATUS_NO_FCPIM_NEXUS = 52, /* No FCP Nexus exists with the + * rport */ + BFA_STATUS_CHECKSUM_FAIL = 53, /* checksum failure */ + BFA_STATUS_GZME_FAILED = 54, /* Get zone member query failed */ + BFA_STATUS_SCSISTART_REQD = 55, /* SCSI disk require START command */ + BFA_STATUS_IOC_FAILURE = 56, /* IOC failure - Retry, if persists + * contact support */ + BFA_STATUS_INVALID_WWN = 57, /* Invalid WWN */ + BFA_STATUS_MISMATCH = 58, /* Version mismatch */ + BFA_STATUS_IOC_ENABLED = 59, /* IOC is already enabled */ + BFA_STATUS_ADAPTER_ENABLED = 60, /* Adapter is not disabled disable + * adapter first */ + BFA_STATUS_IOC_NON_OP = 61, /* IOC is not operational. Enable IOC + * and if it still fails, + * contact support */ + BFA_STATUS_ADDR_MAP_FAILURE = 62, /* PCI base address not mapped + * in OS */ + BFA_STATUS_SAME_NAME = 63, /* Name exists! use a different + * name */ + BFA_STATUS_PENDING = 64, /* API completes asynchronously */ + BFA_STATUS_8G_SPD = 65, /* Speed setting not valid for + * 8G HBA */ + BFA_STATUS_4G_SPD = 66, /* Speed setting not valid for + * 4G HBA */ + BFA_STATUS_AD_IS_ENABLE = 67, /* Adapter is already enabled */ + BFA_STATUS_EINVAL_TOV = 68, /* Invalid path failover TOV */ + BFA_STATUS_EINVAL_QDEPTH = 69, /* Invalid queue depth value */ + BFA_STATUS_VERSION_FAIL = 70, /* Application/Driver version + * mismatch */ + BFA_STATUS_DIAG_BUSY = 71, /* diag busy */ + BFA_STATUS_BEACON_ON = 72, /* Port Beacon already on */ + BFA_STATUS_BEACON_OFF = 73, /* Port Beacon already off */ + BFA_STATUS_LBEACON_ON = 74, /* Link End-to-End Beacon already + * on */ + BFA_STATUS_LBEACON_OFF = 75, /* Link End-to-End Beacon already + * off */ + BFA_STATUS_PORT_NOT_INITED = 76, /* Port not initialized */ + BFA_STATUS_RPSC_ENABLED = 77, /* Target has a valid speed */ + BFA_STATUS_ENOFSAVE = 78, /* No saved firmware trace */ + BFA_STATUS_BAD_FILE = 79, /* Not a valid Brocade Boot Code + * file */ + BFA_STATUS_RLIM_EN = 80, /* Target rate limiting is already + * enabled */ + BFA_STATUS_RLIM_DIS = 81, /* Target rate limiting is already + * disabled */ + BFA_STATUS_IOC_DISABLED = 82, /* IOC is already disabled */ + BFA_STATUS_ADAPTER_DISABLED = 83, /* Adapter is already disabled */ + BFA_STATUS_BIOS_DISABLED = 84, /* Bios is already disabled */ + BFA_STATUS_AUTH_ENABLED = 85, /* Authentication is already + * enabled */ + BFA_STATUS_AUTH_DISABLED = 86, /* Authentication is already + * disabled */ + BFA_STATUS_ERROR_TRL_ENABLED = 87, /* Target rate limiting is + * enabled */ + BFA_STATUS_ERROR_QOS_ENABLED = 88, /* QoS is enabled */ + BFA_STATUS_NO_SFP_DEV = 89, /* No SFP device check or replace SFP */ + BFA_STATUS_MEMTEST_FAILED = 90, /* Memory test failed contact + * support */ + BFA_STATUS_INVALID_DEVID = 91, /* Invalid device id provided */ + BFA_STATUS_QOS_ENABLED = 92, /* QOS is already enabled */ + BFA_STATUS_QOS_DISABLED = 93, /* QOS is already disabled */ + BFA_STATUS_INCORRECT_DRV_CONFIG = 94, /* Check configuration + * key/value pair */ + BFA_STATUS_REG_FAIL = 95, /* Can't read windows registry */ + BFA_STATUS_IM_INV_CODE = 96, /* Invalid IOCTL code */ + BFA_STATUS_IM_INV_VLAN = 97, /* Invalid VLAN ID */ + BFA_STATUS_IM_INV_ADAPT_NAME = 98, /* Invalid adapter name */ + BFA_STATUS_IM_LOW_RESOURCES = 99, /* Memory allocation failure in + * driver */ + BFA_STATUS_IM_VLANID_IS_PVID = 100, /* Given VLAN id same as PVID */ + BFA_STATUS_IM_VLANID_EXISTS = 101, /* Given VLAN id already exists */ + BFA_STATUS_IM_FW_UPDATE_FAIL = 102, /* Updating firmware with new + * VLAN ID failed */ + BFA_STATUS_PORTLOG_ENABLED = 103, /* Port Log is already enabled */ + BFA_STATUS_PORTLOG_DISABLED = 104, /* Port Log is already disabled */ + BFA_STATUS_FILE_NOT_FOUND = 105, /* Specified file could not be + * found */ + BFA_STATUS_QOS_FC_ONLY = 106, /* QOS can be enabled for FC mode + * only */ + BFA_STATUS_RLIM_FC_ONLY = 107, /* RATELIM can be enabled for FC mode + * only */ + BFA_STATUS_CT_SPD = 108, /* Invalid speed selection for Catapult. */ + BFA_STATUS_LEDTEST_OP = 109, /* LED test is operating */ + BFA_STATUS_CEE_NOT_DN = 110, /* eth port is not at down state, please + * bring down first */ + BFA_STATUS_10G_SPD = 111, /* Speed setting not valid for 10G HBA */ + BFA_STATUS_IM_INV_TEAM_NAME = 112, /* Invalid team name */ + BFA_STATUS_IM_DUP_TEAM_NAME = 113, /* Given team name already + * exists */ + BFA_STATUS_IM_ADAPT_ALREADY_IN_TEAM = 114, /* Given adapter is part + * of another team */ + BFA_STATUS_IM_ADAPT_HAS_VLANS = 115, /* Adapter has VLANs configured. + * Delete all VLANs before + * creating team */ + BFA_STATUS_IM_PVID_MISMATCH = 116, /* Mismatching PVIDs configured + * for adapters */ + BFA_STATUS_IM_LINK_SPEED_MISMATCH = 117, /* Mismatching link speeds + * configured for adapters */ + BFA_STATUS_IM_MTU_MISMATCH = 118, /* Mismatching MTUs configured for + * adapters */ + BFA_STATUS_IM_RSS_MISMATCH = 119, /* Mismatching RSS parameters + * configured for adapters */ + BFA_STATUS_IM_HDS_MISMATCH = 120, /* Mismatching HDS parameters + * configured for adapters */ + BFA_STATUS_IM_OFFLOAD_MISMATCH = 121, /* Mismatching offload + * parameters configured for + * adapters */ + BFA_STATUS_IM_PORT_PARAMS = 122, /* Error setting port parameters */ + BFA_STATUS_IM_PORT_NOT_IN_TEAM = 123, /* Port is not part of team */ + BFA_STATUS_IM_CANNOT_REM_PRI = 124, /* Primary adapter cannot be + * removed. Change primary before + * removing */ + BFA_STATUS_IM_MAX_PORTS_REACHED = 125, /* Exceeding maximum ports + * per team */ + BFA_STATUS_IM_LAST_PORT_DELETE = 126, /* Last port in team being + * deleted */ + BFA_STATUS_IM_NO_DRIVER = 127, /* IM driver is not installed */ + BFA_STATUS_IM_MAX_VLANS_REACHED = 128, /* Exceeding maximum VLANs + * per port */ + BFA_STATUS_TOMCAT_SPD_NOT_ALLOWED = 129, /* Bios speed config not + * allowed for CNA */ + BFA_STATUS_NO_MINPORT_DRIVER = 130, /* Miniport driver is not + * loaded */ + BFA_STATUS_CARD_TYPE_MISMATCH = 131, /* Card type mismatch */ + BFA_STATUS_BAD_ASICBLK = 132, /* Bad ASIC block */ + BFA_STATUS_NO_DRIVER = 133, /* Storage/Ethernet driver not loaded */ + BFA_STATUS_INVALID_MAC = 134, /* Invalid mac address */ + BFA_STATUS_IM_NO_VLAN = 135, /* No VLANs configured on the adapter */ + BFA_STATUS_IM_ETH_LB_FAILED = 136, /* Ethernet loopback test failed */ + BFA_STATUS_IM_PVID_REMOVE = 137, /* Cannot remove port vlan (PVID) */ + BFA_STATUS_IM_PVID_EDIT = 138, /* Cannot edit port vlan (PVID) */ + BFA_STATUS_CNA_NO_BOOT = 139, /* Boot upload not allowed for CNA */ + BFA_STATUS_IM_PVID_NON_ZERO = 140, /* Port VLAN ID (PVID) is Set to + * Non-Zero Value */ + BFA_STATUS_IM_INETCFG_LOCK_FAILED = 141, /* Acquiring Network + * Subsytem Lock Failed.Please + * try after some time */ + BFA_STATUS_IM_GET_INETCFG_FAILED = 142, /* Acquiring Network Subsytem + * handle Failed. Please try + * after some time */ + BFA_STATUS_IM_NOT_BOUND = 143, /* Brocade 10G Ethernet Service is not + * Enabled on this port */ + BFA_STATUS_INSUFFICIENT_PERMS = 144, /* User doesn't have sufficient + * permissions to execute the BCU + * application */ + BFA_STATUS_IM_INV_VLAN_NAME = 145, /* Invalid/Reserved Vlan name + * string. The name is not allowed + * for the normal Vlans */ + BFA_STATUS_CMD_NOTSUPP_CNA = 146, /* Command not supported for CNA */ + BFA_STATUS_IM_PASSTHRU_EDIT = 147, /* Can not edit passthru vlan id */ + BFA_STATUS_IM_BIND_FAILED = 148, /*! < IM Driver bind operation + * failed */ + BFA_STATUS_IM_UNBIND_FAILED = 149, /* ! < IM Driver unbind operation + * failed */ + BFA_STATUS_MAX_VAL /* Unknown error code */ +}; +#define bfa_status_t enum bfa_status + +enum bfa_eproto_status { + BFA_EPROTO_BAD_ACCEPT = 0, + BFA_EPROTO_UNKNOWN_RSP = 1 +}; +#define bfa_eproto_status_t enum bfa_eproto_status + +#endif /* __BFA_DEFS_STATUS_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_tin.h b/drivers/scsi/bfa/include/defs/bfa_defs_tin.h new file mode 100644 index 000000000000..e05a2db7abed --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_tin.h @@ -0,0 +1,118 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_TIN_H__ +#define __BFA_DEFS_TIN_H__ + +#include <protocol/types.h> +#include <protocol/fc.h> + +/** + * FCS tin states + */ +enum bfa_tin_state_e { + BFA_TIN_SM_OFFLINE = 0, /* tin is offline */ + BFA_TIN_SM_WOS_LOGIN = 1, /* Waiting PRLI ACC/RJT from ULP */ + BFA_TIN_SM_WFW_ONLINE = 2, /* Waiting ACK to PRLI ACC from FW */ + BFA_TIN_SM_ONLINE = 3, /* tin login is complete */ + BFA_TIN_SM_WIO_RELOGIN = 4, /* tin relogin is in progress */ + BFA_TIN_SM_WIO_LOGOUT = 5, /* Processing of PRLO req from + * Initiator is in progress + */ + BFA_TIN_SM_WOS_LOGOUT = 6, /* Processing of PRLO req from + * Initiator is in progress + */ + BFA_TIN_SM_WIO_CLEAN = 7, /* Waiting for IO cleanup before tin + * is offline. This can be triggered + * by RPORT LOGO (rcvd/sent) or by + * PRLO (rcvd/sent) + */ +}; + +struct bfa_prli_req_s { + struct fchs_s fchs; + struct fc_prli_s prli_payload; +}; + +struct bfa_prlo_req_s { + struct fchs_s fchs; + struct fc_prlo_s prlo_payload; +}; + +void bfa_tin_send_login_rsp(void *bfa_tin, u32 login_rsp, + struct fc_ls_rjt_s rjt_payload); +void bfa_tin_send_logout_rsp(void *bfa_tin, u32 logout_rsp, + struct fc_ls_rjt_s rjt_payload); +/** + * FCS target port statistics + */ +struct bfa_tin_stats_s { + u32 onlines; /* ITN nexus onlines (PRLI done) */ + u32 offlines; /* ITN Nexus offlines */ + u32 prli_req_parse_err; /* prli req parsing errors */ + u32 prli_rsp_rjt; /* num prli rsp rejects sent */ + u32 prli_rsp_acc; /* num prli rsp accepts sent */ + u32 cleanup_comps; /* ITN cleanup completions */ +}; + +/** + * FCS tin attributes returned in queries + */ +struct bfa_tin_attr_s { + enum bfa_tin_state_e state; + u8 seq_retry; /* Sequence retry supported */ + u8 rsvd[3]; +}; + +/** + * BFA TIN async event data structure for BFAL + */ +enum bfa_tin_aen_event { + BFA_TIN_AEN_ONLINE = 1, /* Target online */ + BFA_TIN_AEN_OFFLINE = 2, /* Target offline */ + BFA_TIN_AEN_DISCONNECT = 3, /* Target disconnected */ +}; + +/** + * BFA TIN event data structure. + */ +struct bfa_tin_aen_data_s { + u16 vf_id; /* vf_id of the IT nexus */ + u16 rsvd[3]; + wwn_t lpwwn; /* WWN of logical port */ + wwn_t rpwwn; /* WWN of remote(target) port */ +}; + +/** + * Below APIs are needed from BFA driver + * Move these to BFA driver public header file? + */ +/* TIN rcvd new PRLI & gets bfad_tin_t ptr from driver this callback */ +void *bfad_tin_rcvd_login_req(void *bfad_tm_port, void *bfa_tin, + wwn_t rp_wwn, u32 rp_fcid, + struct bfa_prli_req_s prli_req); +/* TIN rcvd new PRLO */ +void bfad_tin_rcvd_logout_req(void *bfad_tin, wwn_t rp_wwn, u32 rp_fcid, + struct bfa_prlo_req_s prlo_req); +/* TIN is online and ready for IO */ +void bfad_tin_online(void *bfad_tin); +/* TIN is offline and BFA driver can shutdown its upper stack */ +void bfad_tin_offline(void *bfad_tin); +/* TIN does not need this BFA driver tin tag anymore, so can be freed */ +void bfad_tin_res_free(void *bfad_tin); + +#endif /* __BFA_DEFS_TIN_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_tsensor.h b/drivers/scsi/bfa/include/defs/bfa_defs_tsensor.h new file mode 100644 index 000000000000..31881d218515 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_tsensor.h @@ -0,0 +1,43 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_TSENSOR_H__ +#define __BFA_DEFS_TSENSOR_H__ + +#include <bfa_os_inc.h> +#include <defs/bfa_defs_types.h> + +/** + * Temperature sensor status values + */ +enum bfa_tsensor_status { + BFA_TSENSOR_STATUS_UNKNOWN = 1, /* unkown status */ + BFA_TSENSOR_STATUS_FAULTY = 2, /* sensor is faulty */ + BFA_TSENSOR_STATUS_BELOW_MIN = 3, /* temperature below mininum */ + BFA_TSENSOR_STATUS_NOMINAL = 4, /* normal temperature */ + BFA_TSENSOR_STATUS_ABOVE_MAX = 5, /* temperature above maximum */ +}; + +/** + * Temperature sensor attribute + */ +struct bfa_tsensor_attr_s { + enum bfa_tsensor_status status; /* temperature sensor status */ + u32 value; /* current temperature in celsius */ +}; + +#endif /* __BFA_DEFS_TSENSOR_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_types.h b/drivers/scsi/bfa/include/defs/bfa_defs_types.h new file mode 100644 index 000000000000..4348332b107a --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_types.h @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_TYPES_H__ +#define __BFA_DEFS_TYPES_H__ + +#include <bfa_os_inc.h> + +enum bfa_boolean { + BFA_FALSE = 0, + BFA_TRUE = 1 +}; +#define bfa_boolean_t enum bfa_boolean + +#define BFA_STRING_32 32 + +#endif /* __BFA_DEFS_TYPES_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_version.h b/drivers/scsi/bfa/include/defs/bfa_defs_version.h new file mode 100644 index 000000000000..f8902a2c9aad --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_version.h @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#ifndef __BFA_DEFS_VERSION_H__ +#define __BFA_DEFS_VERSION_H__ + +#define BFA_VERSION_LEN 64 + +#endif diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_vf.h b/drivers/scsi/bfa/include/defs/bfa_defs_vf.h new file mode 100644 index 000000000000..3235be5e9423 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_vf.h @@ -0,0 +1,74 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_VF_H__ +#define __BFA_DEFS_VF_H__ + +#include <bfa_os_inc.h> +#include <defs/bfa_defs_port.h> +#include <protocol/types.h> + +/** + * VF states + */ +enum bfa_vf_state { + BFA_VF_UNINIT = 0, /* fabric is not yet initialized */ + BFA_VF_LINK_DOWN = 1, /* link is down */ + BFA_VF_FLOGI = 2, /* flogi is in progress */ + BFA_VF_AUTH = 3, /* authentication in progress */ + BFA_VF_NOFABRIC = 4, /* fabric is not present */ + BFA_VF_ONLINE = 5, /* login to fabric is complete */ + BFA_VF_EVFP = 6, /* EVFP is in progress */ + BFA_VF_ISOLATED = 7, /* port isolated due to vf_id mismatch */ +}; + +/** + * VF statistics + */ +struct bfa_vf_stats_s { + u32 flogi_sent; /* Num FLOGIs sent */ + u32 flogi_rsp_err; /* FLOGI response errors */ + u32 flogi_acc_err; /* FLOGI accept errors */ + u32 flogi_accepts; /* FLOGI accepts received */ + u32 flogi_rejects; /* FLOGI rejects received */ + u32 flogi_unknown_rsp; /* Unknown responses for FLOGI */ + u32 flogi_alloc_wait; /* Allocation waits prior to + * sending FLOGI + */ + u32 flogi_rcvd; /* FLOGIs received */ + u32 flogi_rejected; /* Incoming FLOGIs rejected */ + u32 fabric_onlines; /* Internal fabric online + * notification sent to other + * modules + */ + u32 fabric_offlines; /* Internal fabric offline + * notification sent to other + * modules + */ + u32 resvd; +}; + +/** + * VF attributes returned in queries + */ +struct bfa_vf_attr_s { + enum bfa_vf_state state; /* VF state */ + u32 rsvd; + wwn_t fabric_name; /* fabric name */ +}; + +#endif /* __BFA_DEFS_VF_H__ */ diff --git a/drivers/scsi/bfa/include/defs/bfa_defs_vport.h b/drivers/scsi/bfa/include/defs/bfa_defs_vport.h new file mode 100644 index 000000000000..9f021f43b3b4 --- /dev/null +++ b/drivers/scsi/bfa/include/defs/bfa_defs_vport.h @@ -0,0 +1,91 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_DEFS_VPORT_H__ +#define __BFA_DEFS_VPORT_H__ + +#include <bfa_os_inc.h> +#include <defs/bfa_defs_port.h> +#include <protocol/types.h> + +/** + * VPORT states + */ +enum bfa_vport_state { + BFA_FCS_VPORT_UNINIT = 0, + BFA_FCS_VPORT_CREATED = 1, + BFA_FCS_VPORT_OFFLINE = 1, + BFA_FCS_VPORT_FDISC_SEND = 2, + BFA_FCS_VPORT_FDISC = 3, + BFA_FCS_VPORT_FDISC_RETRY = 4, + BFA_FCS_VPORT_ONLINE = 5, + BFA_FCS_VPORT_DELETING = 6, + BFA_FCS_VPORT_CLEANUP = 6, + BFA_FCS_VPORT_LOGO_SEND = 7, + BFA_FCS_VPORT_LOGO = 8, + BFA_FCS_VPORT_ERROR = 9, + BFA_FCS_VPORT_MAX_STATE, +}; + +/** + * vport statistics + */ +struct bfa_vport_stats_s { + struct bfa_port_stats_s port_stats; /* base class (port) stats */ + /* + * TODO - remove + */ + + u32 fdisc_sent; /* num fdisc sent */ + u32 fdisc_accepts; /* fdisc accepts */ + u32 fdisc_retries; /* fdisc retries */ + u32 fdisc_timeouts; /* fdisc timeouts */ + u32 fdisc_rsp_err; /* fdisc response error */ + u32 fdisc_acc_bad; /* bad fdisc accepts */ + u32 fdisc_rejects; /* fdisc rejects */ + u32 fdisc_unknown_rsp; + /* + *!< fdisc rsp unknown error + */ + u32 fdisc_alloc_wait;/* fdisc req (fcxp)alloc wait */ + + u32 logo_alloc_wait;/* logo req (fcxp) alloc wait */ + u32 logo_sent; /* logo sent */ + u32 logo_accepts; /* logo accepts */ + u32 logo_rejects; /* logo rejects */ + u32 logo_rsp_err; /* logo rsp errors */ + u32 logo_unknown_rsp; + /* logo rsp unknown errors */ + + u32 fab_no_npiv; /* fabric does not support npiv */ + + u32 fab_offline; /* offline events from fab SM */ + u32 fab_online; /* online events from fab SM */ + u32 fab_cleanup; /* cleanup request from fab SM */ + u32 rsvd; +}; + +/** + * BFA vport attribute returned in queries + */ +struct bfa_vport_attr_s { + struct bfa_port_attr_s port_attr; /* base class (port) attributes */ + enum bfa_vport_state vport_state; /* vport state */ + u32 rsvd; +}; + +#endif /* __BFA_DEFS_VPORT_H__ */ diff --git a/drivers/scsi/bfa/include/fcb/bfa_fcb.h b/drivers/scsi/bfa/include/fcb/bfa_fcb.h new file mode 100644 index 000000000000..2963b0bc30e7 --- /dev/null +++ b/drivers/scsi/bfa/include/fcb/bfa_fcb.h @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcb.h BFA FCS callback interfaces + */ + +#ifndef __BFA_FCB_H__ +#define __BFA_FCB_H__ + +/** + * fcb Main fcs callbacks + */ + +void bfa_fcb_exit(struct bfad_s *bfad); + + + +#endif /* __BFA_FCB_H__ */ diff --git a/drivers/scsi/bfa/include/fcb/bfa_fcb_fcpim.h b/drivers/scsi/bfa/include/fcb/bfa_fcb_fcpim.h new file mode 100644 index 000000000000..a6c70aee0aa3 --- /dev/null +++ b/drivers/scsi/bfa/include/fcb/bfa_fcb_fcpim.h @@ -0,0 +1,76 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** +* : bfad_fcpim.h - BFA FCS initiator mode remote port callbacks + */ + +#ifndef __BFAD_FCB_FCPIM_H__ +#define __BFAD_FCB_FCPIM_H__ + +struct bfad_itnim_s; + +/* + * RPIM callbacks + */ + +/** + * Memory allocation for remote port instance. Called before PRLI is + * initiated to the remote target port. + * + * @param[in] bfad - driver instance + * @param[out] itnim - FCS remote port (IM) instance + * @param[out] itnim_drv - driver remote port (IM) instance + * + * @return None + */ +void bfa_fcb_itnim_alloc(struct bfad_s *bfad, struct bfa_fcs_itnim_s **itnim, + struct bfad_itnim_s **itnim_drv); + +/** + * Free remote port (IM) instance. + * + * @param[in] bfad - driver instance + * @param[in] itnim_drv - driver remote port instance + * + * @return None + */ +void bfa_fcb_itnim_free(struct bfad_s *bfad, + struct bfad_itnim_s *itnim_drv); + +/** + * Notification of when login with a remote target device is complete. + * + * @param[in] itnim_drv - driver remote port instance + * + * @return None + */ +void bfa_fcb_itnim_online(struct bfad_itnim_s *itnim_drv); + +/** + * Notification when login with the remote device is severed. + * + * @param[in] itnim_drv - driver remote port instance + * + * @return None + */ +void bfa_fcb_itnim_offline(struct bfad_itnim_s *itnim_drv); + +void bfa_fcb_itnim_tov_begin(struct bfad_itnim_s *itnim_drv); +void bfa_fcb_itnim_tov(struct bfad_itnim_s *itnim_drv); + +#endif /* __BFAD_FCB_FCPIM_H__ */ diff --git a/drivers/scsi/bfa/include/fcb/bfa_fcb_port.h b/drivers/scsi/bfa/include/fcb/bfa_fcb_port.h new file mode 100644 index 000000000000..5fd7f986fa32 --- /dev/null +++ b/drivers/scsi/bfa/include/fcb/bfa_fcb_port.h @@ -0,0 +1,113 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcb_port.h BFA FCS virtual port driver interfaces + */ + +#ifndef __BFA_FCB_PORT_H__ +#define __BFA_FCB_PORT_H__ + +#include <fcb/bfa_fcb_vport.h> +/** + * fcs_port_fcb FCS port driver interfaces + */ + +/* + * Forward declarations + */ +struct bfad_port_s; + +/* + * Callback functions from BFA FCS to driver + */ + +/** + * Call from FCS to driver module when a port is instantiated. The port + * can be a base port or a virtual port with in the base fabric or + * a virtual fabric. + * + * On this callback, driver is supposed to create scsi_host, scsi_tgt or + * network interfaces bases on ports personality/roles. + * + * base port of base fabric: vf_drv == NULL && vp_drv == NULL + * vport of base fabric: vf_drv == NULL && vp_drv != NULL + * base port of VF: vf_drv != NULL && vp_drv == NULL + * vport of VF: vf_drv != NULL && vp_drv != NULL + * + * @param[in] bfad - driver instance + * @param[in] port - FCS port instance + * @param[in] roles - port roles: IM, TM, IP + * @param[in] vf_drv - VF driver instance, NULL if base fabric (no VF) + * @param[in] vp_drv - vport driver instance, NULL if base port + * + * @return None + */ +struct bfad_port_s *bfa_fcb_port_new(struct bfad_s *bfad, + struct bfa_fcs_port_s *port, + enum bfa_port_role roles, struct bfad_vf_s *vf_drv, + struct bfad_vport_s *vp_drv); + +/** + * Call from FCS to driver module when a port is deleted. The port + * can be a base port or a virtual port with in the base fabric or + * a virtual fabric. + * + * @param[in] bfad - driver instance + * @param[in] roles - port roles: IM, TM, IP + * @param[in] vf_drv - VF driver instance, NULL if base fabric (no VF) + * @param[in] vp_drv - vport driver instance, NULL if base port + * + * @return None + */ +void bfa_fcb_port_delete(struct bfad_s *bfad, enum bfa_port_role roles, + struct bfad_vf_s *vf_drv, struct bfad_vport_s *vp_drv); + +/** + * Notification when port transitions to ONLINE state. + * + * Online notification is a logical link up for the local port. This + * notification is sent after a successfull FLOGI, or a successful + * link initialization in proviate-loop or N2N topologies. + * + * @param[in] bfad - driver instance + * @param[in] roles - port roles: IM, TM, IP + * @param[in] vf_drv - VF driver instance, NULL if base fabric (no VF) + * @param[in] vp_drv - vport driver instance, NULL if base port + * + * @return None + */ +void bfa_fcb_port_online(struct bfad_s *bfad, enum bfa_port_role roles, + struct bfad_vf_s *vf_drv, struct bfad_vport_s *vp_drv); + +/** + * Notification when port transitions to OFFLINE state. + * + * Offline notification is a logical link down for the local port. + * + * @param[in] bfad - driver instance + * @param[in] roles - port roles: IM, TM, IP + * @param[in] vf_drv - VF driver instance, NULL if base fabric (no VF) + * @param[in] vp_drv - vport driver instance, NULL if base port + * + * @return None + */ +void bfa_fcb_port_offline(struct bfad_s *bfad, enum bfa_port_role roles, + struct bfad_vf_s *vf_drv, struct bfad_vport_s *vp_drv); + + +#endif /* __BFA_FCB_PORT_H__ */ diff --git a/drivers/scsi/bfa/include/fcb/bfa_fcb_rport.h b/drivers/scsi/bfa/include/fcb/bfa_fcb_rport.h new file mode 100644 index 000000000000..e0261bb6d1c1 --- /dev/null +++ b/drivers/scsi/bfa/include/fcb/bfa_fcb_rport.h @@ -0,0 +1,80 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcb_rport.h BFA FCS rport driver interfaces + */ + +#ifndef __BFA_FCB_RPORT_H__ +#define __BFA_FCB_RPORT_H__ + +/** + * fcs_rport_fcb Remote port driver interfaces + */ + + +struct bfad_rport_s; + +/* + * Callback functions from BFA FCS to driver + */ + +/** + * Completion callback for bfa_fcs_rport_add(). + * + * @param[in] rport_drv - driver instance of rport + * + * @return None + */ +void bfa_fcb_rport_add(struct bfad_rport_s *rport_drv); + +/** + * Completion callback for bfa_fcs_rport_remove(). + * + * @param[in] rport_drv - driver instance of rport + * + * @return None + */ +void bfa_fcb_rport_remove(struct bfad_rport_s *rport_drv); + +/** + * Call to allocate a rport instance. + * + * @param[in] bfad - driver instance + * @param[out] rport - BFA FCS instance of rport + * @param[out] rport_drv - driver instance of rport + * + * @retval BFA_STATUS_OK - successfully allocated + * @retval BFA_STATUS_ENOMEM - cannot allocate + */ +bfa_status_t bfa_fcb_rport_alloc(struct bfad_s *bfad, + struct bfa_fcs_rport_s **rport, + struct bfad_rport_s **rport_drv); + +/** + * Call to free rport memory resources. + * + * @param[in] bfad - driver instance + * @param[in] rport_drv - driver instance of rport + * + * @return None + */ +void bfa_fcb_rport_free(struct bfad_s *bfad, struct bfad_rport_s **rport_drv); + + + +#endif /* __BFA_FCB_RPORT_H__ */ diff --git a/drivers/scsi/bfa/include/fcb/bfa_fcb_vf.h b/drivers/scsi/bfa/include/fcb/bfa_fcb_vf.h new file mode 100644 index 000000000000..cfd3fac0a4e2 --- /dev/null +++ b/drivers/scsi/bfa/include/fcb/bfa_fcb_vf.h @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcb_vf.h BFA FCS virtual fabric driver interfaces + */ + +#ifndef __BFA_FCB_VF_H__ +#define __BFA_FCB_VF_H__ + +/** + * fcs_vf_fcb Virtual fabric driver intrefaces + */ + + +struct bfad_vf_s; + +/* + * Callback functions from BFA FCS to driver + */ + +/** + * Completion callback for bfa_fcs_vf_stop(). + * + * @param[in] vf_drv - driver instance of vf + * + * @return None + */ +void bfa_fcb_vf_stop(struct bfad_vf_s *vf_drv); + + + +#endif /* __BFA_FCB_VF_H__ */ diff --git a/drivers/scsi/bfa/include/fcb/bfa_fcb_vport.h b/drivers/scsi/bfa/include/fcb/bfa_fcb_vport.h new file mode 100644 index 000000000000..a39f474c2fcf --- /dev/null +++ b/drivers/scsi/bfa/include/fcb/bfa_fcb_vport.h @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcb_vport.h BFA FCS virtual port driver interfaces + */ + +#ifndef __BFA_FCB_VPORT_H__ +#define __BFA_FCB_VPORT_H__ + +/** + * fcs_vport_fcb Virtual port driver interfaces + */ + + +struct bfad_vport_s; + +/* + * Callback functions from BFA FCS to driver + */ + +/** + * Completion callback for bfa_fcs_vport_delete(). + * + * @param[in] vport_drv - driver instance of vport + * + * @return None + */ +void bfa_fcb_vport_delete(struct bfad_vport_s *vport_drv); + + + +#endif /* __BFA_FCB_VPORT_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs.h b/drivers/scsi/bfa/include/fcs/bfa_fcs.h new file mode 100644 index 000000000000..627669c65546 --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs.h @@ -0,0 +1,73 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCS_H__ +#define __BFA_FCS_H__ + +#include <cs/bfa_debug.h> +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_version.h> +#include <bfa.h> +#include <fcs/bfa_fcs_fabric.h> + +#define BFA_FCS_OS_STR_LEN 64 + +struct bfa_fcs_stats_s { + struct { + u32 untagged; /* untagged receive frames */ + u32 tagged; /* tagged receive frames */ + u32 vfid_unknown; /* VF id is unknown */ + } uf; +}; + +struct bfa_fcs_driver_info_s { + u8 version[BFA_VERSION_LEN]; /* Driver Version */ + u8 host_machine_name[BFA_FCS_OS_STR_LEN]; + u8 host_os_name[BFA_FCS_OS_STR_LEN]; /* OS name and version */ + u8 host_os_patch[BFA_FCS_OS_STR_LEN];/* patch or service pack */ + u8 os_device_name[BFA_FCS_OS_STR_LEN]; /* Driver Device Name */ +}; + +struct bfa_fcs_s { + struct bfa_s *bfa; /* corresponding BFA bfa instance */ + struct bfad_s *bfad; /* corresponding BDA driver instance */ + struct bfa_log_mod_s *logm; /* driver logging module instance */ + struct bfa_trc_mod_s *trcmod; /* tracing module */ + struct bfa_aen_s *aen; /* aen component */ + bfa_boolean_t vf_enabled; /* VF mode is enabled */ + bfa_boolean_t min_cfg; /* min cfg enabled/disabled */ + u16 port_vfid; /* port default VF ID */ + struct bfa_fcs_driver_info_s driver_info; + struct bfa_fcs_fabric_s fabric; /* base fabric state machine */ + struct bfa_fcs_stats_s stats; /* FCS statistics */ + struct bfa_wc_s wc; /* waiting counter */ +}; + +/* + * bfa fcs API functions + */ +void bfa_fcs_init(struct bfa_fcs_s *fcs, struct bfa_s *bfa, struct bfad_s *bfad, + bfa_boolean_t min_cfg); +void bfa_fcs_driver_info_init(struct bfa_fcs_s *fcs, + struct bfa_fcs_driver_info_s *driver_info); +void bfa_fcs_exit(struct bfa_fcs_s *fcs); +void bfa_fcs_trc_init(struct bfa_fcs_s *fcs, struct bfa_trc_mod_s *trcmod); +void bfa_fcs_log_init(struct bfa_fcs_s *fcs, struct bfa_log_mod_s *logmod); +void bfa_fcs_aen_init(struct bfa_fcs_s *fcs, struct bfa_aen_s *aen); +void bfa_fcs_start(struct bfa_fcs_s *fcs); + +#endif /* __BFA_FCS_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs_auth.h b/drivers/scsi/bfa/include/fcs/bfa_fcs_auth.h new file mode 100644 index 000000000000..28c4c9ff08b3 --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs_auth.h @@ -0,0 +1,82 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCS_AUTH_H__ +#define __BFA_FCS_AUTH_H__ + +struct bfa_fcs_s; + +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_auth.h> +#include <defs/bfa_defs_vf.h> +#include <cs/bfa_q.h> +#include <cs/bfa_sm.h> +#include <defs/bfa_defs_pport.h> +#include <fcs/bfa_fcs_lport.h> +#include <protocol/fc_sp.h> + +struct bfa_fcs_fabric_s; + + + +struct bfa_fcs_auth_s { + bfa_sm_t sm; /* state machine */ + bfa_boolean_t policy; /* authentication enabled/disabled */ + enum bfa_auth_status status; /* authentication status */ + enum auth_rjt_codes rjt_code; /* auth reject status */ + enum auth_rjt_code_exps rjt_code_exp; /* auth reject reason */ + enum bfa_auth_algo algo; /* Authentication algorithm */ + struct bfa_auth_stats_s stats; /* Statistics */ + enum auth_dh_gid group; /* DH(diffie-hellman) Group */ + enum bfa_auth_secretsource source; /* Secret source */ + char secret[BFA_AUTH_SECRET_STRING_LEN]; + /* secret string */ + u8 secret_len; + /* secret string length */ + u8 nretries; + /* number of retries */ + struct bfa_fcs_fabric_s *fabric;/* pointer to fabric */ + u8 sentcode; /* pointer to response data */ + u8 *response; /* pointer to response data */ + struct bfa_timer_s delay_timer; /* delay timer */ + struct bfa_fcxp_s *fcxp; /* pointer to fcxp */ + struct bfa_fcxp_wqe_s fcxp_wqe; +}; + +/** + * bfa fcs authentication public functions + */ +bfa_status_t bfa_fcs_auth_get_attr(struct bfa_fcs_s *port, + struct bfa_auth_attr_s *attr); +bfa_status_t bfa_fcs_auth_set_policy(struct bfa_fcs_s *port, + bfa_boolean_t policy); +enum bfa_auth_status bfa_fcs_auth_get_status(struct bfa_fcs_s *port); +bfa_status_t bfa_fcs_auth_set_algo(struct bfa_fcs_s *port, + enum bfa_auth_algo algo); +bfa_status_t bfa_fcs_auth_get_stats(struct bfa_fcs_s *port, + struct bfa_auth_stats_s *stats); +bfa_status_t bfa_fcs_auth_set_dh_group(struct bfa_fcs_s *port, int group); +bfa_status_t bfa_fcs_auth_set_secretstring(struct bfa_fcs_s *port, + char *secret); +bfa_status_t bfa_fcs_auth_set_secretstring_encrypt(struct bfa_fcs_s *port, + u32 secret[], u32 len); +bfa_status_t bfa_fcs_auth_set_secretsource(struct bfa_fcs_s *port, + enum bfa_auth_secretsource src); +bfa_status_t bfa_fcs_auth_reset_stats(struct bfa_fcs_s *port); +bfa_status_t bfa_fcs_auth_reinit(struct bfa_fcs_s *port); + +#endif /* __BFA_FCS_AUTH_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs_fabric.h b/drivers/scsi/bfa/include/fcs/bfa_fcs_fabric.h new file mode 100644 index 000000000000..4ffd2242d3de --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs_fabric.h @@ -0,0 +1,112 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCS_FABRIC_H__ +#define __BFA_FCS_FABRIC_H__ + +struct bfa_fcs_s; + +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_vf.h> +#include <cs/bfa_q.h> +#include <cs/bfa_sm.h> +#include <defs/bfa_defs_pport.h> +#include <fcs/bfa_fcs_lport.h> +#include <protocol/fc_sp.h> +#include <fcs/bfa_fcs_auth.h> + +/* + * forward declaration + */ +struct bfad_vf_s; + +enum bfa_fcs_fabric_type { + BFA_FCS_FABRIC_UNKNOWN = 0, + BFA_FCS_FABRIC_SWITCHED = 1, + BFA_FCS_FABRIC_PLOOP = 2, + BFA_FCS_FABRIC_N2N = 3, +}; + + +struct bfa_fcs_fabric_s { + struct list_head qe; /* queue element */ + bfa_sm_t sm; /* state machine */ + struct bfa_fcs_s *fcs; /* FCS instance */ + struct bfa_fcs_port_s bport; /* base logical port */ + enum bfa_fcs_fabric_type fab_type; /* fabric type */ + enum bfa_pport_type oper_type; /* current link topology */ + u8 is_vf; /* is virtual fabric? */ + u8 is_npiv; /* is NPIV supported ? */ + u8 is_auth; /* is Security/Auth supported ? */ + u16 bb_credit; /* BB credit from fabric */ + u16 vf_id; /* virtual fabric ID */ + u16 num_vports; /* num vports */ + u16 rsvd; + struct list_head vport_q; /* queue of virtual ports */ + struct list_head vf_q; /* queue of virtual fabrics */ + struct bfad_vf_s *vf_drv; /* driver vf structure */ + struct bfa_timer_s link_timer; /* Link Failure timer. Vport */ + wwn_t fabric_name; /* attached fabric name */ + bfa_boolean_t auth_reqd; /* authentication required */ + struct bfa_timer_s delay_timer; /* delay timer */ + union { + u16 swp_vfid;/* switch port VF id */ + } event_arg; + struct bfa_fcs_auth_s auth; /* authentication config */ + struct bfa_wc_s wc; /* wait counter for delete */ + struct bfa_vf_stats_s stats; /* fabric/vf stats */ + struct bfa_lps_s *lps; /* lport login services */ + u8 fabric_ip_addr[BFA_FCS_FABRIC_IPADDR_SZ]; /* attached + * fabric's ip addr + */ +}; + +#define bfa_fcs_fabric_npiv_capable(__f) (__f)->is_npiv +#define bfa_fcs_fabric_is_switched(__f) \ + ((__f)->fab_type == BFA_FCS_FABRIC_SWITCHED) + +/** + * The design calls for a single implementation of base fabric and vf. + */ +#define bfa_fcs_vf_t struct bfa_fcs_fabric_s + +struct bfa_vf_event_s { + u32 undefined; +}; + +/** + * bfa fcs vf public functions + */ +bfa_status_t bfa_fcs_vf_mode_enable(struct bfa_fcs_s *fcs, u16 vf_id); +bfa_status_t bfa_fcs_vf_mode_disable(struct bfa_fcs_s *fcs); +bfa_status_t bfa_fcs_vf_create(bfa_fcs_vf_t *vf, struct bfa_fcs_s *fcs, + u16 vf_id, struct bfa_port_cfg_s *port_cfg, + struct bfad_vf_s *vf_drv); +bfa_status_t bfa_fcs_vf_delete(bfa_fcs_vf_t *vf); +void bfa_fcs_vf_start(bfa_fcs_vf_t *vf); +bfa_status_t bfa_fcs_vf_stop(bfa_fcs_vf_t *vf); +void bfa_fcs_vf_list(struct bfa_fcs_s *fcs, u16 *vf_ids, int *nvfs); +void bfa_fcs_vf_list_all(struct bfa_fcs_s *fcs, u16 *vf_ids, int *nvfs); +void bfa_fcs_vf_get_attr(bfa_fcs_vf_t *vf, struct bfa_vf_attr_s *vf_attr); +void bfa_fcs_vf_get_stats(bfa_fcs_vf_t *vf, + struct bfa_vf_stats_s *vf_stats); +void bfa_fcs_vf_clear_stats(bfa_fcs_vf_t *vf); +void bfa_fcs_vf_get_ports(bfa_fcs_vf_t *vf, wwn_t vpwwn[], int *nports); +bfa_fcs_vf_t *bfa_fcs_vf_lookup(struct bfa_fcs_s *fcs, u16 vf_id); +struct bfad_vf_s *bfa_fcs_vf_get_drv_vf(bfa_fcs_vf_t *vf); + +#endif /* __BFA_FCS_FABRIC_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs_fcpim.h b/drivers/scsi/bfa/include/fcs/bfa_fcs_fcpim.h new file mode 100644 index 000000000000..e719f2c3eb35 --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs_fcpim.h @@ -0,0 +1,131 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_fcpim.h BFA FCS FCP Initiator Mode interfaces/defines. + */ + +#ifndef __BFA_FCS_FCPIM_H__ +#define __BFA_FCS_FCPIM_H__ + +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_itnim.h> +#include <fcs/bfa_fcs.h> +#include <fcs/bfa_fcs_rport.h> +#include <fcs/bfa_fcs_lport.h> +#include <bfa_fcpim.h> + +/* + * forward declarations + */ +struct bfad_itnim_s; + +struct bfa_fcs_itnim_s { + bfa_sm_t sm; /* state machine */ + struct bfa_fcs_rport_s *rport; /* parent remote rport */ + struct bfad_itnim_s *itnim_drv; /* driver peer instance */ + struct bfa_fcs_s *fcs; /* fcs instance */ + struct bfa_timer_s timer; /* timer functions */ + struct bfa_itnim_s *bfa_itnim; /* BFA itnim struct */ + bfa_boolean_t seq_rec; /* seq recovery support */ + bfa_boolean_t rec_support; /* REC supported */ + bfa_boolean_t conf_comp; /* FCP_CONF support */ + bfa_boolean_t task_retry_id; /* task retry id supp */ + struct bfa_fcxp_wqe_s fcxp_wqe; /* wait qelem for fcxp */ + struct bfa_fcxp_s *fcxp; /* FCXP in use */ + struct bfa_itnim_stats_s stats; /* itn statistics */ +}; + + +static inline struct bfad_port_s * +bfa_fcs_itnim_get_drvport(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->rport->port->bfad_port; +} + + +static inline struct bfa_fcs_port_s * +bfa_fcs_itnim_get_port(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->rport->port; +} + + +static inline wwn_t +bfa_fcs_itnim_get_nwwn(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->rport->nwwn; +} + + +static inline wwn_t +bfa_fcs_itnim_get_pwwn(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->rport->pwwn; +} + + +static inline u32 +bfa_fcs_itnim_get_fcid(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->rport->pid; +} + + +static inline u32 +bfa_fcs_itnim_get_maxfrsize(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->rport->maxfrsize; +} + + +static inline enum fc_cos +bfa_fcs_itnim_get_cos(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->rport->fc_cos; +} + + +static inline struct bfad_itnim_s * +bfa_fcs_itnim_get_drvitn(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->itnim_drv; +} + + +static inline struct bfa_itnim_s * +bfa_fcs_itnim_get_halitn(struct bfa_fcs_itnim_s *itnim) +{ + return itnim->bfa_itnim; +} + +/** + * bfa fcs FCP Initiator mode API functions + */ +void bfa_fcs_itnim_get_attr(struct bfa_fcs_itnim_s *itnim, + struct bfa_itnim_attr_s *attr); +void bfa_fcs_itnim_get_stats(struct bfa_fcs_itnim_s *itnim, + struct bfa_itnim_stats_s *stats); +struct bfa_fcs_itnim_s *bfa_fcs_itnim_lookup(struct bfa_fcs_port_s *port, + wwn_t rpwwn); +bfa_status_t bfa_fcs_itnim_attr_get(struct bfa_fcs_port_s *port, wwn_t rpwwn, + struct bfa_itnim_attr_s *attr); +bfa_status_t bfa_fcs_itnim_stats_get(struct bfa_fcs_port_s *port, wwn_t rpwwn, + struct bfa_itnim_stats_s *stats); +bfa_status_t bfa_fcs_itnim_stats_clear(struct bfa_fcs_port_s *port, + wwn_t rpwwn); +#endif /* __BFA_FCS_FCPIM_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs_fdmi.h b/drivers/scsi/bfa/include/fcs/bfa_fcs_fdmi.h new file mode 100644 index 000000000000..4441fffc9c82 --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs_fdmi.h @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_fdmi.h BFA fcs fdmi module public interface + */ + +#ifndef __BFA_FCS_FDMI_H__ +#define __BFA_FCS_FDMI_H__ +#include <bfa_os_inc.h> +#include <protocol/fdmi.h> + +#define BFA_FCS_FDMI_SUPORTED_SPEEDS (FDMI_TRANS_SPEED_1G | \ + FDMI_TRANS_SPEED_2G | \ + FDMI_TRANS_SPEED_4G | \ + FDMI_TRANS_SPEED_8G) + +/* +* HBA Attribute Block : BFA internal representation. Note : Some variable +* sizes have been trimmed to suit BFA For Ex : Model will be "Brocade". Based + * on this the size has been reduced to 16 bytes from the standard's 64 bytes. + */ +struct bfa_fcs_fdmi_hba_attr_s { + wwn_t node_name; + u8 manufacturer[64]; + u8 serial_num[64]; + u8 model[16]; + u8 model_desc[256]; + u8 hw_version[8]; + u8 driver_version[8]; + u8 option_rom_ver[BFA_VERSION_LEN]; + u8 fw_version[8]; + u8 os_name[256]; + u32 max_ct_pyld; +}; + +/* + * Port Attribute Block + */ +struct bfa_fcs_fdmi_port_attr_s { + u8 supp_fc4_types[32]; /* supported FC4 types */ + u32 supp_speed; /* supported speed */ + u32 curr_speed; /* current Speed */ + u32 max_frm_size; /* max frame size */ + u8 os_device_name[256]; /* OS device Name */ + u8 host_name[256]; /* host name */ +}; + +#endif /* __BFA_FCS_FDMI_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs_lport.h b/drivers/scsi/bfa/include/fcs/bfa_fcs_lport.h new file mode 100644 index 000000000000..b85cba884b96 --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs_lport.h @@ -0,0 +1,226 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_port.h BFA fcs port module public interface + */ + +#ifndef __BFA_FCS_PORT_H__ +#define __BFA_FCS_PORT_H__ + +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_port.h> +#include <defs/bfa_defs_pport.h> +#include <defs/bfa_defs_rport.h> +#include <cs/bfa_q.h> +#include <bfa_svc.h> +#include <cs/bfa_wc.h> + +struct bfa_fcs_s; +struct bfa_fcs_fabric_s; + +/* +* @todo : need to move to a global config file. + * Maximum Vports supported per physical port or vf. + */ +#define BFA_FCS_MAX_VPORTS_SUPP_CB 255 +#define BFA_FCS_MAX_VPORTS_SUPP_CT 191 + +/* +* @todo : need to move to a global config file. + * Maximum Rports supported per port (physical/logical). + */ +#define BFA_FCS_MAX_RPORTS_SUPP 256 /* @todo : tentative value */ + + +struct bfa_fcs_port_ns_s { + bfa_sm_t sm; /* state machine */ + struct bfa_timer_s timer; + struct bfa_fcs_port_s *port; /* parent port */ + struct bfa_fcxp_s *fcxp; + struct bfa_fcxp_wqe_s fcxp_wqe; +}; + + +struct bfa_fcs_port_scn_s { + bfa_sm_t sm; /* state machine */ + struct bfa_timer_s timer; + struct bfa_fcs_port_s *port; /* parent port */ + struct bfa_fcxp_s *fcxp; + struct bfa_fcxp_wqe_s fcxp_wqe; +}; + + +struct bfa_fcs_port_fdmi_s { + bfa_sm_t sm; /* state machine */ + struct bfa_timer_s timer; + struct bfa_fcs_port_ms_s *ms; /* parent ms */ + struct bfa_fcxp_s *fcxp; + struct bfa_fcxp_wqe_s fcxp_wqe; + u8 retry_cnt; /* retry count */ + u8 rsvd[3]; +}; + + +struct bfa_fcs_port_ms_s { + bfa_sm_t sm; /* state machine */ + struct bfa_timer_s timer; + struct bfa_fcs_port_s *port; /* parent port */ + struct bfa_fcxp_s *fcxp; + struct bfa_fcxp_wqe_s fcxp_wqe; + struct bfa_fcs_port_fdmi_s fdmi; /* FDMI component of MS */ + u8 retry_cnt; /* retry count */ + u8 rsvd[3]; +}; + + +struct bfa_fcs_port_fab_s { + struct bfa_fcs_port_ns_s ns; /* NS component of port */ + struct bfa_fcs_port_scn_s scn; /* scn component of port */ + struct bfa_fcs_port_ms_s ms; /* MS component of port */ +}; + + + +#define MAX_ALPA_COUNT 127 + +struct bfa_fcs_port_loop_s { + u8 num_alpa; /* Num of ALPA entries in the map */ + u8 alpa_pos_map[MAX_ALPA_COUNT]; /* ALPA Positional + *Map */ + struct bfa_fcs_port_s *port; /* parent port */ +}; + + + +struct bfa_fcs_port_n2n_s { + u32 rsvd; + u16 reply_oxid; /* ox_id from the req flogi to be + *used in flogi acc */ + wwn_t rem_port_wwn; /* Attached port's wwn */ +}; + + +union bfa_fcs_port_topo_u { + struct bfa_fcs_port_fab_s pfab; + struct bfa_fcs_port_loop_s ploop; + struct bfa_fcs_port_n2n_s pn2n; +}; + + +struct bfa_fcs_port_s { + struct list_head qe; /* used by port/vport */ + bfa_sm_t sm; /* state machine */ + struct bfa_fcs_fabric_s *fabric; /* parent fabric */ + struct bfa_port_cfg_s port_cfg; /* port configuration */ + struct bfa_timer_s link_timer; /* timer for link offline */ + u32 pid : 24; /* FC address */ + u8 lp_tag; /* lport tag */ + u16 num_rports; /* Num of r-ports */ + struct list_head rport_q; /* queue of discovered r-ports */ + struct bfa_fcs_s *fcs; /* FCS instance */ + union bfa_fcs_port_topo_u port_topo; /* fabric/loop/n2n details */ + struct bfad_port_s *bfad_port; /* driver peer instance */ + struct bfa_fcs_vport_s *vport; /* NULL for base ports */ + struct bfa_fcxp_s *fcxp; + struct bfa_fcxp_wqe_s fcxp_wqe; + struct bfa_port_stats_s stats; + struct bfa_wc_s wc; /* waiting counter for events */ +}; + +#define bfa_fcs_lport_t struct bfa_fcs_port_s + +/** + * Symbolic Name related defines + * Total bytes 255. + * Physical Port's symbolic name 128 bytes. + * For Vports, Vport's symbolic name is appended to the Physical port's + * Symbolic Name. + * + * Physical Port's symbolic name Format : (Total 128 bytes) + * Adapter Model number/name : 12 bytes + * Driver Version : 10 bytes + * Host Machine Name : 30 bytes + * Host OS Info : 48 bytes + * Host OS PATCH Info : 16 bytes + * ( remaining 12 bytes reserved to be used for separator) + */ +#define BFA_FCS_PORT_SYMBNAME_SEPARATOR " | " + +#define BFA_FCS_PORT_SYMBNAME_MODEL_SZ 12 +#define BFA_FCS_PORT_SYMBNAME_VERSION_SZ 10 +#define BFA_FCS_PORT_SYMBNAME_MACHINENAME_SZ 30 +#define BFA_FCS_PORT_SYMBNAME_OSINFO_SZ 48 +#define BFA_FCS_PORT_SYMBNAME_OSPATCH_SZ 16 + +/** + * Get FC port ID for a logical port. + */ +#define bfa_fcs_port_get_fcid(_lport) ((_lport)->pid) +#define bfa_fcs_port_get_pwwn(_lport) ((_lport)->port_cfg.pwwn) +#define bfa_fcs_port_get_nwwn(_lport) ((_lport)->port_cfg.nwwn) +#define bfa_fcs_port_get_psym_name(_lport) ((_lport)->port_cfg.sym_name) +#define bfa_fcs_port_is_initiator(_lport) \ + ((_lport)->port_cfg.roles & BFA_PORT_ROLE_FCP_IM) +#define bfa_fcs_port_is_target(_lport) \ + ((_lport)->port_cfg.roles & BFA_PORT_ROLE_FCP_TM) +#define bfa_fcs_port_get_nrports(_lport) \ + ((_lport) ? (_lport)->num_rports : 0) + +static inline struct bfad_port_s * +bfa_fcs_port_get_drvport(struct bfa_fcs_port_s *port) +{ + return port->bfad_port; +} + + +#define bfa_fcs_port_get_opertype(_lport) (_lport)->fabric->oper_type + + +#define bfa_fcs_port_get_fabric_name(_lport) (_lport)->fabric->fabric_name + + +#define bfa_fcs_port_get_fabric_ipaddr(_lport) (_lport)->fabric->fabric_ip_addr + +/** + * bfa fcs port public functions + */ +void bfa_fcs_cfg_base_port(struct bfa_fcs_s *fcs, + struct bfa_port_cfg_s *port_cfg); +struct bfa_fcs_port_s *bfa_fcs_get_base_port(struct bfa_fcs_s *fcs); +void bfa_fcs_port_get_rports(struct bfa_fcs_port_s *port, + wwn_t rport_wwns[], int *nrports); + +wwn_t bfa_fcs_port_get_rport(struct bfa_fcs_port_s *port, wwn_t wwn, + int index, int nrports, bfa_boolean_t bwwn); + +struct bfa_fcs_port_s *bfa_fcs_lookup_port(struct bfa_fcs_s *fcs, + u16 vf_id, wwn_t lpwwn); + +void bfa_fcs_port_get_info(struct bfa_fcs_port_s *port, + struct bfa_port_info_s *port_info); +void bfa_fcs_port_get_attr(struct bfa_fcs_port_s *port, + struct bfa_port_attr_s *port_attr); +void bfa_fcs_port_get_stats(struct bfa_fcs_port_s *fcs_port, + struct bfa_port_stats_s *port_stats); +void bfa_fcs_port_clear_stats(struct bfa_fcs_port_s *fcs_port); +enum bfa_pport_speed bfa_fcs_port_get_rport_max_speed( + struct bfa_fcs_port_s *port); +void bfa_fcs_port_enable_ipfc_roles(struct bfa_fcs_port_s *fcs_port); +void bfa_fcs_port_disable_ipfc_roles(struct bfa_fcs_port_s *fcs_port); + +#endif /* __BFA_FCS_PORT_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs_rport.h b/drivers/scsi/bfa/include/fcs/bfa_fcs_rport.h new file mode 100644 index 000000000000..702b95b76c2d --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs_rport.h @@ -0,0 +1,104 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __BFA_FCS_RPORT_H__ +#define __BFA_FCS_RPORT_H__ + +#include <defs/bfa_defs_status.h> +#include <cs/bfa_q.h> +#include <fcs/bfa_fcs.h> +#include <defs/bfa_defs_rport.h> + +#define BFA_FCS_RPORT_DEF_DEL_TIMEOUT 90 /* in secs */ +/* + * forward declarations + */ +struct bfad_rport_s; + +struct bfa_fcs_itnim_s; +struct bfa_fcs_tin_s; +struct bfa_fcs_iprp_s; + +/* Rport Features (RPF) */ +struct bfa_fcs_rpf_s { + bfa_sm_t sm; /* state machine */ + struct bfa_fcs_rport_s *rport; /* parent rport */ + struct bfa_timer_s timer; /* general purpose timer */ + struct bfa_fcxp_s *fcxp; /* FCXP needed for discarding */ + struct bfa_fcxp_wqe_s fcxp_wqe; /* fcxp wait queue element */ + int rpsc_retries; /* max RPSC retry attempts */ + enum bfa_pport_speed rpsc_speed; /* Current Speed from RPSC. + * O if RPSC fails */ + enum bfa_pport_speed assigned_speed; /* Speed assigned by the user. + * will be used if RPSC is not + * supported by the rport */ +}; + +struct bfa_fcs_rport_s { + struct list_head qe; /* used by port/vport */ + struct bfa_fcs_port_s *port; /* parent FCS port */ + struct bfa_fcs_s *fcs; /* fcs instance */ + struct bfad_rport_s *rp_drv; /* driver peer instance */ + u32 pid; /* port ID of rport */ + u16 maxfrsize; /* maximum frame size */ + u16 reply_oxid; /* OX_ID of inbound requests */ + enum fc_cos fc_cos; /* FC classes of service supp */ + bfa_boolean_t cisc; /* CISC capable device */ + wwn_t pwwn; /* port wwn of rport */ + wwn_t nwwn; /* node wwn of rport */ + struct bfa_rport_symname_s psym_name; /* port symbolic name */ + bfa_sm_t sm; /* state machine */ + struct bfa_timer_s timer; /* general purpose timer */ + struct bfa_fcs_itnim_s *itnim; /* ITN initiator mode role */ + struct bfa_fcs_tin_s *tin; /* ITN initiator mode role */ + struct bfa_fcs_iprp_s *iprp; /* IP/FC role */ + struct bfa_rport_s *bfa_rport; /* BFA Rport */ + struct bfa_fcxp_s *fcxp; /* FCXP needed for discarding */ + int plogi_retries; /* max plogi retry attempts */ + int ns_retries; /* max NS query retry attempts */ + struct bfa_fcxp_wqe_s fcxp_wqe; /* fcxp wait queue element */ + struct bfa_rport_stats_s stats; /* rport stats */ + enum bfa_rport_function scsi_function; /* Initiator/Target */ + struct bfa_fcs_rpf_s rpf; /* Rport features module */ +}; + +static inline struct bfa_rport_s * +bfa_fcs_rport_get_halrport(struct bfa_fcs_rport_s *rport) +{ + return rport->bfa_rport; +} + +/** + * bfa fcs rport API functions + */ +bfa_status_t bfa_fcs_rport_add(struct bfa_fcs_port_s *port, wwn_t *pwwn, + struct bfa_fcs_rport_s *rport, + struct bfad_rport_s *rport_drv); +bfa_status_t bfa_fcs_rport_remove(struct bfa_fcs_rport_s *rport); +void bfa_fcs_rport_get_attr(struct bfa_fcs_rport_s *rport, + struct bfa_rport_attr_s *attr); +void bfa_fcs_rport_get_stats(struct bfa_fcs_rport_s *rport, + struct bfa_rport_stats_s *stats); +void bfa_fcs_rport_clear_stats(struct bfa_fcs_rport_s *rport); +struct bfa_fcs_rport_s *bfa_fcs_rport_lookup(struct bfa_fcs_port_s *port, + wwn_t rpwwn); +struct bfa_fcs_rport_s *bfa_fcs_rport_lookup_by_nwwn( + struct bfa_fcs_port_s *port, wwn_t rnwwn); +void bfa_fcs_rport_set_del_timeout(u8 rport_tmo); +void bfa_fcs_rport_set_speed(struct bfa_fcs_rport_s *rport, + enum bfa_pport_speed speed); +#endif /* __BFA_FCS_RPORT_H__ */ diff --git a/drivers/scsi/bfa/include/fcs/bfa_fcs_vport.h b/drivers/scsi/bfa/include/fcs/bfa_fcs_vport.h new file mode 100644 index 000000000000..cd33f2cd5c34 --- /dev/null +++ b/drivers/scsi/bfa/include/fcs/bfa_fcs_vport.h @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_vport.h BFA fcs vport module public interface + */ + +#ifndef __BFA_FCS_VPORT_H__ +#define __BFA_FCS_VPORT_H__ + +#include <defs/bfa_defs_status.h> +#include <defs/bfa_defs_port.h> +#include <defs/bfa_defs_vport.h> +#include <fcs/bfa_fcs.h> +#include <fcb/bfa_fcb_vport.h> + +struct bfa_fcs_vport_s { + struct list_head qe; /* queue elem */ + bfa_sm_t sm; /* state machine */ + bfa_fcs_lport_t lport; /* logical port */ + struct bfa_timer_s timer; /* general purpose timer */ + struct bfad_vport_s *vport_drv; /* Driver private */ + struct bfa_vport_stats_s vport_stats; /* vport statistics */ + struct bfa_lps_s *lps; /* Lport login service */ + int fdisc_retries; +}; + +#define bfa_fcs_vport_get_port(vport) \ + ((struct bfa_fcs_port_s *)(&vport->port)) + +/** + * bfa fcs vport public functions + */ +bfa_status_t bfa_fcs_vport_create(struct bfa_fcs_vport_s *vport, + struct bfa_fcs_s *fcs, u16 vf_id, + struct bfa_port_cfg_s *port_cfg, + struct bfad_vport_s *vport_drv); +bfa_status_t bfa_fcs_vport_delete(struct bfa_fcs_vport_s *vport); +bfa_status_t bfa_fcs_vport_start(struct bfa_fcs_vport_s *vport); +bfa_status_t bfa_fcs_vport_stop(struct bfa_fcs_vport_s *vport); +void bfa_fcs_vport_get_attr(struct bfa_fcs_vport_s *vport, + struct bfa_vport_attr_s *vport_attr); +void bfa_fcs_vport_get_stats(struct bfa_fcs_vport_s *vport, + struct bfa_vport_stats_s *vport_stats); +void bfa_fcs_vport_clr_stats(struct bfa_fcs_vport_s *vport); +struct bfa_fcs_vport_s *bfa_fcs_vport_lookup(struct bfa_fcs_s *fcs, + u16 vf_id, wwn_t vpwwn); + +#endif /* __BFA_FCS_VPORT_H__ */ diff --git a/drivers/scsi/bfa/include/log/bfa_log_fcs.h b/drivers/scsi/bfa/include/log/bfa_log_fcs.h new file mode 100644 index 000000000000..b6f5df8827f8 --- /dev/null +++ b/drivers/scsi/bfa/include/log/bfa_log_fcs.h @@ -0,0 +1,28 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* + * messages define for FCS Module + */ +#ifndef __BFA_LOG_FCS_H__ +#define __BFA_LOG_FCS_H__ +#include <cs/bfa_log.h> +#define BFA_LOG_FCS_FABRIC_NOSWITCH \ + (((u32) BFA_LOG_FCS_ID << BFA_LOG_MODID_OFFSET) | 1) +#define BFA_LOG_FCS_FABRIC_ISOLATED \ + (((u32) BFA_LOG_FCS_ID << BFA_LOG_MODID_OFFSET) | 2) +#endif diff --git a/drivers/scsi/bfa/include/log/bfa_log_hal.h b/drivers/scsi/bfa/include/log/bfa_log_hal.h new file mode 100644 index 000000000000..0412aea2ec30 --- /dev/null +++ b/drivers/scsi/bfa/include/log/bfa_log_hal.h @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for HAL Module */ +#ifndef __BFA_LOG_HAL_H__ +#define __BFA_LOG_HAL_H__ +#include <cs/bfa_log.h> +#define BFA_LOG_HAL_ASSERT \ + (((u32) BFA_LOG_HAL_ID << BFA_LOG_MODID_OFFSET) | 1) +#define BFA_LOG_HAL_HEARTBEAT_FAILURE \ + (((u32) BFA_LOG_HAL_ID << BFA_LOG_MODID_OFFSET) | 2) +#define BFA_LOG_HAL_FCPIM_PARM_INVALID \ + (((u32) BFA_LOG_HAL_ID << BFA_LOG_MODID_OFFSET) | 3) +#define BFA_LOG_HAL_SM_ASSERT \ + (((u32) BFA_LOG_HAL_ID << BFA_LOG_MODID_OFFSET) | 4) +#endif diff --git a/drivers/scsi/bfa/include/log/bfa_log_linux.h b/drivers/scsi/bfa/include/log/bfa_log_linux.h new file mode 100644 index 000000000000..317c0547ee16 --- /dev/null +++ b/drivers/scsi/bfa/include/log/bfa_log_linux.h @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* messages define for LINUX Module */ +#ifndef __BFA_LOG_LINUX_H__ +#define __BFA_LOG_LINUX_H__ +#include <cs/bfa_log.h> +#define BFA_LOG_LINUX_DEVICE_CLAIMED \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 1) +#define BFA_LOG_LINUX_HASH_INIT_FAILED \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 2) +#define BFA_LOG_LINUX_SYSFS_FAILED \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 3) +#define BFA_LOG_LINUX_MEM_ALLOC_FAILED \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 4) +#define BFA_LOG_LINUX_DRIVER_REGISTRATION_FAILED \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 5) +#define BFA_LOG_LINUX_ITNIM_FREE \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 6) +#define BFA_LOG_LINUX_ITNIM_ONLINE \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 7) +#define BFA_LOG_LINUX_ITNIM_OFFLINE \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 8) +#define BFA_LOG_LINUX_SCSI_HOST_FREE \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 9) +#define BFA_LOG_LINUX_SCSI_ABORT \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 10) +#define BFA_LOG_LINUX_SCSI_ABORT_COMP \ + (((u32) BFA_LOG_LINUX_ID << BFA_LOG_MODID_OFFSET) | 11) +#endif diff --git a/drivers/scsi/bfa/include/log/bfa_log_wdrv.h b/drivers/scsi/bfa/include/log/bfa_log_wdrv.h new file mode 100644 index 000000000000..809a95f7afe2 --- /dev/null +++ b/drivers/scsi/bfa/include/log/bfa_log_wdrv.h @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/* + * messages define for WDRV Module + */ +#ifndef __BFA_LOG_WDRV_H__ +#define __BFA_LOG_WDRV_H__ +#include <cs/bfa_log.h> +#define BFA_LOG_WDRV_IOC_INIT_ERROR \ + (((u32) BFA_LOG_WDRV_ID << BFA_LOG_MODID_OFFSET) | 1) +#define BFA_LOG_WDRV_IOC_INTERNAL_ERROR \ + (((u32) BFA_LOG_WDRV_ID << BFA_LOG_MODID_OFFSET) | 2) +#define BFA_LOG_WDRV_IOC_START_ERROR \ + (((u32) BFA_LOG_WDRV_ID << BFA_LOG_MODID_OFFSET) | 3) +#define BFA_LOG_WDRV_IOC_STOP_ERROR \ + (((u32) BFA_LOG_WDRV_ID << BFA_LOG_MODID_OFFSET) | 4) +#define BFA_LOG_WDRV_INSUFFICIENT_RESOURCES \ + (((u32) BFA_LOG_WDRV_ID << BFA_LOG_MODID_OFFSET) | 5) +#define BFA_LOG_WDRV_BASE_ADDRESS_MAP_ERROR \ + (((u32) BFA_LOG_WDRV_ID << BFA_LOG_MODID_OFFSET) | 6) +#endif diff --git a/drivers/scsi/bfa/include/protocol/ct.h b/drivers/scsi/bfa/include/protocol/ct.h new file mode 100644 index 000000000000..c59d6630b070 --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/ct.h @@ -0,0 +1,492 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __CT_H__ +#define __CT_H__ + +#include <protocol/types.h> + +#pragma pack(1) + +struct ct_hdr_s{ + u32 rev_id:8; /* Revision of the CT */ + u32 in_id:24; /* Initiator Id */ + u32 gs_type:8; /* Generic service Type */ + u32 gs_sub_type:8; /* Generic service sub type */ + u32 options:8; /* options */ + u32 rsvrd:8; /* reserved */ + u32 cmd_rsp_code:16;/* ct command/response code */ + u32 max_res_size:16;/* maximum/residual size */ + u32 frag_id:8; /* fragment ID */ + u32 reason_code:8; /* reason code */ + u32 exp_code:8; /* explanation code */ + u32 vendor_unq:8; /* vendor unique */ +}; + +/* + * defines for the Revision + */ +enum { + CT_GS3_REVISION = 0x01, +}; + +/* + * defines for gs_type + */ +enum { + CT_GSTYPE_KEYSERVICE = 0xF7, + CT_GSTYPE_ALIASSERVICE = 0xF8, + CT_GSTYPE_MGMTSERVICE = 0xFA, + CT_GSTYPE_TIMESERVICE = 0xFB, + CT_GSTYPE_DIRSERVICE = 0xFC, +}; + +/* + * defines for gs_sub_type for gs type directory service + */ +enum { + CT_GSSUBTYPE_NAMESERVER = 0x02, +}; + +/* + * defines for gs_sub_type for gs type management service + */ +enum { + CT_GSSUBTYPE_CFGSERVER = 0x01, + CT_GSSUBTYPE_UNZONED_NS = 0x02, + CT_GSSUBTYPE_ZONESERVER = 0x03, + CT_GSSUBTYPE_LOCKSERVER = 0x04, + CT_GSSUBTYPE_HBA_MGMTSERVER = 0x10, /* for FDMI */ +}; + +/* + * defines for CT response code field + */ +enum { + CT_RSP_REJECT = 0x8001, + CT_RSP_ACCEPT = 0x8002, +}; + +/* + * defintions for CT reason code + */ +enum { + CT_RSN_INV_CMD = 0x01, + CT_RSN_INV_VER = 0x02, + CT_RSN_LOGIC_ERR = 0x03, + CT_RSN_INV_SIZE = 0x04, + CT_RSN_LOGICAL_BUSY = 0x05, + CT_RSN_PROTO_ERR = 0x07, + CT_RSN_UNABLE_TO_PERF = 0x09, + CT_RSN_NOT_SUPP = 0x0B, + CT_RSN_SERVER_NOT_AVBL = 0x0D, + CT_RSN_SESSION_COULD_NOT_BE_ESTBD = 0x0E, + CT_RSN_VENDOR_SPECIFIC = 0xFF, + +}; + +/* + * definitions for explanations code for Name server + */ +enum { + CT_NS_EXP_NOADDITIONAL = 0x00, + CT_NS_EXP_ID_NOT_REG = 0x01, + CT_NS_EXP_PN_NOT_REG = 0x02, + CT_NS_EXP_NN_NOT_REG = 0x03, + CT_NS_EXP_CS_NOT_REG = 0x04, + CT_NS_EXP_IPN_NOT_REG = 0x05, + CT_NS_EXP_IPA_NOT_REG = 0x06, + CT_NS_EXP_FT_NOT_REG = 0x07, + CT_NS_EXP_SPN_NOT_REG = 0x08, + CT_NS_EXP_SNN_NOT_REG = 0x09, + CT_NS_EXP_PT_NOT_REG = 0x0A, + CT_NS_EXP_IPP_NOT_REG = 0x0B, + CT_NS_EXP_FPN_NOT_REG = 0x0C, + CT_NS_EXP_HA_NOT_REG = 0x0D, + CT_NS_EXP_FD_NOT_REG = 0x0E, + CT_NS_EXP_FF_NOT_REG = 0x0F, + CT_NS_EXP_ACCESSDENIED = 0x10, + CT_NS_EXP_UNACCEPTABLE_ID = 0x11, + CT_NS_EXP_DATABASEEMPTY = 0x12, + CT_NS_EXP_NOT_REG_IN_SCOPE = 0x13, + CT_NS_EXP_DOM_ID_NOT_PRESENT = 0x14, + CT_NS_EXP_PORT_NUM_NOT_PRESENT = 0x15, + CT_NS_EXP_NO_DEVICE_ATTACHED = 0x16 +}; + +/* + * defintions for the explanation code for all servers + */ +enum { + CT_EXP_AUTH_EXCEPTION = 0xF1, + CT_EXP_DB_FULL = 0xF2, + CT_EXP_DB_EMPTY = 0xF3, + CT_EXP_PROCESSING_REQ = 0xF4, + CT_EXP_UNABLE_TO_VERIFY_CONN = 0xF5, + CT_EXP_DEVICES_NOT_IN_CMN_ZONE = 0xF6 +}; + +/* + * Command codes for Name server + */ +enum { + GS_GID_PN = 0x0121, /* Get Id on port name */ + GS_GPN_ID = 0x0112, /* Get port name on ID */ + GS_GNN_ID = 0x0113, /* Get node name on ID */ + GS_GID_FT = 0x0171, /* Get Id on FC4 type */ + GS_GSPN_ID = 0x0118, /* Get symbolic PN on ID */ + GS_RFT_ID = 0x0217, /* Register fc4type on ID */ + GS_RSPN_ID = 0x0218, /* Register symbolic PN on ID */ + GS_RPN_ID = 0x0212, /* Register port name */ + GS_RNN_ID = 0x0213, /* Register node name */ + GS_RCS_ID = 0x0214, /* Register class of service */ + GS_RPT_ID = 0x021A, /* Register port type */ + GS_GA_NXT = 0x0100, /* Get all next */ + GS_RFF_ID = 0x021F, /* Register FC4 Feature */ +}; + +struct fcgs_id_req_s{ + u32 rsvd:8; + u32 dap:24; /* port identifier */ +}; +#define fcgs_gpnid_req_t struct fcgs_id_req_s +#define fcgs_gnnid_req_t struct fcgs_id_req_s +#define fcgs_gspnid_req_t struct fcgs_id_req_s + +struct fcgs_gidpn_req_s{ + wwn_t port_name; /* port wwn */ +}; + +struct fcgs_gidpn_resp_s{ + u32 rsvd:8; + u32 dap:24; /* port identifier */ +}; + +/** + * RFT_ID + */ +struct fcgs_rftid_req_s { + u32 rsvd:8; + u32 dap:24; /* port identifier */ + u32 fc4_type[8]; /* fc4 types */ +}; + +/** + * RFF_ID : Register FC4 features. + */ + +#define FC_GS_FCP_FC4_FEATURE_INITIATOR 0x02 +#define FC_GS_FCP_FC4_FEATURE_TARGET 0x01 + +struct fcgs_rffid_req_s{ + u32 rsvd :8; + u32 dap :24; /* port identifier */ + u32 rsvd1 :16; + u32 fc4ftr_bits :8; /* fc4 feature bits */ + u32 fc4_type :8; /* corresponding FC4 Type */ +}; + +/** + * GID_FT Request + */ +struct fcgs_gidft_req_s{ + u8 reserved; + u8 domain_id; /* domain, 0 - all fabric */ + u8 area_id; /* area, 0 - whole domain */ + u8 fc4_type; /* FC_TYPE_FCP for SCSI devices */ +}; /* GID_FT Request */ + +/** + * GID_FT Response + */ +struct fcgs_gidft_resp_s { + u8 last:1; /* last port identifier flag */ + u8 reserved:7; + u32 pid:24; /* port identifier */ +}; /* GID_FT Response */ + +/** + * RSPN_ID + */ +struct fcgs_rspnid_req_s{ + u32 rsvd:8; + u32 dap:24; /* port identifier */ + u8 spn_len; /* symbolic port name length */ + u8 spn[256]; /* symbolic port name */ +}; + +/** + * RPN_ID + */ +struct fcgs_rpnid_req_s{ + u32 rsvd:8; + u32 port_id:24; + wwn_t port_name; +}; + +/** + * RNN_ID + */ +struct fcgs_rnnid_req_s{ + u32 rsvd:8; + u32 port_id:24; + wwn_t node_name; +}; + +/** + * RCS_ID + */ +struct fcgs_rcsid_req_s{ + u32 rsvd:8; + u32 port_id:24; + u32 cos; +}; + +/** + * RPT_ID + */ +struct fcgs_rptid_req_s{ + u32 rsvd:8; + u32 port_id:24; + u32 port_type:8; + u32 rsvd1:24; +}; + +/** + * GA_NXT Request + */ +struct fcgs_ganxt_req_s{ + u32 rsvd:8; + u32 port_id:24; +}; + +/** + * GA_NXT Response + */ +struct fcgs_ganxt_rsp_s{ + u32 port_type:8; /* Port Type */ + u32 port_id:24; /* Port Identifier */ + wwn_t port_name; /* Port Name */ + u8 spn_len; /* Length of Symbolic Port Name */ + char spn[255]; /* Symbolic Port Name */ + wwn_t node_name; /* Node Name */ + u8 snn_len; /* Length of Symbolic Node Name */ + char snn[255]; /* Symbolic Node Name */ + u8 ipa[8]; /* Initial Process Associator */ + u8 ip[16]; /* IP Address */ + u32 cos; /* Class of Service */ + u32 fc4types[8]; /* FC-4 TYPEs */ + wwn_t fabric_port_name; + /* Fabric Port Name */ + u32 rsvd:8; /* Reserved */ + u32 hard_addr:24; /* Hard Address */ +}; + +/* + * Fabric Config Server + */ + +/* + * Command codes for Fabric Configuration Server + */ +enum { + GS_FC_GFN_CMD = 0x0114, /* GS FC Get Fabric Name */ + GS_FC_GMAL_CMD = 0x0116, /* GS FC GMAL */ + GS_FC_TRACE_CMD = 0x0400, /* GS FC Trace Route */ + GS_FC_PING_CMD = 0x0401, /* GS FC Ping */ +}; + +/* + * Source or Destination Port Tags. + */ +enum { + GS_FTRACE_TAG_NPORT_ID = 1, + GS_FTRACE_TAG_NPORT_NAME = 2, +}; + +/* +* Port Value : Could be a Port id or wwn + */ +union fcgs_port_val_u{ + u32 nport_id; + wwn_t nport_wwn; +}; + +#define GS_FTRACE_MAX_HOP_COUNT 20 +#define GS_FTRACE_REVISION 1 + +/* + * Ftrace Related Structures. + */ + +/* + * STR (Switch Trace) Reject Reason Codes. From FC-SW. + */ +enum { + GS_FTRACE_STR_CMD_COMPLETED_SUCC = 0, + GS_FTRACE_STR_CMD_NOT_SUPP_IN_NEXT_SWITCH, + GS_FTRACE_STR_NO_RESP_FROM_NEXT_SWITCH, + GS_FTRACE_STR_MAX_HOP_CNT_REACHED, + GS_FTRACE_STR_SRC_PORT_NOT_FOUND, + GS_FTRACE_STR_DST_PORT_NOT_FOUND, + GS_FTRACE_STR_DEVICES_NOT_IN_COMMON_ZONE, + GS_FTRACE_STR_NO_ROUTE_BW_PORTS, + GS_FTRACE_STR_NO_ADDL_EXPLN, + GS_FTRACE_STR_FABRIC_BUSY, + GS_FTRACE_STR_FABRIC_BUILD_IN_PROGRESS, + GS_FTRACE_STR_VENDOR_SPECIFIC_ERR_START = 0xf0, + GS_FTRACE_STR_VENDOR_SPECIFIC_ERR_END = 0xff, +}; + +/* + * Ftrace Request + */ +struct fcgs_ftrace_req_s{ + u32 revision; + u16 src_port_tag; /* Source Port tag */ + u16 src_port_len; /* Source Port len */ + union fcgs_port_val_u src_port_val; /* Source Port value */ + u16 dst_port_tag; /* Destination Port tag */ + u16 dst_port_len; /* Destination Port len */ + union fcgs_port_val_u dst_port_val; /* Destination Port value */ + u32 token; + u8 vendor_id[8]; /* T10 Vendor Identifier */ + u8 vendor_info[8]; /* Vendor specific Info */ + u32 max_hop_cnt; /* Max Hop Count */ +}; + +/* + * Path info structure + */ +struct fcgs_ftrace_path_info_s{ + wwn_t switch_name; /* Switch WWN */ + u32 domain_id; + wwn_t ingress_port_name; /* Ingress ports wwn */ + u32 ingress_phys_port_num; /* Ingress ports physical port + * number + */ + wwn_t egress_port_name; /* Ingress ports wwn */ + u32 egress_phys_port_num; /* Ingress ports physical port + * number + */ +}; + +/* + * Ftrace Acc Response + */ +struct fcgs_ftrace_resp_s{ + u32 revision; + u32 token; + u8 vendor_id[8]; /* T10 Vendor Identifier */ + u8 vendor_info[8]; /* Vendor specific Info */ + u32 str_rej_reason_code; /* STR Reject Reason Code */ + u32 num_path_info_entries; /* No. of path info entries */ + /* + * path info entry/entries. + */ + struct fcgs_ftrace_path_info_s path_info[1]; + +}; + +/* +* Fabric Config Server : FCPing + */ + +/* + * FC Ping Request + */ +struct fcgs_fcping_req_s{ + u32 revision; + u16 port_tag; + u16 port_len; /* Port len */ + union fcgs_port_val_u port_val; /* Port value */ + u32 token; +}; + +/* + * FC Ping Response + */ +struct fcgs_fcping_resp_s{ + u32 token; +}; + +/* + * Command codes for zone server query. + */ +enum { + ZS_GZME = 0x0124, /* Get zone member extended */ +}; + +/* + * ZS GZME request + */ +#define ZS_GZME_ZNAMELEN 32 +struct zs_gzme_req_s{ + u8 znamelen; + u8 rsvd[3]; + u8 zname[ZS_GZME_ZNAMELEN]; +}; + +enum zs_mbr_type{ + ZS_MBR_TYPE_PWWN = 1, + ZS_MBR_TYPE_DOMPORT = 2, + ZS_MBR_TYPE_PORTID = 3, + ZS_MBR_TYPE_NWWN = 4, +}; + +struct zs_mbr_wwn_s{ + u8 mbr_type; + u8 rsvd[3]; + wwn_t wwn; +}; + +struct zs_query_resp_s{ + u32 nmbrs; /* number of zone members */ + struct zs_mbr_wwn_s mbr[1]; +}; + +/* + * GMAL Command ( Get ( interconnect Element) Management Address List) + * To retrieve the IP Address of a Switch. + */ + +#define CT_GMAL_RESP_PREFIX_TELNET "telnet://" +#define CT_GMAL_RESP_PREFIX_HTTP "http://" + +/* GMAL/GFN request */ +struct fcgs_req_s { + wwn_t wwn; /* PWWN/NWWN */ +}; + +#define fcgs_gmal_req_t struct fcgs_req_s +#define fcgs_gfn_req_t struct fcgs_req_s + +/* Accept Response to GMAL */ +struct fcgs_gmal_resp_s { + u32 ms_len; /* Num of entries */ + u8 ms_ma[256]; +}; + +struct fc_gmal_entry_s { + u8 len; + u8 prefix[7]; /* like "http://" */ + u8 ip_addr[248]; +}; + +#pragma pack() + +#endif diff --git a/drivers/scsi/bfa/include/protocol/fc.h b/drivers/scsi/bfa/include/protocol/fc.h new file mode 100644 index 000000000000..3e39ba58cfb5 --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/fc.h @@ -0,0 +1,1105 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __FC_H__ +#define __FC_H__ + +#include <protocol/types.h> + +#pragma pack(1) + +/* + * Fibre Channel Header Structure (FCHS) definition + */ +struct fchs_s { +#ifdef __BIGENDIAN + u32 routing:4; /* routing bits */ + u32 cat_info:4; /* category info */ +#else + u32 cat_info:4; /* category info */ + u32 routing:4; /* routing bits */ +#endif + u32 d_id:24; /* destination identifier */ + + u32 cs_ctl:8; /* class specific control */ + u32 s_id:24; /* source identifier */ + + u32 type:8; /* data structure type */ + u32 f_ctl:24; /* initial frame control */ + + u8 seq_id; /* sequence identifier */ + u8 df_ctl; /* data field control */ + u16 seq_cnt; /* sequence count */ + + u16 ox_id; /* originator exchange ID */ + u16 rx_id; /* responder exchange ID */ + + u32 ro; /* relative offset */ +}; +/* + * Fibre Channel BB_E Header Structure + */ +struct fcbbehs_s { + u16 ver_rsvd; + u32 rsvd[2]; + u32 rsvd__sof; +}; + +#define FC_SEQ_ID_MAX 256 + +/* + * routing bit definitions + */ +enum { + FC_RTG_FC4_DEV_DATA = 0x0, /* FC-4 Device Data */ + FC_RTG_EXT_LINK = 0x2, /* Extended Link Data */ + FC_RTG_FC4_LINK_DATA = 0x3, /* FC-4 Link Data */ + FC_RTG_VIDEO_DATA = 0x4, /* Video Data */ + FC_RTG_EXT_HDR = 0x5, /* VFT, IFR or Encapsuled */ + FC_RTG_BASIC_LINK = 0x8, /* Basic Link data */ + FC_RTG_LINK_CTRL = 0xC, /* Link Control */ +}; + +/* + * information category for extended link data and FC-4 Link Data + */ +enum { + FC_CAT_LD_REQUEST = 0x2, /* Request */ + FC_CAT_LD_REPLY = 0x3, /* Reply */ + FC_CAT_LD_DIAG = 0xF, /* for DIAG use only */ +}; + +/* + * information category for extended headers (VFT, IFR or encapsulation) + */ +enum { + FC_CAT_VFT_HDR = 0x0, /* Virtual fabric tagging header */ + FC_CAT_IFR_HDR = 0x1, /* Inter-Fabric routing header */ + FC_CAT_ENC_HDR = 0x2, /* Encapsulation header */ +}; + +/* + * information category for FC-4 device data + */ +enum { + FC_CAT_UNCATEG_INFO = 0x0, /* Uncategorized information */ + FC_CAT_SOLICIT_DATA = 0x1, /* Solicited Data */ + FC_CAT_UNSOLICIT_CTRL = 0x2, /* Unsolicited Control */ + FC_CAT_SOLICIT_CTRL = 0x3, /* Solicited Control */ + FC_CAT_UNSOLICIT_DATA = 0x4, /* Unsolicited Data */ + FC_CAT_DATA_DESC = 0x5, /* Data Descriptor */ + FC_CAT_UNSOLICIT_CMD = 0x6, /* Unsolicited Command */ + FC_CAT_CMD_STATUS = 0x7, /* Command Status */ +}; + +/* + * information category for Link Control + */ +enum { + FC_CAT_ACK_1 = 0x00, + FC_CAT_ACK_0_N = 0x01, + FC_CAT_P_RJT = 0x02, + FC_CAT_F_RJT = 0x03, + FC_CAT_P_BSY = 0x04, + FC_CAT_F_BSY_DATA = 0x05, + FC_CAT_F_BSY_LINK_CTL = 0x06, + FC_CAT_F_LCR = 0x07, + FC_CAT_NTY = 0x08, + FC_CAT_END = 0x09, +}; + +/* + * Type Field Definitions. FC-PH Section 18.5 pg. 165 + */ +enum { + FC_TYPE_BLS = 0x0, /* Basic Link Service */ + FC_TYPE_ELS = 0x1, /* Extended Link Service */ + FC_TYPE_IP = 0x5, /* IP */ + FC_TYPE_FCP = 0x8, /* SCSI-FCP */ + FC_TYPE_GPP = 0x9, /* SCSI_GPP */ + FC_TYPE_SERVICES = 0x20, /* Fibre Channel Services */ + FC_TYPE_FC_FSS = 0x22, /* Fabric Switch Services */ + FC_TYPE_FC_AL = 0x23, /* FC-AL */ + FC_TYPE_FC_SNMP = 0x24, /* FC-SNMP */ + FC_TYPE_MAX = 256, /* 256 FC-4 types */ +}; + +struct fc_fc4types_s{ + u8 bits[FC_TYPE_MAX / 8]; +}; + +/* + * Frame Control Definitions. FC-PH Table-45. pg. 168 + */ +enum { + FCTL_EC_ORIG = 0x000000, /* exchange originator */ + FCTL_EC_RESP = 0x800000, /* exchange responder */ + FCTL_SEQ_INI = 0x000000, /* sequence initiator */ + FCTL_SEQ_REC = 0x400000, /* sequence recipient */ + FCTL_FS_EXCH = 0x200000, /* first sequence of xchg */ + FCTL_LS_EXCH = 0x100000, /* last sequence of xchg */ + FCTL_END_SEQ = 0x080000, /* last frame of sequence */ + FCTL_SI_XFER = 0x010000, /* seq initiative transfer */ + FCTL_RO_PRESENT = 0x000008, /* relative offset present */ + FCTL_FILLBYTE_MASK = 0x000003 /* , fill byte mask */ +}; + +/* + * Fabric Well Known Addresses + */ +enum { + FC_MIN_WELL_KNOWN_ADDR = 0xFFFFF0, + FC_DOMAIN_CONTROLLER_MASK = 0xFFFC00, + FC_ALIAS_SERVER = 0xFFFFF8, + FC_MGMT_SERVER = 0xFFFFFA, + FC_TIME_SERVER = 0xFFFFFB, + FC_NAME_SERVER = 0xFFFFFC, + FC_FABRIC_CONTROLLER = 0xFFFFFD, + FC_FABRIC_PORT = 0xFFFFFE, + FC_BROADCAST_SERVER = 0xFFFFFF +}; + +/* + * domain/area/port defines + */ +#define FC_DOMAIN_MASK 0xFF0000 +#define FC_DOMAIN_SHIFT 16 +#define FC_AREA_MASK 0x00FF00 +#define FC_AREA_SHIFT 8 +#define FC_PORT_MASK 0x0000FF +#define FC_PORT_SHIFT 0 + +#define FC_GET_DOMAIN(p) (((p) & FC_DOMAIN_MASK) >> FC_DOMAIN_SHIFT) +#define FC_GET_AREA(p) (((p) & FC_AREA_MASK) >> FC_AREA_SHIFT) +#define FC_GET_PORT(p) (((p) & FC_PORT_MASK) >> FC_PORT_SHIFT) + +#define FC_DOMAIN_CTRLR(p) (FC_DOMAIN_CONTROLLER_MASK | (FC_GET_DOMAIN(p))) + +enum { + FC_RXID_ANY = 0xFFFFU, +}; + +/* + * generic ELS command + */ +struct fc_els_cmd_s{ + u32 els_code:8; /* ELS Command Code */ + u32 reserved:24; +}; + +/* + * ELS Command Codes. FC-PH Table-75. pg. 223 + */ +enum { + FC_ELS_LS_RJT = 0x1, /* Link Service Reject. */ + FC_ELS_ACC = 0x02, /* Accept */ + FC_ELS_PLOGI = 0x03, /* N_Port Login. */ + FC_ELS_FLOGI = 0x04, /* F_Port Login. */ + FC_ELS_LOGO = 0x05, /* Logout. */ + FC_ELS_ABTX = 0x06, /* Abort Exchange */ + FC_ELS_RES = 0x08, /* Read Exchange status */ + FC_ELS_RSS = 0x09, /* Read sequence status block */ + FC_ELS_RSI = 0x0A, /* Request Sequence Initiative */ + FC_ELS_ESTC = 0x0C, /* Estimate Credit. */ + FC_ELS_RTV = 0x0E, /* Read Timeout Value. */ + FC_ELS_RLS = 0x0F, /* Read Link Status. */ + FC_ELS_ECHO = 0x10, /* Echo */ + FC_ELS_TEST = 0x11, /* Test */ + FC_ELS_RRQ = 0x12, /* Reinstate Recovery Qualifier. */ + FC_ELS_REC = 0x13, /* Add this for TAPE support in FCR */ + FC_ELS_PRLI = 0x20, /* Process Login */ + FC_ELS_PRLO = 0x21, /* Process Logout. */ + FC_ELS_SCN = 0x22, /* State Change Notification. */ + FC_ELS_TPRLO = 0x24, /* Third Party Process Logout. */ + FC_ELS_PDISC = 0x50, /* Discover N_Port Parameters. */ + FC_ELS_FDISC = 0x51, /* Discover F_Port Parameters. */ + FC_ELS_ADISC = 0x52, /* Discover Address. */ + FC_ELS_FAN = 0x60, /* Fabric Address Notification */ + FC_ELS_RSCN = 0x61, /* Reg State Change Notification */ + FC_ELS_SCR = 0x62, /* State Change Registration. */ + FC_ELS_RTIN = 0x77, /* Mangement server request */ + FC_ELS_RNID = 0x78, /* Mangement server request */ + FC_ELS_RLIR = 0x79, /* Registered Link Incident Record */ + + FC_ELS_RPSC = 0x7D, /* Report Port Speed Capabilities */ + FC_ELS_QSA = 0x7E, /* Query Security Attributes. Ref FC-SP */ + FC_ELS_E2E_LBEACON = 0x81, + /* End-to-End Link Beacon */ + FC_ELS_AUTH = 0x90, /* Authentication. Ref FC-SP */ + FC_ELS_RFCN = 0x97, /* Request Fabric Change Notification. Ref + *FC-SP */ + +}; + +/* + * Version numbers for FC-PH standards, + * used in login to indicate what port + * supports. See FC-PH-X table 158. + */ +enum { + FC_PH_VER_4_3 = 0x09, + FC_PH_VER_PH_3 = 0x20, +}; + +/* + * PDU size defines + */ +enum { + FC_MIN_PDUSZ = 512, + FC_MAX_PDUSZ = 2112, +}; + +/* + * N_Port PLOGI Common Service Parameters. + * FC-PH-x. Figure-76. pg. 308. + */ +struct fc_plogi_csp_s{ + u8 verhi; /* FC-PH high version */ + u8 verlo; /* FC-PH low version */ + u16 bbcred; /* BB_Credit */ + +#ifdef __BIGENDIAN + u8 ciro:1, /* continuously increasing RO */ + rro:1, /* random relative offset */ + npiv_supp:1, /* NPIV supported */ + port_type:1, /* N_Port/F_port */ + altbbcred:1, /* alternate BB_Credit */ + resolution:1, /* ms/ns ED_TOV resolution */ + vvl_info:1, /* VVL Info included */ + reserved1:1; + + u8 hg_supp:1, + query_dbc:1, + security:1, + sync_cap:1, + r_t_tov:1, + dh_dup_supp:1, + cisc:1, /* continuously increasing seq count */ + payload:1; +#else + u8 reserved2:2, + resolution:1, /* ms/ns ED_TOV resolution */ + altbbcred:1, /* alternate BB_Credit */ + port_type:1, /* N_Port/F_port */ + npiv_supp:1, /* NPIV supported */ + rro:1, /* random relative offset */ + ciro:1; /* continuously increasing RO */ + + u8 payload:1, + cisc:1, /* continuously increasing seq count */ + dh_dup_supp:1, + r_t_tov:1, + sync_cap:1, + security:1, + query_dbc:1, + hg_supp:1; +#endif + + u16 rxsz; /* recieve data_field size */ + + u16 conseq; + u16 ro_bitmap; + + u32 e_d_tov; +}; + +/* + * N_Port PLOGI Class Specific Parameters. + * FC-PH-x. Figure 78. pg. 318. + */ +struct fc_plogi_clp_s{ +#ifdef __BIGENDIAN + u32 class_valid:1; + u32 intermix:1; /* class intermix supported if set =1. + * valid only for class1. Reserved for + * class2 & class3 + */ + u32 reserved1:2; + u32 sequential:1; + u32 reserved2:3; +#else + u32 reserved2:3; + u32 sequential:1; + u32 reserved1:2; + u32 intermix:1; /* class intermix supported if set =1. + * valid only for class1. Reserved for + * class2 & class3 + */ + u32 class_valid:1; +#endif + + u32 reserved3:24; + + u32 reserved4:16; + u32 rxsz:16; /* Receive data_field size */ + + u32 reserved5:8; + u32 conseq:8; + u32 e2e_credit:16; /* end to end credit */ + + u32 reserved7:8; + u32 ospx:8; + u32 reserved8:16; +}; + +#define FLOGI_VVL_BRCD 0x42524344 /* ASCII value for each character in + * string "BRCD" */ + +/* + * PLOGI els command and reply payload + */ +struct fc_logi_s{ + struct fc_els_cmd_s els_cmd; /* ELS command code */ + struct fc_plogi_csp_s csp; /* common service params */ + wwn_t port_name; + wwn_t node_name; + struct fc_plogi_clp_s class1; /* class 1 service parameters */ + struct fc_plogi_clp_s class2; /* class 2 service parameters */ + struct fc_plogi_clp_s class3; /* class 3 service parameters */ + struct fc_plogi_clp_s class4; /* class 4 service parameters */ + u8 vvl[16]; /* vendor version level */ +}; + +/* + * LOGO els command payload + */ +struct fc_logo_s{ + struct fc_els_cmd_s els_cmd; /* ELS command code */ + u32 res1:8; + u32 nport_id:24; /* N_Port identifier of source */ + wwn_t orig_port_name; /* Port name of the LOGO originator */ +}; + +/* + * ADISC els command payload + */ +struct fc_adisc_s { + struct fc_els_cmd_s els_cmd; /* ELS command code */ + u32 res1:8; + u32 orig_HA:24; /* originator hard address */ + wwn_t orig_port_name; /* originator port name */ + wwn_t orig_node_name; /* originator node name */ + u32 res2:8; + u32 nport_id:24; /* originator NPortID */ +}; + +/* + * Exchange status block + */ +struct fc_exch_status_blk_s{ + u32 oxid:16; + u32 rxid:16; + u32 res1:8; + u32 orig_np:24; /* originator NPortID */ + u32 res2:8; + u32 resp_np:24; /* responder NPortID */ + u32 es_bits; + u32 res3; + /* + * un modified section of the fields + */ +}; + +/* + * RES els command payload + */ +struct fc_res_s { + struct fc_els_cmd_s els_cmd; /* ELS command code */ + u32 res1:8; + u32 nport_id:24; /* N_Port identifier of source */ + u32 oxid:16; + u32 rxid:16; + u8 assoc_hdr[32]; +}; + +/* + * RES els accept payload + */ +struct fc_res_acc_s{ + struct fc_els_cmd_s els_cmd; /* ELS command code */ + struct fc_exch_status_blk_s fc_exch_blk; /* Exchange status block */ +}; + +/* + * REC els command payload + */ +struct fc_rec_s { + struct fc_els_cmd_s els_cmd; /* ELS command code */ + u32 res1:8; + u32 nport_id:24; /* N_Port identifier of source */ + u32 oxid:16; + u32 rxid:16; +}; + +#define FC_REC_ESB_OWN_RSP 0x80000000 /* responder owns */ +#define FC_REC_ESB_SI 0x40000000 /* SI is owned */ +#define FC_REC_ESB_COMP 0x20000000 /* exchange is complete */ +#define FC_REC_ESB_ENDCOND_ABN 0x10000000 /* abnormal ending */ +#define FC_REC_ESB_RQACT 0x04000000 /* recovery qual active */ +#define FC_REC_ESB_ERRP_MSK 0x03000000 +#define FC_REC_ESB_OXID_INV 0x00800000 /* invalid OXID */ +#define FC_REC_ESB_RXID_INV 0x00400000 /* invalid RXID */ +#define FC_REC_ESB_PRIO_INUSE 0x00200000 + +/* + * REC els accept payload + */ +struct fc_rec_acc_s { + struct fc_els_cmd_s els_cmd; /* ELS command code */ + u32 oxid:16; + u32 rxid:16; + u32 res1:8; + u32 orig_id:24; /* N_Port id of exchange originator */ + u32 res2:8; + u32 resp_id:24; /* N_Port id of exchange responder */ + u32 count; /* data transfer count */ + u32 e_stat; /* exchange status */ +}; + +/* + * RSI els payload + */ +struct fc_rsi_s { + struct fc_els_cmd_s els_cmd; + u32 res1:8; + u32 orig_sid:24; + u32 oxid:16; + u32 rxid:16; +}; + +/* + * structure for PRLI paramater pages, both request & response + * see FC-PH-X table 113 & 115 for explanation also FCP table 8 + */ +struct fc_prli_params_s{ + u32 reserved: 16; +#ifdef __BIGENDIAN + u32 reserved1: 5; + u32 rec_support : 1; + u32 task_retry_id : 1; + u32 retry : 1; + + u32 confirm : 1; + u32 doverlay:1; + u32 initiator:1; + u32 target:1; + u32 cdmix:1; + u32 drmix:1; + u32 rxrdisab:1; + u32 wxrdisab:1; +#else + u32 retry : 1; + u32 task_retry_id : 1; + u32 rec_support : 1; + u32 reserved1: 5; + + u32 wxrdisab:1; + u32 rxrdisab:1; + u32 drmix:1; + u32 cdmix:1; + u32 target:1; + u32 initiator:1; + u32 doverlay:1; + u32 confirm : 1; +#endif +}; + +/* + * valid values for rspcode in PRLI ACC payload + */ +enum { + FC_PRLI_ACC_XQTD = 0x1, /* request executed */ + FC_PRLI_ACC_PREDEF_IMG = 0x5, /* predefined image - no prli needed */ +}; + +struct fc_prli_params_page_s{ + u32 type:8; + u32 codext:8; +#ifdef __BIGENDIAN + u32 origprocasv:1; + u32 rsppav:1; + u32 imagepair:1; + u32 reserved1:1; + u32 rspcode:4; +#else + u32 rspcode:4; + u32 reserved1:1; + u32 imagepair:1; + u32 rsppav:1; + u32 origprocasv:1; +#endif + u32 reserved2:8; + + u32 origprocas; + u32 rspprocas; + struct fc_prli_params_s servparams; +}; + +/* + * PRLI request and accept payload, FC-PH-X tables 112 & 114 + */ +struct fc_prli_s{ + u32 command:8; + u32 pglen:8; + u32 pagebytes:16; + struct fc_prli_params_page_s parampage; +}; + +/* + * PRLO logout params page + */ +struct fc_prlo_params_page_s{ + u32 type:8; + u32 type_ext:8; +#ifdef __BIGENDIAN + u32 opa_valid:1; /* originator process associator + * valid + */ + u32 rpa_valid:1; /* responder process associator valid */ + u32 res1:14; +#else + u32 res1:14; + u32 rpa_valid:1; /* responder process associator valid */ + u32 opa_valid:1; /* originator process associator + * valid + */ +#endif + u32 orig_process_assc; + u32 resp_process_assc; + + u32 res2; +}; + +/* + * PRLO els command payload + */ +struct fc_prlo_s{ + u32 command:8; + u32 page_len:8; + u32 payload_len:16; + struct fc_prlo_params_page_s prlo_params[1]; +}; + +/* + * PRLO Logout response parameter page + */ +struct fc_prlo_acc_params_page_s{ + u32 type:8; + u32 type_ext:8; + +#ifdef __BIGENDIAN + u32 opa_valid:1; /* originator process associator + * valid + */ + u32 rpa_valid:1; /* responder process associator valid */ + u32 res1:14; +#else + u32 res1:14; + u32 rpa_valid:1; /* responder process associator valid */ + u32 opa_valid:1; /* originator process associator + * valid + */ +#endif + u32 orig_process_assc; + u32 resp_process_assc; + + u32 fc4type_csp; +}; + +/* + * PRLO els command ACC payload + */ +struct fc_prlo_acc_s{ + u32 command:8; + u32 page_len:8; + u32 payload_len:16; + struct fc_prlo_acc_params_page_s prlo_acc_params[1]; +}; + +/* + * SCR els command payload + */ +enum { + FC_SCR_REG_FUNC_FABRIC_DETECTED = 0x01, + FC_SCR_REG_FUNC_N_PORT_DETECTED = 0x02, + FC_SCR_REG_FUNC_FULL = 0x03, + FC_SCR_REG_FUNC_CLEAR_REG = 0xFF, +}; + +/* SCR VU registrations */ +enum { + FC_VU_SCR_REG_FUNC_FABRIC_NAME_CHANGE = 0x01 +}; + +struct fc_scr_s{ + u32 command:8; + u32 res:24; + u32 vu_reg_func:8; /* Vendor Unique Registrations */ + u32 res1:16; + u32 reg_func:8; +}; + +/* + * Information category for Basic link data + */ +enum { + FC_CAT_NOP = 0x0, + FC_CAT_ABTS = 0x1, + FC_CAT_RMC = 0x2, + FC_CAT_BA_ACC = 0x4, + FC_CAT_BA_RJT = 0x5, + FC_CAT_PRMT = 0x6, +}; + +/* + * LS_RJT els reply payload + */ +struct fc_ls_rjt_s { + struct fc_els_cmd_s els_cmd; /* ELS command code */ + u32 res1:8; + u32 reason_code:8; /* Reason code for reject */ + u32 reason_code_expl:8; /* Reason code explanation */ + u32 vendor_unique:8; /* Vendor specific */ +}; + +/* + * LS_RJT reason codes + */ +enum { + FC_LS_RJT_RSN_INV_CMD_CODE = 0x01, + FC_LS_RJT_RSN_LOGICAL_ERROR = 0x03, + FC_LS_RJT_RSN_LOGICAL_BUSY = 0x05, + FC_LS_RJT_RSN_PROTOCOL_ERROR = 0x07, + FC_LS_RJT_RSN_UNABLE_TO_PERF_CMD = 0x09, + FC_LS_RJT_RSN_CMD_NOT_SUPP = 0x0B, +}; + +/* + * LS_RJT reason code explanation + */ +enum { + FC_LS_RJT_EXP_NO_ADDL_INFO = 0x00, + FC_LS_RJT_EXP_SPARMS_ERR_OPTIONS = 0x01, + FC_LS_RJT_EXP_SPARMS_ERR_INI_CTL = 0x03, + FC_LS_RJT_EXP_SPARMS_ERR_REC_CTL = 0x05, + FC_LS_RJT_EXP_SPARMS_ERR_RXSZ = 0x07, + FC_LS_RJT_EXP_SPARMS_ERR_CONSEQ = 0x09, + FC_LS_RJT_EXP_SPARMS_ERR_CREDIT = 0x0B, + FC_LS_RJT_EXP_INV_PORT_NAME = 0x0D, + FC_LS_RJT_EXP_INV_NODE_FABRIC_NAME = 0x0E, + FC_LS_RJT_EXP_INV_CSP = 0x0F, + FC_LS_RJT_EXP_INV_ASSOC_HDR = 0x11, + FC_LS_RJT_EXP_ASSOC_HDR_REQD = 0x13, + FC_LS_RJT_EXP_INV_ORIG_S_ID = 0x15, + FC_LS_RJT_EXP_INV_OXID_RXID_COMB = 0x17, + FC_LS_RJT_EXP_CMD_ALREADY_IN_PROG = 0x19, + FC_LS_RJT_EXP_LOGIN_REQUIRED = 0x1E, + FC_LS_RJT_EXP_INVALID_NPORT_ID = 0x1F, + FC_LS_RJT_EXP_INSUFF_RES = 0x29, + FC_LS_RJT_EXP_CMD_NOT_SUPP = 0x2C, + FC_LS_RJT_EXP_INV_PAYLOAD_LEN = 0x2D, +}; + +/* + * RRQ els command payload + */ +struct fc_rrq_s{ + struct fc_els_cmd_s els_cmd; /* ELS command code */ + u32 res1:8; + u32 s_id:24; /* exchange originator S_ID */ + + u32 ox_id:16; /* originator exchange ID */ + u32 rx_id:16; /* responder exchange ID */ + + u32 res2[8]; /* optional association header */ +}; + +/* + * ABTS BA_ACC reply payload + */ +struct fc_ba_acc_s{ + u32 seq_id_valid:8; /* set to 0x00 for Abort Exchange */ + u32 seq_id:8; /* invalid for Abort Exchange */ + u32 res2:16; + u32 ox_id:16; /* OX_ID from ABTS frame */ + u32 rx_id:16; /* RX_ID from ABTS frame */ + u32 low_seq_cnt:16; /* set to 0x0000 for Abort Exchange */ + u32 high_seq_cnt:16;/* set to 0xFFFF for Abort Exchange */ +}; + +/* + * ABTS BA_RJT reject payload + */ +struct fc_ba_rjt_s{ + u32 res1:8; /* Reserved */ + u32 reason_code:8; /* reason code for reject */ + u32 reason_expl:8; /* reason code explanation */ + u32 vendor_unique:8;/* vendor unique reason code,set to 0 */ +}; + +/* + * TPRLO logout parameter page + */ +struct fc_tprlo_params_page_s{ + u32 type:8; + u32 type_ext:8; + +#ifdef __BIGENDIAN + u32 opa_valid:1; + u32 rpa_valid:1; + u32 tpo_nport_valid:1; + u32 global_process_logout:1; + u32 res1:12; +#else + u32 res1:12; + u32 global_process_logout:1; + u32 tpo_nport_valid:1; + u32 rpa_valid:1; + u32 opa_valid:1; +#endif + + u32 orig_process_assc; + u32 resp_process_assc; + + u32 res2:8; + u32 tpo_nport_id; +}; + +/* + * TPRLO ELS command payload + */ +struct fc_tprlo_s{ + u32 command:8; + u32 page_len:8; + u32 payload_len:16; + + struct fc_tprlo_params_page_s tprlo_params[1]; +}; + +enum fc_tprlo_type{ + FC_GLOBAL_LOGO = 1, + FC_TPR_LOGO +}; + +/* + * TPRLO els command ACC payload + */ +struct fc_tprlo_acc_s{ + u32 command:8; + u32 page_len:8; + u32 payload_len:16; + struct fc_prlo_acc_params_page_s tprlo_acc_params[1]; +}; + +/* + * RSCN els command req payload + */ +#define FC_RSCN_PGLEN 0x4 + +enum fc_rscn_format{ + FC_RSCN_FORMAT_PORTID = 0x0, + FC_RSCN_FORMAT_AREA = 0x1, + FC_RSCN_FORMAT_DOMAIN = 0x2, + FC_RSCN_FORMAT_FABRIC = 0x3, +}; + +struct fc_rscn_event_s{ + u32 format:2; + u32 qualifier:4; + u32 resvd:2; + u32 portid:24; +}; + +struct fc_rscn_pl_s{ + u8 command; + u8 pagelen; + u16 payldlen; + struct fc_rscn_event_s event[1]; +}; + +/* + * ECHO els command req payload + */ +struct fc_echo_s { + struct fc_els_cmd_s els_cmd; +}; + +/* + * RNID els command + */ + +#define RNID_NODEID_DATA_FORMAT_COMMON 0x00 +#define RNID_NODEID_DATA_FORMAT_FCP3 0x08 +#define RNID_NODEID_DATA_FORMAT_DISCOVERY 0xDF + +#define RNID_ASSOCIATED_TYPE_UNKNOWN 0x00000001 +#define RNID_ASSOCIATED_TYPE_OTHER 0x00000002 +#define RNID_ASSOCIATED_TYPE_HUB 0x00000003 +#define RNID_ASSOCIATED_TYPE_SWITCH 0x00000004 +#define RNID_ASSOCIATED_TYPE_GATEWAY 0x00000005 +#define RNID_ASSOCIATED_TYPE_STORAGE_DEVICE 0x00000009 +#define RNID_ASSOCIATED_TYPE_HOST 0x0000000A +#define RNID_ASSOCIATED_TYPE_STORAGE_SUBSYSTEM 0x0000000B +#define RNID_ASSOCIATED_TYPE_STORAGE_ACCESS_DEVICE 0x0000000E +#define RNID_ASSOCIATED_TYPE_NAS_SERVER 0x00000011 +#define RNID_ASSOCIATED_TYPE_BRIDGE 0x00000002 +#define RNID_ASSOCIATED_TYPE_VIRTUALIZATION_DEVICE 0x00000003 +#define RNID_ASSOCIATED_TYPE_MULTI_FUNCTION_DEVICE 0x000000FF + +/* + * RNID els command payload + */ +struct fc_rnid_cmd_s{ + struct fc_els_cmd_s els_cmd; + u32 node_id_data_format:8; + u32 reserved:24; +}; + +/* + * RNID els response payload + */ + +struct fc_rnid_common_id_data_s{ + wwn_t port_name; + wwn_t node_name; +}; + +struct fc_rnid_general_topology_data_s{ + u32 vendor_unique[4]; + u32 asso_type; + u32 phy_port_num; + u32 num_attached_nodes; + u32 node_mgmt:8; + u32 ip_version:8; + u32 udp_tcp_port_num:16; + u32 ip_address[4]; + u32 reserved:16; + u32 vendor_specific:16; +}; + +struct fc_rnid_acc_s{ + struct fc_els_cmd_s els_cmd; + u32 node_id_data_format:8; + u32 common_id_data_length:8; + u32 reserved:8; + u32 specific_id_data_length:8; + struct fc_rnid_common_id_data_s common_id_data; + struct fc_rnid_general_topology_data_s gen_topology_data; +}; + +#define RNID_ASSOCIATED_TYPE_UNKNOWN 0x00000001 +#define RNID_ASSOCIATED_TYPE_OTHER 0x00000002 +#define RNID_ASSOCIATED_TYPE_HUB 0x00000003 +#define RNID_ASSOCIATED_TYPE_SWITCH 0x00000004 +#define RNID_ASSOCIATED_TYPE_GATEWAY 0x00000005 +#define RNID_ASSOCIATED_TYPE_STORAGE_DEVICE 0x00000009 +#define RNID_ASSOCIATED_TYPE_HOST 0x0000000A +#define RNID_ASSOCIATED_TYPE_STORAGE_SUBSYSTEM 0x0000000B +#define RNID_ASSOCIATED_TYPE_STORAGE_ACCESS_DEVICE 0x0000000E +#define RNID_ASSOCIATED_TYPE_NAS_SERVER 0x00000011 +#define RNID_ASSOCIATED_TYPE_BRIDGE 0x00000002 +#define RNID_ASSOCIATED_TYPE_VIRTUALIZATION_DEVICE 0x00000003 +#define RNID_ASSOCIATED_TYPE_MULTI_FUNCTION_DEVICE 0x000000FF + +enum fc_rpsc_speed_cap{ + RPSC_SPEED_CAP_1G = 0x8000, + RPSC_SPEED_CAP_2G = 0x4000, + RPSC_SPEED_CAP_4G = 0x2000, + RPSC_SPEED_CAP_10G = 0x1000, + RPSC_SPEED_CAP_8G = 0x0800, + RPSC_SPEED_CAP_16G = 0x0400, + + RPSC_SPEED_CAP_UNKNOWN = 0x0001, +}; + +enum fc_rpsc_op_speed_s{ + RPSC_OP_SPEED_1G = 0x8000, + RPSC_OP_SPEED_2G = 0x4000, + RPSC_OP_SPEED_4G = 0x2000, + RPSC_OP_SPEED_10G = 0x1000, + RPSC_OP_SPEED_8G = 0x0800, + RPSC_OP_SPEED_16G = 0x0400, + + RPSC_OP_SPEED_NOT_EST = 0x0001, /*! speed not established */ +}; + +struct fc_rpsc_speed_info_s{ + u16 port_speed_cap; /*! see fc_rpsc_speed_cap_t */ + u16 port_op_speed; /*! see fc_rpsc_op_speed_t */ +}; + +enum link_e2e_beacon_subcmd{ + LINK_E2E_BEACON_ON = 1, + LINK_E2E_BEACON_OFF = 2 +}; + +enum beacon_type{ + BEACON_TYPE_NORMAL = 1, /*! Normal Beaconing. Green */ + BEACON_TYPE_WARN = 2, /*! Warning Beaconing. Yellow/Amber */ + BEACON_TYPE_CRITICAL = 3 /*! Critical Beaconing. Red */ +}; + +struct link_e2e_beacon_param_s { + u8 beacon_type; /* Beacon Type. See beacon_type_t */ + u8 beacon_frequency; + /* Beacon frequency. Number of blinks + * per 10 seconds + */ + u16 beacon_duration;/* Beacon duration (in Seconds). The + * command operation should be + * terminated at the end of this + * timeout value. + * + * Ignored if diag_sub_cmd is + * LINK_E2E_BEACON_OFF. + * + * If 0, beaconing will continue till a + * BEACON OFF request is received + */ +}; + +/* + * Link E2E beacon request/good response format. For LS_RJTs use fc_ls_rjt_t + */ +struct link_e2e_beacon_req_s{ + u32 ls_code; /*! FC_ELS_E2E_LBEACON in requests * + *or FC_ELS_ACC in good replies */ + u32 ls_sub_cmd; /*! See link_e2e_beacon_subcmd_t */ + struct link_e2e_beacon_param_s beacon_parm; +}; + +/** + * If RPSC request is sent to the Domain Controller, the request is for + * all the ports within that domain (TODO - I don't think FOS implements + * this...). + */ +struct fc_rpsc_cmd_s{ + struct fc_els_cmd_s els_cmd; +}; + +/* + * RPSC Acc + */ +struct fc_rpsc_acc_s{ + u32 command:8; + u32 rsvd:8; + u32 num_entries:16; + + struct fc_rpsc_speed_info_s speed_info[1]; +}; + +/** + * If RPSC2 request is sent to the Domain Controller, + */ +#define FC_BRCD_TOKEN 0x42524344 + +struct fc_rpsc2_cmd_s{ + struct fc_els_cmd_s els_cmd; + u32 token; + u16 resvd; + u16 num_pids; /* Number of pids in the request */ + struct { + u32 rsvd1:8; + u32 pid:24; /* port identifier */ + } pid_list[1]; +}; + +enum fc_rpsc2_port_type{ + RPSC2_PORT_TYPE_UNKNOWN = 0, + RPSC2_PORT_TYPE_NPORT = 1, + RPSC2_PORT_TYPE_NLPORT = 2, + RPSC2_PORT_TYPE_NPIV_PORT = 0x5f, + RPSC2_PORT_TYPE_NPORT_TRUNK = 0x6f, +}; + +/* + * RPSC2 portInfo entry structure + */ +struct fc_rpsc2_port_info_s{ + u32 pid; /* PID */ + u16 resvd1; + u16 index; /* port number / index */ + u8 resvd2; + u8 type; /* port type N/NL/... */ + u16 speed; /* port Operating Speed */ +}; + +/* + * RPSC2 Accept payload + */ +struct fc_rpsc2_acc_s{ + u8 els_cmd; + u8 resvd; + u16 num_pids; /* Number of pids in the request */ + struct fc_rpsc2_port_info_s port_info[1]; /* port information */ +}; + +/** + * bit fields so that multiple classes can be specified + */ +enum fc_cos{ + FC_CLASS_2 = 0x04, + FC_CLASS_3 = 0x08, + FC_CLASS_2_3 = 0x0C, +}; + +/* + * symbolic name + */ +struct fc_symname_s{ + u8 symname[FC_SYMNAME_MAX]; +}; + +struct fc_alpabm_s{ + u8 alpa_bm[FC_ALPA_MAX / 8]; +}; + +/* + * protocol default timeout values + */ +#define FC_ED_TOV 2 +#define FC_REC_TOV (FC_ED_TOV + 1) +#define FC_RA_TOV 10 +#define FC_ELS_TOV (2 * FC_RA_TOV) + +/* + * virtual fabric related defines + */ +#define FC_VF_ID_NULL 0 /* must not be used as VF_ID */ +#define FC_VF_ID_MIN 1 +#define FC_VF_ID_MAX 0xEFF +#define FC_VF_ID_CTL 0xFEF /* control VF_ID */ + +/** + * Virtual Fabric Tagging header format + * @caution This is defined only in BIG ENDIAN format. + */ +struct fc_vft_s{ + u32 r_ctl:8; + u32 ver:2; + u32 type:4; + u32 res_a:2; + u32 priority:3; + u32 vf_id:12; + u32 res_b:1; + u32 hopct:8; + u32 res_c:24; +}; + +#pragma pack() + +#endif diff --git a/drivers/scsi/bfa/include/protocol/fc_sp.h b/drivers/scsi/bfa/include/protocol/fc_sp.h new file mode 100644 index 000000000000..55bb0b31d04b --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/fc_sp.h @@ -0,0 +1,224 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __FC_SP_H__ +#define __FC_SP_H__ + +#include <protocol/types.h> + +#pragma pack(1) + +enum auth_els_flags{ + FC_AUTH_ELS_MORE_FRAGS_FLAG = 0x80, /*! bit-7. More Fragments + * Follow + */ + FC_AUTH_ELS_CONCAT_FLAG = 0x40, /*! bit-6. Concatenation Flag */ + FC_AUTH_ELS_SEQ_NUM_FLAG = 0x01 /*! bit-0. Sequence Number */ +}; + +enum auth_msg_codes{ + FC_AUTH_MC_AUTH_RJT = 0x0A, /*! Auth Reject */ + FC_AUTH_MC_AUTH_NEG = 0x0B, /*! Auth Negotiate */ + FC_AUTH_MC_AUTH_DONE = 0x0C, /*! Auth Done */ + + FC_AUTH_MC_DHCHAP_CHAL = 0x10, /*! DHCHAP Challenge */ + FC_AUTH_MC_DHCHAP_REPLY = 0x11, /*! DHCHAP Reply */ + FC_AUTH_MC_DHCHAP_SUCC = 0x12, /*! DHCHAP Success */ + + FC_AUTH_MC_FCAP_REQ = 0x13, /*! FCAP Request */ + FC_AUTH_MC_FCAP_ACK = 0x14, /*! FCAP Acknowledge */ + FC_AUTH_MC_FCAP_CONF = 0x15, /*! FCAP Confirm */ + + FC_AUTH_MC_FCPAP_INIT = 0x16, /*! FCPAP Init */ + FC_AUTH_MC_FCPAP_ACC = 0x17, /*! FCPAP Accept */ + FC_AUTH_MC_FCPAP_COMP = 0x18, /*! FCPAP Complete */ + + FC_AUTH_MC_IKE_SA_INIT = 0x22, /*! IKE SA INIT */ + FC_AUTH_MC_IKE_SA_AUTH = 0x23, /*! IKE SA Auth */ + FC_AUTH_MC_IKE_CREATE_CHILD_SA = 0x24, /*! IKE Create Child SA */ + FC_AUTH_MC_IKE_INFO = 0x25, /*! IKE informational */ +}; + +enum auth_proto_version{ + FC_AUTH_PROTO_VER_1 = 1, /*! Protocol Version 1 */ +}; + +enum { + FC_AUTH_ELS_COMMAND_CODE = 0x90,/*! Authentication ELS Command code */ + FC_AUTH_PROTO_PARAM_LEN_SZ = 4, /*! Size of Proto Parameter Len Field */ + FC_AUTH_PROTO_PARAM_VAL_SZ = 4, /*! Size of Proto Parameter Val Field */ + FC_MAX_AUTH_SECRET_LEN = 256, + /*! Maximum secret string length */ + FC_AUTH_NUM_USABLE_PROTO_LEN_SZ = 4, + /*! Size of usable protocols field */ + FC_AUTH_RESP_VALUE_LEN_SZ = 4, + /*! Size of response value length */ + FC_MAX_CHAP_KEY_LEN = 256, /*! Maximum md5 digest length */ + FC_MAX_AUTH_RETRIES = 3, /*! Maximum number of retries */ + FC_MD5_DIGEST_LEN = 16, /*! MD5 digest length */ + FC_SHA1_DIGEST_LEN = 20, /*! SHA1 digest length */ + FC_MAX_DHG_SUPPORTED = 1, /*! Maximum DH Groups supported */ + FC_MAX_ALG_SUPPORTED = 1, /*! Maximum algorithms supported */ + FC_MAX_PROTO_SUPPORTED = 1, /*! Maximum protocols supported */ + FC_START_TXN_ID = 2, /*! Starting transaction ID */ +}; + +enum auth_proto_id{ + FC_AUTH_PROTO_DHCHAP = 0x00000001, + FC_AUTH_PROTO_FCAP = 0x00000002, + FC_AUTH_PROTO_FCPAP = 0x00000003, + FC_AUTH_PROTO_IKEv2 = 0x00000004, + FC_AUTH_PROTO_IKEv2_AUTH = 0x00000005, +}; + +struct auth_name_s{ + u16 name_tag; /*! Name Tag = 1 for Authentication */ + u16 name_len; /*! Name Length = 8 for Authentication + */ + wwn_t name; /*! Name. TODO - is this PWWN */ +}; + + +enum auth_hash_func{ + FC_AUTH_HASH_FUNC_MD5 = 0x00000005, + FC_AUTH_HASH_FUNC_SHA_1 = 0x00000006, +}; + +enum auth_dh_gid{ + FC_AUTH_DH_GID_0_DHG_NULL = 0x00000000, + FC_AUTH_DH_GID_1_DHG_1024 = 0x00000001, + FC_AUTH_DH_GID_2_DHG_1280 = 0x00000002, + FC_AUTH_DH_GID_3_DHG_1536 = 0x00000003, + FC_AUTH_DH_GID_4_DHG_2048 = 0x00000004, + FC_AUTH_DH_GID_6_DHG_3072 = 0x00000006, + FC_AUTH_DH_GID_7_DHG_4096 = 0x00000007, + FC_AUTH_DH_GID_8_DHG_6144 = 0x00000008, + FC_AUTH_DH_GID_9_DHG_8192 = 0x00000009, +}; + +struct auth_els_msg_s { + u8 auth_els_code; /* Authentication ELS Code (0x90) */ + u8 auth_els_flag; /* Authentication ELS Flags */ + u8 auth_msg_code; /* Authentication Message Code */ + u8 proto_version; /* Protocol Version */ + u32 msg_len; /* Message Length */ + u32 trans_id; /* Transaction Identifier (T_ID) */ + + /* Msg payload follows... */ +}; + + +enum auth_neg_param_tags { + FC_AUTH_NEG_DHCHAP_HASHLIST = 0x0001, + FC_AUTH_NEG_DHCHAP_DHG_ID_LIST = 0x0002, +}; + + +struct dhchap_param_format_s { + u16 tag; /*! Parameter Tag. See + * auth_neg_param_tags_t + */ + u16 word_cnt; + + /* followed by variable length parameter value... */ +}; + +struct auth_proto_params_s { + u32 proto_param_len; + u32 proto_id; + + /* + * Followed by variable length Protocol specific parameters. DH-CHAP + * uses dhchap_param_format_t + */ +}; + +struct auth_neg_msg_s { + struct auth_name_s auth_ini_name; + u32 usable_auth_protos; + struct auth_proto_params_s proto_params[1]; /*! (1..usable_auth_proto) + * protocol params + */ +}; + +struct auth_dh_val_s { + u32 dh_val_len; + u32 dh_val[1]; +}; + +struct auth_dhchap_chal_msg_s { + struct auth_els_msg_s hdr; + struct auth_name_s auth_responder_name; /* TODO VRK - is auth_name_t + * type OK? + */ + u32 hash_id; + u32 dh_grp_id; + u32 chal_val_len; + char chal_val[1]; + + /* ...followed by variable Challenge length/value and DH length/value */ +}; + + +enum auth_rjt_codes { + FC_AUTH_RJT_CODE_AUTH_FAILURE = 0x01, + FC_AUTH_RJT_CODE_LOGICAL_ERR = 0x02, +}; + +enum auth_rjt_code_exps { + FC_AUTH_CEXP_AUTH_MECH_NOT_USABLE = 0x01, + FC_AUTH_CEXP_DH_GROUP_NOT_USABLE = 0x02, + FC_AUTH_CEXP_HASH_FUNC_NOT_USABLE = 0x03, + FC_AUTH_CEXP_AUTH_XACT_STARTED = 0x04, + FC_AUTH_CEXP_AUTH_FAILED = 0x05, + FC_AUTH_CEXP_INCORRECT_PLD = 0x06, + FC_AUTH_CEXP_INCORRECT_PROTO_MSG = 0x07, + FC_AUTH_CEXP_RESTART_AUTH_PROTO = 0x08, + FC_AUTH_CEXP_AUTH_CONCAT_NOT_SUPP = 0x09, + FC_AUTH_CEXP_PROTO_VER_NOT_SUPP = 0x0A, +}; + +enum auth_status { + FC_AUTH_STATE_INPROGRESS = 0, /*! authentication in progress */ + FC_AUTH_STATE_FAILED = 1, /*! authentication failed */ + FC_AUTH_STATE_SUCCESS = 2 /*! authentication successful */ +}; + +struct auth_rjt_msg_s { + struct auth_els_msg_s hdr; + u8 reason_code; + u8 reason_code_exp; + u8 rsvd[2]; +}; + + +struct auth_dhchap_neg_msg_s { + struct auth_els_msg_s hdr; + struct auth_neg_msg_s nego; +}; + +struct auth_dhchap_reply_msg_s { + struct auth_els_msg_s hdr; + + /* + * followed by response value length & Value + DH Value Length & Value + */ +}; + +#pragma pack() + +#endif /* __FC_SP_H__ */ diff --git a/drivers/scsi/bfa/include/protocol/fcp.h b/drivers/scsi/bfa/include/protocol/fcp.h new file mode 100644 index 000000000000..9ade68ad2853 --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/fcp.h @@ -0,0 +1,186 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __FCPPROTO_H__ +#define __FCPPROTO_H__ + +#include <protocol/scsi.h> + +#pragma pack(1) + +enum { + FCP_RJT = 0x01000000, /* SRR reject */ + FCP_SRR_ACCEPT = 0x02000000, /* SRR accept */ + FCP_SRR = 0x14000000, /* Sequence Retransmission Request */ +}; + +/* + * SRR FC-4 LS payload + */ +struct fc_srr_s{ + u32 ls_cmd; + u32 ox_id:16; /* ox-id */ + u32 rx_id:16; /* rx-id */ + u32 ro; /* relative offset */ + u32 r_ctl:8; /* R_CTL for I.U. */ + u32 res:24; +}; + + +/* + * FCP_CMND definitions + */ +#define FCP_CMND_CDB_LEN 16 +#define FCP_CMND_LUN_LEN 8 + +struct fcp_cmnd_s{ + lun_t lun; /* 64-bit LU number */ + u8 crn; /* command reference number */ +#ifdef __BIGENDIAN + u8 resvd:1, + priority:4, /* FCP-3: SAM-3 priority */ + taskattr:3; /* scsi task attribute */ +#else + u8 taskattr:3, /* scsi task attribute */ + priority:4, /* FCP-3: SAM-3 priority */ + resvd:1; +#endif + u8 tm_flags; /* task management flags */ +#ifdef __BIGENDIAN + u8 addl_cdb_len:6, /* additional CDB length words */ + iodir:2; /* read/write FCP_DATA IUs */ +#else + u8 iodir:2, /* read/write FCP_DATA IUs */ + addl_cdb_len:6; /* additional CDB length */ +#endif + struct scsi_cdb_s cdb; + + /* + * !!! additional cdb bytes follows here!!! + */ + u32 fcp_dl; /* bytes to be transferred */ +}; + +#define fcp_cmnd_cdb_len(_cmnd) ((_cmnd)->addl_cdb_len * 4 + FCP_CMND_CDB_LEN) +#define fcp_cmnd_fcpdl(_cmnd) ((&(_cmnd)->fcp_dl)[(_cmnd)->addl_cdb_len]) + +/* + * fcp_cmnd_t.iodir field values + */ +enum fcp_iodir{ + FCP_IODIR_NONE = 0, + FCP_IODIR_WRITE = 1, + FCP_IODIR_READ = 2, + FCP_IODIR_RW = 3, +}; + +/* + * Task attribute field + */ +enum { + FCP_TASK_ATTR_SIMPLE = 0, + FCP_TASK_ATTR_HOQ = 1, + FCP_TASK_ATTR_ORDERED = 2, + FCP_TASK_ATTR_ACA = 4, + FCP_TASK_ATTR_UNTAGGED = 5, /* obsolete in FCP-3 */ +}; + +/* + * Task management flags field - only one bit shall be set + */ +#ifndef BIT +#define BIT(_x) (1 << (_x)) +#endif +enum fcp_tm_cmnd{ + FCP_TM_ABORT_TASK_SET = BIT(1), + FCP_TM_CLEAR_TASK_SET = BIT(2), + FCP_TM_LUN_RESET = BIT(4), + FCP_TM_TARGET_RESET = BIT(5), /* obsolete in FCP-3 */ + FCP_TM_CLEAR_ACA = BIT(6), +}; + +/* + * FCP_XFER_RDY IU defines + */ +struct fcp_xfer_rdy_s{ + u32 data_ro; + u32 burst_len; + u32 reserved; +}; + +/* + * FCP_RSP residue flags + */ +enum fcp_residue{ + FCP_NO_RESIDUE = 0, /* no residue */ + FCP_RESID_OVER = 1, /* more data left that was not sent */ + FCP_RESID_UNDER = 2, /* less data than requested */ +}; + +enum { + FCP_RSPINFO_GOOD = 0, + FCP_RSPINFO_DATALEN_MISMATCH = 1, + FCP_RSPINFO_CMND_INVALID = 2, + FCP_RSPINFO_ROLEN_MISMATCH = 3, + FCP_RSPINFO_TM_NOT_SUPP = 4, + FCP_RSPINFO_TM_FAILED = 5, +}; + +struct fcp_rspinfo_s{ + u32 res0:24; + u32 rsp_code:8; /* response code (as above) */ + u32 res1; +}; + +struct fcp_resp_s{ + u32 reserved[2]; /* 2 words reserved */ + u16 reserved2; +#ifdef __BIGENDIAN + u8 reserved3:3; + u8 fcp_conf_req:1; /* FCP_CONF is requested */ + u8 resid_flags:2; /* underflow/overflow */ + u8 sns_len_valid:1;/* sense len is valid */ + u8 rsp_len_valid:1;/* response len is valid */ +#else + u8 rsp_len_valid:1;/* response len is valid */ + u8 sns_len_valid:1;/* sense len is valid */ + u8 resid_flags:2; /* underflow/overflow */ + u8 fcp_conf_req:1; /* FCP_CONF is requested */ + u8 reserved3:3; +#endif + u8 scsi_status; /* one byte SCSI status */ + u32 residue; /* residual data bytes */ + u32 sns_len; /* length od sense info */ + u32 rsp_len; /* length of response info */ +}; + +#define fcp_snslen(__fcprsp) ((__fcprsp)->sns_len_valid ? \ + (__fcprsp)->sns_len : 0) +#define fcp_rsplen(__fcprsp) ((__fcprsp)->rsp_len_valid ? \ + (__fcprsp)->rsp_len : 0) +#define fcp_rspinfo(__fcprsp) ((struct fcp_rspinfo_s *)((__fcprsp) + 1)) +#define fcp_snsinfo(__fcprsp) (((u8 *)fcp_rspinfo(__fcprsp)) + \ + fcp_rsplen(__fcprsp)) + +struct fcp_cmnd_fr_s{ + struct fchs_s fchs; + struct fcp_cmnd_s fcp; +}; + +#pragma pack() + +#endif diff --git a/drivers/scsi/bfa/include/protocol/fdmi.h b/drivers/scsi/bfa/include/protocol/fdmi.h new file mode 100644 index 000000000000..6c05c268c71b --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/fdmi.h @@ -0,0 +1,163 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __FDMI_H__ +#define __FDMI_H__ + +#include <protocol/types.h> +#include <protocol/fc.h> +#include <protocol/ct.h> + +#pragma pack(1) + +/* + * FDMI Command Codes + */ +#define FDMI_GRHL 0x0100 +#define FDMI_GHAT 0x0101 +#define FDMI_GRPL 0x0102 +#define FDMI_GPAT 0x0110 +#define FDMI_RHBA 0x0200 +#define FDMI_RHAT 0x0201 +#define FDMI_RPRT 0x0210 +#define FDMI_RPA 0x0211 +#define FDMI_DHBA 0x0300 +#define FDMI_DPRT 0x0310 + +/* + * FDMI reason codes + */ +#define FDMI_NO_ADDITIONAL_EXP 0x00 +#define FDMI_HBA_ALREADY_REG 0x10 +#define FDMI_HBA_ATTRIB_NOT_REG 0x11 +#define FDMI_HBA_ATTRIB_MULTIPLE 0x12 +#define FDMI_HBA_ATTRIB_LENGTH_INVALID 0x13 +#define FDMI_HBA_ATTRIB_NOT_PRESENT 0x14 +#define FDMI_PORT_ORIG_NOT_IN_LIST 0x15 +#define FDMI_PORT_HBA_NOT_IN_LIST 0x16 +#define FDMI_PORT_ATTRIB_NOT_REG 0x20 +#define FDMI_PORT_NOT_REG 0x21 +#define FDMI_PORT_ATTRIB_MULTIPLE 0x22 +#define FDMI_PORT_ATTRIB_LENGTH_INVALID 0x23 +#define FDMI_PORT_ALREADY_REGISTEREED 0x24 + +/* + * FDMI Transmission Speed Mask values + */ +#define FDMI_TRANS_SPEED_1G 0x00000001 +#define FDMI_TRANS_SPEED_2G 0x00000002 +#define FDMI_TRANS_SPEED_10G 0x00000004 +#define FDMI_TRANS_SPEED_4G 0x00000008 +#define FDMI_TRANS_SPEED_8G 0x00000010 +#define FDMI_TRANS_SPEED_16G 0x00000020 +#define FDMI_TRANS_SPEED_UNKNOWN 0x00008000 + +/* + * FDMI HBA attribute types + */ +enum fdmi_hba_attribute_type { + FDMI_HBA_ATTRIB_NODENAME = 1, /* 0x0001 */ + FDMI_HBA_ATTRIB_MANUFACTURER, /* 0x0002 */ + FDMI_HBA_ATTRIB_SERIALNUM, /* 0x0003 */ + FDMI_HBA_ATTRIB_MODEL, /* 0x0004 */ + FDMI_HBA_ATTRIB_MODEL_DESC, /* 0x0005 */ + FDMI_HBA_ATTRIB_HW_VERSION, /* 0x0006 */ + FDMI_HBA_ATTRIB_DRIVER_VERSION, /* 0x0007 */ + FDMI_HBA_ATTRIB_ROM_VERSION, /* 0x0008 */ + FDMI_HBA_ATTRIB_FW_VERSION, /* 0x0009 */ + FDMI_HBA_ATTRIB_OS_NAME, /* 0x000A */ + FDMI_HBA_ATTRIB_MAX_CT, /* 0x000B */ + + FDMI_HBA_ATTRIB_MAX_TYPE +}; + +/* + * FDMI Port attribute types + */ +enum fdmi_port_attribute_type { + FDMI_PORT_ATTRIB_FC4_TYPES = 1, /* 0x0001 */ + FDMI_PORT_ATTRIB_SUPP_SPEED, /* 0x0002 */ + FDMI_PORT_ATTRIB_PORT_SPEED, /* 0x0003 */ + FDMI_PORT_ATTRIB_FRAME_SIZE, /* 0x0004 */ + FDMI_PORT_ATTRIB_DEV_NAME, /* 0x0005 */ + FDMI_PORT_ATTRIB_HOST_NAME, /* 0x0006 */ + + FDMI_PORT_ATTR_MAX_TYPE +}; + +/* + * FDMI attribute + */ +struct fdmi_attr_s { + u16 type; + u16 len; + u8 value[1]; +}; + +/* + * HBA Attribute Block + */ +struct fdmi_hba_attr_s { + u32 attr_count; /* # of attributes */ + struct fdmi_attr_s hba_attr; /* n attributes */ +}; + +/* + * Registered Port List + */ +struct fdmi_port_list_s { + u32 num_ports; /* number Of Port Entries */ + wwn_t port_entry; /* one or more */ +}; + +/* + * Port Attribute Block + */ +struct fdmi_port_attr_s { + u32 attr_count; /* # of attributes */ + struct fdmi_attr_s port_attr; /* n attributes */ +}; + +/* + * FDMI Register HBA Attributes + */ +struct fdmi_rhba_s { + wwn_t hba_id; /* HBA Identifier */ + struct fdmi_port_list_s port_list; /* Registered Port List */ + struct fdmi_hba_attr_s hba_attr_blk; /* HBA attribute block */ +}; + +/* + * FDMI Register Port + */ +struct fdmi_rprt_s { + wwn_t hba_id; /* HBA Identifier */ + wwn_t port_name; /* Port wwn */ + struct fdmi_port_attr_s port_attr_blk; /* Port Attr Block */ +}; + +/* + * FDMI Register Port Attributes + */ +struct fdmi_rpa_s { + wwn_t port_name; /* port wwn */ + struct fdmi_port_attr_s port_attr_blk; /* Port Attr Block */ +}; + +#pragma pack() + +#endif diff --git a/drivers/scsi/bfa/include/protocol/pcifw.h b/drivers/scsi/bfa/include/protocol/pcifw.h new file mode 100644 index 000000000000..6830dc3ee58a --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/pcifw.h @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * pcifw.h PCI FW related headers + */ + +#ifndef __PCIFW_H__ +#define __PCIFW_H__ + +#pragma pack(1) + +struct pnp_hdr_s{ + u32 signature; /* "$PnP" */ + u8 rev; /* Struct revision */ + u8 len; /* Header structure len in multiples + * of 16 bytes */ + u16 off; /* Offset to next header 00 if none */ + u8 rsvd; /* Reserved byte */ + u8 cksum; /* 8-bit checksum for this header */ + u32 pnp_dev_id; /* PnP Device Id */ + u16 mfstr; /* Pointer to manufacturer string */ + u16 prstr; /* Pointer to product string */ + u8 devtype[3]; /* Device Type Code */ + u8 devind; /* Device Indicator */ + u16 bcventr; /* Bootstrap entry vector */ + u16 rsvd2; /* Reserved */ + u16 sriv; /* Static resource information vector */ +}; + +struct pci_3_0_ds_s{ + u32 sig; /* Signature "PCIR" */ + u16 vendid; /* Vendor ID */ + u16 devid; /* Device ID */ + u16 devlistoff; /* Device List Offset */ + u16 len; /* PCI Data Structure Length */ + u8 rev; /* PCI Data Structure Revision */ + u8 clcode[3]; /* Class Code */ + u16 imglen; /* Code image length in multiples of + * 512 bytes */ + u16 coderev; /* Revision level of code/data */ + u8 codetype; /* Code type 0x00 - BIOS */ + u8 indr; /* Last image indicator */ + u16 mrtimglen; /* Max Run Time Image Length */ + u16 cuoff; /* Config Utility Code Header Offset */ + u16 dmtfclp; /* DMTF CLP entry point offset */ +}; + +struct pci_optrom_hdr_s{ + u16 sig; /* Signature 0x55AA */ + u8 len; /* Option ROM length in units of 512 bytes */ + u8 inivec[3]; /* Initialization vector */ + u8 rsvd[16]; /* Reserved field */ + u16 verptr; /* Pointer to version string - private */ + u16 pcids; /* Pointer to PCI data structure */ + u16 pnphdr; /* Pointer to PnP expansion header */ +}; + +#pragma pack() + +#endif diff --git a/drivers/scsi/bfa/include/protocol/scsi.h b/drivers/scsi/bfa/include/protocol/scsi.h new file mode 100644 index 000000000000..b220e6b4f6e1 --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/scsi.h @@ -0,0 +1,1648 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __SCSI_H__ +#define __SCSI_H__ + +#include <protocol/types.h> + +#pragma pack(1) + +/* + * generic SCSI cdb definition + */ +#define SCSI_MAX_CDBLEN 16 +struct scsi_cdb_s{ + u8 scsi_cdb[SCSI_MAX_CDBLEN]; +}; + +/* + * scsi lun serial number definition + */ +#define SCSI_LUN_SN_LEN 32 +struct scsi_lun_sn_s{ + u8 lun_sn[SCSI_LUN_SN_LEN]; +}; + +/* + * SCSI Direct Access Commands + */ +enum { + SCSI_OP_TEST_UNIT_READY = 0x00, + SCSI_OP_REQUEST_SENSE = 0x03, + SCSI_OP_FORMAT_UNIT = 0x04, + SCSI_OP_READ6 = 0x08, + SCSI_OP_WRITE6 = 0x0A, + SCSI_OP_WRITE_FILEMARKS = 0x10, + SCSI_OP_INQUIRY = 0x12, + SCSI_OP_MODE_SELECT6 = 0x15, + SCSI_OP_RESERVE6 = 0x16, + SCSI_OP_RELEASE6 = 0x17, + SCSI_OP_MODE_SENSE6 = 0x1A, + SCSI_OP_START_STOP_UNIT = 0x1B, + SCSI_OP_SEND_DIAGNOSTIC = 0x1D, + SCSI_OP_READ_CAPACITY = 0x25, + SCSI_OP_READ10 = 0x28, + SCSI_OP_WRITE10 = 0x2A, + SCSI_OP_VERIFY10 = 0x2F, + SCSI_OP_READ_DEFECT_DATA = 0x37, + SCSI_OP_LOG_SELECT = 0x4C, + SCSI_OP_LOG_SENSE = 0x4D, + SCSI_OP_MODE_SELECT10 = 0x55, + SCSI_OP_RESERVE10 = 0x56, + SCSI_OP_RELEASE10 = 0x57, + SCSI_OP_MODE_SENSE10 = 0x5A, + SCSI_OP_PER_RESERVE_IN = 0x5E, + SCSI_OP_PER_RESERVE_OUR = 0x5E, + SCSI_OP_READ16 = 0x88, + SCSI_OP_WRITE16 = 0x8A, + SCSI_OP_VERIFY16 = 0x8F, + SCSI_OP_READ_CAPACITY16 = 0x9E, + SCSI_OP_REPORT_LUNS = 0xA0, + SCSI_OP_READ12 = 0xA8, + SCSI_OP_WRITE12 = 0xAA, + SCSI_OP_UNDEF = 0xFF, +}; + +/* + * SCSI START_STOP_UNIT command + */ +struct scsi_start_stop_unit_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 lun:3; + u8 reserved1:4; + u8 immed:1; +#else + u8 immed:1; + u8 reserved1:4; + u8 lun:3; +#endif + u8 reserved2; + u8 reserved3; +#ifdef __BIGENDIAN + u8 power_conditions:4; + u8 reserved4:2; + u8 loEj:1; + u8 start:1; +#else + u8 start:1; + u8 loEj:1; + u8 reserved4:2; + u8 power_conditions:4; +#endif + u8 control; +}; + +/* + * SCSI SEND_DIAGNOSTIC command + */ +struct scsi_send_diagnostic_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 self_test_code:3; + u8 pf:1; + u8 reserved1:1; + u8 self_test:1; + u8 dev_offl:1; + u8 unit_offl:1; +#else + u8 unit_offl:1; + u8 dev_offl:1; + u8 self_test:1; + u8 reserved1:1; + u8 pf:1; + u8 self_test_code:3; +#endif + u8 reserved2; + + u8 param_list_length[2]; /* MSB first */ + u8 control; + +}; + +/* + * SCSI READ10/WRITE10 commands + */ +struct scsi_rw10_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 lun:3; + u8 dpo:1; /* Disable Page Out */ + u8 fua:1; /* Force Unit Access */ + u8 reserved1:2; + u8 rel_adr:1; /* relative address */ +#else + u8 rel_adr:1; + u8 reserved1:2; + u8 fua:1; + u8 dpo:1; + u8 lun:3; +#endif + u8 lba0; /* logical block address - MSB */ + u8 lba1; + u8 lba2; + u8 lba3; /* LSB */ + u8 reserved3; + u8 xfer_length0; /* transfer length in blocks - MSB */ + u8 xfer_length1; /* LSB */ + u8 control; +}; + +#define SCSI_CDB10_GET_LBA(cdb) \ + (((cdb)->lba0 << 24) | ((cdb)->lba1 << 16) | \ + ((cdb)->lba2 << 8) | (cdb)->lba3) + +#define SCSI_CDB10_SET_LBA(cdb, lba) { \ + (cdb)->lba0 = lba >> 24; \ + (cdb)->lba1 = (lba >> 16) & 0xFF; \ + (cdb)->lba2 = (lba >> 8) & 0xFF; \ + (cdb)->lba3 = lba & 0xFF; \ +} + +#define SCSI_CDB10_GET_TL(cdb) \ + ((cdb)->xfer_length0 << 8 | (cdb)->xfer_length1) +#define SCSI_CDB10_SET_TL(cdb, tl) { \ + (cdb)->xfer_length0 = tl >> 8; \ + (cdb)->xfer_length1 = tl & 0xFF; \ +} + +/* + * SCSI READ6/WRITE6 commands + */ +struct scsi_rw6_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 lun:3; + u8 lba0:5; /* MSb */ +#else + u8 lba0:5; /* MSb */ + u8 lun:3; +#endif + u8 lba1; + u8 lba2; /* LSB */ + u8 xfer_length; + u8 control; +}; + +#define SCSI_TAPE_CDB6_GET_TL(cdb) \ + (((cdb)->tl0 << 16) | ((cdb)->tl1 << 8) | (cdb)->tl2) + +#define SCSI_TAPE_CDB6_SET_TL(cdb, tl) { \ + (cdb)->tl0 = tl >> 16; \ + (cdb)->tl1 = (tl >> 8) & 0xFF; \ + (cdb)->tl2 = tl & 0xFF; \ +} + +/* + * SCSI sequential (TAPE) wrtie command + */ +struct scsi_tape_wr_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 rsvd:7; + u8 fixed:1; /* MSb */ +#else + u8 fixed:1; /* MSb */ + u8 rsvd:7; +#endif + u8 tl0; /* Msb */ + u8 tl1; + u8 tl2; /* Lsb */ + + u8 control; +}; + +#define SCSI_CDB6_GET_LBA(cdb) \ + (((cdb)->lba0 << 16) | ((cdb)->lba1 << 8) | (cdb)->lba2) + +#define SCSI_CDB6_SET_LBA(cdb, lba) { \ + (cdb)->lba0 = lba >> 16; \ + (cdb)->lba1 = (lba >> 8) & 0xFF; \ + (cdb)->lba2 = lba & 0xFF; \ +} + +#define SCSI_CDB6_GET_TL(cdb) ((cdb)->xfer_length) +#define SCSI_CDB6_SET_TL(cdb, tl) { \ + (cdb)->xfer_length = tl; \ +} + +/* + * SCSI sense data format + */ +struct scsi_sense_s{ +#ifdef __BIGENDIAN + u8 valid:1; + u8 rsp_code:7; +#else + u8 rsp_code:7; + u8 valid:1; +#endif + u8 seg_num; +#ifdef __BIGENDIAN + u8 file_mark:1; + u8 eom:1; /* end of media */ + u8 ili:1; /* incorrect length indicator */ + u8 reserved:1; + u8 sense_key:4; +#else + u8 sense_key:4; + u8 reserved:1; + u8 ili:1; /* incorrect length indicator */ + u8 eom:1; /* end of media */ + u8 file_mark:1; +#endif + u8 information[4]; /* device-type or command specific info + */ + u8 add_sense_length; + /* additional sense length */ + u8 command_info[4];/* command specific information + */ + u8 asc; /* additional sense code */ + u8 ascq; /* additional sense code qualifier */ + u8 fru_code; /* field replaceable unit code */ +#ifdef __BIGENDIAN + u8 sksv:1; /* sense key specific valid */ + u8 c_d:1; /* command/data bit */ + u8 res1:2; + u8 bpv:1; /* bit pointer valid */ + u8 bpointer:3; /* bit pointer */ +#else + u8 bpointer:3; /* bit pointer */ + u8 bpv:1; /* bit pointer valid */ + u8 res1:2; + u8 c_d:1; /* command/data bit */ + u8 sksv:1; /* sense key specific valid */ +#endif + u8 fpointer[2]; /* field pointer */ +}; + +#define SCSI_SENSE_CUR_ERR 0x70 +#define SCSI_SENSE_DEF_ERR 0x71 + +/* + * SCSI sense key values + */ +#define SCSI_SK_NO_SENSE 0x0 +#define SCSI_SK_REC_ERR 0x1 /* recovered error */ +#define SCSI_SK_NOT_READY 0x2 +#define SCSI_SK_MED_ERR 0x3 /* medium error */ +#define SCSI_SK_HW_ERR 0x4 /* hardware error */ +#define SCSI_SK_ILLEGAL_REQ 0x5 +#define SCSI_SK_UNIT_ATT 0x6 /* unit attention */ +#define SCSI_SK_DATA_PROTECT 0x7 +#define SCSI_SK_BLANK_CHECK 0x8 +#define SCSI_SK_VENDOR_SPEC 0x9 +#define SCSI_SK_COPY_ABORTED 0xA +#define SCSI_SK_ABORTED_CMND 0xB +#define SCSI_SK_VOL_OVERFLOW 0xD +#define SCSI_SK_MISCOMPARE 0xE + +/* + * SCSI additional sense codes + */ +#define SCSI_ASC_NO_ADD_SENSE 0x00 +#define SCSI_ASC_LUN_NOT_READY 0x04 +#define SCSI_ASC_LUN_COMMUNICATION 0x08 +#define SCSI_ASC_WRITE_ERROR 0x0C +#define SCSI_ASC_INVALID_CMND_CODE 0x20 +#define SCSI_ASC_BAD_LBA 0x21 +#define SCSI_ASC_INVALID_FIELD_IN_CDB 0x24 +#define SCSI_ASC_LUN_NOT_SUPPORTED 0x25 +#define SCSI_ASC_LUN_WRITE_PROTECT 0x27 +#define SCSI_ASC_POWERON_BDR 0x29 /* power on reset, bus reset, + * bus device reset + */ +#define SCSI_ASC_PARAMS_CHANGED 0x2A +#define SCSI_ASC_CMND_CLEARED_BY_A_I 0x2F +#define SCSI_ASC_SAVING_PARAM_NOTSUPP 0x39 +#define SCSI_ASC_TOCC 0x3F /* target operating condtions + * changed + */ +#define SCSI_ASC_PARITY_ERROR 0x47 +#define SCSI_ASC_CMND_PHASE_ERROR 0x4A +#define SCSI_ASC_DATA_PHASE_ERROR 0x4B +#define SCSI_ASC_VENDOR_SPEC 0x7F + +/* + * SCSI additional sense code qualifiers + */ +#define SCSI_ASCQ_CAUSE_NOT_REPORT 0x00 +#define SCSI_ASCQ_BECOMING_READY 0x01 +#define SCSI_ASCQ_INIT_CMD_REQ 0x02 +#define SCSI_ASCQ_FORMAT_IN_PROGRESS 0x04 +#define SCSI_ASCQ_OPERATION_IN_PROGRESS 0x07 +#define SCSI_ASCQ_SELF_TEST_IN_PROGRESS 0x09 +#define SCSI_ASCQ_WR_UNEXP_UNSOL_DATA 0x0C +#define SCSI_ASCQ_WR_NOTENG_UNSOL_DATA 0x0D + +#define SCSI_ASCQ_LBA_OUT_OF_RANGE 0x00 +#define SCSI_ASCQ_INVALID_ELEMENT_ADDR 0x01 + +#define SCSI_ASCQ_LUN_WRITE_PROTECTED 0x00 +#define SCSI_ASCQ_LUN_HW_WRITE_PROTECTED 0x01 +#define SCSI_ASCQ_LUN_SW_WRITE_PROTECTED 0x02 + +#define SCSI_ASCQ_POR 0x01 /* power on reset */ +#define SCSI_ASCQ_SBR 0x02 /* scsi bus reset */ +#define SCSI_ASCQ_BDR 0x03 /* bus device reset */ +#define SCSI_ASCQ_DIR 0x04 /* device internal reset */ + +#define SCSI_ASCQ_MODE_PARAMS_CHANGED 0x01 +#define SCSI_ASCQ_LOG_PARAMS_CHANGED 0x02 +#define SCSI_ASCQ_RESERVATIONS_PREEMPTED 0x03 +#define SCSI_ASCQ_RESERVATIONS_RELEASED 0x04 +#define SCSI_ASCQ_REGISTRATIONS_PREEMPTED 0x05 + +#define SCSI_ASCQ_MICROCODE_CHANGED 0x01 +#define SCSI_ASCQ_CHANGED_OPER_COND 0x02 +#define SCSI_ASCQ_INQ_CHANGED 0x03 /* inquiry data changed */ +#define SCSI_ASCQ_DI_CHANGED 0x05 /* device id changed */ +#define SCSI_ASCQ_RL_DATA_CHANGED 0x0E /* report luns data changed */ + +#define SCSI_ASCQ_DP_CRC_ERR 0x01 /* data phase crc error */ +#define SCSI_ASCQ_DP_SCSI_PARITY_ERR 0x02 /* data phase scsi parity error + */ +#define SCSI_ASCQ_IU_CRC_ERR 0x03 /* information unit crc error */ +#define SCSI_ASCQ_PROTO_SERV_CRC_ERR 0x05 + +#define SCSI_ASCQ_LUN_TIME_OUT 0x01 + +/* ------------------------------------------------------------ + * SCSI INQUIRY + * ------------------------------------------------------------*/ + +struct scsi_inquiry_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 lun:3; + u8 reserved1:3; + u8 cmd_dt:1; + u8 evpd:1; +#else + u8 evpd:1; + u8 cmd_dt:1; + u8 reserved1:3; + u8 lun:3; +#endif + u8 page_code; + u8 reserved2; + u8 alloc_length; + u8 control; +}; + +struct scsi_inquiry_vendor_s{ + u8 vendor_id[8]; +}; + +struct scsi_inquiry_prodid_s{ + u8 product_id[16]; +}; + +struct scsi_inquiry_prodrev_s{ + u8 product_rev[4]; +}; + +struct scsi_inquiry_data_s{ +#ifdef __BIGENDIAN + u8 peripheral_qual:3; /* peripheral qualifier */ + u8 device_type:5; /* peripheral device type */ + + u8 rmb:1; /* removable medium bit */ + u8 device_type_mod:7; /* device type modifier */ + + u8 version; + + u8 aenc:1; /* async event notification capability + */ + u8 trm_iop:1; /* terminate I/O process */ + u8 norm_aca:1; /* normal ACA supported */ + u8 hi_support:1; /* SCSI-3: supports REPORT LUNS */ + u8 rsp_data_format:4; + + u8 additional_len; + u8 sccs:1; + u8 reserved1:7; + + u8 reserved2:1; + u8 enc_serv:1; /* enclosure service component */ + u8 reserved3:1; + u8 multi_port:1; /* multi-port device */ + u8 m_chngr:1; /* device in medium transport element */ + u8 ack_req_q:1; /* SIP specific bit */ + u8 addr32:1; /* SIP specific bit */ + u8 addr16:1; /* SIP specific bit */ + + u8 rel_adr:1; /* relative address */ + u8 w_bus32:1; + u8 w_bus16:1; + u8 synchronous:1; + u8 linked_commands:1; + u8 trans_dis:1; + u8 cmd_queue:1; /* command queueing supported */ + u8 soft_reset:1; /* soft reset alternative (VS) */ +#else + u8 device_type:5; /* peripheral device type */ + u8 peripheral_qual:3; + /* peripheral qualifier */ + + u8 device_type_mod:7; + /* device type modifier */ + u8 rmb:1; /* removable medium bit */ + + u8 version; + + u8 rsp_data_format:4; + u8 hi_support:1; /* SCSI-3: supports REPORT LUNS */ + u8 norm_aca:1; /* normal ACA supported */ + u8 terminate_iop:1;/* terminate I/O process */ + u8 aenc:1; /* async event notification capability + */ + + u8 additional_len; + u8 reserved1:7; + u8 sccs:1; + + u8 addr16:1; /* SIP specific bit */ + u8 addr32:1; /* SIP specific bit */ + u8 ack_req_q:1; /* SIP specific bit */ + u8 m_chngr:1; /* device in medium transport element */ + u8 multi_port:1; /* multi-port device */ + u8 reserved3:1; /* TBD - Vendor Specific */ + u8 enc_serv:1; /* enclosure service component */ + u8 reserved2:1; + + u8 soft_seset:1; /* soft reset alternative (VS) */ + u8 cmd_queue:1; /* command queueing supported */ + u8 trans_dis:1; + u8 linked_commands:1; + u8 synchronous:1; + u8 w_bus16:1; + u8 w_bus32:1; + u8 rel_adr:1; /* relative address */ +#endif + struct scsi_inquiry_vendor_s vendor_id; + struct scsi_inquiry_prodid_s product_id; + struct scsi_inquiry_prodrev_s product_rev; + u8 vendor_specific[20]; + u8 reserved4[40]; +}; + +/* + * inquiry.peripheral_qual field values + */ +#define SCSI_DEVQUAL_DEFAULT 0 +#define SCSI_DEVQUAL_NOT_CONNECTED 1 +#define SCSI_DEVQUAL_NOT_SUPPORTED 3 + +/* + * inquiry.device_type field values + */ +#define SCSI_DEVICE_DIRECT_ACCESS 0x00 +#define SCSI_DEVICE_SEQ_ACCESS 0x01 +#define SCSI_DEVICE_ARRAY_CONTROLLER 0x0C +#define SCSI_DEVICE_UNKNOWN 0x1F + +/* + * inquiry.version + */ +#define SCSI_VERSION_ANSI_X3131 2 /* ANSI X3.131 SCSI-2 */ +#define SCSI_VERSION_SPC 3 /* SPC (SCSI-3), ANSI X3.301:1997 */ +#define SCSI_VERSION_SPC_2 4 /* SPC-2 */ + +/* + * response data format + */ +#define SCSI_RSP_DATA_FORMAT 2 /* SCSI-2 & SPC */ + +/* + * SCSI inquiry page codes + */ +#define SCSI_INQ_PAGE_VPD_PAGES 0x00 /* supported vpd pages */ +#define SCSI_INQ_PAGE_USN_PAGE 0x80 /* unit serial number page */ +#define SCSI_INQ_PAGE_DEV_IDENT 0x83 /* device indentification page + */ +#define SCSI_INQ_PAGES_MAX 3 + +/* + * supported vital product data pages + */ +struct scsi_inq_page_vpd_pages_s{ +#ifdef __BIGENDIAN + u8 peripheral_qual:3; + u8 device_type:5; +#else + u8 device_type:5; + u8 peripheral_qual:3; +#endif + u8 page_code; + u8 reserved; + u8 page_length; + u8 pages[SCSI_INQ_PAGES_MAX]; +}; + +/* + * Unit serial number page + */ +#define SCSI_INQ_USN_LEN 32 + +struct scsi_inq_usn_s{ + char usn[SCSI_INQ_USN_LEN]; +}; + +struct scsi_inq_page_usn_s{ +#ifdef __BIGENDIAN + u8 peripheral_qual:3; + u8 device_type:5; +#else + u8 device_type:5; + u8 peripheral_qual:3; +#endif + u8 page_code; + u8 reserved1; + u8 page_length; + struct scsi_inq_usn_s usn; +}; + +enum { + SCSI_INQ_DIP_CODE_BINARY = 1, /* identifier has binary value */ + SCSI_INQ_DIP_CODE_ASCII = 2, /* identifier has ascii value */ +}; + +enum { + SCSI_INQ_DIP_ASSOC_LUN = 0, /* id is associated with device */ + SCSI_INQ_DIP_ASSOC_PORT = 1, /* id is associated with port that + * received the request + */ +}; + +enum { + SCSI_INQ_ID_TYPE_VENDOR = 1, + SCSI_INQ_ID_TYPE_IEEE = 2, + SCSI_INQ_ID_TYPE_FC_FS = 3, + SCSI_INQ_ID_TYPE_OTHER = 4, +}; + +struct scsi_inq_dip_desc_s{ +#ifdef __BIGENDIAN + u8 res0:4; + u8 code_set:4; + u8 res1:2; + u8 association:2; + u8 id_type:4; +#else + u8 code_set:4; + u8 res0:4; + u8 id_type:4; + u8 association:2; + u8 res1:2; +#endif + u8 res2; + u8 id_len; + struct scsi_lun_sn_s id; +}; + +/* + * Device indentification page + */ +struct scsi_inq_page_dev_ident_s{ +#ifdef __BIGENDIAN + u8 peripheral_qual:3; + u8 device_type:5; +#else + u8 device_type:5; + u8 peripheral_qual:3; +#endif + u8 page_code; + u8 reserved1; + u8 page_length; + struct scsi_inq_dip_desc_s desc; +}; + +/* ------------------------------------------------------------ + * READ CAPACITY + * ------------------------------------------------------------ + */ + +struct scsi_read_capacity_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 lun:3; + u8 reserved1:4; + u8 rel_adr:1; +#else + u8 rel_adr:1; + u8 reserved1:4; + u8 lun:3; +#endif + u8 lba0; /* MSB */ + u8 lba1; + u8 lba2; + u8 lba3; /* LSB */ + u8 reserved2; + u8 reserved3; +#ifdef __BIGENDIAN + u8 reserved4:7; + u8 pmi:1; /* partial medium indicator */ +#else + u8 pmi:1; /* partial medium indicator */ + u8 reserved4:7; +#endif + u8 control; +}; + +struct scsi_read_capacity_data_s{ + u32 max_lba; /* maximum LBA available */ + u32 block_length; /* in bytes */ +}; + +struct scsi_read_capacity16_data_s{ + u64 lba; /* maximum LBA available */ + u32 block_length; /* in bytes */ +#ifdef __BIGENDIAN + u8 reserved1:4, + p_type:3, + prot_en:1; + u8 reserved2:4, + lb_pbe:4; /* logical blocks per physical block + * exponent */ + u16 reserved3:2, + lba_align:14; /* lowest aligned logical block + * address */ +#else + u16 lba_align:14, /* lowest aligned logical block + * address */ + reserved3:2; + u8 lb_pbe:4, /* logical blocks per physical block + * exponent */ + reserved2:4; + u8 prot_en:1, + p_type:3, + reserved1:4; +#endif + u64 reserved4; + u64 reserved5; +}; + +/* ------------------------------------------------------------ + * REPORT LUNS command + * ------------------------------------------------------------ + */ + +struct scsi_report_luns_s{ + u8 opcode; /* A0h - REPORT LUNS opCode */ + u8 reserved1[5]; + u8 alloc_length[4];/* allocation length MSB first */ + u8 reserved2; + u8 control; +}; + +#define SCSI_REPORT_LUN_ALLOC_LENGTH(rl) \ + ((rl->alloc_length[0] << 24) | (rl->alloc_length[1] << 16) | \ + (rl->alloc_length[2] << 8) | (rl->alloc_length[3])) + +#define SCSI_REPORT_LUNS_SET_ALLOCLEN(rl, alloc_len) { \ + (rl)->alloc_length[0] = (alloc_len) >> 24; \ + (rl)->alloc_length[1] = ((alloc_len) >> 16) & 0xFF; \ + (rl)->alloc_length[2] = ((alloc_len) >> 8) & 0xFF; \ + (rl)->alloc_length[3] = (alloc_len) & 0xFF; \ +} + +struct scsi_report_luns_data_s{ + u32 lun_list_length; /* length of LUN list length */ + u32 reserved; + lun_t lun[1]; /* first LUN in lun list */ +}; + +/* ------------------------------------------------------------- + * SCSI mode parameters + * ----------------------------------------------------------- + */ +enum { + SCSI_DA_MEDIUM_DEF = 0, /* direct access default medium type */ + SCSI_DA_MEDIUM_SS = 1, /* direct access single sided */ + SCSI_DA_MEDIUM_DS = 2, /* direct access double sided */ +}; + +/* + * SCSI Mode Select(6) cdb + */ +struct scsi_mode_select6_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:3; + u8 pf:1; /* page format */ + u8 reserved2:3; + u8 sp:1; /* save pages if set to 1 */ +#else + u8 sp:1; /* save pages if set to 1 */ + u8 reserved2:3; + u8 pf:1; /* page format */ + u8 reserved1:3; +#endif + u8 reserved3[2]; + u8 alloc_len; + u8 control; +}; + +/* + * SCSI Mode Select(10) cdb + */ +struct scsi_mode_select10_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:3; + u8 pf:1; /* page format */ + u8 reserved2:3; + u8 sp:1; /* save pages if set to 1 */ +#else + u8 sp:1; /* save pages if set to 1 */ + u8 reserved2:3; + u8 pf:1; /* page format */ + u8 reserved1:3; +#endif + u8 reserved3[5]; + u8 alloc_len_msb; + u8 alloc_len_lsb; + u8 control; +}; + +/* + * SCSI Mode Sense(6) cdb + */ +struct scsi_mode_sense6_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:4; + u8 dbd:1; /* disable block discriptors if set to 1 */ + u8 reserved2:3; + + u8 pc:2; /* page control */ + u8 page_code:6; +#else + u8 reserved2:3; + u8 dbd:1; /* disable block descriptors if set to 1 */ + u8 reserved1:4; + + u8 page_code:6; + u8 pc:2; /* page control */ +#endif + u8 reserved3; + u8 alloc_len; + u8 control; +}; + +/* + * SCSI Mode Sense(10) cdb + */ +struct scsi_mode_sense10_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:3; + u8 LLBAA:1; /* long LBA accepted if set to 1 */ + u8 dbd:1; /* disable block descriptors if set + * to 1 + */ + u8 reserved2:3; + + u8 pc:2; /* page control */ + u8 page_code:6; +#else + u8 reserved2:3; + u8 dbd:1; /* disable block descriptors if set to + * 1 + */ + u8 LLBAA:1; /* long LBA accepted if set to 1 */ + u8 reserved1:3; + + u8 page_code:6; + u8 pc:2; /* page control */ +#endif + u8 reserved3[4]; + u8 alloc_len_msb; + u8 alloc_len_lsb; + u8 control; +}; + +#define SCSI_CDB10_GET_AL(cdb) \ + ((cdb)->alloc_len_msb << 8 | (cdb)->alloc_len_lsb) + +#define SCSI_CDB10_SET_AL(cdb, al) { \ + (cdb)->alloc_len_msb = al >> 8; \ + (cdb)->alloc_len_lsb = al & 0xFF; \ +} + +#define SCSI_CDB6_GET_AL(cdb) ((cdb)->alloc_len) + +#define SCSI_CDB6_SET_AL(cdb, al) { \ + (cdb)->alloc_len = al; \ +} + +/* + * page control field values + */ +#define SCSI_PC_CURRENT_VALUES 0x0 +#define SCSI_PC_CHANGEABLE_VALUES 0x1 +#define SCSI_PC_DEFAULT_VALUES 0x2 +#define SCSI_PC_SAVED_VALUES 0x3 + +/* + * SCSI mode page codes + */ +#define SCSI_MP_VENDOR_SPEC 0x00 +#define SCSI_MP_DISC_RECN 0x02 /* disconnect-reconnect page */ +#define SCSI_MP_FORMAT_DEVICE 0x03 +#define SCSI_MP_RDG 0x04 /* rigid disk geometry page */ +#define SCSI_MP_FDP 0x05 /* flexible disk page */ +#define SCSI_MP_CACHING 0x08 /* caching page */ +#define SCSI_MP_CONTROL 0x0A /* control mode page */ +#define SCSI_MP_MED_TYPES_SUP 0x0B /* medium types supported page */ +#define SCSI_MP_INFO_EXCP_CNTL 0x1C /* informational exception control */ +#define SCSI_MP_ALL 0x3F /* return all pages - mode sense only */ + +/* + * mode parameter header + */ +struct scsi_mode_param_header6_s{ + u8 mode_datalen; + u8 medium_type; + + /* + * device specific parameters expanded for direct access devices + */ +#ifdef __BIGENDIAN + u32 wp:1; /* write protected */ + u32 reserved1:2; + u32 dpofua:1; /* disable page out + force unit access + */ + u32 reserved2:4; +#else + u32 reserved2:4; + u32 dpofua:1; /* disable page out + force unit access + */ + u32 reserved1:2; + u32 wp:1; /* write protected */ +#endif + + u8 block_desclen; +}; + +struct scsi_mode_param_header10_s{ + u32 mode_datalen:16; + u32 medium_type:8; + + /* + * device specific parameters expanded for direct access devices + */ +#ifdef __BIGENDIAN + u32 wp:1; /* write protected */ + u32 reserved1:2; + u32 dpofua:1; /* disable page out + force unit access + */ + u32 reserved2:4; +#else + u32 reserved2:4; + u32 dpofua:1; /* disable page out + force unit access + */ + u32 reserved1:2; + u32 wp:1; /* write protected */ +#endif + +#ifdef __BIGENDIAN + u32 reserved3:7; + u32 longlba:1; +#else + u32 longlba:1; + u32 reserved3:7; +#endif + u32 reserved4:8; + u32 block_desclen:16; +}; + +/* + * mode parameter block descriptor + */ +struct scsi_mode_param_desc_s{ + u32 nblks; + u32 density_code:8; + u32 block_length:24; +}; + +/* + * Disconnect-reconnect mode page format + */ +struct scsi_mp_disc_recn_s{ +#ifdef __BIGENDIAN + u8 ps:1; + u8 reserved1:1; + u8 page_code:6; +#else + u8 page_code:6; + u8 reserved1:1; + u8 ps:1; +#endif + u8 page_len; + u8 buf_full_ratio; + u8 buf_empty_ratio; + + u8 bil_msb; /* bus inactivity limit -MSB */ + u8 bil_lsb; /* bus inactivity limit -LSB */ + + u8 dtl_msb; /* disconnect time limit - MSB */ + u8 dtl_lsb; /* disconnect time limit - LSB */ + + u8 ctl_msb; /* connect time limit - MSB */ + u8 ctl_lsb; /* connect time limit - LSB */ + + u8 max_burst_len_msb; + u8 max_burst_len_lsb; +#ifdef __BIGENDIAN + u8 emdp:1; /* enable modify data pointers */ + u8 fa:3; /* fair arbitration */ + u8 dimm:1; /* disconnect immediate */ + u8 dtdc:3; /* data transfer disconnect control */ +#else + u8 dtdc:3; /* data transfer disconnect control */ + u8 dimm:1; /* disconnect immediate */ + u8 fa:3; /* fair arbitration */ + u8 emdp:1; /* enable modify data pointers */ +#endif + + u8 reserved3; + + u8 first_burst_len_msb; + u8 first_burst_len_lsb; +}; + +/* + * SCSI format device mode page + */ +struct scsi_mp_format_device_s{ +#ifdef __BIGENDIAN + u32 ps:1; + u32 reserved1:1; + u32 page_code:6; +#else + u32 page_code:6; + u32 reserved1:1; + u32 ps:1; +#endif + u32 page_len:8; + u32 tracks_per_zone:16; + + u32 a_sec_per_zone:16; + u32 a_tracks_per_zone:16; + + u32 a_tracks_per_lun:16; /* alternate tracks/lun-MSB */ + u32 sec_per_track:16; /* sectors/track-MSB */ + + u32 bytes_per_sector:16; + u32 interleave:16; + + u32 tsf:16; /* track skew factor-MSB */ + u32 csf:16; /* cylinder skew factor-MSB */ + +#ifdef __BIGENDIAN + u32 ssec:1; /* soft sector formatting */ + u32 hsec:1; /* hard sector formatting */ + u32 rmb:1; /* removable media */ + u32 surf:1; /* surface */ + u32 reserved2:4; +#else + u32 reserved2:4; + u32 surf:1; /* surface */ + u32 rmb:1; /* removable media */ + u32 hsec:1; /* hard sector formatting */ + u32 ssec:1; /* soft sector formatting */ +#endif + u32 reserved3:24; +}; + +/* + * SCSI rigid disk device geometry page + */ +struct scsi_mp_rigid_device_geometry_s{ +#ifdef __BIGENDIAN + u32 ps:1; + u32 reserved1:1; + u32 page_code:6; +#else + u32 page_code:6; + u32 reserved1:1; + u32 ps:1; +#endif + u32 page_len:8; + u32 num_cylinders0:8; + u32 num_cylinders1:8; + + u32 num_cylinders2:8; + u32 num_heads:8; + u32 scwp0:8; + u32 scwp1:8; + + u32 scwp2:8; + u32 scrwc0:8; + u32 scrwc1:8; + u32 scrwc2:8; + + u32 dsr:16; + u32 lscyl0:8; + u32 lscyl1:8; + + u32 lscyl2:8; +#ifdef __BIGENDIAN + u32 reserved2:6; + u32 rpl:2; /* rotational position locking */ +#else + u32 rpl:2; /* rotational position locking */ + u32 reserved2:6; +#endif + u32 rot_off:8; + u32 reserved3:8; + + u32 med_rot_rate:16; + u32 reserved4:16; +}; + +/* + * SCSI caching mode page + */ +struct scsi_mp_caching_s{ +#ifdef __BIGENDIAN + u8 ps:1; + u8 res1:1; + u8 page_code:6; +#else + u8 page_code:6; + u8 res1:1; + u8 ps:1; +#endif + u8 page_len; +#ifdef __BIGENDIAN + u8 ic:1; /* initiator control */ + u8 abpf:1; /* abort pre-fetch */ + u8 cap:1; /* caching analysis permitted */ + u8 disc:1; /* discontinuity */ + u8 size:1; /* size enable */ + u8 wce:1; /* write cache enable */ + u8 mf:1; /* multiplication factor */ + u8 rcd:1; /* read cache disable */ + + u8 drrp:4; /* demand read retention priority */ + u8 wrp:4; /* write retention priority */ +#else + u8 rcd:1; /* read cache disable */ + u8 mf:1; /* multiplication factor */ + u8 wce:1; /* write cache enable */ + u8 size:1; /* size enable */ + u8 disc:1; /* discontinuity */ + u8 cap:1; /* caching analysis permitted */ + u8 abpf:1; /* abort pre-fetch */ + u8 ic:1; /* initiator control */ + + u8 wrp:4; /* write retention priority */ + u8 drrp:4; /* demand read retention priority */ +#endif + u8 dptl[2];/* disable pre-fetch transfer length */ + u8 min_prefetch[2]; + u8 max_prefetch[2]; + u8 max_prefetch_limit[2]; +#ifdef __BIGENDIAN + u8 fsw:1; /* force sequential write */ + u8 lbcss:1;/* logical block cache segment size */ + u8 dra:1; /* disable read ahead */ + u8 vs:2; /* vendor specific */ + u8 res2:3; +#else + u8 res2:3; + u8 vs:2; /* vendor specific */ + u8 dra:1; /* disable read ahead */ + u8 lbcss:1;/* logical block cache segment size */ + u8 fsw:1; /* force sequential write */ +#endif + u8 num_cache_segs; + + u8 cache_seg_size[2]; + u8 res3; + u8 non_cache_seg_size[3]; +}; + +/* + * SCSI control mode page + */ +struct scsi_mp_control_page_s{ +#ifdef __BIGENDIAN +u8 ps:1; +u8 reserved1:1; +u8 page_code:6; +#else +u8 page_code:6; +u8 reserved1:1; +u8 ps:1; +#endif + u8 page_len; +#ifdef __BIGENDIAN + u8 tst:3; /* task set type */ + u8 reserved3:3; + u8 gltsd:1; /* global logging target save disable */ + u8 rlec:1; /* report log exception condition */ + + u8 qalgo_mod:4; /* queue alogorithm modifier */ + u8 reserved4:1; + u8 qerr:2; /* queue error management */ + u8 dque:1; /* disable queuing */ + + u8 reserved5:1; + u8 rac:1; /* report a check */ + u8 reserved6:2; + u8 swp:1; /* software write protect */ + u8 raerp:1; /* ready AER permission */ + u8 uaaerp:1; /* unit attenstion AER permission */ + u8 eaerp:1; /* error AER permission */ + + u8 reserved7:5; + u8 autoload_mod:3; +#else + u8 rlec:1; /* report log exception condition */ + u8 gltsd:1; /* global logging target save disable */ + u8 reserved3:3; + u8 tst:3; /* task set type */ + + u8 dque:1; /* disable queuing */ + u8 qerr:2; /* queue error management */ + u8 reserved4:1; + u8 qalgo_mod:4; /* queue alogorithm modifier */ + + u8 eaerp:1; /* error AER permission */ + u8 uaaerp:1; /* unit attenstion AER permission */ + u8 raerp:1; /* ready AER permission */ + u8 swp:1; /* software write protect */ + u8 reserved6:2; + u8 rac:1; /* report a check */ + u8 reserved5:1; + + u8 autoload_mod:3; + u8 reserved7:5; +#endif + u8 rahp_msb; /* ready AER holdoff period - MSB */ + u8 rahp_lsb; /* ready AER holdoff period - LSB */ + + u8 busy_timeout_period_msb; + u8 busy_timeout_period_lsb; + + u8 ext_selftest_compl_time_msb; + u8 ext_selftest_compl_time_lsb; +}; + +/* + * SCSI medium types supported mode page + */ +struct scsi_mp_medium_types_sup_s{ +#ifdef __BIGENDIAN + u8 ps:1; + u8 reserved1:1; + u8 page_code:6; +#else + u8 page_code:6; + u8 reserved1:1; + u8 ps:1; +#endif + u8 page_len; + + u8 reserved3[2]; + u8 med_type1_sup; /* medium type one supported */ + u8 med_type2_sup; /* medium type two supported */ + u8 med_type3_sup; /* medium type three supported */ + u8 med_type4_sup; /* medium type four supported */ +}; + +/* + * SCSI informational exception control mode page + */ +struct scsi_mp_info_excpt_cntl_s{ +#ifdef __BIGENDIAN + u8 ps:1; + u8 reserved1:1; + u8 page_code:6; +#else + u8 page_code:6; + u8 reserved1:1; + u8 ps:1; +#endif + u8 page_len; +#ifdef __BIGENDIAN + u8 perf:1; /* performance */ + u8 reserved3:1; + u8 ebf:1; /* enable background fucntion */ + u8 ewasc:1; /* enable warning */ + u8 dexcpt:1; /* disable exception control */ + u8 test:1; /* enable test device failure + * notification + */ + u8 reserved4:1; + u8 log_error:1; + + u8 reserved5:4; + u8 mrie:4; /* method of reporting info + * exceptions + */ +#else + u8 log_error:1; + u8 reserved4:1; + u8 test:1; /* enable test device failure + * notification + */ + u8 dexcpt:1; /* disable exception control */ + u8 ewasc:1; /* enable warning */ + u8 ebf:1; /* enable background fucntion */ + u8 reserved3:1; + u8 perf:1; /* performance */ + + u8 mrie:4; /* method of reporting info + * exceptions + */ + u8 reserved5:4; +#endif + u8 interval_timer_msb; + u8 interval_timer_lsb; + + u8 report_count_msb; + u8 report_count_lsb; +}; + +/* + * Methods of reporting informational exceptions + */ +#define SCSI_MP_IEC_NO_REPORT 0x0 /* no reporting of exceptions */ +#define SCSI_MP_IEC_AER 0x1 /* async event reporting */ +#define SCSI_MP_IEC_UNIT_ATTN 0x2 /* generate unit attenstion */ +#define SCSI_MO_IEC_COND_REC_ERR 0x3 /* conditionally generate recovered + * error + */ +#define SCSI_MP_IEC_UNCOND_REC_ERR 0x4 /* unconditionally generate recovered + * error + */ +#define SCSI_MP_IEC_NO_SENSE 0x5 /* generate no sense */ +#define SCSI_MP_IEC_ON_REQUEST 0x6 /* only report exceptions on request */ + +/* + * SCSI flexible disk page + */ +struct scsi_mp_flexible_disk_s{ +#ifdef __BIGENDIAN + u8 ps:1; + u8 reserved1:1; + u8 page_code:6; +#else + u8 page_code:6; + u8 reserved1:1; + u8 ps:1; +#endif + u8 page_len; + + u8 transfer_rate_msb; + u8 transfer_rate_lsb; + + u8 num_heads; + u8 num_sectors; + + u8 bytes_per_sector_msb; + u8 bytes_per_sector_lsb; + + u8 num_cylinders_msb; + u8 num_cylinders_lsb; + + u8 sc_wpc_msb; /* starting cylinder-write + * precompensation msb + */ + u8 sc_wpc_lsb; /* starting cylinder-write + * precompensation lsb + */ + u8 sc_rwc_msb; /* starting cylinder-reduced write + * current msb + */ + u8 sc_rwc_lsb; /* starting cylinder-reduced write + * current lsb + */ + + u8 dev_step_rate_msb; + u8 dev_step_rate_lsb; + + u8 dev_step_pulse_width; + + u8 head_sd_msb; /* head settle delay msb */ + u8 head_sd_lsb; /* head settle delay lsb */ + + u8 motor_on_delay; + u8 motor_off_delay; +#ifdef __BIGENDIAN + u8 trdy:1; /* true ready bit */ + u8 ssn:1; /* start sector number bit */ + u8 mo:1; /* motor on bit */ + u8 reserved3:5; + + u8 reserved4:4; + u8 spc:4; /* step pulse per cylinder */ +#else + u8 reserved3:5; + u8 mo:1; /* motor on bit */ + u8 ssn:1; /* start sector number bit */ + u8 trdy:1; /* true ready bit */ + + u8 spc:4; /* step pulse per cylinder */ + u8 reserved4:4; +#endif + u8 write_comp; + u8 head_load_delay; + u8 head_unload_delay; +#ifdef __BIGENDIAN + u8 pin34:4; /* pin34 usage */ + u8 pin2:4; /* pin2 usage */ + + u8 pin4:4; /* pin4 usage */ + u8 pin1:4; /* pin1 usage */ +#else + u8 pin2:4; /* pin2 usage */ + u8 pin34:4; /* pin34 usage */ + + u8 pin1:4; /* pin1 usage */ + u8 pin4:4; /* pin4 usage */ +#endif + u8 med_rot_rate_msb; + u8 med_rot_rate_lsb; + + u8 reserved5[2]; +}; + +struct scsi_mode_page_format_data6_s{ + struct scsi_mode_param_header6_s mph; /* mode page header */ + struct scsi_mode_param_desc_s desc; /* block descriptor */ + struct scsi_mp_format_device_s format; /* format device data */ +}; + +struct scsi_mode_page_format_data10_s{ + struct scsi_mode_param_header10_s mph; /* mode page header */ + struct scsi_mode_param_desc_s desc; /* block descriptor */ + struct scsi_mp_format_device_s format; /* format device data */ +}; + +struct scsi_mode_page_rdg_data6_s{ + struct scsi_mode_param_header6_s mph; /* mode page header */ + struct scsi_mode_param_desc_s desc; /* block descriptor */ + struct scsi_mp_rigid_device_geometry_s rdg; + /* rigid geometry data */ +}; + +struct scsi_mode_page_rdg_data10_s{ + struct scsi_mode_param_header10_s mph; /* mode page header */ + struct scsi_mode_param_desc_s desc; /* block descriptor */ + struct scsi_mp_rigid_device_geometry_s rdg; + /* rigid geometry data */ +}; + +struct scsi_mode_page_cache6_s{ + struct scsi_mode_param_header6_s mph; /* mode page header */ + struct scsi_mode_param_desc_s desc; /* block descriptor */ + struct scsi_mp_caching_s cache; /* cache page data */ +}; + +struct scsi_mode_page_cache10_s{ + struct scsi_mode_param_header10_s mph; /* mode page header */ + struct scsi_mode_param_desc_s desc; /* block descriptor */ + struct scsi_mp_caching_s cache; /* cache page data */ +}; + +/* -------------------------------------------------------------- + * Format Unit command + * ------------------------------------------------------------ + */ + +/* + * Format Unit CDB + */ +struct scsi_format_unit_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 res1:3; + u8 fmtdata:1; /* if set, data out phase has format + * data + */ + u8 cmplst:1; /* if set, defect list is complete */ + u8 def_list:3; /* format of defect descriptor is + * fmtdata =1 + */ +#else + u8 def_list:3; /* format of defect descriptor is + * fmtdata = 1 + */ + u8 cmplst:1; /* if set, defect list is complete */ + u8 fmtdata:1; /* if set, data out phase has format + * data + */ + u8 res1:3; +#endif + u8 interleave_msb; + u8 interleave_lsb; + u8 vendor_spec; + u8 control; +}; + +/* + * h + */ +struct scsi_reserve6_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved:3; + u8 obsolete:4; + u8 extent:1; +#else + u8 extent:1; + u8 obsolete:4; + u8 reserved:3; +#endif + u8 reservation_id; + u16 param_list_len; + u8 control; +}; + +/* + * h + */ +struct scsi_release6_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:3; + u8 obsolete:4; + u8 extent:1; +#else + u8 extent:1; + u8 obsolete:4; + u8 reserved1:3; +#endif + u8 reservation_id; + u16 reserved2; + u8 control; +}; + +/* + * h + */ +struct scsi_reserve10_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:3; + u8 third_party:1; + u8 reserved2:2; + u8 long_id:1; + u8 extent:1; +#else + u8 extent:1; + u8 long_id:1; + u8 reserved2:2; + u8 third_party:1; + u8 reserved1:3; +#endif + u8 reservation_id; + u8 third_pty_dev_id; + u8 reserved3; + u8 reserved4; + u8 reserved5; + u16 param_list_len; + u8 control; +}; + +struct scsi_release10_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:3; + u8 third_party:1; + u8 reserved2:2; + u8 long_id:1; + u8 extent:1; +#else + u8 extent:1; + u8 long_id:1; + u8 reserved2:2; + u8 third_party:1; + u8 reserved1:3; +#endif + u8 reservation_id; + u8 third_pty_dev_id; + u8 reserved3; + u8 reserved4; + u8 reserved5; + u16 param_list_len; + u8 control; +}; + +struct scsi_verify10_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 lun:3; + u8 dpo:1; + u8 reserved:2; + u8 bytchk:1; + u8 reladdr:1; +#else + u8 reladdr:1; + u8 bytchk:1; + u8 reserved:2; + u8 dpo:1; + u8 lun:3; +#endif + u8 lba0; + u8 lba1; + u8 lba2; + u8 lba3; + u8 reserved1; + u8 verification_len0; + u8 verification_len1; + u8 control_byte; +}; + +struct scsi_request_sense_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 lun:3; + u8 reserved:5; +#else + u8 reserved:5; + u8 lun:3; +#endif + u8 reserved0; + u8 reserved1; + u8 alloc_len; + u8 control_byte; +}; + +/* ------------------------------------------------------------ + * SCSI status byte values + * ------------------------------------------------------------ + */ +#define SCSI_STATUS_GOOD 0x00 +#define SCSI_STATUS_CHECK_CONDITION 0x02 +#define SCSI_STATUS_CONDITION_MET 0x04 +#define SCSI_STATUS_BUSY 0x08 +#define SCSI_STATUS_INTERMEDIATE 0x10 +#define SCSI_STATUS_ICM 0x14 /* intermediate condition met */ +#define SCSI_STATUS_RESERVATION_CONFLICT 0x18 +#define SCSI_STATUS_COMMAND_TERMINATED 0x22 +#define SCSI_STATUS_QUEUE_FULL 0x28 +#define SCSI_STATUS_ACA_ACTIVE 0x30 + +#define SCSI_MAX_ALLOC_LEN 0xFF /* maximum allocarion length + * in CDBs + */ + +#define SCSI_OP_WRITE_VERIFY10 0x2E +#define SCSI_OP_WRITE_VERIFY12 0xAE +#define SCSI_OP_UNDEF 0xFF + +/* + * SCSI WRITE-VERIFY(10) command + */ +struct scsi_write_verify10_s{ + u8 opcode; +#ifdef __BIGENDIAN + u8 reserved1:3; + u8 dpo:1; /* Disable Page Out */ + u8 reserved2:1; + u8 ebp:1; /* erse by-pass */ + u8 bytchk:1; /* byte check */ + u8 rel_adr:1; /* relative address */ +#else + u8 rel_adr:1; /* relative address */ + u8 bytchk:1; /* byte check */ + u8 ebp:1; /* erse by-pass */ + u8 reserved2:1; + u8 dpo:1; /* Disable Page Out */ + u8 reserved1:3; +#endif + u8 lba0; /* logical block address - MSB */ + u8 lba1; + u8 lba2; + u8 lba3; /* LSB */ + u8 reserved3; + u8 xfer_length0; /* transfer length in blocks - MSB */ + u8 xfer_length1; /* LSB */ + u8 control; +}; + +#pragma pack() + +#endif /* __SCSI_H__ */ diff --git a/drivers/scsi/bfa/include/protocol/types.h b/drivers/scsi/bfa/include/protocol/types.h new file mode 100644 index 000000000000..2875a6cced3b --- /dev/null +++ b/drivers/scsi/bfa/include/protocol/types.h @@ -0,0 +1,42 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * types.h Protocol defined base types + */ + +#ifndef __TYPES_H__ +#define __TYPES_H__ + +#include <bfa_os_inc.h> + +#define wwn_t u64 +#define lun_t u64 + +#define WWN_NULL (0) +#define FC_SYMNAME_MAX 256 /* max name server symbolic name size */ +#define FC_ALPA_MAX 128 + +#pragma pack(1) + +#define MAC_ADDRLEN (6) +struct mac_s { u8 mac[MAC_ADDRLEN]; }; +#define mac_t struct mac_s + +#pragma pack() + +#endif diff --git a/drivers/scsi/bfa/loop.c b/drivers/scsi/bfa/loop.c new file mode 100644 index 000000000000..a418dedebe9e --- /dev/null +++ b/drivers/scsi/bfa/loop.c @@ -0,0 +1,422 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * port_loop.c vport private loop implementation. + */ +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "fcs_trcmod.h" +#include "lport_priv.h" + +BFA_TRC_FILE(FCS, LOOP); + +/** + * ALPA to LIXA bitmap mapping + * + * ALPA 0x00 (Word 0, Bit 30) is invalid for N_Ports. Also Word 0 Bit 31 + * is for L_bit (login required) and is filled as ALPA 0x00 here. + */ +static const u8 port_loop_alpa_map[] = { + 0xEF, 0xE8, 0xE4, 0xE2, 0xE1, 0xE0, 0xDC, 0xDA, /* Word 3 Bits 0..7 */ + 0xD9, 0xD6, 0xD5, 0xD4, 0xD3, 0xD2, 0xD1, 0xCE, /* Word 3 Bits 8..15 */ + 0xCD, 0xCC, 0xCB, 0xCA, 0xC9, 0xC7, 0xC6, 0xC5, /* Word 3 Bits 16..23 */ + 0xC3, 0xBC, 0xBA, 0xB9, 0xB6, 0xB5, 0xB4, 0xB3, /* Word 3 Bits 24..31 */ + + 0xB2, 0xB1, 0xAE, 0xAD, 0xAC, 0xAB, 0xAA, 0xA9, /* Word 2 Bits 0..7 */ + 0xA7, 0xA6, 0xA5, 0xA3, 0x9F, 0x9E, 0x9D, 0x9B, /* Word 2 Bits 8..15 */ + 0x98, 0x97, 0x90, 0x8F, 0x88, 0x84, 0x82, 0x81, /* Word 2 Bits 16..23 */ + 0x80, 0x7C, 0x7A, 0x79, 0x76, 0x75, 0x74, 0x73, /* Word 2 Bits 24..31 */ + + 0x72, 0x71, 0x6E, 0x6D, 0x6C, 0x6B, 0x6A, 0x69, /* Word 1 Bits 0..7 */ + 0x67, 0x66, 0x65, 0x63, 0x5C, 0x5A, 0x59, 0x56, /* Word 1 Bits 8..15 */ + 0x55, 0x54, 0x53, 0x52, 0x51, 0x4E, 0x4D, 0x4C, /* Word 1 Bits 16..23 */ + 0x4B, 0x4A, 0x49, 0x47, 0x46, 0x45, 0x43, 0x3C, /* Word 1 Bits 24..31 */ + + 0x3A, 0x39, 0x36, 0x35, 0x34, 0x33, 0x32, 0x31, /* Word 0 Bits 0..7 */ + 0x2E, 0x2D, 0x2C, 0x2B, 0x2A, 0x29, 0x27, 0x26, /* Word 0 Bits 8..15 */ + 0x25, 0x23, 0x1F, 0x1E, 0x1D, 0x1B, 0x18, 0x17, /* Word 0 Bits 16..23 */ + 0x10, 0x0F, 0x08, 0x04, 0x02, 0x01, 0x00, 0x00, /* Word 0 Bits 24..31 */ +}; + +/* + * Local Functions + */ +bfa_status_t bfa_fcs_port_loop_send_plogi(struct bfa_fcs_port_s *port, + u8 alpa); + +void bfa_fcs_port_loop_plogi_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); + +bfa_status_t bfa_fcs_port_loop_send_adisc(struct bfa_fcs_port_s *port, + u8 alpa); + +void bfa_fcs_port_loop_adisc_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); + +bfa_status_t bfa_fcs_port_loop_send_plogi_acc(struct bfa_fcs_port_s *port, + u8 alpa); + +void bfa_fcs_port_loop_plogi_acc_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); + +bfa_status_t bfa_fcs_port_loop_send_adisc_acc(struct bfa_fcs_port_s *port, + u8 alpa); + +void bfa_fcs_port_loop_adisc_acc_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +/** + * Called by port to initializar in provate LOOP topology. + */ +void +bfa_fcs_port_loop_init(struct bfa_fcs_port_s *port) +{ +} + +/** + * Called by port to notify transition to online state. + */ +void +bfa_fcs_port_loop_online(struct bfa_fcs_port_s *port) +{ + + u8 num_alpa = port->port_topo.ploop.num_alpa; + u8 *alpa_pos_map = port->port_topo.ploop.alpa_pos_map; + struct bfa_fcs_rport_s *r_port; + int ii = 0; + + /* + * If the port role is Initiator Mode, create Rports. + */ + if (port->port_cfg.roles == BFA_PORT_ROLE_FCP_IM) { + /* + * Check if the ALPA positional bitmap is available. + * if not, we send PLOGI to all possible ALPAs. + */ + if (num_alpa > 0) { + for (ii = 0; ii < num_alpa; ii++) { + /* + * ignore ALPA of bfa port + */ + if (alpa_pos_map[ii] != port->pid) { + r_port = bfa_fcs_rport_create(port, + alpa_pos_map[ii]); + } + } + } else { + for (ii = 0; ii < MAX_ALPA_COUNT; ii++) { + /* + * ignore ALPA of bfa port + */ + if ((port_loop_alpa_map[ii] > 0) + && (port_loop_alpa_map[ii] != port->pid)) + bfa_fcs_port_loop_send_plogi(port, + port_loop_alpa_map[ii]); + /**TBD */ + } + } + } else { + /* + * TBD Target Mode ?? + */ + } + +} + +/** + * Called by port to notify transition to offline state. + */ +void +bfa_fcs_port_loop_offline(struct bfa_fcs_port_s *port) +{ + +} + +/** + * Called by port to notify a LIP on the loop. + */ +void +bfa_fcs_port_loop_lip(struct bfa_fcs_port_s *port) +{ +} + +/** + * Local Functions. + */ +bfa_status_t +bfa_fcs_port_loop_send_plogi(struct bfa_fcs_port_s *port, u8 alpa) +{ + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp = NULL; + int len; + + bfa_trc(port->fcs, alpa); + + fcxp = bfa_fcxp_alloc(NULL, port->fcs->bfa, 0, 0, NULL, NULL, NULL, + NULL); + bfa_assert(fcxp); + + len = fc_plogi_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), alpa, + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn, + bfa_pport_get_maxfrsize(port->fcs->bfa)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, + bfa_fcs_port_loop_plogi_response, (void *)port, + FC_MAX_PDUSZ, FC_RA_TOV); + + return BFA_STATUS_OK; +} + +/** + * Called by fcxp to notify the Plogi response + */ +void +bfa_fcs_port_loop_plogi_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_s *port = (struct bfa_fcs_port_s *) cbarg; + struct fc_logi_s *plogi_resp; + struct fc_els_cmd_s *els_cmd; + + bfa_trc(port->fcs, req_status); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + /* + * @todo + * This could mean that the device with this APLA does not + * exist on the loop. + */ + + return; + } + + els_cmd = (struct fc_els_cmd_s *) BFA_FCXP_RSP_PLD(fcxp); + plogi_resp = (struct fc_logi_s *) els_cmd; + + if (els_cmd->els_code == FC_ELS_ACC) { + bfa_fcs_rport_start(port, rsp_fchs, plogi_resp); + } else { + bfa_trc(port->fcs, plogi_resp->els_cmd.els_code); + bfa_assert(0); + } +} + +bfa_status_t +bfa_fcs_port_loop_send_plogi_acc(struct bfa_fcs_port_s *port, u8 alpa) +{ + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + int len; + + bfa_trc(port->fcs, alpa); + + fcxp = bfa_fcxp_alloc(NULL, port->fcs->bfa, 0, 0, NULL, NULL, NULL, + NULL); + bfa_assert(fcxp); + + len = fc_plogi_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), alpa, + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn, + bfa_pport_get_maxfrsize(port->fcs->bfa)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, + bfa_fcs_port_loop_plogi_acc_response, + (void *)port, FC_MAX_PDUSZ, 0); /* No response + * expected + */ + + return BFA_STATUS_OK; +} + +/* + * Plogi Acc Response + * We donot do any processing here. + */ +void +bfa_fcs_port_loop_plogi_acc_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + + struct bfa_fcs_port_s *port = (struct bfa_fcs_port_s *) cbarg; + + bfa_trc(port->fcs, port->pid); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + return; + } +} + +bfa_status_t +bfa_fcs_port_loop_send_adisc(struct bfa_fcs_port_s *port, u8 alpa) +{ + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + int len; + + bfa_trc(port->fcs, alpa); + + fcxp = bfa_fcxp_alloc(NULL, port->fcs->bfa, 0, 0, NULL, NULL, NULL, + NULL); + bfa_assert(fcxp); + + len = fc_adisc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), alpa, + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, + bfa_fcs_port_loop_adisc_response, (void *)port, + FC_MAX_PDUSZ, FC_RA_TOV); + + return BFA_STATUS_OK; +} + +/** + * Called by fcxp to notify the ADISC response + */ +void +bfa_fcs_port_loop_adisc_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_s *port = (struct bfa_fcs_port_s *) cbarg; + struct bfa_fcs_rport_s *rport; + struct fc_adisc_s *adisc_resp; + struct fc_els_cmd_s *els_cmd; + u32 pid = rsp_fchs->s_id; + + bfa_trc(port->fcs, req_status); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + /* + * TBD : we may need to retry certain requests + */ + bfa_fcxp_free(fcxp); + return; + } + + els_cmd = (struct fc_els_cmd_s *) BFA_FCXP_RSP_PLD(fcxp); + adisc_resp = (struct fc_adisc_s *) els_cmd; + + if (els_cmd->els_code == FC_ELS_ACC) { + } else { + bfa_trc(port->fcs, adisc_resp->els_cmd.els_code); + + /* + * TBD: we may need to check for reject codes and retry + */ + rport = bfa_fcs_port_get_rport_by_pid(port, pid); + if (rport) { + list_del(&rport->qe); + bfa_fcs_rport_delete(rport); + } + + } + return; +} + +bfa_status_t +bfa_fcs_port_loop_send_adisc_acc(struct bfa_fcs_port_s *port, u8 alpa) +{ + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + int len; + + bfa_trc(port->fcs, alpa); + + fcxp = bfa_fcxp_alloc(NULL, port->fcs->bfa, 0, 0, NULL, NULL, NULL, + NULL); + bfa_assert(fcxp); + + len = fc_adisc_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), alpa, + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, + bfa_fcs_port_loop_adisc_acc_response, + (void *)port, FC_MAX_PDUSZ, 0); /* no reponse + * expected + */ + + return BFA_STATUS_OK; +} + +/* + * Adisc Acc Response + * We donot do any processing here. + */ +void +bfa_fcs_port_loop_adisc_acc_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + + struct bfa_fcs_port_s *port = (struct bfa_fcs_port_s *) cbarg; + + bfa_trc(port->fcs, port->pid); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + return; + } +} diff --git a/drivers/scsi/bfa/lport_api.c b/drivers/scsi/bfa/lport_api.c new file mode 100644 index 000000000000..8f51a83f1834 --- /dev/null +++ b/drivers/scsi/bfa/lport_api.c @@ -0,0 +1,291 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * port_api.c BFA FCS port + */ + +#include <fcs/bfa_fcs.h> +#include <fcs/bfa_fcs_lport.h> +#include <fcs/bfa_fcs_rport.h> +#include "fcs_rport.h" +#include "fcs_fabric.h" +#include "fcs_trcmod.h" +#include "fcs_vport.h" + +BFA_TRC_FILE(FCS, PORT_API); + + + +/** + * fcs_port_api BFA FCS port API + */ + +void +bfa_fcs_cfg_base_port(struct bfa_fcs_s *fcs, struct bfa_port_cfg_s *port_cfg) +{ +} + +struct bfa_fcs_port_s * +bfa_fcs_get_base_port(struct bfa_fcs_s *fcs) +{ + return (&fcs->fabric.bport); +} + +wwn_t +bfa_fcs_port_get_rport(struct bfa_fcs_port_s *port, wwn_t wwn, int index, + int nrports, bfa_boolean_t bwwn) +{ + struct list_head *qh, *qe; + struct bfa_fcs_rport_s *rport = NULL; + int i; + struct bfa_fcs_s *fcs; + + if (port == NULL || nrports == 0) + return (wwn_t) 0; + + fcs = port->fcs; + bfa_trc(fcs, (u32) nrports); + + i = 0; + qh = &port->rport_q; + qe = bfa_q_first(qh); + + while ((qe != qh) && (i < nrports)) { + rport = (struct bfa_fcs_rport_s *)qe; + if (bfa_os_ntoh3b(rport->pid) > 0xFFF000) { + qe = bfa_q_next(qe); + bfa_trc(fcs, (u32) rport->pwwn); + bfa_trc(fcs, rport->pid); + bfa_trc(fcs, i); + continue; + } + + if (bwwn) { + if (!memcmp(&wwn, &rport->pwwn, 8)) + break; + } else { + if (i == index) + break; + } + + i++; + qe = bfa_q_next(qe); + } + + bfa_trc(fcs, i); + if (rport) { + return rport->pwwn; + } else { + return (wwn_t) 0; + } +} + +void +bfa_fcs_port_get_rports(struct bfa_fcs_port_s *port, wwn_t rport_wwns[], + int *nrports) +{ + struct list_head *qh, *qe; + struct bfa_fcs_rport_s *rport = NULL; + int i; + struct bfa_fcs_s *fcs; + + if (port == NULL || rport_wwns == NULL || *nrports == 0) + return; + + fcs = port->fcs; + bfa_trc(fcs, (u32) *nrports); + + i = 0; + qh = &port->rport_q; + qe = bfa_q_first(qh); + + while ((qe != qh) && (i < *nrports)) { + rport = (struct bfa_fcs_rport_s *)qe; + if (bfa_os_ntoh3b(rport->pid) > 0xFFF000) { + qe = bfa_q_next(qe); + bfa_trc(fcs, (u32) rport->pwwn); + bfa_trc(fcs, rport->pid); + bfa_trc(fcs, i); + continue; + } + + rport_wwns[i] = rport->pwwn; + + i++; + qe = bfa_q_next(qe); + } + + bfa_trc(fcs, i); + *nrports = i; + return; +} + +/* + * Iterate's through all the rport's in the given port to + * determine the maximum operating speed. + */ +enum bfa_pport_speed +bfa_fcs_port_get_rport_max_speed(struct bfa_fcs_port_s *port) +{ + struct list_head *qh, *qe; + struct bfa_fcs_rport_s *rport = NULL; + struct bfa_fcs_s *fcs; + enum bfa_pport_speed max_speed = 0; + struct bfa_pport_attr_s pport_attr; + enum bfa_pport_speed pport_speed; + + if (port == NULL) + return 0; + + fcs = port->fcs; + + /* + * Get Physical port's current speed + */ + bfa_pport_get_attr(port->fcs->bfa, &pport_attr); + pport_speed = pport_attr.speed; + bfa_trc(fcs, pport_speed); + + qh = &port->rport_q; + qe = bfa_q_first(qh); + + while (qe != qh) { + rport = (struct bfa_fcs_rport_s *)qe; + if ((bfa_os_ntoh3b(rport->pid) > 0xFFF000) + || (bfa_fcs_rport_get_state(rport) == BFA_RPORT_OFFLINE)) { + qe = bfa_q_next(qe); + continue; + } + + if ((rport->rpf.rpsc_speed == BFA_PPORT_SPEED_8GBPS) + || (rport->rpf.rpsc_speed > pport_speed)) { + max_speed = rport->rpf.rpsc_speed; + break; + } else if (rport->rpf.rpsc_speed > max_speed) { + max_speed = rport->rpf.rpsc_speed; + } + + qe = bfa_q_next(qe); + } + + bfa_trc(fcs, max_speed); + return max_speed; +} + +struct bfa_fcs_port_s * +bfa_fcs_lookup_port(struct bfa_fcs_s *fcs, u16 vf_id, wwn_t lpwwn) +{ + struct bfa_fcs_vport_s *vport; + bfa_fcs_vf_t *vf; + + bfa_assert(fcs != NULL); + + vf = bfa_fcs_vf_lookup(fcs, vf_id); + if (vf == NULL) { + bfa_trc(fcs, vf_id); + return (NULL); + } + + if (!lpwwn || (vf->bport.port_cfg.pwwn == lpwwn)) + return (&vf->bport); + + vport = bfa_fcs_fabric_vport_lookup(vf, lpwwn); + if (vport) + return (&vport->lport); + + return (NULL); +} + +/* + * API corresponding to VmWare's NPIV_VPORT_GETINFO. + */ +void +bfa_fcs_port_get_info(struct bfa_fcs_port_s *port, + struct bfa_port_info_s *port_info) +{ + + bfa_trc(port->fcs, port->fabric->fabric_name); + + if (port->vport == NULL) { + /* + * This is a Physical port + */ + port_info->port_type = BFA_PORT_TYPE_PHYSICAL; + + /* + * @todo : need to fix the state & reason + */ + port_info->port_state = 0; + port_info->offline_reason = 0; + + port_info->port_wwn = bfa_fcs_port_get_pwwn(port); + port_info->node_wwn = bfa_fcs_port_get_nwwn(port); + + port_info->max_vports_supp = bfa_fcs_vport_get_max(port->fcs); + port_info->num_vports_inuse = + bfa_fcs_fabric_vport_count(port->fabric); + port_info->max_rports_supp = BFA_FCS_MAX_RPORTS_SUPP; + port_info->num_rports_inuse = port->num_rports; + } else { + /* + * This is a virtual port + */ + port_info->port_type = BFA_PORT_TYPE_VIRTUAL; + + /* + * @todo : need to fix the state & reason + */ + port_info->port_state = 0; + port_info->offline_reason = 0; + + port_info->port_wwn = bfa_fcs_port_get_pwwn(port); + port_info->node_wwn = bfa_fcs_port_get_nwwn(port); + } +} + +void +bfa_fcs_port_get_stats(struct bfa_fcs_port_s *fcs_port, + struct bfa_port_stats_s *port_stats) +{ + bfa_os_memcpy(port_stats, &fcs_port->stats, + sizeof(struct bfa_port_stats_s)); + return; +} + +void +bfa_fcs_port_clear_stats(struct bfa_fcs_port_s *fcs_port) +{ + bfa_os_memset(&fcs_port->stats, 0, sizeof(struct bfa_port_stats_s)); + return; +} + +void +bfa_fcs_port_enable_ipfc_roles(struct bfa_fcs_port_s *fcs_port) +{ + fcs_port->port_cfg.roles |= BFA_PORT_ROLE_FCP_IPFC; + return; +} + +void +bfa_fcs_port_disable_ipfc_roles(struct bfa_fcs_port_s *fcs_port) +{ + fcs_port->port_cfg.roles &= ~BFA_PORT_ROLE_FCP_IPFC; + return; +} + + diff --git a/drivers/scsi/bfa/lport_priv.h b/drivers/scsi/bfa/lport_priv.h new file mode 100644 index 000000000000..dbae370a599a --- /dev/null +++ b/drivers/scsi/bfa/lport_priv.h @@ -0,0 +1,82 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#ifndef __VP_PRIV_H__ +#define __VP_PRIV_H__ + +#include <fcs/bfa_fcs_lport.h> +#include <fcs/bfa_fcs_vport.h> + +/* + * Functions exported by vps + */ +void bfa_fcs_vport_init(struct bfa_fcs_vport_s *vport); + +/* + * Functions exported by vps + */ +void bfa_fcs_vps_online(struct bfa_fcs_port_s *port); +void bfa_fcs_vps_offline(struct bfa_fcs_port_s *port); +void bfa_fcs_vps_lip(struct bfa_fcs_port_s *port); + +/* + * Functions exported by port_fab + */ +void bfa_fcs_port_fab_init(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_fab_online(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_fab_offline(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_fab_rx_frame(struct bfa_fcs_port_s *port, + u8 *rx_frame, u32 len); + +/* + * Functions exported by VP-NS. + */ +void bfa_fcs_port_ns_init(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_ns_offline(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_ns_online(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_ns_query(struct bfa_fcs_port_s *port); + +/* + * Functions exported by VP-SCN + */ +void bfa_fcs_port_scn_init(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_scn_offline(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_scn_online(struct bfa_fcs_port_s *vport); +void bfa_fcs_port_scn_process_rscn(struct bfa_fcs_port_s *port, + struct fchs_s *rx_frame, u32 len); + +/* + * Functions exported by VP-N2N + */ + +void bfa_fcs_port_n2n_init(struct bfa_fcs_port_s *port); +void bfa_fcs_port_n2n_online(struct bfa_fcs_port_s *port); +void bfa_fcs_port_n2n_offline(struct bfa_fcs_port_s *port); +void bfa_fcs_port_n2n_rx_frame(struct bfa_fcs_port_s *port, + u8 *rx_frame, u32 len); + +/* + * Functions exported by VP-LOOP + */ +void bfa_fcs_port_loop_init(struct bfa_fcs_port_s *port); +void bfa_fcs_port_loop_online(struct bfa_fcs_port_s *port); +void bfa_fcs_port_loop_offline(struct bfa_fcs_port_s *port); +void bfa_fcs_port_loop_lip(struct bfa_fcs_port_s *port); +void bfa_fcs_port_loop_rx_frame(struct bfa_fcs_port_s *port, + u8 *rx_frame, u32 len); + +#endif /* __VP_PRIV_H__ */ diff --git a/drivers/scsi/bfa/ms.c b/drivers/scsi/bfa/ms.c new file mode 100644 index 000000000000..c96b3ca007ae --- /dev/null +++ b/drivers/scsi/bfa/ms.c @@ -0,0 +1,759 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + + +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include "lport_priv.h" + +BFA_TRC_FILE(FCS, MS); + +#define BFA_FCS_MS_CMD_MAX_RETRIES 2 +/* + * forward declarations + */ +static void bfa_fcs_port_ms_send_plogi(void *ms_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ms_timeout(void *arg); +static void bfa_fcs_port_ms_plogi_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); + +static void bfa_fcs_port_ms_send_gmal(void *ms_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ms_gmal_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_ms_send_gfn(void *ms_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ms_gfn_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +/** + * fcs_ms_sm FCS MS state machine + */ + +/** + * MS State Machine events + */ +enum port_ms_event { + MSSM_EVENT_PORT_ONLINE = 1, + MSSM_EVENT_PORT_OFFLINE = 2, + MSSM_EVENT_RSP_OK = 3, + MSSM_EVENT_RSP_ERROR = 4, + MSSM_EVENT_TIMEOUT = 5, + MSSM_EVENT_FCXP_SENT = 6, + MSSM_EVENT_PORT_FABRIC_RSCN = 7 +}; + +static void bfa_fcs_port_ms_sm_offline(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_plogi_sending(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_plogi(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_plogi_retry(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_gmal_sending(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_gmal(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_gmal_retry(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_gfn_sending(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_gfn(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_gfn_retry(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +static void bfa_fcs_port_ms_sm_online(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event); +/** + * Start in offline state - awaiting NS to send start. + */ +static void +bfa_fcs_port_ms_sm_offline(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_PORT_ONLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_plogi_sending); + bfa_fcs_port_ms_send_plogi(ms, NULL); + break; + + case MSSM_EVENT_PORT_OFFLINE: + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_plogi_sending(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_FCXP_SENT: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_plogi); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ms->port), + &ms->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_plogi(struct bfa_fcs_port_ms_s *ms, enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_RSP_ERROR: + /* + * Start timer for a delayed retry + */ + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_plogi_retry); + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ms->port), &ms->timer, + bfa_fcs_port_ms_timeout, ms, + BFA_FCS_RETRY_TIMEOUT); + break; + + case MSSM_EVENT_RSP_OK: + /* + * since plogi is done, now invoke MS related sub-modules + */ + bfa_fcs_port_fdmi_online(ms); + + /** + * if this is a Vport, go to online state. + */ + if (ms->port->vport) { + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_online); + break; + } + + /* + * For a base port we need to get the + * switch's IP address. + */ + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gmal_sending); + bfa_fcs_port_ms_send_gmal(ms, NULL); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_fcxp_discard(ms->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_plogi_retry(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_plogi_sending); + bfa_fcs_port_ms_send_plogi(ms, NULL); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_timer_stop(&ms->timer); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_online(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + /* + * now invoke MS related sub-modules + */ + bfa_fcs_port_fdmi_offline(ms); + break; + + case MSSM_EVENT_PORT_FABRIC_RSCN: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gfn_sending); + ms->retry_cnt = 0; + bfa_fcs_port_ms_send_gfn(ms, NULL); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_gmal_sending(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_FCXP_SENT: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gmal); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ms->port), + &ms->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_gmal(struct bfa_fcs_port_ms_s *ms, enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_RSP_ERROR: + /* + * Start timer for a delayed retry + */ + if (ms->retry_cnt++ < BFA_FCS_MS_CMD_MAX_RETRIES) { + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gmal_retry); + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ms->port), + &ms->timer, bfa_fcs_port_ms_timeout, ms, + BFA_FCS_RETRY_TIMEOUT); + } else { + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gfn_sending); + bfa_fcs_port_ms_send_gfn(ms, NULL); + ms->retry_cnt = 0; + } + break; + + case MSSM_EVENT_RSP_OK: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gfn_sending); + bfa_fcs_port_ms_send_gfn(ms, NULL); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_fcxp_discard(ms->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_gmal_retry(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gmal_sending); + bfa_fcs_port_ms_send_gmal(ms, NULL); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_timer_stop(&ms->timer); + break; + + default: + bfa_assert(0); + } +} + +/** + * ms_pvt MS local functions + */ + +static void +bfa_fcs_port_ms_send_gmal(void *ms_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ms_s *ms = ms_cbarg; + struct bfa_fcs_port_s *port = ms->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(port->fcs, port->pid); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &ms->fcxp_wqe, + bfa_fcs_port_ms_send_gmal, ms); + return; + } + ms->fcxp = fcxp; + + len = fc_gmal_req_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_fcs_port_get_fcid(port), + bfa_lps_get_peer_nwwn(port->fabric->lps)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ms_gmal_response, + (void *)ms, FC_MAX_PDUSZ, FC_RA_TOV); + + bfa_sm_send_event(ms, MSSM_EVENT_FCXP_SENT); +} + +static void +bfa_fcs_port_ms_gmal_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ms_s *ms = (struct bfa_fcs_port_ms_s *)cbarg; + struct bfa_fcs_port_s *port = ms->port; + struct ct_hdr_s *cthdr = NULL; + struct fcgs_gmal_resp_s *gmal_resp; + struct fc_gmal_entry_s *gmal_entry; + u32 num_entries; + u8 *rsp_str; + + bfa_trc(port->fcs, req_status); + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + gmal_resp = (struct fcgs_gmal_resp_s *)(cthdr + 1); + num_entries = bfa_os_ntohl(gmal_resp->ms_len); + if (num_entries == 0) { + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); + return; + } + /* + * The response could contain multiple Entries. + * Entries for SNMP interface, etc. + * We look for the entry with a telnet prefix. + * First "http://" entry refers to IP addr + */ + + gmal_entry = (struct fc_gmal_entry_s *)gmal_resp->ms_ma; + while (num_entries > 0) { + if (strncmp + (gmal_entry->prefix, CT_GMAL_RESP_PREFIX_HTTP, + sizeof(gmal_entry->prefix)) == 0) { + + /* + * if the IP address is terminating with a '/', + * remove it. *Byte 0 consists of the length + * of the string. + */ + rsp_str = &(gmal_entry->prefix[0]); + if (rsp_str[gmal_entry->len - 1] == '/') + rsp_str[gmal_entry->len - 1] = 0; + /* + * copy IP Address to fabric + */ + strncpy(bfa_fcs_port_get_fabric_ipaddr(port), + gmal_entry->ip_addr, + BFA_FCS_FABRIC_IPADDR_SZ); + break; + } else { + --num_entries; + ++gmal_entry; + } + } + + bfa_sm_send_event(ms, MSSM_EVENT_RSP_OK); + return; + } + + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); +} + +static void +bfa_fcs_port_ms_sm_gfn_sending(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_FCXP_SENT: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gfn); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ms->port), + &ms->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_gfn(struct bfa_fcs_port_ms_s *ms, enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_RSP_ERROR: + /* + * Start timer for a delayed retry + */ + if (ms->retry_cnt++ < BFA_FCS_MS_CMD_MAX_RETRIES) { + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gfn_retry); + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ms->port), + &ms->timer, bfa_fcs_port_ms_timeout, ms, + BFA_FCS_RETRY_TIMEOUT); + } else { + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_online); + ms->retry_cnt = 0; + } + break; + + case MSSM_EVENT_RSP_OK: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_online); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_fcxp_discard(ms->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ms_sm_gfn_retry(struct bfa_fcs_port_ms_s *ms, + enum port_ms_event event) +{ + bfa_trc(ms->port->fcs, ms->port->port_cfg.pwwn); + bfa_trc(ms->port->fcs, event); + + switch (event) { + case MSSM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_gfn_sending); + bfa_fcs_port_ms_send_gfn(ms, NULL); + break; + + case MSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + bfa_timer_stop(&ms->timer); + break; + + default: + bfa_assert(0); + } +} + +/** + * ms_pvt MS local functions + */ + +static void +bfa_fcs_port_ms_send_gfn(void *ms_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ms_s *ms = ms_cbarg; + struct bfa_fcs_port_s *port = ms->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(port->fcs, port->pid); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &ms->fcxp_wqe, + bfa_fcs_port_ms_send_gfn, ms); + return; + } + ms->fcxp = fcxp; + + len = fc_gfn_req_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_fcs_port_get_fcid(port), + bfa_lps_get_peer_nwwn(port->fabric->lps)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ms_gfn_response, + (void *)ms, FC_MAX_PDUSZ, FC_RA_TOV); + + bfa_sm_send_event(ms, MSSM_EVENT_FCXP_SENT); +} + +static void +bfa_fcs_port_ms_gfn_response(void *fcsarg, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ms_s *ms = (struct bfa_fcs_port_ms_s *)cbarg; + struct bfa_fcs_port_s *port = ms->port; + struct ct_hdr_s *cthdr = NULL; + wwn_t *gfn_resp; + + bfa_trc(port->fcs, req_status); + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + gfn_resp = (wwn_t *) (cthdr + 1); + /* + * check if it has actually changed + */ + if ((memcmp + ((void *)&bfa_fcs_port_get_fabric_name(port), gfn_resp, + sizeof(wwn_t)) != 0)) + bfa_fcs_fabric_set_fabric_name(port->fabric, *gfn_resp); + bfa_sm_send_event(ms, MSSM_EVENT_RSP_OK); + return; + } + + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); +} + +/** + * ms_pvt MS local functions + */ + +static void +bfa_fcs_port_ms_send_plogi(void *ms_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ms_s *ms = ms_cbarg; + struct bfa_fcs_port_s *port = ms->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(port->fcs, port->pid); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + port->stats.ms_plogi_alloc_wait++; + bfa_fcxp_alloc_wait(port->fcs->bfa, &ms->fcxp_wqe, + bfa_fcs_port_ms_send_plogi, ms); + return; + } + ms->fcxp = fcxp; + + len = fc_plogi_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_os_hton3b(FC_MGMT_SERVER), + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn, + bfa_pport_get_maxfrsize(port->fcs->bfa)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ms_plogi_response, + (void *)ms, FC_MAX_PDUSZ, FC_RA_TOV); + + port->stats.ms_plogi_sent++; + bfa_sm_send_event(ms, MSSM_EVENT_FCXP_SENT); +} + +static void +bfa_fcs_port_ms_plogi_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ms_s *ms = (struct bfa_fcs_port_ms_s *)cbarg; + + struct bfa_fcs_port_s *port = ms->port; + struct fc_els_cmd_s *els_cmd; + struct fc_ls_rjt_s *ls_rjt; + + bfa_trc(port->fcs, req_status); + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + port->stats.ms_plogi_rsp_err++; + bfa_trc(port->fcs, req_status); + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); + return; + } + + els_cmd = (struct fc_els_cmd_s *) BFA_FCXP_RSP_PLD(fcxp); + + switch (els_cmd->els_code) { + + case FC_ELS_ACC: + if (rsp_len < sizeof(struct fc_logi_s)) { + bfa_trc(port->fcs, rsp_len); + port->stats.ms_plogi_acc_err++; + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); + break; + } + port->stats.ms_plogi_accepts++; + bfa_sm_send_event(ms, MSSM_EVENT_RSP_OK); + break; + + case FC_ELS_LS_RJT: + ls_rjt = (struct fc_ls_rjt_s *) BFA_FCXP_RSP_PLD(fcxp); + + bfa_trc(port->fcs, ls_rjt->reason_code); + bfa_trc(port->fcs, ls_rjt->reason_code_expl); + + port->stats.ms_rejects++; + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); + break; + + default: + port->stats.ms_plogi_unknown_rsp++; + bfa_trc(port->fcs, els_cmd->els_code); + bfa_sm_send_event(ms, MSSM_EVENT_RSP_ERROR); + } +} + +static void +bfa_fcs_port_ms_timeout(void *arg) +{ + struct bfa_fcs_port_ms_s *ms = (struct bfa_fcs_port_ms_s *)arg; + + ms->port->stats.ms_timeouts++; + bfa_sm_send_event(ms, MSSM_EVENT_TIMEOUT); +} + + +void +bfa_fcs_port_ms_init(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ms_s *ms = BFA_FCS_GET_MS_FROM_PORT(port); + + ms->port = port; + bfa_sm_set_state(ms, bfa_fcs_port_ms_sm_offline); + + /* + * Invoke init routines of sub modules. + */ + bfa_fcs_port_fdmi_init(ms); +} + +void +bfa_fcs_port_ms_offline(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ms_s *ms = BFA_FCS_GET_MS_FROM_PORT(port); + + ms->port = port; + bfa_sm_send_event(ms, MSSM_EVENT_PORT_OFFLINE); +} + +void +bfa_fcs_port_ms_online(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ms_s *ms = BFA_FCS_GET_MS_FROM_PORT(port); + + ms->port = port; + bfa_sm_send_event(ms, MSSM_EVENT_PORT_ONLINE); +} + +void +bfa_fcs_port_ms_fabric_rscn(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ms_s *ms = BFA_FCS_GET_MS_FROM_PORT(port); + + /* + * @todo. Handle this only when in Online state + */ + if (bfa_sm_cmp_state(ms, bfa_fcs_port_ms_sm_online)) + bfa_sm_send_event(ms, MSSM_EVENT_PORT_FABRIC_RSCN); +} diff --git a/drivers/scsi/bfa/n2n.c b/drivers/scsi/bfa/n2n.c new file mode 100644 index 000000000000..735456824346 --- /dev/null +++ b/drivers/scsi/bfa/n2n.c @@ -0,0 +1,105 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * n2n.c n2n implementation. + */ +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "fcs_trcmod.h" +#include "lport_priv.h" + +BFA_TRC_FILE(FCS, N2N); + +/** + * Called by fcs/port to initialize N2N topology. + */ +void +bfa_fcs_port_n2n_init(struct bfa_fcs_port_s *port) +{ +} + +/** + * Called by fcs/port to notify transition to online state. + */ +void +bfa_fcs_port_n2n_online(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_n2n_s *n2n_port = &port->port_topo.pn2n; + struct bfa_port_cfg_s *pcfg = &port->port_cfg; + struct bfa_fcs_rport_s *rport; + + bfa_trc(port->fcs, pcfg->pwwn); + + /* + * If our PWWN is > than that of the r-port, we have to initiate PLOGI + * and assign an Address. if not, we need to wait for its PLOGI. + * + * If our PWWN is < than that of the remote port, it will send a PLOGI + * with the PIDs assigned. The rport state machine take care of this + * incoming PLOGI. + */ + if (memcmp + ((void *)&pcfg->pwwn, (void *)&n2n_port->rem_port_wwn, + sizeof(wwn_t)) > 0) { + port->pid = N2N_LOCAL_PID; + /** + * First, check if we know the device by pwwn. + */ + rport = bfa_fcs_port_get_rport_by_pwwn(port, + n2n_port->rem_port_wwn); + if (rport) { + bfa_trc(port->fcs, rport->pid); + bfa_trc(port->fcs, rport->pwwn); + rport->pid = N2N_REMOTE_PID; + bfa_fcs_rport_online(rport); + return; + } + + /* + * In n2n there can be only one rport. Delete the old one whose + * pid should be zero, because it is offline. + */ + if (port->num_rports > 0) { + rport = bfa_fcs_port_get_rport_by_pid(port, 0); + bfa_assert(rport != NULL); + if (rport) { + bfa_trc(port->fcs, rport->pwwn); + bfa_fcs_rport_delete(rport); + } + } + bfa_fcs_rport_create(port, N2N_REMOTE_PID); + } +} + +/** + * Called by fcs/port to notify transition to offline state. + */ +void +bfa_fcs_port_n2n_offline(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_n2n_s *n2n_port = &port->port_topo.pn2n; + + bfa_trc(port->fcs, port->pid); + port->pid = 0; + n2n_port->rem_port_wwn = 0; + n2n_port->reply_oxid = 0; +} + + diff --git a/drivers/scsi/bfa/ns.c b/drivers/scsi/bfa/ns.c new file mode 100644 index 000000000000..59fea99d67a4 --- /dev/null +++ b/drivers/scsi/bfa/ns.c @@ -0,0 +1,1243 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * @page ns_sm_info VPORT NS State Machine + * + * @section ns_sm_interactions VPORT NS State Machine Interactions + * + * @section ns_sm VPORT NS State Machine + * img ns_sm.jpg + */ +#include <bfa.h> +#include <bfa_svc.h> +#include <bfa_iocfc.h> +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include "fcs.h" +#include "lport_priv.h" + +BFA_TRC_FILE(FCS, NS); + +/* + * forward declarations + */ +static void bfa_fcs_port_ns_send_plogi(void *ns_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ns_send_rspn_id(void *ns_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ns_send_rft_id(void *ns_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ns_send_rff_id(void *ns_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ns_send_gid_ft(void *ns_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_ns_timeout(void *arg); +static void bfa_fcs_port_ns_plogi_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_ns_rspn_id_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_ns_rft_id_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_ns_rff_id_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_ns_gid_ft_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_ns_process_gidft_pids(struct bfa_fcs_port_s *port, + u32 *pid_buf, + u32 n_pids); + +static void bfa_fcs_port_ns_boot_target_disc(struct bfa_fcs_port_s *port); +/** + * fcs_ns_sm FCS nameserver interface state machine + */ + +/** + * VPort NS State Machine events + */ +enum vport_ns_event { + NSSM_EVENT_PORT_ONLINE = 1, + NSSM_EVENT_PORT_OFFLINE = 2, + NSSM_EVENT_PLOGI_SENT = 3, + NSSM_EVENT_RSP_OK = 4, + NSSM_EVENT_RSP_ERROR = 5, + NSSM_EVENT_TIMEOUT = 6, + NSSM_EVENT_NS_QUERY = 7, + NSSM_EVENT_RSPNID_SENT = 8, + NSSM_EVENT_RFTID_SENT = 9, + NSSM_EVENT_RFFID_SENT = 10, + NSSM_EVENT_GIDFT_SENT = 11, +}; + +static void bfa_fcs_port_ns_sm_offline(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_plogi_sending(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_plogi(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_plogi_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_sending_rspn_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_rspn_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_rspn_id_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_sending_rft_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_rft_id_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_rft_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_sending_rff_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_rff_id_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_rff_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_sending_gid_ft(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_gid_ft(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_gid_ft_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +static void bfa_fcs_port_ns_sm_online(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event); +/** + * Start in offline state - awaiting linkup + */ +static void +bfa_fcs_port_ns_sm_offline(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_PORT_ONLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_plogi_sending); + bfa_fcs_port_ns_send_plogi(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_plogi_sending(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_PLOGI_SENT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_plogi); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ns->port), + &ns->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_plogi(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RSP_ERROR: + /* + * Start timer for a delayed retry + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_plogi_retry); + ns->port->stats.ns_retries++; + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ns->port), &ns->timer, + bfa_fcs_port_ns_timeout, ns, + BFA_FCS_RETRY_TIMEOUT); + break; + + case NSSM_EVENT_RSP_OK: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_rspn_id); + bfa_fcs_port_ns_send_rspn_id(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_discard(ns->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_plogi_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_plogi_sending); + bfa_fcs_port_ns_send_plogi(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_timer_stop(&ns->timer); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_sending_rspn_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RSPNID_SENT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_rspn_id); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ns->port), + &ns->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_rspn_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RSP_ERROR: + /* + * Start timer for a delayed retry + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_rspn_id_retry); + ns->port->stats.ns_retries++; + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ns->port), &ns->timer, + bfa_fcs_port_ns_timeout, ns, + BFA_FCS_RETRY_TIMEOUT); + break; + + case NSSM_EVENT_RSP_OK: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_rft_id); + bfa_fcs_port_ns_send_rft_id(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_fcxp_discard(ns->fcxp); + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_rspn_id_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_TIMEOUT: + /* + * Retry Timer Expired. Re-send + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_rspn_id); + bfa_fcs_port_ns_send_rspn_id(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_timer_stop(&ns->timer); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_sending_rft_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RFTID_SENT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_rft_id); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ns->port), + &ns->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_rft_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RSP_OK: + /* + * Now move to register FC4 Features + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_rff_id); + bfa_fcs_port_ns_send_rff_id(ns, NULL); + break; + + case NSSM_EVENT_RSP_ERROR: + /* + * Start timer for a delayed retry + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_rft_id_retry); + ns->port->stats.ns_retries++; + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ns->port), &ns->timer, + bfa_fcs_port_ns_timeout, ns, + BFA_FCS_RETRY_TIMEOUT); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_discard(ns->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_rft_id_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_TIMEOUT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_rft_id); + bfa_fcs_port_ns_send_rft_id(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_timer_stop(&ns->timer); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_sending_rff_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RFFID_SENT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_rff_id); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ns->port), + &ns->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_rff_id(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RSP_OK: + + /* + * If min cfg mode is enabled, we donot initiate rport + * discovery with the fabric. Instead, we will retrieve the + * boot targets from HAL/FW. + */ + if (__fcs_min_cfg(ns->port->fcs)) { + bfa_fcs_port_ns_boot_target_disc(ns->port); + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_online); + return; + } + + /* + * If the port role is Initiator Mode issue NS query. + * If it is Target Mode, skip this and go to online. + */ + if (BFA_FCS_VPORT_IS_INITIATOR_MODE(ns->port)) { + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_gid_ft); + bfa_fcs_port_ns_send_gid_ft(ns, NULL); + } else if (BFA_FCS_VPORT_IS_TARGET_MODE(ns->port)) { + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_online); + } + /* + * kick off mgmt srvr state machine + */ + bfa_fcs_port_ms_online(ns->port); + break; + + case NSSM_EVENT_RSP_ERROR: + /* + * Start timer for a delayed retry + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_rff_id_retry); + ns->port->stats.ns_retries++; + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ns->port), &ns->timer, + bfa_fcs_port_ns_timeout, ns, + BFA_FCS_RETRY_TIMEOUT); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_discard(ns->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_rff_id_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_TIMEOUT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_rff_id); + bfa_fcs_port_ns_send_rff_id(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_timer_stop(&ns->timer); + break; + + default: + bfa_assert(0); + } +} +static void +bfa_fcs_port_ns_sm_sending_gid_ft(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_GIDFT_SENT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_gid_ft); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_walloc_cancel(BFA_FCS_GET_HAL_FROM_PORT(ns->port), + &ns->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_gid_ft(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_RSP_OK: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_online); + break; + + case NSSM_EVENT_RSP_ERROR: + /* + * TBD: for certain reject codes, we don't need to retry + */ + /* + * Start timer for a delayed retry + */ + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_gid_ft_retry); + ns->port->stats.ns_retries++; + bfa_timer_start(BFA_FCS_GET_HAL_FROM_PORT(ns->port), &ns->timer, + bfa_fcs_port_ns_timeout, ns, + BFA_FCS_RETRY_TIMEOUT); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_fcxp_discard(ns->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_gid_ft_retry(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_TIMEOUT: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_gid_ft); + bfa_fcs_port_ns_send_gid_ft(ns, NULL); + break; + + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + bfa_timer_stop(&ns->timer); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_ns_sm_online(struct bfa_fcs_port_ns_s *ns, + enum vport_ns_event event) +{ + bfa_trc(ns->port->fcs, ns->port->port_cfg.pwwn); + bfa_trc(ns->port->fcs, event); + + switch (event) { + case NSSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); + break; + + case NSSM_EVENT_NS_QUERY: + /* + * If the port role is Initiator Mode issue NS query. + * If it is Target Mode, skip this and go to online. + */ + if (BFA_FCS_VPORT_IS_INITIATOR_MODE(ns->port)) { + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_sending_gid_ft); + bfa_fcs_port_ns_send_gid_ft(ns, NULL); + }; + break; + + default: + bfa_assert(0); + } +} + + + +/** + * ns_pvt Nameserver local functions + */ + +static void +bfa_fcs_port_ns_send_plogi(void *ns_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ns_s *ns = ns_cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(port->fcs, port->pid); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + port->stats.ns_plogi_alloc_wait++; + bfa_fcxp_alloc_wait(port->fcs->bfa, &ns->fcxp_wqe, + bfa_fcs_port_ns_send_plogi, ns); + return; + } + ns->fcxp = fcxp; + + len = fc_plogi_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_os_hton3b(FC_NAME_SERVER), + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn, + bfa_pport_get_maxfrsize(port->fcs->bfa)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ns_plogi_response, + (void *)ns, FC_MAX_PDUSZ, FC_RA_TOV); + port->stats.ns_plogi_sent++; + + bfa_sm_send_event(ns, NSSM_EVENT_PLOGI_SENT); +} + +static void +bfa_fcs_port_ns_plogi_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ns_s *ns = (struct bfa_fcs_port_ns_s *)cbarg; + struct bfa_fcs_port_s *port = ns->port; + /* struct fc_logi_s *plogi_resp; */ + struct fc_els_cmd_s *els_cmd; + struct fc_ls_rjt_s *ls_rjt; + + bfa_trc(port->fcs, req_status); + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + port->stats.ns_plogi_rsp_err++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + return; + } + + els_cmd = (struct fc_els_cmd_s *) BFA_FCXP_RSP_PLD(fcxp); + + switch (els_cmd->els_code) { + + case FC_ELS_ACC: + if (rsp_len < sizeof(struct fc_logi_s)) { + bfa_trc(port->fcs, rsp_len); + port->stats.ns_plogi_acc_err++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + break; + } + port->stats.ns_plogi_accepts++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_OK); + break; + + case FC_ELS_LS_RJT: + ls_rjt = (struct fc_ls_rjt_s *) BFA_FCXP_RSP_PLD(fcxp); + + bfa_trc(port->fcs, ls_rjt->reason_code); + bfa_trc(port->fcs, ls_rjt->reason_code_expl); + + port->stats.ns_rejects++; + + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + break; + + default: + port->stats.ns_plogi_unknown_rsp++; + bfa_trc(port->fcs, els_cmd->els_code); + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + } +} + +/** + * Register the symbolic port name. + */ +static void +bfa_fcs_port_ns_send_rspn_id(void *ns_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ns_s *ns = ns_cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + u8 symbl[256]; + u8 *psymbl = &symbl[0]; + + bfa_os_memset(symbl, 0, sizeof(symbl)); + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + port->stats.ns_rspnid_alloc_wait++; + bfa_fcxp_alloc_wait(port->fcs->bfa, &ns->fcxp_wqe, + bfa_fcs_port_ns_send_rspn_id, ns); + return; + } + ns->fcxp = fcxp; + + /* + * for V-Port, form a Port Symbolic Name + */ + if (port->vport) { + /**For Vports, + * we append the vport's port symbolic name to that of the base port. + */ + + strncpy((char *)psymbl, + (char *) + &(bfa_fcs_port_get_psym_name + (bfa_fcs_get_base_port(port->fcs))), + strlen((char *) + &bfa_fcs_port_get_psym_name(bfa_fcs_get_base_port + (port->fcs)))); + + /* + * Ensure we have a null terminating string. + */ + ((char *) + psymbl)[strlen((char *) + &bfa_fcs_port_get_psym_name + (bfa_fcs_get_base_port(port->fcs)))] = 0; + + strncat((char *)psymbl, + (char *)&(bfa_fcs_port_get_psym_name(port)), + strlen((char *)&bfa_fcs_port_get_psym_name(port))); + } else { + psymbl = (u8 *) &(bfa_fcs_port_get_psym_name(port)); + } + + len = fc_rspnid_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_fcs_port_get_fcid(port), 0, psymbl); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ns_rspn_id_response, + (void *)ns, FC_MAX_PDUSZ, FC_RA_TOV); + + port->stats.ns_rspnid_sent++; + + bfa_sm_send_event(ns, NSSM_EVENT_RSPNID_SENT); +} + +static void +bfa_fcs_port_ns_rspn_id_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ns_s *ns = (struct bfa_fcs_port_ns_s *)cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct ct_hdr_s *cthdr = NULL; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + port->stats.ns_rspnid_rsp_err++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + port->stats.ns_rspnid_accepts++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_OK); + return; + } + + port->stats.ns_rspnid_rejects++; + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); +} + +/** + * Register FC4-Types + * TBD, Need to retrieve this from the OS driver, in case IPFC is enabled ? + */ +static void +bfa_fcs_port_ns_send_rft_id(void *ns_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ns_s *ns = ns_cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + port->stats.ns_rftid_alloc_wait++; + bfa_fcxp_alloc_wait(port->fcs->bfa, &ns->fcxp_wqe, + bfa_fcs_port_ns_send_rft_id, ns); + return; + } + ns->fcxp = fcxp; + + len = fc_rftid_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.roles); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ns_rft_id_response, + (void *)ns, FC_MAX_PDUSZ, FC_RA_TOV); + + port->stats.ns_rftid_sent++; + bfa_sm_send_event(ns, NSSM_EVENT_RFTID_SENT); +} + +static void +bfa_fcs_port_ns_rft_id_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ns_s *ns = (struct bfa_fcs_port_ns_s *)cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct ct_hdr_s *cthdr = NULL; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + port->stats.ns_rftid_rsp_err++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + port->stats.ns_rftid_accepts++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_OK); + return; + } + + port->stats.ns_rftid_rejects++; + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); +} + +/** +* Register FC4-Features : Should be done after RFT_ID + */ +static void +bfa_fcs_port_ns_send_rff_id(void *ns_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ns_s *ns = ns_cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + u8 fc4_ftrs = 0; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + port->stats.ns_rffid_alloc_wait++; + bfa_fcxp_alloc_wait(port->fcs->bfa, &ns->fcxp_wqe, + bfa_fcs_port_ns_send_rff_id, ns); + return; + } + ns->fcxp = fcxp; + + if (BFA_FCS_VPORT_IS_INITIATOR_MODE(ns->port)) { + fc4_ftrs = FC_GS_FCP_FC4_FEATURE_INITIATOR; + } else if (BFA_FCS_VPORT_IS_TARGET_MODE(ns->port)) { + fc4_ftrs = FC_GS_FCP_FC4_FEATURE_TARGET; + } + + len = fc_rffid_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_fcs_port_get_fcid(port), 0, FC_TYPE_FCP, + fc4_ftrs); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ns_rff_id_response, + (void *)ns, FC_MAX_PDUSZ, FC_RA_TOV); + + port->stats.ns_rffid_sent++; + bfa_sm_send_event(ns, NSSM_EVENT_RFFID_SENT); +} + +static void +bfa_fcs_port_ns_rff_id_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ns_s *ns = (struct bfa_fcs_port_ns_s *)cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct ct_hdr_s *cthdr = NULL; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + port->stats.ns_rffid_rsp_err++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + port->stats.ns_rffid_accepts++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_OK); + return; + } + + port->stats.ns_rffid_rejects++; + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + + if (cthdr->reason_code == CT_RSN_NOT_SUPP) { + /* + * if this command is not supported, we don't retry + */ + bfa_sm_send_event(ns, NSSM_EVENT_RSP_OK); + } else { + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + } +} + +/** + * Query Fabric for FC4-Types Devices. + * +* TBD : Need to use a local (FCS private) response buffer, since the response + * can be larger than 2K. + */ +static void +bfa_fcs_port_ns_send_gid_ft(void *ns_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_ns_s *ns = ns_cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(port->fcs, port->pid); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + port->stats.ns_gidft_alloc_wait++; + bfa_fcxp_alloc_wait(port->fcs->bfa, &ns->fcxp_wqe, + bfa_fcs_port_ns_send_gid_ft, ns); + return; + } + ns->fcxp = fcxp; + + /* + * This query is only initiated for FCP initiator mode. + */ + len = fc_gid_ft_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), ns->port->pid, + FC_TYPE_FCP); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_ns_gid_ft_response, + (void *)ns, bfa_fcxp_get_maxrsp(port->fcs->bfa), + FC_RA_TOV); + + port->stats.ns_gidft_sent++; + + bfa_sm_send_event(ns, NSSM_EVENT_GIDFT_SENT); +} + +static void +bfa_fcs_port_ns_gid_ft_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_ns_s *ns = (struct bfa_fcs_port_ns_s *)cbarg; + struct bfa_fcs_port_s *port = ns->port; + struct ct_hdr_s *cthdr = NULL; + u32 n_pids; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + port->stats.ns_gidft_rsp_err++; + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + return; + } + + if (resid_len != 0) { + /* + * TBD : we will need to allocate a larger buffer & retry the + * command + */ + bfa_trc(port->fcs, rsp_len); + bfa_trc(port->fcs, resid_len); + return; + } + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + switch (cthdr->cmd_rsp_code) { + + case CT_RSP_ACCEPT: + + port->stats.ns_gidft_accepts++; + n_pids = (fc_get_ctresp_pyld_len(rsp_len) / sizeof(u32)); + bfa_trc(port->fcs, n_pids); + bfa_fcs_port_ns_process_gidft_pids(port, + (u32 *) (cthdr + 1), + n_pids); + bfa_sm_send_event(ns, NSSM_EVENT_RSP_OK); + break; + + case CT_RSP_REJECT: + + /* + * Check the reason code & explanation. + * There may not have been any FC4 devices in the fabric + */ + port->stats.ns_gidft_rejects++; + bfa_trc(port->fcs, cthdr->reason_code); + bfa_trc(port->fcs, cthdr->exp_code); + + if ((cthdr->reason_code == CT_RSN_UNABLE_TO_PERF) + && (cthdr->exp_code == CT_NS_EXP_FT_NOT_REG)) { + + bfa_sm_send_event(ns, NSSM_EVENT_RSP_OK); + } else { + /* + * for all other errors, retry + */ + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + } + break; + + default: + port->stats.ns_gidft_unknown_rsp++; + bfa_trc(port->fcs, cthdr->cmd_rsp_code); + bfa_sm_send_event(ns, NSSM_EVENT_RSP_ERROR); + } +} + +/** + * This routine will be called by bfa_timer on timer timeouts. + * + * param[in] port - pointer to bfa_fcs_port_t. + * + * return + * void + * +* Special Considerations: + * + * note + */ +static void +bfa_fcs_port_ns_timeout(void *arg) +{ + struct bfa_fcs_port_ns_s *ns = (struct bfa_fcs_port_ns_s *)arg; + + ns->port->stats.ns_timeouts++; + bfa_sm_send_event(ns, NSSM_EVENT_TIMEOUT); +} + +/* + * Process the PID list in GID_FT response + */ +static void +bfa_fcs_port_ns_process_gidft_pids(struct bfa_fcs_port_s *port, + u32 *pid_buf, u32 n_pids) +{ + struct fcgs_gidft_resp_s *gidft_entry; + struct bfa_fcs_rport_s *rport; + u32 ii; + + for (ii = 0; ii < n_pids; ii++) { + gidft_entry = (struct fcgs_gidft_resp_s *) &pid_buf[ii]; + + if (gidft_entry->pid == port->pid) + continue; + + /* + * Check if this rport already exists + */ + rport = bfa_fcs_port_get_rport_by_pid(port, gidft_entry->pid); + if (rport == NULL) { + /* + * this is a new device. create rport + */ + rport = bfa_fcs_rport_create(port, gidft_entry->pid); + } else { + /* + * this rport already exists + */ + bfa_fcs_rport_scn(rport); + } + + bfa_trc(port->fcs, gidft_entry->pid); + + /* + * if the last entry bit is set, bail out. + */ + if (gidft_entry->last) + return; + } +} + +/** + * fcs_ns_public FCS nameserver public interfaces + */ + +/* + * Functions called by port/fab. + * These will send relevant Events to the ns state machine. + */ +void +bfa_fcs_port_ns_init(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ns_s *ns = BFA_FCS_GET_NS_FROM_PORT(port); + + ns->port = port; + bfa_sm_set_state(ns, bfa_fcs_port_ns_sm_offline); +} + +void +bfa_fcs_port_ns_offline(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ns_s *ns = BFA_FCS_GET_NS_FROM_PORT(port); + + ns->port = port; + bfa_sm_send_event(ns, NSSM_EVENT_PORT_OFFLINE); +} + +void +bfa_fcs_port_ns_online(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ns_s *ns = BFA_FCS_GET_NS_FROM_PORT(port); + + ns->port = port; + bfa_sm_send_event(ns, NSSM_EVENT_PORT_ONLINE); +} + +void +bfa_fcs_port_ns_query(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_ns_s *ns = BFA_FCS_GET_NS_FROM_PORT(port); + + bfa_trc(port->fcs, port->pid); + bfa_sm_send_event(ns, NSSM_EVENT_NS_QUERY); +} + +static void +bfa_fcs_port_ns_boot_target_disc(struct bfa_fcs_port_s *port) +{ + + struct bfa_fcs_rport_s *rport; + u8 nwwns; + wwn_t *wwns; + int ii; + + bfa_iocfc_get_bootwwns(port->fcs->bfa, &nwwns, &wwns); + + for (ii = 0; ii < nwwns; ++ii) { + rport = bfa_fcs_rport_create_by_wwn(port, wwns[ii]); + bfa_assert(rport); + } +} + + diff --git a/drivers/scsi/bfa/plog.c b/drivers/scsi/bfa/plog.c new file mode 100644 index 000000000000..86af818d17bb --- /dev/null +++ b/drivers/scsi/bfa/plog.c @@ -0,0 +1,184 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa_os_inc.h> +#include <cs/bfa_plog.h> +#include <cs/bfa_debug.h> + +static int +plkd_validate_logrec(struct bfa_plog_rec_s *pl_rec) +{ + if ((pl_rec->log_type != BFA_PL_LOG_TYPE_INT) + && (pl_rec->log_type != BFA_PL_LOG_TYPE_STRING)) + return 1; + + if ((pl_rec->log_type != BFA_PL_LOG_TYPE_INT) + && (pl_rec->log_num_ints > BFA_PL_INT_LOG_SZ)) + return 1; + + return 0; +} + +static void +bfa_plog_add(struct bfa_plog_s *plog, struct bfa_plog_rec_s *pl_rec) +{ + u16 tail; + struct bfa_plog_rec_s *pl_recp; + + if (plog->plog_enabled == 0) + return; + + if (plkd_validate_logrec(pl_rec)) { + bfa_assert(0); + return; + } + + tail = plog->tail; + + pl_recp = &(plog->plog_recs[tail]); + + bfa_os_memcpy(pl_recp, pl_rec, sizeof(struct bfa_plog_rec_s)); + + pl_recp->tv = BFA_TRC_TS(plog); + BFA_PL_LOG_REC_INCR(plog->tail); + + if (plog->head == plog->tail) + BFA_PL_LOG_REC_INCR(plog->head); +} + +void +bfa_plog_init(struct bfa_plog_s *plog) +{ + bfa_os_memset((char *)plog, 0, sizeof(struct bfa_plog_s)); + + bfa_os_memcpy(plog->plog_sig, BFA_PL_SIG_STR, BFA_PL_SIG_LEN); + plog->head = plog->tail = 0; + plog->plog_enabled = 1; +} + +void +bfa_plog_str(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, + u16 misc, char *log_str) +{ + struct bfa_plog_rec_s lp; + + if (plog->plog_enabled) { + bfa_os_memset(&lp, 0, sizeof(struct bfa_plog_rec_s)); + lp.mid = mid; + lp.eid = event; + lp.log_type = BFA_PL_LOG_TYPE_STRING; + lp.misc = misc; + strncpy(lp.log_entry.string_log, log_str, + BFA_PL_STRING_LOG_SZ - 1); + lp.log_entry.string_log[BFA_PL_STRING_LOG_SZ - 1] = '\0'; + bfa_plog_add(plog, &lp); + } +} + +void +bfa_plog_intarr(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, + u16 misc, u32 *intarr, u32 num_ints) +{ + struct bfa_plog_rec_s lp; + u32 i; + + if (num_ints > BFA_PL_INT_LOG_SZ) + num_ints = BFA_PL_INT_LOG_SZ; + + if (plog->plog_enabled) { + bfa_os_memset(&lp, 0, sizeof(struct bfa_plog_rec_s)); + lp.mid = mid; + lp.eid = event; + lp.log_type = BFA_PL_LOG_TYPE_INT; + lp.misc = misc; + + for (i = 0; i < num_ints; i++) + bfa_os_assign(lp.log_entry.int_log[i], + intarr[i]); + + lp.log_num_ints = (u8) num_ints; + + bfa_plog_add(plog, &lp); + } +} + +void +bfa_plog_fchdr(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, + u16 misc, struct fchs_s *fchdr) +{ + struct bfa_plog_rec_s lp; + u32 *tmp_int = (u32 *) fchdr; + u32 ints[BFA_PL_INT_LOG_SZ]; + + if (plog->plog_enabled) { + bfa_os_memset(&lp, 0, sizeof(struct bfa_plog_rec_s)); + + ints[0] = tmp_int[0]; + ints[1] = tmp_int[1]; + ints[2] = tmp_int[4]; + + bfa_plog_intarr(plog, mid, event, misc, ints, 3); + } +} + +void +bfa_plog_fchdr_and_pl(struct bfa_plog_s *plog, enum bfa_plog_mid mid, + enum bfa_plog_eid event, u16 misc, struct fchs_s *fchdr, + u32 pld_w0) +{ + struct bfa_plog_rec_s lp; + u32 *tmp_int = (u32 *) fchdr; + u32 ints[BFA_PL_INT_LOG_SZ]; + + if (plog->plog_enabled) { + bfa_os_memset(&lp, 0, sizeof(struct bfa_plog_rec_s)); + + ints[0] = tmp_int[0]; + ints[1] = tmp_int[1]; + ints[2] = tmp_int[4]; + ints[3] = pld_w0; + + bfa_plog_intarr(plog, mid, event, misc, ints, 4); + } +} + +void +bfa_plog_clear(struct bfa_plog_s *plog) +{ + plog->head = plog->tail = 0; +} + +void +bfa_plog_enable(struct bfa_plog_s *plog) +{ + plog->plog_enabled = 1; +} + +void +bfa_plog_disable(struct bfa_plog_s *plog) +{ + plog->plog_enabled = 0; +} + +bfa_boolean_t +bfa_plog_get_setting(struct bfa_plog_s *plog) +{ + return((bfa_boolean_t)plog->plog_enabled); +} diff --git a/drivers/scsi/bfa/rport.c b/drivers/scsi/bfa/rport.c new file mode 100644 index 000000000000..9cf58bb138dc --- /dev/null +++ b/drivers/scsi/bfa/rport.c @@ -0,0 +1,2618 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * rport.c Remote port implementation. + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include "fcbuild.h" +#include "fcs_vport.h" +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "fcs_fcpim.h" +#include "fcs_fcptm.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include "fcs.h" +#include <fcb/bfa_fcb_rport.h> +#include <aen/bfa_aen_rport.h> + +BFA_TRC_FILE(FCS, RPORT); + +#define BFA_FCS_RPORT_MAX_RETRIES (5) + +/* In millisecs */ +static u32 bfa_fcs_rport_del_timeout = + BFA_FCS_RPORT_DEF_DEL_TIMEOUT * 1000; + +/* + * forward declarations + */ +static struct bfa_fcs_rport_s *bfa_fcs_rport_alloc(struct bfa_fcs_port_s *port, + wwn_t pwwn, u32 rpid); +static void bfa_fcs_rport_free(struct bfa_fcs_rport_s *rport); +static void bfa_fcs_rport_hal_online(struct bfa_fcs_rport_s *rport); +static void bfa_fcs_rport_online_action(struct bfa_fcs_rport_s *rport); +static void bfa_fcs_rport_offline_action(struct bfa_fcs_rport_s *rport); +static void bfa_fcs_rport_update(struct bfa_fcs_rport_s *rport, + struct fc_logi_s *plogi); +static void bfa_fcs_rport_fc4_pause(struct bfa_fcs_rport_s *rport); +static void bfa_fcs_rport_fc4_resume(struct bfa_fcs_rport_s *rport); +static void bfa_fcs_rport_timeout(void *arg); +static void bfa_fcs_rport_send_plogi(void *rport_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_rport_send_plogiacc(void *rport_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_rport_plogi_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_rport_send_adisc(void *rport_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_rport_adisc_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_rport_send_gidpn(void *rport_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_rport_gidpn_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_rport_send_logo(void *rport_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_rport_send_logo_acc(void *rport_cbarg); +static void bfa_fcs_rport_process_prli(struct bfa_fcs_rport_s *rport, + struct fchs_s *rx_fchs, u16 len); +static void bfa_fcs_rport_send_ls_rjt(struct bfa_fcs_rport_s *rport, + struct fchs_s *rx_fchs, u8 reason_code, + u8 reason_code_expl); +static void bfa_fcs_rport_process_adisc(struct bfa_fcs_rport_s *rport, + struct fchs_s *rx_fchs, u16 len); +/** + * fcs_rport_sm FCS rport state machine events + */ + +enum rport_event { + RPSM_EVENT_PLOGI_SEND = 1, /* new rport; start with PLOGI */ + RPSM_EVENT_PLOGI_RCVD = 2, /* Inbound PLOGI from remote port */ + RPSM_EVENT_PLOGI_COMP = 3, /* PLOGI completed to rport */ + RPSM_EVENT_LOGO_RCVD = 4, /* LOGO from remote device */ + RPSM_EVENT_LOGO_IMP = 5, /* implicit logo for SLER */ + RPSM_EVENT_FCXP_SENT = 6, /* Frame from has been sent */ + RPSM_EVENT_DELETE = 7, /* RPORT delete request */ + RPSM_EVENT_SCN = 8, /* state change notification */ + RPSM_EVENT_ACCEPTED = 9,/* Good response from remote device */ + RPSM_EVENT_FAILED = 10, /* Request to rport failed. */ + RPSM_EVENT_TIMEOUT = 11, /* Rport SM timeout event */ + RPSM_EVENT_HCB_ONLINE = 12, /* BFA rport online callback */ + RPSM_EVENT_HCB_OFFLINE = 13, /* BFA rport offline callback */ + RPSM_EVENT_FC4_OFFLINE = 14, /* FC-4 offline complete */ + RPSM_EVENT_ADDRESS_CHANGE = 15, /* Rport's PID has changed */ + RPSM_EVENT_ADDRESS_DISC = 16 /* Need to Discover rport's PID */ +}; + +static void bfa_fcs_rport_sm_uninit(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_plogi_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_plogiacc_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_plogi_retry(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_plogi(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_hal_online(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_online(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_nsquery_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_nsquery(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_adisc_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_adisc(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_fc4_logorcv(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_fc4_logosend(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_fc4_offline(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_hcb_offline(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_hcb_logorcv(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_hcb_logosend(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_logo_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_offline(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_nsdisc_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_nsdisc_retry(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_nsdisc_sent(struct bfa_fcs_rport_s *rport, + enum rport_event event); +static void bfa_fcs_rport_sm_nsdisc_sent(struct bfa_fcs_rport_s *rport, + enum rport_event event); + +static struct bfa_sm_table_s rport_sm_table[] = { + {BFA_SM(bfa_fcs_rport_sm_uninit), BFA_RPORT_UNINIT}, + {BFA_SM(bfa_fcs_rport_sm_plogi_sending), BFA_RPORT_PLOGI}, + {BFA_SM(bfa_fcs_rport_sm_plogiacc_sending), BFA_RPORT_ONLINE}, + {BFA_SM(bfa_fcs_rport_sm_plogi_retry), BFA_RPORT_PLOGI_RETRY}, + {BFA_SM(bfa_fcs_rport_sm_plogi), BFA_RPORT_PLOGI}, + {BFA_SM(bfa_fcs_rport_sm_hal_online), BFA_RPORT_ONLINE}, + {BFA_SM(bfa_fcs_rport_sm_online), BFA_RPORT_ONLINE}, + {BFA_SM(bfa_fcs_rport_sm_nsquery_sending), BFA_RPORT_NSQUERY}, + {BFA_SM(bfa_fcs_rport_sm_nsquery), BFA_RPORT_NSQUERY}, + {BFA_SM(bfa_fcs_rport_sm_adisc_sending), BFA_RPORT_ADISC}, + {BFA_SM(bfa_fcs_rport_sm_adisc), BFA_RPORT_ADISC}, + {BFA_SM(bfa_fcs_rport_sm_fc4_logorcv), BFA_RPORT_LOGORCV}, + {BFA_SM(bfa_fcs_rport_sm_fc4_logosend), BFA_RPORT_LOGO}, + {BFA_SM(bfa_fcs_rport_sm_fc4_offline), BFA_RPORT_OFFLINE}, + {BFA_SM(bfa_fcs_rport_sm_hcb_offline), BFA_RPORT_OFFLINE}, + {BFA_SM(bfa_fcs_rport_sm_hcb_logorcv), BFA_RPORT_LOGORCV}, + {BFA_SM(bfa_fcs_rport_sm_hcb_logosend), BFA_RPORT_LOGO}, + {BFA_SM(bfa_fcs_rport_sm_logo_sending), BFA_RPORT_LOGO}, + {BFA_SM(bfa_fcs_rport_sm_offline), BFA_RPORT_OFFLINE}, + {BFA_SM(bfa_fcs_rport_sm_nsdisc_sending), BFA_RPORT_NSDISC}, + {BFA_SM(bfa_fcs_rport_sm_nsdisc_retry), BFA_RPORT_NSDISC}, + {BFA_SM(bfa_fcs_rport_sm_nsdisc_sent), BFA_RPORT_NSDISC}, +}; + +/** + * Beginning state. + */ +static void +bfa_fcs_rport_sm_uninit(struct bfa_fcs_rport_s *rport, enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_PLOGI_SEND: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogi_sending); + rport->plogi_retries = 0; + bfa_fcs_rport_send_plogi(rport, NULL); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_fcs_rport_hal_online(rport); + break; + + case RPSM_EVENT_ADDRESS_CHANGE: + case RPSM_EVENT_ADDRESS_DISC: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + default: + bfa_assert(0); + } +} + +/** + * PLOGI is being sent. + */ +static void +bfa_fcs_rport_sm_plogi_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FCXP_SENT: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogi); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + case RPSM_EVENT_LOGO_IMP: + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_SCN: + break; + + default: + bfa_assert(0); + } +} + +/** + * PLOGI is being sent. + */ +static void +bfa_fcs_rport_sm_plogiacc_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FCXP_SENT: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_fcs_rport_hal_online(rport); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_SCN: + /** + * Ignore, SCN is possibly online notification. + */ + break; + + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + case RPSM_EVENT_LOGO_IMP: + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_HCB_OFFLINE: + /** + * Ignore BFA callback, on a PLOGI receive we call bfa offline. + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * PLOGI is sent. + */ +static void +bfa_fcs_rport_sm_plogi_retry(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_SCN: + bfa_timer_stop(&rport->timer); + /* + * !! fall through !! + */ + + case RPSM_EVENT_TIMEOUT: + rport->plogi_retries++; + if (rport->plogi_retries < BFA_FCS_RPORT_MAX_RETRIES) { + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogi_sending); + bfa_fcs_rport_send_plogi(rport, NULL); + } else { + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + } + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_LOGO_RCVD: + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_timer_stop(&rport->timer); + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + case RPSM_EVENT_LOGO_IMP: + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_timer_stop(&rport->timer); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_hal_online(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * PLOGI is sent. + */ +static void +bfa_fcs_rport_sm_plogi(struct bfa_fcs_rport_s *rport, enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_ACCEPTED: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + rport->plogi_retries = 0; + bfa_fcs_rport_hal_online(rport); + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_fcs_rport_send_logo_acc(rport); + bfa_fcxp_discard(rport->fcxp); + /* + * !! fall through !! + */ + case RPSM_EVENT_FAILED: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogi_retry); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + BFA_FCS_RETRY_TIMEOUT); + break; + + case RPSM_EVENT_LOGO_IMP: + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_fcxp_discard(rport->fcxp); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_fcxp_discard(rport->fcxp); + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_SCN: + /** + * Ignore SCN - wait for PLOGI response. + */ + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_hal_online(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * PLOGI is complete. Awaiting BFA rport online callback. FC-4s + * are offline. + */ +static void +bfa_fcs_rport_sm_hal_online(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_HCB_ONLINE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_online); + bfa_fcs_rport_online_action(rport); + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_logorcv); + bfa_rport_offline(rport->bfa_rport); + break; + + case RPSM_EVENT_LOGO_IMP: + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_offline); + bfa_rport_offline(rport->bfa_rport); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_rport_offline(rport->bfa_rport); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_logosend); + bfa_rport_offline(rport->bfa_rport); + break; + + case RPSM_EVENT_SCN: + /** + * @todo + * Ignore SCN - PLOGI just completed, FC-4 login should detect + * device failures. + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport is ONLINE. FC-4s active. + */ +static void +bfa_fcs_rport_sm_online(struct bfa_fcs_rport_s *rport, enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_SCN: + /** + * Pause FC-4 activity till rport is authenticated. + * In switched fabrics, check presence of device in nameserver + * first. + */ + bfa_fcs_rport_fc4_pause(rport); + + if (bfa_fcs_fabric_is_switched(rport->port->fabric)) { + bfa_sm_set_state(rport, + bfa_fcs_rport_sm_nsquery_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + } else { + bfa_sm_set_state(rport, bfa_fcs_rport_sm_adisc_sending); + bfa_fcs_rport_send_adisc(rport, NULL); + } + break; + + case RPSM_EVENT_PLOGI_RCVD: + case RPSM_EVENT_LOGO_IMP: + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logosend); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logorcv); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_PLOGI_COMP: + break; + + default: + bfa_assert(0); + } +} + +/** + * An SCN event is received in ONLINE state. NS query is being sent + * prior to ADISC authentication with rport. FC-4s are paused. + */ +static void +bfa_fcs_rport_sm_nsquery_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FCXP_SENT: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsquery); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logosend); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_SCN: + /** + * ignore SCN, wait for response to query itself + */ + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logorcv); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_LOGO_IMP: + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_PLOGI_RCVD: + case RPSM_EVENT_ADDRESS_CHANGE: + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_offline_action(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * An SCN event is received in ONLINE state. NS query is sent to rport. + * FC-4s are paused. + */ +static void +bfa_fcs_rport_sm_nsquery(struct bfa_fcs_rport_s *rport, enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_ACCEPTED: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_adisc_sending); + bfa_fcs_rport_send_adisc(rport, NULL); + break; + + case RPSM_EVENT_FAILED: + rport->ns_retries++; + if (rport->ns_retries < BFA_FCS_RPORT_MAX_RETRIES) { + bfa_sm_set_state(rport, + bfa_fcs_rport_sm_nsquery_sending); + bfa_fcs_rport_send_gidpn(rport, NULL); + } else { + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcs_rport_offline_action(rport); + } + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logosend); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_SCN: + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logorcv); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_PLOGI_COMP: + case RPSM_EVENT_ADDRESS_CHANGE: + case RPSM_EVENT_PLOGI_RCVD: + case RPSM_EVENT_LOGO_IMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_offline_action(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * An SCN event is received in ONLINE state. ADISC is being sent for + * authenticating with rport. FC-4s are paused. + */ +static void +bfa_fcs_rport_sm_adisc_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FCXP_SENT: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_adisc); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logosend); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_LOGO_IMP: + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logorcv); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_SCN: + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_offline_action(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * An SCN event is received in ONLINE state. ADISC is to rport. + * FC-4s are paused. + */ +static void +bfa_fcs_rport_sm_adisc(struct bfa_fcs_rport_s *rport, enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_ACCEPTED: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_online); + bfa_fcs_rport_fc4_resume(rport); + break; + + case RPSM_EVENT_PLOGI_RCVD: + /** + * Too complex to cleanup FC-4 & rport and then acc to PLOGI. + * At least go offline when a PLOGI is received. + */ + bfa_fcxp_discard(rport->fcxp); + /* + * !!! fall through !!! + */ + + case RPSM_EVENT_FAILED: + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logosend); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_SCN: + /** + * already processing RSCN + */ + break; + + case RPSM_EVENT_LOGO_IMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_offline); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_offline_action(rport); + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logorcv); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_offline_action(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport has sent LOGO. Awaiting FC-4 offline completion callback. + */ +static void +bfa_fcs_rport_sm_fc4_logorcv(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FC4_OFFLINE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_logorcv); + bfa_rport_offline(rport->bfa_rport); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logosend); + break; + + case RPSM_EVENT_LOGO_RCVD: + case RPSM_EVENT_ADDRESS_CHANGE: + break; + + default: + bfa_assert(0); + } +} + +/** + * LOGO needs to be sent to rport. Awaiting FC-4 offline completion + * callback. + */ +static void +bfa_fcs_rport_sm_fc4_logosend(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FC4_OFFLINE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_logosend); + bfa_rport_offline(rport->bfa_rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport is going offline. Awaiting FC-4 offline completion callback. + */ +static void +bfa_fcs_rport_sm_fc4_offline(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FC4_OFFLINE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_offline); + bfa_rport_offline(rport->bfa_rport); + break; + + case RPSM_EVENT_SCN: + case RPSM_EVENT_LOGO_IMP: + case RPSM_EVENT_LOGO_RCVD: + case RPSM_EVENT_ADDRESS_CHANGE: + /** + * rport is already going offline. + * SCN - ignore and wait till transitioning to offline state + */ + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_fc4_logosend); + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport is offline. FC-4s are offline. Awaiting BFA rport offline + * callback. + */ +static void +bfa_fcs_rport_sm_hcb_offline(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_HCB_OFFLINE: + case RPSM_EVENT_ADDRESS_CHANGE: + if (bfa_fcs_port_is_online(rport->port)) { + bfa_sm_set_state(rport, + bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + } else { + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + } + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_SCN: + case RPSM_EVENT_LOGO_RCVD: + /** + * Ignore, already offline. + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport is offline. FC-4s are offline. Awaiting BFA rport offline + * callback to send LOGO accept. + */ +static void +bfa_fcs_rport_sm_hcb_logorcv(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_HCB_OFFLINE: + case RPSM_EVENT_ADDRESS_CHANGE: + if (rport->pid) + bfa_fcs_rport_send_logo_acc(rport); + /* + * If the lport is online and if the rport is not a well known + * address port, we try to re-discover the r-port. + */ + if (bfa_fcs_port_is_online(rport->port) + && (!BFA_FCS_PID_IS_WKA(rport->pid))) { + bfa_sm_set_state(rport, + bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + } else { + /* + * if it is not a well known address, reset the pid to + * + */ + if (!BFA_FCS_PID_IS_WKA(rport->pid)) + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + } + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_logosend); + break; + + case RPSM_EVENT_LOGO_IMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hcb_offline); + break; + + case RPSM_EVENT_LOGO_RCVD: + /** + * Ignore - already processing a LOGO. + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport is being deleted. FC-4s are offline. Awaiting BFA rport offline + * callback to send LOGO. + */ +static void +bfa_fcs_rport_sm_hcb_logosend(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_HCB_OFFLINE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_logo_sending); + bfa_fcs_rport_send_logo(rport, NULL); + break; + + case RPSM_EVENT_LOGO_RCVD: + case RPSM_EVENT_ADDRESS_CHANGE: + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport is being deleted. FC-4s are offline. LOGO is being sent. + */ +static void +bfa_fcs_rport_sm_logo_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FCXP_SENT: + /* + * Once LOGO is sent, we donot wait for the response + */ + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_SCN: + case RPSM_EVENT_ADDRESS_CHANGE: + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_free(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport is offline. FC-4s are offline. BFA rport is offline. + * Timer active to delete stale rport. + */ +static void +bfa_fcs_rport_sm_offline(struct bfa_fcs_rport_s *rport, enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_TIMEOUT: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_SCN: + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + bfa_timer_stop(&rport->timer); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_LOGO_RCVD: + case RPSM_EVENT_LOGO_IMP: + break; + + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_hal_online(rport); + break; + + case RPSM_EVENT_PLOGI_SEND: + bfa_timer_stop(&rport->timer); + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogi_sending); + rport->plogi_retries = 0; + bfa_fcs_rport_send_plogi(rport, NULL); + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport address has changed. Nameserver discovery request is being sent. + */ +static void +bfa_fcs_rport_sm_nsdisc_sending(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_FCXP_SENT: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sent); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_SCN: + case RPSM_EVENT_LOGO_RCVD: + case RPSM_EVENT_PLOGI_SEND: + break; + + case RPSM_EVENT_ADDRESS_CHANGE: + rport->ns_retries = 0; /* reset the retry count */ + break; + + case RPSM_EVENT_LOGO_IMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rport->fcxp_wqe); + bfa_fcs_rport_hal_online(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Nameserver discovery failed. Waiting for timeout to retry. + */ +static void +bfa_fcs_rport_sm_nsdisc_retry(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_TIMEOUT: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + case RPSM_EVENT_SCN: + case RPSM_EVENT_ADDRESS_CHANGE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_nsdisc_sending); + bfa_timer_stop(&rport->timer); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_LOGO_IMP: + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_timer_stop(&rport->timer); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_LOGO_RCVD: + bfa_fcs_rport_send_logo_acc(rport); + break; + + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_timer_stop(&rport->timer); + bfa_fcs_rport_hal_online(rport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Rport address has changed. Nameserver discovery request is sent. + */ +static void +bfa_fcs_rport_sm_nsdisc_sent(struct bfa_fcs_rport_s *rport, + enum rport_event event) +{ + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPSM_EVENT_ACCEPTED: + case RPSM_EVENT_ADDRESS_CHANGE: + if (rport->pid) { + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogi_sending); + bfa_fcs_rport_send_plogi(rport, NULL); + } else { + bfa_sm_set_state(rport, + bfa_fcs_rport_sm_nsdisc_sending); + rport->ns_retries = 0; + bfa_fcs_rport_send_gidpn(rport, NULL); + } + break; + + case RPSM_EVENT_FAILED: + rport->ns_retries++; + if (rport->ns_retries < BFA_FCS_RPORT_MAX_RETRIES) { + bfa_sm_set_state(rport, + bfa_fcs_rport_sm_nsdisc_sending); + bfa_fcs_rport_send_gidpn(rport, NULL); + } else { + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + }; + break; + + case RPSM_EVENT_DELETE: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_free(rport); + break; + + case RPSM_EVENT_PLOGI_RCVD: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_plogiacc_sending); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_send_plogiacc(rport, NULL); + break; + + case RPSM_EVENT_LOGO_IMP: + rport->pid = 0; + bfa_sm_set_state(rport, bfa_fcs_rport_sm_offline); + bfa_fcxp_discard(rport->fcxp); + bfa_timer_start(rport->fcs->bfa, &rport->timer, + bfa_fcs_rport_timeout, rport, + bfa_fcs_rport_del_timeout); + break; + + case RPSM_EVENT_SCN: + /** + * ignore, wait for NS query response + */ + break; + + case RPSM_EVENT_LOGO_RCVD: + /** + * Not logged-in yet. Accept LOGO. + */ + bfa_fcs_rport_send_logo_acc(rport); + break; + + case RPSM_EVENT_PLOGI_COMP: + bfa_sm_set_state(rport, bfa_fcs_rport_sm_hal_online); + bfa_fcxp_discard(rport->fcxp); + bfa_fcs_rport_hal_online(rport); + break; + + default: + bfa_assert(0); + } +} + + + +/** + * fcs_rport_private FCS RPORT provate functions + */ + +static void +bfa_fcs_rport_send_plogi(void *rport_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_rport_s *rport = rport_cbarg; + struct bfa_fcs_port_s *port = rport->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(rport->fcs, rport->pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &rport->fcxp_wqe, + bfa_fcs_rport_send_plogi, rport); + return; + } + rport->fcxp = fcxp; + + len = fc_plogi_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rport->pid, + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn, + bfa_pport_get_maxfrsize(port->fcs->bfa)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_rport_plogi_response, + (void *)rport, FC_MAX_PDUSZ, FC_RA_TOV); + + rport->stats.plogis++; + bfa_sm_send_event(rport, RPSM_EVENT_FCXP_SENT); +} + +static void +bfa_fcs_rport_plogi_response(void *fcsarg, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)cbarg; + struct fc_logi_s *plogi_rsp; + struct fc_ls_rjt_s *ls_rjt; + struct bfa_fcs_rport_s *twin; + struct list_head *qe; + + bfa_trc(rport->fcs, rport->pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(rport->fcs, req_status); + rport->stats.plogi_failed++; + bfa_sm_send_event(rport, RPSM_EVENT_FAILED); + return; + } + + plogi_rsp = (struct fc_logi_s *) BFA_FCXP_RSP_PLD(fcxp); + + /** + * Check for failure first. + */ + if (plogi_rsp->els_cmd.els_code != FC_ELS_ACC) { + ls_rjt = (struct fc_ls_rjt_s *) BFA_FCXP_RSP_PLD(fcxp); + + bfa_trc(rport->fcs, ls_rjt->reason_code); + bfa_trc(rport->fcs, ls_rjt->reason_code_expl); + + rport->stats.plogi_rejects++; + bfa_sm_send_event(rport, RPSM_EVENT_FAILED); + return; + } + + /** + * PLOGI is complete. Make sure this device is not one of the known + * device with a new FC port address. + */ + list_for_each(qe, &rport->port->rport_q) { + twin = (struct bfa_fcs_rport_s *)qe; + if (twin == rport) + continue; + if (!rport->pwwn && (plogi_rsp->port_name == twin->pwwn)) { + bfa_trc(rport->fcs, twin->pid); + bfa_trc(rport->fcs, rport->pid); + + /* + * Update plogi stats in twin + */ + twin->stats.plogis += rport->stats.plogis; + twin->stats.plogi_rejects += rport->stats.plogi_rejects; + twin->stats.plogi_timeouts += + rport->stats.plogi_timeouts; + twin->stats.plogi_failed += rport->stats.plogi_failed; + twin->stats.plogi_rcvd += rport->stats.plogi_rcvd; + twin->stats.plogi_accs++; + + bfa_fcs_rport_delete(rport); + + bfa_fcs_rport_update(twin, plogi_rsp); + twin->pid = rsp_fchs->s_id; + bfa_sm_send_event(twin, RPSM_EVENT_PLOGI_COMP); + return; + } + } + + /** + * Normal login path -- no evil twins. + */ + rport->stats.plogi_accs++; + bfa_fcs_rport_update(rport, plogi_rsp); + bfa_sm_send_event(rport, RPSM_EVENT_ACCEPTED); +} + +static void +bfa_fcs_rport_send_plogiacc(void *rport_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_rport_s *rport = rport_cbarg; + struct bfa_fcs_port_s *port = rport->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->reply_oxid); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &rport->fcxp_wqe, + bfa_fcs_rport_send_plogiacc, rport); + return; + } + rport->fcxp = fcxp; + + len = fc_plogi_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rport->pid, + bfa_fcs_port_get_fcid(port), rport->reply_oxid, + port->port_cfg.pwwn, port->port_cfg.nwwn, + bfa_pport_get_maxfrsize(port->fcs->bfa)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, NULL, NULL, FC_MAX_PDUSZ, 0); + + bfa_sm_send_event(rport, RPSM_EVENT_FCXP_SENT); +} + +static void +bfa_fcs_rport_send_adisc(void *rport_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_rport_s *rport = rport_cbarg; + struct bfa_fcs_port_s *port = rport->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(rport->fcs, rport->pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &rport->fcxp_wqe, + bfa_fcs_rport_send_adisc, rport); + return; + } + rport->fcxp = fcxp; + + len = fc_adisc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rport->pid, + bfa_fcs_port_get_fcid(port), 0, + port->port_cfg.pwwn, port->port_cfg.nwwn); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_rport_adisc_response, + rport, FC_MAX_PDUSZ, FC_RA_TOV); + + rport->stats.adisc_sent++; + bfa_sm_send_event(rport, RPSM_EVENT_FCXP_SENT); +} + +static void +bfa_fcs_rport_adisc_response(void *fcsarg, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)cbarg; + void *pld = bfa_fcxp_get_rspbuf(fcxp); + struct fc_ls_rjt_s *ls_rjt; + + if (req_status != BFA_STATUS_OK) { + bfa_trc(rport->fcs, req_status); + rport->stats.adisc_failed++; + bfa_sm_send_event(rport, RPSM_EVENT_FAILED); + return; + } + + if (fc_adisc_rsp_parse((struct fc_adisc_s *)pld, rsp_len, rport->pwwn, + rport->nwwn) == FC_PARSE_OK) { + rport->stats.adisc_accs++; + bfa_sm_send_event(rport, RPSM_EVENT_ACCEPTED); + return; + } + + rport->stats.adisc_rejects++; + ls_rjt = pld; + bfa_trc(rport->fcs, ls_rjt->els_cmd.els_code); + bfa_trc(rport->fcs, ls_rjt->reason_code); + bfa_trc(rport->fcs, ls_rjt->reason_code_expl); + bfa_sm_send_event(rport, RPSM_EVENT_FAILED); +} + +static void +bfa_fcs_rport_send_gidpn(void *rport_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_rport_s *rport = rport_cbarg; + struct bfa_fcs_port_s *port = rport->port; + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + int len; + + bfa_trc(rport->fcs, rport->pid); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &rport->fcxp_wqe, + bfa_fcs_rport_send_gidpn, rport); + return; + } + rport->fcxp = fcxp; + + len = fc_gidpn_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_fcs_port_get_fcid(port), 0, rport->pwwn); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_rport_gidpn_response, + (void *)rport, FC_MAX_PDUSZ, FC_RA_TOV); + + bfa_sm_send_event(rport, RPSM_EVENT_FCXP_SENT); +} + +static void +bfa_fcs_rport_gidpn_response(void *fcsarg, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)cbarg; + struct bfa_fcs_rport_s *twin; + struct list_head *qe; + struct ct_hdr_s *cthdr; + struct fcgs_gidpn_resp_s *gidpn_rsp; + + bfa_trc(rport->fcs, rport->pwwn); + + cthdr = (struct ct_hdr_s *) BFA_FCXP_RSP_PLD(fcxp); + cthdr->cmd_rsp_code = bfa_os_ntohs(cthdr->cmd_rsp_code); + + if (cthdr->cmd_rsp_code == CT_RSP_ACCEPT) { + /* + * Check if the pid is the same as before. + */ + gidpn_rsp = (struct fcgs_gidpn_resp_s *) (cthdr + 1); + + if (gidpn_rsp->dap == rport->pid) { + /* + * Device is online + */ + bfa_sm_send_event(rport, RPSM_EVENT_ACCEPTED); + } else { + /* + * Device's PID has changed. We need to cleanup and + * re-login. If there is another device with the the + * newly discovered pid, send an scn notice so that its + * new pid can be discovered. + */ + list_for_each(qe, &rport->port->rport_q) { + twin = (struct bfa_fcs_rport_s *)qe; + if (twin == rport) + continue; + if (gidpn_rsp->dap == twin->pid) { + bfa_trc(rport->fcs, twin->pid); + bfa_trc(rport->fcs, rport->pid); + + twin->pid = 0; + bfa_sm_send_event(twin, + RPSM_EVENT_ADDRESS_CHANGE); + } + } + rport->pid = gidpn_rsp->dap; + bfa_sm_send_event(rport, RPSM_EVENT_ADDRESS_CHANGE); + } + return; + } + + /* + * Reject Response + */ + switch (cthdr->reason_code) { + case CT_RSN_LOGICAL_BUSY: + /* + * Need to retry + */ + bfa_sm_send_event(rport, RPSM_EVENT_TIMEOUT); + break; + + case CT_RSN_UNABLE_TO_PERF: + /* + * device doesn't exist : Start timer to cleanup this later. + */ + bfa_sm_send_event(rport, RPSM_EVENT_FAILED); + break; + + default: + bfa_sm_send_event(rport, RPSM_EVENT_FAILED); + break; + } +} + +/** + * Called to send a logout to the rport. + */ +static void +bfa_fcs_rport_send_logo(void *rport_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_rport_s *rport = rport_cbarg; + struct bfa_fcs_port_s *port; + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + u16 len; + + bfa_trc(rport->fcs, rport->pid); + + port = rport->port; + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &rport->fcxp_wqe, + bfa_fcs_rport_send_logo, rport); + return; + } + rport->fcxp = fcxp; + + len = fc_logo_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rport->pid, + bfa_fcs_port_get_fcid(port), 0, + bfa_fcs_port_get_pwwn(port)); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, NULL, rport, FC_MAX_PDUSZ, + FC_ED_TOV); + + rport->stats.logos++; + bfa_fcxp_discard(rport->fcxp); + bfa_sm_send_event(rport, RPSM_EVENT_FCXP_SENT); +} + +/** + * Send ACC for a LOGO received. + */ +static void +bfa_fcs_rport_send_logo_acc(void *rport_cbarg) +{ + struct bfa_fcs_rport_s *rport = rport_cbarg; + struct bfa_fcs_port_s *port; + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + u16 len; + + bfa_trc(rport->fcs, rport->pid); + + port = rport->port; + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + rport->stats.logo_rcvd++; + len = fc_logo_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rport->pid, + bfa_fcs_port_get_fcid(port), rport->reply_oxid); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, NULL, NULL, FC_MAX_PDUSZ, 0); +} + +/** + * This routine will be called by bfa_timer on timer timeouts. + * + * param[in] rport - pointer to bfa_fcs_port_ns_t. + * param[out] rport_status - pointer to return vport status in + * + * return + * void + * +* Special Considerations: + * + * note + */ +static void +bfa_fcs_rport_timeout(void *arg) +{ + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)arg; + + rport->stats.plogi_timeouts++; + bfa_sm_send_event(rport, RPSM_EVENT_TIMEOUT); +} + +static void +bfa_fcs_rport_process_prli(struct bfa_fcs_rport_s *rport, + struct fchs_s *rx_fchs, u16 len) +{ + struct bfa_fcxp_s *fcxp; + struct fchs_s fchs; + struct bfa_fcs_port_s *port = rport->port; + struct fc_prli_s *prli; + + bfa_trc(port->fcs, rx_fchs->s_id); + bfa_trc(port->fcs, rx_fchs->d_id); + + rport->stats.prli_rcvd++; + + if (BFA_FCS_VPORT_IS_TARGET_MODE(port)) { + /* + * Target Mode : Let the fcptm handle it + */ + bfa_fcs_tin_rx_prli(rport->tin, rx_fchs, len); + return; + } + + /* + * We are either in Initiator or ipfc Mode + */ + prli = (struct fc_prli_s *) (rx_fchs + 1); + + if (prli->parampage.servparams.initiator) { + bfa_trc(rport->fcs, prli->parampage.type); + rport->scsi_function = BFA_RPORT_INITIATOR; + bfa_fcs_itnim_is_initiator(rport->itnim); + } else { + /* + * @todo: PRLI from a target ? + */ + bfa_trc(port->fcs, rx_fchs->s_id); + rport->scsi_function = BFA_RPORT_TARGET; + } + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + len = fc_prli_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), rx_fchs->ox_id, + port->port_cfg.roles); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, NULL, NULL, FC_MAX_PDUSZ, 0); +} + +static void +bfa_fcs_rport_process_rpsc(struct bfa_fcs_rport_s *rport, + struct fchs_s *rx_fchs, u16 len) +{ + struct bfa_fcxp_s *fcxp; + struct fchs_s fchs; + struct bfa_fcs_port_s *port = rport->port; + struct fc_rpsc_speed_info_s speeds; + struct bfa_pport_attr_s pport_attr; + + bfa_trc(port->fcs, rx_fchs->s_id); + bfa_trc(port->fcs, rx_fchs->d_id); + + rport->stats.rpsc_rcvd++; + speeds.port_speed_cap = + RPSC_SPEED_CAP_1G | RPSC_SPEED_CAP_2G | RPSC_SPEED_CAP_4G | + RPSC_SPEED_CAP_8G; + + /* + * get curent speed from pport attributes from BFA + */ + bfa_pport_get_attr(port->fcs->bfa, &pport_attr); + + speeds.port_op_speed = fc_bfa_speed_to_rpsc_operspeed(pport_attr.speed); + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + len = fc_rpsc_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), rx_fchs->ox_id, + &speeds); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, NULL, NULL, FC_MAX_PDUSZ, 0); +} + +static void +bfa_fcs_rport_process_adisc(struct bfa_fcs_rport_s *rport, + struct fchs_s *rx_fchs, u16 len) +{ + struct bfa_fcxp_s *fcxp; + struct fchs_s fchs; + struct bfa_fcs_port_s *port = rport->port; + struct fc_adisc_s *adisc; + + bfa_trc(port->fcs, rx_fchs->s_id); + bfa_trc(port->fcs, rx_fchs->d_id); + + rport->stats.adisc_rcvd++; + + if (BFA_FCS_VPORT_IS_TARGET_MODE(port)) { + /* + * @todo : Target Mode handling + */ + bfa_trc(port->fcs, rx_fchs->d_id); + bfa_assert(0); + return; + } + + adisc = (struct fc_adisc_s *) (rx_fchs + 1); + + /* + * Accept if the itnim for this rport is online. Else reject the ADISC + */ + if (bfa_fcs_itnim_get_online_state(rport->itnim) == BFA_STATUS_OK) { + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + len = fc_adisc_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), + rx_fchs->ox_id, port->port_cfg.pwwn, + port->port_cfg.nwwn); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, + BFA_FALSE, FC_CLASS_3, len, &fchs, NULL, NULL, + FC_MAX_PDUSZ, 0); + } else { + rport->stats.adisc_rejected++; + bfa_fcs_rport_send_ls_rjt(rport, rx_fchs, + FC_LS_RJT_RSN_UNABLE_TO_PERF_CMD, + FC_LS_RJT_EXP_LOGIN_REQUIRED); + } + +} + +static void +bfa_fcs_rport_hal_online(struct bfa_fcs_rport_s *rport) +{ + struct bfa_fcs_port_s *port = rport->port; + struct bfa_rport_info_s rport_info; + + rport_info.pid = rport->pid; + rport_info.local_pid = port->pid; + rport_info.lp_tag = port->lp_tag; + rport_info.vf_id = port->fabric->vf_id; + rport_info.vf_en = port->fabric->is_vf; + rport_info.fc_class = rport->fc_cos; + rport_info.cisc = rport->cisc; + rport_info.max_frmsz = rport->maxfrsize; + bfa_rport_online(rport->bfa_rport, &rport_info); +} + +static void +bfa_fcs_rport_fc4_pause(struct bfa_fcs_rport_s *rport) +{ + if (bfa_fcs_port_is_initiator(rport->port)) + bfa_fcs_itnim_pause(rport->itnim); + + if (bfa_fcs_port_is_target(rport->port)) + bfa_fcs_tin_pause(rport->tin); +} + +static void +bfa_fcs_rport_fc4_resume(struct bfa_fcs_rport_s *rport) +{ + if (bfa_fcs_port_is_initiator(rport->port)) + bfa_fcs_itnim_resume(rport->itnim); + + if (bfa_fcs_port_is_target(rport->port)) + bfa_fcs_tin_resume(rport->tin); +} + +static struct bfa_fcs_rport_s * +bfa_fcs_rport_alloc(struct bfa_fcs_port_s *port, wwn_t pwwn, u32 rpid) +{ + struct bfa_fcs_s *fcs = port->fcs; + struct bfa_fcs_rport_s *rport; + struct bfad_rport_s *rport_drv; + + /** + * allocate rport + */ + if (bfa_fcb_rport_alloc(fcs->bfad, &rport, &rport_drv) + != BFA_STATUS_OK) { + bfa_trc(fcs, rpid); + return NULL; + } + + /* + * Initialize r-port + */ + rport->port = port; + rport->fcs = fcs; + rport->rp_drv = rport_drv; + rport->pid = rpid; + rport->pwwn = pwwn; + + /** + * allocate BFA rport + */ + rport->bfa_rport = bfa_rport_create(port->fcs->bfa, rport); + if (!rport->bfa_rport) { + bfa_trc(fcs, rpid); + kfree(rport_drv); + return NULL; + } + + /** + * allocate FC-4s + */ + bfa_assert(bfa_fcs_port_is_initiator(port) ^ + bfa_fcs_port_is_target(port)); + + if (bfa_fcs_port_is_initiator(port)) { + rport->itnim = bfa_fcs_itnim_create(rport); + if (!rport->itnim) { + bfa_trc(fcs, rpid); + bfa_rport_delete(rport->bfa_rport); + kfree(rport_drv); + return NULL; + } + } + + if (bfa_fcs_port_is_target(port)) { + rport->tin = bfa_fcs_tin_create(rport); + if (!rport->tin) { + bfa_trc(fcs, rpid); + bfa_rport_delete(rport->bfa_rport); + kfree(rport_drv); + return NULL; + } + } + + bfa_fcs_port_add_rport(port, rport); + + bfa_sm_set_state(rport, bfa_fcs_rport_sm_uninit); + + /* + * Initialize the Rport Features(RPF) Sub Module + */ + if (!BFA_FCS_PID_IS_WKA(rport->pid)) + bfa_fcs_rpf_init(rport); + + return rport; +} + + +static void +bfa_fcs_rport_free(struct bfa_fcs_rport_s *rport) +{ + struct bfa_fcs_port_s *port = rport->port; + + /** + * - delete FC-4s + * - delete BFA rport + * - remove from queue of rports + */ + if (bfa_fcs_port_is_initiator(port)) + bfa_fcs_itnim_delete(rport->itnim); + + if (bfa_fcs_port_is_target(port)) + bfa_fcs_tin_delete(rport->tin); + + bfa_rport_delete(rport->bfa_rport); + bfa_fcs_port_del_rport(port, rport); + kfree(rport->rp_drv); +} + +static void +bfa_fcs_rport_aen_post(struct bfa_fcs_rport_s *rport, + enum bfa_rport_aen_event event, + struct bfa_rport_aen_data_s *data) +{ + union bfa_aen_data_u aen_data; + struct bfa_log_mod_s *logmod = rport->fcs->logm; + wwn_t lpwwn = bfa_fcs_port_get_pwwn(rport->port); + wwn_t rpwwn = rport->pwwn; + char lpwwn_ptr[BFA_STRING_32]; + char rpwwn_ptr[BFA_STRING_32]; + char *prio_str[] = { "unknown", "high", "medium", "low" }; + + wwn2str(lpwwn_ptr, lpwwn); + wwn2str(rpwwn_ptr, rpwwn); + + switch (event) { + case BFA_RPORT_AEN_ONLINE: + bfa_log(logmod, BFA_AEN_RPORT_ONLINE, rpwwn_ptr, lpwwn_ptr); + break; + case BFA_RPORT_AEN_OFFLINE: + bfa_log(logmod, BFA_AEN_RPORT_OFFLINE, rpwwn_ptr, lpwwn_ptr); + break; + case BFA_RPORT_AEN_DISCONNECT: + bfa_log(logmod, BFA_AEN_RPORT_DISCONNECT, rpwwn_ptr, lpwwn_ptr); + break; + case BFA_RPORT_AEN_QOS_PRIO: + aen_data.rport.priv.qos = data->priv.qos; + bfa_log(logmod, BFA_AEN_RPORT_QOS_PRIO, + prio_str[aen_data.rport.priv.qos.qos_priority], + rpwwn_ptr, lpwwn_ptr); + break; + case BFA_RPORT_AEN_QOS_FLOWID: + aen_data.rport.priv.qos = data->priv.qos; + bfa_log(logmod, BFA_AEN_RPORT_QOS_FLOWID, + aen_data.rport.priv.qos.qos_flow_id, rpwwn_ptr, + lpwwn_ptr); + break; + default: + break; + } + + aen_data.rport.vf_id = rport->port->fabric->vf_id; + aen_data.rport.ppwwn = + bfa_fcs_port_get_pwwn(bfa_fcs_get_base_port(rport->fcs)); + aen_data.rport.lpwwn = lpwwn; + aen_data.rport.rpwwn = rpwwn; +} + +static void +bfa_fcs_rport_online_action(struct bfa_fcs_rport_s *rport) +{ + struct bfa_fcs_port_s *port = rport->port; + + rport->stats.onlines++; + + if (bfa_fcs_port_is_initiator(port)) { + bfa_fcs_itnim_rport_online(rport->itnim); + if (!BFA_FCS_PID_IS_WKA(rport->pid)) + bfa_fcs_rpf_rport_online(rport); + }; + + if (bfa_fcs_port_is_target(port)) + bfa_fcs_tin_rport_online(rport->tin); + + /* + * Don't post events for well known addresses + */ + if (!BFA_FCS_PID_IS_WKA(rport->pid)) + bfa_fcs_rport_aen_post(rport, BFA_RPORT_AEN_ONLINE, NULL); +} + +static void +bfa_fcs_rport_offline_action(struct bfa_fcs_rport_s *rport) +{ + struct bfa_fcs_port_s *port = rport->port; + + rport->stats.offlines++; + + /* + * Don't post events for well known addresses + */ + if (!BFA_FCS_PID_IS_WKA(rport->pid)) { + if (bfa_fcs_port_is_online(rport->port) == BFA_TRUE) { + bfa_fcs_rport_aen_post(rport, BFA_RPORT_AEN_DISCONNECT, + NULL); + } else { + bfa_fcs_rport_aen_post(rport, BFA_RPORT_AEN_OFFLINE, + NULL); + } + } + + if (bfa_fcs_port_is_initiator(port)) { + bfa_fcs_itnim_rport_offline(rport->itnim); + if (!BFA_FCS_PID_IS_WKA(rport->pid)) + bfa_fcs_rpf_rport_offline(rport); + } + + if (bfa_fcs_port_is_target(port)) + bfa_fcs_tin_rport_offline(rport->tin); +} + +/** + * Update rport parameters from PLOGI or PLOGI accept. + */ +static void +bfa_fcs_rport_update(struct bfa_fcs_rport_s *rport, struct fc_logi_s *plogi) +{ + struct bfa_fcs_port_s *port = rport->port; + + /** + * - port name + * - node name + */ + rport->pwwn = plogi->port_name; + rport->nwwn = plogi->node_name; + + /** + * - class of service + */ + rport->fc_cos = 0; + if (plogi->class3.class_valid) + rport->fc_cos = FC_CLASS_3; + + if (plogi->class2.class_valid) + rport->fc_cos |= FC_CLASS_2; + + /** + * - CISC + * - MAX receive frame size + */ + rport->cisc = plogi->csp.cisc; + rport->maxfrsize = bfa_os_ntohs(plogi->class3.rxsz); + + bfa_trc(port->fcs, bfa_os_ntohs(plogi->csp.bbcred)); + bfa_trc(port->fcs, port->fabric->bb_credit); + /** + * Direct Attach P2P mode : + * This is to handle a bug (233476) in IBM targets in Direct Attach + * Mode. Basically, in FLOGI Accept the target would have erroneously + * set the BB Credit to the value used in the FLOGI sent by the HBA. + * It uses the correct value (its own BB credit) in PLOGI. + */ + if ((!bfa_fcs_fabric_is_switched(port->fabric)) + && (bfa_os_ntohs(plogi->csp.bbcred) < port->fabric->bb_credit)) { + + bfa_trc(port->fcs, bfa_os_ntohs(plogi->csp.bbcred)); + bfa_trc(port->fcs, port->fabric->bb_credit); + + port->fabric->bb_credit = bfa_os_ntohs(plogi->csp.bbcred); + bfa_pport_set_tx_bbcredit(port->fcs->bfa, + port->fabric->bb_credit); + } + +} + +/** + * Called to handle LOGO received from an existing remote port. + */ +static void +bfa_fcs_rport_process_logo(struct bfa_fcs_rport_s *rport, struct fchs_s *fchs) +{ + rport->reply_oxid = fchs->ox_id; + bfa_trc(rport->fcs, rport->reply_oxid); + + rport->stats.logo_rcvd++; + bfa_sm_send_event(rport, RPSM_EVENT_LOGO_RCVD); +} + + + +/** + * fcs_rport_public FCS rport public interfaces + */ + +/** + * Called by bport/vport to create a remote port instance for a discovered + * remote device. + * + * @param[in] port - base port or vport + * @param[in] rpid - remote port ID + * + * @return None + */ +struct bfa_fcs_rport_s * +bfa_fcs_rport_create(struct bfa_fcs_port_s *port, u32 rpid) +{ + struct bfa_fcs_rport_s *rport; + + bfa_trc(port->fcs, rpid); + rport = bfa_fcs_rport_alloc(port, WWN_NULL, rpid); + if (!rport) + return NULL; + + bfa_sm_send_event(rport, RPSM_EVENT_PLOGI_SEND); + return rport; +} + +/** + * Called to create a rport for which only the wwn is known. + * + * @param[in] port - base port + * @param[in] rpwwn - remote port wwn + * + * @return None + */ +struct bfa_fcs_rport_s * +bfa_fcs_rport_create_by_wwn(struct bfa_fcs_port_s *port, wwn_t rpwwn) +{ + struct bfa_fcs_rport_s *rport; + + bfa_trc(port->fcs, rpwwn); + rport = bfa_fcs_rport_alloc(port, rpwwn, 0); + if (!rport) + return NULL; + + bfa_sm_send_event(rport, RPSM_EVENT_ADDRESS_DISC); + return rport; +} + +/** + * Called by bport in private loop topology to indicate that a + * rport has been discovered and plogi has been completed. + * + * @param[in] port - base port or vport + * @param[in] rpid - remote port ID + */ +void +bfa_fcs_rport_start(struct bfa_fcs_port_s *port, struct fchs_s *fchs, + struct fc_logi_s *plogi) +{ + struct bfa_fcs_rport_s *rport; + + rport = bfa_fcs_rport_alloc(port, WWN_NULL, fchs->s_id); + if (!rport) + return; + + bfa_fcs_rport_update(rport, plogi); + + bfa_sm_send_event(rport, RPSM_EVENT_PLOGI_COMP); +} + +/** + * Called by bport/vport to handle PLOGI received from a new remote port. + * If an existing rport does a plogi, it will be handled separately. + */ +void +bfa_fcs_rport_plogi_create(struct bfa_fcs_port_s *port, struct fchs_s *fchs, + struct fc_logi_s *plogi) +{ + struct bfa_fcs_rport_s *rport; + + rport = bfa_fcs_rport_alloc(port, plogi->port_name, fchs->s_id); + if (!rport) + return; + + bfa_fcs_rport_update(rport, plogi); + + rport->reply_oxid = fchs->ox_id; + bfa_trc(rport->fcs, rport->reply_oxid); + + rport->stats.plogi_rcvd++; + bfa_sm_send_event(rport, RPSM_EVENT_PLOGI_RCVD); +} + +static int +wwn_compare(wwn_t wwn1, wwn_t wwn2) +{ + u8 *b1 = (u8 *) &wwn1; + u8 *b2 = (u8 *) &wwn2; + int i; + + for (i = 0; i < sizeof(wwn_t); i++) { + if (b1[i] < b2[i]) + return -1; + if (b1[i] > b2[i]) + return 1; + } + return 0; +} + +/** + * Called by bport/vport to handle PLOGI received from an existing + * remote port. + */ +void +bfa_fcs_rport_plogi(struct bfa_fcs_rport_s *rport, struct fchs_s *rx_fchs, + struct fc_logi_s *plogi) +{ + /** + * @todo Handle P2P and initiator-initiator. + */ + + bfa_fcs_rport_update(rport, plogi); + + rport->reply_oxid = rx_fchs->ox_id; + bfa_trc(rport->fcs, rport->reply_oxid); + + /** + * In Switched fabric topology, + * PLOGI to each other. If our pwwn is smaller, ignore it, + * if it is not a well known address. + * If the link topology is N2N, + * this Plogi should be accepted. + */ + if ((wwn_compare(rport->port->port_cfg.pwwn, rport->pwwn) == -1) + && (bfa_fcs_fabric_is_switched(rport->port->fabric)) + && (!BFA_FCS_PID_IS_WKA(rport->pid))) { + bfa_trc(rport->fcs, rport->pid); + return; + } + + rport->stats.plogi_rcvd++; + bfa_sm_send_event(rport, RPSM_EVENT_PLOGI_RCVD); +} + +/** + * Called by bport/vport to delete a remote port instance. + * +* Rport delete is called under the following conditions: + * - vport is deleted + * - vf is deleted + * - explicit request from OS to delete rport (vmware) + */ +void +bfa_fcs_rport_delete(struct bfa_fcs_rport_s *rport) +{ + bfa_sm_send_event(rport, RPSM_EVENT_DELETE); +} + +/** + * Called by bport/vport to when a target goes offline. + * + */ +void +bfa_fcs_rport_offline(struct bfa_fcs_rport_s *rport) +{ + bfa_sm_send_event(rport, RPSM_EVENT_LOGO_IMP); +} + +/** + * Called by bport in n2n when a target (attached port) becomes online. + * + */ +void +bfa_fcs_rport_online(struct bfa_fcs_rport_s *rport) +{ + bfa_sm_send_event(rport, RPSM_EVENT_PLOGI_SEND); +} + +/** + * Called by bport/vport to notify SCN for the remote port + */ +void +bfa_fcs_rport_scn(struct bfa_fcs_rport_s *rport) +{ + + rport->stats.rscns++; + bfa_sm_send_event(rport, RPSM_EVENT_SCN); +} + +/** + * Called by fcpim to notify that the ITN cleanup is done. + */ +void +bfa_fcs_rport_itnim_ack(struct bfa_fcs_rport_s *rport) +{ + bfa_sm_send_event(rport, RPSM_EVENT_FC4_OFFLINE); +} + +/** + * Called by fcptm to notify that the ITN cleanup is done. + */ +void +bfa_fcs_rport_tin_ack(struct bfa_fcs_rport_s *rport) +{ + bfa_sm_send_event(rport, RPSM_EVENT_FC4_OFFLINE); +} + +/** + * This routine BFA callback for bfa_rport_online() call. + * + * param[in] cb_arg - rport struct. + * + * return + * void + * +* Special Considerations: + * + * note + */ +void +bfa_cb_rport_online(void *cbarg) +{ + + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)cbarg; + + bfa_trc(rport->fcs, rport->pwwn); + bfa_sm_send_event(rport, RPSM_EVENT_HCB_ONLINE); +} + +/** + * This routine BFA callback for bfa_rport_offline() call. + * + * param[in] rport - + * + * return + * void + * + * Special Considerations: + * + * note + */ +void +bfa_cb_rport_offline(void *cbarg) +{ + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)cbarg; + + bfa_trc(rport->fcs, rport->pwwn); + bfa_sm_send_event(rport, RPSM_EVENT_HCB_OFFLINE); +} + +/** + * This routine is a static BFA callback when there is a QoS flow_id + * change notification + * + * @param[in] rport - + * + * @return void + * + * Special Considerations: + * + * @note + */ +void +bfa_cb_rport_qos_scn_flowid(void *cbarg, + struct bfa_rport_qos_attr_s old_qos_attr, + struct bfa_rport_qos_attr_s new_qos_attr) +{ + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)cbarg; + struct bfa_rport_aen_data_s aen_data; + + bfa_trc(rport->fcs, rport->pwwn); + aen_data.priv.qos = new_qos_attr; + bfa_fcs_rport_aen_post(rport, BFA_RPORT_AEN_QOS_FLOWID, &aen_data); +} + +/** + * This routine is a static BFA callback when there is a QoS priority + * change notification + * + * @param[in] rport - + * + * @return void + * + * Special Considerations: + * + * @note + */ +void +bfa_cb_rport_qos_scn_prio(void *cbarg, struct bfa_rport_qos_attr_s old_qos_attr, + struct bfa_rport_qos_attr_s new_qos_attr) +{ + struct bfa_fcs_rport_s *rport = (struct bfa_fcs_rport_s *)cbarg; + struct bfa_rport_aen_data_s aen_data; + + bfa_trc(rport->fcs, rport->pwwn); + aen_data.priv.qos = new_qos_attr; + bfa_fcs_rport_aen_post(rport, BFA_RPORT_AEN_QOS_PRIO, &aen_data); +} + +/** + * Called to process any unsolicted frames from this remote port + */ +void +bfa_fcs_rport_logo_imp(struct bfa_fcs_rport_s *rport) +{ + bfa_sm_send_event(rport, RPSM_EVENT_LOGO_IMP); +} + +/** + * Called to process any unsolicted frames from this remote port + */ +void +bfa_fcs_rport_uf_recv(struct bfa_fcs_rport_s *rport, struct fchs_s *fchs, + u16 len) +{ + struct bfa_fcs_port_s *port = rport->port; + struct fc_els_cmd_s *els_cmd; + + bfa_trc(rport->fcs, fchs->s_id); + bfa_trc(rport->fcs, fchs->d_id); + bfa_trc(rport->fcs, fchs->type); + + if (fchs->type != FC_TYPE_ELS) + return; + + els_cmd = (struct fc_els_cmd_s *) (fchs + 1); + + bfa_trc(rport->fcs, els_cmd->els_code); + + switch (els_cmd->els_code) { + case FC_ELS_LOGO: + bfa_fcs_rport_process_logo(rport, fchs); + break; + + case FC_ELS_ADISC: + bfa_fcs_rport_process_adisc(rport, fchs, len); + break; + + case FC_ELS_PRLO: + if (bfa_fcs_port_is_initiator(port)) + bfa_fcs_fcpim_uf_recv(rport->itnim, fchs, len); + + if (bfa_fcs_port_is_target(port)) + bfa_fcs_fcptm_uf_recv(rport->tin, fchs, len); + break; + + case FC_ELS_PRLI: + bfa_fcs_rport_process_prli(rport, fchs, len); + break; + + case FC_ELS_RPSC: + bfa_fcs_rport_process_rpsc(rport, fchs, len); + break; + + default: + bfa_fcs_rport_send_ls_rjt(rport, fchs, + FC_LS_RJT_RSN_CMD_NOT_SUPP, + FC_LS_RJT_EXP_NO_ADDL_INFO); + break; + } +} + +/* + * Send a LS reject + */ +static void +bfa_fcs_rport_send_ls_rjt(struct bfa_fcs_rport_s *rport, struct fchs_s *rx_fchs, + u8 reason_code, u8 reason_code_expl) +{ + struct bfa_fcs_port_s *port = rport->port; + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + int len; + + bfa_trc(rport->fcs, rx_fchs->s_id); + + fcxp = bfa_fcs_fcxp_alloc(rport->fcs); + if (!fcxp) + return; + + len = fc_ls_rjt_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), rx_fchs->ox_id, + reason_code, reason_code_expl); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, NULL, NULL, FC_MAX_PDUSZ, 0); +} + +/** + * Module initialization + */ +void +bfa_fcs_rport_modinit(struct bfa_fcs_s *fcs) +{ +} + +/** + * Module cleanup + */ +void +bfa_fcs_rport_modexit(struct bfa_fcs_s *fcs) +{ + bfa_fcs_modexit_comp(fcs); +} + +/** + * Return state of rport. + */ +int +bfa_fcs_rport_get_state(struct bfa_fcs_rport_s *rport) +{ + return bfa_sm_to_state(rport_sm_table, rport->sm); +} + +/** + * Called by the Driver to set rport delete/ageout timeout + * + * param[in] rport timeout value in seconds. + * + * return None + */ +void +bfa_fcs_rport_set_del_timeout(u8 rport_tmo) +{ + /* + * convert to Millisecs + */ + if (rport_tmo > 0) + bfa_fcs_rport_del_timeout = rport_tmo * 1000; +} diff --git a/drivers/scsi/bfa/rport_api.c b/drivers/scsi/bfa/rport_api.c new file mode 100644 index 000000000000..3dae1774181e --- /dev/null +++ b/drivers/scsi/bfa/rport_api.c @@ -0,0 +1,180 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_vport.h" +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "fcs_trcmod.h" + +BFA_TRC_FILE(FCS, RPORT_API); + +/** + * rport_api.c Remote port implementation. + */ + +/** + * fcs_rport_api FCS rport API. + */ + +/** + * Direct API to add a target by port wwn. This interface is used, for + * example, by bios when target pwwn is known from boot lun configuration. + */ +bfa_status_t +bfa_fcs_rport_add(struct bfa_fcs_port_s *port, wwn_t *pwwn, + struct bfa_fcs_rport_s *rport, + struct bfad_rport_s *rport_drv) +{ + bfa_trc(port->fcs, *pwwn); + + return BFA_STATUS_OK; +} + +/** + * Direct API to remove a target and its associated resources. This + * interface is used, for example, by vmware driver to remove target + * ports from the target list for a VM. + */ +bfa_status_t +bfa_fcs_rport_remove(struct bfa_fcs_rport_s *rport_in) +{ + + struct bfa_fcs_rport_s *rport; + + bfa_trc(rport_in->fcs, rport_in->pwwn); + + rport = bfa_fcs_port_get_rport_by_pwwn(rport_in->port, rport_in->pwwn); + if (rport == NULL) { + /* + * TBD Error handling + */ + bfa_trc(rport_in->fcs, rport_in->pid); + return BFA_STATUS_UNKNOWN_RWWN; + } + + /* + * TBD if this remote port is online, send a logo + */ + return BFA_STATUS_OK; + +} + +/** + * Remote device status for display/debug. + */ +void +bfa_fcs_rport_get_attr(struct bfa_fcs_rport_s *rport, + struct bfa_rport_attr_s *rport_attr) +{ + struct bfa_rport_qos_attr_s qos_attr; + struct bfa_fcs_port_s *port = rport->port; + + bfa_os_memset(rport_attr, 0, sizeof(struct bfa_rport_attr_s)); + + rport_attr->pid = rport->pid; + rport_attr->pwwn = rport->pwwn; + rport_attr->nwwn = rport->nwwn; + rport_attr->cos_supported = rport->fc_cos; + rport_attr->df_sz = rport->maxfrsize; + rport_attr->state = bfa_fcs_rport_get_state(rport); + rport_attr->fc_cos = rport->fc_cos; + rport_attr->cisc = rport->cisc; + rport_attr->scsi_function = rport->scsi_function; + rport_attr->curr_speed = rport->rpf.rpsc_speed; + rport_attr->assigned_speed = rport->rpf.assigned_speed; + + bfa_rport_get_qos_attr(rport->bfa_rport, &qos_attr); + rport_attr->qos_attr = qos_attr; + + rport_attr->trl_enforced = BFA_FALSE; + if (bfa_pport_is_ratelim(port->fcs->bfa)) { + if ((rport->rpf.rpsc_speed == BFA_PPORT_SPEED_UNKNOWN) || + (rport->rpf.rpsc_speed < + bfa_fcs_port_get_rport_max_speed(port))) + rport_attr->trl_enforced = BFA_TRUE; + } + + /* + * TODO + * rport->symname + */ +} + +/** + * Per remote device statistics. + */ +void +bfa_fcs_rport_get_stats(struct bfa_fcs_rport_s *rport, + struct bfa_rport_stats_s *stats) +{ + *stats = rport->stats; +} + +void +bfa_fcs_rport_clear_stats(struct bfa_fcs_rport_s *rport) +{ + bfa_os_memset((char *)&rport->stats, 0, + sizeof(struct bfa_rport_stats_s)); +} + +struct bfa_fcs_rport_s * +bfa_fcs_rport_lookup(struct bfa_fcs_port_s *port, wwn_t rpwwn) +{ + struct bfa_fcs_rport_s *rport; + + rport = bfa_fcs_port_get_rport_by_pwwn(port, rpwwn); + if (rport == NULL) { + /* + * TBD Error handling + */ + } + + return rport; +} + +struct bfa_fcs_rport_s * +bfa_fcs_rport_lookup_by_nwwn(struct bfa_fcs_port_s *port, wwn_t rnwwn) +{ + struct bfa_fcs_rport_s *rport; + + rport = bfa_fcs_port_get_rport_by_nwwn(port, rnwwn); + if (rport == NULL) { + /* + * TBD Error handling + */ + } + + return rport; +} + +/* + * This API is to set the Rport's speed. Should be used when RPSC is not + * supported by the rport. + */ +void +bfa_fcs_rport_set_speed(struct bfa_fcs_rport_s *rport, + enum bfa_pport_speed speed) +{ + rport->rpf.assigned_speed = speed; + + /* Set this speed in f/w only if the RPSC speed is not available */ + if (rport->rpf.rpsc_speed == BFA_PPORT_SPEED_UNKNOWN) + bfa_rport_speed(rport->bfa_rport, speed); +} + + diff --git a/drivers/scsi/bfa/rport_ftrs.c b/drivers/scsi/bfa/rport_ftrs.c new file mode 100644 index 000000000000..8a1f59d596c1 --- /dev/null +++ b/drivers/scsi/bfa/rport_ftrs.c @@ -0,0 +1,375 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * rport_ftrs.c Remote port features (RPF) implementation. + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include "fcbuild.h" +#include "fcs_rport.h" +#include "fcs_lport.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include "fcs.h" + +BFA_TRC_FILE(FCS, RPORT_FTRS); + +#define BFA_FCS_RPF_RETRIES (3) +#define BFA_FCS_RPF_RETRY_TIMEOUT (1000) /* 1 sec (In millisecs) */ + +static void bfa_fcs_rpf_send_rpsc2(void *rport_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_rpf_rpsc2_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_rpf_timeout(void *arg); + +/** + * fcs_rport_ftrs_sm FCS rport state machine events + */ + +enum rpf_event { + RPFSM_EVENT_RPORT_OFFLINE = 1, /* Rport offline */ + RPFSM_EVENT_RPORT_ONLINE = 2, /* Rport online */ + RPFSM_EVENT_FCXP_SENT = 3, /* Frame from has been sent */ + RPFSM_EVENT_TIMEOUT = 4, /* Rport SM timeout event */ + RPFSM_EVENT_RPSC_COMP = 5, + RPFSM_EVENT_RPSC_FAIL = 6, + RPFSM_EVENT_RPSC_ERROR = 7, +}; + +static void bfa_fcs_rpf_sm_uninit(struct bfa_fcs_rpf_s *rpf, + enum rpf_event event); +static void bfa_fcs_rpf_sm_rpsc_sending(struct bfa_fcs_rpf_s *rpf, + enum rpf_event event); +static void bfa_fcs_rpf_sm_rpsc(struct bfa_fcs_rpf_s *rpf, + enum rpf_event event); +static void bfa_fcs_rpf_sm_rpsc_retry(struct bfa_fcs_rpf_s *rpf, + enum rpf_event event); +static void bfa_fcs_rpf_sm_offline(struct bfa_fcs_rpf_s *rpf, + enum rpf_event event); +static void bfa_fcs_rpf_sm_online(struct bfa_fcs_rpf_s *rpf, + enum rpf_event event); + +static void +bfa_fcs_rpf_sm_uninit(struct bfa_fcs_rpf_s *rpf, enum rpf_event event) +{ + struct bfa_fcs_rport_s *rport = rpf->rport; + + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPFSM_EVENT_RPORT_ONLINE : + if (!BFA_FCS_PID_IS_WKA(rport->pid)) { + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_rpsc_sending); + rpf->rpsc_retries = 0; + bfa_fcs_rpf_send_rpsc2(rpf, NULL); + break; + }; + + case RPFSM_EVENT_RPORT_OFFLINE : + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_rpf_sm_rpsc_sending(struct bfa_fcs_rpf_s *rpf, enum rpf_event event) +{ + struct bfa_fcs_rport_s *rport = rpf->rport; + + bfa_trc(rport->fcs, event); + + switch (event) { + case RPFSM_EVENT_FCXP_SENT: + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_rpsc); + break; + + case RPFSM_EVENT_RPORT_OFFLINE : + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_offline); + bfa_fcxp_walloc_cancel(rport->fcs->bfa, &rpf->fcxp_wqe); + rpf->rpsc_retries = 0; + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_rpf_sm_rpsc(struct bfa_fcs_rpf_s *rpf, enum rpf_event event) +{ + struct bfa_fcs_rport_s *rport = rpf->rport; + + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPFSM_EVENT_RPSC_COMP: + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_online); + /* Update speed info in f/w via BFA */ + if (rpf->rpsc_speed != BFA_PPORT_SPEED_UNKNOWN) { + bfa_rport_speed(rport->bfa_rport, rpf->rpsc_speed); + } else if (rpf->assigned_speed != BFA_PPORT_SPEED_UNKNOWN) { + bfa_rport_speed(rport->bfa_rport, rpf->assigned_speed); + } + break; + + case RPFSM_EVENT_RPSC_FAIL: + /* RPSC not supported by rport */ + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_online); + break; + + case RPFSM_EVENT_RPSC_ERROR: + /* need to retry...delayed a bit. */ + if (rpf->rpsc_retries++ < BFA_FCS_RPF_RETRIES) { + bfa_timer_start(rport->fcs->bfa, &rpf->timer, + bfa_fcs_rpf_timeout, rpf, + BFA_FCS_RPF_RETRY_TIMEOUT); + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_rpsc_retry); + } else { + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_online); + } + break; + + case RPFSM_EVENT_RPORT_OFFLINE : + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_offline); + bfa_fcxp_discard(rpf->fcxp); + rpf->rpsc_retries = 0; + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_rpf_sm_rpsc_retry(struct bfa_fcs_rpf_s *rpf, enum rpf_event event) +{ + struct bfa_fcs_rport_s *rport = rpf->rport; + + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPFSM_EVENT_TIMEOUT : + /* re-send the RPSC */ + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_rpsc_sending); + bfa_fcs_rpf_send_rpsc2(rpf, NULL); + break; + + case RPFSM_EVENT_RPORT_OFFLINE : + bfa_timer_stop(&rpf->timer); + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_offline); + rpf->rpsc_retries = 0; + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_rpf_sm_online(struct bfa_fcs_rpf_s *rpf, enum rpf_event event) +{ + struct bfa_fcs_rport_s *rport = rpf->rport; + + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPFSM_EVENT_RPORT_OFFLINE : + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_offline); + rpf->rpsc_retries = 0; + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_rpf_sm_offline(struct bfa_fcs_rpf_s *rpf, enum rpf_event event) +{ + struct bfa_fcs_rport_s *rport = rpf->rport; + + bfa_trc(rport->fcs, rport->pwwn); + bfa_trc(rport->fcs, rport->pid); + bfa_trc(rport->fcs, event); + + switch (event) { + case RPFSM_EVENT_RPORT_ONLINE : + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_rpsc_sending); + bfa_fcs_rpf_send_rpsc2(rpf, NULL); + break; + + case RPFSM_EVENT_RPORT_OFFLINE : + break; + + default: + bfa_assert(0); + } +} +/** + * Called when Rport is created. + */ +void bfa_fcs_rpf_init(struct bfa_fcs_rport_s *rport) +{ + struct bfa_fcs_rpf_s *rpf = &rport->rpf; + + bfa_trc(rport->fcs, rport->pid); + rpf->rport = rport; + + bfa_sm_set_state(rpf, bfa_fcs_rpf_sm_uninit); +} + +/** + * Called when Rport becomes online + */ +void bfa_fcs_rpf_rport_online(struct bfa_fcs_rport_s *rport) +{ + bfa_trc(rport->fcs, rport->pid); + + if (__fcs_min_cfg(rport->port->fcs)) + return; + + if (bfa_fcs_fabric_is_switched(rport->port->fabric)) + bfa_sm_send_event(&rport->rpf, RPFSM_EVENT_RPORT_ONLINE); +} + +/** + * Called when Rport becomes offline + */ +void bfa_fcs_rpf_rport_offline(struct bfa_fcs_rport_s *rport) +{ + bfa_trc(rport->fcs, rport->pid); + + if (__fcs_min_cfg(rport->port->fcs)) + return; + + bfa_sm_send_event(&rport->rpf, RPFSM_EVENT_RPORT_OFFLINE); +} + +static void +bfa_fcs_rpf_timeout(void *arg) +{ + struct bfa_fcs_rpf_s *rpf = (struct bfa_fcs_rpf_s *) arg; + struct bfa_fcs_rport_s *rport = rpf->rport; + + bfa_trc(rport->fcs, rport->pid); + bfa_sm_send_event(rpf, RPFSM_EVENT_TIMEOUT); +} + +static void +bfa_fcs_rpf_send_rpsc2(void *rpf_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_rpf_s *rpf = (struct bfa_fcs_rpf_s *)rpf_cbarg; + struct bfa_fcs_rport_s *rport = rpf->rport; + struct bfa_fcs_port_s *port = rport->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(rport->fcs, rport->pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &rpf->fcxp_wqe, + bfa_fcs_rpf_send_rpsc2, rpf); + return; + } + rpf->fcxp = fcxp; + + len = fc_rpsc2_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rport->pid, + bfa_fcs_port_get_fcid(port), &rport->pid, 1); + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_rpf_rpsc2_response, + rpf, FC_MAX_PDUSZ, FC_RA_TOV); + rport->stats.rpsc_sent++; + bfa_sm_send_event(rpf, RPFSM_EVENT_FCXP_SENT); + +} + +static void +bfa_fcs_rpf_rpsc2_response(void *fcsarg, struct bfa_fcxp_s *fcxp, void *cbarg, + bfa_status_t req_status, u32 rsp_len, + u32 resid_len, struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_rpf_s *rpf = (struct bfa_fcs_rpf_s *) cbarg; + struct bfa_fcs_rport_s *rport = rpf->rport; + struct fc_ls_rjt_s *ls_rjt; + struct fc_rpsc2_acc_s *rpsc2_acc; + u16 num_ents; + + bfa_trc(rport->fcs, req_status); + + if (req_status != BFA_STATUS_OK) { + bfa_trc(rport->fcs, req_status); + if (req_status == BFA_STATUS_ETIMER) + rport->stats.rpsc_failed++; + bfa_sm_send_event(rpf, RPFSM_EVENT_RPSC_ERROR); + return; + } + + rpsc2_acc = (struct fc_rpsc2_acc_s *) BFA_FCXP_RSP_PLD(fcxp); + if (rpsc2_acc->els_cmd == FC_ELS_ACC) { + rport->stats.rpsc_accs++; + num_ents = bfa_os_ntohs(rpsc2_acc->num_pids); + bfa_trc(rport->fcs, num_ents); + if (num_ents > 0) { + bfa_assert(rpsc2_acc->port_info[0].pid != rport->pid); + bfa_trc(rport->fcs, + bfa_os_ntohs(rpsc2_acc->port_info[0].pid)); + bfa_trc(rport->fcs, + bfa_os_ntohs(rpsc2_acc->port_info[0].speed)); + bfa_trc(rport->fcs, + bfa_os_ntohs(rpsc2_acc->port_info[0].index)); + bfa_trc(rport->fcs, + rpsc2_acc->port_info[0].type); + + if (rpsc2_acc->port_info[0].speed == 0) { + bfa_sm_send_event(rpf, RPFSM_EVENT_RPSC_ERROR); + return; + } + + rpf->rpsc_speed = fc_rpsc_operspeed_to_bfa_speed( + bfa_os_ntohs(rpsc2_acc->port_info[0].speed)); + + bfa_sm_send_event(rpf, RPFSM_EVENT_RPSC_COMP); + } + } else { + ls_rjt = (struct fc_ls_rjt_s *) BFA_FCXP_RSP_PLD(fcxp); + bfa_trc(rport->fcs, ls_rjt->reason_code); + bfa_trc(rport->fcs, ls_rjt->reason_code_expl); + rport->stats.rpsc_rejects++; + if (ls_rjt->reason_code == FC_LS_RJT_RSN_CMD_NOT_SUPP) { + bfa_sm_send_event(rpf, RPFSM_EVENT_RPSC_FAIL); + } else { + bfa_sm_send_event(rpf, RPFSM_EVENT_RPSC_ERROR); + } + } +} diff --git a/drivers/scsi/bfa/scn.c b/drivers/scsi/bfa/scn.c new file mode 100644 index 000000000000..bd4771ff62c8 --- /dev/null +++ b/drivers/scsi/bfa/scn.c @@ -0,0 +1,482 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include "fcs_lport.h" +#include "fcs_rport.h" +#include "fcs_ms.h" +#include "fcs_trcmod.h" +#include "fcs_fcxp.h" +#include "fcs.h" +#include "lport_priv.h" + +BFA_TRC_FILE(FCS, SCN); + +#define FC_QOS_RSCN_EVENT 0x0c +#define FC_FABRIC_NAME_RSCN_EVENT 0x0d + +/* + * forward declarations + */ +static void bfa_fcs_port_scn_send_scr(void *scn_cbarg, + struct bfa_fcxp_s *fcxp_alloced); +static void bfa_fcs_port_scn_scr_response(void *fcsarg, + struct bfa_fcxp_s *fcxp, + void *cbarg, + bfa_status_t req_status, + u32 rsp_len, + u32 resid_len, + struct fchs_s *rsp_fchs); +static void bfa_fcs_port_scn_send_ls_acc(struct bfa_fcs_port_s *port, + struct fchs_s *rx_fchs); +static void bfa_fcs_port_scn_timeout(void *arg); + +/** + * fcs_scm_sm FCS SCN state machine + */ + +/** + * VPort SCN State Machine events + */ +enum port_scn_event { + SCNSM_EVENT_PORT_ONLINE = 1, + SCNSM_EVENT_PORT_OFFLINE = 2, + SCNSM_EVENT_RSP_OK = 3, + SCNSM_EVENT_RSP_ERROR = 4, + SCNSM_EVENT_TIMEOUT = 5, + SCNSM_EVENT_SCR_SENT = 6, +}; + +static void bfa_fcs_port_scn_sm_offline(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event); +static void bfa_fcs_port_scn_sm_sending_scr(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event); +static void bfa_fcs_port_scn_sm_scr(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event); +static void bfa_fcs_port_scn_sm_scr_retry(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event); +static void bfa_fcs_port_scn_sm_online(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event); + +/** + * Starting state - awaiting link up. + */ +static void +bfa_fcs_port_scn_sm_offline(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event) +{ + switch (event) { + case SCNSM_EVENT_PORT_ONLINE: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_sending_scr); + bfa_fcs_port_scn_send_scr(scn, NULL); + break; + + case SCNSM_EVENT_PORT_OFFLINE: + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_scn_sm_sending_scr(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event) +{ + switch (event) { + case SCNSM_EVENT_SCR_SENT: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_scr); + break; + + case SCNSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_offline); + bfa_fcxp_walloc_cancel(scn->port->fcs->bfa, &scn->fcxp_wqe); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_scn_sm_scr(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event) +{ + struct bfa_fcs_port_s *port = scn->port; + + switch (event) { + case SCNSM_EVENT_RSP_OK: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_online); + break; + + case SCNSM_EVENT_RSP_ERROR: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_scr_retry); + bfa_timer_start(port->fcs->bfa, &scn->timer, + bfa_fcs_port_scn_timeout, scn, + BFA_FCS_RETRY_TIMEOUT); + break; + + case SCNSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_offline); + bfa_fcxp_discard(scn->fcxp); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_scn_sm_scr_retry(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event) +{ + switch (event) { + case SCNSM_EVENT_TIMEOUT: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_sending_scr); + bfa_fcs_port_scn_send_scr(scn, NULL); + break; + + case SCNSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_offline); + bfa_timer_stop(&scn->timer); + break; + + default: + bfa_assert(0); + } +} + +static void +bfa_fcs_port_scn_sm_online(struct bfa_fcs_port_scn_s *scn, + enum port_scn_event event) +{ + switch (event) { + case SCNSM_EVENT_PORT_OFFLINE: + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_offline); + break; + + default: + bfa_assert(0); + } +} + + + +/** + * fcs_scn_private FCS SCN private functions + */ + +/** + * This routine will be called to send a SCR command. + */ +static void +bfa_fcs_port_scn_send_scr(void *scn_cbarg, struct bfa_fcxp_s *fcxp_alloced) +{ + struct bfa_fcs_port_scn_s *scn = scn_cbarg; + struct bfa_fcs_port_s *port = scn->port; + struct fchs_s fchs; + int len; + struct bfa_fcxp_s *fcxp; + + bfa_trc(port->fcs, port->pid); + bfa_trc(port->fcs, port->port_cfg.pwwn); + + fcxp = fcxp_alloced ? fcxp_alloced : bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) { + bfa_fcxp_alloc_wait(port->fcs->bfa, &scn->fcxp_wqe, + bfa_fcs_port_scn_send_scr, scn); + return; + } + scn->fcxp = fcxp; + + /* + * Handle VU registrations for Base port only + */ + if ((!port->vport) && bfa_ioc_get_fcmode(&port->fcs->bfa->ioc)) { + len = fc_scr_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), + bfa_lps_is_brcd_fabric(port->fabric->lps), + port->pid, 0); + } else { + len = fc_scr_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), BFA_FALSE, + port->pid, 0); + } + + bfa_fcxp_send(fcxp, NULL, port->fabric->vf_id, port->lp_tag, BFA_FALSE, + FC_CLASS_3, len, &fchs, bfa_fcs_port_scn_scr_response, + (void *)scn, FC_MAX_PDUSZ, FC_RA_TOV); + + bfa_sm_send_event(scn, SCNSM_EVENT_SCR_SENT); +} + +static void +bfa_fcs_port_scn_scr_response(void *fcsarg, struct bfa_fcxp_s *fcxp, + void *cbarg, bfa_status_t req_status, + u32 rsp_len, u32 resid_len, + struct fchs_s *rsp_fchs) +{ + struct bfa_fcs_port_scn_s *scn = (struct bfa_fcs_port_scn_s *)cbarg; + struct bfa_fcs_port_s *port = scn->port; + struct fc_els_cmd_s *els_cmd; + struct fc_ls_rjt_s *ls_rjt; + + bfa_trc(port->fcs, port->port_cfg.pwwn); + + /* + * Sanity Checks + */ + if (req_status != BFA_STATUS_OK) { + bfa_trc(port->fcs, req_status); + bfa_sm_send_event(scn, SCNSM_EVENT_RSP_ERROR); + return; + } + + els_cmd = (struct fc_els_cmd_s *) BFA_FCXP_RSP_PLD(fcxp); + + switch (els_cmd->els_code) { + + case FC_ELS_ACC: + bfa_sm_send_event(scn, SCNSM_EVENT_RSP_OK); + break; + + case FC_ELS_LS_RJT: + + ls_rjt = (struct fc_ls_rjt_s *) BFA_FCXP_RSP_PLD(fcxp); + + bfa_trc(port->fcs, ls_rjt->reason_code); + bfa_trc(port->fcs, ls_rjt->reason_code_expl); + + bfa_sm_send_event(scn, SCNSM_EVENT_RSP_ERROR); + break; + + default: + bfa_sm_send_event(scn, SCNSM_EVENT_RSP_ERROR); + } +} + +/* + * Send a LS Accept + */ +static void +bfa_fcs_port_scn_send_ls_acc(struct bfa_fcs_port_s *port, + struct fchs_s *rx_fchs) +{ + struct fchs_s fchs; + struct bfa_fcxp_s *fcxp; + struct bfa_rport_s *bfa_rport = NULL; + int len; + + bfa_trc(port->fcs, rx_fchs->s_id); + + fcxp = bfa_fcs_fcxp_alloc(port->fcs); + if (!fcxp) + return; + + len = fc_ls_acc_build(&fchs, bfa_fcxp_get_reqbuf(fcxp), rx_fchs->s_id, + bfa_fcs_port_get_fcid(port), rx_fchs->ox_id); + + bfa_fcxp_send(fcxp, bfa_rport, port->fabric->vf_id, port->lp_tag, + BFA_FALSE, FC_CLASS_3, len, &fchs, NULL, NULL, + FC_MAX_PDUSZ, 0); +} + +/** + * This routine will be called by bfa_timer on timer timeouts. + * + * param[in] vport - pointer to bfa_fcs_port_t. + * param[out] vport_status - pointer to return vport status in + * + * return + * void + * +* Special Considerations: + * + * note + */ +static void +bfa_fcs_port_scn_timeout(void *arg) +{ + struct bfa_fcs_port_scn_s *scn = (struct bfa_fcs_port_scn_s *)arg; + + bfa_sm_send_event(scn, SCNSM_EVENT_TIMEOUT); +} + + + +/** + * fcs_scn_public FCS state change notification public interfaces + */ + +/* + * Functions called by port/fab + */ +void +bfa_fcs_port_scn_init(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_scn_s *scn = BFA_FCS_GET_SCN_FROM_PORT(port); + + scn->port = port; + bfa_sm_set_state(scn, bfa_fcs_port_scn_sm_offline); +} + +void +bfa_fcs_port_scn_offline(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_scn_s *scn = BFA_FCS_GET_SCN_FROM_PORT(port); + + scn->port = port; + bfa_sm_send_event(scn, SCNSM_EVENT_PORT_OFFLINE); +} + +void +bfa_fcs_port_scn_online(struct bfa_fcs_port_s *port) +{ + struct bfa_fcs_port_scn_s *scn = BFA_FCS_GET_SCN_FROM_PORT(port); + + scn->port = port; + bfa_sm_send_event(scn, SCNSM_EVENT_PORT_ONLINE); +} + +static void +bfa_fcs_port_scn_portid_rscn(struct bfa_fcs_port_s *port, u32 rpid) +{ + struct bfa_fcs_rport_s *rport; + + bfa_trc(port->fcs, rpid); + + /** + * If this is an unknown device, then it just came online. + * Otherwise let rport handle the RSCN event. + */ + rport = bfa_fcs_port_get_rport_by_pid(port, rpid); + if (rport == NULL) { + /* + * If min cfg mode is enabled, we donot need to + * discover any new rports. + */ + if (!__fcs_min_cfg(port->fcs)) + rport = bfa_fcs_rport_create(port, rpid); + } else { + bfa_fcs_rport_scn(rport); + } +} + +/** + * rscn format based PID comparison + */ +#define __fc_pid_match(__c0, __c1, __fmt) \ + (((__fmt) == FC_RSCN_FORMAT_FABRIC) || \ + (((__fmt) == FC_RSCN_FORMAT_DOMAIN) && \ + ((__c0)[0] == (__c1)[0])) || \ + (((__fmt) == FC_RSCN_FORMAT_AREA) && \ + ((__c0)[0] == (__c1)[0]) && \ + ((__c0)[1] == (__c1)[1]))) + +static void +bfa_fcs_port_scn_multiport_rscn(struct bfa_fcs_port_s *port, + enum fc_rscn_format format, u32 rscn_pid) +{ + struct bfa_fcs_rport_s *rport; + struct list_head *qe, *qe_next; + u8 *c0, *c1; + + bfa_trc(port->fcs, format); + bfa_trc(port->fcs, rscn_pid); + + c0 = (u8 *) &rscn_pid; + + list_for_each_safe(qe, qe_next, &port->rport_q) { + rport = (struct bfa_fcs_rport_s *)qe; + c1 = (u8 *) &rport->pid; + if (__fc_pid_match(c0, c1, format)) + bfa_fcs_rport_scn(rport); + } +} + +void +bfa_fcs_port_scn_process_rscn(struct bfa_fcs_port_s *port, struct fchs_s *fchs, + u32 len) +{ + struct fc_rscn_pl_s *rscn = (struct fc_rscn_pl_s *) (fchs + 1); + int num_entries; + u32 rscn_pid; + bfa_boolean_t nsquery = BFA_FALSE; + int i = 0; + + num_entries = + (bfa_os_ntohs(rscn->payldlen) - + sizeof(u32)) / sizeof(rscn->event[0]); + + bfa_trc(port->fcs, num_entries); + + port->stats.num_rscn++; + + bfa_fcs_port_scn_send_ls_acc(port, fchs); + + for (i = 0; i < num_entries; i++) { + rscn_pid = rscn->event[i].portid; + + bfa_trc(port->fcs, rscn->event[i].format); + bfa_trc(port->fcs, rscn_pid); + + switch (rscn->event[i].format) { + case FC_RSCN_FORMAT_PORTID: + if (rscn->event[i].qualifier == FC_QOS_RSCN_EVENT) { + /* + * Ignore this event. f/w would have processed + * it + */ + bfa_trc(port->fcs, rscn_pid); + } else { + port->stats.num_portid_rscn++; + bfa_fcs_port_scn_portid_rscn(port, rscn_pid); + } + break; + + case FC_RSCN_FORMAT_FABRIC: + if (rscn->event[i].qualifier == + FC_FABRIC_NAME_RSCN_EVENT) { + bfa_fcs_port_ms_fabric_rscn(port); + break; + } + /* + * !!!!!!!!! Fall Through !!!!!!!!!!!!! + */ + + case FC_RSCN_FORMAT_AREA: + case FC_RSCN_FORMAT_DOMAIN: + nsquery = BFA_TRUE; + bfa_fcs_port_scn_multiport_rscn(port, + rscn->event[i].format, + rscn_pid); + break; + + default: + bfa_assert(0); + nsquery = BFA_TRUE; + } + } + + /** + * If any of area, domain or fabric RSCN is received, do a fresh discovery + * to find new devices. + */ + if (nsquery) + bfa_fcs_port_ns_query(port); +} + + diff --git a/drivers/scsi/bfa/vfapi.c b/drivers/scsi/bfa/vfapi.c new file mode 100644 index 000000000000..31d81fe2fc48 --- /dev/null +++ b/drivers/scsi/bfa/vfapi.c @@ -0,0 +1,292 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * vfapi.c Fabric module implementation. + */ + +#include "fcs_fabric.h" +#include "fcs_trcmod.h" + +BFA_TRC_FILE(FCS, VFAPI); + +/** + * fcs_vf_api virtual fabrics API + */ + +/** + * Enable VF mode. + * + * @param[in] fcs fcs module instance + * @param[in] vf_id default vf_id of port, FC_VF_ID_NULL + * to use standard default vf_id of 1. + * + * @retval BFA_STATUS_OK vf mode is enabled + * @retval BFA_STATUS_BUSY Port is active. Port must be disabled + * before VF mode can be enabled. + */ +bfa_status_t +bfa_fcs_vf_mode_enable(struct bfa_fcs_s *fcs, u16 vf_id) +{ + return BFA_STATUS_OK; +} + +/** + * Disable VF mode. + * + * @param[in] fcs fcs module instance + * + * @retval BFA_STATUS_OK vf mode is disabled + * @retval BFA_STATUS_BUSY VFs are present and being used. All + * VFs must be deleted before disabling + * VF mode. + */ +bfa_status_t +bfa_fcs_vf_mode_disable(struct bfa_fcs_s *fcs) +{ + return BFA_STATUS_OK; +} + +/** + * Create a new VF instance. + * + * A new VF is created using the given VF configuration. A VF is identified + * by VF id. No duplicate VF creation is allowed with the same VF id. Once + * a VF is created, VF is automatically started after link initialization + * and EVFP exchange is completed. + * + * param[in] vf - FCS vf data structure. Memory is + * allocated by caller (driver) + * param[in] fcs - FCS module + * param[in] vf_cfg - VF configuration + * param[in] vf_drv - Opaque handle back to the driver's + * virtual vf structure + * + * retval BFA_STATUS_OK VF creation is successful + * retval BFA_STATUS_FAILED VF creation failed + * retval BFA_STATUS_EEXIST A VF exists with the given vf_id + */ +bfa_status_t +bfa_fcs_vf_create(bfa_fcs_vf_t *vf, struct bfa_fcs_s *fcs, u16 vf_id, + struct bfa_port_cfg_s *port_cfg, struct bfad_vf_s *vf_drv) +{ + bfa_trc(fcs, vf_id); + return BFA_STATUS_OK; +} + +/** + * Use this function to delete a BFA VF object. VF object should + * be stopped before this function call. + * + * param[in] vf - pointer to bfa_vf_t. + * + * retval BFA_STATUS_OK On vf deletion success + * retval BFA_STATUS_BUSY VF is not in a stopped state + * retval BFA_STATUS_INPROGRESS VF deletion in in progress + */ +bfa_status_t +bfa_fcs_vf_delete(bfa_fcs_vf_t *vf) +{ + bfa_trc(vf->fcs, vf->vf_id); + return BFA_STATUS_OK; +} + +/** + * Start participation in VF. This triggers login to the virtual fabric. + * + * param[in] vf - pointer to bfa_vf_t. + * + * return None + */ +void +bfa_fcs_vf_start(bfa_fcs_vf_t *vf) +{ + bfa_trc(vf->fcs, vf->vf_id); +} + +/** + * Logout with the virtual fabric. + * + * param[in] vf - pointer to bfa_vf_t. + * + * retval BFA_STATUS_OK On success. + * retval BFA_STATUS_INPROGRESS VF is being stopped. + */ +bfa_status_t +bfa_fcs_vf_stop(bfa_fcs_vf_t *vf) +{ + bfa_trc(vf->fcs, vf->vf_id); + return BFA_STATUS_OK; +} + +/** + * Returns attributes of the given VF. + * + * param[in] vf pointer to bfa_vf_t. + * param[out] vf_attr vf attributes returned + * + * return None + */ +void +bfa_fcs_vf_get_attr(bfa_fcs_vf_t *vf, struct bfa_vf_attr_s *vf_attr) +{ + bfa_trc(vf->fcs, vf->vf_id); +} + +/** + * Return statistics associated with the given vf. + * + * param[in] vf pointer to bfa_vf_t. + * param[out] vf_stats vf statistics returned + * + * @return None + */ +void +bfa_fcs_vf_get_stats(bfa_fcs_vf_t *vf, struct bfa_vf_stats_s *vf_stats) +{ + bfa_os_memcpy(vf_stats, &vf->stats, sizeof(struct bfa_vf_stats_s)); + return; +} + +void +/** + * clear statistics associated with the given vf. + * + * param[in] vf pointer to bfa_vf_t. + * + * @return None + */ +bfa_fcs_vf_clear_stats(bfa_fcs_vf_t *vf) +{ + bfa_os_memset(&vf->stats, 0, sizeof(struct bfa_vf_stats_s)); + return; +} + +/** + * Returns FCS vf structure for a given vf_id. + * + * param[in] vf_id - VF_ID + * + * return + * If lookup succeeds, retuns fcs vf object, otherwise returns NULL + */ +bfa_fcs_vf_t * +bfa_fcs_vf_lookup(struct bfa_fcs_s *fcs, u16 vf_id) +{ + bfa_trc(fcs, vf_id); + if (vf_id == FC_VF_ID_NULL) + return (&fcs->fabric); + + /** + * @todo vf support + */ + + return NULL; +} + +/** + * Returns driver VF structure for a given FCS vf. + * + * param[in] vf - pointer to bfa_vf_t + * + * return Driver VF structure + */ +struct bfad_vf_s * +bfa_fcs_vf_get_drv_vf(bfa_fcs_vf_t *vf) +{ + bfa_assert(vf); + bfa_trc(vf->fcs, vf->vf_id); + return vf->vf_drv; +} + +/** + * Return the list of VFs configured. + * + * param[in] fcs fcs module instance + * param[out] vf_ids returned list of vf_ids + * param[in,out] nvfs in:size of vf_ids array, + * out:total elements present, + * actual elements returned is limited by the size + * + * return Driver VF structure + */ +void +bfa_fcs_vf_list(struct bfa_fcs_s *fcs, u16 *vf_ids, int *nvfs) +{ + bfa_trc(fcs, *nvfs); +} + +/** + * Return the list of all VFs visible from fabric. + * + * param[in] fcs fcs module instance + * param[out] vf_ids returned list of vf_ids + * param[in,out] nvfs in:size of vf_ids array, + * out:total elements present, + * actual elements returned is limited by the size + * + * return Driver VF structure + */ +void +bfa_fcs_vf_list_all(struct bfa_fcs_s *fcs, u16 *vf_ids, int *nvfs) +{ + bfa_trc(fcs, *nvfs); +} + +/** + * Return the list of local logical ports present in the given VF. + * + * param[in] vf vf for which logical ports are returned + * param[out] lpwwn returned logical port wwn list + * param[in,out] nlports in:size of lpwwn list; + * out:total elements present, + * actual elements returned is limited by the size + * + */ +void +bfa_fcs_vf_get_ports(bfa_fcs_vf_t *vf, wwn_t lpwwn[], int *nlports) +{ + struct list_head *qe; + struct bfa_fcs_vport_s *vport; + int i; + struct bfa_fcs_s *fcs; + + if (vf == NULL || lpwwn == NULL || *nlports == 0) + return; + + fcs = vf->fcs; + + bfa_trc(fcs, vf->vf_id); + bfa_trc(fcs, (u32) *nlports); + + i = 0; + lpwwn[i++] = vf->bport.port_cfg.pwwn; + + list_for_each(qe, &vf->vport_q) { + if (i >= *nlports) + break; + + vport = (struct bfa_fcs_vport_s *) qe; + lpwwn[i++] = vport->lport.port_cfg.pwwn; + } + + bfa_trc(fcs, i); + *nlports = i; + return; +} + + diff --git a/drivers/scsi/bfa/vport.c b/drivers/scsi/bfa/vport.c new file mode 100644 index 000000000000..c10af06c5714 --- /dev/null +++ b/drivers/scsi/bfa/vport.c @@ -0,0 +1,891 @@ +/* + * Copyright (c) 2005-2009 Brocade Communications Systems, Inc. + * All rights reserved + * www.brocade.com + * + * Linux driver for Brocade Fibre Channel Host Bus Adapter. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License (GPL) Version 2 as + * published by the Free Software Foundation + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + */ + +/** + * bfa_fcs_vport.c FCS virtual port state machine + */ + +#include <bfa.h> +#include <bfa_svc.h> +#include <fcbuild.h> +#include "fcs_fabric.h" +#include "fcs_lport.h" +#include "fcs_vport.h" +#include "fcs_trcmod.h" +#include "fcs.h" +#include <aen/bfa_aen_lport.h> + +BFA_TRC_FILE(FCS, VPORT); + +#define __vport_fcs(__vp) (__vp)->lport.fcs +#define __vport_pwwn(__vp) (__vp)->lport.port_cfg.pwwn +#define __vport_nwwn(__vp) (__vp)->lport.port_cfg.nwwn +#define __vport_bfa(__vp) (__vp)->lport.fcs->bfa +#define __vport_fcid(__vp) (__vp)->lport.pid +#define __vport_fabric(__vp) (__vp)->lport.fabric +#define __vport_vfid(__vp) (__vp)->lport.fabric->vf_id + +#define BFA_FCS_VPORT_MAX_RETRIES 5 +/* + * Forward declarations + */ +static void bfa_fcs_vport_do_fdisc(struct bfa_fcs_vport_s *vport); +static void bfa_fcs_vport_timeout(void *vport_arg); +static void bfa_fcs_vport_do_logo(struct bfa_fcs_vport_s *vport); +static void bfa_fcs_vport_free(struct bfa_fcs_vport_s *vport); + +/** + * fcs_vport_sm FCS virtual port state machine + */ + +/** + * VPort State Machine events + */ +enum bfa_fcs_vport_event { + BFA_FCS_VPORT_SM_CREATE = 1, /* vport create event */ + BFA_FCS_VPORT_SM_DELETE = 2, /* vport delete event */ + BFA_FCS_VPORT_SM_START = 3, /* vport start request */ + BFA_FCS_VPORT_SM_STOP = 4, /* stop: unsupported */ + BFA_FCS_VPORT_SM_ONLINE = 5, /* fabric online */ + BFA_FCS_VPORT_SM_OFFLINE = 6, /* fabric offline event */ + BFA_FCS_VPORT_SM_FRMSENT = 7, /* fdisc/logo sent events */ + BFA_FCS_VPORT_SM_RSP_OK = 8, /* good response */ + BFA_FCS_VPORT_SM_RSP_ERROR = 9, /* error/bad response */ + BFA_FCS_VPORT_SM_TIMEOUT = 10, /* delay timer event */ + BFA_FCS_VPORT_SM_DELCOMP = 11, /* lport delete completion */ + BFA_FCS_VPORT_SM_RSP_DUP_WWN = 12, /* Dup wnn error */ + BFA_FCS_VPORT_SM_RSP_FAILED = 13, /* non-retryable failure */ +}; + +static void bfa_fcs_vport_sm_uninit(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_created(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_offline(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_fdisc(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_fdisc_retry(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_online(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_deleting(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_cleanup(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_logo(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); +static void bfa_fcs_vport_sm_error(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event); + +static struct bfa_sm_table_s vport_sm_table[] = { + {BFA_SM(bfa_fcs_vport_sm_uninit), BFA_FCS_VPORT_UNINIT}, + {BFA_SM(bfa_fcs_vport_sm_created), BFA_FCS_VPORT_CREATED}, + {BFA_SM(bfa_fcs_vport_sm_offline), BFA_FCS_VPORT_OFFLINE}, + {BFA_SM(bfa_fcs_vport_sm_fdisc), BFA_FCS_VPORT_FDISC}, + {BFA_SM(bfa_fcs_vport_sm_fdisc_retry), BFA_FCS_VPORT_FDISC_RETRY}, + {BFA_SM(bfa_fcs_vport_sm_online), BFA_FCS_VPORT_ONLINE}, + {BFA_SM(bfa_fcs_vport_sm_deleting), BFA_FCS_VPORT_DELETING}, + {BFA_SM(bfa_fcs_vport_sm_cleanup), BFA_FCS_VPORT_CLEANUP}, + {BFA_SM(bfa_fcs_vport_sm_logo), BFA_FCS_VPORT_LOGO}, + {BFA_SM(bfa_fcs_vport_sm_error), BFA_FCS_VPORT_ERROR} +}; + +/** + * Beginning state. + */ +static void +bfa_fcs_vport_sm_uninit(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_CREATE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_created); + bfa_fcs_fabric_addvport(__vport_fabric(vport), vport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Created state - a start event is required to start up the state machine. + */ +static void +bfa_fcs_vport_sm_created(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_START: + if (bfa_fcs_fabric_is_online(__vport_fabric(vport)) + && bfa_fcs_fabric_npiv_capable(__vport_fabric(vport))) { + bfa_sm_set_state(vport, bfa_fcs_vport_sm_fdisc); + bfa_fcs_vport_do_fdisc(vport); + } else { + /** + * Fabric is offline or not NPIV capable, stay in + * offline state. + */ + vport->vport_stats.fab_no_npiv++; + bfa_sm_set_state(vport, bfa_fcs_vport_sm_offline); + } + break; + + case BFA_FCS_VPORT_SM_DELETE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_cleanup); + bfa_fcs_port_delete(&vport->lport); + break; + + case BFA_FCS_VPORT_SM_ONLINE: + case BFA_FCS_VPORT_SM_OFFLINE: + /** + * Ignore ONLINE/OFFLINE events from fabric till vport is started. + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * Offline state - awaiting ONLINE event from fabric SM. + */ +static void +bfa_fcs_vport_sm_offline(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_DELETE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_cleanup); + bfa_fcs_port_delete(&vport->lport); + break; + + case BFA_FCS_VPORT_SM_ONLINE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_fdisc); + vport->fdisc_retries = 0; + bfa_fcs_vport_do_fdisc(vport); + break; + + case BFA_FCS_VPORT_SM_OFFLINE: + /* + * This can happen if the vport couldn't be initialzied due + * the fact that the npiv was not enabled on the switch. In + * that case we will put the vport in offline state. However, + * the link can go down and cause the this event to be sent when + * we are already offline. Ignore it. + */ + break; + + default: + bfa_assert(0); + } +} + +/** + * FDISC is sent and awaiting reply from fabric. + */ +static void +bfa_fcs_vport_sm_fdisc(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_DELETE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_logo); + bfa_lps_discard(vport->lps); + bfa_fcs_vport_do_logo(vport); + break; + + case BFA_FCS_VPORT_SM_OFFLINE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_offline); + bfa_lps_discard(vport->lps); + break; + + case BFA_FCS_VPORT_SM_RSP_OK: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_online); + bfa_fcs_port_online(&vport->lport); + break; + + case BFA_FCS_VPORT_SM_RSP_ERROR: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_fdisc_retry); + bfa_timer_start(__vport_bfa(vport), &vport->timer, + bfa_fcs_vport_timeout, vport, + BFA_FCS_RETRY_TIMEOUT); + break; + + case BFA_FCS_VPORT_SM_RSP_FAILED: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_offline); + break; + + case BFA_FCS_VPORT_SM_RSP_DUP_WWN: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_error); + break; + + default: + bfa_assert(0); + } +} + +/** + * FDISC attempt failed - a timer is active to retry FDISC. + */ +static void +bfa_fcs_vport_sm_fdisc_retry(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_DELETE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_cleanup); + bfa_timer_stop(&vport->timer); + bfa_fcs_port_delete(&vport->lport); + break; + + case BFA_FCS_VPORT_SM_OFFLINE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_offline); + bfa_timer_stop(&vport->timer); + break; + + case BFA_FCS_VPORT_SM_TIMEOUT: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_fdisc); + vport->vport_stats.fdisc_retries++; + vport->fdisc_retries++; + bfa_fcs_vport_do_fdisc(vport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Vport is online (FDISC is complete). + */ +static void +bfa_fcs_vport_sm_online(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_DELETE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_deleting); + bfa_fcs_port_delete(&vport->lport); + break; + + case BFA_FCS_VPORT_SM_OFFLINE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_offline); + bfa_lps_discard(vport->lps); + bfa_fcs_port_offline(&vport->lport); + break; + + default: + bfa_assert(0); + } +} + +/** + * Vport is being deleted - awaiting lport delete completion to send + * LOGO to fabric. + */ +static void +bfa_fcs_vport_sm_deleting(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_DELETE: + break; + + case BFA_FCS_VPORT_SM_DELCOMP: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_logo); + bfa_fcs_vport_do_logo(vport); + break; + + case BFA_FCS_VPORT_SM_OFFLINE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_cleanup); + break; + + default: + bfa_assert(0); + } +} + +/** + * Error State. + * This state will be set when the Vport Creation fails due to errors like + * Dup WWN. In this state only operation allowed is a Vport Delete. + */ +static void +bfa_fcs_vport_sm_error(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_DELETE: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_uninit); + bfa_fcs_vport_free(vport); + break; + + default: + bfa_trc(__vport_fcs(vport), event); + } +} + +/** + * Lport cleanup is in progress since vport is being deleted. Fabric is + * offline, so no LOGO is needed to complete vport deletion. + */ +static void +bfa_fcs_vport_sm_cleanup(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_DELCOMP: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_uninit); + bfa_fcs_vport_free(vport); + break; + + case BFA_FCS_VPORT_SM_DELETE: + break; + + default: + bfa_assert(0); + } +} + +/** + * LOGO is sent to fabric. Vport delete is in progress. Lport delete cleanup + * is done. + */ +static void +bfa_fcs_vport_sm_logo(struct bfa_fcs_vport_s *vport, + enum bfa_fcs_vport_event event) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), event); + + switch (event) { + case BFA_FCS_VPORT_SM_OFFLINE: + bfa_lps_discard(vport->lps); + /* + * !!! fall through !!! + */ + + case BFA_FCS_VPORT_SM_RSP_OK: + case BFA_FCS_VPORT_SM_RSP_ERROR: + bfa_sm_set_state(vport, bfa_fcs_vport_sm_uninit); + bfa_fcs_vport_free(vport); + break; + + case BFA_FCS_VPORT_SM_DELETE: + break; + + default: + bfa_assert(0); + } +} + + + +/** + * fcs_vport_private FCS virtual port private functions + */ + +/** + * Send AEN notification + */ +static void +bfa_fcs_vport_aen_post(bfa_fcs_lport_t *port, enum bfa_lport_aen_event event) +{ + union bfa_aen_data_u aen_data; + struct bfa_log_mod_s *logmod = port->fcs->logm; + enum bfa_port_role role = port->port_cfg.roles; + wwn_t lpwwn = bfa_fcs_port_get_pwwn(port); + char lpwwn_ptr[BFA_STRING_32]; + char *role_str[BFA_PORT_ROLE_FCP_MAX / 2 + 1] = + { "Initiator", "Target", "IPFC" }; + + wwn2str(lpwwn_ptr, lpwwn); + + bfa_assert(role <= BFA_PORT_ROLE_FCP_MAX); + + switch (event) { + case BFA_LPORT_AEN_NPIV_DUP_WWN: + bfa_log(logmod, BFA_AEN_LPORT_NPIV_DUP_WWN, lpwwn_ptr, + role_str[role / 2]); + break; + case BFA_LPORT_AEN_NPIV_FABRIC_MAX: + bfa_log(logmod, BFA_AEN_LPORT_NPIV_FABRIC_MAX, lpwwn_ptr, + role_str[role / 2]); + break; + case BFA_LPORT_AEN_NPIV_UNKNOWN: + bfa_log(logmod, BFA_AEN_LPORT_NPIV_UNKNOWN, lpwwn_ptr, + role_str[role / 2]); + break; + default: + break; + } + + aen_data.lport.vf_id = port->fabric->vf_id; + aen_data.lport.roles = role; + aen_data.lport.ppwwn = + bfa_fcs_port_get_pwwn(bfa_fcs_get_base_port(port->fcs)); + aen_data.lport.lpwwn = lpwwn; +} + +/** + * This routine will be called to send a FDISC command. + */ +static void +bfa_fcs_vport_do_fdisc(struct bfa_fcs_vport_s *vport) +{ + bfa_lps_fdisc(vport->lps, vport, + bfa_pport_get_maxfrsize(__vport_bfa(vport)), + __vport_pwwn(vport), __vport_nwwn(vport)); + vport->vport_stats.fdisc_sent++; +} + +static void +bfa_fcs_vport_fdisc_rejected(struct bfa_fcs_vport_s *vport) +{ + u8 lsrjt_rsn = bfa_lps_get_lsrjt_rsn(vport->lps); + u8 lsrjt_expl = bfa_lps_get_lsrjt_expl(vport->lps); + + bfa_trc(__vport_fcs(vport), lsrjt_rsn); + bfa_trc(__vport_fcs(vport), lsrjt_expl); + + /* + * For certain reason codes, we don't want to retry. + */ + switch (bfa_lps_get_lsrjt_expl(vport->lps)) { + case FC_LS_RJT_EXP_INV_PORT_NAME: /* by brocade */ + case FC_LS_RJT_EXP_INVALID_NPORT_ID: /* by Cisco */ + if (vport->fdisc_retries < BFA_FCS_VPORT_MAX_RETRIES) + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_ERROR); + else { + bfa_fcs_vport_aen_post(&vport->lport, + BFA_LPORT_AEN_NPIV_DUP_WWN); + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_DUP_WWN); + } + break; + + case FC_LS_RJT_EXP_INSUFF_RES: + /* + * This means max logins per port/switch setting on the + * switch was exceeded. + */ + if (vport->fdisc_retries < BFA_FCS_VPORT_MAX_RETRIES) + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_ERROR); + else { + bfa_fcs_vport_aen_post(&vport->lport, + BFA_LPORT_AEN_NPIV_FABRIC_MAX); + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_FAILED); + } + break; + + default: + if (vport->fdisc_retries == 0) /* Print only once */ + bfa_fcs_vport_aen_post(&vport->lport, + BFA_LPORT_AEN_NPIV_UNKNOWN); + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_ERROR); + } +} + +/** + * Called to send a logout to the fabric. Used when a V-Port is + * deleted/stopped. + */ +static void +bfa_fcs_vport_do_logo(struct bfa_fcs_vport_s *vport) +{ + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + + vport->vport_stats.logo_sent++; + bfa_lps_fdisclogo(vport->lps); +} + +/** + * This routine will be called by bfa_timer on timer timeouts. + * + * param[in] vport - pointer to bfa_fcs_vport_t. + * param[out] vport_status - pointer to return vport status in + * + * return + * void + * +* Special Considerations: + * + * note + */ +static void +bfa_fcs_vport_timeout(void *vport_arg) +{ + struct bfa_fcs_vport_s *vport = (struct bfa_fcs_vport_s *)vport_arg; + + vport->vport_stats.fdisc_timeouts++; + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_TIMEOUT); +} + +static void +bfa_fcs_vport_free(struct bfa_fcs_vport_s *vport) +{ + bfa_fcs_fabric_delvport(__vport_fabric(vport), vport); + bfa_fcb_vport_delete(vport->vport_drv); + bfa_lps_delete(vport->lps); +} + + + +/** + * fcs_vport_public FCS virtual port public interfaces + */ + +/** + * Online notification from fabric SM. + */ +void +bfa_fcs_vport_online(struct bfa_fcs_vport_s *vport) +{ + vport->vport_stats.fab_online++; + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_ONLINE); +} + +/** + * Offline notification from fabric SM. + */ +void +bfa_fcs_vport_offline(struct bfa_fcs_vport_s *vport) +{ + vport->vport_stats.fab_offline++; + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_OFFLINE); +} + +/** + * Cleanup notification from fabric SM on link timer expiry. + */ +void +bfa_fcs_vport_cleanup(struct bfa_fcs_vport_s *vport) +{ + vport->vport_stats.fab_cleanup++; +} + +/** + * Delete completion callback from associated lport + */ +void +bfa_fcs_vport_delete_comp(struct bfa_fcs_vport_s *vport) +{ + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_DELCOMP); +} + +/** + * Module initialization + */ +void +bfa_fcs_vport_modinit(struct bfa_fcs_s *fcs) +{ +} + +/** + * Module cleanup + */ +void +bfa_fcs_vport_modexit(struct bfa_fcs_s *fcs) +{ + bfa_fcs_modexit_comp(fcs); +} + +u32 +bfa_fcs_vport_get_max(struct bfa_fcs_s *fcs) +{ + struct bfa_ioc_attr_s ioc_attr; + + bfa_get_attr(fcs->bfa, &ioc_attr); + + if (ioc_attr.pci_attr.device_id == BFA_PCI_DEVICE_ID_CT) + return (BFA_FCS_MAX_VPORTS_SUPP_CT); + else + return (BFA_FCS_MAX_VPORTS_SUPP_CB); +} + + + +/** + * fcs_vport_api Virtual port API + */ + +/** + * Use this function to instantiate a new FCS vport object. This + * function will not trigger any HW initialization process (which will be + * done in vport_start() call) + * + * param[in] vport - pointer to bfa_fcs_vport_t. This space + * needs to be allocated by the driver. + * param[in] fcs - FCS instance + * param[in] vport_cfg - vport configuration + * param[in] vf_id - VF_ID if vport is created within a VF. + * FC_VF_ID_NULL to specify base fabric. + * param[in] vport_drv - Opaque handle back to the driver's vport + * structure + * + * retval BFA_STATUS_OK - on success. + * retval BFA_STATUS_FAILED - on failure. + */ +bfa_status_t +bfa_fcs_vport_create(struct bfa_fcs_vport_s *vport, struct bfa_fcs_s *fcs, + u16 vf_id, struct bfa_port_cfg_s *vport_cfg, + struct bfad_vport_s *vport_drv) +{ + if (vport_cfg->pwwn == 0) + return (BFA_STATUS_INVALID_WWN); + + if (bfa_fcs_port_get_pwwn(&fcs->fabric.bport) == vport_cfg->pwwn) + return BFA_STATUS_VPORT_WWN_BP; + + if (bfa_fcs_vport_lookup(fcs, vf_id, vport_cfg->pwwn) != NULL) + return BFA_STATUS_VPORT_EXISTS; + + if (bfa_fcs_fabric_vport_count(&fcs->fabric) == + bfa_fcs_vport_get_max(fcs)) + return BFA_STATUS_VPORT_MAX; + + vport->lps = bfa_lps_alloc(fcs->bfa); + if (!vport->lps) + return BFA_STATUS_VPORT_MAX; + + vport->vport_drv = vport_drv; + bfa_sm_set_state(vport, bfa_fcs_vport_sm_uninit); + + bfa_fcs_lport_init(&vport->lport, fcs, vf_id, vport_cfg, vport); + + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_CREATE); + + return BFA_STATUS_OK; +} + +/** + * Use this function initialize the vport. + * + * @param[in] vport - pointer to bfa_fcs_vport_t. + * + * @returns None + */ +bfa_status_t +bfa_fcs_vport_start(struct bfa_fcs_vport_s *vport) +{ + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_START); + + return BFA_STATUS_OK; +} + +/** + * Use this function quiese the vport object. This function will return + * immediately, when the vport is actually stopped, the + * bfa_drv_vport_stop_cb() will be called. + * + * param[in] vport - pointer to bfa_fcs_vport_t. + * + * return None + */ +bfa_status_t +bfa_fcs_vport_stop(struct bfa_fcs_vport_s *vport) +{ + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_STOP); + + return BFA_STATUS_OK; +} + +/** + * Use this function to delete a vport object. Fabric object should + * be stopped before this function call. + * + * param[in] vport - pointer to bfa_fcs_vport_t. + * + * return None + */ +bfa_status_t +bfa_fcs_vport_delete(struct bfa_fcs_vport_s *vport) +{ + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_DELETE); + + return BFA_STATUS_OK; +} + +/** + * Use this function to get vport's current status info. + * + * param[in] vport pointer to bfa_fcs_vport_t. + * param[out] attr pointer to return vport attributes + * + * return None + */ +void +bfa_fcs_vport_get_attr(struct bfa_fcs_vport_s *vport, + struct bfa_vport_attr_s *attr) +{ + if (vport == NULL || attr == NULL) + return; + + bfa_os_memset(attr, 0, sizeof(struct bfa_vport_attr_s)); + + bfa_fcs_port_get_attr(&vport->lport, &attr->port_attr); + attr->vport_state = bfa_sm_to_state(vport_sm_table, vport->sm); +} + +/** + * Use this function to get vport's statistics. + * + * param[in] vport pointer to bfa_fcs_vport_t. + * param[out] stats pointer to return vport statistics in + * + * return None + */ +void +bfa_fcs_vport_get_stats(struct bfa_fcs_vport_s *vport, + struct bfa_vport_stats_s *stats) +{ + *stats = vport->vport_stats; +} + +/** + * Use this function to clear vport's statistics. + * + * param[in] vport pointer to bfa_fcs_vport_t. + * + * return None + */ +void +bfa_fcs_vport_clr_stats(struct bfa_fcs_vport_s *vport) +{ + bfa_os_memset(&vport->vport_stats, 0, sizeof(struct bfa_vport_stats_s)); +} + +/** + * Lookup a virtual port. Excludes base port from lookup. + */ +struct bfa_fcs_vport_s * +bfa_fcs_vport_lookup(struct bfa_fcs_s *fcs, u16 vf_id, wwn_t vpwwn) +{ + struct bfa_fcs_vport_s *vport; + struct bfa_fcs_fabric_s *fabric; + + bfa_trc(fcs, vf_id); + bfa_trc(fcs, vpwwn); + + fabric = bfa_fcs_vf_lookup(fcs, vf_id); + if (!fabric) { + bfa_trc(fcs, vf_id); + return NULL; + } + + vport = bfa_fcs_fabric_vport_lookup(fabric, vpwwn); + return vport; +} + +/** + * FDISC Response + */ +void +bfa_cb_lps_fdisc_comp(void *bfad, void *uarg, bfa_status_t status) +{ + struct bfa_fcs_vport_s *vport = uarg; + + bfa_trc(__vport_fcs(vport), __vport_pwwn(vport)); + bfa_trc(__vport_fcs(vport), status); + + switch (status) { + case BFA_STATUS_OK: + /* + * Initialiaze the V-Port fields + */ + __vport_fcid(vport) = bfa_lps_get_pid(vport->lps); + vport->vport_stats.fdisc_accepts++; + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_OK); + break; + + case BFA_STATUS_INVALID_MAC: + /* + * Only for CNA + */ + vport->vport_stats.fdisc_acc_bad++; + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_ERROR); + + break; + + case BFA_STATUS_EPROTOCOL: + switch (bfa_lps_get_extstatus(vport->lps)) { + case BFA_EPROTO_BAD_ACCEPT: + vport->vport_stats.fdisc_acc_bad++; + break; + + case BFA_EPROTO_UNKNOWN_RSP: + vport->vport_stats.fdisc_unknown_rsp++; + break; + + default: + break; + } + + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_ERROR); + break; + + case BFA_STATUS_FABRIC_RJT: + vport->vport_stats.fdisc_rejects++; + bfa_fcs_vport_fdisc_rejected(vport); + break; + + default: + vport->vport_stats.fdisc_rsp_err++; + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_ERROR); + } +} + +/** + * LOGO response + */ +void +bfa_cb_lps_fdisclogo_comp(void *bfad, void *uarg) +{ + struct bfa_fcs_vport_s *vport = uarg; + bfa_sm_send_event(vport, BFA_FCS_VPORT_SM_RSP_OK); +} + + diff --git a/drivers/scsi/bnx2i/bnx2i.h b/drivers/scsi/bnx2i/bnx2i.h index d7576f28c6e9..5edde1a8c04d 100644 --- a/drivers/scsi/bnx2i/bnx2i.h +++ b/drivers/scsi/bnx2i/bnx2i.h @@ -100,6 +100,8 @@ #define CTX_OFFSET 0x10000 #define MAX_CID_CNT 0x4000 +#define BNX2I_570X_PAGE_SIZE_DEFAULT 4096 + /* 5709 context registers */ #define BNX2_MQ_CONFIG2 0x00003d00 #define BNX2_MQ_CONFIG2_CONT_SZ (0x7L<<4) diff --git a/drivers/scsi/bnx2i/bnx2i_hwi.c b/drivers/scsi/bnx2i/bnx2i_hwi.c index 41e1b0e7e2ef..5c8d7630c13e 100644 --- a/drivers/scsi/bnx2i/bnx2i_hwi.c +++ b/drivers/scsi/bnx2i/bnx2i_hwi.c @@ -2386,7 +2386,7 @@ int bnx2i_map_ep_dbell_regs(struct bnx2i_endpoint *ep) ctx_sz = (config2 & BNX2_MQ_CONFIG2_CONT_SZ) >> 3; if (ctx_sz) reg_off = CTX_OFFSET + MAX_CID_CNT * MB_KERNEL_CTX_SIZE - + PAGE_SIZE * + + BNX2I_570X_PAGE_SIZE_DEFAULT * (((cid_num - first_l4l5) / ctx_sz) + 256); else reg_off = CTX_OFFSET + (MB_KERNEL_CTX_SIZE * cid_num); diff --git a/drivers/scsi/bnx2i/bnx2i_iscsi.c b/drivers/scsi/bnx2i/bnx2i_iscsi.c index 9a7ba71f1af4..cafb888c2376 100644 --- a/drivers/scsi/bnx2i/bnx2i_iscsi.c +++ b/drivers/scsi/bnx2i/bnx2i_iscsi.c @@ -1243,7 +1243,7 @@ bnx2i_session_create(struct iscsi_endpoint *ep, cmds_max = BNX2I_SQ_WQES_MIN; cls_session = iscsi_session_setup(&bnx2i_iscsi_transport, shost, - cmds_max, sizeof(struct bnx2i_cmd), + cmds_max, 0, sizeof(struct bnx2i_cmd), initial_cmdsn, ISCSI_MAX_TARGET); if (!cls_session) return NULL; diff --git a/drivers/scsi/cxgb3i/cxgb3i_iscsi.c b/drivers/scsi/cxgb3i/cxgb3i_iscsi.c index c399f485aa7d..2631bddd255e 100644 --- a/drivers/scsi/cxgb3i/cxgb3i_iscsi.c +++ b/drivers/scsi/cxgb3i/cxgb3i_iscsi.c @@ -422,7 +422,7 @@ cxgb3i_session_create(struct iscsi_endpoint *ep, u16 cmds_max, u16 qdepth, BUG_ON(hba != iscsi_host_priv(shost)); cls_session = iscsi_session_setup(&cxgb3i_iscsi_transport, shost, - cmds_max, + cmds_max, 0, sizeof(struct iscsi_tcp_task) + sizeof(struct cxgb3i_task_data), initial_cmdsn, ISCSI_MAX_TARGET); diff --git a/drivers/scsi/device_handler/scsi_dh_rdac.c b/drivers/scsi/device_handler/scsi_dh_rdac.c index 11c89311427e..268189d31d9c 100644 --- a/drivers/scsi/device_handler/scsi_dh_rdac.c +++ b/drivers/scsi/device_handler/scsi_dh_rdac.c @@ -500,8 +500,6 @@ static int mode_select_handle_sense(struct scsi_device *sdev, if (!ret) goto done; - err = SCSI_DH_OK; - switch (sense_hdr.sense_key) { case NO_SENSE: case ABORTED_COMMAND: diff --git a/drivers/scsi/dpt_i2o.c b/drivers/scsi/dpt_i2o.c index b6af63ca980b..496764349c41 100644 --- a/drivers/scsi/dpt_i2o.c +++ b/drivers/scsi/dpt_i2o.c @@ -1918,6 +1918,10 @@ static int adpt_i2o_passthru(adpt_hba* pHba, u32 __user *arg) } size = size>>16; size *= 4; + if (size > MAX_MESSAGE_SIZE) { + rcode = -EINVAL; + goto cleanup; + } /* Copy in the user's I2O command */ if (copy_from_user (msg, user_msg, size)) { rcode = -EFAULT; diff --git a/drivers/scsi/gdth.c b/drivers/scsi/gdth.c index 185e6bc4dd40..9e8fce0f0c1b 100644 --- a/drivers/scsi/gdth.c +++ b/drivers/scsi/gdth.c @@ -2900,7 +2900,7 @@ static int gdth_read_event(gdth_ha_str *ha, int handle, gdth_evt_str *estr) eindex = handle; estr->event_source = 0; - if (eindex >= MAX_EVENTS) { + if (eindex < 0 || eindex >= MAX_EVENTS) { spin_unlock_irqrestore(&ha->smp_lock, flags); return eindex; } diff --git a/drivers/scsi/hptiop.c b/drivers/scsi/hptiop.c index c596ab5f05c3..a0e7e711ff9d 100644 --- a/drivers/scsi/hptiop.c +++ b/drivers/scsi/hptiop.c @@ -1,6 +1,6 @@ /* * HighPoint RR3xxx/4xxx controller driver for Linux - * Copyright (C) 2006-2007 HighPoint Technologies, Inc. All Rights Reserved. + * Copyright (C) 2006-2009 HighPoint Technologies, Inc. All Rights Reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -41,7 +41,7 @@ MODULE_DESCRIPTION("HighPoint RocketRAID 3xxx/4xxx Controller Driver"); static char driver_name[] = "hptiop"; static const char driver_name_long[] = "RocketRAID 3xxx/4xxx Controller driver"; -static const char driver_ver[] = "v1.3 (071203)"; +static const char driver_ver[] = "v1.6 (090910)"; static int iop_send_sync_msg(struct hptiop_hba *hba, u32 msg, u32 millisec); static void hptiop_finish_scsi_req(struct hptiop_hba *hba, u32 tag, @@ -115,9 +115,13 @@ static void hptiop_drain_outbound_queue_itl(struct hptiop_hba *hba) static int iop_intr_itl(struct hptiop_hba *hba) { struct hpt_iopmu_itl __iomem *iop = hba->u.itl.iop; + void __iomem *plx = hba->u.itl.plx; u32 status; int ret = 0; + if (plx && readl(plx + 0x11C5C) & 0xf) + writel(1, plx + 0x11C60); + status = readl(&iop->outbound_intstatus); if (status & IOPMU_OUTBOUND_INT_MSG0) { @@ -460,15 +464,25 @@ static void __iomem *hptiop_map_pci_bar(struct hptiop_hba *hba, int index) static int hptiop_map_pci_bar_itl(struct hptiop_hba *hba) { + struct pci_dev *pcidev = hba->pcidev; hba->u.itl.iop = hptiop_map_pci_bar(hba, 0); - if (hba->u.itl.iop) - return 0; - else + if (hba->u.itl.iop == NULL) return -1; + if ((pcidev->device & 0xff00) == 0x4400) { + hba->u.itl.plx = hba->u.itl.iop; + hba->u.itl.iop = hptiop_map_pci_bar(hba, 2); + if (hba->u.itl.iop == NULL) { + iounmap(hba->u.itl.plx); + return -1; + } + } + return 0; } static void hptiop_unmap_pci_bar_itl(struct hptiop_hba *hba) { + if (hba->u.itl.plx) + iounmap(hba->u.itl.plx); iounmap(hba->u.itl.iop); } @@ -1239,22 +1253,23 @@ static struct hptiop_adapter_ops hptiop_mv_ops = { static struct pci_device_id hptiop_id_table[] = { { PCI_VDEVICE(TTI, 0x3220), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3320), (kernel_ulong_t)&hptiop_itl_ops }, - { PCI_VDEVICE(TTI, 0x3520), (kernel_ulong_t)&hptiop_itl_ops }, - { PCI_VDEVICE(TTI, 0x4320), (kernel_ulong_t)&hptiop_itl_ops }, + { PCI_VDEVICE(TTI, 0x3410), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3510), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3511), (kernel_ulong_t)&hptiop_itl_ops }, + { PCI_VDEVICE(TTI, 0x3520), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3521), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3522), (kernel_ulong_t)&hptiop_itl_ops }, - { PCI_VDEVICE(TTI, 0x3410), (kernel_ulong_t)&hptiop_itl_ops }, - { PCI_VDEVICE(TTI, 0x3540), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3530), (kernel_ulong_t)&hptiop_itl_ops }, + { PCI_VDEVICE(TTI, 0x3540), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3560), (kernel_ulong_t)&hptiop_itl_ops }, - { PCI_VDEVICE(TTI, 0x4322), (kernel_ulong_t)&hptiop_itl_ops }, - { PCI_VDEVICE(TTI, 0x4321), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x4210), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x4211), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x4310), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x4311), (kernel_ulong_t)&hptiop_itl_ops }, + { PCI_VDEVICE(TTI, 0x4320), (kernel_ulong_t)&hptiop_itl_ops }, + { PCI_VDEVICE(TTI, 0x4321), (kernel_ulong_t)&hptiop_itl_ops }, + { PCI_VDEVICE(TTI, 0x4322), (kernel_ulong_t)&hptiop_itl_ops }, + { PCI_VDEVICE(TTI, 0x4400), (kernel_ulong_t)&hptiop_itl_ops }, { PCI_VDEVICE(TTI, 0x3120), (kernel_ulong_t)&hptiop_mv_ops }, { PCI_VDEVICE(TTI, 0x3122), (kernel_ulong_t)&hptiop_mv_ops }, { PCI_VDEVICE(TTI, 0x3020), (kernel_ulong_t)&hptiop_mv_ops }, diff --git a/drivers/scsi/hptiop.h b/drivers/scsi/hptiop.h index a0289f219752..0b871c0ae568 100644 --- a/drivers/scsi/hptiop.h +++ b/drivers/scsi/hptiop.h @@ -1,6 +1,6 @@ /* * HighPoint RR3xxx/4xxx controller driver for Linux - * Copyright (C) 2006-2007 HighPoint Technologies, Inc. All Rights Reserved. + * Copyright (C) 2006-2009 HighPoint Technologies, Inc. All Rights Reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -228,6 +228,7 @@ struct hptiop_hba { union { struct { struct hpt_iopmu_itl __iomem *iop; + void __iomem *plx; } itl; struct { struct hpt_iopmv_regs *regs; diff --git a/drivers/scsi/ipr.c b/drivers/scsi/ipr.c index 5f045505a1f4..76d294fc7846 100644 --- a/drivers/scsi/ipr.c +++ b/drivers/scsi/ipr.c @@ -4189,6 +4189,25 @@ static irqreturn_t ipr_handle_other_interrupt(struct ipr_ioa_cfg *ioa_cfg, } /** + * ipr_isr_eh - Interrupt service routine error handler + * @ioa_cfg: ioa config struct + * @msg: message to log + * + * Return value: + * none + **/ +static void ipr_isr_eh(struct ipr_ioa_cfg *ioa_cfg, char *msg) +{ + ioa_cfg->errors_logged++; + dev_err(&ioa_cfg->pdev->dev, "%s\n", msg); + + if (WAIT_FOR_DUMP == ioa_cfg->sdt_state) + ioa_cfg->sdt_state = GET_DUMP; + + ipr_initiate_ioa_reset(ioa_cfg, IPR_SHUTDOWN_NONE); +} + +/** * ipr_isr - Interrupt service routine * @irq: irq number * @devp: pointer to ioa config struct @@ -4203,6 +4222,7 @@ static irqreturn_t ipr_isr(int irq, void *devp) volatile u32 int_reg, int_mask_reg; u32 ioasc; u16 cmd_index; + int num_hrrq = 0; struct ipr_cmnd *ipr_cmd; irqreturn_t rc = IRQ_NONE; @@ -4233,13 +4253,7 @@ static irqreturn_t ipr_isr(int irq, void *devp) IPR_HRRQ_REQ_RESP_HANDLE_MASK) >> IPR_HRRQ_REQ_RESP_HANDLE_SHIFT; if (unlikely(cmd_index >= IPR_NUM_CMD_BLKS)) { - ioa_cfg->errors_logged++; - dev_err(&ioa_cfg->pdev->dev, "Invalid response handle from IOA\n"); - - if (WAIT_FOR_DUMP == ioa_cfg->sdt_state) - ioa_cfg->sdt_state = GET_DUMP; - - ipr_initiate_ioa_reset(ioa_cfg, IPR_SHUTDOWN_NONE); + ipr_isr_eh(ioa_cfg, "Invalid response handle from IOA"); spin_unlock_irqrestore(ioa_cfg->host->host_lock, lock_flags); return IRQ_HANDLED; } @@ -4266,8 +4280,18 @@ static irqreturn_t ipr_isr(int irq, void *devp) if (ipr_cmd != NULL) { /* Clear the PCI interrupt */ - writel(IPR_PCII_HRRQ_UPDATED, ioa_cfg->regs.clr_interrupt_reg); - int_reg = readl(ioa_cfg->regs.sense_interrupt_reg) & ~int_mask_reg; + do { + writel(IPR_PCII_HRRQ_UPDATED, ioa_cfg->regs.clr_interrupt_reg); + int_reg = readl(ioa_cfg->regs.sense_interrupt_reg) & ~int_mask_reg; + } while (int_reg & IPR_PCII_HRRQ_UPDATED && + num_hrrq++ < IPR_MAX_HRRQ_RETRIES); + + if (int_reg & IPR_PCII_HRRQ_UPDATED) { + ipr_isr_eh(ioa_cfg, "Error clearing HRRQ"); + spin_unlock_irqrestore(ioa_cfg->host->host_lock, lock_flags); + return IRQ_HANDLED; + } + } else break; } diff --git a/drivers/scsi/ipr.h b/drivers/scsi/ipr.h index 163245a1c3e5..19bbcf39f0c9 100644 --- a/drivers/scsi/ipr.h +++ b/drivers/scsi/ipr.h @@ -144,6 +144,7 @@ #define IPR_IOA_MAX_SECTORS 32767 #define IPR_VSET_MAX_SECTORS 512 #define IPR_MAX_CDB_LEN 16 +#define IPR_MAX_HRRQ_RETRIES 3 #define IPR_DEFAULT_BUS_WIDTH 16 #define IPR_80MBs_SCSI_RATE ((80 * 10) / (IPR_DEFAULT_BUS_WIDTH / 8)) diff --git a/drivers/scsi/iscsi_tcp.c b/drivers/scsi/iscsi_tcp.c index 2b1b834a098b..edc49ca49cea 100644 --- a/drivers/scsi/iscsi_tcp.c +++ b/drivers/scsi/iscsi_tcp.c @@ -811,7 +811,7 @@ iscsi_sw_tcp_session_create(struct iscsi_endpoint *ep, uint16_t cmds_max, goto free_host; cls_session = iscsi_session_setup(&iscsi_sw_tcp_transport, shost, - cmds_max, + cmds_max, 0, sizeof(struct iscsi_tcp_task) + sizeof(struct iscsi_sw_tcp_hdrbuf), initial_cmdsn, 0); diff --git a/drivers/scsi/libiscsi.c b/drivers/scsi/libiscsi.c index 8dc73c489a17..f1a4246f890c 100644 --- a/drivers/scsi/libiscsi.c +++ b/drivers/scsi/libiscsi.c @@ -2436,7 +2436,7 @@ static void iscsi_host_dec_session_cnt(struct Scsi_Host *shost) */ struct iscsi_cls_session * iscsi_session_setup(struct iscsi_transport *iscsit, struct Scsi_Host *shost, - uint16_t cmds_max, int cmd_task_size, + uint16_t cmds_max, int dd_size, int cmd_task_size, uint32_t initial_cmdsn, unsigned int id) { struct iscsi_host *ihost = shost_priv(shost); @@ -2486,7 +2486,8 @@ iscsi_session_setup(struct iscsi_transport *iscsit, struct Scsi_Host *shost, scsi_cmds = total_cmds - ISCSI_MGMT_CMDS_MAX; cls_session = iscsi_alloc_session(shost, iscsit, - sizeof(struct iscsi_session)); + sizeof(struct iscsi_session) + + dd_size); if (!cls_session) goto dec_session_count; session = cls_session->dd_data; @@ -2503,6 +2504,7 @@ iscsi_session_setup(struct iscsi_transport *iscsit, struct Scsi_Host *shost, session->max_cmdsn = initial_cmdsn + 1; session->max_r2t = 1; session->tt = iscsit; + session->dd_data = cls_session->dd_data + sizeof(*session); mutex_init(&session->eh_mutex); spin_lock_init(&session->lock); diff --git a/drivers/scsi/libsas/sas_expander.c b/drivers/scsi/libsas/sas_expander.c index b3381959acce..33cf988c8c8a 100644 --- a/drivers/scsi/libsas/sas_expander.c +++ b/drivers/scsi/libsas/sas_expander.c @@ -960,7 +960,6 @@ static int sas_ex_discover_dev(struct domain_device *dev, int phy_id) } } - res = 0; } return res; diff --git a/drivers/scsi/lpfc/lpfc_scsi.c b/drivers/scsi/lpfc/lpfc_scsi.c index 61d089703806..c88f59f0ce30 100644 --- a/drivers/scsi/lpfc/lpfc_scsi.c +++ b/drivers/scsi/lpfc/lpfc_scsi.c @@ -56,8 +56,6 @@ static char *dif_op_str[] = { "SCSI_PROT_WRITE_INSERT", "SCSI_PROT_READ_PASS", "SCSI_PROT_WRITE_PASS", - "SCSI_PROT_READ_CONVERT", - "SCSI_PROT_WRITE_CONVERT" }; static void lpfc_release_scsi_buf_s4(struct lpfc_hba *phba, struct lpfc_scsi_buf *psb); @@ -1131,13 +1129,11 @@ lpfc_sc_to_sli_prof(struct scsi_cmnd *sc) ret_prof = LPFC_PROF_A1; break; - case SCSI_PROT_READ_CONVERT: - case SCSI_PROT_WRITE_CONVERT: + case SCSI_PROT_READ_PASS: + case SCSI_PROT_WRITE_PASS: ret_prof = LPFC_PROF_AST1; break; - case SCSI_PROT_READ_PASS: - case SCSI_PROT_WRITE_PASS: case SCSI_PROT_NORMAL: default: printk(KERN_ERR "Bad op/guard:%d/%d combination\n", @@ -1157,8 +1153,6 @@ lpfc_sc_to_sli_prof(struct scsi_cmnd *sc) ret_prof = LPFC_PROF_C1; break; - case SCSI_PROT_READ_CONVERT: - case SCSI_PROT_WRITE_CONVERT: case SCSI_PROT_READ_INSERT: case SCSI_PROT_WRITE_STRIP: case SCSI_PROT_NORMAL: @@ -1209,8 +1203,7 @@ lpfc_get_cmd_dif_parms(struct scsi_cmnd *sc, uint16_t *apptagmask, static int cnt; if (protcnt && (op == SCSI_PROT_WRITE_STRIP || - op == SCSI_PROT_WRITE_PASS || - op == SCSI_PROT_WRITE_CONVERT)) { + op == SCSI_PROT_WRITE_PASS)) { cnt++; spt = page_address(sg_page(scsi_prot_sglist(sc))) + @@ -1501,8 +1494,6 @@ lpfc_prot_group_type(struct lpfc_hba *phba, struct scsi_cmnd *sc) case SCSI_PROT_WRITE_STRIP: case SCSI_PROT_READ_PASS: case SCSI_PROT_WRITE_PASS: - case SCSI_PROT_WRITE_CONVERT: - case SCSI_PROT_READ_CONVERT: ret = LPFC_PG_TYPE_DIF_BUF; break; default: diff --git a/drivers/scsi/mpt2sas/Kconfig b/drivers/scsi/mpt2sas/Kconfig index 4a86855c23b3..70c4c2467dd8 100644 --- a/drivers/scsi/mpt2sas/Kconfig +++ b/drivers/scsi/mpt2sas/Kconfig @@ -2,7 +2,7 @@ # Kernel configuration file for the MPT2SAS # # This code is based on drivers/scsi/mpt2sas/Kconfig -# Copyright (C) 2007-2008 LSI Corporation +# Copyright (C) 2007-2009 LSI Corporation # (mailto:DL-MPTFusionLinux@lsi.com) # This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/mpt2sas/mpi/mpi2.h b/drivers/scsi/mpt2sas/mpi/mpi2.h index 7bb2ece8b2e4..f9f6c0839276 100644 --- a/drivers/scsi/mpt2sas/mpi/mpi2.h +++ b/drivers/scsi/mpt2sas/mpi/mpi2.h @@ -8,7 +8,7 @@ * scatter/gather formats. * Creation Date: June 21, 2006 * - * mpi2.h Version: 02.00.11 + * mpi2.h Version: 02.00.12 * * Version History * --------------- @@ -45,6 +45,13 @@ * 10-02-08 02.00.10 Bumped MPI2_HEADER_VERSION_UNIT. * Moved LUN field defines from mpi2_init.h. * 01-19-09 02.00.11 Bumped MPI2_HEADER_VERSION_UNIT. + * 05-06-09 02.00.12 Bumped MPI2_HEADER_VERSION_UNIT. + * In all request and reply descriptors, replaced VF_ID + * field with MSIxIndex field. + * Removed DevHandle field from + * MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR and made those + * bytes reserved. + * Added RAID Accelerator functionality. * -------------------------------------------------------------------------- */ @@ -70,7 +77,7 @@ #define MPI2_VERSION_02_00 (0x0200) /* versioning for this MPI header set */ -#define MPI2_HEADER_VERSION_UNIT (0x0B) +#define MPI2_HEADER_VERSION_UNIT (0x0C) #define MPI2_HEADER_VERSION_DEV (0x00) #define MPI2_HEADER_VERSION_UNIT_MASK (0xFF00) #define MPI2_HEADER_VERSION_UNIT_SHIFT (8) @@ -257,7 +264,7 @@ typedef volatile struct _MPI2_SYSTEM_INTERFACE_REGS typedef struct _MPI2_DEFAULT_REQUEST_DESCRIPTOR { U8 RequestFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 SMID; /* 0x02 */ U16 LMID; /* 0x04 */ U16 DescriptorTypeDependent; /* 0x06 */ @@ -271,6 +278,7 @@ typedef struct _MPI2_DEFAULT_REQUEST_DESCRIPTOR #define MPI2_REQ_DESCRIPT_FLAGS_SCSI_TARGET (0x02) #define MPI2_REQ_DESCRIPT_FLAGS_HIGH_PRIORITY (0x06) #define MPI2_REQ_DESCRIPT_FLAGS_DEFAULT_TYPE (0x08) +#define MPI2_REQ_DESCRIPT_FLAGS_RAID_ACCELERATOR (0x0A) #define MPI2_REQ_DESCRIPT_FLAGS_IOC_FIFO_MARKER (0x01) @@ -279,7 +287,7 @@ typedef struct _MPI2_DEFAULT_REQUEST_DESCRIPTOR typedef struct _MPI2_HIGH_PRIORITY_REQUEST_DESCRIPTOR { U8 RequestFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 SMID; /* 0x02 */ U16 LMID; /* 0x04 */ U16 Reserved1; /* 0x06 */ @@ -293,7 +301,7 @@ typedef struct _MPI2_HIGH_PRIORITY_REQUEST_DESCRIPTOR typedef struct _MPI2_SCSI_IO_REQUEST_DESCRIPTOR { U8 RequestFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 SMID; /* 0x02 */ U16 LMID; /* 0x04 */ U16 DevHandle; /* 0x06 */ @@ -306,7 +314,7 @@ typedef struct _MPI2_SCSI_IO_REQUEST_DESCRIPTOR typedef struct _MPI2_SCSI_TARGET_REQUEST_DESCRIPTOR { U8 RequestFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 SMID; /* 0x02 */ U16 LMID; /* 0x04 */ U16 IoIndex; /* 0x06 */ @@ -315,14 +323,29 @@ typedef struct _MPI2_SCSI_TARGET_REQUEST_DESCRIPTOR Mpi2SCSITargetRequestDescriptor_t, MPI2_POINTER pMpi2SCSITargetRequestDescriptor_t; + +/* RAID Accelerator Request Descriptor */ +typedef struct _MPI2_RAID_ACCEL_REQUEST_DESCRIPTOR { + U8 RequestFlags; /* 0x00 */ + U8 MSIxIndex; /* 0x01 */ + U16 SMID; /* 0x02 */ + U16 LMID; /* 0x04 */ + U16 Reserved; /* 0x06 */ +} MPI2_RAID_ACCEL_REQUEST_DESCRIPTOR, + MPI2_POINTER PTR_MPI2_RAID_ACCEL_REQUEST_DESCRIPTOR, + Mpi2RAIDAcceleratorRequestDescriptor_t, + MPI2_POINTER pMpi2RAIDAcceleratorRequestDescriptor_t; + + /* union of Request Descriptors */ typedef union _MPI2_REQUEST_DESCRIPTOR_UNION { - MPI2_DEFAULT_REQUEST_DESCRIPTOR Default; - MPI2_HIGH_PRIORITY_REQUEST_DESCRIPTOR HighPriority; - MPI2_SCSI_IO_REQUEST_DESCRIPTOR SCSIIO; - MPI2_SCSI_TARGET_REQUEST_DESCRIPTOR SCSITarget; - U64 Words; + MPI2_DEFAULT_REQUEST_DESCRIPTOR Default; + MPI2_HIGH_PRIORITY_REQUEST_DESCRIPTOR HighPriority; + MPI2_SCSI_IO_REQUEST_DESCRIPTOR SCSIIO; + MPI2_SCSI_TARGET_REQUEST_DESCRIPTOR SCSITarget; + MPI2_RAID_ACCEL_REQUEST_DESCRIPTOR RAIDAccelerator; + U64 Words; } MPI2_REQUEST_DESCRIPTOR_UNION, MPI2_POINTER PTR_MPI2_REQUEST_DESCRIPTOR_UNION, Mpi2RequestDescriptorUnion_t, MPI2_POINTER pMpi2RequestDescriptorUnion_t; @@ -333,19 +356,20 @@ typedef union _MPI2_REQUEST_DESCRIPTOR_UNION typedef struct _MPI2_DEFAULT_REPLY_DESCRIPTOR { U8 ReplyFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 DescriptorTypeDependent1; /* 0x02 */ U32 DescriptorTypeDependent2; /* 0x04 */ } MPI2_DEFAULT_REPLY_DESCRIPTOR, MPI2_POINTER PTR_MPI2_DEFAULT_REPLY_DESCRIPTOR, Mpi2DefaultReplyDescriptor_t, MPI2_POINTER pMpi2DefaultReplyDescriptor_t; /* defines for the ReplyFlags field */ -#define MPI2_RPY_DESCRIPT_FLAGS_TYPE_MASK (0x0F) -#define MPI2_RPY_DESCRIPT_FLAGS_SCSI_IO_SUCCESS (0x00) -#define MPI2_RPY_DESCRIPT_FLAGS_ADDRESS_REPLY (0x01) -#define MPI2_RPY_DESCRIPT_FLAGS_TARGETASSIST_SUCCESS (0x02) -#define MPI2_RPY_DESCRIPT_FLAGS_TARGET_COMMAND_BUFFER (0x03) -#define MPI2_RPY_DESCRIPT_FLAGS_UNUSED (0x0F) +#define MPI2_RPY_DESCRIPT_FLAGS_TYPE_MASK (0x0F) +#define MPI2_RPY_DESCRIPT_FLAGS_SCSI_IO_SUCCESS (0x00) +#define MPI2_RPY_DESCRIPT_FLAGS_ADDRESS_REPLY (0x01) +#define MPI2_RPY_DESCRIPT_FLAGS_TARGETASSIST_SUCCESS (0x02) +#define MPI2_RPY_DESCRIPT_FLAGS_TARGET_COMMAND_BUFFER (0x03) +#define MPI2_RPY_DESCRIPT_FLAGS_RAID_ACCELERATOR_SUCCESS (0x05) +#define MPI2_RPY_DESCRIPT_FLAGS_UNUSED (0x0F) /* values for marking a reply descriptor as unused */ #define MPI2_RPY_DESCRIPT_UNUSED_WORD0_MARK (0xFFFFFFFF) @@ -355,7 +379,7 @@ typedef struct _MPI2_DEFAULT_REPLY_DESCRIPTOR typedef struct _MPI2_ADDRESS_REPLY_DESCRIPTOR { U8 ReplyFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 SMID; /* 0x02 */ U32 ReplyFrameAddress; /* 0x04 */ } MPI2_ADDRESS_REPLY_DESCRIPTOR, MPI2_POINTER PTR_MPI2_ADDRESS_REPLY_DESCRIPTOR, @@ -368,10 +392,10 @@ typedef struct _MPI2_ADDRESS_REPLY_DESCRIPTOR typedef struct _MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR { U8 ReplyFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 SMID; /* 0x02 */ U16 TaskTag; /* 0x04 */ - U16 DevHandle; /* 0x06 */ + U16 Reserved1; /* 0x06 */ } MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR, MPI2_POINTER PTR_MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR, Mpi2SCSIIOSuccessReplyDescriptor_t, @@ -382,7 +406,7 @@ typedef struct _MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR typedef struct _MPI2_TARGETASSIST_SUCCESS_REPLY_DESCRIPTOR { U8 ReplyFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U16 SMID; /* 0x02 */ U8 SequenceNumber; /* 0x04 */ U8 Reserved1; /* 0x05 */ @@ -397,7 +421,7 @@ typedef struct _MPI2_TARGETASSIST_SUCCESS_REPLY_DESCRIPTOR typedef struct _MPI2_TARGET_COMMAND_BUFFER_REPLY_DESCRIPTOR { U8 ReplyFlags; /* 0x00 */ - U8 VF_ID; /* 0x01 */ + U8 MSIxIndex; /* 0x01 */ U8 VP_ID; /* 0x02 */ U8 Flags; /* 0x03 */ U16 InitiatorDevHandle; /* 0x04 */ @@ -411,15 +435,28 @@ typedef struct _MPI2_TARGET_COMMAND_BUFFER_REPLY_DESCRIPTOR #define MPI2_RPY_DESCRIPT_TCB_FLAGS_PHYNUM_MASK (0x3F) +/* RAID Accelerator Success Reply Descriptor */ +typedef struct _MPI2_RAID_ACCELERATOR_SUCCESS_REPLY_DESCRIPTOR { + U8 ReplyFlags; /* 0x00 */ + U8 MSIxIndex; /* 0x01 */ + U16 SMID; /* 0x02 */ + U32 Reserved; /* 0x04 */ +} MPI2_RAID_ACCELERATOR_SUCCESS_REPLY_DESCRIPTOR, + MPI2_POINTER PTR_MPI2_RAID_ACCELERATOR_SUCCESS_REPLY_DESCRIPTOR, + Mpi2RAIDAcceleratorSuccessReplyDescriptor_t, + MPI2_POINTER pMpi2RAIDAcceleratorSuccessReplyDescriptor_t; + + /* union of Reply Descriptors */ typedef union _MPI2_REPLY_DESCRIPTORS_UNION { - MPI2_DEFAULT_REPLY_DESCRIPTOR Default; - MPI2_ADDRESS_REPLY_DESCRIPTOR AddressReply; - MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR SCSIIOSuccess; - MPI2_TARGETASSIST_SUCCESS_REPLY_DESCRIPTOR TargetAssistSuccess; - MPI2_TARGET_COMMAND_BUFFER_REPLY_DESCRIPTOR TargetCommandBuffer; - U64 Words; + MPI2_DEFAULT_REPLY_DESCRIPTOR Default; + MPI2_ADDRESS_REPLY_DESCRIPTOR AddressReply; + MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR SCSIIOSuccess; + MPI2_TARGETASSIST_SUCCESS_REPLY_DESCRIPTOR TargetAssistSuccess; + MPI2_TARGET_COMMAND_BUFFER_REPLY_DESCRIPTOR TargetCommandBuffer; + MPI2_RAID_ACCELERATOR_SUCCESS_REPLY_DESCRIPTOR RAIDAcceleratorSuccess; + U64 Words; } MPI2_REPLY_DESCRIPTORS_UNION, MPI2_POINTER PTR_MPI2_REPLY_DESCRIPTORS_UNION, Mpi2ReplyDescriptorsUnion_t, MPI2_POINTER pMpi2ReplyDescriptorsUnion_t; @@ -458,6 +495,7 @@ typedef union _MPI2_REPLY_DESCRIPTORS_UNION #define MPI2_FUNCTION_DIAG_RELEASE (0x1E) /* Diagnostic Release */ #define MPI2_FUNCTION_TARGET_CMD_BUF_BASE_POST (0x24) /* Target Command Buffer Post Base */ #define MPI2_FUNCTION_TARGET_CMD_BUF_LIST_POST (0x25) /* Target Command Buffer Post List */ +#define MPI2_FUNCTION_RAID_ACCELERATOR (0x2C) /* RAID Accelerator*/ @@ -555,12 +593,17 @@ typedef union _MPI2_REPLY_DESCRIPTORS_UNION #define MPI2_IOCSTATUS_DIAGNOSTIC_RELEASED (0x00A0) +/**************************************************************************** +* RAID Accelerator values +****************************************************************************/ + +#define MPI2_IOCSTATUS_RAID_ACCEL_ERROR (0x00B0) /**************************************************************************** * IOCStatus flag to indicate that log info is available ****************************************************************************/ -#define MPI2_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE (0x8000) +#define MPI2_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE (0x8000) /**************************************************************************** * IOCLogInfo Types diff --git a/drivers/scsi/mpt2sas/mpi/mpi2_cnfg.h b/drivers/scsi/mpt2sas/mpi/mpi2_cnfg.h index 2f27cf6d6c65..ab47c4679640 100644 --- a/drivers/scsi/mpt2sas/mpi/mpi2_cnfg.h +++ b/drivers/scsi/mpt2sas/mpi/mpi2_cnfg.h @@ -6,7 +6,7 @@ * Title: MPI Configuration messages and pages * Creation Date: November 10, 2006 * - * mpi2_cnfg.h Version: 02.00.10 + * mpi2_cnfg.h Version: 02.00.11 * * Version History * --------------- @@ -95,6 +95,11 @@ * Added MPI2_SAS_DEVICE0_ASTATUS_DEVICE_BLOCKED define. * Added PortGroups, DmaGroup, and ControlGroup fields to * SAS Device Page 0. + * 05-06-09 02.00.11 Added structures and defines for IO Unit Page 5 and IO + * Unit Page 6. + * Added expander reduced functionality data to SAS + * Expander Page 0. + * Added SAS PHY Page 2 and SAS PHY Page 3. * -------------------------------------------------------------------------- */ @@ -723,6 +728,65 @@ typedef struct _MPI2_CONFIG_PAGE_IO_UNIT_3 #define MPI2_IOUNITPAGE3_GPIO_SETTING_ON (0x0001) +/* IO Unit Page 5 */ + +/* + * Upper layer code (drivers, utilities, etc.) should leave this define set to + * one and check Header.PageLength or NumDmaEngines at runtime. + */ +#ifndef MPI2_IOUNITPAGE5_DMAENGINE_ENTRIES +#define MPI2_IOUNITPAGE5_DMAENGINE_ENTRIES (1) +#endif + +typedef struct _MPI2_CONFIG_PAGE_IO_UNIT_5 { + MPI2_CONFIG_PAGE_HEADER Header; /* 0x00 */ + U64 RaidAcceleratorBufferBaseAddress; /* 0x04 */ + U64 RaidAcceleratorBufferSize; /* 0x0C */ + U64 RaidAcceleratorControlBaseAddress; /* 0x14 */ + U8 RAControlSize; /* 0x1C */ + U8 NumDmaEngines; /* 0x1D */ + U8 RAMinControlSize; /* 0x1E */ + U8 RAMaxControlSize; /* 0x1F */ + U32 Reserved1; /* 0x20 */ + U32 Reserved2; /* 0x24 */ + U32 Reserved3; /* 0x28 */ + U32 DmaEngineCapabilities + [MPI2_IOUNITPAGE5_DMAENGINE_ENTRIES]; /* 0x2C */ +} MPI2_CONFIG_PAGE_IO_UNIT_5, MPI2_POINTER PTR_MPI2_CONFIG_PAGE_IO_UNIT_5, + Mpi2IOUnitPage5_t, MPI2_POINTER pMpi2IOUnitPage5_t; + +#define MPI2_IOUNITPAGE5_PAGEVERSION (0x00) + +/* defines for IO Unit Page 5 DmaEngineCapabilities field */ +#define MPI2_IOUNITPAGE5_DMA_CAP_MASK_MAX_REQUESTS (0xFF00) +#define MPI2_IOUNITPAGE5_DMA_CAP_SHIFT_MAX_REQUESTS (16) + +#define MPI2_IOUNITPAGE5_DMA_CAP_EEDP (0x0008) +#define MPI2_IOUNITPAGE5_DMA_CAP_PARITY_GENERATION (0x0004) +#define MPI2_IOUNITPAGE5_DMA_CAP_HASHING (0x0002) +#define MPI2_IOUNITPAGE5_DMA_CAP_ENCRYPTION (0x0001) + + +/* IO Unit Page 6 */ + +typedef struct _MPI2_CONFIG_PAGE_IO_UNIT_6 { + MPI2_CONFIG_PAGE_HEADER Header; /* 0x00 */ + U16 Flags; /* 0x04 */ + U8 RAHostControlSize; /* 0x06 */ + U8 Reserved0; /* 0x07 */ + U64 RaidAcceleratorHostControlBaseAddress; /* 0x08 */ + U32 Reserved1; /* 0x10 */ + U32 Reserved2; /* 0x14 */ + U32 Reserved3; /* 0x18 */ +} MPI2_CONFIG_PAGE_IO_UNIT_6, MPI2_POINTER PTR_MPI2_CONFIG_PAGE_IO_UNIT_6, + Mpi2IOUnitPage6_t, MPI2_POINTER pMpi2IOUnitPage6_t; + +#define MPI2_IOUNITPAGE6_PAGEVERSION (0x00) + +/* defines for IO Unit Page 6 Flags field */ +#define MPI2_IOUNITPAGE6_FLAGS_ENABLE_RAID_ACCELERATOR (0x0001) + + /**************************************************************************** * IOC Config Pages ****************************************************************************/ @@ -1709,10 +1773,14 @@ typedef struct _MPI2_CONFIG_PAGE_EXPANDER_0 U64 ActiveZoneManagerSASAddress;/* 0x2C */ U16 ZoneLockInactivityLimit; /* 0x34 */ U16 Reserved1; /* 0x36 */ + U8 TimeToReducedFunc; /* 0x38 */ + U8 InitialTimeToReducedFunc; /* 0x39 */ + U8 MaxReducedFuncTime; /* 0x3A */ + U8 Reserved2; /* 0x3B */ } MPI2_CONFIG_PAGE_EXPANDER_0, MPI2_POINTER PTR_MPI2_CONFIG_PAGE_EXPANDER_0, Mpi2ExpanderPage0_t, MPI2_POINTER pMpi2ExpanderPage0_t; -#define MPI2_SASEXPANDER0_PAGEVERSION (0x05) +#define MPI2_SASEXPANDER0_PAGEVERSION (0x06) /* values for SAS Expander Page 0 DiscoveryStatus field */ #define MPI2_SAS_EXPANDER0_DS_MAX_ENCLOSURES_EXCEED (0x80000000) @@ -1737,6 +1805,7 @@ typedef struct _MPI2_CONFIG_PAGE_EXPANDER_0 #define MPI2_SAS_EXPANDER0_DS_LOOP_DETECTED (0x00000001) /* values for SAS Expander Page 0 Flags field */ +#define MPI2_SAS_EXPANDER0_FLAGS_REDUCED_FUNCTIONALITY (0x2000) #define MPI2_SAS_EXPANDER0_FLAGS_ZONE_LOCKED (0x1000) #define MPI2_SAS_EXPANDER0_FLAGS_SUPPORTED_PHYSICAL_PRES (0x0800) #define MPI2_SAS_EXPANDER0_FLAGS_ASSERTED_PHYSICAL_PRES (0x0400) @@ -1944,6 +2013,133 @@ typedef struct _MPI2_CONFIG_PAGE_SAS_PHY_1 #define MPI2_SASPHY1_PAGEVERSION (0x01) +/* SAS PHY Page 2 */ + +typedef struct _MPI2_SASPHY2_PHY_EVENT { + U8 PhyEventCode; /* 0x00 */ + U8 Reserved1; /* 0x01 */ + U16 Reserved2; /* 0x02 */ + U32 PhyEventInfo; /* 0x04 */ +} MPI2_SASPHY2_PHY_EVENT, MPI2_POINTER PTR_MPI2_SASPHY2_PHY_EVENT, + Mpi2SasPhy2PhyEvent_t, MPI2_POINTER pMpi2SasPhy2PhyEvent_t; + +/* use MPI2_SASPHY3_EVENT_CODE_ for the PhyEventCode field */ + + +/* + * Host code (drivers, BIOS, utilities, etc.) should leave this define set to + * one and check Header.ExtPageLength or NumPhyEvents at runtime. + */ +#ifndef MPI2_SASPHY2_PHY_EVENT_MAX +#define MPI2_SASPHY2_PHY_EVENT_MAX (1) +#endif + +typedef struct _MPI2_CONFIG_PAGE_SAS_PHY_2 { + MPI2_CONFIG_EXTENDED_PAGE_HEADER Header; /* 0x00 */ + U32 Reserved1; /* 0x08 */ + U8 NumPhyEvents; /* 0x0C */ + U8 Reserved2; /* 0x0D */ + U16 Reserved3; /* 0x0E */ + MPI2_SASPHY2_PHY_EVENT PhyEvent[MPI2_SASPHY2_PHY_EVENT_MAX]; + /* 0x10 */ +} MPI2_CONFIG_PAGE_SAS_PHY_2, MPI2_POINTER PTR_MPI2_CONFIG_PAGE_SAS_PHY_2, + Mpi2SasPhyPage2_t, MPI2_POINTER pMpi2SasPhyPage2_t; + +#define MPI2_SASPHY2_PAGEVERSION (0x00) + + +/* SAS PHY Page 3 */ + +typedef struct _MPI2_SASPHY3_PHY_EVENT_CONFIG { + U8 PhyEventCode; /* 0x00 */ + U8 Reserved1; /* 0x01 */ + U16 Reserved2; /* 0x02 */ + U8 CounterType; /* 0x04 */ + U8 ThresholdWindow; /* 0x05 */ + U8 TimeUnits; /* 0x06 */ + U8 Reserved3; /* 0x07 */ + U32 EventThreshold; /* 0x08 */ + U16 ThresholdFlags; /* 0x0C */ + U16 Reserved4; /* 0x0E */ +} MPI2_SASPHY3_PHY_EVENT_CONFIG, MPI2_POINTER PTR_MPI2_SASPHY3_PHY_EVENT_CONFIG, + Mpi2SasPhy3PhyEventConfig_t, MPI2_POINTER pMpi2SasPhy3PhyEventConfig_t; + +/* values for PhyEventCode field */ +#define MPI2_SASPHY3_EVENT_CODE_NO_EVENT (0x00) +#define MPI2_SASPHY3_EVENT_CODE_INVALID_DWORD (0x01) +#define MPI2_SASPHY3_EVENT_CODE_RUNNING_DISPARITY_ERROR (0x02) +#define MPI2_SASPHY3_EVENT_CODE_LOSS_DWORD_SYNC (0x03) +#define MPI2_SASPHY3_EVENT_CODE_PHY_RESET_PROBLEM (0x04) +#define MPI2_SASPHY3_EVENT_CODE_ELASTICITY_BUF_OVERFLOW (0x05) +#define MPI2_SASPHY3_EVENT_CODE_RX_ERROR (0x06) +#define MPI2_SASPHY3_EVENT_CODE_RX_ADDR_FRAME_ERROR (0x20) +#define MPI2_SASPHY3_EVENT_CODE_TX_AC_OPEN_REJECT (0x21) +#define MPI2_SASPHY3_EVENT_CODE_RX_AC_OPEN_REJECT (0x22) +#define MPI2_SASPHY3_EVENT_CODE_TX_RC_OPEN_REJECT (0x23) +#define MPI2_SASPHY3_EVENT_CODE_RX_RC_OPEN_REJECT (0x24) +#define MPI2_SASPHY3_EVENT_CODE_RX_AIP_PARTIAL_WAITING_ON (0x25) +#define MPI2_SASPHY3_EVENT_CODE_RX_AIP_CONNECT_WAITING_ON (0x26) +#define MPI2_SASPHY3_EVENT_CODE_TX_BREAK (0x27) +#define MPI2_SASPHY3_EVENT_CODE_RX_BREAK (0x28) +#define MPI2_SASPHY3_EVENT_CODE_BREAK_TIMEOUT (0x29) +#define MPI2_SASPHY3_EVENT_CODE_CONNECTION (0x2A) +#define MPI2_SASPHY3_EVENT_CODE_PEAKTX_PATHWAY_BLOCKED (0x2B) +#define MPI2_SASPHY3_EVENT_CODE_PEAKTX_ARB_WAIT_TIME (0x2C) +#define MPI2_SASPHY3_EVENT_CODE_PEAK_ARB_WAIT_TIME (0x2D) +#define MPI2_SASPHY3_EVENT_CODE_PEAK_CONNECT_TIME (0x2E) +#define MPI2_SASPHY3_EVENT_CODE_TX_SSP_FRAMES (0x40) +#define MPI2_SASPHY3_EVENT_CODE_RX_SSP_FRAMES (0x41) +#define MPI2_SASPHY3_EVENT_CODE_TX_SSP_ERROR_FRAMES (0x42) +#define MPI2_SASPHY3_EVENT_CODE_RX_SSP_ERROR_FRAMES (0x43) +#define MPI2_SASPHY3_EVENT_CODE_TX_CREDIT_BLOCKED (0x44) +#define MPI2_SASPHY3_EVENT_CODE_RX_CREDIT_BLOCKED (0x45) +#define MPI2_SASPHY3_EVENT_CODE_TX_SATA_FRAMES (0x50) +#define MPI2_SASPHY3_EVENT_CODE_RX_SATA_FRAMES (0x51) +#define MPI2_SASPHY3_EVENT_CODE_SATA_OVERFLOW (0x52) +#define MPI2_SASPHY3_EVENT_CODE_TX_SMP_FRAMES (0x60) +#define MPI2_SASPHY3_EVENT_CODE_RX_SMP_FRAMES (0x61) +#define MPI2_SASPHY3_EVENT_CODE_RX_SMP_ERROR_FRAMES (0x63) +#define MPI2_SASPHY3_EVENT_CODE_HOTPLUG_TIMEOUT (0xD0) +#define MPI2_SASPHY3_EVENT_CODE_MISALIGNED_MUX_PRIMITIVE (0xD1) +#define MPI2_SASPHY3_EVENT_CODE_RX_AIP (0xD2) + +/* values for the CounterType field */ +#define MPI2_SASPHY3_COUNTER_TYPE_WRAPPING (0x00) +#define MPI2_SASPHY3_COUNTER_TYPE_SATURATING (0x01) +#define MPI2_SASPHY3_COUNTER_TYPE_PEAK_VALUE (0x02) + +/* values for the TimeUnits field */ +#define MPI2_SASPHY3_TIME_UNITS_10_MICROSECONDS (0x00) +#define MPI2_SASPHY3_TIME_UNITS_100_MICROSECONDS (0x01) +#define MPI2_SASPHY3_TIME_UNITS_1_MILLISECOND (0x02) +#define MPI2_SASPHY3_TIME_UNITS_10_MILLISECONDS (0x03) + +/* values for the ThresholdFlags field */ +#define MPI2_SASPHY3_TFLAGS_PHY_RESET (0x0002) +#define MPI2_SASPHY3_TFLAGS_EVENT_NOTIFY (0x0001) + +/* + * Host code (drivers, BIOS, utilities, etc.) should leave this define set to + * one and check Header.ExtPageLength or NumPhyEvents at runtime. + */ +#ifndef MPI2_SASPHY3_PHY_EVENT_MAX +#define MPI2_SASPHY3_PHY_EVENT_MAX (1) +#endif + +typedef struct _MPI2_CONFIG_PAGE_SAS_PHY_3 { + MPI2_CONFIG_EXTENDED_PAGE_HEADER Header; /* 0x00 */ + U32 Reserved1; /* 0x08 */ + U8 NumPhyEvents; /* 0x0C */ + U8 Reserved2; /* 0x0D */ + U16 Reserved3; /* 0x0E */ + MPI2_SASPHY3_PHY_EVENT_CONFIG PhyEventConfig + [MPI2_SASPHY3_PHY_EVENT_MAX]; /* 0x10 */ +} MPI2_CONFIG_PAGE_SAS_PHY_3, MPI2_POINTER PTR_MPI2_CONFIG_PAGE_SAS_PHY_3, + Mpi2SasPhyPage3_t, MPI2_POINTER pMpi2SasPhyPage3_t; + +#define MPI2_SASPHY3_PAGEVERSION (0x00) + + /**************************************************************************** * SAS Port Config Pages ****************************************************************************/ diff --git a/drivers/scsi/mpt2sas/mpi/mpi2_history.txt b/drivers/scsi/mpt2sas/mpi/mpi2_history.txt new file mode 100644 index 000000000000..65fcaa31cb30 --- /dev/null +++ b/drivers/scsi/mpt2sas/mpi/mpi2_history.txt @@ -0,0 +1,334 @@ + ============================== + Fusion-MPT MPI 2.0 Header File Change History + ============================== + + Copyright (c) 2000-2009 LSI Corporation. + + --------------------------------------- + Header Set Release Version: 02.00.12 + Header Set Release Date: 05-06-09 + --------------------------------------- + + Filename Current version Prior version + ---------- --------------- ------------- + mpi2.h 02.00.12 02.00.11 + mpi2_cnfg.h 02.00.11 02.00.10 + mpi2_init.h 02.00.07 02.00.06 + mpi2_ioc.h 02.00.11 02.00.10 + mpi2_raid.h 02.00.03 02.00.03 + mpi2_sas.h 02.00.02 02.00.02 + mpi2_targ.h 02.00.03 02.00.03 + mpi2_tool.h 02.00.03 02.00.02 + mpi2_type.h 02.00.00 02.00.00 + mpi2_ra.h 02.00.00 + mpi2_history.txt 02.00.11 02.00.12 + + + * Date Version Description + * -------- -------- ------------------------------------------------------ + +mpi2.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 06-04-07 02.00.01 Bumped MPI2_HEADER_VERSION_UNIT. + * 06-26-07 02.00.02 Bumped MPI2_HEADER_VERSION_UNIT. + * 08-31-07 02.00.03 Bumped MPI2_HEADER_VERSION_UNIT. + * Moved ReplyPostHostIndex register to offset 0x6C of the + * MPI2_SYSTEM_INTERFACE_REGS and modified the define for + * MPI2_REPLY_POST_HOST_INDEX_OFFSET. + * Added union of request descriptors. + * Added union of reply descriptors. + * 10-31-07 02.00.04 Bumped MPI2_HEADER_VERSION_UNIT. + * Added define for MPI2_VERSION_02_00. + * Fixed the size of the FunctionDependent5 field in the + * MPI2_DEFAULT_REPLY structure. + * 12-18-07 02.00.05 Bumped MPI2_HEADER_VERSION_UNIT. + * Removed the MPI-defined Fault Codes and extended the + * product specific codes up to 0xEFFF. + * Added a sixth key value for the WriteSequence register + * and changed the flush value to 0x0. + * Added message function codes for Diagnostic Buffer Post + * and Diagnsotic Release. + * New IOCStatus define: MPI2_IOCSTATUS_DIAGNOSTIC_RELEASED + * Moved MPI2_VERSION_UNION from mpi2_ioc.h. + * 02-29-08 02.00.06 Bumped MPI2_HEADER_VERSION_UNIT. + * 03-03-08 02.00.07 Bumped MPI2_HEADER_VERSION_UNIT. + * 05-21-08 02.00.08 Bumped MPI2_HEADER_VERSION_UNIT. + * Added #defines for marking a reply descriptor as unused. + * 06-27-08 02.00.09 Bumped MPI2_HEADER_VERSION_UNIT. + * 10-02-08 02.00.10 Bumped MPI2_HEADER_VERSION_UNIT. + * Moved LUN field defines from mpi2_init.h. + * 01-19-09 02.00.11 Bumped MPI2_HEADER_VERSION_UNIT. + * 05-06-09 02.00.12 Bumped MPI2_HEADER_VERSION_UNIT. + * In all request and reply descriptors, replaced VF_ID + * field with MSIxIndex field. + * Removed DevHandle field from + * MPI2_SCSI_IO_SUCCESS_REPLY_DESCRIPTOR and made those + * bytes reserved. + * Added RAID Accelerator functionality. + * -------------------------------------------------------------------------- + +mpi2_cnfg.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 06-04-07 02.00.01 Added defines for SAS IO Unit Page 2 PhyFlags. + * Added Manufacturing Page 11. + * Added MPI2_SAS_EXPANDER0_FLAGS_CONNECTOR_END_DEVICE + * define. + * 06-26-07 02.00.02 Adding generic structure for product-specific + * Manufacturing pages: MPI2_CONFIG_PAGE_MANUFACTURING_PS. + * Rework of BIOS Page 2 configuration page. + * Fixed MPI2_BIOSPAGE2_BOOT_DEVICE to be a union of the + * forms. + * Added configuration pages IOC Page 8 and Driver + * Persistent Mapping Page 0. + * 08-31-07 02.00.03 Modified configuration pages dealing with Integrated + * RAID (Manufacturing Page 4, RAID Volume Pages 0 and 1, + * RAID Physical Disk Pages 0 and 1, RAID Configuration + * Page 0). + * Added new value for AccessStatus field of SAS Device + * Page 0 (_SATA_NEEDS_INITIALIZATION). + * 10-31-07 02.00.04 Added missing SEPDevHandle field to + * MPI2_CONFIG_PAGE_SAS_ENCLOSURE_0. + * 12-18-07 02.00.05 Modified IO Unit Page 0 to use 32-bit version fields for + * NVDATA. + * Modified IOC Page 7 to use masks and added field for + * SASBroadcastPrimitiveMasks. + * Added MPI2_CONFIG_PAGE_BIOS_4. + * Added MPI2_CONFIG_PAGE_LOG_0. + * 02-29-08 02.00.06 Modified various names to make them 32-character unique. + * Added SAS Device IDs. + * Updated Integrated RAID configuration pages including + * Manufacturing Page 4, IOC Page 6, and RAID Configuration + * Page 0. + * 05-21-08 02.00.07 Added define MPI2_MANPAGE4_MIX_SSD_SAS_SATA. + * Added define MPI2_MANPAGE4_PHYSDISK_128MB_COERCION. + * Fixed define MPI2_IOCPAGE8_FLAGS_ENCLOSURE_SLOT_MAPPING. + * Added missing MaxNumRoutedSasAddresses field to + * MPI2_CONFIG_PAGE_EXPANDER_0. + * Added SAS Port Page 0. + * Modified structure layout for + * MPI2_CONFIG_PAGE_DRIVER_MAPPING_0. + * 06-27-08 02.00.08 Changed MPI2_CONFIG_PAGE_RD_PDISK_1 to use + * MPI2_RAID_PHYS_DISK1_PATH_MAX to size the array. + * 10-02-08 02.00.09 Changed MPI2_RAID_PGAD_CONFIGNUM_MASK from 0x0000FFFF + * to 0x000000FF. + * Added two new values for the Physical Disk Coercion Size + * bits in the Flags field of Manufacturing Page 4. + * Added product-specific Manufacturing pages 16 to 31. + * Modified Flags bits for controlling write cache on SATA + * drives in IO Unit Page 1. + * Added new bit to AdditionalControlFlags of SAS IO Unit + * Page 1 to control Invalid Topology Correction. + * Added SupportedPhysDisks field to RAID Volume Page 1 and + * added related defines. + * Added additional defines for RAID Volume Page 0 + * VolumeStatusFlags field. + * Modified meaning of RAID Volume Page 0 VolumeSettings + * define for auto-configure of hot-swap drives. + * Added PhysDiskAttributes field (and related defines) to + * RAID Physical Disk Page 0. + * Added MPI2_SAS_PHYINFO_PHY_VACANT define. + * Added three new DiscoveryStatus bits for SAS IO Unit + * Page 0 and SAS Expander Page 0. + * Removed multiplexing information from SAS IO Unit pages. + * Added BootDeviceWaitTime field to SAS IO Unit Page 4. + * Removed Zone Address Resolved bit from PhyInfo and from + * Expander Page 0 Flags field. + * Added two new AccessStatus values to SAS Device Page 0 + * for indicating routing problems. Added 3 reserved words + * to this page. + * 01-19-09 02.00.10 Fixed defines for GPIOVal field of IO Unit Page 3. + * Inserted missing reserved field into structure for IOC + * Page 6. + * Added more pending task bits to RAID Volume Page 0 + * VolumeStatusFlags defines. + * Added MPI2_PHYSDISK0_STATUS_FLAG_NOT_CERTIFIED define. + * Added a new DiscoveryStatus bit for SAS IO Unit Page 0 + * and SAS Expander Page 0 to flag a downstream initiator + * when in simplified routing mode. + * Removed SATA Init Failure defines for DiscoveryStatus + * fields of SAS IO Unit Page 0 and SAS Expander Page 0. + * Added MPI2_SAS_DEVICE0_ASTATUS_DEVICE_BLOCKED define. + * Added PortGroups, DmaGroup, and ControlGroup fields to + * SAS Device Page 0. + * 05-06-09 02.00.11 Added structures and defines for IO Unit Page 5 and IO + * Unit Page 6. + * Added expander reduced functionality data to SAS + * Expander Page 0. + * Added SAS PHY Page 2 and SAS PHY Page 3. + * -------------------------------------------------------------------------- + +mpi2_init.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 10-31-07 02.00.01 Fixed name for pMpi2SCSITaskManagementRequest_t. + * 12-18-07 02.00.02 Modified Task Management Target Reset Method defines. + * 02-29-08 02.00.03 Added Query Task Set and Query Unit Attention. + * 03-03-08 02.00.04 Fixed name of struct _MPI2_SCSI_TASK_MANAGE_REPLY. + * 05-21-08 02.00.05 Fixed typo in name of Mpi2SepRequest_t. + * 10-02-08 02.00.06 Removed Untagged and No Disconnect values from SCSI IO + * Control field Task Attribute flags. + * Moved LUN field defines to mpi2.h becasue they are + * common to many structures. + * 05-06-09 02.00.07 Changed task management type of Query Unit Attention to + * Query Asynchronous Event. + * Defined two new bits in the SlotStatus field of the SCSI + * Enclosure Processor Request and Reply. + * -------------------------------------------------------------------------- + +mpi2_ioc.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 06-04-07 02.00.01 In IOCFacts Reply structure, renamed MaxDevices to + * MaxTargets. + * Added TotalImageSize field to FWDownload Request. + * Added reserved words to FWUpload Request. + * 06-26-07 02.00.02 Added IR Configuration Change List Event. + * 08-31-07 02.00.03 Removed SystemReplyQueueDepth field from the IOCInit + * request and replaced it with + * ReplyDescriptorPostQueueDepth and ReplyFreeQueueDepth. + * Replaced the MinReplyQueueDepth field of the IOCFacts + * reply with MaxReplyDescriptorPostQueueDepth. + * Added MPI2_RDPQ_DEPTH_MIN define to specify the minimum + * depth for the Reply Descriptor Post Queue. + * Added SASAddress field to Initiator Device Table + * Overflow Event data. + * 10-31-07 02.00.04 Added ReasonCode MPI2_EVENT_SAS_INIT_RC_NOT_RESPONDING + * for SAS Initiator Device Status Change Event data. + * Modified Reason Code defines for SAS Topology Change + * List Event data, including adding a bit for PHY Vacant + * status, and adding a mask for the Reason Code. + * Added define for + * MPI2_EVENT_SAS_TOPO_ES_DELAY_NOT_RESPONDING. + * Added define for MPI2_EXT_IMAGE_TYPE_MEGARAID. + * 12-18-07 02.00.05 Added Boot Status defines for the IOCExceptions field of + * the IOCFacts Reply. + * Removed MPI2_IOCFACTS_CAPABILITY_EXTENDED_BUFFER define. + * Moved MPI2_VERSION_UNION to mpi2.h. + * Changed MPI2_EVENT_NOTIFICATION_REQUEST to use masks + * instead of enables, and added SASBroadcastPrimitiveMasks + * field. + * Added Log Entry Added Event and related structure. + * 02-29-08 02.00.06 Added define MPI2_IOCFACTS_CAPABILITY_INTEGRATED_RAID. + * Removed define MPI2_IOCFACTS_PROTOCOL_SMP_TARGET. + * Added MaxVolumes and MaxPersistentEntries fields to + * IOCFacts reply. + * Added ProtocalFlags and IOCCapabilities fields to + * MPI2_FW_IMAGE_HEADER. + * Removed MPI2_PORTENABLE_FLAGS_ENABLE_SINGLE_PORT. + * 03-03-08 02.00.07 Fixed MPI2_FW_IMAGE_HEADER by changing Reserved26 to + * a U16 (from a U32). + * Removed extra 's' from EventMasks name. + * 06-27-08 02.00.08 Fixed an offset in a comment. + * 10-02-08 02.00.09 Removed SystemReplyFrameSize from MPI2_IOC_INIT_REQUEST. + * Removed CurReplyFrameSize from MPI2_IOC_FACTS_REPLY and + * renamed MinReplyFrameSize to ReplyFrameSize. + * Added MPI2_IOCFACTS_EXCEPT_IR_FOREIGN_CONFIG_MAX. + * Added two new RAIDOperation values for Integrated RAID + * Operations Status Event data. + * Added four new IR Configuration Change List Event data + * ReasonCode values. + * Added two new ReasonCode defines for SAS Device Status + * Change Event data. + * Added three new DiscoveryStatus bits for the SAS + * Discovery event data. + * Added Multiplexing Status Change bit to the PhyStatus + * field of the SAS Topology Change List event data. + * Removed define for MPI2_INIT_IMAGE_BOOTFLAGS_XMEMCOPY. + * BootFlags are now product-specific. + * Added defines for the indivdual signature bytes + * for MPI2_INIT_IMAGE_FOOTER. + * 01-19-09 02.00.10 Added MPI2_IOCFACTS_CAPABILITY_EVENT_REPLAY define. + * Added MPI2_EVENT_SAS_DISC_DS_DOWNSTREAM_INITIATOR + * define. + * Added MPI2_EVENT_SAS_DEV_STAT_RC_SATA_INIT_FAILURE + * define. + * Removed MPI2_EVENT_SAS_DISC_DS_SATA_INIT_FAILURE define. + * 05-06-09 02.00.11 Added MPI2_IOCFACTS_CAPABILITY_RAID_ACCELERATOR define. + * Added MPI2_IOCFACTS_CAPABILITY_MSI_X_INDEX define. + * Added two new reason codes for SAS Device Status Change + * Event. + * Added new event: SAS PHY Counter. + * -------------------------------------------------------------------------- + +mpi2_raid.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 08-31-07 02.00.01 Modifications to RAID Action request and reply, + * including the Actions and ActionData. + * 02-29-08 02.00.02 Added MPI2_RAID_ACTION_ADATA_DISABL_FULL_REBUILD. + * 05-21-08 02.00.03 Added MPI2_RAID_VOL_CREATION_NUM_PHYSDISKS so that + * the PhysDisk array in MPI2_RAID_VOLUME_CREATION_STRUCT + * can be sized by the build environment. + * -------------------------------------------------------------------------- + +mpi2_sas.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 06-26-07 02.00.01 Added Clear All Persistent Operation to SAS IO Unit + * Control Request. + * 10-02-08 02.00.02 Added Set IOC Parameter Operation to SAS IO Unit Control + * Request. + * -------------------------------------------------------------------------- + +mpi2_targ.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 08-31-07 02.00.01 Added Command Buffer Data Location Address Space bits to + * BufferPostFlags field of CommandBufferPostBase Request. + * 02-29-08 02.00.02 Modified various names to make them 32-character unique. + * 10-02-08 02.00.03 Removed NextCmdBufferOffset from + * MPI2_TARGET_CMD_BUF_POST_BASE_REQUEST. + * Target Status Send Request only takes a single SGE for + * response data. + * -------------------------------------------------------------------------- + +mpi2_tool.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * 12-18-07 02.00.01 Added Diagnostic Buffer Post and Diagnostic Release + * structures and defines. + * 02-29-08 02.00.02 Modified various names to make them 32-character unique. + * 05-06-09 02.00.03 Added ISTWI Read Write Tool and Diagnostic CLI Tool. + * -------------------------------------------------------------------------- + +mpi2_type.h + * 04-30-07 02.00.00 Corresponds to Fusion-MPT MPI Specification Rev A. + * -------------------------------------------------------------------------- + +mpi2_ra.h + * 05-06-09 02.00.00 Initial version. + * -------------------------------------------------------------------------- + +mpi2_history.txt Parts list history + +Filename 02.00.12 +---------- -------- +mpi2.h 02.00.12 +mpi2_cnfg.h 02.00.11 +mpi2_init.h 02.00.07 +mpi2_ioc.h 02.00.11 +mpi2_raid.h 02.00.03 +mpi2_sas.h 02.00.02 +mpi2_targ.h 02.00.03 +mpi2_tool.h 02.00.03 +mpi2_type.h 02.00.00 +mpi2_ra.h 02.00.00 + +Filename 02.00.11 02.00.10 02.00.09 02.00.08 02.00.07 02.00.06 +---------- -------- -------- -------- -------- -------- -------- +mpi2.h 02.00.11 02.00.10 02.00.09 02.00.08 02.00.07 02.00.06 +mpi2_cnfg.h 02.00.10 02.00.09 02.00.08 02.00.07 02.00.06 02.00.06 +mpi2_init.h 02.00.06 02.00.06 02.00.05 02.00.05 02.00.04 02.00.03 +mpi2_ioc.h 02.00.10 02.00.09 02.00.08 02.00.07 02.00.07 02.00.06 +mpi2_raid.h 02.00.03 02.00.03 02.00.03 02.00.03 02.00.02 02.00.02 +mpi2_sas.h 02.00.02 02.00.02 02.00.01 02.00.01 02.00.01 02.00.01 +mpi2_targ.h 02.00.03 02.00.03 02.00.02 02.00.02 02.00.02 02.00.02 +mpi2_tool.h 02.00.02 02.00.02 02.00.02 02.00.02 02.00.02 02.00.02 +mpi2_type.h 02.00.00 02.00.00 02.00.00 02.00.00 02.00.00 02.00.00 + +Filename 02.00.05 02.00.04 02.00.03 02.00.02 02.00.01 02.00.00 +---------- -------- -------- -------- -------- -------- -------- +mpi2.h 02.00.05 02.00.04 02.00.03 02.00.02 02.00.01 02.00.00 +mpi2_cnfg.h 02.00.05 02.00.04 02.00.03 02.00.02 02.00.01 02.00.00 +mpi2_init.h 02.00.02 02.00.01 02.00.00 02.00.00 02.00.00 02.00.00 +mpi2_ioc.h 02.00.05 02.00.04 02.00.03 02.00.02 02.00.01 02.00.00 +mpi2_raid.h 02.00.01 02.00.01 02.00.01 02.00.00 02.00.00 02.00.00 +mpi2_sas.h 02.00.01 02.00.01 02.00.01 02.00.01 02.00.00 02.00.00 +mpi2_targ.h 02.00.01 02.00.01 02.00.01 02.00.00 02.00.00 02.00.00 +mpi2_tool.h 02.00.01 02.00.00 02.00.00 02.00.00 02.00.00 02.00.00 +mpi2_type.h 02.00.00 02.00.00 02.00.00 02.00.00 02.00.00 02.00.00 + diff --git a/drivers/scsi/mpt2sas/mpi/mpi2_init.h b/drivers/scsi/mpt2sas/mpi/mpi2_init.h index f1115f0f0eb2..563e56d2e945 100644 --- a/drivers/scsi/mpt2sas/mpi/mpi2_init.h +++ b/drivers/scsi/mpt2sas/mpi/mpi2_init.h @@ -1,12 +1,12 @@ /* - * Copyright (c) 2000-2008 LSI Corporation. + * Copyright (c) 2000-2009 LSI Corporation. * * * Name: mpi2_init.h * Title: MPI SCSI initiator mode messages and structures * Creation Date: June 23, 2006 * - * mpi2_init.h Version: 02.00.06 + * mpi2_init.h Version: 02.00.07 * * Version History * --------------- @@ -23,6 +23,10 @@ * Control field Task Attribute flags. * Moved LUN field defines to mpi2.h becasue they are * common to many structures. + * 05-06-09 02.00.07 Changed task management type of Query Unit Attention to + * Query Asynchronous Event. + * Defined two new bits in the SlotStatus field of the SCSI + * Enclosure Processor Request and Reply. * -------------------------------------------------------------------------- */ @@ -289,7 +293,11 @@ typedef struct _MPI2_SCSI_TASK_MANAGE_REQUEST #define MPI2_SCSITASKMGMT_TASKTYPE_QUERY_TASK (0x07) #define MPI2_SCSITASKMGMT_TASKTYPE_CLR_ACA (0x08) #define MPI2_SCSITASKMGMT_TASKTYPE_QRY_TASK_SET (0x09) -#define MPI2_SCSITASKMGMT_TASKTYPE_QRY_UNIT_ATTENTION (0x0A) +#define MPI2_SCSITASKMGMT_TASKTYPE_QRY_ASYNC_EVENT (0x0A) + +/* obsolete TaskType name */ +#define MPI2_SCSITASKMGMT_TASKTYPE_QRY_UNIT_ATTENTION \ + (MPI2_SCSITASKMGMT_TASKTYPE_QRY_ASYNC_EVENT) /* MsgFlags bits */ @@ -375,6 +383,8 @@ typedef struct _MPI2_SEP_REQUEST #define MPI2_SEP_REQ_SLOTSTATUS_HOT_SPARE (0x00000100) #define MPI2_SEP_REQ_SLOTSTATUS_UNCONFIGURED (0x00000080) #define MPI2_SEP_REQ_SLOTSTATUS_PREDICTED_FAULT (0x00000040) +#define MPI2_SEP_REQ_SLOTSTATUS_IN_CRITICAL_ARRAY (0x00000010) +#define MPI2_SEP_REQ_SLOTSTATUS_IN_FAILED_ARRAY (0x00000008) #define MPI2_SEP_REQ_SLOTSTATUS_DEV_REBUILDING (0x00000004) #define MPI2_SEP_REQ_SLOTSTATUS_DEV_FAULTY (0x00000002) #define MPI2_SEP_REQ_SLOTSTATUS_NO_ERROR (0x00000001) @@ -410,6 +420,8 @@ typedef struct _MPI2_SEP_REPLY #define MPI2_SEP_REPLY_SLOTSTATUS_HOT_SPARE (0x00000100) #define MPI2_SEP_REPLY_SLOTSTATUS_UNCONFIGURED (0x00000080) #define MPI2_SEP_REPLY_SLOTSTATUS_PREDICTED_FAULT (0x00000040) +#define MPI2_SEP_REPLY_SLOTSTATUS_IN_CRITICAL_ARRAY (0x00000010) +#define MPI2_SEP_REPLY_SLOTSTATUS_IN_FAILED_ARRAY (0x00000008) #define MPI2_SEP_REPLY_SLOTSTATUS_DEV_REBUILDING (0x00000004) #define MPI2_SEP_REPLY_SLOTSTATUS_DEV_FAULTY (0x00000002) #define MPI2_SEP_REPLY_SLOTSTATUS_NO_ERROR (0x00000001) diff --git a/drivers/scsi/mpt2sas/mpi/mpi2_ioc.h b/drivers/scsi/mpt2sas/mpi/mpi2_ioc.h index 8c5d81870c03..c294128bdeb4 100644 --- a/drivers/scsi/mpt2sas/mpi/mpi2_ioc.h +++ b/drivers/scsi/mpt2sas/mpi/mpi2_ioc.h @@ -6,7 +6,7 @@ * Title: MPI IOC, Port, Event, FW Download, and FW Upload messages * Creation Date: October 11, 2006 * - * mpi2_ioc.h Version: 02.00.10 + * mpi2_ioc.h Version: 02.00.11 * * Version History * --------------- @@ -79,6 +79,11 @@ * Added MPI2_EVENT_SAS_DEV_STAT_RC_SATA_INIT_FAILURE * define. * Removed MPI2_EVENT_SAS_DISC_DS_SATA_INIT_FAILURE define. + * 05-06-09 02.00.11 Added MPI2_IOCFACTS_CAPABILITY_RAID_ACCELERATOR define. + * Added MPI2_IOCFACTS_CAPABILITY_MSI_X_INDEX define. + * Added two new reason codes for SAS Device Status Change + * Event. + * Added new event: SAS PHY Counter. * -------------------------------------------------------------------------- */ @@ -261,6 +266,8 @@ typedef struct _MPI2_IOC_FACTS_REPLY /* ProductID field uses MPI2_FW_HEADER_PID_ */ /* IOCCapabilities */ +#define MPI2_IOCFACTS_CAPABILITY_MSI_X_INDEX (0x00008000) +#define MPI2_IOCFACTS_CAPABILITY_RAID_ACCELERATOR (0x00004000) #define MPI2_IOCFACTS_CAPABILITY_EVENT_REPLAY (0x00002000) #define MPI2_IOCFACTS_CAPABILITY_INTEGRATED_RAID (0x00001000) #define MPI2_IOCFACTS_CAPABILITY_TLR (0x00000800) @@ -440,6 +447,7 @@ typedef struct _MPI2_EVENT_NOTIFICATION_REPLY #define MPI2_EVENT_IR_PHYSICAL_DISK (0x001F) #define MPI2_EVENT_IR_CONFIGURATION_CHANGE_LIST (0x0020) #define MPI2_EVENT_LOG_ENTRY_ADDED (0x0021) +#define MPI2_EVENT_SAS_PHY_COUNTER (0x0022) /* Log Entry Added Event data */ @@ -502,17 +510,19 @@ typedef struct _MPI2_EVENT_DATA_SAS_DEVICE_STATUS_CHANGE MPI2_POINTER pMpi2EventDataSasDeviceStatusChange_t; /* SAS Device Status Change Event data ReasonCode values */ -#define MPI2_EVENT_SAS_DEV_STAT_RC_SMART_DATA (0x05) -#define MPI2_EVENT_SAS_DEV_STAT_RC_UNSUPPORTED (0x07) -#define MPI2_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET (0x08) -#define MPI2_EVENT_SAS_DEV_STAT_RC_TASK_ABORT_INTERNAL (0x09) -#define MPI2_EVENT_SAS_DEV_STAT_RC_ABORT_TASK_SET_INTERNAL (0x0A) -#define MPI2_EVENT_SAS_DEV_STAT_RC_CLEAR_TASK_SET_INTERNAL (0x0B) -#define MPI2_EVENT_SAS_DEV_STAT_RC_QUERY_TASK_INTERNAL (0x0C) -#define MPI2_EVENT_SAS_DEV_STAT_RC_ASYNC_NOTIFICATION (0x0D) -#define MPI2_EVENT_SAS_DEV_STAT_RC_CMP_INTERNAL_DEV_RESET (0x0E) -#define MPI2_EVENT_SAS_DEV_STAT_RC_CMP_TASK_ABORT_INTERNAL (0x0F) -#define MPI2_EVENT_SAS_DEV_STAT_RC_SATA_INIT_FAILURE (0x10) +#define MPI2_EVENT_SAS_DEV_STAT_RC_SMART_DATA (0x05) +#define MPI2_EVENT_SAS_DEV_STAT_RC_UNSUPPORTED (0x07) +#define MPI2_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET (0x08) +#define MPI2_EVENT_SAS_DEV_STAT_RC_TASK_ABORT_INTERNAL (0x09) +#define MPI2_EVENT_SAS_DEV_STAT_RC_ABORT_TASK_SET_INTERNAL (0x0A) +#define MPI2_EVENT_SAS_DEV_STAT_RC_CLEAR_TASK_SET_INTERNAL (0x0B) +#define MPI2_EVENT_SAS_DEV_STAT_RC_QUERY_TASK_INTERNAL (0x0C) +#define MPI2_EVENT_SAS_DEV_STAT_RC_ASYNC_NOTIFICATION (0x0D) +#define MPI2_EVENT_SAS_DEV_STAT_RC_CMP_INTERNAL_DEV_RESET (0x0E) +#define MPI2_EVENT_SAS_DEV_STAT_RC_CMP_TASK_ABORT_INTERNAL (0x0F) +#define MPI2_EVENT_SAS_DEV_STAT_RC_SATA_INIT_FAILURE (0x10) +#define MPI2_EVENT_SAS_DEV_STAT_RC_EXPANDER_REDUCED_FUNCTIONALITY (0x11) +#define MPI2_EVENT_SAS_DEV_STAT_RC_CMP_EXPANDER_REDUCED_FUNCTIONALITY (0x12) /* Integrated RAID Operation Status Event data */ @@ -822,6 +832,37 @@ typedef struct _MPI2_EVENT_DATA_SAS_ENCL_DEV_STATUS_CHANGE #define MPI2_EVENT_SAS_ENCL_RC_NOT_RESPONDING (0x02) +/* SAS PHY Counter Event data */ + +typedef struct _MPI2_EVENT_DATA_SAS_PHY_COUNTER { + U64 TimeStamp; /* 0x00 */ + U32 Reserved1; /* 0x08 */ + U8 PhyEventCode; /* 0x0C */ + U8 PhyNum; /* 0x0D */ + U16 Reserved2; /* 0x0E */ + U32 PhyEventInfo; /* 0x10 */ + U8 CounterType; /* 0x14 */ + U8 ThresholdWindow; /* 0x15 */ + U8 TimeUnits; /* 0x16 */ + U8 Reserved3; /* 0x17 */ + U32 EventThreshold; /* 0x18 */ + U16 ThresholdFlags; /* 0x1C */ + U16 Reserved4; /* 0x1E */ +} MPI2_EVENT_DATA_SAS_PHY_COUNTER, + MPI2_POINTER PTR_MPI2_EVENT_DATA_SAS_PHY_COUNTER, + Mpi2EventDataSasPhyCounter_t, MPI2_POINTER pMpi2EventDataSasPhyCounter_t; + +/* use MPI2_SASPHY3_EVENT_CODE_ values from mpi2_cnfg.h for the + * PhyEventCode field + * use MPI2_SASPHY3_COUNTER_TYPE_ values from mpi2_cnfg.h for the + * CounterType field + * use MPI2_SASPHY3_TIME_UNITS_ values from mpi2_cnfg.h for the + * TimeUnits field + * use MPI2_SASPHY3_TFLAGS_ values from mpi2_cnfg.h for the + * ThresholdFlags field + * */ + + /**************************************************************************** * EventAck message ****************************************************************************/ diff --git a/drivers/scsi/mpt2sas/mpi/mpi2_tool.h b/drivers/scsi/mpt2sas/mpi/mpi2_tool.h index 2ff4e936bd39..007e950f7bfa 100644 --- a/drivers/scsi/mpt2sas/mpi/mpi2_tool.h +++ b/drivers/scsi/mpt2sas/mpi/mpi2_tool.h @@ -1,12 +1,12 @@ /* - * Copyright (c) 2000-2008 LSI Corporation. + * Copyright (c) 2000-2009 LSI Corporation. * * * Name: mpi2_tool.h * Title: MPI diagnostic tool structures and definitions * Creation Date: March 26, 2007 * - * mpi2_tool.h Version: 02.00.02 + * mpi2_tool.h Version: 02.00.03 * * Version History * --------------- @@ -17,6 +17,7 @@ * 12-18-07 02.00.01 Added Diagnostic Buffer Post and Diagnostic Release * structures and defines. * 02-29-08 02.00.02 Modified various names to make them 32-character unique. + * 05-06-09 02.00.03 Added ISTWI Read Write Tool and Diagnostic CLI Tool. * -------------------------------------------------------------------------- */ @@ -32,7 +33,10 @@ /* defines for the Tools */ #define MPI2_TOOLBOX_CLEAN_TOOL (0x00) #define MPI2_TOOLBOX_MEMORY_MOVE_TOOL (0x01) +#define MPI2_TOOLBOX_ISTWI_READ_WRITE_TOOL (0x03) #define MPI2_TOOLBOX_BEACON_TOOL (0x05) +#define MPI2_TOOLBOX_DIAGNOSTIC_CLI_TOOL (0x06) + /**************************************************************************** * Toolbox reply @@ -112,6 +116,77 @@ typedef struct _MPI2_TOOLBOX_MEM_MOVE_REQUEST /**************************************************************************** +* Toolbox ISTWI Read Write Tool +****************************************************************************/ + +/* Toolbox ISTWI Read Write Tool request message */ +typedef struct _MPI2_TOOLBOX_ISTWI_READ_WRITE_REQUEST { + U8 Tool; /* 0x00 */ + U8 Reserved1; /* 0x01 */ + U8 ChainOffset; /* 0x02 */ + U8 Function; /* 0x03 */ + U16 Reserved2; /* 0x04 */ + U8 Reserved3; /* 0x06 */ + U8 MsgFlags; /* 0x07 */ + U8 VP_ID; /* 0x08 */ + U8 VF_ID; /* 0x09 */ + U16 Reserved4; /* 0x0A */ + U32 Reserved5; /* 0x0C */ + U32 Reserved6; /* 0x10 */ + U8 DevIndex; /* 0x14 */ + U8 Action; /* 0x15 */ + U8 SGLFlags; /* 0x16 */ + U8 Reserved7; /* 0x17 */ + U16 TxDataLength; /* 0x18 */ + U16 RxDataLength; /* 0x1A */ + U32 Reserved8; /* 0x1C */ + U32 Reserved9; /* 0x20 */ + U32 Reserved10; /* 0x24 */ + U32 Reserved11; /* 0x28 */ + U32 Reserved12; /* 0x2C */ + MPI2_SGE_SIMPLE_UNION SGL; /* 0x30 */ +} MPI2_TOOLBOX_ISTWI_READ_WRITE_REQUEST, + MPI2_POINTER PTR_MPI2_TOOLBOX_ISTWI_READ_WRITE_REQUEST, + Mpi2ToolboxIstwiReadWriteRequest_t, + MPI2_POINTER pMpi2ToolboxIstwiReadWriteRequest_t; + +/* values for the Action field */ +#define MPI2_TOOL_ISTWI_ACTION_READ_DATA (0x01) +#define MPI2_TOOL_ISTWI_ACTION_WRITE_DATA (0x02) +#define MPI2_TOOL_ISTWI_ACTION_SEQUENCE (0x03) +#define MPI2_TOOL_ISTWI_ACTION_RESERVE_BUS (0x10) +#define MPI2_TOOL_ISTWI_ACTION_RELEASE_BUS (0x11) +#define MPI2_TOOL_ISTWI_ACTION_RESET (0x12) + +/* values for SGLFlags field are in the SGL section of mpi2.h */ + + +/* Toolbox ISTWI Read Write Tool reply message */ +typedef struct _MPI2_TOOLBOX_ISTWI_REPLY { + U8 Tool; /* 0x00 */ + U8 Reserved1; /* 0x01 */ + U8 MsgLength; /* 0x02 */ + U8 Function; /* 0x03 */ + U16 Reserved2; /* 0x04 */ + U8 Reserved3; /* 0x06 */ + U8 MsgFlags; /* 0x07 */ + U8 VP_ID; /* 0x08 */ + U8 VF_ID; /* 0x09 */ + U16 Reserved4; /* 0x0A */ + U16 Reserved5; /* 0x0C */ + U16 IOCStatus; /* 0x0E */ + U32 IOCLogInfo; /* 0x10 */ + U8 DevIndex; /* 0x14 */ + U8 Action; /* 0x15 */ + U8 IstwiStatus; /* 0x16 */ + U8 Reserved6; /* 0x17 */ + U16 TxDataCount; /* 0x18 */ + U16 RxDataCount; /* 0x1A */ +} MPI2_TOOLBOX_ISTWI_REPLY, MPI2_POINTER PTR_MPI2_TOOLBOX_ISTWI_REPLY, + Mpi2ToolboxIstwiReply_t, MPI2_POINTER pMpi2ToolboxIstwiReply_t; + + +/**************************************************************************** * Toolbox Beacon Tool request ****************************************************************************/ @@ -139,6 +214,61 @@ typedef struct _MPI2_TOOLBOX_BEACON_REQUEST #define MPI2_TOOLBOX_FLAGS_BEACONMODE_ON (0x01) +/**************************************************************************** +* Toolbox Diagnostic CLI Tool +****************************************************************************/ + +#define MPI2_TOOLBOX_DIAG_CLI_CMD_LENGTH (0x5C) + +/* Toolbox Diagnostic CLI Tool request message */ +typedef struct _MPI2_TOOLBOX_DIAGNOSTIC_CLI_REQUEST { + U8 Tool; /* 0x00 */ + U8 Reserved1; /* 0x01 */ + U8 ChainOffset; /* 0x02 */ + U8 Function; /* 0x03 */ + U16 Reserved2; /* 0x04 */ + U8 Reserved3; /* 0x06 */ + U8 MsgFlags; /* 0x07 */ + U8 VP_ID; /* 0x08 */ + U8 VF_ID; /* 0x09 */ + U16 Reserved4; /* 0x0A */ + U8 SGLFlags; /* 0x0C */ + U8 Reserved5; /* 0x0D */ + U16 Reserved6; /* 0x0E */ + U32 DataLength; /* 0x10 */ + U8 DiagnosticCliCommand + [MPI2_TOOLBOX_DIAG_CLI_CMD_LENGTH]; /* 0x14 */ + MPI2_SGE_SIMPLE_UNION SGL; /* 0x70 */ +} MPI2_TOOLBOX_DIAGNOSTIC_CLI_REQUEST, + MPI2_POINTER PTR_MPI2_TOOLBOX_DIAGNOSTIC_CLI_REQUEST, + Mpi2ToolboxDiagnosticCliRequest_t, + MPI2_POINTER pMpi2ToolboxDiagnosticCliRequest_t; + +/* values for SGLFlags field are in the SGL section of mpi2.h */ + + +/* Toolbox Diagnostic CLI Tool reply message */ +typedef struct _MPI2_TOOLBOX_DIAGNOSTIC_CLI_REPLY { + U8 Tool; /* 0x00 */ + U8 Reserved1; /* 0x01 */ + U8 MsgLength; /* 0x02 */ + U8 Function; /* 0x03 */ + U16 Reserved2; /* 0x04 */ + U8 Reserved3; /* 0x06 */ + U8 MsgFlags; /* 0x07 */ + U8 VP_ID; /* 0x08 */ + U8 VF_ID; /* 0x09 */ + U16 Reserved4; /* 0x0A */ + U16 Reserved5; /* 0x0C */ + U16 IOCStatus; /* 0x0E */ + U32 IOCLogInfo; /* 0x10 */ + U32 ReturnedDataLength; /* 0x14 */ +} MPI2_TOOLBOX_DIAGNOSTIC_CLI_REPLY, + MPI2_POINTER PTR_MPI2_TOOLBOX_DIAG_CLI_REPLY, + Mpi2ToolboxDiagnosticCliReply_t, + MPI2_POINTER pMpi2ToolboxDiagnosticCliReply_t; + + /***************************************************************************** * * Diagnostic Buffer Messages diff --git a/drivers/scsi/mpt2sas/mpt2sas_base.c b/drivers/scsi/mpt2sas/mpt2sas_base.c index d95d2f274cb3..670241efa4b5 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_base.c +++ b/drivers/scsi/mpt2sas/mpt2sas_base.c @@ -3,7 +3,7 @@ * for access to MPT (Message Passing Technology) firmware. * * This code is based on drivers/scsi/mpt2sas/mpt2_base.c - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or @@ -63,7 +63,7 @@ static MPT_CALLBACK mpt_callbacks[MPT_MAX_CALLBACKS]; #define FAULT_POLLING_INTERVAL 1000 /* in milliseconds */ -#define MPT2SAS_MAX_REQUEST_QUEUE 500 /* maximum controller queue depth */ +#define MPT2SAS_MAX_REQUEST_QUEUE 600 /* maximum controller queue depth */ static int max_queue_depth = -1; module_param(max_queue_depth, int, 0); @@ -543,13 +543,13 @@ mpt2sas_base_fault_info(struct MPT2SAS_ADAPTER *ioc , u16 fault_code) * _base_display_reply_info - * @ioc: pointer to scsi command object * @smid: system request message index - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * * Return nothing. */ static void -_base_display_reply_info(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, +_base_display_reply_info(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, u32 reply) { MPI2DefaultReply_t *mpi_reply; @@ -572,22 +572,24 @@ _base_display_reply_info(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, * mpt2sas_base_done - base internal command completion routine * @ioc: pointer to scsi command object * @smid: system request message index - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -void -mpt2sas_base_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) +u8 +mpt2sas_base_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply) { MPI2DefaultReply_t *mpi_reply; mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); if (mpi_reply && mpi_reply->Function == MPI2_FUNCTION_EVENT_ACK) - return; + return 1; if (ioc->base_cmds.status == MPT2_CMD_NOT_USED) - return; + return 1; ioc->base_cmds.status |= MPT2_CMD_COMPLETE; if (mpi_reply) { @@ -596,18 +598,20 @@ mpt2sas_base_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) } ioc->base_cmds.status &= ~MPT2_CMD_PENDING; complete(&ioc->base_cmds.done); + return 1; } /** * _base_async_event - main callback handler for firmware asyn events * @ioc: pointer to scsi command object - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -static void -_base_async_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) +static u8 +_base_async_event(struct MPT2SAS_ADAPTER *ioc, u8 msix_index, u32 reply) { Mpi2EventNotificationReply_t *mpi_reply; Mpi2EventAckRequest_t *ack_request; @@ -615,9 +619,9 @@ _base_async_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); if (!mpi_reply) - return; + return 1; if (mpi_reply->Function != MPI2_FUNCTION_EVENT_NOTIFICATION) - return; + return 1; #ifdef CONFIG_SCSI_MPT2SAS_LOGGING _base_display_event_data(ioc, mpi_reply); #endif @@ -635,16 +639,47 @@ _base_async_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) ack_request->Function = MPI2_FUNCTION_EVENT_ACK; ack_request->Event = mpi_reply->Event; ack_request->EventContext = mpi_reply->EventContext; - ack_request->VF_ID = VF_ID; - mpt2sas_base_put_smid_default(ioc, smid, VF_ID); + ack_request->VF_ID = 0; /* TODO */ + ack_request->VP_ID = 0; + mpt2sas_base_put_smid_default(ioc, smid); out: /* scsih callback handler */ - mpt2sas_scsih_event_callback(ioc, VF_ID, reply); + mpt2sas_scsih_event_callback(ioc, msix_index, reply); /* ctl callback handler */ - mpt2sas_ctl_event_callback(ioc, VF_ID, reply); + mpt2sas_ctl_event_callback(ioc, msix_index, reply); + + return 1; +} + +/** + * _base_get_cb_idx - obtain the callback index + * @ioc: per adapter object + * @smid: system request message index + * + * Return callback index. + */ +static u8 +_base_get_cb_idx(struct MPT2SAS_ADAPTER *ioc, u16 smid) +{ + int i; + u8 cb_idx = 0xFF; + + if (smid >= ioc->hi_priority_smid) { + if (smid < ioc->internal_smid) { + i = smid - ioc->hi_priority_smid; + cb_idx = ioc->hpr_lookup[i].cb_idx; + } else { + i = smid - ioc->internal_smid; + cb_idx = ioc->internal_lookup[i].cb_idx; + } + } else { + i = smid - 1; + cb_idx = ioc->scsi_lookup[i].cb_idx; + } + return cb_idx; } /** @@ -680,7 +715,6 @@ _base_unmask_interrupts(struct MPT2SAS_ADAPTER *ioc) { u32 him_register; - writel(0, &ioc->chip->HostInterruptStatus); him_register = readl(&ioc->chip->HostInterruptMask); him_register &= ~MPI2_HIM_RIM; writel(him_register, &ioc->chip->HostInterruptMask); @@ -712,9 +746,10 @@ _base_interrupt(int irq, void *bus_id) u16 smid; u8 cb_idx; u32 reply; - u8 VF_ID; + u8 msix_index; struct MPT2SAS_ADAPTER *ioc = bus_id; Mpi2ReplyDescriptorsUnion_t *rpf; + u8 rc; if (ioc->mask_interrupts) return IRQ_NONE; @@ -733,7 +768,7 @@ _base_interrupt(int irq, void *bus_id) reply = 0; cb_idx = 0xFF; smid = le16_to_cpu(rpf->Default.DescriptorTypeDependent1); - VF_ID = rpf->Default.VF_ID; + msix_index = rpf->Default.MSIxIndex; if (request_desript_type == MPI2_RPY_DESCRIPT_FLAGS_ADDRESS_REPLY) { reply = le32_to_cpu @@ -745,16 +780,18 @@ _base_interrupt(int irq, void *bus_id) MPI2_RPY_DESCRIPT_FLAGS_TARGETASSIST_SUCCESS) goto next; if (smid) - cb_idx = ioc->scsi_lookup[smid - 1].cb_idx; + cb_idx = _base_get_cb_idx(ioc, smid); if (smid && cb_idx != 0xFF) { - mpt_callbacks[cb_idx](ioc, smid, VF_ID, reply); + rc = mpt_callbacks[cb_idx](ioc, smid, msix_index, + reply); if (reply) - _base_display_reply_info(ioc, smid, VF_ID, + _base_display_reply_info(ioc, smid, msix_index, reply); - mpt2sas_base_free_smid(ioc, smid); + if (rc) + mpt2sas_base_free_smid(ioc, smid); } if (!smid) - _base_async_event(ioc, VF_ID, reply); + _base_async_event(ioc, msix_index, reply); /* reply free queue handling */ if (reply) { @@ -1191,19 +1228,6 @@ mpt2sas_base_map_resources(struct MPT2SAS_ADAPTER *ioc) } /** - * mpt2sas_base_get_msg_frame_dma - obtain request mf pointer phys addr - * @ioc: per adapter object - * @smid: system request message index(smid zero is invalid) - * - * Returns phys pointer to message frame. - */ -dma_addr_t -mpt2sas_base_get_msg_frame_dma(struct MPT2SAS_ADAPTER *ioc, u16 smid) -{ - return ioc->request_dma + (smid * ioc->request_sz); -} - -/** * mpt2sas_base_get_msg_frame - obtain request mf pointer * @ioc: per adapter object * @smid: system request message index(smid zero is invalid) @@ -1258,7 +1282,7 @@ mpt2sas_base_get_reply_virt_addr(struct MPT2SAS_ADAPTER *ioc, u32 phys_addr) } /** - * mpt2sas_base_get_smid - obtain a free smid + * mpt2sas_base_get_smid - obtain a free smid from internal queue * @ioc: per adapter object * @cb_idx: callback index * @@ -1272,6 +1296,39 @@ mpt2sas_base_get_smid(struct MPT2SAS_ADAPTER *ioc, u8 cb_idx) u16 smid; spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); + if (list_empty(&ioc->internal_free_list)) { + spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); + printk(MPT2SAS_ERR_FMT "%s: smid not available\n", + ioc->name, __func__); + return 0; + } + + request = list_entry(ioc->internal_free_list.next, + struct request_tracker, tracker_list); + request->cb_idx = cb_idx; + smid = request->smid; + list_del(&request->tracker_list); + spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); + return smid; +} + +/** + * mpt2sas_base_get_smid_scsiio - obtain a free smid from scsiio queue + * @ioc: per adapter object + * @cb_idx: callback index + * @scmd: pointer to scsi command object + * + * Returns smid (zero is invalid) + */ +u16 +mpt2sas_base_get_smid_scsiio(struct MPT2SAS_ADAPTER *ioc, u8 cb_idx, + struct scsi_cmnd *scmd) +{ + unsigned long flags; + struct request_tracker *request; + u16 smid; + + spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); if (list_empty(&ioc->free_list)) { spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); printk(MPT2SAS_ERR_FMT "%s: smid not available\n", @@ -1281,6 +1338,36 @@ mpt2sas_base_get_smid(struct MPT2SAS_ADAPTER *ioc, u8 cb_idx) request = list_entry(ioc->free_list.next, struct request_tracker, tracker_list); + request->scmd = scmd; + request->cb_idx = cb_idx; + smid = request->smid; + list_del(&request->tracker_list); + spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); + return smid; +} + +/** + * mpt2sas_base_get_smid_hpr - obtain a free smid from hi-priority queue + * @ioc: per adapter object + * @cb_idx: callback index + * + * Returns smid (zero is invalid) + */ +u16 +mpt2sas_base_get_smid_hpr(struct MPT2SAS_ADAPTER *ioc, u8 cb_idx) +{ + unsigned long flags; + struct request_tracker *request; + u16 smid; + + spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); + if (list_empty(&ioc->hpr_free_list)) { + spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); + return 0; + } + + request = list_entry(ioc->hpr_free_list.next, + struct request_tracker, tracker_list); request->cb_idx = cb_idx; smid = request->smid; list_del(&request->tracker_list); @@ -1300,10 +1387,32 @@ void mpt2sas_base_free_smid(struct MPT2SAS_ADAPTER *ioc, u16 smid) { unsigned long flags; + int i; spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); - ioc->scsi_lookup[smid - 1].cb_idx = 0xFF; - list_add_tail(&ioc->scsi_lookup[smid - 1].tracker_list, + if (smid >= ioc->hi_priority_smid) { + if (smid < ioc->internal_smid) { + /* hi-priority */ + i = smid - ioc->hi_priority_smid; + ioc->hpr_lookup[i].cb_idx = 0xFF; + list_add_tail(&ioc->hpr_lookup[i].tracker_list, + &ioc->hpr_free_list); + } else { + /* internal queue */ + i = smid - ioc->internal_smid; + ioc->internal_lookup[i].cb_idx = 0xFF; + list_add_tail(&ioc->internal_lookup[i].tracker_list, + &ioc->internal_free_list); + } + spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); + return; + } + + /* scsiio queue */ + i = smid - 1; + ioc->scsi_lookup[i].cb_idx = 0xFF; + ioc->scsi_lookup[i].scmd = NULL; + list_add_tail(&ioc->scsi_lookup[i].tracker_list, &ioc->free_list); spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); @@ -1352,21 +1461,19 @@ static inline void _base_writeq(__u64 b, volatile void __iomem *addr, * mpt2sas_base_put_smid_scsi_io - send SCSI_IO request to firmware * @ioc: per adapter object * @smid: system request message index - * @vf_id: virtual function id * @handle: device handle * * Return nothing. */ void -mpt2sas_base_put_smid_scsi_io(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 vf_id, - u16 handle) +mpt2sas_base_put_smid_scsi_io(struct MPT2SAS_ADAPTER *ioc, u16 smid, u16 handle) { Mpi2RequestDescriptorUnion_t descriptor; u64 *request = (u64 *)&descriptor; descriptor.SCSIIO.RequestFlags = MPI2_REQ_DESCRIPT_FLAGS_SCSI_IO; - descriptor.SCSIIO.VF_ID = vf_id; + descriptor.SCSIIO.MSIxIndex = 0; /* TODO */ descriptor.SCSIIO.SMID = cpu_to_le16(smid); descriptor.SCSIIO.DevHandle = cpu_to_le16(handle); descriptor.SCSIIO.LMID = 0; @@ -1379,20 +1486,18 @@ mpt2sas_base_put_smid_scsi_io(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 vf_id, * mpt2sas_base_put_smid_hi_priority - send Task Managment request to firmware * @ioc: per adapter object * @smid: system request message index - * @vf_id: virtual function id * * Return nothing. */ void -mpt2sas_base_put_smid_hi_priority(struct MPT2SAS_ADAPTER *ioc, u16 smid, - u8 vf_id) +mpt2sas_base_put_smid_hi_priority(struct MPT2SAS_ADAPTER *ioc, u16 smid) { Mpi2RequestDescriptorUnion_t descriptor; u64 *request = (u64 *)&descriptor; descriptor.HighPriority.RequestFlags = MPI2_REQ_DESCRIPT_FLAGS_HIGH_PRIORITY; - descriptor.HighPriority.VF_ID = vf_id; + descriptor.HighPriority.MSIxIndex = 0; /* TODO */ descriptor.HighPriority.SMID = cpu_to_le16(smid); descriptor.HighPriority.LMID = 0; descriptor.HighPriority.Reserved1 = 0; @@ -1404,18 +1509,17 @@ mpt2sas_base_put_smid_hi_priority(struct MPT2SAS_ADAPTER *ioc, u16 smid, * mpt2sas_base_put_smid_default - Default, primarily used for config pages * @ioc: per adapter object * @smid: system request message index - * @vf_id: virtual function id * * Return nothing. */ void -mpt2sas_base_put_smid_default(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 vf_id) +mpt2sas_base_put_smid_default(struct MPT2SAS_ADAPTER *ioc, u16 smid) { Mpi2RequestDescriptorUnion_t descriptor; u64 *request = (u64 *)&descriptor; descriptor.Default.RequestFlags = MPI2_REQ_DESCRIPT_FLAGS_DEFAULT_TYPE; - descriptor.Default.VF_ID = vf_id; + descriptor.Default.MSIxIndex = 0; /* TODO */ descriptor.Default.SMID = cpu_to_le16(smid); descriptor.Default.LMID = 0; descriptor.Default.DescriptorTypeDependent = 0; @@ -1427,21 +1531,20 @@ mpt2sas_base_put_smid_default(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 vf_id) * mpt2sas_base_put_smid_target_assist - send Target Assist/Status to firmware * @ioc: per adapter object * @smid: system request message index - * @vf_id: virtual function id * @io_index: value used to track the IO * * Return nothing. */ void mpt2sas_base_put_smid_target_assist(struct MPT2SAS_ADAPTER *ioc, u16 smid, - u8 vf_id, u16 io_index) + u16 io_index) { Mpi2RequestDescriptorUnion_t descriptor; u64 *request = (u64 *)&descriptor; descriptor.SCSITarget.RequestFlags = MPI2_REQ_DESCRIPT_FLAGS_SCSI_TARGET; - descriptor.SCSITarget.VF_ID = vf_id; + descriptor.SCSITarget.MSIxIndex = 0; /* TODO */ descriptor.SCSITarget.SMID = cpu_to_le16(smid); descriptor.SCSITarget.LMID = 0; descriptor.SCSITarget.IoIndex = cpu_to_le16(io_index); @@ -1717,6 +1820,8 @@ _base_release_memory_pools(struct MPT2SAS_ADAPTER *ioc) } kfree(ioc->scsi_lookup); + kfree(ioc->hpr_lookup); + kfree(ioc->internal_lookup); } @@ -1736,7 +1841,6 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) u16 num_of_reply_frames; u16 chains_needed_per_io; u32 sz, total_sz; - u16 i; u32 retry_sz; u16 max_request_credit; @@ -1764,7 +1868,10 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) MPT2SAS_MAX_REQUEST_QUEUE) ? MPT2SAS_MAX_REQUEST_QUEUE : facts->RequestCredit; } - ioc->request_depth = max_request_credit; + + ioc->hba_queue_depth = max_request_credit; + ioc->hi_priority_depth = facts->HighPriorityCredit; + ioc->internal_depth = ioc->hi_priority_depth + 5; /* request frame size */ ioc->request_sz = facts->IOCRequestFrameSize * 4; @@ -1802,7 +1909,7 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) ioc->chains_needed_per_io = chains_needed_per_io; /* reply free queue sizing - taking into account for events */ - num_of_reply_frames = ioc->request_depth + 32; + num_of_reply_frames = ioc->hba_queue_depth + 32; /* number of replies frames can't be a multiple of 16 */ /* decrease number of reply frames by 1 */ @@ -1823,7 +1930,7 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) * frames */ - queue_size = ioc->request_depth + num_of_reply_frames + 1; + queue_size = ioc->hba_queue_depth + num_of_reply_frames + 1; /* round up to 16 byte boundary */ if (queue_size % 16) queue_size += 16 - (queue_size % 16); @@ -1837,60 +1944,85 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) if (queue_diff % 16) queue_diff += 16 - (queue_diff % 16); - /* adjust request_depth, reply_free_queue_depth, + /* adjust hba_queue_depth, reply_free_queue_depth, * and queue_size */ - ioc->request_depth -= queue_diff; + ioc->hba_queue_depth -= queue_diff; ioc->reply_free_queue_depth -= queue_diff; queue_size -= queue_diff; } ioc->reply_post_queue_depth = queue_size; - /* max scsi host queue depth */ - ioc->shost->can_queue = ioc->request_depth - INTERNAL_CMDS_COUNT; - dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "scsi host queue: depth" - "(%d)\n", ioc->name, ioc->shost->can_queue)); - dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "scatter gather: " "sge_in_main_msg(%d), sge_per_chain(%d), sge_per_io(%d), " "chains_per_io(%d)\n", ioc->name, ioc->max_sges_in_main_message, ioc->max_sges_in_chain_message, ioc->shost->sg_tablesize, ioc->chains_needed_per_io)); + ioc->scsiio_depth = ioc->hba_queue_depth - + ioc->hi_priority_depth - ioc->internal_depth; + + /* set the scsi host can_queue depth + * with some internal commands that could be outstanding + */ + ioc->shost->can_queue = ioc->scsiio_depth - (2); + dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "scsi host: " + "can_queue depth (%d)\n", ioc->name, ioc->shost->can_queue)); + /* contiguous pool for request and chains, 16 byte align, one extra " * "frame for smid=0 */ - ioc->chain_depth = ioc->chains_needed_per_io * ioc->request_depth; - sz = ((ioc->request_depth + 1 + ioc->chain_depth) * ioc->request_sz); + ioc->chain_depth = ioc->chains_needed_per_io * ioc->scsiio_depth; + sz = ((ioc->scsiio_depth + 1 + ioc->chain_depth) * ioc->request_sz); + + /* hi-priority queue */ + sz += (ioc->hi_priority_depth * ioc->request_sz); + + /* internal queue */ + sz += (ioc->internal_depth * ioc->request_sz); ioc->request_dma_sz = sz; ioc->request = pci_alloc_consistent(ioc->pdev, sz, &ioc->request_dma); if (!ioc->request) { printk(MPT2SAS_ERR_FMT "request pool: pci_alloc_consistent " - "failed: req_depth(%d), chains_per_io(%d), frame_sz(%d), " - "total(%d kB)\n", ioc->name, ioc->request_depth, + "failed: hba_depth(%d), chains_per_io(%d), frame_sz(%d), " + "total(%d kB)\n", ioc->name, ioc->hba_queue_depth, ioc->chains_needed_per_io, ioc->request_sz, sz/1024); - if (ioc->request_depth < MPT2SAS_SAS_QUEUE_DEPTH) + if (ioc->scsiio_depth < MPT2SAS_SAS_QUEUE_DEPTH) goto out; retry_sz += 64; - ioc->request_depth = max_request_credit - retry_sz; + ioc->hba_queue_depth = max_request_credit - retry_sz; goto retry_allocation; } if (retry_sz) printk(MPT2SAS_ERR_FMT "request pool: pci_alloc_consistent " - "succeed: req_depth(%d), chains_per_io(%d), frame_sz(%d), " - "total(%d kb)\n", ioc->name, ioc->request_depth, + "succeed: hba_depth(%d), chains_per_io(%d), frame_sz(%d), " + "total(%d kb)\n", ioc->name, ioc->hba_queue_depth, ioc->chains_needed_per_io, ioc->request_sz, sz/1024); - ioc->chain = ioc->request + ((ioc->request_depth + 1) * + + /* hi-priority queue */ + ioc->hi_priority = ioc->request + ((ioc->scsiio_depth + 1) * + ioc->request_sz); + ioc->hi_priority_dma = ioc->request_dma + ((ioc->scsiio_depth + 1) * + ioc->request_sz); + + /* internal queue */ + ioc->internal = ioc->hi_priority + (ioc->hi_priority_depth * + ioc->request_sz); + ioc->internal_dma = ioc->hi_priority_dma + (ioc->hi_priority_depth * + ioc->request_sz); + + ioc->chain = ioc->internal + (ioc->internal_depth * ioc->request_sz); - ioc->chain_dma = ioc->request_dma + ((ioc->request_depth + 1) * + ioc->chain_dma = ioc->internal_dma + (ioc->internal_depth * ioc->request_sz); + dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "request pool(0x%p): " "depth(%d), frame_size(%d), pool_size(%d kB)\n", ioc->name, - ioc->request, ioc->request_depth, ioc->request_sz, - ((ioc->request_depth + 1) * ioc->request_sz)/1024)); + ioc->request, ioc->hba_queue_depth, ioc->request_sz, + (ioc->hba_queue_depth * ioc->request_sz)/1024)); dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "chain pool(0x%p): depth" "(%d), frame_size(%d), pool_size(%d kB)\n", ioc->name, ioc->chain, ioc->chain_depth, ioc->request_sz, ((ioc->chain_depth * @@ -1899,7 +2031,7 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) ioc->name, (unsigned long long) ioc->request_dma)); total_sz += sz; - ioc->scsi_lookup = kcalloc(ioc->request_depth, + ioc->scsi_lookup = kcalloc(ioc->scsiio_depth, sizeof(struct request_tracker), GFP_KERNEL); if (!ioc->scsi_lookup) { printk(MPT2SAS_ERR_FMT "scsi_lookup: kcalloc failed\n", @@ -1907,12 +2039,38 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) goto out; } - /* initialize some bits */ - for (i = 0; i < ioc->request_depth; i++) - ioc->scsi_lookup[i].smid = i + 1; + dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "scsiio(0x%p): " + "depth(%d)\n", ioc->name, ioc->request, + ioc->scsiio_depth)); + + /* initialize hi-priority queue smid's */ + ioc->hpr_lookup = kcalloc(ioc->hi_priority_depth, + sizeof(struct request_tracker), GFP_KERNEL); + if (!ioc->hpr_lookup) { + printk(MPT2SAS_ERR_FMT "hpr_lookup: kcalloc failed\n", + ioc->name); + goto out; + } + ioc->hi_priority_smid = ioc->scsiio_depth + 1; + dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "hi_priority(0x%p): " + "depth(%d), start smid(%d)\n", ioc->name, ioc->hi_priority, + ioc->hi_priority_depth, ioc->hi_priority_smid)); + + /* initialize internal queue smid's */ + ioc->internal_lookup = kcalloc(ioc->internal_depth, + sizeof(struct request_tracker), GFP_KERNEL); + if (!ioc->internal_lookup) { + printk(MPT2SAS_ERR_FMT "internal_lookup: kcalloc failed\n", + ioc->name); + goto out; + } + ioc->internal_smid = ioc->hi_priority_smid + ioc->hi_priority_depth; + dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "internal(0x%p): " + "depth(%d), start smid(%d)\n", ioc->name, ioc->internal, + ioc->internal_depth, ioc->internal_smid)); /* sense buffers, 4 byte align */ - sz = ioc->request_depth * SCSI_SENSE_BUFFERSIZE; + sz = ioc->scsiio_depth * SCSI_SENSE_BUFFERSIZE; ioc->sense_dma_pool = pci_pool_create("sense pool", ioc->pdev, sz, 4, 0); if (!ioc->sense_dma_pool) { @@ -1929,7 +2087,7 @@ _base_allocate_memory_pools(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) } dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "sense pool(0x%p): depth(%d), element_size(%d), pool_size" - "(%d kB)\n", ioc->name, ioc->sense, ioc->request_depth, + "(%d kB)\n", ioc->name, ioc->sense, ioc->scsiio_depth, SCSI_SENSE_BUFFERSIZE, sz/1024)); dinitprintk(ioc, printk(MPT2SAS_INFO_FMT "sense_dma(0x%llx)\n", ioc->name, (unsigned long long)ioc->sense_dma)); @@ -2304,7 +2462,7 @@ _base_handshake_req_reply_wait(struct MPT2SAS_ADAPTER *ioc, int request_bytes, ((request_bytes/4)<<MPI2_DOORBELL_ADD_DWORDS_SHIFT)), &ioc->chip->Doorbell); - if ((_base_wait_for_doorbell_int(ioc, 5, sleep_flag))) { + if ((_base_wait_for_doorbell_int(ioc, 5, NO_SLEEP))) { printk(MPT2SAS_ERR_FMT "doorbell handshake " "int failed (line=%d)\n", ioc->name, __LINE__); return -EFAULT; @@ -2454,7 +2612,8 @@ mpt2sas_base_sas_iounit_control(struct MPT2SAS_ADAPTER *ioc, if (mpi_request->Operation == MPI2_SAS_OP_PHY_HARD_RESET || mpi_request->Operation == MPI2_SAS_OP_PHY_LINK_RESET) ioc->ioc_link_reset_in_progress = 1; - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->base_cmds.done); timeleft = wait_for_completion_timeout(&ioc->base_cmds.done, msecs_to_jiffies(10000)); if ((mpi_request->Operation == MPI2_SAS_OP_PHY_HARD_RESET || @@ -2555,7 +2714,8 @@ mpt2sas_base_scsi_enclosure_processor(struct MPT2SAS_ADAPTER *ioc, request = mpt2sas_base_get_msg_frame(ioc, smid); ioc->base_cmds.smid = smid; memcpy(request, mpi_request, sizeof(Mpi2SepReply_t)); - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->base_cmds.done); timeleft = wait_for_completion_timeout(&ioc->base_cmds.done, msecs_to_jiffies(10000)); if (!(ioc->base_cmds.status & MPT2_CMD_COMPLETE)) { @@ -2701,13 +2861,12 @@ _base_get_ioc_facts(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) /** * _base_send_ioc_init - send ioc_init to firmware * @ioc: per adapter object - * @VF_ID: virtual function id * @sleep_flag: CAN_SLEEP or NO_SLEEP * * Returns 0 for success, non-zero for failure. */ static int -_base_send_ioc_init(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, int sleep_flag) +_base_send_ioc_init(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) { Mpi2IOCInitRequest_t mpi_request; Mpi2IOCInitReply_t mpi_reply; @@ -2719,7 +2878,8 @@ _base_send_ioc_init(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, int sleep_flag) memset(&mpi_request, 0, sizeof(Mpi2IOCInitRequest_t)); mpi_request.Function = MPI2_FUNCTION_IOC_INIT; mpi_request.WhoInit = MPI2_WHOINIT_HOST_DRIVER; - mpi_request.VF_ID = VF_ID; + mpi_request.VF_ID = 0; /* TODO */ + mpi_request.VP_ID = 0; mpi_request.MsgVersion = cpu_to_le16(MPI2_VERSION); mpi_request.HeaderVersion = cpu_to_le16(MPI2_HEADER_VERSION); @@ -2795,13 +2955,12 @@ _base_send_ioc_init(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, int sleep_flag) /** * _base_send_port_enable - send port_enable(discovery stuff) to firmware * @ioc: per adapter object - * @VF_ID: virtual function id * @sleep_flag: CAN_SLEEP or NO_SLEEP * * Returns 0 for success, non-zero for failure. */ static int -_base_send_port_enable(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, int sleep_flag) +_base_send_port_enable(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) { Mpi2PortEnableRequest_t *mpi_request; u32 ioc_state; @@ -2829,9 +2988,11 @@ _base_send_port_enable(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, int sleep_flag) ioc->base_cmds.smid = smid; memset(mpi_request, 0, sizeof(Mpi2PortEnableRequest_t)); mpi_request->Function = MPI2_FUNCTION_PORT_ENABLE; - mpi_request->VF_ID = VF_ID; + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; - mpt2sas_base_put_smid_default(ioc, smid, VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->base_cmds.done); timeleft = wait_for_completion_timeout(&ioc->base_cmds.done, 300*HZ); if (!(ioc->base_cmds.status & MPT2_CMD_COMPLETE)) { @@ -2892,13 +3053,12 @@ _base_unmask_events(struct MPT2SAS_ADAPTER *ioc, u16 event) /** * _base_event_notification - send event notification * @ioc: per adapter object - * @VF_ID: virtual function id * @sleep_flag: CAN_SLEEP or NO_SLEEP * * Returns 0 for success, non-zero for failure. */ static int -_base_event_notification(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, int sleep_flag) +_base_event_notification(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) { Mpi2EventNotificationRequest_t *mpi_request; unsigned long timeleft; @@ -2926,11 +3086,13 @@ _base_event_notification(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, int sleep_flag) ioc->base_cmds.smid = smid; memset(mpi_request, 0, sizeof(Mpi2EventNotificationRequest_t)); mpi_request->Function = MPI2_FUNCTION_EVENT_NOTIFICATION; - mpi_request->VF_ID = VF_ID; + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; for (i = 0; i < MPI2_EVENT_NOTIFY_EVENTMASK_WORDS; i++) mpi_request->EventMasks[i] = le32_to_cpu(ioc->event_masks[i]); - mpt2sas_base_put_smid_default(ioc, smid, VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->base_cmds.done); timeleft = wait_for_completion_timeout(&ioc->base_cmds.done, 30*HZ); if (!(ioc->base_cmds.status & MPT2_CMD_COMPLETE)) { printk(MPT2SAS_ERR_FMT "%s: timeout\n", @@ -2981,7 +3143,7 @@ mpt2sas_base_validate_event_type(struct MPT2SAS_ADAPTER *ioc, u32 *event_type) return; mutex_lock(&ioc->base_cmds.mutex); - _base_event_notification(ioc, 0, CAN_SLEEP); + _base_event_notification(ioc, CAN_SLEEP); mutex_unlock(&ioc->base_cmds.mutex); } @@ -3006,7 +3168,6 @@ _base_diag_reset(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) drsprintk(ioc, printk(MPT2SAS_DEBUG_FMT "clear interrupts\n", ioc->name)); - writel(0, &ioc->chip->HostInterruptStatus); count = 0; do { @@ -3160,30 +3321,60 @@ _base_make_ioc_ready(struct MPT2SAS_ADAPTER *ioc, int sleep_flag, /** * _base_make_ioc_operational - put controller in OPERATIONAL state * @ioc: per adapter object - * @VF_ID: virtual function id * @sleep_flag: CAN_SLEEP or NO_SLEEP * * Returns 0 for success, non-zero for failure. */ static int -_base_make_ioc_operational(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - int sleep_flag) +_base_make_ioc_operational(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) { int r, i; unsigned long flags; u32 reply_address; + u16 smid; + struct _tr_list *delayed_tr, *delayed_tr_next; dinitprintk(ioc, printk(MPT2SAS_DEBUG_FMT "%s\n", ioc->name, __func__)); + /* clean the delayed target reset list */ + list_for_each_entry_safe(delayed_tr, delayed_tr_next, + &ioc->delayed_tr_list, list) { + list_del(&delayed_tr->list); + kfree(delayed_tr); + } + /* initialize the scsi lookup free list */ spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); INIT_LIST_HEAD(&ioc->free_list); - for (i = 0; i < ioc->request_depth; i++) { + smid = 1; + for (i = 0; i < ioc->scsiio_depth; i++, smid++) { ioc->scsi_lookup[i].cb_idx = 0xFF; + ioc->scsi_lookup[i].smid = smid; + ioc->scsi_lookup[i].scmd = NULL; list_add_tail(&ioc->scsi_lookup[i].tracker_list, &ioc->free_list); } + + /* hi-priority queue */ + INIT_LIST_HEAD(&ioc->hpr_free_list); + smid = ioc->hi_priority_smid; + for (i = 0; i < ioc->hi_priority_depth; i++, smid++) { + ioc->hpr_lookup[i].cb_idx = 0xFF; + ioc->hpr_lookup[i].smid = smid; + list_add_tail(&ioc->hpr_lookup[i].tracker_list, + &ioc->hpr_free_list); + } + + /* internal queue */ + INIT_LIST_HEAD(&ioc->internal_free_list); + smid = ioc->internal_smid; + for (i = 0; i < ioc->internal_depth; i++, smid++) { + ioc->internal_lookup[i].cb_idx = 0xFF; + ioc->internal_lookup[i].smid = smid; + list_add_tail(&ioc->internal_lookup[i].tracker_list, + &ioc->internal_free_list); + } spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); /* initialize Reply Free Queue */ @@ -3196,7 +3387,7 @@ _base_make_ioc_operational(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, for (i = 0; i < ioc->reply_post_queue_depth; i++) ioc->reply_post_free[i].Words = ULLONG_MAX; - r = _base_send_ioc_init(ioc, VF_ID, sleep_flag); + r = _base_send_ioc_init(ioc, sleep_flag); if (r) return r; @@ -3207,14 +3398,14 @@ _base_make_ioc_operational(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, writel(0, &ioc->chip->ReplyPostHostIndex); _base_unmask_interrupts(ioc); - r = _base_event_notification(ioc, VF_ID, sleep_flag); + r = _base_event_notification(ioc, sleep_flag); if (r) return r; if (sleep_flag == CAN_SLEEP) _base_static_config_pages(ioc); - r = _base_send_port_enable(ioc, VF_ID, sleep_flag); + r = _base_send_port_enable(ioc, sleep_flag); if (r) return r; @@ -3278,6 +3469,17 @@ mpt2sas_base_attach(struct MPT2SAS_ADAPTER *ioc) if (r) goto out_free_resources; + ioc->pfacts = kcalloc(ioc->facts.NumberOfPorts, + sizeof(Mpi2PortFactsReply_t), GFP_KERNEL); + if (!ioc->pfacts) + goto out_free_resources; + + for (i = 0 ; i < ioc->facts.NumberOfPorts; i++) { + r = _base_get_port_facts(ioc, i, CAN_SLEEP); + if (r) + goto out_free_resources; + } + r = _base_allocate_memory_pools(ioc, CAN_SLEEP); if (r) goto out_free_resources; @@ -3286,7 +3488,6 @@ mpt2sas_base_attach(struct MPT2SAS_ADAPTER *ioc) /* base internal command bits */ mutex_init(&ioc->base_cmds.mutex); - init_completion(&ioc->base_cmds.done); ioc->base_cmds.reply = kzalloc(ioc->reply_sz, GFP_KERNEL); ioc->base_cmds.status = MPT2_CMD_NOT_USED; @@ -3294,7 +3495,6 @@ mpt2sas_base_attach(struct MPT2SAS_ADAPTER *ioc) ioc->transport_cmds.reply = kzalloc(ioc->reply_sz, GFP_KERNEL); ioc->transport_cmds.status = MPT2_CMD_NOT_USED; mutex_init(&ioc->transport_cmds.mutex); - init_completion(&ioc->transport_cmds.done); /* task management internal command bits */ ioc->tm_cmds.reply = kzalloc(ioc->reply_sz, GFP_KERNEL); @@ -3310,7 +3510,6 @@ mpt2sas_base_attach(struct MPT2SAS_ADAPTER *ioc) ioc->ctl_cmds.reply = kzalloc(ioc->reply_sz, GFP_KERNEL); ioc->ctl_cmds.status = MPT2_CMD_NOT_USED; mutex_init(&ioc->ctl_cmds.mutex); - init_completion(&ioc->ctl_cmds.done); for (i = 0; i < MPI2_EVENT_NOTIFY_EVENTMASK_WORDS; i++) ioc->event_masks[i] = -1; @@ -3327,18 +3526,7 @@ mpt2sas_base_attach(struct MPT2SAS_ADAPTER *ioc) _base_unmask_events(ioc, MPI2_EVENT_IR_OPERATION_STATUS); _base_unmask_events(ioc, MPI2_EVENT_TASK_SET_FULL); _base_unmask_events(ioc, MPI2_EVENT_LOG_ENTRY_ADDED); - - ioc->pfacts = kcalloc(ioc->facts.NumberOfPorts, - sizeof(Mpi2PortFactsReply_t), GFP_KERNEL); - if (!ioc->pfacts) - goto out_free_resources; - - for (i = 0 ; i < ioc->facts.NumberOfPorts; i++) { - r = _base_get_port_facts(ioc, i, CAN_SLEEP); - if (r) - goto out_free_resources; - } - r = _base_make_ioc_operational(ioc, 0, CAN_SLEEP); + r = _base_make_ioc_operational(ioc, CAN_SLEEP); if (r) goto out_free_resources; @@ -3466,7 +3654,7 @@ _wait_for_commands_to_complete(struct MPT2SAS_ADAPTER *ioc, int sleep_flag) /* pending command count */ spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); - for (i = 0; i < ioc->request_depth; i++) + for (i = 0; i < ioc->scsiio_depth; i++) if (ioc->scsi_lookup[i].cb_idx != 0xFF) ioc->pending_io_count++; spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); @@ -3490,7 +3678,7 @@ int mpt2sas_base_hard_reset_handler(struct MPT2SAS_ADAPTER *ioc, int sleep_flag, enum reset_type type) { - int r, i; + int r; unsigned long flags; dtmprintk(ioc, printk(MPT2SAS_DEBUG_FMT "%s: enter\n", ioc->name, @@ -3513,9 +3701,7 @@ mpt2sas_base_hard_reset_handler(struct MPT2SAS_ADAPTER *ioc, int sleep_flag, if (r) goto out; _base_reset_handler(ioc, MPT2_IOC_AFTER_RESET); - for (i = 0 ; i < ioc->facts.NumberOfPorts; i++) - r = _base_make_ioc_operational(ioc, ioc->pfacts[i].VF_ID, - sleep_flag); + r = _base_make_ioc_operational(ioc, sleep_flag); if (!r) _base_reset_handler(ioc, MPT2_IOC_DONE_RESET); out: diff --git a/drivers/scsi/mpt2sas/mpt2sas_base.h b/drivers/scsi/mpt2sas/mpt2sas_base.h index 2faab1e690e9..0cf6bc236e4d 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_base.h +++ b/drivers/scsi/mpt2sas/mpt2sas_base.h @@ -3,7 +3,7 @@ * for access to MPT (Message Passing Technology) firmware. * * This code is based on drivers/scsi/mpt2sas/mpt2_base.h - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or @@ -69,10 +69,10 @@ #define MPT2SAS_DRIVER_NAME "mpt2sas" #define MPT2SAS_AUTHOR "LSI Corporation <DL-MPTFusionLinux@lsi.com>" #define MPT2SAS_DESCRIPTION "LSI MPT Fusion SAS 2.0 Device Driver" -#define MPT2SAS_DRIVER_VERSION "01.100.06.00" -#define MPT2SAS_MAJOR_VERSION 01 +#define MPT2SAS_DRIVER_VERSION "02.100.03.00" +#define MPT2SAS_MAJOR_VERSION 02 #define MPT2SAS_MINOR_VERSION 100 -#define MPT2SAS_BUILD_VERSION 06 +#define MPT2SAS_BUILD_VERSION 03 #define MPT2SAS_RELEASE_VERSION 00 /* @@ -264,6 +264,13 @@ struct _internal_cmd { * SAS Topology Structures */ +#define MPTSAS_STATE_TR_SEND 0x0001 +#define MPTSAS_STATE_TR_COMPLETE 0x0002 +#define MPTSAS_STATE_CNTRL_SEND 0x0004 +#define MPTSAS_STATE_CNTRL_COMPLETE 0x0008 + +#define MPT2SAS_REQ_SAS_CNTRL 0x0010 + /** * struct _sas_device - attached device information * @list: sas device list @@ -300,6 +307,7 @@ struct _sas_device { u16 slot; u8 hidden_raid_component; u8 responding; + u16 state; }; /** @@ -436,6 +444,17 @@ struct request_tracker { struct list_head tracker_list; }; +/** + * struct _tr_list - target reset list + * @handle: device handle + * @state: state machine + */ +struct _tr_list { + struct list_head list; + u16 handle; + u16 state; +}; + typedef void (*MPT_ADD_SGE)(void *paddr, u32 flags_length, dma_addr_t dma_addr); /** @@ -510,8 +529,9 @@ typedef void (*MPT_ADD_SGE)(void *paddr, u32 flags_length, dma_addr_t dma_addr); * @config_page_sz: config page size * @config_page: reserve memory for config page payload * @config_page_dma: + * @hba_queue_depth: hba request queue depth * @sge_size: sg element size for either 32/64 bit - * @request_depth: hba request queue depth + * @scsiio_depth: SCSI_IO queue depth * @request_sz: per request frame size * @request: pool of request frames * @request_dma: @@ -528,6 +548,18 @@ typedef void (*MPT_ADD_SGE)(void *paddr, u32 flags_length, dma_addr_t dma_addr); * @chains_needed_per_io: max chains per io * @chain_offset_value_for_main_message: location 1st sg in main * @chain_depth: total chains allocated + * @hi_priority_smid: + * @hi_priority: + * @hi_priority_dma: + * @hi_priority_depth: + * @hpr_lookup: + * @hpr_free_list: + * @internal_smid: + * @internal: + * @internal_dma: + * @internal_depth: + * @internal_lookup: + * @internal_free_list: * @sense: pool of sense * @sense_dma: * @sense_dma_pool: @@ -597,6 +629,8 @@ struct MPT2SAS_ADAPTER { u8 ctl_cb_idx; u8 base_cb_idx; u8 config_cb_idx; + u8 tm_tr_cb_idx; + u8 tm_sas_control_cb_idx; struct _internal_cmd base_cmds; struct _internal_cmd transport_cmds; struct _internal_cmd tm_cmds; @@ -643,9 +677,10 @@ struct MPT2SAS_ADAPTER { void *config_page; dma_addr_t config_page_dma; - /* request */ + /* scsiio request */ + u16 hba_queue_depth; u16 sge_size; - u16 request_depth; + u16 scsiio_depth; u16 request_sz; u8 *request; dma_addr_t request_dma; @@ -665,6 +700,22 @@ struct MPT2SAS_ADAPTER { u16 chain_offset_value_for_main_message; u16 chain_depth; + /* hi-priority queue */ + u16 hi_priority_smid; + u8 *hi_priority; + dma_addr_t hi_priority_dma; + u16 hi_priority_depth; + struct request_tracker *hpr_lookup; + struct list_head hpr_free_list; + + /* internal queue */ + u16 internal_smid; + u8 *internal; + dma_addr_t internal_dma; + u16 internal_depth; + struct request_tracker *internal_lookup; + struct list_head internal_free_list; + /* sense */ u8 *sense; dma_addr_t sense_dma; @@ -690,6 +741,8 @@ struct MPT2SAS_ADAPTER { struct dma_pool *reply_post_free_dma_pool; u32 reply_post_host_index; + struct list_head delayed_tr_list; + /* diag buffer support */ u8 *diag_buffer[MPI2_DIAG_BUF_TYPE_COUNT]; u32 diag_buffer_sz[MPI2_DIAG_BUF_TYPE_COUNT]; @@ -701,7 +754,7 @@ struct MPT2SAS_ADAPTER { u32 diagnostic_flags[MPI2_DIAG_BUF_TYPE_COUNT]; }; -typedef void (*MPT_CALLBACK)(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, +typedef u8 (*MPT_CALLBACK)(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, u32 reply); @@ -720,22 +773,28 @@ int mpt2sas_base_hard_reset_handler(struct MPT2SAS_ADAPTER *ioc, int sleep_flag, void *mpt2sas_base_get_msg_frame(struct MPT2SAS_ADAPTER *ioc, u16 smid); void *mpt2sas_base_get_sense_buffer(struct MPT2SAS_ADAPTER *ioc, u16 smid); void mpt2sas_base_build_zero_len_sge(struct MPT2SAS_ADAPTER *ioc, void *paddr); -dma_addr_t mpt2sas_base_get_msg_frame_dma(struct MPT2SAS_ADAPTER *ioc, u16 smid); -dma_addr_t mpt2sas_base_get_sense_buffer_dma(struct MPT2SAS_ADAPTER *ioc, u16 smid); +dma_addr_t mpt2sas_base_get_sense_buffer_dma(struct MPT2SAS_ADAPTER *ioc, + u16 smid); + +/* hi-priority queue */ +u16 mpt2sas_base_get_smid_hpr(struct MPT2SAS_ADAPTER *ioc, u8 cb_idx); +u16 mpt2sas_base_get_smid_scsiio(struct MPT2SAS_ADAPTER *ioc, u8 cb_idx, + struct scsi_cmnd *scmd); u16 mpt2sas_base_get_smid(struct MPT2SAS_ADAPTER *ioc, u8 cb_idx); void mpt2sas_base_free_smid(struct MPT2SAS_ADAPTER *ioc, u16 smid); -void mpt2sas_base_put_smid_scsi_io(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 vf_id, +void mpt2sas_base_put_smid_scsi_io(struct MPT2SAS_ADAPTER *ioc, u16 smid, u16 handle); -void mpt2sas_base_put_smid_hi_priority(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 vf_id); +void mpt2sas_base_put_smid_hi_priority(struct MPT2SAS_ADAPTER *ioc, u16 smid); void mpt2sas_base_put_smid_target_assist(struct MPT2SAS_ADAPTER *ioc, u16 smid, - u8 vf_id, u16 io_index); -void mpt2sas_base_put_smid_default(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 vf_id); + u16 io_index); +void mpt2sas_base_put_smid_default(struct MPT2SAS_ADAPTER *ioc, u16 smid); void mpt2sas_base_initialize_callback_handler(void); u8 mpt2sas_base_register_callback_handler(MPT_CALLBACK cb_func); void mpt2sas_base_release_callback_handler(u8 cb_idx); -void mpt2sas_base_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply); +u8 mpt2sas_base_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply); void *mpt2sas_base_get_reply_virt_addr(struct MPT2SAS_ADAPTER *ioc, u32 phys_addr); u32 mpt2sas_base_get_iocstate(struct MPT2SAS_ADAPTER *ioc, int cooked); @@ -749,6 +808,8 @@ int mpt2sas_base_scsi_enclosure_processor(struct MPT2SAS_ADAPTER *ioc, void mpt2sas_base_validate_event_type(struct MPT2SAS_ADAPTER *ioc, u32 *event_type); /* scsih shared API */ +u8 mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 msix_index, + u32 reply); void mpt2sas_scsih_issue_tm(struct MPT2SAS_ADAPTER *ioc, u16 handle, uint lun, u8 type, u16 smid_task, ulong timeout); void mpt2sas_scsih_set_tm_flag(struct MPT2SAS_ADAPTER *ioc, u16 handle); @@ -760,11 +821,11 @@ struct _sas_node *mpt2sas_scsih_expander_find_by_sas_address(struct MPT2SAS_ADAP struct _sas_device *mpt2sas_scsih_sas_device_find_by_sas_address( struct MPT2SAS_ADAPTER *ioc, u64 sas_address); -void mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply); void mpt2sas_scsih_reset_handler(struct MPT2SAS_ADAPTER *ioc, int reset_phase); /* config shared API */ -void mpt2sas_config_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply); +u8 mpt2sas_config_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply); int mpt2sas_config_get_number_hba_phys(struct MPT2SAS_ADAPTER *ioc, u8 *num_phys); int mpt2sas_config_get_manufacturing_pg0(struct MPT2SAS_ADAPTER *ioc, Mpi2ConfigReply_t *mpi_reply, Mpi2ManufacturingPage0_t *config_page); @@ -817,14 +878,17 @@ extern struct device_attribute *mpt2sas_host_attrs[]; extern struct device_attribute *mpt2sas_dev_attrs[]; void mpt2sas_ctl_init(void); void mpt2sas_ctl_exit(void); -void mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply); +u8 mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply); void mpt2sas_ctl_reset_handler(struct MPT2SAS_ADAPTER *ioc, int reset_phase); -void mpt2sas_ctl_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply); +u8 mpt2sas_ctl_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 msix_index, + u32 reply); void mpt2sas_ctl_add_to_event_log(struct MPT2SAS_ADAPTER *ioc, Mpi2EventNotificationReply_t *mpi_reply); /* transport shared API */ -void mpt2sas_transport_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply); +u8 mpt2sas_transport_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply); struct _sas_port *mpt2sas_transport_port_add(struct MPT2SAS_ADAPTER *ioc, u16 handle, u16 parent_handle); void mpt2sas_transport_port_remove(struct MPT2SAS_ADAPTER *ioc, u64 sas_address, @@ -838,6 +902,8 @@ void mpt2sas_transport_update_links(struct MPT2SAS_ADAPTER *ioc, u16 handle, extern struct sas_function_template mpt2sas_transport_functions; extern struct scsi_transport_template *mpt2sas_transport_template; extern int scsi_internal_device_block(struct scsi_device *sdev); +extern u8 mpt2sas_stm_zero_smid_handler(struct MPT2SAS_ADAPTER *ioc, + u8 msix_index, u32 reply); extern int scsi_internal_device_unblock(struct scsi_device *sdev); #endif /* MPT2SAS_BASE_H_INCLUDED */ diff --git a/drivers/scsi/mpt2sas/mpt2sas_config.c b/drivers/scsi/mpt2sas/mpt2sas_config.c index ab8c560865d8..594a389c6526 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_config.c +++ b/drivers/scsi/mpt2sas/mpt2sas_config.c @@ -2,7 +2,7 @@ * This module provides common API for accessing firmware configuration pages * * This code is based on drivers/scsi/mpt2sas/mpt2_base.c - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or @@ -227,23 +227,25 @@ _config_free_config_dma_memory(struct MPT2SAS_ADAPTER *ioc, * mpt2sas_config_done - config page completion routine * @ioc: per adapter object * @smid: system request message index - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * Context: none. * * The callback handler when using _config_request. * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -void -mpt2sas_config_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) +u8 +mpt2sas_config_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply) { MPI2DefaultReply_t *mpi_reply; if (ioc->config_cmds.status == MPT2_CMD_NOT_USED) - return; + return 1; if (ioc->config_cmds.smid != smid) - return; + return 1; ioc->config_cmds.status |= MPT2_CMD_COMPLETE; mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); if (mpi_reply) { @@ -257,6 +259,7 @@ mpt2sas_config_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) #endif ioc->config_cmds.smid = USHORT_MAX; complete(&ioc->config_cmds.done); + return 1; } /** @@ -303,6 +306,9 @@ _config_request(struct MPT2SAS_ADAPTER *ioc, Mpi2ConfigRequest_t retry_count = 0; memset(&mem, 0, sizeof(struct config_request)); + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; + if (config_page) { mpi_request->Header.PageVersion = mpi_reply->Header.PageVersion; mpi_request->Header.PageNumber = mpi_reply->Header.PageNumber; @@ -380,7 +386,7 @@ _config_request(struct MPT2SAS_ADAPTER *ioc, Mpi2ConfigRequest_t _config_display_some_debug(ioc, smid, "config_request", NULL); #endif init_completion(&ioc->config_cmds.done); - mpt2sas_base_put_smid_default(ioc, smid, config_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); timeleft = wait_for_completion_timeout(&ioc->config_cmds.done, timeout*HZ); if (!(ioc->config_cmds.status & MPT2_CMD_COMPLETE)) { diff --git a/drivers/scsi/mpt2sas/mpt2sas_ctl.c b/drivers/scsi/mpt2sas/mpt2sas_ctl.c index c2a51018910f..57d724633906 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_ctl.c +++ b/drivers/scsi/mpt2sas/mpt2sas_ctl.c @@ -3,7 +3,7 @@ * controllers * * This code is based on drivers/scsi/mpt2sas/mpt2_ctl.c - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or @@ -219,23 +219,25 @@ _ctl_display_some_debug(struct MPT2SAS_ADAPTER *ioc, u16 smid, * mpt2sas_ctl_done - ctl module completion routine * @ioc: per adapter object * @smid: system request message index - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * Context: none. * * The callback handler when using ioc->ctl_cb_idx. * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -void -mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) +u8 +mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply) { MPI2DefaultReply_t *mpi_reply; if (ioc->ctl_cmds.status == MPT2_CMD_NOT_USED) - return; + return 1; if (ioc->ctl_cmds.smid != smid) - return; + return 1; ioc->ctl_cmds.status |= MPT2_CMD_COMPLETE; mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); if (mpi_reply) { @@ -247,6 +249,7 @@ mpt2sas_ctl_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) #endif ioc->ctl_cmds.status &= ~MPT2_CMD_PENDING; complete(&ioc->ctl_cmds.done); + return 1; } /** @@ -328,22 +331,25 @@ mpt2sas_ctl_add_to_event_log(struct MPT2SAS_ADAPTER *ioc, /** * mpt2sas_ctl_event_callback - firmware event handler (called at ISR time) * @ioc: per adapter object - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * Context: interrupt. * * This function merely adds a new work task into ioc->firmware_event_thread. * The tasks are worked from _firmware_event_work in user context. * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -void -mpt2sas_ctl_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) +u8 +mpt2sas_ctl_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 msix_index, + u32 reply) { Mpi2EventNotificationReply_t *mpi_reply; mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); mpt2sas_ctl_add_to_event_log(ioc, mpi_reply); + return 1; } /** @@ -507,7 +513,7 @@ _ctl_set_task_mid(struct MPT2SAS_ADAPTER *ioc, struct mpt2_ioctl_command *karg, handle = le16_to_cpu(tm_request->DevHandle); spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); - for (i = ioc->request_depth; i && !found; i--) { + for (i = ioc->scsiio_depth; i && !found; i--) { scmd = ioc->scsi_lookup[i - 1].scmd; if (scmd == NULL || scmd->device == NULL || scmd->device->hostdata == NULL) @@ -614,7 +620,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, printk(MPT2SAS_INFO_FMT "%s: ioc is operational\n", ioc->name, __func__); - smid = mpt2sas_base_get_smid(ioc, ioc->ctl_cb_idx); + smid = mpt2sas_base_get_smid_scsiio(ioc, ioc->ctl_cb_idx, NULL); if (!smid) { printk(MPT2SAS_ERR_FMT "%s: failed obtaining a smid\n", ioc->name, __func__); @@ -737,7 +743,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, (u32)mpt2sas_base_get_sense_buffer_dma(ioc, smid); priv_sense = mpt2sas_base_get_sense_buffer(ioc, smid); memset(priv_sense, 0, SCSI_SENSE_BUFFERSIZE); - mpt2sas_base_put_smid_scsi_io(ioc, smid, 0, + mpt2sas_base_put_smid_scsi_io(ioc, smid, le16_to_cpu(mpi_request->FunctionDependent1)); break; } @@ -759,8 +765,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, mutex_lock(&ioc->tm_cmds.mutex); mpt2sas_scsih_set_tm_flag(ioc, le16_to_cpu( tm_request->DevHandle)); - mpt2sas_base_put_smid_hi_priority(ioc, smid, - mpi_request->VF_ID); + mpt2sas_base_put_smid_hi_priority(ioc, smid); break; } case MPI2_FUNCTION_SMP_PASSTHROUGH: @@ -781,7 +786,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, ioc->ioc_link_reset_in_progress = 1; ioc->ignore_loginfos = 1; } - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); break; } case MPI2_FUNCTION_SAS_IO_UNIT_CONTROL: @@ -795,11 +800,11 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, ioc->ioc_link_reset_in_progress = 1; ioc->ignore_loginfos = 1; } - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); break; } default: - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); break; } @@ -807,6 +812,7 @@ _ctl_do_mpt_command(struct MPT2SAS_ADAPTER *ioc, timeout = MPT2_IOCTL_DEFAULT_TIMEOUT; else timeout = karg.timeout; + init_completion(&ioc->ctl_cmds.done); timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, timeout*HZ); if (mpi_request->Function == MPI2_FUNCTION_SCSI_TASK_MGMT) { @@ -1371,6 +1377,8 @@ _ctl_diag_register(void __user *arg, enum block_state state) mpi_request->Flags = cpu_to_le32(karg.diagnostic_flags); mpi_request->BufferAddress = cpu_to_le64(request_data_dma); mpi_request->BufferLength = cpu_to_le32(request_data_sz); + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; dctlprintk(ioc, printk(MPT2SAS_DEBUG_FMT "%s: diag_buffer(0x%p), " "dma(0x%llx), sz(%d)\n", ioc->name, __func__, request_data, @@ -1380,7 +1388,8 @@ _ctl_diag_register(void __user *arg, enum block_state state) mpi_request->ProductSpecific[i] = cpu_to_le32(ioc->product_specific[buffer_type][i]); - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->ctl_cmds.done); timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); @@ -1643,8 +1652,11 @@ _ctl_send_release(struct MPT2SAS_ADAPTER *ioc, u8 buffer_type, u8 *issue_reset) mpi_request->Function = MPI2_FUNCTION_DIAG_RELEASE; mpi_request->BufferType = buffer_type; + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->ctl_cmds.done); timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); @@ -1902,8 +1914,11 @@ _ctl_diag_read_buffer(void __user *arg, enum block_state state) for (i = 0; i < MPT2_PRODUCT_SPECIFIC_DWORDS; i++) mpi_request->ProductSpecific[i] = cpu_to_le32(ioc->product_specific[buffer_type][i]); + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; - mpt2sas_base_put_smid_default(ioc, smid, mpi_request->VF_ID); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->ctl_cmds.done); timeleft = wait_for_completion_timeout(&ioc->ctl_cmds.done, MPT2_IOCTL_DEFAULT_TIMEOUT*HZ); @@ -2069,6 +2084,7 @@ static long _ctl_ioctl(struct file *file, unsigned int cmd, unsigned long arg) { long ret; + lock_kernel(); ret = _ctl_ioctl_main(file, cmd, (void __user *)arg); unlock_kernel(); @@ -2143,6 +2159,7 @@ static long _ctl_ioctl_compat(struct file *file, unsigned cmd, unsigned long arg) { long ret; + lock_kernel(); if (cmd == MPT2COMMAND32) ret = _ctl_compat_mpt_command(file, cmd, arg); diff --git a/drivers/scsi/mpt2sas/mpt2sas_ctl.h b/drivers/scsi/mpt2sas/mpt2sas_ctl.h index 4da11435533f..211f296dd191 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_ctl.h +++ b/drivers/scsi/mpt2sas/mpt2sas_ctl.h @@ -3,7 +3,7 @@ * controllers * * This code is based on drivers/scsi/mpt2sas/mpt2_ctl.h - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/mpt2sas/mpt2sas_debug.h b/drivers/scsi/mpt2sas/mpt2sas_debug.h index ad325096e842..5308a25cb307 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_debug.h +++ b/drivers/scsi/mpt2sas/mpt2sas_debug.h @@ -2,7 +2,7 @@ * Logging Support for MPT (Message Passing Technology) based controllers * * This code is based on drivers/scsi/mpt2sas/mpt2_debug.c - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or diff --git a/drivers/scsi/mpt2sas/mpt2sas_scsih.c b/drivers/scsi/mpt2sas/mpt2sas_scsih.c index 774b34525bba..86ab32d7ab15 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_scsih.c +++ b/drivers/scsi/mpt2sas/mpt2sas_scsih.c @@ -2,7 +2,7 @@ * Scsi Host Layer for MPT (Message Passing Technology) based controllers * * This code is based on drivers/scsi/mpt2sas/mpt2_scsih.c - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or @@ -79,6 +79,9 @@ static u8 transport_cb_idx = -1; static u8 config_cb_idx = -1; static int mpt_ids; +static u8 tm_tr_cb_idx = -1 ; +static u8 tm_sas_control_cb_idx = -1; + /* command line options */ static u32 logging_level; MODULE_PARM_DESC(logging_level, " bits for enabling additional logging info " @@ -109,6 +112,7 @@ struct sense_info { * @work: work object (ioc->fault_reset_work_q) * @ioc: per adapter object * @VF_ID: virtual function id + * @VP_ID: virtual port id * @host_reset_handling: handling events during host reset * @ignore: flag meaning this event has been marked to ignore * @event: firmware event MPI2_EVENT_XXX defined in mpt2_ioc.h @@ -121,6 +125,7 @@ struct fw_event_work { struct work_struct work; struct MPT2SAS_ADAPTER *ioc; u8 VF_ID; + u8 VP_ID; u8 host_reset_handling; u8 ignore; u16 event; @@ -138,8 +143,10 @@ struct fw_event_work { * @lun: lun number * @cdb_length: cdb length * @cdb: cdb contents - * @valid_reply: flag set for reply message * @timeout: timeout for this command + * @VF_ID: virtual function id + * @VP_ID: virtual port id + * @valid_reply: flag set for reply message * @sense_length: sense length * @ioc_status: ioc status * @scsi_state: scsi state @@ -161,6 +168,8 @@ struct _scsi_io_transfer { u8 cdb_length; u8 cdb[32]; u8 timeout; + u8 VF_ID; + u8 VP_ID; u8 valid_reply; /* the following bits are only valid when 'valid_reply = 1' */ u32 sense_length; @@ -756,66 +765,16 @@ _scsih_is_end_device(u32 device_info) } /** - * _scsih_scsi_lookup_get - returns scmd entry + * mptscsih_get_scsi_lookup - returns scmd entry * @ioc: per adapter object * @smid: system request message index - * Context: This function will acquire ioc->scsi_lookup_lock. * * Returns the smid stored scmd pointer. */ static struct scsi_cmnd * _scsih_scsi_lookup_get(struct MPT2SAS_ADAPTER *ioc, u16 smid) { - unsigned long flags; - struct scsi_cmnd *scmd; - - spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); - scmd = ioc->scsi_lookup[smid - 1].scmd; - spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); - return scmd; -} - -/** - * mptscsih_getclear_scsi_lookup - returns scmd entry - * @ioc: per adapter object - * @smid: system request message index - * Context: This function will acquire ioc->scsi_lookup_lock. - * - * Returns the smid stored scmd pointer, as well as clearing the scmd pointer. - */ -static struct scsi_cmnd * -_scsih_scsi_lookup_getclear(struct MPT2SAS_ADAPTER *ioc, u16 smid) -{ - unsigned long flags; - struct scsi_cmnd *scmd; - - spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); - scmd = ioc->scsi_lookup[smid - 1].scmd; - ioc->scsi_lookup[smid - 1].scmd = NULL; - spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); - return scmd; -} - -/** - * _scsih_scsi_lookup_set - updates scmd entry in lookup - * @ioc: per adapter object - * @smid: system request message index - * @scmd: pointer to scsi command object - * Context: This function will acquire ioc->scsi_lookup_lock. - * - * This will save scmd pointer in the scsi_lookup array. - * - * Return nothing. - */ -static void -_scsih_scsi_lookup_set(struct MPT2SAS_ADAPTER *ioc, u16 smid, - struct scsi_cmnd *scmd) -{ - unsigned long flags; - - spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); - ioc->scsi_lookup[smid - 1].scmd = scmd; - spin_unlock_irqrestore(&ioc->scsi_lookup_lock, flags); + return ioc->scsi_lookup[smid - 1].scmd; } /** @@ -838,9 +797,9 @@ _scsih_scsi_lookup_find_by_scmd(struct MPT2SAS_ADAPTER *ioc, struct scsi_cmnd spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); smid = 0; - for (i = 0; i < ioc->request_depth; i++) { + for (i = 0; i < ioc->scsiio_depth; i++) { if (ioc->scsi_lookup[i].scmd == scmd) { - smid = i + 1; + smid = ioc->scsi_lookup[i].smid; goto out; } } @@ -869,7 +828,7 @@ _scsih_scsi_lookup_find_by_target(struct MPT2SAS_ADAPTER *ioc, int id, spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); found = 0; - for (i = 0 ; i < ioc->request_depth; i++) { + for (i = 0 ; i < ioc->scsiio_depth; i++) { if (ioc->scsi_lookup[i].scmd && (ioc->scsi_lookup[i].scmd->device->id == id && ioc->scsi_lookup[i].scmd->device->channel == channel)) { @@ -903,7 +862,7 @@ _scsih_scsi_lookup_find_by_lun(struct MPT2SAS_ADAPTER *ioc, int id, spin_lock_irqsave(&ioc->scsi_lookup_lock, flags); found = 0; - for (i = 0 ; i < ioc->request_depth; i++) { + for (i = 0 ; i < ioc->scsiio_depth; i++) { if (ioc->scsi_lookup[i].scmd && (ioc->scsi_lookup[i].scmd->device->id == id && ioc->scsi_lookup[i].scmd->device->channel == channel && @@ -1113,7 +1072,7 @@ _scsih_change_queue_depth(struct scsi_device *sdev, int qdepth) } /** - * _scsih_change_queue_depth - changing device queue tag type + * _scsih_change_queue_type - changing device queue tag type * @sdev: scsi device struct * @tag_type: requested tag type * @@ -1679,23 +1638,24 @@ _scsih_response_code(struct MPT2SAS_ADAPTER *ioc, u8 response_code) * _scsih_tm_done - tm completion routine * @ioc: per adapter object * @smid: system request message index - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * Context: none. * * The callback handler when using scsih_issue_tm. * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -static void -_scsih_tm_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) +static u8 +_scsih_tm_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, u32 reply) { MPI2DefaultReply_t *mpi_reply; if (ioc->tm_cmds.status == MPT2_CMD_NOT_USED) - return; + return 1; if (ioc->tm_cmds.smid != smid) - return; + return 1; ioc->tm_cmds.status |= MPT2_CMD_COMPLETE; mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); if (mpi_reply) { @@ -1704,6 +1664,7 @@ _scsih_tm_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) } ioc->tm_cmds.status &= ~MPT2_CMD_PENDING; complete(&ioc->tm_cmds.done); + return 1; } /** @@ -1790,7 +1751,6 @@ mpt2sas_scsih_issue_tm(struct MPT2SAS_ADAPTER *ioc, u16 handle, uint lun, u16 smid = 0; u32 ioc_state; unsigned long timeleft; - u8 VF_ID = 0; if (ioc->tm_cmds.status != MPT2_CMD_NOT_USED) { printk(MPT2SAS_INFO_FMT "%s: tm_cmd busy!!!\n", @@ -1817,7 +1777,7 @@ mpt2sas_scsih_issue_tm(struct MPT2SAS_ADAPTER *ioc, u16 handle, uint lun, goto issue_host_reset; } - smid = mpt2sas_base_get_smid(ioc, ioc->tm_cb_idx); + smid = mpt2sas_base_get_smid_hpr(ioc, ioc->tm_cb_idx); if (!smid) { printk(MPT2SAS_ERR_FMT "%s: failed obtaining a smid\n", ioc->name, __func__); @@ -1825,7 +1785,8 @@ mpt2sas_scsih_issue_tm(struct MPT2SAS_ADAPTER *ioc, u16 handle, uint lun, } dtmprintk(ioc, printk(MPT2SAS_INFO_FMT "sending tm: handle(0x%04x)," - " task_type(0x%02x), smid(%d)\n", ioc->name, handle, type, smid)); + " task_type(0x%02x), smid(%d)\n", ioc->name, handle, type, + smid_task)); ioc->tm_cmds.status = MPT2_CMD_PENDING; mpi_request = mpt2sas_base_get_msg_frame(ioc, smid); ioc->tm_cmds.smid = smid; @@ -1834,10 +1795,12 @@ mpt2sas_scsih_issue_tm(struct MPT2SAS_ADAPTER *ioc, u16 handle, uint lun, mpi_request->DevHandle = cpu_to_le16(handle); mpi_request->TaskType = type; mpi_request->TaskMID = cpu_to_le16(smid_task); + mpi_request->VP_ID = 0; /* TODO */ + mpi_request->VF_ID = 0; int_to_scsilun(lun, (struct scsi_lun *)mpi_request->LUN); mpt2sas_scsih_set_tm_flag(ioc, handle); init_completion(&ioc->tm_cmds.done); - mpt2sas_base_put_smid_hi_priority(ioc, smid, VF_ID); + mpt2sas_base_put_smid_hi_priority(ioc, smid); timeleft = wait_for_completion_timeout(&ioc->tm_cmds.done, timeout*HZ); mpt2sas_scsih_clear_tm_flag(ioc, handle); if (!(ioc->tm_cmds.status & MPT2_CMD_COMPLETE)) { @@ -2075,7 +2038,7 @@ _scsih_target_reset(struct scsi_cmnd *scmd) } /** - * _scsih_abort - eh threads main host reset routine + * _scsih_host_reset - eh threads main host reset routine * @sdev: scsi device struct * * Returns SUCCESS if command aborted else FAILED @@ -2354,6 +2317,231 @@ _scsih_block_io_to_children_attached_directly(struct MPT2SAS_ADAPTER *ioc, } /** + * _scsih_tm_tr_send - send task management request + * @ioc: per adapter object + * @handle: device handle + * Context: interrupt time. + * + * This code is to initiate the device removal handshake protocal + * with controller firmware. This function will issue target reset + * using high priority request queue. It will send a sas iounit + * controll request (MPI2_SAS_OP_REMOVE_DEVICE) from this completion. + * + * This is designed to send muliple task management request at the same + * time to the fifo. If the fifo is full, we will append the request, + * and process it in a future completion. + */ +static void +_scsih_tm_tr_send(struct MPT2SAS_ADAPTER *ioc, u16 handle) +{ + Mpi2SCSITaskManagementRequest_t *mpi_request; + struct MPT2SAS_TARGET *sas_target_priv_data; + u16 smid; + struct _sas_device *sas_device; + unsigned long flags; + struct _tr_list *delayed_tr; + + if (ioc->shost_recovery) { + printk(MPT2SAS_INFO_FMT "%s: host reset in progress!\n", + __func__, ioc->name); + return; + } + + spin_lock_irqsave(&ioc->sas_device_lock, flags); + sas_device = _scsih_sas_device_find_by_handle(ioc, handle); + if (!sas_device) { + spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + printk(MPT2SAS_ERR_FMT "%s: failed finding sas_device\n", + ioc->name, __func__); + return; + } + spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + + /* skip is hidden raid component */ + if (sas_device->hidden_raid_component) + return; + + smid = mpt2sas_base_get_smid_hpr(ioc, ioc->tm_tr_cb_idx); + if (!smid) { + delayed_tr = kzalloc(sizeof(*delayed_tr), GFP_ATOMIC); + if (!delayed_tr) + return; + INIT_LIST_HEAD(&delayed_tr->list); + delayed_tr->handle = handle; + delayed_tr->state = MPT2SAS_REQ_SAS_CNTRL; + list_add_tail(&delayed_tr->list, + &ioc->delayed_tr_list); + if (sas_device->starget) + dewtprintk(ioc, starget_printk(KERN_INFO, + sas_device->starget, "DELAYED:tr:handle(0x%04x), " + "(open)\n", sas_device->handle)); + return; + } + + if (sas_device->starget && sas_device->starget->hostdata) { + sas_target_priv_data = sas_device->starget->hostdata; + sas_target_priv_data->tm_busy = 1; + dewtprintk(ioc, starget_printk(KERN_INFO, sas_device->starget, + "tr:handle(0x%04x), (open)\n", sas_device->handle)); + } + + mpi_request = mpt2sas_base_get_msg_frame(ioc, smid); + memset(mpi_request, 0, sizeof(Mpi2SCSITaskManagementRequest_t)); + mpi_request->Function = MPI2_FUNCTION_SCSI_TASK_MGMT; + mpi_request->DevHandle = cpu_to_le16(handle); + mpi_request->TaskType = MPI2_SCSITASKMGMT_TASKTYPE_TARGET_RESET; + sas_device->state |= MPTSAS_STATE_TR_SEND; + sas_device->state |= MPT2SAS_REQ_SAS_CNTRL; + mpt2sas_base_put_smid_hi_priority(ioc, smid); +} + + + +/** + * _scsih_sas_control_complete - completion routine + * @ioc: per adapter object + * @smid: system request message index + * @msix_index: MSIX table index supplied by the OS + * @reply: reply message frame(lower 32bit addr) + * Context: interrupt time. + * + * This is the sas iounit controll completion routine. + * This code is part of the code to initiate the device removal + * handshake protocal with controller firmware. + * + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. + */ +static u8 +_scsih_sas_control_complete(struct MPT2SAS_ADAPTER *ioc, u16 smid, + u8 msix_index, u32 reply) +{ + unsigned long flags; + u16 handle; + struct _sas_device *sas_device; + Mpi2SasIoUnitControlReply_t *mpi_reply = + mpt2sas_base_get_reply_virt_addr(ioc, reply); + + handle = le16_to_cpu(mpi_reply->DevHandle); + + spin_lock_irqsave(&ioc->sas_device_lock, flags); + sas_device = _scsih_sas_device_find_by_handle(ioc, handle); + if (!sas_device) { + spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + printk(MPT2SAS_ERR_FMT "%s: failed finding sas_device\n", + ioc->name, __func__); + return 1; + } + sas_device->state |= MPTSAS_STATE_CNTRL_COMPLETE; + spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + + if (sas_device->starget) + dewtprintk(ioc, starget_printk(KERN_INFO, sas_device->starget, + "sc_complete:handle(0x%04x), " + "ioc_status(0x%04x), loginfo(0x%08x)\n", + handle, le16_to_cpu(mpi_reply->IOCStatus), + le32_to_cpu(mpi_reply->IOCLogInfo))); + return 1; +} + +/** + * _scsih_tm_tr_complete - + * @ioc: per adapter object + * @smid: system request message index + * @msix_index: MSIX table index supplied by the OS + * @reply: reply message frame(lower 32bit addr) + * Context: interrupt time. + * + * This is the target reset completion routine. + * This code is part of the code to initiate the device removal + * handshake protocal with controller firmware. + * It will send a sas iounit controll request (MPI2_SAS_OP_REMOVE_DEVICE) + * + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. + */ +static u8 +_scsih_tm_tr_complete(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, + u32 reply) +{ + unsigned long flags; + u16 handle; + struct _sas_device *sas_device; + Mpi2SCSITaskManagementReply_t *mpi_reply = + mpt2sas_base_get_reply_virt_addr(ioc, reply); + Mpi2SasIoUnitControlRequest_t *mpi_request; + u16 smid_sas_ctrl; + struct MPT2SAS_TARGET *sas_target_priv_data; + struct _tr_list *delayed_tr; + u8 rc; + + handle = le16_to_cpu(mpi_reply->DevHandle); + spin_lock_irqsave(&ioc->sas_device_lock, flags); + sas_device = _scsih_sas_device_find_by_handle(ioc, handle); + if (!sas_device) { + spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + printk(MPT2SAS_ERR_FMT "%s: failed finding sas_device\n", + ioc->name, __func__); + return 1; + } + sas_device->state |= MPTSAS_STATE_TR_COMPLETE; + spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + + if (sas_device->starget) + dewtprintk(ioc, starget_printk(KERN_INFO, sas_device->starget, + "tr_complete:handle(0x%04x), (%s) ioc_status(0x%04x), " + "loginfo(0x%08x), completed(%d)\n", + sas_device->handle, (sas_device->state & + MPT2SAS_REQ_SAS_CNTRL) ? "open" : "active", + le16_to_cpu(mpi_reply->IOCStatus), + le32_to_cpu(mpi_reply->IOCLogInfo), + le32_to_cpu(mpi_reply->TerminationCount))); + + if (sas_device->starget && sas_device->starget->hostdata) { + sas_target_priv_data = sas_device->starget->hostdata; + sas_target_priv_data->tm_busy = 0; + } + + if (!list_empty(&ioc->delayed_tr_list)) { + delayed_tr = list_entry(ioc->delayed_tr_list.next, + struct _tr_list, list); + mpt2sas_base_free_smid(ioc, smid); + if (delayed_tr->state & MPT2SAS_REQ_SAS_CNTRL) + _scsih_tm_tr_send(ioc, delayed_tr->handle); + list_del(&delayed_tr->list); + kfree(delayed_tr); + rc = 0; /* tells base_interrupt not to free mf */ + } else + rc = 1; + + + if (!(sas_device->state & MPT2SAS_REQ_SAS_CNTRL)) + return rc; + + if (ioc->shost_recovery) { + printk(MPT2SAS_INFO_FMT "%s: host reset in progress!\n", + __func__, ioc->name); + return rc; + } + + smid_sas_ctrl = mpt2sas_base_get_smid(ioc, ioc->tm_sas_control_cb_idx); + if (!smid_sas_ctrl) { + printk(MPT2SAS_ERR_FMT "%s: failed obtaining a smid\n", + ioc->name, __func__); + return rc; + } + + mpi_request = mpt2sas_base_get_msg_frame(ioc, smid_sas_ctrl); + memset(mpi_request, 0, sizeof(Mpi2SasIoUnitControlRequest_t)); + mpi_request->Function = MPI2_FUNCTION_SAS_IO_UNIT_CONTROL; + mpi_request->Operation = MPI2_SAS_OP_REMOVE_DEVICE; + mpi_request->DevHandle = mpi_reply->DevHandle; + sas_device->state |= MPTSAS_STATE_CNTRL_SEND; + mpt2sas_base_put_smid_default(ioc, smid_sas_ctrl); + return rc; +} + +/** * _scsih_check_topo_delete_events - sanity check on topo events * @ioc: per adapter object * @event_data: the event data payload @@ -2375,6 +2563,21 @@ _scsih_check_topo_delete_events(struct MPT2SAS_ADAPTER *ioc, u16 expander_handle; struct _sas_node *sas_expander; unsigned long flags; + int i, reason_code; + u16 handle; + + for (i = 0 ; i < event_data->NumEntries; i++) { + if (event_data->PHY[i].PhyStatus & + MPI2_EVENT_SAS_TOPO_PHYSTATUS_VACANT) + continue; + handle = le16_to_cpu(event_data->PHY[i].AttachedDevHandle); + if (!handle) + continue; + reason_code = event_data->PHY[i].PhyStatus & + MPI2_EVENT_SAS_TOPO_RC_MASK; + if (reason_code == MPI2_EVENT_SAS_TOPO_RC_TARG_NOT_RESPONDING) + _scsih_tm_tr_send(ioc, handle); + } expander_handle = le16_to_cpu(event_data->ExpanderDevHandle); if (expander_handle < ioc->sas_hba.num_phys) { @@ -2433,8 +2636,8 @@ _scsih_flush_running_cmds(struct MPT2SAS_ADAPTER *ioc) u16 smid; u16 count = 0; - for (smid = 1; smid <= ioc->request_depth; smid++) { - scmd = _scsih_scsi_lookup_getclear(ioc, smid); + for (smid = 1; smid <= ioc->scsiio_depth; smid++) { + scmd = _scsih_scsi_lookup_get(ioc, smid); if (!scmd) continue; count++; @@ -2616,7 +2819,7 @@ _scsih_qcmd(struct scsi_cmnd *scmd, void (*done)(struct scsi_cmnd *)) if ((sas_device_priv_data->flags & MPT_DEVICE_TLR_ON)) mpi_control |= MPI2_SCSIIO_CONTROL_TLR_ON; - smid = mpt2sas_base_get_smid(ioc, ioc->scsi_io_cb_idx); + smid = mpt2sas_base_get_smid_scsiio(ioc, ioc->scsi_io_cb_idx, scmd); if (!smid) { printk(MPT2SAS_ERR_FMT "%s: failed obtaining a smid\n", ioc->name, __func__); @@ -2643,7 +2846,8 @@ _scsih_qcmd(struct scsi_cmnd *scmd, void (*done)(struct scsi_cmnd *)) mpi_request->SGLOffset0 = offsetof(Mpi2SCSIIORequest_t, SGL) / 4; mpi_request->SGLFlags = cpu_to_le16(MPI2_SCSIIO_SGLFLAGS_TYPE_MPI + MPI2_SCSIIO_SGLFLAGS_SYSTEM_ADDR); - + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; int_to_scsilun(sas_device_priv_data->lun, (struct scsi_lun *) mpi_request->LUN); memcpy(mpi_request->CDB.CDB32, scmd->cmnd, scmd->cmd_len); @@ -2657,8 +2861,7 @@ _scsih_qcmd(struct scsi_cmnd *scmd, void (*done)(struct scsi_cmnd *)) } } - _scsih_scsi_lookup_set(ioc, smid, scmd); - mpt2sas_base_put_smid_scsi_io(ioc, smid, 0, + mpt2sas_base_put_smid_scsi_io(ioc, smid, sas_device_priv_data->sas_target->handle); return 0; @@ -2954,15 +3157,16 @@ _scsih_smart_predicted_fault(struct MPT2SAS_ADAPTER *ioc, u16 handle) * _scsih_io_done - scsi request callback * @ioc: per adapter object * @smid: system request message index - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * - * Callback handler when using scsih_qcmd. + * Callback handler when using _scsih_qcmd. * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -static void -_scsih_io_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) +static u8 +_scsih_io_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, u32 reply) { Mpi2SCSIIORequest_t *mpi_request; Mpi2SCSIIOReply_t *mpi_reply; @@ -2976,9 +3180,9 @@ _scsih_io_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) u32 response_code; mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); - scmd = _scsih_scsi_lookup_getclear(ioc, smid); + scmd = _scsih_scsi_lookup_get(ioc, smid); if (scmd == NULL) - return; + return 1; mpi_request = mpt2sas_base_get_msg_frame(ioc, smid); @@ -3134,6 +3338,7 @@ _scsih_io_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, u32 reply) out: scsi_dma_unmap(scmd); scmd->scsi_done(scmd); + return 1; } /** @@ -3398,9 +3603,8 @@ _scsih_expander_add(struct MPT2SAS_ADAPTER *ioc, u16 handle) } } - sas_address = le64_to_cpu(expander_pg0.SASAddress); - spin_lock_irqsave(&ioc->sas_node_lock, flags); + sas_address = le64_to_cpu(expander_pg0.SASAddress); sas_expander = mpt2sas_scsih_expander_find_by_sas_address(ioc, sas_address); spin_unlock_irqrestore(&ioc->sas_node_lock, flags); @@ -3666,6 +3870,12 @@ _scsih_remove_device(struct MPT2SAS_ADAPTER *ioc, u16 handle) if (ioc->remove_host) goto out; + if ((sas_device->state & MPTSAS_STATE_TR_COMPLETE)) { + dewtprintk(ioc, printk(MPT2SAS_INFO_FMT "\tskip " + "target_reset handle(0x%04x)\n", ioc->name, handle)); + goto skip_tr; + } + /* Target Reset to flush out all the outstanding IO */ device_handle = (sas_device->hidden_raid_component) ? sas_device->volume_handle : handle; @@ -3682,6 +3892,13 @@ _scsih_remove_device(struct MPT2SAS_ADAPTER *ioc, u16 handle) if (ioc->shost_recovery) goto out; } + skip_tr: + + if ((sas_device->state & MPTSAS_STATE_CNTRL_COMPLETE)) { + dewtprintk(ioc, printk(MPT2SAS_INFO_FMT "\tskip " + "sas_cntrl handle(0x%04x)\n", ioc->name, handle)); + goto out; + } /* SAS_IO_UNIT_CNTR - send REMOVE_DEVICE */ dewtprintk(ioc, printk(MPT2SAS_INFO_FMT "sas_iounit: handle" @@ -3690,7 +3907,8 @@ _scsih_remove_device(struct MPT2SAS_ADAPTER *ioc, u16 handle) mpi_request.Function = MPI2_FUNCTION_SAS_IO_UNIT_CONTROL; mpi_request.Operation = MPI2_SAS_OP_REMOVE_DEVICE; mpi_request.DevHandle = handle; - mpi_request.VF_ID = 0; + mpi_request.VF_ID = 0; /* TODO */ + mpi_request.VP_ID = 0; if ((mpt2sas_base_sas_iounit_control(ioc, &mpi_reply, &mpi_request)) != 0) { printk(MPT2SAS_ERR_FMT "failure at %s:%d/%s()!\n", @@ -3800,15 +4018,12 @@ _scsih_sas_topology_change_event_debug(struct MPT2SAS_ADAPTER *ioc, /** * _scsih_sas_topology_change_event - handle topology changes * @ioc: per adapter object - * @VF_ID: - * @event_data: event data payload - * fw_event: + * @fw_event: The fw_event_work object * Context: user. * */ static void -_scsih_sas_topology_change_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataSasTopologyChangeList_t *event_data, +_scsih_sas_topology_change_event(struct MPT2SAS_ADAPTER *ioc, struct fw_event_work *fw_event) { int i; @@ -3818,6 +4033,7 @@ _scsih_sas_topology_change_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, struct _sas_node *sas_expander; unsigned long flags; u8 link_rate_; + Mpi2EventDataSasTopologyChangeList_t *event_data = fw_event->event_data; #ifdef CONFIG_SCSI_MPT2SAS_LOGGING if (ioc->logging_level & MPT_DEBUG_EVENT_WORK_TASK) @@ -3851,15 +4067,16 @@ _scsih_sas_topology_change_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, } if (ioc->shost_recovery) return; - if (event_data->PHY[i].PhyStatus & - MPI2_EVENT_SAS_TOPO_PHYSTATUS_VACANT) + phy_number = event_data->StartPhyNum + i; + reason_code = event_data->PHY[i].PhyStatus & + MPI2_EVENT_SAS_TOPO_RC_MASK; + if ((event_data->PHY[i].PhyStatus & + MPI2_EVENT_SAS_TOPO_PHYSTATUS_VACANT) && (reason_code != + MPI2_EVENT_SAS_TOPO_RC_TARG_NOT_RESPONDING)) continue; handle = le16_to_cpu(event_data->PHY[i].AttachedDevHandle); if (!handle) continue; - phy_number = event_data->StartPhyNum + i; - reason_code = event_data->PHY[i].PhyStatus & - MPI2_EVENT_SAS_TOPO_RC_MASK; link_rate_ = event_data->PHY[i].LinkRate >> 4; switch (reason_code) { case MPI2_EVENT_SAS_TOPO_RC_PHY_CHANGED: @@ -3971,19 +4188,19 @@ _scsih_sas_device_status_change_event_debug(struct MPT2SAS_ADAPTER *ioc, /** * _scsih_sas_device_status_change_event - handle device status change * @ioc: per adapter object - * @VF_ID: - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void -_scsih_sas_device_status_change_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataSasDeviceStatusChange_t *event_data) +_scsih_sas_device_status_change_event(struct MPT2SAS_ADAPTER *ioc, + struct fw_event_work *fw_event) { #ifdef CONFIG_SCSI_MPT2SAS_LOGGING if (ioc->logging_level & MPT_DEBUG_EVENT_WORK_TASK) - _scsih_sas_device_status_change_event_debug(ioc, event_data); + _scsih_sas_device_status_change_event_debug(ioc, + fw_event->event_data); #endif } @@ -4026,34 +4243,33 @@ _scsih_sas_enclosure_dev_status_change_event_debug(struct MPT2SAS_ADAPTER *ioc, /** * _scsih_sas_enclosure_dev_status_change_event - handle enclosure events * @ioc: per adapter object - * @VF_ID: - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void _scsih_sas_enclosure_dev_status_change_event(struct MPT2SAS_ADAPTER *ioc, - u8 VF_ID, Mpi2EventDataSasEnclDevStatusChange_t *event_data) + struct fw_event_work *fw_event) { #ifdef CONFIG_SCSI_MPT2SAS_LOGGING if (ioc->logging_level & MPT_DEBUG_EVENT_WORK_TASK) _scsih_sas_enclosure_dev_status_change_event_debug(ioc, - event_data); + fw_event->event_data); #endif } /** * _scsih_sas_broadcast_primative_event - handle broadcast events * @ioc: per adapter object - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void -_scsih_sas_broadcast_primative_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataSasBroadcastPrimitive_t *event_data) +_scsih_sas_broadcast_primative_event(struct MPT2SAS_ADAPTER *ioc, + struct fw_event_work *fw_event) { struct scsi_cmnd *scmd; u16 smid, handle; @@ -4062,11 +4278,12 @@ _scsih_sas_broadcast_primative_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 termination_count; u32 query_count; Mpi2SCSITaskManagementReply_t *mpi_reply; - +#ifdef CONFIG_SCSI_MPT2SAS_LOGGING + Mpi2EventDataSasBroadcastPrimitive_t *event_data = fw_event->event_data; +#endif dewtprintk(ioc, printk(MPT2SAS_DEBUG_FMT "broadcast primative: " "phy number(%d), width(%d)\n", ioc->name, event_data->PhyNum, event_data->PortWidth)); - dtmprintk(ioc, printk(MPT2SAS_DEBUG_FMT "%s: enter\n", ioc->name, __func__)); @@ -4074,7 +4291,7 @@ _scsih_sas_broadcast_primative_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, termination_count = 0; query_count = 0; mpi_reply = ioc->tm_cmds.reply; - for (smid = 1; smid <= ioc->request_depth; smid++) { + for (smid = 1; smid <= ioc->scsiio_depth; smid++) { scmd = _scsih_scsi_lookup_get(ioc, smid); if (!scmd) continue; @@ -4121,23 +4338,25 @@ _scsih_sas_broadcast_primative_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, /** * _scsih_sas_discovery_event - handle discovery events * @ioc: per adapter object - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void -_scsih_sas_discovery_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataSasDiscovery_t *event_data) +_scsih_sas_discovery_event(struct MPT2SAS_ADAPTER *ioc, + struct fw_event_work *fw_event) { + Mpi2EventDataSasDiscovery_t *event_data = fw_event->event_data; + #ifdef CONFIG_SCSI_MPT2SAS_LOGGING if (ioc->logging_level & MPT_DEBUG_EVENT_WORK_TASK) { printk(MPT2SAS_DEBUG_FMT "discovery event: (%s)", ioc->name, (event_data->ReasonCode == MPI2_EVENT_SAS_DISC_RC_STARTED) ? "start" : "stop"); if (event_data->DiscoveryStatus) - printk(MPT2SAS_DEBUG_FMT ", discovery_status(0x%08x)", - ioc->name, le32_to_cpu(event_data->DiscoveryStatus)); + printk("discovery_status(0x%08x)", + le32_to_cpu(event_data->DiscoveryStatus)); printk("\n"); } #endif @@ -4488,19 +4707,19 @@ _scsih_sas_ir_config_change_event_debug(struct MPT2SAS_ADAPTER *ioc, /** * _scsih_sas_ir_config_change_event - handle ir configuration change events * @ioc: per adapter object - * @VF_ID: - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void -_scsih_sas_ir_config_change_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataIrConfigChangeList_t *event_data) +_scsih_sas_ir_config_change_event(struct MPT2SAS_ADAPTER *ioc, + struct fw_event_work *fw_event) { Mpi2EventIrConfigElement_t *element; int i; u8 foreign_config; + Mpi2EventDataIrConfigChangeList_t *event_data = fw_event->event_data; #ifdef CONFIG_SCSI_MPT2SAS_LOGGING if (ioc->logging_level & MPT_DEBUG_EVENT_WORK_TASK) @@ -4543,14 +4762,14 @@ _scsih_sas_ir_config_change_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, /** * _scsih_sas_ir_volume_event - IR volume event * @ioc: per adapter object - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void -_scsih_sas_ir_volume_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataIrVolume_t *event_data) +_scsih_sas_ir_volume_event(struct MPT2SAS_ADAPTER *ioc, + struct fw_event_work *fw_event) { u64 wwid; unsigned long flags; @@ -4559,6 +4778,7 @@ _scsih_sas_ir_volume_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 state; int rc; struct MPT2SAS_TARGET *sas_target_priv_data; + Mpi2EventDataIrVolume_t *event_data = fw_event->event_data; if (event_data->ReasonCode != MPI2_EVENT_IR_VOLUME_RC_STATE_CHANGED) return; @@ -4628,14 +4848,14 @@ _scsih_sas_ir_volume_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, /** * _scsih_sas_ir_physical_disk_event - PD event * @ioc: per adapter object - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void -_scsih_sas_ir_physical_disk_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataIrPhysicalDisk_t *event_data) +_scsih_sas_ir_physical_disk_event(struct MPT2SAS_ADAPTER *ioc, + struct fw_event_work *fw_event) { u16 handle; u32 state; @@ -4644,6 +4864,7 @@ _scsih_sas_ir_physical_disk_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, Mpi2ConfigReply_t mpi_reply; Mpi2SasDevicePage0_t sas_device_pg0; u32 ioc_status; + Mpi2EventDataIrPhysicalDisk_t *event_data = fw_event->event_data; if (event_data->ReasonCode != MPI2_EVENT_IR_PHYSDISK_RC_STATE_CHANGED) return; @@ -4743,33 +4964,33 @@ _scsih_sas_ir_operation_status_event_debug(struct MPT2SAS_ADAPTER *ioc, /** * _scsih_sas_ir_operation_status_event - handle RAID operation events * @ioc: per adapter object - * @VF_ID: - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Return nothing. */ static void -_scsih_sas_ir_operation_status_event(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataIrOperationStatus_t *event_data) +_scsih_sas_ir_operation_status_event(struct MPT2SAS_ADAPTER *ioc, + struct fw_event_work *fw_event) { #ifdef CONFIG_SCSI_MPT2SAS_LOGGING if (ioc->logging_level & MPT_DEBUG_EVENT_WORK_TASK) - _scsih_sas_ir_operation_status_event_debug(ioc, event_data); + _scsih_sas_ir_operation_status_event_debug(ioc, + fw_event->event_data); #endif } /** * _scsih_task_set_full - handle task set full * @ioc: per adapter object - * @event_data: event data payload + * @fw_event: The fw_event_work object * Context: user. * * Throttle back qdepth. */ static void -_scsih_task_set_full(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, - Mpi2EventDataTaskSetFull_t *event_data) +_scsih_task_set_full(struct MPT2SAS_ADAPTER *ioc, struct fw_event_work + *fw_event) { unsigned long flags; struct _sas_device *sas_device; @@ -4780,6 +5001,7 @@ _scsih_task_set_full(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u16 handle; int id, channel; u64 sas_address; + Mpi2EventDataTaskSetFull_t *event_data = fw_event->event_data; current_depth = le16_to_cpu(event_data->CurrentDepth); handle = le16_to_cpu(event_data->DevHandle); @@ -4868,6 +5090,10 @@ _scsih_mark_responding_sas_device(struct MPT2SAS_ADAPTER *ioc, u64 sas_address, if (sas_device->sas_address == sas_address && sas_device->slot == slot && sas_device->starget) { sas_device->responding = 1; + sas_device->state = 0; + starget = sas_device->starget; + sas_target_priv_data = starget->hostdata; + sas_target_priv_data->tm_busy = 0; starget_printk(KERN_INFO, sas_device->starget, "handle(0x%04x), sas_addr(0x%016llx), enclosure " "logical id(0x%016llx), slot(%d)\n", handle, @@ -4880,8 +5106,6 @@ _scsih_mark_responding_sas_device(struct MPT2SAS_ADAPTER *ioc, u64 sas_address, printk(KERN_INFO "\thandle changed from(0x%04x)!!!\n", sas_device->handle); sas_device->handle = handle; - starget = sas_device->starget; - sas_target_priv_data = starget->hostdata; sas_target_priv_data->handle = handle; goto out; } @@ -5227,44 +5451,38 @@ _firmware_event_work(struct work_struct *work) switch (fw_event->event) { case MPI2_EVENT_SAS_TOPOLOGY_CHANGE_LIST: - _scsih_sas_topology_change_event(ioc, fw_event->VF_ID, - fw_event->event_data, fw_event); + _scsih_sas_topology_change_event(ioc, fw_event); break; case MPI2_EVENT_SAS_DEVICE_STATUS_CHANGE: - _scsih_sas_device_status_change_event(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_sas_device_status_change_event(ioc, + fw_event); break; case MPI2_EVENT_SAS_DISCOVERY: - _scsih_sas_discovery_event(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_sas_discovery_event(ioc, + fw_event); break; case MPI2_EVENT_SAS_BROADCAST_PRIMITIVE: - _scsih_sas_broadcast_primative_event(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_sas_broadcast_primative_event(ioc, + fw_event); break; case MPI2_EVENT_SAS_ENCL_DEVICE_STATUS_CHANGE: _scsih_sas_enclosure_dev_status_change_event(ioc, - fw_event->VF_ID, fw_event->event_data); + fw_event); break; case MPI2_EVENT_IR_CONFIGURATION_CHANGE_LIST: - _scsih_sas_ir_config_change_event(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_sas_ir_config_change_event(ioc, fw_event); break; case MPI2_EVENT_IR_VOLUME: - _scsih_sas_ir_volume_event(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_sas_ir_volume_event(ioc, fw_event); break; case MPI2_EVENT_IR_PHYSICAL_DISK: - _scsih_sas_ir_physical_disk_event(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_sas_ir_physical_disk_event(ioc, fw_event); break; case MPI2_EVENT_IR_OPERATION_STATUS: - _scsih_sas_ir_operation_status_event(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_sas_ir_operation_status_event(ioc, fw_event); break; case MPI2_EVENT_TASK_SET_FULL: - _scsih_task_set_full(ioc, fw_event->VF_ID, - fw_event->event_data); + _scsih_task_set_full(ioc, fw_event); break; } _scsih_fw_event_free(ioc, fw_event); @@ -5273,17 +5491,19 @@ _firmware_event_work(struct work_struct *work) /** * mpt2sas_scsih_event_callback - firmware event handler (called at ISR time) * @ioc: per adapter object - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * Context: interrupt. * * This function merely adds a new work task into ioc->firmware_event_thread. * The tasks are worked from _firmware_event_work in user context. * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -void -mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) +u8 +mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 msix_index, + u32 reply) { struct fw_event_work *fw_event; Mpi2EventNotificationReply_t *mpi_reply; @@ -5294,11 +5514,11 @@ mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) spin_lock_irqsave(&ioc->fw_event_lock, flags); if (ioc->fw_events_off || ioc->remove_host) { spin_unlock_irqrestore(&ioc->fw_event_lock, flags); - return; + return 1; } spin_unlock_irqrestore(&ioc->fw_event_lock, flags); - mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); + mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); event = le16_to_cpu(mpi_reply->Event); switch (event) { @@ -5312,7 +5532,7 @@ mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) if (baen_data->Primitive != MPI2_EVENT_PRIMITIVE_ASYNCHRONOUS_EVENT || ioc->broadcast_aen_busy) - return; + return 1; ioc->broadcast_aen_busy = 1; break; } @@ -5334,14 +5554,14 @@ mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) break; default: /* ignore the rest */ - return; + return 1; } fw_event = kzalloc(sizeof(struct fw_event_work), GFP_ATOMIC); if (!fw_event) { printk(MPT2SAS_ERR_FMT "failure at %s:%d/%s()!\n", ioc->name, __FILE__, __LINE__, __func__); - return; + return 1; } fw_event->event_data = kzalloc(mpi_reply->EventDataLength*4, GFP_ATOMIC); @@ -5349,15 +5569,17 @@ mpt2sas_scsih_event_callback(struct MPT2SAS_ADAPTER *ioc, u8 VF_ID, u32 reply) printk(MPT2SAS_ERR_FMT "failure at %s:%d/%s()!\n", ioc->name, __FILE__, __LINE__, __func__); kfree(fw_event); - return; + return 1; } memcpy(fw_event->event_data, mpi_reply->EventData, mpi_reply->EventDataLength*4); fw_event->ioc = ioc; - fw_event->VF_ID = VF_ID; + fw_event->VF_ID = mpi_reply->VF_ID; + fw_event->VP_ID = mpi_reply->VP_ID; fw_event->event = event; _scsih_fw_event_add(ioc, fw_event); + return 1; } /* shost template */ @@ -5617,7 +5839,7 @@ _scsih_probe_raid(struct MPT2SAS_ADAPTER *ioc) } /** - * _scsih_probe_sas - reporting raid volumes to sas transport + * _scsih_probe_sas - reporting sas devices to sas transport * @ioc: per adapter object * * Called during initial loading of the driver. @@ -5714,6 +5936,8 @@ _scsih_probe(struct pci_dev *pdev, const struct pci_device_id *id) ioc->base_cb_idx = base_cb_idx; ioc->transport_cb_idx = transport_cb_idx; ioc->config_cb_idx = config_cb_idx; + ioc->tm_tr_cb_idx = tm_tr_cb_idx; + ioc->tm_sas_control_cb_idx = tm_sas_control_cb_idx; ioc->logging_level = logging_level; /* misc semaphores and spin locks */ spin_lock_init(&ioc->ioc_reset_in_progress_lock); @@ -5729,6 +5953,7 @@ _scsih_probe(struct pci_dev *pdev, const struct pci_device_id *id) INIT_LIST_HEAD(&ioc->fw_event_list); INIT_LIST_HEAD(&ioc->raid_device_list); INIT_LIST_HEAD(&ioc->sas_hba.sas_port_list); + INIT_LIST_HEAD(&ioc->delayed_tr_list); /* init shost parameters */ shost->max_cmd_len = 16; @@ -5745,6 +5970,7 @@ _scsih_probe(struct pci_dev *pdev, const struct pci_device_id *id) scsi_host_set_prot(shost, SHOST_DIF_TYPE1_PROTECTION | SHOST_DIF_TYPE3_PROTECTION); + scsi_host_set_guard(shost, SHOST_DIX_GUARD_CRC); /* event thread */ snprintf(ioc->firmware_event_name, sizeof(ioc->firmware_event_name), @@ -5894,6 +6120,11 @@ _scsih_init(void) /* ctl module callback handler */ ctl_cb_idx = mpt2sas_base_register_callback_handler(mpt2sas_ctl_done); + tm_tr_cb_idx = mpt2sas_base_register_callback_handler( + _scsih_tm_tr_complete); + tm_sas_control_cb_idx = mpt2sas_base_register_callback_handler( + _scsih_sas_control_complete); + mpt2sas_ctl_init(); error = pci_register_driver(&scsih_driver); @@ -5924,6 +6155,9 @@ _scsih_exit(void) mpt2sas_base_release_callback_handler(config_cb_idx); mpt2sas_base_release_callback_handler(ctl_cb_idx); + mpt2sas_base_release_callback_handler(tm_tr_cb_idx); + mpt2sas_base_release_callback_handler(tm_sas_control_cb_idx); + mpt2sas_ctl_exit(); } diff --git a/drivers/scsi/mpt2sas/mpt2sas_transport.c b/drivers/scsi/mpt2sas/mpt2sas_transport.c index 742324a0a11e..eb98188c7f3f 100644 --- a/drivers/scsi/mpt2sas/mpt2sas_transport.c +++ b/drivers/scsi/mpt2sas/mpt2sas_transport.c @@ -2,7 +2,7 @@ * SAS Transport Layer for MPT (Message Passing Technology) based controllers * * This code is based on drivers/scsi/mpt2sas/mpt2_transport.c - * Copyright (C) 2007-2008 LSI Corporation + * Copyright (C) 2007-2009 LSI Corporation * (mailto:DL-MPTFusionLinux@lsi.com) * * This program is free software; you can redistribute it and/or @@ -212,25 +212,26 @@ _transport_set_identify(struct MPT2SAS_ADAPTER *ioc, u16 handle, * mpt2sas_transport_done - internal transport layer callback handler. * @ioc: per adapter object * @smid: system request message index - * @VF_ID: virtual function id + * @msix_index: MSIX table index supplied by the OS * @reply: reply message frame(lower 32bit addr) * * Callback handler when sending internal generated transport cmds. * The callback index passed is `ioc->transport_cb_idx` * - * Return nothing. + * Return 1 meaning mf should be freed from _base_interrupt + * 0 means the mf is freed from this function. */ -void -mpt2sas_transport_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, +u8 +mpt2sas_transport_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 msix_index, u32 reply) { MPI2DefaultReply_t *mpi_reply; mpi_reply = mpt2sas_base_get_reply_virt_addr(ioc, reply); if (ioc->transport_cmds.status == MPT2_CMD_NOT_USED) - return; + return 1; if (ioc->transport_cmds.smid != smid) - return; + return 1; ioc->transport_cmds.status |= MPT2_CMD_COMPLETE; if (mpi_reply) { memcpy(ioc->transport_cmds.reply, mpi_reply, @@ -239,6 +240,7 @@ mpt2sas_transport_done(struct MPT2SAS_ADAPTER *ioc, u16 smid, u8 VF_ID, } ioc->transport_cmds.status &= ~MPT2_CMD_PENDING; complete(&ioc->transport_cmds.done); + return 1; } /* report manufacture request structure */ @@ -369,6 +371,8 @@ _transport_expander_report_manufacture(struct MPT2SAS_ADAPTER *ioc, memset(mpi_request, 0, sizeof(Mpi2SmpPassthroughRequest_t)); mpi_request->Function = MPI2_FUNCTION_SMP_PASSTHROUGH; mpi_request->PhysicalPort = 0xFF; + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; sas_address_le = (u64 *)&mpi_request->SASAddress; *sas_address_le = cpu_to_le64(sas_address); mpi_request->RequestDataLength = sizeof(struct rep_manu_request); @@ -396,7 +400,8 @@ _transport_expander_report_manufacture(struct MPT2SAS_ADAPTER *ioc, dtransportprintk(ioc, printk(MPT2SAS_DEBUG_FMT "report_manufacture - " "send to sas_addr(0x%016llx)\n", ioc->name, (unsigned long long)sas_address)); - mpt2sas_base_put_smid_default(ioc, smid, 0 /* VF_ID */); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->transport_cmds.done); timeleft = wait_for_completion_timeout(&ioc->transport_cmds.done, 10*HZ); @@ -1106,6 +1111,8 @@ _transport_smp_handler(struct Scsi_Host *shost, struct sas_rphy *rphy, memset(mpi_request, 0, sizeof(Mpi2SmpPassthroughRequest_t)); mpi_request->Function = MPI2_FUNCTION_SMP_PASSTHROUGH; mpi_request->PhysicalPort = 0xFF; + mpi_request->VF_ID = 0; /* TODO */ + mpi_request->VP_ID = 0; *((u64 *)&mpi_request->SASAddress) = (rphy) ? cpu_to_le64(rphy->identify.sas_address) : cpu_to_le64(ioc->sas_hba.sas_address); @@ -1147,7 +1154,8 @@ _transport_smp_handler(struct Scsi_Host *shost, struct sas_rphy *rphy, dtransportprintk(ioc, printk(MPT2SAS_DEBUG_FMT "%s - " "sending smp request\n", ioc->name, __func__)); - mpt2sas_base_put_smid_default(ioc, smid, 0 /* VF_ID */); + mpt2sas_base_put_smid_default(ioc, smid); + init_completion(&ioc->transport_cmds.done); timeleft = wait_for_completion_timeout(&ioc->transport_cmds.done, 10*HZ); diff --git a/drivers/scsi/mvsas/mv_defs.h b/drivers/scsi/mvsas/mv_defs.h index f8cb9defb961..1849da1f030d 100644 --- a/drivers/scsi/mvsas/mv_defs.h +++ b/drivers/scsi/mvsas/mv_defs.h @@ -25,6 +25,8 @@ #ifndef _MV_DEFS_H_ #define _MV_DEFS_H_ +#define PCI_DEVICE_ID_ARECA_1300 0x1300 +#define PCI_DEVICE_ID_ARECA_1320 0x1320 enum chip_flavors { chip_6320, @@ -32,6 +34,8 @@ enum chip_flavors { chip_6485, chip_9480, chip_9180, + chip_1300, + chip_1320 }; /* driver compile-time configuration */ diff --git a/drivers/scsi/mvsas/mv_init.c b/drivers/scsi/mvsas/mv_init.c index 8646a19f999d..c790d45876c4 100644 --- a/drivers/scsi/mvsas/mv_init.c +++ b/drivers/scsi/mvsas/mv_init.c @@ -32,6 +32,8 @@ static const struct mvs_chip_info mvs_chips[] = { [chip_6485] = { 1, 8, 0x800, 33, 32, 10, &mvs_64xx_dispatch, }, [chip_9180] = { 2, 4, 0x800, 17, 64, 9, &mvs_94xx_dispatch, }, [chip_9480] = { 2, 4, 0x800, 17, 64, 9, &mvs_94xx_dispatch, }, + [chip_1300] = { 1, 4, 0x400, 17, 16, 9, &mvs_64xx_dispatch, }, + [chip_1320] = { 2, 4, 0x800, 17, 64, 9, &mvs_94xx_dispatch, }, }; #define SOC_SAS_NUM 2 @@ -653,6 +655,8 @@ static struct pci_device_id __devinitdata mvs_pci_table[] = { { PCI_VDEVICE(MARVELL, 0x6485), chip_6485 }, { PCI_VDEVICE(MARVELL, 0x9480), chip_9480 }, { PCI_VDEVICE(MARVELL, 0x9180), chip_9180 }, + { PCI_VDEVICE(ARECA, PCI_DEVICE_ID_ARECA_1300), chip_1300 }, + { PCI_VDEVICE(ARECA, PCI_DEVICE_ID_ARECA_1320), chip_1320 }, { } /* terminate list */ }; diff --git a/drivers/scsi/pmcraid.c b/drivers/scsi/pmcraid.c index 4302f06e4ec9..0a97bc9074bb 100644 --- a/drivers/scsi/pmcraid.c +++ b/drivers/scsi/pmcraid.c @@ -46,6 +46,7 @@ #include <linux/mutex.h> #include <scsi/scsi.h> #include <scsi/scsi_host.h> +#include <scsi/scsi_device.h> #include <scsi/scsi_tcq.h> #include <scsi/scsi_eh.h> #include <scsi/scsi_cmnd.h> @@ -684,7 +685,7 @@ static void pmcraid_timeout_handler(struct pmcraid_cmd *cmd) struct pmcraid_instance *pinstance = cmd->drv_inst; unsigned long lock_flags; - dev_err(&pinstance->pdev->dev, + dev_info(&pinstance->pdev->dev, "Adapter being reset due to command timeout.\n"); /* Command timeouts result in hard reset sequence. The command that got @@ -815,8 +816,9 @@ static void pmcraid_erp_done(struct pmcraid_cmd *cmd) if (PMCRAID_IOASC_SENSE_KEY(ioasc) > 0) { scsi_cmd->result |= (DID_ERROR << 16); - pmcraid_err("command CDB[0] = %x failed with IOASC: 0x%08X\n", - cmd->ioa_cb->ioarcb.cdb[0], ioasc); + scmd_printk(KERN_INFO, scsi_cmd, + "command CDB[0] = %x failed with IOASC: 0x%08X\n", + cmd->ioa_cb->ioarcb.cdb[0], ioasc); } /* if we had allocated sense buffers for request sense, copy the sense @@ -1069,7 +1071,7 @@ static struct pmcraid_cmd *pmcraid_init_hcam ioarcb->data_transfer_length = cpu_to_le32(rcb_size); - ioadl[0].flags |= cpu_to_le32(IOADL_FLAGS_READ_LAST); + ioadl[0].flags |= IOADL_FLAGS_READ_LAST; ioadl[0].data_len = cpu_to_le32(rcb_size); ioadl[0].address = cpu_to_le32(dma); @@ -1541,13 +1543,13 @@ static void pmcraid_handle_error_log(struct pmcraid_instance *pinstance) if (pinstance->ldn.hcam->notification_lost == HOSTRCB_NOTIFICATIONS_LOST) - dev_err(&pinstance->pdev->dev, "Error notifications lost\n"); + dev_info(&pinstance->pdev->dev, "Error notifications lost\n"); ioasc = le32_to_cpu(hcam_ldn->error_log.fd_ioasc); if (ioasc == PMCRAID_IOASC_UA_BUS_WAS_RESET || ioasc == PMCRAID_IOASC_UA_BUS_WAS_RESET_BY_OTHER) { - dev_err(&pinstance->pdev->dev, + dev_info(&pinstance->pdev->dev, "UnitAttention due to IOA Bus Reset\n"); scsi_report_bus_reset( pinstance->host, @@ -1584,7 +1586,7 @@ static void pmcraid_process_ccn(struct pmcraid_cmd *cmd) atomic_read(&pinstance->ccn.ignore) == 1) { return; } else if (ioasc) { - dev_err(&pinstance->pdev->dev, + dev_info(&pinstance->pdev->dev, "Host RCB (CCN) failed with IOASC: 0x%08X\n", ioasc); spin_lock_irqsave(pinstance->host->host_lock, lock_flags); pmcraid_send_hcam(pinstance, PMCRAID_HCAM_CODE_CONFIG_CHANGE); @@ -1634,7 +1636,7 @@ static void pmcraid_process_ldn(struct pmcraid_cmd *cmd) return; } } else { - dev_err(&pinstance->pdev->dev, + dev_info(&pinstance->pdev->dev, "Host RCB(LDN) failed with IOASC: 0x%08X\n", ioasc); } /* send netlink message for HCAM notification if enabled */ @@ -1822,7 +1824,6 @@ static void pmcraid_fail_outstanding_cmds(struct pmcraid_instance *pinstance) scsi_dma_unmap(scsi_cmd); pmcraid_return_cmd(cmd); - pmcraid_info("failing(%d) CDB[0] = %x result: %x\n", le32_to_cpu(resp) >> 2, cmd->ioa_cb->ioarcb.cdb[0], @@ -2250,7 +2251,7 @@ static void pmcraid_request_sense(struct pmcraid_cmd *cmd) ioadl->address = cpu_to_le64(cmd->sense_buffer_dma); ioadl->data_len = cpu_to_le32(SCSI_SENSE_BUFFERSIZE); - ioadl->flags = cpu_to_le32(IOADL_FLAGS_LAST_DESC); + ioadl->flags = IOADL_FLAGS_LAST_DESC; /* request sense might be called as part of error response processing * which runs in tasklets context. It is possible that mid-layer might @@ -2514,7 +2515,8 @@ static int pmcraid_reset_device( res = scsi_cmd->device->hostdata; if (!res) { - pmcraid_err("reset_device: NULL resource pointer\n"); + sdev_printk(KERN_ERR, scsi_cmd->device, + "reset_device: NULL resource pointer\n"); return FAILED; } @@ -2752,8 +2754,8 @@ static int pmcraid_eh_abort_handler(struct scsi_cmnd *scsi_cmd) pinstance = (struct pmcraid_instance *)scsi_cmd->device->host->hostdata; - dev_err(&pinstance->pdev->dev, - "I/O command timed out, aborting it.\n"); + scmd_printk(KERN_INFO, scsi_cmd, + "I/O command timed out, aborting it.\n"); res = scsi_cmd->device->hostdata; @@ -2824,7 +2826,8 @@ static int pmcraid_eh_abort_handler(struct scsi_cmnd *scsi_cmd) */ static int pmcraid_eh_device_reset_handler(struct scsi_cmnd *scmd) { - pmcraid_err("Doing device reset due to an I/O command timeout.\n"); + scmd_printk(KERN_INFO, scmd, + "resetting device due to an I/O command timeout.\n"); return pmcraid_reset_device(scmd, PMCRAID_INTERNAL_TIMEOUT, RESET_DEVICE_LUN); @@ -2832,7 +2835,8 @@ static int pmcraid_eh_device_reset_handler(struct scsi_cmnd *scmd) static int pmcraid_eh_bus_reset_handler(struct scsi_cmnd *scmd) { - pmcraid_err("Doing bus reset due to an I/O command timeout.\n"); + scmd_printk(KERN_INFO, scmd, + "Doing bus reset due to an I/O command timeout.\n"); return pmcraid_reset_device(scmd, PMCRAID_RESET_BUS_TIMEOUT, RESET_DEVICE_BUS); @@ -2840,7 +2844,8 @@ static int pmcraid_eh_bus_reset_handler(struct scsi_cmnd *scmd) static int pmcraid_eh_target_reset_handler(struct scsi_cmnd *scmd) { - pmcraid_err("Doing target reset due to an I/O command timeout.\n"); + scmd_printk(KERN_INFO, scmd, + "Doing target reset due to an I/O command timeout.\n"); return pmcraid_reset_device(scmd, PMCRAID_INTERNAL_TIMEOUT, RESET_DEVICE_TARGET); @@ -2988,11 +2993,11 @@ static int pmcraid_build_ioadl( nseg = scsi_dma_map(scsi_cmd); if (nseg < 0) { - dev_err(&pinstance->pdev->dev, "scsi_map_dma failed!\n"); + scmd_printk(KERN_ERR, scsi_cmd, "scsi_map_dma failed!\n"); return -1; } else if (nseg > PMCRAID_MAX_IOADLS) { scsi_dma_unmap(scsi_cmd); - dev_err(&pinstance->pdev->dev, + scmd_printk(KERN_ERR, scsi_cmd, "sg count is (%d) more than allowed!\n", nseg); return -1; } @@ -3012,7 +3017,7 @@ static int pmcraid_build_ioadl( ioadl[i].flags = 0; } /* setup last descriptor */ - ioadl[i - 1].flags = cpu_to_le32(IOADL_FLAGS_LAST_DESC); + ioadl[i - 1].flags = IOADL_FLAGS_LAST_DESC; return 0; } @@ -3382,7 +3387,7 @@ static int pmcraid_build_passthrough_ioadls( } /* setup the last descriptor */ - ioadl[i - 1].flags = cpu_to_le32(IOADL_FLAGS_LAST_DESC); + ioadl[i - 1].flags = IOADL_FLAGS_LAST_DESC; return 0; } @@ -5040,7 +5045,7 @@ static int pmcraid_resume(struct pci_dev *pdev) rc = pci_enable_device(pdev); if (rc) { - pmcraid_err("pmcraid: Enable device failed\n"); + dev_err(&pdev->dev, "resume: Enable device failed\n"); return rc; } @@ -5054,7 +5059,7 @@ static int pmcraid_resume(struct pci_dev *pdev) rc = pci_set_consistent_dma_mask(pdev, DMA_BIT_MASK(32)); if (rc != 0) { - dev_err(&pdev->dev, "Failed to set PCI DMA mask\n"); + dev_err(&pdev->dev, "resume: Failed to set PCI DMA mask\n"); goto disable_device; } @@ -5063,7 +5068,8 @@ static int pmcraid_resume(struct pci_dev *pdev) rc = pmcraid_register_interrupt_handler(pinstance); if (rc) { - pmcraid_err("resume: couldn't register interrupt handlers\n"); + dev_err(&pdev->dev, + "resume: couldn't register interrupt handlers\n"); rc = -ENODEV; goto release_host; } @@ -5080,7 +5086,7 @@ static int pmcraid_resume(struct pci_dev *pdev) * state. */ if (pmcraid_reset_bringup(pinstance)) { - pmcraid_err("couldn't initialize IOA \n"); + dev_err(&pdev->dev, "couldn't initialize IOA \n"); rc = -ENODEV; goto release_tasklets; } @@ -5187,7 +5193,7 @@ static void pmcraid_init_res_table(struct pmcraid_cmd *cmd) LIST_HEAD(old_res); if (pinstance->cfg_table->flags & MICROCODE_UPDATE_REQUIRED) - dev_err(&pinstance->pdev->dev, "Require microcode download\n"); + pmcraid_err("IOA requires microcode download\n"); /* resource list is protected by pinstance->resource_lock. * init_res_table can be called from probe (user-thread) or runtime @@ -5224,8 +5230,7 @@ static void pmcraid_init_res_table(struct pmcraid_cmd *cmd) if (!found) { if (list_empty(&pinstance->free_res_q)) { - dev_err(&pinstance->pdev->dev, - "Too many devices attached\n"); + pmcraid_err("Too many devices attached\n"); break; } @@ -5309,7 +5314,7 @@ static void pmcraid_querycfg(struct pmcraid_cmd *cmd) cpu_to_le32(sizeof(struct pmcraid_config_table)); ioadl = &(ioarcb->add_data.u.ioadl[0]); - ioadl->flags = cpu_to_le32(IOADL_FLAGS_LAST_DESC); + ioadl->flags = IOADL_FLAGS_LAST_DESC; ioadl->address = cpu_to_le64(pinstance->cfg_table_bus_addr); ioadl->data_len = cpu_to_le32(sizeof(struct pmcraid_config_table)); @@ -5442,7 +5447,7 @@ static int __devinit pmcraid_probe( rc = pmcraid_register_interrupt_handler(pinstance); if (rc) { - pmcraid_err("couldn't register interrupt handler\n"); + dev_err(&pdev->dev, "couldn't register interrupt handler\n"); goto out_scsi_host_put; } @@ -5466,7 +5471,7 @@ static int __devinit pmcraid_probe( */ pmcraid_info("starting IOA initialization sequence\n"); if (pmcraid_reset_bringup(pinstance)) { - pmcraid_err("couldn't initialize IOA \n"); + dev_err(&pdev->dev, "couldn't initialize IOA \n"); rc = 1; goto out_release_bufs; } @@ -5534,7 +5539,6 @@ static struct pci_driver pmcraid_driver = { .shutdown = pmcraid_shutdown }; - /** * pmcraid_init - module load entry point */ @@ -5566,7 +5570,6 @@ static int __init pmcraid_init(void) goto out_unreg_chrdev; } - error = pmcraid_netlink_init(); if (error) @@ -5584,6 +5587,7 @@ static int __init pmcraid_init(void) out_unreg_chrdev: unregister_chrdev_region(MKDEV(pmcraid_major, 0), PMCRAID_MAX_ADAPTERS); + out_init: return error; } diff --git a/drivers/scsi/qla2xxx/qla_mid.c b/drivers/scsi/qla2xxx/qla_mid.c index 42b799abba57..e07b3617f019 100644 --- a/drivers/scsi/qla2xxx/qla_mid.c +++ b/drivers/scsi/qla2xxx/qla_mid.c @@ -568,7 +568,7 @@ qla25xx_create_req_que(struct qla_hw_data *ha, uint16_t options, if (req == NULL) { qla_printk(KERN_WARNING, ha, "could not allocate memory" "for request que\n"); - goto que_failed; + goto failed; } req->length = REQUEST_ENTRY_CNT_24XX; @@ -632,6 +632,7 @@ qla25xx_create_req_que(struct qla_hw_data *ha, uint16_t options, que_failed: qla25xx_free_req_que(base_vha, req); +failed: return 0; } @@ -659,7 +660,7 @@ qla25xx_create_rsp_que(struct qla_hw_data *ha, uint16_t options, if (rsp == NULL) { qla_printk(KERN_WARNING, ha, "could not allocate memory for" " response que\n"); - goto que_failed; + goto failed; } rsp->length = RESPONSE_ENTRY_CNT_MQ; @@ -728,6 +729,7 @@ qla25xx_create_rsp_que(struct qla_hw_data *ha, uint16_t options, que_failed: qla25xx_free_rsp_que(base_vha, rsp); +failed: return 0; } diff --git a/drivers/scsi/scsi.c b/drivers/scsi/scsi.c index b6e03074cb8f..dd098cad337b 100644 --- a/drivers/scsi/scsi.c +++ b/drivers/scsi/scsi.c @@ -241,10 +241,7 @@ scsi_host_alloc_command(struct Scsi_Host *shost, gfp_t gfp_mask) */ struct scsi_cmnd *__scsi_get_command(struct Scsi_Host *shost, gfp_t gfp_mask) { - struct scsi_cmnd *cmd; - unsigned char *buf; - - cmd = scsi_host_alloc_command(shost, gfp_mask); + struct scsi_cmnd *cmd = scsi_host_alloc_command(shost, gfp_mask); if (unlikely(!cmd)) { unsigned long flags; @@ -258,9 +255,15 @@ struct scsi_cmnd *__scsi_get_command(struct Scsi_Host *shost, gfp_t gfp_mask) spin_unlock_irqrestore(&shost->free_list_lock, flags); if (cmd) { + void *buf, *prot; + buf = cmd->sense_buffer; + prot = cmd->prot_sdb; + memset(cmd, 0, sizeof(*cmd)); + cmd->sense_buffer = buf; + cmd->prot_sdb = prot; } } diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c index fb9af207d61d..c4103bef41b5 100644 --- a/drivers/scsi/scsi_debug.c +++ b/drivers/scsi/scsi_debug.c @@ -50,6 +50,7 @@ #include <scsi/scsi_host.h> #include <scsi/scsicam.h> #include <scsi/scsi_eh.h> +#include <scsi/scsi_dbg.h> #include "sd.h" #include "scsi_logging.h" @@ -64,6 +65,7 @@ static const char * scsi_debug_version_date = "20070104"; #define PARAMETER_LIST_LENGTH_ERR 0x1a #define INVALID_OPCODE 0x20 #define ADDR_OUT_OF_RANGE 0x21 +#define INVALID_COMMAND_OPCODE 0x20 #define INVALID_FIELD_IN_CDB 0x24 #define INVALID_FIELD_IN_PARAM_LIST 0x26 #define POWERON_RESET 0x29 @@ -180,7 +182,7 @@ static int sdebug_sectors_per; /* sectors per cylinder */ #define SDEBUG_SENSE_LEN 32 #define SCSI_DEBUG_CANQUEUE 255 -#define SCSI_DEBUG_MAX_CMD_LEN 16 +#define SCSI_DEBUG_MAX_CMD_LEN 32 struct sdebug_dev_info { struct list_head dev_list; @@ -296,9 +298,25 @@ static void mk_sense_buffer(struct sdebug_dev_info *devip, int key, } static void get_data_transfer_info(unsigned char *cmd, - unsigned long long *lba, unsigned int *num) + unsigned long long *lba, unsigned int *num, + u32 *ei_lba) { + *ei_lba = 0; + switch (*cmd) { + case VARIABLE_LENGTH_CMD: + *lba = (u64)cmd[19] | (u64)cmd[18] << 8 | + (u64)cmd[17] << 16 | (u64)cmd[16] << 24 | + (u64)cmd[15] << 32 | (u64)cmd[14] << 40 | + (u64)cmd[13] << 48 | (u64)cmd[12] << 56; + + *ei_lba = (u32)cmd[23] | (u32)cmd[22] << 8 | + (u32)cmd[21] << 16 | (u32)cmd[20] << 24; + + *num = (u32)cmd[31] | (u32)cmd[30] << 8 | (u32)cmd[29] << 16 | + (u32)cmd[28] << 24; + break; + case WRITE_16: case READ_16: *lba = (u64)cmd[9] | (u64)cmd[8] << 8 | @@ -1589,7 +1607,7 @@ static int do_device_access(struct scsi_cmnd *scmd, } static int prot_verify_read(struct scsi_cmnd *SCpnt, sector_t start_sec, - unsigned int sectors) + unsigned int sectors, u32 ei_lba) { unsigned int i, resid; struct scatterlist *psgl; @@ -1636,13 +1654,23 @@ static int prot_verify_read(struct scsi_cmnd *SCpnt, sector_t start_sec, return 0x01; } - if (scsi_debug_dif != SD_DIF_TYPE3_PROTECTION && + if (scsi_debug_dif == SD_DIF_TYPE1_PROTECTION && be32_to_cpu(sdt[i].ref_tag) != (sector & 0xffffffff)) { printk(KERN_ERR "%s: REF check failed on sector %lu\n", __func__, (unsigned long)sector); dif_errors++; return 0x03; } + + if (scsi_debug_dif == SD_DIF_TYPE2_PROTECTION && + be32_to_cpu(sdt[i].ref_tag) != ei_lba) { + printk(KERN_ERR "%s: REF check failed on sector %lu\n", + __func__, (unsigned long)sector); + dif_errors++; + return 0x03; + } + + ei_lba++; } resid = sectors * 8; /* Bytes of protection data to copy into sgl */ @@ -1670,7 +1698,8 @@ static int prot_verify_read(struct scsi_cmnd *SCpnt, sector_t start_sec, } static int resp_read(struct scsi_cmnd *SCpnt, unsigned long long lba, - unsigned int num, struct sdebug_dev_info *devip) + unsigned int num, struct sdebug_dev_info *devip, + u32 ei_lba) { unsigned long iflags; int ret; @@ -1699,7 +1728,7 @@ static int resp_read(struct scsi_cmnd *SCpnt, unsigned long long lba, /* DIX + T10 DIF */ if (scsi_debug_dix && scsi_prot_sg_count(SCpnt)) { - int prot_ret = prot_verify_read(SCpnt, lba, num); + int prot_ret = prot_verify_read(SCpnt, lba, num, ei_lba); if (prot_ret) { mk_sense_buffer(devip, ABORTED_COMMAND, 0x10, prot_ret); @@ -1735,7 +1764,7 @@ void dump_sector(unsigned char *buf, int len) } static int prot_verify_write(struct scsi_cmnd *SCpnt, sector_t start_sec, - unsigned int sectors) + unsigned int sectors, u32 ei_lba) { int i, j, ret; struct sd_dif_tuple *sdt; @@ -1749,11 +1778,6 @@ static int prot_verify_write(struct scsi_cmnd *SCpnt, sector_t start_sec, sector = do_div(tmp_sec, sdebug_store_sectors); - if (((SCpnt->cmnd[1] >> 5) & 7) != 1) { - printk(KERN_WARNING "scsi_debug: WRPROTECT != 1\n"); - return 0; - } - BUG_ON(scsi_sg_count(SCpnt) == 0); BUG_ON(scsi_prot_sg_count(SCpnt) == 0); @@ -1808,7 +1832,7 @@ static int prot_verify_write(struct scsi_cmnd *SCpnt, sector_t start_sec, goto out; } - if (scsi_debug_dif != SD_DIF_TYPE3_PROTECTION && + if (scsi_debug_dif == SD_DIF_TYPE1_PROTECTION && be32_to_cpu(sdt->ref_tag) != (start_sec & 0xffffffff)) { printk(KERN_ERR @@ -1819,6 +1843,16 @@ static int prot_verify_write(struct scsi_cmnd *SCpnt, sector_t start_sec, goto out; } + if (scsi_debug_dif == SD_DIF_TYPE2_PROTECTION && + be32_to_cpu(sdt->ref_tag) != ei_lba) { + printk(KERN_ERR + "%s: REF check failed on sector %lu\n", + __func__, (unsigned long)sector); + ret = 0x03; + dump_sector(daddr, scsi_debug_sector_size); + goto out; + } + /* Would be great to copy this in bigger * chunks. However, for the sake of * correctness we need to verify each sector @@ -1832,6 +1866,7 @@ static int prot_verify_write(struct scsi_cmnd *SCpnt, sector_t start_sec, sector = 0; /* Force wrap */ start_sec++; + ei_lba++; daddr += scsi_debug_sector_size; ppage_offset += sizeof(struct sd_dif_tuple); } @@ -1853,7 +1888,8 @@ out: } static int resp_write(struct scsi_cmnd *SCpnt, unsigned long long lba, - unsigned int num, struct sdebug_dev_info *devip) + unsigned int num, struct sdebug_dev_info *devip, + u32 ei_lba) { unsigned long iflags; int ret; @@ -1864,7 +1900,7 @@ static int resp_write(struct scsi_cmnd *SCpnt, unsigned long long lba, /* DIX + T10 DIF */ if (scsi_debug_dix && scsi_prot_sg_count(SCpnt)) { - int prot_ret = prot_verify_write(SCpnt, lba, num); + int prot_ret = prot_verify_write(SCpnt, lba, num, ei_lba); if (prot_ret) { mk_sense_buffer(devip, ILLEGAL_REQUEST, 0x10, prot_ret); @@ -2872,11 +2908,12 @@ static int __init scsi_debug_init(void) case SD_DIF_TYPE0_PROTECTION: case SD_DIF_TYPE1_PROTECTION: + case SD_DIF_TYPE2_PROTECTION: case SD_DIF_TYPE3_PROTECTION: break; default: - printk(KERN_ERR "scsi_debug_init: dif must be 0, 1 or 3\n"); + printk(KERN_ERR "scsi_debug_init: dif must be 0, 1, 2 or 3\n"); return -EINVAL; } @@ -3121,6 +3158,7 @@ int scsi_debug_queuecommand(struct scsi_cmnd *SCpnt, done_funct_t done) int len, k; unsigned int num; unsigned long long lba; + u32 ei_lba; int errsts = 0; int target = SCpnt->device->id; struct sdebug_dev_info *devip = NULL; @@ -3254,14 +3292,30 @@ int scsi_debug_queuecommand(struct scsi_cmnd *SCpnt, done_funct_t done) case READ_16: case READ_12: case READ_10: + /* READ{10,12,16} and DIF Type 2 are natural enemies */ + if (scsi_debug_dif == SD_DIF_TYPE2_PROTECTION && + cmd[1] & 0xe0) { + mk_sense_buffer(devip, ILLEGAL_REQUEST, + INVALID_COMMAND_OPCODE, 0); + errsts = check_condition_result; + break; + } + + if ((scsi_debug_dif == SD_DIF_TYPE1_PROTECTION || + scsi_debug_dif == SD_DIF_TYPE3_PROTECTION) && + (cmd[1] & 0xe0) == 0) + printk(KERN_ERR "Unprotected RD/WR to DIF device\n"); + + /* fall through */ case READ_6: +read: errsts = check_readiness(SCpnt, 0, devip); if (errsts) break; if (scsi_debug_fake_rw) break; - get_data_transfer_info(cmd, &lba, &num); - errsts = resp_read(SCpnt, lba, num, devip); + get_data_transfer_info(cmd, &lba, &num, &ei_lba); + errsts = resp_read(SCpnt, lba, num, devip, ei_lba); if (inj_recovered && (0 == errsts)) { mk_sense_buffer(devip, RECOVERED_ERROR, THRESHOLD_EXCEEDED, 0); @@ -3288,14 +3342,30 @@ int scsi_debug_queuecommand(struct scsi_cmnd *SCpnt, done_funct_t done) case WRITE_16: case WRITE_12: case WRITE_10: + /* WRITE{10,12,16} and DIF Type 2 are natural enemies */ + if (scsi_debug_dif == SD_DIF_TYPE2_PROTECTION && + cmd[1] & 0xe0) { + mk_sense_buffer(devip, ILLEGAL_REQUEST, + INVALID_COMMAND_OPCODE, 0); + errsts = check_condition_result; + break; + } + + if ((scsi_debug_dif == SD_DIF_TYPE1_PROTECTION || + scsi_debug_dif == SD_DIF_TYPE3_PROTECTION) && + (cmd[1] & 0xe0) == 0) + printk(KERN_ERR "Unprotected RD/WR to DIF device\n"); + + /* fall through */ case WRITE_6: +write: errsts = check_readiness(SCpnt, 0, devip); if (errsts) break; if (scsi_debug_fake_rw) break; - get_data_transfer_info(cmd, &lba, &num); - errsts = resp_write(SCpnt, lba, num, devip); + get_data_transfer_info(cmd, &lba, &num, &ei_lba); + errsts = resp_write(SCpnt, lba, num, devip, ei_lba); if (inj_recovered && (0 == errsts)) { mk_sense_buffer(devip, RECOVERED_ERROR, THRESHOLD_EXCEEDED, 0); @@ -3341,15 +3411,38 @@ int scsi_debug_queuecommand(struct scsi_cmnd *SCpnt, done_funct_t done) break; if (scsi_debug_fake_rw) break; - get_data_transfer_info(cmd, &lba, &num); - errsts = resp_read(SCpnt, lba, num, devip); + get_data_transfer_info(cmd, &lba, &num, &ei_lba); + errsts = resp_read(SCpnt, lba, num, devip, ei_lba); if (errsts) break; - errsts = resp_write(SCpnt, lba, num, devip); + errsts = resp_write(SCpnt, lba, num, devip, ei_lba); if (errsts) break; errsts = resp_xdwriteread(SCpnt, lba, num, devip); break; + case VARIABLE_LENGTH_CMD: + if (scsi_debug_dif == SD_DIF_TYPE2_PROTECTION) { + + if ((cmd[10] & 0xe0) == 0) + printk(KERN_ERR + "Unprotected RD/WR to DIF device\n"); + + if (cmd[9] == READ_32) { + BUG_ON(SCpnt->cmd_len < 32); + goto read; + } + + if (cmd[9] == WRITE_32) { + BUG_ON(SCpnt->cmd_len < 32); + goto write; + } + } + + mk_sense_buffer(devip, ILLEGAL_REQUEST, + INVALID_FIELD_IN_CDB, 0); + errsts = check_condition_result; + break; + default: if (SCSI_DEBUG_OPT_NOISE & scsi_debug_opts) printk(KERN_INFO "scsi_debug: Opcode: 0x%x not " diff --git a/drivers/scsi/scsi_error.c b/drivers/scsi/scsi_error.c index 877204daf549..1b0060b791e8 100644 --- a/drivers/scsi/scsi_error.c +++ b/drivers/scsi/scsi_error.c @@ -725,6 +725,9 @@ static int scsi_send_eh_cmnd(struct scsi_cmnd *scmd, unsigned char *cmnd, case NEEDS_RETRY: case FAILED: break; + case ADD_TO_MLQUEUE: + rtn = NEEDS_RETRY; + break; default: rtn = FAILED; break; diff --git a/drivers/scsi/scsi_scan.c b/drivers/scsi/scsi_scan.c index c44783801402..0547a7f44d42 100644 --- a/drivers/scsi/scsi_scan.c +++ b/drivers/scsi/scsi_scan.c @@ -317,6 +317,7 @@ static struct scsi_device *scsi_alloc_sdev(struct scsi_target *starget, out_device_destroy: scsi_device_set_state(sdev, SDEV_DEL); transport_destroy_device(&sdev->sdev_gendev); + put_device(&sdev->sdev_dev); put_device(&sdev->sdev_gendev); out: if (display_failure_msg) @@ -957,6 +958,7 @@ static inline void scsi_destroy_sdev(struct scsi_device *sdev) if (sdev->host->hostt->slave_destroy) sdev->host->hostt->slave_destroy(sdev); transport_destroy_device(&sdev->sdev_gendev); + put_device(&sdev->sdev_dev); put_device(&sdev->sdev_gendev); } diff --git a/drivers/scsi/scsi_sysfs.c b/drivers/scsi/scsi_sysfs.c index fde54537d715..5c7eb63a19d1 100644 --- a/drivers/scsi/scsi_sysfs.c +++ b/drivers/scsi/scsi_sysfs.c @@ -864,10 +864,6 @@ int scsi_sysfs_add_sdev(struct scsi_device *sdev) goto clean_device; } - /* take a reference for the sdev_dev; this is - * released by the sdev_class .release */ - get_device(&sdev->sdev_gendev); - /* create queue files, which may be writable, depending on the host */ if (sdev->host->hostt->change_queue_depth) error = device_create_file(&sdev->sdev_gendev, &sdev_attr_queue_depth_rw); @@ -917,6 +913,7 @@ int scsi_sysfs_add_sdev(struct scsi_device *sdev) device_del(&sdev->sdev_gendev); transport_destroy_device(&sdev->sdev_gendev); + put_device(&sdev->sdev_dev); put_device(&sdev->sdev_gendev); return error; @@ -1065,7 +1062,7 @@ void scsi_sysfs_device_initialize(struct scsi_device *sdev) sdev->host->host_no, sdev->channel, sdev->id, sdev->lun); device_initialize(&sdev->sdev_dev); - sdev->sdev_dev.parent = &sdev->sdev_gendev; + sdev->sdev_dev.parent = get_device(&sdev->sdev_gendev); sdev->sdev_dev.class = &sdev_class; dev_set_name(&sdev->sdev_dev, "%d:%d:%d:%d", sdev->host->host_no, sdev->channel, sdev->id, sdev->lun); diff --git a/drivers/scsi/scsi_transport_fc.c b/drivers/scsi/scsi_transport_fc.c index b98885de6876..c6f70dae9b2e 100644 --- a/drivers/scsi/scsi_transport_fc.c +++ b/drivers/scsi/scsi_transport_fc.c @@ -3586,6 +3586,7 @@ enum fc_dispatch_result { /** * fc_bsg_host_dispatch - process fc host bsg requests and dispatch to LLDD + * @q: fc host request queue * @shost: scsi host rport attached to * @job: bsg job to be processed */ @@ -3655,6 +3656,7 @@ fc_bsg_host_dispatch(struct request_queue *q, struct Scsi_Host *shost, fail_host_msg: /* return the errno failure code as the only status */ BUG_ON(job->reply_len < sizeof(uint32_t)); + job->reply->reply_payload_rcv_len = 0; job->reply->result = ret; job->reply_len = sizeof(uint32_t); fc_bsg_jobdone(job); @@ -3693,6 +3695,7 @@ fc_bsg_goose_queue(struct fc_rport *rport) /** * fc_bsg_rport_dispatch - process rport bsg requests and dispatch to LLDD + * @q: rport request queue * @shost: scsi host rport attached to * @rport: rport request destined to * @job: bsg job to be processed @@ -3739,6 +3742,7 @@ check_bidi: fail_rport_msg: /* return the errno failure code as the only status */ BUG_ON(job->reply_len < sizeof(uint32_t)); + job->reply->reply_payload_rcv_len = 0; job->reply->result = ret; job->reply_len = sizeof(uint32_t); fc_bsg_jobdone(job); @@ -3795,6 +3799,7 @@ fc_bsg_request_handler(struct request_queue *q, struct Scsi_Host *shost, /* check if we have the msgcode value at least */ if (job->request_len < sizeof(uint32_t)) { BUG_ON(job->reply_len < sizeof(uint32_t)); + job->reply->reply_payload_rcv_len = 0; job->reply->result = -ENOMSG; job->reply_len = sizeof(uint32_t); fc_bsg_jobdone(job); diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c index 8dd96dcd716c..9093c7261f33 100644 --- a/drivers/scsi/sd.c +++ b/drivers/scsi/sd.c @@ -116,6 +116,9 @@ static DEFINE_IDA(sd_index_ida); * object after last put) */ static DEFINE_MUTEX(sd_ref_mutex); +struct kmem_cache *sd_cdb_cache; +mempool_t *sd_cdb_pool; + static const char *sd_cache_types[] = { "write through", "none", "write back", "write back, no read (daft)" @@ -370,6 +373,31 @@ static void scsi_disk_put(struct scsi_disk *sdkp) mutex_unlock(&sd_ref_mutex); } +static void sd_prot_op(struct scsi_cmnd *scmd, unsigned int dif) +{ + unsigned int prot_op = SCSI_PROT_NORMAL; + unsigned int dix = scsi_prot_sg_count(scmd); + + if (scmd->sc_data_direction == DMA_FROM_DEVICE) { + if (dif && dix) + prot_op = SCSI_PROT_READ_PASS; + else if (dif && !dix) + prot_op = SCSI_PROT_READ_STRIP; + else if (!dif && dix) + prot_op = SCSI_PROT_READ_INSERT; + } else { + if (dif && dix) + prot_op = SCSI_PROT_WRITE_PASS; + else if (dif && !dix) + prot_op = SCSI_PROT_WRITE_INSERT; + else if (!dif && dix) + prot_op = SCSI_PROT_WRITE_STRIP; + } + + scsi_set_prot_op(scmd, prot_op); + scsi_set_prot_type(scmd, dif); +} + /** * sd_init_command - build a scsi (read or write) command from * information in the request structure. @@ -388,6 +416,7 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) sector_t threshold; unsigned int this_count = blk_rq_sectors(rq); int ret, host_dif; + unsigned char protect; if (rq->cmd_type == REQ_TYPE_BLOCK_PC) { ret = scsi_setup_blk_pc_cmnd(sdp, rq); @@ -520,13 +549,49 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) /* Set RDPROTECT/WRPROTECT if disk is formatted with DIF */ host_dif = scsi_host_dif_capable(sdp->host, sdkp->protection_type); if (host_dif) - SCpnt->cmnd[1] = 1 << 5; + protect = 1 << 5; else - SCpnt->cmnd[1] = 0; + protect = 0; - if (block > 0xffffffff) { + if (host_dif == SD_DIF_TYPE2_PROTECTION) { + SCpnt->cmnd = mempool_alloc(sd_cdb_pool, GFP_ATOMIC); + + if (unlikely(SCpnt->cmnd == NULL)) { + ret = BLKPREP_DEFER; + goto out; + } + + SCpnt->cmd_len = SD_EXT_CDB_SIZE; + memset(SCpnt->cmnd, 0, SCpnt->cmd_len); + SCpnt->cmnd[0] = VARIABLE_LENGTH_CMD; + SCpnt->cmnd[7] = 0x18; + SCpnt->cmnd[9] = (rq_data_dir(rq) == READ) ? READ_32 : WRITE_32; + SCpnt->cmnd[10] = protect | (blk_fua_rq(rq) ? 0x8 : 0); + + /* LBA */ + SCpnt->cmnd[12] = sizeof(block) > 4 ? (unsigned char) (block >> 56) & 0xff : 0; + SCpnt->cmnd[13] = sizeof(block) > 4 ? (unsigned char) (block >> 48) & 0xff : 0; + SCpnt->cmnd[14] = sizeof(block) > 4 ? (unsigned char) (block >> 40) & 0xff : 0; + SCpnt->cmnd[15] = sizeof(block) > 4 ? (unsigned char) (block >> 32) & 0xff : 0; + SCpnt->cmnd[16] = (unsigned char) (block >> 24) & 0xff; + SCpnt->cmnd[17] = (unsigned char) (block >> 16) & 0xff; + SCpnt->cmnd[18] = (unsigned char) (block >> 8) & 0xff; + SCpnt->cmnd[19] = (unsigned char) block & 0xff; + + /* Expected Indirect LBA */ + SCpnt->cmnd[20] = (unsigned char) (block >> 24) & 0xff; + SCpnt->cmnd[21] = (unsigned char) (block >> 16) & 0xff; + SCpnt->cmnd[22] = (unsigned char) (block >> 8) & 0xff; + SCpnt->cmnd[23] = (unsigned char) block & 0xff; + + /* Transfer length */ + SCpnt->cmnd[28] = (unsigned char) (this_count >> 24) & 0xff; + SCpnt->cmnd[29] = (unsigned char) (this_count >> 16) & 0xff; + SCpnt->cmnd[30] = (unsigned char) (this_count >> 8) & 0xff; + SCpnt->cmnd[31] = (unsigned char) this_count & 0xff; + } else if (block > 0xffffffff) { SCpnt->cmnd[0] += READ_16 - READ_6; - SCpnt->cmnd[1] |= blk_fua_rq(rq) ? 0x8 : 0; + SCpnt->cmnd[1] = protect | (blk_fua_rq(rq) ? 0x8 : 0); SCpnt->cmnd[2] = sizeof(block) > 4 ? (unsigned char) (block >> 56) & 0xff : 0; SCpnt->cmnd[3] = sizeof(block) > 4 ? (unsigned char) (block >> 48) & 0xff : 0; SCpnt->cmnd[4] = sizeof(block) > 4 ? (unsigned char) (block >> 40) & 0xff : 0; @@ -547,7 +612,7 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) this_count = 0xffff; SCpnt->cmnd[0] += READ_10 - READ_6; - SCpnt->cmnd[1] |= blk_fua_rq(rq) ? 0x8 : 0; + SCpnt->cmnd[1] = protect | (blk_fua_rq(rq) ? 0x8 : 0); SCpnt->cmnd[2] = (unsigned char) (block >> 24) & 0xff; SCpnt->cmnd[3] = (unsigned char) (block >> 16) & 0xff; SCpnt->cmnd[4] = (unsigned char) (block >> 8) & 0xff; @@ -578,8 +643,7 @@ static int sd_prep_fn(struct request_queue *q, struct request *rq) /* If DIF or DIX is enabled, tell HBA how to handle request */ if (host_dif || scsi_prot_sg_count(SCpnt)) - sd_dif_op(SCpnt, host_dif, scsi_prot_sg_count(SCpnt), - sdkp->protection_type); + sd_prot_op(SCpnt, host_dif); /* * We shouldn't disconnect in the middle of a sector, so with a dumb @@ -1023,6 +1087,7 @@ static int sd_done(struct scsi_cmnd *SCpnt) int result = SCpnt->result; unsigned int good_bytes = result ? 0 : scsi_bufflen(SCpnt); struct scsi_sense_hdr sshdr; + struct scsi_disk *sdkp = scsi_disk(SCpnt->request->rq_disk); int sense_valid = 0; int sense_deferred = 0; @@ -1084,6 +1149,10 @@ static int sd_done(struct scsi_cmnd *SCpnt) if (rq_data_dir(SCpnt->request) == READ && scsi_prot_sg_count(SCpnt)) sd_dif_complete(SCpnt, good_bytes); + if (scsi_host_dif_capable(sdkp->device->host, sdkp->protection_type) + == SD_DIF_TYPE2_PROTECTION && SCpnt->cmnd != SCpnt->request->cmd) + mempool_free(SCpnt->cmnd, sd_cdb_pool); + return good_bytes; } @@ -1238,34 +1307,28 @@ void sd_read_protection_type(struct scsi_disk *sdkp, unsigned char *buffer) u8 type; if (scsi_device_protection(sdp) == 0 || (buffer[12] & 1) == 0) - type = 0; - else - type = ((buffer[12] >> 1) & 7) + 1; /* P_TYPE 0 = Type 1 */ + return; - sdkp->protection_type = type; + type = ((buffer[12] >> 1) & 7) + 1; /* P_TYPE 0 = Type 1 */ - switch (type) { - case SD_DIF_TYPE0_PROTECTION: - case SD_DIF_TYPE1_PROTECTION: - case SD_DIF_TYPE3_PROTECTION: - break; + if (type == sdkp->protection_type || !sdkp->first_scan) + return; - case SD_DIF_TYPE2_PROTECTION: - sd_printk(KERN_ERR, sdkp, "formatted with DIF Type 2 " \ - "protection which is currently unsupported. " \ - "Disabling disk!\n"); - goto disable; + sdkp->protection_type = type; - default: - sd_printk(KERN_ERR, sdkp, "formatted with unknown " \ - "protection type %d. Disabling disk!\n", type); - goto disable; + if (type > SD_DIF_TYPE3_PROTECTION) { + sd_printk(KERN_ERR, sdkp, "formatted with unsupported " \ + "protection type %u. Disabling disk!\n", type); + sdkp->capacity = 0; + return; } - return; - -disable: - sdkp->capacity = 0; + if (scsi_host_dif_capable(sdp->host, type)) + sd_printk(KERN_NOTICE, sdkp, + "Enabling DIF Type %u protection\n", type); + else + sd_printk(KERN_NOTICE, sdkp, + "Disabling DIF Type %u protection\n", type); } static void read_capacity_error(struct scsi_disk *sdkp, struct scsi_device *sdp, @@ -2300,8 +2363,24 @@ static int __init init_sd(void) if (err) goto err_out_class; + sd_cdb_cache = kmem_cache_create("sd_ext_cdb", SD_EXT_CDB_SIZE, + 0, 0, NULL); + if (!sd_cdb_cache) { + printk(KERN_ERR "sd: can't init extended cdb cache\n"); + goto err_out_class; + } + + sd_cdb_pool = mempool_create_slab_pool(SD_MEMPOOL_SIZE, sd_cdb_cache); + if (!sd_cdb_pool) { + printk(KERN_ERR "sd: can't init extended cdb pool\n"); + goto err_out_cache; + } + return 0; +err_out_cache: + kmem_cache_destroy(sd_cdb_cache); + err_out_class: class_unregister(&sd_disk_class); err_out: @@ -2321,6 +2400,9 @@ static void __exit exit_sd(void) SCSI_LOG_HLQUEUE(3, printk("exit_sd: exiting sd driver\n")); + mempool_destroy(sd_cdb_pool); + kmem_cache_destroy(sd_cdb_cache); + scsi_unregister_driver(&sd_template.gendrv); class_unregister(&sd_disk_class); diff --git a/drivers/scsi/sd.h b/drivers/scsi/sd.h index 8474b5bad3fe..e374804d26fb 100644 --- a/drivers/scsi/sd.h +++ b/drivers/scsi/sd.h @@ -37,6 +37,11 @@ */ #define SD_LAST_BUGGY_SECTORS 8 +enum { + SD_EXT_CDB_SIZE = 32, /* Extended CDB size */ + SD_MEMPOOL_SIZE = 2, /* CDB pool size */ +}; + struct scsi_disk { struct scsi_driver *driver; /* always &sd_template */ struct scsi_device *device; @@ -101,16 +106,12 @@ struct sd_dif_tuple { #ifdef CONFIG_BLK_DEV_INTEGRITY -extern void sd_dif_op(struct scsi_cmnd *, unsigned int, unsigned int, unsigned int); extern void sd_dif_config_host(struct scsi_disk *); extern int sd_dif_prepare(struct request *rq, sector_t, unsigned int); extern void sd_dif_complete(struct scsi_cmnd *, unsigned int); #else /* CONFIG_BLK_DEV_INTEGRITY */ -static inline void sd_dif_op(struct scsi_cmnd *cmd, unsigned int a, unsigned int b, unsigned int c) -{ -} static inline void sd_dif_config_host(struct scsi_disk *disk) { } diff --git a/drivers/scsi/sd_dif.c b/drivers/scsi/sd_dif.c index 82f14a9482d0..88da97745710 100644 --- a/drivers/scsi/sd_dif.c +++ b/drivers/scsi/sd_dif.c @@ -320,15 +320,6 @@ void sd_dif_config_host(struct scsi_disk *sdkp) dif = 0; dix = 1; } - if (type) { - if (dif) - sd_printk(KERN_NOTICE, sdkp, - "Enabling DIF Type %d protection\n", type); - else - sd_printk(KERN_NOTICE, sdkp, - "Disabling DIF Type %d protection\n", type); - } - if (!dix) return; @@ -360,62 +351,6 @@ void sd_dif_config_host(struct scsi_disk *sdkp) } /* - * DIF DMA operation magic decoder ring. - */ -void sd_dif_op(struct scsi_cmnd *scmd, unsigned int dif, unsigned int dix, unsigned int type) -{ - int csum_convert, prot_op; - - prot_op = 0; - - /* Convert checksum? */ - if (scsi_host_get_guard(scmd->device->host) != SHOST_DIX_GUARD_CRC) - csum_convert = 1; - else - csum_convert = 0; - - BUG_ON(dif && (scmd->cmnd[0] == READ_6 || scmd->cmnd[0] == WRITE_6)); - - switch (scmd->cmnd[0]) { - case READ_6: - case READ_10: - case READ_12: - case READ_16: - if (dif && dix) - if (csum_convert) - prot_op = SCSI_PROT_READ_CONVERT; - else - prot_op = SCSI_PROT_READ_PASS; - else if (dif && !dix) - prot_op = SCSI_PROT_READ_STRIP; - else if (!dif && dix) - prot_op = SCSI_PROT_READ_INSERT; - - break; - - case WRITE_6: - case WRITE_10: - case WRITE_12: - case WRITE_16: - if (dif && dix) - if (csum_convert) - prot_op = SCSI_PROT_WRITE_CONVERT; - else - prot_op = SCSI_PROT_WRITE_PASS; - else if (dif && !dix) - prot_op = SCSI_PROT_WRITE_INSERT; - else if (!dif && dix) - prot_op = SCSI_PROT_WRITE_STRIP; - - break; - } - - scsi_set_prot_op(scmd, prot_op); - if (dif) - scsi_set_prot_type(scmd, type); -} - -/* * The virtual start sector is the one that was originally submitted * by the block layer. Due to partitioning, MD/DM cloning, etc. the * actual physical start sector is likely to be different. Remap diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c index 747a5e5c1276..040f751809ea 100644 --- a/drivers/scsi/sg.c +++ b/drivers/scsi/sg.c @@ -1708,11 +1708,6 @@ static int sg_finish_rem_req(Sg_request * srp) Sg_scatter_hold *req_schp = &srp->data; SCSI_LOG_TIMEOUT(4, printk("sg_finish_rem_req: res_used=%d\n", (int) srp->res_used)); - if (srp->res_used) - sg_unlink_reserve(sfp, srp); - else - sg_remove_scat(req_schp); - if (srp->rq) { if (srp->bio) ret = blk_rq_unmap_user(srp->bio); @@ -1720,6 +1715,11 @@ static int sg_finish_rem_req(Sg_request * srp) blk_put_request(srp->rq); } + if (srp->res_used) + sg_unlink_reserve(sfp, srp); + else + sg_remove_scat(req_schp); + sg_remove_request(sfp, srp); return ret; diff --git a/drivers/scsi/sr.c b/drivers/scsi/sr.c index eb61f7a70e1d..d6f340f48a3b 100644 --- a/drivers/scsi/sr.c +++ b/drivers/scsi/sr.c @@ -684,14 +684,20 @@ static void get_sectorsize(struct scsi_cd *cd) cd->capacity = 0x1fffff; sector_size = 2048; /* A guess, just in case */ } else { -#if 0 - if (cdrom_get_last_written(&cd->cdi, - &cd->capacity)) -#endif - cd->capacity = 1 + ((buffer[0] << 24) | - (buffer[1] << 16) | - (buffer[2] << 8) | - buffer[3]); + long last_written; + + cd->capacity = 1 + ((buffer[0] << 24) | (buffer[1] << 16) | + (buffer[2] << 8) | buffer[3]); + /* + * READ_CAPACITY doesn't return the correct size on + * certain UDF media. If last_written is larger, use + * it instead. + * + * http://bugzilla.kernel.org/show_bug.cgi?id=9668 + */ + if (!cdrom_get_last_written(&cd->cdi, &last_written)) + cd->capacity = max_t(long, cd->capacity, last_written); + sector_size = (buffer[4] << 24) | (buffer[5] << 16) | (buffer[6] << 8) | buffer[7]; switch (sector_size) { diff --git a/drivers/scsi/st.c b/drivers/scsi/st.c index b33d04250bbc..12d58a7ed6bc 100644 --- a/drivers/scsi/st.c +++ b/drivers/scsi/st.c @@ -2859,11 +2859,8 @@ static int st_int_ioctl(struct scsi_tape *STp, unsigned int cmd_in, unsigned lon ioctl_result = st_int_ioctl(STp, MTBSF, 1); if (cmd_in == MTSETBLK || cmd_in == SET_DENS_AND_BLK) { - int old_block_size = STp->block_size; STp->block_size = arg & MT_ST_BLKSIZE_MASK; if (STp->block_size != 0) { - if (old_block_size == 0) - normalize_buffer(STp->buffer); (STp->buffer)->buffer_blocks = (STp->buffer)->buffer_size / STp->block_size; } diff --git a/drivers/serial/8250.c b/drivers/serial/8250.c index b1ae774016f1..737b4c960971 100644 --- a/drivers/serial/8250.c +++ b/drivers/serial/8250.c @@ -1089,7 +1089,7 @@ static void autoconfig(struct uart_8250_port *up, unsigned int probeflags) if (!up->port.iobase && !up->port.mapbase && !up->port.membase) return; - DEBUG_AUTOCONF("ttyS%d: autoconf (0x%04x, 0x%p): ", + DEBUG_AUTOCONF("ttyS%d: autoconf (0x%04lx, 0x%p): ", serial_index(&up->port), up->port.iobase, up->port.membase); /* diff --git a/drivers/serial/8250_pci.c b/drivers/serial/8250_pci.c index e7108e75653d..b28af13c45a1 100644 --- a/drivers/serial/8250_pci.c +++ b/drivers/serial/8250_pci.c @@ -1561,11 +1561,16 @@ enum pci_board_num_t { pbn_exar_XR17C152, pbn_exar_XR17C154, pbn_exar_XR17C158, + pbn_exar_ibm_saturn, pbn_pasemi_1682M, pbn_ni8430_2, pbn_ni8430_4, pbn_ni8430_8, pbn_ni8430_16, + pbn_ADDIDATA_PCIe_1_3906250, + pbn_ADDIDATA_PCIe_2_3906250, + pbn_ADDIDATA_PCIe_4_3906250, + pbn_ADDIDATA_PCIe_8_3906250, }; /* @@ -2146,6 +2151,13 @@ static struct pciserial_board pci_boards[] __devinitdata = { .base_baud = 921600, .uart_offset = 0x200, }, + [pbn_exar_ibm_saturn] = { + .flags = FL_BASE0, + .num_ports = 1, + .base_baud = 921600, + .uart_offset = 0x200, + }, + /* * PA Semi PWRficient PA6T-1682M on-chip UART */ @@ -2185,6 +2197,37 @@ static struct pciserial_board pci_boards[] __devinitdata = { .uart_offset = 0x10, .first_offset = 0x800, }, + /* + * ADDI-DATA GmbH PCI-Express communication cards <info@addi-data.com> + */ + [pbn_ADDIDATA_PCIe_1_3906250] = { + .flags = FL_BASE0, + .num_ports = 1, + .base_baud = 3906250, + .uart_offset = 0x200, + .first_offset = 0x1000, + }, + [pbn_ADDIDATA_PCIe_2_3906250] = { + .flags = FL_BASE0, + .num_ports = 2, + .base_baud = 3906250, + .uart_offset = 0x200, + .first_offset = 0x1000, + }, + [pbn_ADDIDATA_PCIe_4_3906250] = { + .flags = FL_BASE0, + .num_ports = 4, + .base_baud = 3906250, + .uart_offset = 0x200, + .first_offset = 0x1000, + }, + [pbn_ADDIDATA_PCIe_8_3906250] = { + .flags = FL_BASE0, + .num_ports = 8, + .base_baud = 3906250, + .uart_offset = 0x200, + .first_offset = 0x1000, + }, }; static const struct pci_device_id softmodem_blacklist[] = { @@ -2340,7 +2383,7 @@ pciserial_init_ports(struct pci_dev *dev, const struct pciserial_board *board) break; #ifdef SERIAL_DEBUG_PCI - printk(KERN_DEBUG "Setup PCI port: port %x, irq %d, type %d\n", + printk(KERN_DEBUG "Setup PCI port: port %lx, irq %d, type %d\n", serial_port.iobase, serial_port.irq, serial_port.iotype); #endif @@ -2649,6 +2692,9 @@ static struct pci_device_id serial_pci_tbl[] = { PCI_SUBVENDOR_ID_CONNECT_TECH, PCI_SUBDEVICE_ID_CONNECT_TECH_PCI_UART_8_485, 0, 0, pbn_b0_8_1843200_200 }, + { PCI_VENDOR_ID_EXAR, PCI_DEVICE_ID_EXAR_XR17C152, + PCI_VENDOR_ID_IBM, PCI_SUBDEVICE_ID_IBM_SATURN_SERIAL_ONE_PORT, + 0, 0, pbn_exar_ibm_saturn }, { PCI_VENDOR_ID_SEALEVEL, PCI_DEVICE_ID_SEALEVEL_U530, PCI_ANY_ID, PCI_ANY_ID, 0, 0, @@ -3093,6 +3139,12 @@ static struct pci_device_id serial_pci_tbl[] = { { PCI_VENDOR_ID_LAVA, PCI_DEVICE_ID_LAVA_QUATRO_B, PCI_ANY_ID, PCI_ANY_ID, 0, 0, pbn_b0_bt_2_115200 }, + { PCI_VENDOR_ID_LAVA, PCI_DEVICE_ID_LAVA_QUATTRO_A, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, + pbn_b0_bt_2_115200 }, + { PCI_VENDOR_ID_LAVA, PCI_DEVICE_ID_LAVA_QUATTRO_B, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, + pbn_b0_bt_2_115200 }, { PCI_VENDOR_ID_LAVA, PCI_DEVICE_ID_LAVA_OCTO_A, PCI_ANY_ID, PCI_ANY_ID, 0, 0, pbn_b0_bt_4_460800 }, @@ -3556,6 +3608,38 @@ static struct pci_device_id serial_pci_tbl[] = { 0, pbn_b0_8_115200 }, + { PCI_VENDOR_ID_ADDIDATA, + PCI_DEVICE_ID_ADDIDATA_APCIe7500, + PCI_ANY_ID, + PCI_ANY_ID, + 0, + 0, + pbn_ADDIDATA_PCIe_4_3906250 }, + + { PCI_VENDOR_ID_ADDIDATA, + PCI_DEVICE_ID_ADDIDATA_APCIe7420, + PCI_ANY_ID, + PCI_ANY_ID, + 0, + 0, + pbn_ADDIDATA_PCIe_2_3906250 }, + + { PCI_VENDOR_ID_ADDIDATA, + PCI_DEVICE_ID_ADDIDATA_APCIe7300, + PCI_ANY_ID, + PCI_ANY_ID, + 0, + 0, + pbn_ADDIDATA_PCIe_1_3906250 }, + + { PCI_VENDOR_ID_ADDIDATA, + PCI_DEVICE_ID_ADDIDATA_APCIe7800, + PCI_ANY_ID, + PCI_ANY_ID, + 0, + 0, + pbn_ADDIDATA_PCIe_8_3906250 }, + { PCI_VENDOR_ID_NETMOS, PCI_DEVICE_ID_NETMOS_9835, PCI_VENDOR_ID_IBM, 0x0299, 0, 0, pbn_b0_bt_2_115200 }, diff --git a/drivers/serial/atmel_serial.c b/drivers/serial/atmel_serial.c index 3551c5cb7094..9d948bccafaf 100644 --- a/drivers/serial/atmel_serial.c +++ b/drivers/serial/atmel_serial.c @@ -1531,7 +1531,7 @@ static int __devinit atmel_serial_probe(struct platform_device *pdev) void *data; int ret; - BUILD_BUG_ON(!is_power_of_2(ATMEL_SERIAL_RINGSIZE)); + BUILD_BUG_ON(ATMEL_SERIAL_RINGSIZE & (ATMEL_SERIAL_RINGSIZE - 1)); port = &atmel_ports[pdev->id]; port->backup_imr = 0; diff --git a/drivers/serial/mpc52xx_uart.c b/drivers/serial/mpc52xx_uart.c index d7bcd074d383..7ce9e9f567a3 100644 --- a/drivers/serial/mpc52xx_uart.c +++ b/drivers/serial/mpc52xx_uart.c @@ -705,7 +705,7 @@ mpc52xx_uart_verify_port(struct uart_port *port, struct serial_struct *ser) return -EINVAL; if ((ser->irq != port->irq) || - (ser->io_type != SERIAL_IO_MEM) || + (ser->io_type != UPIO_MEM) || (ser->baud_base != port->uartclk) || (ser->iomem_base != (void *)port->mapbase) || (ser->hub6 != 0)) diff --git a/drivers/serial/serial_core.c b/drivers/serial/serial_core.c index 1689bda1d13b..dcc72444e8e7 100644 --- a/drivers/serial/serial_core.c +++ b/drivers/serial/serial_core.c @@ -1270,6 +1270,9 @@ static void uart_close(struct tty_struct *tty, struct file *filp) BUG_ON(!kernel_locked()); + if (!state) + return; + uport = state->uart_port; port = &state->port; @@ -1316,9 +1319,9 @@ static void uart_close(struct tty_struct *tty, struct file *filp) */ if (port->flags & ASYNC_INITIALIZED) { unsigned long flags; - spin_lock_irqsave(&port->lock, flags); + spin_lock_irqsave(&uport->lock, flags); uport->ops->stop_rx(uport); - spin_unlock_irqrestore(&port->lock, flags); + spin_unlock_irqrestore(&uport->lock, flags); /* * Before we drop DTR, make sure the UART transmitter * has completely drained; this is especially diff --git a/drivers/serial/sh-sci.c b/drivers/serial/sh-sci.c index 85119fb7cb50..6498bd1fb6dd 100644 --- a/drivers/serial/sh-sci.c +++ b/drivers/serial/sh-sci.c @@ -1143,7 +1143,7 @@ static void serial_console_write(struct console *co, const char *s, while ((sci_in(port, SCxSR) & bits) != bits) cpu_relax(); - if (sci_port->disable); + if (sci_port->disable) sci_port->disable(port); } diff --git a/drivers/spi/amba-pl022.c b/drivers/spi/amba-pl022.c index 958a3ffc8987..ff5bbb9c43c9 100644 --- a/drivers/spi/amba-pl022.c +++ b/drivers/spi/amba-pl022.c @@ -1826,7 +1826,7 @@ static struct amba_id pl022_ids[] = { * ST Micro derivative, this has 32bit wide * and 32 locations deep TX/RX FIFO */ - .id = 0x00108022, + .id = 0x01080022, .mask = 0xffffffff, .data = &vendor_st, }, diff --git a/drivers/spi/spi_stmp.c b/drivers/spi/spi_stmp.c index d871dc23909c..2552bb364005 100644 --- a/drivers/spi/spi_stmp.c +++ b/drivers/spi/spi_stmp.c @@ -242,7 +242,7 @@ static int stmp_spi_txrx_dma(struct stmp_spi *ss, int cs, wait_for_completion(&ss->done); if (!busy_wait(readl(ss->regs + HW_SSP_CTRL0) & BM_SSP_CTRL0_RUN)) - status = ETIMEDOUT; + status = -ETIMEDOUT; if (!dma_buf) dma_unmap_single(ss->master_dev, spi_buf_dma, len, dir); diff --git a/drivers/staging/Kconfig b/drivers/staging/Kconfig index 4e3873bfd010..dfcd75cf4907 100644 --- a/drivers/staging/Kconfig +++ b/drivers/staging/Kconfig @@ -59,8 +59,6 @@ source "drivers/staging/echo/Kconfig" source "drivers/staging/poch/Kconfig" -source "drivers/staging/agnx/Kconfig" - source "drivers/staging/otus/Kconfig" source "drivers/staging/rt2860/Kconfig" @@ -95,8 +93,6 @@ source "drivers/staging/dst/Kconfig" source "drivers/staging/pohmelfs/Kconfig" -source "drivers/staging/stlc45xx/Kconfig" - source "drivers/staging/b3dfg/Kconfig" source "drivers/staging/phison/Kconfig" @@ -129,8 +125,6 @@ source "drivers/staging/sep/Kconfig" source "drivers/staging/iio/Kconfig" -source "drivers/staging/cowloop/Kconfig" - source "drivers/staging/strip/Kconfig" source "drivers/staging/arlan/Kconfig" diff --git a/drivers/staging/Makefile b/drivers/staging/Makefile index fb1d7851b563..7719d04a4a86 100644 --- a/drivers/staging/Makefile +++ b/drivers/staging/Makefile @@ -12,7 +12,6 @@ obj-$(CONFIG_W35UND) += winbond/ obj-$(CONFIG_PRISM2_USB) += wlan-ng/ obj-$(CONFIG_ECHO) += echo/ obj-$(CONFIG_POCH) += poch/ -obj-$(CONFIG_AGNX) += agnx/ obj-$(CONFIG_OTUS) += otus/ obj-$(CONFIG_RT2860) += rt2860/ obj-$(CONFIG_RT2870) += rt2870/ @@ -30,7 +29,6 @@ obj-$(CONFIG_ANDROID) += android/ obj-$(CONFIG_ANDROID) += dream/ obj-$(CONFIG_DST) += dst/ obj-$(CONFIG_POHMELFS) += pohmelfs/ -obj-$(CONFIG_STLC45XX) += stlc45xx/ obj-$(CONFIG_B3DFG) += b3dfg/ obj-$(CONFIG_IDE_PHISON) += phison/ obj-$(CONFIG_PLAN9AUTH) += p9auth/ @@ -46,7 +44,6 @@ obj-$(CONFIG_VME_BUS) += vme/ obj-$(CONFIG_RAR_REGISTER) += rar/ obj-$(CONFIG_DX_SEP) += sep/ obj-$(CONFIG_IIO) += iio/ -obj-$(CONFIG_COWLOOP) += cowloop/ obj-$(CONFIG_STRIP) += strip/ obj-$(CONFIG_ARLAN) += arlan/ obj-$(CONFIG_WAVELAN) += wavelan/ diff --git a/drivers/staging/agnx/Kconfig b/drivers/staging/agnx/Kconfig deleted file mode 100644 index 7f43549e36dd..000000000000 --- a/drivers/staging/agnx/Kconfig +++ /dev/null @@ -1,5 +0,0 @@ -config AGNX - tristate "Wireless Airgo AGNX support" - depends on WLAN_80211 && MAC80211 - ---help--- - This is an experimental driver for Airgo AGNX00 wireless chip. diff --git a/drivers/staging/agnx/Makefile b/drivers/staging/agnx/Makefile deleted file mode 100644 index 1216564a312d..000000000000 --- a/drivers/staging/agnx/Makefile +++ /dev/null @@ -1,8 +0,0 @@ -obj-$(CONFIG_AGNX) += agnx.o - -agnx-objs := rf.o \ - pci.o \ - xmit.o \ - table.o \ - sta.o \ - phy.o diff --git a/drivers/staging/agnx/TODO b/drivers/staging/agnx/TODO deleted file mode 100644 index 89bec74318aa..000000000000 --- a/drivers/staging/agnx/TODO +++ /dev/null @@ -1,22 +0,0 @@ -2008 7/18 - -The RX has can't receive OFDM packet correctly, -Guess it need be do RX calibrate. - - -before 2008 3/1 - -1: The RX get too much "CRC failed" pakets, it make the card work very unstable, -2: After running a while, the card will get infinity "RX Frame" and "Error" -interrupt, not know the root reason so far, try to fix it -3: Using two tx queue txd and txm but not only txm. -4: Set the hdr correctly. -5: Try to do recalibrate correvtly -6: To support G mode in future -7: Fix the mac address can't be readed and set correctly in BE machine. -8: Fix include and exclude FCS in promisous mode and manage mode -9: Using sta_notify to notice sta change -10: Turn on frame reception at the end of start -11: Guess the card support HW_MULTICAST_FILTER -12: The tx process should be implment atomic? -13: Using mac80211 function to control the TX&RX LED. diff --git a/drivers/staging/agnx/agnx.h b/drivers/staging/agnx/agnx.h deleted file mode 100644 index 3963d2597a11..000000000000 --- a/drivers/staging/agnx/agnx.h +++ /dev/null @@ -1,156 +0,0 @@ -#ifndef AGNX_H_ -#define AGNX_H_ - -#include <linux/io.h> - -#include "xmit.h" - -#define PFX KBUILD_MODNAME ": " - -static inline u32 agnx_read32(void __iomem *mem_region, u32 offset) -{ - return ioread32(mem_region + offset); -} - -static inline void agnx_write32(void __iomem *mem_region, u32 offset, u32 val) -{ - iowrite32(val, mem_region + offset); -} - -/* static const struct ieee80211_rate agnx_rates_80211b[] = { */ -/* { .rate = 10, */ -/* .val = 0xa, */ -/* .flags = IEEE80211_RATE_CCK }, */ -/* { .rate = 20, */ -/* .val = 0x14, */ -/* .hw_value = -0x14, */ -/* .flags = IEEE80211_RATE_CCK_2 }, */ -/* { .rate = 55, */ -/* .val = 0x37, */ -/* .val2 = -0x37, */ -/* .flags = IEEE80211_RATE_CCK_2 }, */ -/* { .rate = 110, */ -/* .val = 0x6e, */ -/* .val2 = -0x6e, */ -/* .flags = IEEE80211_RATE_CCK_2 } */ -/* }; */ - - -static const struct ieee80211_rate agnx_rates_80211g[] = { -/* { .bitrate = 10, .hw_value = 1, .flags = IEEE80211_RATE_SHORT_PREAMBLE }, */ -/* { .bitrate = 20, .hw_value = 2, .flags = IEEE80211_RATE_SHORT_PREAMBLE }, */ -/* { .bitrate = 55, .hw_value = 3, .flags = IEEE80211_RATE_SHORT_PREAMBLE }, */ -/* { .bitrate = 110, .hw_value = 4, .flags = IEEE80211_RATE_SHORT_PREAMBLE }, */ - { .bitrate = 10, .hw_value = 1, }, - { .bitrate = 20, .hw_value = 2, }, - { .bitrate = 55, .hw_value = 3, }, - { .bitrate = 110, .hw_value = 4,}, - - { .bitrate = 60, .hw_value = 0xB, }, - { .bitrate = 90, .hw_value = 0xF, }, - { .bitrate = 120, .hw_value = 0xA }, - { .bitrate = 180, .hw_value = 0xE, }, -/* { .bitrate = 240, .hw_value = 0xd, }, */ - { .bitrate = 360, .hw_value = 0xD, }, - { .bitrate = 480, .hw_value = 0x8, }, - { .bitrate = 540, .hw_value = 0xC, }, -}; - -static const struct ieee80211_channel agnx_channels[] = { - { .center_freq = 2412, .hw_value = 1, }, - { .center_freq = 2417, .hw_value = 2, }, - { .center_freq = 2422, .hw_value = 3, }, - { .center_freq = 2427, .hw_value = 4, }, - { .center_freq = 2432, .hw_value = 5, }, - { .center_freq = 2437, .hw_value = 6, }, - { .center_freq = 2442, .hw_value = 7, }, - { .center_freq = 2447, .hw_value = 8, }, - { .center_freq = 2452, .hw_value = 9, }, - { .center_freq = 2457, .hw_value = 10, }, - { .center_freq = 2462, .hw_value = 11, }, - { .center_freq = 2467, .hw_value = 12, }, - { .center_freq = 2472, .hw_value = 13, }, - { .center_freq = 2484, .hw_value = 14, }, -}; - -#define NUM_DRIVE_MODES 2 -/* Agnx operate mode */ -enum { - AGNX_MODE_80211A, - AGNX_MODE_80211A_OOB, - AGNX_MODE_80211A_MIMO, - AGNX_MODE_80211B_SHORT, - AGNX_MODE_80211B_LONG, - AGNX_MODE_80211G, - AGNX_MODE_80211G_OOB, - AGNX_MODE_80211G_MIMO, -}; - -enum { - AGNX_UNINIT, - AGNX_START, - AGNX_STOP, -}; - -struct agnx_priv { - struct pci_dev *pdev; - struct ieee80211_hw *hw; - - spinlock_t lock; - struct mutex mutex; - unsigned int init_status; - - void __iomem *ctl; /* pointer to base ram address */ - void __iomem *data; /* pointer to mem region #2 */ - - struct agnx_ring rx; - struct agnx_ring txm; - struct agnx_ring txd; - - /* Need volatile? */ - u32 irq_status; - - struct delayed_work periodic_work; /* Periodic tasks like recalibrate */ - struct ieee80211_low_level_stats stats; - - /* unsigned int phymode; */ - int mode; - int channel; - u8 bssid[ETH_ALEN]; - - u8 mac_addr[ETH_ALEN]; - u8 revid; - - struct ieee80211_supported_band band; -}; - - -#define AGNX_CHAINS_MAX 6 -#define AGNX_PERIODIC_DELAY 60000 /* unit: ms */ -#define LOCAL_STAID 0 /* the station entry for the card itself */ -#define BSSID_STAID 1 /* the station entry for the bsssid AP */ -#define spi_delay() udelay(40) -#define eeprom_delay() udelay(40) -#define routing_table_delay() udelay(50) - -/* PDU pool MEM region #2 */ -#define AGNX_PDUPOOL 0x40000 /* PDU pool */ -#define AGNX_PDUPOOL_SIZE 0x8000 /* PDU pool size*/ -#define AGNX_PDU_TX_WQ 0x41000 /* PDU list TX workqueue */ -#define AGNX_PDU_FREE 0x41800 /* Free Pool */ -#define PDU_SIZE 0x80 /* Free Pool node size */ -#define PDU_FREE_CNT 0xd0 /* Free pool node count */ - - -/* RF stuffs */ -extern void rf_chips_init(struct agnx_priv *priv); -extern void spi_rc_write(void __iomem *mem_region, u32 chip_ids, u32 sw); -extern void calibrate_oscillator(struct agnx_priv *priv); -extern void do_calibration(struct agnx_priv *priv); -extern void antenna_calibrate(struct agnx_priv *priv); -extern void __antenna_calibrate(struct agnx_priv *priv); -extern void print_offsets(struct agnx_priv *priv); -extern int agnx_set_channel(struct agnx_priv *priv, unsigned int channel); - - -#endif /* AGNX_H_ */ diff --git a/drivers/staging/agnx/debug.h b/drivers/staging/agnx/debug.h deleted file mode 100644 index 7947f327a214..000000000000 --- a/drivers/staging/agnx/debug.h +++ /dev/null @@ -1,416 +0,0 @@ -#ifndef AGNX_DEBUG_H_ -#define AGNX_DEBUG_H_ - -#include "agnx.h" -#include "phy.h" -#include "sta.h" -#include "xmit.h" - -#define AGNX_TRACE printk(KERN_ERR PFX "function:%s line:%d\n", __func__, __LINE__) - -#define PRINTK_LE16(prefix, var) printk(KERN_DEBUG PFX #prefix ": " #var " 0x%.4x\n", le16_to_cpu(var)) -#define PRINTK_LE32(prefix, var) printk(KERN_DEBUG PFX #prefix ": " #var " 0x%.8x\n", le32_to_cpu(var)) -#define PRINTK_U8(prefix, var) printk(KERN_DEBUG PFX #prefix ": " #var " 0x%.2x\n", var) -#define PRINTK_BE16(prefix, var) printk(KERN_DEBUG PFX #prefix ": " #var " 0x%.4x\n", be16_to_cpu(var)) -#define PRINTK_BE32(prefix, var) printk(KERN_DEBUG PFX #prefix ": " #var " 0x%.8x\n", be32_to_cpu(var)) -#define PRINTK_BITS(prefix, field) printk(KERN_DEBUG PFX #prefix ": " #field ": 0x%x\n", (reg & field) >> field##_SHIFT) - -static inline void agnx_bug(char *reason) -{ - printk(KERN_ERR PFX "%s\n", reason); - BUG(); -} - -static inline void agnx_print_desc(struct agnx_desc *desc) -{ - u32 reg = be32_to_cpu(desc->frag); - - PRINTK_BITS(DESC, PACKET_LEN); - - if (reg & FIRST_FRAG) { - PRINTK_BITS(DESC, FIRST_PACKET_MASK); - PRINTK_BITS(DESC, FIRST_RESERV2); - PRINTK_BITS(DESC, FIRST_TKIP_ERROR); - PRINTK_BITS(DESC, FIRST_TKIP_PACKET); - PRINTK_BITS(DESC, FIRST_RESERV1); - PRINTK_BITS(DESC, FIRST_FRAG_LEN); - } else { - PRINTK_BITS(DESC, SUB_RESERV2); - PRINTK_BITS(DESC, SUB_TKIP_ERROR); - PRINTK_BITS(DESC, SUB_TKIP_PACKET); - PRINTK_BITS(DESC, SUB_RESERV1); - PRINTK_BITS(DESC, SUB_FRAG_LEN); - } - - PRINTK_BITS(DESC, FIRST_FRAG); - PRINTK_BITS(DESC, LAST_FRAG); - PRINTK_BITS(DESC, OWNER); -} - - -static inline void dump_ieee80211b_phy_hdr(__be32 _11b0, __be32 _11b1) -{ - -} - -static inline void agnx_print_hdr(struct agnx_hdr *hdr) -{ - u32 reg; - int i; - - reg = be32_to_cpu(hdr->reg0); - PRINTK_BITS(HDR, RTS); - PRINTK_BITS(HDR, MULTICAST); - PRINTK_BITS(HDR, ACK); - PRINTK_BITS(HDR, TM); - PRINTK_BITS(HDR, RELAY); - PRINTK_BITS(HDR, REVISED_FCS); - PRINTK_BITS(HDR, NEXT_BUFFER_ADDR); - - reg = be32_to_cpu(hdr->reg1); - PRINTK_BITS(HDR, MAC_HDR_LEN); - PRINTK_BITS(HDR, DURATION_OVERIDE); - PRINTK_BITS(HDR, PHY_HDR_OVERIDE); - PRINTK_BITS(HDR, CRC_FAIL); - PRINTK_BITS(HDR, SEQUENCE_NUMBER); - PRINTK_BITS(HDR, BUFF_HEAD_ADDR); - - reg = be32_to_cpu(hdr->reg2); - PRINTK_BITS(HDR, PDU_COUNT); - PRINTK_BITS(HDR, WEP_KEY); - PRINTK_BITS(HDR, USES_WEP_KEY); - PRINTK_BITS(HDR, KEEP_ALIVE); - PRINTK_BITS(HDR, BUFF_TAIL_ADDR); - - reg = be32_to_cpu(hdr->reg3); - PRINTK_BITS(HDR, CTS_11G); - PRINTK_BITS(HDR, RTS_11G); - PRINTK_BITS(HDR, FRAG_SIZE); - PRINTK_BITS(HDR, PAYLOAD_LEN); - PRINTK_BITS(HDR, FRAG_NUM); - - reg = be32_to_cpu(hdr->reg4); - PRINTK_BITS(HDR, RELAY_STAID); - PRINTK_BITS(HDR, STATION_ID); - PRINTK_BITS(HDR, WORKQUEUE_ID); - - reg = be32_to_cpu(hdr->reg5); - /* printf the route flag */ - PRINTK_BITS(HDR, ROUTE_HOST); - PRINTK_BITS(HDR, ROUTE_CARD_CPU); - PRINTK_BITS(HDR, ROUTE_ENCRYPTION); - PRINTK_BITS(HDR, ROUTE_TX); - PRINTK_BITS(HDR, ROUTE_RX1); - PRINTK_BITS(HDR, ROUTE_RX2); - PRINTK_BITS(HDR, ROUTE_COMPRESSION); - - PRINTK_BE32(HDR, hdr->_11g0); - PRINTK_BE32(HDR, hdr->_11g1); - PRINTK_BE32(HDR, hdr->_11b0); - PRINTK_BE32(HDR, hdr->_11b1); - - dump_ieee80211b_phy_hdr(hdr->_11b0, hdr->_11b1); - - /* Fixme */ - for (i = 0; i < ARRAY_SIZE(hdr->mac_hdr); i++) { - if (i == 0) - printk(KERN_DEBUG PFX "IEEE80211 HDR: "); - printk("%.2x ", hdr->mac_hdr[i]); - if (i + 1 == ARRAY_SIZE(hdr->mac_hdr)) - printk("\n"); - } - - PRINTK_BE16(HDR, hdr->rts_duration); - PRINTK_BE16(HDR, hdr->last_duration); - PRINTK_BE16(HDR, hdr->sec_last_duration); - PRINTK_BE16(HDR, hdr->other_duration); - PRINTK_BE16(HDR, hdr->tx_other_duration); - PRINTK_BE16(HDR, hdr->last_11g_len); - PRINTK_BE16(HDR, hdr->other_11g_len); - PRINTK_BE16(HDR, hdr->last_11b_len); - PRINTK_BE16(HDR, hdr->other_11b_len); - - /* FIXME */ - reg = be16_to_cpu(hdr->reg6); - PRINTK_BITS(HDR, MBF); - PRINTK_BITS(HDR, RSVD4); - - PRINTK_BE16(HDR, hdr->rx_frag_stat); - - PRINTK_BE32(HDR, hdr->time_stamp); - PRINTK_BE32(HDR, hdr->phy_stats_hi); - PRINTK_BE32(HDR, hdr->phy_stats_lo); - PRINTK_BE32(HDR, hdr->mic_key0); - PRINTK_BE32(HDR, hdr->mic_key1); -} /* agnx_print_hdr */ - - -static inline void agnx_print_rx_hdr(struct agnx_hdr *hdr) -{ - agnx_print_hdr(hdr); - - PRINTK_BE16(HDR, hdr->rx.rx_packet_duration); - PRINTK_BE16(HDR, hdr->rx.replay_cnt); - - PRINTK_U8(HDR, hdr->rx_channel); -} - -static inline void agnx_print_tx_hdr(struct agnx_hdr *hdr) -{ - agnx_print_hdr(hdr); - - PRINTK_U8(HDR, hdr->tx.long_retry_limit); - PRINTK_U8(HDR, hdr->tx.short_retry_limit); - PRINTK_U8(HDR, hdr->tx.long_retry_cnt); - PRINTK_U8(HDR, hdr->tx.short_retry_cnt); - - PRINTK_U8(HDR, hdr->rx_channel); -} - -static inline void -agnx_print_sta_power(struct agnx_priv *priv, unsigned int sta_idx) -{ - struct agnx_sta_power power; - u32 reg; - - get_sta_power(priv, &power, sta_idx); - - reg = le32_to_cpu(power.reg); - PRINTK_BITS(STA_POWER, SIGNAL); - PRINTK_BITS(STA_POWER, RATE); - PRINTK_BITS(STA_POWER, TIFS); - PRINTK_BITS(STA_POWER, EDCF); - PRINTK_BITS(STA_POWER, CHANNEL_BOND); - PRINTK_BITS(STA_POWER, PHY_MODE); - PRINTK_BITS(STA_POWER, POWER_LEVEL); - PRINTK_BITS(STA_POWER, NUM_TRANSMITTERS); -} - -static inline void -agnx_print_sta_tx_wq(struct agnx_priv *priv, unsigned int sta_idx, unsigned int wq_idx) -{ - struct agnx_sta_tx_wq tx_wq; - u32 reg; - - get_sta_tx_wq(priv, &tx_wq, sta_idx, wq_idx); - - reg = le32_to_cpu(tx_wq.reg0); - PRINTK_BITS(STA_TX_WQ, TAIL_POINTER); - PRINTK_BITS(STA_TX_WQ, HEAD_POINTER_LOW); - - reg = le32_to_cpu(tx_wq.reg3); - PRINTK_BITS(STA_TX_WQ, HEAD_POINTER_HIGH); - PRINTK_BITS(STA_TX_WQ, ACK_POINTER_LOW); - - reg = le32_to_cpu(tx_wq.reg1); - PRINTK_BITS(STA_TX_WQ, ACK_POINTER_HIGH); - PRINTK_BITS(STA_TX_WQ, HEAD_TIMOUT_TAIL_PACK_CNT); - PRINTK_BITS(STA_TX_WQ, ACK_TIMOUT_TAIL_PACK_CNT); - - reg = le32_to_cpu(tx_wq.reg2); - PRINTK_BITS(STA_TX_WQ, HEAD_TIMOUT_WIN_LIM_BYTE_CNT); - PRINTK_BITS(STA_TX_WQ, HEAD_TIMOUT_WIN_LIM_FRAG_CNT); - PRINTK_BITS(STA_TX_WQ, WORK_QUEUE_ACK_TYPE); - PRINTK_BITS(STA_TX_WQ, WORK_QUEUE_VALID); -} - -static inline void agnx_print_sta_traffic(struct agnx_sta_traffic *traffic) -{ - u32 reg; - - reg = le32_to_cpu(traffic->reg0); - PRINTK_BITS(STA_TRAFFIC, ACK_TIMOUT_CNT); - PRINTK_BITS(STA_TRAFFIC, TRAFFIC_ACK_TYPE); - PRINTK_BITS(STA_TRAFFIC, NEW_PACKET); - PRINTK_BITS(STA_TRAFFIC, TRAFFIC_VALID); - PRINTK_BITS(STA_TRAFFIC, RX_HDR_DESC_POINTER); - - reg = le32_to_cpu(traffic->reg1); - PRINTK_BITS(STA_TRAFFIC, RX_PACKET_TIMESTAMP); - PRINTK_BITS(STA_TRAFFIC, TRAFFIC_RESERVED); - PRINTK_BITS(STA_TRAFFIC, SV); - PRINTK_BITS(STA_TRAFFIC, RX_SEQUENCE_NUM); - - PRINTK_LE32(STA_TRAFFIC, traffic->tx_replay_cnt_low); - - PRINTK_LE16(STA_TRAFFIC, traffic->tx_replay_cnt_high); - PRINTK_LE16(STA_TRAFFIC, traffic->rx_replay_cnt_high); - - PRINTK_LE32(STA_TRAFFIC, traffic->rx_replay_cnt_low); -} - -static inline void agnx_print_sta(struct agnx_priv *priv, unsigned int sta_idx) -{ - struct agnx_sta station; - struct agnx_sta *sta = &station; - u32 reg; - unsigned int i; - - get_sta(priv, sta, sta_idx); - - for (i = 0; i < 4; i++) - PRINTK_LE32(STA, sta->tx_session_keys[i]); - for (i = 0; i < 4; i++) - PRINTK_LE32(STA, sta->rx_session_keys[i]); - - reg = le32_to_cpu(sta->reg); - PRINTK_BITS(STA, ID_1); - PRINTK_BITS(STA, ID_0); - PRINTK_BITS(STA, ENABLE_CONCATENATION); - PRINTK_BITS(STA, ENABLE_DECOMPRESSION); - PRINTK_BITS(STA, STA_RESERVED); - PRINTK_BITS(STA, EAP); - PRINTK_BITS(STA, ED_NULL); - PRINTK_BITS(STA, ENCRYPTION_POLICY); - PRINTK_BITS(STA, DEFINED_KEY_ID); - PRINTK_BITS(STA, FIXED_KEY); - PRINTK_BITS(STA, KEY_VALID); - PRINTK_BITS(STA, STATION_VALID); - - PRINTK_LE32(STA, sta->tx_aes_blks_unicast); - PRINTK_LE32(STA, sta->rx_aes_blks_unicast); - - PRINTK_LE16(STA, sta->aes_format_err_unicast_cnt); - PRINTK_LE16(STA, sta->aes_replay_unicast); - - PRINTK_LE16(STA, sta->aes_decrypt_err_unicast); - PRINTK_LE16(STA, sta->aes_decrypt_err_default); - - PRINTK_LE16(STA, sta->single_retry_packets); - PRINTK_LE16(STA, sta->failed_tx_packets); - - PRINTK_LE16(STA, sta->muti_retry_packets); - PRINTK_LE16(STA, sta->ack_timeouts); - - PRINTK_LE16(STA, sta->frag_tx_cnt); - PRINTK_LE16(STA, sta->rts_brq_sent); - - PRINTK_LE16(STA, sta->tx_packets); - PRINTK_LE16(STA, sta->cts_back_timeout); - - PRINTK_LE32(STA, sta->phy_stats_high); - PRINTK_LE32(STA, sta->phy_stats_low); - - /* for (i = 0; i < 8; i++) */ - agnx_print_sta_traffic(sta->traffic + 0); - - PRINTK_LE16(STA, sta->traffic_class0_frag_success); - PRINTK_LE16(STA, sta->traffic_class1_frag_success); - PRINTK_LE16(STA, sta->traffic_class2_frag_success); - PRINTK_LE16(STA, sta->traffic_class3_frag_success); - PRINTK_LE16(STA, sta->traffic_class4_frag_success); - PRINTK_LE16(STA, sta->traffic_class5_frag_success); - PRINTK_LE16(STA, sta->traffic_class6_frag_success); - PRINTK_LE16(STA, sta->traffic_class7_frag_success); - - PRINTK_LE16(STA, sta->num_frag_non_prime_rates); - PRINTK_LE16(STA, sta->ack_timeout_non_prime_rates); -} - - -static inline void dump_ieee80211_hdr(struct ieee80211_hdr *hdr, char *tag) -{ - u16 fctl; - int hdrlen; - - fctl = le16_to_cpu(hdr->frame_control); - switch (fctl & IEEE80211_FCTL_FTYPE) { - case IEEE80211_FTYPE_DATA: - printk(PFX "%s DATA ", tag); - break; - case IEEE80211_FTYPE_CTL: - printk(PFX "%s CTL ", tag); - break; - case IEEE80211_FTYPE_MGMT: - printk(PFX "%s MGMT ", tag); - switch (fctl & IEEE80211_FCTL_STYPE) { - case IEEE80211_STYPE_ASSOC_REQ: - printk("SubType: ASSOC_REQ "); - break; - case IEEE80211_STYPE_ASSOC_RESP: - printk("SubType: ASSOC_RESP "); - break; - case IEEE80211_STYPE_REASSOC_REQ: - printk("SubType: REASSOC_REQ "); - break; - case IEEE80211_STYPE_REASSOC_RESP: - printk("SubType: REASSOC_RESP "); - break; - case IEEE80211_STYPE_PROBE_REQ: - printk("SubType: PROBE_REQ "); - break; - case IEEE80211_STYPE_PROBE_RESP: - printk("SubType: PROBE_RESP "); - break; - case IEEE80211_STYPE_BEACON: - printk("SubType: BEACON "); - break; - case IEEE80211_STYPE_ATIM: - printk("SubType: ATIM "); - break; - case IEEE80211_STYPE_DISASSOC: - printk("SubType: DISASSOC "); - break; - case IEEE80211_STYPE_AUTH: - printk("SubType: AUTH "); - break; - case IEEE80211_STYPE_DEAUTH: - printk("SubType: DEAUTH "); - break; - case IEEE80211_STYPE_ACTION: - printk("SubType: ACTION "); - break; - default: - printk("SubType: Unknow\n"); - } - break; - default: - printk(PFX "%s Packet type: Unknow\n", tag); - } - - hdrlen = ieee80211_hdrlen(fctl); - - if (hdrlen >= 4) - printk("FC=0x%04x DUR=0x%04x", - fctl, le16_to_cpu(hdr->duration_id)); - if (hdrlen >= 10) - printk(" A1=%pM", hdr->addr1); - if (hdrlen >= 16) - printk(" A2=%pM", hdr->addr2); - if (hdrlen >= 24) - printk(" A3=%pM", hdr->addr3); - if (hdrlen >= 30) - printk(" A4=%pM", hdr->addr4); - printk("\n"); -} - -static inline void dump_txm_registers(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - int i; - for (i = 0; i <= 0x1e8; i += 4) - printk(KERN_DEBUG PFX "TXM: %x---> 0x%.8x\n", i, ioread32(ctl + i)); -} -static inline void dump_rxm_registers(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - int i; - for (i = 0; i <= 0x108; i += 4) - printk(KERN_DEBUG PFX "RXM: %x---> 0x%.8x\n", i, ioread32(ctl + 0x2000 + i)); -} -static inline void dump_bm_registers(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - int i; - for (i = 0; i <= 0x90; i += 4) - printk(KERN_DEBUG PFX "BM: %x---> 0x%.8x\n", i, ioread32(ctl + 0x2c00 + i)); -} -static inline void dump_cir_registers(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - int i; - for (i = 0; i <= 0xb8; i += 4) - printk(KERN_DEBUG PFX "CIR: %x---> 0x%.8x\n", i, ioread32(ctl + 0x3000 + i)); -} - -#endif /* AGNX_DEBUG_H_ */ diff --git a/drivers/staging/agnx/pci.c b/drivers/staging/agnx/pci.c deleted file mode 100644 index 32b5489456a8..000000000000 --- a/drivers/staging/agnx/pci.c +++ /dev/null @@ -1,635 +0,0 @@ -/** - * Airgo MIMO wireless driver - * - * Copyright (c) 2007 Li YanBo <dreamfly281@gmail.com> - - * Thanks for Jeff Williams <angelbane@gmail.com> do reverse engineer - * works and published the SPECS at http://airgo.wdwconsulting.net/mymoin - - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. - */ - -#include <linux/init.h> -#include <linux/etherdevice.h> -#include <linux/pci.h> -#include <linux/delay.h> - -#include "agnx.h" -#include "debug.h" -#include "xmit.h" -#include "phy.h" - -MODULE_AUTHOR("Li YanBo <dreamfly281@gmail.com>"); -MODULE_DESCRIPTION("Airgo MIMO PCI wireless driver"); -MODULE_LICENSE("GPL"); - -static struct pci_device_id agnx_pci_id_tbl[] __devinitdata = { - { PCI_DEVICE(0x17cb, 0x0001) }, /* Beklin F5d8010, Netgear WGM511 etc */ - { PCI_DEVICE(0x17cb, 0x0002) }, /* Netgear Wpnt511 */ - { 0 } -}; - -MODULE_DEVICE_TABLE(pci, agnx_pci_id_tbl); - - -static inline void agnx_interrupt_ack(struct agnx_priv *priv, u32 *reason) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - if (*reason & AGNX_STAT_RX) { - /* Mark complete RX */ - reg = ioread32(ctl + AGNX_CIR_RXCTL); - reg |= 0x4; - iowrite32(reg, ctl + AGNX_CIR_RXCTL); - /* disable Rx interrupt */ - } - if (*reason & AGNX_STAT_TX) { - reg = ioread32(ctl + AGNX_CIR_TXDCTL); - if (reg & 0x4) { - iowrite32(reg, ctl + AGNX_CIR_TXDCTL); - *reason |= AGNX_STAT_TXD; - } - reg = ioread32(ctl + AGNX_CIR_TXMCTL); - if (reg & 0x4) { - iowrite32(reg, ctl + AGNX_CIR_TXMCTL); - *reason |= AGNX_STAT_TXM; - } - } -#if 0 - if (*reason & AGNX_STAT_X) { - reg = ioread32(ctl + AGNX_INT_STAT); - iowrite32(reg, ctl + AGNX_INT_STAT); - /* FIXME reinit interrupt mask */ - reg = 0xc390bf9 & ~IRQ_TX_BEACON; - reg &= ~IRQ_TX_DISABLE; - iowrite32(reg, ctl + AGNX_INT_MASK); - iowrite32(0x800, ctl + AGNX_CIR_BLKCTL); - } -#endif -} /* agnx_interrupt_ack */ - -static irqreturn_t agnx_interrupt_handler(int irq, void *dev_id) -{ - struct ieee80211_hw *dev = dev_id; - struct agnx_priv *priv = dev->priv; - void __iomem *ctl = priv->ctl; - irqreturn_t ret = IRQ_NONE; - u32 irq_reason; - - spin_lock(&priv->lock); - -/* printk(KERN_ERR PFX "Get a interrupt %s\n", __func__); */ - - if (priv->init_status != AGNX_START) - goto out; - - /* FiXME Here has no lock, Is this will lead to race? */ - irq_reason = ioread32(ctl + AGNX_CIR_BLKCTL); - if (!(irq_reason & 0x7)) - goto out; - - ret = IRQ_HANDLED; - priv->irq_status = ioread32(ctl + AGNX_INT_STAT); - -/* printk(PFX "Interrupt reason is 0x%x\n", irq_reason); */ - /* Make sure the txm and txd flags don't conflict with other unknown - interrupt flag, maybe is not necessary */ - irq_reason &= 0xF; - - disable_rx_interrupt(priv); - /* TODO Make sure the card finished initialized */ - agnx_interrupt_ack(priv, &irq_reason); - - if (irq_reason & AGNX_STAT_RX) - handle_rx_irq(priv); - if (irq_reason & AGNX_STAT_TXD) - handle_txd_irq(priv); - if (irq_reason & AGNX_STAT_TXM) - handle_txm_irq(priv); - if (irq_reason & AGNX_STAT_X) - handle_other_irq(priv); - - enable_rx_interrupt(priv); -out: - spin_unlock(&priv->lock); - return ret; -} /* agnx_interrupt_handler */ - - -/* FIXME */ -static int agnx_tx(struct ieee80211_hw *dev, struct sk_buff *skb) -{ - AGNX_TRACE; - return _agnx_tx(dev->priv, skb); -} /* agnx_tx */ - - -static int agnx_get_mac_address(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - /* Attention! directly read the MAC or other date from EEPROM will - lead to cardbus(WGM511) lock up when write to PM PLL register */ - reg = agnx_read32(ctl, 0x3544); - udelay(40); - reg = agnx_read32(ctl, 0x354c); - udelay(50); - /* Get the mac address */ - reg = agnx_read32(ctl, 0x3544); - udelay(40); - - /* HACK */ - reg = cpu_to_le32(reg); - priv->mac_addr[0] = ((u8 *)®)[2]; - priv->mac_addr[1] = ((u8 *)®)[3]; - reg = agnx_read32(ctl, 0x3548); - udelay(50); - *((u32 *)(priv->mac_addr + 2)) = cpu_to_le32(reg); - - if (!is_valid_ether_addr(priv->mac_addr)) { - printk(KERN_WARNING PFX "read mac %pM\n", priv->mac_addr); - printk(KERN_WARNING PFX "Invalid hwaddr! Using random hwaddr\n"); - random_ether_addr(priv->mac_addr); - } - - return 0; -} /* agnx_get_mac_address */ - -static int agnx_alloc_rings(struct agnx_priv *priv) -{ - unsigned int len; - AGNX_TRACE; - - /* Allocate RX/TXM/TXD rings info */ - priv->rx.size = AGNX_RX_RING_SIZE; - priv->txm.size = AGNX_TXM_RING_SIZE; - priv->txd.size = AGNX_TXD_RING_SIZE; - - len = priv->rx.size + priv->txm.size + priv->txd.size; - -/* priv->rx.info = kzalloc(sizeof(struct agnx_info) * len, GFP_KERNEL); */ - priv->rx.info = kzalloc(sizeof(struct agnx_info) * len, GFP_ATOMIC); - if (!priv->rx.info) - return -ENOMEM; - priv->txm.info = priv->rx.info + priv->rx.size; - priv->txd.info = priv->txm.info + priv->txm.size; - - /* Allocate RX/TXM/TXD descriptors */ - priv->rx.desc = pci_alloc_consistent(priv->pdev, sizeof(struct agnx_desc) * len, - &priv->rx.dma); - if (!priv->rx.desc) { - kfree(priv->rx.info); - return -ENOMEM; - } - - priv->txm.desc = priv->rx.desc + priv->rx.size; - priv->txm.dma = priv->rx.dma + sizeof(struct agnx_desc) * priv->rx.size; - priv->txd.desc = priv->txm.desc + priv->txm.size; - priv->txd.dma = priv->txm.dma + sizeof(struct agnx_desc) * priv->txm.size; - - return 0; -} /* agnx_alloc_rings */ - -static void rings_free(struct agnx_priv *priv) -{ - unsigned int len = priv->rx.size + priv->txm.size + priv->txd.size; - unsigned long flags; - AGNX_TRACE; - - spin_lock_irqsave(&priv->lock, flags); - kfree(priv->rx.info); - pci_free_consistent(priv->pdev, sizeof(struct agnx_desc) * len, - priv->rx.desc, priv->rx.dma); - spin_unlock_irqrestore(&priv->lock, flags); -} - -#if 0 -static void agnx_periodic_work_handler(struct work_struct *work) -{ - struct agnx_priv *priv = container_of(work, struct agnx_priv, periodic_work.work); -/* unsigned long flags; */ - unsigned long delay; - - /* fixme: using mutex?? */ -/* spin_lock_irqsave(&priv->lock, flags); */ - - /* TODO Recalibrate*/ -/* calibrate_oscillator(priv); */ -/* antenna_calibrate(priv); */ -/* agnx_send_packet(priv, 997); */ - /* FIXME */ -/* if (debug == 3) */ -/* delay = msecs_to_jiffies(AGNX_PERIODIC_DELAY); */ -/* else */ - delay = msecs_to_jiffies(AGNX_PERIODIC_DELAY); -/* delay = round_jiffies(HZ * 15); */ - - queue_delayed_work(priv->hw->workqueue, &priv->periodic_work, delay); - -/* spin_unlock_irqrestore(&priv->lock, flags); */ -} -#endif - -static int agnx_start(struct ieee80211_hw *dev) -{ - struct agnx_priv *priv = dev->priv; - /* unsigned long delay; */ - int err = 0; - AGNX_TRACE; - - err = agnx_alloc_rings(priv); - if (err) { - printk(KERN_ERR PFX "Can't alloc RX/TXM/TXD rings\n"); - goto out; - } - err = request_irq(priv->pdev->irq, &agnx_interrupt_handler, - IRQF_SHARED, "agnx_pci", dev); - if (err) { - printk(KERN_ERR PFX "Failed to register IRQ handler\n"); - rings_free(priv); - goto out; - } - -/* mdelay(500); */ - - might_sleep(); - agnx_hw_init(priv); - -/* mdelay(500); */ - might_sleep(); - - priv->init_status = AGNX_START; -/* INIT_DELAYED_WORK(&priv->periodic_work, agnx_periodic_work_handler); */ -/* delay = msecs_to_jiffies(AGNX_PERIODIC_DELAY); */ -/* queue_delayed_work(priv->hw->workqueue, &priv->periodic_work, delay); */ -out: - return err; -} /* agnx_start */ - -static void agnx_stop(struct ieee80211_hw *dev) -{ - struct agnx_priv *priv = dev->priv; - AGNX_TRACE; - - priv->init_status = AGNX_STOP; - /* make sure hardware will not generate irq */ - agnx_hw_reset(priv); - free_irq(priv->pdev->irq, dev); -/* flush_workqueue(priv->hw->workqueue); */ -/* cancel_delayed_work_sync(&priv->periodic_work); */ - unfill_rings(priv); - rings_free(priv); -} - -static int agnx_config(struct ieee80211_hw *dev, u32 changed) -{ - struct agnx_priv *priv = dev->priv; - struct ieee80211_conf *conf = &dev->conf; - int channel = ieee80211_frequency_to_channel(conf->channel->center_freq); - AGNX_TRACE; - - spin_lock(&priv->lock); - /* FIXME need priv lock? */ - if (channel != priv->channel) { - priv->channel = channel; - agnx_set_channel(priv, priv->channel); - } - - spin_unlock(&priv->lock); - return 0; -} - -static void agnx_bss_info_changed(struct ieee80211_hw *dev, - struct ieee80211_vif *vif, - struct ieee80211_bss_conf *conf, - u32 changed) -{ - struct agnx_priv *priv = dev->priv; - void __iomem *ctl = priv->ctl; - AGNX_TRACE; - - if (!(changed & BSS_CHANGED_BSSID)) - return; - - spin_lock(&priv->lock); - - if (memcmp(conf->bssid, priv->bssid, ETH_ALEN)) { - agnx_set_bssid(priv, conf->bssid); - memcpy(priv->bssid, conf->bssid, ETH_ALEN); - hash_write(priv, conf->bssid, BSSID_STAID); - sta_init(priv, BSSID_STAID); - /* FIXME needed? */ - sta_power_init(priv, BSSID_STAID); - agnx_write32(ctl, AGNX_BM_MTSM, 0xff & ~0x1); - } - spin_unlock(&priv->lock); -} /* agnx_bss_info_changed */ - - -static void agnx_configure_filter(struct ieee80211_hw *dev, - unsigned int changed_flags, - unsigned int *total_flags, - int mc_count, struct dev_mc_list *mclist) -{ - unsigned int new_flags = 0; - - *total_flags = new_flags; - /* TODO */ -} - -static int agnx_add_interface(struct ieee80211_hw *dev, - struct ieee80211_if_init_conf *conf) -{ - struct agnx_priv *priv = dev->priv; - AGNX_TRACE; - - spin_lock(&priv->lock); - /* FIXME */ - if (priv->mode != NL80211_IFTYPE_MONITOR) - return -EOPNOTSUPP; - - switch (conf->type) { - case NL80211_IFTYPE_STATION: - priv->mode = conf->type; - break; - default: - return -EOPNOTSUPP; - } - - spin_unlock(&priv->lock); - - return 0; -} - -static void agnx_remove_interface(struct ieee80211_hw *dev, - struct ieee80211_if_init_conf *conf) -{ - struct agnx_priv *priv = dev->priv; - AGNX_TRACE; - - /* TODO */ - priv->mode = NL80211_IFTYPE_MONITOR; -} - -static int agnx_get_stats(struct ieee80211_hw *dev, - struct ieee80211_low_level_stats *stats) -{ - struct agnx_priv *priv = dev->priv; - AGNX_TRACE; - spin_lock(&priv->lock); - /* TODO !! */ - memcpy(stats, &priv->stats, sizeof(*stats)); - spin_unlock(&priv->lock); - - return 0; -} - -static u64 agnx_get_tsft(struct ieee80211_hw *dev) -{ - void __iomem *ctl = ((struct agnx_priv *)dev->priv)->ctl; - u32 tsftl; - u64 tsft; - AGNX_TRACE; - - /* FIXME */ - tsftl = ioread32(ctl + AGNX_TXM_TIMESTAMPLO); - tsft = ioread32(ctl + AGNX_TXM_TIMESTAMPHI); - tsft <<= 32; - tsft |= tsftl; - - return tsft; -} - -static int agnx_get_tx_stats(struct ieee80211_hw *dev, - struct ieee80211_tx_queue_stats *stats) -{ - struct agnx_priv *priv = dev->priv; - AGNX_TRACE; - - /* FIXME now we just using txd queue, but should using txm queue too */ - stats[0].len = (priv->txd.idx - priv->txd.idx_sent) / 2; - stats[0].limit = priv->txd.size - 2; - stats[0].count = priv->txd.idx / 2; - - return 0; -} - -static struct ieee80211_ops agnx_ops = { - .tx = agnx_tx, - .start = agnx_start, - .stop = agnx_stop, - .add_interface = agnx_add_interface, - .remove_interface = agnx_remove_interface, - .config = agnx_config, - .bss_info_changed = agnx_bss_info_changed, - .configure_filter = agnx_configure_filter, - .get_stats = agnx_get_stats, - .get_tx_stats = agnx_get_tx_stats, - .get_tsf = agnx_get_tsft -}; - -static void __devexit agnx_pci_remove(struct pci_dev *pdev) -{ - struct ieee80211_hw *dev = pci_get_drvdata(pdev); - struct agnx_priv *priv; - AGNX_TRACE; - - if (!dev) - return; - priv = dev->priv; - ieee80211_unregister_hw(dev); - pci_iounmap(pdev, priv->ctl); - pci_iounmap(pdev, priv->data); - pci_release_regions(pdev); - pci_disable_device(pdev); - - ieee80211_free_hw(dev); -} - -static int __devinit agnx_pci_probe(struct pci_dev *pdev, - const struct pci_device_id *id) -{ - struct ieee80211_hw *dev; - struct agnx_priv *priv; - int err; - - err = pci_enable_device(pdev); - if (err) { - dev_err(&pdev->dev, "can't enable pci device\n"); - return err; - } - - err = pci_request_regions(pdev, "agnx-pci"); - if (err) { - dev_err(&pdev->dev, "can't reserve PCI resources\n"); - return err; - } - - if (pci_set_dma_mask(pdev, DMA_BIT_MASK(32)) || - pci_set_consistent_dma_mask(pdev, DMA_BIT_MASK(32))) { - dev_err(&pdev->dev, "no suitable DMA available\n"); - err = -EIO; - goto err_free_reg; - } - - pci_set_master(pdev); - - dev = ieee80211_alloc_hw(sizeof(*priv), &agnx_ops); - if (!dev) { - dev_err(&pdev->dev, "ieee80211 alloc failed\n"); - err = -ENOMEM; - goto err_free_reg; - } - priv = dev->priv; - memset(priv, 0, sizeof(*priv)); - priv->mode = NL80211_IFTYPE_MONITOR; - priv->pdev = pdev; - priv->hw = dev; - spin_lock_init(&priv->lock); - priv->init_status = AGNX_UNINIT; - - priv->ctl = pci_iomap(pdev, 0, 0); -/* dev_dbg(&pdev->dev, "MEM1 mapped address is 0x%p\n", priv->ctl); */ - if (!priv->ctl) { - dev_err(&pdev->dev, "can't map device memory\n"); - err = -ENOMEM; - goto err_free_dev; - } - priv->data = pci_iomap(pdev, 1, 0); - if (!priv->data) { - dev_err(&pdev->dev, "can't map device memory\n"); - err = -ENOMEM; - goto err_iounmap2; - } - - pci_read_config_byte(pdev, PCI_REVISION_ID, &priv->revid); - - priv->band.channels = (struct ieee80211_channel *)agnx_channels; - priv->band.n_channels = ARRAY_SIZE(agnx_channels); - priv->band.bitrates = (struct ieee80211_rate *)agnx_rates_80211g; - priv->band.n_bitrates = ARRAY_SIZE(agnx_rates_80211g); - - /* Init ieee802.11 dev */ - SET_IEEE80211_DEV(dev, &pdev->dev); - pci_set_drvdata(pdev, dev); - dev->extra_tx_headroom = sizeof(struct agnx_hdr); - - /* FIXME It only include FCS in promious mode but not manage mode */ -/* dev->flags = IEEE80211_HW_RX_INCLUDES_FCS; */ - dev->channel_change_time = 5000; - dev->max_signal = 100; - /* FIXME */ - dev->queues = 1; - - agnx_get_mac_address(priv); - - SET_IEEE80211_PERM_ADDR(dev, priv->mac_addr); - -/* /\* FIXME *\/ */ -/* for (i = 1; i < NUM_DRIVE_MODES; i++) { */ -/* err = ieee80211_register_hwmode(dev, &priv->modes[i]); */ -/* if (err) { */ -/* printk(KERN_ERR PFX "Can't register hwmode\n"); */ -/* goto err_iounmap; */ -/* } */ -/* } */ - - priv->channel = 1; - dev->wiphy->bands[IEEE80211_BAND_2GHZ] = &priv->band; - - err = ieee80211_register_hw(dev); - if (err) { - dev_err(&pdev->dev, "can't register hardware\n"); - goto err_iounmap; - } - - agnx_hw_reset(priv); - - dev_info(&pdev->dev, "%s: hwaddr %pM, Rev 0x%02x\n", - wiphy_name(dev->wiphy), - dev->wiphy->perm_addr, priv->revid); - return 0; - - err_iounmap: - pci_iounmap(pdev, priv->data); - - err_iounmap2: - pci_iounmap(pdev, priv->ctl); - - err_free_dev: - pci_set_drvdata(pdev, NULL); - ieee80211_free_hw(dev); - - err_free_reg: - pci_release_regions(pdev); - - pci_disable_device(pdev); - return err; -} /* agnx_pci_probe*/ - -#ifdef CONFIG_PM - -static int agnx_pci_suspend(struct pci_dev *pdev, pm_message_t state) -{ - struct ieee80211_hw *dev = pci_get_drvdata(pdev); - AGNX_TRACE; - - ieee80211_stop_queues(dev); - agnx_stop(dev); - - pci_save_state(pdev); - pci_set_power_state(pdev, pci_choose_state(pdev, state)); - return 0; -} - -static int agnx_pci_resume(struct pci_dev *pdev) -{ - struct ieee80211_hw *dev = pci_get_drvdata(pdev); - AGNX_TRACE; - - pci_set_power_state(pdev, PCI_D0); - pci_restore_state(pdev); - - agnx_start(dev); - ieee80211_wake_queues(dev); - - return 0; -} - -#else - -#define agnx_pci_suspend NULL -#define agnx_pci_resume NULL - -#endif /* CONFIG_PM */ - - -static struct pci_driver agnx_pci_driver = { - .name = "agnx-pci", - .id_table = agnx_pci_id_tbl, - .probe = agnx_pci_probe, - .remove = __devexit_p(agnx_pci_remove), - .suspend = agnx_pci_suspend, - .resume = agnx_pci_resume, -}; - -static int __init agnx_pci_init(void) -{ - AGNX_TRACE; - return pci_register_driver(&agnx_pci_driver); -} - -static void __exit agnx_pci_exit(void) -{ - AGNX_TRACE; - pci_unregister_driver(&agnx_pci_driver); -} - - -module_init(agnx_pci_init); -module_exit(agnx_pci_exit); diff --git a/drivers/staging/agnx/phy.c b/drivers/staging/agnx/phy.c deleted file mode 100644 index ec1ca86fa0c4..000000000000 --- a/drivers/staging/agnx/phy.c +++ /dev/null @@ -1,960 +0,0 @@ -/** - * Airgo MIMO wireless driver - * - * Copyright (c) 2007 Li YanBo <dreamfly281@gmail.com> - - * Thanks for Jeff Williams <angelbane@gmail.com> do reverse engineer - * works and published the SPECS at http://airgo.wdwconsulting.net/mymoin - - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. - */ - -#include <linux/init.h> -#include <linux/etherdevice.h> -#include <linux/pci.h> -#include <linux/delay.h> -#include "agnx.h" -#include "debug.h" -#include "phy.h" -#include "table.h" -#include "sta.h" -#include "xmit.h" - -u8 read_from_eeprom(struct agnx_priv *priv, u16 address) -{ - void __iomem *ctl = priv->ctl; - struct agnx_eeprom cmd; - u32 reg; - - memset(&cmd, 0, sizeof(cmd)); - cmd.cmd = EEPROM_CMD_READ << AGNX_EEPROM_COMMAND_SHIFT; - cmd.address = address; - /* Verify that the Status bit is clear */ - /* Read Command and Address are written to the Serial Interface */ - iowrite32(*(__le32 *)&cmd, ctl + AGNX_CIR_SERIALITF); - /* Wait for the Status bit to clear again */ - eeprom_delay(); - /* Read from Data */ - reg = ioread32(ctl + AGNX_CIR_SERIALITF); - - cmd = *(struct agnx_eeprom *)® - - return cmd.data; -} - -static int card_full_reset(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - reg = agnx_read32(ctl, AGNX_CIR_BLKCTL); - agnx_write32(ctl, AGNX_CIR_BLKCTL, 0x80); - reg = agnx_read32(ctl, AGNX_CIR_BLKCTL); - return 0; -} - -inline void enable_power_saving(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg &= ~0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); -} - -inline void disable_power_saving(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg |= 0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); -} - - -void disable_receiver(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - AGNX_TRACE; - - /* FIXME Disable the receiver */ - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x0); - /* Set gain control reset */ - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x1); - /* Reset gain control reset */ - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x0); -} - - -/* Fixme this shoule be disable RX, above is enable RX */ -void enable_receiver(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - AGNX_TRACE; - - /* Set adaptive gain control discovery mode */ - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x3); - /* Set gain control reset */ - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x1); - /* Clear gain control reset */ - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x0); -} - -static void mac_address_set(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u8 *mac_addr = priv->mac_addr; - u32 reg; - - /* FIXME */ - reg = (mac_addr[0] << 24) | (mac_addr[1] << 16) | mac_addr[2] << 8 | mac_addr[3]; - iowrite32(reg, ctl + AGNX_RXM_MACHI); - reg = (mac_addr[4] << 8) | mac_addr[5]; - iowrite32(reg, ctl + AGNX_RXM_MACLO); -} - -static void receiver_bssid_set(struct agnx_priv *priv, const u8 *bssid) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - disable_receiver(priv); - /* FIXME */ - reg = bssid[0] << 24 | (bssid[1] << 16) | (bssid[2] << 8) | bssid[3]; - iowrite32(reg, ctl + AGNX_RXM_BSSIDHI); - reg = (bssid[4] << 8) | bssid[5]; - iowrite32(reg, ctl + AGNX_RXM_BSSIDLO); - - /* Enable the receiver */ - enable_receiver(priv); - - /* Clear the TSF */ -/* agnx_write32(ctl, AGNX_TXM_TSFLO, 0x0); */ -/* agnx_write32(ctl, AGNX_TXM_TSFHI, 0x0); */ - /* Clear the TBTT */ - agnx_write32(ctl, AGNX_TXM_TBTTLO, 0x0); - agnx_write32(ctl, AGNX_TXM_TBTTHI, 0x0); - disable_receiver(priv); -} /* receiver_bssid_set */ - -static void band_management_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - void __iomem *data = priv->data; - u32 reg; - int i; - AGNX_TRACE; - - agnx_write32(ctl, AGNX_BM_TXWADDR, AGNX_PDU_TX_WQ); - agnx_write32(ctl, AGNX_CIR_ADDRWIN, 0x0); - memset_io(data + AGNX_PDUPOOL, 0x0, AGNX_PDUPOOL_SIZE); - agnx_write32(ctl, AGNX_BM_BMCTL, 0x200); - - agnx_write32(ctl, AGNX_BM_CIPDUWCNT, 0x40); - agnx_write32(ctl, AGNX_BM_SPPDUWCNT, 0x2); - agnx_write32(ctl, AGNX_BM_RFPPDUWCNT, 0x0); - agnx_write32(ctl, AGNX_BM_RHPPDUWCNT, 0x22); - - /* FIXME Initialize the Free Pool Linked List */ - /* 1. Write the Address of the Next Node ((0x41800 + node*size)/size) - to the first word of each node. */ - for (i = 0; i < PDU_FREE_CNT; i++) { - iowrite32((AGNX_PDU_FREE + (i+1)*PDU_SIZE)/PDU_SIZE, - data + AGNX_PDU_FREE + (PDU_SIZE * i)); - /* The last node should be set to 0x0 */ - if ((i + 1) == PDU_FREE_CNT) - memset_io(data + AGNX_PDU_FREE + (PDU_SIZE * i), - 0x0, PDU_SIZE); - } - - /* Head is First Pool address (0x41800) / size (0x80) */ - agnx_write32(ctl, AGNX_BM_FPLHP, AGNX_PDU_FREE/PDU_SIZE); - /* Tail is Last Pool Address (0x47f80) / size (0x80) */ - agnx_write32(ctl, AGNX_BM_FPLTP, 0x47f80/PDU_SIZE); - /* Count is Number of Nodes in the Pool (0xd0) */ - agnx_write32(ctl, AGNX_BM_FPCNT, PDU_FREE_CNT); - - /* Start all workqueue */ - agnx_write32(ctl, AGNX_BM_CIWQCTL, 0x80000); - agnx_write32(ctl, AGNX_BM_CPULWCTL, 0x80000); - agnx_write32(ctl, AGNX_BM_CPUHWCTL, 0x80000); - agnx_write32(ctl, AGNX_BM_CPUTXWCTL, 0x80000); - agnx_write32(ctl, AGNX_BM_CPURXWCTL, 0x80000); - agnx_write32(ctl, AGNX_BM_SPRXWCTL, 0x80000); - agnx_write32(ctl, AGNX_BM_SPTXWCTL, 0x80000); - agnx_write32(ctl, AGNX_BM_RFPWCTL, 0x80000); - - /* Enable the Band Management */ - reg = agnx_read32(ctl, AGNX_BM_BMCTL); - reg |= 0x1; - agnx_write32(ctl, AGNX_BM_BMCTL, reg); -} /* band_managment_init */ - - -static void system_itf_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - agnx_write32(ctl, AGNX_SYSITF_GPIOUT, 0x0); - agnx_write32(ctl, AGNX_PM_TESTPHY, 0x11e143a); - - if (priv->revid == 0) { - reg = agnx_read32(ctl, AGNX_SYSITF_SYSMODE); - reg |= 0x11; - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, reg); - } - /* ??? What is that means? it should difference for differice type - of cards */ - agnx_write32(ctl, AGNX_CIR_SERIALITF, 0xfff81006); - - agnx_write32(ctl, AGNX_SYSITF_GPIOIN, 0x1f0000); - agnx_write32(ctl, AGNX_SYSITF_GPIOUT, 0x5); - reg = agnx_read32(ctl, AGNX_SYSITF_GPIOIN); -} - -static void encryption_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - AGNX_TRACE; - - agnx_write32(ctl, AGNX_ENCRY_WEPKEY0, 0x0); - agnx_write32(ctl, AGNX_ENCRY_WEPKEY1, 0x0); - agnx_write32(ctl, AGNX_ENCRY_WEPKEY2, 0x0); - agnx_write32(ctl, AGNX_ENCRY_WEPKEY3, 0x0); - agnx_write32(ctl, AGNX_ENCRY_CCMRECTL, 0x8); -} - -static void tx_management_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - void __iomem *data = priv->data; - u32 reg; - AGNX_TRACE; - - /* Fill out the ComputationalEngineLookupTable - * starting at memory #2 offset 0x800 - */ - tx_engine_lookup_tbl_init(priv); - memset_io(data + 0x1000, 0, 0xfe0); - /* Enable Transmission Management Functions */ - agnx_write32(ctl, AGNX_TXM_ETMF, 0x3ff); - /* Write 0x3f to Transmission Template */ - agnx_write32(ctl, AGNX_TXM_TXTEMP, 0x3f); - - if (priv->revid >= 2) - agnx_write32(ctl, AGNX_TXM_SIFSPIFS, 0x1e140a0b); - else - agnx_write32(ctl, AGNX_TXM_SIFSPIFS, 0x1e190a0b); - - reg = agnx_read32(ctl, AGNX_TXM_TIFSEIFS); - reg &= 0xff00; - reg |= 0xb; - agnx_write32(ctl, AGNX_TXM_TIFSEIFS, reg); - reg = agnx_read32(ctl, AGNX_TXM_TIFSEIFS); - reg &= 0xffff00ff; - reg |= 0xa00; - agnx_write32(ctl, AGNX_TXM_TIFSEIFS, reg); - /* Enable TIFS */ - agnx_write32(ctl, AGNX_TXM_CTL, 0x40000); - - reg = agnx_read32(ctl, AGNX_TXM_TIFSEIFS); - reg &= 0xff00ffff; - reg |= 0x510000; - agnx_write32(ctl, AGNX_TXM_TIFSEIFS, reg); - reg = agnx_read32(ctl, AGNX_TXM_PROBDELAY); - reg &= 0xff00ffff; - agnx_write32(ctl, AGNX_TXM_PROBDELAY, reg); - reg = agnx_read32(ctl, AGNX_TXM_TIFSEIFS); - reg &= 0x00ffffff; - reg |= 0x1c000000; - agnx_write32(ctl, AGNX_TXM_TIFSEIFS, reg); - reg = agnx_read32(ctl, AGNX_TXM_PROBDELAY); - reg &= 0x00ffffff; - reg |= 0x01000000; - agnx_write32(ctl, AGNX_TXM_PROBDELAY, reg); - - /* # Set DIF 0-1,2-3,4-5,6-7 to defaults */ - agnx_write32(ctl, AGNX_TXM_DIF01, 0x321d321d); - agnx_write32(ctl, AGNX_TXM_DIF23, 0x321d321d); - agnx_write32(ctl, AGNX_TXM_DIF45, 0x321d321d); - agnx_write32(ctl, AGNX_TXM_DIF67, 0x321d321d); - - /* Max Ack timeout limit */ - agnx_write32(ctl, AGNX_TXM_MAXACKTIM, 0x1e19); - /* Max RX Data Timeout count, */ - reg = agnx_read32(ctl, AGNX_TXM_MAXRXTIME); - reg &= 0xffff0000; - reg |= 0xff; - agnx_write32(ctl, AGNX_TXM_MAXRXTIME, reg); - - /* CF poll RX Timeout count */ - reg = agnx_read32(ctl, AGNX_TXM_CFPOLLRXTIM); - reg &= 0xffff; - reg |= 0xff0000; - agnx_write32(ctl, AGNX_TXM_CFPOLLRXTIM, reg); - - /* Max Timeout Exceeded count, */ - reg = agnx_read32(ctl, AGNX_TXM_MAXTIMOUT); - reg &= 0xff00ffff; - reg |= 0x190000; - agnx_write32(ctl, AGNX_TXM_MAXTIMOUT, reg); - - /* CF ack timeout limit for 11b */ - reg = agnx_read32(ctl, AGNX_TXM_CFACKT11B); - reg &= 0xff00; - reg |= 0x1e; - agnx_write32(ctl, AGNX_TXM_CFACKT11B, reg); - - /* Max CF Poll Timeout Count */ - reg = agnx_read32(ctl, AGNX_TXM_CFPOLLRXTIM); - reg &= 0xffff0000; - reg |= 0x19; - agnx_write32(ctl, AGNX_TXM_CFPOLLRXTIM, reg); - /* CF Poll RX Timeout Count */ - reg = agnx_read32(ctl, AGNX_TXM_CFPOLLRXTIM); - reg &= 0xffff0000; - reg |= 0x1e; - agnx_write32(ctl, AGNX_TXM_CFPOLLRXTIM, reg); - - /* # write default to */ - /* 1. Schedule Empty Count */ - agnx_write32(ctl, AGNX_TXM_SCHEMPCNT, 0x5); - /* 2. CFP Period Count */ - agnx_write32(ctl, AGNX_TXM_CFPERCNT, 0x1); - /* 3. CFP MDV */ - agnx_write32(ctl, AGNX_TXM_CFPMDV, 0x10000); - - /* Probe Delay */ - reg = agnx_read32(ctl, AGNX_TXM_PROBDELAY); - reg &= 0xffff0000; - reg |= 0x400; - agnx_write32(ctl, AGNX_TXM_PROBDELAY, reg); - - /* Max CCA count Slot */ - reg = agnx_read32(ctl, AGNX_TXM_MAXCCACNTSLOT); - reg &= 0xffff00ff; - reg |= 0x900; - agnx_write32(ctl, AGNX_TXM_MAXCCACNTSLOT, reg); - - /* Slot limit/1 msec Limit */ - reg = agnx_read32(ctl, AGNX_TXM_SLOTLIMIT); - reg &= 0xff00ffff; - reg |= 0x140077; - agnx_write32(ctl, AGNX_TXM_SLOTLIMIT, reg); - - /* # Set CW #(0-7) to default */ - agnx_write32(ctl, AGNX_TXM_CW0, 0xff0007); - agnx_write32(ctl, AGNX_TXM_CW1, 0xff0007); - agnx_write32(ctl, AGNX_TXM_CW2, 0xff0007); - agnx_write32(ctl, AGNX_TXM_CW3, 0xff0007); - agnx_write32(ctl, AGNX_TXM_CW4, 0xff0007); - agnx_write32(ctl, AGNX_TXM_CW5, 0xff0007); - agnx_write32(ctl, AGNX_TXM_CW6, 0xff0007); - agnx_write32(ctl, AGNX_TXM_CW7, 0xff0007); - - /* # Set Short/Long limit #(0-7) to default */ - agnx_write32(ctl, AGNX_TXM_SLBEALIM0, 0xa000a); - agnx_write32(ctl, AGNX_TXM_SLBEALIM1, 0xa000a); - agnx_write32(ctl, AGNX_TXM_SLBEALIM2, 0xa000a); - agnx_write32(ctl, AGNX_TXM_SLBEALIM3, 0xa000a); - agnx_write32(ctl, AGNX_TXM_SLBEALIM4, 0xa000a); - agnx_write32(ctl, AGNX_TXM_SLBEALIM5, 0xa000a); - agnx_write32(ctl, AGNX_TXM_SLBEALIM6, 0xa000a); - agnx_write32(ctl, AGNX_TXM_SLBEALIM7, 0xa000a); - - reg = agnx_read32(ctl, AGNX_TXM_CTL); - reg |= 0x1400; - agnx_write32(ctl, AGNX_TXM_CTL, reg); - /* Wait for bit 0 in Control Reg to clear */ - udelay(80); - reg = agnx_read32(ctl, AGNX_TXM_CTL); - /* Or 0x18000 to Control reg */ - reg = agnx_read32(ctl, AGNX_TXM_CTL); - reg |= 0x18000; - agnx_write32(ctl, AGNX_TXM_CTL, reg); - /* Wait for bit 0 in Control Reg to clear */ - udelay(80); - reg = agnx_read32(ctl, AGNX_TXM_CTL); - - /* Set Listen Interval Count to default */ - agnx_write32(ctl, AGNX_TXM_LISINTERCNT, 0x1); - /* Set DTIM period count to default */ - agnx_write32(ctl, AGNX_TXM_DTIMPERICNT, 0x2000); -} /* tx_management_init */ - -static void rx_management_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - AGNX_TRACE; - - /* Initialize the Routing Table */ - routing_table_init(priv); - - if (priv->revid >= 3) { - agnx_write32(ctl, 0x2074, 0x1f171710); - agnx_write32(ctl, 0x2078, 0x10100d0d); - agnx_write32(ctl, 0x207c, 0x11111010); - } else { - agnx_write32(ctl, AGNX_RXM_DELAY11, 0x0); - } - agnx_write32(ctl, AGNX_RXM_REQRATE, 0x8195e00); -} - - -static void agnx_timer_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - AGNX_TRACE; - -/* /\* Write 0x249f00 (tick duration?) to Timer 1 *\/ */ -/* agnx_write32(ctl, AGNX_TIMCTL_TIMER1, 0x249f00); */ -/* /\* Write 0xe2 to Timer 1 Control *\/ */ -/* agnx_write32(ctl, AGNX_TIMCTL_TIM1CTL, 0xe2); */ - - /* Write 0x249f00 (tick duration?) to Timer 1 */ - agnx_write32(ctl, AGNX_TIMCTL_TIMER1, 0x0); - /* Write 0xe2 to Timer 1 Control */ - agnx_write32(ctl, AGNX_TIMCTL_TIM1CTL, 0x0); - - iowrite32(0xFFFFFFFF, priv->ctl + AGNX_TXM_BEACON_CTL); -} - -static void power_manage_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - agnx_write32(ctl, AGNX_PM_MACMSW, 0x1f); - agnx_write32(ctl, AGNX_PM_RFCTL, 0x1f); - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg &= 0xf00f; - reg |= 0xa0; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); - - if (priv->revid >= 3) { - reg = agnx_read32(ctl, AGNX_PM_SOFTRST); - reg |= 0x18; - agnx_write32(ctl, AGNX_PM_SOFTRST, reg); - } -} /* power_manage_init */ - - -static void gain_ctlcnt_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - agnx_write32(ctl, AGNX_GCR_TRACNT5, 0x119); - agnx_write32(ctl, AGNX_GCR_TRACNT6, 0x118); - agnx_write32(ctl, AGNX_GCR_TRACNT7, 0x117); - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg |= 0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg &= ~0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); - - agnx_write32(ctl, AGNX_CIR_ADDRWIN, 0x0); - - /* FIXME Write the initial Station Descriptor for the card */ - sta_init(priv, LOCAL_STAID); - sta_init(priv, BSSID_STAID); - - /* Enable staion 0 and 1 can do TX */ - /* It seemed if we set other bit to 1 the bit 0 will - be auto change to 0 */ - agnx_write32(ctl, AGNX_BM_TXTOPEER, 0x2 | 0x1); -/* agnx_write32(ctl, AGNX_BM_TXTOPEER, 0x1); */ -} /* gain_ctlcnt_init */ - - -static void phy_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - void __iomem *data = priv->data; - u32 reg; - AGNX_TRACE; - - /* Load InitialGainTable */ - gain_table_init(priv); - - agnx_write32(ctl, AGNX_CIR_ADDRWIN, 0x2000000); - - /* Clear the following offsets in Memory Range #2: */ - memset_io(data + 0x5040, 0, 0xa * 4); - memset_io(data + 0x5080, 0, 0xa * 4); - memset_io(data + 0x50c0, 0, 0xa * 4); - memset_io(data + 0x5400, 0, 0x80 * 4); - memset_io(data + 0x6000, 0, 0x280 * 4); - memset_io(data + 0x7000, 0, 0x280 * 4); - memset_io(data + 0x8000, 0, 0x280 * 4); - - /* Initialize the Following Registers According to PCI Revision ID */ - if (priv->revid == 0) { - /* fixme the part hasn't been update but below has been update - based on WGM511 */ - agnx_write32(ctl, AGNX_ACI_LEN, 0xf); - agnx_write32(ctl, AGNX_ACI_TIMER1, 0x1d); - agnx_write32(ctl, AGNX_ACI_TIMER2, 0x3); - agnx_write32(ctl, AGNX_ACI_AICCHA0OVE, 0x11); - agnx_write32(ctl, AGNX_ACI_AICCHA1OVE, 0x0); - agnx_write32(ctl, AGNX_GCR_THD0A, 0x64); - agnx_write32(ctl, AGNX_GCR_THD0AL, 0x4b); - agnx_write32(ctl, AGNX_GCR_THD0B, 0x4b); - agnx_write32(ctl, AGNX_GCR_DUNSAT, 0x14); - agnx_write32(ctl, AGNX_GCR_DSAT, 0x24); - agnx_write32(ctl, AGNX_GCR_DFIRCAL, 0x8); - agnx_write32(ctl, AGNX_GCR_DGCTL11A, 0x1a); - agnx_write32(ctl, AGNX_GCR_DGCTL11B, 0x3); - agnx_write32(ctl, AGNX_GCR_GAININIT, 0xd); - agnx_write32(ctl, AGNX_GCR_THNOSIG, 0x1); - agnx_write32(ctl, AGNX_GCR_COARSTEP, 0x7); - agnx_write32(ctl, AGNX_GCR_SIFST11A, 0x28); - agnx_write32(ctl, AGNX_GCR_SIFST11B, 0x28); - reg = agnx_read32(ctl, AGNX_GCR_CWDETEC); - reg |= 0x1; - agnx_write32(ctl, AGNX_GCR_CWDETEC, reg); - agnx_write32(ctl, AGNX_GCR_0X38, 0x1e); - agnx_write32(ctl, AGNX_GCR_BOACT, 0x26); - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x3); - agnx_write32(ctl, AGNX_GCR_NLISTANT, 0x3); - agnx_write32(ctl, AGNX_GCR_NACTIANT, 0x3); - agnx_write32(ctl, AGNX_GCR_NMEASANT, 0x3); - agnx_write32(ctl, AGNX_GCR_NCAPTANT, 0x3); - agnx_write32(ctl, AGNX_GCR_THCAP11A, 0x0); - agnx_write32(ctl, AGNX_GCR_THCAP11B, 0x0); - agnx_write32(ctl, AGNX_GCR_THCAPRX11A, 0x0); - agnx_write32(ctl, AGNX_GCR_THCAPRX11B, 0x0); - agnx_write32(ctl, AGNX_GCR_THLEVDRO, 0x10); - agnx_write32(ctl, AGNX_GCR_MAXRXTIME11A, 0x1); - agnx_write32(ctl, AGNX_GCR_MAXRXTIME11B, 0x1); - agnx_write32(ctl, AGNX_GCR_CORRTIME, 0x190); - agnx_write32(ctl, AGNX_GCR_SIGHTH, 0x78); - agnx_write32(ctl, AGNX_GCR_SIGLTH, 0x1c); - agnx_write32(ctl, AGNX_GCR_CORRDROP, 0x0); - agnx_write32(ctl, AGNX_GCR_THCD, 0x0); - agnx_write32(ctl, AGNX_GCR_MAXPOWDIFF, 0x1); - agnx_write32(ctl, AGNX_GCR_TESTBUS, 0x0); - agnx_write32(ctl, AGNX_GCR_ANTCFG, 0x1f); - agnx_write32(ctl, AGNX_GCR_THJUMP, 0x14); - agnx_write32(ctl, AGNX_GCR_THPOWER, 0x0); - agnx_write32(ctl, AGNX_GCR_THPOWCLIP, 0x30); - agnx_write32(ctl, AGNX_GCR_THD0BTFEST, 0x32); - agnx_write32(ctl, AGNX_GCR_THRX11BPOWMIN, 0x19); - agnx_write32(ctl, AGNX_GCR_0X14c, 0x0); - agnx_write32(ctl, AGNX_GCR_0X150, 0x0); - agnx_write32(ctl, 0x9400, 0x0); - agnx_write32(ctl, 0x940c, 0x6ff); - agnx_write32(ctl, 0x9428, 0xa0); - agnx_write32(ctl, 0x9434, 0x0); - agnx_write32(ctl, 0x9c04, 0x15); - agnx_write32(ctl, 0x9c0c, 0x7f); - agnx_write32(ctl, 0x9c34, 0x0); - agnx_write32(ctl, 0xc000, 0x38d); - agnx_write32(ctl, 0x14018, 0x0); - agnx_write32(ctl, 0x16000, 0x1); - agnx_write32(ctl, 0x11004, 0x0); - agnx_write32(ctl, 0xec54, 0xa); - agnx_write32(ctl, 0xec1c, 0x5); - } else if (priv->revid > 0) { - agnx_write32(ctl, AGNX_ACI_LEN, 0xf); - agnx_write32(ctl, AGNX_ACI_TIMER1, 0x21); - agnx_write32(ctl, AGNX_ACI_TIMER2, 0x27); - agnx_write32(ctl, AGNX_ACI_AICCHA0OVE, 0x11); - agnx_write32(ctl, AGNX_ACI_AICCHA1OVE, 0x0); - agnx_write32(ctl, AGNX_GCR_DUNSAT, 0x14); - agnx_write32(ctl, AGNX_GCR_DSAT, 0x24); - agnx_write32(ctl, AGNX_GCR_DFIRCAL, 0x8); - agnx_write32(ctl, AGNX_GCR_DGCTL11A, 0x1a); - agnx_write32(ctl, AGNX_GCR_DGCTL11B, 0x3); - agnx_write32(ctl, AGNX_GCR_GAININIT, 0xd); - agnx_write32(ctl, AGNX_GCR_THNOSIG, 0x1); - agnx_write32(ctl, AGNX_GCR_COARSTEP, 0x7); - agnx_write32(ctl, AGNX_GCR_SIFST11A, 0x28); - agnx_write32(ctl, AGNX_GCR_SIFST11B, 0x28); - agnx_write32(ctl, AGNX_GCR_CWDETEC, 0x0); - agnx_write32(ctl, AGNX_GCR_0X38, 0x1e); -/* agnx_write32(ctl, AGNX_GCR_BOACT, 0x26);*/ - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x3); - - agnx_write32(ctl, AGNX_GCR_THCAP11A, 0x32); - agnx_write32(ctl, AGNX_GCR_THCAP11B, 0x32); - agnx_write32(ctl, AGNX_GCR_THCAPRX11A, 0x32); - agnx_write32(ctl, AGNX_GCR_THCAPRX11B, 0x32); - agnx_write32(ctl, AGNX_GCR_THLEVDRO, 0x10); - agnx_write32(ctl, AGNX_GCR_MAXRXTIME11A, 0x1ad); - agnx_write32(ctl, AGNX_GCR_MAXRXTIME11B, 0xa10); - agnx_write32(ctl, AGNX_GCR_CORRTIME, 0x190); - agnx_write32(ctl, AGNX_GCR_CORRDROP, 0x0); - agnx_write32(ctl, AGNX_GCR_THCD, 0x0); - agnx_write32(ctl, AGNX_GCR_THCS, 0x0); - agnx_write32(ctl, AGNX_GCR_MAXPOWDIFF, 0x4); - agnx_write32(ctl, AGNX_GCR_TESTBUS, 0x0); - agnx_write32(ctl, AGNX_GCR_THJUMP, 0x1e); - agnx_write32(ctl, AGNX_GCR_THPOWER, 0x0); - agnx_write32(ctl, AGNX_GCR_THPOWCLIP, 0x2a); - agnx_write32(ctl, AGNX_GCR_THD0BTFEST, 0x3c); - agnx_write32(ctl, AGNX_GCR_THRX11BPOWMIN, 0x19); - agnx_write32(ctl, AGNX_GCR_0X14c, 0x0); - agnx_write32(ctl, AGNX_GCR_0X150, 0x0); - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x0); - agnx_write32(ctl, AGNX_GCR_WATCHDOG, 0x37); - agnx_write32(ctl, 0x9400, 0x0); - agnx_write32(ctl, 0x940c, 0x6ff); - agnx_write32(ctl, 0x9428, 0xa0); - agnx_write32(ctl, 0x9434, 0x0); - agnx_write32(ctl, 0x9c04, 0x15); - agnx_write32(ctl, 0x9c0c, 0x7f); - agnx_write32(ctl, 0x9c34, 0x0); - agnx_write32(ctl, 0xc000, 0x38d); - agnx_write32(ctl, 0x14014, 0x1000); - agnx_write32(ctl, 0x14018, 0x0); - agnx_write32(ctl, 0x16000, 0x1); - agnx_write32(ctl, 0x11004, 0x0); - agnx_write32(ctl, 0xec54, 0xa); - agnx_write32(ctl, 0xec1c, 0x50); - } else if (priv->revid > 1) { - reg = agnx_read32(ctl, 0xec18); - reg |= 0x8; - agnx_write32(ctl, 0xec18, reg); - } - - /* Write the TX Fir Coefficient Table */ - tx_fir_table_init(priv); - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg &= ~0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); - reg = agnx_read32(ctl, AGNX_PM_PLLCTL); - reg |= 0x1; - agnx_write32(ctl, AGNX_PM_PLLCTL, reg); - -/* reg = agnx_read32(ctl, 0x1a030); */ -/* reg &= ~0x4; */ -/* agnx_write32(ctl, 0x1a030, reg); */ - - agnx_write32(ctl, AGNX_GCR_TRACNT4, 0x113); -} /* phy_init */ - -static void chip_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - band_management_init(priv); - - rf_chips_init(priv); - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg |= 0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); - - /* Initialize the PHY */ - phy_init(priv); - - encryption_init(priv); - - tx_management_init(priv); - - rx_management_init(priv); - - power_manage_init(priv); - - /* Initialize the Timers */ - agnx_timer_init(priv); - - /* Write 0xc390bf9 to Interrupt Mask (Disable TX) */ - reg = 0xc390bf9 & ~IRQ_TX_BEACON; - reg &= ~IRQ_TX_DISABLE; - agnx_write32(ctl, AGNX_INT_MASK, reg); - - reg = agnx_read32(ctl, AGNX_CIR_BLKCTL); - reg |= 0x800; - agnx_write32(ctl, AGNX_CIR_BLKCTL, reg); - - /* set it when need get multicast enable? */ - agnx_write32(ctl, AGNX_BM_MTSM, 0xff); -} /* chip_init */ - - -static inline void set_promis_and_managed(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x10 | 0x2); - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x10 | 0x2); -} -static inline void set_learn_mode(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x8); -} -static inline void set_scan_mode(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x20); -} -static inline void set_promiscuous_mode(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - /* agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x210);*/ - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x10); -} -static inline void set_managed_mode(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x2); -} -static inline void set_adhoc_mode(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, 0x0); -} - -#if 0 -static void unknow_register_write(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x0, 0x3e); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x4, 0xb2); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x8, 0x140); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0xc, 0x1C0); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x10, 0x1FF); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x14, 0x1DD); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x18, 0x15F); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x1c, 0xA1); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x20, 0x3E7); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x24, 0x36B); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x28, 0x348); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x2c, 0x37D); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x30, 0x3DE); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x34, 0x36); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x38, 0x64); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x3c, 0x57); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x40, 0x23); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x44, 0x3ED); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x48, 0x3C9); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x4c, 0x3CA); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x50, 0x3E7); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x54, 0x8); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x58, 0x1F); - agnx_write32(ctl, AGNX_UNKNOWN_BASE + 0x5c, 0x1a); -} -#endif - -static void card_interface_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u8 bssid[ETH_ALEN] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff}; - u32 reg; - unsigned int i; - AGNX_TRACE; - - might_sleep(); - /* Clear RX Control and Enable RX queues */ - agnx_write32(ctl, AGNX_CIR_RXCTL, 0x8); - - might_sleep(); - /* Do a full reset of the card */ - card_full_reset(priv); - might_sleep(); - - /* Check and set Card Endianness */ - reg = ioread32(priv->ctl + AGNX_CIR_ENDIAN); - /* TODO If not 0xB3B2B1B0 set to 0xB3B2B1B0 */ - printk(KERN_INFO PFX "CIR_ENDIAN is %x\n", reg); - - - /* Config the eeprom */ - agnx_write32(ctl, AGNX_CIR_SERIALITF, 0x7000086); - udelay(10); - reg = agnx_read32(ctl, AGNX_CIR_SERIALITF); - - - agnx_write32(ctl, AGNX_PM_SOFTRST, 0x80000033); - reg = agnx_read32(ctl, 0xec50); - reg |= 0xf; - agnx_write32(ctl, 0xec50, reg); - agnx_write32(ctl, AGNX_PM_SOFTRST, 0x0); - - - reg = agnx_read32(ctl, AGNX_SYSITF_GPIOIN); - udelay(10); - reg = agnx_read32(ctl, AGNX_CIR_SERIALITF); - - /* Dump the eeprom */ - do { - char eeprom[0x100000/0x100]; - - for (i = 0; i < 0x100000; i += 0x100) { - agnx_write32(ctl, AGNX_CIR_SERIALITF, 0x3000000 + i); - udelay(13); - reg = agnx_read32(ctl, AGNX_CIR_SERIALITF); - udelay(70); - reg = agnx_read32(ctl, AGNX_CIR_SERIALITF); - eeprom[i/0x100] = reg & 0xFF; - udelay(10); - } - print_hex_dump_bytes(PFX "EEPROM: ", DUMP_PREFIX_NONE, eeprom, - ARRAY_SIZE(eeprom)); - } while (0); - - spi_rc_write(ctl, RF_CHIP0, 0x26); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - - /* Initialize the system interface */ - system_itf_init(priv); - - might_sleep(); - /* Chip Initialization (Polaris) */ - chip_init(priv); - might_sleep(); - - /* Calibrate the antennae */ - antenna_calibrate(priv); - - reg = agnx_read32(ctl, 0xec50); - reg &= ~0x40; - agnx_write32(ctl, 0xec50, reg); - agnx_write32(ctl, AGNX_PM_SOFTRST, 0x0); - agnx_write32(ctl, AGNX_PM_PLLCTL, 0x1); - - reg = agnx_read32(ctl, AGNX_BM_BMCTL); - reg |= 0x8000; - agnx_write32(ctl, AGNX_BM_BMCTL, reg); - enable_receiver(priv); - reg = agnx_read32(ctl, AGNX_SYSITF_SYSMODE); - reg |= 0x200; - agnx_write32(ctl, AGNX_SYSITF_SYSMODE, reg); - enable_receiver(priv); - - might_sleep(); - /* Initialize Gain Control Counts */ - gain_ctlcnt_init(priv); - - /* Write Initial Station Power Template for this station(#0) */ - sta_power_init(priv, LOCAL_STAID); - - might_sleep(); - /* Initialize the rx,td,tm rings, for each node in the ring */ - fill_rings(priv); - - might_sleep(); - - - agnx_write32(ctl, AGNX_PM_SOFTRST, 0x80000033); - agnx_write32(ctl, 0xec50, 0xc); - agnx_write32(ctl, AGNX_PM_SOFTRST, 0x0); - - /* FIXME Initialize the transmit control register */ - agnx_write32(ctl, AGNX_TXM_CTL, 0x194c1); - - enable_receiver(priv); - - might_sleep(); - /* FIXME Set the Receive Control Mac Address to card address */ - mac_address_set(priv); - enable_receiver(priv); - might_sleep(); - - /* Set the recieve request rate */ - /* FIXME Enable the request */ - /* Check packet length */ - /* Set maximum packet length */ -/* agnx_write32(ctl, AGNX_RXM_REQRATE, 0x88195e00); */ -/* enable_receiver(priv); */ - - /* Set the Receiver BSSID */ - receiver_bssid_set(priv, bssid); - - /* FIXME Set to managed mode */ - set_managed_mode(priv); -/* set_promiscuous_mode(priv); */ -/* set_scan_mode(priv); */ -/* set_learn_mode(priv); */ -/* set_promis_and_managed(priv); */ -/* set_adhoc_mode(priv); */ - - /* Set the recieve request rate */ - /* Check packet length */ - agnx_write32(ctl, AGNX_RXM_REQRATE, 0x08000000); - reg = agnx_read32(ctl, AGNX_RXM_REQRATE); - /* Set maximum packet length */ - reg |= 0x00195e00; - agnx_write32(ctl, AGNX_RXM_REQRATE, reg); - - /* Configure the RX and TX interrupt */ - reg = ENABLE_RX_INTERRUPT | RX_CACHE_LINE | FRAG_LEN_2048 | FRAG_BE; - agnx_write32(ctl, AGNX_CIR_RXCFG, reg); - /* FIXME */ - reg = ENABLE_TX_INTERRUPT | TX_CACHE_LINE | FRAG_LEN_2048 | FRAG_BE; - agnx_write32(ctl, AGNX_CIR_TXCFG, reg); - - /* Enable RX TX Interrupts */ - agnx_write32(ctl, AGNX_CIR_RXCTL, 0x80); - agnx_write32(ctl, AGNX_CIR_TXMCTL, 0x80); - agnx_write32(ctl, AGNX_CIR_TXDCTL, 0x80); - - /* FIXME Set the master control interrupt in block control */ - agnx_write32(ctl, AGNX_CIR_BLKCTL, 0x800); - - /* Enable RX and TX queues */ - reg = agnx_read32(ctl, AGNX_CIR_RXCTL); - reg |= 0x8; - agnx_write32(ctl, AGNX_CIR_RXCTL, reg); - reg = agnx_read32(ctl, AGNX_CIR_TXMCTL); - reg |= 0x8; - agnx_write32(ctl, AGNX_CIR_TXMCTL, reg); - reg = agnx_read32(ctl, AGNX_CIR_TXDCTL); - reg |= 0x8; - agnx_write32(ctl, AGNX_CIR_TXDCTL, reg); - - agnx_write32(ctl, AGNX_SYSITF_GPIOUT, 0x5); - /* FIXME */ - /* unknow_register_write(priv); */ - /* Update local card hash entry */ - hash_write(priv, priv->mac_addr, LOCAL_STAID); - - might_sleep(); - - /* FIXME */ - agnx_set_channel(priv, 1); - might_sleep(); -} /* agnx_card_interface_init */ - - -void agnx_hw_init(struct agnx_priv *priv) -{ - AGNX_TRACE; - might_sleep(); - card_interface_init(priv); -} - -int agnx_hw_reset(struct agnx_priv *priv) -{ - return card_full_reset(priv); -} - -int agnx_set_ssid(struct agnx_priv *priv, u8 *ssid, size_t ssid_len) -{ - AGNX_TRACE; - return 0; -} - -void agnx_set_bssid(struct agnx_priv *priv, const u8 *bssid) -{ - receiver_bssid_set(priv, bssid); -} diff --git a/drivers/staging/agnx/phy.h b/drivers/staging/agnx/phy.h deleted file mode 100644 index a955f05361e7..000000000000 --- a/drivers/staging/agnx/phy.h +++ /dev/null @@ -1,409 +0,0 @@ -#ifndef AGNX_PHY_H_ -#define AGNX_PHY_H_ - -#include "agnx.h" - -/* Transmission Managment Registers */ -#define AGNX_TXM_BASE 0x0000 -#define AGNX_TXM_CTL 0x0000 /* control register */ -#define AGNX_TXM_ETMF 0x0004 /* enable transmission management functions */ -#define AGNX_TXM_TXTEMP 0x0008 /* transmission template */ -#define AGNX_TXM_RETRYSTAID 0x000c /* Retry Station ID */ -#define AGNX_TXM_TIMESTAMPLO 0x0010 /* Timestamp Lo */ -#define AGNX_TXM_TIMESTAMPHI 0x0014 /* Timestamp Hi */ -#define AGNX_TXM_TXDELAY 0x0018 /* tx delay */ -#define AGNX_TXM_TBTTLO 0x0020 /* tbtt Lo */ -#define AGNX_TXM_TBTTHI 0x0024 /* tbtt Hi */ -#define AGNX_TXM_BEAINTER 0x0028 /* Beacon Interval */ -#define AGNX_TXM_NAV 0x0030 /* NAV */ -#define AGNX_TXM_CFPMDV 0x0034 /* CFP MDV */ -#define AGNX_TXM_CFPERCNT 0x0038 /* CFP period count */ -#define AGNX_TXM_PROBDELAY 0x003c /* probe delay */ -#define AGNX_TXM_LISINTERCNT 0x0040 /* listen interval count */ -#define AGNX_TXM_DTIMPERICNT 0x004c /* DTIM period count */ - -#define AGNX_TXM_BEACON_CTL 0x005c /* beacon control */ - -#define AGNX_TXM_SCHEMPCNT 0x007c /* schedule empty count */ -#define AGNX_TXM_MAXTIMOUT 0x0084 /* max timeout exceed count */ -#define AGNX_TXM_MAXCFPTIM 0x0088 /* max CF poll timeout count */ -#define AGNX_TXM_MAXRXTIME 0x008c /* max RX timeout count */ -#define AGNX_TXM_MAXACKTIM 0x0090 /* max ACK timeout count */ -#define AGNX_TXM_DIF01 0x00a0 /* DIF 0-1 */ -#define AGNX_TXM_DIF23 0x00a4 /* DIF 2-3 */ -#define AGNX_TXM_DIF45 0x00a8 /* DIF 4-5 */ -#define AGNX_TXM_DIF67 0x00ac /* DIF 6-7 */ -#define AGNX_TXM_SIFSPIFS 0x00b0 /* SIFS/PIFS */ -#define AGNX_TXM_TIFSEIFS 0x00b4 /* TIFS/EIFS */ -#define AGNX_TXM_MAXCCACNTSLOT 0x00b8 /* max CCA count slot */ -#define AGNX_TXM_SLOTLIMIT 0x00bc /* slot limit/1 msec limit */ -#define AGNX_TXM_CFPOLLRXTIM 0x00f0 /* CF poll RX timeout count */ -#define AGNX_TXM_CFACKT11B 0x00f4 /* CF ack timeout limit for 11b */ -#define AGNX_TXM_CW0 0x0100 /* CW 0 */ -#define AGNX_TXM_SLBEALIM0 0x0108 /* short/long beacon limit 0 */ -#define AGNX_TXM_CW1 0x0120 /* CW 1 */ -#define AGNX_TXM_SLBEALIM1 0x0128 /* short/long beacon limit 1 */ -#define AGNX_TXM_CW2 0x0140 /* CW 2 */ -#define AGNX_TXM_SLBEALIM2 0x0148 /* short/long beacon limit 2 */ -#define AGNX_TXM_CW3 0x0160 /* CW 3 */ -#define AGNX_TXM_SLBEALIM3 0x0168 /* short/long beacon limit 3 */ -#define AGNX_TXM_CW4 0x0180 /* CW 4 */ -#define AGNX_TXM_SLBEALIM4 0x0188 /* short/long beacon limit 4 */ -#define AGNX_TXM_CW5 0x01a0 /* CW 5 */ -#define AGNX_TXM_SLBEALIM5 0x01a8 /* short/long beacon limit 5 */ -#define AGNX_TXM_CW6 0x01c0 /* CW 6 */ -#define AGNX_TXM_SLBEALIM6 0x01c8 /* short/long beacon limit 6 */ -#define AGNX_TXM_CW7 0x01e0 /* CW 7 */ -#define AGNX_TXM_SLBEALIM7 0x01e8 /* short/long beacon limit 7 */ -#define AGNX_TXM_BEACONTEMP 0x1000 /* beacon template */ -#define AGNX_TXM_STAPOWTEMP 0x1a00 /* Station Power Template */ - -/* Receive Management Control Registers */ -#define AGNX_RXM_BASE 0x2000 -#define AGNX_RXM_REQRATE 0x2000 /* requested rate */ -#define AGNX_RXM_MACHI 0x2004 /* first 4 bytes of mac address */ -#define AGNX_RXM_MACLO 0x2008 /* last 2 bytes of mac address */ -#define AGNX_RXM_BSSIDHI 0x200c /* bssid hi */ -#define AGNX_RXM_BSSIDLO 0x2010 /* bssid lo */ -#define AGNX_RXM_HASH_CMD_FLAG 0x2014 /* Flags for the RX Hash Command Default:0 */ -#define AGNX_RXM_HASH_CMD_HIGH 0x2018 /* The High half of the Hash Command */ -#define AGNX_RXM_HASH_CMD_LOW 0x201c /* The Low half of the Hash Command */ -#define AGNX_RXM_ROUTAB 0x2020 /* routing table */ -#define ROUTAB_SUBTYPE_SHIFT 24 -#define ROUTAB_TYPE_SHIFT 28 -#define ROUTAB_STATUS_SHIFT 30 -#define ROUTAB_RW_SHIFT 31 -#define ROUTAB_ROUTE_DROP 0xf00000 /* Drop */ -#define ROUTAB_ROUTE_CPU 0x400000 /* CPU */ -#define ROUTAB_ROUTE_ENCRY 0x500800 /* Encryption */ -#define ROUTAB_ROUTE_RFP 0x800000 /* RFP */ - -#define ROUTAB_TYPE_MANAG 0x0 /* Management */ -#define ROUTAB_TYPE_CTL 0x1 /* Control */ -#define ROUTAB_TYPE_DATA 0x2 /* Data */ - -#define ROUTAB_SUBTYPE_DATA 0x0 -#define ROUTAB_SUBTYPE_DATAACK 0x1 -#define ROUTAB_SUBTYPE_DATAPOLL 0x2 -#define ROUTAB_SUBTYPE_DATAPOLLACK 0x3 -#define ROUTAB_SUBTYPE_NULL 0x4 /* NULL */ -#define ROUTAB_SUBTYPE_NULLACK 0x5 -#define ROUTAB_SUBTYPE_NULLPOLL 0x6 -#define ROUTAB_SUBTYPE_NULLPOLLACK 0x7 -#define ROUTAB_SUBTYPE_QOSDATA 0x8 /* QOS DATA */ -#define ROUTAB_SUBTYPE_QOSDATAACK 0x9 -#define ROUTAB_SUBTYPE_QOSDATAPOLL 0xa -#define ROUTAB_SUBTYPE_QOSDATAACKPOLL 0xb -#define ROUTAB_SUBTYPE_QOSNULL 0xc -#define ROUTAB_SUBTYPE_QOSNULLACK 0xd -#define ROUTAB_SUBTYPE_QOSNULLPOLL 0xe -#define ROUTAB_SUBTYPE_QOSNULLPOLLACK 0xf -#define AGNX_RXM_DELAY11 0x2024 /* delay 11(AB) */ -#define AGNX_RXM_SOF_CNT 0x2028 /* SOF Count */ -#define AGNX_RXM_FRAG_CNT 0x202c /* Fragment Count*/ -#define AGNX_RXM_FCS_CNT 0x2030 /* FCS Count */ -#define AGNX_RXM_BSSID_MISS_CNT 0x2034 /* BSSID Miss Count */ -#define AGNX_RXM_PDU_ERR_CNT 0x2038 /* PDU Error Count */ -#define AGNX_RXM_DEST_MISS_CNT 0x203C /* Destination Miss Count */ -#define AGNX_RXM_DROP_CNT 0x2040 /* Drop Count */ -#define AGNX_RXM_ABORT_CNT 0x2044 /* Abort Count */ -#define AGNX_RXM_RELAY_CNT 0x2048 /* Relay Count */ -#define AGNX_RXM_HASH_MISS_CNT 0x204c /* Hash Miss Count */ -#define AGNX_RXM_SA_HI 0x2050 /* Address of received packet Hi */ -#define AGNX_RXM_SA_LO 0x2054 /* Address of received packet Lo */ -#define AGNX_RXM_HASH_DUMP_LST 0x2100 /* Contains Hash Data */ -#define AGNX_RXM_HASH_DUMP_MST 0x2104 /* Contains Hash Data */ -#define AGNX_RXM_HASH_DUMP_DATA 0x2108 /* The Station ID to dump */ - - -/* Encryption Managment */ -#define AGNX_ENCRY_BASE 0x2400 -#define AGNX_ENCRY_WEPKEY0 0x2440 /* wep key #0 */ -#define AGNX_ENCRY_WEPKEY1 0x2444 /* wep key #1 */ -#define AGNX_ENCRY_WEPKEY2 0x2448 /* wep key #2 */ -#define AGNX_ENCRY_WEPKEY3 0x244c /* wep key #3 */ -#define AGNX_ENCRY_CCMRECTL 0x2460 /* ccm replay control */ - - -/* Band Management Registers */ -#define AGNX_BM_BASE 0x2c00 -#define AGNX_BM_BMCTL 0x2c00 /* band management control */ -#define AGNX_BM_TXWADDR 0x2c18 /* tx workqueue address start */ -#define AGNX_BM_TXTOPEER 0x2c24 /* transmit to peers */ -#define AGNX_BM_FPLHP 0x2c2c /* free pool list head pointer */ -#define AGNX_BM_FPLTP 0x2c30 /* free pool list tail pointer */ -#define AGNX_BM_FPCNT 0x2c34 /* free pool count */ -#define AGNX_BM_CIPDUWCNT 0x2c38 /* card interface pdu workqueue count */ -#define AGNX_BM_SPPDUWCNT 0x2c3c /* sp pdu workqueue count */ -#define AGNX_BM_RFPPDUWCNT 0x2c40 /* rfp pdu workqueue count */ -#define AGNX_BM_RHPPDUWCNT 0x2c44 /* rhp pdu workqueue count */ -#define AGNX_BM_CIWQCTL 0x2c48 /* Card Interface WorkQueue Control */ -#define AGNX_BM_CPUTXWCTL 0x2c50 /* cpu tx workqueue control */ -#define AGNX_BM_CPURXWCTL 0x2c58 /* cpu rx workqueue control */ -#define AGNX_BM_CPULWCTL 0x2c60 /* cpu low workqueue control */ -#define AGNX_BM_CPUHWCTL 0x2c68 /* cpu high workqueue control */ -#define AGNX_BM_SPTXWCTL 0x2c70 /* sp tx workqueue control */ -#define AGNX_BM_SPRXWCTL 0x2c78 /* sp rx workqueue control */ -#define AGNX_BM_RFPWCTL 0x2c80 /* RFP workqueue control */ -#define AGNX_BM_MTSM 0x2c90 /* Multicast Transmit Station Mask */ - -/* Card Interface Registers (32bits) */ -#define AGNX_CIR_BASE 0x3000 -#define AGNX_CIR_BLKCTL 0x3000 /* block control*/ -#define AGNX_STAT_TX 0x1 -#define AGNX_STAT_RX 0x2 -#define AGNX_STAT_X 0x4 -/* Below two interrupt flags will be set by our but not CPU or the card */ -#define AGNX_STAT_TXD 0x10 -#define AGNX_STAT_TXM 0x20 - -#define AGNX_CIR_ADDRWIN 0x3004 /* Addressable Windows*/ -#define AGNX_CIR_ENDIAN 0x3008 /* card endianness */ -#define AGNX_CIR_SERIALITF 0x3020 /* serial interface */ -#define AGNX_CIR_RXCFG 0x3040 /* receive config */ -#define ENABLE_RX_INTERRUPT 0x20 -#define RX_CACHE_LINE 0x8 -/* the RX fragment length */ -#define FRAG_LEN_256 0x0 /* 256B */ -#define FRAG_LEN_512 0x1 -#define FRAG_LEN_1024 0x2 -#define FRAG_LEN_2048 0x3 -#define FRAG_BE 0x10 -#define AGNX_CIR_RXCTL 0x3050 /* receive control */ -/* memory address, chipside */ -#define AGNX_CIR_RXCMSTART 0x3054 /* receive client memory start */ -#define AGNX_CIR_RXCMEND 0x3058 /* receive client memory end */ -/* memory address, pci */ -#define AGNX_CIR_RXHOSTADDR 0x3060 /* receive hostside address */ -/* memory address, chipside */ -#define AGNX_CIR_RXCLIADDR 0x3064 /* receive clientside address */ -#define AGNX_CIR_RXDMACTL 0x3068 /* receive dma control */ -#define AGNX_CIR_TXCFG 0x3080 /* transmit config */ -#define AGNX_CIR_TXMCTL 0x3090 /* Transmit Management Control */ -#define ENABLE_TX_INTERRUPT 0x20 -#define TX_CACHE_LINE 0x8 -#define AGNX_CIR_TXMSTART 0x3094 /* Transmit Management Start */ -#define AGNX_CIR_TXMEND 0x3098 /* Transmit Management End */ -#define AGNX_CIR_TXDCTL 0x30a0 /* transmit data control */ -/* memeory address, chipset */ -#define AGNX_CIR_TXDSTART 0x30a4 /* transmit data start */ -#define AGNX_CIR_TXDEND 0x30a8 /* transmit data end */ -#define AGNX_CIR_TXMHADDR 0x30b0 /* Transmit Management Hostside Address */ -#define AGNX_CIR_TXMCADDR 0x30b4 /* Transmit Management Clientside Address */ -#define AGNX_CIR_TXDMACTL 0x30b8 /* transmit dma control */ - - -/* Power Managment Unit */ -#define AGNX_PM_BASE 0x3c00 -#define AGNX_PM_PMCTL 0x3c00 /* PM Control*/ -#define AGNX_PM_MACMSW 0x3c08 /* MAC Manual Slow Work Enable */ -#define AGNX_PM_RFCTL 0x3c0c /* RF Control */ -#define AGNX_PM_PHYMW 0x3c14 /* Phy Mannal Work */ -#define AGNX_PM_SOFTRST 0x3c18 /* PMU Soft Reset */ -#define AGNX_PM_PLLCTL 0x3c1c /* PMU PLL control*/ -#define AGNX_PM_TESTPHY 0x3c24 /* PMU Test Phy */ - - -/* Interrupt Control interface */ -#define AGNX_INT_BASE 0x4000 -#define AGNX_INT_STAT 0x4000 /* interrupt status */ -#define AGNX_INT_MASK 0x400c /* interrupt mask */ -/* FIXME */ -#define IRQ_TX_BEACON 0x1 /* TX Beacon */ -#define IRQ_TX_RETRY 0x8 /* TX Retry Interrupt */ -#define IRQ_TX_ACTIVITY 0x10 /* TX Activity */ -#define IRQ_RX_ACTIVITY 0x20 /* RX Activity */ -/* FIXME I guess that instead RX a none exist staion's packet or - the station hasn't been init */ -#define IRQ_RX_X 0x40 -#define IRQ_RX_Y 0x80 /* RX ? */ -#define IRQ_RX_HASHHIT 0x100 /* RX Hash Hit */ -#define IRQ_RX_FRAME 0x200 /* RX Frame */ -#define IRQ_ERR_INT 0x400 /* Error Interrupt */ -#define IRQ_TX_QUE_FULL 0x800 /* TX Workqueue Full */ -#define IRQ_BANDMAN_ERR 0x10000 /* Bandwidth Management Error */ -#define IRQ_TX_DISABLE 0x20000 /* TX Disable */ -#define IRQ_RX_IVASESKEY 0x80000 /* RX Invalid Session Key */ -#define IRQ_RX_KEYIDMIS 0x100000 /* RX key ID Mismatch */ -#define IRQ_REP_THHIT 0x200000 /* Replay Threshold Hit */ -#define IRQ_TIMER1 0x4000000 /* Timer1 */ -#define IRQ_TIMER_CNT 0x10000000 /* Timer Count */ -#define IRQ_PHY_FASTINT 0x20000000 /* Phy Fast Interrupt */ -#define IRQ_PHY_SLOWINT 0x40000000 /* Phy Slow Interrupt */ -#define IRQ_OTHER 0x80000000 /* Unknow interrupt */ -#define AGNX_IRQ_ALL 0xffffffff - -/* System Interface */ -#define AGNX_SYSITF_BASE 0x4400 -#define AGNX_SYSITF_SYSMODE 0x4400 /* system mode */ -#define AGNX_SYSITF_GPIOIN 0x4410 /* GPIO In */ -/* PIN lines for leds? */ -#define AGNX_SYSITF_GPIOUT 0x4414 /* GPIO Out */ - -/* Timer Control */ -#define AGNX_TIMCTL_TIMER1 0x4800 /* Timer 1 */ -#define AGNX_TIMCTL_TIM1CTL 0x4808 /* Timer 1 Control */ - - -/* Antenna Calibration Interface */ -#define AGNX_ACI_BASE 0x5000 -#define AGNX_ACI_MODE 0x5000 /* Mode */ -#define AGNX_ACI_MEASURE 0x5004 /* Measure */ -#define AGNX_ACI_SELCHAIN 0x5008 /* Select Chain */ -#define AGNX_ACI_LEN 0x500c /* Length */ -#define AGNX_ACI_TIMER1 0x5018 /* Timer 1 */ -#define AGNX_ACI_TIMER2 0x501c /* Timer 2 */ -#define AGNX_ACI_OFFSET 0x5020 /* Offset */ -#define AGNX_ACI_STATUS 0x5030 /* Status */ -#define CALI_IDLE 0x0 -#define CALI_DONE 0x1 -#define CALI_BUSY 0x2 -#define CALI_ERR 0x3 -#define AGNX_ACI_AICCHA0OVE 0x5034 /* AIC Channel 0 Override */ -#define AGNX_ACI_AICCHA1OVE 0x5038 /* AIC Channel 1 Override */ - -/* Gain Control Registers */ -#define AGNX_GCR_BASE 0x9000 -/* threshold of primary antenna */ -#define AGNX_GCR_THD0A 0x9000 /* threshold? D0 A */ -/* low threshold of primary antenna */ -#define AGNX_GCR_THD0AL 0x9004 /* threshold? D0 A low */ -/* threshold of secondary antenna */ -#define AGNX_GCR_THD0B 0x9008 /* threshold? D0_B */ -#define AGNX_GCR_DUNSAT 0x900c /* d unsaturated */ -#define AGNX_GCR_DSAT 0x9010 /* d saturated */ -#define AGNX_GCR_DFIRCAL 0x9014 /* D Fir/Cal */ -#define AGNX_GCR_DGCTL11A 0x9018 /* d gain control 11a */ -#define AGNX_GCR_DGCTL11B 0x901c /* d gain control 11b */ -/* strength of gain */ -#define AGNX_GCR_GAININIT 0x9020 /* gain initialization */ -#define AGNX_GCR_THNOSIG 0x9024 /* threhold no signal */ -#define AGNX_GCR_COARSTEP 0x9028 /* coarse stepping */ -#define AGNX_GCR_SIFST11A 0x902c /* sifx time 11a */ -#define AGNX_GCR_SIFST11B 0x9030 /* sifx time 11b */ -#define AGNX_GCR_CWDETEC 0x9034 /* cw detection */ -#define AGNX_GCR_0X38 0x9038 /* ???? */ -#define AGNX_GCR_BOACT 0x903c /* BO Active */ -#define AGNX_GCR_BOINACT 0x9040 /* BO Inactive */ -#define AGNX_GCR_BODYNA 0x9044 /* BO dynamic */ -/* 802.11 mode(a,b,g) */ -#define AGNX_GCR_DISCOVMOD 0x9048 /* discovery mode */ -#define AGNX_GCR_NLISTANT 0x904c /* number of listening antenna */ -#define AGNX_GCR_NACTIANT 0x9050 /* number of active antenna */ -#define AGNX_GCR_NMEASANT 0x9054 /* number of measuring antenna */ -#define AGNX_GCR_NCAPTANT 0x9058 /* number of capture antenna */ -#define AGNX_GCR_THCAP11A 0x905c /* threshold capture 11a */ -#define AGNX_GCR_THCAP11B 0x9060 /* threshold capture 11b */ -#define AGNX_GCR_THCAPRX11A 0x9064 /* threshold capture rx 11a */ -#define AGNX_GCR_THCAPRX11B 0x9068 /* threshold capture rx 11b */ -#define AGNX_GCR_THLEVDRO 0x906c /* threshold level drop */ -#define AGNX_GCR_GAINSET0 0x9070 /* Gainset 0 */ -#define AGNX_GCR_GAINSET1 0x9074 /* Gainset 1 */ -#define AGNX_GCR_GAINSET2 0x9078 /* Gainset 2 */ -#define AGNX_GCR_MAXRXTIME11A 0x907c /* maximum rx time 11a */ -#define AGNX_GCR_MAXRXTIME11B 0x9080 /* maximum rx time 11b */ -#define AGNX_GCR_CORRTIME 0x9084 /* correction time */ -/* reset the subsystem, 0 = disable, 1 = enable */ -#define AGNX_GCR_RSTGCTL 0x9088 /* reset gain control */ -/* channel receiving */ -#define AGNX_GCR_RXCHANEL 0x908c /* receive channel */ -#define AGNX_GCR_NOISE0 0x9090 /* Noise 0 */ -#define AGNX_GCR_NOISE1 0x9094 /* Noise 1 */ -#define AGNX_GCR_NOISE2 0x9098 /* Noise 2 */ -#define AGNX_GCR_SIGHTH 0x909c /* Signal High Threshold */ -#define AGNX_GCR_SIGLTH 0x90a0 /* Signal Low Threshold */ -#define AGNX_GCR_CORRDROP 0x90a4 /* correction drop */ -/* threshold of tertiay antenna */ -#define AGNX_GCR_THCD 0x90a8 /* threshold? CD */ -#define AGNX_GCR_THCS 0x90ac /* threshold? CS */ -#define AGNX_GCR_MAXPOWDIFF 0x90b8 /* maximum power difference */ -#define AGNX_GCR_TRACNT4 0x90ec /* Transition Count 4 */ -#define AGNX_GCR_TRACNT5 0x90f0 /* transition count 5 */ -#define AGNX_GCR_TRACNT6 0x90f4 /* transition count 6 */ -#define AGNX_GCR_TRACNT7 0x90f8 /* transition coutn 7 */ -#define AGNX_GCR_TESTBUS 0x911c /* test bus */ -#define AGNX_GCR_CHAINNUM 0x9120 /* Number of Chains */ -#define AGNX_GCR_ANTCFG 0x9124 /* Antenna Config */ -#define AGNX_GCR_THJUMP 0x912c /* threhold jump */ -#define AGNX_GCR_THPOWER 0x9130 /* threshold power */ -#define AGNX_GCR_THPOWCLIP 0x9134 /* threshold power clip*/ -#define AGNX_GCR_FORCECTLCLK 0x9138 /* Force Gain Control Clock */ -#define AGNX_GCR_GAINSETWRITE 0x913c /* Gainset Write */ -#define AGNX_GCR_THD0BTFEST 0x9140 /* threshold d0 b tf estimate */ -#define AGNX_GCR_THRX11BPOWMIN 0x9144 /* threshold rx 11b power minimum */ -#define AGNX_GCR_0X14c 0x914c /* ?? */ -#define AGNX_GCR_0X150 0x9150 /* ?? */ -#define AGNX_GCR_RXOVERIDE 0x9194 /* recieve override */ -#define AGNX_GCR_WATCHDOG 0x91b0 /* watchdog timeout */ - - -/* Spi Interface */ -#define AGNX_SPI_BASE 0xdc00 -#define AGNX_SPI_CFG 0xdc00 /* spi configuration */ -/* Only accept 16 bits */ -#define AGNX_SPI_WMSW 0xdc04 /* write most significant word */ -/* Only accept 16 bits */ -#define AGNX_SPI_WLSW 0xdc08 /* write least significant word */ -#define AGNX_SPI_CTL 0xdc0c /* spi control */ -#define AGNX_SPI_RMSW 0xdc10 /* read most significant word */ -#define AGNX_SPI_RLSW 0xdc14 /* read least significant word */ -/* SPI Control Mask */ -#define SPI_READ_CTL 0x4000 /* read control */ -#define SPI_BUSY_CTL 0x8000 /* busy control */ -/* RF and synth chips in spi */ -#define RF_CHIP0 0x400 -#define RF_CHIP1 0x800 -#define RF_CHIP2 0x1000 -#define SYNTH_CHIP 0x2000 - -/* Unknown register */ -#define AGNX_UNKNOWN_BASE 0x7800 - -/* FIXME MonitorGain */ -#define AGNX_MONGCR_BASE 0x12000 - -/* Gain Table */ -#define AGNX_GAIN_TABLE 0x12400 - -/* The initial FIR coefficient table */ -#define AGNX_FIR_BASE 0x19804 - -#define AGNX_ENGINE_LOOKUP_TBL 0x800 - -/* eeprom commands */ -#define EEPROM_CMD_NULL 0x0 /* NULL */ -#define EEPROM_CMD_WRITE 0x2 /* write */ -#define EEPROM_CMD_READ 0x3 /* read */ -#define EEPROM_CMD_STATUSREAD 0x5 /* status register read */ -#define EEPROM_CMD_WRITEENABLE 0x6 /* write enable */ -#define EEPROM_CMD_CONFIGURE 0x7 /* configure */ - -#define EEPROM_DATAFORCOFIGURE 0x6 /* ??? */ - -/* eeprom address */ -#define EEPROM_ADDR_SUBVID 0x0 /* Sub Vendor ID */ -#define EEPROM_ADDR_SUBSID 0x2 /* Sub System ID */ -#define EEPROM_ADDR_MACADDR 0x146 /* MAC Address */ -#define EEPROM_ADDR_LOTYPE 0x14f /* LO type */ - -struct agnx_eeprom { - u8 data; /* date */ - u16 address; /* address in EEPROM */ - u8 cmd; /* command, unknown, status */ -} __attribute__((__packed__)); - -#define AGNX_EEPROM_COMMAND_SHIFT 5 -#define AGNX_EEPROM_COMMAND_STAT 0x01 - -void disable_receiver(struct agnx_priv *priv); -void enable_receiver(struct agnx_priv *priv); -u8 read_from_eeprom(struct agnx_priv *priv, u16 address); -void agnx_hw_init(struct agnx_priv *priv); -int agnx_hw_reset(struct agnx_priv *priv); -int agnx_set_ssid(struct agnx_priv *priv, u8 *ssid, size_t ssid_len); -void agnx_set_bssid(struct agnx_priv *priv, const u8 *bssid); -void enable_power_saving(struct agnx_priv *priv); -void disable_power_saving(struct agnx_priv *priv); -void calibrate_antenna_period(unsigned long data); - -#endif /* AGNX_PHY_H_ */ diff --git a/drivers/staging/agnx/rf.c b/drivers/staging/agnx/rf.c deleted file mode 100644 index 42e457a1844f..000000000000 --- a/drivers/staging/agnx/rf.c +++ /dev/null @@ -1,893 +0,0 @@ -/** - * Airgo MIMO wireless driver - * - * Copyright (c) 2007 Li YanBo <dreamfly281@gmail.com> - - * Thanks for Jeff Williams <angelbane@gmail.com> do reverse engineer - * works and published the SPECS at http://airgo.wdwconsulting.net/mymoin - - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation; - */ - -#include <linux/pci.h> -#include <linux/delay.h> -#include "agnx.h" -#include "debug.h" -#include "phy.h" -#include "table.h" - -/* FIXME! */ -static inline void spi_write(void __iomem *region, u32 chip_ids, u32 sw, - u16 size, u32 control) -{ - u32 reg; - u32 lsw = sw & 0xffff; /* lower 16 bits of sw*/ - u32 msw = sw >> 16; /* high 16 bits of sw */ - - /* FIXME Write Most Significant Word of the 32bit data to MSW */ - /* FIXME And Least Significant Word to LSW */ - iowrite32((lsw), region + AGNX_SPI_WLSW); - iowrite32((msw), region + AGNX_SPI_WMSW); - reg = chip_ids | size | control; - /* Write chip id(s), write size and busy control to Control Register */ - iowrite32((reg), region + AGNX_SPI_CTL); - /* Wait for Busy control to clear */ - spi_delay(); -} - -/* - * Write to SPI Synth register - */ -static inline void spi_sy_write(void __iomem *region, u32 chip_ids, u32 sw) -{ - /* FIXME the size 0x15 is a magic value*/ - spi_write(region, chip_ids, sw, 0x15, SPI_BUSY_CTL); -} - -/* - * Write to SPI RF register - */ -static inline void spi_rf_write(void __iomem *region, u32 chip_ids, u32 sw) -{ - /* FIXME the size 0xd is a magic value*/ - spi_write(region, chip_ids, sw, 0xd, SPI_BUSY_CTL); -} /* spi_rf_write */ - -/* - * Write to SPI with Read Control bit set - */ -inline void spi_rc_write(void __iomem *region, u32 chip_ids, u32 sw) -{ - /* FIXME the size 0xe5 is a magic value */ - spi_write(region, chip_ids, sw, 0xe5, SPI_BUSY_CTL|SPI_READ_CTL); -} - -/* Get the active chains's count */ -static int get_active_chains(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - int num = 0; - u32 reg; - AGNX_TRACE; - - spi_rc_write(ctl, RF_CHIP0, 0x21); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - if (reg == 1) - num++; - - spi_rc_write(ctl, RF_CHIP1, 0x21); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - if (reg == 1) - num++; - - spi_rc_write(ctl, RF_CHIP2, 0x21); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - if (reg == 1) - num++; - - spi_rc_write(ctl, RF_CHIP0, 0x26); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - if (0x33 != reg) - printk(KERN_WARNING PFX "Unmatched rf chips result\n"); - - return num; -} /* get_active_chains */ - -void rf_chips_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - int num; - AGNX_TRACE; - - if (priv->revid == 1) { - reg = agnx_read32(ctl, AGNX_SYSITF_GPIOUT); - reg |= 0x8; - agnx_write32(ctl, AGNX_SYSITF_GPIOUT, reg); - } - - /* Set SPI clock speed to 200NS */ - reg = agnx_read32(ctl, AGNX_SPI_CFG); - reg &= ~0xF; - reg |= 0x3; - agnx_write32(ctl, AGNX_SPI_CFG, reg); - - /* Set SPI clock speed to 50NS */ - reg = agnx_read32(ctl, AGNX_SPI_CFG); - reg &= ~0xF; - reg |= 0x1; - agnx_write32(ctl, AGNX_SPI_CFG, reg); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1101); - - num = get_active_chains(priv); - printk(KERN_INFO PFX "Active chains are %d\n", num); - - reg = agnx_read32(ctl, AGNX_SPI_CFG); - reg &= ~0xF; - agnx_write32(ctl, AGNX_SPI_CFG, reg); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1908); -} /* rf_chips_init */ - - -static u32 channel_tbl[15][9] = { - {0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, - {1, 0x00, 0x00, 0x624, 0x00, 0x1a4, 0x28, 0x00, 0x1e}, - {2, 0x00, 0x00, 0x615, 0x00, 0x1ae, 0x28, 0x00, 0x1e}, - {3, 0x00, 0x00, 0x61a, 0x00, 0x1ae, 0x28, 0x00, 0x1e}, - {4, 0x00, 0x00, 0x61f, 0x00, 0x1ae, 0x28, 0x00, 0x1e}, - {5, 0x00, 0x00, 0x624, 0x00, 0x1ae, 0x28, 0x00, 0x1e}, - {6, 0x00, 0x00, 0x61f, 0x00, 0x1b3, 0x28, 0x00, 0x1e}, - {7, 0x00, 0x00, 0x624, 0x00, 0x1b3, 0x28, 0x00, 0x1e}, - {8, 0x00, 0x00, 0x629, 0x00, 0x1b3, 0x28, 0x00, 0x1e}, - {9, 0x00, 0x00, 0x624, 0x00, 0x1b8, 0x28, 0x00, 0x1e}, - {10, 0x00, 0x00, 0x629, 0x00, 0x1b8, 0x28, 0x00, 0x1e}, - {11, 0x00, 0x00, 0x62e, 0x00, 0x1b8, 0x28, 0x00, 0x1e}, - {12, 0x00, 0x00, 0x633, 0x00, 0x1b8, 0x28, 0x00, 0x1e}, - {13, 0x00, 0x00, 0x628, 0x00, 0x1b8, 0x28, 0x00, 0x1e}, - {14, 0x00, 0x00, 0x644, 0x00, 0x1b8, 0x28, 0x00, 0x1e}, -}; - - -static inline void -channel_tbl_write(struct agnx_priv *priv, unsigned int channel, unsigned int reg_num) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - reg = channel_tbl[channel][reg_num]; - reg <<= 4; - reg |= reg_num; - spi_sy_write(ctl, SYNTH_CHIP, reg); -} - -static void synth_freq_set(struct agnx_priv *priv, unsigned int channel) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1201); - - /* Set the Clock bits to 50NS */ - reg = agnx_read32(ctl, AGNX_SPI_CFG); - reg &= ~0xF; - reg |= 0x1; - agnx_write32(ctl, AGNX_SPI_CFG, reg); - - /* Write 0x00c0 to LSW and 0x3 to MSW of Synth Chip */ - spi_sy_write(ctl, SYNTH_CHIP, 0x300c0); - - spi_sy_write(ctl, SYNTH_CHIP, 0x32); - - /* # Write to Register 1 on the Synth Chip */ - channel_tbl_write(priv, channel, 1); - /* # Write to Register 3 on the Synth Chip */ - channel_tbl_write(priv, channel, 3); - /* # Write to Register 6 on the Synth Chip */ - channel_tbl_write(priv, channel, 6); - /* # Write to Register 5 on the Synth Chip */ - channel_tbl_write(priv, channel, 5); - /* # Write to register 8 on the Synth Chip */ - channel_tbl_write(priv, channel, 8); - - /* FIXME Clear the clock bits */ - reg = agnx_read32(ctl, AGNX_SPI_CFG); - reg &= ~0xf; - agnx_write32(ctl, AGNX_SPI_CFG, reg); -} /* synth_chip_init */ - - -static void antenna_init(struct agnx_priv *priv, int num_antenna) -{ - void __iomem *ctl = priv->ctl; - - switch (num_antenna) { - case 1: - agnx_write32(ctl, AGNX_GCR_NLISTANT, 1); - agnx_write32(ctl, AGNX_GCR_NMEASANT, 1); - agnx_write32(ctl, AGNX_GCR_NACTIANT, 1); - agnx_write32(ctl, AGNX_GCR_NCAPTANT, 1); - - agnx_write32(ctl, AGNX_GCR_ANTCFG, 7); - agnx_write32(ctl, AGNX_GCR_BOACT, 34); - agnx_write32(ctl, AGNX_GCR_BOINACT, 34); - agnx_write32(ctl, AGNX_GCR_BODYNA, 30); - - agnx_write32(ctl, AGNX_GCR_THD0A, 125); - agnx_write32(ctl, AGNX_GCR_THD0AL, 100); - agnx_write32(ctl, AGNX_GCR_THD0B, 90); - - agnx_write32(ctl, AGNX_GCR_THD0BTFEST, 80); - agnx_write32(ctl, AGNX_GCR_SIGHTH, 100); - agnx_write32(ctl, AGNX_GCR_SIGLTH, 16); - break; - case 2: - agnx_write32(ctl, AGNX_GCR_NLISTANT, 2); - agnx_write32(ctl, AGNX_GCR_NMEASANT, 2); - agnx_write32(ctl, AGNX_GCR_NACTIANT, 2); - agnx_write32(ctl, AGNX_GCR_NCAPTANT, 2); - agnx_write32(ctl, AGNX_GCR_ANTCFG, 15); - agnx_write32(ctl, AGNX_GCR_BOACT, 36); - agnx_write32(ctl, AGNX_GCR_BOINACT, 36); - agnx_write32(ctl, AGNX_GCR_BODYNA, 32); - agnx_write32(ctl, AGNX_GCR_THD0A, 120); - agnx_write32(ctl, AGNX_GCR_THD0AL, 100); - agnx_write32(ctl, AGNX_GCR_THD0B, 80); - agnx_write32(ctl, AGNX_GCR_THD0BTFEST, 70); - agnx_write32(ctl, AGNX_GCR_SIGHTH, 100); - agnx_write32(ctl, AGNX_GCR_SIGLTH, 32); - break; - case 3: - agnx_write32(ctl, AGNX_GCR_NLISTANT, 3); - agnx_write32(ctl, AGNX_GCR_NMEASANT, 3); - agnx_write32(ctl, AGNX_GCR_NACTIANT, 3); - agnx_write32(ctl, AGNX_GCR_NCAPTANT, 3); - agnx_write32(ctl, AGNX_GCR_ANTCFG, 31); - agnx_write32(ctl, AGNX_GCR_BOACT, 36); - agnx_write32(ctl, AGNX_GCR_BOINACT, 36); - agnx_write32(ctl, AGNX_GCR_BODYNA, 32); - agnx_write32(ctl, AGNX_GCR_THD0A, 100); - agnx_write32(ctl, AGNX_GCR_THD0AL, 100); - agnx_write32(ctl, AGNX_GCR_THD0B, 70); - agnx_write32(ctl, AGNX_GCR_THD0BTFEST, 70); - agnx_write32(ctl, AGNX_GCR_SIGHTH, 100); - agnx_write32(ctl, AGNX_GCR_SIGLTH, 48); -/* agnx_write32(ctl, AGNX_GCR_SIGLTH, 16); */ - break; - default: - printk(KERN_WARNING PFX "Unknow antenna number\n"); - } -} /* antenna_init */ - -static void chain_update(struct agnx_priv *priv, u32 chain) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - spi_rc_write(ctl, RF_CHIP0, 0x20); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - - if (reg == 0x4) - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, reg|0x1000); - else if (reg != 0x0) - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, reg|0x1000); - else { - if (chain == 3 || chain == 6) { - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, reg|0x1000); - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x0); - } else if (chain == 2 || chain == 4) { - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, reg|0x1000); - spi_rf_write(ctl, RF_CHIP2, 0x1005); - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x824); - } else if (chain == 1) { - spi_rf_write(ctl, RF_CHIP0, reg|0x1000); - spi_rf_write(ctl, RF_CHIP1|RF_CHIP2, 0x1004); - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0xc36); - } - } - - spi_rc_write(ctl, RF_CHIP0, 0x22); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - - switch (reg) { - case 0: - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1005); - break; - case 1: - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1201); - break; - case 2: - if (chain == 6 || chain == 4) { - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1202); - spi_rf_write(ctl, RF_CHIP2, 0x1005); - } else if (chain < 3) { - spi_rf_write(ctl, RF_CHIP0, 0x1202); - spi_rf_write(ctl, RF_CHIP1|RF_CHIP2, 0x1005); - } - break; - default: - if (chain == 3) { - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1203); - spi_rf_write(ctl, RF_CHIP2, 0x1201); - } else if (chain == 2) { - spi_rf_write(ctl, RF_CHIP0, 0x1203); - spi_rf_write(ctl, RF_CHIP2, 0x1200); - spi_rf_write(ctl, RF_CHIP1, 0x1201); - } else if (chain == 1) { - spi_rf_write(ctl, RF_CHIP0, 0x1203); - spi_rf_write(ctl, RF_CHIP1|RF_CHIP2, 0x1200); - } else if (chain == 4) { - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1203); - spi_rf_write(ctl, RF_CHIP2, 0x1201); - } else { - spi_rf_write(ctl, RF_CHIP0, 0x1203); - spi_rf_write(ctl, RF_CHIP1|RF_CHIP2, 0x1201); - } - } -} /* chain_update */ - -static void antenna_config(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - /* Write 0x0 to the TX Management Control Register Enable bit */ - reg = agnx_read32(ctl, AGNX_TXM_CTL); - reg &= ~0x1; - agnx_write32(ctl, AGNX_TXM_CTL, reg); - - /* FIXME */ - /* Set initial value based on number of Antennae */ - antenna_init(priv, 3); - - /* FIXME Update Power Templates for current valid Stations */ - /* sta_power_init(priv, 0);*/ - - /* FIXME the number of chains should get from eeprom*/ - chain_update(priv, AGNX_CHAINS_MAX); -} /* antenna_config */ - -void calibrate_oscillator(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - spi_rc_write(ctl, RF_CHIP0|RF_CHIP1, 0x1201); - reg = agnx_read32(ctl, AGNX_GCR_GAINSET1); - reg |= 0x10; - agnx_write32(ctl, AGNX_GCR_GAINSET1, reg); - - agnx_write32(ctl, AGNX_GCR_GAINSETWRITE, 1); - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 1); - - agnx_write32(ctl, AGNX_ACI_LEN, 0x3ff); - - agnx_write32(ctl, AGNX_ACI_TIMER1, 0x27); - agnx_write32(ctl, AGNX_ACI_TIMER2, 0x27); - /* (Residual DC Calibration) to Calibration Mode */ - agnx_write32(ctl, AGNX_ACI_MODE, 0x2); - - spi_rc_write(ctl, RF_CHIP0|RF_CHIP1, 0x1004); - agnx_write32(ctl, AGNX_ACI_LEN, 0x3ff); - /* (TX LO Calibration) to Calibration Mode */ - agnx_write32(ctl, AGNX_ACI_MODE, 0x4); - - do { - u32 reg1, reg2, reg3; - /* Enable Power Saving Control */ - enable_power_saving(priv); - /* Save the following registers to restore */ - reg1 = ioread32(ctl + 0x11000); - reg2 = ioread32(ctl + 0xec50); - reg3 = ioread32(ctl + 0xec54); - wmb(); - - agnx_write32(ctl, 0x11000, 0xcfdf); - agnx_write32(ctl, 0xec50, 0x70); - /* Restore the registers */ - agnx_write32(ctl, 0x11000, reg1); - agnx_write32(ctl, 0xec50, reg2); - agnx_write32(ctl, 0xec54, reg3); - /* Disable Power Saving Control */ - disable_power_saving(priv); - } while (0); - - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0); -} /* calibrate_oscillator */ - - -static void radio_channel_set(struct agnx_priv *priv, unsigned int channel) -{ - void __iomem *ctl = priv->ctl; - unsigned int freq = priv->band.channels[channel - 1].center_freq; - u32 reg; - AGNX_TRACE; - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1201); - /* Set SPI Clock to 50 Ns */ - reg = agnx_read32(ctl, AGNX_SPI_CFG); - reg &= ~0xF; - reg |= 0x1; - agnx_write32(ctl, AGNX_SPI_CFG, reg); - - /* Clear the Disable Tx interrupt bit in Interrupt Mask */ -/* reg = agnx_read32(ctl, AGNX_INT_MASK); */ -/* reg &= ~IRQ_TX_DISABLE; */ -/* agnx_write32(ctl, AGNX_INT_MASK, reg); */ - - /* Band Selection */ - reg = agnx_read32(ctl, AGNX_SYSITF_GPIOUT); - reg |= 0x8; - agnx_write32(ctl, AGNX_SYSITF_GPIOUT, reg); - - /* FIXME Set the SiLabs Chip Frequency */ - synth_freq_set(priv, channel); - - reg = agnx_read32(ctl, AGNX_PM_SOFTRST); - reg |= 0x80100030; - agnx_write32(ctl, AGNX_PM_SOFTRST, reg); - reg = agnx_read32(ctl, AGNX_PM_PLLCTL); - reg |= 0x20009; - agnx_write32(ctl, AGNX_PM_PLLCTL, reg); - - agnx_write32(ctl, AGNX_SYSITF_GPIOUT, 0x5); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1100); - - /* Load the MonitorGain Table */ - monitor_gain_table_init(priv); - - /* Load the TX Fir table */ - tx_fir_table_init(priv); - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg |= 0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); - - spi_rc_write(ctl, RF_CHIP0|RF_CHIP1, 0x22); - udelay(80); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - - - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0xff); - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x3); - - reg = agnx_read32(ctl, 0xec50); - reg |= 0x4f; - agnx_write32(ctl, 0xec50, reg); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1201); - agnx_write32(ctl, 0x11008, 0x1); - agnx_write32(ctl, 0x1100c, 0x0); - agnx_write32(ctl, 0x11008, 0x0); - agnx_write32(ctl, 0xec50, 0xc); - - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x3); - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x0); - agnx_write32(ctl, 0x11010, 0x6e); - agnx_write32(ctl, 0x11014, 0x6c); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1201); - - /* Calibrate the Antenna */ - /* antenna_calibrate(priv); */ - /* Calibrate the TxLocalOscillator */ - calibrate_oscillator(priv); - - reg = agnx_read32(ctl, AGNX_PM_PMCTL); - reg &= ~0x8; - agnx_write32(ctl, AGNX_PM_PMCTL, reg); - agnx_write32(ctl, AGNX_GCR_GAININIT, 0xa); - agnx_write32(ctl, AGNX_GCR_THCD, 0x0); - - agnx_write32(ctl, 0x11018, 0xb); - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x0); - - /* Write Frequency to Gain Control Channel */ - agnx_write32(ctl, AGNX_GCR_RXCHANEL, freq); - /* Write 0x140000/Freq to 0x9c08 */ - reg = 0x140000/freq; - agnx_write32(ctl, 0x9c08, reg); - - reg = agnx_read32(ctl, AGNX_PM_SOFTRST); - reg &= ~0x80100030; - agnx_write32(ctl, AGNX_PM_SOFTRST, reg); - - reg = agnx_read32(ctl, AGNX_PM_PLLCTL); - reg &= ~0x20009; - reg |= 0x1; - agnx_write32(ctl, AGNX_PM_PLLCTL, reg); - - agnx_write32(ctl, AGNX_ACI_MODE, 0x0); - -/* FIXME According to Number of Chains: */ - -/* 1. 1: */ -/* 1. Write 0x1203 to RF Chip 0 */ -/* 2. Write 0x1200 to RF Chips 1 +2 */ -/* 2. 2: */ -/* 1. Write 0x1203 to RF Chip 0 */ -/* 2. Write 0x1200 to RF Chip 2 */ -/* 3. Write 0x1201 to RF Chip 1 */ -/* 3. 3: */ -/* 1. Write 0x1203 to RF Chip 0 */ -/* 2. Write 0x1201 to RF Chip 1 + 2 */ -/* 4. 4: */ -/* 1. Write 0x1203 to RF Chip 0 + 1 */ -/* 2. Write 0x1200 to RF Chip 2 */ - -/* 5. 6: */ - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1, 0x1203); - spi_rf_write(ctl, RF_CHIP2, 0x1201); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1000); - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x0); - - /* FIXME Set the Disable Tx interrupt bit in Interrupt Mask - (Or 0x20000 to Interrupt Mask) */ -/* reg = agnx_read32(ctl, AGNX_INT_MASK); */ -/* reg |= IRQ_TX_DISABLE; */ -/* agnx_write32(ctl, AGNX_INT_MASK, reg); */ - - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x1); - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x0); - - /* Configure the Antenna */ - antenna_config(priv); - - /* Write 0x0 to Discovery Mode Enable detect G, B, A packet? */ - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0); - - reg = agnx_read32(ctl, AGNX_RXM_REQRATE); - reg |= 0x80000000; - agnx_write32(ctl, AGNX_RXM_REQRATE, reg); - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x1); - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x0); - - /* enable radio on and the power LED */ - reg = agnx_read32(ctl, AGNX_SYSITF_GPIOUT); - reg &= ~0x1; - reg |= 0x2; - agnx_write32(ctl, AGNX_SYSITF_GPIOUT, reg); - - reg = agnx_read32(ctl, AGNX_TXM_CTL); - reg |= 0x1; - agnx_write32(ctl, AGNX_TXM_CTL, reg); -} /* radio_channel_set */ - -static void base_band_filter_calibrate(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1700); - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1001); - agnx_write32(ctl, AGNX_GCR_FORCECTLCLK, 0x0); - spi_rc_write(ctl, RF_CHIP0, 0x27); - spi_rc_write(ctl, RF_CHIP1, 0x27); - spi_rc_write(ctl, RF_CHIP2, 0x27); - agnx_write32(ctl, AGNX_GCR_FORCECTLCLK, 0x1); -} - -static void print_offset(struct agnx_priv *priv, u32 chain) -{ - void __iomem *ctl = priv->ctl; - u32 offset; - - iowrite32((chain), ctl + AGNX_ACI_SELCHAIN); - udelay(10); - offset = (ioread32(ctl + AGNX_ACI_OFFSET)); - printk(PFX "Chain is 0x%x, Offset is 0x%x\n", chain, offset); -} - -void print_offsets(struct agnx_priv *priv) -{ - print_offset(priv, 0); - print_offset(priv, 4); - print_offset(priv, 1); - print_offset(priv, 5); - print_offset(priv, 2); - print_offset(priv, 6); -} - - -struct chains { - u32 cali; /* calibrate value*/ - -#define NEED_CALIBRATE 0 -#define SUCCESS_CALIBRATE 1 - int status; -}; - -static void chain_calibrate(struct agnx_priv *priv, struct chains *chains, - unsigned int num) -{ - void __iomem *ctl = priv->ctl; - u32 calibra = chains[num].cali; - - if (num < 3) - calibra |= 0x1400; - else - calibra |= 0x1500; - - switch (num) { - case 0: - case 4: - spi_rf_write(ctl, RF_CHIP0, calibra); - break; - case 1: - case 5: - spi_rf_write(ctl, RF_CHIP1, calibra); - break; - case 2: - case 6: - spi_rf_write(ctl, RF_CHIP2, calibra); - break; - default: - BUG(); - } -} /* chain_calibrate */ - -static inline void get_calibrete_value(struct agnx_priv *priv, struct chains *chains, - unsigned int num) -{ - void __iomem *ctl = priv->ctl; - u32 offset; - - iowrite32((num), ctl + AGNX_ACI_SELCHAIN); - /* FIXME */ - udelay(10); - offset = (ioread32(ctl + AGNX_ACI_OFFSET)); - - if (offset < 0xf) { - chains[num].status = SUCCESS_CALIBRATE; - return; - } - - if (num == 0 || num == 1 || num == 2) { - if (0 == chains[num].cali) - chains[num].cali = 0xff; - else - chains[num].cali--; - } else - chains[num].cali++; - - chains[num].status = NEED_CALIBRATE; -} - -static inline void calibra_delay(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - unsigned int i = 100; - - wmb(); - while (--i) { - reg = (ioread32(ctl + AGNX_ACI_STATUS)); - if (reg == 0x4000) - break; - udelay(10); - } - if (!i) - printk(PFX "calibration failed\n"); -} - -void do_calibration(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - struct chains chains[7]; - unsigned int i, j; - AGNX_TRACE; - - for (i = 0; i < 7; i++) { - if (i == 3) - continue; - - chains[i].cali = 0x7f; - chains[i].status = NEED_CALIBRATE; - } - - /* FIXME 0x300 is a magic number */ - for (j = 0; j < 0x300; j++) { - if (chains[0].status == SUCCESS_CALIBRATE && - chains[1].status == SUCCESS_CALIBRATE && - chains[2].status == SUCCESS_CALIBRATE && - chains[4].status == SUCCESS_CALIBRATE && - chains[5].status == SUCCESS_CALIBRATE && - chains[6].status == SUCCESS_CALIBRATE) - break; - - /* Attention, there is no chain 3 */ - for (i = 0; i < 7; i++) { - if (i == 3) - continue; - if (chains[i].status == NEED_CALIBRATE) - chain_calibrate(priv, chains, i); - } - /* Write 0x1 to Calibration Measure */ - iowrite32((0x1), ctl + AGNX_ACI_MEASURE); - calibra_delay(priv); - - for (i = 0; i < 7; i++) { - if (i == 3) - continue; - - get_calibrete_value(priv, chains, i); - } - } - printk(PFX "Clibrate times is %d\n", j); - print_offsets(priv); -} /* do_calibration */ - -void antenna_calibrate(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - AGNX_TRACE; - - agnx_write32(ctl, AGNX_GCR_NLISTANT, 0x3); - agnx_write32(ctl, AGNX_GCR_NMEASANT, 0x3); - agnx_write32(ctl, AGNX_GCR_NACTIANT, 0x3); - agnx_write32(ctl, AGNX_GCR_NCAPTANT, 0x3); - - agnx_write32(ctl, AGNX_GCR_ANTCFG, 0x1f); - agnx_write32(ctl, AGNX_GCR_BOACT, 0x24); - agnx_write32(ctl, AGNX_GCR_BOINACT, 0x24); - agnx_write32(ctl, AGNX_GCR_BODYNA, 0x20); - agnx_write32(ctl, AGNX_GCR_THD0A, 0x64); - agnx_write32(ctl, AGNX_GCR_THD0AL, 0x64); - agnx_write32(ctl, AGNX_GCR_THD0B, 0x46); - agnx_write32(ctl, AGNX_GCR_THD0BTFEST, 0x3c); - agnx_write32(ctl, AGNX_GCR_SIGHTH, 0x64); - agnx_write32(ctl, AGNX_GCR_SIGLTH, 0x30); - - spi_rc_write(ctl, RF_CHIP0, 0x20); - /* Fixme */ - udelay(80); - /* 1. Should read 0x0 */ - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - if (0x0 != reg) - printk(KERN_WARNING PFX "Unmatched rf chips result\n"); - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1000); - - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x0); - - spi_rc_write(ctl, RF_CHIP0, 0x22); - udelay(80); - reg = agnx_read32(ctl, AGNX_SPI_RLSW); - if (0x0 != reg) - printk(KERN_WARNING PFX "Unmatched rf chips result\n"); - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1005); - - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x1); - agnx_write32(ctl, AGNX_GCR_RSTGCTL, 0x0); - - reg = agnx_read32(ctl, AGNX_PM_SOFTRST); - reg |= 0x1c000032; - agnx_write32(ctl, AGNX_PM_SOFTRST, reg); - reg = agnx_read32(ctl, AGNX_PM_PLLCTL); - reg |= 0x0003f07; - agnx_write32(ctl, AGNX_PM_PLLCTL, reg); - - reg = agnx_read32(ctl, 0xec50); - reg |= 0x40; - agnx_write32(ctl, 0xec50, reg); - - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0xff8); - agnx_write32(ctl, AGNX_GCR_DISCOVMOD, 0x3); - - agnx_write32(ctl, AGNX_GCR_CHAINNUM, 0x6); - agnx_write32(ctl, 0x19874, 0x0); - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1700); - - /* Calibrate the BaseBandFilter */ - base_band_filter_calibrate(priv); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1002); - - agnx_write32(ctl, AGNX_GCR_GAINSET0, 0x1d); - agnx_write32(ctl, AGNX_GCR_GAINSET1, 0x1d); - agnx_write32(ctl, AGNX_GCR_GAINSET2, 0x1d); - agnx_write32(ctl, AGNX_GCR_GAINSETWRITE, 0x1); - - agnx_write32(ctl, AGNX_ACI_MODE, 0x1); - agnx_write32(ctl, AGNX_ACI_LEN, 0x3ff); - - agnx_write32(ctl, AGNX_ACI_TIMER1, 0x27); - agnx_write32(ctl, AGNX_ACI_TIMER2, 0x27); - - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1400); - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1500); - - /* Measure Calibration */ - agnx_write32(ctl, AGNX_ACI_MEASURE, 0x1); - calibra_delay(priv); - - /* do calibration */ - do_calibration(priv); - - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x0); - agnx_write32(ctl, AGNX_ACI_TIMER1, 0x21); - agnx_write32(ctl, AGNX_ACI_TIMER2, 0x27); - agnx_write32(ctl, AGNX_ACI_LEN, 0xf); - - reg = agnx_read32(ctl, AGNX_GCR_GAINSET0); - reg &= 0xf; - agnx_write32(ctl, AGNX_GCR_GAINSET0, reg); - reg = agnx_read32(ctl, AGNX_GCR_GAINSET1); - reg &= 0xf; - agnx_write32(ctl, AGNX_GCR_GAINSET1, reg); - reg = agnx_read32(ctl, AGNX_GCR_GAINSET2); - reg &= 0xf; - agnx_write32(ctl, AGNX_GCR_GAINSET2, reg); - - agnx_write32(ctl, AGNX_GCR_GAINSETWRITE, 0x0); - disable_receiver(priv); -} /* antenna_calibrate */ - -void __antenna_calibrate(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - /* Calibrate the BaseBandFilter */ - /* base_band_filter_calibrate(priv); */ - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1002); - - - agnx_write32(ctl, AGNX_GCR_GAINSET0, 0x1d); - agnx_write32(ctl, AGNX_GCR_GAINSET1, 0x1d); - agnx_write32(ctl, AGNX_GCR_GAINSET2, 0x1d); - - agnx_write32(ctl, AGNX_GCR_GAINSETWRITE, 0x1); - - agnx_write32(ctl, AGNX_ACI_MODE, 0x1); - agnx_write32(ctl, AGNX_ACI_LEN, 0x3ff); - - - agnx_write32(ctl, AGNX_ACI_TIMER1, 0x27); - agnx_write32(ctl, AGNX_ACI_TIMER2, 0x27); - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1400); - spi_rf_write(ctl, RF_CHIP0|RF_CHIP1|RF_CHIP2, 0x1500); - /* Measure Calibration */ - agnx_write32(ctl, AGNX_ACI_MEASURE, 0x1); - calibra_delay(priv); - do_calibration(priv); - agnx_write32(ctl, AGNX_GCR_RXOVERIDE, 0x0); - - agnx_write32(ctl, AGNX_ACI_TIMER1, 0x21); - agnx_write32(ctl, AGNX_ACI_TIMER2, 0x27); - - agnx_write32(ctl, AGNX_ACI_LEN, 0xf); - - reg = agnx_read32(ctl, AGNX_GCR_GAINSET0); - reg &= 0xf; - agnx_write32(ctl, AGNX_GCR_GAINSET0, reg); - reg = agnx_read32(ctl, AGNX_GCR_GAINSET1); - reg &= 0xf; - agnx_write32(ctl, AGNX_GCR_GAINSET1, reg); - reg = agnx_read32(ctl, AGNX_GCR_GAINSET2); - reg &= 0xf; - agnx_write32(ctl, AGNX_GCR_GAINSET2, reg); - - - agnx_write32(ctl, AGNX_GCR_GAINSETWRITE, 0x0); - - /* Write 0x3 Gain Control Discovery Mode */ - enable_receiver(priv); -} - -int agnx_set_channel(struct agnx_priv *priv, unsigned int channel) -{ - AGNX_TRACE; - - printk(KERN_ERR PFX "Channel is %d %s\n", channel, __func__); - radio_channel_set(priv, channel); - return 0; -} diff --git a/drivers/staging/agnx/sta.c b/drivers/staging/agnx/sta.c deleted file mode 100644 index 3e7db5e2811a..000000000000 --- a/drivers/staging/agnx/sta.c +++ /dev/null @@ -1,218 +0,0 @@ -#include <linux/delay.h> -#include <linux/etherdevice.h> -#include "phy.h" -#include "sta.h" -#include "debug.h" - -void hash_read(struct agnx_priv *priv, u32 reghi, u32 reglo, u8 sta_id) -{ - void __iomem *ctl = priv->ctl; - - reglo &= 0xFFFF; - reglo |= 0x30000000; - reglo |= 0x40000000; /* Set status busy */ - reglo |= sta_id << 16; - - iowrite32(0, ctl + AGNX_RXM_HASH_CMD_FLAG); - iowrite32(reghi, ctl + AGNX_RXM_HASH_CMD_HIGH); - iowrite32(reglo, ctl + AGNX_RXM_HASH_CMD_LOW); - - reghi = ioread32(ctl + AGNX_RXM_HASH_CMD_HIGH); - reglo = ioread32(ctl + AGNX_RXM_HASH_CMD_LOW); - printk(PFX "RX hash cmd are : %.8x%.8x\n", reghi, reglo); -} - -void hash_write(struct agnx_priv *priv, const u8 *mac_addr, u8 sta_id) -{ - void __iomem *ctl = priv->ctl; - u32 reghi, reglo; - - if (!is_valid_ether_addr(mac_addr)) - printk(KERN_WARNING PFX "Update hash table: Invalid hwaddr!\n"); - - reghi = mac_addr[0] << 24 | mac_addr[1] << 16 | mac_addr[2] << 8 | mac_addr[3]; - reglo = mac_addr[4] << 8 | mac_addr[5]; - reglo |= 0x10000000; /* Set hash commmand */ - reglo |= 0x40000000; /* Set status busy */ - reglo |= sta_id << 16; - - iowrite32(0, ctl + AGNX_RXM_HASH_CMD_FLAG); - iowrite32(reghi, ctl + AGNX_RXM_HASH_CMD_HIGH); - iowrite32(reglo, ctl + AGNX_RXM_HASH_CMD_LOW); - - reglo = ioread32(ctl + AGNX_RXM_HASH_CMD_LOW); - if (!(reglo & 0x80000000)) - printk(KERN_WARNING PFX "Update hash table failed\n"); -} - -void hash_delete(struct agnx_priv *priv, u32 reghi, u32 reglo, u8 sta_id) -{ - void __iomem *ctl = priv->ctl; - - reglo &= 0xFFFF; - reglo |= 0x20000000; - reglo |= 0x40000000; /* Set status busy */ - reglo |= sta_id << 16; - - iowrite32(0, ctl + AGNX_RXM_HASH_CMD_FLAG); - iowrite32(reghi, ctl + AGNX_RXM_HASH_CMD_HIGH); - iowrite32(reglo, ctl + AGNX_RXM_HASH_CMD_LOW); - reghi = ioread32(ctl + AGNX_RXM_HASH_CMD_HIGH); - - reglo = ioread32(ctl + AGNX_RXM_HASH_CMD_LOW); - printk(PFX "RX hash cmd are : %.8x%.8x\n", reghi, reglo); - -} - -void hash_dump(struct agnx_priv *priv, u8 sta_id) -{ - void __iomem *ctl = priv->ctl; - u32 reghi, reglo; - - reglo = 0x40000000; /* status bit */ - iowrite32(reglo, ctl + AGNX_RXM_HASH_CMD_LOW); - iowrite32(sta_id << 16, ctl + AGNX_RXM_HASH_DUMP_DATA); - - udelay(80); - - reghi = ioread32(ctl + AGNX_RXM_HASH_CMD_HIGH); - reglo = ioread32(ctl + AGNX_RXM_HASH_CMD_LOW); - printk(PFX "hash cmd are : %.8x%.8x\n", reghi, reglo); - reghi = ioread32(ctl + AGNX_RXM_HASH_CMD_FLAG); - printk(PFX "hash flag is : %.8x\n", reghi); - reghi = ioread32(ctl + AGNX_RXM_HASH_DUMP_MST); - reglo = ioread32(ctl + AGNX_RXM_HASH_DUMP_LST); - printk(PFX "hash dump mst lst: %.8x%.8x\n", reghi, reglo); - reghi = ioread32(ctl + AGNX_RXM_HASH_DUMP_DATA); - printk(PFX "hash dump data: %.8x\n", reghi); -} - -void get_sta_power(struct agnx_priv *priv, struct agnx_sta_power *power, unsigned int sta_idx) -{ - void __iomem *ctl = priv->ctl; - memcpy_fromio(power, ctl + AGNX_TXM_STAPOWTEMP + sizeof(*power) * sta_idx, - sizeof(*power)); -} - -inline void -set_sta_power(struct agnx_priv *priv, struct agnx_sta_power *power, unsigned int sta_idx) -{ - void __iomem *ctl = priv->ctl; - /* FIXME 2. Write Template to offset + station number */ - memcpy_toio(ctl + AGNX_TXM_STAPOWTEMP + sizeof(*power) * sta_idx, - power, sizeof(*power)); -} - - -void get_sta_tx_wq(struct agnx_priv *priv, struct agnx_sta_tx_wq *tx_wq, - unsigned int sta_idx, unsigned int wq_idx) -{ - void __iomem *data = priv->data; - memcpy_fromio(tx_wq, data + AGNX_PDU_TX_WQ + sizeof(*tx_wq) * STA_TX_WQ_NUM * sta_idx + - sizeof(*tx_wq) * wq_idx, sizeof(*tx_wq)); - -} - -inline void set_sta_tx_wq(struct agnx_priv *priv, struct agnx_sta_tx_wq *tx_wq, - unsigned int sta_idx, unsigned int wq_idx) -{ - void __iomem *data = priv->data; - memcpy_toio(data + AGNX_PDU_TX_WQ + sizeof(*tx_wq) * STA_TX_WQ_NUM * sta_idx + - sizeof(*tx_wq) * wq_idx, tx_wq, sizeof(*tx_wq)); -} - - -void get_sta(struct agnx_priv *priv, struct agnx_sta *sta, unsigned int sta_idx) -{ - void __iomem *data = priv->data; - - memcpy_fromio(sta, data + AGNX_PDUPOOL + sizeof(*sta) * sta_idx, - sizeof(*sta)); -} - -inline void set_sta(struct agnx_priv *priv, struct agnx_sta *sta, unsigned int sta_idx) -{ - void __iomem *data = priv->data; - - memcpy_toio(data + AGNX_PDUPOOL + sizeof(*sta) * sta_idx, - sta, sizeof(*sta)); -} - -/* FIXME */ -void sta_power_init(struct agnx_priv *priv, unsigned int sta_idx) -{ - struct agnx_sta_power power; - u32 reg; - AGNX_TRACE; - - memset(&power, 0, sizeof(power)); - reg = agnx_set_bits(EDCF, EDCF_SHIFT, 0x1); - power.reg = cpu_to_le32(reg); - set_sta_power(priv, &power, sta_idx); - udelay(40); -} /* add_power_template */ - - -/* @num: The #number of station that is visible to the card */ -static void sta_tx_workqueue_init(struct agnx_priv *priv, unsigned int sta_idx) -{ - struct agnx_sta_tx_wq tx_wq; - u32 reg; - unsigned int i; - - memset(&tx_wq, 0, sizeof(tx_wq)); - - reg = agnx_set_bits(WORK_QUEUE_VALID, WORK_QUEUE_VALID_SHIFT, 1); - reg |= agnx_set_bits(WORK_QUEUE_ACK_TYPE, WORK_QUEUE_ACK_TYPE_SHIFT, 1); -/* reg |= agnx_set_bits(WORK_QUEUE_ACK_TYPE, WORK_QUEUE_ACK_TYPE_SHIFT, 0); */ - tx_wq.reg2 |= cpu_to_le32(reg); - - /* Suppose all 8 traffic class are used */ - for (i = 0; i < STA_TX_WQ_NUM; i++) - set_sta_tx_wq(priv, &tx_wq, sta_idx, i); -} /* sta_tx_workqueue_init */ - - -static void sta_traffic_init(struct agnx_sta_traffic *traffic) -{ - u32 reg; - memset(traffic, 0, sizeof(*traffic)); - - reg = agnx_set_bits(NEW_PACKET, NEW_PACKET_SHIFT, 1); - reg |= agnx_set_bits(TRAFFIC_VALID, TRAFFIC_VALID_SHIFT, 1); -/* reg |= agnx_set_bits(TRAFFIC_ACK_TYPE, TRAFFIC_ACK_TYPE_SHIFT, 1); */ - traffic->reg0 = cpu_to_le32(reg); - - /* 3. setting RX Sequence Number to 4095 */ - reg = agnx_set_bits(RX_SEQUENCE_NUM, RX_SEQUENCE_NUM_SHIFT, 4095); - traffic->reg1 = cpu_to_le32(reg); -} - - -/* @num: The #number of station that is visible to the card */ -void sta_init(struct agnx_priv *priv, unsigned int sta_idx) -{ - /* FIXME the length of sta is 256 bytes Is that - * dangerous to stack overflow? */ - struct agnx_sta sta; - u32 reg; - int i; - - memset(&sta, 0, sizeof(sta)); - /* Set valid to 1 */ - reg = agnx_set_bits(STATION_VALID, STATION_VALID_SHIFT, 1); - /* Set Enable Concatenation to 0 (?) */ - reg |= agnx_set_bits(ENABLE_CONCATENATION, ENABLE_CONCATENATION_SHIFT, 0); - /* Set Enable Decompression to 0 (?) */ - reg |= agnx_set_bits(ENABLE_DECOMPRESSION, ENABLE_DECOMPRESSION_SHIFT, 0); - sta.reg = cpu_to_le32(reg); - - /* Initialize each of the Traffic Class Structures by: */ - for (i = 0; i < 8; i++) - sta_traffic_init(sta.traffic + i); - - set_sta(priv, &sta, sta_idx); - sta_tx_workqueue_init(priv, sta_idx); -} /* sta_descriptor_init */ - - diff --git a/drivers/staging/agnx/sta.h b/drivers/staging/agnx/sta.h deleted file mode 100644 index fd504e3f3870..000000000000 --- a/drivers/staging/agnx/sta.h +++ /dev/null @@ -1,222 +0,0 @@ -#ifndef AGNX_STA_H_ -#define AGNX_STA_H_ - -#define STA_TX_WQ_NUM 8 /* The number of TX workqueue one STA has */ - -struct agnx_hash_cmd { - __be32 cmdhi; -#define MACLO 0xFFFF0000 -#define MACLO_SHIFT 16 -#define STA_ID 0x0000FFF0 -#define STA_ID_SHIFT 4 -#define CMD 0x0000000C -#define CMD_SHIFT 2 -#define STATUS 0x00000002 -#define STATUS_SHIFT 1 -#define PASS 0x00000001 -#define PASS_SHIFT 1 - __be32 cmdlo; -} __attribute__((__packed__)); - - -/* - * Station Power Template - * FIXME Just for agn100 yet - */ -struct agnx_sta_power { - __le32 reg; -#define SIGNAL 0x000000FF /* signal */ -#define SIGNAL_SHIFT 0 -#define RATE 0x00000F00 -#define RATE_SHIFT 8 -#define TIFS 0x00001000 -#define TIFS_SHIFT 12 -#define EDCF 0x00002000 -#define EDCF_SHIFT 13 -#define CHANNEL_BOND 0x00004000 -#define CHANNEL_BOND_SHIFT 14 -#define PHY_MODE 0x00038000 -#define PHY_MODE_SHIFT 15 -#define POWER_LEVEL 0x007C0000 -#define POWER_LEVEL_SHIFT 18 -#define NUM_TRANSMITTERS 0x00800000 -#define NUM_TRANSMITTERS_SHIFT 23 -} __attribute__((__packed__)); - -/* - * TX Workqueue Descriptor - */ -struct agnx_sta_tx_wq { - __le32 reg0; -#define HEAD_POINTER_LOW 0xFF000000 /* Head pointer low */ -#define HEAD_POINTER_LOW_SHIFT 24 -#define TAIL_POINTER 0x00FFFFFF /* Tail pointer */ -#define TAIL_POINTER_SHIFT 0 - - __le32 reg3; -#define ACK_POINTER_LOW 0xFFFF0000 /* ACK pointer low */ -#define ACK_POINTER_LOW_SHIFT 16 -#define HEAD_POINTER_HIGH 0x0000FFFF /* Head pointer high */ -#define HEAD_POINTER_HIGH_SHIFT 0 - - __le32 reg1; -/* ACK timeout tail packet count */ -#define ACK_TIMOUT_TAIL_PACK_CNT 0xFFF00000 -#define ACK_TIMOUT_TAIL_PACK_CNT_SHIFT 20 -/* Head timeout tail packet count */ -#define HEAD_TIMOUT_TAIL_PACK_CNT 0x000FFF00 -#define HEAD_TIMOUT_TAIL_PACK_CNT_SHIFT 8 -#define ACK_POINTER_HIGH 0x000000FF /* ACK pointer high */ -#define ACK_POINTER_HIGH_SHIFT 0 - - __le32 reg2; -#define WORK_QUEUE_VALID 0x80000000 /* valid */ -#define WORK_QUEUE_VALID_SHIFT 31 -#define WORK_QUEUE_ACK_TYPE 0x40000000 /* ACK type */ -#define WORK_QUEUE_ACK_TYPE_SHIFT 30 -/* Head timeout window limit fragmentation count */ -#define HEAD_TIMOUT_WIN_LIM_FRAG_CNT 0x3FFF0000 -#define HEAD_TIMOUT_WIN_LIM_FRAG_CNT_SHIFT 16 -/* Head timeout window limit byte count */ -#define HEAD_TIMOUT_WIN_LIM_BYTE_CNT 0x0000FFFF -#define HEAD_TIMOUT_WIN_LIM_BYTE_CNT_SHIFT 0 -} __attribute__((__packed__)); - - -/* - * Traffic Class Structure - */ -struct agnx_sta_traffic { - __le32 reg0; -#define ACK_TIMOUT_CNT 0xFF800000 /* ACK Timeout Counts */ -#define ACK_TIMOUT_CNT_SHIFT 23 -#define TRAFFIC_ACK_TYPE 0x00600000 /* ACK Type */ -#define TRAFFIC_ACK_TYPE_SHIFT 21 -#define NEW_PACKET 0x00100000 /* New Packet */ -#define NEW_PACKET_SHIFT 20 -#define TRAFFIC_VALID 0x00080000 /* Valid */ -#define TRAFFIC_VALID_SHIFT 19 -#define RX_HDR_DESC_POINTER 0x0007FFFF /* RX Header Descripter pointer */ -#define RX_HDR_DESC_POINTER_SHIFT 0 - - __le32 reg1; -#define RX_PACKET_TIMESTAMP 0xFFFF0000 /* RX Packet Timestamp */ -#define RX_PACKET_TIMESTAMP_SHIFT 16 -#define TRAFFIC_RESERVED 0x0000E000 /* Reserved */ -#define TRAFFIC_RESERVED_SHIFT 13 -#define SV 0x00001000 /* sv */ -#define SV_SHIFT 12 -#define RX_SEQUENCE_NUM 0x00000FFF /* RX Sequence Number */ -#define RX_SEQUENCE_NUM_SHIFT 0 - - __le32 tx_replay_cnt_low; /* TX Replay Counter Low */ - - __le16 tx_replay_cnt_high; /* TX Replay Counter High */ - __le16 rx_replay_cnt_high; /* RX Replay Counter High */ - - __be32 rx_replay_cnt_low; /* RX Replay Counter Low */ -} __attribute__((__packed__)); - -/* - * Station Descriptors - */ -struct agnx_sta { - __le32 tx_session_keys[4]; /* Transmit Session Key (0-3) */ - __le32 rx_session_keys[4]; /* Receive Session Key (0-3) */ - - __le32 reg; -#define ID_1 0xC0000000 /* id 1 */ -#define ID_1_SHIFT 30 -#define ID_0 0x30000000 /* id 0 */ -#define ID_0_SHIFT 28 -#define ENABLE_CONCATENATION 0x0FF00000 /* Enable concatenation */ -#define ENABLE_CONCATENATION_SHIFT 20 -#define ENABLE_DECOMPRESSION 0x000FF000 /* Enable decompression */ -#define ENABLE_DECOMPRESSION_SHIFT 12 -#define STA_RESERVED 0x00000C00 /* Reserved */ -#define STA_RESERVED_SHIFT 10 -#define EAP 0x00000200 /* EAP */ -#define EAP_SHIFT 9 -#define ED_NULL 0x00000100 /* ED NULL */ -#define ED_NULL_SHIFT 8 -#define ENCRYPTION_POLICY 0x000000E0 /* Encryption Policy */ -#define ENCRYPTION_POLICY_SHIFT 5 -#define DEFINED_KEY_ID 0x00000018 /* Defined Key ID */ -#define DEFINED_KEY_ID_SHIFT 3 -#define FIXED_KEY 0x00000004 /* Fixed Key */ -#define FIXED_KEY_SHIFT 2 -#define KEY_VALID 0x00000002 /* Key Valid */ -#define KEY_VALID_SHIFT 1 -#define STATION_VALID 0x00000001 /* Station Valid */ -#define STATION_VALID_SHIFT 0 - - __le32 tx_aes_blks_unicast; /* TX AES Blks Unicast */ - __le32 rx_aes_blks_unicast; /* RX AES Blks Unicast */ - - __le16 aes_format_err_unicast_cnt; /* AES Format Error Unicast Counts */ - __le16 aes_replay_unicast; /* AES Replay Unicast */ - - __le16 aes_decrypt_err_unicast; /* AES Decrypt Error Unicast */ - __le16 aes_decrypt_err_default; /* AES Decrypt Error default */ - - __le16 single_retry_packets; /* Single Retry Packets */ - __le16 failed_tx_packets; /* Failed Tx Packets */ - - __le16 muti_retry_packets; /* Multiple Retry Packets */ - __le16 ack_timeouts; /* ACK Timeouts */ - - __le16 frag_tx_cnt; /* Fragment TX Counts */ - __le16 rts_brq_sent; /* RTS Brq Sent */ - - __le16 tx_packets; /* TX Packets */ - __le16 cts_back_timeout; /* CTS Back Timeout */ - - __le32 phy_stats_high; /* PHY Stats High */ - __le32 phy_stats_low; /* PHY Stats Low */ - - struct agnx_sta_traffic traffic[8]; /* Traffic Class Structure (8) */ - - __le16 traffic_class0_frag_success; /* Traffic Class 0 Fragment Success */ - __le16 traffic_class1_frag_success; /* Traffic Class 1 Fragment Success */ - __le16 traffic_class2_frag_success; /* Traffic Class 2 Fragment Success */ - __le16 traffic_class3_frag_success; /* Traffic Class 3 Fragment Success */ - __le16 traffic_class4_frag_success; /* Traffic Class 4 Fragment Success */ - __le16 traffic_class5_frag_success; /* Traffic Class 5 Fragment Success */ - __le16 traffic_class6_frag_success; /* Traffic Class 6 Fragment Success */ - __le16 traffic_class7_frag_success; /* Traffic Class 7 Fragment Success */ - - __le16 num_frag_non_prime_rates; /* number of Fragments for non-prime rates */ - __le16 ack_timeout_non_prime_rates; /* ACK Timeout for non-prime rates */ - -} __attribute__((__packed__)); - - -struct agnx_beacon_hdr { - struct agnx_sta_power power; /* Tx Station Power Template */ - u8 phy_hdr[6]; /* PHY Hdr */ - u8 frame_len_lo; /* Frame Length Lo */ - u8 frame_len_hi; /* Frame Length Hi */ - u8 mac_hdr[24]; /* MAC Header */ - /* FIXME */ - /* 802.11(abg) beacon */ -} __attribute__((__packed__)); - -void hash_write(struct agnx_priv *priv, const u8 *mac_addr, u8 sta_id); -void hash_dump(struct agnx_priv *priv, u8 sta_id); -void hash_read(struct agnx_priv *priv, u32 reghi, u32 reglo, u8 sta_id); -void hash_delete(struct agnx_priv *priv, u32 reghi, u32 reglo, u8 sta_id); - -void get_sta_power(struct agnx_priv *priv, struct agnx_sta_power *power, unsigned int sta_idx); -void set_sta_power(struct agnx_priv *priv, struct agnx_sta_power *power, - unsigned int sta_idx); -void get_sta_tx_wq(struct agnx_priv *priv, struct agnx_sta_tx_wq *tx_wq, - unsigned int sta_idx, unsigned int wq_idx); -void set_sta_tx_wq(struct agnx_priv *priv, struct agnx_sta_tx_wq *tx_wq, - unsigned int sta_idx, unsigned int wq_idx); -void get_sta(struct agnx_priv *priv, struct agnx_sta *sta, unsigned int sta_idx); -void set_sta(struct agnx_priv *priv, struct agnx_sta *sta, unsigned int sta_idx); - -void sta_power_init(struct agnx_priv *priv, unsigned int num); -void sta_init(struct agnx_priv *priv, unsigned int num); - -#endif /* AGNX_STA_H_ */ diff --git a/drivers/staging/agnx/table.c b/drivers/staging/agnx/table.c deleted file mode 100644 index b52fef9db0e3..000000000000 --- a/drivers/staging/agnx/table.c +++ /dev/null @@ -1,168 +0,0 @@ -#include <linux/pci.h> -#include <linux/delay.h> -#include "agnx.h" -#include "debug.h" -#include "phy.h" - -static const u32 -tx_fir_table[] = { 0x19, 0x5d, 0xce, 0x151, 0x1c3, 0x1ff, 0x1ea, 0x17c, 0xcf, - 0x19, 0x38e, 0x350, 0x362, 0x3ad, 0x5, 0x44, 0x59, 0x49, - 0x21, 0x3f7, 0x3e0, 0x3e3, 0x3f3, 0x0 }; - -void tx_fir_table_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - int i; - - for (i = 0; i < ARRAY_SIZE(tx_fir_table); i++) - iowrite32(tx_fir_table[i], ctl + AGNX_FIR_BASE + i*4); -} /* fir_table_setup */ - - -static const u32 -gain_table[] = { 0x8, 0x8, 0xf, 0x13, 0x17, 0x1b, 0x1f, 0x23, 0x27, 0x2b, - 0x2f, 0x33, 0x37, 0x3b, 0x3f, 0x43, 0x47, 0x4b, 0x4f, - 0x53, 0x57, 0x5b, 0x5f, 0x5f, 0x5f, 0x5f, 0x5f, 0x5f, - 0x5f, 0x5f, 0x5f, 0x5f }; - -void gain_table_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - int i; - - for (i = 0; i < ARRAY_SIZE(gain_table); i++) { - iowrite32(gain_table[i], ctl + AGNX_GAIN_TABLE + i*4); - iowrite32(gain_table[i], ctl + AGNX_GAIN_TABLE + i*4 + 0x80); - } -} /* gain_table_init */ - -void monitor_gain_table_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - unsigned int i; - - for (i = 0; i < 0x44; i += 4) { - iowrite32(0x61, ctl + AGNX_MONGCR_BASE + i); - iowrite32(0x61, ctl + AGNX_MONGCR_BASE + 0x200 + i); - } - for (i = 0x44; i < 0x64; i += 4) { - iowrite32(0x6e, ctl + AGNX_MONGCR_BASE + i); - iowrite32(0x6e, ctl + AGNX_MONGCR_BASE + 0x200 + i); - } - for (i = 0x64; i < 0x94; i += 4) { - iowrite32(0x7a, ctl + AGNX_MONGCR_BASE + i); - iowrite32(0x7a, ctl + AGNX_MONGCR_BASE + 0x200 + i); - } - for (i = 0x94; i < 0xdc; i += 4) { - iowrite32(0x87, ctl + AGNX_MONGCR_BASE + i); - iowrite32(0x87, ctl + AGNX_MONGCR_BASE + 0x200 + i); - } - for (i = 0xdc; i < 0x148; i += 4) { - iowrite32(0x95, ctl + AGNX_MONGCR_BASE + i); - iowrite32(0x95, ctl + AGNX_MONGCR_BASE + 0x200 + i); - } - for (i = 0x148; i < 0x1e8; i += 4) { - iowrite32(0xa2, ctl + AGNX_MONGCR_BASE + i); - iowrite32(0xa2, ctl + AGNX_MONGCR_BASE + 0x200 + i); - } - for (i = 0x1e8; i <= 0x1fc; i += 4) { - iowrite32(0xb0, ctl + AGNX_MONGCR_BASE + i); - iowrite32(0xb0, ctl + AGNX_MONGCR_BASE + 0x200 + i); - } -} /* monitor_gain_table_init */ - - -void routing_table_init(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - unsigned int type, subtype; - u32 reg; - - disable_receiver(priv); - - for (type = 0; type < 0x3; type++) { - for (subtype = 0; subtype < 0x10; subtype++) { - /* 1. Set Routing table to R/W and to Return status on Read */ - reg = (type << ROUTAB_TYPE_SHIFT) | - (subtype << ROUTAB_SUBTYPE_SHIFT); - reg |= (1 << ROUTAB_RW_SHIFT) | (1 << ROUTAB_STATUS_SHIFT); - if (type == ROUTAB_TYPE_DATA) { - /* NULL goes to RFP */ - if (subtype == ROUTAB_SUBTYPE_NULL) -/* reg |= ROUTAB_ROUTE_RFP; */ - reg |= ROUTAB_ROUTE_CPU; - /* QOS NULL goes to CPU */ - else if (subtype == ROUTAB_SUBTYPE_QOSNULL) - reg |= ROUTAB_ROUTE_CPU; - /* All Data and QOS data subtypes go to Encryption */ - else if ((subtype == ROUTAB_SUBTYPE_DATA) || - (subtype == ROUTAB_SUBTYPE_DATAACK) || - (subtype == ROUTAB_SUBTYPE_DATAPOLL) || - (subtype == ROUTAB_SUBTYPE_DATAPOLLACK) || - (subtype == ROUTAB_SUBTYPE_QOSDATA) || - (subtype == ROUTAB_SUBTYPE_QOSDATAACK) || - (subtype == ROUTAB_SUBTYPE_QOSDATAPOLL) || - (subtype == ROUTAB_SUBTYPE_QOSDATAACKPOLL)) - reg |= ROUTAB_ROUTE_ENCRY; -/* reg |= ROUTAB_ROUTE_CPU; */ - /*Drop NULL and QOS NULL ack, poll and poll ack*/ - else if ((subtype == ROUTAB_SUBTYPE_NULLACK) || - (subtype == ROUTAB_SUBTYPE_QOSNULLACK) || - (subtype == ROUTAB_SUBTYPE_NULLPOLL) || - (subtype == ROUTAB_SUBTYPE_QOSNULLPOLL) || - (subtype == ROUTAB_SUBTYPE_NULLPOLLACK) || - (subtype == ROUTAB_SUBTYPE_QOSNULLPOLLACK)) -/* reg |= ROUTAB_ROUTE_DROP; */ - reg |= ROUTAB_ROUTE_CPU; - } else { - reg |= (ROUTAB_ROUTE_CPU); - } - iowrite32(reg, ctl + AGNX_RXM_ROUTAB); - /* Check to verify that the status bit cleared */ - routing_table_delay(); - } - } - enable_receiver(priv); -} /* routing_table_init */ - -void tx_engine_lookup_tbl_init(struct agnx_priv *priv) -{ - void __iomem *data = priv->data; - unsigned int i; - - for (i = 0; i <= 28; i += 4) - iowrite32(0xb00c, data + AGNX_ENGINE_LOOKUP_TBL + i); - for (i = 32; i <= 120; i += 8) { - iowrite32(0x1e58, data + AGNX_ENGINE_LOOKUP_TBL + i); - iowrite32(0xb00c, data + AGNX_ENGINE_LOOKUP_TBL + i + 4); - } - - for (i = 128; i <= 156; i += 4) - iowrite32(0x980c, data + AGNX_ENGINE_LOOKUP_TBL + i); - for (i = 160; i <= 248; i += 8) { - iowrite32(0x1858, data + AGNX_ENGINE_LOOKUP_TBL + i); - iowrite32(0x980c, data + AGNX_ENGINE_LOOKUP_TBL + i + 4); - } - - for (i = 256; i <= 284; i += 4) - iowrite32(0x980c, data + AGNX_ENGINE_LOOKUP_TBL + i); - for (i = 288; i <= 376; i += 8) { - iowrite32(0x1a58, data + AGNX_ENGINE_LOOKUP_TBL + i); - iowrite32(0x1858, data + AGNX_ENGINE_LOOKUP_TBL + i + 4); - } - - for (i = 512; i <= 540; i += 4) - iowrite32(0xc00c, data + AGNX_ENGINE_LOOKUP_TBL + i); - for (i = 544; i <= 632; i += 8) { - iowrite32(0x2058, data + AGNX_ENGINE_LOOKUP_TBL + i); - iowrite32(0xc00c, data + AGNX_ENGINE_LOOKUP_TBL + i + 4); - } - - for (i = 640; i <= 668; i += 4) - iowrite32(0xc80c, data + AGNX_ENGINE_LOOKUP_TBL + i); - for (i = 672; i <= 764; i += 8) { - iowrite32(0x2258, data + AGNX_ENGINE_LOOKUP_TBL + i); - iowrite32(0xc80c, data + AGNX_ENGINE_LOOKUP_TBL + i + 4); - } -} - diff --git a/drivers/staging/agnx/table.h b/drivers/staging/agnx/table.h deleted file mode 100644 index f0626b5ee86b..000000000000 --- a/drivers/staging/agnx/table.h +++ /dev/null @@ -1,10 +0,0 @@ -#ifndef AGNX_TABLE_H_ -#define AGNX_TABLE_H_ - -void tx_fir_table_init(struct agnx_priv *priv); -void gain_table_init(struct agnx_priv *priv); -void monitor_gain_table_init(struct agnx_priv *priv); -void routing_table_init(struct agnx_priv *priv); -void tx_engine_lookup_tbl_init(struct agnx_priv *priv); - -#endif /* AGNX_TABLE_H_ */ diff --git a/drivers/staging/agnx/xmit.c b/drivers/staging/agnx/xmit.c deleted file mode 100644 index 42db41070cf0..000000000000 --- a/drivers/staging/agnx/xmit.c +++ /dev/null @@ -1,836 +0,0 @@ -/** - * Airgo MIMO wireless driver - * - * Copyright (c) 2007 Li YanBo <dreamfly281@gmail.com> - - * Thanks for Jeff Williams <angelbane@gmail.com> do reverse engineer - * works and published the SPECS at http://airgo.wdwconsulting.net/mymoin - - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. - */ - -#include <linux/pci.h> -#include <linux/delay.h> -#include "agnx.h" -#include "debug.h" -#include "phy.h" - -unsigned int rx_frame_cnt; -/* unsigned int local_tx_sent_cnt = 0; */ - -static inline void disable_rx_engine(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - iowrite32(0x100, ctl + AGNX_CIR_RXCTL); - /* Wait for RX Control to have the Disable Rx Interrupt (0x100) set */ - ioread32(ctl + AGNX_CIR_RXCTL); -} - -static inline void enable_rx_engine(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - iowrite32(0x80, ctl + AGNX_CIR_RXCTL); - ioread32(ctl + AGNX_CIR_RXCTL); -} - -inline void disable_rx_interrupt(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - disable_rx_engine(priv); - reg = ioread32(ctl + AGNX_CIR_RXCFG); - reg &= ~0x20; - iowrite32(reg, ctl + AGNX_CIR_RXCFG); - ioread32(ctl + AGNX_CIR_RXCFG); -} - -inline void enable_rx_interrupt(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - u32 reg; - - reg = ioread32(ctl + AGNX_CIR_RXCFG); - reg |= 0x20; - iowrite32(reg, ctl + AGNX_CIR_RXCFG); - ioread32(ctl + AGNX_CIR_RXCFG); - enable_rx_engine(priv); -} - -static inline void rx_desc_init(struct agnx_priv *priv, unsigned int idx) -{ - struct agnx_desc *desc = priv->rx.desc + idx; - struct agnx_info *info = priv->rx.info + idx; - - memset(info, 0, sizeof(*info)); - - info->dma_len = IEEE80211_MAX_RTS_THRESHOLD + sizeof(struct agnx_hdr); - info->skb = dev_alloc_skb(info->dma_len); - if (info->skb == NULL) - agnx_bug("refill err"); - - info->mapping = pci_map_single(priv->pdev, skb_tail_pointer(info->skb), - info->dma_len, PCI_DMA_FROMDEVICE); - memset(desc, 0, sizeof(*desc)); - desc->dma_addr = cpu_to_be32(info->mapping); - /* Set the owner to the card */ - desc->frag = cpu_to_be32(be32_to_cpu(desc->frag) | OWNER); -} - -static inline void rx_desc_reinit(struct agnx_priv *priv, unsigned int idx) -{ - struct agnx_info *info = priv->rx.info + idx; - - /* Cause ieee80211 will free the skb buffer, so we needn't to free it again?! */ - pci_unmap_single(priv->pdev, info->mapping, info->dma_len, PCI_DMA_FROMDEVICE); - rx_desc_init(priv, idx); -} - -static inline void rx_desc_reusing(struct agnx_priv *priv, unsigned int idx) -{ - struct agnx_desc *desc = priv->rx.desc + idx; - struct agnx_info *info = priv->rx.info + idx; - - memset(desc, 0, sizeof(*desc)); - desc->dma_addr = cpu_to_be32(info->mapping); - /* Set the owner to the card */ - desc->frag = cpu_to_be32(be32_to_cpu(desc->frag) | OWNER); -} - -static void rx_desc_free(struct agnx_priv *priv, unsigned int idx) -{ - struct agnx_desc *desc = priv->rx.desc + idx; - struct agnx_info *info = priv->rx.info + idx; - - BUG_ON(!desc || !info); - if (info->mapping) - pci_unmap_single(priv->pdev, info->mapping, info->dma_len, PCI_DMA_FROMDEVICE); - if (info->skb) - dev_kfree_skb(info->skb); - memset(info, 0, sizeof(*info)); - memset(desc, 0, sizeof(*desc)); -} - -static inline void __tx_desc_free(struct agnx_priv *priv, - struct agnx_desc *desc, struct agnx_info *info) -{ - BUG_ON(!desc || !info); - /* TODO make sure mapping, skb and len are consistency */ - if (info->mapping) - pci_unmap_single(priv->pdev, info->mapping, - info->dma_len, PCI_DMA_TODEVICE); - if (info->type == PACKET) - dev_kfree_skb(info->skb); - - memset(info, 0, sizeof(*info)); - memset(desc, 0, sizeof(*desc)); -} - -static void txm_desc_free(struct agnx_priv *priv, unsigned int idx) -{ - struct agnx_desc *desc = priv->txm.desc + idx; - struct agnx_info *info = priv->txm.info + idx; - - __tx_desc_free(priv, desc, info); -} - -static void txd_desc_free(struct agnx_priv *priv, unsigned int idx) -{ - struct agnx_desc *desc = priv->txd.desc + idx; - struct agnx_info *info = priv->txd.info + idx; - - __tx_desc_free(priv, desc, info); -} - -int fill_rings(struct agnx_priv *priv) -{ - void __iomem *ctl = priv->ctl; - unsigned int i; - u32 reg; - AGNX_TRACE; - - priv->txd.idx_sent = priv->txm.idx_sent = 0; - priv->rx.idx = priv->txm.idx = priv->txd.idx = 0; - - for (i = 0; i < priv->rx.size; i++) - rx_desc_init(priv, i); - for (i = 0; i < priv->txm.size; i++) { - memset(priv->txm.desc + i, 0, sizeof(struct agnx_desc)); - memset(priv->txm.info + i, 0, sizeof(struct agnx_info)); - } - for (i = 0; i < priv->txd.size; i++) { - memset(priv->txd.desc + i, 0, sizeof(struct agnx_desc)); - memset(priv->txd.info + i, 0, sizeof(struct agnx_info)); - } - - /* FIXME Set the card RX TXM and TXD address */ - agnx_write32(ctl, AGNX_CIR_RXCMSTART, priv->rx.dma); - agnx_write32(ctl, AGNX_CIR_RXCMEND, priv->txm.dma); - - agnx_write32(ctl, AGNX_CIR_TXMSTART, priv->txm.dma); - agnx_write32(ctl, AGNX_CIR_TXMEND, priv->txd.dma); - - agnx_write32(ctl, AGNX_CIR_TXDSTART, priv->txd.dma); - agnx_write32(ctl, AGNX_CIR_TXDEND, priv->txd.dma + - sizeof(struct agnx_desc) * priv->txd.size); - - /* FIXME Relinquish control of rings to card */ - reg = agnx_read32(ctl, AGNX_CIR_BLKCTL); - reg &= ~0x800; - agnx_write32(ctl, AGNX_CIR_BLKCTL, reg); - return 0; -} /* fill_rings */ - -void unfill_rings(struct agnx_priv *priv) -{ - unsigned long flags; - unsigned int i; - AGNX_TRACE; - - spin_lock_irqsave(&priv->lock, flags); - - for (i = 0; i < priv->rx.size; i++) - rx_desc_free(priv, i); - for (i = 0; i < priv->txm.size; i++) - txm_desc_free(priv, i); - for (i = 0; i < priv->txd.size; i++) - txd_desc_free(priv, i); - - spin_unlock_irqrestore(&priv->lock, flags); -} - -/* Extract the bitrate out of a CCK PLCP header. - copy from bcm43xx driver */ -static inline u8 agnx_plcp_get_bitrate_cck(__be32 *phyhdr_11b) -{ - /* FIXME */ - switch (*(u8 *)phyhdr_11b) { - case 0x0A: - return 0; - case 0x14: - return 1; - case 0x37: - return 2; - case 0x6E: - return 3; - } - agnx_bug("Wrong plcp rate"); - return 0; -} - -/* FIXME */ -static inline u8 agnx_plcp_get_bitrate_ofdm(__be32 *phyhdr_11g) -{ - u8 rate = *(u8 *)phyhdr_11g & 0xF; - - printk(PFX "G mode rate is 0x%x\n", rate); - return rate; -} - -/* FIXME */ -static void get_rx_stats(struct agnx_priv *priv, struct agnx_hdr *hdr, - struct ieee80211_rx_status *stat) -{ - void __iomem *ctl = priv->ctl; - u8 *rssi; - u32 noise; - /* FIXME just for test */ - int snr = 40; /* signal-to-noise ratio */ - - memset(stat, 0, sizeof(*stat)); - /* RSSI */ - rssi = (u8 *)&hdr->phy_stats_lo; -/* stat->ssi = (rssi[0] + rssi[1] + rssi[2]) / 3; */ - /* Noise */ - noise = ioread32(ctl + AGNX_GCR_NOISE0); - noise += ioread32(ctl + AGNX_GCR_NOISE1); - noise += ioread32(ctl + AGNX_GCR_NOISE2); - stat->noise = noise / 3; - /* Signal quality */ -/* snr = stat->ssi - stat->noise; */ - if (snr >= 0 && snr < 40) - stat->signal = 5 * snr / 2; - else if (snr >= 40) - stat->signal = 100; - else - stat->signal = 0; - - - if (hdr->_11b0 && !hdr->_11g0) { - stat->rate_idx = agnx_plcp_get_bitrate_cck(&hdr->_11b0); - } else if (!hdr->_11b0 && hdr->_11g0) { - printk(PFX "RX: Found G mode packet\n"); - stat->rate_idx = agnx_plcp_get_bitrate_ofdm(&hdr->_11g0); - } else - agnx_bug("Unknown packets type"); - - - stat->band = IEEE80211_BAND_2GHZ; - stat->freq = agnx_channels[priv->channel - 1].center_freq; -/* stat->antenna = 3; - stat->mactime = be32_to_cpu(hdr->time_stamp); - stat->channel = priv->channel; */ -} - -static inline void combine_hdr_frag(struct ieee80211_hdr *ieeehdr, - struct sk_buff *skb) -{ - u16 fctl; - unsigned int hdrlen; - - fctl = le16_to_cpu(ieeehdr->frame_control); - hdrlen = ieee80211_hdrlen(fctl); - /* FIXME */ - if (hdrlen < (2+2+6)/*minimum hdr*/ || - hdrlen > sizeof(struct ieee80211_mgmt)) { - printk(KERN_ERR PFX "hdr len is %d\n", hdrlen); - agnx_bug("Wrong ieee80211 hdr detected"); - } - skb_push(skb, hdrlen); - memcpy(skb->data, ieeehdr, hdrlen); -} /* combine_hdr_frag */ - -static inline int agnx_packet_check(struct agnx_priv *priv, struct agnx_hdr *agnxhdr, - unsigned packet_len) -{ - if (agnx_get_bits(CRC_FAIL, CRC_FAIL_SHIFT, be32_to_cpu(agnxhdr->reg1)) == 1) { - printk(PFX "RX: CRC check fail\n"); - goto drop; - } - if (packet_len > 2048) { - printk(PFX "RX: Too long packet detected\n"); - goto drop; - } - - /* FIXME Just usable for Promious Mode, for Manage mode exclude FCS */ -/* if (packet_len - sizeof(*agnxhdr) < FCS_LEN) { */ -/* printk(PFX "RX: Too short packet detected\n"); */ -/* goto drop; */ -/* } */ - return 0; -drop: - priv->stats.dot11FCSErrorCount++; - return -1; -} - -void handle_rx_irq(struct agnx_priv *priv) -{ - struct ieee80211_rx_status status; - unsigned int len; -/* AGNX_TRACE; */ - - do { - struct agnx_desc *desc; - u32 frag; - struct agnx_info *info; - struct agnx_hdr *hdr; - struct sk_buff *skb; - unsigned int i = priv->rx.idx % priv->rx.size; - - desc = priv->rx.desc + i; - frag = be32_to_cpu(desc->frag); - if (frag & OWNER) - break; - - info = priv->rx.info + i; - skb = info->skb; - hdr = (struct agnx_hdr *)(skb->data); - - len = (frag & PACKET_LEN) >> PACKET_LEN_SHIFT; - if (agnx_packet_check(priv, hdr, len) == -1) { - rx_desc_reusing(priv, i); - continue; - } - skb_put(skb, len); - - do { - u16 fctl; - fctl = le16_to_cpu(((struct ieee80211_hdr *)hdr->mac_hdr)->frame_control); - if ((fctl & IEEE80211_FCTL_STYPE) != IEEE80211_STYPE_BEACON)/* && !(fctl & IEEE80211_STYPE_BEACON)) */ - dump_ieee80211_hdr((struct ieee80211_hdr *)hdr->mac_hdr, "RX"); - } while (0); - - if (hdr->_11b0 && !hdr->_11g0) { -/* int j; - u16 fctl = le16_to_cpu(((struct ieee80211_hdr *)hdr->mac_hdr) - ->frame_control); - if ( (fctl & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA) { - agnx_print_rx_hdr(hdr); - agnx_print_sta(priv, BSSID_STAID); - for (j = 0; j < 8; j++) - agnx_print_sta_tx_wq(priv, BSSID_STAID, j); - } */ - - get_rx_stats(priv, hdr, &status); - skb_pull(skb, sizeof(*hdr)); - combine_hdr_frag((struct ieee80211_hdr *)hdr->mac_hdr, skb); - } else if (!hdr->_11b0 && hdr->_11g0) { -/* int j; */ - agnx_print_rx_hdr(hdr); - agnx_print_sta(priv, BSSID_STAID); -/* for (j = 0; j < 8; j++) */ - agnx_print_sta_tx_wq(priv, BSSID_STAID, 0); - - print_hex_dump_bytes("agnx: RX_PACKET: ", DUMP_PREFIX_NONE, - skb->data, skb->len + 8); - -/* if (agnx_plcp_get_bitrate_ofdm(&hdr->_11g0) == 0) */ - get_rx_stats(priv, hdr, &status); - skb_pull(skb, sizeof(*hdr)); - combine_hdr_frag((struct ieee80211_hdr *) - ((void *)&hdr->mac_hdr), skb); -/* dump_ieee80211_hdr((struct ieee80211_hdr *)skb->data, "RX G"); */ - } else - agnx_bug("Unknown packets type"); - memcpy(IEEE80211_SKB_RXCB(skb), &status, sizeof(status)); - ieee80211_rx_irqsafe(priv->hw, skb); - rx_desc_reinit(priv, i); - - } while (priv->rx.idx++); -} /* handle_rx_irq */ - -static inline void handle_tx_irq(struct agnx_priv *priv, struct agnx_ring *ring) -{ - struct agnx_desc *desc; - struct agnx_info *info; - unsigned int idx; - - for (idx = ring->idx_sent; idx < ring->idx; idx++) { - unsigned int i = idx % ring->size; - u32 frag; - - desc = ring->desc + i; - info = ring->info + i; - - frag = be32_to_cpu(desc->frag); - if (frag & OWNER) { - if (info->type == HEADER) - break; - else - agnx_bug("TX error"); - } - - pci_unmap_single(priv->pdev, info->mapping, info->dma_len, PCI_DMA_TODEVICE); - - do { -/* int j; */ - size_t len; - len = info->skb->len - sizeof(struct agnx_hdr) + info->hdr_len; -/* if (len == 614) { */ -/* agnx_print_desc(desc); */ - if (info->type == PACKET) { -/* agnx_print_tx_hdr((struct agnx_hdr *)info->skb->data); */ -/* agnx_print_sta_power(priv, LOCAL_STAID); */ -/* agnx_print_sta(priv, LOCAL_STAID); */ -/* for (j = 0; j < 8; j++) */ -/* agnx_print_sta_tx_wq(priv, LOCAL_STAID, 0); */ -/* agnx_print_sta_power(priv, BSSID_STAID); */ -/* agnx_print_sta(priv, BSSID_STAID); */ -/* for (j = 0; j < 8; j++) */ -/* agnx_print_sta_tx_wq(priv, BSSID_STAID, 0); */ - } -/* } */ - } while (0); - - if (info->type == PACKET) { -/* dump_txm_registers(priv); - dump_rxm_registers(priv); - dump_bm_registers(priv); - dump_cir_registers(priv); */ - } - - if (info->type == PACKET) { -/* struct ieee80211_hdr *hdr; */ - struct ieee80211_tx_info *txi = IEEE80211_SKB_CB(info->skb); - - skb_pull(info->skb, sizeof(struct agnx_hdr)); - memcpy(skb_push(info->skb, info->hdr_len), &info->hdr, info->hdr_len); - -/* dump_ieee80211_hdr((struct ieee80211_hdr *)info->skb->data, "TX_HANDLE"); */ -/* print_hex_dump_bytes("agnx: TX_HANDLE: ", DUMP_PREFIX_NONE, */ -/* info->skb->data, info->skb->len); */ - - if (!(txi->flags & IEEE80211_TX_CTL_NO_ACK)) - txi->flags |= IEEE80211_TX_STAT_ACK; - - ieee80211_tx_status_irqsafe(priv->hw, info->skb); - - -/* info->tx_status.queue_number = (ring->size - i) / 2; */ -/* ieee80211_tx_status_irqsafe(priv->hw, info->skb, &(info->tx_status)); */ -/* } else */ -/* dev_kfree_skb_irq(info->skb); */ - } - memset(desc, 0, sizeof(*desc)); - memset(info, 0, sizeof(*info)); - } - - ring->idx_sent = idx; - /* TODO fill the priv->low_level_stats */ - - /* ieee80211_wake_queue(priv->hw, 0); */ -} - -void handle_txm_irq(struct agnx_priv *priv) -{ - handle_tx_irq(priv, &priv->txm); -} - -void handle_txd_irq(struct agnx_priv *priv) -{ - handle_tx_irq(priv, &priv->txd); -} - -void handle_other_irq(struct agnx_priv *priv) -{ -/* void __iomem *ctl = priv->ctl; */ - u32 status = priv->irq_status; - void __iomem *ctl = priv->ctl; - u32 reg; - - if (status & IRQ_TX_BEACON) { - iowrite32(IRQ_TX_BEACON, ctl + AGNX_INT_STAT); - printk(PFX "IRQ: TX Beacon control is 0X%.8X\n", ioread32(ctl + AGNX_TXM_BEACON_CTL)); - printk(PFX "IRQ: TX Beacon rx frame num: %d\n", rx_frame_cnt); - } - if (status & IRQ_TX_RETRY) { - reg = ioread32(ctl + AGNX_TXM_RETRYSTAID); - printk(PFX "IRQ: TX Retry, RETRY STA ID is %x\n", reg); - } - if (status & IRQ_TX_ACTIVITY) - printk(PFX "IRQ: TX Activity\n"); - if (status & IRQ_RX_ACTIVITY) - printk(PFX "IRQ: RX Activity\n"); - if (status & IRQ_RX_X) - printk(PFX "IRQ: RX X\n"); - if (status & IRQ_RX_Y) { - reg = ioread32(ctl + AGNX_INT_MASK); - reg &= ~IRQ_RX_Y; - iowrite32(reg, ctl + AGNX_INT_MASK); - iowrite32(IRQ_RX_Y, ctl + AGNX_INT_STAT); - printk(PFX "IRQ: RX Y\n"); - } - if (status & IRQ_RX_HASHHIT) { - reg = ioread32(ctl + AGNX_INT_MASK); - reg &= ~IRQ_RX_HASHHIT; - iowrite32(reg, ctl + AGNX_INT_MASK); - iowrite32(IRQ_RX_HASHHIT, ctl + AGNX_INT_STAT); - printk(PFX "IRQ: RX Hash Hit\n"); - - } - if (status & IRQ_RX_FRAME) { - reg = ioread32(ctl + AGNX_INT_MASK); - reg &= ~IRQ_RX_FRAME; - iowrite32(reg, ctl + AGNX_INT_MASK); - iowrite32(IRQ_RX_FRAME, ctl + AGNX_INT_STAT); - printk(PFX "IRQ: RX Frame\n"); - rx_frame_cnt++; - } - if (status & IRQ_ERR_INT) { - iowrite32(IRQ_ERR_INT, ctl + AGNX_INT_STAT); -/* agnx_hw_reset(priv); */ - printk(PFX "IRQ: Error Interrupt\n"); - } - if (status & IRQ_TX_QUE_FULL) - printk(PFX "IRQ: TX Workqueue Full\n"); - if (status & IRQ_BANDMAN_ERR) - printk(PFX "IRQ: Bandwidth Management Error\n"); - if (status & IRQ_TX_DISABLE) - printk(PFX "IRQ: TX Disable\n"); - if (status & IRQ_RX_IVASESKEY) - printk(PFX "IRQ: RX Invalid Session Key\n"); - if (status & IRQ_REP_THHIT) - printk(PFX "IRQ: Replay Threshold Hit\n"); - if (status & IRQ_TIMER1) - printk(PFX "IRQ: Timer1\n"); - if (status & IRQ_TIMER_CNT) - printk(PFX "IRQ: Timer Count\n"); - if (status & IRQ_PHY_FASTINT) - printk(PFX "IRQ: Phy Fast Interrupt\n"); - if (status & IRQ_PHY_SLOWINT) - printk(PFX "IRQ: Phy Slow Interrupt\n"); - if (status & IRQ_OTHER) - printk(PFX "IRQ: 0x80000000\n"); -} /* handle_other_irq */ - - -static inline void route_flag_set(struct agnx_hdr *txhdr) -{ -/* u32 reg = 0; */ - - /* FIXME */ -/* reg = (0x7 << ROUTE_COMPRESSION_SHIFT) & ROUTE_COMPRESSION; */ -/* txhdr->reg5 = cpu_to_be32(reg); */ - txhdr->reg5 = (0xa << 0x0) | (0x7 << 0x18); -/* txhdr->reg5 = cpu_to_be32((0xa << 0x0) | (0x7 << 0x18)); */ -/* txhdr->reg5 = cpu_to_be32(0x7 << 0x0); */ -} - -/* Return 0 if no match */ -static inline unsigned int get_power_level(unsigned int rate, unsigned int antennas_num) -{ - unsigned int power_level; - - switch (rate) { - case 10: - case 20: - case 55: - case 60: - case 90: - case 120: - power_level = 22; - break; - - case 180: - power_level = 19; - break; - - case 240: - power_level = 18; - break; - - case 360: - power_level = 16; - break; - - case 480: - power_level = 15; - break; - - case 540: - power_level = 14; - break; - default: - agnx_bug("Error rate setting\n"); - } - - if (power_level && (antennas_num == 2)) - power_level -= 3; - - return power_level; -} - -static inline void fill_agnx_hdr(struct agnx_priv *priv, struct agnx_info *tx_info) -{ - struct agnx_hdr *txhdr = (struct agnx_hdr *)tx_info->skb->data; - size_t len; - u16 fc = le16_to_cpu(*(__le16 *)&tx_info->hdr); - u32 reg; - - memset(txhdr, 0, sizeof(*txhdr)); - -/* reg = agnx_set_bits(STATION_ID, STATION_ID_SHIFT, LOCAL_STAID); */ - reg = agnx_set_bits(STATION_ID, STATION_ID_SHIFT, BSSID_STAID); - reg |= agnx_set_bits(WORKQUEUE_ID, WORKQUEUE_ID_SHIFT, 0); - txhdr->reg4 = cpu_to_be32(reg); - - /* Set the Hardware Sequence Number to 1? */ - reg = agnx_set_bits(SEQUENCE_NUMBER, SEQUENCE_NUMBER_SHIFT, 0); -/* reg = agnx_set_bits(SEQUENCE_NUMBER, SEQUENCE_NUMBER_SHIFT, 1); */ - reg |= agnx_set_bits(MAC_HDR_LEN, MAC_HDR_LEN_SHIFT, tx_info->hdr_len); - txhdr->reg1 = cpu_to_be32(reg); - /* Set the agnx_hdr's MAC header */ - memcpy(txhdr->mac_hdr, &tx_info->hdr, tx_info->hdr_len); - - reg = agnx_set_bits(ACK, ACK_SHIFT, 1); -/* reg = agnx_set_bits(ACK, ACK_SHIFT, 0); */ - reg |= agnx_set_bits(MULTICAST, MULTICAST_SHIFT, 0); -/* reg |= agnx_set_bits(MULTICAST, MULTICAST_SHIFT, 1); */ - reg |= agnx_set_bits(RELAY, RELAY_SHIFT, 0); - reg |= agnx_set_bits(TM, TM_SHIFT, 0); - txhdr->reg0 = cpu_to_be32(reg); - - /* Set the long and short retry limits */ - txhdr->tx.short_retry_limit = tx_info->txi->control.rates[0].count; - txhdr->tx.long_retry_limit = tx_info->txi->control.rates[0].count; - - /* FIXME */ - len = tx_info->skb->len - sizeof(*txhdr) + tx_info->hdr_len + FCS_LEN; - if (fc & IEEE80211_FCTL_PROTECTED) - len += 8; - len = 2398; - reg = agnx_set_bits(FRAG_SIZE, FRAG_SIZE_SHIFT, len); - len = tx_info->skb->len - sizeof(*txhdr); - reg |= agnx_set_bits(PAYLOAD_LEN, PAYLOAD_LEN_SHIFT, len); - txhdr->reg3 = cpu_to_be32(reg); - - route_flag_set(txhdr); -} /* fill_hdr */ - -static void txm_power_set(struct agnx_priv *priv, - struct ieee80211_tx_info *txi) -{ - struct agnx_sta_power power; - u32 reg; - - /* FIXME */ - if (txi->control.rates[0].idx < 0) { - /* For B mode Short Preamble */ - reg = agnx_set_bits(PHY_MODE, PHY_MODE_SHIFT, AGNX_MODE_80211B_SHORT); -/* control->tx_rate = -control->tx_rate; */ - } else - reg = agnx_set_bits(PHY_MODE, PHY_MODE_SHIFT, AGNX_MODE_80211G); -/* reg = agnx_set_bits(PHY_MODE, PHY_MODE_SHIFT, AGNX_MODE_80211B_LONG); */ - reg |= agnx_set_bits(SIGNAL, SIGNAL_SHIFT, 0xB); - reg |= agnx_set_bits(RATE, RATE_SHIFT, 0xB); -/* reg |= agnx_set_bits(POWER_LEVEL, POWER_LEVEL_SHIFT, 15); */ - reg |= agnx_set_bits(POWER_LEVEL, POWER_LEVEL_SHIFT, 20); - /* if rate < 11M set it to 0 */ - reg |= agnx_set_bits(NUM_TRANSMITTERS, NUM_TRANSMITTERS_SHIFT, 1); -/* reg |= agnx_set_bits(EDCF, EDCF_SHIFT, 1); */ -/* reg |= agnx_set_bits(TIFS, TIFS_SHIFT, 1); */ - - power.reg = reg; -/* power.reg = cpu_to_le32(reg); */ - -/* set_sta_power(priv, &power, LOCAL_STAID); */ - set_sta_power(priv, &power, BSSID_STAID); -} - -static inline int tx_packet_check(struct sk_buff *skb) -{ - unsigned int ieee_len = ieee80211_get_hdrlen_from_skb(skb); - if (skb->len > 2048) { - printk(KERN_ERR PFX "length is %d\n", skb->len); - agnx_bug("Too long TX skb"); - return -1; - } - /* FIXME */ - if (skb->len == ieee_len) { - printk(PFX "A strange TX packet\n"); - return -1; - /* tx_faile_irqsafe(); */ - } - return 0; -} - -static int __agnx_tx(struct agnx_priv *priv, struct sk_buff *skb, - struct agnx_ring *ring) -{ - struct agnx_desc *hdr_desc, *frag_desc; - struct agnx_info *hdr_info, *frag_info; - struct ieee80211_tx_info *txi = IEEE80211_SKB_CB(skb); - unsigned long flags; - unsigned int i; - - spin_lock_irqsave(&priv->lock, flags); - - /* The RX interrupt need be Disable until this TX packet - is handled in the next tx interrupt */ - disable_rx_interrupt(priv); - - i = ring->idx; - ring->idx += 2; -/* if (priv->txm_idx - priv->txm_idx_sent == AGNX_TXM_RING_SIZE - 2) */ -/* ieee80211_stop_queue(priv->hw, 0); */ - - /* Set agnx header's info and desc */ - i %= ring->size; - hdr_desc = ring->desc + i; - hdr_info = ring->info + i; - hdr_info->hdr_len = ieee80211_get_hdrlen_from_skb(skb); - memcpy(&hdr_info->hdr, skb->data, hdr_info->hdr_len); - - /* Add the agnx header to the front of the SKB */ - skb_push(skb, sizeof(struct agnx_hdr) - hdr_info->hdr_len); - - hdr_info->txi = txi; - hdr_info->dma_len = sizeof(struct agnx_hdr); - hdr_info->skb = skb; - hdr_info->type = HEADER; - fill_agnx_hdr(priv, hdr_info); - hdr_info->mapping = pci_map_single(priv->pdev, skb->data, - hdr_info->dma_len, PCI_DMA_TODEVICE); - do { - u32 frag = 0; - frag |= agnx_set_bits(FIRST_FRAG, FIRST_FRAG_SHIFT, 1); - frag |= agnx_set_bits(LAST_FRAG, LAST_FRAG_SHIFT, 0); - frag |= agnx_set_bits(PACKET_LEN, PACKET_LEN_SHIFT, skb->len); - frag |= agnx_set_bits(FIRST_FRAG_LEN, FIRST_FRAG_LEN_SHIFT, 1); - frag |= agnx_set_bits(OWNER, OWNER_SHIFT, 1); - hdr_desc->frag = cpu_to_be32(frag); - } while (0); - hdr_desc->dma_addr = cpu_to_be32(hdr_info->mapping); - - - /* Set Frag's info and desc */ - i = (i + 1) % ring->size; - frag_desc = ring->desc + i; - frag_info = ring->info + i; - memcpy(frag_info, hdr_info, sizeof(struct agnx_info)); - frag_info->type = PACKET; - frag_info->dma_len = skb->len - hdr_info->dma_len; - frag_info->mapping = pci_map_single(priv->pdev, skb->data + hdr_info->dma_len, - frag_info->dma_len, PCI_DMA_TODEVICE); - do { - u32 frag = 0; - frag |= agnx_set_bits(FIRST_FRAG, FIRST_FRAG_SHIFT, 0); - frag |= agnx_set_bits(LAST_FRAG, LAST_FRAG_SHIFT, 1); - frag |= agnx_set_bits(PACKET_LEN, PACKET_LEN_SHIFT, skb->len); - frag |= agnx_set_bits(SUB_FRAG_LEN, SUB_FRAG_LEN_SHIFT, frag_info->dma_len); - frag_desc->frag = cpu_to_be32(frag); - } while (0); - frag_desc->dma_addr = cpu_to_be32(frag_info->mapping); - - txm_power_set(priv, txi); - -/* do { */ -/* int j; */ -/* size_t len; */ -/* len = skb->len - hdr_info->dma_len + hdr_info->hdr_len; */ -/* if (len == 614) { */ -/* agnx_print_desc(hdr_desc); */ -/* agnx_print_desc(frag_desc); */ -/* agnx_print_tx_hdr((struct agnx_hdr *)skb->data); */ -/* agnx_print_sta_power(priv, LOCAL_STAID); */ -/* agnx_print_sta(priv, LOCAL_STAID); */ -/* for (j = 0; j < 8; j++) */ -/* agnx_print_sta_tx_wq(priv, LOCAL_STAID, j); */ -/* agnx_print_sta_power(priv, BSSID_STAID); */ -/* agnx_print_sta(priv, BSSID_STAID); */ -/* for (j = 0; j < 8; j++) */ -/* agnx_print_sta_tx_wq(priv, BSSID_STAID, j); */ -/* } */ -/* } while (0); */ - - spin_unlock_irqrestore(&priv->lock, flags); - - /* FIXME ugly code */ - /* Trigger TXM */ - do { - u32 reg; - reg = (ioread32(priv->ctl + AGNX_CIR_TXMCTL)); - reg |= 0x8; - iowrite32((reg), priv->ctl + AGNX_CIR_TXMCTL); - } while (0); - - /* Trigger TXD */ - do { - u32 reg; - reg = (ioread32(priv->ctl + AGNX_CIR_TXDCTL)); - reg |= 0x8; - iowrite32((reg), priv->ctl + AGNX_CIR_TXDCTL); - } while (0); - - return 0; -} - -int _agnx_tx(struct agnx_priv *priv, struct sk_buff *skb) -{ - u16 fctl; - - if (tx_packet_check(skb)) - return 0; - -/* print_hex_dump_bytes("agnx: TX_PACKET: ", DUMP_PREFIX_NONE, */ -/* skb->data, skb->len); */ - - fctl = le16_to_cpu(*((__le16 *)skb->data)); - - if ((fctl & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA) - return __agnx_tx(priv, skb, &priv->txd); - else - return __agnx_tx(priv, skb, &priv->txm); -} diff --git a/drivers/staging/agnx/xmit.h b/drivers/staging/agnx/xmit.h deleted file mode 100644 index 93ac4157e697..000000000000 --- a/drivers/staging/agnx/xmit.h +++ /dev/null @@ -1,250 +0,0 @@ -#ifndef AGNX_XMIT_H_ -#define AGNX_XMIT_H_ - -#include <net/mac80211.h> - -struct agnx_priv; - -static inline u32 agnx_set_bits(u32 mask, u8 shift, u32 value) -{ - return (value << shift) & mask; -} - -static inline u32 agnx_get_bits(u32 mask, u8 shift, u32 value) -{ - return (value & mask) >> shift; -} - - -struct agnx_rx { - __be16 rx_packet_duration; /* RX Packet Duration */ - __be16 replay_cnt; /* Replay Count */ -} __attribute__((__packed__)); - - -struct agnx_tx { - u8 long_retry_limit; /* Long Retry Limit */ - u8 short_retry_limit; /* Short Retry Limit */ - u8 long_retry_cnt; /* Long Retry Count */ - u8 short_retry_cnt; /* Short Retry Count */ -} __attribute__((__packed__)); - - -/* Copy from bcm43xx */ -#define P4D_BYT3S(magic, nr_bytes) u8 __p4dding##magic[nr_bytes] -#define P4D_BYTES(line, nr_bytes) P4D_BYT3S(line, nr_bytes) -#define PAD_BYTES(nr_bytes) P4D_BYTES(__LINE__, nr_bytes) - -#define P4D_BIT3S(magic, nr_bits) __be32 __padding##magic:nr_bits -#define P4D_BITS(line, nr_bits) P4D_BIT3S(line, nr_bits) -#define PAD_BITS(nr_bits) P4D_BITS(__LINE__, nr_bits) - - -struct agnx_hdr { - __be32 reg0; -#define RTS 0x80000000 /* RTS */ -#define RTS_SHIFT 31 -#define MULTICAST 0x40000000 /* multicast */ -#define MULTICAST_SHIFT 30 -#define ACK 0x30000000 /* ACK */ -#define ACK_SHIFT 28 -#define TM 0x08000000 /* TM */ -#define TM_SHIFT 27 -#define RELAY 0x04000000 /* Relay */ -#define RELAY_SHIFT 26 -/* PAD_BITS(4); */ -#define REVISED_FCS 0x00380000 /* revised FCS */ -#define REVISED_FCS_SHIFT 19 -#define NEXT_BUFFER_ADDR 0x0007FFFF /* Next Buffer Address */ -#define NEXT_BUFFER_ADDR_SHIFT 0 - - __be32 reg1; -#define MAC_HDR_LEN 0xFC000000 /* MAC Header Length */ -#define MAC_HDR_LEN_SHIFT 26 -#define DURATION_OVERIDE 0x02000000 /* Duration Override */ -#define DURATION_OVERIDE_SHIFT 25 -#define PHY_HDR_OVERIDE 0x01000000 /* PHY Header Override */ -#define PHY_HDR_OVERIDE_SHIFT 24 -#define CRC_FAIL 0x00800000 /* CRC fail */ -#define CRC_FAIL_SHIFT 23 -/* PAD_BITS(1); */ -#define SEQUENCE_NUMBER 0x00200000 /* Sequence Number */ -#define SEQUENCE_NUMBER_SHIFT 21 -/* PAD_BITS(2); */ -#define BUFF_HEAD_ADDR 0x0007FFFF /* Buffer Head Address */ -#define BUFF_HEAD_ADDR_SHIFT 0 - - __be32 reg2; -#define PDU_COUNT 0xFC000000 /* PDU Count */ -#define PDU_COUNT_SHIFT 26 -/* PAD_BITS(3); */ -#define WEP_KEY 0x00600000 /* WEP Key # */ -#define WEP_KEY_SHIFT 21 -#define USES_WEP_KEY 0x00100000 /* Uses WEP Key */ -#define USES_WEP_KEY_SHIFT 20 -#define KEEP_ALIVE 0x00080000 /* Keep alive */ -#define KEEP_ALIVE_SHIFT 19 -#define BUFF_TAIL_ADDR 0x0007FFFF /* Buffer Tail Address */ -#define BUFF_TAIL_ADDR_SHIFT 0 - - __be32 reg3; -#define CTS_11G 0x80000000 /* CTS in 11g */ -#define CTS_11G_SHIFT 31 -#define RTS_11G 0x40000000 /* RTS in 11g */ -#define RTS_11G_SHIFT 30 -/* PAD_BITS(2); */ -#define FRAG_SIZE 0x0FFF0000 /* fragment size */ -#define FRAG_SIZE_SHIFT 16 -#define PAYLOAD_LEN 0x0000FFF0 /* payload length */ -#define PAYLOAD_LEN_SHIFT 4 -#define FRAG_NUM 0x0000000F /* number of frags */ -#define FRAG_NUM_SHIFT 0 - - __be32 reg4; -/* PAD_BITS(4); */ -#define RELAY_STAID 0x0FFF0000 /* relayStald */ -#define RELAY_STAID_SHIFT 16 -#define STATION_ID 0x0000FFF0 /* Station ID */ -#define STATION_ID_SHIFT 4 -#define WORKQUEUE_ID 0x0000000F /* Workqueue ID */ -#define WORKQUEUE_ID_SHIFT 0 - - /* FIXME this register maybe is LE? */ - __be32 reg5; -/* PAD_BITS(4); */ -#define ROUTE_HOST 0x0F000000 -#define ROUTE_HOST_SHIFT 24 -#define ROUTE_CARD_CPU 0x00F00000 -#define ROUTE_CARD_CPU_SHIFT 20 -#define ROUTE_ENCRYPTION 0x000F0000 -#define ROUTE_ENCRYPTION_SHIFT 16 -#define ROUTE_TX 0x0000F000 -#define ROUTE_TX_SHIFT 12 -#define ROUTE_RX1 0x00000F00 -#define ROUTE_RX1_SHIFT 8 -#define ROUTE_RX2 0x000000F0 -#define ROUTE_RX2_SHIFT 4 -#define ROUTE_COMPRESSION 0x0000000F -#define ROUTE_COMPRESSION_SHIFT 0 - - __be32 _11g0; /* 11g */ - __be32 _11g1; /* 11g */ - __be32 _11b0; /* 11b */ - __be32 _11b1; /* 11b */ - u8 mac_hdr[32]; /* MAC header */ - - __be16 rts_duration; /* RTS duration */ - __be16 last_duration; /* Last duration */ - __be16 sec_last_duration; /* Second to Last duration */ - __be16 other_duration; /* Other duration */ - __be16 tx_last_duration; /* TX Last duration */ - __be16 tx_other_duration; /* TX Other Duration */ - __be16 last_11g_len; /* Length of last 11g */ - __be16 other_11g_len; /* Lenght of other 11g */ - - __be16 last_11b_len; /* Length of last 11b */ - __be16 other_11b_len; /* Lenght of other 11b */ - - - __be16 reg6; -#define MBF 0xF000 /* mbf */ -#define MBF_SHIFT 12 -#define RSVD4 0x0FFF /* rsvd4 */ -#define RSVD4_SHIFT 0 - - __be16 rx_frag_stat; /* RX fragmentation status */ - - __be32 time_stamp; /* TimeStamp */ - __be32 phy_stats_hi; /* PHY stats hi */ - __be32 phy_stats_lo; /* PHY stats lo */ - __be32 mic_key0; /* MIC key 0 */ - __be32 mic_key1; /* MIC key 1 */ - - union { /* RX/TX Union */ - struct agnx_rx rx; - struct agnx_tx tx; - }; - - u8 rx_channel; /* Recieve Channel */ - PAD_BYTES(3); - - u8 reserved[4]; -} __attribute__((__packed__)); - - -struct agnx_desc { -#define PACKET_LEN 0xFFF00000 -#define PACKET_LEN_SHIFT 20 -/* ------------------------------------------------ */ -#define FIRST_PACKET_MASK 0x00080000 -#define FIRST_PACKET_MASK_SHIFT 19 -#define FIRST_RESERV2 0x00040000 -#define FIRST_RESERV2_SHIFT 18 -#define FIRST_TKIP_ERROR 0x00020000 -#define FIRST_TKIP_ERROR_SHIFT 17 -#define FIRST_TKIP_PACKET 0x00010000 -#define FIRST_TKIP_PACKET_SHIFT 16 -#define FIRST_RESERV1 0x0000F000 -#define FIRST_RESERV1_SHIFT 12 -#define FIRST_FRAG_LEN 0x00000FF8 -#define FIRST_FRAG_LEN_SHIFT 3 -/* ------------------------------------------------ */ -#define SUB_RESERV2 0x000c0000 -#define SUB_RESERV2_SHIFT 18 -#define SUB_TKIP_ERROR 0x00020000 -#define SUB_TKIP_ERROR_SHIFT 17 -#define SUB_TKIP_PACKET 0x00010000 -#define SUB_TKIP_PACKET_SHIFT 16 -#define SUB_RESERV1 0x00008000 -#define SUB_RESERV1_SHIFT 15 -#define SUB_FRAG_LEN 0x00007FF8 -#define SUB_FRAG_LEN_SHIFT 3 -/* ------------------------------------------------ */ -#define FIRST_FRAG 0x00000004 -#define FIRST_FRAG_SHIFT 2 -#define LAST_FRAG 0x00000002 -#define LAST_FRAG_SHIFT 1 -#define OWNER 0x00000001 -#define OWNER_SHIFT 0 - __be32 frag; - __be32 dma_addr; -} __attribute__((__packed__)); - -enum {HEADER, PACKET}; - -struct agnx_info { - struct sk_buff *skb; - dma_addr_t mapping; - u32 dma_len; /* dma buffer len */ - /* Below fields only usful for tx */ - u32 hdr_len; /* ieee80211 header length */ - unsigned int type; - struct ieee80211_tx_info *txi; - struct ieee80211_hdr hdr; -}; - - -struct agnx_ring { - struct agnx_desc *desc; - dma_addr_t dma; - struct agnx_info *info; - /* Will lead to overflow when sent packet number enough? */ - unsigned int idx; - unsigned int idx_sent; /* only usful for txd and txm */ - unsigned int size; -}; - -#define AGNX_RX_RING_SIZE 128 -#define AGNX_TXD_RING_SIZE 256 -#define AGNX_TXM_RING_SIZE 128 - -void disable_rx_interrupt(struct agnx_priv *priv); -void enable_rx_interrupt(struct agnx_priv *priv); -int fill_rings(struct agnx_priv *priv); -void unfill_rings(struct agnx_priv *priv); -void handle_rx_irq(struct agnx_priv *priv); -void handle_txd_irq(struct agnx_priv *priv); -void handle_txm_irq(struct agnx_priv *priv); -void handle_other_irq(struct agnx_priv *priv); -int _agnx_tx(struct agnx_priv *priv, struct sk_buff *skb); -#endif /* AGNX_XMIT_H_ */ diff --git a/drivers/staging/android/Kconfig b/drivers/staging/android/Kconfig index 247194992374..eb675635ae60 100644 --- a/drivers/staging/android/Kconfig +++ b/drivers/staging/android/Kconfig @@ -2,6 +2,7 @@ menu "Android" config ANDROID bool "Android Drivers" + depends on BROKEN default N ---help--- Enable support for various drivers needed on the Android platform diff --git a/drivers/staging/b3dfg/b3dfg.c b/drivers/staging/b3dfg/b3dfg.c index 94c5d27d24d7..cda26bb493b3 100644 --- a/drivers/staging/b3dfg/b3dfg.c +++ b/drivers/staging/b3dfg/b3dfg.c @@ -36,6 +36,7 @@ #include <linux/wait.h> #include <linux/mm.h> #include <linux/uaccess.h> +#include <linux/sched.h> static unsigned int b3dfg_nbuf = 2; diff --git a/drivers/staging/comedi/Kconfig b/drivers/staging/comedi/Kconfig index af723cb9d08f..d63c889ce557 100644 --- a/drivers/staging/comedi/Kconfig +++ b/drivers/staging/comedi/Kconfig @@ -1,7 +1,7 @@ config COMEDI tristate "Data acquisition support (comedi)" default N - depends on m + depends on m && (PCI || PCMCIA || PCCARD || USB) ---help--- Enable support a wide range of data acquisition devices for Linux. diff --git a/drivers/staging/comedi/comedi_fops.c b/drivers/staging/comedi/comedi_fops.c index f54bb9b3ee37..aaad76e0a76a 100644 --- a/drivers/staging/comedi/comedi_fops.c +++ b/drivers/staging/comedi/comedi_fops.c @@ -2337,7 +2337,7 @@ static int resize_async_buffer(struct comedi_device *dev, } DPRINTK("comedi%i subd %d buffer resized to %i bytes\n", - dev->minor, s - dev->subdevices, async->prealloc_bufsz); + dev->minor, (int)(s - dev->subdevices), async->prealloc_bufsz); return 0; } diff --git a/drivers/staging/comedi/drivers/cb_das16_cs.c b/drivers/staging/comedi/drivers/cb_das16_cs.c index 12d12b43a6f1..80c0df8656f3 100644 --- a/drivers/staging/comedi/drivers/cb_das16_cs.c +++ b/drivers/staging/comedi/drivers/cb_das16_cs.c @@ -744,7 +744,7 @@ static int das16cs_pcmcia_attach(struct pcmcia_device *link) /* Initialize the pcmcia_device structure */ /* Interrupt setup */ - link->irq.Attributes = IRQ_TYPE_EXCLUSIVE; + link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING; link->irq.IRQInfo1 = IRQ_LEVEL_ID; link->irq.Handler = NULL; diff --git a/drivers/staging/comedi/drivers/cb_pcidio.c b/drivers/staging/comedi/drivers/cb_pcidio.c index 4d10bc31d461..09e6e3bdfb3e 100644 --- a/drivers/staging/comedi/drivers/cb_pcidio.c +++ b/drivers/staging/comedi/drivers/cb_pcidio.c @@ -53,7 +53,8 @@ Passing a zero for an option is the same as leaving it unspecified. * Some drivers use arrays such as this, other do not. */ struct pcidio_board { - const char *name; /* anme of the board */ + const char *name; /* name of the board */ + int dev_id; int n_8255; /* number of 8255 chips on board */ /* indices of base address regions */ @@ -64,18 +65,21 @@ struct pcidio_board { static const struct pcidio_board pcidio_boards[] = { { .name = "pci-dio24", + .dev_id = 0x0028, .n_8255 = 1, .pcicontroler_badrindex = 1, .dioregs_badrindex = 2, }, { .name = "pci-dio24h", + .dev_id = 0x0014, .n_8255 = 1, .pcicontroler_badrindex = 1, .dioregs_badrindex = 2, }, { .name = "pci-dio48h", + .dev_id = 0x000b, .n_8255 = 2, .pcicontroler_badrindex = 0, .dioregs_badrindex = 1, @@ -206,7 +210,7 @@ static int pcidio_attach(struct comedi_device *dev, struct comedi_devconfig *it) continue; /* loop through cards supported by this driver */ for (index = 0; index < ARRAY_SIZE(pcidio_boards); index++) { - if (pcidio_pci_table[index].device != pcidev->device) + if (pcidio_boards[index].dev_id != pcidev->device) continue; /* was a particular bus/slot requested? */ diff --git a/drivers/staging/comedi/drivers/jr3_pci.c b/drivers/staging/comedi/drivers/jr3_pci.c index 14bf29bf5781..0d2c2eb23b23 100644 --- a/drivers/staging/comedi/drivers/jr3_pci.c +++ b/drivers/staging/comedi/drivers/jr3_pci.c @@ -515,6 +515,7 @@ static struct poll_delay_t jr3_pci_poll_subdevice(struct comedi_subdevice *s) { struct poll_delay_t result = poll_delay_min_max(1000, 2000); struct jr3_pci_subdev_private *p = s->private; + int i; if (p) { volatile struct jr3_channel *channel = p->channel; @@ -570,18 +571,11 @@ static struct poll_delay_t jr3_pci_poll_subdevice(struct comedi_subdevice *s) p->serial_no); /* Transformation all zeros */ - transf.link[0].link_type = - (enum link_types)0; - transf.link[0].link_amount = 0; - transf.link[1].link_type = - (enum link_types)0; - transf.link[1].link_amount = 0; - transf.link[2].link_type = - (enum link_types)0; - transf.link[2].link_amount = 0; - transf.link[3].link_type = - (enum link_types)0; - transf.link[3].link_amount = 0; + for (i = 0; i < ARRAY_SIZE(transf.link); i++) { + transf.link[i].link_type = + (enum link_types)0; + transf.link[i].link_amount = 0; + } set_transforms(channel, transf, 0); use_transform(channel, 0); diff --git a/drivers/staging/comedi/drivers/me_daq.c b/drivers/staging/comedi/drivers/me_daq.c index 2cda7ad1d32f..80e192d2e77e 100644 --- a/drivers/staging/comedi/drivers/me_daq.c +++ b/drivers/staging/comedi/drivers/me_daq.c @@ -51,6 +51,7 @@ from http://www.comedi.org */ #include <linux/interrupt.h> +#include <linux/sched.h> #include "../comedidev.h" #include "comedi_pci.h" diff --git a/drivers/staging/comedi/drivers/ni_65xx.c b/drivers/staging/comedi/drivers/ni_65xx.c index 6b118c15b49e..bbf75eb6d7f2 100644 --- a/drivers/staging/comedi/drivers/ni_65xx.c +++ b/drivers/staging/comedi/drivers/ni_65xx.c @@ -418,15 +418,15 @@ static int ni_65xx_dio_insn_bits(struct comedi_device *dev, return -EINVAL; base_bitfield_channel = CR_CHAN(insn->chanspec); for (j = 0; j < max_ports_per_bitfield; ++j) { + const unsigned port_offset = ni_65xx_port_by_channel(base_bitfield_channel) + j; const unsigned port = - sprivate(s)->base_port + - ni_65xx_port_by_channel(base_bitfield_channel) + j; + sprivate(s)->base_port + port_offset; unsigned base_port_channel; unsigned port_mask, port_data, port_read_bits; int bitshift; if (port >= ni_65xx_total_num_ports(board(dev))) break; - base_port_channel = port * ni_65xx_channels_per_port; + base_port_channel = port_offset * ni_65xx_channels_per_port; port_mask = data[0]; port_data = data[1]; bitshift = base_port_channel - base_bitfield_channel; @@ -457,6 +457,12 @@ static int ni_65xx_dio_insn_bits(struct comedi_device *dev, port_read_bits = readb(private(dev)->mite->daq_io_addr + Port_Data(port)); /* printk("read 0x%x from port %i\n", port_read_bits, port); */ + if (s->type == COMEDI_SUBD_DO && board(dev)->invert_outputs) { + /* Outputs inverted, so invert value read back from + * DO subdevice. (Does not apply to boards with DIO + * subdevice.) */ + port_read_bits ^= 0xFF; + } if (bitshift > 0) { port_read_bits <<= bitshift; } else { diff --git a/drivers/staging/comedi/drivers/ni_daq_700.c b/drivers/staging/comedi/drivers/ni_daq_700.c index 6a7797604c97..ec31a3970664 100644 --- a/drivers/staging/comedi/drivers/ni_daq_700.c +++ b/drivers/staging/comedi/drivers/ni_daq_700.c @@ -520,7 +520,7 @@ static int dio700_cs_attach(struct pcmcia_device *link) link->priv = local; /* Interrupt setup */ - link->irq.Attributes = IRQ_TYPE_EXCLUSIVE; + link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING; link->irq.IRQInfo1 = IRQ_LEVEL_ID; link->irq.Handler = NULL; diff --git a/drivers/staging/comedi/drivers/ni_daq_dio24.c b/drivers/staging/comedi/drivers/ni_daq_dio24.c index b06e81c526e8..0700a8bddd1e 100644 --- a/drivers/staging/comedi/drivers/ni_daq_dio24.c +++ b/drivers/staging/comedi/drivers/ni_daq_dio24.c @@ -271,7 +271,7 @@ static int dio24_cs_attach(struct pcmcia_device *link) link->priv = local; /* Interrupt setup */ - link->irq.Attributes = IRQ_TYPE_EXCLUSIVE; + link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING; link->irq.IRQInfo1 = IRQ_LEVEL_ID; link->irq.Handler = NULL; diff --git a/drivers/staging/comedi/drivers/ni_labpc_cs.c b/drivers/staging/comedi/drivers/ni_labpc_cs.c index 57aecfa883c7..a3053b8da1c6 100644 --- a/drivers/staging/comedi/drivers/ni_labpc_cs.c +++ b/drivers/staging/comedi/drivers/ni_labpc_cs.c @@ -246,7 +246,7 @@ static int labpc_cs_attach(struct pcmcia_device *link) link->priv = local; /* Interrupt setup */ - link->irq.Attributes = IRQ_TYPE_EXCLUSIVE | IRQ_FORCED_PULSE; + link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING | IRQ_FORCED_PULSE; link->irq.IRQInfo1 = IRQ_INFO2_VALID | IRQ_PULSE_ID; link->irq.Handler = NULL; diff --git a/drivers/staging/comedi/drivers/ni_mio_common.c b/drivers/staging/comedi/drivers/ni_mio_common.c index e3ffb067ead1..753ee0512342 100644 --- a/drivers/staging/comedi/drivers/ni_mio_common.c +++ b/drivers/staging/comedi/drivers/ni_mio_common.c @@ -62,6 +62,7 @@ /* #define DEBUG_STATUS_B */ #include <linux/interrupt.h> +#include <linux/sched.h> #include "8255.h" #include "mite.h" #include "comedi_fc.h" diff --git a/drivers/staging/comedi/drivers/ni_mio_cs.c b/drivers/staging/comedi/drivers/ni_mio_cs.c index b7322963cf78..9aef87fc81dc 100644 --- a/drivers/staging/comedi/drivers/ni_mio_cs.c +++ b/drivers/staging/comedi/drivers/ni_mio_cs.c @@ -273,7 +273,7 @@ static int cs_attach(struct pcmcia_device *link) { link->io.Attributes1 = IO_DATA_PATH_WIDTH_16; link->io.NumPorts1 = 16; - link->irq.Attributes = IRQ_TYPE_EXCLUSIVE; + link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING; link->irq.IRQInfo1 = IRQ_LEVEL_ID; link->conf.Attributes = CONF_ENABLE_IRQ; link->conf.IntType = INT_MEMORY_AND_IO; diff --git a/drivers/staging/comedi/drivers/ni_pcidio.c b/drivers/staging/comedi/drivers/ni_pcidio.c index 52b2eca9e73d..d544698f2414 100644 --- a/drivers/staging/comedi/drivers/ni_pcidio.c +++ b/drivers/staging/comedi/drivers/ni_pcidio.c @@ -70,6 +70,7 @@ comedi_nonfree_firmware tarball available from http://www.comedi.org /* #define DEBUG_FLAGS */ #include <linux/interrupt.h> +#include <linux/sched.h> #include "../comedidev.h" #include "mite.h" diff --git a/drivers/staging/comedi/drivers/ni_pcimio.c b/drivers/staging/comedi/drivers/ni_pcimio.c index 19d87553d906..24c8b8ed5b4c 100644 --- a/drivers/staging/comedi/drivers/ni_pcimio.c +++ b/drivers/staging/comedi/drivers/ni_pcimio.c @@ -29,7 +29,7 @@ Devices: [National Instruments] PCI-MIO-16XE-50 (ni_pcimio), PCI-MIO-16XE-10, PXI-6030E, PCI-MIO-16E-1, PCI-MIO-16E-4, PCI-6014, PCI-6040E, PXI-6040E, PCI-6030E, PCI-6031E, PCI-6032E, PCI-6033E, PCI-6071E, PCI-6023E, PCI-6024E, PCI-6025E, PXI-6025E, PCI-6034E, PCI-6035E, PCI-6052E, - PCI-6110, PCI-6111, PCI-6220, PCI-6221, PCI-6224, PXI-6224, PCI-6225, + PCI-6110, PCI-6111, PCI-6220, PCI-6221, PCI-6224, PXI-6224, PCI-6225, PXI-6225, PCI-6229, PCI-6250, PCI-6251, PCIe-6251, PCI-6254, PCI-6259, PCIe-6259, PCI-6280, PCI-6281, PXI-6281, PCI-6284, PCI-6289, PCI-6711, PXI-6711, PCI-6713, PXI-6713, @@ -179,6 +179,7 @@ static DEFINE_PCI_DEVICE_TABLE(ni_pci_table) = { PCI_VENDOR_ID_NATINST, 0x70f2, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { PCI_VENDOR_ID_NATINST, 0x710d, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { PCI_VENDOR_ID_NATINST, 0x716c, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { + PCI_VENDOR_ID_NATINST, 0x716d, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { PCI_VENDOR_ID_NATINST, 0x717f, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { PCI_VENDOR_ID_NATINST, 0x71bc, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { PCI_VENDOR_ID_NATINST, 0x717d, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, { @@ -953,6 +954,25 @@ static const struct ni_board_struct ni_boards[] = { .has_8255 = 0, }, { + .device_id = 0x716d, + .name = "pxi-6225", + .n_adchan = 80, + .adbits = 16, + .ai_fifo_depth = 4095, + .gainlkup = ai_gain_622x, + .ai_speed = 4000, + .n_aochan = 2, + .aobits = 16, + .ao_fifo_depth = 8191, + .ao_range_table = &range_ni_M_622x_ao, + .reg_type = ni_reg_622x, + .ao_unipolar = 0, + .ao_speed = 1200, + .num_p0_dio_channels = 32, + .caldac = {caldac_none}, + .has_8255 = 0, + }, + { .device_id = 0x70aa, .name = "pci-6229", .n_adchan = 32, diff --git a/drivers/staging/comedi/drivers/quatech_daqp_cs.c b/drivers/staging/comedi/drivers/quatech_daqp_cs.c index f63bdc35cffd..344b82353e08 100644 --- a/drivers/staging/comedi/drivers/quatech_daqp_cs.c +++ b/drivers/staging/comedi/drivers/quatech_daqp_cs.c @@ -1079,7 +1079,7 @@ static int daqp_cs_attach(struct pcmcia_device *link) link->priv = local; /* Interrupt setup */ - link->irq.Attributes = IRQ_TYPE_EXCLUSIVE | IRQ_HANDLE_PRESENT; + link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING | IRQ_HANDLE_PRESENT; link->irq.IRQInfo1 = IRQ_LEVEL_ID; link->irq.Handler = daqp_interrupt; link->irq.Instance = local; diff --git a/drivers/staging/comedi/drivers/s526.c b/drivers/staging/comedi/drivers/s526.c index b89e1ec267c5..07c21e686f27 100644 --- a/drivers/staging/comedi/drivers/s526.c +++ b/drivers/staging/comedi/drivers/s526.c @@ -43,6 +43,7 @@ comedi_config /dev/comedi0 s526 0x2C0,0x3 #include "../comedidev.h" #include <linux/ioport.h> +#include <asm/byteorder.h> #define S526_SIZE 64 @@ -113,6 +114,7 @@ static const int s526_ports[] = { }; struct counter_mode_register_t { +#if defined (__LITTLE_ENDIAN_BITFIELD) unsigned short coutSource:1; unsigned short coutPolarity:1; unsigned short autoLoadResetRcap:3; @@ -124,12 +126,27 @@ struct counter_mode_register_t { unsigned short outputRegLatchCtrl:1; unsigned short preloadRegSel:1; unsigned short reserved:1; + #elif defined(__BIG_ENDIAN_BITFIELD) + unsigned short reserved:1; + unsigned short preloadRegSel:1; + unsigned short outputRegLatchCtrl:1; + unsigned short countDirCtrl:1; + unsigned short countDir:1; + unsigned short clockSource:2; + unsigned short ctEnableCtrl:2; + unsigned short hwCtEnableSource:2; + unsigned short autoLoadResetRcap:3; + unsigned short coutPolarity:1; + unsigned short coutSource:1; +#else +#error Unknown bit field order +#endif }; -union { +union cmReg { struct counter_mode_register_t reg; unsigned short value; -} cmReg; +}; #define MAX_GPCT_CONFIG_DATA 6 @@ -285,6 +302,7 @@ static int s526_attach(struct comedi_device *dev, struct comedi_devconfig *it) int i, n; /* short value; */ /* int subdev_channel = 0; */ + union cmReg cmReg; printk("comedi%d: s526: ", dev->minor); @@ -375,7 +393,7 @@ static int s526_attach(struct comedi_device *dev, struct comedi_devconfig *it) if (thisboard->have_dio) { s->type = COMEDI_SUBD_DIO; s->subdev_flags = SDF_READABLE | SDF_WRITABLE; - s->n_chan = 2; + s->n_chan = 8; s->maxdata = 1; s->range_table = &range_digital; s->insn_bits = s526_dio_insn_bits; @@ -435,11 +453,11 @@ static int s526_attach(struct comedi_device *dev, struct comedi_devconfig *it) udelay(1000); printk("Read back mode reg=0x%04x\n", inw(ADDR_CHAN_REG(REG_C0M, n))); - /* Load the pre-laod register high word */ + /* Load the pre-load register high word */ /* value = (short) (0x55); */ /* outw(value, ADDR_CHAN_REG(REG_C0H, n)); */ - /* Load the pre-laod register low word */ + /* Load the pre-load register low word */ /* value = (short)(0xaa55); */ /* outw(value, ADDR_CHAN_REG(REG_C0L, n)); */ @@ -516,6 +534,7 @@ static int s526_gpct_insn_config(struct comedi_device *dev, int subdev_channel = CR_CHAN(insn->chanspec); /* Unpack chanspec */ int i; short value; + union cmReg cmReg; /* printk("s526: GPCT_INSN_CONFIG: Configuring Channel %d\n", subdev_channel); */ @@ -568,19 +587,8 @@ static int s526_gpct_insn_config(struct comedi_device *dev, #if 1 /* Set Counter Mode Register */ - cmReg.reg.coutSource = 0; /* out RCAP */ - cmReg.reg.coutPolarity = 0; /* Polarity inverted */ - cmReg.reg.autoLoadResetRcap = 0; /* Auto load disabled */ - cmReg.reg.hwCtEnableSource = 2; /* NOT RCAP */ - cmReg.reg.ctEnableCtrl = 1; /* 1: Software, >1 : Hardware */ - cmReg.reg.clockSource = 3; /* x4 */ - cmReg.reg.countDir = 0; /* up */ - cmReg.reg.countDirCtrl = 0; /* quadrature */ - cmReg.reg.outputRegLatchCtrl = 0; /* latch on read */ - cmReg.reg.preloadRegSel = 0; /* PR0 */ - cmReg.reg.reserved = 0; + cmReg.value = insn->data[1] & 0xFFFF; - /* Set Counter Mode Register */ /* printk("s526: Counter Mode register=%x\n", cmReg.value); */ outw(cmReg.value, ADDR_CHAN_REG(REG_C0M, subdev_channel)); @@ -615,11 +623,11 @@ static int s526_gpct_insn_config(struct comedi_device *dev, cmReg.value = (short)(insn->data[1] & 0xFFFF); outw(cmReg.value, ADDR_CHAN_REG(REG_C0M, subdev_channel)); - /* Load the pre-laod register high word */ + /* Load the pre-load register high word */ value = (short)((insn->data[2] >> 16) & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0H, subdev_channel)); - /* Load the pre-laod register low word */ + /* Load the pre-load register low word */ value = (short)(insn->data[2] & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0L, subdev_channel)); @@ -653,11 +661,11 @@ static int s526_gpct_insn_config(struct comedi_device *dev, cmReg.reg.preloadRegSel = 0; /* PR0 */ outw(cmReg.value, ADDR_CHAN_REG(REG_C0M, subdev_channel)); - /* Load the pre-laod register 0 high word */ + /* Load the pre-load register 0 high word */ value = (short)((insn->data[2] >> 16) & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0H, subdev_channel)); - /* Load the pre-laod register 0 low word */ + /* Load the pre-load register 0 low word */ value = (short)(insn->data[2] & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0L, subdev_channel)); @@ -666,17 +674,17 @@ static int s526_gpct_insn_config(struct comedi_device *dev, cmReg.reg.preloadRegSel = 1; /* PR1 */ outw(cmReg.value, ADDR_CHAN_REG(REG_C0M, subdev_channel)); - /* Load the pre-laod register 1 high word */ + /* Load the pre-load register 1 high word */ value = (short)((insn->data[3] >> 16) & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0H, subdev_channel)); - /* Load the pre-laod register 1 low word */ + /* Load the pre-load register 1 low word */ value = (short)(insn->data[3] & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0L, subdev_channel)); /* Write the Counter Control Register */ - if (insn->data[3] != 0) { - value = (short)(insn->data[3] & 0xFFFF); + if (insn->data[4] != 0) { + value = (short)(insn->data[4] & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0C, subdev_channel)); } break; @@ -698,11 +706,11 @@ static int s526_gpct_insn_config(struct comedi_device *dev, cmReg.reg.preloadRegSel = 0; /* PR0 */ outw(cmReg.value, ADDR_CHAN_REG(REG_C0M, subdev_channel)); - /* Load the pre-laod register 0 high word */ + /* Load the pre-load register 0 high word */ value = (short)((insn->data[2] >> 16) & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0H, subdev_channel)); - /* Load the pre-laod register 0 low word */ + /* Load the pre-load register 0 low word */ value = (short)(insn->data[2] & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0L, subdev_channel)); @@ -711,17 +719,17 @@ static int s526_gpct_insn_config(struct comedi_device *dev, cmReg.reg.preloadRegSel = 1; /* PR1 */ outw(cmReg.value, ADDR_CHAN_REG(REG_C0M, subdev_channel)); - /* Load the pre-laod register 1 high word */ + /* Load the pre-load register 1 high word */ value = (short)((insn->data[3] >> 16) & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0H, subdev_channel)); - /* Load the pre-laod register 1 low word */ + /* Load the pre-load register 1 low word */ value = (short)(insn->data[3] & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0L, subdev_channel)); /* Write the Counter Control Register */ - if (insn->data[3] != 0) { - value = (short)(insn->data[3] & 0xFFFF); + if (insn->data[4] != 0) { + value = (short)(insn->data[4] & 0xFFFF); outw(value, ADDR_CHAN_REG(REG_C0C, subdev_channel)); } break; @@ -741,6 +749,7 @@ static int s526_gpct_winsn(struct comedi_device *dev, { int subdev_channel = CR_CHAN(insn->chanspec); /* Unpack chanspec */ short value; + union cmReg cmReg; printk("s526: GPCT_INSN_WRITE on channel %d\n", subdev_channel); cmReg.value = inw(ADDR_CHAN_REG(REG_C0M, subdev_channel)); @@ -775,9 +784,8 @@ static int s526_gpct_winsn(struct comedi_device *dev, (devpriv->s526_gpct_config[subdev_channel]).data[1] = insn->data[1]; } else { - printk("%d \t %d\n", insn->data[1], insn->data[2]); - printk - ("s526: INSN_WRITE: PTG: Problem with Pulse params\n"); + printk("s526: INSN_WRITE: PTG: Problem with Pulse params -> %d %d\n", + insn->data[0], insn->data[1]); return -EINVAL; } @@ -949,7 +957,7 @@ static int s526_dio_insn_bits(struct comedi_device *dev, data[1] = inw(ADDR_REG(REG_DIO)) & 0xFF; /* low 8 bits are the data */ /* or we could just return the software copy of the output values if * it was a purely digital output subdevice */ - /* data[1]=s->state; */ + /* data[1]=s->state & 0xFF; */ return 2; } @@ -959,28 +967,33 @@ static int s526_dio_insn_config(struct comedi_device *dev, struct comedi_insn *insn, unsigned int *data) { int chan = CR_CHAN(insn->chanspec); - short value; + int group, mask; printk("S526 DIO insn_config\n"); - if (insn->n != 1) - return -EINVAL; - - value = inw(ADDR_REG(REG_DIO)); - /* The input or output configuration of each digital line is * configured by a special insn_config instruction. chanspec * contains the channel to be changed, and data[0] contains the * value COMEDI_INPUT or COMEDI_OUTPUT. */ - if (data[0] == COMEDI_OUTPUT) { - value |= 1 << (chan + 10); /* bit 10/11 set the group 1/2's mode */ - s->io_bits |= (0xF << chan); - } else { - value &= ~(1 << (chan + 10)); /* 1 is output, 0 is input. */ - s->io_bits &= ~(0xF << chan); + group = chan >> 2; + mask = 0xF << (group << 2); + switch (data[0]) { + case INSN_CONFIG_DIO_OUTPUT: + s->state |= 1 << (group + 10); // bit 10/11 set the group 1/2's mode + s->io_bits |= mask; + break; + case INSN_CONFIG_DIO_INPUT: + s->state &= ~(1 << (group + 10));// 1 is output, 0 is input. + s->io_bits &= ~mask; + break; + case INSN_CONFIG_DIO_QUERY: + data[1] = (s->io_bits & mask) ? COMEDI_OUTPUT : COMEDI_INPUT; + return insn->n; + default: + return -EINVAL; } - outw(value, ADDR_REG(REG_DIO)); + outw(s->state, ADDR_REG(REG_DIO)); return 1; } diff --git a/drivers/staging/comedi/drivers/serial2002.c b/drivers/staging/comedi/drivers/serial2002.c index a21967983942..82aa86e718b2 100644 --- a/drivers/staging/comedi/drivers/serial2002.c +++ b/drivers/staging/comedi/drivers/serial2002.c @@ -35,6 +35,7 @@ Status: in development #include <linux/delay.h> #include <linux/ioport.h> +#include <linux/sched.h> #include <asm/termios.h> #include <asm/ioctls.h> diff --git a/drivers/staging/cowloop/Kconfig b/drivers/staging/cowloop/Kconfig deleted file mode 100644 index 58d2a23bd2c1..000000000000 --- a/drivers/staging/cowloop/Kconfig +++ /dev/null @@ -1,16 +0,0 @@ -config COWLOOP - tristate "copy-on-write pseudo Block Driver" - depends on BLOCK - default n - ---help--- - Cowloop is a "copy-on-write" pseudo block driver. It can be - stacked on top of a "real" block driver, and catches all write - operations on their way from the file systems layer above to - the real driver below, effectively shielding the lower driver - from those write accesses. The requests are then diverted to - an ordinary file, located somewhere else (configurable). Later - read requests are checked to see whether they can be serviced - by the "real" block driver below, or must be pulled in from - the diverted location. More information and userspace tools to - use the driver are on the project's website - http://www.ATComputing.nl/cowloop/ diff --git a/drivers/staging/cowloop/Makefile b/drivers/staging/cowloop/Makefile deleted file mode 100644 index 2b6b81a63d21..000000000000 --- a/drivers/staging/cowloop/Makefile +++ /dev/null @@ -1 +0,0 @@ -obj-$(CONFIG_COWLOOP) += cowloop.o diff --git a/drivers/staging/cowloop/TODO b/drivers/staging/cowloop/TODO deleted file mode 100644 index 9399d1c16e15..000000000000 --- a/drivers/staging/cowloop/TODO +++ /dev/null @@ -1,11 +0,0 @@ -TODO: - - checkpatch.pl cleanups - - run sparse to ensure clean - - fix up 32/64bit ioctl issues - - move proc file usage to debugfs - - audit ioctls - - add documentation - - get linux-fsdevel to review it - -Please send patches to "H.J. Thomassen" <hjt@ATComputing.nl> and -Greg Kroah-Hartman <gregkh@suse.de> diff --git a/drivers/staging/cowloop/cowloop.c b/drivers/staging/cowloop/cowloop.c deleted file mode 100644 index a71c743a1196..000000000000 --- a/drivers/staging/cowloop/cowloop.c +++ /dev/null @@ -1,2842 +0,0 @@ -/* -** COWLOOP block device driver (2.6 kernel compliant) -** ======================================================================= -** Read-write loop-driver with copy-on-write functionality. -** -** Synopsis: -** -** modprobe cowloop [maxcows=..] [rdofile=..... cowfile=.... [option=r]] -** -** Definition of number of configured cowdevices: -** maxcows= number of configured cowdevices (default: 16) -** (do not confuse this with MAXCOWS: absolute maximum as compiled) -** -** One pair of filenames can be supplied during insmod/modprobe to open -** the first cowdevice: -** rdofile= read-only file (or filesystem) -** cowfile= storage-space for modified blocks of read-only file(system) -** option=r repair cowfile automatically if it appears to be dirty -** -** Other cowdevices can be activated via the command "cowdev" -** whenever the cowloop-driver is loaded. -** -** The read-only file may be of type 'regular' or 'block-device'. -** -** The cowfile must be of type 'regular'. -** If an existing regular file is used as cowfile, its contents will be -** used again for the current read-only file. When the cowfile has not been -** closed properly during a previous session (i.e. rmmod cowloop), the -** cowloop-driver refuses to open it unless the parameter "option=r" is -** specified. -** -** Layout of cowfile: -** -** +-----------------------------+ -** | cow head block | MAPUNIT bytes -** |-----------------------------| -** | | MAPUNIT bytes -** |--- ---| -** | | MAPUNIT bytes -** |--- ---| -** | used-block bitmap | MAPUNIT bytes -** |-----------------------------| -** | gap to align start-offset | -** | to 4K multiple | -** |-----------------------------| <---- start-offset cow blocks -** | | -** | written cow blocks | MAPUNIT bytes -** | ..... | -** -** cowhead block: -** - contains general info about the rdofile which is related -** to this cowfile -** -** used-block bitmap: -** - contains one bit per block with a size of MAPUNIT bytes -** - bit-value '1' = block has been written on cow -** '0' = block unused on cow -** - total bitmap rounded to multiples of MAPUNIT -** -** ============================================================================ -** Author: Gerlof Langeveld - AT Computing (March 2003) -** Current maintainer: Hendrik-Jan Thomassen - AT Computing (Summer 2006) -** Email: hjt@ATComputing.nl -** ---------------------------------------------------------------------------- -** Copyright (C) 2003-2009 AT Consultancy -** -** This program is free software; you can redistribute it and/or modify it -** under the terms of the GNU General Public License as published by the -** Free Software Foundation; either version 2, or (at your option) any -** later version. -** -** This program is distributed in the hope that it will be useful, but -** WITHOUT ANY WARRANTY; without even the implied warranty of -** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -** See the GNU General Public License for more details. -** -** You should have received a copy of the GNU General Public License -** along with this program; if not, write to the Free Software -** Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -** ---------------------------------------------------------------------------- -** -** Major modifications: -** -** 200405 Ported to kernel-version 2.6 Hendrik-Jan Thomassen -** 200405 Added cowhead to cowfile to garantee -** consistency with read-only file Gerlof Langeveld -** 200405 Postponed flushing of bitmaps to improve -** performance. Gerlof Langeveld -** 200405 Inline recovery for dirty cowfiles. Gerlof Langeveld -** 200502 Redesign to support more cowdevices. Gerlof Langeveld -** 200502 Support devices/file > 2 Gbytes. Gerlof Langeveld -** 200507 Check for free space to expand cowfile. Gerlof Langeveld -** 200902 Upgrade for kernel 2.6.28 Hendrik-Jan Thomassen -** -** Inspired by -** loop.c by Theodore Ts'o and -** cloop.c by Paul `Rusty' Russell & Klaus Knopper. -** -** Design-considerations: -** -** For the first experiments with the cowloop-driver, the request-queue -** made use of the do_generic_file_read() which worked fine except -** in combination with the cloop-driver; that combination -** resulted in a non-interruptible hangup of the system during -** heavy load. Other experiments using the `make_request' interface also -** resulted in unpredictable system hangups (with proper use of spinlocks). -** -** To overcome these problems, the cowloop-driver starts a kernel-thread -** for every active cowdevice. -** All read- and write-request on the read-only file and copy-on-write file -** are handled in the context of that thread. -** A scheme has been designed to wakeup the kernel-thread as -** soon as I/O-requests are available in the request-queue; this thread -** handles the requests one-by-one by calling the proper read- or -** write-function related to the open read-only file or copy-on-write file. -** When all pending requests have been handled, the kernel-thread goes -** back to sleep-state. -** This approach requires some additional context-switches; however the -** performance loss during heavy I/O is less than 3%. -** -** -------------------------------------------------------------------------*/ -/* The following is the cowloop package version number. It must be - identical to the content of the include-file "version.h" that is - used in all supporting utilities: */ -char revision[] = "$Revision: 3.1 $"; /* cowlo_init_module() has - assumptions about this string's format */ - -/* Note that the following numbers are *not* the cowloop package version - numbers, but separate revision history numbers to track the - modifications of this particular source file: */ -/* $Log: cowloop.c,v $ -** -** Revision 1.30 2009/02/08 hjt -** Integrated earlier fixes -** Upgraded to kernel 2.6.28 (thanks Jerome Poulin) -** -** Revision 1.29 2006/12/03 22:12:00 hjt -** changed 'cowdevlock' from spinlock to semaphore, to avoid -** "scheduling while atomic". Contributed by Juergen Christ. -** Added version.h again -** -** Revision 1.28 2006/08/16 16:00:00 hjt -** malloc each individual cowloopdevice struct separately -** -** Revision 1.27 2006/03/14 14:57:03 root -** Removed include version.h -** -** Revision 1.26 2005/08/08 11:22:48 root -** Implement possibility to close a cow file or reopen a cowfile read-only. -** -** Revision 1.25 2005/08/03 14:00:39 root -** Added modinfo info to driver. -** -** Revision 1.24 2005/07/21 06:14:53 root -** Cosmetic changes source code. -** -** Revision 1.23 2005/07/20 13:07:32 root -** Supply ioctl to write watchdog program to react on lack of cowfile space. -** -** Revision 1.22 2005/07/20 07:53:34 root -** Regular verification of free space in filesystem holding the cowfile -** (give warnings whenever space is almost exhausted). -** Terminology change: checksum renamed to fingerprint. -** -** Revision 1.21 2005/07/19 09:21:52 root -** Removing maximum limit of 16 Gb per cowdevice. -** -** Revision 1.20 2005/07/19 07:50:33 root -** Minor bugfixes and cosmetic changes. -** -** Revision 1.19 2005/06/10 12:29:55 root -** Removed lock/unlock operation from cowlo_open(). -** -** Revision 1.18 2005/05/09 12:56:26 root -** Allow a cowdevice to be open more than once -** (needed for support of ReiserFS and XFS). -** -** Revision 1.17 2005/03/17 14:36:16 root -** Fixed some license issues. -** -** Revision 1.16 2005/03/07 14:42:05 root -** Only allow one parallel open per cowdevice. -** -** Revision 1.15 2005/02/18 11:52:04 gerlof -** Redesign to support more than one cowdevice > 2 Gb space. -** -** Revision 1.14 2004/08/17 14:19:16 gerlof -** Modified output of /proc/cowloop. -** -** Revision 1.13 2004/08/16 07:21:10 gerlof -** Separate statistical counter for read on rdofile and cowfile. -** -** Revision 1.12 2004/08/11 06:52:11 gerlof -** Modified messages. -** -** Revision 1.11 2004/08/11 06:44:11 gerlof -** Modified log messages. -** -** Revision 1.10 2004/08/10 12:27:27 gerlof -** Cosmetic changes. -** -** Revision 1.9 2004/08/09 11:43:37 gerlof -** Removed double definition of major number (COWMAJOR). -** -** Revision 1.8 2004/08/09 08:03:39 gerlof -** Cleanup of messages. -** -** Revision 1.7 2004/05/27 06:37:33 gerlof -** Modified /proc message. -** -** Revision 1.6 2004/05/26 21:23:28 gerlof -** Modified /proc output. -** -** Revision 1.5 2004/05/26 13:23:34 gerlof -** Support cowsync to force flushing the bitmaps and cowhead. -** -** Revision 1.4 2004/05/26 11:11:10 gerlof -** Updated the comment to the actual situation. -** -** Revision 1.3 2004/05/26 10:50:00 gerlof -** Implemented recovery-option. -** -** Revision 1.2 2004/05/25 15:14:41 gerlof -** Modified bitmap flushing strategy. -** -*/ - -#define COWMAJOR 241 - -// #define COWDEBUG - -#ifdef COWDEBUG -#define DEBUGP printk -#define DCOW KERN_ALERT -#else -#define DEBUGP(format, x...) -#endif - -#include <linux/types.h> -#include <linux/autoconf.h> -#ifndef AUTOCONF_INCLUDED -#include <linux/config.h> -#endif -#include <linux/module.h> -#include <linux/version.h> -#include <linux/moduleparam.h> -#include <linux/init.h> -#include <linux/errno.h> -#include <linux/kernel.h> -#include <linux/major.h> -#include <linux/sched.h> -#include <linux/fs.h> -#include <linux/file.h> -#include <linux/stat.h> -#include <linux/vmalloc.h> -#include <linux/slab.h> -#include <linux/semaphore.h> -#include <asm/uaccess.h> -#include <linux/proc_fs.h> -#include <linux/blkdev.h> -#include <linux/buffer_head.h> -#include <linux/hdreg.h> -#include <linux/genhd.h> -#include <linux/statfs.h> - -#include "cowloop.h" - -MODULE_LICENSE("GPL"); -/* MODULE_AUTHOR("Gerlof Langeveld <gerlof@ATComputing.nl>"); obsolete address */ -MODULE_AUTHOR("Hendrik-Jan Thomassen <hjt@ATComputing.nl>"); /* current maintainer */ -MODULE_DESCRIPTION("Copy-on-write loop driver"); -MODULE_PARM_DESC(maxcows, " Number of configured cowdevices (default 16)"); -MODULE_PARM_DESC(rdofile, " Read-only file for /dev/cow/0"); -MODULE_PARM_DESC(cowfile, " Cowfile for /dev/cow/0"); -MODULE_PARM_DESC(option, " Repair cowfile if inconsistent: option=r"); - -#define DEVICE_NAME "cow" - -#define DFLCOWS 16 /* default cowloop devices */ - -static int maxcows = DFLCOWS; -module_param(maxcows, int, 0); -static char *rdofile = ""; -module_param(rdofile, charp, 0); -static char *cowfile = ""; -module_param(cowfile, charp, 0); -static char *option = ""; -module_param(option, charp, 0); - -/* -** per cowdevice several bitmap chunks are allowed of MAPCHUNKSZ each -** -** each bitmap chunk can describe MAPCHUNKSZ * 8 * MAPUNIT bytes of data -** suppose: -** MAPCHUNKSZ 4096 and MAPUNIT 1024 --> 4096 * 8 * 1024 = 32 Mb per chunk -*/ -#define MAPCHUNKSZ 4096 /* #bytes per bitmap chunk (do not change) */ - -#define SPCMINBLK 100 /* space threshold to give warning messages */ -#define SPCDFLINTVL 16 /* once every SPCDFLINTVL writes to cowfile, */ - /* available space in filesystem is checked */ - -#define CALCMAP(x) ((x)/(MAPCHUNKSZ*8)) -#define CALCBYTE(x) (((x)%(MAPCHUNKSZ*8))>>3) -#define CALCBIT(x) ((x)&7) - -#define ALLCOW 1 -#define ALLRDO 2 -#define MIXEDUP 3 - -static char allzeroes[MAPUNIT]; - -/* -** administration per cowdevice (pair of cowfile/rdofile) -*/ - -/* bit-values for state */ -#define COWDEVOPEN 0x01 /* cowdevice opened */ -#define COWRWCOWOPEN 0x02 /* cowfile opened read-write */ -#define COWRDCOWOPEN 0x04 /* cowfile opened read-only */ -#define COWWATCHDOG 0x08 /* ioctl for watchdog cowfile space active */ - -#define COWCOWOPEN (COWRWCOWOPEN|COWRDCOWOPEN) - -struct cowloop_device -{ - /* - ** current status - */ - int state; /* bit-values (see above) */ - int opencnt; /* # opens for cowdevice */ - - /* - ** open file pointers - */ - struct file *rdofp, *cowfp; /* open file pointers */ - char *rdoname, *cowname; /* file names */ - - /* - ** request queue administration - */ - struct request_queue *rqueue; - spinlock_t rqlock; - struct gendisk *gd; - - /* - ** administration about read-only file - */ - unsigned int numblocks; /* # blocks input file in MAPUNIT */ - unsigned int blocksz; /* minimum unit to access this dev */ - unsigned long fingerprint; /* fingerprint of current rdofile */ - struct block_device *belowdev; /* block device below us */ - struct gendisk *belowgd; /* gendisk for blk dev below us */ - struct request_queue *belowq; /* req. queue of blk dev below us */ - - /* - ** bitmap administration to register which blocks are modified - */ - long int mapsize; /* total size of bitmap (bytes) */ - long int mapremain; /* remaining bytes in last bitmap */ - int mapcount; /* number of bitmaps in use */ - char **mapcache; /* area with pointers to bitmaps */ - - char *iobuf; /* databuffer of MAPUNIT bytes */ - struct cowhead *cowhead; /* buffer containing cowhead */ - - /* - ** administration for interface with the kernel-thread - */ - int pid; /* pid==0: no thread available */ - struct request *req; /* request to be handled now */ - wait_queue_head_t waitq; /* wait-Q: thread waits for work */ - char closedown; /* boolean: thread exit required */ - char qfilled; /* boolean: I/O request pending */ - char iobusy; /* boolean: req under treatment */ - - /* - ** administration to keep track of free space in cowfile filesystem - */ - unsigned long blksize; /* block size of fs (bytes) */ - unsigned long blktotal; /* recent total space in fs (blocks) */ - unsigned long blkavail; /* recent free space in fs (blocks) */ - - wait_queue_head_t watchq; /* wait-Q: watcher awaits threshold */ - unsigned long watchthresh; /* threshold of watcher (blocks) */ - - /* - ** statistical counters - */ - unsigned long rdoreads; /* number of read-actions rdo */ - unsigned long cowreads; /* number of read-actions cow */ - unsigned long cowwrites; /* number of write-actions */ - unsigned long nrcowblocks; /* number of blocks in use on cow */ -}; - -static struct cowloop_device **cowdevall; /* ptr to ptrs to all cowdevices */ -static struct semaphore cowdevlock; /* generic lock for cowdevs */ - -static struct gendisk *cowctlgd; /* gendisk control channel */ -static spinlock_t cowctlrqlock; /* for req.q. of ctrl. channel */ - -/* -** private directory /proc/cow -*/ -struct proc_dir_entry *cowlo_procdir; - -/* -** function prototypes -*/ -static long int cowlo_do_request (struct request *req); -static void cowlo_sync (void); -static int cowlo_checkio (struct cowloop_device *, int, loff_t); -static int cowlo_readmix (struct cowloop_device *, void *, int, loff_t); -static int cowlo_writemix (struct cowloop_device *, void *, int, loff_t); -static long int cowlo_readrdo (struct cowloop_device *, void *, int, loff_t); -static long int cowlo_readcow (struct cowloop_device *, void *, int, loff_t); -static long int cowlo_readcowraw (struct cowloop_device *, void *, int, loff_t); -static long int cowlo_writecow (struct cowloop_device *, void *, int, loff_t); -static long int cowlo_writecowraw(struct cowloop_device *, void *, int, loff_t); -static int cowlo_ioctl (struct block_device *, fmode_t, - unsigned int, unsigned long); -static int cowlo_makepair (struct cowpair __user *); -static int cowlo_removepair (unsigned long __user *); -static int cowlo_watch (struct cowpair __user *); -static int cowlo_cowctl (unsigned long __user *, int); -static int cowlo_openpair (char *, char *, int, int); -static int cowlo_closepair (struct cowloop_device *); -static int cowlo_openrdo (struct cowloop_device *, char *); -static int cowlo_opencow (struct cowloop_device *, char *, int); -static void cowlo_undo_openrdo(struct cowloop_device *); -static void cowlo_undo_opencow(struct cowloop_device *); - -/*****************************************************************************/ -/* System call handling */ -/*****************************************************************************/ - -/* -** handle system call open()/mount() -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int cowlo_open(struct block_device *bdev, fmode_t mode) -{ - struct inode *inode = bdev->bd_inode; - - if (!inode) - return -EINVAL; - - if (imajor(inode) != COWMAJOR) { - printk(KERN_WARNING - "cowloop - unexpected major %d\n", imajor(inode)); - return -ENODEV; - } - - switch (iminor(inode)) { - case COWCTL: - DEBUGP(DCOW"cowloop - open %d control\n", COWCTL); - break; - - default: - DEBUGP(DCOW"cowloop - open minor %d\n", iminor(inode)); - - if ( iminor(inode) >= maxcows ) - return -ENODEV; - - if ( !((cowdevall[iminor(inode)])->state & COWDEVOPEN) ) - return -ENODEV; - - (cowdevall[iminor(inode)])->opencnt++; - } - - return 0; -} - -/* -** handle system call close()/umount() -** -** returns: -** 0 - okay -*/ -static int cowlo_release(struct gendisk *gd, fmode_t mode) -{ - struct block_device *bdev; - struct inode *inode; - - bdev = bdget_disk(gd, 0); - inode = bdev->bd_inode; - if (!inode) - return 0; - - DEBUGP(DCOW"cowloop - release (close) minor %d\n", iminor(inode)); - - if ( iminor(inode) != COWCTL) - (cowdevall[iminor(inode)])->opencnt--; - - return 0; -} - -/* -** handle system call ioctl() -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int cowlo_ioctl(struct block_device *bdev, fmode_t mode, - unsigned int cmd, unsigned long arg) -{ - struct hd_geometry geo; - struct inode *inode = bdev->bd_inode; - - DEBUGP(DCOW "cowloop - ioctl cmd %x\n", cmd); - - switch ( iminor(inode) ) { - - /* - ** allowed via control device only - */ - case COWCTL: - switch (cmd) { - /* - ** write all bitmap chunks and cowheaders to cowfiles - */ - case COWSYNC: - down(&cowdevlock); - cowlo_sync(); - up(&cowdevlock); - return 0; - - /* - ** open a new cowdevice (pair of rdofile/cowfile) - */ - case COWMKPAIR: - return cowlo_makepair((void __user *)arg); - - /* - ** close a cowdevice (pair of rdofile/cowfile) - */ - case COWRMPAIR: - return cowlo_removepair((void __user *)arg); - - /* - ** watch free space of filesystem containing cowfile - */ - case COWWATCH: - return cowlo_watch((void __user *)arg); - - /* - ** close cowfile for active device - */ - case COWCLOSE: - return cowlo_cowctl((void __user *)arg, COWCLOSE); - - /* - ** reopen cowfile read-only for active device - */ - case COWRDOPEN: - return cowlo_cowctl((void __user *)arg, COWRDOPEN); - - default: - return -EINVAL; - } /* end of switch on command */ - - /* - ** allowed for any other cowdevice - */ - default: - switch (cmd) { - /* - ** HDIO_GETGEO must be supported for fdisk, etc - */ - case HDIO_GETGEO: - geo.cylinders = 0; - geo.heads = 0; - geo.sectors = 0; - - if (copy_to_user((void __user *)arg, &geo, sizeof geo)) - return -EFAULT; - return 0; - - default: - return -EINVAL; - } /* end of switch on ioctl-cmd code parameter */ - } /* end of switch on minor number */ -} - -static struct block_device_operations cowlo_fops = -{ - .owner = THIS_MODULE, - .open = cowlo_open, /* called upon open */ - .release = cowlo_release, /* called upon close */ - .ioctl = cowlo_ioctl, /* called upon ioctl */ -}; - -/* -** handle ioctl-command COWMKPAIR: -** open a new cowdevice (pair of rdofile/cowfile) on-the-fly -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_makepair(struct cowpair __user *arg) -{ - int i, rv=0; - struct cowpair cowpair; - unsigned char *cowpath; - unsigned char *rdopath; - - /* - ** retrieve info about pathnames - */ - if ( copy_from_user(&cowpair, arg, sizeof cowpair) ) - return -EFAULT; - - if ( (MAJOR(cowpair.device) != COWMAJOR) && (cowpair.device != ANYDEV) ) - return -EINVAL; - - if ( (MINOR(cowpair.device) >= maxcows) && (cowpair.device != ANYDEV) ) - return -EINVAL; - - /* - ** retrieve pathname strings - */ - if ( (cowpair.cowflen > PATH_MAX) || (cowpair.rdoflen > PATH_MAX) ) - return -ENAMETOOLONG; - - if ( !(cowpath = kmalloc(cowpair.cowflen+1, GFP_KERNEL)) ) - return -ENOMEM; - - if ( copy_from_user(cowpath, (void __user *)cowpair.cowfile, - cowpair.cowflen) ) { - kfree(cowpath); - return -EFAULT; - } - *(cowpath+cowpair.cowflen) = 0; - - if ( !(rdopath = kmalloc(cowpair.rdoflen+1, GFP_KERNEL)) ) { - kfree(cowpath); - return -ENOMEM; - } - - if ( copy_from_user(rdopath, (void __user *)cowpair.rdofile, - cowpair.rdoflen) ) { - kfree(rdopath); - kfree(cowpath); - return -EFAULT; - } - *(rdopath+cowpair.rdoflen) = 0; - - /* - ** open new cowdevice - */ - if ( cowpair.device == ANYDEV) { - /* - ** search first unused minor - */ - for (i=0, rv=-EBUSY; i < maxcows; i++) { - if ( !((cowdevall[i])->state & COWDEVOPEN) ) { - rv = cowlo_openpair(rdopath, cowpath, 0, i); - break; - } - } - - if (rv) { /* open failed? */ - kfree(rdopath); - kfree(cowpath); - return rv; - } - - /* - ** return newly allocated cowdevice to user space - */ - cowpair.device = MKDEV(COWMAJOR, i); - - if ( copy_to_user(arg, &cowpair, sizeof cowpair)) { - kfree(rdopath); - kfree(cowpath); - return -EFAULT; - } - } else { /* specific minor requested */ - if ( (rv = cowlo_openpair(rdopath, cowpath, 0, - MINOR(cowpair.device)))) { - kfree(rdopath); - kfree(cowpath); - return rv; - } - } - - return 0; -} - -/* -** handle ioctl-command COWRMPAIR: -** deactivate an existing cowdevice (pair of rdofile/cowfile) on-the-fly -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_removepair(unsigned long __user *arg) -{ - unsigned long cowdevice; - struct cowloop_device *cowdev; - - /* - ** retrieve info about device to be removed - */ - if ( copy_from_user(&cowdevice, arg, sizeof cowdevice)) - return -EFAULT; - - /* - ** verify major-minor number - */ - if ( MAJOR(cowdevice) != COWMAJOR) - return -EINVAL; - - if ( MINOR(cowdevice) >= maxcows) - return -EINVAL; - - cowdev = cowdevall[MINOR(cowdevice)]; - - if ( !(cowdev->state & COWDEVOPEN) ) - return -ENODEV; - - /* - ** synchronize bitmaps and close cowdevice - */ - if (cowdev->state & COWRWCOWOPEN) { - down(&cowdevlock); - cowlo_sync(); - up(&cowdevlock); - } - - return cowlo_closepair(cowdev); -} - -/* -** handle ioctl-command COWWATCH: -** watch the free space of the filesystem containing a cowfile -** of an open cowdevice -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_watch(struct cowpair __user *arg) -{ - struct cowloop_device *cowdev; - struct cowwatch cowwatch; - - /* - ** retrieve structure holding info - */ - if ( copy_from_user(&cowwatch, arg, sizeof cowwatch)) - return -EFAULT; - - /* - ** verify if cowdevice exists and is currently open - */ - if ( MINOR(cowwatch.device) >= maxcows) - return -EINVAL; - - cowdev = cowdevall[MINOR(cowwatch.device)]; - - if ( !(cowdev->state & COWDEVOPEN) ) - return -ENODEV; - - /* - ** if the WATCHWAIT-option is set, wait until the indicated - ** threshold is reached (only one waiter allowed) - */ - if (cowwatch.flags & WATCHWAIT) { - /* - ** check if already another waiter active - ** for this cowdevice - */ - if (cowdev->state & COWWATCHDOG) - return -EAGAIN; - - cowdev->state |= COWWATCHDOG; - - cowdev->watchthresh = (unsigned long long) - cowwatch.threshold / - (cowdev->blksize / 1024); - - if (wait_event_interruptible(cowdev->watchq, - cowdev->watchthresh >= cowdev->blkavail)) { - cowdev->state &= ~COWWATCHDOG; - return EINTR; - } - - cowdev->state &= ~COWWATCHDOG; - } - - cowwatch.totalkb = (unsigned long long)cowdev->blktotal * - cowdev->blksize / 1024; - cowwatch.availkb = (unsigned long long)cowdev->blkavail * - cowdev->blksize / 1024; - - if ( copy_to_user(arg, &cowwatch, sizeof cowwatch)) - return -EFAULT; - - return 0; -} - -/* -** handle ioctl-commands COWCLOSE and COWRDOPEN: -** COWCLOSE - close the cowfile while the cowdevice remains open; -** this allows an unmount of the filesystem on which -** the cowfile resides -** COWRDOPEN - close the cowfile and reopen it for read-only; -** this allows a remount read-ony of the filesystem -** on which the cowfile resides -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_cowctl(unsigned long __user *arg, int cmd) -{ - struct cowloop_device *cowdev; - unsigned long cowdevice; - - /* - ** retrieve info about device to be removed - */ - if ( copy_from_user(&cowdevice, arg, sizeof cowdevice)) - return -EFAULT; - - /* - ** verify major-minor number - */ - if ( MAJOR(cowdevice) != COWMAJOR) - return -EINVAL; - - if ( MINOR(cowdevice) >= maxcows) - return -EINVAL; - - cowdev = cowdevall[MINOR(cowdevice)]; - - if ( !(cowdev->state & COWDEVOPEN) ) - return -ENODEV; - - /* - ** synchronize bitmaps and close cowfile - */ - if (cowdev->state & COWRWCOWOPEN) { - down(&cowdevlock); - cowlo_sync(); - up(&cowdevlock); - } - - /* - ** handle specific ioctl-command - */ - switch (cmd) { - case COWRDOPEN: - /* - ** if the cowfile is still opened read-write - */ - if (cowdev->state & COWRWCOWOPEN) { - /* - ** close the cowfile - */ - if (cowdev->cowfp) - filp_close(cowdev->cowfp, 0); - - cowdev->state &= ~COWRWCOWOPEN; - - /* - ** open again for read-only - */ - cowdev->cowfp = filp_open(cowdev->cowname, - O_RDONLY|O_LARGEFILE, 0600); - - if ( (cowdev->cowfp == NULL) || IS_ERR(cowdev->cowfp) ) { - printk(KERN_ERR - "cowloop - failed to reopen cowfile %s\n", - cowdev->cowname); - return -EINVAL; - } - - /* - ** mark cowfile open for read-only - */ - cowdev->state |= COWRDCOWOPEN; - } else { - return -EINVAL; - } - break; - - case COWCLOSE: - /* - ** if the cowfile is still open - */ - if (cowdev->state & COWCOWOPEN) { - /* - ** close the cowfile - */ - if (cowdev->cowfp) - filp_close(cowdev->cowfp, 0); - - cowdev->state &= ~COWCOWOPEN; - } - } - - return 0; -} - - -/*****************************************************************************/ -/* Handling of I/O-requests for a cowdevice */ -/*****************************************************************************/ - -/* -** function to be called by core-kernel to handle the I/O-requests -** in the queue -*/ -static void cowlo_request(struct request_queue *q) -{ - struct request *req; - struct cowloop_device *cowdev; - - DEBUGP(DCOW "cowloop - request function called....\n"); - - while((req = blk_peek_request(q)) != NULL) { - DEBUGP(DCOW "cowloop - got next request\n"); - - if (! blk_fs_request(req)) { - /* this is not a normal file system request */ - __blk_end_request_cur(req, -EIO); - continue; - } - cowdev = req->rq_disk->private_data; - - if (cowdev->iobusy) - return; - else - cowdev->iobusy = 1; - - /* - ** when no kernel-thread is available, the request will - ** produce an I/O-error - */ - if (!cowdev->pid) { - printk(KERN_ERR"cowloop - no thread available\n"); - __blk_end_request_cur(req, -EIO); /* request failed */ - cowdev->iobusy = 0; - continue; - } - - /* - ** handle I/O-request in the context of the kernel-thread - */ - cowdev->req = req; - cowdev->qfilled = 1; - - wake_up_interruptible_sync(&cowdev->waitq); - - /* - ** get out of this function now while the I/O-request is - ** under treatment of the kernel-thread; this function - ** will be called again after the current I/O-request has - ** been finished by the thread - */ - return; - } -} - -/* -** daemon-process (kernel-thread) executes this function -*/ -static int -cowlo_daemon(struct cowloop_device *cowdev) -{ - int rv; - int minor; - char myname[16]; - - for (minor = 0; minor < maxcows; minor++) { - if (cowdev == cowdevall[minor]) break; - } - sprintf(myname, "cowloopd%d", minor); - - daemonize(myname); - - while (!cowdev->closedown) { - /* - ** sleep while waiting for an I/O request; - ** note that no non-interruptible wait has been used - ** because the non-interruptible version of - ** a *synchronous* wake_up does not exist (any more) - */ - if (wait_event_interruptible(cowdev->waitq, cowdev->qfilled)){ - flush_signals(current); /* ignore signal-based wakeup */ - continue; - } - - if (cowdev->closedown) /* module will be unloaded ? */{ - cowdev->pid = 0; - return 0; - } - - /* - ** woken up by the I/O-request handler: treat requested I/O - */ - cowdev->qfilled = 0; - - rv = cowlo_do_request(cowdev->req); - - /* - ** reacquire the queue-spinlock for manipulating - ** the request-queue and dequeue the request - */ - spin_lock_irq(&cowdev->rqlock); - - __blk_end_request_cur(cowdev->req, rv); - cowdev->iobusy = 0; - - /* - ** initiate the next request from the queue - */ - cowlo_request(cowdev->rqueue); - - spin_unlock_irq(&cowdev->rqlock); - } - return 0; -} - -/* -** function to be called in the context of the kernel thread -** to handle the queued I/O-requests -** -** returns: -** 0 - fail -** 1 - success -*/ -static long int -cowlo_do_request(struct request *req) -{ - unsigned long len; - long int rv; - loff_t offset; - struct cowloop_device *cowdev = req->rq_disk->private_data; - - /* - ** calculate some variables which are needed later on - */ - len = blk_rq_cur_sectors(req) << 9; - offset = (loff_t) blk_rq_pos(req) << 9; - - DEBUGP(DCOW"cowloop - req cmd=%d offset=%lld len=%lu addr=%p\n", - *(req->cmd), offset, len, req->buffer); - - /* - ** handle READ- or WRITE-request - */ - switch (rq_data_dir(req)) { - /**********************************************************/ - case READ: - switch ( cowlo_checkio(cowdev, len, offset) ) { - case ALLCOW: - rv = cowlo_readcow(cowdev, req->buffer, len, offset); - break; - - case ALLRDO: - rv = cowlo_readrdo(cowdev, req->buffer, len, offset); - break; - - case MIXEDUP: - rv = cowlo_readmix(cowdev, req->buffer, len, offset); - break; - - default: - rv = 0; /* never happens */ - } - break; - - /**********************************************************/ - case WRITE: - switch ( cowlo_checkio(cowdev, len, offset) ) { - case ALLCOW: - /* - ** straight-forward write will do... - */ - DEBUGP(DCOW"cowloop - write straight "); - - rv = cowlo_writecow(cowdev, req->buffer, len, offset); - break; /* from switch */ - - case ALLRDO: - if ( (len & MUMASK) == 0) { - DEBUGP(DCOW"cowloop - write straight "); - - rv = cowlo_writecow(cowdev, req->buffer, - len, offset); - break; - } - - case MIXEDUP: - rv = cowlo_writemix(cowdev, req->buffer, len, offset); - break; - - default: - rv = 0; /* never happens */ - } - break; - - default: - printk(KERN_ERR - "cowloop - unrecognized command %d\n", *(req->cmd)); - rv = 0; - } - - return (rv <= 0 ? 0 : 1); -} - -/* -** check for a given I/O-request if all underlying blocks -** (with size MAPUNIT) are either in the read-only file or in -** the cowfile (or a combination of the two) -** -** returns: -** ALLRDO - all underlying blocks in rdofile -** ALLCOW - all underlying blocks in cowfile -** MIXEDUP - underlying blocks partly in rdofile and partly in cowfile -*/ -static int -cowlo_checkio(struct cowloop_device *cowdev, int len, loff_t offset) -{ - unsigned long mapnum, bytenum, bitnum, blocknr, partlen; - long int totcnt, cowcnt; - char *mc; - - /* - ** notice that the requested block might cross - ** a blocksize boundary while one of the concerned - ** blocks resides in the read-only file and another - ** one in the copy-on-write file; in that case the - ** request will be broken up into pieces - */ - if ( (len <= MAPUNIT) && - (MAPUNIT - (offset & MUMASK) <= len) ) { - /* - ** easy situation: - ** requested data-block entirely fits within - ** the mapunit used for the bitmap - ** check if that block is located in rdofile or - ** cowfile - */ - blocknr = offset >> MUSHIFT; - - mapnum = CALCMAP (blocknr); - bytenum = CALCBYTE(blocknr); - bitnum = CALCBIT (blocknr); - - if (*(*(cowdev->mapcache+mapnum)+bytenum)&(1<<bitnum)) - return ALLCOW; - else - return ALLRDO; - } - - /* - ** less easy situation: - ** the requested data-block does not fit within the mapunit - ** used for the bitmap - ** check if *all* underlying blocks involved reside on the rdofile - ** or the cowfile (so still no breakup required) - */ - for (cowcnt=totcnt=0; len > 0; len-=partlen, offset+=partlen, totcnt++){ - /* - ** calculate blocknr of involved block - */ - blocknr = offset >> MUSHIFT; - - /* - ** calculate partial length for this transfer - */ - partlen = MAPUNIT - (offset & MUMASK); - if (partlen > len) - partlen = len; - - /* - ** is this block located in the cowfile - */ - mapnum = CALCMAP (blocknr); - bytenum = CALCBYTE(blocknr); - bitnum = CALCBIT (blocknr); - - mc = *(cowdev->mapcache+mapnum); - - if (*(mc+bytenum)&(1<<bitnum)) - cowcnt++;; - - DEBUGP(DCOW - "cowloop - check %lu - map %lu, byte %lu, bit %lu, " - "cowcnt %ld, totcnt %ld %02x %p\n", - blocknr, mapnum, bytenum, bitnum, cowcnt, totcnt, - *(mc+bytenum), mc); - } - - if (cowcnt == 0) /* all involved blocks on rdofile? */ - return ALLRDO; - - if (cowcnt == totcnt) /* all involved blocks on cowfile? */ - return ALLCOW; - - /* - ** situation somewhat more complicated: - ** involved underlying blocks spread over both files - */ - return MIXEDUP; -} - -/* -** read requested chunk partly from rdofile and partly from cowfile -** -** returns: -** 0 - fail -** 1 - success -*/ -static int -cowlo_readmix(struct cowloop_device *cowdev, void *buf, int len, loff_t offset) -{ - unsigned long mapnum, bytenum, bitnum, blocknr, partlen; - long int rv; - char *mc; - - /* - ** complicated approach: breakup required of read-request - */ - for (rv=1; len > 0; len-=partlen, buf+=partlen, offset+=partlen) { - /* - ** calculate blocknr of entire block - */ - blocknr = offset >> MUSHIFT; - - /* - ** calculate partial length for this transfer - */ - partlen = MAPUNIT - (offset & MUMASK); - if (partlen > len) - partlen = len; - - /* - ** is this block located in the cowfile - */ - mapnum = CALCMAP (blocknr); - bytenum = CALCBYTE(blocknr); - bitnum = CALCBIT (blocknr); - mc = *(cowdev->mapcache+mapnum); - - if (*(mc+bytenum)&(1<<bitnum)) { - /* - ** read (partial) block from cowfile - */ - DEBUGP(DCOW"cowloop - split read " - "cow partlen=%ld off=%lld\n", partlen, offset); - - if (cowlo_readcow(cowdev, buf, partlen, offset) <= 0) - rv = 0; - } else { - /* - ** read (partial) block from rdofile - */ - DEBUGP(DCOW"cowloop - split read " - "rdo partlen=%ld off=%lld\n", partlen, offset); - - if (cowlo_readrdo(cowdev, buf, partlen, offset) <= 0) - rv = 0; - } - } - - return rv; -} - -/* -** chunk to be written to the cowfile needs pieces to be -** read from the rdofile -** -** returns: -** 0 - fail -** 1 - success -*/ -static int -cowlo_writemix(struct cowloop_device *cowdev, void *buf, int len, loff_t offset) -{ - unsigned long mapnum, bytenum, bitnum, blocknr, partlen; - long int rv; - char *mc; - - /* - ** somewhat more complicated stuff is required: - ** if the request is larger than one underlying - ** block or is spread over two underlying blocks, - ** split the request into pieces; if a block does not - ** start at a block boundary, take care that - ** surrounding data is read first (if needed), - ** fit the new data in and write it as a full block - */ - for (rv=1; len > 0; len-=partlen, buf+=partlen, offset+=partlen) { - /* - ** calculate partial length for this transfer - */ - partlen = MAPUNIT - (offset & MUMASK); - if (partlen > len) - partlen = len; - - /* - ** calculate blocknr of entire block - */ - blocknr = offset >> MUSHIFT; - - /* - ** has this block been written before? - */ - mapnum = CALCMAP (blocknr); - bytenum = CALCBYTE(blocknr); - bitnum = CALCBIT (blocknr); - mc = *(cowdev->mapcache+mapnum); - - if (*(mc+bytenum)&(1<<bitnum)) { - /* - ** block has been written before; - ** write transparantly to cowfile - */ - DEBUGP(DCOW - "cowloop - splitwr transp\n"); - - if (cowlo_writecow(cowdev, buf, partlen, offset) <= 0) - rv = 0; - } else { - /* - ** block has never been written before, - ** so read entire block from - ** read-only file first, unless - ** a full block is requested to - ** be written - */ - if (partlen < MAPUNIT) { - if (cowlo_readrdo(cowdev, cowdev->iobuf, - MAPUNIT, (loff_t)blocknr << MUSHIFT) <= 0) - rv = 0; - } - - /* - ** transfer modified part into - ** the block just read - */ - memcpy(cowdev->iobuf + (offset & MUMASK), buf, partlen); - - /* - ** write entire block to cowfile - */ - DEBUGP(DCOW"cowloop - split " - "partlen=%ld off=%lld\n", - partlen, (loff_t)blocknr << MUSHIFT); - - if (cowlo_writecow(cowdev, cowdev->iobuf, MAPUNIT, - (loff_t)blocknr << MUSHIFT) <= 0) - rv = 0; - } - } - - return rv; -} - -/*****************************************************************************/ -/* I/O-support for read-only file and copy-on-write file */ -/*****************************************************************************/ - -/* -** read data from the read-only file -** -** return-value: similar to user-mode read -*/ -static long int -cowlo_readrdo(struct cowloop_device *cowdev, void *buf, int len, loff_t offset) -{ - long int rv; - mm_segment_t old_fs; - loff_t saveoffset = offset; - - DEBUGP(DCOW"cowloop - readrdo called\n"); - - old_fs = get_fs(); - set_fs( get_ds() ); - rv = cowdev->rdofp->f_op->read(cowdev->rdofp, buf, len, &offset); - set_fs(old_fs); - - if (rv < len) { - printk(KERN_WARNING "cowloop - read-failure %ld on rdofile" - "- offset=%lld len=%d\n", - rv, saveoffset, len); - } - - cowdev->rdoreads++; - return rv; -} - -/* -** read cowfile from a modified offset, i.e. skipping the bitmap and cowhead -** -** return-value: similar to user-mode read -*/ -static long int -cowlo_readcow(struct cowloop_device *cowdev, void *buf, int len, loff_t offset) -{ - DEBUGP(DCOW"cowloop - readcow called\n"); - - offset += cowdev->cowhead->doffset; - - return cowlo_readcowraw(cowdev, buf, len, offset); -} - -/* -** read cowfile from an absolute offset -** -** return-value: similar to user-mode read -*/ -static long int -cowlo_readcowraw(struct cowloop_device *cowdev, - void *buf, int len, loff_t offset) -{ - long int rv; - mm_segment_t old_fs; - loff_t saveoffset = offset; - - DEBUGP(DCOW"cowloop - readcowraw called\n"); - - /* - ** be sure that cowfile is opened for read-write - */ - if ( !(cowdev->state & COWCOWOPEN) ) { - printk(KERN_WARNING - "cowloop - read request from cowfile refused\n"); - - return -EBADF; - } - - /* - ** issue low level read - */ - old_fs = get_fs(); - set_fs( get_ds() ); - rv = cowdev->cowfp->f_op->read(cowdev->cowfp, buf, len, &offset); - set_fs(old_fs); - - if (rv < len) { - printk(KERN_WARNING - "cowloop - read-failure %ld on cowfile" - "- offset=%lld len=%d\n", rv, saveoffset, len); - } - - cowdev->cowreads++; - return rv; -} - -/* -** write cowfile from a modified offset, i.e. skipping the bitmap and cowhead -** -** if a block is written for the first time while its contents consists -** of binary zeroes only, the concerning bitmap is flushed to the cowfile -** -** return-value: similar to user-mode write -*/ -static long int -cowlo_writecow(struct cowloop_device *cowdev, void *buf, int len, loff_t offset) -{ - long int rv; - unsigned long mapnum=0, mapbyte=0, mapbit=0, cowblock=0, partlen; - char *tmpptr, *mapptr = NULL; - loff_t tmpoffset, mapoffset = 0; - - DEBUGP(DCOW"cowloop - writecow called\n"); - - /* - ** be sure that cowfile is opened for read-write - */ - if ( !(cowdev->state & COWRWCOWOPEN) ) { - printk(KERN_WARNING - "cowloop - Write request to cowfile refused\n"); - - return -EBADF; - } - - /* - ** write the entire block to the cowfile - */ - tmpoffset = offset + cowdev->cowhead->doffset; - - rv = cowlo_writecowraw(cowdev, buf, len, tmpoffset); - - /* - ** verify if enough space available on filesystem holding - ** the cowfile - ** - when the last write failed (might be caused by lack of space) - ** - when a watcher is active (to react adequatly) - ** - when the previous check indicated fs was almost full - ** - with regular intervals - */ - if ( (rv <= 0) || - (cowdev->state & COWWATCHDOG) || - (cowdev->blkavail / 2 < SPCDFLINTVL) || - (cowdev->cowwrites % SPCDFLINTVL == 0) ) { - struct kstatfs ks; - - if (vfs_statfs(cowdev->cowfp->f_dentry, &ks)==0){ - if (ks.f_bavail <= SPCMINBLK) { - switch (ks.f_bavail) { - case 0: - case 1: - case 2: - case 3: - printk(KERN_ALERT - "cowloop - " - "ALERT: cowfile full!\n"); - break; - - default: - printk(KERN_WARNING - "cowloop - cowfile almost " - "full (only %llu Kb free)\n", - (unsigned long long) - ks.f_bsize * ks.f_bavail /1024); - } - } - - cowdev->blktotal = ks.f_blocks; - cowdev->blkavail = ks.f_bavail; - - /* - ** wakeup watcher if threshold has been reached - */ - if ( (cowdev->state & COWWATCHDOG) && - (cowdev->watchthresh >= cowdev->blkavail) ) { - wake_up_interruptible(&cowdev->watchq); - } - } - } - - if (rv <= 0) - return rv; - - DEBUGP(DCOW"cowloop - block written\n"); - - /* - ** check if block(s) is/are written to the cowfile - ** for the first time; if so, adapt the bitmap - */ - for (; len > 0; len-=partlen, offset+=partlen, buf+=partlen) { - /* - ** calculate partial length for this transfer - */ - partlen = MAPUNIT - (offset & MUMASK); - if (partlen > len) - partlen = len; - - /* - ** calculate bitnr of written chunk of cowblock - */ - cowblock = offset >> MUSHIFT; - - mapnum = CALCMAP (cowblock); - mapbyte = CALCBYTE(cowblock); - mapbit = CALCBIT (cowblock); - - if (*(*(cowdev->mapcache+mapnum)+mapbyte) & (1<<mapbit)) - continue; /* already written before */ - - /* - ** if the block is written for the first time, - ** the corresponding bit should be set in the bitmap - */ - *(*(cowdev->mapcache+mapnum)+mapbyte) |= (1<<mapbit); - - cowdev->nrcowblocks++; - - DEBUGP(DCOW"cowloop - bitupdate blk=%ld map=%ld " - "byte=%ld bit=%ld\n", - cowblock, mapnum, mapbyte, mapbit); - - /* - ** check if the cowhead in the cowfile is currently - ** marked clean; if so, mark it dirty and flush it - */ - if ( !(cowdev->cowhead->flags &= COWDIRTY)) { - cowdev->cowhead->flags |= COWDIRTY; - - cowlo_writecowraw(cowdev, cowdev->cowhead, - MAPUNIT, (loff_t)0); - } - - /* - ** if the written datablock contained binary zeroes, - ** the bitmap block should be marked to be flushed to disk - ** (blocks containing all zeroes cannot be recovered by - ** the cowrepair-program later on if cowloop is not properly - ** removed via rmmod) - */ - if ( memcmp(buf, allzeroes, partlen) ) /* not all zeroes? */ - continue; /* no flush needed */ - - /* - ** calculate positions of bitmap block to be flushed - ** - pointer of bitmap block in memory - ** - offset of bitmap block in cowfile - */ - tmpptr = *(cowdev->mapcache+mapnum) + (mapbyte & (~MUMASK)); - tmpoffset = (loff_t) MAPUNIT + mapnum * MAPCHUNKSZ + - (mapbyte & (~MUMASK)); - - /* - ** flush a bitmap block at the moment that all bits have - ** been set in that block, i.e. at the moment that we - ** switch to another bitmap block - */ - if ( (mapoffset != 0) && (mapoffset != tmpoffset) ) { - if (cowlo_writecowraw(cowdev, mapptr, MAPUNIT, - mapoffset) < 0) { - printk(KERN_WARNING - "cowloop - write-failure on bitmap - " - "blk=%ld map=%ld byte=%ld bit=%ld\n", - cowblock, mapnum, mapbyte, mapbit); - } - - DEBUGP(DCOW"cowloop - bitmap blk written %lld\n", - mapoffset); - } - - /* - ** remember offset in cowfile and offset in memory - ** for bitmap to be flushed; flushing will be done - ** as soon as all updates in this bitmap block have - ** been done - */ - mapoffset = tmpoffset; - mapptr = tmpptr; - } - - /* - ** any new block written containing binary zeroes? - */ - if (mapoffset) { - if (cowlo_writecowraw(cowdev, mapptr, MAPUNIT, mapoffset) < 0) { - printk(KERN_WARNING - "cowloop - write-failure on bitmap - " - "blk=%ld map=%ld byte=%ld bit=%ld\n", - cowblock, mapnum, mapbyte, mapbit); - } - - DEBUGP(DCOW"cowloop - bitmap block written %lld\n", mapoffset); - } - - return rv; -} - -/* -** write cowfile from an absolute offset -** -** return-value: similar to user-mode write -*/ -static long int -cowlo_writecowraw(struct cowloop_device *cowdev, - void *buf, int len, loff_t offset) -{ - long int rv; - mm_segment_t old_fs; - loff_t saveoffset = offset; - - DEBUGP(DCOW"cowloop - writecowraw called\n"); - - /* - ** be sure that cowfile is opened for read-write - */ - if ( !(cowdev->state & COWRWCOWOPEN) ) { - printk(KERN_WARNING - "cowloop - write request to cowfile refused\n"); - - return -EBADF; - } - - /* - ** issue low level write - */ - old_fs = get_fs(); - set_fs( get_ds() ); - rv = cowdev->cowfp->f_op->write(cowdev->cowfp, buf, len, &offset); - set_fs(old_fs); - - if (rv < len) { - printk(KERN_WARNING - "cowloop - write-failure %ld on cowfile" - "- offset=%lld len=%d\n", rv, saveoffset, len); - } - - cowdev->cowwrites++; - return rv; -} - - -/* -** readproc-function: called when the corresponding /proc-file is read -*/ -static int -cowlo_readproc(char *buf, char **start, off_t pos, int cnt, int *eof, void *p) -{ - struct cowloop_device *cowdev = p; - - revision[sizeof revision - 3] = '\0'; - - return sprintf(buf, - " cowloop version: %9s\n\n" - " device state: %s%s%s%s\n" - " number of opens: %9d\n" - " pid of thread: %9d\n\n" - " read-only file: %9s\n" - " rdoreads: %9lu\n\n" - "copy-on-write file: %9s\n" - " state cowfile: %9s\n" - " bitmap-blocks: %9lu (of %d bytes)\n" - " cowblocks in use: %9lu (of %d bytes)\n" - " cowreads: %9lu\n" - " cowwrites: %9lu\n", - &revision[11], - - cowdev->state & COWDEVOPEN ? "devopen " : "", - cowdev->state & COWRWCOWOPEN ? "cowopenrw " : "", - cowdev->state & COWRDCOWOPEN ? "cowopenro " : "", - cowdev->state & COWWATCHDOG ? "watchdog " : "", - - cowdev->opencnt, - cowdev->pid, - cowdev->rdoname, - cowdev->rdoreads, - cowdev->cowname, - cowdev->cowhead->flags & COWDIRTY ? "dirty":"clean", - cowdev->mapsize >> MUSHIFT, MAPUNIT, - cowdev->nrcowblocks, MAPUNIT, - cowdev->cowreads, - cowdev->cowwrites); -} - -/*****************************************************************************/ -/* Setup and destroy cowdevices */ -/*****************************************************************************/ - -/* -** open and prepare a cowdevice (rdofile and cowfile) and allocate bitmaps -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_openpair(char *rdof, char *cowf, int autorecover, int minor) -{ - long int rv; - struct cowloop_device *cowdev = cowdevall[minor]; - struct kstatfs ks; - - down(&cowdevlock); - - /* - ** requested device exists? - */ - if (minor >= maxcows) { - up(&cowdevlock); - return -ENODEV; - } - - /* - ** requested device already assigned to cowdevice? - */ - if (cowdev->state & COWDEVOPEN) { - up(&cowdevlock); - return -EBUSY; - } - - /* - ** initialize administration - */ - memset(cowdev, 0, sizeof *cowdev); - - spin_lock_init (&cowdev->rqlock); - init_waitqueue_head(&cowdev->waitq); - init_waitqueue_head(&cowdev->watchq); - - /* - ** open the read-only file - */ - DEBUGP(DCOW"cowloop - call openrdo....\n"); - - if ( (rv = cowlo_openrdo(cowdev, rdof)) ) { - cowlo_undo_openrdo(cowdev); - up(&cowdevlock); - return rv; - } - - /* - ** open the cowfile - */ - DEBUGP(DCOW"cowloop - call opencow....\n"); - - if ( (rv = cowlo_opencow(cowdev, cowf, autorecover)) ) { - cowlo_undo_openrdo(cowdev); - cowlo_undo_opencow(cowdev); - up(&cowdevlock); - return rv; - } - - /* - ** administer total and available size of filesystem holding cowfile - */ - if (vfs_statfs(cowdev->cowfp->f_dentry, &ks)==0) { - cowdev->blksize = ks.f_bsize; - cowdev->blktotal = ks.f_blocks; - cowdev->blkavail = ks.f_bavail; - } else { - cowdev->blksize = 1024; /* avoid division by zero */ - } - - /* - ** flush the (recovered) bitmaps and cowhead to the cowfile - */ - DEBUGP(DCOW"cowloop - call cowsync....\n"); - - cowlo_sync(); - - /* - ** allocate gendisk for the cow device - */ - DEBUGP(DCOW"cowloop - alloc disk....\n"); - - if ((cowdev->gd = alloc_disk(1)) == NULL) { - printk(KERN_WARNING - "cowloop - unable to alloc_disk for cowloop\n"); - - cowlo_undo_openrdo(cowdev); - cowlo_undo_opencow(cowdev); - up(&cowdevlock); - return -ENOMEM; - } - - cowdev->gd->major = COWMAJOR; - cowdev->gd->first_minor = minor; - cowdev->gd->minors = 1; - cowdev->gd->fops = &cowlo_fops; - cowdev->gd->private_data = cowdev; - sprintf(cowdev->gd->disk_name, "%s%d", DEVICE_NAME, minor); - - /* in .5 Kb units */ - set_capacity(cowdev->gd, (cowdev->numblocks*(MAPUNIT/512))); - - DEBUGP(DCOW"cowloop - init request queue....\n"); - - if ((cowdev->rqueue = blk_init_queue(cowlo_request, &cowdev->rqlock)) - == NULL) { - printk(KERN_WARNING - "cowloop - unable to get request queue for cowloop\n"); - - del_gendisk(cowdev->gd); - cowlo_undo_openrdo(cowdev); - cowlo_undo_opencow(cowdev); - up(&cowdevlock); - return -EINVAL; - } - - blk_queue_logical_block_size(cowdev->rqueue, cowdev->blocksz); - cowdev->gd->queue = cowdev->rqueue; - - /* - ** start kernel thread to handle requests - */ - DEBUGP(DCOW"cowloop - kickoff daemon....\n"); - - cowdev->pid = kernel_thread((int (*)(void *))cowlo_daemon, cowdev, 0); - - /* - ** create a file below directory /proc/cow for this new cowdevice - */ - if (cowlo_procdir) { - char tmpname[64]; - - sprintf(tmpname, "%d", minor); - - create_proc_read_entry(tmpname, 0 , cowlo_procdir, - cowlo_readproc, cowdev); - } - - cowdev->state |= COWDEVOPEN; - - cowdev->rdoname = rdof; - cowdev->cowname = cowf; - - /* - ** enable the new disk; this triggers the first request! - */ - DEBUGP(DCOW"cowloop - call add_disk....\n"); - - add_disk(cowdev->gd); - - up(&cowdevlock); - return 0; -} - -/* -** close a cowdevice (pair of rdofile/cowfile) and release memory -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_closepair(struct cowloop_device *cowdev) -{ - int minor; - - down(&cowdevlock); - - /* - ** if cowdevice is not activated at all, refuse - */ - if ( !(cowdev->state & COWDEVOPEN) ) { - up(&cowdevlock); - return -ENODEV; - } - - /* - ** if this cowdevice is still open, refuse - */ - if (cowdev->opencnt > 0) { - up(&cowdevlock); - return -EBUSY; - } - - up(&cowdevlock); - - /* - ** wakeup watcher (if any) - */ - if (cowdev->state & COWWATCHDOG) { - cowdev->watchthresh = cowdev->blkavail; - wake_up_interruptible(&cowdev->watchq); - } - - /* - ** wakeup kernel-thread to be able to exit - ** and wait until it has exited - */ - cowdev->closedown = 1; - cowdev->qfilled = 1; - wake_up_interruptible(&cowdev->waitq); - - while (cowdev->pid) - schedule(); - - del_gendisk(cowdev->gd); /* revert the alloc_disk() */ - put_disk(cowdev->gd); /* revert the add_disk() */ - - if (cowlo_procdir) { - char tmpname[64]; - - for (minor = 0; minor < maxcows; minor++) { - if (cowdev == cowdevall[minor]) break; - } - sprintf(tmpname, "%d", minor); - - remove_proc_entry(tmpname, cowlo_procdir); - } - - blk_cleanup_queue(cowdev->rqueue); - - /* - ** release memory for filenames if these names have - ** been allocated dynamically - */ - if ( (cowdev->cowname) && (cowdev->cowname != cowfile)) - kfree(cowdev->cowname); - - if ( (cowdev->rdoname) && (cowdev->rdoname != rdofile)) - kfree(cowdev->rdoname); - - cowlo_undo_openrdo(cowdev); - cowlo_undo_opencow(cowdev); - - cowdev->state &= ~COWDEVOPEN; - - return 0; -} - -/* -** open the read-only file -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_openrdo(struct cowloop_device *cowdev, char *rdof) -{ - struct file *f; - struct inode *inode; - long int i, nrval; - - DEBUGP(DCOW"cowloop - openrdo called\n"); - - /* - ** open the read-only file - */ - if(*rdof == '\0') { - printk(KERN_ERR - "cowloop - specify name for read-only file\n\n"); - return -EINVAL; - } - - f = filp_open(rdof, O_RDONLY|O_LARGEFILE, 0); - - if ( (f == NULL) || IS_ERR(f) ) { - printk(KERN_ERR - "cowloop - open of rdofile %s failed\n", rdof); - return -EINVAL; - } - - cowdev->rdofp = f; - - inode = f->f_dentry->d_inode; - - if ( !S_ISREG(inode->i_mode) && !S_ISBLK(inode->i_mode) ) { - printk(KERN_ERR - "cowloop - %s not regular file or blockdev\n", rdof); - return -EINVAL; - } - - DEBUGP(DCOW"cowloop - determine size rdo....\n"); - - /* - ** determine block-size and total size of read-only file - */ - if (S_ISREG(inode->i_mode)) { - /* - ** read-only file is a regular file - */ - cowdev->blocksz = 512; /* other value fails */ - cowdev->numblocks = inode->i_size >> MUSHIFT; - - if (inode->i_size & MUMASK) { - printk(KERN_WARNING - "cowloop - rdofile %s truncated to multiple " - "of %d bytes\n", rdof, MAPUNIT); - } - - DEBUGP(DCOW"cowloop - RO=regular: numblocks=%d, blocksz=%d\n", - cowdev->numblocks, cowdev->blocksz); - } else { - /* - ** read-only file is a block device - */ - cowdev->belowdev = inode->i_bdev; - cowdev->belowgd = cowdev->belowdev->bd_disk; /* gendisk */ - - if (cowdev->belowdev->bd_part) { - cowdev->numblocks = cowdev->belowdev->bd_part->nr_sects - / (MAPUNIT/512); - } - - if (cowdev->belowgd) { - cowdev->belowq = cowdev->belowgd->queue; - - if (cowdev->numblocks == 0) { - cowdev->numblocks = get_capacity(cowdev->belowgd) - / (MAPUNIT/512); - } - } - - - if (cowdev->belowq) - cowdev->blocksz = queue_logical_block_size(cowdev->belowq); - - if (cowdev->blocksz == 0) - cowdev->blocksz = BLOCK_SIZE; /* default 2^10 */ - - DEBUGP(DCOW"cowloop - numblocks=%d, " - "blocksz=%d, belowgd=%p, belowq=%p\n", - cowdev->numblocks, cowdev->blocksz, - cowdev->belowgd, cowdev->belowq); - - DEBUGP(DCOW"cowloop - belowdev.bd_block_size=%d\n", - cowdev->belowdev->bd_block_size); - } - - if (cowdev->numblocks == 0) { - printk(KERN_ERR "cowloop - %s has no contents\n", rdof); - return -EINVAL; - } - - /* - ** reserve space in memory as generic I/O buffer - */ - cowdev->iobuf = kmalloc(MAPUNIT, GFP_KERNEL); - - if (!cowdev->iobuf) { - printk(KERN_ERR - "cowloop - cannot get space for buffer %d\n", MAPUNIT); - return -ENOMEM; - } - - DEBUGP(DCOW"cowloop - determine fingerprint rdo....\n"); - - /* - ** determine fingerprint for read-only file - ** calculate fingerprint from first four datablocks - ** which do not contain binary zeroes - */ - for (i=0, cowdev->fingerprint=0, nrval=0; - (nrval < 4)&&(i < cowdev->numblocks); i++) { - int j; - unsigned char cs; - - /* - ** read next block - */ - if (cowlo_readrdo(cowdev, cowdev->iobuf, MAPUNIT, - (loff_t)i << MUSHIFT) < 1) - break; - - /* - ** calculate fingerprint by adding all byte-values - */ - for (j=0, cs=0; j < MAPUNIT; j++) - cs += *(cowdev->iobuf+j); - - if (cs == 0) /* block probably contained zeroes */ - continue; - - /* - ** shift byte-value to proper place in final fingerprint - */ - cowdev->fingerprint |= cs << (nrval*8); - nrval++; - } - - return 0; -} - -/* -** undo memory allocs and file opens issued so far -** related to the read-only file -*/ -static void -cowlo_undo_openrdo(struct cowloop_device *cowdev) -{ - if(cowdev->iobuf); - kfree(cowdev->iobuf); - - if (cowdev->rdofp) - filp_close(cowdev->rdofp, 0); -} - -/* -** open the cowfile -** -** returns: -** 0 - okay -** < 0 - error value -*/ -static int -cowlo_opencow(struct cowloop_device *cowdev, char *cowf, int autorecover) -{ - long int i, rv; - int minor; - unsigned long nb; - struct file *f; - struct inode *inode; - loff_t offset; - struct cowloop_device *cowtmp; - - DEBUGP(DCOW"cowloop - opencow called\n"); - - /* - ** open copy-on-write file (read-write) - */ - if (cowf[0] == '\0') { - printk(KERN_ERR - "cowloop - specify name of copy-on-write file\n\n"); - return -EINVAL; - } - - f = filp_open(cowf, O_RDWR|O_LARGEFILE, 0600); - - if ( (f == NULL) || IS_ERR(f) ) { - /* - ** non-existing cowfile: try to create - */ - f = filp_open(cowf, O_RDWR|O_CREAT|O_LARGEFILE, 0600); - - if ( (f == NULL) || IS_ERR(f) ) { - printk(KERN_ERR - "cowloop - failed to open file %s for read-write\n\n", - cowf); - return -EINVAL; - } - } - - cowdev->cowfp = f; - - inode = f->f_dentry->d_inode; - - if (!S_ISREG(inode->i_mode)) { - printk(KERN_ERR "cowloop - %s is not regular file\n", cowf); - return -EINVAL; - } - - /* - ** check if this cowfile is already in use for another cowdevice - */ - for (minor = 0; minor < maxcows; minor++) { - - cowtmp = cowdevall[minor]; - - if ( !(cowtmp->state & COWDEVOPEN) ) - continue; - - if (cowtmp == cowdev) - continue; - - if (cowtmp->cowfp->f_dentry->d_inode == f->f_dentry->d_inode) { - printk(KERN_ERR - "cowloop - %s: already in use as cow\n", cowf); - return -EBUSY; - } - } - - /* - ** mark cowfile open for read-write - */ - cowdev->state |= COWRWCOWOPEN; - - /* - ** calculate size (in bytes) for total bitmap in cowfile; - ** when the size of the cowhead block is added, the start-offset - ** for the modified data blocks can be found - */ - nb = cowdev->numblocks; - - if (nb%8) /* transform #bits to #bytes */ - nb+=8; /* rounded if necessary */ - nb /= 8; - - if (nb & MUMASK) /* round up #bytes to MAPUNIT chunks */ - cowdev->mapsize = ( (nb>>MUSHIFT) +1) << MUSHIFT; - else - cowdev->mapsize = nb; - - /* - ** reserve space in memory for the cowhead - */ - cowdev->cowhead = kmalloc(MAPUNIT, GFP_KERNEL); - - if (!cowdev->cowhead) { - printk(KERN_ERR "cowloop - cannot get space for cowhead %d\n", - MAPUNIT); - return -ENOMEM; - } - - memset(cowdev->cowhead, 0, MAPUNIT); - - DEBUGP(DCOW"cowloop - prepare cowhead....\n"); - - /* - ** check if the cowfile exists or should be created - */ - if (inode->i_size != 0) { - /* - ** existing cowfile: read the cow head - */ - if (inode->i_size < MAPUNIT) { - printk(KERN_ERR - "cowloop - existing cowfile %s too small\n", - cowf); - return -EINVAL; - } - - cowlo_readcowraw(cowdev, cowdev->cowhead, MAPUNIT, (loff_t) 0); - - /* - ** verify if the existing file is really a cowfile - */ - if (cowdev->cowhead->magic != COWMAGIC) { - printk(KERN_ERR - "cowloop - cowfile %s has incorrect format\n", - cowf); - return -EINVAL; - } - - /* - ** verify the cowhead version of the cowfile - */ - if (cowdev->cowhead->version > COWVERSION) { - printk(KERN_ERR - "cowloop - cowfile %s newer than this driver\n", - cowf); - return -EINVAL; - } - - /* - ** make sure that this is not a packed cowfile - */ - if (cowdev->cowhead->flags & COWPACKED) { - printk(KERN_ERR - "cowloop - packed cowfile %s not accepted\n", cowf); - return -EINVAL; - } - - /* - ** verify if the cowfile has been properly closed - */ - if (cowdev->cowhead->flags & COWDIRTY) { - /* - ** cowfile was not properly closed; - ** check if automatic recovery is required - ** (actual recovery will be done later on) - */ - if (!autorecover) { - printk(KERN_ERR - "cowloop - cowfile %s is dirty " - "(not properly closed by rmmod?)\n", - cowf); - printk(KERN_ERR - "cowloop - run cowrepair or specify " - "'option=r' to recover\n"); - return -EINVAL; - } - } - - /* - ** verify if the cowfile is really related to this rdofile - */ - if (cowdev->cowhead->rdoblocks != cowdev->numblocks) { - printk(KERN_ERR - "cowloop - cowfile %s (size %lld) not related " - "to rdofile (size %lld)\n", - cowf, - (long long)cowdev->cowhead->rdoblocks <<MUSHIFT, - (long long)cowdev->numblocks <<MUSHIFT); - return -EINVAL; - } - - if (cowdev->cowhead->rdofingerprint != cowdev->fingerprint) { - printk(KERN_ERR - "cowloop - cowfile %s not related to rdofile " - " (fingerprint err - rdofile modified?)\n", cowf); - return -EINVAL; - } - } else { - /* - ** new cowfile: determine the minimal size (cowhead+bitmap) - */ - offset = (loff_t) MAPUNIT + cowdev->mapsize - 1; - - if ( cowlo_writecowraw(cowdev, "", 1, offset) < 1) { - printk(KERN_ERR - "cowloop - cannot set cowfile to size %lld\n", - offset+1); - return -EINVAL; - } - - /* - ** prepare new cowhead - */ - cowdev->cowhead->magic = COWMAGIC; - cowdev->cowhead->version = COWVERSION; - cowdev->cowhead->mapunit = MAPUNIT; - cowdev->cowhead->mapsize = cowdev->mapsize; - cowdev->cowhead->rdoblocks = cowdev->numblocks; - cowdev->cowhead->rdofingerprint = cowdev->fingerprint; - cowdev->cowhead->cowused = 0; - - /* - ** calculate start offset of data in cowfile, - ** rounded up to multiple of 4K to avoid - ** unnecessary disk-usage for written datablocks in - ** the sparsed cowfile on e.g. 4K filesystems - */ - cowdev->cowhead->doffset = - ((MAPUNIT+cowdev->mapsize+4095)>>12)<<12; - } - - cowdev->cowhead->flags = 0; - - DEBUGP(DCOW"cowloop - reserve space bitmap....\n"); - - /* - ** reserve space in memory for the entire bitmap and - ** fill it with the bitmap-data from disk; the entire - ** bitmap is allocated in several chunks because kmalloc - ** has restrictions regarding the allowed size per kmalloc - */ - cowdev->mapcount = (cowdev->mapsize+MAPCHUNKSZ-1)/MAPCHUNKSZ; - - /* - ** the size of every bitmap chunk will be MAPCHUNKSZ bytes, except for - ** the last bitmap chunk: calculate remaining size for this chunk - */ - if (cowdev->mapsize % MAPCHUNKSZ == 0) - cowdev->mapremain = MAPCHUNKSZ; - else - cowdev->mapremain = cowdev->mapsize % MAPCHUNKSZ; - - /* - ** allocate space to store all pointers for the bitmap-chunks - ** (initialize area with zeroes to allow proper undo) - */ - cowdev->mapcache = kmalloc(cowdev->mapcount * sizeof(char *), - GFP_KERNEL); - if (!cowdev->mapcache) { - printk(KERN_ERR - "cowloop - can not allocate space for bitmap ptrs\n"); - return -ENOMEM; - } - - memset(cowdev->mapcache, 0, cowdev->mapcount * sizeof(char *)); - - /* - ** allocate space to store the bitmap-chunks themselves - */ - for (i=0; i < cowdev->mapcount; i++) { - if (i < (cowdev->mapcount-1)) - *(cowdev->mapcache+i) = kmalloc(MAPCHUNKSZ, GFP_KERNEL); - else - *(cowdev->mapcache+i) = kmalloc(cowdev->mapremain, - GFP_KERNEL); - - if (*(cowdev->mapcache+i) == NULL) { - printk(KERN_ERR "cowloop - no space for bitmapchunk %ld" - " totmapsz=%ld, mapcnt=%d mapunit=%d\n", - i, cowdev->mapsize, cowdev->mapcount, - MAPUNIT); - return -ENOMEM; - } - } - - DEBUGP(DCOW"cowloop - read bitmap from cow....\n"); - - /* - ** read the entire bitmap from the cowfile into the in-memory cache; - ** count the number of blocks that are in use already - ** (statistical purposes) - */ - for (i=0, offset=MAPUNIT; i < cowdev->mapcount; - i++, offset+=MAPCHUNKSZ) { - unsigned long numbytes; - - if (i < (cowdev->mapcount-1)) - /* - ** full bitmap chunk - */ - numbytes = MAPCHUNKSZ; - else - /* - ** last bitmap chunk: might be partly filled - */ - numbytes = cowdev->mapremain; - - cowlo_readcowraw(cowdev, *(cowdev->mapcache+i), - numbytes, offset); - } - - /* - ** if the cowfile was dirty and automatic recovery is required, - ** reconstruct a proper bitmap in memory now - */ - if (cowdev->cowhead->flags & COWDIRTY) { - unsigned long long blocknum; - char databuf[MAPUNIT]; - unsigned long mapnum, mapbyte, mapbit; - - printk(KERN_NOTICE "cowloop - recover dirty cowfile %s....\n", - cowf); - - /* - ** read all data blocks - */ - for (blocknum=0, rv=1, offset=0; - cowlo_readcow(cowdev, databuf, MAPUNIT, offset) > 0; - blocknum++, offset += MAPUNIT) { - - /* - ** if this datablock contains real data (not binary - ** zeroes), set the corresponding bit in the bitmap - */ - if ( memcmp(databuf, allzeroes, MAPUNIT) == 0) - continue; - - mapnum = CALCMAP (blocknum); - mapbyte = CALCBYTE(blocknum); - mapbit = CALCBIT (blocknum); - - *(*(cowdev->mapcache+mapnum)+mapbyte) |= (1<<mapbit); - } - - printk(KERN_NOTICE "cowloop - cowfile recovery completed\n"); - } - - /* - ** count all bits set in the bitmaps for statistical purposes - */ - for (i=0, cowdev->nrcowblocks = 0; i < cowdev->mapcount; i++) { - long numbytes; - char *p; - - if (i < (cowdev->mapcount-1)) - numbytes = MAPCHUNKSZ; - else - numbytes = cowdev->mapremain; - - p = *(cowdev->mapcache+i); - - for (numbytes--; numbytes >= 0; numbytes--, p++) { - /* - ** for only eight checks the following construction - ** is faster than a loop-construction - */ - if ((*p) & 0x01) cowdev->nrcowblocks++; - if ((*p) & 0x02) cowdev->nrcowblocks++; - if ((*p) & 0x04) cowdev->nrcowblocks++; - if ((*p) & 0x08) cowdev->nrcowblocks++; - if ((*p) & 0x10) cowdev->nrcowblocks++; - if ((*p) & 0x20) cowdev->nrcowblocks++; - if ((*p) & 0x40) cowdev->nrcowblocks++; - if ((*p) & 0x80) cowdev->nrcowblocks++; - } - } - - /* - ** consistency-check for number of bits set in bitmap - */ - if ( !(cowdev->cowhead->flags & COWDIRTY) && - (cowdev->cowhead->cowused != cowdev->nrcowblocks) ) { - printk(KERN_ERR "cowloop - inconsistent cowfile admi\n"); - return -EINVAL; - } - - return 0; -} - -/* -** undo memory allocs and file opens issued so far -** related to the cowfile -*/ -static void -cowlo_undo_opencow(struct cowloop_device *cowdev) -{ - int i; - - if (cowdev->mapcache) { - for (i=0; i < cowdev->mapcount; i++) { - if (*(cowdev->mapcache+i) != NULL) - kfree( *(cowdev->mapcache+i) ); - } - - kfree(cowdev->mapcache); - } - - if (cowdev->cowhead) - kfree(cowdev->cowhead); - - if ( (cowdev->state & COWCOWOPEN) && (cowdev->cowfp) ) - filp_close(cowdev->cowfp, 0); - - /* - ** mark cowfile closed - */ - cowdev->state &= ~COWCOWOPEN; -} - -/* -** flush the entire bitmap and the cowhead (clean) to the cowfile -** -** must be called with the cowdevices-lock set -*/ -static void -cowlo_sync(void) -{ - int i, minor; - loff_t offset; - struct cowloop_device *cowdev; - - for (minor=0; minor < maxcows; minor++) { - cowdev = cowdevall[minor]; - if ( ! (cowdev->state & COWRWCOWOPEN) ) - continue; - - for (i=0, offset=MAPUNIT; i < cowdev->mapcount; - i++, offset += MAPCHUNKSZ) { - unsigned long numbytes; - - if (i < (cowdev->mapcount-1)) - /* - ** full bitmap chunk - */ - numbytes = MAPCHUNKSZ; - else - /* - ** last bitmap chunk: might be partly filled - */ - numbytes = cowdev->mapremain; - - DEBUGP(DCOW - "cowloop - flushing bitmap %2d (%3ld Kb)\n", - i, numbytes/1024); - - if (cowlo_writecowraw(cowdev, *(cowdev->mapcache+i), - numbytes, offset) < numbytes) { - break; - } - } - - /* - ** flush clean up-to-date cowhead to cowfile - */ - cowdev->cowhead->cowused = cowdev->nrcowblocks; - cowdev->cowhead->flags &= ~COWDIRTY; - - DEBUGP(DCOW "cowloop - flushing cowhead (%3d Kb)\n", - MAPUNIT/1024); - - cowlo_writecowraw(cowdev, cowdev->cowhead, MAPUNIT, (loff_t) 0); - } -} - -/*****************************************************************************/ -/* Module loading/unloading */ -/*****************************************************************************/ - -/* -** called during insmod/modprobe -*/ -static int __init -cowlo_init_module(void) -{ - int rv; - int minor, uptocows; - - revision[sizeof revision - 3] = '\0'; - - printk(KERN_NOTICE "cowloop - (C) 2009 ATComputing.nl - version: %s\n", &revision[11]); - printk(KERN_NOTICE "cowloop - info: www.ATComputing.nl/cowloop\n"); - - memset(allzeroes, 0, MAPUNIT); - - /* - ** Setup administration for all possible cowdevices. - ** Note that their minor numbers go from 0 to MAXCOWS-1 inclusive - ** and minor == MAXCOWS-1 is reserved for the control device. - */ - if ((maxcows < 1) || (maxcows > MAXCOWS)) { - printk(KERN_WARNING - "cowloop - maxcows exceeds maximum of %d\n", MAXCOWS); - - maxcows = DFLCOWS; - } - - /* allocate room for a table with a pointer to each cowloop_device: */ - if ( (cowdevall = kmalloc(maxcows * sizeof(struct cowloop_device *), - GFP_KERNEL)) == NULL) { - printk(KERN_WARNING - "cowloop - can not alloc table for %d devs\n", maxcows); - uptocows = 0; - rv = -ENOMEM; - goto error_out; - } - memset(cowdevall, 0, maxcows * sizeof(struct cowloop_device *)); - /* then hook an actual cowloop_device struct to each pointer: */ - for (minor=0; minor < maxcows; minor++) { - if ((cowdevall[minor] = kmalloc(sizeof(struct cowloop_device), - GFP_KERNEL)) == NULL) { - printk(KERN_WARNING - "cowloop - can not alloc admin-struct for dev no %d\n", minor); - - uptocows = minor; /* this is how far we got.... */ - rv = -ENOMEM; - goto error_out; - } - memset(cowdevall[minor], 0, sizeof(struct cowloop_device)); - } - uptocows = maxcows; /* we got all devices */ - - sema_init(&cowdevlock, 1); - - /* - ** register cowloop module - */ - if ( register_blkdev(COWMAJOR, DEVICE_NAME) < 0) { - printk(KERN_WARNING - "cowloop - unable to get major %d for cowloop\n", COWMAJOR); - rv = -EIO; - goto error_out; - } - - /* - ** create a directory below /proc to allocate a file - ** for each cowdevice that is allocated later on - */ - cowlo_procdir = proc_mkdir("cow", NULL); - - /* - ** check if a cowdevice has to be opened during insmod/modprobe; - ** two parameters should be specified then: rdofile= and cowfile= - */ - if( (rdofile[0] != '\0') && (cowfile[0] != '\0') ) { - char *po = option; - int wantrecover = 0; - - /* - ** check if automatic recovery is wanted - */ - while (*po) { - if (*po == 'r') { - wantrecover = 1; - break; - } - po++; - } - - /* - ** open new cowdevice with minor number 0 - */ - if ( (rv = cowlo_openpair(rdofile, cowfile, wantrecover, 0))) { - remove_proc_entry("cow", NULL); - unregister_blkdev(COWMAJOR, DEVICE_NAME); - goto error_out; - } - } else { - /* - ** check if only one parameter has been specified - */ - if( (rdofile[0] != '\0') || (cowfile[0] != '\0') ) { - printk(KERN_ERR - "cowloop - only one filename specified\n"); - remove_proc_entry("cow", NULL); - unregister_blkdev(COWMAJOR, DEVICE_NAME); - rv = -EINVAL; - goto error_out; - } - } - - /* - ** allocate fake disk as control channel to handle the requests - ** to activate and deactivate cowdevices dynamically - */ - if (!(cowctlgd = alloc_disk(1))) { - printk(KERN_WARNING - "cowloop - unable to alloc_disk for cowctl\n"); - - remove_proc_entry("cow", NULL); - (void) cowlo_closepair(cowdevall[0]); - unregister_blkdev(COWMAJOR, DEVICE_NAME); - rv = -ENOMEM; - goto error_out; - } - - spin_lock_init(&cowctlrqlock); - cowctlgd->major = COWMAJOR; - cowctlgd->first_minor = COWCTL; - cowctlgd->minors = 1; - cowctlgd->fops = &cowlo_fops; - cowctlgd->private_data = NULL; - /* the device has capacity 0, so there will be no q-requests */ - cowctlgd->queue = blk_init_queue(NULL, &cowctlrqlock); - sprintf(cowctlgd->disk_name, "cowctl"); - set_capacity(cowctlgd, 0); - - add_disk(cowctlgd); - - printk(KERN_NOTICE "cowloop - number of configured cowdevices: %d\n", - maxcows); - if (rdofile[0] != '\0') { - printk(KERN_NOTICE "cowloop - initialized on rdofile=%s\n", - rdofile); - } else { - printk(KERN_NOTICE "cowloop - initialized without rdofile yet\n"); - } - return 0; - -error_out: - for (minor=0; minor < uptocows ; minor++) { - kfree(cowdevall[minor]); - } - kfree(cowdevall); - return rv; -} - -/* -** called during rmmod -*/ -static void __exit -cowlo_cleanup_module(void) -{ - int minor; - - /* - ** flush bitmaps and cowheads to the cowfiles - */ - down(&cowdevlock); - cowlo_sync(); - up(&cowdevlock); - - /* - ** close all cowdevices - */ - for (minor=0; minor < maxcows; minor++) - (void) cowlo_closepair(cowdevall[minor]); - - unregister_blkdev(COWMAJOR, DEVICE_NAME); - - /* - ** get rid of /proc/cow and unregister the driver - */ - remove_proc_entry("cow", NULL); - - for (minor = 0; minor < maxcows; minor++) { - kfree(cowdevall[minor]); - } - kfree(cowdevall); - - del_gendisk(cowctlgd); /* revert the alloc_disk() */ - put_disk (cowctlgd); /* revert the add_disk() */ - blk_cleanup_queue(cowctlgd->queue); /* cleanup the empty queue */ - - printk(KERN_NOTICE "cowloop - unloaded\n"); -} - -module_init(cowlo_init_module); -module_exit(cowlo_cleanup_module); diff --git a/drivers/staging/cowloop/cowloop.h b/drivers/staging/cowloop/cowloop.h deleted file mode 100644 index bbd4a35ac667..000000000000 --- a/drivers/staging/cowloop/cowloop.h +++ /dev/null @@ -1,66 +0,0 @@ -/* -** DO NOT MODIFY THESE VALUES (would make old cowfiles unusable) -*/ -#define MAPUNIT 1024 /* blocksize for bit in bitmap */ -#define MUSHIFT 10 /* bitshift for bit in bitmap */ -#define MUMASK 0x3ff /* bitmask for bit in bitmap */ - -#define COWMAGIC 0x574f437f /* byte-swapped '7f C O W' */ -#define COWDIRTY 0x01 -#define COWPACKED 0x02 -#define COWVERSION 1 - -struct cowhead -{ - int magic; /* identifies a cowfile */ - short version; /* version of cowhead */ - short flags; /* flags indicating status */ - unsigned long mapunit; /* blocksize per bit in bitmap */ - unsigned long mapsize; /* total size of bitmap (bytes) */ - unsigned long doffset; /* start-offset datablocks in cow */ - unsigned long rdoblocks; /* size of related read-only file */ - unsigned long rdofingerprint; /* fingerprint of read-only file */ - unsigned long cowused; /* number of datablocks used in cow */ -}; - -#define COWDEVDIR "/dev/cow/" -#define COWDEVICE COWDEVDIR "%ld" -#define COWCONTROL COWDEVDIR "ctl" - -#define MAXCOWS 1024 -#define COWCTL (MAXCOWS-1) /* minor number of /dev/cow/ctl */ - -#define COWPROCDIR "/proc/cow/" -#define COWPROCFILE COWPROCDIR "%d" - -/* -** ioctl related stuff -*/ -#define ANYDEV ((unsigned long)-1) - -struct cowpair -{ - unsigned char *rdofile; /* pathname of the rdofile */ - unsigned char *cowfile; /* pathname of the cowfile */ - unsigned short rdoflen; /* length of rdofile pathname */ - unsigned short cowflen; /* length of cowfile pathname */ - unsigned long device; /* requested/returned device number */ -}; - -struct cowwatch -{ - int flags; /* request flags */ - unsigned long device; /* requested device number */ - unsigned long threshold; /* continue if free Kb < threshold */ - unsigned long totalkb; /* ret: total filesystem size (Kb) */ - unsigned long availkb; /* ret: free filesystem size (Kb) */ -}; - -#define WATCHWAIT 0x01 /* block until threshold reached */ - -#define COWSYNC _IO ('C', 1) -#define COWMKPAIR _IOW ('C', 2, struct cowpair) -#define COWRMPAIR _IOW ('C', 3, unsigned long) -#define COWWATCH _IOW ('C', 4, struct cowwatch) -#define COWCLOSE _IOW ('C', 5, unsigned long) -#define COWRDOPEN _IOW ('C', 6, unsigned long) diff --git a/drivers/staging/et131x/et1310_address_map.h b/drivers/staging/et131x/et1310_address_map.h index 6294d3814e72..2c3d65a622a7 100644 --- a/drivers/staging/et131x/et1310_address_map.h +++ b/drivers/staging/et131x/et1310_address_map.h @@ -223,7 +223,7 @@ typedef union _TXDMA_PR_NUM_DES_t { extern inline void add_10bit(u32 *v, int n) { - *v = INDEX10(*v + n); + *v = INDEX10(*v + n) | (*v & ET_DMA10_WRAP); } /* diff --git a/drivers/staging/et131x/et1310_rx.c b/drivers/staging/et131x/et1310_rx.c index 8f2e91fa0a86..10e21db57ac3 100644 --- a/drivers/staging/et131x/et1310_rx.c +++ b/drivers/staging/et131x/et1310_rx.c @@ -1177,12 +1177,20 @@ void et131x_handle_recv_interrupt(struct et131x_adapter *etdev) static inline u32 bump_fbr(u32 *fbr, u32 limit) { - u32 v = *fbr; - add_10bit(&v, 1); - if (v > limit) - v = (*fbr & ~ET_DMA10_MASK) ^ ET_DMA10_WRAP; - *fbr = v; - return v; + u32 v = *fbr; + v++; + /* This works for all cases where limit < 1024. The 1023 case + works because 1023++ is 1024 which means the if condition is not + taken but the carry of the bit into the wrap bit toggles the wrap + value correctly */ + if ((v & ET_DMA10_MASK) > limit) { + v &= ~ET_DMA10_MASK; + v ^= ET_DMA10_WRAP; + } + /* For the 1023 case */ + v &= (ET_DMA10_MASK|ET_DMA10_WRAP); + *fbr = v; + return v; } /** diff --git a/drivers/staging/hv/ChannelMgmt.h b/drivers/staging/hv/ChannelMgmt.h index a839d8fe6cec..fa973d86b624 100644 --- a/drivers/staging/hv/ChannelMgmt.h +++ b/drivers/staging/hv/ChannelMgmt.h @@ -26,6 +26,7 @@ #define _CHANNEL_MGMT_H_ #include <linux/list.h> +#include <linux/timer.h> #include "RingBuffer.h" #include "VmbusChannelInterface.h" #include "VmbusPacketFormat.h" @@ -54,7 +55,7 @@ enum vmbus_channel_message_type { ChannelMessageViewRangeRemove = 18, #endif ChannelMessageCount -} __attribute__((packed)); +}; struct vmbus_channel_message_header { enum vmbus_channel_message_type MessageType; diff --git a/drivers/staging/hv/NetVsc.c b/drivers/staging/hv/NetVsc.c index 1610b845198f..d384c0ddf069 100644 --- a/drivers/staging/hv/NetVsc.c +++ b/drivers/staging/hv/NetVsc.c @@ -1052,7 +1052,7 @@ static void NetVscOnReceive(struct hv_device *Device, */ spin_lock_irqsave(&netDevice->receive_packet_list_lock, flags); while (!list_empty(&netDevice->ReceivePacketList)) { - list_move_tail(&netDevice->ReceivePacketList, &listHead); + list_move_tail(netDevice->ReceivePacketList.next, &listHead); if (++count == vmxferpagePacket->RangeCount + 1) break; } @@ -1071,7 +1071,7 @@ static void NetVscOnReceive(struct hv_device *Device, /* Return it to the freelist */ spin_lock_irqsave(&netDevice->receive_packet_list_lock, flags); for (i = count; i != 0; i--) { - list_move_tail(&listHead, + list_move_tail(listHead.next, &netDevice->ReceivePacketList); } spin_unlock_irqrestore(&netDevice->receive_packet_list_lock, @@ -1085,8 +1085,7 @@ static void NetVscOnReceive(struct hv_device *Device, } /* Remove the 1st packet to represent the xfer page packet itself */ - xferpagePacket = list_entry(&listHead, struct xferpage_packet, - ListEntry); + xferpagePacket = (struct xferpage_packet*)listHead.next; list_del(&xferpagePacket->ListEntry); /* This is how much we can satisfy */ @@ -1102,8 +1101,7 @@ static void NetVscOnReceive(struct hv_device *Device, /* Each range represents 1 RNDIS pkt that contains 1 ethernet frame */ for (i = 0; i < (count - 1); i++) { - netvscPacket = list_entry(&listHead, struct hv_netvsc_packet, - ListEntry); + netvscPacket = (struct hv_netvsc_packet*)listHead.next; list_del(&netvscPacket->ListEntry); /* Initialize the netvsc packet */ diff --git a/drivers/staging/hv/TODO b/drivers/staging/hv/TODO index 4d390b237742..dbfbde937a66 100644 --- a/drivers/staging/hv/TODO +++ b/drivers/staging/hv/TODO @@ -1,11 +1,17 @@ TODO: - fix remaining checkpatch warnings and errors + - use of /** when it is not a kerneldoc header - remove RingBuffer.c to us in-kernel ringbuffer functions instead. - audit the vmbus to verify it is working properly with the driver model + - convert vmbus driver interface function pointer tables + to constant, a.k.a vmbus_ops - see if the vmbus can be merged with the other virtual busses in the kernel - audit the network driver + - use existing net_device_stats struct in network device + - checking for carrier inside open is wrong, network device API + confusion?? - audit the block driver - audit the scsi driver diff --git a/drivers/staging/hv/osd.c b/drivers/staging/hv/osd.c index 8fe543bd9910..3a4793a0fd05 100644 --- a/drivers/staging/hv/osd.c +++ b/drivers/staging/hv/osd.c @@ -30,6 +30,7 @@ #include <linux/ioport.h> #include <linux/irq.h> #include <linux/interrupt.h> +#include <linux/sched.h> #include <linux/wait.h> #include <linux/spinlock.h> #include <linux/workqueue.h> diff --git a/drivers/staging/hv/osd.h b/drivers/staging/hv/osd.h index 9504604c72bd..ce064e8ea644 100644 --- a/drivers/staging/hv/osd.h +++ b/drivers/staging/hv/osd.h @@ -25,6 +25,7 @@ #ifndef _OSD_H_ #define _OSD_H_ +#include <linux/workqueue.h> /* Defines */ #define ALIGN_UP(value, align) (((value) & (align-1)) ? \ diff --git a/drivers/staging/hv/vmbus_drv.c b/drivers/staging/hv/vmbus_drv.c index 582318f10222..894eecfc63ca 100644 --- a/drivers/staging/hv/vmbus_drv.c +++ b/drivers/staging/hv/vmbus_drv.c @@ -507,12 +507,12 @@ static struct hv_device *vmbus_child_device_create(struct hv_guid *type, child_device_obj = &child_device_ctx->device_obj; child_device_obj->context = context; - memcpy(&child_device_obj->deviceType, &type, sizeof(struct hv_guid)); - memcpy(&child_device_obj->deviceInstance, &instance, + memcpy(&child_device_obj->deviceType, type, sizeof(struct hv_guid)); + memcpy(&child_device_obj->deviceInstance, instance, sizeof(struct hv_guid)); - memcpy(&child_device_ctx->class_id, &type, sizeof(struct hv_guid)); - memcpy(&child_device_ctx->device_id, &instance, sizeof(struct hv_guid)); + memcpy(&child_device_ctx->class_id, type, sizeof(struct hv_guid)); + memcpy(&child_device_ctx->device_id, instance, sizeof(struct hv_guid)); DPRINT_EXIT(VMBUS_DRV); @@ -537,18 +537,7 @@ static int vmbus_child_device_register(struct hv_device *root_device_obj, DPRINT_DBG(VMBUS_DRV, "child device (%p) registering", child_device_ctx); - /* Make sure we are not registered already */ - if (strlen(dev_name(&child_device_ctx->device)) != 0) { - DPRINT_ERR(VMBUS_DRV, - "child device (%p) already registered - busid %s", - child_device_ctx, - dev_name(&child_device_ctx->device)); - - ret = -1; - goto Cleanup; - } - - /* Set the device bus id. Otherwise, device_register()will fail. */ + /* Set the device name. Otherwise, device_register() will fail. */ dev_set_name(&child_device_ctx->device, "vmbus_0_%d", atomic_inc_return(&device_num)); @@ -573,7 +562,6 @@ static int vmbus_child_device_register(struct hv_device *root_device_obj, DPRINT_INFO(VMBUS_DRV, "child device (%p) registered", &child_device_ctx->device); -Cleanup: DPRINT_EXIT(VMBUS_DRV); return ret; @@ -623,8 +611,6 @@ static void vmbus_child_device_destroy(struct hv_device *device_obj) static int vmbus_uevent(struct device *device, struct kobj_uevent_env *env) { struct device_context *device_ctx = device_to_device_context(device); - int i = 0; - int len = 0; int ret; DPRINT_ENTER(VMBUS_DRV); @@ -644,8 +630,6 @@ static int vmbus_uevent(struct device *device, struct kobj_uevent_env *env) device_ctx->class_id.data[14], device_ctx->class_id.data[15]); - env->envp_idx = i; - env->buflen = len; ret = add_uevent_var(env, "VMBUS_DEVICE_CLASS_GUID={" "%02x%02x%02x%02x-%02x%02x-%02x%02x-" "%02x%02x%02x%02x%02x%02x%02x%02x}", @@ -691,8 +675,6 @@ static int vmbus_uevent(struct device *device, struct kobj_uevent_env *env) if (ret) return ret; - env->envp[env->envp_idx] = NULL; - DPRINT_EXIT(VMBUS_DRV); return 0; diff --git a/drivers/staging/iio/Kconfig b/drivers/staging/iio/Kconfig index beb99a547f09..4586650d65c3 100644 --- a/drivers/staging/iio/Kconfig +++ b/drivers/staging/iio/Kconfig @@ -4,6 +4,7 @@ menuconfig IIO tristate "Industrial I/O support" + depends on !S390 ---help--- The industrial I/O subsystem provides a unified framework for drivers for many different types of embedded sensors using a diff --git a/drivers/staging/iio/industrialio-core.c b/drivers/staging/iio/industrialio-core.c index 1fa18f255814..768f44894d08 100644 --- a/drivers/staging/iio/industrialio-core.c +++ b/drivers/staging/iio/industrialio-core.c @@ -18,6 +18,8 @@ #include <linux/fs.h> #include <linux/interrupt.h> #include <linux/poll.h> +#include <linux/sched.h> +#include <linux/wait.h> #include <linux/cdev.h> #include "iio.h" #include "trigger_consumer.h" diff --git a/drivers/staging/otus/Kconfig b/drivers/staging/otus/Kconfig index d549d08fd495..f6cc2625e341 100644 --- a/drivers/staging/otus/Kconfig +++ b/drivers/staging/otus/Kconfig @@ -1,6 +1,6 @@ config OTUS tristate "Atheros OTUS 802.11n USB wireless support" - depends on USB && WLAN_80211 && MAC80211 + depends on USB && WLAN && MAC80211 default N ---help--- Enable support for Atheros 802.11n USB hardware: diff --git a/drivers/staging/p9auth/p9auth.c b/drivers/staging/p9auth/p9auth.c index 9111dcba37a1..8ccfff723eec 100644 --- a/drivers/staging/p9auth/p9auth.c +++ b/drivers/staging/p9auth/p9auth.c @@ -183,7 +183,7 @@ static ssize_t cap_write(struct file *filp, const char __user *buf, user_buf_running = NULL; hash_str = NULL; node_ptr = kmalloc(sizeof(struct cap_node), GFP_KERNEL); - user_buf = kzalloc(count, GFP_KERNEL); + user_buf = kzalloc(count+1, GFP_KERNEL); if (!node_ptr || !user_buf) goto out; @@ -207,6 +207,7 @@ static ssize_t cap_write(struct file *filp, const char __user *buf, list_add(&(node_ptr->list), &(dev->head->list)); node_ptr = NULL; } else { + char *tmpu; if (!cap_devices[0].head || list_empty(&(cap_devices[0].head->list))) { retval = -EINVAL; @@ -218,10 +219,10 @@ static ssize_t cap_write(struct file *filp, const char __user *buf, * need to split it and hash 'user1@user2' using 'randomstring' * as the key. */ - user_buf_running = kstrdup(user_buf, GFP_KERNEL); - source_user = strsep(&user_buf_running, "@"); - target_user = strsep(&user_buf_running, "@"); - rand_str = strsep(&user_buf_running, "@"); + tmpu = user_buf_running = kstrdup(user_buf, GFP_KERNEL); + source_user = strsep(&tmpu, "@"); + target_user = strsep(&tmpu, "@"); + rand_str = tmpu; if (!source_user || !target_user || !rand_str) { retval = -EINVAL; goto out; @@ -229,7 +230,8 @@ static ssize_t cap_write(struct file *filp, const char __user *buf, /* hash the string user1@user2 with rand_str as the key */ len = strlen(source_user) + strlen(target_user) + 1; - hash_str = kzalloc(len, GFP_KERNEL); + /* src, @, len, \0 */ + hash_str = kzalloc(len+1, GFP_KERNEL); strcat(hash_str, source_user); strcat(hash_str, "@"); strcat(hash_str, target_user); diff --git a/drivers/staging/panel/panel.c b/drivers/staging/panel/panel.c index dd7d3fde9699..4ce399b6d237 100644 --- a/drivers/staging/panel/panel.c +++ b/drivers/staging/panel/panel.c @@ -2071,11 +2071,15 @@ static void panel_detach(struct parport *port) return; } - if (keypad_enabled && keypad_initialized) + if (keypad_enabled && keypad_initialized) { misc_deregister(&keypad_dev); + keypad_initialized = 0; + } - if (lcd_enabled && lcd_initialized) + if (lcd_enabled && lcd_initialized) { misc_deregister(&lcd_dev); + lcd_initialized = 0; + } parport_release(pprt); parport_unregister_device(pprt); @@ -2211,13 +2215,16 @@ static void __exit panel_cleanup_module(void) del_timer(&scan_timer); if (pprt != NULL) { - if (keypad_enabled) + if (keypad_enabled) { misc_deregister(&keypad_dev); + keypad_initialized = 0; + } if (lcd_enabled) { panel_lcd_print("\x0cLCD driver " PANEL_VERSION "\nunloaded.\x1b[Lc\x1b[Lb\x1b[L-"); misc_deregister(&lcd_dev); + lcd_initialized = 0; } /* TODO: free all input signals */ diff --git a/drivers/staging/poch/poch.c b/drivers/staging/poch/poch.c index 0d111ddfabb2..2eb8e3d43c4d 100644 --- a/drivers/staging/poch/poch.c +++ b/drivers/staging/poch/poch.c @@ -20,6 +20,7 @@ #include <linux/init.h> #include <linux/ioctl.h> #include <linux/io.h> +#include <linux/sched.h> #include "poch.h" diff --git a/drivers/staging/rt2860/Kconfig b/drivers/staging/rt2860/Kconfig index 7f44e5e72463..efe38e25c5ed 100644 --- a/drivers/staging/rt2860/Kconfig +++ b/drivers/staging/rt2860/Kconfig @@ -1,5 +1,5 @@ config RT2860 tristate "Ralink 2860 wireless support" - depends on PCI && X86 && WLAN_80211 + depends on PCI && X86 && WLAN ---help--- This is an experimental driver for the Ralink 2860 wireless chip. diff --git a/drivers/staging/rt2860/common/cmm_data_2860.c b/drivers/staging/rt2860/common/cmm_data_2860.c index fb1735533b74..857ff450b6c9 100644 --- a/drivers/staging/rt2860/common/cmm_data_2860.c +++ b/drivers/staging/rt2860/common/cmm_data_2860.c @@ -363,6 +363,8 @@ int RtmpPCIMgmtKickOut( ULONG SwIdx = pAd->MgmtRing.TxCpuIdx; pTxD = (PTXD_STRUC) pAd->MgmtRing.Cell[SwIdx].AllocVa; + if (!pTxD) + return 0; pAd->MgmtRing.Cell[SwIdx].pNdisPacket = pPacket; pAd->MgmtRing.Cell[SwIdx].pNextNdisPacket = NULL; diff --git a/drivers/staging/rt2860/common/cmm_info.c b/drivers/staging/rt2860/common/cmm_info.c index 9d589c240ed0..019cc4474ce8 100644 --- a/drivers/staging/rt2860/common/cmm_info.c +++ b/drivers/staging/rt2860/common/cmm_info.c @@ -25,6 +25,7 @@ ************************************************************************* */ +#include <linux/sched.h> #include "../rt_config.h" INT Show_SSID_Proc( diff --git a/drivers/staging/rt2860/rt_linux.c b/drivers/staging/rt2860/rt_linux.c index b396a9b570e2..ed27b8545a1b 100644 --- a/drivers/staging/rt2860/rt_linux.c +++ b/drivers/staging/rt2860/rt_linux.c @@ -25,6 +25,7 @@ ************************************************************************* */ +#include <linux/sched.h> #include "rt_config.h" ULONG RTDebugLevel = RT_DEBUG_ERROR; diff --git a/drivers/staging/rt2870/Kconfig b/drivers/staging/rt2870/Kconfig index 76841f6dea93..aea5c8221810 100644 --- a/drivers/staging/rt2870/Kconfig +++ b/drivers/staging/rt2870/Kconfig @@ -1,5 +1,5 @@ config RT2870 tristate "Ralink 2870/3070 wireless support" - depends on USB && X86 && WLAN_80211 + depends on USB && X86 && WLAN ---help--- This is an experimental driver for the Ralink xx70 wireless chips. diff --git a/drivers/staging/rt3090/Kconfig b/drivers/staging/rt3090/Kconfig index 255e8eaa4836..2b3f745d72b7 100644 --- a/drivers/staging/rt3090/Kconfig +++ b/drivers/staging/rt3090/Kconfig @@ -1,5 +1,5 @@ config RT3090 tristate "Ralink 3090 wireless support" - depends on PCI && X86 && WLAN_80211 + depends on PCI && X86 && WLAN ---help--- This is an experimental driver for the Ralink 3090 wireless chip. diff --git a/drivers/staging/rt3090/common/cmm_info.c b/drivers/staging/rt3090/common/cmm_info.c index 5be0714666cb..3e51e98b474c 100644 --- a/drivers/staging/rt3090/common/cmm_info.c +++ b/drivers/staging/rt3090/common/cmm_info.c @@ -34,6 +34,7 @@ --------- ---------- ---------------------------------------------- */ +#include <linux/sched.h> #include "../rt_config.h" diff --git a/drivers/staging/rt3090/rt_linux.c b/drivers/staging/rt3090/rt_linux.c index d2241ecdf583..9b94aa6eb904 100644 --- a/drivers/staging/rt3090/rt_linux.c +++ b/drivers/staging/rt3090/rt_linux.c @@ -25,6 +25,7 @@ ************************************************************************* */ +#include <linux/sched.h> #include "rt_config.h" ULONG RTDebugLevel = RT_DEBUG_ERROR; diff --git a/drivers/staging/rtl8187se/Kconfig b/drivers/staging/rtl8187se/Kconfig index faf6c6087414..3211dd3765a0 100644 --- a/drivers/staging/rtl8187se/Kconfig +++ b/drivers/staging/rtl8187se/Kconfig @@ -1,6 +1,6 @@ config RTL8187SE tristate "RealTek RTL8187SE Wireless LAN NIC driver" - depends on PCI + depends on PCI && WLAN select WIRELESS_EXT select WEXT_PRIV default N diff --git a/drivers/staging/rtl8187se/ieee80211/ieee80211_crypt.c b/drivers/staging/rtl8187se/ieee80211/ieee80211_crypt.c index 013c3e19ae25..4c5d63fd5833 100644 --- a/drivers/staging/rtl8187se/ieee80211/ieee80211_crypt.c +++ b/drivers/staging/rtl8187se/ieee80211/ieee80211_crypt.c @@ -53,10 +53,8 @@ void ieee80211_crypt_deinit_entries(struct ieee80211_device *ieee, list_del(ptr); - if (entry->ops) { + if (entry->ops) entry->ops->deinit(entry->priv); - module_put(entry->ops->owner); - } kfree(entry); } } diff --git a/drivers/staging/rtl8187se/ieee80211/ieee80211_module.c b/drivers/staging/rtl8187se/ieee80211/ieee80211_module.c index 6fbe4890cb66..18392fce487d 100644 --- a/drivers/staging/rtl8187se/ieee80211/ieee80211_module.c +++ b/drivers/staging/rtl8187se/ieee80211/ieee80211_module.c @@ -189,10 +189,8 @@ void free_ieee80211(struct net_device *dev) for (i = 0; i < WEP_KEYS; i++) { struct ieee80211_crypt_data *crypt = ieee->crypt[i]; if (crypt) { - if (crypt->ops) { + if (crypt->ops) crypt->ops->deinit(crypt->priv); - module_put(crypt->ops->owner); - } kfree(crypt); ieee->crypt[i] = NULL; } diff --git a/drivers/staging/rtl8187se/ieee80211/ieee80211_softmac.c b/drivers/staging/rtl8187se/ieee80211/ieee80211_softmac.c index 59b2ab48cdcf..334e4c7ec61b 100644 --- a/drivers/staging/rtl8187se/ieee80211/ieee80211_softmac.c +++ b/drivers/staging/rtl8187se/ieee80211/ieee80211_softmac.c @@ -2839,16 +2839,12 @@ static int ieee80211_wpa_set_encryption(struct ieee80211_device *ieee, goto skip_host_crypt; ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - if (ops == NULL && strcmp(param->u.crypt.alg, "WEP") == 0) { - request_module("ieee80211_crypt_wep"); + if (ops == NULL && strcmp(param->u.crypt.alg, "WEP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - } else if (ops == NULL && strcmp(param->u.crypt.alg, "TKIP") == 0) { - request_module("ieee80211_crypt_tkip"); + else if (ops == NULL && strcmp(param->u.crypt.alg, "TKIP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - } else if (ops == NULL && strcmp(param->u.crypt.alg, "CCMP") == 0) { - request_module("ieee80211_crypt_ccmp"); + else if (ops == NULL && strcmp(param->u.crypt.alg, "CCMP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - } if (ops == NULL) { printk("unknown crypto alg '%s'\n", param->u.crypt.alg); param->u.crypt.err = IEEE_CRYPT_ERR_UNKNOWN_ALG; @@ -2869,7 +2865,7 @@ static int ieee80211_wpa_set_encryption(struct ieee80211_device *ieee, } memset(new_crypt, 0, sizeof(struct ieee80211_crypt_data)); new_crypt->ops = ops; - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(param->u.crypt.idx); diff --git a/drivers/staging/rtl8187se/ieee80211/ieee80211_wx.c b/drivers/staging/rtl8187se/ieee80211/ieee80211_wx.c index 8d8bdd0a130e..a08b97a09512 100644 --- a/drivers/staging/rtl8187se/ieee80211/ieee80211_wx.c +++ b/drivers/staging/rtl8187se/ieee80211/ieee80211_wx.c @@ -331,12 +331,10 @@ int ieee80211_wx_set_encode(struct ieee80211_device *ieee, return -ENOMEM; memset(new_crypt, 0, sizeof(struct ieee80211_crypt_data)); new_crypt->ops = ieee80211_get_crypto_ops("WEP"); - if (!new_crypt->ops) { - request_module("ieee80211_crypt_wep"); + if (!new_crypt->ops) new_crypt->ops = ieee80211_get_crypto_ops("WEP"); - } - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(key); if (!new_crypt->ops || !new_crypt->priv) { @@ -483,7 +481,7 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, struct iw_encode_ext *ext = (struct iw_encode_ext *)extra; int i, idx, ret = 0; int group_key = 0; - const char *alg, *module; + const char *alg; struct ieee80211_crypto_ops *ops; struct ieee80211_crypt_data **crypt; @@ -539,15 +537,12 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, switch (ext->alg) { case IW_ENCODE_ALG_WEP: alg = "WEP"; - module = "ieee80211_crypt_wep"; break; case IW_ENCODE_ALG_TKIP: alg = "TKIP"; - module = "ieee80211_crypt_tkip"; break; case IW_ENCODE_ALG_CCMP: alg = "CCMP"; - module = "ieee80211_crypt_ccmp"; break; default: IEEE80211_DEBUG_WX("%s: unknown crypto alg %d\n", @@ -558,10 +553,8 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, // printk("8-09-08-9=====>%s, alg name:%s\n",__func__, alg); ops = ieee80211_get_crypto_ops(alg); - if (ops == NULL) { - request_module(module); + if (ops == NULL) ops = ieee80211_get_crypto_ops(alg); - } if (ops == NULL) { IEEE80211_DEBUG_WX("%s: unknown crypto alg %d\n", dev->name, ext->alg); @@ -581,7 +574,7 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, goto done; } new_crypt->ops = ops; - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(idx); if (new_crypt->priv == NULL) { kfree(new_crypt); diff --git a/drivers/staging/rtl8192e/Kconfig b/drivers/staging/rtl8192e/Kconfig index 5c077b9fdc77..2ae3745f775f 100644 --- a/drivers/staging/rtl8192e/Kconfig +++ b/drivers/staging/rtl8192e/Kconfig @@ -1,6 +1,6 @@ config RTL8192E tristate "RealTek RTL8192E Wireless LAN NIC driver" - depends on PCI + depends on PCI && WLAN select WIRELESS_EXT select WEXT_PRIV default N diff --git a/drivers/staging/rtl8192e/ieee80211/ieee80211_crypt.c b/drivers/staging/rtl8192e/ieee80211/ieee80211_crypt.c index 1a8ea8a40c3c..b1c54932da3e 100644 --- a/drivers/staging/rtl8192e/ieee80211/ieee80211_crypt.c +++ b/drivers/staging/rtl8192e/ieee80211/ieee80211_crypt.c @@ -53,14 +53,8 @@ void ieee80211_crypt_deinit_entries(struct ieee80211_device *ieee, list_del(ptr); - if (entry->ops) { + if (entry->ops) entry->ops->deinit(entry->priv); -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0) - module_put(entry->ops->owner); -#else - __MOD_DEC_USE_COUNT(entry->ops->owner); -#endif - } kfree(entry); } } diff --git a/drivers/staging/rtl8192e/ieee80211/ieee80211_module.c b/drivers/staging/rtl8192e/ieee80211/ieee80211_module.c index 16256a31f993..12c2a18e1fa2 100644 --- a/drivers/staging/rtl8192e/ieee80211/ieee80211_module.c +++ b/drivers/staging/rtl8192e/ieee80211/ieee80211_module.c @@ -242,14 +242,8 @@ void free_ieee80211(struct net_device *dev) for (i = 0; i < WEP_KEYS; i++) { struct ieee80211_crypt_data *crypt = ieee->crypt[i]; if (crypt) { - if (crypt->ops) { + if (crypt->ops) crypt->ops->deinit(crypt->priv); -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0) - module_put(crypt->ops->owner); -#else - __MOD_DEC_USE_COUNT(crypt->ops->owner); -#endif - } kfree(crypt); ieee->crypt[i] = NULL; } diff --git a/drivers/staging/rtl8192e/ieee80211/ieee80211_softmac.c b/drivers/staging/rtl8192e/ieee80211/ieee80211_softmac.c index 2fc04df872ca..eae7c4579a68 100644 --- a/drivers/staging/rtl8192e/ieee80211/ieee80211_softmac.c +++ b/drivers/staging/rtl8192e/ieee80211/ieee80211_softmac.c @@ -3284,17 +3284,14 @@ static int ieee80211_wpa_set_encryption(struct ieee80211_device *ieee, goto skip_host_crypt; ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - if (ops == NULL && strcmp(param->u.crypt.alg, "WEP") == 0) { - request_module("ieee80211_crypt_wep"); + if (ops == NULL && strcmp(param->u.crypt.alg, "WEP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - //set WEP40 first, it will be modified according to WEP104 or WEP40 at other place - } else if (ops == NULL && strcmp(param->u.crypt.alg, "TKIP") == 0) { - request_module("ieee80211_crypt_tkip"); + /* set WEP40 first, it will be modified according to WEP104 or + * WEP40 at other place */ + else if (ops == NULL && strcmp(param->u.crypt.alg, "TKIP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - } else if (ops == NULL && strcmp(param->u.crypt.alg, "CCMP") == 0) { - request_module("ieee80211_crypt_ccmp"); + else if (ops == NULL && strcmp(param->u.crypt.alg, "CCMP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - } if (ops == NULL) { printk("unknown crypto alg '%s'\n", param->u.crypt.alg); param->u.crypt.err = IEEE_CRYPT_ERR_UNKNOWN_ALG; @@ -3315,11 +3312,7 @@ static int ieee80211_wpa_set_encryption(struct ieee80211_device *ieee, } memset(new_crypt, 0, sizeof(struct ieee80211_crypt_data)); new_crypt->ops = ops; -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0) - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) -#else - if (new_crypt->ops && try_inc_mod_count(new_crypt->ops->owner)) -#endif + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(param->u.crypt.idx); diff --git a/drivers/staging/rtl8192e/ieee80211/ieee80211_wx.c b/drivers/staging/rtl8192e/ieee80211/ieee80211_wx.c index 223483126b0e..4e34a1f4c66b 100644 --- a/drivers/staging/rtl8192e/ieee80211/ieee80211_wx.c +++ b/drivers/staging/rtl8192e/ieee80211/ieee80211_wx.c @@ -482,15 +482,9 @@ int ieee80211_wx_set_encode(struct ieee80211_device *ieee, return -ENOMEM; memset(new_crypt, 0, sizeof(struct ieee80211_crypt_data)); new_crypt->ops = ieee80211_get_crypto_ops("WEP"); - if (!new_crypt->ops) { - request_module("ieee80211_crypt_wep"); + if (!new_crypt->ops) new_crypt->ops = ieee80211_get_crypto_ops("WEP"); - } -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0) - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) -#else - if (new_crypt->ops && try_inc_mod_count(new_crypt->ops->owner)) -#endif + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(key); if (!new_crypt->ops || !new_crypt->priv) { @@ -644,7 +638,7 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, struct iw_encode_ext *ext = (struct iw_encode_ext *)extra; int i, idx; int group_key = 0; - const char *alg, *module; + const char *alg; struct ieee80211_crypto_ops *ops; struct ieee80211_crypt_data **crypt; @@ -711,15 +705,12 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, switch (ext->alg) { case IW_ENCODE_ALG_WEP: alg = "WEP"; - module = "ieee80211_crypt_wep"; break; case IW_ENCODE_ALG_TKIP: alg = "TKIP"; - module = "ieee80211_crypt_tkip"; break; case IW_ENCODE_ALG_CCMP: alg = "CCMP"; - module = "ieee80211_crypt_ccmp"; break; default: IEEE80211_DEBUG_WX("%s: unknown crypto alg %d\n", @@ -730,10 +721,8 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, printk("alg name:%s\n",alg); ops = ieee80211_get_crypto_ops(alg); - if (ops == NULL) { - request_module(module); + if (ops == NULL) ops = ieee80211_get_crypto_ops(alg); - } if (ops == NULL) { IEEE80211_DEBUG_WX("%s: unknown crypto alg %d\n", dev->name, ext->alg); @@ -758,7 +747,7 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, goto done; } new_crypt->ops = ops; - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(idx); if (new_crypt->priv == NULL) { kfree(new_crypt); diff --git a/drivers/staging/rtl8192e/r8192E_core.c b/drivers/staging/rtl8192e/r8192E_core.c index d4fa65489655..b0802a7aeb5f 100644 --- a/drivers/staging/rtl8192e/r8192E_core.c +++ b/drivers/staging/rtl8192e/r8192E_core.c @@ -46,6 +46,7 @@ #undef DEBUG_TX_DESC //#define CONFIG_RTL8192_IO_MAP +#include <linux/vmalloc.h> #include <asm/uaccess.h> #include "r8192E_hw.h" #include "r8192E.h" diff --git a/drivers/staging/rtl8192su/Kconfig b/drivers/staging/rtl8192su/Kconfig index 770f41280f21..b8c95f942069 100644 --- a/drivers/staging/rtl8192su/Kconfig +++ b/drivers/staging/rtl8192su/Kconfig @@ -1,6 +1,6 @@ config RTL8192SU tristate "RealTek RTL8192SU Wireless LAN NIC driver" - depends on PCI + depends on PCI && WLAN depends on WIRELESS_EXT default N ---help--- diff --git a/drivers/staging/rtl8192su/ieee80211/ieee80211_crypt.c b/drivers/staging/rtl8192su/ieee80211/ieee80211_crypt.c index d76a54d59d2f..521e7b989934 100644 --- a/drivers/staging/rtl8192su/ieee80211/ieee80211_crypt.c +++ b/drivers/staging/rtl8192su/ieee80211/ieee80211_crypt.c @@ -53,10 +53,8 @@ void ieee80211_crypt_deinit_entries(struct ieee80211_device *ieee, list_del(ptr); - if (entry->ops) { + if (entry->ops) entry->ops->deinit(entry->priv); - module_put(entry->ops->owner); - } kfree(entry); } } diff --git a/drivers/staging/rtl8192su/ieee80211/ieee80211_module.c b/drivers/staging/rtl8192su/ieee80211/ieee80211_module.c index 68dc8fa094cc..c3383bb8b760 100644 --- a/drivers/staging/rtl8192su/ieee80211/ieee80211_module.c +++ b/drivers/staging/rtl8192su/ieee80211/ieee80211_module.c @@ -216,10 +216,8 @@ void free_ieee80211(struct net_device *dev) for (i = 0; i < WEP_KEYS; i++) { struct ieee80211_crypt_data *crypt = ieee->crypt[i]; if (crypt) { - if (crypt->ops) { + if (crypt->ops) crypt->ops->deinit(crypt->priv); - module_put(crypt->ops->owner); - } kfree(crypt); ieee->crypt[i] = NULL; } diff --git a/drivers/staging/rtl8192su/ieee80211/ieee80211_softmac.c b/drivers/staging/rtl8192su/ieee80211/ieee80211_softmac.c index c64ae03f68a0..fd8e11252f1b 100644 --- a/drivers/staging/rtl8192su/ieee80211/ieee80211_softmac.c +++ b/drivers/staging/rtl8192su/ieee80211/ieee80211_softmac.c @@ -3026,17 +3026,14 @@ static int ieee80211_wpa_set_encryption(struct ieee80211_device *ieee, goto skip_host_crypt; ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - if (ops == NULL && strcmp(param->u.crypt.alg, "WEP") == 0) { - request_module("ieee80211_crypt_wep"); + if (ops == NULL && strcmp(param->u.crypt.alg, "WEP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - //set WEP40 first, it will be modified according to WEP104 or WEP40 at other place - } else if (ops == NULL && strcmp(param->u.crypt.alg, "TKIP") == 0) { - request_module("ieee80211_crypt_tkip"); + /* set WEP40 first, it will be modified according to WEP104 or + * WEP40 at other place */ + else if (ops == NULL && strcmp(param->u.crypt.alg, "TKIP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - } else if (ops == NULL && strcmp(param->u.crypt.alg, "CCMP") == 0) { - request_module("ieee80211_crypt_ccmp"); + else if (ops == NULL && strcmp(param->u.crypt.alg, "CCMP") == 0) ops = ieee80211_get_crypto_ops(param->u.crypt.alg); - } if (ops == NULL) { printk("unknown crypto alg '%s'\n", param->u.crypt.alg); param->u.crypt.err = IEEE_CRYPT_ERR_UNKNOWN_ALG; @@ -3058,7 +3055,7 @@ static int ieee80211_wpa_set_encryption(struct ieee80211_device *ieee, memset(new_crypt, 0, sizeof(struct ieee80211_crypt_data)); new_crypt->ops = ops; - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(param->u.crypt.idx); diff --git a/drivers/staging/rtl8192su/ieee80211/ieee80211_wx.c b/drivers/staging/rtl8192su/ieee80211/ieee80211_wx.c index 107759024335..6146c6435dde 100644 --- a/drivers/staging/rtl8192su/ieee80211/ieee80211_wx.c +++ b/drivers/staging/rtl8192su/ieee80211/ieee80211_wx.c @@ -358,11 +358,9 @@ int ieee80211_wx_set_encode(struct ieee80211_device *ieee, return -ENOMEM; memset(new_crypt, 0, sizeof(struct ieee80211_crypt_data)); new_crypt->ops = ieee80211_get_crypto_ops("WEP"); - if (!new_crypt->ops) { - request_module("ieee80211_crypt_wep"); + if (!new_crypt->ops) new_crypt->ops = ieee80211_get_crypto_ops("WEP"); - } - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(key); if (!new_crypt->ops || !new_crypt->priv) { @@ -507,7 +505,7 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, struct iw_encode_ext *ext = (struct iw_encode_ext *)extra; int i, idx; int group_key = 0; - const char *alg, *module; + const char *alg; struct ieee80211_crypto_ops *ops; struct ieee80211_crypt_data **crypt; @@ -570,15 +568,12 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, switch (ext->alg) { case IW_ENCODE_ALG_WEP: alg = "WEP"; - module = "ieee80211_crypt_wep"; break; case IW_ENCODE_ALG_TKIP: alg = "TKIP"; - module = "ieee80211_crypt_tkip"; break; case IW_ENCODE_ALG_CCMP: alg = "CCMP"; - module = "ieee80211_crypt_ccmp"; break; default: IEEE80211_DEBUG_WX("%s: unknown crypto alg %d\n", @@ -589,10 +584,8 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, printk("alg name:%s\n",alg); ops = ieee80211_get_crypto_ops(alg); - if (ops == NULL) { - request_module("%s", module); + if (ops == NULL) ops = ieee80211_get_crypto_ops(alg); - } if (ops == NULL) { IEEE80211_DEBUG_WX("%s: unknown crypto alg %d\n", dev->name, ext->alg); @@ -612,7 +605,7 @@ int ieee80211_wx_set_encode_ext(struct ieee80211_device *ieee, goto done; } new_crypt->ops = ops; - if (new_crypt->ops && try_module_get(new_crypt->ops->owner)) + if (new_crypt->ops) new_crypt->priv = new_crypt->ops->init(idx); if (new_crypt->priv == NULL) { kfree(new_crypt); diff --git a/drivers/staging/sep/sep_driver.c b/drivers/staging/sep/sep_driver.c index 87f8a1192762..f890a16096c0 100644 --- a/drivers/staging/sep/sep_driver.c +++ b/drivers/staging/sep/sep_driver.c @@ -38,6 +38,7 @@ #include <linux/mm.h> #include <linux/poll.h> #include <linux/wait.h> +#include <linux/sched.h> #include <linux/pci.h> #include <linux/firmware.h> #include <asm/ioctl.h> diff --git a/drivers/staging/stlc45xx/Kconfig b/drivers/staging/stlc45xx/Kconfig deleted file mode 100644 index 947fb75a9c68..000000000000 --- a/drivers/staging/stlc45xx/Kconfig +++ /dev/null @@ -1,8 +0,0 @@ -config STLC45XX - tristate "stlc4550/4560 support" - depends on MAC80211 && WLAN_80211 && SPI_MASTER && GENERIC_HARDIRQS - ---help--- - This is a driver for stlc4550 and stlc4560 chipsets. - - To compile this driver as a module, choose M here: the module will be - called stlc45xx. If unsure, say N. diff --git a/drivers/staging/stlc45xx/Makefile b/drivers/staging/stlc45xx/Makefile deleted file mode 100644 index 7ee32903055a..000000000000 --- a/drivers/staging/stlc45xx/Makefile +++ /dev/null @@ -1 +0,0 @@ -obj-$(CONFIG_STLC45XX) += stlc45xx.o diff --git a/drivers/staging/stlc45xx/stlc45xx.c b/drivers/staging/stlc45xx/stlc45xx.c deleted file mode 100644 index be99eb33d817..000000000000 --- a/drivers/staging/stlc45xx/stlc45xx.c +++ /dev/null @@ -1,2594 +0,0 @@ -/* - * This file is part of stlc45xx - * - * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies). - * - * Contact: Kalle Valo <kalle.valo@nokia.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * version 2 as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA - * 02110-1301 USA - * - */ - -#include "stlc45xx.h" - -#include <linux/module.h> -#include <linux/platform_device.h> -#include <linux/interrupt.h> -#include <linux/firmware.h> -#include <linux/delay.h> -#include <linux/irq.h> -#include <linux/spi/spi.h> -#include <linux/etherdevice.h> -#include <linux/gpio.h> -#include <linux/moduleparam.h> - -#include "stlc45xx_lmac.h" - -/* - * gpios should be handled in board files and provided via platform data, - * but because it's currently impossible for stlc45xx to have a header file - * in include/linux, let's use module paramaters for now - */ -static int stlc45xx_gpio_power = 97; -module_param(stlc45xx_gpio_power, int, 0444); -MODULE_PARM_DESC(stlc45xx_gpio_power, "stlc45xx gpio number for power line"); - -static int stlc45xx_gpio_irq = 87; -module_param(stlc45xx_gpio_irq, int, 0444); -MODULE_PARM_DESC(stlc45xx_gpio_irq, "stlc45xx gpio number for irq line"); - -static const u8 default_cal_channels[] = { - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x6c, 0x09, - 0x00, 0x00, 0xc9, 0xff, 0xd8, 0xff, 0x00, 0x00, 0x00, 0x01, 0x10, - 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0xe0, 0x00, 0xe0, 0x00, - 0xe0, 0x00, 0xe0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, - 0x00, 0x54, 0x01, 0xab, 0xf6, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, - 0xc0, 0x42, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, - 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x22, 0x01, 0x37, 0xa9, - 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0x00, 0xbc, 0x00, - 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, - 0x00, 0xbc, 0xfb, 0x00, 0xca, 0x79, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, - 0x2b, 0xc0, 0x2b, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, - 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0xd0, 0x00, 0x5d, - 0x54, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0x00, 0xaa, - 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, - 0xaa, 0x00, 0xaa, 0xa7, 0x00, 0xa9, 0x3d, 0xc0, 0x17, 0xc0, 0x17, - 0xc0, 0x17, 0xc0, 0x17, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, - 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x7a, 0x00, - 0x06, 0x2c, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0x00, - 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, - 0x00, 0x96, 0x00, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x06, 0x80, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x71, 0x09, 0x00, 0x00, 0xc9, 0xff, 0xd8, - 0xff, 0x00, 0x00, 0x00, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, - 0x10, 0x01, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xd0, - 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0x54, 0x01, 0xab, 0xf6, - 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0x00, 0xcb, 0x00, - 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, - 0x00, 0xcb, 0x22, 0x01, 0x37, 0xa9, 0xc0, 0x33, 0xc0, 0x33, 0xc0, - 0x33, 0xc0, 0x33, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, - 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0xfb, 0x00, 0xca, - 0x79, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0x00, 0xb4, - 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, - 0xb4, 0x00, 0xb4, 0xd0, 0x00, 0x5d, 0x54, 0xc0, 0x21, 0xc0, 0x21, - 0xc0, 0x21, 0xc0, 0x21, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, - 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0xa7, 0x00, - 0xa9, 0x3d, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0x00, - 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, - 0x00, 0xa0, 0x00, 0xa0, 0x7a, 0x00, 0x06, 0x2c, 0xc0, 0x0d, 0xc0, - 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, - 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x80, 0x80, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x76, - 0x09, 0x00, 0x00, 0xc9, 0xff, 0xd8, 0xff, 0x00, 0x00, 0x00, 0x01, - 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0xf0, 0x00, 0xf0, - 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, - 0xd0, 0x00, 0x54, 0x01, 0xab, 0xf6, 0xc0, 0x42, 0xc0, 0x42, 0xc0, - 0x42, 0xc0, 0x42, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, - 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x22, 0x01, 0x37, - 0xa9, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0x00, 0xbc, - 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, - 0xbc, 0x00, 0xbc, 0xfb, 0x00, 0xca, 0x79, 0xc0, 0x2b, 0xc0, 0x2b, - 0xc0, 0x2b, 0xc0, 0x2b, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, - 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0xd0, 0x00, - 0x5d, 0x54, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0x00, - 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, - 0x00, 0xaa, 0x00, 0xaa, 0xa7, 0x00, 0xa9, 0x3d, 0xc0, 0x17, 0xc0, - 0x17, 0xc0, 0x17, 0xc0, 0x17, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, - 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x7a, - 0x00, 0x06, 0x2c, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, - 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, - 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x06, 0x80, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x7b, 0x09, 0x00, 0x00, 0xc9, 0xff, - 0xd8, 0xff, 0x00, 0x00, 0x00, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, - 0x01, 0x10, 0x01, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, - 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0x54, 0x01, 0xab, - 0xf6, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0x00, 0xcb, - 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, - 0xcb, 0x00, 0xcb, 0x22, 0x01, 0x37, 0xa9, 0xc0, 0x33, 0xc0, 0x33, - 0xc0, 0x33, 0xc0, 0x33, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, - 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0xfb, 0x00, - 0xca, 0x79, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0x00, - 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, - 0x00, 0xb4, 0x00, 0xb4, 0xd0, 0x00, 0x5d, 0x54, 0xc0, 0x21, 0xc0, - 0x21, 0xc0, 0x21, 0xc0, 0x21, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, - 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0xa7, - 0x00, 0xa9, 0x3d, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, - 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, - 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x7a, 0x00, 0x06, 0x2c, 0xc0, 0x0d, - 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0x00, 0x96, 0x00, 0x96, 0x00, - 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x80, - 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x80, 0x09, 0x00, 0x00, 0xc9, 0xff, 0xd8, 0xff, 0x00, 0x00, 0x00, - 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0xf0, 0x00, - 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, - 0x00, 0xd0, 0x00, 0x54, 0x01, 0xab, 0xf6, 0xc0, 0x42, 0xc0, 0x42, - 0xc0, 0x42, 0xc0, 0x42, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, - 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x22, 0x01, - 0x37, 0xa9, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0x00, - 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, - 0x00, 0xbc, 0x00, 0xbc, 0xfb, 0x00, 0xca, 0x79, 0xc0, 0x2b, 0xc0, - 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, - 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0xd0, - 0x00, 0x5d, 0x54, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, - 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, - 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0xa7, 0x00, 0xa9, 0x3d, 0xc0, 0x17, - 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0x00, 0xa0, 0x00, 0xa0, 0x00, - 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, - 0x7a, 0x00, 0x06, 0x2c, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, - 0x0d, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, - 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x06, 0x80, 0x80, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x85, 0x09, 0x00, 0x00, 0xc9, - 0xff, 0xd8, 0xff, 0x00, 0x00, 0x00, 0x01, 0x10, 0x01, 0x10, 0x01, - 0x10, 0x01, 0x10, 0x01, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xf0, - 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0x54, 0x01, - 0xab, 0xf6, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0x00, - 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, - 0x00, 0xcb, 0x00, 0xcb, 0x22, 0x01, 0x37, 0xa9, 0xc0, 0x33, 0xc0, - 0x33, 0xc0, 0x33, 0xc0, 0x33, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, - 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0xfb, - 0x00, 0xca, 0x79, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, - 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, - 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0xd0, 0x00, 0x5d, 0x54, 0xc0, 0x21, - 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0x00, 0xaa, 0x00, 0xaa, 0x00, - 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, - 0xa7, 0x00, 0xa9, 0x3d, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0xc0, - 0x17, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, - 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x7a, 0x00, 0x06, 0x2c, 0xc0, - 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0x00, 0x96, 0x00, 0x96, - 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, - 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, - 0x80, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x8a, 0x09, 0x00, 0x00, 0xc9, 0xff, 0xd8, 0xff, 0x00, 0x00, - 0x00, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0xf0, - 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xd0, 0x00, 0xd0, 0x00, - 0xd0, 0x00, 0xd0, 0x00, 0x54, 0x01, 0xab, 0xf6, 0xc0, 0x42, 0xc0, - 0x42, 0xc0, 0x42, 0xc0, 0x42, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, - 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x22, - 0x01, 0x37, 0xa9, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, - 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, - 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0xfb, 0x00, 0xca, 0x79, 0xc0, 0x2b, - 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0x00, 0xb4, 0x00, 0xb4, 0x00, - 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, - 0xd0, 0x00, 0x5d, 0x54, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0xc0, - 0x21, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, - 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0xa7, 0x00, 0xa9, 0x3d, 0xc0, - 0x17, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0x00, 0xa0, 0x00, 0xa0, - 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, - 0xa0, 0x7a, 0x00, 0x06, 0x2c, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, - 0xc0, 0x0d, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, - 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x80, 0x80, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8f, 0x09, 0x00, 0x00, - 0xc9, 0xff, 0xd8, 0xff, 0x00, 0x00, 0x00, 0x01, 0x10, 0x01, 0x10, - 0x01, 0x10, 0x01, 0x10, 0x01, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, - 0xf0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0x54, - 0x01, 0xab, 0xf6, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, - 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, - 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x22, 0x01, 0x37, 0xa9, 0xc0, 0x33, - 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0x00, 0xbc, 0x00, 0xbc, 0x00, - 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, - 0xfb, 0x00, 0xca, 0x79, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, - 0x2b, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, - 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0xd0, 0x00, 0x5d, 0x54, 0xc0, - 0x21, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0x00, 0xaa, 0x00, 0xaa, - 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, - 0xaa, 0xa7, 0x00, 0xa9, 0x3d, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, - 0xc0, 0x17, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, - 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x7a, 0x00, 0x06, 0x2c, - 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0x00, 0x96, 0x00, - 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, - 0x00, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x06, 0x80, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x94, 0x09, 0x00, 0x00, 0xc9, 0xff, 0xd8, 0xff, 0x00, - 0x00, 0x00, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, - 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xd0, 0x00, 0xd0, - 0x00, 0xd0, 0x00, 0xd0, 0x00, 0x54, 0x01, 0xab, 0xf6, 0xc0, 0x42, - 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0x00, 0xcb, 0x00, 0xcb, 0x00, - 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, - 0x22, 0x01, 0x37, 0xa9, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0xc0, - 0x33, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, - 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0xfb, 0x00, 0xca, 0x79, 0xc0, - 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0x00, 0xb4, 0x00, 0xb4, - 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, - 0xb4, 0xd0, 0x00, 0x5d, 0x54, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, - 0xc0, 0x21, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, - 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0xa7, 0x00, 0xa9, 0x3d, - 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0x00, 0xa0, 0x00, - 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, - 0x00, 0xa0, 0x7a, 0x00, 0x06, 0x2c, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, - 0x0d, 0xc0, 0x0d, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, - 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x80, 0x80, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x99, 0x09, 0x00, - 0x00, 0xc9, 0xff, 0xd8, 0xff, 0x00, 0x00, 0x00, 0x01, 0x10, 0x01, - 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0xf0, 0x00, 0xf0, 0x00, 0xf0, - 0x00, 0xf0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, - 0x54, 0x01, 0xab, 0xf6, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0xc0, - 0x42, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, - 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x22, 0x01, 0x37, 0xa9, 0xc0, - 0x33, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, 0x00, 0xbc, 0x00, 0xbc, - 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, - 0xbc, 0xfb, 0x00, 0xca, 0x79, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, - 0xc0, 0x2b, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, - 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0xd0, 0x00, 0x5d, 0x54, - 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0xc0, 0x21, 0x00, 0xaa, 0x00, - 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, - 0x00, 0xaa, 0xa7, 0x00, 0xa9, 0x3d, 0xc0, 0x17, 0xc0, 0x17, 0xc0, - 0x17, 0xc0, 0x17, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, - 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x7a, 0x00, 0x06, - 0x2c, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0xc0, 0x0d, 0x00, 0x96, - 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, - 0x96, 0x00, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x06, 0x80, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x9e, 0x09, 0x00, 0x00, 0xc9, 0xff, 0xd8, 0xff, - 0x00, 0x00, 0x00, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, 0x01, 0x10, - 0x01, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xf0, 0x00, 0xd0, 0x00, - 0xd0, 0x00, 0xd0, 0x00, 0xd0, 0x00, 0x54, 0x01, 0xab, 0xf6, 0xc0, - 0x42, 0xc0, 0x42, 0xc0, 0x42, 0xc0, 0x42, 0x00, 0xcb, 0x00, 0xcb, - 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, 0xcb, 0x00, - 0xcb, 0x22, 0x01, 0x37, 0xa9, 0xc0, 0x33, 0xc0, 0x33, 0xc0, 0x33, - 0xc0, 0x33, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, - 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0x00, 0xbc, 0xfb, 0x00, 0xca, 0x79, - 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0xc0, 0x2b, 0x00, 0xb4, 0x00, - 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, 0x00, 0xb4, - 0x00, 0xb4, 0xd0, 0x00, 0x5d, 0x54, 0xc0, 0x21, 0xc0, 0x21, 0xc0, - 0x21, 0xc0, 0x21, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, - 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0x00, 0xaa, 0xa7, 0x00, 0xa9, - 0x3d, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0xc0, 0x17, 0x00, 0xa0, - 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, 0xa0, 0x00, - 0xa0, 0x00, 0xa0, 0x7a, 0x00, 0x06, 0x2c, 0xc0, 0x0d, 0xc0, 0x0d, - 0xc0, 0x0d, 0xc0, 0x0d, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, - 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x96, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x80, 0x80, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00 }; - -static const u8 default_cal_rssi[] = { - 0x0a, 0x01, 0x72, 0xfe, 0x1a, 0x00, 0x00, 0x00, 0x0a, 0x01, 0x72, - 0xfe, 0x1a, 0x00, 0x00, 0x00, 0x0a, 0x01, 0x72, 0xfe, 0x1a, 0x00, - 0x00, 0x00, 0x0a, 0x01, 0x72, 0xfe, 0x1a, 0x00, 0x00, 0x00, 0x0a, - 0x01, 0x72, 0xfe, 0x1a, 0x00, 0x00, 0x00, 0x0a, 0x01, 0x72, 0xfe, - 0x1a, 0x00, 0x00, 0x00, 0x0a, 0x01, 0x72, 0xfe, 0x1a, 0x00, 0x00, - 0x00, 0x0a, 0x01, 0x72, 0xfe, 0x1a, 0x00, 0x00, 0x00, 0x0a, 0x01, - 0x72, 0xfe, 0x1a, 0x00, 0x00, 0x00, 0x0a, 0x01, 0x72, 0xfe, 0x1a, - 0x00, 0x00, 0x00, 0x0a, 0x01, 0x72, 0xfe, 0x1a, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00 }; - -static void stlc45xx_tx_edcf(struct stlc45xx *stlc); -static void stlc45xx_tx_setup(struct stlc45xx *stlc); -static void stlc45xx_tx_scan(struct stlc45xx *stlc); -static void stlc45xx_tx_psm(struct stlc45xx *stlc, bool enable); -static int stlc45xx_tx_nullfunc(struct stlc45xx *stlc, bool powersave); -static int stlc45xx_tx_pspoll(struct stlc45xx *stlc, bool powersave); - -static ssize_t stlc45xx_sysfs_show_cal_rssi(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - struct stlc45xx *stlc = dev_get_drvdata(dev); - ssize_t len; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - len = PAGE_SIZE; - - mutex_lock(&stlc->mutex); - - if (stlc->cal_rssi) - hex_dump_to_buffer(stlc->cal_rssi, RSSI_CAL_ARRAY_LEN, 16, - 2, buf, len, 0); - mutex_unlock(&stlc->mutex); - - len = strlen(buf); - - return len; -} - -static ssize_t stlc45xx_sysfs_store_cal_rssi(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) -{ - struct stlc45xx *stlc = dev_get_drvdata(dev); - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - mutex_lock(&stlc->mutex); - - if (count != RSSI_CAL_ARRAY_LEN) { - stlc45xx_error("invalid cal_rssi length: %zu", count); - count = 0; - goto out_unlock; - } - - kfree(stlc->cal_rssi); - - stlc->cal_rssi = kmemdup(buf, RSSI_CAL_ARRAY_LEN, GFP_KERNEL); - - if (!stlc->cal_rssi) { - stlc45xx_error("failed to allocate memory for cal_rssi"); - count = 0; - goto out_unlock; - } - - out_unlock: - mutex_unlock(&stlc->mutex); - - return count; -} - -static ssize_t stlc45xx_sysfs_show_cal_channels(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - struct stlc45xx *stlc = dev_get_drvdata(dev); - ssize_t len; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - len = PAGE_SIZE; - - mutex_lock(&stlc->mutex); - - if (stlc->cal_channels) - hex_dump_to_buffer(stlc->cal_channels, CHANNEL_CAL_ARRAY_LEN, - 16, 2, buf, len, 0); - - mutex_unlock(&stlc->mutex); - - len = strlen(buf); - - return len; -} - -static ssize_t stlc45xx_sysfs_store_cal_channels(struct device *dev, - struct device_attribute *attr, - const char *buf, size_t count) -{ - struct stlc45xx *stlc = dev_get_drvdata(dev); - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - mutex_lock(&stlc->mutex); - - if (count != CHANNEL_CAL_ARRAY_LEN) { - stlc45xx_error("invalid cal_channels size: %zu ", count); - count = 0; - goto out_unlock; - } - - kfree(stlc->cal_channels); - - stlc->cal_channels = kmemdup(buf, count, GFP_KERNEL); - - if (!stlc->cal_channels) { - stlc45xx_error("failed to allocate memory for cal_channels"); - count = 0; - goto out_unlock; - } - -out_unlock: - mutex_unlock(&stlc->mutex); - - return count; -} - -static ssize_t stlc45xx_sysfs_show_tx_buf(struct device *dev, - struct device_attribute *attr, - char *buf) -{ - struct stlc45xx *stlc = dev_get_drvdata(dev); - struct txbuffer *entry; - ssize_t len = 0; - - stlc45xx_debug(DEBUG_FUNC, "%s()", __func__); - - mutex_lock(&stlc->mutex); - - list_for_each_entry(entry, &stlc->tx_sent, tx_list) { - len += sprintf(buf + len, "0x%x: 0x%x-0x%x\n", - entry->handle, entry->start, - entry->end); - } - - mutex_unlock(&stlc->mutex); - - return len; -} - -static DEVICE_ATTR(cal_rssi, S_IRUGO | S_IWUSR, - stlc45xx_sysfs_show_cal_rssi, - stlc45xx_sysfs_store_cal_rssi); -static DEVICE_ATTR(cal_channels, S_IRUGO | S_IWUSR, - stlc45xx_sysfs_show_cal_channels, - stlc45xx_sysfs_store_cal_channels); -static DEVICE_ATTR(tx_buf, S_IRUGO, stlc45xx_sysfs_show_tx_buf, NULL); - -static void stlc45xx_spi_read(struct stlc45xx *stlc, unsigned long addr, - void *buf, size_t len) -{ - struct spi_transfer t[2]; - struct spi_message m; - - /* We first push the address */ - addr = (addr << 8) | ADDR_READ_BIT_15; - - spi_message_init(&m); - memset(t, 0, sizeof(t)); - - t[0].tx_buf = &addr; - t[0].len = 2; - spi_message_add_tail(&t[0], &m); - - t[1].rx_buf = buf; - t[1].len = len; - spi_message_add_tail(&t[1], &m); - - spi_sync(stlc->spi, &m); -} - - -static void stlc45xx_spi_write(struct stlc45xx *stlc, unsigned long addr, - void *buf, size_t len) -{ - struct spi_transfer t[3]; - struct spi_message m; - u16 last_word; - - /* We first push the address */ - addr = addr << 8; - - spi_message_init(&m); - memset(t, 0, sizeof(t)); - - t[0].tx_buf = &addr; - t[0].len = 2; - spi_message_add_tail(&t[0], &m); - - t[1].tx_buf = buf; - t[1].len = len; - spi_message_add_tail(&t[1], &m); - - if (len % 2) { - last_word = ((u8 *)buf)[len - 1]; - - t[2].tx_buf = &last_word; - t[2].len = 2; - spi_message_add_tail(&t[2], &m); - } - - spi_sync(stlc->spi, &m); -} - -static u16 stlc45xx_read16(struct stlc45xx *stlc, unsigned long addr) -{ - u16 val; - - stlc45xx_spi_read(stlc, addr, &val, sizeof(val)); - - return val; -} - -static u32 stlc45xx_read32(struct stlc45xx *stlc, unsigned long addr) -{ - u32 val; - - stlc45xx_spi_read(stlc, addr, &val, sizeof(val)); - - return val; -} - -static void stlc45xx_write16(struct stlc45xx *stlc, unsigned long addr, u16 val) -{ - stlc45xx_spi_write(stlc, addr, &val, sizeof(val)); -} - -static void stlc45xx_write32(struct stlc45xx *stlc, unsigned long addr, u32 val) -{ - stlc45xx_spi_write(stlc, addr, &val, sizeof(val)); -} - -struct stlc45xx_spi_reg { - u16 address; - u16 length; - char *name; -}; - -/* caller must hold tx_lock */ -static void stlc45xx_txbuffer_dump(struct stlc45xx *stlc) -{ - struct txbuffer *txbuffer; - char *buf, *pos; - int buf_len, l, count; - - if (!(DEBUG_LEVEL & DEBUG_TXBUFFER)) - return; - - stlc45xx_debug(DEBUG_FUNC, "%s()", __func__); - - buf_len = 500; - buf = kmalloc(buf_len, GFP_ATOMIC); - if (!buf) - return; - - pos = buf; - count = 0; - - list_for_each_entry(txbuffer, &stlc->txbuffer, buffer_list) { - l = snprintf(pos, buf_len, "0x%x-0x%x,", - txbuffer->start, txbuffer->end); - /* drop the null byte */ - pos += l; - buf_len -= l; - count++; - } - - if (count == 0) - *pos = '\0'; - else - *--pos = '\0'; - - stlc45xx_debug(DEBUG_TXBUFFER, "txbuffer: in buffer %d regions: %s", - count, buf); - - kfree(buf); -} - -/* caller must hold tx_lock */ -static int stlc45xx_txbuffer_find(struct stlc45xx *stlc, size_t len) -{ - struct txbuffer *txbuffer; - int pos; - - stlc45xx_debug(DEBUG_FUNC, "%s()", __func__); - - pos = FIRMWARE_TXBUFFER_START; - - if (list_empty(&stlc->txbuffer)) - goto out; - - /* - * the entries in txbuffer must be in the same order as they are in - * the real buffer - */ - list_for_each_entry(txbuffer, &stlc->txbuffer, buffer_list) { - if (pos + len < txbuffer->start) - break; - pos = ALIGN(txbuffer->end + 1, 4); - } - - if (pos + len > FIRMWARE_TXBUFFER_END) - /* not enough room */ - pos = -1; - - stlc45xx_debug(DEBUG_TXBUFFER, "txbuffer: find %zu B: 0x%x", len, pos); - -out: - return pos; -} - -static int stlc45xx_txbuffer_add(struct stlc45xx *stlc, - struct txbuffer *txbuffer) -{ - struct txbuffer *r, *prev = NULL; - - if (list_empty(&stlc->txbuffer)) { - list_add(&txbuffer->buffer_list, &stlc->txbuffer); - return 0; - } - - r = list_first_entry(&stlc->txbuffer, struct txbuffer, buffer_list); - - if (txbuffer->start < r->start) { - /* add to the beginning of the list */ - list_add(&txbuffer->buffer_list, &stlc->txbuffer); - return 0; - } - - prev = NULL; - list_for_each_entry(r, &stlc->txbuffer, buffer_list) { - /* skip first entry, we checked for that above */ - if (!prev) { - prev = r; - continue; - } - - /* double-check overlaps */ - WARN_ON_ONCE(txbuffer->start >= r->start && - txbuffer->start <= r->end); - WARN_ON_ONCE(txbuffer->end >= r->start && - txbuffer->end <= r->end); - - if (prev->end < txbuffer->start && - txbuffer->end < r->start) { - /* insert at this spot */ - list_add_tail(&txbuffer->buffer_list, &r->buffer_list); - return 0; - } - - prev = r; - } - - /* not found */ - list_add_tail(&txbuffer->buffer_list, &stlc->txbuffer); - - return 0; - -} - -/* caller must hold tx_lock */ -static struct txbuffer *stlc45xx_txbuffer_alloc(struct stlc45xx *stlc, - size_t frame_len) -{ - struct txbuffer *entry = NULL; - size_t len; - int pos; - - stlc45xx_debug(DEBUG_FUNC, "%s()", __func__); - - len = FIRMWARE_TXBUFFER_HEADER + frame_len + FIRMWARE_TXBUFFER_TRAILER; - pos = stlc45xx_txbuffer_find(stlc, len); - - if (pos < 0) - return NULL; - - WARN_ON_ONCE(pos + len > FIRMWARE_TXBUFFER_END); - WARN_ON_ONCE(pos < FIRMWARE_TXBUFFER_START); - - entry = kmalloc(sizeof(*entry), GFP_ATOMIC); - entry->start = pos; - entry->frame_start = pos + FIRMWARE_TXBUFFER_HEADER; - entry->end = entry->start + len - 1; - - stlc45xx_debug(DEBUG_TXBUFFER, "txbuffer: allocated 0x%x-0x%x", - entry->start, entry->end); - - stlc45xx_txbuffer_add(stlc, entry); - - stlc45xx_txbuffer_dump(stlc); - - return entry; -} - -/* caller must hold tx_lock */ -static void stlc45xx_txbuffer_free(struct stlc45xx *stlc, - struct txbuffer *txbuffer) -{ - stlc45xx_debug(DEBUG_FUNC, "%s()", __func__); - - stlc45xx_debug(DEBUG_TXBUFFER, "txbuffer: freed 0x%x-0x%x", - txbuffer->start, txbuffer->end); - - list_del(&txbuffer->buffer_list); - kfree(txbuffer); -} - - -static int stlc45xx_wait_bit(struct stlc45xx *stlc, u16 reg, u32 mask, - u32 expected) -{ - int i; - char buffer[4]; - - for (i = 0; i < 2000; i++) { - stlc45xx_spi_read(stlc, reg, buffer, sizeof(buffer)); - if (((*(u32 *)buffer) & mask) == expected) - return 1; - msleep(1); - } - - return 0; -} - -static int stlc45xx_request_firmware(struct stlc45xx *stlc) -{ - const struct firmware *fw; - int ret; - - /* FIXME: should driver use it's own struct device? */ - ret = request_firmware(&fw, "3826.arm", &stlc->spi->dev); - - if (ret < 0) { - stlc45xx_error("request_firmware() failed: %d", ret); - return ret; - } - - if (fw->size % 4) { - stlc45xx_error("firmware size is not multiple of 32bit: %zu", - fw->size); - return -EILSEQ; /* Illegal byte sequence */; - } - - if (fw->size < 1000) { - stlc45xx_error("firmware is too small: %zu", fw->size); - return -EILSEQ; - } - - stlc->fw = kmemdup(fw->data, fw->size, GFP_KERNEL); - if (!stlc->fw) { - stlc45xx_error("could not allocate memory for firmware"); - return -ENOMEM; - } - - stlc->fw_len = fw->size; - - release_firmware(fw); - - return 0; -} - -static int stlc45xx_upload_firmware(struct stlc45xx *stlc) -{ - struct s_dma_regs dma_regs; - unsigned long fw_len, fw_addr; - long _fw_len; - int ret; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - if (!stlc->fw) { - ret = stlc45xx_request_firmware(stlc); - if (ret < 0) - return ret; - } - - /* stop the device */ - stlc45xx_write16(stlc, SPI_ADRS_DEV_CTRL_STAT, - SPI_CTRL_STAT_HOST_OVERRIDE | SPI_CTRL_STAT_HOST_RESET - | SPI_CTRL_STAT_START_HALTED); - - msleep(TARGET_BOOT_SLEEP); - - stlc45xx_write16(stlc, SPI_ADRS_DEV_CTRL_STAT, - SPI_CTRL_STAT_HOST_OVERRIDE - | SPI_CTRL_STAT_START_HALTED); - - msleep(TARGET_BOOT_SLEEP); - - fw_addr = FIRMWARE_ADDRESS; - fw_len = stlc->fw_len; - - while (fw_len > 0) { - _fw_len = (fw_len > SPI_MAX_PACKET_SIZE) - ? SPI_MAX_PACKET_SIZE : fw_len; - dma_regs.cmd = SPI_DMA_WRITE_CTRL_ENABLE; - dma_regs.len = cpu_to_le16(_fw_len); - dma_regs.addr = cpu_to_le32(fw_addr); - - fw_len -= _fw_len; - fw_addr += _fw_len; - - stlc45xx_write16(stlc, SPI_ADRS_DMA_WRITE_CTRL, dma_regs.cmd); - - if (stlc45xx_wait_bit(stlc, SPI_ADRS_DMA_WRITE_CTRL, - HOST_ALLOWED, HOST_ALLOWED) == 0) { - stlc45xx_error("fw_upload not allowed to DMA write"); - return -EAGAIN; - } - - stlc45xx_write16(stlc, SPI_ADRS_DMA_WRITE_LEN, dma_regs.len); - stlc45xx_write32(stlc, SPI_ADRS_DMA_WRITE_BASE, dma_regs.addr); - - stlc45xx_spi_write(stlc, SPI_ADRS_DMA_DATA, stlc->fw, _fw_len); - - /* FIXME: I think this doesn't work if firmware is large, - * this loop goes to second round. fw->data is not - * increased at all! */ - } - - BUG_ON(fw_len != 0); - - /* enable host interrupts */ - stlc45xx_write32(stlc, SPI_ADRS_HOST_INT_EN, SPI_HOST_INTS_DEFAULT); - - /* boot the device */ - stlc45xx_write16(stlc, SPI_ADRS_DEV_CTRL_STAT, - SPI_CTRL_STAT_HOST_OVERRIDE | SPI_CTRL_STAT_HOST_RESET - | SPI_CTRL_STAT_RAM_BOOT); - - msleep(TARGET_BOOT_SLEEP); - - stlc45xx_write16(stlc, SPI_ADRS_DEV_CTRL_STAT, - SPI_CTRL_STAT_HOST_OVERRIDE | SPI_CTRL_STAT_RAM_BOOT); - msleep(TARGET_BOOT_SLEEP); - - return 0; -} - -/* caller must hold tx_lock */ -static void stlc45xx_check_txsent(struct stlc45xx *stlc) -{ - struct txbuffer *entry, *n; - - list_for_each_entry_safe(entry, n, &stlc->tx_sent, tx_list) { - if (time_after(jiffies, entry->lifetime)) { - if (net_ratelimit()) - stlc45xx_warning("frame 0x%x lifetime exceeded", - entry->start); - list_del(&entry->tx_list); - skb_pull(entry->skb, entry->header_len); - ieee80211_tx_status(stlc->hw, entry->skb); - stlc45xx_txbuffer_free(stlc, entry); - } - } -} - -static void stlc45xx_power_off(struct stlc45xx *stlc) -{ - disable_irq(gpio_to_irq(stlc45xx_gpio_irq)); - gpio_set_value(stlc45xx_gpio_power, 0); -} - -static void stlc45xx_power_on(struct stlc45xx *stlc) -{ - gpio_set_value(stlc45xx_gpio_power, 1); - enable_irq(gpio_to_irq(stlc45xx_gpio_irq)); - - /* - * need to wait a while before device can be accessed, the length - * is just a guess - */ - msleep(10); -} - -/* caller must hold tx_lock */ -static void stlc45xx_flush_queues(struct stlc45xx *stlc) -{ - struct txbuffer *entry; - - while (!list_empty(&stlc->tx_sent)) { - entry = list_first_entry(&stlc->tx_sent, - struct txbuffer, tx_list); - list_del(&entry->tx_list); - dev_kfree_skb(entry->skb); - stlc45xx_txbuffer_free(stlc, entry); - } - - WARN_ON(!list_empty(&stlc->tx_sent)); - - while (!list_empty(&stlc->tx_pending)) { - entry = list_first_entry(&stlc->tx_pending, - struct txbuffer, tx_list); - list_del(&entry->tx_list); - dev_kfree_skb(entry->skb); - stlc45xx_txbuffer_free(stlc, entry); - } - - WARN_ON(!list_empty(&stlc->tx_pending)); - WARN_ON(!list_empty(&stlc->txbuffer)); -} - -static void stlc45xx_work_reset(struct work_struct *work) -{ - struct stlc45xx *stlc = container_of(work, struct stlc45xx, - work_reset); - - mutex_lock(&stlc->mutex); - - if (stlc->fw_state != FW_STATE_RESET) - goto out; - - stlc45xx_power_off(stlc); - - mutex_unlock(&stlc->mutex); - - /* wait that all work_structs have finished, we can't hold - * stlc->mutex to avoid deadlock */ - cancel_work_sync(&stlc->work); - - /* FIXME: find out good value to wait for chip power down */ - msleep(100); - - mutex_lock(&stlc->mutex); - - /* FIXME: we should gracefully handle if the state has changed - * after re-acquiring mutex */ - WARN_ON(stlc->fw_state != FW_STATE_RESET); - - spin_lock_bh(&stlc->tx_lock); - stlc45xx_flush_queues(stlc); - spin_unlock_bh(&stlc->tx_lock); - - stlc->fw_state = FW_STATE_RESETTING; - - stlc45xx_power_on(stlc); - stlc45xx_upload_firmware(stlc); - -out: - mutex_unlock(&stlc->mutex); -} - -/* caller must hold mutex */ -static void stlc45xx_reset(struct stlc45xx *stlc) -{ - stlc45xx_warning("resetting firmware"); - stlc->fw_state = FW_STATE_RESET; - ieee80211_stop_queues(stlc->hw); - queue_work(stlc->hw->workqueue, &stlc->work_reset); -} - -static void stlc45xx_work_tx_timeout(struct work_struct *work) -{ - struct stlc45xx *stlc = container_of(work, struct stlc45xx, - work_tx_timeout.work); - - stlc45xx_warning("tx timeout"); - - mutex_lock(&stlc->mutex); - - if (stlc->fw_state != FW_STATE_READY) - goto out; - - stlc45xx_reset(stlc); - -out: - mutex_unlock(&stlc->mutex); -} - -static void stlc45xx_int_ack(struct stlc45xx *stlc, u32 val) -{ - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - stlc45xx_write32(stlc, SPI_ADRS_HOST_INT_ACK, val); -} - -static void stlc45xx_wakeup(struct stlc45xx *stlc) -{ - unsigned long timeout; - u32 ints; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - /* wake the chip */ - stlc45xx_write32(stlc, SPI_ADRS_ARM_INTERRUPTS, SPI_TARGET_INT_WAKEUP); - - /* And wait for the READY interrupt */ - timeout = jiffies + HZ; - - ints = stlc45xx_read32(stlc, SPI_ADRS_HOST_INTERRUPTS); - while (!(ints & SPI_HOST_INT_READY)) { - if (time_after(jiffies, timeout)) - goto out; - ints = stlc45xx_read32(stlc, SPI_ADRS_HOST_INTERRUPTS); - } - - stlc45xx_int_ack(stlc, SPI_HOST_INT_READY); - -out: - return; -} - -static void stlc45xx_sleep(struct stlc45xx *stlc) -{ - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - stlc45xx_write32(stlc, SPI_ADRS_ARM_INTERRUPTS, SPI_TARGET_INT_SLEEP); -} - -static void stlc45xx_int_ready(struct stlc45xx *stlc) -{ - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - stlc45xx_write32(stlc, SPI_ADRS_HOST_INT_EN, - SPI_HOST_INT_UPDATE | SPI_HOST_INT_SW_UPDATE); - - switch (stlc->fw_state) { - case FW_STATE_BOOTING: - stlc->fw_state = FW_STATE_READY; - complete(&stlc->fw_comp); - break; - case FW_STATE_RESETTING: - stlc->fw_state = FW_STATE_READY; - - stlc45xx_tx_scan(stlc); - stlc45xx_tx_setup(stlc); - stlc45xx_tx_edcf(stlc); - - ieee80211_wake_queues(stlc->hw); - break; - default: - break; - } -} - -static int stlc45xx_rx_txack(struct stlc45xx *stlc, struct sk_buff *skb) -{ - struct ieee80211_tx_info *info; - struct s_lm_control *control; - struct s_lmo_tx *tx; - struct txbuffer *entry; - int found = 0; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - control = (struct s_lm_control *) skb->data; - tx = (struct s_lmo_tx *) (control + 1); - - if (list_empty(&stlc->tx_sent)) { - if (net_ratelimit()) - stlc45xx_warning("no frames waiting for " - "acknowledgement"); - return -1; - } - - list_for_each_entry(entry, &stlc->tx_sent, tx_list) { - if (control->handle == entry->handle) { - found = 1; - break; - } - } - - if (!found) { - if (net_ratelimit()) - stlc45xx_warning("couldn't find frame for tx ack 0x%x", - control->handle); - return -1; - } - - stlc45xx_debug(DEBUG_TX, "TX ACK 0x%x", entry->handle); - - if (entry->status_needed) { - info = IEEE80211_SKB_CB(entry->skb); - - if (!(tx->flags & LM_TX_FAILED)) { - /* frame was acked */ - info->flags |= IEEE80211_TX_STAT_ACK; - info->status.ack_signal = tx->rcpi / 2 - 110; - } - - skb_pull(entry->skb, entry->header_len); - - ieee80211_tx_status(stlc->hw, entry->skb); - } - - list_del(&entry->tx_list); - - stlc45xx_check_txsent(stlc); - if (list_empty(&stlc->tx_sent)) - /* there are no pending frames, we can stop the tx timeout - * timer */ - cancel_delayed_work(&stlc->work_tx_timeout); - - spin_lock_bh(&stlc->tx_lock); - - stlc45xx_txbuffer_free(stlc, entry); - - if (stlc->tx_queue_stopped && - stlc45xx_txbuffer_find(stlc, MAX_FRAME_LEN) != -1) { - stlc45xx_debug(DEBUG_QUEUE, "room in tx buffer, waking queues"); - ieee80211_wake_queues(stlc->hw); - stlc->tx_queue_stopped = 0; - } - - spin_unlock_bh(&stlc->tx_lock); - - return 0; -} - -static int stlc45xx_rx_control(struct stlc45xx *stlc, struct sk_buff *skb) -{ - struct s_lm_control *control; - int ret = 0; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - control = (struct s_lm_control *) skb->data; - - switch (control->oid) { - case LM_OID_TX: - ret = stlc45xx_rx_txack(stlc, skb); - break; - case LM_OID_SETUP: - case LM_OID_SCAN: - case LM_OID_TRAP: - case LM_OID_EDCF: - case LM_OID_KEYCACHE: - case LM_OID_PSM: - case LM_OID_STATS: - case LM_OID_LED: - default: - stlc45xx_warning("unhandled rx control oid %d\n", - control->oid); - break; - } - - dev_kfree_skb(skb); - - return ret; -} - -/* copied from mac80211 */ -static void stlc45xx_parse_elems(u8 *start, size_t len, - struct stlc45xx_ie_tim **tim, - size_t *tim_len) -{ - size_t left = len; - u8 *pos = start; - - while (left >= 2) { - u8 id, elen; - - id = *pos++; - elen = *pos++; - left -= 2; - - if (elen > left) - return; - - switch (id) { - case WLAN_EID_TIM: - *tim = (struct stlc45xx_ie_tim *) pos; - *tim_len = elen; - break; - default: - break; - } - - left -= elen; - pos += elen; - } -} - -/* - * mac80211 doesn't have support for asking frames with PS-Poll, so let's - * implement in the driver for now. We have to add support to mac80211 - * later. - */ -static int stlc45xx_check_more_data(struct stlc45xx *stlc, struct sk_buff *skb) -{ - struct s_lm_data_in *data = (struct s_lm_data_in *) skb->data; - struct ieee80211_hdr *hdr; - size_t len; - u16 fc; - - hdr = (void *) skb->data + sizeof(*data); - len = skb->len - sizeof(*data); - - /* minimum frame length is the null frame length 24 bytes */ - if (len < 24) { - stlc45xx_warning("invalid frame length when checking for " - "more data"); - return -EINVAL; - } - - fc = le16_to_cpu(hdr->frame_control); - if (!(fc & IEEE80211_FCTL_FROMDS)) - /* this is not from DS */ - return 0; - - if (compare_ether_addr(hdr->addr1, stlc->mac_addr) != 0) - /* the frame was not for us */ - return 0; - - if (!(fc & IEEE80211_FCTL_MOREDATA)) { - /* AP has no more frames buffered for us */ - stlc45xx_debug(DEBUG_PSM, "all buffered frames retrieved"); - stlc->pspolling = false; - return 0; - } - - /* MOREDATA bit is set, let's ask for a new frame from the AP */ - stlc45xx_tx_pspoll(stlc, stlc->psm); - - return 0; -} - -/* - * mac80211 cannot read TIM from beacons, so let's add a hack to the - * driver. We have to add support to mac80211 later. - */ -static int stlc45xx_rx_data_beacon(struct stlc45xx *stlc, struct sk_buff *skb) -{ - struct s_lm_data_in *data = (struct s_lm_data_in *) skb->data; - size_t len = skb->len, tim_len = 0, baselen, pvbmap_len; - struct ieee80211_mgmt *mgmt; - struct stlc45xx_ie_tim *tim = NULL; - int bmap_offset, index, aid_bit; - - mgmt = (void *) skb->data + sizeof(*data); - - baselen = (u8 *) mgmt->u.beacon.variable - (u8 *) mgmt; - if (baselen > len) { - stlc45xx_warning("invalid baselen in beacon"); - return -EINVAL; - } - - stlc45xx_parse_elems(mgmt->u.beacon.variable, len - baselen, &tim, - &tim_len); - - if (!tim) { - stlc45xx_warning("didn't find tim from a beacon"); - return -EINVAL; - } - - bmap_offset = tim->bmap_control & 0xfe; - index = stlc->aid / 8 - bmap_offset; - - pvbmap_len = tim_len - 3; - if (index > pvbmap_len) - return -EINVAL; - - aid_bit = !!(tim->pvbmap[index] & (1 << stlc->aid % 8)); - - stlc45xx_debug(DEBUG_PSM, "fc 0x%x duration %d seq %d dtim %u " - "bmap_control 0x%x aid_bit %d", - mgmt->frame_control, mgmt->duration, mgmt->seq_ctrl >> 4, - tim->dtim_count, tim->bmap_control, aid_bit); - - if (!aid_bit) - return 0; - - stlc->pspolling = true; - stlc45xx_tx_pspoll(stlc, stlc->psm); - - return 0; -} - -static int stlc45xx_rx_data(struct stlc45xx *stlc, struct sk_buff *skb) -{ - struct ieee80211_rx_status status; - struct s_lm_data_in *data = (struct s_lm_data_in *) skb->data; - int align = 0; - u8 *p, align_len; - u16 len; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - if (stlc->psm) { - if (data->flags & LM_IN_BEACON) - stlc45xx_rx_data_beacon(stlc, skb); - else if (stlc->pspolling && (data->flags & LM_IN_DATA)) - stlc45xx_check_more_data(stlc, skb); - } - - memset(&status, 0, sizeof(status)); - - status.freq = data->frequency; - status.signal = data->rcpi / 2 - 110; - - /* let's assume that maximum rcpi value is 140 (= 35 dBm) */ - status.qual = data->rcpi * 100 / 140; - - status.band = IEEE80211_BAND_2GHZ; - - /* - * FIXME: this gives warning from __ieee80211_rx() - * - * status.rate_idx = data->rate; - */ - - len = data->length; - - if (data->flags & LM_FLAG_ALIGN) - align = 1; - - skb_pull(skb, sizeof(*data)); - - if (align) { - p = skb->data; - align_len = *p; - skb_pull(skb, align_len); - } - - skb_trim(skb, len); - - stlc45xx_debug(DEBUG_RX, "rx data 0x%p %d B", skb->data, skb->len); - stlc45xx_dump(DEBUG_RX_CONTENT, skb->data, skb->len); - - memcpy(IEEE80211_SKB_RXCB(skb), &status, sizeof(status)); - ieee80211_rx(stlc->hw, skb); - - return 0; -} - - - -static int stlc45xx_rx(struct stlc45xx *stlc) -{ - struct s_lm_control *control; - struct sk_buff *skb; - int ret; - u16 len; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - stlc45xx_wakeup(stlc); - - /* dummy read to flush SPI DMA controller bug */ - stlc45xx_read16(stlc, SPI_ADRS_GEN_PURP_1); - - len = stlc45xx_read16(stlc, SPI_ADRS_DMA_DATA); - - if (len == 0) { - stlc45xx_warning("rx request of zero bytes"); - return 0; - } - - skb = dev_alloc_skb(len); - if (!skb) { - stlc45xx_warning("could not alloc skb"); - return 0; - } - - stlc45xx_spi_read(stlc, SPI_ADRS_DMA_DATA, skb_put(skb, len), len); - - stlc45xx_sleep(stlc); - - stlc45xx_debug(DEBUG_RX, "rx frame 0x%p %d B", skb->data, skb->len); - stlc45xx_dump(DEBUG_RX_CONTENT, skb->data, skb->len); - - control = (struct s_lm_control *) skb->data; - - if (control->flags & LM_FLAG_CONTROL) - ret = stlc45xx_rx_control(stlc, skb); - else - ret = stlc45xx_rx_data(stlc, skb); - - return ret; -} - - -static irqreturn_t stlc45xx_interrupt(int irq, void *config) -{ - struct spi_device *spi = config; - struct stlc45xx *stlc = dev_get_drvdata(&spi->dev); - - stlc45xx_debug(DEBUG_IRQ, "IRQ"); - - queue_work(stlc->hw->workqueue, &stlc->work); - - return IRQ_HANDLED; -} - -static int stlc45xx_tx_frame(struct stlc45xx *stlc, u32 address, - void *buf, size_t len) -{ - struct s_dma_regs dma_regs; - unsigned long timeout; - int ret = 0; - u32 ints; - - stlc->tx_frames++; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - stlc45xx_debug(DEBUG_TX, "tx frame 0x%p %zu B", buf, len); - stlc45xx_dump(DEBUG_TX_CONTENT, buf, len); - - stlc45xx_wakeup(stlc); - - dma_regs.cmd = SPI_DMA_WRITE_CTRL_ENABLE; - dma_regs.len = cpu_to_le16(len); - dma_regs.addr = cpu_to_le32(address); - - stlc45xx_spi_write(stlc, SPI_ADRS_DMA_WRITE_CTRL, &dma_regs, - sizeof(dma_regs)); - - stlc45xx_spi_write(stlc, SPI_ADRS_DMA_DATA, buf, len); - - timeout = jiffies + 2 * HZ; - ints = stlc45xx_read32(stlc, SPI_ADRS_HOST_INTERRUPTS); - while (!(ints & SPI_HOST_INT_WR_READY)) { - if (time_after(jiffies, timeout)) { - stlc45xx_warning("WR_READY timeout"); - ret = -1; - goto out; - } - ints = stlc45xx_read32(stlc, SPI_ADRS_HOST_INTERRUPTS); - } - - stlc45xx_int_ack(stlc, SPI_HOST_INT_WR_READY); - - stlc45xx_sleep(stlc); - -out: - return ret; -} - -static int stlc45xx_wq_tx(struct stlc45xx *stlc) -{ - struct txbuffer *entry; - int ret = 0; - - spin_lock_bh(&stlc->tx_lock); - - while (!list_empty(&stlc->tx_pending)) { - entry = list_entry(stlc->tx_pending.next, - struct txbuffer, tx_list); - - list_del_init(&entry->tx_list); - - spin_unlock_bh(&stlc->tx_lock); - - ret = stlc45xx_tx_frame(stlc, entry->frame_start, - entry->skb->data, entry->skb->len); - - spin_lock_bh(&stlc->tx_lock); - - if (ret < 0) { - /* frame transfer to firmware buffer failed */ - /* FIXME: report this to mac80211 */ - dev_kfree_skb(entry->skb); - stlc45xx_txbuffer_free(stlc, entry); - goto out; - } - - list_add(&entry->tx_list, &stlc->tx_sent); - queue_delayed_work(stlc->hw->workqueue, - &stlc->work_tx_timeout, - msecs_to_jiffies(TX_TIMEOUT)); - } - -out: - spin_unlock_bh(&stlc->tx_lock); - return ret; -} - -static void stlc45xx_work(struct work_struct *work) -{ - struct stlc45xx *stlc = container_of(work, struct stlc45xx, work); - u32 ints; - int ret; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - mutex_lock(&stlc->mutex); - - if (stlc->fw_state == FW_STATE_OFF && - stlc->fw_state == FW_STATE_RESET) - goto out; - - ints = stlc45xx_read32(stlc, SPI_ADRS_HOST_INTERRUPTS); - stlc45xx_debug(DEBUG_BH, "begin host_ints 0x%08x", ints); - - if (ints & SPI_HOST_INT_READY) { - stlc45xx_int_ready(stlc); - stlc45xx_int_ack(stlc, SPI_HOST_INT_READY); - } - - if (stlc->fw_state != FW_STATE_READY) - goto out; - - if (ints & SPI_HOST_INT_UPDATE) { - stlc45xx_int_ack(stlc, SPI_HOST_INT_UPDATE); - ret = stlc45xx_rx(stlc); - if (ret < 0) { - stlc45xx_reset(stlc); - goto out; - } - } - if (ints & SPI_HOST_INT_SW_UPDATE) { - stlc45xx_int_ack(stlc, SPI_HOST_INT_SW_UPDATE); - ret = stlc45xx_rx(stlc); - if (ret < 0) { - stlc45xx_reset(stlc); - goto out; - } - } - - ret = stlc45xx_wq_tx(stlc); - if (ret < 0) { - stlc45xx_reset(stlc); - goto out; - } - - ints = stlc45xx_read32(stlc, SPI_ADRS_HOST_INTERRUPTS); - stlc45xx_debug(DEBUG_BH, "end host_ints 0x%08x", ints); - -out: - mutex_unlock(&stlc->mutex); -} - -static void stlc45xx_tx_edcf(struct stlc45xx *stlc) -{ - struct s_lm_control *control; - struct s_lmo_edcf *edcf; - size_t len, edcf_len; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - edcf_len = sizeof(*edcf); - len = sizeof(*control) + edcf_len; - control = kzalloc(len, GFP_KERNEL); - edcf = (struct s_lmo_edcf *) (control + 1); - - control->flags = LM_FLAG_CONTROL | LM_CTRL_OPSET; - control->length = edcf_len; - control->oid = LM_OID_EDCF; - - edcf->slottime = 0x14; - edcf->sifs = 10; - edcf->eofpad = 6; - edcf->maxburst = 1500; - - edcf->queues[0].aifs = 2; - edcf->queues[0].pad0 = 1; - edcf->queues[0].cwmin = 3; - edcf->queues[0].cwmax = 7; - edcf->queues[0].txop = 47; - edcf->queues[1].aifs = 2; - edcf->queues[1].pad0 = 0; - edcf->queues[1].cwmin = 7; - edcf->queues[1].cwmax = 15; - edcf->queues[1].txop = 94; - edcf->queues[2].aifs = 3; - edcf->queues[2].pad0 = 0; - edcf->queues[2].cwmin = 15; - edcf->queues[2].cwmax = 1023; - edcf->queues[2].txop = 0; - edcf->queues[3].aifs = 7; - edcf->queues[3].pad0 = 0; - edcf->queues[3].cwmin = 15; - edcf->queues[3].cwmax = 1023; - edcf->queues[3].txop = 0; - edcf->queues[4].aifs = 13; - edcf->queues[4].pad0 = 99; - edcf->queues[4].cwmin = 3437; - edcf->queues[4].cwmax = 512; - edcf->queues[4].txop = 12; - edcf->queues[5].aifs = 142; - edcf->queues[5].pad0 = 109; - edcf->queues[5].cwmin = 8756; - edcf->queues[5].cwmax = 6; - edcf->queues[5].txop = 0; - edcf->queues[6].aifs = 4; - edcf->queues[6].pad0 = 0; - edcf->queues[6].cwmin = 0; - edcf->queues[6].cwmax = 58705; - edcf->queues[6].txop = 25716; - edcf->queues[7].aifs = 0; - edcf->queues[7].pad0 = 0; - edcf->queues[7].cwmin = 0; - edcf->queues[7].cwmax = 0; - edcf->queues[7].txop = 0; - - stlc45xx_tx_frame(stlc, FIRMWARE_CONFIG_START, control, len); - - kfree(control); -} - -static void stlc45xx_tx_setup(struct stlc45xx *stlc) -{ - struct s_lm_control *control; - struct s_lmo_setup *setup; - size_t len, setup_len; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - setup_len = sizeof(*setup); - len = sizeof(*control) + setup_len; - control = kzalloc(len, GFP_KERNEL); - setup = (struct s_lmo_setup *) (control + 1); - - control->flags = LM_FLAG_CONTROL | LM_CTRL_OPSET; - control->length = setup_len; - control->oid = LM_OID_SETUP; - - setup->flags = LM_SETUP_INFRA; - setup->antenna = 2; - setup->rx_align = 0; - setup->rx_buffer = FIRMWARE_RXBUFFER_START; - setup->rx_mtu = FIRMWARE_MTU; - setup->frontend = 5; - setup->timeout = 0; - setup->truncate = 48896; - setup->bratemask = 0xffffffff; - setup->ref_clock = 644245094; - setup->lpf_bandwidth = 65535; - setup->osc_start_delay = 65535; - - memcpy(setup->macaddr, stlc->mac_addr, ETH_ALEN); - memcpy(setup->bssid, stlc->bssid, ETH_ALEN); - - stlc45xx_tx_frame(stlc, FIRMWARE_CONFIG_START, control, len); - - kfree(control); -} - -static void stlc45xx_tx_scan(struct stlc45xx *stlc) -{ - struct s_lm_control *control; - struct s_lmo_scan *scan; - size_t len, scan_len; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - scan_len = sizeof(*scan); - len = sizeof(*control) + scan_len; - control = kzalloc(len, GFP_KERNEL); - scan = (struct s_lmo_scan *) (control + 1); - - control->flags = LM_FLAG_CONTROL | LM_CTRL_OPSET; - control->length = scan_len; - control->oid = LM_OID_SCAN; - - scan->flags = LM_SCAN_EXIT; - scan->bratemask = 0x15f; - scan->aloft[0] = 3; - scan->aloft[1] = 3; - scan->aloft[2] = 1; - scan->aloft[3] = 0; - scan->aloft[4] = 0; - scan->aloft[5] = 0; - scan->aloft[6] = 0; - scan->aloft[7] = 0; - - memcpy(&scan->rssical, &stlc->cal_rssi[(stlc->channel - 1) * - RSSI_CAL_LEN], - RSSI_CAL_LEN); - memcpy(&scan->channel, &stlc->cal_channels[(stlc->channel - 1) * - CHANNEL_CAL_LEN], - CHANNEL_CAL_LEN); - - stlc45xx_tx_frame(stlc, FIRMWARE_CONFIG_START, control, len); - - kfree(control); -} - -/* - * caller must hold mutex - */ -static int stlc45xx_tx_pspoll(struct stlc45xx *stlc, bool powersave) -{ - struct ieee80211_hdr *pspoll; - int payload_len, padding, i; - struct s_lm_data_out *data; - struct txbuffer *entry; - struct sk_buff *skb; - char *payload; - u16 fc; - - skb = dev_alloc_skb(stlc->hw->extra_tx_headroom + 16); - if (!skb) { - stlc45xx_warning("failed to allocate pspoll frame"); - return -ENOMEM; - } - skb_reserve(skb, stlc->hw->extra_tx_headroom); - - pspoll = (struct ieee80211_hdr *) skb_put(skb, 16); - memset(pspoll, 0, 16); - fc = IEEE80211_FTYPE_CTL | IEEE80211_STYPE_PSPOLL; - if (powersave) - fc |= IEEE80211_FCTL_PM; - pspoll->frame_control = cpu_to_le16(fc); - pspoll->duration_id = cpu_to_le16(stlc->aid); - - /* aid in PS-Poll has its two MSBs each set to 1 */ - pspoll->duration_id |= cpu_to_le16(1 << 15) | cpu_to_le16(1 << 14); - - memcpy(pspoll->addr1, stlc->bssid, ETH_ALEN); - memcpy(pspoll->addr2, stlc->mac_addr, ETH_ALEN); - - stlc45xx_debug(DEBUG_PSM, "sending PS-Poll frame to %pM (powersave %d, " - "fc 0x%x, aid %d)", pspoll->addr1, - powersave, fc, stlc->aid); - - spin_lock_bh(&stlc->tx_lock); - - entry = stlc45xx_txbuffer_alloc(stlc, skb->len); - - spin_unlock_bh(&stlc->tx_lock); - - if (!entry) { - /* - * The queue should be stopped before the firmware buffer - * is full, so firmware buffer should always have enough - * space. - * - * But I'm too lazy and omit it for now. - */ - if (net_ratelimit()) - stlc45xx_warning("firmware tx buffer full is full " - "for null frame"); - return -ENOSPC; - } - - payload = skb->data; - payload_len = skb->len; - padding = (int) (skb->data - sizeof(*data)) & 3; - entry->header_len = sizeof(*data) + padding; - - entry->skb = skb; - entry->status_needed = false; - entry->handle = (u32) skb; - entry->lifetime = jiffies + msecs_to_jiffies(TX_FRAME_LIFETIME); - - stlc45xx_debug(DEBUG_TX, "tx data 0x%x (0x%p payload %d B " - "padding %d header_len %d)", - entry->handle, payload, payload_len, padding, - entry->header_len); - stlc45xx_dump(DEBUG_TX_CONTENT, payload, payload_len); - - data = (struct s_lm_data_out *) skb_push(skb, entry->header_len); - - memset(data, 0, entry->header_len); - - if (padding) - data->flags = LM_FLAG_ALIGN; - - data->flags = LM_OUT_BURST; - data->length = payload_len; - data->handle = entry->handle; - data->aid = 1; - data->rts_retries = 7; - data->retries = 7; - data->aloft_ctrl = 0; - data->crypt_offset = 58; - data->keytype = 0; - data->keylen = 0; - data->queue = LM_QUEUE_DATA3; - data->backlog = 32; - data->antenna = 2; - data->cts = 3; - data->power = 127; - - for (i = 0; i < 8; i++) - data->aloft[i] = 0; - - /* - * check if there's enough space in tx buffer - * - * FIXME: ignored for now - */ - - stlc45xx_tx_frame(stlc, entry->start, skb->data, skb->len); - - list_add(&entry->tx_list, &stlc->tx_sent); - - return 0; -} - -/* - * caller must hold mutex - * - * shamelessly stolen from mac80211/ieee80211_send_nullfunc - */ -static int stlc45xx_tx_nullfunc(struct stlc45xx *stlc, bool powersave) -{ - struct ieee80211_hdr *nullfunc; - int payload_len, padding, i; - struct s_lm_data_out *data; - struct txbuffer *entry; - struct sk_buff *skb; - char *payload; - u16 fc; - - skb = dev_alloc_skb(stlc->hw->extra_tx_headroom + 24); - if (!skb) { - stlc45xx_warning("failed to allocate buffer for null frame\n"); - return -ENOMEM; - } - skb_reserve(skb, stlc->hw->extra_tx_headroom); - - nullfunc = (struct ieee80211_hdr *) skb_put(skb, 24); - memset(nullfunc, 0, 24); - fc = IEEE80211_FTYPE_DATA | IEEE80211_STYPE_NULLFUNC | - IEEE80211_FCTL_TODS; - - if (powersave) - fc |= IEEE80211_FCTL_PM; - - nullfunc->frame_control = cpu_to_le16(fc); - memcpy(nullfunc->addr1, stlc->bssid, ETH_ALEN); - memcpy(nullfunc->addr2, stlc->mac_addr, ETH_ALEN); - memcpy(nullfunc->addr3, stlc->bssid, ETH_ALEN); - - stlc45xx_debug(DEBUG_PSM, "sending Null frame to %pM (powersave %d, " - "fc 0x%x)", nullfunc->addr1, powersave, fc); - - spin_lock_bh(&stlc->tx_lock); - - entry = stlc45xx_txbuffer_alloc(stlc, skb->len); - - spin_unlock_bh(&stlc->tx_lock); - - if (!entry) { - /* - * The queue should be stopped before the firmware buffer - * is full, so firmware buffer should always have enough - * space. - * - * But I'm too lazy and omit it for now. - */ - if (net_ratelimit()) - stlc45xx_warning("firmware tx buffer full is full " - "for null frame"); - return -ENOSPC; - } - - payload = skb->data; - payload_len = skb->len; - padding = (int) (skb->data - sizeof(*data)) & 3; - entry->header_len = sizeof(*data) + padding; - - entry->skb = skb; - entry->status_needed = false; - entry->handle = (u32) skb; - entry->lifetime = jiffies + msecs_to_jiffies(TX_FRAME_LIFETIME); - - stlc45xx_debug(DEBUG_TX, "tx data 0x%x (0x%p payload %d B " - "padding %d header_len %d)", - entry->handle, payload, payload_len, padding, - entry->header_len); - stlc45xx_dump(DEBUG_TX_CONTENT, payload, payload_len); - - data = (struct s_lm_data_out *) skb_push(skb, entry->header_len); - - memset(data, 0, entry->header_len); - - if (padding) - data->flags = LM_FLAG_ALIGN; - - data->flags = LM_OUT_BURST; - data->length = payload_len; - data->handle = entry->handle; - data->aid = 1; - data->rts_retries = 7; - data->retries = 7; - data->aloft_ctrl = 0; - data->crypt_offset = 58; - data->keytype = 0; - data->keylen = 0; - data->queue = LM_QUEUE_DATA3; - data->backlog = 32; - data->antenna = 2; - data->cts = 3; - data->power = 127; - - for (i = 0; i < 8; i++) - data->aloft[i] = 0; - - /* - * check if there's enough space in tx buffer - * - * FIXME: ignored for now - */ - - stlc45xx_tx_frame(stlc, entry->start, skb->data, skb->len); - - list_add(&entry->tx_list, &stlc->tx_sent); - - return 0; -} - -/* caller must hold mutex */ -static void stlc45xx_tx_psm(struct stlc45xx *stlc, bool enable) -{ - struct s_lm_control *control; - struct s_lmo_psm *psm; - size_t len, psm_len; - - WARN_ON(!stlc->associated); - WARN_ON(stlc->aid < 1); - WARN_ON(stlc->aid > 2007); - - psm_len = sizeof(*psm); - len = sizeof(*control) + psm_len; - control = kzalloc(len, GFP_KERNEL); - psm = (struct s_lmo_psm *) (control + 1); - - control->flags = LM_FLAG_CONTROL | LM_CTRL_OPSET; - control->length = psm_len; - control->oid = LM_OID_PSM; - - if (enable) - psm->flags |= LM_PSM; - - psm->aid = stlc->aid; - - psm->beacon_rcpi_skip_max = 60; - - psm->intervals[0].interval = 1; - psm->intervals[0].periods = 1; - psm->intervals[1].interval = 1; - psm->intervals[1].periods = 1; - psm->intervals[2].interval = 1; - psm->intervals[2].periods = 1; - psm->intervals[3].interval = 1; - psm->intervals[3].periods = 1; - - psm->nr = 0; - psm->exclude[0] = 0; - - stlc45xx_debug(DEBUG_PSM, "sending LM_OID_PSM (aid %d, interval %d)", - psm->aid, psm->intervals[0].interval); - - stlc45xx_tx_frame(stlc, FIRMWARE_CONFIG_START, control, len); - - kfree(control); -} - -static int stlc45xx_op_tx(struct ieee80211_hw *hw, struct sk_buff *skb) -{ - struct stlc45xx *stlc = hw->priv; - struct ieee80211_tx_info *info; - struct ieee80211_rate *rate; - int payload_len, padding, i; - struct s_lm_data_out *data; - struct txbuffer *entry; - char *payload; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - spin_lock_bh(&stlc->tx_lock); - - entry = stlc45xx_txbuffer_alloc(stlc, skb->len); - if (!entry) { - /* the queue should be stopped before the firmware buffer - * is full, so firmware buffer should always have enough - * space */ - if (net_ratelimit()) - stlc45xx_warning("firmware buffer full"); - spin_unlock_bh(&stlc->tx_lock); - return NETDEV_TX_BUSY; - } - - info = IEEE80211_SKB_CB(skb); - - payload = skb->data; - payload_len = skb->len; - padding = (int) (skb->data - sizeof(*data)) & 3; - entry->header_len = sizeof(*data) + padding; - - entry->skb = skb; - entry->status_needed = true; - entry->handle = (u32) skb; - entry->lifetime = jiffies + msecs_to_jiffies(TX_FRAME_LIFETIME); - - stlc45xx_debug(DEBUG_TX, "tx data 0x%x (0x%p payload %d B " - "padding %d header_len %d)", - entry->handle, payload, payload_len, padding, - entry->header_len); - stlc45xx_dump(DEBUG_TX_CONTENT, payload, payload_len); - - data = (struct s_lm_data_out *) skb_push(skb, entry->header_len); - - memset(data, 0, entry->header_len); - - if (padding) - data->flags = LM_FLAG_ALIGN; - - data->flags = LM_OUT_BURST; - data->length = payload_len; - data->handle = entry->handle; - data->aid = 1; - data->rts_retries = 7; - data->retries = 7; - data->aloft_ctrl = 0; - data->crypt_offset = 58; - data->keytype = 0; - data->keylen = 0; - data->queue = 2; - data->backlog = 32; - data->antenna = 2; - data->cts = 3; - data->power = 127; - - for (i = 0; i < 8; i++) { - rate = ieee80211_get_tx_rate(stlc->hw, info); - data->aloft[i] = rate->hw_value; - } - - list_add_tail(&entry->tx_list, &stlc->tx_pending); - - /* check if there's enough space in tx buffer */ - if (stlc45xx_txbuffer_find(stlc, MAX_FRAME_LEN) == -1) { - stlc45xx_debug(DEBUG_QUEUE, "tx buffer full, stopping queues"); - stlc->tx_queue_stopped = 1; - ieee80211_stop_queues(stlc->hw); - } - - queue_work(stlc->hw->workqueue, &stlc->work); - - spin_unlock_bh(&stlc->tx_lock); - - return NETDEV_TX_OK; -} - -static int stlc45xx_op_start(struct ieee80211_hw *hw) -{ - struct stlc45xx *stlc = hw->priv; - unsigned long timeout; - int ret = 0; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - mutex_lock(&stlc->mutex); - - stlc->fw_state = FW_STATE_BOOTING; - stlc->channel = 1; - - stlc45xx_power_on(stlc); - - ret = stlc45xx_upload_firmware(stlc); - if (ret < 0) { - stlc45xx_power_off(stlc); - goto out_unlock; - } - - stlc->tx_queue_stopped = 0; - - mutex_unlock(&stlc->mutex); - - timeout = msecs_to_jiffies(2000); - timeout = wait_for_completion_interruptible_timeout(&stlc->fw_comp, - timeout); - if (!timeout) { - stlc45xx_error("firmware boot failed"); - stlc45xx_power_off(stlc); - ret = -1; - goto out; - } - - stlc45xx_debug(DEBUG_BOOT, "firmware booted"); - - /* FIXME: should we take mutex just after wait_for_completion()? */ - mutex_lock(&stlc->mutex); - - WARN_ON(stlc->fw_state != FW_STATE_READY); - -out_unlock: - mutex_unlock(&stlc->mutex); - -out: - return ret; -} - -static void stlc45xx_op_stop(struct ieee80211_hw *hw) -{ - struct stlc45xx *stlc = hw->priv; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - mutex_lock(&stlc->mutex); - - WARN_ON(stlc->fw_state != FW_STATE_READY); - - stlc45xx_power_off(stlc); - - /* FIXME: make sure that all work_structs have completed */ - - spin_lock_bh(&stlc->tx_lock); - stlc45xx_flush_queues(stlc); - spin_unlock_bh(&stlc->tx_lock); - - stlc->fw_state = FW_STATE_OFF; - - mutex_unlock(&stlc->mutex); -} - -static int stlc45xx_op_add_interface(struct ieee80211_hw *hw, - struct ieee80211_if_init_conf *conf) -{ - struct stlc45xx *stlc = hw->priv; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - switch (conf->type) { - case NL80211_IFTYPE_STATION: - break; - default: - return -EOPNOTSUPP; - } - - memcpy(stlc->mac_addr, conf->mac_addr, ETH_ALEN); - - return 0; -} - -static void stlc45xx_op_remove_interface(struct ieee80211_hw *hw, - struct ieee80211_if_init_conf *conf) -{ - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); -} - -static int stlc45xx_op_config(struct ieee80211_hw *hw, u32 changed) -{ - struct stlc45xx *stlc = hw->priv; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - mutex_lock(&stlc->mutex); - - stlc->channel = hw->conf.channel->hw_value; - stlc45xx_tx_scan(stlc); - stlc45xx_tx_setup(stlc); - stlc45xx_tx_edcf(stlc); - - if ((hw->conf.flags & IEEE80211_CONF_PS) != stlc->psm) { - stlc->psm = hw->conf.flags & IEEE80211_CONF_PS; - if (stlc->associated) { - stlc45xx_tx_psm(stlc, stlc->psm); - stlc45xx_tx_nullfunc(stlc, stlc->psm); - } - } - - mutex_unlock(&stlc->mutex); - - return 0; -} - -static void stlc45xx_op_configure_filter(struct ieee80211_hw *hw, - unsigned int changed_flags, - unsigned int *total_flags, - int mc_count, - struct dev_addr_list *mc_list) -{ - *total_flags = 0; -} - -static void stlc45xx_op_bss_info_changed(struct ieee80211_hw *hw, - struct ieee80211_vif *vif, - struct ieee80211_bss_conf *info, - u32 changed) -{ - struct stlc45xx *stlc = hw->priv; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - mutex_lock(&stlc->mutex); - - memcpy(stlc->bssid, info->bssid, ETH_ALEN); - stlc45xx_tx_setup(stlc); - - mutex_unlock(&stlc->mutex); - - if (changed & BSS_CHANGED_ASSOC) { - stlc->associated = info->assoc; - if (info->assoc) - stlc->aid = info->aid; - else - stlc->aid = -1; - - if (stlc->psm) { - stlc45xx_tx_psm(stlc, stlc->psm); - stlc45xx_tx_nullfunc(stlc, stlc->psm); - } - } -} - - -/* can't be const, mac80211 writes to this */ -static struct ieee80211_rate stlc45xx_rates[] = { - { .bitrate = 10, .hw_value = 0, .hw_value_short = 0, }, - { .bitrate = 20, .hw_value = 1, .hw_value_short = 1, }, - { .bitrate = 55, .hw_value = 2, .hw_value_short = 2, }, - { .bitrate = 110, .hw_value = 3, .hw_value_short = 3, }, - { .bitrate = 60, .hw_value = 4, .hw_value_short = 4, }, - { .bitrate = 90, .hw_value = 5, .hw_value_short = 5, }, - { .bitrate = 120, .hw_value = 6, .hw_value_short = 6, }, - { .bitrate = 180, .hw_value = 7, .hw_value_short = 7, }, - { .bitrate = 240, .hw_value = 8, .hw_value_short = 8, }, - { .bitrate = 360, .hw_value = 9, .hw_value_short = 9, }, - { .bitrate = 480, .hw_value = 10, .hw_value_short = 10, }, - { .bitrate = 540, .hw_value = 11, .hw_value_short = 11, }, -}; - -/* can't be const, mac80211 writes to this */ -static struct ieee80211_channel stlc45xx_channels[] = { - { .hw_value = 1, .center_freq = 2412}, - { .hw_value = 2, .center_freq = 2417}, - { .hw_value = 3, .center_freq = 2422}, - { .hw_value = 4, .center_freq = 2427}, - { .hw_value = 5, .center_freq = 2432}, - { .hw_value = 6, .center_freq = 2437}, - { .hw_value = 7, .center_freq = 2442}, - { .hw_value = 8, .center_freq = 2447}, - { .hw_value = 9, .center_freq = 2452}, - { .hw_value = 10, .center_freq = 2457}, - { .hw_value = 11, .center_freq = 2462}, - { .hw_value = 12, .center_freq = 2467}, - { .hw_value = 13, .center_freq = 2472}, -}; - -/* can't be const, mac80211 writes to this */ -static struct ieee80211_supported_band stlc45xx_band_2ghz = { - .channels = stlc45xx_channels, - .n_channels = ARRAY_SIZE(stlc45xx_channels), - .bitrates = stlc45xx_rates, - .n_bitrates = ARRAY_SIZE(stlc45xx_rates), -}; - -static const struct ieee80211_ops stlc45xx_ops = { - .start = stlc45xx_op_start, - .stop = stlc45xx_op_stop, - .add_interface = stlc45xx_op_add_interface, - .remove_interface = stlc45xx_op_remove_interface, - .config = stlc45xx_op_config, - .configure_filter = stlc45xx_op_configure_filter, - .tx = stlc45xx_op_tx, - .bss_info_changed = stlc45xx_op_bss_info_changed, -}; - -static int stlc45xx_register_mac80211(struct stlc45xx *stlc) -{ - /* FIXME: SET_IEEE80211_PERM_ADDR() requires default_mac_addr - to be non-const for some strange reason */ - static u8 default_mac_addr[ETH_ALEN] = { - 0x00, 0x02, 0xee, 0xc0, 0xff, 0xee - }; - int ret; - - SET_IEEE80211_PERM_ADDR(stlc->hw, default_mac_addr); - - ret = ieee80211_register_hw(stlc->hw); - if (ret) { - stlc45xx_error("unable to register mac80211 hw: %d", ret); - return ret; - } - - return 0; -} - -static void stlc45xx_device_release(struct device *dev) -{ - -} - -static struct platform_device stlc45xx_device = { - .name = "stlc45xx", - .id = -1, - - /* device model insists to have a release function */ - .dev = { - .release = stlc45xx_device_release, - }, -}; - -static int __devinit stlc45xx_probe(struct spi_device *spi) -{ - struct stlc45xx *stlc; - struct ieee80211_hw *hw; - int ret; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - /* mac80211 alloc */ - hw = ieee80211_alloc_hw(sizeof(*stlc), &stlc45xx_ops); - if (!hw) { - stlc45xx_error("could not alloc ieee80211_hw"); - ret = -ENOMEM; - goto out; - } - - /* mac80211 clears hw->priv */ - stlc = hw->priv; - - stlc->hw = hw; - dev_set_drvdata(&spi->dev, stlc); - stlc->spi = spi; - - spi->bits_per_word = 16; - spi->max_speed_hz = 24000000; - - ret = spi_setup(spi); - if (ret < 0) - stlc45xx_error("spi_setup failed"); - - ret = gpio_request(stlc45xx_gpio_power, "stlc45xx power"); - if (ret < 0) { - stlc45xx_error("power GPIO request failed: %d", ret); - return ret; - } - - ret = gpio_request(stlc45xx_gpio_irq, "stlc45xx irq"); - if (ret < 0) { - stlc45xx_error("irq GPIO request failed: %d", ret); - goto out; - } - - gpio_direction_output(stlc45xx_gpio_power, 0); - gpio_direction_input(stlc45xx_gpio_irq); - - ret = request_irq(gpio_to_irq(stlc45xx_gpio_irq), - stlc45xx_interrupt, IRQF_DISABLED, "stlc45xx", - stlc->spi); - if (ret < 0) - /* FIXME: handle the error */ - stlc45xx_error("request_irq() failed"); - - set_irq_type(gpio_to_irq(stlc45xx_gpio_irq), - IRQ_TYPE_EDGE_RISING); - - disable_irq(gpio_to_irq(stlc45xx_gpio_irq)); - - ret = platform_device_register(&stlc45xx_device); - if (ret) { - stlc45xx_error("Couldn't register wlan_omap device."); - return ret; - } - dev_set_drvdata(&stlc45xx_device.dev, stlc); - - INIT_WORK(&stlc->work, stlc45xx_work); - INIT_WORK(&stlc->work_reset, stlc45xx_work_reset); - INIT_DELAYED_WORK(&stlc->work_tx_timeout, stlc45xx_work_tx_timeout); - mutex_init(&stlc->mutex); - init_completion(&stlc->fw_comp); - spin_lock_init(&stlc->tx_lock); - INIT_LIST_HEAD(&stlc->txbuffer); - INIT_LIST_HEAD(&stlc->tx_pending); - INIT_LIST_HEAD(&stlc->tx_sent); - - hw->flags = IEEE80211_HW_RX_INCLUDES_FCS | - IEEE80211_HW_SIGNAL_DBM | - IEEE80211_HW_NOISE_DBM; - /* four bytes for padding */ - hw->extra_tx_headroom = sizeof(struct s_lm_data_out) + 4; - - /* unit us */ - hw->channel_change_time = 1000; - - hw->wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION); - hw->wiphy->bands[IEEE80211_BAND_2GHZ] = &stlc45xx_band_2ghz; - - SET_IEEE80211_DEV(hw, &spi->dev); - - BUILD_BUG_ON(sizeof(default_cal_rssi) != RSSI_CAL_ARRAY_LEN); - BUILD_BUG_ON(sizeof(default_cal_channels) != CHANNEL_CAL_ARRAY_LEN); - - stlc->cal_rssi = kmemdup(default_cal_rssi, RSSI_CAL_ARRAY_LEN, - GFP_KERNEL); - stlc->cal_channels = kmemdup(default_cal_channels, - CHANNEL_CAL_ARRAY_LEN, - GFP_KERNEL); - - ret = device_create_file(&stlc45xx_device.dev, &dev_attr_cal_rssi); - if (ret < 0) { - stlc45xx_error("failed to create sysfs file cal_rssi"); - goto out; - } - - ret = device_create_file(&stlc45xx_device.dev, &dev_attr_cal_channels); - if (ret < 0) { - stlc45xx_error("failed to create sysfs file cal_channels"); - goto out; - } - - ret = device_create_file(&stlc45xx_device.dev, &dev_attr_tx_buf); - if (ret < 0) { - stlc45xx_error("failed to create sysfs file tx_buf"); - goto out; - } - - ret = stlc45xx_register_mac80211(stlc); - if (ret < 0) - goto out; - - stlc45xx_info("v" DRIVER_VERSION " loaded"); - - stlc45xx_info("config buffer 0x%x-0x%x", - FIRMWARE_CONFIG_START, FIRMWARE_CONFIG_END); - stlc45xx_info("tx 0x%x-0x%x, rx 0x%x-0x%x", - FIRMWARE_TXBUFFER_START, FIRMWARE_TXBUFFER_END, - FIRMWARE_RXBUFFER_START, FIRMWARE_RXBUFFER_END); - -out: - return ret; -} - -static int __devexit stlc45xx_remove(struct spi_device *spi) -{ - struct stlc45xx *stlc = dev_get_drvdata(&spi->dev); - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - platform_device_unregister(&stlc45xx_device); - - ieee80211_unregister_hw(stlc->hw); - - free_irq(gpio_to_irq(stlc45xx_gpio_irq), spi); - - gpio_free(stlc45xx_gpio_power); - gpio_free(stlc45xx_gpio_irq); - - /* FIXME: free cal_channels and cal_rssi? */ - - kfree(stlc->fw); - - mutex_destroy(&stlc->mutex); - - /* frees also stlc */ - ieee80211_free_hw(stlc->hw); - stlc = NULL; - - return 0; -} - - -static struct spi_driver stlc45xx_spi_driver = { - .driver = { - /* use cx3110x name because board-n800.c uses that for the - * SPI port */ - .name = "cx3110x", - .bus = &spi_bus_type, - .owner = THIS_MODULE, - }, - - .probe = stlc45xx_probe, - .remove = __devexit_p(stlc45xx_remove), -}; - -static int __init stlc45xx_init(void) -{ - int ret; - - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - ret = spi_register_driver(&stlc45xx_spi_driver); - if (ret < 0) { - stlc45xx_error("failed to register SPI driver: %d", ret); - goto out; - } - -out: - return ret; -} - -static void __exit stlc45xx_exit(void) -{ - stlc45xx_debug(DEBUG_FUNC, "%s", __func__); - - spi_unregister_driver(&stlc45xx_spi_driver); - - stlc45xx_info("unloaded"); -} - -module_init(stlc45xx_init); -module_exit(stlc45xx_exit); - -MODULE_LICENSE("GPL"); -MODULE_AUTHOR("Kalle Valo <kalle.valo@nokia.com>"); -MODULE_ALIAS("spi:cx3110x"); diff --git a/drivers/staging/stlc45xx/stlc45xx.h b/drivers/staging/stlc45xx/stlc45xx.h deleted file mode 100644 index ac96bbbde79f..000000000000 --- a/drivers/staging/stlc45xx/stlc45xx.h +++ /dev/null @@ -1,283 +0,0 @@ -/* - * This file is part of stlc45xx - * - * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies). - * - * Contact: Kalle Valo <kalle.valo@nokia.com> - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * version 2 as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA - * 02110-1301 USA - * - */ - -#include <linux/mutex.h> -#include <linux/list.h> -#include <net/mac80211.h> - -#include "stlc45xx_lmac.h" - -#define DRIVER_NAME "stlc45xx" -#define DRIVER_VERSION "0.1.3" - -#define DRIVER_PREFIX DRIVER_NAME ": " - -enum { - DEBUG_NONE = 0, - DEBUG_FUNC = 1 << 0, - DEBUG_IRQ = 1 << 1, - DEBUG_BH = 1 << 2, - DEBUG_RX = 1 << 3, - DEBUG_RX_CONTENT = 1 << 5, - DEBUG_TX = 1 << 6, - DEBUG_TX_CONTENT = 1 << 8, - DEBUG_TXBUFFER = 1 << 9, - DEBUG_QUEUE = 1 << 10, - DEBUG_BOOT = 1 << 11, - DEBUG_PSM = 1 << 12, - DEBUG_ALL = ~0, -}; - -#define DEBUG_LEVEL DEBUG_NONE -/* #define DEBUG_LEVEL DEBUG_ALL */ -/* #define DEBUG_LEVEL (DEBUG_TX | DEBUG_RX | DEBUG_IRQ) */ -/* #define DEBUG_LEVEL (DEBUG_TX | DEBUG_MEMREGION | DEBUG_QUEUE) */ -/* #define DEBUG_LEVEL (DEBUG_MEMREGION | DEBUG_QUEUE) */ - -#define stlc45xx_error(fmt, arg...) \ - printk(KERN_ERR DRIVER_PREFIX "ERROR " fmt "\n", ##arg) - -#define stlc45xx_warning(fmt, arg...) \ - printk(KERN_WARNING DRIVER_PREFIX "WARNING " fmt "\n", ##arg) - -#define stlc45xx_info(fmt, arg...) \ - printk(KERN_INFO DRIVER_PREFIX fmt "\n", ##arg) - -#define stlc45xx_debug(level, fmt, arg...) \ - do { \ - if (level & DEBUG_LEVEL) \ - printk(KERN_DEBUG DRIVER_PREFIX fmt "\n", ##arg); \ - } while (0) - -#define stlc45xx_dump(level, buf, len) \ - do { \ - if (level & DEBUG_LEVEL) \ - print_hex_dump(KERN_DEBUG, "", DUMP_PREFIX_OFFSET, \ - 16, 1, buf, len, 1); \ - } while (0) - -#define MAC2STR(a) ((a)[0], (a)[1], (a)[2], (a)[3], (a)[4], (a)[5]) -#define MACSTR "%02x:%02x:%02x:%02x:%02x:%02x" - -/* Bit 15 is read/write bit; ON = READ, OFF = WRITE */ -#define ADDR_READ_BIT_15 0x8000 - -#define SPI_ADRS_ARM_INTERRUPTS 0x00 -#define SPI_ADRS_ARM_INT_EN 0x04 - -#define SPI_ADRS_HOST_INTERRUPTS 0x08 -#define SPI_ADRS_HOST_INT_EN 0x0c -#define SPI_ADRS_HOST_INT_ACK 0x10 - -#define SPI_ADRS_GEN_PURP_1 0x14 -#define SPI_ADRS_GEN_PURP_2 0x18 - -/* high word */ -#define SPI_ADRS_DEV_CTRL_STAT 0x26 - -#define SPI_ADRS_DMA_DATA 0x28 - -#define SPI_ADRS_DMA_WRITE_CTRL 0x2c -#define SPI_ADRS_DMA_WRITE_LEN 0x2e -#define SPI_ADRS_DMA_WRITE_BASE 0x30 - -#define SPI_ADRS_DMA_READ_CTRL 0x34 -#define SPI_ADRS_DMA_READ_LEN 0x36 -#define SPI_ADRS_DMA_READ_BASE 0x38 - -#define SPI_CTRL_STAT_HOST_OVERRIDE 0x8000 -#define SPI_CTRL_STAT_START_HALTED 0x4000 -#define SPI_CTRL_STAT_RAM_BOOT 0x2000 -#define SPI_CTRL_STAT_HOST_RESET 0x1000 -#define SPI_CTRL_STAT_HOST_CPU_EN 0x0800 - -#define SPI_DMA_WRITE_CTRL_ENABLE 0x0001 -#define SPI_DMA_READ_CTRL_ENABLE 0x0001 -#define HOST_ALLOWED (1 << 7) - -#define FIRMWARE_ADDRESS 0x20000 - -#define SPI_TIMEOUT 100 /* msec */ - -#define SPI_MAX_TX_PACKETS 32 - -#define SPI_MAX_PACKET_SIZE 32767 - -#define SPI_TARGET_INT_WAKEUP 0x00000001 -#define SPI_TARGET_INT_SLEEP 0x00000002 -#define SPI_TARGET_INT_RDDONE 0x00000004 - -#define SPI_TARGET_INT_CTS 0x00004000 -#define SPI_TARGET_INT_DR 0x00008000 - -#define SPI_HOST_INT_READY 0x00000001 -#define SPI_HOST_INT_WR_READY 0x00000002 -#define SPI_HOST_INT_SW_UPDATE 0x00000004 -#define SPI_HOST_INT_UPDATE 0x10000000 - -/* clear to send */ -#define SPI_HOST_INT_CTS 0x00004000 - -/* data ready */ -#define SPI_HOST_INT_DR 0x00008000 - -#define SPI_HOST_INTS_DEFAULT \ - (SPI_HOST_INT_READY | SPI_HOST_INT_UPDATE | SPI_HOST_INT_SW_UPDATE) - -#define TARGET_BOOT_SLEEP 50 - -/* The firmware buffer is divided into three areas: - * - * o config area (for control commands) - * o tx buffer - * o rx buffer - */ -#define FIRMWARE_BUFFER_START 0x20200 -#define FIRMWARE_BUFFER_END 0x27c60 -#define FIRMWARE_BUFFER_LEN (FIRMWARE_BUFFER_END - FIRMWARE_BUFFER_START) -#define FIRMWARE_MTU 3240 -#define FIRMWARE_CONFIG_PAYLOAD_LEN 1024 -#define FIRMWARE_CONFIG_START FIRMWARE_BUFFER_START -#define FIRMWARE_CONFIG_LEN (sizeof(struct s_lm_control) + \ - FIRMWARE_CONFIG_PAYLOAD_LEN) -#define FIRMWARE_CONFIG_END (FIRMWARE_CONFIG_START + FIRMWARE_CONFIG_LEN - 1) -#define FIRMWARE_RXBUFFER_LEN (5 * FIRMWARE_MTU + 1024) -#define FIRMWARE_RXBUFFER_START (FIRMWARE_BUFFER_END - FIRMWARE_RXBUFFER_LEN) -#define FIRMWARE_RXBUFFER_END (FIRMWARE_RXBUFFER_START + \ - FIRMWARE_RXBUFFER_LEN - 1) -#define FIRMWARE_TXBUFFER_START (FIRMWARE_BUFFER_START + FIRMWARE_CONFIG_LEN) -#define FIRMWARE_TXBUFFER_LEN (FIRMWARE_BUFFER_LEN - FIRMWARE_CONFIG_LEN - \ - FIRMWARE_RXBUFFER_LEN) -#define FIRMWARE_TXBUFFER_END (FIRMWARE_TXBUFFER_START + \ - FIRMWARE_TXBUFFER_LEN - 1) - -#define FIRMWARE_TXBUFFER_HEADER 100 -#define FIRMWARE_TXBUFFER_TRAILER 4 - -/* FIXME: come up with a proper value */ -#define MAX_FRAME_LEN 2500 - -/* unit is ms */ -#define TX_FRAME_LIFETIME 2000 -#define TX_TIMEOUT 4000 - -#define SUPPORTED_CHANNELS 13 - -/* FIXME */ -/* #define CHANNEL_CAL_LEN offsetof(struct s_lmo_scan, bratemask) - \ */ -/* offsetof(struct s_lmo_scan, channel) */ -#define CHANNEL_CAL_LEN 292 -#define CHANNEL_CAL_ARRAY_LEN (SUPPORTED_CHANNELS * CHANNEL_CAL_LEN) -/* FIXME */ -/* #define RSSI_CAL_LEN sizeof(struct s_lmo_scan) - \ */ -/* offsetof(struct s_lmo_scan, rssical) */ -#define RSSI_CAL_LEN 8 -#define RSSI_CAL_ARRAY_LEN (SUPPORTED_CHANNELS * RSSI_CAL_LEN) - -struct s_dma_regs { - unsigned short cmd; - unsigned short len; - unsigned long addr; -}; - -struct stlc45xx_ie_tim { - u8 dtim_count; - u8 dtim_period; - u8 bmap_control; - u8 pvbmap[251]; -}; - -struct txbuffer { - /* can be removed when switched to skb queue */ - struct list_head tx_list; - - struct list_head buffer_list; - - int start; - int frame_start; - int end; - - struct sk_buff *skb; - u32 handle; - - bool status_needed; - - int header_len; - - /* unit jiffies */ - unsigned long lifetime; -}; - -enum fw_state { - FW_STATE_OFF, - FW_STATE_BOOTING, - FW_STATE_READY, - FW_STATE_RESET, - FW_STATE_RESETTING, -}; - -struct stlc45xx { - struct ieee80211_hw *hw; - struct spi_device *spi; - struct work_struct work; - struct work_struct work_reset; - struct delayed_work work_tx_timeout; - struct mutex mutex; - struct completion fw_comp; - - - u8 bssid[ETH_ALEN]; - u8 mac_addr[ETH_ALEN]; - int channel; - - u8 *cal_rssi; - u8 *cal_channels; - - enum fw_state fw_state; - - spinlock_t tx_lock; - - /* protected by tx_lock */ - struct list_head txbuffer; - - /* protected by tx_lock */ - struct list_head tx_pending; - - /* protected by tx_lock */ - int tx_queue_stopped; - - /* protected by mutex */ - struct list_head tx_sent; - - int tx_frames; - - u8 *fw; - int fw_len; - - bool psm; - bool associated; - int aid; - bool pspolling; -}; - - diff --git a/drivers/staging/stlc45xx/stlc45xx_lmac.h b/drivers/staging/stlc45xx/stlc45xx_lmac.h deleted file mode 100644 index af5db801347f..000000000000 --- a/drivers/staging/stlc45xx/stlc45xx_lmac.h +++ /dev/null @@ -1,434 +0,0 @@ -/************************************************************************ -* This is the LMAC API interface header file for STLC4560. * -* Copyright (C) 2007 Conexant Systems, Inc. * -* This program is free software; you can redistribute it and/or * -* modify it under the terms of the GNU General Public License * -* as published by the Free Software Foundation; either version 2 * -* of the License, or (at your option) any later version. * -* * -* This program is distributed in the hope that it will be useful, * -* but WITHOUT ANY WARRANTY; without even the implied warranty of * -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * -* GNU General Public License for more details. * -* * -* You should have received a copy of the GNU General Public License * -* along with this program. If not, see <http://www.gnu.org/licenses/>.* -*************************************************************************/ - -#ifndef __lmac_h__ -#define __lmac_h__ - -#define LM_TOP_VARIANT 0x0506 -#define LM_BOTTOM_VARIANT 0x0506 - -/* - * LMAC - UMAC interface definition: - */ - -#define LM_FLAG_CONTROL 0x8000 -#define LM_FLAG_ALIGN 0x4000 - -#define LM_CTRL_OPSET 0x0001 - -#define LM_OUT_PROMISC 0x0001 -#define LM_OUT_TIMESTAMP 0x0002 -#define LM_OUT_SEQNR 0x0004 -#define LM_OUT_BURST 0x0010 -#define LM_OUT_NOCANCEL 0x0020 -#define LM_OUT_CLEARTIM 0x0040 -#define LM_OUT_HITCHHIKE 0x0080 -#define LM_OUT_COMPRESS 0x0100 -#define LM_OUT_CONCAT 0x0200 -#define LM_OUT_PCS_ACCEPT 0x0400 -#define LM_OUT_WAITEOSP 0x0800 - - -#define LM_ALOFT_SP 0x10 -#define LM_ALOFT_CTS 0x20 -#define LM_ALOFT_RTS 0x40 -#define LM_ALOFT_MASK 0x1f -#define LM_ALOFT_RATE 0x0f - -#define LM_IN_FCS_GOOD 0x0001 -#define LM_IN_MATCH_MAC 0x0002 -#define LM_IN_MCBC 0x0004 -#define LM_IN_BEACON 0x0008 -#define LM_IN_MATCH_BSS 0x0010 -#define LM_IN_BCAST_BSS 0x0020 -#define LM_IN_DATA 0x0040 -#define LM_IN_TRUNCATED 0x0080 - -#define LM_IN_TRANSPARENT 0x0200 - -#define LM_QUEUE_BEACON 0 -#define LM_QUEUE_SCAN 1 -#define LM_QUEUE_MGT 2 -#define LM_QUEUE_MCBC 3 -#define LM_QUEUE_DATA 4 -#define LM_QUEUE_DATA0 4 -#define LM_QUEUE_DATA1 5 -#define LM_QUEUE_DATA2 6 -#define LM_QUEUE_DATA3 7 - -#define LM_SETUP_INFRA 0x0001 -#define LM_SETUP_IBSS 0x0002 -#define LM_SETUP_TRANSPARENT 0x0008 -#define LM_SETUP_PROMISCUOUS 0x0010 -#define LM_SETUP_HIBERNATE 0x0020 -#define LM_SETUP_NOACK 0x0040 -#define LM_SETUP_RX_DISABLED 0x0080 - -#define LM_ANTENNA_0 0 -#define LM_ANTENNA_1 1 -#define LM_ANTENNA_DIVERSITY 2 - -#define LM_TX_FAILED 0x0001 -#define LM_TX_PSM 0x0002 -#define LM_TX_PSM_CANCELLED 0x0004 - -#define LM_SCAN_EXIT 0x0001 -#define LM_SCAN_TRAP 0x0002 -#define LM_SCAN_ACTIVE 0x0004 -#define LM_SCAN_FILTER 0x0008 - -#define LM_PSM 0x0001 -#define LM_PSM_DTIM 0x0002 -#define LM_PSM_MCBC 0x0004 -#define LM_PSM_CHECKSUM 0x0008 -#define LM_PSM_SKIP_MORE_DATA 0x0010 -#define LM_PSM_BEACON_TIMEOUT 0x0020 -#define LM_PSM_HFOSLEEP 0x0040 -#define LM_PSM_AUTOSWITCH_SLEEP 0x0080 -#define LM_PSM_LPIT 0x0100 -#define LM_PSM_BF_UCAST_SKIP 0x0200 -#define LM_PSM_BF_MCAST_SKIP 0x0400 - -/* hfosleep */ -#define LM_PSM_SLEEP_OPTION_MASK (LM_PSM_AUTOSWITCH_SLEEP | LM_PSM_HFOSLEEP) -#define LM_PSM_SLEEP_OPTION_SHIFT 6 -/* hfosleepend */ -#define LM_PSM_BF_OPTION_MASK (LM_PSM_BF_MCAST_SKIP | LM_PSM_BF_UCAST_SKIP) -#define LM_PSM_BF_OPTION_SHIFT 9 - - -#define LM_PRIVACC_WEP 0x01 -#define LM_PRIVACC_TKIP 0x02 -#define LM_PRIVACC_MICHAEL 0x04 -#define LM_PRIVACC_CCX_KP 0x08 -#define LM_PRIVACC_CCX_MIC 0x10 -#define LM_PRIVACC_AES_CCMP 0x20 - -/* size of s_lm_descr in words */ -#define LM_DESCR_SIZE_WORDS 11 - -#ifndef __ASSEMBLER__ - -enum { - LM_MODE_CLIENT = 0, - LM_MODE_AP -}; - -struct s_lm_descr { - uint16_t modes; - uint16_t flags; - uint32_t buffer_start; - uint32_t buffer_end; - uint8_t header; - uint8_t trailer; - uint8_t tx_queues; - uint8_t tx_depth; - uint8_t privacy; - uint8_t rx_keycache; - uint8_t tim_size; - uint8_t pad1; - uint8_t rates[16]; - uint32_t link; - uint16_t mtu; -}; - - -struct s_lm_control { - uint16_t flags; - uint16_t length; - uint32_t handle; - uint16_t oid; - uint16_t pad; - /* uint8_t data[]; */ -}; - -enum { - LM_PRIV_NONE = 0, - LM_PRIV_WEP, - LM_PRIV_TKIP, - LM_PRIV_TKIPMICHAEL, - LM_PRIV_CCX_WEPMIC, - LM_PRIV_CCX_KPMIC, - LM_PRIV_CCX_KP, - LM_PRIV_AES_CCMP -}; - -enum { - LM_DECRYPT_NONE, - LM_DECRYPT_OK, - LM_DECRYPT_NOKEY, - LM_DECRYPT_NOMICHAEL, - LM_DECRYPT_NOCKIPMIC, - LM_DECRYPT_FAIL_WEP, - LM_DECRYPT_FAIL_TKIP, - LM_DECRYPT_FAIL_MICHAEL, - LM_DECRYPT_FAIL_CKIPKP, - LM_DECRYPT_FAIL_CKIPMIC, - LM_DECRYPT_FAIL_AESCCMP -}; - -struct s_lm_data_out { - uint16_t flags; - uint16_t length; - uint32_t handle; - uint16_t aid; - uint8_t rts_retries; - uint8_t retries; - uint8_t aloft[8]; - uint8_t aloft_ctrl; - uint8_t crypt_offset; - uint8_t keytype; - uint8_t keylen; - uint8_t key[16]; - uint8_t queue; - uint8_t backlog; - uint16_t durations[4]; - uint8_t antenna; - uint8_t cts; - int16_t power; - uint8_t pad[2]; - /*uint8_t data[];*/ -}; - -#define LM_RCPI_INVALID (0xff) - -struct s_lm_data_in { - uint16_t flags; - uint16_t length; - uint16_t frequency; - uint8_t antenna; - uint8_t rate; - uint8_t rcpi; - uint8_t sq; - uint8_t decrypt; - uint8_t rssi_raw; - uint32_t clock[2]; - /*uint8_t data[];*/ -}; - -union u_lm_data { - struct s_lm_data_out out; - struct s_lm_data_in in; -}; - -enum { - LM_OID_SETUP = 0, - LM_OID_SCAN = 1, - LM_OID_TRAP = 2, - LM_OID_EDCF = 3, - LM_OID_KEYCACHE = 4, - LM_OID_PSM = 6, - LM_OID_TXCANCEL = 7, - LM_OID_TX = 8, - LM_OID_BURST = 9, - LM_OID_STATS = 10, - LM_OID_LED = 13, - LM_OID_TIMER = 15, - LM_OID_NAV = 20, - LM_OID_PCS = 22, - LM_OID_BT_BALANCER = 28, - LM_OID_GROUP_ADDRESS_TABLE = 30, - LM_OID_ARPTABLE = 31, - LM_OID_BT_OPTIONS = 35 -}; - -enum { - LM_FRONTEND_UNKNOWN = 0, - LM_FRONTEND_DUETTE3, - LM_FRONTEND_DUETTE2, - LM_FRONTEND_FRISBEE, - LM_FRONTEND_CROSSBOW, - LM_FRONTEND_LONGBOW -}; - - -#define INVALID_LPF_BANDWIDTH 0xffff -#define INVALID_OSC_START_DELAY 0xffff - -struct s_lmo_setup { - uint16_t flags; - uint8_t macaddr[6]; - uint8_t bssid[6]; - uint8_t antenna; - uint8_t rx_align; - uint32_t rx_buffer; - uint16_t rx_mtu; - uint16_t frontend; - uint16_t timeout; - uint16_t truncate; - uint32_t bratemask; - uint8_t sbss_offset; - uint8_t mcast_window; - uint8_t rx_rssi_threshold; - uint8_t rx_ed_threshold; - uint32_t ref_clock; - uint16_t lpf_bandwidth; - uint16_t osc_start_delay; -}; - - -struct s_lmo_scan { - uint16_t flags; - uint16_t dwell; - uint8_t channel[292]; - uint32_t bratemask; - uint8_t aloft[8]; - uint8_t rssical[8]; -}; - - -enum { - LM_TRAP_SCAN = 0, - LM_TRAP_TIMER, - LM_TRAP_BEACON_TX, - LM_TRAP_FAA_RADIO_ON, - LM_TRAP_FAA_RADIO_OFF, - LM_TRAP_RADAR, - LM_TRAP_NO_BEACON, - LM_TRAP_TBTT, - LM_TRAP_SCO_ENTER, - LM_TRAP_SCO_EXIT -}; - -struct s_lmo_trap { - uint16_t event; - uint16_t frequency; -}; - -struct s_lmo_timer { - uint32_t interval; -}; - -struct s_lmo_nav { - uint32_t period; -}; - - -struct s_lmo_edcf_queue; - -struct s_lmo_edcf { - uint8_t flags; - uint8_t slottime; - uint8_t sifs; - uint8_t eofpad; - struct s_lmo_edcf_queue { - uint8_t aifs; - uint8_t pad0; - uint16_t cwmin; - uint16_t cwmax; - uint16_t txop; - } queues[8]; - uint8_t mapping[4]; - uint16_t maxburst; - uint16_t round_trip_delay; -}; - -struct s_lmo_keycache { - uint8_t entry; - uint8_t keyid; - uint8_t address[6]; - uint8_t pad[2]; - uint8_t keytype; - uint8_t keylen; - uint8_t key[24]; -}; - - -struct s_lm_interval; - -struct s_lmo_psm { - uint16_t flags; - uint16_t aid; - struct s_lm_interval { - uint16_t interval; - uint16_t periods; - } intervals[4]; - /* uint16_t pad; */ - uint8_t beacon_rcpi_skip_max; - uint8_t rcpi_delta_threshold; - uint8_t nr; - uint8_t exclude[1]; -}; - -#define MC_FILTER_ADDRESS_NUM 4 - -struct s_lmo_group_address_table { - uint16_t filter_enable; - uint16_t num_address; - uint8_t macaddr_list[MC_FILTER_ADDRESS_NUM][6]; -}; - -struct s_lmo_txcancel { - uint32_t address[1]; -}; - - -struct s_lmo_tx { - uint8_t flags; - uint8_t retries; - uint8_t rcpi; - uint8_t sq; - uint16_t seqctrl; - uint8_t antenna; - uint8_t pad; -}; - -struct s_lmo_burst { - uint8_t flags; - uint8_t queue; - uint8_t backlog; - uint8_t pad; - uint16_t durations[32]; -}; - -struct s_lmo_stats { - uint32_t valid; - uint32_t fcs; - uint32_t abort; - uint32_t phyabort; - uint32_t rts_success; - uint32_t rts_fail; - uint32_t timestamp; - uint32_t time_tx; - uint32_t noisefloor; - uint32_t sample_noise[8]; - uint32_t sample_cca; - uint32_t sample_tx; -}; - - -struct s_lmo_led { - uint16_t flags; - uint16_t mask[2]; - uint16_t delay/*[2]*/; -}; - - -struct s_lmo_bt_balancer { - uint16_t prio_thresh; - uint16_t acl_thresh; -}; - - -struct s_lmo_arp_table { - uint16_t filter_enable; - uint32_t ipaddr; -}; - -#endif /* __ASSEMBLER__ */ - -#endif /* __lmac_h__ */ diff --git a/drivers/staging/vme/bridges/vme_ca91cx42.c b/drivers/staging/vme/bridges/vme_ca91cx42.c index 3d2a84c45829..e139eaeaa174 100644 --- a/drivers/staging/vme/bridges/vme_ca91cx42.c +++ b/drivers/staging/vme/bridges/vme_ca91cx42.c @@ -25,6 +25,7 @@ #include <linux/poll.h> #include <linux/interrupt.h> #include <linux/spinlock.h> +#include <linux/sched.h> #include <asm/time.h> #include <asm/io.h> #include <asm/uaccess.h> diff --git a/drivers/staging/vme/bridges/vme_tsi148.c b/drivers/staging/vme/bridges/vme_tsi148.c index 8960fa9ee7aa..00fe0803c21c 100644 --- a/drivers/staging/vme/bridges/vme_tsi148.c +++ b/drivers/staging/vme/bridges/vme_tsi148.c @@ -25,6 +25,7 @@ #include <linux/dma-mapping.h> #include <linux/interrupt.h> #include <linux/spinlock.h> +#include <linux/sched.h> #include <asm/time.h> #include <asm/io.h> #include <asm/uaccess.h> diff --git a/drivers/staging/vt6656/main_usb.c b/drivers/staging/vt6656/main_usb.c index 7f96bcaf1c60..05186110c029 100644 --- a/drivers/staging/vt6656/main_usb.c +++ b/drivers/staging/vt6656/main_usb.c @@ -1332,7 +1332,6 @@ device_release_WPADEV(pDevice); free_netdev(pDevice->dev); } - kfree(pDevice); DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO "device_disconnect3.. \n"); } diff --git a/drivers/staging/winbond/Kconfig b/drivers/staging/winbond/Kconfig index 940460c39f36..132671d96d0d 100644 --- a/drivers/staging/winbond/Kconfig +++ b/drivers/staging/winbond/Kconfig @@ -1,6 +1,6 @@ config W35UND tristate "IS89C35 WLAN USB driver" - depends on MAC80211 && WLAN_80211 && USB && EXPERIMENTAL + depends on MAC80211 && WLAN && USB && EXPERIMENTAL default n ---help--- This is highly experimental driver for Winbond WIFI card. diff --git a/drivers/staging/winbond/wbusb.c b/drivers/staging/winbond/wbusb.c index 8950724f168e..067082a7d759 100644 --- a/drivers/staging/winbond/wbusb.c +++ b/drivers/staging/winbond/wbusb.c @@ -51,10 +51,26 @@ static struct ieee80211_supported_band wbsoft_band_2GHz = { .n_bitrates = ARRAY_SIZE(wbsoft_rates), }; +static void hal_set_beacon_period(struct hw_data *pHwData, u16 beacon_period) +{ + u32 tmp; + + if (pHwData->SurpriseRemove) + return; + + pHwData->BeaconPeriod = beacon_period; + tmp = pHwData->BeaconPeriod << 16; + tmp |= pHwData->ProbeDelay; + Wb35Reg_Write(pHwData, 0x0848, tmp); +} + static int wbsoft_add_interface(struct ieee80211_hw *dev, struct ieee80211_if_init_conf *conf) { - printk("wbsoft_add interface called\n"); + struct wbsoft_priv *priv = dev->priv; + + hal_set_beacon_period(&priv->sHwData, conf->vif->bss_conf.beacon_int); + return 0; } @@ -83,10 +99,16 @@ static int wbsoft_get_tx_stats(struct ieee80211_hw *hw, return 0; } +static u64 wbsoft_prepare_multicast(struct ieee80211_hw *hw, int mc_count, + struct dev_addr_list *mc_list) +{ + return mc_count; +} + static void wbsoft_configure_filter(struct ieee80211_hw *dev, unsigned int changed_flags, unsigned int *total_flags, - int mc_count, struct dev_mc_list *mclist) + u64 multicast) { unsigned int new_flags; @@ -94,7 +116,7 @@ static void wbsoft_configure_filter(struct ieee80211_hw *dev, if (*total_flags & FIF_PROMISC_IN_BSS) new_flags |= FIF_PROMISC_IN_BSS; - else if ((*total_flags & FIF_ALLMULTI) || (mc_count > 32)) + else if ((*total_flags & FIF_ALLMULTI) || (multicast > 32)) new_flags |= FIF_ALLMULTI; dev->flags &= ~IEEE80211_HW_RX_INCLUDES_FCS; @@ -138,19 +160,6 @@ static void hal_set_radio_mode(struct hw_data *pHwData, unsigned char radio_off) Wb35Reg_Write(pHwData, 0x0824, reg->M24_MacControl); } -static void hal_set_beacon_period(struct hw_data *pHwData, u16 beacon_period) -{ - u32 tmp; - - if (pHwData->SurpriseRemove) - return; - - pHwData->BeaconPeriod = beacon_period; - tmp = pHwData->BeaconPeriod << 16; - tmp |= pHwData->ProbeDelay; - Wb35Reg_Write(pHwData, 0x0848, tmp); -} - static void hal_set_current_channel_ex(struct hw_data *pHwData, ChanInfo channel) { @@ -244,7 +253,6 @@ static void hal_set_accept_beacon(struct hw_data *pHwData, u8 enable) static int wbsoft_config(struct ieee80211_hw *dev, u32 changed) { struct wbsoft_priv *priv = dev->priv; - struct ieee80211_conf *conf = &dev->conf; ChanInfo ch; printk("wbsoft_config called\n"); @@ -254,7 +262,6 @@ static int wbsoft_config(struct ieee80211_hw *dev, u32 changed) ch.ChanNo = 1; hal_set_current_channel(&priv->sHwData, ch); - hal_set_beacon_period(&priv->sHwData, conf->beacon_int); hal_set_accept_broadcast(&priv->sHwData, 1); hal_set_accept_promiscuous(&priv->sHwData, 1); hal_set_accept_multicast(&priv->sHwData, 1); @@ -277,6 +284,7 @@ static const struct ieee80211_ops wbsoft_ops = { .add_interface = wbsoft_add_interface, .remove_interface = wbsoft_remove_interface, .config = wbsoft_config, + .prepare_multicast = wbsoft_prepare_multicast, .configure_filter = wbsoft_configure_filter, .get_stats = wbsoft_get_stats, .get_tx_stats = wbsoft_get_tx_stats, diff --git a/drivers/staging/wlan-ng/Kconfig b/drivers/staging/wlan-ng/Kconfig index 9959b658c8cf..f44294b0d8dc 100644 --- a/drivers/staging/wlan-ng/Kconfig +++ b/drivers/staging/wlan-ng/Kconfig @@ -1,6 +1,6 @@ config PRISM2_USB tristate "Prism2.5/3 USB driver" - depends on WLAN_80211 && USB && WIRELESS_EXT + depends on WLAN && USB && WIRELESS_EXT default n ---help--- This is the wlan-ng prism 2.5/3 USB driver for a wide range of diff --git a/drivers/thermal/thermal_sys.c b/drivers/thermal/thermal_sys.c index 4e83c297ec9e..6f8d8f971212 100644 --- a/drivers/thermal/thermal_sys.c +++ b/drivers/thermal/thermal_sys.c @@ -180,15 +180,15 @@ trip_point_type_show(struct device *dev, struct device_attribute *attr, switch (type) { case THERMAL_TRIP_CRITICAL: - return sprintf(buf, "critical"); + return sprintf(buf, "critical\n"); case THERMAL_TRIP_HOT: - return sprintf(buf, "hot"); + return sprintf(buf, "hot\n"); case THERMAL_TRIP_PASSIVE: - return sprintf(buf, "passive"); + return sprintf(buf, "passive\n"); case THERMAL_TRIP_ACTIVE: - return sprintf(buf, "active"); + return sprintf(buf, "active\n"); default: - return sprintf(buf, "unknown"); + return sprintf(buf, "unknown\n"); } } diff --git a/drivers/uio/uio.c b/drivers/uio/uio.c index a9d707047202..e941367dd28f 100644 --- a/drivers/uio/uio.c +++ b/drivers/uio/uio.c @@ -19,6 +19,7 @@ #include <linux/device.h> #include <linux/mm.h> #include <linux/idr.h> +#include <linux/sched.h> #include <linux/string.h> #include <linux/kobject.h> #include <linux/uio_driver.h> diff --git a/drivers/uio/uio_pdrv_genirq.c b/drivers/uio/uio_pdrv_genirq.c index 02347c57357d..aa53db9f2e88 100644 --- a/drivers/uio/uio_pdrv_genirq.c +++ b/drivers/uio/uio_pdrv_genirq.c @@ -178,6 +178,7 @@ static int uio_pdrv_genirq_probe(struct platform_device *pdev) return 0; bad1: kfree(priv); + pm_runtime_disable(&pdev->dev); bad0: return ret; } diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c index e3861b21e776..e4eca7810bcf 100644 --- a/drivers/usb/class/cdc-acm.c +++ b/drivers/usb/class/cdc-acm.c @@ -609,9 +609,9 @@ static int acm_tty_open(struct tty_struct *tty, struct file *filp) acm->throttle = 0; - tasklet_schedule(&acm->urb_task); set_bit(ASYNCB_INITIALIZED, &acm->port.flags); rv = tty_port_block_til_ready(&acm->port, tty, filp); + tasklet_schedule(&acm->urb_task); done: mutex_unlock(&acm->mutex); err_out: @@ -686,15 +686,21 @@ static void acm_tty_close(struct tty_struct *tty, struct file *filp) /* Perform the closing process and see if we need to do the hardware shutdown */ - if (!acm || tty_port_close_start(&acm->port, tty, filp) == 0) + if (!acm) + return; + if (tty_port_close_start(&acm->port, tty, filp) == 0) { + mutex_lock(&open_mutex); + if (!acm->dev) { + tty_port_tty_set(&acm->port, NULL); + acm_tty_unregister(acm); + tty->driver_data = NULL; + } + mutex_unlock(&open_mutex); return; + } acm_port_down(acm, 0); tty_port_close_end(&acm->port, tty); - mutex_lock(&open_mutex); tty_port_tty_set(&acm->port, NULL); - if (!acm->dev) - acm_tty_unregister(acm); - mutex_unlock(&open_mutex); } static int acm_tty_write(struct tty_struct *tty, diff --git a/drivers/usb/class/usbtmc.c b/drivers/usb/class/usbtmc.c index 864f0ba6a344..2473cf0c6b1d 100644 --- a/drivers/usb/class/usbtmc.c +++ b/drivers/usb/class/usbtmc.c @@ -39,7 +39,7 @@ #define USBTMC_SIZE_IOBUFFER 2048 /* Default USB timeout (in milliseconds) */ -#define USBTMC_TIMEOUT 10 +#define USBTMC_TIMEOUT 5000 /* * Maximum number of read cycles to empty bulk in endpoint during CLEAR and diff --git a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig index 33351312327f..a18e3c5dd82e 100644 --- a/drivers/usb/gadget/Kconfig +++ b/drivers/usb/gadget/Kconfig @@ -223,6 +223,7 @@ config USB_OTG config USB_GADGET_PXA25X boolean "PXA 25x or IXP 4xx" depends on (ARCH_PXA && PXA25x) || ARCH_IXP4XX + select USB_OTG_UTILS help Intel's PXA 25x series XScale ARM-5TE processors include an integrated full speed USB 1.1 device controller. The diff --git a/drivers/usb/gadget/ether.c b/drivers/usb/gadget/ether.c index f37de283d0ab..167cb2a8ecef 100644 --- a/drivers/usb/gadget/ether.c +++ b/drivers/usb/gadget/ether.c @@ -61,11 +61,6 @@ * simpler, Microsoft pushes their own approach: RNDIS. The published * RNDIS specs are ambiguous and appear to be incomplete, and are also * needlessly complex. They borrow more from CDC ACM than CDC ECM. - * - * While CDC ECM, CDC Subset, and RNDIS are designed to extend the ethernet - * interface to the target, CDC EEM was designed to use ethernet over the USB - * link between the host and target. CDC EEM is implemented as an alternative - * to those other protocols when that communication model is more appropriate */ #define DRIVER_DESC "Ethernet Gadget" @@ -157,8 +152,8 @@ static inline bool has_rndis(void) #define RNDIS_PRODUCT_NUM 0xa4a2 /* Ethernet/RNDIS Gadget */ /* For EEM gadgets */ -#define EEM_VENDOR_NUM 0x0525 /* INVALID - NEEDS TO BE ALLOCATED */ -#define EEM_PRODUCT_NUM 0xa4a1 /* INVALID - NEEDS TO BE ALLOCATED */ +#define EEM_VENDOR_NUM 0x1d6b /* Linux Foundation */ +#define EEM_PRODUCT_NUM 0x0102 /* EEM Gadget */ /*-------------------------------------------------------------------------*/ diff --git a/drivers/usb/gadget/fsl_udc_core.c b/drivers/usb/gadget/fsl_udc_core.c index 42a74b8a0bb8..fa3d142ba64d 100644 --- a/drivers/usb/gadget/fsl_udc_core.c +++ b/drivers/usb/gadget/fsl_udc_core.c @@ -2139,7 +2139,7 @@ static int fsl_proc_read(char *page, char **start, off_t off, int count, static void fsl_udc_release(struct device *dev) { complete(udc_controller->done); - dma_free_coherent(dev, udc_controller->ep_qh_size, + dma_free_coherent(dev->parent, udc_controller->ep_qh_size, udc_controller->ep_qh, udc_controller->ep_qh_dma); kfree(udc_controller); } diff --git a/drivers/usb/gadget/imx_udc.c b/drivers/usb/gadget/imx_udc.c index c52a681f376c..01ee0b9bc957 100644 --- a/drivers/usb/gadget/imx_udc.c +++ b/drivers/usb/gadget/imx_udc.c @@ -1402,7 +1402,8 @@ static int __init imx_udc_probe(struct platform_device *pdev) struct clk *clk; void __iomem *base; int ret = 0; - int i, res_size; + int i; + resource_size_t res_size; res = platform_get_resource(pdev, IORESOURCE_MEM, 0); if (!res) { @@ -1416,7 +1417,7 @@ static int __init imx_udc_probe(struct platform_device *pdev) return -ENODEV; } - res_size = res->end - res->start + 1; + res_size = resource_size(res); if (!request_mem_region(res->start, res_size, res->name)) { dev_err(&pdev->dev, "can't allocate %d bytes at %d address\n", res_size, res->start); @@ -1527,8 +1528,7 @@ static int __exit imx_udc_remove(struct platform_device *pdev) clk_disable(imx_usb->clk); iounmap(imx_usb->base); - release_mem_region(imx_usb->res->start, - imx_usb->res->end - imx_usb->res->start + 1); + release_mem_region(imx_usb->res->start, resource_size(imx_usb->res)); if (pdata->exit) pdata->exit(&pdev->dev); diff --git a/drivers/usb/gadget/r8a66597-udc.h b/drivers/usb/gadget/r8a66597-udc.h index 03087e7b9190..9a537aa07968 100644 --- a/drivers/usb/gadget/r8a66597-udc.h +++ b/drivers/usb/gadget/r8a66597-udc.h @@ -131,31 +131,48 @@ static inline u16 r8a66597_read(struct r8a66597 *r8a66597, unsigned long offset) } static inline void r8a66597_read_fifo(struct r8a66597 *r8a66597, - unsigned long offset, u16 *buf, + unsigned long offset, + unsigned char *buf, int len) { + unsigned long fifoaddr = r8a66597->reg + offset; + unsigned int data; + int i; + if (r8a66597->pdata->on_chip) { - unsigned long fifoaddr = r8a66597->reg + offset; - unsigned long count; - union { - unsigned long dword; - unsigned char byte[4]; - } data; - unsigned char *pb; - int i; - - count = len / 4; - insl(fifoaddr, buf, count); - - if (len & 0x00000003) { - data.dword = inl(fifoaddr); - pb = (unsigned char *)buf + count * 4; - for (i = 0; i < (len & 0x00000003); i++) - pb[i] = data.byte[i]; + /* 32-bit accesses for on_chip controllers */ + + /* aligned buf case */ + if (len >= 4 && !((unsigned long)buf & 0x03)) { + insl(fifoaddr, buf, len / 4); + buf += len & ~0x03; + len &= 0x03; + } + + /* unaligned buf case */ + for (i = 0; i < len; i++) { + if (!(i & 0x03)) + data = inl(fifoaddr); + + buf[i] = (data >> ((i & 0x03) * 8)) & 0xff; } } else { - len = (len + 1) / 2; - insw(r8a66597->reg + offset, buf, len); + /* 16-bit accesses for external controllers */ + + /* aligned buf case */ + if (len >= 2 && !((unsigned long)buf & 0x01)) { + insw(fifoaddr, buf, len / 2); + buf += len & ~0x01; + len &= 0x01; + } + + /* unaligned buf case */ + for (i = 0; i < len; i++) { + if (!(i & 0x01)) + data = inw(fifoaddr); + + buf[i] = (data >> ((i & 0x01) * 8)) & 0xff; + } } } @@ -166,38 +183,40 @@ static inline void r8a66597_write(struct r8a66597 *r8a66597, u16 val, } static inline void r8a66597_write_fifo(struct r8a66597 *r8a66597, - unsigned long offset, u16 *buf, + unsigned long offset, + unsigned char *buf, int len) { unsigned long fifoaddr = r8a66597->reg + offset; + int adj = 0; + int i; if (r8a66597->pdata->on_chip) { - unsigned long count; - unsigned char *pb; - int i; - - count = len / 4; - outsl(fifoaddr, buf, count); - - if (len & 0x00000003) { - pb = (unsigned char *)buf + count * 4; - for (i = 0; i < (len & 0x00000003); i++) { - if (r8a66597_read(r8a66597, CFIFOSEL) & BIGEND) - outb(pb[i], fifoaddr + i); - else - outb(pb[i], fifoaddr + 3 - i); - } + /* 32-bit access only if buf is 32-bit aligned */ + if (len >= 4 && !((unsigned long)buf & 0x03)) { + outsl(fifoaddr, buf, len / 4); + buf += len & ~0x03; + len &= 0x03; } } else { - int odd = len & 0x0001; - - len = len / 2; - outsw(fifoaddr, buf, len); - if (unlikely(odd)) { - buf = &buf[len]; - outb((unsigned char)*buf, fifoaddr); + /* 16-bit access only if buf is 16-bit aligned */ + if (len >= 2 && !((unsigned long)buf & 0x01)) { + outsw(fifoaddr, buf, len / 2); + buf += len & ~0x01; + len &= 0x01; } } + + /* adjust fifo address in the little endian case */ + if (!(r8a66597_read(r8a66597, CFIFOSEL) & BIGEND)) { + if (r8a66597->pdata->on_chip) + adj = 0x03; /* 32-bit wide */ + else + adj = 0x01; /* 16-bit wide */ + } + + for (i = 0; i < len; i++) + outb(buf[i], fifoaddr + adj - (i & adj)); } static inline void r8a66597_mdfy(struct r8a66597 *r8a66597, diff --git a/drivers/usb/host/ehci-sched.c b/drivers/usb/host/ehci-sched.c index 3ea05936851f..b25cdea93a1f 100644 --- a/drivers/usb/host/ehci-sched.c +++ b/drivers/usb/host/ehci-sched.c @@ -1400,6 +1400,10 @@ iso_stream_schedule ( goto fail; } + period = urb->interval; + if (!stream->highspeed) + period <<= 3; + now = ehci_readl(ehci, &ehci->regs->frame_index) % mod; /* when's the last uframe this urb could start? */ @@ -1417,14 +1421,15 @@ iso_stream_schedule ( /* Fell behind (by up to twice the slop amount)? */ if (start >= max - 2 * 8 * SCHEDULE_SLOP) - start += stream->interval * DIV_ROUND_UP( - max - start, stream->interval) - mod; + start += period * DIV_ROUND_UP( + max - start, period) - mod; /* Tried to schedule too far into the future? */ if (unlikely((start + sched->span) >= max)) { status = -EFBIG; goto fail; } + stream->next_uframe = start; goto ready; } @@ -1440,10 +1445,6 @@ iso_stream_schedule ( /* NOTE: assumes URB_ISO_ASAP, to limit complexity/bugs */ - period = urb->interval; - if (!stream->highspeed) - period <<= 3; - /* find a uframe slot with enough bandwidth */ for (; start < (stream->next_uframe + period); start++) { int enough_space; diff --git a/drivers/usb/host/isp1362-hcd.c b/drivers/usb/host/isp1362-hcd.c index e35d82808bab..5c774ab98252 100644 --- a/drivers/usb/host/isp1362-hcd.c +++ b/drivers/usb/host/isp1362-hcd.c @@ -2284,10 +2284,10 @@ static int isp1362_mem_config(struct usb_hcd *hcd) dev_info(hcd->self.controller, "ISP1362 Memory usage:\n"); dev_info(hcd->self.controller, " ISTL: 2 * %4d: %4d @ $%04x:$%04x\n", istl_size / 2, istl_size, 0, istl_size / 2); - dev_info(hcd->self.controller, " INTL: %4d * (%3u+8): %4d @ $%04x\n", + dev_info(hcd->self.controller, " INTL: %4d * (%3lu+8): %4d @ $%04x\n", ISP1362_INTL_BUFFERS, intl_blksize - PTD_HEADER_SIZE, intl_size, istl_size); - dev_info(hcd->self.controller, " ATL : %4d * (%3u+8): %4d @ $%04x\n", + dev_info(hcd->self.controller, " ATL : %4d * (%3lu+8): %4d @ $%04x\n", atl_buffers, atl_blksize - PTD_HEADER_SIZE, atl_size, istl_size + intl_size); dev_info(hcd->self.controller, " USED/FREE: %4d %4d\n", total, @@ -2677,12 +2677,12 @@ static int __devexit isp1362_remove(struct platform_device *pdev) DBG(0, "%s: Removing HCD\n", __func__); usb_remove_hcd(hcd); - DBG(0, "%s: Unmapping data_reg @ %08x\n", __func__, - (u32)isp1362_hcd->data_reg); + DBG(0, "%s: Unmapping data_reg @ %p\n", __func__, + isp1362_hcd->data_reg); iounmap(isp1362_hcd->data_reg); - DBG(0, "%s: Unmapping addr_reg @ %08x\n", __func__, - (u32)isp1362_hcd->addr_reg); + DBG(0, "%s: Unmapping addr_reg @ %p\n", __func__, + isp1362_hcd->addr_reg); iounmap(isp1362_hcd->addr_reg); res = platform_get_resource(pdev, IORESOURCE_MEM, 1); @@ -2810,16 +2810,16 @@ static int __init isp1362_probe(struct platform_device *pdev) return 0; err6: - DBG(0, "%s: Freeing dev %08x\n", __func__, (u32)isp1362_hcd); + DBG(0, "%s: Freeing dev %p\n", __func__, isp1362_hcd); usb_put_hcd(hcd); err5: - DBG(0, "%s: Unmapping data_reg @ %08x\n", __func__, (u32)data_reg); + DBG(0, "%s: Unmapping data_reg @ %p\n", __func__, data_reg); iounmap(data_reg); err4: DBG(0, "%s: Releasing mem region %08lx\n", __func__, (long unsigned int)data->start); release_mem_region(data->start, resource_len(data)); err3: - DBG(0, "%s: Unmapping addr_reg @ %08x\n", __func__, (u32)addr_reg); + DBG(0, "%s: Unmapping addr_reg @ %p\n", __func__, addr_reg); iounmap(addr_reg); err2: DBG(0, "%s: Releasing mem region %08lx\n", __func__, (long unsigned int)addr->start); diff --git a/drivers/usb/host/isp1362.h b/drivers/usb/host/isp1362.h index fe60f62a32f3..1a253ebf7e50 100644 --- a/drivers/usb/host/isp1362.h +++ b/drivers/usb/host/isp1362.h @@ -580,7 +580,7 @@ static inline const char *ISP1362_INT_NAME(int n) static inline void ALIGNSTAT(struct isp1362_hcd *isp1362_hcd, void *ptr) { - unsigned p = (unsigned)ptr; + unsigned long p = (unsigned long)ptr; if (!(p & 0xf)) isp1362_hcd->stat16++; else if (!(p & 0x7)) @@ -770,7 +770,7 @@ static void isp1362_write_fifo(struct isp1362_hcd *isp1362_hcd, void *buf, u16 l if (!len) return; - if ((unsigned)dp & 0x1) { + if ((unsigned long)dp & 0x1) { /* not aligned */ for (; len > 1; len -= 2) { data = *dp++; @@ -962,8 +962,8 @@ static void isp1362_read_buffer(struct isp1362_hcd *isp1362_hcd, void *buf, u16 isp1362_write_diraddr(isp1362_hcd, offset, len); - DBG(3, "%s: Reading %d byte from buffer @%04x to memory @ %08x\n", __func__, - len, offset, (u32)buf); + DBG(3, "%s: Reading %d byte from buffer @%04x to memory @ %p\n", + __func__, len, offset, buf); isp1362_write_reg16(isp1362_hcd, HCuPINT, HCuPINT_EOT); _WARN_ON((isp1362_read_reg16(isp1362_hcd, HCuPINT) & HCuPINT_EOT)); @@ -982,8 +982,8 @@ static void isp1362_write_buffer(struct isp1362_hcd *isp1362_hcd, void *buf, u16 isp1362_write_diraddr(isp1362_hcd, offset, len); - DBG(3, "%s: Writing %d byte to buffer @%04x from memory @ %08x\n", __func__, - len, offset, (u32)buf); + DBG(3, "%s: Writing %d byte to buffer @%04x from memory @ %p\n", + __func__, len, offset, buf); isp1362_write_reg16(isp1362_hcd, HCuPINT, HCuPINT_EOT); _WARN_ON((isp1362_read_reg16(isp1362_hcd, HCuPINT) & HCuPINT_EOT)); diff --git a/drivers/usb/host/ohci-hcd.c b/drivers/usb/host/ohci-hcd.c index 78bb7710f36d..24eb74781919 100644 --- a/drivers/usb/host/ohci-hcd.c +++ b/drivers/usb/host/ohci-hcd.c @@ -87,6 +87,7 @@ static int ohci_restart (struct ohci_hcd *ohci); #ifdef CONFIG_PCI static void quirk_amd_pll(int state); static void amd_iso_dev_put(void); +static void sb800_prefetch(struct ohci_hcd *ohci, int on); #else static inline void quirk_amd_pll(int state) { @@ -96,6 +97,10 @@ static inline void amd_iso_dev_put(void) { return; } +static inline void sb800_prefetch(struct ohci_hcd *ohci, int on) +{ + return; +} #endif diff --git a/drivers/usb/host/ohci-pci.c b/drivers/usb/host/ohci-pci.c index d2ba04dd785e..b8a1148f248e 100644 --- a/drivers/usb/host/ohci-pci.c +++ b/drivers/usb/host/ohci-pci.c @@ -177,6 +177,13 @@ static int ohci_quirk_amd700(struct usb_hcd *hcd) return 0; pci_read_config_byte(amd_smbus_dev, PCI_REVISION_ID, &rev); + + /* SB800 needs pre-fetch fix */ + if ((rev >= 0x40) && (rev <= 0x4f)) { + ohci->flags |= OHCI_QUIRK_AMD_PREFETCH; + ohci_dbg(ohci, "enabled AMD prefetch quirk\n"); + } + if ((rev > 0x3b) || (rev < 0x30)) { pci_dev_put(amd_smbus_dev); amd_smbus_dev = NULL; @@ -262,6 +269,19 @@ static void amd_iso_dev_put(void) } +static void sb800_prefetch(struct ohci_hcd *ohci, int on) +{ + struct pci_dev *pdev; + u16 misc; + + pdev = to_pci_dev(ohci_to_hcd(ohci)->self.controller); + pci_read_config_word(pdev, 0x50, &misc); + if (on == 0) + pci_write_config_word(pdev, 0x50, misc & 0xfcff); + else + pci_write_config_word(pdev, 0x50, misc | 0x0300); +} + /* List of quirks for OHCI */ static const struct pci_device_id ohci_pci_quirks[] = { { diff --git a/drivers/usb/host/ohci-q.c b/drivers/usb/host/ohci-q.c index 16fecb8ecc39..35288bcae0db 100644 --- a/drivers/usb/host/ohci-q.c +++ b/drivers/usb/host/ohci-q.c @@ -49,9 +49,12 @@ __acquires(ohci->lock) switch (usb_pipetype (urb->pipe)) { case PIPE_ISOCHRONOUS: ohci_to_hcd(ohci)->self.bandwidth_isoc_reqs--; - if (ohci_to_hcd(ohci)->self.bandwidth_isoc_reqs == 0 - && quirk_amdiso(ohci)) - quirk_amd_pll(1); + if (ohci_to_hcd(ohci)->self.bandwidth_isoc_reqs == 0) { + if (quirk_amdiso(ohci)) + quirk_amd_pll(1); + if (quirk_amdprefetch(ohci)) + sb800_prefetch(ohci, 0); + } break; case PIPE_INTERRUPT: ohci_to_hcd(ohci)->self.bandwidth_int_reqs--; @@ -680,9 +683,12 @@ static void td_submit_urb ( data + urb->iso_frame_desc [cnt].offset, urb->iso_frame_desc [cnt].length, urb, cnt); } - if (ohci_to_hcd(ohci)->self.bandwidth_isoc_reqs == 0 - && quirk_amdiso(ohci)) - quirk_amd_pll(0); + if (ohci_to_hcd(ohci)->self.bandwidth_isoc_reqs == 0) { + if (quirk_amdiso(ohci)) + quirk_amd_pll(0); + if (quirk_amdprefetch(ohci)) + sb800_prefetch(ohci, 1); + } periodic = ohci_to_hcd(ohci)->self.bandwidth_isoc_reqs++ == 0 && ohci_to_hcd(ohci)->self.bandwidth_int_reqs == 0; break; diff --git a/drivers/usb/host/ohci.h b/drivers/usb/host/ohci.h index 222011f6172c..5bf15fed0d9f 100644 --- a/drivers/usb/host/ohci.h +++ b/drivers/usb/host/ohci.h @@ -402,6 +402,7 @@ struct ohci_hcd { #define OHCI_QUIRK_FRAME_NO 0x80 /* no big endian frame_no shift */ #define OHCI_QUIRK_HUB_POWER 0x100 /* distrust firmware power/oc setup */ #define OHCI_QUIRK_AMD_ISO 0x200 /* ISO transfers*/ +#define OHCI_QUIRK_AMD_PREFETCH 0x400 /* pre-fetch for ISO transfer */ // there are also chip quirks/bugs in init logic struct work_struct nec_work; /* Worker for NEC quirk */ @@ -433,6 +434,10 @@ static inline int quirk_amdiso(struct ohci_hcd *ohci) { return ohci->flags & OHCI_QUIRK_AMD_ISO; } +static inline int quirk_amdprefetch(struct ohci_hcd *ohci) +{ + return ohci->flags & OHCI_QUIRK_AMD_PREFETCH; +} #else static inline int quirk_nec(struct ohci_hcd *ohci) { @@ -446,6 +451,10 @@ static inline int quirk_amdiso(struct ohci_hcd *ohci) { return 0; } +static inline int quirk_amdprefetch(struct ohci_hcd *ohci) +{ + return 0; +} #endif /* convert between an hcd pointer and the corresponding ohci_hcd */ diff --git a/drivers/usb/host/pci-quirks.c b/drivers/usb/host/pci-quirks.c index 23cf3bde4762..83b5f9cea85a 100644 --- a/drivers/usb/host/pci-quirks.c +++ b/drivers/usb/host/pci-quirks.c @@ -475,4 +475,4 @@ static void __devinit quirk_usb_early_handoff(struct pci_dev *pdev) else if (pdev->class == PCI_CLASS_SERIAL_USB_XHCI) quirk_usb_handoff_xhci(pdev); } -DECLARE_PCI_FIXUP_HEADER(PCI_ANY_ID, PCI_ANY_ID, quirk_usb_early_handoff); +DECLARE_PCI_FIXUP_FINAL(PCI_ANY_ID, PCI_ANY_ID, quirk_usb_early_handoff); diff --git a/drivers/usb/host/r8a66597-hcd.c b/drivers/usb/host/r8a66597-hcd.c index 749b53742828..e33d36256350 100644 --- a/drivers/usb/host/r8a66597-hcd.c +++ b/drivers/usb/host/r8a66597-hcd.c @@ -1003,19 +1003,20 @@ static void r8a66597_check_syssts(struct r8a66597 *r8a66597, int port, if (syssts == SE0) { r8a66597_write(r8a66597, ~ATTCH, get_intsts_reg(port)); r8a66597_bset(r8a66597, ATTCHE, get_intenb_reg(port)); - return; - } + } else { + if (syssts == FS_JSTS) + r8a66597_bset(r8a66597, HSE, get_syscfg_reg(port)); + else if (syssts == LS_JSTS) + r8a66597_bclr(r8a66597, HSE, get_syscfg_reg(port)); - if (syssts == FS_JSTS) - r8a66597_bset(r8a66597, HSE, get_syscfg_reg(port)); - else if (syssts == LS_JSTS) - r8a66597_bclr(r8a66597, HSE, get_syscfg_reg(port)); + r8a66597_write(r8a66597, ~DTCH, get_intsts_reg(port)); + r8a66597_bset(r8a66597, DTCHE, get_intenb_reg(port)); - r8a66597_write(r8a66597, ~DTCH, get_intsts_reg(port)); - r8a66597_bset(r8a66597, DTCHE, get_intenb_reg(port)); + if (r8a66597->bus_suspended) + usb_hcd_resume_root_hub(r8a66597_to_hcd(r8a66597)); + } - if (r8a66597->bus_suspended) - usb_hcd_resume_root_hub(r8a66597_to_hcd(r8a66597)); + usb_hcd_poll_rh_status(r8a66597_to_hcd(r8a66597)); } /* this function must be called with interrupt disabled */ @@ -1024,6 +1025,8 @@ static void r8a66597_usb_connect(struct r8a66597 *r8a66597, int port) u16 speed = get_rh_usb_speed(r8a66597, port); struct r8a66597_root_hub *rh = &r8a66597->root_hub[port]; + rh->port &= ~((1 << USB_PORT_FEAT_HIGHSPEED) | + (1 << USB_PORT_FEAT_LOWSPEED)); if (speed == HSMODE) rh->port |= (1 << USB_PORT_FEAT_HIGHSPEED); else if (speed == LSMODE) diff --git a/drivers/usb/host/whci/asl.c b/drivers/usb/host/whci/asl.c index c632437c7649..562eba108816 100644 --- a/drivers/usb/host/whci/asl.c +++ b/drivers/usb/host/whci/asl.c @@ -115,6 +115,10 @@ static uint32_t process_qset(struct whc *whc, struct whc_qset *qset) if (status & QTD_STS_HALTED) { /* Ug, an error. */ process_halted_qtd(whc, qset, td); + /* A halted qTD always triggers an update + because the qset was either removed or + reactivated. */ + update |= WHC_UPDATE_UPDATED; goto done; } @@ -305,6 +309,7 @@ int asl_urb_dequeue(struct whc *whc, struct urb *urb, int status) struct whc_urb *wurb = urb->hcpriv; struct whc_qset *qset = wurb->qset; struct whc_std *std, *t; + bool has_qtd = false; int ret; unsigned long flags; @@ -315,17 +320,21 @@ int asl_urb_dequeue(struct whc *whc, struct urb *urb, int status) goto out; list_for_each_entry_safe(std, t, &qset->stds, list_node) { - if (std->urb == urb) + if (std->urb == urb) { + if (std->qtd) + has_qtd = true; qset_free_std(whc, std); - else + } else std->qtd = NULL; /* so this std is re-added when the qset is */ } - asl_qset_remove(whc, qset); - wurb->status = status; - wurb->is_async = true; - queue_work(whc->workqueue, &wurb->dequeue_work); - + if (has_qtd) { + asl_qset_remove(whc, qset); + wurb->status = status; + wurb->is_async = true; + queue_work(whc->workqueue, &wurb->dequeue_work); + } else + qset_remove_urb(whc, qset, urb, status); out: spin_unlock_irqrestore(&whc->lock, flags); diff --git a/drivers/usb/host/whci/pzl.c b/drivers/usb/host/whci/pzl.c index a9e05bac6646..0db3fb2dc03a 100644 --- a/drivers/usb/host/whci/pzl.c +++ b/drivers/usb/host/whci/pzl.c @@ -121,6 +121,10 @@ static enum whc_update pzl_process_qset(struct whc *whc, struct whc_qset *qset) if (status & QTD_STS_HALTED) { /* Ug, an error. */ process_halted_qtd(whc, qset, td); + /* A halted qTD always triggers an update + because the qset was either removed or + reactivated. */ + update |= WHC_UPDATE_UPDATED; goto done; } @@ -333,6 +337,7 @@ int pzl_urb_dequeue(struct whc *whc, struct urb *urb, int status) struct whc_urb *wurb = urb->hcpriv; struct whc_qset *qset = wurb->qset; struct whc_std *std, *t; + bool has_qtd = false; int ret; unsigned long flags; @@ -343,17 +348,22 @@ int pzl_urb_dequeue(struct whc *whc, struct urb *urb, int status) goto out; list_for_each_entry_safe(std, t, &qset->stds, list_node) { - if (std->urb == urb) + if (std->urb == urb) { + if (std->qtd) + has_qtd = true; qset_free_std(whc, std); - else + } else std->qtd = NULL; /* so this std is re-added when the qset is */ } - pzl_qset_remove(whc, qset); - wurb->status = status; - wurb->is_async = false; - queue_work(whc->workqueue, &wurb->dequeue_work); - + if (has_qtd) { + pzl_qset_remove(whc, qset); + update_pzl_hw_view(whc); + wurb->status = status; + wurb->is_async = false; + queue_work(whc->workqueue, &wurb->dequeue_work); + } else + qset_remove_urb(whc, qset, urb, status); out: spin_unlock_irqrestore(&whc->lock, flags); diff --git a/drivers/usb/host/xhci-hcd.c b/drivers/usb/host/xhci-hcd.c index 99911e727e0b..932f99938481 100644 --- a/drivers/usb/host/xhci-hcd.c +++ b/drivers/usb/host/xhci-hcd.c @@ -335,6 +335,12 @@ void xhci_event_ring_work(unsigned long arg) spin_lock_irqsave(&xhci->lock, flags); temp = xhci_readl(xhci, &xhci->op_regs->status); xhci_dbg(xhci, "op reg status = 0x%x\n", temp); + if (temp == 0xffffffff) { + xhci_dbg(xhci, "HW died, polling stopped.\n"); + spin_unlock_irqrestore(&xhci->lock, flags); + return; + } + temp = xhci_readl(xhci, &xhci->ir_set->irq_pending); xhci_dbg(xhci, "ir_set 0 pending = 0x%x\n", temp); xhci_dbg(xhci, "No-op commands handled = %d\n", xhci->noops_handled); @@ -776,6 +782,7 @@ int xhci_urb_dequeue(struct usb_hcd *hcd, struct urb *urb, int status) { unsigned long flags; int ret; + u32 temp; struct xhci_hcd *xhci; struct xhci_td *td; unsigned int ep_index; @@ -788,6 +795,17 @@ int xhci_urb_dequeue(struct usb_hcd *hcd, struct urb *urb, int status) ret = usb_hcd_check_unlink_urb(hcd, urb, status); if (ret || !urb->hcpriv) goto done; + temp = xhci_readl(xhci, &xhci->op_regs->status); + if (temp == 0xffffffff) { + xhci_dbg(xhci, "HW died, freeing TD.\n"); + td = (struct xhci_td *) urb->hcpriv; + + usb_hcd_unlink_urb_from_ep(hcd, urb); + spin_unlock_irqrestore(&xhci->lock, flags); + usb_hcd_giveback_urb(xhci_to_hcd(xhci), urb, -ESHUTDOWN); + kfree(td); + return ret; + } xhci_dbg(xhci, "Cancel URB %p\n", urb); xhci_dbg(xhci, "Event ring:\n"); @@ -877,7 +895,7 @@ int xhci_drop_endpoint(struct usb_hcd *hcd, struct usb_device *udev, ctrl_ctx->drop_flags |= drop_flag; new_drop_flags = ctrl_ctx->drop_flags; - ctrl_ctx->add_flags = ~drop_flag; + ctrl_ctx->add_flags &= ~drop_flag; new_add_flags = ctrl_ctx->add_flags; last_ctx = xhci_last_valid_endpoint(ctrl_ctx->add_flags); @@ -1410,11 +1428,20 @@ void xhci_free_dev(struct usb_hcd *hcd, struct usb_device *udev) { struct xhci_hcd *xhci = hcd_to_xhci(hcd); unsigned long flags; + u32 state; if (udev->slot_id == 0) return; spin_lock_irqsave(&xhci->lock, flags); + /* Don't disable the slot if the host controller is dead. */ + state = xhci_readl(xhci, &xhci->op_regs->status); + if (state == 0xffffffff) { + xhci_free_virt_device(xhci, udev->slot_id); + spin_unlock_irqrestore(&xhci->lock, flags); + return; + } + if (xhci_queue_slot_control(xhci, TRB_DISABLE_SLOT, udev->slot_id)) { spin_unlock_irqrestore(&xhci->lock, flags); xhci_dbg(xhci, "FIXME: allocate a command ring segment\n"); diff --git a/drivers/usb/host/xhci-mem.c b/drivers/usb/host/xhci-mem.c index 1db4fea8c170..b8fd270a8b0d 100644 --- a/drivers/usb/host/xhci-mem.c +++ b/drivers/usb/host/xhci-mem.c @@ -802,9 +802,11 @@ void xhci_mem_cleanup(struct xhci_hcd *xhci) int i; /* Free the Event Ring Segment Table and the actual Event Ring */ - xhci_writel(xhci, 0, &xhci->ir_set->erst_size); - xhci_write_64(xhci, 0, &xhci->ir_set->erst_base); - xhci_write_64(xhci, 0, &xhci->ir_set->erst_dequeue); + if (xhci->ir_set) { + xhci_writel(xhci, 0, &xhci->ir_set->erst_size); + xhci_write_64(xhci, 0, &xhci->ir_set->erst_base); + xhci_write_64(xhci, 0, &xhci->ir_set->erst_dequeue); + } size = sizeof(struct xhci_erst_entry)*(xhci->erst.num_entries); if (xhci->erst.entries) pci_free_consistent(pdev, size, @@ -841,9 +843,9 @@ void xhci_mem_cleanup(struct xhci_hcd *xhci) xhci->dcbaa, xhci->dcbaa->dma); xhci->dcbaa = NULL; + scratchpad_free(xhci); xhci->page_size = 0; xhci->page_shift = 0; - scratchpad_free(xhci); } int xhci_mem_init(struct xhci_hcd *xhci, gfp_t flags) diff --git a/drivers/usb/host/xhci-ring.c b/drivers/usb/host/xhci-ring.c index 173c39c76489..821b7b4709de 100644 --- a/drivers/usb/host/xhci-ring.c +++ b/drivers/usb/host/xhci-ring.c @@ -864,9 +864,11 @@ static struct xhci_segment *trb_in_td( cur_seg = start_seg; do { + if (start_dma == 0) + return 0; /* We may get an event for a Link TRB in the middle of a TD */ end_seg_dma = xhci_trb_virt_to_dma(cur_seg, - &start_seg->trbs[TRBS_PER_SEGMENT - 1]); + &cur_seg->trbs[TRBS_PER_SEGMENT - 1]); /* If the end TRB isn't in this segment, this is set to 0 */ end_trb_dma = xhci_trb_virt_to_dma(cur_seg, end_trb); @@ -893,8 +895,9 @@ static struct xhci_segment *trb_in_td( } cur_seg = cur_seg->next; start_dma = xhci_trb_virt_to_dma(cur_seg, &cur_seg->trbs[0]); - } while (1); + } while (cur_seg != start_seg); + return 0; } /* diff --git a/drivers/usb/misc/usblcd.c b/drivers/usb/misc/usblcd.c index 29092b8e59ce..4fb120357c55 100644 --- a/drivers/usb/misc/usblcd.c +++ b/drivers/usb/misc/usblcd.c @@ -313,7 +313,8 @@ static int lcd_probe(struct usb_interface *interface, const struct usb_device_id if (le16_to_cpu(dev->udev->descriptor.idProduct) != 0x0001) { dev_warn(&interface->dev, "USBLCD model not supported.\n"); - return -ENODEV; + retval = -ENODEV; + goto error; } /* set up the endpoint information */ diff --git a/drivers/usb/mon/mon_bin.c b/drivers/usb/mon/mon_bin.c index 9ed3e741bee1..10f3205798e8 100644 --- a/drivers/usb/mon/mon_bin.c +++ b/drivers/usb/mon/mon_bin.c @@ -348,12 +348,12 @@ static unsigned int mon_buff_area_alloc_contiguous(struct mon_reader_bin *rp, /* * Return a few (kilo-)bytes to the head of the buffer. - * This is used if a DMA fetch fails. + * This is used if a data fetch fails. */ static void mon_buff_area_shrink(struct mon_reader_bin *rp, unsigned int size) { - size = (size + PKT_ALIGN-1) & ~(PKT_ALIGN-1); + /* size &= ~(PKT_ALIGN-1); -- we're called with aligned size */ rp->b_cnt -= size; if (rp->b_in < size) rp->b_in += rp->b_size; @@ -433,6 +433,7 @@ static void mon_bin_event(struct mon_reader_bin *rp, struct urb *urb, unsigned int urb_length; unsigned int offset; unsigned int length; + unsigned int delta; unsigned int ndesc, lendesc; unsigned char dir; struct mon_bin_hdr *ep; @@ -537,8 +538,10 @@ static void mon_bin_event(struct mon_reader_bin *rp, struct urb *urb, if (length != 0) { ep->flag_data = mon_bin_get_data(rp, offset, urb, length); if (ep->flag_data != 0) { /* Yes, it's 0x00, not '0' */ - ep->len_cap = 0; - mon_buff_area_shrink(rp, length); + delta = (ep->len_cap + PKT_ALIGN-1) & ~(PKT_ALIGN-1); + ep->len_cap -= length; + delta -= (ep->len_cap + PKT_ALIGN-1) & ~(PKT_ALIGN-1); + mon_buff_area_shrink(rp, delta); } } else { ep->flag_data = data_tag; diff --git a/drivers/usb/musb/Kconfig b/drivers/usb/musb/Kconfig index 803adcb5ac1d..b84abd8ee8a5 100644 --- a/drivers/usb/musb/Kconfig +++ b/drivers/usb/musb/Kconfig @@ -8,8 +8,8 @@ comment "Enable Host or Gadget support to see Inventra options" # (M)HDRC = (Multipoint) Highspeed Dual-Role Controller config USB_MUSB_HDRC - depends on (USB || USB_GADGET) && HAVE_CLK - depends on !SUPERH + depends on (USB || USB_GADGET) + depends on (ARM || BLACKFIN) select NOP_USB_XCEIV if ARCH_DAVINCI select TWL4030_USB if MACH_OMAP_3430SDP select NOP_USB_XCEIV if MACH_OMAP3EVM diff --git a/drivers/usb/musb/blackfin.c b/drivers/usb/musb/blackfin.c index f2f66ebc7362..fcec87ea709e 100644 --- a/drivers/usb/musb/blackfin.c +++ b/drivers/usb/musb/blackfin.c @@ -14,7 +14,6 @@ #include <linux/slab.h> #include <linux/init.h> #include <linux/list.h> -#include <linux/clk.h> #include <linux/gpio.h> #include <linux/io.h> diff --git a/drivers/usb/musb/musb_core.h b/drivers/usb/musb/musb_core.h index 381d648a36b8..6aa5f22e5274 100644 --- a/drivers/usb/musb/musb_core.h +++ b/drivers/usb/musb/musb_core.h @@ -95,6 +95,13 @@ struct musb_ep; #endif #endif /* need MUSB gadget selection */ +#ifndef CONFIG_HAVE_CLK +/* Dummy stub for clk framework */ +#define clk_get(dev, id) NULL +#define clk_put(clock) do {} while (0) +#define clk_enable(clock) do {} while (0) +#define clk_disable(clock) do {} while (0) +#endif #ifdef CONFIG_PROC_FS #include <linux/fs.h> diff --git a/drivers/usb/musb/musb_regs.h b/drivers/usb/musb/musb_regs.h index fbfd3fd9ce1f..cc1d71b57d3c 100644 --- a/drivers/usb/musb/musb_regs.h +++ b/drivers/usb/musb/musb_regs.h @@ -439,15 +439,6 @@ static inline void musb_write_txhubport(void __iomem *mbase, u8 epnum, /* Not implemented - HW has seperate Tx/Rx FIFO */ #define MUSB_TXCSR_MODE 0x0000 -/* - * Dummy stub for clk framework, it will be removed - * until Blackfin supports clk framework - */ -#define clk_get(dev, id) NULL -#define clk_put(clock) do {} while (0) -#define clk_enable(clock) do {} while (0) -#define clk_disable(clock) do {} while (0) - static inline void musb_write_txfifosz(void __iomem *mbase, u8 c_size) { } diff --git a/drivers/usb/serial/aircable.c b/drivers/usb/serial/aircable.c index 2cbfab3716e5..b10ac8409411 100644 --- a/drivers/usb/serial/aircable.c +++ b/drivers/usb/serial/aircable.c @@ -554,13 +554,12 @@ static void aircable_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct aircable_private *priv = usb_get_serial_port_data(port); - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->rx_lock, flags); + spin_lock_irq(&priv->rx_lock); priv->rx_flags |= THROTTLED; - spin_unlock_irqrestore(&priv->rx_lock, flags); + spin_unlock_irq(&priv->rx_lock); } /* Based on ftdi_sio.c unthrottle */ @@ -569,14 +568,13 @@ static void aircable_unthrottle(struct tty_struct *tty) struct usb_serial_port *port = tty->driver_data; struct aircable_private *priv = usb_get_serial_port_data(port); int actually_throttled; - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->rx_lock, flags); + spin_lock_irq(&priv->rx_lock); actually_throttled = priv->rx_flags & ACTUALLY_THROTTLED; priv->rx_flags &= ~(THROTTLED | ACTUALLY_THROTTLED); - spin_unlock_irqrestore(&priv->rx_lock, flags); + spin_unlock_irq(&priv->rx_lock); if (actually_throttled) schedule_work(&priv->rx_work); diff --git a/drivers/usb/serial/cp210x.c b/drivers/usb/serial/cp210x.c index 4a208fe85bc9..bd254ec97d14 100644 --- a/drivers/usb/serial/cp210x.c +++ b/drivers/usb/serial/cp210x.c @@ -50,6 +50,8 @@ static int cp210x_tiocmset_port(struct usb_serial_port *port, struct file *, static void cp210x_break_ctl(struct tty_struct *, int); static int cp210x_startup(struct usb_serial *); static void cp210x_disconnect(struct usb_serial *); +static void cp210x_dtr_rts(struct usb_serial_port *p, int on); +static int cp210x_carrier_raised(struct usb_serial_port *p); static int debug; @@ -113,6 +115,7 @@ static struct usb_device_id id_table [] = { { USB_DEVICE(0x166A, 0x0303) }, /* Clipsal 5500PCU C-Bus USB interface */ { USB_DEVICE(0x16D6, 0x0001) }, /* Jablotron serial interface */ { USB_DEVICE(0x18EF, 0xE00F) }, /* ELV USB-I2C-Interface */ + { USB_DEVICE(0x413C, 0x9500) }, /* DW700 GPS USB interface */ { } /* Terminating Entry */ }; @@ -142,6 +145,8 @@ static struct usb_serial_driver cp210x_device = { .tiocmset = cp210x_tiocmset, .attach = cp210x_startup, .disconnect = cp210x_disconnect, + .dtr_rts = cp210x_dtr_rts, + .carrier_raised = cp210x_carrier_raised }; /* Config request types */ @@ -745,6 +750,14 @@ static int cp210x_tiocmset_port(struct usb_serial_port *port, struct file *file, return cp210x_set_config(port, CP210X_SET_MHS, &control, 2); } +static void cp210x_dtr_rts(struct usb_serial_port *p, int on) +{ + if (on) + cp210x_tiocmset_port(p, NULL, TIOCM_DTR|TIOCM_RTS, 0); + else + cp210x_tiocmset_port(p, NULL, 0, TIOCM_DTR|TIOCM_RTS); +} + static int cp210x_tiocmget (struct tty_struct *tty, struct file *file) { struct usb_serial_port *port = tty->driver_data; @@ -767,6 +780,15 @@ static int cp210x_tiocmget (struct tty_struct *tty, struct file *file) return result; } +static int cp210x_carrier_raised(struct usb_serial_port *p) +{ + unsigned int control; + cp210x_get_config(p, CP210X_GET_MDMSTS, &control, 1); + if (control & CONTROL_DCD) + return 1; + return 0; +} + static void cp210x_break_ctl (struct tty_struct *tty, int break_state) { struct usb_serial_port *port = tty->driver_data; diff --git a/drivers/usb/serial/cypress_m8.c b/drivers/usb/serial/cypress_m8.c index e0a8b715f2f2..a591ebec0f89 100644 --- a/drivers/usb/serial/cypress_m8.c +++ b/drivers/usb/serial/cypress_m8.c @@ -1155,13 +1155,12 @@ static void cypress_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct cypress_private *priv = usb_get_serial_port_data(port); - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); priv->rx_flags = THROTTLED; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); } @@ -1170,14 +1169,13 @@ static void cypress_unthrottle(struct tty_struct *tty) struct usb_serial_port *port = tty->driver_data; struct cypress_private *priv = usb_get_serial_port_data(port); int actually_throttled, result; - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); actually_throttled = priv->rx_flags & ACTUALLY_THROTTLED; priv->rx_flags = 0; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); if (!priv->comm_is_ok) return; @@ -1185,7 +1183,7 @@ static void cypress_unthrottle(struct tty_struct *tty) if (actually_throttled) { port->interrupt_in_urb->dev = port->serial->dev; - result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); + result = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL); if (result) { dev_err(&port->dev, "%s - failed submitting read urb, " "error %d\n", __func__, result); diff --git a/drivers/usb/serial/digi_acceleport.c b/drivers/usb/serial/digi_acceleport.c index ab3dd991586b..68e80be6b9e1 100644 --- a/drivers/usb/serial/digi_acceleport.c +++ b/drivers/usb/serial/digi_acceleport.c @@ -898,16 +898,16 @@ static void digi_rx_unthrottle(struct tty_struct *tty) spin_lock_irqsave(&priv->dp_port_lock, flags); - /* turn throttle off */ - priv->dp_throttled = 0; - priv->dp_throttle_restart = 0; - /* restart read chain */ if (priv->dp_throttle_restart) { port->read_urb->dev = port->serial->dev; ret = usb_submit_urb(port->read_urb, GFP_ATOMIC); } + /* turn throttle off */ + priv->dp_throttled = 0; + priv->dp_throttle_restart = 0; + spin_unlock_irqrestore(&priv->dp_port_lock, flags); if (ret) diff --git a/drivers/usb/serial/empeg.c b/drivers/usb/serial/empeg.c index 33c9e9cf9eb2..7dd0e3eadbe6 100644 --- a/drivers/usb/serial/empeg.c +++ b/drivers/usb/serial/empeg.c @@ -391,7 +391,7 @@ static void empeg_unthrottle(struct tty_struct *tty) dbg("%s - port %d", __func__, port->number); port->read_urb->dev = port->serial->dev; - result = usb_submit_urb(port->read_urb, GFP_ATOMIC); + result = usb_submit_urb(port->read_urb, GFP_KERNEL); if (result) dev_err(&port->dev, "%s - failed submitting read urb, error %d\n", diff --git a/drivers/usb/serial/ftdi_sio.c b/drivers/usb/serial/ftdi_sio.c index 4f883b1773d0..9c60d6d4908a 100644 --- a/drivers/usb/serial/ftdi_sio.c +++ b/drivers/usb/serial/ftdi_sio.c @@ -76,13 +76,7 @@ struct ftdi_private { unsigned long last_dtr_rts; /* saved modem control outputs */ wait_queue_head_t delta_msr_wait; /* Used for TIOCMIWAIT */ char prev_status, diff_status; /* Used for TIOCMIWAIT */ - __u8 rx_flags; /* receive state flags (throttling) */ - spinlock_t rx_lock; /* spinlock for receive state */ - struct delayed_work rx_work; struct usb_serial_port *port; - int rx_processed; - unsigned long rx_bytes; - __u16 interface; /* FT2232C, FT2232H or FT4232H port interface (0 for FT232/245) */ @@ -737,10 +731,6 @@ static const char *ftdi_chip_name[] = { /* Constants for read urb and write urb */ #define BUFSZ 512 -/* rx_flags */ -#define THROTTLED 0x01 -#define ACTUALLY_THROTTLED 0x02 - /* Used for TIOCMIWAIT */ #define FTDI_STATUS_B0_MASK (FTDI_RS0_CTS | FTDI_RS0_DSR | FTDI_RS0_RI | FTDI_RS0_RLSD) #define FTDI_STATUS_B1_MASK (FTDI_RS_BI) @@ -763,7 +753,7 @@ static int ftdi_write_room(struct tty_struct *tty); static int ftdi_chars_in_buffer(struct tty_struct *tty); static void ftdi_write_bulk_callback(struct urb *urb); static void ftdi_read_bulk_callback(struct urb *urb); -static void ftdi_process_read(struct work_struct *work); +static void ftdi_process_read(struct usb_serial_port *port); static void ftdi_set_termios(struct tty_struct *tty, struct usb_serial_port *port, struct ktermios *old); static int ftdi_tiocmget(struct tty_struct *tty, struct file *file); @@ -1234,7 +1224,6 @@ static int set_serial_info(struct tty_struct *tty, (new_serial.flags & ASYNC_FLAGS)); priv->custom_divisor = new_serial.custom_divisor; - tty->low_latency = (priv->flags & ASYNC_LOW_LATENCY) ? 1 : 0; write_latency_timer(port); check_and_exit: @@ -1527,7 +1516,6 @@ static int ftdi_sio_port_probe(struct usb_serial_port *port) } kref_init(&priv->kref); - spin_lock_init(&priv->rx_lock); spin_lock_init(&priv->tx_lock); init_waitqueue_head(&priv->delta_msr_wait); /* This will push the characters through immediately rather @@ -1549,7 +1537,6 @@ static int ftdi_sio_port_probe(struct usb_serial_port *port) port->read_urb->transfer_buffer_length = BUFSZ; } - INIT_DELAYED_WORK(&priv->rx_work, ftdi_process_read); priv->port = port; /* Free port's existing write urb and transfer buffer. */ @@ -1686,6 +1673,26 @@ static int ftdi_sio_port_remove(struct usb_serial_port *port) return 0; } +static int ftdi_submit_read_urb(struct usb_serial_port *port, gfp_t mem_flags) +{ + struct urb *urb = port->read_urb; + struct usb_serial *serial = port->serial; + int result; + + usb_fill_bulk_urb(urb, serial->dev, + usb_rcvbulkpipe(serial->dev, + port->bulk_in_endpointAddress), + urb->transfer_buffer, + urb->transfer_buffer_length, + ftdi_read_bulk_callback, port); + result = usb_submit_urb(urb, mem_flags); + if (result) + dev_err(&port->dev, + "%s - failed submitting read urb, error %d\n", + __func__, result); + return result; +} + static int ftdi_open(struct tty_struct *tty, struct usb_serial_port *port) { /* ftdi_open */ struct usb_device *dev = port->serial->dev; @@ -1700,12 +1707,6 @@ static int ftdi_open(struct tty_struct *tty, struct usb_serial_port *port) spin_lock_irqsave(&priv->tx_lock, flags); priv->tx_bytes = 0; spin_unlock_irqrestore(&priv->tx_lock, flags); - spin_lock_irqsave(&priv->rx_lock, flags); - priv->rx_bytes = 0; - spin_unlock_irqrestore(&priv->rx_lock, flags); - - if (tty) - tty->low_latency = (priv->flags & ASYNC_LOW_LATENCY) ? 1 : 0; write_latency_timer(port); @@ -1725,23 +1726,14 @@ static int ftdi_open(struct tty_struct *tty, struct usb_serial_port *port) ftdi_set_termios(tty, port, tty->termios); /* Not throttled */ - spin_lock_irqsave(&priv->rx_lock, flags); - priv->rx_flags &= ~(THROTTLED | ACTUALLY_THROTTLED); - spin_unlock_irqrestore(&priv->rx_lock, flags); + spin_lock_irqsave(&port->lock, flags); + port->throttled = 0; + port->throttle_req = 0; + spin_unlock_irqrestore(&port->lock, flags); /* Start reading from the device */ - priv->rx_processed = 0; - usb_fill_bulk_urb(port->read_urb, dev, - usb_rcvbulkpipe(dev, port->bulk_in_endpointAddress), - port->read_urb->transfer_buffer, - port->read_urb->transfer_buffer_length, - ftdi_read_bulk_callback, port); - result = usb_submit_urb(port->read_urb, GFP_KERNEL); - if (result) - dev_err(&port->dev, - "%s - failed submitting read urb, error %d\n", - __func__, result); - else + result = ftdi_submit_read_urb(port, GFP_KERNEL); + if (!result) kref_get(&priv->kref); return result; @@ -1787,10 +1779,6 @@ static void ftdi_close(struct usb_serial_port *port) dbg("%s", __func__); - - /* cancel any scheduled reading */ - cancel_delayed_work_sync(&priv->rx_work); - /* shutdown our bulk read */ usb_kill_urb(port->read_urb); kref_put(&priv->kref, ftdi_sio_priv_release); @@ -2013,271 +2001,121 @@ static int ftdi_chars_in_buffer(struct tty_struct *tty) return buffered; } -static void ftdi_read_bulk_callback(struct urb *urb) +static int ftdi_process_packet(struct tty_struct *tty, + struct usb_serial_port *port, struct ftdi_private *priv, + char *packet, int len) { - struct usb_serial_port *port = urb->context; - struct tty_struct *tty; - struct ftdi_private *priv; - unsigned long countread; - unsigned long flags; - int status = urb->status; - - if (urb->number_of_packets > 0) { - dev_err(&port->dev, "%s transfer_buffer_length %d " - "actual_length %d number of packets %d\n", __func__, - urb->transfer_buffer_length, - urb->actual_length, urb->number_of_packets); - dev_err(&port->dev, "%s transfer_flags %x\n", __func__, - urb->transfer_flags); - } + int i; + char status; + char flag; + char *ch; dbg("%s - port %d", __func__, port->number); - if (port->port.count <= 0) - return; - - tty = tty_port_tty_get(&port->port); - if (!tty) { - dbg("%s - bad tty pointer - exiting", __func__); - return; + if (len < 2) { + dbg("malformed packet"); + return 0; } - priv = usb_get_serial_port_data(port); - if (!priv) { - dbg("%s - bad port private data pointer - exiting", __func__); - goto out; + /* Compare new line status to the old one, signal if different/ + N.B. packet may be processed more than once, but differences + are only processed once. */ + status = packet[0] & FTDI_STATUS_B0_MASK; + if (status != priv->prev_status) { + priv->diff_status |= status ^ priv->prev_status; + wake_up_interruptible(&priv->delta_msr_wait); + priv->prev_status = status; } - if (urb != port->read_urb) - dev_err(&port->dev, "%s - Not my urb!\n", __func__); - - if (status) { - /* This will happen at close every time so it is a dbg not an - err */ - dbg("(this is ok on close) nonzero read bulk status received: %d", status); - goto out; + /* + * Although the device uses a bitmask and hence can have multiple + * errors on a packet - the order here sets the priority the error is + * returned to the tty layer. + */ + flag = TTY_NORMAL; + if (packet[1] & FTDI_RS_OE) { + flag = TTY_OVERRUN; + dbg("OVERRRUN error"); + } + if (packet[1] & FTDI_RS_BI) { + flag = TTY_BREAK; + dbg("BREAK received"); + usb_serial_handle_break(port); + } + if (packet[1] & FTDI_RS_PE) { + flag = TTY_PARITY; + dbg("PARITY error"); + } + if (packet[1] & FTDI_RS_FE) { + flag = TTY_FRAME; + dbg("FRAMING error"); } - /* count data bytes, but not status bytes */ - countread = urb->actual_length; - countread -= 2 * DIV_ROUND_UP(countread, priv->max_packet_size); - spin_lock_irqsave(&priv->rx_lock, flags); - priv->rx_bytes += countread; - spin_unlock_irqrestore(&priv->rx_lock, flags); - - ftdi_process_read(&priv->rx_work.work); -out: - tty_kref_put(tty); -} /* ftdi_read_bulk_callback */ - + len -= 2; + if (!len) + return 0; /* status only */ + ch = packet + 2; + + if (!(port->console && port->sysrq) && flag == TTY_NORMAL) + tty_insert_flip_string(tty, ch, len); + else { + for (i = 0; i < len; i++, ch++) { + if (!usb_serial_handle_sysrq_char(tty, port, *ch)) + tty_insert_flip_char(tty, *ch, flag); + } + } + return len; +} -static void ftdi_process_read(struct work_struct *work) -{ /* ftdi_process_read */ - struct ftdi_private *priv = - container_of(work, struct ftdi_private, rx_work.work); - struct usb_serial_port *port = priv->port; - struct urb *urb; +static void ftdi_process_read(struct usb_serial_port *port) +{ + struct urb *urb = port->read_urb; struct tty_struct *tty; - char error_flag; - unsigned char *data; - + struct ftdi_private *priv = usb_get_serial_port_data(port); + char *data = (char *)urb->transfer_buffer; int i; - int result; - int need_flip; - int packet_offset; - unsigned long flags; - - dbg("%s - port %d", __func__, port->number); - - if (port->port.count <= 0) - return; + int len; + int count = 0; tty = tty_port_tty_get(&port->port); - if (!tty) { - dbg("%s - bad tty pointer - exiting", __func__); + if (!tty) return; - } - - priv = usb_get_serial_port_data(port); - if (!priv) { - dbg("%s - bad port private data pointer - exiting", __func__); - goto out; - } - - urb = port->read_urb; - if (!urb) { - dbg("%s - bad read_urb pointer - exiting", __func__); - goto out; - } - - data = urb->transfer_buffer; - if (priv->rx_processed) { - dbg("%s - already processed: %d bytes, %d remain", __func__, - priv->rx_processed, - urb->actual_length - priv->rx_processed); - } else { - /* The first two bytes of every read packet are status */ - if (urb->actual_length > 2) - usb_serial_debug_data(debug, &port->dev, __func__, - urb->actual_length, data); - else - dbg("Status only: %03oo %03oo", data[0], data[1]); + for (i = 0; i < urb->actual_length; i += priv->max_packet_size) { + len = min_t(int, urb->actual_length - i, priv->max_packet_size); + count += ftdi_process_packet(tty, port, priv, &data[i], len); } - - /* TO DO -- check for hung up line and handle appropriately: */ - /* send hangup */ - /* See acm.c - you do a tty_hangup - eg tty_hangup(tty) */ - /* if CD is dropped and the line is not CLOCAL then we should hangup */ - - need_flip = 0; - for (packet_offset = priv->rx_processed; - packet_offset < urb->actual_length; packet_offset += priv->max_packet_size) { - int length; - - /* Compare new line status to the old one, signal if different/ - N.B. packet may be processed more than once, but differences - are only processed once. */ - char new_status = data[packet_offset + 0] & - FTDI_STATUS_B0_MASK; - if (new_status != priv->prev_status) { - priv->diff_status |= - new_status ^ priv->prev_status; - wake_up_interruptible(&priv->delta_msr_wait); - priv->prev_status = new_status; - } - - length = min_t(u32, priv->max_packet_size, urb->actual_length-packet_offset)-2; - if (length < 0) { - dev_err(&port->dev, "%s - bad packet length: %d\n", - __func__, length+2); - length = 0; - } - - if (priv->rx_flags & THROTTLED) { - dbg("%s - throttled", __func__); - break; - } - if (tty_buffer_request_room(tty, length) < length) { - /* break out & wait for throttling/unthrottling to - happen */ - dbg("%s - receive room low", __func__); - break; - } - - /* Handle errors and break */ - error_flag = TTY_NORMAL; - /* Although the device uses a bitmask and hence can have - multiple errors on a packet - the order here sets the - priority the error is returned to the tty layer */ - - if (data[packet_offset+1] & FTDI_RS_OE) { - error_flag = TTY_OVERRUN; - dbg("OVERRRUN error"); - } - if (data[packet_offset+1] & FTDI_RS_BI) { - error_flag = TTY_BREAK; - dbg("BREAK received"); - usb_serial_handle_break(port); - } - if (data[packet_offset+1] & FTDI_RS_PE) { - error_flag = TTY_PARITY; - dbg("PARITY error"); - } - if (data[packet_offset+1] & FTDI_RS_FE) { - error_flag = TTY_FRAME; - dbg("FRAMING error"); - } - if (length > 0) { - for (i = 2; i < length+2; i++) { - /* Note that the error flag is duplicated for - every character received since we don't know - which character it applied to */ - if (!usb_serial_handle_sysrq_char(tty, port, - data[packet_offset + i])) - tty_insert_flip_char(tty, - data[packet_offset + i], - error_flag); - } - need_flip = 1; - } - -#ifdef NOT_CORRECT_BUT_KEEPING_IT_FOR_NOW - /* if a parity error is detected you get status packets forever - until a character is sent without a parity error. - This doesn't work well since the application receives a - never ending stream of bad data - even though new data - hasn't been sent. Therefore I (bill) have taken this out. - However - this might make sense for framing errors and so on - so I am leaving the code in for now. - */ - else { - if (error_flag != TTY_NORMAL) { - dbg("error_flag is not normal"); - /* In this case it is just status - if that is - an error send a bad character */ - if (tty->flip.count >= TTY_FLIPBUF_SIZE) - tty_flip_buffer_push(tty); - tty_insert_flip_char(tty, 0xff, error_flag); - need_flip = 1; - } - } -#endif - } /* "for(packet_offset=0..." */ - - /* Low latency */ - if (need_flip) + if (count) tty_flip_buffer_push(tty); + tty_kref_put(tty); +} - if (packet_offset < urb->actual_length) { - /* not completely processed - record progress */ - priv->rx_processed = packet_offset; - dbg("%s - incomplete, %d bytes processed, %d remain", - __func__, packet_offset, - urb->actual_length - packet_offset); - /* check if we were throttled while processing */ - spin_lock_irqsave(&priv->rx_lock, flags); - if (priv->rx_flags & THROTTLED) { - priv->rx_flags |= ACTUALLY_THROTTLED; - spin_unlock_irqrestore(&priv->rx_lock, flags); - dbg("%s - deferring remainder until unthrottled", - __func__); - goto out; - } - spin_unlock_irqrestore(&priv->rx_lock, flags); - /* if the port is closed stop trying to read */ - if (port->port.count > 0) - /* delay processing of remainder */ - schedule_delayed_work(&priv->rx_work, 1); - else - dbg("%s - port is closed", __func__); - goto out; - } - - /* urb is completely processed */ - priv->rx_processed = 0; +static void ftdi_read_bulk_callback(struct urb *urb) +{ + struct usb_serial_port *port = urb->context; + unsigned long flags; - /* if the port is closed stop trying to read */ - if (port->port.count > 0) { - /* Continue trying to always read */ - usb_fill_bulk_urb(port->read_urb, port->serial->dev, - usb_rcvbulkpipe(port->serial->dev, - port->bulk_in_endpointAddress), - port->read_urb->transfer_buffer, - port->read_urb->transfer_buffer_length, - ftdi_read_bulk_callback, port); + dbg("%s - port %d", __func__, port->number); - result = usb_submit_urb(port->read_urb, GFP_ATOMIC); - if (result) - dev_err(&port->dev, - "%s - failed resubmitting read urb, error %d\n", - __func__, result); + if (urb->status) { + dbg("%s - nonzero read bulk status received: %d", + __func__, urb->status); + return; } -out: - tty_kref_put(tty); -} /* ftdi_process_read */ + usb_serial_debug_data(debug, &port->dev, __func__, + urb->actual_length, urb->transfer_buffer); + ftdi_process_read(port); + + spin_lock_irqsave(&port->lock, flags); + port->throttled = port->throttle_req; + if (!port->throttled) { + spin_unlock_irqrestore(&port->lock, flags); + ftdi_submit_read_urb(port, GFP_ATOMIC); + } else + spin_unlock_irqrestore(&port->lock, flags); +} static void ftdi_break_ctl(struct tty_struct *tty, int break_state) { @@ -2609,33 +2447,31 @@ static int ftdi_ioctl(struct tty_struct *tty, struct file *file, static void ftdi_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; - struct ftdi_private *priv = usb_get_serial_port_data(port); unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->rx_lock, flags); - priv->rx_flags |= THROTTLED; - spin_unlock_irqrestore(&priv->rx_lock, flags); + spin_lock_irqsave(&port->lock, flags); + port->throttle_req = 1; + spin_unlock_irqrestore(&port->lock, flags); } - -static void ftdi_unthrottle(struct tty_struct *tty) +void ftdi_unthrottle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; - struct ftdi_private *priv = usb_get_serial_port_data(port); - int actually_throttled; + int was_throttled; unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->rx_lock, flags); - actually_throttled = priv->rx_flags & ACTUALLY_THROTTLED; - priv->rx_flags &= ~(THROTTLED | ACTUALLY_THROTTLED); - spin_unlock_irqrestore(&priv->rx_lock, flags); + spin_lock_irqsave(&port->lock, flags); + was_throttled = port->throttled; + port->throttled = port->throttle_req = 0; + spin_unlock_irqrestore(&port->lock, flags); - if (actually_throttled) - schedule_delayed_work(&priv->rx_work, 0); + /* Resubmit urb if throttled and open. */ + if (was_throttled && test_bit(ASYNCB_INITIALIZED, &port->port.flags)) + ftdi_submit_read_urb(port, GFP_KERNEL); } static int __init ftdi_init(void) diff --git a/drivers/usb/serial/garmin_gps.c b/drivers/usb/serial/garmin_gps.c index 20432d345529..5ac900e5a50e 100644 --- a/drivers/usb/serial/garmin_gps.c +++ b/drivers/usb/serial/garmin_gps.c @@ -1390,14 +1390,13 @@ static void garmin_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct garmin_data *garmin_data_p = usb_get_serial_port_data(port); - unsigned long flags; dbg("%s - port %d", __func__, port->number); /* set flag, data received will be put into a queue for later processing */ - spin_lock_irqsave(&garmin_data_p->lock, flags); + spin_lock_irq(&garmin_data_p->lock); garmin_data_p->flags |= FLAGS_QUEUING|FLAGS_THROTTLED; - spin_unlock_irqrestore(&garmin_data_p->lock, flags); + spin_unlock_irq(&garmin_data_p->lock); } @@ -1405,13 +1404,12 @@ static void garmin_unthrottle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct garmin_data *garmin_data_p = usb_get_serial_port_data(port); - unsigned long flags; int status; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&garmin_data_p->lock, flags); + spin_lock_irq(&garmin_data_p->lock); garmin_data_p->flags &= ~FLAGS_THROTTLED; - spin_unlock_irqrestore(&garmin_data_p->lock, flags); + spin_unlock_irq(&garmin_data_p->lock); /* in native mode send queued data to tty, in serial mode nothing needs to be done here */ @@ -1419,7 +1417,7 @@ static void garmin_unthrottle(struct tty_struct *tty) garmin_flush_queue(garmin_data_p); if (0 != (garmin_data_p->flags & FLAGS_BULK_IN_ACTIVE)) { - status = usb_submit_urb(port->read_urb, GFP_ATOMIC); + status = usb_submit_urb(port->read_urb, GFP_KERNEL); if (status) dev_err(&port->dev, "%s - failed resubmitting read urb, error %d\n", diff --git a/drivers/usb/serial/generic.c b/drivers/usb/serial/generic.c index deba08c7a015..bbe005cefcfb 100644 --- a/drivers/usb/serial/generic.c +++ b/drivers/usb/serial/generic.c @@ -546,7 +546,7 @@ void usb_serial_generic_unthrottle(struct tty_struct *tty) if (was_throttled) { /* Resume reading from device */ - usb_serial_generic_resubmit_read_urb(port, GFP_KERNEL); + flush_and_resubmit_read_urb(port); } } diff --git a/drivers/usb/serial/ipaq.c b/drivers/usb/serial/ipaq.c index 24fcc64b837d..d6231c38813e 100644 --- a/drivers/usb/serial/ipaq.c +++ b/drivers/usb/serial/ipaq.c @@ -966,6 +966,15 @@ static int ipaq_calc_num_ports(struct usb_serial *serial) static int ipaq_startup(struct usb_serial *serial) { dbg("%s", __func__); + + /* Some of the devices in ipaq_id_table[] are composite, and we + * shouldn't bind to all the interfaces. This test will rule out + * some obviously invalid possibilities. + */ + if (serial->num_bulk_in < serial->num_ports || + serial->num_bulk_out < serial->num_ports) + return -ENODEV; + if (serial->dev->actconfig->desc.bConfigurationValue != 1) { /* * FIXME: HP iPaq rx3715, possibly others, have 1 config that diff --git a/drivers/usb/serial/keyspan_pda.c b/drivers/usb/serial/keyspan_pda.c index 257c16cc6b2a..1296a097f5c3 100644 --- a/drivers/usb/serial/keyspan_pda.c +++ b/drivers/usb/serial/keyspan_pda.c @@ -290,7 +290,7 @@ static void keyspan_pda_rx_unthrottle(struct tty_struct *tty) /* just restart the receive interrupt URB */ dbg("keyspan_pda_rx_unthrottle port %d", port->number); port->interrupt_in_urb->dev = port->serial->dev; - if (usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC)) + if (usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL)) dbg(" usb_submit_urb(read urb) failed"); return; } diff --git a/drivers/usb/serial/kl5kusb105.c b/drivers/usb/serial/kl5kusb105.c index f7373371b137..3a7873806f46 100644 --- a/drivers/usb/serial/kl5kusb105.c +++ b/drivers/usb/serial/kl5kusb105.c @@ -951,7 +951,7 @@ static void klsi_105_unthrottle(struct tty_struct *tty) dbg("%s - port %d", __func__, port->number); port->read_urb->dev = port->serial->dev; - result = usb_submit_urb(port->read_urb, GFP_ATOMIC); + result = usb_submit_urb(port->read_urb, GFP_KERNEL); if (result) dev_err(&port->dev, "%s - failed submitting read urb, error %d\n", diff --git a/drivers/usb/serial/mct_u232.c b/drivers/usb/serial/mct_u232.c index ad4998bbf16f..cd009cb280a5 100644 --- a/drivers/usb/serial/mct_u232.c +++ b/drivers/usb/serial/mct_u232.c @@ -777,20 +777,19 @@ static void mct_u232_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct mct_u232_private *priv = usb_get_serial_port_data(port); - unsigned long flags; unsigned int control_state; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); priv->rx_flags |= THROTTLED; if (C_CRTSCTS(tty)) { priv->control_state &= ~TIOCM_RTS; control_state = priv->control_state; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); (void) mct_u232_set_modem_ctrl(port->serial, control_state); } else { - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); } } @@ -799,20 +798,19 @@ static void mct_u232_unthrottle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct mct_u232_private *priv = usb_get_serial_port_data(port); - unsigned long flags; unsigned int control_state; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); if ((priv->rx_flags & THROTTLED) && C_CRTSCTS(tty)) { priv->rx_flags &= ~THROTTLED; priv->control_state |= TIOCM_RTS; control_state = priv->control_state; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); (void) mct_u232_set_modem_ctrl(port->serial, control_state); } else { - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); } } diff --git a/drivers/usb/serial/opticon.c b/drivers/usb/serial/opticon.c index 1085a577c5c1..80f59b6350cb 100644 --- a/drivers/usb/serial/opticon.c +++ b/drivers/usb/serial/opticon.c @@ -314,21 +314,24 @@ static void opticon_unthrottle(struct tty_struct *tty) struct usb_serial_port *port = tty->driver_data; struct opticon_private *priv = usb_get_serial_data(port->serial); unsigned long flags; - int result; + int result, was_throttled; dbg("%s - port %d", __func__, port->number); spin_lock_irqsave(&priv->lock, flags); priv->throttled = false; + was_throttled = priv->actually_throttled; priv->actually_throttled = false; spin_unlock_irqrestore(&priv->lock, flags); priv->bulk_read_urb->dev = port->serial->dev; - result = usb_submit_urb(priv->bulk_read_urb, GFP_ATOMIC); - if (result) - dev_err(&port->dev, - "%s - failed submitting read urb, error %d\n", + if (was_throttled) { + result = usb_submit_urb(priv->bulk_read_urb, GFP_ATOMIC); + if (result) + dev_err(&port->dev, + "%s - failed submitting read urb, error %d\n", __func__, result); + } } static int opticon_tiocmget(struct tty_struct *tty, struct file *file) diff --git a/drivers/usb/serial/option.c b/drivers/usb/serial/option.c index f66e39883218..319aaf9725b3 100644 --- a/drivers/usb/serial/option.c +++ b/drivers/usb/serial/option.c @@ -165,6 +165,7 @@ static int option_resume(struct usb_serial *serial); #define HUAWEI_PRODUCT_E143D 0x143D #define HUAWEI_PRODUCT_E143E 0x143E #define HUAWEI_PRODUCT_E143F 0x143F +#define HUAWEI_PRODUCT_E14AC 0x14AC #define QUANTA_VENDOR_ID 0x0408 #define QUANTA_PRODUCT_Q101 0xEA02 @@ -307,6 +308,7 @@ static int option_resume(struct usb_serial *serial); #define DLINK_VENDOR_ID 0x1186 #define DLINK_PRODUCT_DWM_652 0x3e04 +#define DLINK_PRODUCT_DWM_652_U5 0xce16 #define QISDA_VENDOR_ID 0x1da5 #define QISDA_PRODUCT_H21_4512 0x4512 @@ -314,10 +316,14 @@ static int option_resume(struct usb_serial *serial); #define QISDA_PRODUCT_H20_4515 0x4515 #define QISDA_PRODUCT_H20_4519 0x4519 +/* TLAYTECH PRODUCTS */ +#define TLAYTECH_VENDOR_ID 0x20B9 +#define TLAYTECH_PRODUCT_TEU800 0x1682 /* TOSHIBA PRODUCTS */ #define TOSHIBA_VENDOR_ID 0x0930 #define TOSHIBA_PRODUCT_HSDPA_MINICARD 0x1302 +#define TOSHIBA_PRODUCT_G450 0x0d45 #define ALINK_VENDOR_ID 0x1e0e #define ALINK_PRODUCT_3GU 0x9200 @@ -326,6 +332,9 @@ static int option_resume(struct usb_serial *serial); #define ALCATEL_VENDOR_ID 0x1bbb #define ALCATEL_PRODUCT_X060S 0x0000 +/* Airplus products */ +#define AIRPLUS_VENDOR_ID 0x1011 +#define AIRPLUS_PRODUCT_MCD650 0x3198 static struct usb_device_id option_ids[] = { { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_COLT) }, @@ -424,6 +433,7 @@ static struct usb_device_id option_ids[] = { { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E143D, 0xff, 0xff, 0xff) }, { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E143E, 0xff, 0xff, 0xff) }, { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E143F, 0xff, 0xff, 0xff) }, + { USB_DEVICE(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E14AC) }, { USB_DEVICE(AMOI_VENDOR_ID, AMOI_PRODUCT_9508) }, { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, NOVATELWIRELESS_PRODUCT_V640) }, /* Novatel Merlin V640/XV620 */ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, NOVATELWIRELESS_PRODUCT_V620) }, /* Novatel Merlin V620/S620 */ @@ -577,14 +587,18 @@ static struct usb_device_id option_ids[] = { { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, ZTE_PRODUCT_AC2726, 0xff, 0xff, 0xff) }, { USB_DEVICE(BENQ_VENDOR_ID, BENQ_PRODUCT_H10) }, { USB_DEVICE(DLINK_VENDOR_ID, DLINK_PRODUCT_DWM_652) }, + { USB_DEVICE(ALINK_VENDOR_ID, DLINK_PRODUCT_DWM_652_U5) }, /* Yes, ALINK_VENDOR_ID */ { USB_DEVICE(QISDA_VENDOR_ID, QISDA_PRODUCT_H21_4512) }, { USB_DEVICE(QISDA_VENDOR_ID, QISDA_PRODUCT_H21_4523) }, { USB_DEVICE(QISDA_VENDOR_ID, QISDA_PRODUCT_H20_4515) }, { USB_DEVICE(QISDA_VENDOR_ID, QISDA_PRODUCT_H20_4519) }, + { USB_DEVICE(TOSHIBA_VENDOR_ID, TOSHIBA_PRODUCT_G450) }, { USB_DEVICE(TOSHIBA_VENDOR_ID, TOSHIBA_PRODUCT_HSDPA_MINICARD ) }, /* Toshiba 3G HSDPA == Novatel Expedite EU870D MiniCard */ { USB_DEVICE(ALINK_VENDOR_ID, 0x9000) }, { USB_DEVICE_AND_INTERFACE_INFO(ALINK_VENDOR_ID, ALINK_PRODUCT_3GU, 0xff, 0xff, 0xff) }, { USB_DEVICE(ALCATEL_VENDOR_ID, ALCATEL_PRODUCT_X060S) }, + { USB_DEVICE(AIRPLUS_VENDOR_ID, AIRPLUS_PRODUCT_MCD650) }, + { USB_DEVICE(TLAYTECH_VENDOR_ID, TLAYTECH_PRODUCT_TEU800) }, { } /* Terminating entry */ }; MODULE_DEVICE_TABLE(usb, option_ids); diff --git a/drivers/usb/serial/oti6858.c b/drivers/usb/serial/oti6858.c index 0f4a70ce3823..c644e26394b4 100644 --- a/drivers/usb/serial/oti6858.c +++ b/drivers/usb/serial/oti6858.c @@ -288,7 +288,7 @@ static void setup_line(struct work_struct *work) dbg("%s(): submitting interrupt urb", __func__); port->interrupt_in_urb->dev = port->serial->dev; - result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); + result = usb_submit_urb(port->interrupt_in_urb, GFP_KERNEL); if (result != 0) { dev_err(&port->dev, "%s(): usb_submit_urb() failed" " with error %d\n", __func__, result); @@ -335,7 +335,7 @@ void send_data(struct work_struct *work) dbg("%s(): submitting interrupt urb", __func__); port->interrupt_in_urb->dev = port->serial->dev; - result = usb_submit_urb(port->interrupt_in_urb, GFP_ATOMIC); + result = usb_submit_urb(port->interrupt_in_urb, GFP_NOIO); if (result != 0) { dev_err(&port->dev, "%s(): usb_submit_urb() failed" " with error %d\n", __func__, result); @@ -349,7 +349,7 @@ void send_data(struct work_struct *work) port->write_urb->transfer_buffer_length = count; port->write_urb->dev = port->serial->dev; - result = usb_submit_urb(port->write_urb, GFP_ATOMIC); + result = usb_submit_urb(port->write_urb, GFP_NOIO); if (result != 0) { dev_err(&port->dev, "%s(): usb_submit_urb() failed" " with error %d\n", __func__, result); diff --git a/drivers/usb/serial/pl2303.c b/drivers/usb/serial/pl2303.c index 1128e01525b1..9ec1a49e2362 100644 --- a/drivers/usb/serial/pl2303.c +++ b/drivers/usb/serial/pl2303.c @@ -1046,13 +1046,15 @@ static void pl2303_push_data(struct tty_struct *tty, /* overrun is special, not associated with a char */ if (line_status & UART_OVERRUN_ERROR) tty_insert_flip_char(tty, 0, TTY_OVERRUN); - if (port->console && port->sysrq) { + + if (tty_flag == TTY_NORMAL && !(port->console && port->sysrq)) + tty_insert_flip_string(tty, data, urb->actual_length); + else { int i; for (i = 0; i < urb->actual_length; ++i) if (!usb_serial_handle_sysrq_char(tty, port, data[i])) tty_insert_flip_char(tty, data[i], tty_flag); - } else - tty_insert_flip_string(tty, data, urb->actual_length); + } tty_flip_buffer_push(tty); } diff --git a/drivers/usb/serial/sierra.c b/drivers/usb/serial/sierra.c index 8c075b2416bb..5019325ba25d 100644 --- a/drivers/usb/serial/sierra.c +++ b/drivers/usb/serial/sierra.c @@ -17,7 +17,7 @@ Whom based his on the Keyspan driver by Hugh Blemings <hugh@blemings.org> */ -#define DRIVER_VERSION "v.1.3.7" +#define DRIVER_VERSION "v.1.3.8" #define DRIVER_AUTHOR "Kevin Lloyd, Elina Pasheva, Matthew Safar, Rory Filer" #define DRIVER_DESC "USB Driver for Sierra Wireless USB modems" @@ -296,7 +296,6 @@ struct sierra_port_private { int dsr_state; int dcd_state; int ri_state; - unsigned int opened:1; }; @@ -306,6 +305,8 @@ static int sierra_send_setup(struct usb_serial_port *port) struct sierra_port_private *portdata; __u16 interface = 0; int val = 0; + int do_send = 0; + int retval; dev_dbg(&port->dev, "%s\n", __func__); @@ -324,10 +325,7 @@ static int sierra_send_setup(struct usb_serial_port *port) */ if (port->interrupt_in_urb) { /* send control message */ - return usb_control_msg(serial->dev, - usb_rcvctrlpipe(serial->dev, 0), - 0x22, 0x21, val, interface, - NULL, 0, USB_CTRL_SET_TIMEOUT); + do_send = 1; } } @@ -339,12 +337,18 @@ static int sierra_send_setup(struct usb_serial_port *port) interface = 1; else if (port->bulk_out_endpointAddress == 5) interface = 2; - return usb_control_msg(serial->dev, - usb_rcvctrlpipe(serial->dev, 0), - 0x22, 0x21, val, interface, - NULL, 0, USB_CTRL_SET_TIMEOUT); + + do_send = 1; } - return 0; + if (!do_send) + return 0; + + usb_autopm_get_interface(serial->interface); + retval = usb_control_msg(serial->dev, usb_rcvctrlpipe(serial->dev, 0), + 0x22, 0x21, val, interface, NULL, 0, USB_CTRL_SET_TIMEOUT); + usb_autopm_put_interface(serial->interface); + + return retval; } static void sierra_set_termios(struct tty_struct *tty, @@ -773,8 +777,11 @@ static void sierra_close(struct usb_serial_port *port) if (serial->dev) { mutex_lock(&serial->disc_mutex); - if (!serial->disconnected) + if (!serial->disconnected) { + serial->interface->needs_remote_wakeup = 0; + usb_autopm_get_interface(serial->interface); sierra_send_setup(port); + } mutex_unlock(&serial->disc_mutex); spin_lock_irq(&intfdata->susp_lock); portdata->opened = 0; @@ -788,8 +795,6 @@ static void sierra_close(struct usb_serial_port *port) sierra_release_urb(portdata->in_urbs[i]); portdata->in_urbs[i] = NULL; } - usb_autopm_get_interface(serial->interface); - serial->interface->needs_remote_wakeup = 0; } } @@ -827,6 +832,8 @@ static int sierra_open(struct tty_struct *tty, struct usb_serial_port *port) if (err) { /* get rid of everything as in close */ sierra_close(port); + /* restore balance for autopm */ + usb_autopm_put_interface(serial->interface); return err; } sierra_send_setup(port); @@ -915,7 +922,7 @@ static void sierra_release(struct usb_serial *serial) #ifdef CONFIG_PM static void stop_read_write_urbs(struct usb_serial *serial) { - int i, j; + int i; struct usb_serial_port *port; struct sierra_port_private *portdata; @@ -923,8 +930,7 @@ static void stop_read_write_urbs(struct usb_serial *serial) for (i = 0; i < serial->num_ports; ++i) { port = serial->port[i]; portdata = usb_get_serial_port_data(port); - for (j = 0; j < N_IN_URB; j++) - usb_kill_urb(portdata->in_urbs[j]); + sierra_stop_rx_urbs(port); usb_kill_anchored_urbs(&portdata->active); } } diff --git a/drivers/usb/serial/symbolserial.c b/drivers/usb/serial/symbolserial.c index cb7e95f9fcbf..b282c0f2d8e5 100644 --- a/drivers/usb/serial/symbolserial.c +++ b/drivers/usb/serial/symbolserial.c @@ -165,34 +165,36 @@ static void symbol_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct symbol_private *priv = usb_get_serial_data(port->serial); - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); priv->throttled = true; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); } static void symbol_unthrottle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct symbol_private *priv = usb_get_serial_data(port->serial); - unsigned long flags; int result; + bool was_throttled; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); priv->throttled = false; + was_throttled = priv->actually_throttled; priv->actually_throttled = false; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); priv->int_urb->dev = port->serial->dev; - result = usb_submit_urb(priv->int_urb, GFP_ATOMIC); - if (result) - dev_err(&port->dev, - "%s - failed submitting read urb, error %d\n", + if (was_throttled) { + result = usb_submit_urb(priv->int_urb, GFP_KERNEL); + if (result) + dev_err(&port->dev, + "%s - failed submitting read urb, error %d\n", __func__, result); + } } static int symbol_startup(struct usb_serial *serial) diff --git a/drivers/usb/serial/usb-serial.c b/drivers/usb/serial/usb-serial.c index aa6b2ae951ae..bd3fa7ff15b1 100644 --- a/drivers/usb/serial/usb-serial.c +++ b/drivers/usb/serial/usb-serial.c @@ -156,7 +156,8 @@ static void destroy_serial(struct kref *kref) if (serial->minor != SERIAL_TTY_NO_MINOR) return_serial(serial); - serial->type->release(serial); + if (serial->attached) + serial->type->release(serial); /* Now that nothing is using the ports, they can be freed */ for (i = 0; i < serial->num_port_pointers; ++i) { @@ -1059,12 +1060,15 @@ int usb_serial_probe(struct usb_interface *interface, module_put(type->driver.owner); if (retval < 0) goto probe_error; + serial->attached = 1; if (retval > 0) { /* quietly accept this device, but don't bind to a serial port as it's about to disappear */ serial->num_ports = 0; goto exit; } + } else { + serial->attached = 1; } if (get_free_serial(serial, num_ports, &minor) == NULL) { @@ -1164,8 +1168,10 @@ int usb_serial_suspend(struct usb_interface *intf, pm_message_t message) if (serial->type->suspend) { r = serial->type->suspend(serial, message); - if (r < 0) + if (r < 0) { + serial->suspending = 0; goto err_out; + } } for (i = 0; i < serial->num_ports; ++i) { diff --git a/drivers/usb/serial/visor.c b/drivers/usb/serial/visor.c index 1aa5d20a5d99..ad1f9232292d 100644 --- a/drivers/usb/serial/visor.c +++ b/drivers/usb/serial/visor.c @@ -513,7 +513,8 @@ static void visor_read_bulk_callback(struct urb *urb) tty_kref_put(tty); } spin_lock(&priv->lock); - priv->bytes_in += available_room; + if (tty) + priv->bytes_in += available_room; } else { spin_lock(&priv->lock); @@ -582,12 +583,11 @@ static void visor_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct visor_private *priv = usb_get_serial_port_data(port); - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); priv->throttled = 1; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); } @@ -595,21 +595,23 @@ static void visor_unthrottle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct visor_private *priv = usb_get_serial_port_data(port); - unsigned long flags; - int result; + int result, was_throttled; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&priv->lock, flags); + spin_lock_irq(&priv->lock); priv->throttled = 0; + was_throttled = priv->actually_throttled; priv->actually_throttled = 0; - spin_unlock_irqrestore(&priv->lock, flags); + spin_unlock_irq(&priv->lock); - port->read_urb->dev = port->serial->dev; - result = usb_submit_urb(port->read_urb, GFP_ATOMIC); - if (result) - dev_err(&port->dev, - "%s - failed submitting read urb, error %d\n", + if (was_throttled) { + port->read_urb->dev = port->serial->dev; + result = usb_submit_urb(port->read_urb, GFP_KERNEL); + if (result) + dev_err(&port->dev, + "%s - failed submitting read urb, error %d\n", __func__, result); + } } static int palm_os_3_probe(struct usb_serial *serial, diff --git a/drivers/usb/serial/whiteheat.c b/drivers/usb/serial/whiteheat.c index 62424eec33ec..1093d2eb046a 100644 --- a/drivers/usb/serial/whiteheat.c +++ b/drivers/usb/serial/whiteheat.c @@ -949,13 +949,12 @@ static void whiteheat_throttle(struct tty_struct *tty) { struct usb_serial_port *port = tty->driver_data; struct whiteheat_private *info = usb_get_serial_port_data(port); - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&info->lock, flags); + spin_lock_irq(&info->lock); info->flags |= THROTTLED; - spin_unlock_irqrestore(&info->lock, flags); + spin_unlock_irq(&info->lock); return; } @@ -966,14 +965,13 @@ static void whiteheat_unthrottle(struct tty_struct *tty) struct usb_serial_port *port = tty->driver_data; struct whiteheat_private *info = usb_get_serial_port_data(port); int actually_throttled; - unsigned long flags; dbg("%s - port %d", __func__, port->number); - spin_lock_irqsave(&info->lock, flags); + spin_lock_irq(&info->lock); actually_throttled = info->flags & ACTUALLY_THROTTLED; info->flags &= ~(THROTTLED | ACTUALLY_THROTTLED); - spin_unlock_irqrestore(&info->lock, flags); + spin_unlock_irq(&info->lock); if (actually_throttled) rx_data_softint(&info->rx_work); diff --git a/drivers/usb/storage/transport.c b/drivers/usb/storage/transport.c index e20dc525d177..589f6b4404f0 100644 --- a/drivers/usb/storage/transport.c +++ b/drivers/usb/storage/transport.c @@ -696,7 +696,7 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) /* device supports and needs bigger sense buffer */ if (us->fflags & US_FL_SANE_SENSE) sense_size = ~0; - +Retry_Sense: US_DEBUGP("Issuing auto-REQUEST_SENSE\n"); scsi_eh_prep_cmnd(srb, &ses, NULL, 0, sense_size); @@ -720,6 +720,21 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) srb->result = DID_ABORT << 16; goto Handle_Errors; } + + /* Some devices claim to support larger sense but fail when + * trying to request it. When a transport failure happens + * using US_FS_SANE_SENSE, we always retry with a standard + * (small) sense request. This fixes some USB GSM modems + */ + if (temp_result == USB_STOR_TRANSPORT_FAILED && + (us->fflags & US_FL_SANE_SENSE) && + sense_size != US_SENSE_SIZE) { + US_DEBUGP("-- auto-sense failure, retry small sense\n"); + sense_size = US_SENSE_SIZE; + goto Retry_Sense; + } + + /* Other failures */ if (temp_result != USB_STOR_TRANSPORT_GOOD) { US_DEBUGP("-- auto-sense failure\n"); @@ -768,17 +783,32 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) /* set the result so the higher layers expect this data */ srb->result = SAM_STAT_CHECK_CONDITION; - /* If things are really okay, then let's show that. Zero - * out the sense buffer so the higher layers won't realize - * we did an unsolicited auto-sense. */ - if (result == USB_STOR_TRANSPORT_GOOD && - /* Filemark 0, ignore EOM, ILI 0, no sense */ + /* We often get empty sense data. This could indicate that + * everything worked or that there was an unspecified + * problem. We have to decide which. + */ + if ( /* Filemark 0, ignore EOM, ILI 0, no sense */ (srb->sense_buffer[2] & 0xaf) == 0 && /* No ASC or ASCQ */ srb->sense_buffer[12] == 0 && srb->sense_buffer[13] == 0) { - srb->result = SAM_STAT_GOOD; - srb->sense_buffer[0] = 0x0; + + /* If things are really okay, then let's show that. + * Zero out the sense buffer so the higher layers + * won't realize we did an unsolicited auto-sense. + */ + if (result == USB_STOR_TRANSPORT_GOOD) { + srb->result = SAM_STAT_GOOD; + srb->sense_buffer[0] = 0x0; + + /* If there was a problem, report an unspecified + * hardware error to prevent the higher layers from + * entering an infinite retry loop. + */ + } else { + srb->result = DID_ERROR << 16; + srb->sense_buffer[2] = HARDWARE_ERROR; + } } } diff --git a/drivers/usb/storage/unusual_devs.h b/drivers/usb/storage/unusual_devs.h index 079ae0f7bec1..d4f034ebaa8a 100644 --- a/drivers/usb/storage/unusual_devs.h +++ b/drivers/usb/storage/unusual_devs.h @@ -1823,6 +1823,13 @@ UNUSUAL_DEV( 0x4102, 0x1020, 0x0100, 0x0100, US_SC_DEVICE, US_PR_DEVICE, NULL, US_FL_IGNORE_RESIDUE ), +/* Reported by Sergey Pinaev <dfo@antex.ru> */ +UNUSUAL_DEV( 0x4102, 0x1059, 0x0000, 0x0000, + "iRiver", + "P7K", + US_SC_DEVICE, US_PR_DEVICE, NULL, + US_FL_MAX_SECTORS_64 ), + /* * David Härdeman <david@2gen.com> * The key makes the SCSI stack print confusing (but harmless) messages diff --git a/drivers/usb/wusbcore/security.c b/drivers/usb/wusbcore/security.c index b2f149fedcc5..4516c36436e6 100644 --- a/drivers/usb/wusbcore/security.c +++ b/drivers/usb/wusbcore/security.c @@ -200,35 +200,40 @@ int wusb_dev_sec_add(struct wusbhc *wusbhc, { int result, bytes, secd_size; struct device *dev = &usb_dev->dev; - struct usb_security_descriptor secd; + struct usb_security_descriptor *secd; const struct usb_encryption_descriptor *etd, *ccm1_etd = NULL; - void *secd_buf; const void *itr, *top; char buf[64]; + secd = kmalloc(sizeof(struct usb_security_descriptor), GFP_KERNEL); + if (secd == NULL) { + result = -ENOMEM; + goto out; + } + result = usb_get_descriptor(usb_dev, USB_DT_SECURITY, - 0, &secd, sizeof(secd)); + 0, secd, sizeof(struct usb_security_descriptor)); if (result < sizeof(secd)) { dev_err(dev, "Can't read security descriptor or " "not enough data: %d\n", result); - goto error_secd; + goto out; } - secd_size = le16_to_cpu(secd.wTotalLength); - secd_buf = kmalloc(secd_size, GFP_KERNEL); - if (secd_buf == NULL) { + secd_size = le16_to_cpu(secd->wTotalLength); + secd = krealloc(secd, secd_size, GFP_KERNEL); + if (secd == NULL) { dev_err(dev, "Can't allocate space for security descriptors\n"); - goto error_secd_alloc; + goto out; } result = usb_get_descriptor(usb_dev, USB_DT_SECURITY, - 0, secd_buf, secd_size); + 0, secd, secd_size); if (result < secd_size) { dev_err(dev, "Can't read security descriptor or " "not enough data: %d\n", result); - goto error_secd_all; + goto out; } bytes = 0; - itr = secd_buf + sizeof(secd); - top = secd_buf + result; + itr = &secd[1]; + top = (void *)secd + result; while (itr < top) { etd = itr; if (top - itr < sizeof(*etd)) { @@ -259,24 +264,16 @@ int wusb_dev_sec_add(struct wusbhc *wusbhc, dev_err(dev, "WUSB device doesn't support CCM1 encryption, " "can't use!\n"); result = -EINVAL; - goto error_no_ccm1; + goto out; } wusb_dev->ccm1_etd = *ccm1_etd; dev_dbg(dev, "supported encryption: %s; using %s (0x%02x/%02x)\n", buf, wusb_et_name(ccm1_etd->bEncryptionType), ccm1_etd->bEncryptionValue, ccm1_etd->bAuthKeyIndex); result = 0; - kfree(secd_buf); out: + kfree(secd); return result; - - -error_no_ccm1: -error_secd_all: - kfree(secd_buf); -error_secd_alloc: -error_secd: - goto out; } void wusb_dev_sec_rm(struct wusb_dev *wusb_dev) diff --git a/drivers/uwb/whc-rc.c b/drivers/uwb/whc-rc.c index 1d9a6f54658e..01950c62dc8d 100644 --- a/drivers/uwb/whc-rc.c +++ b/drivers/uwb/whc-rc.c @@ -42,6 +42,7 @@ #include <linux/init.h> #include <linux/module.h> #include <linux/pci.h> +#include <linux/sched.h> #include <linux/dma-mapping.h> #include <linux/interrupt.h> #include <linux/workqueue.h> diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig index 9bbb2855ea91..188e1ba3b69f 100644 --- a/drivers/video/Kconfig +++ b/drivers/video/Kconfig @@ -2121,7 +2121,7 @@ config FB_EP93XX config FB_PRE_INIT_FB bool "Don't reinitialize, use bootloader's GDC/Display configuration" - depends on FB_MB862XX_LIME + depends on FB && FB_MB862XX_LIME ---help--- Select this option if display contents should be inherited as set by the bootloader. diff --git a/drivers/video/atafb.c b/drivers/video/atafb.c index 8cd279be74e5..37624f74e88b 100644 --- a/drivers/video/atafb.c +++ b/drivers/video/atafb.c @@ -329,12 +329,6 @@ extern unsigned char fontdata_8x16[]; * * * perform fb specific mmap * * int (*fb_mmap)(struct fb_info *info, struct vm_area_struct *vma); - * - * * save current hardware state * - * void (*fb_save_state)(struct fb_info *info); - * - * * restore saved state * - * void (*fb_restore_state)(struct fb_info *info); * } ; */ diff --git a/drivers/video/atmel_lcdfb.c b/drivers/video/atmel_lcdfb.c index 2830ffd72976..d5e801076d33 100644 --- a/drivers/video/atmel_lcdfb.c +++ b/drivers/video/atmel_lcdfb.c @@ -484,6 +484,7 @@ static int atmel_lcdfb_set_par(struct fb_info *info) unsigned long value; unsigned long clk_value_khz; unsigned long bits_per_line; + unsigned long pix_factor = 2; might_sleep(); @@ -516,20 +517,24 @@ static int atmel_lcdfb_set_par(struct fb_info *info) /* Now, the LCDC core... */ /* Set pixel clock */ + if (cpu_is_at91sam9g45() && !cpu_is_at91sam9g45es()) + pix_factor = 1; + clk_value_khz = clk_get_rate(sinfo->lcdc_clk) / 1000; value = DIV_ROUND_UP(clk_value_khz, PICOS2KHZ(info->var.pixclock)); - if (value < 2) { + if (value < pix_factor) { dev_notice(info->device, "Bypassing pixel clock divider\n"); lcdc_writel(sinfo, ATMEL_LCDC_LCDCON1, ATMEL_LCDC_BYPASS); } else { - value = (value / 2) - 1; + value = (value / pix_factor) - 1; dev_dbg(info->device, " * programming CLKVAL = 0x%08lx\n", value); lcdc_writel(sinfo, ATMEL_LCDC_LCDCON1, value << ATMEL_LCDC_CLKVAL_OFFSET); - info->var.pixclock = KHZ2PICOS(clk_value_khz / (2 * (value + 1))); + info->var.pixclock = + KHZ2PICOS(clk_value_khz / (pix_factor * (value + 1))); dev_dbg(info->device, " updated pixclk: %lu KHz\n", PICOS2KHZ(info->var.pixclock)); } diff --git a/drivers/video/backlight/corgi_lcd.c b/drivers/video/backlight/corgi_lcd.c index 2211a852af9c..96774949cd30 100644 --- a/drivers/video/backlight/corgi_lcd.c +++ b/drivers/video/backlight/corgi_lcd.c @@ -433,8 +433,9 @@ static int corgi_bl_update_status(struct backlight_device *bd) if (corgibl_flags & CORGIBL_SUSPENDED) intensity = 0; - if (corgibl_flags & CORGIBL_BATTLOW) - intensity &= lcd->limit_mask; + + if ((corgibl_flags & CORGIBL_BATTLOW) && intensity > lcd->limit_mask) + intensity = lcd->limit_mask; return corgi_bl_set_intensity(lcd, intensity); } diff --git a/drivers/video/backlight/lcd.c b/drivers/video/backlight/lcd.c index b6449470106c..a482dd7b0311 100644 --- a/drivers/video/backlight/lcd.c +++ b/drivers/video/backlight/lcd.c @@ -56,7 +56,7 @@ static int fb_notifier_callback(struct notifier_block *self, static int lcd_register_fb(struct lcd_device *ld) { - memset(&ld->fb_notif, 0, sizeof(&ld->fb_notif)); + memset(&ld->fb_notif, 0, sizeof(ld->fb_notif)); ld->fb_notif.notifier_call = fb_notifier_callback; return fb_register_client(&ld->fb_notif); } diff --git a/drivers/video/console/fbcon.c b/drivers/video/console/fbcon.c index 5a686cea23f4..3681c6a88212 100644 --- a/drivers/video/console/fbcon.c +++ b/drivers/video/console/fbcon.c @@ -2311,14 +2311,11 @@ static int fbcon_blank(struct vc_data *vc, int blank, int mode_switch) ops->graphics = 1; if (!blank) { - if (info->fbops->fb_save_state) - info->fbops->fb_save_state(info); var.activate = FB_ACTIVATE_NOW | FB_ACTIVATE_FORCE; fb_set_var(info, &var); ops->graphics = 0; ops->var = info->var; - } else if (info->fbops->fb_restore_state) - info->fbops->fb_restore_state(info); + } } if (!fbcon_is_inactive(vc, info)) { diff --git a/drivers/video/da8xx-fb.c b/drivers/video/da8xx-fb.c index 42e1005e2916..035d56835b75 100644 --- a/drivers/video/da8xx-fb.c +++ b/drivers/video/da8xx-fb.c @@ -26,7 +26,6 @@ #include <linux/device.h> #include <linux/platform_device.h> #include <linux/uaccess.h> -#include <linux/device.h> #include <linux/interrupt.h> #include <linux/clk.h> #include <video/da8xx-fb.h> @@ -705,7 +704,7 @@ static int __init fb_probe(struct platform_device *device) if (i == ARRAY_SIZE(known_lcd_panels)) { dev_err(&device->dev, "GLCD: No valid panel found\n"); - ret = ENODEV; + ret = -ENODEV; goto err_clk_disable; } else dev_info(&device->dev, "GLCD: Found %s panel\n", diff --git a/drivers/video/msm/mddi.c b/drivers/video/msm/mddi.c index f2de5a1acd6d..474421fe79a6 100644 --- a/drivers/video/msm/mddi.c +++ b/drivers/video/msm/mddi.c @@ -24,11 +24,10 @@ #include <linux/spinlock.h> #include <linux/clk.h> #include <linux/io.h> +#include <linux/sched.h> #include <mach/msm_iomap.h> #include <mach/irqs.h> #include <mach/board.h> -#include <linux/delay.h> - #include <mach/msm_fb.h> #include "mddi_hw.h" diff --git a/drivers/video/msm/mddi_client_nt35399.c b/drivers/video/msm/mddi_client_nt35399.c index 9c78050ac799..c9e9349451cb 100644 --- a/drivers/video/msm/mddi_client_nt35399.c +++ b/drivers/video/msm/mddi_client_nt35399.c @@ -19,6 +19,7 @@ #include <linux/kernel.h> #include <linux/platform_device.h> #include <linux/interrupt.h> +#include <linux/sched.h> #include <linux/gpio.h> #include <mach/msm_fb.h> diff --git a/drivers/video/msm/mddi_client_toshiba.c b/drivers/video/msm/mddi_client_toshiba.c index 80d0f5fdf0b1..71048e78f7f0 100644 --- a/drivers/video/msm/mddi_client_toshiba.c +++ b/drivers/video/msm/mddi_client_toshiba.c @@ -20,6 +20,7 @@ #include <linux/platform_device.h> #include <linux/interrupt.h> #include <linux/gpio.h> +#include <linux/sched.h> #include <mach/msm_fb.h> diff --git a/drivers/video/msm/mdp.c b/drivers/video/msm/mdp.c index 99636a2b20f2..6c519e2fa2b7 100644 --- a/drivers/video/msm/mdp.c +++ b/drivers/video/msm/mdp.c @@ -22,9 +22,6 @@ #include <linux/wait.h> #include <linux/clk.h> #include <linux/file.h> -#ifdef CONFIG_ANDROID_PMEM -#include <linux/android_pmem.h> -#endif #include <linux/major.h> #include <mach/msm_iomap.h> @@ -262,11 +259,6 @@ int get_img(struct mdp_img *img, struct fb_info *info, struct file *file; unsigned long vstart; -#ifdef CONFIG_ANDROID_PMEM - if (!get_pmem_file(img->memory_id, start, &vstart, len, filep)) - return 0; -#endif - file = fget_light(img->memory_id, &put_needed); if (file == NULL) return -1; @@ -283,12 +275,6 @@ int get_img(struct mdp_img *img, struct fb_info *info, void put_img(struct file *src_file, struct file *dst_file) { -#ifdef CONFIG_ANDROID_PMEM - if (src_file) - put_pmem_file(src_file); - if (dst_file) - put_pmem_file(dst_file); -#endif } int mdp_blit(struct mdp_device *mdp_dev, struct fb_info *fb, @@ -320,9 +306,6 @@ int mdp_blit(struct mdp_device *mdp_dev, struct fb_info *fb, if (unlikely(get_img(&req->dst, fb, &dst_start, &dst_len, &dst_file))) { printk(KERN_ERR "mpd_ppp: could not retrieve dst image from " "memory\n"); -#ifdef CONFIG_ANDROID_PMEM - put_pmem_file(src_file); -#endif return -EINVAL; } mutex_lock(&mdp_mutex); @@ -499,7 +482,6 @@ int mdp_probe(struct platform_device *pdev) /* register mdp device */ mdp->mdp_dev.dev.parent = &pdev->dev; mdp->mdp_dev.dev.class = mdp_class; - snprintf(mdp->mdp_dev.dev.bus_id, BUS_ID_SIZE, "mdp%d", pdev->id); /* if you can remove the platform device you'd have to implement * this: diff --git a/drivers/video/msm/mdp_ppp.c b/drivers/video/msm/mdp_ppp.c index ba2c4673b648..4ff001f4cbbd 100644 --- a/drivers/video/msm/mdp_ppp.c +++ b/drivers/video/msm/mdp_ppp.c @@ -16,7 +16,6 @@ #include <linux/file.h> #include <linux/delay.h> #include <linux/msm_mdp.h> -#include <linux/android_pmem.h> #include <mach/msm_fb.h> #include "mdp_hw.h" @@ -579,25 +578,6 @@ static int valid_src_dst(unsigned long src_start, unsigned long src_len, static void flush_imgs(struct mdp_blit_req *req, struct mdp_regs *regs, struct file *src_file, struct file *dst_file) { -#ifdef CONFIG_ANDROID_PMEM - uint32_t src0_len, src1_len, dst0_len, dst1_len; - - /* flush src images to memory before dma to mdp */ - get_len(&req->src, &req->src_rect, regs->src_bpp, &src0_len, - &src1_len); - flush_pmem_file(src_file, req->src.offset, src0_len); - if (IS_PSEUDOPLNR(req->src.format)) - flush_pmem_file(src_file, req->src.offset + src0_len, - src1_len); - - /* flush dst images */ - get_len(&req->dst, &req->dst_rect, regs->dst_bpp, &dst0_len, - &dst1_len); - flush_pmem_file(dst_file, req->dst.offset, dst0_len); - if (IS_PSEUDOPLNR(req->dst.format)) - flush_pmem_file(dst_file, req->dst.offset + dst0_len, - dst1_len); -#endif } static void get_chroma_addr(struct mdp_img *img, struct mdp_rect *rect, diff --git a/drivers/video/omap/blizzard.c b/drivers/video/omap/blizzard.c index d5e59556f9e2..70dadf9d2334 100644 --- a/drivers/video/omap/blizzard.c +++ b/drivers/video/omap/blizzard.c @@ -93,7 +93,7 @@ struct blizzard_reg_list { }; /* These need to be saved / restored separately from the rest. */ -static struct blizzard_reg_list blizzard_pll_regs[] = { +static const struct blizzard_reg_list blizzard_pll_regs[] = { { .start = 0x04, /* Don't save PLL ctrl (0x0C) */ .end = 0x0a, @@ -104,7 +104,7 @@ static struct blizzard_reg_list blizzard_pll_regs[] = { }, }; -static struct blizzard_reg_list blizzard_gen_regs[] = { +static const struct blizzard_reg_list blizzard_gen_regs[] = { { .start = 0x18, /* SDRAM control */ .end = 0x20, @@ -191,7 +191,7 @@ struct blizzard_struct { struct omapfb_device *fbdev; struct lcd_ctrl_extif *extif; - struct lcd_ctrl *int_ctrl; + const struct lcd_ctrl *int_ctrl; void (*power_up)(struct device *dev); void (*power_down)(struct device *dev); @@ -1372,7 +1372,7 @@ static void blizzard_get_caps(int plane, struct omapfb_caps *caps) (1 << OMAPFB_COLOR_YUV420); } -static void _save_regs(struct blizzard_reg_list *list, int cnt) +static void _save_regs(const struct blizzard_reg_list *list, int cnt) { int i; @@ -1383,7 +1383,7 @@ static void _save_regs(struct blizzard_reg_list *list, int cnt) } } -static void _restore_regs(struct blizzard_reg_list *list, int cnt) +static void _restore_regs(const struct blizzard_reg_list *list, int cnt) { int i; diff --git a/drivers/video/omap/omapfb_main.c b/drivers/video/omap/omapfb_main.c index 125e605b8c68..0d0c8c8b9b56 100644 --- a/drivers/video/omap/omapfb_main.c +++ b/drivers/video/omap/omapfb_main.c @@ -393,7 +393,7 @@ static void omapfb_sync(struct fb_info *fbi) * Set fb_info.fix fields and also updates fbdev. * When calling this fb_info.var must be set up already. */ -static void set_fb_fix(struct fb_info *fbi) +static void set_fb_fix(struct fb_info *fbi, int from_init) { struct fb_fix_screeninfo *fix = &fbi->fix; struct fb_var_screeninfo *var = &fbi->var; @@ -403,10 +403,16 @@ static void set_fb_fix(struct fb_info *fbi) rg = &plane->fbdev->mem_desc.region[plane->idx]; fbi->screen_base = rg->vaddr; - mutex_lock(&fbi->mm_lock); - fix->smem_start = rg->paddr; - fix->smem_len = rg->size; - mutex_unlock(&fbi->mm_lock); + + if (!from_init) { + mutex_lock(&fbi->mm_lock); + fix->smem_start = rg->paddr; + fix->smem_len = rg->size; + mutex_unlock(&fbi->mm_lock); + } else { + fix->smem_start = rg->paddr; + fix->smem_len = rg->size; + } fix->type = FB_TYPE_PACKED_PIXELS; bpp = var->bits_per_pixel; @@ -704,7 +710,7 @@ static int omapfb_set_par(struct fb_info *fbi) int r = 0; omapfb_rqueue_lock(fbdev); - set_fb_fix(fbi); + set_fb_fix(fbi, 0); r = ctrl_change_mode(fbi); omapfb_rqueue_unlock(fbdev); @@ -904,7 +910,7 @@ static int omapfb_setup_mem(struct fb_info *fbi, struct omapfb_mem_info *mi) if (old_size != size) { if (size) { memcpy(&fbi->var, new_var, sizeof(fbi->var)); - set_fb_fix(fbi); + set_fb_fix(fbi, 0); } else { /* * Set these explicitly to indicate that the @@ -1504,7 +1510,7 @@ static int fbinfo_init(struct omapfb_device *fbdev, struct fb_info *info) var->bits_per_pixel = fbdev->panel->bpp; set_fb_var(info, var); - set_fb_fix(info); + set_fb_fix(info, 1); r = fb_alloc_cmap(&info->cmap, 16, 0); if (r != 0) diff --git a/drivers/video/savage/savagefb_driver.c b/drivers/video/savage/savagefb_driver.c index 37b135d5d12e..842d157e1025 100644 --- a/drivers/video/savage/savagefb_driver.c +++ b/drivers/video/savage/savagefb_driver.c @@ -1565,7 +1565,7 @@ static int savagefb_blank(int blank, struct fb_info *info) vga_out8(0x3c5, sr8, par); vga_out8(0x3c4, 0x0d, par); srd = vga_in8(0x3c5, par); - srd &= 0x03; + srd &= 0x50; switch (blank) { case FB_BLANK_UNBLANK: @@ -1606,22 +1606,6 @@ static int savagefb_blank(int blank, struct fb_info *info) return (blank == FB_BLANK_NORMAL) ? 1 : 0; } -static void savagefb_save_state(struct fb_info *info) -{ - struct savagefb_par *par = info->par; - - savage_get_default_par(par, &par->save); -} - -static void savagefb_restore_state(struct fb_info *info) -{ - struct savagefb_par *par = info->par; - - savagefb_blank(FB_BLANK_POWERDOWN, info); - savage_set_default_par(par, &par->save); - savagefb_blank(FB_BLANK_UNBLANK, info); -} - static int savagefb_open(struct fb_info *info, int user) { struct savagefb_par *par = info->par; @@ -1667,8 +1651,6 @@ static struct fb_ops savagefb_ops = { .fb_setcolreg = savagefb_setcolreg, .fb_pan_display = savagefb_pan_display, .fb_blank = savagefb_blank, - .fb_save_state = savagefb_save_state, - .fb_restore_state = savagefb_restore_state, #if defined(CONFIG_FB_SAVAGE_ACCEL) .fb_fillrect = savagefb_fillrect, .fb_copyarea = savagefb_copyarea, diff --git a/drivers/video/uvesafb.c b/drivers/video/uvesafb.c index e35232a18571..54fbb2995a5f 100644 --- a/drivers/video/uvesafb.c +++ b/drivers/video/uvesafb.c @@ -1411,23 +1411,6 @@ static int uvesafb_check_var(struct fb_var_screeninfo *var, return 0; } -static void uvesafb_save_state(struct fb_info *info) -{ - struct uvesafb_par *par = info->par; - - if (par->vbe_state_saved) - kfree(par->vbe_state_saved); - - par->vbe_state_saved = uvesafb_vbe_state_save(par); -} - -static void uvesafb_restore_state(struct fb_info *info) -{ - struct uvesafb_par *par = info->par; - - uvesafb_vbe_state_restore(par, par->vbe_state_saved); -} - static struct fb_ops uvesafb_ops = { .owner = THIS_MODULE, .fb_open = uvesafb_open, @@ -1441,8 +1424,6 @@ static struct fb_ops uvesafb_ops = { .fb_imageblit = cfb_imageblit, .fb_check_var = uvesafb_check_var, .fb_set_par = uvesafb_set_par, - .fb_save_state = uvesafb_save_state, - .fb_restore_state = uvesafb_restore_state, }; static void __devinit uvesafb_init_info(struct fb_info *info, @@ -1459,15 +1440,6 @@ static void __devinit uvesafb_init_info(struct fb_info *info, info->fix.ypanstep = par->ypan ? 1 : 0; info->fix.ywrapstep = (par->ypan > 1) ? 1 : 0; - /* - * If we were unable to get the state buffer size, disable - * functions for saving and restoring the hardware state. - */ - if (par->vbe_state_size == 0) { - info->fbops->fb_save_state = NULL; - info->fbops->fb_restore_state = NULL; - } - /* Disable blanking if the user requested so. */ if (!blank) info->fbops->fb_blank = NULL; diff --git a/drivers/virtio/virtio_balloon.c b/drivers/virtio/virtio_balloon.c index 200c22f55130..9dd588042880 100644 --- a/drivers/virtio/virtio_balloon.c +++ b/drivers/virtio/virtio_balloon.c @@ -19,7 +19,6 @@ */ //#define DEBUG #include <linux/virtio.h> -#include <linux/virtio_ids.h> #include <linux/virtio_balloon.h> #include <linux/swap.h> #include <linux/kthread.h> @@ -248,7 +247,7 @@ out: return err; } -static void virtballoon_remove(struct virtio_device *vdev) +static void __devexit virtballoon_remove(struct virtio_device *vdev) { struct virtio_balloon *vb = vdev->priv; diff --git a/drivers/virtio/virtio_pci.c b/drivers/virtio/virtio_pci.c index 4a1f1ebff7bf..28d9cf7cf72f 100644 --- a/drivers/virtio/virtio_pci.c +++ b/drivers/virtio/virtio_pci.c @@ -530,19 +530,22 @@ static int vp_try_to_find_vqs(struct virtio_device *vdev, unsigned nvqs, err = PTR_ERR(vqs[i]); goto error_find; } + + if (!vp_dev->per_vq_vectors || msix_vec == VIRTIO_MSI_NO_VECTOR) + continue; + /* allocate per-vq irq if available and necessary */ - if (vp_dev->per_vq_vectors) { - snprintf(vp_dev->msix_names[msix_vec], - sizeof *vp_dev->msix_names, - "%s-%s", - dev_name(&vp_dev->vdev.dev), names[i]); - err = request_irq(msix_vec, vring_interrupt, 0, - vp_dev->msix_names[msix_vec], - vqs[i]); - if (err) { - vp_del_vq(vqs[i]); - goto error_find; - } + snprintf(vp_dev->msix_names[msix_vec], + sizeof *vp_dev->msix_names, + "%s-%s", + dev_name(&vp_dev->vdev.dev), names[i]); + err = request_irq(vp_dev->msix_entries[msix_vec].vector, + vring_interrupt, 0, + vp_dev->msix_names[msix_vec], + vqs[i]); + if (err) { + vp_del_vq(vqs[i]); + goto error_find; } } return 0; diff --git a/drivers/virtio/virtio_ring.c b/drivers/virtio/virtio_ring.c index f53600580726..fbd2ecde93e4 100644 --- a/drivers/virtio/virtio_ring.c +++ b/drivers/virtio/virtio_ring.c @@ -285,6 +285,9 @@ static void *vring_get_buf(struct virtqueue *_vq, unsigned int *len) return NULL; } + /* Only get used array entries after they have been exposed by host. */ + rmb(); + i = vq->vring.used->ring[vq->last_used_idx%vq->vring.num].id; *len = vq->vring.used->ring[vq->last_used_idx%vq->vring.num].len; diff --git a/drivers/watchdog/riowd.c b/drivers/watchdog/riowd.c index 1e8f02f440e6..d3c824dc2358 100644 --- a/drivers/watchdog/riowd.c +++ b/drivers/watchdog/riowd.c @@ -206,7 +206,7 @@ static int __devinit riowd_probe(struct of_device *op, dev_set_drvdata(&op->dev, p); riowd_device = p; - err = 0; + return 0; out_iounmap: of_iounmap(&op->resource[0], p->regs, 2); diff --git a/drivers/watchdog/sbc_fitpc2_wdt.c b/drivers/watchdog/sbc_fitpc2_wdt.c index 852ca1977917..91430a89107c 100644 --- a/drivers/watchdog/sbc_fitpc2_wdt.c +++ b/drivers/watchdog/sbc_fitpc2_wdt.c @@ -227,7 +227,7 @@ static int __init fitpc2_wdt_init(void) } err = misc_register(&fitpc2_wdt_miscdev); - if (!err) { + if (err) { pr_err("cannot register miscdev on minor=%d (err=%d)\n", WATCHDOG_MINOR, err); goto err_margin; diff --git a/fs/9p/vfs_dir.c b/fs/9p/vfs_dir.c index 873cd31baa47..15cce53bf61e 100644 --- a/fs/9p/vfs_dir.c +++ b/fs/9p/vfs_dir.c @@ -40,6 +40,24 @@ #include "fid.h" /** + * struct p9_rdir - readdir accounting + * @mutex: mutex protecting readdir + * @head: start offset of current dirread buffer + * @tail: end offset of current dirread buffer + * @buf: dirread buffer + * + * private structure for keeping track of readdir + * allocated on demand + */ + +struct p9_rdir { + struct mutex mutex; + int head; + int tail; + uint8_t *buf; +}; + +/** * dt_type - return file type * @mistat: mistat structure * @@ -70,56 +88,79 @@ static int v9fs_dir_readdir(struct file *filp, void *dirent, filldir_t filldir) { int over; struct p9_wstat st; - int err; + int err = 0; struct p9_fid *fid; int buflen; - char *statbuf; - int n, i = 0; + int reclen = 0; + struct p9_rdir *rdir; P9_DPRINTK(P9_DEBUG_VFS, "name %s\n", filp->f_path.dentry->d_name.name); fid = filp->private_data; buflen = fid->clnt->msize - P9_IOHDRSZ; - statbuf = kmalloc(buflen, GFP_KERNEL); - if (!statbuf) - return -ENOMEM; - - while (1) { - err = v9fs_file_readn(filp, statbuf, NULL, buflen, - fid->rdir_fpos); - if (err <= 0) - break; - - n = err; - while (i < n) { - err = p9stat_read(statbuf + i, buflen-i, &st, - fid->clnt->dotu); + + /* allocate rdir on demand */ + if (!fid->rdir) { + rdir = kmalloc(sizeof(struct p9_rdir) + buflen, GFP_KERNEL); + + if (rdir == NULL) { + err = -ENOMEM; + goto exit; + } + spin_lock(&filp->f_dentry->d_lock); + if (!fid->rdir) { + rdir->buf = (uint8_t *)rdir + sizeof(struct p9_rdir); + mutex_init(&rdir->mutex); + rdir->head = rdir->tail = 0; + fid->rdir = (void *) rdir; + rdir = NULL; + } + spin_unlock(&filp->f_dentry->d_lock); + kfree(rdir); + } + rdir = (struct p9_rdir *) fid->rdir; + + err = mutex_lock_interruptible(&rdir->mutex); + while (err == 0) { + if (rdir->tail == rdir->head) { + err = v9fs_file_readn(filp, rdir->buf, NULL, + buflen, filp->f_pos); + if (err <= 0) + goto unlock_and_exit; + + rdir->head = 0; + rdir->tail = err; + } + + while (rdir->head < rdir->tail) { + err = p9stat_read(rdir->buf + rdir->head, + buflen - rdir->head, &st, + fid->clnt->dotu); if (err) { P9_DPRINTK(P9_DEBUG_VFS, "returned %d\n", err); err = -EIO; p9stat_free(&st); - goto free_and_exit; + goto unlock_and_exit; } - - i += st.size+2; - fid->rdir_fpos += st.size+2; + reclen = st.size+2; over = filldir(dirent, st.name, strlen(st.name), filp->f_pos, v9fs_qid2ino(&st.qid), dt_type(&st)); - filp->f_pos += st.size+2; - p9stat_free(&st); if (over) { err = 0; - goto free_and_exit; + goto unlock_and_exit; } + rdir->head += reclen; + filp->f_pos += reclen; } } -free_and_exit: - kfree(statbuf); +unlock_and_exit: + mutex_unlock(&rdir->mutex); +exit: return err; } diff --git a/fs/9p/vfs_inode.c b/fs/9p/vfs_inode.c index 5947628aefef..18f74ec4dce9 100644 --- a/fs/9p/vfs_inode.c +++ b/fs/9p/vfs_inode.c @@ -994,8 +994,7 @@ static int v9fs_readlink(struct dentry *dentry, char *buffer, int buflen) P9_DPRINTK(P9_DEBUG_VFS, "%s -> %s (%s)\n", dentry->d_name.name, st->extension, buffer); - retval = buflen; - + retval = strnlen(buffer, buflen); done: kfree(st); return retval; @@ -1062,7 +1061,7 @@ static void *v9fs_vfs_follow_link(struct dentry *dentry, struct nameidata *nd) __putname(link); link = ERR_PTR(len); } else - link[len] = 0; + link[min(len, PATH_MAX-1)] = 0; } nd_set_link(nd, link); diff --git a/fs/Kconfig b/fs/Kconfig index d4bf8caad8d0..64d44efad7a5 100644 --- a/fs/Kconfig +++ b/fs/Kconfig @@ -135,8 +135,8 @@ config TMPFS_POSIX_ACL config HUGETLBFS bool "HugeTLB file system support" - depends on X86 || IA64 || PPC64 || SPARC64 || (SUPERH && MMU) || \ - (S390 && 64BIT) || SYS_SUPPORTS_HUGETLBFS || BROKEN + depends on X86 || IA64 || SPARC64 || (S390 && 64BIT) || \ + SYS_SUPPORTS_HUGETLBFS || BROKEN help hugetlbfs is a filesystem backing for HugeTLB pages, based on ramfs. For architectures that support it, say Y here and read @@ -325,8 +325,16 @@ static void bio_fs_destructor(struct bio *bio) * @gfp_mask: allocation mask to use * @nr_iovecs: number of iovecs * - * Allocate a new bio with @nr_iovecs bvecs. If @gfp_mask - * contains __GFP_WAIT, the allocation is guaranteed to succeed. + * bio_alloc will allocate a bio and associated bio_vec array that can hold + * at least @nr_iovecs entries. Allocations will be done from the + * fs_bio_set. Also see @bio_alloc_bioset and @bio_kmalloc. + * + * If %__GFP_WAIT is set, then bio_alloc will always be able to allocate + * a bio. This is due to the mempool guarantees. To make this work, callers + * must never allocate more than 1 bio at a time from this pool. Callers + * that need to allocate more than 1 bio must always submit the previously + * allocated bio for IO before attempting to allocate a new one. Failure to + * do so can cause livelocks under memory pressure. * * RETURNS: * Pointer to new bio on success, NULL on failure. @@ -350,21 +358,13 @@ static void bio_kmalloc_destructor(struct bio *bio) } /** - * bio_alloc - allocate a bio for I/O + * bio_kmalloc - allocate a bio for I/O using kmalloc() * @gfp_mask: the GFP_ mask given to the slab allocator * @nr_iovecs: number of iovecs to pre-allocate * * Description: - * bio_alloc will allocate a bio and associated bio_vec array that can hold - * at least @nr_iovecs entries. Allocations will be done from the - * fs_bio_set. Also see @bio_alloc_bioset. - * - * If %__GFP_WAIT is set, then bio_alloc will always be able to allocate - * a bio. This is due to the mempool guarantees. To make this work, callers - * must never allocate more than 1 bio at a time from this pool. Callers - * that need to allocate more than 1 bio must always submit the previously - * allocated bio for IO before attempting to allocate a new one. Failure to - * do so can cause livelocks under memory pressure. + * Allocate a new bio with @nr_iovecs bvecs. If @gfp_mask contains + * %__GFP_WAIT, the allocation is guaranteed to succeed. * **/ struct bio *bio_kmalloc(gfp_t gfp_mask, int nr_iovecs) @@ -407,7 +407,7 @@ EXPORT_SYMBOL(zero_fill_bio); * * Description: * Put a reference to a &struct bio, either one you have gotten with - * bio_alloc or bio_get. The last put of a bio will free it. + * bio_alloc, bio_get or bio_clone. The last put of a bio will free it. **/ void bio_put(struct bio *bio) { diff --git a/fs/block_dev.c b/fs/block_dev.c index 9cf4b926f8e4..8bed0557d88c 100644 --- a/fs/block_dev.c +++ b/fs/block_dev.c @@ -1248,8 +1248,8 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) bd_set_size(bdev, (loff_t)bdev->bd_part->nr_sects << 9); } } else { - put_disk(disk); module_put(disk->fops->owner); + put_disk(disk); disk = NULL; if (bdev->bd_contains == bdev) { if (bdev->bd_disk->fops->open) { diff --git a/fs/btrfs/acl.c b/fs/btrfs/acl.c index 69b355ae7f49..361604244271 100644 --- a/fs/btrfs/acl.c +++ b/fs/btrfs/acl.c @@ -27,7 +27,7 @@ #include "btrfs_inode.h" #include "xattr.h" -#ifdef CONFIG_BTRFS_POSIX_ACL +#ifdef CONFIG_BTRFS_FS_POSIX_ACL static struct posix_acl *btrfs_get_acl(struct inode *inode, int type) { @@ -313,7 +313,7 @@ struct xattr_handler btrfs_xattr_acl_access_handler = { .set = btrfs_xattr_acl_access_set, }; -#else /* CONFIG_BTRFS_POSIX_ACL */ +#else /* CONFIG_BTRFS_FS_POSIX_ACL */ int btrfs_acl_chmod(struct inode *inode) { @@ -325,4 +325,4 @@ int btrfs_init_acl(struct inode *inode, struct inode *dir) return 0; } -#endif /* CONFIG_BTRFS_POSIX_ACL */ +#endif /* CONFIG_BTRFS_FS_POSIX_ACL */ diff --git a/fs/btrfs/async-thread.c b/fs/btrfs/async-thread.c index 282ca085c2fb..c0861e781cdb 100644 --- a/fs/btrfs/async-thread.c +++ b/fs/btrfs/async-thread.c @@ -64,6 +64,51 @@ struct btrfs_worker_thread { }; /* + * btrfs_start_workers uses kthread_run, which can block waiting for memory + * for a very long time. It will actually throttle on page writeback, + * and so it may not make progress until after our btrfs worker threads + * process all of the pending work structs in their queue + * + * This means we can't use btrfs_start_workers from inside a btrfs worker + * thread that is used as part of cleaning dirty memory, which pretty much + * involves all of the worker threads. + * + * Instead we have a helper queue who never has more than one thread + * where we scheduler thread start operations. This worker_start struct + * is used to contain the work and hold a pointer to the queue that needs + * another worker. + */ +struct worker_start { + struct btrfs_work work; + struct btrfs_workers *queue; +}; + +static void start_new_worker_func(struct btrfs_work *work) +{ + struct worker_start *start; + start = container_of(work, struct worker_start, work); + btrfs_start_workers(start->queue, 1); + kfree(start); +} + +static int start_new_worker(struct btrfs_workers *queue) +{ + struct worker_start *start; + int ret; + + start = kzalloc(sizeof(*start), GFP_NOFS); + if (!start) + return -ENOMEM; + + start->work.func = start_new_worker_func; + start->queue = queue; + ret = btrfs_queue_worker(queue->atomic_worker_start, &start->work); + if (ret) + kfree(start); + return ret; +} + +/* * helper function to move a thread onto the idle list after it * has finished some requests. */ @@ -118,11 +163,13 @@ static void check_pending_worker_creates(struct btrfs_worker_thread *worker) goto out; workers->atomic_start_pending = 0; - if (workers->num_workers >= workers->max_workers) + if (workers->num_workers + workers->num_workers_starting >= + workers->max_workers) goto out; + workers->num_workers_starting += 1; spin_unlock_irqrestore(&workers->lock, flags); - btrfs_start_workers(workers, 1); + start_new_worker(workers); return; out: @@ -390,9 +437,11 @@ int btrfs_stop_workers(struct btrfs_workers *workers) /* * simple init on struct btrfs_workers */ -void btrfs_init_workers(struct btrfs_workers *workers, char *name, int max) +void btrfs_init_workers(struct btrfs_workers *workers, char *name, int max, + struct btrfs_workers *async_helper) { workers->num_workers = 0; + workers->num_workers_starting = 0; INIT_LIST_HEAD(&workers->worker_list); INIT_LIST_HEAD(&workers->idle_list); INIT_LIST_HEAD(&workers->order_list); @@ -404,14 +453,15 @@ void btrfs_init_workers(struct btrfs_workers *workers, char *name, int max) workers->name = name; workers->ordered = 0; workers->atomic_start_pending = 0; - workers->atomic_worker_start = 0; + workers->atomic_worker_start = async_helper; } /* * starts new worker threads. This does not enforce the max worker * count in case you need to temporarily go past it. */ -int btrfs_start_workers(struct btrfs_workers *workers, int num_workers) +static int __btrfs_start_workers(struct btrfs_workers *workers, + int num_workers) { struct btrfs_worker_thread *worker; int ret = 0; @@ -444,6 +494,8 @@ int btrfs_start_workers(struct btrfs_workers *workers, int num_workers) list_add_tail(&worker->worker_list, &workers->idle_list); worker->idle = 1; workers->num_workers++; + workers->num_workers_starting--; + WARN_ON(workers->num_workers_starting < 0); spin_unlock_irq(&workers->lock); } return 0; @@ -452,6 +504,14 @@ fail: return ret; } +int btrfs_start_workers(struct btrfs_workers *workers, int num_workers) +{ + spin_lock_irq(&workers->lock); + workers->num_workers_starting += num_workers; + spin_unlock_irq(&workers->lock); + return __btrfs_start_workers(workers, num_workers); +} + /* * run through the list and find a worker thread that doesn't have a lot * to do right now. This can return null if we aren't yet at the thread @@ -461,7 +521,10 @@ static struct btrfs_worker_thread *next_worker(struct btrfs_workers *workers) { struct btrfs_worker_thread *worker; struct list_head *next; - int enforce_min = workers->num_workers < workers->max_workers; + int enforce_min; + + enforce_min = (workers->num_workers + workers->num_workers_starting) < + workers->max_workers; /* * if we find an idle thread, don't move it to the end of the @@ -509,15 +572,17 @@ again: worker = next_worker(workers); if (!worker) { - if (workers->num_workers >= workers->max_workers) { + if (workers->num_workers + workers->num_workers_starting >= + workers->max_workers) { goto fallback; } else if (workers->atomic_worker_start) { workers->atomic_start_pending = 1; goto fallback; } else { + workers->num_workers_starting++; spin_unlock_irqrestore(&workers->lock, flags); /* we're below the limit, start another worker */ - btrfs_start_workers(workers, 1); + __btrfs_start_workers(workers, 1); goto again; } } diff --git a/fs/btrfs/async-thread.h b/fs/btrfs/async-thread.h index fc089b95ec14..5077746cf85e 100644 --- a/fs/btrfs/async-thread.h +++ b/fs/btrfs/async-thread.h @@ -64,6 +64,8 @@ struct btrfs_workers { /* current number of running workers */ int num_workers; + int num_workers_starting; + /* max number of workers allowed. changed by btrfs_start_workers */ int max_workers; @@ -78,9 +80,10 @@ struct btrfs_workers { /* * are we allowed to sleep while starting workers or are we required - * to start them at a later time? + * to start them at a later time? If we can't sleep, this indicates + * which queue we need to use to schedule thread creation. */ - int atomic_worker_start; + struct btrfs_workers *atomic_worker_start; /* list with all the work threads. The workers on the idle thread * may be actively servicing jobs, but they haven't yet hit the @@ -109,7 +112,8 @@ struct btrfs_workers { int btrfs_queue_worker(struct btrfs_workers *workers, struct btrfs_work *work); int btrfs_start_workers(struct btrfs_workers *workers, int num_workers); int btrfs_stop_workers(struct btrfs_workers *workers); -void btrfs_init_workers(struct btrfs_workers *workers, char *name, int max); +void btrfs_init_workers(struct btrfs_workers *workers, char *name, int max, + struct btrfs_workers *async_starter); int btrfs_requeue_work(struct btrfs_work *work); void btrfs_set_work_high_prio(struct btrfs_work *work); #endif diff --git a/fs/btrfs/btrfs_inode.h b/fs/btrfs/btrfs_inode.h index a54d354cefcb..f6783a42f010 100644 --- a/fs/btrfs/btrfs_inode.h +++ b/fs/btrfs/btrfs_inode.h @@ -86,6 +86,12 @@ struct btrfs_inode { * transid of the trans_handle that last modified this inode */ u64 last_trans; + + /* + * log transid when this inode was last modified + */ + u64 last_sub_trans; + /* * transid that last logged this inode */ @@ -128,12 +134,14 @@ struct btrfs_inode { u64 last_unlink_trans; /* - * These two counters are for delalloc metadata reservations. We keep - * track of how many extents we've accounted for vs how many extents we - * have. + * Counters to keep track of the number of extent item's we may use due + * to delalloc and such. outstanding_extents is the number of extent + * items we think we'll end up using, and reserved_extents is the number + * of extent items we've reserved metadata for. */ - int delalloc_reserved_extents; - int delalloc_extents; + spinlock_t accounting_lock; + int reserved_extents; + int outstanding_extents; /* * ordered_data_close is set by truncate when a file that used diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h index dd8ced9814c4..444b3e9b92a4 100644 --- a/fs/btrfs/ctree.h +++ b/fs/btrfs/ctree.h @@ -691,14 +691,17 @@ struct btrfs_space_info { struct list_head list; + /* for controlling how we free up space for allocations */ + wait_queue_head_t allocate_wait; + wait_queue_head_t flush_wait; + int allocating_chunk; + int flushing; + /* for block groups in our same type */ struct list_head block_groups; spinlock_t lock; struct rw_semaphore groups_sem; atomic_t caching_threads; - - int allocating_chunk; - wait_queue_head_t wait; }; /* @@ -907,6 +910,7 @@ struct btrfs_fs_info { * A third pool does submit_bio to avoid deadlocking with the other * two */ + struct btrfs_workers generic_worker; struct btrfs_workers workers; struct btrfs_workers delalloc_workers; struct btrfs_workers endio_workers; @@ -914,6 +918,7 @@ struct btrfs_fs_info { struct btrfs_workers endio_meta_write_workers; struct btrfs_workers endio_write_workers; struct btrfs_workers submit_workers; + struct btrfs_workers enospc_workers; /* * fixup workers take dirty pages that didn't properly go through * the cow mechanism and make them safe to write. It happens @@ -1004,7 +1009,10 @@ struct btrfs_root { atomic_t log_writers; atomic_t log_commit[2]; unsigned long log_transid; + unsigned long last_log_commit; unsigned long log_batch; + pid_t log_start_pid; + bool log_multiple_pids; u64 objectid; u64 last_trans; @@ -1145,6 +1153,7 @@ struct btrfs_root { #define BTRFS_MOUNT_FLUSHONCOMMIT (1 << 7) #define BTRFS_MOUNT_SSD_SPREAD (1 << 8) #define BTRFS_MOUNT_NOSSD (1 << 9) +#define BTRFS_MOUNT_DISCARD (1 << 10) #define btrfs_clear_opt(o, opt) ((o) &= ~BTRFS_MOUNT_##opt) #define btrfs_set_opt(o, opt) ((o) |= BTRFS_MOUNT_##opt) @@ -2323,7 +2332,7 @@ int btrfs_orphan_del(struct btrfs_trans_handle *trans, struct inode *inode); void btrfs_orphan_cleanup(struct btrfs_root *root); int btrfs_cont_expand(struct inode *inode, loff_t size); int btrfs_invalidate_inodes(struct btrfs_root *root); -extern struct dentry_operations btrfs_dentry_operations; +extern const struct dentry_operations btrfs_dentry_operations; /* ioctl.c */ long btrfs_ioctl(struct file *file, unsigned int cmd, unsigned long arg); @@ -2366,7 +2375,7 @@ int btrfs_parse_options(struct btrfs_root *root, char *options); int btrfs_sync_fs(struct super_block *sb, int wait); /* acl.c */ -#ifdef CONFIG_BTRFS_POSIX_ACL +#ifdef CONFIG_BTRFS_FS_POSIX_ACL int btrfs_check_acl(struct inode *inode, int mask); #else #define btrfs_check_acl NULL diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c index af0435f79fa6..02b6afbd7450 100644 --- a/fs/btrfs/disk-io.c +++ b/fs/btrfs/disk-io.c @@ -917,6 +917,7 @@ static int __setup_root(u32 nodesize, u32 leafsize, u32 sectorsize, atomic_set(&root->log_writers, 0); root->log_batch = 0; root->log_transid = 0; + root->last_log_commit = 0; extent_io_tree_init(&root->dirty_log_pages, fs_info->btree_inode->i_mapping, GFP_NOFS); @@ -1087,6 +1088,7 @@ int btrfs_add_log_tree(struct btrfs_trans_handle *trans, WARN_ON(root->log_root); root->log_root = log_root; root->log_transid = 0; + root->last_log_commit = 0; return 0; } @@ -1746,21 +1748,25 @@ struct btrfs_root *open_ctree(struct super_block *sb, err = -EINVAL; goto fail_iput; } -printk("thread pool is %d\n", fs_info->thread_pool_size); - /* - * we need to start all the end_io workers up front because the - * queue work function gets called at interrupt time, and so it - * cannot dynamically grow. - */ + + btrfs_init_workers(&fs_info->generic_worker, + "genwork", 1, NULL); + btrfs_init_workers(&fs_info->workers, "worker", - fs_info->thread_pool_size); + fs_info->thread_pool_size, + &fs_info->generic_worker); btrfs_init_workers(&fs_info->delalloc_workers, "delalloc", - fs_info->thread_pool_size); + fs_info->thread_pool_size, + &fs_info->generic_worker); btrfs_init_workers(&fs_info->submit_workers, "submit", min_t(u64, fs_devices->num_devices, - fs_info->thread_pool_size)); + fs_info->thread_pool_size), + &fs_info->generic_worker); + btrfs_init_workers(&fs_info->enospc_workers, "enospc", + fs_info->thread_pool_size, + &fs_info->generic_worker); /* a higher idle thresh on the submit workers makes it much more * likely that bios will be send down in a sane order to the @@ -1774,15 +1780,20 @@ printk("thread pool is %d\n", fs_info->thread_pool_size); fs_info->delalloc_workers.idle_thresh = 2; fs_info->delalloc_workers.ordered = 1; - btrfs_init_workers(&fs_info->fixup_workers, "fixup", 1); + btrfs_init_workers(&fs_info->fixup_workers, "fixup", 1, + &fs_info->generic_worker); btrfs_init_workers(&fs_info->endio_workers, "endio", - fs_info->thread_pool_size); + fs_info->thread_pool_size, + &fs_info->generic_worker); btrfs_init_workers(&fs_info->endio_meta_workers, "endio-meta", - fs_info->thread_pool_size); + fs_info->thread_pool_size, + &fs_info->generic_worker); btrfs_init_workers(&fs_info->endio_meta_write_workers, - "endio-meta-write", fs_info->thread_pool_size); + "endio-meta-write", fs_info->thread_pool_size, + &fs_info->generic_worker); btrfs_init_workers(&fs_info->endio_write_workers, "endio-write", - fs_info->thread_pool_size); + fs_info->thread_pool_size, + &fs_info->generic_worker); /* * endios are largely parallel and should have a very @@ -1794,12 +1805,8 @@ printk("thread pool is %d\n", fs_info->thread_pool_size); fs_info->endio_write_workers.idle_thresh = 2; fs_info->endio_meta_write_workers.idle_thresh = 2; - fs_info->endio_workers.atomic_worker_start = 1; - fs_info->endio_meta_workers.atomic_worker_start = 1; - fs_info->endio_write_workers.atomic_worker_start = 1; - fs_info->endio_meta_write_workers.atomic_worker_start = 1; - btrfs_start_workers(&fs_info->workers, 1); + btrfs_start_workers(&fs_info->generic_worker, 1); btrfs_start_workers(&fs_info->submit_workers, 1); btrfs_start_workers(&fs_info->delalloc_workers, 1); btrfs_start_workers(&fs_info->fixup_workers, 1); @@ -1807,6 +1814,7 @@ printk("thread pool is %d\n", fs_info->thread_pool_size); btrfs_start_workers(&fs_info->endio_meta_workers, 1); btrfs_start_workers(&fs_info->endio_meta_write_workers, 1); btrfs_start_workers(&fs_info->endio_write_workers, 1); + btrfs_start_workers(&fs_info->enospc_workers, 1); fs_info->bdi.ra_pages *= btrfs_super_num_devices(disk_super); fs_info->bdi.ra_pages = max(fs_info->bdi.ra_pages, @@ -2012,6 +2020,7 @@ fail_chunk_root: free_extent_buffer(chunk_root->node); free_extent_buffer(chunk_root->commit_root); fail_sb_buffer: + btrfs_stop_workers(&fs_info->generic_worker); btrfs_stop_workers(&fs_info->fixup_workers); btrfs_stop_workers(&fs_info->delalloc_workers); btrfs_stop_workers(&fs_info->workers); @@ -2020,6 +2029,7 @@ fail_sb_buffer: btrfs_stop_workers(&fs_info->endio_meta_write_workers); btrfs_stop_workers(&fs_info->endio_write_workers); btrfs_stop_workers(&fs_info->submit_workers); + btrfs_stop_workers(&fs_info->enospc_workers); fail_iput: invalidate_inode_pages2(fs_info->btree_inode->i_mapping); iput(fs_info->btree_inode); @@ -2437,6 +2447,7 @@ int close_ctree(struct btrfs_root *root) iput(fs_info->btree_inode); + btrfs_stop_workers(&fs_info->generic_worker); btrfs_stop_workers(&fs_info->fixup_workers); btrfs_stop_workers(&fs_info->delalloc_workers); btrfs_stop_workers(&fs_info->workers); @@ -2445,6 +2456,7 @@ int close_ctree(struct btrfs_root *root) btrfs_stop_workers(&fs_info->endio_meta_write_workers); btrfs_stop_workers(&fs_info->endio_write_workers); btrfs_stop_workers(&fs_info->submit_workers); + btrfs_stop_workers(&fs_info->enospc_workers); btrfs_close_devices(fs_info->fs_devices); btrfs_mapping_tree_free(&fs_info->mapping_tree); diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c index 359a754c782c..94627c4cc193 100644 --- a/fs/btrfs/extent-tree.c +++ b/fs/btrfs/extent-tree.c @@ -1568,23 +1568,23 @@ static int remove_extent_backref(struct btrfs_trans_handle *trans, return ret; } -#ifdef BIO_RW_DISCARD static void btrfs_issue_discard(struct block_device *bdev, u64 start, u64 len) { blkdev_issue_discard(bdev, start >> 9, len >> 9, GFP_KERNEL, DISCARD_FL_BARRIER); } -#endif static int btrfs_discard_extent(struct btrfs_root *root, u64 bytenr, u64 num_bytes) { -#ifdef BIO_RW_DISCARD int ret; u64 map_length = num_bytes; struct btrfs_multi_bio *multi = NULL; + if (!btrfs_test_opt(root, DISCARD)) + return 0; + /* Tell the block device(s) that the sectors can be discarded */ ret = btrfs_map_block(&root->fs_info->mapping_tree, READ, bytenr, &map_length, &multi, 0); @@ -1604,9 +1604,6 @@ static int btrfs_discard_extent(struct btrfs_root *root, u64 bytenr, } return ret; -#else - return 0; -#endif } int btrfs_inc_extent_ref(struct btrfs_trans_handle *trans, @@ -2824,14 +2821,17 @@ int btrfs_unreserve_metadata_for_delalloc(struct btrfs_root *root, num_items); spin_lock(&meta_sinfo->lock); - if (BTRFS_I(inode)->delalloc_reserved_extents <= - BTRFS_I(inode)->delalloc_extents) { + spin_lock(&BTRFS_I(inode)->accounting_lock); + if (BTRFS_I(inode)->reserved_extents <= + BTRFS_I(inode)->outstanding_extents) { + spin_unlock(&BTRFS_I(inode)->accounting_lock); spin_unlock(&meta_sinfo->lock); return 0; } + spin_unlock(&BTRFS_I(inode)->accounting_lock); - BTRFS_I(inode)->delalloc_reserved_extents--; - BUG_ON(BTRFS_I(inode)->delalloc_reserved_extents < 0); + BTRFS_I(inode)->reserved_extents--; + BUG_ON(BTRFS_I(inode)->reserved_extents < 0); if (meta_sinfo->bytes_delalloc < num_bytes) { bug = true; @@ -2864,6 +2864,107 @@ static void check_force_delalloc(struct btrfs_space_info *meta_sinfo) meta_sinfo->force_delalloc = 0; } +struct async_flush { + struct btrfs_root *root; + struct btrfs_space_info *info; + struct btrfs_work work; +}; + +static noinline void flush_delalloc_async(struct btrfs_work *work) +{ + struct async_flush *async; + struct btrfs_root *root; + struct btrfs_space_info *info; + + async = container_of(work, struct async_flush, work); + root = async->root; + info = async->info; + + btrfs_start_delalloc_inodes(root); + wake_up(&info->flush_wait); + btrfs_wait_ordered_extents(root, 0); + + spin_lock(&info->lock); + info->flushing = 0; + spin_unlock(&info->lock); + wake_up(&info->flush_wait); + + kfree(async); +} + +static void wait_on_flush(struct btrfs_space_info *info) +{ + DEFINE_WAIT(wait); + u64 used; + + while (1) { + prepare_to_wait(&info->flush_wait, &wait, + TASK_UNINTERRUPTIBLE); + spin_lock(&info->lock); + if (!info->flushing) { + spin_unlock(&info->lock); + break; + } + + used = info->bytes_used + info->bytes_reserved + + info->bytes_pinned + info->bytes_readonly + + info->bytes_super + info->bytes_root + + info->bytes_may_use + info->bytes_delalloc; + if (used < info->total_bytes) { + spin_unlock(&info->lock); + break; + } + spin_unlock(&info->lock); + schedule(); + } + finish_wait(&info->flush_wait, &wait); +} + +static void flush_delalloc(struct btrfs_root *root, + struct btrfs_space_info *info) +{ + struct async_flush *async; + bool wait = false; + + spin_lock(&info->lock); + + if (!info->flushing) { + info->flushing = 1; + init_waitqueue_head(&info->flush_wait); + } else { + wait = true; + } + + spin_unlock(&info->lock); + + if (wait) { + wait_on_flush(info); + return; + } + + async = kzalloc(sizeof(*async), GFP_NOFS); + if (!async) + goto flush; + + async->root = root; + async->info = info; + async->work.func = flush_delalloc_async; + + btrfs_queue_worker(&root->fs_info->enospc_workers, + &async->work); + wait_on_flush(info); + return; + +flush: + btrfs_start_delalloc_inodes(root); + btrfs_wait_ordered_extents(root, 0); + + spin_lock(&info->lock); + info->flushing = 0; + spin_unlock(&info->lock); + wake_up(&info->flush_wait); +} + static int maybe_allocate_chunk(struct btrfs_root *root, struct btrfs_space_info *info) { @@ -2876,10 +2977,10 @@ static int maybe_allocate_chunk(struct btrfs_root *root, free_space = btrfs_super_total_bytes(disk_super); /* - * we allow the metadata to grow to a max of either 5gb or 5% of the + * we allow the metadata to grow to a max of either 10gb or 5% of the * space in the volume. */ - min_metadata = min((u64)5 * 1024 * 1024 * 1024, + min_metadata = min((u64)10 * 1024 * 1024 * 1024, div64_u64(free_space * 5, 100)); if (info->total_bytes >= min_metadata) { spin_unlock(&info->lock); @@ -2894,7 +2995,7 @@ static int maybe_allocate_chunk(struct btrfs_root *root, if (!info->allocating_chunk) { info->force_alloc = 1; info->allocating_chunk = 1; - init_waitqueue_head(&info->wait); + init_waitqueue_head(&info->allocate_wait); } else { wait = true; } @@ -2902,7 +3003,7 @@ static int maybe_allocate_chunk(struct btrfs_root *root, spin_unlock(&info->lock); if (wait) { - wait_event(info->wait, + wait_event(info->allocate_wait, !info->allocating_chunk); return 1; } @@ -2923,7 +3024,7 @@ out: spin_lock(&info->lock); info->allocating_chunk = 0; spin_unlock(&info->lock); - wake_up(&info->wait); + wake_up(&info->allocate_wait); if (ret) return 0; @@ -2981,21 +3082,20 @@ again: filemap_flush(inode->i_mapping); goto again; } else if (flushed == 3) { - btrfs_start_delalloc_inodes(root); - btrfs_wait_ordered_extents(root, 0); + flush_delalloc(root, meta_sinfo); goto again; } spin_lock(&meta_sinfo->lock); meta_sinfo->bytes_delalloc -= num_bytes; spin_unlock(&meta_sinfo->lock); printk(KERN_ERR "enospc, has %d, reserved %d\n", - BTRFS_I(inode)->delalloc_extents, - BTRFS_I(inode)->delalloc_reserved_extents); + BTRFS_I(inode)->outstanding_extents, + BTRFS_I(inode)->reserved_extents); dump_space_info(meta_sinfo, 0, 0); return -ENOSPC; } - BTRFS_I(inode)->delalloc_reserved_extents++; + BTRFS_I(inode)->reserved_extents++; check_force_delalloc(meta_sinfo); spin_unlock(&meta_sinfo->lock); @@ -3094,8 +3194,7 @@ again: } if (retries == 2) { - btrfs_start_delalloc_inodes(root); - btrfs_wait_ordered_extents(root, 0); + flush_delalloc(root, meta_sinfo); goto again; } spin_lock(&meta_sinfo->lock); @@ -3588,6 +3687,14 @@ static int pin_down_bytes(struct btrfs_trans_handle *trans, if (is_data) goto pinit; + /* + * discard is sloooow, and so triggering discards on + * individual btree blocks isn't a good plan. Just + * pin everything in discard mode. + */ + if (btrfs_test_opt(root, DISCARD)) + goto pinit; + buf = btrfs_find_tree_block(root, bytenr, num_bytes); if (!buf) goto pinit; @@ -3995,7 +4102,7 @@ wait_block_group_cache_done(struct btrfs_block_group_cache *cache) } enum btrfs_loop_type { - LOOP_CACHED_ONLY = 0, + LOOP_FIND_IDEAL = 0, LOOP_CACHING_NOWAIT = 1, LOOP_CACHING_WAIT = 2, LOOP_ALLOC_CHUNK = 3, @@ -4024,11 +4131,15 @@ static noinline int find_free_extent(struct btrfs_trans_handle *trans, struct btrfs_block_group_cache *block_group = NULL; int empty_cluster = 2 * 1024 * 1024; int allowed_chunk_alloc = 0; + int done_chunk_alloc = 0; struct btrfs_space_info *space_info; int last_ptr_loop = 0; int loop = 0; bool found_uncached_bg = false; bool failed_cluster_refill = false; + bool failed_alloc = false; + u64 ideal_cache_percent = 0; + u64 ideal_cache_offset = 0; WARN_ON(num_bytes < root->sectorsize); btrfs_set_key_type(ins, BTRFS_EXTENT_ITEM_KEY); @@ -4064,14 +4175,19 @@ static noinline int find_free_extent(struct btrfs_trans_handle *trans, empty_cluster = 0; if (search_start == hint_byte) { +ideal_cache: block_group = btrfs_lookup_block_group(root->fs_info, search_start); /* * we don't want to use the block group if it doesn't match our * allocation bits, or if its not cached. + * + * However if we are re-searching with an ideal block group + * picked out then we don't care that the block group is cached. */ if (block_group && block_group_bits(block_group, data) && - block_group_cache_done(block_group)) { + (block_group->cached != BTRFS_CACHE_NO || + search_start == ideal_cache_offset)) { down_read(&space_info->groups_sem); if (list_empty(&block_group->list) || block_group->ro) { @@ -4083,13 +4199,13 @@ static noinline int find_free_extent(struct btrfs_trans_handle *trans, */ btrfs_put_block_group(block_group); up_read(&space_info->groups_sem); - } else + } else { goto have_block_group; + } } else if (block_group) { btrfs_put_block_group(block_group); } } - search: down_read(&space_info->groups_sem); list_for_each_entry(block_group, &space_info->block_groups, list) { @@ -4101,28 +4217,45 @@ search: have_block_group: if (unlikely(block_group->cached == BTRFS_CACHE_NO)) { + u64 free_percent; + + free_percent = btrfs_block_group_used(&block_group->item); + free_percent *= 100; + free_percent = div64_u64(free_percent, + block_group->key.offset); + free_percent = 100 - free_percent; + if (free_percent > ideal_cache_percent && + likely(!block_group->ro)) { + ideal_cache_offset = block_group->key.objectid; + ideal_cache_percent = free_percent; + } + /* - * we want to start caching kthreads, but not too many - * right off the bat so we don't overwhelm the system, - * so only start them if there are less than 2 and we're - * in the initial allocation phase. + * We only want to start kthread caching if we are at + * the point where we will wait for caching to make + * progress, or if our ideal search is over and we've + * found somebody to start caching. */ if (loop > LOOP_CACHING_NOWAIT || - atomic_read(&space_info->caching_threads) < 2) { + (loop > LOOP_FIND_IDEAL && + atomic_read(&space_info->caching_threads) < 2)) { ret = cache_block_group(block_group); BUG_ON(ret); } - } - - cached = block_group_cache_done(block_group); - if (unlikely(!cached)) { found_uncached_bg = true; - /* if we only want cached bgs, loop */ - if (loop == LOOP_CACHED_ONLY) + /* + * If loop is set for cached only, try the next block + * group. + */ + if (loop == LOOP_FIND_IDEAL) goto loop; } + cached = block_group_cache_done(block_group); + if (unlikely(!cached)) + found_uncached_bg = true; + if (unlikely(block_group->ro)) goto loop; @@ -4233,14 +4366,23 @@ refill_cluster: offset = btrfs_find_space_for_alloc(block_group, search_start, num_bytes, empty_size); - if (!offset && (cached || (!cached && - loop == LOOP_CACHING_NOWAIT))) { - goto loop; - } else if (!offset && (!cached && - loop > LOOP_CACHING_NOWAIT)) { + /* + * If we didn't find a chunk, and we haven't failed on this + * block group before, and this block group is in the middle of + * caching and we are ok with waiting, then go ahead and wait + * for progress to be made, and set failed_alloc to true. + * + * If failed_alloc is true then we've already waited on this + * block group once and should move on to the next block group. + */ + if (!offset && !failed_alloc && !cached && + loop > LOOP_CACHING_NOWAIT) { wait_block_group_cache_progress(block_group, - num_bytes + empty_size); + num_bytes + empty_size); + failed_alloc = true; goto have_block_group; + } else if (!offset) { + goto loop; } checks: search_start = stripe_align(root, offset); @@ -4288,13 +4430,16 @@ checks: break; loop: failed_cluster_refill = false; + failed_alloc = false; btrfs_put_block_group(block_group); } up_read(&space_info->groups_sem); - /* LOOP_CACHED_ONLY, only search fully cached block groups - * LOOP_CACHING_NOWAIT, search partially cached block groups, but - * dont wait foR them to finish caching + /* LOOP_FIND_IDEAL, only search caching/cached bg's, and don't wait for + * for them to make caching progress. Also + * determine the best possible bg to cache + * LOOP_CACHING_NOWAIT, search partially cached block groups, kicking + * caching kthreads as we move along * LOOP_CACHING_WAIT, search everything, and wait if our bg is caching * LOOP_ALLOC_CHUNK, force a chunk allocation and try again * LOOP_NO_EMPTY_SIZE, set empty_size and empty_cluster to 0 and try @@ -4303,12 +4448,47 @@ loop: if (!ins->objectid && loop < LOOP_NO_EMPTY_SIZE && (found_uncached_bg || empty_size || empty_cluster || allowed_chunk_alloc)) { - if (found_uncached_bg) { + if (loop == LOOP_FIND_IDEAL && found_uncached_bg) { found_uncached_bg = false; - if (loop < LOOP_CACHING_WAIT) { - loop++; + loop++; + if (!ideal_cache_percent && + atomic_read(&space_info->caching_threads)) goto search; - } + + /* + * 1 of the following 2 things have happened so far + * + * 1) We found an ideal block group for caching that + * is mostly full and will cache quickly, so we might + * as well wait for it. + * + * 2) We searched for cached only and we didn't find + * anything, and we didn't start any caching kthreads + * either, so chances are we will loop through and + * start a couple caching kthreads, and then come back + * around and just wait for them. This will be slower + * because we will have 2 caching kthreads reading at + * the same time when we could have just started one + * and waited for it to get far enough to give us an + * allocation, so go ahead and go to the wait caching + * loop. + */ + loop = LOOP_CACHING_WAIT; + search_start = ideal_cache_offset; + ideal_cache_percent = 0; + goto ideal_cache; + } else if (loop == LOOP_FIND_IDEAL) { + /* + * Didn't find a uncached bg, wait on anything we find + * next. + */ + loop = LOOP_CACHING_WAIT; + goto search; + } + + if (loop < LOOP_CACHING_WAIT) { + loop++; + goto search; } if (loop == LOOP_ALLOC_CHUNK) { @@ -4320,7 +4500,8 @@ loop: ret = do_chunk_alloc(trans, root, num_bytes + 2 * 1024 * 1024, data, 1); allowed_chunk_alloc = 0; - } else { + done_chunk_alloc = 1; + } else if (!done_chunk_alloc) { space_info->force_alloc = 1; } @@ -4799,6 +4980,7 @@ static noinline void reada_walk_down(struct btrfs_trans_handle *trans, u64 bytenr; u64 generation; u64 refs; + u64 flags; u64 last = 0; u32 nritems; u32 blocksize; @@ -4836,15 +5018,19 @@ static noinline void reada_walk_down(struct btrfs_trans_handle *trans, generation <= root->root_key.offset) continue; + /* We don't lock the tree block, it's OK to be racy here */ + ret = btrfs_lookup_extent_info(trans, root, bytenr, blocksize, + &refs, &flags); + BUG_ON(ret); + BUG_ON(refs == 0); + if (wc->stage == DROP_REFERENCE) { - ret = btrfs_lookup_extent_info(trans, root, - bytenr, blocksize, - &refs, NULL); - BUG_ON(ret); - BUG_ON(refs == 0); if (refs == 1) goto reada; + if (wc->level == 1 && + (flags & BTRFS_BLOCK_FLAG_FULL_BACKREF)) + continue; if (!wc->update_ref || generation <= root->root_key.offset) continue; @@ -4853,6 +5039,10 @@ static noinline void reada_walk_down(struct btrfs_trans_handle *trans, &wc->update_progress); if (ret < 0) continue; + } else { + if (wc->level == 1 && + (flags & BTRFS_BLOCK_FLAG_FULL_BACKREF)) + continue; } reada: ret = readahead_tree_block(root, bytenr, blocksize, @@ -4876,7 +5066,7 @@ reada: static noinline int walk_down_proc(struct btrfs_trans_handle *trans, struct btrfs_root *root, struct btrfs_path *path, - struct walk_control *wc) + struct walk_control *wc, int lookup_info) { int level = wc->level; struct extent_buffer *eb = path->nodes[level]; @@ -4891,8 +5081,9 @@ static noinline int walk_down_proc(struct btrfs_trans_handle *trans, * when reference count of tree block is 1, it won't increase * again. once full backref flag is set, we never clear it. */ - if ((wc->stage == DROP_REFERENCE && wc->refs[level] != 1) || - (wc->stage == UPDATE_BACKREF && !(wc->flags[level] & flag))) { + if (lookup_info && + ((wc->stage == DROP_REFERENCE && wc->refs[level] != 1) || + (wc->stage == UPDATE_BACKREF && !(wc->flags[level] & flag)))) { BUG_ON(!path->locks[level]); ret = btrfs_lookup_extent_info(trans, root, eb->start, eb->len, @@ -4953,7 +5144,7 @@ static noinline int walk_down_proc(struct btrfs_trans_handle *trans, static noinline int do_walk_down(struct btrfs_trans_handle *trans, struct btrfs_root *root, struct btrfs_path *path, - struct walk_control *wc) + struct walk_control *wc, int *lookup_info) { u64 bytenr; u64 generation; @@ -4973,8 +5164,10 @@ static noinline int do_walk_down(struct btrfs_trans_handle *trans, * for the subtree */ if (wc->stage == UPDATE_BACKREF && - generation <= root->root_key.offset) + generation <= root->root_key.offset) { + *lookup_info = 1; return 1; + } bytenr = btrfs_node_blockptr(path->nodes[level], path->slots[level]); blocksize = btrfs_level_size(root, level - 1); @@ -4987,14 +5180,19 @@ static noinline int do_walk_down(struct btrfs_trans_handle *trans, btrfs_tree_lock(next); btrfs_set_lock_blocking(next); - if (wc->stage == DROP_REFERENCE) { - ret = btrfs_lookup_extent_info(trans, root, bytenr, blocksize, - &wc->refs[level - 1], - &wc->flags[level - 1]); - BUG_ON(ret); - BUG_ON(wc->refs[level - 1] == 0); + ret = btrfs_lookup_extent_info(trans, root, bytenr, blocksize, + &wc->refs[level - 1], + &wc->flags[level - 1]); + BUG_ON(ret); + BUG_ON(wc->refs[level - 1] == 0); + *lookup_info = 0; + if (wc->stage == DROP_REFERENCE) { if (wc->refs[level - 1] > 1) { + if (level == 1 && + (wc->flags[0] & BTRFS_BLOCK_FLAG_FULL_BACKREF)) + goto skip; + if (!wc->update_ref || generation <= root->root_key.offset) goto skip; @@ -5008,12 +5206,17 @@ static noinline int do_walk_down(struct btrfs_trans_handle *trans, wc->stage = UPDATE_BACKREF; wc->shared_level = level - 1; } + } else { + if (level == 1 && + (wc->flags[0] & BTRFS_BLOCK_FLAG_FULL_BACKREF)) + goto skip; } if (!btrfs_buffer_uptodate(next, generation)) { btrfs_tree_unlock(next); free_extent_buffer(next); next = NULL; + *lookup_info = 1; } if (!next) { @@ -5036,21 +5239,22 @@ static noinline int do_walk_down(struct btrfs_trans_handle *trans, skip: wc->refs[level - 1] = 0; wc->flags[level - 1] = 0; + if (wc->stage == DROP_REFERENCE) { + if (wc->flags[level] & BTRFS_BLOCK_FLAG_FULL_BACKREF) { + parent = path->nodes[level]->start; + } else { + BUG_ON(root->root_key.objectid != + btrfs_header_owner(path->nodes[level])); + parent = 0; + } - if (wc->flags[level] & BTRFS_BLOCK_FLAG_FULL_BACKREF) { - parent = path->nodes[level]->start; - } else { - BUG_ON(root->root_key.objectid != - btrfs_header_owner(path->nodes[level])); - parent = 0; + ret = btrfs_free_extent(trans, root, bytenr, blocksize, parent, + root->root_key.objectid, level - 1, 0); + BUG_ON(ret); } - - ret = btrfs_free_extent(trans, root, bytenr, blocksize, parent, - root->root_key.objectid, level - 1, 0); - BUG_ON(ret); - btrfs_tree_unlock(next); free_extent_buffer(next); + *lookup_info = 1; return 1; } @@ -5164,6 +5368,7 @@ static noinline int walk_down_tree(struct btrfs_trans_handle *trans, struct walk_control *wc) { int level = wc->level; + int lookup_info = 1; int ret; while (level >= 0) { @@ -5171,14 +5376,14 @@ static noinline int walk_down_tree(struct btrfs_trans_handle *trans, btrfs_header_nritems(path->nodes[level])) break; - ret = walk_down_proc(trans, root, path, wc); + ret = walk_down_proc(trans, root, path, wc, lookup_info); if (ret > 0) break; if (level == 0) break; - ret = do_walk_down(trans, root, path, wc); + ret = do_walk_down(trans, root, path, wc, &lookup_info); if (ret > 0) { path->slots[level]++; continue; diff --git a/fs/btrfs/extent_io.c b/fs/btrfs/extent_io.c index de1793ba004a..96577e8bf9fd 100644 --- a/fs/btrfs/extent_io.c +++ b/fs/btrfs/extent_io.c @@ -460,7 +460,8 @@ static int clear_state_bit(struct extent_io_tree *tree, struct extent_state *state, int bits, int wake, int delete) { - int ret = state->state & bits; + int bits_to_clear = bits & ~EXTENT_DO_ACCOUNTING; + int ret = state->state & bits_to_clear; if ((bits & EXTENT_DIRTY) && (state->state & EXTENT_DIRTY)) { u64 range = state->end - state->start + 1; @@ -468,7 +469,7 @@ static int clear_state_bit(struct extent_io_tree *tree, tree->dirty_bytes -= range; } clear_state_cb(tree, state, bits); - state->state &= ~bits; + state->state &= ~bits_to_clear; if (wake) wake_up(&state->wq); if (delete || state->state == 0) { @@ -956,7 +957,8 @@ int clear_extent_dirty(struct extent_io_tree *tree, u64 start, u64 end, gfp_t mask) { return clear_extent_bit(tree, start, end, - EXTENT_DIRTY | EXTENT_DELALLOC, 0, 0, + EXTENT_DIRTY | EXTENT_DELALLOC | + EXTENT_DO_ACCOUNTING, 0, 0, NULL, mask); } @@ -1401,12 +1403,7 @@ out_failed: int extent_clear_unlock_delalloc(struct inode *inode, struct extent_io_tree *tree, u64 start, u64 end, struct page *locked_page, - int unlock_pages, - int clear_unlock, - int clear_delalloc, int clear_dirty, - int set_writeback, - int end_writeback, - int set_private2) + unsigned long op) { int ret; struct page *pages[16]; @@ -1416,17 +1413,21 @@ int extent_clear_unlock_delalloc(struct inode *inode, int i; int clear_bits = 0; - if (clear_unlock) + if (op & EXTENT_CLEAR_UNLOCK) clear_bits |= EXTENT_LOCKED; - if (clear_dirty) + if (op & EXTENT_CLEAR_DIRTY) clear_bits |= EXTENT_DIRTY; - if (clear_delalloc) + if (op & EXTENT_CLEAR_DELALLOC) clear_bits |= EXTENT_DELALLOC; + if (op & EXTENT_CLEAR_ACCOUNTING) + clear_bits |= EXTENT_DO_ACCOUNTING; + clear_extent_bit(tree, start, end, clear_bits, 1, 0, NULL, GFP_NOFS); - if (!(unlock_pages || clear_dirty || set_writeback || end_writeback || - set_private2)) + if (!(op & (EXTENT_CLEAR_UNLOCK_PAGE | EXTENT_CLEAR_DIRTY | + EXTENT_SET_WRITEBACK | EXTENT_END_WRITEBACK | + EXTENT_SET_PRIVATE2))) return 0; while (nr_pages > 0) { @@ -1435,20 +1436,20 @@ int extent_clear_unlock_delalloc(struct inode *inode, nr_pages, ARRAY_SIZE(pages)), pages); for (i = 0; i < ret; i++) { - if (set_private2) + if (op & EXTENT_SET_PRIVATE2) SetPagePrivate2(pages[i]); if (pages[i] == locked_page) { page_cache_release(pages[i]); continue; } - if (clear_dirty) + if (op & EXTENT_CLEAR_DIRTY) clear_page_dirty_for_io(pages[i]); - if (set_writeback) + if (op & EXTENT_SET_WRITEBACK) set_page_writeback(pages[i]); - if (end_writeback) + if (op & EXTENT_END_WRITEBACK) end_page_writeback(pages[i]); - if (unlock_pages) + if (op & EXTENT_CLEAR_UNLOCK_PAGE) unlock_page(pages[i]); page_cache_release(pages[i]); } @@ -2714,7 +2715,8 @@ int extent_invalidatepage(struct extent_io_tree *tree, lock_extent(tree, start, end, GFP_NOFS); wait_on_page_writeback(page); clear_extent_bit(tree, start, end, - EXTENT_LOCKED | EXTENT_DIRTY | EXTENT_DELALLOC, + EXTENT_LOCKED | EXTENT_DIRTY | EXTENT_DELALLOC | + EXTENT_DO_ACCOUNTING, 1, 1, NULL, GFP_NOFS); return 0; } diff --git a/fs/btrfs/extent_io.h b/fs/btrfs/extent_io.h index 4794ec891fed..36de250a7b2b 100644 --- a/fs/btrfs/extent_io.h +++ b/fs/btrfs/extent_io.h @@ -15,6 +15,7 @@ #define EXTENT_BUFFER_FILLED (1 << 8) #define EXTENT_BOUNDARY (1 << 9) #define EXTENT_NODATASUM (1 << 10) +#define EXTENT_DO_ACCOUNTING (1 << 11) #define EXTENT_IOBITS (EXTENT_LOCKED | EXTENT_WRITEBACK) /* flags for bio submission */ @@ -25,6 +26,16 @@ #define EXTENT_BUFFER_BLOCKING 1 #define EXTENT_BUFFER_DIRTY 2 +/* these are flags for extent_clear_unlock_delalloc */ +#define EXTENT_CLEAR_UNLOCK_PAGE 0x1 +#define EXTENT_CLEAR_UNLOCK 0x2 +#define EXTENT_CLEAR_DELALLOC 0x4 +#define EXTENT_CLEAR_DIRTY 0x8 +#define EXTENT_SET_WRITEBACK 0x10 +#define EXTENT_END_WRITEBACK 0x20 +#define EXTENT_SET_PRIVATE2 0x40 +#define EXTENT_CLEAR_ACCOUNTING 0x80 + /* * page->private values. Every page that is controlled by the extent * map has page->private set to one. @@ -288,10 +299,5 @@ int extent_range_uptodate(struct extent_io_tree *tree, int extent_clear_unlock_delalloc(struct inode *inode, struct extent_io_tree *tree, u64 start, u64 end, struct page *locked_page, - int unlock_page, - int clear_unlock, - int clear_delalloc, int clear_dirty, - int set_writeback, - int end_writeback, - int set_private2); + unsigned long op); #endif diff --git a/fs/btrfs/extent_map.c b/fs/btrfs/extent_map.c index 2c726b7b9faa..ccbdcb54ec5d 100644 --- a/fs/btrfs/extent_map.c +++ b/fs/btrfs/extent_map.c @@ -208,7 +208,7 @@ int unpin_extent_cache(struct extent_map_tree *tree, u64 start, u64 len) write_lock(&tree->lock); em = lookup_extent_mapping(tree, start, len); - WARN_ON(em->start != start || !em); + WARN_ON(!em || em->start != start); if (!em) goto out; diff --git a/fs/btrfs/file.c b/fs/btrfs/file.c index f19e1259a971..06550affbd27 100644 --- a/fs/btrfs/file.c +++ b/fs/btrfs/file.c @@ -878,7 +878,8 @@ again: btrfs_put_ordered_extent(ordered); clear_extent_bits(&BTRFS_I(inode)->io_tree, start_pos, - last_pos - 1, EXTENT_DIRTY | EXTENT_DELALLOC, + last_pos - 1, EXTENT_DIRTY | EXTENT_DELALLOC | + EXTENT_DO_ACCOUNTING, GFP_NOFS); unlock_extent(&BTRFS_I(inode)->io_tree, start_pos, last_pos - 1, GFP_NOFS); @@ -1085,8 +1086,10 @@ out_nolock: btrfs_end_transaction(trans, root); else btrfs_commit_transaction(trans, root); - } else { + } else if (ret != BTRFS_NO_LOG_SYNC) { btrfs_commit_transaction(trans, root); + } else { + btrfs_end_transaction(trans, root); } } if (file->f_flags & O_DIRECT) { @@ -1136,6 +1139,13 @@ int btrfs_sync_file(struct file *file, struct dentry *dentry, int datasync) int ret = 0; struct btrfs_trans_handle *trans; + + /* we wait first, since the writeback may change the inode */ + root->log_batch++; + /* the VFS called filemap_fdatawrite for us */ + btrfs_wait_ordered_range(inode, 0, (u64)-1); + root->log_batch++; + /* * check the transaction that last modified this inode * and see if its already been committed @@ -1143,6 +1153,11 @@ int btrfs_sync_file(struct file *file, struct dentry *dentry, int datasync) if (!BTRFS_I(inode)->last_trans) goto out; + /* + * if the last transaction that changed this file was before + * the current transaction, we can bail out now without any + * syncing + */ mutex_lock(&root->fs_info->trans_mutex); if (BTRFS_I(inode)->last_trans <= root->fs_info->last_trans_committed) { @@ -1152,13 +1167,6 @@ int btrfs_sync_file(struct file *file, struct dentry *dentry, int datasync) } mutex_unlock(&root->fs_info->trans_mutex); - root->log_batch++; - filemap_fdatawrite(inode->i_mapping); - btrfs_wait_ordered_range(inode, 0, (u64)-1); - root->log_batch++; - - if (datasync && !(inode->i_state & I_DIRTY_PAGES)) - goto out; /* * ok we haven't committed the transaction yet, lets do a commit */ @@ -1187,14 +1195,18 @@ int btrfs_sync_file(struct file *file, struct dentry *dentry, int datasync) */ mutex_unlock(&dentry->d_inode->i_mutex); - if (ret > 0) { - ret = btrfs_commit_transaction(trans, root); - } else { - ret = btrfs_sync_log(trans, root); - if (ret == 0) - ret = btrfs_end_transaction(trans, root); - else + if (ret != BTRFS_NO_LOG_SYNC) { + if (ret > 0) { ret = btrfs_commit_transaction(trans, root); + } else { + ret = btrfs_sync_log(trans, root); + if (ret == 0) + ret = btrfs_end_transaction(trans, root); + else + ret = btrfs_commit_transaction(trans, root); + } + } else { + ret = btrfs_end_transaction(trans, root); } mutex_lock(&dentry->d_inode->i_mutex); out: diff --git a/fs/btrfs/free-space-cache.c b/fs/btrfs/free-space-cache.c index 5c2caad76212..cb2849f03251 100644 --- a/fs/btrfs/free-space-cache.c +++ b/fs/btrfs/free-space-cache.c @@ -1296,7 +1296,7 @@ again: window_start = entry->offset; window_free = entry->bytes; last = entry; - max_extent = 0; + max_extent = entry->bytes; } else { last = next; window_free += next->bytes; diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 112e5aa85892..b3ad168a0bfc 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c @@ -424,9 +424,12 @@ again: * and free up our temp pages. */ extent_clear_unlock_delalloc(inode, - &BTRFS_I(inode)->io_tree, - start, end, NULL, 1, 0, - 0, 1, 1, 1, 0); + &BTRFS_I(inode)->io_tree, + start, end, NULL, + EXTENT_CLEAR_UNLOCK_PAGE | EXTENT_CLEAR_DIRTY | + EXTENT_CLEAR_DELALLOC | + EXTENT_CLEAR_ACCOUNTING | + EXTENT_SET_WRITEBACK | EXTENT_END_WRITEBACK); ret = 0; goto free_pages_out; } @@ -535,7 +538,7 @@ static noinline int submit_compressed_extents(struct inode *inode, struct btrfs_root *root = BTRFS_I(inode)->root; struct extent_map_tree *em_tree = &BTRFS_I(inode)->extent_tree; struct extent_io_tree *io_tree; - int ret; + int ret = 0; if (list_empty(&async_cow->extents)) return 0; @@ -549,6 +552,7 @@ static noinline int submit_compressed_extents(struct inode *inode, io_tree = &BTRFS_I(inode)->io_tree; +retry: /* did the compression code fall back to uncompressed IO? */ if (!async_extent->pages) { int page_started = 0; @@ -559,11 +563,11 @@ static noinline int submit_compressed_extents(struct inode *inode, async_extent->ram_size - 1, GFP_NOFS); /* allocate blocks */ - cow_file_range(inode, async_cow->locked_page, - async_extent->start, - async_extent->start + - async_extent->ram_size - 1, - &page_started, &nr_written, 0); + ret = cow_file_range(inode, async_cow->locked_page, + async_extent->start, + async_extent->start + + async_extent->ram_size - 1, + &page_started, &nr_written, 0); /* * if page_started, cow_file_range inserted an @@ -571,7 +575,7 @@ static noinline int submit_compressed_extents(struct inode *inode, * and IO for us. Otherwise, we need to submit * all those pages down to the drive. */ - if (!page_started) + if (!page_started && !ret) extent_write_locked_range(io_tree, inode, async_extent->start, async_extent->start + @@ -599,7 +603,21 @@ static noinline int submit_compressed_extents(struct inode *inode, async_extent->compressed_size, 0, alloc_hint, (u64)-1, &ins, 1); - BUG_ON(ret); + if (ret) { + int i; + for (i = 0; i < async_extent->nr_pages; i++) { + WARN_ON(async_extent->pages[i]->mapping); + page_cache_release(async_extent->pages[i]); + } + kfree(async_extent->pages); + async_extent->nr_pages = 0; + async_extent->pages = NULL; + unlock_extent(io_tree, async_extent->start, + async_extent->start + + async_extent->ram_size - 1, GFP_NOFS); + goto retry; + } + em = alloc_extent_map(GFP_NOFS); em->start = async_extent->start; em->len = async_extent->ram_size; @@ -637,11 +655,14 @@ static noinline int submit_compressed_extents(struct inode *inode, * clear dirty, set writeback and unlock the pages. */ extent_clear_unlock_delalloc(inode, - &BTRFS_I(inode)->io_tree, - async_extent->start, - async_extent->start + - async_extent->ram_size - 1, - NULL, 1, 1, 0, 1, 1, 0, 0); + &BTRFS_I(inode)->io_tree, + async_extent->start, + async_extent->start + + async_extent->ram_size - 1, + NULL, EXTENT_CLEAR_UNLOCK_PAGE | + EXTENT_CLEAR_UNLOCK | + EXTENT_CLEAR_DELALLOC | + EXTENT_CLEAR_DIRTY | EXTENT_SET_WRITEBACK); ret = btrfs_submit_compressed_write(inode, async_extent->start, @@ -712,9 +733,15 @@ static noinline int cow_file_range(struct inode *inode, start, end, 0, NULL); if (ret == 0) { extent_clear_unlock_delalloc(inode, - &BTRFS_I(inode)->io_tree, - start, end, NULL, 1, 1, - 1, 1, 1, 1, 0); + &BTRFS_I(inode)->io_tree, + start, end, NULL, + EXTENT_CLEAR_UNLOCK_PAGE | + EXTENT_CLEAR_UNLOCK | + EXTENT_CLEAR_DELALLOC | + EXTENT_CLEAR_ACCOUNTING | + EXTENT_CLEAR_DIRTY | + EXTENT_SET_WRITEBACK | + EXTENT_END_WRITEBACK); *nr_written = *nr_written + (end - start + PAGE_CACHE_SIZE) / PAGE_CACHE_SIZE; *page_started = 1; @@ -731,13 +758,29 @@ static noinline int cow_file_range(struct inode *inode, em = search_extent_mapping(&BTRFS_I(inode)->extent_tree, start, num_bytes); if (em) { - alloc_hint = em->block_start; - free_extent_map(em); + /* + * if block start isn't an actual block number then find the + * first block in this inode and use that as a hint. If that + * block is also bogus then just don't worry about it. + */ + if (em->block_start >= EXTENT_MAP_LAST_BYTE) { + free_extent_map(em); + em = search_extent_mapping(em_tree, 0, 0); + if (em && em->block_start < EXTENT_MAP_LAST_BYTE) + alloc_hint = em->block_start; + if (em) + free_extent_map(em); + } else { + alloc_hint = em->block_start; + free_extent_map(em); + } } read_unlock(&BTRFS_I(inode)->extent_tree.lock); btrfs_drop_extent_cache(inode, start, start + num_bytes - 1, 0); while (disk_num_bytes > 0) { + unsigned long op; + cur_alloc_size = min(disk_num_bytes, root->fs_info->max_extent); ret = btrfs_reserve_extent(trans, root, cur_alloc_size, root->sectorsize, 0, alloc_hint, @@ -789,10 +832,13 @@ static noinline int cow_file_range(struct inode *inode, * Do set the Private2 bit so we know this page was properly * setup for writepage */ + op = unlock ? EXTENT_CLEAR_UNLOCK_PAGE : 0; + op |= EXTENT_CLEAR_UNLOCK | EXTENT_CLEAR_DELALLOC | + EXTENT_SET_PRIVATE2; + extent_clear_unlock_delalloc(inode, &BTRFS_I(inode)->io_tree, start, start + ram_size - 1, - locked_page, unlock, 1, - 1, 0, 0, 0, 1); + locked_page, op); disk_num_bytes -= cur_alloc_size; num_bytes -= cur_alloc_size; alloc_hint = ins.objectid + ins.offset; @@ -864,8 +910,8 @@ static int cow_file_range_async(struct inode *inode, struct page *locked_page, u64 cur_end; int limit = 10 * 1024 * 1042; - clear_extent_bit(&BTRFS_I(inode)->io_tree, start, end, EXTENT_LOCKED | - EXTENT_DELALLOC, 1, 0, NULL, GFP_NOFS); + clear_extent_bit(&BTRFS_I(inode)->io_tree, start, end, EXTENT_LOCKED, + 1, 0, NULL, GFP_NOFS); while (start < end) { async_cow = kmalloc(sizeof(*async_cow), GFP_NOFS); async_cow->inode = inode; @@ -1006,6 +1052,7 @@ next_slot: if (found_key.offset > cur_offset) { extent_end = found_key.offset; + extent_type = 0; goto out_check; } @@ -1112,8 +1159,10 @@ out_check: BUG_ON(ret); extent_clear_unlock_delalloc(inode, &BTRFS_I(inode)->io_tree, - cur_offset, cur_offset + num_bytes - 1, - locked_page, 1, 1, 1, 0, 0, 0, 1); + cur_offset, cur_offset + num_bytes - 1, + locked_page, EXTENT_CLEAR_UNLOCK_PAGE | + EXTENT_CLEAR_UNLOCK | EXTENT_CLEAR_DELALLOC | + EXTENT_SET_PRIVATE2); cur_offset = extent_end; if (cur_offset > end) break; @@ -1178,15 +1227,17 @@ static int btrfs_split_extent_hook(struct inode *inode, root->fs_info->max_extent); /* - * if we break a large extent up then leave delalloc_extents be, - * since we've already accounted for the large extent. + * if we break a large extent up then leave oustanding_extents + * be, since we've already accounted for the large extent. */ if (div64_u64(new_size + root->fs_info->max_extent - 1, root->fs_info->max_extent) < num_extents) return 0; } - BTRFS_I(inode)->delalloc_extents++; + spin_lock(&BTRFS_I(inode)->accounting_lock); + BTRFS_I(inode)->outstanding_extents++; + spin_unlock(&BTRFS_I(inode)->accounting_lock); return 0; } @@ -1217,7 +1268,9 @@ static int btrfs_merge_extent_hook(struct inode *inode, /* we're not bigger than the max, unreserve the space and go */ if (new_size <= root->fs_info->max_extent) { - BTRFS_I(inode)->delalloc_extents--; + spin_lock(&BTRFS_I(inode)->accounting_lock); + BTRFS_I(inode)->outstanding_extents--; + spin_unlock(&BTRFS_I(inode)->accounting_lock); return 0; } @@ -1231,7 +1284,9 @@ static int btrfs_merge_extent_hook(struct inode *inode, root->fs_info->max_extent) > num_extents) return 0; - BTRFS_I(inode)->delalloc_extents--; + spin_lock(&BTRFS_I(inode)->accounting_lock); + BTRFS_I(inode)->outstanding_extents--; + spin_unlock(&BTRFS_I(inode)->accounting_lock); return 0; } @@ -1253,7 +1308,9 @@ static int btrfs_set_bit_hook(struct inode *inode, u64 start, u64 end, if (!(old & EXTENT_DELALLOC) && (bits & EXTENT_DELALLOC)) { struct btrfs_root *root = BTRFS_I(inode)->root; - BTRFS_I(inode)->delalloc_extents++; + spin_lock(&BTRFS_I(inode)->accounting_lock); + BTRFS_I(inode)->outstanding_extents++; + spin_unlock(&BTRFS_I(inode)->accounting_lock); btrfs_delalloc_reserve_space(root, inode, end - start + 1); spin_lock(&root->fs_info->delalloc_lock); BTRFS_I(inode)->delalloc_bytes += end - start + 1; @@ -1281,8 +1338,12 @@ static int btrfs_clear_bit_hook(struct inode *inode, if ((state->state & EXTENT_DELALLOC) && (bits & EXTENT_DELALLOC)) { struct btrfs_root *root = BTRFS_I(inode)->root; - BTRFS_I(inode)->delalloc_extents--; - btrfs_unreserve_metadata_for_delalloc(root, inode, 1); + if (bits & EXTENT_DO_ACCOUNTING) { + spin_lock(&BTRFS_I(inode)->accounting_lock); + BTRFS_I(inode)->outstanding_extents--; + spin_unlock(&BTRFS_I(inode)->accounting_lock); + btrfs_unreserve_metadata_for_delalloc(root, inode, 1); + } spin_lock(&root->fs_info->delalloc_lock); if (state->end - state->start + 1 > @@ -2442,7 +2503,19 @@ static int btrfs_unlink(struct inode *dir, struct dentry *dentry) root = BTRFS_I(dir)->root; + /* + * 5 items for unlink inode + * 1 for orphan + */ + ret = btrfs_reserve_metadata_space(root, 6); + if (ret) + return ret; + trans = btrfs_start_transaction(root, 1); + if (IS_ERR(trans)) { + btrfs_unreserve_metadata_space(root, 6); + return PTR_ERR(trans); + } btrfs_set_trans_block_group(trans, dir); @@ -2457,6 +2530,7 @@ static int btrfs_unlink(struct inode *dir, struct dentry *dentry) nr = trans->blocks_used; btrfs_end_transaction_throttle(trans, root); + btrfs_unreserve_metadata_space(root, 6); btrfs_btree_balance_dirty(root, nr); return ret; } @@ -2537,7 +2611,16 @@ static int btrfs_rmdir(struct inode *dir, struct dentry *dentry) inode->i_ino == BTRFS_FIRST_FREE_OBJECTID) return -ENOTEMPTY; + ret = btrfs_reserve_metadata_space(root, 5); + if (ret) + return ret; + trans = btrfs_start_transaction(root, 1); + if (IS_ERR(trans)) { + btrfs_unreserve_metadata_space(root, 5); + return PTR_ERR(trans); + } + btrfs_set_trans_block_group(trans, dir); if (unlikely(inode->i_ino == BTRFS_EMPTY_SUBVOL_DIR_OBJECTID)) { @@ -2560,6 +2643,7 @@ static int btrfs_rmdir(struct inode *dir, struct dentry *dentry) out: nr = trans->blocks_used; ret = btrfs_end_transaction_throttle(trans, root); + btrfs_unreserve_metadata_space(root, 5); btrfs_btree_balance_dirty(root, nr); if (ret && !err) @@ -3000,12 +3084,22 @@ static int btrfs_truncate_page(struct address_space *mapping, loff_t from) if ((offset & (blocksize - 1)) == 0) goto out; + ret = btrfs_check_data_free_space(root, inode, PAGE_CACHE_SIZE); + if (ret) + goto out; + + ret = btrfs_reserve_metadata_for_delalloc(root, inode, 1); + if (ret) + goto out; ret = -ENOMEM; again: page = grab_cache_page(mapping, index); - if (!page) + if (!page) { + btrfs_free_reserved_data_space(root, inode, PAGE_CACHE_SIZE); + btrfs_unreserve_metadata_for_delalloc(root, inode, 1); goto out; + } page_start = page_offset(page); page_end = page_start + PAGE_CACHE_SIZE - 1; @@ -3038,6 +3132,10 @@ again: goto again; } + clear_extent_bits(&BTRFS_I(inode)->io_tree, page_start, page_end, + EXTENT_DIRTY | EXTENT_DELALLOC | EXTENT_DO_ACCOUNTING, + GFP_NOFS); + ret = btrfs_set_extent_delalloc(inode, page_start, page_end); if (ret) { unlock_extent(io_tree, page_start, page_end, GFP_NOFS); @@ -3056,6 +3154,9 @@ again: unlock_extent(io_tree, page_start, page_end, GFP_NOFS); out_unlock: + if (ret) + btrfs_free_reserved_data_space(root, inode, PAGE_CACHE_SIZE); + btrfs_unreserve_metadata_for_delalloc(root, inode, 1); unlock_page(page); page_cache_release(page); out: @@ -3079,7 +3180,9 @@ int btrfs_cont_expand(struct inode *inode, loff_t size) if (size <= hole_start) return 0; - btrfs_truncate_page(inode->i_mapping, inode->i_size); + err = btrfs_truncate_page(inode->i_mapping, inode->i_size); + if (err) + return err; while (1) { struct btrfs_ordered_extent *ordered; @@ -3448,6 +3551,7 @@ static noinline void init_btrfs_i(struct inode *inode) bi->generation = 0; bi->sequence = 0; bi->last_trans = 0; + bi->last_sub_trans = 0; bi->logged_trans = 0; bi->delalloc_bytes = 0; bi->reserved_bytes = 0; @@ -3598,12 +3702,14 @@ static int btrfs_dentry_delete(struct dentry *dentry) { struct btrfs_root *root; - if (!dentry->d_inode) - return 0; + if (!dentry->d_inode && !IS_ROOT(dentry)) + dentry = dentry->d_parent; - root = BTRFS_I(dentry->d_inode)->root; - if (btrfs_root_refs(&root->root_item) == 0) - return 1; + if (dentry->d_inode) { + root = BTRFS_I(dentry->d_inode)->root; + if (btrfs_root_refs(&root->root_item) == 0) + return 1; + } return 0; } @@ -4808,7 +4914,8 @@ static void btrfs_invalidatepage(struct page *page, unsigned long offset) */ clear_extent_bit(tree, page_start, page_end, EXTENT_DIRTY | EXTENT_DELALLOC | - EXTENT_LOCKED, 1, 0, NULL, GFP_NOFS); + EXTENT_LOCKED | EXTENT_DO_ACCOUNTING, 1, 0, + NULL, GFP_NOFS); /* * whoever cleared the private bit is responsible * for the finish_ordered_io @@ -4821,8 +4928,8 @@ static void btrfs_invalidatepage(struct page *page, unsigned long offset) lock_extent(tree, page_start, page_end, GFP_NOFS); } clear_extent_bit(tree, page_start, page_end, - EXTENT_LOCKED | EXTENT_DIRTY | EXTENT_DELALLOC, - 1, 1, NULL, GFP_NOFS); + EXTENT_LOCKED | EXTENT_DIRTY | EXTENT_DELALLOC | + EXTENT_DO_ACCOUNTING, 1, 1, NULL, GFP_NOFS); __btrfs_releasepage(page, GFP_NOFS); ClearPageChecked(page); @@ -4917,7 +5024,8 @@ again: * prepare_pages in the normal write path. */ clear_extent_bits(&BTRFS_I(inode)->io_tree, page_start, page_end, - EXTENT_DIRTY | EXTENT_DELALLOC, GFP_NOFS); + EXTENT_DIRTY | EXTENT_DELALLOC | EXTENT_DO_ACCOUNTING, + GFP_NOFS); ret = btrfs_set_extent_delalloc(inode, page_start, page_end); if (ret) { @@ -4944,7 +5052,9 @@ again: set_page_dirty(page); SetPageUptodate(page); - BTRFS_I(inode)->last_trans = root->fs_info->generation + 1; + BTRFS_I(inode)->last_trans = root->fs_info->generation; + BTRFS_I(inode)->last_sub_trans = BTRFS_I(inode)->root->log_transid; + unlock_extent(io_tree, page_start, page_end, GFP_NOFS); out_unlock: @@ -4969,7 +5079,9 @@ static void btrfs_truncate(struct inode *inode) if (IS_APPEND(inode) || IS_IMMUTABLE(inode)) return; - btrfs_truncate_page(inode->i_mapping, inode->i_size); + ret = btrfs_truncate_page(inode->i_mapping, inode->i_size); + if (ret) + return; btrfs_wait_ordered_range(inode, inode->i_size & (~mask), (u64)-1); trans = btrfs_start_transaction(root, 1); @@ -5064,9 +5176,12 @@ struct inode *btrfs_alloc_inode(struct super_block *sb) if (!ei) return NULL; ei->last_trans = 0; + ei->last_sub_trans = 0; ei->logged_trans = 0; - ei->delalloc_extents = 0; - ei->delalloc_reserved_extents = 0; + ei->outstanding_extents = 0; + ei->reserved_extents = 0; + ei->root = NULL; + spin_lock_init(&ei->accounting_lock); btrfs_ordered_inode_tree_init(&ei->ordered_tree); INIT_LIST_HEAD(&ei->i_orphan); INIT_LIST_HEAD(&ei->ordered_operations); @@ -5082,6 +5197,14 @@ void btrfs_destroy_inode(struct inode *inode) WARN_ON(inode->i_data.nrpages); /* + * This can happen where we create an inode, but somebody else also + * created the same inode and we need to destroy the one we already + * created. + */ + if (!root) + goto free; + + /* * Make sure we're properly removed from the ordered operation * lists. */ @@ -5116,6 +5239,7 @@ void btrfs_destroy_inode(struct inode *inode) } inode_tree_del(inode); btrfs_drop_extent_cache(inode, 0, (u64)-1, 0); +free: kmem_cache_free(btrfs_inode_cachep, BTRFS_I(inode)); } @@ -5221,11 +5345,14 @@ static int btrfs_rename(struct inode *old_dir, struct dentry *old_dentry, return -ENOTEMPTY; /* - * 2 items for dir items - * 1 item for orphan entry - * 1 item for ref + * We want to reserve the absolute worst case amount of items. So if + * both inodes are subvols and we need to unlink them then that would + * require 4 item modifications, but if they are both normal inodes it + * would require 5 item modifications, so we'll assume their normal + * inodes. So 5 * 2 is 10, plus 1 for the new link, so 11 total items + * should cover the worst case number of items we'll modify. */ - ret = btrfs_reserve_metadata_space(root, 4); + ret = btrfs_reserve_metadata_space(root, 11); if (ret) return ret; @@ -5341,7 +5468,7 @@ out_fail: if (old_inode->i_ino == BTRFS_FIRST_FREE_OBJECTID) up_read(&root->fs_info->subvol_sem); - btrfs_unreserve_metadata_space(root, 4); + btrfs_unreserve_metadata_space(root, 11); return ret; } @@ -5805,6 +5932,6 @@ static const struct inode_operations btrfs_symlink_inode_operations = { .removexattr = btrfs_removexattr, }; -struct dentry_operations btrfs_dentry_operations = { +const struct dentry_operations btrfs_dentry_operations = { .d_delete = btrfs_dentry_delete, }; diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c index 9a780c8d0ac8..cdbb054102b9 100644 --- a/fs/btrfs/ioctl.c +++ b/fs/btrfs/ioctl.c @@ -830,6 +830,7 @@ out_up_write: out_unlock: mutex_unlock(&inode->i_mutex); if (!err) { + shrink_dcache_sb(root->fs_info->sb); btrfs_invalidate_inodes(dest); d_delete(dentry); } @@ -1122,8 +1123,10 @@ static noinline long btrfs_ioctl_clone(struct file *file, unsigned long srcfd, datao += off - key.offset; datal -= off - key.offset; } - if (key.offset + datao + datal > off + len) - datal = off + len - key.offset - datao; + + if (key.offset + datal > off + len) + datal = off + len - key.offset; + /* disko == 0 means it's a hole */ if (!disko) datao = 0; diff --git a/fs/btrfs/ordered-data.c b/fs/btrfs/ordered-data.c index 897fba835f89..5799bc46a309 100644 --- a/fs/btrfs/ordered-data.c +++ b/fs/btrfs/ordered-data.c @@ -306,6 +306,12 @@ int btrfs_remove_ordered_extent(struct inode *inode, tree->last = NULL; set_bit(BTRFS_ORDERED_COMPLETE, &entry->flags); + spin_lock(&BTRFS_I(inode)->accounting_lock); + BTRFS_I(inode)->outstanding_extents--; + spin_unlock(&BTRFS_I(inode)->accounting_lock); + btrfs_unreserve_metadata_for_delalloc(BTRFS_I(inode)->root, + inode, 1); + spin_lock(&BTRFS_I(inode)->root->fs_info->ordered_extent_lock); list_del_init(&entry->root_extent_list); diff --git a/fs/btrfs/relocation.c b/fs/btrfs/relocation.c index 361ad323faac..cfcc93c93a7b 100644 --- a/fs/btrfs/relocation.c +++ b/fs/btrfs/relocation.c @@ -3518,7 +3518,7 @@ int btrfs_relocate_block_group(struct btrfs_root *extent_root, u64 group_start) BUG_ON(!rc->block_group); btrfs_init_workers(&rc->workers, "relocate", - fs_info->thread_pool_size); + fs_info->thread_pool_size, NULL); rc->extent_root = extent_root; btrfs_prepare_block_group_relocation(extent_root, rc->block_group); @@ -3701,7 +3701,7 @@ int btrfs_recover_relocation(struct btrfs_root *root) mapping_tree_init(&rc->reloc_root_tree); INIT_LIST_HEAD(&rc->reloc_roots); btrfs_init_workers(&rc->workers, "relocate", - root->fs_info->thread_pool_size); + root->fs_info->thread_pool_size, NULL); rc->extent_root = root->fs_info->extent_root; set_reloc_control(rc); diff --git a/fs/btrfs/root-tree.c b/fs/btrfs/root-tree.c index 9351428f30e2..67fa2d29d663 100644 --- a/fs/btrfs/root-tree.c +++ b/fs/btrfs/root-tree.c @@ -159,7 +159,6 @@ int btrfs_update_root(struct btrfs_trans_handle *trans, struct btrfs_root write_extent_buffer(l, item, ptr, sizeof(*item)); btrfs_mark_buffer_dirty(path->nodes[0]); out: - btrfs_release_path(root, path); btrfs_free_path(path); return ret; } @@ -332,7 +331,6 @@ int btrfs_del_root(struct btrfs_trans_handle *trans, struct btrfs_root *root, BUG_ON(refs != 0); ret = btrfs_del_item(trans, root, path); out: - btrfs_release_path(root, path); btrfs_free_path(path); return ret; } diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c index 9de9b2236419..752a5463bf53 100644 --- a/fs/btrfs/super.c +++ b/fs/btrfs/super.c @@ -66,7 +66,8 @@ enum { Opt_degraded, Opt_subvol, Opt_device, Opt_nodatasum, Opt_nodatacow, Opt_max_extent, Opt_max_inline, Opt_alloc_start, Opt_nobarrier, Opt_ssd, Opt_nossd, Opt_ssd_spread, Opt_thread_pool, Opt_noacl, - Opt_compress, Opt_notreelog, Opt_ratio, Opt_flushoncommit, Opt_err, + Opt_compress, Opt_notreelog, Opt_ratio, Opt_flushoncommit, + Opt_discard, Opt_err, }; static match_table_t tokens = { @@ -88,6 +89,7 @@ static match_table_t tokens = { {Opt_notreelog, "notreelog"}, {Opt_flushoncommit, "flushoncommit"}, {Opt_ratio, "metadata_ratio=%d"}, + {Opt_discard, "discard"}, {Opt_err, NULL}, }; @@ -257,6 +259,9 @@ int btrfs_parse_options(struct btrfs_root *root, char *options) info->metadata_ratio); } break; + case Opt_discard: + btrfs_set_opt(info->mount_opt, DISCARD); + break; default: break; } @@ -344,7 +349,7 @@ static int btrfs_fill_super(struct super_block *sb, sb->s_export_op = &btrfs_export_ops; sb->s_xattr = btrfs_xattr_handlers; sb->s_time_gran = 1; -#ifdef CONFIG_BTRFS_POSIX_ACL +#ifdef CONFIG_BTRFS_FS_POSIX_ACL sb->s_flags |= MS_POSIXACL; #endif diff --git a/fs/btrfs/transaction.c b/fs/btrfs/transaction.c index 0b8f36d4400a..c207e8c32c9b 100644 --- a/fs/btrfs/transaction.c +++ b/fs/btrfs/transaction.c @@ -163,8 +163,14 @@ static void wait_current_trans(struct btrfs_root *root) } } +enum btrfs_trans_type { + TRANS_START, + TRANS_JOIN, + TRANS_USERSPACE, +}; + static struct btrfs_trans_handle *start_transaction(struct btrfs_root *root, - int num_blocks, int wait) + int num_blocks, int type) { struct btrfs_trans_handle *h = kmem_cache_alloc(btrfs_trans_handle_cachep, GFP_NOFS); @@ -172,7 +178,8 @@ static struct btrfs_trans_handle *start_transaction(struct btrfs_root *root, mutex_lock(&root->fs_info->trans_mutex); if (!root->fs_info->log_root_recovering && - ((wait == 1 && !root->fs_info->open_ioctl_trans) || wait == 2)) + ((type == TRANS_START && !root->fs_info->open_ioctl_trans) || + type == TRANS_USERSPACE)) wait_current_trans(root); ret = join_transaction(root); BUG_ON(ret); @@ -186,7 +193,7 @@ static struct btrfs_trans_handle *start_transaction(struct btrfs_root *root, h->alloc_exclude_start = 0; h->delayed_ref_updates = 0; - if (!current->journal_info) + if (!current->journal_info && type != TRANS_USERSPACE) current->journal_info = h; root->fs_info->running_transaction->use_count++; @@ -198,18 +205,18 @@ static struct btrfs_trans_handle *start_transaction(struct btrfs_root *root, struct btrfs_trans_handle *btrfs_start_transaction(struct btrfs_root *root, int num_blocks) { - return start_transaction(root, num_blocks, 1); + return start_transaction(root, num_blocks, TRANS_START); } struct btrfs_trans_handle *btrfs_join_transaction(struct btrfs_root *root, int num_blocks) { - return start_transaction(root, num_blocks, 0); + return start_transaction(root, num_blocks, TRANS_JOIN); } struct btrfs_trans_handle *btrfs_start_ioctl_transaction(struct btrfs_root *r, int num_blocks) { - return start_transaction(r, num_blocks, 2); + return start_transaction(r, num_blocks, TRANS_USERSPACE); } /* wait for a transaction commit to be fully complete */ @@ -344,10 +351,10 @@ int btrfs_end_transaction_throttle(struct btrfs_trans_handle *trans, /* * when btree blocks are allocated, they have some corresponding bits set for * them in one of two extent_io trees. This is used to make sure all of - * those extents are on disk for transaction or log commit + * those extents are sent to disk but does not wait on them */ -int btrfs_write_and_wait_marked_extents(struct btrfs_root *root, - struct extent_io_tree *dirty_pages) +int btrfs_write_marked_extents(struct btrfs_root *root, + struct extent_io_tree *dirty_pages) { int ret; int err = 0; @@ -394,6 +401,29 @@ int btrfs_write_and_wait_marked_extents(struct btrfs_root *root, page_cache_release(page); } } + if (err) + werr = err; + return werr; +} + +/* + * when btree blocks are allocated, they have some corresponding bits set for + * them in one of two extent_io trees. This is used to make sure all of + * those extents are on disk for transaction or log commit. We wait + * on all the pages and clear them from the dirty pages state tree + */ +int btrfs_wait_marked_extents(struct btrfs_root *root, + struct extent_io_tree *dirty_pages) +{ + int ret; + int err = 0; + int werr = 0; + struct page *page; + struct inode *btree_inode = root->fs_info->btree_inode; + u64 start = 0; + u64 end; + unsigned long index; + while (1) { ret = find_first_extent_bit(dirty_pages, 0, &start, &end, EXTENT_DIRTY); @@ -424,6 +454,22 @@ int btrfs_write_and_wait_marked_extents(struct btrfs_root *root, return werr; } +/* + * when btree blocks are allocated, they have some corresponding bits set for + * them in one of two extent_io trees. This is used to make sure all of + * those extents are on disk for transaction or log commit + */ +int btrfs_write_and_wait_marked_extents(struct btrfs_root *root, + struct extent_io_tree *dirty_pages) +{ + int ret; + int ret2; + + ret = btrfs_write_marked_extents(root, dirty_pages); + ret2 = btrfs_wait_marked_extents(root, dirty_pages); + return ret || ret2; +} + int btrfs_write_and_wait_transaction(struct btrfs_trans_handle *trans, struct btrfs_root *root) { diff --git a/fs/btrfs/transaction.h b/fs/btrfs/transaction.h index 663c67404918..d4e3e7a6938c 100644 --- a/fs/btrfs/transaction.h +++ b/fs/btrfs/transaction.h @@ -79,6 +79,7 @@ static inline void btrfs_set_inode_last_trans(struct btrfs_trans_handle *trans, struct inode *inode) { BTRFS_I(inode)->last_trans = trans->transaction->transid; + BTRFS_I(inode)->last_sub_trans = BTRFS_I(inode)->root->log_transid; } int btrfs_end_transaction(struct btrfs_trans_handle *trans, @@ -107,5 +108,9 @@ int btrfs_record_root_in_trans(struct btrfs_trans_handle *trans, struct btrfs_root *root); int btrfs_write_and_wait_marked_extents(struct btrfs_root *root, struct extent_io_tree *dirty_pages); +int btrfs_write_marked_extents(struct btrfs_root *root, + struct extent_io_tree *dirty_pages); +int btrfs_wait_marked_extents(struct btrfs_root *root, + struct extent_io_tree *dirty_pages); int btrfs_transaction_in_commit(struct btrfs_fs_info *info); #endif diff --git a/fs/btrfs/tree-log.c b/fs/btrfs/tree-log.c index 7827841b55cb..741666a7676a 100644 --- a/fs/btrfs/tree-log.c +++ b/fs/btrfs/tree-log.c @@ -137,11 +137,20 @@ static int start_log_trans(struct btrfs_trans_handle *trans, mutex_lock(&root->log_mutex); if (root->log_root) { + if (!root->log_start_pid) { + root->log_start_pid = current->pid; + root->log_multiple_pids = false; + } else if (root->log_start_pid != current->pid) { + root->log_multiple_pids = true; + } + root->log_batch++; atomic_inc(&root->log_writers); mutex_unlock(&root->log_mutex); return 0; } + root->log_multiple_pids = false; + root->log_start_pid = current->pid; mutex_lock(&root->fs_info->tree_log_mutex); if (!root->fs_info->log_root_tree) { ret = btrfs_init_log_root_tree(trans, root->fs_info); @@ -1971,6 +1980,7 @@ int btrfs_sync_log(struct btrfs_trans_handle *trans, int ret; struct btrfs_root *log = root->log_root; struct btrfs_root *log_root_tree = root->fs_info->log_root_tree; + u64 log_transid = 0; mutex_lock(&root->log_mutex); index1 = root->log_transid % 2; @@ -1987,10 +1997,11 @@ int btrfs_sync_log(struct btrfs_trans_handle *trans, while (1) { unsigned long batch = root->log_batch; - mutex_unlock(&root->log_mutex); - schedule_timeout_uninterruptible(1); - mutex_lock(&root->log_mutex); - + if (root->log_multiple_pids) { + mutex_unlock(&root->log_mutex); + schedule_timeout_uninterruptible(1); + mutex_lock(&root->log_mutex); + } wait_for_writer(trans, root); if (batch == root->log_batch) break; @@ -2003,14 +2014,19 @@ int btrfs_sync_log(struct btrfs_trans_handle *trans, goto out; } - ret = btrfs_write_and_wait_marked_extents(log, &log->dirty_log_pages); + /* we start IO on all the marked extents here, but we don't actually + * wait for them until later. + */ + ret = btrfs_write_marked_extents(log, &log->dirty_log_pages); BUG_ON(ret); btrfs_set_root_node(&log->root_item, log->node); root->log_batch = 0; + log_transid = root->log_transid; root->log_transid++; log->log_transid = root->log_transid; + root->log_start_pid = 0; smp_mb(); /* * log tree has been flushed to disk, new modifications of @@ -2036,6 +2052,7 @@ int btrfs_sync_log(struct btrfs_trans_handle *trans, index2 = log_root_tree->log_transid % 2; if (atomic_read(&log_root_tree->log_commit[index2])) { + btrfs_wait_marked_extents(log, &log->dirty_log_pages); wait_log_commit(trans, log_root_tree, log_root_tree->log_transid); mutex_unlock(&log_root_tree->log_mutex); @@ -2055,6 +2072,7 @@ int btrfs_sync_log(struct btrfs_trans_handle *trans, * check the full commit flag again */ if (root->fs_info->last_trans_log_full_commit == trans->transid) { + btrfs_wait_marked_extents(log, &log->dirty_log_pages); mutex_unlock(&log_root_tree->log_mutex); ret = -EAGAIN; goto out_wake_log_root; @@ -2063,6 +2081,7 @@ int btrfs_sync_log(struct btrfs_trans_handle *trans, ret = btrfs_write_and_wait_marked_extents(log_root_tree, &log_root_tree->dirty_log_pages); BUG_ON(ret); + btrfs_wait_marked_extents(log, &log->dirty_log_pages); btrfs_set_super_log_root(&root->fs_info->super_for_commit, log_root_tree->node->start); @@ -2082,9 +2101,14 @@ int btrfs_sync_log(struct btrfs_trans_handle *trans, * the running transaction open, so a full commit can't hop * in and cause problems either. */ - write_ctree_super(trans, root->fs_info->tree_root, 2); + write_ctree_super(trans, root->fs_info->tree_root, 1); ret = 0; + mutex_lock(&root->log_mutex); + if (root->last_log_commit < log_transid) + root->last_log_commit = log_transid; + mutex_unlock(&root->log_mutex); + out_wake_log_root: atomic_set(&log_root_tree->log_commit[index2], 0); smp_mb(); @@ -2852,6 +2876,21 @@ out: return ret; } +static int inode_in_log(struct btrfs_trans_handle *trans, + struct inode *inode) +{ + struct btrfs_root *root = BTRFS_I(inode)->root; + int ret = 0; + + mutex_lock(&root->log_mutex); + if (BTRFS_I(inode)->logged_trans == trans->transid && + BTRFS_I(inode)->last_sub_trans <= root->last_log_commit) + ret = 1; + mutex_unlock(&root->log_mutex); + return ret; +} + + /* * helper function around btrfs_log_inode to make sure newly created * parent directories also end up in the log. A minimal inode and backref @@ -2891,6 +2930,11 @@ int btrfs_log_inode_parent(struct btrfs_trans_handle *trans, if (ret) goto end_no_trans; + if (inode_in_log(trans, inode)) { + ret = BTRFS_NO_LOG_SYNC; + goto end_no_trans; + } + start_log_trans(trans, root); ret = btrfs_log_inode(trans, root, inode, inode_only); diff --git a/fs/btrfs/tree-log.h b/fs/btrfs/tree-log.h index d09c7609e16b..0776eacb5083 100644 --- a/fs/btrfs/tree-log.h +++ b/fs/btrfs/tree-log.h @@ -19,6 +19,9 @@ #ifndef __TREE_LOG_ #define __TREE_LOG_ +/* return value for btrfs_log_dentry_safe that means we don't need to log it at all */ +#define BTRFS_NO_LOG_SYNC 256 + int btrfs_sync_log(struct btrfs_trans_handle *trans, struct btrfs_root *root); int btrfs_free_log(struct btrfs_trans_handle *trans, struct btrfs_root *root); diff --git a/fs/btrfs/xattr.c b/fs/btrfs/xattr.c index b0fc93f95fd0..b6dd5967c48a 100644 --- a/fs/btrfs/xattr.c +++ b/fs/btrfs/xattr.c @@ -260,7 +260,7 @@ err: * attributes are handled directly. */ struct xattr_handler *btrfs_xattr_handlers[] = { -#ifdef CONFIG_BTRFS_POSIX_ACL +#ifdef CONFIG_BTRFS_FS_POSIX_ACL &btrfs_xattr_acl_access_handler, &btrfs_xattr_acl_default_handler, #endif diff --git a/fs/cifs/cifsproto.h b/fs/cifs/cifsproto.h index 6928c24d1d42..5646727e33f5 100644 --- a/fs/cifs/cifsproto.h +++ b/fs/cifs/cifsproto.h @@ -388,4 +388,5 @@ extern int CIFSSMBSetPosixACL(const int xid, struct cifsTconInfo *tcon, const struct nls_table *nls_codepage, int remap_special_chars); extern int CIFSGetExtAttr(const int xid, struct cifsTconInfo *tcon, const int netfid, __u64 *pExtAttrBits, __u64 *pMask); +extern void cifs_autodisable_serverino(struct cifs_sb_info *cifs_sb); #endif /* _CIFSPROTO_H */ diff --git a/fs/cifs/connect.c b/fs/cifs/connect.c index 43003e0bef18..63ea83ff687f 100644 --- a/fs/cifs/connect.c +++ b/fs/cifs/connect.c @@ -1577,7 +1577,8 @@ cifs_get_tcp_session(struct smb_vol *volume_info) out_err: if (tcp_ses) { - kfree(tcp_ses->hostname); + if (!IS_ERR(tcp_ses->hostname)) + kfree(tcp_ses->hostname); if (tcp_ses->ssocket) sock_release(tcp_ses->ssocket); kfree(tcp_ses); @@ -2219,16 +2220,8 @@ is_path_accessible(int xid, struct cifsTconInfo *tcon, struct cifs_sb_info *cifs_sb, const char *full_path) { int rc; - __u64 inode_num; FILE_ALL_INFO *pfile_info; - rc = CIFSGetSrvInodeNumber(xid, tcon, full_path, &inode_num, - cifs_sb->local_nls, - cifs_sb->mnt_cifs_flags & - CIFS_MOUNT_MAP_SPECIAL_CHR); - if (rc != -EOPNOTSUPP) - return rc; - pfile_info = kmalloc(sizeof(FILE_ALL_INFO), GFP_KERNEL); if (pfile_info == NULL) return -ENOMEM; diff --git a/fs/cifs/inode.c b/fs/cifs/inode.c index 5e2492535daa..cababd8a52df 100644 --- a/fs/cifs/inode.c +++ b/fs/cifs/inode.c @@ -512,13 +512,10 @@ int cifs_get_inode_info(struct inode **pinode, cifs_sb->local_nls, cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MAP_SPECIAL_CHR); - if (rc1) { + if (rc1 || !fattr.cf_uniqueid) { cFYI(1, ("GetSrvInodeNum rc %d", rc1)); fattr.cf_uniqueid = iunique(sb, ROOT_I); - /* disable serverino if call not supported */ - if (rc1 == -EINVAL) - cifs_sb->mnt_cifs_flags &= - ~CIFS_MOUNT_SERVER_INUM; + cifs_autodisable_serverino(cifs_sb); } } else { fattr.cf_uniqueid = iunique(sb, ROOT_I); diff --git a/fs/cifs/misc.c b/fs/cifs/misc.c index 0241b25ac33f..d27d4ec6579b 100644 --- a/fs/cifs/misc.c +++ b/fs/cifs/misc.c @@ -715,3 +715,17 @@ cifsConvertToUCS(__le16 *target, const char *source, int maxlen, ctoUCS_out: return i; } + +void +cifs_autodisable_serverino(struct cifs_sb_info *cifs_sb) +{ + if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SERVER_INUM) { + cifs_sb->mnt_cifs_flags &= ~CIFS_MOUNT_SERVER_INUM; + cERROR(1, ("Autodisabling the use of server inode numbers on " + "%s. This server doesn't seem to support them " + "properly. Hardlinks will not be recognized on this " + "mount. Consider mounting with the \"noserverino\" " + "option to silence this message.", + cifs_sb->tcon->treeName)); + } +} diff --git a/fs/cifs/readdir.c b/fs/cifs/readdir.c index 1f098ca71636..f84062f9a985 100644 --- a/fs/cifs/readdir.c +++ b/fs/cifs/readdir.c @@ -727,11 +727,12 @@ static int cifs_filldir(char *pfindEntry, struct file *file, filldir_t filldir, cifs_dir_info_to_fattr(&fattr, (FILE_DIRECTORY_INFO *) pfindEntry, cifs_sb); - /* FIXME: make _to_fattr functions fill this out */ - if (pCifsF->srch_inf.info_level == SMB_FIND_FILE_ID_FULL_DIR_INFO) + if (inum && (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SERVER_INUM)) { fattr.cf_uniqueid = inum; - else + } else { fattr.cf_uniqueid = iunique(sb, ROOT_I); + cifs_autodisable_serverino(cifs_sb); + } ino = cifs_uniqueid_to_ino_t(fattr.cf_uniqueid); tmp_dentry = cifs_readdir_lookup(file->f_dentry, &qstring, &fattr); diff --git a/fs/compat.c b/fs/compat.c index d576b552e8e2..6c19040ffeef 100644 --- a/fs/compat.c +++ b/fs/compat.c @@ -1532,6 +1532,8 @@ int compat_do_execve(char * filename, if (retval < 0) goto out; + current->stack_start = current->mm->start_stack; + /* execve succeeded */ current->fs->in_exec = 0; current->in_execve = 0; diff --git a/fs/compat_ioctl.c b/fs/compat_ioctl.c index cacf8a83e394..229e72218165 100644 --- a/fs/compat_ioctl.c +++ b/fs/compat_ioctl.c @@ -1199,7 +1199,7 @@ struct space_resv_32 { /* just account for different alignment */ static int compat_ioctl_preallocate(struct file *file, unsigned long arg) { - struct space_resv_32 __user *p32 = (void __user *)arg; + struct space_resv_32 __user *p32 = compat_ptr(arg); struct space_resv __user *p = compat_alloc_user_space(sizeof(*p)); if (copy_in_user(&p->l_type, &p32->l_type, sizeof(s16)) || @@ -2063,7 +2063,7 @@ asmlinkage long compat_sys_ioctl(unsigned int fd, unsigned int cmd, #else case FS_IOC_RESVSP: case FS_IOC_RESVSP64: - error = ioctl_preallocate(filp, (void __user *)arg); + error = ioctl_preallocate(filp, compat_ptr(arg)); goto out_fput; #endif diff --git a/fs/dlm/lowcomms.c b/fs/dlm/lowcomms.c index 240cef14fe58..70736eb4b516 100644 --- a/fs/dlm/lowcomms.c +++ b/fs/dlm/lowcomms.c @@ -316,6 +316,10 @@ int dlm_lowcomms_connect_node(int nodeid) { struct connection *con; + /* with sctp there's no connecting without sending */ + if (dlm_config.ci_protocol != 0) + return 0; + if (nodeid == dlm_our_nodeid()) return 0; @@ -455,9 +459,9 @@ static void process_sctp_notification(struct connection *con, int prim_len, ret; int addr_len; struct connection *new_con; - struct file *file; sctp_peeloff_arg_t parg; int parglen = sizeof(parg); + int err; /* * We get this before any data for an association. @@ -512,19 +516,22 @@ static void process_sctp_notification(struct connection *con, ret = kernel_getsockopt(con->sock, IPPROTO_SCTP, SCTP_SOCKOPT_PEELOFF, (void *)&parg, &parglen); - if (ret) { + if (ret < 0) { log_print("Can't peel off a socket for " - "connection %d to node %d: err=%d\n", + "connection %d to node %d: err=%d", parg.associd, nodeid, ret); + return; + } + new_con->sock = sockfd_lookup(parg.sd, &err); + if (!new_con->sock) { + log_print("sockfd_lookup error %d", err); + return; } - file = fget(parg.sd); - new_con->sock = SOCKET_I(file->f_dentry->d_inode); add_sock(new_con->sock, new_con); - fput(file); - put_unused_fd(parg.sd); + sockfd_put(new_con->sock); - log_print("got new/restarted association %d nodeid %d", - (int)sn->sn_assoc_change.sac_assoc_id, nodeid); + log_print("connecting to %d sctp association %d", + nodeid, (int)sn->sn_assoc_change.sac_assoc_id); /* Send any pending writes */ clear_bit(CF_CONNECT_PENDING, &new_con->flags); @@ -837,8 +844,6 @@ static void sctp_init_assoc(struct connection *con) if (con->retries++ > MAX_CONNECT_RETRIES) return; - log_print("Initiating association with node %d", con->nodeid); - if (nodeid_to_addr(con->nodeid, (struct sockaddr *)&rem_addr)) { log_print("no address for nodeid %d", con->nodeid); return; @@ -855,11 +860,14 @@ static void sctp_init_assoc(struct connection *con) outmessage.msg_flags = MSG_EOR; spin_lock(&con->writequeue_lock); - e = list_entry(con->writequeue.next, struct writequeue_entry, - list); - BUG_ON((struct list_head *) e == &con->writequeue); + if (list_empty(&con->writequeue)) { + spin_unlock(&con->writequeue_lock); + log_print("writequeue empty for nodeid %d", con->nodeid); + return; + } + e = list_first_entry(&con->writequeue, struct writequeue_entry, list); len = e->len; offset = e->offset; spin_unlock(&con->writequeue_lock); diff --git a/fs/ecryptfs/Kconfig b/fs/ecryptfs/Kconfig index 8aadb99b7634..1cd6d9d3e29a 100644 --- a/fs/ecryptfs/Kconfig +++ b/fs/ecryptfs/Kconfig @@ -1,8 +1,9 @@ config ECRYPT_FS tristate "eCrypt filesystem layer support (EXPERIMENTAL)" - depends on EXPERIMENTAL && KEYS && NET + depends on EXPERIMENTAL && KEYS && CRYPTO select CRYPTO_ECB select CRYPTO_CBC + select CRYPTO_MD5 help Encrypted filesystem that operates on the VFS layer. See <file:Documentation/filesystems/ecryptfs.txt> to learn more about diff --git a/fs/ecryptfs/main.c b/fs/ecryptfs/main.c index 101fe4c7b1ee..c6ac85d6c701 100644 --- a/fs/ecryptfs/main.c +++ b/fs/ecryptfs/main.c @@ -35,6 +35,7 @@ #include <linux/key.h> #include <linux/parser.h> #include <linux/fs_stack.h> +#include <linux/ima.h> #include "ecryptfs_kernel.h" /** @@ -118,6 +119,7 @@ int ecryptfs_init_persistent_file(struct dentry *ecryptfs_dentry) const struct cred *cred = current_cred(); struct ecryptfs_inode_info *inode_info = ecryptfs_inode_to_private(ecryptfs_dentry->d_inode); + int opened_lower_file = 0; int rc = 0; mutex_lock(&inode_info->lower_file_mutex); @@ -134,9 +136,12 @@ int ecryptfs_init_persistent_file(struct dentry *ecryptfs_dentry) "for lower_dentry [0x%p] and lower_mnt [0x%p]; " "rc = [%d]\n", lower_dentry, lower_mnt, rc); inode_info->lower_file = NULL; - } + } else + opened_lower_file = 1; } mutex_unlock(&inode_info->lower_file_mutex); + if (opened_lower_file) + ima_counts_get(inode_info->lower_file); return rc; } diff --git a/fs/exec.c b/fs/exec.c index d49be6bc1793..ba112bd4a339 100644 --- a/fs/exec.c +++ b/fs/exec.c @@ -624,10 +624,8 @@ int setup_arg_pages(struct linux_binprm *bprm, /* Move stack pages down in memory. */ if (stack_shift) { ret = shift_arg_pages(vma, stack_shift); - if (ret) { - up_write(&mm->mmap_sem); - return ret; - } + if (ret) + goto out_unlock; } #ifdef CONFIG_STACK_GROWSUP @@ -641,7 +639,7 @@ int setup_arg_pages(struct linux_binprm *bprm, out_unlock: up_write(&mm->mmap_sem); - return 0; + return ret; } EXPORT_SYMBOL(setup_arg_pages); diff --git a/fs/ext3/fsync.c b/fs/ext3/fsync.c index 451d166bbe93..8209f266e9ad 100644 --- a/fs/ext3/fsync.c +++ b/fs/ext3/fsync.c @@ -46,19 +46,21 @@ int ext3_sync_file(struct file * file, struct dentry *dentry, int datasync) { struct inode *inode = dentry->d_inode; + struct ext3_inode_info *ei = EXT3_I(inode); + journal_t *journal = EXT3_SB(inode->i_sb)->s_journal; int ret = 0; + tid_t commit_tid; + + if (inode->i_sb->s_flags & MS_RDONLY) + return 0; J_ASSERT(ext3_journal_current_handle() == NULL); /* - * data=writeback: + * data=writeback,ordered: * The caller's filemap_fdatawrite()/wait will sync the data. - * sync_inode() will sync the metadata - * - * data=ordered: - * The caller's filemap_fdatawrite() will write the data and - * sync_inode() will write the inode if it is dirty. Then the caller's - * filemap_fdatawait() will wait on the pages. + * Metadata is in the journal, we wait for a proper transaction + * to commit here. * * data=journal: * filemap_fdatawrite won't do anything (the buffers are clean). @@ -73,22 +75,16 @@ int ext3_sync_file(struct file * file, struct dentry *dentry, int datasync) goto out; } - if (datasync && !(inode->i_state & I_DIRTY_DATASYNC)) - goto flush; + if (datasync) + commit_tid = atomic_read(&ei->i_datasync_tid); + else + commit_tid = atomic_read(&ei->i_sync_tid); - /* - * The VFS has written the file data. If the inode is unaltered - * then we need not start a commit. - */ - if (inode->i_state & (I_DIRTY_SYNC|I_DIRTY_DATASYNC)) { - struct writeback_control wbc = { - .sync_mode = WB_SYNC_ALL, - .nr_to_write = 0, /* sys_fsync did this */ - }; - ret = sync_inode(inode, &wbc); + if (log_start_commit(journal, commit_tid)) { + log_wait_commit(journal, commit_tid); goto out; } -flush: + /* * In case we didn't commit a transaction, we have to flush * disk caches manually so that data really is on persistent diff --git a/fs/ext3/inode.c b/fs/ext3/inode.c index acf1b1423327..354ed3b47b30 100644 --- a/fs/ext3/inode.c +++ b/fs/ext3/inode.c @@ -699,8 +699,9 @@ static int ext3_splice_branch(handle_t *handle, struct inode *inode, int err = 0; struct ext3_block_alloc_info *block_i; ext3_fsblk_t current_block; + struct ext3_inode_info *ei = EXT3_I(inode); - block_i = EXT3_I(inode)->i_block_alloc_info; + block_i = ei->i_block_alloc_info; /* * If we're splicing into a [td]indirect block (as opposed to the * inode) then we need to get write access to the [td]indirect block @@ -741,6 +742,8 @@ static int ext3_splice_branch(handle_t *handle, struct inode *inode, inode->i_ctime = CURRENT_TIME_SEC; ext3_mark_inode_dirty(handle, inode); + /* ext3_mark_inode_dirty already updated i_sync_tid */ + atomic_set(&ei->i_datasync_tid, handle->h_transaction->t_tid); /* had we spliced it onto indirect block? */ if (where->bh) { @@ -1735,6 +1738,7 @@ static ssize_t ext3_direct_IO(int rw, struct kiocb *iocb, ssize_t ret; int orphan = 0; size_t count = iov_length(iov, nr_segs); + int retries = 0; if (rw == WRITE) { loff_t final_size = offset + count; @@ -1757,9 +1761,12 @@ static ssize_t ext3_direct_IO(int rw, struct kiocb *iocb, } } +retry: ret = blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, iov, offset, nr_segs, ext3_get_block, NULL); + if (ret == -ENOSPC && ext3_should_retry_alloc(inode->i_sb, &retries)) + goto retry; if (orphan) { int err; @@ -2750,6 +2757,8 @@ struct inode *ext3_iget(struct super_block *sb, unsigned long ino) struct ext3_inode_info *ei; struct buffer_head *bh; struct inode *inode; + journal_t *journal = EXT3_SB(sb)->s_journal; + transaction_t *transaction; long ret; int block; @@ -2827,6 +2836,30 @@ struct inode *ext3_iget(struct super_block *sb, unsigned long ino) ei->i_data[block] = raw_inode->i_block[block]; INIT_LIST_HEAD(&ei->i_orphan); + /* + * Set transaction id's of transactions that have to be committed + * to finish f[data]sync. We set them to currently running transaction + * as we cannot be sure that the inode or some of its metadata isn't + * part of the transaction - the inode could have been reclaimed and + * now it is reread from disk. + */ + if (journal) { + tid_t tid; + + spin_lock(&journal->j_state_lock); + if (journal->j_running_transaction) + transaction = journal->j_running_transaction; + else + transaction = journal->j_committing_transaction; + if (transaction) + tid = transaction->t_tid; + else + tid = journal->j_commit_sequence; + spin_unlock(&journal->j_state_lock); + atomic_set(&ei->i_sync_tid, tid); + atomic_set(&ei->i_datasync_tid, tid); + } + if (inode->i_ino >= EXT3_FIRST_INO(inode->i_sb) + 1 && EXT3_INODE_SIZE(inode->i_sb) > EXT3_GOOD_OLD_INODE_SIZE) { /* @@ -3011,6 +3044,7 @@ again: err = rc; ei->i_state &= ~EXT3_STATE_NEW; + atomic_set(&ei->i_sync_tid, handle->h_transaction->t_tid); out_brelse: brelse (bh); ext3_std_error(inode->i_sb, err); diff --git a/fs/ext3/super.c b/fs/ext3/super.c index 72743d360509..427496c4767c 100644 --- a/fs/ext3/super.c +++ b/fs/ext3/super.c @@ -466,6 +466,8 @@ static struct inode *ext3_alloc_inode(struct super_block *sb) return NULL; ei->i_block_alloc_info = NULL; ei->vfs_inode.i_version = 1; + atomic_set(&ei->i_datasync_tid, 0); + atomic_set(&ei->i_sync_tid, 0); return &ei->vfs_inode; } @@ -2321,7 +2323,18 @@ static int ext3_commit_super(struct super_block *sb, if (!sbh) return error; - es->s_wtime = cpu_to_le32(get_seconds()); + /* + * If the file system is mounted read-only, don't update the + * superblock write time. This avoids updating the superblock + * write time when we are mounting the root file system + * read/only but we need to replay the journal; at that point, + * for people who are east of GMT and who make their clock + * tick in localtime for Windows bug-for-bug compatibility, + * the clock is set in the future, and this will cause e2fsck + * to complain and force a full file system check. + */ + if (!(sb->s_flags & MS_RDONLY)) + es->s_wtime = cpu_to_le32(get_seconds()); es->s_free_blocks_count = cpu_to_le32(ext3_count_free_blocks(sb)); es->s_free_inodes_count = cpu_to_le32(ext3_count_free_inodes(sb)); BUFFER_TRACE(sbh, "marking dirty"); diff --git a/fs/ext4/ext4.h b/fs/ext4/ext4.h index 984ca0cb38c3..8825515eeddd 100644 --- a/fs/ext4/ext4.h +++ b/fs/ext4/ext4.h @@ -322,6 +322,7 @@ static inline __u32 ext4_mask_flags(umode_t mode, __u32 flags) #define EXT4_STATE_NO_EXPAND 0x00000008 /* No space for expansion */ #define EXT4_STATE_DA_ALLOC_CLOSE 0x00000010 /* Alloc DA blks on close */ #define EXT4_STATE_EXT_MIGRATE 0x00000020 /* Inode is migrating */ +#define EXT4_STATE_DIO_UNWRITTEN 0x00000040 /* need convert on dio done*/ /* Used to pass group descriptor data when online resize is done */ struct ext4_new_group_input { @@ -743,6 +744,7 @@ struct ext4_inode_info { #define EXT4_MOUNT_QUOTA 0x80000 /* Some quota option set */ #define EXT4_MOUNT_USRQUOTA 0x100000 /* "old" user quota */ #define EXT4_MOUNT_GRPQUOTA 0x200000 /* "old" group quota */ +#define EXT4_MOUNT_JOURNAL_CHECKSUM 0x800000 /* Journal checksums */ #define EXT4_MOUNT_JOURNAL_ASYNC_COMMIT 0x1000000 /* Journal Async Commit */ #define EXT4_MOUNT_I_VERSION 0x2000000 /* i_version support */ #define EXT4_MOUNT_DELALLOC 0x8000000 /* Delalloc support */ diff --git a/fs/ext4/extents.c b/fs/ext4/extents.c index 10539e364283..715264b4bae4 100644 --- a/fs/ext4/extents.c +++ b/fs/ext4/extents.c @@ -2807,6 +2807,8 @@ fix_extent_len: * into three uninitialized extent(at most). After IO complete, the part * being filled will be convert to initialized by the end_io callback function * via ext4_convert_unwritten_extents(). + * + * Returns the size of uninitialized extent to be written on success. */ static int ext4_split_unwritten_extents(handle_t *handle, struct inode *inode, @@ -2824,7 +2826,6 @@ static int ext4_split_unwritten_extents(handle_t *handle, unsigned int allocated, ee_len, depth; ext4_fsblk_t newblock; int err = 0; - int ret = 0; ext_debug("ext4_split_unwritten_extents: inode %lu," "iblock %llu, max_blocks %u\n", inode->i_ino, @@ -2842,12 +2843,12 @@ static int ext4_split_unwritten_extents(handle_t *handle, ext4_ext_store_pblock(&orig_ex, ext_pblock(ex)); /* - * if the entire unintialized extent length less than - * the size of extent to write, there is no need to split - * uninitialized extent + * If the uninitialized extent begins at the same logical + * block where the write begins, and the write completely + * covers the extent, then we don't need to split it. */ - if (allocated <= max_blocks) - return ret; + if ((iblock == ee_block) && (allocated <= max_blocks)) + return allocated; err = ext4_ext_get_access(handle, inode, path + depth); if (err) @@ -3048,12 +3049,18 @@ ext4_ext_handle_uninitialized_extents(handle_t *handle, struct inode *inode, ret = ext4_split_unwritten_extents(handle, inode, path, iblock, max_blocks, flags); - /* flag the io_end struct that we need convert when IO done */ + /* + * Flag the inode(non aio case) or end_io struct (aio case) + * that this IO needs to convertion to written when IO is + * completed + */ if (io) io->flag = DIO_AIO_UNWRITTEN; + else + EXT4_I(inode)->i_state |= EXT4_STATE_DIO_UNWRITTEN; goto out; } - /* DIO end_io complete, convert the filled extent to written */ + /* async DIO end_io complete, convert the filled extent to written */ if (flags == EXT4_GET_BLOCKS_DIO_CONVERT_EXT) { ret = ext4_convert_unwritten_extents_dio(handle, inode, path); @@ -3295,10 +3302,16 @@ int ext4_ext_get_blocks(handle_t *handle, struct inode *inode, * To avoid unecessary convertion for every aio dio rewrite * to the mid of file, here we flag the IO that is really * need the convertion. - * + * For non asycn direct IO case, flag the inode state + * that we need to perform convertion when IO is done. */ - if (io && flags == EXT4_GET_BLOCKS_DIO_CREATE_EXT) - io->flag = DIO_AIO_UNWRITTEN; + if (flags == EXT4_GET_BLOCKS_DIO_CREATE_EXT) { + if (io) + io->flag = DIO_AIO_UNWRITTEN; + else + EXT4_I(inode)->i_state |= + EXT4_STATE_DIO_UNWRITTEN;; + } } err = ext4_ext_insert_extent(handle, inode, path, &newex, flags); if (err) { @@ -3519,6 +3532,7 @@ retry: * * This function is called from the direct IO end io call back * function, to convert the fallocated extents after IO is completed. + * Returns 0 on success. */ int ext4_convert_unwritten_extents(struct inode *inode, loff_t offset, loff_t len) diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c index 5c5bc5dafff8..2c8caa51addb 100644 --- a/fs/ext4/inode.c +++ b/fs/ext4/inode.c @@ -193,7 +193,7 @@ static int try_to_extend_transaction(handle_t *handle, struct inode *inode) * so before we call here everything must be consistently dirtied against * this transaction. */ - int ext4_truncate_restart_trans(handle_t *handle, struct inode *inode, +int ext4_truncate_restart_trans(handle_t *handle, struct inode *inode, int nblocks) { int ret; @@ -209,6 +209,7 @@ static int try_to_extend_transaction(handle_t *handle, struct inode *inode) up_write(&EXT4_I(inode)->i_data_sem); ret = ext4_journal_restart(handle, blocks_for_truncate(inode)); down_write(&EXT4_I(inode)->i_data_sem); + ext4_discard_preallocations(inode); return ret; } @@ -3445,8 +3446,6 @@ out: return ret; } -/* Maximum number of blocks we map for direct IO at once. */ - static int ext4_get_block_dio_write(struct inode *inode, sector_t iblock, struct buffer_head *bh_result, int create) { @@ -3654,13 +3653,14 @@ static void ext4_end_io_dio(struct kiocb *iocb, loff_t offset, ext4_io_end_t *io_end = iocb->private; struct workqueue_struct *wq; + /* if not async direct IO or dio with 0 bytes write, just return */ + if (!io_end || !size) + return; + ext_debug("ext4_end_io_dio(): io_end 0x%p" "for inode %lu, iocb 0x%p, offset %llu, size %llu\n", iocb->private, io_end->inode->i_ino, iocb, offset, size); - /* if not async direct IO or dio with 0 bytes write, just return */ - if (!io_end || !size) - return; /* if not aio dio with unwritten extents, just free io and return */ if (io_end->flag != DIO_AIO_UNWRITTEN){ @@ -3771,13 +3771,19 @@ static ssize_t ext4_ext_direct_IO(int rw, struct kiocb *iocb, if (ret != -EIOCBQUEUED && ret <= 0 && iocb->private) { ext4_free_io_end(iocb->private); iocb->private = NULL; - } else if (ret > 0) + } else if (ret > 0 && (EXT4_I(inode)->i_state & + EXT4_STATE_DIO_UNWRITTEN)) { + int err; /* * for non AIO case, since the IO is already * completed, we could do the convertion right here */ - ret = ext4_convert_unwritten_extents(inode, - offset, ret); + err = ext4_convert_unwritten_extents(inode, + offset, ret); + if (err < 0) + ret = err; + EXT4_I(inode)->i_state &= ~EXT4_STATE_DIO_UNWRITTEN; + } return ret; } diff --git a/fs/ext4/namei.c b/fs/ext4/namei.c index 7c8fe80bacdd..6d2c1b897fc7 100644 --- a/fs/ext4/namei.c +++ b/fs/ext4/namei.c @@ -1518,12 +1518,8 @@ static int ext4_add_entry(handle_t *handle, struct dentry *dentry, return retval; if (blocks == 1 && !dx_fallback && - EXT4_HAS_COMPAT_FEATURE(sb, EXT4_FEATURE_COMPAT_DIR_INDEX)) { - retval = make_indexed_dir(handle, dentry, inode, bh); - if (retval == -ENOSPC) - brelse(bh); - return retval; - } + EXT4_HAS_COMPAT_FEATURE(sb, EXT4_FEATURE_COMPAT_DIR_INDEX)) + return make_indexed_dir(handle, dentry, inode, bh); brelse(bh); } bh = ext4_append(handle, dir, &block, &retval); @@ -1532,10 +1528,7 @@ static int ext4_add_entry(handle_t *handle, struct dentry *dentry, de = (struct ext4_dir_entry_2 *) bh->b_data; de->inode = 0; de->rec_len = ext4_rec_len_to_disk(blocksize, blocksize); - retval = add_dirent_to_buf(handle, dentry, inode, de, bh); - if (retval == -ENOSPC) - brelse(bh); - return retval; + return add_dirent_to_buf(handle, dentry, inode, de, bh); } /* @@ -1664,8 +1657,7 @@ static int ext4_dx_add_entry(handle_t *handle, struct dentry *dentry, if (!de) goto cleanup; err = add_dirent_to_buf(handle, dentry, inode, de, bh); - if (err != -ENOSPC) - bh = NULL; + bh = NULL; goto cleanup; journal_error: diff --git a/fs/ext4/super.c b/fs/ext4/super.c index 312211ee05af..d4ca92aab514 100644 --- a/fs/ext4/super.c +++ b/fs/ext4/super.c @@ -1300,9 +1300,11 @@ static int parse_options(char *options, struct super_block *sb, *journal_devnum = option; break; case Opt_journal_checksum: - break; /* Kept for backwards compatibility */ + set_opt(sbi->s_mount_opt, JOURNAL_CHECKSUM); + break; case Opt_journal_async_commit: set_opt(sbi->s_mount_opt, JOURNAL_ASYNC_COMMIT); + set_opt(sbi->s_mount_opt, JOURNAL_CHECKSUM); break; case Opt_noload: set_opt(sbi->s_mount_opt, NOLOAD); @@ -2759,14 +2761,20 @@ static int ext4_fill_super(struct super_block *sb, void *data, int silent) goto failed_mount4; } - jbd2_journal_set_features(sbi->s_journal, - JBD2_FEATURE_COMPAT_CHECKSUM, 0, 0); - if (test_opt(sb, JOURNAL_ASYNC_COMMIT)) - jbd2_journal_set_features(sbi->s_journal, 0, 0, + if (test_opt(sb, JOURNAL_ASYNC_COMMIT)) { + jbd2_journal_set_features(sbi->s_journal, + JBD2_FEATURE_COMPAT_CHECKSUM, 0, JBD2_FEATURE_INCOMPAT_ASYNC_COMMIT); - else + } else if (test_opt(sb, JOURNAL_CHECKSUM)) { + jbd2_journal_set_features(sbi->s_journal, + JBD2_FEATURE_COMPAT_CHECKSUM, 0, 0); jbd2_journal_clear_features(sbi->s_journal, 0, 0, JBD2_FEATURE_INCOMPAT_ASYNC_COMMIT); + } else { + jbd2_journal_clear_features(sbi->s_journal, + JBD2_FEATURE_COMPAT_CHECKSUM, 0, + JBD2_FEATURE_INCOMPAT_ASYNC_COMMIT); + } /* We have now updated the journal if required, so we can * validate the data journaling mode. */ diff --git a/fs/fcntl.c b/fs/fcntl.c index fc089f2f7f56..2cf93ec40a67 100644 --- a/fs/fcntl.c +++ b/fs/fcntl.c @@ -284,7 +284,7 @@ static int f_setown_ex(struct file *filp, unsigned long arg) type = PIDTYPE_PID; break; - case F_OWNER_GID: + case F_OWNER_PGRP: type = PIDTYPE_PGID; break; @@ -321,7 +321,7 @@ static int f_getown_ex(struct file *filp, unsigned long arg) break; case PIDTYPE_PGID: - owner.type = F_OWNER_GID; + owner.type = F_OWNER_PGRP; break; default: diff --git a/fs/file.c b/fs/file.c index f313314f996f..87e129030ab1 100644 --- a/fs/file.c +++ b/fs/file.c @@ -10,6 +10,7 @@ #include <linux/fs.h> #include <linux/mm.h> #include <linux/time.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/vmalloc.h> #include <linux/file.h> diff --git a/fs/fuse/dir.c b/fs/fuse/dir.c index 992f6c9410bb..8ada78aade58 100644 --- a/fs/fuse/dir.c +++ b/fs/fuse/dir.c @@ -712,8 +712,10 @@ static int fuse_rename(struct inode *olddir, struct dentry *oldent, fuse_invalidate_attr(newdir); /* newent will end up negative */ - if (newent->d_inode) + if (newent->d_inode) { + fuse_invalidate_attr(newent->d_inode); fuse_invalidate_entry_cache(newent); + } } else if (err == -EINTR) { /* If request was interrupted, DEITY only knows if the rename actually took place. If the invalidation diff --git a/fs/fuse/file.c b/fs/fuse/file.c index a3492f7d207c..c18913a777ae 100644 --- a/fs/fuse/file.c +++ b/fs/fuse/file.c @@ -1063,7 +1063,8 @@ ssize_t fuse_direct_io(struct file *file, const char __user *buf, break; } } - fuse_put_request(fc, req); + if (!IS_ERR(req)) + fuse_put_request(fc, req); if (res > 0) *ppos = pos; @@ -1599,7 +1600,7 @@ static int fuse_ioctl_copy_user(struct page **pages, struct iovec *iov, kaddr += copy; } - kunmap(map); + kunmap(page); } return 0; diff --git a/fs/hfs/btree.c b/fs/hfs/btree.c index 9b9d6395bad3..052f214ea6f0 100644 --- a/fs/hfs/btree.c +++ b/fs/hfs/btree.c @@ -58,6 +58,11 @@ struct hfs_btree *hfs_btree_open(struct super_block *sb, u32 id, btree_keycmp ke } unlock_new_inode(tree->inode); + if (!HFS_I(tree->inode)->first_blocks) { + printk(KERN_ERR "hfs: invalid btree extent records (0 size).\n"); + goto free_inode; + } + mapping = tree->inode->i_mapping; page = read_mapping_page(mapping, 0, NULL); if (IS_ERR(page)) diff --git a/fs/hfsplus/wrapper.c b/fs/hfsplus/wrapper.c index 175d08eacc86..bed78ac8f6d1 100644 --- a/fs/hfsplus/wrapper.c +++ b/fs/hfsplus/wrapper.c @@ -99,6 +99,10 @@ int hfsplus_read_wrapper(struct super_block *sb) if (hfsplus_get_last_session(sb, &part_start, &part_size)) return -EINVAL; + if ((u64)part_start + part_size > 0x100000000ULL) { + pr_err("hfs: volumes larger than 2TB are not supported yet\n"); + return -EINVAL; + } while (1) { bh = sb_bread512(sb, part_start + HFSPLUS_VOLHEAD_SECTOR, vhdr); if (!bh) diff --git a/fs/ioctl.c b/fs/ioctl.c index 7b17a14396ff..6c751106c2e5 100644 --- a/fs/ioctl.c +++ b/fs/ioctl.c @@ -254,7 +254,7 @@ int __generic_block_fiemap(struct inode *inode, u64 len, get_block_t *get_block) { struct buffer_head tmp; - unsigned int start_blk; + unsigned long long start_blk; long long length = 0, map_len = 0; u64 logical = 0, phys = 0, size = 0; u32 flags = FIEMAP_EXTENT_MERGED; diff --git a/fs/jbd/journal.c b/fs/jbd/journal.c index bd3c073b485d..4160afad6d00 100644 --- a/fs/jbd/journal.c +++ b/fs/jbd/journal.c @@ -73,6 +73,7 @@ EXPORT_SYMBOL(journal_errno); EXPORT_SYMBOL(journal_ack_err); EXPORT_SYMBOL(journal_clear_err); EXPORT_SYMBOL(log_wait_commit); +EXPORT_SYMBOL(log_start_commit); EXPORT_SYMBOL(journal_start_commit); EXPORT_SYMBOL(journal_force_commit_nested); EXPORT_SYMBOL(journal_wipe); @@ -756,6 +757,7 @@ journal_t * journal_init_dev(struct block_device *bdev, return journal; out_err: + kfree(journal->j_wbuf); kfree(journal); return NULL; } @@ -820,6 +822,7 @@ journal_t * journal_init_inode (struct inode *inode) return journal; out_err: + kfree(journal->j_wbuf); kfree(journal); return NULL; } diff --git a/fs/jbd2/journal.c b/fs/jbd2/journal.c index b0ab5219becb..fed85388ee86 100644 --- a/fs/jbd2/journal.c +++ b/fs/jbd2/journal.c @@ -913,6 +913,7 @@ journal_t * jbd2_journal_init_dev(struct block_device *bdev, return journal; out_err: + kfree(journal->j_wbuf); jbd2_stats_proc_exit(journal); kfree(journal); return NULL; @@ -986,6 +987,7 @@ journal_t * jbd2_journal_init_inode (struct inode *inode) return journal; out_err: + kfree(journal->j_wbuf); jbd2_stats_proc_exit(journal); kfree(journal); return NULL; diff --git a/fs/nfs/client.c b/fs/nfs/client.c index 63976c0ccc25..99ea196f071f 100644 --- a/fs/nfs/client.c +++ b/fs/nfs/client.c @@ -1180,7 +1180,7 @@ static int nfs4_init_client(struct nfs_client *clp, 1, flags & NFS_MOUNT_NORESVPORT); if (error < 0) goto error; - memcpy(clp->cl_ipaddr, ip_addr, sizeof(clp->cl_ipaddr)); + strlcpy(clp->cl_ipaddr, ip_addr, sizeof(clp->cl_ipaddr)); error = nfs_idmap_new(clp); if (error < 0) { diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 32062c33c859..7cb298525eef 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -1536,6 +1536,8 @@ nfs_link(struct dentry *old_dentry, struct inode *dir, struct dentry *dentry) old_dentry->d_parent->d_name.name, old_dentry->d_name.name, dentry->d_parent->d_name.name, dentry->d_name.name); + nfs_inode_return_delegation(inode); + d_drop(dentry); error = NFS_PROTO(dir)->link(inode, dir, &dentry->d_name); if (error == 0) { diff --git a/fs/nfs/direct.c b/fs/nfs/direct.c index 6c3210099d51..e1d415e97849 100644 --- a/fs/nfs/direct.c +++ b/fs/nfs/direct.c @@ -457,6 +457,7 @@ static void nfs_direct_write_reschedule(struct nfs_direct_req *dreq) }; struct rpc_task_setup task_setup_data = { .rpc_client = NFS_CLIENT(inode), + .rpc_message = &msg, .callback_ops = &nfs_write_direct_ops, .workqueue = nfsiod_workqueue, .flags = RPC_TASK_ASYNC, diff --git a/fs/nfs/nfs4namespace.c b/fs/nfs/nfs4namespace.c index 2636c26d56fa..fa3408f20112 100644 --- a/fs/nfs/nfs4namespace.c +++ b/fs/nfs/nfs4namespace.c @@ -121,7 +121,7 @@ static struct vfsmount *try_location(struct nfs_clone_mount *mountdata, mnt_path = nfs4_pathname_string(&location->rootpath, page2, PAGE_SIZE); if (IS_ERR(mnt_path)) - return mnt; + return ERR_CAST(mnt_path); mountdata->mnt_path = mnt_path; maxbuflen = mnt_path - 1 - page2; @@ -132,15 +132,15 @@ static struct vfsmount *try_location(struct nfs_clone_mount *mountdata, if (buf->len <= 0 || buf->len >= maxbuflen) continue; - mountdata->addr = (struct sockaddr *)&addr; - if (memchr(buf->data, IPV6_SCOPE_DELIMITER, buf->len)) continue; - mountdata->addrlen = nfs_parse_server_name(buf->data, - buf->len, - mountdata->addr, mountdata->addrlen); + + mountdata->addrlen = nfs_parse_server_name(buf->data, buf->len, + (struct sockaddr *)&addr, sizeof(addr)); if (mountdata->addrlen == 0) continue; + + mountdata->addr = (struct sockaddr *)&addr; rpc_set_port(mountdata->addr, NFS_PORT); memcpy(page2, buf->data, buf->len); diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index ed7c269e2514..ff37454fa783 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -72,12 +72,17 @@ static int _nfs4_proc_getattr(struct nfs_server *server, struct nfs_fh *fhandle, /* Prevent leaks of NFSv4 errors into userland */ static int nfs4_map_errors(int err) { - if (err < -1000) { + if (err >= -1000) + return err; + switch (err) { + case -NFS4ERR_RESOURCE: + return -EREMOTEIO; + default: dprintk("%s could not handle NFSv4 error %d\n", __func__, -err); - return -EIO; + break; } - return err; + return -EIO; } /* @@ -3060,9 +3065,6 @@ static void nfs4_renew_done(struct rpc_task *task, void *data) if (time_before(clp->cl_last_renewal,timestamp)) clp->cl_last_renewal = timestamp; spin_unlock(&clp->cl_lock); - dprintk("%s calling put_rpccred on rpc_cred %p\n", __func__, - task->tk_msg.rpc_cred); - put_rpccred(task->tk_msg.rpc_cred); } static const struct rpc_call_ops nfs4_renew_ops = { @@ -4877,7 +4879,6 @@ void nfs41_sequence_call_done(struct rpc_task *task, void *data) nfs41_sequence_free_slot(clp, task->tk_msg.rpc_resp); dprintk("%s rpc_cred %p\n", __func__, task->tk_msg.rpc_cred); - put_rpccred(task->tk_msg.rpc_cred); kfree(task->tk_msg.rpc_argp); kfree(task->tk_msg.rpc_resp); diff --git a/fs/nfs/nfs4renewd.c b/fs/nfs/nfs4renewd.c index e27c6cef18f2..0156c01c212c 100644 --- a/fs/nfs/nfs4renewd.c +++ b/fs/nfs/nfs4renewd.c @@ -127,12 +127,6 @@ nfs4_schedule_state_renewal(struct nfs_client *clp) } void -nfs4_renewd_prepare_shutdown(struct nfs_server *server) -{ - cancel_delayed_work(&server->nfs_client->cl_renewd); -} - -void nfs4_kill_renewd(struct nfs_client *clp) { cancel_delayed_work_sync(&clp->cl_renewd); diff --git a/fs/nfs/nfs4xdr.c b/fs/nfs/nfs4xdr.c index 83ad47cbdd8a..20b4e30e6c82 100644 --- a/fs/nfs/nfs4xdr.c +++ b/fs/nfs/nfs4xdr.c @@ -5681,7 +5681,6 @@ static struct { { NFS4ERR_SERVERFAULT, -ESERVERFAULT }, { NFS4ERR_BADTYPE, -EBADTYPE }, { NFS4ERR_LOCKED, -EAGAIN }, - { NFS4ERR_RESOURCE, -EREMOTEIO }, { NFS4ERR_SYMLINK, -ELOOP }, { NFS4ERR_OP_ILLEGAL, -EOPNOTSUPP }, { NFS4ERR_DEADLOCK, -EDEADLK }, diff --git a/fs/nfs/super.c b/fs/nfs/super.c index 29786d3b9326..90be551b80c1 100644 --- a/fs/nfs/super.c +++ b/fs/nfs/super.c @@ -728,22 +728,24 @@ static void nfs_umount_begin(struct super_block *sb) unlock_kernel(); } -static struct nfs_parsed_mount_data *nfs_alloc_parsed_mount_data(int flags) +static struct nfs_parsed_mount_data *nfs_alloc_parsed_mount_data(unsigned int version) { struct nfs_parsed_mount_data *data; data = kzalloc(sizeof(*data), GFP_KERNEL); if (data) { - data->flags = flags; data->rsize = NFS_MAX_FILE_IO_SIZE; data->wsize = NFS_MAX_FILE_IO_SIZE; data->acregmin = NFS_DEF_ACREGMIN; data->acregmax = NFS_DEF_ACREGMAX; data->acdirmin = NFS_DEF_ACDIRMIN; data->acdirmax = NFS_DEF_ACDIRMAX; + data->mount_server.port = NFS_UNSPEC_PORT; data->nfs_server.port = NFS_UNSPEC_PORT; + data->nfs_server.protocol = XPRT_TRANSPORT_TCP; data->auth_flavors[0] = RPC_AUTH_UNIX; data->auth_flavor_len = 1; + data->version = version; data->minorversion = 0; } return data; @@ -776,15 +778,13 @@ static int nfs_verify_server_address(struct sockaddr *addr) * Select between a default port value and a user-specified port value. * If a zero value is set, then autobind will be used. */ -static void nfs_set_default_port(struct sockaddr *sap, const int parsed_port, +static void nfs_set_port(struct sockaddr *sap, int *port, const unsigned short default_port) { - unsigned short port = default_port; + if (*port == NFS_UNSPEC_PORT) + *port = default_port; - if (parsed_port != NFS_UNSPEC_PORT) - port = parsed_port; - - rpc_set_port(sap, port); + rpc_set_port(sap, *port); } /* @@ -1253,6 +1253,7 @@ static int nfs_parse_mount_options(char *raw, default: dfprintk(MOUNT, "NFS: unrecognized " "transport protocol\n"); + kfree(string); return 0; } break; @@ -1475,7 +1476,7 @@ static int nfs_try_mount(struct nfs_parsed_mount_data *args, args->mount_server.addrlen = args->nfs_server.addrlen; } request.salen = args->mount_server.addrlen; - nfs_set_default_port(request.sap, args->mount_server.port, 0); + nfs_set_port(request.sap, &args->mount_server.port, 0); /* * Now ask the mount server to map our export path @@ -1711,8 +1712,6 @@ static int nfs_validate_mount_data(void *options, if (!(data->flags & NFS_MOUNT_TCP)) args->nfs_server.protocol = XPRT_TRANSPORT_UDP; - else - args->nfs_server.protocol = XPRT_TRANSPORT_TCP; /* N.B. caller will free nfs_server.hostname in all cases */ args->nfs_server.hostname = kstrdup(data->hostname, GFP_KERNEL); args->namlen = data->namlen; @@ -1767,7 +1766,7 @@ static int nfs_validate_mount_data(void *options, goto out_v4_not_compiled; #endif - nfs_set_default_port(sap, args->nfs_server.port, 0); + nfs_set_port(sap, &args->nfs_server.port, 0); nfs_set_mount_transport_protocol(args); @@ -1848,9 +1847,10 @@ nfs_compare_remount_data(struct nfs_server *nfss, data->acdirmin != nfss->acdirmin / HZ || data->acdirmax != nfss->acdirmax / HZ || data->timeo != (10U * nfss->client->cl_timeout->to_initval / HZ) || + data->nfs_server.port != nfss->port || data->nfs_server.addrlen != nfss->nfs_client->cl_addrlen || - memcmp(&data->nfs_server.address, &nfss->nfs_client->cl_addr, - data->nfs_server.addrlen) != 0) + !rpc_cmp_addr((struct sockaddr *)&data->nfs_server.address, + (struct sockaddr *)&nfss->nfs_client->cl_addr)) return -EINVAL; return 0; @@ -1893,6 +1893,7 @@ nfs_remount(struct super_block *sb, int *flags, char *raw_data) data->acdirmin = nfss->acdirmin / HZ; data->acdirmax = nfss->acdirmax / HZ; data->timeo = 10U * nfss->client->cl_timeout->to_initval / HZ; + data->nfs_server.port = nfss->port; data->nfs_server.addrlen = nfss->nfs_client->cl_addrlen; memcpy(&data->nfs_server.address, &nfss->nfs_client->cl_addr, data->nfs_server.addrlen); @@ -2106,7 +2107,7 @@ static int nfs_get_sb(struct file_system_type *fs_type, }; int error = -ENOMEM; - data = nfs_alloc_parsed_mount_data(NFS_MOUNT_VER3 | NFS_MOUNT_TCP); + data = nfs_alloc_parsed_mount_data(3); mntfh = kzalloc(sizeof(*mntfh), GFP_KERNEL); if (data == NULL || mntfh == NULL) goto out_free_fh; @@ -2331,7 +2332,7 @@ static int nfs4_validate_text_mount_data(void *options, { struct sockaddr *sap = (struct sockaddr *)&args->nfs_server.address; - nfs_set_default_port(sap, args->nfs_server.port, NFS_PORT); + nfs_set_port(sap, &args->nfs_server.port, NFS_PORT); nfs_validate_transport_protocol(args); @@ -2376,7 +2377,6 @@ static int nfs4_validate_mount_data(void *options, if (data == NULL) goto out_no_data; - args->version = 4; switch (data->version) { case 1: if (data->host_addrlen > sizeof(args->nfs_server.address)) @@ -2660,7 +2660,7 @@ static int nfs4_get_sb(struct file_system_type *fs_type, struct nfs_parsed_mount_data *data; int error = -ENOMEM; - data = nfs_alloc_parsed_mount_data(0); + data = nfs_alloc_parsed_mount_data(4); if (data == NULL) goto out_free_data; @@ -2690,7 +2690,6 @@ static void nfs4_kill_super(struct super_block *sb) dprintk("--> %s\n", __func__); nfs_super_return_all_delegations(sb); kill_anon_super(sb); - nfs4_renewd_prepare_shutdown(server); nfs_fscache_release_super_cookie(sb); nfs_free_server(server); dprintk("<-- %s\n", __func__); diff --git a/fs/nfsd/nfs3xdr.c b/fs/nfsd/nfs3xdr.c index edf926e1062f..d0a2ce1b4324 100644 --- a/fs/nfsd/nfs3xdr.c +++ b/fs/nfsd/nfs3xdr.c @@ -958,7 +958,7 @@ encode_entry(struct readdir_cd *ccd, const char *name, int namlen, p1 = encode_entry_baggage(cd, p1, name, namlen, ino); if (plus) - p = encode_entryplus_baggage(cd, p1, name, namlen); + p1 = encode_entryplus_baggage(cd, p1, name, namlen); /* determine entry word length and lengths to go in pages */ num_entry_words = p1 - tmp; diff --git a/fs/nilfs2/btnode.c b/fs/nilfs2/btnode.c index 5941958f1e47..84c25382f8e3 100644 --- a/fs/nilfs2/btnode.c +++ b/fs/nilfs2/btnode.c @@ -87,6 +87,7 @@ int nilfs_btnode_submit_block(struct address_space *btnc, __u64 blocknr, brelse(bh); BUG(); } + memset(bh->b_data, 0, 1 << inode->i_blkbits); bh->b_bdev = NILFS_I_NILFS(inode)->ns_bdev; bh->b_blocknr = blocknr; set_buffer_mapped(bh); @@ -276,8 +277,7 @@ void nilfs_btnode_commit_change_key(struct address_space *btnc, "invalid oldkey %lld (newkey=%lld)", (unsigned long long)oldkey, (unsigned long long)newkey); - if (!test_set_buffer_dirty(obh) && TestSetPageDirty(opage)) - BUG(); + nilfs_btnode_mark_dirty(obh); spin_lock_irq(&btnc->tree_lock); radix_tree_delete(&btnc->page_tree, oldkey); diff --git a/fs/nilfs2/cpfile.c b/fs/nilfs2/cpfile.c index 1c6cfb59128d..3f5d5d06f53c 100644 --- a/fs/nilfs2/cpfile.c +++ b/fs/nilfs2/cpfile.c @@ -871,7 +871,6 @@ int nilfs_cpfile_change_cpmode(struct inode *cpfile, __u64 cno, int mode) * exclusive with a new mount job. Though it doesn't cover * umount, it's enough for the purpose. */ - mutex_lock(&nilfs->ns_mount_mutex); if (nilfs_checkpoint_is_mounted(nilfs, cno, 1)) { /* Current implementation does not have to protect plain read-only mounts since they are exclusive @@ -880,7 +879,6 @@ int nilfs_cpfile_change_cpmode(struct inode *cpfile, __u64 cno, int mode) ret = -EBUSY; } else ret = nilfs_cpfile_clear_snapshot(cpfile, cno); - mutex_unlock(&nilfs->ns_mount_mutex); return ret; case NILFS_SNAPSHOT: return nilfs_cpfile_set_snapshot(cpfile, cno); diff --git a/fs/nilfs2/inode.c b/fs/nilfs2/inode.c index 5040220c3732..2a0a5a3ac134 100644 --- a/fs/nilfs2/inode.c +++ b/fs/nilfs2/inode.c @@ -664,7 +664,6 @@ int nilfs_load_inode_block(struct nilfs_sb_info *sbi, struct inode *inode, int err; spin_lock(&sbi->s_inode_lock); - /* Caller of this function MUST lock s_inode_lock */ if (ii->i_bh == NULL) { spin_unlock(&sbi->s_inode_lock); err = nilfs_ifile_get_inode_block(sbi->s_ifile, inode->i_ino, diff --git a/fs/nilfs2/ioctl.c b/fs/nilfs2/ioctl.c index 6572ea4bc4df..f6af76042d80 100644 --- a/fs/nilfs2/ioctl.c +++ b/fs/nilfs2/ioctl.c @@ -99,7 +99,8 @@ static int nilfs_ioctl_wrap_copy(struct the_nilfs *nilfs, static int nilfs_ioctl_change_cpmode(struct inode *inode, struct file *filp, unsigned int cmd, void __user *argp) { - struct inode *cpfile = NILFS_SB(inode->i_sb)->s_nilfs->ns_cpfile; + struct the_nilfs *nilfs = NILFS_SB(inode->i_sb)->s_nilfs; + struct inode *cpfile = nilfs->ns_cpfile; struct nilfs_transaction_info ti; struct nilfs_cpmode cpmode; int ret; @@ -109,14 +110,17 @@ static int nilfs_ioctl_change_cpmode(struct inode *inode, struct file *filp, if (copy_from_user(&cpmode, argp, sizeof(cpmode))) return -EFAULT; + mutex_lock(&nilfs->ns_mount_mutex); nilfs_transaction_begin(inode->i_sb, &ti, 0); ret = nilfs_cpfile_change_cpmode( cpfile, cpmode.cm_cno, cpmode.cm_mode); if (unlikely(ret < 0)) { nilfs_transaction_abort(inode->i_sb); + mutex_unlock(&nilfs->ns_mount_mutex); return ret; } nilfs_transaction_commit(inode->i_sb); /* never fails */ + mutex_unlock(&nilfs->ns_mount_mutex); return ret; } @@ -297,7 +301,18 @@ static int nilfs_ioctl_move_inode_block(struct inode *inode, (unsigned long long)vdesc->vd_vblocknr); return ret; } - bh->b_private = vdesc; + if (unlikely(!list_empty(&bh->b_assoc_buffers))) { + printk(KERN_CRIT "%s: conflicting %s buffer: ino=%llu, " + "cno=%llu, offset=%llu, blocknr=%llu, vblocknr=%llu\n", + __func__, vdesc->vd_flags ? "node" : "data", + (unsigned long long)vdesc->vd_ino, + (unsigned long long)vdesc->vd_cno, + (unsigned long long)vdesc->vd_offset, + (unsigned long long)vdesc->vd_blocknr, + (unsigned long long)vdesc->vd_vblocknr); + brelse(bh); + return -EEXIST; + } list_add_tail(&bh->b_assoc_buffers, buffers); return 0; } @@ -335,24 +350,10 @@ static int nilfs_ioctl_move_blocks(struct the_nilfs *nilfs, list_for_each_entry_safe(bh, n, &buffers, b_assoc_buffers) { ret = nilfs_gccache_wait_and_mark_dirty(bh); if (unlikely(ret < 0)) { - if (ret == -EEXIST) { - vdesc = bh->b_private; - printk(KERN_CRIT - "%s: conflicting %s buffer: " - "ino=%llu, cno=%llu, offset=%llu, " - "blocknr=%llu, vblocknr=%llu\n", - __func__, - vdesc->vd_flags ? "node" : "data", - (unsigned long long)vdesc->vd_ino, - (unsigned long long)vdesc->vd_cno, - (unsigned long long)vdesc->vd_offset, - (unsigned long long)vdesc->vd_blocknr, - (unsigned long long)vdesc->vd_vblocknr); - } + WARN_ON(ret == -EEXIST); goto failed; } list_del_init(&bh->b_assoc_buffers); - bh->b_private = NULL; brelse(bh); } return nmembs; @@ -360,7 +361,6 @@ static int nilfs_ioctl_move_blocks(struct the_nilfs *nilfs, failed: list_for_each_entry_safe(bh, n, &buffers, b_assoc_buffers) { list_del_init(&bh->b_assoc_buffers); - bh->b_private = NULL; brelse(bh); } return ret; @@ -471,7 +471,6 @@ int nilfs_ioctl_prepare_clean_segments(struct the_nilfs *nilfs, return 0; failed: - nilfs_remove_all_gcinode(nilfs); printk(KERN_ERR "NILFS: GC failed during preparation: %s: err=%d\n", msg, ret); return ret; @@ -560,6 +559,8 @@ static int nilfs_ioctl_clean_segments(struct inode *inode, struct file *filp, else ret = nilfs_clean_segments(inode->i_sb, argv, kbufs); + if (ret < 0) + nilfs_remove_all_gcinode(nilfs); clear_nilfs_gc_running(nilfs); out_free: diff --git a/fs/nilfs2/segment.c b/fs/nilfs2/segment.c index 683df89dbae5..6eff66a070d5 100644 --- a/fs/nilfs2/segment.c +++ b/fs/nilfs2/segment.c @@ -2468,17 +2468,22 @@ static void nilfs_segctor_notify(struct nilfs_sc_info *sci, /* Clear requests (even when the construction failed) */ spin_lock(&sci->sc_state_lock); - sci->sc_state &= ~NILFS_SEGCTOR_COMMIT; - if (req->mode == SC_LSEG_SR) { + sci->sc_state &= ~NILFS_SEGCTOR_COMMIT; sci->sc_seq_done = req->seq_accepted; nilfs_segctor_wakeup(sci, req->sc_err ? : req->sb_err); sci->sc_flush_request = 0; - } else if (req->mode == SC_FLUSH_FILE) - sci->sc_flush_request &= ~FLUSH_FILE_BIT; - else if (req->mode == SC_FLUSH_DAT) - sci->sc_flush_request &= ~FLUSH_DAT_BIT; + } else { + if (req->mode == SC_FLUSH_FILE) + sci->sc_flush_request &= ~FLUSH_FILE_BIT; + else if (req->mode == SC_FLUSH_DAT) + sci->sc_flush_request &= ~FLUSH_DAT_BIT; + /* re-enable timer if checkpoint creation was not done */ + if (sci->sc_timer && (sci->sc_state & NILFS_SEGCTOR_COMMIT) && + time_before(jiffies, sci->sc_timer->expires)) + add_timer(sci->sc_timer); + } spin_unlock(&sci->sc_state_lock); } diff --git a/fs/notify/dnotify/dnotify.c b/fs/notify/dnotify/dnotify.c index 828a889be909..7e54e52964dd 100644 --- a/fs/notify/dnotify/dnotify.c +++ b/fs/notify/dnotify/dnotify.c @@ -91,6 +91,7 @@ static int dnotify_handle_event(struct fsnotify_group *group, struct dnotify_struct *dn; struct dnotify_struct **prev; struct fown_struct *fown; + __u32 test_mask = event->mask & ~FS_EVENT_ON_CHILD; to_tell = event->to_tell; @@ -106,7 +107,7 @@ static int dnotify_handle_event(struct fsnotify_group *group, spin_lock(&entry->lock); prev = &dnentry->dn; while ((dn = *prev) != NULL) { - if ((dn->dn_mask & event->mask) == 0) { + if ((dn->dn_mask & test_mask) == 0) { prev = &dn->dn_next; continue; } diff --git a/fs/notify/inode_mark.c b/fs/notify/inode_mark.c index c8a07c65482b..3165d85aada2 100644 --- a/fs/notify/inode_mark.c +++ b/fs/notify/inode_mark.c @@ -324,11 +324,11 @@ int fsnotify_add_mark(struct fsnotify_mark_entry *entry, spin_lock(&group->mark_lock); spin_lock(&inode->i_lock); - entry->group = group; - entry->inode = inode; - lentry = fsnotify_find_mark_entry(group, inode); if (!lentry) { + entry->group = group; + entry->inode = inode; + hlist_add_head(&entry->i_list, &inode->i_fsnotify_mark_entries); list_add(&entry->g_list, &group->mark_entries); diff --git a/fs/notify/notification.c b/fs/notify/notification.c index 3816d5750dd5..b8bf53b4c108 100644 --- a/fs/notify/notification.c +++ b/fs/notify/notification.c @@ -143,7 +143,7 @@ static bool event_compare(struct fsnotify_event *old, struct fsnotify_event *new /* remember, after old was put on the wait_q we aren't * allowed to look at the inode any more, only thing * left to check was if the file_name is the same */ - if (old->name_len && + if (!old->name_len || !strcmp(old->file_name, new->file_name)) return true; break; diff --git a/fs/partitions/check.c b/fs/partitions/check.c index f38fee0311a7..7b685e10cbad 100644 --- a/fs/partitions/check.c +++ b/fs/partitions/check.c @@ -248,11 +248,19 @@ ssize_t part_stat_show(struct device *dev, part_stat_read(p, merges[WRITE]), (unsigned long long)part_stat_read(p, sectors[WRITE]), jiffies_to_msecs(part_stat_read(p, ticks[WRITE])), - p->in_flight, + part_in_flight(p), jiffies_to_msecs(part_stat_read(p, io_ticks)), jiffies_to_msecs(part_stat_read(p, time_in_queue))); } +ssize_t part_inflight_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct hd_struct *p = dev_to_part(dev); + + return sprintf(buf, "%8u %8u\n", p->in_flight[0], p->in_flight[1]); +} + #ifdef CONFIG_FAIL_MAKE_REQUEST ssize_t part_fail_show(struct device *dev, struct device_attribute *attr, char *buf) @@ -281,6 +289,7 @@ static DEVICE_ATTR(start, S_IRUGO, part_start_show, NULL); static DEVICE_ATTR(size, S_IRUGO, part_size_show, NULL); static DEVICE_ATTR(alignment_offset, S_IRUGO, part_alignment_offset_show, NULL); static DEVICE_ATTR(stat, S_IRUGO, part_stat_show, NULL); +static DEVICE_ATTR(inflight, S_IRUGO, part_inflight_show, NULL); #ifdef CONFIG_FAIL_MAKE_REQUEST static struct device_attribute dev_attr_fail = __ATTR(make-it-fail, S_IRUGO|S_IWUSR, part_fail_show, part_fail_store); @@ -292,6 +301,7 @@ static struct attribute *part_attrs[] = { &dev_attr_size.attr, &dev_attr_alignment_offset.attr, &dev_attr_stat.attr, + &dev_attr_inflight.attr, #ifdef CONFIG_FAIL_MAKE_REQUEST &dev_attr_fail.attr, #endif diff --git a/fs/pipe.c b/fs/pipe.c index 52c415114838..ae17d026aaa3 100644 --- a/fs/pipe.c +++ b/fs/pipe.c @@ -777,36 +777,55 @@ pipe_rdwr_release(struct inode *inode, struct file *filp) static int pipe_read_open(struct inode *inode, struct file *filp) { - /* We could have perhaps used atomic_t, but this and friends - below are the only places. So it doesn't seem worthwhile. */ + int ret = -ENOENT; + mutex_lock(&inode->i_mutex); - inode->i_pipe->readers++; + + if (inode->i_pipe) { + ret = 0; + inode->i_pipe->readers++; + } + mutex_unlock(&inode->i_mutex); - return 0; + return ret; } static int pipe_write_open(struct inode *inode, struct file *filp) { + int ret = -ENOENT; + mutex_lock(&inode->i_mutex); - inode->i_pipe->writers++; + + if (inode->i_pipe) { + ret = 0; + inode->i_pipe->writers++; + } + mutex_unlock(&inode->i_mutex); - return 0; + return ret; } static int pipe_rdwr_open(struct inode *inode, struct file *filp) { + int ret = -ENOENT; + mutex_lock(&inode->i_mutex); - if (filp->f_mode & FMODE_READ) - inode->i_pipe->readers++; - if (filp->f_mode & FMODE_WRITE) - inode->i_pipe->writers++; + + if (inode->i_pipe) { + ret = 0; + if (filp->f_mode & FMODE_READ) + inode->i_pipe->readers++; + if (filp->f_mode & FMODE_WRITE) + inode->i_pipe->writers++; + } + mutex_unlock(&inode->i_mutex); - return 0; + return ret; } /* diff --git a/fs/proc/array.c b/fs/proc/array.c index 07f77a7945c3..822c2d506518 100644 --- a/fs/proc/array.c +++ b/fs/proc/array.c @@ -571,7 +571,7 @@ static int do_task_stat(struct seq_file *m, struct pid_namespace *ns, rsslim, mm ? mm->start_code : 0, mm ? mm->end_code : 0, - (permitted) ? task->stack_start : 0, + (permitted && mm) ? task->stack_start : 0, esp, eip, /* The signal information here is obsolete. diff --git a/fs/proc/base.c b/fs/proc/base.c index 837469a96598..af643b5aefe8 100644 --- a/fs/proc/base.c +++ b/fs/proc/base.c @@ -2597,8 +2597,7 @@ static void proc_flush_task_mnt(struct vfsmount *mnt, pid_t pid, pid_t tgid) name.len = snprintf(buf, sizeof(buf), "%d", pid); dentry = d_hash_and_lookup(mnt->mnt_root, &name); if (dentry) { - if (!(current->flags & PF_EXITING)) - shrink_dcache_parent(dentry); + shrink_dcache_parent(dentry); d_drop(dentry); dput(dentry); } diff --git a/fs/proc/kcore.c b/fs/proc/kcore.c index 56013371f9f3..a44a7897fd4d 100644 --- a/fs/proc/kcore.c +++ b/fs/proc/kcore.c @@ -23,7 +23,6 @@ #include <asm/io.h> #include <linux/list.h> #include <linux/ioport.h> -#include <linux/mm.h> #include <linux/memory.h> #include <asm/sections.h> diff --git a/fs/proc/meminfo.c b/fs/proc/meminfo.c index c7bff4f603ff..a65239cfd97e 100644 --- a/fs/proc/meminfo.c +++ b/fs/proc/meminfo.c @@ -99,7 +99,7 @@ static int meminfo_proc_show(struct seq_file *m, void *v) "VmallocUsed: %8lu kB\n" "VmallocChunk: %8lu kB\n" #ifdef CONFIG_MEMORY_FAILURE - "HardwareCorrupted: %8lu kB\n" + "HardwareCorrupted: %5lu kB\n" #endif , K(i.totalram), diff --git a/fs/proc/page.c b/fs/proc/page.c index 2281c2cbfe2b..5033ce0d254b 100644 --- a/fs/proc/page.c +++ b/fs/proc/page.c @@ -94,6 +94,7 @@ static const struct file_operations proc_kpagecount_operations = { #define KPF_COMPOUND_TAIL 16 #define KPF_HUGE 17 #define KPF_UNEVICTABLE 18 +#define KPF_HWPOISON 19 #define KPF_NOPAGE 20 #define KPF_KSM 21 @@ -180,6 +181,10 @@ static u64 get_uflags(struct page *page) u |= kpf_copy_bit(k, KPF_UNEVICTABLE, PG_unevictable); u |= kpf_copy_bit(k, KPF_MLOCKED, PG_mlocked); +#ifdef CONFIG_MEMORY_FAILURE + u |= kpf_copy_bit(k, KPF_HWPOISON, PG_hwpoison); +#endif + #ifdef CONFIG_IA64_UNCACHED_ALLOCATOR u |= kpf_copy_bit(k, KPF_UNCACHED, PG_uncached); #endif diff --git a/fs/romfs/storage.c b/fs/romfs/storage.c index b3208adf8e71..71e2b4d50a0a 100644 --- a/fs/romfs/storage.c +++ b/fs/romfs/storage.c @@ -253,11 +253,11 @@ ssize_t romfs_dev_strnlen(struct super_block *sb, #ifdef CONFIG_ROMFS_ON_MTD if (sb->s_mtd) - return romfs_mtd_strnlen(sb, pos, limit); + return romfs_mtd_strnlen(sb, pos, maxlen); #endif #ifdef CONFIG_ROMFS_ON_BLOCK if (sb->s_bdev) - return romfs_blk_strnlen(sb, pos, limit); + return romfs_blk_strnlen(sb, pos, maxlen); #endif return -EIO; } diff --git a/fs/sysfs/dir.c b/fs/sysfs/dir.c index 0050fc40e8c9..e0201837d244 100644 --- a/fs/sysfs/dir.c +++ b/fs/sysfs/dir.c @@ -21,6 +21,7 @@ #include <linux/completion.h> #include <linux/mutex.h> #include <linux/slab.h> +#include <linux/security.h> #include "sysfs.h" DEFINE_MUTEX(sysfs_mutex); @@ -285,6 +286,9 @@ void release_sysfs_dirent(struct sysfs_dirent * sd) sysfs_put(sd->s_symlink.target_sd); if (sysfs_type(sd) & SYSFS_COPY_NAME) kfree(sd->s_name); + if (sd->s_iattr && sd->s_iattr->ia_secdata) + security_release_secctx(sd->s_iattr->ia_secdata, + sd->s_iattr->ia_secdata_len); kfree(sd->s_iattr); sysfs_free_ino(sd->s_ino); kmem_cache_free(sysfs_dir_cachep, sd); @@ -894,7 +898,8 @@ int sysfs_move_dir(struct kobject *kobj, struct kobject *new_parent_kobj) mutex_lock(&sysfs_rename_mutex); BUG_ON(!sd->s_parent); - new_parent_sd = new_parent_kobj->sd ? new_parent_kobj->sd : &sysfs_root; + new_parent_sd = (new_parent_kobj && new_parent_kobj->sd) ? + new_parent_kobj->sd : &sysfs_root; error = 0; if (sd->s_parent == new_parent_sd) diff --git a/fs/sysfs/file.c b/fs/sysfs/file.c index 561a9c050cef..f5ea4680f15f 100644 --- a/fs/sysfs/file.c +++ b/fs/sysfs/file.c @@ -268,7 +268,7 @@ static int sysfs_get_open_dirent(struct sysfs_dirent *sd, struct sysfs_open_dirent *od, *new_od = NULL; retry: - spin_lock(&sysfs_open_dirent_lock); + spin_lock_irq(&sysfs_open_dirent_lock); if (!sd->s_attr.open && new_od) { sd->s_attr.open = new_od; @@ -281,7 +281,7 @@ static int sysfs_get_open_dirent(struct sysfs_dirent *sd, list_add_tail(&buffer->list, &od->buffers); } - spin_unlock(&sysfs_open_dirent_lock); + spin_unlock_irq(&sysfs_open_dirent_lock); if (od) { kfree(new_od); @@ -315,8 +315,9 @@ static void sysfs_put_open_dirent(struct sysfs_dirent *sd, struct sysfs_buffer *buffer) { struct sysfs_open_dirent *od = sd->s_attr.open; + unsigned long flags; - spin_lock(&sysfs_open_dirent_lock); + spin_lock_irqsave(&sysfs_open_dirent_lock, flags); list_del(&buffer->list); if (atomic_dec_and_test(&od->refcnt)) @@ -324,7 +325,7 @@ static void sysfs_put_open_dirent(struct sysfs_dirent *sd, else od = NULL; - spin_unlock(&sysfs_open_dirent_lock); + spin_unlock_irqrestore(&sysfs_open_dirent_lock, flags); kfree(od); } @@ -456,8 +457,9 @@ static unsigned int sysfs_poll(struct file *filp, poll_table *wait) void sysfs_notify_dirent(struct sysfs_dirent *sd) { struct sysfs_open_dirent *od; + unsigned long flags; - spin_lock(&sysfs_open_dirent_lock); + spin_lock_irqsave(&sysfs_open_dirent_lock, flags); od = sd->s_attr.open; if (od) { @@ -465,7 +467,7 @@ void sysfs_notify_dirent(struct sysfs_dirent *sd) wake_up_interruptible(&od->poll); } - spin_unlock(&sysfs_open_dirent_lock); + spin_unlock_irqrestore(&sysfs_open_dirent_lock, flags); } EXPORT_SYMBOL_GPL(sysfs_notify_dirent); diff --git a/fs/xfs/linux-2.6/xfs_aops.c b/fs/xfs/linux-2.6/xfs_aops.c index 381854461b28..c2e30eea74dc 100644 --- a/fs/xfs/linux-2.6/xfs_aops.c +++ b/fs/xfs/linux-2.6/xfs_aops.c @@ -186,19 +186,37 @@ xfs_destroy_ioend( } /* + * If the end of the current ioend is beyond the current EOF, + * return the new EOF value, otherwise zero. + */ +STATIC xfs_fsize_t +xfs_ioend_new_eof( + xfs_ioend_t *ioend) +{ + xfs_inode_t *ip = XFS_I(ioend->io_inode); + xfs_fsize_t isize; + xfs_fsize_t bsize; + + bsize = ioend->io_offset + ioend->io_size; + isize = MAX(ip->i_size, ip->i_new_size); + isize = MIN(isize, bsize); + return isize > ip->i_d.di_size ? isize : 0; +} + +/* * Update on-disk file size now that data has been written to disk. * The current in-memory file size is i_size. If a write is beyond * eof i_new_size will be the intended file size until i_size is * updated. If this write does not extend all the way to the valid * file size then restrict this update to the end of the write. */ + STATIC void xfs_setfilesize( xfs_ioend_t *ioend) { xfs_inode_t *ip = XFS_I(ioend->io_inode); xfs_fsize_t isize; - xfs_fsize_t bsize; ASSERT((ip->i_d.di_mode & S_IFMT) == S_IFREG); ASSERT(ioend->io_type != IOMAP_READ); @@ -206,16 +224,10 @@ xfs_setfilesize( if (unlikely(ioend->io_error)) return; - bsize = ioend->io_offset + ioend->io_size; - xfs_ilock(ip, XFS_ILOCK_EXCL); - - isize = MAX(ip->i_size, ip->i_new_size); - isize = MIN(isize, bsize); - - if (ip->i_d.di_size < isize) { + isize = xfs_ioend_new_eof(ioend); + if (isize) { ip->i_d.di_size = isize; - ip->i_update_core = 1; xfs_mark_inode_dirty_sync(ip); } @@ -404,10 +416,16 @@ xfs_submit_ioend_bio( struct bio *bio) { atomic_inc(&ioend->io_remaining); - bio->bi_private = ioend; bio->bi_end_io = xfs_end_bio; + /* + * If the I/O is beyond EOF we mark the inode dirty immediately + * but don't update the inode size until I/O completion. + */ + if (xfs_ioend_new_eof(ioend)) + xfs_mark_inode_dirty_sync(XFS_I(ioend->io_inode)); + submit_bio(WRITE, bio); ASSERT(!bio_flagged(bio, BIO_EOPNOTSUPP)); bio_put(bio); diff --git a/fs/xfs/linux-2.6/xfs_file.c b/fs/xfs/linux-2.6/xfs_file.c index 629370974e57..eff61e2732af 100644 --- a/fs/xfs/linux-2.6/xfs_file.c +++ b/fs/xfs/linux-2.6/xfs_file.c @@ -176,14 +176,7 @@ xfs_file_fsync( struct dentry *dentry, int datasync) { - struct inode *inode = dentry->d_inode; - struct xfs_inode *ip = XFS_I(inode); - int error; - - /* capture size updates in I/O completion before writing the inode. */ - error = filemap_fdatawait(inode->i_mapping); - if (error) - return error; + struct xfs_inode *ip = XFS_I(dentry->d_inode); xfs_iflags_clear(ip, XFS_ITRUNCATED); return -xfs_fsync(ip); diff --git a/fs/xfs/linux-2.6/xfs_iops.c b/fs/xfs/linux-2.6/xfs_iops.c index da0159d99f82..cd42ef78f6b5 100644 --- a/fs/xfs/linux-2.6/xfs_iops.c +++ b/fs/xfs/linux-2.6/xfs_iops.c @@ -57,19 +57,22 @@ #include <linux/fiemap.h> /* - * Bring the atime in the XFS inode uptodate. - * Used before logging the inode to disk or when the Linux inode goes away. + * Bring the timestamps in the XFS inode uptodate. + * + * Used before writing the inode to disk. */ void -xfs_synchronize_atime( +xfs_synchronize_times( xfs_inode_t *ip) { struct inode *inode = VFS_I(ip); - if (!(inode->i_state & I_CLEAR)) { - ip->i_d.di_atime.t_sec = (__int32_t)inode->i_atime.tv_sec; - ip->i_d.di_atime.t_nsec = (__int32_t)inode->i_atime.tv_nsec; - } + ip->i_d.di_atime.t_sec = (__int32_t)inode->i_atime.tv_sec; + ip->i_d.di_atime.t_nsec = (__int32_t)inode->i_atime.tv_nsec; + ip->i_d.di_ctime.t_sec = (__int32_t)inode->i_ctime.tv_sec; + ip->i_d.di_ctime.t_nsec = (__int32_t)inode->i_ctime.tv_nsec; + ip->i_d.di_mtime.t_sec = (__int32_t)inode->i_mtime.tv_sec; + ip->i_d.di_mtime.t_nsec = (__int32_t)inode->i_mtime.tv_nsec; } /* @@ -106,32 +109,20 @@ xfs_ichgtime( if ((flags & XFS_ICHGTIME_MOD) && !timespec_equal(&inode->i_mtime, &tv)) { inode->i_mtime = tv; - ip->i_d.di_mtime.t_sec = (__int32_t)tv.tv_sec; - ip->i_d.di_mtime.t_nsec = (__int32_t)tv.tv_nsec; sync_it = 1; } if ((flags & XFS_ICHGTIME_CHG) && !timespec_equal(&inode->i_ctime, &tv)) { inode->i_ctime = tv; - ip->i_d.di_ctime.t_sec = (__int32_t)tv.tv_sec; - ip->i_d.di_ctime.t_nsec = (__int32_t)tv.tv_nsec; sync_it = 1; } /* - * We update the i_update_core field _after_ changing - * the timestamps in order to coordinate properly with - * xfs_iflush() so that we don't lose timestamp updates. - * This keeps us from having to hold the inode lock - * while doing this. We use the SYNCHRONIZE macro to - * ensure that the compiler does not reorder the update - * of i_update_core above the timestamp updates above. + * Update complete - now make sure everyone knows that the inode + * is dirty. */ - if (sync_it) { - SYNCHRONIZE(); - ip->i_update_core = 1; + if (sync_it) xfs_mark_inode_dirty_sync(ip); - } } /* @@ -506,10 +497,8 @@ xfs_vn_getattr( stat->gid = ip->i_d.di_gid; stat->ino = ip->i_ino; stat->atime = inode->i_atime; - stat->mtime.tv_sec = ip->i_d.di_mtime.t_sec; - stat->mtime.tv_nsec = ip->i_d.di_mtime.t_nsec; - stat->ctime.tv_sec = ip->i_d.di_ctime.t_sec; - stat->ctime.tv_nsec = ip->i_d.di_ctime.t_nsec; + stat->mtime = inode->i_mtime; + stat->ctime = inode->i_ctime; stat->blocks = XFS_FSB_TO_BB(mp, ip->i_d.di_nblocks + ip->i_delayed_blks); diff --git a/fs/xfs/linux-2.6/xfs_lrw.c b/fs/xfs/linux-2.6/xfs_lrw.c index 49e4a6aea73c..072050f8d346 100644 --- a/fs/xfs/linux-2.6/xfs_lrw.c +++ b/fs/xfs/linux-2.6/xfs_lrw.c @@ -667,7 +667,7 @@ start: xip->i_new_size = new_size; if (likely(!(ioflags & IO_INVIS))) - xfs_ichgtime(xip, XFS_ICHGTIME_MOD | XFS_ICHGTIME_CHG); + file_update_time(file); /* * If the offset is beyond the size of the file, we have a couple diff --git a/fs/xfs/linux-2.6/xfs_quotaops.c b/fs/xfs/linux-2.6/xfs_quotaops.c index 9e41f91aa269..3d4a0c84d634 100644 --- a/fs/xfs/linux-2.6/xfs_quotaops.c +++ b/fs/xfs/linux-2.6/xfs_quotaops.c @@ -80,7 +80,7 @@ xfs_fs_set_xstate( if (sb->s_flags & MS_RDONLY) return -EROFS; - if (!XFS_IS_QUOTA_RUNNING(mp)) + if (op != Q_XQUOTARM && !XFS_IS_QUOTA_RUNNING(mp)) return -ENOSYS; if (!capable(CAP_SYS_ADMIN)) return -EPERM; diff --git a/fs/xfs/linux-2.6/xfs_super.c b/fs/xfs/linux-2.6/xfs_super.c index bdd41c8c342f..18a4b8e11df2 100644 --- a/fs/xfs/linux-2.6/xfs_super.c +++ b/fs/xfs/linux-2.6/xfs_super.c @@ -977,6 +977,28 @@ xfs_fs_inode_init_once( } /* + * Dirty the XFS inode when mark_inode_dirty_sync() is called so that + * we catch unlogged VFS level updates to the inode. Care must be taken + * here - the transaction code calls mark_inode_dirty_sync() to mark the + * VFS inode dirty in a transaction and clears the i_update_core field; + * it must clear the field after calling mark_inode_dirty_sync() to + * correctly indicate that the dirty state has been propagated into the + * inode log item. + * + * We need the barrier() to maintain correct ordering between unlogged + * updates and the transaction commit code that clears the i_update_core + * field. This requires all updates to be completed before marking the + * inode dirty. + */ +STATIC void +xfs_fs_dirty_inode( + struct inode *inode) +{ + barrier(); + XFS_I(inode)->i_update_core = 1; +} + +/* * Attempt to flush the inode, this will actually fail * if the inode is pinned, but we dirty the inode again * at the point when it is unpinned after a log write, @@ -1126,7 +1148,7 @@ xfs_fs_put_super( } STATIC int -xfs_fs_sync_super( +xfs_fs_sync_fs( struct super_block *sb, int wait) { @@ -1134,23 +1156,23 @@ xfs_fs_sync_super( int error; /* - * Treat a sync operation like a freeze. This is to work - * around a race in sync_inodes() which works in two phases - * - an asynchronous flush, which can write out an inode - * without waiting for file size updates to complete, and a - * synchronous flush, which wont do anything because the - * async flush removed the inode's dirty flag. Also - * sync_inodes() will not see any files that just have - * outstanding transactions to be flushed because we don't - * dirty the Linux inode until after the transaction I/O - * completes. + * Not much we can do for the first async pass. Writing out the + * superblock would be counter-productive as we are going to redirty + * when writing out other data and metadata (and writing out a single + * block is quite fast anyway). + * + * Try to asynchronously kick off quota syncing at least. */ - if (wait || unlikely(sb->s_frozen == SB_FREEZE_WRITE)) - error = xfs_quiesce_data(mp); - else - error = xfs_sync_fsdata(mp, 0); + if (!wait) { + xfs_qm_sync(mp, SYNC_TRYLOCK); + return 0; + } + + error = xfs_quiesce_data(mp); + if (error) + return -error; - if (unlikely(laptop_mode)) { + if (laptop_mode) { int prev_sync_seq = mp->m_sync_seq; /* @@ -1169,7 +1191,7 @@ xfs_fs_sync_super( mp->m_sync_seq != prev_sync_seq); } - return -error; + return 0; } STATIC int @@ -1539,10 +1561,11 @@ xfs_fs_get_sb( static const struct super_operations xfs_super_operations = { .alloc_inode = xfs_fs_alloc_inode, .destroy_inode = xfs_fs_destroy_inode, + .dirty_inode = xfs_fs_dirty_inode, .write_inode = xfs_fs_write_inode, .clear_inode = xfs_fs_clear_inode, .put_super = xfs_fs_put_super, - .sync_fs = xfs_fs_sync_super, + .sync_fs = xfs_fs_sync_fs, .freeze_fs = xfs_fs_freeze, .statfs = xfs_fs_statfs, .remount_fs = xfs_fs_remount, diff --git a/fs/xfs/linux-2.6/xfs_sync.c b/fs/xfs/linux-2.6/xfs_sync.c index 320be6aea492..961df0a22c78 100644 --- a/fs/xfs/linux-2.6/xfs_sync.c +++ b/fs/xfs/linux-2.6/xfs_sync.c @@ -309,11 +309,15 @@ xfs_sync_attr( STATIC int xfs_commit_dummy_trans( struct xfs_mount *mp, - uint log_flags) + uint flags) { struct xfs_inode *ip = mp->m_rootip; struct xfs_trans *tp; int error; + int log_flags = XFS_LOG_FORCE; + + if (flags & SYNC_WAIT) + log_flags |= XFS_LOG_SYNC; /* * Put a dummy transaction in the log to tell recovery @@ -331,13 +335,12 @@ xfs_commit_dummy_trans( xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); xfs_trans_ihold(tp, ip); xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); - /* XXX(hch): ignoring the error here.. */ error = xfs_trans_commit(tp, 0); - xfs_iunlock(ip, XFS_ILOCK_EXCL); + /* the log force ensures this transaction is pushed to disk */ xfs_log_force(mp, 0, log_flags); - return 0; + return error; } int @@ -385,7 +388,20 @@ xfs_sync_fsdata( else XFS_BUF_ASYNC(bp); - return xfs_bwrite(mp, bp); + error = xfs_bwrite(mp, bp); + if (error) + return error; + + /* + * If this is a data integrity sync make sure all pending buffers + * are flushed out for the log coverage check below. + */ + if (flags & SYNC_WAIT) + xfs_flush_buftarg(mp->m_ddev_targp, 1); + + if (xfs_log_need_covered(mp)) + error = xfs_commit_dummy_trans(mp, flags); + return error; out_brelse: xfs_buf_relse(bp); @@ -419,14 +435,16 @@ xfs_quiesce_data( /* push non-blocking */ xfs_sync_data(mp, 0); xfs_qm_sync(mp, SYNC_TRYLOCK); - xfs_filestream_flush(mp); - /* push and block */ + /* push and block till complete */ xfs_sync_data(mp, SYNC_WAIT); xfs_qm_sync(mp, SYNC_WAIT); + /* drop inode references pinned by filestreams */ + xfs_filestream_flush(mp); + /* write superblock and hoover up shutdown errors */ - error = xfs_sync_fsdata(mp, 0); + error = xfs_sync_fsdata(mp, SYNC_WAIT); /* flush data-only devices */ if (mp->m_rtdev_targp) @@ -570,8 +588,6 @@ xfs_sync_worker( /* dgc: errors ignored here */ error = xfs_qm_sync(mp, SYNC_TRYLOCK); error = xfs_sync_fsdata(mp, SYNC_TRYLOCK); - if (xfs_log_need_covered(mp)) - error = xfs_commit_dummy_trans(mp, XFS_LOG_FORCE); } mp->m_sync_seq++; wake_up(&mp->m_wait_single_sync_task); diff --git a/fs/xfs/quota/xfs_qm_syscalls.c b/fs/xfs/quota/xfs_qm_syscalls.c index 4e4276b956e8..5d1a3b98a6e6 100644 --- a/fs/xfs/quota/xfs_qm_syscalls.c +++ b/fs/xfs/quota/xfs_qm_syscalls.c @@ -876,7 +876,6 @@ xfs_dqrele_inode( ip->i_gdquot = NULL; } xfs_iput(ip, XFS_ILOCK_EXCL); - IRELE(ip); return 0; } diff --git a/fs/xfs/xfs_dfrag.c b/fs/xfs/xfs_dfrag.c index 7465f9ee125f..ab89a7e94a0f 100644 --- a/fs/xfs/xfs_dfrag.c +++ b/fs/xfs/xfs_dfrag.c @@ -206,10 +206,10 @@ xfs_swap_extents( * process that the file was not changed out from * under it. */ - if ((sbp->bs_ctime.tv_sec != ip->i_d.di_ctime.t_sec) || - (sbp->bs_ctime.tv_nsec != ip->i_d.di_ctime.t_nsec) || - (sbp->bs_mtime.tv_sec != ip->i_d.di_mtime.t_sec) || - (sbp->bs_mtime.tv_nsec != ip->i_d.di_mtime.t_nsec)) { + if ((sbp->bs_ctime.tv_sec != VFS_I(ip)->i_ctime.tv_sec) || + (sbp->bs_ctime.tv_nsec != VFS_I(ip)->i_ctime.tv_nsec) || + (sbp->bs_mtime.tv_sec != VFS_I(ip)->i_mtime.tv_sec) || + (sbp->bs_mtime.tv_nsec != VFS_I(ip)->i_mtime.tv_nsec)) { error = XFS_ERROR(EBUSY); goto out_unlock; } diff --git a/fs/xfs/xfs_dir2_leaf.c b/fs/xfs/xfs_dir2_leaf.c index fa913e459442..41ad537c49e9 100644 --- a/fs/xfs/xfs_dir2_leaf.c +++ b/fs/xfs/xfs_dir2_leaf.c @@ -854,6 +854,7 @@ xfs_dir2_leaf_getdents( */ ra_want = howmany(bufsize + mp->m_dirblksize, mp->m_sb.sb_blocksize) - 1; + ASSERT(ra_want >= 0); /* * If we don't have as many as we want, and we haven't @@ -1088,7 +1089,8 @@ xfs_dir2_leaf_getdents( */ ptr += length; curoff += length; - bufsize -= length; + /* bufsize may have just been a guess; don't go negative */ + bufsize = bufsize > length ? bufsize - length : 0; } /* diff --git a/fs/xfs/xfs_ialloc.c b/fs/xfs/xfs_ialloc.c index ab64f3efb43b..0785797db828 100644 --- a/fs/xfs/xfs_ialloc.c +++ b/fs/xfs/xfs_ialloc.c @@ -880,6 +880,7 @@ nextag: * Not in range - save last search * location and allocate a new inode */ + xfs_btree_del_cursor(tcur, XFS_BTREE_NOERROR); pag->pagl_leftrec = trec.ir_startino; pag->pagl_rightrec = rec.ir_startino; pag->pagl_pagino = pagino; diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c index c1dc7ef5a1d8..b92a4fa2a0a1 100644 --- a/fs/xfs/xfs_inode.c +++ b/fs/xfs/xfs_inode.c @@ -3068,9 +3068,9 @@ xfs_iflush_int( SYNCHRONIZE(); /* - * Make sure to get the latest atime from the Linux inode. + * Make sure to get the latest timestamps from the Linux inode. */ - xfs_synchronize_atime(ip); + xfs_synchronize_times(ip); if (XFS_TEST_ERROR(be16_to_cpu(dip->di_magic) != XFS_DINODE_MAGIC, mp, XFS_ERRTAG_IFLUSH_1, XFS_RANDOM_IFLUSH_1)) { diff --git a/fs/xfs/xfs_inode.h b/fs/xfs/xfs_inode.h index 0b38b9a869ec..41555de1d1db 100644 --- a/fs/xfs/xfs_inode.h +++ b/fs/xfs/xfs_inode.h @@ -504,7 +504,7 @@ void xfs_ichgtime(xfs_inode_t *, int); void xfs_lock_inodes(xfs_inode_t **, int, uint); void xfs_lock_two_inodes(xfs_inode_t *, xfs_inode_t *, uint); -void xfs_synchronize_atime(xfs_inode_t *); +void xfs_synchronize_times(xfs_inode_t *); void xfs_mark_inode_dirty_sync(xfs_inode_t *); #if defined(XFS_INODE_TRACE) diff --git a/fs/xfs/xfs_inode_item.c b/fs/xfs/xfs_inode_item.c index 47d5b663c37e..9794b876d6ff 100644 --- a/fs/xfs/xfs_inode_item.c +++ b/fs/xfs/xfs_inode_item.c @@ -232,6 +232,15 @@ xfs_inode_item_format( nvecs = 1; /* + * Make sure the linux inode is dirty. We do this before + * clearing i_update_core as the VFS will call back into + * XFS here and set i_update_core, so we need to dirty the + * inode first so that the ordering of i_update_core and + * unlogged modifications still works as described below. + */ + xfs_mark_inode_dirty_sync(ip); + + /* * Clear i_update_core if the timestamps (or any other * non-transactional modification) need flushing/logging * and we're about to log them with the rest of the core. @@ -263,14 +272,9 @@ xfs_inode_item_format( } /* - * Make sure to get the latest atime from the Linux inode. + * Make sure to get the latest timestamps from the Linux inode. */ - xfs_synchronize_atime(ip); - - /* - * make sure the linux inode is dirty - */ - xfs_mark_inode_dirty_sync(ip); + xfs_synchronize_times(ip); vecp->i_addr = (xfs_caddr_t)&ip->i_d; vecp->i_len = sizeof(struct xfs_icdinode); diff --git a/fs/xfs/xfs_itable.c b/fs/xfs/xfs_itable.c index b68f9107e26c..62efab2f3839 100644 --- a/fs/xfs/xfs_itable.c +++ b/fs/xfs/xfs_itable.c @@ -59,6 +59,7 @@ xfs_bulkstat_one_iget( { xfs_icdinode_t *dic; /* dinode core info pointer */ xfs_inode_t *ip; /* incore inode pointer */ + struct inode *inode; int error; error = xfs_iget(mp, NULL, ino, @@ -72,6 +73,7 @@ xfs_bulkstat_one_iget( ASSERT(ip->i_imap.im_blkno != 0); dic = &ip->i_d; + inode = VFS_I(ip); /* xfs_iget returns the following without needing * further change. @@ -83,16 +85,19 @@ xfs_bulkstat_one_iget( buf->bs_uid = dic->di_uid; buf->bs_gid = dic->di_gid; buf->bs_size = dic->di_size; + /* - * We are reading the atime from the Linux inode because the - * dinode might not be uptodate. + * We need to read the timestamps from the Linux inode because + * the VFS keeps writing directly into the inode structure instead + * of telling us about the updates. */ - buf->bs_atime.tv_sec = VFS_I(ip)->i_atime.tv_sec; - buf->bs_atime.tv_nsec = VFS_I(ip)->i_atime.tv_nsec; - buf->bs_mtime.tv_sec = dic->di_mtime.t_sec; - buf->bs_mtime.tv_nsec = dic->di_mtime.t_nsec; - buf->bs_ctime.tv_sec = dic->di_ctime.t_sec; - buf->bs_ctime.tv_nsec = dic->di_ctime.t_nsec; + buf->bs_atime.tv_sec = inode->i_atime.tv_sec; + buf->bs_atime.tv_nsec = inode->i_atime.tv_nsec; + buf->bs_mtime.tv_sec = inode->i_mtime.tv_sec; + buf->bs_mtime.tv_nsec = inode->i_mtime.tv_nsec; + buf->bs_ctime.tv_sec = inode->i_ctime.tv_sec; + buf->bs_ctime.tv_nsec = inode->i_ctime.tv_nsec; + buf->bs_xflags = xfs_ip2xflags(ip); buf->bs_extsize = dic->di_extsize << mp->m_sb.sb_blocklog; buf->bs_extents = dic->di_nextents; diff --git a/fs/xfs/xfs_log_recover.c b/fs/xfs/xfs_log_recover.c index 1099395d7d6c..fb17f8226b09 100644 --- a/fs/xfs/xfs_log_recover.c +++ b/fs/xfs/xfs_log_recover.c @@ -1980,7 +1980,7 @@ xlog_recover_do_reg_buffer( "XFS: NULL dquot in %s.", __func__); goto next; } - if (item->ri_buf[i].i_len < sizeof(xfs_dqblk_t)) { + if (item->ri_buf[i].i_len < sizeof(xfs_disk_dquot_t)) { cmn_err(CE_ALERT, "XFS: dquot too small (%d) in %s.", item->ri_buf[i].i_len, __func__); @@ -2635,7 +2635,7 @@ xlog_recover_do_dquot_trans( "XFS: NULL dquot in %s.", __func__); return XFS_ERROR(EIO); } - if (item->ri_buf[1].i_len < sizeof(xfs_dqblk_t)) { + if (item->ri_buf[1].i_len < sizeof(xfs_disk_dquot_t)) { cmn_err(CE_ALERT, "XFS: dquot too small (%d) in %s.", item->ri_buf[1].i_len, __func__); diff --git a/fs/xfs/xfs_trans_ail.c b/fs/xfs/xfs_trans_ail.c index f31271c30de9..2ffc570679be 100644 --- a/fs/xfs/xfs_trans_ail.c +++ b/fs/xfs/xfs_trans_ail.c @@ -467,6 +467,7 @@ xfs_trans_ail_update( { xfs_log_item_t *dlip = NULL; xfs_log_item_t *mlip; /* ptr to minimum lip */ + xfs_lsn_t tail_lsn; mlip = xfs_ail_min(ailp); @@ -483,8 +484,16 @@ xfs_trans_ail_update( if (mlip == dlip) { mlip = xfs_ail_min(ailp); + /* + * It is not safe to access mlip after the AIL lock is + * dropped, so we must get a copy of li_lsn before we do + * so. This is especially important on 32-bit platforms + * where accessing and updating 64-bit values like li_lsn + * is not atomic. + */ + tail_lsn = mlip->li_lsn; spin_unlock(&ailp->xa_lock); - xfs_log_move_tail(ailp->xa_mount, mlip->li_lsn); + xfs_log_move_tail(ailp->xa_mount, tail_lsn); } else { spin_unlock(&ailp->xa_lock); } @@ -514,6 +523,7 @@ xfs_trans_ail_delete( { xfs_log_item_t *dlip; xfs_log_item_t *mlip; + xfs_lsn_t tail_lsn; if (lip->li_flags & XFS_LI_IN_AIL) { mlip = xfs_ail_min(ailp); @@ -527,9 +537,16 @@ xfs_trans_ail_delete( if (mlip == dlip) { mlip = xfs_ail_min(ailp); + /* + * It is not safe to access mlip after the AIL lock + * is dropped, so we must get a copy of li_lsn + * before we do so. This is especially important + * on 32-bit platforms where accessing and updating + * 64-bit values like li_lsn is not atomic. + */ + tail_lsn = mlip ? mlip->li_lsn : 0; spin_unlock(&ailp->xa_lock); - xfs_log_move_tail(ailp->xa_mount, - (mlip ? mlip->li_lsn : 0)); + xfs_log_move_tail(ailp->xa_mount, tail_lsn); } else { spin_unlock(&ailp->xa_lock); } diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c index a434f287962d..b572f7e840e0 100644 --- a/fs/xfs/xfs_vnodeops.c +++ b/fs/xfs/xfs_vnodeops.c @@ -2476,12 +2476,6 @@ xfs_reclaim( ASSERT(XFS_FORCED_SHUTDOWN(ip->i_mount) || ip->i_delayed_blks == 0); /* - * Make sure the atime in the XFS inode is correct before freeing the - * Linux inode. - */ - xfs_synchronize_atime(ip); - - /* * If we have nothing to flush with this inode then complete the * teardown now, otherwise break the link between the xfs inode and the * linux inode and clean up the xfs inode later. This avoids flushing diff --git a/include/asm-generic/fcntl.h b/include/asm-generic/fcntl.h index 0c3dd8603927..495dc8af4044 100644 --- a/include/asm-generic/fcntl.h +++ b/include/asm-generic/fcntl.h @@ -73,14 +73,23 @@ #define F_SETSIG 10 /* for sockets. */ #define F_GETSIG 11 /* for sockets. */ #endif + +#ifndef CONFIG_64BIT +#ifndef F_GETLK64 +#define F_GETLK64 12 /* using 'struct flock64' */ +#define F_SETLK64 13 +#define F_SETLKW64 14 +#endif +#endif + #ifndef F_SETOWN_EX -#define F_SETOWN_EX 12 -#define F_GETOWN_EX 13 +#define F_SETOWN_EX 15 +#define F_GETOWN_EX 16 #endif #define F_OWNER_TID 0 #define F_OWNER_PID 1 -#define F_OWNER_GID 2 +#define F_OWNER_PGRP 2 struct f_owner_ex { int type; @@ -139,12 +148,6 @@ struct flock { #ifndef CONFIG_64BIT -#ifndef F_GETLK64 -#define F_GETLK64 12 /* using 'struct flock64' */ -#define F_SETLK64 13 -#define F_SETLKW64 14 -#endif - #ifndef HAVE_ARCH_STRUCT_FLOCK64 #ifndef __ARCH_FLOCK64_PAD #define __ARCH_FLOCK64_PAD diff --git a/include/asm-generic/hardirq.h b/include/asm-generic/hardirq.h index 23bb4dad4962..62f59080e5cc 100644 --- a/include/asm-generic/hardirq.h +++ b/include/asm-generic/hardirq.h @@ -6,7 +6,7 @@ #include <linux/irq.h> typedef struct { - unsigned long __softirq_pending; + unsigned int __softirq_pending; } ____cacheline_aligned irq_cpustat_t; #include <linux/irq_cpustat.h> /* Standard mappings for irq_cpustat_t above */ diff --git a/include/drm/drm_crtc_helper.h b/include/drm/drm_crtc_helper.h index ef47dfd8e5e9..b29e20168b5f 100644 --- a/include/drm/drm_crtc_helper.h +++ b/include/drm/drm_crtc_helper.h @@ -61,6 +61,9 @@ struct drm_crtc_helper_funcs { /* Move the crtc on the current fb to the given position *optional* */ int (*mode_set_base)(struct drm_crtc *crtc, int x, int y, struct drm_framebuffer *old_fb); + + /* reload the current crtc LUT */ + void (*load_lut)(struct drm_crtc *crtc); }; struct drm_encoder_helper_funcs { diff --git a/include/drm/drm_fb_helper.h b/include/drm/drm_fb_helper.h index 4aa5740ce59f..58c892a2cbfa 100644 --- a/include/drm/drm_fb_helper.h +++ b/include/drm/drm_fb_helper.h @@ -39,6 +39,8 @@ struct drm_fb_helper_crtc { struct drm_fb_helper_funcs { void (*gamma_set)(struct drm_crtc *crtc, u16 red, u16 green, u16 blue, int regno); + void (*gamma_get)(struct drm_crtc *crtc, u16 *red, u16 *green, + u16 *blue, int regno); }; /* mode specified on the command line */ @@ -71,6 +73,7 @@ struct drm_fb_helper { }; int drm_fb_helper_single_fb_probe(struct drm_device *dev, + int preferred_bpp, int (*fb_create)(struct drm_device *dev, uint32_t fb_width, uint32_t fb_height, @@ -98,9 +101,11 @@ int drm_fb_helper_setcolreg(unsigned regno, void drm_fb_helper_restore(void); void drm_fb_helper_fill_var(struct fb_info *info, struct drm_framebuffer *fb, uint32_t fb_width, uint32_t fb_height); -void drm_fb_helper_fill_fix(struct fb_info *info, uint32_t pitch); +void drm_fb_helper_fill_fix(struct fb_info *info, uint32_t pitch, + uint32_t depth); int drm_fb_helper_add_connector(struct drm_connector *connector); int drm_fb_helper_parse_command_line(struct drm_device *dev); +int drm_fb_helper_setcmap(struct fb_cmap *cmap, struct fb_info *info); #endif diff --git a/include/drm/drm_pciids.h b/include/drm/drm_pciids.h index 3f6e545609be..e6f3b120f51a 100644 --- a/include/drm/drm_pciids.h +++ b/include/drm/drm_pciids.h @@ -80,7 +80,7 @@ {0x1002, 0x5158, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV200}, \ {0x1002, 0x5159, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV100}, \ {0x1002, 0x515A, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV100}, \ - {0x1002, 0x515E, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV100}, \ + {0x1002, 0x515E, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV100|RADEON_SINGLE_CRTC}, \ {0x1002, 0x5460, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV380|RADEON_IS_MOBILITY}, \ {0x1002, 0x5462, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV380|RADEON_IS_MOBILITY}, \ {0x1002, 0x5464, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV380|RADEON_IS_MOBILITY}, \ @@ -113,7 +113,7 @@ {0x1002, 0x5962, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV280}, \ {0x1002, 0x5964, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV280}, \ {0x1002, 0x5965, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV280}, \ - {0x1002, 0x5969, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV100}, \ + {0x1002, 0x5969, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RV100|RADEON_SINGLE_CRTC}, \ {0x1002, 0x5a41, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RS400|RADEON_IS_IGP|RADEON_IS_IGPGART}, \ {0x1002, 0x5a42, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RS400|RADEON_IS_IGP|RADEON_IS_MOBILITY|RADEON_IS_IGPGART}, \ {0x1002, 0x5a61, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RS400|RADEON_IS_IGP|RADEON_IS_IGPGART}, \ diff --git a/include/linux/Kbuild b/include/linux/Kbuild index cff4a101f266..1feed71551c9 100644 --- a/include/linux/Kbuild +++ b/include/linux/Kbuild @@ -126,6 +126,7 @@ header-y += nfs_mount.h header-y += nl80211.h header-y += param.h header-y += pci_regs.h +header-y += perf_event.h header-y += pfkeyv2.h header-y += pg.h header-y += phantom.h @@ -363,6 +364,7 @@ unifdef-y += utsname.h unifdef-y += videodev2.h unifdef-y += videodev.h unifdef-y += virtio_config.h +unifdef-y += virtio_ids.h unifdef-y += virtio_blk.h unifdef-y += virtio_net.h unifdef-y += virtio_9p.h diff --git a/include/linux/ata.h b/include/linux/ata.h index 6299a259ed19..4fb357312b3b 100644 --- a/include/linux/ata.h +++ b/include/linux/ata.h @@ -334,9 +334,12 @@ enum { SETFEATURES_SATA_DISABLE = 0x90, /* Disable use of SATA feature */ /* SETFEATURE Sector counts for SATA features */ - SATA_AN = 0x05, /* Asynchronous Notification */ - SATA_DIPM = 0x03, /* Device Initiated Power Management */ - SATA_FPDMA_AA = 0x02, /* DMA Setup FIS Auto-Activate */ + SATA_FPDMA_OFFSET = 0x01, /* FPDMA non-zero buffer offsets */ + SATA_FPDMA_AA = 0x02, /* FPDMA Setup FIS Auto-Activate */ + SATA_DIPM = 0x03, /* Device Initiated Power Management */ + SATA_FPDMA_IN_ORDER = 0x04, /* FPDMA in-order data delivery */ + SATA_AN = 0x05, /* Asynchronous Notification */ + SATA_SSP = 0x06, /* Software Settings Preservation */ /* feature values for SET_MAX */ ATA_SET_MAX_ADDR = 0x00, diff --git a/include/linux/blkdev.h b/include/linux/blkdev.h index 25119041e034..221cecd86bd3 100644 --- a/include/linux/blkdev.h +++ b/include/linux/blkdev.h @@ -1172,11 +1172,7 @@ static inline void put_dev_sector(Sector p) } struct work_struct; -struct delayed_work; int kblockd_schedule_work(struct request_queue *q, struct work_struct *work); -int kblockd_schedule_delayed_work(struct request_queue *q, - struct delayed_work *work, - unsigned long delay); #define MODULE_ALIAS_BLOCKDEV(major,minor) \ MODULE_ALIAS("block-major-" __stringify(major) "-" __stringify(minor)) diff --git a/include/linux/cpufreq.h b/include/linux/cpufreq.h index 44717eb47639..79a2340d83cd 100644 --- a/include/linux/cpufreq.h +++ b/include/linux/cpufreq.h @@ -291,8 +291,15 @@ struct global_attr { int cpufreq_get_policy(struct cpufreq_policy *policy, unsigned int cpu); int cpufreq_update_policy(unsigned int cpu); +#ifdef CONFIG_CPU_FREQ /* query the current CPU frequency (in kHz). If zero, cpufreq couldn't detect it */ unsigned int cpufreq_get(unsigned int cpu); +#else +static inline unsigned int cpufreq_get(unsigned int cpu) +{ + return 0; +} +#endif /* query the last known CPU freq (in kHz). If zero, cpufreq couldn't detect it */ #ifdef CONFIG_CPU_FREQ diff --git a/include/linux/device.h b/include/linux/device.h index aca31bf7d8ed..2ea3e4921812 100644 --- a/include/linux/device.h +++ b/include/linux/device.h @@ -124,7 +124,9 @@ struct device_driver { struct bus_type *bus; struct module *owner; - const char *mod_name; /* used for built-in modules */ + const char *mod_name; /* used for built-in modules */ + + bool suppress_bind_attrs; /* disables bind/unbind via sysfs */ int (*probe) (struct device *dev); int (*remove) (struct device *dev); diff --git a/include/linux/elf.h b/include/linux/elf.h index 45a937be6d38..90a4ed0ea0e5 100644 --- a/include/linux/elf.h +++ b/include/linux/elf.h @@ -361,6 +361,7 @@ typedef struct elf64_shdr { #define NT_PPC_VSX 0x102 /* PowerPC VSX registers */ #define NT_386_TLS 0x200 /* i386 TLS slots (struct user_desc) */ #define NT_386_IOPERM 0x201 /* x86 io permission bitmap (1=deny) */ +#define NT_PRXSTATUS 0x300 /* s390 upper register halves */ /* Note header in a PT_NOTE section */ diff --git a/include/linux/ext3_fs_i.h b/include/linux/ext3_fs_i.h index ca1bfe90004f..93e7428156ba 100644 --- a/include/linux/ext3_fs_i.h +++ b/include/linux/ext3_fs_i.h @@ -137,6 +137,14 @@ struct ext3_inode_info { * by other means, so we have truncate_mutex. */ struct mutex truncate_mutex; + + /* + * Transactions that contain inode's metadata needed to complete + * fsync and fdatasync, respectively. + */ + atomic_t i_sync_tid; + atomic_t i_datasync_tid; + struct inode vfs_inode; }; diff --git a/include/linux/fb.h b/include/linux/fb.h index a34bdf5a9d23..de9c722e7b90 100644 --- a/include/linux/fb.h +++ b/include/linux/fb.h @@ -669,12 +669,6 @@ struct fb_ops { /* perform fb specific mmap */ int (*fb_mmap)(struct fb_info *info, struct vm_area_struct *vma); - /* save current hardware state */ - void (*fb_save_state)(struct fb_info *info); - - /* restore saved state */ - void (*fb_restore_state)(struct fb_info *info); - /* get capability given var */ void (*fb_get_caps)(struct fb_info *info, struct fb_blit_caps *caps, struct fb_var_screeninfo *var); diff --git a/include/linux/ftrace.h b/include/linux/ftrace.h index cd3d2abaf30a..0b4f97d24d7f 100644 --- a/include/linux/ftrace.h +++ b/include/linux/ftrace.h @@ -241,7 +241,7 @@ extern void ftrace_enable_daemon(void); # define ftrace_set_filter(buf, len, reset) do { } while (0) # define ftrace_disable_daemon() do { } while (0) # define ftrace_enable_daemon() do { } while (0) -static inline void ftrace_release(void *start, unsigned long size) { } +static inline void ftrace_release_mod(struct module *mod) {} static inline int register_ftrace_command(struct ftrace_func_command *cmd) { return -EINVAL; diff --git a/include/linux/futex.h b/include/linux/futex.h index 8ec17997d94f..1e5a26d79232 100644 --- a/include/linux/futex.h +++ b/include/linux/futex.h @@ -33,8 +33,8 @@ #define FUTEX_LOCK_PI_PRIVATE (FUTEX_LOCK_PI | FUTEX_PRIVATE_FLAG) #define FUTEX_UNLOCK_PI_PRIVATE (FUTEX_UNLOCK_PI | FUTEX_PRIVATE_FLAG) #define FUTEX_TRYLOCK_PI_PRIVATE (FUTEX_TRYLOCK_PI | FUTEX_PRIVATE_FLAG) -#define FUTEX_WAIT_BITSET_PRIVATE (FUTEX_WAIT_BITS | FUTEX_PRIVATE_FLAG) -#define FUTEX_WAKE_BITSET_PRIVATE (FUTEX_WAKE_BITS | FUTEX_PRIVATE_FLAG) +#define FUTEX_WAIT_BITSET_PRIVATE (FUTEX_WAIT_BITSET | FUTEX_PRIVATE_FLAG) +#define FUTEX_WAKE_BITSET_PRIVATE (FUTEX_WAKE_BITSET | FUTEX_PRIVATE_FLAG) #define FUTEX_WAIT_REQUEUE_PI_PRIVATE (FUTEX_WAIT_REQUEUE_PI | \ FUTEX_PRIVATE_FLAG) #define FUTEX_CMP_REQUEUE_PI_PRIVATE (FUTEX_CMP_REQUEUE_PI | \ diff --git a/include/linux/genhd.h b/include/linux/genhd.h index 7beaa21b3880..297df45ffd0a 100644 --- a/include/linux/genhd.h +++ b/include/linux/genhd.h @@ -98,7 +98,7 @@ struct hd_struct { int make_it_fail; #endif unsigned long stamp; - int in_flight; + int in_flight[2]; #ifdef CONFIG_SMP struct disk_stats *dkstats; #else @@ -322,18 +322,23 @@ static inline void free_part_stats(struct hd_struct *part) #define part_stat_sub(cpu, gendiskp, field, subnd) \ part_stat_add(cpu, gendiskp, field, -subnd) -static inline void part_inc_in_flight(struct hd_struct *part) +static inline void part_inc_in_flight(struct hd_struct *part, int rw) { - part->in_flight++; + part->in_flight[rw]++; if (part->partno) - part_to_disk(part)->part0.in_flight++; + part_to_disk(part)->part0.in_flight[rw]++; } -static inline void part_dec_in_flight(struct hd_struct *part) +static inline void part_dec_in_flight(struct hd_struct *part, int rw) { - part->in_flight--; + part->in_flight[rw]--; if (part->partno) - part_to_disk(part)->part0.in_flight--; + part_to_disk(part)->part0.in_flight[rw]--; +} + +static inline int part_in_flight(struct hd_struct *part) +{ + return part->in_flight[0] + part->in_flight[1]; } /* block/blk-core.c */ @@ -546,6 +551,8 @@ extern ssize_t part_size_show(struct device *dev, struct device_attribute *attr, char *buf); extern ssize_t part_stat_show(struct device *dev, struct device_attribute *attr, char *buf); +extern ssize_t part_inflight_show(struct device *dev, + struct device_attribute *attr, char *buf); #ifdef CONFIG_FAIL_MAKE_REQUEST extern ssize_t part_fail_show(struct device *dev, struct device_attribute *attr, char *buf); diff --git a/include/linux/i2c.h b/include/linux/i2c.h index 57d41b0abce2..7b40cda57a70 100644 --- a/include/linux/i2c.h +++ b/include/linux/i2c.h @@ -361,6 +361,24 @@ static inline void i2c_set_adapdata(struct i2c_adapter *dev, void *data) dev_set_drvdata(&dev->dev, data); } +/** + * i2c_lock_adapter - Prevent access to an I2C bus segment + * @adapter: Target I2C bus segment + */ +static inline void i2c_lock_adapter(struct i2c_adapter *adapter) +{ + mutex_lock(&adapter->bus_lock); +} + +/** + * i2c_unlock_adapter - Reauthorize access to an I2C bus segment + * @adapter: Target I2C bus segment + */ +static inline void i2c_unlock_adapter(struct i2c_adapter *adapter) +{ + mutex_unlock(&adapter->bus_lock); +} + /*flags for the client struct: */ #define I2C_CLIENT_PEC 0x04 /* Use Packet Error Checking */ #define I2C_CLIENT_TEN 0x10 /* we have a ten bit chip address */ diff --git a/include/linux/i2c/twl4030.h b/include/linux/i2c/twl4030.h index 2d02dfd7076c..508824ee35e6 100644 --- a/include/linux/i2c/twl4030.h +++ b/include/linux/i2c/twl4030.h @@ -349,11 +349,11 @@ struct twl4030_madc_platform_data { int irq_line; }; -/* Boards have uniqe mappings of {col, row} --> keycode. - * Column and row are 4 bits, but range only from 0..7. +/* Boards have uniqe mappings of {row, col} --> keycode. + * Column and row are 8 bits each, but range only from 0..7. * a PERSISTENT_KEY is "always on" and never reported. */ -#define PERSISTENT_KEY(c, r) KEY((c), (r), KEY_RESERVED) +#define PERSISTENT_KEY(r, c) KEY((r), (c), KEY_RESERVED) struct twl4030_keypad_data { const struct matrix_keymap_data *keymap_data; diff --git a/include/linux/init.h b/include/linux/init.h index 400adbb45414..ff8bde520d03 100644 --- a/include/linux/init.h +++ b/include/linux/init.h @@ -271,6 +271,7 @@ void __init parse_early_options(char *cmdline); #else /* MODULE */ /* Don't use these in modules, but some people do... */ +#define early_initcall(fn) module_init(fn) #define core_initcall(fn) module_init(fn) #define postcore_initcall(fn) module_init(fn) #define arch_initcall(fn) module_init(fn) diff --git a/include/linux/input.h b/include/linux/input.h index 0ccfc30cd40f..c2b1a7d244d9 100644 --- a/include/linux/input.h +++ b/include/linux/input.h @@ -1377,6 +1377,10 @@ extern struct class input_class; * methods; erase() is optional. set_gain() and set_autocenter() need * only be implemented if driver sets up FF_GAIN and FF_AUTOCENTER * bits. + * + * Note that playback(), set_gain() and set_autocenter() are called with + * dev->event_lock spinlock held and interrupts off and thus may not + * sleep. */ struct ff_device { int (*upload)(struct input_dev *dev, struct ff_effect *effect, diff --git a/include/linux/interrupt.h b/include/linux/interrupt.h index b78cf8194957..7ca72b74eec7 100644 --- a/include/linux/interrupt.h +++ b/include/linux/interrupt.h @@ -10,7 +10,6 @@ #include <linux/irqreturn.h> #include <linux/irqnr.h> #include <linux/hardirq.h> -#include <linux/sched.h> #include <linux/irqflags.h> #include <linux/smp.h> #include <linux/percpu.h> @@ -610,6 +609,7 @@ extern void debug_poll_all_shared_irqs(void); static inline void debug_poll_all_shared_irqs(void) { } #endif +struct seq_file; int show_interrupts(struct seq_file *p, void *v); struct irq_desc; diff --git a/include/linux/kernel.h b/include/linux/kernel.h index d3cd23f30039..f4e3184fa054 100644 --- a/include/linux/kernel.h +++ b/include/linux/kernel.h @@ -659,6 +659,12 @@ extern int do_sysinfo(struct sysinfo *info); #endif /* __KERNEL__ */ +#ifndef __EXPORTED_HEADERS__ +#ifndef __KERNEL__ +#warning Attempt to use kernel headers from user space, see http://kernelnewbies.org/KernelHeaders +#endif /* __KERNEL__ */ +#endif /* __EXPORTED_HEADERS__ */ + #define SI_LOAD_SHIFT 16 struct sysinfo { long uptime; /* Seconds since boot */ diff --git a/include/linux/libata.h b/include/linux/libata.h index 76319bf03e37..87698640c091 100644 --- a/include/linux/libata.h +++ b/include/linux/libata.h @@ -418,6 +418,17 @@ enum { ATA_TIMING_ACTIVE | ATA_TIMING_RECOVER | ATA_TIMING_DMACK_HOLD | ATA_TIMING_CYCLE | ATA_TIMING_UDMA, + + /* ACPI constants */ + ATA_ACPI_FILTER_SETXFER = 1 << 0, + ATA_ACPI_FILTER_LOCK = 1 << 1, + ATA_ACPI_FILTER_DIPM = 1 << 2, + ATA_ACPI_FILTER_FPDMA_OFFSET = 1 << 3, /* FPDMA non-zero offset */ + ATA_ACPI_FILTER_FPDMA_AA = 1 << 4, /* FPDMA auto activate */ + + ATA_ACPI_FILTER_DEFAULT = ATA_ACPI_FILTER_SETXFER | + ATA_ACPI_FILTER_LOCK | + ATA_ACPI_FILTER_DIPM, }; enum ata_xfer_mask { @@ -587,6 +598,7 @@ struct ata_device { #ifdef CONFIG_ATA_ACPI acpi_handle acpi_handle; union acpi_object *gtf_cache; + unsigned int gtf_filter; #endif /* n_sector is CLEAR_BEGIN, read comment above CLEAR_BEGIN */ u64 n_sectors; /* size of device, if ATA */ diff --git a/include/linux/mmc/host.h b/include/linux/mmc/host.h index 81bb42358595..eaf36364b7d4 100644 --- a/include/linux/mmc/host.h +++ b/include/linux/mmc/host.h @@ -11,6 +11,7 @@ #define LINUX_MMC_HOST_H #include <linux/leds.h> +#include <linux/sched.h> #include <linux/mmc/core.h> diff --git a/include/linux/moduleparam.h b/include/linux/moduleparam.h index 6547c3cdbc4c..82a9124f7d75 100644 --- a/include/linux/moduleparam.h +++ b/include/linux/moduleparam.h @@ -37,7 +37,6 @@ typedef int (*param_set_fn)(const char *val, struct kernel_param *kp); typedef int (*param_get_fn)(char *buffer, struct kernel_param *kp); /* Flag bits for kernel_param.flags */ -#define KPARAM_KMALLOCED 1 #define KPARAM_ISBOOL 2 struct kernel_param { diff --git a/include/linux/nilfs2_fs.h b/include/linux/nilfs2_fs.h index 79fec6af3f9f..ce520402e840 100644 --- a/include/linux/nilfs2_fs.h +++ b/include/linux/nilfs2_fs.h @@ -425,15 +425,6 @@ struct nilfs_dat_entry { }; /** - * struct nilfs_dat_group_desc - block group descriptor - * @dg_nfrees: number of free virtual block numbers in block group - */ -struct nilfs_dat_group_desc { - __le32 dg_nfrees; -}; - - -/** * struct nilfs_snapshot_list - snapshot list * @ssl_next: next checkpoint number on snapshot list * @ssl_prev: previous checkpoint number on snapshot list diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h index da1fda8623e0..84cf1f3b7838 100644 --- a/include/linux/pci_ids.h +++ b/include/linux/pci_ids.h @@ -379,9 +379,6 @@ #define PCI_DEVICE_ID_ATI_IXP600_IDE 0x438c #define PCI_DEVICE_ID_ATI_IXP700_SATA 0x4390 #define PCI_DEVICE_ID_ATI_IXP700_IDE 0x439c -/* AMD SB Chipset */ -#define PCI_DEVICE_ID_AMD_SB900_IDE 0x780c -#define PCI_DEVICE_ID_AMD_SB900_SATA_IDE 0x7800 #define PCI_VENDOR_ID_VLSI 0x1004 #define PCI_DEVICE_ID_VLSI_82C592 0x0005 @@ -485,6 +482,9 @@ #define PCI_DEVICE_ID_IBM_ICOM_V2_ONE_PORT_RVX_ONE_PORT_MDM_PCIE 0x0361 #define PCI_DEVICE_ID_IBM_ICOM_FOUR_PORT_MODEL 0x252 +#define PCI_SUBVENDOR_ID_IBM 0x1014 +#define PCI_SUBDEVICE_ID_IBM_SATURN_SERIAL_ONE_PORT 0x03d4 + #define PCI_VENDOR_ID_UNISYS 0x1018 #define PCI_DEVICE_ID_UNISYS_DMA_DIRECTOR 0x001C @@ -543,7 +543,7 @@ #define PCI_DEVICE_ID_AMD_8131_BRIDGE 0x7450 #define PCI_DEVICE_ID_AMD_8131_APIC 0x7451 #define PCI_DEVICE_ID_AMD_8132_BRIDGE 0x7458 -#define PCI_DEVICE_ID_AMD_SB900_SMBUS 0x780b +#define PCI_DEVICE_ID_AMD_HUDSON2_SMBUS 0x780b #define PCI_DEVICE_ID_AMD_CS5535_IDE 0x208F #define PCI_DEVICE_ID_AMD_CS5536_ISA 0x2090 #define PCI_DEVICE_ID_AMD_CS5536_FLASH 0x2091 @@ -553,9 +553,10 @@ #define PCI_DEVICE_ID_AMD_CS5536_UDC 0x2096 #define PCI_DEVICE_ID_AMD_CS5536_UOC 0x2097 #define PCI_DEVICE_ID_AMD_CS5536_IDE 0x209A - #define PCI_DEVICE_ID_AMD_LX_VIDEO 0x2081 #define PCI_DEVICE_ID_AMD_LX_AES 0x2082 +#define PCI_DEVICE_ID_AMD_HUDSON2_IDE 0x780c +#define PCI_DEVICE_ID_AMD_HUDSON2_SATA_IDE 0x7800 #define PCI_VENDOR_ID_TRIDENT 0x1023 #define PCI_DEVICE_ID_TRIDENT_4DWAVE_DX 0x2000 @@ -776,6 +777,7 @@ #define PCI_DEVICE_ID_TI_X515 0x8036 #define PCI_DEVICE_ID_TI_XX12 0x8039 #define PCI_DEVICE_ID_TI_XX12_FM 0x803b +#define PCI_DEVICE_ID_TI_XIO2000A 0x8231 #define PCI_DEVICE_ID_TI_1130 0xac12 #define PCI_DEVICE_ID_TI_1031 0xac13 #define PCI_DEVICE_ID_TI_1131 0xac15 @@ -1954,6 +1956,8 @@ #define PCI_DEVICE_ID_LAVA_DSERIAL 0x0100 /* 2x 16550 */ #define PCI_DEVICE_ID_LAVA_QUATRO_A 0x0101 /* 2x 16550, half of 4 port */ #define PCI_DEVICE_ID_LAVA_QUATRO_B 0x0102 /* 2x 16550, half of 4 port */ +#define PCI_DEVICE_ID_LAVA_QUATTRO_A 0x0120 /* 2x 16550A, half of 4 port */ +#define PCI_DEVICE_ID_LAVA_QUATTRO_B 0x0121 /* 2x 16550A, half of 4 port */ #define PCI_DEVICE_ID_LAVA_OCTO_A 0x0180 /* 4x 16550A, half of 8 port */ #define PCI_DEVICE_ID_LAVA_OCTO_B 0x0181 /* 4x 16550A, half of 8 port */ #define PCI_DEVICE_ID_LAVA_PORT_PLUS 0x0200 /* 2x 16650 */ @@ -2161,6 +2165,10 @@ #define PCI_DEVICE_ID_ADDIDATA_APCI7420_3 0x700D #define PCI_DEVICE_ID_ADDIDATA_APCI7300_3 0x700E #define PCI_DEVICE_ID_ADDIDATA_APCI7800_3 0x700F +#define PCI_DEVICE_ID_ADDIDATA_APCIe7300 0x7010 +#define PCI_DEVICE_ID_ADDIDATA_APCIe7420 0x7011 +#define PCI_DEVICE_ID_ADDIDATA_APCIe7500 0x7012 +#define PCI_DEVICE_ID_ADDIDATA_APCIe7800 0x7013 #define PCI_VENDOR_ID_PDC 0x15e9 diff --git a/include/linux/perf_event.h b/include/linux/perf_event.h index 3a9d36d1e92a..9e7012689a84 100644 --- a/include/linux/perf_event.h +++ b/include/linux/perf_event.h @@ -442,6 +442,7 @@ enum perf_callchain_context { #include <linux/hrtimer.h> #include <linux/fs.h> #include <linux/pid_namespace.h> +#include <linux/workqueue.h> #include <asm/atomic.h> #define PERF_MAX_STACK_DEPTH 255 @@ -470,8 +471,8 @@ struct hw_perf_event { unsigned long event_base; int idx; }; - union { /* software */ - atomic64_t count; + struct { /* software */ + s64 remaining; struct hrtimer hrtimer; }; }; @@ -513,6 +514,10 @@ struct file; struct perf_mmap_data { struct rcu_head rcu_head; +#ifdef CONFIG_PERF_USE_VMALLOC + struct work_struct work; +#endif + int data_order; int nr_pages; /* nr of data pages */ int writable; /* are we writable */ int nr_locked; /* nr pages mlocked */ diff --git a/include/linux/prctl.h b/include/linux/prctl.h index 931150566ade..a3baeb2c2161 100644 --- a/include/linux/prctl.h +++ b/include/linux/prctl.h @@ -88,6 +88,18 @@ #define PR_TASK_PERF_EVENTS_DISABLE 31 #define PR_TASK_PERF_EVENTS_ENABLE 32 +/* + * Set early/late kill mode for hwpoison memory corruption. + * This influences when the process gets killed on a memory corruption. + */ #define PR_MCE_KILL 33 +# define PR_MCE_KILL_CLEAR 0 +# define PR_MCE_KILL_SET 1 + +# define PR_MCE_KILL_LATE 0 +# define PR_MCE_KILL_EARLY 1 +# define PR_MCE_KILL_DEFAULT 2 + +#define PR_MCE_KILL_GET 34 #endif /* _LINUX_PRCTL_H */ diff --git a/include/linux/rcupdate.h b/include/linux/rcupdate.h index 6fe0363724e9..3ebd0b7bcb08 100644 --- a/include/linux/rcupdate.h +++ b/include/linux/rcupdate.h @@ -77,7 +77,7 @@ extern int rcu_scheduler_active; #error "Unknown RCU implementation specified to kernel configuration" #endif -#define RCU_HEAD_INIT { .next = NULL, .func = NULL } +#define RCU_HEAD_INIT { .next = NULL, .func = NULL } #define RCU_HEAD(head) struct rcu_head head = RCU_HEAD_INIT #define INIT_RCU_HEAD(ptr) do { \ (ptr)->next = NULL; (ptr)->func = NULL; \ @@ -129,12 +129,6 @@ static inline void rcu_read_lock(void) rcu_read_acquire(); } -/** - * rcu_read_unlock - marks the end of an RCU read-side critical section. - * - * See rcu_read_lock() for more information. - */ - /* * So where is rcu_write_lock()? It does not exist, as there is no * way for writers to lock out RCU readers. This is a feature, not @@ -144,6 +138,12 @@ static inline void rcu_read_lock(void) * used as well. RCU does not care how the writers keep out of each * others' way, as long as they do so. */ + +/** + * rcu_read_unlock - marks the end of an RCU read-side critical section. + * + * See rcu_read_lock() for more information. + */ static inline void rcu_read_unlock(void) { rcu_read_release(); @@ -196,6 +196,8 @@ static inline void rcu_read_lock_sched(void) __acquire(RCU_SCHED); rcu_read_acquire(); } + +/* Used by lockdep and tracing: cannot be traced, cannot call lockdep. */ static inline notrace void rcu_read_lock_sched_notrace(void) { preempt_disable_notrace(); @@ -213,6 +215,8 @@ static inline void rcu_read_unlock_sched(void) __release(RCU_SCHED); preempt_enable(); } + +/* Used by lockdep and tracing: cannot be traced, cannot call lockdep. */ static inline notrace void rcu_read_unlock_sched_notrace(void) { __release(RCU_SCHED); diff --git a/include/linux/rcutree.h b/include/linux/rcutree.h index 37682770e9d2..9642c6bcb399 100644 --- a/include/linux/rcutree.h +++ b/include/linux/rcutree.h @@ -30,10 +30,14 @@ #ifndef __LINUX_RCUTREE_H #define __LINUX_RCUTREE_H +struct notifier_block; + extern void rcu_sched_qs(int cpu); extern void rcu_bh_qs(int cpu); - +extern int rcu_cpu_notify(struct notifier_block *self, + unsigned long action, void *hcpu); extern int rcu_needs_cpu(int cpu); +extern int rcu_expedited_torture_stats(char *page); #ifdef CONFIG_TREE_PREEMPT_RCU @@ -72,11 +76,7 @@ static inline void __rcu_read_unlock_bh(void) extern void call_rcu_sched(struct rcu_head *head, void (*func)(struct rcu_head *rcu)); - -static inline void synchronize_rcu_expedited(void) -{ - synchronize_sched_expedited(); -} +extern void synchronize_rcu_expedited(void); static inline void synchronize_rcu_bh_expedited(void) { @@ -85,16 +85,11 @@ static inline void synchronize_rcu_bh_expedited(void) extern void __rcu_init(void); extern void rcu_check_callbacks(int cpu, int user); -extern void rcu_restart_cpu(int cpu); extern long rcu_batches_completed(void); extern long rcu_batches_completed_bh(void); extern long rcu_batches_completed_sched(void); -static inline void rcu_init_sched(void) -{ -} - #ifdef CONFIG_NO_HZ void rcu_enter_nohz(void); void rcu_exit_nohz(void); @@ -107,7 +102,7 @@ static inline void rcu_exit_nohz(void) } #endif /* CONFIG_NO_HZ */ -/* A context switch is a grace period for rcutree. */ +/* A context switch is a grace period for RCU-sched and RCU-bh. */ static inline int rcu_blocking_is_gp(void) { return num_online_cpus() == 1; diff --git a/include/linux/string.h b/include/linux/string.h index 489019ef1694..b8508868d5ad 100644 --- a/include/linux/string.h +++ b/include/linux/string.h @@ -62,7 +62,7 @@ extern char * strnchr(const char *, size_t, int); #ifndef __HAVE_ARCH_STRRCHR extern char * strrchr(const char *,int); #endif -extern char * strstrip(char *); +extern char * __must_check strstrip(char *); #ifndef __HAVE_ARCH_STRSTR extern char * strstr(const char *,const char *); #endif diff --git a/include/linux/suspend.h b/include/linux/suspend.h index cd15df6c63cd..5e781d824e6d 100644 --- a/include/linux/suspend.h +++ b/include/linux/suspend.h @@ -301,6 +301,8 @@ static inline int unregister_pm_notifier(struct notifier_block *nb) #define pm_notifier(fn, pri) do { (void)(fn); } while (0) #endif /* !CONFIG_PM_SLEEP */ +extern struct mutex pm_mutex; + #ifndef CONFIG_HIBERNATION static inline void register_nosave_region(unsigned long b, unsigned long e) { @@ -308,8 +310,23 @@ static inline void register_nosave_region(unsigned long b, unsigned long e) static inline void register_nosave_region_late(unsigned long b, unsigned long e) { } -#endif -extern struct mutex pm_mutex; +static inline void lock_system_sleep(void) {} +static inline void unlock_system_sleep(void) {} + +#else + +/* Let some subsystems like memory hotadd exclude hibernation */ + +static inline void lock_system_sleep(void) +{ + mutex_lock(&pm_mutex); +} + +static inline void unlock_system_sleep(void) +{ + mutex_unlock(&pm_mutex); +} +#endif #endif /* _LINUX_SUSPEND_H */ diff --git a/include/linux/topology.h b/include/linux/topology.h index fc0bf3edeb67..57e63579bfdd 100644 --- a/include/linux/topology.h +++ b/include/linux/topology.h @@ -129,7 +129,7 @@ int arch_update_cpu_topology(void); | 1*SD_BALANCE_FORK \ | 0*SD_BALANCE_WAKE \ | 1*SD_WAKE_AFFINE \ - | 1*SD_PREFER_LOCAL \ + | 0*SD_PREFER_LOCAL \ | 0*SD_SHARE_CPUPOWER \ | 1*SD_SHARE_PKG_RESOURCES \ | 0*SD_SERIALIZE \ @@ -162,7 +162,7 @@ int arch_update_cpu_topology(void); | 1*SD_BALANCE_FORK \ | 0*SD_BALANCE_WAKE \ | 1*SD_WAKE_AFFINE \ - | 1*SD_PREFER_LOCAL \ + | 0*SD_PREFER_LOCAL \ | 0*SD_SHARE_CPUPOWER \ | 0*SD_SHARE_PKG_RESOURCES \ | 0*SD_SERIALIZE \ diff --git a/include/linux/trace_seq.h b/include/linux/trace_seq.h index c134dd1fe6b6..09077f6ed128 100644 --- a/include/linux/trace_seq.h +++ b/include/linux/trace_seq.h @@ -7,7 +7,7 @@ /* * Trace sequences are used to allow a function to call several other functions - * to create a string of data to use (up to a max of PAGE_SIZE. + * to create a string of data to use (up to a max of PAGE_SIZE). */ struct trace_seq { diff --git a/include/linux/usb/serial.h b/include/linux/usb/serial.h index c17eb64d7213..ce911ebf91e8 100644 --- a/include/linux/usb/serial.h +++ b/include/linux/usb/serial.h @@ -150,6 +150,7 @@ struct usb_serial { struct usb_interface *interface; unsigned char disconnected:1; unsigned char suspending:1; + unsigned char attached:1; unsigned char minor; unsigned char num_ports; unsigned char num_port_pointers; diff --git a/include/linux/virtio_9p.h b/include/linux/virtio_9p.h index ea7226a45acb..095e10d148b4 100644 --- a/include/linux/virtio_9p.h +++ b/include/linux/virtio_9p.h @@ -2,6 +2,7 @@ #define _LINUX_VIRTIO_9P_H /* This header is BSD licensed so anyone can use the definitions to implement * compatible drivers/servers. */ +#include <linux/virtio_ids.h> #include <linux/virtio_config.h> /* Maximum number of virtio channels per partition (1 for now) */ diff --git a/include/linux/virtio_balloon.h b/include/linux/virtio_balloon.h index 09d730085060..1418f048cb34 100644 --- a/include/linux/virtio_balloon.h +++ b/include/linux/virtio_balloon.h @@ -2,6 +2,7 @@ #define _LINUX_VIRTIO_BALLOON_H /* This header is BSD licensed so anyone can use the definitions to implement * compatible drivers/servers. */ +#include <linux/virtio_ids.h> #include <linux/virtio_config.h> /* The feature bitmap for virtio balloon */ diff --git a/include/linux/virtio_blk.h b/include/linux/virtio_blk.h index 15cb666581d7..fd294c56d571 100644 --- a/include/linux/virtio_blk.h +++ b/include/linux/virtio_blk.h @@ -3,6 +3,7 @@ /* This header is BSD licensed so anyone can use the definitions to implement * compatible drivers/servers. */ #include <linux/types.h> +#include <linux/virtio_ids.h> #include <linux/virtio_config.h> /* Feature bits */ @@ -13,11 +14,8 @@ #define VIRTIO_BLK_F_RO 5 /* Disk is read-only */ #define VIRTIO_BLK_F_BLK_SIZE 6 /* Block size of disk is available*/ #define VIRTIO_BLK_F_SCSI 7 /* Supports scsi command passthru */ -#define VIRTIO_BLK_F_IDENTIFY 8 /* ATA IDENTIFY supported */ #define VIRTIO_BLK_F_FLUSH 9 /* Cache flush command support */ -#define VIRTIO_BLK_ID_BYTES (sizeof(__u16[256])) /* IDENTIFY DATA */ - struct virtio_blk_config { /* The capacity (in 512-byte sectors). */ __u64 capacity; @@ -33,7 +31,6 @@ struct virtio_blk_config { } geometry; /* block size of device (if VIRTIO_BLK_F_BLK_SIZE) */ __u32 blk_size; - __u8 identify[VIRTIO_BLK_ID_BYTES]; } __attribute__((packed)); /* diff --git a/include/linux/virtio_console.h b/include/linux/virtio_console.h index b5f519806014..fe885174cc1f 100644 --- a/include/linux/virtio_console.h +++ b/include/linux/virtio_console.h @@ -1,6 +1,7 @@ #ifndef _LINUX_VIRTIO_CONSOLE_H #define _LINUX_VIRTIO_CONSOLE_H #include <linux/types.h> +#include <linux/virtio_ids.h> #include <linux/virtio_config.h> /* This header, excluding the #ifdef __KERNEL__ part, is BSD licensed so * anyone can use the definitions to implement compatible drivers/servers. */ diff --git a/include/linux/virtio_net.h b/include/linux/virtio_net.h index 1f41734bbb77..085e42298ce5 100644 --- a/include/linux/virtio_net.h +++ b/include/linux/virtio_net.h @@ -3,6 +3,7 @@ /* This header is BSD licensed so anyone can use the definitions to implement * compatible drivers/servers. */ #include <linux/types.h> +#include <linux/virtio_ids.h> #include <linux/virtio_config.h> #include <linux/if_ether.h> diff --git a/include/linux/virtio_rng.h b/include/linux/virtio_rng.h index 48121c3c434b..c4d5de896f0c 100644 --- a/include/linux/virtio_rng.h +++ b/include/linux/virtio_rng.h @@ -2,6 +2,7 @@ #define _LINUX_VIRTIO_RNG_H /* This header is BSD licensed so anyone can use the definitions to implement * compatible drivers/servers. */ +#include <linux/virtio_ids.h> #include <linux/virtio_config.h> #endif /* _LINUX_VIRTIO_RNG_H */ diff --git a/include/linux/workqueue.h b/include/linux/workqueue.h index 7ef0c7b94f31..cf24c20de9e4 100644 --- a/include/linux/workqueue.h +++ b/include/linux/workqueue.h @@ -207,6 +207,7 @@ extern int queue_delayed_work_on(int cpu, struct workqueue_struct *wq, extern void flush_workqueue(struct workqueue_struct *wq); extern void flush_scheduled_work(void); +extern void flush_delayed_work(struct delayed_work *work); extern int schedule_work(struct work_struct *work); extern int schedule_work_on(int cpu, struct work_struct *work); diff --git a/include/net/9p/client.h b/include/net/9p/client.h index e26812274b75..fb00b329f0d3 100644 --- a/include/net/9p/client.h +++ b/include/net/9p/client.h @@ -159,8 +159,7 @@ struct p9_client { * @qid: the &p9_qid server identifier this handle points to * @iounit: the server reported maximum transaction size for this file * @uid: the numeric uid of the local user who owns this handle - * @aux: transport specific information (unused?) - * @rdir_fpos: tracks offset of file position when reading directory contents + * @rdir: readdir accounting structure (allocated on demand) * @flist: per-client-instance fid tracking * @dlist: per-dentry fid tracking * @@ -174,9 +173,9 @@ struct p9_fid { struct p9_qid qid; u32 iounit; uid_t uid; - void *aux; - int rdir_fpos; + void *rdir; + struct list_head flist; struct list_head dlist; /* list of all fids attached to a dentry */ }; diff --git a/include/pcmcia/ss.h b/include/pcmcia/ss.h index d696a692d94a..e0f6feb8588c 100644 --- a/include/pcmcia/ss.h +++ b/include/pcmcia/ss.h @@ -262,6 +262,8 @@ struct pcmcia_socket { struct device dev; /* data internal to the socket driver */ void *driver_data; + /* status of the card during resume from a system sleep state */ + int resume_status; }; @@ -280,6 +282,8 @@ extern struct pccard_resource_ops pccard_nonstatic_ops; /* socket drivers are expected to use these callbacks in their .drv struct */ extern int pcmcia_socket_dev_suspend(struct device *dev); +extern void pcmcia_socket_dev_early_resume(struct device *dev); +extern void pcmcia_socket_dev_late_resume(struct device *dev); extern int pcmcia_socket_dev_resume(struct device *dev); /* socket drivers use this callback in their IRQ handler */ diff --git a/include/scsi/libiscsi.h b/include/scsi/libiscsi.h index 887e57e3e223..a72edd4eceec 100644 --- a/include/scsi/libiscsi.h +++ b/include/scsi/libiscsi.h @@ -303,6 +303,7 @@ struct iscsi_session { int cmds_max; /* size of cmds array */ struct iscsi_task **cmds; /* Original Cmds arr */ struct iscsi_pool cmdpool; /* PDU's pool */ + void *dd_data; /* LLD private data */ }; enum { @@ -363,7 +364,7 @@ extern int iscsi_target_alloc(struct scsi_target *starget); */ extern struct iscsi_cls_session * iscsi_session_setup(struct iscsi_transport *, struct Scsi_Host *shost, - uint16_t, int, uint32_t, unsigned int); + uint16_t, int, int, uint32_t, unsigned int); extern void iscsi_session_teardown(struct iscsi_cls_session *); extern void iscsi_session_recovery_timedout(struct iscsi_cls_session *); extern int iscsi_set_param(struct iscsi_cls_conn *cls_conn, diff --git a/include/scsi/scsi.h b/include/scsi/scsi.h index 084478e14d24..34c46ab5c31b 100644 --- a/include/scsi/scsi.h +++ b/include/scsi/scsi.h @@ -129,6 +129,9 @@ struct scsi_cmnd; #define MI_REPORT_TARGET_PGS 0x0a /* values for maintenance out */ #define MO_SET_TARGET_PGS 0x0a +/* values for variable length command */ +#define READ_32 0x09 +#define WRITE_32 0x0b /* Values for T10/04-262r7 */ #define ATA_16 0x85 /* 16-byte pass-thru */ diff --git a/include/scsi/scsi_cmnd.h b/include/scsi/scsi_cmnd.h index 3878d1dc7f59..a5e885a111df 100644 --- a/include/scsi/scsi_cmnd.h +++ b/include/scsi/scsi_cmnd.h @@ -229,10 +229,6 @@ enum scsi_prot_operations { /* OS-HBA: Protected, HBA-Target: Protected */ SCSI_PROT_READ_PASS, SCSI_PROT_WRITE_PASS, - - /* OS-HBA: Protected, HBA-Target: Protected, checksum conversion */ - SCSI_PROT_READ_CONVERT, - SCSI_PROT_WRITE_CONVERT, }; static inline void scsi_set_prot_op(struct scsi_cmnd *scmd, unsigned char op) diff --git a/include/scsi/scsi_host.h b/include/scsi/scsi_host.h index b62a097b3ecb..47941fc5aba7 100644 --- a/include/scsi/scsi_host.h +++ b/include/scsi/scsi_host.h @@ -797,24 +797,24 @@ static inline unsigned int scsi_host_get_prot(struct Scsi_Host *shost) static inline unsigned int scsi_host_dif_capable(struct Scsi_Host *shost, unsigned int target_type) { - switch (target_type) { - case 1: return shost->prot_capabilities & SHOST_DIF_TYPE1_PROTECTION; - case 2: return shost->prot_capabilities & SHOST_DIF_TYPE2_PROTECTION; - case 3: return shost->prot_capabilities & SHOST_DIF_TYPE3_PROTECTION; - } + static unsigned char cap[] = { 0, + SHOST_DIF_TYPE1_PROTECTION, + SHOST_DIF_TYPE2_PROTECTION, + SHOST_DIF_TYPE3_PROTECTION }; - return 0; + return shost->prot_capabilities & cap[target_type] ? target_type : 0; } static inline unsigned int scsi_host_dix_capable(struct Scsi_Host *shost, unsigned int target_type) { - switch (target_type) { - case 0: return shost->prot_capabilities & SHOST_DIX_TYPE0_PROTECTION; - case 1: return shost->prot_capabilities & SHOST_DIX_TYPE1_PROTECTION; - case 2: return shost->prot_capabilities & SHOST_DIX_TYPE2_PROTECTION; - case 3: return shost->prot_capabilities & SHOST_DIX_TYPE3_PROTECTION; - } +#if defined(CONFIG_BLK_DEV_INTEGRITY) + static unsigned char cap[] = { SHOST_DIX_TYPE0_PROTECTION, + SHOST_DIX_TYPE1_PROTECTION, + SHOST_DIX_TYPE2_PROTECTION, + SHOST_DIX_TYPE3_PROTECTION }; + return shost->prot_capabilities & cap[target_type]; +#endif return 0; } diff --git a/init/Kconfig b/init/Kconfig index c7bac39d6c61..9e03ef8b311e 100644 --- a/init/Kconfig +++ b/init/Kconfig @@ -297,7 +297,7 @@ config AUDIT config AUDITSYSCALL bool "Enable system-call auditing support" - depends on AUDIT && (X86 || PPC || PPC64 || S390 || IA64 || UML || SPARC64|| SUPERH) + depends on AUDIT && (X86 || PPC || S390 || IA64 || UML || SPARC64 || SUPERH) default y if SECURITY_SELINUX help Enable low-overhead system-call auditing infrastructure that @@ -921,6 +921,11 @@ config HAVE_PERF_EVENTS help See tools/perf/design.txt for details. +config PERF_USE_VMALLOC + bool + help + See tools/perf/design.txt for details + menu "Kernel Performance Events And Counters" config PERF_EVENTS @@ -932,7 +937,7 @@ config PERF_EVENTS Enable kernel support for various performance events provided by software and hardware. - Software events are supported either build-in or via the + Software events are supported either built-in or via the use of generic tracepoints. Most modern CPUs support performance events via performance @@ -944,7 +949,7 @@ config PERF_EVENTS used to profile the code that runs on that CPU. The Linux Performance Event subsystem provides an abstraction of - these software and hardware cevent apabilities, available via a + these software and hardware event capabilities, available via a system call and used by the "perf" utility in tools/perf/. It provides per task and per CPU counters, and it provides event capabilities on top of those. @@ -976,6 +981,19 @@ config PERF_COUNTERS Say N if unsure. +config DEBUG_PERF_USE_VMALLOC + default n + bool "Debug: use vmalloc to back perf mmap() buffers" + depends on PERF_EVENTS && DEBUG_KERNEL + select PERF_USE_VMALLOC + help + Use vmalloc memory to back perf mmap() buffers. + + Mostly useful for debugging the vmalloc code on platforms + that don't require it. + + Say N if unsure. + endmenu config VM_EVENT_COUNTERS diff --git a/init/main.c b/init/main.c index 7449819a4805..5988debfc505 100644 --- a/init/main.c +++ b/init/main.c @@ -778,7 +778,6 @@ static void __init do_initcalls(void) */ static void __init do_basic_setup(void) { - rcu_init_sched(); /* needed by module_init stage. */ init_workqueues(); cpuset_init_smp(); usermodehelper_init(); diff --git a/kernel/cgroup.c b/kernel/cgroup.c index ca83b73fba19..0249f4be9b5c 100644 --- a/kernel/cgroup.c +++ b/kernel/cgroup.c @@ -1710,14 +1710,13 @@ static ssize_t cgroup_write_X64(struct cgroup *cgrp, struct cftype *cft, return -EFAULT; buffer[nbytes] = 0; /* nul-terminate */ - strstrip(buffer); if (cft->write_u64) { - u64 val = simple_strtoull(buffer, &end, 0); + u64 val = simple_strtoull(strstrip(buffer), &end, 0); if (*end) return -EINVAL; retval = cft->write_u64(cgrp, cft, val); } else { - s64 val = simple_strtoll(buffer, &end, 0); + s64 val = simple_strtoll(strstrip(buffer), &end, 0); if (*end) return -EINVAL; retval = cft->write_s64(cgrp, cft, val); @@ -1753,8 +1752,7 @@ static ssize_t cgroup_write_string(struct cgroup *cgrp, struct cftype *cft, } buffer[nbytes] = 0; /* nul-terminate */ - strstrip(buffer); - retval = cft->write_string(cgrp, cft, buffer); + retval = cft->write_string(cgrp, cft, strstrip(buffer)); if (!retval) retval = nbytes; out: diff --git a/kernel/exit.c b/kernel/exit.c index 5859f598c951..f7864ac2ecc1 100644 --- a/kernel/exit.c +++ b/kernel/exit.c @@ -359,10 +359,8 @@ void __set_special_pids(struct pid *pid) { struct task_struct *curr = current->group_leader; - if (task_session(curr) != pid) { + if (task_session(curr) != pid) change_pid(curr, PIDTYPE_SID, pid); - proc_sid_connector(curr); - } if (task_pgrp(curr) != pid) change_pid(curr, PIDTYPE_PGID, pid); @@ -991,8 +989,6 @@ NORET_TYPE void do_exit(long code) tsk->mempolicy = NULL; #endif #ifdef CONFIG_FUTEX - if (unlikely(!list_empty(&tsk->pi_state_list))) - exit_pi_state_list(tsk); if (unlikely(current->pi_state_cache)) kfree(current->pi_state_cache); #endif diff --git a/kernel/fork.c b/kernel/fork.c index 266c6af6ef1b..166b8c49257c 100644 --- a/kernel/fork.c +++ b/kernel/fork.c @@ -91,7 +91,7 @@ int nr_processes(void) int cpu; int total = 0; - for_each_online_cpu(cpu) + for_each_possible_cpu(cpu) total += per_cpu(process_counts, cpu); return total; @@ -570,12 +570,18 @@ void mm_release(struct task_struct *tsk, struct mm_struct *mm) /* Get rid of any futexes when releasing the mm */ #ifdef CONFIG_FUTEX - if (unlikely(tsk->robust_list)) + if (unlikely(tsk->robust_list)) { exit_robust_list(tsk); + tsk->robust_list = NULL; + } #ifdef CONFIG_COMPAT - if (unlikely(tsk->compat_robust_list)) + if (unlikely(tsk->compat_robust_list)) { compat_exit_robust_list(tsk); + tsk->compat_robust_list = NULL; + } #endif + if (unlikely(!list_empty(&tsk->pi_state_list))) + exit_pi_state_list(tsk); #endif /* Get rid of any cached register state */ diff --git a/kernel/futex.c b/kernel/futex.c index b911adceb2c4..fb65e822fc41 100644 --- a/kernel/futex.c +++ b/kernel/futex.c @@ -150,7 +150,8 @@ static struct futex_hash_bucket *hash_futex(union futex_key *key) */ static inline int match_futex(union futex_key *key1, union futex_key *key2) { - return (key1->both.word == key2->both.word + return (key1 && key2 + && key1->both.word == key2->both.word && key1->both.ptr == key2->both.ptr && key1->both.offset == key2->both.offset); } @@ -916,8 +917,8 @@ retry: hb1 = hash_futex(&key1); hb2 = hash_futex(&key2); - double_lock_hb(hb1, hb2); retry_private: + double_lock_hb(hb1, hb2); op_ret = futex_atomic_op_inuser(op, uaddr2); if (unlikely(op_ret < 0)) { @@ -1028,7 +1029,6 @@ static inline void requeue_pi_wake_futex(struct futex_q *q, union futex_key *key, struct futex_hash_bucket *hb) { - drop_futex_key_refs(&q->key); get_futex_key_refs(key); q->key = *key; @@ -1226,6 +1226,7 @@ retry_private: */ if (ret == 1) { WARN_ON(pi_state); + drop_count++; task_count++; ret = get_futex_value_locked(&curval2, uaddr2); if (!ret) @@ -1304,6 +1305,7 @@ retry_private: if (ret == 1) { /* We got the lock. */ requeue_pi_wake_futex(this, &key2, hb2); + drop_count++; continue; } else if (ret) { /* -EDEADLK */ @@ -1791,6 +1793,7 @@ static int futex_wait(u32 __user *uaddr, int fshared, current->timer_slack_ns); } +retry: /* Prepare to wait on uaddr. */ ret = futex_wait_setup(uaddr, val, fshared, &q, &hb); if (ret) @@ -1808,9 +1811,14 @@ static int futex_wait(u32 __user *uaddr, int fshared, goto out_put_key; /* - * We expect signal_pending(current), but another thread may - * have handled it for us already. + * We expect signal_pending(current), but we might be the + * victim of a spurious wakeup as well. */ + if (!signal_pending(current)) { + put_futex_key(fshared, &q.key); + goto retry; + } + ret = -ERESTARTSYS; if (!abs_time) goto out_put_key; @@ -2117,11 +2125,12 @@ int handle_early_requeue_pi_wakeup(struct futex_hash_bucket *hb, * Unqueue the futex_q and determine which it was. */ plist_del(&q->list, &q->list.plist); - drop_futex_key_refs(&q->key); + /* Handle spurious wakeups gracefully */ + ret = -EWOULDBLOCK; if (timeout && !timeout->task) ret = -ETIMEDOUT; - else + else if (signal_pending(current)) ret = -ERESTARTNOINTR; } return ret; diff --git a/kernel/hrtimer.c b/kernel/hrtimer.c index 6d7020490f94..3e1c36e7998f 100644 --- a/kernel/hrtimer.c +++ b/kernel/hrtimer.c @@ -726,8 +726,6 @@ static int hrtimer_switch_to_hres(void) /* "Retrigger" the interrupt to get things going */ retrigger_next_event(NULL); local_irq_restore(flags); - printk(KERN_DEBUG "Switched to high resolution mode on CPU %d\n", - smp_processor_id()); return 1; } diff --git a/kernel/irq/handle.c b/kernel/irq/handle.c index a81cf80554db..17c71bb565c6 100644 --- a/kernel/irq/handle.c +++ b/kernel/irq/handle.c @@ -11,6 +11,7 @@ */ #include <linux/irq.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/module.h> #include <linux/random.h> diff --git a/kernel/irq/spurious.c b/kernel/irq/spurious.c index 114e704760fe..bd7273e6282e 100644 --- a/kernel/irq/spurious.c +++ b/kernel/irq/spurious.c @@ -121,7 +121,9 @@ static void poll_all_shared_irqs(void) if (!(status & IRQ_SPURIOUS_DISABLED)) continue; + local_irq_disable(); try_one_irq(i, desc); + local_irq_enable(); } } diff --git a/kernel/kthread.c b/kernel/kthread.c index 5fe709982caa..ab7ae57773e1 100644 --- a/kernel/kthread.c +++ b/kernel/kthread.c @@ -150,29 +150,6 @@ struct task_struct *kthread_create(int (*threadfn)(void *data), EXPORT_SYMBOL(kthread_create); /** - * kthread_bind - bind a just-created kthread to a cpu. - * @k: thread created by kthread_create(). - * @cpu: cpu (might not be online, must be possible) for @k to run on. - * - * Description: This function is equivalent to set_cpus_allowed(), - * except that @cpu doesn't need to be online, and the thread must be - * stopped (i.e., just returned from kthread_create()). - */ -void kthread_bind(struct task_struct *k, unsigned int cpu) -{ - /* Must have done schedule() in kthread() before we set_task_cpu */ - if (!wait_task_inactive(k, TASK_UNINTERRUPTIBLE)) { - WARN_ON(1); - return; - } - set_task_cpu(k, cpu); - k->cpus_allowed = cpumask_of_cpu(cpu); - k->rt.nr_cpus_allowed = 1; - k->flags |= PF_THREAD_BOUND; -} -EXPORT_SYMBOL(kthread_bind); - -/** * kthread_stop - stop a thread created by kthread_create(). * @k: thread created by kthread_create(). * diff --git a/kernel/lockdep.c b/kernel/lockdep.c index 3815ac1d58b2..9af56723c096 100644 --- a/kernel/lockdep.c +++ b/kernel/lockdep.c @@ -142,6 +142,11 @@ static inline struct lock_class *hlock_class(struct held_lock *hlock) #ifdef CONFIG_LOCK_STAT static DEFINE_PER_CPU(struct lock_class_stats[MAX_LOCKDEP_KEYS], lock_stats); +static inline u64 lockstat_clock(void) +{ + return cpu_clock(smp_processor_id()); +} + static int lock_point(unsigned long points[], unsigned long ip) { int i; @@ -158,7 +163,7 @@ static int lock_point(unsigned long points[], unsigned long ip) return i; } -static void lock_time_inc(struct lock_time *lt, s64 time) +static void lock_time_inc(struct lock_time *lt, u64 time) { if (time > lt->max) lt->max = time; @@ -234,12 +239,12 @@ static void put_lock_stats(struct lock_class_stats *stats) static void lock_release_holdtime(struct held_lock *hlock) { struct lock_class_stats *stats; - s64 holdtime; + u64 holdtime; if (!lock_stat) return; - holdtime = sched_clock() - hlock->holdtime_stamp; + holdtime = lockstat_clock() - hlock->holdtime_stamp; stats = get_lock_stats(hlock_class(hlock)); if (hlock->read) @@ -2792,7 +2797,7 @@ static int __lock_acquire(struct lockdep_map *lock, unsigned int subclass, hlock->references = references; #ifdef CONFIG_LOCK_STAT hlock->waittime_stamp = 0; - hlock->holdtime_stamp = sched_clock(); + hlock->holdtime_stamp = lockstat_clock(); #endif if (check == 2 && !mark_irqflags(curr, hlock)) @@ -3322,7 +3327,7 @@ found_it: if (hlock->instance != lock) return; - hlock->waittime_stamp = sched_clock(); + hlock->waittime_stamp = lockstat_clock(); contention_point = lock_point(hlock_class(hlock)->contention_point, ip); contending_point = lock_point(hlock_class(hlock)->contending_point, @@ -3345,8 +3350,7 @@ __lock_acquired(struct lockdep_map *lock, unsigned long ip) struct held_lock *hlock, *prev_hlock; struct lock_class_stats *stats; unsigned int depth; - u64 now; - s64 waittime = 0; + u64 now, waittime = 0; int i, cpu; depth = curr->lockdep_depth; @@ -3374,7 +3378,7 @@ found_it: cpu = smp_processor_id(); if (hlock->waittime_stamp) { - now = sched_clock(); + now = lockstat_clock(); waittime = now - hlock->waittime_stamp; hlock->holdtime_stamp = now; } diff --git a/kernel/mutex-debug.c b/kernel/mutex-debug.c index 50d022e5a560..ec815a960b5d 100644 --- a/kernel/mutex-debug.c +++ b/kernel/mutex-debug.c @@ -16,6 +16,7 @@ #include <linux/delay.h> #include <linux/module.h> #include <linux/poison.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/kallsyms.h> #include <linux/interrupt.h> diff --git a/kernel/panic.c b/kernel/panic.c index bcdef26e3332..96b45d0b4ba5 100644 --- a/kernel/panic.c +++ b/kernel/panic.c @@ -90,6 +90,8 @@ NORET_TYPE void panic(const char * fmt, ...) atomic_notifier_call_chain(&panic_notifier_list, 0, buf); + bust_spinlocks(0); + if (!panic_blink) panic_blink = no_blink; @@ -136,7 +138,6 @@ NORET_TYPE void panic(const char * fmt, ...) mdelay(1); i++; } - bust_spinlocks(0); } EXPORT_SYMBOL(panic); diff --git a/kernel/params.c b/kernel/params.c index 9da58eabdcb2..d656c276508d 100644 --- a/kernel/params.c +++ b/kernel/params.c @@ -218,15 +218,11 @@ int param_set_charp(const char *val, struct kernel_param *kp) return -ENOSPC; } - if (kp->flags & KPARAM_KMALLOCED) - kfree(*(char **)kp->arg); - /* This is a hack. We can't need to strdup in early boot, and we * don't need to; this mangled commandline is preserved. */ if (slab_is_available()) { - kp->flags |= KPARAM_KMALLOCED; *(char **)kp->arg = kstrdup(val, GFP_KERNEL); - if (!kp->arg) + if (!*(char **)kp->arg) return -ENOMEM; } else *(const char **)kp->arg = val; @@ -304,6 +300,7 @@ static int param_array(const char *name, unsigned int min, unsigned int max, void *elem, int elemsize, int (*set)(const char *, struct kernel_param *kp), + u16 flags, unsigned int *num) { int ret; @@ -313,6 +310,7 @@ static int param_array(const char *name, /* Get the name right for errors. */ kp.name = name; kp.arg = elem; + kp.flags = flags; /* No equals sign? */ if (!val) { @@ -358,7 +356,8 @@ int param_array_set(const char *val, struct kernel_param *kp) unsigned int temp_num; return param_array(kp->name, val, 1, arr->max, arr->elem, - arr->elemsize, arr->set, arr->num ?: &temp_num); + arr->elemsize, arr->set, kp->flags, + arr->num ?: &temp_num); } int param_array_get(char *buffer, struct kernel_param *kp) @@ -605,11 +604,7 @@ void module_param_sysfs_remove(struct module *mod) void destroy_params(const struct kernel_param *params, unsigned num) { - unsigned int i; - - for (i = 0; i < num; i++) - if (params[i].flags & KPARAM_KMALLOCED) - kfree(*(char **)params[i].arg); + /* FIXME: This should free kmalloced charp parameters. It doesn't. */ } static void __init kernel_add_sysfs_param(const char *name, diff --git a/kernel/perf_event.c b/kernel/perf_event.c index 0f86feb6db0c..7f29643c8985 100644 --- a/kernel/perf_event.c +++ b/kernel/perf_event.c @@ -20,6 +20,7 @@ #include <linux/percpu.h> #include <linux/ptrace.h> #include <linux/vmstat.h> +#include <linux/vmalloc.h> #include <linux/hardirq.h> #include <linux/rculist.h> #include <linux/uaccess.h> @@ -1030,14 +1031,10 @@ void __perf_event_sched_out(struct perf_event_context *ctx, update_context_time(ctx); perf_disable(); - if (ctx->nr_active) { - list_for_each_entry(event, &ctx->group_list, group_entry) { - if (event != event->group_leader) - event_sched_out(event, cpuctx, ctx); - else - group_sched_out(event, cpuctx, ctx); - } - } + if (ctx->nr_active) + list_for_each_entry(event, &ctx->group_list, group_entry) + group_sched_out(event, cpuctx, ctx); + perf_enable(); out: spin_unlock(&ctx->lock); @@ -1258,12 +1255,8 @@ __perf_event_sched_in(struct perf_event_context *ctx, if (event->cpu != -1 && event->cpu != cpu) continue; - if (event != event->group_leader) - event_sched_in(event, cpuctx, ctx, cpu); - else { - if (group_can_go_on(event, cpuctx, 1)) - group_sched_in(event, cpuctx, ctx, cpu); - } + if (group_can_go_on(event, cpuctx, 1)) + group_sched_in(event, cpuctx, ctx, cpu); /* * If this pinned group hasn't been scheduled, @@ -1291,15 +1284,9 @@ __perf_event_sched_in(struct perf_event_context *ctx, if (event->cpu != -1 && event->cpu != cpu) continue; - if (event != event->group_leader) { - if (event_sched_in(event, cpuctx, ctx, cpu)) + if (group_can_go_on(event, cpuctx, can_add_hw)) + if (group_sched_in(event, cpuctx, ctx, cpu)) can_add_hw = 0; - } else { - if (group_can_go_on(event, cpuctx, can_add_hw)) { - if (group_sched_in(event, cpuctx, ctx, cpu)) - can_add_hw = 0; - } - } } perf_enable(); out: @@ -1368,7 +1355,7 @@ static void perf_ctx_adjust_freq(struct perf_event_context *ctx) u64 interrupts, freq; spin_lock(&ctx->lock); - list_for_each_entry(event, &ctx->group_list, group_entry) { + list_for_each_entry_rcu(event, &ctx->event_list, event_entry) { if (event->state != PERF_EVENT_STATE_ACTIVE) continue; @@ -2105,49 +2092,31 @@ unlock: rcu_read_unlock(); } -static int perf_mmap_fault(struct vm_area_struct *vma, struct vm_fault *vmf) +static unsigned long perf_data_size(struct perf_mmap_data *data) { - struct perf_event *event = vma->vm_file->private_data; - struct perf_mmap_data *data; - int ret = VM_FAULT_SIGBUS; - - if (vmf->flags & FAULT_FLAG_MKWRITE) { - if (vmf->pgoff == 0) - ret = 0; - return ret; - } - - rcu_read_lock(); - data = rcu_dereference(event->data); - if (!data) - goto unlock; - - if (vmf->pgoff == 0) { - vmf->page = virt_to_page(data->user_page); - } else { - int nr = vmf->pgoff - 1; - - if ((unsigned)nr > data->nr_pages) - goto unlock; + return data->nr_pages << (PAGE_SHIFT + data->data_order); +} - if (vmf->flags & FAULT_FLAG_WRITE) - goto unlock; +#ifndef CONFIG_PERF_USE_VMALLOC - vmf->page = virt_to_page(data->data_pages[nr]); - } +/* + * Back perf_mmap() with regular GFP_KERNEL-0 pages. + */ - get_page(vmf->page); - vmf->page->mapping = vma->vm_file->f_mapping; - vmf->page->index = vmf->pgoff; +static struct page * +perf_mmap_to_page(struct perf_mmap_data *data, unsigned long pgoff) +{ + if (pgoff > data->nr_pages) + return NULL; - ret = 0; -unlock: - rcu_read_unlock(); + if (pgoff == 0) + return virt_to_page(data->user_page); - return ret; + return virt_to_page(data->data_pages[pgoff - 1]); } -static int perf_mmap_data_alloc(struct perf_event *event, int nr_pages) +static struct perf_mmap_data * +perf_mmap_data_alloc(struct perf_event *event, int nr_pages) { struct perf_mmap_data *data; unsigned long size; @@ -2172,19 +2141,10 @@ static int perf_mmap_data_alloc(struct perf_event *event, int nr_pages) goto fail_data_pages; } + data->data_order = 0; data->nr_pages = nr_pages; - atomic_set(&data->lock, -1); - - if (event->attr.watermark) { - data->watermark = min_t(long, PAGE_SIZE * nr_pages, - event->attr.wakeup_watermark); - } - if (!data->watermark) - data->watermark = max(PAGE_SIZE, PAGE_SIZE * nr_pages / 4); - - rcu_assign_pointer(event->data, data); - return 0; + return data; fail_data_pages: for (i--; i >= 0; i--) @@ -2196,7 +2156,7 @@ fail_user_page: kfree(data); fail: - return -ENOMEM; + return NULL; } static void perf_mmap_free_page(unsigned long addr) @@ -2207,28 +2167,169 @@ static void perf_mmap_free_page(unsigned long addr) __free_page(page); } -static void __perf_mmap_data_free(struct rcu_head *rcu_head) +static void perf_mmap_data_free(struct perf_mmap_data *data) { - struct perf_mmap_data *data; int i; - data = container_of(rcu_head, struct perf_mmap_data, rcu_head); - perf_mmap_free_page((unsigned long)data->user_page); for (i = 0; i < data->nr_pages; i++) perf_mmap_free_page((unsigned long)data->data_pages[i]); +} + +#else + +/* + * Back perf_mmap() with vmalloc memory. + * + * Required for architectures that have d-cache aliasing issues. + */ + +static struct page * +perf_mmap_to_page(struct perf_mmap_data *data, unsigned long pgoff) +{ + if (pgoff > (1UL << data->data_order)) + return NULL; + + return vmalloc_to_page((void *)data->user_page + pgoff * PAGE_SIZE); +} + +static void perf_mmap_unmark_page(void *addr) +{ + struct page *page = vmalloc_to_page(addr); + + page->mapping = NULL; +} + +static void perf_mmap_data_free_work(struct work_struct *work) +{ + struct perf_mmap_data *data; + void *base; + int i, nr; + + data = container_of(work, struct perf_mmap_data, work); + nr = 1 << data->data_order; + base = data->user_page; + for (i = 0; i < nr + 1; i++) + perf_mmap_unmark_page(base + (i * PAGE_SIZE)); + + vfree(base); +} + +static void perf_mmap_data_free(struct perf_mmap_data *data) +{ + schedule_work(&data->work); +} + +static struct perf_mmap_data * +perf_mmap_data_alloc(struct perf_event *event, int nr_pages) +{ + struct perf_mmap_data *data; + unsigned long size; + void *all_buf; + + WARN_ON(atomic_read(&event->mmap_count)); + + size = sizeof(struct perf_mmap_data); + size += sizeof(void *); + + data = kzalloc(size, GFP_KERNEL); + if (!data) + goto fail; + + INIT_WORK(&data->work, perf_mmap_data_free_work); + + all_buf = vmalloc_user((nr_pages + 1) * PAGE_SIZE); + if (!all_buf) + goto fail_all_buf; + + data->user_page = all_buf; + data->data_pages[0] = all_buf + PAGE_SIZE; + data->data_order = ilog2(nr_pages); + data->nr_pages = 1; + + return data; + +fail_all_buf: kfree(data); + +fail: + return NULL; } -static void perf_mmap_data_free(struct perf_event *event) +#endif + +static int perf_mmap_fault(struct vm_area_struct *vma, struct vm_fault *vmf) +{ + struct perf_event *event = vma->vm_file->private_data; + struct perf_mmap_data *data; + int ret = VM_FAULT_SIGBUS; + + if (vmf->flags & FAULT_FLAG_MKWRITE) { + if (vmf->pgoff == 0) + ret = 0; + return ret; + } + + rcu_read_lock(); + data = rcu_dereference(event->data); + if (!data) + goto unlock; + + if (vmf->pgoff && (vmf->flags & FAULT_FLAG_WRITE)) + goto unlock; + + vmf->page = perf_mmap_to_page(data, vmf->pgoff); + if (!vmf->page) + goto unlock; + + get_page(vmf->page); + vmf->page->mapping = vma->vm_file->f_mapping; + vmf->page->index = vmf->pgoff; + + ret = 0; +unlock: + rcu_read_unlock(); + + return ret; +} + +static void +perf_mmap_data_init(struct perf_event *event, struct perf_mmap_data *data) +{ + long max_size = perf_data_size(data); + + atomic_set(&data->lock, -1); + + if (event->attr.watermark) { + data->watermark = min_t(long, max_size, + event->attr.wakeup_watermark); + } + + if (!data->watermark) + data->watermark = max_t(long, PAGE_SIZE, max_size / 2); + + + rcu_assign_pointer(event->data, data); +} + +static void perf_mmap_data_free_rcu(struct rcu_head *rcu_head) +{ + struct perf_mmap_data *data; + + data = container_of(rcu_head, struct perf_mmap_data, rcu_head); + perf_mmap_data_free(data); + kfree(data); +} + +static void perf_mmap_data_release(struct perf_event *event) { struct perf_mmap_data *data = event->data; WARN_ON(atomic_read(&event->mmap_count)); rcu_assign_pointer(event->data, NULL); - call_rcu(&data->rcu_head, __perf_mmap_data_free); + call_rcu(&data->rcu_head, perf_mmap_data_free_rcu); } static void perf_mmap_open(struct vm_area_struct *vma) @@ -2244,11 +2345,12 @@ static void perf_mmap_close(struct vm_area_struct *vma) WARN_ON_ONCE(event->ctx->parent_ctx); if (atomic_dec_and_mutex_lock(&event->mmap_count, &event->mmap_mutex)) { + unsigned long size = perf_data_size(event->data); struct user_struct *user = current_user(); - atomic_long_sub(event->data->nr_pages + 1, &user->locked_vm); + atomic_long_sub((size >> PAGE_SHIFT) + 1, &user->locked_vm); vma->vm_mm->locked_vm -= event->data->nr_locked; - perf_mmap_data_free(event); + perf_mmap_data_release(event); mutex_unlock(&event->mmap_mutex); } } @@ -2266,6 +2368,7 @@ static int perf_mmap(struct file *file, struct vm_area_struct *vma) unsigned long user_locked, user_lock_limit; struct user_struct *user = current_user(); unsigned long locked, lock_limit; + struct perf_mmap_data *data; unsigned long vma_size; unsigned long nr_pages; long user_extra, extra; @@ -2328,10 +2431,15 @@ static int perf_mmap(struct file *file, struct vm_area_struct *vma) } WARN_ON(event->data); - ret = perf_mmap_data_alloc(event, nr_pages); - if (ret) + + data = perf_mmap_data_alloc(event, nr_pages); + ret = -ENOMEM; + if (!data) goto unlock; + ret = 0; + perf_mmap_data_init(event, data); + atomic_set(&event->mmap_count, 1); atomic_long_add(user_extra, &user->locked_vm); vma->vm_mm->locked_vm += extra; @@ -2519,7 +2627,7 @@ static bool perf_output_space(struct perf_mmap_data *data, unsigned long tail, if (!data->writable) return true; - mask = (data->nr_pages << PAGE_SHIFT) - 1; + mask = perf_data_size(data) - 1; offset = (offset - tail) & mask; head = (head - tail) & mask; @@ -2624,7 +2732,7 @@ void perf_output_copy(struct perf_output_handle *handle, const void *buf, unsigned int len) { unsigned int pages_mask; - unsigned int offset; + unsigned long offset; unsigned int size; void **pages; @@ -2633,12 +2741,14 @@ void perf_output_copy(struct perf_output_handle *handle, pages = handle->data->data_pages; do { - unsigned int page_offset; + unsigned long page_offset; + unsigned long page_size; int nr; nr = (offset >> PAGE_SHIFT) & pages_mask; - page_offset = offset & (PAGE_SIZE - 1); - size = min_t(unsigned int, PAGE_SIZE - page_offset, len); + page_size = 1UL << (handle->data->data_order + PAGE_SHIFT); + page_offset = offset & (page_size - 1); + size = min_t(unsigned int, page_size - page_offset, len); memcpy(pages[nr] + page_offset, buf, size); @@ -3849,8 +3959,9 @@ static enum hrtimer_restart perf_swevent_hrtimer(struct hrtimer *hrtimer) regs = task_pt_regs(current); if (regs) { - if (perf_event_overflow(event, 0, &data, regs)) - ret = HRTIMER_NORESTART; + if (!(event->attr.exclude_idle && current->pid == 0)) + if (perf_event_overflow(event, 0, &data, regs)) + ret = HRTIMER_NORESTART; } period = max_t(u64, 10000, event->hw.sample_period); @@ -3859,6 +3970,42 @@ static enum hrtimer_restart perf_swevent_hrtimer(struct hrtimer *hrtimer) return ret; } +static void perf_swevent_start_hrtimer(struct perf_event *event) +{ + struct hw_perf_event *hwc = &event->hw; + + hrtimer_init(&hwc->hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); + hwc->hrtimer.function = perf_swevent_hrtimer; + if (hwc->sample_period) { + u64 period; + + if (hwc->remaining) { + if (hwc->remaining < 0) + period = 10000; + else + period = hwc->remaining; + hwc->remaining = 0; + } else { + period = max_t(u64, 10000, hwc->sample_period); + } + __hrtimer_start_range_ns(&hwc->hrtimer, + ns_to_ktime(period), 0, + HRTIMER_MODE_REL, 0); + } +} + +static void perf_swevent_cancel_hrtimer(struct perf_event *event) +{ + struct hw_perf_event *hwc = &event->hw; + + if (hwc->sample_period) { + ktime_t remaining = hrtimer_get_remaining(&hwc->hrtimer); + hwc->remaining = ktime_to_ns(remaining); + + hrtimer_cancel(&hwc->hrtimer); + } +} + /* * Software event: cpu wall time clock */ @@ -3881,22 +4028,14 @@ static int cpu_clock_perf_event_enable(struct perf_event *event) int cpu = raw_smp_processor_id(); atomic64_set(&hwc->prev_count, cpu_clock(cpu)); - hrtimer_init(&hwc->hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); - hwc->hrtimer.function = perf_swevent_hrtimer; - if (hwc->sample_period) { - u64 period = max_t(u64, 10000, hwc->sample_period); - __hrtimer_start_range_ns(&hwc->hrtimer, - ns_to_ktime(period), 0, - HRTIMER_MODE_REL, 0); - } + perf_swevent_start_hrtimer(event); return 0; } static void cpu_clock_perf_event_disable(struct perf_event *event) { - if (event->hw.sample_period) - hrtimer_cancel(&event->hw.hrtimer); + perf_swevent_cancel_hrtimer(event); cpu_clock_perf_event_update(event); } @@ -3933,22 +4072,15 @@ static int task_clock_perf_event_enable(struct perf_event *event) now = event->ctx->time; atomic64_set(&hwc->prev_count, now); - hrtimer_init(&hwc->hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); - hwc->hrtimer.function = perf_swevent_hrtimer; - if (hwc->sample_period) { - u64 period = max_t(u64, 10000, hwc->sample_period); - __hrtimer_start_range_ns(&hwc->hrtimer, - ns_to_ktime(period), 0, - HRTIMER_MODE_REL, 0); - } + + perf_swevent_start_hrtimer(event); return 0; } static void task_clock_perf_event_disable(struct perf_event *event) { - if (event->hw.sample_period) - hrtimer_cancel(&event->hw.hrtimer); + perf_swevent_cancel_hrtimer(event); task_clock_perf_event_update(event, event->ctx->time); } @@ -4781,9 +4913,7 @@ int perf_event_init_task(struct task_struct *child) * We dont have to disable NMIs - we are only looking at * the list, not manipulating it: */ - list_for_each_entry_rcu(event, &parent_ctx->event_list, event_entry) { - if (event != event->group_leader) - continue; + list_for_each_entry(event, &parent_ctx->group_list, group_entry) { if (!event->attr.inherit) { inherited_all = 0; diff --git a/kernel/power/hibernate.c b/kernel/power/hibernate.c index 04b3a83d686f..04a9e90d248f 100644 --- a/kernel/power/hibernate.c +++ b/kernel/power/hibernate.c @@ -693,21 +693,22 @@ static int software_resume(void) /* The snapshot device should not be opened while we're running */ if (!atomic_add_unless(&snapshot_device_available, -1, 0)) { error = -EBUSY; + swsusp_close(FMODE_READ); goto Unlock; } pm_prepare_console(); error = pm_notifier_call_chain(PM_RESTORE_PREPARE); if (error) - goto Finish; + goto close_finish; error = usermodehelper_disable(); if (error) - goto Finish; + goto close_finish; error = create_basic_memory_bitmaps(); if (error) - goto Finish; + goto close_finish; pr_debug("PM: Preparing processes for restore.\n"); error = prepare_processes(); @@ -719,6 +720,7 @@ static int software_resume(void) pr_debug("PM: Reading hibernation image.\n"); error = swsusp_read(&flags); + swsusp_close(FMODE_READ); if (!error) hibernation_restore(flags & SF_PLATFORM_MODE); @@ -737,6 +739,9 @@ static int software_resume(void) mutex_unlock(&pm_mutex); pr_debug("PM: Resume from disk failed.\n"); return error; +close_finish: + swsusp_close(FMODE_READ); + goto Finish; } late_initcall(software_resume); diff --git a/kernel/power/suspend_test.c b/kernel/power/suspend_test.c index 17d8bb1acf9c..25596e450ac7 100644 --- a/kernel/power/suspend_test.c +++ b/kernel/power/suspend_test.c @@ -19,7 +19,7 @@ * The time it takes is system-specific though, so when we test this * during system bootup we allow a LOT of time. */ -#define TEST_SUSPEND_SECONDS 5 +#define TEST_SUSPEND_SECONDS 10 static unsigned long suspend_test_start_time; @@ -49,7 +49,8 @@ void suspend_test_finish(const char *label) * has some performance issues. The stack dump of a WARN_ON * is more likely to get the right attention than a printk... */ - WARN(msec > (TEST_SUSPEND_SECONDS * 1000), "Component: %s\n", label); + WARN(msec > (TEST_SUSPEND_SECONDS * 1000), + "Component: %s, time: %u\n", label, msec); } /* diff --git a/kernel/power/swap.c b/kernel/power/swap.c index b101cdc4df3f..890f6b11b1d3 100644 --- a/kernel/power/swap.c +++ b/kernel/power/swap.c @@ -314,7 +314,6 @@ static int save_image(struct swap_map_handle *handle, { unsigned int m; int ret; - int error = 0; int nr_pages; int err2; struct bio *bio; @@ -329,26 +328,27 @@ static int save_image(struct swap_map_handle *handle, nr_pages = 0; bio = NULL; do_gettimeofday(&start); - do { + while (1) { ret = snapshot_read_next(snapshot, PAGE_SIZE); - if (ret > 0) { - error = swap_write_page(handle, data_of(*snapshot), - &bio); - if (error) - break; - if (!(nr_pages % m)) - printk("\b\b\b\b%3d%%", nr_pages / m); - nr_pages++; - } - } while (ret > 0); + if (ret <= 0) + break; + ret = swap_write_page(handle, data_of(*snapshot), &bio); + if (ret) + break; + if (!(nr_pages % m)) + printk("\b\b\b\b%3d%%", nr_pages / m); + nr_pages++; + } err2 = wait_on_bio_chain(&bio); do_gettimeofday(&stop); - if (!error) - error = err2; - if (!error) + if (!ret) + ret = err2; + if (!ret) printk("\b\b\b\bdone\n"); + else + printk("\n"); swsusp_show_speed(&start, &stop, nr_to_write, "Wrote"); - return error; + return ret; } /** @@ -536,7 +536,8 @@ static int load_image(struct swap_map_handle *handle, snapshot_write_finalize(snapshot); if (!snapshot_image_loaded(snapshot)) error = -ENODATA; - } + } else + printk("\n"); swsusp_show_speed(&start, &stop, nr_to_read, "Read"); return error; } @@ -572,8 +573,6 @@ int swsusp_read(unsigned int *flags_p) error = load_image(&handle, &snapshot, header->pages - 1); release_swap_reader(&handle); - blkdev_put(resume_bdev, FMODE_READ); - if (!error) pr_debug("PM: Image successfully loaded\n"); else @@ -596,7 +595,7 @@ int swsusp_check(void) error = bio_read_page(swsusp_resume_block, swsusp_header, NULL); if (error) - return error; + goto put; if (!memcmp(SWSUSP_SIG, swsusp_header->sig, 10)) { memcpy(swsusp_header->sig, swsusp_header->orig_sig, 10); @@ -604,8 +603,10 @@ int swsusp_check(void) error = bio_write_page(swsusp_resume_block, swsusp_header, NULL); } else { - return -EINVAL; + error = -EINVAL; } + +put: if (error) blkdev_put(resume_bdev, FMODE_READ); else diff --git a/kernel/rcupdate.c b/kernel/rcupdate.c index 37ac45483082..400183346ad2 100644 --- a/kernel/rcupdate.c +++ b/kernel/rcupdate.c @@ -46,22 +46,15 @@ #include <linux/module.h> #include <linux/kernel_stat.h> -enum rcu_barrier { - RCU_BARRIER_STD, - RCU_BARRIER_BH, - RCU_BARRIER_SCHED, -}; +#ifdef CONFIG_DEBUG_LOCK_ALLOC +static struct lock_class_key rcu_lock_key; +struct lockdep_map rcu_lock_map = + STATIC_LOCKDEP_MAP_INIT("rcu_read_lock", &rcu_lock_key); +EXPORT_SYMBOL_GPL(rcu_lock_map); +#endif -static DEFINE_PER_CPU(struct rcu_head, rcu_barrier_head) = {NULL}; -static atomic_t rcu_barrier_cpu_count; -static DEFINE_MUTEX(rcu_barrier_mutex); -static struct completion rcu_barrier_completion; int rcu_scheduler_active __read_mostly; -static atomic_t rcu_migrate_type_count = ATOMIC_INIT(0); -static struct rcu_head rcu_migrate_head[3]; -static DECLARE_WAIT_QUEUE_HEAD(rcu_migrate_wq); - /* * Awaken the corresponding synchronize_rcu() instance now that a * grace period has elapsed. @@ -164,129 +157,10 @@ void synchronize_rcu_bh(void) } EXPORT_SYMBOL_GPL(synchronize_rcu_bh); -static void rcu_barrier_callback(struct rcu_head *notused) -{ - if (atomic_dec_and_test(&rcu_barrier_cpu_count)) - complete(&rcu_barrier_completion); -} - -/* - * Called with preemption disabled, and from cross-cpu IRQ context. - */ -static void rcu_barrier_func(void *type) -{ - int cpu = smp_processor_id(); - struct rcu_head *head = &per_cpu(rcu_barrier_head, cpu); - - atomic_inc(&rcu_barrier_cpu_count); - switch ((enum rcu_barrier)type) { - case RCU_BARRIER_STD: - call_rcu(head, rcu_barrier_callback); - break; - case RCU_BARRIER_BH: - call_rcu_bh(head, rcu_barrier_callback); - break; - case RCU_BARRIER_SCHED: - call_rcu_sched(head, rcu_barrier_callback); - break; - } -} - -static inline void wait_migrated_callbacks(void) -{ - wait_event(rcu_migrate_wq, !atomic_read(&rcu_migrate_type_count)); - smp_mb(); /* In case we didn't sleep. */ -} - -/* - * Orchestrate the specified type of RCU barrier, waiting for all - * RCU callbacks of the specified type to complete. - */ -static void _rcu_barrier(enum rcu_barrier type) -{ - BUG_ON(in_interrupt()); - /* Take cpucontrol mutex to protect against CPU hotplug */ - mutex_lock(&rcu_barrier_mutex); - init_completion(&rcu_barrier_completion); - /* - * Initialize rcu_barrier_cpu_count to 1, then invoke - * rcu_barrier_func() on each CPU, so that each CPU also has - * incremented rcu_barrier_cpu_count. Only then is it safe to - * decrement rcu_barrier_cpu_count -- otherwise the first CPU - * might complete its grace period before all of the other CPUs - * did their increment, causing this function to return too - * early. - */ - atomic_set(&rcu_barrier_cpu_count, 1); - on_each_cpu(rcu_barrier_func, (void *)type, 1); - if (atomic_dec_and_test(&rcu_barrier_cpu_count)) - complete(&rcu_barrier_completion); - wait_for_completion(&rcu_barrier_completion); - mutex_unlock(&rcu_barrier_mutex); - wait_migrated_callbacks(); -} - -/** - * rcu_barrier - Wait until all in-flight call_rcu() callbacks complete. - */ -void rcu_barrier(void) -{ - _rcu_barrier(RCU_BARRIER_STD); -} -EXPORT_SYMBOL_GPL(rcu_barrier); - -/** - * rcu_barrier_bh - Wait until all in-flight call_rcu_bh() callbacks complete. - */ -void rcu_barrier_bh(void) -{ - _rcu_barrier(RCU_BARRIER_BH); -} -EXPORT_SYMBOL_GPL(rcu_barrier_bh); - -/** - * rcu_barrier_sched - Wait for in-flight call_rcu_sched() callbacks. - */ -void rcu_barrier_sched(void) -{ - _rcu_barrier(RCU_BARRIER_SCHED); -} -EXPORT_SYMBOL_GPL(rcu_barrier_sched); - -static void rcu_migrate_callback(struct rcu_head *notused) -{ - if (atomic_dec_and_test(&rcu_migrate_type_count)) - wake_up(&rcu_migrate_wq); -} - -extern int rcu_cpu_notify(struct notifier_block *self, - unsigned long action, void *hcpu); - static int __cpuinit rcu_barrier_cpu_hotplug(struct notifier_block *self, unsigned long action, void *hcpu) { - rcu_cpu_notify(self, action, hcpu); - if (action == CPU_DYING) { - /* - * preempt_disable() in on_each_cpu() prevents stop_machine(), - * so when "on_each_cpu(rcu_barrier_func, (void *)type, 1);" - * returns, all online cpus have queued rcu_barrier_func(), - * and the dead cpu(if it exist) queues rcu_migrate_callback()s. - * - * These callbacks ensure _rcu_barrier() waits for all - * RCU callbacks of the specified type to complete. - */ - atomic_set(&rcu_migrate_type_count, 3); - call_rcu_bh(rcu_migrate_head, rcu_migrate_callback); - call_rcu_sched(rcu_migrate_head + 1, rcu_migrate_callback); - call_rcu(rcu_migrate_head + 2, rcu_migrate_callback); - } else if (action == CPU_DOWN_PREPARE) { - /* Don't need to wait until next removal operation. */ - /* rcu_migrate_head is protected by cpu_add_remove_lock */ - wait_migrated_callbacks(); - } - - return NOTIFY_OK; + return rcu_cpu_notify(self, action, hcpu); } void __init rcu_init(void) diff --git a/kernel/rcutorture.c b/kernel/rcutorture.c index 233768f21f97..697c0a0229d4 100644 --- a/kernel/rcutorture.c +++ b/kernel/rcutorture.c @@ -606,8 +606,6 @@ static struct rcu_torture_ops sched_ops_sync = { .name = "sched_sync" }; -extern int rcu_expedited_torture_stats(char *page); - static struct rcu_torture_ops sched_expedited_ops = { .init = rcu_sync_torture_init, .cleanup = NULL, @@ -650,7 +648,7 @@ rcu_torture_writer(void *arg) old_rp = rcu_torture_current; rp->rtort_mbtest = 1; rcu_assign_pointer(rcu_torture_current, rp); - smp_wmb(); + smp_wmb(); /* Mods to old_rp must follow rcu_assign_pointer() */ if (old_rp) { i = old_rp->rtort_pipe_count; if (i > RCU_TORTURE_PIPE_LEN) diff --git a/kernel/rcutree.c b/kernel/rcutree.c index 52b06f6e158c..f3077c0ab181 100644 --- a/kernel/rcutree.c +++ b/kernel/rcutree.c @@ -49,13 +49,6 @@ #include "rcutree.h" -#ifdef CONFIG_DEBUG_LOCK_ALLOC -static struct lock_class_key rcu_lock_key; -struct lockdep_map rcu_lock_map = - STATIC_LOCKDEP_MAP_INIT("rcu_read_lock", &rcu_lock_key); -EXPORT_SYMBOL_GPL(rcu_lock_map); -#endif - /* Data structures. */ #define RCU_STATE_INITIALIZER(name) { \ @@ -66,10 +59,13 @@ EXPORT_SYMBOL_GPL(rcu_lock_map); NUM_RCU_LVL_2, \ NUM_RCU_LVL_3, /* == MAX_RCU_LVLS */ \ }, \ - .signaled = RCU_SIGNAL_INIT, \ + .signaled = RCU_GP_IDLE, \ .gpnum = -300, \ .completed = -300, \ .onofflock = __SPIN_LOCK_UNLOCKED(&name.onofflock), \ + .orphan_cbs_list = NULL, \ + .orphan_cbs_tail = &name.orphan_cbs_list, \ + .orphan_qlen = 0, \ .fqslock = __SPIN_LOCK_UNLOCKED(&name.fqslock), \ .n_force_qs = 0, \ .n_force_qs_ngp = 0, \ @@ -81,24 +77,16 @@ DEFINE_PER_CPU(struct rcu_data, rcu_sched_data); struct rcu_state rcu_bh_state = RCU_STATE_INITIALIZER(rcu_bh_state); DEFINE_PER_CPU(struct rcu_data, rcu_bh_data); -extern long rcu_batches_completed_sched(void); -static struct rcu_node *rcu_get_root(struct rcu_state *rsp); -static void cpu_quiet_msk(unsigned long mask, struct rcu_state *rsp, - struct rcu_node *rnp, unsigned long flags); -static void cpu_quiet_msk_finish(struct rcu_state *rsp, unsigned long flags); -#ifdef CONFIG_HOTPLUG_CPU -static void __rcu_offline_cpu(int cpu, struct rcu_state *rsp); -#endif /* #ifdef CONFIG_HOTPLUG_CPU */ -static void __rcu_process_callbacks(struct rcu_state *rsp, - struct rcu_data *rdp); -static void __call_rcu(struct rcu_head *head, - void (*func)(struct rcu_head *rcu), - struct rcu_state *rsp); -static int __rcu_pending(struct rcu_state *rsp, struct rcu_data *rdp); -static void __cpuinit rcu_init_percpu_data(int cpu, struct rcu_state *rsp, - int preemptable); -#include "rcutree_plugin.h" +/* + * Return true if an RCU grace period is in progress. The ACCESS_ONCE()s + * permit this function to be invoked without holding the root rcu_node + * structure's ->lock, but of course results can be subject to change. + */ +static int rcu_gp_in_progress(struct rcu_state *rsp) +{ + return ACCESS_ONCE(rsp->completed) != ACCESS_ONCE(rsp->gpnum); +} /* * Note a quiescent state. Because we do not need to know @@ -137,6 +125,10 @@ static int blimit = 10; /* Maximum callbacks per softirq. */ static int qhimark = 10000; /* If this many pending, ignore blimit. */ static int qlowmark = 100; /* Once only this many pending, use blimit. */ +module_param(blimit, int, 0); +module_param(qhimark, int, 0); +module_param(qlowmark, int, 0); + static void force_quiescent_state(struct rcu_state *rsp, int relaxed); static int rcu_pending(int cpu); @@ -173,9 +165,7 @@ cpu_has_callbacks_ready_to_invoke(struct rcu_data *rdp) static int cpu_needs_another_gp(struct rcu_state *rsp, struct rcu_data *rdp) { - /* ACCESS_ONCE() because we are accessing outside of lock. */ - return *rdp->nxttail[RCU_DONE_TAIL] && - ACCESS_ONCE(rsp->completed) == ACCESS_ONCE(rsp->gpnum); + return *rdp->nxttail[RCU_DONE_TAIL] && !rcu_gp_in_progress(rsp); } /* @@ -369,7 +359,7 @@ static long dyntick_recall_completed(struct rcu_state *rsp) /* * Snapshot the specified CPU's dynticks counter so that we can later * credit them with an implicit quiescent state. Return 1 if this CPU - * is already in a quiescent state courtesy of dynticks idle mode. + * is in dynticks idle mode, which is an extended quiescent state. */ static int dyntick_save_progress_counter(struct rcu_data *rdp) { @@ -475,30 +465,34 @@ static void print_other_cpu_stall(struct rcu_state *rsp) long delta; unsigned long flags; struct rcu_node *rnp = rcu_get_root(rsp); - struct rcu_node *rnp_cur = rsp->level[NUM_RCU_LVLS - 1]; - struct rcu_node *rnp_end = &rsp->node[NUM_RCU_NODES]; /* Only let one CPU complain about others per time interval. */ spin_lock_irqsave(&rnp->lock, flags); delta = jiffies - rsp->jiffies_stall; - if (delta < RCU_STALL_RAT_DELAY || rsp->gpnum == rsp->completed) { + if (delta < RCU_STALL_RAT_DELAY || !rcu_gp_in_progress(rsp)) { spin_unlock_irqrestore(&rnp->lock, flags); return; } rsp->jiffies_stall = jiffies + RCU_SECONDS_TILL_STALL_RECHECK; + + /* + * Now rat on any tasks that got kicked up to the root rcu_node + * due to CPU offlining. + */ + rcu_print_task_stall(rnp); spin_unlock_irqrestore(&rnp->lock, flags); /* OK, time to rat on our buddy... */ printk(KERN_ERR "INFO: RCU detected CPU stalls:"); - for (; rnp_cur < rnp_end; rnp_cur++) { + rcu_for_each_leaf_node(rsp, rnp) { rcu_print_task_stall(rnp); - if (rnp_cur->qsmask == 0) + if (rnp->qsmask == 0) continue; - for (cpu = 0; cpu <= rnp_cur->grphi - rnp_cur->grplo; cpu++) - if (rnp_cur->qsmask & (1UL << cpu)) - printk(" %d", rnp_cur->grplo + cpu); + for (cpu = 0; cpu <= rnp->grphi - rnp->grplo; cpu++) + if (rnp->qsmask & (1UL << cpu)) + printk(" %d", rnp->grplo + cpu); } printk(" (detected by %d, t=%ld jiffies)\n", smp_processor_id(), (long)(jiffies - rsp->gp_start)); @@ -537,8 +531,7 @@ static void check_cpu_stall(struct rcu_state *rsp, struct rcu_data *rdp) /* We haven't checked in, so go dump stack. */ print_cpu_stall(rsp); - } else if (rsp->gpnum != rsp->completed && - delta >= RCU_STALL_RAT_DELAY) { + } else if (rcu_gp_in_progress(rsp) && delta >= RCU_STALL_RAT_DELAY) { /* They had two time units to dump stack, so complain. */ print_other_cpu_stall(rsp); @@ -617,9 +610,15 @@ rcu_start_gp(struct rcu_state *rsp, unsigned long flags) note_new_gpnum(rsp, rdp); /* - * Because we are first, we know that all our callbacks will - * be covered by this upcoming grace period, even the ones - * that were registered arbitrarily recently. + * Because this CPU just now started the new grace period, we know + * that all of its callbacks will be covered by this upcoming grace + * period, even the ones that were registered arbitrarily recently. + * Therefore, advance all outstanding callbacks to RCU_WAIT_TAIL. + * + * Other CPUs cannot be sure exactly when the grace period started. + * Therefore, their recently registered callbacks must pass through + * an additional RCU_NEXT_READY stage, so that they will be handled + * by the next RCU grace period. */ rdp->nxttail[RCU_NEXT_READY_TAIL] = rdp->nxttail[RCU_NEXT_TAIL]; rdp->nxttail[RCU_WAIT_TAIL] = rdp->nxttail[RCU_NEXT_TAIL]; @@ -657,15 +656,18 @@ rcu_start_gp(struct rcu_state *rsp, unsigned long flags) * one corresponding to this CPU, due to the fact that we have * irqs disabled. */ - for (rnp = &rsp->node[0]; rnp < &rsp->node[NUM_RCU_NODES]; rnp++) { - spin_lock(&rnp->lock); /* irqs already disabled. */ + rcu_for_each_node_breadth_first(rsp, rnp) { + spin_lock(&rnp->lock); /* irqs already disabled. */ rcu_preempt_check_blocked_tasks(rnp); rnp->qsmask = rnp->qsmaskinit; rnp->gpnum = rsp->gpnum; - spin_unlock(&rnp->lock); /* irqs already disabled. */ + spin_unlock(&rnp->lock); /* irqs remain disabled. */ } + rnp = rcu_get_root(rsp); + spin_lock(&rnp->lock); /* irqs already disabled. */ rsp->signaled = RCU_SIGNAL_INIT; /* force_quiescent_state now OK. */ + spin_unlock(&rnp->lock); /* irqs remain disabled. */ spin_unlock_irqrestore(&rsp->onofflock, flags); } @@ -703,10 +705,11 @@ rcu_process_gp_end(struct rcu_state *rsp, struct rcu_data *rdp) * hold rnp->lock, as required by rcu_start_gp(), which will release it. */ static void cpu_quiet_msk_finish(struct rcu_state *rsp, unsigned long flags) - __releases(rnp->lock) + __releases(rcu_get_root(rsp)->lock) { - WARN_ON_ONCE(rsp->completed == rsp->gpnum); + WARN_ON_ONCE(!rcu_gp_in_progress(rsp)); rsp->completed = rsp->gpnum; + rsp->signaled = RCU_GP_IDLE; rcu_process_gp_end(rsp, rsp->rda[smp_processor_id()]); rcu_start_gp(rsp, flags); /* releases root node's rnp->lock. */ } @@ -842,17 +845,63 @@ rcu_check_quiescent_state(struct rcu_state *rsp, struct rcu_data *rdp) #ifdef CONFIG_HOTPLUG_CPU /* + * Move a dying CPU's RCU callbacks to the ->orphan_cbs_list for the + * specified flavor of RCU. The callbacks will be adopted by the next + * _rcu_barrier() invocation or by the CPU_DEAD notifier, whichever + * comes first. Because this is invoked from the CPU_DYING notifier, + * irqs are already disabled. + */ +static void rcu_send_cbs_to_orphanage(struct rcu_state *rsp) +{ + int i; + struct rcu_data *rdp = rsp->rda[smp_processor_id()]; + + if (rdp->nxtlist == NULL) + return; /* irqs disabled, so comparison is stable. */ + spin_lock(&rsp->onofflock); /* irqs already disabled. */ + *rsp->orphan_cbs_tail = rdp->nxtlist; + rsp->orphan_cbs_tail = rdp->nxttail[RCU_NEXT_TAIL]; + rdp->nxtlist = NULL; + for (i = 0; i < RCU_NEXT_SIZE; i++) + rdp->nxttail[i] = &rdp->nxtlist; + rsp->orphan_qlen += rdp->qlen; + rdp->qlen = 0; + spin_unlock(&rsp->onofflock); /* irqs remain disabled. */ +} + +/* + * Adopt previously orphaned RCU callbacks. + */ +static void rcu_adopt_orphan_cbs(struct rcu_state *rsp) +{ + unsigned long flags; + struct rcu_data *rdp; + + spin_lock_irqsave(&rsp->onofflock, flags); + rdp = rsp->rda[smp_processor_id()]; + if (rsp->orphan_cbs_list == NULL) { + spin_unlock_irqrestore(&rsp->onofflock, flags); + return; + } + *rdp->nxttail[RCU_NEXT_TAIL] = rsp->orphan_cbs_list; + rdp->nxttail[RCU_NEXT_TAIL] = rsp->orphan_cbs_tail; + rdp->qlen += rsp->orphan_qlen; + rsp->orphan_cbs_list = NULL; + rsp->orphan_cbs_tail = &rsp->orphan_cbs_list; + rsp->orphan_qlen = 0; + spin_unlock_irqrestore(&rsp->onofflock, flags); +} + +/* * Remove the outgoing CPU from the bitmasks in the rcu_node hierarchy * and move all callbacks from the outgoing CPU to the current one. */ static void __rcu_offline_cpu(int cpu, struct rcu_state *rsp) { - int i; unsigned long flags; long lastcomp; unsigned long mask; struct rcu_data *rdp = rsp->rda[cpu]; - struct rcu_data *rdp_me; struct rcu_node *rnp; /* Exclude any attempts to start a new grace period. */ @@ -868,39 +917,29 @@ static void __rcu_offline_cpu(int cpu, struct rcu_state *rsp) spin_unlock(&rnp->lock); /* irqs remain disabled. */ break; } - rcu_preempt_offline_tasks(rsp, rnp, rdp); + + /* + * If there was a task blocking the current grace period, + * and if all CPUs have checked in, we need to propagate + * the quiescent state up the rcu_node hierarchy. But that + * is inconvenient at the moment due to deadlock issues if + * this should end the current grace period. So set the + * offlined CPU's bit in ->qsmask in order to force the + * next force_quiescent_state() invocation to clean up this + * mess in a deadlock-free manner. + */ + if (rcu_preempt_offline_tasks(rsp, rnp, rdp) && !rnp->qsmask) + rnp->qsmask |= mask; + mask = rnp->grpmask; spin_unlock(&rnp->lock); /* irqs remain disabled. */ rnp = rnp->parent; } while (rnp != NULL); lastcomp = rsp->completed; - spin_unlock(&rsp->onofflock); /* irqs remain disabled. */ + spin_unlock_irqrestore(&rsp->onofflock, flags); - /* - * Move callbacks from the outgoing CPU to the running CPU. - * Note that the outgoing CPU is now quiscent, so it is now - * (uncharacteristically) safe to access its rcu_data structure. - * Note also that we must carefully retain the order of the - * outgoing CPU's callbacks in order for rcu_barrier() to work - * correctly. Finally, note that we start all the callbacks - * afresh, even those that have passed through a grace period - * and are therefore ready to invoke. The theory is that hotplug - * events are rare, and that if they are frequent enough to - * indefinitely delay callbacks, you have far worse things to - * be worrying about. - */ - rdp_me = rsp->rda[smp_processor_id()]; - if (rdp->nxtlist != NULL) { - *rdp_me->nxttail[RCU_NEXT_TAIL] = rdp->nxtlist; - rdp_me->nxttail[RCU_NEXT_TAIL] = rdp->nxttail[RCU_NEXT_TAIL]; - rdp->nxtlist = NULL; - for (i = 0; i < RCU_NEXT_SIZE; i++) - rdp->nxttail[i] = &rdp->nxtlist; - rdp_me->qlen += rdp->qlen; - rdp->qlen = 0; - } - local_irq_restore(flags); + rcu_adopt_orphan_cbs(rsp); } /* @@ -918,6 +957,14 @@ static void rcu_offline_cpu(int cpu) #else /* #ifdef CONFIG_HOTPLUG_CPU */ +static void rcu_send_cbs_to_orphanage(struct rcu_state *rsp) +{ +} + +static void rcu_adopt_orphan_cbs(struct rcu_state *rsp) +{ +} + static void rcu_offline_cpu(int cpu) { } @@ -928,7 +975,7 @@ static void rcu_offline_cpu(int cpu) * Invoke any RCU callbacks that have made it to the end of their grace * period. Thottle as specified by rdp->blimit. */ -static void rcu_do_batch(struct rcu_data *rdp) +static void rcu_do_batch(struct rcu_state *rsp, struct rcu_data *rdp) { unsigned long flags; struct rcu_head *next, *list, **tail; @@ -981,6 +1028,13 @@ static void rcu_do_batch(struct rcu_data *rdp) if (rdp->blimit == LONG_MAX && rdp->qlen <= qlowmark) rdp->blimit = blimit; + /* Reset ->qlen_last_fqs_check trigger if enough CBs have drained. */ + if (rdp->qlen == 0 && rdp->qlen_last_fqs_check != 0) { + rdp->qlen_last_fqs_check = 0; + rdp->n_force_qs_snap = rsp->n_force_qs; + } else if (rdp->qlen < rdp->qlen_last_fqs_check - qhimark) + rdp->qlen_last_fqs_check = rdp->qlen; + local_irq_restore(flags); /* Re-raise the RCU softirq if there are callbacks remaining. */ @@ -1050,33 +1104,32 @@ static int rcu_process_dyntick(struct rcu_state *rsp, long lastcomp, int cpu; unsigned long flags; unsigned long mask; - struct rcu_node *rnp_cur = rsp->level[NUM_RCU_LVLS - 1]; - struct rcu_node *rnp_end = &rsp->node[NUM_RCU_NODES]; + struct rcu_node *rnp; - for (; rnp_cur < rnp_end; rnp_cur++) { + rcu_for_each_leaf_node(rsp, rnp) { mask = 0; - spin_lock_irqsave(&rnp_cur->lock, flags); + spin_lock_irqsave(&rnp->lock, flags); if (rsp->completed != lastcomp) { - spin_unlock_irqrestore(&rnp_cur->lock, flags); + spin_unlock_irqrestore(&rnp->lock, flags); return 1; } - if (rnp_cur->qsmask == 0) { - spin_unlock_irqrestore(&rnp_cur->lock, flags); + if (rnp->qsmask == 0) { + spin_unlock_irqrestore(&rnp->lock, flags); continue; } - cpu = rnp_cur->grplo; + cpu = rnp->grplo; bit = 1; - for (; cpu <= rnp_cur->grphi; cpu++, bit <<= 1) { - if ((rnp_cur->qsmask & bit) != 0 && f(rsp->rda[cpu])) + for (; cpu <= rnp->grphi; cpu++, bit <<= 1) { + if ((rnp->qsmask & bit) != 0 && f(rsp->rda[cpu])) mask |= bit; } if (mask != 0 && rsp->completed == lastcomp) { - /* cpu_quiet_msk() releases rnp_cur->lock. */ - cpu_quiet_msk(mask, rsp, rnp_cur, flags); + /* cpu_quiet_msk() releases rnp->lock. */ + cpu_quiet_msk(mask, rsp, rnp, flags); continue; } - spin_unlock_irqrestore(&rnp_cur->lock, flags); + spin_unlock_irqrestore(&rnp->lock, flags); } return 0; } @@ -1092,7 +1145,7 @@ static void force_quiescent_state(struct rcu_state *rsp, int relaxed) struct rcu_node *rnp = rcu_get_root(rsp); u8 signaled; - if (ACCESS_ONCE(rsp->completed) == ACCESS_ONCE(rsp->gpnum)) + if (!rcu_gp_in_progress(rsp)) return; /* No grace period in progress, nothing to force. */ if (!spin_trylock_irqsave(&rsp->fqslock, flags)) { rsp->n_force_qs_lh++; /* Inexact, can lose counts. Tough! */ @@ -1113,9 +1166,10 @@ static void force_quiescent_state(struct rcu_state *rsp, int relaxed) } spin_unlock(&rnp->lock); switch (signaled) { + case RCU_GP_IDLE: case RCU_GP_INIT: - break; /* grace period still initializing, ignore. */ + break; /* grace period idle or initializing, ignore. */ case RCU_SAVE_DYNTICK: @@ -1129,7 +1183,8 @@ static void force_quiescent_state(struct rcu_state *rsp, int relaxed) /* Update state, record completion counter. */ spin_lock(&rnp->lock); - if (lastcomp == rsp->completed) { + if (lastcomp == rsp->completed && + rsp->signaled == RCU_SAVE_DYNTICK) { rsp->signaled = RCU_FORCE_QS; dyntick_record_completed(rsp, lastcomp); } @@ -1195,7 +1250,7 @@ __rcu_process_callbacks(struct rcu_state *rsp, struct rcu_data *rdp) } /* If there are callbacks ready, invoke them. */ - rcu_do_batch(rdp); + rcu_do_batch(rsp, rdp); } /* @@ -1251,7 +1306,7 @@ __call_rcu(struct rcu_head *head, void (*func)(struct rcu_head *rcu), rdp->nxttail[RCU_NEXT_TAIL] = &head->next; /* Start a new grace period if one not already started. */ - if (ACCESS_ONCE(rsp->completed) == ACCESS_ONCE(rsp->gpnum)) { + if (!rcu_gp_in_progress(rsp)) { unsigned long nestflag; struct rcu_node *rnp_root = rcu_get_root(rsp); @@ -1259,10 +1314,20 @@ __call_rcu(struct rcu_head *head, void (*func)(struct rcu_head *rcu), rcu_start_gp(rsp, nestflag); /* releases rnp_root->lock. */ } - /* Force the grace period if too many callbacks or too long waiting. */ - if (unlikely(++rdp->qlen > qhimark)) { + /* + * Force the grace period if too many callbacks or too long waiting. + * Enforce hysteresis, and don't invoke force_quiescent_state() + * if some other CPU has recently done so. Also, don't bother + * invoking force_quiescent_state() if the newly enqueued callback + * is the only one waiting for a grace period to complete. + */ + if (unlikely(++rdp->qlen > rdp->qlen_last_fqs_check + qhimark)) { rdp->blimit = LONG_MAX; - force_quiescent_state(rsp, 0); + if (rsp->n_force_qs == rdp->n_force_qs_snap && + *rdp->nxttail[RCU_DONE_TAIL] != head) + force_quiescent_state(rsp, 0); + rdp->n_force_qs_snap = rsp->n_force_qs; + rdp->qlen_last_fqs_check = rdp->qlen; } else if ((long)(ACCESS_ONCE(rsp->jiffies_force_qs) - jiffies) < 0) force_quiescent_state(rsp, 1); local_irq_restore(flags); @@ -1331,7 +1396,7 @@ static int __rcu_pending(struct rcu_state *rsp, struct rcu_data *rdp) } /* Has an RCU GP gone long enough to send resched IPIs &c? */ - if (ACCESS_ONCE(rsp->completed) != ACCESS_ONCE(rsp->gpnum) && + if (rcu_gp_in_progress(rsp) && ((long)(ACCESS_ONCE(rsp->jiffies_force_qs) - jiffies) < 0)) { rdp->n_rp_need_fqs++; return 1; @@ -1368,6 +1433,82 @@ int rcu_needs_cpu(int cpu) rcu_preempt_needs_cpu(cpu); } +static DEFINE_PER_CPU(struct rcu_head, rcu_barrier_head) = {NULL}; +static atomic_t rcu_barrier_cpu_count; +static DEFINE_MUTEX(rcu_barrier_mutex); +static struct completion rcu_barrier_completion; + +static void rcu_barrier_callback(struct rcu_head *notused) +{ + if (atomic_dec_and_test(&rcu_barrier_cpu_count)) + complete(&rcu_barrier_completion); +} + +/* + * Called with preemption disabled, and from cross-cpu IRQ context. + */ +static void rcu_barrier_func(void *type) +{ + int cpu = smp_processor_id(); + struct rcu_head *head = &per_cpu(rcu_barrier_head, cpu); + void (*call_rcu_func)(struct rcu_head *head, + void (*func)(struct rcu_head *head)); + + atomic_inc(&rcu_barrier_cpu_count); + call_rcu_func = type; + call_rcu_func(head, rcu_barrier_callback); +} + +/* + * Orchestrate the specified type of RCU barrier, waiting for all + * RCU callbacks of the specified type to complete. + */ +static void _rcu_barrier(struct rcu_state *rsp, + void (*call_rcu_func)(struct rcu_head *head, + void (*func)(struct rcu_head *head))) +{ + BUG_ON(in_interrupt()); + /* Take mutex to serialize concurrent rcu_barrier() requests. */ + mutex_lock(&rcu_barrier_mutex); + init_completion(&rcu_barrier_completion); + /* + * Initialize rcu_barrier_cpu_count to 1, then invoke + * rcu_barrier_func() on each CPU, so that each CPU also has + * incremented rcu_barrier_cpu_count. Only then is it safe to + * decrement rcu_barrier_cpu_count -- otherwise the first CPU + * might complete its grace period before all of the other CPUs + * did their increment, causing this function to return too + * early. + */ + atomic_set(&rcu_barrier_cpu_count, 1); + preempt_disable(); /* stop CPU_DYING from filling orphan_cbs_list */ + rcu_adopt_orphan_cbs(rsp); + on_each_cpu(rcu_barrier_func, (void *)call_rcu_func, 1); + preempt_enable(); /* CPU_DYING can again fill orphan_cbs_list */ + if (atomic_dec_and_test(&rcu_barrier_cpu_count)) + complete(&rcu_barrier_completion); + wait_for_completion(&rcu_barrier_completion); + mutex_unlock(&rcu_barrier_mutex); +} + +/** + * rcu_barrier_bh - Wait until all in-flight call_rcu_bh() callbacks complete. + */ +void rcu_barrier_bh(void) +{ + _rcu_barrier(&rcu_bh_state, call_rcu_bh); +} +EXPORT_SYMBOL_GPL(rcu_barrier_bh); + +/** + * rcu_barrier_sched - Wait for in-flight call_rcu_sched() callbacks. + */ +void rcu_barrier_sched(void) +{ + _rcu_barrier(&rcu_sched_state, call_rcu_sched); +} +EXPORT_SYMBOL_GPL(rcu_barrier_sched); + /* * Do boot-time initialization of a CPU's per-CPU RCU data. */ @@ -1418,6 +1559,8 @@ rcu_init_percpu_data(int cpu, struct rcu_state *rsp, int preemptable) rdp->beenonline = 1; /* We have now been online. */ rdp->preemptable = preemptable; rdp->passed_quiesc_completed = lastcomp - 1; + rdp->qlen_last_fqs_check = 0; + rdp->n_force_qs_snap = rsp->n_force_qs; rdp->blimit = blimit; spin_unlock(&rnp->lock); /* irqs remain disabled. */ @@ -1464,6 +1607,22 @@ int __cpuinit rcu_cpu_notify(struct notifier_block *self, case CPU_UP_PREPARE_FROZEN: rcu_online_cpu(cpu); break; + case CPU_DYING: + case CPU_DYING_FROZEN: + /* + * preempt_disable() in _rcu_barrier() prevents stop_machine(), + * so when "on_each_cpu(rcu_barrier_func, (void *)type, 1);" + * returns, all online cpus have queued rcu_barrier_func(). + * The dying CPU clears its cpu_online_mask bit and + * moves all of its RCU callbacks to ->orphan_cbs_list + * in the context of stop_machine(), so subsequent calls + * to _rcu_barrier() will adopt these callbacks and only + * then queue rcu_barrier_func() on all remaining CPUs. + */ + rcu_send_cbs_to_orphanage(&rcu_bh_state); + rcu_send_cbs_to_orphanage(&rcu_sched_state); + rcu_preempt_send_cbs_to_orphanage(); + break; case CPU_DEAD: case CPU_DEAD_FROZEN: case CPU_UP_CANCELED: @@ -1526,7 +1685,8 @@ static void __init rcu_init_one(struct rcu_state *rsp) cpustride *= rsp->levelspread[i]; rnp = rsp->level[i]; for (j = 0; j < rsp->levelcnt[i]; j++, rnp++) { - spin_lock_init(&rnp->lock); + if (rnp != rcu_get_root(rsp)) + spin_lock_init(&rnp->lock); rnp->gpnum = 0; rnp->qsmask = 0; rnp->qsmaskinit = 0; @@ -1549,6 +1709,7 @@ static void __init rcu_init_one(struct rcu_state *rsp) INIT_LIST_HEAD(&rnp->blocked_tasks[1]); } } + spin_lock_init(&rcu_get_root(rsp)->lock); } /* @@ -1558,6 +1719,10 @@ static void __init rcu_init_one(struct rcu_state *rsp) */ #define RCU_INIT_FLAVOR(rsp, rcu_data) \ do { \ + int i; \ + int j; \ + struct rcu_node *rnp; \ + \ rcu_init_one(rsp); \ rnp = (rsp)->level[NUM_RCU_LVLS - 1]; \ j = 0; \ @@ -1570,31 +1735,8 @@ do { \ } \ } while (0) -#ifdef CONFIG_TREE_PREEMPT_RCU - -void __init __rcu_init_preempt(void) -{ - int i; /* All used by RCU_INIT_FLAVOR(). */ - int j; - struct rcu_node *rnp; - - RCU_INIT_FLAVOR(&rcu_preempt_state, rcu_preempt_data); -} - -#else /* #ifdef CONFIG_TREE_PREEMPT_RCU */ - -void __init __rcu_init_preempt(void) -{ -} - -#endif /* #else #ifdef CONFIG_TREE_PREEMPT_RCU */ - void __init __rcu_init(void) { - int i; /* All used by RCU_INIT_FLAVOR(). */ - int j; - struct rcu_node *rnp; - rcu_bootup_announce(); #ifdef CONFIG_RCU_CPU_STALL_DETECTOR printk(KERN_INFO "RCU-based detection of stalled CPUs is enabled.\n"); @@ -1605,6 +1747,4 @@ void __init __rcu_init(void) open_softirq(RCU_SOFTIRQ, rcu_process_callbacks); } -module_param(blimit, int, 0); -module_param(qhimark, int, 0); -module_param(qlowmark, int, 0); +#include "rcutree_plugin.h" diff --git a/kernel/rcutree.h b/kernel/rcutree.h index 8e8287a983c2..1899023b0962 100644 --- a/kernel/rcutree.h +++ b/kernel/rcutree.h @@ -48,14 +48,14 @@ #elif NR_CPUS <= RCU_FANOUT_SQ # define NUM_RCU_LVLS 2 # define NUM_RCU_LVL_0 1 -# define NUM_RCU_LVL_1 (((NR_CPUS) + RCU_FANOUT - 1) / RCU_FANOUT) +# define NUM_RCU_LVL_1 DIV_ROUND_UP(NR_CPUS, RCU_FANOUT) # define NUM_RCU_LVL_2 (NR_CPUS) # define NUM_RCU_LVL_3 0 #elif NR_CPUS <= RCU_FANOUT_CUBE # define NUM_RCU_LVLS 3 # define NUM_RCU_LVL_0 1 -# define NUM_RCU_LVL_1 (((NR_CPUS) + RCU_FANOUT_SQ - 1) / RCU_FANOUT_SQ) -# define NUM_RCU_LVL_2 (((NR_CPUS) + (RCU_FANOUT) - 1) / (RCU_FANOUT)) +# define NUM_RCU_LVL_1 DIV_ROUND_UP(NR_CPUS, RCU_FANOUT_SQ) +# define NUM_RCU_LVL_2 DIV_ROUND_UP(NR_CPUS, RCU_FANOUT) # define NUM_RCU_LVL_3 NR_CPUS #else # error "CONFIG_RCU_FANOUT insufficient for NR_CPUS" @@ -79,15 +79,21 @@ struct rcu_dynticks { * Definition for node within the RCU grace-period-detection hierarchy. */ struct rcu_node { - spinlock_t lock; + spinlock_t lock; /* Root rcu_node's lock protects some */ + /* rcu_state fields as well as following. */ long gpnum; /* Current grace period for this node. */ /* This will either be equal to or one */ /* behind the root rcu_node's gpnum. */ unsigned long qsmask; /* CPUs or groups that need to switch in */ /* order for current grace period to proceed.*/ + /* In leaf rcu_node, each bit corresponds to */ + /* an rcu_data structure, otherwise, each */ + /* bit corresponds to a child rcu_node */ + /* structure. */ unsigned long qsmaskinit; /* Per-GP initialization for qsmask. */ unsigned long grpmask; /* Mask to apply to parent qsmask. */ + /* Only one bit will be set in this mask. */ int grplo; /* lowest-numbered CPU or group here. */ int grphi; /* highest-numbered CPU or group here. */ u8 grpnum; /* CPU/group number for next level up. */ @@ -95,8 +101,23 @@ struct rcu_node { struct rcu_node *parent; struct list_head blocked_tasks[2]; /* Tasks blocked in RCU read-side critsect. */ + /* Grace period number (->gpnum) x blocked */ + /* by tasks on the (x & 0x1) element of the */ + /* blocked_tasks[] array. */ } ____cacheline_internodealigned_in_smp; +/* + * Do a full breadth-first scan of the rcu_node structures for the + * specified rcu_state structure. + */ +#define rcu_for_each_node_breadth_first(rsp, rnp) \ + for ((rnp) = &(rsp)->node[0]; \ + (rnp) < &(rsp)->node[NUM_RCU_NODES]; (rnp)++) + +#define rcu_for_each_leaf_node(rsp, rnp) \ + for ((rnp) = (rsp)->level[NUM_RCU_LVLS - 1]; \ + (rnp) < &(rsp)->node[NUM_RCU_NODES]; (rnp)++) + /* Index values for nxttail array in struct rcu_data. */ #define RCU_DONE_TAIL 0 /* Also RCU_WAIT head. */ #define RCU_WAIT_TAIL 1 /* Also RCU_NEXT_READY head. */ @@ -126,23 +147,30 @@ struct rcu_data { * Any of the partitions might be empty, in which case the * pointer to that partition will be equal to the pointer for * the following partition. When the list is empty, all of - * the nxttail elements point to nxtlist, which is NULL. + * the nxttail elements point to the ->nxtlist pointer itself, + * which in that case is NULL. * - * [*nxttail[RCU_NEXT_READY_TAIL], NULL = *nxttail[RCU_NEXT_TAIL]): - * Entries that might have arrived after current GP ended - * [*nxttail[RCU_WAIT_TAIL], *nxttail[RCU_NEXT_READY_TAIL]): - * Entries known to have arrived before current GP ended - * [*nxttail[RCU_DONE_TAIL], *nxttail[RCU_WAIT_TAIL]): - * Entries that batch # <= ->completed - 1: waiting for current GP * [nxtlist, *nxttail[RCU_DONE_TAIL]): * Entries that batch # <= ->completed * The grace period for these entries has completed, and * the other grace-period-completed entries may be moved * here temporarily in rcu_process_callbacks(). + * [*nxttail[RCU_DONE_TAIL], *nxttail[RCU_WAIT_TAIL]): + * Entries that batch # <= ->completed - 1: waiting for current GP + * [*nxttail[RCU_WAIT_TAIL], *nxttail[RCU_NEXT_READY_TAIL]): + * Entries known to have arrived before current GP ended + * [*nxttail[RCU_NEXT_READY_TAIL], *nxttail[RCU_NEXT_TAIL]): + * Entries that might have arrived after current GP ended + * Note that the value of *nxttail[RCU_NEXT_TAIL] will + * always be NULL, as this is the end of the list. */ struct rcu_head *nxtlist; struct rcu_head **nxttail[RCU_NEXT_SIZE]; long qlen; /* # of queued callbacks */ + long qlen_last_fqs_check; + /* qlen at last check for QS forcing */ + unsigned long n_force_qs_snap; + /* did other CPU force QS recently? */ long blimit; /* Upper limit on a processed batch */ #ifdef CONFIG_NO_HZ @@ -173,9 +201,10 @@ struct rcu_data { }; /* Values for signaled field in struct rcu_state. */ -#define RCU_GP_INIT 0 /* Grace period being initialized. */ -#define RCU_SAVE_DYNTICK 1 /* Need to scan dyntick state. */ -#define RCU_FORCE_QS 2 /* Need to force quiescent state. */ +#define RCU_GP_IDLE 0 /* No grace period in progress. */ +#define RCU_GP_INIT 1 /* Grace period being initialized. */ +#define RCU_SAVE_DYNTICK 2 /* Need to scan dyntick state. */ +#define RCU_FORCE_QS 3 /* Need to force quiescent state. */ #ifdef CONFIG_NO_HZ #define RCU_SIGNAL_INIT RCU_SAVE_DYNTICK #else /* #ifdef CONFIG_NO_HZ */ @@ -216,8 +245,19 @@ struct rcu_state { /* Force QS state. */ long gpnum; /* Current gp number. */ long completed; /* # of last completed gp. */ + + /* End of fields guarded by root rcu_node's lock. */ + spinlock_t onofflock; /* exclude on/offline and */ - /* starting new GP. */ + /* starting new GP. Also */ + /* protects the following */ + /* orphan_cbs fields. */ + struct rcu_head *orphan_cbs_list; /* list of rcu_head structs */ + /* orphaned by all CPUs in */ + /* a given leaf rcu_node */ + /* going offline. */ + struct rcu_head **orphan_cbs_tail; /* And tail pointer. */ + long orphan_qlen; /* Number of orphaned cbs. */ spinlock_t fqslock; /* Only one task forcing */ /* quiescent states. */ unsigned long jiffies_force_qs; /* Time at which to invoke */ @@ -255,5 +295,30 @@ extern struct rcu_state rcu_preempt_state; DECLARE_PER_CPU(struct rcu_data, rcu_preempt_data); #endif /* #ifdef CONFIG_TREE_PREEMPT_RCU */ -#endif /* #ifdef RCU_TREE_NONCORE */ +#else /* #ifdef RCU_TREE_NONCORE */ + +/* Forward declarations for rcutree_plugin.h */ +static inline void rcu_bootup_announce(void); +long rcu_batches_completed(void); +static void rcu_preempt_note_context_switch(int cpu); +static int rcu_preempted_readers(struct rcu_node *rnp); +#ifdef CONFIG_RCU_CPU_STALL_DETECTOR +static void rcu_print_task_stall(struct rcu_node *rnp); +#endif /* #ifdef CONFIG_RCU_CPU_STALL_DETECTOR */ +static void rcu_preempt_check_blocked_tasks(struct rcu_node *rnp); +#ifdef CONFIG_HOTPLUG_CPU +static int rcu_preempt_offline_tasks(struct rcu_state *rsp, + struct rcu_node *rnp, + struct rcu_data *rdp); +static void rcu_preempt_offline_cpu(int cpu); +#endif /* #ifdef CONFIG_HOTPLUG_CPU */ +static void rcu_preempt_check_callbacks(int cpu); +static void rcu_preempt_process_callbacks(void); +void call_rcu(struct rcu_head *head, void (*func)(struct rcu_head *rcu)); +static int rcu_preempt_pending(int cpu); +static int rcu_preempt_needs_cpu(int cpu); +static void __cpuinit rcu_preempt_init_percpu_data(int cpu); +static void rcu_preempt_send_cbs_to_orphanage(void); +static void __init __rcu_init_preempt(void); +#endif /* #else #ifdef RCU_TREE_NONCORE */ diff --git a/kernel/rcutree_plugin.h b/kernel/rcutree_plugin.h index 1cee04f627eb..ef2a58c2b9d5 100644 --- a/kernel/rcutree_plugin.h +++ b/kernel/rcutree_plugin.h @@ -150,6 +150,16 @@ void __rcu_read_lock(void) } EXPORT_SYMBOL_GPL(__rcu_read_lock); +/* + * Check for preempted RCU readers blocking the current grace period + * for the specified rcu_node structure. If the caller needs a reliable + * answer, it must hold the rcu_node's ->lock. + */ +static int rcu_preempted_readers(struct rcu_node *rnp) +{ + return !list_empty(&rnp->blocked_tasks[rnp->gpnum & 0x1]); +} + static void rcu_read_unlock_special(struct task_struct *t) { int empty; @@ -196,7 +206,7 @@ static void rcu_read_unlock_special(struct task_struct *t) break; spin_unlock(&rnp->lock); /* irqs remain disabled. */ } - empty = list_empty(&rnp->blocked_tasks[rnp->gpnum & 0x1]); + empty = !rcu_preempted_readers(rnp); list_del_init(&t->rcu_node_entry); t->rcu_blocked_node = NULL; @@ -207,7 +217,7 @@ static void rcu_read_unlock_special(struct task_struct *t) * drop rnp->lock and restore irq. */ if (!empty && rnp->qsmask == 0 && - list_empty(&rnp->blocked_tasks[rnp->gpnum & 0x1])) { + !rcu_preempted_readers(rnp)) { struct rcu_node *rnp_p; if (rnp->parent == NULL) { @@ -257,12 +267,12 @@ static void rcu_print_task_stall(struct rcu_node *rnp) { unsigned long flags; struct list_head *lp; - int phase = rnp->gpnum & 0x1; + int phase; struct task_struct *t; - if (!list_empty(&rnp->blocked_tasks[phase])) { + if (rcu_preempted_readers(rnp)) { spin_lock_irqsave(&rnp->lock, flags); - phase = rnp->gpnum & 0x1; /* re-read under lock. */ + phase = rnp->gpnum & 0x1; lp = &rnp->blocked_tasks[phase]; list_for_each_entry(t, lp, rcu_node_entry) printk(" P%d", t->pid); @@ -281,20 +291,10 @@ static void rcu_print_task_stall(struct rcu_node *rnp) */ static void rcu_preempt_check_blocked_tasks(struct rcu_node *rnp) { - WARN_ON_ONCE(!list_empty(&rnp->blocked_tasks[rnp->gpnum & 0x1])); + WARN_ON_ONCE(rcu_preempted_readers(rnp)); WARN_ON_ONCE(rnp->qsmask); } -/* - * Check for preempted RCU readers for the specified rcu_node structure. - * If the caller needs a reliable answer, it must hold the rcu_node's - * >lock. - */ -static int rcu_preempted_readers(struct rcu_node *rnp) -{ - return !list_empty(&rnp->blocked_tasks[rnp->gpnum & 0x1]); -} - #ifdef CONFIG_HOTPLUG_CPU /* @@ -304,21 +304,25 @@ static int rcu_preempted_readers(struct rcu_node *rnp) * parent is to remove the need for rcu_read_unlock_special() to * make more than two attempts to acquire the target rcu_node's lock. * + * Returns 1 if there was previously a task blocking the current grace + * period on the specified rcu_node structure. + * * The caller must hold rnp->lock with irqs disabled. */ -static void rcu_preempt_offline_tasks(struct rcu_state *rsp, - struct rcu_node *rnp, - struct rcu_data *rdp) +static int rcu_preempt_offline_tasks(struct rcu_state *rsp, + struct rcu_node *rnp, + struct rcu_data *rdp) { int i; struct list_head *lp; struct list_head *lp_root; + int retval = rcu_preempted_readers(rnp); struct rcu_node *rnp_root = rcu_get_root(rsp); struct task_struct *tp; if (rnp == rnp_root) { WARN_ONCE(1, "Last CPU thought to be offlined?"); - return; /* Shouldn't happen: at least one CPU online. */ + return 0; /* Shouldn't happen: at least one CPU online. */ } WARN_ON_ONCE(rnp != rdp->mynode && (!list_empty(&rnp->blocked_tasks[0]) || @@ -342,6 +346,8 @@ static void rcu_preempt_offline_tasks(struct rcu_state *rsp, spin_unlock(&rnp_root->lock); /* irqs remain disabled */ } } + + return retval; } /* @@ -393,6 +399,17 @@ void call_rcu(struct rcu_head *head, void (*func)(struct rcu_head *rcu)) EXPORT_SYMBOL_GPL(call_rcu); /* + * Wait for an rcu-preempt grace period. We are supposed to expedite the + * grace period, but this is the crude slow compatability hack, so just + * invoke synchronize_rcu(). + */ +void synchronize_rcu_expedited(void) +{ + synchronize_rcu(); +} +EXPORT_SYMBOL_GPL(synchronize_rcu_expedited); + +/* * Check to see if there is any immediate preemptable-RCU-related work * to be done. */ @@ -410,6 +427,15 @@ static int rcu_preempt_needs_cpu(int cpu) return !!per_cpu(rcu_preempt_data, cpu).nxtlist; } +/** + * rcu_barrier - Wait until all in-flight call_rcu() callbacks complete. + */ +void rcu_barrier(void) +{ + _rcu_barrier(&rcu_preempt_state, call_rcu); +} +EXPORT_SYMBOL_GPL(rcu_barrier); + /* * Initialize preemptable RCU's per-CPU data. */ @@ -419,6 +445,22 @@ static void __cpuinit rcu_preempt_init_percpu_data(int cpu) } /* + * Move preemptable RCU's callbacks to ->orphan_cbs_list. + */ +static void rcu_preempt_send_cbs_to_orphanage(void) +{ + rcu_send_cbs_to_orphanage(&rcu_preempt_state); +} + +/* + * Initialize preemptable RCU's state structures. + */ +static void __init __rcu_init_preempt(void) +{ + RCU_INIT_FLAVOR(&rcu_preempt_state, rcu_preempt_data); +} + +/* * Check for a task exiting while in a preemptable-RCU read-side * critical section, clean up if so. No need to issue warnings, * as debug_check_no_locks_held() already does this if lockdep @@ -461,6 +503,15 @@ static void rcu_preempt_note_context_switch(int cpu) { } +/* + * Because preemptable RCU does not exist, there are never any preempted + * RCU readers. + */ +static int rcu_preempted_readers(struct rcu_node *rnp) +{ + return 0; +} + #ifdef CONFIG_RCU_CPU_STALL_DETECTOR /* @@ -483,25 +534,19 @@ static void rcu_preempt_check_blocked_tasks(struct rcu_node *rnp) WARN_ON_ONCE(rnp->qsmask); } -/* - * Because preemptable RCU does not exist, there are never any preempted - * RCU readers. - */ -static int rcu_preempted_readers(struct rcu_node *rnp) -{ - return 0; -} - #ifdef CONFIG_HOTPLUG_CPU /* * Because preemptable RCU does not exist, it never needs to migrate - * tasks that were blocked within RCU read-side critical sections. + * tasks that were blocked within RCU read-side critical sections, and + * such non-existent tasks cannot possibly have been blocking the current + * grace period. */ -static void rcu_preempt_offline_tasks(struct rcu_state *rsp, - struct rcu_node *rnp, - struct rcu_data *rdp) +static int rcu_preempt_offline_tasks(struct rcu_state *rsp, + struct rcu_node *rnp, + struct rcu_data *rdp) { + return 0; } /* @@ -518,7 +563,7 @@ static void rcu_preempt_offline_cpu(int cpu) * Because preemptable RCU does not exist, it never has any callbacks * to check. */ -void rcu_preempt_check_callbacks(int cpu) +static void rcu_preempt_check_callbacks(int cpu) { } @@ -526,7 +571,7 @@ void rcu_preempt_check_callbacks(int cpu) * Because preemptable RCU does not exist, it never has any callbacks * to process. */ -void rcu_preempt_process_callbacks(void) +static void rcu_preempt_process_callbacks(void) { } @@ -540,6 +585,16 @@ void call_rcu(struct rcu_head *head, void (*func)(struct rcu_head *rcu)) EXPORT_SYMBOL_GPL(call_rcu); /* + * Wait for an rcu-preempt grace period, but make it happen quickly. + * But because preemptable RCU does not exist, map to rcu-sched. + */ +void synchronize_rcu_expedited(void) +{ + synchronize_sched_expedited(); +} +EXPORT_SYMBOL_GPL(synchronize_rcu_expedited); + +/* * Because preemptable RCU does not exist, it never has any work to do. */ static int rcu_preempt_pending(int cpu) @@ -556,6 +611,16 @@ static int rcu_preempt_needs_cpu(int cpu) } /* + * Because preemptable RCU does not exist, rcu_barrier() is just + * another name for rcu_barrier_sched(). + */ +void rcu_barrier(void) +{ + rcu_barrier_sched(); +} +EXPORT_SYMBOL_GPL(rcu_barrier); + +/* * Because preemptable RCU does not exist, there is no per-CPU * data to initialize. */ @@ -563,4 +628,18 @@ static void __cpuinit rcu_preempt_init_percpu_data(int cpu) { } +/* + * Because there is no preemptable RCU, there are no callbacks to move. + */ +static void rcu_preempt_send_cbs_to_orphanage(void) +{ +} + +/* + * Because preemptable RCU does not exist, it need not be initialized. + */ +static void __init __rcu_init_preempt(void) +{ +} + #endif /* #else #ifdef CONFIG_TREE_PREEMPT_RCU */ diff --git a/kernel/rcutree_trace.c b/kernel/rcutree_trace.c index 179e6ad80dc0..4b31c779e62e 100644 --- a/kernel/rcutree_trace.c +++ b/kernel/rcutree_trace.c @@ -159,13 +159,13 @@ static void print_one_rcu_state(struct seq_file *m, struct rcu_state *rsp) struct rcu_node *rnp; seq_printf(m, "c=%ld g=%ld s=%d jfq=%ld j=%x " - "nfqs=%lu/nfqsng=%lu(%lu) fqlh=%lu\n", + "nfqs=%lu/nfqsng=%lu(%lu) fqlh=%lu oqlen=%ld\n", rsp->completed, rsp->gpnum, rsp->signaled, (long)(rsp->jiffies_force_qs - jiffies), (int)(jiffies & 0xffff), rsp->n_force_qs, rsp->n_force_qs_ngp, rsp->n_force_qs - rsp->n_force_qs_ngp, - rsp->n_force_qs_lh); + rsp->n_force_qs_lh, rsp->orphan_qlen); for (rnp = &rsp->node[0]; rnp - &rsp->node[0] < NUM_RCU_NODES; rnp++) { if (rnp->level != level) { seq_puts(m, "\n"); diff --git a/kernel/sched.c b/kernel/sched.c index 1535f3884b88..3c11ae0a948d 100644 --- a/kernel/sched.c +++ b/kernel/sched.c @@ -309,6 +309,8 @@ static DEFINE_PER_CPU_SHARED_ALIGNED(struct rt_rq, init_rt_rq); */ static DEFINE_SPINLOCK(task_group_lock); +#ifdef CONFIG_FAIR_GROUP_SCHED + #ifdef CONFIG_SMP static int root_task_group_empty(void) { @@ -316,7 +318,6 @@ static int root_task_group_empty(void) } #endif -#ifdef CONFIG_FAIR_GROUP_SCHED #ifdef CONFIG_USER_SCHED # define INIT_TASK_GROUP_LOAD (2*NICE_0_LOAD) #else /* !CONFIG_USER_SCHED */ @@ -676,6 +677,7 @@ inline void update_rq_clock(struct rq *rq) /** * runqueue_is_locked + * @cpu: the processor in question. * * Returns true if the current cpu runqueue is locked. * This interface allows printk to be called with the runqueue lock @@ -1563,11 +1565,7 @@ static unsigned long cpu_avg_load_per_task(int cpu) #ifdef CONFIG_FAIR_GROUP_SCHED -struct update_shares_data { - unsigned long rq_weight[NR_CPUS]; -}; - -static DEFINE_PER_CPU(struct update_shares_data, update_shares_data); +static __read_mostly unsigned long *update_shares_data; static void __set_se_shares(struct sched_entity *se, unsigned long shares); @@ -1577,12 +1575,12 @@ static void __set_se_shares(struct sched_entity *se, unsigned long shares); static void update_group_shares_cpu(struct task_group *tg, int cpu, unsigned long sd_shares, unsigned long sd_rq_weight, - struct update_shares_data *usd) + unsigned long *usd_rq_weight) { unsigned long shares, rq_weight; int boost = 0; - rq_weight = usd->rq_weight[cpu]; + rq_weight = usd_rq_weight[cpu]; if (!rq_weight) { boost = 1; rq_weight = NICE_0_LOAD; @@ -1617,7 +1615,7 @@ static void update_group_shares_cpu(struct task_group *tg, int cpu, static int tg_shares_up(struct task_group *tg, void *data) { unsigned long weight, rq_weight = 0, shares = 0; - struct update_shares_data *usd; + unsigned long *usd_rq_weight; struct sched_domain *sd = data; unsigned long flags; int i; @@ -1626,11 +1624,11 @@ static int tg_shares_up(struct task_group *tg, void *data) return 0; local_irq_save(flags); - usd = &__get_cpu_var(update_shares_data); + usd_rq_weight = per_cpu_ptr(update_shares_data, smp_processor_id()); for_each_cpu(i, sched_domain_span(sd)) { weight = tg->cfs_rq[i]->load.weight; - usd->rq_weight[i] = weight; + usd_rq_weight[i] = weight; /* * If there are currently no tasks on the cpu pretend there @@ -1651,7 +1649,7 @@ static int tg_shares_up(struct task_group *tg, void *data) shares = tg->shares; for_each_cpu(i, sched_domain_span(sd)) - update_group_shares_cpu(tg, i, shares, rq_weight, usd); + update_group_shares_cpu(tg, i, shares, rq_weight, usd_rq_weight); local_irq_restore(flags); @@ -1995,6 +1993,38 @@ static inline void check_class_changed(struct rq *rq, struct task_struct *p, p->sched_class->prio_changed(rq, p, oldprio, running); } +/** + * kthread_bind - bind a just-created kthread to a cpu. + * @p: thread created by kthread_create(). + * @cpu: cpu (might not be online, must be possible) for @k to run on. + * + * Description: This function is equivalent to set_cpus_allowed(), + * except that @cpu doesn't need to be online, and the thread must be + * stopped (i.e., just returned from kthread_create()). + * + * Function lives here instead of kthread.c because it messes with + * scheduler internals which require locking. + */ +void kthread_bind(struct task_struct *p, unsigned int cpu) +{ + struct rq *rq = cpu_rq(cpu); + unsigned long flags; + + /* Must have done schedule() in kthread() before we set_task_cpu */ + if (!wait_task_inactive(p, TASK_UNINTERRUPTIBLE)) { + WARN_ON(1); + return; + } + + spin_lock_irqsave(&rq->lock, flags); + set_task_cpu(p, cpu); + p->cpus_allowed = cpumask_of_cpu(cpu); + p->rt.nr_cpus_allowed = 1; + p->flags |= PF_THREAD_BOUND; + spin_unlock_irqrestore(&rq->lock, flags); +} +EXPORT_SYMBOL(kthread_bind); + #ifdef CONFIG_SMP /* * Is this task likely cache-hot: @@ -2007,7 +2037,7 @@ task_hot(struct task_struct *p, u64 now, struct sched_domain *sd) /* * Buddy candidates are cache hot: */ - if (sched_feat(CACHE_HOT_BUDDY) && + if (sched_feat(CACHE_HOT_BUDDY) && this_rq()->nr_running && (&p->se == cfs_rq_of(&p->se)->next || &p->se == cfs_rq_of(&p->se)->last)) return 1; @@ -2311,7 +2341,7 @@ static int try_to_wake_up(struct task_struct *p, unsigned int state, { int cpu, orig_cpu, this_cpu, success = 0; unsigned long flags; - struct rq *rq; + struct rq *rq, *orig_rq; if (!sched_feat(SYNC_WAKEUPS)) wake_flags &= ~WF_SYNC; @@ -2319,7 +2349,7 @@ static int try_to_wake_up(struct task_struct *p, unsigned int state, this_cpu = get_cpu(); smp_wmb(); - rq = task_rq_lock(p, &flags); + rq = orig_rq = task_rq_lock(p, &flags); update_rq_clock(rq); if (!(p->state & state)) goto out; @@ -2350,6 +2380,10 @@ static int try_to_wake_up(struct task_struct *p, unsigned int state, set_task_cpu(p, cpu); rq = task_rq_lock(p, &flags); + + if (rq != orig_rq) + update_rq_clock(rq); + WARN_ON(p->state != TASK_WAKING); cpu = task_cpu(p); @@ -2515,22 +2549,17 @@ void sched_fork(struct task_struct *p, int clone_flags) __sched_fork(p); /* - * Make sure we do not leak PI boosting priority to the child. - */ - p->prio = current->normal_prio; - - /* * Revert to default priority/policy on fork if requested. */ if (unlikely(p->sched_reset_on_fork)) { - if (p->policy == SCHED_FIFO || p->policy == SCHED_RR) + if (p->policy == SCHED_FIFO || p->policy == SCHED_RR) { p->policy = SCHED_NORMAL; - - if (p->normal_prio < DEFAULT_PRIO) - p->prio = DEFAULT_PRIO; + p->normal_prio = p->static_prio; + } if (PRIO_TO_NICE(p->static_prio) < 0) { p->static_prio = NICE_TO_PRIO(0); + p->normal_prio = p->static_prio; set_load_weight(p); } @@ -2541,6 +2570,11 @@ void sched_fork(struct task_struct *p, int clone_flags) p->sched_reset_on_fork = 0; } + /* + * Make sure we do not leak PI boosting priority to the child. + */ + p->prio = current->normal_prio; + if (!rt_prio(p->prio)) p->sched_class = &fair_sched_class; @@ -2581,8 +2615,6 @@ void wake_up_new_task(struct task_struct *p, unsigned long clone_flags) BUG_ON(p->state != TASK_RUNNING); update_rq_clock(rq); - p->prio = effective_prio(p); - if (!p->sched_class->task_new || !current->se.on_rq) { activate_task(rq, p, 0); } else { @@ -3658,6 +3690,7 @@ static void update_group_power(struct sched_domain *sd, int cpu) /** * update_sg_lb_stats - Update sched_group's statistics for load balancing. + * @sd: The sched_domain whose statistics are to be updated. * @group: sched_group whose statistics are to be updated. * @this_cpu: Cpu for which load balance is currently performed. * @idle: Idle status of this_cpu @@ -6720,9 +6753,6 @@ EXPORT_SYMBOL(yield); /* * This task is about to go to sleep on IO. Increment rq->nr_iowait so * that process accounting knows that this is a task in IO wait state. - * - * But don't do that if it is a deliberate, throttling IO wait (this task - * has set its backing_dev_info: the queue against which it should throttle) */ void __sched io_schedule(void) { @@ -9406,6 +9436,10 @@ void __init sched_init(void) #endif /* CONFIG_USER_SCHED */ #endif /* CONFIG_GROUP_SCHED */ +#if defined CONFIG_FAIR_GROUP_SCHED && defined CONFIG_SMP + update_shares_data = __alloc_percpu(nr_cpu_ids * sizeof(unsigned long), + __alignof__(unsigned long)); +#endif for_each_possible_cpu(i) { struct rq *rq; @@ -9531,13 +9565,13 @@ void __init sched_init(void) current->sched_class = &fair_sched_class; /* Allocate the nohz_cpu_mask if CONFIG_CPUMASK_OFFSTACK */ - alloc_cpumask_var(&nohz_cpu_mask, GFP_NOWAIT); + zalloc_cpumask_var(&nohz_cpu_mask, GFP_NOWAIT); #ifdef CONFIG_SMP #ifdef CONFIG_NO_HZ - alloc_cpumask_var(&nohz.cpu_mask, GFP_NOWAIT); + zalloc_cpumask_var(&nohz.cpu_mask, GFP_NOWAIT); alloc_cpumask_var(&nohz.ilb_grp_nohz_mask, GFP_NOWAIT); #endif - alloc_cpumask_var(&cpu_isolated_map, GFP_NOWAIT); + zalloc_cpumask_var(&cpu_isolated_map, GFP_NOWAIT); #endif /* SMP */ perf_event_init(); diff --git a/kernel/sched_fair.c b/kernel/sched_fair.c index 4e777b47eeda..37087a7fac22 100644 --- a/kernel/sched_fair.c +++ b/kernel/sched_fair.c @@ -822,6 +822,26 @@ check_preempt_tick(struct cfs_rq *cfs_rq, struct sched_entity *curr) * re-elected due to buddy favours. */ clear_buddies(cfs_rq, curr); + return; + } + + /* + * Ensure that a task that missed wakeup preemption by a + * narrow margin doesn't have to wait for a full slice. + * This also mitigates buddy induced latencies under load. + */ + if (!sched_feat(WAKEUP_PREEMPT)) + return; + + if (delta_exec < sysctl_sched_min_granularity) + return; + + if (cfs_rq->nr_running > 1) { + struct sched_entity *se = __pick_next_entity(cfs_rq); + s64 delta = curr->vruntime - se->vruntime; + + if (delta > ideal_runtime) + resched_task(rq_of(cfs_rq)->curr); } } @@ -861,12 +881,18 @@ wakeup_preempt_entity(struct sched_entity *curr, struct sched_entity *se); static struct sched_entity *pick_next_entity(struct cfs_rq *cfs_rq) { struct sched_entity *se = __pick_next_entity(cfs_rq); + struct sched_entity *left = se; - if (cfs_rq->next && wakeup_preempt_entity(cfs_rq->next, se) < 1) - return cfs_rq->next; + if (cfs_rq->next && wakeup_preempt_entity(cfs_rq->next, left) < 1) + se = cfs_rq->next; - if (cfs_rq->last && wakeup_preempt_entity(cfs_rq->last, se) < 1) - return cfs_rq->last; + /* + * Prefer last buddy, try to return the CPU to a preempted task. + */ + if (cfs_rq->last && wakeup_preempt_entity(cfs_rq->last, left) < 1) + se = cfs_rq->last; + + clear_buddies(cfs_rq, se); return se; } @@ -1568,6 +1594,7 @@ static void check_preempt_wakeup(struct rq *rq, struct task_struct *p, int wake_ struct sched_entity *se = &curr->se, *pse = &p->se; struct cfs_rq *cfs_rq = task_cfs_rq(curr); int sync = wake_flags & WF_SYNC; + int scale = cfs_rq->nr_running >= sched_nr_latency; update_curr(cfs_rq); @@ -1582,18 +1609,7 @@ static void check_preempt_wakeup(struct rq *rq, struct task_struct *p, int wake_ if (unlikely(se == pse)) return; - /* - * Only set the backward buddy when the current task is still on the - * rq. This can happen when a wakeup gets interleaved with schedule on - * the ->pre_schedule() or idle_balance() point, either of which can - * drop the rq lock. - * - * Also, during early boot the idle thread is in the fair class, for - * obvious reasons its a bad idea to schedule back to the idle thread. - */ - if (sched_feat(LAST_BUDDY) && likely(se->on_rq && curr != rq->idle)) - set_last_buddy(se); - if (sched_feat(NEXT_BUDDY) && !(wake_flags & WF_FORK)) + if (sched_feat(NEXT_BUDDY) && scale && !(wake_flags & WF_FORK)) set_next_buddy(pse); /* @@ -1639,8 +1655,22 @@ static void check_preempt_wakeup(struct rq *rq, struct task_struct *p, int wake_ BUG_ON(!pse); - if (wakeup_preempt_entity(se, pse) == 1) + if (wakeup_preempt_entity(se, pse) == 1) { resched_task(curr); + /* + * Only set the backward buddy when the current task is still + * on the rq. This can happen when a wakeup gets interleaved + * with schedule on the ->pre_schedule() or idle_balance() + * point, either of which can * drop the rq lock. + * + * Also, during early boot the idle thread is in the fair class, + * for obvious reasons its a bad idea to schedule back to it. + */ + if (unlikely(!se->on_rq || curr == rq->idle)) + return; + if (sched_feat(LAST_BUDDY) && scale && entity_is_task(se)) + set_last_buddy(se); + } } static struct task_struct *pick_next_task_fair(struct rq *rq) @@ -1654,16 +1684,6 @@ static struct task_struct *pick_next_task_fair(struct rq *rq) do { se = pick_next_entity(cfs_rq); - /* - * If se was a buddy, clear it so that it will have to earn - * the favour again. - * - * If se was not a buddy, clear the buddies because neither - * was elegible to run, let them earn it again. - * - * IOW. unconditionally clear buddies. - */ - __clear_buddies(cfs_rq, NULL); set_next_entity(cfs_rq, se); cfs_rq = group_cfs_rq(se); } while (cfs_rq); diff --git a/kernel/sys.c b/kernel/sys.c index 255475d163e0..ce17760d9c51 100644 --- a/kernel/sys.c +++ b/kernel/sys.c @@ -1110,6 +1110,8 @@ SYSCALL_DEFINE0(setsid) err = session; out: write_unlock_irq(&tasklist_lock); + if (err > 0) + proc_sid_connector(group_leader); return err; } @@ -1546,24 +1548,37 @@ SYSCALL_DEFINE5(prctl, int, option, unsigned long, arg2, unsigned long, arg3, if (arg4 | arg5) return -EINVAL; switch (arg2) { - case 0: + case PR_MCE_KILL_CLEAR: if (arg3 != 0) return -EINVAL; current->flags &= ~PF_MCE_PROCESS; break; - case 1: + case PR_MCE_KILL_SET: current->flags |= PF_MCE_PROCESS; - if (arg3 != 0) + if (arg3 == PR_MCE_KILL_EARLY) current->flags |= PF_MCE_EARLY; - else + else if (arg3 == PR_MCE_KILL_LATE) current->flags &= ~PF_MCE_EARLY; + else if (arg3 == PR_MCE_KILL_DEFAULT) + current->flags &= + ~(PF_MCE_EARLY|PF_MCE_PROCESS); + else + return -EINVAL; break; default: return -EINVAL; } error = 0; break; - + case PR_MCE_KILL_GET: + if (arg2 | arg3 | arg4 | arg5) + return -EINVAL; + if (current->flags & PF_MCE_PROCESS) + error = (current->flags & PF_MCE_EARLY) ? + PR_MCE_KILL_EARLY : PR_MCE_KILL_LATE; + else + error = PR_MCE_KILL_DEFAULT; + break; default: error = -EINVAL; break; diff --git a/kernel/sysctl_check.c b/kernel/sysctl_check.c index b38423ca711a..b6e7aaea4604 100644 --- a/kernel/sysctl_check.c +++ b/kernel/sysctl_check.c @@ -1521,7 +1521,7 @@ int sysctl_check_table(struct nsproxy *namespaces, struct ctl_table *table) if (!table->ctl_name && table->strategy) set_fail(&fail, table, "Strategy without ctl_name"); #endif -#ifdef CONFIG_PROC_FS +#ifdef CONFIG_PROC_SYSCTL if (table->procname && !table->proc_handler) set_fail(&fail, table, "No proc_handler"); #endif diff --git a/kernel/time/tick-sched.c b/kernel/time/tick-sched.c index e0f59a21c061..89aed5933ed4 100644 --- a/kernel/time/tick-sched.c +++ b/kernel/time/tick-sched.c @@ -231,6 +231,13 @@ void tick_nohz_stop_sched_tick(int inidle) if (!inidle && !ts->inidle) goto end; + /* + * Set ts->inidle unconditionally. Even if the system did not + * switch to NOHZ mode the cpu frequency governers rely on the + * update of the idle time accounting in tick_nohz_start_idle(). + */ + ts->inidle = 1; + now = tick_nohz_start_idle(ts); /* @@ -248,8 +255,6 @@ void tick_nohz_stop_sched_tick(int inidle) if (unlikely(ts->nohz_mode == NOHZ_MODE_INACTIVE)) goto end; - ts->inidle = 1; - if (need_resched()) goto end; diff --git a/kernel/time/timekeeping.c b/kernel/time/timekeeping.c index fb0f46fa1ecd..c3a4e2907eaa 100644 --- a/kernel/time/timekeeping.c +++ b/kernel/time/timekeeping.c @@ -13,6 +13,7 @@ #include <linux/percpu.h> #include <linux/init.h> #include <linux/mm.h> +#include <linux/sched.h> #include <linux/sysdev.h> #include <linux/clocksource.h> #include <linux/jiffies.h> diff --git a/kernel/trace/ftrace.c b/kernel/trace/ftrace.c index 46592feab5a6..6dc4e5ef7a01 100644 --- a/kernel/trace/ftrace.c +++ b/kernel/trace/ftrace.c @@ -225,7 +225,11 @@ static void ftrace_update_pid_func(void) if (ftrace_trace_function == ftrace_stub) return; +#ifdef CONFIG_HAVE_FUNCTION_TRACE_MCOUNT_TEST func = ftrace_trace_function; +#else + func = __ftrace_trace_function; +#endif if (ftrace_pid_trace) { set_ftrace_pid_function(func); @@ -736,7 +740,7 @@ ftrace_profile_write(struct file *filp, const char __user *ubuf, out: mutex_unlock(&ftrace_profile_lock); - filp->f_pos += cnt; + *ppos += cnt; return cnt; } @@ -1074,14 +1078,9 @@ static void ftrace_replace_code(int enable) failed = __ftrace_replace_code(rec, enable); if (failed) { rec->flags |= FTRACE_FL_FAILED; - if ((system_state == SYSTEM_BOOTING) || - !core_kernel_text(rec->ip)) { - ftrace_free_rec(rec); - } else { - ftrace_bug(failed, rec->ip); - /* Stop processing */ - return; - } + ftrace_bug(failed, rec->ip); + /* Stop processing */ + return; } } while_for_each_ftrace_rec(); } @@ -2223,15 +2222,15 @@ ftrace_regex_write(struct file *file, const char __user *ubuf, ret = ftrace_process_regex(parser->buffer, parser->idx, enable); if (ret) - goto out; + goto out_unlock; trace_parser_clear(parser); } ret = read; - +out_unlock: mutex_unlock(&ftrace_regex_lock); -out: + return ret; } @@ -2658,19 +2657,17 @@ static int ftrace_convert_nops(struct module *mod, } #ifdef CONFIG_MODULES -void ftrace_release(void *start, void *end) +void ftrace_release_mod(struct module *mod) { struct dyn_ftrace *rec; struct ftrace_page *pg; - unsigned long s = (unsigned long)start; - unsigned long e = (unsigned long)end; - if (ftrace_disabled || !start || start == end) + if (ftrace_disabled) return; mutex_lock(&ftrace_lock); do_for_each_ftrace_rec(pg, rec) { - if ((rec->ip >= s) && (rec->ip < e)) { + if (within_module_core(rec->ip, mod)) { /* * rec->ip is changed in ftrace_free_rec() * It should not between s and e if record was freed. @@ -2702,9 +2699,7 @@ static int ftrace_module_notify(struct notifier_block *self, mod->num_ftrace_callsites); break; case MODULE_STATE_GOING: - ftrace_release(mod->ftrace_callsites, - mod->ftrace_callsites + - mod->num_ftrace_callsites); + ftrace_release_mod(mod); break; } diff --git a/kernel/trace/kmemtrace.c b/kernel/trace/kmemtrace.c index 81b1645c8549..a91da69f153a 100644 --- a/kernel/trace/kmemtrace.c +++ b/kernel/trace/kmemtrace.c @@ -501,7 +501,7 @@ static int __init init_kmem_tracer(void) return 1; } - if (!register_tracer(&kmem_tracer)) { + if (register_tracer(&kmem_tracer) != 0) { pr_warning("Warning: could not register the kmem tracer\n"); return 1; } diff --git a/kernel/trace/ring_buffer.c b/kernel/trace/ring_buffer.c index d4ff01970547..5dd017fea6f5 100644 --- a/kernel/trace/ring_buffer.c +++ b/kernel/trace/ring_buffer.c @@ -483,7 +483,7 @@ struct ring_buffer_iter { /* Up this if you want to test the TIME_EXTENTS and normalization */ #define DEBUG_SHIFT 0 -static inline u64 rb_time_stamp(struct ring_buffer *buffer, int cpu) +static inline u64 rb_time_stamp(struct ring_buffer *buffer) { /* shift to debug/test normalization and TIME_EXTENTS */ return buffer->clock() << DEBUG_SHIFT; @@ -494,7 +494,7 @@ u64 ring_buffer_time_stamp(struct ring_buffer *buffer, int cpu) u64 time; preempt_disable_notrace(); - time = rb_time_stamp(buffer, cpu); + time = rb_time_stamp(buffer); preempt_enable_no_resched_notrace(); return time; @@ -599,7 +599,7 @@ static struct list_head *rb_list_head(struct list_head *list) } /* - * rb_is_head_page - test if the give page is the head page + * rb_is_head_page - test if the given page is the head page * * Because the reader may move the head_page pointer, we can * not trust what the head page is (it may be pointing to @@ -1193,6 +1193,7 @@ rb_remove_pages(struct ring_buffer_per_cpu *cpu_buffer, unsigned nr_pages) atomic_inc(&cpu_buffer->record_disabled); synchronize_sched(); + spin_lock_irq(&cpu_buffer->reader_lock); rb_head_page_deactivate(cpu_buffer); for (i = 0; i < nr_pages; i++) { @@ -1207,6 +1208,7 @@ rb_remove_pages(struct ring_buffer_per_cpu *cpu_buffer, unsigned nr_pages) return; rb_reset_cpu(cpu_buffer); + spin_unlock_irq(&cpu_buffer->reader_lock); rb_check_pages(cpu_buffer); @@ -1868,7 +1870,7 @@ rb_move_tail(struct ring_buffer_per_cpu *cpu_buffer, * Nested commits always have zero deltas, so * just reread the time stamp */ - *ts = rb_time_stamp(buffer, cpu_buffer->cpu); + *ts = rb_time_stamp(buffer); next_page->page->time_stamp = *ts; } @@ -2111,7 +2113,7 @@ rb_reserve_next_event(struct ring_buffer *buffer, if (RB_WARN_ON(cpu_buffer, ++nr_loops > 1000)) goto out_fail; - ts = rb_time_stamp(cpu_buffer->buffer, cpu_buffer->cpu); + ts = rb_time_stamp(cpu_buffer->buffer); /* * Only the first commit can update the timestamp. @@ -2681,7 +2683,7 @@ unsigned long ring_buffer_entries(struct ring_buffer *buffer) EXPORT_SYMBOL_GPL(ring_buffer_entries); /** - * ring_buffer_overrun_cpu - get the number of overruns in buffer + * ring_buffer_overruns - get the number of overruns in buffer * @buffer: The ring buffer * * Returns the total number of overruns in the ring buffer diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c index 45068269ebb1..b20d3ec75de9 100644 --- a/kernel/trace/trace.c +++ b/kernel/trace/trace.c @@ -1393,7 +1393,7 @@ int trace_array_vprintk(struct trace_array *tr, int trace_vprintk(unsigned long ip, const char *fmt, va_list args) { - return trace_array_printk(&global_trace, ip, fmt, args); + return trace_array_vprintk(&global_trace, ip, fmt, args); } EXPORT_SYMBOL_GPL(trace_vprintk); @@ -2440,7 +2440,7 @@ tracing_trace_options_write(struct file *filp, const char __user *ubuf, return ret; } - filp->f_pos += cnt; + *ppos += cnt; return cnt; } @@ -2582,7 +2582,7 @@ tracing_ctrl_write(struct file *filp, const char __user *ubuf, } mutex_unlock(&trace_types_lock); - filp->f_pos += cnt; + *ppos += cnt; return cnt; } @@ -2764,7 +2764,7 @@ tracing_set_trace_write(struct file *filp, const char __user *ubuf, if (err) return err; - filp->f_pos += ret; + *ppos += ret; return ret; } @@ -3299,7 +3299,7 @@ tracing_entries_write(struct file *filp, const char __user *ubuf, } } - filp->f_pos += cnt; + *ppos += cnt; /* If check pages failed, return ENOMEM */ if (tracing_disabled) diff --git a/kernel/trace/trace_branch.c b/kernel/trace/trace_branch.c index 7a7a9fd249a9..4a194f08f88c 100644 --- a/kernel/trace/trace_branch.c +++ b/kernel/trace/trace_branch.c @@ -34,6 +34,7 @@ probe_likely_condition(struct ftrace_branch_data *f, int val, int expect) struct trace_array *tr = branch_tracer; struct ring_buffer_event *event; struct trace_branch *entry; + struct ring_buffer *buffer; unsigned long flags; int cpu, pc; const char *p; @@ -54,7 +55,8 @@ probe_likely_condition(struct ftrace_branch_data *f, int val, int expect) goto out; pc = preempt_count(); - event = trace_buffer_lock_reserve(tr, TRACE_BRANCH, + buffer = tr->buffer; + event = trace_buffer_lock_reserve(buffer, TRACE_BRANCH, sizeof(*entry), flags, pc); if (!event) goto out; @@ -74,8 +76,8 @@ probe_likely_condition(struct ftrace_branch_data *f, int val, int expect) entry->line = f->line; entry->correct = val == expect; - if (!filter_check_discard(call, entry, tr->buffer, event)) - ring_buffer_unlock_commit(tr->buffer, event); + if (!filter_check_discard(call, entry, buffer, event)) + ring_buffer_unlock_commit(buffer, event); out: atomic_dec(&tr->data[cpu]->disabled); diff --git a/kernel/trace/trace_event_profile.c b/kernel/trace/trace_event_profile.c index dd44b8768867..8d5c171cc998 100644 --- a/kernel/trace/trace_event_profile.c +++ b/kernel/trace/trace_event_profile.c @@ -31,7 +31,7 @@ static int ftrace_profile_enable_event(struct ftrace_event_call *event) if (atomic_inc_return(&event->profile_count)) return 0; - if (!total_profile_count++) { + if (!total_profile_count) { buf = (char *)alloc_percpu(profile_buf_t); if (!buf) goto fail_buf; @@ -46,14 +46,19 @@ static int ftrace_profile_enable_event(struct ftrace_event_call *event) } ret = event->profile_enable(); - if (!ret) + if (!ret) { + total_profile_count++; return 0; + } - kfree(trace_profile_buf_nmi); fail_buf_nmi: - kfree(trace_profile_buf); + if (!total_profile_count) { + free_percpu(trace_profile_buf_nmi); + free_percpu(trace_profile_buf); + trace_profile_buf_nmi = NULL; + trace_profile_buf = NULL; + } fail_buf: - total_profile_count--; atomic_dec(&event->profile_count); return ret; diff --git a/kernel/trace/trace_events_filter.c b/kernel/trace/trace_events_filter.c index 23245785927f..98a6cc5c64ed 100644 --- a/kernel/trace/trace_events_filter.c +++ b/kernel/trace/trace_events_filter.c @@ -933,8 +933,9 @@ static void postfix_clear(struct filter_parse_state *ps) while (!list_empty(&ps->postfix)) { elt = list_first_entry(&ps->postfix, struct postfix_elt, list); - kfree(elt->operand); list_del(&elt->list); + kfree(elt->operand); + kfree(elt); } } diff --git a/kernel/trace/trace_hw_branches.c b/kernel/trace/trace_hw_branches.c index 23b63859130e..69543a905cd5 100644 --- a/kernel/trace/trace_hw_branches.c +++ b/kernel/trace/trace_hw_branches.c @@ -165,6 +165,7 @@ void trace_hw_branch(u64 from, u64 to) struct ftrace_event_call *call = &event_hw_branch; struct trace_array *tr = hw_branch_trace; struct ring_buffer_event *event; + struct ring_buffer *buf; struct hw_branch_entry *entry; unsigned long irq1; int cpu; @@ -180,7 +181,8 @@ void trace_hw_branch(u64 from, u64 to) if (atomic_inc_return(&tr->data[cpu]->disabled) != 1) goto out; - event = trace_buffer_lock_reserve(tr, TRACE_HW_BRANCHES, + buf = tr->buffer; + event = trace_buffer_lock_reserve(buf, TRACE_HW_BRANCHES, sizeof(*entry), 0, 0); if (!event) goto out; @@ -189,8 +191,8 @@ void trace_hw_branch(u64 from, u64 to) entry->ent.type = TRACE_HW_BRANCHES; entry->from = from; entry->to = to; - if (!filter_check_discard(call, entry, tr->buffer, event)) - trace_buffer_unlock_commit(tr, event, 0, 0); + if (!filter_check_discard(call, entry, buf, event)) + trace_buffer_unlock_commit(buf, event, 0, 0); out: atomic_dec(&tr->data[cpu]->disabled); diff --git a/kernel/trace/trace_output.c b/kernel/trace/trace_output.c index f572f44c6e1e..b6c12c6a1bcd 100644 --- a/kernel/trace/trace_output.c +++ b/kernel/trace/trace_output.c @@ -69,6 +69,9 @@ enum print_line_t trace_print_printk_msg_only(struct trace_iterator *iter) * @s: trace sequence descriptor * @fmt: printf format string * + * It returns 0 if the trace oversizes the buffer's free + * space, 1 otherwise. + * * The tracer may use either sequence operations or its own * copy to user routines. To simplify formating of a trace * trace_seq_printf is used to store strings into a special @@ -95,7 +98,7 @@ trace_seq_printf(struct trace_seq *s, const char *fmt, ...) s->len += ret; - return len; + return 1; } EXPORT_SYMBOL_GPL(trace_seq_printf); @@ -486,16 +489,18 @@ int trace_print_lat_fmt(struct trace_seq *s, struct trace_entry *entry) hardirq ? 'h' : softirq ? 's' : '.')) return 0; - if (entry->lock_depth < 0) - ret = trace_seq_putc(s, '.'); + if (entry->preempt_count) + ret = trace_seq_printf(s, "%x", entry->preempt_count); else - ret = trace_seq_printf(s, "%d", entry->lock_depth); + ret = trace_seq_putc(s, '.'); + if (!ret) return 0; - if (entry->preempt_count) - return trace_seq_printf(s, "%x", entry->preempt_count); - return trace_seq_putc(s, '.'); + if (entry->lock_depth < 0) + return trace_seq_putc(s, '.'); + + return trace_seq_printf(s, "%d", entry->lock_depth); } static int @@ -883,7 +888,7 @@ static int trace_ctxwake_raw(struct trace_iterator *iter, char S) trace_assign_type(field, iter->ent); if (!S) - task_state_char(field->prev_state); + S = task_state_char(field->prev_state); T = task_state_char(field->next_state); if (!trace_seq_printf(&iter->seq, "%d %d %c %d %d %d %c\n", field->prev_pid, @@ -918,7 +923,7 @@ static int trace_ctxwake_hex(struct trace_iterator *iter, char S) trace_assign_type(field, iter->ent); if (!S) - task_state_char(field->prev_state); + S = task_state_char(field->prev_state); T = task_state_char(field->next_state); SEQ_PUT_HEX_FIELD_RET(s, field->prev_pid); diff --git a/kernel/trace/trace_syscalls.c b/kernel/trace/trace_syscalls.c index 9fbce6c9d2e1..527e17eae575 100644 --- a/kernel/trace/trace_syscalls.c +++ b/kernel/trace/trace_syscalls.c @@ -166,7 +166,7 @@ int syscall_exit_format(struct ftrace_event_call *call, struct trace_seq *s) "\tfield:%s %s;\toffset:%zu;\tsize:%zu;\n" "\tfield:%s %s;\toffset:%zu;\tsize:%zu;\n", SYSCALL_FIELD(int, nr), - SYSCALL_FIELD(unsigned long, ret)); + SYSCALL_FIELD(long, ret)); if (!ret) return 0; @@ -212,7 +212,7 @@ int syscall_exit_define_fields(struct ftrace_event_call *call) if (ret) return ret; - ret = trace_define_field(call, SYSCALL_FIELD(unsigned long, ret), 0, + ret = trace_define_field(call, SYSCALL_FIELD(long, ret), 0, FILTER_OTHER); return ret; diff --git a/kernel/user.c b/kernel/user.c index 2c000e7132ac..46d0165ca70c 100644 --- a/kernel/user.c +++ b/kernel/user.c @@ -330,9 +330,9 @@ done: */ static void free_user(struct user_struct *up, unsigned long flags) { - spin_unlock_irqrestore(&uidhash_lock, flags); INIT_DELAYED_WORK(&up->work, cleanup_user_struct); schedule_delayed_work(&up->work, msecs_to_jiffies(1000)); + spin_unlock_irqrestore(&uidhash_lock, flags); } #else /* CONFIG_USER_SCHED && CONFIG_SYSFS */ diff --git a/kernel/workqueue.c b/kernel/workqueue.c index addfe2df93b1..67e526b6ae81 100644 --- a/kernel/workqueue.c +++ b/kernel/workqueue.c @@ -640,6 +640,24 @@ int schedule_delayed_work(struct delayed_work *dwork, EXPORT_SYMBOL(schedule_delayed_work); /** + * flush_delayed_work - block until a dwork_struct's callback has terminated + * @dwork: the delayed work which is to be flushed + * + * Any timeout is cancelled, and any pending work is run immediately. + */ +void flush_delayed_work(struct delayed_work *dwork) +{ + if (del_timer_sync(&dwork->timer)) { + struct cpu_workqueue_struct *cwq; + cwq = wq_per_cpu(keventd_wq, get_cpu()); + __queue_work(cwq, &dwork->work); + put_cpu(); + } + flush_work(&dwork->work); +} +EXPORT_SYMBOL(flush_delayed_work); + +/** * schedule_delayed_work_on - queue work in global workqueue on CPU after delay * @cpu: cpu to use * @dwork: job to be done @@ -667,6 +685,7 @@ EXPORT_SYMBOL(schedule_delayed_work_on); int schedule_on_each_cpu(work_func_t func) { int cpu; + int orig = -1; struct work_struct *works; works = alloc_percpu(struct work_struct); @@ -674,14 +693,28 @@ int schedule_on_each_cpu(work_func_t func) return -ENOMEM; get_online_cpus(); + + /* + * When running in keventd don't schedule a work item on + * itself. Can just call directly because the work queue is + * already bound. This also is faster. + */ + if (current_is_keventd()) + orig = raw_smp_processor_id(); + for_each_online_cpu(cpu) { struct work_struct *work = per_cpu_ptr(works, cpu); INIT_WORK(work, func); - schedule_work_on(cpu, work); + if (cpu != orig) + schedule_work_on(cpu, work); } + if (orig >= 0) + func(per_cpu_ptr(works, orig)); + for_each_online_cpu(cpu) flush_work(per_cpu_ptr(works, cpu)); + put_online_cpus(); free_percpu(works); return 0; diff --git a/lib/Kconfig.debug b/lib/Kconfig.debug index 891155817bc6..234ceb10861f 100644 --- a/lib/Kconfig.debug +++ b/lib/Kconfig.debug @@ -346,8 +346,9 @@ config SLUB_STATS config DEBUG_KMEMLEAK bool "Kernel memory leak detector" - depends on DEBUG_KERNEL && EXPERIMENTAL && (X86 || ARM || PPC) && \ - !MEMORY_HOTPLUG + depends on DEBUG_KERNEL && EXPERIMENTAL && !MEMORY_HOTPLUG && \ + (X86 || ARM || PPC || S390) + select DEBUG_FS if SYSFS select STACKTRACE if STACKTRACE_SUPPORT select KALLSYMS @@ -370,7 +371,7 @@ config DEBUG_KMEMLEAK config DEBUG_KMEMLEAK_EARLY_LOG_SIZE int "Maximum kmemleak early log entries" depends on DEBUG_KMEMLEAK - range 200 2000 + range 200 40000 default 400 help Kmemleak must track all the memory allocations to avoid @@ -391,7 +392,7 @@ config DEBUG_KMEMLEAK_TEST config DEBUG_PREEMPT bool "Debug preemptible kernel" - depends on DEBUG_KERNEL && PREEMPT && (TRACE_IRQFLAGS_SUPPORT || PPC64) + depends on DEBUG_KERNEL && PREEMPT && TRACE_IRQFLAGS_SUPPORT default y help If you say Y here then the kernel will use a debug variant of the diff --git a/lib/debugobjects.c b/lib/debugobjects.c index 2755a3bd16a1..eae56fddfa3b 100644 --- a/lib/debugobjects.c +++ b/lib/debugobjects.c @@ -9,6 +9,7 @@ */ #include <linux/debugobjects.h> #include <linux/interrupt.h> +#include <linux/sched.h> #include <linux/seq_file.h> #include <linux/debugfs.h> #include <linux/hash.h> diff --git a/lib/dma-debug.c b/lib/dma-debug.c index 58a9f9fc609a..ce6b7eabf674 100644 --- a/lib/dma-debug.c +++ b/lib/dma-debug.c @@ -819,9 +819,11 @@ static void check_unmap(struct dma_debug_entry *ref) err_printk(ref->dev, entry, "DMA-API: device driver frees " "DMA memory with different CPU address " "[device address=0x%016llx] [size=%llu bytes] " - "[cpu alloc address=%p] [cpu free address=%p]", + "[cpu alloc address=0x%016llx] " + "[cpu free address=0x%016llx]", ref->dev_addr, ref->size, - (void *)entry->paddr, (void *)ref->paddr); + (unsigned long long)entry->paddr, + (unsigned long long)ref->paddr); } if (ref->sg_call_ents && ref->type == dma_debug_sg && diff --git a/lib/fault-inject.c b/lib/fault-inject.c index f97af55bdd96..7e65af70635e 100644 --- a/lib/fault-inject.c +++ b/lib/fault-inject.c @@ -1,6 +1,7 @@ #include <linux/kernel.h> #include <linux/init.h> #include <linux/random.h> +#include <linux/sched.h> #include <linux/stat.h> #include <linux/types.h> #include <linux/fs.h> diff --git a/lib/string.c b/lib/string.c index b19b87af65a3..e96421ab9a9a 100644 --- a/lib/string.c +++ b/lib/string.c @@ -246,13 +246,17 @@ EXPORT_SYMBOL(strlcat); #undef strcmp int strcmp(const char *cs, const char *ct) { - signed char __res; + unsigned char c1, c2; while (1) { - if ((__res = *cs - *ct++) != 0 || !*cs++) + c1 = *cs++; + c2 = *ct++; + if (c1 != c2) + return c1 < c2 ? -1 : 1; + if (!c1) break; } - return __res; + return 0; } EXPORT_SYMBOL(strcmp); #endif @@ -266,14 +270,18 @@ EXPORT_SYMBOL(strcmp); */ int strncmp(const char *cs, const char *ct, size_t count) { - signed char __res = 0; + unsigned char c1, c2; while (count) { - if ((__res = *cs - *ct++) != 0 || !*cs++) + c1 = *cs++; + c2 = *ct++; + if (c1 != c2) + return c1 < c2 ? -1 : 1; + if (!c1) break; count--; } - return __res; + return 0; } EXPORT_SYMBOL(strncmp); #endif diff --git a/mm/Kconfig b/mm/Kconfig index edd300aca173..44cf6f0a3a6d 100644 --- a/mm/Kconfig +++ b/mm/Kconfig @@ -67,7 +67,7 @@ config DISCONTIGMEM config SPARSEMEM def_bool y - depends on SPARSEMEM_MANUAL + depends on (!SELECT_MEMORY_MODEL && ARCH_SPARSEMEM_ENABLE) || SPARSEMEM_MANUAL config FLATMEM def_bool y @@ -128,11 +128,8 @@ config SPARSEMEM_VMEMMAP config MEMORY_HOTPLUG bool "Allow for memory hot-add" depends on SPARSEMEM || X86_64_ACPI_NUMA - depends on HOTPLUG && !(HIBERNATION && !S390) && ARCH_ENABLE_MEMORY_HOTPLUG - depends on (IA64 || X86 || PPC64 || SUPERH || S390) - -comment "Memory hotplug is currently incompatible with Software Suspend" - depends on SPARSEMEM && HOTPLUG && HIBERNATION && !S390 + depends on HOTPLUG && ARCH_ENABLE_MEMORY_HOTPLUG + depends on (IA64 || X86 || PPC_BOOK3S_64 || SUPERH || S390) config MEMORY_HOTPLUG_SPARSE def_bool y @@ -224,7 +221,9 @@ config KSM the many instances by a single resident page with that content, so saving memory until one or another app needs to modify the content. Recommended for use with KVM, or with other duplicative applications. - See Documentation/vm/ksm.txt for more information. + See Documentation/vm/ksm.txt for more information: KSM is inactive + until a program has madvised that an area is MADV_MERGEABLE, and + root has set /sys/kernel/mm/ksm/run to 1 (if CONFIG_SYSFS is set). config DEFAULT_MMAP_MIN_ADDR int "Low address space to protect from user allocation" diff --git a/mm/backing-dev.c b/mm/backing-dev.c index 3d3accb1f800..11aee09dd2a6 100644 --- a/mm/backing-dev.c +++ b/mm/backing-dev.c @@ -92,7 +92,7 @@ static int bdi_debug_stats_show(struct seq_file *m, void *v) "BdiDirtyThresh: %8lu kB\n" "DirtyThresh: %8lu kB\n" "BackgroundThresh: %8lu kB\n" - "WriteBack threads:%8lu\n" + "WritebackThreads: %8lu\n" "b_dirty: %8lu\n" "b_io: %8lu\n" "b_more_io: %8lu\n" @@ -610,9 +610,26 @@ static void bdi_wb_shutdown(struct backing_dev_info *bdi) kthread_stop(wb->task); } +/* + * This bdi is going away now, make sure that no super_blocks point to it + */ +static void bdi_prune_sb(struct backing_dev_info *bdi) +{ + struct super_block *sb; + + spin_lock(&sb_lock); + list_for_each_entry(sb, &super_blocks, s_list) { + if (sb->s_bdi == bdi) + sb->s_bdi = NULL; + } + spin_unlock(&sb_lock); +} + void bdi_unregister(struct backing_dev_info *bdi) { if (bdi->dev) { + bdi_prune_sb(bdi); + if (!bdi_cap_flush_forker(bdi)) bdi_wb_shutdown(bdi); bdi_debug_unregister(bdi); diff --git a/mm/highmem.c b/mm/highmem.c index 25878cc49daa..9c1e627f282e 100644 --- a/mm/highmem.c +++ b/mm/highmem.c @@ -426,16 +426,21 @@ void __init page_address_init(void) void debug_kmap_atomic(enum km_type type) { - static unsigned warn_count = 10; + static int warn_count = 10; - if (unlikely(warn_count == 0)) + if (unlikely(warn_count < 0)) return; if (unlikely(in_interrupt())) { - if (in_irq()) { + if (in_nmi()) { + if (type != KM_NMI && type != KM_NMI_PTE) { + WARN_ON(1); + warn_count--; + } + } else if (in_irq()) { if (type != KM_IRQ0 && type != KM_IRQ1 && type != KM_BIO_SRC_IRQ && type != KM_BIO_DST_IRQ && - type != KM_BOUNCE_READ) { + type != KM_BOUNCE_READ && type != KM_IRQ_PTE) { WARN_ON(1); warn_count--; } @@ -452,7 +457,9 @@ void debug_kmap_atomic(enum km_type type) } if (type == KM_IRQ0 || type == KM_IRQ1 || type == KM_BOUNCE_READ || - type == KM_BIO_SRC_IRQ || type == KM_BIO_DST_IRQ) { + type == KM_BIO_SRC_IRQ || type == KM_BIO_DST_IRQ || + type == KM_IRQ_PTE || type == KM_NMI || + type == KM_NMI_PTE ) { if (!irqs_disabled()) { WARN_ON(1); warn_count--; diff --git a/mm/kmemleak.c b/mm/kmemleak.c index 4ea4510e2996..8bf765c4f58d 100644 --- a/mm/kmemleak.c +++ b/mm/kmemleak.c @@ -833,12 +833,15 @@ static void early_alloc(struct early_log *log) */ rcu_read_lock(); object = create_object((unsigned long)log->ptr, log->size, - log->min_count, GFP_KERNEL); + log->min_count, GFP_ATOMIC); + if (!object) + goto out; spin_lock_irqsave(&object->lock, flags); for (i = 0; i < log->trace_len; i++) object->trace[i] = log->trace[i]; object->trace_len = log->trace_len; spin_unlock_irqrestore(&object->lock, flags); +out: rcu_read_unlock(); } @@ -184,11 +184,6 @@ static DEFINE_SPINLOCK(ksm_mmlist_lock); sizeof(struct __struct), __alignof__(struct __struct),\ (__flags), NULL) -static void __init ksm_init_max_kernel_pages(void) -{ - ksm_max_kernel_pages = nr_free_buffer_pages() / 4; -} - static int __init ksm_slab_init(void) { rmap_item_cache = KSM_KMEM_CACHE(rmap_item, 0); @@ -1017,6 +1012,7 @@ static struct rmap_item *unstable_tree_search_insert(struct page *page, struct rmap_item *tree_rmap_item; int ret; + cond_resched(); tree_rmap_item = rb_entry(*new, struct rmap_item, node); page2[0] = get_mergeable_page(tree_rmap_item); if (!page2[0]) @@ -1673,7 +1669,7 @@ static int __init ksm_init(void) struct task_struct *ksm_thread; int err; - ksm_init_max_kernel_pages(); + ksm_max_kernel_pages = totalram_pages / 4; err = ksm_slab_init(); if (err) @@ -1697,6 +1693,9 @@ static int __init ksm_init(void) kthread_stop(ksm_thread); goto out_free2; } +#else + ksm_run = KSM_RUN_MERGE; /* no way for user to start it */ + #endif /* CONFIG_SYSFS */ return 0; diff --git a/mm/memory-failure.c b/mm/memory-failure.c index 729d4b15b645..dacc64183874 100644 --- a/mm/memory-failure.c +++ b/mm/memory-failure.c @@ -35,6 +35,7 @@ #include <linux/mm.h> #include <linux/page-flags.h> #include <linux/sched.h> +#include <linux/ksm.h> #include <linux/rmap.h> #include <linux/pagemap.h> #include <linux/swap.h> @@ -370,9 +371,6 @@ static int me_pagecache_clean(struct page *p, unsigned long pfn) int ret = FAILED; struct address_space *mapping; - if (!isolate_lru_page(p)) - page_cache_release(p); - /* * For anonymous pages we're done the only reference left * should be the one m_f() holds. @@ -498,30 +496,18 @@ static int me_pagecache_dirty(struct page *p, unsigned long pfn) */ static int me_swapcache_dirty(struct page *p, unsigned long pfn) { - int ret = FAILED; - ClearPageDirty(p); /* Trigger EIO in shmem: */ ClearPageUptodate(p); - if (!isolate_lru_page(p)) { - page_cache_release(p); - ret = DELAYED; - } - - return ret; + return DELAYED; } static int me_swapcache_clean(struct page *p, unsigned long pfn) { - int ret = FAILED; - - if (!isolate_lru_page(p)) { - page_cache_release(p); - ret = RECOVERED; - } delete_from_swap_cache(p); - return ret; + + return RECOVERED; } /* @@ -611,8 +597,6 @@ static struct page_state { { 0, 0, "unknown page state", me_unknown }, }; -#undef lru - static void action_result(unsigned long pfn, char *msg, int result) { struct page *page = NULL; @@ -629,13 +613,16 @@ static int page_action(struct page_state *ps, struct page *p, unsigned long pfn, int ref) { int result; + int count; result = ps->action(p, pfn); action_result(pfn, ps->msg, result); - if (page_count(p) != 1 + ref) + + count = page_count(p) - 1 - ref; + if (count != 0) printk(KERN_ERR "MCE %#lx: %s page still referenced by %d users\n", - pfn, ps->msg, page_count(p) - 1); + pfn, ps->msg, count); /* Could do more checks here if page looks ok */ /* @@ -661,12 +648,9 @@ static void hwpoison_user_mappings(struct page *p, unsigned long pfn, int i; int kill = 1; - if (PageReserved(p) || PageCompound(p) || PageSlab(p)) + if (PageReserved(p) || PageCompound(p) || PageSlab(p) || PageKsm(p)) return; - if (!PageLRU(p)) - lru_add_drain_all(); - /* * This check implies we don't kill processes if their pages * are in the swap cache early. Those are always late kills. @@ -738,6 +722,7 @@ static void hwpoison_user_mappings(struct page *p, unsigned long pfn, int __memory_failure(unsigned long pfn, int trapno, int ref) { + unsigned long lru_flag; struct page_state *ps; struct page *p; int res; @@ -775,6 +760,24 @@ int __memory_failure(unsigned long pfn, int trapno, int ref) } /* + * We ignore non-LRU pages for good reasons. + * - PG_locked is only well defined for LRU pages and a few others + * - to avoid races with __set_page_locked() + * - to avoid races with __SetPageSlab*() (and more non-atomic ops) + * The check (unnecessarily) ignores LRU pages being isolated and + * walked by the page reclaim code, however that's not a big loss. + */ + if (!PageLRU(p)) + lru_add_drain_all(); + lru_flag = p->flags & lru; + if (isolate_lru_page(p)) { + action_result(pfn, "non LRU", IGNORED); + put_page(p); + return -EBUSY; + } + page_cache_release(p); + + /* * Lock the page and wait for writeback to finish. * It's very difficult to mess with pages currently under IO * and in many cases impossible, so we just avoid it here. @@ -790,7 +793,7 @@ int __memory_failure(unsigned long pfn, int trapno, int ref) /* * Torn down by someone else? */ - if (PageLRU(p) && !PageSwapCache(p) && p->mapping == NULL) { + if ((lru_flag & lru) && !PageSwapCache(p) && p->mapping == NULL) { action_result(pfn, "already truncated LRU", IGNORED); res = 0; goto out; @@ -798,7 +801,7 @@ int __memory_failure(unsigned long pfn, int trapno, int ref) res = -EBUSY; for (ps = error_states;; ps++) { - if ((p->flags & ps->mask) == ps->res) { + if (((p->flags | lru_flag)& ps->mask) == ps->res) { res = page_action(ps, p, pfn, ref); break; } diff --git a/mm/memory.c b/mm/memory.c index 7e91b5f9f690..6ab19dd4a199 100644 --- a/mm/memory.c +++ b/mm/memory.c @@ -641,6 +641,7 @@ static int copy_pte_range(struct mm_struct *dst_mm, struct mm_struct *src_mm, pmd_t *dst_pmd, pmd_t *src_pmd, struct vm_area_struct *vma, unsigned long addr, unsigned long end) { + pte_t *orig_src_pte, *orig_dst_pte; pte_t *src_pte, *dst_pte; spinlock_t *src_ptl, *dst_ptl; int progress = 0; @@ -654,6 +655,8 @@ again: src_pte = pte_offset_map_nested(src_pmd, addr); src_ptl = pte_lockptr(src_mm, src_pmd); spin_lock_nested(src_ptl, SINGLE_DEPTH_NESTING); + orig_src_pte = src_pte; + orig_dst_pte = dst_pte; arch_enter_lazy_mmu_mode(); do { @@ -677,9 +680,9 @@ again: arch_leave_lazy_mmu_mode(); spin_unlock(src_ptl); - pte_unmap_nested(src_pte - 1); + pte_unmap_nested(orig_src_pte); add_mm_rss(dst_mm, rss[0], rss[1]); - pte_unmap_unlock(dst_pte - 1, dst_ptl); + pte_unmap_unlock(orig_dst_pte, dst_ptl); cond_resched(); if (addr != end) goto again; @@ -1820,10 +1823,10 @@ static int apply_to_pte_range(struct mm_struct *mm, pmd_t *pmd, token = pmd_pgtable(*pmd); do { - err = fn(pte, token, addr, data); + err = fn(pte++, token, addr, data); if (err) break; - } while (pte++, addr += PAGE_SIZE, addr != end); + } while (addr += PAGE_SIZE, addr != end); arch_leave_lazy_mmu_mode(); @@ -2539,7 +2542,7 @@ static int do_swap_page(struct mm_struct *mm, struct vm_area_struct *vma, } else if (PageHWPoison(page)) { ret = VM_FAULT_HWPOISON; delayacct_clear_flag(DELAYACCT_PF_SWAPIN); - goto out; + goto out_release; } lock_page(page); @@ -2611,6 +2614,7 @@ out_nomap: pte_unmap_unlock(page_table, ptl); out_page: unlock_page(page); +out_release: page_cache_release(page); return ret; } diff --git a/mm/memory_hotplug.c b/mm/memory_hotplug.c index 821dee596377..2047465cd27c 100644 --- a/mm/memory_hotplug.c +++ b/mm/memory_hotplug.c @@ -26,6 +26,7 @@ #include <linux/migrate.h> #include <linux/page-isolation.h> #include <linux/pfn.h> +#include <linux/suspend.h> #include <asm/tlbflush.h> @@ -447,7 +448,8 @@ int online_pages(unsigned long pfn, unsigned long nr_pages) } #endif /* CONFIG_MEMORY_HOTPLUG_SPARSE */ -static pg_data_t *hotadd_new_pgdat(int nid, u64 start) +/* we are OK calling __meminit stuff here - we have CONFIG_MEMORY_HOTPLUG */ +static pg_data_t __ref *hotadd_new_pgdat(int nid, u64 start) { struct pglist_data *pgdat; unsigned long zones_size[MAX_NR_ZONES] = {0}; @@ -484,14 +486,18 @@ int __ref add_memory(int nid, u64 start, u64 size) struct resource *res; int ret; + lock_system_sleep(); + res = register_memory_resource(start, size); + ret = -EEXIST; if (!res) - return -EEXIST; + goto out; if (!node_online(nid)) { pgdat = hotadd_new_pgdat(nid, start); + ret = -ENOMEM; if (!pgdat) - return -ENOMEM; + goto out; new_pgdat = 1; } @@ -514,7 +520,8 @@ int __ref add_memory(int nid, u64 start, u64 size) BUG_ON(ret); } - return ret; + goto out; + error: /* rollback pgdat allocation and others */ if (new_pgdat) @@ -522,6 +529,8 @@ error: if (res) release_memory_resource(res); +out: + unlock_system_sleep(); return ret; } EXPORT_SYMBOL_GPL(add_memory); @@ -758,6 +767,8 @@ int offline_pages(unsigned long start_pfn, if (!test_pages_in_a_zone(start_pfn, end_pfn)) return -EINVAL; + lock_system_sleep(); + zone = page_zone(pfn_to_page(start_pfn)); node = zone_to_nid(zone); nr_pages = end_pfn - start_pfn; @@ -765,7 +776,7 @@ int offline_pages(unsigned long start_pfn, /* set above range as isolated */ ret = start_isolate_page_range(start_pfn, end_pfn); if (ret) - return ret; + goto out; arg.start_pfn = start_pfn; arg.nr_pages = nr_pages; @@ -843,6 +854,7 @@ repeat: writeback_set_ratelimit(); memory_notify(MEM_OFFLINE, &arg); + unlock_system_sleep(); return 0; failed_removal: @@ -852,6 +864,8 @@ failed_removal: /* pushback to free area */ undo_isolate_page_range(start_pfn, end_pfn); +out: + unlock_system_sleep(); return ret; } diff --git a/mm/mempolicy.c b/mm/mempolicy.c index 7dd9d9f80694..4545d5944243 100644 --- a/mm/mempolicy.c +++ b/mm/mempolicy.c @@ -1024,7 +1024,7 @@ static long do_mbind(unsigned long start, unsigned long len, err = migrate_prep(); if (err) - return err; + goto mpol_out; } { NODEMASK_SCRATCH(scratch); @@ -1039,10 +1039,9 @@ static long do_mbind(unsigned long start, unsigned long len, err = -ENOMEM; NODEMASK_SCRATCH_FREE(scratch); } - if (err) { - mpol_put(new); - return err; - } + if (err) + goto mpol_out; + vma = check_range(mm, start, end, nmask, flags | MPOL_MF_INVERT, &pagelist); @@ -1058,9 +1057,11 @@ static long do_mbind(unsigned long start, unsigned long len, if (!err && nr_failed && (flags & MPOL_MF_STRICT)) err = -EIO; - } + } else + putback_lru_pages(&pagelist); up_write(&mm->mmap_sem); + mpol_out: mpol_put(new); return err; } diff --git a/mm/migrate.c b/mm/migrate.c index 1a4bf4813780..7dbcb22316d2 100644 --- a/mm/migrate.c +++ b/mm/migrate.c @@ -602,7 +602,7 @@ static int unmap_and_move(new_page_t get_new_page, unsigned long private, struct page *newpage = get_new_page(page, private, &result); int rcu_locked = 0; int charge = 0; - struct mem_cgroup *mem; + struct mem_cgroup *mem = NULL; if (!newpage) return -ENOMEM; diff --git a/mm/nommu.c b/mm/nommu.c index 5189b5aed8c0..9876fa0c3ad3 100644 --- a/mm/nommu.c +++ b/mm/nommu.c @@ -1362,9 +1362,11 @@ share: error_just_free: up_write(&nommu_region_sem); error: - fput(region->vm_file); + if (region->vm_file) + fput(region->vm_file); kmem_cache_free(vm_region_jar, region); - fput(vma->vm_file); + if (vma->vm_file) + fput(vma->vm_file); if (vma->vm_flags & VM_EXECUTABLE) removed_exe_file_vma(vma->vm_mm); kmem_cache_free(vm_area_cachep, vma); diff --git a/mm/page-writeback.c b/mm/page-writeback.c index a3b14090b1fb..2c5d79236ead 100644 --- a/mm/page-writeback.c +++ b/mm/page-writeback.c @@ -566,7 +566,8 @@ static void balance_dirty_pages(struct address_space *mapping, if (pages_written >= write_chunk) break; /* We've done our duty */ - schedule_timeout_interruptible(pause); + __set_current_state(TASK_INTERRUPTIBLE); + io_schedule_timeout(pause); /* * Increase the delay for each loop, up to our previous diff --git a/mm/page_alloc.c b/mm/page_alloc.c index bf720550b44d..2bc2ac63f41e 100644 --- a/mm/page_alloc.c +++ b/mm/page_alloc.c @@ -1769,7 +1769,7 @@ gfp_to_alloc_flags(gfp_t gfp_mask) * See also cpuset_zone_allowed() comment in kernel/cpuset.c. */ alloc_flags &= ~ALLOC_CPUSET; - } else if (unlikely(rt_task(p))) + } else if (unlikely(rt_task(p)) && !in_interrupt()) alloc_flags |= ALLOC_HARDER; if (likely(!(gfp_mask & __GFP_NOMEMALLOC))) { @@ -1817,9 +1817,9 @@ __alloc_pages_slowpath(gfp_t gfp_mask, unsigned int order, if (NUMA_BUILD && (gfp_mask & GFP_THISNODE) == GFP_THISNODE) goto nopage; +restart: wake_all_kswapd(order, zonelist, high_zoneidx); -restart: /* * OK, we're below the kswapd watermark and have kicked background * reclaim. Now things get more complex, so set up alloc_flags according @@ -2183,7 +2183,7 @@ void show_free_areas(void) printk("active_anon:%lu inactive_anon:%lu isolated_anon:%lu\n" " active_file:%lu inactive_file:%lu isolated_file:%lu\n" " unevictable:%lu" - " dirty:%lu writeback:%lu unstable:%lu buffer:%lu\n" + " dirty:%lu writeback:%lu unstable:%lu\n" " free:%lu slab_reclaimable:%lu slab_unreclaimable:%lu\n" " mapped:%lu shmem:%lu pagetables:%lu bounce:%lu\n", global_page_state(NR_ACTIVE_ANON), @@ -2196,7 +2196,6 @@ void show_free_areas(void) global_page_state(NR_FILE_DIRTY), global_page_state(NR_WRITEBACK), global_page_state(NR_UNSTABLE_NFS), - nr_blockdev_pages(), global_page_state(NR_FREE_PAGES), global_page_state(NR_SLAB_RECLAIMABLE), global_page_state(NR_SLAB_UNRECLAIMABLE), diff --git a/mm/percpu.c b/mm/percpu.c index 4a048abad043..5adfc268b408 100644 --- a/mm/percpu.c +++ b/mm/percpu.c @@ -153,7 +153,10 @@ static int pcpu_reserved_chunk_limit; * * During allocation, pcpu_alloc_mutex is kept locked all the time and * pcpu_lock is grabbed and released as necessary. All actual memory - * allocations are done using GFP_KERNEL with pcpu_lock released. + * allocations are done using GFP_KERNEL with pcpu_lock released. In + * general, percpu memory can't be allocated with irq off but + * irqsave/restore are still used in alloc path so that it can be used + * from early init path - sched_init() specifically. * * Free path accesses and alters only the index data structures, so it * can be safely called from atomic context. When memory needs to be @@ -352,62 +355,86 @@ static struct pcpu_chunk *pcpu_chunk_addr_search(void *addr) } /** - * pcpu_extend_area_map - extend area map for allocation - * @chunk: target chunk + * pcpu_need_to_extend - determine whether chunk area map needs to be extended + * @chunk: chunk of interest * - * Extend area map of @chunk so that it can accomodate an allocation. - * A single allocation can split an area into three areas, so this - * function makes sure that @chunk->map has at least two extra slots. + * Determine whether area map of @chunk needs to be extended to + * accomodate a new allocation. * * CONTEXT: - * pcpu_alloc_mutex, pcpu_lock. pcpu_lock is released and reacquired - * if area map is extended. + * pcpu_lock. * * RETURNS: - * 0 if noop, 1 if successfully extended, -errno on failure. + * New target map allocation length if extension is necessary, 0 + * otherwise. */ -static int pcpu_extend_area_map(struct pcpu_chunk *chunk) +static int pcpu_need_to_extend(struct pcpu_chunk *chunk) { int new_alloc; - int *new; - size_t size; - /* has enough? */ if (chunk->map_alloc >= chunk->map_used + 2) return 0; - spin_unlock_irq(&pcpu_lock); - new_alloc = PCPU_DFL_MAP_ALLOC; while (new_alloc < chunk->map_used + 2) new_alloc *= 2; - new = pcpu_mem_alloc(new_alloc * sizeof(new[0])); - if (!new) { - spin_lock_irq(&pcpu_lock); + return new_alloc; +} + +/** + * pcpu_extend_area_map - extend area map of a chunk + * @chunk: chunk of interest + * @new_alloc: new target allocation length of the area map + * + * Extend area map of @chunk to have @new_alloc entries. + * + * CONTEXT: + * Does GFP_KERNEL allocation. Grabs and releases pcpu_lock. + * + * RETURNS: + * 0 on success, -errno on failure. + */ +static int pcpu_extend_area_map(struct pcpu_chunk *chunk, int new_alloc) +{ + int *old = NULL, *new = NULL; + size_t old_size = 0, new_size = new_alloc * sizeof(new[0]); + unsigned long flags; + + new = pcpu_mem_alloc(new_size); + if (!new) return -ENOMEM; - } - /* - * Acquire pcpu_lock and switch to new area map. Only free - * could have happened inbetween, so map_used couldn't have - * grown. - */ - spin_lock_irq(&pcpu_lock); - BUG_ON(new_alloc < chunk->map_used + 2); + /* acquire pcpu_lock and switch to new area map */ + spin_lock_irqsave(&pcpu_lock, flags); + + if (new_alloc <= chunk->map_alloc) + goto out_unlock; - size = chunk->map_alloc * sizeof(chunk->map[0]); - memcpy(new, chunk->map, size); + old_size = chunk->map_alloc * sizeof(chunk->map[0]); + memcpy(new, chunk->map, old_size); /* * map_alloc < PCPU_DFL_MAP_ALLOC indicates that the chunk is * one of the first chunks and still using static map. */ if (chunk->map_alloc >= PCPU_DFL_MAP_ALLOC) - pcpu_mem_free(chunk->map, size); + old = chunk->map; chunk->map_alloc = new_alloc; chunk->map = new; + new = NULL; + +out_unlock: + spin_unlock_irqrestore(&pcpu_lock, flags); + + /* + * pcpu_mem_free() might end up calling vfree() which uses + * IRQ-unsafe lock and thus can't be called under pcpu_lock. + */ + pcpu_mem_free(old, old_size); + pcpu_mem_free(new, new_size); + return 0; } @@ -1046,7 +1073,8 @@ static void *pcpu_alloc(size_t size, size_t align, bool reserved) static int warn_limit = 10; struct pcpu_chunk *chunk; const char *err; - int slot, off; + int slot, off, new_alloc; + unsigned long flags; if (unlikely(!size || size > PCPU_MIN_UNIT_SIZE || align > PAGE_SIZE)) { WARN(true, "illegal size (%zu) or align (%zu) for " @@ -1055,19 +1083,30 @@ static void *pcpu_alloc(size_t size, size_t align, bool reserved) } mutex_lock(&pcpu_alloc_mutex); - spin_lock_irq(&pcpu_lock); + spin_lock_irqsave(&pcpu_lock, flags); /* serve reserved allocations from the reserved chunk if available */ if (reserved && pcpu_reserved_chunk) { chunk = pcpu_reserved_chunk; - if (size > chunk->contig_hint || - pcpu_extend_area_map(chunk) < 0) { - err = "failed to extend area map of reserved chunk"; + + if (size > chunk->contig_hint) { + err = "alloc from reserved chunk failed"; goto fail_unlock; } + + while ((new_alloc = pcpu_need_to_extend(chunk))) { + spin_unlock_irqrestore(&pcpu_lock, flags); + if (pcpu_extend_area_map(chunk, new_alloc) < 0) { + err = "failed to extend area map of reserved chunk"; + goto fail_unlock_mutex; + } + spin_lock_irqsave(&pcpu_lock, flags); + } + off = pcpu_alloc_area(chunk, size, align); if (off >= 0) goto area_found; + err = "alloc from reserved chunk failed"; goto fail_unlock; } @@ -1079,14 +1118,20 @@ restart: if (size > chunk->contig_hint) continue; - switch (pcpu_extend_area_map(chunk)) { - case 0: - break; - case 1: - goto restart; /* pcpu_lock dropped, restart */ - default: - err = "failed to extend area map"; - goto fail_unlock; + new_alloc = pcpu_need_to_extend(chunk); + if (new_alloc) { + spin_unlock_irqrestore(&pcpu_lock, flags); + if (pcpu_extend_area_map(chunk, + new_alloc) < 0) { + err = "failed to extend area map"; + goto fail_unlock_mutex; + } + spin_lock_irqsave(&pcpu_lock, flags); + /* + * pcpu_lock has been dropped, need to + * restart cpu_slot list walking. + */ + goto restart; } off = pcpu_alloc_area(chunk, size, align); @@ -1096,7 +1141,7 @@ restart: } /* hmmm... no space left, create a new chunk */ - spin_unlock_irq(&pcpu_lock); + spin_unlock_irqrestore(&pcpu_lock, flags); chunk = alloc_pcpu_chunk(); if (!chunk) { @@ -1104,16 +1149,16 @@ restart: goto fail_unlock_mutex; } - spin_lock_irq(&pcpu_lock); + spin_lock_irqsave(&pcpu_lock, flags); pcpu_chunk_relocate(chunk, -1); goto restart; area_found: - spin_unlock_irq(&pcpu_lock); + spin_unlock_irqrestore(&pcpu_lock, flags); /* populate, map and clear the area */ if (pcpu_populate_chunk(chunk, off, size)) { - spin_lock_irq(&pcpu_lock); + spin_lock_irqsave(&pcpu_lock, flags); pcpu_free_area(chunk, off); err = "failed to populate"; goto fail_unlock; @@ -1125,7 +1170,7 @@ area_found: return __addr_to_pcpu_ptr(chunk->base_addr + off); fail_unlock: - spin_unlock_irq(&pcpu_lock); + spin_unlock_irqrestore(&pcpu_lock, flags); fail_unlock_mutex: mutex_unlock(&pcpu_alloc_mutex); if (warn_limit) { @@ -1870,13 +1915,14 @@ int __init pcpu_embed_first_chunk(size_t reserved_size, ssize_t dyn_size, max_distance = 0; for (group = 0; group < ai->nr_groups; group++) { ai->groups[group].base_offset = areas[group] - base; - max_distance = max(max_distance, ai->groups[group].base_offset); + max_distance = max_t(size_t, max_distance, + ai->groups[group].base_offset); } max_distance += ai->unit_size; /* warn if maximum distance is further than 75% of vmalloc space */ if (max_distance > (VMALLOC_END - VMALLOC_START) * 3 / 4) { - pr_warning("PERCPU: max_distance=0x%lx too large for vmalloc " + pr_warning("PERCPU: max_distance=0x%zx too large for vmalloc " "space 0x%lx\n", max_distance, VMALLOC_END - VMALLOC_START); #ifdef CONFIG_NEED_PER_CPU_PAGE_FIRST_CHUNK diff --git a/mm/swapfile.c b/mm/swapfile.c index a1bc6b9af9a2..9c590eef7912 100644 --- a/mm/swapfile.c +++ b/mm/swapfile.c @@ -1151,8 +1151,7 @@ static int try_to_unuse(unsigned int type) } else retval = unuse_mm(mm, entry, page); - if (set_start_mm && - swap_count(*swap_map) < swcount) { + if (set_start_mm && *swap_map < swcount) { mmput(new_start_mm); atomic_inc(&mm->mm_users); new_start_mm = mm; diff --git a/mm/vmalloc.c b/mm/vmalloc.c index 69511e663234..0f551a4a44cd 100644 --- a/mm/vmalloc.c +++ b/mm/vmalloc.c @@ -12,6 +12,7 @@ #include <linux/mm.h> #include <linux/module.h> #include <linux/highmem.h> +#include <linux/sched.h> #include <linux/slab.h> #include <linux/spinlock.h> #include <linux/interrupt.h> @@ -25,10 +26,10 @@ #include <linux/rcupdate.h> #include <linux/pfn.h> #include <linux/kmemleak.h> -#include <linux/highmem.h> #include <asm/atomic.h> #include <asm/uaccess.h> #include <asm/tlbflush.h> +#include <asm/shmparam.h> /*** Page table manipulation functions ***/ @@ -1156,12 +1157,11 @@ static void insert_vmalloc_vm(struct vm_struct *vm, struct vmap_area *va, } static struct vm_struct *__get_vm_area_node(unsigned long size, - unsigned long flags, unsigned long start, unsigned long end, - int node, gfp_t gfp_mask, void *caller) + unsigned long align, unsigned long flags, unsigned long start, + unsigned long end, int node, gfp_t gfp_mask, void *caller) { static struct vmap_area *va; struct vm_struct *area; - unsigned long align = 1; BUG_ON(in_interrupt()); if (flags & VM_IOREMAP) { @@ -1201,7 +1201,7 @@ static struct vm_struct *__get_vm_area_node(unsigned long size, struct vm_struct *__get_vm_area(unsigned long size, unsigned long flags, unsigned long start, unsigned long end) { - return __get_vm_area_node(size, flags, start, end, -1, GFP_KERNEL, + return __get_vm_area_node(size, 1, flags, start, end, -1, GFP_KERNEL, __builtin_return_address(0)); } EXPORT_SYMBOL_GPL(__get_vm_area); @@ -1210,7 +1210,7 @@ struct vm_struct *__get_vm_area_caller(unsigned long size, unsigned long flags, unsigned long start, unsigned long end, void *caller) { - return __get_vm_area_node(size, flags, start, end, -1, GFP_KERNEL, + return __get_vm_area_node(size, 1, flags, start, end, -1, GFP_KERNEL, caller); } @@ -1225,22 +1225,22 @@ struct vm_struct *__get_vm_area_caller(unsigned long size, unsigned long flags, */ struct vm_struct *get_vm_area(unsigned long size, unsigned long flags) { - return __get_vm_area_node(size, flags, VMALLOC_START, VMALLOC_END, + return __get_vm_area_node(size, 1, flags, VMALLOC_START, VMALLOC_END, -1, GFP_KERNEL, __builtin_return_address(0)); } struct vm_struct *get_vm_area_caller(unsigned long size, unsigned long flags, void *caller) { - return __get_vm_area_node(size, flags, VMALLOC_START, VMALLOC_END, + return __get_vm_area_node(size, 1, flags, VMALLOC_START, VMALLOC_END, -1, GFP_KERNEL, caller); } struct vm_struct *get_vm_area_node(unsigned long size, unsigned long flags, int node, gfp_t gfp_mask) { - return __get_vm_area_node(size, flags, VMALLOC_START, VMALLOC_END, node, - gfp_mask, __builtin_return_address(0)); + return __get_vm_area_node(size, 1, flags, VMALLOC_START, VMALLOC_END, + node, gfp_mask, __builtin_return_address(0)); } static struct vm_struct *find_vm_area(const void *addr) @@ -1403,7 +1403,8 @@ void *vmap(struct page **pages, unsigned int count, } EXPORT_SYMBOL(vmap); -static void *__vmalloc_node(unsigned long size, gfp_t gfp_mask, pgprot_t prot, +static void *__vmalloc_node(unsigned long size, unsigned long align, + gfp_t gfp_mask, pgprot_t prot, int node, void *caller); static void *__vmalloc_area_node(struct vm_struct *area, gfp_t gfp_mask, pgprot_t prot, int node, void *caller) @@ -1417,7 +1418,7 @@ static void *__vmalloc_area_node(struct vm_struct *area, gfp_t gfp_mask, area->nr_pages = nr_pages; /* Please note that the recursion is strictly bounded. */ if (array_size > PAGE_SIZE) { - pages = __vmalloc_node(array_size, gfp_mask | __GFP_ZERO, + pages = __vmalloc_node(array_size, 1, gfp_mask | __GFP_ZERO, PAGE_KERNEL, node, caller); area->flags |= VM_VPAGES; } else { @@ -1476,6 +1477,7 @@ void *__vmalloc_area(struct vm_struct *area, gfp_t gfp_mask, pgprot_t prot) /** * __vmalloc_node - allocate virtually contiguous memory * @size: allocation size + * @align: desired alignment * @gfp_mask: flags for the page level allocator * @prot: protection mask for the allocated pages * @node: node to use for allocation or -1 @@ -1485,8 +1487,9 @@ void *__vmalloc_area(struct vm_struct *area, gfp_t gfp_mask, pgprot_t prot) * allocator with @gfp_mask flags. Map them into contiguous * kernel virtual space, using a pagetable protection of @prot. */ -static void *__vmalloc_node(unsigned long size, gfp_t gfp_mask, pgprot_t prot, - int node, void *caller) +static void *__vmalloc_node(unsigned long size, unsigned long align, + gfp_t gfp_mask, pgprot_t prot, + int node, void *caller) { struct vm_struct *area; void *addr; @@ -1496,8 +1499,8 @@ static void *__vmalloc_node(unsigned long size, gfp_t gfp_mask, pgprot_t prot, if (!size || (size >> PAGE_SHIFT) > totalram_pages) return NULL; - area = __get_vm_area_node(size, VM_ALLOC, VMALLOC_START, VMALLOC_END, - node, gfp_mask, caller); + area = __get_vm_area_node(size, align, VM_ALLOC, VMALLOC_START, + VMALLOC_END, node, gfp_mask, caller); if (!area) return NULL; @@ -1516,7 +1519,7 @@ static void *__vmalloc_node(unsigned long size, gfp_t gfp_mask, pgprot_t prot, void *__vmalloc(unsigned long size, gfp_t gfp_mask, pgprot_t prot) { - return __vmalloc_node(size, gfp_mask, prot, -1, + return __vmalloc_node(size, 1, gfp_mask, prot, -1, __builtin_return_address(0)); } EXPORT_SYMBOL(__vmalloc); @@ -1532,7 +1535,7 @@ EXPORT_SYMBOL(__vmalloc); */ void *vmalloc(unsigned long size) { - return __vmalloc_node(size, GFP_KERNEL | __GFP_HIGHMEM, PAGE_KERNEL, + return __vmalloc_node(size, 1, GFP_KERNEL | __GFP_HIGHMEM, PAGE_KERNEL, -1, __builtin_return_address(0)); } EXPORT_SYMBOL(vmalloc); @@ -1549,7 +1552,8 @@ void *vmalloc_user(unsigned long size) struct vm_struct *area; void *ret; - ret = __vmalloc_node(size, GFP_KERNEL | __GFP_HIGHMEM | __GFP_ZERO, + ret = __vmalloc_node(size, SHMLBA, + GFP_KERNEL | __GFP_HIGHMEM | __GFP_ZERO, PAGE_KERNEL, -1, __builtin_return_address(0)); if (ret) { area = find_vm_area(ret); @@ -1572,7 +1576,7 @@ EXPORT_SYMBOL(vmalloc_user); */ void *vmalloc_node(unsigned long size, int node) { - return __vmalloc_node(size, GFP_KERNEL | __GFP_HIGHMEM, PAGE_KERNEL, + return __vmalloc_node(size, 1, GFP_KERNEL | __GFP_HIGHMEM, PAGE_KERNEL, node, __builtin_return_address(0)); } EXPORT_SYMBOL(vmalloc_node); @@ -1595,7 +1599,7 @@ EXPORT_SYMBOL(vmalloc_node); void *vmalloc_exec(unsigned long size) { - return __vmalloc_node(size, GFP_KERNEL | __GFP_HIGHMEM, PAGE_KERNEL_EXEC, + return __vmalloc_node(size, 1, GFP_KERNEL | __GFP_HIGHMEM, PAGE_KERNEL_EXEC, -1, __builtin_return_address(0)); } @@ -1616,7 +1620,7 @@ void *vmalloc_exec(unsigned long size) */ void *vmalloc_32(unsigned long size) { - return __vmalloc_node(size, GFP_VMALLOC32, PAGE_KERNEL, + return __vmalloc_node(size, 1, GFP_VMALLOC32, PAGE_KERNEL, -1, __builtin_return_address(0)); } EXPORT_SYMBOL(vmalloc_32); @@ -1633,7 +1637,7 @@ void *vmalloc_32_user(unsigned long size) struct vm_struct *area; void *ret; - ret = __vmalloc_node(size, GFP_VMALLOC32 | __GFP_ZERO, PAGE_KERNEL, + ret = __vmalloc_node(size, 1, GFP_VMALLOC32 | __GFP_ZERO, PAGE_KERNEL, -1, __builtin_return_address(0)); if (ret) { area = find_vm_area(ret); diff --git a/mm/vmscan.c b/mm/vmscan.c index 64e438898832..777af57fd8c8 100644 --- a/mm/vmscan.c +++ b/mm/vmscan.c @@ -544,6 +544,16 @@ redo: */ lru = LRU_UNEVICTABLE; add_page_to_unevictable_list(page); + /* + * When racing with an mlock clearing (page is + * unlocked), make sure that if the other thread does + * not observe our setting of PG_lru and fails + * isolation, we see PG_mlocked cleared below and move + * the page back to the evictable list. + * + * The other side is TestClearPageMlocked(). + */ + smp_mb(); } /* @@ -1088,7 +1098,7 @@ static unsigned long shrink_inactive_list(unsigned long max_scan, int lumpy_reclaim = 0; while (unlikely(too_many_isolated(zone, file, sc))) { - congestion_wait(WRITE, HZ/10); + congestion_wait(BLK_RW_ASYNC, HZ/10); /* We are about to die and free our memory. Return now. */ if (fatal_signal_pending(current)) @@ -1356,7 +1366,7 @@ static void shrink_active_list(unsigned long nr_pages, struct zone *zone, * IO, plus JVM can create lots of anon VM_EXEC pages, * so we ignore them here. */ - if ((vm_flags & VM_EXEC) && !PageAnon(page)) { + if ((vm_flags & VM_EXEC) && page_is_file_cache(page)) { list_add(&page->lru, &l_active); continue; } diff --git a/net/8021q/vlan.c b/net/8021q/vlan.c index d9cb020029b9..1483243edf14 100644 --- a/net/8021q/vlan.c +++ b/net/8021q/vlan.c @@ -282,8 +282,11 @@ out_uninit_applicant: if (ngrp) vlan_gvrp_uninit_applicant(real_dev); out_free_group: - if (ngrp) - vlan_group_free(ngrp); + if (ngrp) { + hlist_del_rcu(&ngrp->hlist); + /* Free the group, after all cpu's are done. */ + call_rcu(&ngrp->rcu, vlan_rcu_free); + } return err; } diff --git a/net/9p/client.c b/net/9p/client.c index 5bf5f227dbe0..8af95b2dddd6 100644 --- a/net/9p/client.c +++ b/net/9p/client.c @@ -582,11 +582,9 @@ static struct p9_fid *p9_fid_create(struct p9_client *clnt) memset(&fid->qid, 0, sizeof(struct p9_qid)); fid->mode = -1; - fid->rdir_fpos = 0; fid->uid = current_fsuid(); fid->clnt = clnt; - fid->aux = NULL; - + fid->rdir = NULL; spin_lock_irqsave(&clnt->lock, flags); list_add(&fid->flist, &clnt->fidlist); spin_unlock_irqrestore(&clnt->lock, flags); @@ -609,6 +607,7 @@ static void p9_fid_destroy(struct p9_fid *fid) spin_lock_irqsave(&clnt->lock, flags); list_del(&fid->flist); spin_unlock_irqrestore(&clnt->lock, flags); + kfree(fid->rdir); kfree(fid); } diff --git a/net/9p/trans_virtio.c b/net/9p/trans_virtio.c index b2e07f0dd298..ea1e3daabefe 100644 --- a/net/9p/trans_virtio.c +++ b/net/9p/trans_virtio.c @@ -43,7 +43,6 @@ #include <net/9p/transport.h> #include <linux/scatterlist.h> #include <linux/virtio.h> -#include <linux/virtio_ids.h> #include <linux/virtio_9p.h> #define VIRTQUEUE_NUM 128 diff --git a/net/core/skbuff.c b/net/core/skbuff.c index 941bac907484..739b8f4dd327 100644 --- a/net/core/skbuff.c +++ b/net/core/skbuff.c @@ -2704,7 +2704,8 @@ int skb_gro_receive(struct sk_buff **head, struct sk_buff *skb) NAPI_GRO_CB(skb)->free = 1; goto done; - } + } else if (skb_gro_len(p) != pinfo->gso_size) + return -E2BIG; headroom = skb_headroom(p); nskb = netdev_alloc_skb(p->dev, headroom + skb_gro_offset(p)); diff --git a/net/irda/ircomm/ircomm_tty_attach.c b/net/irda/ircomm/ircomm_tty_attach.c index eafc010907c2..3c1754023022 100644 --- a/net/irda/ircomm/ircomm_tty_attach.c +++ b/net/irda/ircomm/ircomm_tty_attach.c @@ -30,6 +30,7 @@ ********************************************************************/ #include <linux/init.h> +#include <linux/sched.h> #include <net/irda/irda.h> #include <net/irda/irlmp.h> diff --git a/net/irda/irlan/irlan_common.c b/net/irda/irlan/irlan_common.c index 62116829b817..315ead3cb926 100644 --- a/net/irda/irlan/irlan_common.c +++ b/net/irda/irlan/irlan_common.c @@ -30,6 +30,7 @@ #include <linux/init.h> #include <linux/errno.h> #include <linux/proc_fs.h> +#include <linux/sched.h> #include <linux/seq_file.h> #include <linux/random.h> #include <linux/netdevice.h> diff --git a/net/irda/irlan/irlan_eth.c b/net/irda/irlan/irlan_eth.c index 7b6b631f647f..d340110f5c0c 100644 --- a/net/irda/irlan/irlan_eth.c +++ b/net/irda/irlan/irlan_eth.c @@ -30,6 +30,7 @@ #include <linux/inetdevice.h> #include <linux/if_arp.h> #include <linux/module.h> +#include <linux/sched.h> #include <net/arp.h> #include <net/irda/irda.h> diff --git a/net/irda/irnet/irnet_irda.c b/net/irda/irnet/irnet_irda.c index cf9a4b531a98..cccc2e93234f 100644 --- a/net/irda/irnet/irnet_irda.c +++ b/net/irda/irnet/irnet_irda.c @@ -9,6 +9,7 @@ */ #include "irnet_irda.h" /* Private header */ +#include <linux/sched.h> #include <linux/seq_file.h> #include <asm/unaligned.h> diff --git a/net/irda/irnet/irnet_ppp.c b/net/irda/irnet/irnet_ppp.c index 68cbcb19cbd8..7dea882dbb75 100644 --- a/net/irda/irnet/irnet_ppp.c +++ b/net/irda/irnet/irnet_ppp.c @@ -13,6 +13,7 @@ * 2) as a control channel (write commands, read events) */ +#include <linux/sched.h> #include <linux/smp_lock.h> #include "irnet_ppp.h" /* Private header */ /* Please put other headers in irnet.h - Thanks */ diff --git a/net/mac80211/rc80211_pid_debugfs.c b/net/mac80211/rc80211_pid_debugfs.c index a59043fbb0ff..45667054a5f3 100644 --- a/net/mac80211/rc80211_pid_debugfs.c +++ b/net/mac80211/rc80211_pid_debugfs.c @@ -6,6 +6,7 @@ * published by the Free Software Foundation. */ +#include <linux/sched.h> #include <linux/spinlock.h> #include <linux/poll.h> #include <linux/netdevice.h> diff --git a/net/netfilter/nf_conntrack_core.c b/net/netfilter/nf_conntrack_core.c index 0cdfb388a191..b9168c1864ca 100644 --- a/net/netfilter/nf_conntrack_core.c +++ b/net/netfilter/nf_conntrack_core.c @@ -14,6 +14,7 @@ #include <linux/types.h> #include <linux/netfilter.h> #include <linux/module.h> +#include <linux/sched.h> #include <linux/skbuff.h> #include <linux/proc_fs.h> #include <linux/vmalloc.h> diff --git a/net/sunrpc/xprtrdma/svc_rdma_transport.c b/net/sunrpc/xprtrdma/svc_rdma_transport.c index 0cf5e8c27a10..3fa5751af0ec 100644 --- a/net/sunrpc/xprtrdma/svc_rdma_transport.c +++ b/net/sunrpc/xprtrdma/svc_rdma_transport.c @@ -42,6 +42,7 @@ #include <linux/sunrpc/svc_xprt.h> #include <linux/sunrpc/debug.h> #include <linux/sunrpc/rpc_rdma.h> +#include <linux/sched.h> #include <linux/spinlock.h> #include <rdma/ib_verbs.h> #include <rdma/rdma_cm.h> diff --git a/net/wireless/core.c b/net/wireless/core.c index 02835172b227..45bd63ad2eb2 100644 --- a/net/wireless/core.c +++ b/net/wireless/core.c @@ -14,6 +14,7 @@ #include <linux/device.h> #include <linux/etherdevice.h> #include <linux/rtnetlink.h> +#include <linux/sched.h> #include <net/genetlink.h> #include <net/cfg80211.h> #include "nl80211.h" diff --git a/scripts/Kbuild.include b/scripts/Kbuild.include index 4f9c1908593b..c67e73ecd5be 100644 --- a/scripts/Kbuild.include +++ b/scripts/Kbuild.include @@ -100,7 +100,7 @@ as-option = $(call try-run,\ # Usage: cflags-y += $(call as-instr,instr,option1,option2) as-instr = $(call try-run,\ - echo -e "$(1)" | $(CC) $(KBUILD_AFLAGS) -c -xassembler -o "$$TMP" -,$(2),$(3)) + /bin/echo -e "$(1)" | $(CC) $(KBUILD_AFLAGS) -c -xassembler -o "$$TMP" -,$(2),$(3)) # cc-option # Usage: cflags-y += $(call cc-option,-march=winchip-c6,-march=i586) diff --git a/scripts/Makefile.lib b/scripts/Makefile.lib index 7a7778746ea6..ffdafb26f539 100644 --- a/scripts/Makefile.lib +++ b/scripts/Makefile.lib @@ -208,7 +208,7 @@ cmd_gzip = (cat $(filter-out FORCE,$^) | gzip -f -9 > $@) || \ # Bzip2 and LZMA do not include size in file... so we have to fake that; # append the size as a 32-bit littleendian number as gzip does. -size_append = echo -ne $(shell \ +size_append = /bin/echo -ne $(shell \ dec_size=0; \ for F in $1; do \ fsize=$$(stat -c "%s" $$F); \ diff --git a/scripts/checkkconfigsymbols.sh b/scripts/checkkconfigsymbols.sh index 39677c82747a..46be3c5a62b7 100755 --- a/scripts/checkkconfigsymbols.sh +++ b/scripts/checkkconfigsymbols.sh @@ -9,7 +9,7 @@ paths="$@" # Doing this once at the beginning saves a lot of time, on a cache-hot tree. Kconfigs="`find . -name 'Kconfig' -o -name 'Kconfig*[^~]'`" -echo -e "File list \tundefined symbol used" +/bin/echo -e "File list \tundefined symbol used" find $paths -name '*.[chS]' -o -name 'Makefile' -o -name 'Makefile*[^~]'| while read i do # Output the bare Kconfig variable and the filename; the _MODULE part at @@ -54,6 +54,6 @@ while read symb files; do # beyond the purpose of this script. symb_bare=`echo $symb | sed -e 's/_MODULE//'` if ! grep -q "\<$symb_bare\>" $Kconfigs; then - echo -e "$files: \t$symb" + /bin/echo -e "$files: \t$symb" fi done|sort diff --git a/scripts/checkpatch.pl b/scripts/checkpatch.pl index 87bbb8bce9bf..bc4114f1ab30 100755 --- a/scripts/checkpatch.pl +++ b/scripts/checkpatch.pl @@ -2,7 +2,7 @@ # (c) 2001, Dave Jones. <davej@redhat.com> (the file handling bit) # (c) 2005, Joel Schopp <jschopp@austin.ibm.com> (the ugly bit) # (c) 2007,2008, Andy Whitcroft <apw@uk.ibm.com> (new conditions, test suite) -# (c) 2008, Andy Whitcroft <apw@canonical.com> +# (c) 2008,2009, Andy Whitcroft <apw@canonical.com> # Licensed under the terms of the GNU GPL License version 2 use strict; @@ -10,7 +10,7 @@ use strict; my $P = $0; $P =~ s@.*/@@g; -my $V = '0.29'; +my $V = '0.30'; use Getopt::Long qw(:config no_auto_abbrev); @@ -130,7 +130,10 @@ if ($tree) { my $emitted_corrupt = 0; -our $Ident = qr{[A-Za-z_][A-Za-z\d_]*}; +our $Ident = qr{ + [A-Za-z_][A-Za-z\d_]* + (?:\s*\#\#\s*[A-Za-z_][A-Za-z\d_]*)* + }x; our $Storage = qr{extern|static|asmlinkage}; our $Sparse = qr{ __user| @@ -997,23 +1000,25 @@ sub annotate_values { sub possible { my ($possible, $line) = @_; - - print "CHECK<$possible> ($line)\n" if ($dbg_possible > 2); - if ($possible !~ /(?: + my $notPermitted = qr{(?: ^(?: $Modifier| $Storage| $Type| - DEFINE_\S+| + DEFINE_\S+ + )$| + ^(?: goto| return| case| else| asm|__asm__| do - )$| + )(?:\s|$)| ^(?:typedef|struct|enum)\b - )/x) { + )}x; + warn "CHECK<$possible> ($line)\n" if ($dbg_possible > 2); + if ($possible !~ $notPermitted) { # Check for modifiers. $possible =~ s/\s*$Storage\s*//g; $possible =~ s/\s*$Sparse\s*//g; @@ -1022,8 +1027,10 @@ sub possible { } elsif ($possible =~ /\s/) { $possible =~ s/\s*$Type\s*//g; for my $modifier (split(' ', $possible)) { - warn "MODIFIER: $modifier ($possible) ($line)\n" if ($dbg_possible); - push(@modifierList, $modifier); + if ($modifier !~ $notPermitted) { + warn "MODIFIER: $modifier ($possible) ($line)\n" if ($dbg_possible); + push(@modifierList, $modifier); + } } } else { @@ -1138,6 +1145,7 @@ sub process { # suppression flags my %suppress_ifbraces; my %suppress_whiletrailers; + my %suppress_export; # Pre-scan the patch sanitizing the lines. # Pre-scan the patch looking for any __setup documentation. @@ -1230,7 +1238,6 @@ sub process { $linenr++; my $rawline = $rawlines[$linenr - 1]; - my $hunk_line = ($realcnt != 0); #extract the line range in the file after the patch is applied if ($line=~/^\@\@ -\d+(?:,\d+)? \+(\d+)(,(\d+))? \@\@/) { @@ -1247,6 +1254,7 @@ sub process { %suppress_ifbraces = (); %suppress_whiletrailers = (); + %suppress_export = (); next; # track the line number as we move through the hunk, note that @@ -1270,6 +1278,8 @@ sub process { $realcnt--; } + my $hunk_line = ($realcnt != 0); + #make up the handle for any error we report on this line $prefix = "$filename:$realline: " if ($emacs && $file); $prefix = "$filename:$linenr: " if ($emacs && !$file); @@ -1420,13 +1430,22 @@ sub process { } # Check for potential 'bare' types - my ($stat, $cond, $line_nr_next, $remain_next, $off_next); + my ($stat, $cond, $line_nr_next, $remain_next, $off_next, + $realline_next); if ($realcnt && $line =~ /.\s*\S/) { ($stat, $cond, $line_nr_next, $remain_next, $off_next) = ctx_statement_block($linenr, $realcnt, 0); $stat =~ s/\n./\n /g; $cond =~ s/\n./\n /g; + # Find the real next line. + $realline_next = $line_nr_next; + if (defined $realline_next && + (!defined $lines[$realline_next - 1] || + substr($lines[$realline_next - 1], $off_next) =~ /^\s*$/)) { + $realline_next++; + } + my $s = $stat; $s =~ s/{.*$//s; @@ -1661,8 +1680,8 @@ sub process { } # check for initialisation to aggregates open brace on the next line - if ($prevline =~ /$Declare\s*$Ident\s*=\s*$/ && - $line =~ /^.\s*{/) { + if ($line =~ /^.\s*{/ && + $prevline =~ /(?:^|[^=])=\s*$/) { ERROR("that open brace { should be on the previous line\n" . $hereprev); } @@ -1687,21 +1706,40 @@ sub process { $line =~ s@//.*@@; $opline =~ s@//.*@@; -#EXPORT_SYMBOL should immediately follow its function closing }. - if (($line =~ /EXPORT_SYMBOL.*\((.*)\)/) || - ($line =~ /EXPORT_UNUSED_SYMBOL.*\((.*)\)/)) { +# EXPORT_SYMBOL should immediately follow the thing it is exporting, consider +# the whole statement. +#print "APW <$lines[$realline_next - 1]>\n"; + if (defined $realline_next && + exists $lines[$realline_next - 1] && + !defined $suppress_export{$realline_next} && + ($lines[$realline_next - 1] =~ /EXPORT_SYMBOL.*\((.*)\)/ || + $lines[$realline_next - 1] =~ /EXPORT_UNUSED_SYMBOL.*\((.*)\)/)) { my $name = $1; - if ($prevline !~ /(?: - ^.}| + if ($stat !~ /(?: + \n.}\s*$| ^.DEFINE_$Ident\(\Q$name\E\)| ^.DECLARE_$Ident\(\Q$name\E\)| ^.LIST_HEAD\(\Q$name\E\)| - ^.$Type\s*\(\s*\*\s*\Q$name\E\s*\)\s*\(| - \b\Q$name\E(?:\s+$Attribute)?\s*(?:;|=|\[) + ^.(?:$Storage\s+)?$Type\s*\(\s*\*\s*\Q$name\E\s*\)\s*\(| + \b\Q$name\E(?:\s+$Attribute)*\s*(?:;|=|\[|\() )/x) { - WARN("EXPORT_SYMBOL(foo); should immediately follow its function/variable\n" . $herecurr); +#print "FOO A<$lines[$realline_next - 1]> stat<$stat> name<$name>\n"; + $suppress_export{$realline_next} = 2; + } else { + $suppress_export{$realline_next} = 1; } } + if (!defined $suppress_export{$linenr} && + $prevline =~ /^.\s*$/ && + ($line =~ /EXPORT_SYMBOL.*\((.*)\)/ || + $line =~ /EXPORT_UNUSED_SYMBOL.*\((.*)\)/)) { +#print "FOO B <$lines[$linenr - 1]>\n"; + $suppress_export{$linenr} = 2; + } + if (defined $suppress_export{$linenr} && + $suppress_export{$linenr} == 2) { + WARN("EXPORT_SYMBOL(foo); should immediately follow its function/variable\n" . $herecurr); + } # check for external initialisers. if ($line =~ /^.$Type\s*$Ident\s*(?:\s+$Modifier)*\s*=\s*(0|NULL|false)\s*;/) { diff --git a/scripts/dtc/data.c b/scripts/dtc/data.c index dd2e3d39d4c1..fe555e819bf8 100644 --- a/scripts/dtc/data.c +++ b/scripts/dtc/data.c @@ -217,7 +217,7 @@ struct data data_insert_at_marker(struct data d, struct marker *m, return d; } -struct data data_append_markers(struct data d, struct marker *m) +static struct data data_append_markers(struct data d, struct marker *m) { struct marker **mp = &d.markers; diff --git a/scripts/dtc/dtc-lexer.l b/scripts/dtc/dtc-lexer.l index 44dbfd3f0976..a627bbee91d4 100644 --- a/scripts/dtc/dtc-lexer.l +++ b/scripts/dtc/dtc-lexer.l @@ -18,7 +18,7 @@ * USA */ -%option noyywrap nounput yylineno +%option noyywrap noinput nounput yylineno %x INCLUDE %x BYTESTRING diff --git a/scripts/dtc/dtc-lexer.lex.c_shipped b/scripts/dtc/dtc-lexer.lex.c_shipped index ac392cb040f6..e27cc636e326 100644 --- a/scripts/dtc/dtc-lexer.lex.c_shipped +++ b/scripts/dtc/dtc-lexer.lex.c_shipped @@ -9,7 +9,7 @@ #define FLEX_SCANNER #define YY_FLEX_MAJOR_VERSION 2 #define YY_FLEX_MINOR_VERSION 5 -#define YY_FLEX_SUBMINOR_VERSION 34 +#define YY_FLEX_SUBMINOR_VERSION 35 #if YY_FLEX_SUBMINOR_VERSION > 0 #define FLEX_BETA #endif @@ -54,7 +54,6 @@ typedef int flex_int32_t; typedef unsigned char flex_uint8_t; typedef unsigned short int flex_uint16_t; typedef unsigned int flex_uint32_t; -#endif /* ! C99 */ /* Limits of integral types. */ #ifndef INT8_MIN @@ -85,6 +84,8 @@ typedef unsigned int flex_uint32_t; #define UINT32_MAX (4294967295U) #endif +#endif /* ! C99 */ + #endif /* ! FLEXINT_H */ #ifdef __cplusplus @@ -141,7 +142,15 @@ typedef unsigned int flex_uint32_t; /* Size of default input buffer. */ #ifndef YY_BUF_SIZE +#ifdef __ia64__ +/* On IA-64, the buffer size is 16k, not 8k. + * Moreover, YY_BUF_SIZE is 2*YY_READ_BUF_SIZE in the general case. + * Ditto for the __ia64__ case accordingly. + */ +#define YY_BUF_SIZE 32768 +#else #define YY_BUF_SIZE 16384 +#endif /* __ia64__ */ #endif /* The state buf must be large enough to hold one state per character in the main buffer. @@ -192,13 +201,6 @@ extern FILE *yyin, *yyout; #define unput(c) yyunput( c, (yytext_ptr) ) -/* The following is because we cannot portably get our hands on size_t - * (without autoconf's help, which isn't available because we want - * flex-generated scanners to compile on their own). - * Given that the standard has decreed that size_t exists since 1989, - * I guess we can afford to depend on it. Manoj. - */ - #ifndef YY_TYPEDEF_YY_SIZE_T #define YY_TYPEDEF_YY_SIZE_T typedef size_t yy_size_t; @@ -604,6 +606,7 @@ char *yytext; * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 * USA */ +#define YY_NO_INPUT 1 @@ -634,7 +637,7 @@ static int dts_version; /* = 0 */ static void push_input_file(const char *filename); static int pop_input_file(void); -#line 638 "dtc-lexer.lex.c" +#line 641 "dtc-lexer.lex.c" #define INITIAL 0 #define INCLUDE 1 @@ -656,6 +659,35 @@ static int pop_input_file(void); static int yy_init_globals (void ); +/* Accessor methods to globals. + These are made visible to non-reentrant scanners for convenience. */ + +int yylex_destroy (void ); + +int yyget_debug (void ); + +void yyset_debug (int debug_flag ); + +YY_EXTRA_TYPE yyget_extra (void ); + +void yyset_extra (YY_EXTRA_TYPE user_defined ); + +FILE *yyget_in (void ); + +void yyset_in (FILE * in_str ); + +FILE *yyget_out (void ); + +void yyset_out (FILE * out_str ); + +int yyget_leng (void ); + +char *yyget_text (void ); + +int yyget_lineno (void ); + +void yyset_lineno (int line_number ); + /* Macros after this point can all be overridden by user definitions in * section 1. */ @@ -688,7 +720,12 @@ static int input (void ); /* Amount of stuff to slurp up with each read. */ #ifndef YY_READ_BUF_SIZE +#ifdef __ia64__ +/* On IA-64, the buffer size is 16k, not 8k */ +#define YY_READ_BUF_SIZE 16384 +#else #define YY_READ_BUF_SIZE 8192 +#endif /* __ia64__ */ #endif /* Copy whatever the last rule matched to the standard output. */ @@ -696,7 +733,7 @@ static int input (void ); /* This used to be an fputs(), but since the string might contain NUL's, * we now use fwrite(). */ -#define ECHO fwrite( yytext, yyleng, 1, yyout ) +#define ECHO do { if (fwrite( yytext, yyleng, 1, yyout )) {} } while (0) #endif /* Gets input and stuffs it into "buf". number of characters read, or YY_NULL, @@ -707,7 +744,7 @@ static int input (void ); if ( YY_CURRENT_BUFFER_LVALUE->yy_is_interactive ) \ { \ int c = '*'; \ - int n; \ + size_t n; \ for ( n = 0; n < max_size && \ (c = getc( yyin )) != EOF && c != '\n'; ++n ) \ buf[n] = (char) c; \ @@ -791,7 +828,7 @@ YY_DECL #line 64 "dtc-lexer.l" -#line 795 "dtc-lexer.lex.c" +#line 832 "dtc-lexer.lex.c" if ( !(yy_init) ) { @@ -1116,7 +1153,7 @@ YY_RULE_SETUP #line 222 "dtc-lexer.l" ECHO; YY_BREAK -#line 1120 "dtc-lexer.lex.c" +#line 1157 "dtc-lexer.lex.c" case YY_END_OF_BUFFER: { @@ -1840,8 +1877,8 @@ YY_BUFFER_STATE yy_scan_string (yyconst char * yystr ) /** Setup the input buffer state to scan the given bytes. The next call to yylex() will * scan from a @e copy of @a bytes. - * @param bytes the byte buffer to scan - * @param len the number of bytes in the buffer pointed to by @a bytes. + * @param yybytes the byte buffer to scan + * @param _yybytes_len the number of bytes in the buffer pointed to by @a bytes. * * @return the newly allocated buffer state object. */ diff --git a/scripts/dtc/libfdt/fdt_ro.c b/scripts/dtc/libfdt/fdt_ro.c index fbbba44fcd0d..22e692919ff9 100644 --- a/scripts/dtc/libfdt/fdt_ro.c +++ b/scripts/dtc/libfdt/fdt_ro.c @@ -411,7 +411,7 @@ int fdt_node_offset_by_phandle(const void *fdt, uint32_t phandle) &phandle, sizeof(phandle)); } -int _stringlist_contains(const char *strlist, int listlen, const char *str) +static int _stringlist_contains(const char *strlist, int listlen, const char *str) { int len = strlen(str); const char *p; diff --git a/scripts/dtc/treesource.c b/scripts/dtc/treesource.c index ebeb6eb27907..1521ff11bb97 100644 --- a/scripts/dtc/treesource.c +++ b/scripts/dtc/treesource.c @@ -52,7 +52,7 @@ static void write_prefix(FILE *f, int level) fputc('\t', f); } -int isstring(char c) +static int isstring(char c) { return (isprint(c) || (c == '\0') diff --git a/scripts/genksyms/keywords.c_shipped b/scripts/genksyms/keywords.c_shipped index 971e0113ae7a..287467a2e8c7 100644 --- a/scripts/genksyms/keywords.c_shipped +++ b/scripts/genksyms/keywords.c_shipped @@ -1,4 +1,4 @@ -/* ANSI-C code produced by gperf version 3.0.2 */ +/* ANSI-C code produced by gperf version 3.0.3 */ /* Command-line: gperf -L ANSI-C -a -C -E -g -H is_reserved_hash -k '1,3,$' -N is_reserved_word -p -t scripts/genksyms/keywords.gperf */ #if !((' ' == 32) && ('!' == 33) && ('"' == 34) && ('#' == 35) \ @@ -30,7 +30,9 @@ #line 1 "scripts/genksyms/keywords.gperf" -#line 3 "scripts/genksyms/keywords.gperf" +struct resword; +static const struct resword *is_reserved_word(register const char *str, register unsigned int len); +#line 5 "scripts/genksyms/keywords.gperf" struct resword { const char *name; int token; }; /* maximum key range = 62, duplicates = 0 */ @@ -78,6 +80,9 @@ is_reserved_hash (register const char *str, register unsigned int len) #ifdef __GNUC__ __inline +#ifdef __GNUC_STDC_INLINE__ +__attribute__ ((__gnu_inline__)) +#endif #endif const struct resword * is_reserved_word (register const char *str, register unsigned int len) @@ -94,105 +99,105 @@ is_reserved_word (register const char *str, register unsigned int len) static const struct resword wordlist[] = { {""}, {""}, {""}, -#line 26 "scripts/genksyms/keywords.gperf" +#line 28 "scripts/genksyms/keywords.gperf" {"asm", ASM_KEYW}, {""}, -#line 8 "scripts/genksyms/keywords.gperf" +#line 10 "scripts/genksyms/keywords.gperf" {"__asm", ASM_KEYW}, {""}, -#line 9 "scripts/genksyms/keywords.gperf" +#line 11 "scripts/genksyms/keywords.gperf" {"__asm__", ASM_KEYW}, {""}, {""}, -#line 52 "scripts/genksyms/keywords.gperf" +#line 54 "scripts/genksyms/keywords.gperf" {"__typeof__", TYPEOF_KEYW}, {""}, -#line 12 "scripts/genksyms/keywords.gperf" +#line 14 "scripts/genksyms/keywords.gperf" {"__const", CONST_KEYW}, -#line 11 "scripts/genksyms/keywords.gperf" - {"__attribute__", ATTRIBUTE_KEYW}, #line 13 "scripts/genksyms/keywords.gperf" + {"__attribute__", ATTRIBUTE_KEYW}, +#line 15 "scripts/genksyms/keywords.gperf" {"__const__", CONST_KEYW}, -#line 18 "scripts/genksyms/keywords.gperf" +#line 20 "scripts/genksyms/keywords.gperf" {"__signed__", SIGNED_KEYW}, -#line 44 "scripts/genksyms/keywords.gperf" +#line 46 "scripts/genksyms/keywords.gperf" {"static", STATIC_KEYW}, -#line 20 "scripts/genksyms/keywords.gperf" +#line 22 "scripts/genksyms/keywords.gperf" {"__volatile__", VOLATILE_KEYW}, -#line 39 "scripts/genksyms/keywords.gperf" +#line 41 "scripts/genksyms/keywords.gperf" {"int", INT_KEYW}, -#line 32 "scripts/genksyms/keywords.gperf" +#line 34 "scripts/genksyms/keywords.gperf" {"char", CHAR_KEYW}, -#line 33 "scripts/genksyms/keywords.gperf" +#line 35 "scripts/genksyms/keywords.gperf" {"const", CONST_KEYW}, -#line 45 "scripts/genksyms/keywords.gperf" +#line 47 "scripts/genksyms/keywords.gperf" {"struct", STRUCT_KEYW}, -#line 24 "scripts/genksyms/keywords.gperf" +#line 26 "scripts/genksyms/keywords.gperf" {"__restrict__", RESTRICT_KEYW}, -#line 25 "scripts/genksyms/keywords.gperf" +#line 27 "scripts/genksyms/keywords.gperf" {"restrict", RESTRICT_KEYW}, -#line 23 "scripts/genksyms/keywords.gperf" +#line 25 "scripts/genksyms/keywords.gperf" {"_restrict", RESTRICT_KEYW}, -#line 16 "scripts/genksyms/keywords.gperf" +#line 18 "scripts/genksyms/keywords.gperf" {"__inline__", INLINE_KEYW}, -#line 10 "scripts/genksyms/keywords.gperf" +#line 12 "scripts/genksyms/keywords.gperf" {"__attribute", ATTRIBUTE_KEYW}, {""}, -#line 14 "scripts/genksyms/keywords.gperf" +#line 16 "scripts/genksyms/keywords.gperf" {"__extension__", EXTENSION_KEYW}, -#line 35 "scripts/genksyms/keywords.gperf" +#line 37 "scripts/genksyms/keywords.gperf" {"enum", ENUM_KEYW}, -#line 19 "scripts/genksyms/keywords.gperf" +#line 21 "scripts/genksyms/keywords.gperf" {"__volatile", VOLATILE_KEYW}, -#line 36 "scripts/genksyms/keywords.gperf" +#line 38 "scripts/genksyms/keywords.gperf" {"extern", EXTERN_KEYW}, {""}, -#line 17 "scripts/genksyms/keywords.gperf" +#line 19 "scripts/genksyms/keywords.gperf" {"__signed", SIGNED_KEYW}, -#line 7 "scripts/genksyms/keywords.gperf" +#line 9 "scripts/genksyms/keywords.gperf" {"EXPORT_SYMBOL_GPL_FUTURE", EXPORT_SYMBOL_KEYW}, {""}, -#line 51 "scripts/genksyms/keywords.gperf" +#line 53 "scripts/genksyms/keywords.gperf" {"typeof", TYPEOF_KEYW}, -#line 46 "scripts/genksyms/keywords.gperf" +#line 48 "scripts/genksyms/keywords.gperf" {"typedef", TYPEDEF_KEYW}, -#line 15 "scripts/genksyms/keywords.gperf" +#line 17 "scripts/genksyms/keywords.gperf" {"__inline", INLINE_KEYW}, -#line 31 "scripts/genksyms/keywords.gperf" +#line 33 "scripts/genksyms/keywords.gperf" {"auto", AUTO_KEYW}, -#line 47 "scripts/genksyms/keywords.gperf" +#line 49 "scripts/genksyms/keywords.gperf" {"union", UNION_KEYW}, {""}, {""}, -#line 48 "scripts/genksyms/keywords.gperf" +#line 50 "scripts/genksyms/keywords.gperf" {"unsigned", UNSIGNED_KEYW}, -#line 49 "scripts/genksyms/keywords.gperf" +#line 51 "scripts/genksyms/keywords.gperf" {"void", VOID_KEYW}, -#line 42 "scripts/genksyms/keywords.gperf" +#line 44 "scripts/genksyms/keywords.gperf" {"short", SHORT_KEYW}, {""}, {""}, -#line 50 "scripts/genksyms/keywords.gperf" +#line 52 "scripts/genksyms/keywords.gperf" {"volatile", VOLATILE_KEYW}, {""}, -#line 37 "scripts/genksyms/keywords.gperf" +#line 39 "scripts/genksyms/keywords.gperf" {"float", FLOAT_KEYW}, -#line 34 "scripts/genksyms/keywords.gperf" +#line 36 "scripts/genksyms/keywords.gperf" {"double", DOUBLE_KEYW}, {""}, -#line 5 "scripts/genksyms/keywords.gperf" +#line 7 "scripts/genksyms/keywords.gperf" {"EXPORT_SYMBOL", EXPORT_SYMBOL_KEYW}, {""}, {""}, -#line 38 "scripts/genksyms/keywords.gperf" +#line 40 "scripts/genksyms/keywords.gperf" {"inline", INLINE_KEYW}, -#line 6 "scripts/genksyms/keywords.gperf" +#line 8 "scripts/genksyms/keywords.gperf" {"EXPORT_SYMBOL_GPL", EXPORT_SYMBOL_KEYW}, -#line 41 "scripts/genksyms/keywords.gperf" +#line 43 "scripts/genksyms/keywords.gperf" {"register", REGISTER_KEYW}, {""}, -#line 22 "scripts/genksyms/keywords.gperf" +#line 24 "scripts/genksyms/keywords.gperf" {"_Bool", BOOL_KEYW}, -#line 43 "scripts/genksyms/keywords.gperf" +#line 45 "scripts/genksyms/keywords.gperf" {"signed", SIGNED_KEYW}, {""}, {""}, -#line 40 "scripts/genksyms/keywords.gperf" +#line 42 "scripts/genksyms/keywords.gperf" {"long", LONG_KEYW} }; diff --git a/scripts/genksyms/keywords.gperf b/scripts/genksyms/keywords.gperf index 5ef3733225fb..8fe977a4d57b 100644 --- a/scripts/genksyms/keywords.gperf +++ b/scripts/genksyms/keywords.gperf @@ -1,4 +1,6 @@ %{ +struct resword; +static const struct resword *is_reserved_word(register const char *str, register unsigned int len); %} struct resword { const char *name; int token; } %% diff --git a/scripts/get_maintainer.pl b/scripts/get_maintainer.pl index cdb44b63342e..81a67a458e78 100755 --- a/scripts/get_maintainer.pl +++ b/scripts/get_maintainer.pl @@ -5,15 +5,15 @@ # Print selected MAINTAINERS information for # the files modified in a patch or for a file # -# usage: perl scripts/get_maintainers.pl [OPTIONS] <patch> -# perl scripts/get_maintainers.pl [OPTIONS] -f <file> +# usage: perl scripts/get_maintainer.pl [OPTIONS] <patch> +# perl scripts/get_maintainer.pl [OPTIONS] -f <file> # # Licensed under the terms of the GNU GPL License version 2 use strict; my $P = $0; -my $V = '0.20'; +my $V = '0.21'; use Getopt::Long qw(:config no_auto_abbrev); @@ -37,6 +37,7 @@ my $scm = 0; my $web = 0; my $subsystem = 0; my $status = 0; +my $keywords = 1; my $from_filename = 0; my $pattern_depth = 0; my $version = 0; @@ -84,6 +85,7 @@ if (!GetOptions( 'scm!' => \$scm, 'web!' => \$web, 'pattern-depth=i' => \$pattern_depth, + 'k|keywords!' => \$keywords, 'f|file' => \$from_filename, 'v|version' => \$version, 'h|help' => \$help, @@ -132,6 +134,8 @@ if (!top_of_kernel_tree($lk_path)) { ## Read MAINTAINERS for type/value pairs my @typevalue = (); +my %keyword_hash; + open(MAINT, "<${lk_path}MAINTAINERS") || die "$P: Can't open MAINTAINERS\n"; while (<MAINT>) { my $line = $_; @@ -149,6 +153,8 @@ while (<MAINT>) { if ((-d $value)) { $value =~ s@([^/])$@$1/@; } + } elsif ($type eq "K") { + $keyword_hash{@typevalue} = $value; } push(@typevalue, "$type:$value"); } elsif (!/^(\s)*$/) { @@ -188,6 +194,7 @@ if ($email_remove_duplicates) { my @files = (); my @range = (); +my @keyword_tvi = (); foreach my $file (@ARGV) { ##if $file is a directory and it lacks a trailing slash, add one @@ -198,11 +205,24 @@ foreach my $file (@ARGV) { } if ($from_filename) { push(@files, $file); + if (-f $file && $keywords) { + open(FILE, "<$file") or die "$P: Can't open ${file}\n"; + while (<FILE>) { + my $patch_line = $_; + foreach my $line (keys %keyword_hash) { + if ($patch_line =~ m/^.*$keyword_hash{$line}/x) { + push(@keyword_tvi, $line); + } + } + } + close(FILE); + } } else { my $file_cnt = @files; my $lastfile; open(PATCH, "<$file") or die "$P: Can't open ${file}\n"; while (<PATCH>) { + my $patch_line = $_; if (m/^\+\+\+\s+(\S+)/) { my $filename = $1; $filename =~ s@^[^/]*/@@; @@ -213,6 +233,12 @@ foreach my $file (@ARGV) { if ($email_git_blame) { push(@range, "$lastfile:$1:$2"); } + } elsif ($keywords) { + foreach my $line (keys %keyword_hash) { + if ($patch_line =~ m/^[+-].*$keyword_hash{$line}/x) { + push(@keyword_tvi, $line); + } + } } } close(PATCH); @@ -286,6 +312,13 @@ foreach my $file (@files) { } } +if ($keywords) { + @keyword_tvi = sort_and_uniq(@keyword_tvi); + foreach my $line (@keyword_tvi) { + add_categories($line); + } +} + if ($email) { foreach my $chief (@penguin_chief) { if ($chief =~ m/^(.*):(.*)/) { @@ -384,6 +417,7 @@ Output type options: Other options: --pattern-depth => Number of pattern directory traversals (default: 0 (all)) + --keywords => scan patch for keywords (default: 1 (on)) --version => show version --help => show this help information @@ -486,7 +520,6 @@ sub format_email { } sub find_starting_index { - my ($index) = @_; while ($index > 0) { diff --git a/scripts/headers_install.pl b/scripts/headers_install.pl index c6ae4052ab43..b89ca2c58fdb 100644 --- a/scripts/headers_install.pl +++ b/scripts/headers_install.pl @@ -20,7 +20,7 @@ use strict; my ($readdir, $installdir, $arch, @files) = @ARGV; -my $unifdef = "scripts/unifdef -U__KERNEL__"; +my $unifdef = "scripts/unifdef -U__KERNEL__ -D__EXPORTED_HEADERS__"; foreach my $file (@files) { local *INFILE; diff --git a/scripts/kconfig/lex.zconf.c_shipped b/scripts/kconfig/lex.zconf.c_shipped index dc3e81807d13..fdc7113b08d1 100644 --- a/scripts/kconfig/lex.zconf.c_shipped +++ b/scripts/kconfig/lex.zconf.c_shipped @@ -160,7 +160,15 @@ typedef unsigned int flex_uint32_t; /* Size of default input buffer. */ #ifndef YY_BUF_SIZE +#ifdef __ia64__ +/* On IA-64, the buffer size is 16k, not 8k. + * Moreover, YY_BUF_SIZE is 2*YY_READ_BUF_SIZE in the general case. + * Ditto for the __ia64__ case accordingly. + */ +#define YY_BUF_SIZE 32768 +#else #define YY_BUF_SIZE 16384 +#endif /* __ia64__ */ #endif /* The state buf must be large enough to hold one state per character in the main buffer. @@ -802,7 +810,7 @@ static int last_ts, first_ts; static void zconf_endhelp(void); static void zconf_endfile(void); -void new_string(void) +static void new_string(void) { text = malloc(START_STRSIZE); text_asize = START_STRSIZE; @@ -810,7 +818,7 @@ void new_string(void) *text = 0; } -void append_string(const char *str, int size) +static void append_string(const char *str, int size) { int new_size = text_size + size + 1; if (new_size > text_asize) { @@ -824,7 +832,7 @@ void append_string(const char *str, int size) text[text_size] = 0; } -void alloc_string(const char *str, int size) +static void alloc_string(const char *str, int size) { text = malloc(size + 1); memcpy(text, str, size); @@ -914,7 +922,12 @@ static int input (void ); /* Amount of stuff to slurp up with each read. */ #ifndef YY_READ_BUF_SIZE +#ifdef __ia64__ +/* On IA-64, the buffer size is 16k, not 8k */ +#define YY_READ_BUF_SIZE 16384 +#else #define YY_READ_BUF_SIZE 8192 +#endif /* __ia64__ */ #endif /* Copy whatever the last rule matched to the standard output. */ @@ -922,7 +935,7 @@ static int input (void ); /* This used to be an fputs(), but since the string might contain NUL's, * we now use fwrite(). */ -#define ECHO fwrite( zconftext, zconfleng, 1, zconfout ) +#define ECHO do { if (fwrite( zconftext, zconfleng, 1, zconfout )) {} } while (0) #endif /* Gets input and stuffs it into "buf". number of characters read, or YY_NULL, @@ -2060,8 +2073,8 @@ YY_BUFFER_STATE zconf_scan_string (yyconst char * yystr ) /** Setup the input buffer state to scan the given bytes. The next call to zconflex() will * scan from a @e copy of @a bytes. - * @param bytes the byte buffer to scan - * @param len the number of bytes in the buffer pointed to by @a bytes. + * @param yybytes the byte buffer to scan + * @param _yybytes_len the number of bytes in the buffer pointed to by @a bytes. * * @return the newly allocated buffer state object. */ diff --git a/scripts/kconfig/zconf.gperf b/scripts/kconfig/zconf.gperf index 25ef5d01c0af..d8bc74249622 100644 --- a/scripts/kconfig/zconf.gperf +++ b/scripts/kconfig/zconf.gperf @@ -9,6 +9,8 @@ struct kconf_id; +static struct kconf_id *kconf_id_lookup(register const char *str, register unsigned int len); + %% mainmenu, T_MAINMENU, TF_COMMAND menu, T_MENU, TF_COMMAND diff --git a/scripts/kconfig/zconf.hash.c_shipped b/scripts/kconfig/zconf.hash.c_shipped index 5c73d51339d8..c1748faf4634 100644 --- a/scripts/kconfig/zconf.hash.c_shipped +++ b/scripts/kconfig/zconf.hash.c_shipped @@ -30,6 +30,8 @@ #endif struct kconf_id; + +static struct kconf_id *kconf_id_lookup(register const char *str, register unsigned int len); /* maximum key range = 47, duplicates = 0 */ #ifdef __GNUC__ diff --git a/scripts/kconfig/zconf.l b/scripts/kconfig/zconf.l index 21ff69c9ad4e..d8f7236cb0a3 100644 --- a/scripts/kconfig/zconf.l +++ b/scripts/kconfig/zconf.l @@ -39,7 +39,7 @@ static int last_ts, first_ts; static void zconf_endhelp(void); static void zconf_endfile(void); -void new_string(void) +static void new_string(void) { text = malloc(START_STRSIZE); text_asize = START_STRSIZE; @@ -47,7 +47,7 @@ void new_string(void) *text = 0; } -void append_string(const char *str, int size) +static void append_string(const char *str, int size) { int new_size = text_size + size + 1; if (new_size > text_asize) { @@ -61,7 +61,7 @@ void append_string(const char *str, int size) text[text_size] = 0; } -void alloc_string(const char *str, int size) +static void alloc_string(const char *str, int size) { text = malloc(size + 1); memcpy(text, str, size); diff --git a/scripts/kconfig/zconf.tab.c_shipped b/scripts/kconfig/zconf.tab.c_shipped index 95df833b5a9d..6e9dcd59aa87 100644 --- a/scripts/kconfig/zconf.tab.c_shipped +++ b/scripts/kconfig/zconf.tab.c_shipped @@ -1,24 +1,23 @@ -/* A Bison parser, made by GNU Bison 2.3. */ -/* Skeleton implementation for Bison's Yacc-like parsers in C +/* A Bison parser, made by GNU Bison 2.4.1. */ - Copyright (C) 1984, 1989, 1990, 2000, 2001, 2002, 2003, 2004, 2005, 2006 +/* Skeleton implementation for Bison's Yacc-like parsers in C + + Copyright (C) 1984, 1989, 1990, 2000, 2001, 2002, 2003, 2004, 2005, 2006 Free Software Foundation, Inc. - - This program is free software; you can redistribute it and/or modify + + This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2, or (at your option) - any later version. - + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - + You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, - Boston, MA 02110-1301, USA. */ + along with this program. If not, see <http://www.gnu.org/licenses/>. */ /* As a special exception, you may create a larger work that contains part or all of the Bison parser skeleton and distribute that work @@ -29,7 +28,7 @@ special exception, which will cause the skeleton and the resulting Bison output files to be licensed under the GNU General Public License without this special exception. - + This special exception was added by the Free Software Foundation in version 2.2 of Bison. */ @@ -47,7 +46,7 @@ #define YYBISON 1 /* Bison version. */ -#define YYBISON_VERSION "2.3" +#define YYBISON_VERSION "2.4.1" /* Skeleton name. */ #define YYSKELETON_NAME "yacc.c" @@ -55,94 +54,23 @@ /* Pure parsers. */ #define YYPURE 0 +/* Push parsers. */ +#define YYPUSH 0 + +/* Pull parsers. */ +#define YYPULL 1 + /* Using locations. */ #define YYLSP_NEEDED 0 /* Substitute the variable and function names. */ -#define yyparse zconfparse -#define yylex zconflex -#define yyerror zconferror -#define yylval zconflval -#define yychar zconfchar -#define yydebug zconfdebug -#define yynerrs zconfnerrs - - -/* Tokens. */ -#ifndef YYTOKENTYPE -# define YYTOKENTYPE - /* Put the tokens into the symbol table, so that GDB and other debuggers - know about them. */ - enum yytokentype { - T_MAINMENU = 258, - T_MENU = 259, - T_ENDMENU = 260, - T_SOURCE = 261, - T_CHOICE = 262, - T_ENDCHOICE = 263, - T_COMMENT = 264, - T_CONFIG = 265, - T_MENUCONFIG = 266, - T_HELP = 267, - T_HELPTEXT = 268, - T_IF = 269, - T_ENDIF = 270, - T_DEPENDS = 271, - T_OPTIONAL = 272, - T_PROMPT = 273, - T_TYPE = 274, - T_DEFAULT = 275, - T_SELECT = 276, - T_RANGE = 277, - T_OPTION = 278, - T_ON = 279, - T_WORD = 280, - T_WORD_QUOTE = 281, - T_UNEQUAL = 282, - T_CLOSE_PAREN = 283, - T_OPEN_PAREN = 284, - T_EOL = 285, - T_OR = 286, - T_AND = 287, - T_EQUAL = 288, - T_NOT = 289 - }; -#endif -/* Tokens. */ -#define T_MAINMENU 258 -#define T_MENU 259 -#define T_ENDMENU 260 -#define T_SOURCE 261 -#define T_CHOICE 262 -#define T_ENDCHOICE 263 -#define T_COMMENT 264 -#define T_CONFIG 265 -#define T_MENUCONFIG 266 -#define T_HELP 267 -#define T_HELPTEXT 268 -#define T_IF 269 -#define T_ENDIF 270 -#define T_DEPENDS 271 -#define T_OPTIONAL 272 -#define T_PROMPT 273 -#define T_TYPE 274 -#define T_DEFAULT 275 -#define T_SELECT 276 -#define T_RANGE 277 -#define T_OPTION 278 -#define T_ON 279 -#define T_WORD 280 -#define T_WORD_QUOTE 281 -#define T_UNEQUAL 282 -#define T_CLOSE_PAREN 283 -#define T_OPEN_PAREN 284 -#define T_EOL 285 -#define T_OR 286 -#define T_AND 287 -#define T_EQUAL 288 -#define T_NOT 289 - - +#define yyparse zconfparse +#define yylex zconflex +#define yyerror zconferror +#define yylval zconflval +#define yychar zconfchar +#define yydebug zconfdebug +#define yynerrs zconfnerrs /* Copy the first part of user declarations. */ @@ -163,8 +91,6 @@ #define LKC_DIRECT_LINK #include "lkc.h" -#include "zconf.hash.c" - #define printd(mask, fmt...) if (cdebug & (mask)) printf(fmt) #define PRINTD 0x0001 @@ -188,6 +114,7 @@ static struct menu *current_menu, *current_entry; #endif + /* Enabling traces. */ #ifndef YYDEBUG # define YYDEBUG 0 @@ -206,31 +133,77 @@ static struct menu *current_menu, *current_entry; # define YYTOKEN_TABLE 0 #endif + +/* Tokens. */ +#ifndef YYTOKENTYPE +# define YYTOKENTYPE + /* Put the tokens into the symbol table, so that GDB and other debuggers + know about them. */ + enum yytokentype { + T_MAINMENU = 258, + T_MENU = 259, + T_ENDMENU = 260, + T_SOURCE = 261, + T_CHOICE = 262, + T_ENDCHOICE = 263, + T_COMMENT = 264, + T_CONFIG = 265, + T_MENUCONFIG = 266, + T_HELP = 267, + T_HELPTEXT = 268, + T_IF = 269, + T_ENDIF = 270, + T_DEPENDS = 271, + T_OPTIONAL = 272, + T_PROMPT = 273, + T_TYPE = 274, + T_DEFAULT = 275, + T_SELECT = 276, + T_RANGE = 277, + T_OPTION = 278, + T_ON = 279, + T_WORD = 280, + T_WORD_QUOTE = 281, + T_UNEQUAL = 282, + T_CLOSE_PAREN = 283, + T_OPEN_PAREN = 284, + T_EOL = 285, + T_OR = 286, + T_AND = 287, + T_EQUAL = 288, + T_NOT = 289 + }; +#endif + + + #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED typedef union YYSTYPE - { + + char *string; struct file *file; struct symbol *symbol; struct expr *expr; struct menu *menu; struct kconf_id *id; -} -/* Line 187 of yacc.c. */ - YYSTYPE; + + +} YYSTYPE; +# define YYSTYPE_IS_TRIVIAL 1 # define yystype YYSTYPE /* obsolescent; will be withdrawn */ # define YYSTYPE_IS_DECLARED 1 -# define YYSTYPE_IS_TRIVIAL 1 #endif - /* Copy the second part of user declarations. */ -/* Line 216 of yacc.c. */ +/* Include zconf.hash.c here so it can see the token constants. */ +#include "zconf.hash.c" + #ifdef short @@ -306,14 +279,14 @@ typedef short int yytype_int16; #if (defined __STDC__ || defined __C99__FUNC__ \ || defined __cplusplus || defined _MSC_VER) static int -YYID (int i) +YYID (int yyi) #else static int -YYID (i) - int i; +YYID (yyi) + int yyi; #endif { - return i; + return yyi; } #endif @@ -394,9 +367,9 @@ void free (void *); /* INFRINGES ON USER NAME SPACE */ /* A type that is properly aligned for any stack member. */ union yyalloc { - yytype_int16 yyss; - YYSTYPE yyvs; - }; + yytype_int16 yyss_alloc; + YYSTYPE yyvs_alloc; +}; /* The size of the maximum gap between one aligned stack and the next. */ # define YYSTACK_GAP_MAXIMUM (sizeof (union yyalloc) - 1) @@ -430,12 +403,12 @@ union yyalloc elements in the stack, and YYPTR gives the new location of the stack. Advance YYPTR to a properly aligned location for the next stack. */ -# define YYSTACK_RELOCATE(Stack) \ +# define YYSTACK_RELOCATE(Stack_alloc, Stack) \ do \ { \ YYSIZE_T yynewbytes; \ - YYCOPY (&yyptr->Stack, Stack, yysize); \ - Stack = &yyptr->Stack; \ + YYCOPY (&yyptr->Stack_alloc, Stack, yysize); \ + Stack = &yyptr->Stack_alloc; \ yynewbytes = yystacksize * sizeof (*Stack) + YYSTACK_GAP_MAXIMUM; \ yyptr += yynewbytes / sizeof (*yyptr); \ } \ @@ -558,18 +531,18 @@ static const yytype_int8 yyrhs[] = /* YYRLINE[YYN] -- source line where rule number YYN was defined. */ static const yytype_uint16 yyrline[] = { - 0, 104, 104, 106, 108, 109, 110, 111, 112, 113, - 114, 118, 122, 122, 122, 122, 122, 122, 122, 126, - 127, 128, 129, 130, 131, 135, 136, 142, 150, 156, - 164, 174, 176, 177, 178, 179, 180, 181, 184, 192, - 198, 208, 214, 220, 223, 225, 236, 237, 242, 251, - 256, 264, 267, 269, 270, 271, 272, 273, 276, 282, - 293, 299, 309, 311, 316, 324, 332, 335, 337, 338, - 339, 344, 351, 356, 364, 367, 369, 370, 371, 374, - 382, 389, 396, 402, 409, 411, 412, 413, 416, 424, - 426, 431, 432, 435, 436, 437, 441, 442, 445, 446, - 449, 450, 451, 452, 453, 454, 455, 458, 459, 462, - 463 + 0, 107, 107, 109, 111, 112, 113, 114, 115, 116, + 117, 121, 125, 125, 125, 125, 125, 125, 125, 129, + 130, 131, 132, 133, 134, 138, 139, 145, 153, 159, + 167, 177, 179, 180, 181, 182, 183, 184, 187, 195, + 201, 211, 217, 223, 226, 228, 239, 240, 245, 254, + 259, 267, 270, 272, 273, 274, 275, 276, 279, 285, + 296, 302, 312, 314, 319, 327, 335, 338, 340, 341, + 342, 347, 354, 359, 367, 370, 372, 373, 374, 377, + 385, 392, 399, 405, 412, 414, 415, 416, 419, 427, + 429, 434, 435, 438, 439, 440, 444, 445, 448, 449, + 452, 453, 454, 455, 456, 457, 458, 461, 462, 465, + 466 }; #endif @@ -985,17 +958,20 @@ yy_symbol_print (yyoutput, yytype, yyvaluep) #if (defined __STDC__ || defined __C99__FUNC__ \ || defined __cplusplus || defined _MSC_VER) static void -yy_stack_print (yytype_int16 *bottom, yytype_int16 *top) +yy_stack_print (yytype_int16 *yybottom, yytype_int16 *yytop) #else static void -yy_stack_print (bottom, top) - yytype_int16 *bottom; - yytype_int16 *top; +yy_stack_print (yybottom, yytop) + yytype_int16 *yybottom; + yytype_int16 *yytop; #endif { YYFPRINTF (stderr, "Stack now"); - for (; bottom <= top; ++bottom) - YYFPRINTF (stderr, " %d", *bottom); + for (; yybottom <= yytop; yybottom++) + { + int yybot = *yybottom; + YYFPRINTF (stderr, " %d", yybot); + } YYFPRINTF (stderr, "\n"); } @@ -1029,11 +1005,11 @@ yy_reduce_print (yyvsp, yyrule) /* The symbols being reduced. */ for (yyi = 0; yyi < yynrhs; yyi++) { - fprintf (stderr, " $%d = ", yyi + 1); + YYFPRINTF (stderr, " $%d = ", yyi + 1); yy_symbol_print (stderr, yyrhs[yyprhs[yyrule] + yyi], &(yyvsp[(yyi + 1) - (yynrhs)]) ); - fprintf (stderr, "\n"); + YYFPRINTF (stderr, "\n"); } } @@ -1343,10 +1319,8 @@ yydestruct (yymsg, yytype, yyvaluep) break; } } - /* Prevent warnings from -Wmissing-prototypes. */ - #ifdef YYPARSE_PARAM #if defined __STDC__ || defined __cplusplus int yyparse (void *YYPARSE_PARAM); @@ -1362,11 +1336,10 @@ int yyparse (); #endif /* ! YYPARSE_PARAM */ - -/* The look-ahead symbol. */ +/* The lookahead symbol. */ int yychar; -/* The semantic value of the look-ahead symbol. */ +/* The semantic value of the lookahead symbol. */ YYSTYPE yylval; /* Number of syntax errors so far. */ @@ -1374,9 +1347,9 @@ int yynerrs; -/*----------. -| yyparse. | -`----------*/ +/*-------------------------. +| yyparse or yypush_parse. | +`-------------------------*/ #ifdef YYPARSE_PARAM #if (defined __STDC__ || defined __C99__FUNC__ \ @@ -1400,66 +1373,68 @@ yyparse () #endif #endif { - - int yystate; - int yyn; - int yyresult; - /* Number of tokens to shift before error messages enabled. */ - int yyerrstatus; - /* Look-ahead token as an internal (translated) token number. */ - int yytoken = 0; -#if YYERROR_VERBOSE - /* Buffer for error messages, and its allocated size. */ - char yymsgbuf[128]; - char *yymsg = yymsgbuf; - YYSIZE_T yymsg_alloc = sizeof yymsgbuf; -#endif - - /* Three stacks and their tools: - `yyss': related to states, - `yyvs': related to semantic values, - `yyls': related to locations. - Refer to the stacks thru separate pointers, to allow yyoverflow - to reallocate them elsewhere. */ - /* The state stack. */ - yytype_int16 yyssa[YYINITDEPTH]; - yytype_int16 *yyss = yyssa; - yytype_int16 *yyssp; + int yystate; + /* Number of tokens to shift before error messages enabled. */ + int yyerrstatus; - /* The semantic value stack. */ - YYSTYPE yyvsa[YYINITDEPTH]; - YYSTYPE *yyvs = yyvsa; - YYSTYPE *yyvsp; + /* The stacks and their tools: + `yyss': related to states. + `yyvs': related to semantic values. + Refer to the stacks thru separate pointers, to allow yyoverflow + to reallocate them elsewhere. */ + /* The state stack. */ + yytype_int16 yyssa[YYINITDEPTH]; + yytype_int16 *yyss; + yytype_int16 *yyssp; -#define YYPOPSTACK(N) (yyvsp -= (N), yyssp -= (N)) + /* The semantic value stack. */ + YYSTYPE yyvsa[YYINITDEPTH]; + YYSTYPE *yyvs; + YYSTYPE *yyvsp; - YYSIZE_T yystacksize = YYINITDEPTH; + YYSIZE_T yystacksize; + int yyn; + int yyresult; + /* Lookahead token as an internal (translated) token number. */ + int yytoken; /* The variables used to return semantic value and location from the action routines. */ YYSTYPE yyval; +#if YYERROR_VERBOSE + /* Buffer for error messages, and its allocated size. */ + char yymsgbuf[128]; + char *yymsg = yymsgbuf; + YYSIZE_T yymsg_alloc = sizeof yymsgbuf; +#endif + +#define YYPOPSTACK(N) (yyvsp -= (N), yyssp -= (N)) /* The number of symbols on the RHS of the reduced rule. Keep to zero when no symbol should be popped. */ int yylen = 0; + yytoken = 0; + yyss = yyssa; + yyvs = yyvsa; + yystacksize = YYINITDEPTH; + YYDPRINTF ((stderr, "Starting parse\n")); yystate = 0; yyerrstatus = 0; yynerrs = 0; - yychar = YYEMPTY; /* Cause a token to be read. */ + yychar = YYEMPTY; /* Cause a token to be read. */ /* Initialize stack pointers. Waste one element of value and location stack so that they stay on the same level as the state stack. The wasted elements are never initialized. */ - yyssp = yyss; yyvsp = yyvs; @@ -1489,7 +1464,6 @@ yyparse () YYSTYPE *yyvs1 = yyvs; yytype_int16 *yyss1 = yyss; - /* Each stack pointer address is followed by the size of the data in use in that stack, in bytes. This used to be a conditional around just the two extra args, but that might @@ -1497,7 +1471,6 @@ yyparse () yyoverflow (YY_("memory exhausted"), &yyss1, yysize * sizeof (*yyssp), &yyvs1, yysize * sizeof (*yyvsp), - &yystacksize); yyss = yyss1; @@ -1520,9 +1493,8 @@ yyparse () (union yyalloc *) YYSTACK_ALLOC (YYSTACK_BYTES (yystacksize)); if (! yyptr) goto yyexhaustedlab; - YYSTACK_RELOCATE (yyss); - YYSTACK_RELOCATE (yyvs); - + YYSTACK_RELOCATE (yyss_alloc, yyss); + YYSTACK_RELOCATE (yyvs_alloc, yyvs); # undef YYSTACK_RELOCATE if (yyss1 != yyssa) YYSTACK_FREE (yyss1); @@ -1533,7 +1505,6 @@ yyparse () yyssp = yyss + yysize - 1; yyvsp = yyvs + yysize - 1; - YYDPRINTF ((stderr, "Stack size increased to %lu\n", (unsigned long int) yystacksize)); @@ -1543,6 +1514,9 @@ yyparse () YYDPRINTF ((stderr, "Entering state %d\n", yystate)); + if (yystate == YYFINAL) + YYACCEPT; + goto yybackup; /*-----------. @@ -1551,16 +1525,16 @@ yyparse () yybackup: /* Do appropriate processing given the current state. Read a - look-ahead token if we need one and don't already have one. */ + lookahead token if we need one and don't already have one. */ - /* First try to decide what to do without reference to look-ahead token. */ + /* First try to decide what to do without reference to lookahead token. */ yyn = yypact[yystate]; if (yyn == YYPACT_NINF) goto yydefault; - /* Not known => get a look-ahead token if don't already have one. */ + /* Not known => get a lookahead token if don't already have one. */ - /* YYCHAR is either YYEMPTY or YYEOF or a valid look-ahead symbol. */ + /* YYCHAR is either YYEMPTY or YYEOF or a valid lookahead symbol. */ if (yychar == YYEMPTY) { YYDPRINTF ((stderr, "Reading a token: ")); @@ -1592,20 +1566,16 @@ yybackup: goto yyreduce; } - if (yyn == YYFINAL) - YYACCEPT; - /* Count tokens shifted since error; after three, turn off error status. */ if (yyerrstatus) yyerrstatus--; - /* Shift the look-ahead token. */ + /* Shift the lookahead token. */ YY_SYMBOL_PRINT ("Shifting", yytoken, &yylval, &yylloc); - /* Discard the shifted token unless it is eof. */ - if (yychar != YYEOF) - yychar = YYEMPTY; + /* Discard the shifted token. */ + yychar = YYEMPTY; yystate = yyn; *++yyvsp = yylval; @@ -2029,7 +1999,6 @@ yyreduce: break; -/* Line 1267 of yacc.c. */ default: break; } @@ -2041,7 +2010,6 @@ yyreduce: *++yyvsp = yyval; - /* Now `shift' the result of the reduction. Determine what state that goes to, based on the state we popped back to and the rule number reduced by. */ @@ -2106,7 +2074,7 @@ yyerrlab: if (yyerrstatus == 3) { - /* If just tried and failed to reuse look-ahead token after an + /* If just tried and failed to reuse lookahead token after an error, discard it. */ if (yychar <= YYEOF) @@ -2123,7 +2091,7 @@ yyerrlab: } } - /* Else will try to reuse look-ahead token after shifting the error + /* Else will try to reuse lookahead token after shifting the error token. */ goto yyerrlab1; @@ -2180,9 +2148,6 @@ yyerrlab1: YY_STACK_PRINT (yyss, yyssp); } - if (yyn == YYFINAL) - YYACCEPT; - *++yyvsp = yylval; @@ -2207,7 +2172,7 @@ yyabortlab: yyresult = 1; goto yyreturn; -#ifndef yyoverflow +#if !defined(yyoverflow) || YYERROR_VERBOSE /*-------------------------------------------------. | yyexhaustedlab -- memory exhaustion comes here. | `-------------------------------------------------*/ @@ -2218,7 +2183,7 @@ yyexhaustedlab: #endif yyreturn: - if (yychar != YYEOF && yychar != YYEMPTY) + if (yychar != YYEMPTY) yydestruct ("Cleanup: discarding lookahead", yytoken, &yylval); /* Do not reclaim the symbols of the rule which action triggered @@ -2284,7 +2249,7 @@ void conf_parse(const char *name) sym_set_change_count(1); } -const char *zconf_tokenname(int token) +static const char *zconf_tokenname(int token) { switch (token) { case T_MENU: return "menu"; @@ -2348,7 +2313,7 @@ static void zconferror(const char *err) #endif } -void print_quoted_string(FILE *out, const char *str) +static void print_quoted_string(FILE *out, const char *str) { const char *p; int len; @@ -2365,7 +2330,7 @@ void print_quoted_string(FILE *out, const char *str) putc('"', out); } -void print_symbol(FILE *out, struct menu *menu) +static void print_symbol(FILE *out, struct menu *menu) { struct symbol *sym = menu->sym; struct property *prop; diff --git a/scripts/kconfig/zconf.y b/scripts/kconfig/zconf.y index 9710b82466f2..8c43491f8cc9 100644 --- a/scripts/kconfig/zconf.y +++ b/scripts/kconfig/zconf.y @@ -14,8 +14,6 @@ #define LKC_DIRECT_LINK #include "lkc.h" -#include "zconf.hash.c" - #define printd(mask, fmt...) if (cdebug & (mask)) printf(fmt) #define PRINTD 0x0001 @@ -100,6 +98,11 @@ static struct menu *current_menu, *current_entry; menu_end_menu(); } if_entry menu_entry choice_entry +%{ +/* Include zconf.hash.c here so it can see the token constants. */ +#include "zconf.hash.c" +%} + %% input: stmt_list; @@ -501,7 +504,7 @@ void conf_parse(const char *name) sym_set_change_count(1); } -const char *zconf_tokenname(int token) +static const char *zconf_tokenname(int token) { switch (token) { case T_MENU: return "menu"; @@ -565,7 +568,7 @@ static void zconferror(const char *err) #endif } -void print_quoted_string(FILE *out, const char *str) +static void print_quoted_string(FILE *out, const char *str) { const char *p; int len; @@ -582,7 +585,7 @@ void print_quoted_string(FILE *out, const char *str) putc('"', out); } -void print_symbol(FILE *out, struct menu *menu) +static void print_symbol(FILE *out, struct menu *menu) { struct symbol *sym = menu->sym; struct property *prop; diff --git a/scripts/mkcompile_h b/scripts/mkcompile_h index 6a12dd9f1181..bce3d0fe6fbd 100755 --- a/scripts/mkcompile_h +++ b/scripts/mkcompile_h @@ -1,3 +1,5 @@ +#!/bin/sh + TARGET=$1 ARCH=$2 SMP=$3 @@ -50,7 +52,7 @@ UTS_VERSION="$UTS_VERSION $CONFIG_FLAGS $TIMESTAMP" # Truncate to maximum length UTS_LEN=64 -UTS_TRUNCATE="sed -e s/\(.\{1,$UTS_LEN\}\).*/\1/" +UTS_TRUNCATE="cut -b -$UTS_LEN" # Generate a temporary compile.h @@ -66,9 +68,13 @@ UTS_TRUNCATE="sed -e s/\(.\{1,$UTS_LEN\}\).*/\1/" echo \#define LINUX_COMPILE_HOST \"`hostname | $UTS_TRUNCATE`\" if [ -x /bin/dnsdomainname ]; then - echo \#define LINUX_COMPILE_DOMAIN \"`dnsdomainname | $UTS_TRUNCATE`\" + domain=`dnsdomainname 2> /dev/null` elif [ -x /bin/domainname ]; then - echo \#define LINUX_COMPILE_DOMAIN \"`domainname | $UTS_TRUNCATE`\" + domain=`domainname 2> /dev/null` + fi + + if [ -n "$domain" ]; then + echo \#define LINUX_COMPILE_DOMAIN \"`echo $domain | $UTS_TRUNCATE`\" else echo \#define LINUX_COMPILE_DOMAIN fi diff --git a/scripts/package/Makefile b/scripts/package/Makefile index fa4a0a17b7e0..f67cc885c807 100644 --- a/scripts/package/Makefile +++ b/scripts/package/Makefile @@ -18,6 +18,9 @@ # e) generate the rpm files, based on kernel.spec # - Use /. to avoid tar packing just the symlink +# Note that the rpm-pkg target cannot be used with KBUILD_OUTPUT, +# but the binrpm-pkg target can; for some reason O= gets ignored. + # Do we have rpmbuild, otherwise fall back to the older rpm RPM := $(shell if [ -x "/usr/bin/rpmbuild" ]; then echo rpmbuild; \ else echo rpm; fi) @@ -33,6 +36,12 @@ $(objtree)/kernel.spec: $(MKSPEC) $(srctree)/Makefile $(CONFIG_SHELL) $(MKSPEC) > $@ rpm-pkg rpm: $(objtree)/kernel.spec FORCE + @if test -n "$(KBUILD_OUTPUT)"; then \ + echo "Building source + binary RPM is not possible outside the"; \ + echo "kernel source tree. Don't set KBUILD_OUTPUT, or use the"; \ + echo "binrpm-pkg target instead."; \ + false; \ + fi $(MAKE) clean $(PREV) ln -sf $(srctree) $(KERNELPATH) $(CONFIG_SHELL) $(srctree)/scripts/setlocalversion > $(objtree)/.scmversion @@ -61,7 +70,7 @@ binrpm-pkg: $(objtree)/binkernel.spec FORCE set -e; \ mv -f $(objtree)/.tmp_version $(objtree)/.version - $(RPM) $(RPMOPTS) --define "_builddir $(srctree)" --target \ + $(RPM) $(RPMOPTS) --define "_builddir $(objtree)" --target \ $(UTS_MACHINE) -bb $< clean-files += $(objtree)/binkernel.spec diff --git a/scripts/package/mkspec b/scripts/package/mkspec index 3d93f8c81252..47bdd2f99b78 100755 --- a/scripts/package/mkspec +++ b/scripts/package/mkspec @@ -70,7 +70,7 @@ echo 'mkdir -p $RPM_BUILD_ROOT/boot $RPM_BUILD_ROOT/lib/modules' echo 'mkdir -p $RPM_BUILD_ROOT/lib/firmware' echo "%endif" -echo 'INSTALL_MOD_PATH=$RPM_BUILD_ROOT make %{_smp_mflags} modules_install' +echo 'INSTALL_MOD_PATH=$RPM_BUILD_ROOT make %{_smp_mflags} KBUILD_SRC= modules_install' echo "%ifarch ia64" echo 'cp $KBUILD_IMAGE $RPM_BUILD_ROOT'"/boot/efi/vmlinuz-$KERNELRELEASE" echo 'ln -s '"efi/vmlinuz-$KERNELRELEASE" '$RPM_BUILD_ROOT'"/boot/" diff --git a/security/integrity/ima/ima_iint.c b/security/integrity/ima/ima_iint.c index b8dd693f8790..a4e2b1dac943 100644 --- a/security/integrity/ima/ima_iint.c +++ b/security/integrity/ima/ima_iint.c @@ -58,11 +58,11 @@ struct ima_iint_cache *ima_iint_insert(struct inode *inode) if (!ima_initialized) return iint; - iint = kmem_cache_alloc(iint_cache, GFP_KERNEL); + iint = kmem_cache_alloc(iint_cache, GFP_NOFS); if (!iint) return iint; - rc = radix_tree_preload(GFP_KERNEL); + rc = radix_tree_preload(GFP_NOFS); if (rc < 0) goto out; diff --git a/security/keys/keyctl.c b/security/keys/keyctl.c index 2fb28efc5326..06ec722897be 100644 --- a/security/keys/keyctl.c +++ b/security/keys/keyctl.c @@ -873,7 +873,7 @@ static long get_instantiation_keyring(key_serial_t ringid, /* otherwise specify the destination keyring recorded in the * authorisation key (any KEY_SPEC_*_KEYRING) */ if (ringid >= KEY_SPEC_REQUESTOR_KEYRING) { - *_dest_keyring = rka->dest_keyring; + *_dest_keyring = key_get(rka->dest_keyring); return 0; } diff --git a/sound/arm/aaci.c b/sound/arm/aaci.c index dc78272fc39f..1f0f8213e2d5 100644 --- a/sound/arm/aaci.c +++ b/sound/arm/aaci.c @@ -937,6 +937,7 @@ static int __devinit aaci_probe_ac97(struct aaci *aaci) struct snd_ac97 *ac97; int ret; + writel(0, aaci->base + AC97_POWERDOWN); /* * Assert AACIRESET for 2us */ diff --git a/sound/core/pcm.c b/sound/core/pcm.c index 0c1440121c22..c69c60b2a48a 100644 --- a/sound/core/pcm.c +++ b/sound/core/pcm.c @@ -953,11 +953,12 @@ static int snd_pcm_dev_register(struct snd_device *device) struct snd_pcm_substream *substream; struct snd_pcm_notify *notify; char str[16]; - struct snd_pcm *pcm = device->device_data; + struct snd_pcm *pcm; struct device *dev; - if (snd_BUG_ON(!pcm || !device)) + if (snd_BUG_ON(!device || !device->device_data)) return -ENXIO; + pcm = device->device_data; mutex_lock(®ister_mutex); err = snd_pcm_add(pcm); if (err) { diff --git a/sound/core/rawmidi.c b/sound/core/rawmidi.c index c0adc14c91f0..70d6f25ba526 100644 --- a/sound/core/rawmidi.c +++ b/sound/core/rawmidi.c @@ -248,7 +248,8 @@ static int assign_substream(struct snd_rawmidi *rmidi, int subdevice, list_for_each_entry(substream, &s->substreams, list) { if (substream->opened) { if (stream == SNDRV_RAWMIDI_STREAM_INPUT || - !(mode & SNDRV_RAWMIDI_LFLG_APPEND)) + !(mode & SNDRV_RAWMIDI_LFLG_APPEND) || + !substream->append) continue; } if (subdevice < 0 || subdevice == substream->number) { @@ -266,17 +267,21 @@ static int open_substream(struct snd_rawmidi *rmidi, { int err; - err = snd_rawmidi_runtime_create(substream); - if (err < 0) - return err; - err = substream->ops->open(substream); - if (err < 0) - return err; - substream->opened = 1; - if (substream->use_count++ == 0) + if (substream->use_count == 0) { + err = snd_rawmidi_runtime_create(substream); + if (err < 0) + return err; + err = substream->ops->open(substream); + if (err < 0) { + snd_rawmidi_runtime_free(substream); + return err; + } + substream->opened = 1; substream->active_sensing = 0; - if (mode & SNDRV_RAWMIDI_LFLG_APPEND) - substream->append = 1; + if (mode & SNDRV_RAWMIDI_LFLG_APPEND) + substream->append = 1; + } + substream->use_count++; rmidi->streams[substream->stream].substream_opened++; return 0; } @@ -297,27 +302,27 @@ static int rawmidi_open_priv(struct snd_rawmidi *rmidi, int subdevice, int mode, SNDRV_RAWMIDI_STREAM_INPUT, mode, &sinput); if (err < 0) - goto __error; + return err; } if (mode & SNDRV_RAWMIDI_LFLG_OUTPUT) { err = assign_substream(rmidi, subdevice, SNDRV_RAWMIDI_STREAM_OUTPUT, mode, &soutput); if (err < 0) - goto __error; + return err; } if (sinput) { err = open_substream(rmidi, sinput, mode); if (err < 0) - goto __error; + return err; } if (soutput) { err = open_substream(rmidi, soutput, mode); if (err < 0) { if (sinput) close_substream(rmidi, sinput, 0); - goto __error; + return err; } } @@ -325,13 +330,6 @@ static int rawmidi_open_priv(struct snd_rawmidi *rmidi, int subdevice, int mode, rfile->input = sinput; rfile->output = soutput; return 0; - - __error: - if (sinput && sinput->runtime) - snd_rawmidi_runtime_free(sinput); - if (soutput && soutput->runtime) - snd_rawmidi_runtime_free(soutput); - return err; } /* called from sound/core/seq/seq_midi.c */ diff --git a/sound/drivers/dummy.c b/sound/drivers/dummy.c index 6ba066c41d2e..252e04ce602f 100644 --- a/sound/drivers/dummy.c +++ b/sound/drivers/dummy.c @@ -165,7 +165,7 @@ MODULE_PARM_DESC(enable, "Enable this dummy soundcard."); module_param_array(pcm_devs, int, NULL, 0444); MODULE_PARM_DESC(pcm_devs, "PCM devices # (0-4) for dummy driver."); module_param_array(pcm_substreams, int, NULL, 0444); -MODULE_PARM_DESC(pcm_substreams, "PCM substreams # (1-16) for dummy driver."); +MODULE_PARM_DESC(pcm_substreams, "PCM substreams # (1-128) for dummy driver."); //module_param_array(midi_devs, int, NULL, 0444); //MODULE_PARM_DESC(midi_devs, "MIDI devices # (0-2) for dummy driver."); module_param(fake_buffer, bool, 0444); @@ -808,8 +808,6 @@ static int __devinit snd_card_dummy_new_mixer(struct snd_dummy *dummy) unsigned int idx; int err; - if (snd_BUG_ON(!dummy)) - return -EINVAL; spin_lock_init(&dummy->mixer_lock); strcpy(card->mixername, "Dummy Mixer"); diff --git a/sound/drivers/opl3/opl3_midi.c b/sound/drivers/opl3/opl3_midi.c index 6e7d09ae0e82..7d722a025d0d 100644 --- a/sound/drivers/opl3/opl3_midi.c +++ b/sound/drivers/opl3/opl3_midi.c @@ -29,6 +29,8 @@ extern char snd_opl3_regmap[MAX_OPL2_VOICES][4]; extern int use_internal_drums; +static void snd_opl3_note_off_unsafe(void *p, int note, int vel, + struct snd_midi_channel *chan); /* * The next table looks magical, but it certainly is not. Its values have * been calculated as table[i]=8*log(i/64)/log(2) with an obvious exception @@ -242,16 +244,20 @@ void snd_opl3_timer_func(unsigned long data) int again = 0; int i; - spin_lock_irqsave(&opl3->sys_timer_lock, flags); + spin_lock_irqsave(&opl3->voice_lock, flags); for (i = 0; i < opl3->max_voices; i++) { struct snd_opl3_voice *vp = &opl3->voices[i]; if (vp->state > 0 && vp->note_off_check) { if (vp->note_off == jiffies) - snd_opl3_note_off(opl3, vp->note, 0, vp->chan); + snd_opl3_note_off_unsafe(opl3, vp->note, 0, + vp->chan); else again++; } } + spin_unlock_irqrestore(&opl3->voice_lock, flags); + + spin_lock_irqsave(&opl3->sys_timer_lock, flags); if (again) { opl3->tlist.expires = jiffies + 1; /* invoke again */ add_timer(&opl3->tlist); @@ -658,15 +664,14 @@ static void snd_opl3_kill_voice(struct snd_opl3 *opl3, int voice) /* * Release a note in response to a midi note off. */ -void snd_opl3_note_off(void *p, int note, int vel, struct snd_midi_channel *chan) +static void snd_opl3_note_off_unsafe(void *p, int note, int vel, + struct snd_midi_channel *chan) { struct snd_opl3 *opl3; int voice; struct snd_opl3_voice *vp; - unsigned long flags; - opl3 = p; #ifdef DEBUG_MIDI @@ -674,12 +679,9 @@ void snd_opl3_note_off(void *p, int note, int vel, struct snd_midi_channel *chan chan->number, chan->midi_program, note); #endif - spin_lock_irqsave(&opl3->voice_lock, flags); - if (opl3->synth_mode == SNDRV_OPL3_MODE_SEQ) { if (chan->drum_channel && use_internal_drums) { snd_opl3_drum_switch(opl3, note, vel, 0, chan); - spin_unlock_irqrestore(&opl3->voice_lock, flags); return; } /* this loop will hopefully kill all extra voices, because @@ -697,6 +699,16 @@ void snd_opl3_note_off(void *p, int note, int vel, struct snd_midi_channel *chan snd_opl3_kill_voice(opl3, voice); } } +} + +void snd_opl3_note_off(void *p, int note, int vel, + struct snd_midi_channel *chan) +{ + struct snd_opl3 *opl3 = p; + unsigned long flags; + + spin_lock_irqsave(&opl3->voice_lock, flags); + snd_opl3_note_off_unsafe(p, note, vel, chan); spin_unlock_irqrestore(&opl3->voice_lock, flags); } diff --git a/sound/drivers/pcsp/pcsp_lib.c b/sound/drivers/pcsp/pcsp_lib.c index 84cc2658c05b..e1145ac6e908 100644 --- a/sound/drivers/pcsp/pcsp_lib.c +++ b/sound/drivers/pcsp/pcsp_lib.c @@ -39,25 +39,20 @@ static DECLARE_TASKLET(pcsp_pcm_tasklet, pcsp_call_pcm_elapsed, 0); /* write the port and returns the next expire time in ns; * called at the trigger-start and in hrtimer callback */ -static unsigned long pcsp_timer_update(struct hrtimer *handle) +static u64 pcsp_timer_update(struct snd_pcsp *chip) { unsigned char timer_cnt, val; u64 ns; struct snd_pcm_substream *substream; struct snd_pcm_runtime *runtime; - struct snd_pcsp *chip = container_of(handle, struct snd_pcsp, timer); unsigned long flags; if (chip->thalf) { outb(chip->val61, 0x61); chip->thalf = 0; - if (!atomic_read(&chip->timer_active)) - return 0; return chip->ns_rem; } - if (!atomic_read(&chip->timer_active)) - return 0; substream = chip->playback_substream; if (!substream) return 0; @@ -88,24 +83,17 @@ static unsigned long pcsp_timer_update(struct hrtimer *handle) return ns; } -enum hrtimer_restart pcsp_do_timer(struct hrtimer *handle) +static void pcsp_pointer_update(struct snd_pcsp *chip) { - struct snd_pcsp *chip = container_of(handle, struct snd_pcsp, timer); struct snd_pcm_substream *substream; - int periods_elapsed, pointer_update; size_t period_bytes, buffer_bytes; - unsigned long ns; + int periods_elapsed; unsigned long flags; - pointer_update = !chip->thalf; - ns = pcsp_timer_update(handle); - if (!ns) - return HRTIMER_NORESTART; - /* update the playback position */ substream = chip->playback_substream; if (!substream) - return HRTIMER_NORESTART; + return; period_bytes = snd_pcm_lib_period_bytes(substream); buffer_bytes = snd_pcm_lib_buffer_bytes(substream); @@ -134,6 +122,26 @@ enum hrtimer_restart pcsp_do_timer(struct hrtimer *handle) if (periods_elapsed) tasklet_schedule(&pcsp_pcm_tasklet); +} + +enum hrtimer_restart pcsp_do_timer(struct hrtimer *handle) +{ + struct snd_pcsp *chip = container_of(handle, struct snd_pcsp, timer); + int pointer_update; + u64 ns; + + if (!atomic_read(&chip->timer_active) || !chip->playback_substream) + return HRTIMER_NORESTART; + + pointer_update = !chip->thalf; + ns = pcsp_timer_update(chip); + if (!ns) { + printk(KERN_WARNING "PCSP: unexpected stop\n"); + return HRTIMER_NORESTART; + } + + if (pointer_update) + pcsp_pointer_update(chip); hrtimer_forward(handle, hrtimer_get_expires(handle), ns_to_ktime(ns)); @@ -142,8 +150,6 @@ enum hrtimer_restart pcsp_do_timer(struct hrtimer *handle) static int pcsp_start_playing(struct snd_pcsp *chip) { - unsigned long ns; - #if PCSP_DEBUG printk(KERN_INFO "PCSP: start_playing called\n"); #endif @@ -159,11 +165,7 @@ static int pcsp_start_playing(struct snd_pcsp *chip) atomic_set(&chip->timer_active, 1); chip->thalf = 0; - ns = pcsp_timer_update(&pcsp_chip.timer); - if (!ns) - return -EIO; - - hrtimer_start(&pcsp_chip.timer, ktime_set(0, ns), HRTIMER_MODE_REL); + hrtimer_start(&pcsp_chip.timer, ktime_set(0, 0), HRTIMER_MODE_REL); return 0; } @@ -232,21 +234,22 @@ static int snd_pcsp_playback_hw_free(struct snd_pcm_substream *substream) static int snd_pcsp_playback_prepare(struct snd_pcm_substream *substream) { struct snd_pcsp *chip = snd_pcm_substream_chip(substream); + pcsp_sync_stop(chip); + chip->playback_ptr = 0; + chip->period_ptr = 0; + chip->fmt_size = + snd_pcm_format_physical_width(substream->runtime->format) >> 3; + chip->is_signed = snd_pcm_format_signed(substream->runtime->format); #if PCSP_DEBUG printk(KERN_INFO "PCSP: prepare called, " - "size=%zi psize=%zi f=%zi f1=%i\n", + "size=%zi psize=%zi f=%zi f1=%i fsize=%i\n", snd_pcm_lib_buffer_bytes(substream), snd_pcm_lib_period_bytes(substream), snd_pcm_lib_buffer_bytes(substream) / snd_pcm_lib_period_bytes(substream), - substream->runtime->periods); + substream->runtime->periods, + chip->fmt_size); #endif - pcsp_sync_stop(chip); - chip->playback_ptr = 0; - chip->period_ptr = 0; - chip->fmt_size = - snd_pcm_format_physical_width(substream->runtime->format) >> 3; - chip->is_signed = snd_pcm_format_signed(substream->runtime->format); return 0; } diff --git a/sound/drivers/pcsp/pcsp_mixer.c b/sound/drivers/pcsp/pcsp_mixer.c index 199b03377142..903bc846763f 100644 --- a/sound/drivers/pcsp/pcsp_mixer.c +++ b/sound/drivers/pcsp/pcsp_mixer.c @@ -72,7 +72,7 @@ static int pcsp_treble_put(struct snd_kcontrol *kcontrol, if (treble != chip->treble) { chip->treble = treble; #if PCSP_DEBUG - printk(KERN_INFO "PCSP: rate set to %i\n", PCSP_RATE()); + printk(KERN_INFO "PCSP: rate set to %li\n", PCSP_RATE()); #endif changed = 1; } diff --git a/sound/oss/dmasound/dmasound_core.c b/sound/oss/dmasound/dmasound_core.c index 793b7f478433..3f3c3f71db4b 100644 --- a/sound/oss/dmasound/dmasound_core.c +++ b/sound/oss/dmasound/dmasound_core.c @@ -219,7 +219,9 @@ static int shared_resources_initialised; * Mid level stuff */ -struct sound_settings dmasound = { .lock = SPIN_LOCK_UNLOCKED }; +struct sound_settings dmasound = { + .lock = __SPIN_LOCK_UNLOCKED(dmasound.lock) +}; static inline void sound_silence(void) { diff --git a/sound/oss/hex2hex.c b/sound/oss/hex2hex.c index 5460faae98c9..041ef5c52bc2 100644 --- a/sound/oss/hex2hex.c +++ b/sound/oss/hex2hex.c @@ -12,7 +12,7 @@ #define MAX_SIZE (256*1024) unsigned char buf[MAX_SIZE]; -int loadhex(FILE *inf, unsigned char *buf) +static int loadhex(FILE *inf, unsigned char *buf) { int l=0, c, i; diff --git a/sound/oss/sb_common.c b/sound/oss/sb_common.c index 77d0e5efda76..ce4db49291f7 100644 --- a/sound/oss/sb_common.c +++ b/sound/oss/sb_common.c @@ -157,7 +157,7 @@ static void sb_intr (sb_devc *devc) break; default: - /* printk(KERN_WARN "Sound Blaster: Unexpected interrupt\n"); */ + /* printk(KERN_WARNING "Sound Blaster: Unexpected interrupt\n"); */ ; } } @@ -177,7 +177,7 @@ static void sb_intr (sb_devc *devc) break; default: - /* printk(KERN_WARN "Sound Blaster: Unexpected interrupt\n"); */ + /* printk(KERN_WARNING "Sound Blaster: Unexpected interrupt\n"); */ ; } } diff --git a/sound/oss/sb_ess.c b/sound/oss/sb_ess.c index 180e95c87e3e..51a3d381a59e 100644 --- a/sound/oss/sb_ess.c +++ b/sound/oss/sb_ess.c @@ -782,7 +782,7 @@ printk(KERN_INFO "FKS: ess_handle_channel %s irq_mode=%d\n", channel, irq_mode); break; default:; - /* printk(KERN_WARN "ESS: Unexpected interrupt\n"); */ + /* printk(KERN_WARNING "ESS: Unexpected interrupt\n"); */ } } diff --git a/sound/parisc/harmony.c b/sound/parisc/harmony.c index e924492df21d..f47f9e226b08 100644 --- a/sound/parisc/harmony.c +++ b/sound/parisc/harmony.c @@ -624,6 +624,9 @@ snd_harmony_pcm_init(struct snd_harmony *h) struct snd_pcm *pcm; int err; + if (snd_BUG_ON(!h)) + return -EINVAL; + harmony_disable_interrupts(h); err = snd_pcm_new(h->card, "harmony", 0, 1, 1, &pcm); @@ -865,11 +868,12 @@ snd_harmony_mixer_reset(struct snd_harmony *h) static int __devinit snd_harmony_mixer_init(struct snd_harmony *h) { - struct snd_card *card = h->card; + struct snd_card *card; int idx, err; if (snd_BUG_ON(!h)) return -EINVAL; + card = h->card; strcpy(card->mixername, "Harmony Gain control interface"); for (idx = 0; idx < HARMONY_CONTROLS; idx++) { diff --git a/sound/pci/Kconfig b/sound/pci/Kconfig index fb5ee3cc3968..75c602b5b132 100644 --- a/sound/pci/Kconfig +++ b/sound/pci/Kconfig @@ -259,7 +259,6 @@ config SND_CS5530 config SND_CS5535AUDIO tristate "CS5535/CS5536 Audio" - depends on X86 && !X86_64 select SND_PCM select SND_AC97_CODEC help diff --git a/sound/pci/ali5451/ali5451.c b/sound/pci/ali5451/ali5451.c index b458d208720b..aaf4da68969c 100644 --- a/sound/pci/ali5451/ali5451.c +++ b/sound/pci/ali5451/ali5451.c @@ -973,7 +973,7 @@ static void snd_ali_free_voice(struct snd_ali * codec, void *private_data; snd_ali_printk("free_voice: channel=%d\n",pvoice->number); - if (pvoice == NULL || !pvoice->use) + if (!pvoice->use) return; snd_ali_clear_voices(codec, pvoice->number, pvoice->number); spin_lock_irq(&codec->voice_alloc); diff --git a/sound/pci/bt87x.c b/sound/pci/bt87x.c index 24585c6c6d01..4e2b925a94cc 100644 --- a/sound/pci/bt87x.c +++ b/sound/pci/bt87x.c @@ -808,6 +808,8 @@ static struct pci_device_id snd_bt87x_ids[] = { BT_DEVICE(PCI_DEVICE_ID_BROOKTREE_878, 0x1002, 0x0001, GENERIC), /* Leadtek Winfast tv 2000xp delux */ BT_DEVICE(PCI_DEVICE_ID_BROOKTREE_878, 0x107d, 0x6606, GENERIC), + /* Pinnacle PCTV */ + BT_DEVICE(PCI_DEVICE_ID_BROOKTREE_878, 0x11bd, 0x0012, GENERIC), /* Voodoo TV 200 */ BT_DEVICE(PCI_DEVICE_ID_BROOKTREE_878, 0x121a, 0x3000, GENERIC), /* Askey Computer Corp. MagicTView'99 */ diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c index c9ad182e1b4b..6517f589d01d 100644 --- a/sound/pci/hda/hda_intel.c +++ b/sound/pci/hda/hda_intel.c @@ -722,9 +722,10 @@ static unsigned int azx_rirb_get_response(struct hda_bus *bus, chip->last_cmd[addr]); chip->single_cmd = 1; bus->response_reset = 0; - /* re-initialize CORB/RIRB */ + /* release CORB/RIRB */ azx_free_cmd_io(chip); - azx_init_cmd_io(chip); + /* disable unsolicited responses */ + azx_writel(chip, GCTL, azx_readl(chip, GCTL) & ~ICH6_GCTL_UNSOL); return -1; } @@ -865,7 +866,9 @@ static int azx_reset(struct azx *chip) } /* Accept unsolicited responses */ - azx_writel(chip, GCTL, azx_readl(chip, GCTL) | ICH6_GCTL_UNSOL); + if (!chip->single_cmd) + azx_writel(chip, GCTL, azx_readl(chip, GCTL) | + ICH6_GCTL_UNSOL); /* detect codecs */ if (!chip->codec_mask) { @@ -980,7 +983,8 @@ static void azx_init_chip(struct azx *chip) azx_int_enable(chip); /* initialize the codec command I/O */ - azx_init_cmd_io(chip); + if (!chip->single_cmd) + azx_init_cmd_io(chip); /* program the position buffer */ azx_writel(chip, DPLBASE, (u32)chip->posbuf.addr); @@ -2674,6 +2678,7 @@ static struct pci_device_id azx_ids[] = { { PCI_DEVICE(0x10de, 0x044b), .driver_data = AZX_DRIVER_NVIDIA }, { PCI_DEVICE(0x10de, 0x055c), .driver_data = AZX_DRIVER_NVIDIA }, { PCI_DEVICE(0x10de, 0x055d), .driver_data = AZX_DRIVER_NVIDIA }, + { PCI_DEVICE(0x10de, 0x0590), .driver_data = AZX_DRIVER_NVIDIA }, { PCI_DEVICE(0x10de, 0x0774), .driver_data = AZX_DRIVER_NVIDIA }, { PCI_DEVICE(0x10de, 0x0775), .driver_data = AZX_DRIVER_NVIDIA }, { PCI_DEVICE(0x10de, 0x0776), .driver_data = AZX_DRIVER_NVIDIA }, diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c index 3fbbc8c01e70..905859d4f4df 100644 --- a/sound/pci/hda/patch_conexant.c +++ b/sound/pci/hda/patch_conexant.c @@ -110,6 +110,7 @@ struct conexant_spec { unsigned int dell_automute; unsigned int port_d_mode; + unsigned char ext_mic_bias; }; static int conexant_playback_pcm_open(struct hda_pcm_stream *hinfo, @@ -1927,6 +1928,11 @@ static hda_nid_t cxt5066_adc_nids[3] = { 0x14, 0x15, 0x16 }; static hda_nid_t cxt5066_capsrc_nids[1] = { 0x17 }; #define CXT5066_SPDIF_OUT 0x21 +/* OLPC's microphone port is DC coupled for use with external sensors, + * therefore we use a 50% mic bias in order to center the input signal with + * the DC input range of the codec. */ +#define CXT5066_OLPC_EXT_MIC_BIAS PIN_VREF50 + static struct hda_channel_mode cxt5066_modes[1] = { { 2, NULL }, }; @@ -1980,9 +1986,10 @@ static int cxt5066_hp_master_sw_put(struct snd_kcontrol *kcontrol, /* toggle input of built-in and mic jack appropriately */ static void cxt5066_automic(struct hda_codec *codec) { - static struct hda_verb ext_mic_present[] = { + struct conexant_spec *spec = codec->spec; + struct hda_verb ext_mic_present[] = { /* enable external mic, port B */ - {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, + {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, spec->ext_mic_bias}, /* switch to external mic input */ {0x17, AC_VERB_SET_CONNECT_SEL, 0}, @@ -2235,7 +2242,7 @@ static struct hda_verb cxt5066_init_verbs_olpc[] = { {0x19, AC_VERB_SET_CONNECT_SEL, 0x00}, /* DAC1 */ /* Port B: external microphone */ - {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, + {0x1a, AC_VERB_SET_PIN_WIDGET_CONTROL, CXT5066_OLPC_EXT_MIC_BIAS}, /* Port C: internal microphone */ {0x1b, AC_VERB_SET_PIN_WIDGET_CONTROL, PIN_VREF80}, @@ -2325,6 +2332,7 @@ static struct snd_pci_quirk cxt5066_cfg_tbl[] = { CXT5066_LAPTOP), SND_PCI_QUIRK(0x1028, 0x02f5, "Dell", CXT5066_DELL_LAPTOP), + SND_PCI_QUIRK(0x152d, 0x0833, "OLPC XO-1.5", CXT5066_OLPC_XO_1_5), {} }; @@ -2352,6 +2360,7 @@ static int patch_cxt5066(struct hda_codec *codec) spec->input_mux = &cxt5066_capture_source; spec->port_d_mode = PIN_HP; + spec->ext_mic_bias = PIN_VREF80; spec->num_init_verbs = 1; spec->init_verbs[0] = cxt5066_init_verbs; @@ -2383,6 +2392,7 @@ static int patch_cxt5066(struct hda_codec *codec) spec->mixers[spec->num_mixers++] = cxt5066_mixer_master_olpc; spec->mixers[spec->num_mixers++] = cxt5066_mixers; spec->port_d_mode = 0; + spec->ext_mic_bias = CXT5066_OLPC_EXT_MIC_BIAS; /* no S/PDIF out */ spec->multiout.dig_out_nid = 0; diff --git a/sound/pci/hda/patch_nvhdmi.c b/sound/pci/hda/patch_nvhdmi.c index c8435c9a97f9..6afdab09bab7 100644 --- a/sound/pci/hda/patch_nvhdmi.c +++ b/sound/pci/hda/patch_nvhdmi.c @@ -29,6 +29,9 @@ #include "hda_codec.h" #include "hda_local.h" +/* define below to restrict the supported rates and formats */ +/* #define LIMITED_RATE_FMT_SUPPORT */ + struct nvhdmi_spec { struct hda_multi_out multiout; @@ -60,6 +63,22 @@ static struct hda_verb nvhdmi_basic_init[] = { {} /* terminator */ }; +#ifdef LIMITED_RATE_FMT_SUPPORT +/* support only the safe format and rate */ +#define SUPPORTED_RATES SNDRV_PCM_RATE_48000 +#define SUPPORTED_MAXBPS 16 +#define SUPPORTED_FORMATS SNDRV_PCM_FMTBIT_S16_LE +#else +/* support all rates and formats */ +#define SUPPORTED_RATES \ + (SNDRV_PCM_RATE_22050 | SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000 |\ + SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000 | SNDRV_PCM_RATE_176400 |\ + SNDRV_PCM_RATE_192000) +#define SUPPORTED_MAXBPS 24 +#define SUPPORTED_FORMATS \ + (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S32_LE) +#endif + /* * Controls */ @@ -258,9 +277,9 @@ static struct hda_pcm_stream nvhdmi_pcm_digital_playback_8ch = { .channels_min = 2, .channels_max = 8, .nid = Nv_Master_Convert_nid, - .rates = SNDRV_PCM_RATE_48000, - .maxbps = 16, - .formats = SNDRV_PCM_FMTBIT_S16_LE, + .rates = SUPPORTED_RATES, + .maxbps = SUPPORTED_MAXBPS, + .formats = SUPPORTED_FORMATS, .ops = { .open = nvhdmi_dig_playback_pcm_open, .close = nvhdmi_dig_playback_pcm_close_8ch, @@ -273,9 +292,9 @@ static struct hda_pcm_stream nvhdmi_pcm_digital_playback_2ch = { .channels_min = 2, .channels_max = 2, .nid = Nv_Master_Convert_nid, - .rates = SNDRV_PCM_RATE_48000, - .maxbps = 16, - .formats = SNDRV_PCM_FMTBIT_S16_LE, + .rates = SUPPORTED_RATES, + .maxbps = SUPPORTED_MAXBPS, + .formats = SUPPORTED_FORMATS, .ops = { .open = nvhdmi_dig_playback_pcm_open, .close = nvhdmi_dig_playback_pcm_close_2ch, @@ -378,6 +397,7 @@ static int patch_nvhdmi_2ch(struct hda_codec *codec) static struct hda_codec_preset snd_hda_preset_nvhdmi[] = { { .id = 0x10de0002, .name = "MCP78 HDMI", .patch = patch_nvhdmi_8ch }, { .id = 0x10de0003, .name = "MCP78 HDMI", .patch = patch_nvhdmi_8ch }, + { .id = 0x10de0005, .name = "MCP78 HDMI", .patch = patch_nvhdmi_8ch }, { .id = 0x10de0006, .name = "MCP78 HDMI", .patch = patch_nvhdmi_8ch }, { .id = 0x10de0007, .name = "MCP7A HDMI", .patch = patch_nvhdmi_8ch }, { .id = 0x10de0067, .name = "MCP67 HDMI", .patch = patch_nvhdmi_2ch }, @@ -387,6 +407,7 @@ static struct hda_codec_preset snd_hda_preset_nvhdmi[] = { MODULE_ALIAS("snd-hda-codec-id:10de0002"); MODULE_ALIAS("snd-hda-codec-id:10de0003"); +MODULE_ALIAS("snd-hda-codec-id:10de0005"); MODULE_ALIAS("snd-hda-codec-id:10de0006"); MODULE_ALIAS("snd-hda-codec-id:10de0007"); MODULE_ALIAS("snd-hda-codec-id:10de0067"); diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index 7810d3dcad83..70583719282b 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -275,7 +275,7 @@ struct alc_spec { struct snd_kcontrol_new *cap_mixer; /* capture mixer */ unsigned int beep_amp; /* beep amp value, set via set_beep_amp() */ - const struct hda_verb *init_verbs[5]; /* initialization verbs + const struct hda_verb *init_verbs[10]; /* initialization verbs * don't forget NULL * termination! */ @@ -965,6 +965,8 @@ static void alc_automute_pin(struct hda_codec *codec) unsigned int nid = spec->autocfg.hp_pins[0]; int i; + if (!nid) + return; pincap = snd_hda_query_pin_caps(codec, nid); if (pincap & AC_PINCAP_TRIG_REQ) /* need trigger? */ snd_hda_codec_read(codec, nid, 0, AC_VERB_SET_PIN_SENSE, 0); @@ -1332,15 +1334,20 @@ do_sku: * when the external headphone out jack is plugged" */ if (!spec->autocfg.hp_pins[0]) { + hda_nid_t nid; tmp = (ass >> 11) & 0x3; /* HP to chassis */ if (tmp == 0) - spec->autocfg.hp_pins[0] = porta; + nid = porta; else if (tmp == 1) - spec->autocfg.hp_pins[0] = porte; + nid = porte; else if (tmp == 2) - spec->autocfg.hp_pins[0] = portd; + nid = portd; else return 1; + for (i = 0; i < spec->autocfg.line_outs; i++) + if (spec->autocfg.line_out_pins[i] == nid) + return 1; + spec->autocfg.hp_pins[0] = nid; } alc_init_auto_hp(codec); @@ -1362,7 +1369,7 @@ static void alc_ssid_check(struct hda_codec *codec, } /* - * Fix-up pin default configurations + * Fix-up pin default configurations and add default verbs */ struct alc_pincfg { @@ -1370,9 +1377,14 @@ struct alc_pincfg { u32 val; }; -static void alc_fix_pincfg(struct hda_codec *codec, +struct alc_fixup { + const struct alc_pincfg *pins; + const struct hda_verb *verbs; +}; + +static void alc_pick_fixup(struct hda_codec *codec, const struct snd_pci_quirk *quirk, - const struct alc_pincfg **pinfix) + const struct alc_fixup *fix) { const struct alc_pincfg *cfg; @@ -1380,9 +1392,14 @@ static void alc_fix_pincfg(struct hda_codec *codec, if (!quirk) return; - cfg = pinfix[quirk->value]; - for (; cfg->nid; cfg++) - snd_hda_codec_set_pincfg(codec, cfg->nid, cfg->val); + fix += quirk->value; + cfg = fix->pins; + if (cfg) { + for (; cfg->nid; cfg++) + snd_hda_codec_set_pincfg(codec, cfg->nid, cfg->val); + } + if (fix->verbs) + add_verb(codec->spec, fix->verbs); } /* @@ -4667,9 +4684,9 @@ static int alc880_parse_auto_config(struct hda_codec *codec) spec->multiout.dig_out_nid = dig_nid; else { spec->multiout.slave_dig_outs = spec->slave_dig_outs; - spec->slave_dig_outs[i - 1] = dig_nid; - if (i == ARRAY_SIZE(spec->slave_dig_outs) - 1) + if (i >= ARRAY_SIZE(spec->slave_dig_outs) - 1) break; + spec->slave_dig_outs[i - 1] = dig_nid; } } if (spec->autocfg.dig_in_pin) @@ -6232,7 +6249,7 @@ static struct snd_pci_quirk alc260_cfg_tbl[] = { SND_PCI_QUIRK(0x1025, 0x008f, "Acer", ALC260_ACER), SND_PCI_QUIRK(0x1509, 0x4540, "Favorit 100XS", ALC260_FAVORIT100), SND_PCI_QUIRK(0x103c, 0x2808, "HP d5700", ALC260_HP_3013), - SND_PCI_QUIRK(0x103c, 0x280a, "HP d5750", ALC260_HP_3013), + SND_PCI_QUIRK(0x103c, 0x280a, "HP d5750", ALC260_AUTO), /* no quirk */ SND_PCI_QUIRK(0x103c, 0x3010, "HP", ALC260_HP_3013), SND_PCI_QUIRK(0x103c, 0x3011, "HP", ALC260_HP_3013), SND_PCI_QUIRK(0x103c, 0x3012, "HP", ALC260_HP_DC7600), @@ -8894,10 +8911,11 @@ static struct snd_pci_quirk alc882_ssid_cfg_tbl[] = { SND_PCI_QUIRK(0x106b, 0x3800, "MacbookPro 4,1", ALC885_MBP3), SND_PCI_QUIRK(0x106b, 0x3e00, "iMac 24 Aluminum", ALC885_IMAC24), SND_PCI_QUIRK(0x106b, 0x3f00, "Macbook 5,1", ALC885_MB5), - /* FIXME: HP jack sense seems not working for MBP 5,1, so apparently - * no perfect solution yet + /* FIXME: HP jack sense seems not working for MBP 5,1 or 5,2, + * so apparently no perfect solution yet */ SND_PCI_QUIRK(0x106b, 0x4000, "MacbookPro 5,1", ALC885_MB5), + SND_PCI_QUIRK(0x106b, 0x4600, "MacbookPro 5,2", ALC885_MB5), {} /* terminator */ }; @@ -9593,11 +9611,13 @@ static struct alc_pincfg alc882_abit_aw9d_pinfix[] = { { } }; -static const struct alc_pincfg *alc882_pin_fixes[] = { - [PINFIX_ABIT_AW9D_MAX] = alc882_abit_aw9d_pinfix, +static const struct alc_fixup alc882_fixups[] = { + [PINFIX_ABIT_AW9D_MAX] = { + .pins = alc882_abit_aw9d_pinfix + }, }; -static struct snd_pci_quirk alc882_pinfix_tbl[] = { +static struct snd_pci_quirk alc882_fixup_tbl[] = { SND_PCI_QUIRK(0x147b, 0x107a, "Abit AW9D-MAX", PINFIX_ABIT_AW9D_MAX), {} }; @@ -9794,9 +9814,9 @@ static int alc882_parse_auto_config(struct hda_codec *codec) spec->multiout.dig_out_nid = dig_nid; else { spec->multiout.slave_dig_outs = spec->slave_dig_outs; - spec->slave_dig_outs[i - 1] = dig_nid; - if (i == ARRAY_SIZE(spec->slave_dig_outs) - 1) + if (i >= ARRAY_SIZE(spec->slave_dig_outs) - 1) break; + spec->slave_dig_outs[i - 1] = dig_nid; } } if (spec->autocfg.dig_in_pin) @@ -9869,7 +9889,7 @@ static int patch_alc882(struct hda_codec *codec) board_config = ALC882_AUTO; } - alc_fix_pincfg(codec, alc882_pinfix_tbl, alc882_pin_fixes); + alc_pick_fixup(codec, alc882_fixup_tbl, alc882_fixups); if (board_config == ALC882_AUTO) { /* automatic parse from the BIOS config */ @@ -11441,6 +11461,8 @@ static struct snd_pci_quirk alc262_cfg_tbl[] = { SND_PCI_QUIRK(0x104d, 0x820f, "Sony ASSAMD", ALC262_SONY_ASSAMD), SND_PCI_QUIRK(0x104d, 0x9016, "Sony VAIO", ALC262_AUTO), /* dig-only */ SND_PCI_QUIRK(0x104d, 0x9025, "Sony VAIO Z21MN", ALC262_TOSHIBA_S06), + SND_PCI_QUIRK(0x104d, 0x9035, "Sony VAIO VGN-FW170J", ALC262_AUTO), + SND_PCI_QUIRK(0x104d, 0x9047, "Sony VAIO Type G", ALC262_AUTO), SND_PCI_QUIRK_MASK(0x104d, 0xff00, 0x9000, "Sony VAIO", ALC262_SONY_ASSAMD), SND_PCI_QUIRK(0x1179, 0x0001, "Toshiba dynabook SS RX1", @@ -12585,7 +12607,8 @@ static struct snd_pci_quirk alc268_cfg_tbl[] = { SND_PCI_QUIRK(0x1025, 0x015b, "Acer Aspire One", ALC268_ACER_ASPIRE_ONE), SND_PCI_QUIRK(0x1028, 0x0253, "Dell OEM", ALC268_DELL), - SND_PCI_QUIRK(0x1028, 0x02b0, "Dell Inspiron Mini9", ALC268_DELL), + SND_PCI_QUIRK_MASK(0x1028, 0xfff0, 0x02b0, + "Dell Inspiron Mini9/Vostro A90", ALC268_DELL), /* almost compatible with toshiba but with optional digital outs; * auto-probing seems working fine */ @@ -12842,12 +12865,15 @@ static int patch_alc268(struct hda_codec *codec) unsigned int wcap = get_wcaps(codec, 0x07); int i; + spec->capsrc_nids = alc268_capsrc_nids; /* get type */ wcap = get_wcaps_type(wcap); if (spec->auto_mic || wcap != AC_WID_AUD_IN || spec->input_mux->num_items == 1) { spec->adc_nids = alc268_adc_nids_alt; spec->num_adc_nids = ARRAY_SIZE(alc268_adc_nids_alt); + if (spec->auto_mic) + fixup_automic_adc(codec); if (spec->auto_mic || spec->input_mux->num_items == 1) add_mixer(spec, alc268_capture_nosrc_mixer); else @@ -12857,7 +12883,6 @@ static int patch_alc268(struct hda_codec *codec) spec->num_adc_nids = ARRAY_SIZE(alc268_adc_nids); add_mixer(spec, alc268_capture_mixer); } - spec->capsrc_nids = alc268_capsrc_nids; /* set default input source */ for (i = 0; i < spec->num_adc_nids; i++) snd_hda_codec_write_cache(codec, alc268_capsrc_nids[i], @@ -14357,15 +14382,16 @@ static void alc861_auto_init_multi_out(struct hda_codec *codec) static void alc861_auto_init_hp_out(struct hda_codec *codec) { struct alc_spec *spec = codec->spec; - hda_nid_t pin; - pin = spec->autocfg.hp_pins[0]; - if (pin) - alc861_auto_set_output_and_unmute(codec, pin, PIN_HP, + if (spec->autocfg.hp_outs) + alc861_auto_set_output_and_unmute(codec, + spec->autocfg.hp_pins[0], + PIN_HP, spec->multiout.hp_nid); - pin = spec->autocfg.speaker_pins[0]; - if (pin) - alc861_auto_set_output_and_unmute(codec, pin, PIN_OUT, + if (spec->autocfg.speaker_outs) + alc861_auto_set_output_and_unmute(codec, + spec->autocfg.speaker_pins[0], + PIN_OUT, spec->multiout.dac_nids[0]); } @@ -15158,7 +15184,7 @@ static struct snd_pci_quirk alc861vd_cfg_tbl[] = { SND_PCI_QUIRK(0x1019, 0xa88d, "Realtek ALC660 demo", ALC660VD_3ST), SND_PCI_QUIRK(0x103c, 0x30bf, "HP TX1000", ALC861VD_HP), SND_PCI_QUIRK(0x1043, 0x12e2, "Asus z35m", ALC660VD_3ST), - SND_PCI_QUIRK(0x1043, 0x1339, "Asus G1", ALC660VD_3ST), + /*SND_PCI_QUIRK(0x1043, 0x1339, "Asus G1", ALC660VD_3ST),*/ /* auto */ SND_PCI_QUIRK(0x1043, 0x1633, "Asus V1Sn", ALC660VD_ASUS_V1S), SND_PCI_QUIRK(0x1043, 0x81e7, "ASUS", ALC660VD_3ST_DIG), SND_PCI_QUIRK(0x10de, 0x03f0, "Realtek ALC660 demo", ALC660VD_3ST), @@ -15551,6 +15577,29 @@ static void alc861vd_auto_init(struct hda_codec *codec) alc_inithook(codec); } +enum { + ALC660VD_FIX_ASUS_GPIO1 +}; + +/* reset GPIO1 */ +static const struct hda_verb alc660vd_fix_asus_gpio1_verbs[] = { + {0x01, AC_VERB_SET_GPIO_MASK, 0x03}, + {0x01, AC_VERB_SET_GPIO_DIRECTION, 0x01}, + {0x01, AC_VERB_SET_GPIO_DATA, 0x01}, + { } +}; + +static const struct alc_fixup alc861vd_fixups[] = { + [ALC660VD_FIX_ASUS_GPIO1] = { + .verbs = alc660vd_fix_asus_gpio1_verbs, + }, +}; + +static struct snd_pci_quirk alc861vd_fixup_tbl[] = { + SND_PCI_QUIRK(0x1043, 0x1339, "ASUS A7-K", ALC660VD_FIX_ASUS_GPIO1), + {} +}; + static int patch_alc861vd(struct hda_codec *codec) { struct alc_spec *spec; @@ -15572,6 +15621,8 @@ static int patch_alc861vd(struct hda_codec *codec) board_config = ALC861VD_AUTO; } + alc_pick_fixup(codec, alc861vd_fixup_tbl, alc861vd_fixups); + if (board_config == ALC861VD_AUTO) { /* automatic parse from the BIOS config */ err = alc861vd_parse_auto_config(codec); @@ -17329,7 +17380,7 @@ static int alc662_auto_create_extra_out(struct hda_codec *codec, hda_nid_t pin, /* create playback/capture controls for input pins */ #define alc662_auto_create_input_ctls \ - alc880_auto_create_input_ctls + alc882_auto_create_input_ctls static void alc662_auto_set_output_and_unmute(struct hda_codec *codec, hda_nid_t nid, int pin_type, diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c index a9b26828a651..86de305fc9f2 100644 --- a/sound/pci/hda/patch_sigmatel.c +++ b/sound/pci/hda/patch_sigmatel.c @@ -28,6 +28,7 @@ #include <linux/delay.h> #include <linux/slab.h> #include <linux/pci.h> +#include <linux/dmi.h> #include <sound/core.h> #include <sound/asoundef.h> #include <sound/jack.h> @@ -158,6 +159,7 @@ enum { STAC_D965_5ST_NO_FP, STAC_DELL_3ST, STAC_DELL_BIOS, + STAC_927X_VOLKNOB, STAC_927X_MODELS }; @@ -907,6 +909,16 @@ static struct hda_verb d965_core_init[] = { {} }; +static struct hda_verb dell_3st_core_init[] = { + /* don't set delta bit */ + {0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0x7f}, + /* unmute node 0x1b */ + {0x1b, AC_VERB_SET_AMP_GAIN_MUTE, 0xb000}, + /* select node 0x03 as DAC */ + {0x0b, AC_VERB_SET_CONNECT_SEL, 0x01}, + {} +}; + static struct hda_verb stac927x_core_init[] = { /* set master volume and direct control */ { 0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff}, @@ -915,6 +927,14 @@ static struct hda_verb stac927x_core_init[] = { {} }; +static struct hda_verb stac927x_volknob_core_init[] = { + /* don't set delta bit */ + {0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0x7f}, + /* enable analog pc beep path */ + {0x01, AC_VERB_SET_DIGI_CONVERT_2, 1 << 5}, + {} +}; + static struct hda_verb stac9205_core_init[] = { /* set master volume and direct control */ { 0x24, AC_VERB_SET_VOLUME_KNOB_CONTROL, 0xff}, @@ -1570,6 +1590,8 @@ static struct snd_pci_quirk stac92hd73xx_cfg_tbl[] = { "Dell Studio 17", STAC_DELL_M6_DMIC), SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02be, "Dell Studio 1555", STAC_DELL_M6_DMIC), + SND_PCI_QUIRK(PCI_VENDOR_ID_DELL, 0x02bd, + "Dell Studio 1557", STAC_DELL_M6_DMIC), {} /* terminator */ }; @@ -1674,6 +1696,8 @@ static struct snd_pci_quirk stac92hd71bxx_cfg_tbl[] = { "DFI LanParty", STAC_92HD71BXX_REF), SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x30fb, "HP dv4-1222nr", STAC_HP_DV4_1222NR), + SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x1720, + "HP", STAC_HP_DV5), SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x3080, "HP", STAC_HP_DV5), SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_HP, 0xfff0, 0x30f0, @@ -1999,6 +2023,7 @@ static unsigned int *stac927x_brd_tbl[STAC_927X_MODELS] = { [STAC_D965_5ST_NO_FP] = d965_5st_no_fp_pin_configs, [STAC_DELL_3ST] = dell_3st_pin_configs, [STAC_DELL_BIOS] = NULL, + [STAC_927X_VOLKNOB] = NULL, }; static const char *stac927x_models[STAC_927X_MODELS] = { @@ -2010,6 +2035,7 @@ static const char *stac927x_models[STAC_927X_MODELS] = { [STAC_D965_5ST_NO_FP] = "5stack-no-fp", [STAC_DELL_3ST] = "dell-3stack", [STAC_DELL_BIOS] = "dell-bios", + [STAC_927X_VOLKNOB] = "volknob", }; static struct snd_pci_quirk stac927x_cfg_tbl[] = { @@ -2045,6 +2071,8 @@ static struct snd_pci_quirk stac927x_cfg_tbl[] = { "Intel D965", STAC_D965_5ST), SND_PCI_QUIRK_MASK(PCI_VENDOR_ID_INTEL, 0xff00, 0x2500, "Intel D965", STAC_D965_5ST), + /* volume-knob fixes */ + SND_PCI_QUIRK_VENDOR(0x10cf, "FSC", STAC_927X_VOLKNOB), {} /* terminator */ }; @@ -4642,6 +4670,26 @@ static void stac92xx_unsol_event(struct hda_codec *codec, unsigned int res) } } +static int hp_bseries_system(u32 subsystem_id) +{ + switch (subsystem_id) { + case 0x103c307e: + case 0x103c307f: + case 0x103c3080: + case 0x103c3081: + case 0x103c1722: + case 0x103c1723: + case 0x103c1724: + case 0x103c1725: + case 0x103c1726: + case 0x103c1727: + case 0x103c1728: + case 0x103c1729: + return 1; + } + return 0; +} + #ifdef CONFIG_PROC_FS static void stac92hd_proc_hook(struct snd_info_buffer *buffer, struct hda_codec *codec, hda_nid_t nid) @@ -4731,6 +4779,11 @@ static int stac92xx_hp_check_power_status(struct hda_codec *codec, else spec->gpio_data |= spec->gpio_led; /* white */ + if (hp_bseries_system(codec->subsystem_id)) { + /* LED state is inverted on these systems */ + spec->gpio_data ^= spec->gpio_led; + } + stac_gpio_set(codec, spec->gpio_mask, spec->gpio_dir, spec->gpio_data); @@ -5220,6 +5273,7 @@ static int patch_stac92hd71bxx(struct hda_codec *codec) { struct sigmatel_spec *spec; struct hda_verb *unmute_init = stac92hd71bxx_unmute_core_init; + unsigned int pin_cfg; int err = 0; spec = kzalloc(sizeof(*spec), GFP_KERNEL); @@ -5403,6 +5457,45 @@ again: break; } + if (hp_bseries_system(codec->subsystem_id)) { + pin_cfg = snd_hda_codec_get_pincfg(codec, 0x0f); + if (get_defcfg_device(pin_cfg) == AC_JACK_LINE_OUT || + get_defcfg_device(pin_cfg) == AC_JACK_SPEAKER || + get_defcfg_device(pin_cfg) == AC_JACK_HP_OUT) { + /* It was changed in the BIOS to just satisfy MS DTM. + * Lets turn it back into slaved HP + */ + pin_cfg = (pin_cfg & (~AC_DEFCFG_DEVICE)) + | (AC_JACK_HP_OUT << + AC_DEFCFG_DEVICE_SHIFT); + pin_cfg = (pin_cfg & (~(AC_DEFCFG_DEF_ASSOC + | AC_DEFCFG_SEQUENCE))) + | 0x1f; + snd_hda_codec_set_pincfg(codec, 0x0f, pin_cfg); + } + } + + if ((codec->subsystem_id >> 16) == PCI_VENDOR_ID_HP) { + const struct dmi_device *dev = NULL; + while ((dev = dmi_find_device(DMI_DEV_TYPE_OEM_STRING, + NULL, dev))) { + if (strcmp(dev->name, "HP_Mute_LED_1")) { + switch (codec->vendor_id) { + case 0x111d7608: + spec->gpio_led = 0x01; + break; + case 0x111d7600: + case 0x111d7601: + case 0x111d7602: + case 0x111d7603: + spec->gpio_led = 0x08; + break; + } + break; + } + } + } + #ifdef CONFIG_SND_HDA_POWER_SAVE if (spec->gpio_led) { spec->gpio_mask |= spec->gpio_led; @@ -5612,10 +5705,14 @@ static int patch_stac927x(struct hda_codec *codec) spec->dmic_nids = stac927x_dmic_nids; spec->num_dmics = STAC927X_NUM_DMICS; - spec->init = d965_core_init; + spec->init = dell_3st_core_init; spec->dmux_nids = stac927x_dmux_nids; spec->num_dmuxes = ARRAY_SIZE(stac927x_dmux_nids); break; + case STAC_927X_VOLKNOB: + spec->num_dmics = 0; + spec->init = stac927x_volknob_core_init; + break; default: spec->num_dmics = 0; spec->init = stac927x_core_init; diff --git a/sound/pci/ice1712/amp.c b/sound/pci/ice1712/amp.c index 37564300b50d..6da21a2bcade 100644 --- a/sound/pci/ice1712/amp.c +++ b/sound/pci/ice1712/amp.c @@ -52,11 +52,13 @@ static int __devinit snd_vt1724_amp_init(struct snd_ice1712 *ice) /* only use basic functionality for now */ - ice->num_total_dacs = 2; /* only PSDOUT0 is connected */ + /* VT1616 6ch codec connected to PSDOUT0 using packed mode */ + ice->num_total_dacs = 6; ice->num_total_adcs = 2; - /* Chaintech AV-710 has another codecs, which need initialization */ - /* initialize WM8728 codec */ + /* Chaintech AV-710 has another WM8728 codec connected to PSDOUT4 + (shared with the SPDIF output). Mixer control for this codec + is not yet supported. */ if (ice->eeprom.subvendor == VT1724_SUBDEVICE_AV710) { for (i = 0; i < ARRAY_SIZE(wm_inits); i += 2) wm_put(ice, wm_inits[i], wm_inits[i+1]); diff --git a/sound/pci/ice1712/ice1712.c b/sound/pci/ice1712/ice1712.c index cecf1ffeeaaa..d74033a2cfbe 100644 --- a/sound/pci/ice1712/ice1712.c +++ b/sound/pci/ice1712/ice1712.c @@ -2259,7 +2259,7 @@ static int snd_ice1712_pro_peak_get(struct snd_kcontrol *kcontrol, } static struct snd_kcontrol_new snd_ice1712_mixer_pro_peak __devinitdata = { - .iface = SNDRV_CTL_ELEM_IFACE_MIXER, + .iface = SNDRV_CTL_ELEM_IFACE_PCM, .name = "Multi Track Peak", .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, .info = snd_ice1712_pro_peak_info, diff --git a/sound/pci/ice1712/ice1712.h b/sound/pci/ice1712/ice1712.h index 9da2dae64c5b..d063149e7047 100644 --- a/sound/pci/ice1712/ice1712.h +++ b/sound/pci/ice1712/ice1712.h @@ -382,8 +382,8 @@ struct snd_ice1712 { #ifdef CONFIG_PM int (*pm_suspend)(struct snd_ice1712 *); int (*pm_resume)(struct snd_ice1712 *); - int pm_suspend_enabled:1; - int pm_saved_is_spdif_master:1; + unsigned int pm_suspend_enabled:1; + unsigned int pm_saved_is_spdif_master:1; unsigned int pm_saved_spdif_ctrl; unsigned char pm_saved_spdif_cfg; unsigned int pm_saved_route; diff --git a/sound/pci/ice1712/ice1724.c b/sound/pci/ice1712/ice1724.c index af6e00148621..10fc92c05574 100644 --- a/sound/pci/ice1712/ice1724.c +++ b/sound/pci/ice1712/ice1724.c @@ -648,7 +648,7 @@ static int snd_vt1724_set_pro_rate(struct snd_ice1712 *ice, unsigned int rate, (inb(ICEMT1724(ice, DMA_PAUSE)) & DMA_PAUSES)) { /* running? we cannot change the rate now... */ spin_unlock_irqrestore(&ice->reg_lock, flags); - return -EBUSY; + return ((rate == ice->cur_rate) && !force) ? 0 : -EBUSY; } if (!force && is_pro_rate_locked(ice)) { spin_unlock_irqrestore(&ice->reg_lock, flags); @@ -1294,7 +1294,7 @@ static int __devinit snd_vt1724_pcm_spdif(struct snd_ice1712 *ice, int device) snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV, snd_dma_pci_data(ice->pci), - 64*1024, 64*1024); + 256*1024, 256*1024); ice->pcm = pcm; @@ -1408,7 +1408,7 @@ static int __devinit snd_vt1724_pcm_indep(struct snd_ice1712 *ice, int device) snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV, snd_dma_pci_data(ice->pci), - 64*1024, 64*1024); + 256*1024, 256*1024); ice->pcm_ds = pcm; @@ -2110,7 +2110,7 @@ static int snd_vt1724_pro_peak_get(struct snd_kcontrol *kcontrol, } static struct snd_kcontrol_new snd_vt1724_mixer_pro_peak __devinitdata = { - .iface = SNDRV_CTL_ELEM_IFACE_MIXER, + .iface = SNDRV_CTL_ELEM_IFACE_PCM, .name = "Multi Track Peak", .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, .info = snd_vt1724_pro_peak_info, diff --git a/sound/pci/ice1712/prodigy_hifi.c b/sound/pci/ice1712/prodigy_hifi.c index c75515f5be6f..6a9fee3ee78f 100644 --- a/sound/pci/ice1712/prodigy_hifi.c +++ b/sound/pci/ice1712/prodigy_hifi.c @@ -1100,7 +1100,7 @@ static void ak4396_init(struct snd_ice1712 *ice) } #ifdef CONFIG_PM -static int __devinit prodigy_hd2_resume(struct snd_ice1712 *ice) +static int prodigy_hd2_resume(struct snd_ice1712 *ice) { /* initialize ak4396 codec and restore previous mixer volumes */ struct prodigy_hifi_spec *spec = ice->spec; diff --git a/sound/pci/intel8x0.c b/sound/pci/intel8x0.c index 754867ed4785..aac20fb4aad2 100644 --- a/sound/pci/intel8x0.c +++ b/sound/pci/intel8x0.c @@ -1950,6 +1950,12 @@ static struct ac97_quirk ac97_quirks[] __devinitdata = { }, { .subvendor = 0x104d, + .subdevice = 0x8144, + .name = "Sony", + .type = AC97_TUNE_INV_EAPD + }, + { + .subvendor = 0x104d, .subdevice = 0x8197, .name = "Sony S1XP", .type = AC97_TUNE_INV_EAPD diff --git a/sound/pci/via82xx.c b/sound/pci/via82xx.c index acfa4760da49..8a332d2f615c 100644 --- a/sound/pci/via82xx.c +++ b/sound/pci/via82xx.c @@ -386,6 +386,7 @@ struct via82xx { struct snd_pcm *pcms[2]; struct snd_rawmidi *rmidi; + struct snd_kcontrol *dxs_controls[4]; struct snd_ac97_bus *ac97_bus; struct snd_ac97 *ac97; @@ -1216,9 +1217,9 @@ static int snd_via82xx_pcm_open(struct via82xx *chip, struct viadev *viadev, /* - * open callback for playback on via686 and via823x DSX + * open callback for playback on via686 */ -static int snd_via82xx_playback_open(struct snd_pcm_substream *substream) +static int snd_via686_playback_open(struct snd_pcm_substream *substream) { struct via82xx *chip = snd_pcm_substream_chip(substream); struct viadev *viadev = &chip->devs[chip->playback_devno + substream->number]; @@ -1230,6 +1231,32 @@ static int snd_via82xx_playback_open(struct snd_pcm_substream *substream) } /* + * open callback for playback on via823x DXS + */ +static int snd_via8233_playback_open(struct snd_pcm_substream *substream) +{ + struct via82xx *chip = snd_pcm_substream_chip(substream); + struct viadev *viadev; + unsigned int stream; + int err; + + viadev = &chip->devs[chip->playback_devno + substream->number]; + if ((err = snd_via82xx_pcm_open(chip, viadev, substream)) < 0) + return err; + stream = viadev->reg_offset / 0x10; + if (chip->dxs_controls[stream]) { + chip->playback_volume[stream][0] = 0; + chip->playback_volume[stream][1] = 0; + chip->dxs_controls[stream]->vd[0].access &= + ~SNDRV_CTL_ELEM_ACCESS_INACTIVE; + snd_ctl_notify(chip->card, SNDRV_CTL_EVENT_MASK_VALUE | + SNDRV_CTL_EVENT_MASK_INFO, + &chip->dxs_controls[stream]->id); + } + return 0; +} + +/* * open callback for playback on via823x multi-channel */ static int snd_via8233_multi_open(struct snd_pcm_substream *substream) @@ -1302,10 +1329,26 @@ static int snd_via82xx_pcm_close(struct snd_pcm_substream *substream) return 0; } +static int snd_via8233_playback_close(struct snd_pcm_substream *substream) +{ + struct via82xx *chip = snd_pcm_substream_chip(substream); + struct viadev *viadev = substream->runtime->private_data; + unsigned int stream; + + stream = viadev->reg_offset / 0x10; + if (chip->dxs_controls[stream]) { + chip->dxs_controls[stream]->vd[0].access |= + SNDRV_CTL_ELEM_ACCESS_INACTIVE; + snd_ctl_notify(chip->card, SNDRV_CTL_EVENT_MASK_INFO, + &chip->dxs_controls[stream]->id); + } + return snd_via82xx_pcm_close(substream); +} + /* via686 playback callbacks */ static struct snd_pcm_ops snd_via686_playback_ops = { - .open = snd_via82xx_playback_open, + .open = snd_via686_playback_open, .close = snd_via82xx_pcm_close, .ioctl = snd_pcm_lib_ioctl, .hw_params = snd_via82xx_hw_params, @@ -1331,8 +1374,8 @@ static struct snd_pcm_ops snd_via686_capture_ops = { /* via823x DSX playback callbacks */ static struct snd_pcm_ops snd_via8233_playback_ops = { - .open = snd_via82xx_playback_open, - .close = snd_via82xx_pcm_close, + .open = snd_via8233_playback_open, + .close = snd_via8233_playback_close, .ioctl = snd_pcm_lib_ioctl, .hw_params = snd_via82xx_hw_params, .hw_free = snd_via82xx_hw_free, @@ -1626,7 +1669,7 @@ static int snd_via8233_dxs_volume_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol) { struct via82xx *chip = snd_kcontrol_chip(kcontrol); - unsigned int idx = snd_ctl_get_ioff(kcontrol, &ucontrol->id); + unsigned int idx = kcontrol->id.subdevice; ucontrol->value.integer.value[0] = VIA_DXS_MAX_VOLUME - chip->playback_volume[idx][0]; ucontrol->value.integer.value[1] = VIA_DXS_MAX_VOLUME - chip->playback_volume[idx][1]; @@ -1646,7 +1689,7 @@ static int snd_via8233_dxs_volume_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol) { struct via82xx *chip = snd_kcontrol_chip(kcontrol); - unsigned int idx = snd_ctl_get_ioff(kcontrol, &ucontrol->id); + unsigned int idx = kcontrol->id.subdevice; unsigned long port = chip->port + 0x10 * idx; unsigned char val; int i, change = 0; @@ -1705,11 +1748,13 @@ static struct snd_kcontrol_new snd_via8233_pcmdxs_volume_control __devinitdata = }; static struct snd_kcontrol_new snd_via8233_dxs_volume_control __devinitdata = { - .name = "VIA DXS Playback Volume", - .iface = SNDRV_CTL_ELEM_IFACE_MIXER, - .access = (SNDRV_CTL_ELEM_ACCESS_READWRITE | - SNDRV_CTL_ELEM_ACCESS_TLV_READ), - .count = 4, + .iface = SNDRV_CTL_ELEM_IFACE_PCM, + .device = 0, + /* .subdevice set later */ + .name = "PCM Playback Volume", + .access = SNDRV_CTL_ELEM_ACCESS_READWRITE | + SNDRV_CTL_ELEM_ACCESS_TLV_READ | + SNDRV_CTL_ELEM_ACCESS_INACTIVE, .info = snd_via8233_dxs_volume_info, .get = snd_via8233_dxs_volume_get, .put = snd_via8233_dxs_volume_put, @@ -1936,10 +1981,19 @@ static int __devinit snd_via8233_init_misc(struct via82xx *chip) } else /* Using DXS when PCM emulation is enabled is really weird */ { - /* Standalone DXS controls */ - err = snd_ctl_add(chip->card, snd_ctl_new1(&snd_via8233_dxs_volume_control, chip)); - if (err < 0) - return err; + for (i = 0; i < 4; ++i) { + struct snd_kcontrol *kctl; + + kctl = snd_ctl_new1( + &snd_via8233_dxs_volume_control, chip); + if (!kctl) + return -ENOMEM; + kctl->id.subdevice = i; + err = snd_ctl_add(chip->card, kctl); + if (err < 0) + return err; + chip->dxs_controls[i] = kctl; + } } } /* select spdif data slot 10/11 */ diff --git a/sound/pcmcia/pdaudiocf/pdaudiocf.c b/sound/pcmcia/pdaudiocf/pdaudiocf.c index 7dea74b71cf1..64b859925c0b 100644 --- a/sound/pcmcia/pdaudiocf/pdaudiocf.c +++ b/sound/pcmcia/pdaudiocf/pdaudiocf.c @@ -217,20 +217,25 @@ static void snd_pdacf_detach(struct pcmcia_device *link) * configuration callback */ -#define CS_CHECK(fn, ret) \ -do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) - static int pdacf_config(struct pcmcia_device *link) { struct snd_pdacf *pdacf = link->priv; - int last_fn, last_ret; + int ret; snd_printdd(KERN_DEBUG "pdacf_config called\n"); link->conf.ConfigIndex = 0x5; - CS_CHECK(RequestIO, pcmcia_request_io(link, &link->io)); - CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); - CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf)); + ret = pcmcia_request_io(link, &link->io); + if (ret) + goto failed; + + ret = pcmcia_request_irq(link, &link->irq); + if (ret) + goto failed; + + ret = pcmcia_request_configuration(link, &link->conf); + if (ret) + goto failed; if (snd_pdacf_assign_resources(pdacf, link->io.BasePort1, link->irq.AssignedIRQ) < 0) goto failed; @@ -238,8 +243,6 @@ static int pdacf_config(struct pcmcia_device *link) link->dev_node = &pdacf->node; return 0; -cs_failed: - cs_error(link, last_fn, last_ret); failed: pcmcia_disable_device(link); return -ENODEV; diff --git a/sound/pcmcia/vx/vxpocket.c b/sound/pcmcia/vx/vxpocket.c index 7445cc8a47d3..1492744ad67f 100644 --- a/sound/pcmcia/vx/vxpocket.c +++ b/sound/pcmcia/vx/vxpocket.c @@ -213,14 +213,11 @@ static int snd_vxpocket_assign_resources(struct vx_core *chip, int port, int irq * configuration callback */ -#define CS_CHECK(fn, ret) \ -do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) - static int vxpocket_config(struct pcmcia_device *link) { struct vx_core *chip = link->priv; struct snd_vxpocket *vxp = (struct snd_vxpocket *)chip; - int last_fn, last_ret; + int ret; snd_printdd(KERN_DEBUG "vxpocket_config called\n"); @@ -235,9 +232,17 @@ static int vxpocket_config(struct pcmcia_device *link) strcpy(chip->card->driver, vxp440_hw.name); } - CS_CHECK(RequestIO, pcmcia_request_io(link, &link->io)); - CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); - CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf)); + ret = pcmcia_request_io(link, &link->io); + if (ret) + goto failed; + + ret = pcmcia_request_irq(link, &link->irq); + if (ret) + goto failed; + + ret = pcmcia_request_configuration(link, &link->conf); + if (ret) + goto failed; chip->dev = &handle_to_dev(link); snd_card_set_dev(chip->card, chip->dev); @@ -248,8 +253,6 @@ static int vxpocket_config(struct pcmcia_device *link) link->dev_node = &vxp->node; return 0; -cs_failed: - cs_error(link, last_fn, last_ret); failed: pcmcia_disable_device(link); return -ENODEV; diff --git a/sound/ppc/Kconfig b/sound/ppc/Kconfig index bd2338ab2ced..0519c60f5be1 100644 --- a/sound/ppc/Kconfig +++ b/sound/ppc/Kconfig @@ -2,7 +2,7 @@ menuconfig SND_PPC bool "PowerPC sound devices" - depends on PPC64 || PPC32 + depends on PPC default y help Support for sound devices specific to PowerPC architectures. diff --git a/sound/sh/aica.c b/sound/sh/aica.c index 583a3693df75..a0df401ebb9f 100644 --- a/sound/sh/aica.c +++ b/sound/sh/aica.c @@ -49,6 +49,7 @@ MODULE_AUTHOR("Adrian McMenamin <adrian@mcmen.demon.co.uk>"); MODULE_DESCRIPTION("Dreamcast AICA sound (pcm) driver"); MODULE_LICENSE("GPL"); MODULE_SUPPORTED_DEVICE("{{Yamaha/SEGA, AICA}}"); +MODULE_FIRMWARE("aica_firmware.bin"); /* module parameters */ #define CARD_NAME "AICA" diff --git a/sound/soc/codecs/tlv320aic23.c b/sound/soc/codecs/tlv320aic23.c index 0b8dcb5cd729..6b24d8bb02bb 100644 --- a/sound/soc/codecs/tlv320aic23.c +++ b/sound/soc/codecs/tlv320aic23.c @@ -265,8 +265,8 @@ static const int bosr_usb_divisor_table[] = { #define UPPER_GROUP ((1<<8) | (1<<9) | (1<<10) | (1<<11) | (1<<15)) static const unsigned short sr_valid_mask[] = { LOWER_GROUP|UPPER_GROUP, /* Normal, bosr - 0*/ - LOWER_GROUP|UPPER_GROUP, /* Normal, bosr - 1*/ LOWER_GROUP, /* Usb, bosr - 0*/ + LOWER_GROUP|UPPER_GROUP, /* Normal, bosr - 1*/ UPPER_GROUP, /* Usb, bosr - 1*/ }; /* diff --git a/sound/soc/codecs/wm8350.c b/sound/soc/codecs/wm8350.c index 3ff0373dff89..593d5b9c9f03 100644 --- a/sound/soc/codecs/wm8350.c +++ b/sound/soc/codecs/wm8350.c @@ -579,7 +579,7 @@ static const struct snd_kcontrol_new wm8350_left_capt_mixer_controls[] = { SOC_DAPM_SINGLE_TLV("L3 Capture Volume", WM8350_INPUT_MIXER_VOLUME_L, 9, 7, 0, out_mix_tlv), SOC_DAPM_SINGLE("PGA Capture Switch", - WM8350_LEFT_INPUT_VOLUME, 14, 1, 0), + WM8350_LEFT_INPUT_VOLUME, 14, 1, 1), }; /* Right Input Mixer */ @@ -589,7 +589,7 @@ static const struct snd_kcontrol_new wm8350_right_capt_mixer_controls[] = { SOC_DAPM_SINGLE_TLV("L3 Capture Volume", WM8350_INPUT_MIXER_VOLUME_R, 13, 7, 0, out_mix_tlv), SOC_DAPM_SINGLE("PGA Capture Switch", - WM8350_RIGHT_INPUT_VOLUME, 14, 1, 0), + WM8350_RIGHT_INPUT_VOLUME, 14, 1, 1), }; /* Left Mic Mixer */ diff --git a/sound/soc/codecs/wm8940.c b/sound/soc/codecs/wm8940.c index da97aae475a2..1ef2454c5205 100644 --- a/sound/soc/codecs/wm8940.c +++ b/sound/soc/codecs/wm8940.c @@ -790,7 +790,7 @@ static int wm8940_register(struct wm8940_priv *wm8940, codec->reg_cache = &wm8940->reg_cache; ret = snd_soc_codec_set_cache_io(codec, 8, 16, control); - if (ret == 0) { + if (ret < 0) { dev_err(codec->dev, "Failed to set cache I/O: %d\n", ret); return ret; } diff --git a/sound/soc/imx/mxc-ssi.c b/sound/soc/imx/mxc-ssi.c index 3806ff2c0cd4..ccdefe60e752 100644 --- a/sound/soc/imx/mxc-ssi.c +++ b/sound/soc/imx/mxc-ssi.c @@ -397,14 +397,6 @@ static int imx_ssi_set_dai_fmt(struct snd_soc_dai *cpu_dai, break; } - /* sync */ - if (!(fmt & SND_SOC_DAIFMT_ASYNC)) - scr |= SSI_SCR_SYN; - - /* tdm - only for stereo atm */ - if (fmt & SND_SOC_DAIFMT_TDM) - scr |= SSI_SCR_NET; - if (cpu_dai->id == IMX_DAI_SSI0 || cpu_dai->id == IMX_DAI_SSI2) { SSI1_STCR = stcr; SSI1_SRCR = srcr; diff --git a/sound/soc/omap/Kconfig b/sound/soc/omap/Kconfig index 2dee9839be86..653a362425df 100644 --- a/sound/soc/omap/Kconfig +++ b/sound/soc/omap/Kconfig @@ -21,7 +21,18 @@ config SND_OMAP_SOC_AMS_DELTA select SND_OMAP_SOC_MCBSP select SND_SOC_CX20442 help - Say Y if you want to add support for SoC audio on Amstrad Delta. + Say Y if you want to add support for SoC audio device connected to + a handset and a speakerphone found on Amstrad E3 (Delta) videophone. + + Note that in order to get those devices fully supported, you have to + build the kernel with standard serial port driver included and + configured for at least 4 ports. Then, from userspace, you must load + a line discipline #19 on the modem (ttyS3) serial line. The simplest + way to achieve this is to install util-linux-ng and use the included + ldattach utility. This can be started automatically from udev, + a simple rule like this one should do the trick (it does for me): + ACTION=="add", KERNEL=="controlC0", \ + RUN+="/usr/sbin/ldattach 19 /dev/ttyS3" config SND_OMAP_SOC_OSK5912 tristate "SoC Audio support for omap osk5912" diff --git a/sound/soc/omap/omap-pcm.c b/sound/soc/omap/omap-pcm.c index 5735945788bf..6a829eef2a4f 100644 --- a/sound/soc/omap/omap-pcm.c +++ b/sound/soc/omap/omap-pcm.c @@ -195,8 +195,12 @@ static int omap_pcm_prepare(struct snd_pcm_substream *substream) else omap_enable_dma_irq(prtd->dma_ch, OMAP_DMA_FRAME_IRQ); - omap_set_dma_src_burst_mode(prtd->dma_ch, OMAP_DMA_DATA_BURST_16); - omap_set_dma_dest_burst_mode(prtd->dma_ch, OMAP_DMA_DATA_BURST_16); + if (!(cpu_class_is_omap1())) { + omap_set_dma_src_burst_mode(prtd->dma_ch, + OMAP_DMA_DATA_BURST_16); + omap_set_dma_dest_burst_mode(prtd->dma_ch, + OMAP_DMA_DATA_BURST_16); + } return 0; } diff --git a/sound/soc/omap/omap3evm.c b/sound/soc/omap/omap3evm.c index 9114c263077b..13aa380de162 100644 --- a/sound/soc/omap/omap3evm.c +++ b/sound/soc/omap/omap3evm.c @@ -144,4 +144,4 @@ module_exit(omap3evm_soc_exit); MODULE_AUTHOR("Anuj Aggarwal <anuj.aggarwal@ti.com>"); MODULE_DESCRIPTION("ALSA SoC OMAP3 EVM"); -MODULE_LICENSE("GPLv2"); +MODULE_LICENSE("GPL v2"); diff --git a/sound/soc/omap/omap3pandora.c b/sound/soc/omap/omap3pandora.c index ad219aaf7cb8..0cd06f5dd356 100644 --- a/sound/soc/omap/omap3pandora.c +++ b/sound/soc/omap/omap3pandora.c @@ -134,7 +134,7 @@ static int omap3pandora_hp_event(struct snd_soc_dapm_widget *w, * |P| <--- TWL4030 <--------- Line In and MICs */ static const struct snd_soc_dapm_widget omap3pandora_out_dapm_widgets[] = { - SND_SOC_DAPM_DAC("PCM DAC", "Playback", SND_SOC_NOPM, 0, 0), + SND_SOC_DAPM_DAC("PCM DAC", "HiFi Playback", SND_SOC_NOPM, 0, 0), SND_SOC_DAPM_PGA_E("Headphone Amplifier", SND_SOC_NOPM, 0, 0, NULL, 0, omap3pandora_hp_event, SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD), @@ -181,6 +181,7 @@ static int omap3pandora_out_init(struct snd_soc_codec *codec) snd_soc_dapm_nc_pin(codec, "CARKITR"); snd_soc_dapm_nc_pin(codec, "HFL"); snd_soc_dapm_nc_pin(codec, "HFR"); + snd_soc_dapm_nc_pin(codec, "VIBRA"); ret = snd_soc_dapm_new_controls(codec, omap3pandora_out_dapm_widgets, ARRAY_SIZE(omap3pandora_out_dapm_widgets)); diff --git a/sound/soc/s3c24xx/s3c24xx-pcm.c b/sound/soc/s3c24xx/s3c24xx-pcm.c index 5cbbdc80fde3..1f35c6fcf5fd 100644 --- a/sound/soc/s3c24xx/s3c24xx-pcm.c +++ b/sound/soc/s3c24xx/s3c24xx-pcm.c @@ -75,11 +75,19 @@ static void s3c24xx_pcm_enqueue(struct snd_pcm_substream *substream) { struct s3c24xx_runtime_data *prtd = substream->runtime->private_data; dma_addr_t pos = prtd->dma_pos; + unsigned int limit; int ret; pr_debug("Entered %s\n", __func__); - while (prtd->dma_loaded < prtd->dma_limit) { + if (s3c_dma_has_circular()) { + limit = (prtd->dma_end - prtd->dma_start) / prtd->dma_period; + } else + limit = prtd->dma_limit; + + pr_debug("%s: loaded %d, limit %d\n", __func__, prtd->dma_loaded, limit); + + while (prtd->dma_loaded < limit) { unsigned long len = prtd->dma_period; pr_debug("dma_loaded: %d\n", prtd->dma_loaded); @@ -123,7 +131,7 @@ static void s3c24xx_audio_buffdone(struct s3c2410_dma_chan *channel, snd_pcm_period_elapsed(substream); spin_lock(&prtd->lock); - if (prtd->state & ST_RUNNING) { + if (prtd->state & ST_RUNNING && !s3c_dma_has_circular()) { prtd->dma_loaded--; s3c24xx_pcm_enqueue(substream); } @@ -164,6 +172,11 @@ static int s3c24xx_pcm_hw_params(struct snd_pcm_substream *substream, printk(KERN_ERR "failed to get dma channel\n"); return ret; } + + /* use the circular buffering if we have it available. */ + if (s3c_dma_has_circular()) + s3c2410_dma_setflags(prtd->params->channel, + S3C2410_DMAF_CIRCULAR); } s3c2410_dma_set_buffdone_fn(prtd->params->channel, diff --git a/sound/soc/s3c24xx/s3c64xx-i2s.c b/sound/soc/s3c24xx/s3c64xx-i2s.c index 3c06c401d0fb..105a77eeded0 100644 --- a/sound/soc/s3c24xx/s3c64xx-i2s.c +++ b/sound/soc/s3c24xx/s3c64xx-i2s.c @@ -220,6 +220,8 @@ static __devinit int s3c64xx_iis_dev_probe(struct platform_device *pdev) goto err; } + clk_enable(i2s->iis_cclk); + ret = s3c_i2sv2_probe(pdev, dai, i2s, 0); if (ret) goto err_clk; diff --git a/sound/soc/soc-core.c b/sound/soc/soc-core.c index 7ff04ad2a97e..0a1b2f64bbee 100644 --- a/sound/soc/soc-core.c +++ b/sound/soc/soc-core.c @@ -834,6 +834,9 @@ EXPORT_SYMBOL_GPL(snd_soc_resume_device); #define soc_resume NULL #endif +static struct snd_soc_dai_ops null_dai_ops = { +}; + static void snd_soc_instantiate_card(struct snd_soc_card *card) { struct platform_device *pdev = container_of(card->dev, @@ -877,6 +880,11 @@ static void snd_soc_instantiate_card(struct snd_soc_card *card) ac97 = 1; } + for (i = 0; i < card->num_links; i++) { + if (!card->dai_link[i].codec_dai->ops) + card->dai_link[i].codec_dai->ops = &null_dai_ops; + } + /* If we have AC97 in the system then don't wait for the * codec. This will need revisiting if we have to handle * systems with mixed AC97 and non-AC97 parts. Only check for @@ -2329,9 +2337,6 @@ static int snd_soc_unregister_card(struct snd_soc_card *card) return 0; } -static struct snd_soc_dai_ops null_dai_ops = { -}; - /** * snd_soc_register_dai - Register a DAI with the ASoC core * diff --git a/sound/soc/soc-dapm.c b/sound/soc/soc-dapm.c index f79711b9fa5b..d89f6dc00908 100644 --- a/sound/soc/soc-dapm.c +++ b/sound/soc/soc-dapm.c @@ -524,7 +524,7 @@ static int is_connected_output_ep(struct snd_soc_dapm_widget *widget) /* connected jack or spk ? */ if (widget->id == snd_soc_dapm_hp || widget->id == snd_soc_dapm_spk || - widget->id == snd_soc_dapm_line) + (widget->id == snd_soc_dapm_line && !list_empty(&widget->sources))) return 1; } @@ -573,7 +573,8 @@ static int is_connected_input_ep(struct snd_soc_dapm_widget *widget) return 1; /* connected jack ? */ - if (widget->id == snd_soc_dapm_mic || widget->id == snd_soc_dapm_line) + if (widget->id == snd_soc_dapm_mic || + (widget->id == snd_soc_dapm_line && !list_empty(&widget->sinks))) return 1; } @@ -2071,9 +2072,9 @@ int snd_soc_dapm_stream_event(struct snd_soc_codec *codec, } } } - mutex_unlock(&codec->mutex); dapm_power_widgets(codec, event); + mutex_unlock(&codec->mutex); dump_dapm(codec, __func__); return 0; } diff --git a/sound/usb/caiaq/audio.c b/sound/usb/caiaq/audio.c index 121af0644fd9..86b2c3b92df5 100644 --- a/sound/usb/caiaq/audio.c +++ b/sound/usb/caiaq/audio.c @@ -62,10 +62,14 @@ static void activate_substream(struct snd_usb_caiaqdev *dev, struct snd_pcm_substream *sub) { + spin_lock(&dev->spinlock); + if (sub->stream == SNDRV_PCM_STREAM_PLAYBACK) dev->sub_playback[sub->number] = sub; else dev->sub_capture[sub->number] = sub; + + spin_unlock(&dev->spinlock); } static void @@ -269,16 +273,22 @@ snd_usb_caiaq_pcm_pointer(struct snd_pcm_substream *sub) { int index = sub->number; struct snd_usb_caiaqdev *dev = snd_pcm_substream_chip(sub); + snd_pcm_uframes_t ptr; + + spin_lock(&dev->spinlock); if (dev->input_panic || dev->output_panic) - return SNDRV_PCM_POS_XRUN; + ptr = SNDRV_PCM_POS_XRUN; if (sub->stream == SNDRV_PCM_STREAM_PLAYBACK) - return bytes_to_frames(sub->runtime, + ptr = bytes_to_frames(sub->runtime, dev->audio_out_buf_pos[index]); else - return bytes_to_frames(sub->runtime, + ptr = bytes_to_frames(sub->runtime, dev->audio_in_buf_pos[index]); + + spin_unlock(&dev->spinlock); + return ptr; } /* operators for both playback and capture */ diff --git a/sound/usb/caiaq/device.c b/sound/usb/caiaq/device.c index 83e6c1312d47..a3f02dd97440 100644 --- a/sound/usb/caiaq/device.c +++ b/sound/usb/caiaq/device.c @@ -35,7 +35,7 @@ #include "input.h" MODULE_AUTHOR("Daniel Mack <daniel@caiaq.de>"); -MODULE_DESCRIPTION("caiaq USB audio, version 1.3.19"); +MODULE_DESCRIPTION("caiaq USB audio, version 1.3.20"); MODULE_LICENSE("GPL"); MODULE_SUPPORTED_DEVICE("{{Native Instruments, RigKontrol2}," "{Native Instruments, RigKontrol3}," diff --git a/sound/usb/usbaudio.h b/sound/usb/usbaudio.h index 8e7f78941ba6..e9a3a9dca15c 100644 --- a/sound/usb/usbaudio.h +++ b/sound/usb/usbaudio.h @@ -210,7 +210,7 @@ struct snd_usb_midi_endpoint_info { /* */ -#define combine_word(s) ((*s) | ((unsigned int)(s)[1] << 8)) +#define combine_word(s) ((*(s)) | ((unsigned int)(s)[1] << 8)) #define combine_triple(s) (combine_word(s) | ((unsigned int)(s)[2] << 16)) #define combine_quad(s) (combine_triple(s) | ((unsigned int)(s)[3] << 24)) diff --git a/sound/usb/usbmixer.c b/sound/usb/usbmixer.c index 9efcfd08d747..c998220b99c6 100644 --- a/sound/usb/usbmixer.c +++ b/sound/usb/usbmixer.c @@ -1071,6 +1071,15 @@ static int parse_audio_feature_unit(struct mixer_build *state, int unitid, unsig channels = (ftr[0] - 7) / csize - 1; master_bits = snd_usb_combine_bytes(ftr + 6, csize); + /* master configuration quirks */ + switch (state->chip->usb_id) { + case USB_ID(0x08bb, 0x2702): + snd_printk(KERN_INFO + "usbmixer: master volume quirk for PCM2702 chip\n"); + /* disable non-functional volume control */ + master_bits &= ~(1 << (USB_FEATURE_VOLUME - 1)); + break; + } if (channels > 0) first_ch_bits = snd_usb_combine_bytes(ftr + 6 + csize, csize); else diff --git a/tools/perf/Documentation/perf-timechart.txt b/tools/perf/Documentation/perf-timechart.txt index 1c2ed3090cce..a7910099d6fd 100644 --- a/tools/perf/Documentation/perf-timechart.txt +++ b/tools/perf/Documentation/perf-timechart.txt @@ -31,6 +31,9 @@ OPTIONS -w:: --width=:: Select the width of the SVG file (default: 1000) +-p:: +--power-only:: + Only output the CPU power section of the diagram SEE ALSO diff --git a/tools/perf/Makefile b/tools/perf/Makefile index b5f1953b6144..7e190d522cd5 100644 --- a/tools/perf/Makefile +++ b/tools/perf/Makefile @@ -157,11 +157,18 @@ uname_R := $(shell sh -c 'uname -r 2>/dev/null || echo not') uname_P := $(shell sh -c 'uname -p 2>/dev/null || echo not') uname_V := $(shell sh -c 'uname -v 2>/dev/null || echo not') -# If we're on a 64-bit kernel, use -m64 -ifndef NO_64BIT - ifneq ($(patsubst %64,%,$(uname_M)),$(uname_M)) - M64 := -m64 - endif +# +# Add -m32 for cross-builds: +# +ifdef NO_64BIT + MBITS := -m32 +else + # + # If we're on a 64-bit kernel, use -m64: + # + ifneq ($(patsubst %64,%,$(uname_M)),$(uname_M)) + MBITS := -m64 + endif endif # CFLAGS and LDFLAGS are for the users to override from the command line. @@ -170,8 +177,7 @@ endif # Include saner warnings here, which can catch bugs: # -EXTRA_WARNINGS := -Wcast-align -EXTRA_WARNINGS := $(EXTRA_WARNINGS) -Wformat +EXTRA_WARNINGS := -Wformat EXTRA_WARNINGS := $(EXTRA_WARNINGS) -Wformat-security EXTRA_WARNINGS := $(EXTRA_WARNINGS) -Wformat-y2k EXTRA_WARNINGS := $(EXTRA_WARNINGS) -Wshadow @@ -194,7 +200,7 @@ EXTRA_WARNINGS := $(EXTRA_WARNINGS) -Wold-style-definition EXTRA_WARNINGS := $(EXTRA_WARNINGS) -Wstrict-prototypes EXTRA_WARNINGS := $(EXTRA_WARNINGS) -Wdeclaration-after-statement -CFLAGS = $(M64) -ggdb3 -Wall -Wextra -std=gnu99 -Werror -O6 -fstack-protector-all -D_FORTIFY_SOURCE=2 $(EXTRA_WARNINGS) +CFLAGS = $(MBITS) -ggdb3 -Wall -Wextra -std=gnu99 -Werror -O6 -fstack-protector-all -D_FORTIFY_SOURCE=2 $(EXTRA_WARNINGS) LDFLAGS = -lpthread -lrt -lelf -lm ALL_CFLAGS = $(CFLAGS) ALL_LDFLAGS = $(LDFLAGS) @@ -415,8 +421,12 @@ ifeq ($(uname_S),Darwin) PTHREAD_LIBS = endif -ifneq ($(shell sh -c "(echo '\#include <libelf.h>'; echo 'int main(void) { Elf * elf = elf_begin(0, ELF_C_READ_MMAP, 0); return (long)elf; }') | $(CC) -x c - $(ALL_CFLAGS) -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 -o /dev/null $(ALL_LDFLAGS) > /dev/null 2>&1 && echo y"), y) - msg := $(error No libelf.h/libelf found, please install libelf-dev/elfutils-libelf-devel); +ifeq ($(shell sh -c "(echo '\#include <libelf.h>'; echo 'int main(void) { Elf * elf = elf_begin(0, ELF_C_READ, 0); return (long)elf; }') | $(CC) -x c - $(ALL_CFLAGS) -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 -o /dev/null $(ALL_LDFLAGS) > /dev/null 2>&1 && echo y"), y) + ifneq ($(shell sh -c "(echo '\#include <libelf.h>'; echo 'int main(void) { Elf * elf = elf_begin(0, ELF_C_READ_MMAP, 0); return (long)elf; }') | $(CC) -x c - $(ALL_CFLAGS) -D_LARGEFILE64_SOURCE -D_FILE_OFFSET_BITS=64 -o /dev/null $(ALL_LDFLAGS) > /dev/null 2>&1 && echo y"), y) + BASIC_CFLAGS += -DLIBELF_NO_MMAP + endif +else + msg := $(error No libelf.h/libelf found, please install libelf-dev/elfutils-libelf-devel and glibc-dev[el]); endif ifdef NO_DEMANGLE @@ -728,7 +738,7 @@ $(BUILT_INS): perf$X common-cmds.h: util/generate-cmdlist.sh command-list.txt common-cmds.h: $(wildcard Documentation/perf-*.txt) - $(QUIET_GEN)util/generate-cmdlist.sh > $@+ && mv $@+ $@ + $(QUIET_GEN). util/generate-cmdlist.sh > $@+ && mv $@+ $@ $(patsubst %.sh,%,$(SCRIPT_SH)) : % : %.sh $(QUIET_GEN)$(RM) $@ $@+ && \ diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c index a5a050af8e7d..a4be453fc8a9 100644 --- a/tools/perf/builtin-record.c +++ b/tools/perf/builtin-record.c @@ -41,6 +41,7 @@ static int raw_samples = 0; static int system_wide = 0; static int profile_cpu = -1; static pid_t target_pid = -1; +static pid_t child_pid = -1; static int inherit = 1; static int force = 0; static int append_file = 0; @@ -184,6 +185,9 @@ static void sig_handler(int sig) static void sig_atexit(void) { + if (child_pid != -1) + kill(child_pid, SIGTERM); + if (signr == -1) return; @@ -422,7 +426,7 @@ try_again: if (fd[nr_cpu][counter] < 0) { int err = errno; - if (err == EPERM) + if (err == EPERM || err == EACCES) die("Permission error - are you root?\n"); else if (err == ENODEV && profile_cpu != -1) die("No such device - did you specify an out-of-range profile CPU?\n"); @@ -610,6 +614,8 @@ static int __cmd_record(int argc, const char **argv) exit(-1); } } + + child_pid = pid; } if (realtime_prio) { diff --git a/tools/perf/builtin-sched.c b/tools/perf/builtin-sched.c index ea9c15c0cdfe..ce2d5be4f30e 100644 --- a/tools/perf/builtin-sched.c +++ b/tools/perf/builtin-sched.c @@ -1287,7 +1287,7 @@ static struct sort_dimension *available_sorts[] = { static LIST_HEAD(sort_list); -static int sort_dimension__add(char *tok, struct list_head *list) +static int sort_dimension__add(const char *tok, struct list_head *list) { int i; @@ -1917,7 +1917,7 @@ static void setup_sorting(void) free(str); - sort_dimension__add((char *)"pid", &cmp_pid); + sort_dimension__add("pid", &cmp_pid); } static const char *record_args[] = { diff --git a/tools/perf/builtin-stat.c b/tools/perf/builtin-stat.c index e5f6ece65a13..3db31e7bf173 100644 --- a/tools/perf/builtin-stat.c +++ b/tools/perf/builtin-stat.c @@ -69,7 +69,8 @@ static int run_idx = 0; static int run_count = 1; static int inherit = 1; static int scale = 1; -static int target_pid = -1; +static pid_t target_pid = -1; +static pid_t child_pid = -1; static int null_run = 0; static int fd[MAX_NR_CPUS][MAX_COUNTERS]; @@ -285,6 +286,8 @@ static int run_perf_stat(int argc __used, const char **argv) exit(-1); } + child_pid = pid; + /* * Wait for the child to be ready to exec. */ @@ -433,6 +436,9 @@ static void skip_signal(int signo) static void sig_atexit(void) { + if (child_pid != -1) + kill(child_pid, SIGTERM); + if (signr == -1) return; diff --git a/tools/perf/builtin-timechart.c b/tools/perf/builtin-timechart.c index 4405681b3134..e8a510d935e5 100644 --- a/tools/perf/builtin-timechart.c +++ b/tools/perf/builtin-timechart.c @@ -46,6 +46,8 @@ static u64 turbo_frequency; static u64 first_time, last_time; +static int power_only; + static struct perf_header *header; @@ -547,7 +549,7 @@ static void end_sample_processing(void) u64 cpu; struct power_event *pwr; - for (cpu = 0; cpu < numcpus; cpu++) { + for (cpu = 0; cpu <= numcpus; cpu++) { pwr = malloc(sizeof(struct power_event)); if (!pwr) return; @@ -763,19 +765,40 @@ static void draw_wakeups(void) if (c->Y && c->start_time <= we->time && c->end_time >= we->time) { if (p->pid == we->waker) { from = c->Y; - task_from = c->comm; + task_from = strdup(c->comm); } if (p->pid == we->wakee) { to = c->Y; - task_to = c->comm; + task_to = strdup(c->comm); } } c = c->next; } + c = p->all; + while (c) { + if (p->pid == we->waker && !from) { + from = c->Y; + task_from = strdup(c->comm); + } + if (p->pid == we->wakee && !to) { + to = c->Y; + task_to = strdup(c->comm); + } + c = c->next; + } } p = p->next; } + if (!task_from) { + task_from = malloc(40); + sprintf(task_from, "[%i]", we->waker); + } + if (!task_to) { + task_to = malloc(40); + sprintf(task_to, "[%i]", we->wakee); + } + if (we->waker == -1) svg_interrupt(we->time, to); else if (from && to && abs(from - to) == 1) @@ -783,6 +806,9 @@ static void draw_wakeups(void) else svg_partial_wakeline(we->time, from, task_from, to, task_to); we = we->next; + + free(task_from); + free(task_to); } } @@ -871,7 +897,7 @@ static int determine_display_tasks(u64 threshold) /* no exit marker, task kept running to the end */ if (p->end_time == 0) p->end_time = last_time; - if (p->total_time >= threshold) + if (p->total_time >= threshold && !power_only) p->display = 1; c = p->all; @@ -882,7 +908,7 @@ static int determine_display_tasks(u64 threshold) if (c->start_time == 1) c->start_time = first_time; - if (c->total_time >= threshold) { + if (c->total_time >= threshold && !power_only) { c->display = 1; count++; } @@ -1134,6 +1160,8 @@ static const struct option options[] = { "output file name"), OPT_INTEGER('w', "width", &svg_page_width, "page width"), + OPT_BOOLEAN('p', "power-only", &power_only, + "output power data only"), OPT_END() }; diff --git a/tools/perf/builtin-top.c b/tools/perf/builtin-top.c index 1ca88896eee4..e23bc74e734f 100644 --- a/tools/perf/builtin-top.c +++ b/tools/perf/builtin-top.c @@ -686,6 +686,8 @@ static void handle_keypress(int c) switch (c) { case 'd': prompt_integer(&delay_secs, "Enter display delay"); + if (delay_secs < 1) + delay_secs = 1; break; case 'e': prompt_integer(&print_entries, "Enter display entries (lines)"); @@ -782,6 +784,7 @@ static const char *skip_symbols[] = { "exit_idle", "mwait_idle", "mwait_idle_with_hints", + "poll_idle", "ppc64_runlatch_off", "pseries_dedicated_idle_sleep", NULL @@ -1024,7 +1027,7 @@ try_again: if (fd[i][counter] < 0) { int err = errno; - if (err == EPERM) + if (err == EPERM || err == EACCES) die("No permission - are you root?\n"); /* * If it's cycles then fall back to hrtimer diff --git a/tools/perf/builtin-trace.c b/tools/perf/builtin-trace.c index e9d256e2f47d..0c5e4f72f2ba 100644 --- a/tools/perf/builtin-trace.c +++ b/tools/perf/builtin-trace.c @@ -219,10 +219,6 @@ remap: more: event = (event_t *)(buf + head); - size = event->header.size; - if (!size) - size = 8; - if (head + event->header.size >= page_size * mmap_window) { unsigned long shift = page_size * (head / page_size); int res; @@ -237,7 +233,6 @@ more: size = event->header.size; - if (!size || process_event(event, offset, head) < 0) { /* @@ -290,7 +285,6 @@ int cmd_trace(int argc, const char **argv, const char *prefix __used) usage_with_options(annotate_usage, options); } - setup_pager(); return __cmd_trace(); diff --git a/tools/perf/design.txt b/tools/perf/design.txt index f1946d107b10..fdd42a824c98 100644 --- a/tools/perf/design.txt +++ b/tools/perf/design.txt @@ -455,3 +455,6 @@ will need at least this: If your architecture does have hardware capabilities, you can override the weak stub hw_perf_event_init() to register hardware counters. + +Architectures that have d-cache aliassing issues, such as Sparc and ARM, +should select PERF_USE_VMALLOC in order to avoid these for perf mmap(). diff --git a/tools/perf/util/PERF-VERSION-GEN b/tools/perf/util/PERF-VERSION-GEN index c561d1538c03..54552a00a117 100755 --- a/tools/perf/util/PERF-VERSION-GEN +++ b/tools/perf/util/PERF-VERSION-GEN @@ -1,7 +1,7 @@ #!/bin/sh GVF=PERF-VERSION-FILE -DEF_VER=v0.0.1.PERF +DEF_VER=v0.0.2.PERF LF=' ' diff --git a/tools/perf/util/parse-events.c b/tools/perf/util/parse-events.c index 87c424de79ee..8cfb48cbbea0 100644 --- a/tools/perf/util/parse-events.c +++ b/tools/perf/util/parse-events.c @@ -691,7 +691,10 @@ static void store_event_type(const char *orgname) FILE *file; int id; - sprintf(filename, "/sys/kernel/debug/tracing/events/%s/id", orgname); + sprintf(filename, "%s/", debugfs_path); + strncat(filename, orgname, strlen(orgname)); + strcat(filename, "/id"); + c = strchr(filename, ':'); if (c) *c = '/'; diff --git a/tools/perf/util/svghelper.c b/tools/perf/util/svghelper.c index a778fd0f4ae4..b3637db025a2 100644 --- a/tools/perf/util/svghelper.c +++ b/tools/perf/util/svghelper.c @@ -28,7 +28,7 @@ static u64 turbo_frequency, max_freq; int svg_page_width = 1000; -#define MIN_TEXT_SIZE 0.001 +#define MIN_TEXT_SIZE 0.01 static u64 total_height; static FILE *svgfile; @@ -103,7 +103,7 @@ void open_svg(const char *filename, int cpus, int rows, u64 start, u64 end) fprintf(svgfile, " rect.process2 { fill:rgb(180,180,180); fill-opacity:0.9; stroke-width:0; stroke:rgb( 0, 0, 0); } \n"); fprintf(svgfile, " rect.sample { fill:rgb( 0, 0,255); fill-opacity:0.8; stroke-width:0; stroke:rgb( 0, 0, 0); } \n"); fprintf(svgfile, " rect.blocked { fill:rgb(255, 0, 0); fill-opacity:0.5; stroke-width:0; stroke:rgb( 0, 0, 0); } \n"); - fprintf(svgfile, " rect.waiting { fill:rgb(214,214, 0); fill-opacity:0.3; stroke-width:0; stroke:rgb( 0, 0, 0); } \n"); + fprintf(svgfile, " rect.waiting { fill:rgb(224,214, 0); fill-opacity:0.8; stroke-width:0; stroke:rgb( 0, 0, 0); } \n"); fprintf(svgfile, " rect.WAITING { fill:rgb(255,214, 48); fill-opacity:0.6; stroke-width:0; stroke:rgb( 0, 0, 0); } \n"); fprintf(svgfile, " rect.cpu { fill:rgb(192,192,192); fill-opacity:0.2; stroke-width:0.5; stroke:rgb(128,128,128); } \n"); fprintf(svgfile, " rect.pstate { fill:rgb(128,128,128); fill-opacity:0.8; stroke-width:0; } \n"); @@ -217,6 +217,18 @@ static char *cpu_model(void) } fclose(file); } + + /* CPU type */ + file = fopen("/sys/devices/system/cpu/cpu0/cpufreq/scaling_available_frequencies", "r"); + if (file) { + while (fgets(buf, 255, file)) { + unsigned int freq; + freq = strtoull(buf, NULL, 10); + if (freq > max_freq) + max_freq = freq; + } + fclose(file); + } return cpu_m; } diff --git a/tools/perf/util/symbol.c b/tools/perf/util/symbol.c index 559fb06210f5..226f44a2357d 100644 --- a/tools/perf/util/symbol.c +++ b/tools/perf/util/symbol.c @@ -324,8 +324,7 @@ static inline int elf_sym__is_function(const GElf_Sym *sym) { return elf_sym__type(sym) == STT_FUNC && sym->st_name != 0 && - sym->st_shndx != SHN_UNDEF && - sym->st_size != 0; + sym->st_shndx != SHN_UNDEF; } static inline int elf_sym__is_label(const GElf_Sym *sym) @@ -414,7 +413,7 @@ static int dso__synthesize_plt_symbols(struct dso *self, int v) if (fd < 0) goto out; - elf = elf_begin(fd, ELF_C_READ_MMAP, NULL); + elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL); if (elf == NULL) goto out_close; @@ -534,7 +533,7 @@ static int dso__load_sym(struct dso *self, int fd, const char *name, Elf *elf; int nr = 0, kernel = !strcmp("[kernel]", self->name); - elf = elf_begin(fd, ELF_C_READ_MMAP, NULL); + elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL); if (elf == NULL) { if (v) fprintf(stderr, "%s: cannot read %s ELF file.\n", @@ -676,7 +675,7 @@ static char *dso__read_build_id(struct dso *self, int v) if (fd < 0) goto out; - elf = elf_begin(fd, ELF_C_READ_MMAP, NULL); + elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL); if (elf == NULL) { if (v) fprintf(stderr, "%s: cannot read %s ELF file.\n", diff --git a/tools/perf/util/symbol.h b/tools/perf/util/symbol.h index 6e8490716408..829da9edba64 100644 --- a/tools/perf/util/symbol.h +++ b/tools/perf/util/symbol.h @@ -27,6 +27,16 @@ static inline char *bfd_demangle(void __used *v, const char __used *c, #endif #endif +/* + * libelf 0.8.x and earlier do not support ELF_C_READ_MMAP; + * for newer versions we can use mmap to reduce memory usage: + */ +#ifdef LIBELF_NO_MMAP +# define PERF_ELF_C_READ_MMAP ELF_C_READ +#else +# define PERF_ELF_C_READ_MMAP ELF_C_READ_MMAP +#endif + #ifndef DMGL_PARAMS #define DMGL_PARAMS (1 << 0) /* Include function args */ #define DMGL_ANSI (1 << 1) /* Include const, volatile, etc */ diff --git a/tools/perf/util/trace-event-parse.c b/tools/perf/util/trace-event-parse.c index f6a8437141c8..55c9659a56e2 100644 --- a/tools/perf/util/trace-event-parse.c +++ b/tools/perf/util/trace-event-parse.c @@ -618,7 +618,7 @@ static int test_type(enum event_type type, enum event_type expect) } static int test_type_token(enum event_type type, char *token, - enum event_type expect, char *expect_tok) + enum event_type expect, const char *expect_tok) { if (type != expect) { die("Error: expected type %d but read %d", @@ -650,7 +650,7 @@ static int read_expect_type(enum event_type expect, char **tok) return __read_expect_type(expect, tok, 1); } -static int __read_expected(enum event_type expect, char *str, int newline_ok) +static int __read_expected(enum event_type expect, const char *str, int newline_ok) { enum event_type type; char *token; @@ -668,12 +668,12 @@ static int __read_expected(enum event_type expect, char *str, int newline_ok) return 0; } -static int read_expected(enum event_type expect, char *str) +static int read_expected(enum event_type expect, const char *str) { return __read_expected(expect, str, 1); } -static int read_expected_item(enum event_type expect, char *str) +static int read_expected_item(enum event_type expect, const char *str) { return __read_expected(expect, str, 0); } @@ -1968,10 +1968,11 @@ static const struct flag flags[] = { { "NET_TX_SOFTIRQ", 2 }, { "NET_RX_SOFTIRQ", 3 }, { "BLOCK_SOFTIRQ", 4 }, - { "TASKLET_SOFTIRQ", 5 }, - { "SCHED_SOFTIRQ", 6 }, - { "HRTIMER_SOFTIRQ", 7 }, - { "RCU_SOFTIRQ", 8 }, + { "BLOCK_IOPOLL_SOFTIRQ", 5 }, + { "TASKLET_SOFTIRQ", 6 }, + { "SCHED_SOFTIRQ", 7 }, + { "HRTIMER_SOFTIRQ", 8 }, + { "RCU_SOFTIRQ", 9 }, { "HRTIMER_NORESTART", 0 }, { "HRTIMER_RESTART", 1 }, diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index e79c54034bcd..7495ce347344 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c @@ -850,6 +850,19 @@ static void kvm_mmu_notifier_invalidate_page(struct mmu_notifier *mn, } +static void kvm_mmu_notifier_change_pte(struct mmu_notifier *mn, + struct mm_struct *mm, + unsigned long address, + pte_t pte) +{ + struct kvm *kvm = mmu_notifier_to_kvm(mn); + + spin_lock(&kvm->mmu_lock); + kvm->mmu_notifier_seq++; + kvm_set_spte_hva(kvm, address, pte); + spin_unlock(&kvm->mmu_lock); +} + static void kvm_mmu_notifier_invalidate_range_start(struct mmu_notifier *mn, struct mm_struct *mm, unsigned long start, @@ -929,6 +942,7 @@ static const struct mmu_notifier_ops kvm_mmu_notifier_ops = { .invalidate_range_start = kvm_mmu_notifier_invalidate_range_start, .invalidate_range_end = kvm_mmu_notifier_invalidate_range_end, .clear_flush_young = kvm_mmu_notifier_clear_flush_young, + .change_pte = kvm_mmu_notifier_change_pte, .release = kvm_mmu_notifier_release, }; #endif /* CONFIG_MMU_NOTIFIER && KVM_ARCH_WANT_MMU_NOTIFIER */ @@ -2703,8 +2717,6 @@ int kvm_init(void *opaque, unsigned int vcpu_size, int r; int cpu; - kvm_init_debug(); - r = kvm_arch_init(opaque); if (r) goto out_fail; @@ -2771,6 +2783,8 @@ int kvm_init(void *opaque, unsigned int vcpu_size, kvm_preempt_ops.sched_in = kvm_sched_in; kvm_preempt_ops.sched_out = kvm_sched_out; + kvm_init_debug(); + return 0; out_free: @@ -2793,7 +2807,6 @@ out_free_0: out: kvm_arch_exit(); out_fail: - kvm_exit_debug(); return r; } EXPORT_SYMBOL_GPL(kvm_init); @@ -2801,6 +2814,7 @@ EXPORT_SYMBOL_GPL(kvm_init); void kvm_exit(void) { tracepoint_synchronize_unregister(); + kvm_exit_debug(); misc_deregister(&kvm_dev); kmem_cache_destroy(kvm_vcpu_cache); sysdev_unregister(&kvm_sysdev); @@ -2810,7 +2824,6 @@ void kvm_exit(void) on_each_cpu(hardware_disable, NULL, 1); kvm_arch_hardware_unsetup(); kvm_arch_exit(); - kvm_exit_debug(); free_cpumask_var(cpus_hardware_enabled); __free_page(bad_page); } |