mirror of
https://github.com/AuxXxilium/linux_dsm_epyc7002.git
synced 2024-12-02 06:46:42 +07:00
Merge branch 'perf/urgent' into perf/core
Merge reason: add the latest fixes. Signed-off-by: Ingo Molnar <mingo@elte.hu>
This commit is contained in:
commit
8bc84f8731
@ -272,6 +272,8 @@ printk-formats.txt
|
||||
- how to get printk format specifiers right
|
||||
prio_tree.txt
|
||||
- info on radix-priority-search-tree use for indexing vmas.
|
||||
ramoops.txt
|
||||
- documentation of the ramoops oops/panic logging module.
|
||||
rbtree.txt
|
||||
- info on what red-black trees are and what they are for.
|
||||
robust-futex-ABI.txt
|
||||
|
@ -45,7 +45,7 @@ arrived in memory (this becomes more likely with devices behind PCI-PCI
|
||||
bridges). In order to ensure that all the data has arrived in memory,
|
||||
the interrupt handler must read a register on the device which raised
|
||||
the interrupt. PCI transaction ordering rules require that all the data
|
||||
arrives in memory before the value can be returned from the register.
|
||||
arrive in memory before the value may be returned from the register.
|
||||
Using MSIs avoids this problem as the interrupt-generating write cannot
|
||||
pass the data writes, so by the time the interrupt is raised, the driver
|
||||
knows that all the data has arrived in memory.
|
||||
@ -86,13 +86,13 @@ device.
|
||||
|
||||
int pci_enable_msi(struct pci_dev *dev)
|
||||
|
||||
A successful call will allocate ONE interrupt to the device, regardless
|
||||
of how many MSIs the device supports. The device will be switched from
|
||||
A successful call allocates ONE interrupt to the device, regardless
|
||||
of how many MSIs the device supports. The device is switched from
|
||||
pin-based interrupt mode to MSI mode. The dev->irq number is changed
|
||||
to a new number which represents the message signaled interrupt.
|
||||
This function should be called before the driver calls request_irq()
|
||||
since enabling MSIs disables the pin-based IRQ and the driver will not
|
||||
receive interrupts on the old interrupt.
|
||||
to a new number which represents the message signaled interrupt;
|
||||
consequently, this function should be called before the driver calls
|
||||
request_irq(), because an MSI is delivered via a vector that is
|
||||
different from the vector of a pin-based interrupt.
|
||||
|
||||
4.2.2 pci_enable_msi_block
|
||||
|
||||
@ -111,20 +111,20 @@ the device are in the range dev->irq to dev->irq + count - 1.
|
||||
|
||||
If this function returns a negative number, it indicates an error and
|
||||
the driver should not attempt to request any more MSI interrupts for
|
||||
this device. If this function returns a positive number, it will be
|
||||
less than 'count' and indicate the number of interrupts that could have
|
||||
been allocated. In neither case will the irq value have been
|
||||
updated, nor will the device have been switched into MSI mode.
|
||||
this device. If this function returns a positive number, it is
|
||||
less than 'count' and indicates the number of interrupts that could have
|
||||
been allocated. In neither case is the irq value updated or the device
|
||||
switched into MSI mode.
|
||||
|
||||
The device driver must decide what action to take if
|
||||
pci_enable_msi_block() returns a value less than the number asked for.
|
||||
Some devices can make use of fewer interrupts than the maximum they
|
||||
request; in this case the driver should call pci_enable_msi_block()
|
||||
pci_enable_msi_block() returns a value less than the number requested.
|
||||
For instance, the driver could still make use of fewer interrupts;
|
||||
in this case the driver should call pci_enable_msi_block()
|
||||
again. Note that it is not guaranteed to succeed, even when the
|
||||
'count' has been reduced to the value returned from a previous call to
|
||||
pci_enable_msi_block(). This is because there are multiple constraints
|
||||
on the number of vectors that can be allocated; pci_enable_msi_block()
|
||||
will return as soon as it finds any constraint that doesn't allow the
|
||||
returns as soon as it finds any constraint that doesn't allow the
|
||||
call to succeed.
|
||||
|
||||
4.2.3 pci_disable_msi
|
||||
@ -137,10 +137,10 @@ interrupt number and frees the previously allocated message signaled
|
||||
interrupt(s). The interrupt may subsequently be assigned to another
|
||||
device, so drivers should not cache the value of dev->irq.
|
||||
|
||||
A device driver must always call free_irq() on the interrupt(s)
|
||||
for which it has called request_irq() before calling this function.
|
||||
Failure to do so will result in a BUG_ON(), the device will be left with
|
||||
MSI enabled and will leak its vector.
|
||||
Before calling this function, a device driver must always call free_irq()
|
||||
on any interrupt for which it previously called request_irq().
|
||||
Failure to do so results in a BUG_ON(), leaving the device with
|
||||
MSI enabled and thus leaking its vector.
|
||||
|
||||
4.3 Using MSI-X
|
||||
|
||||
@ -155,10 +155,10 @@ struct msix_entry {
|
||||
};
|
||||
|
||||
This allows for the device to use these interrupts in a sparse fashion;
|
||||
for example it could use interrupts 3 and 1027 and allocate only a
|
||||
for example, it could use interrupts 3 and 1027 and yet allocate only a
|
||||
two-element array. The driver is expected to fill in the 'entry' value
|
||||
in each element of the array to indicate which entries it wants the kernel
|
||||
to assign interrupts for. It is invalid to fill in two entries with the
|
||||
in each element of the array to indicate for which entries the kernel
|
||||
should assign interrupts; it is invalid to fill in two entries with the
|
||||
same number.
|
||||
|
||||
4.3.1 pci_enable_msix
|
||||
@ -168,10 +168,11 @@ int pci_enable_msix(struct pci_dev *dev, struct msix_entry *entries, int nvec)
|
||||
Calling this function asks the PCI subsystem to allocate 'nvec' MSIs.
|
||||
The 'entries' argument is a pointer to an array of msix_entry structs
|
||||
which should be at least 'nvec' entries in size. On success, the
|
||||
function will return 0 and the device will have been switched into
|
||||
MSI-X interrupt mode. The 'vector' elements in each entry will have
|
||||
been filled in with the interrupt number. The driver should then call
|
||||
request_irq() for each 'vector' that it decides to use.
|
||||
device is switched into MSI-X mode and the function returns 0.
|
||||
The 'vector' member in each entry is populated with the interrupt number;
|
||||
the driver should then call request_irq() for each 'vector' that it
|
||||
decides to use. The device driver is responsible for keeping track of the
|
||||
interrupts assigned to the MSI-X vectors so it can free them again later.
|
||||
|
||||
If this function returns a negative number, it indicates an error and
|
||||
the driver should not attempt to allocate any more MSI-X interrupts for
|
||||
@ -181,16 +182,14 @@ below.
|
||||
|
||||
This function, in contrast with pci_enable_msi(), does not adjust
|
||||
dev->irq. The device will not generate interrupts for this interrupt
|
||||
number once MSI-X is enabled. The device driver is responsible for
|
||||
keeping track of the interrupts assigned to the MSI-X vectors so it can
|
||||
free them again later.
|
||||
number once MSI-X is enabled.
|
||||
|
||||
Device drivers should normally call this function once per device
|
||||
during the initialization phase.
|
||||
|
||||
It is ideal if drivers can cope with a variable number of MSI-X interrupts,
|
||||
It is ideal if drivers can cope with a variable number of MSI-X interrupts;
|
||||
there are many reasons why the platform may not be able to provide the
|
||||
exact number a driver asks for.
|
||||
exact number that a driver asks for.
|
||||
|
||||
A request loop to achieve that might look like:
|
||||
|
||||
@ -212,15 +211,15 @@ static int foo_driver_enable_msix(struct foo_adapter *adapter, int nvec)
|
||||
|
||||
void pci_disable_msix(struct pci_dev *dev)
|
||||
|
||||
This API should be used to undo the effect of pci_enable_msix(). It frees
|
||||
This function should be used to undo the effect of pci_enable_msix(). It frees
|
||||
the previously allocated message signaled interrupts. The interrupts may
|
||||
subsequently be assigned to another device, so drivers should not cache
|
||||
the value of the 'vector' elements over a call to pci_disable_msix().
|
||||
|
||||
A device driver must always call free_irq() on the interrupt(s)
|
||||
for which it has called request_irq() before calling this function.
|
||||
Failure to do so will result in a BUG_ON(), the device will be left with
|
||||
MSI enabled and will leak its vector.
|
||||
Before calling this function, a device driver must always call free_irq()
|
||||
on any interrupt for which it previously called request_irq().
|
||||
Failure to do so results in a BUG_ON(), leaving the device with
|
||||
MSI-X enabled and thus leaking its vector.
|
||||
|
||||
4.3.3 The MSI-X Table
|
||||
|
||||
@ -232,10 +231,10 @@ mask or unmask an interrupt, it should call disable_irq() / enable_irq().
|
||||
4.4 Handling devices implementing both MSI and MSI-X capabilities
|
||||
|
||||
If a device implements both MSI and MSI-X capabilities, it can
|
||||
run in either MSI mode or MSI-X mode but not both simultaneously.
|
||||
run in either MSI mode or MSI-X mode, but not both simultaneously.
|
||||
This is a requirement of the PCI spec, and it is enforced by the
|
||||
PCI layer. Calling pci_enable_msi() when MSI-X is already enabled or
|
||||
pci_enable_msix() when MSI is already enabled will result in an error.
|
||||
pci_enable_msix() when MSI is already enabled results in an error.
|
||||
If a device driver wishes to switch between MSI and MSI-X at runtime,
|
||||
it must first quiesce the device, then switch it back to pin-interrupt
|
||||
mode, before calling pci_enable_msi() or pci_enable_msix() and resuming
|
||||
@ -251,7 +250,7 @@ the MSI-X facilities in preference to the MSI facilities. As mentioned
|
||||
above, MSI-X supports any number of interrupts between 1 and 2048.
|
||||
In constrast, MSI is restricted to a maximum of 32 interrupts (and
|
||||
must be a power of two). In addition, the MSI interrupt vectors must
|
||||
be allocated consecutively, so the system may not be able to allocate
|
||||
be allocated consecutively, so the system might not be able to allocate
|
||||
as many vectors for MSI as it could for MSI-X. On some platforms, MSI
|
||||
interrupts must all be targeted at the same set of CPUs whereas MSI-X
|
||||
interrupts can all be targeted at different CPUs.
|
||||
@ -281,7 +280,7 @@ disabled to enabled and back again.
|
||||
|
||||
Using 'lspci -v' (as root) may show some devices with "MSI", "Message
|
||||
Signalled Interrupts" or "MSI-X" capabilities. Each of these capabilities
|
||||
has an 'Enable' flag which will be followed with either "+" (enabled)
|
||||
has an 'Enable' flag which is followed with either "+" (enabled)
|
||||
or "-" (disabled).
|
||||
|
||||
|
||||
@ -298,7 +297,7 @@ The PCI stack provides three ways to disable MSIs:
|
||||
|
||||
Some host chipsets simply don't support MSIs properly. If we're
|
||||
lucky, the manufacturer knows this and has indicated it in the ACPI
|
||||
FADT table. In this case, Linux will automatically disable MSIs.
|
||||
FADT table. In this case, Linux automatically disables MSIs.
|
||||
Some boards don't include this information in the table and so we have
|
||||
to detect them ourselves. The complete list of these is found near the
|
||||
quirk_disable_all_msi() function in drivers/pci/quirks.c.
|
||||
@ -317,7 +316,7 @@ Some bridges allow you to enable MSIs by changing some bits in their
|
||||
PCI configuration space (especially the Hypertransport chipsets such
|
||||
as the nVidia nForce and Serverworks HT2000). As with host chipsets,
|
||||
Linux mostly knows about them and automatically enables MSIs if it can.
|
||||
If you have a bridge which Linux doesn't yet know about, you can enable
|
||||
If you have a bridge unknown to Linux, you can enable
|
||||
MSIs in configuration space using whatever method you know works, then
|
||||
enable MSIs on that bridge by doing:
|
||||
|
||||
@ -327,7 +326,7 @@ where $bridge is the PCI address of the bridge you've enabled (eg
|
||||
0000:00:0e.0).
|
||||
|
||||
To disable MSIs, echo 0 instead of 1. Changing this value should be
|
||||
done with caution as it can break interrupt handling for all devices
|
||||
done with caution as it could break interrupt handling for all devices
|
||||
below this bridge.
|
||||
|
||||
Again, please notify linux-pci@vger.kernel.org of any bridges that need
|
||||
@ -336,7 +335,7 @@ special handling.
|
||||
5.3. Disabling MSIs on a single device
|
||||
|
||||
Some devices are known to have faulty MSI implementations. Usually this
|
||||
is handled in the individual device driver but occasionally it's necessary
|
||||
is handled in the individual device driver, but occasionally it's necessary
|
||||
to handle this with a quirk. Some drivers have an option to disable use
|
||||
of MSI. While this is a convenient workaround for the driver author,
|
||||
it is not good practise, and should not be emulated.
|
||||
@ -350,7 +349,7 @@ for your machine. You should also check your .config to be sure you
|
||||
have enabled CONFIG_PCI_MSI.
|
||||
|
||||
Then, 'lspci -t' gives the list of bridges above a device. Reading
|
||||
/sys/bus/pci/devices/*/msi_bus will tell you whether MSI are enabled (1)
|
||||
/sys/bus/pci/devices/*/msi_bus will tell you whether MSIs are enabled (1)
|
||||
or disabled (0). If 0 is found in any of the msi_bus files belonging
|
||||
to bridges between the PCI root and the device, MSIs are disabled.
|
||||
|
||||
|
@ -130,7 +130,7 @@ Linux kernel master tree:
|
||||
ftp.??.kernel.org:/pub/linux/kernel/...
|
||||
?? == your country code, such as "us", "uk", "fr", etc.
|
||||
|
||||
http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git
|
||||
http://git.kernel.org/?p=linux/kernel/git/torvalds/linux.git
|
||||
|
||||
Linux kernel mailing list:
|
||||
linux-kernel@vger.kernel.org
|
||||
|
@ -303,7 +303,7 @@ patches that are being emailed around.
|
||||
|
||||
The sign-off is a simple line at the end of the explanation for the
|
||||
patch, which certifies that you wrote it or otherwise have the right to
|
||||
pass it on as a open-source patch. The rules are pretty simple: if you
|
||||
pass it on as an open-source patch. The rules are pretty simple: if you
|
||||
can certify the below:
|
||||
|
||||
Developer's Certificate of Origin 1.1
|
||||
|
@ -199,18 +199,16 @@ to coerce it into behaving.
|
||||
|
||||
To beat some sense out of the internal editor, do this:
|
||||
|
||||
- Under account settings, composition and addressing, uncheck "Compose
|
||||
messages in HTML format".
|
||||
|
||||
- Edit your Thunderbird config settings so that it won't use format=flowed.
|
||||
Go to "edit->preferences->advanced->config editor" to bring up the
|
||||
thunderbird's registry editor, and set "mailnews.send_plaintext_flowed" to
|
||||
"false".
|
||||
|
||||
- Enable "preformat" mode: Shft-click on the Write icon to bring up the HTML
|
||||
composer, select "Preformat" from the drop-down box just under the subject
|
||||
line, then close the message without saving. (This setting also applies to
|
||||
the text composer, but the only control for it is in the HTML composer.)
|
||||
- Disable HTML Format: Set "mail.identity.id1.compose_html" to "false".
|
||||
|
||||
- Enable "preformat" mode: Set "editor.quotesPreformatted" to "true".
|
||||
|
||||
- Enable UTF8: Set "prefs.converted-to-utf8" to "true".
|
||||
|
||||
- Install the "toggle wordwrap" extension. Download the file from:
|
||||
https://addons.mozilla.org/thunderbird/addon/2351/
|
||||
|
@ -27,7 +27,7 @@ His original code can still be found at:
|
||||
Does anyone know of a more current email address for Makoto? He doesn't
|
||||
respond to the address given above...
|
||||
|
||||
Current maintainer: Sergey S. Kostyliov <rathamahata@php4.ru>
|
||||
This filesystem doesn't have a maintainer.
|
||||
|
||||
WHAT IS THIS DRIVER?
|
||||
==================
|
||||
|
@ -620,17 +620,6 @@
|
||||
(including this document itself) have been moved there, and might
|
||||
be more up to date than the web version.
|
||||
|
||||
* Name: "Linux Source Driver"
|
||||
URL: http://lsd.linux.cz
|
||||
Keywords: Browsing source code.
|
||||
Description: "Linux Source Driver (LSD) is an application, which
|
||||
can make browsing source codes of Linux kernel easier than you can
|
||||
imagine. You can select between multiple versions of kernel (e.g.
|
||||
0.01, 1.0.0, 2.0.33, 2.0.34pre13, 2.0.0, 2.1.101 etc.). With LSD
|
||||
you can search Linux kernel (fulltext, macros, types, functions
|
||||
and variables) and LSD can generate patches for you on the fly
|
||||
(files, directories or kernel)".
|
||||
|
||||
* Name: "Linux Kernel Source Reference"
|
||||
Author: Thomas Graichen.
|
||||
URL: http://marc.info/?l=linux-kernel&m=96446640102205&w=4
|
||||
|
@ -40,6 +40,7 @@ parameter is applicable:
|
||||
ALSA ALSA sound support is enabled.
|
||||
APIC APIC support is enabled.
|
||||
APM Advanced Power Management support is enabled.
|
||||
ARM ARM architecture is enabled.
|
||||
AVR32 AVR32 architecture is enabled.
|
||||
AX25 Appropriate AX.25 support is enabled.
|
||||
BLACKFIN Blackfin architecture is enabled.
|
||||
@ -49,6 +50,7 @@ parameter is applicable:
|
||||
EFI EFI Partitioning (GPT) is enabled
|
||||
EIDE EIDE/ATAPI support is enabled.
|
||||
FB The frame buffer device is enabled.
|
||||
FTRACE Function tracing enabled.
|
||||
GCOV GCOV profiling is enabled.
|
||||
HW Appropriate hardware is enabled.
|
||||
IA-64 IA-64 architecture is enabled.
|
||||
@ -69,6 +71,7 @@ parameter is applicable:
|
||||
Documentation/m68k/kernel-options.txt.
|
||||
MCA MCA bus support is enabled.
|
||||
MDA MDA console support is enabled.
|
||||
MIPS MIPS architecture is enabled.
|
||||
MOUSE Appropriate mouse support is enabled.
|
||||
MSI Message Signaled Interrupts (PCI).
|
||||
MTD MTD (Memory Technology Device) support is enabled.
|
||||
@ -100,7 +103,6 @@ parameter is applicable:
|
||||
SPARC Sparc architecture is enabled.
|
||||
SWSUSP Software suspend (hibernation) is enabled.
|
||||
SUSPEND System suspend states are enabled.
|
||||
FTRACE Function tracing enabled.
|
||||
TPM TPM drivers are enabled.
|
||||
TS Appropriate touchscreen support is enabled.
|
||||
UMS USB Mass Storage support is enabled.
|
||||
@ -115,7 +117,7 @@ parameter is applicable:
|
||||
X86-64 X86-64 architecture is enabled.
|
||||
More X86-64 boot options can be found in
|
||||
Documentation/x86/x86_64/boot-options.txt .
|
||||
X86 Either 32bit or 64bit x86 (same as X86-32+X86-64)
|
||||
X86 Either 32-bit or 64-bit x86 (same as X86-32+X86-64)
|
||||
XEN Xen support is enabled
|
||||
|
||||
In addition, the following text indicates that the option:
|
||||
@ -376,7 +378,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
atkbd.softrepeat= [HW]
|
||||
Use software keyboard repeat
|
||||
|
||||
autotest [IA64]
|
||||
autotest [IA-64]
|
||||
|
||||
baycom_epp= [HW,AX25]
|
||||
Format: <io>,<mode>
|
||||
@ -681,8 +683,8 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
uart[8250],mmio32,<addr>[,options]
|
||||
Start an early, polled-mode console on the 8250/16550
|
||||
UART at the specified I/O port or MMIO address.
|
||||
MMIO inter-register address stride is either 8bit (mmio)
|
||||
or 32bit (mmio32).
|
||||
MMIO inter-register address stride is either 8-bit
|
||||
(mmio) or 32-bit (mmio32).
|
||||
The options are the same as for ttyS, above.
|
||||
|
||||
earlyprintk= [X86,SH,BLACKFIN]
|
||||
@ -725,7 +727,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
See Documentation/block/as-iosched.txt and
|
||||
Documentation/block/deadline-iosched.txt for details.
|
||||
|
||||
elfcorehdr= [IA64,PPC,SH,X86]
|
||||
elfcorehdr= [IA-64,PPC,SH,X86]
|
||||
Specifies physical address of start of kernel core
|
||||
image elf header. Generally kexec loader will
|
||||
pass this option to capture kernel.
|
||||
@ -791,7 +793,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
tracer at boot up. function-list is a comma separated
|
||||
list of functions. This list can be changed at run
|
||||
time by the set_ftrace_filter file in the debugfs
|
||||
tracing directory.
|
||||
tracing directory.
|
||||
|
||||
ftrace_notrace=[function-list]
|
||||
[FTRACE] Do not trace the functions specified in
|
||||
@ -829,7 +831,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
|
||||
hashdist= [KNL,NUMA] Large hashes allocated during boot
|
||||
are distributed across NUMA nodes. Defaults on
|
||||
for 64bit NUMA, off otherwise.
|
||||
for 64-bit NUMA, off otherwise.
|
||||
Format: 0 | 1 (for off | on)
|
||||
|
||||
hcl= [IA-64] SGI's Hardware Graph compatibility layer
|
||||
@ -998,10 +1000,10 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
DMA.
|
||||
forcedac [x86_64]
|
||||
With this option iommu will not optimize to look
|
||||
for io virtual address below 32 bit forcing dual
|
||||
for io virtual address below 32-bit forcing dual
|
||||
address cycle on pci bus for cards supporting greater
|
||||
than 32 bit addressing. The default is to look
|
||||
for translation below 32 bit and if not available
|
||||
than 32-bit addressing. The default is to look
|
||||
for translation below 32-bit and if not available
|
||||
then look in the higher range.
|
||||
strict [Default Off]
|
||||
With this option on every unmap_single operation will
|
||||
@ -1017,7 +1019,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
off disable Interrupt Remapping
|
||||
nosid disable Source ID checking
|
||||
|
||||
inttest= [IA64]
|
||||
inttest= [IA-64]
|
||||
|
||||
iomem= Disable strict checking of access to MMIO memory
|
||||
strict regions from userspace.
|
||||
@ -1034,7 +1036,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
nomerge
|
||||
forcesac
|
||||
soft
|
||||
pt [x86, IA64]
|
||||
pt [x86, IA-64]
|
||||
|
||||
io7= [HW] IO7 for Marvel based alpha systems
|
||||
See comment before marvel_specify_io7 in
|
||||
@ -1165,7 +1167,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
|
||||
kvm-amd.npt= [KVM,AMD] Disable nested paging (virtualized MMU)
|
||||
for all guests.
|
||||
Default is 1 (enabled) if in 64bit or 32bit-PAE mode
|
||||
Default is 1 (enabled) if in 64-bit or 32-bit PAE mode.
|
||||
|
||||
kvm-intel.ept= [KVM,Intel] Disable extended page tables
|
||||
(virtualized MMU) support on capable Intel chips.
|
||||
@ -1202,10 +1204,10 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
libata.dma=0 Disable all PATA and SATA DMA
|
||||
libata.dma=1 PATA and SATA Disk DMA only
|
||||
libata.dma=2 ATAPI (CDROM) DMA only
|
||||
libata.dma=4 Compact Flash DMA only
|
||||
libata.dma=4 Compact Flash DMA only
|
||||
Combinations also work, so libata.dma=3 enables DMA
|
||||
for disks and CDROMs, but not CFs.
|
||||
|
||||
|
||||
libata.ignore_hpa= [LIBATA] Ignore HPA limit
|
||||
libata.ignore_hpa=0 keep BIOS limits (default)
|
||||
libata.ignore_hpa=1 ignore limits, using full disk
|
||||
@ -1331,7 +1333,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
ltpc= [NET]
|
||||
Format: <io>,<irq>,<dma>
|
||||
|
||||
machvec= [IA64] Force the use of a particular machine-vector
|
||||
machvec= [IA-64] Force the use of a particular machine-vector
|
||||
(machvec) in a generic kernel.
|
||||
Example: machvec=hpzx1_swiotlb
|
||||
|
||||
@ -1734,7 +1736,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
|
||||
nointroute [IA-64]
|
||||
|
||||
nojitter [IA64] Disables jitter checking for ITC timers.
|
||||
nojitter [IA-64] Disables jitter checking for ITC timers.
|
||||
|
||||
no-kvmclock [X86,KVM] Disable paravirtualized KVM clock driver
|
||||
|
||||
@ -1800,7 +1802,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
|
||||
nox2apic [X86-64,APIC] Do not enable x2APIC mode.
|
||||
|
||||
nptcg= [IA64] Override max number of concurrent global TLB
|
||||
nptcg= [IA-64] Override max number of concurrent global TLB
|
||||
purges which is reported from either PAL_VM_SUMMARY or
|
||||
SAL PALO.
|
||||
|
||||
@ -2077,7 +2079,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
Format: { parport<nr> | timid | 0 }
|
||||
See also Documentation/parport.txt.
|
||||
|
||||
pmtmr= [X86] Manual setup of pmtmr I/O Port.
|
||||
pmtmr= [X86] Manual setup of pmtmr I/O Port.
|
||||
Override pmtimer IOPort with a hex value.
|
||||
e.g. pmtmr=0x508
|
||||
|
||||
@ -2635,6 +2637,16 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
medium is write-protected).
|
||||
Example: quirks=0419:aaf5:rl,0421:0433:rc
|
||||
|
||||
user_debug= [KNL,ARM]
|
||||
Format: <int>
|
||||
See arch/arm/Kconfig.debug help text.
|
||||
1 - undefined instruction events
|
||||
2 - system calls
|
||||
4 - invalid data aborts
|
||||
8 - SIGSEGV faults
|
||||
16 - SIGBUS faults
|
||||
Example: user_debug=31
|
||||
|
||||
userpte=
|
||||
[X86] Flags controlling user PTE allocations.
|
||||
|
||||
@ -2680,6 +2692,27 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
|
||||
vmpoff= [KNL,S390] Perform z/VM CP command after power off.
|
||||
Format: <command>
|
||||
|
||||
vsyscall= [X86-64]
|
||||
Controls the behavior of vsyscalls (i.e. calls to
|
||||
fixed addresses of 0xffffffffff600x00 from legacy
|
||||
code). Most statically-linked binaries and older
|
||||
versions of glibc use these calls. Because these
|
||||
functions are at fixed addresses, they make nice
|
||||
targets for exploits that can control RIP.
|
||||
|
||||
emulate [default] Vsyscalls turn into traps and are
|
||||
emulated reasonably safely.
|
||||
|
||||
native Vsyscalls are native syscall instructions.
|
||||
This is a little bit faster than trapping
|
||||
and makes a few dynamic recompilers work
|
||||
better than they would in emulation mode.
|
||||
It also makes exploits much easier to write.
|
||||
|
||||
none Vsyscalls don't work at all. This makes
|
||||
them quite hard to use for exploits but
|
||||
might break your system.
|
||||
|
||||
vt.cur_default= [VT] Default cursor shape.
|
||||
Format: 0xCCBBAA, where AA, BB, and CC are the same as
|
||||
the parameters of the <Esc>[?A;B;Cc escape sequence;
|
||||
|
@ -238,6 +238,18 @@ ad_select
|
||||
|
||||
This option was added in bonding version 3.4.0.
|
||||
|
||||
all_slaves_active
|
||||
|
||||
Specifies that duplicate frames (received on inactive ports) should be
|
||||
dropped (0) or delivered (1).
|
||||
|
||||
Normally, bonding will drop duplicate frames (received on inactive
|
||||
ports), which is desirable for most users. But there are some times
|
||||
it is nice to allow duplicate frames to be delivered.
|
||||
|
||||
The default value is 0 (drop duplicate frames received on inactive
|
||||
ports).
|
||||
|
||||
arp_interval
|
||||
|
||||
Specifies the ARP link monitoring frequency in milliseconds.
|
||||
@ -433,6 +445,23 @@ miimon
|
||||
determined. See the High Availability section for additional
|
||||
information. The default value is 0.
|
||||
|
||||
min_links
|
||||
|
||||
Specifies the minimum number of links that must be active before
|
||||
asserting carrier. It is similar to the Cisco EtherChannel min-links
|
||||
feature. This allows setting the minimum number of member ports that
|
||||
must be up (link-up state) before marking the bond device as up
|
||||
(carrier on). This is useful for situations where higher level services
|
||||
such as clustering want to ensure a minimum number of low bandwidth
|
||||
links are active before switchover. This option only affect 802.3ad
|
||||
mode.
|
||||
|
||||
The default value is 0. This will cause carrier to be asserted (for
|
||||
802.3ad mode) whenever there is an active aggregator, regardless of the
|
||||
number of available links in that aggregator. Note that, because an
|
||||
aggregator cannot be active without at least one available link,
|
||||
setting this option to 0 or to 1 has the exact same effect.
|
||||
|
||||
mode
|
||||
|
||||
Specifies one of the bonding policies. The default is
|
||||
|
371
Documentation/networking/scaling.txt
Normal file
371
Documentation/networking/scaling.txt
Normal file
@ -0,0 +1,371 @@
|
||||
Scaling in the Linux Networking Stack
|
||||
|
||||
|
||||
Introduction
|
||||
============
|
||||
|
||||
This document describes a set of complementary techniques in the Linux
|
||||
networking stack to increase parallelism and improve performance for
|
||||
multi-processor systems.
|
||||
|
||||
The following technologies are described:
|
||||
|
||||
RSS: Receive Side Scaling
|
||||
RPS: Receive Packet Steering
|
||||
RFS: Receive Flow Steering
|
||||
Accelerated Receive Flow Steering
|
||||
XPS: Transmit Packet Steering
|
||||
|
||||
|
||||
RSS: Receive Side Scaling
|
||||
=========================
|
||||
|
||||
Contemporary NICs support multiple receive and transmit descriptor queues
|
||||
(multi-queue). On reception, a NIC can send different packets to different
|
||||
queues to distribute processing among CPUs. The NIC distributes packets by
|
||||
applying a filter to each packet that assigns it to one of a small number
|
||||
of logical flows. Packets for each flow are steered to a separate receive
|
||||
queue, which in turn can be processed by separate CPUs. This mechanism is
|
||||
generally known as “Receive-side Scaling” (RSS). The goal of RSS and
|
||||
the other scaling techniques to increase performance uniformly.
|
||||
Multi-queue distribution can also be used for traffic prioritization, but
|
||||
that is not the focus of these techniques.
|
||||
|
||||
The filter used in RSS is typically a hash function over the network
|
||||
and/or transport layer headers-- for example, a 4-tuple hash over
|
||||
IP addresses and TCP ports of a packet. The most common hardware
|
||||
implementation of RSS uses a 128-entry indirection table where each entry
|
||||
stores a queue number. The receive queue for a packet is determined
|
||||
by masking out the low order seven bits of the computed hash for the
|
||||
packet (usually a Toeplitz hash), taking this number as a key into the
|
||||
indirection table and reading the corresponding value.
|
||||
|
||||
Some advanced NICs allow steering packets to queues based on
|
||||
programmable filters. For example, webserver bound TCP port 80 packets
|
||||
can be directed to their own receive queue. Such “n-tuple” filters can
|
||||
be configured from ethtool (--config-ntuple).
|
||||
|
||||
==== RSS Configuration
|
||||
|
||||
The driver for a multi-queue capable NIC typically provides a kernel
|
||||
module parameter for specifying the number of hardware queues to
|
||||
configure. In the bnx2x driver, for instance, this parameter is called
|
||||
num_queues. A typical RSS configuration would be to have one receive queue
|
||||
for each CPU if the device supports enough queues, or otherwise at least
|
||||
one for each cache domain at a particular cache level (L1, L2, etc.).
|
||||
|
||||
The indirection table of an RSS device, which resolves a queue by masked
|
||||
hash, is usually programmed by the driver at initialization. The
|
||||
default mapping is to distribute the queues evenly in the table, but the
|
||||
indirection table can be retrieved and modified at runtime using ethtool
|
||||
commands (--show-rxfh-indir and --set-rxfh-indir). Modifying the
|
||||
indirection table could be done to give different queues different
|
||||
relative weights.
|
||||
|
||||
== RSS IRQ Configuration
|
||||
|
||||
Each receive queue has a separate IRQ associated with it. The NIC triggers
|
||||
this to notify a CPU when new packets arrive on the given queue. The
|
||||
signaling path for PCIe devices uses message signaled interrupts (MSI-X),
|
||||
that can route each interrupt to a particular CPU. The active mapping
|
||||
of queues to IRQs can be determined from /proc/interrupts. By default,
|
||||
an IRQ may be handled on any CPU. Because a non-negligible part of packet
|
||||
processing takes place in receive interrupt handling, it is advantageous
|
||||
to spread receive interrupts between CPUs. To manually adjust the IRQ
|
||||
affinity of each interrupt see Documentation/IRQ-affinity. Some systems
|
||||
will be running irqbalance, a daemon that dynamically optimizes IRQ
|
||||
assignments and as a result may override any manual settings.
|
||||
|
||||
== Suggested Configuration
|
||||
|
||||
RSS should be enabled when latency is a concern or whenever receive
|
||||
interrupt processing forms a bottleneck. Spreading load between CPUs
|
||||
decreases queue length. For low latency networking, the optimal setting
|
||||
is to allocate as many queues as there are CPUs in the system (or the
|
||||
NIC maximum, if lower). Because the aggregate number of interrupts grows
|
||||
with each additional queue, the most efficient high-rate configuration
|
||||
is likely the one with the smallest number of receive queues where no
|
||||
CPU that processes receive interrupts reaches 100% utilization. Per-cpu
|
||||
load can be observed using the mpstat utility.
|
||||
|
||||
|
||||
RPS: Receive Packet Steering
|
||||
============================
|
||||
|
||||
Receive Packet Steering (RPS) is logically a software implementation of
|
||||
RSS. Being in software, it is necessarily called later in the datapath.
|
||||
Whereas RSS selects the queue and hence CPU that will run the hardware
|
||||
interrupt handler, RPS selects the CPU to perform protocol processing
|
||||
above the interrupt handler. This is accomplished by placing the packet
|
||||
on the desired CPU’s backlog queue and waking up the CPU for processing.
|
||||
RPS has some advantages over RSS: 1) it can be used with any NIC,
|
||||
2) software filters can easily be added to hash over new protocols,
|
||||
3) it does not increase hardware device interrupt rate (although it does
|
||||
introduce inter-processor interrupts (IPIs)).
|
||||
|
||||
RPS is called during bottom half of the receive interrupt handler, when
|
||||
a driver sends a packet up the network stack with netif_rx() or
|
||||
netif_receive_skb(). These call the get_rps_cpu() function, which
|
||||
selects the queue that should process a packet.
|
||||
|
||||
The first step in determining the target CPU for RPS is to calculate a
|
||||
flow hash over the packet’s addresses or ports (2-tuple or 4-tuple hash
|
||||
depending on the protocol). This serves as a consistent hash of the
|
||||
associated flow of the packet. The hash is either provided by hardware
|
||||
or will be computed in the stack. Capable hardware can pass the hash in
|
||||
the receive descriptor for the packet; this would usually be the same
|
||||
hash used for RSS (e.g. computed Toeplitz hash). The hash is saved in
|
||||
skb->rx_hash and can be used elsewhere in the stack as a hash of the
|
||||
packet’s flow.
|
||||
|
||||
Each receive hardware queue has an associated list of CPUs to which
|
||||
RPS may enqueue packets for processing. For each received packet,
|
||||
an index into the list is computed from the flow hash modulo the size
|
||||
of the list. The indexed CPU is the target for processing the packet,
|
||||
and the packet is queued to the tail of that CPU’s backlog queue. At
|
||||
the end of the bottom half routine, IPIs are sent to any CPUs for which
|
||||
packets have been queued to their backlog queue. The IPI wakes backlog
|
||||
processing on the remote CPU, and any queued packets are then processed
|
||||
up the networking stack.
|
||||
|
||||
==== RPS Configuration
|
||||
|
||||
RPS requires a kernel compiled with the CONFIG_RPS kconfig symbol (on
|
||||
by default for SMP). Even when compiled in, RPS remains disabled until
|
||||
explicitly configured. The list of CPUs to which RPS may forward traffic
|
||||
can be configured for each receive queue using a sysfs file entry:
|
||||
|
||||
/sys/class/net/<dev>/queues/rx-<n>/rps_cpus
|
||||
|
||||
This file implements a bitmap of CPUs. RPS is disabled when it is zero
|
||||
(the default), in which case packets are processed on the interrupting
|
||||
CPU. Documentation/IRQ-affinity.txt explains how CPUs are assigned to
|
||||
the bitmap.
|
||||
|
||||
== Suggested Configuration
|
||||
|
||||
For a single queue device, a typical RPS configuration would be to set
|
||||
the rps_cpus to the CPUs in the same cache domain of the interrupting
|
||||
CPU. If NUMA locality is not an issue, this could also be all CPUs in
|
||||
the system. At high interrupt rate, it might be wise to exclude the
|
||||
interrupting CPU from the map since that already performs much work.
|
||||
|
||||
For a multi-queue system, if RSS is configured so that a hardware
|
||||
receive queue is mapped to each CPU, then RPS is probably redundant
|
||||
and unnecessary. If there are fewer hardware queues than CPUs, then
|
||||
RPS might be beneficial if the rps_cpus for each queue are the ones that
|
||||
share the same cache domain as the interrupting CPU for that queue.
|
||||
|
||||
|
||||
RFS: Receive Flow Steering
|
||||
==========================
|
||||
|
||||
While RPS steers packets solely based on hash, and thus generally
|
||||
provides good load distribution, it does not take into account
|
||||
application locality. This is accomplished by Receive Flow Steering
|
||||
(RFS). The goal of RFS is to increase datacache hitrate by steering
|
||||
kernel processing of packets to the CPU where the application thread
|
||||
consuming the packet is running. RFS relies on the same RPS mechanisms
|
||||
to enqueue packets onto the backlog of another CPU and to wake up that
|
||||
CPU.
|
||||
|
||||
In RFS, packets are not forwarded directly by the value of their hash,
|
||||
but the hash is used as index into a flow lookup table. This table maps
|
||||
flows to the CPUs where those flows are being processed. The flow hash
|
||||
(see RPS section above) is used to calculate the index into this table.
|
||||
The CPU recorded in each entry is the one which last processed the flow.
|
||||
If an entry does not hold a valid CPU, then packets mapped to that entry
|
||||
are steered using plain RPS. Multiple table entries may point to the
|
||||
same CPU. Indeed, with many flows and few CPUs, it is very likely that
|
||||
a single application thread handles flows with many different flow hashes.
|
||||
|
||||
rps_sock_table is a global flow table that contains the *desired* CPU for
|
||||
flows: the CPU that is currently processing the flow in userspace. Each
|
||||
table value is a CPU index that is updated during calls to recvmsg and
|
||||
sendmsg (specifically, inet_recvmsg(), inet_sendmsg(), inet_sendpage()
|
||||
and tcp_splice_read()).
|
||||
|
||||
When the scheduler moves a thread to a new CPU while it has outstanding
|
||||
receive packets on the old CPU, packets may arrive out of order. To
|
||||
avoid this, RFS uses a second flow table to track outstanding packets
|
||||
for each flow: rps_dev_flow_table is a table specific to each hardware
|
||||
receive queue of each device. Each table value stores a CPU index and a
|
||||
counter. The CPU index represents the *current* CPU onto which packets
|
||||
for this flow are enqueued for further kernel processing. Ideally, kernel
|
||||
and userspace processing occur on the same CPU, and hence the CPU index
|
||||
in both tables is identical. This is likely false if the scheduler has
|
||||
recently migrated a userspace thread while the kernel still has packets
|
||||
enqueued for kernel processing on the old CPU.
|
||||
|
||||
The counter in rps_dev_flow_table values records the length of the current
|
||||
CPU's backlog when a packet in this flow was last enqueued. Each backlog
|
||||
queue has a head counter that is incremented on dequeue. A tail counter
|
||||
is computed as head counter + queue length. In other words, the counter
|
||||
in rps_dev_flow_table[i] records the last element in flow i that has
|
||||
been enqueued onto the currently designated CPU for flow i (of course,
|
||||
entry i is actually selected by hash and multiple flows may hash to the
|
||||
same entry i).
|
||||
|
||||
And now the trick for avoiding out of order packets: when selecting the
|
||||
CPU for packet processing (from get_rps_cpu()) the rps_sock_flow table
|
||||
and the rps_dev_flow table of the queue that the packet was received on
|
||||
are compared. If the desired CPU for the flow (found in the
|
||||
rps_sock_flow table) matches the current CPU (found in the rps_dev_flow
|
||||
table), the packet is enqueued onto that CPU’s backlog. If they differ,
|
||||
the current CPU is updated to match the desired CPU if one of the
|
||||
following is true:
|
||||
|
||||
- The current CPU's queue head counter >= the recorded tail counter
|
||||
value in rps_dev_flow[i]
|
||||
- The current CPU is unset (equal to NR_CPUS)
|
||||
- The current CPU is offline
|
||||
|
||||
After this check, the packet is sent to the (possibly updated) current
|
||||
CPU. These rules aim to ensure that a flow only moves to a new CPU when
|
||||
there are no packets outstanding on the old CPU, as the outstanding
|
||||
packets could arrive later than those about to be processed on the new
|
||||
CPU.
|
||||
|
||||
==== RFS Configuration
|
||||
|
||||
RFS is only available if the kconfig symbol CONFIG_RFS is enabled (on
|
||||
by default for SMP). The functionality remains disabled until explicitly
|
||||
configured. The number of entries in the global flow table is set through:
|
||||
|
||||
/proc/sys/net/core/rps_sock_flow_entries
|
||||
|
||||
The number of entries in the per-queue flow table are set through:
|
||||
|
||||
/sys/class/net/<dev>/queues/tx-<n>/rps_flow_cnt
|
||||
|
||||
== Suggested Configuration
|
||||
|
||||
Both of these need to be set before RFS is enabled for a receive queue.
|
||||
Values for both are rounded up to the nearest power of two. The
|
||||
suggested flow count depends on the expected number of active connections
|
||||
at any given time, which may be significantly less than the number of open
|
||||
connections. We have found that a value of 32768 for rps_sock_flow_entries
|
||||
works fairly well on a moderately loaded server.
|
||||
|
||||
For a single queue device, the rps_flow_cnt value for the single queue
|
||||
would normally be configured to the same value as rps_sock_flow_entries.
|
||||
For a multi-queue device, the rps_flow_cnt for each queue might be
|
||||
configured as rps_sock_flow_entries / N, where N is the number of
|
||||
queues. So for instance, if rps_flow_entries is set to 32768 and there
|
||||
are 16 configured receive queues, rps_flow_cnt for each queue might be
|
||||
configured as 2048.
|
||||
|
||||
|
||||
Accelerated RFS
|
||||
===============
|
||||
|
||||
Accelerated RFS is to RFS what RSS is to RPS: a hardware-accelerated load
|
||||
balancing mechanism that uses soft state to steer flows based on where
|
||||
the application thread consuming the packets of each flow is running.
|
||||
Accelerated RFS should perform better than RFS since packets are sent
|
||||
directly to a CPU local to the thread consuming the data. The target CPU
|
||||
will either be the same CPU where the application runs, or at least a CPU
|
||||
which is local to the application thread’s CPU in the cache hierarchy.
|
||||
|
||||
To enable accelerated RFS, the networking stack calls the
|
||||
ndo_rx_flow_steer driver function to communicate the desired hardware
|
||||
queue for packets matching a particular flow. The network stack
|
||||
automatically calls this function every time a flow entry in
|
||||
rps_dev_flow_table is updated. The driver in turn uses a device specific
|
||||
method to program the NIC to steer the packets.
|
||||
|
||||
The hardware queue for a flow is derived from the CPU recorded in
|
||||
rps_dev_flow_table. The stack consults a CPU to hardware queue map which
|
||||
is maintained by the NIC driver. This is an auto-generated reverse map of
|
||||
the IRQ affinity table shown by /proc/interrupts. Drivers can use
|
||||
functions in the cpu_rmap (“CPU affinity reverse map”) kernel library
|
||||
to populate the map. For each CPU, the corresponding queue in the map is
|
||||
set to be one whose processing CPU is closest in cache locality.
|
||||
|
||||
==== Accelerated RFS Configuration
|
||||
|
||||
Accelerated RFS is only available if the kernel is compiled with
|
||||
CONFIG_RFS_ACCEL and support is provided by the NIC device and driver.
|
||||
It also requires that ntuple filtering is enabled via ethtool. The map
|
||||
of CPU to queues is automatically deduced from the IRQ affinities
|
||||
configured for each receive queue by the driver, so no additional
|
||||
configuration should be necessary.
|
||||
|
||||
== Suggested Configuration
|
||||
|
||||
This technique should be enabled whenever one wants to use RFS and the
|
||||
NIC supports hardware acceleration.
|
||||
|
||||
XPS: Transmit Packet Steering
|
||||
=============================
|
||||
|
||||
Transmit Packet Steering is a mechanism for intelligently selecting
|
||||
which transmit queue to use when transmitting a packet on a multi-queue
|
||||
device. To accomplish this, a mapping from CPU to hardware queue(s) is
|
||||
recorded. The goal of this mapping is usually to assign queues
|
||||
exclusively to a subset of CPUs, where the transmit completions for
|
||||
these queues are processed on a CPU within this set. This choice
|
||||
provides two benefits. First, contention on the device queue lock is
|
||||
significantly reduced since fewer CPUs contend for the same queue
|
||||
(contention can be eliminated completely if each CPU has its own
|
||||
transmit queue). Secondly, cache miss rate on transmit completion is
|
||||
reduced, in particular for data cache lines that hold the sk_buff
|
||||
structures.
|
||||
|
||||
XPS is configured per transmit queue by setting a bitmap of CPUs that
|
||||
may use that queue to transmit. The reverse mapping, from CPUs to
|
||||
transmit queues, is computed and maintained for each network device.
|
||||
When transmitting the first packet in a flow, the function
|
||||
get_xps_queue() is called to select a queue. This function uses the ID
|
||||
of the running CPU as a key into the CPU-to-queue lookup table. If the
|
||||
ID matches a single queue, that is used for transmission. If multiple
|
||||
queues match, one is selected by using the flow hash to compute an index
|
||||
into the set.
|
||||
|
||||
The queue chosen for transmitting a particular flow is saved in the
|
||||
corresponding socket structure for the flow (e.g. a TCP connection).
|
||||
This transmit queue is used for subsequent packets sent on the flow to
|
||||
prevent out of order (ooo) packets. The choice also amortizes the cost
|
||||
of calling get_xps_queues() over all packets in the connection. To avoid
|
||||
ooo packets, the queue for a flow can subsequently only be changed if
|
||||
skb->ooo_okay is set for a packet in the flow. This flag indicates that
|
||||
there are no outstanding packets in the flow, so the transmit queue can
|
||||
change without the risk of generating out of order packets. The
|
||||
transport layer is responsible for setting ooo_okay appropriately. TCP,
|
||||
for instance, sets the flag when all data for a connection has been
|
||||
acknowledged.
|
||||
|
||||
==== XPS Configuration
|
||||
|
||||
XPS is only available if the kconfig symbol CONFIG_XPS is enabled (on by
|
||||
default for SMP). The functionality remains disabled until explicitly
|
||||
configured. To enable XPS, the bitmap of CPUs that may use a transmit
|
||||
queue is configured using the sysfs file entry:
|
||||
|
||||
/sys/class/net/<dev>/queues/tx-<n>/xps_cpus
|
||||
|
||||
== Suggested Configuration
|
||||
|
||||
For a network device with a single transmission queue, XPS configuration
|
||||
has no effect, since there is no choice in this case. In a multi-queue
|
||||
system, XPS is preferably configured so that each CPU maps onto one queue.
|
||||
If there are as many queues as there are CPUs in the system, then each
|
||||
queue can also map onto one CPU, resulting in exclusive pairings that
|
||||
experience no contention. If there are fewer queues than CPUs, then the
|
||||
best CPUs to share a given queue are probably those that share the cache
|
||||
with the CPU that processes transmit completions for that queue
|
||||
(transmit interrupts).
|
||||
|
||||
|
||||
Further Information
|
||||
===================
|
||||
RPS and RFS were introduced in kernel 2.6.35. XPS was incorporated into
|
||||
2.6.38. Original patches were submitted by Tom Herbert
|
||||
(therbert@google.com)
|
||||
|
||||
Accelerated RFS was introduced in 2.6.35. Original patches were
|
||||
submitted by Ben Hutchings (bhutchings@solarflare.com)
|
||||
|
||||
Authors:
|
||||
Tom Herbert (therbert@google.com)
|
||||
Willem de Bruijn (willemb@google.com)
|
76
Documentation/ramoops.txt
Normal file
76
Documentation/ramoops.txt
Normal file
@ -0,0 +1,76 @@
|
||||
Ramoops oops/panic logger
|
||||
=========================
|
||||
|
||||
Sergiu Iordache <sergiu@chromium.org>
|
||||
|
||||
Updated: 8 August 2011
|
||||
|
||||
0. Introduction
|
||||
|
||||
Ramoops is an oops/panic logger that writes its logs to RAM before the system
|
||||
crashes. It works by logging oopses and panics in a circular buffer. Ramoops
|
||||
needs a system with persistent RAM so that the content of that area can
|
||||
survive after a restart.
|
||||
|
||||
1. Ramoops concepts
|
||||
|
||||
Ramoops uses a predefined memory area to store the dump. The start and size of
|
||||
the memory area are set using two variables:
|
||||
* "mem_address" for the start
|
||||
* "mem_size" for the size. The memory size will be rounded down to a
|
||||
power of two.
|
||||
|
||||
The memory area is divided into "record_size" chunks (also rounded down to
|
||||
power of two) and each oops/panic writes a "record_size" chunk of
|
||||
information.
|
||||
|
||||
Dumping both oopses and panics can be done by setting 1 in the "dump_oops"
|
||||
variable while setting 0 in that variable dumps only the panics.
|
||||
|
||||
The module uses a counter to record multiple dumps but the counter gets reset
|
||||
on restart (i.e. new dumps after the restart will overwrite old ones).
|
||||
|
||||
2. Setting the parameters
|
||||
|
||||
Setting the ramoops parameters can be done in 2 different manners:
|
||||
1. Use the module parameters (which have the names of the variables described
|
||||
as before).
|
||||
2. Use a platform device and set the platform data. The parameters can then
|
||||
be set through that platform data. An example of doing that is:
|
||||
|
||||
#include <linux/ramoops.h>
|
||||
[...]
|
||||
|
||||
static struct ramoops_platform_data ramoops_data = {
|
||||
.mem_size = <...>,
|
||||
.mem_address = <...>,
|
||||
.record_size = <...>,
|
||||
.dump_oops = <...>,
|
||||
};
|
||||
|
||||
static struct platform_device ramoops_dev = {
|
||||
.name = "ramoops",
|
||||
.dev = {
|
||||
.platform_data = &ramoops_data,
|
||||
},
|
||||
};
|
||||
|
||||
[... inside a function ...]
|
||||
int ret;
|
||||
|
||||
ret = platform_device_register(&ramoops_dev);
|
||||
if (ret) {
|
||||
printk(KERN_ERR "unable to register platform device\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
3. Dump format
|
||||
|
||||
The data dump begins with a header, currently defined as "====" followed by a
|
||||
timestamp and a new line. The dump then continues with the actual data.
|
||||
|
||||
4. Reading the data
|
||||
|
||||
The dump data can be read from memory (through /dev/mem or other means).
|
||||
Getting the module parameters, which are needed in order to parse the data, can
|
||||
be done through /sys/module/ramoops/parameters/* .
|
@ -8,3 +8,6 @@ lguest/
|
||||
- Extremely simple hypervisor for experimental/educational use.
|
||||
uml/
|
||||
- User Mode Linux, builds/runs Linux kernel as a userspace program.
|
||||
virtio.txt
|
||||
- Text version of draft virtio spec.
|
||||
See http://ozlabs.org/~rusty/virtio-spec
|
||||
|
@ -1996,6 +1996,9 @@ int main(int argc, char *argv[])
|
||||
/* We use a simple helper to copy the arguments separated by spaces. */
|
||||
concat((char *)(boot + 1), argv+optind+2);
|
||||
|
||||
/* Set kernel alignment to 16M (CONFIG_PHYSICAL_ALIGN) */
|
||||
boot->hdr.kernel_alignment = 0x1000000;
|
||||
|
||||
/* Boot protocol version: 2.07 supports the fields for lguest. */
|
||||
boot->hdr.version = 0x207;
|
||||
|
||||
|
2200
Documentation/virtual/virtio-spec.txt
Normal file
2200
Documentation/virtual/virtio-spec.txt
Normal file
File diff suppressed because it is too large
Load Diff
@ -4604,7 +4604,7 @@ F: arch/arm/mach-omap2/clockdomain2xxx_3xxx.c
|
||||
F: arch/arm/mach-omap2/clockdomain44xx.c
|
||||
|
||||
OMAP AUDIO SUPPORT
|
||||
M: Jarkko Nikula <jhnikula@gmail.com>
|
||||
M: Jarkko Nikula <jarkko.nikula@bitmer.com>
|
||||
L: alsa-devel@alsa-project.org (subscribers-only)
|
||||
L: linux-omap@vger.kernel.org
|
||||
S: Maintained
|
||||
@ -4971,7 +4971,7 @@ M: Paul Mackerras <paulus@samba.org>
|
||||
M: Ingo Molnar <mingo@elte.hu>
|
||||
M: Arnaldo Carvalho de Melo <acme@ghostprotocols.net>
|
||||
S: Supported
|
||||
F: kernel/perf_event*.c
|
||||
F: kernel/events/*
|
||||
F: include/linux/perf_event.h
|
||||
F: arch/*/kernel/perf_event*.c
|
||||
F: arch/*/kernel/*/perf_event*.c
|
||||
|
4
Makefile
4
Makefile
@ -1,8 +1,8 @@
|
||||
VERSION = 3
|
||||
PATCHLEVEL = 1
|
||||
SUBLEVEL = 0
|
||||
EXTRAVERSION = -rc1
|
||||
NAME = Sneaky Weasel
|
||||
EXTRAVERSION = -rc2
|
||||
NAME = Wet Seal
|
||||
|
||||
# *DOCUMENTATION*
|
||||
# To see a list of typical targets execute "make help"
|
||||
|
@ -195,10 +195,10 @@ ENTRY(iwmmxt_task_disable)
|
||||
|
||||
@ enable access to CP0 and CP1
|
||||
XSC(mrc p15, 0, r4, c15, c1, 0)
|
||||
XSC(orr r4, r4, #0xf)
|
||||
XSC(orr r4, r4, #0x3)
|
||||
XSC(mcr p15, 0, r4, c15, c1, 0)
|
||||
PJ4(mrc p15, 0, r4, c1, c0, 2)
|
||||
PJ4(orr r4, r4, #0x3)
|
||||
PJ4(orr r4, r4, #0xf)
|
||||
PJ4(mcr p15, 0, r4, c1, c0, 2)
|
||||
|
||||
mov r0, #0 @ nothing to load
|
||||
@ -313,7 +313,7 @@ ENTRY(iwmmxt_task_switch)
|
||||
teq r2, r3 @ next task owns it?
|
||||
movne pc, lr @ no: leave Concan disabled
|
||||
|
||||
1: @ flip Conan access
|
||||
1: @ flip Concan access
|
||||
XSC(eor r1, r1, #0x3)
|
||||
XSC(mcr p15, 0, r1, c15, c1, 0)
|
||||
PJ4(eor r1, r1, #0xf)
|
||||
|
@ -331,6 +331,9 @@ int __init mx25_clocks_init(void)
|
||||
__raw_writel(__raw_readl(CRM_BASE+0x64) | (1 << 7) | (1 << 0),
|
||||
CRM_BASE + 0x64);
|
||||
|
||||
/* Clock source for gpt is ahb_div */
|
||||
__raw_writel(__raw_readl(CRM_BASE+0x64) & ~(1 << 5), CRM_BASE + 0x64);
|
||||
|
||||
mxc_timer_init(&gpt_clk, MX25_IO_ADDRESS(MX25_GPT1_BASE_ADDR), 54);
|
||||
|
||||
return 0;
|
||||
|
@ -30,6 +30,7 @@
|
||||
#include <linux/input.h>
|
||||
#include <linux/gpio.h>
|
||||
#include <linux/delay.h>
|
||||
#include <sound/tlv320aic32x4.h>
|
||||
#include <asm/mach-types.h>
|
||||
#include <asm/mach/arch.h>
|
||||
#include <asm/mach/time.h>
|
||||
@ -196,6 +197,17 @@ static struct pca953x_platform_data visstrim_m10_pca9555_pdata = {
|
||||
.invert = 0,
|
||||
};
|
||||
|
||||
static struct aic32x4_pdata visstrim_m10_aic32x4_pdata = {
|
||||
.power_cfg = AIC32X4_PWR_MICBIAS_2075_LDOIN |
|
||||
AIC32X4_PWR_AVDD_DVDD_WEAK_DISABLE |
|
||||
AIC32X4_PWR_AIC32X4_LDO_ENABLE |
|
||||
AIC32X4_PWR_CMMODE_LDOIN_RANGE_18_36 |
|
||||
AIC32X4_PWR_CMMODE_HP_LDOIN_POWERED,
|
||||
.micpga_routing = AIC32X4_MICPGA_ROUTE_LMIC_IN2R_10K |
|
||||
AIC32X4_MICPGA_ROUTE_RMIC_IN1L_10K,
|
||||
.swapdacs = false,
|
||||
};
|
||||
|
||||
static struct i2c_board_info visstrim_m10_i2c_devices[] = {
|
||||
{
|
||||
I2C_BOARD_INFO("pca9555", 0x20),
|
||||
@ -203,6 +215,7 @@ static struct i2c_board_info visstrim_m10_i2c_devices[] = {
|
||||
},
|
||||
{
|
||||
I2C_BOARD_INFO("tlv320aic32x4", 0x18),
|
||||
.platform_data = &visstrim_m10_aic32x4_pdata,
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -468,7 +468,7 @@ static struct i2c_board_info __initdata mx31ads_i2c1_devices[] = {
|
||||
#endif
|
||||
};
|
||||
|
||||
static void mxc_init_i2c(void)
|
||||
static void __init mxc_init_i2c(void)
|
||||
{
|
||||
i2c_register_board_info(1, mx31ads_i2c1_devices,
|
||||
ARRAY_SIZE(mx31ads_i2c1_devices));
|
||||
@ -486,7 +486,7 @@ static unsigned int ssi_pins[] = {
|
||||
MX31_PIN_STXD5__STXD5,
|
||||
};
|
||||
|
||||
static void mxc_init_audio(void)
|
||||
static void __init mxc_init_audio(void)
|
||||
{
|
||||
imx31_add_imx_ssi(0, NULL);
|
||||
mxc_iomux_setup_multiple_pins(ssi_pins, ARRAY_SIZE(ssi_pins), "ssi");
|
||||
|
@ -192,7 +192,7 @@ static struct mxc_usbh_platform_data usbh2_pdata __initdata = {
|
||||
.portsc = MXC_EHCI_MODE_ULPI | MXC_EHCI_UTMI_8BIT,
|
||||
};
|
||||
|
||||
static void lilly1131_usb_init(void)
|
||||
static void __init lilly1131_usb_init(void)
|
||||
{
|
||||
imx31_add_mxc_ehci_hs(1, &usbh1_pdata);
|
||||
|
||||
|
@ -16,16 +16,18 @@
|
||||
#include <mach/gpio.h>
|
||||
#include <mach/pxa168.h>
|
||||
#include <mach/mfp-pxa168.h>
|
||||
#include <mach/mfp-gplugd.h>
|
||||
|
||||
#include "common.h"
|
||||
|
||||
static unsigned long gplugd_pin_config[] __initdata = {
|
||||
/* UART3 */
|
||||
GPIO8_UART3_SOUT,
|
||||
GPIO9_UART3_SIN,
|
||||
GPI1O_UART3_CTS,
|
||||
GPI11_UART3_RTS,
|
||||
GPIO8_UART3_TXD,
|
||||
GPIO9_UART3_RXD,
|
||||
GPIO1O_UART3_CTS,
|
||||
GPIO11_UART3_RTS,
|
||||
|
||||
/* USB OTG PEN */
|
||||
GPIO18_GPIO,
|
||||
|
||||
/* MMC2 */
|
||||
GPIO28_MMC2_CMD,
|
||||
@ -109,6 +111,12 @@ static unsigned long gplugd_pin_config[] __initdata = {
|
||||
GPIO105_CI2C_SDA,
|
||||
GPIO106_CI2C_SCL,
|
||||
|
||||
/* SPI NOR Flash on SSP2 */
|
||||
GPIO107_SSP2_RXD,
|
||||
GPIO108_SSP2_TXD,
|
||||
GPIO110_GPIO, /* SPI_CSn */
|
||||
GPIO111_SSP2_CLK,
|
||||
|
||||
/* Select JTAG */
|
||||
GPIO109_GPIO,
|
||||
|
||||
@ -154,7 +162,7 @@ static void __init select_disp_freq(void)
|
||||
"frequency\n");
|
||||
} else {
|
||||
gpio_direction_output(35, 1);
|
||||
gpio_free(104);
|
||||
gpio_free(35);
|
||||
}
|
||||
|
||||
if (unlikely(gpio_request(85, "DISP_FREQ_SEL_2"))) {
|
||||
@ -162,7 +170,7 @@ static void __init select_disp_freq(void)
|
||||
"frequency\n");
|
||||
} else {
|
||||
gpio_direction_output(85, 0);
|
||||
gpio_free(104);
|
||||
gpio_free(85);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,52 +0,0 @@
|
||||
/*
|
||||
* linux/arch/arm/mach-mmp/include/mach/mfp-gplugd.h
|
||||
*
|
||||
* MFP definitions used in gplugD
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
#ifndef __MACH_MFP_GPLUGD_H
|
||||
#define __MACH_MFP_GPLUGD_H
|
||||
|
||||
#include <plat/mfp.h>
|
||||
#include <mach/mfp.h>
|
||||
|
||||
/* UART3 */
|
||||
#define GPIO8_UART3_SOUT MFP_CFG(GPIO8, AF2)
|
||||
#define GPIO9_UART3_SIN MFP_CFG(GPIO9, AF2)
|
||||
#define GPI1O_UART3_CTS MFP_CFG(GPIO10, AF2)
|
||||
#define GPI11_UART3_RTS MFP_CFG(GPIO11, AF2)
|
||||
|
||||
/* MMC2 */
|
||||
#define GPIO28_MMC2_CMD MFP_CFG_DRV(GPIO28, AF6, FAST)
|
||||
#define GPIO29_MMC2_CLK MFP_CFG_DRV(GPIO29, AF6, FAST)
|
||||
#define GPIO30_MMC2_DAT0 MFP_CFG_DRV(GPIO30, AF6, FAST)
|
||||
#define GPIO31_MMC2_DAT1 MFP_CFG_DRV(GPIO31, AF6, FAST)
|
||||
#define GPIO32_MMC2_DAT2 MFP_CFG_DRV(GPIO32, AF6, FAST)
|
||||
#define GPIO33_MMC2_DAT3 MFP_CFG_DRV(GPIO33, AF6, FAST)
|
||||
|
||||
/* I2S */
|
||||
#undef GPIO114_I2S_FRM
|
||||
#undef GPIO115_I2S_BCLK
|
||||
|
||||
#define GPIO114_I2S_FRM MFP_CFG_DRV(GPIO114, AF1, FAST)
|
||||
#define GPIO115_I2S_BCLK MFP_CFG_DRV(GPIO115, AF1, FAST)
|
||||
#define GPIO116_I2S_TXD MFP_CFG_DRV(GPIO116, AF1, FAST)
|
||||
|
||||
/* MMC4 */
|
||||
#define GPIO125_MMC4_DAT3 MFP_CFG_DRV(GPIO125, AF7, FAST)
|
||||
#define GPIO126_MMC4_DAT2 MFP_CFG_DRV(GPIO126, AF7, FAST)
|
||||
#define GPIO127_MMC4_DAT1 MFP_CFG_DRV(GPIO127, AF7, FAST)
|
||||
#define GPIO0_2_MMC4_DAT0 MFP_CFG_DRV(GPIO0_2, AF7, FAST)
|
||||
#define GPIO1_2_MMC4_CMD MFP_CFG_DRV(GPIO1_2, AF7, FAST)
|
||||
#define GPIO2_2_MMC4_CLK MFP_CFG_DRV(GPIO2_2, AF7, FAST)
|
||||
|
||||
/* OTG GPIO */
|
||||
#define GPIO_USB_OTG_PEN 18
|
||||
#define GPIO_USB_OIDIR 20
|
||||
|
||||
/* Other GPIOs are 35, 84, 85 */
|
||||
#endif /* __MACH_MFP_GPLUGD_H */
|
@ -203,6 +203,10 @@
|
||||
#define GPIO33_CF_nCD2 MFP_CFG(GPIO33, AF3)
|
||||
|
||||
/* UART */
|
||||
#define GPIO8_UART3_TXD MFP_CFG(GPIO8, AF2)
|
||||
#define GPIO9_UART3_RXD MFP_CFG(GPIO9, AF2)
|
||||
#define GPIO1O_UART3_CTS MFP_CFG(GPIO10, AF2)
|
||||
#define GPIO11_UART3_RTS MFP_CFG(GPIO11, AF2)
|
||||
#define GPIO88_UART2_TXD MFP_CFG(GPIO88, AF2)
|
||||
#define GPIO89_UART2_RXD MFP_CFG(GPIO89, AF2)
|
||||
#define GPIO107_UART1_TXD MFP_CFG_DRV(GPIO107, AF1, FAST)
|
||||
@ -232,6 +236,22 @@
|
||||
#define GPIO53_MMC1_CD MFP_CFG(GPIO53, AF1)
|
||||
#define GPIO46_MMC1_WP MFP_CFG(GPIO46, AF1)
|
||||
|
||||
/* MMC2 */
|
||||
#define GPIO28_MMC2_CMD MFP_CFG_DRV(GPIO28, AF6, FAST)
|
||||
#define GPIO29_MMC2_CLK MFP_CFG_DRV(GPIO29, AF6, FAST)
|
||||
#define GPIO30_MMC2_DAT0 MFP_CFG_DRV(GPIO30, AF6, FAST)
|
||||
#define GPIO31_MMC2_DAT1 MFP_CFG_DRV(GPIO31, AF6, FAST)
|
||||
#define GPIO32_MMC2_DAT2 MFP_CFG_DRV(GPIO32, AF6, FAST)
|
||||
#define GPIO33_MMC2_DAT3 MFP_CFG_DRV(GPIO33, AF6, FAST)
|
||||
|
||||
/* MMC4 */
|
||||
#define GPIO125_MMC4_DAT3 MFP_CFG_DRV(GPIO125, AF7, FAST)
|
||||
#define GPIO126_MMC4_DAT2 MFP_CFG_DRV(GPIO126, AF7, FAST)
|
||||
#define GPIO127_MMC4_DAT1 MFP_CFG_DRV(GPIO127, AF7, FAST)
|
||||
#define GPIO0_2_MMC4_DAT0 MFP_CFG_DRV(GPIO0_2, AF7, FAST)
|
||||
#define GPIO1_2_MMC4_CMD MFP_CFG_DRV(GPIO1_2, AF7, FAST)
|
||||
#define GPIO2_2_MMC4_CLK MFP_CFG_DRV(GPIO2_2, AF7, FAST)
|
||||
|
||||
/* LCD */
|
||||
#define GPIO84_LCD_CS MFP_CFG(GPIO84, AF1)
|
||||
#define GPIO60_LCD_DD0 MFP_CFG(GPIO60, AF1)
|
||||
@ -269,11 +289,12 @@
|
||||
#define GPIO106_CI2C_SCL MFP_CFG(GPIO106, AF1)
|
||||
|
||||
/* I2S */
|
||||
#define GPIO113_I2S_MCLK MFP_CFG(GPIO113,AF6)
|
||||
#define GPIO114_I2S_FRM MFP_CFG(GPIO114,AF1)
|
||||
#define GPIO115_I2S_BCLK MFP_CFG(GPIO115,AF1)
|
||||
#define GPIO116_I2S_RXD MFP_CFG(GPIO116,AF2)
|
||||
#define GPIO117_I2S_TXD MFP_CFG(GPIO117,AF2)
|
||||
#define GPIO113_I2S_MCLK MFP_CFG(GPIO113, AF6)
|
||||
#define GPIO114_I2S_FRM MFP_CFG(GPIO114, AF1)
|
||||
#define GPIO115_I2S_BCLK MFP_CFG(GPIO115, AF1)
|
||||
#define GPIO116_I2S_RXD MFP_CFG(GPIO116, AF2)
|
||||
#define GPIO116_I2S_TXD MFP_CFG(GPIO116, AF1)
|
||||
#define GPIO117_I2S_TXD MFP_CFG(GPIO117, AF2)
|
||||
|
||||
/* PWM */
|
||||
#define GPIO96_PWM3_OUT MFP_CFG(GPIO96, AF1)
|
||||
@ -324,4 +345,10 @@
|
||||
#define GPIO101_MII_MDIO MFP_CFG(GPIO101, AF5)
|
||||
#define GPIO103_RX_DV MFP_CFG(GPIO103, AF5)
|
||||
|
||||
/* SSP2 */
|
||||
#define GPIO107_SSP2_RXD MFP_CFG(GPIO107, AF4)
|
||||
#define GPIO108_SSP2_TXD MFP_CFG(GPIO108, AF4)
|
||||
#define GPIO111_SSP2_CLK MFP_CFG(GPIO111, AF4)
|
||||
#define GPIO112_SSP2_FRM MFP_CFG(GPIO112, AF4)
|
||||
|
||||
#endif /* __ASM_MACH_MFP_PXA168_H */
|
||||
|
@ -51,12 +51,12 @@ static inline uint32_t timer_read(void)
|
||||
{
|
||||
int delay = 100;
|
||||
|
||||
__raw_writel(1, TIMERS_VIRT_BASE + TMR_CVWR(0));
|
||||
__raw_writel(1, TIMERS_VIRT_BASE + TMR_CVWR(1));
|
||||
|
||||
while (delay--)
|
||||
cpu_relax();
|
||||
|
||||
return __raw_readl(TIMERS_VIRT_BASE + TMR_CVWR(0));
|
||||
return __raw_readl(TIMERS_VIRT_BASE + TMR_CVWR(1));
|
||||
}
|
||||
|
||||
unsigned long long notrace sched_clock(void)
|
||||
@ -75,28 +75,51 @@ static irqreturn_t timer_interrupt(int irq, void *dev_id)
|
||||
{
|
||||
struct clock_event_device *c = dev_id;
|
||||
|
||||
/* disable and clear pending interrupt status */
|
||||
__raw_writel(0x0, TIMERS_VIRT_BASE + TMR_IER(0));
|
||||
__raw_writel(0x1, TIMERS_VIRT_BASE + TMR_ICR(0));
|
||||
/*
|
||||
* Clear pending interrupt status.
|
||||
*/
|
||||
__raw_writel(0x01, TIMERS_VIRT_BASE + TMR_ICR(0));
|
||||
|
||||
/*
|
||||
* Disable timer 0.
|
||||
*/
|
||||
__raw_writel(0x02, TIMERS_VIRT_BASE + TMR_CER);
|
||||
|
||||
c->event_handler(c);
|
||||
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
static int timer_set_next_event(unsigned long delta,
|
||||
struct clock_event_device *dev)
|
||||
{
|
||||
unsigned long flags, next;
|
||||
unsigned long flags;
|
||||
|
||||
local_irq_save(flags);
|
||||
|
||||
/* clear pending interrupt status and enable */
|
||||
/*
|
||||
* Disable timer 0.
|
||||
*/
|
||||
__raw_writel(0x02, TIMERS_VIRT_BASE + TMR_CER);
|
||||
|
||||
/*
|
||||
* Clear and enable timer match 0 interrupt.
|
||||
*/
|
||||
__raw_writel(0x01, TIMERS_VIRT_BASE + TMR_ICR(0));
|
||||
__raw_writel(0x01, TIMERS_VIRT_BASE + TMR_IER(0));
|
||||
|
||||
next = timer_read() + delta;
|
||||
__raw_writel(next, TIMERS_VIRT_BASE + TMR_TN_MM(0, 0));
|
||||
/*
|
||||
* Setup new clockevent timer value.
|
||||
*/
|
||||
__raw_writel(delta - 1, TIMERS_VIRT_BASE + TMR_TN_MM(0, 0));
|
||||
|
||||
/*
|
||||
* Enable timer 0.
|
||||
*/
|
||||
__raw_writel(0x03, TIMERS_VIRT_BASE + TMR_CER);
|
||||
|
||||
local_irq_restore(flags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -145,23 +168,26 @@ static struct clocksource cksrc = {
|
||||
static void __init timer_config(void)
|
||||
{
|
||||
uint32_t ccr = __raw_readl(TIMERS_VIRT_BASE + TMR_CCR);
|
||||
uint32_t cer = __raw_readl(TIMERS_VIRT_BASE + TMR_CER);
|
||||
uint32_t cmr = __raw_readl(TIMERS_VIRT_BASE + TMR_CMR);
|
||||
|
||||
__raw_writel(cer & ~0x1, TIMERS_VIRT_BASE + TMR_CER); /* disable */
|
||||
__raw_writel(0x0, TIMERS_VIRT_BASE + TMR_CER); /* disable */
|
||||
|
||||
ccr &= (cpu_is_mmp2()) ? TMR_CCR_CS_0(0) : TMR_CCR_CS_0(3);
|
||||
ccr &= (cpu_is_mmp2()) ? (TMR_CCR_CS_0(0) | TMR_CCR_CS_1(0)) :
|
||||
(TMR_CCR_CS_0(3) | TMR_CCR_CS_1(3));
|
||||
__raw_writel(ccr, TIMERS_VIRT_BASE + TMR_CCR);
|
||||
|
||||
/* free-running mode */
|
||||
__raw_writel(cmr | 0x01, TIMERS_VIRT_BASE + TMR_CMR);
|
||||
/* set timer 0 to periodic mode, and timer 1 to free-running mode */
|
||||
__raw_writel(0x2, TIMERS_VIRT_BASE + TMR_CMR);
|
||||
|
||||
__raw_writel(0x0, TIMERS_VIRT_BASE + TMR_PLCR(0)); /* free-running */
|
||||
__raw_writel(0x1, TIMERS_VIRT_BASE + TMR_PLCR(0)); /* periodic */
|
||||
__raw_writel(0x7, TIMERS_VIRT_BASE + TMR_ICR(0)); /* clear status */
|
||||
__raw_writel(0x0, TIMERS_VIRT_BASE + TMR_IER(0));
|
||||
|
||||
/* enable timer counter */
|
||||
__raw_writel(cer | 0x01, TIMERS_VIRT_BASE + TMR_CER);
|
||||
__raw_writel(0x0, TIMERS_VIRT_BASE + TMR_PLCR(1)); /* free-running */
|
||||
__raw_writel(0x7, TIMERS_VIRT_BASE + TMR_ICR(1)); /* clear status */
|
||||
__raw_writel(0x0, TIMERS_VIRT_BASE + TMR_IER(1));
|
||||
|
||||
/* enable timer 1 counter */
|
||||
__raw_writel(0x2, TIMERS_VIRT_BASE + TMR_CER);
|
||||
}
|
||||
|
||||
static struct irqaction timer_irq = {
|
||||
|
@ -81,7 +81,7 @@ static struct plat_serial8250_port serial_platform_data[] = {
|
||||
.flags = UPF_BOOT_AUTOCONF | UPF_SKIP_TEST | UPF_IOREMAP,
|
||||
}, {
|
||||
.mapbase = (unsigned long)(MX51_CS1_BASE_ADDR + 0x2000000),
|
||||
.irq = irq_to_gpio(CPUIMX51_QUARTD_GPIO),
|
||||
.irq = gpio_to_irq(CPUIMX51_QUARTD_GPIO),
|
||||
.irqflags = IRQF_TRIGGER_HIGH,
|
||||
.uartclk = CPUIMX51_QUART_XTAL,
|
||||
.regshift = CPUIMX51_QUART_REGSHIFT,
|
||||
|
@ -369,7 +369,7 @@ static void __init mx51_babbage_init(void)
|
||||
ARRAY_SIZE(mx51babbage_pads));
|
||||
|
||||
imx51_add_imx_uart(0, &uart_pdata);
|
||||
imx51_add_imx_uart(1, &uart_pdata);
|
||||
imx51_add_imx_uart(1, NULL);
|
||||
imx51_add_imx_uart(2, &uart_pdata);
|
||||
|
||||
babbage_fec_reset();
|
||||
|
@ -108,9 +108,9 @@ static void __init mx51_efikamx_board_id(void)
|
||||
gpio_request(EFIKAMX_PCBID2, "pcbid2");
|
||||
gpio_direction_input(EFIKAMX_PCBID2);
|
||||
|
||||
id = gpio_get_value(EFIKAMX_PCBID0);
|
||||
id |= gpio_get_value(EFIKAMX_PCBID1) << 1;
|
||||
id |= gpio_get_value(EFIKAMX_PCBID2) << 2;
|
||||
id = gpio_get_value(EFIKAMX_PCBID0) ? 1 : 0;
|
||||
id |= (gpio_get_value(EFIKAMX_PCBID1) ? 1 : 0) << 1;
|
||||
id |= (gpio_get_value(EFIKAMX_PCBID2) ? 1 : 0) << 2;
|
||||
|
||||
switch (id) {
|
||||
case 7:
|
||||
|
@ -156,23 +156,24 @@ static struct gpio_keys_button mx51_efikasb_keys[] = {
|
||||
{
|
||||
.code = KEY_POWER,
|
||||
.gpio = EFIKASB_PWRKEY,
|
||||
.type = EV_PWR,
|
||||
.type = EV_KEY,
|
||||
.desc = "Power Button",
|
||||
.wakeup = 1,
|
||||
.debounce_interval = 10, /* ms */
|
||||
.active_low = 1,
|
||||
},
|
||||
{
|
||||
.code = SW_LID,
|
||||
.gpio = EFIKASB_LID,
|
||||
.type = EV_SW,
|
||||
.desc = "Lid Switch",
|
||||
.active_low = 1,
|
||||
},
|
||||
{
|
||||
/* SW_RFKILLALL vs KEY_RFKILL ? */
|
||||
.code = SW_RFKILL_ALL,
|
||||
.code = KEY_RFKILL,
|
||||
.gpio = EFIKASB_RFKILL,
|
||||
.type = EV_SW,
|
||||
.type = EV_KEY,
|
||||
.desc = "rfkill",
|
||||
.active_low = 1,
|
||||
},
|
||||
};
|
||||
|
||||
@ -224,8 +225,8 @@ static void __init mx51_efikasb_board_id(void)
|
||||
gpio_request(EFIKASB_PCBID1, "pcb id1");
|
||||
gpio_direction_input(EFIKASB_PCBID1);
|
||||
|
||||
id = gpio_get_value(EFIKASB_PCBID0);
|
||||
id |= gpio_get_value(EFIKASB_PCBID1) << 1;
|
||||
id = gpio_get_value(EFIKASB_PCBID0) ? 1 : 0;
|
||||
id |= (gpio_get_value(EFIKASB_PCBID1) ? 1 : 0) << 1;
|
||||
|
||||
switch (id) {
|
||||
default:
|
||||
|
@ -271,7 +271,11 @@ static int _clk_pll_enable(struct clk *clk)
|
||||
int i = 0;
|
||||
|
||||
pllbase = _get_pll_base(clk);
|
||||
reg = __raw_readl(pllbase + MXC_PLL_DP_CTL) | MXC_PLL_DP_CTL_UPEN;
|
||||
reg = __raw_readl(pllbase + MXC_PLL_DP_CTL);
|
||||
if (reg & MXC_PLL_DP_CTL_UPEN)
|
||||
return 0;
|
||||
|
||||
reg |= MXC_PLL_DP_CTL_UPEN;
|
||||
__raw_writel(reg, pllbase + MXC_PLL_DP_CTL);
|
||||
|
||||
/* Wait for lock */
|
||||
|
@ -186,7 +186,7 @@ static int initialize_usbh1_port(struct platform_device *pdev)
|
||||
|
||||
mdelay(10);
|
||||
|
||||
return mx51_initialize_usb_hw(0, MXC_EHCI_ITC_NO_THRESHOLD);
|
||||
return mx51_initialize_usb_hw(pdev->id, MXC_EHCI_ITC_NO_THRESHOLD);
|
||||
}
|
||||
|
||||
static struct mxc_usbh_platform_data usbh1_config = {
|
||||
|
@ -7,7 +7,6 @@ config ARCH_OMAP2PLUS_TYPICAL
|
||||
default y
|
||||
select AEABI
|
||||
select REGULATOR
|
||||
select PM
|
||||
select PM_RUNTIME
|
||||
select VFP
|
||||
select NEON if ARCH_OMAP3 || ARCH_OMAP4
|
||||
|
@ -45,8 +45,6 @@ static struct omap_board_config_kernel am3517_crane_config[] __initdata = {
|
||||
static struct omap_board_mux board_mux[] __initdata = {
|
||||
{ .reg_offset = OMAP_MUX_TERMINATOR },
|
||||
};
|
||||
#else
|
||||
#define board_mux NULL
|
||||
#endif
|
||||
|
||||
static void __init am3517_crane_init_early(void)
|
||||
|
@ -491,23 +491,22 @@ static void __init beagle_opp_init(void)
|
||||
|
||||
/* Custom OPP enabled for all xM versions */
|
||||
if (cpu_is_omap3630()) {
|
||||
struct omap_hwmod *mh = omap_hwmod_lookup("mpu");
|
||||
struct omap_hwmod *dh = omap_hwmod_lookup("iva");
|
||||
struct device *dev;
|
||||
struct device *mpu_dev, *iva_dev;
|
||||
|
||||
if (!mh || !dh) {
|
||||
mpu_dev = omap2_get_mpuss_device();
|
||||
iva_dev = omap2_get_iva_device();
|
||||
|
||||
if (!mpu_dev || !iva_dev) {
|
||||
pr_err("%s: Aiee.. no mpu/dsp devices? %p %p\n",
|
||||
__func__, mh, dh);
|
||||
__func__, mpu_dev, iva_dev);
|
||||
return;
|
||||
}
|
||||
/* Enable MPU 1GHz and lower opps */
|
||||
dev = &mh->od->pdev.dev;
|
||||
r = opp_enable(dev, 800000000);
|
||||
r = opp_enable(mpu_dev, 800000000);
|
||||
/* TODO: MPU 1GHz needs SR and ABB */
|
||||
|
||||
/* Enable IVA 800MHz and lower opps */
|
||||
dev = &dh->od->pdev.dev;
|
||||
r |= opp_enable(dev, 660000000);
|
||||
r |= opp_enable(iva_dev, 660000000);
|
||||
/* TODO: DSP 800MHz needs SR and ABB */
|
||||
if (r) {
|
||||
pr_err("%s: failed to enable higher opp %d\n",
|
||||
@ -516,10 +515,8 @@ static void __init beagle_opp_init(void)
|
||||
* Cleanup - disable the higher freqs - we dont care
|
||||
* about the results
|
||||
*/
|
||||
dev = &mh->od->pdev.dev;
|
||||
opp_disable(dev, 800000000);
|
||||
dev = &dh->od->pdev.dev;
|
||||
opp_disable(dev, 660000000);
|
||||
opp_disable(mpu_dev, 800000000);
|
||||
opp_disable(iva_dev, 660000000);
|
||||
}
|
||||
}
|
||||
return;
|
||||
|
@ -18,13 +18,36 @@ extern void omap4_cminst_clkdm_force_sleep(u8 part, s16 inst, u16 cdoffs);
|
||||
extern void omap4_cminst_clkdm_force_wakeup(u8 part, s16 inst, u16 cdoffs);
|
||||
|
||||
extern int omap4_cminst_wait_module_ready(u8 part, u16 inst, s16 cdoffs, u16 clkctrl_offs);
|
||||
extern int omap4_cminst_wait_module_idle(u8 part, u16 inst, s16 cdoffs, u16 clkctrl_offs);
|
||||
|
||||
# ifdef CONFIG_ARCH_OMAP4
|
||||
extern int omap4_cminst_wait_module_idle(u8 part, u16 inst, s16 cdoffs,
|
||||
u16 clkctrl_offs);
|
||||
|
||||
extern void omap4_cminst_module_enable(u8 mode, u8 part, u16 inst, s16 cdoffs,
|
||||
u16 clkctrl_offs);
|
||||
extern void omap4_cminst_module_disable(u8 part, u16 inst, s16 cdoffs,
|
||||
u16 clkctrl_offs);
|
||||
|
||||
# else
|
||||
|
||||
static inline int omap4_cminst_wait_module_idle(u8 part, u16 inst, s16 cdoffs,
|
||||
u16 clkctrl_offs)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline void omap4_cminst_module_enable(u8 mode, u8 part, u16 inst,
|
||||
s16 cdoffs, u16 clkctrl_offs)
|
||||
{
|
||||
}
|
||||
|
||||
static inline void omap4_cminst_module_disable(u8 part, u16 inst, s16 cdoffs,
|
||||
u16 clkctrl_offs)
|
||||
{
|
||||
}
|
||||
|
||||
# endif
|
||||
|
||||
/*
|
||||
* In an ideal world, we would not export these low-level functions,
|
||||
* but this will probably take some time to fix properly
|
||||
|
@ -821,11 +821,10 @@ static void __init omap_mux_set_cmdline_signals(void)
|
||||
if (!omap_mux_options)
|
||||
return;
|
||||
|
||||
options = kmalloc(strlen(omap_mux_options) + 1, GFP_KERNEL);
|
||||
options = kstrdup(omap_mux_options, GFP_KERNEL);
|
||||
if (!options)
|
||||
return;
|
||||
|
||||
strcpy(options, omap_mux_options);
|
||||
next_opt = options;
|
||||
|
||||
while ((token = strsep(&next_opt, ",")) != NULL) {
|
||||
@ -855,24 +854,19 @@ static int __init omap_mux_copy_names(struct omap_mux *src,
|
||||
|
||||
for (i = 0; i < OMAP_MUX_NR_MODES; i++) {
|
||||
if (src->muxnames[i]) {
|
||||
dst->muxnames[i] =
|
||||
kmalloc(strlen(src->muxnames[i]) + 1,
|
||||
GFP_KERNEL);
|
||||
dst->muxnames[i] = kstrdup(src->muxnames[i],
|
||||
GFP_KERNEL);
|
||||
if (!dst->muxnames[i])
|
||||
goto free;
|
||||
strcpy(dst->muxnames[i], src->muxnames[i]);
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef CONFIG_DEBUG_FS
|
||||
for (i = 0; i < OMAP_MUX_NR_SIDES; i++) {
|
||||
if (src->balls[i]) {
|
||||
dst->balls[i] =
|
||||
kmalloc(strlen(src->balls[i]) + 1,
|
||||
GFP_KERNEL);
|
||||
dst->balls[i] = kstrdup(src->balls[i], GFP_KERNEL);
|
||||
if (!dst->balls[i])
|
||||
goto free;
|
||||
strcpy(dst->balls[i], src->balls[i]);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
@ -621,7 +621,7 @@ void sr_disable(struct voltagedomain *voltdm)
|
||||
sr_v2_disable(sr);
|
||||
}
|
||||
|
||||
pm_runtime_put_sync(&sr->pdev->dev);
|
||||
pm_runtime_put_sync_suspend(&sr->pdev->dev);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -860,6 +860,7 @@ static int __init omap_sr_probe(struct platform_device *pdev)
|
||||
irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
|
||||
|
||||
pm_runtime_enable(&pdev->dev);
|
||||
pm_runtime_irq_safe(&pdev->dev);
|
||||
|
||||
sr_info->pdev = pdev;
|
||||
sr_info->srid = pdev->id;
|
||||
|
@ -293,7 +293,8 @@ static void __init omap2_gp_clocksource_init(int gptimer_id,
|
||||
pr_info("OMAP clocksource: GPTIMER%d at %lu Hz\n",
|
||||
gptimer_id, clksrc.rate);
|
||||
|
||||
__omap_dm_timer_load_start(clksrc.io_base, OMAP_TIMER_CTRL_ST, 0, 1);
|
||||
__omap_dm_timer_load_start(clksrc.io_base,
|
||||
OMAP_TIMER_CTRL_ST | OMAP_TIMER_CTRL_AR, 0, 1);
|
||||
init_sched_clock(&cd, dmtimer_update_sched_clock, 32, clksrc.rate);
|
||||
|
||||
if (clocksource_register_hz(&clocksource_gpt, clksrc.rate))
|
||||
|
@ -48,14 +48,7 @@ void __init omap_pmic_init(int bus, u32 clkrate,
|
||||
omap_register_i2c_bus(bus, clkrate, &pmic_i2c_board_info, 1);
|
||||
}
|
||||
|
||||
static struct twl4030_usb_data omap4_usb_pdata = {
|
||||
.phy_init = omap4430_phy_init,
|
||||
.phy_exit = omap4430_phy_exit,
|
||||
.phy_power = omap4430_phy_power,
|
||||
.phy_set_clock = omap4430_phy_set_clk,
|
||||
.phy_suspend = omap4430_phy_suspend,
|
||||
};
|
||||
|
||||
#if defined(CONFIG_ARCH_OMAP3)
|
||||
static struct twl4030_usb_data omap3_usb_pdata = {
|
||||
.usb_mode = T2_USB_MODE_ULPI,
|
||||
};
|
||||
@ -122,6 +115,45 @@ static struct regulator_init_data omap3_vpll2_idata = {
|
||||
.consumer_supplies = omap3_vpll2_supplies,
|
||||
};
|
||||
|
||||
void __init omap3_pmic_get_config(struct twl4030_platform_data *pmic_data,
|
||||
u32 pdata_flags, u32 regulators_flags)
|
||||
{
|
||||
if (!pmic_data->irq_base)
|
||||
pmic_data->irq_base = TWL4030_IRQ_BASE;
|
||||
if (!pmic_data->irq_end)
|
||||
pmic_data->irq_end = TWL4030_IRQ_END;
|
||||
|
||||
/* Common platform data configurations */
|
||||
if (pdata_flags & TWL_COMMON_PDATA_USB && !pmic_data->usb)
|
||||
pmic_data->usb = &omap3_usb_pdata;
|
||||
|
||||
if (pdata_flags & TWL_COMMON_PDATA_BCI && !pmic_data->bci)
|
||||
pmic_data->bci = &omap3_bci_pdata;
|
||||
|
||||
if (pdata_flags & TWL_COMMON_PDATA_MADC && !pmic_data->madc)
|
||||
pmic_data->madc = &omap3_madc_pdata;
|
||||
|
||||
if (pdata_flags & TWL_COMMON_PDATA_AUDIO && !pmic_data->audio)
|
||||
pmic_data->audio = &omap3_audio_pdata;
|
||||
|
||||
/* Common regulator configurations */
|
||||
if (regulators_flags & TWL_COMMON_REGULATOR_VDAC && !pmic_data->vdac)
|
||||
pmic_data->vdac = &omap3_vdac_idata;
|
||||
|
||||
if (regulators_flags & TWL_COMMON_REGULATOR_VPLL2 && !pmic_data->vpll2)
|
||||
pmic_data->vpll2 = &omap3_vpll2_idata;
|
||||
}
|
||||
#endif /* CONFIG_ARCH_OMAP3 */
|
||||
|
||||
#if defined(CONFIG_ARCH_OMAP4)
|
||||
static struct twl4030_usb_data omap4_usb_pdata = {
|
||||
.phy_init = omap4430_phy_init,
|
||||
.phy_exit = omap4430_phy_exit,
|
||||
.phy_power = omap4430_phy_power,
|
||||
.phy_set_clock = omap4430_phy_set_clk,
|
||||
.phy_suspend = omap4430_phy_suspend,
|
||||
};
|
||||
|
||||
static struct regulator_init_data omap4_vdac_idata = {
|
||||
.constraints = {
|
||||
.min_uV = 1800000,
|
||||
@ -273,32 +305,4 @@ void __init omap4_pmic_get_config(struct twl4030_platform_data *pmic_data,
|
||||
!pmic_data->clk32kg)
|
||||
pmic_data->clk32kg = &omap4_clk32kg_idata;
|
||||
}
|
||||
|
||||
void __init omap3_pmic_get_config(struct twl4030_platform_data *pmic_data,
|
||||
u32 pdata_flags, u32 regulators_flags)
|
||||
{
|
||||
if (!pmic_data->irq_base)
|
||||
pmic_data->irq_base = TWL4030_IRQ_BASE;
|
||||
if (!pmic_data->irq_end)
|
||||
pmic_data->irq_end = TWL4030_IRQ_END;
|
||||
|
||||
/* Common platform data configurations */
|
||||
if (pdata_flags & TWL_COMMON_PDATA_USB && !pmic_data->usb)
|
||||
pmic_data->usb = &omap3_usb_pdata;
|
||||
|
||||
if (pdata_flags & TWL_COMMON_PDATA_BCI && !pmic_data->bci)
|
||||
pmic_data->bci = &omap3_bci_pdata;
|
||||
|
||||
if (pdata_flags & TWL_COMMON_PDATA_MADC && !pmic_data->madc)
|
||||
pmic_data->madc = &omap3_madc_pdata;
|
||||
|
||||
if (pdata_flags & TWL_COMMON_PDATA_AUDIO && !pmic_data->audio)
|
||||
pmic_data->audio = &omap3_audio_pdata;
|
||||
|
||||
/* Common regulator configurations */
|
||||
if (regulators_flags & TWL_COMMON_REGULATOR_VDAC && !pmic_data->vdac)
|
||||
pmic_data->vdac = &omap3_vdac_idata;
|
||||
|
||||
if (regulators_flags & TWL_COMMON_REGULATOR_VPLL2 && !pmic_data->vpll2)
|
||||
pmic_data->vpll2 = &omap3_vpll2_idata;
|
||||
}
|
||||
#endif /* CONFIG_ARCH_OMAP4 */
|
||||
|
@ -28,6 +28,7 @@
|
||||
#include <asm/mach-types.h>
|
||||
|
||||
#include <mach/nanoengine.h>
|
||||
#include <mach/hardware.h>
|
||||
|
||||
static DEFINE_SPINLOCK(nano_lock);
|
||||
|
||||
|
@ -44,6 +44,14 @@
|
||||
#define UART_PADDR MX51_UART1_BASE_ADDR
|
||||
#endif
|
||||
|
||||
/* iMX50/53 have same addresses, but not iMX51 */
|
||||
#if defined(CONFIG_SOC_IMX50) || defined(CONFIG_SOC_IMX53)
|
||||
#ifdef UART_PADDR
|
||||
#error "CONFIG_DEBUG_LL is incompatible with multiple archs"
|
||||
#endif
|
||||
#define UART_PADDR MX53_UART1_BASE_ADDR
|
||||
#endif
|
||||
|
||||
#define UART_VADDR IMX_IO_ADDRESS(UART_PADDR)
|
||||
|
||||
.macro addruart, rp, rv
|
||||
|
@ -30,6 +30,9 @@
|
||||
#define MX53_SDHC_PAD_CTRL (PAD_CTL_HYS | PAD_CTL_PKE | PAD_CTL_PUE | \
|
||||
PAD_CTL_PUS_47K_UP | PAD_CTL_DSE_HIGH | \
|
||||
PAD_CTL_SRE_FAST)
|
||||
#define PAD_CTRL_I2C (PAD_CTL_SRE_FAST | PAD_CTL_ODE | PAD_CTL_PKE | \
|
||||
PAD_CTL_PUE | PAD_CTL_DSE_HIGH | PAD_CTL_PUS_100K_UP \
|
||||
| PAD_CTL_HYS)
|
||||
|
||||
#define _MX53_PAD_GPIO_19__KPP_COL_5 IOMUX_PAD(0x348, 0x20, 0, 0x840, 0, 0)
|
||||
#define _MX53_PAD_GPIO_19__GPIO4_5 IOMUX_PAD(0x348, 0x20, 1, 0x0, 0, 0)
|
||||
@ -1256,7 +1259,7 @@
|
||||
#define MX53_PAD_KEY_COL3__GPIO4_12 (_MX53_PAD_KEY_COL3__GPIO4_12 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_COL3__USBOH3_H2_DP (_MX53_PAD_KEY_COL3__USBOH3_H2_DP | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_COL3__SPDIF_IN1 (_MX53_PAD_KEY_COL3__SPDIF_IN1 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_COL3__I2C2_SCL (_MX53_PAD_KEY_COL3__I2C2_SCL | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_COL3__I2C2_SCL (_MX53_PAD_KEY_COL3__I2C2_SCL | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_KEY_COL3__ECSPI1_SS3 (_MX53_PAD_KEY_COL3__ECSPI1_SS3 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_COL3__FEC_CRS (_MX53_PAD_KEY_COL3__FEC_CRS | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_COL3__USBPHY1_SIECLOCK (_MX53_PAD_KEY_COL3__USBPHY1_SIECLOCK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -1264,7 +1267,7 @@
|
||||
#define MX53_PAD_KEY_ROW3__GPIO4_13 (_MX53_PAD_KEY_ROW3__GPIO4_13 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_ROW3__USBOH3_H2_DM (_MX53_PAD_KEY_ROW3__USBOH3_H2_DM | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_ROW3__CCM_ASRC_EXT_CLK (_MX53_PAD_KEY_ROW3__CCM_ASRC_EXT_CLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_ROW3__I2C2_SDA (_MX53_PAD_KEY_ROW3__I2C2_SDA | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_ROW3__I2C2_SDA (_MX53_PAD_KEY_ROW3__I2C2_SDA | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_KEY_ROW3__OSC32K_32K_OUT (_MX53_PAD_KEY_ROW3__OSC32K_32K_OUT | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_ROW3__CCM_PLL4_BYP (_MX53_PAD_KEY_ROW3__CCM_PLL4_BYP | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_KEY_ROW3__USBPHY1_LINESTATE_0 (_MX53_PAD_KEY_ROW3__USBPHY1_LINESTATE_0 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -1536,7 +1539,7 @@
|
||||
#define MX53_PAD_CSI0_DAT8__KPP_COL_7 (_MX53_PAD_CSI0_DAT8__KPP_COL_7 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT8__ECSPI2_SCLK (_MX53_PAD_CSI0_DAT8__ECSPI2_SCLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT8__USBOH3_USBH3_OC (_MX53_PAD_CSI0_DAT8__USBOH3_USBH3_OC | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT8__I2C1_SDA (_MX53_PAD_CSI0_DAT8__I2C1_SDA | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT8__I2C1_SDA (_MX53_PAD_CSI0_DAT8__I2C1_SDA | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_CSI0_DAT8__EMI_EMI_DEBUG_37 (_MX53_PAD_CSI0_DAT8__EMI_EMI_DEBUG_37 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT8__TPIU_TRACE_5 (_MX53_PAD_CSI0_DAT8__TPIU_TRACE_5 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT9__IPU_CSI0_D_9 (_MX53_PAD_CSI0_DAT9__IPU_CSI0_D_9 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -1544,7 +1547,7 @@
|
||||
#define MX53_PAD_CSI0_DAT9__KPP_ROW_7 (_MX53_PAD_CSI0_DAT9__KPP_ROW_7 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT9__ECSPI2_MOSI (_MX53_PAD_CSI0_DAT9__ECSPI2_MOSI | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT9__USBOH3_USBH3_PWR (_MX53_PAD_CSI0_DAT9__USBOH3_USBH3_PWR | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT9__I2C1_SCL (_MX53_PAD_CSI0_DAT9__I2C1_SCL | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT9__I2C1_SCL (_MX53_PAD_CSI0_DAT9__I2C1_SCL | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_CSI0_DAT9__EMI_EMI_DEBUG_38 (_MX53_PAD_CSI0_DAT9__EMI_EMI_DEBUG_38 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT9__TPIU_TRACE_6 (_MX53_PAD_CSI0_DAT9__TPIU_TRACE_6 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_CSI0_DAT10__IPU_CSI0_D_10 (_MX53_PAD_CSI0_DAT10__IPU_CSI0_D_10 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -1631,25 +1634,25 @@
|
||||
#define MX53_PAD_EIM_EB2__CCM_DI1_EXT_CLK (_MX53_PAD_EIM_EB2__CCM_DI1_EXT_CLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_EB2__IPU_SER_DISP1_CS (_MX53_PAD_EIM_EB2__IPU_SER_DISP1_CS | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_EB2__ECSPI1_SS0 (_MX53_PAD_EIM_EB2__ECSPI1_SS0 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_EB2__I2C2_SCL (_MX53_PAD_EIM_EB2__I2C2_SCL | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_EB2__I2C2_SCL (_MX53_PAD_EIM_EB2__I2C2_SCL | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_EIM_D16__EMI_WEIM_D_16 (_MX53_PAD_EIM_D16__EMI_WEIM_D_16 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D16__GPIO3_16 (_MX53_PAD_EIM_D16__GPIO3_16 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D16__IPU_DI0_PIN5 (_MX53_PAD_EIM_D16__IPU_DI0_PIN5 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D16__IPU_DISPB1_SER_CLK (_MX53_PAD_EIM_D16__IPU_DISPB1_SER_CLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D16__ECSPI1_SCLK (_MX53_PAD_EIM_D16__ECSPI1_SCLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D16__I2C2_SDA (_MX53_PAD_EIM_D16__I2C2_SDA | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D16__I2C2_SDA (_MX53_PAD_EIM_D16__I2C2_SDA | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_EIM_D17__EMI_WEIM_D_17 (_MX53_PAD_EIM_D17__EMI_WEIM_D_17 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D17__GPIO3_17 (_MX53_PAD_EIM_D17__GPIO3_17 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D17__IPU_DI0_PIN6 (_MX53_PAD_EIM_D17__IPU_DI0_PIN6 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D17__IPU_DISPB1_SER_DIN (_MX53_PAD_EIM_D17__IPU_DISPB1_SER_DIN | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D17__ECSPI1_MISO (_MX53_PAD_EIM_D17__ECSPI1_MISO | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D17__I2C3_SCL (_MX53_PAD_EIM_D17__I2C3_SCL | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D17__I2C3_SCL (_MX53_PAD_EIM_D17__I2C3_SCL | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_EIM_D18__EMI_WEIM_D_18 (_MX53_PAD_EIM_D18__EMI_WEIM_D_18 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D18__GPIO3_18 (_MX53_PAD_EIM_D18__GPIO3_18 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D18__IPU_DI0_PIN7 (_MX53_PAD_EIM_D18__IPU_DI0_PIN7 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D18__IPU_DISPB1_SER_DIO (_MX53_PAD_EIM_D18__IPU_DISPB1_SER_DIO | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D18__ECSPI1_MOSI (_MX53_PAD_EIM_D18__ECSPI1_MOSI | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D18__I2C3_SDA (_MX53_PAD_EIM_D18__I2C3_SDA | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D18__I2C3_SDA (_MX53_PAD_EIM_D18__I2C3_SDA | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_EIM_D18__IPU_DI1_D0_CS (_MX53_PAD_EIM_D18__IPU_DI1_D0_CS | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D19__EMI_WEIM_D_19 (_MX53_PAD_EIM_D19__EMI_WEIM_D_19 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D19__GPIO3_19 (_MX53_PAD_EIM_D19__GPIO3_19 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -1672,7 +1675,7 @@
|
||||
#define MX53_PAD_EIM_D21__IPU_DI0_PIN17 (_MX53_PAD_EIM_D21__IPU_DI0_PIN17 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D21__IPU_DISPB0_SER_CLK (_MX53_PAD_EIM_D21__IPU_DISPB0_SER_CLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D21__CSPI_SCLK (_MX53_PAD_EIM_D21__CSPI_SCLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D21__I2C1_SCL (_MX53_PAD_EIM_D21__I2C1_SCL | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D21__I2C1_SCL (_MX53_PAD_EIM_D21__I2C1_SCL | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_EIM_D21__USBOH3_USBOTG_OC (_MX53_PAD_EIM_D21__USBOH3_USBOTG_OC | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D22__EMI_WEIM_D_22 (_MX53_PAD_EIM_D22__EMI_WEIM_D_22 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D22__GPIO3_22 (_MX53_PAD_EIM_D22__GPIO3_22 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -1732,7 +1735,7 @@
|
||||
#define MX53_PAD_EIM_D28__UART2_CTS (_MX53_PAD_EIM_D28__UART2_CTS | MUX_PAD_CTRL(MX53_UART_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D28__IPU_DISPB0_SER_DIO (_MX53_PAD_EIM_D28__IPU_DISPB0_SER_DIO | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D28__CSPI_MOSI (_MX53_PAD_EIM_D28__CSPI_MOSI | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D28__I2C1_SDA (_MX53_PAD_EIM_D28__I2C1_SDA | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D28__I2C1_SDA (_MX53_PAD_EIM_D28__I2C1_SDA | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_EIM_D28__IPU_EXT_TRIG (_MX53_PAD_EIM_D28__IPU_EXT_TRIG | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D28__IPU_DI0_PIN13 (_MX53_PAD_EIM_D28__IPU_DI0_PIN13 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_EIM_D29__EMI_WEIM_D_29 (_MX53_PAD_EIM_D29__EMI_WEIM_D_29 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -2297,7 +2300,7 @@
|
||||
#define MX53_PAD_GPIO_9__SCC_FAIL_STATE (_MX53_PAD_GPIO_9__SCC_FAIL_STATE | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_3__ESAI1_HCKR (_MX53_PAD_GPIO_3__ESAI1_HCKR | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_3__GPIO1_3 (_MX53_PAD_GPIO_3__GPIO1_3 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_3__I2C3_SCL (_MX53_PAD_GPIO_3__I2C3_SCL | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_3__I2C3_SCL (_MX53_PAD_GPIO_3__I2C3_SCL | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_GPIO_3__DPLLIP1_TOG_EN (_MX53_PAD_GPIO_3__DPLLIP1_TOG_EN | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_3__CCM_CLKO2 (_MX53_PAD_GPIO_3__CCM_CLKO2 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_3__OBSERVE_MUX_OBSRV_INT_OUT0 (_MX53_PAD_GPIO_3__OBSERVE_MUX_OBSRV_INT_OUT0 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -2305,7 +2308,7 @@
|
||||
#define MX53_PAD_GPIO_3__MLB_MLBCLK (_MX53_PAD_GPIO_3__MLB_MLBCLK | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_6__ESAI1_SCKT (_MX53_PAD_GPIO_6__ESAI1_SCKT | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_6__GPIO1_6 (_MX53_PAD_GPIO_6__GPIO1_6 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_6__I2C3_SDA (_MX53_PAD_GPIO_6__I2C3_SDA | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_6__I2C3_SDA (_MX53_PAD_GPIO_6__I2C3_SDA | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_GPIO_6__CCM_CCM_OUT_0 (_MX53_PAD_GPIO_6__CCM_CCM_OUT_0 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_6__CSU_CSU_INT_DEB (_MX53_PAD_GPIO_6__CSU_CSU_INT_DEB | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_6__OBSERVE_MUX_OBSRV_INT_OUT1 (_MX53_PAD_GPIO_6__OBSERVE_MUX_OBSRV_INT_OUT1 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -2333,7 +2336,7 @@
|
||||
#define MX53_PAD_GPIO_5__CCM_CLKO (_MX53_PAD_GPIO_5__CCM_CLKO | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_5__CSU_CSU_ALARM_AUT_2 (_MX53_PAD_GPIO_5__CSU_CSU_ALARM_AUT_2 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_5__OBSERVE_MUX_OBSRV_INT_OUT4 (_MX53_PAD_GPIO_5__OBSERVE_MUX_OBSRV_INT_OUT4 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_5__I2C3_SCL (_MX53_PAD_GPIO_5__I2C3_SCL | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_5__I2C3_SCL (_MX53_PAD_GPIO_5__I2C3_SCL | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_GPIO_5__CCM_PLL1_BYP (_MX53_PAD_GPIO_5__CCM_PLL1_BYP | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_7__ESAI1_TX4_RX1 (_MX53_PAD_GPIO_7__ESAI1_TX4_RX1 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_7__GPIO1_7 (_MX53_PAD_GPIO_7__GPIO1_7 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
@ -2356,7 +2359,7 @@
|
||||
#define MX53_PAD_GPIO_16__TZIC_PWRFAIL_INT (_MX53_PAD_GPIO_16__TZIC_PWRFAIL_INT | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_16__RTC_CE_RTC_EXT_TRIG1 (_MX53_PAD_GPIO_16__RTC_CE_RTC_EXT_TRIG1 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_16__SPDIF_IN1 (_MX53_PAD_GPIO_16__SPDIF_IN1 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_16__I2C3_SDA (_MX53_PAD_GPIO_16__I2C3_SDA | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_16__I2C3_SDA (_MX53_PAD_GPIO_16__I2C3_SDA | MUX_PAD_CTRL(PAD_CTRL_I2C))
|
||||
#define MX53_PAD_GPIO_16__SJC_DE_B (_MX53_PAD_GPIO_16__SJC_DE_B | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_17__ESAI1_TX0 (_MX53_PAD_GPIO_17__ESAI1_TX0 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
#define MX53_PAD_GPIO_17__GPIO7_12 (_MX53_PAD_GPIO_17__GPIO7_12 | MUX_PAD_CTRL(NO_PAD_CTRL))
|
||||
|
@ -13,6 +13,7 @@ config ARCH_OMAP1
|
||||
bool "TI OMAP1"
|
||||
select CLKDEV_LOOKUP
|
||||
select CLKSRC_MMIO
|
||||
select GENERIC_IRQ_CHIP
|
||||
help
|
||||
"Systems based on omap7xx, omap15xx or omap16xx"
|
||||
|
||||
|
@ -195,6 +195,11 @@
|
||||
|
||||
#define OMAP36XX_DMA_UART4_TX 81 /* S_DMA_80 */
|
||||
#define OMAP36XX_DMA_UART4_RX 82 /* S_DMA_81 */
|
||||
|
||||
/* Only for AM35xx */
|
||||
#define AM35XX_DMA_UART4_TX 54
|
||||
#define AM35XX_DMA_UART4_RX 55
|
||||
|
||||
/*----------------------------------------------------------------------------*/
|
||||
|
||||
#define OMAP1_DMA_TOUT_IRQ (1 << 0)
|
||||
|
@ -357,6 +357,7 @@
|
||||
#define INT_35XX_EMAC_C0_TX_PULSE_IRQ 69
|
||||
#define INT_35XX_EMAC_C0_MISC_PULSE_IRQ 70
|
||||
#define INT_35XX_USBOTG_IRQ 71
|
||||
#define INT_35XX_UART4 84
|
||||
#define INT_35XX_CCDC_VD0_IRQ 88
|
||||
#define INT_35XX_CCDC_VD1_IRQ 92
|
||||
#define INT_35XX_CCDC_VD2_IRQ 93
|
||||
|
@ -56,6 +56,9 @@
|
||||
#define TI816X_UART2_BASE 0x48022000
|
||||
#define TI816X_UART3_BASE 0x48024000
|
||||
|
||||
/* AM3505/3517 UART4 */
|
||||
#define AM35XX_UART4_BASE 0x4809E000 /* Only on AM3505/3517 */
|
||||
|
||||
/* External port on Zoom2/3 */
|
||||
#define ZOOM_UART_BASE 0x10000000
|
||||
#define ZOOM_UART_VIRT 0xfa400000
|
||||
|
@ -423,9 +423,6 @@ static void sgtable_fill_kmalloc(struct sg_table *sgt, u32 pa, u32 da,
|
||||
{
|
||||
unsigned int i;
|
||||
struct scatterlist *sg;
|
||||
void *va;
|
||||
|
||||
va = phys_to_virt(pa);
|
||||
|
||||
for_each_sg(sgt->sgl, sg, sgt->nents, i) {
|
||||
unsigned bytes;
|
||||
|
@ -910,7 +910,7 @@ omapl138_case_a3 MACH_OMAPL138_CASE_A3 OMAPL138_CASE_A3 3280
|
||||
uemd MACH_UEMD UEMD 3281
|
||||
ccwmx51mut MACH_CCWMX51MUT CCWMX51MUT 3282
|
||||
rockhopper MACH_ROCKHOPPER ROCKHOPPER 3283
|
||||
nookcolor MACH_NOOKCOLOR NOOKCOLOR 3284
|
||||
encore MACH_ENCORE ENCORE 3284
|
||||
hkdkc100 MACH_HKDKC100 HKDKC100 3285
|
||||
ts42xx MACH_TS42XX TS42XX 3286
|
||||
aebl MACH_AEBL AEBL 3287
|
||||
|
@ -162,7 +162,6 @@ config IA64_GENERIC
|
||||
select ACPI_NUMA
|
||||
select SWIOTLB
|
||||
select PCI_MSI
|
||||
select DMAR
|
||||
help
|
||||
This selects the system type of your hardware. A "generic" kernel
|
||||
will run on any supported IA-64 system. However, if you configure
|
||||
|
@ -234,3 +234,4 @@ CONFIG_CRYPTO_MD5=y
|
||||
# CONFIG_CRYPTO_ANSI_CPRNG is not set
|
||||
CONFIG_CRC_T10DIF=y
|
||||
CONFIG_MISC_DEVICES=y
|
||||
CONFIG_DMAR=y
|
||||
|
@ -55,6 +55,7 @@ config SPARC64
|
||||
select PERF_USE_VMALLOC
|
||||
select IRQ_PREFLOW_FASTEOI
|
||||
select ARCH_HAVE_NMI_SAFE_CMPXCHG
|
||||
select HAVE_C_RECORDMCOUNT
|
||||
|
||||
config ARCH_DEFCONFIG
|
||||
string
|
||||
|
@ -131,6 +131,15 @@ static inline void arch_write_lock(arch_rwlock_t *rw)
|
||||
*(volatile __u32 *)&lp->lock = ~0U;
|
||||
}
|
||||
|
||||
static void inline arch_write_unlock(arch_rwlock_t *lock)
|
||||
{
|
||||
__asm__ __volatile__(
|
||||
" st %%g0, [%0]"
|
||||
: /* no outputs */
|
||||
: "r" (lock)
|
||||
: "memory");
|
||||
}
|
||||
|
||||
static inline int arch_write_trylock(arch_rwlock_t *rw)
|
||||
{
|
||||
unsigned int val;
|
||||
@ -175,8 +184,6 @@ static inline int __arch_read_trylock(arch_rwlock_t *rw)
|
||||
res; \
|
||||
})
|
||||
|
||||
#define arch_write_unlock(rw) do { (rw)->lock = 0; } while(0)
|
||||
|
||||
#define arch_spin_lock_flags(lock, flags) arch_spin_lock(lock)
|
||||
#define arch_read_lock_flags(rw, flags) arch_read_lock(rw)
|
||||
#define arch_write_lock_flags(rw, flags) arch_write_lock(rw)
|
||||
|
@ -210,14 +210,8 @@ static int inline arch_write_trylock(arch_rwlock_t *lock)
|
||||
return result;
|
||||
}
|
||||
|
||||
#define arch_read_lock(p) arch_read_lock(p)
|
||||
#define arch_read_lock_flags(p, f) arch_read_lock(p)
|
||||
#define arch_read_trylock(p) arch_read_trylock(p)
|
||||
#define arch_read_unlock(p) arch_read_unlock(p)
|
||||
#define arch_write_lock(p) arch_write_lock(p)
|
||||
#define arch_write_lock_flags(p, f) arch_write_lock(p)
|
||||
#define arch_write_unlock(p) arch_write_unlock(p)
|
||||
#define arch_write_trylock(p) arch_write_trylock(p)
|
||||
|
||||
#define arch_read_can_lock(rw) (!((rw)->lock & 0x80000000UL))
|
||||
#define arch_write_can_lock(rw) (!(rw)->lock)
|
||||
|
@ -27,8 +27,8 @@ static inline void fill_ldt(struct desc_struct *desc, const struct user_desc *in
|
||||
|
||||
desc->base2 = (info->base_addr & 0xff000000) >> 24;
|
||||
/*
|
||||
* Don't allow setting of the lm bit. It is useless anyway
|
||||
* because 64bit system calls require __USER_CS:
|
||||
* Don't allow setting of the lm bit. It would confuse
|
||||
* user_64bit_mode and would get overridden by sysret anyway.
|
||||
*/
|
||||
desc->l = 0;
|
||||
}
|
||||
|
@ -17,7 +17,6 @@
|
||||
* Vectors 0 ... 31 : system traps and exceptions - hardcoded events
|
||||
* Vectors 32 ... 127 : device interrupts
|
||||
* Vector 128 : legacy int80 syscall interface
|
||||
* Vector 204 : legacy x86_64 vsyscall emulation
|
||||
* Vectors 129 ... INVALIDATE_TLB_VECTOR_START-1 except 204 : device interrupts
|
||||
* Vectors INVALIDATE_TLB_VECTOR_START ... 255 : special interrupts
|
||||
*
|
||||
@ -51,9 +50,6 @@
|
||||
#ifdef CONFIG_X86_32
|
||||
# define SYSCALL_VECTOR 0x80
|
||||
#endif
|
||||
#ifdef CONFIG_X86_64
|
||||
# define VSYSCALL_EMU_VECTOR 0xcc
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Vectors 0x30-0x3f are used for ISA interrupts.
|
||||
|
@ -41,6 +41,7 @@
|
||||
|
||||
#include <asm/desc_defs.h>
|
||||
#include <asm/kmap_types.h>
|
||||
#include <asm/pgtable_types.h>
|
||||
|
||||
struct page;
|
||||
struct thread_struct;
|
||||
@ -63,6 +64,11 @@ struct paravirt_callee_save {
|
||||
struct pv_info {
|
||||
unsigned int kernel_rpl;
|
||||
int shared_kernel_pmd;
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
u16 extra_user_64bit_cs; /* __USER_CS if none */
|
||||
#endif
|
||||
|
||||
int paravirt_enabled;
|
||||
const char *name;
|
||||
};
|
||||
|
@ -131,6 +131,9 @@ struct pt_regs {
|
||||
#ifdef __KERNEL__
|
||||
|
||||
#include <linux/init.h>
|
||||
#ifdef CONFIG_PARAVIRT
|
||||
#include <asm/paravirt_types.h>
|
||||
#endif
|
||||
|
||||
struct cpuinfo_x86;
|
||||
struct task_struct;
|
||||
@ -187,6 +190,22 @@ static inline int v8086_mode(struct pt_regs *regs)
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
static inline bool user_64bit_mode(struct pt_regs *regs)
|
||||
{
|
||||
#ifndef CONFIG_PARAVIRT
|
||||
/*
|
||||
* On non-paravirt systems, this is the only long mode CPL 3
|
||||
* selector. We do not allow long mode selectors in the LDT.
|
||||
*/
|
||||
return regs->cs == __USER_CS;
|
||||
#else
|
||||
/* Headers are too twisted for this to go in paravirt.h. */
|
||||
return regs->cs == __USER_CS || regs->cs == pv_info.extra_user_64bit_cs;
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* X86_32 CPUs don't save ss and esp if the CPU is already in kernel mode
|
||||
* when it traps. The previous stack will be directly underneath the saved
|
||||
|
@ -40,7 +40,6 @@ asmlinkage void alignment_check(void);
|
||||
asmlinkage void machine_check(void);
|
||||
#endif /* CONFIG_X86_MCE */
|
||||
asmlinkage void simd_coprocessor_error(void);
|
||||
asmlinkage void emulate_vsyscall(void);
|
||||
|
||||
dotraplinkage void do_divide_error(struct pt_regs *, long);
|
||||
dotraplinkage void do_debug(struct pt_regs *, long);
|
||||
@ -67,7 +66,6 @@ dotraplinkage void do_alignment_check(struct pt_regs *, long);
|
||||
dotraplinkage void do_machine_check(struct pt_regs *, long);
|
||||
#endif
|
||||
dotraplinkage void do_simd_coprocessor_error(struct pt_regs *, long);
|
||||
dotraplinkage void do_emulate_vsyscall(struct pt_regs *, long);
|
||||
#ifdef CONFIG_X86_32
|
||||
dotraplinkage void do_iret_error(struct pt_regs *, long);
|
||||
#endif
|
||||
|
@ -681,6 +681,8 @@ __SYSCALL(__NR_syncfs, sys_syncfs)
|
||||
__SYSCALL(__NR_sendmmsg, sys_sendmmsg)
|
||||
#define __NR_setns 308
|
||||
__SYSCALL(__NR_setns, sys_setns)
|
||||
#define __NR_getcpu 309
|
||||
__SYSCALL(__NR_getcpu, sys_getcpu)
|
||||
|
||||
#ifndef __NO_STUBS
|
||||
#define __ARCH_WANT_OLD_READDIR
|
||||
|
@ -27,6 +27,12 @@ extern struct timezone sys_tz;
|
||||
|
||||
extern void map_vsyscall(void);
|
||||
|
||||
/*
|
||||
* Called on instruction fetch fault in vsyscall page.
|
||||
* Returns true if handled.
|
||||
*/
|
||||
extern bool emulate_vsyscall(struct pt_regs *regs, unsigned long address);
|
||||
|
||||
#endif /* __KERNEL__ */
|
||||
|
||||
#endif /* _ASM_X86_VSYSCALL_H */
|
||||
|
@ -17,19 +17,6 @@ CFLAGS_REMOVE_ftrace.o = -pg
|
||||
CFLAGS_REMOVE_early_printk.o = -pg
|
||||
endif
|
||||
|
||||
#
|
||||
# vsyscalls (which work on the user stack) should have
|
||||
# no stack-protector checks:
|
||||
#
|
||||
nostackp := $(call cc-option, -fno-stack-protector)
|
||||
CFLAGS_vsyscall_64.o := $(PROFILING) -g0 $(nostackp)
|
||||
CFLAGS_hpet.o := $(nostackp)
|
||||
CFLAGS_paravirt.o := $(nostackp)
|
||||
GCOV_PROFILE_vsyscall_64.o := n
|
||||
GCOV_PROFILE_hpet.o := n
|
||||
GCOV_PROFILE_tsc.o := n
|
||||
GCOV_PROFILE_paravirt.o := n
|
||||
|
||||
obj-y := process_$(BITS).o signal.o entry_$(BITS).o
|
||||
obj-y += traps.o irq.o irq_$(BITS).o dumpstack_$(BITS).o
|
||||
obj-y += time.o ioport.o ldt.o dumpstack.o
|
||||
|
@ -1111,7 +1111,6 @@ zeroentry spurious_interrupt_bug do_spurious_interrupt_bug
|
||||
zeroentry coprocessor_error do_coprocessor_error
|
||||
errorentry alignment_check do_alignment_check
|
||||
zeroentry simd_coprocessor_error do_simd_coprocessor_error
|
||||
zeroentry emulate_vsyscall do_emulate_vsyscall
|
||||
|
||||
|
||||
/* Reload gs selector with exception handling */
|
||||
|
@ -307,6 +307,10 @@ struct pv_info pv_info = {
|
||||
.paravirt_enabled = 0,
|
||||
.kernel_rpl = 0,
|
||||
.shared_kernel_pmd = 1, /* Only used when CONFIG_X86_PAE is set */
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
.extra_user_64bit_cs = __USER_CS,
|
||||
#endif
|
||||
};
|
||||
|
||||
struct pv_init_ops pv_init_ops = {
|
||||
|
@ -74,7 +74,7 @@ static int is_setting_trap_flag(struct task_struct *child, struct pt_regs *regs)
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
case 0x40 ... 0x4f:
|
||||
if (regs->cs != __USER_CS)
|
||||
if (!user_64bit_mode(regs))
|
||||
/* 32-bit mode: register increment */
|
||||
return 0;
|
||||
/* 64-bit mode: REX prefix */
|
||||
|
@ -872,12 +872,6 @@ void __init trap_init(void)
|
||||
set_bit(SYSCALL_VECTOR, used_vectors);
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
BUG_ON(test_bit(VSYSCALL_EMU_VECTOR, used_vectors));
|
||||
set_system_intr_gate(VSYSCALL_EMU_VECTOR, &emulate_vsyscall);
|
||||
set_bit(VSYSCALL_EMU_VECTOR, used_vectors);
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Should be a barrier for any external CPU state:
|
||||
*/
|
||||
|
@ -71,7 +71,6 @@ PHDRS {
|
||||
text PT_LOAD FLAGS(5); /* R_E */
|
||||
data PT_LOAD FLAGS(6); /* RW_ */
|
||||
#ifdef CONFIG_X86_64
|
||||
user PT_LOAD FLAGS(5); /* R_E */
|
||||
#ifdef CONFIG_SMP
|
||||
percpu PT_LOAD FLAGS(6); /* RW_ */
|
||||
#endif
|
||||
@ -154,44 +153,16 @@ SECTIONS
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
|
||||
#define VSYSCALL_ADDR (-10*1024*1024)
|
||||
|
||||
#define VLOAD_OFFSET (VSYSCALL_ADDR - __vsyscall_0 + LOAD_OFFSET)
|
||||
#define VLOAD(x) (ADDR(x) - VLOAD_OFFSET)
|
||||
|
||||
#define VVIRT_OFFSET (VSYSCALL_ADDR - __vsyscall_0)
|
||||
#define VVIRT(x) (ADDR(x) - VVIRT_OFFSET)
|
||||
|
||||
. = ALIGN(4096);
|
||||
__vsyscall_0 = .;
|
||||
|
||||
. = VSYSCALL_ADDR;
|
||||
.vsyscall : AT(VLOAD(.vsyscall)) {
|
||||
*(.vsyscall_0)
|
||||
|
||||
. = 1024;
|
||||
*(.vsyscall_1)
|
||||
|
||||
. = 2048;
|
||||
*(.vsyscall_2)
|
||||
|
||||
. = 4096; /* Pad the whole page. */
|
||||
} :user =0xcc
|
||||
. = ALIGN(__vsyscall_0 + PAGE_SIZE, PAGE_SIZE);
|
||||
|
||||
#undef VSYSCALL_ADDR
|
||||
#undef VLOAD_OFFSET
|
||||
#undef VLOAD
|
||||
#undef VVIRT_OFFSET
|
||||
#undef VVIRT
|
||||
|
||||
. = ALIGN(PAGE_SIZE);
|
||||
__vvar_page = .;
|
||||
|
||||
.vvar : AT(ADDR(.vvar) - LOAD_OFFSET) {
|
||||
/* work around gold bug 13023 */
|
||||
__vvar_beginning_hack = .;
|
||||
|
||||
/* Place all vvars at the offsets in asm/vvar.h. */
|
||||
#define EMIT_VVAR(name, offset) \
|
||||
. = offset; \
|
||||
/* Place all vvars at the offsets in asm/vvar.h. */
|
||||
#define EMIT_VVAR(name, offset) \
|
||||
. = __vvar_beginning_hack + offset; \
|
||||
*(.vvar_ ## name)
|
||||
#define __VVAR_KERNEL_LDS
|
||||
#include <asm/vvar.h>
|
||||
|
@ -18,9 +18,6 @@
|
||||
* use the vDSO.
|
||||
*/
|
||||
|
||||
/* Disable profiling for userspace code: */
|
||||
#define DISABLE_BRANCH_PROFILING
|
||||
|
||||
#include <linux/time.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/kernel.h>
|
||||
@ -50,12 +47,36 @@
|
||||
#include <asm/vgtod.h>
|
||||
#include <asm/traps.h>
|
||||
|
||||
#define CREATE_TRACE_POINTS
|
||||
#include "vsyscall_trace.h"
|
||||
|
||||
DEFINE_VVAR(int, vgetcpu_mode);
|
||||
DEFINE_VVAR(struct vsyscall_gtod_data, vsyscall_gtod_data) =
|
||||
{
|
||||
.lock = __SEQLOCK_UNLOCKED(__vsyscall_gtod_data.lock),
|
||||
};
|
||||
|
||||
static enum { EMULATE, NATIVE, NONE } vsyscall_mode = EMULATE;
|
||||
|
||||
static int __init vsyscall_setup(char *str)
|
||||
{
|
||||
if (str) {
|
||||
if (!strcmp("emulate", str))
|
||||
vsyscall_mode = EMULATE;
|
||||
else if (!strcmp("native", str))
|
||||
vsyscall_mode = NATIVE;
|
||||
else if (!strcmp("none", str))
|
||||
vsyscall_mode = NONE;
|
||||
else
|
||||
return -EINVAL;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
return -EINVAL;
|
||||
}
|
||||
early_param("vsyscall", vsyscall_setup);
|
||||
|
||||
void update_vsyscall_tz(void)
|
||||
{
|
||||
unsigned long flags;
|
||||
@ -100,7 +121,7 @@ static void warn_bad_vsyscall(const char *level, struct pt_regs *regs,
|
||||
|
||||
printk("%s%s[%d] %s ip:%lx cs:%lx sp:%lx ax:%lx si:%lx di:%lx\n",
|
||||
level, tsk->comm, task_pid_nr(tsk),
|
||||
message, regs->ip - 2, regs->cs,
|
||||
message, regs->ip, regs->cs,
|
||||
regs->sp, regs->ax, regs->si, regs->di);
|
||||
}
|
||||
|
||||
@ -118,46 +139,39 @@ static int addr_to_vsyscall_nr(unsigned long addr)
|
||||
return nr;
|
||||
}
|
||||
|
||||
void dotraplinkage do_emulate_vsyscall(struct pt_regs *regs, long error_code)
|
||||
bool emulate_vsyscall(struct pt_regs *regs, unsigned long address)
|
||||
{
|
||||
struct task_struct *tsk;
|
||||
unsigned long caller;
|
||||
int vsyscall_nr;
|
||||
long ret;
|
||||
|
||||
local_irq_enable();
|
||||
|
||||
/*
|
||||
* Real 64-bit user mode code has cs == __USER_CS. Anything else
|
||||
* is bogus.
|
||||
* No point in checking CS -- the only way to get here is a user mode
|
||||
* trap to a high address, which means that we're in 64-bit user code.
|
||||
*/
|
||||
if (regs->cs != __USER_CS) {
|
||||
/*
|
||||
* If we trapped from kernel mode, we might as well OOPS now
|
||||
* instead of returning to some random address and OOPSing
|
||||
* then.
|
||||
*/
|
||||
BUG_ON(!user_mode(regs));
|
||||
|
||||
/* Compat mode and non-compat 32-bit CS should both segfault. */
|
||||
warn_bad_vsyscall(KERN_WARNING, regs,
|
||||
"illegal int 0xcc from 32-bit mode");
|
||||
goto sigsegv;
|
||||
WARN_ON_ONCE(address != regs->ip);
|
||||
|
||||
if (vsyscall_mode == NONE) {
|
||||
warn_bad_vsyscall(KERN_INFO, regs,
|
||||
"vsyscall attempted with vsyscall=none");
|
||||
return false;
|
||||
}
|
||||
|
||||
/*
|
||||
* x86-ism here: regs->ip points to the instruction after the int 0xcc,
|
||||
* and int 0xcc is two bytes long.
|
||||
*/
|
||||
vsyscall_nr = addr_to_vsyscall_nr(regs->ip - 2);
|
||||
vsyscall_nr = addr_to_vsyscall_nr(address);
|
||||
|
||||
trace_emulate_vsyscall(vsyscall_nr);
|
||||
|
||||
if (vsyscall_nr < 0) {
|
||||
warn_bad_vsyscall(KERN_WARNING, regs,
|
||||
"illegal int 0xcc (exploit attempt?)");
|
||||
"misaligned vsyscall (exploit attempt or buggy program) -- look up the vsyscall kernel parameter if you need a workaround");
|
||||
goto sigsegv;
|
||||
}
|
||||
|
||||
if (get_user(caller, (unsigned long __user *)regs->sp) != 0) {
|
||||
warn_bad_vsyscall(KERN_WARNING, regs, "int 0xcc with bad stack (exploit attempt?)");
|
||||
warn_bad_vsyscall(KERN_WARNING, regs,
|
||||
"vsyscall with bad stack (exploit attempt?)");
|
||||
goto sigsegv;
|
||||
}
|
||||
|
||||
@ -202,13 +216,11 @@ void dotraplinkage do_emulate_vsyscall(struct pt_regs *regs, long error_code)
|
||||
regs->ip = caller;
|
||||
regs->sp += 8;
|
||||
|
||||
local_irq_disable();
|
||||
return;
|
||||
return true;
|
||||
|
||||
sigsegv:
|
||||
regs->ip -= 2; /* The faulting instruction should be the int 0xcc. */
|
||||
force_sig(SIGSEGV, current);
|
||||
local_irq_disable();
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -256,15 +268,21 @@ cpu_vsyscall_notifier(struct notifier_block *n, unsigned long action, void *arg)
|
||||
|
||||
void __init map_vsyscall(void)
|
||||
{
|
||||
extern char __vsyscall_0;
|
||||
unsigned long physaddr_page0 = __pa_symbol(&__vsyscall_0);
|
||||
extern char __vsyscall_page;
|
||||
unsigned long physaddr_vsyscall = __pa_symbol(&__vsyscall_page);
|
||||
extern char __vvar_page;
|
||||
unsigned long physaddr_vvar_page = __pa_symbol(&__vvar_page);
|
||||
|
||||
/* Note that VSYSCALL_MAPPED_PAGES must agree with the code below. */
|
||||
__set_fixmap(VSYSCALL_FIRST_PAGE, physaddr_page0, PAGE_KERNEL_VSYSCALL);
|
||||
__set_fixmap(VSYSCALL_FIRST_PAGE, physaddr_vsyscall,
|
||||
vsyscall_mode == NATIVE
|
||||
? PAGE_KERNEL_VSYSCALL
|
||||
: PAGE_KERNEL_VVAR);
|
||||
BUILD_BUG_ON((unsigned long)__fix_to_virt(VSYSCALL_FIRST_PAGE) !=
|
||||
(unsigned long)VSYSCALL_START);
|
||||
|
||||
__set_fixmap(VVAR_PAGE, physaddr_vvar_page, PAGE_KERNEL_VVAR);
|
||||
BUILD_BUG_ON((unsigned long)__fix_to_virt(VVAR_PAGE) != (unsigned long)VVAR_ADDRESS);
|
||||
BUILD_BUG_ON((unsigned long)__fix_to_virt(VVAR_PAGE) !=
|
||||
(unsigned long)VVAR_ADDRESS);
|
||||
}
|
||||
|
||||
static int __init vsyscall_init(void)
|
||||
|
@ -7,21 +7,31 @@
|
||||
*/
|
||||
|
||||
#include <linux/linkage.h>
|
||||
|
||||
#include <asm/irq_vectors.h>
|
||||
#include <asm/page_types.h>
|
||||
#include <asm/unistd_64.h>
|
||||
|
||||
/* The unused parts of the page are filled with 0xcc by the linker script. */
|
||||
__PAGE_ALIGNED_DATA
|
||||
.globl __vsyscall_page
|
||||
.balign PAGE_SIZE, 0xcc
|
||||
.type __vsyscall_page, @object
|
||||
__vsyscall_page:
|
||||
|
||||
.section .vsyscall_0, "a"
|
||||
ENTRY(vsyscall_0)
|
||||
int $VSYSCALL_EMU_VECTOR
|
||||
END(vsyscall_0)
|
||||
mov $__NR_gettimeofday, %rax
|
||||
syscall
|
||||
ret
|
||||
|
||||
.section .vsyscall_1, "a"
|
||||
ENTRY(vsyscall_1)
|
||||
int $VSYSCALL_EMU_VECTOR
|
||||
END(vsyscall_1)
|
||||
.balign 1024, 0xcc
|
||||
mov $__NR_time, %rax
|
||||
syscall
|
||||
ret
|
||||
|
||||
.section .vsyscall_2, "a"
|
||||
ENTRY(vsyscall_2)
|
||||
int $VSYSCALL_EMU_VECTOR
|
||||
END(vsyscall_2)
|
||||
.balign 1024, 0xcc
|
||||
mov $__NR_getcpu, %rax
|
||||
syscall
|
||||
ret
|
||||
|
||||
.balign 4096, 0xcc
|
||||
|
||||
.size __vsyscall_page, 4096
|
||||
|
29
arch/x86/kernel/vsyscall_trace.h
Normal file
29
arch/x86/kernel/vsyscall_trace.h
Normal file
@ -0,0 +1,29 @@
|
||||
#undef TRACE_SYSTEM
|
||||
#define TRACE_SYSTEM vsyscall
|
||||
|
||||
#if !defined(__VSYSCALL_TRACE_H) || defined(TRACE_HEADER_MULTI_READ)
|
||||
#define __VSYSCALL_TRACE_H
|
||||
|
||||
#include <linux/tracepoint.h>
|
||||
|
||||
TRACE_EVENT(emulate_vsyscall,
|
||||
|
||||
TP_PROTO(int nr),
|
||||
|
||||
TP_ARGS(nr),
|
||||
|
||||
TP_STRUCT__entry(__field(int, nr)),
|
||||
|
||||
TP_fast_assign(
|
||||
__entry->nr = nr;
|
||||
),
|
||||
|
||||
TP_printk("nr = %d", __entry->nr)
|
||||
);
|
||||
|
||||
#endif
|
||||
|
||||
#undef TRACE_INCLUDE_PATH
|
||||
#define TRACE_INCLUDE_PATH ../../arch/x86/kernel
|
||||
#define TRACE_INCLUDE_FILE vsyscall_trace
|
||||
#include <trace/define_trace.h>
|
@ -22,6 +22,8 @@ config KVM
|
||||
depends on HAVE_KVM
|
||||
# for device assignment:
|
||||
depends on PCI
|
||||
# for TASKSTATS/TASK_DELAY_ACCT:
|
||||
depends on NET
|
||||
select PREEMPT_NOTIFIERS
|
||||
select MMU_NOTIFIER
|
||||
select ANON_INODES
|
||||
@ -31,6 +33,7 @@ config KVM
|
||||
select KVM_ASYNC_PF
|
||||
select USER_RETURN_NOTIFIER
|
||||
select KVM_MMIO
|
||||
select TASKSTATS
|
||||
select TASK_DELAY_ACCT
|
||||
---help---
|
||||
Support hosting fully virtualized guest machines using hardware
|
||||
|
@ -17,6 +17,7 @@
|
||||
#include <asm/traps.h> /* dotraplinkage, ... */
|
||||
#include <asm/pgalloc.h> /* pgd_*(), ... */
|
||||
#include <asm/kmemcheck.h> /* kmemcheck_*(), ... */
|
||||
#include <asm/vsyscall.h>
|
||||
|
||||
/*
|
||||
* Page fault error code bits:
|
||||
@ -105,7 +106,7 @@ check_prefetch_opcode(struct pt_regs *regs, unsigned char *instr,
|
||||
* but for now it's good enough to assume that long
|
||||
* mode only uses well known segments or kernel.
|
||||
*/
|
||||
return (!user_mode(regs)) || (regs->cs == __USER_CS);
|
||||
return (!user_mode(regs) || user_64bit_mode(regs));
|
||||
#endif
|
||||
case 0x60:
|
||||
/* 0x64 thru 0x67 are valid prefixes in all modes. */
|
||||
@ -720,6 +721,18 @@ __bad_area_nosemaphore(struct pt_regs *regs, unsigned long error_code,
|
||||
if (is_errata100(regs, address))
|
||||
return;
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
/*
|
||||
* Instruction fetch faults in the vsyscall page might need
|
||||
* emulation.
|
||||
*/
|
||||
if (unlikely((error_code & PF_INSTR) &&
|
||||
((address & ~0xfff) == VSYSCALL_START))) {
|
||||
if (emulate_vsyscall(regs, address))
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (unlikely(show_unhandled_signals))
|
||||
show_signal_msg(regs, error_code, address, tsk);
|
||||
|
||||
|
@ -9,6 +9,7 @@ __PAGE_ALIGNED_DATA
|
||||
vdso_start:
|
||||
.incbin "arch/x86/vdso/vdso.so"
|
||||
vdso_end:
|
||||
.align PAGE_SIZE /* extra data here leaks to userspace. */
|
||||
|
||||
.previous
|
||||
|
||||
|
@ -951,6 +951,10 @@ static const struct pv_info xen_info __initconst = {
|
||||
.paravirt_enabled = 1,
|
||||
.shared_kernel_pmd = 0,
|
||||
|
||||
#ifdef CONFIG_X86_64
|
||||
.extra_user_64bit_cs = FLAT_USER_CS64,
|
||||
#endif
|
||||
|
||||
.name = "Xen",
|
||||
};
|
||||
|
||||
|
@ -1916,6 +1916,7 @@ static void xen_set_fixmap(unsigned idx, phys_addr_t phys, pgprot_t prot)
|
||||
# endif
|
||||
#else
|
||||
case VSYSCALL_LAST_PAGE ... VSYSCALL_FIRST_PAGE:
|
||||
case VVAR_PAGE:
|
||||
#endif
|
||||
case FIX_TEXT_POKE0:
|
||||
case FIX_TEXT_POKE1:
|
||||
@ -1956,7 +1957,8 @@ static void xen_set_fixmap(unsigned idx, phys_addr_t phys, pgprot_t prot)
|
||||
#ifdef CONFIG_X86_64
|
||||
/* Replicate changes to map the vsyscall page into the user
|
||||
pagetable vsyscall mapping. */
|
||||
if (idx >= VSYSCALL_LAST_PAGE && idx <= VSYSCALL_FIRST_PAGE) {
|
||||
if ((idx >= VSYSCALL_LAST_PAGE && idx <= VSYSCALL_FIRST_PAGE) ||
|
||||
idx == VVAR_PAGE) {
|
||||
unsigned long vaddr = __fix_to_virt(idx);
|
||||
set_pte_vaddr_pud(level3_user_vsyscall, vaddr, pte);
|
||||
}
|
||||
|
@ -113,3 +113,4 @@ struct regmap *regmap_init_i2c(struct i2c_client *i2c,
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(regmap_init_i2c);
|
||||
|
||||
MODULE_LICENSE("GPL");
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include <linux/regmap.h>
|
||||
#include <linux/spi/spi.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/module.h>
|
||||
|
||||
static int regmap_spi_write(struct device *dev, const void *data, size_t count)
|
||||
{
|
||||
@ -70,3 +71,5 @@ struct regmap *regmap_init_spi(struct spi_device *spi,
|
||||
return regmap_init(&spi->dev, ®map_spi, config);
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(regmap_init_spi);
|
||||
|
||||
MODULE_LICENSE("GPL");
|
||||
|
@ -317,7 +317,7 @@ static int _regmap_raw_read(struct regmap *map, unsigned int reg, void *val,
|
||||
u8[0] |= map->bus->read_flag_mask;
|
||||
|
||||
ret = map->bus->read(map->dev, map->work_buf, map->format.reg_bytes,
|
||||
val, map->format.val_bytes);
|
||||
val, val_len);
|
||||
if (ret != 0)
|
||||
return ret;
|
||||
|
||||
|
@ -216,15 +216,33 @@ struct inbound_phy_packet_event {
|
||||
struct fw_cdev_event_phy_packet phy_packet;
|
||||
};
|
||||
|
||||
static inline void __user *u64_to_uptr(__u64 value)
|
||||
#ifdef CONFIG_COMPAT
|
||||
static void __user *u64_to_uptr(u64 value)
|
||||
{
|
||||
if (is_compat_task())
|
||||
return compat_ptr(value);
|
||||
else
|
||||
return (void __user *)(unsigned long)value;
|
||||
}
|
||||
|
||||
static u64 uptr_to_u64(void __user *ptr)
|
||||
{
|
||||
if (is_compat_task())
|
||||
return ptr_to_compat(ptr);
|
||||
else
|
||||
return (u64)(unsigned long)ptr;
|
||||
}
|
||||
#else
|
||||
static inline void __user *u64_to_uptr(u64 value)
|
||||
{
|
||||
return (void __user *)(unsigned long)value;
|
||||
}
|
||||
|
||||
static inline __u64 uptr_to_u64(void __user *ptr)
|
||||
static inline u64 uptr_to_u64(void __user *ptr)
|
||||
{
|
||||
return (__u64)(unsigned long)ptr;
|
||||
return (u64)(unsigned long)ptr;
|
||||
}
|
||||
#endif /* CONFIG_COMPAT */
|
||||
|
||||
static int fw_device_op_open(struct inode *inode, struct file *file)
|
||||
{
|
||||
|
@ -2179,8 +2179,13 @@ static int ohci_enable(struct fw_card *card,
|
||||
ohci_driver_name, ohci)) {
|
||||
fw_error("Failed to allocate interrupt %d.\n", dev->irq);
|
||||
pci_disable_msi(dev);
|
||||
dma_free_coherent(ohci->card.device, CONFIG_ROM_SIZE,
|
||||
ohci->config_rom, ohci->config_rom_bus);
|
||||
|
||||
if (config_rom) {
|
||||
dma_free_coherent(ohci->card.device, CONFIG_ROM_SIZE,
|
||||
ohci->next_config_rom,
|
||||
ohci->next_config_rom_bus);
|
||||
ohci->next_config_rom = NULL;
|
||||
}
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
|
@ -499,7 +499,7 @@ static int i915_interrupt_info(struct seq_file *m, void *data)
|
||||
seq_printf(m, "Interrupts received: %d\n",
|
||||
atomic_read(&dev_priv->irq_received));
|
||||
for (i = 0; i < I915_NUM_RINGS; i++) {
|
||||
if (IS_GEN6(dev)) {
|
||||
if (IS_GEN6(dev) || IS_GEN7(dev)) {
|
||||
seq_printf(m, "Graphics Interrupt mask (%s): %08x\n",
|
||||
dev_priv->ring[i].name,
|
||||
I915_READ_IMR(&dev_priv->ring[i]));
|
||||
|
@ -36,6 +36,7 @@
|
||||
#include <linux/io-mapping.h>
|
||||
#include <linux/i2c.h>
|
||||
#include <drm/intel-gtt.h>
|
||||
#include <linux/backlight.h>
|
||||
|
||||
/* General customization:
|
||||
*/
|
||||
@ -690,6 +691,7 @@ typedef struct drm_i915_private {
|
||||
int child_dev_num;
|
||||
struct child_device_config *child_dev;
|
||||
struct drm_connector *int_lvds_connector;
|
||||
struct drm_connector *int_edp_connector;
|
||||
|
||||
bool mchbar_need_disable;
|
||||
|
||||
@ -723,6 +725,8 @@ typedef struct drm_i915_private {
|
||||
/* list of fbdev register on this device */
|
||||
struct intel_fbdev *fbdev;
|
||||
|
||||
struct backlight_device *backlight;
|
||||
|
||||
struct drm_property *broadcast_rgb_property;
|
||||
struct drm_property *force_audio_property;
|
||||
|
||||
|
@ -2058,8 +2058,10 @@ void intel_irq_init(struct drm_device *dev)
|
||||
dev->driver->get_vblank_counter = gm45_get_vblank_counter;
|
||||
}
|
||||
|
||||
|
||||
dev->driver->get_vblank_timestamp = i915_get_vblank_timestamp;
|
||||
if (drm_core_check_feature(dev, DRIVER_MODESET))
|
||||
dev->driver->get_vblank_timestamp = i915_get_vblank_timestamp;
|
||||
else
|
||||
dev->driver->get_vblank_timestamp = NULL;
|
||||
dev->driver->get_scanout_position = i915_get_crtc_scanoutpos;
|
||||
|
||||
if (IS_IVYBRIDGE(dev)) {
|
||||
|
@ -1318,6 +1318,7 @@
|
||||
#define ADPA_PIPE_SELECT_MASK (1<<30)
|
||||
#define ADPA_PIPE_A_SELECT 0
|
||||
#define ADPA_PIPE_B_SELECT (1<<30)
|
||||
#define ADPA_PIPE_SELECT(pipe) ((pipe) << 30)
|
||||
#define ADPA_USE_VGA_HVPOLARITY (1<<15)
|
||||
#define ADPA_SETS_HVPOLARITY 0
|
||||
#define ADPA_VSYNC_CNTL_DISABLE (1<<11)
|
||||
@ -1460,6 +1461,7 @@
|
||||
/* Selects pipe B for LVDS data. Must be set on pre-965. */
|
||||
#define LVDS_PIPEB_SELECT (1 << 30)
|
||||
#define LVDS_PIPE_MASK (1 << 30)
|
||||
#define LVDS_PIPE(pipe) ((pipe) << 30)
|
||||
/* LVDS dithering flag on 965/g4x platform */
|
||||
#define LVDS_ENABLE_DITHER (1 << 25)
|
||||
/* LVDS sync polarity flags. Set to invert (i.e. negative) */
|
||||
@ -1499,9 +1501,6 @@
|
||||
#define LVDS_B0B3_POWER_DOWN (0 << 2)
|
||||
#define LVDS_B0B3_POWER_UP (3 << 2)
|
||||
|
||||
#define LVDS_PIPE_ENABLED(V, P) \
|
||||
(((V) & (LVDS_PIPE_MASK | LVDS_PORT_EN)) == ((P) << 30 | LVDS_PORT_EN))
|
||||
|
||||
/* Video Data Island Packet control */
|
||||
#define VIDEO_DIP_DATA 0x61178
|
||||
#define VIDEO_DIP_CTL 0x61170
|
||||
@ -3256,14 +3255,12 @@
|
||||
#define ADPA_CRT_HOTPLUG_VOLREF_475MV (1<<17)
|
||||
#define ADPA_CRT_HOTPLUG_FORCE_TRIGGER (1<<16)
|
||||
|
||||
#define ADPA_PIPE_ENABLED(V, P) \
|
||||
(((V) & (ADPA_TRANS_SELECT_MASK | ADPA_DAC_ENABLE)) == ((P) << 30 | ADPA_DAC_ENABLE))
|
||||
|
||||
/* or SDVOB */
|
||||
#define HDMIB 0xe1140
|
||||
#define PORT_ENABLE (1 << 31)
|
||||
#define TRANSCODER_A (0)
|
||||
#define TRANSCODER_B (1 << 30)
|
||||
#define TRANSCODER(pipe) ((pipe) << 30)
|
||||
#define TRANSCODER_MASK (1 << 30)
|
||||
#define COLOR_FORMAT_8bpc (0)
|
||||
#define COLOR_FORMAT_12bpc (3 << 26)
|
||||
@ -3280,9 +3277,6 @@
|
||||
#define HSYNC_ACTIVE_HIGH (1 << 3)
|
||||
#define PORT_DETECTED (1 << 2)
|
||||
|
||||
#define HDMI_PIPE_ENABLED(V, P) \
|
||||
(((V) & (TRANSCODER_MASK | PORT_ENABLE)) == ((P) << 30 | PORT_ENABLE))
|
||||
|
||||
/* PCH SDVOB multiplex with HDMIB */
|
||||
#define PCH_SDVOB HDMIB
|
||||
|
||||
@ -3349,6 +3343,7 @@
|
||||
#define PORT_TRANS_B_SEL_CPT (1<<29)
|
||||
#define PORT_TRANS_C_SEL_CPT (2<<29)
|
||||
#define PORT_TRANS_SEL_MASK (3<<29)
|
||||
#define PORT_TRANS_SEL_CPT(pipe) ((pipe) << 29)
|
||||
|
||||
#define TRANS_DP_CTL_A 0xe0300
|
||||
#define TRANS_DP_CTL_B 0xe1300
|
||||
|
@ -871,7 +871,8 @@ int i915_restore_state(struct drm_device *dev)
|
||||
}
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
|
||||
intel_init_clock_gating(dev);
|
||||
if (drm_core_check_feature(dev, DRIVER_MODESET))
|
||||
intel_init_clock_gating(dev);
|
||||
|
||||
if (IS_IRONLAKE_M(dev)) {
|
||||
ironlake_enable_drps(dev);
|
||||
|
@ -980,8 +980,8 @@ static void assert_transcoder_disabled(struct drm_i915_private *dev_priv,
|
||||
pipe_name(pipe));
|
||||
}
|
||||
|
||||
static bool dp_pipe_enabled(struct drm_i915_private *dev_priv, enum pipe pipe,
|
||||
int reg, u32 port_sel, u32 val)
|
||||
static bool dp_pipe_enabled(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, u32 port_sel, u32 val)
|
||||
{
|
||||
if ((val & DP_PORT_EN) == 0)
|
||||
return false;
|
||||
@ -998,11 +998,58 @@ static bool dp_pipe_enabled(struct drm_i915_private *dev_priv, enum pipe pipe,
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool hdmi_pipe_enabled(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, u32 val)
|
||||
{
|
||||
if ((val & PORT_ENABLE) == 0)
|
||||
return false;
|
||||
|
||||
if (HAS_PCH_CPT(dev_priv->dev)) {
|
||||
if ((val & PORT_TRANS_SEL_MASK) != PORT_TRANS_SEL_CPT(pipe))
|
||||
return false;
|
||||
} else {
|
||||
if ((val & TRANSCODER_MASK) != TRANSCODER(pipe))
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool lvds_pipe_enabled(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, u32 val)
|
||||
{
|
||||
if ((val & LVDS_PORT_EN) == 0)
|
||||
return false;
|
||||
|
||||
if (HAS_PCH_CPT(dev_priv->dev)) {
|
||||
if ((val & PORT_TRANS_SEL_MASK) != PORT_TRANS_SEL_CPT(pipe))
|
||||
return false;
|
||||
} else {
|
||||
if ((val & LVDS_PIPE_MASK) != LVDS_PIPE(pipe))
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool adpa_pipe_enabled(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, u32 val)
|
||||
{
|
||||
if ((val & ADPA_DAC_ENABLE) == 0)
|
||||
return false;
|
||||
if (HAS_PCH_CPT(dev_priv->dev)) {
|
||||
if ((val & PORT_TRANS_SEL_MASK) != PORT_TRANS_SEL_CPT(pipe))
|
||||
return false;
|
||||
} else {
|
||||
if ((val & ADPA_PIPE_SELECT_MASK) != ADPA_PIPE_SELECT(pipe))
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
static void assert_pch_dp_disabled(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, int reg, u32 port_sel)
|
||||
{
|
||||
u32 val = I915_READ(reg);
|
||||
WARN(dp_pipe_enabled(dev_priv, pipe, reg, port_sel, val),
|
||||
WARN(dp_pipe_enabled(dev_priv, pipe, port_sel, val),
|
||||
"PCH DP (0x%08x) enabled on transcoder %c, should be disabled\n",
|
||||
reg, pipe_name(pipe));
|
||||
}
|
||||
@ -1011,7 +1058,7 @@ static void assert_pch_hdmi_disabled(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, int reg)
|
||||
{
|
||||
u32 val = I915_READ(reg);
|
||||
WARN(HDMI_PIPE_ENABLED(val, pipe),
|
||||
WARN(hdmi_pipe_enabled(dev_priv, val, pipe),
|
||||
"PCH DP (0x%08x) enabled on transcoder %c, should be disabled\n",
|
||||
reg, pipe_name(pipe));
|
||||
}
|
||||
@ -1028,13 +1075,13 @@ static void assert_pch_ports_disabled(struct drm_i915_private *dev_priv,
|
||||
|
||||
reg = PCH_ADPA;
|
||||
val = I915_READ(reg);
|
||||
WARN(ADPA_PIPE_ENABLED(val, pipe),
|
||||
WARN(adpa_pipe_enabled(dev_priv, val, pipe),
|
||||
"PCH VGA enabled on transcoder %c, should be disabled\n",
|
||||
pipe_name(pipe));
|
||||
|
||||
reg = PCH_LVDS;
|
||||
val = I915_READ(reg);
|
||||
WARN(LVDS_PIPE_ENABLED(val, pipe),
|
||||
WARN(lvds_pipe_enabled(dev_priv, val, pipe),
|
||||
"PCH LVDS enabled on transcoder %c, should be disabled\n",
|
||||
pipe_name(pipe));
|
||||
|
||||
@ -1360,7 +1407,7 @@ static void disable_pch_dp(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, int reg, u32 port_sel)
|
||||
{
|
||||
u32 val = I915_READ(reg);
|
||||
if (dp_pipe_enabled(dev_priv, pipe, reg, port_sel, val)) {
|
||||
if (dp_pipe_enabled(dev_priv, pipe, port_sel, val)) {
|
||||
DRM_DEBUG_KMS("Disabling pch dp %x on pipe %d\n", reg, pipe);
|
||||
I915_WRITE(reg, val & ~DP_PORT_EN);
|
||||
}
|
||||
@ -1370,7 +1417,7 @@ static void disable_pch_hdmi(struct drm_i915_private *dev_priv,
|
||||
enum pipe pipe, int reg)
|
||||
{
|
||||
u32 val = I915_READ(reg);
|
||||
if (HDMI_PIPE_ENABLED(val, pipe)) {
|
||||
if (hdmi_pipe_enabled(dev_priv, val, pipe)) {
|
||||
DRM_DEBUG_KMS("Disabling pch HDMI %x on pipe %d\n",
|
||||
reg, pipe);
|
||||
I915_WRITE(reg, val & ~PORT_ENABLE);
|
||||
@ -1392,12 +1439,13 @@ static void intel_disable_pch_ports(struct drm_i915_private *dev_priv,
|
||||
|
||||
reg = PCH_ADPA;
|
||||
val = I915_READ(reg);
|
||||
if (ADPA_PIPE_ENABLED(val, pipe))
|
||||
if (adpa_pipe_enabled(dev_priv, val, pipe))
|
||||
I915_WRITE(reg, val & ~ADPA_DAC_ENABLE);
|
||||
|
||||
reg = PCH_LVDS;
|
||||
val = I915_READ(reg);
|
||||
if (LVDS_PIPE_ENABLED(val, pipe)) {
|
||||
if (lvds_pipe_enabled(dev_priv, val, pipe)) {
|
||||
DRM_DEBUG_KMS("disable lvds on pipe %d val 0x%08x\n", pipe, val);
|
||||
I915_WRITE(reg, val & ~LVDS_PORT_EN);
|
||||
POSTING_READ(reg);
|
||||
udelay(100);
|
||||
@ -5049,6 +5097,81 @@ static int i9xx_crtc_mode_set(struct drm_crtc *crtc,
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void ironlake_update_pch_refclk(struct drm_device *dev)
|
||||
{
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct drm_mode_config *mode_config = &dev->mode_config;
|
||||
struct drm_crtc *crtc;
|
||||
struct intel_encoder *encoder;
|
||||
struct intel_encoder *has_edp_encoder = NULL;
|
||||
u32 temp;
|
||||
bool has_lvds = false;
|
||||
|
||||
/* We need to take the global config into account */
|
||||
list_for_each_entry(crtc, &mode_config->crtc_list, head) {
|
||||
if (!crtc->enabled)
|
||||
continue;
|
||||
|
||||
list_for_each_entry(encoder, &mode_config->encoder_list,
|
||||
base.head) {
|
||||
if (encoder->base.crtc != crtc)
|
||||
continue;
|
||||
|
||||
switch (encoder->type) {
|
||||
case INTEL_OUTPUT_LVDS:
|
||||
has_lvds = true;
|
||||
case INTEL_OUTPUT_EDP:
|
||||
has_edp_encoder = encoder;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* 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.
|
||||
*/
|
||||
temp = I915_READ(PCH_DREF_CONTROL);
|
||||
/* Always enable nonspread source */
|
||||
temp &= ~DREF_NONSPREAD_SOURCE_MASK;
|
||||
temp |= DREF_NONSPREAD_SOURCE_ENABLE;
|
||||
temp &= ~DREF_SSC_SOURCE_MASK;
|
||||
temp |= DREF_SSC_SOURCE_ENABLE;
|
||||
I915_WRITE(PCH_DREF_CONTROL, temp);
|
||||
|
||||
POSTING_READ(PCH_DREF_CONTROL);
|
||||
udelay(200);
|
||||
|
||||
if (has_edp_encoder) {
|
||||
if (intel_panel_use_ssc(dev_priv)) {
|
||||
temp |= DREF_SSC1_ENABLE;
|
||||
I915_WRITE(PCH_DREF_CONTROL, temp);
|
||||
|
||||
POSTING_READ(PCH_DREF_CONTROL);
|
||||
udelay(200);
|
||||
}
|
||||
temp &= ~DREF_CPU_SOURCE_OUTPUT_MASK;
|
||||
|
||||
/* Enable CPU source on CPU attached eDP */
|
||||
if (!intel_encoder_is_pch_edp(&has_edp_encoder->base)) {
|
||||
if (intel_panel_use_ssc(dev_priv))
|
||||
temp |= DREF_CPU_SOURCE_OUTPUT_DOWNSPREAD;
|
||||
else
|
||||
temp |= DREF_CPU_SOURCE_OUTPUT_NONSPREAD;
|
||||
} else {
|
||||
/* Enable SSC on PCH eDP if needed */
|
||||
if (intel_panel_use_ssc(dev_priv)) {
|
||||
DRM_ERROR("enabling SSC on PCH\n");
|
||||
temp |= DREF_SUPERSPREAD_SOURCE_ENABLE;
|
||||
}
|
||||
}
|
||||
I915_WRITE(PCH_DREF_CONTROL, temp);
|
||||
POSTING_READ(PCH_DREF_CONTROL);
|
||||
udelay(200);
|
||||
}
|
||||
}
|
||||
|
||||
static int ironlake_crtc_mode_set(struct drm_crtc *crtc,
|
||||
struct drm_display_mode *mode,
|
||||
struct drm_display_mode *adjusted_mode,
|
||||
@ -5244,49 +5367,7 @@ static int ironlake_crtc_mode_set(struct drm_crtc *crtc,
|
||||
ironlake_compute_m_n(intel_crtc->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.
|
||||
*/
|
||||
temp = I915_READ(PCH_DREF_CONTROL);
|
||||
/* Always enable nonspread source */
|
||||
temp &= ~DREF_NONSPREAD_SOURCE_MASK;
|
||||
temp |= DREF_NONSPREAD_SOURCE_ENABLE;
|
||||
temp &= ~DREF_SSC_SOURCE_MASK;
|
||||
temp |= DREF_SSC_SOURCE_ENABLE;
|
||||
I915_WRITE(PCH_DREF_CONTROL, temp);
|
||||
|
||||
POSTING_READ(PCH_DREF_CONTROL);
|
||||
udelay(200);
|
||||
|
||||
if (has_edp_encoder) {
|
||||
if (intel_panel_use_ssc(dev_priv)) {
|
||||
temp |= DREF_SSC1_ENABLE;
|
||||
I915_WRITE(PCH_DREF_CONTROL, temp);
|
||||
|
||||
POSTING_READ(PCH_DREF_CONTROL);
|
||||
udelay(200);
|
||||
}
|
||||
temp &= ~DREF_CPU_SOURCE_OUTPUT_MASK;
|
||||
|
||||
/* Enable CPU source on CPU attached eDP */
|
||||
if (!intel_encoder_is_pch_edp(&has_edp_encoder->base)) {
|
||||
if (intel_panel_use_ssc(dev_priv))
|
||||
temp |= DREF_CPU_SOURCE_OUTPUT_DOWNSPREAD;
|
||||
else
|
||||
temp |= DREF_CPU_SOURCE_OUTPUT_NONSPREAD;
|
||||
} else {
|
||||
/* Enable SSC on PCH eDP if needed */
|
||||
if (intel_panel_use_ssc(dev_priv)) {
|
||||
DRM_ERROR("enabling SSC on PCH\n");
|
||||
temp |= DREF_SUPERSPREAD_SOURCE_ENABLE;
|
||||
}
|
||||
}
|
||||
I915_WRITE(PCH_DREF_CONTROL, temp);
|
||||
POSTING_READ(PCH_DREF_CONTROL);
|
||||
udelay(200);
|
||||
}
|
||||
ironlake_update_pch_refclk(dev);
|
||||
|
||||
fp = clock.n << 16 | clock.m1 << 8 | clock.m2;
|
||||
if (has_reduced_clock)
|
||||
|
@ -1841,6 +1841,11 @@ intel_dp_set_property(struct drm_connector *connector,
|
||||
static void
|
||||
intel_dp_destroy (struct drm_connector *connector)
|
||||
{
|
||||
struct drm_device *dev = connector->dev;
|
||||
|
||||
if (intel_dpd_is_edp(dev))
|
||||
intel_panel_destroy_backlight(dev);
|
||||
|
||||
drm_sysfs_connector_remove(connector);
|
||||
drm_connector_cleanup(connector);
|
||||
kfree(connector);
|
||||
@ -2072,6 +2077,8 @@ intel_dp_init(struct drm_device *dev, int output_reg)
|
||||
DRM_MODE_TYPE_PREFERRED;
|
||||
}
|
||||
}
|
||||
dev_priv->int_edp_connector = connector;
|
||||
intel_panel_setup_backlight(dev);
|
||||
}
|
||||
|
||||
intel_dp_add_properties(intel_dp, connector);
|
||||
|
@ -297,9 +297,10 @@ extern void intel_pch_panel_fitting(struct drm_device *dev,
|
||||
extern u32 intel_panel_get_max_backlight(struct drm_device *dev);
|
||||
extern u32 intel_panel_get_backlight(struct drm_device *dev);
|
||||
extern void intel_panel_set_backlight(struct drm_device *dev, u32 level);
|
||||
extern void intel_panel_setup_backlight(struct drm_device *dev);
|
||||
extern int intel_panel_setup_backlight(struct drm_device *dev);
|
||||
extern void intel_panel_enable_backlight(struct drm_device *dev);
|
||||
extern void intel_panel_disable_backlight(struct drm_device *dev);
|
||||
extern void intel_panel_destroy_backlight(struct drm_device *dev);
|
||||
extern enum drm_connector_status intel_panel_detect(struct drm_device *dev);
|
||||
|
||||
extern void intel_crtc_load_lut(struct drm_crtc *crtc);
|
||||
|
@ -72,14 +72,16 @@ static void intel_lvds_enable(struct intel_lvds *intel_lvds)
|
||||
{
|
||||
struct drm_device *dev = intel_lvds->base.base.dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
u32 ctl_reg, lvds_reg;
|
||||
u32 ctl_reg, lvds_reg, stat_reg;
|
||||
|
||||
if (HAS_PCH_SPLIT(dev)) {
|
||||
ctl_reg = PCH_PP_CONTROL;
|
||||
lvds_reg = PCH_LVDS;
|
||||
stat_reg = PCH_PP_STATUS;
|
||||
} else {
|
||||
ctl_reg = PP_CONTROL;
|
||||
lvds_reg = LVDS;
|
||||
stat_reg = PP_STATUS;
|
||||
}
|
||||
|
||||
I915_WRITE(lvds_reg, I915_READ(lvds_reg) | LVDS_PORT_EN);
|
||||
@ -94,17 +96,16 @@ static void intel_lvds_enable(struct intel_lvds *intel_lvds)
|
||||
DRM_DEBUG_KMS("applying panel-fitter: %x, %x\n",
|
||||
intel_lvds->pfit_control,
|
||||
intel_lvds->pfit_pgm_ratios);
|
||||
if (wait_for((I915_READ(PP_STATUS) & PP_ON) == 0, 1000)) {
|
||||
DRM_ERROR("timed out waiting for panel to power off\n");
|
||||
} else {
|
||||
I915_WRITE(PFIT_PGM_RATIOS, intel_lvds->pfit_pgm_ratios);
|
||||
I915_WRITE(PFIT_CONTROL, intel_lvds->pfit_control);
|
||||
intel_lvds->pfit_dirty = false;
|
||||
}
|
||||
|
||||
I915_WRITE(PFIT_PGM_RATIOS, intel_lvds->pfit_pgm_ratios);
|
||||
I915_WRITE(PFIT_CONTROL, intel_lvds->pfit_control);
|
||||
intel_lvds->pfit_dirty = false;
|
||||
}
|
||||
|
||||
I915_WRITE(ctl_reg, I915_READ(ctl_reg) | POWER_TARGET_ON);
|
||||
POSTING_READ(lvds_reg);
|
||||
if (wait_for((I915_READ(stat_reg) & PP_ON) != 0, 1000))
|
||||
DRM_ERROR("timed out waiting for panel to power on\n");
|
||||
|
||||
intel_panel_enable_backlight(dev);
|
||||
}
|
||||
@ -113,24 +114,25 @@ static void intel_lvds_disable(struct intel_lvds *intel_lvds)
|
||||
{
|
||||
struct drm_device *dev = intel_lvds->base.base.dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
u32 ctl_reg, lvds_reg;
|
||||
u32 ctl_reg, lvds_reg, stat_reg;
|
||||
|
||||
if (HAS_PCH_SPLIT(dev)) {
|
||||
ctl_reg = PCH_PP_CONTROL;
|
||||
lvds_reg = PCH_LVDS;
|
||||
stat_reg = PCH_PP_STATUS;
|
||||
} else {
|
||||
ctl_reg = PP_CONTROL;
|
||||
lvds_reg = LVDS;
|
||||
stat_reg = PP_STATUS;
|
||||
}
|
||||
|
||||
intel_panel_disable_backlight(dev);
|
||||
|
||||
I915_WRITE(ctl_reg, I915_READ(ctl_reg) & ~POWER_TARGET_ON);
|
||||
if (wait_for((I915_READ(stat_reg) & PP_ON) == 0, 1000))
|
||||
DRM_ERROR("timed out waiting for panel to power off\n");
|
||||
|
||||
if (intel_lvds->pfit_control) {
|
||||
if (wait_for((I915_READ(PP_STATUS) & PP_ON) == 0, 1000))
|
||||
DRM_ERROR("timed out waiting for panel to power off\n");
|
||||
|
||||
I915_WRITE(PFIT_CONTROL, 0);
|
||||
intel_lvds->pfit_dirty = true;
|
||||
}
|
||||
@ -398,53 +400,21 @@ static bool intel_lvds_mode_fixup(struct drm_encoder *encoder,
|
||||
|
||||
static void intel_lvds_prepare(struct drm_encoder *encoder)
|
||||
{
|
||||
struct drm_device *dev = encoder->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct intel_lvds *intel_lvds = to_intel_lvds(encoder);
|
||||
|
||||
/* We try to do the minimum that is necessary in order to unlock
|
||||
* the registers for mode setting.
|
||||
*
|
||||
* On Ironlake, this is quite simple as we just set the unlock key
|
||||
* and ignore all subtleties. (This may cause some issues...)
|
||||
*
|
||||
/*
|
||||
* Prior to Ironlake, we must disable the pipe if we want to adjust
|
||||
* the panel fitter. However at all other times we can just reset
|
||||
* the registers regardless.
|
||||
*/
|
||||
|
||||
if (HAS_PCH_SPLIT(dev)) {
|
||||
I915_WRITE(PCH_PP_CONTROL,
|
||||
I915_READ(PCH_PP_CONTROL) | PANEL_UNLOCK_REGS);
|
||||
} else if (intel_lvds->pfit_dirty) {
|
||||
I915_WRITE(PP_CONTROL,
|
||||
(I915_READ(PP_CONTROL) | PANEL_UNLOCK_REGS)
|
||||
& ~POWER_TARGET_ON);
|
||||
} else {
|
||||
I915_WRITE(PP_CONTROL,
|
||||
I915_READ(PP_CONTROL) | PANEL_UNLOCK_REGS);
|
||||
}
|
||||
if (!HAS_PCH_SPLIT(encoder->dev) && intel_lvds->pfit_dirty)
|
||||
intel_lvds_disable(intel_lvds);
|
||||
}
|
||||
|
||||
static void intel_lvds_commit(struct drm_encoder *encoder)
|
||||
{
|
||||
struct drm_device *dev = encoder->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct intel_lvds *intel_lvds = to_intel_lvds(encoder);
|
||||
|
||||
/* Undo any unlocking done in prepare to prevent accidental
|
||||
* adjustment of the registers.
|
||||
*/
|
||||
if (HAS_PCH_SPLIT(dev)) {
|
||||
u32 val = I915_READ(PCH_PP_CONTROL);
|
||||
if ((val & PANEL_UNLOCK_REGS) == PANEL_UNLOCK_REGS)
|
||||
I915_WRITE(PCH_PP_CONTROL, val & 0x3);
|
||||
} else {
|
||||
u32 val = I915_READ(PP_CONTROL);
|
||||
if ((val & PANEL_UNLOCK_REGS) == PANEL_UNLOCK_REGS)
|
||||
I915_WRITE(PP_CONTROL, val & 0x3);
|
||||
}
|
||||
|
||||
/* Always do a full power on as we do not know what state
|
||||
* we were left in.
|
||||
*/
|
||||
@ -582,6 +552,8 @@ static void intel_lvds_destroy(struct drm_connector *connector)
|
||||
struct drm_device *dev = connector->dev;
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
|
||||
intel_panel_destroy_backlight(dev);
|
||||
|
||||
if (dev_priv->lid_notifier.notifier_call)
|
||||
acpi_lid_notifier_unregister(&dev_priv->lid_notifier);
|
||||
drm_sysfs_connector_remove(connector);
|
||||
@ -1040,6 +1012,19 @@ bool intel_lvds_init(struct drm_device *dev)
|
||||
pwm = I915_READ(BLC_PWM_PCH_CTL1);
|
||||
pwm |= PWM_PCH_ENABLE;
|
||||
I915_WRITE(BLC_PWM_PCH_CTL1, pwm);
|
||||
/*
|
||||
* Unlock registers and just
|
||||
* leave them unlocked
|
||||
*/
|
||||
I915_WRITE(PCH_PP_CONTROL,
|
||||
I915_READ(PCH_PP_CONTROL) | PANEL_UNLOCK_REGS);
|
||||
} else {
|
||||
/*
|
||||
* Unlock registers and just
|
||||
* leave them unlocked
|
||||
*/
|
||||
I915_WRITE(PP_CONTROL,
|
||||
I915_READ(PP_CONTROL) | PANEL_UNLOCK_REGS);
|
||||
}
|
||||
dev_priv->lid_notifier.notifier_call = intel_lid_notify;
|
||||
if (acpi_lid_notifier_register(&dev_priv->lid_notifier)) {
|
||||
@ -1049,6 +1034,9 @@ bool intel_lvds_init(struct drm_device *dev)
|
||||
/* keep the LVDS connector */
|
||||
dev_priv->int_lvds_connector = connector;
|
||||
drm_sysfs_connector_add(connector);
|
||||
|
||||
intel_panel_setup_backlight(dev);
|
||||
|
||||
return true;
|
||||
|
||||
failed:
|
||||
|
@ -227,7 +227,6 @@ void intel_opregion_asle_intr(struct drm_device *dev)
|
||||
asle->aslc = asle_stat;
|
||||
}
|
||||
|
||||
/* Only present on Ironlake+ */
|
||||
void intel_opregion_gse_intr(struct drm_device *dev)
|
||||
{
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
|
@ -277,7 +277,7 @@ void intel_panel_enable_backlight(struct drm_device *dev)
|
||||
dev_priv->backlight_enabled = true;
|
||||
}
|
||||
|
||||
void intel_panel_setup_backlight(struct drm_device *dev)
|
||||
static void intel_panel_init_backlight(struct drm_device *dev)
|
||||
{
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
|
||||
@ -309,3 +309,73 @@ intel_panel_detect(struct drm_device *dev)
|
||||
|
||||
return connector_status_unknown;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_BACKLIGHT_CLASS_DEVICE
|
||||
static int intel_panel_update_status(struct backlight_device *bd)
|
||||
{
|
||||
struct drm_device *dev = bl_get_data(bd);
|
||||
intel_panel_set_backlight(dev, bd->props.brightness);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int intel_panel_get_brightness(struct backlight_device *bd)
|
||||
{
|
||||
struct drm_device *dev = bl_get_data(bd);
|
||||
return intel_panel_get_backlight(dev);
|
||||
}
|
||||
|
||||
static const struct backlight_ops intel_panel_bl_ops = {
|
||||
.update_status = intel_panel_update_status,
|
||||
.get_brightness = intel_panel_get_brightness,
|
||||
};
|
||||
|
||||
int intel_panel_setup_backlight(struct drm_device *dev)
|
||||
{
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
struct backlight_properties props;
|
||||
struct drm_connector *connector;
|
||||
|
||||
intel_panel_init_backlight(dev);
|
||||
|
||||
if (dev_priv->int_lvds_connector)
|
||||
connector = dev_priv->int_lvds_connector;
|
||||
else if (dev_priv->int_edp_connector)
|
||||
connector = dev_priv->int_edp_connector;
|
||||
else
|
||||
return -ENODEV;
|
||||
|
||||
props.type = BACKLIGHT_RAW;
|
||||
props.max_brightness = intel_panel_get_max_backlight(dev);
|
||||
dev_priv->backlight =
|
||||
backlight_device_register("intel_backlight",
|
||||
&connector->kdev, dev,
|
||||
&intel_panel_bl_ops, &props);
|
||||
|
||||
if (IS_ERR(dev_priv->backlight)) {
|
||||
DRM_ERROR("Failed to register backlight: %ld\n",
|
||||
PTR_ERR(dev_priv->backlight));
|
||||
dev_priv->backlight = NULL;
|
||||
return -ENODEV;
|
||||
}
|
||||
dev_priv->backlight->props.brightness = intel_panel_get_backlight(dev);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void intel_panel_destroy_backlight(struct drm_device *dev)
|
||||
{
|
||||
struct drm_i915_private *dev_priv = dev->dev_private;
|
||||
if (dev_priv->backlight)
|
||||
backlight_device_unregister(dev_priv->backlight);
|
||||
}
|
||||
#else
|
||||
int intel_panel_setup_backlight(struct drm_device *dev)
|
||||
{
|
||||
intel_panel_init_backlight(dev);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void intel_panel_destroy_backlight(struct drm_device *dev)
|
||||
{
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
@ -613,6 +613,18 @@ static bool radeon_dp_get_link_status(struct radeon_connector *radeon_connector,
|
||||
return true;
|
||||
}
|
||||
|
||||
bool radeon_dp_needs_link_train(struct radeon_connector *radeon_connector)
|
||||
{
|
||||
u8 link_status[DP_LINK_STATUS_SIZE];
|
||||
struct radeon_connector_atom_dig *dig = radeon_connector->con_priv;
|
||||
|
||||
if (!radeon_dp_get_link_status(radeon_connector, link_status))
|
||||
return false;
|
||||
if (dp_channel_eq_ok(link_status, dig->dp_lane_count))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
struct radeon_dp_link_train_info {
|
||||
struct radeon_device *rdev;
|
||||
struct drm_encoder *encoder;
|
||||
|
@ -743,7 +743,7 @@ static void evergreen_program_watermarks(struct radeon_device *rdev,
|
||||
!evergreen_average_bandwidth_vs_available_bandwidth(&wm) ||
|
||||
!evergreen_check_latency_hiding(&wm) ||
|
||||
(rdev->disp_priority == 2)) {
|
||||
DRM_INFO("force priority to high\n");
|
||||
DRM_DEBUG_KMS("force priority to high\n");
|
||||
priority_a_cnt |= PRIORITY_ALWAYS_ON;
|
||||
priority_b_cnt |= PRIORITY_ALWAYS_ON;
|
||||
}
|
||||
|
@ -60,18 +60,20 @@ void radeon_connector_hotplug(struct drm_connector *connector)
|
||||
|
||||
radeon_hpd_set_polarity(rdev, radeon_connector->hpd.hpd);
|
||||
|
||||
/* powering up/down the eDP panel generates hpd events which
|
||||
* can interfere with modesetting.
|
||||
*/
|
||||
if (connector->connector_type == DRM_MODE_CONNECTOR_eDP)
|
||||
/* if the connector is already off, don't turn it back on */
|
||||
if (connector->dpms != DRM_MODE_DPMS_ON)
|
||||
return;
|
||||
|
||||
/* pre-r600 did not always have the hpd pins mapped accurately to connectors */
|
||||
if (rdev->family >= CHIP_R600) {
|
||||
if (radeon_hpd_sense(rdev, radeon_connector->hpd.hpd))
|
||||
/* just deal with DP (not eDP) here. */
|
||||
if (connector->connector_type == DRM_MODE_CONNECTOR_DisplayPort) {
|
||||
int saved_dpms = connector->dpms;
|
||||
|
||||
if (radeon_hpd_sense(rdev, radeon_connector->hpd.hpd) &&
|
||||
radeon_dp_needs_link_train(radeon_connector))
|
||||
drm_helper_connector_dpms(connector, DRM_MODE_DPMS_ON);
|
||||
else
|
||||
drm_helper_connector_dpms(connector, DRM_MODE_DPMS_OFF);
|
||||
connector->dpms = saved_dpms;
|
||||
}
|
||||
}
|
||||
|
||||
@ -474,11 +476,19 @@ static void radeon_fixup_lvds_native_mode(struct drm_encoder *encoder,
|
||||
{
|
||||
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
|
||||
struct drm_display_mode *native_mode = &radeon_encoder->native_mode;
|
||||
struct drm_display_mode *t, *mode;
|
||||
|
||||
/* If the EDID preferred mode doesn't match the native mode, use it */
|
||||
list_for_each_entry_safe(mode, t, &connector->probed_modes, head) {
|
||||
if (mode->type & DRM_MODE_TYPE_PREFERRED) {
|
||||
if (mode->hdisplay != native_mode->hdisplay ||
|
||||
mode->vdisplay != native_mode->vdisplay)
|
||||
memcpy(native_mode, mode, sizeof(*mode));
|
||||
}
|
||||
}
|
||||
|
||||
/* Try to get native mode details from EDID if necessary */
|
||||
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->hdisplay &&
|
||||
mode->vdisplay == native_mode->vdisplay) {
|
||||
@ -489,6 +499,7 @@ static void radeon_fixup_lvds_native_mode(struct drm_encoder *encoder,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!native_mode->clock) {
|
||||
DRM_DEBUG_KMS("No LVDS native mode details, disabling RMX\n");
|
||||
radeon_encoder->rmx_type = RMX_OFF;
|
||||
|
@ -32,6 +32,7 @@
|
||||
#include <drm/radeon_drm.h>
|
||||
#include <linux/vgaarb.h>
|
||||
#include <linux/vga_switcheroo.h>
|
||||
#include <linux/efi.h>
|
||||
#include "radeon_reg.h"
|
||||
#include "radeon.h"
|
||||
#include "atom.h"
|
||||
@ -348,6 +349,9 @@ bool radeon_card_posted(struct radeon_device *rdev)
|
||||
{
|
||||
uint32_t reg;
|
||||
|
||||
if (efi_enabled && rdev->pdev->subsystem_vendor == PCI_VENDOR_ID_APPLE)
|
||||
return false;
|
||||
|
||||
/* first check CRTCs */
|
||||
if (ASIC_IS_DCE41(rdev)) {
|
||||
reg = RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC0_REGISTER_OFFSET) |
|
||||
|
@ -2323,6 +2323,9 @@ radeon_add_atom_encoder(struct drm_device *dev,
|
||||
default:
|
||||
encoder->possible_crtcs = 0x3;
|
||||
break;
|
||||
case 4:
|
||||
encoder->possible_crtcs = 0xf;
|
||||
break;
|
||||
case 6:
|
||||
encoder->possible_crtcs = 0x3f;
|
||||
break;
|
||||
|
@ -479,6 +479,7 @@ extern void radeon_dp_set_link_config(struct drm_connector *connector,
|
||||
struct drm_display_mode *mode);
|
||||
extern void radeon_dp_link_train(struct drm_encoder *encoder,
|
||||
struct drm_connector *connector);
|
||||
extern bool radeon_dp_needs_link_train(struct radeon_connector *radeon_connector);
|
||||
extern u8 radeon_dp_getsinktype(struct radeon_connector *radeon_connector);
|
||||
extern bool radeon_dp_getdpcd(struct radeon_connector *radeon_connector);
|
||||
extern void atombios_dig_encoder_setup(struct drm_encoder *encoder, int action, int panel_mode);
|
||||
|
@ -432,13 +432,15 @@ static int aem_read_sensor(struct aem_data *data, u8 elt, u8 reg,
|
||||
aem_send_message(ipmi);
|
||||
|
||||
res = wait_for_completion_timeout(&ipmi->read_complete, IPMI_TIMEOUT);
|
||||
if (!res)
|
||||
return -ETIMEDOUT;
|
||||
if (!res) {
|
||||
res = -ETIMEDOUT;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (ipmi->rx_result || ipmi->rx_msg_len != rs_size ||
|
||||
memcmp(&rs_resp->id, &system_x_id, sizeof(system_x_id))) {
|
||||
kfree(rs_resp);
|
||||
return -ENOENT;
|
||||
res = -ENOENT;
|
||||
goto out;
|
||||
}
|
||||
|
||||
switch (size) {
|
||||
@ -463,8 +465,11 @@ static int aem_read_sensor(struct aem_data *data, u8 elt, u8 reg,
|
||||
break;
|
||||
}
|
||||
}
|
||||
res = 0;
|
||||
|
||||
return 0;
|
||||
out:
|
||||
kfree(rs_resp);
|
||||
return res;
|
||||
}
|
||||
|
||||
/* Update AEM energy registers */
|
||||
|
@ -161,6 +161,17 @@ static int lm25066_write_word_data(struct i2c_client *client, int page, int reg,
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int lm25066_write_byte(struct i2c_client *client, int page, u8 value)
|
||||
{
|
||||
if (page > 1)
|
||||
return -EINVAL;
|
||||
|
||||
if (page == 0)
|
||||
return pmbus_write_byte(client, 0, value);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int lm25066_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id)
|
||||
{
|
||||
@ -204,6 +215,7 @@ static int lm25066_probe(struct i2c_client *client,
|
||||
|
||||
info->read_word_data = lm25066_read_word_data;
|
||||
info->write_word_data = lm25066_write_word_data;
|
||||
info->write_byte = lm25066_write_byte;
|
||||
|
||||
switch (id->driver_data) {
|
||||
case lm25066:
|
||||
|
@ -325,6 +325,7 @@ struct pmbus_driver_info {
|
||||
int (*read_word_data)(struct i2c_client *client, int page, int reg);
|
||||
int (*write_word_data)(struct i2c_client *client, int page, int reg,
|
||||
u16 word);
|
||||
int (*write_byte)(struct i2c_client *client, int page, u8 value);
|
||||
/*
|
||||
* The identify function determines supported PMBus functionality.
|
||||
* This function is only necessary if a chip driver supports multiple
|
||||
|
@ -182,6 +182,24 @@ int pmbus_write_byte(struct i2c_client *client, int page, u8 value)
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(pmbus_write_byte);
|
||||
|
||||
/*
|
||||
* _pmbus_write_byte() is similar to pmbus_write_byte(), but checks if
|
||||
* a device specific mapping funcion exists and calls it if necessary.
|
||||
*/
|
||||
static int _pmbus_write_byte(struct i2c_client *client, int page, u8 value)
|
||||
{
|
||||
struct pmbus_data *data = i2c_get_clientdata(client);
|
||||
const struct pmbus_driver_info *info = data->info;
|
||||
int status;
|
||||
|
||||
if (info->write_byte) {
|
||||
status = info->write_byte(client, page, value);
|
||||
if (status != -ENODATA)
|
||||
return status;
|
||||
}
|
||||
return pmbus_write_byte(client, page, value);
|
||||
}
|
||||
|
||||
int pmbus_write_word_data(struct i2c_client *client, u8 page, u8 reg, u16 word)
|
||||
{
|
||||
int rv;
|
||||
@ -281,7 +299,7 @@ static int _pmbus_read_byte_data(struct i2c_client *client, int page, int reg)
|
||||
|
||||
static void pmbus_clear_fault_page(struct i2c_client *client, int page)
|
||||
{
|
||||
pmbus_write_byte(client, page, PMBUS_CLEAR_FAULTS);
|
||||
_pmbus_write_byte(client, page, PMBUS_CLEAR_FAULTS);
|
||||
}
|
||||
|
||||
void pmbus_clear_faults(struct i2c_client *client)
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user