Unified · Split
| @@ -122,6 +122,7 @@ ForEachMacros: · 121 unmodified lines | |||
| 122 | - 'drm_for_each_bridge_in_chain' | 122 | - 'drm_for_each_bridge_in_chain' |
| 123 | - 'drm_for_each_connector_iter' | 123 | - 'drm_for_each_connector_iter' |
| 124 | - 'drm_for_each_crtc' | 124 | - 'drm_for_each_crtc' |
| 125 | - 'drm_for_each_crtc_reverse' | ||
| 125 | - 'drm_for_each_encoder' | 126 | - 'drm_for_each_encoder' |
| 126 | - 'drm_for_each_encoder_mask' | 127 | - 'drm_for_each_encoder_mask' |
| 127 | - 'drm_for_each_fb' | 128 | - 'drm_for_each_fb' |
| @@ -203,14 +204,13 @@ ForEachMacros: · 75 unmodified lines | |||
| 203 | - 'for_each_matching_node' | 204 | - 'for_each_matching_node' |
| 204 | - 'for_each_matching_node_and_match' | 205 | - 'for_each_matching_node_and_match' |
| 205 | - 'for_each_member' | 206 | - 'for_each_member' |
| 206 | - 'for_each_mem_region' | ||
| 207 | - 'for_each_memblock_type' | ||
| 208 | - 'for_each_memcg_cache_index' | 207 | - 'for_each_memcg_cache_index' |
| 209 | - 'for_each_mem_pfn_range' | 208 | - 'for_each_mem_pfn_range' |
| 210 | - '__for_each_mem_range' | 209 | - '__for_each_mem_range' |
| 211 | - 'for_each_mem_range' | 210 | - 'for_each_mem_range' |
| 212 | - '__for_each_mem_range_rev' | 211 | - '__for_each_mem_range_rev' |
| 213 | - 'for_each_mem_range_rev' | 212 | - 'for_each_mem_range_rev' |
| 213 | - 'for_each_mem_region' | ||
| 214 | - 'for_each_migratetype_order' | 214 | - 'for_each_migratetype_order' |
| 215 | - 'for_each_msi_entry' | 215 | - 'for_each_msi_entry' |
| 216 | - 'for_each_msi_entry_safe' | 216 | - 'for_each_msi_entry_safe' |
| @@ -276,10 +276,8 @@ ForEachMacros: · 59 unmodified lines | |||
| 276 | - 'for_each_reserved_mem_range' | 276 | - 'for_each_reserved_mem_range' |
| 277 | - 'for_each_reserved_mem_region' | 277 | - 'for_each_reserved_mem_region' |
| 278 | - 'for_each_rtd_codec_dais' | 278 | - 'for_each_rtd_codec_dais' |
| 279 | - 'for_each_rtd_codec_dais_rollback' | ||
| 280 | - 'for_each_rtd_components' | 279 | - 'for_each_rtd_components' |
| 281 | - 'for_each_rtd_cpu_dais' | 280 | - 'for_each_rtd_cpu_dais' |
| 282 | - 'for_each_rtd_cpu_dais_rollback' | ||
| 283 | - 'for_each_rtd_dais' | 281 | - 'for_each_rtd_dais' |
| 284 | - 'for_each_set_bit' | 282 | - 'for_each_set_bit' |
| 285 | - 'for_each_set_bit_from' | 283 | - 'for_each_set_bit_from' |
| @@ -298,6 +296,7 @@ ForEachMacros: · 12 unmodified lines | |||
| 298 | - '__for_each_thread' | 296 | - '__for_each_thread' |
| 299 | - 'for_each_thread' | 297 | - 'for_each_thread' |
| 300 | - 'for_each_unicast_dest_pgid' | 298 | - 'for_each_unicast_dest_pgid' |
| 299 | - 'for_each_vsi' | ||
| 301 | - 'for_each_wakeup_source' | 300 | - 'for_each_wakeup_source' |
| 302 | - 'for_each_zone' | 301 | - 'for_each_zone' |
| 303 | - 'for_each_zone_zonelist' | 302 | - 'for_each_zone_zonelist' |
| @@ -330,6 +329,7 @@ ForEachMacros: · 26 unmodified lines | |||
| 330 | - 'hlist_for_each_entry_rcu_bh' | 329 | - 'hlist_for_each_entry_rcu_bh' |
| 331 | - 'hlist_for_each_entry_rcu_notrace' | 330 | - 'hlist_for_each_entry_rcu_notrace' |
| 332 | - 'hlist_for_each_entry_safe' | 331 | - 'hlist_for_each_entry_safe' |
| 332 | - 'hlist_for_each_entry_srcu' | ||
| 333 | - '__hlist_for_each_rcu' | 333 | - '__hlist_for_each_rcu' |
| 334 | - 'hlist_for_each_safe' | 334 | - 'hlist_for_each_safe' |
| 335 | - 'hlist_nulls_for_each_entry' | 335 | - 'hlist_nulls_for_each_entry' |
| @@ -378,6 +378,7 @@ ForEachMacros: · 42 unmodified lines | |||
| 378 | - 'list_for_each_entry_safe_continue' | 378 | - 'list_for_each_entry_safe_continue' |
| 379 | - 'list_for_each_entry_safe_from' | 379 | - 'list_for_each_entry_safe_from' |
| 380 | - 'list_for_each_entry_safe_reverse' | 380 | - 'list_for_each_entry_safe_reverse' |
| 381 | - 'list_for_each_entry_srcu' | ||
| 381 | - 'list_for_each_prev' | 382 | - 'list_for_each_prev' |
| 382 | - 'list_for_each_prev_safe' | 383 | - 'list_for_each_prev_safe' |
| 383 | - 'list_for_each_safe' | 384 | - 'list_for_each_safe' |
| @@ -411,6 +412,8 @@ ForEachMacros: · 27 unmodified lines | |||
| 411 | - 'of_property_for_each_string' | 412 | - 'of_property_for_each_string' |
| 412 | - 'of_property_for_each_u32' | 413 | - 'of_property_for_each_u32' |
| 413 | - 'pci_bus_for_each_resource' | 414 | - 'pci_bus_for_each_resource' |
| 415 | - 'pcl_for_each_chunk' | ||
| 416 | - 'pcl_for_each_segment' | ||
| 414 | - 'pcm_for_each_format' | 417 | - 'pcm_for_each_format' |
| 415 | - 'ping_portaddr_for_each_entry' | 418 | - 'ping_portaddr_for_each_entry' |
| 416 | - 'plist_for_each' | 419 | - 'plist_for_each' |
| @@ -9,9 +9,6 @@ · 8 unmodified lines | |||
| 9 | # | 9 | # |
| 10 | # Please keep this list dictionary sorted. | 10 | # Please keep this list dictionary sorted. |
| 11 | # | 11 | # |
| 12 | # This comment is parsed by git-shortlog: | ||
| 13 | # repo-abbrev: /pub/scm/linux/kernel/git/ | ||
| 14 | # | ||
| 15 | Aaron Durbin <adurbin@google.com> | 12 | Aaron Durbin <adurbin@google.com> |
| 16 | Adam Oldham <oldhamca@gmail.com> | 13 | Adam Oldham <oldhamca@gmail.com> |
| 17 | Adam Radford <aradford@gmail.com> | 14 | Adam Radford <aradford@gmail.com> |
| @@ -40,6 +37,7 @@ Andrew Murray <amurray@thegoodpenguin.co.uk> <amurray@embedded-bits.co.uk> · 22 unmodified lines | |||
| 40 | Andrew Murray <amurray@thegoodpenguin.co.uk> <andrew.murray@arm.com> | 37 | Andrew Murray <amurray@thegoodpenguin.co.uk> <andrew.murray@arm.com> |
| 41 | Andrew Vasquez <andrew.vasquez@qlogic.com> | 38 | Andrew Vasquez <andrew.vasquez@qlogic.com> |
| 42 | Andrey Ryabinin <ryabinin.a.a@gmail.com> <a.ryabinin@samsung.com> | 39 | Andrey Ryabinin <ryabinin.a.a@gmail.com> <a.ryabinin@samsung.com> |
| 40 | Andrey Ryabinin <ryabinin.a.a@gmail.com> <aryabinin@virtuozzo.com> | ||
| 43 | Andy Adamson <andros@citi.umich.edu> | 41 | Andy Adamson <andros@citi.umich.edu> |
| 44 | Antoine Tenart <atenart@kernel.org> <antoine.tenart@bootlin.com> | 42 | Antoine Tenart <atenart@kernel.org> <antoine.tenart@bootlin.com> |
| 45 | Antoine Tenart <atenart@kernel.org> <antoine.tenart@free-electrons.com> | 43 | Antoine Tenart <atenart@kernel.org> <antoine.tenart@free-electrons.com> |
| @@ -55,6 +53,8 @@ Bart Van Assche <bvanassche@acm.org> <bart.vanassche@wdc.com> · 9 unmodified lines | |||
| 55 | Ben Gardner <bgardner@wabtec.com> | 53 | Ben Gardner <bgardner@wabtec.com> |
| 56 | Ben M Cahill <ben.m.cahill@intel.com> | 54 | Ben M Cahill <ben.m.cahill@intel.com> |
| 57 | Björn Steinbrink <B.Steinbrink@gmx.de> | 55 | Björn Steinbrink <B.Steinbrink@gmx.de> |
| 56 | Björn Töpel <bjorn@kernel.org> <bjorn.topel@gmail.com> | ||
| 57 | Björn Töpel <bjorn@kernel.org> <bjorn.topel@intel.com> | ||
| 58 | Boris Brezillon <bbrezillon@kernel.org> <b.brezillon.dev@gmail.com> | 58 | Boris Brezillon <bbrezillon@kernel.org> <b.brezillon.dev@gmail.com> |
| 59 | Boris Brezillon <bbrezillon@kernel.org> <b.brezillon@overkiz.com> | 59 | Boris Brezillon <bbrezillon@kernel.org> <b.brezillon@overkiz.com> |
| 60 | Boris Brezillon <bbrezillon@kernel.org> <boris.brezillon@bootlin.com> | 60 | Boris Brezillon <bbrezillon@kernel.org> <boris.brezillon@bootlin.com> |
| @@ -180,6 +180,8 @@ Kees Cook <keescook@chromium.org> <kees.cook@canonical.com> · 119 unmodified lines | |||
| 180 | Kees Cook <keescook@chromium.org> <keescook@google.com> | 180 | Kees Cook <keescook@chromium.org> <keescook@google.com> |
| 181 | Kees Cook <keescook@chromium.org> <kees@outflux.net> | 181 | Kees Cook <keescook@chromium.org> <kees@outflux.net> |
| 182 | Kees Cook <keescook@chromium.org> <kees@ubuntu.com> | 182 | Kees Cook <keescook@chromium.org> <kees@ubuntu.com> |
| 183 | Keith Busch <kbusch@kernel.org> <keith.busch@intel.com> | ||
| 184 | Keith Busch <kbusch@kernel.org> <keith.busch@linux.intel.com> | ||
| 183 | Kenneth W Chen <kenneth.w.chen@intel.com> | 185 | Kenneth W Chen <kenneth.w.chen@intel.com> |
| 184 | Konstantin Khlebnikov <koct9i@gmail.com> <khlebnikov@yandex-team.ru> | 186 | Konstantin Khlebnikov <koct9i@gmail.com> <khlebnikov@yandex-team.ru> |
| 185 | Konstantin Khlebnikov <koct9i@gmail.com> <k.khlebnikov@samsung.com> | 187 | Konstantin Khlebnikov <koct9i@gmail.com> <k.khlebnikov@samsung.com> |
| @@ -200,6 +202,8 @@ Li Yang <leoyang.li@nxp.com> <leoli@freescale.com> · 14 unmodified lines | |||
| 200 | Li Yang <leoyang.li@nxp.com> <leo@zh-kernel.org> | 202 | Li Yang <leoyang.li@nxp.com> <leo@zh-kernel.org> |
| 201 | Lukasz Luba <lukasz.luba@arm.com> <l.luba@partner.samsung.com> | 203 | Lukasz Luba <lukasz.luba@arm.com> <l.luba@partner.samsung.com> |
| 202 | Maciej W. Rozycki <macro@mips.com> <macro@imgtec.com> | 204 | Maciej W. Rozycki <macro@mips.com> <macro@imgtec.com> |
| 205 | Manivannan Sadhasivam <mani@kernel.org> <manivannanece23@gmail.com> | ||
| 206 | Manivannan Sadhasivam <mani@kernel.org> <manivannan.sadhasivam@linaro.org> | ||
| 203 | Marcin Nowakowski <marcin.nowakowski@mips.com> <marcin.nowakowski@imgtec.com> | 207 | Marcin Nowakowski <marcin.nowakowski@mips.com> <marcin.nowakowski@imgtec.com> |
| 204 | Marc Zyngier <maz@kernel.org> <marc.zyngier@arm.com> | 208 | Marc Zyngier <maz@kernel.org> <marc.zyngier@arm.com> |
| 205 | Mark Brown <broonie@sirena.org.uk> | 209 | Mark Brown <broonie@sirena.org.uk> |
| @@ -245,6 +249,7 @@ Morten Welinder <welinder@anemone.rentec.com> · 39 unmodified lines | |||
| 245 | Morten Welinder <welinder@darter.rentec.com> | 249 | Morten Welinder <welinder@darter.rentec.com> |
| 246 | Morten Welinder <welinder@troll.com> | 250 | Morten Welinder <welinder@troll.com> |
| 247 | Mythri P K <mythripk@ti.com> | 251 | Mythri P K <mythripk@ti.com> |
| 252 | Nathan Chancellor <nathan@kernel.org> <natechancellor@gmail.com> | ||
| 248 | Nguyen Anh Quynh <aquynh@gmail.com> | 253 | Nguyen Anh Quynh <aquynh@gmail.com> |
| 249 | Nicolas Ferre <nicolas.ferre@microchip.com> <nicolas.ferre@atmel.com> | 254 | Nicolas Ferre <nicolas.ferre@microchip.com> <nicolas.ferre@atmel.com> |
| 250 | Nicolas Pitre <nico@fluxnic.net> <nicolas.pitre@linaro.org> | 255 | Nicolas Pitre <nico@fluxnic.net> <nicolas.pitre@linaro.org> |
| @@ -335,6 +340,8 @@ Vinod Koul <vkoul@kernel.org> <vkoul@infradead.org> · 84 unmodified lines | |||
| 335 | Viresh Kumar <vireshk@kernel.org> <viresh.kumar2@arm.com> | 340 | Viresh Kumar <vireshk@kernel.org> <viresh.kumar2@arm.com> |
| 336 | Viresh Kumar <vireshk@kernel.org> <viresh.kumar@st.com> | 341 | Viresh Kumar <vireshk@kernel.org> <viresh.kumar@st.com> |
| 337 | Viresh Kumar <vireshk@kernel.org> <viresh.linux@gmail.com> | 342 | Viresh Kumar <vireshk@kernel.org> <viresh.linux@gmail.com> |
| 343 | Viresh Kumar <viresh.kumar@linaro.org> <viresh.kumar@linaro.org> | ||
| 344 | Viresh Kumar <viresh.kumar@linaro.org> <viresh.kumar@linaro.com> | ||
| 338 | Vivien Didelot <vivien.didelot@gmail.com> <vivien.didelot@savoirfairelinux.com> | 345 | Vivien Didelot <vivien.didelot@gmail.com> <vivien.didelot@savoirfairelinux.com> |
| 339 | Vlad Dogaru <ddvlad@gmail.com> <vlad.dogaru@intel.com> | 346 | Vlad Dogaru <ddvlad@gmail.com> <vlad.dogaru@intel.com> |
| 340 | Vladimir Davydov <vdavydov.dev@gmail.com> <vdavydov@parallels.com> | 347 | Vladimir Davydov <vdavydov.dev@gmail.com> <vdavydov@parallels.com> |
| @@ -710,6 +710,10 @@ S: Las Cuevas 2385 - Bo Guemes · 709 unmodified lines | |||
| 710 | S: Las Heras, Mendoza CP 5539 | 710 | S: Las Heras, Mendoza CP 5539 |
| 711 | S: Argentina | 711 | S: Argentina |
| 712 | 712 | ||
| 713 | N: Jay Cliburn | ||
| 714 | E: jcliburn@gmail.com | ||
| 715 | D: ATLX Ethernet drivers | ||
| 716 | |||
| 713 | N: Steven P. Cole | 717 | N: Steven P. Cole |
| 714 | E: scole@lanl.gov | 718 | E: scole@lanl.gov |
| 715 | E: elenstev@mesatop.com | 719 | E: elenstev@mesatop.com |
| @@ -1284,6 +1288,10 @@ D: Major kbuild rework during the 2.5 cycle · 568 unmodified lines | |||
| 1284 | D: ISDN Maintainer | 1288 | D: ISDN Maintainer |
| 1285 | S: USA | 1289 | S: USA |
| 1286 | 1290 | ||
| 1291 | N: Gerrit Renker | ||
| 1292 | E: gerrit@erg.abdn.ac.uk | ||
| 1293 | D: DCCP protocol support. | ||
| 1294 | |||
| 1287 | N: Philip Gladstone | 1295 | N: Philip Gladstone |
| 1288 | E: philip@gladstonefamily.net | 1296 | E: philip@gladstonefamily.net |
| 1289 | D: Kernel / timekeeping stuff | 1297 | D: Kernel / timekeeping stuff |
| @@ -2138,6 +2146,10 @@ E: seasons@falcon.sch.bme.hu · 848 unmodified lines | |||
| 2138 | E: seasons@makosteszta.sote.hu | 2146 | E: seasons@makosteszta.sote.hu |
| 2139 | D: Original author of software suspend | 2147 | D: Original author of software suspend |
| 2140 | 2148 | ||
| 2149 | N: Alexey Kuznetsov | ||
| 2150 | E: kuznet@ms2.inr.ac.ru | ||
| 2151 | D: Author and maintainer of large parts of the networking stack | ||
| 2152 | |||
| 2141 | N: Jaroslav Kysela | 2153 | N: Jaroslav Kysela |
| 2142 | E: perex@perex.cz | 2154 | E: perex@perex.cz |
| 2143 | W: https://www.perex.cz | 2155 | W: https://www.perex.cz |
| @@ -2696,6 +2708,10 @@ N: Wolfgang Muees · 552 unmodified lines | |||
| 2696 | E: wolfgang@iksw-muees.de | 2708 | E: wolfgang@iksw-muees.de |
| 2697 | D: Auerswald USB driver | 2709 | D: Auerswald USB driver |
| 2698 | 2710 | ||
| 2711 | N: Shrijeet Mukherjee | ||
| 2712 | E: shrijeet@gmail.com | ||
| 2713 | D: Network routing domains (VRF). | ||
| 2714 | |||
| 2699 | N: Paul Mundt | 2715 | N: Paul Mundt |
| 2700 | E: paul.mundt@gmail.com | 2716 | E: paul.mundt@gmail.com |
| 2701 | D: SuperH maintainer | 2717 | D: SuperH maintainer |
| @@ -4110,6 +4126,10 @@ S: B-1206 Jingmao Guojigongyu · 1408 unmodified lines | |||
| 4110 | S: 16 Baliqiao Nanjie, Beijing 101100 | 4126 | S: 16 Baliqiao Nanjie, Beijing 101100 |
| 4111 | S: People's Repulic of China | 4127 | S: People's Repulic of China |
| 4112 | 4128 | ||
| 4129 | N: Aviad Yehezkel | ||
| 4130 | E: aviadye@nvidia.com | ||
| 4131 | D: Kernel TLS implementation and offload support. | ||
| 4132 | |||
| 4113 | N: Victor Yodaiken | 4133 | N: Victor Yodaiken |
| 4114 | E: yodaiken@fsmlabs.com | 4134 | E: yodaiken@fsmlabs.com |
| 4115 | D: RTLinux (RealTime Linux) | 4135 | D: RTLinux (RealTime Linux) |
| @@ -4167,6 +4187,10 @@ S: 1507 145th Place SE #B5 · 51 unmodified lines | |||
| 4167 | S: Bellevue, Washington 98007 | 4187 | S: Bellevue, Washington 98007 |
| 4168 | S: USA | 4188 | S: USA |
| 4169 | 4189 | ||
| 4190 | N: Wensong Zhang | ||
| 4191 | E: wensong@linux-vs.org | ||
| 4192 | D: IP virtual server (IPVS). | ||
| 4193 | |||
| 4170 | N: Haojian Zhuang | 4194 | N: Haojian Zhuang |
| 4171 | E: haojian.zhuang@gmail.com | 4195 | E: haojian.zhuang@gmail.com |
| 4172 | D: MMP support | 4196 | D: MMP support |
| @@ -5,8 +5,8 @@ Description: · 4 unmodified lines | |||
| 5 | Provide a place in sysfs for the device link objects in the | 5 | Provide a place in sysfs for the device link objects in the |
| 6 | kernel at any given time. The name of a device link directory, | 6 | kernel at any given time. The name of a device link directory, |
| 7 | denoted as ... above, is of the form <supplier>--<consumer> | 7 | denoted as ... above, is of the form <supplier>--<consumer> |
| 8 | where <supplier> is the supplier device name and <consumer> is | 8 | where <supplier> is the supplier bus:device name and <consumer> |
| 9 | the consumer device name. | 9 | is the consumer bus:device name. |
| 10 | 10 | ||
| 11 | What: /sys/class/devlink/.../auto_remove_on | 11 | What: /sys/class/devlink/.../auto_remove_on |
| 12 | Date: May 2020 | 12 | Date: May 2020 |
| @@ -4,5 +4,6 @@ Contact: Saravana Kannan <saravanak@google.com> · 3 unmodified lines | |||
| 4 | Description: | 4 | Description: |
| 5 | The /sys/devices/.../consumer:<consumer> are symlinks to device | 5 | The /sys/devices/.../consumer:<consumer> are symlinks to device |
| 6 | links where this device is the supplier. <consumer> denotes the | 6 | links where this device is the supplier. <consumer> denotes the |
| 7 | name of the consumer in that device link. There can be zero or | 7 | name of the consumer in that device link and is of the form |
| 8 | more of these symlinks for a given device. | 8 | bus:device name. There can be zero or more of these symlinks |
| 9 | for a given device. | ||
| @@ -4,5 +4,6 @@ Contact: Saravana Kannan <saravanak@google.com> · 3 unmodified lines | |||
| 4 | Description: | 4 | Description: |
| 5 | The /sys/devices/.../supplier:<supplier> are symlinks to device | 5 | The /sys/devices/.../supplier:<supplier> are symlinks to device |
| 6 | links where this device is the consumer. <supplier> denotes the | 6 | links where this device is the consumer. <supplier> denotes the |
| 7 | name of the supplier in that device link. There can be zero or | 7 | name of the supplier in that device link and is of the form |
| 8 | more of these symlinks for a given device. | 8 | bus:device name. There can be zero or more of these symlinks |
| 9 | for a given device. | ||
| @@ -916,21 +916,25 @@ Date: September 2014 · 915 unmodified lines | |||
| 916 | Contact: Subhash Jadavani <subhashj@codeaurora.org> | 916 | Contact: Subhash Jadavani <subhashj@codeaurora.org> |
| 917 | Description: This entry could be used to set or show the UFS device | 917 | Description: This entry could be used to set or show the UFS device |
| 918 | runtime power management level. The current driver | 918 | runtime power management level. The current driver |
| 919 | implementation supports 6 levels with next target states: | 919 | implementation supports 7 levels with next target states: |
| 920 | 920 | ||
| 921 | == ==================================================== | 921 | == ==================================================== |
| 922 | 0 an UFS device will stay active, an UIC link will | 922 | 0 UFS device will stay active, UIC link will |
| 923 | stay active | 923 | stay active |
| 924 | 1 an UFS device will stay active, an UIC link will | 924 | 1 UFS device will stay active, UIC link will |
| 925 | hibernate | 925 | hibernate |
| 926 | 2 an UFS device will moved to sleep, an UIC link will | 926 | 2 UFS device will be moved to sleep, UIC link will |
| 927 | stay active | 927 | stay active |
| 928 | 3 an UFS device will moved to sleep, an UIC link will | 928 | 3 UFS device will be moved to sleep, UIC link will |
| 929 | hibernate | 929 | hibernate |
| 930 | 4 an UFS device will be powered off, an UIC link will | 930 | 4 UFS device will be powered off, UIC link will |
| 931 | hibernate | 931 | hibernate |
| 932 | 5 an UFS device will be powered off, an UIC link will | 932 | 5 UFS device will be powered off, UIC link will |
| 933 | be powered off | 933 | be powered off |
| 934 | 6 UFS device will be moved to deep sleep, UIC link | ||
| 935 | will be powered off. Note, deep sleep might not be | ||
| 936 | supported in which case this value will not be | ||
| 937 | accepted | ||
| 934 | == ==================================================== | 938 | == ==================================================== |
| 935 | 939 | ||
| 936 | What: /sys/bus/platform/drivers/ufshcd/*/rpm_target_dev_state | 940 | What: /sys/bus/platform/drivers/ufshcd/*/rpm_target_dev_state |
| @@ -954,21 +958,25 @@ Date: September 2014 · 17 unmodified lines | |||
| 954 | Contact: Subhash Jadavani <subhashj@codeaurora.org> | 958 | Contact: Subhash Jadavani <subhashj@codeaurora.org> |
| 955 | Description: This entry could be used to set or show the UFS device | 959 | Description: This entry could be used to set or show the UFS device |
| 956 | system power management level. The current driver | 960 | system power management level. The current driver |
| 957 | implementation supports 6 levels with next target states: | 961 | implementation supports 7 levels with next target states: |
| 958 | 962 | ||
| 959 | == ==================================================== | 963 | == ==================================================== |
| 960 | 0 an UFS device will stay active, an UIC link will | 964 | 0 UFS device will stay active, UIC link will |
| 961 | stay active | 965 | stay active |
| 962 | 1 an UFS device will stay active, an UIC link will | 966 | 1 UFS device will stay active, UIC link will |
| 963 | hibernate | 967 | hibernate |
| 964 | 2 an UFS device will moved to sleep, an UIC link will | 968 | 2 UFS device will be moved to sleep, UIC link will |
| 965 | stay active | 969 | stay active |
| 966 | 3 an UFS device will moved to sleep, an UIC link will | 970 | 3 UFS device will be moved to sleep, UIC link will |
| 967 | hibernate | 971 | hibernate |
| 968 | 4 an UFS device will be powered off, an UIC link will | 972 | 4 UFS device will be powered off, UIC link will |
| 969 | hibernate | 973 | hibernate |
| 970 | 5 an UFS device will be powered off, an UIC link will | 974 | 5 UFS device will be powered off, UIC link will |
| 971 | be powered off | 975 | be powered off |
| 976 | 6 UFS device will be moved to deep sleep, UIC link | ||
| 977 | will be powered off. Note, deep sleep might not be | ||
| 978 | supported in which case this value will not be | ||
| 979 | accepted | ||
| 972 | == ==================================================== | 980 | == ==================================================== |
| 973 | 981 | ||
| 974 | What: /sys/bus/platform/drivers/ufshcd/*/spm_target_dev_state | 982 | What: /sys/bus/platform/drivers/ufshcd/*/spm_target_dev_state |
| @@ -75,7 +75,7 @@ quiet_cmd_sphinx = SPHINX $@ --> file://$(abspath $(BUILDDIR)/$3/$4) · 74 unmodified lines | |||
| 75 | cmd_sphinx = $(MAKE) BUILDDIR=$(abspath $(BUILDDIR)) $(build)=Documentation/userspace-api/media $2 && \ | 75 | cmd_sphinx = $(MAKE) BUILDDIR=$(abspath $(BUILDDIR)) $(build)=Documentation/userspace-api/media $2 && \ |
| 76 | PYTHONDONTWRITEBYTECODE=1 \ | 76 | PYTHONDONTWRITEBYTECODE=1 \ |
| 77 | BUILDDIR=$(abspath $(BUILDDIR)) SPHINX_CONF=$(abspath $(srctree)/$(src)/$5/$(SPHINX_CONF)) \ | 77 | BUILDDIR=$(abspath $(BUILDDIR)) SPHINX_CONF=$(abspath $(srctree)/$(src)/$5/$(SPHINX_CONF)) \ |
| 78 | $(PYTHON) $(srctree)/scripts/jobserver-exec \ | 78 | $(PYTHON3) $(srctree)/scripts/jobserver-exec \ |
| 79 | $(SHELL) $(srctree)/Documentation/sphinx/parallel-wrapper.sh \ | 79 | $(SHELL) $(srctree)/Documentation/sphinx/parallel-wrapper.sh \ |
| 80 | $(SPHINXBUILD) \ | 80 | $(SPHINXBUILD) \ |
| 81 | -b $2 \ | 81 | -b $2 \ |
| @@ -473,7 +473,7 @@ read-side critical sections that follow the idle period (the oval near · 472 unmodified lines | |||
| 473 | the bottom of the diagram above). | 473 | the bottom of the diagram above). |
| 474 | 474 | ||
| 475 | Plumbing this into the full grace-period execution is described | 475 | Plumbing this into the full grace-period execution is described |
| 476 | `below <#Forcing%20Quiescent%20States>`__. | 476 | `below <Forcing Quiescent States_>`__. |
| 477 | 477 | ||
| 478 | CPU-Hotplug Interface | 478 | CPU-Hotplug Interface |
| 479 | ^^^^^^^^^^^^^^^^^^^^^ | 479 | ^^^^^^^^^^^^^^^^^^^^^ |
| @@ -494,7 +494,7 @@ mask to detect CPUs having gone offline since the beginning of this · 14 unmodified lines | |||
| 494 | grace period. | 494 | grace period. |
| 495 | 495 | ||
| 496 | Plumbing this into the full grace-period execution is described | 496 | Plumbing this into the full grace-period execution is described |
| 497 | `below <#Forcing%20Quiescent%20States>`__. | 497 | `below <Forcing Quiescent States_>`__. |
| 498 | 498 | ||
| 499 | Forcing Quiescent States | 499 | Forcing Quiescent States |
| 500 | ^^^^^^^^^^^^^^^^^^^^^^^^ | 500 | ^^^^^^^^^^^^^^^^^^^^^^^^ |
| @@ -532,7 +532,7 @@ from other CPUs. · 31 unmodified lines | |||
| 532 | | RCU. But this diagram is complex enough as it is, so simplicity | | 532 | | RCU. But this diagram is complex enough as it is, so simplicity | |
| 533 | | overrode accuracy. You can think of it as poetic license, or you can | | 533 | | overrode accuracy. You can think of it as poetic license, or you can | |
| 534 | | think of it as misdirection that is resolved in the | | 534 | | think of it as misdirection that is resolved in the | |
| 535 | | `stitched-together diagram <#Putting%20It%20All%20Together>`__. | | 535 | | `stitched-together diagram <Putting It All Together_>`__. | |
| 536 | +-----------------------------------------------------------------------+ | 536 | +-----------------------------------------------------------------------+ |
| 537 | 537 | ||
| 538 | Grace-Period Cleanup | 538 | Grace-Period Cleanup |
| @@ -596,7 +596,7 @@ maintain ordering. For example, if the callback function wakes up a task · 57 unmodified lines | |||
| 596 | that runs on some other CPU, proper ordering must in place in both the | 596 | that runs on some other CPU, proper ordering must in place in both the |
| 597 | callback function and the task being awakened. To see why this is | 597 | callback function and the task being awakened. To see why this is |
| 598 | important, consider the top half of the `grace-period | 598 | important, consider the top half of the `grace-period |
| 599 | cleanup <#Grace-Period%20Cleanup>`__ diagram. The callback might be | 599 | cleanup`_ diagram. The callback might be |
| 600 | running on a CPU corresponding to the leftmost leaf ``rcu_node`` | 600 | running on a CPU corresponding to the leftmost leaf ``rcu_node`` |
| 601 | structure, and awaken a task that is to run on a CPU corresponding to | 601 | structure, and awaken a task that is to run on a CPU corresponding to |
| 602 | the rightmost leaf ``rcu_node`` structure, and the grace-period kernel | 602 | the rightmost leaf ``rcu_node`` structure, and the grace-period kernel |
| @@ -45,7 +45,7 @@ requirements: · 44 unmodified lines | |||
| 45 | #. `Other RCU Flavors`_ | 45 | #. `Other RCU Flavors`_ |
| 46 | #. `Possible Future Changes`_ | 46 | #. `Possible Future Changes`_ |
| 47 | 47 | ||
| 48 | This is followed by a `summary <#Summary>`__, however, the answers to | 48 | This is followed by a summary_, however, the answers to |
| 49 | each quick quiz immediately follows the quiz. Select the big white space | 49 | each quick quiz immediately follows the quiz. Select the big white space |
| 50 | with your mouse to see the answer. | 50 | with your mouse to see the answer. |
| 51 | 51 | ||
| @@ -1096,7 +1096,7 @@ memory barriers. · 1044 unmodified lines | |||
| 1096 | | case, voluntary context switch) within an RCU read-side critical | | 1096 | | case, voluntary context switch) within an RCU read-side critical | |
| 1097 | | section. However, sleeping locks may be used within userspace RCU | | 1097 | | section. However, sleeping locks may be used within userspace RCU | |
| 1098 | | read-side critical sections, and also within Linux-kernel sleepable | | 1098 | | read-side critical sections, and also within Linux-kernel sleepable | |
| 1099 | | RCU `(SRCU) <#Sleepable%20RCU>`__ read-side critical sections. In | | 1099 | | RCU `(SRCU) <Sleepable RCU_>`__ read-side critical sections. In | |
| 1100 | | addition, the -rt patchset turns spinlocks into a sleeping locks so | | 1100 | | addition, the -rt patchset turns spinlocks into a sleeping locks so | |
| 1101 | | that the corresponding critical sections can be preempted, which also | | 1101 | | that the corresponding critical sections can be preempted, which also | |
| 1102 | | means that these sleeplockified spinlocks (but not other sleeping | | 1102 | | means that these sleeplockified spinlocks (but not other sleeping | |
| @@ -1186,7 +1186,7 @@ non-preemptible (``CONFIG_PREEMPT=n``) kernels, and thus `tiny · 83 unmodified lines | |||
| 1186 | RCU <https://lkml.kernel.org/g/20090113221724.GA15307@linux.vnet.ibm.com>`__ | 1186 | RCU <https://lkml.kernel.org/g/20090113221724.GA15307@linux.vnet.ibm.com>`__ |
| 1187 | was born. Josh Triplett has since taken over the small-memory banner | 1187 | was born. Josh Triplett has since taken over the small-memory banner |
| 1188 | with his `Linux kernel tinification <https://tiny.wiki.kernel.org/>`__ | 1188 | with his `Linux kernel tinification <https://tiny.wiki.kernel.org/>`__ |
| 1189 | project, which resulted in `SRCU <#Sleepable%20RCU>`__ becoming optional | 1189 | project, which resulted in `SRCU <Sleepable RCU_>`__ becoming optional |
| 1190 | for those kernels not needing it. | 1190 | for those kernels not needing it. |
| 1191 | 1191 | ||
| 1192 | The remaining performance requirements are, for the most part, | 1192 | The remaining performance requirements are, for the most part, |
| @@ -1457,8 +1457,8 @@ will vary as the value of ``HZ`` varies, and can also be changed using · 264 unmodified lines | |||
| 1457 | the relevant Kconfig options and kernel boot parameters. RCU currently | 1457 | the relevant Kconfig options and kernel boot parameters. RCU currently |
| 1458 | does not do much sanity checking of these parameters, so please use | 1458 | does not do much sanity checking of these parameters, so please use |
| 1459 | caution when changing them. Note that these forward-progress measures | 1459 | caution when changing them. Note that these forward-progress measures |
| 1460 | are provided only for RCU, not for `SRCU <#Sleepable%20RCU>`__ or `Tasks | 1460 | are provided only for RCU, not for `SRCU <Sleepable RCU_>`__ or `Tasks |
| 1461 | RCU <#Tasks%20RCU>`__. | 1461 | RCU`_. |
| 1462 | 1462 | ||
| 1463 | RCU takes the following steps in ``call_rcu()`` to encourage timely | 1463 | RCU takes the following steps in ``call_rcu()`` to encourage timely |
| 1464 | invocation of callbacks when any given non-\ ``rcu_nocbs`` CPU has | 1464 | invocation of callbacks when any given non-\ ``rcu_nocbs`` CPU has |
| @@ -1477,8 +1477,8 @@ encouragement was provided: · 12 unmodified lines | |||
| 1477 | 1477 | ||
| 1478 | Again, these are default values when running at ``HZ=1000``, and can be | 1478 | Again, these are default values when running at ``HZ=1000``, and can be |
| 1479 | overridden. Again, these forward-progress measures are provided only for | 1479 | overridden. Again, these forward-progress measures are provided only for |
| 1480 | RCU, not for `SRCU <#Sleepable%20RCU>`__ or `Tasks | 1480 | RCU, not for `SRCU <Sleepable RCU_>`__ or `Tasks |
| 1481 | RCU <#Tasks%20RCU>`__. Even for RCU, callback-invocation forward | 1481 | RCU`_. Even for RCU, callback-invocation forward |
| 1482 | progress for ``rcu_nocbs`` CPUs is much less well-developed, in part | 1482 | progress for ``rcu_nocbs`` CPUs is much less well-developed, in part |
| 1483 | because workloads benefiting from ``rcu_nocbs`` CPUs tend to invoke | 1483 | because workloads benefiting from ``rcu_nocbs`` CPUs tend to invoke |
| 1484 | ``call_rcu()`` relatively infrequently. If workloads emerge that need | 1484 | ``call_rcu()`` relatively infrequently. If workloads emerge that need |
| @@ -1920,7 +1920,7 @@ Hotplug CPU · 435 unmodified lines | |||
| 1920 | 1920 | ||
| 1921 | The Linux kernel supports CPU hotplug, which means that CPUs can come | 1921 | The Linux kernel supports CPU hotplug, which means that CPUs can come |
| 1922 | and go. It is of course illegal to use any RCU API member from an | 1922 | and go. It is of course illegal to use any RCU API member from an |
| 1923 | offline CPU, with the exception of `SRCU <#Sleepable%20RCU>`__ read-side | 1923 | offline CPU, with the exception of `SRCU <Sleepable RCU_>`__ read-side |
| 1924 | critical sections. This requirement was present from day one in | 1924 | critical sections. This requirement was present from day one in |
| 1925 | DYNIX/ptx, but on the other hand, the Linux kernel's CPU-hotplug | 1925 | DYNIX/ptx, but on the other hand, the Linux kernel's CPU-hotplug |
| 1926 | implementation is “interesting.” | 1926 | implementation is “interesting.” |
| @@ -2177,7 +2177,7 @@ handles these states differently: · 250 unmodified lines | |||
| 2177 | However, RCU must be reliably informed as to whether any given CPU is | 2177 | However, RCU must be reliably informed as to whether any given CPU is |
| 2178 | currently in the idle loop, and, for ``NO_HZ_FULL``, also whether that | 2178 | currently in the idle loop, and, for ``NO_HZ_FULL``, also whether that |
| 2179 | CPU is executing in usermode, as discussed | 2179 | CPU is executing in usermode, as discussed |
| 2180 | `earlier <#Energy%20Efficiency>`__. It also requires that the | 2180 | `earlier <Energy Efficiency_>`__. It also requires that the |
| 2181 | scheduling-clock interrupt be enabled when RCU needs it to be: | 2181 | scheduling-clock interrupt be enabled when RCU needs it to be: |
| 2182 | 2182 | ||
| 2183 | #. If a CPU is either idle or executing in usermode, and RCU believes it | 2183 | #. If a CPU is either idle or executing in usermode, and RCU believes it |
| @@ -2294,7 +2294,7 @@ Performance, Scalability, Response Time, and Reliability · 110 unmodified lines | |||
| 2294 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | 2294 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 2295 | 2295 | ||
| 2296 | Expanding on the `earlier | 2296 | Expanding on the `earlier |
| 2297 | discussion <#Performance%20and%20Scalability>`__, RCU is used heavily by | 2297 | discussion <Performance and Scalability_>`__, RCU is used heavily by |
| 2298 | hot code paths in performance-critical portions of the Linux kernel's | 2298 | hot code paths in performance-critical portions of the Linux kernel's |
| 2299 | networking, security, virtualization, and scheduling code paths. RCU | 2299 | networking, security, virtualization, and scheduling code paths. RCU |
| 2300 | must therefore use efficient implementations, especially in its | 2300 | must therefore use efficient implementations, especially in its |
| @@ -23,7 +23,7 @@ Here is what the fields mean: · 22 unmodified lines | |||
| 23 | 23 | ||
| 24 | - ``name`` | 24 | - ``name`` |
| 25 | is an identifier string. A new /proc file will be created with this | 25 | is an identifier string. A new /proc file will be created with this |
| 26 | ``name below /proc/sys/fs/binfmt_misc``; cannot contain slashes ``/`` for | 26 | name below ``/proc/sys/fs/binfmt_misc``; cannot contain slashes ``/`` for |
| 27 | obvious reasons. | 27 | obvious reasons. |
| 28 | - ``type`` | 28 | - ``type`` |
| 29 | is the type of recognition. Give ``M`` for magic and ``E`` for extension. | 29 | is the type of recognition. Give ``M`` for magic and ``E`` for extension. |
| @@ -83,7 +83,7 @@ Here is what the fields mean: · 53 unmodified lines | |||
| 83 | ``F`` - fix binary | 83 | ``F`` - fix binary |
| 84 | The usual behaviour of binfmt_misc is to spawn the | 84 | The usual behaviour of binfmt_misc is to spawn the |
| 85 | binary lazily when the misc format file is invoked. However, | 85 | binary lazily when the misc format file is invoked. However, |
| 86 | this doesn``t work very well in the face of mount namespaces and | 86 | this doesn't work very well in the face of mount namespaces and |
| 87 | changeroots, so the ``F`` mode opens the binary as soon as the | 87 | changeroots, so the ``F`` mode opens the binary as soon as the |
| 88 | emulation is installed and uses the opened image to spawn the | 88 | emulation is installed and uses the opened image to spawn the |
| 89 | emulator, meaning it is always available once installed, | 89 | emulator, meaning it is always available once installed, |
| @@ -154,7 +154,7 @@ get the boot configuration data. · 153 unmodified lines | |||
| 154 | Because of this "piggyback" method, there is no need to change or | 154 | Because of this "piggyback" method, there is no need to change or |
| 155 | update the boot loader and the kernel image itself as long as the boot | 155 | update the boot loader and the kernel image itself as long as the boot |
| 156 | loader passes the correct initrd file size. If by any chance, the boot | 156 | loader passes the correct initrd file size. If by any chance, the boot |
| 157 | loader passes a longer size, the kernel feils to find the bootconfig data. | 157 | loader passes a longer size, the kernel fails to find the bootconfig data. |
| 158 | 158 | ||
| 159 | To do this operation, Linux kernel provides "bootconfig" command under | 159 | To do this operation, Linux kernel provides "bootconfig" command under |
| 160 | tools/bootconfig, which allows admin to apply or delete the config file | 160 | tools/bootconfig, which allows admin to apply or delete the config file |
| @@ -1029,7 +1029,7 @@ All time durations are in microseconds. · 1028 unmodified lines | |||
| 1029 | one number is written, $MAX is updated. | 1029 | one number is written, $MAX is updated. |
| 1030 | 1030 | ||
| 1031 | cpu.pressure | 1031 | cpu.pressure |
| 1032 | A read-only nested-key file which exists on non-root cgroups. | 1032 | A read-write nested-keyed file. |
| 1033 | 1033 | ||
| 1034 | Shows pressure stall information for CPU. See | 1034 | Shows pressure stall information for CPU. See |
| 1035 | :ref:`Documentation/accounting/psi.rst <psi>` for details. | 1035 | :ref:`Documentation/accounting/psi.rst <psi>` for details. |
| @@ -1475,7 +1475,7 @@ PAGE_SIZE multiple when read back. · 439 unmodified lines | |||
| 1475 | reduces the impact on the workload and memory management. | 1475 | reduces the impact on the workload and memory management. |
| 1476 | 1476 | ||
| 1477 | memory.pressure | 1477 | memory.pressure |
| 1478 | A read-only nested-key file which exists on non-root cgroups. | 1478 | A read-only nested-keyed file. |
| 1479 | 1479 | ||
| 1480 | Shows pressure stall information for memory. See | 1480 | Shows pressure stall information for memory. See |
| 1481 | :ref:`Documentation/accounting/psi.rst <psi>` for details. | 1481 | :ref:`Documentation/accounting/psi.rst <psi>` for details. |
| @@ -1714,7 +1714,7 @@ IO Interface Files · 232 unmodified lines | |||
| 1714 | 8:16 rbps=2097152 wbps=max riops=max wiops=max | 1714 | 8:16 rbps=2097152 wbps=max riops=max wiops=max |
| 1715 | 1715 | ||
| 1716 | io.pressure | 1716 | io.pressure |
| 1717 | A read-only nested-key file which exists on non-root cgroups. | 1717 | A read-only nested-keyed file. |
| 1718 | 1718 | ||
| 1719 | Shows pressure stall information for IO. See | 1719 | Shows pressure stall information for IO. See |
| 1720 | :ref:`Documentation/accounting/psi.rst <psi>` for details. | 1720 | :ref:`Documentation/accounting/psi.rst <psi>` for details. |
| @@ -177,14 +177,20 @@ bitmap_flush_interval:number · 176 unmodified lines | |||
| 177 | The bitmap flush interval in milliseconds. The metadata buffers | 177 | The bitmap flush interval in milliseconds. The metadata buffers |
| 178 | are synchronized when this interval expires. | 178 | are synchronized when this interval expires. |
| 179 | 179 | ||
| 180 | allow_discards | ||
| 181 | Allow block discard requests (a.k.a. TRIM) for the integrity device. | ||
| 182 | Discards are only allowed to devices using internal hash. | ||
| 183 | |||
| 180 | fix_padding | 184 | fix_padding |
| 181 | Use a smaller padding of the tag area that is more | 185 | Use a smaller padding of the tag area that is more |
| 182 | space-efficient. If this option is not present, large padding is | 186 | space-efficient. If this option is not present, large padding is |
| 183 | used - that is for compatibility with older kernels. | 187 | used - that is for compatibility with older kernels. |
| 184 | 188 | ||
| 185 | allow_discards | 189 | legacy_recalculate |
| 186 | Allow block discard requests (a.k.a. TRIM) for the integrity device. | 190 | Allow recalculating of volumes with HMAC keys. This is disabled by |
| 187 | Discards are only allowed to devices using internal hash. | 191 | default for security reasons - an attacker could modify the volume, |
| 192 | set recalc_sector to zero, and the kernel would not detect the | ||
| 193 | modification. | ||
| 188 | 194 | ||
| 189 | The journal mode (D/J), buffer_sectors, journal_watermark, commit_time and | 195 | The journal mode (D/J), buffer_sectors, journal_watermark, commit_time and |
| 190 | allow_discards can be changed when reloading the target (load an inactive | 196 | allow_discards can be changed when reloading the target (load an inactive |
| @@ -3,8 +3,8 @@ · 2 unmodified lines | |||
| 3 | The kernel's command-line parameters | 3 | The kernel's command-line parameters |
| 4 | ==================================== | 4 | ==================================== |
| 5 | 5 | ||
| 6 | The following is a consolidated list of the kernel parameters as | 6 | The following is a consolidated list of the kernel parameters as implemented |
| 7 | implemented by the __setup(), core_param() and module_param() macros | 7 | by the __setup(), early_param(), core_param() and module_param() macros |
| 8 | and sorted into English Dictionary order (defined as ignoring all | 8 | and sorted into English Dictionary order (defined as ignoring all |
| 9 | punctuation and sorting digits before letters in a case insensitive | 9 | punctuation and sorting digits before letters in a case insensitive |
| 10 | manner), and with descriptions where known. | 10 | manner), and with descriptions where known. |
| @@ -1385,7 +1385,7 @@ · 1384 unmodified lines | |||
| 1385 | 1385 | ||
| 1386 | ftrace_filter=[function-list] | 1386 | ftrace_filter=[function-list] |
| 1387 | [FTRACE] Limit the functions traced by the function | 1387 | [FTRACE] Limit the functions traced by the function |
| 1388 | tracer at boot up. function-list is a comma separated | 1388 | tracer at boot up. function-list is a comma-separated |
| 1389 | list of functions. This list can be changed at run | 1389 | list of functions. This list can be changed at run |
| 1390 | time by the set_ftrace_filter file in the debugfs | 1390 | time by the set_ftrace_filter file in the debugfs |
| 1391 | tracing directory. | 1391 | tracing directory. |
| @@ -1399,13 +1399,13 @@ · 7 unmodified lines | |||
| 1399 | ftrace_graph_filter=[function-list] | 1399 | ftrace_graph_filter=[function-list] |
| 1400 | [FTRACE] Limit the top level callers functions traced | 1400 | [FTRACE] Limit the top level callers functions traced |
| 1401 | by the function graph tracer at boot up. | 1401 | by the function graph tracer at boot up. |
| 1402 | function-list is a comma separated list of functions | 1402 | function-list is a comma-separated list of functions |
| 1403 | that can be changed at run time by the | 1403 | that can be changed at run time by the |
| 1404 | set_graph_function file in the debugfs tracing directory. | 1404 | set_graph_function file in the debugfs tracing directory. |
| 1405 | 1405 | ||
| 1406 | ftrace_graph_notrace=[function-list] | 1406 | ftrace_graph_notrace=[function-list] |
| 1407 | [FTRACE] Do not trace from the functions specified in | 1407 | [FTRACE] Do not trace from the functions specified in |
| 1408 | function-list. This list is a comma separated list of | 1408 | function-list. This list is a comma-separated list of |
| 1409 | functions that can be changed at run time by the | 1409 | functions that can be changed at run time by the |
| 1410 | set_graph_notrace file in the debugfs tracing directory. | 1410 | set_graph_notrace file in the debugfs tracing directory. |
| 1411 | 1411 | ||
| @@ -2421,7 +2421,7 @@ · 1009 unmodified lines | |||
| 2421 | when set. | 2421 | when set. |
| 2422 | Format: <int> | 2422 | Format: <int> |
| 2423 | 2423 | ||
| 2424 | libata.force= [LIBATA] Force configurations. The format is comma | 2424 | libata.force= [LIBATA] Force configurations. The format is comma- |
| 2425 | separated list of "[ID:]VAL" where ID is | 2425 | separated list of "[ID:]VAL" where ID is |
| 2426 | PORT[.DEVICE]. PORT and DEVICE are decimal numbers | 2426 | PORT[.DEVICE]. PORT and DEVICE are decimal numbers |
| 2427 | matching port, link or device. Basically, it matches | 2427 | matching port, link or device. Basically, it matches |
| @@ -5145,7 +5145,7 @@ · 2717 unmodified lines | |||
| 5145 | 5145 | ||
| 5146 | stacktrace_filter=[function-list] | 5146 | stacktrace_filter=[function-list] |
| 5147 | [FTRACE] Limit the functions that the stack tracer | 5147 | [FTRACE] Limit the functions that the stack tracer |
| 5148 | will trace at boot up. function-list is a comma separated | 5148 | will trace at boot up. function-list is a comma-separated |
| 5149 | list of functions. This list can be changed at run | 5149 | list of functions. This list can be changed at run |
| 5150 | time by the stack_trace_filter file in the debugfs | 5150 | time by the stack_trace_filter file in the debugfs |
| 5151 | tracing directory. Note, this enables stack tracing | 5151 | tracing directory. Note, this enables stack tracing |
| @@ -5348,7 +5348,7 @@ · 196 unmodified lines | |||
| 5348 | trace_event=[event-list] | 5348 | trace_event=[event-list] |
| 5349 | [FTRACE] Set and start specified trace events in order | 5349 | [FTRACE] Set and start specified trace events in order |
| 5350 | to facilitate early boot debugging. The event-list is a | 5350 | to facilitate early boot debugging. The event-list is a |
| 5351 | comma separated list of trace events to enable. See | 5351 | comma-separated list of trace events to enable. See |
| 5352 | also Documentation/trace/events.rst | 5352 | also Documentation/trace/events.rst |
| 5353 | 5353 | ||
| 5354 | trace_options=[option-list] | 5354 | trace_options=[option-list] |
| @@ -5972,6 +5972,10 @@ · 617 unmodified lines | |||
| 5972 | This option is obsoleted by the "nopv" option, which | 5972 | This option is obsoleted by the "nopv" option, which |
| 5973 | has equivalent effect for XEN platform. | 5973 | has equivalent effect for XEN platform. |
| 5974 | 5974 | ||
| 5975 | xen_no_vector_callback | ||
| 5976 | [KNL,X86,XEN] Disable the vector callback for Xen | ||
| 5977 | event channel interrupts. | ||
| 5978 | |||
| 5975 | xen_scrub_pages= [XEN] | 5979 | xen_scrub_pages= [XEN] |
| 5976 | Boolean option to control scrubbing pages before giving them back | 5980 | Boolean option to control scrubbing pages before giving them back |
| 5977 | to Xen, for use by other domains. Can be also changed at runtime | 5981 | to Xen, for use by other domains. Can be also changed at runtime |
| @@ -13,6 +13,22 @@ This file documents the driver for the Rockchip ISP1 that is part of RK3288 · 12 unmodified lines | |||
| 13 | and RK3399 SoCs. The driver is located under drivers/staging/media/rkisp1 | 13 | and RK3399 SoCs. The driver is located under drivers/staging/media/rkisp1 |
| 14 | and uses the Media-Controller API. | 14 | and uses the Media-Controller API. |
| 15 | 15 | ||
| 16 | Revisions | ||
| 17 | ========= | ||
| 18 | |||
| 19 | There exist multiple smaller revisions to this ISP that got introduced in | ||
| 20 | later SoCs. Revisions can be found in the enum :c:type:`rkisp1_cif_isp_version` | ||
| 21 | in the UAPI and the revision of the ISP inside the running SoC can be read | ||
| 22 | in the field hw_revision of struct media_device_info as returned by | ||
| 23 | ioctl MEDIA_IOC_DEVICE_INFO. | ||
| 24 | |||
| 25 | Versions in use are: | ||
| 26 | |||
| 27 | - RKISP1_V10: used at least in rk3288 and rk3399 | ||
| 28 | - RKISP1_V11: declared in the original vendor code, but not used | ||
| 29 | - RKISP1_V12: used at least in rk3326 and px30 | ||
| 30 | - RKISP1_V13: used at least in rk1808 | ||
| 31 | |||
| 16 | Topology | 32 | Topology |
| 17 | ======== | 33 | ======== |
| 18 | .. _rkisp1_topology_graph: | 34 | .. _rkisp1_topology_graph: |
| @@ -184,7 +184,7 @@ pages either asynchronously or synchronously, depending on the state · 183 unmodified lines | |||
| 184 | of the system. When the system is not loaded, most of the memory is free | 184 | of the system. When the system is not loaded, most of the memory is free |
| 185 | and allocation requests will be satisfied immediately from the free | 185 | and allocation requests will be satisfied immediately from the free |
| 186 | pages supply. As the load increases, the amount of the free pages goes | 186 | pages supply. As the load increases, the amount of the free pages goes |
| 187 | down and when it reaches a certain threshold (high watermark), an | 187 | down and when it reaches a certain threshold (low watermark), an |
| 188 | allocation request will awaken the ``kswapd`` daemon. It will | 188 | allocation request will awaken the ``kswapd`` daemon. It will |
| 189 | asynchronously scan memory pages and either just free them if the data | 189 | asynchronously scan memory pages and either just free them if the data |
| 190 | they contain is available elsewhere, or evict to the backing storage | 190 | they contain is available elsewhere, or evict to the backing storage |
| @@ -70,8 +70,8 @@ trampoline code on the vDSO, that trampoline is never intercepted. · 69 unmodified lines | |||
| 70 | [selector] is a pointer to a char-sized region in the process memory | 70 | [selector] is a pointer to a char-sized region in the process memory |
| 71 | region, that provides a quick way to enable disable syscall redirection | 71 | region, that provides a quick way to enable disable syscall redirection |
| 72 | thread-wide, without the need to invoke the kernel directly. selector | 72 | thread-wide, without the need to invoke the kernel directly. selector |
| 73 | can be set to PR_SYS_DISPATCH_ON or PR_SYS_DISPATCH_OFF. Any other | 73 | can be set to SYSCALL_DISPATCH_FILTER_ALLOW or SYSCALL_DISPATCH_FILTER_BLOCK. |
| 74 | value should terminate the program with a SIGSYS. | 74 | Any other value should terminate the program with a SIGSYS. |
| 75 | 75 | ||
| 76 | Security Notes | 76 | Security Notes |
| 77 | -------------- | 77 | -------------- |
| @@ -100,6 +100,11 @@ Instruction Macros · 99 unmodified lines | |||
| 100 | ~~~~~~~~~~~~~~~~~~ | 100 | ~~~~~~~~~~~~~~~~~~ |
| 101 | This section covers ``SYM_FUNC_*`` and ``SYM_CODE_*`` enumerated above. | 101 | This section covers ``SYM_FUNC_*`` and ``SYM_CODE_*`` enumerated above. |
| 102 | 102 | ||
| 103 | ``objtool`` requires that all code must be contained in an ELF symbol. Symbol | ||
| 104 | names that have a ``.L`` prefix do not emit symbol table entries. ``.L`` | ||
| 105 | prefixed symbols can be used within a code region, but should be avoided for | ||
| 106 | denoting a range of code via ``SYM_*_START/END`` annotations. | ||
| 107 | |||
| 103 | * ``SYM_FUNC_START`` and ``SYM_FUNC_START_LOCAL`` are supposed to be **the | 108 | * ``SYM_FUNC_START`` and ``SYM_FUNC_START_LOCAL`` are supposed to be **the |
| 104 | most frequent markings**. They are used for functions with standard calling | 109 | most frequent markings**. They are used for functions with standard calling |
| 105 | conventions -- global and local. Like in C, they both align the functions to | 110 | conventions -- global and local. Like in C, they both align the functions to |
| @@ -53,7 +53,6 @@ How Linux keeps everything from happening at the same time. See · 52 unmodified lines | |||
| 53 | .. toctree:: | 53 | .. toctree:: |
| 54 | :maxdepth: 1 | 54 | :maxdepth: 1 |
| 55 | 55 | ||
| 56 | atomic_ops | ||
| 57 | refcount-vs-atomic | 56 | refcount-vs-atomic |
| 58 | irq/index | 57 | irq/index |
| 59 | local_ops | 58 | local_ops |
| @@ -160,29 +160,13 @@ intended for use in production as a security mitigation. Therefore it supports · 159 unmodified lines | |||
| 160 | boot parameters that allow to disable KASAN competely or otherwise control | 160 | boot parameters that allow to disable KASAN competely or otherwise control |
| 161 | particular KASAN features. | 161 | particular KASAN features. |
| 162 | 162 | ||
| 163 | The things that can be controlled are: | 163 | - ``kasan=off`` or ``=on`` controls whether KASAN is enabled (default: ``on``). |
| 164 | 164 | ||
| 165 | 1. Whether KASAN is enabled at all. | 165 | - ``kasan.stacktrace=off`` or ``=on`` disables or enables alloc and free stack |
| 166 | 2. Whether KASAN collects and saves alloc/free stacks. | 166 | traces collection (default: ``on``). |
| 167 | 3. Whether KASAN panics on a detected bug or not. | ||
| 168 | 167 | ||
| 169 | The ``kasan.mode`` boot parameter allows to choose one of three main modes: | 168 | - ``kasan.fault=report`` or ``=panic`` controls whether to only print a KASAN |
| 170 | 169 | report or also panic the kernel (default: ``report``). | |
| 171 | - ``kasan.mode=off`` - KASAN is disabled, no tag checks are performed | ||
| 172 | - ``kasan.mode=prod`` - only essential production features are enabled | ||
| 173 | - ``kasan.mode=full`` - all KASAN features are enabled | ||
| 174 | |||
| 175 | The chosen mode provides default control values for the features mentioned | ||
| 176 | above. However it's also possible to override the default values by providing: | ||
| 177 | |||
| 178 | - ``kasan.stacktrace=off`` or ``=on`` - enable alloc/free stack collection | ||
| 179 | (default: ``on`` for ``mode=full``, | ||
| 180 | otherwise ``off``) | ||
| 181 | - ``kasan.fault=report`` or ``=panic`` - only print KASAN report or also panic | ||
| 182 | (default: ``report``) | ||
| 183 | |||
| 184 | If ``kasan.mode`` parameter is not provided, it defaults to ``full`` when | ||
| 185 | ``CONFIG_DEBUG_KERNEL`` is enabled, and to ``prod`` otherwise. | ||
| 186 | 170 | ||
| 187 | For developers | 171 | For developers |
| 188 | ~~~~~~~~~~~~~~ | 172 | ~~~~~~~~~~~~~~ |
| @@ -522,6 +522,63 @@ There's more boilerplate involved, but it can: · 521 unmodified lines | |||
| 522 | * E.g. if we wanted to also test ``sha256sum``, we could add a ``sha256`` | 522 | * E.g. if we wanted to also test ``sha256sum``, we could add a ``sha256`` |
| 523 | field and reuse ``cases``. | 523 | field and reuse ``cases``. |
| 524 | 524 | ||
| 525 | * be converted to a "parameterized test", see below. | ||
| 526 | |||
| 527 | Parameterized Testing | ||
| 528 | ~~~~~~~~~~~~~~~~~~~~~ | ||
| 529 | |||
| 530 | The table-driven testing pattern is common enough that KUnit has special | ||
| 531 | support for it. | ||
| 532 | |||
| 533 | Reusing the same ``cases`` array from above, we can write the test as a | ||
| 534 | "parameterized test" with the following. | ||
| 535 | |||
| 536 | .. code-block:: c | ||
| 537 | |||
| 538 | // This is copy-pasted from above. | ||
| 539 | struct sha1_test_case { | ||
| 540 | const char *str; | ||
| 541 | const char *sha1; | ||
| 542 | }; | ||
| 543 | struct sha1_test_case cases[] = { | ||
| 544 | { | ||
| 545 | .str = "hello world", | ||
| 546 | .sha1 = "2aae6c35c94fcfb415dbe95f408b9ce91ee846ed", | ||
| 547 | }, | ||
| 548 | { | ||
| 549 | .str = "hello world!", | ||
| 550 | .sha1 = "430ce34d020724ed75a196dfc2ad67c77772d169", | ||
| 551 | }, | ||
| 552 | }; | ||
| 553 | |||
| 554 | // Need a helper function to generate a name for each test case. | ||
| 555 | static void case_to_desc(const struct sha1_test_case *t, char *desc) | ||
| 556 | { | ||
| 557 | strcpy(desc, t->str); | ||
| 558 | } | ||
| 559 | // Creates `sha1_gen_params()` to iterate over `cases`. | ||
| 560 | KUNIT_ARRAY_PARAM(sha1, cases, case_to_desc); | ||
| 561 | |||
| 562 | // Looks no different from a normal test. | ||
| 563 | static void sha1_test(struct kunit *test) | ||
| 564 | { | ||
| 565 | // This function can just contain the body of the for-loop. | ||
| 566 | // The former `cases[i]` is accessible under test->param_value. | ||
| 567 | char out[40]; | ||
| 568 | struct sha1_test_case *test_param = (struct sha1_test_case *)(test->param_value); | ||
| 569 | |||
| 570 | sha1sum(test_param->str, out); | ||
| 571 | KUNIT_EXPECT_STREQ_MSG(test, (char *)out, test_param->sha1, | ||
| 572 | "sha1sum(%s)", test_param->str); | ||
| 573 | } | ||
| 574 | |||
| 575 | // Instead of KUNIT_CASE, we use KUNIT_CASE_PARAM and pass in the | ||
| 576 | // function declared by KUNIT_ARRAY_PARAM. | ||
| 577 | static struct kunit_case sha1_test_cases[] = { | ||
| 578 | KUNIT_CASE_PARAM(sha1_test, sha1_gen_params), | ||
| 579 | {} | ||
| 580 | }; | ||
| 581 | |||
| 525 | .. _kunit-on-non-uml: | 582 | .. _kunit-on-non-uml: |
| 526 | 583 | ||
| 527 | KUnit on non-UML architectures | 584 | KUnit on non-UML architectures |
| @@ -232,7 +232,6 @@ properties: · 231 unmodified lines | |||
| 232 | by this cpu (see ./idle-states.yaml). | 232 | by this cpu (see ./idle-states.yaml). |
| 233 | 233 | ||
| 234 | capacity-dmips-mhz: | 234 | capacity-dmips-mhz: |
| 235 | $ref: '/schemas/types.yaml#/definitions/uint32' | ||
| 236 | description: | 235 | description: |
| 237 | u32 value representing CPU capacity (see ./cpu-capacity.txt) in | 236 | u32 value representing CPU capacity (see ./cpu-capacity.txt) in |
| 238 | DMIPS/MHz, relative to highest capacity-dmips-mhz | 237 | DMIPS/MHz, relative to highest capacity-dmips-mhz |
| @@ -40,7 +40,7 @@ Optional properties: · 39 unmodified lines | |||
| 40 | documents on how to describe the way the sii902x device is | 40 | documents on how to describe the way the sii902x device is |
| 41 | connected to the rest of the audio system: | 41 | connected to the rest of the audio system: |
| 42 | Documentation/devicetree/bindings/sound/simple-card.yaml | 42 | Documentation/devicetree/bindings/sound/simple-card.yaml |
| 43 | Documentation/devicetree/bindings/sound/audio-graph-card.txt | 43 | Documentation/devicetree/bindings/sound/audio-graph-card.yaml |
| 44 | Note: In case of the audio-graph-card binding the used port | 44 | Note: In case of the audio-graph-card binding the used port |
| 45 | index should be 3. | 45 | index should be 3. |
| 46 | 46 | ||
| @@ -23,7 +23,7 @@ connected to. · 22 unmodified lines | |||
| 23 | 23 | ||
| 24 | For a description of the display interface sink function blocks, see | 24 | For a description of the display interface sink function blocks, see |
| 25 | Documentation/devicetree/bindings/display/mediatek/mediatek,dsi.txt and | 25 | Documentation/devicetree/bindings/display/mediatek/mediatek,dsi.txt and |
| 26 | Documentation/devicetree/bindings/display/mediatek/mediatek,dpi.txt. | 26 | Documentation/devicetree/bindings/display/mediatek/mediatek,dpi.yaml. |
| 27 | 27 | ||
| 28 | Required properties (all function blocks): | 28 | Required properties (all function blocks): |
| 29 | - compatible: "mediatek,<chip>-disp-<function>", one of | 29 | - compatible: "mediatek,<chip>-disp-<function>", one of |
| @@ -61,7 +61,7 @@ Required properties (DMA function blocks): · 31 unmodified lines | |||
| 61 | "mediatek,<chip>-disp-wdma" | 61 | "mediatek,<chip>-disp-wdma" |
| 62 | the supported chips are mt2701, mt8167 and mt8173. | 62 | the supported chips are mt2701, mt8167 and mt8173. |
| 63 | - larb: Should contain a phandle pointing to the local arbiter device as defined | 63 | - larb: Should contain a phandle pointing to the local arbiter device as defined |
| 64 | in Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.txt | 64 | in Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.yaml |
| 65 | - iommus: Should point to the respective IOMMU block with master port as | 65 | - iommus: Should point to the respective IOMMU block with master port as |
| 66 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt | 66 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt |
| 67 | for details. | 67 | for details. |
| @@ -1,4 +1,6 @@ | |||
| 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) | 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) |
| 2 | # Copyright (C) 2020 Texas Instruments Incorporated | ||
| 3 | # Author: Peter Ujfalusi <peter.ujfalusi@ti.com> | ||
| 2 | %YAML 1.2 | 4 | %YAML 1.2 |
| 3 | --- | 5 | --- |
| 4 | $id: http://devicetree.org/schemas/dma/ti/k3-bcdma.yaml# | 6 | $id: http://devicetree.org/schemas/dma/ti/k3-bcdma.yaml# |
| @@ -7,7 +9,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml# · 2 unmodified lines | |||
| 7 | title: Texas Instruments K3 DMSS BCDMA Device Tree Bindings | 9 | title: Texas Instruments K3 DMSS BCDMA Device Tree Bindings |
| 8 | 10 | ||
| 9 | maintainers: | 11 | maintainers: |
| 10 | - Peter Ujfalusi <peter.ujfalusi@ti.com> | 12 | - Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 11 | 13 | ||
| 12 | description: | | 14 | description: | |
| 13 | The Block Copy DMA (BCDMA) is intended to perform similar functions as the TR | 15 | The Block Copy DMA (BCDMA) is intended to perform similar functions as the TR |
| @@ -1,4 +1,6 @@ | |||
| 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) | 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) |
| 2 | # Copyright (C) 2020 Texas Instruments Incorporated | ||
| 3 | # Author: Peter Ujfalusi <peter.ujfalusi@ti.com> | ||
| 2 | %YAML 1.2 | 4 | %YAML 1.2 |
| 3 | --- | 5 | --- |
| 4 | $id: http://devicetree.org/schemas/dma/ti/k3-pktdma.yaml# | 6 | $id: http://devicetree.org/schemas/dma/ti/k3-pktdma.yaml# |
| @@ -7,7 +9,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml# · 2 unmodified lines | |||
| 7 | title: Texas Instruments K3 DMSS PKTDMA Device Tree Bindings | 9 | title: Texas Instruments K3 DMSS PKTDMA Device Tree Bindings |
| 8 | 10 | ||
| 9 | maintainers: | 11 | maintainers: |
| 10 | - Peter Ujfalusi <peter.ujfalusi@ti.com> | 12 | - Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 11 | 13 | ||
| 12 | description: | | 14 | description: | |
| 13 | The Packet DMA (PKTDMA) is intended to perform similar functions as the packet | 15 | The Packet DMA (PKTDMA) is intended to perform similar functions as the packet |
| @@ -1,4 +1,6 @@ | |||
| 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) | 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) |
| 2 | # Copyright (C) 2019 Texas Instruments Incorporated | ||
| 3 | # Author: Peter Ujfalusi <peter.ujfalusi@ti.com> | ||
| 2 | %YAML 1.2 | 4 | %YAML 1.2 |
| 3 | --- | 5 | --- |
| 4 | $id: http://devicetree.org/schemas/dma/ti/k3-udma.yaml# | 6 | $id: http://devicetree.org/schemas/dma/ti/k3-udma.yaml# |
| @@ -7,7 +9,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml# · 2 unmodified lines | |||
| 7 | title: Texas Instruments K3 NAVSS Unified DMA Device Tree Bindings | 9 | title: Texas Instruments K3 NAVSS Unified DMA Device Tree Bindings |
| 8 | 10 | ||
| 9 | maintainers: | 11 | maintainers: |
| 10 | - Peter Ujfalusi <peter.ujfalusi@ti.com> | 12 | - Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 11 | 13 | ||
| 12 | description: | | 14 | description: | |
| 13 | The UDMA-P is intended to perform similar (but significantly upgraded) | 15 | The UDMA-P is intended to perform similar (but significantly upgraded) |
| @@ -85,7 +85,6 @@ properties: · 84 unmodified lines | |||
| 85 | wlf,micd-timeout-ms: | 85 | wlf,micd-timeout-ms: |
| 86 | description: | 86 | description: |
| 87 | Timeout for microphone detection, specified in milliseconds. | 87 | Timeout for microphone detection, specified in milliseconds. |
| 88 | $ref: "/schemas/types.yaml#/definitions/uint32" | ||
| 89 | 88 | ||
| 90 | wlf,micd-force-micbias: | 89 | wlf,micd-force-micbias: |
| 91 | description: | 90 | description: |
| @@ -49,7 +49,6 @@ properties: · 48 unmodified lines | |||
| 49 | description: | 49 | description: |
| 50 | This property controls the Accumulation Dead band which allows to set the | 50 | This property controls the Accumulation Dead band which allows to set the |
| 51 | level of current below which no accumulation takes place. | 51 | level of current below which no accumulation takes place. |
| 52 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 53 | maximum: 255 | 52 | maximum: 255 |
| 54 | default: 0 | 53 | default: 0 |
| 55 | 54 | ||
| @@ -73,11 +73,9 @@ properties: · 72 unmodified lines | |||
| 73 | description: | | 73 | description: | |
| 74 | Temperature sensor trimming factor. It can be used to manually adjust the | 74 | Temperature sensor trimming factor. It can be used to manually adjust the |
| 75 | temperature measurements within 7.130 degrees Celsius. | 75 | temperature measurements within 7.130 degrees Celsius. |
| 76 | maxItems: 1 | 76 | default: 0 |
| 77 | items: | 77 | minimum: 0 |
| 78 | default: 0 | 78 | maximum: 7130 |
| 79 | minimum: 0 | ||
| 80 | maximum: 7130 | ||
| 81 | 79 | ||
| 82 | additionalProperties: false | 80 | additionalProperties: false |
| 83 | 81 | ||
| @@ -52,7 +52,6 @@ properties: · 51 unmodified lines | |||
| 52 | ti,bus-range-microvolt: | 52 | ti,bus-range-microvolt: |
| 53 | description: | | 53 | description: | |
| 54 | This is the operating range of the bus voltage in microvolt | 54 | This is the operating range of the bus voltage in microvolt |
| 55 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 56 | enum: [16000000, 32000000] | 55 | enum: [16000000, 32000000] |
| 57 | default: 32000000 | 56 | default: 32000000 |
| 58 | 57 | ||
| @@ -39,11 +39,9 @@ properties: · 38 unmodified lines | |||
| 39 | 39 | ||
| 40 | i2c-gpio,delay-us: | 40 | i2c-gpio,delay-us: |
| 41 | description: delay between GPIO operations (may depend on each platform) | 41 | description: delay between GPIO operations (may depend on each platform) |
| 42 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 43 | 42 | ||
| 44 | i2c-gpio,timeout-ms: | 43 | i2c-gpio,timeout-ms: |
| 45 | description: timeout to get data | 44 | description: timeout to get data |
| 46 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 47 | 45 | ||
| 48 | # Deprecated properties, do not use in new device tree sources: | 46 | # Deprecated properties, do not use in new device tree sources: |
| 49 | gpios: | 47 | gpios: |
| @@ -66,21 +66,18 @@ properties: · 65 unmodified lines | |||
| 66 | default: 400000 | 66 | default: 400000 |
| 67 | 67 | ||
| 68 | i2c-sda-hold-time-ns: | 68 | i2c-sda-hold-time-ns: |
| 69 | maxItems: 1 | ||
| 70 | description: | | 69 | description: | |
| 71 | The property should contain the SDA hold time in nanoseconds. This option | 70 | The property should contain the SDA hold time in nanoseconds. This option |
| 72 | is only supported in hardware blocks version 1.11a or newer or on | 71 | is only supported in hardware blocks version 1.11a or newer or on |
| 73 | Microsemi SoCs. | 72 | Microsemi SoCs. |
| 74 | 73 | ||
| 75 | i2c-scl-falling-time-ns: | 74 | i2c-scl-falling-time-ns: |
| 76 | maxItems: 1 | ||
| 77 | description: | | 75 | description: | |
| 78 | The property should contain the SCL falling time in nanoseconds. | 76 | The property should contain the SCL falling time in nanoseconds. |
| 79 | This value is used to compute the tLOW period. | 77 | This value is used to compute the tLOW period. |
| 80 | default: 300 | 78 | default: 300 |
| 81 | 79 | ||
| 82 | i2c-sda-falling-time-ns: | 80 | i2c-sda-falling-time-ns: |
| 83 | maxItems: 1 | ||
| 84 | description: | | 81 | description: | |
| 85 | The property should contain the SDA falling time in nanoseconds. | 82 | The property should contain the SDA falling time in nanoseconds. |
| 86 | This value is used to compute the tHIGH period. | 83 | This value is used to compute the tHIGH period. |
| @@ -16,8 +16,8 @@ description: · 15 unmodified lines | |||
| 16 | properties: | 16 | properties: |
| 17 | compatible: | 17 | compatible: |
| 18 | enum: | 18 | enum: |
| 19 | - bosch,bmc150 | 19 | - bosch,bmc150_accel |
| 20 | - bosch,bmi055 | 20 | - bosch,bmi055_accel |
| 21 | - bosch,bma255 | 21 | - bosch,bma255 |
| 22 | - bosch,bma250e | 22 | - bosch,bma250e |
| 23 | - bosch,bma222 | 23 | - bosch,bma222 |
| @@ -80,7 +80,7 @@ properties: · 79 unmodified lines | |||
| 80 | type: boolean | 80 | type: boolean |
| 81 | 81 | ||
| 82 | bipolar: | 82 | bipolar: |
| 83 | description: see Documentation/devicetree/bindings/iio/adc/adc.txt | 83 | description: see Documentation/devicetree/bindings/iio/adc/adc.yaml |
| 84 | type: boolean | 84 | type: boolean |
| 85 | 85 | ||
| 86 | required: | 86 | required: |
| @@ -23,7 +23,6 @@ properties: · 22 unmodified lines | |||
| 23 | maxItems: 1 | 23 | maxItems: 1 |
| 24 | 24 | ||
| 25 | shunt-resistor-micro-ohms: | 25 | shunt-resistor-micro-ohms: |
| 26 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 27 | description: | | 26 | description: | |
| 28 | Value in micro Ohms of the shunt resistor connected between the RS+ and | 27 | Value in micro Ohms of the shunt resistor connected between the RS+ and |
| 29 | RS- inputs, across which the current is measured. Value needed to compute | 28 | RS- inputs, across which the current is measured. Value needed to compute |
| @@ -246,7 +246,6 @@ patternProperties: · 245 unmodified lines | |||
| 246 | Resolution (bits) to use for conversions: | 246 | Resolution (bits) to use for conversions: |
| 247 | - can be 6, 8, 10 or 12 on stm32f4 | 247 | - can be 6, 8, 10 or 12 on stm32f4 |
| 248 | - can be 8, 10, 12, 14 or 16 on stm32h7 and stm32mp1 | 248 | - can be 8, 10, 12, 14 or 16 on stm32h7 and stm32mp1 |
| 249 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 250 | 249 | ||
| 251 | st,adc-channels: | 250 | st,adc-channels: |
| 252 | description: | | 251 | description: | |
| @@ -42,7 +42,6 @@ properties: · 41 unmodified lines | |||
| 42 | const: 1 | 42 | const: 1 |
| 43 | 43 | ||
| 44 | ti,channel0-current-microamp: | 44 | ti,channel0-current-microamp: |
| 45 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 46 | description: Channel 0 current in uA. | 45 | description: Channel 0 current in uA. |
| 47 | enum: | 46 | enum: |
| 48 | - 0 | 47 | - 0 |
| @@ -51,7 +50,6 @@ properties: · 2 unmodified lines | |||
| 51 | - 20 | 50 | - 20 |
| 52 | 51 | ||
| 53 | ti,channel3-current-microamp: | 52 | ti,channel3-current-microamp: |
| 54 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 55 | description: Channel 3 current in uA. | 53 | description: Channel 3 current in uA. |
| 56 | enum: | 54 | enum: |
| 57 | - 0 | 55 | - 0 |
| @@ -46,31 +46,42 @@ properties: · 45 unmodified lines | |||
| 46 | two properties must be present: | 46 | two properties must be present: |
| 47 | 47 | ||
| 48 | adi,range-microvolt: | 48 | adi,range-microvolt: |
| 49 | $ref: /schemas/types.yaml#/definitions/int32-array | ||
| 50 | description: | | 49 | description: | |
| 51 | Voltage output range specified as <minimum, maximum> | 50 | Voltage output range specified as <minimum, maximum> |
| 52 | enum: | 51 | oneOf: |
| 53 | - [[0, 5000000]] | 52 | - items: |
| 54 | - [[0, 10000000]] | 53 | - const: 0 |
| 55 | - [[-5000000, 5000000]] | 54 | - enum: [5000000, 10000000] |
| 56 | - [[-10000000, 10000000]] | 55 | - items: |
| 56 | - const: -5000000 | ||
| 57 | - const: 5000000 | ||
| 58 | - items: | ||
| 59 | - const: -10000000 | ||
| 60 | - const: 10000000 | ||
| 57 | 61 | ||
| 58 | adi,range-microamp: | 62 | adi,range-microamp: |
| 59 | $ref: /schemas/types.yaml#/definitions/int32-array | ||
| 60 | description: | | 63 | description: | |
| 61 | Current output range specified as <minimum, maximum> | 64 | Current output range specified as <minimum, maximum> |
| 62 | enum: | 65 | oneOf: |
| 63 | - [[0, 20000]] | 66 | - items: |
| 64 | - [[0, 24000]] | 67 | - const: 0 |
| 65 | - [[4, 24000]] | 68 | - enum: [20000, 24000] |
| 66 | - [[-20000, 20000]] | 69 | - items: |
| 67 | - [[-24000, 24000]] | 70 | - const: 4 |
| 68 | - [[-1000, 22000]] | 71 | - const: 24000 |
| 72 | - items: | ||
| 73 | - const: -20000 | ||
| 74 | - const: 20000 | ||
| 75 | - items: | ||
| 76 | - const: -24000 | ||
| 77 | - const: 24000 | ||
| 78 | - items: | ||
| 79 | - const: -1000 | ||
| 80 | - const: 22000 | ||
| 69 | 81 | ||
| 70 | reset-gpios: true | 82 | reset-gpios: true |
| 71 | 83 | ||
| 72 | adi,dc-dc-ilim-microamp: | 84 | adi,dc-dc-ilim-microamp: |
| 73 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 74 | enum: [150000, 200000, 250000, 300000, 350000, 400000] | 85 | enum: [150000, 200000, 250000, 300000, 350000, 400000] |
| 75 | description: | | 86 | description: | |
| 76 | The dc-to-dc converter current limit. | 87 | The dc-to-dc converter current limit. |
| @@ -21,7 +21,6 @@ properties: · 20 unmodified lines | |||
| 21 | description: Connected to ADC_RDY pin. | 21 | description: Connected to ADC_RDY pin. |
| 22 | 22 | ||
| 23 | maxim,led-current-microamp: | 23 | maxim,led-current-microamp: |
| 24 | $ref: /schemas/types.yaml#/definitions/uint32-array | ||
| 25 | minItems: 2 | 24 | minItems: 2 |
| 26 | maxItems: 2 | 25 | maxItems: 2 |
| 27 | description: | | 26 | description: | |
| @@ -5,7 +5,8 @@ Required properties: · 4 unmodified lines | |||
| 5 | - compatible: "adc-keys" | 5 | - compatible: "adc-keys" |
| 6 | - io-channels: Phandle to an ADC channel | 6 | - io-channels: Phandle to an ADC channel |
| 7 | - io-channel-names = "buttons"; | 7 | - io-channel-names = "buttons"; |
| 8 | - keyup-threshold-microvolt: Voltage at which all the keys are considered up. | 8 | - keyup-threshold-microvolt: Voltage above or equal to which all the keys are |
| 9 | considered up. | ||
| 9 | 10 | ||
| 10 | Optional properties: | 11 | Optional properties: |
| 11 | - poll-interval: Poll interval time in milliseconds | 12 | - poll-interval: Poll interval time in milliseconds |
| @@ -17,7 +18,12 @@ Each button (key) is represented as a sub-node of "adc-keys": · 5 unmodified lines | |||
| 17 | Required subnode-properties: | 18 | Required subnode-properties: |
| 18 | - label: Descriptive name of the key. | 19 | - label: Descriptive name of the key. |
| 19 | - linux,code: Keycode to emit. | 20 | - linux,code: Keycode to emit. |
| 20 | - press-threshold-microvolt: Voltage ADC input when this key is pressed. | 21 | - press-threshold-microvolt: voltage above or equal to which this key is |
| 22 | considered pressed. | ||
| 23 | |||
| 24 | No two values of press-threshold-microvolt may be the same. | ||
| 25 | All values of press-threshold-microvolt must be less than | ||
| 26 | keyup-threshold-microvolt. | ||
| 21 | 27 | ||
| 22 | Example: | 28 | Example: |
| 23 | 29 | ||
| @@ -47,3 +53,15 @@ Example: · 23 unmodified lines | |||
| 47 | press-threshold-microvolt = <500000>; | 53 | press-threshold-microvolt = <500000>; |
| 48 | }; | 54 | }; |
| 49 | }; | 55 | }; |
| 56 | |||
| 57 | +--------------------------------+------------------------+ | ||
| 58 | | 2.000.000 <= value | no key pressed | | ||
| 59 | +--------------------------------+------------------------+ | ||
| 60 | | 1.500.000 <= value < 2.000.000 | KEY_VOLUMEUP pressed | | ||
| 61 | +--------------------------------+------------------------+ | ||
| 62 | | 1.000.000 <= value < 1.500.000 | KEY_VOLUMEDOWN pressed | | ||
| 63 | +--------------------------------+------------------------+ | ||
| 64 | | 500.000 <= value < 1.000.000 | KEY_ENTER pressed | | ||
| 65 | +--------------------------------+------------------------+ | ||
| 66 | | value < 500.000 | no key pressed | | ||
| 67 | +--------------------------------+------------------------+ | ||
| @@ -26,6 +26,7 @@ properties: · 25 unmodified lines | |||
| 26 | - goodix,gt927 | 26 | - goodix,gt927 |
| 27 | - goodix,gt9271 | 27 | - goodix,gt9271 |
| 28 | - goodix,gt928 | 28 | - goodix,gt928 |
| 29 | - goodix,gt9286 | ||
| 29 | - goodix,gt967 | 30 | - goodix,gt967 |
| 30 | 31 | ||
| 31 | reg: | 32 | reg: |
| @@ -70,11 +70,9 @@ properties: · 69 unmodified lines | |||
| 70 | 70 | ||
| 71 | touchscreen-x-mm: | 71 | touchscreen-x-mm: |
| 72 | description: horizontal length in mm of the touchscreen | 72 | description: horizontal length in mm of the touchscreen |
| 73 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 74 | 73 | ||
| 75 | touchscreen-y-mm: | 74 | touchscreen-y-mm: |
| 76 | description: vertical length in mm of the touchscreen | 75 | description: vertical length in mm of the touchscreen |
| 77 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 78 | 76 | ||
| 79 | dependencies: | 77 | dependencies: |
| 80 | touchscreen-size-x: [ touchscreen-size-y ] | 78 | touchscreen-size-x: [ touchscreen-size-y ] |
| @@ -0,0 +1,111 @@ | |||
| 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) | ||
| 2 | %YAML 1.2 | ||
| 3 | --- | ||
| 4 | $id: http://devicetree.org/schemas/leds/richtek,rt8515.yaml# | ||
| 5 | $schema: http://devicetree.org/meta-schemas/core.yaml# | ||
| 6 | |||
| 7 | title: Richtek RT8515 1.5A dual channel LED driver | ||
| 8 | |||
| 9 | maintainers: | ||
| 10 | - Linus Walleij <linus.walleij@linaro.org> | ||
| 11 | |||
| 12 | description: | | ||
| 13 | The Richtek RT8515 is a dual channel (two mode) LED driver that | ||
| 14 | supports driving a white LED in flash or torch mode. The maximum | ||
| 15 | current for each mode is defined in hardware using two resistors | ||
| 16 | RFS and RTS. | ||
| 17 | |||
| 18 | properties: | ||
| 19 | compatible: | ||
| 20 | const: richtek,rt8515 | ||
| 21 | |||
| 22 | enf-gpios: | ||
| 23 | maxItems: 1 | ||
| 24 | description: A connection to the 'ENF' (enable flash) pin. | ||
| 25 | |||
| 26 | ent-gpios: | ||
| 27 | maxItems: 1 | ||
| 28 | description: A connection to the 'ENT' (enable torch) pin. | ||
| 29 | |||
| 30 | richtek,rfs-ohms: | ||
| 31 | minimum: 7680 | ||
| 32 | maximum: 367000 | ||
| 33 | description: The resistance value of the RFS resistor. This | ||
| 34 | resistors limits the maximum flash current. This must be set | ||
| 35 | for the property flash-max-microamp to work, the RFS resistor | ||
| 36 | defines the range of the dimmer setting (brightness) of the | ||
| 37 | flash LED. | ||
| 38 | |||
| 39 | richtek,rts-ohms: | ||
| 40 | minimum: 7680 | ||
| 41 | maximum: 367000 | ||
| 42 | description: The resistance value of the RTS resistor. This | ||
| 43 | resistors limits the maximum torch current. This must be set | ||
| 44 | for the property torch-max-microamp to work, the RTS resistor | ||
| 45 | defines the range of the dimmer setting (brightness) of the | ||
| 46 | torch LED. | ||
| 47 | |||
| 48 | led: | ||
| 49 | type: object | ||
| 50 | $ref: common.yaml# | ||
| 51 | properties: | ||
| 52 | function: true | ||
| 53 | color: true | ||
| 54 | flash-max-timeout-us: true | ||
| 55 | |||
| 56 | flash-max-microamp: | ||
| 57 | maximum: 700000 | ||
| 58 | description: The maximum current for flash mode | ||
| 59 | is hardwired to the component using the RFS resistor to | ||
| 60 | ground. The maximum hardware current setting is calculated | ||
| 61 | according to the formula Imax = 5500 / RFS. The lowest | ||
| 62 | allowed resistance value is 7.86 kOhm giving an absolute | ||
| 63 | maximum current of 700mA. By setting this attribute in | ||
| 64 | the device tree, you can further restrict the maximum | ||
| 65 | current below the hardware limit. This requires the RFS | ||
| 66 | to be defined as it defines the maximum range. | ||
| 67 | |||
| 68 | led-max-microamp: | ||
| 69 | maximum: 700000 | ||
| 70 | description: The maximum current for torch mode | ||
| 71 | is hardwired to the component using the RTS resistor to | ||
| 72 | ground. The maximum hardware current setting is calculated | ||
| 73 | according to the formula Imax = 5500 / RTS. The lowest | ||
| 74 | allowed resistance value is 7.86 kOhm giving an absolute | ||
| 75 | maximum current of 700mA. By setting this attribute in | ||
| 76 | the device tree, you can further restrict the maximum | ||
| 77 | current below the hardware limit. This requires the RTS | ||
| 78 | to be defined as it defines the maximum range. | ||
| 79 | |||
| 80 | additionalProperties: false | ||
| 81 | |||
| 82 | required: | ||
| 83 | - compatible | ||
| 84 | - ent-gpios | ||
| 85 | - enf-gpios | ||
| 86 | - led | ||
| 87 | |||
| 88 | additionalProperties: false | ||
| 89 | |||
| 90 | examples: | ||
| 91 | - | | ||
| 92 | #include <dt-bindings/gpio/gpio.h> | ||
| 93 | #include <dt-bindings/leds/common.h> | ||
| 94 | |||
| 95 | led-controller { | ||
| 96 | compatible = "richtek,rt8515"; | ||
| 97 | enf-gpios = <&gpio4 12 GPIO_ACTIVE_HIGH>; | ||
| 98 | ent-gpios = <&gpio4 13 GPIO_ACTIVE_HIGH>; | ||
| 99 | richtek,rfs-ohms = <16000>; | ||
| 100 | richtek,rts-ohms = <100000>; | ||
| 101 | |||
| 102 | led { | ||
| 103 | function = LED_FUNCTION_FLASH; | ||
| 104 | color = <LED_COLOR_ID_WHITE>; | ||
| 105 | flash-max-timeout-us = <250000>; | ||
| 106 | flash-max-microamp = <150000>; | ||
| 107 | led-max-microamp = <25000>; | ||
| 108 | }; | ||
| 109 | }; | ||
| 110 | |||
| 111 | ... | ||
| @@ -16,7 +16,7 @@ Required properties: · 15 unmodified lines | |||
| 16 | - power-domains: a phandle to the power domain, see | 16 | - power-domains: a phandle to the power domain, see |
| 17 | Documentation/devicetree/bindings/power/power_domain.txt for details. | 17 | Documentation/devicetree/bindings/power/power_domain.txt for details. |
| 18 | - mediatek,larb: must contain the local arbiters in the current Socs, see | 18 | - mediatek,larb: must contain the local arbiters in the current Socs, see |
| 19 | Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.txt | 19 | Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.yaml |
| 20 | for details. | 20 | for details. |
| 21 | - iommus: should point to the respective IOMMU block with master port as | 21 | - iommus: should point to the respective IOMMU block with master port as |
| 22 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt | 22 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt |
| @@ -14,7 +14,7 @@ Required properties: · 13 unmodified lines | |||
| 14 | - power-domains: a phandle to the power domain, see | 14 | - power-domains: a phandle to the power domain, see |
| 15 | Documentation/devicetree/bindings/power/power_domain.txt for details. | 15 | Documentation/devicetree/bindings/power/power_domain.txt for details. |
| 16 | - mediatek,larb: must contain the local arbiters in the current SoCs, see | 16 | - mediatek,larb: must contain the local arbiters in the current SoCs, see |
| 17 | Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.txt | 17 | Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.yaml |
| 18 | for details. | 18 | for details. |
| 19 | - iommus: should point to the respective IOMMU block with master port as | 19 | - iommus: should point to the respective IOMMU block with master port as |
| 20 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt | 20 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt |
| @@ -28,7 +28,7 @@ Required properties (DMA function blocks, child node): · 27 unmodified lines | |||
| 28 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt | 28 | argument, see Documentation/devicetree/bindings/iommu/mediatek,iommu.txt |
| 29 | for details. | 29 | for details. |
| 30 | - mediatek,larb: must contain the local arbiters in the current Socs, see | 30 | - mediatek,larb: must contain the local arbiters in the current Socs, see |
| 31 | Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.txt | 31 | Documentation/devicetree/bindings/memory-controllers/mediatek,smi-larb.yaml |
| 32 | for details. | 32 | for details. |
| 33 | 33 | ||
| 34 | Example: | 34 | Example: |
| @@ -259,7 +259,6 @@ properties: · 258 unmodified lines | |||
| 259 | waiting for I/O signalling and card power supply to be stable, | 259 | waiting for I/O signalling and card power supply to be stable, |
| 260 | regardless of whether pwrseq-simple is used. Default to 10ms if | 260 | regardless of whether pwrseq-simple is used. Default to 10ms if |
| 261 | no available. | 261 | no available. |
| 262 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 263 | default: 10 | 262 | default: 10 |
| 264 | 263 | ||
| 265 | supports-cqe: | 264 | supports-cqe: |
| @@ -41,13 +41,11 @@ properties: · 40 unmodified lines | |||
| 41 | description: | 41 | description: |
| 42 | Delay in ms after powering the card and de-asserting the | 42 | Delay in ms after powering the card and de-asserting the |
| 43 | reset-gpios (if any). | 43 | reset-gpios (if any). |
| 44 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 45 | 44 | ||
| 46 | power-off-delay-us: | 45 | power-off-delay-us: |
| 47 | description: | 46 | description: |
| 48 | Delay in us after asserting the reset-gpios (if any) | 47 | Delay in us after asserting the reset-gpios (if any) |
| 49 | during power off of the card. | 48 | during power off of the card. |
| 50 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 51 | 49 | ||
| 52 | required: | 50 | required: |
| 53 | - compatible | 51 | - compatible |
| @@ -122,7 +122,6 @@ properties: · 121 unmodified lines | |||
| 122 | such as flow control thresholds. | 122 | such as flow control thresholds. |
| 123 | 123 | ||
| 124 | rx-internal-delay-ps: | 124 | rx-internal-delay-ps: |
| 125 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 126 | description: | | 125 | description: | |
| 127 | RGMII Receive Clock Delay defined in pico seconds. | 126 | RGMII Receive Clock Delay defined in pico seconds. |
| 128 | This is used for controllers that have configurable RX internal delays. | 127 | This is used for controllers that have configurable RX internal delays. |
| @@ -140,7 +139,6 @@ properties: · 11 unmodified lines | |||
| 140 | is used for components that can have configurable fifo sizes. | 139 | is used for components that can have configurable fifo sizes. |
| 141 | 140 | ||
| 142 | tx-internal-delay-ps: | 141 | tx-internal-delay-ps: |
| 143 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 144 | description: | | 142 | description: | |
| 145 | RGMII Transmit Clock Delay defined in pico seconds. | 143 | RGMII Transmit Clock Delay defined in pico seconds. |
| 146 | This is used for controllers that have configurable TX internal delays. | 144 | This is used for controllers that have configurable TX internal delays. |
| @@ -163,6 +163,7 @@ allOf: · 162 unmodified lines | |||
| 163 | enum: | 163 | enum: |
| 164 | - renesas,etheravb-r8a774a1 | 164 | - renesas,etheravb-r8a774a1 |
| 165 | - renesas,etheravb-r8a774b1 | 165 | - renesas,etheravb-r8a774b1 |
| 166 | - renesas,etheravb-r8a774e1 | ||
| 166 | - renesas,etheravb-r8a7795 | 167 | - renesas,etheravb-r8a7795 |
| 167 | - renesas,etheravb-r8a7796 | 168 | - renesas,etheravb-r8a7796 |
| 168 | - renesas,etheravb-r8a77961 | 169 | - renesas,etheravb-r8a77961 |
| @@ -161,7 +161,8 @@ properties: · 160 unmodified lines | |||
| 161 | * snps,route-dcbcp, DCB Control Packets | 161 | * snps,route-dcbcp, DCB Control Packets |
| 162 | * snps,route-up, Untagged Packets | 162 | * snps,route-up, Untagged Packets |
| 163 | * snps,route-multi-broad, Multicast & Broadcast Packets | 163 | * snps,route-multi-broad, Multicast & Broadcast Packets |
| 164 | * snps,priority, RX queue priority (Range 0x0 to 0xF) | 164 | * snps,priority, bitmask of the tagged frames priorities assigned to |
| 165 | the queue | ||
| 165 | 166 | ||
| 166 | snps,mtl-tx-config: | 167 | snps,mtl-tx-config: |
| 167 | $ref: /schemas/types.yaml#/definitions/phandle | 168 | $ref: /schemas/types.yaml#/definitions/phandle |
| @@ -188,7 +189,10 @@ properties: · 20 unmodified lines | |||
| 188 | * snps,idle_slope, unlock on WoL | 189 | * snps,idle_slope, unlock on WoL |
| 189 | * snps,high_credit, max write outstanding req. limit | 190 | * snps,high_credit, max write outstanding req. limit |
| 190 | * snps,low_credit, max read outstanding req. limit | 191 | * snps,low_credit, max read outstanding req. limit |
| 191 | * snps,priority, TX queue priority (Range 0x0 to 0xF) | 192 | * snps,priority, bitmask of the priorities assigned to the queue. |
| 193 | When a PFC frame is received with priorities matching the bitmask, | ||
| 194 | the queue is blocked from transmitting for the pause time specified | ||
| 195 | in the PFC frame. | ||
| 192 | 196 | ||
| 193 | snps,reset-gpio: | 197 | snps,reset-gpio: |
| 194 | deprecated: true | 198 | deprecated: true |
| @@ -208,7 +212,6 @@ properties: · 13 unmodified lines | |||
| 208 | Triplet of delays. The 1st cell is reset pre-delay in micro | 212 | Triplet of delays. The 1st cell is reset pre-delay in micro |
| 209 | seconds. The 2nd cell is reset pulse in micro seconds. The 3rd | 213 | seconds. The 2nd cell is reset pulse in micro seconds. The 3rd |
| 210 | cell is reset post-delay in micro seconds. | 214 | cell is reset post-delay in micro seconds. |
| 211 | $ref: /schemas/types.yaml#/definitions/uint32-array | ||
| 212 | minItems: 3 | 215 | minItems: 3 |
| 213 | maxItems: 3 | 216 | maxItems: 3 |
| 214 | 217 | ||
| @@ -83,21 +83,18 @@ properties: · 82 unmodified lines | |||
| 83 | for each of the battery capacity lookup table. | 83 | for each of the battery capacity lookup table. |
| 84 | 84 | ||
| 85 | operating-range-celsius: | 85 | operating-range-celsius: |
| 86 | $ref: /schemas/types.yaml#/definitions/uint32-array | ||
| 87 | description: operating temperature range of a battery | 86 | description: operating temperature range of a battery |
| 88 | items: | 87 | items: |
| 89 | - description: minimum temperature at which battery can operate | 88 | - description: minimum temperature at which battery can operate |
| 90 | - description: maximum temperature at which battery can operate | 89 | - description: maximum temperature at which battery can operate |
| 91 | 90 | ||
| 92 | ambient-celsius: | 91 | ambient-celsius: |
| 93 | $ref: /schemas/types.yaml#/definitions/uint32-array | ||
| 94 | description: safe range of ambient temperature | 92 | description: safe range of ambient temperature |
| 95 | items: | 93 | items: |
| 96 | - description: alert when ambient temperature is lower than this value | 94 | - description: alert when ambient temperature is lower than this value |
| 97 | - description: alert when ambient temperature is higher than this value | 95 | - description: alert when ambient temperature is higher than this value |
| 98 | 96 | ||
| 99 | alert-celsius: | 97 | alert-celsius: |
| 100 | $ref: /schemas/types.yaml#/definitions/uint32-array | ||
| 101 | description: safe range of battery temperature | 98 | description: safe range of battery temperature |
| 102 | items: | 99 | items: |
| 103 | - description: alert when battery temperature is lower than this value | 100 | - description: alert when battery temperature is lower than this value |
| @@ -50,7 +50,6 @@ properties: · 49 unmodified lines | |||
| 50 | maxItems: 1 | 50 | maxItems: 1 |
| 51 | 51 | ||
| 52 | input-current-limit-microamp: | 52 | input-current-limit-microamp: |
| 53 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 54 | description: Maximum input current in micro Amps. | 53 | description: Maximum input current in micro Amps. |
| 55 | minimum: 50000 | 54 | minimum: 50000 |
| 56 | maximum: 500000 | 55 | maximum: 500000 |
| @@ -62,7 +62,6 @@ properties: · 61 unmodified lines | |||
| 62 | description: IRQ line information. | 62 | description: IRQ line information. |
| 63 | 63 | ||
| 64 | dlg,irq-polling-delay-passive-ms: | 64 | dlg,irq-polling-delay-passive-ms: |
| 65 | $ref: "/schemas/types.yaml#/definitions/uint32" | ||
| 66 | minimum: 1000 | 65 | minimum: 1000 |
| 67 | maximum: 10000 | 66 | maximum: 10000 |
| 68 | description: | | 67 | description: | |
| @@ -72,11 +72,9 @@ properties: · 71 unmodified lines | |||
| 72 | 72 | ||
| 73 | startup-delay-us: | 73 | startup-delay-us: |
| 74 | description: startup time in microseconds | 74 | description: startup time in microseconds |
| 75 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 76 | 75 | ||
| 77 | off-on-delay-us: | 76 | off-on-delay-us: |
| 78 | description: off delay time in microseconds | 77 | description: off delay time in microseconds |
| 79 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 80 | 78 | ||
| 81 | enable-active-high: | 79 | enable-active-high: |
| 82 | description: | 80 | description: |
| @@ -19,7 +19,9 @@ description: | · 18 unmodified lines | |||
| 19 | properties: | 19 | properties: |
| 20 | compatible: | 20 | compatible: |
| 21 | enum: | 21 | enum: |
| 22 | - nxp,pf8x00 | 22 | - nxp,pf8100 |
| 23 | - nxp,pf8121a | ||
| 24 | - nxp,pf8200 | ||
| 23 | 25 | ||
| 24 | reg: | 26 | reg: |
| 25 | maxItems: 1 | 27 | maxItems: 1 |
| @@ -118,7 +120,7 @@ examples: · 92 unmodified lines | |||
| 118 | #size-cells = <0>; | 120 | #size-cells = <0>; |
| 119 | 121 | ||
| 120 | pmic@8 { | 122 | pmic@8 { |
| 121 | compatible = "nxp,pf8x00"; | 123 | compatible = "nxp,pf8100"; |
| 122 | reg = <0x08>; | 124 | reg = <0x08>; |
| 123 | 125 | ||
| 124 | regulators { | 126 | regulators { |
| @@ -44,6 +44,7 @@ First Level Nodes - PMIC · 43 unmodified lines | |||
| 44 | Definition: Must be one of below: | 44 | Definition: Must be one of below: |
| 45 | "qcom,pm8005-rpmh-regulators" | 45 | "qcom,pm8005-rpmh-regulators" |
| 46 | "qcom,pm8009-rpmh-regulators" | 46 | "qcom,pm8009-rpmh-regulators" |
| 47 | "qcom,pm8009-1-rpmh-regulators" | ||
| 47 | "qcom,pm8150-rpmh-regulators" | 48 | "qcom,pm8150-rpmh-regulators" |
| 48 | "qcom,pm8150l-rpmh-regulators" | 49 | "qcom,pm8150l-rpmh-regulators" |
| 49 | "qcom,pm8350-rpmh-regulators" | 50 | "qcom,pm8350-rpmh-regulators" |
| @@ -27,7 +27,6 @@ properties: · 26 unmodified lines | |||
| 27 | 1: chargeable | 27 | 1: chargeable |
| 28 | 28 | ||
| 29 | quartz-load-femtofarads: | 29 | quartz-load-femtofarads: |
| 30 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 31 | description: | 30 | description: |
| 32 | The capacitive load of the quartz(x-tal), expressed in femto | 31 | The capacitive load of the quartz(x-tal), expressed in femto |
| 33 | Farad (fF). The default value shall be listed (if optional), | 32 | Farad (fF). The default value shall be listed (if optional), |
| @@ -47,7 +46,6 @@ properties: · 13 unmodified lines | |||
| 47 | deprecated: true | 46 | deprecated: true |
| 48 | 47 | ||
| 49 | trickle-resistor-ohms: | 48 | trickle-resistor-ohms: |
| 50 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 51 | description: | 49 | description: |
| 52 | Selected resistor for trickle charger. Should be given | 50 | Selected resistor for trickle charger. Should be given |
| 53 | if trickle charger should be enabled. | 51 | if trickle charger should be enabled. |
| @@ -88,14 +88,12 @@ properties: · 87 unmodified lines | |||
| 88 | description: | 88 | description: |
| 89 | Rate at which poll occurs when auto-poll is set. | 89 | Rate at which poll occurs when auto-poll is set. |
| 90 | default 100ms. | 90 | default 100ms. |
| 91 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 92 | default: 100 | 91 | default: 100 |
| 93 | 92 | ||
| 94 | poll-timeout-ms: | 93 | poll-timeout-ms: |
| 95 | description: | 94 | description: |
| 96 | Poll timeout when auto-poll is set, default | 95 | Poll timeout when auto-poll is set, default |
| 97 | 3000ms. | 96 | 3000ms. |
| 98 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 99 | default: 3000 | 97 | default: 3000 |
| 100 | 98 | ||
| 101 | required: | 99 | required: |
| @@ -7,8 +7,8 @@ $schema: http://devicetree.org/meta-schemas/core.yaml# · 6 unmodified lines | |||
| 7 | title: Mediatek MT8192 with MT6359, RT1015 and RT5682 ASoC sound card driver | 7 | title: Mediatek MT8192 with MT6359, RT1015 and RT5682 ASoC sound card driver |
| 8 | 8 | ||
| 9 | maintainers: | 9 | maintainers: |
| 10 | - Jiaxin Yu <jiaxin.yu@mediatek.com> | 10 | - Jiaxin Yu <jiaxin.yu@mediatek.com> |
| 11 | - Shane Chien <shane.chien@mediatek.com> | 11 | - Shane Chien <shane.chien@mediatek.com> |
| 12 | 12 | ||
| 13 | description: | 13 | description: |
| 14 | This binding describes the MT8192 sound card. | 14 | This binding describes the MT8192 sound card. |
| @@ -41,14 +41,12 @@ properties: · 40 unmodified lines | |||
| 41 | values of 2k, 4k or 8k. If set to 0 it will be off. If this node is not | 41 | values of 2k, 4k or 8k. If set to 0 it will be off. If this node is not |
| 42 | mentioned or if the value is unknown, then micbias resistor is set to | 42 | mentioned or if the value is unknown, then micbias resistor is set to |
| 43 | 4k. | 43 | 4k. |
| 44 | $ref: "/schemas/types.yaml#/definitions/uint32" | ||
| 45 | enum: [ 0, 2, 4, 8 ] | 44 | enum: [ 0, 2, 4, 8 ] |
| 46 | 45 | ||
| 47 | micbias-voltage-m-volts: | 46 | micbias-voltage-m-volts: |
| 48 | description: The bias voltage to be used in mVolts. The voltage can take | 47 | description: The bias voltage to be used in mVolts. The voltage can take |
| 49 | values from 1.25V to 3V by 250mV steps. If this node is not mentioned | 48 | values from 1.25V to 3V by 250mV steps. If this node is not mentioned |
| 50 | or the value is unknown, then the value is set to 1.25V. | 49 | or the value is unknown, then the value is set to 1.25V. |
| 51 | $ref: "/schemas/types.yaml#/definitions/uint32" | ||
| 52 | enum: [ 1250, 1500, 1750, 2000, 2250, 2500, 2750, 3000 ] | 50 | enum: [ 1250, 1500, 1750, 2000, 2250, 2500, 2750, 3000 ] |
| 53 | 51 | ||
| 54 | lrclk-strength: | 52 | lrclk-strength: |
| @@ -1,4 +1,6 @@ | |||
| 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) | 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) |
| 2 | # Copyright (C) 2020 Texas Instruments Incorporated | ||
| 3 | # Author: Peter Ujfalusi <peter.ujfalusi@ti.com> | ||
| 2 | %YAML 1.2 | 4 | %YAML 1.2 |
| 3 | --- | 5 | --- |
| 4 | $id: http://devicetree.org/schemas/sound/ti,j721e-cpb-audio.yaml# | 6 | $id: http://devicetree.org/schemas/sound/ti,j721e-cpb-audio.yaml# |
| @@ -7,7 +9,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml# · 2 unmodified lines | |||
| 7 | title: Texas Instruments J721e Common Processor Board Audio Support | 9 | title: Texas Instruments J721e Common Processor Board Audio Support |
| 8 | 10 | ||
| 9 | maintainers: | 11 | maintainers: |
| 10 | - Peter Ujfalusi <peter.ujfalusi@ti.com> | 12 | - Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 11 | 13 | ||
| 12 | description: | | 14 | description: | |
| 13 | The audio support on the board is using pcm3168a codec connected to McASP10 | 15 | The audio support on the board is using pcm3168a codec connected to McASP10 |
| @@ -1,4 +1,6 @@ | |||
| 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) | 1 | # SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) |
| 2 | # Copyright (C) 2020 Texas Instruments Incorporated | ||
| 3 | # Author: Peter Ujfalusi <peter.ujfalusi@ti.com> | ||
| 2 | %YAML 1.2 | 4 | %YAML 1.2 |
| 3 | --- | 5 | --- |
| 4 | $id: http://devicetree.org/schemas/sound/ti,j721e-cpb-ivi-audio.yaml# | 6 | $id: http://devicetree.org/schemas/sound/ti,j721e-cpb-ivi-audio.yaml# |
| @@ -7,7 +9,7 @@ $schema: http://devicetree.org/meta-schemas/core.yaml# · 2 unmodified lines | |||
| 7 | title: Texas Instruments J721e Common Processor Board Audio Support | 9 | title: Texas Instruments J721e Common Processor Board Audio Support |
| 8 | 10 | ||
| 9 | maintainers: | 11 | maintainers: |
| 10 | - Peter Ujfalusi <peter.ujfalusi@ti.com> | 12 | - Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 11 | 13 | ||
| 12 | description: | | 14 | description: | |
| 13 | The Infotainment board plugs into the Common Processor Board, the support of the | 15 | The Infotainment board plugs into the Common Processor Board, the support of the |
| @@ -11,12 +11,18 @@ maintainers: · 10 unmodified lines | |||
| 11 | 11 | ||
| 12 | properties: | 12 | properties: |
| 13 | compatible: | 13 | compatible: |
| 14 | items: | 14 | oneOf: |
| 15 | - const: ti,j721e-usb | 15 | - const: ti,j721e-usb |
| 16 | - const: ti,am64-usb | ||
| 17 | - items: | ||
| 18 | - const: ti,j721e-usb | ||
| 19 | - const: ti,am64-usb | ||
| 16 | 20 | ||
| 17 | reg: | 21 | reg: |
| 18 | description: module registers | 22 | description: module registers |
| 19 | 23 | ||
| 24 | ranges: true | ||
| 25 | |||
| 20 | power-domains: | 26 | power-domains: |
| 21 | description: | 27 | description: |
| 22 | PM domain provider node and an args specifier containing | 28 | PM domain provider node and an args specifier containing |
| @@ -58,6 +64,8 @@ properties: · 35 unmodified lines | |||
| 58 | '#size-cells': | 64 | '#size-cells': |
| 59 | const: 2 | 65 | const: 2 |
| 60 | 66 | ||
| 67 | dma-coherent: true | ||
| 68 | |||
| 61 | patternProperties: | 69 | patternProperties: |
| 62 | "^usb@": | 70 | "^usb@": |
| 63 | type: object | 71 | type: object |
| @@ -19,7 +19,6 @@ properties: · 18 unmodified lines | |||
| 19 | pattern: "^watchdog(@.*|-[0-9a-f])?$" | 19 | pattern: "^watchdog(@.*|-[0-9a-f])?$" |
| 20 | 20 | ||
| 21 | timeout-sec: | 21 | timeout-sec: |
| 22 | $ref: /schemas/types.yaml#/definitions/uint32 | ||
| 23 | description: | 22 | description: |
| 24 | Contains the watchdog timeout in seconds. | 23 | Contains the watchdog timeout in seconds. |
| 25 | 24 | ||
| @@ -48,12 +48,12 @@ or ``virtualenv``, depending on how your distribution packaged Python 3. · 47 unmodified lines | |||
| 48 | those versions, you should run ``pip install 'docutils==0.12'``. | 48 | those versions, you should run ``pip install 'docutils==0.12'``. |
| 49 | 49 | ||
| 50 | #) It is recommended to use the RTD theme for html output. Depending | 50 | #) It is recommended to use the RTD theme for html output. Depending |
| 51 | on the Sphinx version, it should be installed in separate, | 51 | on the Sphinx version, it should be installed separately, |
| 52 | with ``pip install sphinx_rtd_theme``. | 52 | with ``pip install sphinx_rtd_theme``. |
| 53 | 53 | ||
| 54 | #) Some ReST pages contain math expressions. Due to the way Sphinx work, | 54 | #) Some ReST pages contain math expressions. Due to the way Sphinx works, |
| 55 | those expressions are written using LaTeX notation. It needs texlive | 55 | those expressions are written using LaTeX notation. It needs texlive |
| 56 | installed with amdfonts and amsmath in order to evaluate them. | 56 | installed with amsfonts and amsmath in order to evaluate them. |
| 57 | 57 | ||
| 58 | In summary, if you want to install Sphinx version 1.7.9, you should do:: | 58 | In summary, if you want to install Sphinx version 1.7.9, you should do:: |
| 59 | 59 | ||
| @@ -128,7 +128,7 @@ Sphinx Build · 68 unmodified lines | |||
| 128 | ============ | 128 | ============ |
| 129 | 129 | ||
| 130 | The usual way to generate the documentation is to run ``make htmldocs`` or | 130 | The usual way to generate the documentation is to run ``make htmldocs`` or |
| 131 | ``make pdfdocs``. There are also other formats available, see the documentation | 131 | ``make pdfdocs``. There are also other formats available: see the documentation |
| 132 | section of ``make help``. The generated documentation is placed in | 132 | section of ``make help``. The generated documentation is placed in |
| 133 | format-specific subdirectories under ``Documentation/output``. | 133 | format-specific subdirectories under ``Documentation/output``. |
| 134 | 134 | ||
| @@ -303,17 +303,17 @@ and *targets* (e.g. a ref to ``:ref:`last row <last row>``` / :ref:`last row · 168 unmodified lines | |||
| 303 | - head col 3 | 303 | - head col 3 |
| 304 | - head col 4 | 304 | - head col 4 |
| 305 | 305 | ||
| 306 | * - column 1 | 306 | * - row 1 |
| 307 | - field 1.1 | 307 | - field 1.1 |
| 308 | - field 1.2 with autospan | 308 | - field 1.2 with autospan |
| 309 | 309 | ||
| 310 | * - column 2 | 310 | * - row 2 |
| 311 | - field 2.1 | 311 | - field 2.1 |
| 312 | - :rspan:`1` :cspan:`1` field 2.2 - 3.3 | 312 | - :rspan:`1` :cspan:`1` field 2.2 - 3.3 |
| 313 | 313 | ||
| 314 | * .. _`last row`: | 314 | * .. _`last row`: |
| 315 | 315 | ||
| 316 | - column 3 | 316 | - row 3 |
| 317 | 317 | ||
| 318 | Rendered as: | 318 | Rendered as: |
| 319 | 319 | ||
| @@ -325,17 +325,17 @@ Rendered as: · 5 unmodified lines | |||
| 325 | - head col 3 | 325 | - head col 3 |
| 326 | - head col 4 | 326 | - head col 4 |
| 327 | 327 | ||
| 328 | * - column 1 | 328 | * - row 1 |
| 329 | - field 1.1 | 329 | - field 1.1 |
| 330 | - field 1.2 with autospan | 330 | - field 1.2 with autospan |
| 331 | 331 | ||
| 332 | * - column 2 | 332 | * - row 2 |
| 333 | - field 2.1 | 333 | - field 2.1 |
| 334 | - :rspan:`1` :cspan:`1` field 2.2 - 3.3 | 334 | - :rspan:`1` :cspan:`1` field 2.2 - 3.3 |
| 335 | 335 | ||
| 336 | * .. _`last row`: | 336 | * .. _`last row`: |
| 337 | 337 | ||
| 338 | - column 3 | 338 | - row 3 |
| 339 | 339 | ||
| 340 | Cross-referencing | 340 | Cross-referencing |
| 341 | ----------------- | 341 | ----------------- |
| @@ -361,7 +361,7 @@ Figures & Images · 19 unmodified lines | |||
| 361 | 361 | ||
| 362 | If you want to add an image, you should use the ``kernel-figure`` and | 362 | If you want to add an image, you should use the ``kernel-figure`` and |
| 363 | ``kernel-image`` directives. E.g. to insert a figure with a scalable | 363 | ``kernel-image`` directives. E.g. to insert a figure with a scalable |
| 364 | image format use SVG (:ref:`svg_image_example`):: | 364 | image format, use SVG (:ref:`svg_image_example`):: |
| 365 | 365 | ||
| 366 | .. kernel-figure:: svg_image.svg | 366 | .. kernel-figure:: svg_image.svg |
| 367 | :alt: simple SVG image | 367 | :alt: simple SVG image |
| @@ -375,7 +375,7 @@ image format use SVG (:ref:`svg_image_example`):: · 7 unmodified lines | |||
| 375 | 375 | ||
| 376 | SVG image example | 376 | SVG image example |
| 377 | 377 | ||
| 378 | The kernel figure (and image) directive support **DOT** formatted files, see | 378 | The kernel figure (and image) directive supports **DOT** formatted files, see |
| 379 | 379 | ||
| 380 | * DOT: http://graphviz.org/pdf/dotguide.pdf | 380 | * DOT: http://graphviz.org/pdf/dotguide.pdf |
| 381 | * Graphviz: http://www.graphviz.org/content/dot-language | 381 | * Graphviz: http://www.graphviz.org/content/dot-language |
| @@ -394,7 +394,7 @@ A simple example (:ref:`hello_dot_file`):: · 12 unmodified lines | |||
| 394 | 394 | ||
| 395 | DOT's hello world example | 395 | DOT's hello world example |
| 396 | 396 | ||
| 397 | Embed *render* markups (or languages) like Graphviz's **DOT** is provided by the | 397 | Embedded *render* markups (or languages) like Graphviz's **DOT** are provided by the |
| 398 | ``kernel-render`` directives.:: | 398 | ``kernel-render`` directives.:: |
| 399 | 399 | ||
| 400 | .. kernel-render:: DOT | 400 | .. kernel-render:: DOT |
| @@ -406,7 +406,7 @@ Embed *render* markups (or languages) like Graphviz's **DOT** is provided by the · 5 unmodified lines | |||
| 406 | } | 406 | } |
| 407 | 407 | ||
| 408 | How this will be rendered depends on the installed tools. If Graphviz is | 408 | How this will be rendered depends on the installed tools. If Graphviz is |
| 409 | installed, you will see an vector image. If not the raw markup is inserted as | 409 | installed, you will see a vector image. If not, the raw markup is inserted as |
| 410 | *literal-block* (:ref:`hello_dot_render`). | 410 | *literal-block* (:ref:`hello_dot_render`). |
| 411 | 411 | ||
| 412 | .. _hello_dot_render: | 412 | .. _hello_dot_render: |
| @@ -421,8 +421,8 @@ installed, you will see an vector image. If not the raw markup is inserted as · 8 unmodified lines | |||
| 421 | 421 | ||
| 422 | The *render* directive has all the options known from the *figure* directive, | 422 | The *render* directive has all the options known from the *figure* directive, |
| 423 | plus option ``caption``. If ``caption`` has a value, a *figure* node is | 423 | plus option ``caption``. If ``caption`` has a value, a *figure* node is |
| 424 | inserted. If not, a *image* node is inserted. A ``caption`` is also needed, if | 424 | inserted. If not, an *image* node is inserted. A ``caption`` is also needed, if |
| 425 | you want to refer it (:ref:`hello_svg_render`). | 425 | you want to refer to it (:ref:`hello_svg_render`). |
| 426 | 426 | ||
| 427 | Embedded **SVG**:: | 427 | Embedded **SVG**:: |
| 428 | 428 | ||
| @@ -586,6 +586,14 @@ without significant effort. · 585 unmodified lines | |||
| 586 | The advantage of mounting with the "volatile" option is that all forms of | 586 | The advantage of mounting with the "volatile" option is that all forms of |
| 587 | sync calls to the upper filesystem are omitted. | 587 | sync calls to the upper filesystem are omitted. |
| 588 | 588 | ||
| 589 | In order to avoid a giving a false sense of safety, the syncfs (and fsync) | ||
| 590 | semantics of volatile mounts are slightly different than that of the rest of | ||
| 591 | VFS. If any writeback error occurs on the upperdir's filesystem after a | ||
| 592 | volatile mount takes place, all sync functions will return an error. Once this | ||
| 593 | condition is reached, the filesystem will not recover, and every subsequent sync | ||
| 594 | call will return an error, even if the upperdir has not experience a new error | ||
| 595 | since the last sync call. | ||
| 596 | |||
| 589 | When overlay is mounted with "volatile" option, the directory | 597 | When overlay is mounted with "volatile" option, the directory |
| 590 | "$workdir/work/incompat/volatile" is created. During next mount, overlay | 598 | "$workdir/work/incompat/volatile" is created. During next mount, overlay |
| 591 | checks for this directory and refuses to mount if present. This is a strong | 599 | checks for this directory and refuses to mount if present. This is a strong |
| @@ -50,8 +50,8 @@ The following files belong to it: · 49 unmodified lines | |||
| 50 | 0x00000010 Memory Uncorrectable non-fatal | 50 | 0x00000010 Memory Uncorrectable non-fatal |
| 51 | 0x00000020 Memory Uncorrectable fatal | 51 | 0x00000020 Memory Uncorrectable fatal |
| 52 | 0x00000040 PCI Express Correctable | 52 | 0x00000040 PCI Express Correctable |
| 53 | 0x00000080 PCI Express Uncorrectable fatal | 53 | 0x00000080 PCI Express Uncorrectable non-fatal |
| 54 | 0x00000100 PCI Express Uncorrectable non-fatal | 54 | 0x00000100 PCI Express Uncorrectable fatal |
| 55 | 0x00000200 Platform Correctable | 55 | 0x00000200 Platform Correctable |
| 56 | 0x00000400 Platform Uncorrectable non-fatal | 56 | 0x00000400 Platform Uncorrectable non-fatal |
| 57 | 0x00000800 Platform Uncorrectable fatal | 57 | 0x00000800 Platform Uncorrectable fatal |
| @@ -1,7 +1,7 @@ | |||
| 1 | .. SPDX-License-Identifier: GPL-2.0-or-later | 1 | .. SPDX-License-Identifier: GPL-2.0-or-later |
| 2 | 2 | ||
| 3 | Kernel driver sbtsi_temp | 3 | Kernel driver sbtsi_temp |
| 4 | ================== | 4 | ======================== |
| 5 | 5 | ||
| 6 | Supported hardware: | 6 | Supported hardware: |
| 7 | 7 | ||
| @@ -11,16 +11,13 @@ compiler [1]_. They are useful for runtime instrumentation and static analysis. · 10 unmodified lines | |||
| 11 | We can analyse, change and add further code during compilation via | 11 | We can analyse, change and add further code during compilation via |
| 12 | callbacks [2]_, GIMPLE [3]_, IPA [4]_ and RTL passes [5]_. | 12 | callbacks [2]_, GIMPLE [3]_, IPA [4]_ and RTL passes [5]_. |
| 13 | 13 | ||
| 14 | The GCC plugin infrastructure of the kernel supports all gcc versions from | 14 | The GCC plugin infrastructure of the kernel supports building out-of-tree |
| 15 | 4.5 to 6.0, building out-of-tree modules, cross-compilation and building in a | 15 | modules, cross-compilation and building in a separate directory. |
| 16 | separate directory. | 16 | Plugin source files have to be compilable by a C++ compiler. |
| 17 | Plugin source files have to be compilable by both a C and a C++ compiler as well | ||
| 18 | because gcc versions 4.5 and 4.6 are compiled by a C compiler, | ||
| 19 | gcc-4.7 can be compiled by a C or a C++ compiler, | ||
| 20 | and versions 4.8+ can only be compiled by a C++ compiler. | ||
| 21 | 17 | ||
| 22 | Currently the GCC plugin infrastructure supports only the x86, arm, arm64 and | 18 | Currently the GCC plugin infrastructure supports only some architectures. |
| 23 | powerpc architectures. | 19 | Grep "select HAVE_GCC_PLUGINS" to find out which architectures support |
| 20 | GCC plugins. | ||
| 24 | 21 | ||
| 25 | This infrastructure was ported from grsecurity [6]_ and PaX [7]_. | 22 | This infrastructure was ported from grsecurity [6]_ and PaX [7]_. |
| 26 | 23 | ||
| @@ -47,20 +44,13 @@ Files · 20 unmodified lines | |||
| 47 | This is a compatibility header for GCC plugins. | 44 | This is a compatibility header for GCC plugins. |
| 48 | It should be always included instead of individual gcc headers. | 45 | It should be always included instead of individual gcc headers. |
| 49 | 46 | ||
| 50 | **$(src)/scripts/gcc-plugin.sh** | ||
| 51 | |||
| 52 | This script checks the availability of the included headers in | ||
| 53 | gcc-common.h and chooses the proper host compiler to build the plugins | ||
| 54 | (gcc-4.7 can be built by either gcc or g++). | ||
| 55 | |||
| 56 | **$(src)/scripts/gcc-plugins/gcc-generate-gimple-pass.h, | 47 | **$(src)/scripts/gcc-plugins/gcc-generate-gimple-pass.h, |
| 57 | $(src)/scripts/gcc-plugins/gcc-generate-ipa-pass.h, | 48 | $(src)/scripts/gcc-plugins/gcc-generate-ipa-pass.h, |
| 58 | $(src)/scripts/gcc-plugins/gcc-generate-simple_ipa-pass.h, | 49 | $(src)/scripts/gcc-plugins/gcc-generate-simple_ipa-pass.h, |
| 59 | $(src)/scripts/gcc-plugins/gcc-generate-rtl-pass.h** | 50 | $(src)/scripts/gcc-plugins/gcc-generate-rtl-pass.h** |
| 60 | 51 | ||
| 61 | These headers automatically generate the registration structures for | 52 | These headers automatically generate the registration structures for |
| 62 | GIMPLE, SIMPLE_IPA, IPA and RTL passes. They support all gcc versions | 53 | GIMPLE, SIMPLE_IPA, IPA and RTL passes. |
| 63 | from 4.5 to 6.0. | ||
| 64 | They should be preferred to creating the structures by hand. | 54 | They should be preferred to creating the structures by hand. |
| 65 | 55 | ||
| 66 | 56 | ||
| @@ -68,21 +58,25 @@ Usage · 1 unmodified line | |||
| 68 | ===== | 58 | ===== |
| 69 | 59 | ||
| 70 | You must install the gcc plugin headers for your gcc version, | 60 | You must install the gcc plugin headers for your gcc version, |
| 71 | e.g., on Ubuntu for gcc-4.9:: | 61 | e.g., on Ubuntu for gcc-10:: |
| 72 | 62 | ||
| 73 | apt-get install gcc-4.9-plugin-dev | 63 | apt-get install gcc-10-plugin-dev |
| 74 | 64 | ||
| 75 | Or on Fedora:: | 65 | Or on Fedora:: |
| 76 | 66 | ||
| 77 | dnf install gcc-plugin-devel | 67 | dnf install gcc-plugin-devel |
| 78 | 68 | ||
| 79 | Enable a GCC plugin based feature in the kernel config:: | 69 | Enable the GCC plugin infrastructure and some plugin(s) you want to use |
| 70 | in the kernel config:: | ||
| 80 | 71 | ||
| 81 | CONFIG_GCC_PLUGIN_CYC_COMPLEXITY = y | 72 | CONFIG_GCC_PLUGINS=y |
| 73 | CONFIG_GCC_PLUGIN_CYC_COMPLEXITY=y | ||
| 74 | CONFIG_GCC_PLUGIN_LATENT_ENTROPY=y | ||
| 75 | ... | ||
| 82 | 76 | ||
| 83 | To compile only the plugin(s):: | 77 | To compile the minimum tool set including the plugin(s):: |
| 84 | 78 | ||
| 85 | make gcc-plugins | 79 | make scripts |
| 86 | 80 | ||
| 87 | or just run the kernel make and compile the whole kernel with | 81 | or just run the kernel make and compile the whole kernel with |
| 88 | the cyclomatic complexity GCC plugin. | 82 | the cyclomatic complexity GCC plugin. |
| @@ -91,7 +85,8 @@ the cyclomatic complexity GCC plugin. · 2 unmodified lines | |||
| 91 | 4. How to add a new GCC plugin | 85 | 4. How to add a new GCC plugin |
| 92 | ============================== | 86 | ============================== |
| 93 | 87 | ||
| 94 | The GCC plugins are in $(src)/scripts/gcc-plugins/. You can use a file or a directory | 88 | The GCC plugins are in scripts/gcc-plugins/. You need to put plugin source files |
| 95 | here. It must be added to $(src)/scripts/gcc-plugins/Makefile, | 89 | right under scripts/gcc-plugins/. Creating subdirectories is not supported. |
| 96 | $(src)/scripts/Makefile.gcc-plugins and $(src)/arch/Kconfig. | 90 | It must be added to scripts/gcc-plugins/Makefile, scripts/Makefile.gcc-plugins |
| 91 | and a relevant Kconfig file. | ||
| 97 | See the cyc_complexity_plugin.c (CONFIG_GCC_PLUGIN_CYC_COMPLEXITY) GCC plugin. | 92 | See the cyc_complexity_plugin.c (CONFIG_GCC_PLUGIN_CYC_COMPLEXITY) GCC plugin. |
| @@ -63,6 +63,50 @@ They can be enabled individually. The full list of the parameters: :: · 62 unmodified lines | |||
| 63 | Currently, the integrated assembler is disabled by default. You can pass | 63 | Currently, the integrated assembler is disabled by default. You can pass |
| 64 | ``LLVM_IAS=1`` to enable it. | 64 | ``LLVM_IAS=1`` to enable it. |
| 65 | 65 | ||
| 66 | Supported Architectures | ||
| 67 | ----------------------- | ||
| 68 | |||
| 69 | LLVM does not target all of the architectures that Linux supports and | ||
| 70 | just because a target is supported in LLVM does not mean that the kernel | ||
| 71 | will build or work without any issues. Below is a general summary of | ||
| 72 | architectures that currently work with ``CC=clang`` or ``LLVM=1``. Level | ||
| 73 | of support corresponds to "S" values in the MAINTAINERS files. If an | ||
| 74 | architecture is not present, it either means that LLVM does not target | ||
| 75 | it or there are known issues. Using the latest stable version of LLVM or | ||
| 76 | even the development tree will generally yield the best results. | ||
| 77 | An architecture's ``defconfig`` is generally expected to work well, | ||
| 78 | certain configurations may have problems that have not been uncovered | ||
| 79 | yet. Bug reports are always welcome at the issue tracker below! | ||
| 80 | |||
| 81 | .. list-table:: | ||
| 82 | :widths: 10 10 10 | ||
| 83 | :header-rows: 1 | ||
| 84 | |||
| 85 | * - Architecture | ||
| 86 | - Level of support | ||
| 87 | - ``make`` command | ||
| 88 | * - arm | ||
| 89 | - Supported | ||
| 90 | - ``LLVM=1`` | ||
| 91 | * - arm64 | ||
| 92 | - Supported | ||
| 93 | - ``LLVM=1`` | ||
| 94 | * - mips | ||
| 95 | - Maintained | ||
| 96 | - ``CC=clang`` | ||
| 97 | * - powerpc | ||
| 98 | - Maintained | ||
| 99 | - ``CC=clang`` | ||
| 100 | * - riscv | ||
| 101 | - Maintained | ||
| 102 | - ``CC=clang`` | ||
| 103 | * - s390 | ||
| 104 | - Maintained | ||
| 105 | - ``CC=clang`` | ||
| 106 | * - x86 | ||
| 107 | - Supported | ||
| 108 | - ``LLVM=1`` | ||
| 109 | |||
| 66 | Getting Help | 110 | Getting Help |
| 67 | ------------ | 111 | ------------ |
| 68 | 112 | ||
| @@ -598,7 +598,7 @@ more details, with real examples. · 597 unmodified lines | |||
| 598 | explicitly added to $(targets). | 598 | explicitly added to $(targets). |
| 599 | 599 | ||
| 600 | Assignments to $(targets) are without $(obj)/ prefix. if_changed may be | 600 | Assignments to $(targets) are without $(obj)/ prefix. if_changed may be |
| 601 | used in conjunction with custom rules as defined in "3.9 Custom Rules". | 601 | used in conjunction with custom rules as defined in "3.11 Custom Rules". |
| 602 | 602 | ||
| 603 | Note: It is a typical mistake to forget the FORCE prerequisite. | 603 | Note: It is a typical mistake to forget the FORCE prerequisite. |
| 604 | Another common pitfall is that whitespace is sometimes significant; for | 604 | Another common pitfall is that whitespace is sometimes significant; for |
| @@ -755,7 +755,7 @@ more details, with real examples. · 150 unmodified lines | |||
| 755 | bits on the scripts nonetheless. | 755 | bits on the scripts nonetheless. |
| 756 | 756 | ||
| 757 | Kbuild provides variables $(CONFIG_SHELL), $(AWK), $(PERL), | 757 | Kbuild provides variables $(CONFIG_SHELL), $(AWK), $(PERL), |
| 758 | $(PYTHON) and $(PYTHON3) to refer to interpreters for the respective | 758 | and $(PYTHON3) to refer to interpreters for the respective |
| 759 | scripts. | 759 | scripts. |
| 760 | 760 | ||
| 761 | Example:: | 761 | Example:: |
| @@ -118,11 +118,11 @@ spinlock, but you may block holding a mutex. If you can't lock a mutex, · 117 unmodified lines | |||
| 118 | your task will suspend itself, and be woken up when the mutex is | 118 | your task will suspend itself, and be woken up when the mutex is |
| 119 | released. This means the CPU can do something else while you are | 119 | released. This means the CPU can do something else while you are |
| 120 | waiting. There are many cases when you simply can't sleep (see | 120 | waiting. There are many cases when you simply can't sleep (see |
| 121 | `What Functions Are Safe To Call From Interrupts? <#sleeping-things>`__), | 121 | `What Functions Are Safe To Call From Interrupts?`_), |
| 122 | and so have to use a spinlock instead. | 122 | and so have to use a spinlock instead. |
| 123 | 123 | ||
| 124 | Neither type of lock is recursive: see | 124 | Neither type of lock is recursive: see |
| 125 | `Deadlock: Simple and Advanced <#deadlock>`__. | 125 | `Deadlock: Simple and Advanced`_. |
| 126 | 126 | ||
| 127 | Locks and Uniprocessor Kernels | 127 | Locks and Uniprocessor Kernels |
| 128 | ------------------------------ | 128 | ------------------------------ |
| @@ -179,7 +179,7 @@ perfect world). · 50 unmodified lines | |||
| 179 | 179 | ||
| 180 | Note that you can also use spin_lock_irq() or | 180 | Note that you can also use spin_lock_irq() or |
| 181 | spin_lock_irqsave() here, which stop hardware interrupts | 181 | spin_lock_irqsave() here, which stop hardware interrupts |
| 182 | as well: see `Hard IRQ Context <#hard-irq-context>`__. | 182 | as well: see `Hard IRQ Context`_. |
| 183 | 183 | ||
| 184 | This works perfectly for UP as well: the spin lock vanishes, and this | 184 | This works perfectly for UP as well: the spin lock vanishes, and this |
| 185 | macro simply becomes local_bh_disable() | 185 | macro simply becomes local_bh_disable() |
| @@ -230,7 +230,7 @@ The Same Softirq · 44 unmodified lines | |||
| 230 | ~~~~~~~~~~~~~~~~ | 230 | ~~~~~~~~~~~~~~~~ |
| 231 | 231 | ||
| 232 | The same softirq can run on the other CPUs: you can use a per-CPU array | 232 | The same softirq can run on the other CPUs: you can use a per-CPU array |
| 233 | (see `Per-CPU Data <#per-cpu-data>`__) for better performance. If you're | 233 | (see `Per-CPU Data`_) for better performance. If you're |
| 234 | going so far as to use a softirq, you probably care about scalable | 234 | going so far as to use a softirq, you probably care about scalable |
| 235 | performance enough to justify the extra complexity. | 235 | performance enough to justify the extra complexity. |
| 236 | 236 | ||
| @@ -164,46 +164,56 @@ Devlink health reporters · 163 unmodified lines | |||
| 164 | 164 | ||
| 165 | NPA Reporters | 165 | NPA Reporters |
| 166 | ------------- | 166 | ------------- |
| 167 | The NPA reporters are responsible for reporting and recovering the following group of errors | 167 | The NPA reporters are responsible for reporting and recovering the following group of errors: |
| 168 | |||
| 168 | 1. GENERAL events | 169 | 1. GENERAL events |
| 170 | |||
| 169 | - Error due to operation of unmapped PF. | 171 | - Error due to operation of unmapped PF. |
| 170 | - Error due to disabled alloc/free for other HW blocks (NIX, SSO, TIM, DPI and AURA). | 172 | - Error due to disabled alloc/free for other HW blocks (NIX, SSO, TIM, DPI and AURA). |
| 173 | |||
| 171 | 2. ERROR events | 174 | 2. ERROR events |
| 175 | |||
| 172 | - Fault due to NPA_AQ_INST_S read or NPA_AQ_RES_S write. | 176 | - Fault due to NPA_AQ_INST_S read or NPA_AQ_RES_S write. |
| 173 | - AQ Doorbell Error. | 177 | - AQ Doorbell Error. |
| 178 | |||
| 174 | 3. RAS events | 179 | 3. RAS events |
| 180 | |||
| 175 | - RAS Error Reporting for NPA_AQ_INST_S/NPA_AQ_RES_S. | 181 | - RAS Error Reporting for NPA_AQ_INST_S/NPA_AQ_RES_S. |
| 182 | |||
| 176 | 4. RVU events | 183 | 4. RVU events |
| 184 | |||
| 177 | - Error due to unmapped slot. | 185 | - Error due to unmapped slot. |
| 178 | 186 | ||
| 179 | Sample Output | 187 | Sample Output:: |
| 180 | ------------- | 188 | |
| 181 | ~# devlink health | 189 | ~# devlink health |
| 182 | pci/0002:01:00.0: | 190 | pci/0002:01:00.0: |
| 183 | reporter hw_npa_intr | 191 | reporter hw_npa_intr |
| 184 | state healthy error 2872 recover 2872 last_dump_date 2020-12-10 last_dump_time 09:39:09 grace_period 0 auto_recover true auto_dump true | 192 | state healthy error 2872 recover 2872 last_dump_date 2020-12-10 last_dump_time 09:39:09 grace_period 0 auto_recover true auto_dump true |
| 185 | reporter hw_npa_gen | 193 | reporter hw_npa_gen |
| 186 | state healthy error 2872 recover 2872 last_dump_date 2020-12-11 last_dump_time 04:43:04 grace_period 0 auto_recover true auto_dump true | 194 | state healthy error 2872 recover 2872 last_dump_date 2020-12-11 last_dump_time 04:43:04 grace_period 0 auto_recover true auto_dump true |
| 187 | reporter hw_npa_err | 195 | reporter hw_npa_err |
| 188 | state healthy error 2871 recover 2871 last_dump_date 2020-12-10 last_dump_time 09:39:17 grace_period 0 auto_recover true auto_dump true | 196 | state healthy error 2871 recover 2871 last_dump_date 2020-12-10 last_dump_time 09:39:17 grace_period 0 auto_recover true auto_dump true |
| 189 | reporter hw_npa_ras | 197 | reporter hw_npa_ras |
| 190 | state healthy error 0 recover 0 last_dump_date 2020-12-10 last_dump_time 09:32:40 grace_period 0 auto_recover true auto_dump true | 198 | state healthy error 0 recover 0 last_dump_date 2020-12-10 last_dump_time 09:32:40 grace_period 0 auto_recover true auto_dump true |
| 191 | 199 | ||
| 192 | Each reporter dumps the | 200 | Each reporter dumps the |
| 201 | |||
| 193 | - Error Type | 202 | - Error Type |
| 194 | - Error Register value | 203 | - Error Register value |
| 195 | - Reason in words | 204 | - Reason in words |
| 196 | 205 | ||
| 197 | For eg: | 206 | For example:: |
| 198 | ~# devlink health dump show pci/0002:01:00.0 reporter hw_npa_gen | 207 | |
| 199 | NPA_AF_GENERAL: | 208 | ~# devlink health dump show pci/0002:01:00.0 reporter hw_npa_gen |
| 200 | NPA General Interrupt Reg : 1 | 209 | NPA_AF_GENERAL: |
| 201 | NIX0: free disabled RX | 210 | NPA General Interrupt Reg : 1 |
| 202 | ~# devlink health dump show pci/0002:01:00.0 reporter hw_npa_intr | 211 | NIX0: free disabled RX |
| 203 | NPA_AF_RVU: | 212 | ~# devlink health dump show pci/0002:01:00.0 reporter hw_npa_intr |
| 204 | NPA RVU Interrupt Reg : 1 | 213 | NPA_AF_RVU: |
| 205 | Unmap Slot Error | 214 | NPA RVU Interrupt Reg : 1 |
| 206 | ~# devlink health dump show pci/0002:01:00.0 reporter hw_npa_err | 215 | Unmap Slot Error |
| 207 | NPA_AF_ERR: | 216 | ~# devlink health dump show pci/0002:01:00.0 reporter hw_npa_err |
| 208 | NPA Error Interrupt Reg : 4096 | 217 | NPA_AF_ERR: |
| 209 | AQ Doorbell Error | 218 | NPA Error Interrupt Reg : 4096 |
| 219 | AQ Doorbell Error | ||
| @@ -1196,7 +1196,7 @@ icmp_errors_use_inbound_ifaddr - BOOLEAN · 1195 unmodified lines | |||
| 1196 | 1196 | ||
| 1197 | If non-zero, the message will be sent with the primary address of | 1197 | If non-zero, the message will be sent with the primary address of |
| 1198 | the interface that received the packet that caused the icmp error. | 1198 | the interface that received the packet that caused the icmp error. |
| 1199 | This is the behaviour network many administrators will expect from | 1199 | This is the behaviour many network administrators will expect from |
| 1200 | a router. And it can make debugging complicated network layouts | 1200 | a router. And it can make debugging complicated network layouts |
| 1201 | much easier. | 1201 | much easier. |
| 1202 | 1202 | ||
| @@ -1807,12 +1807,24 @@ seg6_flowlabel - INTEGER · 604 unmodified lines | |||
| 1807 | ``conf/default/*``: | 1807 | ``conf/default/*``: |
| 1808 | Change the interface-specific default settings. | 1808 | Change the interface-specific default settings. |
| 1809 | 1809 | ||
| 1810 | These settings would be used during creating new interfaces. | ||
| 1811 | |||
| 1810 | 1812 | ||
| 1811 | ``conf/all/*``: | 1813 | ``conf/all/*``: |
| 1812 | Change all the interface-specific settings. | 1814 | Change all the interface-specific settings. |
| 1813 | 1815 | ||
| 1814 | [XXX: Other special features than forwarding?] | 1816 | [XXX: Other special features than forwarding?] |
| 1815 | 1817 | ||
| 1818 | conf/all/disable_ipv6 - BOOLEAN | ||
| 1819 | Changing this value is same as changing ``conf/default/disable_ipv6`` | ||
| 1820 | setting and also all per-interface ``disable_ipv6`` settings to the same | ||
| 1821 | value. | ||
| 1822 | |||
| 1823 | Reading this value does not have any particular meaning. It does not say | ||
| 1824 | whether IPv6 support is enabled or disabled. Returned value can be 1 | ||
| 1825 | also in the case when some interface has ``disable_ipv6`` set to 0 and | ||
| 1826 | has configured IPv6 addresses. | ||
| 1827 | |||
| 1816 | conf/all/forwarding - BOOLEAN | 1828 | conf/all/forwarding - BOOLEAN |
| 1817 | Enable global IPv6 forwarding between all interfaces. | 1829 | Enable global IPv6 forwarding between all interfaces. |
| 1818 | 1830 | ||
| @@ -6,9 +6,9 @@ · 5 unmodified lines | |||
| 6 | netdev FAQ | 6 | netdev FAQ |
| 7 | ========== | 7 | ========== |
| 8 | 8 | ||
| 9 | Q: What is netdev? | 9 | What is netdev? |
| 10 | ------------------ | 10 | --------------- |
| 11 | A: It is a mailing list for all network-related Linux stuff. This | 11 | It is a mailing list for all network-related Linux stuff. This |
| 12 | includes anything found under net/ (i.e. core code like IPv6) and | 12 | includes anything found under net/ (i.e. core code like IPv6) and |
| 13 | drivers/net (i.e. hardware specific drivers) in the Linux source tree. | 13 | drivers/net (i.e. hardware specific drivers) in the Linux source tree. |
| 14 | 14 | ||
| @@ -25,9 +25,9 @@ Aside from subsystems like that mentioned above, all network-related · 10 unmodified lines | |||
| 25 | Linux development (i.e. RFC, review, comments, etc.) takes place on | 25 | Linux development (i.e. RFC, review, comments, etc.) takes place on |
| 26 | netdev. | 26 | netdev. |
| 27 | 27 | ||
| 28 | Q: How do the changes posted to netdev make their way into Linux? | 28 | How do the changes posted to netdev make their way into Linux? |
| 29 | ----------------------------------------------------------------- | 29 | -------------------------------------------------------------- |
| 30 | A: There are always two trees (git repositories) in play. Both are | 30 | There are always two trees (git repositories) in play. Both are |
| 31 | driven by David Miller, the main network maintainer. There is the | 31 | driven by David Miller, the main network maintainer. There is the |
| 32 | ``net`` tree, and the ``net-next`` tree. As you can probably guess from | 32 | ``net`` tree, and the ``net-next`` tree. As you can probably guess from |
| 33 | the names, the ``net`` tree is for fixes to existing code already in the | 33 | the names, the ``net`` tree is for fixes to existing code already in the |
| @@ -37,9 +37,9 @@ for the future release. You can find the trees here: · 3 unmodified lines | |||
| 37 | - https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git | 37 | - https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git |
| 38 | - https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git | 38 | - https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git |
| 39 | 39 | ||
| 40 | Q: How often do changes from these trees make it to the mainline Linus tree? | 40 | How often do changes from these trees make it to the mainline Linus tree? |
| 41 | ---------------------------------------------------------------------------- | 41 | ------------------------------------------------------------------------- |
| 42 | A: To understand this, you need to know a bit of background information on | 42 | To understand this, you need to know a bit of background information on |
| 43 | the cadence of Linux development. Each new release starts off with a | 43 | the cadence of Linux development. Each new release starts off with a |
| 44 | two week "merge window" where the main maintainers feed their new stuff | 44 | two week "merge window" where the main maintainers feed their new stuff |
| 45 | to Linus for merging into the mainline tree. After the two weeks, the | 45 | to Linus for merging into the mainline tree. After the two weeks, the |
| @@ -81,7 +81,8 @@ focus for ``net`` is on stabilization and bug fixes. · 35 unmodified lines | |||
| 81 | 81 | ||
| 82 | Finally, the vX.Y gets released, and the whole cycle starts over. | 82 | Finally, the vX.Y gets released, and the whole cycle starts over. |
| 83 | 83 | ||
| 84 | Q: So where are we now in this cycle? | 84 | So where are we now in this cycle? |
| 85 | ---------------------------------- | ||
| 85 | 86 | ||
| 86 | Load the mainline (Linus) page here: | 87 | Load the mainline (Linus) page here: |
| 87 | 88 | ||
| @@ -91,9 +92,9 @@ and note the top of the "tags" section. If it is rc1, it is early in · 3 unmodified lines | |||
| 91 | the dev cycle. If it was tagged rc7 a week ago, then a release is | 92 | the dev cycle. If it was tagged rc7 a week ago, then a release is |
| 92 | probably imminent. | 93 | probably imminent. |
| 93 | 94 | ||
| 94 | Q: How do I indicate which tree (net vs. net-next) my patch should be in? | 95 | How do I indicate which tree (net vs. net-next) my patch should be in? |
| 95 | ------------------------------------------------------------------------- | 96 | ---------------------------------------------------------------------- |
| 96 | A: Firstly, think whether you have a bug fix or new "next-like" content. | 97 | Firstly, think whether you have a bug fix or new "next-like" content. |
| 97 | Then once decided, assuming that you use git, use the prefix flag, i.e. | 98 | Then once decided, assuming that you use git, use the prefix flag, i.e. |
| 98 | :: | 99 | :: |
| 99 | 100 | ||
| @@ -105,48 +106,45 @@ in the above is just the subject text of the outgoing e-mail, and you · 5 unmodified lines | |||
| 105 | can manually change it yourself with whatever MUA you are comfortable | 106 | can manually change it yourself with whatever MUA you are comfortable |
| 106 | with. | 107 | with. |
| 107 | 108 | ||
| 108 | Q: I sent a patch and I'm wondering what happened to it? | 109 | I sent a patch and I'm wondering what happened to it - how can I tell whether it got merged? |
| 109 | -------------------------------------------------------- | 110 | -------------------------------------------------------------------------------------------- |
| 110 | Q: How can I tell whether it got merged? | 111 | Start by looking at the main patchworks queue for netdev: |
| 111 | A: Start by looking at the main patchworks queue for netdev: | ||
| 112 | 112 | ||
| 113 | https://patchwork.kernel.org/project/netdevbpf/list/ | 113 | https://patchwork.kernel.org/project/netdevbpf/list/ |
| 114 | 114 | ||
| 115 | The "State" field will tell you exactly where things are at with your | 115 | The "State" field will tell you exactly where things are at with your |
| 116 | patch. | 116 | patch. |
| 117 | 117 | ||
| 118 | Q: The above only says "Under Review". How can I find out more? | 118 | The above only says "Under Review". How can I find out more? |
| 119 | ---------------------------------------------------------------- | 119 | ------------------------------------------------------------- |
| 120 | A: Generally speaking, the patches get triaged quickly (in less than | 120 | Generally speaking, the patches get triaged quickly (in less than |
| 121 | 48h). So be patient. Asking the maintainer for status updates on your | 121 | 48h). So be patient. Asking the maintainer for status updates on your |
| 122 | patch is a good way to ensure your patch is ignored or pushed to the | 122 | patch is a good way to ensure your patch is ignored or pushed to the |
| 123 | bottom of the priority list. | 123 | bottom of the priority list. |
| 124 | 124 | ||
| 125 | Q: I submitted multiple versions of the patch series | 125 | I submitted multiple versions of the patch series. Should I directly update patchwork for the previous versions of these patch series? |
| 126 | ---------------------------------------------------- | 126 | -------------------------------------------------------------------------------------------------------------------------------------- |
| 127 | Q: should I directly update patchwork for the previous versions of these | 127 | No, please don't interfere with the patch status on patchwork, leave |
| 128 | patch series? | ||
| 129 | A: No, please don't interfere with the patch status on patchwork, leave | ||
| 130 | it to the maintainer to figure out what is the most recent and current | 128 | it to the maintainer to figure out what is the most recent and current |
| 131 | version that should be applied. If there is any doubt, the maintainer | 129 | version that should be applied. If there is any doubt, the maintainer |
| 132 | will reply and ask what should be done. | 130 | will reply and ask what should be done. |
| 133 | 131 | ||
| 134 | Q: I made changes to only a few patches in a patch series should I resend only those changed? | 132 | I made changes to only a few patches in a patch series should I resend only those changed? |
| 135 | --------------------------------------------------------------------------------------------- | 133 | ------------------------------------------------------------------------------------------ |
| 136 | A: No, please resend the entire patch series and make sure you do number your | 134 | No, please resend the entire patch series and make sure you do number your |
| 137 | patches such that it is clear this is the latest and greatest set of patches | 135 | patches such that it is clear this is the latest and greatest set of patches |
| 138 | that can be applied. | 136 | that can be applied. |
| 139 | 137 | ||
| 140 | Q: I submitted multiple versions of a patch series and it looks like a version other than the last one has been accepted, what should I do? | 138 | I submitted multiple versions of a patch series and it looks like a version other than the last one has been accepted, what should I do? |
| 141 | ------------------------------------------------------------------------------------------------------------------------------------------- | 139 | ---------------------------------------------------------------------------------------------------------------------------------------- |
| 142 | A: There is no revert possible, once it is pushed out, it stays like that. | 140 | There is no revert possible, once it is pushed out, it stays like that. |
| 143 | Please send incremental versions on top of what has been merged in order to fix | 141 | Please send incremental versions on top of what has been merged in order to fix |
| 144 | the patches the way they would look like if your latest patch series was to be | 142 | the patches the way they would look like if your latest patch series was to be |
| 145 | merged. | 143 | merged. |
| 146 | 144 | ||
| 147 | Q: How can I tell what patches are queued up for backporting to the various stable releases? | 145 | How can I tell what patches are queued up for backporting to the various stable releases? |
| 148 | -------------------------------------------------------------------------------------------- | 146 | ----------------------------------------------------------------------------------------- |
| 149 | A: Normally Greg Kroah-Hartman collects stable commits himself, but for | 147 | Normally Greg Kroah-Hartman collects stable commits himself, but for |
| 150 | networking, Dave collects up patches he deems critical for the | 148 | networking, Dave collects up patches he deems critical for the |
| 151 | networking subsystem, and then hands them off to Greg. | 149 | networking subsystem, and then hands them off to Greg. |
| 152 | 150 | ||
| @@ -169,11 +167,9 @@ simply clone the repo, and then git grep the mainline commit ID, e.g. · 16 unmodified lines | |||
| 169 | releases/3.9.8/ipv6-fix-possible-crashes-in-ip6_cork_release.patch | 167 | releases/3.9.8/ipv6-fix-possible-crashes-in-ip6_cork_release.patch |
| 170 | stable/stable-queue$ | 168 | stable/stable-queue$ |
| 171 | 169 | ||
| 172 | Q: I see a network patch and I think it should be backported to stable. | 170 | I see a network patch and I think it should be backported to stable. Should I request it via stable@vger.kernel.org like the references in the kernel's Documentation/process/stable-kernel-rules.rst file say? |
| 173 | ----------------------------------------------------------------------- | 171 | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 174 | Q: Should I request it via stable@vger.kernel.org like the references in | 172 | No, not for networking. Check the stable queues as per above first |
| 175 | the kernel's Documentation/process/stable-kernel-rules.rst file say? | ||
| 176 | A: No, not for networking. Check the stable queues as per above first | ||
| 177 | to see if it is already queued. If not, then send a mail to netdev, | 173 | to see if it is already queued. If not, then send a mail to netdev, |
| 178 | listing the upstream commit ID and why you think it should be a stable | 174 | listing the upstream commit ID and why you think it should be a stable |
| 179 | candidate. | 175 | candidate. |
| @@ -190,11 +186,9 @@ mainline, the better the odds that it is an OK candidate for stable. So · 10 unmodified lines | |||
| 190 | scrambling to request a commit be added the day after it appears should | 186 | scrambling to request a commit be added the day after it appears should |
| 191 | be avoided. | 187 | be avoided. |
| 192 | 188 | ||
| 193 | Q: I have created a network patch and I think it should be backported to stable. | 189 | I have created a network patch and I think it should be backported to stable. Should I add a Cc: stable@vger.kernel.org like the references in the kernel's Documentation/ directory say? |
| 194 | -------------------------------------------------------------------------------- | 190 | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 195 | Q: Should I add a Cc: stable@vger.kernel.org like the references in the | 191 | No. See above answer. In short, if you think it really belongs in |
| 196 | kernel's Documentation/ directory say? | ||
| 197 | A: No. See above answer. In short, if you think it really belongs in | ||
| 198 | stable, then ensure you write a decent commit log that describes who | 192 | stable, then ensure you write a decent commit log that describes who |
| 199 | gets impacted by the bug fix and how it manifests itself, and when the | 193 | gets impacted by the bug fix and how it manifests itself, and when the |
| 200 | bug was introduced. If you do that properly, then the commit will get | 194 | bug was introduced. If you do that properly, then the commit will get |
| @@ -207,18 +201,18 @@ marker line as described in · 6 unmodified lines | |||
| 207 | :ref:`Documentation/process/submitting-patches.rst <the_canonical_patch_format>` | 201 | :ref:`Documentation/process/submitting-patches.rst <the_canonical_patch_format>` |
| 208 | to temporarily embed that information into the patch that you send. | 202 | to temporarily embed that information into the patch that you send. |
| 209 | 203 | ||
| 210 | Q: Are all networking bug fixes backported to all stable releases? | 204 | Are all networking bug fixes backported to all stable releases? |
| 211 | ------------------------------------------------------------------ | 205 | --------------------------------------------------------------- |
| 212 | A: Due to capacity, Dave could only take care of the backports for the | 206 | Due to capacity, Dave could only take care of the backports for the |
| 213 | last two stable releases. For earlier stable releases, each stable | 207 | last two stable releases. For earlier stable releases, each stable |
| 214 | branch maintainer is supposed to take care of them. If you find any | 208 | branch maintainer is supposed to take care of them. If you find any |
| 215 | patch is missing from an earlier stable branch, please notify | 209 | patch is missing from an earlier stable branch, please notify |
| 216 | stable@vger.kernel.org with either a commit ID or a formal patch | 210 | stable@vger.kernel.org with either a commit ID or a formal patch |
| 217 | backported, and CC Dave and other relevant networking developers. | 211 | backported, and CC Dave and other relevant networking developers. |
| 218 | 212 | ||
| 219 | Q: Is the comment style convention different for the networking content? | 213 | Is the comment style convention different for the networking content? |
| 220 | ------------------------------------------------------------------------ | 214 | --------------------------------------------------------------------- |
| 221 | A: Yes, in a largely trivial way. Instead of this:: | 215 | Yes, in a largely trivial way. Instead of this:: |
| 222 | 216 | ||
| 223 | /* | 217 | /* |
| 224 | * foobar blah blah blah | 218 | * foobar blah blah blah |
| @@ -231,32 +225,30 @@ it is requested that you make it look like this:: · 6 unmodified lines | |||
| 231 | * another line of text | 225 | * another line of text |
| 232 | */ | 226 | */ |
| 233 | 227 | ||
| 234 | Q: I am working in existing code that has the former comment style and not the latter. | 228 | I am working in existing code that has the former comment style and not the latter. Should I submit new code in the former style or the latter? |
| 235 | -------------------------------------------------------------------------------------- | 229 | ----------------------------------------------------------------------------------------------------------------------------------------------- |
| 236 | Q: Should I submit new code in the former style or the latter? | 230 | Make it the latter style, so that eventually all code in the domain |
| 237 | A: Make it the latter style, so that eventually all code in the domain | ||
| 238 | of netdev is of this format. | 231 | of netdev is of this format. |
| 239 | 232 | ||
| 240 | Q: I found a bug that might have possible security implications or similar. | 233 | I found a bug that might have possible security implications or similar. Should I mail the main netdev maintainer off-list? |
| 241 | --------------------------------------------------------------------------- | 234 | --------------------------------------------------------------------------------------------------------------------------- |
| 242 | Q: Should I mail the main netdev maintainer off-list?** | 235 | No. The current netdev maintainer has consistently requested that |
| 243 | A: No. The current netdev maintainer has consistently requested that | ||
| 244 | people use the mailing lists and not reach out directly. If you aren't | 236 | people use the mailing lists and not reach out directly. If you aren't |
| 245 | OK with that, then perhaps consider mailing security@kernel.org or | 237 | OK with that, then perhaps consider mailing security@kernel.org or |
| 246 | reading about http://oss-security.openwall.org/wiki/mailing-lists/distros | 238 | reading about http://oss-security.openwall.org/wiki/mailing-lists/distros |
| 247 | as possible alternative mechanisms. | 239 | as possible alternative mechanisms. |
| 248 | 240 | ||
| 249 | Q: What level of testing is expected before I submit my change? | 241 | What level of testing is expected before I submit my change? |
| 250 | --------------------------------------------------------------- | 242 | ------------------------------------------------------------ |
| 251 | A: If your changes are against ``net-next``, the expectation is that you | 243 | If your changes are against ``net-next``, the expectation is that you |
| 252 | have tested by layering your changes on top of ``net-next``. Ideally | 244 | have tested by layering your changes on top of ``net-next``. Ideally |
| 253 | you will have done run-time testing specific to your change, but at a | 245 | you will have done run-time testing specific to your change, but at a |
| 254 | minimum, your changes should survive an ``allyesconfig`` and an | 246 | minimum, your changes should survive an ``allyesconfig`` and an |
| 255 | ``allmodconfig`` build without new warnings or failures. | 247 | ``allmodconfig`` build without new warnings or failures. |
| 256 | 248 | ||
| 257 | Q: How do I post corresponding changes to user space components? | 249 | How do I post corresponding changes to user space components? |
| 258 | ---------------------------------------------------------------- | 250 | ------------------------------------------------------------- |
| 259 | A: User space code exercising kernel features should be posted | 251 | User space code exercising kernel features should be posted |
| 260 | alongside kernel patches. This gives reviewers a chance to see | 252 | alongside kernel patches. This gives reviewers a chance to see |
| 261 | how any new interface is used and how well it works. | 253 | how any new interface is used and how well it works. |
| 262 | 254 | ||
| @@ -280,9 +272,9 @@ to the mailing list, e.g.:: · 17 unmodified lines | |||
| 280 | Posting as one thread is discouraged because it confuses patchwork | 272 | Posting as one thread is discouraged because it confuses patchwork |
| 281 | (as of patchwork 2.2.2). | 273 | (as of patchwork 2.2.2). |
| 282 | 274 | ||
| 283 | Q: Any other tips to help ensure my net/net-next patch gets OK'd? | 275 | Any other tips to help ensure my net/net-next patch gets OK'd? |
| 284 | ----------------------------------------------------------------- | 276 | -------------------------------------------------------------- |
| 285 | A: Attention to detail. Re-read your own work as if you were the | 277 | Attention to detail. Re-read your own work as if you were the |
| 286 | reviewer. You can start with using ``checkpatch.pl``, perhaps even with | 278 | reviewer. You can start with using ``checkpatch.pl``, perhaps even with |
| 287 | the ``--strict`` flag. But do not be mindlessly robotic in doing so. | 279 | the ``--strict`` flag. But do not be mindlessly robotic in doing so. |
| 288 | If your change is a bug fix, make sure your commit log indicates the | 280 | If your change is a bug fix, make sure your commit log indicates the |
| @@ -10,18 +10,177 @@ Introduction · 9 unmodified lines | |||
| 10 | The following is a random collection of documentation regarding | 10 | The following is a random collection of documentation regarding |
| 11 | network devices. | 11 | network devices. |
| 12 | 12 | ||
| 13 | struct net_device allocation rules | 13 | struct net_device lifetime rules |
| 14 | ================================== | 14 | ================================ |
| 15 | Network device structures need to persist even after module is unloaded and | 15 | Network device structures need to persist even after module is unloaded and |
| 16 | must be allocated with alloc_netdev_mqs() and friends. | 16 | must be allocated with alloc_netdev_mqs() and friends. |
| 17 | If device has registered successfully, it will be freed on last use | 17 | If device has registered successfully, it will be freed on last use |
| 18 | by free_netdev(). This is required to handle the pathologic case cleanly | 18 | by free_netdev(). This is required to handle the pathological case cleanly |
| 19 | (example: rmmod mydriver </sys/class/net/myeth/mtu ) | 19 | (example: ``rmmod mydriver </sys/class/net/myeth/mtu``) |
| 20 | 20 | ||
| 21 | alloc_netdev_mqs()/alloc_netdev() reserve extra space for driver | 21 | alloc_netdev_mqs() / alloc_netdev() reserve extra space for driver |
| 22 | private data which gets freed when the network device is freed. If | 22 | private data which gets freed when the network device is freed. If |
| 23 | separately allocated data is attached to the network device | 23 | separately allocated data is attached to the network device |
| 24 | (netdev_priv(dev)) then it is up to the module exit handler to free that. | 24 | (netdev_priv()) then it is up to the module exit handler to free that. |
| 25 | |||
| 26 | There are two groups of APIs for registering struct net_device. | ||
| 27 | First group can be used in normal contexts where ``rtnl_lock`` is not already | ||
| 28 | held: register_netdev(), unregister_netdev(). | ||
| 29 | Second group can be used when ``rtnl_lock`` is already held: | ||
| 30 | register_netdevice(), unregister_netdevice(), free_netdevice(). | ||
| 31 | |||
| 32 | Simple drivers | ||
| 33 | -------------- | ||
| 34 | |||
| 35 | Most drivers (especially device drivers) handle lifetime of struct net_device | ||
| 36 | in context where ``rtnl_lock`` is not held (e.g. driver probe and remove paths). | ||
| 37 | |||
| 38 | In that case the struct net_device registration is done using | ||
| 39 | the register_netdev(), and unregister_netdev() functions: | ||
| 40 | |||
| 41 | .. code-block:: c | ||
| 42 | |||
| 43 | int probe() | ||
| 44 | { | ||
| 45 | struct my_device_priv *priv; | ||
| 46 | int err; | ||
| 47 | |||
| 48 | dev = alloc_netdev_mqs(...); | ||
| 49 | if (!dev) | ||
| 50 | return -ENOMEM; | ||
| 51 | priv = netdev_priv(dev); | ||
| 52 | |||
| 53 | /* ... do all device setup before calling register_netdev() ... | ||
| 54 | */ | ||
| 55 | |||
| 56 | err = register_netdev(dev); | ||
| 57 | if (err) | ||
| 58 | goto err_undo; | ||
| 59 | |||
| 60 | /* net_device is visible to the user! */ | ||
| 61 | |||
| 62 | err_undo: | ||
| 63 | /* ... undo the device setup ... */ | ||
| 64 | free_netdev(dev); | ||
| 65 | return err; | ||
| 66 | } | ||
| 67 | |||
| 68 | void remove() | ||
| 69 | { | ||
| 70 | unregister_netdev(dev); | ||
| 71 | free_netdev(dev); | ||
| 72 | } | ||
| 73 | |||
| 74 | Note that after calling register_netdev() the device is visible in the system. | ||
| 75 | Users can open it and start sending / receiving traffic immediately, | ||
| 76 | or run any other callback, so all initialization must be done prior to | ||
| 77 | registration. | ||
| 78 | |||
| 79 | unregister_netdev() closes the device and waits for all users to be done | ||
| 80 | with it. The memory of struct net_device itself may still be referenced | ||
| 81 | by sysfs but all operations on that device will fail. | ||
| 82 | |||
| 83 | free_netdev() can be called after unregister_netdev() returns on when | ||
| 84 | register_netdev() failed. | ||
| 85 | |||
| 86 | Device management under RTNL | ||
| 87 | ---------------------------- | ||
| 88 | |||
| 89 | Registering struct net_device while in context which already holds | ||
| 90 | the ``rtnl_lock`` requires extra care. In those scenarios most drivers | ||
| 91 | will want to make use of struct net_device's ``needs_free_netdev`` | ||
| 92 | and ``priv_destructor`` members for freeing of state. | ||
| 93 | |||
| 94 | Example flow of netdev handling under ``rtnl_lock``: | ||
| 95 | |||
| 96 | .. code-block:: c | ||
| 97 | |||
| 98 | static void my_setup(struct net_device *dev) | ||
| 99 | { | ||
| 100 | dev->needs_free_netdev = true; | ||
| 101 | } | ||
| 102 | |||
| 103 | static void my_destructor(struct net_device *dev) | ||
| 104 | { | ||
| 105 | some_obj_destroy(priv->obj); | ||
| 106 | some_uninit(priv); | ||
| 107 | } | ||
| 108 | |||
| 109 | int create_link() | ||
| 110 | { | ||
| 111 | struct my_device_priv *priv; | ||
| 112 | int err; | ||
| 113 | |||
| 114 | ASSERT_RTNL(); | ||
| 115 | |||
| 116 | dev = alloc_netdev(sizeof(*priv), "net%d", NET_NAME_UNKNOWN, my_setup); | ||
| 117 | if (!dev) | ||
| 118 | return -ENOMEM; | ||
| 119 | priv = netdev_priv(dev); | ||
| 120 | |||
| 121 | /* Implicit constructor */ | ||
| 122 | err = some_init(priv); | ||
| 123 | if (err) | ||
| 124 | goto err_free_dev; | ||
| 125 | |||
| 126 | priv->obj = some_obj_create(); | ||
| 127 | if (!priv->obj) { | ||
| 128 | err = -ENOMEM; | ||
| 129 | goto err_some_uninit; | ||
| 130 | } | ||
| 131 | /* End of constructor, set the destructor: */ | ||
| 132 | dev->priv_destructor = my_destructor; | ||
| 133 | |||
| 134 | err = register_netdevice(dev); | ||
| 135 | if (err) | ||
| 136 | /* register_netdevice() calls destructor on failure */ | ||
| 137 | goto err_free_dev; | ||
| 138 | |||
| 139 | /* If anything fails now unregister_netdevice() (or unregister_netdev()) | ||
| 140 | * will take care of calling my_destructor and free_netdev(). | ||
| 141 | */ | ||
| 142 | |||
| 143 | return 0; | ||
| 144 | |||
| 145 | err_some_uninit: | ||
| 146 | some_uninit(priv); | ||
| 147 | err_free_dev: | ||
| 148 | free_netdev(dev); | ||
| 149 | return err; | ||
| 150 | } | ||
| 151 | |||
| 152 | If struct net_device.priv_destructor is set it will be called by the core | ||
| 153 | some time after unregister_netdevice(), it will also be called if | ||
| 154 | register_netdevice() fails. The callback may be invoked with or without | ||
| 155 | ``rtnl_lock`` held. | ||
| 156 | |||
| 157 | There is no explicit constructor callback, driver "constructs" the private | ||
| 158 | netdev state after allocating it and before registration. | ||
| 159 | |||
| 160 | Setting struct net_device.needs_free_netdev makes core call free_netdevice() | ||
| 161 | automatically after unregister_netdevice() when all references to the device | ||
| 162 | are gone. It only takes effect after a successful call to register_netdevice() | ||
| 163 | so if register_netdevice() fails driver is responsible for calling | ||
| 164 | free_netdev(). | ||
| 165 | |||
| 166 | free_netdev() is safe to call on error paths right after unregister_netdevice() | ||
| 167 | or when register_netdevice() fails. Parts of netdev (de)registration process | ||
| 168 | happen after ``rtnl_lock`` is released, therefore in those cases free_netdev() | ||
| 169 | will defer some of the processing until ``rtnl_lock`` is released. | ||
| 170 | |||
| 171 | Devices spawned from struct rtnl_link_ops should never free the | ||
| 172 | struct net_device directly. | ||
| 173 | |||
| 174 | .ndo_init and .ndo_uninit | ||
| 175 | ~~~~~~~~~~~~~~~~~~~~~~~~~ | ||
| 176 | |||
| 177 | ``.ndo_init`` and ``.ndo_uninit`` callbacks are called during net_device | ||
| 178 | registration and de-registration, under ``rtnl_lock``. Drivers can use | ||
| 179 | those e.g. when parts of their init process need to run under ``rtnl_lock``. | ||
| 180 | |||
| 181 | ``.ndo_init`` runs before device is visible in the system, ``.ndo_uninit`` | ||
| 182 | runs during de-registering after device is closed but other subsystems | ||
| 183 | may still have outstanding references to the netdevice. | ||
| 25 | 184 | ||
| 26 | MTU | 185 | MTU |
| 27 | === | 186 | === |
| @@ -64,8 +223,8 @@ ndo_do_ioctl: · 36 unmodified lines | |||
| 64 | Context: process | 223 | Context: process |
| 65 | 224 | ||
| 66 | ndo_get_stats: | 225 | ndo_get_stats: |
| 67 | Synchronization: dev_base_lock rwlock. | 226 | Synchronization: rtnl_lock() semaphore, dev_base_lock rwlock, or RCU. |
| 68 | Context: nominally process, but don't sleep inside an rwlock | 227 | Context: atomic (can't sleep under rwlock or RCU) |
| 69 | 228 | ||
| 70 | ndo_start_xmit: | 229 | ndo_start_xmit: |
| 71 | Synchronization: __netif_tx_lock spinlock. | 230 | Synchronization: __netif_tx_lock spinlock. |
| @@ -8,7 +8,7 @@ Abstract · 7 unmodified lines | |||
| 8 | ======== | 8 | ======== |
| 9 | 9 | ||
| 10 | This file documents the mmap() facility available with the PACKET | 10 | This file documents the mmap() facility available with the PACKET |
| 11 | socket interface on 2.4/2.6/3.x kernels. This type of sockets is used for | 11 | socket interface. This type of sockets is used for |
| 12 | 12 | ||
| 13 | i) capture network traffic with utilities like tcpdump, | 13 | i) capture network traffic with utilities like tcpdump, |
| 14 | ii) transmit network traffic, or any other that needs raw | 14 | ii) transmit network traffic, or any other that needs raw |
| @@ -25,12 +25,12 @@ Please send your comments to · 10 unmodified lines | |||
| 25 | Why use PACKET_MMAP | 25 | Why use PACKET_MMAP |
| 26 | =================== | 26 | =================== |
| 27 | 27 | ||
| 28 | In Linux 2.4/2.6/3.x if PACKET_MMAP is not enabled, the capture process is very | 28 | Non PACKET_MMAP capture process (plain AF_PACKET) is very |
| 29 | inefficient. It uses very limited buffers and requires one system call to | 29 | inefficient. It uses very limited buffers and requires one system call to |
| 30 | capture each packet, it requires two if you want to get packet's timestamp | 30 | capture each packet, it requires two if you want to get packet's timestamp |
| 31 | (like libpcap always does). | 31 | (like libpcap always does). |
| 32 | 32 | ||
| 33 | In the other hand PACKET_MMAP is very efficient. PACKET_MMAP provides a size | 33 | On the other hand PACKET_MMAP is very efficient. PACKET_MMAP provides a size |
| 34 | configurable circular buffer mapped in user space that can be used to either | 34 | configurable circular buffer mapped in user space that can be used to either |
| 35 | send or receive packets. This way reading packets just needs to wait for them, | 35 | send or receive packets. This way reading packets just needs to wait for them, |
| 36 | most of the time there is no need to issue a single system call. Concerning | 36 | most of the time there is no need to issue a single system call. Concerning |
| @@ -252,8 +252,7 @@ PACKET_MMAP setting constraints · 215 unmodified lines | |||
| 252 | 252 | ||
| 253 | In kernel versions prior to 2.4.26 (for the 2.4 branch) and 2.6.5 (2.6 branch), | 253 | In kernel versions prior to 2.4.26 (for the 2.4 branch) and 2.6.5 (2.6 branch), |
| 254 | the PACKET_MMAP buffer could hold only 32768 frames in a 32 bit architecture or | 254 | the PACKET_MMAP buffer could hold only 32768 frames in a 32 bit architecture or |
| 255 | 16384 in a 64 bit architecture. For information on these kernel versions | 255 | 16384 in a 64 bit architecture. |
| 256 | see http://pusa.uv.es/~ulisses/packet_mmap/packet_mmap.pre-2.4.26_2.6.5.txt | ||
| 257 | 256 | ||
| 258 | Block size limit | 257 | Block size limit |
| 259 | ---------------- | 258 | ---------------- |
| @@ -437,7 +436,7 @@ and the following flags apply: · 177 unmodified lines | |||
| 437 | Capture process | 436 | Capture process |
| 438 | ^^^^^^^^^^^^^^^ | 437 | ^^^^^^^^^^^^^^^ |
| 439 | 438 | ||
| 440 | from include/linux/if_packet.h | 439 | From include/linux/if_packet.h:: |
| 441 | 440 | ||
| 442 | #define TP_STATUS_COPY (1 << 1) | 441 | #define TP_STATUS_COPY (1 << 1) |
| 443 | #define TP_STATUS_LOSING (1 << 2) | 442 | #define TP_STATUS_LOSING (1 << 2) |
| @@ -530,7 +530,10 @@ TLS device feature flags only control adding of new TLS connection · 529 unmodified lines | |||
| 530 | offloads, old connections will remain active after flags are cleared. | 530 | offloads, old connections will remain active after flags are cleared. |
| 531 | 531 | ||
| 532 | TLS encryption cannot be offloaded to devices without checksum calculation | 532 | TLS encryption cannot be offloaded to devices without checksum calculation |
| 533 | offload. Hence, TLS TX device feature flag requires NETIF_F_HW_CSUM being set. | 533 | offload. Hence, TLS TX device feature flag requires TX csum offload being set. |
| 534 | Disabling the latter implies clearing the former. Disabling TX checksum offload | 534 | Disabling the latter implies clearing the former. Disabling TX checksum offload |
| 535 | should not affect old connections, and drivers should make sure checksum | 535 | should not affect old connections, and drivers should make sure checksum |
| 536 | calculation does not break for them. | 536 | calculation does not break for them. |
| 537 | Similarly, device-offloaded TLS decryption implies doing RXCSUM. If the user | ||
| 538 | does not want to enable RX csum offload, TLS RX device feature is disabled | ||
| 539 | as well. | ||
| @@ -249,10 +249,8 @@ features; most of these are found in the "kernel hacking" submenu. Several · 248 unmodified lines | |||
| 249 | of these options should be turned on for any kernel used for development or | 249 | of these options should be turned on for any kernel used for development or |
| 250 | testing purposes. In particular, you should turn on: | 250 | testing purposes. In particular, you should turn on: |
| 251 | 251 | ||
| 252 | - ENABLE_MUST_CHECK and FRAME_WARN to get an | 252 | - FRAME_WARN to get warnings for stack frames larger than a given amount. |
| 253 | extra set of warnings for problems like the use of deprecated interfaces | 253 | The output generated can be verbose, but one need not worry about |
| 254 | or ignoring an important return value from a function. The output | ||
| 255 | generated by these warnings can be verbose, but one need not worry about | ||
| 256 | warnings from other parts of the kernel. | 254 | warnings from other parts of the kernel. |
| 257 | 255 | ||
| 258 | - DEBUG_OBJECTS will add code to track the lifetime of various objects | 256 | - DEBUG_OBJECTS will add code to track the lifetime of various objects |
| @@ -1501,7 +1501,7 @@ Module for Digigram miXart8 sound cards. · 1500 unmodified lines | |||
| 1501 | 1501 | ||
| 1502 | This module supports multiple cards. | 1502 | This module supports multiple cards. |
| 1503 | Note: One miXart8 board will be represented as 4 alsa cards. | 1503 | Note: One miXart8 board will be represented as 4 alsa cards. |
| 1504 | See MIXART.txt for details. | 1504 | See Documentation/sound/cards/mixart.rst for details. |
| 1505 | 1505 | ||
| 1506 | When the driver is compiled as a module and the hotplug firmware | 1506 | When the driver is compiled as a module and the hotplug firmware |
| 1507 | is supported, the firmware data is loaded via hotplug automatically. | 1507 | is supported, the firmware data is loaded via hotplug automatically. |
| @@ -71,7 +71,7 @@ core/oss · 70 unmodified lines | |||
| 71 | The codes for PCM and mixer OSS emulation modules are stored in this | 71 | The codes for PCM and mixer OSS emulation modules are stored in this |
| 72 | directory. The rawmidi OSS emulation is included in the ALSA rawmidi | 72 | directory. The rawmidi OSS emulation is included in the ALSA rawmidi |
| 73 | code since it's quite small. The sequencer code is stored in | 73 | code since it's quite small. The sequencer code is stored in |
| 74 | ``core/seq/oss`` directory (see `below <#core-seq-oss>`__). | 74 | ``core/seq/oss`` directory (see `below <core/seq/oss_>`__). |
| 75 | 75 | ||
| 76 | core/seq | 76 | core/seq |
| 77 | ~~~~~~~~ | 77 | ~~~~~~~~ |
| @@ -382,7 +382,7 @@ where ``enable[dev]`` is the module option. · 304 unmodified lines | |||
| 382 | Each time the ``probe`` callback is called, check the availability of | 382 | Each time the ``probe`` callback is called, check the availability of |
| 383 | the device. If not available, simply increment the device index and | 383 | the device. If not available, simply increment the device index and |
| 384 | returns. dev will be incremented also later (`step 7 | 384 | returns. dev will be incremented also later (`step 7 |
| 385 | <#set-the-pci-driver-data-and-return-zero>`__). | 385 | <7) Set the PCI driver data and return zero._>`__). |
| 386 | 386 | ||
| 387 | 2) Create a card instance | 387 | 2) Create a card instance |
| 388 | ~~~~~~~~~~~~~~~~~~~~~~~~~ | 388 | ~~~~~~~~~~~~~~~~~~~~~~~~~ |
| @@ -450,10 +450,10 @@ field contains the information shown in ``/proc/asound/cards``. · 61 unmodified lines | |||
| 450 | 5) Create other components, such as mixer, MIDI, etc. | 450 | 5) Create other components, such as mixer, MIDI, etc. |
| 451 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | 451 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
| 452 | 452 | ||
| 453 | Here you define the basic components such as `PCM <#PCM-Interface>`__, | 453 | Here you define the basic components such as `PCM <PCM Interface_>`__, |
| 454 | mixer (e.g. `AC97 <#API-for-AC97-Codec>`__), MIDI (e.g. | 454 | mixer (e.g. `AC97 <API for AC97 Codec_>`__), MIDI (e.g. |
| 455 | `MPU-401 <#MIDI-MPU401-UART-Interface>`__), and other interfaces. | 455 | `MPU-401 <MIDI (MPU401-UART) Interface_>`__), and other interfaces. |
| 456 | Also, if you want a `proc file <#Proc-Interface>`__, define it here, | 456 | Also, if you want a `proc file <Proc Interface_>`__, define it here, |
| 457 | too. | 457 | too. |
| 458 | 458 | ||
| 459 | 6) Register the card instance. | 459 | 6) Register the card instance. |
| @@ -941,7 +941,7 @@ The allocation of an interrupt source is done like this: · 481 unmodified lines | |||
| 941 | chip->irq = pci->irq; | 941 | chip->irq = pci->irq; |
| 942 | 942 | ||
| 943 | where :c:func:`snd_mychip_interrupt()` is the interrupt handler | 943 | where :c:func:`snd_mychip_interrupt()` is the interrupt handler |
| 944 | defined `later <#pcm-interface-interrupt-handler>`__. Note that | 944 | defined `later <PCM Interrupt Handler_>`__. Note that |
| 945 | ``chip->irq`` should be defined only when :c:func:`request_irq()` | 945 | ``chip->irq`` should be defined only when :c:func:`request_irq()` |
| 946 | succeeded. | 946 | succeeded. |
| 947 | 947 | ||
| @@ -3104,7 +3104,7 @@ processing the output stream in the irq handler. · 2156 unmodified lines | |||
| 3104 | 3104 | ||
| 3105 | If the MPU-401 interface shares its interrupt with the other logical | 3105 | If the MPU-401 interface shares its interrupt with the other logical |
| 3106 | devices on the card, set ``MPU401_INFO_IRQ_HOOK`` (see | 3106 | devices on the card, set ``MPU401_INFO_IRQ_HOOK`` (see |
| 3107 | `below <#MIDI-Interrupt-Handler>`__). | 3107 | `below <MIDI Interrupt Handler_>`__). |
| 3108 | 3108 | ||
| 3109 | Usually, the port address corresponds to the command port and port + 1 | 3109 | Usually, the port address corresponds to the command port and port + 1 |
| 3110 | corresponds to the data port. If not, you may change the ``cport`` | 3110 | corresponds to the data port. If not, you may change the ``cport`` |
| @@ -360,10 +360,9 @@ since the last call to this ioctl. Bit 0 is the first page in the · 359 unmodified lines | |||
| 360 | memory slot. Ensure the entire structure is cleared to avoid padding | 360 | memory slot. Ensure the entire structure is cleared to avoid padding |
| 361 | issues. | 361 | issues. |
| 362 | 362 | ||
| 363 | If KVM_CAP_MULTI_ADDRESS_SPACE is available, bits 16-31 specifies | 363 | If KVM_CAP_MULTI_ADDRESS_SPACE is available, bits 16-31 of slot field specifies |
| 364 | the address space for which you want to return the dirty bitmap. | 364 | the address space for which you want to return the dirty bitmap. See |
| 365 | They must be less than the value that KVM_CHECK_EXTENSION returns for | 365 | KVM_SET_USER_MEMORY_REGION for details on the usage of slot field. |
| 366 | the KVM_CAP_MULTI_ADDRESS_SPACE capability. | ||
| 367 | 366 | ||
| 368 | The bits in the dirty bitmap are cleared before the ioctl returns, unless | 367 | The bits in the dirty bitmap are cleared before the ioctl returns, unless |
| 369 | KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 is enabled. For more information, | 368 | KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 is enabled. For more information, |
| @@ -392,9 +391,14 @@ This ioctl is obsolete and has been removed. · 22 unmodified lines | |||
| 392 | 391 | ||
| 393 | Errors: | 392 | Errors: |
| 394 | 393 | ||
| 395 | ===== ============================= | 394 | ======= ============================================================== |
| 396 | EINTR an unmasked signal is pending | 395 | EINTR an unmasked signal is pending |
| 397 | ===== ============================= | 396 | ENOEXEC the vcpu hasn't been initialized or the guest tried to execute |
| 397 | instructions from device memory (arm64) | ||
| 398 | ENOSYS data abort outside memslots with no syndrome info and | ||
| 399 | KVM_CAP_ARM_NISV_TO_USER not enabled (arm64) | ||
| 400 | EPERM SVE feature set but not finalized (arm64) | ||
| 401 | ======= ============================================================== | ||
| 398 | 402 | ||
| 399 | This ioctl is used to run a guest virtual cpu. While there are no | 403 | This ioctl is used to run a guest virtual cpu. While there are no |
| 400 | explicit parameters, there is an implicit parameter block that can be | 404 | explicit parameters, there is an implicit parameter block that can be |
| @@ -1276,6 +1280,9 @@ field userspace_addr, which must point at user addressable memory for · 875 unmodified lines | |||
| 1276 | the entire memory slot size. Any object may back this memory, including | 1280 | the entire memory slot size. Any object may back this memory, including |
| 1277 | anonymous memory, ordinary files, and hugetlbfs. | 1281 | anonymous memory, ordinary files, and hugetlbfs. |
| 1278 | 1282 | ||
| 1283 | On architectures that support a form of address tagging, userspace_addr must | ||
| 1284 | be an untagged address. | ||
| 1285 | |||
| 1279 | It is recommended that the lower 21 bits of guest_phys_addr and userspace_addr | 1286 | It is recommended that the lower 21 bits of guest_phys_addr and userspace_addr |
| 1280 | be identical. This allows large pages in the guest to be backed by large | 1287 | be identical. This allows large pages in the guest to be backed by large |
| 1281 | pages in the host. | 1288 | pages in the host. |
| @@ -1328,7 +1335,7 @@ documentation when it pops into existence). · 46 unmodified lines | |||
| 1328 | 1335 | ||
| 1329 | :Capability: KVM_CAP_ENABLE_CAP_VM | 1336 | :Capability: KVM_CAP_ENABLE_CAP_VM |
| 1330 | :Architectures: all | 1337 | :Architectures: all |
| 1331 | :Type: vcpu ioctl | 1338 | :Type: vm ioctl |
| 1332 | :Parameters: struct kvm_enable_cap (in) | 1339 | :Parameters: struct kvm_enable_cap (in) |
| 1333 | :Returns: 0 on success; -1 on error | 1340 | :Returns: 0 on success; -1 on error |
| 1334 | 1341 | ||
| @@ -4427,7 +4434,7 @@ to I/O ports. · 3092 unmodified lines | |||
| 4427 | :Capability: KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 | 4434 | :Capability: KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 |
| 4428 | :Architectures: x86, arm, arm64, mips | 4435 | :Architectures: x86, arm, arm64, mips |
| 4429 | :Type: vm ioctl | 4436 | :Type: vm ioctl |
| 4430 | :Parameters: struct kvm_dirty_log (in) | 4437 | :Parameters: struct kvm_clear_dirty_log (in) |
| 4431 | :Returns: 0 on success, -1 on error | 4438 | :Returns: 0 on success, -1 on error |
| 4432 | 4439 | ||
| 4433 | :: | 4440 | :: |
| @@ -4454,10 +4461,9 @@ in KVM's dirty bitmap, and dirty tracking is re-enabled for that page · 20 unmodified lines | |||
| 4454 | (for example via write-protection, or by clearing the dirty bit in | 4461 | (for example via write-protection, or by clearing the dirty bit in |
| 4455 | a page table entry). | 4462 | a page table entry). |
| 4456 | 4463 | ||
| 4457 | If KVM_CAP_MULTI_ADDRESS_SPACE is available, bits 16-31 specifies | 4464 | If KVM_CAP_MULTI_ADDRESS_SPACE is available, bits 16-31 of slot field specifies |
| 4458 | the address space for which you want to return the dirty bitmap. | 4465 | the address space for which you want to clear the dirty status. See |
| 4459 | They must be less than the value that KVM_CHECK_EXTENSION returns for | 4466 | KVM_SET_USER_MEMORY_REGION for details on the usage of slot field. |
| 4460 | the KVM_CAP_MULTI_ADDRESS_SPACE capability. | ||
| 4461 | 4467 | ||
| 4462 | This ioctl is mostly useful when KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 | 4468 | This ioctl is mostly useful when KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 |
| 4463 | is enabled; for more information, see the description of the capability. | 4469 | is enabled; for more information, see the description of the capability. |
| @@ -37,8 +37,10 @@ call L2. · 36 unmodified lines | |||
| 37 | Running nested VMX | 37 | Running nested VMX |
| 38 | ------------------ | 38 | ------------------ |
| 39 | 39 | ||
| 40 | The nested VMX feature is disabled by default. It can be enabled by giving | 40 | The nested VMX feature is enabled by default since Linux kernel v4.20. For |
| 41 | the "nested=1" option to the kvm-intel module. | 41 | older Linux kernel, it can be enabled by giving the "nested=1" option to the |
| 42 | kvm-intel module. | ||
| 43 | |||
| 42 | 44 | ||
| 43 | No modifications are required to user space (qemu). However, qemu's default | 45 | No modifications are required to user space (qemu). However, qemu's default |
| 44 | emulated CPU type (qemu64) does not list the "VMX" CPU feature, so it must be | 46 | emulated CPU type (qemu64) does not list the "VMX" CPU feature, so it must be |
| @@ -74,7 +74,7 @@ few: · 73 unmodified lines | |||
| 74 | Enabling "nested" (x86) | 74 | Enabling "nested" (x86) |
| 75 | ----------------------- | 75 | ----------------------- |
| 76 | 76 | ||
| 77 | From Linux kernel v4.19 onwards, the ``nested`` KVM parameter is enabled | 77 | From Linux kernel v4.20 onwards, the ``nested`` KVM parameter is enabled |
| 78 | by default for Intel and AMD. (Though your Linux distribution might | 78 | by default for Intel and AMD. (Though your Linux distribution might |
| 79 | override this default.) | 79 | override this default.) |
| 80 | 80 | ||
| @@ -203,8 +203,8 @@ F: include/uapi/linux/nl80211.h · 202 unmodified lines | |||
| 203 | F: net/wireless/ | 203 | F: net/wireless/ |
| 204 | 204 | ||
| 205 | 8169 10/100/1000 GIGABIT ETHERNET DRIVER | 205 | 8169 10/100/1000 GIGABIT ETHERNET DRIVER |
| 206 | M: Realtek linux nic maintainers <nic_swsd@realtek.com> | ||
| 207 | M: Heiner Kallweit <hkallweit1@gmail.com> | 206 | M: Heiner Kallweit <hkallweit1@gmail.com> |
| 207 | M: nic_swsd@realtek.com | ||
| 208 | L: netdev@vger.kernel.org | 208 | L: netdev@vger.kernel.org |
| 209 | S: Maintained | 209 | S: Maintained |
| 210 | F: drivers/net/ethernet/realtek/r8169* | 210 | F: drivers/net/ethernet/realtek/r8169* |
| @@ -820,7 +820,6 @@ M: Netanel Belgazal <netanel@amazon.com> · 609 unmodified lines | |||
| 820 | M: Arthur Kiyanovski <akiyano@amazon.com> | 820 | M: Arthur Kiyanovski <akiyano@amazon.com> |
| 821 | R: Guy Tzalik <gtzalik@amazon.com> | 821 | R: Guy Tzalik <gtzalik@amazon.com> |
| 822 | R: Saeed Bishara <saeedb@amazon.com> | 822 | R: Saeed Bishara <saeedb@amazon.com> |
| 823 | R: Zorik Machulsky <zorik@amazon.com> | ||
| 824 | L: netdev@vger.kernel.org | 823 | L: netdev@vger.kernel.org |
| 825 | S: Supported | 824 | S: Supported |
| 826 | F: Documentation/networking/device_drivers/ethernet/amazon/ena.rst | 825 | F: Documentation/networking/device_drivers/ethernet/amazon/ena.rst |
| @@ -907,7 +906,7 @@ AMD KFD · 80 unmodified lines | |||
| 907 | M: Felix Kuehling <Felix.Kuehling@amd.com> | 906 | M: Felix Kuehling <Felix.Kuehling@amd.com> |
| 908 | L: amd-gfx@lists.freedesktop.org | 907 | L: amd-gfx@lists.freedesktop.org |
| 909 | S: Supported | 908 | S: Supported |
| 910 | T: git git://people.freedesktop.org/~agd5f/linux | 909 | T: git https://gitlab.freedesktop.org/agd5f/linux.git |
| 911 | F: drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd*.[ch] | 910 | F: drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd*.[ch] |
| 912 | F: drivers/gpu/drm/amd/amdkfd/ | 911 | F: drivers/gpu/drm/amd/amdkfd/ |
| 913 | F: drivers/gpu/drm/amd/include/cik_structs.h | 912 | F: drivers/gpu/drm/amd/include/cik_structs.h |
| @@ -2119,7 +2118,7 @@ N: atmel · 1205 unmodified lines | |||
| 2119 | ARM/Microchip Sparx5 SoC support | 2118 | ARM/Microchip Sparx5 SoC support |
| 2120 | M: Lars Povlsen <lars.povlsen@microchip.com> | 2119 | M: Lars Povlsen <lars.povlsen@microchip.com> |
| 2121 | M: Steen Hegelund <Steen.Hegelund@microchip.com> | 2120 | M: Steen Hegelund <Steen.Hegelund@microchip.com> |
| 2122 | M: Microchip Linux Driver Support <UNGLinuxDriver@microchip.com> | 2121 | M: UNGLinuxDriver@microchip.com |
| 2123 | L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) | 2122 | L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) |
| 2124 | S: Supported | 2123 | S: Supported |
| 2125 | T: git git://github.com/microchip-ung/linux-upstream.git | 2124 | T: git git://github.com/microchip-ung/linux-upstream.git |
| @@ -2617,8 +2616,8 @@ S: Maintained · 491 unmodified lines | |||
| 2617 | F: drivers/power/reset/keystone-reset.c | 2616 | F: drivers/power/reset/keystone-reset.c |
| 2618 | 2617 | ||
| 2619 | ARM/TEXAS INSTRUMENTS K3 ARCHITECTURE | 2618 | ARM/TEXAS INSTRUMENTS K3 ARCHITECTURE |
| 2620 | M: Tero Kristo <t-kristo@ti.com> | ||
| 2621 | M: Nishanth Menon <nm@ti.com> | 2619 | M: Nishanth Menon <nm@ti.com> |
| 2620 | M: Tero Kristo <kristo@kernel.org> | ||
| 2622 | L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) | 2621 | L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) |
| 2623 | S: Supported | 2622 | S: Supported |
| 2624 | F: Documentation/devicetree/bindings/arm/ti/k3.yaml | 2623 | F: Documentation/devicetree/bindings/arm/ti/k3.yaml |
| @@ -2942,7 +2941,6 @@ S: Maintained · 317 unmodified lines | |||
| 2942 | F: drivers/hwmon/asus_atk0110.c | 2941 | F: drivers/hwmon/asus_atk0110.c |
| 2943 | 2942 | ||
| 2944 | ATLX ETHERNET DRIVERS | 2943 | ATLX ETHERNET DRIVERS |
| 2945 | M: Jay Cliburn <jcliburn@gmail.com> | ||
| 2946 | M: Chris Snook <chris.snook@gmail.com> | 2944 | M: Chris Snook <chris.snook@gmail.com> |
| 2947 | L: netdev@vger.kernel.org | 2945 | L: netdev@vger.kernel.org |
| 2948 | S: Maintained | 2946 | S: Maintained |
| @@ -3241,6 +3239,7 @@ L: netdev@vger.kernel.org · 292 unmodified lines | |||
| 3241 | S: Supported | 3239 | S: Supported |
| 3242 | W: http://sourceforge.net/projects/bonding/ | 3240 | W: http://sourceforge.net/projects/bonding/ |
| 3243 | F: drivers/net/bonding/ | 3241 | F: drivers/net/bonding/ |
| 3242 | F: include/net/bonding.h | ||
| 3244 | F: include/uapi/linux/if_bonding.h | 3243 | F: include/uapi/linux/if_bonding.h |
| 3245 | 3244 | ||
| 3246 | BOSCH SENSORTEC BMA400 ACCELEROMETER IIO DRIVER | 3245 | BOSCH SENSORTEC BMA400 ACCELEROMETER IIO DRIVER |
| @@ -3336,7 +3335,7 @@ F: arch/riscv/net/ · 89 unmodified lines | |||
| 3336 | X: arch/riscv/net/bpf_jit_comp64.c | 3335 | X: arch/riscv/net/bpf_jit_comp64.c |
| 3337 | 3336 | ||
| 3338 | BPF JIT for RISC-V (64-bit) | 3337 | BPF JIT for RISC-V (64-bit) |
| 3339 | M: Björn Töpel <bjorn.topel@gmail.com> | 3338 | M: Björn Töpel <bjorn@kernel.org> |
| 3340 | L: netdev@vger.kernel.org | 3339 | L: netdev@vger.kernel.org |
| 3341 | L: bpf@vger.kernel.org | 3340 | L: bpf@vger.kernel.org |
| 3342 | S: Maintained | 3341 | S: Maintained |
| @@ -3413,7 +3412,7 @@ F: Documentation/devicetree/bindings/pci/brcm,stb-pcie.yaml · 70 unmodified lines | |||
| 3413 | F: drivers/pci/controller/pcie-brcmstb.c | 3412 | F: drivers/pci/controller/pcie-brcmstb.c |
| 3414 | F: drivers/staging/vc04_services | 3413 | F: drivers/staging/vc04_services |
| 3415 | N: bcm2711 | 3414 | N: bcm2711 |
| 3416 | N: bcm2835 | 3415 | N: bcm283* |
| 3417 | 3416 | ||
| 3418 | BROADCOM BCM281XX/BCM11XXX/BCM216XX ARM ARCHITECTURE | 3417 | BROADCOM BCM281XX/BCM11XXX/BCM216XX ARM ARCHITECTURE |
| 3419 | M: Florian Fainelli <f.fainelli@gmail.com> | 3418 | M: Florian Fainelli <f.fainelli@gmail.com> |
| @@ -3556,7 +3555,7 @@ S: Supported · 136 unmodified lines | |||
| 3556 | F: drivers/net/ethernet/broadcom/bnxt/ | 3555 | F: drivers/net/ethernet/broadcom/bnxt/ |
| 3557 | 3556 | ||
| 3558 | BROADCOM BRCM80211 IEEE802.11n WIRELESS DRIVER | 3557 | BROADCOM BRCM80211 IEEE802.11n WIRELESS DRIVER |
| 3559 | M: Arend van Spriel <arend.vanspriel@broadcom.com> | 3558 | M: Arend van Spriel <aspriel@gmail.com> |
| 3560 | M: Franky Lin <franky.lin@broadcom.com> | 3559 | M: Franky Lin <franky.lin@broadcom.com> |
| 3561 | M: Hante Meuleman <hante.meuleman@broadcom.com> | 3560 | M: Hante Meuleman <hante.meuleman@broadcom.com> |
| 3562 | M: Chi-hsien Lin <chi-hsien.lin@infineon.com> | 3561 | M: Chi-hsien Lin <chi-hsien.lin@infineon.com> |
| @@ -3881,9 +3880,9 @@ F: Documentation/devicetree/bindings/mtd/cadence-nand-controller.txt · 318 unmodified lines | |||
| 3881 | F: drivers/mtd/nand/raw/cadence-nand-controller.c | 3880 | F: drivers/mtd/nand/raw/cadence-nand-controller.c |
| 3882 | 3881 | ||
| 3883 | CADENCE USB3 DRD IP DRIVER | 3882 | CADENCE USB3 DRD IP DRIVER |
| 3884 | M: Peter Chen <peter.chen@nxp.com> | 3883 | M: Peter Chen <peter.chen@kernel.org> |
| 3885 | M: Pawel Laszczak <pawell@cadence.com> | 3884 | M: Pawel Laszczak <pawell@cadence.com> |
| 3886 | M: Roger Quadros <rogerq@ti.com> | 3885 | R: Roger Quadros <rogerq@kernel.org> |
| 3887 | R: Aswath Govindraju <a-govindraju@ti.com> | 3886 | R: Aswath Govindraju <a-govindraju@ti.com> |
| 3888 | L: linux-usb@vger.kernel.org | 3887 | L: linux-usb@vger.kernel.org |
| 3889 | S: Maintained | 3888 | S: Maintained |
| @@ -3961,7 +3960,7 @@ F: net/can/ · 71 unmodified lines | |||
| 3961 | CAN-J1939 NETWORK LAYER | 3960 | CAN-J1939 NETWORK LAYER |
| 3962 | M: Robin van der Gracht <robin@protonic.nl> | 3961 | M: Robin van der Gracht <robin@protonic.nl> |
| 3963 | M: Oleksij Rempel <o.rempel@pengutronix.de> | 3962 | M: Oleksij Rempel <o.rempel@pengutronix.de> |
| 3964 | R: Pengutronix Kernel Team <kernel@pengutronix.de> | 3963 | R: kernel@pengutronix.de |
| 3965 | L: linux-can@vger.kernel.org | 3964 | L: linux-can@vger.kernel.org |
| 3966 | S: Maintained | 3965 | S: Maintained |
| 3967 | F: Documentation/networking/j1939.rst | 3966 | F: Documentation/networking/j1939.rst |
| @@ -4163,7 +4162,7 @@ S: Maintained · 195 unmodified lines | |||
| 4163 | F: Documentation/translations/zh_CN/ | 4162 | F: Documentation/translations/zh_CN/ |
| 4164 | 4163 | ||
| 4165 | CHIPIDEA USB HIGH SPEED DUAL ROLE CONTROLLER | 4164 | CHIPIDEA USB HIGH SPEED DUAL ROLE CONTROLLER |
| 4166 | M: Peter Chen <Peter.Chen@nxp.com> | 4165 | M: Peter Chen <peter.chen@kernel.org> |
| 4167 | L: linux-usb@vger.kernel.org | 4166 | L: linux-usb@vger.kernel.org |
| 4168 | S: Maintained | 4167 | S: Maintained |
| 4169 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/peter.chen/usb.git | 4168 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/peter.chen/usb.git |
| @@ -4305,7 +4304,7 @@ S: Maintained · 135 unmodified lines | |||
| 4305 | F: .clang-format | 4304 | F: .clang-format |
| 4306 | 4305 | ||
| 4307 | CLANG/LLVM BUILD SUPPORT | 4306 | CLANG/LLVM BUILD SUPPORT |
| 4308 | M: Nathan Chancellor <natechancellor@gmail.com> | 4307 | M: Nathan Chancellor <nathan@kernel.org> |
| 4309 | M: Nick Desaulniers <ndesaulniers@google.com> | 4308 | M: Nick Desaulniers <ndesaulniers@google.com> |
| 4310 | L: clang-built-linux@googlegroups.com | 4309 | L: clang-built-linux@googlegroups.com |
| 4311 | S: Supported | 4310 | S: Supported |
| @@ -4313,7 +4312,9 @@ W: https://clangbuiltlinux.github.io/ · 1 unmodified line | |||
| 4313 | B: https://github.com/ClangBuiltLinux/linux/issues | 4312 | B: https://github.com/ClangBuiltLinux/linux/issues |
| 4314 | C: irc://chat.freenode.net/clangbuiltlinux | 4313 | C: irc://chat.freenode.net/clangbuiltlinux |
| 4315 | F: Documentation/kbuild/llvm.rst | 4314 | F: Documentation/kbuild/llvm.rst |
| 4315 | F: include/linux/compiler-clang.h | ||
| 4316 | F: scripts/clang-tools/ | 4316 | F: scripts/clang-tools/ |
| 4317 | F: scripts/clang-version.sh | ||
| 4317 | F: scripts/lld-version.sh | 4318 | F: scripts/lld-version.sh |
| 4318 | K: \b(?i:clang|llvm)\b | 4319 | K: \b(?i:clang|llvm)\b |
| 4319 | 4320 | ||
| @@ -4467,7 +4468,7 @@ F: include/linux/console* · 147 unmodified lines | |||
| 4467 | 4468 | ||
| 4468 | CONTROL GROUP (CGROUP) | 4469 | CONTROL GROUP (CGROUP) |
| 4469 | M: Tejun Heo <tj@kernel.org> | 4470 | M: Tejun Heo <tj@kernel.org> |
| 4470 | M: Li Zefan <lizefan@huawei.com> | 4471 | M: Zefan Li <lizefan.x@bytedance.com> |
| 4471 | M: Johannes Weiner <hannes@cmpxchg.org> | 4472 | M: Johannes Weiner <hannes@cmpxchg.org> |
| 4472 | L: cgroups@vger.kernel.org | 4473 | L: cgroups@vger.kernel.org |
| 4473 | S: Maintained | 4474 | S: Maintained |
| @@ -4491,11 +4492,9 @@ F: block/blk-throttle.c · 17 unmodified lines | |||
| 4491 | F: include/linux/blk-cgroup.h | 4492 | F: include/linux/blk-cgroup.h |
| 4492 | 4493 | ||
| 4493 | CONTROL GROUP - CPUSET | 4494 | CONTROL GROUP - CPUSET |
| 4494 | M: Li Zefan <lizefan@huawei.com> | 4495 | M: Zefan Li <lizefan.x@bytedance.com> |
| 4495 | L: cgroups@vger.kernel.org | 4496 | L: cgroups@vger.kernel.org |
| 4496 | S: Maintained | 4497 | S: Maintained |
| 4497 | W: http://www.bullopensource.org/cpuset/ | ||
| 4498 | W: http://oss.sgi.com/projects/cpusets/ | ||
| 4499 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/tj/cgroup.git | 4498 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/tj/cgroup.git |
| 4500 | F: Documentation/admin-guide/cgroup-v1/cpusets.rst | 4499 | F: Documentation/admin-guide/cgroup-v1/cpusets.rst |
| 4501 | F: include/linux/cpuset.h | 4500 | F: include/linux/cpuset.h |
| @@ -4922,9 +4921,8 @@ F: Documentation/scsi/dc395x.rst · 420 unmodified lines | |||
| 4922 | F: drivers/scsi/dc395x.* | 4921 | F: drivers/scsi/dc395x.* |
| 4923 | 4922 | ||
| 4924 | DCCP PROTOCOL | 4923 | DCCP PROTOCOL |
| 4925 | M: Gerrit Renker <gerrit@erg.abdn.ac.uk> | ||
| 4926 | L: dccp@vger.kernel.org | 4924 | L: dccp@vger.kernel.org |
| 4927 | S: Maintained | 4925 | S: Orphan |
| 4928 | W: http://www.linuxfoundation.org/collaborate/workgroups/networking/dccp | 4926 | W: http://www.linuxfoundation.org/collaborate/workgroups/networking/dccp |
| 4929 | F: include/linux/dccp.h | 4927 | F: include/linux/dccp.h |
| 4930 | F: include/linux/tfrc.h | 4928 | F: include/linux/tfrc.h |
| @@ -6474,9 +6472,9 @@ S: Maintained · 1543 unmodified lines | |||
| 6474 | F: drivers/edac/skx_*.[ch] | 6472 | F: drivers/edac/skx_*.[ch] |
| 6475 | 6473 | ||
| 6476 | EDAC-TI | 6474 | EDAC-TI |
| 6477 | M: Tero Kristo <t-kristo@ti.com> | 6475 | M: Tero Kristo <kristo@kernel.org> |
| 6478 | L: linux-edac@vger.kernel.org | 6476 | L: linux-edac@vger.kernel.org |
| 6479 | S: Maintained | 6477 | S: Odd Fixes |
| 6480 | F: drivers/edac/ti_edac.c | 6478 | F: drivers/edac/ti_edac.c |
| 6481 | 6479 | ||
| 6482 | EDIROL UA-101/UA-1000 DRIVER | 6480 | EDIROL UA-101/UA-1000 DRIVER |
| @@ -7363,7 +7361,6 @@ L: linux-hardening@vger.kernel.org · 880 unmodified lines | |||
| 7363 | S: Maintained | 7361 | S: Maintained |
| 7364 | F: Documentation/kbuild/gcc-plugins.rst | 7362 | F: Documentation/kbuild/gcc-plugins.rst |
| 7365 | F: scripts/Makefile.gcc-plugins | 7363 | F: scripts/Makefile.gcc-plugins |
| 7366 | F: scripts/gcc-plugin.sh | ||
| 7367 | F: scripts/gcc-plugins/ | 7364 | F: scripts/gcc-plugins/ |
| 7368 | 7365 | ||
| 7369 | GCOV BASED KERNEL PROFILING | 7366 | GCOV BASED KERNEL PROFILING |
| @@ -8435,11 +8432,8 @@ F: drivers/i3c/ · 1065 unmodified lines | |||
| 8435 | F: include/linux/i3c/ | 8432 | F: include/linux/i3c/ |
| 8436 | 8433 | ||
| 8437 | IA64 (Itanium) PLATFORM | 8434 | IA64 (Itanium) PLATFORM |
| 8438 | M: Tony Luck <tony.luck@intel.com> | ||
| 8439 | M: Fenghua Yu <fenghua.yu@intel.com> | ||
| 8440 | L: linux-ia64@vger.kernel.org | 8435 | L: linux-ia64@vger.kernel.org |
| 8441 | S: Odd Fixes | 8436 | S: Orphan |
| 8442 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/aegl/linux.git | ||
| 8443 | F: Documentation/ia64/ | 8437 | F: Documentation/ia64/ |
| 8444 | F: arch/ia64/ | 8438 | F: arch/ia64/ |
| 8445 | 8439 | ||
| @@ -9240,7 +9234,7 @@ F: tools/testing/selftests/sgx/* · 794 unmodified lines | |||
| 9240 | K: \bSGX_ | 9234 | K: \bSGX_ |
| 9241 | 9235 | ||
| 9242 | INTERCONNECT API | 9236 | INTERCONNECT API |
| 9243 | M: Georgi Djakov <georgi.djakov@linaro.org> | 9237 | M: Georgi Djakov <djakov@kernel.org> |
| 9244 | L: linux-pm@vger.kernel.org | 9238 | L: linux-pm@vger.kernel.org |
| 9245 | S: Maintained | 9239 | S: Maintained |
| 9246 | F: Documentation/devicetree/bindings/interconnect/ | 9240 | F: Documentation/devicetree/bindings/interconnect/ |
| @@ -9273,7 +9267,7 @@ F: drivers/net/ethernet/sgi/ioc3-eth.c · 26 unmodified lines | |||
| 9273 | 9267 | ||
| 9274 | IOMAP FILESYSTEM LIBRARY | 9268 | IOMAP FILESYSTEM LIBRARY |
| 9275 | M: Christoph Hellwig <hch@infradead.org> | 9269 | M: Christoph Hellwig <hch@infradead.org> |
| 9276 | M: Darrick J. Wong <darrick.wong@oracle.com> | 9270 | M: Darrick J. Wong <djwong@kernel.org> |
| 9277 | M: linux-xfs@vger.kernel.org | 9271 | M: linux-xfs@vger.kernel.org |
| 9278 | M: linux-fsdevel@vger.kernel.org | 9272 | M: linux-fsdevel@vger.kernel.org |
| 9279 | L: linux-xfs@vger.kernel.org | 9273 | L: linux-xfs@vger.kernel.org |
| @@ -9327,7 +9321,6 @@ W: http://www.adaptec.com/ · 47 unmodified lines | |||
| 9327 | F: drivers/scsi/ips* | 9321 | F: drivers/scsi/ips* |
| 9328 | 9322 | ||
| 9329 | IPVS | 9323 | IPVS |
| 9330 | M: Wensong Zhang <wensong@linux-vs.org> | ||
| 9331 | M: Simon Horman <horms@verge.net.au> | 9324 | M: Simon Horman <horms@verge.net.au> |
| 9332 | M: Julian Anastasov <ja@ssi.bg> | 9325 | M: Julian Anastasov <ja@ssi.bg> |
| 9333 | L: netdev@vger.kernel.org | 9326 | L: netdev@vger.kernel.org |
| @@ -9564,16 +9557,18 @@ F: Documentation/hwmon/k8temp.rst · 230 unmodified lines | |||
| 9564 | F: drivers/hwmon/k8temp.c | 9557 | F: drivers/hwmon/k8temp.c |
| 9565 | 9558 | ||
| 9566 | KASAN | 9559 | KASAN |
| 9567 | M: Andrey Ryabinin <aryabinin@virtuozzo.com> | 9560 | M: Andrey Ryabinin <ryabinin.a.a@gmail.com> |
| 9568 | R: Alexander Potapenko <glider@google.com> | 9561 | R: Alexander Potapenko <glider@google.com> |
| 9562 | R: Andrey Konovalov <andreyknvl@gmail.com> | ||
| 9569 | R: Dmitry Vyukov <dvyukov@google.com> | 9563 | R: Dmitry Vyukov <dvyukov@google.com> |
| 9570 | L: kasan-dev@googlegroups.com | 9564 | L: kasan-dev@googlegroups.com |
| 9571 | S: Maintained | 9565 | S: Maintained |
| 9572 | F: Documentation/dev-tools/kasan.rst | 9566 | F: Documentation/dev-tools/kasan.rst |
| 9573 | F: arch/*/include/asm/kasan.h | 9567 | F: arch/*/include/asm/*kasan.h |
| 9574 | F: arch/*/mm/kasan_init* | 9568 | F: arch/*/mm/kasan_init* |
| 9575 | F: include/linux/kasan*.h | 9569 | F: include/linux/kasan*.h |
| 9576 | F: lib/test_kasan.c | 9570 | F: lib/Kconfig.kasan |
| 9571 | F: lib/test_kasan*.c | ||
| 9577 | F: mm/kasan/ | 9572 | F: mm/kasan/ |
| 9578 | F: scripts/Makefile.kasan | 9573 | F: scripts/Makefile.kasan |
| 9579 | 9574 | ||
| @@ -9588,7 +9583,7 @@ F: scripts/kconfig/ · 8 unmodified lines | |||
| 9588 | 9583 | ||
| 9589 | KCOV | 9584 | KCOV |
| 9590 | R: Dmitry Vyukov <dvyukov@google.com> | 9585 | R: Dmitry Vyukov <dvyukov@google.com> |
| 9591 | R: Andrey Konovalov <andreyknvl@google.com> | 9586 | R: Andrey Konovalov <andreyknvl@gmail.com> |
| 9592 | L: kasan-dev@googlegroups.com | 9587 | L: kasan-dev@googlegroups.com |
| 9593 | S: Maintained | 9588 | S: Maintained |
| 9594 | F: Documentation/dev-tools/kcov.rst | 9589 | F: Documentation/dev-tools/kcov.rst |
| @@ -9776,7 +9771,7 @@ F: tools/testing/selftests/kvm/s390x/ · 181 unmodified lines | |||
| 9776 | 9771 | ||
| 9777 | KERNEL VIRTUAL MACHINE FOR X86 (KVM/x86) | 9772 | KERNEL VIRTUAL MACHINE FOR X86 (KVM/x86) |
| 9778 | M: Paolo Bonzini <pbonzini@redhat.com> | 9773 | M: Paolo Bonzini <pbonzini@redhat.com> |
| 9779 | R: Sean Christopherson <sean.j.christopherson@intel.com> | 9774 | R: Sean Christopherson <seanjc@google.com> |
| 9780 | R: Vitaly Kuznetsov <vkuznets@redhat.com> | 9775 | R: Vitaly Kuznetsov <vkuznets@redhat.com> |
| 9781 | R: Wanpeng Li <wanpengli@tencent.com> | 9776 | R: Wanpeng Li <wanpengli@tencent.com> |
| 9782 | R: Jim Mattson <jmattson@google.com> | 9777 | R: Jim Mattson <jmattson@google.com> |
| @@ -10260,7 +10255,6 @@ S: Supported · 477 unmodified lines | |||
| 10260 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/paulmck/linux-rcu.git dev | 10255 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/paulmck/linux-rcu.git dev |
| 10261 | F: Documentation/atomic_bitops.txt | 10256 | F: Documentation/atomic_bitops.txt |
| 10262 | F: Documentation/atomic_t.txt | 10257 | F: Documentation/atomic_t.txt |
| 10263 | F: Documentation/core-api/atomic_ops.rst | ||
| 10264 | F: Documentation/core-api/refcount-vs-atomic.rst | 10258 | F: Documentation/core-api/refcount-vs-atomic.rst |
| 10265 | F: Documentation/litmus-tests/ | 10259 | F: Documentation/litmus-tests/ |
| 10266 | F: Documentation/memory-barriers.txt | 10260 | F: Documentation/memory-barriers.txt |
| @@ -10847,7 +10841,7 @@ F: drivers/media/radio/radio-maxiradio* · 580 unmodified lines | |||
| 10847 | 10841 | ||
| 10848 | MCAN MMIO DEVICE DRIVER | 10842 | MCAN MMIO DEVICE DRIVER |
| 10849 | M: Dan Murphy <dmurphy@ti.com> | 10843 | M: Dan Murphy <dmurphy@ti.com> |
| 10850 | M: Sriram Dash <sriram.dash@samsung.com> | 10844 | M: Pankaj Sharma <pankj.sharma@samsung.com> |
| 10851 | L: linux-can@vger.kernel.org | 10845 | L: linux-can@vger.kernel.org |
| 10852 | S: Maintained | 10846 | S: Maintained |
| 10853 | F: Documentation/devicetree/bindings/net/can/bosch,m_can.yaml | 10847 | F: Documentation/devicetree/bindings/net/can/bosch,m_can.yaml |
| @@ -11667,7 +11661,7 @@ F: drivers/media/platform/atmel/atmel-isi.h · 813 unmodified lines | |||
| 11667 | 11661 | ||
| 11668 | MICROCHIP KSZ SERIES ETHERNET SWITCH DRIVER | 11662 | MICROCHIP KSZ SERIES ETHERNET SWITCH DRIVER |
| 11669 | M: Woojung Huh <woojung.huh@microchip.com> | 11663 | M: Woojung Huh <woojung.huh@microchip.com> |
| 11670 | M: Microchip Linux Driver Support <UNGLinuxDriver@microchip.com> | 11664 | M: UNGLinuxDriver@microchip.com |
| 11671 | L: netdev@vger.kernel.org | 11665 | L: netdev@vger.kernel.org |
| 11672 | S: Maintained | 11666 | S: Maintained |
| 11673 | F: Documentation/devicetree/bindings/net/dsa/microchip,ksz.yaml | 11667 | F: Documentation/devicetree/bindings/net/dsa/microchip,ksz.yaml |
| @@ -11677,7 +11671,7 @@ F: net/dsa/tag_ksz.c · 3 unmodified lines | |||
| 11677 | 11671 | ||
| 11678 | MICROCHIP LAN743X ETHERNET DRIVER | 11672 | MICROCHIP LAN743X ETHERNET DRIVER |
| 11679 | M: Bryan Whitehead <bryan.whitehead@microchip.com> | 11673 | M: Bryan Whitehead <bryan.whitehead@microchip.com> |
| 11680 | M: Microchip Linux Driver Support <UNGLinuxDriver@microchip.com> | 11674 | M: UNGLinuxDriver@microchip.com |
| 11681 | L: netdev@vger.kernel.org | 11675 | L: netdev@vger.kernel.org |
| 11682 | S: Maintained | 11676 | S: Maintained |
| 11683 | F: drivers/net/ethernet/microchip/lan743x_* | 11677 | F: drivers/net/ethernet/microchip/lan743x_* |
| @@ -11771,7 +11765,7 @@ F: drivers/net/wireless/microchip/wilc1000/ · 87 unmodified lines | |||
| 11771 | 11765 | ||
| 11772 | MICROSEMI MIPS SOCS | 11766 | MICROSEMI MIPS SOCS |
| 11773 | M: Alexandre Belloni <alexandre.belloni@bootlin.com> | 11767 | M: Alexandre Belloni <alexandre.belloni@bootlin.com> |
| 11774 | M: Microchip Linux Driver Support <UNGLinuxDriver@microchip.com> | 11768 | M: UNGLinuxDriver@microchip.com |
| 11775 | L: linux-mips@vger.kernel.org | 11769 | L: linux-mips@vger.kernel.org |
| 11776 | S: Supported | 11770 | S: Supported |
| 11777 | F: Documentation/devicetree/bindings/mips/mscc.txt | 11771 | F: Documentation/devicetree/bindings/mips/mscc.txt |
| @@ -12418,8 +12412,8 @@ F: tools/testing/selftests/net/ipsec.c · 640 unmodified lines | |||
| 12418 | 12412 | ||
| 12419 | NETWORKING [IPv4/IPv6] | 12413 | NETWORKING [IPv4/IPv6] |
| 12420 | M: "David S. Miller" <davem@davemloft.net> | 12414 | M: "David S. Miller" <davem@davemloft.net> |
| 12421 | M: Alexey Kuznetsov <kuznet@ms2.inr.ac.ru> | ||
| 12422 | M: Hideaki YOSHIFUJI <yoshfuji@linux-ipv6.org> | 12415 | M: Hideaki YOSHIFUJI <yoshfuji@linux-ipv6.org> |
| 12416 | M: David Ahern <dsahern@kernel.org> | ||
| 12423 | L: netdev@vger.kernel.org | 12417 | L: netdev@vger.kernel.org |
| 12424 | S: Maintained | 12418 | S: Maintained |
| 12425 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git | 12419 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git |
| @@ -12475,7 +12469,6 @@ F: net/ipv6/tcp*.c · 49 unmodified lines | |||
| 12475 | 12469 | ||
| 12476 | NETWORKING [TLS] | 12470 | NETWORKING [TLS] |
| 12477 | M: Boris Pismenny <borisp@nvidia.com> | 12471 | M: Boris Pismenny <borisp@nvidia.com> |
| 12478 | M: Aviad Yehezkel <aviadye@nvidia.com> | ||
| 12479 | M: John Fastabend <john.fastabend@gmail.com> | 12472 | M: John Fastabend <john.fastabend@gmail.com> |
| 12480 | M: Daniel Borkmann <daniel@iogearbox.net> | 12473 | M: Daniel Borkmann <daniel@iogearbox.net> |
| 12481 | M: Jakub Kicinski <kuba@kernel.org> | 12474 | M: Jakub Kicinski <kuba@kernel.org> |
| @@ -12825,10 +12818,10 @@ F: tools/objtool/ · 343 unmodified lines | |||
| 12825 | F: include/linux/objtool.h | 12818 | F: include/linux/objtool.h |
| 12826 | 12819 | ||
| 12827 | OCELOT ETHERNET SWITCH DRIVER | 12820 | OCELOT ETHERNET SWITCH DRIVER |
| 12828 | M: Microchip Linux Driver Support <UNGLinuxDriver@microchip.com> | ||
| 12829 | M: Vladimir Oltean <vladimir.oltean@nxp.com> | 12821 | M: Vladimir Oltean <vladimir.oltean@nxp.com> |
| 12830 | M: Claudiu Manoil <claudiu.manoil@nxp.com> | 12822 | M: Claudiu Manoil <claudiu.manoil@nxp.com> |
| 12831 | M: Alexandre Belloni <alexandre.belloni@bootlin.com> | 12823 | M: Alexandre Belloni <alexandre.belloni@bootlin.com> |
| 12824 | M: UNGLinuxDriver@microchip.com | ||
| 12832 | L: netdev@vger.kernel.org | 12825 | L: netdev@vger.kernel.org |
| 12833 | S: Supported | 12826 | S: Supported |
| 12834 | F: drivers/net/dsa/ocelot/* | 12827 | F: drivers/net/dsa/ocelot/* |
| @@ -12850,7 +12843,7 @@ F: include/misc/ocxl* · 15 unmodified lines | |||
| 12850 | F: include/uapi/misc/ocxl.h | 12843 | F: include/uapi/misc/ocxl.h |
| 12851 | 12844 | ||
| 12852 | OMAP AUDIO SUPPORT | 12845 | OMAP AUDIO SUPPORT |
| 12853 | M: Peter Ujfalusi <peter.ujfalusi@ti.com> | 12846 | M: Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 12854 | M: Jarkko Nikula <jarkko.nikula@bitmer.com> | 12847 | M: Jarkko Nikula <jarkko.nikula@bitmer.com> |
| 12855 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) | 12848 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) |
| 12856 | L: linux-omap@vger.kernel.org | 12849 | L: linux-omap@vger.kernel.org |
| @@ -13890,7 +13883,7 @@ F: drivers/platform/x86/peaq-wmi.c · 1033 unmodified lines | |||
| 13890 | 13883 | ||
| 13891 | PENSANDO ETHERNET DRIVERS | 13884 | PENSANDO ETHERNET DRIVERS |
| 13892 | M: Shannon Nelson <snelson@pensando.io> | 13885 | M: Shannon Nelson <snelson@pensando.io> |
| 13893 | M: Pensando Drivers <drivers@pensando.io> | 13886 | M: drivers@pensando.io |
| 13894 | L: netdev@vger.kernel.org | 13887 | L: netdev@vger.kernel.org |
| 13895 | S: Supported | 13888 | S: Supported |
| 13896 | F: Documentation/networking/device_drivers/ethernet/pensando/ionic.rst | 13889 | F: Documentation/networking/device_drivers/ethernet/pensando/ionic.rst |
| @@ -14512,10 +14505,18 @@ S: Supported · 615 unmodified lines | |||
| 14512 | F: drivers/crypto/qat/ | 14505 | F: drivers/crypto/qat/ |
| 14513 | 14506 | ||
| 14514 | QCOM AUDIO (ASoC) DRIVERS | 14507 | QCOM AUDIO (ASoC) DRIVERS |
| 14515 | M: Patrick Lai <plai@codeaurora.org> | 14508 | M: Srinivas Kandagatla <srinivas.kandagatla@linaro.org> |
| 14516 | M: Banajit Goswami <bgoswami@codeaurora.org> | 14509 | M: Banajit Goswami <bgoswami@codeaurora.org> |
| 14517 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) | 14510 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) |
| 14518 | S: Supported | 14511 | S: Supported |
| 14512 | F: sound/soc/codecs/lpass-va-macro.c | ||
| 14513 | F: sound/soc/codecs/lpass-wsa-macro.* | ||
| 14514 | F: sound/soc/codecs/msm8916-wcd-analog.c | ||
| 14515 | F: sound/soc/codecs/msm8916-wcd-digital.c | ||
| 14516 | F: sound/soc/codecs/wcd9335.* | ||
| 14517 | F: sound/soc/codecs/wcd934x.c | ||
| 14518 | F: sound/soc/codecs/wcd-clsh-v2.* | ||
| 14519 | F: sound/soc/codecs/wsa881x.c | ||
| 14519 | F: sound/soc/qcom/ | 14520 | F: sound/soc/qcom/ |
| 14520 | 14521 | ||
| 14521 | QCOM IPA DRIVER | 14522 | QCOM IPA DRIVER |
| @@ -14669,7 +14670,7 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/ath.git · 147 unmodified lines | |||
| 14669 | F: drivers/net/wireless/ath/ath11k/ | 14670 | F: drivers/net/wireless/ath/ath11k/ |
| 14670 | 14671 | ||
| 14671 | QUALCOMM ATHEROS ATH9K WIRELESS DRIVER | 14672 | QUALCOMM ATHEROS ATH9K WIRELESS DRIVER |
| 14672 | M: QCA ath9k Development <ath9k-devel@qca.qualcomm.com> | 14673 | M: ath9k-devel@qca.qualcomm.com |
| 14673 | L: linux-wireless@vger.kernel.org | 14674 | L: linux-wireless@vger.kernel.org |
| 14674 | S: Supported | 14675 | S: Supported |
| 14675 | W: https://wireless.wiki.kernel.org/en/users/Drivers/ath9k | 14676 | W: https://wireless.wiki.kernel.org/en/users/Drivers/ath9k |
| @@ -14820,7 +14821,7 @@ M: Alex Deucher <alexander.deucher@amd.com> · 144 unmodified lines | |||
| 14820 | M: Christian König <christian.koenig@amd.com> | 14821 | M: Christian König <christian.koenig@amd.com> |
| 14821 | L: amd-gfx@lists.freedesktop.org | 14822 | L: amd-gfx@lists.freedesktop.org |
| 14822 | S: Supported | 14823 | S: Supported |
| 14823 | T: git git://people.freedesktop.org/~agd5f/linux | 14824 | T: git https://gitlab.freedesktop.org/agd5f/linux.git |
| 14824 | F: drivers/gpu/drm/amd/ | 14825 | F: drivers/gpu/drm/amd/ |
| 14825 | F: drivers/gpu/drm/radeon/ | 14826 | F: drivers/gpu/drm/radeon/ |
| 14826 | F: include/uapi/drm/amdgpu_drm.h | 14827 | F: include/uapi/drm/amdgpu_drm.h |
| @@ -16321,6 +16322,7 @@ M: Pekka Enberg <penberg@kernel.org> · 1494 unmodified lines | |||
| 16321 | M: David Rientjes <rientjes@google.com> | 16322 | M: David Rientjes <rientjes@google.com> |
| 16322 | M: Joonsoo Kim <iamjoonsoo.kim@lge.com> | 16323 | M: Joonsoo Kim <iamjoonsoo.kim@lge.com> |
| 16323 | M: Andrew Morton <akpm@linux-foundation.org> | 16324 | M: Andrew Morton <akpm@linux-foundation.org> |
| 16325 | M: Vlastimil Babka <vbabka@suse.cz> | ||
| 16324 | L: linux-mm@kvack.org | 16326 | L: linux-mm@kvack.org |
| 16325 | S: Maintained | 16327 | S: Maintained |
| 16326 | F: include/linux/sl?b*.h | 16328 | F: include/linux/sl?b*.h |
| @@ -16710,6 +16712,8 @@ M: Samuel Thibault <samuel.thibault@ens-lyon.org> · 383 unmodified lines | |||
| 16710 | L: speakup@linux-speakup.org | 16712 | L: speakup@linux-speakup.org |
| 16711 | S: Odd Fixes | 16713 | S: Odd Fixes |
| 16712 | W: http://www.linux-speakup.org/ | 16714 | W: http://www.linux-speakup.org/ |
| 16715 | W: https://github.com/linux-speakup/speakup | ||
| 16716 | B: https://github.com/linux-speakup/speakup/issues | ||
| 16713 | F: drivers/accessibility/speakup/ | 16717 | F: drivers/accessibility/speakup/ |
| 16714 | 16718 | ||
| 16715 | SPEAR CLOCK FRAMEWORK SUPPORT | 16719 | SPEAR CLOCK FRAMEWORK SUPPORT |
| @@ -16964,7 +16968,7 @@ M: Olivier Moysan <olivier.moysan@st.com> · 248 unmodified lines | |||
| 16964 | M: Arnaud Pouliquen <arnaud.pouliquen@st.com> | 16968 | M: Arnaud Pouliquen <arnaud.pouliquen@st.com> |
| 16965 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) | 16969 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) |
| 16966 | S: Maintained | 16970 | S: Maintained |
| 16967 | F: Documentation/devicetree/bindings/sound/st,stm32-*.txt | 16971 | F: Documentation/devicetree/bindings/iio/adc/st,stm32-*.yaml |
| 16968 | F: sound/soc/stm/ | 16972 | F: sound/soc/stm/ |
| 16969 | 16973 | ||
| 16970 | STM32 TIMER/LPTIMER DRIVERS | 16974 | STM32 TIMER/LPTIMER DRIVERS |
| @@ -17541,7 +17545,7 @@ F: arch/xtensa/ · 570 unmodified lines | |||
| 17541 | F: drivers/irqchip/irq-xtensa-* | 17545 | F: drivers/irqchip/irq-xtensa-* |
| 17542 | 17546 | ||
| 17543 | TEXAS INSTRUMENTS ASoC DRIVERS | 17547 | TEXAS INSTRUMENTS ASoC DRIVERS |
| 17544 | M: Peter Ujfalusi <peter.ujfalusi@ti.com> | 17548 | M: Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 17545 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) | 17549 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) |
| 17546 | S: Maintained | 17550 | S: Maintained |
| 17547 | F: sound/soc/ti/ | 17551 | F: sound/soc/ti/ |
| @@ -17553,9 +17557,22 @@ S: Supported · 5 unmodified lines | |||
| 17553 | F: Documentation/devicetree/bindings/iio/dac/ti,dac7612.txt | 17557 | F: Documentation/devicetree/bindings/iio/dac/ti,dac7612.txt |
| 17554 | F: drivers/iio/dac/ti-dac7612.c | 17558 | F: drivers/iio/dac/ti-dac7612.c |
| 17555 | 17559 | ||
| 17560 | TEXAS INSTRUMENTS DMA DRIVERS | ||
| 17561 | M: Peter Ujfalusi <peter.ujfalusi@gmail.com> | ||
| 17562 | L: dmaengine@vger.kernel.org | ||
| 17563 | S: Maintained | ||
| 17564 | F: Documentation/devicetree/bindings/dma/ti-dma-crossbar.txt | ||
| 17565 | F: Documentation/devicetree/bindings/dma/ti-edma.txt | ||
| 17566 | F: Documentation/devicetree/bindings/dma/ti/ | ||
| 17567 | F: drivers/dma/ti/ | ||
| 17568 | X: drivers/dma/ti/cppi41.c | ||
| 17569 | F: include/linux/dma/k3-udma-glue.h | ||
| 17570 | F: include/linux/dma/ti-cppi5.h | ||
| 17571 | F: include/linux/dma/k3-psil.h | ||
| 17572 | |||
| 17556 | TEXAS INSTRUMENTS' SYSTEM CONTROL INTERFACE (TISCI) PROTOCOL DRIVER | 17573 | TEXAS INSTRUMENTS' SYSTEM CONTROL INTERFACE (TISCI) PROTOCOL DRIVER |
| 17557 | M: Nishanth Menon <nm@ti.com> | 17574 | M: Nishanth Menon <nm@ti.com> |
| 17558 | M: Tero Kristo <t-kristo@ti.com> | 17575 | M: Tero Kristo <kristo@kernel.org> |
| 17559 | M: Santosh Shilimkar <ssantosh@kernel.org> | 17576 | M: Santosh Shilimkar <ssantosh@kernel.org> |
| 17560 | L: linux-arm-kernel@lists.infradead.org | 17577 | L: linux-arm-kernel@lists.infradead.org |
| 17561 | S: Maintained | 17578 | S: Maintained |
| @@ -17699,9 +17716,9 @@ S: Maintained · 137 unmodified lines | |||
| 17699 | F: drivers/clk/clk-cdce706.c | 17716 | F: drivers/clk/clk-cdce706.c |
| 17700 | 17717 | ||
| 17701 | TI CLOCK DRIVER | 17718 | TI CLOCK DRIVER |
| 17702 | M: Tero Kristo <t-kristo@ti.com> | 17719 | M: Tero Kristo <kristo@kernel.org> |
| 17703 | L: linux-omap@vger.kernel.org | 17720 | L: linux-omap@vger.kernel.org |
| 17704 | S: Maintained | 17721 | S: Odd Fixes |
| 17705 | F: drivers/clk/ti/ | 17722 | F: drivers/clk/ti/ |
| 17706 | F: include/linux/clk/ti.h | 17723 | F: include/linux/clk/ti.h |
| 17707 | 17724 | ||
| @@ -17838,7 +17855,7 @@ F: Documentation/devicetree/bindings/net/nfc/trf7970a.txt · 130 unmodified lines | |||
| 17838 | F: drivers/nfc/trf7970a.c | 17855 | F: drivers/nfc/trf7970a.c |
| 17839 | 17856 | ||
| 17840 | TI TWL4030 SERIES SOC CODEC DRIVER | 17857 | TI TWL4030 SERIES SOC CODEC DRIVER |
| 17841 | M: Peter Ujfalusi <peter.ujfalusi@ti.com> | 17858 | M: Peter Ujfalusi <peter.ujfalusi@gmail.com> |
| 17842 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) | 17859 | L: alsa-devel@alsa-project.org (moderated for non-subscribers) |
| 17843 | S: Maintained | 17860 | S: Maintained |
| 17844 | F: sound/soc/codecs/twl4030* | 17861 | F: sound/soc/codecs/twl4030* |
| @@ -18370,7 +18387,7 @@ F: include/linux/usb/isp116x.h · 525 unmodified lines | |||
| 18370 | 18387 | ||
| 18371 | USB LAN78XX ETHERNET DRIVER | 18388 | USB LAN78XX ETHERNET DRIVER |
| 18372 | M: Woojung Huh <woojung.huh@microchip.com> | 18389 | M: Woojung Huh <woojung.huh@microchip.com> |
| 18373 | M: Microchip Linux Driver Support <UNGLinuxDriver@microchip.com> | 18390 | M: UNGLinuxDriver@microchip.com |
| 18374 | L: netdev@vger.kernel.org | 18391 | L: netdev@vger.kernel.org |
| 18375 | S: Maintained | 18392 | S: Maintained |
| 18376 | F: Documentation/devicetree/bindings/net/microchip,lan78xx.txt | 18393 | F: Documentation/devicetree/bindings/net/microchip,lan78xx.txt |
| @@ -18404,7 +18421,7 @@ F: Documentation/usb/ohci.rst · 27 unmodified lines | |||
| 18404 | F: drivers/usb/host/ohci* | 18421 | F: drivers/usb/host/ohci* |
| 18405 | 18422 | ||
| 18406 | USB OTG FSM (Finite State Machine) | 18423 | USB OTG FSM (Finite State Machine) |
| 18407 | M: Peter Chen <Peter.Chen@nxp.com> | 18424 | M: Peter Chen <peter.chen@kernel.org> |
| 18408 | L: linux-usb@vger.kernel.org | 18425 | L: linux-usb@vger.kernel.org |
| 18409 | S: Maintained | 18426 | S: Maintained |
| 18410 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/peter.chen/usb.git | 18427 | T: git git://git.kernel.org/pub/scm/linux/kernel/git/peter.chen/usb.git |
| @@ -18484,7 +18501,7 @@ F: drivers/net/usb/smsc75xx.* · 73 unmodified lines | |||
| 18484 | 18501 | ||
| 18485 | USB SMSC95XX ETHERNET DRIVER | 18502 | USB SMSC95XX ETHERNET DRIVER |
| 18486 | M: Steve Glendinning <steve.glendinning@shawell.net> | 18503 | M: Steve Glendinning <steve.glendinning@shawell.net> |
| 18487 | M: Microchip Linux Driver Support <UNGLinuxDriver@microchip.com> | 18504 | M: UNGLinuxDriver@microchip.com |
| 18488 | L: netdev@vger.kernel.org | 18505 | L: netdev@vger.kernel.org |
| 18489 | S: Maintained | 18506 | S: Maintained |
| 18490 | F: drivers/net/usb/smsc95xx.* | 18507 | F: drivers/net/usb/smsc95xx.* |
| @@ -19031,7 +19048,7 @@ F: drivers/input/mouse/vmmouse.h · 540 unmodified lines | |||
| 19031 | 19048 | ||
| 19032 | VMWARE VMXNET3 ETHERNET DRIVER | 19049 | VMWARE VMXNET3 ETHERNET DRIVER |
| 19033 | M: Ronak Doshi <doshir@vmware.com> | 19050 | M: Ronak Doshi <doshir@vmware.com> |
| 19034 | M: "VMware, Inc." <pv-drivers@vmware.com> | 19051 | M: pv-drivers@vmware.com |
| 19035 | L: netdev@vger.kernel.org | 19052 | L: netdev@vger.kernel.org |
| 19036 | S: Maintained | 19053 | S: Maintained |
| 19037 | F: drivers/net/vmxnet3/ | 19054 | F: drivers/net/vmxnet3/ |
| @@ -19058,7 +19075,6 @@ K: regulator_get_optional · 20 unmodified lines | |||
| 19058 | 19075 | ||
| 19059 | VRF | 19076 | VRF |
| 19060 | M: David Ahern <dsahern@kernel.org> | 19077 | M: David Ahern <dsahern@kernel.org> |
| 19061 | M: Shrijeet Mukherjee <shrijeet@gmail.com> | ||
| 19062 | L: netdev@vger.kernel.org | 19078 | L: netdev@vger.kernel.org |
| 19063 | S: Maintained | 19079 | S: Maintained |
| 19064 | F: Documentation/networking/vrf.rst | 19080 | F: Documentation/networking/vrf.rst |
| @@ -19409,7 +19425,7 @@ F: drivers/net/ethernet/*/*/*xdp* · 344 unmodified lines | |||
| 19409 | K: (?:\b|_)xdp(?:\b|_) | 19425 | K: (?:\b|_)xdp(?:\b|_) |
| 19410 | 19426 | ||
| 19411 | XDP SOCKETS (AF_XDP) | 19427 | XDP SOCKETS (AF_XDP) |
| 19412 | M: Björn Töpel <bjorn.topel@intel.com> | 19428 | M: Björn Töpel <bjorn@kernel.org> |
| 19413 | M: Magnus Karlsson <magnus.karlsson@intel.com> | 19429 | M: Magnus Karlsson <magnus.karlsson@intel.com> |
| 19414 | R: Jonathan Lemon <jonathan.lemon@gmail.com> | 19430 | R: Jonathan Lemon <jonathan.lemon@gmail.com> |
| 19415 | L: netdev@vger.kernel.org | 19431 | L: netdev@vger.kernel.org |
| @@ -19505,7 +19521,7 @@ F: arch/x86/xen/*swiotlb* · 89 unmodified lines | |||
| 19505 | F: drivers/xen/*swiotlb* | 19521 | F: drivers/xen/*swiotlb* |
| 19506 | 19522 | ||
| 19507 | XFS FILESYSTEM | 19523 | XFS FILESYSTEM |
| 19508 | M: Darrick J. Wong <darrick.wong@oracle.com> | 19524 | M: Darrick J. Wong <djwong@kernel.org> |
| 19509 | M: linux-xfs@vger.kernel.org | 19525 | M: linux-xfs@vger.kernel.org |
| 19510 | L: linux-xfs@vger.kernel.org | 19526 | L: linux-xfs@vger.kernel.org |
| 19511 | S: Supported | 19527 | S: Supported |
| @@ -2,8 +2,8 @@ · 1 unmodified line | |||
| 2 | VERSION = 5 | 2 | VERSION = 5 |
| 3 | PATCHLEVEL = 11 | 3 | PATCHLEVEL = 11 |
| 4 | SUBLEVEL = 0 | 4 | SUBLEVEL = 0 |
| 5 | EXTRAVERSION = -rc2 | 5 | EXTRAVERSION = |
| 6 | NAME = Kleptomaniac Octopus | 6 | NAME = 💕 Valentine's Day Edition 💕 |
| 7 | 7 | ||
| 8 | # *DOCUMENTATION* | 8 | # *DOCUMENTATION* |
| 9 | # To see a list of typical targets execute "make help" | 9 | # To see a list of typical targets execute "make help" |
| @@ -452,7 +452,6 @@ AWK = awk · 442 unmodified lines | |||
| 452 | INSTALLKERNEL := installkernel | 452 | INSTALLKERNEL := installkernel |
| 453 | DEPMOD = depmod | 453 | DEPMOD = depmod |
| 454 | PERL = perl | 454 | PERL = perl |
| 455 | PYTHON = python | ||
| 456 | PYTHON3 = python3 | 455 | PYTHON3 = python3 |
| 457 | CHECK = sparse | 456 | CHECK = sparse |
| 458 | BASH = bash | 457 | BASH = bash |
| @@ -508,7 +507,7 @@ CLANG_FLAGS := · 49 unmodified lines | |||
| 508 | 507 | ||
| 509 | export ARCH SRCARCH CONFIG_SHELL BASH HOSTCC KBUILD_HOSTCFLAGS CROSS_COMPILE LD CC | 508 | export ARCH SRCARCH CONFIG_SHELL BASH HOSTCC KBUILD_HOSTCFLAGS CROSS_COMPILE LD CC |
| 510 | export CPP AR NM STRIP OBJCOPY OBJDUMP READELF PAHOLE RESOLVE_BTFIDS LEX YACC AWK INSTALLKERNEL | 509 | export CPP AR NM STRIP OBJCOPY OBJDUMP READELF PAHOLE RESOLVE_BTFIDS LEX YACC AWK INSTALLKERNEL |
| 511 | export PERL PYTHON PYTHON3 CHECK CHECKFLAGS MAKE UTS_MACHINE HOSTCXX | 510 | export PERL PYTHON3 CHECK CHECKFLAGS MAKE UTS_MACHINE HOSTCXX |
| 512 | export KGZIP KBZIP2 KLZOP LZMA LZ4 XZ ZSTD | 511 | export KGZIP KBZIP2 KLZOP LZMA LZ4 XZ ZSTD |
| 513 | export KBUILD_HOSTCXXFLAGS KBUILD_HOSTLDFLAGS KBUILD_HOSTLDLIBS LDFLAGS_MODULE | 512 | export KBUILD_HOSTCXXFLAGS KBUILD_HOSTLDFLAGS KBUILD_HOSTLDLIBS LDFLAGS_MODULE |
| 514 | 513 | ||
| @@ -812,10 +811,12 @@ KBUILD_CFLAGS += -ftrivial-auto-var-init=zero · 297 unmodified lines | |||
| 812 | KBUILD_CFLAGS += -enable-trivial-auto-var-init-zero-knowing-it-will-be-removed-from-clang | 811 | KBUILD_CFLAGS += -enable-trivial-auto-var-init-zero-knowing-it-will-be-removed-from-clang |
| 813 | endif | 812 | endif |
| 814 | 813 | ||
| 814 | DEBUG_CFLAGS := | ||
| 815 | |||
| 815 | # Workaround for GCC versions < 5.0 | 816 | # Workaround for GCC versions < 5.0 |
| 816 | # https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61801 | 817 | # https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61801 |
| 817 | ifdef CONFIG_CC_IS_GCC | 818 | ifdef CONFIG_CC_IS_GCC |
| 818 | DEBUG_CFLAGS := $(call cc-ifversion, -lt, 0500, $(call cc-option, -fno-var-tracking-assignments)) | 819 | DEBUG_CFLAGS += $(call cc-ifversion, -lt, 0500, $(call cc-option, -fno-var-tracking-assignments)) |
| 819 | endif | 820 | endif |
| 820 | 821 | ||
| 821 | ifdef CONFIG_DEBUG_INFO | 822 | ifdef CONFIG_DEBUG_INFO |
| @@ -948,12 +949,6 @@ KBUILD_CFLAGS += $(call cc-option,-Werror=designated-init) · 126 unmodified lines | |||
| 948 | # change __FILE__ to the relative path from the srctree | 949 | # change __FILE__ to the relative path from the srctree |
| 949 | KBUILD_CPPFLAGS += $(call cc-option,-fmacro-prefix-map=$(srctree)/=) | 950 | KBUILD_CPPFLAGS += $(call cc-option,-fmacro-prefix-map=$(srctree)/=) |
| 950 | 951 | ||
| 951 | # ensure -fcf-protection is disabled when using retpoline as it is | ||
| 952 | # incompatible with -mindirect-branch=thunk-extern | ||
| 953 | ifdef CONFIG_RETPOLINE | ||
| 954 | KBUILD_CFLAGS += $(call cc-option,-fcf-protection=none) | ||
| 955 | endif | ||
| 956 | |||
| 957 | # include additional Makefiles when needed | 952 | # include additional Makefiles when needed |
| 958 | include-y := scripts/Makefile.extrawarn | 953 | include-y := scripts/Makefile.extrawarn |
| 959 | include-$(CONFIG_KASAN) += scripts/Makefile.kasan | 954 | include-$(CONFIG_KASAN) += scripts/Makefile.kasan |
| @@ -1105,6 +1105,12 @@ config HAVE_ARCH_PFN_VALID · 1104 unmodified lines | |||
| 1105 | config ARCH_SUPPORTS_DEBUG_PAGEALLOC | 1105 | config ARCH_SUPPORTS_DEBUG_PAGEALLOC |
| 1106 | bool | 1106 | bool |
| 1107 | 1107 | ||
| 1108 | config ARCH_SPLIT_ARG64 | ||
| 1109 | bool | ||
| 1110 | help | ||
| 1111 | If a 32-bit architecture requires 64-bit arguments to be split into | ||
| 1112 | pairs of 32-bit arguments, select this option. | ||
| 1113 | |||
| 1108 | source "kernel/gcov/Kconfig" | 1114 | source "kernel/gcov/Kconfig" |
| 1109 | 1115 | ||
| 1110 | source "scripts/gcc-plugins/Kconfig" | 1116 | source "scripts/gcc-plugins/Kconfig" |
| @@ -102,16 +102,22 @@ libs-y += arch/arc/lib/ $(LIBGCC) · 101 unmodified lines | |||
| 102 | 102 | ||
| 103 | boot := arch/arc/boot | 103 | boot := arch/arc/boot |
| 104 | 104 | ||
| 105 | #default target for make without any arguments. | 105 | boot_targets := uImage.bin uImage.gz uImage.lzma |
| 106 | KBUILD_IMAGE := $(boot)/bootpImage | ||
| 107 | |||
| 108 | all: bootpImage | ||
| 109 | bootpImage: vmlinux | ||
| 110 | |||
| 111 | boot_targets += uImage uImage.bin uImage.gz | ||
| 112 | 106 | ||
| 107 | PHONY += $(boot_targets) | ||
| 113 | $(boot_targets): vmlinux | 108 | $(boot_targets): vmlinux |
| 114 | $(Q)$(MAKE) $(build)=$(boot) $(boot)/$@ | 109 | $(Q)$(MAKE) $(build)=$(boot) $(boot)/$@ |
| 115 | 110 | ||
| 111 | uimage-default-y := uImage.bin | ||
| 112 | uimage-default-$(CONFIG_KERNEL_GZIP) := uImage.gz | ||
| 113 | uimage-default-$(CONFIG_KERNEL_LZMA) := uImage.lzma | ||
| 114 | |||
| 115 | PHONY += uImage | ||
| 116 | uImage: $(uimage-default-y) | ||
| 117 | @ln -sf $< $(boot)/uImage | ||
| 118 | @$(kecho) ' Image $(boot)/uImage is ready' | ||
| 119 | |||
| 120 | CLEAN_FILES += $(boot)/uImage | ||
| 121 | |||
| 116 | archclean: | 122 | archclean: |
| 117 | $(Q)$(MAKE) $(clean)=$(boot) | 123 | $(Q)$(MAKE) $(clean)=$(boot) |
| @@ -1,5 +1,4 @@ | |||
| 1 | # SPDX-License-Identifier: GPL-2.0 | 1 | # SPDX-License-Identifier: GPL-2.0 |
| 2 | targets := vmlinux.bin vmlinux.bin.gz uImage | ||
| 3 | 2 | ||
| 4 | # uImage build relies on mkimage being availble on your host for ARC target | 3 | # uImage build relies on mkimage being availble on your host for ARC target |
| 5 | # You will need to build u-boot for ARC, rename mkimage to arc-elf32-mkimage | 4 | # You will need to build u-boot for ARC, rename mkimage to arc-elf32-mkimage |
| @@ -7,23 +6,18 @@ targets := vmlinux.bin vmlinux.bin.gz uImage · 1 unmodified line | |||
| 7 | 6 | ||
| 8 | OBJCOPYFLAGS= -O binary -R .note -R .note.gnu.build-id -R .comment -S | 7 | OBJCOPYFLAGS= -O binary -R .note -R .note.gnu.build-id -R .comment -S |
| 9 | 8 | ||
| 10 | LINUX_START_TEXT = $$(readelf -h vmlinux | \ | 9 | LINUX_START_TEXT = $$($(READELF) -h vmlinux | \ |
| 11 | grep "Entry point address" | grep -o 0x.*) | 10 | grep "Entry point address" | grep -o 0x.*) |
| 12 | 11 | ||
| 13 | UIMAGE_LOADADDR = $(CONFIG_LINUX_LINK_BASE) | 12 | UIMAGE_LOADADDR = $(CONFIG_LINUX_LINK_BASE) |
| 14 | UIMAGE_ENTRYADDR = $(LINUX_START_TEXT) | 13 | UIMAGE_ENTRYADDR = $(LINUX_START_TEXT) |
| 15 | 14 | ||
| 16 | suffix-y := bin | 15 | targets += vmlinux.bin |
| 17 | suffix-$(CONFIG_KERNEL_GZIP) := gz | 16 | targets += vmlinux.bin.gz |
| 18 | suffix-$(CONFIG_KERNEL_LZMA) := lzma | 17 | targets += vmlinux.bin.lzma |
| 19 | |||
| 20 | targets += uImage | ||
| 21 | targets += uImage.bin | 18 | targets += uImage.bin |
| 22 | targets += uImage.gz | 19 | targets += uImage.gz |
| 23 | targets += uImage.lzma | 20 | targets += uImage.lzma |
| 24 | extra-y += vmlinux.bin | ||
| 25 | extra-y += vmlinux.bin.gz | ||
| 26 | extra-y += vmlinux.bin.lzma | ||
| 27 | 21 | ||
| 28 | $(obj)/vmlinux.bin: vmlinux FORCE | 22 | $(obj)/vmlinux.bin: vmlinux FORCE |
| 29 | $(call if_changed,objcopy) | 23 | $(call if_changed,objcopy) |
| @@ -42,7 +36,3 @@ $(obj)/uImage.gz: $(obj)/vmlinux.bin.gz FORCE · 12 unmodified lines | |||
| 42 | 36 | ||
| 43 | $(obj)/uImage.lzma: $(obj)/vmlinux.bin.lzma FORCE | 37 | $(obj)/uImage.lzma: $(obj)/vmlinux.bin.lzma FORCE |
| 44 | $(call if_changed,uimage,lzma) | 38 | $(call if_changed,uimage,lzma) |
| 45 | |||
| 46 | $(obj)/uImage: $(obj)/uImage.$(suffix-y) | ||
| 47 | @ln -sf $(notdir $<) $@ | ||
| 48 | @echo ' Image $@ is ready' | ||
| @@ -10,6 +10,7 @@ · 9 unmodified lines | |||
| 10 | #ifndef __ASSEMBLY__ | 10 | #ifndef __ASSEMBLY__ |
| 11 | 11 | ||
| 12 | #define clear_page(paddr) memset((paddr), 0, PAGE_SIZE) | 12 | #define clear_page(paddr) memset((paddr), 0, PAGE_SIZE) |
| 13 | #define copy_user_page(to, from, vaddr, pg) copy_page(to, from) | ||
| 13 | #define copy_page(to, from) memcpy((to), (from), PAGE_SIZE) | 14 | #define copy_page(to, from) memcpy((to), (from), PAGE_SIZE) |
| 14 | 15 | ||
| 15 | struct vm_area_struct; | 16 | struct vm_area_struct; |
| @@ -307,7 +307,7 @@ resume_user_mode_begin: · 306 unmodified lines | |||
| 307 | mov r0, sp ; pt_regs for arg to do_signal()/do_notify_resume() | 307 | mov r0, sp ; pt_regs for arg to do_signal()/do_notify_resume() |
| 308 | 308 | ||
| 309 | GET_CURR_THR_INFO_FLAGS r9 | 309 | GET_CURR_THR_INFO_FLAGS r9 |
| 310 | and.f 0, r9, TIF_SIGPENDING|TIF_NOTIFY_SIGNAL | 310 | and.f 0, r9, _TIF_SIGPENDING|_TIF_NOTIFY_SIGNAL |
| 311 | bz .Lchk_notify_resume | 311 | bz .Lchk_notify_resume |
| 312 | 312 | ||
| 313 | ; Normal Trap/IRQ entry only saves Scratch (caller-saved) regs | 313 | ; Normal Trap/IRQ entry only saves Scratch (caller-saved) regs |
| @@ -7,6 +7,7 @@ menuconfig ARC_SOC_HSDK · 6 unmodified lines | |||
| 7 | depends on ISA_ARCV2 | 7 | depends on ISA_ARCV2 |
| 8 | select ARC_HAS_ACCL_REGS | 8 | select ARC_HAS_ACCL_REGS |
| 9 | select ARC_IRQ_NO_AUTOSAVE | 9 | select ARC_IRQ_NO_AUTOSAVE |
| 10 | select ARC_FPU_SAVE_RESTORE | ||
| 10 | select CLK_HSDK | 11 | select CLK_HSDK |
| 11 | select RESET_CONTROLLER | 12 | select RESET_CONTROLLER |
| 12 | select RESET_HSDK | 13 | select RESET_HSDK |
| @@ -15,7 +15,8 @@ static int node_offset(void *fdt, const char *node_path) · 14 unmodified lines | |||
| 15 | { | 15 | { |
| 16 | int offset = fdt_path_offset(fdt, node_path); | 16 | int offset = fdt_path_offset(fdt, node_path); |
| 17 | if (offset == -FDT_ERR_NOTFOUND) | 17 | if (offset == -FDT_ERR_NOTFOUND) |
| 18 | offset = fdt_add_subnode(fdt, 0, node_path); | 18 | /* Add the node to root if not found, dropping the leading '/' */ |
| 19 | offset = fdt_add_subnode(fdt, 0, node_path + 1); | ||
| 19 | return offset; | 20 | return offset; |
| 20 | } | 21 | } |
| 21 | 22 | ||
| @@ -16,6 +16,13 @@ · 15 unmodified lines | |||
| 16 | stdout-path = &uart1; | 16 | stdout-path = &uart1; |
| 17 | }; | 17 | }; |
| 18 | 18 | ||
| 19 | aliases { | ||
| 20 | mmc0 = &usdhc2; | ||
| 21 | mmc1 = &usdhc3; | ||
| 22 | mmc2 = &usdhc4; | ||
| 23 | /delete-property/ mmc3; | ||
| 24 | }; | ||
| 25 | |||
| 19 | memory@10000000 { | 26 | memory@10000000 { |
| 20 | device_type = "memory"; | 27 | device_type = "memory"; |
| 21 | reg = <0x10000000 0x80000000>; | 28 | reg = <0x10000000 0x80000000>; |
| @@ -418,7 +418,7 @@ · 417 unmodified lines | |||
| 418 | 418 | ||
| 419 | /* VDD_AUD_1P8: Audio codec */ | 419 | /* VDD_AUD_1P8: Audio codec */ |
| 420 | reg_aud_1p8v: ldo3 { | 420 | reg_aud_1p8v: ldo3 { |
| 421 | regulator-name = "vdd1p8"; | 421 | regulator-name = "vdd1p8a"; |
| 422 | regulator-min-microvolt = <1800000>; | 422 | regulator-min-microvolt = <1800000>; |
| 423 | regulator-max-microvolt = <1800000>; | 423 | regulator-max-microvolt = <1800000>; |
| 424 | regulator-boot-on; | 424 | regulator-boot-on; |
| @@ -137,7 +137,7 @@ · 136 unmodified lines | |||
| 137 | 137 | ||
| 138 | lcd_backlight: lcd-backlight { | 138 | lcd_backlight: lcd-backlight { |
| 139 | compatible = "pwm-backlight"; | 139 | compatible = "pwm-backlight"; |
| 140 | pwms = <&pwm4 0 5000000>; | 140 | pwms = <&pwm4 0 5000000 0>; |
| 141 | pwm-names = "LCD_BKLT_PWM"; | 141 | pwm-names = "LCD_BKLT_PWM"; |
| 142 | 142 | ||
| 143 | brightness-levels = <0 10 20 30 40 50 60 70 80 90 100>; | 143 | brightness-levels = <0 10 20 30 40 50 60 70 80 90 100>; |
| @@ -167,7 +167,7 @@ · 23 unmodified lines | |||
| 167 | i2c-gpio,delay-us = <2>; /* ~100 kHz */ | 167 | i2c-gpio,delay-us = <2>; /* ~100 kHz */ |
| 168 | #address-cells = <1>; | 168 | #address-cells = <1>; |
| 169 | #size-cells = <0>; | 169 | #size-cells = <0>; |
| 170 | status = "disabld"; | 170 | status = "disabled"; |
| 171 | }; | 171 | }; |
| 172 | 172 | ||
| 173 | i2c_cam: i2c-gpio-cam { | 173 | i2c_cam: i2c-gpio-cam { |
| @@ -179,7 +179,7 @@ · 5 unmodified lines | |||
| 179 | i2c-gpio,delay-us = <2>; /* ~100 kHz */ | 179 | i2c-gpio,delay-us = <2>; /* ~100 kHz */ |
| 180 | #address-cells = <1>; | 180 | #address-cells = <1>; |
| 181 | #size-cells = <0>; | 181 | #size-cells = <0>; |
| 182 | status = "disabld"; | 182 | status = "disabled"; |
| 183 | }; | 183 | }; |
| 184 | }; | 184 | }; |
| 185 | 185 | ||
| @@ -53,7 +53,6 @@ · 52 unmodified lines | |||
| 53 | &fec { | 53 | &fec { |
| 54 | pinctrl-names = "default"; | 54 | pinctrl-names = "default"; |
| 55 | pinctrl-0 = <&pinctrl_microsom_enet_ar8035>; | 55 | pinctrl-0 = <&pinctrl_microsom_enet_ar8035>; |
| 56 | phy-handle = <&phy>; | ||
| 57 | phy-mode = "rgmii-id"; | 56 | phy-mode = "rgmii-id"; |
| 58 | phy-reset-duration = <2>; | 57 | phy-reset-duration = <2>; |
| 59 | phy-reset-gpios = <&gpio4 15 GPIO_ACTIVE_LOW>; | 58 | phy-reset-gpios = <&gpio4 15 GPIO_ACTIVE_LOW>; |
| @@ -63,10 +62,19 @@ · 3 unmodified lines | |||
| 63 | #address-cells = <1>; | 62 | #address-cells = <1>; |
| 64 | #size-cells = <0>; | 63 | #size-cells = <0>; |
| 65 | 64 | ||
| 66 | phy: ethernet-phy@0 { | 65 | /* |
| 66 | * The PHY can appear at either address 0 or 4 due to the | ||
| 67 | * configuration (LED) pin not being pulled sufficiently. | ||
| 68 | */ | ||
| 69 | ethernet-phy@0 { | ||
| 67 | reg = <0>; | 70 | reg = <0>; |
| 68 | qca,clk-out-frequency = <125000000>; | 71 | qca,clk-out-frequency = <125000000>; |
| 69 | }; | 72 | }; |
| 73 | |||
| 74 | ethernet-phy@4 { | ||
| 75 | reg = <4>; | ||
| 76 | qca,clk-out-frequency = <125000000>; | ||
| 77 | }; | ||
| 70 | }; | 78 | }; |
| 71 | }; | 79 | }; |
| 72 | 80 | ||
| @@ -115,6 +115,7 @@ · 114 unmodified lines | |||
| 115 | compatible = "nxp,pcf2127"; | 115 | compatible = "nxp,pcf2127"; |
| 116 | reg = <0>; | 116 | reg = <0>; |
| 117 | spi-max-frequency = <2000000>; | 117 | spi-max-frequency = <2000000>; |
| 118 | reset-source; | ||
| 118 | }; | 119 | }; |
| 119 | }; | 120 | }; |
| 120 | 121 | ||
| @@ -326,9 +326,6 @@ · 325 unmodified lines | |||
| 326 | 326 | ||
| 327 | clocks = <&xtal_32k>, <&xtal>; | 327 | clocks = <&xtal_32k>, <&xtal>; |
| 328 | clock-names = "xtal_32k", "xtal"; | 328 | clock-names = "xtal_32k", "xtal"; |
| 329 | |||
| 330 | assigned-clocks = <&clk LPC32XX_CLK_HCLK_PLL>; | ||
| 331 | assigned-clock-rates = <208000000>; | ||
| 332 | }; | 329 | }; |
| 333 | }; | 330 | }; |
| 334 | 331 | ||
| @@ -114,7 +114,7 @@ · 113 unmodified lines | |||
| 114 | gpio-sck = <&gpio1 12 GPIO_ACTIVE_HIGH>; | 114 | gpio-sck = <&gpio1 12 GPIO_ACTIVE_HIGH>; |
| 115 | gpio-miso = <&gpio1 18 GPIO_ACTIVE_HIGH>; | 115 | gpio-miso = <&gpio1 18 GPIO_ACTIVE_HIGH>; |
| 116 | gpio-mosi = <&gpio1 20 GPIO_ACTIVE_HIGH>; | 116 | gpio-mosi = <&gpio1 20 GPIO_ACTIVE_HIGH>; |
| 117 | cs-gpios = <&gpio1 19 GPIO_ACTIVE_HIGH>; | 117 | cs-gpios = <&gpio1 19 GPIO_ACTIVE_LOW>; |
| 118 | num-chipselects = <1>; | 118 | num-chipselects = <1>; |
| 119 | 119 | ||
| 120 | /* lcd panel */ | 120 | /* lcd panel */ |
| @@ -124,7 +124,6 @@ · 3 unmodified lines | |||
| 124 | spi-max-frequency = <100000>; | 124 | spi-max-frequency = <100000>; |
| 125 | spi-cpol; | 125 | spi-cpol; |
| 126 | spi-cpha; | 126 | spi-cpha; |
| 127 | spi-cs-high; | ||
| 128 | 127 | ||
| 129 | backlight= <&backlight>; | 128 | backlight= <&backlight>; |
| 130 | label = "lcd"; | 129 | label = "lcd"; |
| @@ -494,3 +494,11 @@ · 493 unmodified lines | |||
| 494 | clock-names = "sysclk"; | 494 | clock-names = "sysclk"; |
| 495 | }; | 495 | }; |
| 496 | }; | 496 | }; |
| 497 | |||
| 498 | &aes1_target { | ||
| 499 | status = "disabled"; | ||
| 500 | }; | ||
| 501 | |||
| 502 | &aes2_target { | ||
| 503 | status = "disabled"; | ||
| 504 | }; | ||
| @@ -16,8 +16,13 @@ · 15 unmodified lines | |||
| 16 | debounce-interval = <10>; | 16 | debounce-interval = <10>; |
| 17 | }; | 17 | }; |
| 18 | 18 | ||
| 19 | /* | ||
| 20 | * We use pad 0x4a100116 abe_dmic_din3.gpio_122 as the irq instead | ||
| 21 | * of the gpio interrupt to avoid lost events in deeper idle states. | ||
| 22 | */ | ||
| 19 | slider { | 23 | slider { |
| 20 | label = "Keypad Slide"; | 24 | label = "Keypad Slide"; |
| 25 | interrupts-extended = <&omap4_pmx_core 0xd6>; | ||
| 21 | gpios = <&gpio4 26 GPIO_ACTIVE_HIGH>; /* gpio122 */ | 26 | gpios = <&gpio4 26 GPIO_ACTIVE_HIGH>; /* gpio122 */ |
| 22 | linux,input-type = <EV_SW>; | 27 | linux,input-type = <EV_SW>; |
| 23 | linux,code = <SW_KEYPAD_SLIDE>; | 28 | linux,code = <SW_KEYPAD_SLIDE>; |
| @@ -45,18 +45,21 @@ · 44 unmodified lines | |||
| 45 | emac: gem@30000 { | 45 | emac: gem@30000 { |
| 46 | compatible = "cadence,gem"; | 46 | compatible = "cadence,gem"; |
| 47 | reg = <0x30000 0x10000>; | 47 | reg = <0x30000 0x10000>; |
| 48 | interrupt-parent = <&vic0>; | ||
| 48 | interrupts = <31>; | 49 | interrupts = <31>; |
| 49 | }; | 50 | }; |
| 50 | 51 | ||
| 51 | dmac1: dmac@40000 { | 52 | dmac1: dmac@40000 { |
| 52 | compatible = "snps,dw-dmac"; | 53 | compatible = "snps,dw-dmac"; |
| 53 | reg = <0x40000 0x10000>; | 54 | reg = <0x40000 0x10000>; |
| 55 | interrupt-parent = <&vic0>; | ||
| 54 | interrupts = <25>; | 56 | interrupts = <25>; |
| 55 | }; | 57 | }; |
| 56 | 58 | ||
| 57 | dmac2: dmac@50000 { | 59 | dmac2: dmac@50000 { |
| 58 | compatible = "snps,dw-dmac"; | 60 | compatible = "snps,dw-dmac"; |
| 59 | reg = <0x50000 0x10000>; | 61 | reg = <0x50000 0x10000>; |
| 62 | interrupt-parent = <&vic0>; | ||
| 60 | interrupts = <26>; | 63 | interrupts = <26>; |
| 61 | }; | 64 | }; |
| 62 | 65 | ||
| @@ -233,6 +236,7 @@ · 170 unmodified lines | |||
| 233 | axi2pico@c0000000 { | 236 | axi2pico@c0000000 { |
| 234 | compatible = "picochip,axi2pico-pc3x2"; | 237 | compatible = "picochip,axi2pico-pc3x2"; |
| 235 | reg = <0xc0000000 0x10000>; | 238 | reg = <0xc0000000 0x10000>; |
| 239 | interrupt-parent = <&vic0>; | ||
| 236 | interrupts = <13 14 15 16 17 18 19 20 21>; | 240 | interrupts = <13 14 15 16 17 18 19 20 21>; |
| 237 | }; | 241 | }; |
| 238 | }; | 242 | }; |
| @@ -12,4 +12,42 @@ · 11 unmodified lines | |||
| 12 | 200000 0>; | 12 | 200000 0>; |
| 13 | }; | 13 | }; |
| 14 | }; | 14 | }; |
| 15 | |||
| 16 | reserved-memory { | ||
| 17 | #address-cells = <1>; | ||
| 18 | #size-cells = <1>; | ||
| 19 | ranges; | ||
| 20 | |||
| 21 | /* Modem trace memory */ | ||
| 22 | ram@06000000 { | ||
| 23 | reg = <0x06000000 0x00f00000>; | ||
| 24 | no-map; | ||
| 25 | }; | ||
| 26 | |||
| 27 | /* Modem shared memory */ | ||
| 28 | ram@06f00000 { | ||
| 29 | reg = <0x06f00000 0x00100000>; | ||
| 30 | no-map; | ||
| 31 | }; | ||
| 32 | |||
| 33 | /* Modem private memory */ | ||
| 34 | ram@07000000 { | ||
| 35 | reg = <0x07000000 0x01000000>; | ||
| 36 | no-map; | ||
| 37 | }; | ||
| 38 | |||
| 39 | /* | ||
| 40 | * Initial Secure Software ISSW memory | ||
| 41 | * | ||
| 42 | * This is probably only used if the kernel tries | ||
| 43 | * to actually call into trustzone to run secure | ||
| 44 | * applications, which the mainline kernel probably | ||
| 45 | * will not do on this old chipset. But you can never | ||
| 46 | * be too careful, so reserve this memory anyway. | ||
| 47 | */ | ||
| 48 | ram@17f00000 { | ||
| 49 | reg = <0x17f00000 0x00100000>; | ||
| 50 | no-map; | ||
| 51 | }; | ||
| 52 | }; | ||
| 15 | }; | 53 | }; |
| @@ -12,4 +12,42 @@ · 11 unmodified lines | |||
| 12 | 200000 0>; | 12 | 200000 0>; |
| 13 | }; | 13 | }; |
| 14 | }; | 14 | }; |
| 15 | |||
| 16 | reserved-memory { | ||
| 17 | #address-cells = <1>; | ||
| 18 | #size-cells = <1>; | ||
| 19 | ranges; | ||
| 20 | |||
| 21 | /* Modem trace memory */ | ||
| 22 | ram@06000000 { | ||
| 23 | reg = <0x06000000 0x00f00000>; | ||
| 24 | no-map; | ||
| 25 | }; | ||
| 26 | |||
| 27 | /* Modem shared memory */ | ||
| 28 | ram@06f00000 { | ||
| 29 | reg = <0x06f00000 0x00100000>; | ||
| 30 | no-map; | ||
| 31 | }; | ||
| 32 | |||
| 33 | /* Modem private memory */ | ||
| 34 | ram@07000000 { | ||
| 35 | reg = <0x07000000 0x01000000>; | ||
| 36 | no-map; | ||
| 37 | }; | ||
| 38 | |||
| 39 | /* | ||
| 40 | * Initial Secure Software ISSW memory | ||
| 41 | * | ||
| 42 | * This is probably only used if the kernel tries | ||
| 43 | * to actually call into trustzone to run secure | ||
| 44 | * applications, which the mainline kernel probably | ||
| 45 | * will not do on this old chipset. But you can never | ||
| 46 | * be too careful, so reserve this memory anyway. | ||
| 47 | */ | ||
| 48 | ram@17f00000 { | ||
| 49 | reg = <0x17f00000 0x00100000>; | ||
| 50 | no-map; | ||
| 51 | }; | ||
| 52 | }; | ||
| 15 | }; | 53 | }; |
| @@ -0,0 +1,35 @@ | |||
| 1 | // SPDX-License-Identifier: GPL-2.0-or-later | ||
| 2 | |||
| 3 | #include "ste-dbx5x0.dtsi" | ||
| 4 | |||
| 5 | / { | ||
| 6 | cpus { | ||
| 7 | cpu@300 { | ||
| 8 | /* cpufreq controls */ | ||
| 9 | operating-points = <1152000 0 | ||
| 10 | 800000 0 | ||
| 11 | 400000 0 | ||
| 12 | 200000 0>; | ||
| 13 | }; | ||
| 14 | }; | ||
| 15 | |||
| 16 | reserved-memory { | ||
| 17 | #address-cells = <1>; | ||
| 18 | #size-cells = <1>; | ||
| 19 | ranges; | ||
| 20 | |||
| 21 | /* | ||
| 22 | * Initial Secure Software ISSW memory | ||
| 23 | * | ||
| 24 | * This is probably only used if the kernel tries | ||
| 25 | * to actually call into trustzone to run secure | ||
| 26 | * applications, which the mainline kernel probably | ||
| 27 | * will not do on this old chipset. But you can never | ||
| 28 | * be too careful, so reserve this memory anyway. | ||
| 29 | */ | ||
| 30 | ram@17f00000 { | ||
| 31 | reg = <0x17f00000 0x00100000>; | ||
| 32 | no-map; | ||
| 33 | }; | ||
| 34 | }; | ||
| 35 | }; | ||
| @@ -4,7 +4,7 @@ · 3 unmodified lines | |||
| 4 | */ | 4 | */ |
| 5 | 5 | ||
| 6 | /dts-v1/; | 6 | /dts-v1/; |
| 7 | #include "ste-db8500.dtsi" | 7 | #include "ste-db9500.dtsi" |
| 8 | #include "ste-href-ab8500.dtsi" | 8 | #include "ste-href-ab8500.dtsi" |
| 9 | #include "ste-href-family-pinctrl.dtsi" | 9 | #include "ste-href-family-pinctrl.dtsi" |
| 10 | 10 | ||
| @@ -329,6 +329,7 @@ · 328 unmodified lines | |||
| 329 | panel@0 { | 329 | panel@0 { |
| 330 | compatible = "samsung,s6e63m0"; | 330 | compatible = "samsung,s6e63m0"; |
| 331 | reg = <0>; | 331 | reg = <0>; |
| 332 | max-brightness = <15>; | ||
| 332 | vdd3-supply = <&panel_reg_3v0>; | 333 | vdd3-supply = <&panel_reg_3v0>; |
| 333 | vci-supply = <&panel_reg_1v8>; | 334 | vci-supply = <&panel_reg_1v8>; |
| 334 | reset-gpios = <&gpio4 11 GPIO_ACTIVE_LOW>; | 335 | reset-gpios = <&gpio4 11 GPIO_ACTIVE_LOW>; |
| @@ -33,9 +33,9 @@ · 32 unmodified lines | |||
| 33 | * during TX anyway and that it only controls drive enable DE | 33 | * during TX anyway and that it only controls drive enable DE |
| 34 | * line. Hence, the RX is always enabled here. | 34 | * line. Hence, the RX is always enabled here. |
| 35 | */ | 35 | */ |
| 36 | rs485-rx-en { | 36 | rs485-rx-en-hog { |
| 37 | gpio-hog; | 37 | gpio-hog; |
| 38 | gpios = <8 GPIO_ACTIVE_HIGH>; | 38 | gpios = <8 0>; |
| 39 | output-low; | 39 | output-low; |
| 40 | line-name = "rs485-rx-en"; | 40 | line-name = "rs485-rx-en"; |
| 41 | }; | 41 | }; |
| @@ -61,9 +61,9 @@ · 19 unmodified lines | |||
| 61 | * order to reset the Hub when USB bus is powered down, but | 61 | * order to reset the Hub when USB bus is powered down, but |
| 62 | * so far there is no such functionality. | 62 | * so far there is no such functionality. |
| 63 | */ | 63 | */ |
| 64 | usb-hub { | 64 | usb-hub-hog { |
| 65 | gpio-hog; | 65 | gpio-hog; |
| 66 | gpios = <2 GPIO_ACTIVE_HIGH>; | 66 | gpios = <2 0>; |
| 67 | output-high; | 67 | output-high; |
| 68 | line-name = "usb-hub-reset"; | 68 | line-name = "usb-hub-reset"; |
| 69 | }; | 69 | }; |
| @@ -87,6 +87,12 @@ · 17 unmodified lines | |||
| 87 | }; | 87 | }; |
| 88 | }; | 88 | }; |
| 89 | 89 | ||
| 90 | &i2c4 { | ||
| 91 | touchscreen@49 { | ||
| 92 | status = "disabled"; | ||
| 93 | }; | ||
| 94 | }; | ||
| 95 | |||
| 90 | &i2c5 { /* TP7/TP8 */ | 96 | &i2c5 { /* TP7/TP8 */ |
| 91 | pinctrl-names = "default"; | 97 | pinctrl-names = "default"; |
| 92 | pinctrl-0 = <&i2c5_pins_a>; | 98 | pinctrl-0 = <&i2c5_pins_a>; |
| @@ -104,7 +110,7 @@ · 11 unmodified lines | |||
| 104 | * are used for on-board microSD slot instead. | 110 | * are used for on-board microSD slot instead. |
| 105 | */ | 111 | */ |
| 106 | /delete-property/broken-cd; | 112 | /delete-property/broken-cd; |
| 107 | cd-gpios = <&gpioi 10 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; | 113 | cd-gpios = <&gpioi 10 GPIO_ACTIVE_HIGH>; |
| 108 | disable-wp; | 114 | disable-wp; |
| 109 | }; | 115 | }; |
| 110 | 116 | ||
| @@ -43,9 +43,9 @@ · 42 unmodified lines | |||
| 43 | * in order to turn on port power when USB bus is powered up, but so | 43 | * in order to turn on port power when USB bus is powered up, but so |
| 44 | * far there is no such functionality. | 44 | * far there is no such functionality. |
| 45 | */ | 45 | */ |
| 46 | usb-port-power { | 46 | usb-port-power-hog { |
| 47 | gpio-hog; | 47 | gpio-hog; |
| 48 | gpios = <13 GPIO_ACTIVE_LOW>; | 48 | gpios = <13 0>; |
| 49 | output-low; | 49 | output-low; |
| 50 | line-name = "usb-port-power"; | 50 | line-name = "usb-port-power"; |
| 51 | }; | 51 | }; |
| @@ -390,7 +390,8 @@ · 389 unmodified lines | |||
| 390 | pinctrl-0 = <&sdmmc1_b4_pins_a &sdmmc1_dir_pins_a>; | 390 | pinctrl-0 = <&sdmmc1_b4_pins_a &sdmmc1_dir_pins_a>; |
| 391 | pinctrl-1 = <&sdmmc1_b4_od_pins_a &sdmmc1_dir_pins_a>; | 391 | pinctrl-1 = <&sdmmc1_b4_od_pins_a &sdmmc1_dir_pins_a>; |
| 392 | pinctrl-2 = <&sdmmc1_b4_sleep_pins_a &sdmmc1_dir_sleep_pins_a>; | 392 | pinctrl-2 = <&sdmmc1_b4_sleep_pins_a &sdmmc1_dir_sleep_pins_a>; |
| 393 | broken-cd; | 393 | cd-gpios = <&gpiog 1 (GPIO_ACTIVE_LOW | GPIO_PULL_UP)>; |
| 394 | disable-wp; | ||
| 394 | st,sig-dir; | 395 | st,sig-dir; |
| 395 | st,neg-edge; | 396 | st,neg-edge; |
| 396 | st,use-ckin; | 397 | st,use-ckin; |
| @@ -110,7 +110,7 @@ · 109 unmodified lines | |||
| 110 | pinctrl-names = "default"; | 110 | pinctrl-names = "default"; |
| 111 | pinctrl-0 = <&gmac_rgmii_pins>; | 111 | pinctrl-0 = <&gmac_rgmii_pins>; |
| 112 | phy-handle = <&phy1>; | 112 | phy-handle = <&phy1>; |
| 113 | phy-mode = "rgmii"; | 113 | phy-mode = "rgmii-id"; |
| 114 | phy-supply = <®_gmac_3v3>; | 114 | phy-supply = <®_gmac_3v3>; |
| 115 | status = "okay"; | 115 | status = "okay"; |
| 116 | }; | 116 | }; |
| @@ -279,6 +279,7 @@ CONFIG_SERIAL_OMAP_CONSOLE=y · 278 unmodified lines | |||
| 279 | CONFIG_SERIAL_DEV_BUS=y | 279 | CONFIG_SERIAL_DEV_BUS=y |
| 280 | CONFIG_I2C_CHARDEV=y | 280 | CONFIG_I2C_CHARDEV=y |
| 281 | CONFIG_SPI=y | 281 | CONFIG_SPI=y |
| 282 | CONFIG_SPI_GPIO=m | ||
| 282 | CONFIG_SPI_OMAP24XX=y | 283 | CONFIG_SPI_OMAP24XX=y |
| 283 | CONFIG_SPI_TI_QSPI=m | 284 | CONFIG_SPI_TI_QSPI=m |
| 284 | CONFIG_HSI=m | 285 | CONFIG_HSI=m |
| @@ -296,7 +297,6 @@ CONFIG_GPIO_TWL4030=y · 11 unmodified lines | |||
| 296 | CONFIG_W1=m | 297 | CONFIG_W1=m |
| 297 | CONFIG_HDQ_MASTER_OMAP=m | 298 | CONFIG_HDQ_MASTER_OMAP=m |
| 298 | CONFIG_W1_SLAVE_DS250X=m | 299 | CONFIG_W1_SLAVE_DS250X=m |
| 299 | CONFIG_POWER_AVS=y | ||
| 300 | CONFIG_POWER_RESET=y | 300 | CONFIG_POWER_RESET=y |
| 301 | CONFIG_POWER_RESET_GPIO=y | 301 | CONFIG_POWER_RESET_GPIO=y |
| 302 | CONFIG_BATTERY_BQ27XXX=m | 302 | CONFIG_BATTERY_BQ27XXX=m |
| @@ -60,6 +60,7 @@ static void chacha_doneon(u32 *state, u8 *dst, const u8 *src, · 59 unmodified lines | |||
| 60 | chacha_block_xor_neon(state, d, s, nrounds); | 60 | chacha_block_xor_neon(state, d, s, nrounds); |
| 61 | if (d != dst) | 61 | if (d != dst) |
| 62 | memcpy(dst, buf, bytes); | 62 | memcpy(dst, buf, bytes); |
| 63 | state[12]++; | ||
| 63 | } | 64 | } |
| 64 | } | 65 | } |
| 65 | 66 | ||
| @@ -0,0 +1,12 @@ | |||
| 1 | /* SPDX-License-Identifier: GPL-2.0 */ | ||
| 2 | #ifndef _ARM_KEXEC_INTERNAL_H | ||
| 3 | #define _ARM_KEXEC_INTERNAL_H | ||
| 4 | |||
| 5 | struct kexec_relocate_data { | ||
| 6 | unsigned long kexec_start_address; | ||
| 7 | unsigned long kexec_indirection_page; | ||
| 8 | unsigned long kexec_mach_type; | ||
| 9 | unsigned long kexec_r2; | ||
| 10 | }; | ||
| 11 | |||
| 12 | #endif | ||
| @@ -149,7 +149,34 @@ · 148 unmodified lines | |||
| 149 | 149 | ||
| 150 | .align | 150 | .align |
| 151 | 99: .word . | 151 | 99: .word . |
| 152 | #if defined(ZIMAGE) | ||
| 153 | .word . + 4 | ||
| 154 | /* | ||
| 155 | * Storage for the state maintained by the macro. | ||
| 156 | * | ||
| 157 | * In the kernel proper, this data is located in arch/arm/mach-tegra/tegra.c. | ||
| 158 | * That's because this header is included from multiple files, and we only | ||
| 159 | * want a single copy of the data. In particular, the UART probing code above | ||
| 160 | * assumes it's running using physical addresses. This is true when this file | ||
| 161 | * is included from head.o, but not when included from debug.o. So we need | ||
| 162 | * to share the probe results between the two copies, rather than having | ||
| 163 | * to re-run the probing again later. | ||
| 164 | * | ||
| 165 | * In the decompressor, we put the storage right here, since common.c | ||
| 166 | * isn't included in the decompressor build. This storage data gets put in | ||
| 167 | * .text even though it's really data, since .data is discarded from the | ||
| 168 | * decompressor. Luckily, .text is writeable in the decompressor, unless | ||
| 169 | * CONFIG_ZBOOT_ROM. That dependency is handled in arch/arm/Kconfig.debug. | ||
| 170 | */ | ||
| 171 | /* Debug UART initialization required */ | ||
| 172 | .word 1 | ||
| 173 | /* Debug UART physical address */ | ||
| 174 | .word 0 | ||
| 175 | /* Debug UART virtual address */ | ||
| 176 | .word 0 | ||
| 177 | #else | ||
| 152 | .word tegra_uart_config | 178 | .word tegra_uart_config |
| 179 | #endif | ||
| 153 | .ltorg | 180 | .ltorg |
| 154 | 181 | ||
| 155 | /* Load previously selected UART address */ | 182 | /* Load previously selected UART address */ |
| @@ -189,30 +216,3 @@ · 33 unmodified lines | |||
| 189 | 216 | ||
| 190 | .macro waituarttxrdy,rd,rx | 217 | .macro waituarttxrdy,rd,rx |
| 191 | .endm | 218 | .endm |
| 192 | |||
| 193 | /* | ||
| 194 | * Storage for the state maintained by the macros above. | ||
| 195 | * | ||
| 196 | * In the kernel proper, this data is located in arch/arm/mach-tegra/tegra.c. | ||
| 197 | * That's because this header is included from multiple files, and we only | ||
| 198 | * want a single copy of the data. In particular, the UART probing code above | ||
| 199 | * assumes it's running using physical addresses. This is true when this file | ||
| 200 | * is included from head.o, but not when included from debug.o. So we need | ||
| 201 | * to share the probe results between the two copies, rather than having | ||
| 202 | * to re-run the probing again later. | ||
| 203 | * | ||
| 204 | * In the decompressor, we put the symbol/storage right here, since common.c | ||
| 205 | * isn't included in the decompressor build. This symbol gets put in .text | ||
| 206 | * even though it's really data, since .data is discarded from the | ||
| 207 | * decompressor. Luckily, .text is writeable in the decompressor, unless | ||
| 208 | * CONFIG_ZBOOT_ROM. That dependency is handled in arch/arm/Kconfig.debug. | ||
| 209 | */ | ||
| 210 | #if defined(ZIMAGE) | ||
| 211 | tegra_uart_config: | ||
| 212 | /* Debug UART initialization required */ | ||
| 213 | .word 1 | ||
| 214 | /* Debug UART physical address */ | ||
| 215 | .word 0 | ||
| 216 | /* Debug UART virtual address */ | ||
| 217 | .word 0 | ||
| 218 | #endif | ||
| @@ -12,6 +12,7 @@ · 11 unmodified lines | |||
| 12 | #include <linux/mm.h> | 12 | #include <linux/mm.h> |
| 13 | #include <linux/dma-mapping.h> | 13 | #include <linux/dma-mapping.h> |
| 14 | #include <asm/cacheflush.h> | 14 | #include <asm/cacheflush.h> |
| 15 | #include <asm/kexec-internal.h> | ||
| 15 | #include <asm/glue-df.h> | 16 | #include <asm/glue-df.h> |
| 16 | #include <asm/glue-pf.h> | 17 | #include <asm/glue-pf.h> |
| 17 | #include <asm/mach/arch.h> | 18 | #include <asm/mach/arch.h> |
| @@ -170,5 +171,9 @@ int main(void) · 152 unmodified lines | |||
| 170 | DEFINE(MPU_RGN_PRBAR, offsetof(struct mpu_rgn, prbar)); | 171 | DEFINE(MPU_RGN_PRBAR, offsetof(struct mpu_rgn, prbar)); |
| 171 | DEFINE(MPU_RGN_PRLAR, offsetof(struct mpu_rgn, prlar)); | 172 | DEFINE(MPU_RGN_PRLAR, offsetof(struct mpu_rgn, prlar)); |
| 172 | #endif | 173 | #endif |
| 174 | DEFINE(KEXEC_START_ADDR, offsetof(struct kexec_relocate_data, kexec_start_address)); | ||
| 175 | DEFINE(KEXEC_INDIR_PAGE, offsetof(struct kexec_relocate_data, kexec_indirection_page)); | ||
| 176 | DEFINE(KEXEC_MACH_TYPE, offsetof(struct kexec_relocate_data, kexec_mach_type)); | ||
| 177 | DEFINE(KEXEC_R2, offsetof(struct kexec_relocate_data, kexec_r2)); | ||
| 173 | return 0; | 178 | return 0; |
| 174 | } | 179 | } |
| @@ -13,6 +13,7 @@ · 12 unmodified lines | |||
| 13 | #include <linux/of_fdt.h> | 13 | #include <linux/of_fdt.h> |
| 14 | #include <asm/mmu_context.h> | 14 | #include <asm/mmu_context.h> |
| 15 | #include <asm/cacheflush.h> | 15 | #include <asm/cacheflush.h> |
| 16 | #include <asm/kexec-internal.h> | ||
| 16 | #include <asm/fncpy.h> | 17 | #include <asm/fncpy.h> |
| 17 | #include <asm/mach-types.h> | 18 | #include <asm/mach-types.h> |
| 18 | #include <asm/smp_plat.h> | 19 | #include <asm/smp_plat.h> |
| @@ -22,11 +23,6 @@ · 3 unmodified lines | |||
| 22 | extern void relocate_new_kernel(void); | 23 | extern void relocate_new_kernel(void); |
| 23 | extern const unsigned int relocate_new_kernel_size; | 24 | extern const unsigned int relocate_new_kernel_size; |
| 24 | 25 | ||
| 25 | extern unsigned long kexec_start_address; | ||
| 26 | extern unsigned long kexec_indirection_page; | ||
| 27 | extern unsigned long kexec_mach_type; | ||
| 28 | extern unsigned long kexec_boot_atags; | ||
| 29 | |||
| 30 | static atomic_t waiting_for_crash_ipi; | 26 | static atomic_t waiting_for_crash_ipi; |
| 31 | 27 | ||
| 32 | /* | 28 | /* |
| @@ -159,6 +155,7 @@ void (*kexec_reinit)(void); · 126 unmodified lines | |||
| 159 | void machine_kexec(struct kimage *image) | 155 | void machine_kexec(struct kimage *image) |
| 160 | { | 156 | { |
| 161 | unsigned long page_list, reboot_entry_phys; | 157 | unsigned long page_list, reboot_entry_phys; |
| 158 | struct kexec_relocate_data *data; | ||
| 162 | void (*reboot_entry)(void); | 159 | void (*reboot_entry)(void); |
| 163 | void *reboot_code_buffer; | 160 | void *reboot_code_buffer; |
| 164 | 161 | ||
| @@ -174,18 +171,17 @@ void machine_kexec(struct kimage *image) · 9 unmodified lines | |||
| 174 | 171 | ||
| 175 | reboot_code_buffer = page_address(image->control_code_page); | 172 | reboot_code_buffer = page_address(image->control_code_page); |
| 176 | 173 | ||
| 177 | /* Prepare parameters for reboot_code_buffer*/ | ||
| 178 | set_kernel_text_rw(); | ||
| 179 | kexec_start_address = image->start; | ||
| 180 | kexec_indirection_page = page_list; | ||
| 181 | kexec_mach_type = machine_arch_type; | ||
| 182 | kexec_boot_atags = image->arch.kernel_r2; | ||
| 183 | |||
| 184 | /* copy our kernel relocation code to the control code page */ | 174 | /* copy our kernel relocation code to the control code page */ |
| 185 | reboot_entry = fncpy(reboot_code_buffer, | 175 | reboot_entry = fncpy(reboot_code_buffer, |
| 186 | &relocate_new_kernel, | 176 | &relocate_new_kernel, |
| 187 | relocate_new_kernel_size); | 177 | relocate_new_kernel_size); |
| 188 | 178 | ||
| 179 | data = reboot_code_buffer + relocate_new_kernel_size; | ||
| 180 | data->kexec_start_address = image->start; | ||
| 181 | data->kexec_indirection_page = page_list; | ||
| 182 | data->kexec_mach_type = machine_arch_type; | ||
| 183 | data->kexec_r2 = image->arch.kernel_r2; | ||
| 184 | |||
| 189 | /* get the identity mapping physical address for the reboot code */ | 185 | /* get the identity mapping physical address for the reboot code */ |
| 190 | reboot_entry_phys = virt_to_idmap(reboot_entry); | 186 | reboot_entry_phys = virt_to_idmap(reboot_entry); |
| 191 | 187 | ||
| @@ -5,14 +5,16 @@ · 4 unmodified lines | |||
| 5 | 5 | ||
| 6 | #include <linux/linkage.h> | 6 | #include <linux/linkage.h> |
| 7 | #include <asm/assembler.h> | 7 | #include <asm/assembler.h> |
| 8 | #include <asm/asm-offsets.h> | ||
| 8 | #include <asm/kexec.h> | 9 | #include <asm/kexec.h> |
| 9 | 10 | ||
| 10 | .align 3 /* not needed for this code, but keeps fncpy() happy */ | 11 | .align 3 /* not needed for this code, but keeps fncpy() happy */ |
| 11 | 12 | ||
| 12 | ENTRY(relocate_new_kernel) | 13 | ENTRY(relocate_new_kernel) |
| 13 | 14 | ||
| 14 | ldr r0,kexec_indirection_page | 15 | adr r7, relocate_new_kernel_end |
| 15 | ldr r1,kexec_start_address | 16 | ldr r0, [r7, #KEXEC_INDIR_PAGE] |
| 17 | ldr r1, [r7, #KEXEC_START_ADDR] | ||
| 16 | 18 | ||
| 17 | /* | 19 | /* |
| 18 | * If there is no indirection page (we are doing crashdumps) | 20 | * If there is no indirection page (we are doing crashdumps) |
| @@ -57,34 +59,16 @@ ENTRY(relocate_new_kernel) · 38 unmodified lines | |||
| 57 | 59 | ||
| 58 | 2: | 60 | 2: |
| 59 | /* Jump to relocated kernel */ | 61 | /* Jump to relocated kernel */ |
| 60 | mov lr,r1 | 62 | mov lr, r1 |
| 61 | mov r0,#0 | 63 | mov r0, #0 |
| 62 | ldr r1,kexec_mach_type | 64 | ldr r1, [r7, #KEXEC_MACH_TYPE] |
| 63 | ldr r2,kexec_boot_atags | 65 | ldr r2, [r7, #KEXEC_R2] |
| 64 | ARM( ret lr ) | 66 | ARM( ret lr ) |
| 65 | THUMB( bx lr ) | 67 | THUMB( bx lr ) |
| 66 | |||
| 67 | .align | ||
| 68 | |||
| 69 | .globl kexec_start_address | ||
| 70 | kexec_start_address: | ||
| 71 | .long 0x0 | ||
| 72 | |||
| 73 | .globl kexec_indirection_page | ||
| 74 | kexec_indirection_page: | ||
| 75 | .long 0x0 | ||
| 76 | |||
| 77 | .globl kexec_mach_type | ||
| 78 | kexec_mach_type: | ||
| 79 | .long 0x0 | ||
| 80 | |||
| 81 | /* phy addr of the atags for the new kernel */ | ||
| 82 | .globl kexec_boot_atags | ||
| 83 | kexec_boot_atags: | ||
| 84 | .long 0x0 | ||
| 85 | 68 | ||
| 86 | ENDPROC(relocate_new_kernel) | 69 | ENDPROC(relocate_new_kernel) |
| 87 | 70 | ||
| 71 | .align 3 | ||
| 88 | relocate_new_kernel_end: | 72 | relocate_new_kernel_end: |
| 89 | 73 | ||
| 90 | .globl relocate_new_kernel_size | 74 | .globl relocate_new_kernel_size |
| @@ -693,18 +693,20 @@ struct page *get_signal_page(void) · 692 unmodified lines | |||
| 693 | 693 | ||
| 694 | addr = page_address(page); | 694 | addr = page_address(page); |
| 695 | 695 | ||
| 696 | /* Poison the entire page */ | ||
| 697 | memset32(addr, __opcode_to_mem_arm(0xe7fddef1), | ||
| 698 | PAGE_SIZE / sizeof(u32)); | ||
| 699 | |||
| 696 | /* Give the signal return code some randomness */ | 700 | /* Give the signal return code some randomness */ |
| 697 | offset = 0x200 + (get_random_int() & 0x7fc); | 701 | offset = 0x200 + (get_random_int() & 0x7fc); |
| 698 | signal_return_offset = offset; | 702 | signal_return_offset = offset; |
| 699 | 703 | ||
| 700 | /* | 704 | /* Copy signal return handlers into the page */ |
| 701 | * Copy signal return handlers into the vector page, and | ||
| 702 | * set sigreturn to be a pointer to these. | ||
| 703 | */ | ||
| 704 | memcpy(addr + offset, sigreturn_codes, sizeof(sigreturn_codes)); | 705 | memcpy(addr + offset, sigreturn_codes, sizeof(sigreturn_codes)); |
| 705 | 706 | ||
| 706 | ptr = (unsigned long)addr + offset; | 707 | /* Flush out all instructions in this page */ |
| 707 | flush_icache_range(ptr, ptr + sizeof(sigreturn_codes)); | 708 | ptr = (unsigned long)addr; |
| 709 | flush_icache_range(ptr, ptr + PAGE_SIZE); | ||
| 708 | 710 | ||
| 709 | return page; | 711 | return page; |
| 710 | } | 712 | } |
| @@ -65,15 +65,15 @@ dc21285_read_config(struct pci_bus *bus, unsigned int devfn, int where, · 64 unmodified lines | |||
| 65 | if (addr) | 65 | if (addr) |
| 66 | switch (size) { | 66 | switch (size) { |
| 67 | case 1: | 67 | case 1: |
| 68 | asm("ldrb %0, [%1, %2]" | 68 | asm volatile("ldrb %0, [%1, %2]" |
| 69 | : "=r" (v) : "r" (addr), "r" (where) : "cc"); | 69 | : "=r" (v) : "r" (addr), "r" (where) : "cc"); |
| 70 | break; | 70 | break; |
| 71 | case 2: | 71 | case 2: |
| 72 | asm("ldrh %0, [%1, %2]" | 72 | asm volatile("ldrh %0, [%1, %2]" |
| 73 | : "=r" (v) : "r" (addr), "r" (where) : "cc"); | 73 | : "=r" (v) : "r" (addr), "r" (where) : "cc"); |
| 74 | break; | 74 | break; |
| 75 | case 4: | 75 | case 4: |
| 76 | asm("ldr %0, [%1, %2]" | 76 | asm volatile("ldr %0, [%1, %2]" |
| 77 | : "=r" (v) : "r" (addr), "r" (where) : "cc"); | 77 | : "=r" (v) : "r" (addr), "r" (where) : "cc"); |
| 78 | break; | 78 | break; |
| 79 | } | 79 | } |
| @@ -99,17 +99,17 @@ dc21285_write_config(struct pci_bus *bus, unsigned int devfn, int where, · 19 unmodified lines | |||
| 99 | if (addr) | 99 | if (addr) |
| 100 | switch (size) { | 100 | switch (size) { |
| 101 | case 1: | 101 | case 1: |
| 102 | asm("strb %0, [%1, %2]" | 102 | asm volatile("strb %0, [%1, %2]" |
| 103 | : : "r" (value), "r" (addr), "r" (where) | 103 | : : "r" (value), "r" (addr), "r" (where) |
| 104 | : "cc"); | 104 | : "cc"); |
| 105 | break; | 105 | break; |
| 106 | case 2: | 106 | case 2: |
| 107 | asm("strh %0, [%1, %2]" | 107 | asm volatile("strh %0, [%1, %2]" |
| 108 | : : "r" (value), "r" (addr), "r" (where) | 108 | : : "r" (value), "r" (addr), "r" (where) |
| 109 | : "cc"); | 109 | : "cc"); |
| 110 | break; | 110 | break; |
| 111 | case 4: | 111 | case 4: |
| 112 | asm("str %0, [%1, %2]" | 112 | asm volatile("str %0, [%1, %2]" |
| 113 | : : "r" (value), "r" (addr), "r" (where) | 113 | : : "r" (value), "r" (addr), "r" (where) |
| 114 | : "cc"); | 114 | : "cc"); |
| 115 | break; | 115 | break; |
| @@ -67,6 +67,7 @@ · 66 unmodified lines | |||
| 67 | #define MX6Q_CCM_CCR 0x0 | 67 | #define MX6Q_CCM_CCR 0x0 |
| 68 | 68 | ||
| 69 | .align 3 | 69 | .align 3 |
| 70 | .arm | ||
| 70 | 71 | ||
| 71 | .macro sync_l2_cache | 72 | .macro sync_l2_cache |
| 72 | 73 | ||
| @@ -203,6 +203,8 @@ static int osk_tps_setup(struct i2c_client *client, void *context) · 202 unmodified lines | |||
| 203 | */ | 203 | */ |
| 204 | gpio_request(OSK_TPS_GPIO_USB_PWR_EN, "n_vbus_en"); | 204 | gpio_request(OSK_TPS_GPIO_USB_PWR_EN, "n_vbus_en"); |
| 205 | gpio_direction_output(OSK_TPS_GPIO_USB_PWR_EN, 1); | 205 | gpio_direction_output(OSK_TPS_GPIO_USB_PWR_EN, 1); |
| 206 | /* Free the GPIO again as the driver will request it */ | ||
| 207 | gpio_free(OSK_TPS_GPIO_USB_PWR_EN); | ||
| 206 | 208 | ||
| 207 | /* Set GPIO 2 high so LED D3 is off by default */ | 209 | /* Set GPIO 2 high so LED D3 is off by default */ |
| 208 | tps65010_set_gpio_out_value(GPIO2, HIGH); | 210 | tps65010_set_gpio_out_value(GPIO2, HIGH); |
| @@ -17,11 +17,10 @@ config ARCH_OMAP3 · 16 unmodified lines | |||
| 17 | bool "TI OMAP3" | 17 | bool "TI OMAP3" |
| 18 | depends on ARCH_MULTI_V7 | 18 | depends on ARCH_MULTI_V7 |
| 19 | select ARCH_OMAP2PLUS | 19 | select ARCH_OMAP2PLUS |
| 20 | select ARM_CPU_SUSPEND if PM | 20 | select ARM_CPU_SUSPEND |
| 21 | select OMAP_HWMOD | 21 | select OMAP_HWMOD |
| 22 | select OMAP_INTERCONNECT | 22 | select OMAP_INTERCONNECT |
| 23 | select PM_OPP if PM | 23 | select PM_OPP |
| 24 | select PM if CPU_IDLE | ||
| 25 | select SOC_HAS_OMAP2_SDRC | 24 | select SOC_HAS_OMAP2_SDRC |
| 26 | select ARM_ERRATA_430973 | 25 | select ARM_ERRATA_430973 |
| 27 | 26 | ||
| @@ -30,7 +29,7 @@ config ARCH_OMAP4 · 2 unmodified lines | |||
| 30 | depends on ARCH_MULTI_V7 | 29 | depends on ARCH_MULTI_V7 |
| 31 | select ARCH_OMAP2PLUS | 30 | select ARCH_OMAP2PLUS |
| 32 | select ARCH_NEEDS_CPU_IDLE_COUPLED if SMP | 31 | select ARCH_NEEDS_CPU_IDLE_COUPLED if SMP |
| 33 | select ARM_CPU_SUSPEND if PM | 32 | select ARM_CPU_SUSPEND |
| 34 | select ARM_ERRATA_720789 | 33 | select ARM_ERRATA_720789 |
| 35 | select ARM_GIC | 34 | select ARM_GIC |
| 36 | select HAVE_ARM_SCU if SMP | 35 | select HAVE_ARM_SCU if SMP |
| @@ -40,7 +39,7 @@ config ARCH_OMAP4 · 3 unmodified lines | |||
| 40 | select OMAP_INTERCONNECT_BARRIER | 39 | select OMAP_INTERCONNECT_BARRIER |
| 41 | select PL310_ERRATA_588369 if CACHE_L2X0 | 40 | select PL310_ERRATA_588369 if CACHE_L2X0 |
| 42 | select PL310_ERRATA_727915 if CACHE_L2X0 | 41 | select PL310_ERRATA_727915 if CACHE_L2X0 |
| 43 | select PM_OPP if PM | 42 | select PM_OPP |
| 44 | select PM if CPU_IDLE | 43 | select PM if CPU_IDLE |
| 45 | select ARM_ERRATA_754322 | 44 | select ARM_ERRATA_754322 |
| 46 | select ARM_ERRATA_775420 | 45 | select ARM_ERRATA_775420 |
| @@ -50,7 +49,7 @@ config SOC_OMAP5 · 3 unmodified lines | |||
| 50 | bool "TI OMAP5" | 49 | bool "TI OMAP5" |
| 51 | depends on ARCH_MULTI_V7 | 50 | depends on ARCH_MULTI_V7 |
| 52 | select ARCH_OMAP2PLUS | 51 | select ARCH_OMAP2PLUS |
| 53 | select ARM_CPU_SUSPEND if PM | 52 | select ARM_CPU_SUSPEND |
| 54 | select ARM_GIC | 53 | select ARM_GIC |
| 55 | select HAVE_ARM_SCU if SMP | 54 | select HAVE_ARM_SCU if SMP |
| 56 | select HAVE_ARM_ARCH_TIMER | 55 | select HAVE_ARM_ARCH_TIMER |
| @@ -58,14 +57,14 @@ config SOC_OMAP5 · 1 unmodified line | |||
| 58 | select OMAP_HWMOD | 57 | select OMAP_HWMOD |
| 59 | select OMAP_INTERCONNECT | 58 | select OMAP_INTERCONNECT |
| 60 | select OMAP_INTERCONNECT_BARRIER | 59 | select OMAP_INTERCONNECT_BARRIER |
| 61 | select PM_OPP if PM | 60 | select PM_OPP |
| 62 | select ZONE_DMA if ARM_LPAE | 61 | select ZONE_DMA if ARM_LPAE |
| 63 | 62 | ||
| 64 | config SOC_AM33XX | 63 | config SOC_AM33XX |
| 65 | bool "TI AM33XX" | 64 | bool "TI AM33XX" |
| 66 | depends on ARCH_MULTI_V7 | 65 | depends on ARCH_MULTI_V7 |
| 67 | select ARCH_OMAP2PLUS | 66 | select ARCH_OMAP2PLUS |
| 68 | select ARM_CPU_SUSPEND if PM | 67 | select ARM_CPU_SUSPEND |
| 69 | 68 | ||
| 70 | config SOC_AM43XX | 69 | config SOC_AM43XX |
| 71 | bool "TI AM43x" | 70 | bool "TI AM43x" |
| @@ -79,13 +78,13 @@ config SOC_AM43XX · 7 unmodified lines | |||
| 79 | select ARM_ERRATA_754322 | 78 | select ARM_ERRATA_754322 |
| 80 | select ARM_ERRATA_775420 | 79 | select ARM_ERRATA_775420 |
| 81 | select OMAP_INTERCONNECT | 80 | select OMAP_INTERCONNECT |
| 82 | select ARM_CPU_SUSPEND if PM | 81 | select ARM_CPU_SUSPEND |
| 83 | 82 | ||
| 84 | config SOC_DRA7XX | 83 | config SOC_DRA7XX |
| 85 | bool "TI DRA7XX" | 84 | bool "TI DRA7XX" |
| 86 | depends on ARCH_MULTI_V7 | 85 | depends on ARCH_MULTI_V7 |
| 87 | select ARCH_OMAP2PLUS | 86 | select ARCH_OMAP2PLUS |
| 88 | select ARM_CPU_SUSPEND if PM | 87 | select ARM_CPU_SUSPEND |
| 89 | select ARM_GIC | 88 | select ARM_GIC |
| 90 | select HAVE_ARM_SCU if SMP | 89 | select HAVE_ARM_SCU if SMP |
| 91 | select HAVE_ARM_ARCH_TIMER | 90 | select HAVE_ARM_ARCH_TIMER |
| @@ -94,7 +93,7 @@ config SOC_DRA7XX · 2 unmodified lines | |||
| 94 | select OMAP_HWMOD | 93 | select OMAP_HWMOD |
| 95 | select OMAP_INTERCONNECT | 94 | select OMAP_INTERCONNECT |
| 96 | select OMAP_INTERCONNECT_BARRIER | 95 | select OMAP_INTERCONNECT_BARRIER |
| 97 | select PM_OPP if PM | 96 | select PM_OPP |
| 98 | select ZONE_DMA if ARM_LPAE | 97 | select ZONE_DMA if ARM_LPAE |
| 99 | select PINCTRL_TI_IODELAY if OF && PINCTRL | 98 | select PINCTRL_TI_IODELAY if OF && PINCTRL |
| 100 | 99 | ||
| @@ -112,9 +111,11 @@ config ARCH_OMAP2PLUS · 11 unmodified lines | |||
| 112 | select OMAP_DM_TIMER | 111 | select OMAP_DM_TIMER |
| 113 | select OMAP_GPMC | 112 | select OMAP_GPMC |
| 114 | select PINCTRL | 113 | select PINCTRL |
| 115 | select PM_GENERIC_DOMAINS if PM | 114 | select PM |
| 116 | select PM_GENERIC_DOMAINS_OF if PM | 115 | select PM_GENERIC_DOMAINS |
| 116 | select PM_GENERIC_DOMAINS_OF | ||
| 117 | select RESET_CONTROLLER | 117 | select RESET_CONTROLLER |
| 118 | select SIMPLE_PM_BUS | ||
| 118 | select SOC_BUS | 119 | select SOC_BUS |
| 119 | select TI_SYSC | 120 | select TI_SYSC |
| 120 | select OMAP_IRQCHIP | 121 | select OMAP_IRQCHIP |
| @@ -140,7 +141,6 @@ config ARCH_OMAP2PLUS_TYPICAL · 19 unmodified lines | |||
| 140 | select I2C_OMAP | 141 | select I2C_OMAP |
| 141 | select MENELAUS if ARCH_OMAP2 | 142 | select MENELAUS if ARCH_OMAP2 |
| 142 | select NEON if CPU_V7 | 143 | select NEON if CPU_V7 |
| 143 | select PM | ||
| 144 | select REGULATOR | 144 | select REGULATOR |
| 145 | select REGULATOR_FIXED_VOLTAGE | 145 | select REGULATOR_FIXED_VOLTAGE |
| 146 | select TWL4030_CORE if ARCH_OMAP3 || ARCH_OMAP4 | 146 | select TWL4030_CORE if ARCH_OMAP3 || ARCH_OMAP4 |
| @@ -151,10 +151,10 @@ static int omap_enter_idle_coupled(struct cpuidle_device *dev, · 150 unmodified lines | |||
| 151 | (cx->mpu_logic_state == PWRDM_POWER_OFF); | 151 | (cx->mpu_logic_state == PWRDM_POWER_OFF); |
| 152 | 152 | ||
| 153 | /* Enter broadcast mode for periodic timers */ | 153 | /* Enter broadcast mode for periodic timers */ |
| 154 | tick_broadcast_enable(); | 154 | RCU_NONIDLE(tick_broadcast_enable()); |
| 155 | 155 | ||
| 156 | /* Enter broadcast mode for one-shot timers */ | 156 | /* Enter broadcast mode for one-shot timers */ |
| 157 | tick_broadcast_enter(); | 157 | RCU_NONIDLE(tick_broadcast_enter()); |
| 158 | 158 | ||
| 159 | /* | 159 | /* |
| 160 | * Call idle CPU PM enter notifier chain so that | 160 | * Call idle CPU PM enter notifier chain so that |
| @@ -166,7 +166,7 @@ static int omap_enter_idle_coupled(struct cpuidle_device *dev, · 5 unmodified lines | |||
| 166 | 166 | ||
| 167 | if (dev->cpu == 0) { | 167 | if (dev->cpu == 0) { |
| 168 | pwrdm_set_logic_retst(mpu_pd, cx->mpu_logic_state); | 168 | pwrdm_set_logic_retst(mpu_pd, cx->mpu_logic_state); |
| 169 | omap_set_pwrdm_state(mpu_pd, cx->mpu_state); | 169 | RCU_NONIDLE(omap_set_pwrdm_state(mpu_pd, cx->mpu_state)); |
| 170 | 170 | ||
| 171 | /* | 171 | /* |
| 172 | * Call idle CPU cluster PM enter notifier chain | 172 | * Call idle CPU cluster PM enter notifier chain |
| @@ -178,7 +178,7 @@ static int omap_enter_idle_coupled(struct cpuidle_device *dev, · 5 unmodified lines | |||
| 178 | index = 0; | 178 | index = 0; |
| 179 | cx = state_ptr + index; | 179 | cx = state_ptr + index; |
| 180 | pwrdm_set_logic_retst(mpu_pd, cx->mpu_logic_state); | 180 | pwrdm_set_logic_retst(mpu_pd, cx->mpu_logic_state); |
| 181 | omap_set_pwrdm_state(mpu_pd, cx->mpu_state); | 181 | RCU_NONIDLE(omap_set_pwrdm_state(mpu_pd, cx->mpu_state)); |
| 182 | mpuss_can_lose_context = 0; | 182 | mpuss_can_lose_context = 0; |
| 183 | } | 183 | } |
| 184 | } | 184 | } |
| @@ -194,9 +194,9 @@ static int omap_enter_idle_coupled(struct cpuidle_device *dev, · 9 unmodified lines | |||
| 194 | mpuss_can_lose_context) | 194 | mpuss_can_lose_context) |
| 195 | gic_dist_disable(); | 195 | gic_dist_disable(); |
| 196 | 196 | ||
| 197 | clkdm_deny_idle(cpu_clkdm[1]); | 197 | RCU_NONIDLE(clkdm_deny_idle(cpu_clkdm[1])); |
| 198 | omap_set_pwrdm_state(cpu_pd[1], PWRDM_POWER_ON); | 198 | RCU_NONIDLE(omap_set_pwrdm_state(cpu_pd[1], PWRDM_POWER_ON)); |
| 199 | clkdm_allow_idle(cpu_clkdm[1]); | 199 | RCU_NONIDLE(clkdm_allow_idle(cpu_clkdm[1])); |
| 200 | 200 | ||
| 201 | if (IS_PM44XX_ERRATUM(PM_OMAP4_ROM_SMP_BOOT_ERRATUM_GICD) && | 201 | if (IS_PM44XX_ERRATUM(PM_OMAP4_ROM_SMP_BOOT_ERRATUM_GICD) && |
| 202 | mpuss_can_lose_context) { | 202 | mpuss_can_lose_context) { |
| @@ -222,7 +222,7 @@ static int omap_enter_idle_coupled(struct cpuidle_device *dev, · 19 unmodified lines | |||
| 222 | cpu_pm_exit(); | 222 | cpu_pm_exit(); |
| 223 | 223 | ||
| 224 | cpu_pm_out: | 224 | cpu_pm_out: |
| 225 | tick_broadcast_exit(); | 225 | RCU_NONIDLE(tick_broadcast_exit()); |
| 226 | 226 | ||
| 227 | fail: | 227 | fail: |
| 228 | cpuidle_coupled_parallel_barrier(dev, &abort_barrier); | 228 | cpuidle_coupled_parallel_barrier(dev, &abort_barrier); |
| @@ -230,10 +230,12 @@ static int _omap_device_notifier_call(struct notifier_block *nb, · 229 unmodified lines | |||
| 230 | break; | 230 | break; |
| 231 | case BUS_NOTIFY_BIND_DRIVER: | 231 | case BUS_NOTIFY_BIND_DRIVER: |
| 232 | od = to_omap_device(pdev); | 232 | od = to_omap_device(pdev); |
| 233 | if (od && (od->_state == OMAP_DEVICE_STATE_ENABLED) && | 233 | if (od) { |
| 234 | pm_runtime_status_suspended(dev)) { | ||
| 235 | od->_driver_status = BUS_NOTIFY_BIND_DRIVER; | 234 | od->_driver_status = BUS_NOTIFY_BIND_DRIVER; |
| 236 | pm_runtime_set_active(dev); | 235 | if (od->_state == OMAP_DEVICE_STATE_ENABLED && |
| 236 | pm_runtime_status_suspended(dev)) { | ||
| 237 | pm_runtime_set_active(dev); | ||
| 238 | } | ||
| 237 | } | 239 | } |
| 238 | break; | 240 | break; |
| 239 | case BUS_NOTIFY_ADD_DEVICE: | 241 | case BUS_NOTIFY_ADD_DEVICE: |
| @@ -522,6 +522,7 @@ static struct of_dev_auxdata omap_auxdata_lookup[] = { · 521 unmodified lines | |||
| 522 | &dra7_ipu1_dsp_iommu_pdata), | 522 | &dra7_ipu1_dsp_iommu_pdata), |
| 523 | #endif | 523 | #endif |
| 524 | /* Common auxdata */ | 524 | /* Common auxdata */ |
| 525 | OF_DEV_AUXDATA("simple-pm-bus", 0, NULL, omap_auxdata_lookup), | ||
| 525 | OF_DEV_AUXDATA("ti,sysc", 0, NULL, &ti_sysc_pdata), | 526 | OF_DEV_AUXDATA("ti,sysc", 0, NULL, &ti_sysc_pdata), |
| 526 | OF_DEV_AUXDATA("pinctrl-single", 0, NULL, &pcs_pdata), | 527 | OF_DEV_AUXDATA("pinctrl-single", 0, NULL, &pcs_pdata), |
| 527 | OF_DEV_AUXDATA("ti,omap-prm-inst", 0, NULL, &ti_prm_pdata), | 528 | OF_DEV_AUXDATA("ti,omap-prm-inst", 0, NULL, &ti_prm_pdata), |
| @@ -71,7 +71,7 @@ static struct omap_voltdm_pmic omap_cpcap_iva = { · 70 unmodified lines | |||
| 71 | .vp_vstepmin = OMAP4_VP_VSTEPMIN_VSTEPMIN, | 71 | .vp_vstepmin = OMAP4_VP_VSTEPMIN_VSTEPMIN, |
| 72 | .vp_vstepmax = OMAP4_VP_VSTEPMAX_VSTEPMAX, | 72 | .vp_vstepmax = OMAP4_VP_VSTEPMAX_VSTEPMAX, |
| 73 | .vddmin = 900000, | 73 | .vddmin = 900000, |
| 74 | .vddmax = 1350000, | 74 | .vddmax = 1375000, |
| 75 | .vp_timeout_us = OMAP4_VP_VLIMITTO_TIMEOUT_US, | 75 | .vp_timeout_us = OMAP4_VP_VLIMITTO_TIMEOUT_US, |
| 76 | .i2c_slave_addr = 0x44, | 76 | .i2c_slave_addr = 0x44, |
| 77 | .volt_reg_addr = 0x0, | 77 | .volt_reg_addr = 0x0, |
| @@ -370,8 +370,6 @@ static int __init xen_guest_init(void) · 369 unmodified lines | |||
| 370 | return -ENOMEM; | 370 | return -ENOMEM; |
| 371 | } | 371 | } |
| 372 | gnttab_init(); | 372 | gnttab_init(); |
| 373 | if (!xen_initial_domain()) | ||
| 374 | xenbus_probe(NULL); | ||
| 375 | 373 | ||
| 376 | /* | 374 | /* |
| 377 | * Making sure board specific code will not set up ops for | 375 | * Making sure board specific code will not set up ops for |
| @@ -174,8 +174,6 @@ config ARM64 · 173 unmodified lines | |||
| 174 | select HAVE_NMI | 174 | select HAVE_NMI |
| 175 | select HAVE_PATA_PLATFORM | 175 | select HAVE_PATA_PLATFORM |
| 176 | select HAVE_PERF_EVENTS | 176 | select HAVE_PERF_EVENTS |
| 177 | select HAVE_PERF_EVENTS_NMI if ARM64_PSEUDO_NMI && HW_PERF_EVENTS | ||
| 178 | select HAVE_HARDLOCKUP_DETECTOR_PERF if PERF_EVENTS && HAVE_PERF_EVENTS_NMI | ||
| 179 | select HAVE_PERF_REGS | 177 | select HAVE_PERF_REGS |
| 180 | select HAVE_PERF_USER_STACK_DUMP | 178 | select HAVE_PERF_USER_STACK_DUMP |
| 181 | select HAVE_REGS_AND_STACK_ACCESS_API | 179 | select HAVE_REGS_AND_STACK_ACCESS_API |
| @@ -10,7 +10,7 @@ · 9 unmodified lines | |||
| 10 | # | 10 | # |
| 11 | # Copyright (C) 1995-2001 by Russell King | 11 | # Copyright (C) 1995-2001 by Russell King |
| 12 | 12 | ||
| 13 | LDFLAGS_vmlinux :=--no-undefined -X -z norelro | 13 | LDFLAGS_vmlinux :=--no-undefined -X |
| 14 | 14 | ||
| 15 | ifeq ($(CONFIG_RELOCATABLE), y) | 15 | ifeq ($(CONFIG_RELOCATABLE), y) |
| 16 | # Pass --no-apply-dynamic-relocs to restore pre-binutils-2.27 behaviour | 16 | # Pass --no-apply-dynamic-relocs to restore pre-binutils-2.27 behaviour |
| @@ -115,16 +115,20 @@ KBUILD_CPPFLAGS += -mbig-endian · 98 unmodified lines | |||
| 115 | CHECKFLAGS += -D__AARCH64EB__ | 115 | CHECKFLAGS += -D__AARCH64EB__ |
| 116 | # Prefer the baremetal ELF build target, but not all toolchains include | 116 | # Prefer the baremetal ELF build target, but not all toolchains include |
| 117 | # it so fall back to the standard linux version if needed. | 117 | # it so fall back to the standard linux version if needed. |
| 118 | KBUILD_LDFLAGS += -EB $(call ld-option, -maarch64elfb, -maarch64linuxb) | 118 | KBUILD_LDFLAGS += -EB $(call ld-option, -maarch64elfb, -maarch64linuxb -z norelro) |
| 119 | UTS_MACHINE := aarch64_be | 119 | UTS_MACHINE := aarch64_be |
| 120 | else | 120 | else |
| 121 | KBUILD_CPPFLAGS += -mlittle-endian | 121 | KBUILD_CPPFLAGS += -mlittle-endian |
| 122 | CHECKFLAGS += -D__AARCH64EL__ | 122 | CHECKFLAGS += -D__AARCH64EL__ |
| 123 | # Same as above, prefer ELF but fall back to linux target if needed. | 123 | # Same as above, prefer ELF but fall back to linux target if needed. |
| 124 | KBUILD_LDFLAGS += -EL $(call ld-option, -maarch64elf, -maarch64linux) | 124 | KBUILD_LDFLAGS += -EL $(call ld-option, -maarch64elf, -maarch64linux -z norelro) |
| 125 | UTS_MACHINE := aarch64 | 125 | UTS_MACHINE := aarch64 |
| 126 | endif | 126 | endif |
| 127 | 127 | ||
| 128 | ifeq ($(CONFIG_LD_IS_LLD), y) | ||
| 129 | KBUILD_LDFLAGS += -z norelro | ||
| 130 | endif | ||
| 131 | |||
| 128 | CHECKFLAGS += -D__aarch64__ | 132 | CHECKFLAGS += -D__aarch64__ |
| 129 | 133 | ||
| 130 | ifeq ($(CONFIG_DYNAMIC_FTRACE_WITH_REGS),y) | 134 | ifeq ($(CONFIG_DYNAMIC_FTRACE_WITH_REGS),y) |
| @@ -280,8 +280,6 @@ · 279 unmodified lines | |||
| 280 | "timing-adjustment"; | 280 | "timing-adjustment"; |
| 281 | rx-fifo-depth = <4096>; | 281 | rx-fifo-depth = <4096>; |
| 282 | tx-fifo-depth = <2048>; | 282 | tx-fifo-depth = <2048>; |
| 283 | resets = <&reset RESET_ETHERNET>; | ||
| 284 | reset-names = "stmmaceth"; | ||
| 285 | power-domains = <&pwrc PWRC_AXG_ETHERNET_MEM_ID>; | 283 | power-domains = <&pwrc PWRC_AXG_ETHERNET_MEM_ID>; |
| 286 | status = "disabled"; | 284 | status = "disabled"; |
| 287 | }; | 285 | }; |
| @@ -224,8 +224,6 @@ · 223 unmodified lines | |||
| 224 | "timing-adjustment"; | 224 | "timing-adjustment"; |
| 225 | rx-fifo-depth = <4096>; | 225 | rx-fifo-depth = <4096>; |
| 226 | tx-fifo-depth = <2048>; | 226 | tx-fifo-depth = <2048>; |
| 227 | resets = <&reset RESET_ETHERNET>; | ||
| 228 | reset-names = "stmmaceth"; | ||
| 229 | status = "disabled"; | 227 | status = "disabled"; |
| 230 | 228 | ||
| 231 | mdio0: mdio { | 229 | mdio0: mdio { |
| @@ -2390,7 +2388,7 @@ · 2158 unmodified lines | |||
| 2390 | interrupts = <GIC_SPI 30 IRQ_TYPE_LEVEL_HIGH>; | 2388 | interrupts = <GIC_SPI 30 IRQ_TYPE_LEVEL_HIGH>; |
| 2391 | dr_mode = "host"; | 2389 | dr_mode = "host"; |
| 2392 | snps,dis_u2_susphy_quirk; | 2390 | snps,dis_u2_susphy_quirk; |
| 2393 | snps,quirk-frame-length-adjustment; | 2391 | snps,quirk-frame-length-adjustment = <0x20>; |
| 2394 | snps,parkmode-disable-ss-quirk; | 2392 | snps,parkmode-disable-ss-quirk; |
| 2395 | }; | 2393 | }; |
| 2396 | }; | 2394 | }; |
| @@ -13,7 +13,6 @@ · 12 unmodified lines | |||
| 13 | #include <dt-bindings/interrupt-controller/irq.h> | 13 | #include <dt-bindings/interrupt-controller/irq.h> |
| 14 | #include <dt-bindings/interrupt-controller/arm-gic.h> | 14 | #include <dt-bindings/interrupt-controller/arm-gic.h> |
| 15 | #include <dt-bindings/power/meson-gxbb-power.h> | 15 | #include <dt-bindings/power/meson-gxbb-power.h> |
| 16 | #include <dt-bindings/reset/amlogic,meson-gxbb-reset.h> | ||
| 17 | #include <dt-bindings/thermal/thermal.h> | 16 | #include <dt-bindings/thermal/thermal.h> |
| 18 | 17 | ||
| 19 | / { | 18 | / { |
| @@ -576,8 +575,6 @@ · 556 unmodified lines | |||
| 576 | interrupt-names = "macirq"; | 575 | interrupt-names = "macirq"; |
| 577 | rx-fifo-depth = <4096>; | 576 | rx-fifo-depth = <4096>; |
| 578 | tx-fifo-depth = <2048>; | 577 | tx-fifo-depth = <2048>; |
| 579 | resets = <&reset RESET_ETHERNET>; | ||
| 580 | reset-names = "stmmaceth"; | ||
| 581 | power-domains = <&pwrc PWRC_GXBB_ETHERNET_MEM_ID>; | 578 | power-domains = <&pwrc PWRC_GXBB_ETHERNET_MEM_ID>; |
| 582 | status = "disabled"; | 579 | status = "disabled"; |
| 583 | }; | 580 | }; |
| @@ -52,7 +52,7 @@ · 51 unmodified lines | |||
| 52 | regulator-min-microvolt = <3300000>; | 52 | regulator-min-microvolt = <3300000>; |
| 53 | regulator-max-microvolt = <3300000>; | 53 | regulator-max-microvolt = <3300000>; |
| 54 | 54 | ||
| 55 | gpio = <&gpio_ao GPIOAO_3 GPIO_ACTIVE_HIGH>; | 55 | gpio = <&gpio_ao GPIOAO_3 GPIO_OPEN_DRAIN>; |
| 56 | enable-active-high; | 56 | enable-active-high; |
| 57 | regulator-always-on; | 57 | regulator-always-on; |
| 58 | }; | 58 | }; |
| @@ -127,7 +127,7 @@ · 126 unmodified lines | |||
| 127 | compatible = "snps,dw-apb-gpio-port"; | 127 | compatible = "snps,dw-apb-gpio-port"; |
| 128 | gpio-controller; | 128 | gpio-controller; |
| 129 | #gpio-cells = <2>; | 129 | #gpio-cells = <2>; |
| 130 | snps,nr-gpios = <32>; | 130 | ngpios = <32>; |
| 131 | reg = <0>; | 131 | reg = <0>; |
| 132 | interrupt-controller; | 132 | interrupt-controller; |
| 133 | #interrupt-cells = <2>; | 133 | #interrupt-cells = <2>; |
| @@ -145,7 +145,7 @@ · 11 unmodified lines | |||
| 145 | compatible = "snps,dw-apb-gpio-port"; | 145 | compatible = "snps,dw-apb-gpio-port"; |
| 146 | gpio-controller; | 146 | gpio-controller; |
| 147 | #gpio-cells = <2>; | 147 | #gpio-cells = <2>; |
| 148 | snps,nr-gpios = <32>; | 148 | ngpios = <32>; |
| 149 | reg = <0>; | 149 | reg = <0>; |
| 150 | interrupt-controller; | 150 | interrupt-controller; |
| 151 | #interrupt-cells = <2>; | 151 | #interrupt-cells = <2>; |
| @@ -163,7 +163,7 @@ · 11 unmodified lines | |||
| 163 | compatible = "snps,dw-apb-gpio-port"; | 163 | compatible = "snps,dw-apb-gpio-port"; |
| 164 | gpio-controller; | 164 | gpio-controller; |
| 165 | #gpio-cells = <2>; | 165 | #gpio-cells = <2>; |
| 166 | snps,nr-gpios = <8>; | 166 | ngpios = <8>; |
| 167 | reg = <0>; | 167 | reg = <0>; |
| 168 | interrupt-controller; | 168 | interrupt-controller; |
| 169 | #interrupt-cells = <2>; | 169 | #interrupt-cells = <2>; |
| @@ -4,11 +4,16 @@ · 3 unmodified lines | |||
| 4 | */ | 4 | */ |
| 5 | usb { | 5 | usb { |
| 6 | compatible = "simple-bus"; | 6 | compatible = "simple-bus"; |
| 7 | dma-ranges; | ||
| 8 | #address-cells = <2>; | 7 | #address-cells = <2>; |
| 9 | #size-cells = <2>; | 8 | #size-cells = <2>; |
| 10 | ranges = <0x0 0x0 0x0 0x68500000 0x0 0x00400000>; | 9 | ranges = <0x0 0x0 0x0 0x68500000 0x0 0x00400000>; |
| 11 | 10 | ||
| 11 | /* | ||
| 12 | * Internally, USB bus to the interconnect can only address up | ||
| 13 | * to 40-bit | ||
| 14 | */ | ||
| 15 | dma-ranges = <0 0 0 0 0x100 0x0>; | ||
| 16 | |||
| 12 | usbphy0: usb-phy@0 { | 17 | usbphy0: usb-phy@0 { |
| 13 | compatible = "brcm,sr-usb-combo-phy"; | 18 | compatible = "brcm,sr-usb-combo-phy"; |
| 14 | reg = <0x0 0x00000000 0x0 0x100>; | 19 | reg = <0x0 0x00000000 0x0 0x100>; |
| @@ -101,7 +101,7 @@ · 100 unmodified lines | |||
| 101 | reboot { | 101 | reboot { |
| 102 | compatible ="syscon-reboot"; | 102 | compatible ="syscon-reboot"; |
| 103 | regmap = <&rst>; | 103 | regmap = <&rst>; |
| 104 | offset = <0xb0>; | 104 | offset = <0>; |
| 105 | mask = <0x02>; | 105 | mask = <0x02>; |
| 106 | }; | 106 | }; |
| 107 | 107 | ||
| @@ -385,7 +385,7 @@ · 384 unmodified lines | |||
| 385 | 385 | ||
| 386 | dcfg: dcfg@1ee0000 { | 386 | dcfg: dcfg@1ee0000 { |
| 387 | compatible = "fsl,ls1046a-dcfg", "syscon"; | 387 | compatible = "fsl,ls1046a-dcfg", "syscon"; |
| 388 | reg = <0x0 0x1ee0000 0x0 0x10000>; | 388 | reg = <0x0 0x1ee0000 0x0 0x1000>; |
| 389 | big-endian; | 389 | big-endian; |
| 390 | }; | 390 | }; |
| 391 | 391 | ||
| @@ -253,7 +253,7 @@ · 252 unmodified lines | |||
| 253 | #size-cells = <1>; | 253 | #size-cells = <1>; |
| 254 | ranges; | 254 | ranges; |
| 255 | 255 | ||
| 256 | spba: bus@30000000 { | 256 | spba: spba-bus@30000000 { |
| 257 | compatible = "fsl,spba-bus", "simple-bus"; | 257 | compatible = "fsl,spba-bus", "simple-bus"; |
| 258 | #address-cells = <1>; | 258 | #address-cells = <1>; |
| 259 | #size-cells = <1>; | 259 | #size-cells = <1>; |
| @@ -266,7 +266,7 @@ · 265 unmodified lines | |||
| 266 | #gpio-cells = <2>; | 266 | #gpio-cells = <2>; |
| 267 | interrupt-controller; | 267 | interrupt-controller; |
| 268 | #interrupt-cells = <2>; | 268 | #interrupt-cells = <2>; |
| 269 | gpio-ranges = <&iomuxc 0 56 26>, <&iomuxc 0 144 4>; | 269 | gpio-ranges = <&iomuxc 0 56 26>, <&iomuxc 26 144 4>; |
| 270 | }; | 270 | }; |
| 271 | 271 | ||
| 272 | gpio4: gpio@30230000 { | 272 | gpio4: gpio@30230000 { |
| @@ -415,7 +415,9 @@ · 414 unmodified lines | |||
| 415 | &gcc { | 415 | &gcc { |
| 416 | protected-clocks = <GCC_QSPI_CORE_CLK>, | 416 | protected-clocks = <GCC_QSPI_CORE_CLK>, |
| 417 | <GCC_QSPI_CORE_CLK_SRC>, | 417 | <GCC_QSPI_CORE_CLK_SRC>, |
| 418 | <GCC_QSPI_CNOC_PERIPH_AHB_CLK>; | 418 | <GCC_QSPI_CNOC_PERIPH_AHB_CLK>, |
| 419 | <GCC_LPASS_Q6_AXI_CLK>, | ||
| 420 | <GCC_LPASS_SWAY_CLK>; | ||
| 419 | }; | 421 | }; |
| 420 | 422 | ||
| 421 | &gpu { | 423 | &gpu { |
| @@ -302,7 +302,9 @@ · 301 unmodified lines | |||
| 302 | &gcc { | 302 | &gcc { |
| 303 | protected-clocks = <GCC_QSPI_CORE_CLK>, | 303 | protected-clocks = <GCC_QSPI_CORE_CLK>, |
| 304 | <GCC_QSPI_CORE_CLK_SRC>, | 304 | <GCC_QSPI_CORE_CLK_SRC>, |
| 305 | <GCC_QSPI_CNOC_PERIPH_AHB_CLK>; | 305 | <GCC_QSPI_CNOC_PERIPH_AHB_CLK>, |
| 306 | <GCC_LPASS_Q6_AXI_CLK>, | ||
| 307 | <GCC_LPASS_SWAY_CLK>; | ||
| 306 | }; | 308 | }; |
| 307 | 309 | ||
| 308 | &gpu { | 310 | &gpu { |
| @@ -320,6 +322,8 @@ · 11 unmodified lines | |||
| 320 | &i2c3 { | 322 | &i2c3 { |
| 321 | status = "okay"; | 323 | status = "okay"; |
| 322 | clock-frequency = <400000>; | 324 | clock-frequency = <400000>; |
| 325 | /* Overwrite pinctrl-0 from sdm845.dtsi */ | ||
| 326 | pinctrl-0 = <&qup_i2c3_default &i2c3_hid_active>; | ||
| 323 | 327 | ||
| 324 | tsel: hid@15 { | 328 | tsel: hid@15 { |
| 325 | compatible = "hid-over-i2c"; | 329 | compatible = "hid-over-i2c"; |
| @@ -327,9 +331,6 @@ · 1 unmodified line | |||
| 327 | hid-descr-addr = <0x1>; | 331 | hid-descr-addr = <0x1>; |
| 328 | 332 | ||
| 329 | interrupts-extended = <&tlmm 37 IRQ_TYPE_LEVEL_HIGH>; | 333 | interrupts-extended = <&tlmm 37 IRQ_TYPE_LEVEL_HIGH>; |
| 330 | |||
| 331 | pinctrl-names = "default"; | ||
| 332 | pinctrl-0 = <&i2c3_hid_active>; | ||
| 333 | }; | 334 | }; |
| 334 | 335 | ||
| 335 | tsc2: hid@2c { | 336 | tsc2: hid@2c { |
| @@ -338,11 +339,6 @@ · 2 unmodified lines | |||
| 338 | hid-descr-addr = <0x20>; | 339 | hid-descr-addr = <0x20>; |
| 339 | 340 | ||
| 340 | interrupts-extended = <&tlmm 37 IRQ_TYPE_LEVEL_HIGH>; | 341 | interrupts-extended = <&tlmm 37 IRQ_TYPE_LEVEL_HIGH>; |
| 341 | |||
| 342 | pinctrl-names = "default"; | ||
| 343 | pinctrl-0 = <&i2c3_hid_active>; | ||
| 344 | |||
| 345 | status = "disabled"; | ||
| 346 | }; | 342 | }; |
| 347 | }; | 343 | }; |
| 348 | 344 | ||
| @@ -1097,7 +1097,7 @@ · 1096 unmodified lines | |||
| 1097 | vopl_mmu: iommu@ff470f00 { | 1097 | vopl_mmu: iommu@ff470f00 { |
| 1098 | compatible = "rockchip,iommu"; | 1098 | compatible = "rockchip,iommu"; |
| 1099 | reg = <0x0 0xff470f00 0x0 0x100>; | 1099 | reg = <0x0 0xff470f00 0x0 0x100>; |
| 1100 | interrupts = <GIC_SPI 79 IRQ_TYPE_LEVEL_HIGH>; | 1100 | interrupts = <GIC_SPI 78 IRQ_TYPE_LEVEL_HIGH>; |
| 1101 | interrupt-names = "vopl_mmu"; | 1101 | interrupt-names = "vopl_mmu"; |
| 1102 | clocks = <&cru ACLK_VOPL>, <&cru HCLK_VOPL>; | 1102 | clocks = <&cru ACLK_VOPL>, <&cru HCLK_VOPL>; |
| 1103 | clock-names = "aclk", "iface"; | 1103 | clock-names = "aclk", "iface"; |
| @@ -114,6 +114,10 @@ · 113 unmodified lines | |||
| 114 | cpu-supply = <&vdd_arm>; | 114 | cpu-supply = <&vdd_arm>; |
| 115 | }; | 115 | }; |
| 116 | 116 | ||
| 117 | &display_subsystem { | ||
| 118 | status = "disabled"; | ||
| 119 | }; | ||
| 120 | |||
| 117 | &gmac2io { | 121 | &gmac2io { |
| 118 | assigned-clocks = <&cru SCLK_MAC2IO>, <&cru SCLK_MAC2IO_EXT>; | 122 | assigned-clocks = <&cru SCLK_MAC2IO>, <&cru SCLK_MAC2IO_EXT>; |
| 119 | assigned-clock-parents = <&gmac_clk>, <&gmac_clk>; | 123 | assigned-clock-parents = <&gmac_clk>, <&gmac_clk>; |
| @@ -790,7 +790,6 @@ · 789 unmodified lines | |||
| 790 | &pcie0 { | 790 | &pcie0 { |
| 791 | bus-scan-delay-ms = <1000>; | 791 | bus-scan-delay-ms = <1000>; |
| 792 | ep-gpios = <&gpio2 RK_PD4 GPIO_ACTIVE_HIGH>; | 792 | ep-gpios = <&gpio2 RK_PD4 GPIO_ACTIVE_HIGH>; |
| 793 | max-link-speed = <2>; | ||
| 794 | num-lanes = <4>; | 793 | num-lanes = <4>; |
| 795 | pinctrl-names = "default"; | 794 | pinctrl-names = "default"; |
| 796 | pinctrl-0 = <&pcie_clkreqn_cpm>; | 795 | pinctrl-0 = <&pcie_clkreqn_cpm>; |
| @@ -234,6 +234,7 @@ · 233 unmodified lines | |||
| 234 | reg = <0x0 0xf8000000 0x0 0x2000000>, | 234 | reg = <0x0 0xf8000000 0x0 0x2000000>, |
| 235 | <0x0 0xfd000000 0x0 0x1000000>; | 235 | <0x0 0xfd000000 0x0 0x1000000>; |
| 236 | reg-names = "axi-base", "apb-base"; | 236 | reg-names = "axi-base", "apb-base"; |
| 237 | device_type = "pci"; | ||
| 237 | #address-cells = <3>; | 238 | #address-cells = <3>; |
| 238 | #size-cells = <2>; | 239 | #size-cells = <2>; |
| 239 | #interrupt-cells = <1>; | 240 | #interrupt-cells = <1>; |
| @@ -252,7 +253,6 @@ · 12 unmodified lines | |||
| 252 | <0 0 0 2 &pcie0_intc 1>, | 253 | <0 0 0 2 &pcie0_intc 1>, |
| 253 | <0 0 0 3 &pcie0_intc 2>, | 254 | <0 0 0 3 &pcie0_intc 2>, |
| 254 | <0 0 0 4 &pcie0_intc 3>; | 255 | <0 0 0 4 &pcie0_intc 3>; |
| 255 | linux,pci-domain = <0>; | ||
| 256 | max-link-speed = <1>; | 256 | max-link-speed = <1>; |
| 257 | msi-map = <0x0 &its 0x0 0x1000>; | 257 | msi-map = <0x0 &its 0x0 0x1000>; |
| 258 | phys = <&pcie_phy 0>, <&pcie_phy 1>, | 258 | phys = <&pcie_phy 0>, <&pcie_phy 1>, |
| @@ -1278,7 +1278,6 @@ · 1019 unmodified lines | |||
| 1278 | compatible = "rockchip,rk3399-vdec"; | 1278 | compatible = "rockchip,rk3399-vdec"; |
| 1279 | reg = <0x0 0xff660000 0x0 0x400>; | 1279 | reg = <0x0 0xff660000 0x0 0x400>; |
| 1280 | interrupts = <GIC_SPI 116 IRQ_TYPE_LEVEL_HIGH 0>; | 1280 | interrupts = <GIC_SPI 116 IRQ_TYPE_LEVEL_HIGH 0>; |
| 1281 | interrupt-names = "vdpu"; | ||
| 1282 | clocks = <&cru ACLK_VDU>, <&cru HCLK_VDU>, | 1281 | clocks = <&cru ACLK_VDU>, <&cru HCLK_VDU>, |
| 1283 | <&cru SCLK_VDU_CA>, <&cru SCLK_VDU_CORE>; | 1282 | <&cru SCLK_VDU_CA>, <&cru SCLK_VDU_CORE>; |
| 1284 | clock-names = "axi", "ahb", "cabac", "core"; | 1283 | clock-names = "axi", "ahb", "cabac", "core"; |
| @@ -991,8 +991,6 @@ CONFIG_ARCH_TEGRA_210_SOC=y · 990 unmodified lines | |||
| 991 | CONFIG_ARCH_TEGRA_186_SOC=y | 991 | CONFIG_ARCH_TEGRA_186_SOC=y |
| 992 | CONFIG_ARCH_TEGRA_194_SOC=y | 992 | CONFIG_ARCH_TEGRA_194_SOC=y |
| 993 | CONFIG_ARCH_TEGRA_234_SOC=y | 993 | CONFIG_ARCH_TEGRA_234_SOC=y |
| 994 | CONFIG_ARCH_K3_AM6_SOC=y | ||
| 995 | CONFIG_ARCH_K3_J721E_SOC=y | ||
| 996 | CONFIG_TI_SCI_PM_DOMAINS=y | 994 | CONFIG_TI_SCI_PM_DOMAINS=y |
| 997 | CONFIG_EXTCON_PTN5150=m | 995 | CONFIG_EXTCON_PTN5150=m |
| 998 | CONFIG_EXTCON_USB_GPIO=y | 996 | CONFIG_EXTCON_USB_GPIO=y |
| @@ -1078,7 +1076,7 @@ CONFIG_INTERCONNECT=y · 79 unmodified lines | |||
| 1078 | CONFIG_INTERCONNECT_QCOM=y | 1076 | CONFIG_INTERCONNECT_QCOM=y |
| 1079 | CONFIG_INTERCONNECT_QCOM_MSM8916=m | 1077 | CONFIG_INTERCONNECT_QCOM_MSM8916=m |
| 1080 | CONFIG_INTERCONNECT_QCOM_OSM_L3=m | 1078 | CONFIG_INTERCONNECT_QCOM_OSM_L3=m |
| 1081 | CONFIG_INTERCONNECT_QCOM_SDM845=m | 1079 | CONFIG_INTERCONNECT_QCOM_SDM845=y |
| 1082 | CONFIG_INTERCONNECT_QCOM_SM8150=m | 1080 | CONFIG_INTERCONNECT_QCOM_SM8150=m |
| 1083 | CONFIG_INTERCONNECT_QCOM_SM8250=m | 1081 | CONFIG_INTERCONNECT_QCOM_SM8250=m |
| 1084 | CONFIG_EXT2_FS=y | 1082 | CONFIG_EXT2_FS=y |
| @@ -17,7 +17,7 @@ · 16 unmodified lines | |||
| 17 | #include <asm/lse.h> | 17 | #include <asm/lse.h> |
| 18 | 18 | ||
| 19 | #define ATOMIC_OP(op) \ | 19 | #define ATOMIC_OP(op) \ |
| 20 | static inline void arch_##op(int i, atomic_t *v) \ | 20 | static __always_inline void arch_##op(int i, atomic_t *v) \ |
| 21 | { \ | 21 | { \ |
| 22 | __lse_ll_sc_body(op, i, v); \ | 22 | __lse_ll_sc_body(op, i, v); \ |
| 23 | } | 23 | } |
| @@ -32,7 +32,7 @@ ATOMIC_OP(atomic_sub) · 8 unmodified lines | |||
| 32 | #undef ATOMIC_OP | 32 | #undef ATOMIC_OP |
| 33 | 33 | ||
| 34 | #define ATOMIC_FETCH_OP(name, op) \ | 34 | #define ATOMIC_FETCH_OP(name, op) \ |
| 35 | static inline int arch_##op##name(int i, atomic_t *v) \ | 35 | static __always_inline int arch_##op##name(int i, atomic_t *v) \ |
| 36 | { \ | 36 | { \ |
| 37 | return __lse_ll_sc_body(op##name, i, v); \ | 37 | return __lse_ll_sc_body(op##name, i, v); \ |
| 38 | } | 38 | } |
| @@ -56,7 +56,7 @@ ATOMIC_FETCH_OPS(atomic_sub_return) · 17 unmodified lines | |||
| 56 | #undef ATOMIC_FETCH_OPS | 56 | #undef ATOMIC_FETCH_OPS |
| 57 | 57 | ||
| 58 | #define ATOMIC64_OP(op) \ | 58 | #define ATOMIC64_OP(op) \ |
| 59 | static inline void arch_##op(long i, atomic64_t *v) \ | 59 | static __always_inline void arch_##op(long i, atomic64_t *v) \ |
| 60 | { \ | 60 | { \ |
| 61 | __lse_ll_sc_body(op, i, v); \ | 61 | __lse_ll_sc_body(op, i, v); \ |
| 62 | } | 62 | } |
| @@ -71,7 +71,7 @@ ATOMIC64_OP(atomic64_sub) · 8 unmodified lines | |||
| 71 | #undef ATOMIC64_OP | 71 | #undef ATOMIC64_OP |
| 72 | 72 | ||
| 73 | #define ATOMIC64_FETCH_OP(name, op) \ | 73 | #define ATOMIC64_FETCH_OP(name, op) \ |
| 74 | static inline long arch_##op##name(long i, atomic64_t *v) \ | 74 | static __always_inline long arch_##op##name(long i, atomic64_t *v) \ |
| 75 | { \ | 75 | { \ |
| 76 | return __lse_ll_sc_body(op##name, i, v); \ | 76 | return __lse_ll_sc_body(op##name, i, v); \ |
| 77 | } | 77 | } |
| @@ -94,7 +94,7 @@ ATOMIC64_FETCH_OPS(atomic64_sub_return) · 16 unmodified lines | |||
| 94 | #undef ATOMIC64_FETCH_OP | 94 | #undef ATOMIC64_FETCH_OP |
| 95 | #undef ATOMIC64_FETCH_OPS | 95 | #undef ATOMIC64_FETCH_OPS |
| 96 | 96 | ||
| 97 | static inline long arch_atomic64_dec_if_positive(atomic64_t *v) | 97 | static __always_inline long arch_atomic64_dec_if_positive(atomic64_t *v) |
| 98 | { | 98 | { |
| 99 | return __lse_ll_sc_body(atomic64_dec_if_positive, v); | 99 | return __lse_ll_sc_body(atomic64_dec_if_positive, v); |
| 100 | } | 100 | } |
| @@ -17,6 +17,7 @@ · 16 unmodified lines | |||
| 17 | #include <linux/jump_label.h> | 17 | #include <linux/jump_label.h> |
| 18 | #include <linux/kvm_types.h> | 18 | #include <linux/kvm_types.h> |
| 19 | #include <linux/percpu.h> | 19 | #include <linux/percpu.h> |
| 20 | #include <linux/psci.h> | ||
| 20 | #include <asm/arch_gicv3.h> | 21 | #include <asm/arch_gicv3.h> |
| 21 | #include <asm/barrier.h> | 22 | #include <asm/barrier.h> |
| 22 | #include <asm/cpufeature.h> | 23 | #include <asm/cpufeature.h> |
| @@ -240,6 +241,28 @@ struct kvm_host_data { · 217 unmodified lines | |||
| 240 | struct kvm_pmu_events pmu_events; | 241 | struct kvm_pmu_events pmu_events; |
| 241 | }; | 242 | }; |
| 242 | 243 | ||
| 244 | struct kvm_host_psci_config { | ||
| 245 | /* PSCI version used by host. */ | ||
| 246 | u32 version; | ||
| 247 | |||
| 248 | /* Function IDs used by host if version is v0.1. */ | ||
| 249 | struct psci_0_1_function_ids function_ids_0_1; | ||
| 250 | |||
| 251 | bool psci_0_1_cpu_suspend_implemented; | ||
| 252 | bool psci_0_1_cpu_on_implemented; | ||
| 253 | bool psci_0_1_cpu_off_implemented; | ||
| 254 | bool psci_0_1_migrate_implemented; | ||
| 255 | }; | ||
| 256 | |||
| 257 | extern struct kvm_host_psci_config kvm_nvhe_sym(kvm_host_psci_config); | ||
| 258 | #define kvm_host_psci_config CHOOSE_NVHE_SYM(kvm_host_psci_config) | ||
| 259 | |||
| 260 | extern s64 kvm_nvhe_sym(hyp_physvirt_offset); | ||
| 261 | #define hyp_physvirt_offset CHOOSE_NVHE_SYM(hyp_physvirt_offset) | ||
| 262 | |||
| 263 | extern u64 kvm_nvhe_sym(hyp_cpu_logical_map)[NR_CPUS]; | ||
| 264 | #define hyp_cpu_logical_map CHOOSE_NVHE_SYM(hyp_cpu_logical_map) | ||
| 265 | |||
| 243 | struct vcpu_reset_state { | 266 | struct vcpu_reset_state { |
| 244 | unsigned long pc; | 267 | unsigned long pc; |
| 245 | unsigned long r0; | 268 | unsigned long r0; |
| @@ -247,11 +247,13 @@ static inline const void *__tag_set(const void *addr, u8 tag) · 246 unmodified lines | |||
| 247 | 247 | ||
| 248 | 248 | ||
| 249 | /* | 249 | /* |
| 250 | * The linear kernel range starts at the bottom of the virtual address space. | 250 | * Check whether an arbitrary address is within the linear map, which |
| 251 | * lives in the [PAGE_OFFSET, PAGE_END) interval at the bottom of the | ||
| 252 | * kernel's TTBR1 address range. | ||
| 251 | */ | 253 | */ |
| 252 | #define __is_lm_address(addr) (((u64)(addr) & ~PAGE_OFFSET) < (PAGE_END - PAGE_OFFSET)) | 254 | #define __is_lm_address(addr) (((u64)(addr) - PAGE_OFFSET) < (PAGE_END - PAGE_OFFSET)) |
| 253 | 255 | ||
| 254 | #define __lm_to_phys(addr) (((addr) & ~PAGE_OFFSET) + PHYS_OFFSET) | 256 | #define __lm_to_phys(addr) (((addr) - PAGE_OFFSET) + PHYS_OFFSET) |
| 255 | #define __kimg_to_phys(addr) ((addr) - kimage_voffset) | 257 | #define __kimg_to_phys(addr) ((addr) - kimage_voffset) |
| 256 | 258 | ||
| 257 | #define __virt_to_phys_nodebug(x) ({ \ | 259 | #define __virt_to_phys_nodebug(x) ({ \ |
| @@ -330,7 +332,7 @@ static inline void *phys_to_virt(phys_addr_t x) · 72 unmodified lines | |||
| 330 | #endif /* !CONFIG_SPARSEMEM_VMEMMAP || CONFIG_DEBUG_VIRTUAL */ | 332 | #endif /* !CONFIG_SPARSEMEM_VMEMMAP || CONFIG_DEBUG_VIRTUAL */ |
| 331 | 333 | ||
| 332 | #define virt_addr_valid(addr) ({ \ | 334 | #define virt_addr_valid(addr) ({ \ |
| 333 | __typeof__(addr) __addr = addr; \ | 335 | __typeof__(addr) __addr = __tag_reset(addr); \ |
| 334 | __is_lm_address(__addr) && pfn_valid(virt_to_pfn(__addr)); \ | 336 | __is_lm_address(__addr) && pfn_valid(virt_to_pfn(__addr)); \ |
| 335 | }) | 337 | }) |
| 336 | 338 | ||
| @@ -176,10 +176,21 @@ static inline void __uaccess_enable_hw_pan(void) · 175 unmodified lines | |||
| 176 | * The Tag check override (TCO) bit disables temporarily the tag checking | 176 | * The Tag check override (TCO) bit disables temporarily the tag checking |
| 177 | * preventing the issue. | 177 | * preventing the issue. |
| 178 | */ | 178 | */ |
| 179 | static inline void uaccess_disable_privileged(void) | 179 | static inline void __uaccess_disable_tco(void) |
| 180 | { | 180 | { |
| 181 | asm volatile(ALTERNATIVE("nop", SET_PSTATE_TCO(0), | 181 | asm volatile(ALTERNATIVE("nop", SET_PSTATE_TCO(0), |
| 182 | ARM64_MTE, CONFIG_KASAN_HW_TAGS)); | 182 | ARM64_MTE, CONFIG_KASAN_HW_TAGS)); |
| 183 | } | ||
| 184 | |||
| 185 | static inline void __uaccess_enable_tco(void) | ||
| 186 | { | ||
| 187 | asm volatile(ALTERNATIVE("nop", SET_PSTATE_TCO(1), | ||
| 188 | ARM64_MTE, CONFIG_KASAN_HW_TAGS)); | ||
| 189 | } | ||
| 190 | |||
| 191 | static inline void uaccess_disable_privileged(void) | ||
| 192 | { | ||
| 193 | __uaccess_disable_tco(); | ||
| 183 | 194 | ||
| 184 | if (uaccess_ttbr0_disable()) | 195 | if (uaccess_ttbr0_disable()) |
| 185 | return; | 196 | return; |
| @@ -189,8 +200,7 @@ static inline void uaccess_disable_privileged(void) · 3 unmodified lines | |||
| 189 | 200 | ||
| 190 | static inline void uaccess_enable_privileged(void) | 201 | static inline void uaccess_enable_privileged(void) |
| 191 | { | 202 | { |
| 192 | asm volatile(ALTERNATIVE("nop", SET_PSTATE_TCO(1), | 203 | __uaccess_enable_tco(); |
| 193 | ARM64_MTE, CONFIG_KASAN_HW_TAGS)); | ||
| 194 | 204 | ||
| 195 | if (uaccess_ttbr0_enable()) | 205 | if (uaccess_ttbr0_enable()) |
| 196 | return; | 206 | return; |
| @@ -75,7 +75,7 @@ int main(void) · 74 unmodified lines | |||
| 75 | DEFINE(S_SDEI_TTBR1, offsetof(struct pt_regs, sdei_ttbr1)); | 75 | DEFINE(S_SDEI_TTBR1, offsetof(struct pt_regs, sdei_ttbr1)); |
| 76 | DEFINE(S_PMR_SAVE, offsetof(struct pt_regs, pmr_save)); | 76 | DEFINE(S_PMR_SAVE, offsetof(struct pt_regs, pmr_save)); |
| 77 | DEFINE(S_STACKFRAME, offsetof(struct pt_regs, stackframe)); | 77 | DEFINE(S_STACKFRAME, offsetof(struct pt_regs, stackframe)); |
| 78 | DEFINE(S_FRAME_SIZE, sizeof(struct pt_regs)); | 78 | DEFINE(PT_REGS_SIZE, sizeof(struct pt_regs)); |
| 79 | BLANK(); | 79 | BLANK(); |
| 80 | #ifdef CONFIG_COMPAT | 80 | #ifdef CONFIG_COMPAT |
| 81 | DEFINE(COMPAT_SIGFRAME_REGS_OFFSET, offsetof(struct compat_sigframe, uc.uc_mcontext.arm_r0)); | 81 | DEFINE(COMPAT_SIGFRAME_REGS_OFFSET, offsetof(struct compat_sigframe, uc.uc_mcontext.arm_r0)); |
| @@ -1701,16 +1701,12 @@ static void bti_enable(const struct arm64_cpu_capabilities *__unused) · 1700 unmodified lines | |||
| 1701 | #ifdef CONFIG_ARM64_MTE | 1701 | #ifdef CONFIG_ARM64_MTE |
| 1702 | static void cpu_enable_mte(struct arm64_cpu_capabilities const *cap) | 1702 | static void cpu_enable_mte(struct arm64_cpu_capabilities const *cap) |
| 1703 | { | 1703 | { |
| 1704 | static bool cleared_zero_page = false; | ||
| 1705 | |||
| 1706 | /* | 1704 | /* |
| 1707 | * Clear the tags in the zero page. This needs to be done via the | 1705 | * Clear the tags in the zero page. This needs to be done via the |
| 1708 | * linear map which has the Tagged attribute. | 1706 | * linear map which has the Tagged attribute. |
| 1709 | */ | 1707 | */ |
| 1710 | if (!cleared_zero_page) { | 1708 | if (!test_and_set_bit(PG_mte_tagged, &ZERO_PAGE(0)->flags)) |
| 1711 | cleared_zero_page = true; | ||
| 1712 | mte_clear_page_tags(lm_alias(empty_zero_page)); | 1709 | mte_clear_page_tags(lm_alias(empty_zero_page)); |
| 1713 | } | ||
| 1714 | 1710 | ||
| 1715 | kasan_init_hw_tags_cpu(); | 1711 | kasan_init_hw_tags_cpu(); |
| 1716 | } | 1712 | } |
| @@ -2568,7 +2564,7 @@ static void verify_hyp_capabilities(void) · 851 unmodified lines | |||
| 2568 | int parange, ipa_max; | 2564 | int parange, ipa_max; |
| 2569 | unsigned int safe_vmid_bits, vmid_bits; | 2565 | unsigned int safe_vmid_bits, vmid_bits; |
| 2570 | 2566 | ||
| 2571 | if (!IS_ENABLED(CONFIG_KVM) || !IS_ENABLED(CONFIG_KVM_ARM_HOST)) | 2567 | if (!IS_ENABLED(CONFIG_KVM)) |
| 2572 | return; | 2568 | return; |
| 2573 | 2569 | ||
| 2574 | safe_mmfr1 = read_sanitised_ftr_reg(SYS_ID_AA64MMFR1_EL1); | 2570 | safe_mmfr1 = read_sanitised_ftr_reg(SYS_ID_AA64MMFR1_EL1); |
| @@ -35,7 +35,7 @@ · 34 unmodified lines | |||
| 35 | */ | 35 | */ |
| 36 | .macro ftrace_regs_entry, allregs=0 | 36 | .macro ftrace_regs_entry, allregs=0 |
| 37 | /* Make room for pt_regs, plus a callee frame */ | 37 | /* Make room for pt_regs, plus a callee frame */ |
| 38 | sub sp, sp, #(S_FRAME_SIZE + 16) | 38 | sub sp, sp, #(PT_REGS_SIZE + 16) |
| 39 | 39 | ||
| 40 | /* Save function arguments (and x9 for simplicity) */ | 40 | /* Save function arguments (and x9 for simplicity) */ |
| 41 | stp x0, x1, [sp, #S_X0] | 41 | stp x0, x1, [sp, #S_X0] |
| @@ -61,15 +61,15 @@ · 19 unmodified lines | |||
| 61 | .endif | 61 | .endif |
| 62 | 62 | ||
| 63 | /* Save the callsite's SP and LR */ | 63 | /* Save the callsite's SP and LR */ |
| 64 | add x10, sp, #(S_FRAME_SIZE + 16) | 64 | add x10, sp, #(PT_REGS_SIZE + 16) |
| 65 | stp x9, x10, [sp, #S_LR] | 65 | stp x9, x10, [sp, #S_LR] |
| 66 | 66 | ||
| 67 | /* Save the PC after the ftrace callsite */ | 67 | /* Save the PC after the ftrace callsite */ |
| 68 | str x30, [sp, #S_PC] | 68 | str x30, [sp, #S_PC] |
| 69 | 69 | ||
| 70 | /* Create a frame record for the callsite above pt_regs */ | 70 | /* Create a frame record for the callsite above pt_regs */ |
| 71 | stp x29, x9, [sp, #S_FRAME_SIZE] | 71 | stp x29, x9, [sp, #PT_REGS_SIZE] |
| 72 | add x29, sp, #S_FRAME_SIZE | 72 | add x29, sp, #PT_REGS_SIZE |
| 73 | 73 | ||
| 74 | /* Create our frame record within pt_regs. */ | 74 | /* Create our frame record within pt_regs. */ |
| 75 | stp x29, x30, [sp, #S_STACKFRAME] | 75 | stp x29, x30, [sp, #S_STACKFRAME] |
| @@ -120,7 +120,7 @@ ftrace_common_return: · 44 unmodified lines | |||
| 120 | ldr x9, [sp, #S_PC] | 120 | ldr x9, [sp, #S_PC] |
| 121 | 121 | ||
| 122 | /* Restore the callsite's SP */ | 122 | /* Restore the callsite's SP */ |
| 123 | add sp, sp, #S_FRAME_SIZE + 16 | 123 | add sp, sp, #PT_REGS_SIZE + 16 |
| 124 | 124 | ||
| 125 | ret x9 | 125 | ret x9 |
| 126 | SYM_CODE_END(ftrace_common) | 126 | SYM_CODE_END(ftrace_common) |
| @@ -130,7 +130,7 @@ SYM_CODE_START(ftrace_graph_caller) · 3 unmodified lines | |||
| 130 | ldr x0, [sp, #S_PC] | 130 | ldr x0, [sp, #S_PC] |
| 131 | sub x0, x0, #AARCH64_INSN_SIZE // ip (callsite's BL insn) | 131 | sub x0, x0, #AARCH64_INSN_SIZE // ip (callsite's BL insn) |
| 132 | add x1, sp, #S_LR // parent_ip (callsite's LR) | 132 | add x1, sp, #S_LR // parent_ip (callsite's LR) |
| 133 | ldr x2, [sp, #S_FRAME_SIZE] // parent fp (callsite's FP) | 133 | ldr x2, [sp, #PT_REGS_SIZE] // parent fp (callsite's FP) |
| 134 | bl prepare_ftrace_return | 134 | bl prepare_ftrace_return |
| 135 | b ftrace_common_return | 135 | b ftrace_common_return |
| 136 | SYM_CODE_END(ftrace_graph_caller) | 136 | SYM_CODE_END(ftrace_graph_caller) |
| @@ -75,7 +75,7 @@ alternative_else_nop_endif · 74 unmodified lines | |||
| 75 | .endif | 75 | .endif |
| 76 | #endif | 76 | #endif |
| 77 | 77 | ||
| 78 | sub sp, sp, #S_FRAME_SIZE | 78 | sub sp, sp, #PT_REGS_SIZE |
| 79 | #ifdef CONFIG_VMAP_STACK | 79 | #ifdef CONFIG_VMAP_STACK |
| 80 | /* | 80 | /* |
| 81 | * Test whether the SP has overflowed, without corrupting a GPR. | 81 | * Test whether the SP has overflowed, without corrupting a GPR. |
| @@ -96,7 +96,7 @@ alternative_else_nop_endif · 14 unmodified lines | |||
| 96 | * userspace, and can clobber EL0 registers to free up GPRs. | 96 | * userspace, and can clobber EL0 registers to free up GPRs. |
| 97 | */ | 97 | */ |
| 98 | 98 | ||
| 99 | /* Stash the original SP (minus S_FRAME_SIZE) in tpidr_el0. */ | 99 | /* Stash the original SP (minus PT_REGS_SIZE) in tpidr_el0. */ |
| 100 | msr tpidr_el0, x0 | 100 | msr tpidr_el0, x0 |
| 101 | 101 | ||
| 102 | /* Recover the original x0 value and stash it in tpidrro_el0 */ | 102 | /* Recover the original x0 value and stash it in tpidrro_el0 */ |
| @@ -182,7 +182,6 @@ alternative_else_nop_endif · 79 unmodified lines | |||
| 182 | mrs_s \tmp2, SYS_GCR_EL1 | 182 | mrs_s \tmp2, SYS_GCR_EL1 |
| 183 | bfi \tmp2, \tmp, #0, #16 | 183 | bfi \tmp2, \tmp, #0, #16 |
| 184 | msr_s SYS_GCR_EL1, \tmp2 | 184 | msr_s SYS_GCR_EL1, \tmp2 |
| 185 | isb | ||
| 186 | #endif | 185 | #endif |
| 187 | .endm | 186 | .endm |
| 188 | 187 | ||
| @@ -194,6 +193,7 @@ alternative_else_nop_endif · 5 unmodified lines | |||
| 194 | ldr_l \tmp, gcr_kernel_excl | 193 | ldr_l \tmp, gcr_kernel_excl |
| 195 | 194 | ||
| 196 | mte_set_gcr \tmp, \tmp2 | 195 | mte_set_gcr \tmp, \tmp2 |
| 196 | isb | ||
| 197 | 1: | 197 | 1: |
| 198 | #endif | 198 | #endif |
| 199 | .endm | 199 | .endm |
| @@ -253,7 +253,7 @@ alternative_else_nop_endif · 53 unmodified lines | |||
| 253 | 253 | ||
| 254 | scs_load tsk, x20 | 254 | scs_load tsk, x20 |
| 255 | .else | 255 | .else |
| 256 | add x21, sp, #S_FRAME_SIZE | 256 | add x21, sp, #PT_REGS_SIZE |
| 257 | get_current_task tsk | 257 | get_current_task tsk |
| 258 | .endif /* \el == 0 */ | 258 | .endif /* \el == 0 */ |
| 259 | mrs x22, elr_el1 | 259 | mrs x22, elr_el1 |
| @@ -377,7 +377,7 @@ alternative_else_nop_endif · 117 unmodified lines | |||
| 377 | ldp x26, x27, [sp, #16 * 13] | 377 | ldp x26, x27, [sp, #16 * 13] |
| 378 | ldp x28, x29, [sp, #16 * 14] | 378 | ldp x28, x29, [sp, #16 * 14] |
| 379 | ldr lr, [sp, #S_LR] | 379 | ldr lr, [sp, #S_LR] |
| 380 | add sp, sp, #S_FRAME_SIZE // restore sp | 380 | add sp, sp, #PT_REGS_SIZE // restore sp |
| 381 | 381 | ||
| 382 | .if \el == 0 | 382 | .if \el == 0 |
| 383 | alternative_insn eret, nop, ARM64_UNMAP_KERNEL_AT_EL0 | 383 | alternative_insn eret, nop, ARM64_UNMAP_KERNEL_AT_EL0 |
| @@ -580,12 +580,12 @@ __bad_stack: · 196 unmodified lines | |||
| 580 | 580 | ||
| 581 | /* | 581 | /* |
| 582 | * Store the original GPRs to the new stack. The orginal SP (minus | 582 | * Store the original GPRs to the new stack. The orginal SP (minus |
| 583 | * S_FRAME_SIZE) was stashed in tpidr_el0 by kernel_ventry. | 583 | * PT_REGS_SIZE) was stashed in tpidr_el0 by kernel_ventry. |
| 584 | */ | 584 | */ |
| 585 | sub sp, sp, #S_FRAME_SIZE | 585 | sub sp, sp, #PT_REGS_SIZE |
| 586 | kernel_entry 1 | 586 | kernel_entry 1 |
| 587 | mrs x0, tpidr_el0 | 587 | mrs x0, tpidr_el0 |
| 588 | add x0, x0, #S_FRAME_SIZE | 588 | add x0, x0, #PT_REGS_SIZE |
| 589 | str x0, [sp, #S_SP] | 589 | str x0, [sp, #S_SP] |
| 590 | 590 | ||
| 591 | /* Stash the regs for handle_bad_stack */ | 591 | /* Stash the regs for handle_bad_stack */ |
| @@ -329,11 +329,12 @@ static int __access_remote_tags(struct mm_struct *mm, unsigned long addr, · 328 unmodified lines | |||
| 329 | * would cause the existing tags to be cleared if the page | 329 | * would cause the existing tags to be cleared if the page |
| 330 | * was never mapped with PROT_MTE. | 330 | * was never mapped with PROT_MTE. |
| 331 | */ | 331 | */ |
| 332 | if (!test_bit(PG_mte_tagged, &page->flags)) { | 332 | if (!(vma->vm_flags & VM_MTE)) { |
| 333 | ret = -EOPNOTSUPP; | 333 | ret = -EOPNOTSUPP; |
| 334 | put_page(page); | 334 | put_page(page); |
| 335 | break; | 335 | break; |
| 336 | } | 336 | } |
| 337 | WARN_ON_ONCE(!test_bit(PG_mte_tagged, &page->flags)); | ||
| 337 | 338 | ||
| 338 | /* limit access to the end of the page */ | 339 | /* limit access to the end of the page */ |
| 339 | offset = offset_in_page(addr); | 340 | offset = offset_in_page(addr); |
| @@ -23,8 +23,6 @@ · 22 unmodified lines | |||
| 23 | #include <linux/platform_device.h> | 23 | #include <linux/platform_device.h> |
| 24 | #include <linux/sched_clock.h> | 24 | #include <linux/sched_clock.h> |
| 25 | #include <linux/smp.h> | 25 | #include <linux/smp.h> |
| 26 | #include <linux/nmi.h> | ||
| 27 | #include <linux/cpufreq.h> | ||
| 28 | 26 | ||
| 29 | /* ARMv8 Cortex-A53 specific event types. */ | 27 | /* ARMv8 Cortex-A53 specific event types. */ |
| 30 | #define ARMV8_A53_PERFCTR_PREF_LINEFILL 0xC2 | 28 | #define ARMV8_A53_PERFCTR_PREF_LINEFILL 0xC2 |
| @@ -1250,21 +1248,10 @@ static struct platform_driver armv8_pmu_driver = { · 1219 unmodified lines | |||
| 1250 | 1248 | ||
| 1251 | static int __init armv8_pmu_driver_init(void) | 1249 | static int __init armv8_pmu_driver_init(void) |
| 1252 | { | 1250 | { |
| 1253 | int ret; | ||
| 1254 | |||
| 1255 | if (acpi_disabled) | 1251 | if (acpi_disabled) |
| 1256 | ret = platform_driver_register(&armv8_pmu_driver); | 1252 | return platform_driver_register(&armv8_pmu_driver); |
| 1257 | else | 1253 | else |
| 1258 | ret = arm_pmu_acpi_probe(armv8_pmuv3_init); | 1254 | return arm_pmu_acpi_probe(armv8_pmuv3_init); |
| 1259 | |||
| 1260 | /* | ||
| 1261 | * Try to re-initialize lockup detector after PMU init in | ||
| 1262 | * case PMU events are triggered via NMIs. | ||
| 1263 | */ | ||
| 1264 | if (ret == 0 && arm_pmu_irq_is_nmi()) | ||
| 1265 | lockup_detector_init(); | ||
| 1266 | |||
| 1267 | return ret; | ||
| 1268 | } | 1255 | } |
| 1269 | device_initcall(armv8_pmu_driver_init) | 1256 | device_initcall(armv8_pmu_driver_init) |
| 1270 | 1257 | ||
| @@ -1322,27 +1309,3 @@ void arch_perf_update_userpage(struct perf_event *event, · 51 unmodified lines | |||
| 1322 | userpg->cap_user_time_zero = 1; | 1309 | userpg->cap_user_time_zero = 1; |
| 1323 | userpg->cap_user_time_short = 1; | 1310 | userpg->cap_user_time_short = 1; |
| 1324 | } | 1311 | } |
| 1325 | |||
| 1326 | #ifdef CONFIG_HARDLOCKUP_DETECTOR_PERF | ||
| 1327 | /* | ||
| 1328 | * Safe maximum CPU frequency in case a particular platform doesn't implement | ||
| 1329 | * cpufreq driver. Although, architecture doesn't put any restrictions on | ||
| 1330 | * maximum frequency but 5 GHz seems to be safe maximum given the available | ||
| 1331 | * Arm CPUs in the market which are clocked much less than 5 GHz. On the other | ||
| 1332 | * hand, we can't make it much higher as it would lead to a large hard-lockup | ||
| 1333 | * detection timeout on parts which are running slower (eg. 1GHz on | ||
| 1334 | * Developerbox) and doesn't possess a cpufreq driver. | ||
| 1335 | */ | ||
| 1336 | #define SAFE_MAX_CPU_FREQ 5000000000UL // 5 GHz | ||
| 1337 | u64 hw_nmi_get_sample_period(int watchdog_thresh) | ||
| 1338 | { | ||
| 1339 | unsigned int cpu = smp_processor_id(); | ||
| 1340 | unsigned long max_cpu_freq; | ||
| 1341 | |||
| 1342 | max_cpu_freq = cpufreq_get_hw_max_freq(cpu) * 1000UL; | ||
| 1343 | if (!max_cpu_freq) | ||
| 1344 | max_cpu_freq = SAFE_MAX_CPU_FREQ; | ||
| 1345 | |||
| 1346 | return (u64)max_cpu_freq * watchdog_thresh; | ||
| 1347 | } | ||
| 1348 | #endif | ||
| @@ -352,8 +352,8 @@ kprobe_breakpoint_ss_handler(struct pt_regs *regs, unsigned int esr) · 351 unmodified lines | |||
| 352 | unsigned long addr = instruction_pointer(regs); | 352 | unsigned long addr = instruction_pointer(regs); |
| 353 | struct kprobe *cur = kprobe_running(); | 353 | struct kprobe *cur = kprobe_running(); |
| 354 | 354 | ||
| 355 | if (cur && (kcb->kprobe_status == KPROBE_HIT_SS) | 355 | if (cur && (kcb->kprobe_status & (KPROBE_HIT_SS | KPROBE_REENTER)) && |
| 356 | && ((unsigned long)&cur->ainsn.api.insn[1] == addr)) { | 356 | ((unsigned long)&cur->ainsn.api.insn[1] == addr)) { |
| 357 | kprobes_restore_local_irqflag(kcb, regs); | 357 | kprobes_restore_local_irqflag(kcb, regs); |
| 358 | post_kprobe_handler(cur, kcb, regs); | 358 | post_kprobe_handler(cur, kcb, regs); |
| 359 | 359 | ||
| @@ -25,7 +25,7 @@ · 24 unmodified lines | |||
| 25 | stp x24, x25, [sp, #S_X24] | 25 | stp x24, x25, [sp, #S_X24] |
| 26 | stp x26, x27, [sp, #S_X26] | 26 | stp x26, x27, [sp, #S_X26] |
| 27 | stp x28, x29, [sp, #S_X28] | 27 | stp x28, x29, [sp, #S_X28] |
| 28 | add x0, sp, #S_FRAME_SIZE | 28 | add x0, sp, #PT_REGS_SIZE |
| 29 | stp lr, x0, [sp, #S_LR] | 29 | stp lr, x0, [sp, #S_LR] |
| 30 | /* | 30 | /* |
| 31 | * Construct a useful saved PSTATE | 31 | * Construct a useful saved PSTATE |
| @@ -62,7 +62,7 @@ · 30 unmodified lines | |||
| 62 | .endm | 62 | .endm |
| 63 | 63 | ||
| 64 | SYM_CODE_START(kretprobe_trampoline) | 64 | SYM_CODE_START(kretprobe_trampoline) |
| 65 | sub sp, sp, #S_FRAME_SIZE | 65 | sub sp, sp, #PT_REGS_SIZE |
| 66 | 66 | ||
| 67 | save_all_base_regs | 67 | save_all_base_regs |
| 68 | 68 | ||
| @@ -76,7 +76,7 @@ SYM_CODE_START(kretprobe_trampoline) · 7 unmodified lines | |||
| 76 | 76 | ||
| 77 | restore_all_base_regs | 77 | restore_all_base_regs |
| 78 | 78 | ||
| 79 | add sp, sp, #S_FRAME_SIZE | 79 | add sp, sp, #PT_REGS_SIZE |
| 80 | ret | 80 | ret |
| 81 | 81 | ||
| 82 | SYM_CODE_END(kretprobe_trampoline) | 82 | SYM_CODE_END(kretprobe_trampoline) |
| @@ -914,13 +914,6 @@ static void do_signal(struct pt_regs *regs) · 913 unmodified lines | |||
| 914 | asmlinkage void do_notify_resume(struct pt_regs *regs, | 914 | asmlinkage void do_notify_resume(struct pt_regs *regs, |
| 915 | unsigned long thread_flags) | 915 | unsigned long thread_flags) |
| 916 | { | 916 | { |
| 917 | /* | ||
| 918 | * The assembly code enters us with IRQs off, but it hasn't | ||
| 919 | * informed the tracing code of that for efficiency reasons. | ||
| 920 | * Update the trace code with the current status. | ||
| 921 | */ | ||
| 922 | trace_hardirqs_off(); | ||
| 923 | |||
| 924 | do { | 917 | do { |
| 925 | if (thread_flags & _TIF_NEED_RESCHED) { | 918 | if (thread_flags & _TIF_NEED_RESCHED) { |
| 926 | /* Unmask Debug and SError for the next task */ | 919 | /* Unmask Debug and SError for the next task */ |
| @@ -434,7 +434,7 @@ static void __init hyp_mode_check(void) · 433 unmodified lines | |||
| 434 | "CPU: CPUs started in inconsistent modes"); | 434 | "CPU: CPUs started in inconsistent modes"); |
| 435 | else | 435 | else |
| 436 | pr_info("CPU: All CPU(s) started at EL1\n"); | 436 | pr_info("CPU: All CPU(s) started at EL1\n"); |
| 437 | if (IS_ENABLED(CONFIG_KVM)) | 437 | if (IS_ENABLED(CONFIG_KVM) && !is_kernel_in_hyp_mode()) |
| 438 | kvm_compute_layout(); | 438 | kvm_compute_layout(); |
| 439 | } | 439 | } |
| 440 | 440 | ||
| @@ -807,7 +807,6 @@ int arch_show_interrupts(struct seq_file *p, int prec) · 366 unmodified lines | |||
| 807 | unsigned int cpu, i; | 807 | unsigned int cpu, i; |
| 808 | 808 | ||
| 809 | for (i = 0; i < NR_IPI; i++) { | 809 | for (i = 0; i < NR_IPI; i++) { |
| 810 | unsigned int irq = irq_desc_get_irq(ipi_desc[i]); | ||
| 811 | seq_printf(p, "%*s%u:%s", prec - 1, "IPI", i, | 810 | seq_printf(p, "%*s%u:%s", prec - 1, "IPI", i, |
| 812 | prec >= 4 ? " " : ""); | 811 | prec >= 4 ? " " : ""); |
| 813 | for_each_online_cpu(cpu) | 812 | for_each_online_cpu(cpu) |
| @@ -9,6 +9,7 @@ · 8 unmodified lines | |||
| 9 | 9 | ||
| 10 | #include <asm/daifflags.h> | 10 | #include <asm/daifflags.h> |
| 11 | #include <asm/debug-monitors.h> | 11 | #include <asm/debug-monitors.h> |
| 12 | #include <asm/exception.h> | ||
| 12 | #include <asm/fpsimd.h> | 13 | #include <asm/fpsimd.h> |
| 13 | #include <asm/syscall.h> | 14 | #include <asm/syscall.h> |
| 14 | #include <asm/thread_info.h> | 15 | #include <asm/thread_info.h> |
| @@ -165,15 +166,8 @@ static void el0_svc_common(struct pt_regs *regs, int scno, int sc_nr, · 150 unmodified lines | |||
| 165 | if (!has_syscall_work(flags) && !IS_ENABLED(CONFIG_DEBUG_RSEQ)) { | 166 | if (!has_syscall_work(flags) && !IS_ENABLED(CONFIG_DEBUG_RSEQ)) { |
| 166 | local_daif_mask(); | 167 | local_daif_mask(); |
| 167 | flags = current_thread_info()->flags; | 168 | flags = current_thread_info()->flags; |
| 168 | if (!has_syscall_work(flags) && !(flags & _TIF_SINGLESTEP)) { | 169 | if (!has_syscall_work(flags) && !(flags & _TIF_SINGLESTEP)) |
| 169 | /* | ||
| 170 | * We're off to userspace, where interrupts are | ||
| 171 | * always enabled after we restore the flags from | ||
| 172 | * the SPSR. | ||
| 173 | */ | ||
| 174 | trace_hardirqs_on(); | ||
| 175 | return; | 170 | return; |
| 176 | } | ||
| 177 | local_daif_restore(DAIF_PROCCTX); | 171 | local_daif_restore(DAIF_PROCCTX); |
| 178 | } | 172 | } |
| 179 | 173 | ||
| @@ -42,7 +42,6 @@ · 41 unmodified lines | |||
| 42 | #include <asm/smp.h> | 42 | #include <asm/smp.h> |
| 43 | #include <asm/stack_pointer.h> | 43 | #include <asm/stack_pointer.h> |
| 44 | #include <asm/stacktrace.h> | 44 | #include <asm/stacktrace.h> |
| 45 | #include <asm/exception.h> | ||
| 46 | #include <asm/system_misc.h> | 45 | #include <asm/system_misc.h> |
| 47 | #include <asm/sysreg.h> | 46 | #include <asm/sysreg.h> |
| 48 | 47 | ||
| @@ -24,8 +24,7 @@ btildflags-$(CONFIG_ARM64_BTI_KERNEL) += -z force-bti · 23 unmodified lines | |||
| 24 | # routines, as x86 does (see 6f121e548f83 ("x86, vdso: Reimplement vdso.so | 24 | # routines, as x86 does (see 6f121e548f83 ("x86, vdso: Reimplement vdso.so |
| 25 | # preparation in build-time C")). | 25 | # preparation in build-time C")). |
| 26 | ldflags-y := -shared -nostdlib -soname=linux-vdso.so.1 --hash-style=sysv \ | 26 | ldflags-y := -shared -nostdlib -soname=linux-vdso.so.1 --hash-style=sysv \ |
| 27 | -Bsymbolic $(call ld-option, --no-eh-frame-hdr) --build-id=sha1 -n \ | 27 | -Bsymbolic --build-id=sha1 -n $(btildflags-y) -T |
| 28 | $(btildflags-y) -T | ||
| 29 | 28 | ||
| 30 | ccflags-y := -fno-common -fno-builtin -fno-stack-protector -ffixed-x18 | 29 | ccflags-y := -fno-common -fno-builtin -fno-stack-protector -ffixed-x18 |
| 31 | ccflags-y += -DDISABLE_BRANCH_PROFILING -DBUILD_VDSO | 30 | ccflags-y += -DDISABLE_BRANCH_PROFILING -DBUILD_VDSO |
| @@ -40,9 +40,6 @@ SECTIONS · 39 unmodified lines | |||
| 40 | PROVIDE (_etext = .); | 40 | PROVIDE (_etext = .); |
| 41 | PROVIDE (etext = .); | 41 | PROVIDE (etext = .); |
| 42 | 42 | ||
| 43 | .eh_frame_hdr : { *(.eh_frame_hdr) } :text :eh_frame_hdr | ||
| 44 | .eh_frame : { KEEP (*(.eh_frame)) } :text | ||
| 45 | |||
| 46 | .dynamic : { *(.dynamic) } :text :dynamic | 43 | .dynamic : { *(.dynamic) } :text :dynamic |
| 47 | 44 | ||
| 48 | .rodata : { *(.rodata*) } :text | 45 | .rodata : { *(.rodata*) } :text |
| @@ -54,6 +51,7 @@ SECTIONS · 5 unmodified lines | |||
| 54 | *(.note.GNU-stack) | 51 | *(.note.GNU-stack) |
| 55 | *(.data .data.* .gnu.linkonce.d.* .sdata*) | 52 | *(.data .data.* .gnu.linkonce.d.* .sdata*) |
| 56 | *(.bss .sbss .dynbss .dynsbss) | 53 | *(.bss .sbss .dynbss .dynsbss) |
| 54 | *(.eh_frame .eh_frame_hdr) | ||
| 57 | } | 55 | } |
| 58 | } | 56 | } |
| 59 | 57 | ||
| @@ -66,7 +64,6 @@ PHDRS · 6 unmodified lines | |||
| 66 | text PT_LOAD FLAGS(5) FILEHDR PHDRS; /* PF_R|PF_X */ | 64 | text PT_LOAD FLAGS(5) FILEHDR PHDRS; /* PF_R|PF_X */ |
| 67 | dynamic PT_DYNAMIC FLAGS(4); /* PF_R */ | 65 | dynamic PT_DYNAMIC FLAGS(4); /* PF_R */ |
| 68 | note PT_NOTE FLAGS(4); /* PF_R */ | 66 | note PT_NOTE FLAGS(4); /* PF_R */ |
| 69 | eh_frame_hdr PT_GNU_EH_FRAME; | ||
| 70 | } | 67 | } |
| 71 | 68 | ||
| 72 | /* | 69 | /* |
| @@ -49,14 +49,6 @@ if KVM · 48 unmodified lines | |||
| 49 | 49 | ||
| 50 | source "virt/kvm/Kconfig" | 50 | source "virt/kvm/Kconfig" |
| 51 | 51 | ||
| 52 | config KVM_ARM_PMU | ||
| 53 | bool "Virtual Performance Monitoring Unit (PMU) support" | ||
| 54 | depends on HW_PERF_EVENTS | ||
| 55 | default y | ||
| 56 | help | ||
| 57 | Adds support for a virtual Performance Monitoring Unit (PMU) in | ||
| 58 | virtual machines. | ||
| 59 | |||
| 60 | endif # KVM | 52 | endif # KVM |
| 61 | 53 | ||
| 62 | endif # VIRTUALIZATION | 54 | endif # VIRTUALIZATION |
| @@ -24,4 +24,4 @@ kvm-y := $(KVM)/kvm_main.o $(KVM)/coalesced_mmio.o $(KVM)/eventfd.o \ · 23 unmodified lines | |||
| 24 | vgic/vgic-mmio-v3.o vgic/vgic-kvm-device.o \ | 24 | vgic/vgic-mmio-v3.o vgic/vgic-kvm-device.o \ |
| 25 | vgic/vgic-its.o vgic/vgic-debug.o | 25 | vgic/vgic-its.o vgic/vgic-debug.o |
| 26 | 26 | ||
| 27 | kvm-$(CONFIG_KVM_ARM_PMU) += pmu-emul.o | 27 | kvm-$(CONFIG_HW_PERF_EVENTS) += pmu-emul.o |
| @@ -1129,9 +1129,10 @@ int kvm_timer_enable(struct kvm_vcpu *vcpu) · 1128 unmodified lines | |||
| 1129 | if (!irqchip_in_kernel(vcpu->kvm)) | 1129 | if (!irqchip_in_kernel(vcpu->kvm)) |
| 1130 | goto no_vgic; | 1130 | goto no_vgic; |
| 1131 | 1131 | ||
| 1132 | if (!vgic_initialized(vcpu->kvm)) | 1132 | /* |
| 1133 | return -ENODEV; | 1133 | * At this stage, we have the guarantee that the vgic is both |
| 1134 | 1134 | * available and initialized. | |
| 1135 | */ | ||
| 1135 | if (!timer_irqs_are_valid(vcpu)) { | 1136 | if (!timer_irqs_are_valid(vcpu)) { |
| 1136 | kvm_debug("incorrectly configured timer irqs\n"); | 1137 | kvm_debug("incorrectly configured timer irqs\n"); |
| 1137 | return -EINVAL; | 1138 | return -EINVAL; |
| @@ -65,10 +65,6 @@ static bool vgic_present; · 64 unmodified lines | |||
| 65 | static DEFINE_PER_CPU(unsigned char, kvm_arm_hardware_enabled); | 65 | static DEFINE_PER_CPU(unsigned char, kvm_arm_hardware_enabled); |
| 66 | DEFINE_STATIC_KEY_FALSE(userspace_irqchip_in_use); | 66 | DEFINE_STATIC_KEY_FALSE(userspace_irqchip_in_use); |
| 67 | 67 | ||
| 68 | extern u64 kvm_nvhe_sym(__cpu_logical_map)[NR_CPUS]; | ||
| 69 | extern u32 kvm_nvhe_sym(kvm_host_psci_version); | ||
| 70 | extern struct psci_0_1_function_ids kvm_nvhe_sym(kvm_host_psci_0_1_function_ids); | ||
| 71 | |||
| 72 | int kvm_arch_vcpu_should_kick(struct kvm_vcpu *vcpu) | 68 | int kvm_arch_vcpu_should_kick(struct kvm_vcpu *vcpu) |
| 73 | { | 69 | { |
| 74 | return kvm_vcpu_exiting_guest_mode(vcpu) == IN_GUEST_MODE; | 70 | return kvm_vcpu_exiting_guest_mode(vcpu) == IN_GUEST_MODE; |
| @@ -584,11 +580,9 @@ static int kvm_vcpu_first_run_init(struct kvm_vcpu *vcpu) · 509 unmodified lines | |||
| 584 | * Map the VGIC hardware resources before running a vcpu the | 580 | * Map the VGIC hardware resources before running a vcpu the |
| 585 | * first time on this VM. | 581 | * first time on this VM. |
| 586 | */ | 582 | */ |
| 587 | if (unlikely(!vgic_ready(kvm))) { | 583 | ret = kvm_vgic_map_resources(kvm); |
| 588 | ret = kvm_vgic_map_resources(kvm); | 584 | if (ret) |
| 589 | if (ret) | 585 | return ret; |
| 590 | return ret; | ||
| 591 | } | ||
| 592 | } else { | 586 | } else { |
| 593 | /* | 587 | /* |
| 594 | * Tell the rest of the code that there are userspace irqchip | 588 | * Tell the rest of the code that there are userspace irqchip |
| @@ -1402,8 +1396,9 @@ static void cpu_init_hyp_mode(void) · 807 unmodified lines | |||
| 1402 | * Calculate the raw per-cpu offset without a translation from the | 1396 | * Calculate the raw per-cpu offset without a translation from the |
| 1403 | * kernel's mapping to the linear mapping, and store it in tpidr_el2 | 1397 | * kernel's mapping to the linear mapping, and store it in tpidr_el2 |
| 1404 | * so that we can use adr_l to access per-cpu variables in EL2. | 1398 | * so that we can use adr_l to access per-cpu variables in EL2. |
| 1399 | * Also drop the KASAN tag which gets in the way... | ||
| 1405 | */ | 1400 | */ |
| 1406 | params->tpidr_el2 = (unsigned long)this_cpu_ptr_nvhe_sym(__per_cpu_start) - | 1401 | params->tpidr_el2 = (unsigned long)kasan_reset_tag(this_cpu_ptr_nvhe_sym(__per_cpu_start)) - |
| 1407 | (unsigned long)kvm_ksym_ref(CHOOSE_NVHE_SYM(__per_cpu_start)); | 1402 | (unsigned long)kvm_ksym_ref(CHOOSE_NVHE_SYM(__per_cpu_start)); |
| 1408 | 1403 | ||
| 1409 | params->mair_el2 = read_sysreg(mair_el1); | 1404 | params->mair_el2 = read_sysreg(mair_el1); |
| @@ -1574,12 +1569,12 @@ static struct notifier_block hyp_init_cpu_pm_nb = { · 164 unmodified lines | |||
| 1574 | .notifier_call = hyp_init_cpu_pm_notifier, | 1569 | .notifier_call = hyp_init_cpu_pm_notifier, |
| 1575 | }; | 1570 | }; |
| 1576 | 1571 | ||
| 1577 | static void __init hyp_cpu_pm_init(void) | 1572 | static void hyp_cpu_pm_init(void) |
| 1578 | { | 1573 | { |
| 1579 | if (!is_protected_kvm_enabled()) | 1574 | if (!is_protected_kvm_enabled()) |
| 1580 | cpu_pm_register_notifier(&hyp_init_cpu_pm_nb); | 1575 | cpu_pm_register_notifier(&hyp_init_cpu_pm_nb); |
| 1581 | } | 1576 | } |
| 1582 | static void __init hyp_cpu_pm_exit(void) | 1577 | static void hyp_cpu_pm_exit(void) |
| 1583 | { | 1578 | { |
| 1584 | if (!is_protected_kvm_enabled()) | 1579 | if (!is_protected_kvm_enabled()) |
| 1585 | cpu_pm_unregister_notifier(&hyp_init_cpu_pm_nb); | 1580 | cpu_pm_unregister_notifier(&hyp_init_cpu_pm_nb); |
| @@ -1604,9 +1599,12 @@ static void init_cpu_logical_map(void) · 18 unmodified lines | |||
| 1604 | * allow any other CPUs from the `possible` set to boot. | 1599 | * allow any other CPUs from the `possible` set to boot. |
| 1605 | */ | 1600 | */ |
| 1606 | for_each_online_cpu(cpu) | 1601 | for_each_online_cpu(cpu) |
| 1607 | kvm_nvhe_sym(__cpu_logical_map)[cpu] = cpu_logical_map(cpu); | 1602 | hyp_cpu_logical_map[cpu] = cpu_logical_map(cpu); |
| 1608 | } | 1603 | } |
| 1609 | 1604 | ||
| 1605 | #define init_psci_0_1_impl_state(config, what) \ | ||
| 1606 | config.psci_0_1_ ## what ## _implemented = psci_ops.what | ||
| 1607 | |||
| 1610 | static bool init_psci_relay(void) | 1608 | static bool init_psci_relay(void) |
| 1611 | { | 1609 | { |
| 1612 | /* | 1610 | /* |
| @@ -1618,8 +1616,15 @@ static bool init_psci_relay(void) · 5 unmodified lines | |||
| 1618 | return false; | 1616 | return false; |
| 1619 | } | 1617 | } |
| 1620 | 1618 | ||
| 1621 | kvm_nvhe_sym(kvm_host_psci_version) = psci_ops.get_version(); | 1619 | kvm_host_psci_config.version = psci_ops.get_version(); |
| 1622 | kvm_nvhe_sym(kvm_host_psci_0_1_function_ids) = get_psci_0_1_function_ids(); | 1620 | |
| 1621 | if (kvm_host_psci_config.version == PSCI_VERSION(0, 1)) { | ||
| 1622 | kvm_host_psci_config.function_ids_0_1 = get_psci_0_1_function_ids(); | ||
| 1623 | init_psci_0_1_impl_state(kvm_host_psci_config, cpu_suspend); | ||
| 1624 | init_psci_0_1_impl_state(kvm_host_psci_config, cpu_on); | ||
| 1625 | init_psci_0_1_impl_state(kvm_host_psci_config, cpu_off); | ||
| 1626 | init_psci_0_1_impl_state(kvm_host_psci_config, migrate); | ||
| 1627 | } | ||
| 1623 | return true; | 1628 | return true; |
| 1624 | } | 1629 | } |
| 1625 | 1630 | ||
| @@ -59,4 +59,13 @@ static inline void __adjust_pc(struct kvm_vcpu *vcpu) · 58 unmodified lines | |||
| 59 | } | 59 | } |
| 60 | } | 60 | } |
| 61 | 61 | ||
| 62 | /* | ||
| 63 | * Skip an instruction while host sysregs are live. | ||
| 64 | * Assumes host is always 64-bit. | ||
| 65 | */ | ||
| 66 | static inline void kvm_skip_host_instr(void) | ||
| 67 | { | ||
| 68 | write_sysreg_el2(read_sysreg_el2(SYS_ELR) + 4, SYS_ELR); | ||
| 69 | } | ||
| 70 | |||
| 62 | #endif | 71 | #endif |
| @@ -47,6 +47,8 @@ __invalid: · 46 unmodified lines | |||
| 47 | b . | 47 | b . |
| 48 | 48 | ||
| 49 | /* | 49 | /* |
| 50 | * Only uses x0..x3 so as to not clobber callee-saved SMCCC registers. | ||
| 51 | * | ||
| 50 | * x0: SMCCC function ID | 52 | * x0: SMCCC function ID |
| 51 | * x1: struct kvm_nvhe_init_params PA | 53 | * x1: struct kvm_nvhe_init_params PA |
| 52 | */ | 54 | */ |
| @@ -70,9 +72,9 @@ __do_hyp_init: · 17 unmodified lines | |||
| 70 | eret | 72 | eret |
| 71 | 73 | ||
| 72 | 1: mov x0, x1 | 74 | 1: mov x0, x1 |
| 73 | mov x4, lr | 75 | mov x3, lr |
| 74 | bl ___kvm_hyp_init | 76 | bl ___kvm_hyp_init // Clobbers x0..x2 |
| 75 | mov lr, x4 | 77 | mov lr, x3 |
| 76 | 78 | ||
| 77 | /* Hello, World! */ | 79 | /* Hello, World! */ |
| 78 | mov x0, #SMCCC_RET_SUCCESS | 80 | mov x0, #SMCCC_RET_SUCCESS |
| @@ -82,8 +84,8 @@ SYM_CODE_END(__kvm_hyp_init) · 3 unmodified lines | |||
| 82 | /* | 84 | /* |
| 83 | * Initialize the hypervisor in EL2. | 85 | * Initialize the hypervisor in EL2. |
| 84 | * | 86 | * |
| 85 | * Only uses x0..x3 so as to not clobber callee-saved SMCCC registers | 87 | * Only uses x0..x2 so as to not clobber callee-saved SMCCC registers |
| 86 | * and leave x4 for the caller. | 88 | * and leave x3 for the caller. |
| 87 | * | 89 | * |
| 88 | * x0: struct kvm_nvhe_init_params PA | 90 | * x0: struct kvm_nvhe_init_params PA |
| 89 | */ | 91 | */ |
| @@ -112,9 +114,9 @@ alternative_else_nop_endif · 22 unmodified lines | |||
| 112 | /* | 114 | /* |
| 113 | * Set the PS bits in TCR_EL2. | 115 | * Set the PS bits in TCR_EL2. |
| 114 | */ | 116 | */ |
| 115 | ldr x1, [x0, #NVHE_INIT_TCR_EL2] | 117 | ldr x0, [x0, #NVHE_INIT_TCR_EL2] |
| 116 | tcr_compute_pa_size x1, #TCR_EL2_PS_SHIFT, x2, x3 | 118 | tcr_compute_pa_size x0, #TCR_EL2_PS_SHIFT, x1, x2 |
| 117 | msr tcr_el2, x1 | 119 | msr tcr_el2, x0 |
| 118 | 120 | ||
| 119 | isb | 121 | isb |
| 120 | 122 | ||
| @@ -193,7 +195,7 @@ SYM_CODE_START_LOCAL(__kvm_hyp_init_cpu) · 72 unmodified lines | |||
| 193 | 195 | ||
| 194 | /* Enable MMU, set vectors and stack. */ | 196 | /* Enable MMU, set vectors and stack. */ |
| 195 | mov x0, x28 | 197 | mov x0, x28 |
| 196 | bl ___kvm_hyp_init // Clobbers x0..x3 | 198 | bl ___kvm_hyp_init // Clobbers x0..x2 |
| 197 | 199 | ||
| 198 | /* Leave idmap. */ | 200 | /* Leave idmap. */ |
| 199 | mov x0, x29 | 201 | mov x0, x29 |
| @@ -157,11 +157,6 @@ static void default_host_smc_handler(struct kvm_cpu_context *host_ctxt) · 156 unmodified lines | |||
| 157 | __kvm_hyp_host_forward_smc(host_ctxt); | 157 | __kvm_hyp_host_forward_smc(host_ctxt); |
| 158 | } | 158 | } |
| 159 | 159 | ||
| 160 | static void skip_host_instruction(void) | ||
| 161 | { | ||
| 162 | write_sysreg_el2(read_sysreg_el2(SYS_ELR) + 4, SYS_ELR); | ||
| 163 | } | ||
| 164 | |||
| 165 | static void handle_host_smc(struct kvm_cpu_context *host_ctxt) | 160 | static void handle_host_smc(struct kvm_cpu_context *host_ctxt) |
| 166 | { | 161 | { |
| 167 | bool handled; | 162 | bool handled; |
| @@ -170,11 +165,8 @@ static void handle_host_smc(struct kvm_cpu_context *host_ctxt) · 2 unmodified lines | |||
| 170 | if (!handled) | 165 | if (!handled) |
| 171 | default_host_smc_handler(host_ctxt); | 166 | default_host_smc_handler(host_ctxt); |
| 172 | 167 | ||
| 173 | /* | 168 | /* SMC was trapped, move ELR past the current PC. */ |
| 174 | * Unlike HVC, the return address of an SMC is the instruction's PC. | 169 | kvm_skip_host_instr(); |
| 175 | * Move the return address past the instruction. | ||
| 176 | */ | ||
| 177 | skip_host_instruction(); | ||
| 178 | } | 170 | } |
| 179 | 171 | ||
| 180 | void handle_trap(struct kvm_cpu_context *host_ctxt) | 172 | void handle_trap(struct kvm_cpu_context *host_ctxt) |
| @@ -14,14 +14,14 @@ · 13 unmodified lines | |||
| 14 | * Other CPUs should not be allowed to boot because their features were | 14 | * Other CPUs should not be allowed to boot because their features were |
| 15 | * not checked against the finalized system capabilities. | 15 | * not checked against the finalized system capabilities. |
| 16 | */ | 16 | */ |
| 17 | u64 __ro_after_init __cpu_logical_map[NR_CPUS] = { [0 ... NR_CPUS-1] = INVALID_HWID }; | 17 | u64 __ro_after_init hyp_cpu_logical_map[NR_CPUS] = { [0 ... NR_CPUS-1] = INVALID_HWID }; |
| 18 | 18 | ||
| 19 | u64 cpu_logical_map(unsigned int cpu) | 19 | u64 cpu_logical_map(unsigned int cpu) |
| 20 | { | 20 | { |
| 21 | if (cpu >= ARRAY_SIZE(__cpu_logical_map)) | 21 | if (cpu >= ARRAY_SIZE(hyp_cpu_logical_map)) |
| 22 | hyp_panic(); | 22 | hyp_panic(); |
| 23 | 23 | ||
| 24 | return __cpu_logical_map[cpu]; | 24 | return hyp_cpu_logical_map[cpu]; |
| 25 | } | 25 | } |
| 26 | 26 | ||
| 27 | unsigned long __hyp_per_cpu_offset(unsigned int cpu) | 27 | unsigned long __hyp_per_cpu_offset(unsigned int cpu) |
| @@ -7,11 +7,8 @@ · 6 unmodified lines | |||
| 7 | #include <asm/kvm_asm.h> | 7 | #include <asm/kvm_asm.h> |
| 8 | #include <asm/kvm_hyp.h> | 8 | #include <asm/kvm_hyp.h> |
| 9 | #include <asm/kvm_mmu.h> | 9 | #include <asm/kvm_mmu.h> |
| 10 | #include <kvm/arm_hypercalls.h> | ||
| 11 | #include <linux/arm-smccc.h> | 10 | #include <linux/arm-smccc.h> |
| 12 | #include <linux/kvm_host.h> | 11 | #include <linux/kvm_host.h> |
| 13 | #include <linux/psci.h> | ||
| 14 | #include <kvm/arm_psci.h> | ||
| 15 | #include <uapi/linux/psci.h> | 12 | #include <uapi/linux/psci.h> |
| 16 | 13 | ||
| 17 | #include <nvhe/trap_handler.h> | 14 | #include <nvhe/trap_handler.h> |
| @@ -22,9 +19,8 @@ void kvm_hyp_cpu_resume(unsigned long r0); · 4 unmodified lines | |||
| 22 | void __noreturn __host_enter(struct kvm_cpu_context *host_ctxt); | 19 | void __noreturn __host_enter(struct kvm_cpu_context *host_ctxt); |
| 23 | 20 | ||
| 24 | /* Config options set by the host. */ | 21 | /* Config options set by the host. */ |
| 25 | __ro_after_init u32 kvm_host_psci_version; | 22 | struct kvm_host_psci_config __ro_after_init kvm_host_psci_config; |
| 26 | __ro_after_init struct psci_0_1_function_ids kvm_host_psci_0_1_function_ids; | 23 | s64 __ro_after_init hyp_physvirt_offset; |
| 27 | __ro_after_init s64 hyp_physvirt_offset; | ||
| 28 | 24 | ||
| 29 | #define __hyp_pa(x) ((phys_addr_t)((x)) + hyp_physvirt_offset) | 25 | #define __hyp_pa(x) ((phys_addr_t)((x)) + hyp_physvirt_offset) |
| 30 | 26 | ||
| @@ -47,19 +43,16 @@ struct psci_boot_args { · 16 unmodified lines | |||
| 47 | static DEFINE_PER_CPU(struct psci_boot_args, cpu_on_args) = PSCI_BOOT_ARGS_INIT; | 43 | static DEFINE_PER_CPU(struct psci_boot_args, cpu_on_args) = PSCI_BOOT_ARGS_INIT; |
| 48 | static DEFINE_PER_CPU(struct psci_boot_args, suspend_args) = PSCI_BOOT_ARGS_INIT; | 44 | static DEFINE_PER_CPU(struct psci_boot_args, suspend_args) = PSCI_BOOT_ARGS_INIT; |
| 49 | 45 | ||
| 50 | static u64 get_psci_func_id(struct kvm_cpu_context *host_ctxt) | 46 | #define is_psci_0_1(what, func_id) \ |
| 51 | { | 47 | (kvm_host_psci_config.psci_0_1_ ## what ## _implemented && \ |
| 52 | DECLARE_REG(u64, func_id, host_ctxt, 0); | 48 | (func_id) == kvm_host_psci_config.function_ids_0_1.what) |
| 53 | |||
| 54 | return func_id; | ||
| 55 | } | ||
| 56 | 49 | ||
| 57 | static bool is_psci_0_1_call(u64 func_id) | 50 | static bool is_psci_0_1_call(u64 func_id) |
| 58 | { | 51 | { |
| 59 | return (func_id == kvm_host_psci_0_1_function_ids.cpu_suspend) || | 52 | return (is_psci_0_1(cpu_suspend, func_id) || |
| 60 | (func_id == kvm_host_psci_0_1_function_ids.cpu_on) || | 53 | is_psci_0_1(cpu_on, func_id) || |
| 61 | (func_id == kvm_host_psci_0_1_function_ids.cpu_off) || | 54 | is_psci_0_1(cpu_off, func_id) || |
| 62 | (func_id == kvm_host_psci_0_1_function_ids.migrate); | 55 | is_psci_0_1(migrate, func_id)); |
| 63 | } | 56 | } |
| 64 | 57 | ||
| 65 | static bool is_psci_0_2_call(u64 func_id) | 58 | static bool is_psci_0_2_call(u64 func_id) |
| @@ -69,16 +62,6 @@ static bool is_psci_0_2_call(u64 func_id) · 3 unmodified lines | |||
| 69 | (PSCI_0_2_FN64(0) <= func_id && func_id <= PSCI_0_2_FN64(31)); | 62 | (PSCI_0_2_FN64(0) <= func_id && func_id <= PSCI_0_2_FN64(31)); |
| 70 | } | 63 | } |
| 71 | 64 | ||
| 72 | static bool is_psci_call(u64 func_id) | ||
| 73 | { | ||
| 74 | switch (kvm_host_psci_version) { | ||
| 75 | case PSCI_VERSION(0, 1): | ||
| 76 | return is_psci_0_1_call(func_id); | ||
| 77 | default: | ||
| 78 | return is_psci_0_2_call(func_id); | ||
| 79 | } | ||
| 80 | } | ||
| 81 | |||
| 82 | static unsigned long psci_call(unsigned long fn, unsigned long arg0, | 65 | static unsigned long psci_call(unsigned long fn, unsigned long arg0, |
| 83 | unsigned long arg1, unsigned long arg2) | 66 | unsigned long arg1, unsigned long arg2) |
| 84 | { | 67 | { |
| @@ -94,12 +77,6 @@ static unsigned long psci_forward(struct kvm_cpu_context *host_ctxt) · 9 unmodified lines | |||
| 94 | cpu_reg(host_ctxt, 2), cpu_reg(host_ctxt, 3)); | 77 | cpu_reg(host_ctxt, 2), cpu_reg(host_ctxt, 3)); |
| 95 | } | 78 | } |
| 96 | 79 | ||
| 97 | static __noreturn unsigned long psci_forward_noreturn(struct kvm_cpu_context *host_ctxt) | ||
| 98 | { | ||
| 99 | psci_forward(host_ctxt); | ||
| 100 | hyp_panic(); /* unreachable */ | ||
| 101 | } | ||
| 102 | |||
| 103 | static unsigned int find_cpu_id(u64 mpidr) | 80 | static unsigned int find_cpu_id(u64 mpidr) |
| 104 | { | 81 | { |
| 105 | unsigned int i; | 82 | unsigned int i; |
| @@ -248,15 +225,14 @@ asmlinkage void __noreturn kvm_host_psci_cpu_entry(bool is_cpu_on) · 142 unmodified lines | |||
| 248 | 225 | ||
| 249 | static unsigned long psci_0_1_handler(u64 func_id, struct kvm_cpu_context *host_ctxt) | 226 | static unsigned long psci_0_1_handler(u64 func_id, struct kvm_cpu_context *host_ctxt) |
| 250 | { | 227 | { |
| 251 | if ((func_id == kvm_host_psci_0_1_function_ids.cpu_off) || | 228 | if (is_psci_0_1(cpu_off, func_id) || is_psci_0_1(migrate, func_id)) |
| 252 | (func_id == kvm_host_psci_0_1_function_ids.migrate)) | ||
| 253 | return psci_forward(host_ctxt); | 229 | return psci_forward(host_ctxt); |
| 254 | else if (func_id == kvm_host_psci_0_1_function_ids.cpu_on) | 230 | if (is_psci_0_1(cpu_on, func_id)) |
| 255 | return psci_cpu_on(func_id, host_ctxt); | 231 | return psci_cpu_on(func_id, host_ctxt); |
| 256 | else if (func_id == kvm_host_psci_0_1_function_ids.cpu_suspend) | 232 | if (is_psci_0_1(cpu_suspend, func_id)) |
| 257 | return psci_cpu_suspend(func_id, host_ctxt); | 233 | return psci_cpu_suspend(func_id, host_ctxt); |
| 258 | else | 234 | |
| 259 | return PSCI_RET_NOT_SUPPORTED; | 235 | return PSCI_RET_NOT_SUPPORTED; |
| 260 | } | 236 | } |
| 261 | 237 | ||
| 262 | static unsigned long psci_0_2_handler(u64 func_id, struct kvm_cpu_context *host_ctxt) | 238 | static unsigned long psci_0_2_handler(u64 func_id, struct kvm_cpu_context *host_ctxt) |
| @@ -269,10 +245,13 @@ static unsigned long psci_0_2_handler(u64 func_id, struct kvm_cpu_context *host_ · 6 unmodified lines | |||
| 269 | case PSCI_0_2_FN_MIGRATE_INFO_TYPE: | 245 | case PSCI_0_2_FN_MIGRATE_INFO_TYPE: |
| 270 | case PSCI_0_2_FN64_MIGRATE_INFO_UP_CPU: | 246 | case PSCI_0_2_FN64_MIGRATE_INFO_UP_CPU: |
| 271 | return psci_forward(host_ctxt); | 247 | return psci_forward(host_ctxt); |
| 248 | /* | ||
| 249 | * SYSTEM_OFF/RESET should not return according to the spec. | ||
| 250 | * Allow it so as to stay robust to broken firmware. | ||
| 251 | */ | ||
| 272 | case PSCI_0_2_FN_SYSTEM_OFF: | 252 | case PSCI_0_2_FN_SYSTEM_OFF: |
| 273 | case PSCI_0_2_FN_SYSTEM_RESET: | 253 | case PSCI_0_2_FN_SYSTEM_RESET: |
| 274 | psci_forward_noreturn(host_ctxt); | 254 | return psci_forward(host_ctxt); |
| 275 | unreachable(); | ||
| 276 | case PSCI_0_2_FN64_CPU_SUSPEND: | 255 | case PSCI_0_2_FN64_CPU_SUSPEND: |
| 277 | return psci_cpu_suspend(func_id, host_ctxt); | 256 | return psci_cpu_suspend(func_id, host_ctxt); |
| 278 | case PSCI_0_2_FN64_CPU_ON: | 257 | case PSCI_0_2_FN64_CPU_ON: |
| @@ -298,20 +277,23 @@ static unsigned long psci_1_0_handler(u64 func_id, struct kvm_cpu_context *host_ · 19 unmodified lines | |||
| 298 | 277 | ||
| 299 | bool kvm_host_psci_handler(struct kvm_cpu_context *host_ctxt) | 278 | bool kvm_host_psci_handler(struct kvm_cpu_context *host_ctxt) |
| 300 | { | 279 | { |
| 301 | u64 func_id = get_psci_func_id(host_ctxt); | 280 | DECLARE_REG(u64, func_id, host_ctxt, 0); |
| 302 | unsigned long ret; | 281 | unsigned long ret; |
| 303 | 282 | ||
| 304 | if (!is_psci_call(func_id)) | 283 | switch (kvm_host_psci_config.version) { |
| 305 | return false; | ||
| 306 | |||
| 307 | switch (kvm_host_psci_version) { | ||
| 308 | case PSCI_VERSION(0, 1): | 284 | case PSCI_VERSION(0, 1): |
| 285 | if (!is_psci_0_1_call(func_id)) | ||
| 286 | return false; | ||
| 309 | ret = psci_0_1_handler(func_id, host_ctxt); | 287 | ret = psci_0_1_handler(func_id, host_ctxt); |
| 310 | break; | 288 | break; |
| 311 | case PSCI_VERSION(0, 2): | 289 | case PSCI_VERSION(0, 2): |
| 290 | if (!is_psci_0_2_call(func_id)) | ||
| 291 | return false; | ||
| 312 | ret = psci_0_2_handler(func_id, host_ctxt); | 292 | ret = psci_0_2_handler(func_id, host_ctxt); |
| 313 | break; | 293 | break; |
| 314 | default: | 294 | default: |
| 295 | if (!is_psci_0_2_call(func_id)) | ||
| 296 | return false; | ||
| 315 | ret = psci_1_0_handler(func_id, host_ctxt); | 297 | ret = psci_1_0_handler(func_id, host_ctxt); |
| 316 | break; | 298 | break; |
| 317 | } | 299 | } |
| @@ -788,7 +788,7 @@ u64 kvm_pmu_get_pmceid(struct kvm_vcpu *vcpu, bool pmceid1) · 787 unmodified lines | |||
| 788 | { | 788 | { |
| 789 | unsigned long *bmap = vcpu->kvm->arch.pmu_filter; | 789 | unsigned long *bmap = vcpu->kvm->arch.pmu_filter; |
| 790 | u64 val, mask = 0; | 790 | u64 val, mask = 0; |
| 791 | int base, i; | 791 | int base, i, nr_events; |
| 792 | 792 | ||
| 793 | if (!pmceid1) { | 793 | if (!pmceid1) { |
| 794 | val = read_sysreg(pmceid0_el0); | 794 | val = read_sysreg(pmceid0_el0); |
| @@ -801,13 +801,17 @@ u64 kvm_pmu_get_pmceid(struct kvm_vcpu *vcpu, bool pmceid1) · 6 unmodified lines | |||
| 801 | if (!bmap) | 801 | if (!bmap) |
| 802 | return val; | 802 | return val; |
| 803 | 803 | ||
| 804 | nr_events = kvm_pmu_event_mask(vcpu->kvm) + 1; | ||
| 805 | |||
| 804 | for (i = 0; i < 32; i += 8) { | 806 | for (i = 0; i < 32; i += 8) { |
| 805 | u64 byte; | 807 | u64 byte; |
| 806 | 808 | ||
| 807 | byte = bitmap_get_value8(bmap, base + i); | 809 | byte = bitmap_get_value8(bmap, base + i); |
| 808 | mask |= byte << i; | 810 | mask |= byte << i; |
| 809 | byte = bitmap_get_value8(bmap, 0x4000 + base + i); | 811 | if (nr_events >= (0x4000 + base + 32)) { |
| 810 | mask |= byte << (32 + i); | 812 | byte = bitmap_get_value8(bmap, 0x4000 + base + i); |
| 813 | mask |= byte << (32 + i); | ||
| 814 | } | ||
| 811 | } | 815 | } |
| 812 | 816 | ||
| 813 | return val & mask; | 817 | return val & mask; |
| @@ -850,8 +854,6 @@ int kvm_arm_pmu_v3_enable(struct kvm_vcpu *vcpu) · 36 unmodified lines | |||
| 850 | return -EINVAL; | 854 | return -EINVAL; |
| 851 | } | 855 | } |
| 852 | 856 | ||
| 853 | kvm_pmu_vcpu_reset(vcpu); | ||
| 854 | |||
| 855 | return 0; | 857 | return 0; |
| 856 | } | 858 | } |
| 857 | 859 | ||
| @@ -43,6 +43,10 @@ · 42 unmodified lines | |||
| 43 | * 64bit interface. | 43 | * 64bit interface. |
| 44 | */ | 44 | */ |
| 45 | 45 | ||
| 46 | #define reg_to_encoding(x) \ | ||
| 47 | sys_reg((u32)(x)->Op0, (u32)(x)->Op1, \ | ||
| 48 | (u32)(x)->CRn, (u32)(x)->CRm, (u32)(x)->Op2) | ||
| 49 | |||
| 46 | static bool read_from_write_only(struct kvm_vcpu *vcpu, | 50 | static bool read_from_write_only(struct kvm_vcpu *vcpu, |
| 47 | struct sys_reg_params *params, | 51 | struct sys_reg_params *params, |
| 48 | const struct sys_reg_desc *r) | 52 | const struct sys_reg_desc *r) |
| @@ -273,8 +277,7 @@ static bool trap_loregion(struct kvm_vcpu *vcpu, · 224 unmodified lines | |||
| 273 | const struct sys_reg_desc *r) | 277 | const struct sys_reg_desc *r) |
| 274 | { | 278 | { |
| 275 | u64 val = read_sanitised_ftr_reg(SYS_ID_AA64MMFR1_EL1); | 279 | u64 val = read_sanitised_ftr_reg(SYS_ID_AA64MMFR1_EL1); |
| 276 | u32 sr = sys_reg((u32)r->Op0, (u32)r->Op1, | 280 | u32 sr = reg_to_encoding(r); |
| 277 | (u32)r->CRn, (u32)r->CRm, (u32)r->Op2); | ||
| 278 | 281 | ||
| 279 | if (!(val & (0xfUL << ID_AA64MMFR1_LOR_SHIFT))) { | 282 | if (!(val & (0xfUL << ID_AA64MMFR1_LOR_SHIFT))) { |
| 280 | kvm_inject_undefined(vcpu); | 283 | kvm_inject_undefined(vcpu); |
| @@ -590,10 +593,23 @@ static void reset_mpidr(struct kvm_vcpu *vcpu, const struct sys_reg_desc *r) · 309 unmodified lines | |||
| 590 | vcpu_write_sys_reg(vcpu, (1ULL << 31) | mpidr, MPIDR_EL1); | 593 | vcpu_write_sys_reg(vcpu, (1ULL << 31) | mpidr, MPIDR_EL1); |
| 591 | } | 594 | } |
| 592 | 595 | ||
| 596 | static unsigned int pmu_visibility(const struct kvm_vcpu *vcpu, | ||
| 597 | const struct sys_reg_desc *r) | ||
| 598 | { | ||
| 599 | if (kvm_vcpu_has_pmu(vcpu)) | ||
| 600 | return 0; | ||
| 601 | |||
| 602 | return REG_HIDDEN; | ||
| 603 | } | ||
| 604 | |||
| 593 | static void reset_pmcr(struct kvm_vcpu *vcpu, const struct sys_reg_desc *r) | 605 | static void reset_pmcr(struct kvm_vcpu *vcpu, const struct sys_reg_desc *r) |
| 594 | { | 606 | { |
| 595 | u64 pmcr, val; | 607 | u64 pmcr, val; |
| 596 | 608 | ||
| 609 | /* No PMU available, PMCR_EL0 may UNDEF... */ | ||
| 610 | if (!kvm_arm_support_pmu_v3()) | ||
| 611 | return; | ||
| 612 | |||
| 597 | pmcr = read_sysreg(pmcr_el0); | 613 | pmcr = read_sysreg(pmcr_el0); |
| 598 | /* | 614 | /* |
| 599 | * Writable bits of PMCR_EL0 (ARMV8_PMU_PMCR_MASK) are reset to UNKNOWN | 615 | * Writable bits of PMCR_EL0 (ARMV8_PMU_PMCR_MASK) are reset to UNKNOWN |
| @@ -609,9 +625,8 @@ static void reset_pmcr(struct kvm_vcpu *vcpu, const struct sys_reg_desc *r) · 9 unmodified lines | |||
| 609 | static bool check_pmu_access_disabled(struct kvm_vcpu *vcpu, u64 flags) | 625 | static bool check_pmu_access_disabled(struct kvm_vcpu *vcpu, u64 flags) |
| 610 | { | 626 | { |
| 611 | u64 reg = __vcpu_sys_reg(vcpu, PMUSERENR_EL0); | 627 | u64 reg = __vcpu_sys_reg(vcpu, PMUSERENR_EL0); |
| 612 | bool enabled = kvm_vcpu_has_pmu(vcpu); | 628 | bool enabled = (reg & flags) || vcpu_mode_priv(vcpu); |
| 613 | 629 | ||
| 614 | enabled &= (reg & flags) || vcpu_mode_priv(vcpu); | ||
| 615 | if (!enabled) | 630 | if (!enabled) |
| 616 | kvm_inject_undefined(vcpu); | 631 | kvm_inject_undefined(vcpu); |
| 617 | 632 | ||
| @@ -896,11 +911,6 @@ static bool access_pmswinc(struct kvm_vcpu *vcpu, struct sys_reg_params *p, · 278 unmodified lines | |||
| 896 | static bool access_pmuserenr(struct kvm_vcpu *vcpu, struct sys_reg_params *p, | 911 | static bool access_pmuserenr(struct kvm_vcpu *vcpu, struct sys_reg_params *p, |
| 897 | const struct sys_reg_desc *r) | 912 | const struct sys_reg_desc *r) |
| 898 | { | 913 | { |
| 899 | if (!kvm_vcpu_has_pmu(vcpu)) { | ||
| 900 | kvm_inject_undefined(vcpu); | ||
| 901 | return false; | ||
| 902 | } | ||
| 903 | |||
| 904 | if (p->is_write) { | 914 | if (p->is_write) { |
| 905 | if (!vcpu_mode_priv(vcpu)) { | 915 | if (!vcpu_mode_priv(vcpu)) { |
| 906 | kvm_inject_undefined(vcpu); | 916 | kvm_inject_undefined(vcpu); |
| @@ -917,10 +927,6 @@ static bool access_pmuserenr(struct kvm_vcpu *vcpu, struct sys_reg_params *p, · 10 unmodified lines | |||
| 917 | return true; | 927 | return true; |
| 918 | } | 928 | } |
| 919 | 929 | ||
| 920 | #define reg_to_encoding(x) \ | ||
| 921 | sys_reg((u32)(x)->Op0, (u32)(x)->Op1, \ | ||
| 922 | (u32)(x)->CRn, (u32)(x)->CRm, (u32)(x)->Op2); | ||
| 923 | |||
| 924 | /* Silly macro to expand the DBG{BCR,BVR,WVR,WCR}n_EL1 registers in one go */ | 930 | /* Silly macro to expand the DBG{BCR,BVR,WVR,WCR}n_EL1 registers in one go */ |
| 925 | #define DBG_BCR_BVR_WCR_WVR_EL1(n) \ | 931 | #define DBG_BCR_BVR_WCR_WVR_EL1(n) \ |
| 926 | { SYS_DESC(SYS_DBGBVRn_EL1(n)), \ | 932 | { SYS_DESC(SYS_DBGBVRn_EL1(n)), \ |
| @@ -932,15 +938,18 @@ static bool access_pmuserenr(struct kvm_vcpu *vcpu, struct sys_reg_params *p, · 5 unmodified lines | |||
| 932 | { SYS_DESC(SYS_DBGWCRn_EL1(n)), \ | 938 | { SYS_DESC(SYS_DBGWCRn_EL1(n)), \ |
| 933 | trap_wcr, reset_wcr, 0, 0, get_wcr, set_wcr } | 939 | trap_wcr, reset_wcr, 0, 0, get_wcr, set_wcr } |
| 934 | 940 | ||
| 941 | #define PMU_SYS_REG(r) \ | ||
| 942 | SYS_DESC(r), .reset = reset_unknown, .visibility = pmu_visibility | ||
| 943 | |||
| 935 | /* Macro to expand the PMEVCNTRn_EL0 register */ | 944 | /* Macro to expand the PMEVCNTRn_EL0 register */ |
| 936 | #define PMU_PMEVCNTR_EL0(n) \ | 945 | #define PMU_PMEVCNTR_EL0(n) \ |
| 937 | { SYS_DESC(SYS_PMEVCNTRn_EL0(n)), \ | 946 | { PMU_SYS_REG(SYS_PMEVCNTRn_EL0(n)), \ |
| 938 | access_pmu_evcntr, reset_unknown, (PMEVCNTR0_EL0 + n), } | 947 | .access = access_pmu_evcntr, .reg = (PMEVCNTR0_EL0 + n), } |
| 939 | 948 | ||
| 940 | /* Macro to expand the PMEVTYPERn_EL0 register */ | 949 | /* Macro to expand the PMEVTYPERn_EL0 register */ |
| 941 | #define PMU_PMEVTYPER_EL0(n) \ | 950 | #define PMU_PMEVTYPER_EL0(n) \ |
| 942 | { SYS_DESC(SYS_PMEVTYPERn_EL0(n)), \ | 951 | { PMU_SYS_REG(SYS_PMEVTYPERn_EL0(n)), \ |
| 943 | access_pmu_evtyper, reset_unknown, (PMEVTYPER0_EL0 + n), } | 952 | .access = access_pmu_evtyper, .reg = (PMEVTYPER0_EL0 + n), } |
| 944 | 953 | ||
| 945 | static bool undef_access(struct kvm_vcpu *vcpu, struct sys_reg_params *p, | 954 | static bool undef_access(struct kvm_vcpu *vcpu, struct sys_reg_params *p, |
| 946 | const struct sys_reg_desc *r) | 955 | const struct sys_reg_desc *r) |
| @@ -1016,8 +1025,7 @@ static bool access_arch_timer(struct kvm_vcpu *vcpu, · 69 unmodified lines | |||
| 1016 | static u64 read_id_reg(const struct kvm_vcpu *vcpu, | 1025 | static u64 read_id_reg(const struct kvm_vcpu *vcpu, |
| 1017 | struct sys_reg_desc const *r, bool raz) | 1026 | struct sys_reg_desc const *r, bool raz) |
| 1018 | { | 1027 | { |
| 1019 | u32 id = sys_reg((u32)r->Op0, (u32)r->Op1, | 1028 | u32 id = reg_to_encoding(r); |
| 1020 | (u32)r->CRn, (u32)r->CRm, (u32)r->Op2); | ||
| 1021 | u64 val = raz ? 0 : read_sanitised_ftr_reg(id); | 1029 | u64 val = raz ? 0 : read_sanitised_ftr_reg(id); |
| 1022 | 1030 | ||
| 1023 | if (id == SYS_ID_AA64PFR0_EL1) { | 1031 | if (id == SYS_ID_AA64PFR0_EL1) { |
| @@ -1058,8 +1066,7 @@ static u64 read_id_reg(const struct kvm_vcpu *vcpu, · 34 unmodified lines | |||
| 1058 | static unsigned int id_visibility(const struct kvm_vcpu *vcpu, | 1066 | static unsigned int id_visibility(const struct kvm_vcpu *vcpu, |
| 1059 | const struct sys_reg_desc *r) | 1067 | const struct sys_reg_desc *r) |
| 1060 | { | 1068 | { |
| 1061 | u32 id = sys_reg((u32)r->Op0, (u32)r->Op1, | 1069 | u32 id = reg_to_encoding(r); |
| 1062 | (u32)r->CRn, (u32)r->CRm, (u32)r->Op2); | ||
| 1063 | 1070 | ||
| 1064 | switch (id) { | 1071 | switch (id) { |
| 1065 | case SYS_ID_AA64ZFR0_EL1: | 1072 | case SYS_ID_AA64ZFR0_EL1: |
| @@ -1482,8 +1489,10 @@ static const struct sys_reg_desc sys_reg_descs[] = { · 416 unmodified lines | |||
| 1482 | { SYS_DESC(SYS_FAR_EL1), access_vm_reg, reset_unknown, FAR_EL1 }, | 1489 | { SYS_DESC(SYS_FAR_EL1), access_vm_reg, reset_unknown, FAR_EL1 }, |
| 1483 | { SYS_DESC(SYS_PAR_EL1), NULL, reset_unknown, PAR_EL1 }, | 1490 | { SYS_DESC(SYS_PAR_EL1), NULL, reset_unknown, PAR_EL1 }, |
| 1484 | 1491 | ||
| 1485 | { SYS_DESC(SYS_PMINTENSET_EL1), access_pminten, reset_unknown, PMINTENSET_EL1 }, | 1492 | { PMU_SYS_REG(SYS_PMINTENSET_EL1), |
| 1486 | { SYS_DESC(SYS_PMINTENCLR_EL1), access_pminten, reset_unknown, PMINTENSET_EL1 }, | 1493 | .access = access_pminten, .reg = PMINTENSET_EL1 }, |
| 1494 | { PMU_SYS_REG(SYS_PMINTENCLR_EL1), | ||
| 1495 | .access = access_pminten, .reg = PMINTENSET_EL1 }, | ||
| 1487 | 1496 | ||
| 1488 | { SYS_DESC(SYS_MAIR_EL1), access_vm_reg, reset_unknown, MAIR_EL1 }, | 1497 | { SYS_DESC(SYS_MAIR_EL1), access_vm_reg, reset_unknown, MAIR_EL1 }, |
| 1489 | { SYS_DESC(SYS_AMAIR_EL1), access_vm_reg, reset_amair_el1, AMAIR_EL1 }, | 1498 | { SYS_DESC(SYS_AMAIR_EL1), access_vm_reg, reset_amair_el1, AMAIR_EL1 }, |
| @@ -1522,23 +1531,36 @@ static const struct sys_reg_desc sys_reg_descs[] = { · 32 unmodified lines | |||
| 1522 | { SYS_DESC(SYS_CSSELR_EL1), access_csselr, reset_unknown, CSSELR_EL1 }, | 1531 | { SYS_DESC(SYS_CSSELR_EL1), access_csselr, reset_unknown, CSSELR_EL1 }, |
| 1523 | { SYS_DESC(SYS_CTR_EL0), access_ctr }, | 1532 | { SYS_DESC(SYS_CTR_EL0), access_ctr }, |
| 1524 | 1533 | ||
| 1525 | { SYS_DESC(SYS_PMCR_EL0), access_pmcr, reset_pmcr, PMCR_EL0 }, | 1534 | { PMU_SYS_REG(SYS_PMCR_EL0), .access = access_pmcr, |
| 1526 | { SYS_DESC(SYS_PMCNTENSET_EL0), access_pmcnten, reset_unknown, PMCNTENSET_EL0 }, | 1535 | .reset = reset_pmcr, .reg = PMCR_EL0 }, |
| 1527 | { SYS_DESC(SYS_PMCNTENCLR_EL0), access_pmcnten, reset_unknown, PMCNTENSET_EL0 }, | 1536 | { PMU_SYS_REG(SYS_PMCNTENSET_EL0), |
| 1528 | { SYS_DESC(SYS_PMOVSCLR_EL0), access_pmovs, reset_unknown, PMOVSSET_EL0 }, | 1537 | .access = access_pmcnten, .reg = PMCNTENSET_EL0 }, |
| 1529 | { SYS_DESC(SYS_PMSWINC_EL0), access_pmswinc, reset_unknown, PMSWINC_EL0 }, | 1538 | { PMU_SYS_REG(SYS_PMCNTENCLR_EL0), |
| 1530 | { SYS_DESC(SYS_PMSELR_EL0), access_pmselr, reset_unknown, PMSELR_EL0 }, | 1539 | .access = access_pmcnten, .reg = PMCNTENSET_EL0 }, |
| 1531 | { SYS_DESC(SYS_PMCEID0_EL0), access_pmceid }, | 1540 | { PMU_SYS_REG(SYS_PMOVSCLR_EL0), |
| 1532 | { SYS_DESC(SYS_PMCEID1_EL0), access_pmceid }, | 1541 | .access = access_pmovs, .reg = PMOVSSET_EL0 }, |
| 1533 | { SYS_DESC(SYS_PMCCNTR_EL0), access_pmu_evcntr, reset_unknown, PMCCNTR_EL0 }, | 1542 | { PMU_SYS_REG(SYS_PMSWINC_EL0), |
| 1534 | { SYS_DESC(SYS_PMXEVTYPER_EL0), access_pmu_evtyper }, | 1543 | .access = access_pmswinc, .reg = PMSWINC_EL0 }, |
| 1535 | { SYS_DESC(SYS_PMXEVCNTR_EL0), access_pmu_evcntr }, | 1544 | { PMU_SYS_REG(SYS_PMSELR_EL0), |
| 1545 | .access = access_pmselr, .reg = PMSELR_EL0 }, | ||
| 1546 | { PMU_SYS_REG(SYS_PMCEID0_EL0), | ||
| 1547 | .access = access_pmceid, .reset = NULL }, | ||
| 1548 | { PMU_SYS_REG(SYS_PMCEID1_EL0), | ||
| 1549 | .access = access_pmceid, .reset = NULL }, | ||
| 1550 | { PMU_SYS_REG(SYS_PMCCNTR_EL0), | ||
| 1551 | .access = access_pmu_evcntr, .reg = PMCCNTR_EL0 }, | ||
| 1552 | { PMU_SYS_REG(SYS_PMXEVTYPER_EL0), | ||
| 1553 | .access = access_pmu_evtyper, .reset = NULL }, | ||
| 1554 | { PMU_SYS_REG(SYS_PMXEVCNTR_EL0), | ||
| 1555 | .access = access_pmu_evcntr, .reset = NULL }, | ||
| 1536 | /* | 1556 | /* |
| 1537 | * PMUSERENR_EL0 resets as unknown in 64bit mode while it resets as zero | 1557 | * PMUSERENR_EL0 resets as unknown in 64bit mode while it resets as zero |
| 1538 | * in 32bit mode. Here we choose to reset it as zero for consistency. | 1558 | * in 32bit mode. Here we choose to reset it as zero for consistency. |
| 1539 | */ | 1559 | */ |
| 1540 | { SYS_DESC(SYS_PMUSERENR_EL0), access_pmuserenr, reset_val, PMUSERENR_EL0, 0 }, | 1560 | { PMU_SYS_REG(SYS_PMUSERENR_EL0), .access = access_pmuserenr, |
| 1541 | { SYS_DESC(SYS_PMOVSSET_EL0), access_pmovs, reset_unknown, PMOVSSET_EL0 }, | 1561 | .reset = reset_val, .reg = PMUSERENR_EL0, .val = 0 }, |
| 1562 | { PMU_SYS_REG(SYS_PMOVSSET_EL0), | ||
| 1563 | .access = access_pmovs, .reg = PMOVSSET_EL0 }, | ||
| 1542 | 1564 | ||
| 1543 | { SYS_DESC(SYS_TPIDR_EL0), NULL, reset_unknown, TPIDR_EL0 }, | 1565 | { SYS_DESC(SYS_TPIDR_EL0), NULL, reset_unknown, TPIDR_EL0 }, |
| 1544 | { SYS_DESC(SYS_TPIDRRO_EL0), NULL, reset_unknown, TPIDRRO_EL0 }, | 1566 | { SYS_DESC(SYS_TPIDRRO_EL0), NULL, reset_unknown, TPIDRRO_EL0 }, |
| @@ -1690,7 +1712,8 @@ static const struct sys_reg_desc sys_reg_descs[] = { · 145 unmodified lines | |||
| 1690 | * PMCCFILTR_EL0 resets as unknown in 64bit mode while it resets as zero | 1712 | * PMCCFILTR_EL0 resets as unknown in 64bit mode while it resets as zero |
| 1691 | * in 32bit mode. Here we choose to reset it as zero for consistency. | 1713 | * in 32bit mode. Here we choose to reset it as zero for consistency. |
| 1692 | */ | 1714 | */ |
| 1693 | { SYS_DESC(SYS_PMCCFILTR_EL0), access_pmu_evtyper, reset_val, PMCCFILTR_EL0, 0 }, | 1715 | { PMU_SYS_REG(SYS_PMCCFILTR_EL0), .access = access_pmu_evtyper, |
| 1716 | .reset = reset_val, .reg = PMCCFILTR_EL0, .val = 0 }, | ||
| 1694 | 1717 | ||
| 1695 | { SYS_DESC(SYS_DACR32_EL2), NULL, reset_unknown, DACR32_EL2 }, | 1718 | { SYS_DESC(SYS_DACR32_EL2), NULL, reset_unknown, DACR32_EL2 }, |
| 1696 | { SYS_DESC(SYS_IFSR32_EL2), NULL, reset_unknown, IFSR32_EL2 }, | 1719 | { SYS_DESC(SYS_IFSR32_EL2), NULL, reset_unknown, IFSR32_EL2 }, |
| @@ -34,17 +34,16 @@ static u64 __early_kern_hyp_va(u64 addr) · 33 unmodified lines | |||
| 34 | } | 34 | } |
| 35 | 35 | ||
| 36 | /* | 36 | /* |
| 37 | * Store a hyp VA <-> PA offset into a hyp-owned variable. | 37 | * Store a hyp VA <-> PA offset into a EL2-owned variable. |
| 38 | */ | 38 | */ |
| 39 | static void init_hyp_physvirt_offset(void) | 39 | static void init_hyp_physvirt_offset(void) |
| 40 | { | 40 | { |
| 41 | extern s64 kvm_nvhe_sym(hyp_physvirt_offset); | ||
| 42 | u64 kern_va, hyp_va; | 41 | u64 kern_va, hyp_va; |
| 43 | 42 | ||
| 44 | /* Compute the offset from the hyp VA and PA of a random symbol. */ | 43 | /* Compute the offset from the hyp VA and PA of a random symbol. */ |
| 45 | kern_va = (u64)kvm_ksym_ref(__hyp_text_start); | 44 | kern_va = (u64)lm_alias(__hyp_text_start); |
| 46 | hyp_va = __early_kern_hyp_va(kern_va); | 45 | hyp_va = __early_kern_hyp_va(kern_va); |
| 47 | CHOOSE_NVHE_SYM(hyp_physvirt_offset) = (s64)__pa(kern_va) - (s64)hyp_va; | 46 | hyp_physvirt_offset = (s64)__pa(kern_va) - (s64)hyp_va; |
| 48 | } | 47 | } |
| 49 | 48 | ||
| 50 | /* | 49 | /* |
| @@ -419,7 +419,8 @@ int vgic_lazy_init(struct kvm *kvm) · 418 unmodified lines | |||
| 419 | * Map the MMIO regions depending on the VGIC model exposed to the guest | 419 | * Map the MMIO regions depending on the VGIC model exposed to the guest |
| 420 | * called on the first VCPU run. | 420 | * called on the first VCPU run. |
| 421 | * Also map the virtual CPU interface into the VM. | 421 | * Also map the virtual CPU interface into the VM. |
| 422 | * v2/v3 derivatives call vgic_init if not already done. | 422 | * v2 calls vgic_init() if not already done. |
| 423 | * v3 and derivatives return an error if the VGIC is not initialized. | ||
| 423 | * vgic_ready() returns true if this function has succeeded. | 424 | * vgic_ready() returns true if this function has succeeded. |
| 424 | * @kvm: kvm struct pointer | 425 | * @kvm: kvm struct pointer |
| 425 | */ | 426 | */ |
| @@ -428,7 +429,13 @@ int kvm_vgic_map_resources(struct kvm *kvm) · 2 unmodified lines | |||
| 428 | struct vgic_dist *dist = &kvm->arch.vgic; | 429 | struct vgic_dist *dist = &kvm->arch.vgic; |
| 429 | int ret = 0; | 430 | int ret = 0; |
| 430 | 431 | ||
| 432 | if (likely(vgic_ready(kvm))) | ||
| 433 | return 0; | ||
| 434 | |||
| 431 | mutex_lock(&kvm->lock); | 435 | mutex_lock(&kvm->lock); |
| 436 | if (vgic_ready(kvm)) | ||
| 437 | goto out; | ||
| 438 | |||
| 432 | if (!irqchip_in_kernel(kvm)) | 439 | if (!irqchip_in_kernel(kvm)) |
| 433 | goto out; | 440 | goto out; |
| 434 | 441 | ||
| @@ -439,6 +446,8 @@ int kvm_vgic_map_resources(struct kvm *kvm) · 4 unmodified lines | |||
| 439 | 446 | ||
| 440 | if (ret) | 447 | if (ret) |
| 441 | __kvm_vgic_destroy(kvm); | 448 | __kvm_vgic_destroy(kvm); |
| 449 | else | ||
| 450 | dist->ready = true; | ||
| 442 | 451 | ||
| 443 | out: | 452 | out: |
| 444 | mutex_unlock(&kvm->lock); | 453 | mutex_unlock(&kvm->lock); |
| @@ -306,20 +306,15 @@ int vgic_v2_map_resources(struct kvm *kvm) · 305 unmodified lines | |||
| 306 | struct vgic_dist *dist = &kvm->arch.vgic; | 306 | struct vgic_dist *dist = &kvm->arch.vgic; |
| 307 | int ret = 0; | 307 | int ret = 0; |
| 308 | 308 | ||
| 309 | if (vgic_ready(kvm)) | ||
| 310 | goto out; | ||
| 311 | |||
| 312 | if (IS_VGIC_ADDR_UNDEF(dist->vgic_dist_base) || | 309 | if (IS_VGIC_ADDR_UNDEF(dist->vgic_dist_base) || |
| 313 | IS_VGIC_ADDR_UNDEF(dist->vgic_cpu_base)) { | 310 | IS_VGIC_ADDR_UNDEF(dist->vgic_cpu_base)) { |
| 314 | kvm_err("Need to set vgic cpu and dist addresses first\n"); | 311 | kvm_err("Need to set vgic cpu and dist addresses first\n"); |
| 315 | ret = -ENXIO; | 312 | return -ENXIO; |
| 316 | goto out; | ||
| 317 | } | 313 | } |
| 318 | 314 | ||
| 319 | if (!vgic_v2_check_base(dist->vgic_dist_base, dist->vgic_cpu_base)) { | 315 | if (!vgic_v2_check_base(dist->vgic_dist_base, dist->vgic_cpu_base)) { |
| 320 | kvm_err("VGIC CPU and dist frames overlap\n"); | 316 | kvm_err("VGIC CPU and dist frames overlap\n"); |
| 321 | ret = -EINVAL; | 317 | return -EINVAL; |
| 322 | goto out; | ||
| 323 | } | 318 | } |
| 324 | 319 | ||
| 325 | /* | 320 | /* |
| @@ -329,13 +324,13 @@ int vgic_v2_map_resources(struct kvm *kvm) · 3 unmodified lines | |||
| 329 | ret = vgic_init(kvm); | 324 | ret = vgic_init(kvm); |
| 330 | if (ret) { | 325 | if (ret) { |
| 331 | kvm_err("Unable to initialize VGIC dynamic data structures\n"); | 326 | kvm_err("Unable to initialize VGIC dynamic data structures\n"); |
| 332 | goto out; | 327 | return ret; |
| 333 | } | 328 | } |
| 334 | 329 | ||
| 335 | ret = vgic_register_dist_iodev(kvm, dist->vgic_dist_base, VGIC_V2); | 330 | ret = vgic_register_dist_iodev(kvm, dist->vgic_dist_base, VGIC_V2); |
| 336 | if (ret) { | 331 | if (ret) { |
| 337 | kvm_err("Unable to register VGIC MMIO regions\n"); | 332 | kvm_err("Unable to register VGIC MMIO regions\n"); |
| 338 | goto out; | 333 | return ret; |
| 339 | } | 334 | } |
| 340 | 335 | ||
| 341 | if (!static_branch_unlikely(&vgic_v2_cpuif_trap)) { | 336 | if (!static_branch_unlikely(&vgic_v2_cpuif_trap)) { |
| @@ -344,14 +339,11 @@ int vgic_v2_map_resources(struct kvm *kvm) · 2 unmodified lines | |||
| 344 | KVM_VGIC_V2_CPU_SIZE, true); | 339 | KVM_VGIC_V2_CPU_SIZE, true); |
| 345 | if (ret) { | 340 | if (ret) { |
| 346 | kvm_err("Unable to remap VGIC CPU to VCPU\n"); | 341 | kvm_err("Unable to remap VGIC CPU to VCPU\n"); |
| 347 | goto out; | 342 | return ret; |
| 348 | } | 343 | } |
| 349 | } | 344 | } |
| 350 | 345 | ||
| 351 | dist->ready = true; | 346 | return 0; |
| 352 | |||
| 353 | out: | ||
| 354 | return ret; | ||
| 355 | } | 347 | } |
| 356 | 348 | ||
| 357 | DEFINE_STATIC_KEY_FALSE(vgic_v2_cpuif_trap); | 349 | DEFINE_STATIC_KEY_FALSE(vgic_v2_cpuif_trap); |
| @@ -500,29 +500,23 @@ int vgic_v3_map_resources(struct kvm *kvm) · 499 unmodified lines | |||
| 500 | int ret = 0; | 500 | int ret = 0; |
| 501 | int c; | 501 | int c; |
| 502 | 502 | ||
| 503 | if (vgic_ready(kvm)) | ||
| 504 | goto out; | ||
| 505 | |||
| 506 | kvm_for_each_vcpu(c, vcpu, kvm) { | 503 | kvm_for_each_vcpu(c, vcpu, kvm) { |
| 507 | struct vgic_cpu *vgic_cpu = &vcpu->arch.vgic_cpu; | 504 | struct vgic_cpu *vgic_cpu = &vcpu->arch.vgic_cpu; |
| 508 | 505 | ||
| 509 | if (IS_VGIC_ADDR_UNDEF(vgic_cpu->rd_iodev.base_addr)) { | 506 | if (IS_VGIC_ADDR_UNDEF(vgic_cpu->rd_iodev.base_addr)) { |
| 510 | kvm_debug("vcpu %d redistributor base not set\n", c); | 507 | kvm_debug("vcpu %d redistributor base not set\n", c); |
| 511 | ret = -ENXIO; | 508 | return -ENXIO; |
| 512 | goto out; | ||
| 513 | } | 509 | } |
| 514 | } | 510 | } |
| 515 | 511 | ||
| 516 | if (IS_VGIC_ADDR_UNDEF(dist->vgic_dist_base)) { | 512 | if (IS_VGIC_ADDR_UNDEF(dist->vgic_dist_base)) { |
| 517 | kvm_err("Need to set vgic distributor addresses first\n"); | 513 | kvm_err("Need to set vgic distributor addresses first\n"); |
| 518 | ret = -ENXIO; | 514 | return -ENXIO; |
| 519 | goto out; | ||
| 520 | } | 515 | } |
| 521 | 516 | ||
| 522 | if (!vgic_v3_check_base(kvm)) { | 517 | if (!vgic_v3_check_base(kvm)) { |
| 523 | kvm_err("VGIC redist and dist frames overlap\n"); | 518 | kvm_err("VGIC redist and dist frames overlap\n"); |
| 524 | ret = -EINVAL; | 519 | return -EINVAL; |
| 525 | goto out; | ||
| 526 | } | 520 | } |
| 527 | 521 | ||
| 528 | /* | 522 | /* |
| @@ -530,22 +524,19 @@ int vgic_v3_map_resources(struct kvm *kvm) · 1 unmodified line | |||
| 530 | * the VGIC before we need to use it. | 524 | * the VGIC before we need to use it. |
| 531 | */ | 525 | */ |
| 532 | if (!vgic_initialized(kvm)) { | 526 | if (!vgic_initialized(kvm)) { |
| 533 | ret = -EBUSY; | 527 | return -EBUSY; |
| 534 | goto out; | ||
| 535 | } | 528 | } |
| 536 | 529 | ||
| 537 | ret = vgic_register_dist_iodev(kvm, dist->vgic_dist_base, VGIC_V3); | 530 | ret = vgic_register_dist_iodev(kvm, dist->vgic_dist_base, VGIC_V3); |
| 538 | if (ret) { | 531 | if (ret) { |
| 539 | kvm_err("Unable to register VGICv3 dist MMIO regions\n"); | 532 | kvm_err("Unable to register VGICv3 dist MMIO regions\n"); |
| 540 | goto out; | 533 | return ret; |
| 541 | } | 534 | } |
| 542 | 535 | ||
| 543 | if (kvm_vgic_global_state.has_gicv4_1) | 536 | if (kvm_vgic_global_state.has_gicv4_1) |
| 544 | vgic_v4_configure_vsgis(kvm); | 537 | vgic_v4_configure_vsgis(kvm); |
| 545 | dist->ready = true; | ||
| 546 | 538 | ||
| 547 | out: | 539 | return 0; |
| 548 | return ret; | ||
| 549 | } | 540 | } |
| 550 | 541 | ||
| 551 | DEFINE_STATIC_KEY_FALSE(vgic_v3_cpuif_trap); | 542 | DEFINE_STATIC_KEY_FALSE(vgic_v3_cpuif_trap); |
| @@ -709,10 +709,11 @@ static int do_tag_check_fault(unsigned long far, unsigned int esr, · 708 unmodified lines | |||
| 709 | struct pt_regs *regs) | 709 | struct pt_regs *regs) |
| 710 | { | 710 | { |
| 711 | /* | 711 | /* |
| 712 | * The architecture specifies that bits 63:60 of FAR_EL1 are UNKNOWN for tag | 712 | * The architecture specifies that bits 63:60 of FAR_EL1 are UNKNOWN |
| 713 | * check faults. Mask them out now so that userspace doesn't see them. | 713 | * for tag check faults. Set them to corresponding bits in the untagged |
| 714 | * address. | ||
| 714 | */ | 715 | */ |
| 715 | far &= (1UL << 60) - 1; | 716 | far = (__untagged_addr(far) & ~MTE_TAG_MASK) | (far & MTE_TAG_MASK); |
| 716 | do_bad_area(far, esr, regs); | 717 | do_bad_area(far, esr, regs); |
| 717 | return 0; | 718 | return 0; |
| 718 | } | 719 | } |
| @@ -53,13 +53,13 @@ s64 memstart_addr __ro_after_init = -1; · 52 unmodified lines | |||
| 53 | EXPORT_SYMBOL(memstart_addr); | 53 | EXPORT_SYMBOL(memstart_addr); |
| 54 | 54 | ||
| 55 | /* | 55 | /* |
| 56 | * We create both ZONE_DMA and ZONE_DMA32. ZONE_DMA covers the first 1G of | 56 | * If the corresponding config options are enabled, we create both ZONE_DMA |
| 57 | * memory as some devices, namely the Raspberry Pi 4, have peripherals with | 57 | * and ZONE_DMA32. By default ZONE_DMA covers the 32-bit addressable memory |
| 58 | * this limited view of the memory. ZONE_DMA32 will cover the rest of the 32 | 58 | * unless restricted on specific platforms (e.g. 30-bit on Raspberry Pi 4). |
| 59 | * bit addressable memory area. | 59 | * In such case, ZONE_DMA32 covers the rest of the 32-bit addressable memory, |
| 60 | * otherwise it is empty. | ||
| 60 | */ | 61 | */ |
| 61 | phys_addr_t arm64_dma_phys_limit __ro_after_init; | 62 | phys_addr_t arm64_dma_phys_limit __ro_after_init; |
| 62 | static phys_addr_t arm64_dma32_phys_limit __ro_after_init; | ||
| 63 | 63 | ||
| 64 | #ifdef CONFIG_KEXEC_CORE | 64 | #ifdef CONFIG_KEXEC_CORE |
| 65 | /* | 65 | /* |
| @@ -84,7 +84,7 @@ static void __init reserve_crashkernel(void) · 18 unmodified lines | |||
| 84 | 84 | ||
| 85 | if (crash_base == 0) { | 85 | if (crash_base == 0) { |
| 86 | /* Current arm64 boot protocol requires 2MB alignment */ | 86 | /* Current arm64 boot protocol requires 2MB alignment */ |
| 87 | crash_base = memblock_find_in_range(0, arm64_dma32_phys_limit, | 87 | crash_base = memblock_find_in_range(0, arm64_dma_phys_limit, |
| 88 | crash_size, SZ_2M); | 88 | crash_size, SZ_2M); |
| 89 | if (crash_base == 0) { | 89 | if (crash_base == 0) { |
| 90 | pr_warn("cannot allocate crashkernel (size:0x%llx)\n", | 90 | pr_warn("cannot allocate crashkernel (size:0x%llx)\n", |
| @@ -196,6 +196,7 @@ static void __init zone_sizes_init(unsigned long min, unsigned long max) · 105 unmodified lines | |||
| 196 | unsigned long max_zone_pfns[MAX_NR_ZONES] = {0}; | 196 | unsigned long max_zone_pfns[MAX_NR_ZONES] = {0}; |
| 197 | unsigned int __maybe_unused acpi_zone_dma_bits; | 197 | unsigned int __maybe_unused acpi_zone_dma_bits; |
| 198 | unsigned int __maybe_unused dt_zone_dma_bits; | 198 | unsigned int __maybe_unused dt_zone_dma_bits; |
| 199 | phys_addr_t __maybe_unused dma32_phys_limit = max_zone_phys(32); | ||
| 199 | 200 | ||
| 200 | #ifdef CONFIG_ZONE_DMA | 201 | #ifdef CONFIG_ZONE_DMA |
| 201 | acpi_zone_dma_bits = fls64(acpi_iort_dma_get_max_cpu_address()); | 202 | acpi_zone_dma_bits = fls64(acpi_iort_dma_get_max_cpu_address()); |
| @@ -205,8 +206,12 @@ static void __init zone_sizes_init(unsigned long min, unsigned long max) · 3 unmodified lines | |||
| 205 | max_zone_pfns[ZONE_DMA] = PFN_DOWN(arm64_dma_phys_limit); | 206 | max_zone_pfns[ZONE_DMA] = PFN_DOWN(arm64_dma_phys_limit); |
| 206 | #endif | 207 | #endif |
| 207 | #ifdef CONFIG_ZONE_DMA32 | 208 | #ifdef CONFIG_ZONE_DMA32 |
| 208 | max_zone_pfns[ZONE_DMA32] = PFN_DOWN(arm64_dma32_phys_limit); | 209 | max_zone_pfns[ZONE_DMA32] = PFN_DOWN(dma32_phys_limit); |
| 210 | if (!arm64_dma_phys_limit) | ||
| 211 | arm64_dma_phys_limit = dma32_phys_limit; | ||
| 209 | #endif | 212 | #endif |
| 213 | if (!arm64_dma_phys_limit) | ||
| 214 | arm64_dma_phys_limit = PHYS_MASK + 1; | ||
| 210 | max_zone_pfns[ZONE_NORMAL] = max; | 215 | max_zone_pfns[ZONE_NORMAL] = max; |
| 211 | 216 | ||
| 212 | free_area_init(max_zone_pfns); | 217 | free_area_init(max_zone_pfns); |
| @@ -394,16 +399,9 @@ void __init arm64_memblock_init(void) · 181 unmodified lines | |||
| 394 | 399 | ||
| 395 | early_init_fdt_scan_reserved_mem(); | 400 | early_init_fdt_scan_reserved_mem(); |
| 396 | 401 | ||
| 397 | if (IS_ENABLED(CONFIG_ZONE_DMA32)) | ||
| 398 | arm64_dma32_phys_limit = max_zone_phys(32); | ||
| 399 | else | ||
| 400 | arm64_dma32_phys_limit = PHYS_MASK + 1; | ||
| 401 | |||
| 402 | reserve_elfcorehdr(); | 402 | reserve_elfcorehdr(); |
| 403 | 403 | ||
| 404 | high_memory = __va(memblock_end_of_DRAM() - 1) + 1; | 404 | high_memory = __va(memblock_end_of_DRAM() - 1) + 1; |
| 405 | |||
| 406 | dma_contiguous_reserve(arm64_dma32_phys_limit); | ||
| 407 | } | 405 | } |
| 408 | 406 | ||
| 409 | void __init bootmem_init(void) | 407 | void __init bootmem_init(void) |
| @@ -438,6 +436,11 @@ void __init bootmem_init(void) · 28 unmodified lines | |||
| 438 | sparse_init(); | 436 | sparse_init(); |
| 439 | zone_sizes_init(min, max); | 437 | zone_sizes_init(min, max); |
| 440 | 438 | ||
| 439 | /* | ||
| 440 | * Reserve the CMA area after arm64_dma_phys_limit was initialised. | ||
| 441 | */ | ||
| 442 | dma_contiguous_reserve(arm64_dma_phys_limit); | ||
| 443 | |||
| 441 | /* | 444 | /* |
| 442 | * request_standard_resources() depends on crashkernel's memory being | 445 | * request_standard_resources() depends on crashkernel's memory being |
| 443 | * reserved, so do it here. | 446 | * reserved, so do it here. |
| @@ -455,7 +458,7 @@ void __init bootmem_init(void) · 11 unmodified lines | |||
| 455 | void __init mem_init(void) | 458 | void __init mem_init(void) |
| 456 | { | 459 | { |
| 457 | if (swiotlb_force == SWIOTLB_FORCE || | 460 | if (swiotlb_force == SWIOTLB_FORCE || |
| 458 | max_pfn > PFN_DOWN(arm64_dma_phys_limit ? : arm64_dma32_phys_limit)) | 461 | max_pfn > PFN_DOWN(arm64_dma_phys_limit)) |
| 459 | swiotlb_init(1); | 462 | swiotlb_init(1); |
| 460 | else | 463 | else |
| 461 | swiotlb_force = SWIOTLB_NO_FORCE; | 464 | swiotlb_force = SWIOTLB_NO_FORCE; |
| @@ -9,7 +9,7 @@ · 8 unmodified lines | |||
| 9 | 9 | ||
| 10 | phys_addr_t __virt_to_phys(unsigned long x) | 10 | phys_addr_t __virt_to_phys(unsigned long x) |
| 11 | { | 11 | { |
| 12 | WARN(!__is_lm_address(x), | 12 | WARN(!__is_lm_address(__tag_reset(x)), |
| 13 | "virt_to_phys used for non-linear address: %pK (%pS)\n", | 13 | "virt_to_phys used for non-linear address: %pK (%pS)\n", |
| 14 | (void *)x, | 14 | (void *)x, |
| 15 | (void *)x); | 15 | (void *)x); |
| @@ -46,7 +46,7 @@ · 45 unmodified lines | |||
| 46 | #endif | 46 | #endif |
| 47 | 47 | ||
| 48 | #ifdef CONFIG_KASAN_HW_TAGS | 48 | #ifdef CONFIG_KASAN_HW_TAGS |
| 49 | #define TCR_KASAN_HW_FLAGS SYS_TCR_EL1_TCMA1 | TCR_TBI1 | 49 | #define TCR_KASAN_HW_FLAGS SYS_TCR_EL1_TCMA1 | TCR_TBI1 | TCR_TBID1 |
| 50 | #else | 50 | #else |
| 51 | #define TCR_KASAN_HW_FLAGS 0 | 51 | #define TCR_KASAN_HW_FLAGS 0 |
| 52 | #endif | 52 | #endif |
| @@ -63,6 +63,9 @@ int main(void) · 62 unmodified lines | |||
| 63 | OFFSET(TI_FLAGS, thread_info, flags); | 63 | OFFSET(TI_FLAGS, thread_info, flags); |
| 64 | OFFSET(TI_CPU, thread_info, cpu); | 64 | OFFSET(TI_CPU, thread_info, cpu); |
| 65 | OFFSET(TI_PRE, thread_info, preempt_count); | 65 | OFFSET(TI_PRE, thread_info, preempt_count); |
| 66 | #ifdef CONFIG_PREEMPTION | ||
| 67 | DEFINE(TI_PRE_COUNT, offsetof(struct thread_info, preempt_count)); | ||
| 68 | #endif | ||
| 66 | 69 | ||
| 67 | return 0; | 70 | return 0; |
| 68 | } | 71 | } |
| @@ -69,7 +69,7 @@ vmlinux.bin: vmlinux FORCE · 68 unmodified lines | |||
| 69 | $(call if_changed,objcopy) | 69 | $(call if_changed,objcopy) |
| 70 | 70 | ||
| 71 | unwcheck: vmlinux | 71 | unwcheck: vmlinux |
| 72 | -$(Q)READELF=$(READELF) $(PYTHON) $(srctree)/arch/ia64/scripts/unwcheck.py $< | 72 | -$(Q)READELF=$(READELF) $(PYTHON3) $(srctree)/arch/ia64/scripts/unwcheck.py $< |
| 73 | 73 | ||
| 74 | archclean: | 74 | archclean: |
| 75 | 75 | ||
| @@ -3,6 +3,7 @@ · 2 unmodified lines | |||
| 3 | #define _ASM_IA64_SPARSEMEM_H | 3 | #define _ASM_IA64_SPARSEMEM_H |
| 4 | 4 | ||
| 5 | #ifdef CONFIG_SPARSEMEM | 5 | #ifdef CONFIG_SPARSEMEM |
| 6 | #include <asm/page.h> | ||
| 6 | /* | 7 | /* |
| 7 | * SECTION_SIZE_BITS 2^N: how big each section will be | 8 | * SECTION_SIZE_BITS 2^N: how big each section will be |
| 8 | * MAX_PHYSMEM_BITS 2^N: how much memory we can have in that space | 9 | * MAX_PHYSMEM_BITS 2^N: how much memory we can have in that space |
| @@ -54,7 +54,7 @@ extern void ia64_xchg_called_with_bad_pointer(void); · 53 unmodified lines | |||
| 54 | }) | 54 | }) |
| 55 | 55 | ||
| 56 | #define xchg(ptr, x) \ | 56 | #define xchg(ptr, x) \ |
| 57 | ((__typeof__(*(ptr))) __xchg((unsigned long) (x), (ptr), sizeof(*(ptr)))) | 57 | ({(__typeof__(*(ptr))) __xchg((unsigned long) (x), (ptr), sizeof(*(ptr)));}) |
| 58 | 58 | ||
| 59 | /* | 59 | /* |
| 60 | * Atomic compare and exchange. Compare OLD with MEM, if identical, | 60 | * Atomic compare and exchange. Compare OLD with MEM, if identical, |
| @@ -171,29 +171,34 @@ void vtime_account_hardirq(struct task_struct *tsk) · 170 unmodified lines | |||
| 171 | static irqreturn_t | 171 | static irqreturn_t |
| 172 | timer_interrupt (int irq, void *dev_id) | 172 | timer_interrupt (int irq, void *dev_id) |
| 173 | { | 173 | { |
| 174 | unsigned long cur_itm, new_itm, ticks; | 174 | unsigned long new_itm; |
| 175 | 175 | ||
| 176 | if (cpu_is_offline(smp_processor_id())) { | 176 | if (cpu_is_offline(smp_processor_id())) { |
| 177 | return IRQ_HANDLED; | 177 | return IRQ_HANDLED; |
| 178 | } | 178 | } |
| 179 | 179 | ||
| 180 | new_itm = local_cpu_data->itm_next; | 180 | new_itm = local_cpu_data->itm_next; |
| 181 | cur_itm = ia64_get_itc(); | ||
| 182 | 181 | ||
| 183 | if (!time_after(cur_itm, new_itm)) { | 182 | if (!time_after(ia64_get_itc(), new_itm)) |
| 184 | printk(KERN_ERR "Oops: timer tick before it's due (itc=%lx,itm=%lx)\n", | 183 | printk(KERN_ERR "Oops: timer tick before it's due (itc=%lx,itm=%lx)\n", |
| 185 | cur_itm, new_itm); | 184 | ia64_get_itc(), new_itm); |
| 186 | ticks = 1; | 185 | |
| 187 | } else { | 186 | while (1) { |
| 188 | ticks = DIV_ROUND_UP(cur_itm - new_itm, | 187 | new_itm += local_cpu_data->itm_delta; |
| 189 | local_cpu_data->itm_delta); | 188 | |
| 190 | new_itm += ticks * local_cpu_data->itm_delta; | 189 | legacy_timer_tick(smp_processor_id() == time_keeper_id); |
| 191 | } | ||
| 192 | 190 | ||
| 193 | if (smp_processor_id() != time_keeper_id) | 191 | local_cpu_data->itm_next = new_itm; |
| 194 | ticks = 0; | ||
| 195 | 192 | ||
| 196 | legacy_timer_tick(ticks); | 193 | if (time_after(new_itm, ia64_get_itc())) |
| 194 | break; | ||
| 195 | |||
| 196 | /* | ||
| 197 | * Allow IPIs to interrupt the timer loop. | ||
| 198 | */ | ||
| 199 | local_irq_enable(); | ||
| 200 | local_irq_disable(); | ||
| 201 | } | ||
| 197 | 202 | ||
| 198 | do { | 203 | do { |
| 199 | /* | 204 | /* |
| @@ -1,4 +1,4 @@ | |||
| 1 | #!/usr/bin/env python | 1 | #!/usr/bin/env python3 |
| 2 | # SPDX-License-Identifier: GPL-2.0 | 2 | # SPDX-License-Identifier: GPL-2.0 |
| 3 | # | 3 | # |
| 4 | # Usage: unwcheck.py FILE | 4 | # Usage: unwcheck.py FILE |
| @@ -62,7 +62,7 @@ extern unsigned long _ramend; · 61 unmodified lines | |||
| 62 | #include <asm/page_no.h> | 62 | #include <asm/page_no.h> |
| 63 | #endif | 63 | #endif |
| 64 | 64 | ||
| 65 | #ifdef CONFIG_DISCONTIGMEM | 65 | #if !defined(CONFIG_MMU) || defined(CONFIG_DISCONTIGMEM) |
| 66 | #define __phys_to_pfn(paddr) ((unsigned long)((paddr) >> PAGE_SHIFT)) | 66 | #define __phys_to_pfn(paddr) ((unsigned long)((paddr) >> PAGE_SHIFT)) |
| 67 | #define __pfn_to_phys(pfn) PFN_PHYS(pfn) | 67 | #define __pfn_to_phys(pfn) PFN_PHYS(pfn) |
| 68 | #endif | 68 | #endif |
| @@ -13,6 +13,7 @@ · 12 unmodified lines | |||
| 13 | #include <linux/libfdt.h> | 13 | #include <linux/libfdt.h> |
| 14 | 14 | ||
| 15 | #include <asm/addrspace.h> | 15 | #include <asm/addrspace.h> |
| 16 | #include <asm/unaligned.h> | ||
| 16 | 17 | ||
| 17 | /* | 18 | /* |
| 18 | * These two variables specify the free mem region | 19 | * These two variables specify the free mem region |
| @@ -117,7 +118,7 @@ void decompress_kernel(unsigned long boot_heap_start) · 98 unmodified lines | |||
| 117 | dtb_size = fdt_totalsize((void *)&__appended_dtb); | 118 | dtb_size = fdt_totalsize((void *)&__appended_dtb); |
| 118 | 119 | ||
| 119 | /* last four bytes is always image size in little endian */ | 120 | /* last four bytes is always image size in little endian */ |
| 120 | image_size = le32_to_cpup((void *)&__image_end - 4); | 121 | image_size = get_unaligned_le32((void *)&__image_end - 4); |
| 121 | 122 | ||
| 122 | /* copy dtb to where the booted kernel will expect it */ | 123 | /* copy dtb to where the booted kernel will expect it */ |
| 123 | memcpy((void *)VMLINUX_LOAD_ADDRESS_ULL + image_size, | 124 | memcpy((void *)VMLINUX_LOAD_ADDRESS_ULL + image_size, |
| @@ -1444,7 +1444,7 @@ static void octeon_irq_setup_secondary_ciu2(void) · 1443 unmodified lines | |||
| 1444 | static int __init octeon_irq_init_ciu( | 1444 | static int __init octeon_irq_init_ciu( |
| 1445 | struct device_node *ciu_node, struct device_node *parent) | 1445 | struct device_node *ciu_node, struct device_node *parent) |
| 1446 | { | 1446 | { |
| 1447 | unsigned int i, r; | 1447 | int i, r; |
| 1448 | struct irq_chip *chip; | 1448 | struct irq_chip *chip; |
| 1449 | struct irq_chip *chip_edge; | 1449 | struct irq_chip *chip_edge; |
| 1450 | struct irq_chip *chip_mbox; | 1450 | struct irq_chip *chip_mbox; |
| @@ -51,6 +51,7 @@ extern void kmap_flush_tlb(unsigned long addr); · 50 unmodified lines | |||
| 51 | 51 | ||
| 52 | #define flush_cache_kmaps() BUG_ON(cpu_has_dc_aliases) | 52 | #define flush_cache_kmaps() BUG_ON(cpu_has_dc_aliases) |
| 53 | 53 | ||
| 54 | #define arch_kmap_local_set_pte(mm, vaddr, ptep, ptev) set_pte(ptep, ptev) | ||
| 54 | #define arch_kmap_local_post_map(vaddr, pteval) local_flush_tlb_one(vaddr) | 55 | #define arch_kmap_local_post_map(vaddr, pteval) local_flush_tlb_one(vaddr) |
| 55 | #define arch_kmap_local_post_unmap(vaddr) local_flush_tlb_one(vaddr) | 56 | #define arch_kmap_local_post_unmap(vaddr) local_flush_tlb_one(vaddr) |
| 56 | 57 | ||
| @@ -103,4 +103,11 @@ jiffies_to_old_timeval32(unsigned long jiffies, struct old_timeval32 *value) · 102 unmodified lines | |||
| 103 | #undef ns_to_kernel_old_timeval | 103 | #undef ns_to_kernel_old_timeval |
| 104 | #define ns_to_kernel_old_timeval ns_to_old_timeval32 | 104 | #define ns_to_kernel_old_timeval ns_to_old_timeval32 |
| 105 | 105 | ||
| 106 | /* | ||
| 107 | * Some data types as stored in coredump. | ||
| 108 | */ | ||
| 109 | #define user_long_t compat_long_t | ||
| 110 | #define user_siginfo_t compat_siginfo_t | ||
| 111 | #define copy_siginfo_to_external copy_siginfo_to_external32 | ||
| 112 | |||
| 106 | #include "../../../fs/binfmt_elf.c" | 113 | #include "../../../fs/binfmt_elf.c" |
| @@ -106,4 +106,11 @@ jiffies_to_old_timeval32(unsigned long jiffies, struct old_timeval32 *value) · 105 unmodified lines | |||
| 106 | #undef ns_to_kernel_old_timeval | 106 | #undef ns_to_kernel_old_timeval |
| 107 | #define ns_to_kernel_old_timeval ns_to_old_timeval32 | 107 | #define ns_to_kernel_old_timeval ns_to_old_timeval32 |
| 108 | 108 | ||
| 109 | /* | ||
| 110 | * Some data types as stored in coredump. | ||
| 111 | */ | ||
| 112 | #define user_long_t compat_long_t | ||
| 113 | #define user_siginfo_t compat_siginfo_t | ||
| 114 | #define copy_siginfo_to_external copy_siginfo_to_external32 | ||
| 115 | |||
| 109 | #include "../../../fs/binfmt_elf.c" | 116 | #include "../../../fs/binfmt_elf.c" |
| @@ -187,8 +187,14 @@ static int __init relocate_exception_table(long offset) · 186 unmodified lines | |||
| 187 | static inline __init unsigned long rotate_xor(unsigned long hash, | 187 | static inline __init unsigned long rotate_xor(unsigned long hash, |
| 188 | const void *area, size_t size) | 188 | const void *area, size_t size) |
| 189 | { | 189 | { |
| 190 | size_t i; | 190 | const typeof(hash) *ptr = PTR_ALIGN(area, sizeof(hash)); |
| 191 | unsigned long *ptr = (unsigned long *)area; | 191 | size_t diff, i; |
| 192 | |||
| 193 | diff = (void *)ptr - area; | ||
| 194 | if (unlikely(size < diff + sizeof(hash))) | ||
| 195 | return hash; | ||
| 196 | |||
| 197 | size = ALIGN_DOWN(size - diff, sizeof(hash)); | ||
| 192 | 198 | ||
| 193 | for (i = 0; i < size / sizeof(hash); i++) { | 199 | for (i = 0; i < size / sizeof(hash); i++) { |
| 194 | /* Rotate by odd number of bits and XOR. */ | 200 | /* Rotate by odd number of bits and XOR. */ |
| @@ -31,7 +31,7 @@ · 30 unmodified lines | |||
| 31 | void __iomem *ioremap(phys_addr_t offset, unsigned long size); | 31 | void __iomem *ioremap(phys_addr_t offset, unsigned long size); |
| 32 | 32 | ||
| 33 | #define iounmap iounmap | 33 | #define iounmap iounmap |
| 34 | extern void iounmap(void *addr); | 34 | extern void iounmap(void __iomem *addr); |
| 35 | 35 | ||
| 36 | #include <asm-generic/io.h> | 36 | #include <asm-generic/io.h> |
| 37 | 37 | ||
| @@ -77,7 +77,7 @@ void __iomem *__ref ioremap(phys_addr_t addr, unsigned long size) · 76 unmodified lines | |||
| 77 | } | 77 | } |
| 78 | EXPORT_SYMBOL(ioremap); | 78 | EXPORT_SYMBOL(ioremap); |
| 79 | 79 | ||
| 80 | void iounmap(void *addr) | 80 | void iounmap(void __iomem *addr) |
| 81 | { | 81 | { |
| 82 | /* If the page is from the fixmap pool then we just clear out | 82 | /* If the page is from the fixmap pool then we just clear out |
| 83 | * the fixmap mapping. | 83 | * the fixmap mapping. |
| @@ -202,9 +202,8 @@ config PREFETCH · 201 unmodified lines | |||
| 202 | depends on PA8X00 || PA7200 | 202 | depends on PA8X00 || PA7200 |
| 203 | 203 | ||
| 204 | config MLONGCALLS | 204 | config MLONGCALLS |
| 205 | bool "Enable the -mlong-calls compiler option for big kernels" | 205 | def_bool y if !MODULES || UBSAN || FTRACE |
| 206 | default y if !MODULES || UBSAN || FTRACE | 206 | bool "Enable the -mlong-calls compiler option for big kernels" if MODULES && !UBSAN && !FTRACE |
| 207 | default n | ||
| 208 | depends on PA8X00 | 207 | depends on PA8X00 |
| 209 | help | 208 | help |
| 210 | If you configure the kernel to include many drivers built-in instead | 209 | If you configure the kernel to include many drivers built-in instead |
| @@ -47,7 +47,4 @@ extern unsigned long txn_affinity_addr(unsigned int irq, int cpu); · 46 unmodified lines | |||
| 47 | extern int cpu_claim_irq(unsigned int irq, struct irq_chip *, void *); | 47 | extern int cpu_claim_irq(unsigned int irq, struct irq_chip *, void *); |
| 48 | extern int cpu_check_affinity(struct irq_data *d, const struct cpumask *dest); | 48 | extern int cpu_check_affinity(struct irq_data *d, const struct cpumask *dest); |
| 49 | 49 | ||
| 50 | /* soft power switch support (power.c) */ | ||
| 51 | extern struct tasklet_struct power_tasklet; | ||
| 52 | |||
| 53 | #endif /* _ASM_PARISC_IRQ_H */ | 50 | #endif /* _ASM_PARISC_IRQ_H */ |
| @@ -997,10 +997,17 @@ intr_do_preempt: · 996 unmodified lines | |||
| 997 | bb,<,n %r20, 31 - PSW_SM_I, intr_restore | 997 | bb,<,n %r20, 31 - PSW_SM_I, intr_restore |
| 998 | nop | 998 | nop |
| 999 | 999 | ||
| 1000 | /* ssm PSW_SM_I done later in intr_restore */ | ||
| 1001 | #ifdef CONFIG_MLONGCALLS | ||
| 1002 | ldil L%intr_restore, %r2 | ||
| 1003 | load32 preempt_schedule_irq, %r1 | ||
| 1004 | bv %r0(%r1) | ||
| 1005 | ldo R%intr_restore(%r2), %r2 | ||
| 1006 | #else | ||
| 1007 | ldil L%intr_restore, %r1 | ||
| 1000 | BL preempt_schedule_irq, %r2 | 1008 | BL preempt_schedule_irq, %r2 |
| 1001 | nop | 1009 | ldo R%intr_restore(%r1), %r2 |
| 1002 | 1010 | #endif | |
| 1003 | b,n intr_restore /* ssm PSW_SM_I done by intr_restore */ | ||
| 1004 | #endif /* CONFIG_PREEMPTION */ | 1011 | #endif /* CONFIG_PREEMPTION */ |
| 1005 | 1012 | ||
| 1006 | /* | 1013 | /* |
| @@ -199,25 +199,31 @@ DECLARE_STATIC_KEY_FALSE(uaccess_flush_key); · 198 unmodified lines | |||
| 199 | 199 | ||
| 200 | #ifdef CONFIG_PPC_PKEY | 200 | #ifdef CONFIG_PPC_PKEY |
| 201 | 201 | ||
| 202 | extern u64 __ro_after_init default_uamor; | ||
| 203 | extern u64 __ro_after_init default_amr; | ||
| 204 | extern u64 __ro_after_init default_iamr; | ||
| 205 | |||
| 202 | #include <asm/mmu.h> | 206 | #include <asm/mmu.h> |
| 203 | #include <asm/ptrace.h> | 207 | #include <asm/ptrace.h> |
| 204 | 208 | ||
| 205 | /* | 209 | /* usage of kthread_use_mm() should inherit the |
| 206 | * For kernel thread that doesn't have thread.regs return | 210 | * AMR value of the operating address space. But, the AMR value is |
| 207 | * default AMR/IAMR values. | 211 | * thread-specific and we inherit the address space and not thread |
| 212 | * access restrictions. Because of this ignore AMR value when accessing | ||
| 213 | * userspace via kernel thread. | ||
| 208 | */ | 214 | */ |
| 209 | static inline u64 current_thread_amr(void) | 215 | static inline u64 current_thread_amr(void) |
| 210 | { | 216 | { |
| 211 | if (current->thread.regs) | 217 | if (current->thread.regs) |
| 212 | return current->thread.regs->amr; | 218 | return current->thread.regs->amr; |
| 213 | return AMR_KUAP_BLOCKED; | 219 | return default_amr; |
| 214 | } | 220 | } |
| 215 | 221 | ||
| 216 | static inline u64 current_thread_iamr(void) | 222 | static inline u64 current_thread_iamr(void) |
| 217 | { | 223 | { |
| 218 | if (current->thread.regs) | 224 | if (current->thread.regs) |
| 219 | return current->thread.regs->iamr; | 225 | return current->thread.regs->iamr; |
| 220 | return AMR_KUEP_BLOCKED; | 226 | return default_iamr; |
| 221 | } | 227 | } |
| 222 | #endif /* CONFIG_PPC_PKEY */ | 228 | #endif /* CONFIG_PPC_PKEY */ |
| 223 | 229 | ||
| @@ -5,10 +5,6 @@ · 4 unmodified lines | |||
| 5 | 5 | ||
| 6 | #include <asm/book3s/64/hash-pkey.h> | 6 | #include <asm/book3s/64/hash-pkey.h> |
| 7 | 7 | ||
| 8 | extern u64 __ro_after_init default_uamor; | ||
| 9 | extern u64 __ro_after_init default_amr; | ||
| 10 | extern u64 __ro_after_init default_iamr; | ||
| 11 | |||
| 12 | static inline u64 vmflag_to_pte_pkey_bits(u64 vm_flags) | 8 | static inline u64 vmflag_to_pte_pkey_bits(u64 vm_flags) |
| 13 | { | 9 | { |
| 14 | if (!mmu_has_feature(MMU_FTR_PKEY)) | 10 | if (!mmu_has_feature(MMU_FTR_PKEY)) |
| @@ -63,6 +63,12 @@ · 62 unmodified lines | |||
| 63 | nop; \ | 63 | nop; \ |
| 64 | nop; | 64 | nop; |
| 65 | 65 | ||
| 66 | #define SCV_ENTRY_FLUSH_SLOT \ | ||
| 67 | SCV_ENTRY_FLUSH_FIXUP_SECTION; \ | ||
| 68 | nop; \ | ||
| 69 | nop; \ | ||
| 70 | nop; | ||
| 71 | |||
| 66 | /* | 72 | /* |
| 67 | * r10 must be free to use, r13 must be paca | 73 | * r10 must be free to use, r13 must be paca |
| 68 | */ | 74 | */ |
| @@ -70,6 +76,13 @@ · 1 unmodified line | |||
| 70 | STF_ENTRY_BARRIER_SLOT; \ | 76 | STF_ENTRY_BARRIER_SLOT; \ |
| 71 | ENTRY_FLUSH_SLOT | 77 | ENTRY_FLUSH_SLOT |
| 72 | 78 | ||
| 79 | /* | ||
| 80 | * r10, ctr must be free to use, r13 must be paca | ||
| 81 | */ | ||
| 82 | #define SCV_INTERRUPT_TO_KERNEL \ | ||
| 83 | STF_ENTRY_BARRIER_SLOT; \ | ||
| 84 | SCV_ENTRY_FLUSH_SLOT | ||
| 85 | |||
| 73 | /* | 86 | /* |
| 74 | * Macros for annotating the expected destination of (h)rfid | 87 | * Macros for annotating the expected destination of (h)rfid |
| 75 | * | 88 | * |
| @@ -240,6 +240,14 @@ label##3: \ · 239 unmodified lines | |||
| 240 | FTR_ENTRY_OFFSET 957b-958b; \ | 240 | FTR_ENTRY_OFFSET 957b-958b; \ |
| 241 | .popsection; | 241 | .popsection; |
| 242 | 242 | ||
| 243 | #define SCV_ENTRY_FLUSH_FIXUP_SECTION \ | ||
| 244 | 957: \ | ||
| 245 | .pushsection __scv_entry_flush_fixup,"a"; \ | ||
| 246 | .align 2; \ | ||
| 247 | 958: \ | ||
| 248 | FTR_ENTRY_OFFSET 957b-958b; \ | ||
| 249 | .popsection; | ||
| 250 | |||
| 243 | #define RFI_FLUSH_FIXUP_SECTION \ | 251 | #define RFI_FLUSH_FIXUP_SECTION \ |
| 244 | 951: \ | 252 | 951: \ |
| 245 | .pushsection __rfi_flush_fixup,"a"; \ | 253 | .pushsection __rfi_flush_fixup,"a"; \ |
| @@ -273,10 +281,12 @@ label##3: \ · 27 unmodified lines | |||
| 273 | 281 | ||
| 274 | extern long stf_barrier_fallback; | 282 | extern long stf_barrier_fallback; |
| 275 | extern long entry_flush_fallback; | 283 | extern long entry_flush_fallback; |
| 284 | extern long scv_entry_flush_fallback; | ||
| 276 | extern long __start___stf_entry_barrier_fixup, __stop___stf_entry_barrier_fixup; | 285 | extern long __start___stf_entry_barrier_fixup, __stop___stf_entry_barrier_fixup; |
| 277 | extern long __start___stf_exit_barrier_fixup, __stop___stf_exit_barrier_fixup; | 286 | extern long __start___stf_exit_barrier_fixup, __stop___stf_exit_barrier_fixup; |
| 278 | extern long __start___uaccess_flush_fixup, __stop___uaccess_flush_fixup; | 287 | extern long __start___uaccess_flush_fixup, __stop___uaccess_flush_fixup; |
| 279 | extern long __start___entry_flush_fixup, __stop___entry_flush_fixup; | 288 | extern long __start___entry_flush_fixup, __stop___entry_flush_fixup; |
| 289 | extern long __start___scv_entry_flush_fixup, __stop___scv_entry_flush_fixup; | ||
| 280 | extern long __start___rfi_flush_fixup, __stop___rfi_flush_fixup; | 290 | extern long __start___rfi_flush_fixup, __stop___rfi_flush_fixup; |
| 281 | extern long __start___barrier_nospec_fixup, __stop___barrier_nospec_fixup; | 291 | extern long __start___barrier_nospec_fixup, __stop___barrier_nospec_fixup; |
| 282 | extern long __start__btb_flush_fixup, __stop__btb_flush_fixup; | 292 | extern long __start__btb_flush_fixup, __stop__btb_flush_fixup; |
| @@ -58,6 +58,8 @@ extern pte_t *pkmap_page_table; · 57 unmodified lines | |||
| 58 | 58 | ||
| 59 | #define flush_cache_kmaps() flush_cache_all() | 59 | #define flush_cache_kmaps() flush_cache_all() |
| 60 | 60 | ||
| 61 | #define arch_kmap_local_set_pte(mm, vaddr, ptep, ptev) \ | ||
| 62 | __set_pte_at(mm, vaddr, ptep, ptev, 1) | ||
| 61 | #define arch_kmap_local_post_map(vaddr, pteval) \ | 63 | #define arch_kmap_local_post_map(vaddr, pteval) \ |
| 62 | local_flush_tlb_page(NULL, vaddr) | 64 | local_flush_tlb_page(NULL, vaddr) |
| 63 | #define arch_kmap_local_post_unmap(vaddr) \ | 65 | #define arch_kmap_local_post_unmap(vaddr) \ |
| @@ -103,6 +103,8 @@ int gettimeofday_fallback(struct __kernel_old_timeval *_tv, struct timezone *_tz · 102 unmodified lines | |||
| 103 | return do_syscall_2(__NR_gettimeofday, (unsigned long)_tv, (unsigned long)_tz); | 103 | return do_syscall_2(__NR_gettimeofday, (unsigned long)_tv, (unsigned long)_tz); |
| 104 | } | 104 | } |
| 105 | 105 | ||
| 106 | #ifdef __powerpc64__ | ||
| 107 | |||
| 106 | static __always_inline | 108 | static __always_inline |
| 107 | int clock_gettime_fallback(clockid_t _clkid, struct __kernel_timespec *_ts) | 109 | int clock_gettime_fallback(clockid_t _clkid, struct __kernel_timespec *_ts) |
| 108 | { | 110 | { |
| @@ -115,10 +117,22 @@ int clock_getres_fallback(clockid_t _clkid, struct __kernel_timespec *_ts) · 6 unmodified lines | |||
| 115 | return do_syscall_2(__NR_clock_getres, _clkid, (unsigned long)_ts); | 117 | return do_syscall_2(__NR_clock_getres, _clkid, (unsigned long)_ts); |
| 116 | } | 118 | } |
| 117 | 119 | ||
| 118 | #ifdef CONFIG_VDSO32 | 120 | #else |
| 119 | 121 | ||
| 120 | #define BUILD_VDSO32 1 | 122 | #define BUILD_VDSO32 1 |
| 121 | 123 | ||
| 124 | static __always_inline | ||
| 125 | int clock_gettime_fallback(clockid_t _clkid, struct __kernel_timespec *_ts) | ||
| 126 | { | ||
| 127 | return do_syscall_2(__NR_clock_gettime64, _clkid, (unsigned long)_ts); | ||
| 128 | } | ||
| 129 | |||
| 130 | static __always_inline | ||
| 131 | int clock_getres_fallback(clockid_t _clkid, struct __kernel_timespec *_ts) | ||
| 132 | { | ||
| 133 | return do_syscall_2(__NR_clock_getres_time64, _clkid, (unsigned long)_ts); | ||
| 134 | } | ||
| 135 | |||
| 122 | static __always_inline | 136 | static __always_inline |
| 123 | int clock_gettime32_fallback(clockid_t _clkid, struct old_timespec32 *_ts) | 137 | int clock_gettime32_fallback(clockid_t _clkid, struct old_timespec32 *_ts) |
| 124 | { | 138 | { |
| @@ -51,7 +51,7 @@ obj-y += ptrace/ · 50 unmodified lines | |||
| 51 | obj-$(CONFIG_PPC64) += setup_64.o \ | 51 | obj-$(CONFIG_PPC64) += setup_64.o \ |
| 52 | paca.o nvram_64.o note.o syscall_64.o | 52 | paca.o nvram_64.o note.o syscall_64.o |
| 53 | obj-$(CONFIG_COMPAT) += sys_ppc32.o signal_32.o | 53 | obj-$(CONFIG_COMPAT) += sys_ppc32.o signal_32.o |
| 54 | obj-$(CONFIG_VDSO32) += vdso32/ | 54 | obj-$(CONFIG_VDSO32) += vdso32_wrapper.o |
| 55 | obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o | 55 | obj-$(CONFIG_PPC_WATCHDOG) += watchdog.o |
| 56 | obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o | 56 | obj-$(CONFIG_HAVE_HW_BREAKPOINT) += hw_breakpoint.o |
| 57 | obj-$(CONFIG_PPC_DAWR) += dawr.o | 57 | obj-$(CONFIG_PPC_DAWR) += dawr.o |
| @@ -60,7 +60,7 @@ obj-$(CONFIG_PPC_BOOK3S_64) += cpu_setup_power.o · 2 unmodified lines | |||
| 60 | obj-$(CONFIG_PPC_BOOK3S_64) += mce.o mce_power.o | 60 | obj-$(CONFIG_PPC_BOOK3S_64) += mce.o mce_power.o |
| 61 | obj-$(CONFIG_PPC_BOOK3E_64) += exceptions-64e.o idle_book3e.o | 61 | obj-$(CONFIG_PPC_BOOK3E_64) += exceptions-64e.o idle_book3e.o |
| 62 | obj-$(CONFIG_PPC_BARRIER_NOSPEC) += security.o | 62 | obj-$(CONFIG_PPC_BARRIER_NOSPEC) += security.o |
| 63 | obj-$(CONFIG_PPC64) += vdso64/ | 63 | obj-$(CONFIG_PPC64) += vdso64_wrapper.o |
| 64 | obj-$(CONFIG_ALTIVEC) += vecemu.o | 64 | obj-$(CONFIG_ALTIVEC) += vecemu.o |
| 65 | obj-$(CONFIG_PPC_BOOK3S_IDLE) += idle_book3s.o | 65 | obj-$(CONFIG_PPC_BOOK3S_IDLE) += idle_book3s.o |
| 66 | procfs-y := proc_powerpc.o | 66 | procfs-y := proc_powerpc.o |
| @@ -75,7 +75,7 @@ BEGIN_FTR_SECTION · 74 unmodified lines | |||
| 75 | bne .Ltabort_syscall | 75 | bne .Ltabort_syscall |
| 76 | END_FTR_SECTION_IFSET(CPU_FTR_TM) | 76 | END_FTR_SECTION_IFSET(CPU_FTR_TM) |
| 77 | #endif | 77 | #endif |
| 78 | INTERRUPT_TO_KERNEL | 78 | SCV_INTERRUPT_TO_KERNEL |
| 79 | mr r10,r1 | 79 | mr r10,r1 |
| 80 | ld r1,PACAKSAVE(r13) | 80 | ld r1,PACAKSAVE(r13) |
| 81 | std r10,0(r1) | 81 | std r10,0(r1) |
| @@ -2993,6 +2993,25 @@ TRAMP_REAL_BEGIN(entry_flush_fallback) · 2992 unmodified lines | |||
| 2993 | ld r11,PACA_EXRFI+EX_R11(r13) | 2993 | ld r11,PACA_EXRFI+EX_R11(r13) |
| 2994 | blr | 2994 | blr |
| 2995 | 2995 | ||
| 2996 | /* | ||
| 2997 | * The SCV entry flush happens with interrupts enabled, so it must disable | ||
| 2998 | * to prevent EXRFI being clobbered by NMIs (e.g., soft_nmi_common). r10 | ||
| 2999 | * (containing LR) does not need to be preserved here because scv entry | ||
| 3000 | * puts 0 in the pt_regs, CTR can be clobbered for the same reason. | ||
| 3001 | */ | ||
| 3002 | TRAMP_REAL_BEGIN(scv_entry_flush_fallback) | ||
| 3003 | li r10,0 | ||
| 3004 | mtmsrd r10,1 | ||
| 3005 | lbz r10,PACAIRQHAPPENED(r13) | ||
| 3006 | ori r10,r10,PACA_IRQ_HARD_DIS | ||
| 3007 | stb r10,PACAIRQHAPPENED(r13) | ||
| 3008 | std r11,PACA_EXRFI+EX_R11(r13) | ||
| 3009 | L1D_DISPLACEMENT_FLUSH | ||
| 3010 | ld r11,PACA_EXRFI+EX_R11(r13) | ||
| 3011 | li r10,MSR_RI | ||
| 3012 | mtmsrd r10,1 | ||
| 3013 | blr | ||
| 3014 | |||
| 2996 | TRAMP_REAL_BEGIN(rfi_flush_fallback) | 3015 | TRAMP_REAL_BEGIN(rfi_flush_fallback) |
| 2997 | SET_SCRATCH0(r13); | 3016 | SET_SCRATCH0(r13); |
| 2998 | GET_PACA(r13); | 3017 | GET_PACA(r13); |
| @@ -260,10 +260,19 @@ __secondary_hold_acknowledge: · 259 unmodified lines | |||
| 260 | MachineCheck: | 260 | MachineCheck: |
| 261 | EXCEPTION_PROLOG_0 | 261 | EXCEPTION_PROLOG_0 |
| 262 | #ifdef CONFIG_PPC_CHRP | 262 | #ifdef CONFIG_PPC_CHRP |
| 263 | #ifdef CONFIG_VMAP_STACK | ||
| 264 | mtspr SPRN_SPRG_SCRATCH2,r1 | ||
| 265 | mfspr r1, SPRN_SPRG_THREAD | ||
| 266 | lwz r1, RTAS_SP(r1) | ||
| 267 | cmpwi cr1, r1, 0 | ||
| 268 | bne cr1, 7f | ||
| 269 | mfspr r1, SPRN_SPRG_SCRATCH2 | ||
| 270 | #else | ||
| 263 | mfspr r11, SPRN_SPRG_THREAD | 271 | mfspr r11, SPRN_SPRG_THREAD |
| 264 | lwz r11, RTAS_SP(r11) | 272 | lwz r11, RTAS_SP(r11) |
| 265 | cmpwi cr1, r11, 0 | 273 | cmpwi cr1, r11, 0 |
| 266 | bne cr1, 7f | 274 | bne cr1, 7f |
| 275 | #endif | ||
| 267 | #endif /* CONFIG_PPC_CHRP */ | 276 | #endif /* CONFIG_PPC_CHRP */ |
| 268 | EXCEPTION_PROLOG_1 for_rtas=1 | 277 | EXCEPTION_PROLOG_1 for_rtas=1 |
| 269 | 7: EXCEPTION_PROLOG_2 | 278 | 7: EXCEPTION_PROLOG_2 |
| @@ -180,13 +180,18 @@ void notrace restore_interrupts(void) · 179 unmodified lines | |||
| 180 | 180 | ||
| 181 | void replay_soft_interrupts(void) | 181 | void replay_soft_interrupts(void) |
| 182 | { | 182 | { |
| 183 | struct pt_regs regs; | ||
| 184 | |||
| 183 | /* | 185 | /* |
| 184 | * We use local_paca rather than get_paca() to avoid all | 186 | * Be careful here, calling these interrupt handlers can cause |
| 185 | * the debug_smp_processor_id() business in this low level | 187 | * softirqs to be raised, which they may run when calling irq_exit, |
| 186 | * function | 188 | * which will cause local_irq_enable() to be run, which can then |
| 189 | * recurse into this function. Don't keep any state across | ||
| 190 | * interrupt handler calls which may change underneath us. | ||
| 191 | * | ||
| 192 | * We use local_paca rather than get_paca() to avoid all the | ||
| 193 | * debug_smp_processor_id() business in this low level function. | ||
| 187 | */ | 194 | */ |
| 188 | unsigned char happened = local_paca->irq_happened; | ||
| 189 | struct pt_regs regs; | ||
| 190 | 195 | ||
| 191 | ppc_save_regs(®s); | 196 | ppc_save_regs(®s); |
| 192 | regs.softe = IRQS_ENABLED; | 197 | regs.softe = IRQS_ENABLED; |
| @@ -209,7 +214,7 @@ again: · 16 unmodified lines | |||
| 209 | * This is a higher priority interrupt than the others, so | 214 | * This is a higher priority interrupt than the others, so |
| 210 | * replay it first. | 215 | * replay it first. |
| 211 | */ | 216 | */ |
| 212 | if (IS_ENABLED(CONFIG_PPC_BOOK3S) && (happened & PACA_IRQ_HMI)) { | 217 | if (IS_ENABLED(CONFIG_PPC_BOOK3S) && (local_paca->irq_happened & PACA_IRQ_HMI)) { |
| 213 | local_paca->irq_happened &= ~PACA_IRQ_HMI; | 218 | local_paca->irq_happened &= ~PACA_IRQ_HMI; |
| 214 | regs.trap = 0xe60; | 219 | regs.trap = 0xe60; |
| 215 | handle_hmi_exception(®s); | 220 | handle_hmi_exception(®s); |
| @@ -217,7 +222,7 @@ again: · 1 unmodified line | |||
| 217 | hard_irq_disable(); | 222 | hard_irq_disable(); |
| 218 | } | 223 | } |
| 219 | 224 | ||
| 220 | if (happened & PACA_IRQ_DEC) { | 225 | if (local_paca->irq_happened & PACA_IRQ_DEC) { |
| 221 | local_paca->irq_happened &= ~PACA_IRQ_DEC; | 226 | local_paca->irq_happened &= ~PACA_IRQ_DEC; |
| 222 | regs.trap = 0x900; | 227 | regs.trap = 0x900; |
| 223 | timer_interrupt(®s); | 228 | timer_interrupt(®s); |
| @@ -225,7 +230,7 @@ again: · 1 unmodified line | |||
| 225 | hard_irq_disable(); | 230 | hard_irq_disable(); |
| 226 | } | 231 | } |
| 227 | 232 | ||
| 228 | if (happened & PACA_IRQ_EE) { | 233 | if (local_paca->irq_happened & PACA_IRQ_EE) { |
| 229 | local_paca->irq_happened &= ~PACA_IRQ_EE; | 234 | local_paca->irq_happened &= ~PACA_IRQ_EE; |
| 230 | regs.trap = 0x500; | 235 | regs.trap = 0x500; |
| 231 | do_IRQ(®s); | 236 | do_IRQ(®s); |
| @@ -233,7 +238,7 @@ again: · 1 unmodified line | |||
| 233 | hard_irq_disable(); | 238 | hard_irq_disable(); |
| 234 | } | 239 | } |
| 235 | 240 | ||
| 236 | if (IS_ENABLED(CONFIG_PPC_DOORBELL) && (happened & PACA_IRQ_DBELL)) { | 241 | if (IS_ENABLED(CONFIG_PPC_DOORBELL) && (local_paca->irq_happened & PACA_IRQ_DBELL)) { |
| 237 | local_paca->irq_happened &= ~PACA_IRQ_DBELL; | 242 | local_paca->irq_happened &= ~PACA_IRQ_DBELL; |
| 238 | if (IS_ENABLED(CONFIG_PPC_BOOK3E)) | 243 | if (IS_ENABLED(CONFIG_PPC_BOOK3E)) |
| 239 | regs.trap = 0x280; | 244 | regs.trap = 0x280; |
| @@ -245,7 +250,7 @@ again: · 5 unmodified lines | |||
| 245 | } | 250 | } |
| 246 | 251 | ||
| 247 | /* Book3E does not support soft-masking PMI interrupts */ | 252 | /* Book3E does not support soft-masking PMI interrupts */ |
| 248 | if (IS_ENABLED(CONFIG_PPC_BOOK3S) && (happened & PACA_IRQ_PMI)) { | 253 | if (IS_ENABLED(CONFIG_PPC_BOOK3S) && (local_paca->irq_happened & PACA_IRQ_PMI)) { |
| 249 | local_paca->irq_happened &= ~PACA_IRQ_PMI; | 254 | local_paca->irq_happened &= ~PACA_IRQ_PMI; |
| 250 | regs.trap = 0xf00; | 255 | regs.trap = 0xf00; |
| 251 | performance_monitor_exception(®s); | 256 | performance_monitor_exception(®s); |
| @@ -253,8 +258,7 @@ again: · 1 unmodified line | |||
| 253 | hard_irq_disable(); | 258 | hard_irq_disable(); |
| 254 | } | 259 | } |
| 255 | 260 | ||
| 256 | happened = local_paca->irq_happened; | 261 | if (local_paca->irq_happened & ~PACA_IRQ_HARD_DIS) { |
| 257 | if (happened & ~PACA_IRQ_HARD_DIS) { | ||
| 258 | /* | 262 | /* |
| 259 | * We are responding to the next interrupt, so interrupt-off | 263 | * We are responding to the next interrupt, so interrupt-off |
| 260 | * latencies should be reset here. | 264 | * latencies should be reset here. |
| @@ -30,7 +30,7 @@ CC32FLAGS += -m32 · 29 unmodified lines | |||
| 30 | KBUILD_CFLAGS := $(filter-out -mcmodel=medium -mabi=elfv1 -mabi=elfv2 -mcall-aixdesc,$(KBUILD_CFLAGS)) | 30 | KBUILD_CFLAGS := $(filter-out -mcmodel=medium -mabi=elfv1 -mabi=elfv2 -mcall-aixdesc,$(KBUILD_CFLAGS)) |
| 31 | endif | 31 | endif |
| 32 | 32 | ||
| 33 | targets := $(obj-vdso32) vdso32.so.dbg | 33 | targets := $(obj-vdso32) vdso32.so.dbg vgettimeofday.o |
| 34 | obj-vdso32 := $(addprefix $(obj)/, $(obj-vdso32)) | 34 | obj-vdso32 := $(addprefix $(obj)/, $(obj-vdso32)) |
| 35 | 35 | ||
| 36 | GCOV_PROFILE := n | 36 | GCOV_PROFILE := n |
| @@ -46,9 +46,6 @@ obj-y += vdso32_wrapper.o · 9 unmodified lines | |||
| 46 | targets += vdso32.lds | 46 | targets += vdso32.lds |
| 47 | CPPFLAGS_vdso32.lds += -P -C -Upowerpc | 47 | CPPFLAGS_vdso32.lds += -P -C -Upowerpc |
| 48 | 48 | ||
| 49 | # Force dependency (incbin is bad) | ||
| 50 | $(obj)/vdso32_wrapper.o : $(obj)/vdso32.so.dbg | ||
| 51 | |||
| 52 | # link rule for the .so file, .lds has to be first | 49 | # link rule for the .so file, .lds has to be first |
| 53 | $(obj)/vdso32.so.dbg: $(src)/vdso32.lds $(obj-vdso32) $(obj)/vgettimeofday.o FORCE | 50 | $(obj)/vdso32.so.dbg: $(src)/vdso32.lds $(obj-vdso32) $(obj)/vgettimeofday.o FORCE |
| 54 | $(call if_changed,vdso32ld_and_check) | 51 | $(call if_changed,vdso32ld_and_check) |
File renamed without changes.
| @@ -17,7 +17,7 @@ endif · 16 unmodified lines | |||
| 17 | 17 | ||
| 18 | # Build rules | 18 | # Build rules |
| 19 | 19 | ||
| 20 | targets := $(obj-vdso64) vdso64.so.dbg | 20 | targets := $(obj-vdso64) vdso64.so.dbg vgettimeofday.o |
| 21 | obj-vdso64 := $(addprefix $(obj)/, $(obj-vdso64)) | 21 | obj-vdso64 := $(addprefix $(obj)/, $(obj-vdso64)) |
| 22 | 22 | ||
| 23 | GCOV_PROFILE := n | 23 | GCOV_PROFILE := n |
| @@ -29,15 +29,9 @@ ccflags-y := -shared -fno-common -fno-builtin -nostdlib \ · 5 unmodified lines | |||
| 29 | -Wl,-soname=linux-vdso64.so.1 -Wl,--hash-style=both | 29 | -Wl,-soname=linux-vdso64.so.1 -Wl,--hash-style=both |
| 30 | asflags-y := -D__VDSO64__ -s | 30 | asflags-y := -D__VDSO64__ -s |
| 31 | 31 | ||
| 32 | obj-y += vdso64_wrapper.o | ||
| 33 | targets += vdso64.lds | 32 | targets += vdso64.lds |
| 34 | CPPFLAGS_vdso64.lds += -P -C -U$(ARCH) | 33 | CPPFLAGS_vdso64.lds += -P -C -U$(ARCH) |
| 35 | 34 | ||
| 36 | $(obj)/vgettimeofday.o: %.o: %.c FORCE | ||
| 37 | |||
| 38 | # Force dependency (incbin is bad) | ||
| 39 | $(obj)/vdso64_wrapper.o : $(obj)/vdso64.so.dbg | ||
| 40 | |||
| 41 | # link rule for the .so file, .lds has to be first | 35 | # link rule for the .so file, .lds has to be first |
| 42 | $(obj)/vdso64.so.dbg: $(src)/vdso64.lds $(obj-vdso64) $(obj)/vgettimeofday.o FORCE | 36 | $(obj)/vdso64.so.dbg: $(src)/vdso64.lds $(obj-vdso64) $(obj)/vgettimeofday.o FORCE |
| 43 | $(call if_changed,vdso64ld_and_check) | 37 | $(call if_changed,vdso64ld_and_check) |
| @@ -15,11 +15,20 @@ · 14 unmodified lines | |||
| 15 | 15 | ||
| 16 | .text | 16 | .text |
| 17 | 17 | ||
| 18 | /* | ||
| 19 | * __kernel_start_sigtramp_rt64 and __kernel_sigtramp_rt64 together | ||
| 20 | * are one function split in two parts. The kernel jumps to the former | ||
| 21 | * and the signal handler indirectly (by blr) returns to the latter. | ||
| 22 | * __kernel_sigtramp_rt64 needs to point to the return address so | ||
| 23 | * glibc can correctly identify the trampoline stack frame. | ||
| 24 | */ | ||
| 18 | .balign 8 | 25 | .balign 8 |
| 19 | .balign IFETCH_ALIGN_BYTES | 26 | .balign IFETCH_ALIGN_BYTES |
| 20 | V_FUNCTION_BEGIN(__kernel_sigtramp_rt64) | 27 | V_FUNCTION_BEGIN(__kernel_start_sigtramp_rt64) |
| 21 | .Lsigrt_start: | 28 | .Lsigrt_start: |
| 22 | bctrl /* call the handler */ | 29 | bctrl /* call the handler */ |
| 30 | V_FUNCTION_END(__kernel_start_sigtramp_rt64) | ||
| 31 | V_FUNCTION_BEGIN(__kernel_sigtramp_rt64) | ||
| 23 | addi r1, r1, __SIGNAL_FRAMESIZE | 32 | addi r1, r1, __SIGNAL_FRAMESIZE |
| 24 | li r0,__NR_rt_sigreturn | 33 | li r0,__NR_rt_sigreturn |
| 25 | sc | 34 | sc |
| @@ -131,4 +131,4 @@ VERSION · 130 unmodified lines | |||
| 131 | /* | 131 | /* |
| 132 | * Make the sigreturn code visible to the kernel. | 132 | * Make the sigreturn code visible to the kernel. |
| 133 | */ | 133 | */ |
| 134 | VDSO_sigtramp_rt64 = __kernel_sigtramp_rt64; | 134 | VDSO_sigtramp_rt64 = __kernel_start_sigtramp_rt64; |
File renamed without changes.
| @@ -85,7 +85,7 @@ SECTIONS · 84 unmodified lines | |||
| 85 | ALIGN_FUNCTION(); | 85 | ALIGN_FUNCTION(); |
| 86 | #endif | 86 | #endif |
| 87 | /* careful! __ftr_alt_* sections need to be close to .text */ | 87 | /* careful! __ftr_alt_* sections need to be close to .text */ |
| 88 | *(.text.hot TEXT_MAIN .text.fixup .text.unlikely .fixup __ftr_alt_* .ref.text); | 88 | *(.text.hot .text.hot.* TEXT_MAIN .text.fixup .text.unlikely .text.unlikely.* .fixup __ftr_alt_* .ref.text); |
| 89 | #ifdef CONFIG_PPC64 | 89 | #ifdef CONFIG_PPC64 |
| 90 | *(.tramp.ftrace.text); | 90 | *(.tramp.ftrace.text); |
| 91 | #endif | 91 | #endif |
| @@ -145,6 +145,13 @@ SECTIONS · 53 unmodified lines | |||
| 145 | __stop___entry_flush_fixup = .; | 145 | __stop___entry_flush_fixup = .; |
| 146 | } | 146 | } |
| 147 | 147 | ||
| 148 | . = ALIGN(8); | ||
| 149 | __scv_entry_flush_fixup : AT(ADDR(__scv_entry_flush_fixup) - LOAD_OFFSET) { | ||
| 150 | __start___scv_entry_flush_fixup = .; | ||
| 151 | *(__scv_entry_flush_fixup) | ||
| 152 | __stop___scv_entry_flush_fixup = .; | ||
| 153 | } | ||
| 154 | |||
| 148 | . = ALIGN(8); | 155 | . = ALIGN(8); |
| 149 | __stf_exit_barrier_fixup : AT(ADDR(__stf_exit_barrier_fixup) - LOAD_OFFSET) { | 156 | __stf_exit_barrier_fixup : AT(ADDR(__stf_exit_barrier_fixup) - LOAD_OFFSET) { |
| 150 | __start___stf_exit_barrier_fixup = .; | 157 | __start___stf_exit_barrier_fixup = .; |
| @@ -187,6 +194,12 @@ SECTIONS · 36 unmodified lines | |||
| 187 | .init.text : AT(ADDR(.init.text) - LOAD_OFFSET) { | 194 | .init.text : AT(ADDR(.init.text) - LOAD_OFFSET) { |
| 188 | _sinittext = .; | 195 | _sinittext = .; |
| 189 | INIT_TEXT | 196 | INIT_TEXT |
| 197 | |||
| 198 | /* | ||
| 199 | *.init.text might be RO so we must ensure this section ends on | ||
| 200 | * a page boundary. | ||
| 201 | */ | ||
| 202 | . = ALIGN(PAGE_SIZE); | ||
| 190 | _einittext = .; | 203 | _einittext = .; |
| 191 | #ifdef CONFIG_PPC64 | 204 | #ifdef CONFIG_PPC64 |
| 192 | *(.tramp.ftrace.init); | 205 | *(.tramp.ftrace.init); |
| @@ -200,6 +213,8 @@ SECTIONS · 7 unmodified lines | |||
| 200 | EXIT_TEXT | 213 | EXIT_TEXT |
| 201 | } | 214 | } |
| 202 | 215 | ||
| 216 | . = ALIGN(PAGE_SIZE); | ||
| 217 | |||
| 203 | INIT_DATA_SECTION(16) | 218 | INIT_DATA_SECTION(16) |
| 204 | 219 | ||
| 205 | . = ALIGN(8); | 220 | . = ALIGN(8); |
| @@ -290,9 +290,6 @@ void do_entry_flush_fixups(enum l1d_flush_type types) · 289 unmodified lines | |||
| 290 | long *start, *end; | 290 | long *start, *end; |
| 291 | int i; | 291 | int i; |
| 292 | 292 | ||
| 293 | start = PTRRELOC(&__start___entry_flush_fixup); | ||
| 294 | end = PTRRELOC(&__stop___entry_flush_fixup); | ||
| 295 | |||
| 296 | instrs[0] = 0x60000000; /* nop */ | 293 | instrs[0] = 0x60000000; /* nop */ |
| 297 | instrs[1] = 0x60000000; /* nop */ | 294 | instrs[1] = 0x60000000; /* nop */ |
| 298 | instrs[2] = 0x60000000; /* nop */ | 295 | instrs[2] = 0x60000000; /* nop */ |
| @@ -312,6 +309,8 @@ void do_entry_flush_fixups(enum l1d_flush_type types) · 13 unmodified lines | |||
| 312 | if (types & L1D_FLUSH_MTTRIG) | 309 | if (types & L1D_FLUSH_MTTRIG) |
| 313 | instrs[i++] = 0x7c12dba6; /* mtspr TRIG2,r0 (SPR #882) */ | 310 | instrs[i++] = 0x7c12dba6; /* mtspr TRIG2,r0 (SPR #882) */ |
| 314 | 311 | ||
| 312 | start = PTRRELOC(&__start___entry_flush_fixup); | ||
| 313 | end = PTRRELOC(&__stop___entry_flush_fixup); | ||
| 315 | for (i = 0; start < end; start++, i++) { | 314 | for (i = 0; start < end; start++, i++) { |
| 316 | dest = (void *)start + *start; | 315 | dest = (void *)start + *start; |
| 317 | 316 | ||
| @@ -328,6 +327,25 @@ void do_entry_flush_fixups(enum l1d_flush_type types) · 10 unmodified lines | |||
| 328 | patch_instruction((struct ppc_inst *)(dest + 2), ppc_inst(instrs[2])); | 327 | patch_instruction((struct ppc_inst *)(dest + 2), ppc_inst(instrs[2])); |
| 329 | } | 328 | } |
| 330 | 329 | ||
| 330 | start = PTRRELOC(&__start___scv_entry_flush_fixup); | ||
| 331 | end = PTRRELOC(&__stop___scv_entry_flush_fixup); | ||
| 332 | for (; start < end; start++, i++) { | ||
| 333 | dest = (void *)start + *start; | ||
| 334 | |||
| 335 | pr_devel("patching dest %lx\n", (unsigned long)dest); | ||
| 336 | |||
| 337 | patch_instruction((struct ppc_inst *)dest, ppc_inst(instrs[0])); | ||
| 338 | |||
| 339 | if (types == L1D_FLUSH_FALLBACK) | ||
| 340 | patch_branch((struct ppc_inst *)(dest + 1), (unsigned long)&scv_entry_flush_fallback, | ||
| 341 | BRANCH_SET_LINK); | ||
| 342 | else | ||
| 343 | patch_instruction((struct ppc_inst *)(dest + 1), ppc_inst(instrs[1])); | ||
| 344 | |||
| 345 | patch_instruction((struct ppc_inst *)(dest + 2), ppc_inst(instrs[2])); | ||
| 346 | } | ||
| 347 | |||
| 348 | |||
| 331 | printk(KERN_DEBUG "entry-flush: patched %d locations (%s flush)\n", i, | 349 | printk(KERN_DEBUG "entry-flush: patched %d locations (%s flush)\n", i, |
| 332 | (types == L1D_FLUSH_NONE) ? "no" : | 350 | (types == L1D_FLUSH_NONE) ? "no" : |
| 333 | (types == L1D_FLUSH_FALLBACK) ? "fallback displacement" : | 351 | (types == L1D_FLUSH_FALLBACK) ? "fallback displacement" : |
| @@ -818,13 +818,15 @@ void emulate_vsx_store(struct instruction_op *op, const union vsx_reg *reg, · 817 unmodified lines | |||
| 818 | break; | 818 | break; |
| 819 | if (rev) { | 819 | if (rev) { |
| 820 | /* reverse 32 bytes */ | 820 | /* reverse 32 bytes */ |
| 821 | buf.d[0] = byterev_8(reg->d[3]); | 821 | union vsx_reg buf32[2]; |
| 822 | buf.d[1] = byterev_8(reg->d[2]); | 822 | buf32[0].d[0] = byterev_8(reg[1].d[1]); |
| 823 | buf.d[2] = byterev_8(reg->d[1]); | 823 | buf32[0].d[1] = byterev_8(reg[1].d[0]); |
| 824 | buf.d[3] = byterev_8(reg->d[0]); | 824 | buf32[1].d[0] = byterev_8(reg[0].d[1]); |
| 825 | reg = &buf; | 825 | buf32[1].d[1] = byterev_8(reg[0].d[0]); |
| 826 | memcpy(mem, buf32, size); | ||
| 827 | } else { | ||
| 828 | memcpy(mem, reg, size); | ||
| 826 | } | 829 | } |
| 827 | memcpy(mem, reg, size); | ||
| 828 | break; | 830 | break; |
| 829 | case 16: | 831 | case 16: |
| 830 | /* stxv, stxvx, stxvl, stxvll */ | 832 | /* stxv, stxvx, stxvl, stxvll */ |
| @@ -31,6 +31,7 @@ static u32 initial_allocation_mask __ro_after_init; · 30 unmodified lines | |||
| 31 | u64 default_amr __ro_after_init = ~0x0UL; | 31 | u64 default_amr __ro_after_init = ~0x0UL; |
| 32 | u64 default_iamr __ro_after_init = 0x5555555555555555UL; | 32 | u64 default_iamr __ro_after_init = 0x5555555555555555UL; |
| 33 | u64 default_uamor __ro_after_init; | 33 | u64 default_uamor __ro_after_init; |
| 34 | EXPORT_SYMBOL(default_amr); | ||
| 34 | /* | 35 | /* |
| 35 | * Key used to implement PROT_EXEC mmap. Denies READ/WRITE | 36 | * Key used to implement PROT_EXEC mmap. Denies READ/WRITE |
| 36 | * We pick key 2 because 0 is special key and 1 is reserved as per ISA. | 37 | * We pick key 2 because 0 is special key and 1 is reserved as per ISA. |
| @@ -137,7 +137,7 @@ config PA_BITS · 136 unmodified lines | |||
| 137 | 137 | ||
| 138 | config PAGE_OFFSET | 138 | config PAGE_OFFSET |
| 139 | hex | 139 | hex |
| 140 | default 0xC0000000 if 32BIT && MAXPHYSMEM_2GB | 140 | default 0xC0000000 if 32BIT && MAXPHYSMEM_1GB |
| 141 | default 0x80000000 if 64BIT && !MMU | 141 | default 0x80000000 if 64BIT && !MMU |
| 142 | default 0xffffffff80000000 if 64BIT && MAXPHYSMEM_2GB | 142 | default 0xffffffff80000000 if 64BIT && MAXPHYSMEM_2GB |
| 143 | default 0xffffffe000000000 if 64BIT && MAXPHYSMEM_128GB | 143 | default 0xffffffe000000000 if 64BIT && MAXPHYSMEM_128GB |
| @@ -247,11 +247,15 @@ config MODULE_SECTIONS · 103 unmodified lines | |||
| 247 | 247 | ||
| 248 | choice | 248 | choice |
| 249 | prompt "Maximum Physical Memory" | 249 | prompt "Maximum Physical Memory" |
| 250 | default MAXPHYSMEM_2GB if 32BIT | 250 | default MAXPHYSMEM_1GB if 32BIT |
| 251 | default MAXPHYSMEM_2GB if 64BIT && CMODEL_MEDLOW | 251 | default MAXPHYSMEM_2GB if 64BIT && CMODEL_MEDLOW |
| 252 | default MAXPHYSMEM_128GB if 64BIT && CMODEL_MEDANY | 252 | default MAXPHYSMEM_128GB if 64BIT && CMODEL_MEDANY |
| 253 | 253 | ||
| 254 | config MAXPHYSMEM_1GB | ||
| 255 | depends on 32BIT | ||
| 256 | bool "1GiB" | ||
| 254 | config MAXPHYSMEM_2GB | 257 | config MAXPHYSMEM_2GB |
| 258 | depends on 64BIT && CMODEL_MEDLOW | ||
| 255 | bool "2GiB" | 259 | bool "2GiB" |
| 256 | config MAXPHYSMEM_128GB | 260 | config MAXPHYSMEM_128GB |
| 257 | depends on 64BIT && CMODEL_MEDANY | 261 | depends on 64BIT && CMODEL_MEDANY |
| @@ -88,6 +88,7 @@ · 87 unmodified lines | |||
| 88 | phy-mode = "gmii"; | 88 | phy-mode = "gmii"; |
| 89 | phy-handle = <&phy0>; | 89 | phy-handle = <&phy0>; |
| 90 | phy0: ethernet-phy@0 { | 90 | phy0: ethernet-phy@0 { |
| 91 | compatible = "ethernet-phy-id0007.0771"; | ||
| 91 | reg = <0>; | 92 | reg = <0>; |
| 92 | }; | 93 | }; |
| 93 | }; | 94 | }; |
| @@ -64,6 +64,8 @@ CONFIG_HW_RANDOM=y · 63 unmodified lines | |||
| 64 | CONFIG_HW_RANDOM_VIRTIO=y | 64 | CONFIG_HW_RANDOM_VIRTIO=y |
| 65 | CONFIG_SPI=y | 65 | CONFIG_SPI=y |
| 66 | CONFIG_SPI_SIFIVE=y | 66 | CONFIG_SPI_SIFIVE=y |
| 67 | CONFIG_GPIOLIB=y | ||
| 68 | CONFIG_GPIO_SIFIVE=y | ||
| 67 | # CONFIG_PTP_1588_CLOCK is not set | 69 | # CONFIG_PTP_1588_CLOCK is not set |
| 68 | CONFIG_POWER_RESET=y | 70 | CONFIG_POWER_RESET=y |
| 69 | CONFIG_DRM=y | 71 | CONFIG_DRM=y |
| @@ -135,7 +135,10 @@ extern phys_addr_t __phys_addr_symbol(unsigned long x); · 134 unmodified lines | |||
| 135 | 135 | ||
| 136 | #endif /* __ASSEMBLY__ */ | 136 | #endif /* __ASSEMBLY__ */ |
| 137 | 137 | ||
| 138 | #define virt_addr_valid(vaddr) (pfn_valid(virt_to_pfn(vaddr))) | 138 | #define virt_addr_valid(vaddr) ({ \ |
| 139 | unsigned long _addr = (unsigned long)vaddr; \ | ||
| 140 | (unsigned long)(_addr) >= PAGE_OFFSET && pfn_valid(virt_to_pfn(_addr)); \ | ||
| 141 | }) | ||
| 139 | 142 | ||
| 140 | #define VM_DATA_DEFAULT_FLAGS VM_DATA_FLAGS_NON_EXEC | 143 | #define VM_DATA_DEFAULT_FLAGS VM_DATA_FLAGS_NON_EXEC |
| 141 | 144 | ||
| @@ -99,7 +99,6 @@ · 98 unmodified lines | |||
| 99 | | _PAGE_DIRTY) | 99 | | _PAGE_DIRTY) |
| 100 | 100 | ||
| 101 | #define PAGE_KERNEL __pgprot(_PAGE_KERNEL) | 101 | #define PAGE_KERNEL __pgprot(_PAGE_KERNEL) |
| 102 | #define PAGE_KERNEL_EXEC __pgprot(_PAGE_KERNEL | _PAGE_EXEC) | ||
| 103 | #define PAGE_KERNEL_READ __pgprot(_PAGE_KERNEL & ~_PAGE_WRITE) | 102 | #define PAGE_KERNEL_READ __pgprot(_PAGE_KERNEL & ~_PAGE_WRITE) |
| 104 | #define PAGE_KERNEL_EXEC __pgprot(_PAGE_KERNEL | _PAGE_EXEC) | 103 | #define PAGE_KERNEL_EXEC __pgprot(_PAGE_KERNEL | _PAGE_EXEC) |
| 105 | #define PAGE_KERNEL_READ_EXEC __pgprot((_PAGE_KERNEL & ~_PAGE_WRITE) \ | 104 | #define PAGE_KERNEL_READ_EXEC __pgprot((_PAGE_KERNEL & ~_PAGE_WRITE) \ |
| @@ -32,14 +32,14 @@ bool kernel_page_present(struct page *page); · 31 unmodified lines | |||
| 32 | 32 | ||
| 33 | #endif /* __ASSEMBLY__ */ | 33 | #endif /* __ASSEMBLY__ */ |
| 34 | 34 | ||
| 35 | #ifdef CONFIG_ARCH_HAS_STRICT_KERNEL_RWX | 35 | #ifdef CONFIG_STRICT_KERNEL_RWX |
| 36 | #ifdef CONFIG_64BIT | 36 | #ifdef CONFIG_64BIT |
| 37 | #define SECTION_ALIGN (1 << 21) | 37 | #define SECTION_ALIGN (1 << 21) |
| 38 | #else | 38 | #else |
| 39 | #define SECTION_ALIGN (1 << 22) | 39 | #define SECTION_ALIGN (1 << 22) |
| 40 | #endif | 40 | #endif |
| 41 | #else /* !CONFIG_ARCH_HAS_STRICT_KERNEL_RWX */ | 41 | #else /* !CONFIG_STRICT_KERNEL_RWX */ |
| 42 | #define SECTION_ALIGN L1_CACHE_BYTES | 42 | #define SECTION_ALIGN L1_CACHE_BYTES |
| 43 | #endif /* CONFIG_ARCH_HAS_STRICT_KERNEL_RWX */ | 43 | #endif /* CONFIG_STRICT_KERNEL_RWX */ |
| 44 | 44 | ||
| 45 | #endif /* _ASM_RISCV_SET_MEMORY_H */ | 45 | #endif /* _ASM_RISCV_SET_MEMORY_H */ |
| @@ -10,7 +10,7 @@ · 9 unmodified lines | |||
| 10 | 10 | ||
| 11 | #include <linux/types.h> | 11 | #include <linux/types.h> |
| 12 | 12 | ||
| 13 | #ifndef GENERIC_TIME_VSYSCALL | 13 | #ifndef CONFIG_GENERIC_TIME_VSYSCALL |
| 14 | struct vdso_data { | 14 | struct vdso_data { |
| 15 | }; | 15 | }; |
| 16 | #endif | 16 | #endif |
| @@ -26,7 +26,16 @@ cache_get_priv_group(struct cacheinfo *this_leaf) · 25 unmodified lines | |||
| 26 | 26 | ||
| 27 | static struct cacheinfo *get_cacheinfo(u32 level, enum cache_type type) | 27 | static struct cacheinfo *get_cacheinfo(u32 level, enum cache_type type) |
| 28 | { | 28 | { |
| 29 | struct cpu_cacheinfo *this_cpu_ci = get_cpu_cacheinfo(smp_processor_id()); | 29 | /* |
| 30 | * Using raw_smp_processor_id() elides a preemptability check, but this | ||
| 31 | * is really indicative of a larger problem: the cacheinfo UABI assumes | ||
| 32 | * that cores have a homonogenous view of the cache hierarchy. That | ||
| 33 | * happens to be the case for the current set of RISC-V systems, but | ||
| 34 | * likely won't be true in general. Since there's no way to provide | ||
| 35 | * correct information for these systems via the current UABI we're | ||
| 36 | * just eliding the check for now. | ||
| 37 | */ | ||
| 38 | struct cpu_cacheinfo *this_cpu_ci = get_cpu_cacheinfo(raw_smp_processor_id()); | ||
| 30 | struct cacheinfo *this_leaf; | 39 | struct cacheinfo *this_leaf; |
| 31 | int index; | 40 | int index; |
| 32 | 41 | ||
| @@ -124,15 +124,15 @@ skip_context_tracking: · 123 unmodified lines | |||
| 124 | REG_L a1, (a1) | 124 | REG_L a1, (a1) |
| 125 | jr a1 | 125 | jr a1 |
| 126 | 1: | 126 | 1: |
| 127 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
| 128 | call trace_hardirqs_on | ||
| 129 | #endif | ||
| 130 | /* | 127 | /* |
| 131 | * Exceptions run with interrupts enabled or disabled depending on the | 128 | * Exceptions run with interrupts enabled or disabled depending on the |
| 132 | * state of SR_PIE in m/sstatus. | 129 | * state of SR_PIE in m/sstatus. |
| 133 | */ | 130 | */ |
| 134 | andi t0, s1, SR_PIE | 131 | andi t0, s1, SR_PIE |
| 135 | beqz t0, 1f | 132 | beqz t0, 1f |
| 133 | #ifdef CONFIG_TRACE_IRQFLAGS | ||
| 134 | call trace_hardirqs_on | ||
| 135 | #endif | ||
| 136 | csrs CSR_STATUS, SR_IE | 136 | csrs CSR_STATUS, SR_IE |
| 137 | 137 | ||
| 138 | 1: | 138 | 1: |
| @@ -155,6 +155,15 @@ skip_context_tracking: · 16 unmodified lines | |||
| 155 | tail do_trap_unknown | 155 | tail do_trap_unknown |
| 156 | 156 | ||
| 157 | handle_syscall: | 157 | handle_syscall: |
| 158 | #ifdef CONFIG_RISCV_M_MODE | ||
| 159 | /* | ||
| 160 | * When running is M-Mode (no MMU config), MPIE does not get set. | ||
| 161 | * As a result, we need to force enable interrupts here because | ||
| 162 | * handle_exception did not do set SR_IE as it always sees SR_PIE | ||
| 163 | * being cleared. | ||
| 164 | */ | ||
| 165 | csrs CSR_STATUS, SR_IE | ||
| 166 | #endif | ||
| 158 | #if defined(CONFIG_TRACE_IRQFLAGS) || defined(CONFIG_CONTEXT_TRACKING) | 167 | #if defined(CONFIG_TRACE_IRQFLAGS) || defined(CONFIG_CONTEXT_TRACKING) |
| 159 | /* Recover a0 - a7 for system calls */ | 168 | /* Recover a0 - a7 for system calls */ |
| 160 | REG_L a0, PT_A0(sp) | 169 | REG_L a0, PT_A0(sp) |
| @@ -186,14 +195,7 @@ check_syscall_nr: · 25 unmodified lines | |||
| 186 | * Syscall number held in a7. | 195 | * Syscall number held in a7. |
| 187 | * If syscall number is above allowed value, redirect to ni_syscall. | 196 | * If syscall number is above allowed value, redirect to ni_syscall. |
| 188 | */ | 197 | */ |
| 189 | bge a7, t0, 1f | 198 | bgeu a7, t0, 1f |
| 190 | /* | ||
| 191 | * Check if syscall is rejected by tracer, i.e., a7 == -1. | ||
| 192 | * If yes, we pretend it was executed. | ||
| 193 | */ | ||
| 194 | li t1, -1 | ||
| 195 | beq a7, t1, ret_from_syscall_rejected | ||
| 196 | blt a7, t1, 1f | ||
| 197 | /* Call syscall */ | 199 | /* Call syscall */ |
| 198 | la s0, sys_call_table | 200 | la s0, sys_call_table |
| 199 | slli t0, a7, RISCV_LGPTR | 201 | slli t0, a7, RISCV_LGPTR |
| @@ -127,7 +127,9 @@ static void __init init_resources(void) · 126 unmodified lines | |||
| 127 | { | 127 | { |
| 128 | struct memblock_region *region = NULL; | 128 | struct memblock_region *region = NULL; |
| 129 | struct resource *res = NULL; | 129 | struct resource *res = NULL; |
| 130 | int ret = 0; | 130 | struct resource *mem_res = NULL; |
| 131 | size_t mem_res_sz = 0; | ||
| 132 | int ret = 0, i = 0; | ||
| 131 | 133 | ||
| 132 | code_res.start = __pa_symbol(_text); | 134 | code_res.start = __pa_symbol(_text); |
| 133 | code_res.end = __pa_symbol(_etext) - 1; | 135 | code_res.end = __pa_symbol(_etext) - 1; |
| @@ -145,16 +147,17 @@ static void __init init_resources(void) · 11 unmodified lines | |||
| 145 | bss_res.end = __pa_symbol(__bss_stop) - 1; | 147 | bss_res.end = __pa_symbol(__bss_stop) - 1; |
| 146 | bss_res.flags = IORESOURCE_SYSTEM_RAM | IORESOURCE_BUSY; | 148 | bss_res.flags = IORESOURCE_SYSTEM_RAM | IORESOURCE_BUSY; |
| 147 | 149 | ||
| 150 | mem_res_sz = (memblock.memory.cnt + memblock.reserved.cnt) * sizeof(*mem_res); | ||
| 151 | mem_res = memblock_alloc(mem_res_sz, SMP_CACHE_BYTES); | ||
| 152 | if (!mem_res) | ||
| 153 | panic("%s: Failed to allocate %zu bytes\n", __func__, mem_res_sz); | ||
| 148 | /* | 154 | /* |
| 149 | * Start by adding the reserved regions, if they overlap | 155 | * Start by adding the reserved regions, if they overlap |
| 150 | * with /memory regions, insert_resource later on will take | 156 | * with /memory regions, insert_resource later on will take |
| 151 | * care of it. | 157 | * care of it. |
| 152 | */ | 158 | */ |
| 153 | for_each_reserved_mem_region(region) { | 159 | for_each_reserved_mem_region(region) { |
| 154 | res = memblock_alloc(sizeof(struct resource), SMP_CACHE_BYTES); | 160 | res = &mem_res[i++]; |
| 155 | if (!res) | ||
| 156 | panic("%s: Failed to allocate %zu bytes\n", __func__, | ||
| 157 | sizeof(struct resource)); | ||
| 158 | 161 | ||
| 159 | res->name = "Reserved"; | 162 | res->name = "Reserved"; |
| 160 | res->flags = IORESOURCE_MEM | IORESOURCE_BUSY; | 163 | res->flags = IORESOURCE_MEM | IORESOURCE_BUSY; |
| @@ -171,8 +174,10 @@ static void __init init_resources(void) · 10 unmodified lines | |||
| 171 | * Ignore any other reserved regions within | 174 | * Ignore any other reserved regions within |
| 172 | * system memory. | 175 | * system memory. |
| 173 | */ | 176 | */ |
| 174 | if (memblock_is_memory(res->start)) | 177 | if (memblock_is_memory(res->start)) { |
| 178 | memblock_free((phys_addr_t) res, sizeof(struct resource)); | ||
| 175 | continue; | 179 | continue; |
| 180 | } | ||
| 176 | 181 | ||
| 177 | ret = add_resource(&iomem_resource, res); | 182 | ret = add_resource(&iomem_resource, res); |
| 178 | if (ret < 0) | 183 | if (ret < 0) |
| @@ -181,10 +186,7 @@ static void __init init_resources(void) · 2 unmodified lines | |||
| 181 | 186 | ||
| 182 | /* Add /memory regions to the resource tree */ | 187 | /* Add /memory regions to the resource tree */ |
| 183 | for_each_mem_region(region) { | 188 | for_each_mem_region(region) { |
| 184 | res = memblock_alloc(sizeof(struct resource), SMP_CACHE_BYTES); | 189 | res = &mem_res[i++]; |
| 185 | if (!res) | ||
| 186 | panic("%s: Failed to allocate %zu bytes\n", __func__, | ||
| 187 | sizeof(struct resource)); | ||
| 188 | 190 | ||
| 189 | if (unlikely(memblock_is_nomap(region))) { | 191 | if (unlikely(memblock_is_nomap(region))) { |
| 190 | res->name = "Reserved"; | 192 | res->name = "Reserved"; |
| @@ -205,9 +207,9 @@ static void __init init_resources(void) · 14 unmodified lines | |||
| 205 | return; | 207 | return; |
| 206 | 208 | ||
| 207 | error: | 209 | error: |
| 208 | memblock_free((phys_addr_t) res, sizeof(struct resource)); | ||
| 209 | /* Better an empty resource tree than an inconsistent one */ | 210 | /* Better an empty resource tree than an inconsistent one */ |
| 210 | release_child_resources(&iomem_resource); | 211 | release_child_resources(&iomem_resource); |
| 212 | memblock_free((phys_addr_t) mem_res, mem_res_sz); | ||
| 211 | } | 213 | } |
| 212 | 214 | ||
| 213 | 215 | ||
| @@ -291,6 +293,8 @@ void free_initmem(void) · 77 unmodified lines | |||
| 291 | unsigned long init_begin = (unsigned long)__init_begin; | 293 | unsigned long init_begin = (unsigned long)__init_begin; |
| 292 | unsigned long init_end = (unsigned long)__init_end; | 294 | unsigned long init_end = (unsigned long)__init_end; |
| 293 | 295 | ||
| 294 | set_memory_rw_nx(init_begin, (init_end - init_begin) >> PAGE_SHIFT); | 296 | if (IS_ENABLED(CONFIG_STRICT_KERNEL_RWX)) |
| 297 | set_memory_rw_nx(init_begin, (init_end - init_begin) >> PAGE_SHIFT); | ||
| 298 | |||
| 295 | free_initmem_default(POISON_FREE_INITMEM); | 299 | free_initmem_default(POISON_FREE_INITMEM); |
| 296 | } | 300 | } |
| @@ -14,7 +14,7 @@ · 13 unmodified lines | |||
| 14 | 14 | ||
| 15 | #include <asm/stacktrace.h> | 15 | #include <asm/stacktrace.h> |
| 16 | 16 | ||
| 17 | register unsigned long sp_in_global __asm__("sp"); | 17 | register const unsigned long sp_in_global __asm__("sp"); |
| 18 | 18 | ||
| 19 | #ifdef CONFIG_FRAME_POINTER | 19 | #ifdef CONFIG_FRAME_POINTER |
| 20 | 20 | ||
| @@ -28,9 +28,8 @@ void notrace walk_stackframe(struct task_struct *task, struct pt_regs *regs, · 7 unmodified lines | |||
| 28 | sp = user_stack_pointer(regs); | 28 | sp = user_stack_pointer(regs); |
| 29 | pc = instruction_pointer(regs); | 29 | pc = instruction_pointer(regs); |
| 30 | } else if (task == NULL || task == current) { | 30 | } else if (task == NULL || task == current) { |
| 31 | const register unsigned long current_sp = sp_in_global; | ||
| 32 | fp = (unsigned long)__builtin_frame_address(0); | 31 | fp = (unsigned long)__builtin_frame_address(0); |
| 33 | sp = current_sp; | 32 | sp = sp_in_global; |
| 34 | pc = (unsigned long)walk_stackframe; | 33 | pc = (unsigned long)walk_stackframe; |
| 35 | } else { | 34 | } else { |
| 36 | /* task blocked in __switch_to */ | 35 | /* task blocked in __switch_to */ |
| @@ -4,6 +4,7 @@ · 3 unmodified lines | |||
| 4 | * Copyright (C) 2017 SiFive | 4 | * Copyright (C) 2017 SiFive |
| 5 | */ | 5 | */ |
| 6 | 6 | ||
| 7 | #include <linux/of_clk.h> | ||
| 7 | #include <linux/clocksource.h> | 8 | #include <linux/clocksource.h> |
| 8 | #include <linux/delay.h> | 9 | #include <linux/delay.h> |
| 9 | #include <asm/sbi.h> | 10 | #include <asm/sbi.h> |
| @@ -24,6 +25,8 @@ void __init time_init(void) · 14 unmodified lines | |||
| 24 | riscv_timebase = prop; | 25 | riscv_timebase = prop; |
| 25 | 26 | ||
| 26 | lpj_fine = riscv_timebase / HZ; | 27 | lpj_fine = riscv_timebase / HZ; |
| 28 | |||
| 29 | of_clk_init(NULL); | ||
| 27 | timer_probe(); | 30 | timer_probe(); |
| 28 | } | 31 | } |
| 29 | 32 | ||
| @@ -12,7 +12,7 @@ · 11 unmodified lines | |||
| 12 | #include <linux/binfmts.h> | 12 | #include <linux/binfmts.h> |
| 13 | #include <linux/err.h> | 13 | #include <linux/err.h> |
| 14 | #include <asm/page.h> | 14 | #include <asm/page.h> |
| 15 | #ifdef GENERIC_TIME_VSYSCALL | 15 | #ifdef CONFIG_GENERIC_TIME_VSYSCALL |
| 16 | #include <vdso/datapage.h> | 16 | #include <vdso/datapage.h> |
| 17 | #else | 17 | #else |
| 18 | #include <asm/vdso.h> | 18 | #include <asm/vdso.h> |
| @@ -157,9 +157,10 @@ disable: · 156 unmodified lines | |||
| 157 | void __init setup_bootmem(void) | 157 | void __init setup_bootmem(void) |
| 158 | { | 158 | { |
| 159 | phys_addr_t mem_start = 0; | 159 | phys_addr_t mem_start = 0; |
| 160 | phys_addr_t start, end = 0; | 160 | phys_addr_t start, dram_end, end = 0; |
| 161 | phys_addr_t vmlinux_end = __pa_symbol(&_end); | 161 | phys_addr_t vmlinux_end = __pa_symbol(&_end); |
| 162 | phys_addr_t vmlinux_start = __pa_symbol(&_start); | 162 | phys_addr_t vmlinux_start = __pa_symbol(&_start); |
| 163 | phys_addr_t max_mapped_addr = __pa(~(ulong)0); | ||
| 163 | u64 i; | 164 | u64 i; |
| 164 | 165 | ||
| 165 | /* Find the memory region containing the kernel */ | 166 | /* Find the memory region containing the kernel */ |
| @@ -181,10 +182,21 @@ void __init setup_bootmem(void) · 15 unmodified lines | |||
| 181 | /* Reserve from the start of the kernel to the end of the kernel */ | 182 | /* Reserve from the start of the kernel to the end of the kernel */ |
| 182 | memblock_reserve(vmlinux_start, vmlinux_end - vmlinux_start); | 183 | memblock_reserve(vmlinux_start, vmlinux_end - vmlinux_start); |
| 183 | 184 | ||
| 184 | max_pfn = PFN_DOWN(memblock_end_of_DRAM()); | 185 | dram_end = memblock_end_of_DRAM(); |
| 186 | |||
| 187 | /* | ||
| 188 | * memblock allocator is not aware of the fact that last 4K bytes of | ||
| 189 | * the addressable memory can not be mapped because of IS_ERR_VALUE | ||
| 190 | * macro. Make sure that last 4k bytes are not usable by memblock | ||
| 191 | * if end of dram is equal to maximum addressable memory. | ||
| 192 | */ | ||
| 193 | if (max_mapped_addr == (dram_end - 1)) | ||
| 194 | memblock_set_current_limit(max_mapped_addr - 4096); | ||
| 195 | |||
| 196 | max_pfn = PFN_DOWN(dram_end); | ||
| 185 | max_low_pfn = max_pfn; | 197 | max_low_pfn = max_pfn; |
| 186 | dma32_phys_limit = min(4UL * SZ_1G, (unsigned long)PFN_PHYS(max_low_pfn)); | 198 | dma32_phys_limit = min(4UL * SZ_1G, (unsigned long)PFN_PHYS(max_low_pfn)); |
| 187 | set_max_mapnr(max_low_pfn); | 199 | set_max_mapnr(max_low_pfn - ARCH_PFN_OFFSET); |
| 188 | 200 | ||
| 189 | #ifdef CONFIG_BLK_DEV_INITRD | 201 | #ifdef CONFIG_BLK_DEV_INITRD |
| 190 | setup_initrd(); | 202 | setup_initrd(); |
| @@ -93,8 +93,8 @@ void __init kasan_init(void) · 92 unmodified lines | |||
| 93 | VMALLOC_END)); | 93 | VMALLOC_END)); |
| 94 | 94 | ||
| 95 | for_each_mem_range(i, &_start, &_end) { | 95 | for_each_mem_range(i, &_start, &_end) { |
| 96 | void *start = (void *)_start; | 96 | void *start = (void *)__va(_start); |
| 97 | void *end = (void *)_end; | 97 | void *end = (void *)__va(_end); |
| 98 | 98 | ||
| 99 | if (start >= end) | 99 | if (start >= end) |
| 100 | break; | 100 | break; |
| @@ -35,7 +35,7 @@ void uv_query_info(void) · 34 unmodified lines | |||
| 35 | uv_info.guest_cpu_stor_len = uvcb.cpu_stor_len; | 35 | uv_info.guest_cpu_stor_len = uvcb.cpu_stor_len; |
| 36 | uv_info.max_sec_stor_addr = ALIGN(uvcb.max_guest_stor_addr, PAGE_SIZE); | 36 | uv_info.max_sec_stor_addr = ALIGN(uvcb.max_guest_stor_addr, PAGE_SIZE); |
| 37 | uv_info.max_num_sec_conf = uvcb.max_num_sec_conf; | 37 | uv_info.max_num_sec_conf = uvcb.max_num_sec_conf; |
| 38 | uv_info.max_guest_cpus = uvcb.max_guest_cpus; | 38 | uv_info.max_guest_cpu_id = uvcb.max_guest_cpu_id; |
| 39 | } | 39 | } |
| 40 | 40 | ||
| 41 | #ifdef CONFIG_PROTECTED_VIRTUALIZATION_GUEST | 41 | #ifdef CONFIG_PROTECTED_VIRTUALIZATION_GUEST |
| @@ -96,7 +96,7 @@ struct uv_cb_qui { · 95 unmodified lines | |||
| 96 | u32 max_num_sec_conf; | 96 | u32 max_num_sec_conf; |
| 97 | u64 max_guest_stor_addr; | 97 | u64 max_guest_stor_addr; |
| 98 | u8 reserved88[158 - 136]; | 98 | u8 reserved88[158 - 136]; |
| 99 | u16 max_guest_cpus; | 99 | u16 max_guest_cpu_id; |
| 100 | u8 reserveda0[200 - 160]; | 100 | u8 reserveda0[200 - 160]; |
| 101 | } __packed __aligned(8); | 101 | } __packed __aligned(8); |
| 102 | 102 | ||
| @@ -273,7 +273,7 @@ struct uv_info { · 170 unmodified lines | |||
| 273 | unsigned long guest_cpu_stor_len; | 273 | unsigned long guest_cpu_stor_len; |
| 274 | unsigned long max_sec_stor_addr; | 274 | unsigned long max_sec_stor_addr; |
| 275 | unsigned int max_num_sec_conf; | 275 | unsigned int max_num_sec_conf; |
| 276 | unsigned short max_guest_cpus; | 276 | unsigned short max_guest_cpu_id; |
| 277 | }; | 277 | }; |
| 278 | 278 | ||
| 279 | extern struct uv_info uv_info; | 279 | extern struct uv_info uv_info; |
| @@ -368,7 +368,7 @@ static ssize_t uv_query_max_guest_cpus(struct kobject *kobj, · 367 unmodified lines | |||
| 368 | struct kobj_attribute *attr, char *page) | 368 | struct kobj_attribute *attr, char *page) |
| 369 | { | 369 | { |
| 370 | return scnprintf(page, PAGE_SIZE, "%d\n", | 370 | return scnprintf(page, PAGE_SIZE, "%d\n", |
| 371 | uv_info.max_guest_cpus); | 371 | uv_info.max_guest_cpu_id + 1); |
| 372 | } | 372 | } |
| 373 | 373 | ||
| 374 | static struct kobj_attribute uv_query_max_guest_cpus_attr = | 374 | static struct kobj_attribute uv_query_max_guest_cpus_attr = |
| @@ -29,7 +29,6 @@ config SUPERH · 28 unmodified lines | |||
| 29 | select HAVE_ARCH_KGDB | 29 | select HAVE_ARCH_KGDB |
| 30 | select HAVE_ARCH_SECCOMP_FILTER | 30 | select HAVE_ARCH_SECCOMP_FILTER |
| 31 | select HAVE_ARCH_TRACEHOOK | 31 | select HAVE_ARCH_TRACEHOOK |
| 32 | select HAVE_COPY_THREAD_TLS | ||
| 33 | select HAVE_DEBUG_BUGVERBOSE | 32 | select HAVE_DEBUG_BUGVERBOSE |
| 34 | select HAVE_DEBUG_KMEMLEAK | 33 | select HAVE_DEBUG_KMEMLEAK |
| 35 | select HAVE_DYNAMIC_FTRACE | 34 | select HAVE_DYNAMIC_FTRACE |
| @@ -11,7 +11,6 @@ · 10 unmodified lines | |||
| 11 | #include <linux/sched.h> | 11 | #include <linux/sched.h> |
| 12 | #include <linux/time.h> | 12 | #include <linux/time.h> |
| 13 | #include <linux/bcd.h> | 13 | #include <linux/bcd.h> |
| 14 | #include <linux/rtc.h> | ||
| 15 | #include <linux/spinlock.h> | 14 | #include <linux/spinlock.h> |
| 16 | #include <linux/io.h> | 15 | #include <linux/io.h> |
| 17 | #include <linux/rtc.h> | 16 | #include <linux/rtc.h> |
| @@ -27,13 +27,12 @@ CONFIG_NETFILTER=y · 26 unmodified lines | |||
| 27 | CONFIG_ATALK=m | 27 | CONFIG_ATALK=m |
| 28 | CONFIG_BLK_DEV_LOOP=y | 28 | CONFIG_BLK_DEV_LOOP=y |
| 29 | CONFIG_BLK_DEV_RAM=y | 29 | CONFIG_BLK_DEV_RAM=y |
| 30 | CONFIG_IDE=y | 30 | CONFIG_ATA=y |
| 31 | CONFIG_BLK_DEV_IDECD=y | 31 | CONFIG_ATA_GENERIC=y |
| 32 | CONFIG_BLK_DEV_OFFBOARD=y | 32 | CONFIG_PATA_ATP867X=y |
| 33 | CONFIG_BLK_DEV_GENERIC=y | ||
| 34 | CONFIG_BLK_DEV_AEC62XX=y | ||
| 35 | CONFIG_SCSI=y | 33 | CONFIG_SCSI=y |
| 36 | CONFIG_BLK_DEV_SD=y | 34 | CONFIG_BLK_DEV_SD=y |
| 35 | CONFIG_BLK_DEV_SR=y | ||
| 37 | CONFIG_SCSI_MULTI_LUN=y | 36 | CONFIG_SCSI_MULTI_LUN=y |
| 38 | CONFIG_MD=y | 37 | CONFIG_MD=y |
| 39 | CONFIG_BLK_DEV_MD=m | 38 | CONFIG_BLK_DEV_MD=m |
| @@ -20,8 +20,6 @@ CONFIG_IP_PNP=y · 19 unmodified lines | |||
| 20 | # CONFIG_IPV6 is not set | 20 | # CONFIG_IPV6 is not set |
| 21 | # CONFIG_FW_LOADER is not set | 21 | # CONFIG_FW_LOADER is not set |
| 22 | CONFIG_BLK_DEV_RAM=y | 22 | CONFIG_BLK_DEV_RAM=y |
| 23 | CONFIG_IDE=y | ||
| 24 | CONFIG_BLK_DEV_IDECD=y | ||
| 25 | CONFIG_NETDEVICES=y | 23 | CONFIG_NETDEVICES=y |
| 26 | CONFIG_NET_ETHERNET=y | 24 | CONFIG_NET_ETHERNET=y |
| 27 | CONFIG_SMC91X=y | 25 | CONFIG_SMC91X=y |
| @@ -44,16 +44,14 @@ CONFIG_NET_SCHED=y · 43 unmodified lines | |||
| 44 | CONFIG_PARPORT=y | 44 | CONFIG_PARPORT=y |
| 45 | CONFIG_BLK_DEV_LOOP=y | 45 | CONFIG_BLK_DEV_LOOP=y |
| 46 | CONFIG_BLK_DEV_RAM=y | 46 | CONFIG_BLK_DEV_RAM=y |
| 47 | CONFIG_IDE=y | ||
| 48 | CONFIG_BLK_DEV_IDECD=y | ||
| 49 | CONFIG_BLK_DEV_PLATFORM=y | ||
| 50 | CONFIG_BLK_DEV_GENERIC=y | ||
| 51 | CONFIG_BLK_DEV_SD=y | 47 | CONFIG_BLK_DEV_SD=y |
| 52 | CONFIG_BLK_DEV_SR=y | 48 | CONFIG_BLK_DEV_SR=y |
| 53 | CONFIG_CHR_DEV_SG=y | 49 | CONFIG_CHR_DEV_SG=y |
| 54 | CONFIG_SCSI_SPI_ATTRS=y | 50 | CONFIG_SCSI_SPI_ATTRS=y |
| 55 | CONFIG_SCSI_FC_ATTRS=y | 51 | CONFIG_SCSI_FC_ATTRS=y |
| 56 | CONFIG_ATA=y | 52 | CONFIG_ATA=y |
| 53 | CONFIG_ATA_GENERIC=y | ||
| 54 | CONFIG_PATA_PLATFORM=y | ||
| 57 | CONFIG_MD=y | 55 | CONFIG_MD=y |
| 58 | CONFIG_BLK_DEV_DM=y | 56 | CONFIG_BLK_DEV_DM=y |
| 59 | CONFIG_NETDEVICES=y | 57 | CONFIG_NETDEVICES=y |
| @@ -116,9 +116,6 @@ CONFIG_MTD_UBI_GLUEBI=m · 115 unmodified lines | |||
| 116 | CONFIG_BLK_DEV_LOOP=y | 116 | CONFIG_BLK_DEV_LOOP=y |
| 117 | CONFIG_BLK_DEV_CRYPTOLOOP=y | 117 | CONFIG_BLK_DEV_CRYPTOLOOP=y |
| 118 | CONFIG_BLK_DEV_RAM=y | 118 | CONFIG_BLK_DEV_RAM=y |
| 119 | CONFIG_IDE=y | ||
| 120 | CONFIG_BLK_DEV_IDECD=y | ||
| 121 | CONFIG_BLK_DEV_PLATFORM=y | ||
| 122 | CONFIG_BLK_DEV_SD=y | 119 | CONFIG_BLK_DEV_SD=y |
| 123 | CONFIG_BLK_DEV_SR=y | 120 | CONFIG_BLK_DEV_SR=y |
| 124 | CONFIG_SCSI_MULTI_LUN=y | 121 | CONFIG_SCSI_MULTI_LUN=y |
| @@ -29,7 +29,6 @@ CONFIG_MTD_BLOCK=y · 28 unmodified lines | |||
| 29 | CONFIG_MTD_CFI=y | 29 | CONFIG_MTD_CFI=y |
| 30 | CONFIG_MTD_CFI_AMDSTD=y | 30 | CONFIG_MTD_CFI_AMDSTD=y |
| 31 | CONFIG_MTD_ROM=y | 31 | CONFIG_MTD_ROM=y |
| 32 | CONFIG_IDE=y | ||
| 33 | CONFIG_SCSI=y | 32 | CONFIG_SCSI=y |
| 34 | CONFIG_NETDEVICES=y | 33 | CONFIG_NETDEVICES=y |
| 35 | CONFIG_NET_ETHERNET=y | 34 | CONFIG_NET_ETHERNET=y |
| @@ -39,9 +39,6 @@ CONFIG_IP_PNP_RARP=y · 38 unmodified lines | |||
| 39 | CONFIG_BLK_DEV_LOOP=y | 39 | CONFIG_BLK_DEV_LOOP=y |
| 40 | CONFIG_BLK_DEV_NBD=y | 40 | CONFIG_BLK_DEV_NBD=y |
| 41 | CONFIG_BLK_DEV_RAM=y | 41 | CONFIG_BLK_DEV_RAM=y |
| 42 | CONFIG_IDE=y | ||
| 43 | CONFIG_BLK_DEV_IDECD=m | ||
| 44 | CONFIG_BLK_DEV_IDETAPE=m | ||
| 45 | CONFIG_SCSI=m | 42 | CONFIG_SCSI=m |
| 46 | CONFIG_BLK_DEV_SD=m | 43 | CONFIG_BLK_DEV_SD=m |
| 47 | CONFIG_BLK_DEV_SR=m | 44 | CONFIG_BLK_DEV_SR=m |
| @@ -63,8 +63,7 @@ config PVR2_DMA · 62 unmodified lines | |||
| 63 | 63 | ||
| 64 | config G2_DMA | 64 | config G2_DMA |
| 65 | tristate "G2 Bus DMA support" | 65 | tristate "G2 Bus DMA support" |
| 66 | depends on SH_DREAMCAST | 66 | depends on SH_DREAMCAST && SH_DMA_API |
| 67 | select SH_DMA_API | ||
| 68 | help | 67 | help |
| 69 | This enables support for the DMA controller for the Dreamcast's | 68 | This enables support for the DMA controller for the Dreamcast's |
| 70 | G2 bus. Drivers that want this will generally enable this on | 69 | G2 bus. Drivers that want this will generally enable this on |
| @@ -16,7 +16,6 @@ · 15 unmodified lines | |||
| 16 | #include <cpu/gpio.h> | 16 | #include <cpu/gpio.h> |
| 17 | #endif | 17 | #endif |
| 18 | 18 | ||
| 19 | #define ARCH_NR_GPIOS 512 | ||
| 20 | #include <asm-generic/gpio.h> | 19 | #include <asm-generic/gpio.h> |
| 21 | 20 | ||
| 22 | #ifdef CONFIG_GPIOLIB | 21 | #ifdef CONFIG_GPIOLIB |
| @@ -14,7 +14,6 @@ · 13 unmodified lines | |||
| 14 | #include <cpu/mmu_context.h> | 14 | #include <cpu/mmu_context.h> |
| 15 | #include <asm/page.h> | 15 | #include <asm/page.h> |
| 16 | #include <asm/cache.h> | 16 | #include <asm/cache.h> |
| 17 | #include <asm/thread_info.h> | ||
| 18 | 17 | ||
| 19 | ! NOTE: | 18 | ! NOTE: |
| 20 | ! GNU as (as of 2.9.1) changes bf/s into bt/s and bra, when the address | 19 | ! GNU as (as of 2.9.1) changes bf/s into bt/s and bra, when the address |
| @@ -105,7 +105,7 @@ config VSYSCALL · 104 unmodified lines | |||
| 105 | (the default value) say Y. | 105 | (the default value) say Y. |
| 106 | 106 | ||
| 107 | config NUMA | 107 | config NUMA |
| 108 | bool "Non Uniform Memory Access (NUMA) Support" | 108 | bool "Non-Uniform Memory Access (NUMA) Support" |
| 109 | depends on MMU && SYS_SUPPORTS_NUMA | 109 | depends on MMU && SYS_SUPPORTS_NUMA |
| 110 | select ARCH_WANT_NUMA_VARIABLE_LOCALITY | 110 | select ARCH_WANT_NUMA_VARIABLE_LOCALITY |
| 111 | default n | 111 | default n |
| @@ -26,7 +26,7 @@ · 25 unmodified lines | |||
| 26 | #include <asm/processor.h> | 26 | #include <asm/processor.h> |
| 27 | #include <asm/mmu_context.h> | 27 | #include <asm/mmu_context.h> |
| 28 | 28 | ||
| 29 | static int asids_seq_show(struct seq_file *file, void *iter) | 29 | static int asids_debugfs_show(struct seq_file *file, void *iter) |
| 30 | { | 30 | { |
| 31 | struct task_struct *p; | 31 | struct task_struct *p; |
| 32 | 32 | ||
| @@ -48,18 +48,7 @@ static int asids_seq_show(struct seq_file *file, void *iter) · 15 unmodified lines | |||
| 48 | return 0; | 48 | return 0; |
| 49 | } | 49 | } |
| 50 | 50 | ||
| 51 | static int asids_debugfs_open(struct inode *inode, struct file *file) | 51 | DEFINE_SHOW_ATTRIBUTE(asids_debugfs); |
| 52 | { | ||
| 53 | return single_open(file, asids_seq_show, inode->i_private); | ||
| 54 | } | ||
| 55 | |||
| 56 | static const struct file_operations asids_debugfs_fops = { | ||
| 57 | .owner = THIS_MODULE, | ||
| 58 | .open = asids_debugfs_open, | ||
| 59 | .read = seq_read, | ||
| 60 | .llseek = seq_lseek, | ||
| 61 | .release = single_release, | ||
| 62 | }; | ||
| 63 | 52 | ||
| 64 | static int __init asids_debugfs_init(void) | 53 | static int __init asids_debugfs_init(void) |
| 65 | { | 54 | { |
| @@ -22,7 +22,7 @@ enum cache_type { · 21 unmodified lines | |||
| 22 | CACHE_TYPE_UNIFIED, | 22 | CACHE_TYPE_UNIFIED, |
| 23 | }; | 23 | }; |
| 24 | 24 | ||
| 25 | static int cache_seq_show(struct seq_file *file, void *iter) | 25 | static int cache_debugfs_show(struct seq_file *file, void *iter) |
| 26 | { | 26 | { |
| 27 | unsigned int cache_type = (unsigned int)file->private; | 27 | unsigned int cache_type = (unsigned int)file->private; |
| 28 | struct cache_info *cache; | 28 | struct cache_info *cache; |
| @@ -94,18 +94,7 @@ static int cache_seq_show(struct seq_file *file, void *iter) · 65 unmodified lines | |||
| 94 | return 0; | 94 | return 0; |
| 95 | } | 95 | } |
| 96 | 96 | ||
| 97 | static int cache_debugfs_open(struct inode *inode, struct file *file) | 97 | DEFINE_SHOW_ATTRIBUTE(cache_debugfs); |
| 98 | { | ||
| 99 | return single_open(file, cache_seq_show, inode->i_private); | ||
| 100 | } | ||
| 101 | |||
| 102 | static const struct file_operations cache_debugfs_fops = { | ||
| 103 | .owner = THIS_MODULE, | ||
| 104 | .open = cache_debugfs_open, | ||
| 105 | .read = seq_read, | ||
| 106 | .llseek = seq_lseek, | ||
| 107 | .release = single_release, | ||
| 108 | }; | ||
| 109 | 98 | ||
| 110 | static int __init cache_debugfs_init(void) | 99 | static int __init cache_debugfs_init(void) |
| 111 | { | 100 | { |
| @@ -812,7 +812,7 @@ bool __in_29bit_mode(void) · 811 unmodified lines | |||
| 812 | return (__raw_readl(PMB_PASCR) & PASCR_SE) == 0; | 812 | return (__raw_readl(PMB_PASCR) & PASCR_SE) == 0; |
| 813 | } | 813 | } |
| 814 | 814 | ||
| 815 | static int pmb_seq_show(struct seq_file *file, void *iter) | 815 | static int pmb_debugfs_show(struct seq_file *file, void *iter) |
| 816 | { | 816 | { |
| 817 | int i; | 817 | int i; |
| 818 | 818 | ||
| @@ -846,18 +846,7 @@ static int pmb_seq_show(struct seq_file *file, void *iter) · 27 unmodified lines | |||
| 846 | return 0; | 846 | return 0; |
| 847 | } | 847 | } |
| 848 | 848 | ||
| 849 | static int pmb_debugfs_open(struct inode *inode, struct file *file) | 849 | DEFINE_SHOW_ATTRIBUTE(pmb_debugfs); |
| 850 | { | ||
| 851 | return single_open(file, pmb_seq_show, NULL); | ||
| 852 | } | ||
| 853 | |||
| 854 | static const struct file_operations pmb_debugfs_fops = { | ||
| 855 | .owner = THIS_MODULE, | ||
| 856 | .open = pmb_debugfs_open, | ||
| 857 | .read = seq_read, | ||
| 858 | .llseek = seq_lseek, | ||
| 859 | .release = single_release, | ||
| 860 | }; | ||
| 861 | 850 | ||
| 862 | static int __init pmb_debugfs_init(void) | 851 | static int __init pmb_debugfs_init(void) |
| 863 | { | 852 | { |
| @@ -1,6 +1,4 @@ | |||
| 1 | # SPDX-License-Identifier: GPL-2.0 | 1 | # SPDX-License-Identifier: GPL-2.0 |
| 2 | # User exported sparc header files | ||
| 3 | |||
| 4 | generated-y += syscall_table_32.h | 2 | generated-y += syscall_table_32.h |
| 5 | generated-y += syscall_table_64.h | 3 | generated-y += syscall_table_64.h |
| 6 | generated-y += syscall_table_c32.h | 4 | generated-y += syscall_table_c32.h |
| @@ -50,10 +50,11 @@ extern pte_t *pkmap_page_table; · 49 unmodified lines | |||
| 50 | 50 | ||
| 51 | #define flush_cache_kmaps() flush_cache_all() | 51 | #define flush_cache_kmaps() flush_cache_all() |
| 52 | 52 | ||
| 53 | /* FIXME: Use __flush_tlb_one(vaddr) instead of flush_cache_all() -- Anton */ | 53 | /* FIXME: Use __flush_*_one(vaddr) instead of flush_*_all() -- Anton */ |
| 54 | #define arch_kmap_local_post_map(vaddr, pteval) flush_cache_all() | 54 | #define arch_kmap_local_pre_map(vaddr, pteval) flush_cache_all() |
| 55 | #define arch_kmap_local_post_unmap(vaddr) flush_cache_all() | 55 | #define arch_kmap_local_pre_unmap(vaddr) flush_cache_all() |
| 56 | 56 | #define arch_kmap_local_post_map(vaddr, pteval) flush_tlb_all() | |
| 57 | #define arch_kmap_local_post_unmap(vaddr) flush_tlb_all() | ||
| 57 | 58 | ||
| 58 | #endif /* __KERNEL__ */ | 59 | #endif /* __KERNEL__ */ |
| 59 | 60 | ||
| @@ -15,7 +15,6 @@ config UML · 14 unmodified lines | |||
| 15 | select HAVE_DEBUG_KMEMLEAK | 15 | select HAVE_DEBUG_KMEMLEAK |
| 16 | select HAVE_DEBUG_BUGVERBOSE | 16 | select HAVE_DEBUG_BUGVERBOSE |
| 17 | select NO_DMA | 17 | select NO_DMA |
| 18 | select ARCH_HAS_SET_MEMORY | ||
| 19 | select GENERIC_IRQ_SHOW | 18 | select GENERIC_IRQ_SHOW |
| 20 | select GENERIC_CPU_DEVICES | 19 | select GENERIC_CPU_DEVICES |
| 21 | select HAVE_GCC_PLUGINS | 20 | select HAVE_GCC_PLUGINS |
| @@ -375,11 +375,11 @@ break_loop: · 374 unmodified lines | |||
| 375 | file = NULL; | 375 | file = NULL; |
| 376 | 376 | ||
| 377 | backing_file = strsep(&str, ",:"); | 377 | backing_file = strsep(&str, ",:"); |
| 378 | if (*backing_file == '\0') | 378 | if (backing_file && *backing_file == '\0') |
| 379 | backing_file = NULL; | 379 | backing_file = NULL; |
| 380 | 380 | ||
| 381 | serial = strsep(&str, ",:"); | 381 | serial = strsep(&str, ",:"); |
| 382 | if (*serial == '\0') | 382 | if (serial && *serial == '\0') |
| 383 | serial = NULL; | 383 | serial = NULL; |
| 384 | 384 | ||
| 385 | if (backing_file && ubd_dev->no_cow) { | 385 | if (backing_file && ubd_dev->no_cow) { |
| @@ -1241,7 +1241,7 @@ static int __init ubd_driver_init(void){ · 855 unmodified lines | |||
| 1241 | /* Letting ubd=sync be like using ubd#s= instead of ubd#= is | 1241 | /* Letting ubd=sync be like using ubd#s= instead of ubd#= is |
| 1242 | * enough. So use anyway the io thread. */ | 1242 | * enough. So use anyway the io thread. */ |
| 1243 | } | 1243 | } |
| 1244 | stack = alloc_stack(0); | 1244 | stack = alloc_stack(0, 0); |
| 1245 | io_pid = start_io_thread(stack + PAGE_SIZE - sizeof(void *), | 1245 | io_pid = start_io_thread(stack + PAGE_SIZE - sizeof(void *), |
| 1246 | &thread_fd); | 1246 | &thread_fd); |
| 1247 | if(io_pid < 0){ | 1247 | if(io_pid < 0){ |
| @@ -1084,6 +1084,7 @@ static void virtio_uml_release_dev(struct device *d) · 1083 unmodified lines | |||
| 1084 | } | 1084 | } |
| 1085 | 1085 | ||
| 1086 | os_close_file(vu_dev->sock); | 1086 | os_close_file(vu_dev->sock); |
| 1087 | kfree(vu_dev); | ||
| 1087 | } | 1088 | } |
| 1088 | 1089 | ||
| 1089 | /* Platform device */ | 1090 | /* Platform device */ |
| @@ -1097,7 +1098,7 @@ static int virtio_uml_probe(struct platform_device *pdev) · 7 unmodified lines | |||
| 1097 | if (!pdata) | 1098 | if (!pdata) |
| 1098 | return -EINVAL; | 1099 | return -EINVAL; |
| 1099 | 1100 | ||
| 1100 | vu_dev = devm_kzalloc(&pdev->dev, sizeof(*vu_dev), GFP_KERNEL); | 1101 | vu_dev = kzalloc(sizeof(*vu_dev), GFP_KERNEL); |
| 1101 | if (!vu_dev) | 1102 | if (!vu_dev) |
| 1102 | return -ENOMEM; | 1103 | return -ENOMEM; |
| 1103 | 1104 | ||
| @@ -5,7 +5,7 @@ · 4 unmodified lines | |||
| 5 | #define ioremap ioremap | 5 | #define ioremap ioremap |
| 6 | static inline void __iomem *ioremap(phys_addr_t offset, size_t size) | 6 | static inline void __iomem *ioremap(phys_addr_t offset, size_t size) |
| 7 | { | 7 | { |
| 8 | return (void __iomem *)(unsigned long)offset; | 8 | return NULL; |
| 9 | } | 9 | } |
| 10 | 10 | ||
| 11 | #define iounmap iounmap | 11 | #define iounmap iounmap |
| @@ -55,15 +55,12 @@ extern unsigned long end_iomem; · 54 unmodified lines | |||
| 55 | #define _PAGE_CHG_MASK (PAGE_MASK | _PAGE_ACCESSED | _PAGE_DIRTY) | 55 | #define _PAGE_CHG_MASK (PAGE_MASK | _PAGE_ACCESSED | _PAGE_DIRTY) |
| 56 | #define __PAGE_KERNEL_EXEC \ | 56 | #define __PAGE_KERNEL_EXEC \ |
| 57 | (_PAGE_PRESENT | _PAGE_RW | _PAGE_DIRTY | _PAGE_ACCESSED) | 57 | (_PAGE_PRESENT | _PAGE_RW | _PAGE_DIRTY | _PAGE_ACCESSED) |
| 58 | #define __PAGE_KERNEL_RO \ | ||
| 59 | (_PAGE_PRESENT | _PAGE_DIRTY | _PAGE_ACCESSED) | ||
| 60 | #define PAGE_NONE __pgprot(_PAGE_PROTNONE | _PAGE_ACCESSED) | 58 | #define PAGE_NONE __pgprot(_PAGE_PROTNONE | _PAGE_ACCESSED) |
| 61 | #define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | _PAGE_ACCESSED) | 59 | #define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | _PAGE_ACCESSED) |
| 62 | #define PAGE_COPY __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED) | 60 | #define PAGE_COPY __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED) |
| 63 | #define PAGE_READONLY __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED) | 61 | #define PAGE_READONLY __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED) |
| 64 | #define PAGE_KERNEL __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_DIRTY | _PAGE_ACCESSED) | 62 | #define PAGE_KERNEL __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_DIRTY | _PAGE_ACCESSED) |
| 65 | #define PAGE_KERNEL_EXEC __pgprot(__PAGE_KERNEL_EXEC) | 63 | #define PAGE_KERNEL_EXEC __pgprot(__PAGE_KERNEL_EXEC) |
| 66 | #define PAGE_KERNEL_RO __pgprot(__PAGE_KERNEL_RO) | ||
| 67 | 64 | ||
| 68 | /* | 65 | /* |
| 69 | * The i386 can't do page protection for execute, and considers that the same | 66 | * The i386 can't do page protection for execute, and considers that the same |
| @@ -1 +0,0 @@ | |||
| 1 | #include <asm-generic/set_memory.h> | ||
| @@ -19,7 +19,7 @@ extern int kmalloc_ok; · 18 unmodified lines | |||
| 19 | #define UML_ROUND_UP(addr) \ | 19 | #define UML_ROUND_UP(addr) \ |
| 20 | ((((unsigned long) addr) + PAGE_SIZE - 1) & PAGE_MASK) | 20 | ((((unsigned long) addr) + PAGE_SIZE - 1) & PAGE_MASK) |
| 21 | 21 | ||
| 22 | extern unsigned long alloc_stack(int atomic); | 22 | extern unsigned long alloc_stack(int order, int atomic); |
| 23 | extern void free_stack(unsigned long stack, int order); | 23 | extern void free_stack(unsigned long stack, int order); |
| 24 | 24 | ||
| 25 | struct pt_regs; | 25 | struct pt_regs; |
| @@ -1,6 +1,7 @@ | |||
| 1 | // SPDX-License-Identifier: GPL-2.0 | 1 | // SPDX-License-Identifier: GPL-2.0 |
| 2 | #include <linux/kmsg_dump.h> | 2 | #include <linux/kmsg_dump.h> |
| 3 | #include <linux/console.h> | 3 | #include <linux/console.h> |
| 4 | #include <linux/string.h> | ||
| 4 | #include <shared/init.h> | 5 | #include <shared/init.h> |
| 5 | #include <shared/kern.h> | 6 | #include <shared/kern.h> |
| 6 | #include <os.h> | 7 | #include <os.h> |
| @@ -16,8 +17,12 @@ static void kmsg_dumper_stdout(struct kmsg_dumper *dumper, · 9 unmodified lines | |||
| 16 | if (!console_trylock()) | 17 | if (!console_trylock()) |
| 17 | return; | 18 | return; |
| 18 | 19 | ||
| 19 | for_each_console(con) | 20 | for_each_console(con) { |
| 20 | break; | 21 | if(strcmp(con->name, "tty") == 0 && |
| 22 | (con->flags & (CON_ENABLED | CON_CONSDEV)) != 0) { | ||
| 23 | break; | ||
| 24 | } | ||
| 25 | } | ||
| 21 | 26 | ||
| 22 | console_unlock(); | 27 | console_unlock(); |
| 23 | 28 | ||
| @@ -32,7 +32,6 @@ · 31 unmodified lines | |||
| 32 | #include <os.h> | 32 | #include <os.h> |
| 33 | #include <skas.h> | 33 | #include <skas.h> |
| 34 | #include <linux/time-internal.h> | 34 | #include <linux/time-internal.h> |
| 35 | #include <asm/set_memory.h> | ||
| 36 | 35 | ||
| 37 | /* | 36 | /* |
| 38 | * This is a per-cpu array. A processor only modifies its entry and it only | 37 | * This is a per-cpu array. A processor only modifies its entry and it only |
| @@ -63,18 +62,16 @@ void free_stack(unsigned long stack, int order) · 24 unmodified lines | |||
| 63 | free_pages(stack, order); | 62 | free_pages(stack, order); |
| 64 | } | 63 | } |
| 65 | 64 | ||
| 66 | unsigned long alloc_stack(int atomic) | 65 | unsigned long alloc_stack(int order, int atomic) |
| 67 | { | 66 | { |
| 68 | unsigned long addr; | 67 | unsigned long page; |
| 69 | gfp_t flags = GFP_KERNEL; | 68 | gfp_t flags = GFP_KERNEL; |
| 70 | 69 | ||
| 71 | if (atomic) | 70 | if (atomic) |
| 72 | flags = GFP_ATOMIC; | 71 | flags = GFP_ATOMIC; |
| 73 | addr = __get_free_pages(flags, 1); | 72 | page = __get_free_pages(flags, order); |
| 74 | 73 | ||
| 75 | set_memory_ro(addr, 1); | 74 | return page; |
| 76 | |||
| 77 | return addr + PAGE_SIZE; | ||
| 78 | } | 75 | } |
| 79 | 76 | ||
| 80 | static inline void set_current(struct task_struct *task) | 77 | static inline void set_current(struct task_struct *task) |
| @@ -535,6 +535,31 @@ invalid_number: · 534 unmodified lines | |||
| 535 | 535 | ||
| 536 | return 1; | 536 | return 1; |
| 537 | } | 537 | } |
| 538 | |||
| 539 | static void time_travel_set_start(void) | ||
| 540 | { | ||
| 541 | if (time_travel_start_set) | ||
| 542 | return; | ||
| 543 | |||
| 544 | switch (time_travel_mode) { | ||
| 545 | case TT_MODE_EXTERNAL: | ||
| 546 | time_travel_start = time_travel_ext_req(UM_TIMETRAVEL_GET_TOD, -1); | ||
| 547 | /* controller gave us the *current* time, so adjust by that */ | ||
| 548 | time_travel_ext_get_time(); | ||
| 549 | time_travel_start -= time_travel_time; | ||
| 550 | break; | ||
| 551 | case TT_MODE_INFCPU: | ||
| 552 | case TT_MODE_BASIC: | ||
| 553 | if (!time_travel_start_set) | ||
| 554 | time_travel_start = os_persistent_clock_emulation(); | ||
| 555 | break; | ||
| 556 | case TT_MODE_OFF: | ||
| 557 | /* we just read the host clock with os_persistent_clock_emulation() */ | ||
| 558 | break; | ||
| 559 | } | ||
| 560 | |||
| 561 | time_travel_start_set = true; | ||
| 562 | } | ||
| 538 | #else /* CONFIG_UML_TIME_TRAVEL_SUPPORT */ | 563 | #else /* CONFIG_UML_TIME_TRAVEL_SUPPORT */ |
| 539 | #define time_travel_start_set 0 | 564 | #define time_travel_start_set 0 |
| 540 | #define time_travel_start 0 | 565 | #define time_travel_start 0 |
| @@ -553,6 +578,10 @@ static void time_travel_set_interval(unsigned long long interval) · 12 unmodified lines | |||
| 553 | { | 578 | { |
| 554 | } | 579 | } |
| 555 | 580 | ||
| 581 | static inline void time_travel_set_start(void) | ||
| 582 | { | ||
| 583 | } | ||
| 584 | |||
| 556 | /* fail link if this actually gets used */ | 585 | /* fail link if this actually gets used */ |
| 557 | extern u64 time_travel_ext_req(u32 op, u64 time); | 586 | extern u64 time_travel_ext_req(u32 op, u64 time); |
| 558 | 587 | ||
| @@ -731,6 +760,8 @@ void read_persistent_clock64(struct timespec64 *ts) · 172 unmodified lines | |||
| 731 | { | 760 | { |
| 732 | long long nsecs; | 761 | long long nsecs; |
| 733 | 762 | ||
| 763 | time_travel_set_start(); | ||
| 764 | |||
| 734 | if (time_travel_mode != TT_MODE_OFF) | 765 | if (time_travel_mode != TT_MODE_OFF) |
| 735 | nsecs = time_travel_start + time_travel_time; | 766 | nsecs = time_travel_start + time_travel_time; |
| 736 | else | 767 | else |
| @@ -742,25 +773,6 @@ void read_persistent_clock64(struct timespec64 *ts) · 5 unmodified lines | |||
| 742 | 773 | ||
| 743 | void __init time_init(void) | 774 | void __init time_init(void) |
| 744 | { | 775 | { |
| 745 | #ifdef CONFIG_UML_TIME_TRAVEL_SUPPORT | ||
| 746 | switch (time_travel_mode) { | ||
| 747 | case TT_MODE_EXTERNAL: | ||
| 748 | time_travel_start = time_travel_ext_req(UM_TIMETRAVEL_GET_TOD, -1); | ||
| 749 | /* controller gave us the *current* time, so adjust by that */ | ||
| 750 | time_travel_ext_get_time(); | ||
| 751 | time_travel_start -= time_travel_time; | ||
| 752 | break; | ||
| 753 | case TT_MODE_INFCPU: | ||
| 754 | case TT_MODE_BASIC: | ||
| 755 | if (!time_travel_start_set) | ||
| 756 | time_travel_start = os_persistent_clock_emulation(); | ||
| 757 | break; | ||
| 758 | case TT_MODE_OFF: | ||
| 759 | /* we just read the host clock with os_persistent_clock_emulation() */ | ||
| 760 | break; | ||
| 761 | } | ||
| 762 | #endif | ||
| 763 | |||
| 764 | timer_set_signal_handler(); | 776 | timer_set_signal_handler(); |
| 765 | late_time_init = um_timer_setup; | 777 | late_time_init = um_timer_setup; |
| 766 | } | 778 | } |
| @@ -608,57 +608,3 @@ void force_flush_all(void) · 607 unmodified lines | |||
| 608 | vma = vma->vm_next; | 608 | vma = vma->vm_next; |
| 609 | } | 609 | } |
| 610 | } | 610 | } |
| 611 | |||
| 612 | struct page_change_data { | ||
| 613 | unsigned int set_mask, clear_mask; | ||
| 614 | }; | ||
| 615 | |||
| 616 | static int change_page_range(pte_t *ptep, unsigned long addr, void *data) | ||
| 617 | { | ||
| 618 | struct page_change_data *cdata = data; | ||
| 619 | pte_t pte = READ_ONCE(*ptep); | ||
| 620 | |||
| 621 | pte_clear_bits(pte, cdata->clear_mask); | ||
| 622 | pte_set_bits(pte, cdata->set_mask); | ||
| 623 | |||
| 624 | set_pte(ptep, pte); | ||
| 625 | return 0; | ||
| 626 | } | ||
| 627 | |||
| 628 | static int change_memory(unsigned long start, unsigned long pages, | ||
| 629 | unsigned int set_mask, unsigned int clear_mask) | ||
| 630 | { | ||
| 631 | unsigned long size = pages * PAGE_SIZE; | ||
| 632 | struct page_change_data data; | ||
| 633 | int ret; | ||
| 634 | |||
| 635 | data.set_mask = set_mask; | ||
| 636 | data.clear_mask = clear_mask; | ||
| 637 | |||
| 638 | ret = apply_to_page_range(&init_mm, start, size, change_page_range, | ||
| 639 | &data); | ||
| 640 | |||
| 641 | flush_tlb_kernel_range(start, start + size); | ||
| 642 | |||
| 643 | return ret; | ||
| 644 | } | ||
| 645 | |||
| 646 | int set_memory_ro(unsigned long addr, int numpages) | ||
| 647 | { | ||
| 648 | return change_memory(addr, numpages, 0, _PAGE_RW); | ||
| 649 | } | ||
| 650 | |||
| 651 | int set_memory_rw(unsigned long addr, int numpages) | ||
| 652 | { | ||
| 653 | return change_memory(addr, numpages, _PAGE_RW, 0); | ||
| 654 | } | ||
| 655 | |||
| 656 | int set_memory_nx(unsigned long addr, int numpages) | ||
| 657 | { | ||
| 658 | return -EOPNOTSUPP; | ||
| 659 | } | ||
| 660 | |||
| 661 | int set_memory_x(unsigned long addr, int numpages) | ||
| 662 | { | ||
| 663 | return -EOPNOTSUPP; | ||
| 664 | } | ||
| @@ -26,7 +26,8 @@ · 25 unmodified lines | |||
| 26 | #include <mem_user.h> | 26 | #include <mem_user.h> |
| 27 | #include <os.h> | 27 | #include <os.h> |
| 28 | 28 | ||
| 29 | #define DEFAULT_COMMAND_LINE "root=98:0" | 29 | #define DEFAULT_COMMAND_LINE_ROOT "root=98:0" |
| 30 | #define DEFAULT_COMMAND_LINE_CONSOLE "console=tty" | ||
| 30 | 31 | ||
| 31 | /* Changed in add_arg and setup_arch, which run before SMP is started */ | 32 | /* Changed in add_arg and setup_arch, which run before SMP is started */ |
| 32 | static char __initdata command_line[COMMAND_LINE_SIZE] = { 0 }; | 33 | static char __initdata command_line[COMMAND_LINE_SIZE] = { 0 }; |
| @@ -109,7 +110,8 @@ unsigned long end_vm; · 76 unmodified lines | |||
| 109 | int ncpus = 1; | 110 | int ncpus = 1; |
| 110 | 111 | ||
| 111 | /* Set in early boot */ | 112 | /* Set in early boot */ |
| 112 | static int have_root __initdata = 0; | 113 | static int have_root __initdata; |
| 114 | static int have_console __initdata; | ||
| 113 | 115 | ||
| 114 | /* Set in uml_mem_setup and modified in linux_main */ | 116 | /* Set in uml_mem_setup and modified in linux_main */ |
| 115 | long long physmem_size = 32 * 1024 * 1024; | 117 | long long physmem_size = 32 * 1024 * 1024; |
| @@ -161,6 +163,17 @@ __uml_setup("debug", no_skas_debug_setup, · 45 unmodified lines | |||
| 161 | " this flag is not needed to run gdb on UML in skas mode\n\n" | 163 | " this flag is not needed to run gdb on UML in skas mode\n\n" |
| 162 | ); | 164 | ); |
| 163 | 165 | ||
| 166 | static int __init uml_console_setup(char *line, int *add) | ||
| 167 | { | ||
| 168 | have_console = 1; | ||
| 169 | return 0; | ||
| 170 | } | ||
| 171 | |||
| 172 | __uml_setup("console=", uml_console_setup, | ||
| 173 | "console=<preferred console>\n" | ||
| 174 | " Specify the preferred console output driver\n\n" | ||
| 175 | ); | ||
| 176 | |||
| 164 | static int __init Usage(char *line, int *add) | 177 | static int __init Usage(char *line, int *add) |
| 165 | { | 178 | { |
| 166 | const char **p; | 179 | const char **p; |
| @@ -264,7 +277,10 @@ int __init linux_main(int argc, char **argv) · 97 unmodified lines | |||
| 264 | add_arg(argv[i]); | 277 | add_arg(argv[i]); |
| 265 | } | 278 | } |
| 266 | if (have_root == 0) | 279 | if (have_root == 0) |
| 267 | add_arg(DEFAULT_COMMAND_LINE); | 280 | add_arg(DEFAULT_COMMAND_LINE_ROOT); |
| 281 | |||
| 282 | if (have_console == 0) | ||
| 283 | add_arg(DEFAULT_COMMAND_LINE_CONSOLE); | ||
| 268 | 284 | ||
| 269 | host_task_size = os_get_top_address(); | 285 | host_task_size = os_get_top_address(); |
| 270 | /* | 286 | /* |
| @@ -45,7 +45,7 @@ int run_helper(void (*pre_exec)(void *), void *pre_data, char **argv) · 44 unmodified lines | |||
| 45 | unsigned long stack, sp; | 45 | unsigned long stack, sp; |
| 46 | int pid, fds[2], ret, n; | 46 | int pid, fds[2], ret, n; |
| 47 | 47 | ||
| 48 | stack = alloc_stack(__cant_sleep()); | 48 | stack = alloc_stack(0, __cant_sleep()); |
| 49 | if (stack == 0) | 49 | if (stack == 0) |
| 50 | return -ENOMEM; | 50 | return -ENOMEM; |
| 51 | 51 | ||
| @@ -116,7 +116,7 @@ int run_helper_thread(int (*proc)(void *), void *arg, unsigned int flags, · 64 unmodified lines | |||
| 116 | unsigned long stack, sp; | 116 | unsigned long stack, sp; |
| 117 | int pid, status, err; | 117 | int pid, status, err; |
| 118 | 118 | ||
| 119 | stack = alloc_stack(__cant_sleep()); | 119 | stack = alloc_stack(0, __cant_sleep()); |
| 120 | if (stack == 0) | 120 | if (stack == 0) |
| 121 | return -ENOMEM; | 121 | return -ENOMEM; |
| 122 | 122 | ||
| @@ -104,5 +104,18 @@ long long os_nsecs(void) · 103 unmodified lines | |||
| 104 | */ | 104 | */ |
| 105 | void os_idle_sleep(void) | 105 | void os_idle_sleep(void) |
| 106 | { | 106 | { |
| 107 | pause(); | 107 | struct itimerspec its; |
| 108 | sigset_t set, old; | ||
| 109 | |||
| 110 | /* block SIGALRM while we analyze the timer state */ | ||
| 111 | sigemptyset(&set); | ||
| 112 | sigaddset(&set, SIGALRM); | ||
| 113 | sigprocmask(SIG_BLOCK, &set, &old); | ||
| 114 | |||
| 115 | /* check the timer, and if it'll fire then wait for it */ | ||
| 116 | timer_gettime(event_high_res_timer, &its); | ||
| 117 | if (its.it_value.tv_sec || its.it_value.tv_nsec) | ||
| 118 | sigsuspend(&old); | ||
| 119 | /* either way, restore the signal mask */ | ||
| 120 | sigprocmask(SIG_UNBLOCK, &set, NULL); | ||
| 108 | } | 121 | } |
| @@ -19,6 +19,7 @@ config X86_32 · 18 unmodified lines | |||
| 19 | select KMAP_LOCAL | 19 | select KMAP_LOCAL |
| 20 | select MODULES_USE_ELF_REL | 20 | select MODULES_USE_ELF_REL |
| 21 | select OLD_SIGACTION | 21 | select OLD_SIGACTION |
| 22 | select ARCH_SPLIT_ARG64 | ||
| 22 | 23 | ||
| 23 | config X86_64 | 24 | config X86_64 |
| 24 | def_bool y | 25 | def_bool y |
| @@ -50,6 +50,9 @@ export BITS · 49 unmodified lines | |||
| 50 | KBUILD_CFLAGS += -mno-sse -mno-mmx -mno-sse2 -mno-3dnow | 50 | KBUILD_CFLAGS += -mno-sse -mno-mmx -mno-sse2 -mno-3dnow |
| 51 | KBUILD_CFLAGS += $(call cc-option,-mno-avx,) | 51 | KBUILD_CFLAGS += $(call cc-option,-mno-avx,) |
| 52 | 52 | ||
| 53 | # Intel CET isn't enabled in the kernel | ||
| 54 | KBUILD_CFLAGS += $(call cc-option,-fcf-protection=none) | ||
| 55 | |||
| 53 | ifeq ($(CONFIG_X86_32),y) | 56 | ifeq ($(CONFIG_X86_32),y) |
| 54 | BITS := 32 | 57 | BITS := 32 |
| 55 | UTS_MACHINE := i386 | 58 | UTS_MACHINE := i386 |
| @@ -73,10 +73,8 @@ static __always_inline void do_syscall_32_irqs_on(struct pt_regs *regs, · 72 unmodified lines | |||
| 73 | unsigned int nr) | 73 | unsigned int nr) |
| 74 | { | 74 | { |
| 75 | if (likely(nr < IA32_NR_syscalls)) { | 75 | if (likely(nr < IA32_NR_syscalls)) { |
| 76 | instrumentation_begin(); | ||
| 77 | nr = array_index_nospec(nr, IA32_NR_syscalls); | 76 | nr = array_index_nospec(nr, IA32_NR_syscalls); |
| 78 | regs->ax = ia32_sys_call_table[nr](regs); | 77 | regs->ax = ia32_sys_call_table[nr](regs); |
| 79 | instrumentation_end(); | ||
| 80 | } | 78 | } |
| 81 | } | 79 | } |
| 82 | 80 | ||
| @@ -91,8 +89,11 @@ __visible noinstr void do_int80_syscall_32(struct pt_regs *regs) · 8 unmodified lines | |||
| 91 | * or may not be necessary, but it matches the old asm behavior. | 89 | * or may not be necessary, but it matches the old asm behavior. |
| 92 | */ | 90 | */ |
| 93 | nr = (unsigned int)syscall_enter_from_user_mode(regs, nr); | 91 | nr = (unsigned int)syscall_enter_from_user_mode(regs, nr); |
| 92 | instrumentation_begin(); | ||
| 94 | 93 | ||
| 95 | do_syscall_32_irqs_on(regs, nr); | 94 | do_syscall_32_irqs_on(regs, nr); |
| 95 | |||
| 96 | instrumentation_end(); | ||
| 96 | syscall_exit_to_user_mode(regs); | 97 | syscall_exit_to_user_mode(regs); |
| 97 | } | 98 | } |
| 98 | 99 | ||
| @@ -121,11 +122,12 @@ static noinstr bool __do_fast_syscall_32(struct pt_regs *regs) · 22 unmodified lines | |||
| 121 | res = get_user(*(u32 *)®s->bp, | 122 | res = get_user(*(u32 *)®s->bp, |
| 122 | (u32 __user __force *)(unsigned long)(u32)regs->sp); | 123 | (u32 __user __force *)(unsigned long)(u32)regs->sp); |
| 123 | } | 124 | } |
| 124 | instrumentation_end(); | ||
| 125 | 125 | ||
| 126 | if (res) { | 126 | if (res) { |
| 127 | /* User code screwed up. */ | 127 | /* User code screwed up. */ |
| 128 | regs->ax = -EFAULT; | 128 | regs->ax = -EFAULT; |
| 129 | |||
| 130 | instrumentation_end(); | ||
| 129 | syscall_exit_to_user_mode(regs); | 131 | syscall_exit_to_user_mode(regs); |
| 130 | return false; | 132 | return false; |
| 131 | } | 133 | } |
| @@ -135,6 +137,8 @@ static noinstr bool __do_fast_syscall_32(struct pt_regs *regs) · 3 unmodified lines | |||
| 135 | 137 | ||
| 136 | /* Now this is just like a normal syscall. */ | 138 | /* Now this is just like a normal syscall. */ |
| 137 | do_syscall_32_irqs_on(regs, nr); | 139 | do_syscall_32_irqs_on(regs, nr); |
| 140 | |||
| 141 | instrumentation_end(); | ||
| 138 | syscall_exit_to_user_mode(regs); | 142 | syscall_exit_to_user_mode(regs); |
| 139 | return true; | 143 | return true; |
| 140 | } | 144 | } |
| @@ -10,7 +10,7 @@ · 9 unmodified lines | |||
| 10 | #include <asm/export.h> | 10 | #include <asm/export.h> |
| 11 | 11 | ||
| 12 | /* rdi: arg1 ... normal C conventions. rax is saved/restored. */ | 12 | /* rdi: arg1 ... normal C conventions. rax is saved/restored. */ |
| 13 | .macro THUNK name, func, put_ret_addr_in_rdi=0 | 13 | .macro THUNK name, func |
| 14 | SYM_FUNC_START_NOALIGN(\name) | 14 | SYM_FUNC_START_NOALIGN(\name) |
| 15 | pushq %rbp | 15 | pushq %rbp |
| 16 | movq %rsp, %rbp | 16 | movq %rsp, %rbp |
| @@ -25,13 +25,8 @@ SYM_FUNC_START_NOALIGN(\name) · 8 unmodified lines | |||
| 25 | pushq %r10 | 25 | pushq %r10 |
| 26 | pushq %r11 | 26 | pushq %r11 |
| 27 | 27 | ||
| 28 | .if \put_ret_addr_in_rdi | ||
| 29 | /* 8(%rbp) is return addr on stack */ | ||
| 30 | movq 8(%rbp), %rdi | ||
| 31 | .endif | ||
| 32 | |||
| 33 | call \func | 28 | call \func |
| 34 | jmp .L_restore | 29 | jmp __thunk_restore |
| 35 | SYM_FUNC_END(\name) | 30 | SYM_FUNC_END(\name) |
| 36 | _ASM_NOKPROBE(\name) | 31 | _ASM_NOKPROBE(\name) |
| 37 | .endm | 32 | .endm |
| @@ -44,7 +39,7 @@ SYM_FUNC_END(\name) · 6 unmodified lines | |||
| 44 | #endif | 39 | #endif |
| 45 | 40 | ||
| 46 | #ifdef CONFIG_PREEMPTION | 41 | #ifdef CONFIG_PREEMPTION |
| 47 | SYM_CODE_START_LOCAL_NOALIGN(.L_restore) | 42 | SYM_CODE_START_LOCAL_NOALIGN(__thunk_restore) |
| 48 | popq %r11 | 43 | popq %r11 |
| 49 | popq %r10 | 44 | popq %r10 |
| 50 | popq %r9 | 45 | popq %r9 |
| @@ -56,6 +51,6 @@ SYM_CODE_START_LOCAL_NOALIGN(.L_restore) · 5 unmodified lines | |||
| 56 | popq %rdi | 51 | popq %rdi |
| 57 | popq %rbp | 52 | popq %rbp |
| 58 | ret | 53 | ret |
| 59 | _ASM_NOKPROBE(.L_restore) | 54 | _ASM_NOKPROBE(__thunk_restore) |
| 60 | SYM_CODE_END(.L_restore) | 55 | SYM_CODE_END(__thunk_restore) |
| 61 | #endif | 56 | #endif |
| @@ -16,6 +16,7 @@ · 15 unmodified lines | |||
| 16 | #include <asm/hyperv-tlfs.h> | 16 | #include <asm/hyperv-tlfs.h> |
| 17 | #include <asm/mshyperv.h> | 17 | #include <asm/mshyperv.h> |
| 18 | #include <asm/idtentry.h> | 18 | #include <asm/idtentry.h> |
| 19 | #include <linux/kexec.h> | ||
| 19 | #include <linux/version.h> | 20 | #include <linux/version.h> |
| 20 | #include <linux/vmalloc.h> | 21 | #include <linux/vmalloc.h> |
| 21 | #include <linux/mm.h> | 22 | #include <linux/mm.h> |
| @@ -26,6 +27,8 @@ · 4 unmodified lines | |||
| 26 | #include <linux/syscore_ops.h> | 27 | #include <linux/syscore_ops.h> |
| 27 | #include <clocksource/hyperv_timer.h> | 28 | #include <clocksource/hyperv_timer.h> |
| 28 | 29 | ||
| 30 | int hyperv_init_cpuhp; | ||
| 31 | |||
| 29 | void *hv_hypercall_pg; | 32 | void *hv_hypercall_pg; |
| 30 | EXPORT_SYMBOL_GPL(hv_hypercall_pg); | 33 | EXPORT_SYMBOL_GPL(hv_hypercall_pg); |
| 31 | 34 | ||
| @@ -312,6 +315,25 @@ static struct syscore_ops hv_syscore_ops = { · 280 unmodified lines | |||
| 312 | .resume = hv_resume, | 315 | .resume = hv_resume, |
| 313 | }; | 316 | }; |
| 314 | 317 | ||
| 318 | static void (* __initdata old_setup_percpu_clockev)(void); | ||
| 319 | |||
| 320 | static void __init hv_stimer_setup_percpu_clockev(void) | ||
| 321 | { | ||
| 322 | /* | ||
| 323 | * Ignore any errors in setting up stimer clockevents | ||
| 324 | * as we can run with the LAPIC timer as a fallback. | ||
| 325 | */ | ||
| 326 | (void)hv_stimer_alloc(); | ||
| 327 | |||
| 328 | /* | ||
| 329 | * Still register the LAPIC timer, because the direct-mode STIMER is | ||
| 330 | * not supported by old versions of Hyper-V. This also allows users | ||
| 331 | * to switch to LAPIC timer via /sys, if they want to. | ||
| 332 | */ | ||
| 333 | if (old_setup_percpu_clockev) | ||
| 334 | old_setup_percpu_clockev(); | ||
| 335 | } | ||
| 336 | |||
| 315 | /* | 337 | /* |
| 316 | * This function is to be invoked early in the boot sequence after the | 338 | * This function is to be invoked early in the boot sequence after the |
| 317 | * hypervisor has been detected. | 339 | * hypervisor has been detected. |
| @@ -390,10 +412,14 @@ void __init hyperv_init(void) · 72 unmodified lines | |||
| 390 | wrmsrl(HV_X64_MSR_HYPERCALL, hypercall_msr.as_uint64); | 412 | wrmsrl(HV_X64_MSR_HYPERCALL, hypercall_msr.as_uint64); |
| 391 | 413 | ||
| 392 | /* | 414 | /* |
| 393 | * Ignore any errors in setting up stimer clockevents | 415 | * hyperv_init() is called before LAPIC is initialized: see |
| 394 | * as we can run with the LAPIC timer as a fallback. | 416 | * apic_intr_mode_init() -> x86_platform.apic_post_init() and |
| 417 | * apic_bsp_setup() -> setup_local_APIC(). The direct-mode STIMER | ||
| 418 | * depends on LAPIC, so hv_stimer_alloc() should be called from | ||
| 419 | * x86_init.timers.setup_percpu_clockev. | ||
| 395 | */ | 420 | */ |
| 396 | (void)hv_stimer_alloc(); | 421 | old_setup_percpu_clockev = x86_init.timers.setup_percpu_clockev; |
| 422 | x86_init.timers.setup_percpu_clockev = hv_stimer_setup_percpu_clockev; | ||
| 397 | 423 | ||
| 398 | hv_apic_init(); | 424 | hv_apic_init(); |
| 399 | 425 | ||
| @@ -401,6 +427,7 @@ void __init hyperv_init(void) · 1 unmodified line | |||
| 401 | 427 | ||
| 402 | register_syscore_ops(&hv_syscore_ops); | 428 | register_syscore_ops(&hv_syscore_ops); |
| 403 | 429 | ||
| 430 | hyperv_init_cpuhp = cpuhp; | ||
| 404 | return; | 431 | return; |
| 405 | 432 | ||
| 406 | remove_cpuhp_state: | 433 | remove_cpuhp_state: |
| @@ -66,11 +66,17 @@ static void hyperv_flush_tlb_others(const struct cpumask *cpus, · 65 unmodified lines | |||
| 66 | if (!hv_hypercall_pg) | 66 | if (!hv_hypercall_pg) |
| 67 | goto do_native; | 67 | goto do_native; |
| 68 | 68 | ||
| 69 | if (cpumask_empty(cpus)) | ||
| 70 | return; | ||
| 71 | |||
| 72 | local_irq_save(flags); | 69 | local_irq_save(flags); |
| 73 | 70 | ||
| 71 | /* | ||
| 72 | * Only check the mask _after_ interrupt has been disabled to avoid the | ||
| 73 | * mask changing under our feet. | ||
| 74 | */ | ||
| 75 | if (cpumask_empty(cpus)) { | ||
| 76 | local_irq_restore(flags); | ||
| 77 | return; | ||
| 78 | } | ||
| 79 | |||
| 74 | flush_pcpu = (struct hv_tlb_flush **) | 80 | flush_pcpu = (struct hv_tlb_flush **) |
| 75 | this_cpu_ptr(hyperv_pcpu_input_arg); | 81 | this_cpu_ptr(hyperv_pcpu_input_arg); |
| 76 | 82 | ||
| @@ -197,16 +197,6 @@ static inline bool apic_needs_pit(void) { return true; } · 196 unmodified lines | |||
| 197 | #endif /* !CONFIG_X86_LOCAL_APIC */ | 197 | #endif /* !CONFIG_X86_LOCAL_APIC */ |
| 198 | 198 | ||
| 199 | #ifdef CONFIG_X86_X2APIC | 199 | #ifdef CONFIG_X86_X2APIC |
| 200 | /* | ||
| 201 | * Make previous memory operations globally visible before | ||
| 202 | * sending the IPI through x2apic wrmsr. We need a serializing instruction or | ||
| 203 | * mfence for this. | ||
| 204 | */ | ||
| 205 | static inline void x2apic_wrmsr_fence(void) | ||
| 206 | { | ||
| 207 | asm volatile("mfence" : : : "memory"); | ||
| 208 | } | ||
| 209 | |||
| 210 | static inline void native_apic_msr_write(u32 reg, u32 v) | 200 | static inline void native_apic_msr_write(u32 reg, u32 v) |
| 211 | { | 201 | { |
| 212 | if (reg == APIC_DFR || reg == APIC_ID || reg == APIC_LDR || | 202 | if (reg == APIC_DFR || reg == APIC_ID || reg == APIC_LDR || |
| @@ -84,4 +84,22 @@ do { \ · 83 unmodified lines | |||
| 84 | 84 | ||
| 85 | #include <asm-generic/barrier.h> | 85 | #include <asm-generic/barrier.h> |
| 86 | 86 | ||
| 87 | /* | ||
| 88 | * Make previous memory operations globally visible before | ||
| 89 | * a WRMSR. | ||
| 90 | * | ||
| 91 | * MFENCE makes writes visible, but only affects load/store | ||
| 92 | * instructions. WRMSR is unfortunately not a load/store | ||
| 93 | * instruction and is unaffected by MFENCE. The LFENCE ensures | ||
| 94 | * that the WRMSR is not reordered. | ||
| 95 | * | ||
| 96 | * Most WRMSRs are full serializing instructions themselves and | ||
| 97 | * do not require this barrier. This is only required for the | ||
| 98 | * IA32_TSC_DEADLINE and X2APIC MSRs. | ||
| 99 | */ | ||
| 100 | static inline void weak_wrmsr_fence(void) | ||
| 101 | { | ||
| 102 | asm volatile("mfence; lfence" : : : "memory"); | ||
| 103 | } | ||
| 104 | |||
| 87 | #endif /* _ASM_X86_BARRIER_H */ | 105 | #endif /* _ASM_X86_BARRIER_H */ |
| @@ -43,8 +43,6 @@ static __always_inline void arch_check_user_regs(struct pt_regs *regs) · 42 unmodified lines | |||
| 43 | } | 43 | } |
| 44 | #define arch_check_user_regs arch_check_user_regs | 44 | #define arch_check_user_regs arch_check_user_regs |
| 45 | 45 | ||
| 46 | #define ARCH_SYSCALL_EXIT_WORK (_TIF_SINGLESTEP) | ||
| 47 | |||
| 48 | static inline void arch_exit_to_user_mode_prepare(struct pt_regs *regs, | 46 | static inline void arch_exit_to_user_mode_prepare(struct pt_regs *regs, |
| 49 | unsigned long ti_work) | 47 | unsigned long ti_work) |
| 50 | { | 48 | { |
| @@ -16,14 +16,25 @@ · 15 unmodified lines | |||
| 16 | * Use kernel_fpu_begin/end() if you intend to use FPU in kernel context. It | 16 | * Use kernel_fpu_begin/end() if you intend to use FPU in kernel context. It |
| 17 | * disables preemption so be careful if you intend to use it for long periods | 17 | * disables preemption so be careful if you intend to use it for long periods |
| 18 | * of time. | 18 | * of time. |
| 19 | * If you intend to use the FPU in softirq you need to check first with | 19 | * If you intend to use the FPU in irq/softirq you need to check first with |
| 20 | * irq_fpu_usable() if it is possible. | 20 | * irq_fpu_usable() if it is possible. |
| 21 | */ | 21 | */ |
| 22 | extern void kernel_fpu_begin(void); | 22 | |
| 23 | /* Kernel FPU states to initialize in kernel_fpu_begin_mask() */ | ||
| 24 | #define KFPU_387 _BITUL(0) /* 387 state will be initialized */ | ||
| 25 | #define KFPU_MXCSR _BITUL(1) /* MXCSR will be initialized */ | ||
| 26 | |||
| 27 | extern void kernel_fpu_begin_mask(unsigned int kfpu_mask); | ||
| 23 | extern void kernel_fpu_end(void); | 28 | extern void kernel_fpu_end(void); |
| 24 | extern bool irq_fpu_usable(void); | 29 | extern bool irq_fpu_usable(void); |
| 25 | extern void fpregs_mark_activate(void); | 30 | extern void fpregs_mark_activate(void); |
| 26 | 31 | ||
| 32 | /* Code that is unaware of kernel_fpu_begin_mask() can use this */ | ||
| 33 | static inline void kernel_fpu_begin(void) | ||
| 34 | { | ||
| 35 | kernel_fpu_begin_mask(KFPU_387 | KFPU_MXCSR); | ||
| 36 | } | ||
| 37 | |||
| 27 | /* | 38 | /* |
| 28 | * Use fpregs_lock() while editing CPU's FPU registers or fpu->state. | 39 | * Use fpregs_lock() while editing CPU's FPU registers or fpu->state. |
| 29 | * A context switch will (and softirq might) save CPU's FPU registers to | 40 | * A context switch will (and softirq might) save CPU's FPU registers to |
| @@ -613,6 +613,7 @@ DECLARE_IDTENTRY_VC(X86_TRAP_VC, exc_vmm_communication); · 612 unmodified lines | |||
| 613 | 613 | ||
| 614 | #ifdef CONFIG_XEN_PV | 614 | #ifdef CONFIG_XEN_PV |
| 615 | DECLARE_IDTENTRY_XENCB(X86_TRAP_OTHER, exc_xen_hypervisor_callback); | 615 | DECLARE_IDTENTRY_XENCB(X86_TRAP_OTHER, exc_xen_hypervisor_callback); |
| 616 | DECLARE_IDTENTRY_RAW(X86_TRAP_OTHER, exc_xen_unknown_trap); | ||
| 616 | #endif | 617 | #endif |
| 617 | 618 | ||
| 618 | /* Device interrupts common/spurious */ | 619 | /* Device interrupts common/spurious */ |
| @@ -97,6 +97,7 @@ · 96 unmodified lines | |||
| 97 | 97 | ||
| 98 | #define INTEL_FAM6_LAKEFIELD 0x8A | 98 | #define INTEL_FAM6_LAKEFIELD 0x8A |
| 99 | #define INTEL_FAM6_ALDERLAKE 0x97 | 99 | #define INTEL_FAM6_ALDERLAKE 0x97 |
| 100 | #define INTEL_FAM6_ALDERLAKE_L 0x9A | ||
| 100 | 101 | ||
| 101 | /* "Small Core" Processors (Atom) */ | 102 | /* "Small Core" Processors (Atom) */ |
| 102 | 103 | ||
| @@ -1010,9 +1010,21 @@ struct kvm_arch { · 1009 unmodified lines | |||
| 1010 | */ | 1010 | */ |
| 1011 | bool tdp_mmu_enabled; | 1011 | bool tdp_mmu_enabled; |
| 1012 | 1012 | ||
| 1013 | /* List of struct tdp_mmu_pages being used as roots */ | 1013 | /* |
| 1014 | * List of struct kvmp_mmu_pages being used as roots. | ||
| 1015 | * All struct kvm_mmu_pages in the list should have | ||
| 1016 | * tdp_mmu_page set. | ||
| 1017 | * All struct kvm_mmu_pages in the list should have a positive | ||
| 1018 | * root_count except when a thread holds the MMU lock and is removing | ||
| 1019 | * an entry from the list. | ||
| 1020 | */ | ||
| 1014 | struct list_head tdp_mmu_roots; | 1021 | struct list_head tdp_mmu_roots; |
| 1015 | /* List of struct tdp_mmu_pages not being used as roots */ | 1022 | |
| 1023 | /* | ||
| 1024 | * List of struct kvmp_mmu_pages not being used as roots. | ||
| 1025 | * All struct kvm_mmu_pages in the list should have | ||
| 1026 | * tdp_mmu_page set and a root_count of 0. | ||
| 1027 | */ | ||
| 1016 | struct list_head tdp_mmu_pages; | 1028 | struct list_head tdp_mmu_pages; |
| 1017 | }; | 1029 | }; |
| 1018 | 1030 | ||
| @@ -1287,6 +1299,8 @@ struct kvm_x86_ops { · 268 unmodified lines | |||
| 1287 | void (*migrate_timers)(struct kvm_vcpu *vcpu); | 1299 | void (*migrate_timers)(struct kvm_vcpu *vcpu); |
| 1288 | void (*msr_filter_changed)(struct kvm_vcpu *vcpu); | 1300 | void (*msr_filter_changed)(struct kvm_vcpu *vcpu); |
| 1289 | int (*complete_emulated_msr)(struct kvm_vcpu *vcpu, int err); | 1301 | int (*complete_emulated_msr)(struct kvm_vcpu *vcpu, int err); |
| 1302 | |||
| 1303 | void (*vcpu_deliver_sipi_vector)(struct kvm_vcpu *vcpu, u8 vector); | ||
| 1290 | }; | 1304 | }; |
| 1291 | 1305 | ||
| 1292 | struct kvm_x86_nested_ops { | 1306 | struct kvm_x86_nested_ops { |
| @@ -1468,6 +1482,7 @@ int kvm_fast_pio(struct kvm_vcpu *vcpu, int size, unsigned short port, int in); · 175 unmodified lines | |||
| 1468 | int kvm_emulate_cpuid(struct kvm_vcpu *vcpu); | 1482 | int kvm_emulate_cpuid(struct kvm_vcpu *vcpu); |
| 1469 | int kvm_emulate_halt(struct kvm_vcpu *vcpu); | 1483 | int kvm_emulate_halt(struct kvm_vcpu *vcpu); |
| 1470 | int kvm_vcpu_halt(struct kvm_vcpu *vcpu); | 1484 | int kvm_vcpu_halt(struct kvm_vcpu *vcpu); |
| 1485 | int kvm_emulate_ap_reset_hold(struct kvm_vcpu *vcpu); | ||
| 1471 | int kvm_emulate_wbinvd(struct kvm_vcpu *vcpu); | 1486 | int kvm_emulate_wbinvd(struct kvm_vcpu *vcpu); |
| 1472 | 1487 | ||
| 1473 | void kvm_get_segment(struct kvm_vcpu *vcpu, struct kvm_segment *var, int seg); | 1488 | void kvm_get_segment(struct kvm_vcpu *vcpu, struct kvm_segment *var, int seg); |
| @@ -74,6 +74,8 @@ static inline void hv_disable_stimer0_percpu_irq(int irq) {} · 73 unmodified lines | |||
| 74 | 74 | ||
| 75 | 75 | ||
| 76 | #if IS_ENABLED(CONFIG_HYPERV) | 76 | #if IS_ENABLED(CONFIG_HYPERV) |
| 77 | extern int hyperv_init_cpuhp; | ||
| 78 | |||
| 77 | extern void *hv_hypercall_pg; | 79 | extern void *hv_hypercall_pg; |
| 78 | extern void __percpu **hyperv_pcpu_input_arg; | 80 | extern void __percpu **hyperv_pcpu_input_arg; |
| 79 | 81 | ||
| @@ -86,7 +86,7 @@ static inline void do_trace_rdpmc(unsigned int msr, u64 val, int failed) {} · 85 unmodified lines | |||
| 86 | * think of extending them - you will be slapped with a stinking trout or a frozen | 86 | * think of extending them - you will be slapped with a stinking trout or a frozen |
| 87 | * shark will reach you, wherever you are! You've been warned. | 87 | * shark will reach you, wherever you are! You've been warned. |
| 88 | */ | 88 | */ |
| 89 | static inline unsigned long long notrace __rdmsr(unsigned int msr) | 89 | static __always_inline unsigned long long __rdmsr(unsigned int msr) |
| 90 | { | 90 | { |
| 91 | DECLARE_ARGS(val, low, high); | 91 | DECLARE_ARGS(val, low, high); |
| 92 | 92 | ||
| @@ -98,7 +98,7 @@ static inline unsigned long long notrace __rdmsr(unsigned int msr) · 5 unmodified lines | |||
| 98 | return EAX_EDX_VAL(val, low, high); | 98 | return EAX_EDX_VAL(val, low, high); |
| 99 | } | 99 | } |
| 100 | 100 | ||
| 101 | static inline void notrace __wrmsr(unsigned int msr, u32 low, u32 high) | 101 | static __always_inline void __wrmsr(unsigned int msr, u32 low, u32 high) |
| 102 | { | 102 | { |
| 103 | asm volatile("1: wrmsr\n" | 103 | asm volatile("1: wrmsr\n" |
| 104 | "2:\n" | 104 | "2:\n" |
| @@ -110,6 +110,8 @@ extern const struct cpumask *cpu_coregroup_mask(int cpu); · 109 unmodified lines | |||
| 110 | #define topology_die_id(cpu) (cpu_data(cpu).cpu_die_id) | 110 | #define topology_die_id(cpu) (cpu_data(cpu).cpu_die_id) |
| 111 | #define topology_core_id(cpu) (cpu_data(cpu).cpu_core_id) | 111 | #define topology_core_id(cpu) (cpu_data(cpu).cpu_core_id) |
| 112 | 112 | ||
| 113 | extern unsigned int __max_die_per_package; | ||
| 114 | |||
| 113 | #ifdef CONFIG_SMP | 115 | #ifdef CONFIG_SMP |
| 114 | #define topology_die_cpumask(cpu) (per_cpu(cpu_die_map, cpu)) | 116 | #define topology_die_cpumask(cpu) (per_cpu(cpu_die_map, cpu)) |
| 115 | #define topology_core_cpumask(cpu) (per_cpu(cpu_core_map, cpu)) | 117 | #define topology_core_cpumask(cpu) (per_cpu(cpu_core_map, cpu)) |
| @@ -118,8 +120,6 @@ extern const struct cpumask *cpu_coregroup_mask(int cpu); · 2 unmodified lines | |||
| 118 | extern unsigned int __max_logical_packages; | 120 | extern unsigned int __max_logical_packages; |
| 119 | #define topology_max_packages() (__max_logical_packages) | 121 | #define topology_max_packages() (__max_logical_packages) |
| 120 | 122 | ||
| 121 | extern unsigned int __max_die_per_package; | ||
| 122 | |||
| 123 | static inline int topology_max_die_per_package(void) | 123 | static inline int topology_max_die_per_package(void) |
| 124 | { | 124 | { |
| 125 | return __max_die_per_package; | 125 | return __max_die_per_package; |
| @@ -41,6 +41,7 @@ · 40 unmodified lines | |||
| 41 | #include <asm/perf_event.h> | 41 | #include <asm/perf_event.h> |
| 42 | #include <asm/x86_init.h> | 42 | #include <asm/x86_init.h> |
| 43 | #include <linux/atomic.h> | 43 | #include <linux/atomic.h> |
| 44 | #include <asm/barrier.h> | ||
| 44 | #include <asm/mpspec.h> | 45 | #include <asm/mpspec.h> |
| 45 | #include <asm/i8259.h> | 46 | #include <asm/i8259.h> |
| 46 | #include <asm/proto.h> | 47 | #include <asm/proto.h> |
| @@ -477,6 +478,9 @@ static int lapic_next_deadline(unsigned long delta, · 430 unmodified lines | |||
| 477 | { | 478 | { |
| 478 | u64 tsc; | 479 | u64 tsc; |
| 479 | 480 | ||
| 481 | /* This MSR is special and need a special fence: */ | ||
| 482 | weak_wrmsr_fence(); | ||
| 483 | |||
| 480 | tsc = rdtsc(); | 484 | tsc = rdtsc(); |
| 481 | wrmsrl(MSR_IA32_TSC_DEADLINE, tsc + (((u64) delta) * TSC_DIVISOR)); | 485 | wrmsrl(MSR_IA32_TSC_DEADLINE, tsc + (((u64) delta) * TSC_DIVISOR)); |
| 482 | return 0; | 486 | return 0; |
| @@ -29,7 +29,8 @@ static void x2apic_send_IPI(int cpu, int vector) · 28 unmodified lines | |||
| 29 | { | 29 | { |
| 30 | u32 dest = per_cpu(x86_cpu_to_logical_apicid, cpu); | 30 | u32 dest = per_cpu(x86_cpu_to_logical_apicid, cpu); |
| 31 | 31 | ||
| 32 | x2apic_wrmsr_fence(); | 32 | /* x2apic MSRs are special and need a special fence: */ |
| 33 | weak_wrmsr_fence(); | ||
| 33 | __x2apic_send_IPI_dest(dest, vector, APIC_DEST_LOGICAL); | 34 | __x2apic_send_IPI_dest(dest, vector, APIC_DEST_LOGICAL); |
| 34 | } | 35 | } |
| 35 | 36 | ||
| @@ -41,7 +42,8 @@ __x2apic_send_IPI_mask(const struct cpumask *mask, int vector, int apic_dest) · 5 unmodified lines | |||
| 41 | unsigned long flags; | 42 | unsigned long flags; |
| 42 | u32 dest; | 43 | u32 dest; |
| 43 | 44 | ||
| 44 | x2apic_wrmsr_fence(); | 45 | /* x2apic MSRs are special and need a special fence: */ |
| 46 | weak_wrmsr_fence(); | ||
| 45 | local_irq_save(flags); | 47 | local_irq_save(flags); |
| 46 | 48 | ||
| 47 | tmpmsk = this_cpu_cpumask_var_ptr(ipi_mask); | 49 | tmpmsk = this_cpu_cpumask_var_ptr(ipi_mask); |
| @@ -43,7 +43,8 @@ static void x2apic_send_IPI(int cpu, int vector) · 42 unmodified lines | |||
| 43 | { | 43 | { |
| 44 | u32 dest = per_cpu(x86_cpu_to_apicid, cpu); | 44 | u32 dest = per_cpu(x86_cpu_to_apicid, cpu); |
| 45 | 45 | ||
| 46 | x2apic_wrmsr_fence(); | 46 | /* x2apic MSRs are special and need a special fence: */ |
| 47 | weak_wrmsr_fence(); | ||
| 47 | __x2apic_send_IPI_dest(dest, vector, APIC_DEST_PHYSICAL); | 48 | __x2apic_send_IPI_dest(dest, vector, APIC_DEST_PHYSICAL); |
| 48 | } | 49 | } |
| 49 | 50 | ||
| @@ -54,7 +55,8 @@ __x2apic_send_IPI_mask(const struct cpumask *mask, int vector, int apic_dest) · 4 unmodified lines | |||
| 54 | unsigned long this_cpu; | 55 | unsigned long this_cpu; |
| 55 | unsigned long flags; | 56 | unsigned long flags; |
| 56 | 57 | ||
| 57 | x2apic_wrmsr_fence(); | 58 | /* x2apic MSRs are special and need a special fence: */ |
| 59 | weak_wrmsr_fence(); | ||
| 58 | 60 | ||
| 59 | local_irq_save(flags); | 61 | local_irq_save(flags); |
| 60 | 62 | ||
| @@ -125,7 +127,8 @@ void __x2apic_send_IPI_shorthand(int vector, u32 which) · 64 unmodified lines | |||
| 125 | { | 127 | { |
| 126 | unsigned long cfg = __prepare_ICR(which, vector, 0); | 128 | unsigned long cfg = __prepare_ICR(which, vector, 0); |
| 127 | 129 | ||
| 128 | x2apic_wrmsr_fence(); | 130 | /* x2apic MSRs are special and need a special fence: */ |
| 131 | weak_wrmsr_fence(); | ||
| 129 | native_x2apic_icr_write(cfg, 0); | 132 | native_x2apic_icr_write(cfg, 0); |
| 130 | } | 133 | } |
| 131 | 134 | ||
| @@ -542,12 +542,12 @@ static void bsp_init_amd(struct cpuinfo_x86 *c) · 541 unmodified lines | |||
| 542 | u32 ecx; | 542 | u32 ecx; |
| 543 | 543 | ||
| 544 | ecx = cpuid_ecx(0x8000001e); | 544 | ecx = cpuid_ecx(0x8000001e); |
| 545 | nodes_per_socket = ((ecx >> 8) & 7) + 1; | 545 | __max_die_per_package = nodes_per_socket = ((ecx >> 8) & 7) + 1; |
| 546 | } else if (boot_cpu_has(X86_FEATURE_NODEID_MSR)) { | 546 | } else if (boot_cpu_has(X86_FEATURE_NODEID_MSR)) { |
| 547 | u64 value; | 547 | u64 value; |
| 548 | 548 | ||
| 549 | rdmsrl(MSR_FAM10H_NODE_ID, value); | 549 | rdmsrl(MSR_FAM10H_NODE_ID, value); |
| 550 | nodes_per_socket = ((value >> 3) & 7) + 1; | 550 | __max_die_per_package = nodes_per_socket = ((value >> 3) & 7) + 1; |
| 551 | } | 551 | } |
| 552 | 552 | ||
| 553 | if (!boot_cpu_has(X86_FEATURE_AMD_SSBD) && | 553 | if (!boot_cpu_has(X86_FEATURE_AMD_SSBD) && |
| @@ -1159,6 +1159,7 @@ static const struct x86_cpu_id split_lock_cpu_ids[] __initconst = { · 1158 unmodified lines | |||
| 1159 | X86_MATCH_INTEL_FAM6_MODEL(TIGERLAKE, 1), | 1159 | X86_MATCH_INTEL_FAM6_MODEL(TIGERLAKE, 1), |
| 1160 | X86_MATCH_INTEL_FAM6_MODEL(SAPPHIRERAPIDS_X, 1), | 1160 | X86_MATCH_INTEL_FAM6_MODEL(SAPPHIRERAPIDS_X, 1), |
| 1161 | X86_MATCH_INTEL_FAM6_MODEL(ALDERLAKE, 1), | 1161 | X86_MATCH_INTEL_FAM6_MODEL(ALDERLAKE, 1), |
| 1162 | X86_MATCH_INTEL_FAM6_MODEL(ALDERLAKE_L, 1), | ||
| 1162 | {} | 1163 | {} |
| 1163 | }; | 1164 | }; |
| 1164 | 1165 | ||
| @@ -1992,10 +1992,9 @@ static __always_inline void exc_machine_check_kernel(struct pt_regs *regs) · 1991 unmodified lines | |||
| 1992 | * that out because it's an indirect call. Annotate it. | 1992 | * that out because it's an indirect call. Annotate it. |
| 1993 | */ | 1993 | */ |
| 1994 | instrumentation_begin(); | 1994 | instrumentation_begin(); |
| 1995 | trace_hardirqs_off_finish(); | 1995 | |
| 1996 | machine_check_vector(regs); | 1996 | machine_check_vector(regs); |
| 1997 | if (regs->flags & X86_EFLAGS_IF) | 1997 | |
| 1998 | trace_hardirqs_on_prepare(); | ||
| 1999 | instrumentation_end(); | 1998 | instrumentation_end(); |
| 2000 | irqentry_nmi_exit(regs, irq_state); | 1999 | irqentry_nmi_exit(regs, irq_state); |
| 2001 | } | 2000 | } |
| @@ -2004,7 +2003,9 @@ static __always_inline void exc_machine_check_user(struct pt_regs *regs) · 2 unmodified lines | |||
| 2004 | { | 2003 | { |
| 2005 | irqentry_enter_from_user_mode(regs); | 2004 | irqentry_enter_from_user_mode(regs); |
| 2006 | instrumentation_begin(); | 2005 | instrumentation_begin(); |
| 2006 | |||
| 2007 | machine_check_vector(regs); | 2007 | machine_check_vector(regs); |
| 2008 | |||
| 2008 | instrumentation_end(); | 2009 | instrumentation_end(); |
| 2009 | irqentry_exit_to_user_mode(regs); | 2010 | irqentry_exit_to_user_mode(regs); |
| 2010 | } | 2011 | } |
| @@ -135,14 +135,32 @@ static void hv_machine_shutdown(void) · 134 unmodified lines | |||
| 135 | { | 135 | { |
| 136 | if (kexec_in_progress && hv_kexec_handler) | 136 | if (kexec_in_progress && hv_kexec_handler) |
| 137 | hv_kexec_handler(); | 137 | hv_kexec_handler(); |
| 138 | |||
| 139 | /* | ||
| 140 | * Call hv_cpu_die() on all the CPUs, otherwise later the hypervisor | ||
| 141 | * corrupts the old VP Assist Pages and can crash the kexec kernel. | ||
| 142 | */ | ||
| 143 | if (kexec_in_progress && hyperv_init_cpuhp > 0) | ||
| 144 | cpuhp_remove_state(hyperv_init_cpuhp); | ||
| 145 | |||
| 146 | /* The function calls stop_other_cpus(). */ | ||
| 138 | native_machine_shutdown(); | 147 | native_machine_shutdown(); |
| 148 | |||
| 149 | /* Disable the hypercall page when there is only 1 active CPU. */ | ||
| 150 | if (kexec_in_progress) | ||
| 151 | hyperv_cleanup(); | ||
| 139 | } | 152 | } |
| 140 | 153 | ||
| 141 | static void hv_machine_crash_shutdown(struct pt_regs *regs) | 154 | static void hv_machine_crash_shutdown(struct pt_regs *regs) |
| 142 | { | 155 | { |
| 143 | if (hv_crash_handler) | 156 | if (hv_crash_handler) |
| 144 | hv_crash_handler(regs); | 157 | hv_crash_handler(regs); |
| 158 | |||
| 159 | /* The function calls crash_smp_send_stop(). */ | ||
| 145 | native_machine_crash_shutdown(regs); | 160 | native_machine_crash_shutdown(regs); |
| 161 | |||
| 162 | /* Disable the hypercall page when there is only 1 active CPU. */ | ||
| 163 | hyperv_cleanup(); | ||
| 146 | } | 164 | } |
| 147 | #endif /* CONFIG_KEXEC_CORE */ | 165 | #endif /* CONFIG_KEXEC_CORE */ |
| 148 | #endif /* CONFIG_HYPERV */ | 166 | #endif /* CONFIG_HYPERV */ |
| @@ -167,9 +167,6 @@ static u8 mtrr_type_lookup_variable(u64 start, u64 end, u64 *partial_end, · 166 unmodified lines | |||
| 167 | *repeat = 0; | 167 | *repeat = 0; |
| 168 | *uniform = 1; | 168 | *uniform = 1; |
| 169 | 169 | ||
| 170 | /* Make end inclusive instead of exclusive */ | ||
| 171 | end--; | ||
| 172 | |||
| 173 | prev_match = MTRR_TYPE_INVALID; | 170 | prev_match = MTRR_TYPE_INVALID; |
| 174 | for (i = 0; i < num_var_ranges; ++i) { | 171 | for (i = 0; i < num_var_ranges; ++i) { |
| 175 | unsigned short start_state, end_state, inclusive; | 172 | unsigned short start_state, end_state, inclusive; |
| @@ -261,6 +258,9 @@ u8 mtrr_type_lookup(u64 start, u64 end, u8 *uniform) · 85 unmodified lines | |||
| 261 | int repeat; | 258 | int repeat; |
| 262 | u64 partial_end; | 259 | u64 partial_end; |
| 263 | 260 | ||
| 261 | /* Make end inclusive instead of exclusive */ | ||
| 262 | end--; | ||
| 263 | |||
| 264 | if (!mtrr_state_set) | 264 | if (!mtrr_state_set) |
| 265 | return MTRR_TYPE_INVALID; | 265 | return MTRR_TYPE_INVALID; |
| 266 | 266 | ||
| @@ -525,89 +525,70 @@ static void rdtgroup_remove(struct rdtgroup *rdtgrp) · 524 unmodified lines | |||
| 525 | kfree(rdtgrp); | 525 | kfree(rdtgrp); |
| 526 | } | 526 | } |
| 527 | 527 | ||
| 528 | struct task_move_callback { | 528 | static void _update_task_closid_rmid(void *task) |
| 529 | struct callback_head work; | ||
| 530 | struct rdtgroup *rdtgrp; | ||
| 531 | }; | ||
| 532 | |||
| 533 | static void move_myself(struct callback_head *head) | ||
| 534 | { | 529 | { |
| 535 | struct task_move_callback *callback; | ||
| 536 | struct rdtgroup *rdtgrp; | ||
| 537 | |||
| 538 | callback = container_of(head, struct task_move_callback, work); | ||
| 539 | rdtgrp = callback->rdtgrp; | ||
| 540 | |||
| 541 | /* | 530 | /* |
| 542 | * If resource group was deleted before this task work callback | 531 | * If the task is still current on this CPU, update PQR_ASSOC MSR. |
| 543 | * was invoked, then assign the task to root group and free the | 532 | * Otherwise, the MSR is updated when the task is scheduled in. |
| 544 | * resource group. | ||
| 545 | */ | 533 | */ |
| 546 | if (atomic_dec_and_test(&rdtgrp->waitcount) && | 534 | if (task == current) |
| 547 | (rdtgrp->flags & RDT_DELETED)) { | 535 | resctrl_sched_in(); |
| 548 | current->closid = 0; | 536 | } |
| 549 | current->rmid = 0; | ||
| 550 | rdtgroup_remove(rdtgrp); | ||
| 551 | } | ||
| 552 | |||
| 553 | if (unlikely(current->flags & PF_EXITING)) | ||
| 554 | goto out; | ||
| 555 | |||
| 556 | preempt_disable(); | ||
| 557 | /* update PQR_ASSOC MSR to make resource group go into effect */ | ||
| 558 | resctrl_sched_in(); | ||
| 559 | preempt_enable(); | ||
| 560 | 537 | ||
| 561 | out: | 538 | static void update_task_closid_rmid(struct task_struct *t) |
| 562 | kfree(callback); | 539 | { |
| 540 | if (IS_ENABLED(CONFIG_SMP) && task_curr(t)) | ||
| 541 | smp_call_function_single(task_cpu(t), _update_task_closid_rmid, t, 1); | ||
| 542 | else | ||
| 543 | _update_task_closid_rmid(t); | ||
| 563 | } | 544 | } |
| 564 | 545 | ||
| 565 | static int __rdtgroup_move_task(struct task_struct *tsk, | 546 | static int __rdtgroup_move_task(struct task_struct *tsk, |
| 566 | struct rdtgroup *rdtgrp) | 547 | struct rdtgroup *rdtgrp) |
| 567 | { | 548 | { |
| 568 | struct task_move_callback *callback; | 549 | /* If the task is already in rdtgrp, no need to move the task. */ |
| 569 | int ret; | 550 | if ((rdtgrp->type == RDTCTRL_GROUP && tsk->closid == rdtgrp->closid && |
| 570 | 551 | tsk->rmid == rdtgrp->mon.rmid) || | |
| 571 | callback = kzalloc(sizeof(*callback), GFP_KERNEL); | 552 | (rdtgrp->type == RDTMON_GROUP && tsk->rmid == rdtgrp->mon.rmid && |
| 572 | if (!callback) | 553 | tsk->closid == rdtgrp->mon.parent->closid)) |
| 573 | return -ENOMEM; | 554 | return 0; |
| 574 | callback->work.func = move_myself; | ||
| 575 | callback->rdtgrp = rdtgrp; | ||
| 576 | 555 | ||
| 577 | /* | 556 | /* |
| 578 | * Take a refcount, so rdtgrp cannot be freed before the | 557 | * Set the task's closid/rmid before the PQR_ASSOC MSR can be |
| 579 | * callback has been invoked. | 558 | * updated by them. |
| 559 | * | ||
| 560 | * For ctrl_mon groups, move both closid and rmid. | ||
| 561 | * For monitor groups, can move the tasks only from | ||
| 562 | * their parent CTRL group. | ||
| 580 | */ | 563 | */ |
| 581 | atomic_inc(&rdtgrp->waitcount); | 564 | |
| 582 | ret = task_work_add(tsk, &callback->work, TWA_RESUME); | 565 | if (rdtgrp->type == RDTCTRL_GROUP) { |
| 583 | if (ret) { | 566 | tsk->closid = rdtgrp->closid; |
| 584 | /* | 567 | tsk->rmid = rdtgrp->mon.rmid; |
| 585 | * Task is exiting. Drop the refcount and free the callback. | 568 | } else if (rdtgrp->type == RDTMON_GROUP) { |
| 586 | * No need to check the refcount as the group cannot be | 569 | if (rdtgrp->mon.parent->closid == tsk->closid) { |
| 587 | * deleted before the write function unlocks rdtgroup_mutex. | ||
| 588 | */ | ||
| 589 | atomic_dec(&rdtgrp->waitcount); | ||
| 590 | kfree(callback); | ||
| 591 | rdt_last_cmd_puts("Task exited\n"); | ||
| 592 | } else { | ||
| 593 | /* | ||
| 594 | * For ctrl_mon groups move both closid and rmid. | ||
| 595 | * For monitor groups, can move the tasks only from | ||
| 596 | * their parent CTRL group. | ||
| 597 | */ | ||
| 598 | if (rdtgrp->type == RDTCTRL_GROUP) { | ||
| 599 | tsk->closid = rdtgrp->closid; | ||
| 600 | tsk->rmid = rdtgrp->mon.rmid; | 570 | tsk->rmid = rdtgrp->mon.rmid; |
| 601 | } else if (rdtgrp->type == RDTMON_GROUP) { | 571 | } else { |
| 602 | if (rdtgrp->mon.parent->closid == tsk->closid) { | 572 | rdt_last_cmd_puts("Can't move task to different control group\n"); |
| 603 | tsk->rmid = rdtgrp->mon.rmid; | 573 | return -EINVAL; |
| 604 | } else { | ||
| 605 | rdt_last_cmd_puts("Can't move task to different control group\n"); | ||
| 606 | ret = -EINVAL; | ||
| 607 | } | ||
| 608 | } | 574 | } |
| 609 | } | 575 | } |
| 610 | return ret; | 576 | |
| 577 | /* | ||
| 578 | * Ensure the task's closid and rmid are written before determining if | ||
| 579 | * the task is current that will decide if it will be interrupted. | ||
| 580 | */ | ||
| 581 | barrier(); | ||
| 582 | |||
| 583 | /* | ||
| 584 | * By now, the task's closid and rmid are set. If the task is current | ||
| 585 | * on a CPU, the PQR_ASSOC MSR needs to be updated to make the resource | ||
| 586 | * group go into effect. If the task is not current, the MSR will be | ||
| 587 | * updated when the task is scheduled in. | ||
| 588 | */ | ||
| 589 | update_task_closid_rmid(tsk); | ||
| 590 | |||
| 591 | return 0; | ||
| 611 | } | 592 | } |
| 612 | 593 | ||
| 613 | static bool is_closid_match(struct task_struct *t, struct rdtgroup *r) | 594 | static bool is_closid_match(struct task_struct *t, struct rdtgroup *r) |
| @@ -72,6 +72,9 @@ static int sgx_release(struct inode *inode, struct file *file) · 71 unmodified lines | |||
| 72 | synchronize_srcu(&encl->srcu); | 72 | synchronize_srcu(&encl->srcu); |
| 73 | mmu_notifier_unregister(&encl_mm->mmu_notifier, encl_mm->mm); | 73 | mmu_notifier_unregister(&encl_mm->mmu_notifier, encl_mm->mm); |
| 74 | kfree(encl_mm); | 74 | kfree(encl_mm); |
| 75 | |||
| 76 | /* 'encl_mm' is gone, put encl_mm->encl reference: */ | ||
| 77 | kref_put(&encl->refcount, sgx_encl_release); | ||
| 75 | } | 78 | } |
| 76 | 79 | ||
| 77 | kref_put(&encl->refcount, sgx_encl_release); | 80 | kref_put(&encl->refcount, sgx_encl_release); |
| @@ -481,6 +481,9 @@ static void sgx_mmu_notifier_free(struct mmu_notifier *mn) · 480 unmodified lines | |||
| 481 | { | 481 | { |
| 482 | struct sgx_encl_mm *encl_mm = container_of(mn, struct sgx_encl_mm, mmu_notifier); | 482 | struct sgx_encl_mm *encl_mm = container_of(mn, struct sgx_encl_mm, mmu_notifier); |
| 483 | 483 | ||
| 484 | /* 'encl_mm' is going away, put encl_mm->encl reference: */ | ||
| 485 | kref_put(&encl_mm->encl->refcount, sgx_encl_release); | ||
| 486 | |||
| 484 | kfree(encl_mm); | 487 | kfree(encl_mm); |
| 485 | } | 488 | } |
| 486 | 489 | ||
| @@ -534,6 +537,8 @@ int sgx_encl_mm_add(struct sgx_encl *encl, struct mm_struct *mm) · 47 unmodified lines | |||
| 534 | if (!encl_mm) | 537 | if (!encl_mm) |
| 535 | return -ENOMEM; | 538 | return -ENOMEM; |
| 536 | 539 | ||
| 540 | /* Grab a refcount for the encl_mm->encl reference: */ | ||
| 541 | kref_get(&encl->refcount); | ||
| 537 | encl_mm->encl = encl; | 542 | encl_mm->encl = encl; |
| 538 | encl_mm->mm = mm; | 543 | encl_mm->mm = mm; |
| 539 | encl_mm->mmu_notifier.ops = &sgx_mmu_notifier_ops; | 544 | encl_mm->mmu_notifier.ops = &sgx_mmu_notifier_ops; |
| @@ -25,10 +25,10 @@ · 24 unmodified lines | |||
| 25 | #define BITS_SHIFT_NEXT_LEVEL(eax) ((eax) & 0x1f) | 25 | #define BITS_SHIFT_NEXT_LEVEL(eax) ((eax) & 0x1f) |
| 26 | #define LEVEL_MAX_SIBLINGS(ebx) ((ebx) & 0xffff) | 26 | #define LEVEL_MAX_SIBLINGS(ebx) ((ebx) & 0xffff) |
| 27 | 27 | ||
| 28 | #ifdef CONFIG_SMP | ||
| 29 | unsigned int __max_die_per_package __read_mostly = 1; | 28 | unsigned int __max_die_per_package __read_mostly = 1; |
| 30 | EXPORT_SYMBOL(__max_die_per_package); | 29 | EXPORT_SYMBOL(__max_die_per_package); |
| 31 | 30 | ||
| 31 | #ifdef CONFIG_SMP | ||
| 32 | /* | 32 | /* |
| 33 | * Check if given CPUID extended toplogy "leaf" is implemented | 33 | * Check if given CPUID extended toplogy "leaf" is implemented |
| 34 | */ | 34 | */ |
| @@ -121,7 +121,7 @@ int copy_fpregs_to_fpstate(struct fpu *fpu) · 120 unmodified lines | |||
| 121 | } | 121 | } |
| 122 | EXPORT_SYMBOL(copy_fpregs_to_fpstate); | 122 | EXPORT_SYMBOL(copy_fpregs_to_fpstate); |
| 123 | 123 | ||
| 124 | void kernel_fpu_begin(void) | 124 | void kernel_fpu_begin_mask(unsigned int kfpu_mask) |
| 125 | { | 125 | { |
| 126 | preempt_disable(); | 126 | preempt_disable(); |
| 127 | 127 | ||
| @@ -141,13 +141,14 @@ void kernel_fpu_begin(void) · 13 unmodified lines | |||
| 141 | } | 141 | } |
| 142 | __cpu_invalidate_fpregs_state(); | 142 | __cpu_invalidate_fpregs_state(); |
| 143 | 143 | ||
| 144 | if (boot_cpu_has(X86_FEATURE_XMM)) | 144 | /* Put sane initial values into the control registers. */ |
| 145 | if (likely(kfpu_mask & KFPU_MXCSR) && boot_cpu_has(X86_FEATURE_XMM)) | ||
| 145 | ldmxcsr(MXCSR_DEFAULT); | 146 | ldmxcsr(MXCSR_DEFAULT); |
| 146 | 147 | ||
| 147 | if (boot_cpu_has(X86_FEATURE_FPU)) | 148 | if (unlikely(kfpu_mask & KFPU_387) && boot_cpu_has(X86_FEATURE_FPU)) |
| 148 | asm volatile ("fninit"); | 149 | asm volatile ("fninit"); |
| 149 | } | 150 | } |
| 150 | EXPORT_SYMBOL_GPL(kernel_fpu_begin); | 151 | EXPORT_SYMBOL_GPL(kernel_fpu_begin_mask); |
| 151 | 152 | ||
| 152 | void kernel_fpu_end(void) | 153 | void kernel_fpu_end(void) |
| 153 | { | 154 | { |
| @@ -269,6 +269,20 @@ static inline bool within_cpu_entry(unsigned long addr, unsigned long end) · 268 unmodified lines | |||
| 269 | CPU_ENTRY_AREA_TOTAL_SIZE)) | 269 | CPU_ENTRY_AREA_TOTAL_SIZE)) |
| 270 | return true; | 270 | return true; |
| 271 | 271 | ||
| 272 | /* | ||
| 273 | * When FSGSBASE is enabled, paranoid_entry() fetches the per-CPU | ||
| 274 | * GSBASE value via __per_cpu_offset or pcpu_unit_offsets. | ||
| 275 | */ | ||
| 276 | #ifdef CONFIG_SMP | ||
| 277 | if (within_area(addr, end, (unsigned long)__per_cpu_offset, | ||
| 278 | sizeof(unsigned long) * nr_cpu_ids)) | ||
| 279 | return true; | ||
| 280 | #else | ||
| 281 | if (within_area(addr, end, (unsigned long)&pcpu_unit_offsets, | ||
| 282 | sizeof(pcpu_unit_offsets))) | ||
| 283 | return true; | ||
| 284 | #endif | ||
| 285 | |||
| 272 | for_each_possible_cpu(cpu) { | 286 | for_each_possible_cpu(cpu) { |
| 273 | /* The original rw GDT is being used after load_direct_gdt() */ | 287 | /* The original rw GDT is being used after load_direct_gdt() */ |
| 274 | if (within_area(addr, end, (unsigned long)get_cpu_gdt_rw(cpu), | 288 | if (within_area(addr, end, (unsigned long)get_cpu_gdt_rw(cpu), |
| @@ -293,6 +307,14 @@ static inline bool within_cpu_entry(unsigned long addr, unsigned long end) · 18 unmodified lines | |||
| 293 | (unsigned long)&per_cpu(cpu_tlbstate, cpu), | 307 | (unsigned long)&per_cpu(cpu_tlbstate, cpu), |
| 294 | sizeof(struct tlb_state))) | 308 | sizeof(struct tlb_state))) |
| 295 | return true; | 309 | return true; |
| 310 | |||
| 311 | /* | ||
| 312 | * When in guest (X86_FEATURE_HYPERVISOR), local_db_save() | ||
| 313 | * will read per-cpu cpu_dr7 before clear dr7 register. | ||
| 314 | */ | ||
| 315 | if (within_area(addr, end, (unsigned long)&per_cpu(cpu_dr7, cpu), | ||
| 316 | sizeof(cpu_dr7))) | ||
| 317 | return true; | ||
| 296 | } | 318 | } |
| 297 | 319 | ||
| 298 | return false; | 320 | return false; |
| @@ -491,15 +513,12 @@ static int hw_breakpoint_handler(struct die_args *args) · 192 unmodified lines | |||
| 491 | struct perf_event *bp; | 513 | struct perf_event *bp; |
| 492 | unsigned long *dr6_p; | 514 | unsigned long *dr6_p; |
| 493 | unsigned long dr6; | 515 | unsigned long dr6; |
| 516 | bool bpx; | ||
| 494 | 517 | ||
| 495 | /* The DR6 value is pointed by args->err */ | 518 | /* The DR6 value is pointed by args->err */ |
| 496 | dr6_p = (unsigned long *)ERR_PTR(args->err); | 519 | dr6_p = (unsigned long *)ERR_PTR(args->err); |
| 497 | dr6 = *dr6_p; | 520 | dr6 = *dr6_p; |
| 498 | 521 | ||
| 499 | /* If it's a single step, TRAP bits are random */ | ||
| 500 | if (dr6 & DR_STEP) | ||
| 501 | return NOTIFY_DONE; | ||
| 502 | |||
| 503 | /* Do an early return if no trap bits are set in DR6 */ | 522 | /* Do an early return if no trap bits are set in DR6 */ |
| 504 | if ((dr6 & DR_TRAP_BITS) == 0) | 523 | if ((dr6 & DR_TRAP_BITS) == 0) |
| 505 | return NOTIFY_DONE; | 524 | return NOTIFY_DONE; |
| @@ -509,28 +528,29 @@ static int hw_breakpoint_handler(struct die_args *args) · 3 unmodified lines | |||
| 509 | if (likely(!(dr6 & (DR_TRAP0 << i)))) | 528 | if (likely(!(dr6 & (DR_TRAP0 << i)))) |
| 510 | continue; | 529 | continue; |
| 511 | 530 | ||
| 531 | bp = this_cpu_read(bp_per_reg[i]); | ||
| 532 | if (!bp) | ||
| 533 | continue; | ||
| 534 | |||
| 535 | bpx = bp->hw.info.type == X86_BREAKPOINT_EXECUTE; | ||
| 536 | |||
| 512 | /* | 537 | /* |
| 513 | * The counter may be concurrently released but that can only | 538 | * TF and data breakpoints are traps and can be merged, however |
| 514 | * occur from a call_rcu() path. We can then safely fetch | 539 | * instruction breakpoints are faults and will be raised |
| 515 | * the breakpoint, use its callback, touch its counter | 540 | * separately. |
| 516 | * while we are in an rcu_read_lock() path. | 541 | * |
| 542 | * However DR6 can indicate both TF and instruction | ||
| 543 | * breakpoints. In that case take TF as that has precedence and | ||
| 544 | * delay the instruction breakpoint for the next exception. | ||
| 517 | */ | 545 | */ |
| 518 | rcu_read_lock(); | 546 | if (bpx && (dr6 & DR_STEP)) |
| 547 | continue; | ||
| 519 | 548 | ||
| 520 | bp = this_cpu_read(bp_per_reg[i]); | ||
| 521 | /* | 549 | /* |
| 522 | * Reset the 'i'th TRAP bit in dr6 to denote completion of | 550 | * Reset the 'i'th TRAP bit in dr6 to denote completion of |
| 523 | * exception handling | 551 | * exception handling |
| 524 | */ | 552 | */ |
| 525 | (*dr6_p) &= ~(DR_TRAP0 << i); | 553 | (*dr6_p) &= ~(DR_TRAP0 << i); |
| 526 | /* | ||
| 527 | * bp can be NULL due to lazy debug register switching | ||
| 528 | * or due to concurrent perf counter removing. | ||
| 529 | */ | ||
| 530 | if (!bp) { | ||
| 531 | rcu_read_unlock(); | ||
| 532 | break; | ||
| 533 | } | ||
| 534 | 554 | ||
| 535 | perf_bp_event(bp, args->regs); | 555 | perf_bp_event(bp, args->regs); |
| 536 | 556 | ||
| @@ -538,11 +558,10 @@ static int hw_breakpoint_handler(struct die_args *args) · 1 unmodified line | |||
| 538 | * Set up resume flag to avoid breakpoint recursion when | 558 | * Set up resume flag to avoid breakpoint recursion when |
| 539 | * returning back to origin. | 559 | * returning back to origin. |
| 540 | */ | 560 | */ |
| 541 | if (bp->hw.info.type == X86_BREAKPOINT_EXECUTE) | 561 | if (bpx) |
| 542 | args->regs->flags |= X86_EFLAGS_RF; | 562 | args->regs->flags |= X86_EFLAGS_RF; |
| 543 | |||
| 544 | rcu_read_unlock(); | ||
| 545 | } | 563 | } |
| 564 | |||
| 546 | /* | 565 | /* |
| 547 | * Further processing in do_debug() is needed for a) user-space | 566 | * Further processing in do_debug() is needed for a) user-space |
| 548 | * breakpoints (to generate signals) and b) when the system has | 567 | * breakpoints (to generate signals) and b) when the system has |
| @@ -305,14 +305,14 @@ static enum es_result vc_ioio_exitinfo(struct es_em_ctxt *ctxt, u64 *exitinfo) · 304 unmodified lines | |||
| 305 | case 0xe4: | 305 | case 0xe4: |
| 306 | case 0xe5: | 306 | case 0xe5: |
| 307 | *exitinfo |= IOIO_TYPE_IN; | 307 | *exitinfo |= IOIO_TYPE_IN; |
| 308 | *exitinfo |= (u64)insn->immediate.value << 16; | 308 | *exitinfo |= (u8)insn->immediate.value << 16; |
| 309 | break; | 309 | break; |
| 310 | 310 | ||
| 311 | /* OUT immediate opcodes */ | 311 | /* OUT immediate opcodes */ |
| 312 | case 0xe6: | 312 | case 0xe6: |
| 313 | case 0xe7: | 313 | case 0xe7: |
| 314 | *exitinfo |= IOIO_TYPE_OUT; | 314 | *exitinfo |= IOIO_TYPE_OUT; |
| 315 | *exitinfo |= (u64)insn->immediate.value << 16; | 315 | *exitinfo |= (u8)insn->immediate.value << 16; |
| 316 | break; | 316 | break; |
| 317 | 317 | ||
| 318 | /* IN register opcodes */ | 318 | /* IN register opcodes */ |
| @@ -225,7 +225,7 @@ static inline u64 sev_es_rd_ghcb_msr(void) · 224 unmodified lines | |||
| 225 | return __rdmsr(MSR_AMD64_SEV_ES_GHCB); | 225 | return __rdmsr(MSR_AMD64_SEV_ES_GHCB); |
| 226 | } | 226 | } |
| 227 | 227 | ||
| 228 | static inline void sev_es_wr_ghcb_msr(u64 val) | 228 | static __always_inline void sev_es_wr_ghcb_msr(u64 val) |
| 229 | { | 229 | { |
| 230 | u32 low, high; | 230 | u32 low, high; |
| 231 | 231 | ||
| @@ -286,6 +286,12 @@ static enum es_result vc_write_mem(struct es_em_ctxt *ctxt, · 54 unmodified lines | |||
| 286 | u16 d2; | 286 | u16 d2; |
| 287 | u8 d1; | 287 | u8 d1; |
| 288 | 288 | ||
| 289 | /* If instruction ran in kernel mode and the I/O buffer is in kernel space */ | ||
| 290 | if (!user_mode(ctxt->regs) && !access_ok(target, size)) { | ||
| 291 | memcpy(dst, buf, size); | ||
| 292 | return ES_OK; | ||
| 293 | } | ||
| 294 | |||
| 289 | switch (size) { | 295 | switch (size) { |
| 290 | case 1: | 296 | case 1: |
| 291 | memcpy(&d1, buf, 1); | 297 | memcpy(&d1, buf, 1); |
| @@ -335,6 +341,12 @@ static enum es_result vc_read_mem(struct es_em_ctxt *ctxt, · 43 unmodified lines | |||
| 335 | u16 d2; | 341 | u16 d2; |
| 336 | u8 d1; | 342 | u8 d1; |
| 337 | 343 | ||
| 344 | /* If instruction ran in kernel mode and the I/O buffer is in kernel space */ | ||
| 345 | if (!user_mode(ctxt->regs) && !access_ok(s, size)) { | ||
| 346 | memcpy(buf, src, size); | ||
| 347 | return ES_OK; | ||
| 348 | } | ||
| 349 | |||
| 338 | switch (size) { | 350 | switch (size) { |
| 339 | case 1: | 351 | case 1: |
| 340 | if (get_user(d1, s)) | 352 | if (get_user(d1, s)) |
| @@ -56,6 +56,7 @@ · 55 unmodified lines | |||
| 56 | #include <linux/numa.h> | 56 | #include <linux/numa.h> |
| 57 | #include <linux/pgtable.h> | 57 | #include <linux/pgtable.h> |
| 58 | #include <linux/overflow.h> | 58 | #include <linux/overflow.h> |
| 59 | #include <linux/syscore_ops.h> | ||
| 59 | 60 | ||
| 60 | #include <asm/acpi.h> | 61 | #include <asm/acpi.h> |
| 61 | #include <asm/desc.h> | 62 | #include <asm/desc.h> |
| @@ -1832,6 +1833,7 @@ void arch_set_max_freq_ratio(bool turbo_disabled) · 1770 unmodified lines | |||
| 1832 | arch_max_freq_ratio = turbo_disabled ? SCHED_CAPACITY_SCALE : | 1833 | arch_max_freq_ratio = turbo_disabled ? SCHED_CAPACITY_SCALE : |
| 1833 | arch_turbo_freq_ratio; | 1834 | arch_turbo_freq_ratio; |
| 1834 | } | 1835 | } |
| 1836 | EXPORT_SYMBOL_GPL(arch_set_max_freq_ratio); | ||
| 1835 | 1837 | ||
| 1836 | static bool turbo_disabled(void) | 1838 | static bool turbo_disabled(void) |
| 1837 | { | 1839 | { |
| @@ -2083,6 +2085,23 @@ static void init_counter_refs(void) · 245 unmodified lines | |||
| 2083 | this_cpu_write(arch_prev_mperf, mperf); | 2085 | this_cpu_write(arch_prev_mperf, mperf); |
| 2084 | } | 2086 | } |
| 2085 | 2087 | ||
| 2088 | #ifdef CONFIG_PM_SLEEP | ||
| 2089 | static struct syscore_ops freq_invariance_syscore_ops = { | ||
| 2090 | .resume = init_counter_refs, | ||
| 2091 | }; | ||
| 2092 | |||
| 2093 | static void register_freq_invariance_syscore_ops(void) | ||
| 2094 | { | ||
| 2095 | /* Bail out if registered already. */ | ||
| 2096 | if (freq_invariance_syscore_ops.node.prev) | ||
| 2097 | return; | ||
| 2098 | |||
| 2099 | register_syscore_ops(&freq_invariance_syscore_ops); | ||
| 2100 | } | ||
| 2101 | #else | ||
| 2102 | static inline void register_freq_invariance_syscore_ops(void) {} | ||
| 2103 | #endif | ||
| 2104 | |||
| 2086 | static void init_freq_invariance(bool secondary, bool cppc_ready) | 2105 | static void init_freq_invariance(bool secondary, bool cppc_ready) |
| 2087 | { | 2106 | { |
| 2088 | bool ret = false; | 2107 | bool ret = false; |
| @@ -2109,6 +2128,7 @@ static void init_freq_invariance(bool secondary, bool cppc_ready) · 20 unmodified lines | |||
| 2109 | if (ret) { | 2128 | if (ret) { |
| 2110 | init_counter_refs(); | 2129 | init_counter_refs(); |
| 2111 | static_branch_enable(&arch_scale_freq_key); | 2130 | static_branch_enable(&arch_scale_freq_key); |
| 2131 | register_freq_invariance_syscore_ops(); | ||
| 2112 | pr_info("Estimated ratio of average max frequency by base frequency (times 1024): %llu\n", arch_max_freq_ratio); | 2132 | pr_info("Estimated ratio of average max frequency by base frequency (times 1024): %llu\n", arch_max_freq_ratio); |
| 2113 | } else { | 2133 | } else { |
| 2114 | pr_debug("Couldn't determine max cpu frequency, necessary for scale-invariant accounting.\n"); | 2134 | pr_debug("Couldn't determine max cpu frequency, necessary for scale-invariant accounting.\n"); |
| @@ -127,12 +127,17 @@ static int enable_single_step(struct task_struct *child) · 126 unmodified lines | |||
| 127 | regs->flags |= X86_EFLAGS_TF; | 127 | regs->flags |= X86_EFLAGS_TF; |
| 128 | 128 | ||
| 129 | /* | 129 | /* |
| 130 | * Always set TIF_SINGLESTEP - this guarantees that | 130 | * Always set TIF_SINGLESTEP. This will also |
| 131 | * we single-step system calls etc.. This will also | ||
| 132 | * cause us to set TF when returning to user mode. | 131 | * cause us to set TF when returning to user mode. |
| 133 | */ | 132 | */ |
| 134 | set_tsk_thread_flag(child, TIF_SINGLESTEP); | 133 | set_tsk_thread_flag(child, TIF_SINGLESTEP); |
| 135 | 134 | ||
| 135 | /* | ||
| 136 | * Ensure that a trap is triggered once stepping out of a system | ||
| 137 | * call prior to executing any user instruction. | ||
| 138 | */ | ||
| 139 | set_task_syscall_work(child, SYSCALL_EXIT_TRAP); | ||
| 140 | |||
| 136 | oflags = regs->flags; | 141 | oflags = regs->flags; |
| 137 | 142 | ||
| 138 | /* Set TF on the kernel stack.. */ | 143 | /* Set TF on the kernel stack.. */ |
| @@ -230,6 +235,7 @@ void user_disable_single_step(struct task_struct *child) · 91 unmodified lines | |||
| 230 | 235 | ||
| 231 | /* Always clear TIF_SINGLESTEP... */ | 236 | /* Always clear TIF_SINGLESTEP... */ |
| 232 | clear_tsk_thread_flag(child, TIF_SINGLESTEP); | 237 | clear_tsk_thread_flag(child, TIF_SINGLESTEP); |
| 238 | clear_task_syscall_work(child, SYSCALL_EXIT_TRAP); | ||
| 233 | 239 | ||
| 234 | /* But touch TF only if it was set by us.. */ | 240 | /* But touch TF only if it was set by us.. */ |
| 235 | if (test_and_clear_tsk_thread_flag(child, TIF_FORCED_TF)) | 241 | if (test_and_clear_tsk_thread_flag(child, TIF_FORCED_TF)) |
| @@ -321,7 +321,7 @@ int kvm_vcpu_ioctl_get_cpuid2(struct kvm_vcpu *vcpu, · 320 unmodified lines | |||
| 321 | if (cpuid->nent < vcpu->arch.cpuid_nent) | 321 | if (cpuid->nent < vcpu->arch.cpuid_nent) |
| 322 | goto out; | 322 | goto out; |
| 323 | r = -EFAULT; | 323 | r = -EFAULT; |
| 324 | if (copy_to_user(entries, &vcpu->arch.cpuid_entries, | 324 | if (copy_to_user(entries, vcpu->arch.cpuid_entries, |
| 325 | vcpu->arch.cpuid_nent * sizeof(struct kvm_cpuid_entry2))) | 325 | vcpu->arch.cpuid_nent * sizeof(struct kvm_cpuid_entry2))) |
| 326 | goto out; | 326 | goto out; |
| 327 | return 0; | 327 | return 0; |
| @@ -2879,6 +2879,8 @@ static int em_sysenter(struct x86_emulate_ctxt *ctxt) · 2878 unmodified lines | |||
| 2879 | ops->get_msr(ctxt, MSR_IA32_SYSENTER_ESP, &msr_data); | 2879 | ops->get_msr(ctxt, MSR_IA32_SYSENTER_ESP, &msr_data); |
| 2880 | *reg_write(ctxt, VCPU_REGS_RSP) = (efer & EFER_LMA) ? msr_data : | 2880 | *reg_write(ctxt, VCPU_REGS_RSP) = (efer & EFER_LMA) ? msr_data : |
| 2881 | (u32)msr_data; | 2881 | (u32)msr_data; |
| 2882 | if (efer & EFER_LMA) | ||
| 2883 | ctxt->mode = X86EMUL_MODE_PROT64; | ||
| 2882 | 2884 | ||
| 2883 | return X86EMUL_CONTINUE; | 2885 | return X86EMUL_CONTINUE; |
| 2884 | } | 2886 | } |
| @@ -9,31 +9,6 @@ · 8 unmodified lines | |||
| 9 | (X86_CR4_PVI | X86_CR4_DE | X86_CR4_PCE | X86_CR4_OSFXSR \ | 9 | (X86_CR4_PVI | X86_CR4_DE | X86_CR4_PCE | X86_CR4_OSFXSR \ |
| 10 | | X86_CR4_OSXMMEXCPT | X86_CR4_PGE | X86_CR4_TSD | X86_CR4_FSGSBASE) | 10 | | X86_CR4_OSXMMEXCPT | X86_CR4_PGE | X86_CR4_TSD | X86_CR4_FSGSBASE) |
| 11 | 11 | ||
| 12 | static inline bool kvm_register_is_available(struct kvm_vcpu *vcpu, | ||
| 13 | enum kvm_reg reg) | ||
| 14 | { | ||
| 15 | return test_bit(reg, (unsigned long *)&vcpu->arch.regs_avail); | ||
| 16 | } | ||
| 17 | |||
| 18 | static inline bool kvm_register_is_dirty(struct kvm_vcpu *vcpu, | ||
| 19 | enum kvm_reg reg) | ||
| 20 | { | ||
| 21 | return test_bit(reg, (unsigned long *)&vcpu->arch.regs_dirty); | ||
| 22 | } | ||
| 23 | |||
| 24 | static inline void kvm_register_mark_available(struct kvm_vcpu *vcpu, | ||
| 25 | enum kvm_reg reg) | ||
| 26 | { | ||
| 27 | __set_bit(reg, (unsigned long *)&vcpu->arch.regs_avail); | ||
| 28 | } | ||
| 29 | |||
| 30 | static inline void kvm_register_mark_dirty(struct kvm_vcpu *vcpu, | ||
| 31 | enum kvm_reg reg) | ||
| 32 | { | ||
| 33 | __set_bit(reg, (unsigned long *)&vcpu->arch.regs_avail); | ||
| 34 | __set_bit(reg, (unsigned long *)&vcpu->arch.regs_dirty); | ||
| 35 | } | ||
| 36 | |||
| 37 | #define BUILD_KVM_GPR_ACCESSORS(lname, uname) \ | 12 | #define BUILD_KVM_GPR_ACCESSORS(lname, uname) \ |
| 38 | static __always_inline unsigned long kvm_##lname##_read(struct kvm_vcpu *vcpu)\ | 13 | static __always_inline unsigned long kvm_##lname##_read(struct kvm_vcpu *vcpu)\ |
| 39 | { \ | 14 | { \ |
| @@ -43,7 +18,6 @@ static __always_inline void kvm_##lname##_write(struct kvm_vcpu *vcpu, \ · 3 unmodified lines | |||
| 43 | unsigned long val) \ | 18 | unsigned long val) \ |
| 44 | { \ | 19 | { \ |
| 45 | vcpu->arch.regs[VCPU_REGS_##uname] = val; \ | 20 | vcpu->arch.regs[VCPU_REGS_##uname] = val; \ |
| 46 | kvm_register_mark_dirty(vcpu, VCPU_REGS_##uname); \ | ||
| 47 | } | 21 | } |
| 48 | BUILD_KVM_GPR_ACCESSORS(rax, RAX) | 22 | BUILD_KVM_GPR_ACCESSORS(rax, RAX) |
| 49 | BUILD_KVM_GPR_ACCESSORS(rbx, RBX) | 23 | BUILD_KVM_GPR_ACCESSORS(rbx, RBX) |
| @@ -63,6 +37,31 @@ BUILD_KVM_GPR_ACCESSORS(r14, R14) · 13 unmodified lines | |||
| 63 | BUILD_KVM_GPR_ACCESSORS(r15, R15) | 37 | BUILD_KVM_GPR_ACCESSORS(r15, R15) |
| 64 | #endif | 38 | #endif |
| 65 | 39 | ||
| 40 | static inline bool kvm_register_is_available(struct kvm_vcpu *vcpu, | ||
| 41 | enum kvm_reg reg) | ||
| 42 | { | ||
| 43 | return test_bit(reg, (unsigned long *)&vcpu->arch.regs_avail); | ||
| 44 | } | ||
| 45 | |||
| 46 | static inline bool kvm_register_is_dirty(struct kvm_vcpu *vcpu, | ||
| 47 | enum kvm_reg reg) | ||
| 48 | { | ||
| 49 | return test_bit(reg, (unsigned long *)&vcpu->arch.regs_dirty); | ||
| 50 | } | ||
| 51 | |||
| 52 | static inline void kvm_register_mark_available(struct kvm_vcpu *vcpu, | ||
| 53 | enum kvm_reg reg) | ||
| 54 | { | ||
| 55 | __set_bit(reg, (unsigned long *)&vcpu->arch.regs_avail); | ||
| 56 | } | ||
| 57 | |||
| 58 | static inline void kvm_register_mark_dirty(struct kvm_vcpu *vcpu, | ||
| 59 | enum kvm_reg reg) | ||
| 60 | { | ||
| 61 | __set_bit(reg, (unsigned long *)&vcpu->arch.regs_avail); | ||
| 62 | __set_bit(reg, (unsigned long *)&vcpu->arch.regs_dirty); | ||
| 63 | } | ||
| 64 | |||
| 66 | static inline unsigned long kvm_register_read(struct kvm_vcpu *vcpu, int reg) | 65 | static inline unsigned long kvm_register_read(struct kvm_vcpu *vcpu, int reg) |
| 67 | { | 66 | { |
| 68 | if (WARN_ON_ONCE((unsigned int)reg >= NR_VCPU_REGS)) | 67 | if (WARN_ON_ONCE((unsigned int)reg >= NR_VCPU_REGS)) |
| @@ -674,7 +674,7 @@ static bool pv_eoi_get_pending(struct kvm_vcpu *vcpu) · 673 unmodified lines | |||
| 674 | (unsigned long long)vcpu->arch.pv_eoi.msr_val); | 674 | (unsigned long long)vcpu->arch.pv_eoi.msr_val); |
| 675 | return false; | 675 | return false; |
| 676 | } | 676 | } |
| 677 | return val & 0x1; | 677 | return val & KVM_PV_EOI_ENABLED; |
| 678 | } | 678 | } |
| 679 | 679 | ||
| 680 | static void pv_eoi_set_pending(struct kvm_vcpu *vcpu) | 680 | static void pv_eoi_set_pending(struct kvm_vcpu *vcpu) |
| @@ -2898,7 +2898,7 @@ void kvm_apic_accept_events(struct kvm_vcpu *vcpu) · 2217 unmodified lines | |||
| 2898 | /* evaluate pending_events before reading the vector */ | 2898 | /* evaluate pending_events before reading the vector */ |
| 2899 | smp_rmb(); | 2899 | smp_rmb(); |
| 2900 | sipi_vector = apic->sipi_vector; | 2900 | sipi_vector = apic->sipi_vector; |
| 2901 | kvm_vcpu_deliver_sipi_vector(vcpu, sipi_vector); | 2901 | kvm_x86_ops.vcpu_deliver_sipi_vector(vcpu, sipi_vector); |
| 2902 | vcpu->arch.mp_state = KVM_MP_STATE_RUNNABLE; | 2902 | vcpu->arch.mp_state = KVM_MP_STATE_RUNNABLE; |
| 2903 | } | 2903 | } |
| 2904 | } | 2904 | } |
| @@ -44,12 +44,19 @@ · 43 unmodified lines | |||
| 44 | #define PT32_ROOT_LEVEL 2 | 44 | #define PT32_ROOT_LEVEL 2 |
| 45 | #define PT32E_ROOT_LEVEL 3 | 45 | #define PT32E_ROOT_LEVEL 3 |
| 46 | 46 | ||
| 47 | static inline u64 rsvd_bits(int s, int e) | 47 | static __always_inline u64 rsvd_bits(int s, int e) |
| 48 | { | 48 | { |
| 49 | BUILD_BUG_ON(__builtin_constant_p(e) && __builtin_constant_p(s) && e < s); | ||
| 50 | |||
| 51 | if (__builtin_constant_p(e)) | ||
| 52 | BUILD_BUG_ON(e > 63); | ||
| 53 | else | ||
| 54 | e &= 63; | ||
| 55 | |||
| 49 | if (e < s) | 56 | if (e < s) |
| 50 | return 0; | 57 | return 0; |
| 51 | 58 | ||
| 52 | return ((1ULL << (e - s + 1)) - 1) << s; | 59 | return ((2ULL << (e - s)) - 1) << s; |
| 53 | } | 60 | } |
| 54 | 61 | ||
| 55 | void kvm_mmu_set_mmio_spte_mask(u64 mmio_value, u64 access_mask); | 62 | void kvm_mmu_set_mmio_spte_mask(u64 mmio_value, u64 access_mask); |
| @@ -3493,26 +3493,25 @@ static bool mmio_info_in_cache(struct kvm_vcpu *vcpu, u64 addr, bool direct) · 3492 unmodified lines | |||
| 3493 | * Return the level of the lowest level SPTE added to sptes. | 3493 | * Return the level of the lowest level SPTE added to sptes. |
| 3494 | * That SPTE may be non-present. | 3494 | * That SPTE may be non-present. |
| 3495 | */ | 3495 | */ |
| 3496 | static int get_walk(struct kvm_vcpu *vcpu, u64 addr, u64 *sptes) | 3496 | static int get_walk(struct kvm_vcpu *vcpu, u64 addr, u64 *sptes, int *root_level) |
| 3497 | { | 3497 | { |
| 3498 | struct kvm_shadow_walk_iterator iterator; | 3498 | struct kvm_shadow_walk_iterator iterator; |
| 3499 | int leaf = vcpu->arch.mmu->root_level; | 3499 | int leaf = -1; |
| 3500 | u64 spte; | 3500 | u64 spte; |
| 3501 | 3501 | ||
| 3502 | |||
| 3503 | walk_shadow_page_lockless_begin(vcpu); | 3502 | walk_shadow_page_lockless_begin(vcpu); |
| 3504 | 3503 | ||
| 3505 | for (shadow_walk_init(&iterator, vcpu, addr); | 3504 | for (shadow_walk_init(&iterator, vcpu, addr), |
| 3505 | *root_level = iterator.level; | ||
| 3506 | shadow_walk_okay(&iterator); | 3506 | shadow_walk_okay(&iterator); |
| 3507 | __shadow_walk_next(&iterator, spte)) { | 3507 | __shadow_walk_next(&iterator, spte)) { |
| 3508 | leaf = iterator.level; | 3508 | leaf = iterator.level; |
| 3509 | spte = mmu_spte_get_lockless(iterator.sptep); | 3509 | spte = mmu_spte_get_lockless(iterator.sptep); |
| 3510 | 3510 | ||
| 3511 | sptes[leaf - 1] = spte; | 3511 | sptes[leaf] = spte; |
| 3512 | 3512 | ||
| 3513 | if (!is_shadow_present_pte(spte)) | 3513 | if (!is_shadow_present_pte(spte)) |
| 3514 | break; | 3514 | break; |
| 3515 | |||
| 3516 | } | 3515 | } |
| 3517 | 3516 | ||
| 3518 | walk_shadow_page_lockless_end(vcpu); | 3517 | walk_shadow_page_lockless_end(vcpu); |
| @@ -3520,14 +3519,12 @@ static int get_walk(struct kvm_vcpu *vcpu, u64 addr, u64 *sptes) · 1 unmodified line | |||
| 3520 | return leaf; | 3519 | return leaf; |
| 3521 | } | 3520 | } |
| 3522 | 3521 | ||
| 3523 | /* return true if reserved bit is detected on spte. */ | 3522 | /* return true if reserved bit(s) are detected on a valid, non-MMIO SPTE. */ |
| 3524 | static bool get_mmio_spte(struct kvm_vcpu *vcpu, u64 addr, u64 *sptep) | 3523 | static bool get_mmio_spte(struct kvm_vcpu *vcpu, u64 addr, u64 *sptep) |
| 3525 | { | 3524 | { |
| 3526 | u64 sptes[PT64_ROOT_MAX_LEVEL]; | 3525 | u64 sptes[PT64_ROOT_MAX_LEVEL + 1]; |
| 3527 | struct rsvd_bits_validate *rsvd_check; | 3526 | struct rsvd_bits_validate *rsvd_check; |
| 3528 | int root = vcpu->arch.mmu->shadow_root_level; | 3527 | int root, leaf, level; |
| 3529 | int leaf; | ||
| 3530 | int level; | ||
| 3531 | bool reserved = false; | 3528 | bool reserved = false; |
| 3532 | 3529 | ||
| 3533 | if (!VALID_PAGE(vcpu->arch.mmu->root_hpa)) { | 3530 | if (!VALID_PAGE(vcpu->arch.mmu->root_hpa)) { |
| @@ -3536,35 +3533,45 @@ static bool get_mmio_spte(struct kvm_vcpu *vcpu, u64 addr, u64 *sptep) · 2 unmodified lines | |||
| 3536 | } | 3533 | } |
| 3537 | 3534 | ||
| 3538 | if (is_tdp_mmu_root(vcpu->kvm, vcpu->arch.mmu->root_hpa)) | 3535 | if (is_tdp_mmu_root(vcpu->kvm, vcpu->arch.mmu->root_hpa)) |
| 3539 | leaf = kvm_tdp_mmu_get_walk(vcpu, addr, sptes); | 3536 | leaf = kvm_tdp_mmu_get_walk(vcpu, addr, sptes, &root); |
| 3540 | else | 3537 | else |
| 3541 | leaf = get_walk(vcpu, addr, sptes); | 3538 | leaf = get_walk(vcpu, addr, sptes, &root); |
| 3539 | |||
| 3540 | if (unlikely(leaf < 0)) { | ||
| 3541 | *sptep = 0ull; | ||
| 3542 | return reserved; | ||
| 3543 | } | ||
| 3544 | |||
| 3545 | *sptep = sptes[leaf]; | ||
| 3546 | |||
| 3547 | /* | ||
| 3548 | * Skip reserved bits checks on the terminal leaf if it's not a valid | ||
| 3549 | * SPTE. Note, this also (intentionally) skips MMIO SPTEs, which, by | ||
| 3550 | * design, always have reserved bits set. The purpose of the checks is | ||
| 3551 | * to detect reserved bits on non-MMIO SPTEs. i.e. buggy SPTEs. | ||
| 3552 | */ | ||
| 3553 | if (!is_shadow_present_pte(sptes[leaf])) | ||
| 3554 | leaf++; | ||
| 3542 | 3555 | ||
| 3543 | rsvd_check = &vcpu->arch.mmu->shadow_zero_check; | 3556 | rsvd_check = &vcpu->arch.mmu->shadow_zero_check; |
| 3544 | 3557 | ||
| 3545 | for (level = root; level >= leaf; level--) { | 3558 | for (level = root; level >= leaf; level--) |
| 3546 | if (!is_shadow_present_pte(sptes[level - 1])) | ||
| 3547 | break; | ||
| 3548 | /* | 3559 | /* |
| 3549 | * Use a bitwise-OR instead of a logical-OR to aggregate the | 3560 | * Use a bitwise-OR instead of a logical-OR to aggregate the |
| 3550 | * reserved bit and EPT's invalid memtype/XWR checks to avoid | 3561 | * reserved bit and EPT's invalid memtype/XWR checks to avoid |
| 3551 | * adding a Jcc in the loop. | 3562 | * adding a Jcc in the loop. |
| 3552 | */ | 3563 | */ |
| 3553 | reserved |= __is_bad_mt_xwr(rsvd_check, sptes[level - 1]) | | 3564 | reserved |= __is_bad_mt_xwr(rsvd_check, sptes[level]) | |
| 3554 | __is_rsvd_bits_set(rsvd_check, sptes[level - 1], | 3565 | __is_rsvd_bits_set(rsvd_check, sptes[level], level); |
| 3555 | level); | ||
| 3556 | } | ||
| 3557 | 3566 | ||
| 3558 | if (reserved) { | 3567 | if (reserved) { |
| 3559 | pr_err("%s: detect reserved bits on spte, addr 0x%llx, dump hierarchy:\n", | 3568 | pr_err("%s: detect reserved bits on spte, addr 0x%llx, dump hierarchy:\n", |
| 3560 | __func__, addr); | 3569 | __func__, addr); |
| 3561 | for (level = root; level >= leaf; level--) | 3570 | for (level = root; level >= leaf; level--) |
| 3562 | pr_err("------ spte 0x%llx level %d.\n", | 3571 | pr_err("------ spte 0x%llx level %d.\n", |
| 3563 | sptes[level - 1], level); | 3572 | sptes[level], level); |
| 3564 | } | 3573 | } |
| 3565 | 3574 | ||
| 3566 | *sptep = sptes[leaf - 1]; | ||
| 3567 | |||
| 3568 | return reserved; | 3575 | return reserved; |
| 3569 | } | 3576 | } |
| 3570 | 3577 | ||
| @@ -44,7 +44,48 @@ void kvm_mmu_uninit_tdp_mmu(struct kvm *kvm) · 43 unmodified lines | |||
| 44 | WARN_ON(!list_empty(&kvm->arch.tdp_mmu_roots)); | 44 | WARN_ON(!list_empty(&kvm->arch.tdp_mmu_roots)); |
| 45 | } | 45 | } |
| 46 | 46 | ||
| 47 | #define for_each_tdp_mmu_root(_kvm, _root) \ | 47 | static void tdp_mmu_put_root(struct kvm *kvm, struct kvm_mmu_page *root) |
| 48 | { | ||
| 49 | if (kvm_mmu_put_root(kvm, root)) | ||
| 50 | kvm_tdp_mmu_free_root(kvm, root); | ||
| 51 | } | ||
| 52 | |||
| 53 | static inline bool tdp_mmu_next_root_valid(struct kvm *kvm, | ||
| 54 | struct kvm_mmu_page *root) | ||
| 55 | { | ||
| 56 | lockdep_assert_held(&kvm->mmu_lock); | ||
| 57 | |||
| 58 | if (list_entry_is_head(root, &kvm->arch.tdp_mmu_roots, link)) | ||
| 59 | return false; | ||
| 60 | |||
| 61 | kvm_mmu_get_root(kvm, root); | ||
| 62 | return true; | ||
| 63 | |||
| 64 | } | ||
| 65 | |||
| 66 | static inline struct kvm_mmu_page *tdp_mmu_next_root(struct kvm *kvm, | ||
| 67 | struct kvm_mmu_page *root) | ||
| 68 | { | ||
| 69 | struct kvm_mmu_page *next_root; | ||
| 70 | |||
| 71 | next_root = list_next_entry(root, link); | ||
| 72 | tdp_mmu_put_root(kvm, root); | ||
| 73 | return next_root; | ||
| 74 | } | ||
| 75 | |||
| 76 | /* | ||
| 77 | * Note: this iterator gets and puts references to the roots it iterates over. | ||
| 78 | * This makes it safe to release the MMU lock and yield within the loop, but | ||
| 79 | * if exiting the loop early, the caller must drop the reference to the most | ||
| 80 | * recent root. (Unless keeping a live reference is desirable.) | ||
| 81 | */ | ||
| 82 | #define for_each_tdp_mmu_root_yield_safe(_kvm, _root) \ | ||
| 83 | for (_root = list_first_entry(&_kvm->arch.tdp_mmu_roots, \ | ||
| 84 | typeof(*_root), link); \ | ||
| 85 | tdp_mmu_next_root_valid(_kvm, _root); \ | ||
| 86 | _root = tdp_mmu_next_root(_kvm, _root)) | ||
| 87 | |||
| 88 | #define for_each_tdp_mmu_root(_kvm, _root) \ | ||
| 48 | list_for_each_entry(_root, &_kvm->arch.tdp_mmu_roots, link) | 89 | list_for_each_entry(_root, &_kvm->arch.tdp_mmu_roots, link) |
| 49 | 90 | ||
| 50 | bool is_tdp_mmu_root(struct kvm *kvm, hpa_t hpa) | 91 | bool is_tdp_mmu_root(struct kvm *kvm, hpa_t hpa) |
| @@ -447,18 +488,9 @@ bool kvm_tdp_mmu_zap_gfn_range(struct kvm *kvm, gfn_t start, gfn_t end) · 396 unmodified lines | |||
| 447 | struct kvm_mmu_page *root; | 488 | struct kvm_mmu_page *root; |
| 448 | bool flush = false; | 489 | bool flush = false; |
| 449 | 490 | ||
| 450 | for_each_tdp_mmu_root(kvm, root) { | 491 | for_each_tdp_mmu_root_yield_safe(kvm, root) |
| 451 | /* | ||
| 452 | * Take a reference on the root so that it cannot be freed if | ||
| 453 | * this thread releases the MMU lock and yields in this loop. | ||
| 454 | */ | ||
| 455 | kvm_mmu_get_root(kvm, root); | ||
| 456 | |||
| 457 | flush |= zap_gfn_range(kvm, root, start, end, true); | 492 | flush |= zap_gfn_range(kvm, root, start, end, true); |
| 458 | 493 | ||
| 459 | kvm_mmu_put_root(kvm, root); | ||
| 460 | } | ||
| 461 | |||
| 462 | return flush; | 494 | return flush; |
| 463 | } | 495 | } |
| 464 | 496 | ||
| @@ -619,13 +651,7 @@ static int kvm_tdp_mmu_handle_hva_range(struct kvm *kvm, unsigned long start, · 154 unmodified lines | |||
| 619 | int ret = 0; | 651 | int ret = 0; |
| 620 | int as_id; | 652 | int as_id; |
| 621 | 653 | ||
| 622 | for_each_tdp_mmu_root(kvm, root) { | 654 | for_each_tdp_mmu_root_yield_safe(kvm, root) { |
| 623 | /* | ||
| 624 | * Take a reference on the root so that it cannot be freed if | ||
| 625 | * this thread releases the MMU lock and yields in this loop. | ||
| 626 | */ | ||
| 627 | kvm_mmu_get_root(kvm, root); | ||
| 628 | |||
| 629 | as_id = kvm_mmu_page_as_id(root); | 655 | as_id = kvm_mmu_page_as_id(root); |
| 630 | slots = __kvm_memslots(kvm, as_id); | 656 | slots = __kvm_memslots(kvm, as_id); |
| 631 | kvm_for_each_memslot(memslot, slots) { | 657 | kvm_for_each_memslot(memslot, slots) { |
| @@ -647,8 +673,6 @@ static int kvm_tdp_mmu_handle_hva_range(struct kvm *kvm, unsigned long start, · 15 unmodified lines | |||
| 647 | ret |= handler(kvm, memslot, root, gfn_start, | 673 | ret |= handler(kvm, memslot, root, gfn_start, |
| 648 | gfn_end, data); | 674 | gfn_end, data); |
| 649 | } | 675 | } |
| 650 | |||
| 651 | kvm_mmu_put_root(kvm, root); | ||
| 652 | } | 676 | } |
| 653 | 677 | ||
| 654 | return ret; | 678 | return ret; |
| @@ -838,21 +862,13 @@ bool kvm_tdp_mmu_wrprot_slot(struct kvm *kvm, struct kvm_memory_slot *slot, · 183 unmodified lines | |||
| 838 | int root_as_id; | 862 | int root_as_id; |
| 839 | bool spte_set = false; | 863 | bool spte_set = false; |
| 840 | 864 | ||
| 841 | for_each_tdp_mmu_root(kvm, root) { | 865 | for_each_tdp_mmu_root_yield_safe(kvm, root) { |
| 842 | root_as_id = kvm_mmu_page_as_id(root); | 866 | root_as_id = kvm_mmu_page_as_id(root); |
| 843 | if (root_as_id != slot->as_id) | 867 | if (root_as_id != slot->as_id) |
| 844 | continue; | 868 | continue; |
| 845 | 869 | ||
| 846 | /* | ||
| 847 | * Take a reference on the root so that it cannot be freed if | ||
| 848 | * this thread releases the MMU lock and yields in this loop. | ||
| 849 | */ | ||
| 850 | kvm_mmu_get_root(kvm, root); | ||
| 851 | |||
| 852 | spte_set |= wrprot_gfn_range(kvm, root, slot->base_gfn, | 870 | spte_set |= wrprot_gfn_range(kvm, root, slot->base_gfn, |
| 853 | slot->base_gfn + slot->npages, min_level); | 871 | slot->base_gfn + slot->npages, min_level); |
| 854 | |||
| 855 | kvm_mmu_put_root(kvm, root); | ||
| 856 | } | 872 | } |
| 857 | 873 | ||
| 858 | return spte_set; | 874 | return spte_set; |
| @@ -906,21 +922,13 @@ bool kvm_tdp_mmu_clear_dirty_slot(struct kvm *kvm, struct kvm_memory_slot *slot) · 47 unmodified lines | |||
| 906 | int root_as_id; | 922 | int root_as_id; |
| 907 | bool spte_set = false; | 923 | bool spte_set = false; |
| 908 | 924 | ||
| 909 | for_each_tdp_mmu_root(kvm, root) { | 925 | for_each_tdp_mmu_root_yield_safe(kvm, root) { |
| 910 | root_as_id = kvm_mmu_page_as_id(root); | 926 | root_as_id = kvm_mmu_page_as_id(root); |
| 911 | if (root_as_id != slot->as_id) | 927 | if (root_as_id != slot->as_id) |
| 912 | continue; | 928 | continue; |
| 913 | 929 | ||
| 914 | /* | ||
| 915 | * Take a reference on the root so that it cannot be freed if | ||
| 916 | * this thread releases the MMU lock and yields in this loop. | ||
| 917 | */ | ||
| 918 | kvm_mmu_get_root(kvm, root); | ||
| 919 | |||
| 920 | spte_set |= clear_dirty_gfn_range(kvm, root, slot->base_gfn, | 930 | spte_set |= clear_dirty_gfn_range(kvm, root, slot->base_gfn, |
| 921 | slot->base_gfn + slot->npages); | 931 | slot->base_gfn + slot->npages); |
| 922 | |||
| 923 | kvm_mmu_put_root(kvm, root); | ||
| 924 | } | 932 | } |
| 925 | 933 | ||
| 926 | return spte_set; | 934 | return spte_set; |
| @@ -1029,28 +1037,20 @@ bool kvm_tdp_mmu_slot_set_dirty(struct kvm *kvm, struct kvm_memory_slot *slot) · 102 unmodified lines | |||
| 1029 | int root_as_id; | 1037 | int root_as_id; |
| 1030 | bool spte_set = false; | 1038 | bool spte_set = false; |
| 1031 | 1039 | ||
| 1032 | for_each_tdp_mmu_root(kvm, root) { | 1040 | for_each_tdp_mmu_root_yield_safe(kvm, root) { |
| 1033 | root_as_id = kvm_mmu_page_as_id(root); | 1041 | root_as_id = kvm_mmu_page_as_id(root); |
| 1034 | if (root_as_id != slot->as_id) | 1042 | if (root_as_id != slot->as_id) |
| 1035 | continue; | 1043 | continue; |
| 1036 | 1044 | ||
| 1037 | /* | ||
| 1038 | * Take a reference on the root so that it cannot be freed if | ||
| 1039 | * this thread releases the MMU lock and yields in this loop. | ||
| 1040 | */ | ||
| 1041 | kvm_mmu_get_root(kvm, root); | ||
| 1042 | |||
| 1043 | spte_set |= set_dirty_gfn_range(kvm, root, slot->base_gfn, | 1045 | spte_set |= set_dirty_gfn_range(kvm, root, slot->base_gfn, |
| 1044 | slot->base_gfn + slot->npages); | 1046 | slot->base_gfn + slot->npages); |
| 1045 | |||
| 1046 | kvm_mmu_put_root(kvm, root); | ||
| 1047 | } | 1047 | } |
| 1048 | return spte_set; | 1048 | return spte_set; |
| 1049 | } | 1049 | } |
| 1050 | 1050 | ||
| 1051 | /* | 1051 | /* |
| 1052 | * Clear non-leaf entries (and free associated page tables) which could | 1052 | * Clear leaf entries which could be replaced by large mappings, for |
| 1053 | * be replaced by large mappings, for GFNs within the slot. | 1053 | * GFNs within the slot. |
| 1054 | */ | 1054 | */ |
| 1055 | static void zap_collapsible_spte_range(struct kvm *kvm, | 1055 | static void zap_collapsible_spte_range(struct kvm *kvm, |
| 1056 | struct kvm_mmu_page *root, | 1056 | struct kvm_mmu_page *root, |
| @@ -1062,7 +1062,7 @@ static void zap_collapsible_spte_range(struct kvm *kvm, · 5 unmodified lines | |||
| 1062 | 1062 | ||
| 1063 | tdp_root_for_each_pte(iter, root, start, end) { | 1063 | tdp_root_for_each_pte(iter, root, start, end) { |
| 1064 | if (!is_shadow_present_pte(iter.old_spte) || | 1064 | if (!is_shadow_present_pte(iter.old_spte) || |
| 1065 | is_last_spte(iter.old_spte, iter.level)) | 1065 | !is_last_spte(iter.old_spte, iter.level)) |
| 1066 | continue; | 1066 | continue; |
| 1067 | 1067 | ||
| 1068 | pfn = spte_to_pfn(iter.old_spte); | 1068 | pfn = spte_to_pfn(iter.old_spte); |
| @@ -1089,21 +1089,13 @@ void kvm_tdp_mmu_zap_collapsible_sptes(struct kvm *kvm, · 20 unmodified lines | |||
| 1089 | struct kvm_mmu_page *root; | 1089 | struct kvm_mmu_page *root; |
| 1090 | int root_as_id; | 1090 | int root_as_id; |
| 1091 | 1091 | ||
| 1092 | for_each_tdp_mmu_root(kvm, root) { | 1092 | for_each_tdp_mmu_root_yield_safe(kvm, root) { |
| 1093 | root_as_id = kvm_mmu_page_as_id(root); | 1093 | root_as_id = kvm_mmu_page_as_id(root); |
| 1094 | if (root_as_id != slot->as_id) | 1094 | if (root_as_id != slot->as_id) |
| 1095 | continue; | 1095 | continue; |
| 1096 | 1096 | ||
| 1097 | /* | ||
| 1098 | * Take a reference on the root so that it cannot be freed if | ||
| 1099 | * this thread releases the MMU lock and yields in this loop. | ||
| 1100 | */ | ||
| 1101 | kvm_mmu_get_root(kvm, root); | ||
| 1102 | |||
| 1103 | zap_collapsible_spte_range(kvm, root, slot->base_gfn, | 1097 | zap_collapsible_spte_range(kvm, root, slot->base_gfn, |
| 1104 | slot->base_gfn + slot->npages); | 1098 | slot->base_gfn + slot->npages); |
| 1105 | |||
| 1106 | kvm_mmu_put_root(kvm, root); | ||
| 1107 | } | 1099 | } |
| 1108 | } | 1100 | } |
| 1109 | 1101 | ||
| @@ -1160,16 +1152,19 @@ bool kvm_tdp_mmu_write_protect_gfn(struct kvm *kvm, · 50 unmodified lines | |||
| 1160 | * Return the level of the lowest level SPTE added to sptes. | 1152 | * Return the level of the lowest level SPTE added to sptes. |
| 1161 | * That SPTE may be non-present. | 1153 | * That SPTE may be non-present. |
| 1162 | */ | 1154 | */ |
| 1163 | int kvm_tdp_mmu_get_walk(struct kvm_vcpu *vcpu, u64 addr, u64 *sptes) | 1155 | int kvm_tdp_mmu_get_walk(struct kvm_vcpu *vcpu, u64 addr, u64 *sptes, |
| 1156 | int *root_level) | ||
| 1164 | { | 1157 | { |
| 1165 | struct tdp_iter iter; | 1158 | struct tdp_iter iter; |
| 1166 | struct kvm_mmu *mmu = vcpu->arch.mmu; | 1159 | struct kvm_mmu *mmu = vcpu->arch.mmu; |
| 1167 | int leaf = vcpu->arch.mmu->shadow_root_level; | ||
| 1168 | gfn_t gfn = addr >> PAGE_SHIFT; | 1160 | gfn_t gfn = addr >> PAGE_SHIFT; |
| 1161 | int leaf = -1; | ||
| 1162 | |||
| 1163 | *root_level = vcpu->arch.mmu->shadow_root_level; | ||
| 1169 | 1164 | ||
| 1170 | tdp_mmu_for_each_pte(iter, mmu, gfn, gfn + 1) { | 1165 | tdp_mmu_for_each_pte(iter, mmu, gfn, gfn + 1) { |
| 1171 | leaf = iter.level; | 1166 | leaf = iter.level; |
| 1172 | sptes[leaf - 1] = iter.old_spte; | 1167 | sptes[leaf] = iter.old_spte; |
| 1173 | } | 1168 | } |
| 1174 | 1169 | ||
| 1175 | return leaf; | 1170 | return leaf; |
| @@ -44,5 +44,7 @@ void kvm_tdp_mmu_zap_collapsible_sptes(struct kvm *kvm, · 43 unmodified lines | |||
| 44 | bool kvm_tdp_mmu_write_protect_gfn(struct kvm *kvm, | 44 | bool kvm_tdp_mmu_write_protect_gfn(struct kvm *kvm, |
| 45 | struct kvm_memory_slot *slot, gfn_t gfn); | 45 | struct kvm_memory_slot *slot, gfn_t gfn); |
| 46 | 46 | ||
| 47 | int kvm_tdp_mmu_get_walk(struct kvm_vcpu *vcpu, u64 addr, u64 *sptes); | 47 | int kvm_tdp_mmu_get_walk(struct kvm_vcpu *vcpu, u64 addr, u64 *sptes, |
| 48 | int *root_level); | ||
| 49 | |||
| 48 | #endif /* __KVM_X86_MMU_TDP_MMU_H */ | 50 | #endif /* __KVM_X86_MMU_TDP_MMU_H */ |
| @@ -199,6 +199,10 @@ static bool nested_svm_vmrun_msrpm(struct vcpu_svm *svm) · 198 unmodified lines | |||
| 199 | static bool svm_get_nested_state_pages(struct kvm_vcpu *vcpu) | 199 | static bool svm_get_nested_state_pages(struct kvm_vcpu *vcpu) |
| 200 | { | 200 | { |
| 201 | struct vcpu_svm *svm = to_svm(vcpu); | 201 | struct vcpu_svm *svm = to_svm(vcpu); |
| 202 | |||
| 203 | if (WARN_ON(!is_guest_mode(vcpu))) | ||
| 204 | return true; | ||
| 205 | |||
| 202 | if (!nested_svm_vmrun_msrpm(svm)) { | 206 | if (!nested_svm_vmrun_msrpm(svm)) { |
| 203 | vcpu->run->exit_reason = KVM_EXIT_INTERNAL_ERROR; | 207 | vcpu->run->exit_reason = KVM_EXIT_INTERNAL_ERROR; |
| 204 | vcpu->run->internal.suberror = | 208 | vcpu->run->internal.suberror = |
| @@ -227,6 +231,7 @@ static bool nested_vmcb_check_controls(struct vmcb_control_area *control) · 22 unmodified lines | |||
| 227 | 231 | ||
| 228 | static bool nested_vmcb_checks(struct vcpu_svm *svm, struct vmcb *vmcb12) | 232 | static bool nested_vmcb_checks(struct vcpu_svm *svm, struct vmcb *vmcb12) |
| 229 | { | 233 | { |
| 234 | struct kvm_vcpu *vcpu = &svm->vcpu; | ||
| 230 | bool vmcb12_lma; | 235 | bool vmcb12_lma; |
| 231 | 236 | ||
| 232 | if ((vmcb12->save.efer & EFER_SVME) == 0) | 237 | if ((vmcb12->save.efer & EFER_SVME) == 0) |
| @@ -240,18 +245,10 @@ static bool nested_vmcb_checks(struct vcpu_svm *svm, struct vmcb *vmcb12) · 7 unmodified lines | |||
| 240 | 245 | ||
| 241 | vmcb12_lma = (vmcb12->save.efer & EFER_LME) && (vmcb12->save.cr0 & X86_CR0_PG); | 246 | vmcb12_lma = (vmcb12->save.efer & EFER_LME) && (vmcb12->save.cr0 & X86_CR0_PG); |
| 242 | 247 | ||
| 243 | if (!vmcb12_lma) { | 248 | if (vmcb12_lma) { |
| 244 | if (vmcb12->save.cr4 & X86_CR4_PAE) { | ||
| 245 | if (vmcb12->save.cr3 & MSR_CR3_LEGACY_PAE_RESERVED_MASK) | ||
| 246 | return false; | ||
| 247 | } else { | ||
| 248 | if (vmcb12->save.cr3 & MSR_CR3_LEGACY_RESERVED_MASK) | ||
| 249 | return false; | ||
| 250 | } | ||
| 251 | } else { | ||
| 252 | if (!(vmcb12->save.cr4 & X86_CR4_PAE) || | 249 | if (!(vmcb12->save.cr4 & X86_CR4_PAE) || |
| 253 | !(vmcb12->save.cr0 & X86_CR0_PE) || | 250 | !(vmcb12->save.cr0 & X86_CR0_PE) || |
| 254 | (vmcb12->save.cr3 & MSR_CR3_LONG_MBZ_MASK)) | 251 | (vmcb12->save.cr3 & vcpu->arch.cr3_lm_rsvd_bits)) |
| 255 | return false; | 252 | return false; |
| 256 | } | 253 | } |
| 257 | if (!kvm_is_valid_cr4(&svm->vcpu, vmcb12->save.cr4)) | 254 | if (!kvm_is_valid_cr4(&svm->vcpu, vmcb12->save.cr4)) |
| @@ -595,6 +592,8 @@ int nested_svm_vmexit(struct vcpu_svm *svm) · 337 unmodified lines | |||
| 595 | svm->nested.vmcb12_gpa = 0; | 592 | svm->nested.vmcb12_gpa = 0; |
| 596 | WARN_ON_ONCE(svm->nested.nested_run_pending); | 593 | WARN_ON_ONCE(svm->nested.nested_run_pending); |
| 597 | 594 | ||
| 595 | kvm_clear_request(KVM_REQ_GET_NESTED_STATE_PAGES, &svm->vcpu); | ||
| 596 | |||
| 598 | /* in case we halted in L2 */ | 597 | /* in case we halted in L2 */ |
| 599 | svm->vcpu.arch.mp_state = KVM_MP_STATE_RUNNABLE; | 598 | svm->vcpu.arch.mp_state = KVM_MP_STATE_RUNNABLE; |
| 600 | 599 | ||
| @@ -754,6 +753,7 @@ void svm_leave_nested(struct vcpu_svm *svm) · 153 unmodified lines | |||
| 754 | leave_guest_mode(&svm->vcpu); | 753 | leave_guest_mode(&svm->vcpu); |
| 755 | copy_vmcb_control_area(&vmcb->control, &hsave->control); | 754 | copy_vmcb_control_area(&vmcb->control, &hsave->control); |
| 756 | nested_svm_uninit_mmu_context(&svm->vcpu); | 755 | nested_svm_uninit_mmu_context(&svm->vcpu); |
| 756 | vmcb_mark_all_dirty(svm->vmcb); | ||
| 757 | } | 757 | } |
| 758 | 758 | ||
| 759 | kvm_clear_request(KVM_REQ_GET_NESTED_STATE_PAGES, &svm->vcpu); | 759 | kvm_clear_request(KVM_REQ_GET_NESTED_STATE_PAGES, &svm->vcpu); |
| @@ -1194,6 +1194,10 @@ static int svm_set_nested_state(struct kvm_vcpu *vcpu, · 434 unmodified lines | |||
| 1194 | * in the registers, the save area of the nested state instead | 1194 | * in the registers, the save area of the nested state instead |
| 1195 | * contains saved L1 state. | 1195 | * contains saved L1 state. |
| 1196 | */ | 1196 | */ |
| 1197 | |||
| 1198 | svm->nested.nested_run_pending = | ||
| 1199 | !!(kvm_state->flags & KVM_STATE_NESTED_RUN_PENDING); | ||
| 1200 | |||
| 1197 | copy_vmcb_control_area(&hsave->control, &svm->vmcb->control); | 1201 | copy_vmcb_control_area(&hsave->control, &svm->vmcb->control); |
| 1198 | hsave->save = *save; | 1202 | hsave->save = *save; |
| 1199 | 1203 | ||
| @@ -342,6 +342,8 @@ static struct page **sev_pin_memory(struct kvm *kvm, unsigned long uaddr, · 341 unmodified lines | |||
| 342 | unsigned long first, last; | 342 | unsigned long first, last; |
| 343 | int ret; | 343 | int ret; |
| 344 | 344 | ||
| 345 | lockdep_assert_held(&kvm->lock); | ||
| 346 | |||
| 345 | if (ulen == 0 || uaddr + ulen < uaddr) | 347 | if (ulen == 0 || uaddr + ulen < uaddr) |
| 346 | return ERR_PTR(-EINVAL); | 348 | return ERR_PTR(-EINVAL); |
| 347 | 349 | ||
| @@ -1119,12 +1121,20 @@ int svm_register_enc_region(struct kvm *kvm, · 771 unmodified lines | |||
| 1119 | if (!region) | 1121 | if (!region) |
| 1120 | return -ENOMEM; | 1122 | return -ENOMEM; |
| 1121 | 1123 | ||
| 1124 | mutex_lock(&kvm->lock); | ||
| 1122 | region->pages = sev_pin_memory(kvm, range->addr, range->size, ®ion->npages, 1); | 1125 | region->pages = sev_pin_memory(kvm, range->addr, range->size, ®ion->npages, 1); |
| 1123 | if (IS_ERR(region->pages)) { | 1126 | if (IS_ERR(region->pages)) { |
| 1124 | ret = PTR_ERR(region->pages); | 1127 | ret = PTR_ERR(region->pages); |
| 1128 | mutex_unlock(&kvm->lock); | ||
| 1125 | goto e_free; | 1129 | goto e_free; |
| 1126 | } | 1130 | } |
| 1127 | 1131 | ||
| 1132 | region->uaddr = range->addr; | ||
| 1133 | region->size = range->size; | ||
| 1134 | |||
| 1135 | list_add_tail(®ion->list, &sev->regions_list); | ||
| 1136 | mutex_unlock(&kvm->lock); | ||
| 1137 | |||
| 1128 | /* | 1138 | /* |
| 1129 | * The guest may change the memory encryption attribute from C=0 -> C=1 | 1139 | * The guest may change the memory encryption attribute from C=0 -> C=1 |
| 1130 | * or vice versa for this memory range. Lets make sure caches are | 1140 | * or vice versa for this memory range. Lets make sure caches are |
| @@ -1133,13 +1143,6 @@ int svm_register_enc_region(struct kvm *kvm, · 2 unmodified lines | |||
| 1133 | */ | 1143 | */ |
| 1134 | sev_clflush_pages(region->pages, region->npages); | 1144 | sev_clflush_pages(region->pages, region->npages); |
| 1135 | 1145 | ||
| 1136 | region->uaddr = range->addr; | ||
| 1137 | region->size = range->size; | ||
| 1138 | |||
| 1139 | mutex_lock(&kvm->lock); | ||
| 1140 | list_add_tail(®ion->list, &sev->regions_list); | ||
| 1141 | mutex_unlock(&kvm->lock); | ||
| 1142 | |||
| 1143 | return ret; | 1146 | return ret; |
| 1144 | 1147 | ||
| 1145 | e_free: | 1148 | e_free: |
| @@ -1415,16 +1418,13 @@ static void sev_es_sync_to_ghcb(struct vcpu_svm *svm) · 269 unmodified lines | |||
| 1415 | * to be returned: | 1418 | * to be returned: |
| 1416 | * GPRs RAX, RBX, RCX, RDX | 1419 | * GPRs RAX, RBX, RCX, RDX |
| 1417 | * | 1420 | * |
| 1418 | * Copy their values to the GHCB if they are dirty. | 1421 | * Copy their values, even if they may not have been written during the |
| 1422 | * VM-Exit. It's the guest's responsibility to not consume random data. | ||
| 1419 | */ | 1423 | */ |
| 1420 | if (kvm_register_is_dirty(vcpu, VCPU_REGS_RAX)) | 1424 | ghcb_set_rax(ghcb, vcpu->arch.regs[VCPU_REGS_RAX]); |
| 1421 | ghcb_set_rax(ghcb, vcpu->arch.regs[VCPU_REGS_RAX]); | 1425 | ghcb_set_rbx(ghcb, vcpu->arch.regs[VCPU_REGS_RBX]); |
| 1422 | if (kvm_register_is_dirty(vcpu, VCPU_REGS_RBX)) | 1426 | ghcb_set_rcx(ghcb, vcpu->arch.regs[VCPU_REGS_RCX]); |
| 1423 | ghcb_set_rbx(ghcb, vcpu->arch.regs[VCPU_REGS_RBX]); | 1427 | ghcb_set_rdx(ghcb, vcpu->arch.regs[VCPU_REGS_RDX]); |
| 1424 | if (kvm_register_is_dirty(vcpu, VCPU_REGS_RCX)) | ||
| 1425 | ghcb_set_rcx(ghcb, vcpu->arch.regs[VCPU_REGS_RCX]); | ||
| 1426 | if (kvm_register_is_dirty(vcpu, VCPU_REGS_RDX)) | ||
| 1427 | ghcb_set_rdx(ghcb, vcpu->arch.regs[VCPU_REGS_RDX]); | ||
| 1428 | } | 1428 | } |
| 1429 | 1429 | ||
| 1430 | static void sev_es_sync_from_ghcb(struct vcpu_svm *svm) | 1430 | static void sev_es_sync_from_ghcb(struct vcpu_svm *svm) |
| @@ -1563,6 +1563,7 @@ static int sev_es_validate_vmgexit(struct vcpu_svm *svm) · 132 unmodified lines | |||
| 1563 | goto vmgexit_err; | 1563 | goto vmgexit_err; |
| 1564 | break; | 1564 | break; |
| 1565 | case SVM_VMGEXIT_NMI_COMPLETE: | 1565 | case SVM_VMGEXIT_NMI_COMPLETE: |
| 1566 | case SVM_VMGEXIT_AP_HLT_LOOP: | ||
| 1566 | case SVM_VMGEXIT_AP_JUMP_TABLE: | 1567 | case SVM_VMGEXIT_AP_JUMP_TABLE: |
| 1567 | case SVM_VMGEXIT_UNSUPPORTED_EVENT: | 1568 | case SVM_VMGEXIT_UNSUPPORTED_EVENT: |
| 1568 | break; | 1569 | break; |
| @@ -1888,6 +1889,9 @@ int sev_handle_vmgexit(struct vcpu_svm *svm) · 319 unmodified lines | |||
| 1888 | case SVM_VMGEXIT_NMI_COMPLETE: | 1889 | case SVM_VMGEXIT_NMI_COMPLETE: |
| 1889 | ret = svm_invoke_exit_handler(svm, SVM_EXIT_IRET); | 1890 | ret = svm_invoke_exit_handler(svm, SVM_EXIT_IRET); |
| 1890 | break; | 1891 | break; |
| 1892 | case SVM_VMGEXIT_AP_HLT_LOOP: | ||
| 1893 | ret = kvm_emulate_ap_reset_hold(&svm->vcpu); | ||
| 1894 | break; | ||
| 1891 | case SVM_VMGEXIT_AP_JUMP_TABLE: { | 1895 | case SVM_VMGEXIT_AP_JUMP_TABLE: { |
| 1892 | struct kvm_sev_info *sev = &to_kvm_svm(svm->vcpu.kvm)->sev_info; | 1896 | struct kvm_sev_info *sev = &to_kvm_svm(svm->vcpu.kvm)->sev_info; |
| 1893 | 1897 | ||
| @@ -2001,7 +2005,7 @@ void sev_es_vcpu_load(struct vcpu_svm *svm, int cpu) · 107 unmodified lines | |||
| 2001 | * of which one step is to perform a VMLOAD. Since hardware does not | 2005 | * of which one step is to perform a VMLOAD. Since hardware does not |
| 2002 | * perform a VMSAVE on VMRUN, the host savearea must be updated. | 2006 | * perform a VMSAVE on VMRUN, the host savearea must be updated. |
| 2003 | */ | 2007 | */ |
| 2004 | asm volatile(__ex("vmsave") : : "a" (__sme_page_pa(sd->save_area)) : "memory"); | 2008 | asm volatile(__ex("vmsave %0") : : "a" (__sme_page_pa(sd->save_area)) : "memory"); |
| 2005 | 2009 | ||
| 2006 | /* | 2010 | /* |
| 2007 | * Certain MSRs are restored on VMEXIT, only save ones that aren't | 2011 | * Certain MSRs are restored on VMEXIT, only save ones that aren't |
| @@ -2040,3 +2044,21 @@ void sev_es_vcpu_put(struct vcpu_svm *svm) · 32 unmodified lines | |||
| 2040 | wrmsrl(host_save_user_msrs[i].index, svm->host_user_msrs[i]); | 2044 | wrmsrl(host_save_user_msrs[i].index, svm->host_user_msrs[i]); |
| 2041 | } | 2045 | } |
| 2042 | } | 2046 | } |
| 2047 | |||
| 2048 | void sev_vcpu_deliver_sipi_vector(struct kvm_vcpu *vcpu, u8 vector) | ||
| 2049 | { | ||
| 2050 | struct vcpu_svm *svm = to_svm(vcpu); | ||
| 2051 | |||
| 2052 | /* First SIPI: Use the values as initially set by the VMM */ | ||
| 2053 | if (!svm->received_first_sipi) { | ||
| 2054 | svm->received_first_sipi = true; | ||
| 2055 | return; | ||
| 2056 | } | ||
| 2057 | |||
| 2058 | /* | ||
| 2059 | * Subsequent SIPI: Return from an AP Reset Hold VMGEXIT, where | ||
| 2060 | * the guest will set the CS and RIP. Set SW_EXIT_INFO_2 to a | ||
| 2061 | * non-zero value. | ||
| 2062 | */ | ||
| 2063 | ghcb_set_sw_exit_info_2(svm->ghcb, 1); | ||
| 2064 | } | ||
| @@ -454,6 +454,11 @@ static int has_svm(void) · 453 unmodified lines | |||
| 454 | return 0; | 454 | return 0; |
| 455 | } | 455 | } |
| 456 | 456 | ||
| 457 | if (sev_active()) { | ||
| 458 | pr_info("KVM is unsupported when running as an SEV guest\n"); | ||
| 459 | return 0; | ||
| 460 | } | ||
| 461 | |||
| 457 | return 1; | 462 | return 1; |
| 458 | } | 463 | } |
| 459 | 464 | ||
| @@ -3677,8 +3682,6 @@ static fastpath_t svm_exit_handlers_fastpath(struct kvm_vcpu *vcpu) · 3217 unmodified lines | |||
| 3677 | return EXIT_FASTPATH_NONE; | 3682 | return EXIT_FASTPATH_NONE; |
| 3678 | } | 3683 | } |
| 3679 | 3684 | ||
| 3680 | void __svm_vcpu_run(unsigned long vmcb_pa, unsigned long *regs); | ||
| 3681 | |||
| 3682 | static noinstr void svm_vcpu_enter_exit(struct kvm_vcpu *vcpu, | 3685 | static noinstr void svm_vcpu_enter_exit(struct kvm_vcpu *vcpu, |
| 3683 | struct vcpu_svm *svm) | 3686 | struct vcpu_svm *svm) |
| 3684 | { | 3687 | { |
| @@ -3741,6 +3744,8 @@ static __no_kcsan fastpath_t svm_vcpu_run(struct kvm_vcpu *vcpu) · 56 unmodified lines | |||
| 3741 | { | 3744 | { |
| 3742 | struct vcpu_svm *svm = to_svm(vcpu); | 3745 | struct vcpu_svm *svm = to_svm(vcpu); |
| 3743 | 3746 | ||
| 3747 | trace_kvm_entry(vcpu); | ||
| 3748 | |||
| 3744 | svm->vmcb->save.rax = vcpu->arch.regs[VCPU_REGS_RAX]; | 3749 | svm->vmcb->save.rax = vcpu->arch.regs[VCPU_REGS_RAX]; |
| 3745 | svm->vmcb->save.rsp = vcpu->arch.regs[VCPU_REGS_RSP]; | 3750 | svm->vmcb->save.rsp = vcpu->arch.regs[VCPU_REGS_RSP]; |
| 3746 | svm->vmcb->save.rip = vcpu->arch.regs[VCPU_REGS_RIP]; | 3751 | svm->vmcb->save.rip = vcpu->arch.regs[VCPU_REGS_RIP]; |
| @@ -4384,6 +4389,14 @@ static bool svm_apic_init_signal_blocked(struct kvm_vcpu *vcpu) · 637 unmodified lines | |||
| 4384 | (vmcb_is_intercept(&svm->vmcb->control, INTERCEPT_INIT)); | 4389 | (vmcb_is_intercept(&svm->vmcb->control, INTERCEPT_INIT)); |
| 4385 | } | 4390 | } |
| 4386 | 4391 | ||
| 4392 | static void svm_vcpu_deliver_sipi_vector(struct kvm_vcpu *vcpu, u8 vector) | ||
| 4393 | { | ||
| 4394 | if (!sev_es_guest(vcpu->kvm)) | ||
| 4395 | return kvm_vcpu_deliver_sipi_vector(vcpu, vector); | ||
| 4396 | |||
| 4397 | sev_vcpu_deliver_sipi_vector(vcpu, vector); | ||
| 4398 | } | ||
| 4399 | |||
| 4387 | static void svm_vm_destroy(struct kvm *kvm) | 4400 | static void svm_vm_destroy(struct kvm *kvm) |
| 4388 | { | 4401 | { |
| 4389 | avic_vm_destroy(kvm); | 4402 | avic_vm_destroy(kvm); |
| @@ -4526,6 +4539,8 @@ static struct kvm_x86_ops svm_x86_ops __initdata = { · 136 unmodified lines | |||
| 4526 | 4539 | ||
| 4527 | .msr_filter_changed = svm_msr_filter_changed, | 4540 | .msr_filter_changed = svm_msr_filter_changed, |
| 4528 | .complete_emulated_msr = svm_complete_emulated_msr, | 4541 | .complete_emulated_msr = svm_complete_emulated_msr, |
| 4542 | |||
| 4543 | .vcpu_deliver_sipi_vector = svm_vcpu_deliver_sipi_vector, | ||
| 4529 | }; | 4544 | }; |
| 4530 | 4545 | ||
| 4531 | static struct kvm_x86_init_ops svm_init_ops __initdata = { | 4546 | static struct kvm_x86_init_ops svm_init_ops __initdata = { |
| @@ -185,6 +185,7 @@ struct vcpu_svm { · 184 unmodified lines | |||
| 185 | struct vmcb_save_area *vmsa; | 185 | struct vmcb_save_area *vmsa; |
| 186 | struct ghcb *ghcb; | 186 | struct ghcb *ghcb; |
| 187 | struct kvm_host_map ghcb_map; | 187 | struct kvm_host_map ghcb_map; |
| 188 | bool received_first_sipi; | ||
| 188 | 189 | ||
| 189 | /* SEV-ES scratch area support */ | 190 | /* SEV-ES scratch area support */ |
| 190 | void *ghcb_sa; | 191 | void *ghcb_sa; |
| @@ -402,9 +403,6 @@ static inline bool gif_set(struct vcpu_svm *svm) · 211 unmodified lines | |||
| 402 | } | 403 | } |
| 403 | 404 | ||
| 404 | /* svm.c */ | 405 | /* svm.c */ |
| 405 | #define MSR_CR3_LEGACY_RESERVED_MASK 0xfe7U | ||
| 406 | #define MSR_CR3_LEGACY_PAE_RESERVED_MASK 0x7U | ||
| 407 | #define MSR_CR3_LONG_MBZ_MASK 0xfff0000000000000U | ||
| 408 | #define MSR_INVALID 0xffffffffU | 406 | #define MSR_INVALID 0xffffffffU |
| 409 | 407 | ||
| 410 | extern int sev; | 408 | extern int sev; |
| @@ -591,6 +589,7 @@ void sev_es_init_vmcb(struct vcpu_svm *svm); · 180 unmodified lines | |||
| 591 | void sev_es_create_vcpu(struct vcpu_svm *svm); | 589 | void sev_es_create_vcpu(struct vcpu_svm *svm); |
| 592 | void sev_es_vcpu_load(struct vcpu_svm *svm, int cpu); | 590 | void sev_es_vcpu_load(struct vcpu_svm *svm, int cpu); |
| 593 | void sev_es_vcpu_put(struct vcpu_svm *svm); | 591 | void sev_es_vcpu_put(struct vcpu_svm *svm); |
| 592 | void sev_vcpu_deliver_sipi_vector(struct kvm_vcpu *vcpu, u8 vector); | ||
| 594 | 593 | ||
| 595 | /* vmenter.S */ | 594 | /* vmenter.S */ |
| 596 | 595 | ||
| @@ -3124,13 +3124,9 @@ static int nested_vmx_check_vmentry_hw(struct kvm_vcpu *vcpu) · 3123 unmodified lines | |||
| 3124 | return 0; | 3124 | return 0; |
| 3125 | } | 3125 | } |
| 3126 | 3126 | ||
| 3127 | static bool nested_get_vmcs12_pages(struct kvm_vcpu *vcpu) | 3127 | static bool nested_get_evmcs_page(struct kvm_vcpu *vcpu) |
| 3128 | { | 3128 | { |
| 3129 | struct vmcs12 *vmcs12 = get_vmcs12(vcpu); | ||
| 3130 | struct vcpu_vmx *vmx = to_vmx(vcpu); | 3129 | struct vcpu_vmx *vmx = to_vmx(vcpu); |
| 3131 | struct kvm_host_map *map; | ||
| 3132 | struct page *page; | ||
| 3133 | u64 hpa; | ||
| 3134 | 3130 | ||
| 3135 | /* | 3131 | /* |
| 3136 | * hv_evmcs may end up being not mapped after migration (when | 3132 | * hv_evmcs may end up being not mapped after migration (when |
| @@ -3153,6 +3149,17 @@ static bool nested_get_vmcs12_pages(struct kvm_vcpu *vcpu) · 16 unmodified lines | |||
| 3153 | } | 3149 | } |
| 3154 | } | 3150 | } |
| 3155 | 3151 | ||
| 3152 | return true; | ||
| 3153 | } | ||
| 3154 | |||
| 3155 | static bool nested_get_vmcs12_pages(struct kvm_vcpu *vcpu) | ||
| 3156 | { | ||
| 3157 | struct vmcs12 *vmcs12 = get_vmcs12(vcpu); | ||
| 3158 | struct vcpu_vmx *vmx = to_vmx(vcpu); | ||
| 3159 | struct kvm_host_map *map; | ||
| 3160 | struct page *page; | ||
| 3161 | u64 hpa; | ||
| 3162 | |||
| 3156 | if (nested_cpu_has2(vmcs12, SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES)) { | 3163 | if (nested_cpu_has2(vmcs12, SECONDARY_EXEC_VIRTUALIZE_APIC_ACCESSES)) { |
| 3157 | /* | 3164 | /* |
| 3158 | * Translate L1 physical address to host physical | 3165 | * Translate L1 physical address to host physical |
| @@ -3221,6 +3228,18 @@ static bool nested_get_vmcs12_pages(struct kvm_vcpu *vcpu) · 62 unmodified lines | |||
| 3221 | exec_controls_setbit(vmx, CPU_BASED_USE_MSR_BITMAPS); | 3228 | exec_controls_setbit(vmx, CPU_BASED_USE_MSR_BITMAPS); |
| 3222 | else | 3229 | else |
| 3223 | exec_controls_clearbit(vmx, CPU_BASED_USE_MSR_BITMAPS); | 3230 | exec_controls_clearbit(vmx, CPU_BASED_USE_MSR_BITMAPS); |
| 3231 | |||
| 3232 | return true; | ||
| 3233 | } | ||
| 3234 | |||
| 3235 | static bool vmx_get_nested_state_pages(struct kvm_vcpu *vcpu) | ||
| 3236 | { | ||
| 3237 | if (!nested_get_evmcs_page(vcpu)) | ||
| 3238 | return false; | ||
| 3239 | |||
| 3240 | if (is_guest_mode(vcpu) && !nested_get_vmcs12_pages(vcpu)) | ||
| 3241 | return false; | ||
| 3242 | |||
| 3224 | return true; | 3243 | return true; |
| 3225 | } | 3244 | } |
| 3226 | 3245 | ||
| @@ -4442,6 +4461,8 @@ void nested_vmx_vmexit(struct kvm_vcpu *vcpu, u32 vm_exit_reason, · 1215 unmodified lines | |||
| 4442 | /* trying to cancel vmlaunch/vmresume is a bug */ | 4461 | /* trying to cancel vmlaunch/vmresume is a bug */ |
| 4443 | WARN_ON_ONCE(vmx->nested.nested_run_pending); | 4462 | WARN_ON_ONCE(vmx->nested.nested_run_pending); |
| 4444 | 4463 | ||
| 4464 | kvm_clear_request(KVM_REQ_GET_NESTED_STATE_PAGES, vcpu); | ||
| 4465 | |||
| 4445 | /* Service the TLB flush request for L2 before switching to L1. */ | 4466 | /* Service the TLB flush request for L2 before switching to L1. */ |
| 4446 | if (kvm_check_request(KVM_REQ_TLB_FLUSH_CURRENT, vcpu)) | 4467 | if (kvm_check_request(KVM_REQ_TLB_FLUSH_CURRENT, vcpu)) |
| 4447 | kvm_vcpu_flush_tlb_current(vcpu); | 4468 | kvm_vcpu_flush_tlb_current(vcpu); |
| @@ -6075,11 +6096,14 @@ static int vmx_get_nested_state(struct kvm_vcpu *vcpu, · 1627 unmodified lines | |||
| 6075 | if (is_guest_mode(vcpu)) { | 6096 | if (is_guest_mode(vcpu)) { |
| 6076 | sync_vmcs02_to_vmcs12(vcpu, vmcs12); | 6097 | sync_vmcs02_to_vmcs12(vcpu, vmcs12); |
| 6077 | sync_vmcs02_to_vmcs12_rare(vcpu, vmcs12); | 6098 | sync_vmcs02_to_vmcs12_rare(vcpu, vmcs12); |
| 6078 | } else if (!vmx->nested.need_vmcs12_to_shadow_sync) { | 6099 | } else { |
| 6079 | if (vmx->nested.hv_evmcs) | 6100 | copy_vmcs02_to_vmcs12_rare(vcpu, get_vmcs12(vcpu)); |
| 6080 | copy_enlightened_to_vmcs12(vmx); | 6101 | if (!vmx->nested.need_vmcs12_to_shadow_sync) { |
| 6081 | else if (enable_shadow_vmcs) | 6102 | if (vmx->nested.hv_evmcs) |
| 6082 | copy_shadow_to_vmcs12(vmx); | 6103 | copy_enlightened_to_vmcs12(vmx); |
| 6104 | else if (enable_shadow_vmcs) | ||
| 6105 | copy_shadow_to_vmcs12(vmx); | ||
| 6106 | } | ||
| 6083 | } | 6107 | } |
| 6084 | 6108 | ||
| 6085 | BUILD_BUG_ON(sizeof(user_vmx_nested_state->vmcs12) < VMCS12_SIZE); | 6109 | BUILD_BUG_ON(sizeof(user_vmx_nested_state->vmcs12) < VMCS12_SIZE); |
| @@ -6600,7 +6624,7 @@ struct kvm_x86_nested_ops vmx_nested_ops = { · 514 unmodified lines | |||
| 6600 | .hv_timer_pending = nested_vmx_preemption_timer_pending, | 6624 | .hv_timer_pending = nested_vmx_preemption_timer_pending, |
| 6601 | .get_state = vmx_get_nested_state, | 6625 | .get_state = vmx_get_nested_state, |
| 6602 | .set_state = vmx_set_nested_state, | 6626 | .set_state = vmx_set_nested_state, |
| 6603 | .get_nested_state_pages = nested_get_vmcs12_pages, | 6627 | .get_nested_state_pages = vmx_get_nested_state_pages, |
| 6604 | .write_log_dirty = nested_vmx_write_pml_buffer, | 6628 | .write_log_dirty = nested_vmx_write_pml_buffer, |
| 6605 | .enable_evmcs = nested_enable_evmcs, | 6629 | .enable_evmcs = nested_enable_evmcs, |
| 6606 | .get_evmcs_version = nested_get_evmcs_version, | 6630 | .get_evmcs_version = nested_get_evmcs_version, |
| @@ -29,7 +29,7 @@ static struct kvm_event_hw_type_mapping intel_arch_events[] = { · 28 unmodified lines | |||
| 29 | [4] = { 0x2e, 0x41, PERF_COUNT_HW_CACHE_MISSES }, | 29 | [4] = { 0x2e, 0x41, PERF_COUNT_HW_CACHE_MISSES }, |
| 30 | [5] = { 0xc4, 0x00, PERF_COUNT_HW_BRANCH_INSTRUCTIONS }, | 30 | [5] = { 0xc4, 0x00, PERF_COUNT_HW_BRANCH_INSTRUCTIONS }, |
| 31 | [6] = { 0xc5, 0x00, PERF_COUNT_HW_BRANCH_MISSES }, | 31 | [6] = { 0xc5, 0x00, PERF_COUNT_HW_BRANCH_MISSES }, |
| 32 | [7] = { 0x00, 0x30, PERF_COUNT_HW_REF_CPU_CYCLES }, | 32 | [7] = { 0x00, 0x03, PERF_COUNT_HW_REF_CPU_CYCLES }, |
| 33 | }; | 33 | }; |
| 34 | 34 | ||
| 35 | /* mapping between fixed pmc index and intel_arch_events array */ | 35 | /* mapping between fixed pmc index and intel_arch_events array */ |
| @@ -345,7 +345,9 @@ static void intel_pmu_refresh(struct kvm_vcpu *vcpu) · 309 unmodified lines | |||
| 345 | 345 | ||
| 346 | pmu->nr_arch_gp_counters = min_t(int, eax.split.num_counters, | 346 | pmu->nr_arch_gp_counters = min_t(int, eax.split.num_counters, |
| 347 | x86_pmu.num_counters_gp); | 347 | x86_pmu.num_counters_gp); |
| 348 | eax.split.bit_width = min_t(int, eax.split.bit_width, x86_pmu.bit_width_gp); | ||
| 348 | pmu->counter_bitmask[KVM_PMC_GP] = ((u64)1 << eax.split.bit_width) - 1; | 349 | pmu->counter_bitmask[KVM_PMC_GP] = ((u64)1 << eax.split.bit_width) - 1; |
| 350 | eax.split.mask_length = min_t(int, eax.split.mask_length, x86_pmu.events_mask_len); | ||
| 349 | pmu->available_event_types = ~entry->ebx & | 351 | pmu->available_event_types = ~entry->ebx & |
| 350 | ((1ull << eax.split.mask_length) - 1); | 352 | ((1ull << eax.split.mask_length) - 1); |
| 351 | 353 | ||
| @@ -355,6 +357,8 @@ static void intel_pmu_refresh(struct kvm_vcpu *vcpu) · 3 unmodified lines | |||
| 355 | pmu->nr_arch_fixed_counters = | 357 | pmu->nr_arch_fixed_counters = |
| 356 | min_t(int, edx.split.num_counters_fixed, | 358 | min_t(int, edx.split.num_counters_fixed, |
| 357 | x86_pmu.num_counters_fixed); | 359 | x86_pmu.num_counters_fixed); |
| 360 | edx.split.bit_width_fixed = min_t(int, | ||
| 361 | edx.split.bit_width_fixed, x86_pmu.bit_width_fixed); | ||
| 358 | pmu->counter_bitmask[KVM_PMC_FIXED] = | 362 | pmu->counter_bitmask[KVM_PMC_FIXED] = |
| 359 | ((u64)1 << edx.split.bit_width_fixed) - 1; | 363 | ((u64)1 << edx.split.bit_width_fixed) - 1; |
| 360 | } | 364 | } |
| @@ -6653,6 +6653,8 @@ reenter_guest: · 6652 unmodified lines | |||
| 6653 | if (vmx->emulation_required) | 6653 | if (vmx->emulation_required) |
| 6654 | return EXIT_FASTPATH_NONE; | 6654 | return EXIT_FASTPATH_NONE; |
| 6655 | 6655 | ||
| 6656 | trace_kvm_entry(vcpu); | ||
| 6657 | |||
| 6656 | if (vmx->ple_window_dirty) { | 6658 | if (vmx->ple_window_dirty) { |
| 6657 | vmx->ple_window_dirty = false; | 6659 | vmx->ple_window_dirty = false; |
| 6658 | vmcs_write32(PLE_WINDOW, vmx->ple_window); | 6660 | vmcs_write32(PLE_WINDOW, vmx->ple_window); |
| @@ -6858,11 +6860,20 @@ static int vmx_create_vcpu(struct kvm_vcpu *vcpu) · 199 unmodified lines | |||
| 6858 | switch (index) { | 6860 | switch (index) { |
| 6859 | case MSR_IA32_TSX_CTRL: | 6861 | case MSR_IA32_TSX_CTRL: |
| 6860 | /* | 6862 | /* |
| 6861 | * No need to pass TSX_CTRL_CPUID_CLEAR through, so | 6863 | * TSX_CTRL_CPUID_CLEAR is handled in the CPUID |
| 6862 | * let's avoid changing CPUID bits under the host | 6864 | * interception. Keep the host value unchanged to avoid |
| 6863 | * kernel's feet. | 6865 | * changing CPUID bits under the host kernel's feet. |
| 6866 | * | ||
| 6867 | * hle=0, rtm=0, tsx_ctrl=1 can be found with some | ||
| 6868 | * combinations of new kernel and old userspace. If | ||
| 6869 | * those guests run on a tsx=off host, do allow guests | ||
| 6870 | * to use TSX_CTRL, but do not change the value on the | ||
| 6871 | * host so that TSX remains always disabled. | ||
| 6864 | */ | 6872 | */ |
| 6865 | vmx->guest_uret_msrs[j].mask = ~(u64)TSX_CTRL_CPUID_CLEAR; | 6873 | if (boot_cpu_has(X86_FEATURE_RTM)) |
| 6874 | vmx->guest_uret_msrs[j].mask = ~(u64)TSX_CTRL_CPUID_CLEAR; | ||
| 6875 | else | ||
| 6876 | vmx->guest_uret_msrs[j].mask = 0; | ||
| 6866 | break; | 6877 | break; |
| 6867 | default: | 6878 | default: |
| 6868 | vmx->guest_uret_msrs[j].mask = -1ull; | 6879 | vmx->guest_uret_msrs[j].mask = -1ull; |
| @@ -7707,6 +7718,8 @@ static struct kvm_x86_ops vmx_x86_ops __initdata = { · 838 unmodified lines | |||
| 7707 | .msr_filter_changed = vmx_msr_filter_changed, | 7718 | .msr_filter_changed = vmx_msr_filter_changed, |
| 7708 | .complete_emulated_msr = kvm_complete_insn_gp, | 7719 | .complete_emulated_msr = kvm_complete_insn_gp, |
| 7709 | .cpu_dirty_log_size = vmx_cpu_dirty_log_size, | 7720 | .cpu_dirty_log_size = vmx_cpu_dirty_log_size, |
| 7721 | |||
| 7722 | .vcpu_deliver_sipi_vector = kvm_vcpu_deliver_sipi_vector, | ||
| 7710 | }; | 7723 | }; |
| 7711 | 7724 | ||
| 7712 | static __init int hardware_setup(void) | 7725 | static __init int hardware_setup(void) |
| @@ -105,6 +105,7 @@ static u64 __read_mostly cr4_reserved_bits = CR4_RESERVED_BITS; · 104 unmodified lines | |||
| 105 | 105 | ||
| 106 | static void update_cr8_intercept(struct kvm_vcpu *vcpu); | 106 | static void update_cr8_intercept(struct kvm_vcpu *vcpu); |
| 107 | static void process_nmi(struct kvm_vcpu *vcpu); | 107 | static void process_nmi(struct kvm_vcpu *vcpu); |
| 108 | static void process_smi(struct kvm_vcpu *vcpu); | ||
| 108 | static void enter_smm(struct kvm_vcpu *vcpu); | 109 | static void enter_smm(struct kvm_vcpu *vcpu); |
| 109 | static void __kvm_set_rflags(struct kvm_vcpu *vcpu, unsigned long rflags); | 110 | static void __kvm_set_rflags(struct kvm_vcpu *vcpu, unsigned long rflags); |
| 110 | static void store_regs(struct kvm_vcpu *vcpu); | 111 | static void store_regs(struct kvm_vcpu *vcpu); |
| @@ -1393,16 +1394,24 @@ static u64 kvm_get_arch_capabilities(void) · 1282 unmodified lines | |||
| 1393 | if (!boot_cpu_has_bug(X86_BUG_MDS)) | 1394 | if (!boot_cpu_has_bug(X86_BUG_MDS)) |
| 1394 | data |= ARCH_CAP_MDS_NO; | 1395 | data |= ARCH_CAP_MDS_NO; |
| 1395 | 1396 | ||
| 1396 | /* | 1397 | if (!boot_cpu_has(X86_FEATURE_RTM)) { |
| 1397 | * On TAA affected systems: | 1398 | /* |
| 1398 | * - nothing to do if TSX is disabled on the host. | 1399 | * If RTM=0 because the kernel has disabled TSX, the host might |
| 1399 | * - we emulate TSX_CTRL if present on the host. | 1400 | * have TAA_NO or TSX_CTRL. Clear TAA_NO (the guest sees RTM=0 |
| 1400 | * This lets the guest use VERW to clear CPU buffers. | 1401 | * and therefore knows that there cannot be TAA) but keep |
| 1401 | */ | 1402 | * TSX_CTRL: some buggy userspaces leave it set on tsx=on hosts, |
| 1402 | if (!boot_cpu_has(X86_FEATURE_RTM)) | 1403 | * and we want to allow migrating those guests to tsx=off hosts. |
| 1403 | data &= ~(ARCH_CAP_TAA_NO | ARCH_CAP_TSX_CTRL_MSR); | 1404 | */ |
| 1404 | else if (!boot_cpu_has_bug(X86_BUG_TAA)) | 1405 | data &= ~ARCH_CAP_TAA_NO; |
| 1406 | } else if (!boot_cpu_has_bug(X86_BUG_TAA)) { | ||
| 1405 | data |= ARCH_CAP_TAA_NO; | 1407 | data |= ARCH_CAP_TAA_NO; |
| 1408 | } else { | ||
| 1409 | /* | ||
| 1410 | * Nothing to do here; we emulate TSX_CTRL if present on the | ||
| 1411 | * host so the guest can choose between disabling TSX or | ||
| 1412 | * using VERW to clear CPU buffers. | ||
| 1413 | */ | ||
| 1414 | } | ||
| 1406 | 1415 | ||
| 1407 | return data; | 1416 | return data; |
| 1408 | } | 1417 | } |
| @@ -4230,6 +4239,9 @@ static void kvm_vcpu_ioctl_x86_get_vcpu_events(struct kvm_vcpu *vcpu, · 2821 unmodified lines | |||
| 4230 | { | 4239 | { |
| 4231 | process_nmi(vcpu); | 4240 | process_nmi(vcpu); |
| 4232 | 4241 | ||
| 4242 | if (kvm_check_request(KVM_REQ_SMI, vcpu)) | ||
| 4243 | process_smi(vcpu); | ||
| 4244 | |||
| 4233 | /* | 4245 | /* |
| 4234 | * In guest mode, payload delivery should be deferred, | 4246 | * In guest mode, payload delivery should be deferred, |
| 4235 | * so that the L1 hypervisor can intercept #PF before | 4247 | * so that the L1 hypervisor can intercept #PF before |
| @@ -7976,17 +7988,22 @@ void kvm_arch_exit(void) · 3740 unmodified lines | |||
| 7976 | kmem_cache_destroy(x86_fpu_cache); | 7988 | kmem_cache_destroy(x86_fpu_cache); |
| 7977 | } | 7989 | } |
| 7978 | 7990 | ||
| 7979 | int kvm_vcpu_halt(struct kvm_vcpu *vcpu) | 7991 | static int __kvm_vcpu_halt(struct kvm_vcpu *vcpu, int state, int reason) |
| 7980 | { | 7992 | { |
| 7981 | ++vcpu->stat.halt_exits; | 7993 | ++vcpu->stat.halt_exits; |
| 7982 | if (lapic_in_kernel(vcpu)) { | 7994 | if (lapic_in_kernel(vcpu)) { |
| 7983 | vcpu->arch.mp_state = KVM_MP_STATE_HALTED; | 7995 | vcpu->arch.mp_state = state; |
| 7984 | return 1; | 7996 | return 1; |
| 7985 | } else { | 7997 | } else { |
| 7986 | vcpu->run->exit_reason = KVM_EXIT_HLT; | 7998 | vcpu->run->exit_reason = reason; |
| 7987 | return 0; | 7999 | return 0; |
| 7988 | } | 8000 | } |
| 7989 | } | 8001 | } |
| 8002 | |||
| 8003 | int kvm_vcpu_halt(struct kvm_vcpu *vcpu) | ||
| 8004 | { | ||
| 8005 | return __kvm_vcpu_halt(vcpu, KVM_MP_STATE_HALTED, KVM_EXIT_HLT); | ||
| 8006 | } | ||
| 7990 | EXPORT_SYMBOL_GPL(kvm_vcpu_halt); | 8007 | EXPORT_SYMBOL_GPL(kvm_vcpu_halt); |
| 7991 | 8008 | ||
| 7992 | int kvm_emulate_halt(struct kvm_vcpu *vcpu) | 8009 | int kvm_emulate_halt(struct kvm_vcpu *vcpu) |
| @@ -8000,6 +8017,14 @@ int kvm_emulate_halt(struct kvm_vcpu *vcpu) · 7 unmodified lines | |||
| 8000 | } | 8017 | } |
| 8001 | EXPORT_SYMBOL_GPL(kvm_emulate_halt); | 8018 | EXPORT_SYMBOL_GPL(kvm_emulate_halt); |
| 8002 | 8019 | ||
| 8020 | int kvm_emulate_ap_reset_hold(struct kvm_vcpu *vcpu) | ||
| 8021 | { | ||
| 8022 | int ret = kvm_skip_emulated_instruction(vcpu); | ||
| 8023 | |||
| 8024 | return __kvm_vcpu_halt(vcpu, KVM_MP_STATE_AP_RESET_HOLD, KVM_EXIT_AP_RESET_HOLD) && ret; | ||
| 8025 | } | ||
| 8026 | EXPORT_SYMBOL_GPL(kvm_emulate_ap_reset_hold); | ||
| 8027 | |||
| 8003 | #ifdef CONFIG_X86_64 | 8028 | #ifdef CONFIG_X86_64 |
| 8004 | static int kvm_pv_clock_pairing(struct kvm_vcpu *vcpu, gpa_t paddr, | 8029 | static int kvm_pv_clock_pairing(struct kvm_vcpu *vcpu, gpa_t paddr, |
| 8005 | unsigned long clock_type) | 8030 | unsigned long clock_type) |
| @@ -8973,8 +8998,6 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu) · 967 unmodified lines | |||
| 8973 | kvm_x86_ops.request_immediate_exit(vcpu); | 8998 | kvm_x86_ops.request_immediate_exit(vcpu); |
| 8974 | } | 8999 | } |
| 8975 | 9000 | ||
| 8976 | trace_kvm_entry(vcpu); | ||
| 8977 | |||
| 8978 | fpregs_assert_state_consistent(); | 9001 | fpregs_assert_state_consistent(); |
| 8979 | if (test_thread_flag(TIF_NEED_FPU_LOAD)) | 9002 | if (test_thread_flag(TIF_NEED_FPU_LOAD)) |
| 8980 | switch_fpu_return(); | 9003 | switch_fpu_return(); |
| @@ -9094,6 +9117,7 @@ static inline int vcpu_block(struct kvm *kvm, struct kvm_vcpu *vcpu) · 113 unmodified lines | |||
| 9094 | kvm_apic_accept_events(vcpu); | 9117 | kvm_apic_accept_events(vcpu); |
| 9095 | switch(vcpu->arch.mp_state) { | 9118 | switch(vcpu->arch.mp_state) { |
| 9096 | case KVM_MP_STATE_HALTED: | 9119 | case KVM_MP_STATE_HALTED: |
| 9120 | case KVM_MP_STATE_AP_RESET_HOLD: | ||
| 9097 | vcpu->arch.pv.pv_unhalted = false; | 9121 | vcpu->arch.pv.pv_unhalted = false; |
| 9098 | vcpu->arch.mp_state = | 9122 | vcpu->arch.mp_state = |
| 9099 | KVM_MP_STATE_RUNNABLE; | 9123 | KVM_MP_STATE_RUNNABLE; |
| @@ -9520,8 +9544,9 @@ int kvm_arch_vcpu_ioctl_get_mpstate(struct kvm_vcpu *vcpu, · 420 unmodified lines | |||
| 9520 | kvm_load_guest_fpu(vcpu); | 9544 | kvm_load_guest_fpu(vcpu); |
| 9521 | 9545 | ||
| 9522 | kvm_apic_accept_events(vcpu); | 9546 | kvm_apic_accept_events(vcpu); |
| 9523 | if (vcpu->arch.mp_state == KVM_MP_STATE_HALTED && | 9547 | if ((vcpu->arch.mp_state == KVM_MP_STATE_HALTED || |
| 9524 | vcpu->arch.pv.pv_unhalted) | 9548 | vcpu->arch.mp_state == KVM_MP_STATE_AP_RESET_HOLD) && |
| 9549 | vcpu->arch.pv.pv_unhalted) | ||
| 9525 | mp_state->mp_state = KVM_MP_STATE_RUNNABLE; | 9550 | mp_state->mp_state = KVM_MP_STATE_RUNNABLE; |
| 9526 | else | 9551 | else |
| 9527 | mp_state->mp_state = vcpu->arch.mp_state; | 9552 | mp_state->mp_state = vcpu->arch.mp_state; |
| @@ -9599,6 +9624,8 @@ static bool kvm_is_valid_sregs(struct kvm_vcpu *vcpu, struct kvm_sregs *sregs) · 71 unmodified lines | |||
| 9599 | */ | 9624 | */ |
| 9600 | if (!(sregs->cr4 & X86_CR4_PAE) || !(sregs->efer & EFER_LMA)) | 9625 | if (!(sregs->cr4 & X86_CR4_PAE) || !(sregs->efer & EFER_LMA)) |
| 9601 | return false; | 9626 | return false; |
| 9627 | if (sregs->cr3 & vcpu->arch.cr3_lm_rsvd_bits) | ||
| 9628 | return false; | ||
| 9602 | } else { | 9629 | } else { |
| 9603 | /* | 9630 | /* |
| 9604 | * Not in 64-bit mode: EFER.LMA is clear and the code | 9631 | * Not in 64-bit mode: EFER.LMA is clear and the code |
| @@ -9976,6 +10003,7 @@ int kvm_arch_vcpu_create(struct kvm_vcpu *vcpu) · 371 unmodified lines | |||
| 9976 | fx_init(vcpu); | 10003 | fx_init(vcpu); |
| 9977 | 10004 | ||
| 9978 | vcpu->arch.maxphyaddr = cpuid_query_maxphyaddr(vcpu); | 10005 | vcpu->arch.maxphyaddr = cpuid_query_maxphyaddr(vcpu); |
| 10006 | vcpu->arch.cr3_lm_rsvd_bits = rsvd_bits(cpuid_maxphyaddr(vcpu), 63); | ||
| 9979 | 10007 | ||
| 9980 | vcpu->arch.pat = MSR_IA32_CR_PAT_DEFAULT; | 10008 | vcpu->arch.pat = MSR_IA32_CR_PAT_DEFAULT; |
| 9981 | 10009 | ||
| @@ -10152,6 +10180,7 @@ void kvm_vcpu_deliver_sipi_vector(struct kvm_vcpu *vcpu, u8 vector) · 170 unmodified lines | |||
| 10152 | kvm_set_segment(vcpu, &cs, VCPU_SREG_CS); | 10180 | kvm_set_segment(vcpu, &cs, VCPU_SREG_CS); |
| 10153 | kvm_rip_write(vcpu, 0); | 10181 | kvm_rip_write(vcpu, 0); |
| 10154 | } | 10182 | } |
| 10183 | EXPORT_SYMBOL_GPL(kvm_vcpu_deliver_sipi_vector); | ||
| 10155 | 10184 | ||
| 10156 | int kvm_arch_hardware_enable(void) | 10185 | int kvm_arch_hardware_enable(void) |
| 10157 | { | 10186 | { |
| @@ -10476,7 +10505,7 @@ void __user * __x86_set_memory_region(struct kvm *kvm, int id, gpa_t gpa, · 318 unmodified lines | |||
| 10476 | return 0; | 10505 | return 0; |
| 10477 | 10506 | ||
| 10478 | old_npages = slot->npages; | 10507 | old_npages = slot->npages; |
| 10479 | hva = 0; | 10508 | hva = slot->userspace_addr; |
| 10480 | } | 10509 | } |
| 10481 | 10510 | ||
| 10482 | for (i = 0; i < KVM_ADDRESS_SPACE_NUM; i++) { | 10511 | for (i = 0; i < KVM_ADDRESS_SPACE_NUM; i++) { |
| @@ -11538,6 +11567,7 @@ int kvm_sev_es_string_io(struct kvm_vcpu *vcpu, unsigned int size, · 1055 unmodified lines | |||
| 11538 | } | 11567 | } |
| 11539 | EXPORT_SYMBOL_GPL(kvm_sev_es_string_io); | 11568 | EXPORT_SYMBOL_GPL(kvm_sev_es_string_io); |
| 11540 | 11569 | ||
| 11570 | EXPORT_TRACEPOINT_SYMBOL_GPL(kvm_entry); | ||
| 11541 | EXPORT_TRACEPOINT_SYMBOL_GPL(kvm_exit); | 11571 | EXPORT_TRACEPOINT_SYMBOL_GPL(kvm_exit); |
| 11542 | EXPORT_TRACEPOINT_SYMBOL_GPL(kvm_fast_mmio); | 11572 | EXPORT_TRACEPOINT_SYMBOL_GPL(kvm_fast_mmio); |
| 11543 | EXPORT_TRACEPOINT_SYMBOL_GPL(kvm_inj_virq); | 11573 | EXPORT_TRACEPOINT_SYMBOL_GPL(kvm_inj_virq); |
| @@ -425,6 +425,8 @@ bool kvm_msr_allowed(struct kvm_vcpu *vcpu, u32 index, u32 type); · 424 unmodified lines | |||
| 425 | __reserved_bits |= X86_CR4_UMIP; \ | 425 | __reserved_bits |= X86_CR4_UMIP; \ |
| 426 | if (!__cpu_has(__c, X86_FEATURE_VMX)) \ | 426 | if (!__cpu_has(__c, X86_FEATURE_VMX)) \ |
| 427 | __reserved_bits |= X86_CR4_VMXE; \ | 427 | __reserved_bits |= X86_CR4_VMXE; \ |
| 428 | if (!__cpu_has(__c, X86_FEATURE_PCID)) \ | ||
| 429 | __reserved_bits |= X86_CR4_PCIDE; \ | ||
| 428 | __reserved_bits; \ | 430 | __reserved_bits; \ |
| 429 | }) | 431 | }) |
| 430 | 432 | ||
| @@ -26,6 +26,16 @@ · 25 unmodified lines | |||
| 26 | #include <asm/fpu/api.h> | 26 | #include <asm/fpu/api.h> |
| 27 | #include <asm/asm.h> | 27 | #include <asm/asm.h> |
| 28 | 28 | ||
| 29 | /* | ||
| 30 | * Use KFPU_387. MMX instructions are not affected by MXCSR, | ||
| 31 | * but both AMD and Intel documentation states that even integer MMX | ||
| 32 | * operations will result in #MF if an exception is pending in FCW. | ||
| 33 | * | ||
| 34 | * EMMS is not needed afterwards because, after calling kernel_fpu_end(), | ||
| 35 | * any subsequent user of the 387 stack will reinitialize it using | ||
| 36 | * KFPU_387. | ||
| 37 | */ | ||
| 38 | |||
| 29 | void *_mmx_memcpy(void *to, const void *from, size_t len) | 39 | void *_mmx_memcpy(void *to, const void *from, size_t len) |
| 30 | { | 40 | { |
| 31 | void *p; | 41 | void *p; |
| @@ -37,7 +47,7 @@ void *_mmx_memcpy(void *to, const void *from, size_t len) · 5 unmodified lines | |||
| 37 | p = to; | 47 | p = to; |
| 38 | i = len >> 6; /* len/64 */ | 48 | i = len >> 6; /* len/64 */ |
| 39 | 49 | ||
| 40 | kernel_fpu_begin(); | 50 | kernel_fpu_begin_mask(KFPU_387); |
| 41 | 51 | ||
| 42 | __asm__ __volatile__ ( | 52 | __asm__ __volatile__ ( |
| 43 | "1: prefetch (%0)\n" /* This set is 28 bytes */ | 53 | "1: prefetch (%0)\n" /* This set is 28 bytes */ |
| @@ -127,7 +137,7 @@ static void fast_clear_page(void *page) · 83 unmodified lines | |||
| 127 | { | 137 | { |
| 128 | int i; | 138 | int i; |
| 129 | 139 | ||
| 130 | kernel_fpu_begin(); | 140 | kernel_fpu_begin_mask(KFPU_387); |
| 131 | 141 | ||
| 132 | __asm__ __volatile__ ( | 142 | __asm__ __volatile__ ( |
| 133 | " pxor %%mm0, %%mm0\n" : : | 143 | " pxor %%mm0, %%mm0\n" : : |
| @@ -160,7 +170,7 @@ static void fast_copy_page(void *to, void *from) · 26 unmodified lines | |||
| 160 | { | 170 | { |
| 161 | int i; | 171 | int i; |
| 162 | 172 | ||
| 163 | kernel_fpu_begin(); | 173 | kernel_fpu_begin_mask(KFPU_387); |
| 164 | 174 | ||
| 165 | /* | 175 | /* |
| 166 | * maybe the prefetch stuff can go before the expensive fnsave... | 176 | * maybe the prefetch stuff can go before the expensive fnsave... |
| @@ -247,7 +257,7 @@ static void fast_clear_page(void *page) · 80 unmodified lines | |||
| 247 | { | 257 | { |
| 248 | int i; | 258 | int i; |
| 249 | 259 | ||
| 250 | kernel_fpu_begin(); | 260 | kernel_fpu_begin_mask(KFPU_387); |
| 251 | 261 | ||
| 252 | __asm__ __volatile__ ( | 262 | __asm__ __volatile__ ( |
| 253 | " pxor %%mm0, %%mm0\n" : : | 263 | " pxor %%mm0, %%mm0\n" : : |
| @@ -282,7 +292,7 @@ static void fast_copy_page(void *to, void *from) · 28 unmodified lines | |||
| 282 | { | 292 | { |
| 283 | int i; | 293 | int i; |
| 284 | 294 | ||
| 285 | kernel_fpu_begin(); | 295 | kernel_fpu_begin_mask(KFPU_387); |
| 286 | 296 | ||
| 287 | __asm__ __volatile__ ( | 297 | __asm__ __volatile__ ( |
| 288 | "1: prefetch (%0)\n" | 298 | "1: prefetch (%0)\n" |
| @@ -382,6 +382,7 @@ bool sev_active(void) · 381 unmodified lines | |||
| 382 | { | 382 | { |
| 383 | return sev_status & MSR_AMD64_SEV_ENABLED; | 383 | return sev_status & MSR_AMD64_SEV_ENABLED; |
| 384 | } | 384 | } |
| 385 | EXPORT_SYMBOL_GPL(sev_active); | ||
| 385 | 386 | ||
| 386 | /* Needs to be called from non-instrumentable code */ | 387 | /* Needs to be called from non-instrumentable code */ |
| 387 | bool noinstr sev_es_active(void) | 388 | bool noinstr sev_es_active(void) |
| @@ -829,6 +829,8 @@ int pud_free_pmd_page(pud_t *pud, unsigned long addr) · 828 unmodified lines | |||
| 829 | } | 829 | } |
| 830 | 830 | ||
| 831 | free_page((unsigned long)pmd_sv); | 831 | free_page((unsigned long)pmd_sv); |
| 832 | |||
| 833 | pgtable_pmd_page_dtor(virt_to_page(pmd)); | ||
| 832 | free_page((unsigned long)pmd); | 834 | free_page((unsigned long)pmd); |
| 833 | 835 | ||
| 834 | return 1; | 836 | return 1; |
| @@ -9,16 +9,23 @@ · 8 unmodified lines | |||
| 9 | in the right sequence from here. */ | 9 | in the right sequence from here. */ |
| 10 | static __init int pci_arch_init(void) | 10 | static __init int pci_arch_init(void) |
| 11 | { | 11 | { |
| 12 | int type; | 12 | int type, pcbios = 1; |
| 13 | |||
| 14 | x86_create_pci_msi_domain(); | ||
| 15 | 13 | ||
| 16 | type = pci_direct_probe(); | 14 | type = pci_direct_probe(); |
| 17 | 15 | ||
| 18 | if (!(pci_probe & PCI_PROBE_NOEARLY)) | 16 | if (!(pci_probe & PCI_PROBE_NOEARLY)) |
| 19 | pci_mmcfg_early_init(); | 17 | pci_mmcfg_early_init(); |
| 20 | 18 | ||
| 21 | if (x86_init.pci.arch_init && !x86_init.pci.arch_init()) | 19 | if (x86_init.pci.arch_init) |
| 20 | pcbios = x86_init.pci.arch_init(); | ||
| 21 | |||
| 22 | /* | ||
| 23 | * Must happen after x86_init.pci.arch_init(). Xen sets up the | ||
| 24 | * x86_init.irqs.create_pci_msi_domain there. | ||
| 25 | */ | ||
| 26 | x86_create_pci_msi_domain(); | ||
| 27 | |||
| 28 | if (!pcbios) | ||
| 22 | return 0; | 29 | return 0; |
| 23 | 30 | ||
| 24 | pci_pcbios_init(); | 31 | pci_pcbios_init(); |
| @@ -115,31 +115,12 @@ void efi_sync_low_kernel_mappings(void) · 114 unmodified lines | |||
| 115 | pud_t *pud_k, *pud_efi; | 115 | pud_t *pud_k, *pud_efi; |
| 116 | pgd_t *efi_pgd = efi_mm.pgd; | 116 | pgd_t *efi_pgd = efi_mm.pgd; |
| 117 | 117 | ||
| 118 | /* | ||
| 119 | * We can share all PGD entries apart from the one entry that | ||
| 120 | * covers the EFI runtime mapping space. | ||
| 121 | * | ||
| 122 | * Make sure the EFI runtime region mappings are guaranteed to | ||
| 123 | * only span a single PGD entry and that the entry also maps | ||
| 124 | * other important kernel regions. | ||
| 125 | */ | ||
| 126 | MAYBE_BUILD_BUG_ON(pgd_index(EFI_VA_END) != pgd_index(MODULES_END)); | ||
| 127 | MAYBE_BUILD_BUG_ON((EFI_VA_START & PGDIR_MASK) != | ||
| 128 | (EFI_VA_END & PGDIR_MASK)); | ||
| 129 | |||
| 130 | pgd_efi = efi_pgd + pgd_index(PAGE_OFFSET); | 118 | pgd_efi = efi_pgd + pgd_index(PAGE_OFFSET); |
| 131 | pgd_k = pgd_offset_k(PAGE_OFFSET); | 119 | pgd_k = pgd_offset_k(PAGE_OFFSET); |
| 132 | 120 | ||
| 133 | num_entries = pgd_index(EFI_VA_END) - pgd_index(PAGE_OFFSET); | 121 | num_entries = pgd_index(EFI_VA_END) - pgd_index(PAGE_OFFSET); |
| 134 | memcpy(pgd_efi, pgd_k, sizeof(pgd_t) * num_entries); | 122 | memcpy(pgd_efi, pgd_k, sizeof(pgd_t) * num_entries); |
| 135 | 123 | ||
| 136 | /* | ||
| 137 | * As with PGDs, we share all P4D entries apart from the one entry | ||
| 138 | * that covers the EFI runtime mapping space. | ||
| 139 | */ | ||
| 140 | BUILD_BUG_ON(p4d_index(EFI_VA_END) != p4d_index(MODULES_END)); | ||
| 141 | BUILD_BUG_ON((EFI_VA_START & P4D_MASK) != (EFI_VA_END & P4D_MASK)); | ||
| 142 | |||
| 143 | pgd_efi = efi_pgd + pgd_index(EFI_VA_END); | 124 | pgd_efi = efi_pgd + pgd_index(EFI_VA_END); |
| 144 | pgd_k = pgd_offset_k(EFI_VA_END); | 125 | pgd_k = pgd_offset_k(EFI_VA_END); |
| 145 | p4d_efi = p4d_offset(pgd_efi, 0); | 126 | p4d_efi = p4d_offset(pgd_efi, 0); |
| @@ -164,10 +164,10 @@ static int xen_cpu_up_prepare_hvm(unsigned int cpu) · 163 unmodified lines | |||
| 164 | else | 164 | else |
| 165 | per_cpu(xen_vcpu_id, cpu) = cpu; | 165 | per_cpu(xen_vcpu_id, cpu) = cpu; |
| 166 | rc = xen_vcpu_setup(cpu); | 166 | rc = xen_vcpu_setup(cpu); |
| 167 | if (rc) | 167 | if (rc || !xen_have_vector_callback) |
| 168 | return rc; | 168 | return rc; |
| 169 | 169 | ||
| 170 | if (xen_have_vector_callback && xen_feature(XENFEAT_hvm_safe_pvclock)) | 170 | if (xen_feature(XENFEAT_hvm_safe_pvclock)) |
| 171 | xen_setup_timer(cpu); | 171 | xen_setup_timer(cpu); |
| 172 | 172 | ||
| 173 | rc = xen_smp_intr_init(cpu); | 173 | rc = xen_smp_intr_init(cpu); |
| @@ -188,6 +188,8 @@ static int xen_cpu_dead_hvm(unsigned int cpu) · 14 unmodified lines | |||
| 188 | return 0; | 188 | return 0; |
| 189 | } | 189 | } |
| 190 | 190 | ||
| 191 | static bool no_vector_callback __initdata; | ||
| 192 | |||
| 191 | static void __init xen_hvm_guest_init(void) | 193 | static void __init xen_hvm_guest_init(void) |
| 192 | { | 194 | { |
| 193 | if (xen_pv_domain()) | 195 | if (xen_pv_domain()) |
| @@ -207,7 +209,7 @@ static void __init xen_hvm_guest_init(void) · 13 unmodified lines | |||
| 207 | 209 | ||
| 208 | xen_panic_handler_init(); | 210 | xen_panic_handler_init(); |
| 209 | 211 | ||
| 210 | if (xen_feature(XENFEAT_hvm_callback_vector)) | 212 | if (!no_vector_callback && xen_feature(XENFEAT_hvm_callback_vector)) |
| 211 | xen_have_vector_callback = 1; | 213 | xen_have_vector_callback = 1; |
| 212 | 214 | ||
| 213 | xen_hvm_smp_init(); | 215 | xen_hvm_smp_init(); |
| @@ -233,6 +235,13 @@ static __init int xen_parse_nopv(char *arg) · 19 unmodified lines | |||
| 233 | } | 235 | } |
| 234 | early_param("xen_nopv", xen_parse_nopv); | 236 | early_param("xen_nopv", xen_parse_nopv); |
| 235 | 237 | ||
| 238 | static __init int xen_parse_no_vector_callback(char *arg) | ||
| 239 | { | ||
| 240 | no_vector_callback = true; | ||
| 241 | return 0; | ||
| 242 | } | ||
| 243 | early_param("xen_no_vector_callback", xen_parse_no_vector_callback); | ||
| 244 | |||
| 236 | bool __init xen_hvm_need_lapic(void) | 245 | bool __init xen_hvm_need_lapic(void) |
| 237 | { | 246 | { |
| 238 | if (xen_pv_domain()) | 247 | if (xen_pv_domain()) |
| @@ -583,6 +583,13 @@ DEFINE_IDTENTRY_RAW(xenpv_exc_debug) · 582 unmodified lines | |||
| 583 | exc_debug(regs); | 583 | exc_debug(regs); |
| 584 | } | 584 | } |
| 585 | 585 | ||
| 586 | DEFINE_IDTENTRY_RAW(exc_xen_unknown_trap) | ||
| 587 | { | ||
| 588 | /* This should never happen and there is no way to handle it. */ | ||
| 589 | pr_err("Unknown trap in Xen PV mode."); | ||
| 590 | BUG(); | ||
| 591 | } | ||
| 592 | |||
| 586 | struct trap_array_entry { | 593 | struct trap_array_entry { |
| 587 | void (*orig)(void); | 594 | void (*orig)(void); |
| 588 | void (*xen)(void); | 595 | void (*xen)(void); |
| @@ -631,6 +638,7 @@ static bool __ref get_trap_addr(void **addr, unsigned int ist) · 42 unmodified lines | |||
| 631 | { | 638 | { |
| 632 | unsigned int nr; | 639 | unsigned int nr; |
| 633 | bool ist_okay = false; | 640 | bool ist_okay = false; |
| 641 | bool found = false; | ||
| 634 | 642 | ||
| 635 | /* | 643 | /* |
| 636 | * Replace trap handler addresses by Xen specific ones. | 644 | * Replace trap handler addresses by Xen specific ones. |
| @@ -645,6 +653,7 @@ static bool __ref get_trap_addr(void **addr, unsigned int ist) · 8 unmodified lines | |||
| 645 | if (*addr == entry->orig) { | 653 | if (*addr == entry->orig) { |
| 646 | *addr = entry->xen; | 654 | *addr = entry->xen; |
| 647 | ist_okay = entry->ist_okay; | 655 | ist_okay = entry->ist_okay; |
| 656 | found = true; | ||
| 648 | break; | 657 | break; |
| 649 | } | 658 | } |
| 650 | } | 659 | } |
| @@ -655,9 +664,13 @@ static bool __ref get_trap_addr(void **addr, unsigned int ist) · 4 unmodified lines | |||
| 655 | nr = (*addr - (void *)early_idt_handler_array[0]) / | 664 | nr = (*addr - (void *)early_idt_handler_array[0]) / |
| 656 | EARLY_IDT_HANDLER_SIZE; | 665 | EARLY_IDT_HANDLER_SIZE; |
| 657 | *addr = (void *)xen_early_idt_handler_array[nr]; | 666 | *addr = (void *)xen_early_idt_handler_array[nr]; |
| 667 | found = true; | ||
| 658 | } | 668 | } |
| 659 | 669 | ||
| 660 | if (WARN_ON(ist != 0 && !ist_okay)) | 670 | if (!found) |
| 671 | *addr = (void *)xen_asm_exc_xen_unknown_trap; | ||
| 672 | |||
| 673 | if (WARN_ON(found && ist != 0 && !ist_okay)) | ||
| 661 | return false; | 674 | return false; |
| 662 | 675 | ||
| 663 | return true; | 676 | return true; |
| @@ -33,9 +33,11 @@ static void __init xen_hvm_smp_prepare_cpus(unsigned int max_cpus) · 32 unmodified lines | |||
| 33 | int cpu; | 33 | int cpu; |
| 34 | 34 | ||
| 35 | native_smp_prepare_cpus(max_cpus); | 35 | native_smp_prepare_cpus(max_cpus); |
| 36 | WARN_ON(xen_smp_intr_init(0)); | ||
| 37 | 36 | ||
| 38 | xen_init_lock_cpu(0); | 37 | if (xen_have_vector_callback) { |
| 38 | WARN_ON(xen_smp_intr_init(0)); | ||
| 39 | xen_init_lock_cpu(0); | ||
| 40 | } | ||
| 39 | 41 | ||
| 40 | for_each_possible_cpu(cpu) { | 42 | for_each_possible_cpu(cpu) { |
| 41 | if (cpu == 0) | 43 | if (cpu == 0) |
| @@ -50,9 +52,11 @@ static void __init xen_hvm_smp_prepare_cpus(unsigned int max_cpus) · 8 unmodified lines | |||
| 50 | static void xen_hvm_cpu_die(unsigned int cpu) | 52 | static void xen_hvm_cpu_die(unsigned int cpu) |
| 51 | { | 53 | { |
| 52 | if (common_cpu_die(cpu) == 0) { | 54 | if (common_cpu_die(cpu) == 0) { |
| 53 | xen_smp_intr_free(cpu); | 55 | if (xen_have_vector_callback) { |
| 54 | xen_uninit_lock_cpu(cpu); | 56 | xen_smp_intr_free(cpu); |
| 55 | xen_teardown_timer(cpu); | 57 | xen_uninit_lock_cpu(cpu); |
| 58 | xen_teardown_timer(cpu); | ||
| 59 | } | ||
| 56 | } | 60 | } |
| 57 | } | 61 | } |
| 58 | #else | 62 | #else |
| @@ -64,14 +68,19 @@ static void xen_hvm_cpu_die(unsigned int cpu) · 5 unmodified lines | |||
| 64 | 68 | ||
| 65 | void __init xen_hvm_smp_init(void) | 69 | void __init xen_hvm_smp_init(void) |
| 66 | { | 70 | { |
| 67 | if (!xen_have_vector_callback) | 71 | smp_ops.smp_prepare_boot_cpu = xen_hvm_smp_prepare_boot_cpu; |
| 72 | smp_ops.smp_prepare_cpus = xen_hvm_smp_prepare_cpus; | ||
| 73 | smp_ops.smp_cpus_done = xen_smp_cpus_done; | ||
| 74 | smp_ops.cpu_die = xen_hvm_cpu_die; | ||
| 75 | |||
| 76 | if (!xen_have_vector_callback) { | ||
| 77 | #ifdef CONFIG_PARAVIRT_SPINLOCKS | ||
| 78 | nopvspin = true; | ||
| 79 | #endif | ||
| 68 | return; | 80 | return; |
| 81 | } | ||
| 69 | 82 | ||
| 70 | smp_ops.smp_prepare_cpus = xen_hvm_smp_prepare_cpus; | ||
| 71 | smp_ops.smp_send_reschedule = xen_smp_send_reschedule; | 83 | smp_ops.smp_send_reschedule = xen_smp_send_reschedule; |
| 72 | smp_ops.cpu_die = xen_hvm_cpu_die; | ||
| 73 | smp_ops.send_call_func_ipi = xen_smp_send_call_function_ipi; | 84 | smp_ops.send_call_func_ipi = xen_smp_send_call_function_ipi; |
| 74 | smp_ops.send_call_func_single_ipi = xen_smp_send_call_function_single_ipi; | 85 | smp_ops.send_call_func_single_ipi = xen_smp_send_call_function_single_ipi; |
| 75 | smp_ops.smp_prepare_boot_cpu = xen_hvm_smp_prepare_boot_cpu; | ||
| 76 | smp_ops.smp_cpus_done = xen_smp_cpus_done; | ||
| 77 | } | 86 | } |
| @@ -178,6 +178,7 @@ xen_pv_trap asm_exc_simd_coprocessor_error · 177 unmodified lines | |||
| 178 | #ifdef CONFIG_IA32_EMULATION | 178 | #ifdef CONFIG_IA32_EMULATION |
| 179 | xen_pv_trap entry_INT80_compat | 179 | xen_pv_trap entry_INT80_compat |
| 180 | #endif | 180 | #endif |
| 181 | xen_pv_trap asm_exc_xen_unknown_trap | ||
| 181 | xen_pv_trap asm_exc_xen_hypervisor_callback | 182 | xen_pv_trap asm_exc_xen_hypervisor_callback |
| 182 | 183 | ||
| 183 | __INIT | 184 | __INIT |
| @@ -1016,6 +1016,8 @@ static void blkcg_css_offline(struct cgroup_subsys_state *css) · 1015 unmodified lines | |||
| 1016 | */ | 1016 | */ |
| 1017 | void blkcg_destroy_blkgs(struct blkcg *blkcg) | 1017 | void blkcg_destroy_blkgs(struct blkcg *blkcg) |
| 1018 | { | 1018 | { |
| 1019 | might_sleep(); | ||
| 1020 | |||
| 1019 | spin_lock_irq(&blkcg->lock); | 1021 | spin_lock_irq(&blkcg->lock); |
| 1020 | 1022 | ||
| 1021 | while (!hlist_empty(&blkcg->blkg_list)) { | 1023 | while (!hlist_empty(&blkcg->blkg_list)) { |
| @@ -1023,14 +1025,20 @@ void blkcg_destroy_blkgs(struct blkcg *blkcg) · 1 unmodified line | |||
| 1023 | struct blkcg_gq, blkcg_node); | 1025 | struct blkcg_gq, blkcg_node); |
| 1024 | struct request_queue *q = blkg->q; | 1026 | struct request_queue *q = blkg->q; |
| 1025 | 1027 | ||
| 1026 | if (spin_trylock(&q->queue_lock)) { | 1028 | if (need_resched() || !spin_trylock(&q->queue_lock)) { |
| 1027 | blkg_destroy(blkg); | 1029 | /* |
| 1028 | spin_unlock(&q->queue_lock); | 1030 | * Given that the system can accumulate a huge number |
| 1029 | } else { | 1031 | * of blkgs in pathological cases, check to see if we |
| 1032 | * need to rescheduling to avoid softlockup. | ||
| 1033 | */ | ||
| 1030 | spin_unlock_irq(&blkcg->lock); | 1034 | spin_unlock_irq(&blkcg->lock); |
| 1031 | cpu_relax(); | 1035 | cond_resched(); |
| 1032 | spin_lock_irq(&blkcg->lock); | 1036 | spin_lock_irq(&blkcg->lock); |
| 1037 | continue; | ||
| 1033 | } | 1038 | } |
| 1039 | |||
| 1040 | blkg_destroy(blkg); | ||
| 1041 | spin_unlock(&q->queue_lock); | ||
| 1034 | } | 1042 | } |
| 1035 | 1043 | ||
| 1036 | spin_unlock_irq(&blkcg->lock); | 1044 | spin_unlock_irq(&blkcg->lock); |
| @@ -2551,8 +2551,8 @@ static void ioc_rqos_throttle(struct rq_qos *rqos, struct bio *bio) · 2550 unmodified lines | |||
| 2551 | bool use_debt, ioc_locked; | 2551 | bool use_debt, ioc_locked; |
| 2552 | unsigned long flags; | 2552 | unsigned long flags; |
| 2553 | 2553 | ||
| 2554 | /* bypass IOs if disabled or for root cgroup */ | 2554 | /* bypass IOs if disabled, still initializing, or for root cgroup */ |
| 2555 | if (!ioc->enabled || !iocg->level) | 2555 | if (!ioc->enabled || !iocg || !iocg->level) |
| 2556 | return; | 2556 | return; |
| 2557 | 2557 | ||
| 2558 | /* calculate the absolute vtime cost */ | 2558 | /* calculate the absolute vtime cost */ |
| @@ -2679,14 +2679,14 @@ static void ioc_rqos_merge(struct rq_qos *rqos, struct request *rq, · 120 unmodified lines | |||
| 2679 | struct bio *bio) | 2679 | struct bio *bio) |
| 2680 | { | 2680 | { |
| 2681 | struct ioc_gq *iocg = blkg_to_iocg(bio->bi_blkg); | 2681 | struct ioc_gq *iocg = blkg_to_iocg(bio->bi_blkg); |
| 2682 | struct ioc *ioc = iocg->ioc; | 2682 | struct ioc *ioc = rqos_to_ioc(rqos); |
| 2683 | sector_t bio_end = bio_end_sector(bio); | 2683 | sector_t bio_end = bio_end_sector(bio); |
| 2684 | struct ioc_now now; | 2684 | struct ioc_now now; |
| 2685 | u64 vtime, abs_cost, cost; | 2685 | u64 vtime, abs_cost, cost; |
| 2686 | unsigned long flags; | 2686 | unsigned long flags; |
| 2687 | 2687 | ||
| 2688 | /* bypass if disabled or for root cgroup */ | 2688 | /* bypass if disabled, still initializing, or for root cgroup */ |
| 2689 | if (!ioc->enabled || !iocg->level) | 2689 | if (!ioc->enabled || !iocg || !iocg->level) |
| 2690 | return; | 2690 | return; |
| 2691 | 2691 | ||
| 2692 | abs_cost = calc_vtime_cost(bio, iocg, true); | 2692 | abs_cost = calc_vtime_cost(bio, iocg, true); |
| @@ -2863,6 +2863,12 @@ static int blk_iocost_init(struct request_queue *q) · 170 unmodified lines | |||
| 2863 | ioc_refresh_params(ioc, true); | 2863 | ioc_refresh_params(ioc, true); |
| 2864 | spin_unlock_irq(&ioc->lock); | 2864 | spin_unlock_irq(&ioc->lock); |
| 2865 | 2865 | ||
| 2866 | /* | ||
| 2867 | * rqos must be added before activation to allow iocg_pd_init() to | ||
| 2868 | * lookup the ioc from q. This means that the rqos methods may get | ||
| 2869 | * called before policy activation completion, can't assume that the | ||
| 2870 | * target bio has an iocg associated and need to test for NULL iocg. | ||
| 2871 | */ | ||
| 2866 | rq_qos_add(q, rqos); | 2872 | rq_qos_add(q, rqos); |
| 2867 | ret = blkcg_activate_policy(q, &blkcg_policy_iocost); | 2873 | ret = blkcg_activate_policy(q, &blkcg_policy_iocost); |
| 2868 | if (ret) { | 2874 | if (ret) { |
| @@ -246,6 +246,7 @@ static const char *const hctx_flag_name[] = { · 245 unmodified lines | |||
| 246 | HCTX_FLAG_NAME(BLOCKING), | 246 | HCTX_FLAG_NAME(BLOCKING), |
| 247 | HCTX_FLAG_NAME(NO_SCHED), | 247 | HCTX_FLAG_NAME(NO_SCHED), |
| 248 | HCTX_FLAG_NAME(STACKING), | 248 | HCTX_FLAG_NAME(STACKING), |
| 249 | HCTX_FLAG_NAME(TAG_HCTX_SHARED), | ||
| 249 | }; | 250 | }; |
| 250 | #undef HCTX_FLAG_NAME | 251 | #undef HCTX_FLAG_NAME |
| 251 | 252 | ||
| @@ -304,7 +304,7 @@ static inline bool hctx_may_queue(struct blk_mq_hw_ctx *hctx, · 303 unmodified lines | |||
| 304 | struct request_queue *q = hctx->queue; | 304 | struct request_queue *q = hctx->queue; |
| 305 | struct blk_mq_tag_set *set = q->tag_set; | 305 | struct blk_mq_tag_set *set = q->tag_set; |
| 306 | 306 | ||
| 307 | if (!test_bit(BLK_MQ_S_TAG_ACTIVE, &q->queue_flags)) | 307 | if (!test_bit(QUEUE_FLAG_HCTX_ACTIVE, &q->queue_flags)) |
| 308 | return true; | 308 | return true; |
| 309 | users = atomic_read(&set->active_queues_shared_sbitmap); | 309 | users = atomic_read(&set->active_queues_shared_sbitmap); |
| 310 | } else { | 310 | } else { |
| @@ -45,10 +45,11 @@ static void disk_release_events(struct gendisk *disk); · 44 unmodified lines | |||
| 45 | void set_capacity(struct gendisk *disk, sector_t sectors) | 45 | void set_capacity(struct gendisk *disk, sector_t sectors) |
| 46 | { | 46 | { |
| 47 | struct block_device *bdev = disk->part0; | 47 | struct block_device *bdev = disk->part0; |
| 48 | unsigned long flags; | ||
| 48 | 49 | ||
| 49 | spin_lock(&bdev->bd_size_lock); | 50 | spin_lock_irqsave(&bdev->bd_size_lock, flags); |
| 50 | i_size_write(bdev->bd_inode, (loff_t)sectors << SECTOR_SHIFT); | 51 | i_size_write(bdev->bd_inode, (loff_t)sectors << SECTOR_SHIFT); |
| 51 | spin_unlock(&bdev->bd_size_lock); | 52 | spin_unlock_irqrestore(&bdev->bd_size_lock, flags); |
| 52 | } | 53 | } |
| 53 | EXPORT_SYMBOL(set_capacity); | 54 | EXPORT_SYMBOL(set_capacity); |
| 54 | 55 | ||
| @@ -246,15 +247,18 @@ struct block_device *disk_part_iter_next(struct disk_part_iter *piter) · 191 unmodified lines | |||
| 246 | part = rcu_dereference(ptbl->part[piter->idx]); | 247 | part = rcu_dereference(ptbl->part[piter->idx]); |
| 247 | if (!part) | 248 | if (!part) |
| 248 | continue; | 249 | continue; |
| 250 | piter->part = bdgrab(part); | ||
| 251 | if (!piter->part) | ||
| 252 | continue; | ||
| 249 | if (!bdev_nr_sectors(part) && | 253 | if (!bdev_nr_sectors(part) && |
| 250 | !(piter->flags & DISK_PITER_INCL_EMPTY) && | 254 | !(piter->flags & DISK_PITER_INCL_EMPTY) && |
| 251 | !(piter->flags & DISK_PITER_INCL_EMPTY_PART0 && | 255 | !(piter->flags & DISK_PITER_INCL_EMPTY_PART0 && |
| 252 | piter->idx == 0)) | 256 | piter->idx == 0)) { |
| 257 | bdput(piter->part); | ||
| 258 | piter->part = NULL; | ||
| 253 | continue; | 259 | continue; |
| 260 | } | ||
| 254 | 261 | ||
| 255 | piter->part = bdgrab(part); | ||
| 256 | if (!piter->part) | ||
| 257 | continue; | ||
| 258 | piter->idx += inc; | 262 | piter->idx += inc; |
| 259 | break; | 263 | break; |
| 260 | } | 264 | } |
| @@ -88,9 +88,11 @@ static int (*check_part[])(struct parsed_partitions *) = { · 87 unmodified lines | |||
| 88 | 88 | ||
| 89 | static void bdev_set_nr_sectors(struct block_device *bdev, sector_t sectors) | 89 | static void bdev_set_nr_sectors(struct block_device *bdev, sector_t sectors) |
| 90 | { | 90 | { |
| 91 | spin_lock(&bdev->bd_size_lock); | 91 | unsigned long flags; |
| 92 | |||
| 93 | spin_lock_irqsave(&bdev->bd_size_lock, flags); | ||
| 92 | i_size_write(bdev->bd_inode, (loff_t)sectors << SECTOR_SHIFT); | 94 | i_size_write(bdev->bd_inode, (loff_t)sectors << SECTOR_SHIFT); |
| 93 | spin_unlock(&bdev->bd_size_lock); | 95 | spin_unlock_irqrestore(&bdev->bd_size_lock, flags); |
| 94 | } | 96 | } |
| 95 | 97 | ||
| 96 | static struct parsed_partitions *allocate_partitions(struct gendisk *hd) | 98 | static struct parsed_partitions *allocate_partitions(struct gendisk *hd) |
| @@ -384,7 +386,7 @@ static struct block_device *add_partition(struct gendisk *disk, int partno, · 287 unmodified lines | |||
| 384 | 386 | ||
| 385 | err = blk_alloc_devt(bdev, &devt); | 387 | err = blk_alloc_devt(bdev, &devt); |
| 386 | if (err) | 388 | if (err) |
| 387 | goto out_bdput; | 389 | goto out_put; |
| 388 | pdev->devt = devt; | 390 | pdev->devt = devt; |
| 389 | 391 | ||
| 390 | /* delay uevent until 'holders' subdir is created */ | 392 | /* delay uevent until 'holders' subdir is created */ |
| @@ -354,7 +354,7 @@ static uint32_t derive_pub_key(const void *pub_key, uint32_t len, uint8_t *buf) · 353 unmodified lines | |||
| 354 | memcpy(cur, e, sizeof(e)); | 354 | memcpy(cur, e, sizeof(e)); |
| 355 | cur += sizeof(e); | 355 | cur += sizeof(e); |
| 356 | /* Zero parameters to satisfy set_pub_key ABI. */ | 356 | /* Zero parameters to satisfy set_pub_key ABI. */ |
| 357 | memset(cur, 0, SETKEY_PARAMS_SIZE); | 357 | memzero_explicit(cur, SETKEY_PARAMS_SIZE); |
| 358 | 358 | ||
| 359 | return cur - buf; | 359 | return cur - buf; |
| 360 | } | 360 | } |
| @@ -356,7 +356,8 @@ int public_key_verify_signature(const struct public_key *pkey, · 355 unmodified lines | |||
| 356 | if (ret) | 356 | if (ret) |
| 357 | goto error_free_key; | 357 | goto error_free_key; |
| 358 | 358 | ||
| 359 | if (strcmp(sig->pkey_algo, "sm2") == 0 && sig->data_size) { | 359 | if (sig->pkey_algo && strcmp(sig->pkey_algo, "sm2") == 0 && |
| 360 | sig->data_size) { | ||
| 360 | ret = cert_sig_digest_update(sig, tfm); | 361 | ret = cert_sig_digest_update(sig, tfm); |
| 361 | if (ret) | 362 | if (ret) |
| 362 | goto error_free_key; | 363 | goto error_free_key; |
| @@ -39,7 +39,8 @@ static int ecdh_set_secret(struct crypto_kpp *tfm, const void *buf, · 38 unmodified lines | |||
| 39 | struct ecdh params; | 39 | struct ecdh params; |
| 40 | unsigned int ndigits; | 40 | unsigned int ndigits; |
| 41 | 41 | ||
| 42 | if (crypto_ecdh_decode_key(buf, len, ¶ms) < 0) | 42 | if (crypto_ecdh_decode_key(buf, len, ¶ms) < 0 || |
| 43 | params.key_size > sizeof(ctx->private_key)) | ||
| 43 | return -EINVAL; | 44 | return -EINVAL; |
| 44 | 45 | ||
| 45 | ndigits = ecdh_supported_curve(params.curve_id); | 46 | ndigits = ecdh_supported_curve(params.curve_id); |
| @@ -107,6 +107,8 @@ do_xor_speed(struct xor_block_template *tmpl, void *b1, void *b2) · 106 unmodified lines | |||
| 107 | preempt_enable(); | 107 | preempt_enable(); |
| 108 | 108 | ||
| 109 | // bytes/ns == GB/s, multiply by 1000 to get MB/s [not MiB/s] | 109 | // bytes/ns == GB/s, multiply by 1000 to get MB/s [not MiB/s] |
| 110 | if (!min) | ||
| 111 | min = 1; | ||
| 110 | speed = (1000 * REPS * BENCH_SIZE) / (unsigned int)ktime_to_ns(min); | 112 | speed = (1000 * REPS * BENCH_SIZE) / (unsigned int)ktime_to_ns(min); |
| 111 | tmpl->speed = speed; | 113 | tmpl->speed = speed; |
| 112 | 114 | ||
| @@ -395,9 +395,6 @@ config ACPI_CONTAINER · 394 unmodified lines | |||
| 395 | 395 | ||
| 396 | This helps support hotplug of nodes, CPUs, and memory. | 396 | This helps support hotplug of nodes, CPUs, and memory. |
| 397 | 397 | ||
| 398 | To compile this driver as a module, choose M here: | ||
| 399 | the module will be called container. | ||
| 400 | |||
| 401 | config ACPI_HOTPLUG_MEMORY | 398 | config ACPI_HOTPLUG_MEMORY |
| 402 | bool "Memory Hotplug" | 399 | bool "Memory Hotplug" |
| 403 | depends on MEMORY_HOTPLUG | 400 | depends on MEMORY_HOTPLUG |
| @@ -411,9 +408,6 @@ config ACPI_HOTPLUG_MEMORY · 7 unmodified lines | |||
| 411 | removing memory devices at runtime, you need not enable | 408 | removing memory devices at runtime, you need not enable |
| 412 | this driver. | 409 | this driver. |
| 413 | 410 | ||
| 414 | To compile this driver as a module, choose M here: | ||
| 415 | the module will be called acpi_memhotplug. | ||
| 416 | |||
| 417 | config ACPI_HOTPLUG_IOAPIC | 411 | config ACPI_HOTPLUG_IOAPIC |
| 418 | bool | 412 | bool |
| 419 | depends on PCI | 413 | depends on PCI |
| @@ -495,8 +495,9 @@ acpi_ns_repair_HID(struct acpi_evaluate_info *info, · 494 unmodified lines | |||
| 495 | union acpi_operand_object **return_object_ptr) | 495 | union acpi_operand_object **return_object_ptr) |
| 496 | { | 496 | { |
| 497 | union acpi_operand_object *return_object = *return_object_ptr; | 497 | union acpi_operand_object *return_object = *return_object_ptr; |
| 498 | char *dest; | 498 | union acpi_operand_object *new_string; |
| 499 | char *source; | 499 | char *source; |
| 500 | char *dest; | ||
| 500 | 501 | ||
| 501 | ACPI_FUNCTION_NAME(ns_repair_HID); | 502 | ACPI_FUNCTION_NAME(ns_repair_HID); |
| 502 | 503 | ||
| @@ -517,6 +518,13 @@ acpi_ns_repair_HID(struct acpi_evaluate_info *info, · 14 unmodified lines | |||
| 517 | return_ACPI_STATUS(AE_OK); | 518 | return_ACPI_STATUS(AE_OK); |
| 518 | } | 519 | } |
| 519 | 520 | ||
| 521 | /* It is simplest to always create a new string object */ | ||
| 522 | |||
| 523 | new_string = acpi_ut_create_string_object(return_object->string.length); | ||
| 524 | if (!new_string) { | ||
| 525 | return_ACPI_STATUS(AE_NO_MEMORY); | ||
| 526 | } | ||
| 527 | |||
| 520 | /* | 528 | /* |
| 521 | * Remove a leading asterisk if present. For some unknown reason, there | 529 | * Remove a leading asterisk if present. For some unknown reason, there |
| 522 | * are many machines in the field that contains IDs like this. | 530 | * are many machines in the field that contains IDs like this. |
| @@ -526,7 +534,7 @@ acpi_ns_repair_HID(struct acpi_evaluate_info *info, · 3 unmodified lines | |||
| 526 | source = return_object->string.pointer; | 534 | source = return_object->string.pointer; |
| 527 | if (*source == '*') { | 535 | if (*source == '*') { |
| 528 | source++; | 536 | source++; |
| 529 | return_object->string.length--; | 537 | new_string->string.length--; |
| 530 | 538 | ||
| 531 | ACPI_DEBUG_PRINT((ACPI_DB_REPAIR, | 539 | ACPI_DEBUG_PRINT((ACPI_DB_REPAIR, |
| 532 | "%s: Removed invalid leading asterisk\n", | 540 | "%s: Removed invalid leading asterisk\n", |
| @@ -541,11 +549,12 @@ acpi_ns_repair_HID(struct acpi_evaluate_info *info, · 8 unmodified lines | |||
| 541 | * "NNNN####" where N is an uppercase letter or decimal digit, and | 549 | * "NNNN####" where N is an uppercase letter or decimal digit, and |
| 542 | * # is a hex digit. | 550 | * # is a hex digit. |
| 543 | */ | 551 | */ |
| 544 | for (dest = return_object->string.pointer; *source; dest++, source++) { | 552 | for (dest = new_string->string.pointer; *source; dest++, source++) { |
| 545 | *dest = (char)toupper((int)*source); | 553 | *dest = (char)toupper((int)*source); |
| 546 | } | 554 | } |
| 547 | return_object->string.pointer[return_object->string.length] = 0; | ||
| 548 | 555 | ||
| 556 | acpi_ut_remove_reference(return_object); | ||
| 557 | *return_object_ptr = new_string; | ||
| 549 | return_ACPI_STATUS(AE_OK); | 558 | return_ACPI_STATUS(AE_OK); |
| 550 | } | 559 | } |
| 551 | 560 | ||
| @@ -1107,6 +1107,11 @@ static int nc_dma_get_range(struct device *dev, u64 *size) · 1106 unmodified lines | |||
| 1107 | 1107 | ||
| 1108 | ncomp = (struct acpi_iort_named_component *)node->node_data; | 1108 | ncomp = (struct acpi_iort_named_component *)node->node_data; |
| 1109 | 1109 | ||
| 1110 | if (!ncomp->memory_address_limit) { | ||
| 1111 | pr_warn(FW_BUG "Named component missing memory address limit\n"); | ||
| 1112 | return -EINVAL; | ||
| 1113 | } | ||
| 1114 | |||
| 1110 | *size = ncomp->memory_address_limit >= 64 ? U64_MAX : | 1115 | *size = ncomp->memory_address_limit >= 64 ? U64_MAX : |
| 1111 | 1ULL<<ncomp->memory_address_limit; | 1116 | 1ULL<<ncomp->memory_address_limit; |
| 1112 | 1117 | ||
| @@ -1126,6 +1131,11 @@ static int rc_dma_get_range(struct device *dev, u64 *size) · 13 unmodified lines | |||
| 1126 | 1131 | ||
| 1127 | rc = (struct acpi_iort_root_complex *)node->node_data; | 1132 | rc = (struct acpi_iort_root_complex *)node->node_data; |
| 1128 | 1133 | ||
| 1134 | if (!rc->memory_address_limit) { | ||
| 1135 | pr_warn(FW_BUG "Root complex missing memory address limit\n"); | ||
| 1136 | return -EINVAL; | ||
| 1137 | } | ||
| 1138 | |||
| 1129 | *size = rc->memory_address_limit >= 64 ? U64_MAX : | 1139 | *size = rc->memory_address_limit >= 64 ? U64_MAX : |
| 1130 | 1ULL<<rc->memory_address_limit; | 1140 | 1ULL<<rc->memory_address_limit; |
| 1131 | 1141 | ||
| @@ -1173,8 +1183,8 @@ void iort_dma_setup(struct device *dev, u64 *dma_addr, u64 *dma_size) · 41 unmodified lines | |||
| 1173 | end = dmaaddr + size - 1; | 1183 | end = dmaaddr + size - 1; |
| 1174 | mask = DMA_BIT_MASK(ilog2(end) + 1); | 1184 | mask = DMA_BIT_MASK(ilog2(end) + 1); |
| 1175 | dev->bus_dma_limit = end; | 1185 | dev->bus_dma_limit = end; |
| 1176 | dev->coherent_dma_mask = mask; | 1186 | dev->coherent_dma_mask = min(dev->coherent_dma_mask, mask); |
| 1177 | *dev->dma_mask = mask; | 1187 | *dev->dma_mask = min(*dev->dma_mask, mask); |
| 1178 | } | 1188 | } |
| 1179 | 1189 | ||
| 1180 | *dma_addr = dmaaddr; | 1190 | *dma_addr = dmaaddr; |
| @@ -251,20 +251,12 @@ int __acpi_device_uevent_modalias(struct acpi_device *adev, · 250 unmodified lines | |||
| 251 | if (add_uevent_var(env, "MODALIAS=")) | 251 | if (add_uevent_var(env, "MODALIAS=")) |
| 252 | return -ENOMEM; | 252 | return -ENOMEM; |
| 253 | 253 | ||
| 254 | len = create_pnp_modalias(adev, &env->buf[env->buflen - 1], | 254 | if (adev->data.of_compatible) |
| 255 | sizeof(env->buf) - env->buflen); | 255 | len = create_of_modalias(adev, &env->buf[env->buflen - 1], |
| 256 | if (len < 0) | 256 | sizeof(env->buf) - env->buflen); |
| 257 | return len; | 257 | else |
| 258 | 258 | len = create_pnp_modalias(adev, &env->buf[env->buflen - 1], | |
| 259 | env->buflen += len; | 259 | sizeof(env->buf) - env->buflen); |
| 260 | if (!adev->data.of_compatible) | ||
| 261 | return 0; | ||
| 262 | |||
| 263 | if (len > 0 && add_uevent_var(env, "MODALIAS=")) | ||
| 264 | return -ENOMEM; | ||
| 265 | |||
| 266 | len = create_of_modalias(adev, &env->buf[env->buflen - 1], | ||
| 267 | sizeof(env->buf) - env->buflen); | ||
| 268 | if (len < 0) | 260 | if (len < 0) |
| 269 | return len; | 261 | return len; |
| 270 | 262 | ||
| @@ -97,7 +97,7 @@ void acpi_scan_table_handler(u32 event, void *table, void *context); · 96 unmodified lines | |||
| 97 | extern struct list_head acpi_bus_id_list; | 97 | extern struct list_head acpi_bus_id_list; |
| 98 | 98 | ||
| 99 | struct acpi_device_bus_id { | 99 | struct acpi_device_bus_id { |
| 100 | char bus_id[15]; | 100 | const char *bus_id; |
| 101 | unsigned int instance_no; | 101 | unsigned int instance_no; |
| 102 | struct list_head node; | 102 | struct list_head node; |
| 103 | }; | 103 | }; |
| @@ -2269,40 +2269,24 @@ static const struct attribute_group *acpi_nfit_region_attribute_groups[] = { · 2268 unmodified lines | |||
| 2269 | 2269 | ||
| 2270 | /* enough info to uniquely specify an interleave set */ | 2270 | /* enough info to uniquely specify an interleave set */ |
| 2271 | struct nfit_set_info { | 2271 | struct nfit_set_info { |
| 2272 | struct nfit_set_info_map { | 2272 | u64 region_offset; |
| 2273 | u64 region_offset; | 2273 | u32 serial_number; |
| 2274 | u32 serial_number; | 2274 | u32 pad; |
| 2275 | u32 pad; | ||
| 2276 | } mapping[0]; | ||
| 2277 | }; | 2275 | }; |
| 2278 | 2276 | ||
| 2279 | struct nfit_set_info2 { | 2277 | struct nfit_set_info2 { |
| 2280 | struct nfit_set_info_map2 { | 2278 | u64 region_offset; |
| 2281 | u64 region_offset; | 2279 | u32 serial_number; |
| 2282 | u32 serial_number; | 2280 | u16 vendor_id; |
| 2283 | u16 vendor_id; | 2281 | u16 manufacturing_date; |
| 2284 | u16 manufacturing_date; | 2282 | u8 manufacturing_location; |
| 2285 | u8 manufacturing_location; | 2283 | u8 reserved[31]; |
| 2286 | u8 reserved[31]; | ||
| 2287 | } mapping[0]; | ||
| 2288 | }; | 2284 | }; |
| 2289 | 2285 | ||
| 2290 | static size_t sizeof_nfit_set_info(int num_mappings) | ||
| 2291 | { | ||
| 2292 | return sizeof(struct nfit_set_info) | ||
| 2293 | + num_mappings * sizeof(struct nfit_set_info_map); | ||
| 2294 | } | ||
| 2295 | |||
| 2296 | static size_t sizeof_nfit_set_info2(int num_mappings) | ||
| 2297 | { | ||
| 2298 | return sizeof(struct nfit_set_info2) | ||
| 2299 | + num_mappings * sizeof(struct nfit_set_info_map2); | ||
| 2300 | } | ||
| 2301 | |||
| 2302 | static int cmp_map_compat(const void *m0, const void *m1) | 2286 | static int cmp_map_compat(const void *m0, const void *m1) |
| 2303 | { | 2287 | { |
| 2304 | const struct nfit_set_info_map *map0 = m0; | 2288 | const struct nfit_set_info *map0 = m0; |
| 2305 | const struct nfit_set_info_map *map1 = m1; | 2289 | const struct nfit_set_info *map1 = m1; |
| 2306 | 2290 | ||
| 2307 | return memcmp(&map0->region_offset, &map1->region_offset, | 2291 | return memcmp(&map0->region_offset, &map1->region_offset, |
| 2308 | sizeof(u64)); | 2292 | sizeof(u64)); |
| @@ -2310,8 +2294,8 @@ static int cmp_map_compat(const void *m0, const void *m1) · 1 unmodified line | |||
| 2310 | 2294 | ||
| 2311 | static int cmp_map(const void *m0, const void *m1) | 2295 | static int cmp_map(const void *m0, const void *m1) |
| 2312 | { | 2296 | { |
| 2313 | const struct nfit_set_info_map *map0 = m0; | 2297 | const struct nfit_set_info *map0 = m0; |
| 2314 | const struct nfit_set_info_map *map1 = m1; | 2298 | const struct nfit_set_info *map1 = m1; |
| 2315 | 2299 | ||
| 2316 | if (map0->region_offset < map1->region_offset) | 2300 | if (map0->region_offset < map1->region_offset) |
| 2317 | return -1; | 2301 | return -1; |
| @@ -2322,8 +2306,8 @@ static int cmp_map(const void *m0, const void *m1) · 4 unmodified lines | |||
| 2322 | 2306 | ||
| 2323 | static int cmp_map2(const void *m0, const void *m1) | 2307 | static int cmp_map2(const void *m0, const void *m1) |
| 2324 | { | 2308 | { |
| 2325 | const struct nfit_set_info_map2 *map0 = m0; | 2309 | const struct nfit_set_info2 *map0 = m0; |
| 2326 | const struct nfit_set_info_map2 *map1 = m1; | 2310 | const struct nfit_set_info2 *map1 = m1; |
| 2327 | 2311 | ||
| 2328 | if (map0->region_offset < map1->region_offset) | 2312 | if (map0->region_offset < map1->region_offset) |
| 2329 | return -1; | 2313 | return -1; |
| @@ -2361,22 +2345,22 @@ static int acpi_nfit_init_interleave_set(struct acpi_nfit_desc *acpi_desc, · 31 unmodified lines | |||
| 2361 | return -ENOMEM; | 2345 | return -ENOMEM; |
| 2362 | import_guid(&nd_set->type_guid, spa->range_guid); | 2346 | import_guid(&nd_set->type_guid, spa->range_guid); |
| 2363 | 2347 | ||
| 2364 | info = devm_kzalloc(dev, sizeof_nfit_set_info(nr), GFP_KERNEL); | 2348 | info = devm_kcalloc(dev, nr, sizeof(*info), GFP_KERNEL); |
| 2365 | if (!info) | 2349 | if (!info) |
| 2366 | return -ENOMEM; | 2350 | return -ENOMEM; |
| 2367 | 2351 | ||
| 2368 | info2 = devm_kzalloc(dev, sizeof_nfit_set_info2(nr), GFP_KERNEL); | 2352 | info2 = devm_kcalloc(dev, nr, sizeof(*info2), GFP_KERNEL); |
| 2369 | if (!info2) | 2353 | if (!info2) |
| 2370 | return -ENOMEM; | 2354 | return -ENOMEM; |
| 2371 | 2355 | ||
| 2372 | for (i = 0; i < nr; i++) { | 2356 | for (i = 0; i < nr; i++) { |
| 2373 | struct nd_mapping_desc *mapping = &ndr_desc->mapping[i]; | 2357 | struct nd_mapping_desc *mapping = &ndr_desc->mapping[i]; |
| 2374 | struct nfit_set_info_map *map = &info->mapping[i]; | ||
| 2375 | struct nfit_set_info_map2 *map2 = &info2->mapping[i]; | ||
| 2376 | struct nvdimm *nvdimm = mapping->nvdimm; | 2358 | struct nvdimm *nvdimm = mapping->nvdimm; |
| 2377 | struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); | 2359 | struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); |
| 2378 | struct acpi_nfit_memory_map *memdev = memdev_from_spa(acpi_desc, | 2360 | struct nfit_set_info *map = &info[i]; |
| 2379 | spa->range_index, i); | 2361 | struct nfit_set_info2 *map2 = &info2[i]; |
| 2362 | struct acpi_nfit_memory_map *memdev = | ||
| 2363 | memdev_from_spa(acpi_desc, spa->range_index, i); | ||
| 2380 | struct acpi_nfit_control_region *dcr = nfit_mem->dcr; | 2364 | struct acpi_nfit_control_region *dcr = nfit_mem->dcr; |
| 2381 | 2365 | ||
| 2382 | if (!memdev || !nfit_mem->dcr) { | 2366 | if (!memdev || !nfit_mem->dcr) { |
| @@ -2395,23 +2379,20 @@ static int acpi_nfit_init_interleave_set(struct acpi_nfit_desc *acpi_desc, · 12 unmodified lines | |||
| 2395 | } | 2379 | } |
| 2396 | 2380 | ||
| 2397 | /* v1.1 namespaces */ | 2381 | /* v1.1 namespaces */ |
| 2398 | sort(&info->mapping[0], nr, sizeof(struct nfit_set_info_map), | 2382 | sort(info, nr, sizeof(*info), cmp_map, NULL); |
| 2399 | cmp_map, NULL); | 2383 | nd_set->cookie1 = nd_fletcher64(info, sizeof(*info) * nr, 0); |
| 2400 | nd_set->cookie1 = nd_fletcher64(info, sizeof_nfit_set_info(nr), 0); | ||
| 2401 | 2384 | ||
| 2402 | /* v1.2 namespaces */ | 2385 | /* v1.2 namespaces */ |
| 2403 | sort(&info2->mapping[0], nr, sizeof(struct nfit_set_info_map2), | 2386 | sort(info2, nr, sizeof(*info2), cmp_map2, NULL); |
| 2404 | cmp_map2, NULL); | 2387 | nd_set->cookie2 = nd_fletcher64(info2, sizeof(*info2) * nr, 0); |
| 2405 | nd_set->cookie2 = nd_fletcher64(info2, sizeof_nfit_set_info2(nr), 0); | ||
| 2406 | 2388 | ||
| 2407 | /* support v1.1 namespaces created with the wrong sort order */ | 2389 | /* support v1.1 namespaces created with the wrong sort order */ |
| 2408 | sort(&info->mapping[0], nr, sizeof(struct nfit_set_info_map), | 2390 | sort(info, nr, sizeof(*info), cmp_map_compat, NULL); |
| 2409 | cmp_map_compat, NULL); | 2391 | nd_set->altcookie = nd_fletcher64(info, sizeof(*info) * nr, 0); |
| 2410 | nd_set->altcookie = nd_fletcher64(info, sizeof_nfit_set_info(nr), 0); | ||
| 2411 | 2392 | ||
| 2412 | /* record the result of the sort for the mapping position */ | 2393 | /* record the result of the sort for the mapping position */ |
| 2413 | for (i = 0; i < nr; i++) { | 2394 | for (i = 0; i < nr; i++) { |
| 2414 | struct nfit_set_info_map2 *map2 = &info2->mapping[i]; | 2395 | struct nfit_set_info2 *map2 = &info2[i]; |
| 2415 | int j; | 2396 | int j; |
| 2416 | 2397 | ||
| 2417 | for (j = 0; j < nr; j++) { | 2398 | for (j = 0; j < nr; j++) { |
| @@ -486,6 +486,7 @@ static void acpi_device_del(struct acpi_device *device) · 485 unmodified lines | |||
| 486 | acpi_device_bus_id->instance_no--; | 486 | acpi_device_bus_id->instance_no--; |
| 487 | else { | 487 | else { |
| 488 | list_del(&acpi_device_bus_id->node); | 488 | list_del(&acpi_device_bus_id->node); |
| 489 | kfree_const(acpi_device_bus_id->bus_id); | ||
| 489 | kfree(acpi_device_bus_id); | 490 | kfree(acpi_device_bus_id); |
| 490 | } | 491 | } |
| 491 | break; | 492 | break; |
| @@ -585,6 +586,8 @@ static int acpi_get_device_data(acpi_handle handle, struct acpi_device **device, · 93 unmodified lines | |||
| 585 | if (!device) | 586 | if (!device) |
| 586 | return -EINVAL; | 587 | return -EINVAL; |
| 587 | 588 | ||
| 589 | *device = NULL; | ||
| 590 | |||
| 588 | status = acpi_get_data_full(handle, acpi_scan_drop_device, | 591 | status = acpi_get_data_full(handle, acpi_scan_drop_device, |
| 589 | (void **)device, callback); | 592 | (void **)device, callback); |
| 590 | if (ACPI_FAILURE(status) || !*device) { | 593 | if (ACPI_FAILURE(status) || !*device) { |
| @@ -674,7 +677,14 @@ int acpi_device_add(struct acpi_device *device, · 83 unmodified lines | |||
| 674 | } | 677 | } |
| 675 | if (!found) { | 678 | if (!found) { |
| 676 | acpi_device_bus_id = new_bus_id; | 679 | acpi_device_bus_id = new_bus_id; |
| 677 | strcpy(acpi_device_bus_id->bus_id, acpi_device_hid(device)); | 680 | acpi_device_bus_id->bus_id = |
| 681 | kstrdup_const(acpi_device_hid(device), GFP_KERNEL); | ||
| 682 | if (!acpi_device_bus_id->bus_id) { | ||
| 683 | pr_err(PREFIX "Memory allocation error for bus id\n"); | ||
| 684 | result = -ENOMEM; | ||
| 685 | goto err_free_new_bus_id; | ||
| 686 | } | ||
| 687 | |||
| 678 | acpi_device_bus_id->instance_no = 0; | 688 | acpi_device_bus_id->instance_no = 0; |
| 679 | list_add_tail(&acpi_device_bus_id->node, &acpi_bus_id_list); | 689 | list_add_tail(&acpi_device_bus_id->node, &acpi_bus_id_list); |
| 680 | } | 690 | } |
| @@ -709,6 +719,11 @@ int acpi_device_add(struct acpi_device *device, · 28 unmodified lines | |||
| 709 | if (device->parent) | 719 | if (device->parent) |
| 710 | list_del(&device->node); | 720 | list_del(&device->node); |
| 711 | list_del(&device->wakeup_list); | 721 | list_del(&device->wakeup_list); |
| 722 | |||
| 723 | err_free_new_bus_id: | ||
| 724 | if (!found) | ||
| 725 | kfree(new_bus_id); | ||
| 726 | |||
| 712 | mutex_unlock(&acpi_device_lock); | 727 | mutex_unlock(&acpi_device_lock); |
| 713 | 728 | ||
| 714 | err_detach: | 729 | err_detach: |
| @@ -2108,12 +2123,12 @@ void acpi_walk_dep_device_list(acpi_handle handle) · 1393 unmodified lines | |||
| 2108 | list_for_each_entry_safe(dep, tmp, &acpi_dep_list, node) { | 2123 | list_for_each_entry_safe(dep, tmp, &acpi_dep_list, node) { |
| 2109 | if (dep->supplier == handle) { | 2124 | if (dep->supplier == handle) { |
| 2110 | acpi_bus_get_device(dep->consumer, &adev); | 2125 | acpi_bus_get_device(dep->consumer, &adev); |
| 2111 | if (!adev) | ||
| 2112 | continue; | ||
| 2113 | 2126 | ||
| 2114 | adev->dep_unmet--; | 2127 | if (adev) { |
| 2115 | if (!adev->dep_unmet) | 2128 | adev->dep_unmet--; |
| 2116 | acpi_bus_attach(adev, true); | 2129 | if (!adev->dep_unmet) |
| 2130 | acpi_bus_attach(adev, true); | ||
| 2131 | } | ||
| 2117 | 2132 | ||
| 2118 | list_del(&dep->node); | 2133 | list_del(&dep->node); |
| 2119 | kfree(dep); | 2134 | kfree(dep); |
| @@ -174,6 +174,8 @@ struct acpi_thermal { · 173 unmodified lines | |||
| 174 | struct thermal_zone_device *thermal_zone; | 174 | struct thermal_zone_device *thermal_zone; |
| 175 | int kelvin_offset; /* in millidegrees */ | 175 | int kelvin_offset; /* in millidegrees */ |
| 176 | struct work_struct thermal_check_work; | 176 | struct work_struct thermal_check_work; |
| 177 | struct mutex thermal_check_lock; | ||
| 178 | refcount_t thermal_check_count; | ||
| 177 | }; | 179 | }; |
| 178 | 180 | ||
| 179 | /* -------------------------------------------------------------------------- | 181 | /* -------------------------------------------------------------------------- |
| @@ -495,14 +497,6 @@ static int acpi_thermal_get_trip_points(struct acpi_thermal *tz) · 315 unmodified lines | |||
| 495 | return 0; | 497 | return 0; |
| 496 | } | 498 | } |
| 497 | 499 | ||
| 498 | static void acpi_thermal_check(void *data) | ||
| 499 | { | ||
| 500 | struct acpi_thermal *tz = data; | ||
| 501 | |||
| 502 | thermal_zone_device_update(tz->thermal_zone, | ||
| 503 | THERMAL_EVENT_UNSPECIFIED); | ||
| 504 | } | ||
| 505 | |||
| 506 | /* sys I/F for generic thermal sysfs support */ | 500 | /* sys I/F for generic thermal sysfs support */ |
| 507 | 501 | ||
| 508 | static int thermal_get_temp(struct thermal_zone_device *thermal, int *temp) | 502 | static int thermal_get_temp(struct thermal_zone_device *thermal, int *temp) |
| @@ -900,6 +894,12 @@ static void acpi_thermal_unregister_thermal_zone(struct acpi_thermal *tz) · 391 unmodified lines | |||
| 900 | Driver Interface | 894 | Driver Interface |
| 901 | -------------------------------------------------------------------------- */ | 895 | -------------------------------------------------------------------------- */ |
| 902 | 896 | ||
| 897 | static void acpi_queue_thermal_check(struct acpi_thermal *tz) | ||
| 898 | { | ||
| 899 | if (!work_pending(&tz->thermal_check_work)) | ||
| 900 | queue_work(acpi_thermal_pm_queue, &tz->thermal_check_work); | ||
| 901 | } | ||
| 902 | |||
| 903 | static void acpi_thermal_notify(struct acpi_device *device, u32 event) | 903 | static void acpi_thermal_notify(struct acpi_device *device, u32 event) |
| 904 | { | 904 | { |
| 905 | struct acpi_thermal *tz = acpi_driver_data(device); | 905 | struct acpi_thermal *tz = acpi_driver_data(device); |
| @@ -910,17 +910,17 @@ static void acpi_thermal_notify(struct acpi_device *device, u32 event) · 4 unmodified lines | |||
| 910 | 910 | ||
| 911 | switch (event) { | 911 | switch (event) { |
| 912 | case ACPI_THERMAL_NOTIFY_TEMPERATURE: | 912 | case ACPI_THERMAL_NOTIFY_TEMPERATURE: |
| 913 | acpi_thermal_check(tz); | 913 | acpi_queue_thermal_check(tz); |
| 914 | break; | 914 | break; |
| 915 | case ACPI_THERMAL_NOTIFY_THRESHOLDS: | 915 | case ACPI_THERMAL_NOTIFY_THRESHOLDS: |
| 916 | acpi_thermal_trips_update(tz, ACPI_TRIPS_REFRESH_THRESHOLDS); | 916 | acpi_thermal_trips_update(tz, ACPI_TRIPS_REFRESH_THRESHOLDS); |
| 917 | acpi_thermal_check(tz); | 917 | acpi_queue_thermal_check(tz); |
| 918 | acpi_bus_generate_netlink_event(device->pnp.device_class, | 918 | acpi_bus_generate_netlink_event(device->pnp.device_class, |
| 919 | dev_name(&device->dev), event, 0); | 919 | dev_name(&device->dev), event, 0); |
| 920 | break; | 920 | break; |
| 921 | case ACPI_THERMAL_NOTIFY_DEVICES: | 921 | case ACPI_THERMAL_NOTIFY_DEVICES: |
| 922 | acpi_thermal_trips_update(tz, ACPI_TRIPS_REFRESH_DEVICES); | 922 | acpi_thermal_trips_update(tz, ACPI_TRIPS_REFRESH_DEVICES); |
| 923 | acpi_thermal_check(tz); | 923 | acpi_queue_thermal_check(tz); |
| 924 | acpi_bus_generate_netlink_event(device->pnp.device_class, | 924 | acpi_bus_generate_netlink_event(device->pnp.device_class, |
| 925 | dev_name(&device->dev), event, 0); | 925 | dev_name(&device->dev), event, 0); |
| 926 | break; | 926 | break; |
| @@ -1020,7 +1020,25 @@ static void acpi_thermal_check_fn(struct work_struct *work) · 93 unmodified lines | |||
| 1020 | { | 1020 | { |
| 1021 | struct acpi_thermal *tz = container_of(work, struct acpi_thermal, | 1021 | struct acpi_thermal *tz = container_of(work, struct acpi_thermal, |
| 1022 | thermal_check_work); | 1022 | thermal_check_work); |
| 1023 | acpi_thermal_check(tz); | 1023 | |
| 1024 | /* | ||
| 1025 | * In general, it is not sufficient to check the pending bit, because | ||
| 1026 | * subsequent instances of this function may be queued after one of them | ||
| 1027 | * has started running (e.g. if _TMP sleeps). Avoid bailing out if just | ||
| 1028 | * one of them is running, though, because it may have done the actual | ||
| 1029 | * check some time ago, so allow at least one of them to block on the | ||
| 1030 | * mutex while another one is running the update. | ||
| 1031 | */ | ||
| 1032 | if (!refcount_dec_not_one(&tz->thermal_check_count)) | ||
| 1033 | return; | ||
| 1034 | |||
| 1035 | mutex_lock(&tz->thermal_check_lock); | ||
| 1036 | |||
| 1037 | thermal_zone_device_update(tz->thermal_zone, THERMAL_EVENT_UNSPECIFIED); | ||
| 1038 | |||
| 1039 | refcount_inc(&tz->thermal_check_count); | ||
| 1040 | |||
| 1041 | mutex_unlock(&tz->thermal_check_lock); | ||
| 1024 | } | 1042 | } |
| 1025 | 1043 | ||
| 1026 | static int acpi_thermal_add(struct acpi_device *device) | 1044 | static int acpi_thermal_add(struct acpi_device *device) |
| @@ -1052,6 +1070,8 @@ static int acpi_thermal_add(struct acpi_device *device) · 25 unmodified lines | |||
| 1052 | if (result) | 1070 | if (result) |
| 1053 | goto free_memory; | 1071 | goto free_memory; |
| 1054 | 1072 | ||
| 1073 | refcount_set(&tz->thermal_check_count, 3); | ||
| 1074 | mutex_init(&tz->thermal_check_lock); | ||
| 1055 | INIT_WORK(&tz->thermal_check_work, acpi_thermal_check_fn); | 1075 | INIT_WORK(&tz->thermal_check_work, acpi_thermal_check_fn); |
| 1056 | 1076 | ||
| 1057 | pr_info(PREFIX "%s [%s] (%ld C)\n", acpi_device_name(device), | 1077 | pr_info(PREFIX "%s [%s] (%ld C)\n", acpi_device_name(device), |
| @@ -1117,7 +1137,7 @@ static int acpi_thermal_resume(struct device *dev) · 59 unmodified lines | |||
| 1117 | tz->state.active |= tz->trips.active[i].flags.enabled; | 1137 | tz->state.active |= tz->trips.active[i].flags.enabled; |
| 1118 | } | 1138 | } |
| 1119 | 1139 | ||
| 1120 | queue_work(acpi_thermal_pm_queue, &tz->thermal_check_work); | 1140 | acpi_queue_thermal_check(tz); |
| 1121 | 1141 | ||
| 1122 | return AE_OK; | 1142 | return AE_OK; |
| 1123 | } | 1143 | } |
| @@ -105,18 +105,8 @@ static void lpi_device_get_constraints_amd(void) · 104 unmodified lines | |||
| 105 | 105 | ||
| 106 | for (i = 0; i < out_obj->package.count; i++) { | 106 | for (i = 0; i < out_obj->package.count; i++) { |
| 107 | union acpi_object *package = &out_obj->package.elements[i]; | 107 | union acpi_object *package = &out_obj->package.elements[i]; |
| 108 | struct lpi_device_info_amd info = { }; | ||
| 109 | 108 | ||
| 110 | if (package->type == ACPI_TYPE_INTEGER) { | 109 | if (package->type == ACPI_TYPE_PACKAGE) { |
| 111 | switch (i) { | ||
| 112 | case 0: | ||
| 113 | info.revision = package->integer.value; | ||
| 114 | break; | ||
| 115 | case 1: | ||
| 116 | info.count = package->integer.value; | ||
| 117 | break; | ||
| 118 | } | ||
| 119 | } else if (package->type == ACPI_TYPE_PACKAGE) { | ||
| 120 | lpi_constraints_table = kcalloc(package->package.count, | 110 | lpi_constraints_table = kcalloc(package->package.count, |
| 121 | sizeof(*lpi_constraints_table), | 111 | sizeof(*lpi_constraints_table), |
| 122 | GFP_KERNEL); | 112 | GFP_KERNEL); |
| @@ -135,12 +125,10 @@ static void lpi_device_get_constraints_amd(void) · 12 unmodified lines | |||
| 135 | 125 | ||
| 136 | for (k = 0; k < info_obj->package.count; ++k) { | 126 | for (k = 0; k < info_obj->package.count; ++k) { |
| 137 | union acpi_object *obj = &info_obj->package.elements[k]; | 127 | union acpi_object *obj = &info_obj->package.elements[k]; |
| 138 | union acpi_object *obj_new; | ||
| 139 | 128 | ||
| 140 | list = &lpi_constraints_table[lpi_constraints_table_size]; | 129 | list = &lpi_constraints_table[lpi_constraints_table_size]; |
| 141 | list->min_dstate = -1; | 130 | list->min_dstate = -1; |
| 142 | 131 | ||
| 143 | obj_new = &obj[k]; | ||
| 144 | switch (k) { | 132 | switch (k) { |
| 145 | case 0: | 133 | case 0: |
| 146 | dev_info.enabled = obj->integer.value; | 134 | dev_info.enabled = obj->integer.value; |
| @@ -3607,7 +3607,7 @@ static int idt77252_init_one(struct pci_dev *pcidev, · 3606 unmodified lines | |||
| 3607 | 3607 | ||
| 3608 | if ((err = dma_set_mask_and_coherent(&pcidev->dev, DMA_BIT_MASK(32)))) { | 3608 | if ((err = dma_set_mask_and_coherent(&pcidev->dev, DMA_BIT_MASK(32)))) { |
| 3609 | printk("idt77252: can't enable DMA for PCI device at %s\n", pci_name(pcidev)); | 3609 | printk("idt77252: can't enable DMA for PCI device at %s\n", pci_name(pcidev)); |
| 3610 | return err; | 3610 | goto err_out_disable_pdev; |
| 3611 | } | 3611 | } |
| 3612 | 3612 | ||
| 3613 | card = kzalloc(sizeof(struct idt77252_dev), GFP_KERNEL); | 3613 | card = kzalloc(sizeof(struct idt77252_dev), GFP_KERNEL); |
| @@ -208,6 +208,16 @@ int device_links_read_lock_held(void) · 207 unmodified lines | |||
| 208 | #endif | 208 | #endif |
| 209 | #endif /* !CONFIG_SRCU */ | 209 | #endif /* !CONFIG_SRCU */ |
| 210 | 210 | ||
| 211 | static bool device_is_ancestor(struct device *dev, struct device *target) | ||
| 212 | { | ||
| 213 | while (target->parent) { | ||
| 214 | target = target->parent; | ||
| 215 | if (dev == target) | ||
| 216 | return true; | ||
| 217 | } | ||
| 218 | return false; | ||
| 219 | } | ||
| 220 | |||
| 211 | /** | 221 | /** |
| 212 | * device_is_dependent - Check if one device depends on another one | 222 | * device_is_dependent - Check if one device depends on another one |
| 213 | * @dev: Device to check dependencies for. | 223 | * @dev: Device to check dependencies for. |
| @@ -221,7 +231,12 @@ int device_is_dependent(struct device *dev, void *target) · 7 unmodified lines | |||
| 221 | struct device_link *link; | 231 | struct device_link *link; |
| 222 | int ret; | 232 | int ret; |
| 223 | 233 | ||
| 224 | if (dev == target) | 234 | /* |
| 235 | * The "ancestors" check is needed to catch the case when the target | ||
| 236 | * device has not been completely initialized yet and it is still | ||
| 237 | * missing from the list of children of its parent device. | ||
| 238 | */ | ||
| 239 | if (dev == target || device_is_ancestor(dev, target)) | ||
| 225 | return 1; | 240 | return 1; |
| 226 | 241 | ||
| 227 | ret = device_for_each_child(dev, target, device_is_dependent); | 242 | ret = device_for_each_child(dev, target, device_is_dependent); |
| @@ -456,7 +471,9 @@ static int devlink_add_symlinks(struct device *dev, · 228 unmodified lines | |||
| 456 | struct device *con = link->consumer; | 471 | struct device *con = link->consumer; |
| 457 | char *buf; | 472 | char *buf; |
| 458 | 473 | ||
| 459 | len = max(strlen(dev_name(sup)), strlen(dev_name(con))); | 474 | len = max(strlen(dev_bus_name(sup)) + strlen(dev_name(sup)), |
| 475 | strlen(dev_bus_name(con)) + strlen(dev_name(con))); | ||
| 476 | len += strlen(":"); | ||
| 460 | len += strlen("supplier:") + 1; | 477 | len += strlen("supplier:") + 1; |
| 461 | buf = kzalloc(len, GFP_KERNEL); | 478 | buf = kzalloc(len, GFP_KERNEL); |
| 462 | if (!buf) | 479 | if (!buf) |
| @@ -470,12 +487,12 @@ static int devlink_add_symlinks(struct device *dev, · 7 unmodified lines | |||
| 470 | if (ret) | 487 | if (ret) |
| 471 | goto err_con; | 488 | goto err_con; |
| 472 | 489 | ||
| 473 | snprintf(buf, len, "consumer:%s", dev_name(con)); | 490 | snprintf(buf, len, "consumer:%s:%s", dev_bus_name(con), dev_name(con)); |
| 474 | ret = sysfs_create_link(&sup->kobj, &link->link_dev.kobj, buf); | 491 | ret = sysfs_create_link(&sup->kobj, &link->link_dev.kobj, buf); |
| 475 | if (ret) | 492 | if (ret) |
| 476 | goto err_con_dev; | 493 | goto err_con_dev; |
| 477 | 494 | ||
| 478 | snprintf(buf, len, "supplier:%s", dev_name(sup)); | 495 | snprintf(buf, len, "supplier:%s:%s", dev_bus_name(sup), dev_name(sup)); |
| 479 | ret = sysfs_create_link(&con->kobj, &link->link_dev.kobj, buf); | 496 | ret = sysfs_create_link(&con->kobj, &link->link_dev.kobj, buf); |
| 480 | if (ret) | 497 | if (ret) |
| 481 | goto err_sup_dev; | 498 | goto err_sup_dev; |
| @@ -483,7 +500,7 @@ static int devlink_add_symlinks(struct device *dev, · 1 unmodified line | |||
| 483 | goto out; | 500 | goto out; |
| 484 | 501 | ||
| 485 | err_sup_dev: | 502 | err_sup_dev: |
| 486 | snprintf(buf, len, "consumer:%s", dev_name(con)); | 503 | snprintf(buf, len, "consumer:%s:%s", dev_bus_name(con), dev_name(con)); |
| 487 | sysfs_remove_link(&sup->kobj, buf); | 504 | sysfs_remove_link(&sup->kobj, buf); |
| 488 | err_con_dev: | 505 | err_con_dev: |
| 489 | sysfs_remove_link(&link->link_dev.kobj, "consumer"); | 506 | sysfs_remove_link(&link->link_dev.kobj, "consumer"); |
| @@ -506,7 +523,9 @@ static void devlink_remove_symlinks(struct device *dev, · 16 unmodified lines | |||
| 506 | sysfs_remove_link(&link->link_dev.kobj, "consumer"); | 523 | sysfs_remove_link(&link->link_dev.kobj, "consumer"); |
| 507 | sysfs_remove_link(&link->link_dev.kobj, "supplier"); | 524 | sysfs_remove_link(&link->link_dev.kobj, "supplier"); |
| 508 | 525 | ||
| 509 | len = max(strlen(dev_name(sup)), strlen(dev_name(con))); | 526 | len = max(strlen(dev_bus_name(sup)) + strlen(dev_name(sup)), |
| 527 | strlen(dev_bus_name(con)) + strlen(dev_name(con))); | ||
| 528 | len += strlen(":"); | ||
| 510 | len += strlen("supplier:") + 1; | 529 | len += strlen("supplier:") + 1; |
| 511 | buf = kzalloc(len, GFP_KERNEL); | 530 | buf = kzalloc(len, GFP_KERNEL); |
| 512 | if (!buf) { | 531 | if (!buf) { |
| @@ -514,9 +533,9 @@ static void devlink_remove_symlinks(struct device *dev, · 1 unmodified line | |||
| 514 | return; | 533 | return; |
| 515 | } | 534 | } |
| 516 | 535 | ||
| 517 | snprintf(buf, len, "supplier:%s", dev_name(sup)); | 536 | snprintf(buf, len, "supplier:%s:%s", dev_bus_name(sup), dev_name(sup)); |
| 518 | sysfs_remove_link(&con->kobj, buf); | 537 | sysfs_remove_link(&con->kobj, buf); |
| 519 | snprintf(buf, len, "consumer:%s", dev_name(con)); | 538 | snprintf(buf, len, "consumer:%s:%s", dev_bus_name(con), dev_name(con)); |
| 520 | sysfs_remove_link(&sup->kobj, buf); | 539 | sysfs_remove_link(&sup->kobj, buf); |
| 521 | kfree(buf); | 540 | kfree(buf); |
| 522 | } | 541 | } |
| @@ -737,8 +756,9 @@ struct device_link *device_link_add(struct device *consumer, · 214 unmodified lines | |||
| 737 | 756 | ||
| 738 | link->link_dev.class = &devlink_class; | 757 | link->link_dev.class = &devlink_class; |
| 739 | device_set_pm_not_required(&link->link_dev); | 758 | device_set_pm_not_required(&link->link_dev); |
| 740 | dev_set_name(&link->link_dev, "%s--%s", | 759 | dev_set_name(&link->link_dev, "%s:%s--%s:%s", |
| 741 | dev_name(supplier), dev_name(consumer)); | 760 | dev_bus_name(supplier), dev_name(supplier), |
| 761 | dev_bus_name(consumer), dev_name(consumer)); | ||
| 742 | if (device_register(&link->link_dev)) { | 762 | if (device_register(&link->link_dev)) { |
| 743 | put_device(consumer); | 763 | put_device(consumer); |
| 744 | put_device(supplier); | 764 | put_device(supplier); |
| @@ -1808,9 +1828,7 @@ const char *dev_driver_string(const struct device *dev) · 1063 unmodified lines | |||
| 1808 | * never change once they are set, so they don't need special care. | 1828 | * never change once they are set, so they don't need special care. |
| 1809 | */ | 1829 | */ |
| 1810 | drv = READ_ONCE(dev->driver); | 1830 | drv = READ_ONCE(dev->driver); |
| 1811 | return drv ? drv->name : | 1831 | return drv ? drv->name : dev_bus_name(dev); |
| 1812 | (dev->bus ? dev->bus->name : | ||
| 1813 | (dev->class ? dev->class->name : "")); | ||
| 1814 | } | 1832 | } |
| 1815 | EXPORT_SYMBOL(dev_driver_string); | 1833 | EXPORT_SYMBOL(dev_driver_string); |
| 1816 | 1834 | ||
| @@ -4414,6 +4432,12 @@ static inline bool fwnode_is_primary(struct fwnode_handle *fwnode) · 2597 unmodified lines | |||
| 4414 | * | 4432 | * |
| 4415 | * Set the device's firmware node pointer to @fwnode, but if a secondary | 4433 | * Set the device's firmware node pointer to @fwnode, but if a secondary |
| 4416 | * firmware node of the device is present, preserve it. | 4434 | * firmware node of the device is present, preserve it. |
| 4435 | * | ||
| 4436 | * Valid fwnode cases are: | ||
| 4437 | * - primary --> secondary --> -ENODEV | ||
| 4438 | * - primary --> NULL | ||
| 4439 | * - secondary --> -ENODEV | ||
| 4440 | * - NULL | ||
| 4417 | */ | 4441 | */ |
| 4418 | void set_primary_fwnode(struct device *dev, struct fwnode_handle *fwnode) | 4442 | void set_primary_fwnode(struct device *dev, struct fwnode_handle *fwnode) |
| 4419 | { | 4443 | { |
| @@ -4432,8 +4456,9 @@ void set_primary_fwnode(struct device *dev, struct fwnode_handle *fwnode) · 12 unmodified lines | |||
| 4432 | } else { | 4456 | } else { |
| 4433 | if (fwnode_is_primary(fn)) { | 4457 | if (fwnode_is_primary(fn)) { |
| 4434 | dev->fwnode = fn->secondary; | 4458 | dev->fwnode = fn->secondary; |
| 4459 | /* Set fn->secondary = NULL, so fn remains the primary fwnode */ | ||
| 4435 | if (!(parent && fn == parent->fwnode)) | 4460 | if (!(parent && fn == parent->fwnode)) |
| 4436 | fn->secondary = ERR_PTR(-ENODEV); | 4461 | fn->secondary = NULL; |
| 4437 | } else { | 4462 | } else { |
| 4438 | dev->fwnode = NULL; | 4463 | dev->fwnode = NULL; |
| 4439 | } | 4464 | } |
| @@ -370,13 +370,6 @@ static void driver_bound(struct device *dev) · 369 unmodified lines | |||
| 370 | 370 | ||
| 371 | device_pm_check_callbacks(dev); | 371 | device_pm_check_callbacks(dev); |
| 372 | 372 | ||
| 373 | /* | ||
| 374 | * Reorder successfully probed devices to the end of the device list. | ||
| 375 | * This ensures that suspend/resume order matches probe order, which | ||
| 376 | * is usually what drivers rely on. | ||
| 377 | */ | ||
| 378 | device_pm_move_to_tail(dev); | ||
| 379 | |||
| 380 | /* | 373 | /* |
| 381 | * Make sure the device is no longer in one of the deferred lists and | 374 | * Make sure the device is no longer in one of the deferred lists and |
| 382 | * kick off retrying all pending devices | 375 | * kick off retrying all pending devices |
| @@ -619,6 +612,8 @@ dev_groups_failed: · 236 unmodified lines | |||
| 619 | else if (drv->remove) | 612 | else if (drv->remove) |
| 620 | drv->remove(dev); | 613 | drv->remove(dev); |
| 621 | probe_failed: | 614 | probe_failed: |
| 615 | kfree(dev->dma_range_map); | ||
| 616 | dev->dma_range_map = NULL; | ||
| 622 | if (dev->bus) | 617 | if (dev->bus) |
| 623 | blocking_notifier_call_chain(&dev->bus->p->bus_notifier, | 618 | blocking_notifier_call_chain(&dev->bus->p->bus_notifier, |
| 624 | BUS_NOTIFY_DRIVER_NOT_BOUND, dev); | 619 | BUS_NOTIFY_DRIVER_NOT_BOUND, dev); |
| @@ -366,6 +366,8 @@ int devm_platform_get_irqs_affinity(struct platform_device *dev, · 365 unmodified lines | |||
| 366 | return -ERANGE; | 366 | return -ERANGE; |
| 367 | 367 | ||
| 368 | nvec = platform_irq_count(dev); | 368 | nvec = platform_irq_count(dev); |
| 369 | if (nvec < 0) | ||
| 370 | return nvec; | ||
| 369 | 371 | ||
| 370 | if (nvec < minvec) | 372 | if (nvec < minvec) |
| 371 | return -ENOSPC; | 373 | return -ENOSPC; |
| @@ -582,8 +582,12 @@ void regmap_debugfs_init(struct regmap *map) · 581 unmodified lines | |||
| 582 | devname = dev_name(map->dev); | 582 | devname = dev_name(map->dev); |
| 583 | 583 | ||
| 584 | if (name) { | 584 | if (name) { |
| 585 | map->debugfs_name = kasprintf(GFP_KERNEL, "%s-%s", | 585 | if (!map->debugfs_name) { |
| 586 | map->debugfs_name = kasprintf(GFP_KERNEL, "%s-%s", | ||
| 586 | devname, name); | 587 | devname, name); |
| 588 | if (!map->debugfs_name) | ||
| 589 | return; | ||
| 590 | } | ||
| 587 | name = map->debugfs_name; | 591 | name = map->debugfs_name; |
| 588 | } else { | 592 | } else { |
| 589 | name = devname; | 593 | name = devname; |
| @@ -591,9 +595,10 @@ void regmap_debugfs_init(struct regmap *map) · 1 unmodified line | |||
| 591 | 595 | ||
| 592 | if (!strcmp(name, "dummy")) { | 596 | if (!strcmp(name, "dummy")) { |
| 593 | kfree(map->debugfs_name); | 597 | kfree(map->debugfs_name); |
| 594 | |||
| 595 | map->debugfs_name = kasprintf(GFP_KERNEL, "dummy%d", | 598 | map->debugfs_name = kasprintf(GFP_KERNEL, "dummy%d", |
| 596 | dummy_index); | 599 | dummy_index); |
| 600 | if (!map->debugfs_name) | ||
| 601 | return; | ||
| 597 | name = map->debugfs_name; | 602 | name = map->debugfs_name; |
| 598 | dummy_index++; | 603 | dummy_index++; |
| 599 | } | 604 | } |
| @@ -445,6 +445,7 @@ config BLK_DEV_RBD · 444 unmodified lines | |||
| 445 | config BLK_DEV_RSXX | 445 | config BLK_DEV_RSXX |
| 446 | tristate "IBM Flash Adapter 900GB Full Height PCIe Device Driver" | 446 | tristate "IBM Flash Adapter 900GB Full Height PCIe Device Driver" |
| 447 | depends on PCI | 447 | depends on PCI |
| 448 | select CRC32 | ||
| 448 | help | 449 | help |
| 449 | Device driver for IBM's high speed PCIe SSD | 450 | Device driver for IBM's high speed PCIe SSD |
| 450 | storage device: Flash Adapter 900GB Full Height. | 451 | storage device: Flash Adapter 900GB Full Height. |
| @@ -1022,6 +1022,12 @@ static int nbd_add_socket(struct nbd_device *nbd, unsigned long arg, · 1021 unmodified lines | |||
| 1022 | if (!sock) | 1022 | if (!sock) |
| 1023 | return err; | 1023 | return err; |
| 1024 | 1024 | ||
| 1025 | /* | ||
| 1026 | * We need to make sure we don't get any errant requests while we're | ||
| 1027 | * reallocating the ->socks array. | ||
| 1028 | */ | ||
| 1029 | blk_mq_freeze_queue(nbd->disk->queue); | ||
| 1030 | |||
| 1025 | if (!netlink && !nbd->task_setup && | 1031 | if (!netlink && !nbd->task_setup && |
| 1026 | !test_bit(NBD_RT_BOUND, &config->runtime_flags)) | 1032 | !test_bit(NBD_RT_BOUND, &config->runtime_flags)) |
| 1027 | nbd->task_setup = current; | 1033 | nbd->task_setup = current; |
| @@ -1060,10 +1066,12 @@ static int nbd_add_socket(struct nbd_device *nbd, unsigned long arg, · 32 unmodified lines | |||
| 1060 | nsock->cookie = 0; | 1066 | nsock->cookie = 0; |
| 1061 | socks[config->num_connections++] = nsock; | 1067 | socks[config->num_connections++] = nsock; |
| 1062 | atomic_inc(&config->live_connections); | 1068 | atomic_inc(&config->live_connections); |
| 1069 | blk_mq_unfreeze_queue(nbd->disk->queue); | ||
| 1063 | 1070 | ||
| 1064 | return 0; | 1071 | return 0; |
| 1065 | 1072 | ||
| 1066 | put_socket: | 1073 | put_socket: |
| 1074 | blk_mq_unfreeze_queue(nbd->disk->queue); | ||
| 1067 | sockfd_put(sock); | 1075 | sockfd_put(sock); |
| 1068 | return err; | 1076 | return err; |
| 1069 | } | 1077 | } |
| @@ -6,7 +6,10 @@ · 5 unmodified lines | |||
| 6 | #define CREATE_TRACE_POINTS | 6 | #define CREATE_TRACE_POINTS |
| 7 | #include "trace.h" | 7 | #include "trace.h" |
| 8 | 8 | ||
| 9 | #define MB_TO_SECTS(mb) (((sector_t)mb * SZ_1M) >> SECTOR_SHIFT) | 9 | static inline sector_t mb_to_sects(unsigned long mb) |
| 10 | { | ||
| 11 | return ((sector_t)mb * SZ_1M) >> SECTOR_SHIFT; | ||
| 12 | } | ||
| 10 | 13 | ||
| 11 | static inline unsigned int null_zone_no(struct nullb_device *dev, sector_t sect) | 14 | static inline unsigned int null_zone_no(struct nullb_device *dev, sector_t sect) |
| 12 | { | 15 | { |
| @@ -77,12 +80,11 @@ int null_init_zoned_dev(struct nullb_device *dev, struct request_queue *q) · 64 unmodified lines | |||
| 77 | return -EINVAL; | 80 | return -EINVAL; |
| 78 | } | 81 | } |
| 79 | 82 | ||
| 80 | zone_capacity_sects = MB_TO_SECTS(dev->zone_capacity); | 83 | zone_capacity_sects = mb_to_sects(dev->zone_capacity); |
| 81 | dev_capacity_sects = MB_TO_SECTS(dev->size); | 84 | dev_capacity_sects = mb_to_sects(dev->size); |
| 82 | dev->zone_size_sects = MB_TO_SECTS(dev->zone_size); | 85 | dev->zone_size_sects = mb_to_sects(dev->zone_size); |
| 83 | dev->nr_zones = dev_capacity_sects >> ilog2(dev->zone_size_sects); | 86 | dev->nr_zones = round_up(dev_capacity_sects, dev->zone_size_sects) |
| 84 | if (dev_capacity_sects & (dev->zone_size_sects - 1)) | 87 | >> ilog2(dev->zone_size_sects); |
| 85 | dev->nr_zones++; | ||
| 86 | 88 | ||
| 87 | dev->zones = kvmalloc_array(dev->nr_zones, sizeof(struct nullb_zone), | 89 | dev->zones = kvmalloc_array(dev->nr_zones, sizeof(struct nullb_zone), |
| 88 | GFP_KERNEL | __GFP_ZERO); | 90 | GFP_KERNEL | __GFP_ZERO); |
| @@ -7,6 +7,7 @@ config BLK_DEV_RNBD_CLIENT · 6 unmodified lines | |||
| 7 | tristate "RDMA Network Block Device driver client" | 7 | tristate "RDMA Network Block Device driver client" |
| 8 | depends on INFINIBAND_RTRS_CLIENT | 8 | depends on INFINIBAND_RTRS_CLIENT |
| 9 | select BLK_DEV_RNBD | 9 | select BLK_DEV_RNBD |
| 10 | select SG_POOL | ||
| 10 | help | 11 | help |
| 11 | RNBD client is a network block device driver using rdma transport. | 12 | RNBD client is a network block device driver using rdma transport. |
| 12 | 13 | ||
| @@ -90,3 +90,4 @@ Kleber Souza <kleber.souza@profitbricks.com> · 89 unmodified lines | |||
| 90 | Lutz Pogrell <lutz.pogrell@cloud.ionos.com> | 90 | Lutz Pogrell <lutz.pogrell@cloud.ionos.com> |
| 91 | Milind Dumbare <Milind.dumbare@gmail.com> | 91 | Milind Dumbare <Milind.dumbare@gmail.com> |
| 92 | Roman Penyaev <roman.penyaev@profitbricks.com> | 92 | Roman Penyaev <roman.penyaev@profitbricks.com> |
| 93 | Swapnil Ingle <ingleswapnil@gmail.com> | ||
| @@ -375,12 +375,19 @@ static struct rnbd_iu *rnbd_get_iu(struct rnbd_clt_session *sess, · 374 unmodified lines | |||
| 375 | init_waitqueue_head(&iu->comp.wait); | 375 | init_waitqueue_head(&iu->comp.wait); |
| 376 | iu->comp.errno = INT_MAX; | 376 | iu->comp.errno = INT_MAX; |
| 377 | 377 | ||
| 378 | if (sg_alloc_table(&iu->sgt, 1, GFP_KERNEL)) { | ||
| 379 | rnbd_put_permit(sess, permit); | ||
| 380 | kfree(iu); | ||
| 381 | return NULL; | ||
| 382 | } | ||
| 383 | |||
| 378 | return iu; | 384 | return iu; |
| 379 | } | 385 | } |
| 380 | 386 | ||
| 381 | static void rnbd_put_iu(struct rnbd_clt_session *sess, struct rnbd_iu *iu) | 387 | static void rnbd_put_iu(struct rnbd_clt_session *sess, struct rnbd_iu *iu) |
| 382 | { | 388 | { |
| 383 | if (atomic_dec_and_test(&iu->refcount)) { | 389 | if (atomic_dec_and_test(&iu->refcount)) { |
| 390 | sg_free_table(&iu->sgt); | ||
| 384 | rnbd_put_permit(sess, iu->permit); | 391 | rnbd_put_permit(sess, iu->permit); |
| 385 | kfree(iu); | 392 | kfree(iu); |
| 386 | } | 393 | } |
| @@ -487,8 +494,6 @@ static int send_msg_close(struct rnbd_clt_dev *dev, u32 device_id, bool wait) · 100 unmodified lines | |||
| 487 | iu->buf = NULL; | 494 | iu->buf = NULL; |
| 488 | iu->dev = dev; | 495 | iu->dev = dev; |
| 489 | 496 | ||
| 490 | sg_alloc_table(&iu->sgt, 1, GFP_KERNEL); | ||
| 491 | |||
| 492 | msg.hdr.type = cpu_to_le16(RNBD_MSG_CLOSE); | 497 | msg.hdr.type = cpu_to_le16(RNBD_MSG_CLOSE); |
| 493 | msg.device_id = cpu_to_le32(device_id); | 498 | msg.device_id = cpu_to_le32(device_id); |
| 494 | 499 | ||
| @@ -502,7 +507,6 @@ static int send_msg_close(struct rnbd_clt_dev *dev, u32 device_id, bool wait) · 7 unmodified lines | |||
| 502 | err = errno; | 507 | err = errno; |
| 503 | } | 508 | } |
| 504 | 509 | ||
| 505 | sg_free_table(&iu->sgt); | ||
| 506 | rnbd_put_iu(sess, iu); | 510 | rnbd_put_iu(sess, iu); |
| 507 | return err; | 511 | return err; |
| 508 | } | 512 | } |
| @@ -575,7 +579,6 @@ static int send_msg_open(struct rnbd_clt_dev *dev, bool wait) · 66 unmodified lines | |||
| 575 | iu->buf = rsp; | 579 | iu->buf = rsp; |
| 576 | iu->dev = dev; | 580 | iu->dev = dev; |
| 577 | 581 | ||
| 578 | sg_alloc_table(&iu->sgt, 1, GFP_KERNEL); | ||
| 579 | sg_init_one(iu->sgt.sgl, rsp, sizeof(*rsp)); | 582 | sg_init_one(iu->sgt.sgl, rsp, sizeof(*rsp)); |
| 580 | 583 | ||
| 581 | msg.hdr.type = cpu_to_le16(RNBD_MSG_OPEN); | 584 | msg.hdr.type = cpu_to_le16(RNBD_MSG_OPEN); |
| @@ -594,7 +597,6 @@ static int send_msg_open(struct rnbd_clt_dev *dev, bool wait) · 12 unmodified lines | |||
| 594 | err = errno; | 597 | err = errno; |
| 595 | } | 598 | } |
| 596 | 599 | ||
| 597 | sg_free_table(&iu->sgt); | ||
| 598 | rnbd_put_iu(sess, iu); | 600 | rnbd_put_iu(sess, iu); |
| 599 | return err; | 601 | return err; |
| 600 | } | 602 | } |
| @@ -622,8 +624,6 @@ static int send_msg_sess_info(struct rnbd_clt_session *sess, bool wait) · 21 unmodified lines | |||
| 622 | 624 | ||
| 623 | iu->buf = rsp; | 625 | iu->buf = rsp; |
| 624 | iu->sess = sess; | 626 | iu->sess = sess; |
| 625 | |||
| 626 | sg_alloc_table(&iu->sgt, 1, GFP_KERNEL); | ||
| 627 | sg_init_one(iu->sgt.sgl, rsp, sizeof(*rsp)); | 627 | sg_init_one(iu->sgt.sgl, rsp, sizeof(*rsp)); |
| 628 | 628 | ||
| 629 | msg.hdr.type = cpu_to_le16(RNBD_MSG_SESS_INFO); | 629 | msg.hdr.type = cpu_to_le16(RNBD_MSG_SESS_INFO); |
| @@ -650,7 +650,6 @@ put_iu: · 20 unmodified lines | |||
| 650 | } else { | 650 | } else { |
| 651 | err = errno; | 651 | err = errno; |
| 652 | } | 652 | } |
| 653 | sg_free_table(&iu->sgt); | ||
| 654 | rnbd_put_iu(sess, iu); | 653 | rnbd_put_iu(sess, iu); |
| 655 | return err; | 654 | return err; |
| 656 | } | 655 | } |
| @@ -1698,7 +1697,8 @@ static void rnbd_destroy_sessions(void) · 1041 unmodified lines | |||
| 1698 | */ | 1697 | */ |
| 1699 | 1698 | ||
| 1700 | list_for_each_entry_safe(sess, sn, &sess_list, list) { | 1699 | list_for_each_entry_safe(sess, sn, &sess_list, list) { |
| 1701 | WARN_ON(!rnbd_clt_get_sess(sess)); | 1700 | if (!rnbd_clt_get_sess(sess)) |
| 1701 | continue; | ||
| 1702 | close_rtrs(sess); | 1702 | close_rtrs(sess); |
| 1703 | list_for_each_entry_safe(dev, tn, &sess->devs_list, list) { | 1703 | list_for_each_entry_safe(dev, tn, &sess->devs_list, list) { |
| 1704 | /* | 1704 | /* |
| @@ -338,10 +338,12 @@ static int rnbd_srv_link_ev(struct rtrs_srv *rtrs, · 337 unmodified lines | |||
| 338 | 338 | ||
| 339 | void rnbd_srv_sess_dev_force_close(struct rnbd_srv_sess_dev *sess_dev) | 339 | void rnbd_srv_sess_dev_force_close(struct rnbd_srv_sess_dev *sess_dev) |
| 340 | { | 340 | { |
| 341 | mutex_lock(&sess_dev->sess->lock); | 341 | struct rnbd_srv_session *sess = sess_dev->sess; |
| 342 | rnbd_srv_destroy_dev_session_sysfs(sess_dev); | 342 | |
| 343 | mutex_unlock(&sess_dev->sess->lock); | ||
| 344 | sess_dev->keep_id = true; | 343 | sess_dev->keep_id = true; |
| 344 | mutex_lock(&sess->lock); | ||
| 345 | rnbd_srv_destroy_dev_session_sysfs(sess_dev); | ||
| 346 | mutex_unlock(&sess->lock); | ||
| 345 | } | 347 | } |
| 346 | 348 | ||
| 347 | static int process_msg_close(struct rtrs_srv *rtrs, | 349 | static int process_msg_close(struct rtrs_srv *rtrs, |
| @@ -945,7 +945,8 @@ static void blkif_set_queue_limits(struct blkfront_info *info) · 944 unmodified lines | |||
| 945 | if (info->feature_discard) { | 945 | if (info->feature_discard) { |
| 946 | blk_queue_flag_set(QUEUE_FLAG_DISCARD, rq); | 946 | blk_queue_flag_set(QUEUE_FLAG_DISCARD, rq); |
| 947 | blk_queue_max_discard_sectors(rq, get_capacity(gd)); | 947 | blk_queue_max_discard_sectors(rq, get_capacity(gd)); |
| 948 | rq->limits.discard_granularity = info->discard_granularity; | 948 | rq->limits.discard_granularity = info->discard_granularity ?: |
| 949 | info->physical_sector_size; | ||
| 949 | rq->limits.discard_alignment = info->discard_alignment; | 950 | rq->limits.discard_alignment = info->discard_alignment; |
| 950 | if (info->feature_secdiscard) | 951 | if (info->feature_secdiscard) |
| 951 | blk_queue_flag_set(QUEUE_FLAG_SECERASE, rq); | 952 | blk_queue_flag_set(QUEUE_FLAG_SECERASE, rq); |
| @@ -2179,19 +2180,12 @@ static void blkfront_closing(struct blkfront_info *info) · 1227 unmodified lines | |||
| 2179 | 2180 | ||
| 2180 | static void blkfront_setup_discard(struct blkfront_info *info) | 2181 | static void blkfront_setup_discard(struct blkfront_info *info) |
| 2181 | { | 2182 | { |
| 2182 | int err; | ||
| 2183 | unsigned int discard_granularity; | ||
| 2184 | unsigned int discard_alignment; | ||
| 2185 | |||
| 2186 | info->feature_discard = 1; | 2183 | info->feature_discard = 1; |
| 2187 | err = xenbus_gather(XBT_NIL, info->xbdev->otherend, | 2184 | info->discard_granularity = xenbus_read_unsigned(info->xbdev->otherend, |
| 2188 | "discard-granularity", "%u", &discard_granularity, | 2185 | "discard-granularity", |
| 2189 | "discard-alignment", "%u", &discard_alignment, | 2186 | 0); |
| 2190 | NULL); | 2187 | info->discard_alignment = xenbus_read_unsigned(info->xbdev->otherend, |
| 2191 | if (!err) { | 2188 | "discard-alignment", 0); |
| 2192 | info->discard_granularity = discard_granularity; | ||
| 2193 | info->discard_alignment = discard_alignment; | ||
| 2194 | } | ||
| 2195 | info->feature_secdiscard = | 2189 | info->feature_secdiscard = |
| 2196 | !!xenbus_read_unsigned(info->xbdev->otherend, "discard-secure", | 2190 | !!xenbus_read_unsigned(info->xbdev->otherend, "discard-secure", |
| 2197 | 0); | 2191 | 0); |
| @@ -54,6 +54,7 @@ static int integrator_lm_populate(int num, struct device *dev) · 53 unmodified lines | |||
| 54 | ret = of_platform_default_populate(child, NULL, dev); | 54 | ret = of_platform_default_populate(child, NULL, dev); |
| 55 | if (ret) { | 55 | if (ret) { |
| 56 | dev_err(dev, "failed to populate module\n"); | 56 | dev_err(dev, "failed to populate module\n"); |
| 57 | of_node_put(child); | ||
| 57 | return ret; | 58 | return ret; |
| 58 | } | 59 | } |
| 59 | } | 60 | } |
| @@ -16,6 +16,7 @@ · 15 unmodified lines | |||
| 16 | 16 | ||
| 17 | static int simple_pm_bus_probe(struct platform_device *pdev) | 17 | static int simple_pm_bus_probe(struct platform_device *pdev) |
| 18 | { | 18 | { |
| 19 | const struct of_dev_auxdata *lookup = dev_get_platdata(&pdev->dev); | ||
| 19 | struct device_node *np = pdev->dev.of_node; | 20 | struct device_node *np = pdev->dev.of_node; |
| 20 | 21 | ||
| 21 | dev_dbg(&pdev->dev, "%s\n", __func__); | 22 | dev_dbg(&pdev->dev, "%s\n", __func__); |
| @@ -23,7 +24,7 @@ static int simple_pm_bus_probe(struct platform_device *pdev) · 1 unmodified line | |||
| 23 | pm_runtime_enable(&pdev->dev); | 24 | pm_runtime_enable(&pdev->dev); |
| 24 | 25 | ||
| 25 | if (np) | 26 | if (np) |
| 26 | of_platform_populate(np, NULL, NULL, &pdev->dev); | 27 | of_platform_populate(np, NULL, lookup, &pdev->dev); |
| 27 | 28 | ||
| 28 | return 0; | 29 | return 0; |
| 29 | } | 30 | } |
| @@ -6,8 +6,6 @@ config MXC_CLK · 5 unmodified lines | |||
| 6 | 6 | ||
| 7 | config MXC_CLK_SCU | 7 | config MXC_CLK_SCU |
| 8 | tristate | 8 | tristate |
| 9 | depends on ARCH_MXC | ||
| 10 | depends on IMX_SCU && HAVE_ARM_SMCCC | ||
| 11 | 9 | ||
| 12 | config CLK_IMX1 | 10 | config CLK_IMX1 |
| 13 | def_bool SOC_IMX1 | 11 | def_bool SOC_IMX1 |
| @@ -392,7 +392,8 @@ static int mmp2_audio_clk_remove(struct platform_device *pdev) · 391 unmodified lines | |||
| 392 | return 0; | 392 | return 0; |
| 393 | } | 393 | } |
| 394 | 394 | ||
| 395 | static int __maybe_unused mmp2_audio_clk_suspend(struct device *dev) | 395 | #ifdef CONFIG_PM |
| 396 | static int mmp2_audio_clk_suspend(struct device *dev) | ||
| 396 | { | 397 | { |
| 397 | struct mmp2_audio_clk *priv = dev_get_drvdata(dev); | 398 | struct mmp2_audio_clk *priv = dev_get_drvdata(dev); |
| 398 | 399 | ||
| @@ -404,7 +405,7 @@ static int __maybe_unused mmp2_audio_clk_suspend(struct device *dev) · 5 unmodified lines | |||
| 404 | return 0; | 405 | return 0; |
| 405 | } | 406 | } |
| 406 | 407 | ||
| 407 | static int __maybe_unused mmp2_audio_clk_resume(struct device *dev) | 408 | static int mmp2_audio_clk_resume(struct device *dev) |
| 408 | { | 409 | { |
| 409 | struct mmp2_audio_clk *priv = dev_get_drvdata(dev); | 410 | struct mmp2_audio_clk *priv = dev_get_drvdata(dev); |
| 410 | 411 | ||
| @@ -415,6 +416,7 @@ static int __maybe_unused mmp2_audio_clk_resume(struct device *dev) · 4 unmodified lines | |||
| 415 | 416 | ||
| 416 | return 0; | 417 | return 0; |
| 417 | } | 418 | } |
| 419 | #endif | ||
| 418 | 420 | ||
| 419 | static const struct dev_pm_ops mmp2_audio_clk_pm_ops = { | 421 | static const struct dev_pm_ops mmp2_audio_clk_pm_ops = { |
| 420 | SET_RUNTIME_PM_OPS(mmp2_audio_clk_suspend, mmp2_audio_clk_resume, NULL) | 422 | SET_RUNTIME_PM_OPS(mmp2_audio_clk_suspend, mmp2_audio_clk_resume, NULL) |
| @@ -891,21 +891,6 @@ static struct clk_branch gcc_boot_rom_ahb_clk = { · 890 unmodified lines | |||
| 891 | }, | 891 | }, |
| 892 | }; | 892 | }; |
| 893 | 893 | ||
| 894 | static struct clk_branch gcc_camera_ahb_clk = { | ||
| 895 | .halt_reg = 0xb008, | ||
| 896 | .halt_check = BRANCH_HALT, | ||
| 897 | .hwcg_reg = 0xb008, | ||
| 898 | .hwcg_bit = 1, | ||
| 899 | .clkr = { | ||
| 900 | .enable_reg = 0xb008, | ||
| 901 | .enable_mask = BIT(0), | ||
| 902 | .hw.init = &(struct clk_init_data){ | ||
| 903 | .name = "gcc_camera_ahb_clk", | ||
| 904 | .ops = &clk_branch2_ops, | ||
| 905 | }, | ||
| 906 | }, | ||
| 907 | }; | ||
| 908 | |||
| 909 | static struct clk_branch gcc_camera_hf_axi_clk = { | 894 | static struct clk_branch gcc_camera_hf_axi_clk = { |
| 910 | .halt_reg = 0xb020, | 895 | .halt_reg = 0xb020, |
| 911 | .halt_check = BRANCH_HALT, | 896 | .halt_check = BRANCH_HALT, |
| @@ -2317,7 +2302,6 @@ static struct clk_regmap *gcc_sc7180_clocks[] = { · 1405 unmodified lines | |||
| 2317 | [GCC_AGGRE_UFS_PHY_AXI_CLK] = &gcc_aggre_ufs_phy_axi_clk.clkr, | 2302 | [GCC_AGGRE_UFS_PHY_AXI_CLK] = &gcc_aggre_ufs_phy_axi_clk.clkr, |
| 2318 | [GCC_AGGRE_USB3_PRIM_AXI_CLK] = &gcc_aggre_usb3_prim_axi_clk.clkr, | 2303 | [GCC_AGGRE_USB3_PRIM_AXI_CLK] = &gcc_aggre_usb3_prim_axi_clk.clkr, |
| 2319 | [GCC_BOOT_ROM_AHB_CLK] = &gcc_boot_rom_ahb_clk.clkr, | 2304 | [GCC_BOOT_ROM_AHB_CLK] = &gcc_boot_rom_ahb_clk.clkr, |
| 2320 | [GCC_CAMERA_AHB_CLK] = &gcc_camera_ahb_clk.clkr, | ||
| 2321 | [GCC_CAMERA_HF_AXI_CLK] = &gcc_camera_hf_axi_clk.clkr, | 2305 | [GCC_CAMERA_HF_AXI_CLK] = &gcc_camera_hf_axi_clk.clkr, |
| 2322 | [GCC_CAMERA_THROTTLE_HF_AXI_CLK] = &gcc_camera_throttle_hf_axi_clk.clkr, | 2306 | [GCC_CAMERA_THROTTLE_HF_AXI_CLK] = &gcc_camera_throttle_hf_axi_clk.clkr, |
| 2323 | [GCC_CAMERA_XO_CLK] = &gcc_camera_xo_clk.clkr, | 2307 | [GCC_CAMERA_XO_CLK] = &gcc_camera_xo_clk.clkr, |
| @@ -2519,11 +2503,12 @@ static int gcc_sc7180_probe(struct platform_device *pdev) · 195 unmodified lines | |||
| 2519 | 2503 | ||
| 2520 | /* | 2504 | /* |
| 2521 | * Keep the clocks always-ON | 2505 | * Keep the clocks always-ON |
| 2522 | * GCC_CPUSS_GNOC_CLK, GCC_VIDEO_AHB_CLK, GCC_DISP_AHB_CLK | 2506 | * GCC_CPUSS_GNOC_CLK, GCC_VIDEO_AHB_CLK, GCC_CAMERA_AHB_CLK, |
| 2523 | * GCC_GPU_CFG_AHB_CLK | 2507 | * GCC_DISP_AHB_CLK, GCC_GPU_CFG_AHB_CLK |
| 2524 | */ | 2508 | */ |
| 2525 | regmap_update_bits(regmap, 0x48004, BIT(0), BIT(0)); | 2509 | regmap_update_bits(regmap, 0x48004, BIT(0), BIT(0)); |
| 2526 | regmap_update_bits(regmap, 0x0b004, BIT(0), BIT(0)); | 2510 | regmap_update_bits(regmap, 0x0b004, BIT(0), BIT(0)); |
| 2511 | regmap_update_bits(regmap, 0x0b008, BIT(0), BIT(0)); | ||
| 2527 | regmap_update_bits(regmap, 0x0b00c, BIT(0), BIT(0)); | 2512 | regmap_update_bits(regmap, 0x0b00c, BIT(0), BIT(0)); |
| 2528 | regmap_update_bits(regmap, 0x71004, BIT(0), BIT(0)); | 2513 | regmap_update_bits(regmap, 0x71004, BIT(0), BIT(0)); |
| 2529 | 2514 | ||
| @@ -722,7 +722,7 @@ static struct clk_rcg2 gcc_sdcc2_apps_clk_src = { · 721 unmodified lines | |||
| 722 | .name = "gcc_sdcc2_apps_clk_src", | 722 | .name = "gcc_sdcc2_apps_clk_src", |
| 723 | .parent_data = gcc_parent_data_4, | 723 | .parent_data = gcc_parent_data_4, |
| 724 | .num_parents = 5, | 724 | .num_parents = 5, |
| 725 | .ops = &clk_rcg2_ops, | 725 | .ops = &clk_rcg2_floor_ops, |
| 726 | }, | 726 | }, |
| 727 | }; | 727 | }; |
| 728 | 728 | ||
| @@ -745,7 +745,7 @@ static struct clk_rcg2 gcc_sdcc4_apps_clk_src = { · 16 unmodified lines | |||
| 745 | .name = "gcc_sdcc4_apps_clk_src", | 745 | .name = "gcc_sdcc4_apps_clk_src", |
| 746 | .parent_data = gcc_parent_data_0, | 746 | .parent_data = gcc_parent_data_0, |
| 747 | .num_parents = 3, | 747 | .num_parents = 3, |
| 748 | .ops = &clk_rcg2_ops, | 748 | .ops = &clk_rcg2_floor_ops, |
| 749 | }, | 749 | }, |
| 750 | }; | 750 | }; |
| 751 | 751 | ||
| @@ -108,7 +108,7 @@ static unsigned long ccu_mp_round_rate(struct ccu_mux_internal *mux, · 107 unmodified lines | |||
| 108 | max_m = cmp->m.max ?: 1 << cmp->m.width; | 108 | max_m = cmp->m.max ?: 1 << cmp->m.width; |
| 109 | max_p = cmp->p.max ?: 1 << ((1 << cmp->p.width) - 1); | 109 | max_p = cmp->p.max ?: 1 << ((1 << cmp->p.width) - 1); |
| 110 | 110 | ||
| 111 | if (!(clk_hw_get_flags(hw) & CLK_SET_RATE_PARENT)) { | 111 | if (!clk_hw_can_set_rate_parent(&cmp->common.hw)) { |
| 112 | ccu_mp_find_best(*parent_rate, rate, max_m, max_p, &m, &p); | 112 | ccu_mp_find_best(*parent_rate, rate, max_m, max_p, &m, &p); |
| 113 | rate = *parent_rate / p / m; | 113 | rate = *parent_rate / p / m; |
| 114 | } else { | 114 | } else { |
| @@ -1256,6 +1256,8 @@ static struct tegra_clk_init_table init_table[] __initdata = { · 1255 unmodified lines | |||
| 1256 | { TEGRA30_CLK_I2S3_SYNC, TEGRA30_CLK_CLK_MAX, 24000000, 0 }, | 1256 | { TEGRA30_CLK_I2S3_SYNC, TEGRA30_CLK_CLK_MAX, 24000000, 0 }, |
| 1257 | { TEGRA30_CLK_I2S4_SYNC, TEGRA30_CLK_CLK_MAX, 24000000, 0 }, | 1257 | { TEGRA30_CLK_I2S4_SYNC, TEGRA30_CLK_CLK_MAX, 24000000, 0 }, |
| 1258 | { TEGRA30_CLK_VIMCLK_SYNC, TEGRA30_CLK_CLK_MAX, 24000000, 0 }, | 1258 | { TEGRA30_CLK_VIMCLK_SYNC, TEGRA30_CLK_CLK_MAX, 24000000, 0 }, |
| 1259 | { TEGRA30_CLK_HDA, TEGRA30_CLK_PLL_P, 102000000, 0 }, | ||
| 1260 | { TEGRA30_CLK_HDA2CODEC_2X, TEGRA30_CLK_PLL_P, 48000000, 0 }, | ||
| 1259 | /* must be the last entry */ | 1261 | /* must be the last entry */ |
| 1260 | { TEGRA30_CLK_CLK_MAX, TEGRA30_CLK_CLK_MAX, 0, 0 }, | 1262 | { TEGRA30_CLK_CLK_MAX, TEGRA30_CLK_CLK_MAX, 0, 0 }, |
| 1261 | }; | 1263 | }; |
| @@ -235,36 +235,6 @@ static ssize_t ti_eqep_position_ceiling_write(struct counter_device *counter, · 234 unmodified lines | |||
| 235 | return len; | 235 | return len; |
| 236 | } | 236 | } |
| 237 | 237 | ||
| 238 | static ssize_t ti_eqep_position_floor_read(struct counter_device *counter, | ||
| 239 | struct counter_count *count, | ||
| 240 | void *ext_priv, char *buf) | ||
| 241 | { | ||
| 242 | struct ti_eqep_cnt *priv = counter->priv; | ||
| 243 | u32 qposinit; | ||
| 244 | |||
| 245 | regmap_read(priv->regmap32, QPOSINIT, &qposinit); | ||
| 246 | |||
| 247 | return sprintf(buf, "%u\n", qposinit); | ||
| 248 | } | ||
| 249 | |||
| 250 | static ssize_t ti_eqep_position_floor_write(struct counter_device *counter, | ||
| 251 | struct counter_count *count, | ||
| 252 | void *ext_priv, const char *buf, | ||
| 253 | size_t len) | ||
| 254 | { | ||
| 255 | struct ti_eqep_cnt *priv = counter->priv; | ||
| 256 | int err; | ||
| 257 | u32 res; | ||
| 258 | |||
| 259 | err = kstrtouint(buf, 0, &res); | ||
| 260 | if (err < 0) | ||
| 261 | return err; | ||
| 262 | |||
| 263 | regmap_write(priv->regmap32, QPOSINIT, res); | ||
| 264 | |||
| 265 | return len; | ||
| 266 | } | ||
| 267 | |||
| 268 | static ssize_t ti_eqep_position_enable_read(struct counter_device *counter, | 238 | static ssize_t ti_eqep_position_enable_read(struct counter_device *counter, |
| 269 | struct counter_count *count, | 239 | struct counter_count *count, |
| 270 | void *ext_priv, char *buf) | 240 | void *ext_priv, char *buf) |
| @@ -301,11 +271,6 @@ static struct counter_count_ext ti_eqep_position_ext[] = { · 30 unmodified lines | |||
| 301 | .read = ti_eqep_position_ceiling_read, | 271 | .read = ti_eqep_position_ceiling_read, |
| 302 | .write = ti_eqep_position_ceiling_write, | 272 | .write = ti_eqep_position_ceiling_write, |
| 303 | }, | 273 | }, |
| 304 | { | ||
| 305 | .name = "floor", | ||
| 306 | .read = ti_eqep_position_floor_read, | ||
| 307 | .write = ti_eqep_position_floor_write, | ||
| 308 | }, | ||
| 309 | { | 274 | { |
| 310 | .name = "enable", | 275 | .name = "enable", |
| 311 | .read = ti_eqep_position_enable_read, | 276 | .read = ti_eqep_position_enable_read, |
| @@ -26,6 +26,7 @@ · 25 unmodified lines | |||
| 26 | #include <linux/uaccess.h> | 26 | #include <linux/uaccess.h> |
| 27 | 27 | ||
| 28 | #include <acpi/processor.h> | 28 | #include <acpi/processor.h> |
| 29 | #include <acpi/cppc_acpi.h> | ||
| 29 | 30 | ||
| 30 | #include <asm/msr.h> | 31 | #include <asm/msr.h> |
| 31 | #include <asm/processor.h> | 32 | #include <asm/processor.h> |
| @@ -53,6 +54,7 @@ struct acpi_cpufreq_data { · 21 unmodified lines | |||
| 53 | unsigned int resume; | 54 | unsigned int resume; |
| 54 | unsigned int cpu_feature; | 55 | unsigned int cpu_feature; |
| 55 | unsigned int acpi_perf_cpu; | 56 | unsigned int acpi_perf_cpu; |
| 57 | unsigned int first_perf_state; | ||
| 56 | cpumask_var_t freqdomain_cpus; | 58 | cpumask_var_t freqdomain_cpus; |
| 57 | void (*cpu_freq_write)(struct acpi_pct_register *reg, u32 val); | 59 | void (*cpu_freq_write)(struct acpi_pct_register *reg, u32 val); |
| 58 | u32 (*cpu_freq_read)(struct acpi_pct_register *reg); | 60 | u32 (*cpu_freq_read)(struct acpi_pct_register *reg); |
| @@ -221,10 +223,10 @@ static unsigned extract_msr(struct cpufreq_policy *policy, u32 msr) · 162 unmodified lines | |||
| 221 | 223 | ||
| 222 | perf = to_perf_data(data); | 224 | perf = to_perf_data(data); |
| 223 | 225 | ||
| 224 | cpufreq_for_each_entry(pos, policy->freq_table) | 226 | cpufreq_for_each_entry(pos, policy->freq_table + data->first_perf_state) |
| 225 | if (msr == perf->states[pos->driver_data].status) | 227 | if (msr == perf->states[pos->driver_data].status) |
| 226 | return pos->frequency; | 228 | return pos->frequency; |
| 227 | return policy->freq_table[0].frequency; | 229 | return policy->freq_table[data->first_perf_state].frequency; |
| 228 | } | 230 | } |
| 229 | 231 | ||
| 230 | static unsigned extract_freq(struct cpufreq_policy *policy, u32 val) | 232 | static unsigned extract_freq(struct cpufreq_policy *policy, u32 val) |
| @@ -363,6 +365,7 @@ static unsigned int get_cur_freq_on_cpu(unsigned int cpu) · 132 unmodified lines | |||
| 363 | struct cpufreq_policy *policy; | 365 | struct cpufreq_policy *policy; |
| 364 | unsigned int freq; | 366 | unsigned int freq; |
| 365 | unsigned int cached_freq; | 367 | unsigned int cached_freq; |
| 368 | unsigned int state; | ||
| 366 | 369 | ||
| 367 | pr_debug("%s (%d)\n", __func__, cpu); | 370 | pr_debug("%s (%d)\n", __func__, cpu); |
| 368 | 371 | ||
| @@ -374,7 +377,11 @@ static unsigned int get_cur_freq_on_cpu(unsigned int cpu) · 5 unmodified lines | |||
| 374 | if (unlikely(!data || !policy->freq_table)) | 377 | if (unlikely(!data || !policy->freq_table)) |
| 375 | return 0; | 378 | return 0; |
| 376 | 379 | ||
| 377 | cached_freq = policy->freq_table[to_perf_data(data)->state].frequency; | 380 | state = to_perf_data(data)->state; |
| 381 | if (state < data->first_perf_state) | ||
| 382 | state = data->first_perf_state; | ||
| 383 | |||
| 384 | cached_freq = policy->freq_table[state].frequency; | ||
| 378 | freq = extract_freq(policy, get_cur_val(cpumask_of(cpu), data)); | 385 | freq = extract_freq(policy, get_cur_val(cpumask_of(cpu), data)); |
| 379 | if (freq != cached_freq) { | 386 | if (freq != cached_freq) { |
| 380 | /* | 387 | /* |
| @@ -628,16 +635,54 @@ static int acpi_cpufreq_blacklist(struct cpuinfo_x86 *c) · 247 unmodified lines | |||
| 628 | } | 635 | } |
| 629 | #endif | 636 | #endif |
| 630 | 637 | ||
| 638 | #ifdef CONFIG_ACPI_CPPC_LIB | ||
| 639 | static u64 get_max_boost_ratio(unsigned int cpu) | ||
| 640 | { | ||
| 641 | struct cppc_perf_caps perf_caps; | ||
| 642 | u64 highest_perf, nominal_perf; | ||
| 643 | int ret; | ||
| 644 | |||
| 645 | if (acpi_pstate_strict) | ||
| 646 | return 0; | ||
| 647 | |||
| 648 | ret = cppc_get_perf_caps(cpu, &perf_caps); | ||
| 649 | if (ret) { | ||
| 650 | pr_debug("CPU%d: Unable to get performance capabilities (%d)\n", | ||
| 651 | cpu, ret); | ||
| 652 | return 0; | ||
| 653 | } | ||
| 654 | |||
| 655 | highest_perf = perf_caps.highest_perf; | ||
| 656 | nominal_perf = perf_caps.nominal_perf; | ||
| 657 | |||
| 658 | if (!highest_perf || !nominal_perf) { | ||
| 659 | pr_debug("CPU%d: highest or nominal performance missing\n", cpu); | ||
| 660 | return 0; | ||
| 661 | } | ||
| 662 | |||
| 663 | if (highest_perf < nominal_perf) { | ||
| 664 | pr_debug("CPU%d: nominal performance above highest\n", cpu); | ||
| 665 | return 0; | ||
| 666 | } | ||
| 667 | |||
| 668 | return div_u64(highest_perf << SCHED_CAPACITY_SHIFT, nominal_perf); | ||
| 669 | } | ||
| 670 | #else | ||
| 671 | static inline u64 get_max_boost_ratio(unsigned int cpu) { return 0; } | ||
| 672 | #endif | ||
| 673 | |||
| 631 | static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy) | 674 | static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy) |
| 632 | { | 675 | { |
| 633 | unsigned int i; | 676 | struct cpufreq_frequency_table *freq_table; |
| 634 | unsigned int valid_states = 0; | 677 | struct acpi_processor_performance *perf; |
| 635 | unsigned int cpu = policy->cpu; | ||
| 636 | struct acpi_cpufreq_data *data; | 678 | struct acpi_cpufreq_data *data; |
| 679 | unsigned int cpu = policy->cpu; | ||
| 680 | struct cpuinfo_x86 *c = &cpu_data(cpu); | ||
| 681 | unsigned int valid_states = 0; | ||
| 637 | unsigned int result = 0; | 682 | unsigned int result = 0; |
| 638 | struct cpuinfo_x86 *c = &cpu_data(policy->cpu); | 683 | unsigned int state_count; |
| 639 | struct acpi_processor_performance *perf; | 684 | u64 max_boost_ratio; |
| 640 | struct cpufreq_frequency_table *freq_table; | 685 | unsigned int i; |
| 641 | #ifdef CONFIG_SMP | 686 | #ifdef CONFIG_SMP |
| 642 | static int blacklisted; | 687 | static int blacklisted; |
| 643 | #endif | 688 | #endif |
| @@ -750,8 +795,28 @@ static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy) · 106 unmodified lines | |||
| 750 | goto err_unreg; | 795 | goto err_unreg; |
| 751 | } | 796 | } |
| 752 | 797 | ||
| 753 | freq_table = kcalloc(perf->state_count + 1, sizeof(*freq_table), | 798 | state_count = perf->state_count + 1; |
| 754 | GFP_KERNEL); | 799 | |
| 800 | max_boost_ratio = get_max_boost_ratio(cpu); | ||
| 801 | if (max_boost_ratio) { | ||
| 802 | /* | ||
| 803 | * Make a room for one more entry to represent the highest | ||
| 804 | * available "boost" frequency. | ||
| 805 | */ | ||
| 806 | state_count++; | ||
| 807 | valid_states++; | ||
| 808 | data->first_perf_state = valid_states; | ||
| 809 | } else { | ||
| 810 | /* | ||
| 811 | * If the maximum "boost" frequency is unknown, ask the arch | ||
| 812 | * scale-invariance code to use the "nominal" performance for | ||
| 813 | * CPU utilization scaling so as to prevent the schedutil | ||
| 814 | * governor from selecting inadequate CPU frequencies. | ||
| 815 | */ | ||
| 816 | arch_set_max_freq_ratio(true); | ||
| 817 | } | ||
| 818 | |||
| 819 | freq_table = kcalloc(state_count, sizeof(*freq_table), GFP_KERNEL); | ||
| 755 | if (!freq_table) { | 820 | if (!freq_table) { |
| 756 | result = -ENOMEM; | 821 | result = -ENOMEM; |
| 757 | goto err_unreg; | 822 | goto err_unreg; |
| @@ -785,6 +850,30 @@ static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy) · 27 unmodified lines | |||
| 785 | valid_states++; | 850 | valid_states++; |
| 786 | } | 851 | } |
| 787 | freq_table[valid_states].frequency = CPUFREQ_TABLE_END; | 852 | freq_table[valid_states].frequency = CPUFREQ_TABLE_END; |
| 853 | |||
| 854 | if (max_boost_ratio) { | ||
| 855 | unsigned int state = data->first_perf_state; | ||
| 856 | unsigned int freq = freq_table[state].frequency; | ||
| 857 | |||
| 858 | /* | ||
| 859 | * Because the loop above sorts the freq_table entries in the | ||
| 860 | * descending order, freq is the maximum frequency in the table. | ||
| 861 | * Assume that it corresponds to the CPPC nominal frequency and | ||
| 862 | * use it to populate the frequency field of the extra "boost" | ||
| 863 | * frequency entry. | ||
| 864 | */ | ||
| 865 | freq_table[0].frequency = freq * max_boost_ratio >> SCHED_CAPACITY_SHIFT; | ||
| 866 | /* | ||
| 867 | * The purpose of the extra "boost" frequency entry is to make | ||
| 868 | * the rest of cpufreq aware of the real maximum frequency, but | ||
| 869 | * the way to request it is the same as for the first_perf_state | ||
| 870 | * entry that is expected to cover the entire range of "boost" | ||
| 871 | * frequencies of the CPU, so copy the driver_data value from | ||
| 872 | * that entry. | ||
| 873 | */ | ||
| 874 | freq_table[0].driver_data = freq_table[state].driver_data; | ||
| 875 | } | ||
| 876 | |||
| 788 | policy->freq_table = freq_table; | 877 | policy->freq_table = freq_table; |
| 789 | perf->state = 0; | 878 | perf->state = 0; |
| 790 | 879 | ||
| @@ -858,8 +947,10 @@ static void acpi_cpufreq_cpu_ready(struct cpufreq_policy *policy) · 67 unmodified lines | |||
| 858 | { | 947 | { |
| 859 | struct acpi_processor_performance *perf = per_cpu_ptr(acpi_perf_data, | 948 | struct acpi_processor_performance *perf = per_cpu_ptr(acpi_perf_data, |
| 860 | policy->cpu); | 949 | policy->cpu); |
| 950 | struct acpi_cpufreq_data *data = policy->driver_data; | ||
| 951 | unsigned int freq = policy->freq_table[data->first_perf_state].frequency; | ||
| 861 | 952 | ||
| 862 | if (perf->states[0].core_frequency * 1000 != policy->cpuinfo.max_freq) | 953 | if (perf->states[0].core_frequency * 1000 != freq) |
| 863 | pr_warn(FW_WARN "P-state 0 is not max freq\n"); | 954 | pr_warn(FW_WARN "P-state 0 is not max freq\n"); |
| 864 | } | 955 | } |
| 865 | 956 | ||
| @@ -76,11 +76,6 @@ static inline int ceiling_fp(int32_t x) · 75 unmodified lines | |||
| 76 | return ret; | 76 | return ret; |
| 77 | } | 77 | } |
| 78 | 78 | ||
| 79 | static inline int32_t percent_fp(int percent) | ||
| 80 | { | ||
| 81 | return div_fp(percent, 100); | ||
| 82 | } | ||
| 83 | |||
| 84 | static inline u64 mul_ext_fp(u64 x, u64 y) | 79 | static inline u64 mul_ext_fp(u64 x, u64 y) |
| 85 | { | 80 | { |
| 86 | return (x * y) >> EXT_FRAC_BITS; | 81 | return (x * y) >> EXT_FRAC_BITS; |
| @@ -91,11 +86,6 @@ static inline u64 div_ext_fp(u64 x, u64 y) · 4 unmodified lines | |||
| 91 | return div64_u64(x << EXT_FRAC_BITS, y); | 86 | return div64_u64(x << EXT_FRAC_BITS, y); |
| 92 | } | 87 | } |
| 93 | 88 | ||
| 94 | static inline int32_t percent_ext_fp(int percent) | ||
| 95 | { | ||
| 96 | return div_ext_fp(percent, 100); | ||
| 97 | } | ||
| 98 | |||
| 99 | /** | 89 | /** |
| 100 | * struct sample - Store performance sample | 90 | * struct sample - Store performance sample |
| 101 | * @core_avg_perf: Ratio of APERF/MPERF which is the actual average | 91 | * @core_avg_perf: Ratio of APERF/MPERF which is the actual average |
| @@ -2653,12 +2643,13 @@ static void intel_cpufreq_adjust_perf(unsigned int cpunum, · 2551 unmodified lines | |||
| 2653 | unsigned long capacity) | 2643 | unsigned long capacity) |
| 2654 | { | 2644 | { |
| 2655 | struct cpudata *cpu = all_cpu_data[cpunum]; | 2645 | struct cpudata *cpu = all_cpu_data[cpunum]; |
| 2646 | u64 hwp_cap = READ_ONCE(cpu->hwp_cap_cached); | ||
| 2656 | int old_pstate = cpu->pstate.current_pstate; | 2647 | int old_pstate = cpu->pstate.current_pstate; |
| 2657 | int cap_pstate, min_pstate, max_pstate, target_pstate; | 2648 | int cap_pstate, min_pstate, max_pstate, target_pstate; |
| 2658 | 2649 | ||
| 2659 | update_turbo_state(); | 2650 | update_turbo_state(); |
| 2660 | cap_pstate = global.turbo_disabled ? cpu->pstate.max_pstate : | 2651 | cap_pstate = global.turbo_disabled ? HWP_GUARANTEED_PERF(hwp_cap) : |
| 2661 | cpu->pstate.turbo_pstate; | 2652 | HWP_HIGHEST_PERF(hwp_cap); |
| 2662 | 2653 | ||
| 2663 | /* Optimization: Avoid unnecessary divisions. */ | 2654 | /* Optimization: Avoid unnecessary divisions. */ |
| 2664 | 2655 | ||
| @@ -878,9 +878,9 @@ static int get_transition_latency(struct powernow_k8_data *data) · 877 unmodified lines | |||
| 878 | 878 | ||
| 879 | /* Take a frequency, and issue the fid/vid transition command */ | 879 | /* Take a frequency, and issue the fid/vid transition command */ |
| 880 | static int transition_frequency_fidvid(struct powernow_k8_data *data, | 880 | static int transition_frequency_fidvid(struct powernow_k8_data *data, |
| 881 | unsigned int index) | 881 | unsigned int index, |
| 882 | struct cpufreq_policy *policy) | ||
| 882 | { | 883 | { |
| 883 | struct cpufreq_policy *policy; | ||
| 884 | u32 fid = 0; | 884 | u32 fid = 0; |
| 885 | u32 vid = 0; | 885 | u32 vid = 0; |
| 886 | int res; | 886 | int res; |
| @@ -912,9 +912,6 @@ static int transition_frequency_fidvid(struct powernow_k8_data *data, · 25 unmodified lines | |||
| 912 | freqs.old = find_khz_freq_from_fid(data->currfid); | 912 | freqs.old = find_khz_freq_from_fid(data->currfid); |
| 913 | freqs.new = find_khz_freq_from_fid(fid); | 913 | freqs.new = find_khz_freq_from_fid(fid); |
| 914 | 914 | ||
| 915 | policy = cpufreq_cpu_get(smp_processor_id()); | ||
| 916 | cpufreq_cpu_put(policy); | ||
| 917 | |||
| 918 | cpufreq_freq_transition_begin(policy, &freqs); | 915 | cpufreq_freq_transition_begin(policy, &freqs); |
| 919 | res = transition_fid_vid(data, fid, vid); | 916 | res = transition_fid_vid(data, fid, vid); |
| 920 | cpufreq_freq_transition_end(policy, &freqs, res); | 917 | cpufreq_freq_transition_end(policy, &freqs, res); |
| @@ -969,7 +966,7 @@ static long powernowk8_target_fn(void *arg) · 48 unmodified lines | |||
| 969 | 966 | ||
| 970 | powernow_k8_acpi_pst_values(data, newstate); | 967 | powernow_k8_acpi_pst_values(data, newstate); |
| 971 | 968 | ||
| 972 | ret = transition_frequency_fidvid(data, newstate); | 969 | ret = transition_frequency_fidvid(data, newstate, pol); |
| 973 | 970 | ||
| 974 | if (ret) { | 971 | if (ret) { |
| 975 | pr_err("transition frequency failed\n"); | 972 | pr_err("transition frequency failed\n"); |
| @@ -366,6 +366,7 @@ if CRYPTO_DEV_OMAP · 365 unmodified lines | |||
| 366 | config CRYPTO_DEV_OMAP_SHAM | 366 | config CRYPTO_DEV_OMAP_SHAM |
| 367 | tristate "Support for OMAP MD5/SHA1/SHA2 hw accelerator" | 367 | tristate "Support for OMAP MD5/SHA1/SHA2 hw accelerator" |
| 368 | depends on ARCH_OMAP2PLUS | 368 | depends on ARCH_OMAP2PLUS |
| 369 | select CRYPTO_ENGINE | ||
| 369 | select CRYPTO_SHA1 | 370 | select CRYPTO_SHA1 |
| 370 | select CRYPTO_MD5 | 371 | select CRYPTO_MD5 |
| 371 | select CRYPTO_SHA256 | 372 | select CRYPTO_SHA256 |
| @@ -300,11 +300,11 @@ struct mv_cesa_tdma_desc { · 299 unmodified lines | |||
| 300 | __le32 byte_cnt; | 300 | __le32 byte_cnt; |
| 301 | union { | 301 | union { |
| 302 | __le32 src; | 302 | __le32 src; |
| 303 | dma_addr_t src_dma; | 303 | u32 src_dma; |
| 304 | }; | 304 | }; |
| 305 | union { | 305 | union { |
| 306 | __le32 dst; | 306 | __le32 dst; |
| 307 | dma_addr_t dst_dma; | 307 | u32 dst_dma; |
| 308 | }; | 308 | }; |
| 309 | __le32 next_dma; | 309 | __le32 next_dma; |
| 310 | 310 | ||
| @@ -76,10 +76,6 @@ static void dma_buf_release(struct dentry *dentry) · 75 unmodified lines | |||
| 76 | 76 | ||
| 77 | dmabuf->ops->release(dmabuf); | 77 | dmabuf->ops->release(dmabuf); |
| 78 | 78 | ||
| 79 | mutex_lock(&db_list.lock); | ||
| 80 | list_del(&dmabuf->list_node); | ||
| 81 | mutex_unlock(&db_list.lock); | ||
| 82 | |||
| 83 | if (dmabuf->resv == (struct dma_resv *)&dmabuf[1]) | 79 | if (dmabuf->resv == (struct dma_resv *)&dmabuf[1]) |
| 84 | dma_resv_fini(dmabuf->resv); | 80 | dma_resv_fini(dmabuf->resv); |
| 85 | 81 | ||
| @@ -88,6 +84,22 @@ static void dma_buf_release(struct dentry *dentry) · 2 unmodified lines | |||
| 88 | kfree(dmabuf); | 84 | kfree(dmabuf); |
| 89 | } | 85 | } |
| 90 | 86 | ||
| 87 | static int dma_buf_file_release(struct inode *inode, struct file *file) | ||
| 88 | { | ||
| 89 | struct dma_buf *dmabuf; | ||
| 90 | |||
| 91 | if (!is_dma_buf_file(file)) | ||
| 92 | return -EINVAL; | ||
| 93 | |||
| 94 | dmabuf = file->private_data; | ||
| 95 | |||
| 96 | mutex_lock(&db_list.lock); | ||
| 97 | list_del(&dmabuf->list_node); | ||
| 98 | mutex_unlock(&db_list.lock); | ||
| 99 | |||
| 100 | return 0; | ||
| 101 | } | ||
| 102 | |||
| 91 | static const struct dentry_operations dma_buf_dentry_ops = { | 103 | static const struct dentry_operations dma_buf_dentry_ops = { |
| 92 | .d_dname = dmabuffs_dname, | 104 | .d_dname = dmabuffs_dname, |
| 93 | .d_release = dma_buf_release, | 105 | .d_release = dma_buf_release, |
| @@ -413,6 +425,7 @@ static void dma_buf_show_fdinfo(struct seq_file *m, struct file *file) · 319 unmodified lines | |||
| 413 | } | 425 | } |
| 414 | 426 | ||
| 415 | static const struct file_operations dma_buf_fops = { | 427 | static const struct file_operations dma_buf_fops = { |
| 428 | .release = dma_buf_file_release, | ||
| 416 | .mmap = dma_buf_mmap_internal, | 429 | .mmap = dma_buf_mmap_internal, |
| 417 | .llseek = dma_buf_llseek, | 430 | .llseek = dma_buf_llseek, |
| 418 | .poll = dma_buf_poll, | 431 | .poll = dma_buf_poll, |
| @@ -251,6 +251,9 @@ static void cma_heap_dma_buf_release(struct dma_buf *dmabuf) · 250 unmodified lines | |||
| 251 | buffer->vaddr = NULL; | 251 | buffer->vaddr = NULL; |
| 252 | } | 252 | } |
| 253 | 253 | ||
| 254 | /* free page list */ | ||
| 255 | kfree(buffer->pages); | ||
| 256 | /* release memory */ | ||
| 254 | cma_release(cma_heap->cma, buffer->cma_pages, buffer->pagecount); | 257 | cma_release(cma_heap->cma, buffer->cma_pages, buffer->pagecount); |
| 255 | kfree(buffer); | 258 | kfree(buffer); |
| 256 | } | 259 | } |
| @@ -1110,7 +1110,6 @@ static void __dma_async_device_channel_unregister(struct dma_device *device, · 1109 unmodified lines | |||
| 1110 | "%s called while %d clients hold a reference\n", | 1110 | "%s called while %d clients hold a reference\n", |
| 1111 | __func__, chan->client_count); | 1111 | __func__, chan->client_count); |
| 1112 | mutex_lock(&dma_list_mutex); | 1112 | mutex_lock(&dma_list_mutex); |
| 1113 | list_del(&chan->device_node); | ||
| 1114 | device->chancnt--; | 1113 | device->chancnt--; |
| 1115 | chan->dev->chan = NULL; | 1114 | chan->dev->chan = NULL; |
| 1116 | mutex_unlock(&dma_list_mutex); | 1115 | mutex_unlock(&dma_list_mutex); |
| @@ -86,12 +86,12 @@ static struct dw_edma_chunk *dw_edma_alloc_chunk(struct dw_edma_desc *desc) · 85 unmodified lines | |||
| 86 | 86 | ||
| 87 | if (desc->chunk) { | 87 | if (desc->chunk) { |
| 88 | /* Create and add new element into the linked list */ | 88 | /* Create and add new element into the linked list */ |
| 89 | desc->chunks_alloc++; | ||
| 90 | list_add_tail(&chunk->list, &desc->chunk->list); | ||
| 91 | if (!dw_edma_alloc_burst(chunk)) { | 89 | if (!dw_edma_alloc_burst(chunk)) { |
| 92 | kfree(chunk); | 90 | kfree(chunk); |
| 93 | return NULL; | 91 | return NULL; |
| 94 | } | 92 | } |
| 93 | desc->chunks_alloc++; | ||
| 94 | list_add_tail(&chunk->list, &desc->chunk->list); | ||
| 95 | } else { | 95 | } else { |
| 96 | /* List head */ | 96 | /* List head */ |
| 97 | chunk->burst = NULL; | 97 | chunk->burst = NULL; |
| @@ -982,11 +982,8 @@ static int dwc_alloc_chan_resources(struct dma_chan *chan) · 981 unmodified lines | |||
| 982 | 982 | ||
| 983 | dev_vdbg(chan2dev(chan), "%s\n", __func__); | 983 | dev_vdbg(chan2dev(chan), "%s\n", __func__); |
| 984 | 984 | ||
| 985 | pm_runtime_get_sync(dw->dma.dev); | ||
| 986 | |||
| 987 | /* ASSERT: channel is idle */ | 985 | /* ASSERT: channel is idle */ |
| 988 | if (dma_readl(dw, CH_EN) & dwc->mask) { | 986 | if (dma_readl(dw, CH_EN) & dwc->mask) { |
| 989 | pm_runtime_put_sync_suspend(dw->dma.dev); | ||
| 990 | dev_dbg(chan2dev(chan), "DMA channel not idle?\n"); | 987 | dev_dbg(chan2dev(chan), "DMA channel not idle?\n"); |
| 991 | return -EIO; | 988 | return -EIO; |
| 992 | } | 989 | } |
| @@ -1003,7 +1000,6 @@ static int dwc_alloc_chan_resources(struct dma_chan *chan) · 10 unmodified lines | |||
| 1003 | * We need controller-specific data to set up slave transfers. | 1000 | * We need controller-specific data to set up slave transfers. |
| 1004 | */ | 1001 | */ |
| 1005 | if (chan->private && !dw_dma_filter(chan, chan->private)) { | 1002 | if (chan->private && !dw_dma_filter(chan, chan->private)) { |
| 1006 | pm_runtime_put_sync_suspend(dw->dma.dev); | ||
| 1007 | dev_warn(chan2dev(chan), "Wrong controller-specific data\n"); | 1003 | dev_warn(chan2dev(chan), "Wrong controller-specific data\n"); |
| 1008 | return -EINVAL; | 1004 | return -EINVAL; |
| 1009 | } | 1005 | } |
| @@ -1047,8 +1043,6 @@ static void dwc_free_chan_resources(struct dma_chan *chan) · 37 unmodified lines | |||
| 1047 | if (!dw->in_use) | 1043 | if (!dw->in_use) |
| 1048 | do_dw_dma_off(dw); | 1044 | do_dw_dma_off(dw); |
| 1049 | 1045 | ||
| 1050 | pm_runtime_put_sync_suspend(dw->dma.dev); | ||
| 1051 | |||
| 1052 | dev_vdbg(chan2dev(chan), "%s: done\n", __func__); | 1046 | dev_vdbg(chan2dev(chan), "%s: done\n", __func__); |
| 1053 | } | 1047 | } |
| 1054 | 1048 | ||
| @@ -398,17 +398,31 @@ static inline bool idxd_is_enabled(struct idxd_device *idxd) · 397 unmodified lines | |||
| 398 | return false; | 398 | return false; |
| 399 | } | 399 | } |
| 400 | 400 | ||
| 401 | static inline bool idxd_device_is_halted(struct idxd_device *idxd) | ||
| 402 | { | ||
| 403 | union gensts_reg gensts; | ||
| 404 | |||
| 405 | gensts.bits = ioread32(idxd->reg_base + IDXD_GENSTATS_OFFSET); | ||
| 406 | |||
| 407 | return (gensts.state == IDXD_DEVICE_STATE_HALT); | ||
| 408 | } | ||
| 409 | |||
| 401 | /* | 410 | /* |
| 402 | * This is function is only used for reset during probe and will | 411 | * This is function is only used for reset during probe and will |
| 403 | * poll for completion. Once the device is setup with interrupts, | 412 | * poll for completion. Once the device is setup with interrupts, |
| 404 | * all commands will be done via interrupt completion. | 413 | * all commands will be done via interrupt completion. |
| 405 | */ | 414 | */ |
| 406 | void idxd_device_init_reset(struct idxd_device *idxd) | 415 | int idxd_device_init_reset(struct idxd_device *idxd) |
| 407 | { | 416 | { |
| 408 | struct device *dev = &idxd->pdev->dev; | 417 | struct device *dev = &idxd->pdev->dev; |
| 409 | union idxd_command_reg cmd; | 418 | union idxd_command_reg cmd; |
| 410 | unsigned long flags; | 419 | unsigned long flags; |
| 411 | 420 | ||
| 421 | if (idxd_device_is_halted(idxd)) { | ||
| 422 | dev_warn(&idxd->pdev->dev, "Device is HALTED!\n"); | ||
| 423 | return -ENXIO; | ||
| 424 | } | ||
| 425 | |||
| 412 | memset(&cmd, 0, sizeof(cmd)); | 426 | memset(&cmd, 0, sizeof(cmd)); |
| 413 | cmd.cmd = IDXD_CMD_RESET_DEVICE; | 427 | cmd.cmd = IDXD_CMD_RESET_DEVICE; |
| 414 | dev_dbg(dev, "%s: sending reset for init.\n", __func__); | 428 | dev_dbg(dev, "%s: sending reset for init.\n", __func__); |
| @@ -419,6 +433,7 @@ void idxd_device_init_reset(struct idxd_device *idxd) · 4 unmodified lines | |||
| 419 | IDXD_CMDSTS_ACTIVE) | 433 | IDXD_CMDSTS_ACTIVE) |
| 420 | cpu_relax(); | 434 | cpu_relax(); |
| 421 | spin_unlock_irqrestore(&idxd->dev_lock, flags); | 435 | spin_unlock_irqrestore(&idxd->dev_lock, flags); |
| 436 | return 0; | ||
| 422 | } | 437 | } |
| 423 | 438 | ||
| 424 | static void idxd_cmd_exec(struct idxd_device *idxd, int cmd_code, u32 operand, | 439 | static void idxd_cmd_exec(struct idxd_device *idxd, int cmd_code, u32 operand, |
| @@ -428,6 +443,12 @@ static void idxd_cmd_exec(struct idxd_device *idxd, int cmd_code, u32 operand, · 3 unmodified lines | |||
| 428 | DECLARE_COMPLETION_ONSTACK(done); | 443 | DECLARE_COMPLETION_ONSTACK(done); |
| 429 | unsigned long flags; | 444 | unsigned long flags; |
| 430 | 445 | ||
| 446 | if (idxd_device_is_halted(idxd)) { | ||
| 447 | dev_warn(&idxd->pdev->dev, "Device is HALTED!\n"); | ||
| 448 | *status = IDXD_CMDSTS_HW_ERR; | ||
| 449 | return; | ||
| 450 | } | ||
| 451 | |||
| 431 | memset(&cmd, 0, sizeof(cmd)); | 452 | memset(&cmd, 0, sizeof(cmd)); |
| 432 | cmd.cmd = cmd_code; | 453 | cmd.cmd = cmd_code; |
| 433 | cmd.operand = operand; | 454 | cmd.operand = operand; |
| @@ -205,5 +205,8 @@ int idxd_register_dma_channel(struct idxd_wq *wq) · 204 unmodified lines | |||
| 205 | 205 | ||
| 206 | void idxd_unregister_dma_channel(struct idxd_wq *wq) | 206 | void idxd_unregister_dma_channel(struct idxd_wq *wq) |
| 207 | { | 207 | { |
| 208 | dma_async_device_channel_unregister(&wq->idxd->dma_dev, &wq->dma_chan); | 208 | struct dma_chan *chan = &wq->dma_chan; |
| 209 | |||
| 210 | dma_async_device_channel_unregister(&wq->idxd->dma_dev, chan); | ||
| 211 | list_del(&chan->device_node); | ||
| 209 | } | 212 | } |
| @@ -326,7 +326,7 @@ void idxd_mask_msix_vector(struct idxd_device *idxd, int vec_id); · 325 unmodified lines | |||
| 326 | void idxd_unmask_msix_vector(struct idxd_device *idxd, int vec_id); | 326 | void idxd_unmask_msix_vector(struct idxd_device *idxd, int vec_id); |
| 327 | 327 | ||
| 328 | /* device control */ | 328 | /* device control */ |
| 329 | void idxd_device_init_reset(struct idxd_device *idxd); | 329 | int idxd_device_init_reset(struct idxd_device *idxd); |
| 330 | int idxd_device_enable(struct idxd_device *idxd); | 330 | int idxd_device_enable(struct idxd_device *idxd); |
| 331 | int idxd_device_disable(struct idxd_device *idxd); | 331 | int idxd_device_disable(struct idxd_device *idxd); |
| 332 | void idxd_device_reset(struct idxd_device *idxd); | 332 | void idxd_device_reset(struct idxd_device *idxd); |
| @@ -335,7 +335,10 @@ static int idxd_probe(struct idxd_device *idxd) · 334 unmodified lines | |||
| 335 | int rc; | 335 | int rc; |
| 336 | 336 | ||
| 337 | dev_dbg(dev, "%s entered and resetting device\n", __func__); | 337 | dev_dbg(dev, "%s entered and resetting device\n", __func__); |
| 338 | idxd_device_init_reset(idxd); | 338 | rc = idxd_device_init_reset(idxd); |
| 339 | if (rc < 0) | ||
| 340 | return rc; | ||
| 341 | |||
| 339 | dev_dbg(dev, "IDXD reset complete\n"); | 342 | dev_dbg(dev, "IDXD reset complete\n"); |
| 340 | 343 | ||
| 341 | if (IS_ENABLED(CONFIG_INTEL_IDXD_SVM)) { | 344 | if (IS_ENABLED(CONFIG_INTEL_IDXD_SVM)) { |
| @@ -111,19 +111,14 @@ irqreturn_t idxd_irq_handler(int vec, void *data) · 110 unmodified lines | |||
| 111 | return IRQ_WAKE_THREAD; | 111 | return IRQ_WAKE_THREAD; |
| 112 | } | 112 | } |
| 113 | 113 | ||
| 114 | irqreturn_t idxd_misc_thread(int vec, void *data) | 114 | static int process_misc_interrupts(struct idxd_device *idxd, u32 cause) |
| 115 | { | 115 | { |
| 116 | struct idxd_irq_entry *irq_entry = data; | ||
| 117 | struct idxd_device *idxd = irq_entry->idxd; | ||
| 118 | struct device *dev = &idxd->pdev->dev; | 116 | struct device *dev = &idxd->pdev->dev; |
| 119 | union gensts_reg gensts; | 117 | union gensts_reg gensts; |
| 120 | u32 cause, val = 0; | 118 | u32 val = 0; |
| 121 | int i; | 119 | int i; |
| 122 | bool err = false; | 120 | bool err = false; |
| 123 | 121 | ||
| 124 | cause = ioread32(idxd->reg_base + IDXD_INTCAUSE_OFFSET); | ||
| 125 | iowrite32(cause, idxd->reg_base + IDXD_INTCAUSE_OFFSET); | ||
| 126 | |||
| 127 | if (cause & IDXD_INTC_ERR) { | 122 | if (cause & IDXD_INTC_ERR) { |
| 128 | spin_lock_bh(&idxd->dev_lock); | 123 | spin_lock_bh(&idxd->dev_lock); |
| 129 | for (i = 0; i < 4; i++) | 124 | for (i = 0; i < 4; i++) |
| @@ -181,7 +176,7 @@ irqreturn_t idxd_misc_thread(int vec, void *data) · 51 unmodified lines | |||
| 181 | val); | 176 | val); |
| 182 | 177 | ||
| 183 | if (!err) | 178 | if (!err) |
| 184 | goto out; | 179 | return 0; |
| 185 | 180 | ||
| 186 | /* | 181 | /* |
| 187 | * This case should rarely happen and typically is due to software | 182 | * This case should rarely happen and typically is due to software |
| @@ -211,37 +206,58 @@ irqreturn_t idxd_misc_thread(int vec, void *data) · 23 unmodified lines | |||
| 211 | gensts.reset_type == IDXD_DEVICE_RESET_FLR ? | 206 | gensts.reset_type == IDXD_DEVICE_RESET_FLR ? |
| 212 | "FLR" : "system reset"); | 207 | "FLR" : "system reset"); |
| 213 | spin_unlock_bh(&idxd->dev_lock); | 208 | spin_unlock_bh(&idxd->dev_lock); |
| 209 | return -ENXIO; | ||
| 214 | } | 210 | } |
| 215 | } | 211 | } |
| 216 | 212 | ||
| 217 | out: | 213 | return 0; |
| 214 | } | ||
| 215 | |||
| 216 | irqreturn_t idxd_misc_thread(int vec, void *data) | ||
| 217 | { | ||
| 218 | struct idxd_irq_entry *irq_entry = data; | ||
| 219 | struct idxd_device *idxd = irq_entry->idxd; | ||
| 220 | int rc; | ||
| 221 | u32 cause; | ||
| 222 | |||
| 223 | cause = ioread32(idxd->reg_base + IDXD_INTCAUSE_OFFSET); | ||
| 224 | if (cause) | ||
| 225 | iowrite32(cause, idxd->reg_base + IDXD_INTCAUSE_OFFSET); | ||
| 226 | |||
| 227 | while (cause) { | ||
| 228 | rc = process_misc_interrupts(idxd, cause); | ||
| 229 | if (rc < 0) | ||
| 230 | break; | ||
| 231 | cause = ioread32(idxd->reg_base + IDXD_INTCAUSE_OFFSET); | ||
| 232 | if (cause) | ||
| 233 | iowrite32(cause, idxd->reg_base + IDXD_INTCAUSE_OFFSET); | ||
| 234 | } | ||
| 235 | |||
| 218 | idxd_unmask_msix_vector(idxd, irq_entry->id); | 236 | idxd_unmask_msix_vector(idxd, irq_entry->id); |
| 219 | return IRQ_HANDLED; | 237 | return IRQ_HANDLED; |
| 220 | } | 238 | } |
| 221 | 239 | ||
| 222 | static bool process_fault(struct idxd_desc *desc, u64 fault_addr) | 240 | static inline bool match_fault(struct idxd_desc *desc, u64 fault_addr) |
| 223 | { | 241 | { |
| 224 | /* | 242 | /* |
| 225 | * Completion address can be bad as well. Check fault address match for descriptor | 243 | * Completion address can be bad as well. Check fault address match for descriptor |
| 226 | * and completion address. | 244 | * and completion address. |
| 227 | */ | 245 | */ |
| 228 | if ((u64)desc->hw == fault_addr || | 246 | if ((u64)desc->hw == fault_addr || (u64)desc->completion == fault_addr) { |
| 229 | (u64)desc->completion == fault_addr) { | 247 | struct idxd_device *idxd = desc->wq->idxd; |
| 230 | idxd_dma_complete_txd(desc, IDXD_COMPLETE_DEV_FAIL); | 248 | struct device *dev = &idxd->pdev->dev; |
| 249 | |||
| 250 | dev_warn(dev, "desc with fault address: %#llx\n", fault_addr); | ||
| 231 | return true; | 251 | return true; |
| 232 | } | 252 | } |
| 233 | 253 | ||
| 234 | return false; | 254 | return false; |
| 235 | } | 255 | } |
| 236 | 256 | ||
| 237 | static bool complete_desc(struct idxd_desc *desc) | 257 | static inline void complete_desc(struct idxd_desc *desc, enum idxd_complete_type reason) |
| 238 | { | 258 | { |
| 239 | if (desc->completion->status) { | 259 | idxd_dma_complete_txd(desc, reason); |
| 240 | idxd_dma_complete_txd(desc, IDXD_COMPLETE_NORMAL); | 260 | idxd_free_desc(desc->wq, desc); |
| 241 | return true; | ||
| 242 | } | ||
| 243 | |||
| 244 | return false; | ||
| 245 | } | 261 | } |
| 246 | 262 | ||
| 247 | static int irq_process_pending_llist(struct idxd_irq_entry *irq_entry, | 263 | static int irq_process_pending_llist(struct idxd_irq_entry *irq_entry, |
| @@ -251,25 +267,25 @@ static int irq_process_pending_llist(struct idxd_irq_entry *irq_entry, · 3 unmodified lines | |||
| 251 | struct idxd_desc *desc, *t; | 267 | struct idxd_desc *desc, *t; |
| 252 | struct llist_node *head; | 268 | struct llist_node *head; |
| 253 | int queued = 0; | 269 | int queued = 0; |
| 254 | bool completed = false; | ||
| 255 | unsigned long flags; | 270 | unsigned long flags; |
| 271 | enum idxd_complete_type reason; | ||
| 256 | 272 | ||
| 257 | *processed = 0; | 273 | *processed = 0; |
| 258 | head = llist_del_all(&irq_entry->pending_llist); | 274 | head = llist_del_all(&irq_entry->pending_llist); |
| 259 | if (!head) | 275 | if (!head) |
| 260 | goto out; | 276 | goto out; |
| 261 | 277 | ||
| 262 | llist_for_each_entry_safe(desc, t, head, llnode) { | 278 | if (wtype == IRQ_WORK_NORMAL) |
| 263 | if (wtype == IRQ_WORK_NORMAL) | 279 | reason = IDXD_COMPLETE_NORMAL; |
| 264 | completed = complete_desc(desc); | 280 | else |
| 265 | else if (wtype == IRQ_WORK_PROCESS_FAULT) | 281 | reason = IDXD_COMPLETE_DEV_FAIL; |
| 266 | completed = process_fault(desc, data); | ||
| 267 | 282 | ||
| 268 | if (completed) { | 283 | llist_for_each_entry_safe(desc, t, head, llnode) { |
| 269 | idxd_free_desc(desc->wq, desc); | 284 | if (desc->completion->status) { |
| 285 | if ((desc->completion->status & DSA_COMP_STATUS_MASK) != DSA_COMP_SUCCESS) | ||
| 286 | match_fault(desc, data); | ||
| 287 | complete_desc(desc, reason); | ||
| 270 | (*processed)++; | 288 | (*processed)++; |
| 271 | if (wtype == IRQ_WORK_PROCESS_FAULT) | ||
| 272 | break; | ||
| 273 | } else { | 289 | } else { |
| 274 | spin_lock_irqsave(&irq_entry->list_lock, flags); | 290 | spin_lock_irqsave(&irq_entry->list_lock, flags); |
| 275 | list_add_tail(&desc->list, | 291 | list_add_tail(&desc->list, |
| @@ -287,42 +303,46 @@ static int irq_process_work_list(struct idxd_irq_entry *irq_entry, · 11 unmodified lines | |||
| 287 | enum irq_work_type wtype, | 303 | enum irq_work_type wtype, |
| 288 | int *processed, u64 data) | 304 | int *processed, u64 data) |
| 289 | { | 305 | { |
| 290 | struct list_head *node, *next; | ||
| 291 | int queued = 0; | 306 | int queued = 0; |
| 292 | bool completed = false; | ||
| 293 | unsigned long flags; | 307 | unsigned long flags; |
| 308 | LIST_HEAD(flist); | ||
| 309 | struct idxd_desc *desc, *n; | ||
| 310 | enum idxd_complete_type reason; | ||
| 294 | 311 | ||
| 295 | *processed = 0; | 312 | *processed = 0; |
| 296 | spin_lock_irqsave(&irq_entry->list_lock, flags); | 313 | if (wtype == IRQ_WORK_NORMAL) |
| 297 | if (list_empty(&irq_entry->work_list)) | 314 | reason = IDXD_COMPLETE_NORMAL; |
| 298 | goto out; | 315 | else |
| 299 | 316 | reason = IDXD_COMPLETE_DEV_FAIL; | |
| 300 | list_for_each_safe(node, next, &irq_entry->work_list) { | ||
| 301 | struct idxd_desc *desc = | ||
| 302 | container_of(node, struct idxd_desc, list); | ||
| 303 | 317 | ||
| 318 | /* | ||
| 319 | * This lock protects list corruption from access of list outside of the irq handler | ||
| 320 | * thread. | ||
| 321 | */ | ||
| 322 | spin_lock_irqsave(&irq_entry->list_lock, flags); | ||
| 323 | if (list_empty(&irq_entry->work_list)) { | ||
| 304 | spin_unlock_irqrestore(&irq_entry->list_lock, flags); | 324 | spin_unlock_irqrestore(&irq_entry->list_lock, flags); |
| 305 | if (wtype == IRQ_WORK_NORMAL) | 325 | return 0; |
| 306 | completed = complete_desc(desc); | 326 | } |
| 307 | else if (wtype == IRQ_WORK_PROCESS_FAULT) | ||
| 308 | completed = process_fault(desc, data); | ||
| 309 | 327 | ||
| 310 | if (completed) { | 328 | list_for_each_entry_safe(desc, n, &irq_entry->work_list, list) { |
| 311 | spin_lock_irqsave(&irq_entry->list_lock, flags); | 329 | if (desc->completion->status) { |
| 312 | list_del(&desc->list); | 330 | list_del(&desc->list); |
| 313 | spin_unlock_irqrestore(&irq_entry->list_lock, flags); | ||
| 314 | idxd_free_desc(desc->wq, desc); | ||
| 315 | (*processed)++; | 331 | (*processed)++; |
| 316 | if (wtype == IRQ_WORK_PROCESS_FAULT) | 332 | list_add_tail(&desc->list, &flist); |
| 317 | return queued; | ||
| 318 | } else { | 333 | } else { |
| 319 | queued++; | 334 | queued++; |
| 320 | } | 335 | } |
| 321 | spin_lock_irqsave(&irq_entry->list_lock, flags); | ||
| 322 | } | 336 | } |
| 323 | 337 | ||
| 324 | out: | ||
| 325 | spin_unlock_irqrestore(&irq_entry->list_lock, flags); | 338 | spin_unlock_irqrestore(&irq_entry->list_lock, flags); |
| 339 | |||
| 340 | list_for_each_entry(desc, &flist, list) { | ||
| 341 | if ((desc->completion->status & DSA_COMP_STATUS_MASK) != DSA_COMP_SUCCESS) | ||
| 342 | match_fault(desc, data); | ||
| 343 | complete_desc(desc, reason); | ||
| 344 | } | ||
| 345 | |||
| 326 | return queued; | 346 | return queued; |
| 327 | } | 347 | } |
| 328 | 348 | ||
| @@ -434,7 +434,7 @@ int idxd_register_driver(void) · 433 unmodified lines | |||
| 434 | return 0; | 434 | return 0; |
| 435 | 435 | ||
| 436 | drv_fail: | 436 | drv_fail: |
| 437 | for (; i > 0; i--) | 437 | while (--i >= 0) |
| 438 | driver_unregister(&idxd_drvs[i]->drv); | 438 | driver_unregister(&idxd_drvs[i]->drv); |
| 439 | return rc; | 439 | return rc; |
| 440 | } | 440 | } |
| @@ -1840,7 +1840,7 @@ int idxd_register_bus_type(void) · 1399 unmodified lines | |||
| 1840 | return 0; | 1840 | return 0; |
| 1841 | 1841 | ||
| 1842 | bus_err: | 1842 | bus_err: |
| 1843 | for (; i > 0; i--) | 1843 | while (--i >= 0) |
| 1844 | bus_unregister(idxd_bus_types[i]); | 1844 | bus_unregister(idxd_bus_types[i]); |
| 1845 | return rc; | 1845 | return rc; |
| 1846 | } | 1846 | } |
| @@ -1007,6 +1007,7 @@ static int mtk_hsdma_probe(struct platform_device *pdev) · 1006 unmodified lines | |||
| 1007 | return 0; | 1007 | return 0; |
| 1008 | 1008 | ||
| 1009 | err_free: | 1009 | err_free: |
| 1010 | mtk_hsdma_hw_deinit(hsdma); | ||
| 1010 | of_dma_controller_free(pdev->dev.of_node); | 1011 | of_dma_controller_free(pdev->dev.of_node); |
| 1011 | err_unregister: | 1012 | err_unregister: |
| 1012 | dma_async_device_unregister(dd); | 1013 | dma_async_device_unregister(dd); |
| @@ -350,7 +350,7 @@ static int milbeaut_xdmac_probe(struct platform_device *pdev) · 349 unmodified lines | |||
| 350 | 350 | ||
| 351 | ret = dma_async_device_register(ddev); | 351 | ret = dma_async_device_register(ddev); |
| 352 | if (ret) | 352 | if (ret) |
| 353 | return ret; | 353 | goto disable_xdmac; |
| 354 | 354 | ||
| 355 | ret = of_dma_controller_register(dev->of_node, | 355 | ret = of_dma_controller_register(dev->of_node, |
| 356 | of_dma_simple_xlate, mdev); | 356 | of_dma_simple_xlate, mdev); |
| @@ -363,6 +363,8 @@ static int milbeaut_xdmac_probe(struct platform_device *pdev) · 6 unmodified lines | |||
| 363 | 363 | ||
| 364 | unregister_dmac: | 364 | unregister_dmac: |
| 365 | dma_async_device_unregister(ddev); | 365 | dma_async_device_unregister(ddev); |
| 366 | disable_xdmac: | ||
| 367 | disable_xdmac(mdev); | ||
| 366 | return ret; | 368 | return ret; |
| 367 | } | 369 | } |
| 368 | 370 | ||
| @@ -630,7 +630,7 @@ static struct dma_async_tx_descriptor *bam_prep_slave_sg(struct dma_chan *chan, · 629 unmodified lines | |||
| 630 | GFP_NOWAIT); | 630 | GFP_NOWAIT); |
| 631 | 631 | ||
| 632 | if (!async_desc) | 632 | if (!async_desc) |
| 633 | goto err_out; | 633 | return NULL; |
| 634 | 634 | ||
| 635 | if (flags & DMA_PREP_FENCE) | 635 | if (flags & DMA_PREP_FENCE) |
| 636 | async_desc->flags |= DESC_FLAG_NWD; | 636 | async_desc->flags |= DESC_FLAG_NWD; |
| @@ -670,10 +670,6 @@ static struct dma_async_tx_descriptor *bam_prep_slave_sg(struct dma_chan *chan, · 33 unmodified lines | |||
| 670 | } | 670 | } |
| 671 | 671 | ||
| 672 | return vchan_tx_prep(&bchan->vc, &async_desc->vd, flags); | 672 | return vchan_tx_prep(&bchan->vc, &async_desc->vd, flags); |
| 673 | |||
| 674 | err_out: | ||
| 675 | kfree(async_desc); | ||
| 676 | return NULL; | ||
| 677 | } | 673 | } |
| 678 | 674 | ||
| 679 | /** | 675 | /** |
| @@ -1416,7 +1416,7 @@ static int gpi_alloc_ring(struct gpi_ring *ring, u32 elements, · 1415 unmodified lines | |||
| 1416 | len = 1 << bit; | 1416 | len = 1 << bit; |
| 1417 | ring->alloc_size = (len + (len - 1)); | 1417 | ring->alloc_size = (len + (len - 1)); |
| 1418 | dev_dbg(gpii->gpi_dev->dev, | 1418 | dev_dbg(gpii->gpi_dev->dev, |
| 1419 | "#el:%u el_size:%u len:%u actual_len:%llu alloc_size:%lu\n", | 1419 | "#el:%u el_size:%u len:%u actual_len:%llu alloc_size:%zu\n", |
| 1420 | elements, el_size, (elements * el_size), len, | 1420 | elements, el_size, (elements * el_size), len, |
| 1421 | ring->alloc_size); | 1421 | ring->alloc_size); |
| 1422 | 1422 | ||
| @@ -1424,7 +1424,7 @@ static int gpi_alloc_ring(struct gpi_ring *ring, u32 elements, · 1 unmodified line | |||
| 1424 | ring->alloc_size, | 1424 | ring->alloc_size, |
| 1425 | &ring->dma_handle, GFP_KERNEL); | 1425 | &ring->dma_handle, GFP_KERNEL); |
| 1426 | if (!ring->pre_aligned) { | 1426 | if (!ring->pre_aligned) { |
| 1427 | dev_err(gpii->gpi_dev->dev, "could not alloc size:%lu mem for ring\n", | 1427 | dev_err(gpii->gpi_dev->dev, "could not alloc size:%zu mem for ring\n", |
| 1428 | ring->alloc_size); | 1428 | ring->alloc_size); |
| 1429 | return -ENOMEM; | 1429 | return -ENOMEM; |
| 1430 | } | 1430 | } |
| @@ -1444,8 +1444,8 @@ static int gpi_alloc_ring(struct gpi_ring *ring, u32 elements, · 13 unmodified lines | |||
| 1444 | smp_wmb(); | 1444 | smp_wmb(); |
| 1445 | 1445 | ||
| 1446 | dev_dbg(gpii->gpi_dev->dev, | 1446 | dev_dbg(gpii->gpi_dev->dev, |
| 1447 | "phy_pre:0x%0llx phy_alig:0x%0llx len:%u el_size:%u elements:%u\n", | 1447 | "phy_pre:%pad phy_alig:%pa len:%u el_size:%u elements:%u\n", |
| 1448 | ring->dma_handle, ring->phys_addr, ring->len, | 1448 | &ring->dma_handle, &ring->phys_addr, ring->len, |
| 1449 | ring->el_size, ring->elements); | 1449 | ring->el_size, ring->elements); |
| 1450 | 1450 | ||
| 1451 | return 0; | 1451 | return 0; |
| @@ -1948,7 +1948,7 @@ static int gpi_ch_init(struct gchan *gchan) · 496 unmodified lines | |||
| 1948 | return ret; | 1948 | return ret; |
| 1949 | 1949 | ||
| 1950 | error_start_chan: | 1950 | error_start_chan: |
| 1951 | for (i = i - 1; i >= 0; i++) { | 1951 | for (i = i - 1; i >= 0; i--) { |
| 1952 | gpi_stop_chan(&gpii->gchan[i]); | 1952 | gpi_stop_chan(&gpii->gchan[i]); |
| 1953 | gpi_send_cmd(gpii, gchan, GPI_CH_CMD_RESET); | 1953 | gpi_send_cmd(gpii, gchan, GPI_CH_CMD_RESET); |
| 1954 | } | 1954 | } |
| @@ -199,7 +199,7 @@ · 198 unmodified lines | |||
| 199 | #define STM32_MDMA_MAX_CHANNELS 63 | 199 | #define STM32_MDMA_MAX_CHANNELS 63 |
| 200 | #define STM32_MDMA_MAX_REQUESTS 256 | 200 | #define STM32_MDMA_MAX_REQUESTS 256 |
| 201 | #define STM32_MDMA_MAX_BURST 128 | 201 | #define STM32_MDMA_MAX_BURST 128 |
| 202 | #define STM32_MDMA_VERY_HIGH_PRIORITY 0x11 | 202 | #define STM32_MDMA_VERY_HIGH_PRIORITY 0x3 |
| 203 | 203 | ||
| 204 | enum stm32_mdma_trigger_mode { | 204 | enum stm32_mdma_trigger_mode { |
| 205 | STM32_MDMA_BUFFER, | 205 | STM32_MDMA_BUFFER, |
| @@ -2401,7 +2401,8 @@ static int bcdma_alloc_chan_resources(struct dma_chan *chan) · 2400 unmodified lines | |||
| 2401 | dev_err(ud->ddev.dev, | 2401 | dev_err(ud->ddev.dev, |
| 2402 | "Descriptor pool allocation failed\n"); | 2402 | "Descriptor pool allocation failed\n"); |
| 2403 | uc->use_dma_pool = false; | 2403 | uc->use_dma_pool = false; |
| 2404 | return -ENOMEM; | 2404 | ret = -ENOMEM; |
| 2405 | goto err_res_free; | ||
| 2405 | } | 2406 | } |
| 2406 | 2407 | ||
| 2407 | uc->use_dma_pool = true; | 2408 | uc->use_dma_pool = true; |
| @@ -4698,9 +4699,9 @@ static int pktdma_setup_resources(struct udma_dev *ud) · 2290 unmodified lines | |||
| 4698 | ud->tchan_tpl.levels = 1; | 4699 | ud->tchan_tpl.levels = 1; |
| 4699 | } | 4700 | } |
| 4700 | 4701 | ||
| 4701 | ud->tchan_tpl.levels = ud->tchan_tpl.levels; | 4702 | ud->rchan_tpl.levels = ud->tchan_tpl.levels; |
| 4702 | ud->tchan_tpl.start_idx[0] = ud->tchan_tpl.start_idx[0]; | 4703 | ud->rchan_tpl.start_idx[0] = ud->tchan_tpl.start_idx[0]; |
| 4703 | ud->tchan_tpl.start_idx[1] = ud->tchan_tpl.start_idx[1]; | 4704 | ud->rchan_tpl.start_idx[1] = ud->tchan_tpl.start_idx[1]; |
| 4704 | 4705 | ||
| 4705 | ud->tchan_map = devm_kmalloc_array(dev, BITS_TO_LONGS(ud->tchan_cnt), | 4706 | ud->tchan_map = devm_kmalloc_array(dev, BITS_TO_LONGS(ud->tchan_cnt), |
| 4706 | sizeof(unsigned long), GFP_KERNEL); | 4707 | sizeof(unsigned long), GFP_KERNEL); |
| @@ -2781,7 +2781,7 @@ static int xilinx_dma_chan_probe(struct xilinx_dma_device *xdev, · 2780 unmodified lines | |||
| 2781 | has_dre = false; | 2781 | has_dre = false; |
| 2782 | 2782 | ||
| 2783 | if (!has_dre) | 2783 | if (!has_dre) |
| 2784 | xdev->common.copy_align = fls(width - 1); | 2784 | xdev->common.copy_align = (enum dmaengine_alignment)fls(width - 1); |
| 2785 | 2785 | ||
| 2786 | if (of_device_is_compatible(node, "xlnx,axi-vdma-mm2s-channel") || | 2786 | if (of_device_is_compatible(node, "xlnx,axi-vdma-mm2s-channel") || |
| 2787 | of_device_is_compatible(node, "xlnx,axi-dma-mm2s-channel") || | 2787 | of_device_is_compatible(node, "xlnx,axi-dma-mm2s-channel") || |
| @@ -2900,7 +2900,8 @@ static int xilinx_dma_chan_probe(struct xilinx_dma_device *xdev, · 112 unmodified lines | |||
| 2900 | static int xilinx_dma_child_probe(struct xilinx_dma_device *xdev, | 2900 | static int xilinx_dma_child_probe(struct xilinx_dma_device *xdev, |
| 2901 | struct device_node *node) | 2901 | struct device_node *node) |
| 2902 | { | 2902 | { |
| 2903 | int ret, i, nr_channels = 1; | 2903 | int ret, i; |
| 2904 | u32 nr_channels = 1; | ||
| 2904 | 2905 | ||
| 2905 | ret = of_property_read_u32(node, "dma-channels", &nr_channels); | 2906 | ret = of_property_read_u32(node, "dma-channels", &nr_channels); |
| 2906 | if (xdev->dma_config->dmatype == XDMA_TYPE_AXIMCDMA && ret < 0) | 2907 | if (xdev->dma_config->dmatype == XDMA_TYPE_AXIMCDMA && ret < 0) |
| @@ -3112,7 +3113,11 @@ static int xilinx_dma_probe(struct platform_device *pdev) · 205 unmodified lines | |||
| 3112 | } | 3113 | } |
| 3113 | 3114 | ||
| 3114 | /* Register the DMA engine with the core */ | 3115 | /* Register the DMA engine with the core */ |
| 3115 | dma_async_device_register(&xdev->common); | 3116 | err = dma_async_device_register(&xdev->common); |
| 3117 | if (err) { | ||
| 3118 | dev_err(xdev->dev, "failed to register the dma device\n"); | ||
| 3119 | goto error; | ||
| 3120 | } | ||
| 3116 | 3121 | ||
| 3117 | err = of_dma_controller_register(node, of_dma_xilinx_xlate, | 3122 | err = of_dma_controller_register(node, of_dma_xilinx_xlate, |
| 3118 | xdev); | 3123 | xdev); |
| @@ -3,8 +3,9 @@ · 2 unmodified lines | |||
| 3 | * apple-properties.c - EFI device properties on Macs | 3 | * apple-properties.c - EFI device properties on Macs |
| 4 | * Copyright (C) 2016 Lukas Wunner <lukas@wunner.de> | 4 | * Copyright (C) 2016 Lukas Wunner <lukas@wunner.de> |
| 5 | * | 5 | * |
| 6 | * Note, all properties are considered as u8 arrays. | 6 | * Properties are stored either as: |
| 7 | * To get a value of any of them the caller must use device_property_read_u8_array(). | 7 | * u8 arrays which can be retrieved with device_property_read_u8_array() or |
| 8 | * booleans which can be queried with device_property_present(). | ||
| 8 | */ | 9 | */ |
| 9 | 10 | ||
| 10 | #define pr_fmt(fmt) "apple-properties: " fmt | 11 | #define pr_fmt(fmt) "apple-properties: " fmt |
| @@ -88,8 +89,12 @@ static void __init unmarshal_key_value_pairs(struct dev_header *dev_header, · 77 unmodified lines | |||
| 88 | 89 | ||
| 89 | entry_data = ptr + key_len + sizeof(val_len); | 90 | entry_data = ptr + key_len + sizeof(val_len); |
| 90 | entry_len = val_len - sizeof(val_len); | 91 | entry_len = val_len - sizeof(val_len); |
| 91 | entry[i] = PROPERTY_ENTRY_U8_ARRAY_LEN(key, entry_data, | 92 | if (entry_len) |
| 92 | entry_len); | 93 | entry[i] = PROPERTY_ENTRY_U8_ARRAY_LEN(key, entry_data, |
| 94 | entry_len); | ||
| 95 | else | ||
| 96 | entry[i] = PROPERTY_ENTRY_BOOL(key); | ||
| 97 | |||
| 93 | if (dump_properties) { | 98 | if (dump_properties) { |
| 94 | dev_info(dev, "property: %s\n", key); | 99 | dev_info(dev, "property: %s\n", key); |
| 95 | print_hex_dump(KERN_INFO, pr_fmt(), DUMP_PREFIX_OFFSET, | 100 | print_hex_dump(KERN_INFO, pr_fmt(), DUMP_PREFIX_OFFSET, |
| @@ -13,6 +13,7 @@ config IMX_DSP · 12 unmodified lines | |||
| 13 | config IMX_SCU | 13 | config IMX_SCU |
| 14 | bool "IMX SCU Protocol driver" | 14 | bool "IMX SCU Protocol driver" |
| 15 | depends on IMX_MBOX | 15 | depends on IMX_MBOX |
| 16 | select SOC_BUS | ||
| 16 | help | 17 | help |
| 17 | The System Controller Firmware (SCFW) is a low-level system function | 18 | The System Controller Firmware (SCFW) is a low-level system function |
| 18 | which runs on a dedicated Cortex-M core to provide power, clock, and | 19 | which runs on a dedicated Cortex-M core to provide power, clock, and |
| @@ -441,8 +441,9 @@ config GPIO_MXC · 440 unmodified lines | |||
| 441 | select GENERIC_IRQ_CHIP | 441 | select GENERIC_IRQ_CHIP |
| 442 | 442 | ||
| 443 | config GPIO_MXS | 443 | config GPIO_MXS |
| 444 | def_bool y | 444 | bool "Freescale MXS GPIO support" if COMPILE_TEST |
| 445 | depends on ARCH_MXS || COMPILE_TEST | 445 | depends on ARCH_MXS || COMPILE_TEST |
| 446 | default y if ARCH_MXS | ||
| 446 | select GPIO_GENERIC | 447 | select GPIO_GENERIC |
| 447 | select GENERIC_IRQ_CHIP | 448 | select GENERIC_IRQ_CHIP |
| 448 | 449 | ||
| @@ -521,7 +522,8 @@ config GPIO_SAMA5D2_PIOBU · 72 unmodified lines | |||
| 521 | 522 | ||
| 522 | config GPIO_SIFIVE | 523 | config GPIO_SIFIVE |
| 523 | bool "SiFive GPIO support" | 524 | bool "SiFive GPIO support" |
| 524 | depends on OF_GPIO && IRQ_DOMAIN_HIERARCHY | 525 | depends on OF_GPIO |
| 526 | select IRQ_DOMAIN_HIERARCHY | ||
| 525 | select GPIO_GENERIC | 527 | select GPIO_GENERIC |
| 526 | select GPIOLIB_IRQCHIP | 528 | select GPIOLIB_IRQCHIP |
| 527 | select REGMAP_MMIO | 529 | select REGMAP_MMIO |
| @@ -597,6 +599,8 @@ config GPIO_TEGRA · 69 unmodified lines | |||
| 597 | default ARCH_TEGRA | 599 | default ARCH_TEGRA |
| 598 | depends on ARCH_TEGRA || COMPILE_TEST | 600 | depends on ARCH_TEGRA || COMPILE_TEST |
| 599 | depends on OF_GPIO | 601 | depends on OF_GPIO |
| 602 | select GPIOLIB_IRQCHIP | ||
| 603 | select IRQ_DOMAIN_HIERARCHY | ||
| 600 | help | 604 | help |
| 601 | Say yes here to support GPIO pins on NVIDIA Tegra SoCs. | 605 | Say yes here to support GPIO pins on NVIDIA Tegra SoCs. |
| 602 | 606 | ||
| @@ -25,6 +25,9 @@ · 24 unmodified lines | |||
| 25 | /* Maximum value for gpio line identifiers */ | 25 | /* Maximum value for gpio line identifiers */ |
| 26 | #define EP93XX_GPIO_LINE_MAX 63 | 26 | #define EP93XX_GPIO_LINE_MAX 63 |
| 27 | 27 | ||
| 28 | /* Number of GPIO chips in EP93XX */ | ||
| 29 | #define EP93XX_GPIO_CHIP_NUM 8 | ||
| 30 | |||
| 28 | /* Maximum value for irq capable line identifiers */ | 31 | /* Maximum value for irq capable line identifiers */ |
| 29 | #define EP93XX_GPIO_LINE_MAX_IRQ 23 | 32 | #define EP93XX_GPIO_LINE_MAX_IRQ 23 |
| 30 | 33 | ||
| @@ -34,74 +37,75 @@ · 3 unmodified lines | |||
| 34 | */ | 37 | */ |
| 35 | #define EP93XX_GPIO_F_IRQ_BASE 80 | 38 | #define EP93XX_GPIO_F_IRQ_BASE 80 |
| 36 | 39 | ||
| 37 | struct ep93xx_gpio { | 40 | struct ep93xx_gpio_irq_chip { |
| 38 | void __iomem *base; | 41 | struct irq_chip ic; |
| 39 | struct gpio_chip gc[8]; | 42 | u8 irq_offset; |
| 43 | u8 int_unmasked; | ||
| 44 | u8 int_enabled; | ||
| 45 | u8 int_type1; | ||
| 46 | u8 int_type2; | ||
| 47 | u8 int_debounce; | ||
| 40 | }; | 48 | }; |
| 41 | 49 | ||
| 42 | /************************************************************************* | 50 | struct ep93xx_gpio_chip { |
| 43 | * Interrupt handling for EP93xx on-chip GPIOs | 51 | struct gpio_chip gc; |
| 44 | *************************************************************************/ | 52 | struct ep93xx_gpio_irq_chip *eic; |
| 45 | static unsigned char gpio_int_unmasked[3]; | 53 | }; |
| 46 | static unsigned char gpio_int_enabled[3]; | ||
| 47 | static unsigned char gpio_int_type1[3]; | ||
| 48 | static unsigned char gpio_int_type2[3]; | ||
| 49 | static unsigned char gpio_int_debounce[3]; | ||
| 50 | |||
| 51 | /* Port ordering is: A B F */ | ||
| 52 | static const u8 int_type1_register_offset[3] = { 0x90, 0xac, 0x4c }; | ||
| 53 | static const u8 int_type2_register_offset[3] = { 0x94, 0xb0, 0x50 }; | ||
| 54 | static const u8 eoi_register_offset[3] = { 0x98, 0xb4, 0x54 }; | ||
| 55 | static const u8 int_en_register_offset[3] = { 0x9c, 0xb8, 0x58 }; | ||
| 56 | static const u8 int_debounce_register_offset[3] = { 0xa8, 0xc4, 0x64 }; | ||
| 57 | |||
| 58 | static void ep93xx_gpio_update_int_params(struct ep93xx_gpio *epg, unsigned port) | ||
| 59 | { | ||
| 60 | BUG_ON(port > 2); | ||
| 61 | 54 | ||
| 62 | writeb_relaxed(0, epg->base + int_en_register_offset[port]); | 55 | struct ep93xx_gpio { |
| 56 | void __iomem *base; | ||
| 57 | struct ep93xx_gpio_chip gc[EP93XX_GPIO_CHIP_NUM]; | ||
| 58 | }; | ||
| 63 | 59 | ||
| 64 | writeb_relaxed(gpio_int_type2[port], | 60 | #define to_ep93xx_gpio_chip(x) container_of(x, struct ep93xx_gpio_chip, gc) |
| 65 | epg->base + int_type2_register_offset[port]); | ||
| 66 | 61 | ||
| 67 | writeb_relaxed(gpio_int_type1[port], | 62 | static struct ep93xx_gpio_irq_chip *to_ep93xx_gpio_irq_chip(struct gpio_chip *gc) |
| 68 | epg->base + int_type1_register_offset[port]); | 63 | { |
| 64 | struct ep93xx_gpio_chip *egc = to_ep93xx_gpio_chip(gc); | ||
| 69 | 65 | ||
| 70 | writeb(gpio_int_unmasked[port] & gpio_int_enabled[port], | 66 | return egc->eic; |
| 71 | epg->base + int_en_register_offset[port]); | ||
| 72 | } | 67 | } |
| 73 | 68 | ||
| 74 | static int ep93xx_gpio_port(struct gpio_chip *gc) | 69 | /************************************************************************* |
| 70 | * Interrupt handling for EP93xx on-chip GPIOs | ||
| 71 | *************************************************************************/ | ||
| 72 | #define EP93XX_INT_TYPE1_OFFSET 0x00 | ||
| 73 | #define EP93XX_INT_TYPE2_OFFSET 0x04 | ||
| 74 | #define EP93XX_INT_EOI_OFFSET 0x08 | ||
| 75 | #define EP93XX_INT_EN_OFFSET 0x0c | ||
| 76 | #define EP93XX_INT_STATUS_OFFSET 0x10 | ||
| 77 | #define EP93XX_INT_RAW_STATUS_OFFSET 0x14 | ||
| 78 | #define EP93XX_INT_DEBOUNCE_OFFSET 0x18 | ||
| 79 | |||
| 80 | static void ep93xx_gpio_update_int_params(struct ep93xx_gpio *epg, | ||
| 81 | struct ep93xx_gpio_irq_chip *eic) | ||
| 75 | { | 82 | { |
| 76 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); | 83 | writeb_relaxed(0, epg->base + eic->irq_offset + EP93XX_INT_EN_OFFSET); |
| 77 | int port = 0; | ||
| 78 | 84 | ||
| 79 | while (port < ARRAY_SIZE(epg->gc) && gc != &epg->gc[port]) | 85 | writeb_relaxed(eic->int_type2, |
| 80 | port++; | 86 | epg->base + eic->irq_offset + EP93XX_INT_TYPE2_OFFSET); |
| 81 | 87 | ||
| 82 | /* This should not happen but is there as a last safeguard */ | 88 | writeb_relaxed(eic->int_type1, |
| 83 | if (port == ARRAY_SIZE(epg->gc)) { | 89 | epg->base + eic->irq_offset + EP93XX_INT_TYPE1_OFFSET); |
| 84 | pr_crit("can't find the GPIO port\n"); | ||
| 85 | return 0; | ||
| 86 | } | ||
| 87 | 90 | ||
| 88 | return port; | 91 | writeb_relaxed(eic->int_unmasked & eic->int_enabled, |
| 92 | epg->base + eic->irq_offset + EP93XX_INT_EN_OFFSET); | ||
| 89 | } | 93 | } |
| 90 | 94 | ||
| 91 | static void ep93xx_gpio_int_debounce(struct gpio_chip *gc, | 95 | static void ep93xx_gpio_int_debounce(struct gpio_chip *gc, |
| 92 | unsigned int offset, bool enable) | 96 | unsigned int offset, bool enable) |
| 93 | { | 97 | { |
| 94 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); | 98 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); |
| 95 | int port = ep93xx_gpio_port(gc); | 99 | struct ep93xx_gpio_irq_chip *eic = to_ep93xx_gpio_irq_chip(gc); |
| 96 | int port_mask = BIT(offset); | 100 | int port_mask = BIT(offset); |
| 97 | 101 | ||
| 98 | if (enable) | 102 | if (enable) |
| 99 | gpio_int_debounce[port] |= port_mask; | 103 | eic->int_debounce |= port_mask; |
| 100 | else | 104 | else |
| 101 | gpio_int_debounce[port] &= ~port_mask; | 105 | eic->int_debounce &= ~port_mask; |
| 102 | 106 | ||
| 103 | writeb(gpio_int_debounce[port], | 107 | writeb(eic->int_debounce, |
| 104 | epg->base + int_debounce_register_offset[port]); | 108 | epg->base + eic->irq_offset + EP93XX_INT_DEBOUNCE_OFFSET); |
| 105 | } | 109 | } |
| 106 | 110 | ||
| 107 | static void ep93xx_gpio_ab_irq_handler(struct irq_desc *desc) | 111 | static void ep93xx_gpio_ab_irq_handler(struct irq_desc *desc) |
| @@ -122,12 +126,12 @@ static void ep93xx_gpio_ab_irq_handler(struct irq_desc *desc) · 14 unmodified lines | |||
| 122 | */ | 126 | */ |
| 123 | stat = readb(epg->base + EP93XX_GPIO_A_INT_STATUS); | 127 | stat = readb(epg->base + EP93XX_GPIO_A_INT_STATUS); |
| 124 | for_each_set_bit(offset, &stat, 8) | 128 | for_each_set_bit(offset, &stat, 8) |
| 125 | generic_handle_irq(irq_find_mapping(epg->gc[0].irq.domain, | 129 | generic_handle_irq(irq_find_mapping(epg->gc[0].gc.irq.domain, |
| 126 | offset)); | 130 | offset)); |
| 127 | 131 | ||
| 128 | stat = readb(epg->base + EP93XX_GPIO_B_INT_STATUS); | 132 | stat = readb(epg->base + EP93XX_GPIO_B_INT_STATUS); |
| 129 | for_each_set_bit(offset, &stat, 8) | 133 | for_each_set_bit(offset, &stat, 8) |
| 130 | generic_handle_irq(irq_find_mapping(epg->gc[1].irq.domain, | 134 | generic_handle_irq(irq_find_mapping(epg->gc[1].gc.irq.domain, |
| 131 | offset)); | 135 | offset)); |
| 132 | 136 | ||
| 133 | chained_irq_exit(irqchip, desc); | 137 | chained_irq_exit(irqchip, desc); |
| @@ -153,52 +157,52 @@ static void ep93xx_gpio_f_irq_handler(struct irq_desc *desc) · 19 unmodified lines | |||
| 153 | static void ep93xx_gpio_irq_ack(struct irq_data *d) | 157 | static void ep93xx_gpio_irq_ack(struct irq_data *d) |
| 154 | { | 158 | { |
| 155 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); | 159 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); |
| 160 | struct ep93xx_gpio_irq_chip *eic = to_ep93xx_gpio_irq_chip(gc); | ||
| 156 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); | 161 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); |
| 157 | int port = ep93xx_gpio_port(gc); | ||
| 158 | int port_mask = BIT(d->irq & 7); | 162 | int port_mask = BIT(d->irq & 7); |
| 159 | 163 | ||
| 160 | if (irqd_get_trigger_type(d) == IRQ_TYPE_EDGE_BOTH) { | 164 | if (irqd_get_trigger_type(d) == IRQ_TYPE_EDGE_BOTH) { |
| 161 | gpio_int_type2[port] ^= port_mask; /* switch edge direction */ | 165 | eic->int_type2 ^= port_mask; /* switch edge direction */ |
| 162 | ep93xx_gpio_update_int_params(epg, port); | 166 | ep93xx_gpio_update_int_params(epg, eic); |
| 163 | } | 167 | } |
| 164 | 168 | ||
| 165 | writeb(port_mask, epg->base + eoi_register_offset[port]); | 169 | writeb(port_mask, epg->base + eic->irq_offset + EP93XX_INT_EOI_OFFSET); |
| 166 | } | 170 | } |
| 167 | 171 | ||
| 168 | static void ep93xx_gpio_irq_mask_ack(struct irq_data *d) | 172 | static void ep93xx_gpio_irq_mask_ack(struct irq_data *d) |
| 169 | { | 173 | { |
| 170 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); | 174 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); |
| 175 | struct ep93xx_gpio_irq_chip *eic = to_ep93xx_gpio_irq_chip(gc); | ||
| 171 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); | 176 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); |
| 172 | int port = ep93xx_gpio_port(gc); | ||
| 173 | int port_mask = BIT(d->irq & 7); | 177 | int port_mask = BIT(d->irq & 7); |
| 174 | 178 | ||
| 175 | if (irqd_get_trigger_type(d) == IRQ_TYPE_EDGE_BOTH) | 179 | if (irqd_get_trigger_type(d) == IRQ_TYPE_EDGE_BOTH) |
| 176 | gpio_int_type2[port] ^= port_mask; /* switch edge direction */ | 180 | eic->int_type2 ^= port_mask; /* switch edge direction */ |
| 177 | 181 | ||
| 178 | gpio_int_unmasked[port] &= ~port_mask; | 182 | eic->int_unmasked &= ~port_mask; |
| 179 | ep93xx_gpio_update_int_params(epg, port); | 183 | ep93xx_gpio_update_int_params(epg, eic); |
| 180 | 184 | ||
| 181 | writeb(port_mask, epg->base + eoi_register_offset[port]); | 185 | writeb(port_mask, epg->base + eic->irq_offset + EP93XX_INT_EOI_OFFSET); |
| 182 | } | 186 | } |
| 183 | 187 | ||
| 184 | static void ep93xx_gpio_irq_mask(struct irq_data *d) | 188 | static void ep93xx_gpio_irq_mask(struct irq_data *d) |
| 185 | { | 189 | { |
| 186 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); | 190 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); |
| 191 | struct ep93xx_gpio_irq_chip *eic = to_ep93xx_gpio_irq_chip(gc); | ||
| 187 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); | 192 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); |
| 188 | int port = ep93xx_gpio_port(gc); | ||
| 189 | 193 | ||
| 190 | gpio_int_unmasked[port] &= ~BIT(d->irq & 7); | 194 | eic->int_unmasked &= ~BIT(d->irq & 7); |
| 191 | ep93xx_gpio_update_int_params(epg, port); | 195 | ep93xx_gpio_update_int_params(epg, eic); |
| 192 | } | 196 | } |
| 193 | 197 | ||
| 194 | static void ep93xx_gpio_irq_unmask(struct irq_data *d) | 198 | static void ep93xx_gpio_irq_unmask(struct irq_data *d) |
| 195 | { | 199 | { |
| 196 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); | 200 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); |
| 201 | struct ep93xx_gpio_irq_chip *eic = to_ep93xx_gpio_irq_chip(gc); | ||
| 197 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); | 202 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); |
| 198 | int port = ep93xx_gpio_port(gc); | ||
| 199 | 203 | ||
| 200 | gpio_int_unmasked[port] |= BIT(d->irq & 7); | 204 | eic->int_unmasked |= BIT(d->irq & 7); |
| 201 | ep93xx_gpio_update_int_params(epg, port); | 205 | ep93xx_gpio_update_int_params(epg, eic); |
| 202 | } | 206 | } |
| 203 | 207 | ||
| 204 | /* | 208 | /* |
| @@ -209,8 +213,8 @@ static void ep93xx_gpio_irq_unmask(struct irq_data *d) · 4 unmodified lines | |||
| 209 | static int ep93xx_gpio_irq_type(struct irq_data *d, unsigned int type) | 213 | static int ep93xx_gpio_irq_type(struct irq_data *d, unsigned int type) |
| 210 | { | 214 | { |
| 211 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); | 215 | struct gpio_chip *gc = irq_data_get_irq_chip_data(d); |
| 216 | struct ep93xx_gpio_irq_chip *eic = to_ep93xx_gpio_irq_chip(gc); | ||
| 212 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); | 217 | struct ep93xx_gpio *epg = gpiochip_get_data(gc); |
| 213 | int port = ep93xx_gpio_port(gc); | ||
| 214 | int offset = d->irq & 7; | 218 | int offset = d->irq & 7; |
| 215 | int port_mask = BIT(offset); | 219 | int port_mask = BIT(offset); |
| 216 | irq_flow_handler_t handler; | 220 | irq_flow_handler_t handler; |
| @@ -219,32 +223,32 @@ static int ep93xx_gpio_irq_type(struct irq_data *d, unsigned int type) · 2 unmodified lines | |||
| 219 | 223 | ||
| 220 | switch (type) { | 224 | switch (type) { |
| 221 | case IRQ_TYPE_EDGE_RISING: | 225 | case IRQ_TYPE_EDGE_RISING: |
| 222 | gpio_int_type1[port] |= port_mask; | 226 | eic->int_type1 |= port_mask; |
| 223 | gpio_int_type2[port] |= port_mask; | 227 | eic->int_type2 |= port_mask; |
| 224 | handler = handle_edge_irq; | 228 | handler = handle_edge_irq; |
| 225 | break; | 229 | break; |
| 226 | case IRQ_TYPE_EDGE_FALLING: | 230 | case IRQ_TYPE_EDGE_FALLING: |
| 227 | gpio_int_type1[port] |= port_mask; | 231 | eic->int_type1 |= port_mask; |
| 228 | gpio_int_type2[port] &= ~port_mask; | 232 | eic->int_type2 &= ~port_mask; |
| 229 | handler = handle_edge_irq; | 233 | handler = handle_edge_irq; |
| 230 | break; | 234 | break; |
| 231 | case IRQ_TYPE_LEVEL_HIGH: | 235 | case IRQ_TYPE_LEVEL_HIGH: |
| 232 | gpio_int_type1[port] &= ~port_mask; | 236 | eic->int_type1 &= ~port_mask; |
| 233 | gpio_int_type2[port] |= port_mask; | 237 | eic->int_type2 |= port_mask; |
| 234 | handler = handle_level_irq; | 238 | handler = handle_level_irq; |
| 235 | break; | 239 | break; |
| 236 | case IRQ_TYPE_LEVEL_LOW: | 240 | case IRQ_TYPE_LEVEL_LOW: |
| 237 | gpio_int_type1[port] &= ~port_mask; | 241 | eic->int_type1 &= ~port_mask; |
| 238 | gpio_int_type2[port] &= ~port_mask; | 242 | eic->int_type2 &= ~port_mask; |
| 239 | handler = handle_level_irq; | 243 | handler = handle_level_irq; |
| 240 | break; | 244 | break; |
| 241 | case IRQ_TYPE_EDGE_BOTH: | 245 | case IRQ_TYPE_EDGE_BOTH: |
| 242 | gpio_int_type1[port] |= port_mask; | 246 | eic->int_type1 |= port_mask; |
| 243 | /* set initial polarity based on current input level */ | 247 | /* set initial polarity based on current input level */ |
| 244 | if (gc->get(gc, offset)) | 248 | if (gc->get(gc, offset)) |
| 245 | gpio_int_type2[port] &= ~port_mask; /* falling */ | 249 | eic->int_type2 &= ~port_mask; /* falling */ |
| 246 | else | 250 | else |
| 247 | gpio_int_type2[port] |= port_mask; /* rising */ | 251 | eic->int_type2 |= port_mask; /* rising */ |
| 248 | handler = handle_edge_irq; | 252 | handler = handle_edge_irq; |
| 249 | break; | 253 | break; |
| 250 | default: | 254 | default: |
| @@ -253,22 +257,13 @@ static int ep93xx_gpio_irq_type(struct irq_data *d, unsigned int type) · 2 unmodified lines | |||
| 253 | 257 | ||
| 254 | irq_set_handler_locked(d, handler); | 258 | irq_set_handler_locked(d, handler); |
| 255 | 259 | ||
| 256 | gpio_int_enabled[port] |= port_mask; | 260 | eic->int_enabled |= port_mask; |
| 257 | 261 | ||
| 258 | ep93xx_gpio_update_int_params(epg, port); | 262 | ep93xx_gpio_update_int_params(epg, eic); |
| 259 | 263 | ||
| 260 | return 0; | 264 | return 0; |
| 261 | } | 265 | } |
| 262 | 266 | ||
| 263 | static struct irq_chip ep93xx_gpio_irq_chip = { | ||
| 264 | .name = "GPIO", | ||
| 265 | .irq_ack = ep93xx_gpio_irq_ack, | ||
| 266 | .irq_mask_ack = ep93xx_gpio_irq_mask_ack, | ||
| 267 | .irq_mask = ep93xx_gpio_irq_mask, | ||
| 268 | .irq_unmask = ep93xx_gpio_irq_unmask, | ||
| 269 | .irq_set_type = ep93xx_gpio_irq_type, | ||
| 270 | }; | ||
| 271 | |||
| 272 | /************************************************************************* | 267 | /************************************************************************* |
| 273 | * gpiolib interface for EP93xx on-chip GPIOs | 268 | * gpiolib interface for EP93xx on-chip GPIOs |
| 274 | *************************************************************************/ | 269 | *************************************************************************/ |
| @@ -276,17 +271,19 @@ struct ep93xx_gpio_bank { · 1 unmodified line | |||
| 276 | const char *label; | 271 | const char *label; |
| 277 | int data; | 272 | int data; |
| 278 | int dir; | 273 | int dir; |
| 274 | int irq; | ||
| 279 | int base; | 275 | int base; |
| 280 | bool has_irq; | 276 | bool has_irq; |
| 281 | bool has_hierarchical_irq; | 277 | bool has_hierarchical_irq; |
| 282 | unsigned int irq_base; | 278 | unsigned int irq_base; |
| 283 | }; | 279 | }; |
| 284 | 280 | ||
| 285 | #define EP93XX_GPIO_BANK(_label, _data, _dir, _base, _has_irq, _has_hier, _irq_base) \ | 281 | #define EP93XX_GPIO_BANK(_label, _data, _dir, _irq, _base, _has_irq, _has_hier, _irq_base) \ |
| 286 | { \ | 282 | { \ |
| 287 | .label = _label, \ | 283 | .label = _label, \ |
| 288 | .data = _data, \ | 284 | .data = _data, \ |
| 289 | .dir = _dir, \ | 285 | .dir = _dir, \ |
| 286 | .irq = _irq, \ | ||
| 290 | .base = _base, \ | 287 | .base = _base, \ |
| 291 | .has_irq = _has_irq, \ | 288 | .has_irq = _has_irq, \ |
| 292 | .has_hierarchical_irq = _has_hier, \ | 289 | .has_hierarchical_irq = _has_hier, \ |
| @@ -295,16 +292,16 @@ struct ep93xx_gpio_bank { · 2 unmodified lines | |||
| 295 | 292 | ||
| 296 | static struct ep93xx_gpio_bank ep93xx_gpio_banks[] = { | 293 | static struct ep93xx_gpio_bank ep93xx_gpio_banks[] = { |
| 297 | /* Bank A has 8 IRQs */ | 294 | /* Bank A has 8 IRQs */ |
| 298 | EP93XX_GPIO_BANK("A", 0x00, 0x10, 0, true, false, 64), | 295 | EP93XX_GPIO_BANK("A", 0x00, 0x10, 0x90, 0, true, false, 64), |
| 299 | /* Bank B has 8 IRQs */ | 296 | /* Bank B has 8 IRQs */ |
| 300 | EP93XX_GPIO_BANK("B", 0x04, 0x14, 8, true, false, 72), | 297 | EP93XX_GPIO_BANK("B", 0x04, 0x14, 0xac, 8, true, false, 72), |
| 301 | EP93XX_GPIO_BANK("C", 0x08, 0x18, 40, false, false, 0), | 298 | EP93XX_GPIO_BANK("C", 0x08, 0x18, 0x00, 40, false, false, 0), |
| 302 | EP93XX_GPIO_BANK("D", 0x0c, 0x1c, 24, false, false, 0), | 299 | EP93XX_GPIO_BANK("D", 0x0c, 0x1c, 0x00, 24, false, false, 0), |
| 303 | EP93XX_GPIO_BANK("E", 0x20, 0x24, 32, false, false, 0), | 300 | EP93XX_GPIO_BANK("E", 0x20, 0x24, 0x00, 32, false, false, 0), |
| 304 | /* Bank F has 8 IRQs */ | 301 | /* Bank F has 8 IRQs */ |
| 305 | EP93XX_GPIO_BANK("F", 0x30, 0x34, 16, false, true, 0), | 302 | EP93XX_GPIO_BANK("F", 0x30, 0x34, 0x4c, 16, false, true, 0), |
| 306 | EP93XX_GPIO_BANK("G", 0x38, 0x3c, 48, false, false, 0), | 303 | EP93XX_GPIO_BANK("G", 0x38, 0x3c, 0x00, 48, false, false, 0), |
| 307 | EP93XX_GPIO_BANK("H", 0x40, 0x44, 56, false, false, 0), | 304 | EP93XX_GPIO_BANK("H", 0x40, 0x44, 0x00, 56, false, false, 0), |
| 308 | }; | 305 | }; |
| 309 | 306 | ||
| 310 | static int ep93xx_gpio_set_config(struct gpio_chip *gc, unsigned offset, | 307 | static int ep93xx_gpio_set_config(struct gpio_chip *gc, unsigned offset, |
| @@ -326,13 +323,23 @@ static int ep93xx_gpio_f_to_irq(struct gpio_chip *gc, unsigned offset) · 15 unmodified lines | |||
| 326 | return EP93XX_GPIO_F_IRQ_BASE + offset; | 323 | return EP93XX_GPIO_F_IRQ_BASE + offset; |
| 327 | } | 324 | } |
| 328 | 325 | ||
| 329 | static int ep93xx_gpio_add_bank(struct gpio_chip *gc, | 326 | static void ep93xx_init_irq_chip(struct device *dev, struct irq_chip *ic) |
| 327 | { | ||
| 328 | ic->irq_ack = ep93xx_gpio_irq_ack; | ||
| 329 | ic->irq_mask_ack = ep93xx_gpio_irq_mask_ack; | ||
| 330 | ic->irq_mask = ep93xx_gpio_irq_mask; | ||
| 331 | ic->irq_unmask = ep93xx_gpio_irq_unmask; | ||
| 332 | ic->irq_set_type = ep93xx_gpio_irq_type; | ||
| 333 | } | ||
| 334 | |||
| 335 | static int ep93xx_gpio_add_bank(struct ep93xx_gpio_chip *egc, | ||
| 330 | struct platform_device *pdev, | 336 | struct platform_device *pdev, |
| 331 | struct ep93xx_gpio *epg, | 337 | struct ep93xx_gpio *epg, |
| 332 | struct ep93xx_gpio_bank *bank) | 338 | struct ep93xx_gpio_bank *bank) |
| 333 | { | 339 | { |
| 334 | void __iomem *data = epg->base + bank->data; | 340 | void __iomem *data = epg->base + bank->data; |
| 335 | void __iomem *dir = epg->base + bank->dir; | 341 | void __iomem *dir = epg->base + bank->dir; |
| 342 | struct gpio_chip *gc = &egc->gc; | ||
| 336 | struct device *dev = &pdev->dev; | 343 | struct device *dev = &pdev->dev; |
| 337 | struct gpio_irq_chip *girq; | 344 | struct gpio_irq_chip *girq; |
| 338 | int err; | 345 | int err; |
| @@ -346,8 +353,21 @@ static int ep93xx_gpio_add_bank(struct gpio_chip *gc, · 7 unmodified lines | |||
| 346 | 353 | ||
| 347 | girq = &gc->irq; | 354 | girq = &gc->irq; |
| 348 | if (bank->has_irq || bank->has_hierarchical_irq) { | 355 | if (bank->has_irq || bank->has_hierarchical_irq) { |
| 356 | struct irq_chip *ic; | ||
| 357 | |||
| 349 | gc->set_config = ep93xx_gpio_set_config; | 358 | gc->set_config = ep93xx_gpio_set_config; |
| 350 | girq->chip = &ep93xx_gpio_irq_chip; | 359 | egc->eic = devm_kcalloc(dev, 1, |
| 360 | sizeof(*egc->eic), | ||
| 361 | GFP_KERNEL); | ||
| 362 | if (!egc->eic) | ||
| 363 | return -ENOMEM; | ||
| 364 | egc->eic->irq_offset = bank->irq; | ||
| 365 | ic = &egc->eic->ic; | ||
| 366 | ic->name = devm_kasprintf(dev, GFP_KERNEL, "gpio-irq-%s", bank->label); | ||
| 367 | if (!ic->name) | ||
| 368 | return -ENOMEM; | ||
| 369 | ep93xx_init_irq_chip(dev, ic); | ||
| 370 | girq->chip = ic; | ||
| 351 | } | 371 | } |
| 352 | 372 | ||
| 353 | if (bank->has_irq) { | 373 | if (bank->has_irq) { |
| @@ -389,7 +409,7 @@ static int ep93xx_gpio_add_bank(struct gpio_chip *gc, · 35 unmodified lines | |||
| 389 | gpio_irq = EP93XX_GPIO_F_IRQ_BASE + i; | 409 | gpio_irq = EP93XX_GPIO_F_IRQ_BASE + i; |
| 390 | irq_set_chip_data(gpio_irq, &epg->gc[5]); | 410 | irq_set_chip_data(gpio_irq, &epg->gc[5]); |
| 391 | irq_set_chip_and_handler(gpio_irq, | 411 | irq_set_chip_and_handler(gpio_irq, |
| 392 | &ep93xx_gpio_irq_chip, | 412 | girq->chip, |
| 393 | handle_level_irq); | 413 | handle_level_irq); |
| 394 | irq_clear_status_flags(gpio_irq, IRQ_NOREQUEST); | 414 | irq_clear_status_flags(gpio_irq, IRQ_NOREQUEST); |
| 395 | } | 415 | } |
| @@ -415,7 +435,7 @@ static int ep93xx_gpio_probe(struct platform_device *pdev) · 19 unmodified lines | |||
| 415 | return PTR_ERR(epg->base); | 435 | return PTR_ERR(epg->base); |
| 416 | 436 | ||
| 417 | for (i = 0; i < ARRAY_SIZE(ep93xx_gpio_banks); i++) { | 437 | for (i = 0; i < ARRAY_SIZE(ep93xx_gpio_banks); i++) { |
| 418 | struct gpio_chip *gc = &epg->gc[i]; | 438 | struct ep93xx_gpio_chip *gc = &epg->gc[i]; |
| 419 | struct ep93xx_gpio_bank *bank = &ep93xx_gpio_banks[i]; | 439 | struct ep93xx_gpio_bank *bank = &ep93xx_gpio_banks[i]; |
| 420 | 440 | ||
| 421 | if (ep93xx_gpio_add_bank(gc, pdev, epg, bank)) | 441 | if (ep93xx_gpio_add_bank(gc, pdev, epg, bank)) |
| @@ -676,20 +676,17 @@ static void mvebu_pwm_get_state(struct pwm_chip *chip, · 675 unmodified lines | |||
| 676 | else | 676 | else |
| 677 | state->duty_cycle = 1; | 677 | state->duty_cycle = 1; |
| 678 | 678 | ||
| 679 | val = (unsigned long long) u; /* on duration */ | ||
| 679 | regmap_read(mvpwm->regs, mvebu_pwmreg_blink_off_duration(mvpwm), &u); | 680 | regmap_read(mvpwm->regs, mvebu_pwmreg_blink_off_duration(mvpwm), &u); |
| 680 | val = (unsigned long long) u * NSEC_PER_SEC; | 681 | val += (unsigned long long) u; /* period = on + off duration */ |
| 682 | val *= NSEC_PER_SEC; | ||
| 681 | do_div(val, mvpwm->clk_rate); | 683 | do_div(val, mvpwm->clk_rate); |
| 682 | if (val < state->duty_cycle) { | 684 | if (val > UINT_MAX) |
| 685 | state->period = UINT_MAX; | ||
| 686 | else if (val) | ||
| 687 | state->period = val; | ||
| 688 | else | ||
| 683 | state->period = 1; | 689 | state->period = 1; |
| 684 | } else { | ||
| 685 | val -= state->duty_cycle; | ||
| 686 | if (val > UINT_MAX) | ||
| 687 | state->period = UINT_MAX; | ||
| 688 | else if (val) | ||
| 689 | state->period = val; | ||
| 690 | else | ||
| 691 | state->period = 1; | ||
| 692 | } | ||
| 693 | 690 | ||
| 694 | regmap_read(mvchip->regs, GPIO_BLINK_EN_OFF + mvchip->offset, &u); | 691 | regmap_read(mvchip->regs, GPIO_BLINK_EN_OFF + mvchip->offset, &u); |
| 695 | if (u) | 692 | if (u) |
| @@ -776,6 +776,8 @@ static void edge_detector_stop(struct line *line) · 775 unmodified lines | |||
| 776 | cancel_delayed_work_sync(&line->work); | 776 | cancel_delayed_work_sync(&line->work); |
| 777 | WRITE_ONCE(line->sw_debounced, 0); | 777 | WRITE_ONCE(line->sw_debounced, 0); |
| 778 | WRITE_ONCE(line->eflags, 0); | 778 | WRITE_ONCE(line->eflags, 0); |
| 779 | if (line->desc) | ||
| 780 | WRITE_ONCE(line->desc->debounce_period_us, 0); | ||
| 779 | /* do not change line->level - see comment in debounced_value() */ | 781 | /* do not change line->level - see comment in debounced_value() */ |
| 780 | } | 782 | } |
| 781 | 783 | ||
| @@ -1979,6 +1981,21 @@ struct gpio_chardev_data { · 1197 unmodified lines | |||
| 1979 | #endif | 1981 | #endif |
| 1980 | }; | 1982 | }; |
| 1981 | 1983 | ||
| 1984 | static int chipinfo_get(struct gpio_chardev_data *cdev, void __user *ip) | ||
| 1985 | { | ||
| 1986 | struct gpio_device *gdev = cdev->gdev; | ||
| 1987 | struct gpiochip_info chipinfo; | ||
| 1988 | |||
| 1989 | memset(&chipinfo, 0, sizeof(chipinfo)); | ||
| 1990 | |||
| 1991 | strscpy(chipinfo.name, dev_name(&gdev->dev), sizeof(chipinfo.name)); | ||
| 1992 | strscpy(chipinfo.label, gdev->label, sizeof(chipinfo.label)); | ||
| 1993 | chipinfo.lines = gdev->ngpio; | ||
| 1994 | if (copy_to_user(ip, &chipinfo, sizeof(chipinfo))) | ||
| 1995 | return -EFAULT; | ||
| 1996 | return 0; | ||
| 1997 | } | ||
| 1998 | |||
| 1982 | #ifdef CONFIG_GPIO_CDEV_V1 | 1999 | #ifdef CONFIG_GPIO_CDEV_V1 |
| 1983 | /* | 2000 | /* |
| 1984 | * returns 0 if the versions match, else the previously selected ABI version | 2001 | * returns 0 if the versions match, else the previously selected ABI version |
| @@ -1993,6 +2010,41 @@ static int lineinfo_ensure_abi_version(struct gpio_chardev_data *cdata, · 8 unmodified lines | |||
| 1993 | 2010 | ||
| 1994 | return abiv; | 2011 | return abiv; |
| 1995 | } | 2012 | } |
| 2013 | |||
| 2014 | static int lineinfo_get_v1(struct gpio_chardev_data *cdev, void __user *ip, | ||
| 2015 | bool watch) | ||
| 2016 | { | ||
| 2017 | struct gpio_desc *desc; | ||
| 2018 | struct gpioline_info lineinfo; | ||
| 2019 | struct gpio_v2_line_info lineinfo_v2; | ||
| 2020 | |||
| 2021 | if (copy_from_user(&lineinfo, ip, sizeof(lineinfo))) | ||
| 2022 | return -EFAULT; | ||
| 2023 | |||
| 2024 | /* this doubles as a range check on line_offset */ | ||
| 2025 | desc = gpiochip_get_desc(cdev->gdev->chip, lineinfo.line_offset); | ||
| 2026 | if (IS_ERR(desc)) | ||
| 2027 | return PTR_ERR(desc); | ||
| 2028 | |||
| 2029 | if (watch) { | ||
| 2030 | if (lineinfo_ensure_abi_version(cdev, 1)) | ||
| 2031 | return -EPERM; | ||
| 2032 | |||
| 2033 | if (test_and_set_bit(lineinfo.line_offset, cdev->watched_lines)) | ||
| 2034 | return -EBUSY; | ||
| 2035 | } | ||
| 2036 | |||
| 2037 | gpio_desc_to_lineinfo(desc, &lineinfo_v2); | ||
| 2038 | gpio_v2_line_info_to_v1(&lineinfo_v2, &lineinfo); | ||
| 2039 | |||
| 2040 | if (copy_to_user(ip, &lineinfo, sizeof(lineinfo))) { | ||
| 2041 | if (watch) | ||
| 2042 | clear_bit(lineinfo.line_offset, cdev->watched_lines); | ||
| 2043 | return -EFAULT; | ||
| 2044 | } | ||
| 2045 | |||
| 2046 | return 0; | ||
| 2047 | } | ||
| 1996 | #endif | 2048 | #endif |
| 1997 | 2049 | ||
| 1998 | static int lineinfo_get(struct gpio_chardev_data *cdev, void __user *ip, | 2050 | static int lineinfo_get(struct gpio_chardev_data *cdev, void __user *ip, |
| @@ -2030,6 +2082,22 @@ static int lineinfo_get(struct gpio_chardev_data *cdev, void __user *ip, · 31 unmodified lines | |||
| 2030 | return 0; | 2082 | return 0; |
| 2031 | } | 2083 | } |
| 2032 | 2084 | ||
| 2085 | static int lineinfo_unwatch(struct gpio_chardev_data *cdev, void __user *ip) | ||
| 2086 | { | ||
| 2087 | __u32 offset; | ||
| 2088 | |||
| 2089 | if (copy_from_user(&offset, ip, sizeof(offset))) | ||
| 2090 | return -EFAULT; | ||
| 2091 | |||
| 2092 | if (offset >= cdev->gdev->ngpio) | ||
| 2093 | return -EINVAL; | ||
| 2094 | |||
| 2095 | if (!test_and_clear_bit(offset, cdev->watched_lines)) | ||
| 2096 | return -EBUSY; | ||
| 2097 | |||
| 2098 | return 0; | ||
| 2099 | } | ||
| 2100 | |||
| 2033 | /* | 2101 | /* |
| 2034 | * gpio_ioctl() - ioctl handler for the GPIO chardev | 2102 | * gpio_ioctl() - ioctl handler for the GPIO chardev |
| 2035 | */ | 2103 | */ |
| @@ -2037,80 +2105,24 @@ static long gpio_ioctl(struct file *file, unsigned int cmd, unsigned long arg) · 1 unmodified line | |||
| 2037 | { | 2105 | { |
| 2038 | struct gpio_chardev_data *cdev = file->private_data; | 2106 | struct gpio_chardev_data *cdev = file->private_data; |
| 2039 | struct gpio_device *gdev = cdev->gdev; | 2107 | struct gpio_device *gdev = cdev->gdev; |
| 2040 | struct gpio_chip *gc = gdev->chip; | ||
| 2041 | void __user *ip = (void __user *)arg; | 2108 | void __user *ip = (void __user *)arg; |
| 2042 | __u32 offset; | ||
| 2043 | 2109 | ||
| 2044 | /* We fail any subsequent ioctl():s when the chip is gone */ | 2110 | /* We fail any subsequent ioctl():s when the chip is gone */ |
| 2045 | if (!gc) | 2111 | if (!gdev->chip) |
| 2046 | return -ENODEV; | 2112 | return -ENODEV; |
| 2047 | 2113 | ||
| 2048 | /* Fill in the struct and pass to userspace */ | 2114 | /* Fill in the struct and pass to userspace */ |
| 2049 | if (cmd == GPIO_GET_CHIPINFO_IOCTL) { | 2115 | if (cmd == GPIO_GET_CHIPINFO_IOCTL) { |
| 2050 | struct gpiochip_info chipinfo; | 2116 | return chipinfo_get(cdev, ip); |
| 2051 | |||
| 2052 | memset(&chipinfo, 0, sizeof(chipinfo)); | ||
| 2053 | |||
| 2054 | strscpy(chipinfo.name, dev_name(&gdev->dev), | ||
| 2055 | sizeof(chipinfo.name)); | ||
| 2056 | strscpy(chipinfo.label, gdev->label, | ||
| 2057 | sizeof(chipinfo.label)); | ||
| 2058 | chipinfo.lines = gdev->ngpio; | ||
| 2059 | if (copy_to_user(ip, &chipinfo, sizeof(chipinfo))) | ||
| 2060 | return -EFAULT; | ||
| 2061 | return 0; | ||
| 2062 | #ifdef CONFIG_GPIO_CDEV_V1 | 2117 | #ifdef CONFIG_GPIO_CDEV_V1 |
| 2063 | } else if (cmd == GPIO_GET_LINEINFO_IOCTL) { | ||
| 2064 | struct gpio_desc *desc; | ||
| 2065 | struct gpioline_info lineinfo; | ||
| 2066 | struct gpio_v2_line_info lineinfo_v2; | ||
| 2067 | |||
| 2068 | if (copy_from_user(&lineinfo, ip, sizeof(lineinfo))) | ||
| 2069 | return -EFAULT; | ||
| 2070 | |||
| 2071 | /* this doubles as a range check on line_offset */ | ||
| 2072 | desc = gpiochip_get_desc(gc, lineinfo.line_offset); | ||
| 2073 | if (IS_ERR(desc)) | ||
| 2074 | return PTR_ERR(desc); | ||
| 2075 | |||
| 2076 | gpio_desc_to_lineinfo(desc, &lineinfo_v2); | ||
| 2077 | gpio_v2_line_info_to_v1(&lineinfo_v2, &lineinfo); | ||
| 2078 | |||
| 2079 | if (copy_to_user(ip, &lineinfo, sizeof(lineinfo))) | ||
| 2080 | return -EFAULT; | ||
| 2081 | return 0; | ||
| 2082 | } else if (cmd == GPIO_GET_LINEHANDLE_IOCTL) { | 2118 | } else if (cmd == GPIO_GET_LINEHANDLE_IOCTL) { |
| 2083 | return linehandle_create(gdev, ip); | 2119 | return linehandle_create(gdev, ip); |
| 2084 | } else if (cmd == GPIO_GET_LINEEVENT_IOCTL) { | 2120 | } else if (cmd == GPIO_GET_LINEEVENT_IOCTL) { |
| 2085 | return lineevent_create(gdev, ip); | 2121 | return lineevent_create(gdev, ip); |
| 2086 | } else if (cmd == GPIO_GET_LINEINFO_WATCH_IOCTL) { | 2122 | } else if (cmd == GPIO_GET_LINEINFO_IOCTL || |
| 2087 | struct gpio_desc *desc; | 2123 | cmd == GPIO_GET_LINEINFO_WATCH_IOCTL) { |
| 2088 | struct gpioline_info lineinfo; | 2124 | return lineinfo_get_v1(cdev, ip, |
| 2089 | struct gpio_v2_line_info lineinfo_v2; | 2125 | cmd == GPIO_GET_LINEINFO_WATCH_IOCTL); |
| 2090 | |||
| 2091 | if (copy_from_user(&lineinfo, ip, sizeof(lineinfo))) | ||
| 2092 | return -EFAULT; | ||
| 2093 | |||
| 2094 | /* this doubles as a range check on line_offset */ | ||
| 2095 | desc = gpiochip_get_desc(gc, lineinfo.line_offset); | ||
| 2096 | if (IS_ERR(desc)) | ||
| 2097 | return PTR_ERR(desc); | ||
| 2098 | |||
| 2099 | if (lineinfo_ensure_abi_version(cdev, 1)) | ||
| 2100 | return -EPERM; | ||
| 2101 | |||
| 2102 | if (test_and_set_bit(lineinfo.line_offset, cdev->watched_lines)) | ||
| 2103 | return -EBUSY; | ||
| 2104 | |||
| 2105 | gpio_desc_to_lineinfo(desc, &lineinfo_v2); | ||
| 2106 | gpio_v2_line_info_to_v1(&lineinfo_v2, &lineinfo); | ||
| 2107 | |||
| 2108 | if (copy_to_user(ip, &lineinfo, sizeof(lineinfo))) { | ||
| 2109 | clear_bit(lineinfo.line_offset, cdev->watched_lines); | ||
| 2110 | return -EFAULT; | ||
| 2111 | } | ||
| 2112 | |||
| 2113 | return 0; | ||
| 2114 | #endif /* CONFIG_GPIO_CDEV_V1 */ | 2126 | #endif /* CONFIG_GPIO_CDEV_V1 */ |
| 2115 | } else if (cmd == GPIO_V2_GET_LINEINFO_IOCTL || | 2127 | } else if (cmd == GPIO_V2_GET_LINEINFO_IOCTL || |
| 2116 | cmd == GPIO_V2_GET_LINEINFO_WATCH_IOCTL) { | 2128 | cmd == GPIO_V2_GET_LINEINFO_WATCH_IOCTL) { |
| @@ -2119,16 +2131,7 @@ static long gpio_ioctl(struct file *file, unsigned int cmd, unsigned long arg) · 2 unmodified lines | |||
| 2119 | } else if (cmd == GPIO_V2_GET_LINE_IOCTL) { | 2131 | } else if (cmd == GPIO_V2_GET_LINE_IOCTL) { |
| 2120 | return linereq_create(gdev, ip); | 2132 | return linereq_create(gdev, ip); |
| 2121 | } else if (cmd == GPIO_GET_LINEINFO_UNWATCH_IOCTL) { | 2133 | } else if (cmd == GPIO_GET_LINEINFO_UNWATCH_IOCTL) { |
| 2122 | if (copy_from_user(&offset, ip, sizeof(offset))) | 2134 | return lineinfo_unwatch(cdev, ip); |
| 2123 | return -EFAULT; | ||
| 2124 | |||
| 2125 | if (offset >= cdev->gdev->ngpio) | ||
| 2126 | return -EINVAL; | ||
| 2127 | |||
| 2128 | if (!test_and_clear_bit(offset, cdev->watched_lines)) | ||
| 2129 | return -EBUSY; | ||
| 2130 | |||
| 2131 | return 0; | ||
| 2132 | } | 2135 | } |
| 2133 | return -EINVAL; | 2136 | return -EINVAL; |
| 2134 | } | 2137 | } |
| @@ -603,7 +603,11 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data, · 602 unmodified lines | |||
| 603 | ret = gdev->id; | 603 | ret = gdev->id; |
| 604 | goto err_free_gdev; | 604 | goto err_free_gdev; |
| 605 | } | 605 | } |
| 606 | dev_set_name(&gdev->dev, GPIOCHIP_NAME "%d", gdev->id); | 606 | |
| 607 | ret = dev_set_name(&gdev->dev, GPIOCHIP_NAME "%d", gdev->id); | ||
| 608 | if (ret) | ||
| 609 | goto err_free_ida; | ||
| 610 | |||
| 607 | device_initialize(&gdev->dev); | 611 | device_initialize(&gdev->dev); |
| 608 | dev_set_drvdata(&gdev->dev, gdev); | 612 | dev_set_drvdata(&gdev->dev, gdev); |
| 609 | if (gc->parent && gc->parent->driver) | 613 | if (gc->parent && gc->parent->driver) |
| @@ -617,7 +621,7 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data, · 7 unmodified lines | |||
| 617 | gdev->descs = kcalloc(gc->ngpio, sizeof(gdev->descs[0]), GFP_KERNEL); | 621 | gdev->descs = kcalloc(gc->ngpio, sizeof(gdev->descs[0]), GFP_KERNEL); |
| 618 | if (!gdev->descs) { | 622 | if (!gdev->descs) { |
| 619 | ret = -ENOMEM; | 623 | ret = -ENOMEM; |
| 620 | goto err_free_ida; | 624 | goto err_free_dev_name; |
| 621 | } | 625 | } |
| 622 | 626 | ||
| 623 | if (gc->ngpio == 0) { | 627 | if (gc->ngpio == 0) { |
| @@ -768,6 +772,8 @@ err_free_label: · 144 unmodified lines | |||
| 768 | kfree_const(gdev->label); | 772 | kfree_const(gdev->label); |
| 769 | err_free_descs: | 773 | err_free_descs: |
| 770 | kfree(gdev->descs); | 774 | kfree(gdev->descs); |
| 775 | err_free_dev_name: | ||
| 776 | kfree(dev_name(&gdev->dev)); | ||
| 771 | err_free_ida: | 777 | err_free_ida: |
| 772 | ida_free(&gpio_ida, gdev->id); | 778 | ida_free(&gpio_ida, gdev->id); |
| 773 | err_free_gdev: | 779 | err_free_gdev: |
| @@ -1489,6 +1495,9 @@ static int gpiochip_add_irqchip(struct gpio_chip *gc, · 715 unmodified lines | |||
| 1489 | type = IRQ_TYPE_NONE; | 1495 | type = IRQ_TYPE_NONE; |
| 1490 | } | 1496 | } |
| 1491 | 1497 | ||
| 1498 | if (gc->to_irq) | ||
| 1499 | chip_warn(gc, "to_irq is redefined in %s and you shouldn't rely on it\n", __func__); | ||
| 1500 | |||
| 1492 | gc->to_irq = gpiochip_to_irq; | 1501 | gc->to_irq = gpiochip_to_irq; |
| 1493 | gc->irq.default_type = type; | 1502 | gc->irq.default_type = type; |
| 1494 | gc->irq.lock_key = lock_key; | 1503 | gc->irq.lock_key = lock_key; |
| @@ -2548,7 +2557,7 @@ int gpiod_get_array_value_complex(bool raw, bool can_sleep, · 1053 unmodified lines | |||
| 2548 | struct gpio_chip *gc = desc_array[i]->gdev->chip; | 2557 | struct gpio_chip *gc = desc_array[i]->gdev->chip; |
| 2549 | unsigned long fastpath[2 * BITS_TO_LONGS(FASTPATH_NGPIO)]; | 2558 | unsigned long fastpath[2 * BITS_TO_LONGS(FASTPATH_NGPIO)]; |
| 2550 | unsigned long *mask, *bits; | 2559 | unsigned long *mask, *bits; |
| 2551 | int first, j, ret; | 2560 | int first, j; |
| 2552 | 2561 | ||
| 2553 | if (likely(gc->ngpio <= FASTPATH_NGPIO)) { | 2562 | if (likely(gc->ngpio <= FASTPATH_NGPIO)) { |
| 2554 | mask = fastpath; | 2563 | mask = fastpath; |
| @@ -26,6 +26,7 @@ · 25 unmodified lines | |||
| 26 | #include <linux/sched/task.h> | 26 | #include <linux/sched/task.h> |
| 27 | 27 | ||
| 28 | #include "amdgpu_object.h" | 28 | #include "amdgpu_object.h" |
| 29 | #include "amdgpu_gem.h" | ||
| 29 | #include "amdgpu_vm.h" | 30 | #include "amdgpu_vm.h" |
| 30 | #include "amdgpu_amdkfd.h" | 31 | #include "amdgpu_amdkfd.h" |
| 31 | #include "amdgpu_dma_buf.h" | 32 | #include "amdgpu_dma_buf.h" |
| @@ -1152,7 +1153,7 @@ int amdgpu_amdkfd_gpuvm_alloc_memory_of_gpu( · 1120 unmodified lines | |||
| 1152 | struct sg_table *sg = NULL; | 1153 | struct sg_table *sg = NULL; |
| 1153 | uint64_t user_addr = 0; | 1154 | uint64_t user_addr = 0; |
| 1154 | struct amdgpu_bo *bo; | 1155 | struct amdgpu_bo *bo; |
| 1155 | struct amdgpu_bo_param bp; | 1156 | struct drm_gem_object *gobj; |
| 1156 | u32 domain, alloc_domain; | 1157 | u32 domain, alloc_domain; |
| 1157 | u64 alloc_flags; | 1158 | u64 alloc_flags; |
| 1158 | int ret; | 1159 | int ret; |
| @@ -1220,19 +1221,14 @@ int amdgpu_amdkfd_gpuvm_alloc_memory_of_gpu( · 61 unmodified lines | |||
| 1220 | pr_debug("\tcreate BO VA 0x%llx size 0x%llx domain %s\n", | 1221 | pr_debug("\tcreate BO VA 0x%llx size 0x%llx domain %s\n", |
| 1221 | va, size, domain_string(alloc_domain)); | 1222 | va, size, domain_string(alloc_domain)); |
| 1222 | 1223 | ||
| 1223 | memset(&bp, 0, sizeof(bp)); | 1224 | ret = amdgpu_gem_object_create(adev, size, 1, alloc_domain, alloc_flags, |
| 1224 | bp.size = size; | 1225 | bo_type, NULL, &gobj); |
| 1225 | bp.byte_align = 1; | ||
| 1226 | bp.domain = alloc_domain; | ||
| 1227 | bp.flags = alloc_flags; | ||
| 1228 | bp.type = bo_type; | ||
| 1229 | bp.resv = NULL; | ||
| 1230 | ret = amdgpu_bo_create(adev, &bp, &bo); | ||
| 1231 | if (ret) { | 1226 | if (ret) { |
| 1232 | pr_debug("Failed to create BO on domain %s. ret %d\n", | 1227 | pr_debug("Failed to create BO on domain %s. ret %d\n", |
| 1233 | domain_string(alloc_domain), ret); | 1228 | domain_string(alloc_domain), ret); |
| 1234 | goto err_bo_create; | 1229 | goto err_bo_create; |
| 1235 | } | 1230 | } |
| 1231 | bo = gem_to_amdgpu_bo(gobj); | ||
| 1236 | if (bo_type == ttm_bo_type_sg) { | 1232 | if (bo_type == ttm_bo_type_sg) { |
| 1237 | bo->tbo.sg = sg; | 1233 | bo->tbo.sg = sg; |
| 1238 | bo->tbo.ttm->sg = sg; | 1234 | bo->tbo.ttm->sg = sg; |
| @@ -112,6 +112,7 @@ int amdgpu_atomfirmware_allocate_fb_scratch(struct amdgpu_device *adev) · 111 unmodified lines | |||
| 112 | union igp_info { | 112 | union igp_info { |
| 113 | struct atom_integrated_system_info_v1_11 v11; | 113 | struct atom_integrated_system_info_v1_11 v11; |
| 114 | struct atom_integrated_system_info_v1_12 v12; | 114 | struct atom_integrated_system_info_v1_12 v12; |
| 115 | struct atom_integrated_system_info_v2_1 v21; | ||
| 115 | }; | 116 | }; |
| 116 | 117 | ||
| 117 | union umc_info { | 118 | union umc_info { |
| @@ -209,24 +210,42 @@ amdgpu_atomfirmware_get_vram_info(struct amdgpu_device *adev, · 91 unmodified lines | |||
| 209 | if (adev->flags & AMD_IS_APU) { | 210 | if (adev->flags & AMD_IS_APU) { |
| 210 | igp_info = (union igp_info *) | 211 | igp_info = (union igp_info *) |
| 211 | (mode_info->atom_context->bios + data_offset); | 212 | (mode_info->atom_context->bios + data_offset); |
| 212 | switch (crev) { | 213 | switch (frev) { |
| 213 | case 11: | 214 | case 1: |
| 214 | mem_channel_number = igp_info->v11.umachannelnumber; | 215 | switch (crev) { |
| 215 | /* channel width is 64 */ | 216 | case 11: |
| 216 | if (vram_width) | 217 | case 12: |
| 217 | *vram_width = mem_channel_number * 64; | 218 | mem_channel_number = igp_info->v11.umachannelnumber; |
| 218 | mem_type = igp_info->v11.memorytype; | 219 | if (!mem_channel_number) |
| 219 | if (vram_type) | 220 | mem_channel_number = 1; |
| 220 | *vram_type = convert_atom_mem_type_to_vram_type(adev, mem_type); | 221 | /* channel width is 64 */ |
| 222 | if (vram_width) | ||
| 223 | *vram_width = mem_channel_number * 64; | ||
| 224 | mem_type = igp_info->v11.memorytype; | ||
| 225 | if (vram_type) | ||
| 226 | *vram_type = convert_atom_mem_type_to_vram_type(adev, mem_type); | ||
| 227 | break; | ||
| 228 | default: | ||
| 229 | return -EINVAL; | ||
| 230 | } | ||
| 221 | break; | 231 | break; |
| 222 | case 12: | 232 | case 2: |
| 223 | mem_channel_number = igp_info->v12.umachannelnumber; | 233 | switch (crev) { |
| 224 | /* channel width is 64 */ | 234 | case 1: |
| 225 | if (vram_width) | 235 | case 2: |
| 226 | *vram_width = mem_channel_number * 64; | 236 | mem_channel_number = igp_info->v21.umachannelnumber; |
| 227 | mem_type = igp_info->v12.memorytype; | 237 | if (!mem_channel_number) |
| 228 | if (vram_type) | 238 | mem_channel_number = 1; |
| 229 | *vram_type = convert_atom_mem_type_to_vram_type(adev, mem_type); | 239 | /* channel width is 64 */ |
| 240 | if (vram_width) | ||
| 241 | *vram_width = mem_channel_number * 64; | ||
| 242 | mem_type = igp_info->v21.memorytype; | ||
| 243 | if (vram_type) | ||
| 244 | *vram_type = convert_atom_mem_type_to_vram_type(adev, mem_type); | ||
| 245 | break; | ||
| 246 | default: | ||
| 247 | return -EINVAL; | ||
| 248 | } | ||
| 230 | break; | 249 | break; |
| 231 | default: | 250 | default: |
| 232 | return -EINVAL; | 251 | return -EINVAL; |
| @@ -81,7 +81,6 @@ MODULE_FIRMWARE("amdgpu/navi10_gpu_info.bin"); · 80 unmodified lines | |||
| 81 | MODULE_FIRMWARE("amdgpu/navi14_gpu_info.bin"); | 81 | MODULE_FIRMWARE("amdgpu/navi14_gpu_info.bin"); |
| 82 | MODULE_FIRMWARE("amdgpu/navi12_gpu_info.bin"); | 82 | MODULE_FIRMWARE("amdgpu/navi12_gpu_info.bin"); |
| 83 | MODULE_FIRMWARE("amdgpu/vangogh_gpu_info.bin"); | 83 | MODULE_FIRMWARE("amdgpu/vangogh_gpu_info.bin"); |
| 84 | MODULE_FIRMWARE("amdgpu/green_sardine_gpu_info.bin"); | ||
| 85 | 84 | ||
| 86 | #define AMDGPU_RESUME_MS 2000 | 85 | #define AMDGPU_RESUME_MS 2000 |
| 87 | 86 | ||
| @@ -2548,11 +2547,11 @@ static int amdgpu_device_ip_fini(struct amdgpu_device *adev) · 2460 unmodified lines | |||
| 2548 | if (adev->gmc.xgmi.num_physical_nodes > 1) | 2547 | if (adev->gmc.xgmi.num_physical_nodes > 1) |
| 2549 | amdgpu_xgmi_remove_device(adev); | 2548 | amdgpu_xgmi_remove_device(adev); |
| 2550 | 2549 | ||
| 2551 | amdgpu_amdkfd_device_fini(adev); | ||
| 2552 | |||
| 2553 | amdgpu_device_set_pg_state(adev, AMD_PG_STATE_UNGATE); | 2550 | amdgpu_device_set_pg_state(adev, AMD_PG_STATE_UNGATE); |
| 2554 | amdgpu_device_set_cg_state(adev, AMD_CG_STATE_UNGATE); | 2551 | amdgpu_device_set_cg_state(adev, AMD_CG_STATE_UNGATE); |
| 2555 | 2552 | ||
| 2553 | amdgpu_amdkfd_device_fini(adev); | ||
| 2554 | |||
| 2556 | /* need to disable SMC first */ | 2555 | /* need to disable SMC first */ |
| 2557 | for (i = 0; i < adev->num_ip_blocks; i++) { | 2556 | for (i = 0; i < adev->num_ip_blocks; i++) { |
| 2558 | if (!adev->ip_blocks[i].status.hw) | 2557 | if (!adev->ip_blocks[i].status.hw) |
| @@ -3034,7 +3033,7 @@ bool amdgpu_device_asic_has_dc_support(enum amd_asic_type asic_type) · 475 unmodified lines | |||
| 3034 | #endif | 3033 | #endif |
| 3035 | default: | 3034 | default: |
| 3036 | if (amdgpu_dc > 0) | 3035 | if (amdgpu_dc > 0) |
| 3037 | DRM_INFO("Display Core has been requested via kernel parameter " | 3036 | DRM_INFO_ONCE("Display Core has been requested via kernel parameter " |
| 3038 | "but isn't supported by ASIC, ignoring\n"); | 3037 | "but isn't supported by ASIC, ignoring\n"); |
| 3039 | return false; | 3038 | return false; |
| 3040 | } | 3039 | } |
| @@ -926,8 +926,10 @@ amdgpu_display_user_framebuffer_create(struct drm_device *dev, · 925 unmodified lines | |||
| 926 | struct drm_file *file_priv, | 926 | struct drm_file *file_priv, |
| 927 | const struct drm_mode_fb_cmd2 *mode_cmd) | 927 | const struct drm_mode_fb_cmd2 *mode_cmd) |
| 928 | { | 928 | { |
| 929 | struct drm_gem_object *obj; | ||
| 930 | struct amdgpu_framebuffer *amdgpu_fb; | 929 | struct amdgpu_framebuffer *amdgpu_fb; |
| 930 | struct drm_gem_object *obj; | ||
| 931 | struct amdgpu_bo *bo; | ||
| 932 | uint32_t domains; | ||
| 931 | int ret; | 933 | int ret; |
| 932 | 934 | ||
| 933 | obj = drm_gem_object_lookup(file_priv, mode_cmd->handles[0]); | 935 | obj = drm_gem_object_lookup(file_priv, mode_cmd->handles[0]); |
| @@ -938,7 +940,9 @@ amdgpu_display_user_framebuffer_create(struct drm_device *dev, · 4 unmodified lines | |||
| 938 | } | 940 | } |
| 939 | 941 | ||
| 940 | /* Handle is imported dma-buf, so cannot be migrated to VRAM for scanout */ | 942 | /* Handle is imported dma-buf, so cannot be migrated to VRAM for scanout */ |
| 941 | if (obj->import_attach) { | 943 | bo = gem_to_amdgpu_bo(obj); |
| 944 | domains = amdgpu_display_supported_domains(drm_to_adev(dev), bo->flags); | ||
| 945 | if (obj->import_attach && !(domains & AMDGPU_GEM_DOMAIN_GTT)) { | ||
| 942 | drm_dbg_kms(dev, "Cannot create framebuffer from imported dma_buf\n"); | 946 | drm_dbg_kms(dev, "Cannot create framebuffer from imported dma_buf\n"); |
| 943 | return ERR_PTR(-EINVAL); | 947 | return ERR_PTR(-EINVAL); |
| 944 | } | 948 | } |
| @@ -1085,6 +1085,8 @@ static const struct pci_device_id pciidlist[] = { · 1084 unmodified lines | |||
| 1085 | 1085 | ||
| 1086 | /* Renoir */ | 1086 | /* Renoir */ |
| 1087 | {0x1002, 0x1636, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RENOIR|AMD_IS_APU}, | 1087 | {0x1002, 0x1636, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RENOIR|AMD_IS_APU}, |
| 1088 | {0x1002, 0x1638, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RENOIR|AMD_IS_APU}, | ||
| 1089 | {0x1002, 0x164C, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RENOIR|AMD_IS_APU}, | ||
| 1088 | 1090 | ||
| 1089 | /* Navi12 */ | 1091 | /* Navi12 */ |
| 1090 | {0x1002, 0x7360, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_NAVI12}, | 1092 | {0x1002, 0x7360, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_NAVI12}, |
| @@ -269,8 +269,8 @@ int amdgpu_gem_create_ioctl(struct drm_device *dev, void *data, · 268 unmodified lines | |||
| 269 | resv = vm->root.base.bo->tbo.base.resv; | 269 | resv = vm->root.base.bo->tbo.base.resv; |
| 270 | } | 270 | } |
| 271 | 271 | ||
| 272 | retry: | ||
| 273 | initial_domain = (u32)(0xffffffff & args->in.domains); | 272 | initial_domain = (u32)(0xffffffff & args->in.domains); |
| 273 | retry: | ||
| 274 | r = amdgpu_gem_object_create(adev, size, args->in.alignment, | 274 | r = amdgpu_gem_object_create(adev, size, args->in.alignment, |
| 275 | initial_domain, | 275 | initial_domain, |
| 276 | flags, ttm_bo_type_device, resv, &gobj); | 276 | flags, ttm_bo_type_device, resv, &gobj); |
| @@ -897,7 +897,7 @@ int amdgpu_bo_pin_restricted(struct amdgpu_bo *bo, u32 domain, · 896 unmodified lines | |||
| 897 | return -EINVAL; | 897 | return -EINVAL; |
| 898 | 898 | ||
| 899 | /* A shared bo cannot be migrated to VRAM */ | 899 | /* A shared bo cannot be migrated to VRAM */ |
| 900 | if (bo->prime_shared_count) { | 900 | if (bo->prime_shared_count || bo->tbo.base.import_attach) { |
| 901 | if (domain & AMDGPU_GEM_DOMAIN_GTT) | 901 | if (domain & AMDGPU_GEM_DOMAIN_GTT) |
| 902 | domain = AMDGPU_GEM_DOMAIN_GTT; | 902 | domain = AMDGPU_GEM_DOMAIN_GTT; |
| 903 | else | 903 | else |
| @@ -563,7 +563,7 @@ static int psp_asd_load(struct psp_context *psp) · 562 unmodified lines | |||
| 563 | * add workaround to bypass it for sriov now. | 563 | * add workaround to bypass it for sriov now. |
| 564 | * TODO: add version check to make it common | 564 | * TODO: add version check to make it common |
| 565 | */ | 565 | */ |
| 566 | if (amdgpu_sriov_vf(psp->adev) || !psp->asd_fw) | 566 | if (amdgpu_sriov_vf(psp->adev) || !psp->asd_ucode_size) |
| 567 | return 0; | 567 | return 0; |
| 568 | 568 | ||
| 569 | cmd = kzalloc(sizeof(struct psp_gfx_cmd_resp), GFP_KERNEL); | 569 | cmd = kzalloc(sizeof(struct psp_gfx_cmd_resp), GFP_KERNEL); |
| @@ -1315,8 +1315,12 @@ static int psp_hdcp_terminate(struct psp_context *psp) · 745 unmodified lines | |||
| 1315 | if (amdgpu_sriov_vf(psp->adev)) | 1315 | if (amdgpu_sriov_vf(psp->adev)) |
| 1316 | return 0; | 1316 | return 0; |
| 1317 | 1317 | ||
| 1318 | if (!psp->hdcp_context.hdcp_initialized) | 1318 | if (!psp->hdcp_context.hdcp_initialized) { |
| 1319 | return 0; | 1319 | if (psp->hdcp_context.hdcp_shared_buf) |
| 1320 | goto out; | ||
| 1321 | else | ||
| 1322 | return 0; | ||
| 1323 | } | ||
| 1320 | 1324 | ||
| 1321 | ret = psp_hdcp_unload(psp); | 1325 | ret = psp_hdcp_unload(psp); |
| 1322 | if (ret) | 1326 | if (ret) |
| @@ -1324,6 +1328,7 @@ static int psp_hdcp_terminate(struct psp_context *psp) · 1 unmodified line | |||
| 1324 | 1328 | ||
| 1325 | psp->hdcp_context.hdcp_initialized = false; | 1329 | psp->hdcp_context.hdcp_initialized = false; |
| 1326 | 1330 | ||
| 1331 | out: | ||
| 1327 | /* free hdcp shared memory */ | 1332 | /* free hdcp shared memory */ |
| 1328 | amdgpu_bo_free_kernel(&psp->hdcp_context.hdcp_shared_bo, | 1333 | amdgpu_bo_free_kernel(&psp->hdcp_context.hdcp_shared_bo, |
| 1329 | &psp->hdcp_context.hdcp_shared_mc_addr, | 1334 | &psp->hdcp_context.hdcp_shared_mc_addr, |
| @@ -1462,8 +1467,12 @@ static int psp_dtm_terminate(struct psp_context *psp) · 132 unmodified lines | |||
| 1462 | if (amdgpu_sriov_vf(psp->adev)) | 1467 | if (amdgpu_sriov_vf(psp->adev)) |
| 1463 | return 0; | 1468 | return 0; |
| 1464 | 1469 | ||
| 1465 | if (!psp->dtm_context.dtm_initialized) | 1470 | if (!psp->dtm_context.dtm_initialized) { |
| 1466 | return 0; | 1471 | if (psp->dtm_context.dtm_shared_buf) |
| 1472 | goto out; | ||
| 1473 | else | ||
| 1474 | return 0; | ||
| 1475 | } | ||
| 1467 | 1476 | ||
| 1468 | ret = psp_dtm_unload(psp); | 1477 | ret = psp_dtm_unload(psp); |
| 1469 | if (ret) | 1478 | if (ret) |
| @@ -1471,6 +1480,7 @@ static int psp_dtm_terminate(struct psp_context *psp) · 1 unmodified line | |||
| 1471 | 1480 | ||
| 1472 | psp->dtm_context.dtm_initialized = false; | 1481 | psp->dtm_context.dtm_initialized = false; |
| 1473 | 1482 | ||
| 1483 | out: | ||
| 1474 | /* free hdcp shared memory */ | 1484 | /* free hdcp shared memory */ |
| 1475 | amdgpu_bo_free_kernel(&psp->dtm_context.dtm_shared_bo, | 1485 | amdgpu_bo_free_kernel(&psp->dtm_context.dtm_shared_bo, |
| 1476 | &psp->dtm_context.dtm_shared_mc_addr, | 1486 | &psp->dtm_context.dtm_shared_mc_addr, |
| @@ -2589,11 +2599,10 @@ static int parse_ta_bin_descriptor(struct psp_context *psp, · 1112 unmodified lines | |||
| 2589 | 2599 | ||
| 2590 | switch (desc->fw_type) { | 2600 | switch (desc->fw_type) { |
| 2591 | case TA_FW_TYPE_PSP_ASD: | 2601 | case TA_FW_TYPE_PSP_ASD: |
| 2592 | psp->asd_fw_version = le32_to_cpu(desc->fw_version); | 2602 | psp->asd_fw_version = le32_to_cpu(desc->fw_version); |
| 2593 | psp->asd_feature_version = le32_to_cpu(desc->fw_version); | 2603 | psp->asd_feature_version = le32_to_cpu(desc->fw_version); |
| 2594 | psp->asd_ucode_size = le32_to_cpu(desc->size_bytes); | 2604 | psp->asd_ucode_size = le32_to_cpu(desc->size_bytes); |
| 2595 | psp->asd_start_addr = ucode_start_addr; | 2605 | psp->asd_start_addr = ucode_start_addr; |
| 2596 | psp->asd_fw = psp->ta_fw; | ||
| 2597 | break; | 2606 | break; |
| 2598 | case TA_FW_TYPE_PSP_XGMI: | 2607 | case TA_FW_TYPE_PSP_XGMI: |
| 2599 | psp->ta_xgmi_ucode_version = le32_to_cpu(desc->fw_version); | 2608 | psp->ta_xgmi_ucode_version = le32_to_cpu(desc->fw_version); |
| @@ -1518,7 +1518,7 @@ static int amdgpu_ras_badpages_read(struct amdgpu_device *adev, · 1517 unmodified lines | |||
| 1518 | struct amdgpu_ras *con = amdgpu_ras_get_context(adev); | 1518 | struct amdgpu_ras *con = amdgpu_ras_get_context(adev); |
| 1519 | struct ras_err_handler_data *data; | 1519 | struct ras_err_handler_data *data; |
| 1520 | int i = 0; | 1520 | int i = 0; |
| 1521 | int ret = 0; | 1521 | int ret = 0, status; |
| 1522 | 1522 | ||
| 1523 | if (!con || !con->eh_data || !bps || !count) | 1523 | if (!con || !con->eh_data || !bps || !count) |
| 1524 | return -EINVAL; | 1524 | return -EINVAL; |
| @@ -1543,12 +1543,12 @@ static int amdgpu_ras_badpages_read(struct amdgpu_device *adev, · 18 unmodified lines | |||
| 1543 | .size = AMDGPU_GPU_PAGE_SIZE, | 1543 | .size = AMDGPU_GPU_PAGE_SIZE, |
| 1544 | .flags = AMDGPU_RAS_RETIRE_PAGE_RESERVED, | 1544 | .flags = AMDGPU_RAS_RETIRE_PAGE_RESERVED, |
| 1545 | }; | 1545 | }; |
| 1546 | ret = amdgpu_vram_mgr_query_page_status( | 1546 | status = amdgpu_vram_mgr_query_page_status( |
| 1547 | ttm_manager_type(&adev->mman.bdev, TTM_PL_VRAM), | 1547 | ttm_manager_type(&adev->mman.bdev, TTM_PL_VRAM), |
| 1548 | data->bps[i].retired_page); | 1548 | data->bps[i].retired_page); |
| 1549 | if (ret == -EBUSY) | 1549 | if (status == -EBUSY) |
| 1550 | (*bps)[i].flags = AMDGPU_RAS_RETIRE_PAGE_PENDING; | 1550 | (*bps)[i].flags = AMDGPU_RAS_RETIRE_PAGE_PENDING; |
| 1551 | else if (ret == -ENOENT) | 1551 | else if (status == -ENOENT) |
| 1552 | (*bps)[i].flags = AMDGPU_RAS_RETIRE_PAGE_FAULT; | 1552 | (*bps)[i].flags = AMDGPU_RAS_RETIRE_PAGE_FAULT; |
| 1553 | } | 1553 | } |
| 1554 | 1554 | ||
| @@ -30,6 +30,7 @@ · 29 unmodified lines | |||
| 30 | #define EEPROM_I2C_TARGET_ADDR_VEGA20 0xA0 | 30 | #define EEPROM_I2C_TARGET_ADDR_VEGA20 0xA0 |
| 31 | #define EEPROM_I2C_TARGET_ADDR_ARCTURUS 0xA8 | 31 | #define EEPROM_I2C_TARGET_ADDR_ARCTURUS 0xA8 |
| 32 | #define EEPROM_I2C_TARGET_ADDR_ARCTURUS_D342 0xA0 | 32 | #define EEPROM_I2C_TARGET_ADDR_ARCTURUS_D342 0xA0 |
| 33 | #define EEPROM_I2C_TARGET_ADDR_SIENNA_CICHLID 0xA0 | ||
| 33 | 34 | ||
| 34 | /* | 35 | /* |
| 35 | * The 2 macros bellow represent the actual size in bytes that | 36 | * The 2 macros bellow represent the actual size in bytes that |
| @@ -62,7 +63,8 @@ · 26 unmodified lines | |||
| 62 | static bool __is_ras_eeprom_supported(struct amdgpu_device *adev) | 63 | static bool __is_ras_eeprom_supported(struct amdgpu_device *adev) |
| 63 | { | 64 | { |
| 64 | if ((adev->asic_type == CHIP_VEGA20) || | 65 | if ((adev->asic_type == CHIP_VEGA20) || |
| 65 | (adev->asic_type == CHIP_ARCTURUS)) | 66 | (adev->asic_type == CHIP_ARCTURUS) || |
| 67 | (adev->asic_type == CHIP_SIENNA_CICHLID)) | ||
| 66 | return true; | 68 | return true; |
| 67 | 69 | ||
| 68 | return false; | 70 | return false; |
| @@ -100,6 +102,10 @@ static bool __get_eeprom_i2c_addr(struct amdgpu_device *adev, · 31 unmodified lines | |||
| 100 | case CHIP_ARCTURUS: | 102 | case CHIP_ARCTURUS: |
| 101 | return __get_eeprom_i2c_addr_arct(adev, i2c_addr); | 103 | return __get_eeprom_i2c_addr_arct(adev, i2c_addr); |
| 102 | 104 | ||
| 105 | case CHIP_SIENNA_CICHLID: | ||
| 106 | *i2c_addr = EEPROM_I2C_TARGET_ADDR_SIENNA_CICHLID; | ||
| 107 | break; | ||
| 108 | |||
| 103 | default: | 109 | default: |
| 104 | return false; | 110 | return false; |
| 105 | } | 111 | } |
| @@ -99,6 +99,14 @@ · 98 unmodified lines | |||
| 99 | #define mmGCR_GENERAL_CNTL_Sienna_Cichlid 0x1580 | 99 | #define mmGCR_GENERAL_CNTL_Sienna_Cichlid 0x1580 |
| 100 | #define mmGCR_GENERAL_CNTL_Sienna_Cichlid_BASE_IDX 0 | 100 | #define mmGCR_GENERAL_CNTL_Sienna_Cichlid_BASE_IDX 0 |
| 101 | 101 | ||
| 102 | #define mmCGTS_TCC_DISABLE_Vangogh 0x5006 | ||
| 103 | #define mmCGTS_TCC_DISABLE_Vangogh_BASE_IDX 1 | ||
| 104 | #define mmCGTS_USER_TCC_DISABLE_Vangogh 0x5007 | ||
| 105 | #define mmCGTS_USER_TCC_DISABLE_Vangogh_BASE_IDX 1 | ||
| 106 | #define mmGOLDEN_TSC_COUNT_UPPER_Vangogh 0x0025 | ||
| 107 | #define mmGOLDEN_TSC_COUNT_UPPER_Vangogh_BASE_IDX 1 | ||
| 108 | #define mmGOLDEN_TSC_COUNT_LOWER_Vangogh 0x0026 | ||
| 109 | #define mmGOLDEN_TSC_COUNT_LOWER_Vangogh_BASE_IDX 1 | ||
| 102 | #define mmSPI_CONFIG_CNTL_1_Vangogh 0x2441 | 110 | #define mmSPI_CONFIG_CNTL_1_Vangogh 0x2441 |
| 103 | #define mmSPI_CONFIG_CNTL_1_Vangogh_BASE_IDX 1 | 111 | #define mmSPI_CONFIG_CNTL_1_Vangogh_BASE_IDX 1 |
| 104 | #define mmVGT_TF_MEMORY_BASE_HI_Vangogh 0x2261 | 112 | #define mmVGT_TF_MEMORY_BASE_HI_Vangogh 0x2261 |
| @@ -115,6 +123,8 @@ · 10 unmodified lines | |||
| 115 | #define mmVGT_ESGS_RING_SIZE_Vangogh_BASE_IDX 1 | 123 | #define mmVGT_ESGS_RING_SIZE_Vangogh_BASE_IDX 1 |
| 116 | #define mmSPI_CONFIG_CNTL_Vangogh 0x2440 | 124 | #define mmSPI_CONFIG_CNTL_Vangogh 0x2440 |
| 117 | #define mmSPI_CONFIG_CNTL_Vangogh_BASE_IDX 1 | 125 | #define mmSPI_CONFIG_CNTL_Vangogh_BASE_IDX 1 |
| 126 | #define mmGCR_GENERAL_CNTL_Vangogh 0x1580 | ||
| 127 | #define mmGCR_GENERAL_CNTL_Vangogh_BASE_IDX 0 | ||
| 118 | 128 | ||
| 119 | #define mmCP_HYP_PFP_UCODE_ADDR 0x5814 | 129 | #define mmCP_HYP_PFP_UCODE_ADDR 0x5814 |
| 120 | #define mmCP_HYP_PFP_UCODE_ADDR_BASE_IDX 1 | 130 | #define mmCP_HYP_PFP_UCODE_ADDR_BASE_IDX 1 |
| @@ -160,6 +170,9 @@ · 39 unmodified lines | |||
| 160 | #define mmGCVM_L2_CGTT_CLK_CTRL_Sienna_Cichlid 0x15db | 170 | #define mmGCVM_L2_CGTT_CLK_CTRL_Sienna_Cichlid 0x15db |
| 161 | #define mmGCVM_L2_CGTT_CLK_CTRL_Sienna_Cichlid_BASE_IDX 0 | 171 | #define mmGCVM_L2_CGTT_CLK_CTRL_Sienna_Cichlid_BASE_IDX 0 |
| 162 | 172 | ||
| 173 | #define mmGC_THROTTLE_CTRL_Sienna_Cichlid 0x2030 | ||
| 174 | #define mmGC_THROTTLE_CTRL_Sienna_Cichlid_BASE_IDX 0 | ||
| 175 | |||
| 163 | MODULE_FIRMWARE("amdgpu/navi10_ce.bin"); | 176 | MODULE_FIRMWARE("amdgpu/navi10_ce.bin"); |
| 164 | MODULE_FIRMWARE("amdgpu/navi10_pfp.bin"); | 177 | MODULE_FIRMWARE("amdgpu/navi10_pfp.bin"); |
| 165 | MODULE_FIRMWARE("amdgpu/navi10_me.bin"); | 178 | MODULE_FIRMWARE("amdgpu/navi10_me.bin"); |
| @@ -3237,7 +3250,7 @@ static const struct soc15_reg_golden golden_settings_gc_10_3_vangogh[] = · 3071 unmodified lines | |||
| 3237 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmDB_DEBUG4, 0xffffffff, 0x00800000), | 3250 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmDB_DEBUG4, 0xffffffff, 0x00800000), |
| 3238 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmDB_EXCEPTION_CONTROL, 0x7fff0f1f, 0x00b80000), | 3251 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmDB_EXCEPTION_CONTROL, 0x7fff0f1f, 0x00b80000), |
| 3239 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGB_ADDR_CONFIG, 0x0c1807ff, 0x00000142), | 3252 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGB_ADDR_CONFIG, 0x0c1807ff, 0x00000142), |
| 3240 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGCR_GENERAL_CNTL, 0x1ff1ffff, 0x00000500), | 3253 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGCR_GENERAL_CNTL_Vangogh, 0x1ff1ffff, 0x00000500), |
| 3241 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGL1_PIPE_STEER, 0x000000ff, 0x000000e4), | 3254 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGL1_PIPE_STEER, 0x000000ff, 0x000000e4), |
| 3242 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGL2_PIPE_STEER_0, 0x77777777, 0x32103210), | 3255 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGL2_PIPE_STEER_0, 0x77777777, 0x32103210), |
| 3243 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGL2_PIPE_STEER_1, 0x77777777, 0x32103210), | 3256 | SOC15_REG_GOLDEN_VALUE(GC, 0, mmGL2_PIPE_STEER_1, 0x77777777, 0x32103210), |
| @@ -3324,6 +3337,7 @@ static void gfx_v10_0_ring_emit_de_meta(struct amdgpu_ring *ring, bool resume); · 80 unmodified lines | |||
| 3324 | static void gfx_v10_0_ring_emit_frame_cntl(struct amdgpu_ring *ring, bool start, bool secure); | 3337 | static void gfx_v10_0_ring_emit_frame_cntl(struct amdgpu_ring *ring, bool start, bool secure); |
| 3325 | static u32 gfx_v10_3_get_disabled_sa(struct amdgpu_device *adev); | 3338 | static u32 gfx_v10_3_get_disabled_sa(struct amdgpu_device *adev); |
| 3326 | static void gfx_v10_3_program_pbb_mode(struct amdgpu_device *adev); | 3339 | static void gfx_v10_3_program_pbb_mode(struct amdgpu_device *adev); |
| 3340 | static void gfx_v10_3_set_power_brake_sequence(struct amdgpu_device *adev); | ||
| 3327 | 3341 | ||
| 3328 | static void gfx10_kiq_set_resources(struct amdgpu_ring *kiq_ring, uint64_t queue_mask) | 3342 | static void gfx10_kiq_set_resources(struct amdgpu_ring *kiq_ring, uint64_t queue_mask) |
| 3329 | { | 3343 | { |
| @@ -4926,8 +4940,18 @@ static void gfx_v10_0_tcp_harvest(struct amdgpu_device *adev) · 1596 unmodified lines | |||
| 4926 | static void gfx_v10_0_get_tcc_info(struct amdgpu_device *adev) | 4940 | static void gfx_v10_0_get_tcc_info(struct amdgpu_device *adev) |
| 4927 | { | 4941 | { |
| 4928 | /* TCCs are global (not instanced). */ | 4942 | /* TCCs are global (not instanced). */ |
| 4929 | uint32_t tcc_disable = RREG32_SOC15(GC, 0, mmCGTS_TCC_DISABLE) | | 4943 | uint32_t tcc_disable; |
| 4930 | RREG32_SOC15(GC, 0, mmCGTS_USER_TCC_DISABLE); | 4944 | |
| 4945 | switch (adev->asic_type) { | ||
| 4946 | case CHIP_VANGOGH: | ||
| 4947 | tcc_disable = RREG32_SOC15(GC, 0, mmCGTS_TCC_DISABLE_Vangogh) | | ||
| 4948 | RREG32_SOC15(GC, 0, mmCGTS_USER_TCC_DISABLE_Vangogh); | ||
| 4949 | break; | ||
| 4950 | default: | ||
| 4951 | tcc_disable = RREG32_SOC15(GC, 0, mmCGTS_TCC_DISABLE) | | ||
| 4952 | RREG32_SOC15(GC, 0, mmCGTS_USER_TCC_DISABLE); | ||
| 4953 | break; | ||
| 4954 | } | ||
| 4931 | 4955 | ||
| 4932 | adev->gfx.config.tcc_disabled_mask = | 4956 | adev->gfx.config.tcc_disabled_mask = |
| 4933 | REG_GET_FIELD(tcc_disable, CGTS_TCC_DISABLE, TCC_DISABLE) | | 4957 | REG_GET_FIELD(tcc_disable, CGTS_TCC_DISABLE, TCC_DISABLE) | |
| @@ -7192,6 +7216,9 @@ static int gfx_v10_0_hw_init(void *handle) · 2258 unmodified lines | |||
| 7192 | if (adev->asic_type == CHIP_SIENNA_CICHLID) | 7216 | if (adev->asic_type == CHIP_SIENNA_CICHLID) |
| 7193 | gfx_v10_3_program_pbb_mode(adev); | 7217 | gfx_v10_3_program_pbb_mode(adev); |
| 7194 | 7218 | ||
| 7219 | if (adev->asic_type >= CHIP_SIENNA_CICHLID) | ||
| 7220 | gfx_v10_3_set_power_brake_sequence(adev); | ||
| 7221 | |||
| 7195 | return r; | 7222 | return r; |
| 7196 | } | 7223 | } |
| 7197 | 7224 | ||
| @@ -7377,8 +7404,16 @@ static uint64_t gfx_v10_0_get_gpu_clock_counter(struct amdgpu_device *adev) · 179 unmodified lines | |||
| 7377 | 7404 | ||
| 7378 | amdgpu_gfx_off_ctrl(adev, false); | 7405 | amdgpu_gfx_off_ctrl(adev, false); |
| 7379 | mutex_lock(&adev->gfx.gpu_clock_mutex); | 7406 | mutex_lock(&adev->gfx.gpu_clock_mutex); |
| 7380 | clock = (uint64_t)RREG32_SOC15(SMUIO, 0, mmGOLDEN_TSC_COUNT_LOWER) | | 7407 | switch (adev->asic_type) { |
| 7381 | ((uint64_t)RREG32_SOC15(SMUIO, 0, mmGOLDEN_TSC_COUNT_UPPER) << 32ULL); | 7408 | case CHIP_VANGOGH: |
| 7409 | clock = (uint64_t)RREG32_SOC15(SMUIO, 0, mmGOLDEN_TSC_COUNT_LOWER_Vangogh) | | ||
| 7410 | ((uint64_t)RREG32_SOC15(SMUIO, 0, mmGOLDEN_TSC_COUNT_UPPER_Vangogh) << 32ULL); | ||
| 7411 | break; | ||
| 7412 | default: | ||
| 7413 | clock = (uint64_t)RREG32_SOC15(SMUIO, 0, mmGOLDEN_TSC_COUNT_LOWER) | | ||
| 7414 | ((uint64_t)RREG32_SOC15(SMUIO, 0, mmGOLDEN_TSC_COUNT_UPPER) << 32ULL); | ||
| 7415 | break; | ||
| 7416 | } | ||
| 7382 | mutex_unlock(&adev->gfx.gpu_clock_mutex); | 7417 | mutex_unlock(&adev->gfx.gpu_clock_mutex); |
| 7383 | amdgpu_gfx_off_ctrl(adev, true); | 7418 | amdgpu_gfx_off_ctrl(adev, true); |
| 7384 | return clock; | 7419 | return clock; |
| @@ -9169,6 +9204,31 @@ static void gfx_v10_3_program_pbb_mode(struct amdgpu_device *adev) · 1784 unmodified lines | |||
| 9169 | } | 9204 | } |
| 9170 | } | 9205 | } |
| 9171 | 9206 | ||
| 9207 | static void gfx_v10_3_set_power_brake_sequence(struct amdgpu_device *adev) | ||
| 9208 | { | ||
| 9209 | WREG32_SOC15(GC, 0, mmGRBM_GFX_INDEX, | ||
| 9210 | (0x1 << GRBM_GFX_INDEX__SA_BROADCAST_WRITES__SHIFT) | | ||
| 9211 | (0x1 << GRBM_GFX_INDEX__INSTANCE_BROADCAST_WRITES__SHIFT) | | ||
| 9212 | (0x1 << GRBM_GFX_INDEX__SE_BROADCAST_WRITES__SHIFT)); | ||
| 9213 | |||
| 9214 | WREG32_SOC15(GC, 0, mmGC_CAC_IND_INDEX, ixPWRBRK_STALL_PATTERN_CTRL); | ||
| 9215 | WREG32_SOC15(GC, 0, mmGC_CAC_IND_DATA, | ||
| 9216 | (0x1 << PWRBRK_STALL_PATTERN_CTRL__PWRBRK_STEP_INTERVAL__SHIFT) | | ||
| 9217 | (0x12 << PWRBRK_STALL_PATTERN_CTRL__PWRBRK_BEGIN_STEP__SHIFT) | | ||
| 9218 | (0x13 << PWRBRK_STALL_PATTERN_CTRL__PWRBRK_END_STEP__SHIFT) | | ||
| 9219 | (0xf << PWRBRK_STALL_PATTERN_CTRL__PWRBRK_THROTTLE_PATTERN_BIT_NUMS__SHIFT)); | ||
| 9220 | |||
| 9221 | WREG32_SOC15(GC, 0, mmGC_THROTTLE_CTRL_Sienna_Cichlid, | ||
| 9222 | (0x1 << GC_THROTTLE_CTRL__PWRBRK_STALL_EN__SHIFT) | | ||
| 9223 | (0x1 << GC_THROTTLE_CTRL__PATTERN_MODE__SHIFT) | | ||
| 9224 | (0x5 << GC_THROTTLE_CTRL__RELEASE_STEP_INTERVAL__SHIFT)); | ||
| 9225 | |||
| 9226 | WREG32_SOC15(GC, 0, mmDIDT_IND_INDEX, ixDIDT_SQ_THROTTLE_CTRL); | ||
| 9227 | |||
| 9228 | WREG32_SOC15(GC, 0, mmDIDT_IND_DATA, | ||
| 9229 | (0x1 << DIDT_SQ_THROTTLE_CTRL__PWRBRK_STALL_EN__SHIFT)); | ||
| 9230 | } | ||
| 9231 | |||
| 9172 | const struct amdgpu_ip_block_version gfx_v10_0_ip_block = | 9232 | const struct amdgpu_ip_block_version gfx_v10_0_ip_block = |
| 9173 | { | 9233 | { |
| 9174 | .type = AMD_IP_BLOCK_TYPE_GFX, | 9234 | .type = AMD_IP_BLOCK_TYPE_GFX, |
| @@ -310,7 +310,7 @@ static void mmhub_v2_3_setup_vmid_config(struct amdgpu_device *adev) · 309 unmodified lines | |||
| 310 | /* Send no-retry XNACK on fault to suppress VM fault storm. */ | 310 | /* Send no-retry XNACK on fault to suppress VM fault storm. */ |
| 311 | tmp = REG_SET_FIELD(tmp, MMVM_CONTEXT1_CNTL, | 311 | tmp = REG_SET_FIELD(tmp, MMVM_CONTEXT1_CNTL, |
| 312 | RETRY_PERMISSION_OR_INVALID_PAGE_FAULT, | 312 | RETRY_PERMISSION_OR_INVALID_PAGE_FAULT, |
| 313 | !amdgpu_noretry); | 313 | !adev->gmc.noretry); |
| 314 | WREG32_SOC15_OFFSET(MMHUB, 0, mmMMVM_CONTEXT1_CNTL, | 314 | WREG32_SOC15_OFFSET(MMHUB, 0, mmMMVM_CONTEXT1_CNTL, |
| 315 | i * hub->ctx_distance, tmp); | 315 | i * hub->ctx_distance, tmp); |
| 316 | WREG32_SOC15_OFFSET(MMHUB, 0, mmMMVM_CONTEXT1_PAGE_TABLE_START_ADDR_LO32, | 316 | WREG32_SOC15_OFFSET(MMHUB, 0, mmMMVM_CONTEXT1_PAGE_TABLE_START_ADDR_LO32, |
| @@ -491,12 +491,11 @@ mmhub_v2_3_update_medium_grain_clock_gating(struct amdgpu_device *adev, · 174 unmodified lines | |||
| 491 | { | 491 | { |
| 492 | uint32_t def, data, def1, data1; | 492 | uint32_t def, data, def1, data1; |
| 493 | 493 | ||
| 494 | def = data = RREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_MISC_CG); | 494 | def = data = RREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_CGTT_CLK_CTRL); |
| 495 | def1 = data1 = RREG32_SOC15(MMHUB, 0, mmDAGB0_CNTL_MISC2); | 495 | def1 = data1 = RREG32_SOC15(MMHUB, 0, mmDAGB0_CNTL_MISC2); |
| 496 | 496 | ||
| 497 | if (enable && (adev->cg_flags & AMD_CG_SUPPORT_MC_MGCG)) { | 497 | if (enable && (adev->cg_flags & AMD_CG_SUPPORT_MC_MGCG)) { |
| 498 | data |= MM_ATC_L2_MISC_CG__ENABLE_MASK; | 498 | data &= ~MM_ATC_L2_CGTT_CLK_CTRL__SOFT_OVERRIDE_MASK; |
| 499 | |||
| 500 | data1 &= ~(DAGB0_CNTL_MISC2__DISABLE_WRREQ_CG_MASK | | 499 | data1 &= ~(DAGB0_CNTL_MISC2__DISABLE_WRREQ_CG_MASK | |
| 501 | DAGB0_CNTL_MISC2__DISABLE_WRRET_CG_MASK | | 500 | DAGB0_CNTL_MISC2__DISABLE_WRRET_CG_MASK | |
| 502 | DAGB0_CNTL_MISC2__DISABLE_RDREQ_CG_MASK | | 501 | DAGB0_CNTL_MISC2__DISABLE_RDREQ_CG_MASK | |
| @@ -505,8 +504,7 @@ mmhub_v2_3_update_medium_grain_clock_gating(struct amdgpu_device *adev, · 2 unmodified lines | |||
| 505 | DAGB0_CNTL_MISC2__DISABLE_TLBRD_CG_MASK); | 504 | DAGB0_CNTL_MISC2__DISABLE_TLBRD_CG_MASK); |
| 506 | 505 | ||
| 507 | } else { | 506 | } else { |
| 508 | data &= ~MM_ATC_L2_MISC_CG__ENABLE_MASK; | 507 | data |= MM_ATC_L2_CGTT_CLK_CTRL__SOFT_OVERRIDE_MASK; |
| 509 | |||
| 510 | data1 |= (DAGB0_CNTL_MISC2__DISABLE_WRREQ_CG_MASK | | 508 | data1 |= (DAGB0_CNTL_MISC2__DISABLE_WRREQ_CG_MASK | |
| 511 | DAGB0_CNTL_MISC2__DISABLE_WRRET_CG_MASK | | 509 | DAGB0_CNTL_MISC2__DISABLE_WRRET_CG_MASK | |
| 512 | DAGB0_CNTL_MISC2__DISABLE_RDREQ_CG_MASK | | 510 | DAGB0_CNTL_MISC2__DISABLE_RDREQ_CG_MASK | |
| @@ -516,7 +514,7 @@ mmhub_v2_3_update_medium_grain_clock_gating(struct amdgpu_device *adev, · 3 unmodified lines | |||
| 516 | } | 514 | } |
| 517 | 515 | ||
| 518 | if (def != data) | 516 | if (def != data) |
| 519 | WREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_MISC_CG, data); | 517 | WREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_CGTT_CLK_CTRL, data); |
| 520 | if (def1 != data1) | 518 | if (def1 != data1) |
| 521 | WREG32_SOC15(MMHUB, 0, mmDAGB0_CNTL_MISC2, data1); | 519 | WREG32_SOC15(MMHUB, 0, mmDAGB0_CNTL_MISC2, data1); |
| 522 | } | 520 | } |
| @@ -525,17 +523,44 @@ static void · 2 unmodified lines | |||
| 525 | mmhub_v2_3_update_medium_grain_light_sleep(struct amdgpu_device *adev, | 523 | mmhub_v2_3_update_medium_grain_light_sleep(struct amdgpu_device *adev, |
| 526 | bool enable) | 524 | bool enable) |
| 527 | { | 525 | { |
| 528 | uint32_t def, data; | 526 | uint32_t def, data, def1, data1, def2, data2; |
| 529 | 527 | ||
| 530 | def = data = RREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_MISC_CG); | 528 | def = data = RREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_CGTT_CLK_CTRL); |
| 531 | 529 | def1 = data1 = RREG32_SOC15(MMHUB, 0, mmDAGB0_WR_CGTT_CLK_CTRL); | |
| 532 | if (enable && (adev->cg_flags & AMD_CG_SUPPORT_MC_LS)) | 530 | def2 = data2 = RREG32_SOC15(MMHUB, 0, mmDAGB0_RD_CGTT_CLK_CTRL); |
| 533 | data |= MM_ATC_L2_MISC_CG__MEM_LS_ENABLE_MASK; | 531 | |
| 534 | else | 532 | if (enable && (adev->cg_flags & AMD_CG_SUPPORT_MC_LS)) { |
| 535 | data &= ~MM_ATC_L2_MISC_CG__MEM_LS_ENABLE_MASK; | 533 | data &= ~MM_ATC_L2_CGTT_CLK_CTRL__MGLS_OVERRIDE_MASK; |
| 534 | data1 &= !(DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_MASK | | ||
| 535 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_WRITE_MASK | | ||
| 536 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_READ_MASK | | ||
| 537 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_RETURN_MASK | | ||
| 538 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_REGISTER_MASK); | ||
| 539 | data2 &= !(DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_MASK | | ||
| 540 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_WRITE_MASK | | ||
| 541 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_READ_MASK | | ||
| 542 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_RETURN_MASK | | ||
| 543 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_REGISTER_MASK); | ||
| 544 | } else { | ||
| 545 | data |= MM_ATC_L2_CGTT_CLK_CTRL__MGLS_OVERRIDE_MASK; | ||
| 546 | data1 |= (DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_MASK | | ||
| 547 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_WRITE_MASK | | ||
| 548 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_READ_MASK | | ||
| 549 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_RETURN_MASK | | ||
| 550 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_REGISTER_MASK); | ||
| 551 | data2 |= (DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_MASK | | ||
| 552 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_WRITE_MASK | | ||
| 553 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_READ_MASK | | ||
| 554 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_RETURN_MASK | | ||
| 555 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_REGISTER_MASK); | ||
| 556 | } | ||
| 536 | 557 | ||
| 537 | if (def != data) | 558 | if (def != data) |
| 538 | WREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_MISC_CG, data); | 559 | WREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_CGTT_CLK_CTRL, data); |
| 560 | if (def1 != data1) | ||
| 561 | WREG32_SOC15(MMHUB, 0, mmDAGB0_WR_CGTT_CLK_CTRL, data1); | ||
| 562 | if (def2 != data2) | ||
| 563 | WREG32_SOC15(MMHUB, 0, mmDAGB0_RD_CGTT_CLK_CTRL, data2); | ||
| 539 | } | 564 | } |
| 540 | 565 | ||
| 541 | static int mmhub_v2_3_set_clockgating(struct amdgpu_device *adev, | 566 | static int mmhub_v2_3_set_clockgating(struct amdgpu_device *adev, |
| @@ -554,26 +579,39 @@ static int mmhub_v2_3_set_clockgating(struct amdgpu_device *adev, · 12 unmodified lines | |||
| 554 | 579 | ||
| 555 | static void mmhub_v2_3_get_clockgating(struct amdgpu_device *adev, u32 *flags) | 580 | static void mmhub_v2_3_get_clockgating(struct amdgpu_device *adev, u32 *flags) |
| 556 | { | 581 | { |
| 557 | int data, data1; | 582 | int data, data1, data2, data3; |
| 558 | 583 | ||
| 559 | if (amdgpu_sriov_vf(adev)) | 584 | if (amdgpu_sriov_vf(adev)) |
| 560 | *flags = 0; | 585 | *flags = 0; |
| 561 | 586 | ||
| 562 | data = RREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_MISC_CG); | 587 | data = RREG32_SOC15(MMHUB, 0, mmDAGB0_CNTL_MISC2); |
| 563 | data1 = RREG32_SOC15(MMHUB, 0, mmDAGB0_CNTL_MISC2); | 588 | data1 = RREG32_SOC15(MMHUB, 0, mmMM_ATC_L2_CGTT_CLK_CTRL); |
| 589 | data2 = RREG32_SOC15(MMHUB, 0, mmDAGB0_WR_CGTT_CLK_CTRL); | ||
| 590 | data3 = RREG32_SOC15(MMHUB, 0, mmDAGB0_RD_CGTT_CLK_CTRL); | ||
| 564 | 591 | ||
| 565 | /* AMD_CG_SUPPORT_MC_MGCG */ | 592 | /* AMD_CG_SUPPORT_MC_MGCG */ |
| 566 | if ((data & MM_ATC_L2_MISC_CG__ENABLE_MASK) && | 593 | if (!(data & (DAGB0_CNTL_MISC2__DISABLE_WRREQ_CG_MASK | |
| 567 | !(data1 & (DAGB0_CNTL_MISC2__DISABLE_WRREQ_CG_MASK | | ||
| 568 | DAGB0_CNTL_MISC2__DISABLE_WRRET_CG_MASK | | 594 | DAGB0_CNTL_MISC2__DISABLE_WRRET_CG_MASK | |
| 569 | DAGB0_CNTL_MISC2__DISABLE_RDREQ_CG_MASK | | 595 | DAGB0_CNTL_MISC2__DISABLE_RDREQ_CG_MASK | |
| 570 | DAGB0_CNTL_MISC2__DISABLE_RDRET_CG_MASK | | 596 | DAGB0_CNTL_MISC2__DISABLE_RDRET_CG_MASK | |
| 571 | DAGB0_CNTL_MISC2__DISABLE_TLBWR_CG_MASK | | 597 | DAGB0_CNTL_MISC2__DISABLE_TLBWR_CG_MASK | |
| 572 | DAGB0_CNTL_MISC2__DISABLE_TLBRD_CG_MASK))) | 598 | DAGB0_CNTL_MISC2__DISABLE_TLBRD_CG_MASK)) |
| 573 | *flags |= AMD_CG_SUPPORT_MC_MGCG; | 599 | && !(data1 & MM_ATC_L2_CGTT_CLK_CTRL__SOFT_OVERRIDE_MASK)) { |
| 600 | *flags |= AMD_CG_SUPPORT_MC_MGCG; | ||
| 601 | } | ||
| 574 | 602 | ||
| 575 | /* AMD_CG_SUPPORT_MC_LS */ | 603 | /* AMD_CG_SUPPORT_MC_LS */ |
| 576 | if (data & MM_ATC_L2_MISC_CG__MEM_LS_ENABLE_MASK) | 604 | if (!(data1 & MM_ATC_L2_CGTT_CLK_CTRL__MGLS_OVERRIDE_MASK) |
| 605 | && !(data2 & (DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_MASK | | ||
| 606 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_WRITE_MASK | | ||
| 607 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_READ_MASK | | ||
| 608 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_RETURN_MASK | | ||
| 609 | DAGB0_WR_CGTT_CLK_CTRL__LS_OVERRIDE_REGISTER_MASK)) | ||
| 610 | && !(data3 & (DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_MASK | | ||
| 611 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_WRITE_MASK | | ||
| 612 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_READ_MASK | | ||
| 613 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_RETURN_MASK | | ||
| 614 | DAGB0_RD_CGTT_CLK_CTRL__LS_OVERRIDE_REGISTER_MASK))) | ||
| 577 | *flags |= AMD_CG_SUPPORT_MC_LS; | 615 | *flags |= AMD_CG_SUPPORT_MC_LS; |
| 578 | } | 616 | } |
| 579 | 617 | ||
| @@ -47,7 +47,7 @@ enum psp_gfx_crtl_cmd_id · 46 unmodified lines | |||
| 47 | GFX_CTRL_CMD_ID_DISABLE_INT = 0x00060000, /* disable PSP-to-Gfx interrupt */ | 47 | GFX_CTRL_CMD_ID_DISABLE_INT = 0x00060000, /* disable PSP-to-Gfx interrupt */ |
| 48 | GFX_CTRL_CMD_ID_MODE1_RST = 0x00070000, /* trigger the Mode 1 reset */ | 48 | GFX_CTRL_CMD_ID_MODE1_RST = 0x00070000, /* trigger the Mode 1 reset */ |
| 49 | GFX_CTRL_CMD_ID_GBR_IH_SET = 0x00080000, /* set Gbr IH_RB_CNTL registers */ | 49 | GFX_CTRL_CMD_ID_GBR_IH_SET = 0x00080000, /* set Gbr IH_RB_CNTL registers */ |
| 50 | GFX_CTRL_CMD_ID_CONSUME_CMD = 0x000A0000, /* send interrupt to psp for updating write pointer of vf */ | 50 | GFX_CTRL_CMD_ID_CONSUME_CMD = 0x00090000, /* send interrupt to psp for updating write pointer of vf */ |
| 51 | GFX_CTRL_CMD_ID_DESTROY_GPCOM_RING = 0x000C0000, /* destroy GPCOM ring */ | 51 | GFX_CTRL_CMD_ID_DESTROY_GPCOM_RING = 0x000C0000, /* destroy GPCOM ring */ |
| 52 | 52 | ||
| 53 | GFX_CTRL_CMD_ID_MAX = 0x000F0000, /* max command ID */ | 53 | GFX_CTRL_CMD_ID_MAX = 0x000F0000, /* max command ID */ |
| @@ -1239,7 +1239,8 @@ static int soc15_common_early_init(void *handle) · 1238 unmodified lines | |||
| 1239 | break; | 1239 | break; |
| 1240 | case CHIP_RENOIR: | 1240 | case CHIP_RENOIR: |
| 1241 | adev->asic_funcs = &soc15_asic_funcs; | 1241 | adev->asic_funcs = &soc15_asic_funcs; |
| 1242 | if (adev->pdev->device == 0x1636) | 1242 | if ((adev->pdev->device == 0x1636) || |
| 1243 | (adev->pdev->device == 0x164c)) | ||
| 1243 | adev->apu_flags |= AMD_APU_IS_RENOIR; | 1244 | adev->apu_flags |= AMD_APU_IS_RENOIR; |
| 1244 | else | 1245 | else |
| 1245 | adev->apu_flags |= AMD_APU_IS_GREEN_SARDINE; | 1246 | adev->apu_flags |= AMD_APU_IS_GREEN_SARDINE; |
| @@ -1040,11 +1040,14 @@ static int kfd_create_vcrat_image_cpu(void *pcrat_image, size_t *size) · 1039 unmodified lines | |||
| 1040 | (struct crat_subtype_iolink *)sub_type_hdr); | 1040 | (struct crat_subtype_iolink *)sub_type_hdr); |
| 1041 | if (ret < 0) | 1041 | if (ret < 0) |
| 1042 | return ret; | 1042 | return ret; |
| 1043 | crat_table->length += (sub_type_hdr->length * entries); | ||
| 1044 | crat_table->total_entries += entries; | ||
| 1045 | 1043 | ||
| 1046 | sub_type_hdr = (typeof(sub_type_hdr))((char *)sub_type_hdr + | 1044 | if (entries) { |
| 1047 | sub_type_hdr->length * entries); | 1045 | crat_table->length += (sub_type_hdr->length * entries); |
| 1046 | crat_table->total_entries += entries; | ||
| 1047 | |||
| 1048 | sub_type_hdr = (typeof(sub_type_hdr))((char *)sub_type_hdr + | ||
| 1049 | sub_type_hdr->length * entries); | ||
| 1050 | } | ||
| 1048 | #else | 1051 | #else |
| 1049 | pr_info("IO link not available for non x86 platforms\n"); | 1052 | pr_info("IO link not available for non x86 platforms\n"); |
| 1050 | #endif | 1053 | #endif |
| @@ -6,7 +6,7 @@ config DRM_AMD_DC · 5 unmodified lines | |||
| 6 | bool "AMD DC - Enable new display engine" | 6 | bool "AMD DC - Enable new display engine" |
| 7 | default y | 7 | default y |
| 8 | select SND_HDA_COMPONENT if SND_HDA_CORE | 8 | select SND_HDA_COMPONENT if SND_HDA_CORE |
| 9 | select DRM_AMD_DC_DCN if (X86 || PPC64 || (ARM64 && KERNEL_MODE_NEON)) && !(KCOV_INSTRUMENT_ALL && KCOV_ENABLE_COMPARISONS) | 9 | select DRM_AMD_DC_DCN if (X86 || PPC64) && !(KCOV_INSTRUMENT_ALL && KCOV_ENABLE_COMPARISONS) |
| 10 | help | 10 | help |
| 11 | Choose this option if you want to use the new display engine | 11 | Choose this option if you want to use the new display engine |
| 12 | support for AMDGPU. This adds required support for Vega and | 12 | support for AMDGPU. This adds required support for Vega and |
| @@ -939,41 +939,6 @@ static void mmhub_read_system_context(struct amdgpu_device *adev, struct dc_phy_ · 938 unmodified lines | |||
| 939 | } | 939 | } |
| 940 | #endif | 940 | #endif |
| 941 | 941 | ||
| 942 | #ifdef CONFIG_DEBUG_FS | ||
| 943 | static int create_crtc_crc_properties(struct amdgpu_display_manager *dm) | ||
| 944 | { | ||
| 945 | dm->crc_win_x_start_property = | ||
| 946 | drm_property_create_range(adev_to_drm(dm->adev), | ||
| 947 | DRM_MODE_PROP_ATOMIC, | ||
| 948 | "AMD_CRC_WIN_X_START", 0, U16_MAX); | ||
| 949 | if (!dm->crc_win_x_start_property) | ||
| 950 | return -ENOMEM; | ||
| 951 | |||
| 952 | dm->crc_win_y_start_property = | ||
| 953 | drm_property_create_range(adev_to_drm(dm->adev), | ||
| 954 | DRM_MODE_PROP_ATOMIC, | ||
| 955 | "AMD_CRC_WIN_Y_START", 0, U16_MAX); | ||
| 956 | if (!dm->crc_win_y_start_property) | ||
| 957 | return -ENOMEM; | ||
| 958 | |||
| 959 | dm->crc_win_x_end_property = | ||
| 960 | drm_property_create_range(adev_to_drm(dm->adev), | ||
| 961 | DRM_MODE_PROP_ATOMIC, | ||
| 962 | "AMD_CRC_WIN_X_END", 0, U16_MAX); | ||
| 963 | if (!dm->crc_win_x_end_property) | ||
| 964 | return -ENOMEM; | ||
| 965 | |||
| 966 | dm->crc_win_y_end_property = | ||
| 967 | drm_property_create_range(adev_to_drm(dm->adev), | ||
| 968 | DRM_MODE_PROP_ATOMIC, | ||
| 969 | "AMD_CRC_WIN_Y_END", 0, U16_MAX); | ||
| 970 | if (!dm->crc_win_y_end_property) | ||
| 971 | return -ENOMEM; | ||
| 972 | |||
| 973 | return 0; | ||
| 974 | } | ||
| 975 | #endif | ||
| 976 | |||
| 977 | static int amdgpu_dm_init(struct amdgpu_device *adev) | 942 | static int amdgpu_dm_init(struct amdgpu_device *adev) |
| 978 | { | 943 | { |
| 979 | struct dc_init_data init_data; | 944 | struct dc_init_data init_data; |
| @@ -1120,10 +1085,6 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) · 140 unmodified lines | |||
| 1120 | 1085 | ||
| 1121 | dc_init_callbacks(adev->dm.dc, &init_params); | 1086 | dc_init_callbacks(adev->dm.dc, &init_params); |
| 1122 | } | 1087 | } |
| 1123 | #endif | ||
| 1124 | #ifdef CONFIG_DEBUG_FS | ||
| 1125 | if (create_crtc_crc_properties(&adev->dm)) | ||
| 1126 | DRM_ERROR("amdgpu: failed to create crc property.\n"); | ||
| 1127 | #endif | 1088 | #endif |
| 1128 | if (amdgpu_dm_initialize_drm_device(adev)) { | 1089 | if (amdgpu_dm_initialize_drm_device(adev)) { |
| 1129 | DRM_ERROR( | 1090 | DRM_ERROR( |
| @@ -1872,8 +1833,8 @@ static void emulated_link_detect(struct dc_link *link) · 742 unmodified lines | |||
| 1872 | link->type = dc_connection_none; | 1833 | link->type = dc_connection_none; |
| 1873 | prev_sink = link->local_sink; | 1834 | prev_sink = link->local_sink; |
| 1874 | 1835 | ||
| 1875 | if (prev_sink != NULL) | 1836 | if (prev_sink) |
| 1876 | dc_sink_retain(prev_sink); | 1837 | dc_sink_release(prev_sink); |
| 1877 | 1838 | ||
| 1878 | switch (link->connector_signal) { | 1839 | switch (link->connector_signal) { |
| 1879 | case SIGNAL_TYPE_HDMI_TYPE_A: { | 1840 | case SIGNAL_TYPE_HDMI_TYPE_A: { |
| @@ -1973,7 +1934,7 @@ static void dm_gpureset_commit_state(struct dc_state *dc_state, · 93 unmodified lines | |||
| 1973 | dc_commit_updates_for_stream( | 1934 | dc_commit_updates_for_stream( |
| 1974 | dm->dc, bundle->surface_updates, | 1935 | dm->dc, bundle->surface_updates, |
| 1975 | dc_state->stream_status->plane_count, | 1936 | dc_state->stream_status->plane_count, |
| 1976 | dc_state->streams[k], &bundle->stream_update, dc_state); | 1937 | dc_state->streams[k], &bundle->stream_update); |
| 1977 | } | 1938 | } |
| 1978 | 1939 | ||
| 1979 | cleanup: | 1940 | cleanup: |
| @@ -2004,8 +1965,7 @@ static void dm_set_dpms_off(struct dc_link *link) · 24 unmodified lines | |||
| 2004 | 1965 | ||
| 2005 | stream_update.stream = stream_state; | 1966 | stream_update.stream = stream_state; |
| 2006 | dc_commit_updates_for_stream(stream_state->ctx->dc, NULL, 0, | 1967 | dc_commit_updates_for_stream(stream_state->ctx->dc, NULL, 0, |
| 2007 | stream_state, &stream_update, | 1968 | stream_state, &stream_update); |
| 2008 | stream_state->ctx->dc->current_state); | ||
| 2009 | mutex_unlock(&adev->dm.dc_lock); | 1969 | mutex_unlock(&adev->dm.dc_lock); |
| 2010 | } | 1970 | } |
| 2011 | 1971 | ||
| @@ -2369,8 +2329,10 @@ void amdgpu_dm_update_connector_after_detect( · 357 unmodified lines | |||
| 2369 | * TODO: check if we still need the S3 mode update workaround. | 2329 | * TODO: check if we still need the S3 mode update workaround. |
| 2370 | * If yes, put it here. | 2330 | * If yes, put it here. |
| 2371 | */ | 2331 | */ |
| 2372 | if (aconnector->dc_sink) | 2332 | if (aconnector->dc_sink) { |
| 2373 | amdgpu_dm_update_freesync_caps(connector, NULL); | 2333 | amdgpu_dm_update_freesync_caps(connector, NULL); |
| 2334 | dc_sink_release(aconnector->dc_sink); | ||
| 2335 | } | ||
| 2374 | 2336 | ||
| 2375 | aconnector->dc_sink = sink; | 2337 | aconnector->dc_sink = sink; |
| 2376 | dc_sink_retain(aconnector->dc_sink); | 2338 | dc_sink_retain(aconnector->dc_sink); |
| @@ -2386,9 +2348,6 @@ void amdgpu_dm_update_connector_after_detect( · 9 unmodified lines | |||
| 2386 | 2348 | ||
| 2387 | drm_connector_update_edid_property(connector, | 2349 | drm_connector_update_edid_property(connector, |
| 2388 | aconnector->edid); | 2350 | aconnector->edid); |
| 2389 | aconnector->num_modes = drm_add_edid_modes(connector, aconnector->edid); | ||
| 2390 | drm_connector_list_update(connector); | ||
| 2391 | |||
| 2392 | if (aconnector->dc_link->aux_mode) | 2351 | if (aconnector->dc_link->aux_mode) |
| 2393 | drm_dp_cec_set_edid(&aconnector->dm_dp_aux.aux, | 2352 | drm_dp_cec_set_edid(&aconnector->dm_dp_aux.aux, |
| 2394 | aconnector->edid); | 2353 | aconnector->edid); |
| @@ -5334,64 +5293,12 @@ dm_crtc_duplicate_state(struct drm_crtc *crtc) · 2939 unmodified lines | |||
| 5334 | state->crc_src = cur->crc_src; | 5293 | state->crc_src = cur->crc_src; |
| 5335 | state->cm_has_degamma = cur->cm_has_degamma; | 5294 | state->cm_has_degamma = cur->cm_has_degamma; |
| 5336 | state->cm_is_degamma_srgb = cur->cm_is_degamma_srgb; | 5295 | state->cm_is_degamma_srgb = cur->cm_is_degamma_srgb; |
| 5337 | #ifdef CONFIG_DEBUG_FS | 5296 | |
| 5338 | state->crc_window = cur->crc_window; | ||
| 5339 | #endif | ||
| 5340 | /* TODO Duplicate dc_stream after objects are stream object is flattened */ | 5297 | /* TODO Duplicate dc_stream after objects are stream object is flattened */ |
| 5341 | 5298 | ||
| 5342 | return &state->base; | 5299 | return &state->base; |
| 5343 | } | 5300 | } |
| 5344 | 5301 | ||
| 5345 | #ifdef CONFIG_DEBUG_FS | ||
| 5346 | static int amdgpu_dm_crtc_atomic_set_property(struct drm_crtc *crtc, | ||
| 5347 | struct drm_crtc_state *crtc_state, | ||
| 5348 | struct drm_property *property, | ||
| 5349 | uint64_t val) | ||
| 5350 | { | ||
| 5351 | struct drm_device *dev = crtc->dev; | ||
| 5352 | struct amdgpu_device *adev = drm_to_adev(dev); | ||
| 5353 | struct dm_crtc_state *dm_new_state = | ||
| 5354 | to_dm_crtc_state(crtc_state); | ||
| 5355 | |||
| 5356 | if (property == adev->dm.crc_win_x_start_property) | ||
| 5357 | dm_new_state->crc_window.x_start = val; | ||
| 5358 | else if (property == adev->dm.crc_win_y_start_property) | ||
| 5359 | dm_new_state->crc_window.y_start = val; | ||
| 5360 | else if (property == adev->dm.crc_win_x_end_property) | ||
| 5361 | dm_new_state->crc_window.x_end = val; | ||
| 5362 | else if (property == adev->dm.crc_win_y_end_property) | ||
| 5363 | dm_new_state->crc_window.y_end = val; | ||
| 5364 | else | ||
| 5365 | return -EINVAL; | ||
| 5366 | |||
| 5367 | return 0; | ||
| 5368 | } | ||
| 5369 | |||
| 5370 | static int amdgpu_dm_crtc_atomic_get_property(struct drm_crtc *crtc, | ||
| 5371 | const struct drm_crtc_state *state, | ||
| 5372 | struct drm_property *property, | ||
| 5373 | uint64_t *val) | ||
| 5374 | { | ||
| 5375 | struct drm_device *dev = crtc->dev; | ||
| 5376 | struct amdgpu_device *adev = drm_to_adev(dev); | ||
| 5377 | struct dm_crtc_state *dm_state = | ||
| 5378 | to_dm_crtc_state(state); | ||
| 5379 | |||
| 5380 | if (property == adev->dm.crc_win_x_start_property) | ||
| 5381 | *val = dm_state->crc_window.x_start; | ||
| 5382 | else if (property == adev->dm.crc_win_y_start_property) | ||
| 5383 | *val = dm_state->crc_window.y_start; | ||
| 5384 | else if (property == adev->dm.crc_win_x_end_property) | ||
| 5385 | *val = dm_state->crc_window.x_end; | ||
| 5386 | else if (property == adev->dm.crc_win_y_end_property) | ||
| 5387 | *val = dm_state->crc_window.y_end; | ||
| 5388 | else | ||
| 5389 | return -EINVAL; | ||
| 5390 | |||
| 5391 | return 0; | ||
| 5392 | } | ||
| 5393 | #endif | ||
| 5394 | |||
| 5395 | static inline int dm_set_vupdate_irq(struct drm_crtc *crtc, bool enable) | 5302 | static inline int dm_set_vupdate_irq(struct drm_crtc *crtc, bool enable) |
| 5396 | { | 5303 | { |
| 5397 | enum dc_irq_source irq_source; | 5304 | enum dc_irq_source irq_source; |
| @@ -5458,10 +5365,6 @@ static const struct drm_crtc_funcs amdgpu_dm_crtc_funcs = { · 60 unmodified lines | |||
| 5458 | .enable_vblank = dm_enable_vblank, | 5365 | .enable_vblank = dm_enable_vblank, |
| 5459 | .disable_vblank = dm_disable_vblank, | 5366 | .disable_vblank = dm_disable_vblank, |
| 5460 | .get_vblank_timestamp = drm_crtc_vblank_helper_get_vblank_timestamp, | 5367 | .get_vblank_timestamp = drm_crtc_vblank_helper_get_vblank_timestamp, |
| 5461 | #ifdef CONFIG_DEBUG_FS | ||
| 5462 | .atomic_set_property = amdgpu_dm_crtc_atomic_set_property, | ||
| 5463 | .atomic_get_property = amdgpu_dm_crtc_atomic_get_property, | ||
| 5464 | #endif | ||
| 5465 | }; | 5368 | }; |
| 5466 | 5369 | ||
| 5467 | static enum drm_connector_status | 5370 | static enum drm_connector_status |
| @@ -6663,25 +6566,6 @@ static int amdgpu_dm_plane_init(struct amdgpu_display_manager *dm, · 1195 unmodified lines | |||
| 6663 | return 0; | 6566 | return 0; |
| 6664 | } | 6567 | } |
| 6665 | 6568 | ||
| 6666 | #ifdef CONFIG_DEBUG_FS | ||
| 6667 | static void attach_crtc_crc_properties(struct amdgpu_display_manager *dm, | ||
| 6668 | struct amdgpu_crtc *acrtc) | ||
| 6669 | { | ||
| 6670 | drm_object_attach_property(&acrtc->base.base, | ||
| 6671 | dm->crc_win_x_start_property, | ||
| 6672 | 0); | ||
| 6673 | drm_object_attach_property(&acrtc->base.base, | ||
| 6674 | dm->crc_win_y_start_property, | ||
| 6675 | 0); | ||
| 6676 | drm_object_attach_property(&acrtc->base.base, | ||
| 6677 | dm->crc_win_x_end_property, | ||
| 6678 | 0); | ||
| 6679 | drm_object_attach_property(&acrtc->base.base, | ||
| 6680 | dm->crc_win_y_end_property, | ||
| 6681 | 0); | ||
| 6682 | } | ||
| 6683 | #endif | ||
| 6684 | |||
| 6685 | static int amdgpu_dm_crtc_init(struct amdgpu_display_manager *dm, | 6569 | static int amdgpu_dm_crtc_init(struct amdgpu_display_manager *dm, |
| 6686 | struct drm_plane *plane, | 6570 | struct drm_plane *plane, |
| 6687 | uint32_t crtc_index) | 6571 | uint32_t crtc_index) |
| @@ -6729,9 +6613,7 @@ static int amdgpu_dm_crtc_init(struct amdgpu_display_manager *dm, · 41 unmodified lines | |||
| 6729 | drm_crtc_enable_color_mgmt(&acrtc->base, MAX_COLOR_LUT_ENTRIES, | 6613 | drm_crtc_enable_color_mgmt(&acrtc->base, MAX_COLOR_LUT_ENTRIES, |
| 6730 | true, MAX_COLOR_LUT_ENTRIES); | 6614 | true, MAX_COLOR_LUT_ENTRIES); |
| 6731 | drm_mode_crtc_set_gamma_size(&acrtc->base, MAX_COLOR_LEGACY_LUT_ENTRIES); | 6615 | drm_mode_crtc_set_gamma_size(&acrtc->base, MAX_COLOR_LEGACY_LUT_ENTRIES); |
| 6732 | #ifdef CONFIG_DEBUG_FS | 6616 | |
| 6733 | attach_crtc_crc_properties(dm, acrtc); | ||
| 6734 | #endif | ||
| 6735 | return 0; | 6617 | return 0; |
| 6736 | 6618 | ||
| 6737 | fail: | 6619 | fail: |
| @@ -7666,7 +7548,7 @@ static void amdgpu_dm_commit_planes(struct drm_atomic_state *state, · 928 unmodified lines | |||
| 7666 | struct drm_crtc *pcrtc, | 7548 | struct drm_crtc *pcrtc, |
| 7667 | bool wait_for_vblank) | 7549 | bool wait_for_vblank) |
| 7668 | { | 7550 | { |
| 7669 | uint32_t i; | 7551 | int i; |
| 7670 | uint64_t timestamp_ns; | 7552 | uint64_t timestamp_ns; |
| 7671 | struct drm_plane *plane; | 7553 | struct drm_plane *plane; |
| 7672 | struct drm_plane_state *old_plane_state, *new_plane_state; | 7554 | struct drm_plane_state *old_plane_state, *new_plane_state; |
| @@ -7707,7 +7589,7 @@ static void amdgpu_dm_commit_planes(struct drm_atomic_state *state, · 34 unmodified lines | |||
| 7707 | amdgpu_dm_commit_cursors(state); | 7589 | amdgpu_dm_commit_cursors(state); |
| 7708 | 7590 | ||
| 7709 | /* update planes when needed */ | 7591 | /* update planes when needed */ |
| 7710 | for_each_oldnew_plane_in_state(state, plane, old_plane_state, new_plane_state, i) { | 7592 | for_each_oldnew_plane_in_state_reverse(state, plane, old_plane_state, new_plane_state, i) { |
| 7711 | struct drm_crtc *crtc = new_plane_state->crtc; | 7593 | struct drm_crtc *crtc = new_plane_state->crtc; |
| 7712 | struct drm_crtc_state *new_crtc_state; | 7594 | struct drm_crtc_state *new_crtc_state; |
| 7713 | struct drm_framebuffer *fb = new_plane_state->fb; | 7595 | struct drm_framebuffer *fb = new_plane_state->fb; |
| @@ -7930,8 +7812,7 @@ static void amdgpu_dm_commit_planes(struct drm_atomic_state *state, · 216 unmodified lines | |||
| 7930 | bundle->surface_updates, | 7812 | bundle->surface_updates, |
| 7931 | planes_count, | 7813 | planes_count, |
| 7932 | acrtc_state->stream, | 7814 | acrtc_state->stream, |
| 7933 | &bundle->stream_update, | 7815 | &bundle->stream_update); |
| 7934 | dc_state); | ||
| 7935 | 7816 | ||
| 7936 | /** | 7817 | /** |
| 7937 | * Enable or disable the interrupts on the backend. | 7818 | * Enable or disable the interrupts on the backend. |
| @@ -8267,13 +8148,13 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) · 329 unmodified lines | |||
| 8267 | struct dm_connector_state *dm_new_con_state = to_dm_connector_state(new_con_state); | 8148 | struct dm_connector_state *dm_new_con_state = to_dm_connector_state(new_con_state); |
| 8268 | struct dm_connector_state *dm_old_con_state = to_dm_connector_state(old_con_state); | 8149 | struct dm_connector_state *dm_old_con_state = to_dm_connector_state(old_con_state); |
| 8269 | struct amdgpu_crtc *acrtc = to_amdgpu_crtc(dm_new_con_state->base.crtc); | 8150 | struct amdgpu_crtc *acrtc = to_amdgpu_crtc(dm_new_con_state->base.crtc); |
| 8270 | struct dc_surface_update dummy_updates[MAX_SURFACES]; | 8151 | struct dc_surface_update surface_updates[MAX_SURFACES]; |
| 8271 | struct dc_stream_update stream_update; | 8152 | struct dc_stream_update stream_update; |
| 8272 | struct dc_info_packet hdr_packet; | 8153 | struct dc_info_packet hdr_packet; |
| 8273 | struct dc_stream_status *status = NULL; | 8154 | struct dc_stream_status *status = NULL; |
| 8274 | bool abm_changed, hdr_changed, scaling_changed; | 8155 | bool abm_changed, hdr_changed, scaling_changed; |
| 8275 | 8156 | ||
| 8276 | memset(&dummy_updates, 0, sizeof(dummy_updates)); | 8157 | memset(&surface_updates, 0, sizeof(surface_updates)); |
| 8277 | memset(&stream_update, 0, sizeof(stream_update)); | 8158 | memset(&stream_update, 0, sizeof(stream_update)); |
| 8278 | 8159 | ||
| 8279 | if (acrtc) { | 8160 | if (acrtc) { |
| @@ -8330,16 +8211,15 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) · 50 unmodified lines | |||
| 8330 | * To fix this, DC should permit updating only stream properties. | 8211 | * To fix this, DC should permit updating only stream properties. |
| 8331 | */ | 8212 | */ |
| 8332 | for (j = 0; j < status->plane_count; j++) | 8213 | for (j = 0; j < status->plane_count; j++) |
| 8333 | dummy_updates[j].surface = status->plane_states[0]; | 8214 | surface_updates[j].surface = status->plane_states[j]; |
| 8334 | 8215 | ||
| 8335 | 8216 | ||
| 8336 | mutex_lock(&dm->dc_lock); | 8217 | mutex_lock(&dm->dc_lock); |
| 8337 | dc_commit_updates_for_stream(dm->dc, | 8218 | dc_commit_updates_for_stream(dm->dc, |
| 8338 | dummy_updates, | 8219 | surface_updates, |
| 8339 | status->plane_count, | 8220 | status->plane_count, |
| 8340 | dm_new_crtc_state->stream, | 8221 | dm_new_crtc_state->stream, |
| 8341 | &stream_update, | 8222 | &stream_update); |
| 8342 | dc_state); | ||
| 8343 | mutex_unlock(&dm->dc_lock); | 8223 | mutex_unlock(&dm->dc_lock); |
| 8344 | } | 8224 | } |
| 8345 | 8225 | ||
| @@ -8368,7 +8248,6 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) · 22 unmodified lines | |||
| 8368 | */ | 8248 | */ |
| 8369 | for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { | 8249 | for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { |
| 8370 | struct amdgpu_crtc *acrtc = to_amdgpu_crtc(crtc); | 8250 | struct amdgpu_crtc *acrtc = to_amdgpu_crtc(crtc); |
| 8371 | bool configure_crc = false; | ||
| 8372 | 8251 | ||
| 8373 | dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); | 8252 | dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); |
| 8374 | 8253 | ||
| @@ -8378,30 +8257,21 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) · 3 unmodified lines | |||
| 8378 | dc_stream_retain(dm_new_crtc_state->stream); | 8257 | dc_stream_retain(dm_new_crtc_state->stream); |
| 8379 | acrtc->dm_irq_params.stream = dm_new_crtc_state->stream; | 8258 | acrtc->dm_irq_params.stream = dm_new_crtc_state->stream; |
| 8380 | manage_dm_interrupts(adev, acrtc, true); | 8259 | manage_dm_interrupts(adev, acrtc, true); |
| 8381 | } | 8260 | |
| 8382 | #ifdef CONFIG_DEBUG_FS | 8261 | #ifdef CONFIG_DEBUG_FS |
| 8383 | if (new_crtc_state->active && | ||
| 8384 | amdgpu_dm_is_valid_crc_source(dm_new_crtc_state->crc_src)) { | ||
| 8385 | /** | 8262 | /** |
| 8386 | * Frontend may have changed so reapply the CRC capture | 8263 | * Frontend may have changed so reapply the CRC capture |
| 8387 | * settings for the stream. | 8264 | * settings for the stream. |
| 8388 | */ | 8265 | */ |
| 8389 | dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); | 8266 | dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); |
| 8390 | dm_old_crtc_state = to_dm_crtc_state(old_crtc_state); | ||
| 8391 | |||
| 8392 | if (amdgpu_dm_crc_window_is_default(dm_new_crtc_state)) { | ||
| 8393 | if (!old_crtc_state->active || drm_atomic_crtc_needs_modeset(new_crtc_state)) | ||
| 8394 | configure_crc = true; | ||
| 8395 | } else { | ||
| 8396 | if (amdgpu_dm_crc_window_changed(dm_new_crtc_state, dm_old_crtc_state)) | ||
| 8397 | configure_crc = true; | ||
| 8398 | } | ||
| 8399 | 8267 | ||
| 8400 | if (configure_crc) | 8268 | if (amdgpu_dm_is_valid_crc_source(dm_new_crtc_state->crc_src)) { |
| 8401 | amdgpu_dm_crtc_configure_crc_source( | 8269 | amdgpu_dm_crtc_configure_crc_source( |
| 8402 | crtc, dm_new_crtc_state, dm_new_crtc_state->crc_src); | 8270 | crtc, dm_new_crtc_state, |
| 8403 | } | 8271 | dm_new_crtc_state->crc_src); |
| 8272 | } | ||
| 8404 | #endif | 8273 | #endif |
| 8274 | } | ||
| 8405 | } | 8275 | } |
| 8406 | 8276 | ||
| 8407 | for_each_new_crtc_in_state(state, crtc, new_crtc_state, j) | 8277 | for_each_new_crtc_in_state(state, crtc, new_crtc_state, j) |
| @@ -8486,14 +8356,14 @@ static int dm_force_atomic_commit(struct drm_connector *connector) · 78 unmodified lines | |||
| 8486 | 8356 | ||
| 8487 | ret = PTR_ERR_OR_ZERO(conn_state); | 8357 | ret = PTR_ERR_OR_ZERO(conn_state); |
| 8488 | if (ret) | 8358 | if (ret) |
| 8489 | goto err; | 8359 | goto out; |
| 8490 | 8360 | ||
| 8491 | /* Attach crtc to drm_atomic_state*/ | 8361 | /* Attach crtc to drm_atomic_state*/ |
| 8492 | crtc_state = drm_atomic_get_crtc_state(state, &disconnected_acrtc->base); | 8362 | crtc_state = drm_atomic_get_crtc_state(state, &disconnected_acrtc->base); |
| 8493 | 8363 | ||
| 8494 | ret = PTR_ERR_OR_ZERO(crtc_state); | 8364 | ret = PTR_ERR_OR_ZERO(crtc_state); |
| 8495 | if (ret) | 8365 | if (ret) |
| 8496 | goto err; | 8366 | goto out; |
| 8497 | 8367 | ||
| 8498 | /* force a restore */ | 8368 | /* force a restore */ |
| 8499 | crtc_state->mode_changed = true; | 8369 | crtc_state->mode_changed = true; |
| @@ -8503,17 +8373,15 @@ static int dm_force_atomic_commit(struct drm_connector *connector) · 3 unmodified lines | |||
| 8503 | 8373 | ||
| 8504 | ret = PTR_ERR_OR_ZERO(plane_state); | 8374 | ret = PTR_ERR_OR_ZERO(plane_state); |
| 8505 | if (ret) | 8375 | if (ret) |
| 8506 | goto err; | 8376 | goto out; |
| 8507 | |||
| 8508 | 8377 | ||
| 8509 | /* Call commit internally with the state we just constructed */ | 8378 | /* Call commit internally with the state we just constructed */ |
| 8510 | ret = drm_atomic_commit(state); | 8379 | ret = drm_atomic_commit(state); |
| 8511 | if (!ret) | ||
| 8512 | return 0; | ||
| 8513 | 8380 | ||
| 8514 | err: | 8381 | out: |
| 8515 | DRM_ERROR("Restoring old state failed with %i\n", ret); | ||
| 8516 | drm_atomic_state_put(state); | 8382 | drm_atomic_state_put(state); |
| 8383 | if (ret) | ||
| 8384 | DRM_ERROR("Restoring old state failed with %i\n", ret); | ||
| 8517 | 8385 | ||
| 8518 | return ret; | 8386 | return ret; |
| 8519 | } | 8387 | } |
| @@ -336,32 +336,6 @@ struct amdgpu_display_manager { · 335 unmodified lines | |||
| 336 | */ | 336 | */ |
| 337 | const struct gpu_info_soc_bounding_box_v1_0 *soc_bounding_box; | 337 | const struct gpu_info_soc_bounding_box_v1_0 *soc_bounding_box; |
| 338 | 338 | ||
| 339 | #ifdef CONFIG_DEBUG_FS | ||
| 340 | /** | ||
| 341 | * @crc_win_x_start_property: | ||
| 342 | * | ||
| 343 | * X start of the crc calculation window | ||
| 344 | */ | ||
| 345 | struct drm_property *crc_win_x_start_property; | ||
| 346 | /** | ||
| 347 | * @crc_win_y_start_property: | ||
| 348 | * | ||
| 349 | * Y start of the crc calculation window | ||
| 350 | */ | ||
| 351 | struct drm_property *crc_win_y_start_property; | ||
| 352 | /** | ||
| 353 | * @crc_win_x_end_property: | ||
| 354 | * | ||
| 355 | * X end of the crc calculation window | ||
| 356 | */ | ||
| 357 | struct drm_property *crc_win_x_end_property; | ||
| 358 | /** | ||
| 359 | * @crc_win_y_end_property: | ||
| 360 | * | ||
| 361 | * Y end of the crc calculation window | ||
| 362 | */ | ||
| 363 | struct drm_property *crc_win_y_end_property; | ||
| 364 | #endif | ||
| 365 | /** | 339 | /** |
| 366 | * @mst_encoders: | 340 | * @mst_encoders: |
| 367 | * | 341 | * |
| @@ -448,15 +422,6 @@ struct dm_plane_state { · 80 unmodified lines | |||
| 448 | struct dc_plane_state *dc_state; | 422 | struct dc_plane_state *dc_state; |
| 449 | }; | 423 | }; |
| 450 | 424 | ||
| 451 | #ifdef CONFIG_DEBUG_FS | ||
| 452 | struct crc_rec { | ||
| 453 | uint16_t x_start; | ||
| 454 | uint16_t y_start; | ||
| 455 | uint16_t x_end; | ||
| 456 | uint16_t y_end; | ||
| 457 | }; | ||
| 458 | #endif | ||
| 459 | |||
| 460 | struct dm_crtc_state { | 425 | struct dm_crtc_state { |
| 461 | struct drm_crtc_state base; | 426 | struct drm_crtc_state base; |
| 462 | struct dc_stream_state *stream; | 427 | struct dc_stream_state *stream; |
| @@ -479,9 +444,6 @@ struct dm_crtc_state { · 16 unmodified lines | |||
| 479 | struct dc_info_packet vrr_infopacket; | 444 | struct dc_info_packet vrr_infopacket; |
| 480 | 445 | ||
| 481 | int abm_level; | 446 | int abm_level; |
| 482 | #ifdef CONFIG_DEBUG_FS | ||
| 483 | struct crc_rec crc_window; | ||
| 484 | #endif | ||
| 485 | }; | 447 | }; |
| 486 | 448 | ||
| 487 | #define to_dm_crtc_state(x) container_of(x, struct dm_crtc_state, base) | 449 | #define to_dm_crtc_state(x) container_of(x, struct dm_crtc_state, base) |
| @@ -81,41 +81,6 @@ const char *const *amdgpu_dm_crtc_get_crc_sources(struct drm_crtc *crtc, · 80 unmodified lines | |||
| 81 | return pipe_crc_sources; | 81 | return pipe_crc_sources; |
| 82 | } | 82 | } |
| 83 | 83 | ||
| 84 | static void amdgpu_dm_set_crc_window_default(struct dm_crtc_state *dm_crtc_state) | ||
| 85 | { | ||
| 86 | dm_crtc_state->crc_window.x_start = 0; | ||
| 87 | dm_crtc_state->crc_window.y_start = 0; | ||
| 88 | dm_crtc_state->crc_window.x_end = 0; | ||
| 89 | dm_crtc_state->crc_window.y_end = 0; | ||
| 90 | } | ||
| 91 | |||
| 92 | bool amdgpu_dm_crc_window_is_default(struct dm_crtc_state *dm_crtc_state) | ||
| 93 | { | ||
| 94 | bool ret = true; | ||
| 95 | |||
| 96 | if ((dm_crtc_state->crc_window.x_start != 0) || | ||
| 97 | (dm_crtc_state->crc_window.y_start != 0) || | ||
| 98 | (dm_crtc_state->crc_window.x_end != 0) || | ||
| 99 | (dm_crtc_state->crc_window.y_end != 0)) | ||
| 100 | ret = false; | ||
| 101 | |||
| 102 | return ret; | ||
| 103 | } | ||
| 104 | |||
| 105 | bool amdgpu_dm_crc_window_changed(struct dm_crtc_state *dm_new_crtc_state, | ||
| 106 | struct dm_crtc_state *dm_old_crtc_state) | ||
| 107 | { | ||
| 108 | bool ret = false; | ||
| 109 | |||
| 110 | if ((dm_new_crtc_state->crc_window.x_start != dm_old_crtc_state->crc_window.x_start) || | ||
| 111 | (dm_new_crtc_state->crc_window.y_start != dm_old_crtc_state->crc_window.y_start) || | ||
| 112 | (dm_new_crtc_state->crc_window.x_end != dm_old_crtc_state->crc_window.x_end) || | ||
| 113 | (dm_new_crtc_state->crc_window.y_end != dm_old_crtc_state->crc_window.y_end)) | ||
| 114 | ret = true; | ||
| 115 | |||
| 116 | return ret; | ||
| 117 | } | ||
| 118 | |||
| 119 | int | 84 | int |
| 120 | amdgpu_dm_crtc_verify_crc_source(struct drm_crtc *crtc, const char *src_name, | 85 | amdgpu_dm_crtc_verify_crc_source(struct drm_crtc *crtc, const char *src_name, |
| 121 | size_t *values_cnt) | 86 | size_t *values_cnt) |
| @@ -140,7 +105,6 @@ int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc, · 18 unmodified lines | |||
| 140 | struct dc_stream_state *stream_state = dm_crtc_state->stream; | 105 | struct dc_stream_state *stream_state = dm_crtc_state->stream; |
| 141 | bool enable = amdgpu_dm_is_valid_crc_source(source); | 106 | bool enable = amdgpu_dm_is_valid_crc_source(source); |
| 142 | int ret = 0; | 107 | int ret = 0; |
| 143 | struct crc_params *crc_window = NULL, tmp_window; | ||
| 144 | 108 | ||
| 145 | /* Configuration will be deferred to stream enable. */ | 109 | /* Configuration will be deferred to stream enable. */ |
| 146 | if (!stream_state) | 110 | if (!stream_state) |
| @@ -150,24 +114,8 @@ int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc, · 3 unmodified lines | |||
| 150 | 114 | ||
| 151 | /* Enable CRTC CRC generation if necessary. */ | 115 | /* Enable CRTC CRC generation if necessary. */ |
| 152 | if (dm_is_crc_source_crtc(source) || source == AMDGPU_DM_PIPE_CRC_SOURCE_NONE) { | 116 | if (dm_is_crc_source_crtc(source) || source == AMDGPU_DM_PIPE_CRC_SOURCE_NONE) { |
| 153 | if (!enable) | ||
| 154 | amdgpu_dm_set_crc_window_default(dm_crtc_state); | ||
| 155 | |||
| 156 | if (!amdgpu_dm_crc_window_is_default(dm_crtc_state)) { | ||
| 157 | crc_window = &tmp_window; | ||
| 158 | |||
| 159 | tmp_window.windowa_x_start = dm_crtc_state->crc_window.x_start; | ||
| 160 | tmp_window.windowa_y_start = dm_crtc_state->crc_window.y_start; | ||
| 161 | tmp_window.windowa_x_end = dm_crtc_state->crc_window.x_end; | ||
| 162 | tmp_window.windowa_y_end = dm_crtc_state->crc_window.y_end; | ||
| 163 | tmp_window.windowb_x_start = dm_crtc_state->crc_window.x_start; | ||
| 164 | tmp_window.windowb_y_start = dm_crtc_state->crc_window.y_start; | ||
| 165 | tmp_window.windowb_x_end = dm_crtc_state->crc_window.x_end; | ||
| 166 | tmp_window.windowb_y_end = dm_crtc_state->crc_window.y_end; | ||
| 167 | } | ||
| 168 | |||
| 169 | if (!dc_stream_configure_crc(stream_state->ctx->dc, | 117 | if (!dc_stream_configure_crc(stream_state->ctx->dc, |
| 170 | stream_state, crc_window, enable, enable)) { | 118 | stream_state, NULL, enable, enable)) { |
| 171 | ret = -EINVAL; | 119 | ret = -EINVAL; |
| 172 | goto unlock; | 120 | goto unlock; |
| 173 | } | 121 | } |
| @@ -47,9 +47,6 @@ static inline bool amdgpu_dm_is_valid_crc_source(enum amdgpu_dm_pipe_crc_source · 46 unmodified lines | |||
| 47 | 47 | ||
| 48 | /* amdgpu_dm_crc.c */ | 48 | /* amdgpu_dm_crc.c */ |
| 49 | #ifdef CONFIG_DEBUG_FS | 49 | #ifdef CONFIG_DEBUG_FS |
| 50 | bool amdgpu_dm_crc_window_is_default(struct dm_crtc_state *dm_crtc_state); | ||
| 51 | bool amdgpu_dm_crc_window_changed(struct dm_crtc_state *dm_new_crtc_state, | ||
| 52 | struct dm_crtc_state *dm_old_crtc_state); | ||
| 53 | int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc, | 50 | int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc, |
| 54 | struct dm_crtc_state *dm_crtc_state, | 51 | struct dm_crtc_state *dm_crtc_state, |
| 55 | enum amdgpu_dm_pipe_crc_source source); | 52 | enum amdgpu_dm_pipe_crc_source source); |
| @@ -833,6 +833,9 @@ bool compute_mst_dsc_configs_for_state(struct drm_atomic_state *state, · 832 unmodified lines | |||
| 833 | if (computed_streams[i]) | 833 | if (computed_streams[i]) |
| 834 | continue; | 834 | continue; |
| 835 | 835 | ||
| 836 | if (dcn20_remove_stream_from_ctx(stream->ctx->dc, dc_state, stream) != DC_OK) | ||
| 837 | return false; | ||
| 838 | |||
| 836 | mutex_lock(&aconnector->mst_mgr.lock); | 839 | mutex_lock(&aconnector->mst_mgr.lock); |
| 837 | if (!compute_mst_dsc_configs_for_link(state, dc_state, stream->link)) { | 840 | if (!compute_mst_dsc_configs_for_link(state, dc_state, stream->link)) { |
| 838 | mutex_unlock(&aconnector->mst_mgr.lock); | 841 | mutex_unlock(&aconnector->mst_mgr.lock); |
| @@ -850,7 +853,8 @@ bool compute_mst_dsc_configs_for_state(struct drm_atomic_state *state, · 11 unmodified lines | |||
| 850 | stream = dc_state->streams[i]; | 853 | stream = dc_state->streams[i]; |
| 851 | 854 | ||
| 852 | if (stream->timing.flags.DSC == 1) | 855 | if (stream->timing.flags.DSC == 1) |
| 853 | dc_stream_add_dsc_to_resource(stream->ctx->dc, dc_state, stream); | 856 | if (dc_stream_add_dsc_to_resource(stream->ctx->dc, dc_state, stream) != DC_OK) |
| 857 | return false; | ||
| 854 | } | 858 | } |
| 855 | 859 | ||
| 856 | return true; | 860 | return true; |
| @@ -33,10 +33,6 @@ ifdef CONFIG_PPC64 · 32 unmodified lines | |||
| 33 | calcs_ccflags := -mhard-float -maltivec | 33 | calcs_ccflags := -mhard-float -maltivec |
| 34 | endif | 34 | endif |
| 35 | 35 | ||
| 36 | ifdef CONFIG_ARM64 | ||
| 37 | calcs_rcflags := -mgeneral-regs-only | ||
| 38 | endif | ||
| 39 | |||
| 40 | ifdef CONFIG_CC_IS_GCC | 36 | ifdef CONFIG_CC_IS_GCC |
| 41 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 37 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 42 | IS_OLD_GCC = 1 | 38 | IS_OLD_GCC = 1 |
| @@ -104,13 +104,6 @@ ifdef CONFIG_PPC64 · 103 unmodified lines | |||
| 104 | CFLAGS_$(AMDDALPATH)/dc/clk_mgr/dcn21/rn_clk_mgr.o := $(call cc-option,-mno-gnu-attribute) | 104 | CFLAGS_$(AMDDALPATH)/dc/clk_mgr/dcn21/rn_clk_mgr.o := $(call cc-option,-mno-gnu-attribute) |
| 105 | endif | 105 | endif |
| 106 | 106 | ||
| 107 | # prevent build errors: | ||
| 108 | # ...: '-mgeneral-regs-only' is incompatible with the use of floating-point types | ||
| 109 | # this file is unused on arm64, just like on ppc64 | ||
| 110 | ifdef CONFIG_ARM64 | ||
| 111 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/clk_mgr/dcn21/rn_clk_mgr.o := -mgeneral-regs-only | ||
| 112 | endif | ||
| 113 | |||
| 114 | AMD_DAL_CLK_MGR_DCN21 = $(addprefix $(AMDDALPATH)/dc/clk_mgr/dcn21/,$(CLK_MGR_DCN21)) | 107 | AMD_DAL_CLK_MGR_DCN21 = $(addprefix $(AMDDALPATH)/dc/clk_mgr/dcn21/,$(CLK_MGR_DCN21)) |
| 115 | 108 | ||
| 116 | AMD_DISPLAY_FILES += $(AMD_DAL_CLK_MGR_DCN21) | 109 | AMD_DISPLAY_FILES += $(AMD_DAL_CLK_MGR_DCN21) |
| @@ -125,13 +118,6 @@ ifdef CONFIG_PPC64 · 8 unmodified lines | |||
| 125 | CFLAGS_$(AMDDALPATH)/dc/clk_mgr/dcn30/dcn30_clk_mgr.o := $(call cc-option,-mno-gnu-attribute) | 118 | CFLAGS_$(AMDDALPATH)/dc/clk_mgr/dcn30/dcn30_clk_mgr.o := $(call cc-option,-mno-gnu-attribute) |
| 126 | endif | 119 | endif |
| 127 | 120 | ||
| 128 | # prevent build errors: | ||
| 129 | # ...: '-mgeneral-regs-only' is incompatible with the use of floating-point types | ||
| 130 | # this file is unused on arm64, just like on ppc64 | ||
| 131 | ifdef CONFIG_ARM64 | ||
| 132 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/clk_mgr/dcn30/dcn30_clk_mgr.o := -mgeneral-regs-only | ||
| 133 | endif | ||
| 134 | |||
| 135 | AMD_DAL_CLK_MGR_DCN30 = $(addprefix $(AMDDALPATH)/dc/clk_mgr/dcn30/,$(CLK_MGR_DCN30)) | 121 | AMD_DAL_CLK_MGR_DCN30 = $(addprefix $(AMDDALPATH)/dc/clk_mgr/dcn30/,$(CLK_MGR_DCN30)) |
| 136 | 122 | ||
| 137 | AMD_DISPLAY_FILES += $(AMD_DAL_CLK_MGR_DCN30) | 123 | AMD_DISPLAY_FILES += $(AMD_DAL_CLK_MGR_DCN30) |
| @@ -146,13 +132,6 @@ ifdef CONFIG_PPC64 · 8 unmodified lines | |||
| 146 | CFLAGS_$(AMDDALPATH)/dc/clk_mgr/dcn301/vg_clk_mgr.o := $(call cc-option,-mno-gnu-attribute) | 132 | CFLAGS_$(AMDDALPATH)/dc/clk_mgr/dcn301/vg_clk_mgr.o := $(call cc-option,-mno-gnu-attribute) |
| 147 | endif | 133 | endif |
| 148 | 134 | ||
| 149 | # prevent build errors: | ||
| 150 | # ...: '-mgeneral-regs-only' is incompatible with the use of floating-point types | ||
| 151 | # this file is unused on arm64, just like on ppc64 | ||
| 152 | ifdef CONFIG_ARM64 | ||
| 153 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/clk_mgr/dcn301/vg_clk_mgr.o := -mgeneral-regs-only | ||
| 154 | endif | ||
| 155 | |||
| 156 | AMD_DAL_CLK_MGR_DCN301 = $(addprefix $(AMDDALPATH)/dc/clk_mgr/dcn301/,$(CLK_MGR_DCN301)) | 135 | AMD_DAL_CLK_MGR_DCN301 = $(addprefix $(AMDDALPATH)/dc/clk_mgr/dcn301/,$(CLK_MGR_DCN301)) |
| 157 | 136 | ||
| 158 | AMD_DISPLAY_FILES += $(AMD_DAL_CLK_MGR_DCN301) | 137 | AMD_DISPLAY_FILES += $(AMD_DAL_CLK_MGR_DCN301) |
| @@ -251,6 +251,7 @@ static void dcn3_update_clocks(struct clk_mgr *clk_mgr_base, · 250 unmodified lines | |||
| 251 | struct dmcu *dmcu = clk_mgr_base->ctx->dc->res_pool->dmcu; | 251 | struct dmcu *dmcu = clk_mgr_base->ctx->dc->res_pool->dmcu; |
| 252 | bool force_reset = false; | 252 | bool force_reset = false; |
| 253 | bool update_uclk = false; | 253 | bool update_uclk = false; |
| 254 | bool p_state_change_support; | ||
| 254 | 255 | ||
| 255 | if (dc->work_arounds.skip_clock_update || !clk_mgr->smu_present) | 256 | if (dc->work_arounds.skip_clock_update || !clk_mgr->smu_present) |
| 256 | return; | 257 | return; |
| @@ -291,8 +292,9 @@ static void dcn3_update_clocks(struct clk_mgr *clk_mgr_base, · 34 unmodified lines | |||
| 291 | clk_mgr_base->clks.socclk_khz = new_clocks->socclk_khz; | 292 | clk_mgr_base->clks.socclk_khz = new_clocks->socclk_khz; |
| 292 | 293 | ||
| 293 | clk_mgr_base->clks.prev_p_state_change_support = clk_mgr_base->clks.p_state_change_support; | 294 | clk_mgr_base->clks.prev_p_state_change_support = clk_mgr_base->clks.p_state_change_support; |
| 294 | if (should_update_pstate_support(safe_to_lower, new_clocks->p_state_change_support, clk_mgr_base->clks.p_state_change_support)) { | 295 | p_state_change_support = new_clocks->p_state_change_support || (display_count == 0); |
| 295 | clk_mgr_base->clks.p_state_change_support = new_clocks->p_state_change_support; | 296 | if (should_update_pstate_support(safe_to_lower, p_state_change_support, clk_mgr_base->clks.p_state_change_support)) { |
| 297 | clk_mgr_base->clks.p_state_change_support = p_state_change_support; | ||
| 296 | 298 | ||
| 297 | /* to disable P-State switching, set UCLK min = max */ | 299 | /* to disable P-State switching, set UCLK min = max */ |
| 298 | if (!clk_mgr_base->clks.p_state_change_support) | 300 | if (!clk_mgr_base->clks.p_state_change_support) |
| @@ -2679,8 +2679,7 @@ void dc_commit_updates_for_stream(struct dc *dc, · 2678 unmodified lines | |||
| 2679 | struct dc_surface_update *srf_updates, | 2679 | struct dc_surface_update *srf_updates, |
| 2680 | int surface_count, | 2680 | int surface_count, |
| 2681 | struct dc_stream_state *stream, | 2681 | struct dc_stream_state *stream, |
| 2682 | struct dc_stream_update *stream_update, | 2682 | struct dc_stream_update *stream_update) |
| 2683 | struct dc_state *state) | ||
| 2684 | { | 2683 | { |
| 2685 | const struct dc_stream_status *stream_status; | 2684 | const struct dc_stream_status *stream_status; |
| 2686 | enum surface_update_type update_type; | 2685 | enum surface_update_type update_type; |
| @@ -2699,6 +2698,12 @@ void dc_commit_updates_for_stream(struct dc *dc, · 12 unmodified lines | |||
| 2699 | 2698 | ||
| 2700 | 2699 | ||
| 2701 | if (update_type >= UPDATE_TYPE_FULL) { | 2700 | if (update_type >= UPDATE_TYPE_FULL) { |
| 2701 | struct dc_plane_state *new_planes[MAX_SURFACES]; | ||
| 2702 | |||
| 2703 | memset(new_planes, 0, sizeof(new_planes)); | ||
| 2704 | |||
| 2705 | for (i = 0; i < surface_count; i++) | ||
| 2706 | new_planes[i] = srf_updates[i].surface; | ||
| 2702 | 2707 | ||
| 2703 | /* initialize scratch memory for building context */ | 2708 | /* initialize scratch memory for building context */ |
| 2704 | context = dc_create_state(dc); | 2709 | context = dc_create_state(dc); |
| @@ -2707,15 +2712,21 @@ void dc_commit_updates_for_stream(struct dc *dc, · 2 unmodified lines | |||
| 2707 | return; | 2712 | return; |
| 2708 | } | 2713 | } |
| 2709 | 2714 | ||
| 2710 | dc_resource_state_copy_construct(state, context); | 2715 | dc_resource_state_copy_construct( |
| 2716 | dc->current_state, context); | ||
| 2711 | 2717 | ||
| 2712 | for (i = 0; i < dc->res_pool->pipe_count; i++) { | 2718 | /*remove old surfaces from context */ |
| 2713 | struct pipe_ctx *new_pipe = &context->res_ctx.pipe_ctx[i]; | 2719 | if (!dc_rem_all_planes_for_stream(dc, stream, context)) { |
| 2714 | struct pipe_ctx *old_pipe = &dc->current_state->res_ctx.pipe_ctx[i]; | 2720 | DC_ERROR("Failed to remove streams for new validate context!\n"); |
| 2721 | return; | ||
| 2722 | } | ||
| 2715 | 2723 | ||
| 2716 | if (new_pipe->plane_state && new_pipe->plane_state != old_pipe->plane_state) | 2724 | /* add surface to context */ |
| 2717 | new_pipe->plane_state->force_full_update = true; | 2725 | if (!dc_add_all_planes_for_stream(dc, stream, new_planes, surface_count, context)) { |
| 2726 | DC_ERROR("Failed to add streams for new validate context!\n"); | ||
| 2727 | return; | ||
| 2718 | } | 2728 | } |
| 2729 | |||
| 2719 | } | 2730 | } |
| 2720 | 2731 | ||
| 2721 | 2732 | ||
| @@ -2487,9 +2487,14 @@ enum dc_status dc_link_validate_mode_timing( · 2486 unmodified lines | |||
| 2487 | static struct abm *get_abm_from_stream_res(const struct dc_link *link) | 2487 | static struct abm *get_abm_from_stream_res(const struct dc_link *link) |
| 2488 | { | 2488 | { |
| 2489 | int i; | 2489 | int i; |
| 2490 | struct dc *dc = link->ctx->dc; | 2490 | struct dc *dc = NULL; |
| 2491 | struct abm *abm = NULL; | 2491 | struct abm *abm = NULL; |
| 2492 | 2492 | ||
| 2493 | if (!link || !link->ctx) | ||
| 2494 | return NULL; | ||
| 2495 | |||
| 2496 | dc = link->ctx->dc; | ||
| 2497 | |||
| 2493 | for (i = 0; i < MAX_PIPES; i++) { | 2498 | for (i = 0; i < MAX_PIPES; i++) { |
| 2494 | struct pipe_ctx pipe_ctx = dc->current_state->res_ctx.pipe_ctx[i]; | 2499 | struct pipe_ctx pipe_ctx = dc->current_state->res_ctx.pipe_ctx[i]; |
| 2495 | struct dc_stream_state *stream = pipe_ctx.stream; | 2500 | struct dc_stream_state *stream = pipe_ctx.stream; |
| @@ -892,13 +892,13 @@ static uint32_t translate_training_aux_read_interval(uint32_t dpcd_aux_read_inte · 891 unmodified lines | |||
| 892 | 892 | ||
| 893 | switch (dpcd_aux_read_interval) { | 893 | switch (dpcd_aux_read_interval) { |
| 894 | case 0x01: | 894 | case 0x01: |
| 895 | aux_rd_interval_us = 400; | 895 | aux_rd_interval_us = 4000; |
| 896 | break; | 896 | break; |
| 897 | case 0x02: | 897 | case 0x02: |
| 898 | aux_rd_interval_us = 4000; | 898 | aux_rd_interval_us = 8000; |
| 899 | break; | 899 | break; |
| 900 | case 0x03: | 900 | case 0x03: |
| 901 | aux_rd_interval_us = 8000; | 901 | aux_rd_interval_us = 12000; |
| 902 | break; | 902 | break; |
| 903 | case 0x04: | 903 | case 0x04: |
| 904 | aux_rd_interval_us = 16000; | 904 | aux_rd_interval_us = 16000; |
| @@ -2399,6 +2399,9 @@ static bool decide_dp_link_settings(struct dc_link *link, struct dc_link_setting · 1494 unmodified lines | |||
| 2399 | initial_link_setting; | 2399 | initial_link_setting; |
| 2400 | uint32_t link_bw; | 2400 | uint32_t link_bw; |
| 2401 | 2401 | ||
| 2402 | if (req_bw > dc_link_bandwidth_kbps(link, &link->verified_link_cap)) | ||
| 2403 | return false; | ||
| 2404 | |||
| 2402 | /* search for the minimum link setting that: | 2405 | /* search for the minimum link setting that: |
| 2403 | * 1. is supported according to the link training result | 2406 | * 1. is supported according to the link training result |
| 2404 | * 2. could support the b/w requested by the timing | 2407 | * 2. could support the b/w requested by the timing |
| @@ -3045,14 +3048,14 @@ bool dc_link_handle_hpd_rx_irq(struct dc_link *link, union hpd_irq_data *out_hpd · 640 unmodified lines | |||
| 3045 | for (i = 0; i < MAX_PIPES; i++) { | 3048 | for (i = 0; i < MAX_PIPES; i++) { |
| 3046 | pipe_ctx = &link->dc->current_state->res_ctx.pipe_ctx[i]; | 3049 | pipe_ctx = &link->dc->current_state->res_ctx.pipe_ctx[i]; |
| 3047 | if (pipe_ctx && pipe_ctx->stream && !pipe_ctx->stream->dpms_off && | 3050 | if (pipe_ctx && pipe_ctx->stream && !pipe_ctx->stream->dpms_off && |
| 3048 | pipe_ctx->stream->link == link) | 3051 | pipe_ctx->stream->link == link && !pipe_ctx->prev_odm_pipe) |
| 3049 | core_link_disable_stream(pipe_ctx); | 3052 | core_link_disable_stream(pipe_ctx); |
| 3050 | } | 3053 | } |
| 3051 | 3054 | ||
| 3052 | for (i = 0; i < MAX_PIPES; i++) { | 3055 | for (i = 0; i < MAX_PIPES; i++) { |
| 3053 | pipe_ctx = &link->dc->current_state->res_ctx.pipe_ctx[i]; | 3056 | pipe_ctx = &link->dc->current_state->res_ctx.pipe_ctx[i]; |
| 3054 | if (pipe_ctx && pipe_ctx->stream && !pipe_ctx->stream->dpms_off && | 3057 | if (pipe_ctx && pipe_ctx->stream && !pipe_ctx->stream->dpms_off && |
| 3055 | pipe_ctx->stream->link == link) | 3058 | pipe_ctx->stream->link == link && !pipe_ctx->prev_odm_pipe) |
| 3056 | core_link_enable_stream(link->dc->current_state, pipe_ctx); | 3059 | core_link_enable_stream(link->dc->current_state, pipe_ctx); |
| 3057 | } | 3060 | } |
| 3058 | 3061 | ||
| @@ -3992,7 +3995,7 @@ bool dc_link_dp_set_test_pattern( · 933 unmodified lines | |||
| 3992 | unsigned int cust_pattern_size) | 3995 | unsigned int cust_pattern_size) |
| 3993 | { | 3996 | { |
| 3994 | struct pipe_ctx *pipes = link->dc->current_state->res_ctx.pipe_ctx; | 3997 | struct pipe_ctx *pipes = link->dc->current_state->res_ctx.pipe_ctx; |
| 3995 | struct pipe_ctx *pipe_ctx = &pipes[0]; | 3998 | struct pipe_ctx *pipe_ctx = NULL; |
| 3996 | unsigned int lane; | 3999 | unsigned int lane; |
| 3997 | unsigned int i; | 4000 | unsigned int i; |
| 3998 | unsigned char link_qual_pattern[LANE_COUNT_DP_MAX] = {0}; | 4001 | unsigned char link_qual_pattern[LANE_COUNT_DP_MAX] = {0}; |
| @@ -4002,12 +4005,18 @@ bool dc_link_dp_set_test_pattern( · 3 unmodified lines | |||
| 4002 | memset(&training_pattern, 0, sizeof(training_pattern)); | 4005 | memset(&training_pattern, 0, sizeof(training_pattern)); |
| 4003 | 4006 | ||
| 4004 | for (i = 0; i < MAX_PIPES; i++) { | 4007 | for (i = 0; i < MAX_PIPES; i++) { |
| 4008 | if (pipes[i].stream == NULL) | ||
| 4009 | continue; | ||
| 4010 | |||
| 4005 | if (pipes[i].stream->link == link && !pipes[i].top_pipe && !pipes[i].prev_odm_pipe) { | 4011 | if (pipes[i].stream->link == link && !pipes[i].top_pipe && !pipes[i].prev_odm_pipe) { |
| 4006 | pipe_ctx = &pipes[i]; | 4012 | pipe_ctx = &pipes[i]; |
| 4007 | break; | 4013 | break; |
| 4008 | } | 4014 | } |
| 4009 | } | 4015 | } |
| 4010 | 4016 | ||
| 4017 | if (pipe_ctx == NULL) | ||
| 4018 | return false; | ||
| 4019 | |||
| 4011 | /* Reset CRTC Test Pattern if it is currently running and request is VideoMode */ | 4020 | /* Reset CRTC Test Pattern if it is currently running and request is VideoMode */ |
| 4012 | if (link->test_pattern_enabled && test_pattern == | 4021 | if (link->test_pattern_enabled && test_pattern == |
| 4013 | DP_TEST_PATTERN_VIDEO_MODE) { | 4022 | DP_TEST_PATTERN_VIDEO_MODE) { |
| @@ -283,8 +283,7 @@ void dc_commit_updates_for_stream(struct dc *dc, · 282 unmodified lines | |||
| 283 | struct dc_surface_update *srf_updates, | 283 | struct dc_surface_update *srf_updates, |
| 284 | int surface_count, | 284 | int surface_count, |
| 285 | struct dc_stream_state *stream, | 285 | struct dc_stream_state *stream, |
| 286 | struct dc_stream_update *stream_update, | 286 | struct dc_stream_update *stream_update); |
| 287 | struct dc_state *state); | ||
| 288 | /* | 287 | /* |
| 289 | * Log the current stream state. | 288 | * Log the current stream state. |
| 290 | */ | 289 | */ |
| @@ -31,11 +31,4 @@ DCN10 = dcn10_init.o dcn10_resource.o dcn10_ipp.o dcn10_hw_sequencer.o \ · 30 unmodified lines | |||
| 31 | 31 | ||
| 32 | AMD_DAL_DCN10 = $(addprefix $(AMDDALPATH)/dc/dcn10/,$(DCN10)) | 32 | AMD_DAL_DCN10 = $(addprefix $(AMDDALPATH)/dc/dcn10/,$(DCN10)) |
| 33 | 33 | ||
| 34 | # fix: | ||
| 35 | # ...: '-mgeneral-regs-only' is incompatible with the use of floating-point types | ||
| 36 | # aarch64 does not support soft-float, so use hard-float and handle this in code | ||
| 37 | ifdef CONFIG_ARM64 | ||
| 38 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/dcn10/dcn10_resource.o := -mgeneral-regs-only | ||
| 39 | endif | ||
| 40 | |||
| 41 | AMD_DISPLAY_FILES += $(AMD_DAL_DCN10) | 34 | AMD_DISPLAY_FILES += $(AMD_DAL_DCN10) |
| @@ -647,8 +647,13 @@ static void power_on_plane( · 646 unmodified lines | |||
| 647 | if (REG(DC_IP_REQUEST_CNTL)) { | 647 | if (REG(DC_IP_REQUEST_CNTL)) { |
| 648 | REG_SET(DC_IP_REQUEST_CNTL, 0, | 648 | REG_SET(DC_IP_REQUEST_CNTL, 0, |
| 649 | IP_REQUEST_EN, 1); | 649 | IP_REQUEST_EN, 1); |
| 650 | hws->funcs.dpp_pg_control(hws, plane_id, true); | 650 | |
| 651 | hws->funcs.hubp_pg_control(hws, plane_id, true); | 651 | if (hws->funcs.dpp_pg_control) |
| 652 | hws->funcs.dpp_pg_control(hws, plane_id, true); | ||
| 653 | |||
| 654 | if (hws->funcs.hubp_pg_control) | ||
| 655 | hws->funcs.hubp_pg_control(hws, plane_id, true); | ||
| 656 | |||
| 652 | REG_SET(DC_IP_REQUEST_CNTL, 0, | 657 | REG_SET(DC_IP_REQUEST_CNTL, 0, |
| 653 | IP_REQUEST_EN, 0); | 658 | IP_REQUEST_EN, 0); |
| 654 | DC_LOG_DEBUG( | 659 | DC_LOG_DEBUG( |
| @@ -1082,8 +1087,13 @@ void dcn10_plane_atomic_power_down(struct dc *dc, · 427 unmodified lines | |||
| 1082 | if (REG(DC_IP_REQUEST_CNTL)) { | 1087 | if (REG(DC_IP_REQUEST_CNTL)) { |
| 1083 | REG_SET(DC_IP_REQUEST_CNTL, 0, | 1088 | REG_SET(DC_IP_REQUEST_CNTL, 0, |
| 1084 | IP_REQUEST_EN, 1); | 1089 | IP_REQUEST_EN, 1); |
| 1085 | hws->funcs.dpp_pg_control(hws, dpp->inst, false); | 1090 | |
| 1086 | hws->funcs.hubp_pg_control(hws, hubp->inst, false); | 1091 | if (hws->funcs.dpp_pg_control) |
| 1092 | hws->funcs.dpp_pg_control(hws, dpp->inst, false); | ||
| 1093 | |||
| 1094 | if (hws->funcs.hubp_pg_control) | ||
| 1095 | hws->funcs.hubp_pg_control(hws, hubp->inst, false); | ||
| 1096 | |||
| 1087 | dpp->funcs->dpp_reset(dpp); | 1097 | dpp->funcs->dpp_reset(dpp); |
| 1088 | REG_SET(DC_IP_REQUEST_CNTL, 0, | 1098 | REG_SET(DC_IP_REQUEST_CNTL, 0, |
| 1089 | IP_REQUEST_EN, 0); | 1099 | IP_REQUEST_EN, 0); |
| @@ -470,7 +470,7 @@ void mpc1_cursor_lock(struct mpc *mpc, int opp_id, bool lock) · 469 unmodified lines | |||
| 470 | unsigned int mpc1_get_mpc_out_mux(struct mpc *mpc, int opp_id) | 470 | unsigned int mpc1_get_mpc_out_mux(struct mpc *mpc, int opp_id) |
| 471 | { | 471 | { |
| 472 | struct dcn10_mpc *mpc10 = TO_DCN10_MPC(mpc); | 472 | struct dcn10_mpc *mpc10 = TO_DCN10_MPC(mpc); |
| 473 | uint32_t val = 0; | 473 | uint32_t val = 0xf; |
| 474 | 474 | ||
| 475 | if (opp_id < MAX_OPP && REG(MUX[opp_id])) | 475 | if (opp_id < MAX_OPP && REG(MUX[opp_id])) |
| 476 | REG_GET(MUX[opp_id], MPC_OUT_MUX, &val); | 476 | REG_GET(MUX[opp_id], MPC_OUT_MUX, &val); |
| @@ -608,8 +608,8 @@ static const struct dc_debug_options debug_defaults_drv = { · 607 unmodified lines | |||
| 608 | .disable_pplib_clock_request = false, | 608 | .disable_pplib_clock_request = false, |
| 609 | .disable_pplib_wm_range = false, | 609 | .disable_pplib_wm_range = false, |
| 610 | .pplib_wm_report_mode = WM_REPORT_DEFAULT, | 610 | .pplib_wm_report_mode = WM_REPORT_DEFAULT, |
| 611 | .pipe_split_policy = MPC_SPLIT_DYNAMIC, | 611 | .pipe_split_policy = MPC_SPLIT_AVOID, |
| 612 | .force_single_disp_pipe_split = true, | 612 | .force_single_disp_pipe_split = false, |
| 613 | .disable_dcc = DCC_ENABLE, | 613 | .disable_dcc = DCC_ENABLE, |
| 614 | .voltage_align_fclk = true, | 614 | .voltage_align_fclk = true, |
| 615 | .disable_stereo_support = true, | 615 | .disable_stereo_support = true, |
| @@ -1534,15 +1534,8 @@ static bool dcn10_resource_construct( · 918 unmodified lines | |||
| 1534 | memcpy(dc->dcn_ip, &dcn10_ip_defaults, sizeof(dcn10_ip_defaults)); | 1534 | memcpy(dc->dcn_ip, &dcn10_ip_defaults, sizeof(dcn10_ip_defaults)); |
| 1535 | memcpy(dc->dcn_soc, &dcn10_soc_defaults, sizeof(dcn10_soc_defaults)); | 1535 | memcpy(dc->dcn_soc, &dcn10_soc_defaults, sizeof(dcn10_soc_defaults)); |
| 1536 | 1536 | ||
| 1537 | #if defined(CONFIG_ARM64) | ||
| 1538 | /* Aarch64 does not support -msoft-float/-mfloat-abi=soft */ | ||
| 1539 | DC_FP_START(); | ||
| 1540 | dcn10_resource_construct_fp(dc); | ||
| 1541 | DC_FP_END(); | ||
| 1542 | #else | ||
| 1543 | /* Other architectures we build for build this with soft-float */ | 1537 | /* Other architectures we build for build this with soft-float */ |
| 1544 | dcn10_resource_construct_fp(dc); | 1538 | dcn10_resource_construct_fp(dc); |
| 1545 | #endif | ||
| 1546 | 1539 | ||
| 1547 | pool->base.pp_smu = dcn10_pp_smu_create(ctx); | 1540 | pool->base.pp_smu = dcn10_pp_smu_create(ctx); |
| 1548 | 1541 | ||
| @@ -17,10 +17,6 @@ ifdef CONFIG_PPC64 · 16 unmodified lines | |||
| 17 | CFLAGS_$(AMDDALPATH)/dc/dcn20/dcn20_resource.o := -mhard-float -maltivec | 17 | CFLAGS_$(AMDDALPATH)/dc/dcn20/dcn20_resource.o := -mhard-float -maltivec |
| 18 | endif | 18 | endif |
| 19 | 19 | ||
| 20 | ifdef CONFIG_ARM64 | ||
| 21 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/dcn20/dcn20_resource.o := -mgeneral-regs-only | ||
| 22 | endif | ||
| 23 | |||
| 24 | ifdef CONFIG_CC_IS_GCC | 20 | ifdef CONFIG_CC_IS_GCC |
| 25 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 21 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 26 | IS_OLD_GCC = 1 | 22 | IS_OLD_GCC = 1 |
| @@ -1062,8 +1062,13 @@ static void dcn20_power_on_plane( · 1061 unmodified lines | |||
| 1062 | if (REG(DC_IP_REQUEST_CNTL)) { | 1062 | if (REG(DC_IP_REQUEST_CNTL)) { |
| 1063 | REG_SET(DC_IP_REQUEST_CNTL, 0, | 1063 | REG_SET(DC_IP_REQUEST_CNTL, 0, |
| 1064 | IP_REQUEST_EN, 1); | 1064 | IP_REQUEST_EN, 1); |
| 1065 | dcn20_dpp_pg_control(hws, pipe_ctx->plane_res.dpp->inst, true); | 1065 | |
| 1066 | dcn20_hubp_pg_control(hws, pipe_ctx->plane_res.hubp->inst, true); | 1066 | if (hws->funcs.dpp_pg_control) |
| 1067 | hws->funcs.dpp_pg_control(hws, pipe_ctx->plane_res.dpp->inst, true); | ||
| 1068 | |||
| 1069 | if (hws->funcs.hubp_pg_control) | ||
| 1070 | hws->funcs.hubp_pg_control(hws, pipe_ctx->plane_res.hubp->inst, true); | ||
| 1071 | |||
| 1067 | REG_SET(DC_IP_REQUEST_CNTL, 0, | 1072 | REG_SET(DC_IP_REQUEST_CNTL, 0, |
| 1068 | IP_REQUEST_EN, 0); | 1073 | IP_REQUEST_EN, 0); |
| 1069 | DC_LOG_DEBUG( | 1074 | DC_LOG_DEBUG( |
| @@ -297,8 +297,8 @@ static struct _vcs_dpi_soc_bounding_box_st dcn2_0_soc = { · 296 unmodified lines | |||
| 297 | }, | 297 | }, |
| 298 | }, | 298 | }, |
| 299 | .num_states = 5, | 299 | .num_states = 5, |
| 300 | .sr_exit_time_us = 11.6, | 300 | .sr_exit_time_us = 8.6, |
| 301 | .sr_enter_plus_exit_time_us = 13.9, | 301 | .sr_enter_plus_exit_time_us = 10.9, |
| 302 | .urgent_latency_us = 4.0, | 302 | .urgent_latency_us = 4.0, |
| 303 | .urgent_latency_pixel_data_only_us = 4.0, | 303 | .urgent_latency_pixel_data_only_us = 4.0, |
| 304 | .urgent_latency_pixel_mixed_with_vm_data_us = 4.0, | 304 | .urgent_latency_pixel_mixed_with_vm_data_us = 4.0, |
| @@ -2517,8 +2517,7 @@ struct pipe_ctx *dcn20_find_secondary_pipe(struct dc *dc, · 2212 unmodified lines | |||
| 2517 | * if this primary pipe has a bottom pipe in prev. state | 2517 | * if this primary pipe has a bottom pipe in prev. state |
| 2518 | * and if the bottom pipe is still available (which it should be), | 2518 | * and if the bottom pipe is still available (which it should be), |
| 2519 | * pick that pipe as secondary | 2519 | * pick that pipe as secondary |
| 2520 | * Same logic applies for ODM pipes. Since mpo is not allowed with odm | 2520 | * Same logic applies for ODM pipes |
| 2521 | * check in else case. | ||
| 2522 | */ | 2521 | */ |
| 2523 | if (dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].bottom_pipe) { | 2522 | if (dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].bottom_pipe) { |
| 2524 | preferred_pipe_idx = dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].bottom_pipe->pipe_idx; | 2523 | preferred_pipe_idx = dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].bottom_pipe->pipe_idx; |
| @@ -2526,7 +2525,9 @@ struct pipe_ctx *dcn20_find_secondary_pipe(struct dc *dc, · 1 unmodified line | |||
| 2526 | secondary_pipe = &res_ctx->pipe_ctx[preferred_pipe_idx]; | 2525 | secondary_pipe = &res_ctx->pipe_ctx[preferred_pipe_idx]; |
| 2527 | secondary_pipe->pipe_idx = preferred_pipe_idx; | 2526 | secondary_pipe->pipe_idx = preferred_pipe_idx; |
| 2528 | } | 2527 | } |
| 2529 | } else if (dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].next_odm_pipe) { | 2528 | } |
| 2529 | if (secondary_pipe == NULL && | ||
| 2530 | dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].next_odm_pipe) { | ||
| 2530 | preferred_pipe_idx = dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].next_odm_pipe->pipe_idx; | 2531 | preferred_pipe_idx = dc->current_state->res_ctx.pipe_ctx[primary_pipe->pipe_idx].next_odm_pipe->pipe_idx; |
| 2531 | if (res_ctx->pipe_ctx[preferred_pipe_idx].stream == NULL) { | 2532 | if (res_ctx->pipe_ctx[preferred_pipe_idx].stream == NULL) { |
| 2532 | secondary_pipe = &res_ctx->pipe_ctx[preferred_pipe_idx]; | 2533 | secondary_pipe = &res_ctx->pipe_ctx[preferred_pipe_idx]; |
| @@ -13,10 +13,6 @@ ifdef CONFIG_PPC64 · 12 unmodified lines | |||
| 13 | CFLAGS_$(AMDDALPATH)/dc/dcn21/dcn21_resource.o := -mhard-float -maltivec | 13 | CFLAGS_$(AMDDALPATH)/dc/dcn21/dcn21_resource.o := -mhard-float -maltivec |
| 14 | endif | 14 | endif |
| 15 | 15 | ||
| 16 | ifdef CONFIG_ARM64 | ||
| 17 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/dcn21/dcn21_resource.o := -mgeneral-regs-only | ||
| 18 | endif | ||
| 19 | |||
| 20 | ifdef CONFIG_CC_IS_GCC | 16 | ifdef CONFIG_CC_IS_GCC |
| 21 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 17 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 22 | IS_OLD_GCC = 1 | 18 | IS_OLD_GCC = 1 |
| @@ -296,7 +296,7 @@ struct _vcs_dpi_soc_bounding_box_st dcn2_1_soc = { · 295 unmodified lines | |||
| 296 | .num_banks = 8, | 296 | .num_banks = 8, |
| 297 | .num_chans = 4, | 297 | .num_chans = 4, |
| 298 | .vmm_page_size_bytes = 4096, | 298 | .vmm_page_size_bytes = 4096, |
| 299 | .dram_clock_change_latency_us = 23.84, | 299 | .dram_clock_change_latency_us = 11.72, |
| 300 | .return_bus_width_bytes = 64, | 300 | .return_bus_width_bytes = 64, |
| 301 | .dispclk_dppclk_vco_speed_mhz = 3600, | 301 | .dispclk_dppclk_vco_speed_mhz = 3600, |
| 302 | .xfc_bus_transport_time_us = 4, | 302 | .xfc_bus_transport_time_us = 4, |
| @@ -906,6 +906,8 @@ enum dcn20_clk_src_array_id { · 603 unmodified lines | |||
| 906 | DCN20_CLK_SRC_PLL0, | 906 | DCN20_CLK_SRC_PLL0, |
| 907 | DCN20_CLK_SRC_PLL1, | 907 | DCN20_CLK_SRC_PLL1, |
| 908 | DCN20_CLK_SRC_PLL2, | 908 | DCN20_CLK_SRC_PLL2, |
| 909 | DCN20_CLK_SRC_PLL3, | ||
| 910 | DCN20_CLK_SRC_PLL4, | ||
| 909 | DCN20_CLK_SRC_TOTAL_DCN21 | 911 | DCN20_CLK_SRC_TOTAL_DCN21 |
| 910 | }; | 912 | }; |
| 911 | 913 | ||
| @@ -2030,6 +2032,14 @@ static bool dcn21_resource_construct( · 1118 unmodified lines | |||
| 2030 | dcn21_clock_source_create(ctx, ctx->dc_bios, | 2032 | dcn21_clock_source_create(ctx, ctx->dc_bios, |
| 2031 | CLOCK_SOURCE_COMBO_PHY_PLL2, | 2033 | CLOCK_SOURCE_COMBO_PHY_PLL2, |
| 2032 | &clk_src_regs[2], false); | 2034 | &clk_src_regs[2], false); |
| 2035 | pool->base.clock_sources[DCN20_CLK_SRC_PLL3] = | ||
| 2036 | dcn21_clock_source_create(ctx, ctx->dc_bios, | ||
| 2037 | CLOCK_SOURCE_COMBO_PHY_PLL3, | ||
| 2038 | &clk_src_regs[3], false); | ||
| 2039 | pool->base.clock_sources[DCN20_CLK_SRC_PLL4] = | ||
| 2040 | dcn21_clock_source_create(ctx, ctx->dc_bios, | ||
| 2041 | CLOCK_SOURCE_COMBO_PHY_PLL4, | ||
| 2042 | &clk_src_regs[4], false); | ||
| 2033 | 2043 | ||
| 2034 | pool->base.clk_src_count = DCN20_CLK_SRC_TOTAL_DCN21; | 2044 | pool->base.clk_src_count = DCN20_CLK_SRC_TOTAL_DCN21; |
| 2035 | 2045 | ||
| @@ -32,8 +32,8 @@ DCN30 = dcn30_init.o dcn30_hubbub.o dcn30_hubp.o dcn30_dpp.o dcn30_optc.o \ · 31 unmodified lines | |||
| 32 | 32 | ||
| 33 | 33 | ||
| 34 | ifdef CONFIG_X86 | 34 | ifdef CONFIG_X86 |
| 35 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_resource.o := -mhard-float -msse | 35 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_resource.o := -msse |
| 36 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_optc.o := -mhard-float -msse | 36 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_optc.o := -msse |
| 37 | endif | 37 | endif |
| 38 | 38 | ||
| 39 | ifdef CONFIG_PPC64 | 39 | ifdef CONFIG_PPC64 |
| @@ -41,15 +41,12 @@ CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_resource.o := -mhard-float -maltivec · 1 unmodified line | |||
| 41 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_optc.o := -mhard-float -maltivec | 41 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_optc.o := -mhard-float -maltivec |
| 42 | endif | 42 | endif |
| 43 | 43 | ||
| 44 | ifdef CONFIG_ARM64 | ||
| 45 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/dcn30/dcn30_resource.o := -mgeneral-regs-only | ||
| 46 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/dcn30/dcn30_optc.o := -mgeneral-regs-only | ||
| 47 | endif | ||
| 48 | |||
| 49 | ifdef CONFIG_CC_IS_GCC | 44 | ifdef CONFIG_CC_IS_GCC |
| 50 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 45 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 51 | IS_OLD_GCC = 1 | 46 | IS_OLD_GCC = 1 |
| 52 | endif | 47 | endif |
| 48 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_resource.o += -mhard-float | ||
| 49 | CFLAGS_$(AMDDALPATH)/dc/dcn30/dcn30_optc.o += -mhard-float | ||
| 53 | endif | 50 | endif |
| 54 | 51 | ||
| 55 | ifdef CONFIG_X86 | 52 | ifdef CONFIG_X86 |
| @@ -14,21 +14,18 @@ DCN301 = dcn301_init.o dcn301_resource.o dcn301_dccg.o \ · 13 unmodified lines | |||
| 14 | dcn301_dio_link_encoder.o dcn301_hwseq.o dcn301_panel_cntl.o dcn301_hubbub.o | 14 | dcn301_dio_link_encoder.o dcn301_hwseq.o dcn301_panel_cntl.o dcn301_hubbub.o |
| 15 | 15 | ||
| 16 | ifdef CONFIG_X86 | 16 | ifdef CONFIG_X86 |
| 17 | CFLAGS_$(AMDDALPATH)/dc/dcn301/dcn301_resource.o := -mhard-float -msse | 17 | CFLAGS_$(AMDDALPATH)/dc/dcn301/dcn301_resource.o := -msse |
| 18 | endif | 18 | endif |
| 19 | 19 | ||
| 20 | ifdef CONFIG_PPC64 | 20 | ifdef CONFIG_PPC64 |
| 21 | CFLAGS_$(AMDDALPATH)/dc/dcn301/dcn301_resource.o := -mhard-float -maltivec | 21 | CFLAGS_$(AMDDALPATH)/dc/dcn301/dcn301_resource.o := -mhard-float -maltivec |
| 22 | endif | 22 | endif |
| 23 | 23 | ||
| 24 | ifdef CONFIG_ARM64 | ||
| 25 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/dcn301/dcn301_resource.o := -mgeneral-regs-only | ||
| 26 | endif | ||
| 27 | |||
| 28 | ifdef CONFIG_CC_IS_GCC | 24 | ifdef CONFIG_CC_IS_GCC |
| 29 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 25 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 30 | IS_OLD_GCC = 1 | 26 | IS_OLD_GCC = 1 |
| 31 | endif | 27 | endif |
| 28 | CFLAGS_$(AMDDALPATH)/dc/dcn301/dcn301_resource.o += -mhard-float | ||
| 32 | endif | 29 | endif |
| 33 | 30 | ||
| 34 | ifdef CONFIG_X86 | 31 | ifdef CONFIG_X86 |
| @@ -1731,6 +1731,7 @@ static struct resource_funcs dcn301_res_pool_funcs = { · 1730 unmodified lines | |||
| 1731 | .populate_dml_pipes = dcn30_populate_dml_pipes_from_context, | 1731 | .populate_dml_pipes = dcn30_populate_dml_pipes_from_context, |
| 1732 | .acquire_idle_pipe_for_layer = dcn20_acquire_idle_pipe_for_layer, | 1732 | .acquire_idle_pipe_for_layer = dcn20_acquire_idle_pipe_for_layer, |
| 1733 | .add_stream_to_ctx = dcn30_add_stream_to_ctx, | 1733 | .add_stream_to_ctx = dcn30_add_stream_to_ctx, |
| 1734 | .add_dsc_to_stream_resource = dcn20_add_dsc_to_stream_resource, | ||
| 1734 | .remove_stream_from_ctx = dcn20_remove_stream_from_ctx, | 1735 | .remove_stream_from_ctx = dcn20_remove_stream_from_ctx, |
| 1735 | .populate_dml_writeback_from_context = dcn30_populate_dml_writeback_from_context, | 1736 | .populate_dml_writeback_from_context = dcn30_populate_dml_writeback_from_context, |
| 1736 | .set_mcif_arb_params = dcn30_set_mcif_arb_params, | 1737 | .set_mcif_arb_params = dcn30_set_mcif_arb_params, |
| @@ -13,21 +13,18 @@ · 12 unmodified lines | |||
| 13 | DCN3_02 = dcn302_init.o dcn302_hwseq.o dcn302_resource.o | 13 | DCN3_02 = dcn302_init.o dcn302_hwseq.o dcn302_resource.o |
| 14 | 14 | ||
| 15 | ifdef CONFIG_X86 | 15 | ifdef CONFIG_X86 |
| 16 | CFLAGS_$(AMDDALPATH)/dc/dcn302/dcn302_resource.o := -mhard-float -msse | 16 | CFLAGS_$(AMDDALPATH)/dc/dcn302/dcn302_resource.o := -msse |
| 17 | endif | 17 | endif |
| 18 | 18 | ||
| 19 | ifdef CONFIG_PPC64 | 19 | ifdef CONFIG_PPC64 |
| 20 | CFLAGS_$(AMDDALPATH)/dc/dcn302/dcn302_resource.o := -mhard-float -maltivec | 20 | CFLAGS_$(AMDDALPATH)/dc/dcn302/dcn302_resource.o := -mhard-float -maltivec |
| 21 | endif | 21 | endif |
| 22 | 22 | ||
| 23 | ifdef CONFIG_ARM64 | ||
| 24 | CFLAGS_REMOVE_$(AMDDALPATH)/dc/dcn302/dcn302_resource.o := -mgeneral-regs-only | ||
| 25 | endif | ||
| 26 | |||
| 27 | ifdef CONFIG_CC_IS_GCC | 23 | ifdef CONFIG_CC_IS_GCC |
| 28 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 24 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 29 | IS_OLD_GCC = 1 | 25 | IS_OLD_GCC = 1 |
| 30 | endif | 26 | endif |
| 27 | CFLAGS_$(AMDDALPATH)/dc/dcn302/dcn302_resource.o += -mhard-float | ||
| 31 | endif | 28 | endif |
| 32 | 29 | ||
| 33 | ifdef CONFIG_X86 | 30 | ifdef CONFIG_X86 |
| @@ -33,10 +33,6 @@ ifdef CONFIG_PPC64 · 32 unmodified lines | |||
| 33 | dml_ccflags := -mhard-float -maltivec | 33 | dml_ccflags := -mhard-float -maltivec |
| 34 | endif | 34 | endif |
| 35 | 35 | ||
| 36 | ifdef CONFIG_ARM64 | ||
| 37 | dml_rcflags := -mgeneral-regs-only | ||
| 38 | endif | ||
| 39 | |||
| 40 | ifdef CONFIG_CC_IS_GCC | 36 | ifdef CONFIG_CC_IS_GCC |
| 41 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 37 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 42 | IS_OLD_GCC = 1 | 38 | IS_OLD_GCC = 1 |
| @@ -2635,14 +2635,15 @@ static void dml20v2_DISPCLKDPPCLKDCFCLKDeepSleepPrefetchParametersWatermarksAndP · 2634 unmodified lines | |||
| 2635 | } | 2635 | } |
| 2636 | 2636 | ||
| 2637 | if (mode_lib->vba.DRAMClockChangeSupportsVActive && | 2637 | if (mode_lib->vba.DRAMClockChangeSupportsVActive && |
| 2638 | mode_lib->vba.MinActiveDRAMClockChangeMargin > 60 && | 2638 | mode_lib->vba.MinActiveDRAMClockChangeMargin > 60) { |
| 2639 | mode_lib->vba.PrefetchMode[mode_lib->vba.VoltageLevel][mode_lib->vba.maxMpcComb] == 0) { | ||
| 2640 | mode_lib->vba.DRAMClockChangeWatermark += 25; | 2639 | mode_lib->vba.DRAMClockChangeWatermark += 25; |
| 2641 | 2640 | ||
| 2642 | for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) { | 2641 | for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) { |
| 2643 | if (mode_lib->vba.DRAMClockChangeWatermark > | 2642 | if (mode_lib->vba.PrefetchMode[mode_lib->vba.VoltageLevel][mode_lib->vba.maxMpcComb] == 0) { |
| 2644 | dml_max(mode_lib->vba.StutterEnterPlusExitWatermark, mode_lib->vba.UrgentWatermark)) | 2643 | if (mode_lib->vba.DRAMClockChangeWatermark > |
| 2645 | mode_lib->vba.MinTTUVBlank[k] += 25; | 2644 | dml_max(mode_lib->vba.StutterEnterPlusExitWatermark, mode_lib->vba.UrgentWatermark)) |
| 2645 | mode_lib->vba.MinTTUVBlank[k] += 25; | ||
| 2646 | } | ||
| 2646 | } | 2647 | } |
| 2647 | 2648 | ||
| 2648 | mode_lib->vba.DRAMClockChangeSupport[0][0] = dm_dram_clock_change_vactive; | 2649 | mode_lib->vba.DRAMClockChangeSupport[0][0] = dm_dram_clock_change_vactive; |
| @@ -10,10 +10,6 @@ ifdef CONFIG_PPC64 · 9 unmodified lines | |||
| 10 | dsc_ccflags := -mhard-float -maltivec | 10 | dsc_ccflags := -mhard-float -maltivec |
| 11 | endif | 11 | endif |
| 12 | 12 | ||
| 13 | ifdef CONFIG_ARM64 | ||
| 14 | dsc_rcflags := -mgeneral-regs-only | ||
| 15 | endif | ||
| 16 | |||
| 17 | ifdef CONFIG_CC_IS_GCC | 13 | ifdef CONFIG_CC_IS_GCC |
| 18 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) | 14 | ifeq ($(call cc-ifversion, -lt, 0701, y), y) |
| 19 | IS_OLD_GCC = 1 | 15 | IS_OLD_GCC = 1 |
| @@ -55,10 +55,6 @@ · 54 unmodified lines | |||
| 55 | #include <asm/fpu/api.h> | 55 | #include <asm/fpu/api.h> |
| 56 | #define DC_FP_START() kernel_fpu_begin() | 56 | #define DC_FP_START() kernel_fpu_begin() |
| 57 | #define DC_FP_END() kernel_fpu_end() | 57 | #define DC_FP_END() kernel_fpu_end() |
| 58 | #elif defined(CONFIG_ARM64) | ||
| 59 | #include <asm/neon.h> | ||
| 60 | #define DC_FP_START() kernel_neon_begin() | ||
| 61 | #define DC_FP_END() kernel_neon_end() | ||
| 62 | #elif defined(CONFIG_PPC64) | 58 | #elif defined(CONFIG_PPC64) |
| 63 | #include <asm/switch_to.h> | 59 | #include <asm/switch_to.h> |
| 64 | #include <asm/cputable.h> | 60 | #include <asm/cputable.h> |
| @@ -553,6 +553,7 @@ struct pptable_funcs { · 552 unmodified lines | |||
| 553 | *clock_req); | 553 | *clock_req); |
| 554 | uint32_t (*get_fan_control_mode)(struct smu_context *smu); | 554 | uint32_t (*get_fan_control_mode)(struct smu_context *smu); |
| 555 | int (*set_fan_control_mode)(struct smu_context *smu, uint32_t mode); | 555 | int (*set_fan_control_mode)(struct smu_context *smu, uint32_t mode); |
| 556 | int (*set_fan_speed_percent)(struct smu_context *smu, uint32_t speed); | ||
| 556 | int (*set_fan_speed_rpm)(struct smu_context *smu, uint32_t speed); | 557 | int (*set_fan_speed_rpm)(struct smu_context *smu, uint32_t speed); |
| 557 | int (*set_xgmi_pstate)(struct smu_context *smu, uint32_t pstate); | 558 | int (*set_xgmi_pstate)(struct smu_context *smu, uint32_t pstate); |
| 558 | int (*gfx_off_control)(struct smu_context *smu, bool enable); | 559 | int (*gfx_off_control)(struct smu_context *smu, bool enable); |
| @@ -203,6 +203,9 @@ int · 202 unmodified lines | |||
| 203 | smu_v11_0_set_fan_control_mode(struct smu_context *smu, | 203 | smu_v11_0_set_fan_control_mode(struct smu_context *smu, |
| 204 | uint32_t mode); | 204 | uint32_t mode); |
| 205 | 205 | ||
| 206 | int | ||
| 207 | smu_v11_0_set_fan_speed_percent(struct smu_context *smu, uint32_t speed); | ||
| 208 | |||
| 206 | int smu_v11_0_set_fan_speed_rpm(struct smu_context *smu, | 209 | int smu_v11_0_set_fan_speed_rpm(struct smu_context *smu, |
| 207 | uint32_t speed); | 210 | uint32_t speed); |
| 208 | 211 | ||
| @@ -251,7 +251,7 @@ static int smu10_set_hard_min_gfxclk_by_freq(struct pp_hwmgr *hwmgr, uint32_t cl · 250 unmodified lines | |||
| 251 | smu10_data->gfx_actual_soft_min_freq = clock; | 251 | smu10_data->gfx_actual_soft_min_freq = clock; |
| 252 | smum_send_msg_to_smc_with_parameter(hwmgr, | 252 | smum_send_msg_to_smc_with_parameter(hwmgr, |
| 253 | PPSMC_MSG_SetHardMinGfxClk, | 253 | PPSMC_MSG_SetHardMinGfxClk, |
| 254 | smu10_data->gfx_actual_soft_min_freq, | 254 | clock, |
| 255 | NULL); | 255 | NULL); |
| 256 | } | 256 | } |
| 257 | return 0; | 257 | return 0; |
| @@ -558,7 +558,8 @@ static int smu10_hwmgr_backend_init(struct pp_hwmgr *hwmgr) · 300 unmodified lines | |||
| 558 | 558 | ||
| 559 | /* enable the pp_od_clk_voltage sysfs file */ | 559 | /* enable the pp_od_clk_voltage sysfs file */ |
| 560 | hwmgr->od_enabled = 1; | 560 | hwmgr->od_enabled = 1; |
| 561 | 561 | /* disabled fine grain tuning function by default */ | |
| 562 | data->fine_grain_enabled = 0; | ||
| 562 | return result; | 563 | return result; |
| 563 | } | 564 | } |
| 564 | 565 | ||
| @@ -597,6 +598,7 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 32 unmodified lines | |||
| 597 | uint32_t min_mclk = hwmgr->display_config->min_mem_set_clock/100; | 598 | uint32_t min_mclk = hwmgr->display_config->min_mem_set_clock/100; |
| 598 | uint32_t index_fclk = data->clock_vol_info.vdd_dep_on_fclk->count - 1; | 599 | uint32_t index_fclk = data->clock_vol_info.vdd_dep_on_fclk->count - 1; |
| 599 | uint32_t index_socclk = data->clock_vol_info.vdd_dep_on_socclk->count - 1; | 600 | uint32_t index_socclk = data->clock_vol_info.vdd_dep_on_socclk->count - 1; |
| 601 | uint32_t fine_grain_min_freq = 0, fine_grain_max_freq = 0; | ||
| 600 | 602 | ||
| 601 | if (hwmgr->smu_version < 0x1E3700) { | 603 | if (hwmgr->smu_version < 0x1E3700) { |
| 602 | pr_info("smu firmware version too old, can not set dpm level\n"); | 604 | pr_info("smu firmware version too old, can not set dpm level\n"); |
| @@ -613,6 +615,14 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 10 unmodified lines | |||
| 613 | switch (level) { | 615 | switch (level) { |
| 614 | case AMD_DPM_FORCED_LEVEL_HIGH: | 616 | case AMD_DPM_FORCED_LEVEL_HIGH: |
| 615 | case AMD_DPM_FORCED_LEVEL_PROFILE_PEAK: | 617 | case AMD_DPM_FORCED_LEVEL_PROFILE_PEAK: |
| 618 | data->fine_grain_enabled = 0; | ||
| 619 | |||
| 620 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &fine_grain_min_freq); | ||
| 621 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &fine_grain_max_freq); | ||
| 622 | |||
| 623 | data->gfx_actual_soft_min_freq = fine_grain_min_freq; | ||
| 624 | data->gfx_actual_soft_max_freq = fine_grain_max_freq; | ||
| 625 | |||
| 616 | smum_send_msg_to_smc_with_parameter(hwmgr, | 626 | smum_send_msg_to_smc_with_parameter(hwmgr, |
| 617 | PPSMC_MSG_SetHardMinGfxClk, | 627 | PPSMC_MSG_SetHardMinGfxClk, |
| 618 | data->gfx_max_freq_limit/100, | 628 | data->gfx_max_freq_limit/100, |
| @@ -648,6 +658,14 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 29 unmodified lines | |||
| 648 | NULL); | 658 | NULL); |
| 649 | break; | 659 | break; |
| 650 | case AMD_DPM_FORCED_LEVEL_PROFILE_MIN_SCLK: | 660 | case AMD_DPM_FORCED_LEVEL_PROFILE_MIN_SCLK: |
| 661 | data->fine_grain_enabled = 0; | ||
| 662 | |||
| 663 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &fine_grain_min_freq); | ||
| 664 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &fine_grain_max_freq); | ||
| 665 | |||
| 666 | data->gfx_actual_soft_min_freq = fine_grain_min_freq; | ||
| 667 | data->gfx_actual_soft_max_freq = fine_grain_max_freq; | ||
| 668 | |||
| 651 | smum_send_msg_to_smc_with_parameter(hwmgr, | 669 | smum_send_msg_to_smc_with_parameter(hwmgr, |
| 652 | PPSMC_MSG_SetHardMinGfxClk, | 670 | PPSMC_MSG_SetHardMinGfxClk, |
| 653 | min_sclk, | 671 | min_sclk, |
| @@ -658,6 +676,14 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 4 unmodified lines | |||
| 658 | NULL); | 676 | NULL); |
| 659 | break; | 677 | break; |
| 660 | case AMD_DPM_FORCED_LEVEL_PROFILE_MIN_MCLK: | 678 | case AMD_DPM_FORCED_LEVEL_PROFILE_MIN_MCLK: |
| 679 | data->fine_grain_enabled = 0; | ||
| 680 | |||
| 681 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &fine_grain_min_freq); | ||
| 682 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &fine_grain_max_freq); | ||
| 683 | |||
| 684 | data->gfx_actual_soft_min_freq = fine_grain_min_freq; | ||
| 685 | data->gfx_actual_soft_max_freq = fine_grain_max_freq; | ||
| 686 | |||
| 661 | smum_send_msg_to_smc_with_parameter(hwmgr, | 687 | smum_send_msg_to_smc_with_parameter(hwmgr, |
| 662 | PPSMC_MSG_SetHardMinFclkByFreq, | 688 | PPSMC_MSG_SetHardMinFclkByFreq, |
| 663 | min_mclk, | 689 | min_mclk, |
| @@ -668,6 +694,14 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 4 unmodified lines | |||
| 668 | NULL); | 694 | NULL); |
| 669 | break; | 695 | break; |
| 670 | case AMD_DPM_FORCED_LEVEL_PROFILE_STANDARD: | 696 | case AMD_DPM_FORCED_LEVEL_PROFILE_STANDARD: |
| 697 | data->fine_grain_enabled = 0; | ||
| 698 | |||
| 699 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &fine_grain_min_freq); | ||
| 700 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &fine_grain_max_freq); | ||
| 701 | |||
| 702 | data->gfx_actual_soft_min_freq = fine_grain_min_freq; | ||
| 703 | data->gfx_actual_soft_max_freq = fine_grain_max_freq; | ||
| 704 | |||
| 671 | smum_send_msg_to_smc_with_parameter(hwmgr, | 705 | smum_send_msg_to_smc_with_parameter(hwmgr, |
| 672 | PPSMC_MSG_SetHardMinGfxClk, | 706 | PPSMC_MSG_SetHardMinGfxClk, |
| 673 | SMU10_UMD_PSTATE_GFXCLK, | 707 | SMU10_UMD_PSTATE_GFXCLK, |
| @@ -703,6 +737,14 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 29 unmodified lines | |||
| 703 | NULL); | 737 | NULL); |
| 704 | break; | 738 | break; |
| 705 | case AMD_DPM_FORCED_LEVEL_AUTO: | 739 | case AMD_DPM_FORCED_LEVEL_AUTO: |
| 740 | data->fine_grain_enabled = 0; | ||
| 741 | |||
| 742 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &fine_grain_min_freq); | ||
| 743 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &fine_grain_max_freq); | ||
| 744 | |||
| 745 | data->gfx_actual_soft_min_freq = fine_grain_min_freq; | ||
| 746 | data->gfx_actual_soft_max_freq = fine_grain_max_freq; | ||
| 747 | |||
| 706 | smum_send_msg_to_smc_with_parameter(hwmgr, | 748 | smum_send_msg_to_smc_with_parameter(hwmgr, |
| 707 | PPSMC_MSG_SetHardMinGfxClk, | 749 | PPSMC_MSG_SetHardMinGfxClk, |
| 708 | min_sclk, | 750 | min_sclk, |
| @@ -741,6 +783,14 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 32 unmodified lines | |||
| 741 | NULL); | 783 | NULL); |
| 742 | break; | 784 | break; |
| 743 | case AMD_DPM_FORCED_LEVEL_LOW: | 785 | case AMD_DPM_FORCED_LEVEL_LOW: |
| 786 | data->fine_grain_enabled = 0; | ||
| 787 | |||
| 788 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &fine_grain_min_freq); | ||
| 789 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &fine_grain_max_freq); | ||
| 790 | |||
| 791 | data->gfx_actual_soft_min_freq = fine_grain_min_freq; | ||
| 792 | data->gfx_actual_soft_max_freq = fine_grain_max_freq; | ||
| 793 | |||
| 744 | smum_send_msg_to_smc_with_parameter(hwmgr, | 794 | smum_send_msg_to_smc_with_parameter(hwmgr, |
| 745 | PPSMC_MSG_SetHardMinGfxClk, | 795 | PPSMC_MSG_SetHardMinGfxClk, |
| 746 | data->gfx_min_freq_limit/100, | 796 | data->gfx_min_freq_limit/100, |
| @@ -759,6 +809,7 @@ static int smu10_dpm_force_dpm_level(struct pp_hwmgr *hwmgr, · 12 unmodified lines | |||
| 759 | NULL); | 809 | NULL); |
| 760 | break; | 810 | break; |
| 761 | case AMD_DPM_FORCED_LEVEL_MANUAL: | 811 | case AMD_DPM_FORCED_LEVEL_MANUAL: |
| 812 | data->fine_grain_enabled = 1; | ||
| 762 | case AMD_DPM_FORCED_LEVEL_PROFILE_EXIT: | 813 | case AMD_DPM_FORCED_LEVEL_PROFILE_EXIT: |
| 763 | default: | 814 | default: |
| 764 | break; | 815 | break; |
| @@ -948,6 +999,8 @@ static int smu10_print_clock_levels(struct pp_hwmgr *hwmgr, · 183 unmodified lines | |||
| 948 | struct smu10_voltage_dependency_table *mclk_table = | 999 | struct smu10_voltage_dependency_table *mclk_table = |
| 949 | data->clock_vol_info.vdd_dep_on_fclk; | 1000 | data->clock_vol_info.vdd_dep_on_fclk; |
| 950 | uint32_t i, now, size = 0; | 1001 | uint32_t i, now, size = 0; |
| 1002 | uint32_t min_freq, max_freq = 0; | ||
| 1003 | uint32_t ret = 0; | ||
| 951 | 1004 | ||
| 952 | switch (type) { | 1005 | switch (type) { |
| 953 | case PP_SCLK: | 1006 | case PP_SCLK: |
| @@ -983,18 +1036,28 @@ static int smu10_print_clock_levels(struct pp_hwmgr *hwmgr, · 29 unmodified lines | |||
| 983 | break; | 1036 | break; |
| 984 | case OD_SCLK: | 1037 | case OD_SCLK: |
| 985 | if (hwmgr->od_enabled) { | 1038 | if (hwmgr->od_enabled) { |
| 986 | size = sprintf(buf, "%s:\n", "OD_SCLK"); | 1039 | ret = smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &min_freq); |
| 1040 | if (ret) | ||
| 1041 | return ret; | ||
| 1042 | ret = smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &max_freq); | ||
| 1043 | if (ret) | ||
| 1044 | return ret; | ||
| 987 | 1045 | ||
| 1046 | size = sprintf(buf, "%s:\n", "OD_SCLK"); | ||
| 988 | size += sprintf(buf + size, "0: %10uMhz\n", | 1047 | size += sprintf(buf + size, "0: %10uMhz\n", |
| 989 | (data->gfx_actual_soft_min_freq > 0) ? data->gfx_actual_soft_min_freq : data->gfx_min_freq_limit/100); | 1048 | (data->gfx_actual_soft_min_freq > 0) ? data->gfx_actual_soft_min_freq : min_freq); |
| 990 | size += sprintf(buf + size, "1: %10uMhz\n", data->gfx_max_freq_limit/100); | 1049 | size += sprintf(buf + size, "1: %10uMhz\n", |
| 1050 | (data->gfx_actual_soft_max_freq > 0) ? data->gfx_actual_soft_max_freq : max_freq); | ||
| 991 | } | 1051 | } |
| 992 | break; | 1052 | break; |
| 993 | case OD_RANGE: | 1053 | case OD_RANGE: |
| 994 | if (hwmgr->od_enabled) { | 1054 | if (hwmgr->od_enabled) { |
| 995 | uint32_t min_freq, max_freq = 0; | 1055 | ret = smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &min_freq); |
| 996 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &min_freq); | 1056 | if (ret) |
| 997 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &max_freq); | 1057 | return ret; |
| 1058 | ret = smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &max_freq); | ||
| 1059 | if (ret) | ||
| 1060 | return ret; | ||
| 998 | 1061 | ||
| 999 | size = sprintf(buf, "%s:\n", "OD_RANGE"); | 1062 | size = sprintf(buf, "%s:\n", "OD_RANGE"); |
| 1000 | size += sprintf(buf + size, "SCLK: %7uMHz %10uMHz\n", | 1063 | size += sprintf(buf + size, "SCLK: %7uMHz %10uMHz\n", |
| @@ -1414,23 +1477,96 @@ static int smu10_set_fine_grain_clk_vol(struct pp_hwmgr *hwmgr, · 413 unmodified lines | |||
| 1414 | enum PP_OD_DPM_TABLE_COMMAND type, | 1477 | enum PP_OD_DPM_TABLE_COMMAND type, |
| 1415 | long *input, uint32_t size) | 1478 | long *input, uint32_t size) |
| 1416 | { | 1479 | { |
| 1480 | uint32_t min_freq, max_freq = 0; | ||
| 1481 | struct smu10_hwmgr *smu10_data = (struct smu10_hwmgr *)(hwmgr->backend); | ||
| 1482 | int ret = 0; | ||
| 1483 | |||
| 1417 | if (!hwmgr->od_enabled) { | 1484 | if (!hwmgr->od_enabled) { |
| 1418 | pr_err("Fine grain not support\n"); | 1485 | pr_err("Fine grain not support\n"); |
| 1419 | return -EINVAL; | 1486 | return -EINVAL; |
| 1420 | } | 1487 | } |
| 1421 | 1488 | ||
| 1422 | if (size != 2) { | 1489 | if (!smu10_data->fine_grain_enabled) { |
| 1423 | pr_err("Input parameter number not correct\n"); | 1490 | pr_err("Fine grain not started\n"); |
| 1424 | return -EINVAL; | 1491 | return -EINVAL; |
| 1425 | } | 1492 | } |
| 1426 | 1493 | ||
| 1427 | if (type == PP_OD_EDIT_SCLK_VDDC_TABLE) { | 1494 | if (type == PP_OD_EDIT_SCLK_VDDC_TABLE) { |
| 1428 | if (input[0] == 0) | 1495 | if (size != 2) { |
| 1429 | smu10_set_hard_min_gfxclk_by_freq(hwmgr, input[1]); | 1496 | pr_err("Input parameter number not correct\n"); |
| 1430 | else if (input[0] == 1) | ||
| 1431 | smu10_set_soft_max_gfxclk_by_freq(hwmgr, input[1]); | ||
| 1432 | else | ||
| 1433 | return -EINVAL; | 1497 | return -EINVAL; |
| 1498 | } | ||
| 1499 | |||
| 1500 | if (input[0] == 0) { | ||
| 1501 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &min_freq); | ||
| 1502 | if (input[1] < min_freq) { | ||
| 1503 | pr_err("Fine grain setting minimum sclk (%ld) MHz is less than the minimum allowed (%d) MHz\n", | ||
| 1504 | input[1], min_freq); | ||
| 1505 | return -EINVAL; | ||
| 1506 | } | ||
| 1507 | smu10_data->gfx_actual_soft_min_freq = input[1]; | ||
| 1508 | } else if (input[0] == 1) { | ||
| 1509 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &max_freq); | ||
| 1510 | if (input[1] > max_freq) { | ||
| 1511 | pr_err("Fine grain setting maximum sclk (%ld) MHz is greater than the maximum allowed (%d) MHz\n", | ||
| 1512 | input[1], max_freq); | ||
| 1513 | return -EINVAL; | ||
| 1514 | } | ||
| 1515 | smu10_data->gfx_actual_soft_max_freq = input[1]; | ||
| 1516 | } else { | ||
| 1517 | return -EINVAL; | ||
| 1518 | } | ||
| 1519 | } else if (type == PP_OD_RESTORE_DEFAULT_TABLE) { | ||
| 1520 | if (size != 0) { | ||
| 1521 | pr_err("Input parameter number not correct\n"); | ||
| 1522 | return -EINVAL; | ||
| 1523 | } | ||
| 1524 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMinGfxclkFrequency, &min_freq); | ||
| 1525 | smum_send_msg_to_smc(hwmgr, PPSMC_MSG_GetMaxGfxclkFrequency, &max_freq); | ||
| 1526 | |||
| 1527 | smu10_data->gfx_actual_soft_min_freq = min_freq; | ||
| 1528 | smu10_data->gfx_actual_soft_max_freq = max_freq; | ||
| 1529 | |||
| 1530 | ret = smum_send_msg_to_smc_with_parameter(hwmgr, | ||
| 1531 | PPSMC_MSG_SetHardMinGfxClk, | ||
| 1532 | min_freq, | ||
| 1533 | NULL); | ||
| 1534 | if (ret) | ||
| 1535 | return ret; | ||
| 1536 | |||
| 1537 | ret = smum_send_msg_to_smc_with_parameter(hwmgr, | ||
| 1538 | PPSMC_MSG_SetSoftMaxGfxClk, | ||
| 1539 | max_freq, | ||
| 1540 | NULL); | ||
| 1541 | if (ret) | ||
| 1542 | return ret; | ||
| 1543 | } else if (type == PP_OD_COMMIT_DPM_TABLE) { | ||
| 1544 | if (size != 0) { | ||
| 1545 | pr_err("Input parameter number not correct\n"); | ||
| 1546 | return -EINVAL; | ||
| 1547 | } | ||
| 1548 | |||
| 1549 | if (smu10_data->gfx_actual_soft_min_freq > smu10_data->gfx_actual_soft_max_freq) { | ||
| 1550 | pr_err("The setting minimun sclk (%d) MHz is greater than the setting maximum sclk (%d) MHz\n", | ||
| 1551 | smu10_data->gfx_actual_soft_min_freq, smu10_data->gfx_actual_soft_max_freq); | ||
| 1552 | return -EINVAL; | ||
| 1553 | } | ||
| 1554 | |||
| 1555 | ret = smum_send_msg_to_smc_with_parameter(hwmgr, | ||
| 1556 | PPSMC_MSG_SetHardMinGfxClk, | ||
| 1557 | smu10_data->gfx_actual_soft_min_freq, | ||
| 1558 | NULL); | ||
| 1559 | if (ret) | ||
| 1560 | return ret; | ||
| 1561 | |||
| 1562 | ret = smum_send_msg_to_smc_with_parameter(hwmgr, | ||
| 1563 | PPSMC_MSG_SetSoftMaxGfxClk, | ||
| 1564 | smu10_data->gfx_actual_soft_max_freq, | ||
| 1565 | NULL); | ||
| 1566 | if (ret) | ||
| 1567 | return ret; | ||
| 1568 | } else { | ||
| 1569 | return -EINVAL; | ||
| 1434 | } | 1570 | } |
| 1435 | 1571 | ||
| 1436 | return 0; | 1572 | return 0; |
| @@ -283,6 +283,7 @@ struct smu10_hwmgr { · 282 unmodified lines | |||
| 283 | uint32_t vclk_soft_min; | 283 | uint32_t vclk_soft_min; |
| 284 | uint32_t dclk_soft_min; | 284 | uint32_t dclk_soft_min; |
| 285 | uint32_t gfx_actual_soft_min_freq; | 285 | uint32_t gfx_actual_soft_min_freq; |
| 286 | uint32_t gfx_actual_soft_max_freq; | ||
| 286 | uint32_t gfx_min_freq_limit; | 287 | uint32_t gfx_min_freq_limit; |
| 287 | uint32_t gfx_max_freq_limit; /* in 10Khz*/ | 288 | uint32_t gfx_max_freq_limit; /* in 10Khz*/ |
| 288 | 289 | ||
| @@ -299,6 +300,8 @@ struct smu10_hwmgr { · 10 unmodified lines | |||
| 299 | bool need_min_deep_sleep_dcefclk; | 300 | bool need_min_deep_sleep_dcefclk; |
| 300 | uint32_t deep_sleep_dcefclk; | 301 | uint32_t deep_sleep_dcefclk; |
| 301 | uint32_t num_active_display; | 302 | uint32_t num_active_display; |
| 303 | |||
| 304 | bool fine_grain_enabled; | ||
| 302 | }; | 305 | }; |
| 303 | 306 | ||
| 304 | struct pp_hwmgr; | 307 | struct pp_hwmgr; |
| @@ -2151,19 +2151,14 @@ int smu_get_fan_speed_percent(struct smu_context *smu, uint32_t *speed) · 2150 unmodified lines | |||
| 2151 | int smu_set_fan_speed_percent(struct smu_context *smu, uint32_t speed) | 2151 | int smu_set_fan_speed_percent(struct smu_context *smu, uint32_t speed) |
| 2152 | { | 2152 | { |
| 2153 | int ret = 0; | 2153 | int ret = 0; |
| 2154 | uint32_t rpm; | ||
| 2155 | 2154 | ||
| 2156 | if (!smu->pm_enabled || !smu->adev->pm.dpm_enabled) | 2155 | if (!smu->pm_enabled || !smu->adev->pm.dpm_enabled) |
| 2157 | return -EOPNOTSUPP; | 2156 | return -EOPNOTSUPP; |
| 2158 | 2157 | ||
| 2159 | mutex_lock(&smu->mutex); | 2158 | mutex_lock(&smu->mutex); |
| 2160 | 2159 | ||
| 2161 | if (smu->ppt_funcs->set_fan_speed_rpm) { | 2160 | if (smu->ppt_funcs->set_fan_speed_percent) |
| 2162 | if (speed > 100) | 2161 | ret = smu->ppt_funcs->set_fan_speed_percent(smu, speed); |
| 2163 | speed = 100; | ||
| 2164 | rpm = speed * smu->fan_max_rpm / 100; | ||
| 2165 | ret = smu->ppt_funcs->set_fan_speed_rpm(smu, rpm); | ||
| 2166 | } | ||
| 2167 | 2162 | ||
| 2168 | mutex_unlock(&smu->mutex); | 2163 | mutex_unlock(&smu->mutex); |
| 2169 | 2164 | ||
| @@ -2326,6 +2326,7 @@ static const struct pptable_funcs arcturus_ppt_funcs = { · 2325 unmodified lines | |||
| 2326 | .display_clock_voltage_request = smu_v11_0_display_clock_voltage_request, | 2326 | .display_clock_voltage_request = smu_v11_0_display_clock_voltage_request, |
| 2327 | .get_fan_control_mode = smu_v11_0_get_fan_control_mode, | 2327 | .get_fan_control_mode = smu_v11_0_get_fan_control_mode, |
| 2328 | .set_fan_control_mode = smu_v11_0_set_fan_control_mode, | 2328 | .set_fan_control_mode = smu_v11_0_set_fan_control_mode, |
| 2329 | .set_fan_speed_percent = smu_v11_0_set_fan_speed_percent, | ||
| 2329 | .set_fan_speed_rpm = smu_v11_0_set_fan_speed_rpm, | 2330 | .set_fan_speed_rpm = smu_v11_0_set_fan_speed_rpm, |
| 2330 | .set_xgmi_pstate = smu_v11_0_set_xgmi_pstate, | 2331 | .set_xgmi_pstate = smu_v11_0_set_xgmi_pstate, |
| 2331 | .gfx_off_control = smu_v11_0_gfx_off_control, | 2332 | .gfx_off_control = smu_v11_0_gfx_off_control, |
| @@ -2456,6 +2456,7 @@ static const struct pptable_funcs navi10_ppt_funcs = { · 2455 unmodified lines | |||
| 2456 | .display_clock_voltage_request = smu_v11_0_display_clock_voltage_request, | 2456 | .display_clock_voltage_request = smu_v11_0_display_clock_voltage_request, |
| 2457 | .get_fan_control_mode = smu_v11_0_get_fan_control_mode, | 2457 | .get_fan_control_mode = smu_v11_0_get_fan_control_mode, |
| 2458 | .set_fan_control_mode = smu_v11_0_set_fan_control_mode, | 2458 | .set_fan_control_mode = smu_v11_0_set_fan_control_mode, |
| 2459 | .set_fan_speed_percent = smu_v11_0_set_fan_speed_percent, | ||
| 2459 | .set_fan_speed_rpm = smu_v11_0_set_fan_speed_rpm, | 2460 | .set_fan_speed_rpm = smu_v11_0_set_fan_speed_rpm, |
| 2460 | .set_xgmi_pstate = smu_v11_0_set_xgmi_pstate, | 2461 | .set_xgmi_pstate = smu_v11_0_set_xgmi_pstate, |
| 2461 | .gfx_off_control = smu_v11_0_gfx_off_control, | 2462 | .gfx_off_control = smu_v11_0_gfx_off_control, |
| @@ -2372,7 +2372,7 @@ static void sienna_cichlid_fill_i2c_req(SwI2cRequest_t *req, bool write, · 2371 unmodified lines | |||
| 2372 | { | 2372 | { |
| 2373 | int i; | 2373 | int i; |
| 2374 | 2374 | ||
| 2375 | req->I2CcontrollerPort = 0; | 2375 | req->I2CcontrollerPort = 1; |
| 2376 | req->I2CSpeed = 2; | 2376 | req->I2CSpeed = 2; |
| 2377 | req->SlaveAddress = address; | 2377 | req->SlaveAddress = address; |
| 2378 | req->NumCmds = numbytes; | 2378 | req->NumCmds = numbytes; |
| @@ -2802,6 +2802,7 @@ static const struct pptable_funcs sienna_cichlid_ppt_funcs = { · 423 unmodified lines | |||
| 2802 | .display_clock_voltage_request = smu_v11_0_display_clock_voltage_request, | 2802 | .display_clock_voltage_request = smu_v11_0_display_clock_voltage_request, |
| 2803 | .get_fan_control_mode = smu_v11_0_get_fan_control_mode, | 2803 | .get_fan_control_mode = smu_v11_0_get_fan_control_mode, |
| 2804 | .set_fan_control_mode = smu_v11_0_set_fan_control_mode, | 2804 | .set_fan_control_mode = smu_v11_0_set_fan_control_mode, |
| 2805 | .set_fan_speed_percent = smu_v11_0_set_fan_speed_percent, | ||
| 2805 | .set_fan_speed_rpm = smu_v11_0_set_fan_speed_rpm, | 2806 | .set_fan_speed_rpm = smu_v11_0_set_fan_speed_rpm, |
| 2806 | .set_xgmi_pstate = smu_v11_0_set_xgmi_pstate, | 2807 | .set_xgmi_pstate = smu_v11_0_set_xgmi_pstate, |
| 2807 | .gfx_off_control = smu_v11_0_gfx_off_control, | 2808 | .gfx_off_control = smu_v11_0_gfx_off_control, |
| @@ -1173,6 +1173,35 @@ smu_v11_0_set_fan_static_mode(struct smu_context *smu, uint32_t mode) · 1172 unmodified lines | |||
| 1173 | return 0; | 1173 | return 0; |
| 1174 | } | 1174 | } |
| 1175 | 1175 | ||
| 1176 | int | ||
| 1177 | smu_v11_0_set_fan_speed_percent(struct smu_context *smu, uint32_t speed) | ||
| 1178 | { | ||
| 1179 | struct amdgpu_device *adev = smu->adev; | ||
| 1180 | uint32_t duty100, duty; | ||
| 1181 | uint64_t tmp64; | ||
| 1182 | |||
| 1183 | if (speed > 100) | ||
| 1184 | speed = 100; | ||
| 1185 | |||
| 1186 | if (smu_v11_0_auto_fan_control(smu, 0)) | ||
| 1187 | return -EINVAL; | ||
| 1188 | |||
| 1189 | duty100 = REG_GET_FIELD(RREG32_SOC15(THM, 0, mmCG_FDO_CTRL1), | ||
| 1190 | CG_FDO_CTRL1, FMAX_DUTY100); | ||
| 1191 | if (!duty100) | ||
| 1192 | return -EINVAL; | ||
| 1193 | |||
| 1194 | tmp64 = (uint64_t)speed * duty100; | ||
| 1195 | do_div(tmp64, 100); | ||
| 1196 | duty = (uint32_t)tmp64; | ||
| 1197 | |||
| 1198 | WREG32_SOC15(THM, 0, mmCG_FDO_CTRL0, | ||
| 1199 | REG_SET_FIELD(RREG32_SOC15(THM, 0, mmCG_FDO_CTRL0), | ||
| 1200 | CG_FDO_CTRL0, FDO_STATIC_DUTY, duty)); | ||
| 1201 | |||
| 1202 | return smu_v11_0_set_fan_static_mode(smu, FDO_PWM_MODE_STATIC); | ||
| 1203 | } | ||
| 1204 | |||
| 1176 | int | 1205 | int |
| 1177 | smu_v11_0_set_fan_control_mode(struct smu_context *smu, | 1206 | smu_v11_0_set_fan_control_mode(struct smu_context *smu, |
| 1178 | uint32_t mode) | 1207 | uint32_t mode) |
| @@ -1181,7 +1210,7 @@ smu_v11_0_set_fan_control_mode(struct smu_context *smu, · 2 unmodified lines | |||
| 1181 | 1210 | ||
| 1182 | switch (mode) { | 1211 | switch (mode) { |
| 1183 | case AMD_FAN_CTRL_NONE: | 1212 | case AMD_FAN_CTRL_NONE: |
| 1184 | ret = smu_v11_0_set_fan_speed_rpm(smu, smu->fan_max_rpm); | 1213 | ret = smu_v11_0_set_fan_speed_percent(smu, 100); |
| 1185 | break; | 1214 | break; |
| 1186 | case AMD_FAN_CTRL_MANUAL: | 1215 | case AMD_FAN_CTRL_MANUAL: |
| 1187 | ret = smu_v11_0_auto_fan_control(smu, 0); | 1216 | ret = smu_v11_0_auto_fan_control(smu, 0); |
| @@ -252,7 +252,8 @@ static int vangogh_get_smu_metrics_data(struct smu_context *smu, · 251 unmodified lines | |||
| 252 | *value = metrics->UvdActivity; | 252 | *value = metrics->UvdActivity; |
| 253 | break; | 253 | break; |
| 254 | case METRICS_AVERAGE_SOCKETPOWER: | 254 | case METRICS_AVERAGE_SOCKETPOWER: |
| 255 | *value = metrics->CurrentSocketPower; | 255 | *value = (metrics->CurrentSocketPower << 8) / |
| 256 | 1000 ; | ||
| 256 | break; | 257 | break; |
| 257 | case METRICS_TEMPERATURE_EDGE: | 258 | case METRICS_TEMPERATURE_EDGE: |
| 258 | *value = metrics->GfxTemperature / 100 * | 259 | *value = metrics->GfxTemperature / 100 * |
| @@ -590,14 +591,17 @@ static ssize_t vangogh_get_gpu_metrics(struct smu_context *smu, · 331 unmodified lines | |||
| 590 | gpu_metrics->average_socket_power = metrics.CurrentSocketPower; | 591 | gpu_metrics->average_socket_power = metrics.CurrentSocketPower; |
| 591 | gpu_metrics->average_cpu_power = metrics.Power[0]; | 592 | gpu_metrics->average_cpu_power = metrics.Power[0]; |
| 592 | gpu_metrics->average_soc_power = metrics.Power[1]; | 593 | gpu_metrics->average_soc_power = metrics.Power[1]; |
| 594 | gpu_metrics->average_gfx_power = metrics.Power[2]; | ||
| 593 | memcpy(&gpu_metrics->average_core_power[0], | 595 | memcpy(&gpu_metrics->average_core_power[0], |
| 594 | &metrics.CorePower[0], | 596 | &metrics.CorePower[0], |
| 595 | sizeof(uint16_t) * 8); | 597 | sizeof(uint16_t) * 8); |
| 596 | 598 | ||
| 597 | gpu_metrics->average_gfxclk_frequency = metrics.GfxclkFrequency; | 599 | gpu_metrics->average_gfxclk_frequency = metrics.GfxclkFrequency; |
| 598 | gpu_metrics->average_socclk_frequency = metrics.SocclkFrequency; | 600 | gpu_metrics->average_socclk_frequency = metrics.SocclkFrequency; |
| 601 | gpu_metrics->average_uclk_frequency = metrics.MemclkFrequency; | ||
| 599 | gpu_metrics->average_fclk_frequency = metrics.MemclkFrequency; | 602 | gpu_metrics->average_fclk_frequency = metrics.MemclkFrequency; |
| 600 | gpu_metrics->average_vclk_frequency = metrics.VclkFrequency; | 603 | gpu_metrics->average_vclk_frequency = metrics.VclkFrequency; |
| 604 | gpu_metrics->average_dclk_frequency = metrics.DclkFrequency; | ||
| 601 | 605 | ||
| 602 | memcpy(&gpu_metrics->current_coreclk[0], | 606 | memcpy(&gpu_metrics->current_coreclk[0], |
| 603 | &metrics.CoreFrequency[0], | 607 | &metrics.CoreFrequency[0], |
| @@ -188,6 +188,7 @@ static int renoir_get_dpm_clk_limited(struct smu_context *smu, enum smu_clk_type · 187 unmodified lines | |||
| 188 | return -EINVAL; | 188 | return -EINVAL; |
| 189 | *freq = clk_table->SocClocks[dpm_level].Freq; | 189 | *freq = clk_table->SocClocks[dpm_level].Freq; |
| 190 | break; | 190 | break; |
| 191 | case SMU_UCLK: | ||
| 191 | case SMU_MCLK: | 192 | case SMU_MCLK: |
| 192 | if (dpm_level >= NUM_FCLK_DPM_LEVELS) | 193 | if (dpm_level >= NUM_FCLK_DPM_LEVELS) |
| 193 | return -EINVAL; | 194 | return -EINVAL; |
| @@ -1120,7 +1121,7 @@ static ssize_t renoir_get_gpu_metrics(struct smu_context *smu, · 926 unmodified lines | |||
| 1120 | static int renoir_gfx_state_change_set(struct smu_context *smu, uint32_t state) | 1121 | static int renoir_gfx_state_change_set(struct smu_context *smu, uint32_t state) |
| 1121 | { | 1122 | { |
| 1122 | 1123 | ||
| 1123 | return smu_cmn_send_smc_msg_with_param(smu, SMU_MSG_GpuChangeState, state, NULL); | 1124 | return 0; |
| 1124 | } | 1125 | } |
| 1125 | 1126 | ||
| 1126 | static const struct pptable_funcs renoir_ppt_funcs = { | 1127 | static const struct pptable_funcs renoir_ppt_funcs = { |
| @@ -225,6 +225,7 @@ int smu_v12_0_set_soft_freq_limited_range(struct smu_context *smu, enum smu_clk_ · 224 unmodified lines | |||
| 225 | break; | 225 | break; |
| 226 | case SMU_FCLK: | 226 | case SMU_FCLK: |
| 227 | case SMU_MCLK: | 227 | case SMU_MCLK: |
| 228 | case SMU_UCLK: | ||
| 228 | ret = smu_cmn_send_smc_msg_with_param(smu, SMU_MSG_SetHardMinFclkByFreq, min, NULL); | 229 | ret = smu_cmn_send_smc_msg_with_param(smu, SMU_MSG_SetHardMinFclkByFreq, min, NULL); |
| 229 | if (ret) | 230 | if (ret) |
| 230 | return ret; | 231 | return ret; |
| @@ -14,6 +14,7 @@ · 13 unmodified lines | |||
| 14 | #include <linux/regmap.h> | 14 | #include <linux/regmap.h> |
| 15 | #include <linux/regulator/consumer.h> | 15 | #include <linux/regulator/consumer.h> |
| 16 | #include <linux/wait.h> | 16 | #include <linux/wait.h> |
| 17 | #include <linux/workqueue.h> | ||
| 17 | 18 | ||
| 18 | #include <sound/hdmi-codec.h> | 19 | #include <sound/hdmi-codec.h> |
| 19 | 20 | ||
| @@ -36,6 +37,7 @@ struct lt9611uxc { · 16 unmodified lines | |||
| 36 | struct mutex ocm_lock; | 37 | struct mutex ocm_lock; |
| 37 | 38 | ||
| 38 | struct wait_queue_head wq; | 39 | struct wait_queue_head wq; |
| 40 | struct work_struct work; | ||
| 39 | 41 | ||
| 40 | struct device_node *dsi0_node; | 42 | struct device_node *dsi0_node; |
| 41 | struct device_node *dsi1_node; | 43 | struct device_node *dsi1_node; |
| @@ -52,6 +54,8 @@ struct lt9611uxc { · 10 unmodified lines | |||
| 52 | 54 | ||
| 53 | bool hpd_supported; | 55 | bool hpd_supported; |
| 54 | bool edid_read; | 56 | bool edid_read; |
| 57 | /* can be accessed from different threads, so protect this with ocm_lock */ | ||
| 58 | bool hdmi_connected; | ||
| 55 | uint8_t fw_version; | 59 | uint8_t fw_version; |
| 56 | }; | 60 | }; |
| 57 | 61 | ||
| @@ -143,21 +147,41 @@ static irqreturn_t lt9611uxc_irq_thread_handler(int irq, void *dev_id) · 85 unmodified lines | |||
| 143 | if (irq_status) | 147 | if (irq_status) |
| 144 | regmap_write(lt9611uxc->regmap, 0xb022, 0); | 148 | regmap_write(lt9611uxc->regmap, 0xb022, 0); |
| 145 | 149 | ||
| 146 | lt9611uxc_unlock(lt9611uxc); | 150 | if (irq_status & BIT(0)) { |
| 147 | |||
| 148 | if (irq_status & BIT(0)) | ||
| 149 | lt9611uxc->edid_read = !!(hpd_status & BIT(0)); | 151 | lt9611uxc->edid_read = !!(hpd_status & BIT(0)); |
| 152 | wake_up_all(<9611uxc->wq); | ||
| 153 | } | ||
| 150 | 154 | ||
| 151 | if (irq_status & BIT(1)) { | 155 | if (irq_status & BIT(1)) { |
| 152 | if (lt9611uxc->connector.dev) | 156 | lt9611uxc->hdmi_connected = hpd_status & BIT(1); |
| 153 | drm_kms_helper_hotplug_event(lt9611uxc->connector.dev); | 157 | schedule_work(<9611uxc->work); |
| 154 | else | ||
| 155 | drm_bridge_hpd_notify(<9611uxc->bridge, !!(hpd_status & BIT(1))); | ||
| 156 | } | 158 | } |
| 157 | 159 | ||
| 160 | lt9611uxc_unlock(lt9611uxc); | ||
| 161 | |||
| 158 | return IRQ_HANDLED; | 162 | return IRQ_HANDLED; |
| 159 | } | 163 | } |
| 160 | 164 | ||
| 165 | static void lt9611uxc_hpd_work(struct work_struct *work) | ||
| 166 | { | ||
| 167 | struct lt9611uxc *lt9611uxc = container_of(work, struct lt9611uxc, work); | ||
| 168 | bool connected; | ||
| 169 | |||
| 170 | if (lt9611uxc->connector.dev) | ||
| 171 | drm_kms_helper_hotplug_event(lt9611uxc->connector.dev); | ||
| 172 | else { | ||
| 173 | |||
| 174 | mutex_lock(<9611uxc->ocm_lock); | ||
| 175 | connected = lt9611uxc->hdmi_connected; | ||
| 176 | mutex_unlock(<9611uxc->ocm_lock); | ||
| 177 | |||
| 178 | drm_bridge_hpd_notify(<9611uxc->bridge, | ||
| 179 | connected ? | ||
| 180 | connector_status_connected : | ||
| 181 | connector_status_disconnected); | ||
| 182 | } | ||
| 183 | } | ||
| 184 | |||
| 161 | static void lt9611uxc_reset(struct lt9611uxc *lt9611uxc) | 185 | static void lt9611uxc_reset(struct lt9611uxc *lt9611uxc) |
| 162 | { | 186 | { |
| 163 | gpiod_set_value_cansleep(lt9611uxc->reset_gpio, 1); | 187 | gpiod_set_value_cansleep(lt9611uxc->reset_gpio, 1); |
| @@ -445,18 +469,21 @@ static enum drm_connector_status lt9611uxc_bridge_detect(struct drm_bridge *brid · 281 unmodified lines | |||
| 445 | struct lt9611uxc *lt9611uxc = bridge_to_lt9611uxc(bridge); | 469 | struct lt9611uxc *lt9611uxc = bridge_to_lt9611uxc(bridge); |
| 446 | unsigned int reg_val = 0; | 470 | unsigned int reg_val = 0; |
| 447 | int ret; | 471 | int ret; |
| 448 | int connected = 1; | 472 | bool connected = true; |
| 473 | |||
| 474 | lt9611uxc_lock(lt9611uxc); | ||
| 449 | 475 | ||
| 450 | if (lt9611uxc->hpd_supported) { | 476 | if (lt9611uxc->hpd_supported) { |
| 451 | lt9611uxc_lock(lt9611uxc); | ||
| 452 | ret = regmap_read(lt9611uxc->regmap, 0xb023, ®_val); | 477 | ret = regmap_read(lt9611uxc->regmap, 0xb023, ®_val); |
| 453 | lt9611uxc_unlock(lt9611uxc); | ||
| 454 | 478 | ||
| 455 | if (ret) | 479 | if (ret) |
| 456 | dev_err(lt9611uxc->dev, "failed to read hpd status: %d\n", ret); | 480 | dev_err(lt9611uxc->dev, "failed to read hpd status: %d\n", ret); |
| 457 | else | 481 | else |
| 458 | connected = reg_val & BIT(1); | 482 | connected = reg_val & BIT(1); |
| 459 | } | 483 | } |
| 484 | lt9611uxc->hdmi_connected = connected; | ||
| 485 | |||
| 486 | lt9611uxc_unlock(lt9611uxc); | ||
| 460 | 487 | ||
| 461 | return connected ? connector_status_connected : | 488 | return connected ? connector_status_connected : |
| 462 | connector_status_disconnected; | 489 | connector_status_disconnected; |
| @@ -465,7 +492,7 @@ static enum drm_connector_status lt9611uxc_bridge_detect(struct drm_bridge *brid · 2 unmodified lines | |||
| 465 | static int lt9611uxc_wait_for_edid(struct lt9611uxc *lt9611uxc) | 492 | static int lt9611uxc_wait_for_edid(struct lt9611uxc *lt9611uxc) |
| 466 | { | 493 | { |
| 467 | return wait_event_interruptible_timeout(lt9611uxc->wq, lt9611uxc->edid_read, | 494 | return wait_event_interruptible_timeout(lt9611uxc->wq, lt9611uxc->edid_read, |
| 468 | msecs_to_jiffies(100)); | 495 | msecs_to_jiffies(500)); |
| 469 | } | 496 | } |
| 470 | 497 | ||
| 471 | static int lt9611uxc_get_edid_block(void *data, u8 *buf, unsigned int block, size_t len) | 498 | static int lt9611uxc_get_edid_block(void *data, u8 *buf, unsigned int block, size_t len) |
| @@ -503,7 +530,10 @@ static struct edid *lt9611uxc_bridge_get_edid(struct drm_bridge *bridge, · 31 unmodified lines | |||
| 503 | ret = lt9611uxc_wait_for_edid(lt9611uxc); | 530 | ret = lt9611uxc_wait_for_edid(lt9611uxc); |
| 504 | if (ret < 0) { | 531 | if (ret < 0) { |
| 505 | dev_err(lt9611uxc->dev, "wait for EDID failed: %d\n", ret); | 532 | dev_err(lt9611uxc->dev, "wait for EDID failed: %d\n", ret); |
| 506 | return ERR_PTR(ret); | 533 | return NULL; |
| 534 | } else if (ret == 0) { | ||
| 535 | dev_err(lt9611uxc->dev, "wait for EDID timeout\n"); | ||
| 536 | return NULL; | ||
| 507 | } | 537 | } |
| 508 | 538 | ||
| 509 | return drm_do_get_edid(connector, lt9611uxc_get_edid_block, lt9611uxc); | 539 | return drm_do_get_edid(connector, lt9611uxc_get_edid_block, lt9611uxc); |
| @@ -926,6 +956,8 @@ retry: · 416 unmodified lines | |||
| 926 | lt9611uxc->fw_version = ret; | 956 | lt9611uxc->fw_version = ret; |
| 927 | 957 | ||
| 928 | init_waitqueue_head(<9611uxc->wq); | 958 | init_waitqueue_head(<9611uxc->wq); |
| 959 | INIT_WORK(<9611uxc->work, lt9611uxc_hpd_work); | ||
| 960 | |||
| 929 | ret = devm_request_threaded_irq(dev, client->irq, NULL, | 961 | ret = devm_request_threaded_irq(dev, client->irq, NULL, |
| 930 | lt9611uxc_irq_thread_handler, | 962 | lt9611uxc_irq_thread_handler, |
| 931 | IRQF_ONESHOT, "lt9611uxc", lt9611uxc); | 963 | IRQF_ONESHOT, "lt9611uxc", lt9611uxc); |
| @@ -962,6 +994,7 @@ static int lt9611uxc_remove(struct i2c_client *client) · 30 unmodified lines | |||
| 962 | struct lt9611uxc *lt9611uxc = i2c_get_clientdata(client); | 994 | struct lt9611uxc *lt9611uxc = i2c_get_clientdata(client); |
| 963 | 995 | ||
| 964 | disable_irq(client->irq); | 996 | disable_irq(client->irq); |
| 997 | flush_scheduled_work(); | ||
| 965 | lt9611uxc_audio_exit(lt9611uxc); | 998 | lt9611uxc_audio_exit(lt9611uxc); |
| 966 | drm_bridge_remove(<9611uxc->bridge); | 999 | drm_bridge_remove(<9611uxc->bridge); |
| 967 | 1000 | ||
| @@ -3021,7 +3021,7 @@ int drm_atomic_helper_set_config(struct drm_mode_set *set, · 3020 unmodified lines | |||
| 3021 | 3021 | ||
| 3022 | ret = handle_conflicting_encoders(state, true); | 3022 | ret = handle_conflicting_encoders(state, true); |
| 3023 | if (ret) | 3023 | if (ret) |
| 3024 | return ret; | 3024 | goto fail; |
| 3025 | 3025 | ||
| 3026 | ret = drm_atomic_commit(state); | 3026 | ret = drm_atomic_commit(state); |
| 3027 | 3027 | ||
| @@ -3629,14 +3629,26 @@ static int drm_dp_send_up_ack_reply(struct drm_dp_mst_topology_mgr *mgr, · 3628 unmodified lines | |||
| 3629 | return 0; | 3629 | return 0; |
| 3630 | } | 3630 | } |
| 3631 | 3631 | ||
| 3632 | static int drm_dp_get_vc_payload_bw(u8 dp_link_bw, u8 dp_link_count) | 3632 | /** |
| 3633 | * drm_dp_get_vc_payload_bw - get the VC payload BW for an MST link | ||
| 3634 | * @link_rate: link rate in 10kbits/s units | ||
| 3635 | * @link_lane_count: lane count | ||
| 3636 | * | ||
| 3637 | * Calculate the total bandwidth of a MultiStream Transport link. The returned | ||
| 3638 | * value is in units of PBNs/(timeslots/1 MTP). This value can be used to | ||
| 3639 | * convert the number of PBNs required for a given stream to the number of | ||
| 3640 | * timeslots this stream requires in each MTP. | ||
| 3641 | */ | ||
| 3642 | int drm_dp_get_vc_payload_bw(int link_rate, int link_lane_count) | ||
| 3633 | { | 3643 | { |
| 3634 | if (dp_link_bw == 0 || dp_link_count == 0) | 3644 | if (link_rate == 0 || link_lane_count == 0) |
| 3635 | DRM_DEBUG_KMS("invalid link bandwidth in DPCD: %x (link count: %d)\n", | 3645 | DRM_DEBUG_KMS("invalid link rate/lane count: (%d / %d)\n", |
| 3636 | dp_link_bw, dp_link_count); | 3646 | link_rate, link_lane_count); |
| 3637 | 3647 | ||
| 3638 | return dp_link_bw * dp_link_count / 2; | 3648 | /* See DP v2.0 2.6.4.2, VCPayload_Bandwidth_for_OneTimeSlotPer_MTP_Allocation */ |
| 3649 | return link_rate * link_lane_count / 54000; | ||
| 3639 | } | 3650 | } |
| 3651 | EXPORT_SYMBOL(drm_dp_get_vc_payload_bw); | ||
| 3640 | 3652 | ||
| 3641 | /** | 3653 | /** |
| 3642 | * drm_dp_read_mst_cap() - check whether or not a sink supports MST | 3654 | * drm_dp_read_mst_cap() - check whether or not a sink supports MST |
| @@ -3692,7 +3704,7 @@ int drm_dp_mst_topology_mgr_set_mst(struct drm_dp_mst_topology_mgr *mgr, bool ms · 49 unmodified lines | |||
| 3692 | goto out_unlock; | 3704 | goto out_unlock; |
| 3693 | } | 3705 | } |
| 3694 | 3706 | ||
| 3695 | mgr->pbn_div = drm_dp_get_vc_payload_bw(mgr->dpcd[1], | 3707 | mgr->pbn_div = drm_dp_get_vc_payload_bw(drm_dp_bw_code_to_link_rate(mgr->dpcd[1]), |
| 3696 | mgr->dpcd[2] & DP_MAX_LANE_COUNT_MASK); | 3708 | mgr->dpcd[2] & DP_MAX_LANE_COUNT_MASK); |
| 3697 | if (mgr->pbn_div == 0) { | 3709 | if (mgr->pbn_div == 0) { |
| 3698 | ret = -EINVAL; | 3710 | ret = -EINVAL; |
| @@ -4212,6 +4224,7 @@ drm_dp_mst_detect_port(struct drm_connector *connector, · 513 unmodified lines | |||
| 4212 | 4224 | ||
| 4213 | switch (port->pdt) { | 4225 | switch (port->pdt) { |
| 4214 | case DP_PEER_DEVICE_NONE: | 4226 | case DP_PEER_DEVICE_NONE: |
| 4227 | break; | ||
| 4215 | case DP_PEER_DEVICE_MST_BRANCHING: | 4228 | case DP_PEER_DEVICE_MST_BRANCHING: |
| 4216 | if (!port->mcs) | 4229 | if (!port->mcs) |
| 4217 | ret = connector_status_connected; | 4230 | ret = connector_status_connected; |
| @@ -387,9 +387,16 @@ static int drm_gem_vram_kmap_locked(struct drm_gem_vram_object *gbo, · 386 unmodified lines | |||
| 387 | if (gbo->vmap_use_count > 0) | 387 | if (gbo->vmap_use_count > 0) |
| 388 | goto out; | 388 | goto out; |
| 389 | 389 | ||
| 390 | ret = ttm_bo_vmap(&gbo->bo, &gbo->map); | 390 | /* |
| 391 | if (ret) | 391 | * VRAM helpers unmap the BO only on demand. So the previous |
| 392 | return ret; | 392 | * page mapping might still be around. Only vmap if the there's |
| 393 | * no mapping present. | ||
| 394 | */ | ||
| 395 | if (dma_buf_map_is_null(&gbo->map)) { | ||
| 396 | ret = ttm_bo_vmap(&gbo->bo, &gbo->map); | ||
| 397 | if (ret) | ||
| 398 | return ret; | ||
| 399 | } | ||
| 393 | 400 | ||
| 394 | out: | 401 | out: |
| 395 | ++gbo->vmap_use_count; | 402 | ++gbo->vmap_use_count; |
| @@ -577,6 +584,7 @@ static void drm_gem_vram_bo_driver_move_notify(struct drm_gem_vram_object *gbo, · 181 unmodified lines | |||
| 577 | return; | 584 | return; |
| 578 | 585 | ||
| 579 | ttm_bo_vunmap(bo, &gbo->map); | 586 | ttm_bo_vunmap(bo, &gbo->map); |
| 587 | dma_buf_map_clear(&gbo->map); /* explicitly clear mapping for next vmap call */ | ||
| 580 | } | 588 | } |
| 581 | 589 | ||
| 582 | static int drm_gem_vram_bo_driver_move(struct drm_gem_vram_object *gbo, | 590 | static int drm_gem_vram_bo_driver_move(struct drm_gem_vram_object *gbo, |
| @@ -1163,7 +1163,14 @@ retry: · 1162 unmodified lines | |||
| 1163 | if (ret) | 1163 | if (ret) |
| 1164 | goto out; | 1164 | goto out; |
| 1165 | 1165 | ||
| 1166 | if (old_fb->format != fb->format) { | 1166 | /* |
| 1167 | * Only check the FOURCC format code, excluding modifiers. This is | ||
| 1168 | * enough for all legacy drivers. Atomic drivers have their own | ||
| 1169 | * checks in their ->atomic_check implementation, which will | ||
| 1170 | * return -EINVAL if any hw or driver constraint is violated due | ||
| 1171 | * to modifier changes. | ||
| 1172 | */ | ||
| 1173 | if (old_fb->format->format != fb->format->format) { | ||
| 1167 | DRM_DEBUG_KMS("Page flip is not allowed to change frame buffer format.\n"); | 1174 | DRM_DEBUG_KMS("Page flip is not allowed to change frame buffer format.\n"); |
| 1168 | ret = -EINVAL; | 1175 | ret = -EINVAL; |
| 1169 | goto out; | 1176 | goto out; |
| @@ -388,19 +388,18 @@ int drm_syncobj_find_fence(struct drm_file *file_private, · 387 unmodified lines | |||
| 388 | return -ENOENT; | 388 | return -ENOENT; |
| 389 | 389 | ||
| 390 | *fence = drm_syncobj_fence_get(syncobj); | 390 | *fence = drm_syncobj_fence_get(syncobj); |
| 391 | drm_syncobj_put(syncobj); | ||
| 392 | 391 | ||
| 393 | if (*fence) { | 392 | if (*fence) { |
| 394 | ret = dma_fence_chain_find_seqno(fence, point); | 393 | ret = dma_fence_chain_find_seqno(fence, point); |
| 395 | if (!ret) | 394 | if (!ret) |
| 396 | return 0; | 395 | goto out; |
| 397 | dma_fence_put(*fence); | 396 | dma_fence_put(*fence); |
| 398 | } else { | 397 | } else { |
| 399 | ret = -EINVAL; | 398 | ret = -EINVAL; |
| 400 | } | 399 | } |
| 401 | 400 | ||
| 402 | if (!(flags & DRM_SYNCOBJ_WAIT_FLAGS_WAIT_FOR_SUBMIT)) | 401 | if (!(flags & DRM_SYNCOBJ_WAIT_FLAGS_WAIT_FOR_SUBMIT)) |
| 403 | return ret; | 402 | goto out; |
| 404 | 403 | ||
| 405 | memset(&wait, 0, sizeof(wait)); | 404 | memset(&wait, 0, sizeof(wait)); |
| 406 | wait.task = current; | 405 | wait.task = current; |
| @@ -432,6 +431,9 @@ int drm_syncobj_find_fence(struct drm_file *file_private, · 25 unmodified lines | |||
| 432 | if (wait.node.next) | 431 | if (wait.node.next) |
| 433 | drm_syncobj_remove_wait(syncobj, &wait); | 432 | drm_syncobj_remove_wait(syncobj, &wait); |
| 434 | 433 | ||
| 434 | out: | ||
| 435 | drm_syncobj_put(syncobj); | ||
| 436 | |||
| 435 | return ret; | 437 | return ret; |
| 436 | } | 438 | } |
| 437 | EXPORT_SYMBOL(drm_syncobj_find_fence); | 439 | EXPORT_SYMBOL(drm_syncobj_find_fence); |
| @@ -38,6 +38,7 @@ i915-y += i915_drv.o \ · 37 unmodified lines | |||
| 38 | i915_config.o \ | 38 | i915_config.o \ |
| 39 | i915_irq.o \ | 39 | i915_irq.o \ |
| 40 | i915_getparam.o \ | 40 | i915_getparam.o \ |
| 41 | i915_mitigations.o \ | ||
| 41 | i915_params.o \ | 42 | i915_params.o \ |
| 42 | i915_pci.o \ | 43 | i915_pci.o \ |
| 43 | i915_scatterlist.o \ | 44 | i915_scatterlist.o \ |
| @@ -1616,10 +1616,6 @@ static void gen11_dsi_get_power_domains(struct intel_encoder *encoder, · 1615 unmodified lines | |||
| 1616 | 1616 | ||
| 1617 | get_dsi_io_power_domains(i915, | 1617 | get_dsi_io_power_domains(i915, |
| 1618 | enc_to_intel_dsi(encoder)); | 1618 | enc_to_intel_dsi(encoder)); |
| 1619 | |||
| 1620 | if (crtc_state->dsc.compression_enable) | ||
| 1621 | intel_display_power_get(i915, | ||
| 1622 | intel_dsc_power_domain(crtc_state)); | ||
| 1623 | } | 1619 | } |
| 1624 | 1620 | ||
| 1625 | static bool gen11_dsi_get_hw_state(struct intel_encoder *encoder, | 1621 | static bool gen11_dsi_get_hw_state(struct intel_encoder *encoder, |
| @@ -2754,13 +2754,15 @@ static void icl_mg_phy_ddi_vswing_sequence(struct intel_encoder *encoder, · 2753 unmodified lines | |||
| 2754 | int n_entries, ln; | 2754 | int n_entries, ln; |
| 2755 | u32 val; | 2755 | u32 val; |
| 2756 | 2756 | ||
| 2757 | if (enc_to_dig_port(encoder)->tc_mode == TC_PORT_TBT_ALT) | ||
| 2758 | return; | ||
| 2759 | |||
| 2757 | ddi_translations = icl_get_mg_buf_trans(encoder, crtc_state, &n_entries); | 2760 | ddi_translations = icl_get_mg_buf_trans(encoder, crtc_state, &n_entries); |
| 2758 | /* The table does not have values for level 3 and level 9. */ | 2761 | if (level >= n_entries) { |
| 2759 | if (level >= n_entries || level == 3 || level == 9) { | ||
| 2760 | drm_dbg_kms(&dev_priv->drm, | 2762 | drm_dbg_kms(&dev_priv->drm, |
| 2761 | "DDI translation not found for level %d. Using %d instead.", | 2763 | "DDI translation not found for level %d. Using %d instead.", |
| 2762 | level, n_entries - 2); | 2764 | level, n_entries - 1); |
| 2763 | level = n_entries - 2; | 2765 | level = n_entries - 1; |
| 2764 | } | 2766 | } |
| 2765 | 2767 | ||
| 2766 | /* Set MG_TX_LINK_PARAMS cri_use_fs32 to 0. */ | 2768 | /* Set MG_TX_LINK_PARAMS cri_use_fs32 to 0. */ |
| @@ -2891,6 +2893,9 @@ tgl_dkl_phy_ddi_vswing_sequence(struct intel_encoder *encoder, · 124 unmodified lines | |||
| 2891 | u32 val, dpcnt_mask, dpcnt_val; | 2893 | u32 val, dpcnt_mask, dpcnt_val; |
| 2892 | int n_entries, ln; | 2894 | int n_entries, ln; |
| 2893 | 2895 | ||
| 2896 | if (enc_to_dig_port(encoder)->tc_mode == TC_PORT_TBT_ALT) | ||
| 2897 | return; | ||
| 2898 | |||
| 2894 | ddi_translations = tgl_get_dkl_buf_trans(encoder, crtc_state, &n_entries); | 2899 | ddi_translations = tgl_get_dkl_buf_trans(encoder, crtc_state, &n_entries); |
| 2895 | 2900 | ||
| 2896 | if (level >= n_entries) | 2901 | if (level >= n_entries) |
| @@ -3532,6 +3537,23 @@ static void intel_ddi_disable_fec_state(struct intel_encoder *encoder, · 635 unmodified lines | |||
| 3532 | intel_de_posting_read(dev_priv, dp_tp_ctl_reg(encoder, crtc_state)); | 3537 | intel_de_posting_read(dev_priv, dp_tp_ctl_reg(encoder, crtc_state)); |
| 3533 | } | 3538 | } |
| 3534 | 3539 | ||
| 3540 | static void intel_ddi_power_up_lanes(struct intel_encoder *encoder, | ||
| 3541 | const struct intel_crtc_state *crtc_state) | ||
| 3542 | { | ||
| 3543 | struct drm_i915_private *i915 = to_i915(encoder->base.dev); | ||
| 3544 | struct intel_digital_port *dig_port = enc_to_dig_port(encoder); | ||
| 3545 | enum phy phy = intel_port_to_phy(i915, encoder->port); | ||
| 3546 | |||
| 3547 | if (intel_phy_is_combo(i915, phy)) { | ||
| 3548 | bool lane_reversal = | ||
| 3549 | dig_port->saved_port_bits & DDI_BUF_PORT_REVERSAL; | ||
| 3550 | |||
| 3551 | intel_combo_phy_power_up_lanes(i915, phy, false, | ||
| 3552 | crtc_state->lane_count, | ||
| 3553 | lane_reversal); | ||
| 3554 | } | ||
| 3555 | } | ||
| 3556 | |||
| 3535 | static void tgl_ddi_pre_enable_dp(struct intel_atomic_state *state, | 3557 | static void tgl_ddi_pre_enable_dp(struct intel_atomic_state *state, |
| 3536 | struct intel_encoder *encoder, | 3558 | struct intel_encoder *encoder, |
| 3537 | const struct intel_crtc_state *crtc_state, | 3559 | const struct intel_crtc_state *crtc_state, |
| @@ -3621,14 +3643,7 @@ static void tgl_ddi_pre_enable_dp(struct intel_atomic_state *state, · 83 unmodified lines | |||
| 3621 | * 7.f Combo PHY: Configure PORT_CL_DW10 Static Power Down to power up | 3643 | * 7.f Combo PHY: Configure PORT_CL_DW10 Static Power Down to power up |
| 3622 | * the used lanes of the DDI. | 3644 | * the used lanes of the DDI. |
| 3623 | */ | 3645 | */ |
| 3624 | if (intel_phy_is_combo(dev_priv, phy)) { | 3646 | intel_ddi_power_up_lanes(encoder, crtc_state); |
| 3625 | bool lane_reversal = | ||
| 3626 | dig_port->saved_port_bits & DDI_BUF_PORT_REVERSAL; | ||
| 3627 | |||
| 3628 | intel_combo_phy_power_up_lanes(dev_priv, phy, false, | ||
| 3629 | crtc_state->lane_count, | ||
| 3630 | lane_reversal); | ||
| 3631 | } | ||
| 3632 | 3647 | ||
| 3633 | /* | 3648 | /* |
| 3634 | * 7.g Configure and enable DDI_BUF_CTL | 3649 | * 7.g Configure and enable DDI_BUF_CTL |
| @@ -3713,19 +3728,12 @@ static void hsw_ddi_pre_enable_dp(struct intel_atomic_state *state, · 78 unmodified lines | |||
| 3713 | else | 3728 | else |
| 3714 | intel_prepare_dp_ddi_buffers(encoder, crtc_state); | 3729 | intel_prepare_dp_ddi_buffers(encoder, crtc_state); |
| 3715 | 3730 | ||
| 3716 | if (intel_phy_is_combo(dev_priv, phy)) { | 3731 | intel_ddi_power_up_lanes(encoder, crtc_state); |
| 3717 | bool lane_reversal = | ||
| 3718 | dig_port->saved_port_bits & DDI_BUF_PORT_REVERSAL; | ||
| 3719 | |||
| 3720 | intel_combo_phy_power_up_lanes(dev_priv, phy, false, | ||
| 3721 | crtc_state->lane_count, | ||
| 3722 | lane_reversal); | ||
| 3723 | } | ||
| 3724 | 3732 | ||
| 3725 | intel_ddi_init_dp_buf_reg(encoder, crtc_state); | 3733 | intel_ddi_init_dp_buf_reg(encoder, crtc_state); |
| 3726 | if (!is_mst) | 3734 | if (!is_mst) |
| 3727 | intel_dp_set_power(intel_dp, DP_SET_POWER_D0); | 3735 | intel_dp_set_power(intel_dp, DP_SET_POWER_D0); |
| 3728 | intel_dp_configure_protocol_converter(intel_dp); | 3736 | intel_dp_configure_protocol_converter(intel_dp, crtc_state); |
| 3729 | intel_dp_sink_set_decompression_state(intel_dp, crtc_state, | 3737 | intel_dp_sink_set_decompression_state(intel_dp, crtc_state, |
| 3730 | true); | 3738 | true); |
| 3731 | intel_dp_sink_set_fec_ready(intel_dp, crtc_state); | 3739 | intel_dp_sink_set_fec_ready(intel_dp, crtc_state); |
| @@ -4206,6 +4214,8 @@ static void intel_enable_ddi_hdmi(struct intel_atomic_state *state, · 474 unmodified lines | |||
| 4206 | intel_de_write(dev_priv, reg, val); | 4214 | intel_de_write(dev_priv, reg, val); |
| 4207 | } | 4215 | } |
| 4208 | 4216 | ||
| 4217 | intel_ddi_power_up_lanes(encoder, crtc_state); | ||
| 4218 | |||
| 4209 | /* In HDMI/DVI mode, the port width, and swing/emphasis values | 4219 | /* In HDMI/DVI mode, the port width, and swing/emphasis values |
| 4210 | * are ignored so nothing special needs to be done besides | 4220 | * are ignored so nothing special needs to be done besides |
| 4211 | * enabling the port. | 4221 | * enabling the port. |
| @@ -2309,7 +2309,7 @@ intel_pin_and_fence_fb_obj(struct drm_framebuffer *fb, · 2308 unmodified lines | |||
| 2309 | */ | 2309 | */ |
| 2310 | ret = i915_vma_pin_fence(vma); | 2310 | ret = i915_vma_pin_fence(vma); |
| 2311 | if (ret != 0 && INTEL_GEN(dev_priv) < 4) { | 2311 | if (ret != 0 && INTEL_GEN(dev_priv) < 4) { |
| 2312 | i915_gem_object_unpin_from_display_plane(vma); | 2312 | i915_vma_unpin(vma); |
| 2313 | vma = ERR_PTR(ret); | 2313 | vma = ERR_PTR(ret); |
| 2314 | goto err; | 2314 | goto err; |
| 2315 | } | 2315 | } |
| @@ -2327,12 +2327,9 @@ err: · 11 unmodified lines | |||
| 2327 | 2327 | ||
| 2328 | void intel_unpin_fb_vma(struct i915_vma *vma, unsigned long flags) | 2328 | void intel_unpin_fb_vma(struct i915_vma *vma, unsigned long flags) |
| 2329 | { | 2329 | { |
| 2330 | i915_gem_object_lock(vma->obj, NULL); | ||
| 2331 | if (flags & PLANE_HAS_FENCE) | 2330 | if (flags & PLANE_HAS_FENCE) |
| 2332 | i915_vma_unpin_fence(vma); | 2331 | i915_vma_unpin_fence(vma); |
| 2333 | i915_gem_object_unpin_from_display_plane(vma); | 2332 | i915_vma_unpin(vma); |
| 2334 | i915_gem_object_unlock(vma->obj); | ||
| 2335 | |||
| 2336 | i915_vma_put(vma); | 2333 | i915_vma_put(vma); |
| 2337 | } | 2334 | } |
| 2338 | 2335 | ||
| @@ -4807,6 +4804,8 @@ u32 glk_plane_color_ctl(const struct intel_crtc_state *crtc_state, · 2468 unmodified lines | |||
| 4807 | plane_color_ctl |= PLANE_COLOR_YUV_RANGE_CORRECTION_DISABLE; | 4804 | plane_color_ctl |= PLANE_COLOR_YUV_RANGE_CORRECTION_DISABLE; |
| 4808 | } else if (fb->format->is_yuv) { | 4805 | } else if (fb->format->is_yuv) { |
| 4809 | plane_color_ctl |= PLANE_COLOR_INPUT_CSC_ENABLE; | 4806 | plane_color_ctl |= PLANE_COLOR_INPUT_CSC_ENABLE; |
| 4807 | if (plane_state->hw.color_range == DRM_COLOR_YCBCR_FULL_RANGE) | ||
| 4808 | plane_color_ctl |= PLANE_COLOR_YUV_RANGE_CORRECTION_DISABLE; | ||
| 4810 | } | 4809 | } |
| 4811 | 4810 | ||
| 4812 | return plane_color_ctl; | 4811 | return plane_color_ctl; |
| @@ -1436,6 +1436,9 @@ struct intel_dp { · 1435 unmodified lines | |||
| 1436 | bool ycbcr_444_to_420; | 1436 | bool ycbcr_444_to_420; |
| 1437 | } dfp; | 1437 | } dfp; |
| 1438 | 1438 | ||
| 1439 | /* To control wakeup latency, e.g. for irq-driven dp aux transfers. */ | ||
| 1440 | struct pm_qos_request pm_qos; | ||
| 1441 | |||
| 1439 | /* Display stream compression testing */ | 1442 | /* Display stream compression testing */ |
| 1440 | bool force_dsc_en; | 1443 | bool force_dsc_en; |
| 1441 | 1444 | ||
| @@ -1489,7 +1489,7 @@ intel_dp_aux_xfer(struct intel_dp *intel_dp, · 1488 unmodified lines | |||
| 1489 | * lowest possible wakeup latency and so prevent the cpu from going into | 1489 | * lowest possible wakeup latency and so prevent the cpu from going into |
| 1490 | * deep sleep states. | 1490 | * deep sleep states. |
| 1491 | */ | 1491 | */ |
| 1492 | cpu_latency_qos_update_request(&i915->pm_qos, 0); | 1492 | cpu_latency_qos_update_request(&intel_dp->pm_qos, 0); |
| 1493 | 1493 | ||
| 1494 | intel_dp_check_edp(intel_dp); | 1494 | intel_dp_check_edp(intel_dp); |
| 1495 | 1495 | ||
| @@ -1622,7 +1622,7 @@ done: · 126 unmodified lines | |||
| 1622 | 1622 | ||
| 1623 | ret = recv_bytes; | 1623 | ret = recv_bytes; |
| 1624 | out: | 1624 | out: |
| 1625 | cpu_latency_qos_update_request(&i915->pm_qos, PM_QOS_DEFAULT_VALUE); | 1625 | cpu_latency_qos_update_request(&intel_dp->pm_qos, PM_QOS_DEFAULT_VALUE); |
| 1626 | 1626 | ||
| 1627 | if (vdd) | 1627 | if (vdd) |
| 1628 | edp_panel_vdd_off(intel_dp, false); | 1628 | edp_panel_vdd_off(intel_dp, false); |
| @@ -1898,6 +1898,9 @@ static i915_reg_t tgl_aux_data_reg(struct intel_dp *intel_dp, int index) · 269 unmodified lines | |||
| 1898 | static void | 1898 | static void |
| 1899 | intel_dp_aux_fini(struct intel_dp *intel_dp) | 1899 | intel_dp_aux_fini(struct intel_dp *intel_dp) |
| 1900 | { | 1900 | { |
| 1901 | if (cpu_latency_qos_request_active(&intel_dp->pm_qos)) | ||
| 1902 | cpu_latency_qos_remove_request(&intel_dp->pm_qos); | ||
| 1903 | |||
| 1901 | kfree(intel_dp->aux.name); | 1904 | kfree(intel_dp->aux.name); |
| 1902 | } | 1905 | } |
| 1903 | 1906 | ||
| @@ -1950,6 +1953,7 @@ intel_dp_aux_init(struct intel_dp *intel_dp) · 46 unmodified lines | |||
| 1950 | encoder->base.name); | 1953 | encoder->base.name); |
| 1951 | 1954 | ||
| 1952 | intel_dp->aux.transfer = intel_dp_aux_transfer; | 1955 | intel_dp->aux.transfer = intel_dp_aux_transfer; |
| 1956 | cpu_latency_qos_add_request(&intel_dp->pm_qos, PM_QOS_DEFAULT_VALUE); | ||
| 1953 | } | 1957 | } |
| 1954 | 1958 | ||
| 1955 | bool intel_dp_source_supports_hbr2(struct intel_dp *intel_dp) | 1959 | bool intel_dp_source_supports_hbr2(struct intel_dp *intel_dp) |
| @@ -4010,7 +4014,8 @@ static void intel_dp_enable_port(struct intel_dp *intel_dp, · 2054 unmodified lines | |||
| 4010 | intel_de_posting_read(dev_priv, intel_dp->output_reg); | 4014 | intel_de_posting_read(dev_priv, intel_dp->output_reg); |
| 4011 | } | 4015 | } |
| 4012 | 4016 | ||
| 4013 | void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp) | 4017 | void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp, |
| 4018 | const struct intel_crtc_state *crtc_state) | ||
| 4014 | { | 4019 | { |
| 4015 | struct drm_i915_private *i915 = dp_to_i915(intel_dp); | 4020 | struct drm_i915_private *i915 = dp_to_i915(intel_dp); |
| 4016 | u8 tmp; | 4021 | u8 tmp; |
| @@ -4029,8 +4034,8 @@ void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp) · 12 unmodified lines | |||
| 4029 | drm_dbg_kms(&i915->drm, "Failed to set protocol converter HDMI mode to %s\n", | 4034 | drm_dbg_kms(&i915->drm, "Failed to set protocol converter HDMI mode to %s\n", |
| 4030 | enableddisabled(intel_dp->has_hdmi_sink)); | 4035 | enableddisabled(intel_dp->has_hdmi_sink)); |
| 4031 | 4036 | ||
| 4032 | tmp = intel_dp->dfp.ycbcr_444_to_420 ? | 4037 | tmp = crtc_state->output_format == INTEL_OUTPUT_FORMAT_YCBCR444 && |
| 4033 | DP_CONVERSION_TO_YCBCR420_ENABLE : 0; | 4038 | intel_dp->dfp.ycbcr_444_to_420 ? DP_CONVERSION_TO_YCBCR420_ENABLE : 0; |
| 4034 | 4039 | ||
| 4035 | if (drm_dp_dpcd_writeb(&intel_dp->aux, | 4040 | if (drm_dp_dpcd_writeb(&intel_dp->aux, |
| 4036 | DP_PROTOCOL_CONVERTER_CONTROL_1, tmp) != 1) | 4041 | DP_PROTOCOL_CONVERTER_CONTROL_1, tmp) != 1) |
| @@ -4084,7 +4089,7 @@ static void intel_enable_dp(struct intel_atomic_state *state, · 47 unmodified lines | |||
| 4084 | } | 4089 | } |
| 4085 | 4090 | ||
| 4086 | intel_dp_set_power(intel_dp, DP_SET_POWER_D0); | 4091 | intel_dp_set_power(intel_dp, DP_SET_POWER_D0); |
| 4087 | intel_dp_configure_protocol_converter(intel_dp); | 4092 | intel_dp_configure_protocol_converter(intel_dp, pipe_config); |
| 4088 | intel_dp_start_link_train(intel_dp, pipe_config); | 4093 | intel_dp_start_link_train(intel_dp, pipe_config); |
| 4089 | intel_dp_stop_link_train(intel_dp, pipe_config); | 4094 | intel_dp_stop_link_train(intel_dp, pipe_config); |
| 4090 | 4095 | ||
| @@ -4632,24 +4637,6 @@ ivb_cpu_edp_set_signal_levels(struct intel_dp *intel_dp, · 541 unmodified lines | |||
| 4632 | intel_de_posting_read(dev_priv, intel_dp->output_reg); | 4637 | intel_de_posting_read(dev_priv, intel_dp->output_reg); |
| 4633 | } | 4638 | } |
| 4634 | 4639 | ||
| 4635 | void intel_dp_set_signal_levels(struct intel_dp *intel_dp, | ||
| 4636 | const struct intel_crtc_state *crtc_state) | ||
| 4637 | { | ||
| 4638 | struct drm_i915_private *dev_priv = dp_to_i915(intel_dp); | ||
| 4639 | u8 train_set = intel_dp->train_set[0]; | ||
| 4640 | |||
| 4641 | drm_dbg_kms(&dev_priv->drm, "Using vswing level %d%s\n", | ||
| 4642 | train_set & DP_TRAIN_VOLTAGE_SWING_MASK, | ||
| 4643 | train_set & DP_TRAIN_MAX_SWING_REACHED ? " (max)" : ""); | ||
| 4644 | drm_dbg_kms(&dev_priv->drm, "Using pre-emphasis level %d%s\n", | ||
| 4645 | (train_set & DP_TRAIN_PRE_EMPHASIS_MASK) >> | ||
| 4646 | DP_TRAIN_PRE_EMPHASIS_SHIFT, | ||
| 4647 | train_set & DP_TRAIN_MAX_PRE_EMPHASIS_REACHED ? | ||
| 4648 | " (max)" : ""); | ||
| 4649 | |||
| 4650 | intel_dp->set_signal_levels(intel_dp, crtc_state); | ||
| 4651 | } | ||
| 4652 | |||
| 4653 | void | 4640 | void |
| 4654 | intel_dp_program_link_training_pattern(struct intel_dp *intel_dp, | 4641 | intel_dp_program_link_training_pattern(struct intel_dp *intel_dp, |
| 4655 | const struct intel_crtc_state *crtc_state, | 4642 | const struct intel_crtc_state *crtc_state, |
| @@ -5698,7 +5685,7 @@ static void intel_dp_process_phy_request(struct intel_dp *intel_dp, · 1042 unmodified lines | |||
| 5698 | 5685 | ||
| 5699 | intel_dp_autotest_phy_ddi_disable(intel_dp, crtc_state); | 5686 | intel_dp_autotest_phy_ddi_disable(intel_dp, crtc_state); |
| 5700 | 5687 | ||
| 5701 | intel_dp_set_signal_levels(intel_dp, crtc_state); | 5688 | intel_dp_set_signal_levels(intel_dp, crtc_state, DP_PHY_DPRX); |
| 5702 | 5689 | ||
| 5703 | intel_dp_phy_pattern_update(intel_dp, crtc_state); | 5690 | intel_dp_phy_pattern_update(intel_dp, crtc_state); |
| 5704 | 5691 | ||
| @@ -51,7 +51,8 @@ int intel_dp_get_link_train_fallback_values(struct intel_dp *intel_dp, · 50 unmodified lines | |||
| 51 | int intel_dp_retrain_link(struct intel_encoder *encoder, | 51 | int intel_dp_retrain_link(struct intel_encoder *encoder, |
| 52 | struct drm_modeset_acquire_ctx *ctx); | 52 | struct drm_modeset_acquire_ctx *ctx); |
| 53 | void intel_dp_set_power(struct intel_dp *intel_dp, u8 mode); | 53 | void intel_dp_set_power(struct intel_dp *intel_dp, u8 mode); |
| 54 | void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp); | 54 | void intel_dp_configure_protocol_converter(struct intel_dp *intel_dp, |
| 55 | const struct intel_crtc_state *crtc_state); | ||
| 55 | void intel_dp_sink_set_decompression_state(struct intel_dp *intel_dp, | 56 | void intel_dp_sink_set_decompression_state(struct intel_dp *intel_dp, |
| 56 | const struct intel_crtc_state *crtc_state, | 57 | const struct intel_crtc_state *crtc_state, |
| 57 | bool enable); | 58 | bool enable); |
| @@ -95,9 +96,6 @@ void · 37 unmodified lines | |||
| 95 | intel_dp_program_link_training_pattern(struct intel_dp *intel_dp, | 96 | intel_dp_program_link_training_pattern(struct intel_dp *intel_dp, |
| 96 | const struct intel_crtc_state *crtc_state, | 97 | const struct intel_crtc_state *crtc_state, |
| 97 | u8 dp_train_pat); | 98 | u8 dp_train_pat); |
| 98 | void | ||
| 99 | intel_dp_set_signal_levels(struct intel_dp *intel_dp, | ||
| 100 | const struct intel_crtc_state *crtc_state); | ||
| 101 | void intel_dp_compute_rate(struct intel_dp *intel_dp, int port_clock, | 99 | void intel_dp_compute_rate(struct intel_dp *intel_dp, int port_clock, |
| 102 | u8 *link_bw, u8 *rate_select); | 100 | u8 *link_bw, u8 *rate_select); |
| 103 | bool intel_dp_source_supports_hbr2(struct intel_dp *intel_dp); | 101 | bool intel_dp_source_supports_hbr2(struct intel_dp *intel_dp); |
| @@ -334,6 +334,27 @@ intel_dp_set_link_train(struct intel_dp *intel_dp, · 333 unmodified lines | |||
| 334 | return drm_dp_dpcd_write(&intel_dp->aux, reg, buf, len) == len; | 334 | return drm_dp_dpcd_write(&intel_dp->aux, reg, buf, len) == len; |
| 335 | } | 335 | } |
| 336 | 336 | ||
| 337 | void intel_dp_set_signal_levels(struct intel_dp *intel_dp, | ||
| 338 | const struct intel_crtc_state *crtc_state, | ||
| 339 | enum drm_dp_phy dp_phy) | ||
| 340 | { | ||
| 341 | struct drm_i915_private *dev_priv = dp_to_i915(intel_dp); | ||
| 342 | u8 train_set = intel_dp->train_set[0]; | ||
| 343 | char phy_name[10]; | ||
| 344 | |||
| 345 | drm_dbg_kms(&dev_priv->drm, "Using vswing level %d%s, pre-emphasis level %d%s, at %s\n", | ||
| 346 | train_set & DP_TRAIN_VOLTAGE_SWING_MASK, | ||
| 347 | train_set & DP_TRAIN_MAX_SWING_REACHED ? " (max)" : "", | ||
| 348 | (train_set & DP_TRAIN_PRE_EMPHASIS_MASK) >> | ||
| 349 | DP_TRAIN_PRE_EMPHASIS_SHIFT, | ||
| 350 | train_set & DP_TRAIN_MAX_PRE_EMPHASIS_REACHED ? | ||
| 351 | " (max)" : "", | ||
| 352 | intel_dp_phy_name(dp_phy, phy_name, sizeof(phy_name))); | ||
| 353 | |||
| 354 | if (intel_dp_phy_is_downstream_of_source(intel_dp, dp_phy)) | ||
| 355 | intel_dp->set_signal_levels(intel_dp, crtc_state); | ||
| 356 | } | ||
| 357 | |||
| 337 | static bool | 358 | static bool |
| 338 | intel_dp_reset_link_train(struct intel_dp *intel_dp, | 359 | intel_dp_reset_link_train(struct intel_dp *intel_dp, |
| 339 | const struct intel_crtc_state *crtc_state, | 360 | const struct intel_crtc_state *crtc_state, |
| @@ -341,7 +362,7 @@ intel_dp_reset_link_train(struct intel_dp *intel_dp, · 1 unmodified line | |||
| 341 | u8 dp_train_pat) | 362 | u8 dp_train_pat) |
| 342 | { | 363 | { |
| 343 | memset(intel_dp->train_set, 0, sizeof(intel_dp->train_set)); | 364 | memset(intel_dp->train_set, 0, sizeof(intel_dp->train_set)); |
| 344 | intel_dp_set_signal_levels(intel_dp, crtc_state); | 365 | intel_dp_set_signal_levels(intel_dp, crtc_state, dp_phy); |
| 345 | return intel_dp_set_link_train(intel_dp, crtc_state, dp_phy, dp_train_pat); | 366 | return intel_dp_set_link_train(intel_dp, crtc_state, dp_phy, dp_train_pat); |
| 346 | } | 367 | } |
| 347 | 368 | ||
| @@ -355,7 +376,7 @@ intel_dp_update_link_train(struct intel_dp *intel_dp, · 7 unmodified lines | |||
| 355 | DP_TRAINING_LANE0_SET_PHY_REPEATER(dp_phy); | 376 | DP_TRAINING_LANE0_SET_PHY_REPEATER(dp_phy); |
| 356 | int ret; | 377 | int ret; |
| 357 | 378 | ||
| 358 | intel_dp_set_signal_levels(intel_dp, crtc_state); | 379 | intel_dp_set_signal_levels(intel_dp, crtc_state, dp_phy); |
| 359 | 380 | ||
| 360 | ret = drm_dp_dpcd_write(&intel_dp->aux, reg, | 381 | ret = drm_dp_dpcd_write(&intel_dp->aux, reg, |
| 361 | intel_dp->train_set, crtc_state->lane_count); | 382 | intel_dp->train_set, crtc_state->lane_count); |
| @@ -17,6 +17,9 @@ void intel_dp_get_adjust_train(struct intel_dp *intel_dp, · 16 unmodified lines | |||
| 17 | const struct intel_crtc_state *crtc_state, | 17 | const struct intel_crtc_state *crtc_state, |
| 18 | enum drm_dp_phy dp_phy, | 18 | enum drm_dp_phy dp_phy, |
| 19 | const u8 link_status[DP_LINK_STATUS_SIZE]); | 19 | const u8 link_status[DP_LINK_STATUS_SIZE]); |
| 20 | void intel_dp_set_signal_levels(struct intel_dp *intel_dp, | ||
| 21 | const struct intel_crtc_state *crtc_state, | ||
| 22 | enum drm_dp_phy dp_phy); | ||
| 20 | void intel_dp_start_link_train(struct intel_dp *intel_dp, | 23 | void intel_dp_start_link_train(struct intel_dp *intel_dp, |
| 21 | const struct intel_crtc_state *crtc_state); | 24 | const struct intel_crtc_state *crtc_state); |
| 22 | void intel_dp_stop_link_train(struct intel_dp *intel_dp, | 25 | void intel_dp_stop_link_train(struct intel_dp *intel_dp, |
| @@ -69,7 +69,9 @@ static int intel_dp_mst_compute_link_config(struct intel_encoder *encoder, · 68 unmodified lines | |||
| 69 | 69 | ||
| 70 | slots = drm_dp_atomic_find_vcpi_slots(state, &intel_dp->mst_mgr, | 70 | slots = drm_dp_atomic_find_vcpi_slots(state, &intel_dp->mst_mgr, |
| 71 | connector->port, | 71 | connector->port, |
| 72 | crtc_state->pbn, 0); | 72 | crtc_state->pbn, |
| 73 | drm_dp_get_vc_payload_bw(crtc_state->port_clock, | ||
| 74 | crtc_state->lane_count)); | ||
| 73 | if (slots == -EDEADLK) | 75 | if (slots == -EDEADLK) |
| 74 | return slots; | 76 | return slots; |
| 75 | if (slots >= 0) | 77 | if (slots >= 0) |
| @@ -2210,6 +2210,7 @@ void intel_hdcp_update_pipe(struct intel_atomic_state *state, · 2209 unmodified lines | |||
| 2210 | if (content_protection_type_changed) { | 2210 | if (content_protection_type_changed) { |
| 2211 | mutex_lock(&hdcp->mutex); | 2211 | mutex_lock(&hdcp->mutex); |
| 2212 | hdcp->value = DRM_MODE_CONTENT_PROTECTION_DESIRED; | 2212 | hdcp->value = DRM_MODE_CONTENT_PROTECTION_DESIRED; |
| 2213 | drm_connector_get(&connector->base); | ||
| 2213 | schedule_work(&hdcp->prop_work); | 2214 | schedule_work(&hdcp->prop_work); |
| 2214 | mutex_unlock(&hdcp->mutex); | 2215 | mutex_unlock(&hdcp->mutex); |
| 2215 | } | 2216 | } |
| @@ -2221,6 +2222,14 @@ void intel_hdcp_update_pipe(struct intel_atomic_state *state, · 5 unmodified lines | |||
| 2221 | desired_and_not_enabled = | 2222 | desired_and_not_enabled = |
| 2222 | hdcp->value != DRM_MODE_CONTENT_PROTECTION_ENABLED; | 2223 | hdcp->value != DRM_MODE_CONTENT_PROTECTION_ENABLED; |
| 2223 | mutex_unlock(&hdcp->mutex); | 2224 | mutex_unlock(&hdcp->mutex); |
| 2225 | /* | ||
| 2226 | * If HDCP already ENABLED and CP property is DESIRED, schedule | ||
| 2227 | * prop_work to update correct CP property to user space. | ||
| 2228 | */ | ||
| 2229 | if (!desired_and_not_enabled && !content_protection_type_changed) { | ||
| 2230 | drm_connector_get(&connector->base); | ||
| 2231 | schedule_work(&hdcp->prop_work); | ||
| 2232 | } | ||
| 2224 | } | 2233 | } |
| 2225 | 2234 | ||
| 2226 | if (desired_and_not_enabled || content_protection_type_changed) | 2235 | if (desired_and_not_enabled || content_protection_type_changed) |
| @@ -182,6 +182,7 @@ struct intel_overlay { · 181 unmodified lines | |||
| 182 | struct intel_crtc *crtc; | 182 | struct intel_crtc *crtc; |
| 183 | struct i915_vma *vma; | 183 | struct i915_vma *vma; |
| 184 | struct i915_vma *old_vma; | 184 | struct i915_vma *old_vma; |
| 185 | struct intel_frontbuffer *frontbuffer; | ||
| 185 | bool active; | 186 | bool active; |
| 186 | bool pfit_active; | 187 | bool pfit_active; |
| 187 | u32 pfit_vscale_ratio; /* shifted-point number, (1<<12) == 1.0 */ | 188 | u32 pfit_vscale_ratio; /* shifted-point number, (1<<12) == 1.0 */ |
| @@ -282,21 +283,19 @@ static void intel_overlay_flip_prepare(struct intel_overlay *overlay, · 94 unmodified lines | |||
| 282 | struct i915_vma *vma) | 283 | struct i915_vma *vma) |
| 283 | { | 284 | { |
| 284 | enum pipe pipe = overlay->crtc->pipe; | 285 | enum pipe pipe = overlay->crtc->pipe; |
| 285 | struct intel_frontbuffer *from = NULL, *to = NULL; | 286 | struct intel_frontbuffer *frontbuffer = NULL; |
| 286 | 287 | ||
| 287 | drm_WARN_ON(&overlay->i915->drm, overlay->old_vma); | 288 | drm_WARN_ON(&overlay->i915->drm, overlay->old_vma); |
| 288 | 289 | ||
| 289 | if (overlay->vma) | ||
| 290 | from = intel_frontbuffer_get(overlay->vma->obj); | ||
| 291 | if (vma) | 290 | if (vma) |
| 292 | to = intel_frontbuffer_get(vma->obj); | 291 | frontbuffer = intel_frontbuffer_get(vma->obj); |
| 293 | 292 | ||
| 294 | intel_frontbuffer_track(from, to, INTEL_FRONTBUFFER_OVERLAY(pipe)); | 293 | intel_frontbuffer_track(overlay->frontbuffer, frontbuffer, |
| 294 | INTEL_FRONTBUFFER_OVERLAY(pipe)); | ||
| 295 | 295 | ||
| 296 | if (to) | 296 | if (overlay->frontbuffer) |
| 297 | intel_frontbuffer_put(to); | 297 | intel_frontbuffer_put(overlay->frontbuffer); |
| 298 | if (from) | 298 | overlay->frontbuffer = frontbuffer; |
| 299 | intel_frontbuffer_put(from); | ||
| 300 | 299 | ||
| 301 | intel_frontbuffer_flip_prepare(overlay->i915, | 300 | intel_frontbuffer_flip_prepare(overlay->i915, |
| 302 | INTEL_FRONTBUFFER_OVERLAY(pipe)); | 301 | INTEL_FRONTBUFFER_OVERLAY(pipe)); |
| @@ -359,7 +358,7 @@ static void intel_overlay_release_old_vma(struct intel_overlay *overlay) · 56 unmodified lines | |||
| 359 | intel_frontbuffer_flip_complete(overlay->i915, | 358 | intel_frontbuffer_flip_complete(overlay->i915, |
| 360 | INTEL_FRONTBUFFER_OVERLAY(overlay->crtc->pipe)); | 359 | INTEL_FRONTBUFFER_OVERLAY(overlay->crtc->pipe)); |
| 361 | 360 | ||
| 362 | i915_gem_object_unpin_from_display_plane(vma); | 361 | i915_vma_unpin(vma); |
| 363 | i915_vma_put(vma); | 362 | i915_vma_put(vma); |
| 364 | } | 363 | } |
| 365 | 364 | ||
| @@ -860,7 +859,7 @@ static int intel_overlay_do_put_image(struct intel_overlay *overlay, · 494 unmodified lines | |||
| 860 | return 0; | 859 | return 0; |
| 861 | 860 | ||
| 862 | out_unpin: | 861 | out_unpin: |
| 863 | i915_gem_object_unpin_from_display_plane(vma); | 862 | i915_vma_unpin(vma); |
| 864 | out_pin_section: | 863 | out_pin_section: |
| 865 | atomic_dec(&dev_priv->gpu_error.pending_fb_pin); | 864 | atomic_dec(&dev_priv->gpu_error.pending_fb_pin); |
| 866 | 865 | ||
| @@ -1650,16 +1650,13 @@ static int lpt_setup_backlight(struct intel_connector *connector, enum pipe unus · 1649 unmodified lines | |||
| 1650 | val = pch_get_backlight(connector); | 1650 | val = pch_get_backlight(connector); |
| 1651 | else | 1651 | else |
| 1652 | val = lpt_get_backlight(connector); | 1652 | val = lpt_get_backlight(connector); |
| 1653 | val = intel_panel_compute_brightness(connector, val); | ||
| 1654 | panel->backlight.level = clamp(val, panel->backlight.min, | ||
| 1655 | panel->backlight.max); | ||
| 1656 | 1653 | ||
| 1657 | if (cpu_mode) { | 1654 | if (cpu_mode) { |
| 1658 | drm_dbg_kms(&dev_priv->drm, | 1655 | drm_dbg_kms(&dev_priv->drm, |
| 1659 | "CPU backlight register was enabled, switching to PCH override\n"); | 1656 | "CPU backlight register was enabled, switching to PCH override\n"); |
| 1660 | 1657 | ||
| 1661 | /* Write converted CPU PWM value to PCH override register */ | 1658 | /* Write converted CPU PWM value to PCH override register */ |
| 1662 | lpt_set_backlight(connector->base.state, panel->backlight.level); | 1659 | lpt_set_backlight(connector->base.state, val); |
| 1663 | intel_de_write(dev_priv, BLC_PWM_PCH_CTL1, | 1660 | intel_de_write(dev_priv, BLC_PWM_PCH_CTL1, |
| 1664 | pch_ctl1 | BLM_PCH_OVERRIDE_ENABLE); | 1661 | pch_ctl1 | BLM_PCH_OVERRIDE_ENABLE); |
| 1665 | 1662 | ||
| @@ -1667,6 +1664,10 @@ static int lpt_setup_backlight(struct intel_connector *connector, enum pipe unus · 1 unmodified line | |||
| 1667 | cpu_ctl2 & ~BLM_PWM_ENABLE); | 1664 | cpu_ctl2 & ~BLM_PWM_ENABLE); |
| 1668 | } | 1665 | } |
| 1669 | 1666 | ||
| 1667 | val = intel_panel_compute_brightness(connector, val); | ||
| 1668 | panel->backlight.level = clamp(val, panel->backlight.min, | ||
| 1669 | panel->backlight.max); | ||
| 1670 | |||
| 1670 | return 0; | 1671 | return 0; |
| 1671 | } | 1672 | } |
| 1672 | 1673 | ||
| @@ -618,13 +618,19 @@ skl_program_scaler(struct intel_plane *plane, · 617 unmodified lines | |||
| 618 | 618 | ||
| 619 | /* Preoffset values for YUV to RGB Conversion */ | 619 | /* Preoffset values for YUV to RGB Conversion */ |
| 620 | #define PREOFF_YUV_TO_RGB_HI 0x1800 | 620 | #define PREOFF_YUV_TO_RGB_HI 0x1800 |
| 621 | #define PREOFF_YUV_TO_RGB_ME 0x1F00 | 621 | #define PREOFF_YUV_TO_RGB_ME 0x0000 |
| 622 | #define PREOFF_YUV_TO_RGB_LO 0x1800 | 622 | #define PREOFF_YUV_TO_RGB_LO 0x1800 |
| 623 | 623 | ||
| 624 | #define ROFF(x) (((x) & 0xffff) << 16) | 624 | #define ROFF(x) (((x) & 0xffff) << 16) |
| 625 | #define GOFF(x) (((x) & 0xffff) << 0) | 625 | #define GOFF(x) (((x) & 0xffff) << 0) |
| 626 | #define BOFF(x) (((x) & 0xffff) << 16) | 626 | #define BOFF(x) (((x) & 0xffff) << 16) |
| 627 | 627 | ||
| 628 | /* | ||
| 629 | * Programs the input color space conversion stage for ICL HDR planes. | ||
| 630 | * Note that it is assumed that this stage always happens after YUV | ||
| 631 | * range correction. Thus, the input to this stage is assumed to be | ||
| 632 | * in full-range YCbCr. | ||
| 633 | */ | ||
| 628 | static void | 634 | static void |
| 629 | icl_program_input_csc(struct intel_plane *plane, | 635 | icl_program_input_csc(struct intel_plane *plane, |
| 630 | const struct intel_crtc_state *crtc_state, | 636 | const struct intel_crtc_state *crtc_state, |
| @@ -672,52 +678,7 @@ icl_program_input_csc(struct intel_plane *plane, · 41 unmodified lines | |||
| 672 | 0x0, 0x7800, 0x7F10, | 678 | 0x0, 0x7800, 0x7F10, |
| 673 | }, | 679 | }, |
| 674 | }; | 680 | }; |
| 675 | 681 | const u16 *csc = input_csc_matrix[plane_state->hw.color_encoding]; | |
| 676 | /* Matrix for Limited Range to Full Range Conversion */ | ||
| 677 | static const u16 input_csc_matrix_lr[][9] = { | ||
| 678 | /* | ||
| 679 | * BT.601 Limted range YCbCr -> full range RGB | ||
| 680 | * The matrix required is : | ||
| 681 | * [1.164384, 0.000, 1.596027, | ||
| 682 | * 1.164384, -0.39175, -0.812813, | ||
| 683 | * 1.164384, 2.017232, 0.0000] | ||
| 684 | */ | ||
| 685 | [DRM_COLOR_YCBCR_BT601] = { | ||
| 686 | 0x7CC8, 0x7950, 0x0, | ||
| 687 | 0x8D00, 0x7950, 0x9C88, | ||
| 688 | 0x0, 0x7950, 0x6810, | ||
| 689 | }, | ||
| 690 | /* | ||
| 691 | * BT.709 Limited range YCbCr -> full range RGB | ||
| 692 | * The matrix required is : | ||
| 693 | * [1.164384, 0.000, 1.792741, | ||
| 694 | * 1.164384, -0.213249, -0.532909, | ||
| 695 | * 1.164384, 2.112402, 0.0000] | ||
| 696 | */ | ||
| 697 | [DRM_COLOR_YCBCR_BT709] = { | ||
| 698 | 0x7E58, 0x7950, 0x0, | ||
| 699 | 0x8888, 0x7950, 0xADA8, | ||
| 700 | 0x0, 0x7950, 0x6870, | ||
| 701 | }, | ||
| 702 | /* | ||
| 703 | * BT.2020 Limited range YCbCr -> full range RGB | ||
| 704 | * The matrix required is : | ||
| 705 | * [1.164, 0.000, 1.678, | ||
| 706 | * 1.164, -0.1873, -0.6504, | ||
| 707 | * 1.164, 2.1417, 0.0000] | ||
| 708 | */ | ||
| 709 | [DRM_COLOR_YCBCR_BT2020] = { | ||
| 710 | 0x7D70, 0x7950, 0x0, | ||
| 711 | 0x8A68, 0x7950, 0xAC00, | ||
| 712 | 0x0, 0x7950, 0x6890, | ||
| 713 | }, | ||
| 714 | }; | ||
| 715 | const u16 *csc; | ||
| 716 | |||
| 717 | if (plane_state->hw.color_range == DRM_COLOR_YCBCR_FULL_RANGE) | ||
| 718 | csc = input_csc_matrix[plane_state->hw.color_encoding]; | ||
| 719 | else | ||
| 720 | csc = input_csc_matrix_lr[plane_state->hw.color_encoding]; | ||
| 721 | 682 | ||
| 722 | intel_de_write_fw(dev_priv, PLANE_INPUT_CSC_COEFF(pipe, plane_id, 0), | 683 | intel_de_write_fw(dev_priv, PLANE_INPUT_CSC_COEFF(pipe, plane_id, 0), |
| 723 | ROFF(csc[0]) | GOFF(csc[1])); | 684 | ROFF(csc[0]) | GOFF(csc[1])); |
| @@ -734,14 +695,8 @@ icl_program_input_csc(struct intel_plane *plane, · 10 unmodified lines | |||
| 734 | 695 | ||
| 735 | intel_de_write_fw(dev_priv, PLANE_INPUT_CSC_PREOFF(pipe, plane_id, 0), | 696 | intel_de_write_fw(dev_priv, PLANE_INPUT_CSC_PREOFF(pipe, plane_id, 0), |
| 736 | PREOFF_YUV_TO_RGB_HI); | 697 | PREOFF_YUV_TO_RGB_HI); |
| 737 | if (plane_state->hw.color_range == DRM_COLOR_YCBCR_FULL_RANGE) | 698 | intel_de_write_fw(dev_priv, PLANE_INPUT_CSC_PREOFF(pipe, plane_id, 1), |
| 738 | intel_de_write_fw(dev_priv, | 699 | PREOFF_YUV_TO_RGB_ME); |
| 739 | PLANE_INPUT_CSC_PREOFF(pipe, plane_id, 1), | ||
| 740 | 0); | ||
| 741 | else | ||
| 742 | intel_de_write_fw(dev_priv, | ||
| 743 | PLANE_INPUT_CSC_PREOFF(pipe, plane_id, 1), | ||
| 744 | PREOFF_YUV_TO_RGB_ME); | ||
| 745 | intel_de_write_fw(dev_priv, PLANE_INPUT_CSC_PREOFF(pipe, plane_id, 2), | 700 | intel_de_write_fw(dev_priv, PLANE_INPUT_CSC_PREOFF(pipe, plane_id, 2), |
| 746 | PREOFF_YUV_TO_RGB_LO); | 701 | PREOFF_YUV_TO_RGB_LO); |
| 747 | intel_de_write_fw(dev_priv, | 702 | intel_de_write_fw(dev_priv, |
| @@ -23,36 +23,6 @@ static const char *tc_port_mode_name(enum tc_port_mode mode) · 22 unmodified lines | |||
| 23 | return names[mode]; | 23 | return names[mode]; |
| 24 | } | 24 | } |
| 25 | 25 | ||
| 26 | static void | ||
| 27 | tc_port_load_fia_params(struct drm_i915_private *i915, | ||
| 28 | struct intel_digital_port *dig_port) | ||
| 29 | { | ||
| 30 | enum port port = dig_port->base.port; | ||
| 31 | enum tc_port tc_port = intel_port_to_tc(i915, port); | ||
| 32 | u32 modular_fia; | ||
| 33 | |||
| 34 | if (INTEL_INFO(i915)->display.has_modular_fia) { | ||
| 35 | modular_fia = intel_uncore_read(&i915->uncore, | ||
| 36 | PORT_TX_DFLEXDPSP(FIA1)); | ||
| 37 | drm_WARN_ON(&i915->drm, modular_fia == 0xffffffff); | ||
| 38 | modular_fia &= MODULAR_FIA_MASK; | ||
| 39 | } else { | ||
| 40 | modular_fia = 0; | ||
| 41 | } | ||
| 42 | |||
| 43 | /* | ||
| 44 | * Each Modular FIA instance houses 2 TC ports. In SOC that has more | ||
| 45 | * than two TC ports, there are multiple instances of Modular FIA. | ||
| 46 | */ | ||
| 47 | if (modular_fia) { | ||
| 48 | dig_port->tc_phy_fia = tc_port / 2; | ||
| 49 | dig_port->tc_phy_fia_idx = tc_port % 2; | ||
| 50 | } else { | ||
| 51 | dig_port->tc_phy_fia = FIA1; | ||
| 52 | dig_port->tc_phy_fia_idx = tc_port; | ||
| 53 | } | ||
| 54 | } | ||
| 55 | |||
| 56 | static enum intel_display_power_domain | 26 | static enum intel_display_power_domain |
| 57 | tc_cold_get_power_domain(struct intel_digital_port *dig_port) | 27 | tc_cold_get_power_domain(struct intel_digital_port *dig_port) |
| 58 | { | 28 | { |
| @@ -646,6 +616,43 @@ void intel_tc_port_put_link(struct intel_digital_port *dig_port) · 587 unmodified lines | |||
| 646 | mutex_unlock(&dig_port->tc_lock); | 616 | mutex_unlock(&dig_port->tc_lock); |
| 647 | } | 617 | } |
| 648 | 618 | ||
| 619 | static bool | ||
| 620 | tc_has_modular_fia(struct drm_i915_private *i915, struct intel_digital_port *dig_port) | ||
| 621 | { | ||
| 622 | intel_wakeref_t wakeref; | ||
| 623 | u32 val; | ||
| 624 | |||
| 625 | if (!INTEL_INFO(i915)->display.has_modular_fia) | ||
| 626 | return false; | ||
| 627 | |||
| 628 | wakeref = tc_cold_block(dig_port); | ||
| 629 | val = intel_uncore_read(&i915->uncore, PORT_TX_DFLEXDPSP(FIA1)); | ||
| 630 | tc_cold_unblock(dig_port, wakeref); | ||
| 631 | |||
| 632 | drm_WARN_ON(&i915->drm, val == 0xffffffff); | ||
| 633 | |||
| 634 | return val & MODULAR_FIA_MASK; | ||
| 635 | } | ||
| 636 | |||
| 637 | static void | ||
| 638 | tc_port_load_fia_params(struct drm_i915_private *i915, struct intel_digital_port *dig_port) | ||
| 639 | { | ||
| 640 | enum port port = dig_port->base.port; | ||
| 641 | enum tc_port tc_port = intel_port_to_tc(i915, port); | ||
| 642 | |||
| 643 | /* | ||
| 644 | * Each Modular FIA instance houses 2 TC ports. In SOC that has more | ||
| 645 | * than two TC ports, there are multiple instances of Modular FIA. | ||
| 646 | */ | ||
| 647 | if (tc_has_modular_fia(i915, dig_port)) { | ||
| 648 | dig_port->tc_phy_fia = tc_port / 2; | ||
| 649 | dig_port->tc_phy_fia_idx = tc_port % 2; | ||
| 650 | } else { | ||
| 651 | dig_port->tc_phy_fia = FIA1; | ||
| 652 | dig_port->tc_phy_fia_idx = tc_port; | ||
| 653 | } | ||
| 654 | } | ||
| 655 | |||
| 649 | void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy) | 656 | void intel_tc_port_init(struct intel_digital_port *dig_port, bool is_legacy) |
| 650 | { | 657 | { |
| 651 | struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev); | 658 | struct drm_i915_private *i915 = to_i915(dig_port->base.base.dev); |
| @@ -812,10 +812,20 @@ static void intel_dsi_pre_enable(struct intel_atomic_state *state, · 811 unmodified lines | |||
| 812 | intel_dsi_prepare(encoder, pipe_config); | 812 | intel_dsi_prepare(encoder, pipe_config); |
| 813 | 813 | ||
| 814 | intel_dsi_vbt_exec_sequence(intel_dsi, MIPI_SEQ_POWER_ON); | 814 | intel_dsi_vbt_exec_sequence(intel_dsi, MIPI_SEQ_POWER_ON); |
| 815 | intel_dsi_msleep(intel_dsi, intel_dsi->panel_on_delay); | ||
| 816 | 815 | ||
| 817 | /* Deassert reset */ | 816 | /* |
| 818 | intel_dsi_vbt_exec_sequence(intel_dsi, MIPI_SEQ_DEASSERT_RESET); | 817 | * Give the panel time to power-on and then deassert its reset. |
| 818 | * Depending on the VBT MIPI sequences version the deassert-seq | ||
| 819 | * may contain the necessary delay, intel_dsi_msleep() will skip | ||
| 820 | * the delay in that case. If there is no deassert-seq, then an | ||
| 821 | * unconditional msleep is used to give the panel time to power-on. | ||
| 822 | */ | ||
| 823 | if (dev_priv->vbt.dsi.sequence[MIPI_SEQ_DEASSERT_RESET]) { | ||
| 824 | intel_dsi_msleep(intel_dsi, intel_dsi->panel_on_delay); | ||
| 825 | intel_dsi_vbt_exec_sequence(intel_dsi, MIPI_SEQ_DEASSERT_RESET); | ||
| 826 | } else { | ||
| 827 | msleep(intel_dsi->panel_on_delay); | ||
| 828 | } | ||
| 819 | 829 | ||
| 820 | if (IS_GEMINILAKE(dev_priv)) { | 830 | if (IS_GEMINILAKE(dev_priv)) { |
| 821 | glk_cold_boot = glk_dsi_enable_io(encoder); | 831 | glk_cold_boot = glk_dsi_enable_io(encoder); |
| @@ -387,48 +387,6 @@ err: · 386 unmodified lines | |||
| 387 | return vma; | 387 | return vma; |
| 388 | } | 388 | } |
| 389 | 389 | ||
| 390 | static void i915_gem_object_bump_inactive_ggtt(struct drm_i915_gem_object *obj) | ||
| 391 | { | ||
| 392 | struct drm_i915_private *i915 = to_i915(obj->base.dev); | ||
| 393 | struct i915_vma *vma; | ||
| 394 | |||
| 395 | if (list_empty(&obj->vma.list)) | ||
| 396 | return; | ||
| 397 | |||
| 398 | mutex_lock(&i915->ggtt.vm.mutex); | ||
| 399 | spin_lock(&obj->vma.lock); | ||
| 400 | for_each_ggtt_vma(vma, obj) { | ||
| 401 | if (!drm_mm_node_allocated(&vma->node)) | ||
| 402 | continue; | ||
| 403 | |||
| 404 | GEM_BUG_ON(vma->vm != &i915->ggtt.vm); | ||
| 405 | list_move_tail(&vma->vm_link, &vma->vm->bound_list); | ||
| 406 | } | ||
| 407 | spin_unlock(&obj->vma.lock); | ||
| 408 | mutex_unlock(&i915->ggtt.vm.mutex); | ||
| 409 | |||
| 410 | if (i915_gem_object_is_shrinkable(obj)) { | ||
| 411 | unsigned long flags; | ||
| 412 | |||
| 413 | spin_lock_irqsave(&i915->mm.obj_lock, flags); | ||
| 414 | |||
| 415 | if (obj->mm.madv == I915_MADV_WILLNEED && | ||
| 416 | !atomic_read(&obj->mm.shrink_pin)) | ||
| 417 | list_move_tail(&obj->mm.link, &i915->mm.shrink_list); | ||
| 418 | |||
| 419 | spin_unlock_irqrestore(&i915->mm.obj_lock, flags); | ||
| 420 | } | ||
| 421 | } | ||
| 422 | |||
| 423 | void | ||
| 424 | i915_gem_object_unpin_from_display_plane(struct i915_vma *vma) | ||
| 425 | { | ||
| 426 | /* Bump the LRU to try and avoid premature eviction whilst flipping */ | ||
| 427 | i915_gem_object_bump_inactive_ggtt(vma->obj); | ||
| 428 | |||
| 429 | i915_vma_unpin(vma); | ||
| 430 | } | ||
| 431 | |||
| 432 | /** | 390 | /** |
| 433 | * Moves a single object to the CPU read, and possibly write domain. | 391 | * Moves a single object to the CPU read, and possibly write domain. |
| 434 | * @obj: object to act on | 392 | * @obj: object to act on |
| @@ -569,9 +527,6 @@ i915_gem_set_domain_ioctl(struct drm_device *dev, void *data, · 134 unmodified lines | |||
| 569 | else | 527 | else |
| 570 | err = i915_gem_object_set_to_cpu_domain(obj, write_domain); | 528 | err = i915_gem_object_set_to_cpu_domain(obj, write_domain); |
| 571 | 529 | ||
| 572 | /* And bump the LRU for this access */ | ||
| 573 | i915_gem_object_bump_inactive_ggtt(obj); | ||
| 574 | |||
| 575 | i915_gem_object_unlock(obj); | 530 | i915_gem_object_unlock(obj); |
| 576 | 531 | ||
| 577 | if (write_domain) | 532 | if (write_domain) |
| @@ -1046,7 +1046,7 @@ static void reloc_gpu_flush(struct i915_execbuffer *eb, struct reloc_cache *cach · 1045 unmodified lines | |||
| 1046 | GEM_BUG_ON(cache->rq_size >= obj->base.size / sizeof(u32)); | 1046 | GEM_BUG_ON(cache->rq_size >= obj->base.size / sizeof(u32)); |
| 1047 | cache->rq_cmd[cache->rq_size] = MI_BATCH_BUFFER_END; | 1047 | cache->rq_cmd[cache->rq_size] = MI_BATCH_BUFFER_END; |
| 1048 | 1048 | ||
| 1049 | __i915_gem_object_flush_map(obj, 0, sizeof(u32) * (cache->rq_size + 1)); | 1049 | i915_gem_object_flush_map(obj); |
| 1050 | i915_gem_object_unpin_map(obj); | 1050 | i915_gem_object_unpin_map(obj); |
| 1051 | 1051 | ||
| 1052 | intel_gt_chipset_flush(cache->rq->engine->gt); | 1052 | intel_gt_chipset_flush(cache->rq->engine->gt); |
| @@ -1296,6 +1296,8 @@ static int __reloc_gpu_alloc(struct i915_execbuffer *eb, · 243 unmodified lines | |||
| 1296 | goto err_pool; | 1296 | goto err_pool; |
| 1297 | } | 1297 | } |
| 1298 | 1298 | ||
| 1299 | memset32(cmd, 0, pool->obj->base.size / sizeof(u32)); | ||
| 1300 | |||
| 1299 | batch = i915_vma_instance(pool->obj, vma->vm, NULL); | 1301 | batch = i915_vma_instance(pool->obj, vma->vm, NULL); |
| 1300 | if (IS_ERR(batch)) { | 1302 | if (IS_ERR(batch)) { |
| 1301 | err = PTR_ERR(batch); | 1303 | err = PTR_ERR(batch); |
| @@ -486,7 +486,6 @@ i915_gem_object_pin_to_display_plane(struct drm_i915_gem_object *obj, · 485 unmodified lines | |||
| 486 | u32 alignment, | 486 | u32 alignment, |
| 487 | const struct i915_ggtt_view *view, | 487 | const struct i915_ggtt_view *view, |
| 488 | unsigned int flags); | 488 | unsigned int flags); |
| 489 | void i915_gem_object_unpin_from_display_plane(struct i915_vma *vma); | ||
| 490 | 489 | ||
| 491 | void i915_gem_object_make_unshrinkable(struct drm_i915_gem_object *obj); | 490 | void i915_gem_object_make_unshrinkable(struct drm_i915_gem_object *obj); |
| 492 | void i915_gem_object_make_shrinkable(struct drm_i915_gem_object *obj); | 491 | void i915_gem_object_make_shrinkable(struct drm_i915_gem_object *obj); |
| @@ -7,8 +7,6 @@ · 6 unmodified lines | |||
| 7 | #include "i915_drv.h" | 7 | #include "i915_drv.h" |
| 8 | #include "intel_gpu_commands.h" | 8 | #include "intel_gpu_commands.h" |
| 9 | 9 | ||
| 10 | #define MAX_URB_ENTRIES 64 | ||
| 11 | #define STATE_SIZE (4 * 1024) | ||
| 12 | #define GT3_INLINE_DATA_DELAYS 0x1E00 | 10 | #define GT3_INLINE_DATA_DELAYS 0x1E00 |
| 13 | #define batch_advance(Y, CS) GEM_BUG_ON((Y)->end != (CS)) | 11 | #define batch_advance(Y, CS) GEM_BUG_ON((Y)->end != (CS)) |
| 14 | 12 | ||
| @@ -34,38 +32,59 @@ struct batch_chunk { · 19 unmodified lines | |||
| 34 | }; | 32 | }; |
| 35 | 33 | ||
| 36 | struct batch_vals { | 34 | struct batch_vals { |
| 37 | u32 max_primitives; | 35 | u32 max_threads; |
| 38 | u32 max_urb_entries; | ||
| 39 | u32 cmd_size; | ||
| 40 | u32 state_size; | ||
| 41 | u32 state_start; | 36 | u32 state_start; |
| 42 | u32 batch_size; | 37 | u32 surface_start; |
| 43 | u32 surface_height; | 38 | u32 surface_height; |
| 44 | u32 surface_width; | 39 | u32 surface_width; |
| 45 | u32 scratch_size; | 40 | u32 size; |
| 46 | u32 max_size; | ||
| 47 | }; | 41 | }; |
| 48 | 42 | ||
| 43 | static inline int num_primitives(const struct batch_vals *bv) | ||
| 44 | { | ||
| 45 | /* | ||
| 46 | * We need to saturate the GPU with work in order to dispatch | ||
| 47 | * a shader on every HW thread, and clear the thread-local registers. | ||
| 48 | * In short, we have to dispatch work faster than the shaders can | ||
| 49 | * run in order to fill the EU and occupy each HW thread. | ||
| 50 | */ | ||
| 51 | return bv->max_threads; | ||
| 52 | } | ||
| 53 | |||
| 49 | static void | 54 | static void |
| 50 | batch_get_defaults(struct drm_i915_private *i915, struct batch_vals *bv) | 55 | batch_get_defaults(struct drm_i915_private *i915, struct batch_vals *bv) |
| 51 | { | 56 | { |
| 52 | if (IS_HASWELL(i915)) { | 57 | if (IS_HASWELL(i915)) { |
| 53 | bv->max_primitives = 280; | 58 | switch (INTEL_INFO(i915)->gt) { |
| 54 | bv->max_urb_entries = MAX_URB_ENTRIES; | 59 | default: |
| 60 | case 1: | ||
| 61 | bv->max_threads = 70; | ||
| 62 | break; | ||
| 63 | case 2: | ||
| 64 | bv->max_threads = 140; | ||
| 65 | break; | ||
| 66 | case 3: | ||
| 67 | bv->max_threads = 280; | ||
| 68 | break; | ||
| 69 | } | ||
| 55 | bv->surface_height = 16 * 16; | 70 | bv->surface_height = 16 * 16; |
| 56 | bv->surface_width = 32 * 2 * 16; | 71 | bv->surface_width = 32 * 2 * 16; |
| 57 | } else { | 72 | } else { |
| 58 | bv->max_primitives = 128; | 73 | switch (INTEL_INFO(i915)->gt) { |
| 59 | bv->max_urb_entries = MAX_URB_ENTRIES / 2; | 74 | default: |
| 75 | case 1: /* including vlv */ | ||
| 76 | bv->max_threads = 36; | ||
| 77 | break; | ||
| 78 | case 2: | ||
| 79 | bv->max_threads = 128; | ||
| 80 | break; | ||
| 81 | } | ||
| 60 | bv->surface_height = 16 * 8; | 82 | bv->surface_height = 16 * 8; |
| 61 | bv->surface_width = 32 * 16; | 83 | bv->surface_width = 32 * 16; |
| 62 | } | 84 | } |
| 63 | bv->cmd_size = bv->max_primitives * 4096; | 85 | bv->state_start = round_up(SZ_1K + num_primitives(bv) * 64, SZ_4K); |
| 64 | bv->state_size = STATE_SIZE; | 86 | bv->surface_start = bv->state_start + SZ_4K; |
| 65 | bv->state_start = bv->cmd_size; | 87 | bv->size = bv->surface_start + bv->surface_height * bv->surface_width; |
| 66 | bv->batch_size = bv->cmd_size + bv->state_size; | ||
| 67 | bv->scratch_size = bv->surface_height * bv->surface_width; | ||
| 68 | bv->max_size = bv->batch_size + bv->scratch_size; | ||
| 69 | } | 88 | } |
| 70 | 89 | ||
| 71 | static void batch_init(struct batch_chunk *bc, | 90 | static void batch_init(struct batch_chunk *bc, |
| @@ -155,7 +174,8 @@ static u32 · 83 unmodified lines | |||
| 155 | gen7_fill_binding_table(struct batch_chunk *state, | 174 | gen7_fill_binding_table(struct batch_chunk *state, |
| 156 | const struct batch_vals *bv) | 175 | const struct batch_vals *bv) |
| 157 | { | 176 | { |
| 158 | u32 surface_start = gen7_fill_surface_state(state, bv->batch_size, bv); | 177 | u32 surface_start = |
| 178 | gen7_fill_surface_state(state, bv->surface_start, bv); | ||
| 159 | u32 *cs = batch_alloc_items(state, 32, 8); | 179 | u32 *cs = batch_alloc_items(state, 32, 8); |
| 160 | u32 offset = batch_offset(state, cs); | 180 | u32 offset = batch_offset(state, cs); |
| 161 | 181 | ||
| @@ -214,9 +234,9 @@ static void · 52 unmodified lines | |||
| 214 | gen7_emit_state_base_address(struct batch_chunk *batch, | 234 | gen7_emit_state_base_address(struct batch_chunk *batch, |
| 215 | u32 surface_state_base) | 235 | u32 surface_state_base) |
| 216 | { | 236 | { |
| 217 | u32 *cs = batch_alloc_items(batch, 0, 12); | 237 | u32 *cs = batch_alloc_items(batch, 0, 10); |
| 218 | 238 | ||
| 219 | *cs++ = STATE_BASE_ADDRESS | (12 - 2); | 239 | *cs++ = STATE_BASE_ADDRESS | (10 - 2); |
| 220 | /* general */ | 240 | /* general */ |
| 221 | *cs++ = batch_addr(batch) | BASE_ADDRESS_MODIFY; | 241 | *cs++ = batch_addr(batch) | BASE_ADDRESS_MODIFY; |
| 222 | /* surface */ | 242 | /* surface */ |
| @@ -233,8 +253,6 @@ gen7_emit_state_base_address(struct batch_chunk *batch, · 10 unmodified lines | |||
| 233 | *cs++ = BASE_ADDRESS_MODIFY; | 253 | *cs++ = BASE_ADDRESS_MODIFY; |
| 234 | *cs++ = 0; | 254 | *cs++ = 0; |
| 235 | *cs++ = BASE_ADDRESS_MODIFY; | 255 | *cs++ = BASE_ADDRESS_MODIFY; |
| 236 | *cs++ = 0; | ||
| 237 | *cs++ = 0; | ||
| 238 | batch_advance(batch, cs); | 256 | batch_advance(batch, cs); |
| 239 | } | 257 | } |
| 240 | 258 | ||
| @@ -244,8 +262,7 @@ gen7_emit_vfe_state(struct batch_chunk *batch, · 3 unmodified lines | |||
| 244 | u32 urb_size, u32 curbe_size, | 262 | u32 urb_size, u32 curbe_size, |
| 245 | u32 mode) | 263 | u32 mode) |
| 246 | { | 264 | { |
| 247 | u32 urb_entries = bv->max_urb_entries; | 265 | u32 threads = bv->max_threads - 1; |
| 248 | u32 threads = bv->max_primitives - 1; | ||
| 249 | u32 *cs = batch_alloc_items(batch, 32, 8); | 266 | u32 *cs = batch_alloc_items(batch, 32, 8); |
| 250 | 267 | ||
| 251 | *cs++ = MEDIA_VFE_STATE | (8 - 2); | 268 | *cs++ = MEDIA_VFE_STATE | (8 - 2); |
| @@ -254,7 +271,7 @@ gen7_emit_vfe_state(struct batch_chunk *batch, · 2 unmodified lines | |||
| 254 | *cs++ = 0; | 271 | *cs++ = 0; |
| 255 | 272 | ||
| 256 | /* number of threads & urb entries for GPGPU vs Media Mode */ | 273 | /* number of threads & urb entries for GPGPU vs Media Mode */ |
| 257 | *cs++ = threads << 16 | urb_entries << 8 | mode << 2; | 274 | *cs++ = threads << 16 | 1 << 8 | mode << 2; |
| 258 | 275 | ||
| 259 | *cs++ = 0; | 276 | *cs++ = 0; |
| 260 | 277 | ||
| @@ -293,17 +310,12 @@ gen7_emit_media_object(struct batch_chunk *batch, · 32 unmodified lines | |||
| 293 | { | 310 | { |
| 294 | unsigned int x_offset = (media_object_index % 16) * 64; | 311 | unsigned int x_offset = (media_object_index % 16) * 64; |
| 295 | unsigned int y_offset = (media_object_index / 16) * 16; | 312 | unsigned int y_offset = (media_object_index / 16) * 16; |
| 296 | unsigned int inline_data_size; | 313 | unsigned int pkt = 6 + 3; |
| 297 | unsigned int media_batch_size; | ||
| 298 | unsigned int i; | ||
| 299 | u32 *cs; | 314 | u32 *cs; |
| 300 | 315 | ||
| 301 | inline_data_size = 112 * 8; | 316 | cs = batch_alloc_items(batch, 8, pkt); |
| 302 | media_batch_size = inline_data_size + 6; | ||
| 303 | |||
| 304 | cs = batch_alloc_items(batch, 8, media_batch_size); | ||
| 305 | 317 | ||
| 306 | *cs++ = MEDIA_OBJECT | (media_batch_size - 2); | 318 | *cs++ = MEDIA_OBJECT | (pkt - 2); |
| 307 | 319 | ||
| 308 | /* interface descriptor offset */ | 320 | /* interface descriptor offset */ |
| 309 | *cs++ = 0; | 321 | *cs++ = 0; |
| @@ -317,25 +329,44 @@ gen7_emit_media_object(struct batch_chunk *batch, · 7 unmodified lines | |||
| 317 | *cs++ = 0; | 329 | *cs++ = 0; |
| 318 | 330 | ||
| 319 | /* inline */ | 331 | /* inline */ |
| 320 | *cs++ = (y_offset << 16) | (x_offset); | 332 | *cs++ = y_offset << 16 | x_offset; |
| 321 | *cs++ = 0; | 333 | *cs++ = 0; |
| 322 | *cs++ = GT3_INLINE_DATA_DELAYS; | 334 | *cs++ = GT3_INLINE_DATA_DELAYS; |
| 323 | for (i = 3; i < inline_data_size; i++) | ||
| 324 | *cs++ = 0; | ||
| 325 | 335 | ||
| 326 | batch_advance(batch, cs); | 336 | batch_advance(batch, cs); |
| 327 | } | 337 | } |
| 328 | 338 | ||
| 329 | static void gen7_emit_pipeline_flush(struct batch_chunk *batch) | 339 | static void gen7_emit_pipeline_flush(struct batch_chunk *batch) |
| 330 | { | 340 | { |
| 331 | u32 *cs = batch_alloc_items(batch, 0, 5); | 341 | u32 *cs = batch_alloc_items(batch, 0, 4); |
| 332 | 342 | ||
| 333 | *cs++ = GFX_OP_PIPE_CONTROL(5); | 343 | *cs++ = GFX_OP_PIPE_CONTROL(4); |
| 334 | *cs++ = PIPE_CONTROL_STATE_CACHE_INVALIDATE | | 344 | *cs++ = PIPE_CONTROL_RENDER_TARGET_CACHE_FLUSH | |
| 335 | PIPE_CONTROL_GLOBAL_GTT_IVB; | 345 | PIPE_CONTROL_DEPTH_CACHE_FLUSH | |
| 346 | PIPE_CONTROL_DC_FLUSH_ENABLE | | ||
| 347 | PIPE_CONTROL_CS_STALL; | ||
| 336 | *cs++ = 0; | 348 | *cs++ = 0; |
| 337 | *cs++ = 0; | 349 | *cs++ = 0; |
| 350 | |||
| 351 | batch_advance(batch, cs); | ||
| 352 | } | ||
| 353 | |||
| 354 | static void gen7_emit_pipeline_invalidate(struct batch_chunk *batch) | ||
| 355 | { | ||
| 356 | u32 *cs = batch_alloc_items(batch, 0, 8); | ||
| 357 | |||
| 358 | /* ivb: Stall before STATE_CACHE_INVALIDATE */ | ||
| 359 | *cs++ = GFX_OP_PIPE_CONTROL(4); | ||
| 360 | *cs++ = PIPE_CONTROL_STALL_AT_SCOREBOARD | | ||
| 361 | PIPE_CONTROL_CS_STALL; | ||
| 362 | *cs++ = 0; | ||
| 363 | *cs++ = 0; | ||
| 364 | |||
| 365 | *cs++ = GFX_OP_PIPE_CONTROL(4); | ||
| 366 | *cs++ = PIPE_CONTROL_STATE_CACHE_INVALIDATE; | ||
| 338 | *cs++ = 0; | 367 | *cs++ = 0; |
| 368 | *cs++ = 0; | ||
| 369 | |||
| 339 | batch_advance(batch, cs); | 370 | batch_advance(batch, cs); |
| 340 | } | 371 | } |
| 341 | 372 | ||
| @@ -344,34 +375,46 @@ static void emit_batch(struct i915_vma * const vma, · 2 unmodified lines | |||
| 344 | const struct batch_vals *bv) | 375 | const struct batch_vals *bv) |
| 345 | { | 376 | { |
| 346 | struct drm_i915_private *i915 = vma->vm->i915; | 377 | struct drm_i915_private *i915 = vma->vm->i915; |
| 347 | unsigned int desc_count = 64; | 378 | const unsigned int desc_count = 1; |
| 348 | const u32 urb_size = 112; | 379 | const unsigned int urb_size = 1; |
| 349 | struct batch_chunk cmds, state; | 380 | struct batch_chunk cmds, state; |
| 350 | u32 interface_descriptor; | 381 | u32 descriptors; |
| 351 | unsigned int i; | 382 | unsigned int i; |
| 352 | 383 | ||
| 353 | batch_init(&cmds, vma, start, 0, bv->cmd_size); | 384 | batch_init(&cmds, vma, start, 0, bv->state_start); |
| 354 | batch_init(&state, vma, start, bv->state_start, bv->state_size); | 385 | batch_init(&state, vma, start, bv->state_start, SZ_4K); |
| 355 | 386 | ||
| 356 | interface_descriptor = | 387 | descriptors = gen7_fill_interface_descriptor(&state, bv, |
| 357 | gen7_fill_interface_descriptor(&state, bv, | 388 | IS_HASWELL(i915) ? |
| 358 | IS_HASWELL(i915) ? | 389 | &cb_kernel_hsw : |
| 359 | &cb_kernel_hsw : | 390 | &cb_kernel_ivb, |
| 360 | &cb_kernel_ivb, | 391 | desc_count); |
| 361 | desc_count); | 392 | |
| 393 | /* Reset inherited context registers */ | ||
| 394 | gen7_emit_pipeline_invalidate(&cmds); | ||
| 395 | batch_add(&cmds, MI_LOAD_REGISTER_IMM(2)); | ||
| 396 | batch_add(&cmds, i915_mmio_reg_offset(CACHE_MODE_0_GEN7)); | ||
| 397 | batch_add(&cmds, 0xffff0000); | ||
| 398 | batch_add(&cmds, i915_mmio_reg_offset(CACHE_MODE_1)); | ||
| 399 | batch_add(&cmds, 0xffff0000 | PIXEL_SUBSPAN_COLLECT_OPT_DISABLE); | ||
| 362 | gen7_emit_pipeline_flush(&cmds); | 400 | gen7_emit_pipeline_flush(&cmds); |
| 401 | |||
| 402 | /* Switch to the media pipeline and our base address */ | ||
| 403 | gen7_emit_pipeline_invalidate(&cmds); | ||
| 363 | batch_add(&cmds, PIPELINE_SELECT | PIPELINE_SELECT_MEDIA); | 404 | batch_add(&cmds, PIPELINE_SELECT | PIPELINE_SELECT_MEDIA); |
| 364 | batch_add(&cmds, MI_NOOP); | 405 | batch_add(&cmds, MI_NOOP); |
| 365 | gen7_emit_state_base_address(&cmds, interface_descriptor); | 406 | gen7_emit_pipeline_invalidate(&cmds); |
| 407 | |||
| 366 | gen7_emit_pipeline_flush(&cmds); | 408 | gen7_emit_pipeline_flush(&cmds); |
| 409 | gen7_emit_state_base_address(&cmds, descriptors); | ||
| 410 | gen7_emit_pipeline_invalidate(&cmds); | ||
| 367 | 411 | ||
| 412 | /* Set the clear-residual kernel state */ | ||
| 368 | gen7_emit_vfe_state(&cmds, bv, urb_size - 1, 0, 0); | 413 | gen7_emit_vfe_state(&cmds, bv, urb_size - 1, 0, 0); |
| 414 | gen7_emit_interface_descriptor_load(&cmds, descriptors, desc_count); | ||
| 369 | 415 | ||
| 370 | gen7_emit_interface_descriptor_load(&cmds, | 416 | /* Execute the kernel on all HW threads */ |
| 371 | interface_descriptor, | 417 | for (i = 0; i < num_primitives(bv); i++) |
| 372 | desc_count); | ||
| 373 | |||
| 374 | for (i = 0; i < bv->max_primitives; i++) | ||
| 375 | gen7_emit_media_object(&cmds, i); | 418 | gen7_emit_media_object(&cmds, i); |
| 376 | 419 | ||
| 377 | batch_add(&cmds, MI_BATCH_BUFFER_END); | 420 | batch_add(&cmds, MI_BATCH_BUFFER_END); |
| @@ -385,15 +428,15 @@ int gen7_setup_clear_gpr_bb(struct intel_engine_cs * const engine, · 7 unmodified lines | |||
| 385 | 428 | ||
| 386 | batch_get_defaults(engine->i915, &bv); | 429 | batch_get_defaults(engine->i915, &bv); |
| 387 | if (!vma) | 430 | if (!vma) |
| 388 | return bv.max_size; | 431 | return bv.size; |
| 389 | 432 | ||
| 390 | GEM_BUG_ON(vma->obj->base.size < bv.max_size); | 433 | GEM_BUG_ON(vma->obj->base.size < bv.size); |
| 391 | 434 | ||
| 392 | batch = i915_gem_object_pin_map(vma->obj, I915_MAP_WC); | 435 | batch = i915_gem_object_pin_map(vma->obj, I915_MAP_WC); |
| 393 | if (IS_ERR(batch)) | 436 | if (IS_ERR(batch)) |
| 394 | return PTR_ERR(batch); | 437 | return PTR_ERR(batch); |
| 395 | 438 | ||
| 396 | emit_batch(vma, memset(batch, 0, bv.max_size), &bv); | 439 | emit_batch(vma, memset(batch, 0, bv.size), &bv); |
| 397 | 440 | ||
| 398 | i915_gem_object_flush_map(vma->obj); | 441 | i915_gem_object_flush_map(vma->obj); |
| 399 | __i915_gem_object_release_map(vma->obj); | 442 | __i915_gem_object_release_map(vma->obj); |
| @@ -134,11 +134,6 @@ static bool remove_signaling_context(struct intel_breadcrumbs *b, · 133 unmodified lines | |||
| 134 | return true; | 134 | return true; |
| 135 | } | 135 | } |
| 136 | 136 | ||
| 137 | static inline bool __request_completed(const struct i915_request *rq) | ||
| 138 | { | ||
| 139 | return i915_seqno_passed(__hwsp_seqno(rq), rq->fence.seqno); | ||
| 140 | } | ||
| 141 | |||
| 142 | __maybe_unused static bool | 137 | __maybe_unused static bool |
| 143 | check_signal_order(struct intel_context *ce, struct i915_request *rq) | 138 | check_signal_order(struct intel_context *ce, struct i915_request *rq) |
| 144 | { | 139 | { |
| @@ -192,18 +187,6 @@ static void add_retire(struct intel_breadcrumbs *b, struct intel_timeline *tl) · 47 unmodified lines | |||
| 192 | intel_engine_add_retire(b->irq_engine, tl); | 187 | intel_engine_add_retire(b->irq_engine, tl); |
| 193 | } | 188 | } |
| 194 | 189 | ||
| 195 | static bool __signal_request(struct i915_request *rq) | ||
| 196 | { | ||
| 197 | GEM_BUG_ON(test_bit(I915_FENCE_FLAG_SIGNAL, &rq->fence.flags)); | ||
| 198 | |||
| 199 | if (!__dma_fence_signal(&rq->fence)) { | ||
| 200 | i915_request_put(rq); | ||
| 201 | return false; | ||
| 202 | } | ||
| 203 | |||
| 204 | return true; | ||
| 205 | } | ||
| 206 | |||
| 207 | static struct llist_node * | 190 | static struct llist_node * |
| 208 | slist_add(struct llist_node *node, struct llist_node *head) | 191 | slist_add(struct llist_node *node, struct llist_node *head) |
| 209 | { | 192 | { |
| @@ -257,7 +240,7 @@ static void signal_irq_work(struct irq_work *work) · 47 unmodified lines | |||
| 257 | list_for_each_entry_rcu(rq, &ce->signals, signal_link) { | 240 | list_for_each_entry_rcu(rq, &ce->signals, signal_link) { |
| 258 | bool release; | 241 | bool release; |
| 259 | 242 | ||
| 260 | if (!__request_completed(rq)) | 243 | if (!__i915_request_is_complete(rq)) |
| 261 | break; | 244 | break; |
| 262 | 245 | ||
| 263 | if (!test_and_clear_bit(I915_FENCE_FLAG_SIGNAL, | 246 | if (!test_and_clear_bit(I915_FENCE_FLAG_SIGNAL, |
| @@ -274,9 +257,11 @@ static void signal_irq_work(struct irq_work *work) · 10 unmodified lines | |||
| 274 | release = remove_signaling_context(b, ce); | 257 | release = remove_signaling_context(b, ce); |
| 275 | spin_unlock(&ce->signal_lock); | 258 | spin_unlock(&ce->signal_lock); |
| 276 | 259 | ||
| 277 | if (__signal_request(rq)) | 260 | if (__dma_fence_signal(&rq->fence)) |
| 278 | /* We own signal_node now, xfer to local list */ | 261 | /* We own signal_node now, xfer to local list */ |
| 279 | signal = slist_add(&rq->signal_node, signal); | 262 | signal = slist_add(&rq->signal_node, signal); |
| 263 | else | ||
| 264 | i915_request_put(rq); | ||
| 280 | 265 | ||
| 281 | if (release) { | 266 | if (release) { |
| 282 | add_retire(b, ce->timeline); | 267 | add_retire(b, ce->timeline); |
| @@ -363,6 +348,17 @@ void intel_breadcrumbs_free(struct intel_breadcrumbs *b) · 80 unmodified lines | |||
| 363 | kfree(b); | 348 | kfree(b); |
| 364 | } | 349 | } |
| 365 | 350 | ||
| 351 | static void irq_signal_request(struct i915_request *rq, | ||
| 352 | struct intel_breadcrumbs *b) | ||
| 353 | { | ||
| 354 | if (!__dma_fence_signal(&rq->fence)) | ||
| 355 | return; | ||
| 356 | |||
| 357 | i915_request_get(rq); | ||
| 358 | if (llist_add(&rq->signal_node, &b->signaled_requests)) | ||
| 359 | irq_work_queue(&b->irq_work); | ||
| 360 | } | ||
| 361 | |||
| 366 | static void insert_breadcrumb(struct i915_request *rq) | 362 | static void insert_breadcrumb(struct i915_request *rq) |
| 367 | { | 363 | { |
| 368 | struct intel_breadcrumbs *b = READ_ONCE(rq->engine)->breadcrumbs; | 364 | struct intel_breadcrumbs *b = READ_ONCE(rq->engine)->breadcrumbs; |
| @@ -372,17 +368,13 @@ static void insert_breadcrumb(struct i915_request *rq) · 3 unmodified lines | |||
| 372 | if (test_bit(I915_FENCE_FLAG_SIGNAL, &rq->fence.flags)) | 368 | if (test_bit(I915_FENCE_FLAG_SIGNAL, &rq->fence.flags)) |
| 373 | return; | 369 | return; |
| 374 | 370 | ||
| 375 | i915_request_get(rq); | ||
| 376 | |||
| 377 | /* | 371 | /* |
| 378 | * If the request is already completed, we can transfer it | 372 | * If the request is already completed, we can transfer it |
| 379 | * straight onto a signaled list, and queue the irq worker for | 373 | * straight onto a signaled list, and queue the irq worker for |
| 380 | * its signal completion. | 374 | * its signal completion. |
| 381 | */ | 375 | */ |
| 382 | if (__request_completed(rq)) { | 376 | if (__i915_request_is_complete(rq)) { |
| 383 | if (__signal_request(rq) && | 377 | irq_signal_request(rq, b); |
| 384 | llist_add(&rq->signal_node, &b->signaled_requests)) | ||
| 385 | irq_work_queue(&b->irq_work); | ||
| 386 | return; | 378 | return; |
| 387 | } | 379 | } |
| 388 | 380 | ||
| @@ -413,6 +405,8 @@ static void insert_breadcrumb(struct i915_request *rq) · 24 unmodified lines | |||
| 413 | break; | 405 | break; |
| 414 | } | 406 | } |
| 415 | } | 407 | } |
| 408 | |||
| 409 | i915_request_get(rq); | ||
| 416 | list_add_rcu(&rq->signal_link, pos); | 410 | list_add_rcu(&rq->signal_link, pos); |
| 417 | GEM_BUG_ON(!check_signal_order(ce, rq)); | 411 | GEM_BUG_ON(!check_signal_order(ce, rq)); |
| 418 | GEM_BUG_ON(test_bit(DMA_FENCE_FLAG_SIGNALED_BIT, &rq->fence.flags)); | 412 | GEM_BUG_ON(test_bit(DMA_FENCE_FLAG_SIGNALED_BIT, &rq->fence.flags)); |
| @@ -453,19 +447,25 @@ bool i915_request_enable_breadcrumb(struct i915_request *rq) · 34 unmodified lines | |||
| 453 | 447 | ||
| 454 | void i915_request_cancel_breadcrumb(struct i915_request *rq) | 448 | void i915_request_cancel_breadcrumb(struct i915_request *rq) |
| 455 | { | 449 | { |
| 450 | struct intel_breadcrumbs *b = READ_ONCE(rq->engine)->breadcrumbs; | ||
| 456 | struct intel_context *ce = rq->context; | 451 | struct intel_context *ce = rq->context; |
| 457 | bool release; | 452 | bool release; |
| 458 | 453 | ||
| 459 | if (!test_and_clear_bit(I915_FENCE_FLAG_SIGNAL, &rq->fence.flags)) | 454 | spin_lock(&ce->signal_lock); |
| 455 | if (!test_and_clear_bit(I915_FENCE_FLAG_SIGNAL, &rq->fence.flags)) { | ||
| 456 | spin_unlock(&ce->signal_lock); | ||
| 460 | return; | 457 | return; |
| 458 | } | ||
| 461 | 459 | ||
| 462 | spin_lock(&ce->signal_lock); | ||
| 463 | list_del_rcu(&rq->signal_link); | 460 | list_del_rcu(&rq->signal_link); |
| 464 | release = remove_signaling_context(rq->engine->breadcrumbs, ce); | 461 | release = remove_signaling_context(b, ce); |
| 465 | spin_unlock(&ce->signal_lock); | 462 | spin_unlock(&ce->signal_lock); |
| 466 | if (release) | 463 | if (release) |
| 467 | intel_context_put(ce); | 464 | intel_context_put(ce); |
| 468 | 465 | ||
| 466 | if (__i915_request_is_complete(rq)) | ||
| 467 | irq_signal_request(rq, b); | ||
| 468 | |||
| 469 | i915_request_put(rq); | 469 | i915_request_put(rq); |
| 470 | } | 470 | } |
| 471 | 471 | ||
| @@ -526,16 +526,39 @@ static int init_ggtt(struct i915_ggtt *ggtt) · 525 unmodified lines | |||
| 526 | 526 | ||
| 527 | mutex_init(&ggtt->error_mutex); | 527 | mutex_init(&ggtt->error_mutex); |
| 528 | if (ggtt->mappable_end) { | 528 | if (ggtt->mappable_end) { |
| 529 | /* Reserve a mappable slot for our lockless error capture */ | 529 | /* |
| 530 | ret = drm_mm_insert_node_in_range(&ggtt->vm.mm, | 530 | * Reserve a mappable slot for our lockless error capture. |
| 531 | &ggtt->error_capture, | 531 | * |
| 532 | PAGE_SIZE, 0, | 532 | * We strongly prefer taking address 0x0 in order to protect |
| 533 | I915_COLOR_UNEVICTABLE, | 533 | * other critical buffers against accidental overwrites, |
| 534 | 0, ggtt->mappable_end, | 534 | * as writing to address 0 is a very common mistake. |
| 535 | DRM_MM_INSERT_LOW); | 535 | * |
| 536 | if (ret) | 536 | * Since 0 may already be in use by the system (e.g. the BIOS |
| 537 | return ret; | 537 | * framebuffer), we let the reservation fail quietly and hope |
| 538 | * 0 remains reserved always. | ||
| 539 | * | ||
| 540 | * If we fail to reserve 0, and then fail to find any space | ||
| 541 | * for an error-capture, remain silent. We can afford not | ||
| 542 | * to reserve an error_capture node as we have fallback | ||
| 543 | * paths, and we trust that 0 will remain reserved. However, | ||
| 544 | * the only likely reason for failure to insert is a driver | ||
| 545 | * bug, which we expect to cause other failures... | ||
| 546 | */ | ||
| 547 | ggtt->error_capture.size = I915_GTT_PAGE_SIZE; | ||
| 548 | ggtt->error_capture.color = I915_COLOR_UNEVICTABLE; | ||
| 549 | if (drm_mm_reserve_node(&ggtt->vm.mm, &ggtt->error_capture)) | ||
| 550 | drm_mm_insert_node_in_range(&ggtt->vm.mm, | ||
| 551 | &ggtt->error_capture, | ||
| 552 | ggtt->error_capture.size, 0, | ||
| 553 | ggtt->error_capture.color, | ||
| 554 | 0, ggtt->mappable_end, | ||
| 555 | DRM_MM_INSERT_LOW); | ||
| 538 | } | 556 | } |
| 557 | if (drm_mm_node_allocated(&ggtt->error_capture)) | ||
| 558 | drm_dbg(&ggtt->vm.i915->drm, | ||
| 559 | "Reserved GGTT:[%llx, %llx] for use by error capture\n", | ||
| 560 | ggtt->error_capture.start, | ||
| 561 | ggtt->error_capture.start + ggtt->error_capture.size); | ||
| 539 | 562 | ||
| 540 | /* | 563 | /* |
| 541 | * The upper portion of the GuC address space has a sizeable hole | 564 | * The upper portion of the GuC address space has a sizeable hole |
| @@ -548,9 +571,9 @@ static int init_ggtt(struct i915_ggtt *ggtt) · 6 unmodified lines | |||
| 548 | 571 | ||
| 549 | /* Clear any non-preallocated blocks */ | 572 | /* Clear any non-preallocated blocks */ |
| 550 | drm_mm_for_each_hole(entry, &ggtt->vm.mm, hole_start, hole_end) { | 573 | drm_mm_for_each_hole(entry, &ggtt->vm.mm, hole_start, hole_end) { |
| 551 | drm_dbg_kms(&ggtt->vm.i915->drm, | 574 | drm_dbg(&ggtt->vm.i915->drm, |
| 552 | "clearing unused GTT space: [%lx, %lx]\n", | 575 | "clearing unused GTT space: [%lx, %lx]\n", |
| 553 | hole_start, hole_end); | 576 | hole_start, hole_end); |
| 554 | ggtt->vm.clear_range(&ggtt->vm, hole_start, | 577 | ggtt->vm.clear_range(&ggtt->vm, hole_start, |
| 555 | hole_end - hole_start); | 578 | hole_end - hole_start); |
| 556 | } | 579 | } |
| @@ -3988,6 +3988,9 @@ err: · 3987 unmodified lines | |||
| 3988 | static void lrc_destroy_wa_ctx(struct intel_engine_cs *engine) | 3988 | static void lrc_destroy_wa_ctx(struct intel_engine_cs *engine) |
| 3989 | { | 3989 | { |
| 3990 | i915_vma_unpin_and_release(&engine->wa_ctx.vma, 0); | 3990 | i915_vma_unpin_and_release(&engine->wa_ctx.vma, 0); |
| 3991 | |||
| 3992 | /* Called on error unwind, clear all flags to prevent further use */ | ||
| 3993 | memset(&engine->wa_ctx, 0, sizeof(engine->wa_ctx)); | ||
| 3991 | } | 3994 | } |
| 3992 | 3995 | ||
| 3993 | typedef u32 *(*wa_bb_func_t)(struct intel_engine_cs *engine, u32 *batch); | 3996 | typedef u32 *(*wa_bb_func_t)(struct intel_engine_cs *engine, u32 *batch); |
| @@ -32,6 +32,7 @@ · 31 unmodified lines | |||
| 32 | #include "gen6_ppgtt.h" | 32 | #include "gen6_ppgtt.h" |
| 33 | #include "gen7_renderclear.h" | 33 | #include "gen7_renderclear.h" |
| 34 | #include "i915_drv.h" | 34 | #include "i915_drv.h" |
| 35 | #include "i915_mitigations.h" | ||
| 35 | #include "intel_breadcrumbs.h" | 36 | #include "intel_breadcrumbs.h" |
| 36 | #include "intel_context.h" | 37 | #include "intel_context.h" |
| 37 | #include "intel_gt.h" | 38 | #include "intel_gt.h" |
| @@ -886,7 +887,8 @@ static int switch_context(struct i915_request *rq) · 848 unmodified lines | |||
| 886 | GEM_BUG_ON(HAS_EXECLISTS(engine->i915)); | 887 | GEM_BUG_ON(HAS_EXECLISTS(engine->i915)); |
| 887 | 888 | ||
| 888 | if (engine->wa_ctx.vma && ce != engine->kernel_context) { | 889 | if (engine->wa_ctx.vma && ce != engine->kernel_context) { |
| 889 | if (engine->wa_ctx.vma->private != ce) { | 890 | if (engine->wa_ctx.vma->private != ce && |
| 891 | i915_mitigate_clear_residuals()) { | ||
| 890 | ret = clear_residuals(rq); | 892 | ret = clear_residuals(rq); |
| 891 | if (ret) | 893 | if (ret) |
| 892 | return ret; | 894 | return ret; |
| @@ -1290,7 +1292,7 @@ int intel_ring_submission_setup(struct intel_engine_cs *engine) · 397 unmodified lines | |||
| 1290 | 1292 | ||
| 1291 | GEM_BUG_ON(timeline->hwsp_ggtt != engine->status_page.vma); | 1293 | GEM_BUG_ON(timeline->hwsp_ggtt != engine->status_page.vma); |
| 1292 | 1294 | ||
| 1293 | if (IS_HASWELL(engine->i915) && engine->class == RENDER_CLASS) { | 1295 | if (IS_GEN(engine->i915, 7) && engine->class == RENDER_CLASS) { |
| 1294 | err = gen7_ctx_switch_bb_init(engine); | 1296 | err = gen7_ctx_switch_bb_init(engine); |
| 1295 | if (err) | 1297 | if (err) |
| 1296 | goto err_ring_unpin; | 1298 | goto err_ring_unpin; |
| @@ -126,6 +126,10 @@ static void __rcu_cacheline_free(struct rcu_head *rcu) · 125 unmodified lines | |||
| 126 | struct intel_timeline_cacheline *cl = | 126 | struct intel_timeline_cacheline *cl = |
| 127 | container_of(rcu, typeof(*cl), rcu); | 127 | container_of(rcu, typeof(*cl), rcu); |
| 128 | 128 | ||
| 129 | /* Must wait until after all *rq->hwsp are complete before removing */ | ||
| 130 | i915_gem_object_unpin_map(cl->hwsp->vma->obj); | ||
| 131 | __idle_hwsp_free(cl->hwsp, ptr_unmask_bits(cl->vaddr, CACHELINE_BITS)); | ||
| 132 | |||
| 129 | i915_active_fini(&cl->active); | 133 | i915_active_fini(&cl->active); |
| 130 | kfree(cl); | 134 | kfree(cl); |
| 131 | } | 135 | } |
| @@ -133,11 +137,6 @@ static void __rcu_cacheline_free(struct rcu_head *rcu) · 1 unmodified line | |||
| 133 | static void __idle_cacheline_free(struct intel_timeline_cacheline *cl) | 137 | static void __idle_cacheline_free(struct intel_timeline_cacheline *cl) |
| 134 | { | 138 | { |
| 135 | GEM_BUG_ON(!i915_active_is_idle(&cl->active)); | 139 | GEM_BUG_ON(!i915_active_is_idle(&cl->active)); |
| 136 | |||
| 137 | i915_gem_object_unpin_map(cl->hwsp->vma->obj); | ||
| 138 | i915_vma_put(cl->hwsp->vma); | ||
| 139 | __idle_hwsp_free(cl->hwsp, ptr_unmask_bits(cl->vaddr, CACHELINE_BITS)); | ||
| 140 | |||
| 141 | call_rcu(&cl->rcu, __rcu_cacheline_free); | 140 | call_rcu(&cl->rcu, __rcu_cacheline_free); |
| 142 | } | 141 | } |
| 143 | 142 | ||
| @@ -179,7 +178,6 @@ cacheline_alloc(struct intel_timeline_hwsp *hwsp, unsigned int cacheline) · 35 unmodified lines | |||
| 179 | return ERR_CAST(vaddr); | 178 | return ERR_CAST(vaddr); |
| 180 | } | 179 | } |
| 181 | 180 | ||
| 182 | i915_vma_get(hwsp->vma); | ||
| 183 | cl->hwsp = hwsp; | 181 | cl->hwsp = hwsp; |
| 184 | cl->vaddr = page_pack_bits(vaddr, cacheline); | 182 | cl->vaddr = page_pack_bits(vaddr, cacheline); |
| 185 | 183 | ||
| @@ -53,6 +53,7 @@ void intel_uc_fw_change_status(struct intel_uc_fw *uc_fw, · 52 unmodified lines | |||
| 53 | fw_def(ELKHARTLAKE, 0, guc_def(ehl, 49, 0, 1), huc_def(ehl, 9, 0, 0)) \ | 53 | fw_def(ELKHARTLAKE, 0, guc_def(ehl, 49, 0, 1), huc_def(ehl, 9, 0, 0)) \ |
| 54 | fw_def(ICELAKE, 0, guc_def(icl, 49, 0, 1), huc_def(icl, 9, 0, 0)) \ | 54 | fw_def(ICELAKE, 0, guc_def(icl, 49, 0, 1), huc_def(icl, 9, 0, 0)) \ |
| 55 | fw_def(COMETLAKE, 5, guc_def(cml, 49, 0, 1), huc_def(cml, 4, 0, 0)) \ | 55 | fw_def(COMETLAKE, 5, guc_def(cml, 49, 0, 1), huc_def(cml, 4, 0, 0)) \ |
| 56 | fw_def(COMETLAKE, 0, guc_def(kbl, 49, 0, 1), huc_def(kbl, 4, 0, 0)) \ | ||
| 56 | fw_def(COFFEELAKE, 0, guc_def(kbl, 49, 0, 1), huc_def(kbl, 4, 0, 0)) \ | 57 | fw_def(COFFEELAKE, 0, guc_def(kbl, 49, 0, 1), huc_def(kbl, 4, 0, 0)) \ |
| 57 | fw_def(GEMINILAKE, 0, guc_def(glk, 49, 0, 1), huc_def(glk, 4, 0, 0)) \ | 58 | fw_def(GEMINILAKE, 0, guc_def(glk, 49, 0, 1), huc_def(glk, 4, 0, 0)) \ |
| 58 | fw_def(KABYLAKE, 0, guc_def(kbl, 49, 0, 1), huc_def(kbl, 4, 0, 0)) \ | 59 | fw_def(KABYLAKE, 0, guc_def(kbl, 49, 0, 1), huc_def(kbl, 4, 0, 0)) \ |
| @@ -217,6 +217,15 @@ static void emulate_monitor_status_change(struct intel_vgpu *vgpu) · 216 unmodified lines | |||
| 217 | DDI_BUF_CTL_ENABLE); | 217 | DDI_BUF_CTL_ENABLE); |
| 218 | vgpu_vreg_t(vgpu, DDI_BUF_CTL(port)) |= DDI_BUF_IS_IDLE; | 218 | vgpu_vreg_t(vgpu, DDI_BUF_CTL(port)) |= DDI_BUF_IS_IDLE; |
| 219 | } | 219 | } |
| 220 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) &= | ||
| 221 | ~(PORTA_HOTPLUG_ENABLE | PORTA_HOTPLUG_STATUS_MASK); | ||
| 222 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) &= | ||
| 223 | ~(PORTB_HOTPLUG_ENABLE | PORTB_HOTPLUG_STATUS_MASK); | ||
| 224 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) &= | ||
| 225 | ~(PORTC_HOTPLUG_ENABLE | PORTC_HOTPLUG_STATUS_MASK); | ||
| 226 | /* No hpd_invert set in vgpu vbt, need to clear invert mask */ | ||
| 227 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) &= ~BXT_DDI_HPD_INVERT_MASK; | ||
| 228 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) &= ~BXT_DE_PORT_HOTPLUG_MASK; | ||
| 220 | 229 | ||
| 221 | vgpu_vreg_t(vgpu, BXT_P_CR_GT_DISP_PWRON) &= ~(BIT(0) | BIT(1)); | 230 | vgpu_vreg_t(vgpu, BXT_P_CR_GT_DISP_PWRON) &= ~(BIT(0) | BIT(1)); |
| 222 | vgpu_vreg_t(vgpu, BXT_PORT_CL1CM_DW0(DPIO_PHY0)) &= | 231 | vgpu_vreg_t(vgpu, BXT_PORT_CL1CM_DW0(DPIO_PHY0)) &= |
| @@ -273,6 +282,8 @@ static void emulate_monitor_status_change(struct intel_vgpu *vgpu) · 50 unmodified lines | |||
| 273 | vgpu_vreg_t(vgpu, TRANS_DDI_FUNC_CTL(TRANSCODER_EDP)) |= | 282 | vgpu_vreg_t(vgpu, TRANS_DDI_FUNC_CTL(TRANSCODER_EDP)) |= |
| 274 | (TRANS_DDI_BPC_8 | TRANS_DDI_MODE_SELECT_DP_SST | | 283 | (TRANS_DDI_BPC_8 | TRANS_DDI_MODE_SELECT_DP_SST | |
| 275 | TRANS_DDI_FUNC_ENABLE); | 284 | TRANS_DDI_FUNC_ENABLE); |
| 285 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) |= | ||
| 286 | PORTA_HOTPLUG_ENABLE; | ||
| 276 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= | 287 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= |
| 277 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_A); | 288 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_A); |
| 278 | } | 289 | } |
| @@ -301,6 +312,8 @@ static void emulate_monitor_status_change(struct intel_vgpu *vgpu) · 22 unmodified lines | |||
| 301 | (TRANS_DDI_BPC_8 | TRANS_DDI_MODE_SELECT_DP_SST | | 312 | (TRANS_DDI_BPC_8 | TRANS_DDI_MODE_SELECT_DP_SST | |
| 302 | (PORT_B << TRANS_DDI_PORT_SHIFT) | | 313 | (PORT_B << TRANS_DDI_PORT_SHIFT) | |
| 303 | TRANS_DDI_FUNC_ENABLE); | 314 | TRANS_DDI_FUNC_ENABLE); |
| 315 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) |= | ||
| 316 | PORTB_HOTPLUG_ENABLE; | ||
| 304 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= | 317 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= |
| 305 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_B); | 318 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_B); |
| 306 | } | 319 | } |
| @@ -329,6 +342,8 @@ static void emulate_monitor_status_change(struct intel_vgpu *vgpu) · 22 unmodified lines | |||
| 329 | (TRANS_DDI_BPC_8 | TRANS_DDI_MODE_SELECT_DP_SST | | 342 | (TRANS_DDI_BPC_8 | TRANS_DDI_MODE_SELECT_DP_SST | |
| 330 | (PORT_B << TRANS_DDI_PORT_SHIFT) | | 343 | (PORT_B << TRANS_DDI_PORT_SHIFT) | |
| 331 | TRANS_DDI_FUNC_ENABLE); | 344 | TRANS_DDI_FUNC_ENABLE); |
| 345 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) |= | ||
| 346 | PORTC_HOTPLUG_ENABLE; | ||
| 332 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= | 347 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= |
| 333 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_C); | 348 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_C); |
| 334 | } | 349 | } |
| @@ -661,44 +676,62 @@ void intel_vgpu_emulate_hotplug(struct intel_vgpu *vgpu, bool connected) · 326 unmodified lines | |||
| 661 | PORTD_HOTPLUG_STATUS_MASK; | 676 | PORTD_HOTPLUG_STATUS_MASK; |
| 662 | intel_vgpu_trigger_virtual_event(vgpu, DP_D_HOTPLUG); | 677 | intel_vgpu_trigger_virtual_event(vgpu, DP_D_HOTPLUG); |
| 663 | } else if (IS_BROXTON(i915)) { | 678 | } else if (IS_BROXTON(i915)) { |
| 664 | if (connected) { | 679 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_A)) { |
| 665 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_A)) { | 680 | if (connected) { |
| 666 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= | 681 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= |
| 667 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_A); | 682 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_A); |
| 683 | } else { | ||
| 684 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) &= | ||
| 685 | ~GEN8_DE_PORT_HOTPLUG(HPD_PORT_A); | ||
| 668 | } | 686 | } |
| 669 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_B)) { | 687 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_IIR) |= |
| 670 | vgpu_vreg_t(vgpu, SFUSE_STRAP) |= | 688 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_A); |
| 671 | SFUSE_STRAP_DDIB_DETECTED; | 689 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) &= |
| 690 | ~PORTA_HOTPLUG_STATUS_MASK; | ||
| 691 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) |= | ||
| 692 | PORTA_HOTPLUG_LONG_DETECT; | ||
| 693 | intel_vgpu_trigger_virtual_event(vgpu, DP_A_HOTPLUG); | ||
| 694 | } | ||
| 695 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_B)) { | ||
| 696 | if (connected) { | ||
| 672 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= | 697 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= |
| 673 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_B); | 698 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_B); |
| 674 | } | ||
| 675 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_C)) { | ||
| 676 | vgpu_vreg_t(vgpu, SFUSE_STRAP) |= | 699 | vgpu_vreg_t(vgpu, SFUSE_STRAP) |= |
| 677 | SFUSE_STRAP_DDIC_DETECTED; | 700 | SFUSE_STRAP_DDIB_DETECTED; |
| 678 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= | 701 | } else { |
| 679 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_C); | ||
| 680 | } | ||
| 681 | } else { | ||
| 682 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_A)) { | ||
| 683 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) &= | 702 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) &= |
| 684 | ~GEN8_DE_PORT_HOTPLUG(HPD_PORT_A); | 703 | ~GEN8_DE_PORT_HOTPLUG(HPD_PORT_B); |
| 685 | } | ||
| 686 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_B)) { | ||
| 687 | vgpu_vreg_t(vgpu, SFUSE_STRAP) &= | 704 | vgpu_vreg_t(vgpu, SFUSE_STRAP) &= |
| 688 | ~SFUSE_STRAP_DDIB_DETECTED; | 705 | ~SFUSE_STRAP_DDIB_DETECTED; |
| 689 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) &= | ||
| 690 | ~GEN8_DE_PORT_HOTPLUG(HPD_PORT_B); | ||
| 691 | } | 706 | } |
| 692 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_C)) { | 707 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_IIR) |= |
| 693 | vgpu_vreg_t(vgpu, SFUSE_STRAP) &= | 708 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_B); |
| 694 | ~SFUSE_STRAP_DDIC_DETECTED; | 709 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) &= |
| 710 | ~PORTB_HOTPLUG_STATUS_MASK; | ||
| 711 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) |= | ||
| 712 | PORTB_HOTPLUG_LONG_DETECT; | ||
| 713 | intel_vgpu_trigger_virtual_event(vgpu, DP_B_HOTPLUG); | ||
| 714 | } | ||
| 715 | if (intel_vgpu_has_monitor_on_port(vgpu, PORT_C)) { | ||
| 716 | if (connected) { | ||
| 717 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) |= | ||
| 718 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_C); | ||
| 719 | vgpu_vreg_t(vgpu, SFUSE_STRAP) |= | ||
| 720 | SFUSE_STRAP_DDIC_DETECTED; | ||
| 721 | } else { | ||
| 695 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) &= | 722 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_ISR) &= |
| 696 | ~GEN8_DE_PORT_HOTPLUG(HPD_PORT_C); | 723 | ~GEN8_DE_PORT_HOTPLUG(HPD_PORT_C); |
| 724 | vgpu_vreg_t(vgpu, SFUSE_STRAP) &= | ||
| 725 | ~SFUSE_STRAP_DDIC_DETECTED; | ||
| 697 | } | 726 | } |
| 727 | vgpu_vreg_t(vgpu, GEN8_DE_PORT_IIR) |= | ||
| 728 | GEN8_DE_PORT_HOTPLUG(HPD_PORT_C); | ||
| 729 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) &= | ||
| 730 | ~PORTC_HOTPLUG_STATUS_MASK; | ||
| 731 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) |= | ||
| 732 | PORTC_HOTPLUG_LONG_DETECT; | ||
| 733 | intel_vgpu_trigger_virtual_event(vgpu, DP_C_HOTPLUG); | ||
| 698 | } | 734 | } |
| 699 | vgpu_vreg_t(vgpu, PCH_PORT_HOTPLUG) |= | ||
| 700 | PORTB_HOTPLUG_STATUS_MASK; | ||
| 701 | intel_vgpu_trigger_virtual_event(vgpu, DP_B_HOTPLUG); | ||
| 702 | } | 735 | } |
| 703 | } | 736 | } |
| 704 | 737 | ||
| @@ -437,10 +437,9 @@ static struct intel_vgpu *__intel_gvt_create_vgpu(struct intel_gvt *gvt, · 436 unmodified lines | |||
| 437 | if (ret) | 437 | if (ret) |
| 438 | goto out_clean_sched_policy; | 438 | goto out_clean_sched_policy; |
| 439 | 439 | ||
| 440 | if (IS_BROADWELL(dev_priv)) | 440 | if (IS_BROADWELL(dev_priv) || IS_BROXTON(dev_priv)) |
| 441 | ret = intel_gvt_hypervisor_set_edid(vgpu, PORT_B); | 441 | ret = intel_gvt_hypervisor_set_edid(vgpu, PORT_B); |
| 442 | /* FixMe: Re-enable APL/BXT once vfio_edid enabled */ | 442 | else |
| 443 | else if (!IS_BROXTON(dev_priv)) | ||
| 444 | ret = intel_gvt_hypervisor_set_edid(vgpu, PORT_D); | 443 | ret = intel_gvt_hypervisor_set_edid(vgpu, PORT_D); |
| 445 | if (ret) | 444 | if (ret) |
| 446 | goto out_clean_sched_policy; | 445 | goto out_clean_sched_policy; |
| @@ -631,24 +631,26 @@ static int flush_lazy_signals(struct i915_active *ref) · 630 unmodified lines | |||
| 631 | 631 | ||
| 632 | int __i915_active_wait(struct i915_active *ref, int state) | 632 | int __i915_active_wait(struct i915_active *ref, int state) |
| 633 | { | 633 | { |
| 634 | int err; | ||
| 635 | |||
| 636 | might_sleep(); | 634 | might_sleep(); |
| 637 | 635 | ||
| 638 | if (!i915_active_acquire_if_busy(ref)) | ||
| 639 | return 0; | ||
| 640 | |||
| 641 | /* Any fence added after the wait begins will not be auto-signaled */ | 636 | /* Any fence added after the wait begins will not be auto-signaled */ |
| 642 | err = flush_lazy_signals(ref); | 637 | if (i915_active_acquire_if_busy(ref)) { |
| 643 | i915_active_release(ref); | 638 | int err; |
| 644 | if (err) | ||
| 645 | return err; | ||
| 646 | 639 | ||
| 647 | if (!i915_active_is_idle(ref) && | 640 | err = flush_lazy_signals(ref); |
| 648 | ___wait_var_event(ref, i915_active_is_idle(ref), | 641 | i915_active_release(ref); |
| 649 | state, 0, 0, schedule())) | 642 | if (err) |
| 650 | return -EINTR; | 643 | return err; |
| 651 | 644 | ||
| 645 | if (___wait_var_event(ref, i915_active_is_idle(ref), | ||
| 646 | state, 0, 0, schedule())) | ||
| 647 | return -EINTR; | ||
| 648 | } | ||
| 649 | |||
| 650 | /* | ||
| 651 | * After the wait is complete, the caller may free the active. | ||
| 652 | * We have to flush any concurrent retirement before returning. | ||
| 653 | */ | ||
| 652 | flush_work(&ref->work); | 654 | flush_work(&ref->work); |
| 653 | return 0; | 655 | return 0; |
| 654 | } | 656 | } |
| @@ -1166,7 +1166,7 @@ static u32 *copy_batch(struct drm_i915_gem_object *dst_obj, · 1165 unmodified lines | |||
| 1166 | } | 1166 | } |
| 1167 | } | 1167 | } |
| 1168 | if (IS_ERR(src)) { | 1168 | if (IS_ERR(src)) { |
| 1169 | unsigned long x, n; | 1169 | unsigned long x, n, remain; |
| 1170 | void *ptr; | 1170 | void *ptr; |
| 1171 | 1171 | ||
| 1172 | /* | 1172 | /* |
| @@ -1177,14 +1177,15 @@ static u32 *copy_batch(struct drm_i915_gem_object *dst_obj, · 4 unmodified lines | |||
| 1177 | * We don't care about copying too much here as we only | 1177 | * We don't care about copying too much here as we only |
| 1178 | * validate up to the end of the batch. | 1178 | * validate up to the end of the batch. |
| 1179 | */ | 1179 | */ |
| 1180 | remain = length; | ||
| 1180 | if (!(dst_obj->cache_coherent & I915_BO_CACHE_COHERENT_FOR_READ)) | 1181 | if (!(dst_obj->cache_coherent & I915_BO_CACHE_COHERENT_FOR_READ)) |
| 1181 | length = round_up(length, | 1182 | remain = round_up(remain, |
| 1182 | boot_cpu_data.x86_clflush_size); | 1183 | boot_cpu_data.x86_clflush_size); |
| 1183 | 1184 | ||
| 1184 | ptr = dst; | 1185 | ptr = dst; |
| 1185 | x = offset_in_page(offset); | 1186 | x = offset_in_page(offset); |
| 1186 | for (n = offset >> PAGE_SHIFT; length; n++) { | 1187 | for (n = offset >> PAGE_SHIFT; remain; n++) { |
| 1187 | int len = min(length, PAGE_SIZE - x); | 1188 | int len = min(remain, PAGE_SIZE - x); |
| 1188 | 1189 | ||
| 1189 | src = kmap_atomic(i915_gem_object_get_page(src_obj, n)); | 1190 | src = kmap_atomic(i915_gem_object_get_page(src_obj, n)); |
| 1190 | if (needs_clflush) | 1191 | if (needs_clflush) |
| @@ -1193,13 +1194,15 @@ static u32 *copy_batch(struct drm_i915_gem_object *dst_obj, · 2 unmodified lines | |||
| 1193 | kunmap_atomic(src); | 1194 | kunmap_atomic(src); |
| 1194 | 1195 | ||
| 1195 | ptr += len; | 1196 | ptr += len; |
| 1196 | length -= len; | 1197 | remain -= len; |
| 1197 | x = 0; | 1198 | x = 0; |
| 1198 | } | 1199 | } |
| 1199 | } | 1200 | } |
| 1200 | 1201 | ||
| 1201 | i915_gem_object_unpin_pages(src_obj); | 1202 | i915_gem_object_unpin_pages(src_obj); |
| 1202 | 1203 | ||
| 1204 | memset32(dst + length, 0, (dst_obj->base.size - length) / sizeof(u32)); | ||
| 1205 | |||
| 1203 | /* dst_obj is returned with vmap pinned */ | 1206 | /* dst_obj is returned with vmap pinned */ |
| 1204 | return dst; | 1207 | return dst; |
| 1205 | } | 1208 | } |
| @@ -1392,11 +1395,6 @@ static unsigned long *alloc_whitelist(u32 batch_length) · 186 unmodified lines | |||
| 1392 | 1395 | ||
| 1393 | #define LENGTH_BIAS 2 | 1396 | #define LENGTH_BIAS 2 |
| 1394 | 1397 | ||
| 1395 | static bool shadow_needs_clflush(struct drm_i915_gem_object *obj) | ||
| 1396 | { | ||
| 1397 | return !(obj->cache_coherent & I915_BO_CACHE_COHERENT_FOR_WRITE); | ||
| 1398 | } | ||
| 1399 | |||
| 1400 | /** | 1398 | /** |
| 1401 | * intel_engine_cmd_parser() - parse a batch buffer for privilege violations | 1399 | * intel_engine_cmd_parser() - parse a batch buffer for privilege violations |
| 1402 | * @engine: the engine on which the batch is to execute | 1400 | * @engine: the engine on which the batch is to execute |
| @@ -1538,16 +1536,9 @@ int intel_engine_cmd_parser(struct intel_engine_cs *engine, · 135 unmodified lines | |||
| 1538 | ret = 0; /* allow execution */ | 1536 | ret = 0; /* allow execution */ |
| 1539 | } | 1537 | } |
| 1540 | } | 1538 | } |
| 1541 | |||
| 1542 | if (shadow_needs_clflush(shadow->obj)) | ||
| 1543 | drm_clflush_virt_range(batch_end, 8); | ||
| 1544 | } | 1539 | } |
| 1545 | 1540 | ||
| 1546 | if (shadow_needs_clflush(shadow->obj)) { | 1541 | i915_gem_object_flush_map(shadow->obj); |
| 1547 | void *ptr = page_mask_bits(shadow->obj->mm.mapping); | ||
| 1548 | |||
| 1549 | drm_clflush_virt_range(ptr, (void *)(cmd + 1) - ptr); | ||
| 1550 | } | ||
| 1551 | 1542 | ||
| 1552 | if (!IS_ERR_OR_NULL(jump_whitelist)) | 1543 | if (!IS_ERR_OR_NULL(jump_whitelist)) |
| 1553 | kfree(jump_whitelist); | 1544 | kfree(jump_whitelist); |
| @@ -578,8 +578,6 @@ static int i915_driver_hw_probe(struct drm_i915_private *dev_priv) · 577 unmodified lines | |||
| 578 | 578 | ||
| 579 | pci_set_master(pdev); | 579 | pci_set_master(pdev); |
| 580 | 580 | ||
| 581 | cpu_latency_qos_add_request(&dev_priv->pm_qos, PM_QOS_DEFAULT_VALUE); | ||
| 582 | |||
| 583 | intel_gt_init_workarounds(dev_priv); | 581 | intel_gt_init_workarounds(dev_priv); |
| 584 | 582 | ||
| 585 | /* On the 945G/GM, the chipset reports the MSI capability on the | 583 | /* On the 945G/GM, the chipset reports the MSI capability on the |
| @@ -626,7 +624,6 @@ static int i915_driver_hw_probe(struct drm_i915_private *dev_priv) · 40 unmodified lines | |||
| 626 | err_msi: | 624 | err_msi: |
| 627 | if (pdev->msi_enabled) | 625 | if (pdev->msi_enabled) |
| 628 | pci_disable_msi(pdev); | 626 | pci_disable_msi(pdev); |
| 629 | cpu_latency_qos_remove_request(&dev_priv->pm_qos); | ||
| 630 | err_mem_regions: | 627 | err_mem_regions: |
| 631 | intel_memory_regions_driver_release(dev_priv); | 628 | intel_memory_regions_driver_release(dev_priv); |
| 632 | err_ggtt: | 629 | err_ggtt: |
| @@ -648,8 +645,6 @@ static void i915_driver_hw_remove(struct drm_i915_private *dev_priv) · 15 unmodified lines | |||
| 648 | 645 | ||
| 649 | if (pdev->msi_enabled) | 646 | if (pdev->msi_enabled) |
| 650 | pci_disable_msi(pdev); | 647 | pci_disable_msi(pdev); |
| 651 | |||
| 652 | cpu_latency_qos_remove_request(&dev_priv->pm_qos); | ||
| 653 | } | 648 | } |
| 654 | 649 | ||
| 655 | /** | 650 | /** |
| @@ -1052,6 +1047,8 @@ static void intel_shutdown_encoders(struct drm_i915_private *dev_priv) · 396 unmodified lines | |||
| 1052 | 1047 | ||
| 1053 | void i915_driver_shutdown(struct drm_i915_private *i915) | 1048 | void i915_driver_shutdown(struct drm_i915_private *i915) |
| 1054 | { | 1049 | { |
| 1050 | disable_rpm_wakeref_asserts(&i915->runtime_pm); | ||
| 1051 | |||
| 1055 | i915_gem_suspend(i915); | 1052 | i915_gem_suspend(i915); |
| 1056 | 1053 | ||
| 1057 | drm_kms_helper_poll_disable(&i915->drm); | 1054 | drm_kms_helper_poll_disable(&i915->drm); |
| @@ -1065,6 +1062,8 @@ void i915_driver_shutdown(struct drm_i915_private *i915) · 7 unmodified lines | |||
| 1065 | 1062 | ||
| 1066 | intel_suspend_encoders(i915); | 1063 | intel_suspend_encoders(i915); |
| 1067 | intel_shutdown_encoders(i915); | 1064 | intel_shutdown_encoders(i915); |
| 1065 | |||
| 1066 | enable_rpm_wakeref_asserts(&i915->runtime_pm); | ||
| 1068 | } | 1067 | } |
| 1069 | 1068 | ||
| 1070 | static bool suspend_to_idle(struct drm_i915_private *dev_priv) | 1069 | static bool suspend_to_idle(struct drm_i915_private *dev_priv) |
| @@ -891,9 +891,6 @@ struct drm_i915_private { · 890 unmodified lines | |||
| 891 | 891 | ||
| 892 | bool display_irqs_enabled; | 892 | bool display_irqs_enabled; |
| 893 | 893 | ||
| 894 | /* To control wakeup latency, e.g. for irq-driven dp aux transfers. */ | ||
| 895 | struct pm_qos_request pm_qos; | ||
| 896 | |||
| 897 | /* Sideband mailbox protection */ | 894 | /* Sideband mailbox protection */ |
| 898 | struct mutex sb_lock; | 895 | struct mutex sb_lock; |
| 899 | struct pm_qos_request sb_qos; | 896 | struct pm_qos_request sb_qos; |
| @@ -1349,7 +1346,7 @@ intel_subplatform(const struct intel_runtime_info *info, enum intel_platform p) · 449 unmodified lines | |||
| 1349 | { | 1346 | { |
| 1350 | const unsigned int pi = __platform_mask_index(info, p); | 1347 | const unsigned int pi = __platform_mask_index(info, p); |
| 1351 | 1348 | ||
| 1352 | return info->platform_mask[pi] & INTEL_SUBPLATFORM_BITS; | 1349 | return info->platform_mask[pi] & ((1 << INTEL_SUBPLATFORM_BITS) - 1); |
| 1353 | } | 1350 | } |
| 1354 | 1351 | ||
| 1355 | static __always_inline bool | 1352 | static __always_inline bool |
| @@ -0,0 +1,146 @@ | |||
| 1 | // SPDX-License-Identifier: MIT | ||
| 2 | /* | ||
| 3 | * Copyright © 2021 Intel Corporation | ||
| 4 | */ | ||
| 5 | |||
| 6 | #include <linux/kernel.h> | ||
| 7 | #include <linux/moduleparam.h> | ||
| 8 | #include <linux/slab.h> | ||
| 9 | #include <linux/string.h> | ||
| 10 | |||
| 11 | #include "i915_drv.h" | ||
| 12 | #include "i915_mitigations.h" | ||
| 13 | |||
| 14 | static unsigned long mitigations __read_mostly = ~0UL; | ||
| 15 | |||
| 16 | enum { | ||
| 17 | CLEAR_RESIDUALS = 0, | ||
| 18 | }; | ||
| 19 | |||
| 20 | static const char * const names[] = { | ||
| 21 | [CLEAR_RESIDUALS] = "residuals", | ||
| 22 | }; | ||
| 23 | |||
| 24 | bool i915_mitigate_clear_residuals(void) | ||
| 25 | { | ||
| 26 | return READ_ONCE(mitigations) & BIT(CLEAR_RESIDUALS); | ||
| 27 | } | ||
| 28 | |||
| 29 | static int mitigations_set(const char *val, const struct kernel_param *kp) | ||
| 30 | { | ||
| 31 | unsigned long new = ~0UL; | ||
| 32 | char *str, *sep, *tok; | ||
| 33 | bool first = true; | ||
| 34 | int err = 0; | ||
| 35 | |||
| 36 | BUILD_BUG_ON(ARRAY_SIZE(names) >= BITS_PER_TYPE(mitigations)); | ||
| 37 | |||
| 38 | str = kstrdup(val, GFP_KERNEL); | ||
| 39 | if (!str) | ||
| 40 | return -ENOMEM; | ||
| 41 | |||
| 42 | for (sep = str; (tok = strsep(&sep, ","));) { | ||
| 43 | bool enable = true; | ||
| 44 | int i; | ||
| 45 | |||
| 46 | /* Be tolerant of leading/trailing whitespace */ | ||
| 47 | tok = strim(tok); | ||
| 48 | |||
| 49 | if (first) { | ||
| 50 | first = false; | ||
| 51 | |||
| 52 | if (!strcmp(tok, "auto")) | ||
| 53 | continue; | ||
| 54 | |||
| 55 | new = 0; | ||
| 56 | if (!strcmp(tok, "off")) | ||
| 57 | continue; | ||
| 58 | } | ||
| 59 | |||
| 60 | if (*tok == '!') { | ||
| 61 | enable = !enable; | ||
| 62 | tok++; | ||
| 63 | } | ||
| 64 | |||
| 65 | if (!strncmp(tok, "no", 2)) { | ||
| 66 | enable = !enable; | ||
| 67 | tok += 2; | ||
| 68 | } | ||
| 69 | |||
| 70 | if (*tok == '\0') | ||
| 71 | continue; | ||
| 72 | |||
| 73 | for (i = 0; i < ARRAY_SIZE(names); i++) { | ||
| 74 | if (!strcmp(tok, names[i])) { | ||
| 75 | if (enable) | ||
| 76 | new |= BIT(i); | ||
| 77 | else | ||
| 78 | new &= ~BIT(i); | ||
| 79 | break; | ||
| 80 | } | ||
| 81 | } | ||
| 82 | if (i == ARRAY_SIZE(names)) { | ||
| 83 | pr_err("Bad \"%s.mitigations=%s\", '%s' is unknown\n", | ||
| 84 | DRIVER_NAME, val, tok); | ||
| 85 | err = -EINVAL; | ||
| 86 | break; | ||
| 87 | } | ||
| 88 | } | ||
| 89 | kfree(str); | ||
| 90 | if (err) | ||
| 91 | return err; | ||
| 92 | |||
| 93 | WRITE_ONCE(mitigations, new); | ||
| 94 | return 0; | ||
| 95 | } | ||
| 96 | |||
| 97 | static int mitigations_get(char *buffer, const struct kernel_param *kp) | ||
| 98 | { | ||
| 99 | unsigned long local = READ_ONCE(mitigations); | ||
| 100 | int count, i; | ||
| 101 | bool enable; | ||
| 102 | |||
| 103 | if (!local) | ||
| 104 | return scnprintf(buffer, PAGE_SIZE, "%s\n", "off"); | ||
| 105 | |||
| 106 | if (local & BIT(BITS_PER_LONG - 1)) { | ||
| 107 | count = scnprintf(buffer, PAGE_SIZE, "%s,", "auto"); | ||
| 108 | enable = false; | ||
| 109 | } else { | ||
| 110 | enable = true; | ||
| 111 | count = 0; | ||
| 112 | } | ||
| 113 | |||
| 114 | for (i = 0; i < ARRAY_SIZE(names); i++) { | ||
| 115 | if ((local & BIT(i)) != enable) | ||
| 116 | continue; | ||
| 117 | |||
| 118 | count += scnprintf(buffer + count, PAGE_SIZE - count, | ||
| 119 | "%s%s,", enable ? "" : "!", names[i]); | ||
| 120 | } | ||
| 121 | |||
| 122 | buffer[count - 1] = '\n'; | ||
| 123 | return count; | ||
| 124 | } | ||
| 125 | |||
| 126 | static const struct kernel_param_ops ops = { | ||
| 127 | .set = mitigations_set, | ||
| 128 | .get = mitigations_get, | ||
| 129 | }; | ||
| 130 | |||
| 131 | module_param_cb_unsafe(mitigations, &ops, NULL, 0600); | ||
| 132 | MODULE_PARM_DESC(mitigations, | ||
| 133 | "Selectively enable security mitigations for all Intel® GPUs in the system.\n" | ||
| 134 | "\n" | ||
| 135 | " auto -- enables all mitigations required for the platform [default]\n" | ||
| 136 | " off -- disables all mitigations\n" | ||
| 137 | "\n" | ||
| 138 | "Individual mitigations can be enabled by passing a comma-separated string,\n" | ||
| 139 | "e.g. mitigations=residuals to enable only clearing residuals or\n" | ||
| 140 | "mitigations=auto,noresiduals to disable only the clear residual mitigation.\n" | ||
| 141 | "Either '!' or 'no' may be used to switch from enabling the mitigation to\n" | ||
| 142 | "disabling it.\n" | ||
| 143 | "\n" | ||
| 144 | "Active mitigations for Ivybridge, Baytrail, Haswell:\n" | ||
| 145 | " residuals -- clear all thread-local registers between contexts" | ||
| 146 | ); | ||
| @@ -0,0 +1,13 @@ | |||
| 1 | /* SPDX-License-Identifier: MIT */ | ||
| 2 | /* | ||
| 3 | * Copyright © 2021 Intel Corporation | ||
| 4 | */ | ||
| 5 | |||
| 6 | #ifndef __I915_MITIGATIONS_H__ | ||
| 7 | #define __I915_MITIGATIONS_H__ | ||
| 8 | |||
| 9 | #include <linux/types.h> | ||
| 10 | |||
| 11 | bool i915_mitigate_clear_residuals(void); | ||
| 12 | |||
| 13 | #endif /* __I915_MITIGATIONS_H__ */ | ||
| @@ -184,13 +184,24 @@ static u64 get_rc6(struct intel_gt *gt) · 183 unmodified lines | |||
| 184 | return val; | 184 | return val; |
| 185 | } | 185 | } |
| 186 | 186 | ||
| 187 | static void park_rc6(struct drm_i915_private *i915) | 187 | static void init_rc6(struct i915_pmu *pmu) |
| 188 | { | 188 | { |
| 189 | struct i915_pmu *pmu = &i915->pmu; | 189 | struct drm_i915_private *i915 = container_of(pmu, typeof(*i915), pmu); |
| 190 | intel_wakeref_t wakeref; | ||
| 190 | 191 | ||
| 191 | if (pmu->enable & config_enabled_mask(I915_PMU_RC6_RESIDENCY)) | 192 | with_intel_runtime_pm(i915->gt.uncore->rpm, wakeref) { |
| 192 | pmu->sample[__I915_SAMPLE_RC6].cur = __get_rc6(&i915->gt); | 193 | pmu->sample[__I915_SAMPLE_RC6].cur = __get_rc6(&i915->gt); |
| 194 | pmu->sample[__I915_SAMPLE_RC6_LAST_REPORTED].cur = | ||
| 195 | pmu->sample[__I915_SAMPLE_RC6].cur; | ||
| 196 | pmu->sleep_last = ktime_get(); | ||
| 197 | } | ||
| 198 | } | ||
| 193 | 199 | ||
| 200 | static void park_rc6(struct drm_i915_private *i915) | ||
| 201 | { | ||
| 202 | struct i915_pmu *pmu = &i915->pmu; | ||
| 203 | |||
| 204 | pmu->sample[__I915_SAMPLE_RC6].cur = __get_rc6(&i915->gt); | ||
| 194 | pmu->sleep_last = ktime_get(); | 205 | pmu->sleep_last = ktime_get(); |
| 195 | } | 206 | } |
| 196 | 207 | ||
| @@ -201,6 +212,7 @@ static u64 get_rc6(struct intel_gt *gt) · 4 unmodified lines | |||
| 201 | return __get_rc6(gt); | 212 | return __get_rc6(gt); |
| 202 | } | 213 | } |
| 203 | 214 | ||
| 215 | static void init_rc6(struct i915_pmu *pmu) { } | ||
| 204 | static void park_rc6(struct drm_i915_private *i915) {} | 216 | static void park_rc6(struct drm_i915_private *i915) {} |
| 205 | 217 | ||
| 206 | #endif | 218 | #endif |
| @@ -612,10 +624,8 @@ static void i915_pmu_enable(struct perf_event *event) · 405 unmodified lines | |||
| 612 | container_of(event->pmu, typeof(*i915), pmu.base); | 624 | container_of(event->pmu, typeof(*i915), pmu.base); |
| 613 | unsigned int bit = event_enabled_bit(event); | 625 | unsigned int bit = event_enabled_bit(event); |
| 614 | struct i915_pmu *pmu = &i915->pmu; | 626 | struct i915_pmu *pmu = &i915->pmu; |
| 615 | intel_wakeref_t wakeref; | ||
| 616 | unsigned long flags; | 627 | unsigned long flags; |
| 617 | 628 | ||
| 618 | wakeref = intel_runtime_pm_get(&i915->runtime_pm); | ||
| 619 | spin_lock_irqsave(&pmu->lock, flags); | 629 | spin_lock_irqsave(&pmu->lock, flags); |
| 620 | 630 | ||
| 621 | /* | 631 | /* |
| @@ -626,13 +636,6 @@ static void i915_pmu_enable(struct perf_event *event) · 4 unmodified lines | |||
| 626 | GEM_BUG_ON(bit >= ARRAY_SIZE(pmu->enable_count)); | 636 | GEM_BUG_ON(bit >= ARRAY_SIZE(pmu->enable_count)); |
| 627 | GEM_BUG_ON(pmu->enable_count[bit] == ~0); | 637 | GEM_BUG_ON(pmu->enable_count[bit] == ~0); |
| 628 | 638 | ||
| 629 | if (pmu->enable_count[bit] == 0 && | ||
| 630 | config_enabled_mask(I915_PMU_RC6_RESIDENCY) & BIT_ULL(bit)) { | ||
| 631 | pmu->sample[__I915_SAMPLE_RC6_LAST_REPORTED].cur = 0; | ||
| 632 | pmu->sample[__I915_SAMPLE_RC6].cur = __get_rc6(&i915->gt); | ||
| 633 | pmu->sleep_last = ktime_get(); | ||
| 634 | } | ||
| 635 | |||
| 636 | pmu->enable |= BIT_ULL(bit); | 639 | pmu->enable |= BIT_ULL(bit); |
| 637 | pmu->enable_count[bit]++; | 640 | pmu->enable_count[bit]++; |
| 638 | 641 | ||
| @@ -673,8 +676,6 @@ static void i915_pmu_enable(struct perf_event *event) · 34 unmodified lines | |||
| 673 | * an existing non-zero value. | 676 | * an existing non-zero value. |
| 674 | */ | 677 | */ |
| 675 | local64_set(&event->hw.prev_count, __i915_pmu_event_read(event)); | 678 | local64_set(&event->hw.prev_count, __i915_pmu_event_read(event)); |
| 676 | |||
| 677 | intel_runtime_pm_put(&i915->runtime_pm, wakeref); | ||
| 678 | } | 679 | } |
| 679 | 680 | ||
| 680 | static void i915_pmu_disable(struct perf_event *event) | 681 | static void i915_pmu_disable(struct perf_event *event) |
| @@ -1130,6 +1131,7 @@ void i915_pmu_register(struct drm_i915_private *i915) · 449 unmodified lines | |||
| 1130 | hrtimer_init(&pmu->timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); | 1131 | hrtimer_init(&pmu->timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); |
| 1131 | pmu->timer.function = i915_sample; | 1132 | pmu->timer.function = i915_sample; |
| 1132 | pmu->cpuhp.cpu = -1; | 1133 | pmu->cpuhp.cpu = -1; |
| 1134 | init_rc6(pmu); | ||
| 1133 | 1135 | ||
| 1134 | if (!is_igp(i915)) { | 1136 | if (!is_igp(i915)) { |
| 1135 | pmu->name = kasprintf(GFP_KERNEL, | 1137 | pmu->name = kasprintf(GFP_KERNEL, |
| @@ -434,7 +434,7 @@ static inline u32 hwsp_seqno(const struct i915_request *rq) · 433 unmodified lines | |||
| 434 | 434 | ||
| 435 | static inline bool __i915_request_has_started(const struct i915_request *rq) | 435 | static inline bool __i915_request_has_started(const struct i915_request *rq) |
| 436 | { | 436 | { |
| 437 | return i915_seqno_passed(hwsp_seqno(rq), rq->fence.seqno - 1); | 437 | return i915_seqno_passed(__hwsp_seqno(rq), rq->fence.seqno - 1); |
| 438 | } | 438 | } |
| 439 | 439 | ||
| 440 | /** | 440 | /** |
| @@ -465,11 +465,19 @@ static inline bool __i915_request_has_started(const struct i915_request *rq) · 24 unmodified lines | |||
| 465 | */ | 465 | */ |
| 466 | static inline bool i915_request_started(const struct i915_request *rq) | 466 | static inline bool i915_request_started(const struct i915_request *rq) |
| 467 | { | 467 | { |
| 468 | bool result; | ||
| 469 | |||
| 468 | if (i915_request_signaled(rq)) | 470 | if (i915_request_signaled(rq)) |
| 469 | return true; | 471 | return true; |
| 470 | 472 | ||
| 471 | /* Remember: started but may have since been preempted! */ | 473 | result = true; |
| 472 | return __i915_request_has_started(rq); | 474 | rcu_read_lock(); /* the HWSP may be freed at runtime */ |
| 475 | if (likely(!i915_request_signaled(rq))) | ||
| 476 | /* Remember: started but may have since been preempted! */ | ||
| 477 | result = __i915_request_has_started(rq); | ||
| 478 | rcu_read_unlock(); | ||
| 479 | |||
| 480 | return result; | ||
| 473 | } | 481 | } |
| 474 | 482 | ||
| 475 | /** | 483 | /** |
| @@ -482,10 +490,16 @@ static inline bool i915_request_started(const struct i915_request *rq) · 6 unmodified lines | |||
| 482 | */ | 490 | */ |
| 483 | static inline bool i915_request_is_running(const struct i915_request *rq) | 491 | static inline bool i915_request_is_running(const struct i915_request *rq) |
| 484 | { | 492 | { |
| 493 | bool result; | ||
| 494 | |||
| 485 | if (!i915_request_is_active(rq)) | 495 | if (!i915_request_is_active(rq)) |
| 486 | return false; | 496 | return false; |
| 487 | 497 | ||
| 488 | return __i915_request_has_started(rq); | 498 | rcu_read_lock(); |
| 499 | result = __i915_request_has_started(rq) && i915_request_is_active(rq); | ||
| 500 | rcu_read_unlock(); | ||
| 501 | |||
| 502 | return result; | ||
| 489 | } | 503 | } |
| 490 | 504 | ||
| 491 | /** | 505 | /** |
| @@ -509,12 +523,25 @@ static inline bool i915_request_is_ready(const struct i915_request *rq) · 17 unmodified lines | |||
| 509 | return !list_empty(&rq->sched.link); | 523 | return !list_empty(&rq->sched.link); |
| 510 | } | 524 | } |
| 511 | 525 | ||
| 526 | static inline bool __i915_request_is_complete(const struct i915_request *rq) | ||
| 527 | { | ||
| 528 | return i915_seqno_passed(__hwsp_seqno(rq), rq->fence.seqno); | ||
| 529 | } | ||
| 530 | |||
| 512 | static inline bool i915_request_completed(const struct i915_request *rq) | 531 | static inline bool i915_request_completed(const struct i915_request *rq) |
| 513 | { | 532 | { |
| 533 | bool result; | ||
| 534 | |||
| 514 | if (i915_request_signaled(rq)) | 535 | if (i915_request_signaled(rq)) |
| 515 | return true; | 536 | return true; |
| 516 | 537 | ||
| 517 | return i915_seqno_passed(hwsp_seqno(rq), rq->fence.seqno); | 538 | result = true; |
| 539 | rcu_read_lock(); /* the HWSP may be freed at runtime */ | ||
| 540 | if (likely(!i915_request_signaled(rq))) | ||
| 541 | result = __i915_request_is_complete(rq); | ||
| 542 | rcu_read_unlock(); | ||
| 543 | |||
| 544 | return result; | ||
| 518 | } | 545 | } |
| 519 | 546 | ||
| 520 | static inline void i915_request_mark_complete(struct i915_request *rq) | 547 | static inline void i915_request_mark_complete(struct i915_request *rq) |
| @@ -1880,7 +1880,7 @@ static int igt_cs_tlb(void *arg) · 1879 unmodified lines | |||
| 1880 | vma = i915_vma_instance(out, vm, NULL); | 1880 | vma = i915_vma_instance(out, vm, NULL); |
| 1881 | if (IS_ERR(vma)) { | 1881 | if (IS_ERR(vma)) { |
| 1882 | err = PTR_ERR(vma); | 1882 | err = PTR_ERR(vma); |
| 1883 | goto out_put_batch; | 1883 | goto out_put_out; |
| 1884 | } | 1884 | } |
| 1885 | 1885 | ||
| 1886 | err = i915_vma_pin(vma, 0, 0, | 1886 | err = i915_vma_pin(vma, 0, 0, |
| @@ -534,8 +534,10 @@ struct msm_gpu *a2xx_gpu_init(struct drm_device *dev) · 533 unmodified lines | |||
| 534 | 534 | ||
| 535 | if (!gpu->aspace) { | 535 | if (!gpu->aspace) { |
| 536 | dev_err(dev->dev, "No memory protection without MMU\n"); | 536 | dev_err(dev->dev, "No memory protection without MMU\n"); |
| 537 | ret = -ENXIO; | 537 | if (!allow_vram_carveout) { |
| 538 | goto fail; | 538 | ret = -ENXIO; |
| 539 | goto fail; | ||
| 540 | } | ||
| 539 | } | 541 | } |
| 540 | 542 | ||
| 541 | return gpu; | 543 | return gpu; |
| @@ -564,8 +564,10 @@ struct msm_gpu *a3xx_gpu_init(struct drm_device *dev) · 563 unmodified lines | |||
| 564 | * implement a cmdstream validator. | 564 | * implement a cmdstream validator. |
| 565 | */ | 565 | */ |
| 566 | DRM_DEV_ERROR(dev->dev, "No memory protection without IOMMU\n"); | 566 | DRM_DEV_ERROR(dev->dev, "No memory protection without IOMMU\n"); |
| 567 | ret = -ENXIO; | 567 | if (!allow_vram_carveout) { |
| 568 | goto fail; | 568 | ret = -ENXIO; |
| 569 | goto fail; | ||
| 570 | } | ||
| 569 | } | 571 | } |
| 570 | 572 | ||
| 571 | icc_path = devm_of_icc_get(&pdev->dev, "gfx-mem"); | 573 | icc_path = devm_of_icc_get(&pdev->dev, "gfx-mem"); |
| @@ -692,8 +692,10 @@ struct msm_gpu *a4xx_gpu_init(struct drm_device *dev) · 691 unmodified lines | |||
| 692 | * implement a cmdstream validator. | 692 | * implement a cmdstream validator. |
| 693 | */ | 693 | */ |
| 694 | DRM_DEV_ERROR(dev->dev, "No memory protection without IOMMU\n"); | 694 | DRM_DEV_ERROR(dev->dev, "No memory protection without IOMMU\n"); |
| 695 | ret = -ENXIO; | 695 | if (!allow_vram_carveout) { |
| 696 | goto fail; | 696 | ret = -ENXIO; |
| 697 | goto fail; | ||
| 698 | } | ||
| 697 | } | 699 | } |
| 698 | 700 | ||
| 699 | icc_path = devm_of_icc_get(&pdev->dev, "gfx-mem"); | 701 | icc_path = devm_of_icc_get(&pdev->dev, "gfx-mem"); |
| @@ -18,6 +18,10 @@ bool snapshot_debugbus = false; · 17 unmodified lines | |||
| 18 | MODULE_PARM_DESC(snapshot_debugbus, "Include debugbus sections in GPU devcoredump (if not fused off)"); | 18 | MODULE_PARM_DESC(snapshot_debugbus, "Include debugbus sections in GPU devcoredump (if not fused off)"); |
| 19 | module_param_named(snapshot_debugbus, snapshot_debugbus, bool, 0600); | 19 | module_param_named(snapshot_debugbus, snapshot_debugbus, bool, 0600); |
| 20 | 20 | ||
| 21 | bool allow_vram_carveout = false; | ||
| 22 | MODULE_PARM_DESC(allow_vram_carveout, "Allow using VRAM Carveout, in place of IOMMU"); | ||
| 23 | module_param_named(allow_vram_carveout, allow_vram_carveout, bool, 0600); | ||
| 24 | |||
| 21 | static const struct adreno_info gpulist[] = { | 25 | static const struct adreno_info gpulist[] = { |
| 22 | { | 26 | { |
| 23 | .rev = ADRENO_REV(2, 0, 0, 0), | 27 | .rev = ADRENO_REV(2, 0, 0, 0), |
| @@ -191,8 +191,6 @@ adreno_iommu_create_address_space(struct msm_gpu *gpu, · 190 unmodified lines | |||
| 191 | struct platform_device *pdev) | 191 | struct platform_device *pdev) |
| 192 | { | 192 | { |
| 193 | struct adreno_gpu *adreno_gpu = to_adreno_gpu(gpu); | 193 | struct adreno_gpu *adreno_gpu = to_adreno_gpu(gpu); |
| 194 | struct a6xx_gpu *a6xx_gpu = to_a6xx_gpu(adreno_gpu); | ||
| 195 | struct io_pgtable_domain_attr pgtbl_cfg; | ||
| 196 | struct iommu_domain *iommu; | 194 | struct iommu_domain *iommu; |
| 197 | struct msm_mmu *mmu; | 195 | struct msm_mmu *mmu; |
| 198 | struct msm_gem_address_space *aspace; | 196 | struct msm_gem_address_space *aspace; |
| @@ -202,13 +200,18 @@ adreno_iommu_create_address_space(struct msm_gpu *gpu, · 3 unmodified lines | |||
| 202 | if (!iommu) | 200 | if (!iommu) |
| 203 | return NULL; | 201 | return NULL; |
| 204 | 202 | ||
| 205 | /* | 203 | |
| 206 | * This allows GPU to set the bus attributes required to use system | 204 | if (adreno_is_a6xx(adreno_gpu)) { |
| 207 | * cache on behalf of the iommu page table walker. | 205 | struct a6xx_gpu *a6xx_gpu = to_a6xx_gpu(adreno_gpu); |
| 208 | */ | 206 | struct io_pgtable_domain_attr pgtbl_cfg; |
| 209 | if (!IS_ERR(a6xx_gpu->htw_llc_slice)) { | 207 | /* |
| 210 | pgtbl_cfg.quirks = IO_PGTABLE_QUIRK_ARM_OUTER_WBWA; | 208 | * This allows GPU to set the bus attributes required to use system |
| 211 | iommu_domain_set_attr(iommu, DOMAIN_ATTR_IO_PGTABLE_CFG, &pgtbl_cfg); | 209 | * cache on behalf of the iommu page table walker. |
| 210 | */ | ||
| 211 | if (!IS_ERR(a6xx_gpu->htw_llc_slice)) { | ||
| 212 | pgtbl_cfg.quirks = IO_PGTABLE_QUIRK_ARM_OUTER_WBWA; | ||
| 213 | iommu_domain_set_attr(iommu, DOMAIN_ATTR_IO_PGTABLE_CFG, &pgtbl_cfg); | ||
| 214 | } | ||
| 212 | } | 215 | } |
| 213 | 216 | ||
| 214 | mmu = msm_iommu_new(&pdev->dev, iommu); | 217 | mmu = msm_iommu_new(&pdev->dev, iommu); |
| @@ -18,6 +18,7 @@ · 17 unmodified lines | |||
| 18 | #include "adreno_pm4.xml.h" | 18 | #include "adreno_pm4.xml.h" |
| 19 | 19 | ||
| 20 | extern bool snapshot_debugbus; | 20 | extern bool snapshot_debugbus; |
| 21 | extern bool allow_vram_carveout; | ||
| 21 | 22 | ||
| 22 | enum { | 23 | enum { |
| 23 | ADRENO_FW_PM4 = 0, | 24 | ADRENO_FW_PM4 = 0, |
| @@ -211,6 +212,11 @@ static inline int adreno_is_a540(struct adreno_gpu *gpu) · 187 unmodified lines | |||
| 211 | return gpu->revn == 540; | 212 | return gpu->revn == 540; |
| 212 | } | 213 | } |
| 213 | 214 | ||
| 215 | static inline bool adreno_is_a6xx(struct adreno_gpu *gpu) | ||
| 216 | { | ||
| 217 | return ((gpu->revn < 700 && gpu->revn > 599)); | ||
| 218 | } | ||
| 219 | |||
| 214 | static inline int adreno_is_a618(struct adreno_gpu *gpu) | 220 | static inline int adreno_is_a618(struct adreno_gpu *gpu) |
| 215 | { | 221 | { |
| 216 | return gpu->revn == 618; | 222 | return gpu->revn == 618; |
| @@ -693,6 +693,13 @@ static int dp_irq_hpd_handle(struct dp_display_private *dp, u32 data) · 692 unmodified lines | |||
| 693 | return 0; | 693 | return 0; |
| 694 | } | 694 | } |
| 695 | 695 | ||
| 696 | if (state == ST_CONNECT_PENDING) { | ||
| 697 | /* wait until ST_CONNECTED */ | ||
| 698 | dp_add_event(dp, EV_IRQ_HPD_INT, 0, 1); /* delay = 1 */ | ||
| 699 | mutex_unlock(&dp->event_mutex); | ||
| 700 | return 0; | ||
| 701 | } | ||
| 702 | |||
| 696 | ret = dp_display_usbpd_attention_cb(&dp->pdev->dev); | 703 | ret = dp_display_usbpd_attention_cb(&dp->pdev->dev); |
| 697 | if (ret == -ECONNRESET) { /* cable unplugged */ | 704 | if (ret == -ECONNRESET) { /* cable unplugged */ |
| 698 | dp->core_initialized = false; | 705 | dp->core_initialized = false; |
| @@ -167,12 +167,18 @@ int dp_panel_read_sink_caps(struct dp_panel *dp_panel, · 166 unmodified lines | |||
| 167 | panel = container_of(dp_panel, struct dp_panel_private, dp_panel); | 167 | panel = container_of(dp_panel, struct dp_panel_private, dp_panel); |
| 168 | 168 | ||
| 169 | rc = dp_panel_read_dpcd(dp_panel); | 169 | rc = dp_panel_read_dpcd(dp_panel); |
| 170 | if (rc) { | ||
| 171 | DRM_ERROR("read dpcd failed %d\n", rc); | ||
| 172 | return rc; | ||
| 173 | } | ||
| 174 | |||
| 170 | bw_code = drm_dp_link_rate_to_bw_code(dp_panel->link_info.rate); | 175 | bw_code = drm_dp_link_rate_to_bw_code(dp_panel->link_info.rate); |
| 171 | if (rc || !is_link_rate_valid(bw_code) || | 176 | if (!is_link_rate_valid(bw_code) || |
| 172 | !is_lane_count_valid(dp_panel->link_info.num_lanes) || | 177 | !is_lane_count_valid(dp_panel->link_info.num_lanes) || |
| 173 | (bw_code > dp_panel->max_bw_code)) { | 178 | (bw_code > dp_panel->max_bw_code)) { |
| 174 | DRM_ERROR("read dpcd failed %d\n", rc); | 179 | DRM_ERROR("Illegal link rate=%d lane=%d\n", dp_panel->link_info.rate, |
| 175 | return rc; | 180 | dp_panel->link_info.num_lanes); |
| 181 | return -EINVAL; | ||
| 176 | } | 182 | } |
| 177 | 183 | ||
| 178 | if (dp_panel->dfp_present) { | 184 | if (dp_panel->dfp_present) { |
| @@ -457,14 +457,14 @@ static int msm_drm_init(struct device *dev, const struct drm_driver *drv) · 456 unmodified lines | |||
| 457 | 457 | ||
| 458 | drm_mode_config_init(ddev); | 458 | drm_mode_config_init(ddev); |
| 459 | 459 | ||
| 460 | /* Bind all our sub-components: */ | 460 | ret = msm_init_vram(ddev); |
| 461 | ret = component_bind_all(dev, ddev); | ||
| 462 | if (ret) | 461 | if (ret) |
| 463 | goto err_destroy_mdss; | 462 | goto err_destroy_mdss; |
| 464 | 463 | ||
| 465 | ret = msm_init_vram(ddev); | 464 | /* Bind all our sub-components: */ |
| 465 | ret = component_bind_all(dev, ddev); | ||
| 466 | if (ret) | 466 | if (ret) |
| 467 | goto err_msm_uninit; | 467 | goto err_destroy_mdss; |
| 468 | 468 | ||
| 469 | dma_set_max_seg_size(dev, UINT_MAX); | 469 | dma_set_max_seg_size(dev, UINT_MAX); |
| 470 | 470 | ||
| @@ -96,6 +96,8 @@ static struct page **get_pages(struct drm_gem_object *obj) · 95 unmodified lines | |||
| 96 | { | 96 | { |
| 97 | struct msm_gem_object *msm_obj = to_msm_bo(obj); | 97 | struct msm_gem_object *msm_obj = to_msm_bo(obj); |
| 98 | 98 | ||
| 99 | WARN_ON(!msm_gem_is_locked(obj)); | ||
| 100 | |||
| 99 | if (!msm_obj->pages) { | 101 | if (!msm_obj->pages) { |
| 100 | struct drm_device *dev = obj->dev; | 102 | struct drm_device *dev = obj->dev; |
| 101 | struct page **p; | 103 | struct page **p; |
| @@ -988,6 +990,8 @@ void msm_gem_free_object(struct drm_gem_object *obj) · 886 unmodified lines | |||
| 988 | if (msm_obj->pages) | 990 | if (msm_obj->pages) |
| 989 | kvfree(msm_obj->pages); | 991 | kvfree(msm_obj->pages); |
| 990 | 992 | ||
| 993 | put_iova_vmas(obj); | ||
| 994 | |||
| 991 | /* dma_buf_detach() grabs resv lock, so we need to unlock | 995 | /* dma_buf_detach() grabs resv lock, so we need to unlock |
| 992 | * prior to drm_prime_gem_destroy | 996 | * prior to drm_prime_gem_destroy |
| 993 | */ | 997 | */ |
| @@ -997,11 +1001,10 @@ void msm_gem_free_object(struct drm_gem_object *obj) · 3 unmodified lines | |||
| 997 | } else { | 1001 | } else { |
| 998 | msm_gem_vunmap(obj); | 1002 | msm_gem_vunmap(obj); |
| 999 | put_pages(obj); | 1003 | put_pages(obj); |
| 1004 | put_iova_vmas(obj); | ||
| 1000 | msm_gem_unlock(obj); | 1005 | msm_gem_unlock(obj); |
| 1001 | } | 1006 | } |
| 1002 | 1007 | ||
| 1003 | put_iova_vmas(obj); | ||
| 1004 | |||
| 1005 | drm_gem_object_release(obj); | 1008 | drm_gem_object_release(obj); |
| 1006 | 1009 | ||
| 1007 | kfree(msm_obj); | 1010 | kfree(msm_obj); |
| @@ -1115,6 +1118,8 @@ static struct drm_gem_object *_msm_gem_new(struct drm_device *dev, · 107 unmodified lines | |||
| 1115 | struct msm_gem_vma *vma; | 1118 | struct msm_gem_vma *vma; |
| 1116 | struct page **pages; | 1119 | struct page **pages; |
| 1117 | 1120 | ||
| 1121 | drm_gem_private_object_init(dev, obj, size); | ||
| 1122 | |||
| 1118 | msm_gem_lock(obj); | 1123 | msm_gem_lock(obj); |
| 1119 | 1124 | ||
| 1120 | vma = add_vma(obj, NULL); | 1125 | vma = add_vma(obj, NULL); |
| @@ -1126,9 +1131,9 @@ static struct drm_gem_object *_msm_gem_new(struct drm_device *dev, · 5 unmodified lines | |||
| 1126 | 1131 | ||
| 1127 | to_msm_bo(obj)->vram_node = &vma->node; | 1132 | to_msm_bo(obj)->vram_node = &vma->node; |
| 1128 | 1133 | ||
| 1129 | drm_gem_private_object_init(dev, obj, size); | 1134 | msm_gem_lock(obj); |
| 1130 | |||
| 1131 | pages = get_pages(obj); | 1135 | pages = get_pages(obj); |
| 1136 | msm_gem_unlock(obj); | ||
| 1132 | if (IS_ERR(pages)) { | 1137 | if (IS_ERR(pages)) { |
| 1133 | ret = PTR_ERR(pages); | 1138 | ret = PTR_ERR(pages); |
| 1134 | goto fail; | 1139 | goto fail; |
| @@ -37,6 +37,7 @@ nouveau-y += dispnv50/wimmc37b.o · 36 unmodified lines | |||
| 37 | nouveau-y += dispnv50/wndw.o | 37 | nouveau-y += dispnv50/wndw.o |
| 38 | nouveau-y += dispnv50/wndwc37e.o | 38 | nouveau-y += dispnv50/wndwc37e.o |
| 39 | nouveau-y += dispnv50/wndwc57e.o | 39 | nouveau-y += dispnv50/wndwc57e.o |
| 40 | nouveau-y += dispnv50/wndwc67e.o | ||
| 40 | 41 | ||
| 41 | nouveau-y += dispnv50/base.o | 42 | nouveau-y += dispnv50/base.o |
| 42 | nouveau-y += dispnv50/base507c.o | 43 | nouveau-y += dispnv50/base507c.o |
| @@ -88,7 +88,11 @@ base507c_image_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) · 87 unmodified lines | |||
| 88 | NVVAL(NV507C, SET_CONVERSION, OFS, 0x64)); | 88 | NVVAL(NV507C, SET_CONVERSION, OFS, 0x64)); |
| 89 | } else { | 89 | } else { |
| 90 | PUSH_MTHD(push, NV507C, SET_PROCESSING, | 90 | PUSH_MTHD(push, NV507C, SET_PROCESSING, |
| 91 | NVDEF(NV507C, SET_PROCESSING, USE_GAIN_OFS, DISABLE)); | 91 | NVDEF(NV507C, SET_PROCESSING, USE_GAIN_OFS, DISABLE), |
| 92 | |||
| 93 | SET_CONVERSION, | ||
| 94 | NVVAL(NV507C, SET_CONVERSION, GAIN, 0) | | ||
| 95 | NVVAL(NV507C, SET_CONVERSION, OFS, 0)); | ||
| 92 | } | 96 | } |
| 93 | 97 | ||
| 94 | PUSH_MTHD(push, NV507C, SURFACE_SET_OFFSET(0, 0), asyw->image.offset[0] >> 8); | 98 | PUSH_MTHD(push, NV507C, SURFACE_SET_OFFSET(0, 0), asyw->image.offset[0] >> 8); |
| @@ -49,7 +49,11 @@ base827c_image_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) · 48 unmodified lines | |||
| 49 | NVVAL(NV827C, SET_CONVERSION, OFS, 0x64)); | 49 | NVVAL(NV827C, SET_CONVERSION, OFS, 0x64)); |
| 50 | } else { | 50 | } else { |
| 51 | PUSH_MTHD(push, NV827C, SET_PROCESSING, | 51 | PUSH_MTHD(push, NV827C, SET_PROCESSING, |
| 52 | NVDEF(NV827C, SET_PROCESSING, USE_GAIN_OFS, DISABLE)); | 52 | NVDEF(NV827C, SET_PROCESSING, USE_GAIN_OFS, DISABLE), |
| 53 | |||
| 54 | SET_CONVERSION, | ||
| 55 | NVVAL(NV827C, SET_CONVERSION, GAIN, 0) | | ||
| 56 | NVVAL(NV827C, SET_CONVERSION, OFS, 0)); | ||
| 53 | } | 57 | } |
| 54 | 58 | ||
| 55 | PUSH_MTHD(push, NV827C, SURFACE_SET_OFFSET(0, 0), asyw->image.offset[0] >> 8, | 59 | PUSH_MTHD(push, NV827C, SURFACE_SET_OFFSET(0, 0), asyw->image.offset[0] >> 8, |
| @@ -42,6 +42,7 @@ nv50_core_new(struct nouveau_drm *drm, struct nv50_core **pcore) · 41 unmodified lines | |||
| 42 | int version; | 42 | int version; |
| 43 | int (*new)(struct nouveau_drm *, s32, struct nv50_core **); | 43 | int (*new)(struct nouveau_drm *, s32, struct nv50_core **); |
| 44 | } cores[] = { | 44 | } cores[] = { |
| 45 | { GA102_DISP_CORE_CHANNEL_DMA, 0, corec57d_new }, | ||
| 45 | { TU102_DISP_CORE_CHANNEL_DMA, 0, corec57d_new }, | 46 | { TU102_DISP_CORE_CHANNEL_DMA, 0, corec57d_new }, |
| 46 | { GV100_DISP_CORE_CHANNEL_DMA, 0, corec37d_new }, | 47 | { GV100_DISP_CORE_CHANNEL_DMA, 0, corec37d_new }, |
| 47 | { GP102_DISP_CORE_CHANNEL_DMA, 0, core917d_new }, | 48 | { GP102_DISP_CORE_CHANNEL_DMA, 0, core917d_new }, |
| @@ -31,6 +31,7 @@ nv50_curs_new(struct nouveau_drm *drm, int head, struct nv50_wndw **pwndw) · 30 unmodified lines | |||
| 31 | int version; | 31 | int version; |
| 32 | int (*new)(struct nouveau_drm *, int, s32, struct nv50_wndw **); | 32 | int (*new)(struct nouveau_drm *, int, s32, struct nv50_wndw **); |
| 33 | } curses[] = { | 33 | } curses[] = { |
| 34 | { GA102_DISP_CURSOR, 0, cursc37a_new }, | ||
| 34 | { TU102_DISP_CURSOR, 0, cursc37a_new }, | 35 | { TU102_DISP_CURSOR, 0, cursc37a_new }, |
| 35 | { GV100_DISP_CURSOR, 0, cursc37a_new }, | 36 | { GV100_DISP_CURSOR, 0, cursc37a_new }, |
| 36 | { GK104_DISP_CURSOR, 0, curs907a_new }, | 37 | { GK104_DISP_CURSOR, 0, curs907a_new }, |
| @@ -222,7 +222,7 @@ nv50_dmac_wait(struct nvif_push *push, u32 size) · 221 unmodified lines | |||
| 222 | 222 | ||
| 223 | int | 223 | int |
| 224 | nv50_dmac_create(struct nvif_device *device, struct nvif_object *disp, | 224 | nv50_dmac_create(struct nvif_device *device, struct nvif_object *disp, |
| 225 | const s32 *oclass, u8 head, void *data, u32 size, u64 syncbuf, | 225 | const s32 *oclass, u8 head, void *data, u32 size, s64 syncbuf, |
| 226 | struct nv50_dmac *dmac) | 226 | struct nv50_dmac *dmac) |
| 227 | { | 227 | { |
| 228 | struct nouveau_cli *cli = (void *)device->object.client; | 228 | struct nouveau_cli *cli = (void *)device->object.client; |
| @@ -271,7 +271,7 @@ nv50_dmac_create(struct nvif_device *device, struct nvif_object *disp, · 42 unmodified lines | |||
| 271 | if (ret) | 271 | if (ret) |
| 272 | return ret; | 272 | return ret; |
| 273 | 273 | ||
| 274 | if (!syncbuf) | 274 | if (syncbuf < 0) |
| 275 | return 0; | 275 | return 0; |
| 276 | 276 | ||
| 277 | ret = nvif_object_ctor(&dmac->base.user, "kmsSyncCtxDma", NV50_DISP_HANDLE_SYNCBUF, | 277 | ret = nvif_object_ctor(&dmac->base.user, "kmsSyncCtxDma", NV50_DISP_HANDLE_SYNCBUF, |
| @@ -2663,6 +2663,14 @@ nv50_display_create(struct drm_device *dev) · 2385 unmodified lines | |||
| 2663 | else | 2663 | else |
| 2664 | nouveau_display(dev)->format_modifiers = disp50xx_modifiers; | 2664 | nouveau_display(dev)->format_modifiers = disp50xx_modifiers; |
| 2665 | 2665 | ||
| 2666 | if (disp->disp->object.oclass >= GK104_DISP) { | ||
| 2667 | dev->mode_config.cursor_width = 256; | ||
| 2668 | dev->mode_config.cursor_height = 256; | ||
| 2669 | } else { | ||
| 2670 | dev->mode_config.cursor_width = 64; | ||
| 2671 | dev->mode_config.cursor_height = 64; | ||
| 2672 | } | ||
| 2673 | |||
| 2666 | /* create crtc objects to represent the hw heads */ | 2674 | /* create crtc objects to represent the hw heads */ |
| 2667 | if (disp->disp->object.oclass >= GV100_DISP) | 2675 | if (disp->disp->object.oclass >= GV100_DISP) |
| 2668 | crtcs = nvif_rd32(&device->object, 0x610060) & 0xff; | 2676 | crtcs = nvif_rd32(&device->object, 0x610060) & 0xff; |
| @@ -95,7 +95,7 @@ struct nv50_outp_atom { · 94 unmodified lines | |||
| 95 | 95 | ||
| 96 | int nv50_dmac_create(struct nvif_device *device, struct nvif_object *disp, | 96 | int nv50_dmac_create(struct nvif_device *device, struct nvif_object *disp, |
| 97 | const s32 *oclass, u8 head, void *data, u32 size, | 97 | const s32 *oclass, u8 head, void *data, u32 size, |
| 98 | u64 syncbuf, struct nv50_dmac *dmac); | 98 | s64 syncbuf, struct nv50_dmac *dmac); |
| 99 | void nv50_dmac_destroy(struct nv50_dmac *); | 99 | void nv50_dmac_destroy(struct nv50_dmac *); |
| 100 | 100 | ||
| 101 | /* | 101 | /* |
| @@ -22,6 +22,7 @@ · 21 unmodified lines | |||
| 22 | #include "head.h" | 22 | #include "head.h" |
| 23 | #include "core.h" | 23 | #include "core.h" |
| 24 | 24 | ||
| 25 | #include "nvif/push.h" | ||
| 25 | #include <nvif/push507c.h> | 26 | #include <nvif/push507c.h> |
| 26 | 27 | ||
| 27 | #include <nvhw/class/cl917d.h> | 28 | #include <nvhw/class/cl917d.h> |
| @@ -73,6 +74,31 @@ head917d_base(struct nv50_head *head, struct nv50_head_atom *asyh) · 45 unmodified lines | |||
| 73 | return 0; | 74 | return 0; |
| 74 | } | 75 | } |
| 75 | 76 | ||
| 77 | static int | ||
| 78 | head917d_curs_set(struct nv50_head *head, struct nv50_head_atom *asyh) | ||
| 79 | { | ||
| 80 | struct nvif_push *push = nv50_disp(head->base.base.dev)->core->chan.push; | ||
| 81 | const int i = head->base.index; | ||
| 82 | int ret; | ||
| 83 | |||
| 84 | ret = PUSH_WAIT(push, 5); | ||
| 85 | if (ret) | ||
| 86 | return ret; | ||
| 87 | |||
| 88 | PUSH_MTHD(push, NV917D, HEAD_SET_CONTROL_CURSOR(i), | ||
| 89 | NVDEF(NV917D, HEAD_SET_CONTROL_CURSOR, ENABLE, ENABLE) | | ||
| 90 | NVVAL(NV917D, HEAD_SET_CONTROL_CURSOR, FORMAT, asyh->curs.format) | | ||
| 91 | NVVAL(NV917D, HEAD_SET_CONTROL_CURSOR, SIZE, asyh->curs.layout) | | ||
| 92 | NVVAL(NV917D, HEAD_SET_CONTROL_CURSOR, HOT_SPOT_X, 0) | | ||
| 93 | NVVAL(NV917D, HEAD_SET_CONTROL_CURSOR, HOT_SPOT_Y, 0) | | ||
| 94 | NVDEF(NV917D, HEAD_SET_CONTROL_CURSOR, COMPOSITION, ALPHA_BLEND), | ||
| 95 | |||
| 96 | HEAD_SET_OFFSET_CURSOR(i), asyh->curs.offset >> 8); | ||
| 97 | |||
| 98 | PUSH_MTHD(push, NV917D, HEAD_SET_CONTEXT_DMA_CURSOR(i), asyh->curs.handle); | ||
| 99 | return 0; | ||
| 100 | } | ||
| 101 | |||
| 76 | int | 102 | int |
| 77 | head917d_curs_layout(struct nv50_head *head, struct nv50_wndw_atom *asyw, | 103 | head917d_curs_layout(struct nv50_head *head, struct nv50_wndw_atom *asyw, |
| 78 | struct nv50_head_atom *asyh) | 104 | struct nv50_head_atom *asyh) |
| @@ -101,7 +127,7 @@ head917d = { · 22 unmodified lines | |||
| 101 | .core_clr = head907d_core_clr, | 127 | .core_clr = head907d_core_clr, |
| 102 | .curs_layout = head917d_curs_layout, | 128 | .curs_layout = head917d_curs_layout, |
| 103 | .curs_format = head507d_curs_format, | 129 | .curs_format = head507d_curs_format, |
| 104 | .curs_set = head907d_curs_set, | 130 | .curs_set = head917d_curs_set, |
| 105 | .curs_clr = head907d_curs_clr, | 131 | .curs_clr = head907d_curs_clr, |
| 106 | .base = head917d_base, | 132 | .base = head917d_base, |
| 107 | .ovly = head907d_ovly, | 133 | .ovly = head907d_ovly, |
| @@ -31,6 +31,7 @@ nv50_wimm_init(struct nouveau_drm *drm, struct nv50_wndw *wndw) · 30 unmodified lines | |||
| 31 | int version; | 31 | int version; |
| 32 | int (*init)(struct nouveau_drm *, s32, struct nv50_wndw *); | 32 | int (*init)(struct nouveau_drm *, s32, struct nv50_wndw *); |
| 33 | } wimms[] = { | 33 | } wimms[] = { |
| 34 | { GA102_DISP_WINDOW_IMM_CHANNEL_DMA, 0, wimmc37b_init }, | ||
| 34 | { TU102_DISP_WINDOW_IMM_CHANNEL_DMA, 0, wimmc37b_init }, | 35 | { TU102_DISP_WINDOW_IMM_CHANNEL_DMA, 0, wimmc37b_init }, |
| 35 | { GV100_DISP_WINDOW_IMM_CHANNEL_DMA, 0, wimmc37b_init }, | 36 | { GV100_DISP_WINDOW_IMM_CHANNEL_DMA, 0, wimmc37b_init }, |
| 36 | {} | 37 | {} |
| @@ -76,7 +76,7 @@ wimmc37b_init_(const struct nv50_wimm_func *func, struct nouveau_drm *drm, · 75 unmodified lines | |||
| 76 | int ret; | 76 | int ret; |
| 77 | 77 | ||
| 78 | ret = nv50_dmac_create(&drm->client.device, &disp->disp->object, | 78 | ret = nv50_dmac_create(&drm->client.device, &disp->disp->object, |
| 79 | &oclass, 0, &args, sizeof(args), 0, | 79 | &oclass, 0, &args, sizeof(args), -1, |
| 80 | &wndw->wimm); | 80 | &wndw->wimm); |
| 81 | if (ret) { | 81 | if (ret) { |
| 82 | NV_ERROR(drm, "wimm%04x allocation failed: %d\n", oclass, ret); | 82 | NV_ERROR(drm, "wimm%04x allocation failed: %d\n", oclass, ret); |
| @@ -702,6 +702,11 @@ nv50_wndw_init(struct nv50_wndw *wndw) · 701 unmodified lines | |||
| 702 | nvif_notify_get(&wndw->notify); | 702 | nvif_notify_get(&wndw->notify); |
| 703 | } | 703 | } |
| 704 | 704 | ||
| 705 | static const u64 nv50_cursor_format_modifiers[] = { | ||
| 706 | DRM_FORMAT_MOD_LINEAR, | ||
| 707 | DRM_FORMAT_MOD_INVALID, | ||
| 708 | }; | ||
| 709 | |||
| 705 | int | 710 | int |
| 706 | nv50_wndw_new_(const struct nv50_wndw_func *func, struct drm_device *dev, | 711 | nv50_wndw_new_(const struct nv50_wndw_func *func, struct drm_device *dev, |
| 707 | enum drm_plane_type type, const char *name, int index, | 712 | enum drm_plane_type type, const char *name, int index, |
| @@ -713,6 +718,7 @@ nv50_wndw_new_(const struct nv50_wndw_func *func, struct drm_device *dev, · 5 unmodified lines | |||
| 713 | struct nvif_mmu *mmu = &drm->client.mmu; | 718 | struct nvif_mmu *mmu = &drm->client.mmu; |
| 714 | struct nv50_disp *disp = nv50_disp(dev); | 719 | struct nv50_disp *disp = nv50_disp(dev); |
| 715 | struct nv50_wndw *wndw; | 720 | struct nv50_wndw *wndw; |
| 721 | const u64 *format_modifiers; | ||
| 716 | int nformat; | 722 | int nformat; |
| 717 | int ret; | 723 | int ret; |
| 718 | 724 | ||
| @@ -728,10 +734,13 @@ nv50_wndw_new_(const struct nv50_wndw_func *func, struct drm_device *dev, · 9 unmodified lines | |||
| 728 | 734 | ||
| 729 | for (nformat = 0; format[nformat]; nformat++); | 735 | for (nformat = 0; format[nformat]; nformat++); |
| 730 | 736 | ||
| 731 | ret = drm_universal_plane_init(dev, &wndw->plane, heads, &nv50_wndw, | 737 | if (type == DRM_PLANE_TYPE_CURSOR) |
| 732 | format, nformat, | 738 | format_modifiers = nv50_cursor_format_modifiers; |
| 733 | nouveau_display(dev)->format_modifiers, | 739 | else |
| 734 | type, "%s-%d", name, index); | 740 | format_modifiers = nouveau_display(dev)->format_modifiers; |
| 741 | |||
| 742 | ret = drm_universal_plane_init(dev, &wndw->plane, heads, &nv50_wndw, format, nformat, | ||
| 743 | format_modifiers, type, "%s-%d", name, index); | ||
| 735 | if (ret) { | 744 | if (ret) { |
| 736 | kfree(*pwndw); | 745 | kfree(*pwndw); |
| 737 | *pwndw = NULL; | 746 | *pwndw = NULL; |
| @@ -784,6 +793,7 @@ nv50_wndw_new(struct nouveau_drm *drm, enum drm_plane_type type, int index, · 46 unmodified lines | |||
| 784 | int (*new)(struct nouveau_drm *, enum drm_plane_type, | 793 | int (*new)(struct nouveau_drm *, enum drm_plane_type, |
| 785 | int, s32, struct nv50_wndw **); | 794 | int, s32, struct nv50_wndw **); |
| 786 | } wndws[] = { | 795 | } wndws[] = { |
| 796 | { GA102_DISP_WINDOW_CHANNEL_DMA, 0, wndwc67e_new }, | ||
| 787 | { TU102_DISP_WINDOW_CHANNEL_DMA, 0, wndwc57e_new }, | 797 | { TU102_DISP_WINDOW_CHANNEL_DMA, 0, wndwc57e_new }, |
| 788 | { GV100_DISP_WINDOW_CHANNEL_DMA, 0, wndwc37e_new }, | 798 | { GV100_DISP_WINDOW_CHANNEL_DMA, 0, wndwc37e_new }, |
| 789 | {} | 799 | {} |
| @@ -129,6 +129,14 @@ int wndwc37e_update(struct nv50_wndw *, u32 *); · 128 unmodified lines | |||
| 129 | 129 | ||
| 130 | int wndwc57e_new(struct nouveau_drm *, enum drm_plane_type, int, s32, | 130 | int wndwc57e_new(struct nouveau_drm *, enum drm_plane_type, int, s32, |
| 131 | struct nv50_wndw **); | 131 | struct nv50_wndw **); |
| 132 | bool wndwc57e_ilut(struct nv50_wndw *, struct nv50_wndw_atom *, int); | ||
| 133 | int wndwc57e_ilut_set(struct nv50_wndw *, struct nv50_wndw_atom *); | ||
| 134 | int wndwc57e_ilut_clr(struct nv50_wndw *); | ||
| 135 | int wndwc57e_csc_set(struct nv50_wndw *, struct nv50_wndw_atom *); | ||
| 136 | int wndwc57e_csc_clr(struct nv50_wndw *); | ||
| 137 | |||
| 138 | int wndwc67e_new(struct nouveau_drm *, enum drm_plane_type, int, s32, | ||
| 139 | struct nv50_wndw **); | ||
| 132 | 140 | ||
| 133 | int nv50_wndw_new(struct nouveau_drm *, enum drm_plane_type, int index, | 141 | int nv50_wndw_new(struct nouveau_drm *, enum drm_plane_type, int index, |
| 134 | struct nv50_wndw **); | 142 | struct nv50_wndw **); |
| @@ -80,7 +80,7 @@ wndwc57e_image_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) · 79 unmodified lines | |||
| 80 | return 0; | 80 | return 0; |
| 81 | } | 81 | } |
| 82 | 82 | ||
| 83 | static int | 83 | int |
| 84 | wndwc57e_csc_clr(struct nv50_wndw *wndw) | 84 | wndwc57e_csc_clr(struct nv50_wndw *wndw) |
| 85 | { | 85 | { |
| 86 | struct nvif_push *push = wndw->wndw.push; | 86 | struct nvif_push *push = wndw->wndw.push; |
| @@ -98,7 +98,7 @@ wndwc57e_csc_clr(struct nv50_wndw *wndw) · 11 unmodified lines | |||
| 98 | return 0; | 98 | return 0; |
| 99 | } | 99 | } |
| 100 | 100 | ||
| 101 | static int | 101 | int |
| 102 | wndwc57e_csc_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) | 102 | wndwc57e_csc_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) |
| 103 | { | 103 | { |
| 104 | struct nvif_push *push = wndw->wndw.push; | 104 | struct nvif_push *push = wndw->wndw.push; |
| @@ -111,7 +111,7 @@ wndwc57e_csc_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) · 6 unmodified lines | |||
| 111 | return 0; | 111 | return 0; |
| 112 | } | 112 | } |
| 113 | 113 | ||
| 114 | static int | 114 | int |
| 115 | wndwc57e_ilut_clr(struct nv50_wndw *wndw) | 115 | wndwc57e_ilut_clr(struct nv50_wndw *wndw) |
| 116 | { | 116 | { |
| 117 | struct nvif_push *push = wndw->wndw.push; | 117 | struct nvif_push *push = wndw->wndw.push; |
| @@ -124,7 +124,7 @@ wndwc57e_ilut_clr(struct nv50_wndw *wndw) · 6 unmodified lines | |||
| 124 | return 0; | 124 | return 0; |
| 125 | } | 125 | } |
| 126 | 126 | ||
| 127 | static int | 127 | int |
| 128 | wndwc57e_ilut_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) | 128 | wndwc57e_ilut_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) |
| 129 | { | 129 | { |
| 130 | struct nvif_push *push = wndw->wndw.push; | 130 | struct nvif_push *push = wndw->wndw.push; |
| @@ -179,7 +179,7 @@ wndwc57e_ilut_load(struct drm_color_lut *in, int size, void __iomem *mem) · 48 unmodified lines | |||
| 179 | writew(readw(mem - 4), mem + 4); | 179 | writew(readw(mem - 4), mem + 4); |
| 180 | } | 180 | } |
| 181 | 181 | ||
| 182 | static bool | 182 | bool |
| 183 | wndwc57e_ilut(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw, int size) | 183 | wndwc57e_ilut(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw, int size) |
| 184 | { | 184 | { |
| 185 | if (size = size ? size : 1024, size != 256 && size != 1024) | 185 | if (size = size ? size : 1024, size != 256 && size != 1024) |
| @@ -0,0 +1,106 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "wndw.h" | ||
| 23 | #include "atom.h" | ||
| 24 | |||
| 25 | #include <nvif/pushc37b.h> | ||
| 26 | |||
| 27 | #include <nvhw/class/clc57e.h> | ||
| 28 | |||
| 29 | static int | ||
| 30 | wndwc67e_image_set(struct nv50_wndw *wndw, struct nv50_wndw_atom *asyw) | ||
| 31 | { | ||
| 32 | struct nvif_push *push = wndw->wndw.push; | ||
| 33 | int ret; | ||
| 34 | |||
| 35 | if ((ret = PUSH_WAIT(push, 17))) | ||
| 36 | return ret; | ||
| 37 | |||
| 38 | PUSH_MTHD(push, NVC57E, SET_PRESENT_CONTROL, | ||
| 39 | NVVAL(NVC57E, SET_PRESENT_CONTROL, MIN_PRESENT_INTERVAL, asyw->image.interval) | | ||
| 40 | NVVAL(NVC57E, SET_PRESENT_CONTROL, BEGIN_MODE, asyw->image.mode) | | ||
| 41 | NVDEF(NVC57E, SET_PRESENT_CONTROL, TIMESTAMP_MODE, DISABLE)); | ||
| 42 | |||
| 43 | PUSH_MTHD(push, NVC57E, SET_SIZE, | ||
| 44 | NVVAL(NVC57E, SET_SIZE, WIDTH, asyw->image.w) | | ||
| 45 | NVVAL(NVC57E, SET_SIZE, HEIGHT, asyw->image.h), | ||
| 46 | |||
| 47 | SET_STORAGE, | ||
| 48 | NVVAL(NVC57E, SET_STORAGE, BLOCK_HEIGHT, asyw->image.blockh), | ||
| 49 | |||
| 50 | SET_PARAMS, | ||
| 51 | NVVAL(NVC57E, SET_PARAMS, FORMAT, asyw->image.format) | | ||
| 52 | NVDEF(NVC57E, SET_PARAMS, CLAMP_BEFORE_BLEND, DISABLE) | | ||
| 53 | NVDEF(NVC57E, SET_PARAMS, SWAP_UV, DISABLE) | | ||
| 54 | NVDEF(NVC57E, SET_PARAMS, FMT_ROUNDING_MODE, ROUND_TO_NEAREST), | ||
| 55 | |||
| 56 | SET_PLANAR_STORAGE(0), | ||
| 57 | NVVAL(NVC57E, SET_PLANAR_STORAGE, PITCH, asyw->image.blocks[0]) | | ||
| 58 | NVVAL(NVC57E, SET_PLANAR_STORAGE, PITCH, asyw->image.pitch[0] >> 6)); | ||
| 59 | |||
| 60 | PUSH_MTHD(push, NVC57E, SET_CONTEXT_DMA_ISO(0), asyw->image.handle, 1); | ||
| 61 | PUSH_MTHD(push, NVC57E, SET_OFFSET(0), asyw->image.offset[0] >> 8); | ||
| 62 | |||
| 63 | PUSH_MTHD(push, NVC57E, SET_POINT_IN(0), | ||
| 64 | NVVAL(NVC57E, SET_POINT_IN, X, asyw->state.src_x >> 16) | | ||
| 65 | NVVAL(NVC57E, SET_POINT_IN, Y, asyw->state.src_y >> 16)); | ||
| 66 | |||
| 67 | PUSH_MTHD(push, NVC57E, SET_SIZE_IN, | ||
| 68 | NVVAL(NVC57E, SET_SIZE_IN, WIDTH, asyw->state.src_w >> 16) | | ||
| 69 | NVVAL(NVC57E, SET_SIZE_IN, HEIGHT, asyw->state.src_h >> 16)); | ||
| 70 | |||
| 71 | PUSH_MTHD(push, NVC57E, SET_SIZE_OUT, | ||
| 72 | NVVAL(NVC57E, SET_SIZE_OUT, WIDTH, asyw->state.crtc_w) | | ||
| 73 | NVVAL(NVC57E, SET_SIZE_OUT, HEIGHT, asyw->state.crtc_h)); | ||
| 74 | return 0; | ||
| 75 | } | ||
| 76 | |||
| 77 | static const struct nv50_wndw_func | ||
| 78 | wndwc67e = { | ||
| 79 | .acquire = wndwc37e_acquire, | ||
| 80 | .release = wndwc37e_release, | ||
| 81 | .sema_set = wndwc37e_sema_set, | ||
| 82 | .sema_clr = wndwc37e_sema_clr, | ||
| 83 | .ntfy_set = wndwc37e_ntfy_set, | ||
| 84 | .ntfy_clr = wndwc37e_ntfy_clr, | ||
| 85 | .ntfy_reset = corec37d_ntfy_init, | ||
| 86 | .ntfy_wait_begun = base507c_ntfy_wait_begun, | ||
| 87 | .ilut = wndwc57e_ilut, | ||
| 88 | .ilut_identity = true, | ||
| 89 | .ilut_size = 1024, | ||
| 90 | .xlut_set = wndwc57e_ilut_set, | ||
| 91 | .xlut_clr = wndwc57e_ilut_clr, | ||
| 92 | .csc = base907c_csc, | ||
| 93 | .csc_set = wndwc57e_csc_set, | ||
| 94 | .csc_clr = wndwc57e_csc_clr, | ||
| 95 | .image_set = wndwc67e_image_set, | ||
| 96 | .image_clr = wndwc37e_image_clr, | ||
| 97 | .blend_set = wndwc37e_blend_set, | ||
| 98 | .update = wndwc37e_update, | ||
| 99 | }; | ||
| 100 | |||
| 101 | int | ||
| 102 | wndwc67e_new(struct nouveau_drm *drm, enum drm_plane_type type, int index, | ||
| 103 | s32 oclass, struct nv50_wndw **pwndw) | ||
| 104 | { | ||
| 105 | return wndwc37e_new_(&wndwc67e, drm, type, index, oclass, BIT(index >> 1), pwndw); | ||
| 106 | } | ||
| @@ -66,6 +66,10 @@ · 65 unmodified lines | |||
| 66 | #define NV917D_HEAD_SET_CONTROL_CURSOR_COMPOSITION_ALPHA_BLEND (0x00000000) | 66 | #define NV917D_HEAD_SET_CONTROL_CURSOR_COMPOSITION_ALPHA_BLEND (0x00000000) |
| 67 | #define NV917D_HEAD_SET_CONTROL_CURSOR_COMPOSITION_PREMULT_ALPHA_BLEND (0x00000001) | 67 | #define NV917D_HEAD_SET_CONTROL_CURSOR_COMPOSITION_PREMULT_ALPHA_BLEND (0x00000001) |
| 68 | #define NV917D_HEAD_SET_CONTROL_CURSOR_COMPOSITION_XOR (0x00000002) | 68 | #define NV917D_HEAD_SET_CONTROL_CURSOR_COMPOSITION_XOR (0x00000002) |
| 69 | #define NV917D_HEAD_SET_OFFSET_CURSOR(a) (0x00000484 + (a)*0x00000300) | ||
| 70 | #define NV917D_HEAD_SET_OFFSET_CURSOR_ORIGIN 31:0 | ||
| 71 | #define NV917D_HEAD_SET_CONTEXT_DMA_CURSOR(a) (0x0000048C + (a)*0x00000300) | ||
| 72 | #define NV917D_HEAD_SET_CONTEXT_DMA_CURSOR_HANDLE 31:0 | ||
| 69 | #define NV917D_HEAD_SET_DITHER_CONTROL(a) (0x000004A0 + (a)*0x00000300) | 73 | #define NV917D_HEAD_SET_DITHER_CONTROL(a) (0x000004A0 + (a)*0x00000300) |
| 70 | #define NV917D_HEAD_SET_DITHER_CONTROL_ENABLE 0:0 | 74 | #define NV917D_HEAD_SET_DITHER_CONTROL_ENABLE 0:0 |
| 71 | #define NV917D_HEAD_SET_DITHER_CONTROL_ENABLE_DISABLE (0x00000000) | 75 | #define NV917D_HEAD_SET_DITHER_CONTROL_ENABLE_DISABLE (0x00000000) |
| @@ -33,6 +33,7 @@ struct nv_device_info_v0 { · 32 unmodified lines | |||
| 33 | #define NV_DEVICE_INFO_V0_PASCAL 0x0a | 33 | #define NV_DEVICE_INFO_V0_PASCAL 0x0a |
| 34 | #define NV_DEVICE_INFO_V0_VOLTA 0x0b | 34 | #define NV_DEVICE_INFO_V0_VOLTA 0x0b |
| 35 | #define NV_DEVICE_INFO_V0_TURING 0x0c | 35 | #define NV_DEVICE_INFO_V0_TURING 0x0c |
| 36 | #define NV_DEVICE_INFO_V0_AMPERE 0x0d | ||
| 36 | __u8 family; | 37 | __u8 family; |
| 37 | __u8 pad06[2]; | 38 | __u8 pad06[2]; |
| 38 | __u64 ram_size; | 39 | __u64 ram_size; |
| @@ -88,6 +88,7 @@ · 87 unmodified lines | |||
| 88 | #define GP102_DISP /* cl5070.h */ 0x00009870 | 88 | #define GP102_DISP /* cl5070.h */ 0x00009870 |
| 89 | #define GV100_DISP /* cl5070.h */ 0x0000c370 | 89 | #define GV100_DISP /* cl5070.h */ 0x0000c370 |
| 90 | #define TU102_DISP /* cl5070.h */ 0x0000c570 | 90 | #define TU102_DISP /* cl5070.h */ 0x0000c570 |
| 91 | #define GA102_DISP /* cl5070.h */ 0x0000c670 | ||
| 91 | 92 | ||
| 92 | #define GV100_DISP_CAPS 0x0000c373 | 93 | #define GV100_DISP_CAPS 0x0000c373 |
| 93 | 94 | ||
| @@ -103,6 +104,7 @@ · 9 unmodified lines | |||
| 103 | #define GK104_DISP_CURSOR /* cl507a.h */ 0x0000917a | 104 | #define GK104_DISP_CURSOR /* cl507a.h */ 0x0000917a |
| 104 | #define GV100_DISP_CURSOR /* cl507a.h */ 0x0000c37a | 105 | #define GV100_DISP_CURSOR /* cl507a.h */ 0x0000c37a |
| 105 | #define TU102_DISP_CURSOR /* cl507a.h */ 0x0000c57a | 106 | #define TU102_DISP_CURSOR /* cl507a.h */ 0x0000c57a |
| 107 | #define GA102_DISP_CURSOR /* cl507a.h */ 0x0000c67a | ||
| 106 | 108 | ||
| 107 | #define NV50_DISP_OVERLAY /* cl507b.h */ 0x0000507b | 109 | #define NV50_DISP_OVERLAY /* cl507b.h */ 0x0000507b |
| 108 | #define G82_DISP_OVERLAY /* cl507b.h */ 0x0000827b | 110 | #define G82_DISP_OVERLAY /* cl507b.h */ 0x0000827b |
| @@ -112,6 +114,7 @@ · 3 unmodified lines | |||
| 112 | 114 | ||
| 113 | #define GV100_DISP_WINDOW_IMM_CHANNEL_DMA /* clc37b.h */ 0x0000c37b | 115 | #define GV100_DISP_WINDOW_IMM_CHANNEL_DMA /* clc37b.h */ 0x0000c37b |
| 114 | #define TU102_DISP_WINDOW_IMM_CHANNEL_DMA /* clc37b.h */ 0x0000c57b | 116 | #define TU102_DISP_WINDOW_IMM_CHANNEL_DMA /* clc37b.h */ 0x0000c57b |
| 117 | #define GA102_DISP_WINDOW_IMM_CHANNEL_DMA /* clc37b.h */ 0x0000c67b | ||
| 115 | 118 | ||
| 116 | #define NV50_DISP_BASE_CHANNEL_DMA /* cl507c.h */ 0x0000507c | 119 | #define NV50_DISP_BASE_CHANNEL_DMA /* cl507c.h */ 0x0000507c |
| 117 | #define G82_DISP_BASE_CHANNEL_DMA /* cl507c.h */ 0x0000827c | 120 | #define G82_DISP_BASE_CHANNEL_DMA /* cl507c.h */ 0x0000827c |
| @@ -135,6 +138,7 @@ · 17 unmodified lines | |||
| 135 | #define GP102_DISP_CORE_CHANNEL_DMA /* cl507d.h */ 0x0000987d | 138 | #define GP102_DISP_CORE_CHANNEL_DMA /* cl507d.h */ 0x0000987d |
| 136 | #define GV100_DISP_CORE_CHANNEL_DMA /* cl507d.h */ 0x0000c37d | 139 | #define GV100_DISP_CORE_CHANNEL_DMA /* cl507d.h */ 0x0000c37d |
| 137 | #define TU102_DISP_CORE_CHANNEL_DMA /* cl507d.h */ 0x0000c57d | 140 | #define TU102_DISP_CORE_CHANNEL_DMA /* cl507d.h */ 0x0000c57d |
| 141 | #define GA102_DISP_CORE_CHANNEL_DMA /* cl507d.h */ 0x0000c67d | ||
| 138 | 142 | ||
| 139 | #define NV50_DISP_OVERLAY_CHANNEL_DMA /* cl507e.h */ 0x0000507e | 143 | #define NV50_DISP_OVERLAY_CHANNEL_DMA /* cl507e.h */ 0x0000507e |
| 140 | #define G82_DISP_OVERLAY_CHANNEL_DMA /* cl507e.h */ 0x0000827e | 144 | #define G82_DISP_OVERLAY_CHANNEL_DMA /* cl507e.h */ 0x0000827e |
| @@ -145,6 +149,7 @@ · 4 unmodified lines | |||
| 145 | 149 | ||
| 146 | #define GV100_DISP_WINDOW_CHANNEL_DMA /* clc37e.h */ 0x0000c37e | 150 | #define GV100_DISP_WINDOW_CHANNEL_DMA /* clc37e.h */ 0x0000c37e |
| 147 | #define TU102_DISP_WINDOW_CHANNEL_DMA /* clc37e.h */ 0x0000c57e | 151 | #define TU102_DISP_WINDOW_CHANNEL_DMA /* clc37e.h */ 0x0000c57e |
| 152 | #define GA102_DISP_WINDOW_CHANNEL_DMA /* clc37e.h */ 0x0000c67e | ||
| 148 | 153 | ||
| 149 | #define NV50_TESLA 0x00005097 | 154 | #define NV50_TESLA 0x00005097 |
| 150 | #define G82_TESLA 0x00008297 | 155 | #define G82_TESLA 0x00008297 |
| @@ -123,131 +123,131 @@ PUSH_KICK(struct nvif_push *push) · 122 unmodified lines | |||
| 123 | } while(0) | 123 | } while(0) |
| 124 | #endif | 124 | #endif |
| 125 | 125 | ||
| 126 | #define PUSH_1(X,f,ds,n,c,o,p,s,mA,dA) do { \ | 126 | #define PUSH_1(X,f,ds,n,o,p,s,mA,dA) do { \ |
| 127 | PUSH_##o##_HDR((p), s, mA, (c)+(n)); \ | 127 | PUSH_##o##_HDR((p), s, mA, (ds)+(n)); \ |
| 128 | PUSH_##f(X, (p), X##mA, 1, o, (dA), ds, ""); \ | 128 | PUSH_##f(X, (p), X##mA, 1, o, (dA), ds, ""); \ |
| 129 | } while(0) | 129 | } while(0) |
| 130 | #define PUSH_2(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 130 | #define PUSH_2(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 131 | PUSH_ASSERT((mB) - (mA) == (1?PUSH_##o##_INC), "mthd1"); \ | 131 | PUSH_ASSERT((mB) - (mA) == (1?PUSH_##o##_INC), "mthd1"); \ |
| 132 | PUSH_1(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 132 | PUSH_1(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 133 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 133 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 134 | } while(0) | 134 | } while(0) |
| 135 | #define PUSH_3(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 135 | #define PUSH_3(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 136 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd2"); \ | 136 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd2"); \ |
| 137 | PUSH_2(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 137 | PUSH_2(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 138 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 138 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 139 | } while(0) | 139 | } while(0) |
| 140 | #define PUSH_4(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 140 | #define PUSH_4(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 141 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd3"); \ | 141 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd3"); \ |
| 142 | PUSH_3(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 142 | PUSH_3(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 143 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 143 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 144 | } while(0) | 144 | } while(0) |
| 145 | #define PUSH_5(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 145 | #define PUSH_5(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 146 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd4"); \ | 146 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd4"); \ |
| 147 | PUSH_4(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 147 | PUSH_4(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 148 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 148 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 149 | } while(0) | 149 | } while(0) |
| 150 | #define PUSH_6(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 150 | #define PUSH_6(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 151 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd5"); \ | 151 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd5"); \ |
| 152 | PUSH_5(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 152 | PUSH_5(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 153 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 153 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 154 | } while(0) | 154 | } while(0) |
| 155 | #define PUSH_7(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 155 | #define PUSH_7(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 156 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd6"); \ | 156 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd6"); \ |
| 157 | PUSH_6(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 157 | PUSH_6(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 158 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 158 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 159 | } while(0) | 159 | } while(0) |
| 160 | #define PUSH_8(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 160 | #define PUSH_8(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 161 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd7"); \ | 161 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd7"); \ |
| 162 | PUSH_7(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 162 | PUSH_7(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 163 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 163 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 164 | } while(0) | 164 | } while(0) |
| 165 | #define PUSH_9(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 165 | #define PUSH_9(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 166 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd8"); \ | 166 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd8"); \ |
| 167 | PUSH_8(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 167 | PUSH_8(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 168 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 168 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 169 | } while(0) | 169 | } while(0) |
| 170 | #define PUSH_10(X,f,ds,n,c,o,p,s,mB,dB,mA,dA,a...) do { \ | 170 | #define PUSH_10(X,f,ds,n,o,p,s,mB,dB,mA,dA,a...) do { \ |
| 171 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd9"); \ | 171 | PUSH_ASSERT((mB) - (mA) == (0?PUSH_##o##_INC), "mthd9"); \ |
| 172 | PUSH_9(X, DATA_, 1, ds, (c)+(n), o, (p), s, X##mA, (dA), ##a); \ | 172 | PUSH_9(X, DATA_, 1, (ds) + (n), o, (p), s, X##mA, (dA), ##a); \ |
| 173 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ | 173 | PUSH_##f(X, (p), X##mB, 0, o, (dB), ds, ""); \ |
| 174 | } while(0) | 174 | } while(0) |
| 175 | 175 | ||
| 176 | #define PUSH_1D(X,o,p,s,mA,dA) \ | 176 | #define PUSH_1D(X,o,p,s,mA,dA) \ |
| 177 | PUSH_1(X, DATA_, 1, 1, 0, o, (p), s, X##mA, (dA)) | 177 | PUSH_1(X, DATA_, 1, 0, o, (p), s, X##mA, (dA)) |
| 178 | #define PUSH_2D(X,o,p,s,mA,dA,mB,dB) \ | 178 | #define PUSH_2D(X,o,p,s,mA,dA,mB,dB) \ |
| 179 | PUSH_2(X, DATA_, 1, 1, 0, o, (p), s, X##mB, (dB), \ | 179 | PUSH_2(X, DATA_, 1, 0, o, (p), s, X##mB, (dB), \ |
| 180 | X##mA, (dA)) | 180 | X##mA, (dA)) |
| 181 | #define PUSH_3D(X,o,p,s,mA,dA,mB,dB,mC,dC) \ | 181 | #define PUSH_3D(X,o,p,s,mA,dA,mB,dB,mC,dC) \ |
| 182 | PUSH_3(X, DATA_, 1, 1, 0, o, (p), s, X##mC, (dC), \ | 182 | PUSH_3(X, DATA_, 1, 0, o, (p), s, X##mC, (dC), \ |
| 183 | X##mB, (dB), \ | 183 | X##mB, (dB), \ |
| 184 | X##mA, (dA)) | 184 | X##mA, (dA)) |
| 185 | #define PUSH_4D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD) \ | 185 | #define PUSH_4D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD) \ |
| 186 | PUSH_4(X, DATA_, 1, 1, 0, o, (p), s, X##mD, (dD), \ | 186 | PUSH_4(X, DATA_, 1, 0, o, (p), s, X##mD, (dD), \ |
| 187 | X##mC, (dC), \ | 187 | X##mC, (dC), \ |
| 188 | X##mB, (dB), \ | 188 | X##mB, (dB), \ |
| 189 | X##mA, (dA)) | 189 | X##mA, (dA)) |
| 190 | #define PUSH_5D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE) \ | 190 | #define PUSH_5D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE) \ |
| 191 | PUSH_5(X, DATA_, 1, 1, 0, o, (p), s, X##mE, (dE), \ | 191 | PUSH_5(X, DATA_, 1, 0, o, (p), s, X##mE, (dE), \ |
| 192 | X##mD, (dD), \ | 192 | X##mD, (dD), \ |
| 193 | X##mC, (dC), \ | 193 | X##mC, (dC), \ |
| 194 | X##mB, (dB), \ | 194 | X##mB, (dB), \ |
| 195 | X##mA, (dA)) | 195 | X##mA, (dA)) |
| 196 | #define PUSH_6D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF) \ | 196 | #define PUSH_6D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF) \ |
| 197 | PUSH_6(X, DATA_, 1, 1, 0, o, (p), s, X##mF, (dF), \ | 197 | PUSH_6(X, DATA_, 1, 0, o, (p), s, X##mF, (dF), \ |
| 198 | X##mE, (dE), \ | 198 | X##mE, (dE), \ |
| 199 | X##mD, (dD), \ | 199 | X##mD, (dD), \ |
| 200 | X##mC, (dC), \ | 200 | X##mC, (dC), \ |
| 201 | X##mB, (dB), \ | 201 | X##mB, (dB), \ |
| 202 | X##mA, (dA)) | 202 | X##mA, (dA)) |
| 203 | #define PUSH_7D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG) \ | 203 | #define PUSH_7D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG) \ |
| 204 | PUSH_7(X, DATA_, 1, 1, 0, o, (p), s, X##mG, (dG), \ | 204 | PUSH_7(X, DATA_, 1, 0, o, (p), s, X##mG, (dG), \ |
| 205 | X##mF, (dF), \ | 205 | X##mF, (dF), \ |
| 206 | X##mE, (dE), \ | 206 | X##mE, (dE), \ |
| 207 | X##mD, (dD), \ | 207 | X##mD, (dD), \ |
| 208 | X##mC, (dC), \ | 208 | X##mC, (dC), \ |
| 209 | X##mB, (dB), \ | 209 | X##mB, (dB), \ |
| 210 | X##mA, (dA)) | 210 | X##mA, (dA)) |
| 211 | #define PUSH_8D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG,mH,dH) \ | 211 | #define PUSH_8D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG,mH,dH) \ |
| 212 | PUSH_8(X, DATA_, 1, 1, 0, o, (p), s, X##mH, (dH), \ | 212 | PUSH_8(X, DATA_, 1, 0, o, (p), s, X##mH, (dH), \ |
| 213 | X##mG, (dG), \ | 213 | X##mG, (dG), \ |
| 214 | X##mF, (dF), \ | 214 | X##mF, (dF), \ |
| 215 | X##mE, (dE), \ | 215 | X##mE, (dE), \ |
| 216 | X##mD, (dD), \ | 216 | X##mD, (dD), \ |
| 217 | X##mC, (dC), \ | 217 | X##mC, (dC), \ |
| 218 | X##mB, (dB), \ | 218 | X##mB, (dB), \ |
| 219 | X##mA, (dA)) | 219 | X##mA, (dA)) |
| 220 | #define PUSH_9D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG,mH,dH,mI,dI) \ | 220 | #define PUSH_9D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG,mH,dH,mI,dI) \ |
| 221 | PUSH_9(X, DATA_, 1, 1, 0, o, (p), s, X##mI, (dI), \ | 221 | PUSH_9(X, DATA_, 1, 0, o, (p), s, X##mI, (dI), \ |
| 222 | X##mH, (dH), \ | 222 | X##mH, (dH), \ |
| 223 | X##mG, (dG), \ | 223 | X##mG, (dG), \ |
| 224 | X##mF, (dF), \ | 224 | X##mF, (dF), \ |
| 225 | X##mE, (dE), \ | 225 | X##mE, (dE), \ |
| 226 | X##mD, (dD), \ | 226 | X##mD, (dD), \ |
| 227 | X##mC, (dC), \ | 227 | X##mC, (dC), \ |
| 228 | X##mB, (dB), \ | 228 | X##mB, (dB), \ |
| 229 | X##mA, (dA)) | 229 | X##mA, (dA)) |
| 230 | #define PUSH_10D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG,mH,dH,mI,dI,mJ,dJ) \ | 230 | #define PUSH_10D(X,o,p,s,mA,dA,mB,dB,mC,dC,mD,dD,mE,dE,mF,dF,mG,dG,mH,dH,mI,dI,mJ,dJ) \ |
| 231 | PUSH_10(X, DATA_, 1, 1, 0, o, (p), s, X##mJ, (dJ), \ | 231 | PUSH_10(X, DATA_, 1, 0, o, (p), s, X##mJ, (dJ), \ |
| 232 | X##mI, (dI), \ | 232 | X##mI, (dI), \ |
| 233 | X##mH, (dH), \ | 233 | X##mH, (dH), \ |
| 234 | X##mG, (dG), \ | 234 | X##mG, (dG), \ |
| 235 | X##mF, (dF), \ | 235 | X##mF, (dF), \ |
| 236 | X##mE, (dE), \ | 236 | X##mE, (dE), \ |
| 237 | X##mD, (dD), \ | 237 | X##mD, (dD), \ |
| 238 | X##mC, (dC), \ | 238 | X##mC, (dC), \ |
| 239 | X##mB, (dB), \ | 239 | X##mB, (dB), \ |
| 240 | X##mA, (dA)) | 240 | X##mA, (dA)) |
| 241 | 241 | ||
| 242 | #define PUSH_1P(X,o,p,s,mA,dp,ds) \ | 242 | #define PUSH_1P(X,o,p,s,mA,dp,ds) \ |
| 243 | PUSH_1(X, DATAp, ds, ds, 0, o, (p), s, X##mA, (dp)) | 243 | PUSH_1(X, DATAp, ds, 0, o, (p), s, X##mA, (dp)) |
| 244 | #define PUSH_2P(X,o,p,s,mA,dA,mB,dp,ds) \ | 244 | #define PUSH_2P(X,o,p,s,mA,dA,mB,dp,ds) \ |
| 245 | PUSH_2(X, DATAp, ds, ds, 0, o, (p), s, X##mB, (dp), \ | 245 | PUSH_2(X, DATAp, ds, 0, o, (p), s, X##mB, (dp), \ |
| 246 | X##mA, (dA)) | 246 | X##mA, (dA)) |
| 247 | #define PUSH_3P(X,o,p,s,mA,dA,mB,dB,mC,dp,ds) \ | 247 | #define PUSH_3P(X,o,p,s,mA,dA,mB,dB,mC,dp,ds) \ |
| 248 | PUSH_3(X, DATAp, ds, ds, 0, o, (p), s, X##mC, (dp), \ | 248 | PUSH_3(X, DATAp, ds, 0, o, (p), s, X##mC, (dp), \ |
| 249 | X##mB, (dB), \ | 249 | X##mB, (dB), \ |
| 250 | X##mA, (dA)) | 250 | X##mA, (dA)) |
| 251 | 251 | ||
| 252 | #define PUSH_(A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,IMPL,...) IMPL | 252 | #define PUSH_(A,B,C,D,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,IMPL,...) IMPL |
| 253 | #define PUSH(A...) PUSH_(A, PUSH_10P, PUSH_10D, \ | 253 | #define PUSH(A...) PUSH_(A, PUSH_10P, PUSH_10D, \ |
| @@ -120,6 +120,7 @@ struct nvkm_device { · 119 unmodified lines | |||
| 120 | GP100 = 0x130, | 120 | GP100 = 0x130, |
| 121 | GV100 = 0x140, | 121 | GV100 = 0x140, |
| 122 | TU100 = 0x160, | 122 | TU100 = 0x160, |
| 123 | GA100 = 0x170, | ||
| 123 | } card_type; | 124 | } card_type; |
| 124 | u32 chipset; | 125 | u32 chipset; |
| 125 | u8 chiprev; | 126 | u8 chiprev; |
| @@ -37,4 +37,5 @@ int gp100_disp_new(struct nvkm_device *, int, struct nvkm_disp **); · 36 unmodified lines | |||
| 37 | int gp102_disp_new(struct nvkm_device *, int, struct nvkm_disp **); | 37 | int gp102_disp_new(struct nvkm_device *, int, struct nvkm_disp **); |
| 38 | int gv100_disp_new(struct nvkm_device *, int, struct nvkm_disp **); | 38 | int gv100_disp_new(struct nvkm_device *, int, struct nvkm_disp **); |
| 39 | int tu102_disp_new(struct nvkm_device *, int, struct nvkm_disp **); | 39 | int tu102_disp_new(struct nvkm_device *, int, struct nvkm_disp **); |
| 40 | int ga102_disp_new(struct nvkm_device *, int, struct nvkm_disp **); | ||
| 40 | #endif | 41 | #endif |
| @@ -32,4 +32,5 @@ int gm107_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); · 31 unmodified lines | |||
| 32 | int gm200_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); | 32 | int gm200_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); |
| 33 | int gv100_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); | 33 | int gv100_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); |
| 34 | int tu102_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); | 34 | int tu102_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); |
| 35 | int ga100_devinit_new(struct nvkm_device *, int, struct nvkm_devinit **); | ||
| 35 | #endif | 36 | #endif |
| @@ -86,6 +86,8 @@ int gp100_fb_new(struct nvkm_device *, int, struct nvkm_fb **); · 85 unmodified lines | |||
| 86 | int gp102_fb_new(struct nvkm_device *, int, struct nvkm_fb **); | 86 | int gp102_fb_new(struct nvkm_device *, int, struct nvkm_fb **); |
| 87 | int gp10b_fb_new(struct nvkm_device *, int, struct nvkm_fb **); | 87 | int gp10b_fb_new(struct nvkm_device *, int, struct nvkm_fb **); |
| 88 | int gv100_fb_new(struct nvkm_device *, int, struct nvkm_fb **); | 88 | int gv100_fb_new(struct nvkm_device *, int, struct nvkm_fb **); |
| 89 | int ga100_fb_new(struct nvkm_device *, int, struct nvkm_fb **); | ||
| 90 | int ga102_fb_new(struct nvkm_device *, int, struct nvkm_fb **); | ||
| 89 | 91 | ||
| 90 | #include <subdev/bios.h> | 92 | #include <subdev/bios.h> |
| 91 | #include <subdev/bios/ramcfg.h> | 93 | #include <subdev/bios/ramcfg.h> |
| @@ -37,4 +37,5 @@ int nv50_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); · 36 unmodified lines | |||
| 37 | int g94_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); | 37 | int g94_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); |
| 38 | int gf119_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); | 38 | int gf119_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); |
| 39 | int gk104_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); | 39 | int gk104_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); |
| 40 | int ga102_gpio_new(struct nvkm_device *, int, struct nvkm_gpio **); | ||
| 40 | #endif | 41 | #endif |
| @@ -92,6 +92,7 @@ int g94_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); · 91 unmodified lines | |||
| 92 | int gf117_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); | 92 | int gf117_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); |
| 93 | int gf119_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); | 93 | int gf119_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); |
| 94 | int gk104_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); | 94 | int gk104_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); |
| 95 | int gk110_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); | ||
| 95 | int gm200_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); | 96 | int gm200_i2c_new(struct nvkm_device *, int, struct nvkm_i2c **); |
| 96 | 97 | ||
| 97 | static inline int | 98 | static inline int |
| @@ -32,4 +32,5 @@ int gk20a_mc_new(struct nvkm_device *, int, struct nvkm_mc **); · 31 unmodified lines | |||
| 32 | int gp100_mc_new(struct nvkm_device *, int, struct nvkm_mc **); | 32 | int gp100_mc_new(struct nvkm_device *, int, struct nvkm_mc **); |
| 33 | int gp10b_mc_new(struct nvkm_device *, int, struct nvkm_mc **); | 33 | int gp10b_mc_new(struct nvkm_device *, int, struct nvkm_mc **); |
| 34 | int tu102_mc_new(struct nvkm_device *, int, struct nvkm_mc **); | 34 | int tu102_mc_new(struct nvkm_device *, int, struct nvkm_mc **); |
| 35 | int ga100_mc_new(struct nvkm_device *, int, struct nvkm_mc **); | ||
| 35 | #endif | 36 | #endif |
| @@ -256,6 +256,7 @@ nouveau_backlight_init(struct drm_connector *connector) · 255 unmodified lines | |||
| 256 | case NV_DEVICE_INFO_V0_PASCAL: | 256 | case NV_DEVICE_INFO_V0_PASCAL: |
| 257 | case NV_DEVICE_INFO_V0_VOLTA: | 257 | case NV_DEVICE_INFO_V0_VOLTA: |
| 258 | case NV_DEVICE_INFO_V0_TURING: | 258 | case NV_DEVICE_INFO_V0_TURING: |
| 259 | case NV_DEVICE_INFO_V0_AMPERE: //XXX: not confirmed | ||
| 259 | ret = nv50_backlight_init(nv_encoder, &props, &ops); | 260 | ret = nv50_backlight_init(nv_encoder, &props, &ops); |
| 260 | break; | 261 | break; |
| 261 | default: | 262 | default: |
| @@ -547,7 +547,7 @@ nouveau_bo_sync_for_device(struct nouveau_bo *nvbo) · 546 unmodified lines | |||
| 547 | { | 547 | { |
| 548 | struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev); | 548 | struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev); |
| 549 | struct ttm_tt *ttm_dma = (struct ttm_tt *)nvbo->bo.ttm; | 549 | struct ttm_tt *ttm_dma = (struct ttm_tt *)nvbo->bo.ttm; |
| 550 | int i; | 550 | int i, j; |
| 551 | 551 | ||
| 552 | if (!ttm_dma) | 552 | if (!ttm_dma) |
| 553 | return; | 553 | return; |
| @@ -556,10 +556,21 @@ nouveau_bo_sync_for_device(struct nouveau_bo *nvbo) · 2 unmodified lines | |||
| 556 | if (nvbo->force_coherent) | 556 | if (nvbo->force_coherent) |
| 557 | return; | 557 | return; |
| 558 | 558 | ||
| 559 | for (i = 0; i < ttm_dma->num_pages; i++) | 559 | for (i = 0; i < ttm_dma->num_pages; ++i) { |
| 560 | struct page *p = ttm_dma->pages[i]; | ||
| 561 | size_t num_pages = 1; | ||
| 562 | |||
| 563 | for (j = i + 1; j < ttm_dma->num_pages; ++j) { | ||
| 564 | if (++p != ttm_dma->pages[j]) | ||
| 565 | break; | ||
| 566 | |||
| 567 | ++num_pages; | ||
| 568 | } | ||
| 560 | dma_sync_single_for_device(drm->dev->dev, | 569 | dma_sync_single_for_device(drm->dev->dev, |
| 561 | ttm_dma->dma_address[i], | 570 | ttm_dma->dma_address[i], |
| 562 | PAGE_SIZE, DMA_TO_DEVICE); | 571 | num_pages * PAGE_SIZE, DMA_TO_DEVICE); |
| 572 | i += num_pages; | ||
| 573 | } | ||
| 563 | } | 574 | } |
| 564 | 575 | ||
| 565 | void | 576 | void |
| @@ -567,7 +578,7 @@ nouveau_bo_sync_for_cpu(struct nouveau_bo *nvbo) · 1 unmodified line | |||
| 567 | { | 578 | { |
| 568 | struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev); | 579 | struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev); |
| 569 | struct ttm_tt *ttm_dma = (struct ttm_tt *)nvbo->bo.ttm; | 580 | struct ttm_tt *ttm_dma = (struct ttm_tt *)nvbo->bo.ttm; |
| 570 | int i; | 581 | int i, j; |
| 571 | 582 | ||
| 572 | if (!ttm_dma) | 583 | if (!ttm_dma) |
| 573 | return; | 584 | return; |
| @@ -576,9 +587,21 @@ nouveau_bo_sync_for_cpu(struct nouveau_bo *nvbo) · 2 unmodified lines | |||
| 576 | if (nvbo->force_coherent) | 587 | if (nvbo->force_coherent) |
| 577 | return; | 588 | return; |
| 578 | 589 | ||
| 579 | for (i = 0; i < ttm_dma->num_pages; i++) | 590 | for (i = 0; i < ttm_dma->num_pages; ++i) { |
| 591 | struct page *p = ttm_dma->pages[i]; | ||
| 592 | size_t num_pages = 1; | ||
| 593 | |||
| 594 | for (j = i + 1; j < ttm_dma->num_pages; ++j) { | ||
| 595 | if (++p != ttm_dma->pages[j]) | ||
| 596 | break; | ||
| 597 | |||
| 598 | ++num_pages; | ||
| 599 | } | ||
| 600 | |||
| 580 | dma_sync_single_for_cpu(drm->dev->dev, ttm_dma->dma_address[i], | 601 | dma_sync_single_for_cpu(drm->dev->dev, ttm_dma->dma_address[i], |
| 581 | PAGE_SIZE, DMA_FROM_DEVICE); | 602 | num_pages * PAGE_SIZE, DMA_FROM_DEVICE); |
| 603 | i += num_pages; | ||
| 604 | } | ||
| 582 | } | 605 | } |
| 583 | 606 | ||
| 584 | void nouveau_bo_add_io_reserve_lru(struct ttm_buffer_object *bo) | 607 | void nouveau_bo_add_io_reserve_lru(struct ttm_buffer_object *bo) |
| @@ -315,6 +315,10 @@ nouveau_svmm_init(struct drm_device *dev, void *data, · 314 unmodified lines | |||
| 315 | struct drm_nouveau_svm_init *args = data; | 315 | struct drm_nouveau_svm_init *args = data; |
| 316 | int ret; | 316 | int ret; |
| 317 | 317 | ||
| 318 | /* We need to fail if svm is disabled */ | ||
| 319 | if (!cli->drm->svm) | ||
| 320 | return -ENOSYS; | ||
| 321 | |||
| 318 | /* Allocate tracking for SVM-enabled VMM. */ | 322 | /* Allocate tracking for SVM-enabled VMM. */ |
| 319 | if (!(svmm = kzalloc(sizeof(*svmm), GFP_KERNEL))) | 323 | if (!(svmm = kzalloc(sizeof(*svmm), GFP_KERNEL))) |
| 320 | return -ENOMEM; | 324 | return -ENOMEM; |
| @@ -35,6 +35,7 @@ nvif_disp_ctor(struct nvif_device *device, const char *name, s32 oclass, · 34 unmodified lines | |||
| 35 | struct nvif_disp *disp) | 35 | struct nvif_disp *disp) |
| 36 | { | 36 | { |
| 37 | static const struct nvif_mclass disps[] = { | 37 | static const struct nvif_mclass disps[] = { |
| 38 | { GA102_DISP, -1 }, | ||
| 38 | { TU102_DISP, -1 }, | 39 | { TU102_DISP, -1 }, |
| 39 | { GV100_DISP, -1 }, | 40 | { GV100_DISP, -1 }, |
| 40 | { GP102_DISP, -1 }, | 41 | { GP102_DISP, -1 }, |
| @@ -1815,7 +1815,7 @@ nvf0_chipset = { · 1814 unmodified lines | |||
| 1815 | .fb = gk110_fb_new, | 1815 | .fb = gk110_fb_new, |
| 1816 | .fuse = gf100_fuse_new, | 1816 | .fuse = gf100_fuse_new, |
| 1817 | .gpio = gk104_gpio_new, | 1817 | .gpio = gk104_gpio_new, |
| 1818 | .i2c = gk104_i2c_new, | 1818 | .i2c = gk110_i2c_new, |
| 1819 | .ibus = gk104_ibus_new, | 1819 | .ibus = gk104_ibus_new, |
| 1820 | .iccsense = gf100_iccsense_new, | 1820 | .iccsense = gf100_iccsense_new, |
| 1821 | .imem = nv50_instmem_new, | 1821 | .imem = nv50_instmem_new, |
| @@ -1853,7 +1853,7 @@ nvf1_chipset = { · 31 unmodified lines | |||
| 1853 | .fb = gk110_fb_new, | 1853 | .fb = gk110_fb_new, |
| 1854 | .fuse = gf100_fuse_new, | 1854 | .fuse = gf100_fuse_new, |
| 1855 | .gpio = gk104_gpio_new, | 1855 | .gpio = gk104_gpio_new, |
| 1856 | .i2c = gk104_i2c_new, | 1856 | .i2c = gk110_i2c_new, |
| 1857 | .ibus = gk104_ibus_new, | 1857 | .ibus = gk104_ibus_new, |
| 1858 | .iccsense = gf100_iccsense_new, | 1858 | .iccsense = gf100_iccsense_new, |
| 1859 | .imem = nv50_instmem_new, | 1859 | .imem = nv50_instmem_new, |
| @@ -1891,7 +1891,7 @@ nv106_chipset = { · 31 unmodified lines | |||
| 1891 | .fb = gk110_fb_new, | 1891 | .fb = gk110_fb_new, |
| 1892 | .fuse = gf100_fuse_new, | 1892 | .fuse = gf100_fuse_new, |
| 1893 | .gpio = gk104_gpio_new, | 1893 | .gpio = gk104_gpio_new, |
| 1894 | .i2c = gk104_i2c_new, | 1894 | .i2c = gk110_i2c_new, |
| 1895 | .ibus = gk104_ibus_new, | 1895 | .ibus = gk104_ibus_new, |
| 1896 | .iccsense = gf100_iccsense_new, | 1896 | .iccsense = gf100_iccsense_new, |
| 1897 | .imem = nv50_instmem_new, | 1897 | .imem = nv50_instmem_new, |
| @@ -1929,7 +1929,7 @@ nv108_chipset = { · 31 unmodified lines | |||
| 1929 | .fb = gk110_fb_new, | 1929 | .fb = gk110_fb_new, |
| 1930 | .fuse = gf100_fuse_new, | 1930 | .fuse = gf100_fuse_new, |
| 1931 | .gpio = gk104_gpio_new, | 1931 | .gpio = gk104_gpio_new, |
| 1932 | .i2c = gk104_i2c_new, | 1932 | .i2c = gk110_i2c_new, |
| 1933 | .ibus = gk104_ibus_new, | 1933 | .ibus = gk104_ibus_new, |
| 1934 | .iccsense = gf100_iccsense_new, | 1934 | .iccsense = gf100_iccsense_new, |
| 1935 | .imem = nv50_instmem_new, | 1935 | .imem = nv50_instmem_new, |
| @@ -1967,7 +1967,7 @@ nv117_chipset = { · 31 unmodified lines | |||
| 1967 | .fb = gm107_fb_new, | 1967 | .fb = gm107_fb_new, |
| 1968 | .fuse = gm107_fuse_new, | 1968 | .fuse = gm107_fuse_new, |
| 1969 | .gpio = gk104_gpio_new, | 1969 | .gpio = gk104_gpio_new, |
| 1970 | .i2c = gk104_i2c_new, | 1970 | .i2c = gk110_i2c_new, |
| 1971 | .ibus = gk104_ibus_new, | 1971 | .ibus = gk104_ibus_new, |
| 1972 | .iccsense = gf100_iccsense_new, | 1972 | .iccsense = gf100_iccsense_new, |
| 1973 | .imem = nv50_instmem_new, | 1973 | .imem = nv50_instmem_new, |
| @@ -2003,7 +2003,7 @@ nv118_chipset = { · 29 unmodified lines | |||
| 2003 | .fb = gm107_fb_new, | 2003 | .fb = gm107_fb_new, |
| 2004 | .fuse = gm107_fuse_new, | 2004 | .fuse = gm107_fuse_new, |
| 2005 | .gpio = gk104_gpio_new, | 2005 | .gpio = gk104_gpio_new, |
| 2006 | .i2c = gk104_i2c_new, | 2006 | .i2c = gk110_i2c_new, |
| 2007 | .ibus = gk104_ibus_new, | 2007 | .ibus = gk104_ibus_new, |
| 2008 | .iccsense = gf100_iccsense_new, | 2008 | .iccsense = gf100_iccsense_new, |
| 2009 | .imem = nv50_instmem_new, | 2009 | .imem = nv50_instmem_new, |
| @@ -2652,6 +2652,61 @@ nv168_chipset = { · 642 unmodified lines | |||
| 2652 | .sec2 = tu102_sec2_new, | 2652 | .sec2 = tu102_sec2_new, |
| 2653 | }; | 2653 | }; |
| 2654 | 2654 | ||
| 2655 | static const struct nvkm_device_chip | ||
| 2656 | nv170_chipset = { | ||
| 2657 | .name = "GA100", | ||
| 2658 | .bar = tu102_bar_new, | ||
| 2659 | .bios = nvkm_bios_new, | ||
| 2660 | .devinit = ga100_devinit_new, | ||
| 2661 | .fb = ga100_fb_new, | ||
| 2662 | .gpio = gk104_gpio_new, | ||
| 2663 | .i2c = gm200_i2c_new, | ||
| 2664 | .ibus = gm200_ibus_new, | ||
| 2665 | .imem = nv50_instmem_new, | ||
| 2666 | .mc = ga100_mc_new, | ||
| 2667 | .mmu = tu102_mmu_new, | ||
| 2668 | .pci = gp100_pci_new, | ||
| 2669 | .timer = gk20a_timer_new, | ||
| 2670 | }; | ||
| 2671 | |||
| 2672 | static const struct nvkm_device_chip | ||
| 2673 | nv172_chipset = { | ||
| 2674 | .name = "GA102", | ||
| 2675 | .bar = tu102_bar_new, | ||
| 2676 | .bios = nvkm_bios_new, | ||
| 2677 | .devinit = ga100_devinit_new, | ||
| 2678 | .fb = ga102_fb_new, | ||
| 2679 | .gpio = ga102_gpio_new, | ||
| 2680 | .i2c = gm200_i2c_new, | ||
| 2681 | .ibus = gm200_ibus_new, | ||
| 2682 | .imem = nv50_instmem_new, | ||
| 2683 | .mc = ga100_mc_new, | ||
| 2684 | .mmu = tu102_mmu_new, | ||
| 2685 | .pci = gp100_pci_new, | ||
| 2686 | .timer = gk20a_timer_new, | ||
| 2687 | .disp = ga102_disp_new, | ||
| 2688 | .dma = gv100_dma_new, | ||
| 2689 | }; | ||
| 2690 | |||
| 2691 | static const struct nvkm_device_chip | ||
| 2692 | nv174_chipset = { | ||
| 2693 | .name = "GA104", | ||
| 2694 | .bar = tu102_bar_new, | ||
| 2695 | .bios = nvkm_bios_new, | ||
| 2696 | .devinit = ga100_devinit_new, | ||
| 2697 | .fb = ga102_fb_new, | ||
| 2698 | .gpio = ga102_gpio_new, | ||
| 2699 | .i2c = gm200_i2c_new, | ||
| 2700 | .ibus = gm200_ibus_new, | ||
| 2701 | .imem = nv50_instmem_new, | ||
| 2702 | .mc = ga100_mc_new, | ||
| 2703 | .mmu = tu102_mmu_new, | ||
| 2704 | .pci = gp100_pci_new, | ||
| 2705 | .timer = gk20a_timer_new, | ||
| 2706 | .disp = ga102_disp_new, | ||
| 2707 | .dma = gv100_dma_new, | ||
| 2708 | }; | ||
| 2709 | |||
| 2655 | static int | 2710 | static int |
| 2656 | nvkm_device_event_ctor(struct nvkm_object *object, void *data, u32 size, | 2711 | nvkm_device_event_ctor(struct nvkm_object *object, void *data, u32 size, |
| 2657 | struct nvkm_notify *notify) | 2712 | struct nvkm_notify *notify) |
| @@ -3063,6 +3118,7 @@ nvkm_device_ctor(const struct nvkm_device_func *func, · 405 unmodified lines | |||
| 3063 | case 0x130: device->card_type = GP100; break; | 3118 | case 0x130: device->card_type = GP100; break; |
| 3064 | case 0x140: device->card_type = GV100; break; | 3119 | case 0x140: device->card_type = GV100; break; |
| 3065 | case 0x160: device->card_type = TU100; break; | 3120 | case 0x160: device->card_type = TU100; break; |
| 3121 | case 0x170: device->card_type = GA100; break; | ||
| 3066 | default: | 3122 | default: |
| 3067 | break; | 3123 | break; |
| 3068 | } | 3124 | } |
| @@ -3160,10 +3216,23 @@ nvkm_device_ctor(const struct nvkm_device_func *func, · 91 unmodified lines | |||
| 3160 | case 0x166: device->chip = &nv166_chipset; break; | 3216 | case 0x166: device->chip = &nv166_chipset; break; |
| 3161 | case 0x167: device->chip = &nv167_chipset; break; | 3217 | case 0x167: device->chip = &nv167_chipset; break; |
| 3162 | case 0x168: device->chip = &nv168_chipset; break; | 3218 | case 0x168: device->chip = &nv168_chipset; break; |
| 3219 | case 0x172: device->chip = &nv172_chipset; break; | ||
| 3220 | case 0x174: device->chip = &nv174_chipset; break; | ||
| 3163 | default: | 3221 | default: |
| 3164 | nvdev_error(device, "unknown chipset (%08x)\n", boot0); | 3222 | if (nvkm_boolopt(device->cfgopt, "NvEnableUnsupportedChipsets", false)) { |
| 3165 | ret = -ENODEV; | 3223 | switch (device->chipset) { |
| 3166 | goto done; | 3224 | case 0x170: device->chip = &nv170_chipset; break; |
| 3225 | default: | ||
| 3226 | break; | ||
| 3227 | } | ||
| 3228 | } | ||
| 3229 | |||
| 3230 | if (!device->chip) { | ||
| 3231 | nvdev_error(device, "unknown chipset (%08x)\n", boot0); | ||
| 3232 | ret = -ENODEV; | ||
| 3233 | goto done; | ||
| 3234 | } | ||
| 3235 | break; | ||
| 3167 | } | 3236 | } |
| 3168 | 3237 | ||
| 3169 | nvdev_info(device, "NVIDIA %s (%08x)\n", | 3238 | nvdev_info(device, "NVIDIA %s (%08x)\n", |
| @@ -176,6 +176,7 @@ nvkm_udevice_info(struct nvkm_udevice *udev, void *data, u32 size) · 175 unmodified lines | |||
| 176 | case GP100: args->v0.family = NV_DEVICE_INFO_V0_PASCAL; break; | 176 | case GP100: args->v0.family = NV_DEVICE_INFO_V0_PASCAL; break; |
| 177 | case GV100: args->v0.family = NV_DEVICE_INFO_V0_VOLTA; break; | 177 | case GV100: args->v0.family = NV_DEVICE_INFO_V0_VOLTA; break; |
| 178 | case TU100: args->v0.family = NV_DEVICE_INFO_V0_TURING; break; | 178 | case TU100: args->v0.family = NV_DEVICE_INFO_V0_TURING; break; |
| 179 | case GA100: args->v0.family = NV_DEVICE_INFO_V0_AMPERE; break; | ||
| 179 | default: | 180 | default: |
| 180 | args->v0.family = 0; | 181 | args->v0.family = 0; |
| 181 | break; | 182 | break; |
| @@ -17,6 +17,7 @@ nvkm-y += nvkm/engine/disp/gp100.o · 16 unmodified lines | |||
| 17 | nvkm-y += nvkm/engine/disp/gp102.o | 17 | nvkm-y += nvkm/engine/disp/gp102.o |
| 18 | nvkm-y += nvkm/engine/disp/gv100.o | 18 | nvkm-y += nvkm/engine/disp/gv100.o |
| 19 | nvkm-y += nvkm/engine/disp/tu102.o | 19 | nvkm-y += nvkm/engine/disp/tu102.o |
| 20 | nvkm-y += nvkm/engine/disp/ga102.o | ||
| 20 | nvkm-y += nvkm/engine/disp/vga.o | 21 | nvkm-y += nvkm/engine/disp/vga.o |
| 21 | 22 | ||
| 22 | nvkm-y += nvkm/engine/disp/head.o | 23 | nvkm-y += nvkm/engine/disp/head.o |
| @@ -42,6 +43,7 @@ nvkm-y += nvkm/engine/disp/sorgm200.o · 19 unmodified lines | |||
| 42 | nvkm-y += nvkm/engine/disp/sorgp100.o | 43 | nvkm-y += nvkm/engine/disp/sorgp100.o |
| 43 | nvkm-y += nvkm/engine/disp/sorgv100.o | 44 | nvkm-y += nvkm/engine/disp/sorgv100.o |
| 44 | nvkm-y += nvkm/engine/disp/sortu102.o | 45 | nvkm-y += nvkm/engine/disp/sortu102.o |
| 46 | nvkm-y += nvkm/engine/disp/sorga102.o | ||
| 45 | 47 | ||
| 46 | nvkm-y += nvkm/engine/disp/outp.o | 48 | nvkm-y += nvkm/engine/disp/outp.o |
| 47 | nvkm-y += nvkm/engine/disp/dp.o | 49 | nvkm-y += nvkm/engine/disp/dp.o |
| @@ -75,6 +77,7 @@ nvkm-y += nvkm/engine/disp/rootgp100.o · 27 unmodified lines | |||
| 75 | nvkm-y += nvkm/engine/disp/rootgp102.o | 77 | nvkm-y += nvkm/engine/disp/rootgp102.o |
| 76 | nvkm-y += nvkm/engine/disp/rootgv100.o | 78 | nvkm-y += nvkm/engine/disp/rootgv100.o |
| 77 | nvkm-y += nvkm/engine/disp/roottu102.o | 79 | nvkm-y += nvkm/engine/disp/roottu102.o |
| 80 | nvkm-y += nvkm/engine/disp/rootga102.o | ||
| 78 | 81 | ||
| 79 | nvkm-y += nvkm/engine/disp/capsgv100.o | 82 | nvkm-y += nvkm/engine/disp/capsgv100.o |
| 80 | 83 | ||
| @@ -33,6 +33,12 @@ · 32 unmodified lines | |||
| 33 | 33 | ||
| 34 | #include <nvif/event.h> | 34 | #include <nvif/event.h> |
| 35 | 35 | ||
| 36 | /* IED scripts are no longer used by UEFI/RM from Ampere, but have been updated for | ||
| 37 | * the x86 option ROM. However, the relevant VBIOS table versions weren't modified, | ||
| 38 | * so we're unable to detect this in a nice way. | ||
| 39 | */ | ||
| 40 | #define AMPERE_IED_HACK(disp) ((disp)->engine.subdev.device->card_type >= GA100) | ||
| 41 | |||
| 36 | struct lt_state { | 42 | struct lt_state { |
| 37 | struct nvkm_dp *dp; | 43 | struct nvkm_dp *dp; |
| 38 | u8 stat[6]; | 44 | u8 stat[6]; |
| @@ -238,6 +244,19 @@ nvkm_dp_train_links(struct nvkm_dp *dp) · 199 unmodified lines | |||
| 238 | dp->dpcd[DPCD_RC02] &= ~DPCD_RC02_TPS3_SUPPORTED; | 244 | dp->dpcd[DPCD_RC02] &= ~DPCD_RC02_TPS3_SUPPORTED; |
| 239 | lt.pc2 = dp->dpcd[DPCD_RC02] & DPCD_RC02_TPS3_SUPPORTED; | 245 | lt.pc2 = dp->dpcd[DPCD_RC02] & DPCD_RC02_TPS3_SUPPORTED; |
| 240 | 246 | ||
| 247 | if (AMPERE_IED_HACK(disp) && (lnkcmp = lt.dp->info.script[0])) { | ||
| 248 | /* Execute BeforeLinkTraining script from DP Info table. */ | ||
| 249 | while (ior->dp.bw < nvbios_rd08(bios, lnkcmp)) | ||
| 250 | lnkcmp += 3; | ||
| 251 | lnkcmp = nvbios_rd16(bios, lnkcmp + 1); | ||
| 252 | |||
| 253 | nvbios_init(&dp->outp.disp->engine.subdev, lnkcmp, | ||
| 254 | init.outp = &dp->outp.info; | ||
| 255 | init.or = ior->id; | ||
| 256 | init.link = ior->asy.link; | ||
| 257 | ); | ||
| 258 | } | ||
| 259 | |||
| 241 | /* Set desired link configuration on the source. */ | 260 | /* Set desired link configuration on the source. */ |
| 242 | if ((lnkcmp = lt.dp->info.lnkcmp)) { | 261 | if ((lnkcmp = lt.dp->info.lnkcmp)) { |
| 243 | if (dp->version < 0x30) { | 262 | if (dp->version < 0x30) { |
| @@ -316,12 +335,14 @@ nvkm_dp_train_init(struct nvkm_dp *dp) · 72 unmodified lines | |||
| 316 | ); | 335 | ); |
| 317 | } | 336 | } |
| 318 | 337 | ||
| 319 | /* Execute BeforeLinkTraining script from DP Info table. */ | 338 | if (!AMPERE_IED_HACK(dp->outp.disp)) { |
| 320 | nvbios_init(&dp->outp.disp->engine.subdev, dp->info.script[0], | 339 | /* Execute BeforeLinkTraining script from DP Info table. */ |
| 321 | init.outp = &dp->outp.info; | 340 | nvbios_init(&dp->outp.disp->engine.subdev, dp->info.script[0], |
| 322 | init.or = dp->outp.ior->id; | 341 | init.outp = &dp->outp.info; |
| 323 | init.link = dp->outp.ior->asy.link; | 342 | init.or = dp->outp.ior->id; |
| 324 | ); | 343 | init.link = dp->outp.ior->asy.link; |
| 344 | ); | ||
| 345 | } | ||
| 325 | } | 346 | } |
| 326 | 347 | ||
| 327 | static const struct dp_rates { | 348 | static const struct dp_rates { |
| @@ -0,0 +1,46 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "nv50.h" | ||
| 23 | #include "head.h" | ||
| 24 | #include "ior.h" | ||
| 25 | #include "channv50.h" | ||
| 26 | #include "rootnv50.h" | ||
| 27 | |||
| 28 | static const struct nv50_disp_func | ||
| 29 | ga102_disp = { | ||
| 30 | .init = tu102_disp_init, | ||
| 31 | .fini = gv100_disp_fini, | ||
| 32 | .intr = gv100_disp_intr, | ||
| 33 | .uevent = &gv100_disp_chan_uevent, | ||
| 34 | .super = gv100_disp_super, | ||
| 35 | .root = &ga102_disp_root_oclass, | ||
| 36 | .wndw = { .cnt = gv100_disp_wndw_cnt }, | ||
| 37 | .head = { .cnt = gv100_head_cnt, .new = gv100_head_new }, | ||
| 38 | .sor = { .cnt = gv100_sor_cnt, .new = ga102_sor_new }, | ||
| 39 | .ramht_size = 0x2000, | ||
| 40 | }; | ||
| 41 | |||
| 42 | int | ||
| 43 | ga102_disp_new(struct nvkm_device *device, int index, struct nvkm_disp **pdisp) | ||
| 44 | { | ||
| 45 | return nv50_disp_new_(&ga102_disp, device, index, pdisp); | ||
| 46 | } | ||
| @@ -150,6 +150,8 @@ void gv100_sor_dp_audio(struct nvkm_ior *, int, bool); · 149 unmodified lines | |||
| 150 | void gv100_sor_dp_audio_sym(struct nvkm_ior *, int, u16, u32); | 150 | void gv100_sor_dp_audio_sym(struct nvkm_ior *, int, u16, u32); |
| 151 | void gv100_sor_dp_watermark(struct nvkm_ior *, int, u8); | 151 | void gv100_sor_dp_watermark(struct nvkm_ior *, int, u8); |
| 152 | 152 | ||
| 153 | void tu102_sor_dp_vcpi(struct nvkm_ior *, int, u8, u8, u16, u16); | ||
| 154 | |||
| 153 | void g84_hdmi_ctrl(struct nvkm_ior *, int, bool, u8, u8, u8 *, u8 , u8 *, u8); | 155 | void g84_hdmi_ctrl(struct nvkm_ior *, int, bool, u8, u8, u8 *, u8 , u8 *, u8); |
| 154 | void gt215_hdmi_ctrl(struct nvkm_ior *, int, bool, u8, u8, u8 *, u8 , u8 *, u8); | 156 | void gt215_hdmi_ctrl(struct nvkm_ior *, int, bool, u8, u8, u8 *, u8 , u8 *, u8); |
| 155 | void gf119_hdmi_ctrl(struct nvkm_ior *, int, bool, u8, u8, u8 *, u8 , u8 *, u8); | 157 | void gf119_hdmi_ctrl(struct nvkm_ior *, int, bool, u8, u8, u8 *, u8 , u8 *, u8); |
| @@ -207,4 +209,6 @@ int gv100_sor_cnt(struct nvkm_disp *, unsigned long *); · 51 unmodified lines | |||
| 207 | int gv100_sor_new(struct nvkm_disp *, int); | 209 | int gv100_sor_new(struct nvkm_disp *, int); |
| 208 | 210 | ||
| 209 | int tu102_sor_new(struct nvkm_disp *, int); | 211 | int tu102_sor_new(struct nvkm_disp *, int); |
| 212 | |||
| 213 | int ga102_sor_new(struct nvkm_disp *, int); | ||
| 210 | #endif | 214 | #endif |
| @@ -86,6 +86,8 @@ void gv100_disp_intr(struct nv50_disp *); · 85 unmodified lines | |||
| 86 | void gv100_disp_super(struct work_struct *); | 86 | void gv100_disp_super(struct work_struct *); |
| 87 | int gv100_disp_wndw_cnt(struct nvkm_disp *, unsigned long *); | 87 | int gv100_disp_wndw_cnt(struct nvkm_disp *, unsigned long *); |
| 88 | 88 | ||
| 89 | int tu102_disp_init(struct nv50_disp *); | ||
| 90 | |||
| 89 | void nv50_disp_dptmds_war_2(struct nv50_disp *, struct dcb_output *); | 91 | void nv50_disp_dptmds_war_2(struct nv50_disp *, struct dcb_output *); |
| 90 | void nv50_disp_dptmds_war_3(struct nv50_disp *, struct dcb_output *); | 92 | void nv50_disp_dptmds_war_3(struct nv50_disp *, struct dcb_output *); |
| 91 | void nv50_disp_update_sppll1(struct nv50_disp *); | 93 | void nv50_disp_update_sppll1(struct nv50_disp *); |
| @@ -0,0 +1,52 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "rootnv50.h" | ||
| 23 | #include "channv50.h" | ||
| 24 | |||
| 25 | #include <nvif/class.h> | ||
| 26 | |||
| 27 | static const struct nv50_disp_root_func | ||
| 28 | ga102_disp_root = { | ||
| 29 | .user = { | ||
| 30 | {{-1,-1,GV100_DISP_CAPS }, gv100_disp_caps_new }, | ||
| 31 | {{0,0,GA102_DISP_CURSOR }, gv100_disp_curs_new }, | ||
| 32 | {{0,0,GA102_DISP_WINDOW_IMM_CHANNEL_DMA}, gv100_disp_wimm_new }, | ||
| 33 | {{0,0,GA102_DISP_CORE_CHANNEL_DMA }, gv100_disp_core_new }, | ||
| 34 | {{0,0,GA102_DISP_WINDOW_CHANNEL_DMA }, gv100_disp_wndw_new }, | ||
| 35 | {} | ||
| 36 | }, | ||
| 37 | }; | ||
| 38 | |||
| 39 | static int | ||
| 40 | ga102_disp_root_new(struct nvkm_disp *disp, const struct nvkm_oclass *oclass, | ||
| 41 | void *data, u32 size, struct nvkm_object **pobject) | ||
| 42 | { | ||
| 43 | return nv50_disp_root_new_(&ga102_disp_root, disp, oclass, data, size, pobject); | ||
| 44 | } | ||
| 45 | |||
| 46 | const struct nvkm_disp_oclass | ||
| 47 | ga102_disp_root_oclass = { | ||
| 48 | .base.oclass = GA102_DISP, | ||
| 49 | .base.minver = -1, | ||
| 50 | .base.maxver = -1, | ||
| 51 | .ctor = ga102_disp_root_new, | ||
| 52 | }; | ||
| @@ -41,4 +41,5 @@ extern const struct nvkm_disp_oclass gp100_disp_root_oclass; · 40 unmodified lines | |||
| 41 | extern const struct nvkm_disp_oclass gp102_disp_root_oclass; | 41 | extern const struct nvkm_disp_oclass gp102_disp_root_oclass; |
| 42 | extern const struct nvkm_disp_oclass gv100_disp_root_oclass; | 42 | extern const struct nvkm_disp_oclass gv100_disp_root_oclass; |
| 43 | extern const struct nvkm_disp_oclass tu102_disp_root_oclass; | 43 | extern const struct nvkm_disp_oclass tu102_disp_root_oclass; |
| 44 | extern const struct nvkm_disp_oclass ga102_disp_root_oclass; | ||
| 44 | #endif | 45 | #endif |
| @@ -0,0 +1,140 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "ior.h" | ||
| 23 | |||
| 24 | #include <subdev/timer.h> | ||
| 25 | |||
| 26 | static int | ||
| 27 | ga102_sor_dp_links(struct nvkm_ior *sor, struct nvkm_i2c_aux *aux) | ||
| 28 | { | ||
| 29 | struct nvkm_device *device = sor->disp->engine.subdev.device; | ||
| 30 | const u32 soff = nv50_ior_base(sor); | ||
| 31 | const u32 loff = nv50_sor_link(sor); | ||
| 32 | u32 dpctrl = 0x00000000; | ||
| 33 | u32 clksor = 0x00000000; | ||
| 34 | |||
| 35 | switch (sor->dp.bw) { | ||
| 36 | case 0x06: clksor |= 0x00000000; break; | ||
| 37 | case 0x0a: clksor |= 0x00040000; break; | ||
| 38 | case 0x14: clksor |= 0x00080000; break; | ||
| 39 | case 0x1e: clksor |= 0x000c0000; break; | ||
| 40 | default: | ||
| 41 | WARN_ON(1); | ||
| 42 | return -EINVAL; | ||
| 43 | } | ||
| 44 | |||
| 45 | dpctrl |= ((1 << sor->dp.nr) - 1) << 16; | ||
| 46 | if (sor->dp.mst) | ||
| 47 | dpctrl |= 0x40000000; | ||
| 48 | if (sor->dp.ef) | ||
| 49 | dpctrl |= 0x00004000; | ||
| 50 | |||
| 51 | nvkm_mask(device, 0x612300 + soff, 0x007c0000, clksor); | ||
| 52 | |||
| 53 | /*XXX*/ | ||
| 54 | nvkm_msec(device, 40, NVKM_DELAY); | ||
| 55 | nvkm_mask(device, 0x612300 + soff, 0x00030000, 0x00010000); | ||
| 56 | nvkm_mask(device, 0x61c10c + loff, 0x00000003, 0x00000001); | ||
| 57 | |||
| 58 | nvkm_mask(device, 0x61c10c + loff, 0x401f4000, dpctrl); | ||
| 59 | return 0; | ||
| 60 | } | ||
| 61 | |||
| 62 | static void | ||
| 63 | ga102_sor_clock(struct nvkm_ior *sor) | ||
| 64 | { | ||
| 65 | struct nvkm_device *device = sor->disp->engine.subdev.device; | ||
| 66 | u32 div2 = 0; | ||
| 67 | if (sor->asy.proto == TMDS) { | ||
| 68 | if (sor->tmds.high_speed) | ||
| 69 | div2 = 1; | ||
| 70 | } | ||
| 71 | nvkm_wr32(device, 0x00ec08 + (sor->id * 0x10), 0x00000000); | ||
| 72 | nvkm_wr32(device, 0x00ec04 + (sor->id * 0x10), div2); | ||
| 73 | } | ||
| 74 | |||
| 75 | static const struct nvkm_ior_func | ||
| 76 | ga102_sor_hda = { | ||
| 77 | .route = { | ||
| 78 | .get = gm200_sor_route_get, | ||
| 79 | .set = gm200_sor_route_set, | ||
| 80 | }, | ||
| 81 | .state = gv100_sor_state, | ||
| 82 | .power = nv50_sor_power, | ||
| 83 | .clock = ga102_sor_clock, | ||
| 84 | .hdmi = { | ||
| 85 | .ctrl = gv100_hdmi_ctrl, | ||
| 86 | .scdc = gm200_hdmi_scdc, | ||
| 87 | }, | ||
| 88 | .dp = { | ||
| 89 | .lanes = { 0, 1, 2, 3 }, | ||
| 90 | .links = ga102_sor_dp_links, | ||
| 91 | .power = g94_sor_dp_power, | ||
| 92 | .pattern = gm107_sor_dp_pattern, | ||
| 93 | .drive = gm200_sor_dp_drive, | ||
| 94 | .vcpi = tu102_sor_dp_vcpi, | ||
| 95 | .audio = gv100_sor_dp_audio, | ||
| 96 | .audio_sym = gv100_sor_dp_audio_sym, | ||
| 97 | .watermark = gv100_sor_dp_watermark, | ||
| 98 | }, | ||
| 99 | .hda = { | ||
| 100 | .hpd = gf119_hda_hpd, | ||
| 101 | .eld = gf119_hda_eld, | ||
| 102 | .device_entry = gv100_hda_device_entry, | ||
| 103 | }, | ||
| 104 | }; | ||
| 105 | |||
| 106 | static const struct nvkm_ior_func | ||
| 107 | ga102_sor = { | ||
| 108 | .route = { | ||
| 109 | .get = gm200_sor_route_get, | ||
| 110 | .set = gm200_sor_route_set, | ||
| 111 | }, | ||
| 112 | .state = gv100_sor_state, | ||
| 113 | .power = nv50_sor_power, | ||
| 114 | .clock = ga102_sor_clock, | ||
| 115 | .hdmi = { | ||
| 116 | .ctrl = gv100_hdmi_ctrl, | ||
| 117 | .scdc = gm200_hdmi_scdc, | ||
| 118 | }, | ||
| 119 | .dp = { | ||
| 120 | .lanes = { 0, 1, 2, 3 }, | ||
| 121 | .links = ga102_sor_dp_links, | ||
| 122 | .power = g94_sor_dp_power, | ||
| 123 | .pattern = gm107_sor_dp_pattern, | ||
| 124 | .drive = gm200_sor_dp_drive, | ||
| 125 | .vcpi = tu102_sor_dp_vcpi, | ||
| 126 | .audio = gv100_sor_dp_audio, | ||
| 127 | .audio_sym = gv100_sor_dp_audio_sym, | ||
| 128 | .watermark = gv100_sor_dp_watermark, | ||
| 129 | }, | ||
| 130 | }; | ||
| 131 | |||
| 132 | int | ||
| 133 | ga102_sor_new(struct nvkm_disp *disp, int id) | ||
| 134 | { | ||
| 135 | struct nvkm_device *device = disp->engine.subdev.device; | ||
| 136 | u32 hda = nvkm_rd32(device, 0x08a15c); | ||
| 137 | if (hda & BIT(id)) | ||
| 138 | return nvkm_ior_new_(&ga102_sor_hda, disp, SOR, id); | ||
| 139 | return nvkm_ior_new_(&ga102_sor, disp, SOR, id); | ||
| 140 | } | ||
| @@ -23,7 +23,7 @@ · 22 unmodified lines | |||
| 23 | 23 | ||
| 24 | #include <subdev/timer.h> | 24 | #include <subdev/timer.h> |
| 25 | 25 | ||
| 26 | static void | 26 | void |
| 27 | tu102_sor_dp_vcpi(struct nvkm_ior *sor, int head, | 27 | tu102_sor_dp_vcpi(struct nvkm_ior *sor, int head, |
| 28 | u8 slot, u8 slot_nr, u16 pbn, u16 aligned) | 28 | u8 slot, u8 slot_nr, u16 pbn, u16 aligned) |
| 29 | { | 29 | { |
| @@ -28,7 +28,7 @@ · 27 unmodified lines | |||
| 28 | #include <core/gpuobj.h> | 28 | #include <core/gpuobj.h> |
| 29 | #include <subdev/timer.h> | 29 | #include <subdev/timer.h> |
| 30 | 30 | ||
| 31 | static int | 31 | int |
| 32 | tu102_disp_init(struct nv50_disp *disp) | 32 | tu102_disp_init(struct nv50_disp *disp) |
| 33 | { | 33 | { |
| 34 | struct nvkm_device *device = disp->base.engine.subdev.device; | 34 | struct nvkm_device *device = disp->base.engine.subdev.device; |
| @@ -75,7 +75,7 @@ shadow_image(struct nvkm_bios *bios, int idx, u32 offset, struct shadow *mthd) · 74 unmodified lines | |||
| 75 | nvkm_debug(subdev, "%08x: type %02x, %d bytes\n", | 75 | nvkm_debug(subdev, "%08x: type %02x, %d bytes\n", |
| 76 | image.base, image.type, image.size); | 76 | image.base, image.type, image.size); |
| 77 | 77 | ||
| 78 | if (!shadow_fetch(bios, mthd, image.size)) { | 78 | if (!shadow_fetch(bios, mthd, image.base + image.size)) { |
| 79 | nvkm_debug(subdev, "%08x: fetch failed\n", image.base); | 79 | nvkm_debug(subdev, "%08x: fetch failed\n", image.base); |
| 80 | return 0; | 80 | return 0; |
| 81 | } | 81 | } |
| @@ -64,6 +64,9 @@ pramin_init(struct nvkm_bios *bios, const char *name) · 63 unmodified lines | |||
| 64 | return NULL; | 64 | return NULL; |
| 65 | 65 | ||
| 66 | /* we can't get the bios image pointer without PDISP */ | 66 | /* we can't get the bios image pointer without PDISP */ |
| 67 | if (device->card_type >= GA100) | ||
| 68 | addr = device->chipset == 0x170; /*XXX: find the fuse reg for this */ | ||
| 69 | else | ||
| 67 | if (device->card_type >= GM100) | 70 | if (device->card_type >= GM100) |
| 68 | addr = nvkm_rd32(device, 0x021c04); | 71 | addr = nvkm_rd32(device, 0x021c04); |
| 69 | else | 72 | else |
| @@ -15,3 +15,4 @@ nvkm-y += nvkm/subdev/devinit/gm107.o · 14 unmodified lines | |||
| 15 | nvkm-y += nvkm/subdev/devinit/gm200.o | 15 | nvkm-y += nvkm/subdev/devinit/gm200.o |
| 16 | nvkm-y += nvkm/subdev/devinit/gv100.o | 16 | nvkm-y += nvkm/subdev/devinit/gv100.o |
| 17 | nvkm-y += nvkm/subdev/devinit/tu102.o | 17 | nvkm-y += nvkm/subdev/devinit/tu102.o |
| 18 | nvkm-y += nvkm/subdev/devinit/ga100.o | ||
| @@ -0,0 +1,76 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "nv50.h" | ||
| 23 | |||
| 24 | #include <subdev/bios.h> | ||
| 25 | #include <subdev/bios/pll.h> | ||
| 26 | #include <subdev/clk/pll.h> | ||
| 27 | |||
| 28 | static int | ||
| 29 | ga100_devinit_pll_set(struct nvkm_devinit *init, u32 type, u32 freq) | ||
| 30 | { | ||
| 31 | struct nvkm_subdev *subdev = &init->subdev; | ||
| 32 | struct nvkm_device *device = subdev->device; | ||
| 33 | struct nvbios_pll info; | ||
| 34 | int head = type - PLL_VPLL0; | ||
| 35 | int N, fN, M, P; | ||
| 36 | int ret; | ||
| 37 | |||
| 38 | ret = nvbios_pll_parse(device->bios, type, &info); | ||
| 39 | if (ret) | ||
| 40 | return ret; | ||
| 41 | |||
| 42 | ret = gt215_pll_calc(subdev, &info, freq, &N, &fN, &M, &P); | ||
| 43 | if (ret < 0) | ||
| 44 | return ret; | ||
| 45 | |||
| 46 | switch (info.type) { | ||
| 47 | case PLL_VPLL0: | ||
| 48 | case PLL_VPLL1: | ||
| 49 | case PLL_VPLL2: | ||
| 50 | case PLL_VPLL3: | ||
| 51 | nvkm_wr32(device, 0x00ef00 + (head * 0x40), 0x02080004); | ||
| 52 | nvkm_wr32(device, 0x00ef18 + (head * 0x40), (N << 16) | fN); | ||
| 53 | nvkm_wr32(device, 0x00ef04 + (head * 0x40), (P << 16) | M); | ||
| 54 | nvkm_wr32(device, 0x00e9c0 + (head * 0x04), 0x00000001); | ||
| 55 | break; | ||
| 56 | default: | ||
| 57 | nvkm_warn(subdev, "%08x/%dKhz unimplemented\n", type, freq); | ||
| 58 | ret = -EINVAL; | ||
| 59 | break; | ||
| 60 | } | ||
| 61 | |||
| 62 | return ret; | ||
| 63 | } | ||
| 64 | |||
| 65 | static const struct nvkm_devinit_func | ||
| 66 | ga100_devinit = { | ||
| 67 | .init = nv50_devinit_init, | ||
| 68 | .post = tu102_devinit_post, | ||
| 69 | .pll_set = ga100_devinit_pll_set, | ||
| 70 | }; | ||
| 71 | |||
| 72 | int | ||
| 73 | ga100_devinit_new(struct nvkm_device *device, int index, struct nvkm_devinit **pinit) | ||
| 74 | { | ||
| 75 | return nv50_devinit_new_(&ga100_devinit, device, index, pinit); | ||
| 76 | } | ||
| @@ -19,4 +19,5 @@ void nvkm_devinit_ctor(const struct nvkm_devinit_func *, struct nvkm_device *, · 18 unmodified lines | |||
| 19 | int index, struct nvkm_devinit *); | 19 | int index, struct nvkm_devinit *); |
| 20 | 20 | ||
| 21 | int nv04_devinit_post(struct nvkm_devinit *, bool); | 21 | int nv04_devinit_post(struct nvkm_devinit *, bool); |
| 22 | int tu102_devinit_post(struct nvkm_devinit *, bool); | ||
| 22 | #endif | 23 | #endif |
| @@ -65,7 +65,7 @@ tu102_devinit_pll_set(struct nvkm_devinit *init, u32 type, u32 freq) · 64 unmodified lines | |||
| 65 | return ret; | 65 | return ret; |
| 66 | } | 66 | } |
| 67 | 67 | ||
| 68 | static int | 68 | int |
| 69 | tu102_devinit_post(struct nvkm_devinit *base, bool post) | 69 | tu102_devinit_post(struct nvkm_devinit *base, bool post) |
| 70 | { | 70 | { |
| 71 | struct nv50_devinit *init = nv50_devinit(base); | 71 | struct nv50_devinit *init = nv50_devinit(base); |
| @@ -32,6 +32,8 @@ nvkm-y += nvkm/subdev/fb/gp100.o · 31 unmodified lines | |||
| 32 | nvkm-y += nvkm/subdev/fb/gp102.o | 32 | nvkm-y += nvkm/subdev/fb/gp102.o |
| 33 | nvkm-y += nvkm/subdev/fb/gp10b.o | 33 | nvkm-y += nvkm/subdev/fb/gp10b.o |
| 34 | nvkm-y += nvkm/subdev/fb/gv100.o | 34 | nvkm-y += nvkm/subdev/fb/gv100.o |
| 35 | nvkm-y += nvkm/subdev/fb/ga100.o | ||
| 36 | nvkm-y += nvkm/subdev/fb/ga102.o | ||
| 35 | 37 | ||
| 36 | nvkm-y += nvkm/subdev/fb/ram.o | 38 | nvkm-y += nvkm/subdev/fb/ram.o |
| 37 | nvkm-y += nvkm/subdev/fb/ramnv04.o | 39 | nvkm-y += nvkm/subdev/fb/ramnv04.o |
| @@ -52,6 +54,7 @@ nvkm-y += nvkm/subdev/fb/ramgk104.o · 14 unmodified lines | |||
| 52 | nvkm-y += nvkm/subdev/fb/ramgm107.o | 54 | nvkm-y += nvkm/subdev/fb/ramgm107.o |
| 53 | nvkm-y += nvkm/subdev/fb/ramgm200.o | 55 | nvkm-y += nvkm/subdev/fb/ramgm200.o |
| 54 | nvkm-y += nvkm/subdev/fb/ramgp100.o | 56 | nvkm-y += nvkm/subdev/fb/ramgp100.o |
| 57 | nvkm-y += nvkm/subdev/fb/ramga102.o | ||
| 55 | nvkm-y += nvkm/subdev/fb/sddr2.o | 58 | nvkm-y += nvkm/subdev/fb/sddr2.o |
| 56 | nvkm-y += nvkm/subdev/fb/sddr3.o | 59 | nvkm-y += nvkm/subdev/fb/sddr3.o |
| 57 | nvkm-y += nvkm/subdev/fb/gddr3.o | 60 | nvkm-y += nvkm/subdev/fb/gddr3.o |
| @@ -0,0 +1,40 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "gf100.h" | ||
| 23 | #include "ram.h" | ||
| 24 | |||
| 25 | static const struct nvkm_fb_func | ||
| 26 | ga100_fb = { | ||
| 27 | .dtor = gf100_fb_dtor, | ||
| 28 | .oneinit = gf100_fb_oneinit, | ||
| 29 | .init = gp100_fb_init, | ||
| 30 | .init_page = gv100_fb_init_page, | ||
| 31 | .init_unkn = gp100_fb_init_unkn, | ||
| 32 | .ram_new = gp100_ram_new, | ||
| 33 | .default_bigpage = 16, | ||
| 34 | }; | ||
| 35 | |||
| 36 | int | ||
| 37 | ga100_fb_new(struct nvkm_device *device, int index, struct nvkm_fb **pfb) | ||
| 38 | { | ||
| 39 | return gp102_fb_new_(&ga100_fb, device, index, pfb); | ||
| 40 | } | ||
| @@ -0,0 +1,40 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "gf100.h" | ||
| 23 | #include "ram.h" | ||
| 24 | |||
| 25 | static const struct nvkm_fb_func | ||
| 26 | ga102_fb = { | ||
| 27 | .dtor = gf100_fb_dtor, | ||
| 28 | .oneinit = gf100_fb_oneinit, | ||
| 29 | .init = gp100_fb_init, | ||
| 30 | .init_page = gv100_fb_init_page, | ||
| 31 | .init_unkn = gp100_fb_init_unkn, | ||
| 32 | .ram_new = ga102_ram_new, | ||
| 33 | .default_bigpage = 16, | ||
| 34 | }; | ||
| 35 | |||
| 36 | int | ||
| 37 | ga102_fb_new(struct nvkm_device *device, int index, struct nvkm_fb **pfb) | ||
| 38 | { | ||
| 39 | return gp102_fb_new_(&ga102_fb, device, index, pfb); | ||
| 40 | } | ||
| @@ -22,7 +22,7 @@ · 21 unmodified lines | |||
| 22 | #include "gf100.h" | 22 | #include "gf100.h" |
| 23 | #include "ram.h" | 23 | #include "ram.h" |
| 24 | 24 | ||
| 25 | static int | 25 | int |
| 26 | gv100_fb_init_page(struct nvkm_fb *fb) | 26 | gv100_fb_init_page(struct nvkm_fb *fb) |
| 27 | { | 27 | { |
| 28 | return (fb->page == 16) ? 0 : -EINVAL; | 28 | return (fb->page == 16) ? 0 : -EINVAL; |
| @@ -82,4 +82,6 @@ int gp102_fb_new_(const struct nvkm_fb_func *, struct nvkm_device *, int, · 81 unmodified lines | |||
| 82 | struct nvkm_fb **); | 82 | struct nvkm_fb **); |
| 83 | bool gp102_fb_vpr_scrub_required(struct nvkm_fb *); | 83 | bool gp102_fb_vpr_scrub_required(struct nvkm_fb *); |
| 84 | int gp102_fb_vpr_scrub(struct nvkm_fb *); | 84 | int gp102_fb_vpr_scrub(struct nvkm_fb *); |
| 85 | |||
| 86 | int gv100_fb_init_page(struct nvkm_fb *); | ||
| 85 | #endif | 87 | #endif |
| @@ -70,4 +70,5 @@ int gk104_ram_new(struct nvkm_fb *, struct nvkm_ram **); · 69 unmodified lines | |||
| 70 | int gm107_ram_new(struct nvkm_fb *, struct nvkm_ram **); | 70 | int gm107_ram_new(struct nvkm_fb *, struct nvkm_ram **); |
| 71 | int gm200_ram_new(struct nvkm_fb *, struct nvkm_ram **); | 71 | int gm200_ram_new(struct nvkm_fb *, struct nvkm_ram **); |
| 72 | int gp100_ram_new(struct nvkm_fb *, struct nvkm_ram **); | 72 | int gp100_ram_new(struct nvkm_fb *, struct nvkm_ram **); |
| 73 | int ga102_ram_new(struct nvkm_fb *, struct nvkm_ram **); | ||
| 73 | #endif | 74 | #endif |
| @@ -0,0 +1,40 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "ram.h" | ||
| 23 | |||
| 24 | #include <subdev/bios.h> | ||
| 25 | #include <subdev/bios/init.h> | ||
| 26 | #include <subdev/bios/rammap.h> | ||
| 27 | |||
| 28 | static const struct nvkm_ram_func | ||
| 29 | ga102_ram = { | ||
| 30 | }; | ||
| 31 | |||
| 32 | int | ||
| 33 | ga102_ram_new(struct nvkm_fb *fb, struct nvkm_ram **pram) | ||
| 34 | { | ||
| 35 | struct nvkm_device *device = fb->subdev.device; | ||
| 36 | enum nvkm_ram_type type = nvkm_fb_bios_memtype(device->bios); | ||
| 37 | u32 size = nvkm_rd32(device, 0x1183a4); | ||
| 38 | |||
| 39 | return nvkm_ram_new_(&ga102_ram, fb, type, (u64)size << 20, pram); | ||
| 40 | } | ||
| @@ -5,3 +5,4 @@ nvkm-y += nvkm/subdev/gpio/nv50.o · 4 unmodified lines | |||
| 5 | nvkm-y += nvkm/subdev/gpio/g94.o | 5 | nvkm-y += nvkm/subdev/gpio/g94.o |
| 6 | nvkm-y += nvkm/subdev/gpio/gf119.o | 6 | nvkm-y += nvkm/subdev/gpio/gf119.o |
| 7 | nvkm-y += nvkm/subdev/gpio/gk104.o | 7 | nvkm-y += nvkm/subdev/gpio/gk104.o |
| 8 | nvkm-y += nvkm/subdev/gpio/ga102.o | ||
| @@ -0,0 +1,118 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "priv.h" | ||
| 23 | |||
| 24 | static void | ||
| 25 | ga102_gpio_reset(struct nvkm_gpio *gpio, u8 match) | ||
| 26 | { | ||
| 27 | struct nvkm_device *device = gpio->subdev.device; | ||
| 28 | struct nvkm_bios *bios = device->bios; | ||
| 29 | u8 ver, len; | ||
| 30 | u16 entry; | ||
| 31 | int ent = -1; | ||
| 32 | |||
| 33 | while ((entry = dcb_gpio_entry(bios, 0, ++ent, &ver, &len))) { | ||
| 34 | u32 data = nvbios_rd32(bios, entry); | ||
| 35 | u8 line = (data & 0x0000003f); | ||
| 36 | u8 defs = !!(data & 0x00000080); | ||
| 37 | u8 func = (data & 0x0000ff00) >> 8; | ||
| 38 | u8 unk0 = (data & 0x00ff0000) >> 16; | ||
| 39 | u8 unk1 = (data & 0x1f000000) >> 24; | ||
| 40 | |||
| 41 | if ( func == DCB_GPIO_UNUSED || | ||
| 42 | (match != DCB_GPIO_UNUSED && match != func)) | ||
| 43 | continue; | ||
| 44 | |||
| 45 | nvkm_gpio_set(gpio, 0, func, line, defs); | ||
| 46 | |||
| 47 | nvkm_mask(device, 0x021200 + (line * 4), 0xff, unk0); | ||
| 48 | if (unk1--) | ||
| 49 | nvkm_mask(device, 0x00d740 + (unk1 * 4), 0xff, line); | ||
| 50 | } | ||
| 51 | } | ||
| 52 | |||
| 53 | static int | ||
| 54 | ga102_gpio_drive(struct nvkm_gpio *gpio, int line, int dir, int out) | ||
| 55 | { | ||
| 56 | struct nvkm_device *device = gpio->subdev.device; | ||
| 57 | u32 data = ((dir ^ 1) << 13) | (out << 12); | ||
| 58 | nvkm_mask(device, 0x021200 + (line * 4), 0x00003000, data); | ||
| 59 | nvkm_mask(device, 0x00d604, 0x00000001, 0x00000001); /* update? */ | ||
| 60 | return 0; | ||
| 61 | } | ||
| 62 | |||
| 63 | static int | ||
| 64 | ga102_gpio_sense(struct nvkm_gpio *gpio, int line) | ||
| 65 | { | ||
| 66 | struct nvkm_device *device = gpio->subdev.device; | ||
| 67 | return !!(nvkm_rd32(device, 0x021200 + (line * 4)) & 0x00004000); | ||
| 68 | } | ||
| 69 | |||
| 70 | static void | ||
| 71 | ga102_gpio_intr_stat(struct nvkm_gpio *gpio, u32 *hi, u32 *lo) | ||
| 72 | { | ||
| 73 | struct nvkm_device *device = gpio->subdev.device; | ||
| 74 | u32 intr0 = nvkm_rd32(device, 0x021640); | ||
| 75 | u32 intr1 = nvkm_rd32(device, 0x02164c); | ||
| 76 | u32 stat0 = nvkm_rd32(device, 0x021648) & intr0; | ||
| 77 | u32 stat1 = nvkm_rd32(device, 0x021654) & intr1; | ||
| 78 | *lo = (stat1 & 0xffff0000) | (stat0 >> 16); | ||
| 79 | *hi = (stat1 << 16) | (stat0 & 0x0000ffff); | ||
| 80 | nvkm_wr32(device, 0x021640, intr0); | ||
| 81 | nvkm_wr32(device, 0x02164c, intr1); | ||
| 82 | } | ||
| 83 | |||
| 84 | static void | ||
| 85 | ga102_gpio_intr_mask(struct nvkm_gpio *gpio, u32 type, u32 mask, u32 data) | ||
| 86 | { | ||
| 87 | struct nvkm_device *device = gpio->subdev.device; | ||
| 88 | u32 inte0 = nvkm_rd32(device, 0x021648); | ||
| 89 | u32 inte1 = nvkm_rd32(device, 0x021654); | ||
| 90 | if (type & NVKM_GPIO_LO) | ||
| 91 | inte0 = (inte0 & ~(mask << 16)) | (data << 16); | ||
| 92 | if (type & NVKM_GPIO_HI) | ||
| 93 | inte0 = (inte0 & ~(mask & 0xffff)) | (data & 0xffff); | ||
| 94 | mask >>= 16; | ||
| 95 | data >>= 16; | ||
| 96 | if (type & NVKM_GPIO_LO) | ||
| 97 | inte1 = (inte1 & ~(mask << 16)) | (data << 16); | ||
| 98 | if (type & NVKM_GPIO_HI) | ||
| 99 | inte1 = (inte1 & ~mask) | data; | ||
| 100 | nvkm_wr32(device, 0x021648, inte0); | ||
| 101 | nvkm_wr32(device, 0x021654, inte1); | ||
| 102 | } | ||
| 103 | |||
| 104 | static const struct nvkm_gpio_func | ||
| 105 | ga102_gpio = { | ||
| 106 | .lines = 32, | ||
| 107 | .intr_stat = ga102_gpio_intr_stat, | ||
| 108 | .intr_mask = ga102_gpio_intr_mask, | ||
| 109 | .drive = ga102_gpio_drive, | ||
| 110 | .sense = ga102_gpio_sense, | ||
| 111 | .reset = ga102_gpio_reset, | ||
| 112 | }; | ||
| 113 | |||
| 114 | int | ||
| 115 | ga102_gpio_new(struct nvkm_device *device, int index, struct nvkm_gpio **pgpio) | ||
| 116 | { | ||
| 117 | return nvkm_gpio_new_(&ga102_gpio, device, index, pgpio); | ||
| 118 | } | ||
| @@ -7,6 +7,7 @@ nvkm-y += nvkm/subdev/i2c/g94.o · 6 unmodified lines | |||
| 7 | nvkm-y += nvkm/subdev/i2c/gf117.o | 7 | nvkm-y += nvkm/subdev/i2c/gf117.o |
| 8 | nvkm-y += nvkm/subdev/i2c/gf119.o | 8 | nvkm-y += nvkm/subdev/i2c/gf119.o |
| 9 | nvkm-y += nvkm/subdev/i2c/gk104.o | 9 | nvkm-y += nvkm/subdev/i2c/gk104.o |
| 10 | nvkm-y += nvkm/subdev/i2c/gk110.o | ||
| 10 | nvkm-y += nvkm/subdev/i2c/gm200.o | 11 | nvkm-y += nvkm/subdev/i2c/gm200.o |
| 11 | 12 | ||
| 12 | nvkm-y += nvkm/subdev/i2c/pad.o | 13 | nvkm-y += nvkm/subdev/i2c/pad.o |
| @@ -3,6 +3,13 @@ · 2 unmodified lines | |||
| 3 | #define __NVKM_I2C_AUX_H__ | 3 | #define __NVKM_I2C_AUX_H__ |
| 4 | #include "pad.h" | 4 | #include "pad.h" |
| 5 | 5 | ||
| 6 | static inline void | ||
| 7 | nvkm_i2c_aux_autodpcd(struct nvkm_i2c *i2c, int aux, bool enable) | ||
| 8 | { | ||
| 9 | if (i2c->func->aux_autodpcd) | ||
| 10 | i2c->func->aux_autodpcd(i2c, aux, false); | ||
| 11 | } | ||
| 12 | |||
| 6 | struct nvkm_i2c_aux_func { | 13 | struct nvkm_i2c_aux_func { |
| 7 | bool address_only; | 14 | bool address_only; |
| 8 | int (*xfer)(struct nvkm_i2c_aux *, bool retry, u8 type, | 15 | int (*xfer)(struct nvkm_i2c_aux *, bool retry, u8 type, |
| @@ -77,7 +77,8 @@ g94_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 76 unmodified lines | |||
| 77 | u8 type, u32 addr, u8 *data, u8 *size) | 77 | u8 type, u32 addr, u8 *data, u8 *size) |
| 78 | { | 78 | { |
| 79 | struct g94_i2c_aux *aux = g94_i2c_aux(obj); | 79 | struct g94_i2c_aux *aux = g94_i2c_aux(obj); |
| 80 | struct nvkm_device *device = aux->base.pad->i2c->subdev.device; | 80 | struct nvkm_i2c *i2c = aux->base.pad->i2c; |
| 81 | struct nvkm_device *device = i2c->subdev.device; | ||
| 81 | const u32 base = aux->ch * 0x50; | 82 | const u32 base = aux->ch * 0x50; |
| 82 | u32 ctrl, stat, timeout, retries = 0; | 83 | u32 ctrl, stat, timeout, retries = 0; |
| 83 | u32 xbuf[4] = {}; | 84 | u32 xbuf[4] = {}; |
| @@ -96,6 +97,8 @@ g94_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 12 unmodified lines | |||
| 96 | goto out; | 97 | goto out; |
| 97 | } | 98 | } |
| 98 | 99 | ||
| 100 | nvkm_i2c_aux_autodpcd(i2c, aux->ch, false); | ||
| 101 | |||
| 99 | if (!(type & 1)) { | 102 | if (!(type & 1)) { |
| 100 | memcpy(xbuf, data, *size); | 103 | memcpy(xbuf, data, *size); |
| 101 | for (i = 0; i < 16; i += 4) { | 104 | for (i = 0; i < 16; i += 4) { |
| @@ -128,7 +131,7 @@ g94_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 26 unmodified lines | |||
| 128 | if (!timeout--) { | 131 | if (!timeout--) { |
| 129 | AUX_ERR(&aux->base, "timeout %08x", ctrl); | 132 | AUX_ERR(&aux->base, "timeout %08x", ctrl); |
| 130 | ret = -EIO; | 133 | ret = -EIO; |
| 131 | goto out; | 134 | goto out_err; |
| 132 | } | 135 | } |
| 133 | } while (ctrl & 0x00010000); | 136 | } while (ctrl & 0x00010000); |
| 134 | ret = 0; | 137 | ret = 0; |
| @@ -154,7 +157,8 @@ g94_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 19 unmodified lines | |||
| 154 | memcpy(data, xbuf, *size); | 157 | memcpy(data, xbuf, *size); |
| 155 | *size = stat & 0x0000001f; | 158 | *size = stat & 0x0000001f; |
| 156 | } | 159 | } |
| 157 | 160 | out_err: | |
| 161 | nvkm_i2c_aux_autodpcd(i2c, aux->ch, true); | ||
| 158 | out: | 162 | out: |
| 159 | g94_i2c_aux_fini(aux); | 163 | g94_i2c_aux_fini(aux); |
| 160 | return ret < 0 ? ret : (stat & 0x000f0000) >> 16; | 164 | return ret < 0 ? ret : (stat & 0x000f0000) >> 16; |
| @@ -33,7 +33,7 @@ static void · 32 unmodified lines | |||
| 33 | gm200_i2c_aux_fini(struct gm200_i2c_aux *aux) | 33 | gm200_i2c_aux_fini(struct gm200_i2c_aux *aux) |
| 34 | { | 34 | { |
| 35 | struct nvkm_device *device = aux->base.pad->i2c->subdev.device; | 35 | struct nvkm_device *device = aux->base.pad->i2c->subdev.device; |
| 36 | nvkm_mask(device, 0x00d954 + (aux->ch * 0x50), 0x00310000, 0x00000000); | 36 | nvkm_mask(device, 0x00d954 + (aux->ch * 0x50), 0x00710000, 0x00000000); |
| 37 | } | 37 | } |
| 38 | 38 | ||
| 39 | static int | 39 | static int |
| @@ -54,10 +54,10 @@ gm200_i2c_aux_init(struct gm200_i2c_aux *aux) · 14 unmodified lines | |||
| 54 | AUX_ERR(&aux->base, "begin idle timeout %08x", ctrl); | 54 | AUX_ERR(&aux->base, "begin idle timeout %08x", ctrl); |
| 55 | return -EBUSY; | 55 | return -EBUSY; |
| 56 | } | 56 | } |
| 57 | } while (ctrl & 0x03010000); | 57 | } while (ctrl & 0x07010000); |
| 58 | 58 | ||
| 59 | /* set some magic, and wait up to 1ms for it to appear */ | 59 | /* set some magic, and wait up to 1ms for it to appear */ |
| 60 | nvkm_mask(device, 0x00d954 + (aux->ch * 0x50), 0x00300000, ureq); | 60 | nvkm_mask(device, 0x00d954 + (aux->ch * 0x50), 0x00700000, ureq); |
| 61 | timeout = 1000; | 61 | timeout = 1000; |
| 62 | do { | 62 | do { |
| 63 | ctrl = nvkm_rd32(device, 0x00d954 + (aux->ch * 0x50)); | 63 | ctrl = nvkm_rd32(device, 0x00d954 + (aux->ch * 0x50)); |
| @@ -67,7 +67,7 @@ gm200_i2c_aux_init(struct gm200_i2c_aux *aux) · 3 unmodified lines | |||
| 67 | gm200_i2c_aux_fini(aux); | 67 | gm200_i2c_aux_fini(aux); |
| 68 | return -EBUSY; | 68 | return -EBUSY; |
| 69 | } | 69 | } |
| 70 | } while ((ctrl & 0x03000000) != urep); | 70 | } while ((ctrl & 0x07000000) != urep); |
| 71 | 71 | ||
| 72 | return 0; | 72 | return 0; |
| 73 | } | 73 | } |
| @@ -77,7 +77,8 @@ gm200_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 3 unmodified lines | |||
| 77 | u8 type, u32 addr, u8 *data, u8 *size) | 77 | u8 type, u32 addr, u8 *data, u8 *size) |
| 78 | { | 78 | { |
| 79 | struct gm200_i2c_aux *aux = gm200_i2c_aux(obj); | 79 | struct gm200_i2c_aux *aux = gm200_i2c_aux(obj); |
| 80 | struct nvkm_device *device = aux->base.pad->i2c->subdev.device; | 80 | struct nvkm_i2c *i2c = aux->base.pad->i2c; |
| 81 | struct nvkm_device *device = i2c->subdev.device; | ||
| 81 | const u32 base = aux->ch * 0x50; | 82 | const u32 base = aux->ch * 0x50; |
| 82 | u32 ctrl, stat, timeout, retries = 0; | 83 | u32 ctrl, stat, timeout, retries = 0; |
| 83 | u32 xbuf[4] = {}; | 84 | u32 xbuf[4] = {}; |
| @@ -96,6 +97,8 @@ gm200_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 12 unmodified lines | |||
| 96 | goto out; | 97 | goto out; |
| 97 | } | 98 | } |
| 98 | 99 | ||
| 100 | nvkm_i2c_aux_autodpcd(i2c, aux->ch, false); | ||
| 101 | |||
| 99 | if (!(type & 1)) { | 102 | if (!(type & 1)) { |
| 100 | memcpy(xbuf, data, *size); | 103 | memcpy(xbuf, data, *size); |
| 101 | for (i = 0; i < 16; i += 4) { | 104 | for (i = 0; i < 16; i += 4) { |
| @@ -128,7 +131,7 @@ gm200_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 26 unmodified lines | |||
| 128 | if (!timeout--) { | 131 | if (!timeout--) { |
| 129 | AUX_ERR(&aux->base, "timeout %08x", ctrl); | 132 | AUX_ERR(&aux->base, "timeout %08x", ctrl); |
| 130 | ret = -EIO; | 133 | ret = -EIO; |
| 131 | goto out; | 134 | goto out_err; |
| 132 | } | 135 | } |
| 133 | } while (ctrl & 0x00010000); | 136 | } while (ctrl & 0x00010000); |
| 134 | ret = 0; | 137 | ret = 0; |
| @@ -155,6 +158,8 @@ gm200_i2c_aux_xfer(struct nvkm_i2c_aux *obj, bool retry, · 20 unmodified lines | |||
| 155 | *size = stat & 0x0000001f; | 158 | *size = stat & 0x0000001f; |
| 156 | } | 159 | } |
| 157 | 160 | ||
| 161 | out_err: | ||
| 162 | nvkm_i2c_aux_autodpcd(i2c, aux->ch, true); | ||
| 158 | out: | 163 | out: |
| 159 | gm200_i2c_aux_fini(aux); | 164 | gm200_i2c_aux_fini(aux); |
| 160 | return ret < 0 ? ret : (stat & 0x000f0000) >> 16; | 165 | return ret < 0 ? ret : (stat & 0x000f0000) >> 16; |
| @@ -0,0 +1,45 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "priv.h" | ||
| 23 | #include "pad.h" | ||
| 24 | |||
| 25 | static void | ||
| 26 | gk110_aux_autodpcd(struct nvkm_i2c *i2c, int aux, bool enable) | ||
| 27 | { | ||
| 28 | nvkm_mask(i2c->subdev.device, 0x00e4f8 + (aux * 0x50), 0x00010000, enable << 16); | ||
| 29 | } | ||
| 30 | |||
| 31 | static const struct nvkm_i2c_func | ||
| 32 | gk110_i2c = { | ||
| 33 | .pad_x_new = gf119_i2c_pad_x_new, | ||
| 34 | .pad_s_new = gf119_i2c_pad_s_new, | ||
| 35 | .aux = 4, | ||
| 36 | .aux_stat = gk104_aux_stat, | ||
| 37 | .aux_mask = gk104_aux_mask, | ||
| 38 | .aux_autodpcd = gk110_aux_autodpcd, | ||
| 39 | }; | ||
| 40 | |||
| 41 | int | ||
| 42 | gk110_i2c_new(struct nvkm_device *device, int index, struct nvkm_i2c **pi2c) | ||
| 43 | { | ||
| 44 | return nvkm_i2c_new_(&gk110_i2c, device, index, pi2c); | ||
| 45 | } | ||
| @@ -24,6 +24,12 @@ · 23 unmodified lines | |||
| 24 | #include "priv.h" | 24 | #include "priv.h" |
| 25 | #include "pad.h" | 25 | #include "pad.h" |
| 26 | 26 | ||
| 27 | static void | ||
| 28 | gm200_aux_autodpcd(struct nvkm_i2c *i2c, int aux, bool enable) | ||
| 29 | { | ||
| 30 | nvkm_mask(i2c->subdev.device, 0x00d968 + (aux * 0x50), 0x00010000, enable << 16); | ||
| 31 | } | ||
| 32 | |||
| 27 | static const struct nvkm_i2c_func | 33 | static const struct nvkm_i2c_func |
| 28 | gm200_i2c = { | 34 | gm200_i2c = { |
| 29 | .pad_x_new = gf119_i2c_pad_x_new, | 35 | .pad_x_new = gf119_i2c_pad_x_new, |
| @@ -31,6 +37,7 @@ gm200_i2c = { · 1 unmodified line | |||
| 31 | .aux = 8, | 37 | .aux = 8, |
| 32 | .aux_stat = gk104_aux_stat, | 38 | .aux_stat = gk104_aux_stat, |
| 33 | .aux_mask = gk104_aux_mask, | 39 | .aux_mask = gk104_aux_mask, |
| 40 | .aux_autodpcd = gm200_aux_autodpcd, | ||
| 34 | }; | 41 | }; |
| 35 | 42 | ||
| 36 | int | 43 | int |
| @@ -1,7 +1,7 @@ | |||
| 1 | /* SPDX-License-Identifier: MIT */ | 1 | /* SPDX-License-Identifier: MIT */ |
| 2 | #ifndef __NVKM_I2C_PAD_H__ | 2 | #ifndef __NVKM_I2C_PAD_H__ |
| 3 | #define __NVKM_I2C_PAD_H__ | 3 | #define __NVKM_I2C_PAD_H__ |
| 4 | #include <subdev/i2c.h> | 4 | #include "priv.h" |
| 5 | 5 | ||
| 6 | struct nvkm_i2c_pad { | 6 | struct nvkm_i2c_pad { |
| 7 | const struct nvkm_i2c_pad_func *func; | 7 | const struct nvkm_i2c_pad_func *func; |
| @@ -23,6 +23,10 @@ struct nvkm_i2c_func { · 22 unmodified lines | |||
| 23 | /* mask on/off interrupt types for a given set of auxch | 23 | /* mask on/off interrupt types for a given set of auxch |
| 24 | */ | 24 | */ |
| 25 | void (*aux_mask)(struct nvkm_i2c *, u32, u32, u32); | 25 | void (*aux_mask)(struct nvkm_i2c *, u32, u32, u32); |
| 26 | |||
| 27 | /* enable/disable HW-initiated DPCD reads | ||
| 28 | */ | ||
| 29 | void (*aux_autodpcd)(struct nvkm_i2c *, int aux, bool enable); | ||
| 26 | }; | 30 | }; |
| 27 | 31 | ||
| 28 | void g94_aux_stat(struct nvkm_i2c *, u32 *, u32 *, u32 *, u32 *); | 32 | void g94_aux_stat(struct nvkm_i2c *, u32 *, u32 *, u32 *, u32 *); |
| @@ -22,6 +22,7 @@ · 21 unmodified lines | |||
| 22 | * Authors: Ben Skeggs | 22 | * Authors: Ben Skeggs |
| 23 | */ | 23 | */ |
| 24 | #include "priv.h" | 24 | #include "priv.h" |
| 25 | #include <subdev/timer.h> | ||
| 25 | 26 | ||
| 26 | static void | 27 | static void |
| 27 | gf100_ibus_intr_hub(struct nvkm_subdev *ibus, int i) | 28 | gf100_ibus_intr_hub(struct nvkm_subdev *ibus, int i) |
| @@ -31,7 +32,6 @@ gf100_ibus_intr_hub(struct nvkm_subdev *ibus, int i) · 3 unmodified lines | |||
| 31 | u32 data = nvkm_rd32(device, 0x122124 + (i * 0x0400)); | 32 | u32 data = nvkm_rd32(device, 0x122124 + (i * 0x0400)); |
| 32 | u32 stat = nvkm_rd32(device, 0x122128 + (i * 0x0400)); | 33 | u32 stat = nvkm_rd32(device, 0x122128 + (i * 0x0400)); |
| 33 | nvkm_debug(ibus, "HUB%d: %06x %08x (%08x)\n", i, addr, data, stat); | 34 | nvkm_debug(ibus, "HUB%d: %06x %08x (%08x)\n", i, addr, data, stat); |
| 34 | nvkm_mask(device, 0x122128 + (i * 0x0400), 0x00000200, 0x00000000); | ||
| 35 | } | 35 | } |
| 36 | 36 | ||
| 37 | static void | 37 | static void |
| @@ -42,7 +42,6 @@ gf100_ibus_intr_rop(struct nvkm_subdev *ibus, int i) · 4 unmodified lines | |||
| 42 | u32 data = nvkm_rd32(device, 0x124124 + (i * 0x0400)); | 42 | u32 data = nvkm_rd32(device, 0x124124 + (i * 0x0400)); |
| 43 | u32 stat = nvkm_rd32(device, 0x124128 + (i * 0x0400)); | 43 | u32 stat = nvkm_rd32(device, 0x124128 + (i * 0x0400)); |
| 44 | nvkm_debug(ibus, "ROP%d: %06x %08x (%08x)\n", i, addr, data, stat); | 44 | nvkm_debug(ibus, "ROP%d: %06x %08x (%08x)\n", i, addr, data, stat); |
| 45 | nvkm_mask(device, 0x124128 + (i * 0x0400), 0x00000200, 0x00000000); | ||
| 46 | } | 45 | } |
| 47 | 46 | ||
| 48 | static void | 47 | static void |
| @@ -53,7 +52,6 @@ gf100_ibus_intr_gpc(struct nvkm_subdev *ibus, int i) · 4 unmodified lines | |||
| 53 | u32 data = nvkm_rd32(device, 0x128124 + (i * 0x0400)); | 52 | u32 data = nvkm_rd32(device, 0x128124 + (i * 0x0400)); |
| 54 | u32 stat = nvkm_rd32(device, 0x128128 + (i * 0x0400)); | 53 | u32 stat = nvkm_rd32(device, 0x128128 + (i * 0x0400)); |
| 55 | nvkm_debug(ibus, "GPC%d: %06x %08x (%08x)\n", i, addr, data, stat); | 54 | nvkm_debug(ibus, "GPC%d: %06x %08x (%08x)\n", i, addr, data, stat); |
| 56 | nvkm_mask(device, 0x128128 + (i * 0x0400), 0x00000200, 0x00000000); | ||
| 57 | } | 55 | } |
| 58 | 56 | ||
| 59 | void | 57 | void |
| @@ -90,6 +88,12 @@ gf100_ibus_intr(struct nvkm_subdev *ibus) · 30 unmodified lines | |||
| 90 | intr1 &= ~stat; | 88 | intr1 &= ~stat; |
| 91 | } | 89 | } |
| 92 | } | 90 | } |
| 91 | |||
| 92 | nvkm_mask(device, 0x121c4c, 0x0000003f, 0x00000002); | ||
| 93 | nvkm_msec(device, 2000, | ||
| 94 | if (!(nvkm_rd32(device, 0x121c4c) & 0x0000003f)) | ||
| 95 | break; | ||
| 96 | ); | ||
| 93 | } | 97 | } |
| 94 | 98 | ||
| 95 | static int | 99 | static int |
| @@ -22,6 +22,7 @@ · 21 unmodified lines | |||
| 22 | * Authors: Ben Skeggs | 22 | * Authors: Ben Skeggs |
| 23 | */ | 23 | */ |
| 24 | #include "priv.h" | 24 | #include "priv.h" |
| 25 | #include <subdev/timer.h> | ||
| 25 | 26 | ||
| 26 | static void | 27 | static void |
| 27 | gk104_ibus_intr_hub(struct nvkm_subdev *ibus, int i) | 28 | gk104_ibus_intr_hub(struct nvkm_subdev *ibus, int i) |
| @@ -31,7 +32,6 @@ gk104_ibus_intr_hub(struct nvkm_subdev *ibus, int i) · 3 unmodified lines | |||
| 31 | u32 data = nvkm_rd32(device, 0x122124 + (i * 0x0800)); | 32 | u32 data = nvkm_rd32(device, 0x122124 + (i * 0x0800)); |
| 32 | u32 stat = nvkm_rd32(device, 0x122128 + (i * 0x0800)); | 33 | u32 stat = nvkm_rd32(device, 0x122128 + (i * 0x0800)); |
| 33 | nvkm_debug(ibus, "HUB%d: %06x %08x (%08x)\n", i, addr, data, stat); | 34 | nvkm_debug(ibus, "HUB%d: %06x %08x (%08x)\n", i, addr, data, stat); |
| 34 | nvkm_mask(device, 0x122128 + (i * 0x0800), 0x00000200, 0x00000000); | ||
| 35 | } | 35 | } |
| 36 | 36 | ||
| 37 | static void | 37 | static void |
| @@ -42,7 +42,6 @@ gk104_ibus_intr_rop(struct nvkm_subdev *ibus, int i) · 4 unmodified lines | |||
| 42 | u32 data = nvkm_rd32(device, 0x124124 + (i * 0x0800)); | 42 | u32 data = nvkm_rd32(device, 0x124124 + (i * 0x0800)); |
| 43 | u32 stat = nvkm_rd32(device, 0x124128 + (i * 0x0800)); | 43 | u32 stat = nvkm_rd32(device, 0x124128 + (i * 0x0800)); |
| 44 | nvkm_debug(ibus, "ROP%d: %06x %08x (%08x)\n", i, addr, data, stat); | 44 | nvkm_debug(ibus, "ROP%d: %06x %08x (%08x)\n", i, addr, data, stat); |
| 45 | nvkm_mask(device, 0x124128 + (i * 0x0800), 0x00000200, 0x00000000); | ||
| 46 | } | 45 | } |
| 47 | 46 | ||
| 48 | static void | 47 | static void |
| @@ -53,7 +52,6 @@ gk104_ibus_intr_gpc(struct nvkm_subdev *ibus, int i) · 4 unmodified lines | |||
| 53 | u32 data = nvkm_rd32(device, 0x128124 + (i * 0x0800)); | 52 | u32 data = nvkm_rd32(device, 0x128124 + (i * 0x0800)); |
| 54 | u32 stat = nvkm_rd32(device, 0x128128 + (i * 0x0800)); | 53 | u32 stat = nvkm_rd32(device, 0x128128 + (i * 0x0800)); |
| 55 | nvkm_debug(ibus, "GPC%d: %06x %08x (%08x)\n", i, addr, data, stat); | 54 | nvkm_debug(ibus, "GPC%d: %06x %08x (%08x)\n", i, addr, data, stat); |
| 56 | nvkm_mask(device, 0x128128 + (i * 0x0800), 0x00000200, 0x00000000); | ||
| 57 | } | 55 | } |
| 58 | 56 | ||
| 59 | void | 57 | void |
| @@ -90,6 +88,12 @@ gk104_ibus_intr(struct nvkm_subdev *ibus) · 30 unmodified lines | |||
| 90 | intr1 &= ~stat; | 88 | intr1 &= ~stat; |
| 91 | } | 89 | } |
| 92 | } | 90 | } |
| 91 | |||
| 92 | nvkm_mask(device, 0x12004c, 0x0000003f, 0x00000002); | ||
| 93 | nvkm_msec(device, 2000, | ||
| 94 | if (!(nvkm_rd32(device, 0x12004c) & 0x0000003f)) | ||
| 95 | break; | ||
| 96 | ); | ||
| 93 | } | 97 | } |
| 94 | 98 | ||
| 95 | static int | 99 | static int |
| @@ -14,3 +14,4 @@ nvkm-y += nvkm/subdev/mc/gk20a.o · 13 unmodified lines | |||
| 14 | nvkm-y += nvkm/subdev/mc/gp100.o | 14 | nvkm-y += nvkm/subdev/mc/gp100.o |
| 15 | nvkm-y += nvkm/subdev/mc/gp10b.o | 15 | nvkm-y += nvkm/subdev/mc/gp10b.o |
| 16 | nvkm-y += nvkm/subdev/mc/tu102.o | 16 | nvkm-y += nvkm/subdev/mc/tu102.o |
| 17 | nvkm-y += nvkm/subdev/mc/ga100.o | ||
| @@ -0,0 +1,74 @@ | |||
| 1 | /* | ||
| 2 | * Copyright 2021 Red Hat Inc. | ||
| 3 | * | ||
| 4 | * Permission is hereby granted, free of charge, to any person obtaining a | ||
| 5 | * copy of this software and associated documentation files (the "Software"), | ||
| 6 | * to deal in the Software without restriction, including without limitation | ||
| 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, | ||
| 8 | * and/or sell copies of the Software, and to permit persons to whom the | ||
| 9 | * Software is furnished to do so, subject to the following conditions: | ||
| 10 | * | ||
| 11 | * The above copyright notice and this permission notice shall be included in | ||
| 12 | * all copies or substantial portions of the Software. | ||
| 13 | * | ||
| 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
| 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
| 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL | ||
| 17 | * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
| 18 | * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
| 19 | * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
| 20 | * OTHER DEALINGS IN THE SOFTWARE. | ||
| 21 | */ | ||
| 22 | #include "priv.h" | ||
| 23 | |||
| 24 | static void | ||
| 25 | ga100_mc_intr_unarm(struct nvkm_mc *mc) | ||
| 26 | { | ||
| 27 | nvkm_wr32(mc->subdev.device, 0xb81610, 0x00000004); | ||
| 28 | } | ||
| 29 | |||
| 30 | static void | ||
| 31 | ga100_mc_intr_rearm(struct nvkm_mc *mc) | ||
| 32 | { | ||
| 33 | nvkm_wr32(mc->subdev.device, 0xb81608, 0x00000004); | ||
| 34 | } | ||
| 35 | |||
| 36 | static void | ||
| 37 | ga100_mc_intr_mask(struct nvkm_mc *mc, u32 mask, u32 intr) | ||
| 38 | { | ||
| 39 | nvkm_wr32(mc->subdev.device, 0xb81210, mask & intr ); | ||
| 40 | nvkm_wr32(mc->subdev.device, 0xb81410, mask & ~(mask & intr)); | ||
| 41 | } | ||
| 42 | |||
| 43 | static u32 | ||
| 44 | ga100_mc_intr_stat(struct nvkm_mc *mc) | ||
| 45 | { | ||
| 46 | u32 intr_top = nvkm_rd32(mc->subdev.device, 0xb81600), intr = 0x00000000; | ||
| 47 | if (intr_top & 0x00000004) | ||
| 48 | intr = nvkm_mask(mc->subdev.device, 0xb81010, 0x00000000, 0x00000000); | ||
| 49 | return intr; | ||
| 50 | } | ||
| 51 | |||
| 52 | static void | ||
| 53 | ga100_mc_init(struct nvkm_mc *mc) | ||
| 54 | { | ||
| 55 | nv50_mc_init(mc); | ||
| 56 | nvkm_wr32(mc->subdev.device, 0xb81210, 0xffffffff); | ||
| 57 | } | ||
| 58 | |||
| 59 | static const struct nvkm_mc_func | ||
| 60 | ga100_mc = { | ||
| 61 | .init = ga100_mc_init, | ||
| 62 | .intr = gp100_mc_intr, | ||
| 63 | .intr_unarm = ga100_mc_intr_unarm, | ||
| 64 | .intr_rearm = ga100_mc_intr_rearm, | ||
| 65 | .intr_mask = ga100_mc_intr_mask, | ||
| 66 | .intr_stat = ga100_mc_intr_stat, | ||
| 67 | .reset = gk104_mc_reset, | ||
| 68 | }; | ||
| 69 | |||
| 70 | int | ||
| 71 | ga100_mc_new(struct nvkm_device *device, int index, struct nvkm_mc **pmc) | ||
| 72 | { | ||
| 73 | return nvkm_mc_new_(&ga100_mc, device, index, pmc); | ||
| 74 | } | ||
| @@ -316,9 +316,9 @@ nvkm_mmu_vram(struct nvkm_mmu *mmu) · 315 unmodified lines | |||
| 316 | { | 316 | { |
| 317 | struct nvkm_device *device = mmu->subdev.device; | 317 | struct nvkm_device *device = mmu->subdev.device; |
| 318 | struct nvkm_mm *mm = &device->fb->ram->vram; | 318 | struct nvkm_mm *mm = &device->fb->ram->vram; |
| 319 | const u32 sizeN = nvkm_mm_heap_size(mm, NVKM_RAM_MM_NORMAL); | 319 | const u64 sizeN = nvkm_mm_heap_size(mm, NVKM_RAM_MM_NORMAL); |
| 320 | const u32 sizeU = nvkm_mm_heap_size(mm, NVKM_RAM_MM_NOMAP); | 320 | const u64 sizeU = nvkm_mm_heap_size(mm, NVKM_RAM_MM_NOMAP); |
| 321 | const u32 sizeM = nvkm_mm_heap_size(mm, NVKM_RAM_MM_MIXED); | 321 | const u64 sizeM = nvkm_mm_heap_size(mm, NVKM_RAM_MM_MIXED); |
| 322 | u8 type = NVKM_MEM_KIND * !!mmu->func->kind; | 322 | u8 type = NVKM_MEM_KIND * !!mmu->func->kind; |
| 323 | u8 heap = NVKM_MEM_VRAM; | 323 | u8 heap = NVKM_MEM_VRAM; |
| 324 | int heapM, heapN, heapU; | 324 | int heapM, heapN, heapU; |
| @@ -730,9 +730,6 @@ int radeon_ttm_init(struct radeon_device *rdev) · 729 unmodified lines | |||
| 730 | } | 730 | } |
| 731 | rdev->mman.initialized = true; | 731 | rdev->mman.initialized = true; |
| 732 | 732 | ||
| 733 | ttm_pool_init(&rdev->mman.bdev.pool, rdev->dev, rdev->need_swiotlb, | ||
| 734 | dma_addressing_limited(&rdev->pdev->dev)); | ||
| 735 | |||
| 736 | r = radeon_ttm_init_vram(rdev); | 733 | r = radeon_ttm_init_vram(rdev); |
| 737 | if (r) { | 734 | if (r) { |
| 738 | DRM_ERROR("Failed initializing VRAM heap.\n"); | 735 | DRM_ERROR("Failed initializing VRAM heap.\n"); |
| @@ -689,6 +689,30 @@ static void sun4i_tcon1_mode_set(struct sun4i_tcon *tcon, · 688 unmodified lines | |||
| 689 | SUN4I_TCON1_BASIC5_V_SYNC(vsync) | | 689 | SUN4I_TCON1_BASIC5_V_SYNC(vsync) | |
| 690 | SUN4I_TCON1_BASIC5_H_SYNC(hsync)); | 690 | SUN4I_TCON1_BASIC5_H_SYNC(hsync)); |
| 691 | 691 | ||
| 692 | /* Setup the polarity of multiple signals */ | ||
| 693 | if (tcon->quirks->polarity_in_ch0) { | ||
| 694 | val = 0; | ||
| 695 | |||
| 696 | if (mode->flags & DRM_MODE_FLAG_PHSYNC) | ||
| 697 | val |= SUN4I_TCON0_IO_POL_HSYNC_POSITIVE; | ||
| 698 | |||
| 699 | if (mode->flags & DRM_MODE_FLAG_PVSYNC) | ||
| 700 | val |= SUN4I_TCON0_IO_POL_VSYNC_POSITIVE; | ||
| 701 | |||
| 702 | regmap_write(tcon->regs, SUN4I_TCON0_IO_POL_REG, val); | ||
| 703 | } else { | ||
| 704 | /* according to vendor driver, this bit must be always set */ | ||
| 705 | val = SUN4I_TCON1_IO_POL_UNKNOWN; | ||
| 706 | |||
| 707 | if (mode->flags & DRM_MODE_FLAG_PHSYNC) | ||
| 708 | val |= SUN4I_TCON1_IO_POL_HSYNC_POSITIVE; | ||
| 709 | |||
| 710 | if (mode->flags & DRM_MODE_FLAG_PVSYNC) | ||
| 711 | val |= SUN4I_TCON1_IO_POL_VSYNC_POSITIVE; | ||
| 712 | |||
| 713 | regmap_write(tcon->regs, SUN4I_TCON1_IO_POL_REG, val); | ||
| 714 | } | ||
| 715 | |||
| 692 | /* Map output pins to channel 1 */ | 716 | /* Map output pins to channel 1 */ |
| 693 | regmap_update_bits(tcon->regs, SUN4I_TCON_GCTL_REG, | 717 | regmap_update_bits(tcon->regs, SUN4I_TCON_GCTL_REG, |
| 694 | SUN4I_TCON_GCTL_IOMAP_MASK, | 718 | SUN4I_TCON_GCTL_IOMAP_MASK, |
| @@ -1517,6 +1541,7 @@ static const struct sun4i_tcon_quirks sun8i_a83t_tv_quirks = { · 822 unmodified lines | |||
| 1517 | 1541 | ||
| 1518 | static const struct sun4i_tcon_quirks sun8i_r40_tv_quirks = { | 1542 | static const struct sun4i_tcon_quirks sun8i_r40_tv_quirks = { |
| 1519 | .has_channel_1 = true, | 1543 | .has_channel_1 = true, |
| 1544 | .polarity_in_ch0 = true, | ||
| 1520 | .set_mux = sun8i_r40_tcon_tv_set_mux, | 1545 | .set_mux = sun8i_r40_tcon_tv_set_mux, |
| 1521 | }; | 1546 | }; |
| 1522 | 1547 | ||
| @@ -153,6 +153,11 @@ · 152 unmodified lines | |||
| 153 | #define SUN4I_TCON1_BASIC5_V_SYNC(height) (((height) - 1) & 0x3ff) | 153 | #define SUN4I_TCON1_BASIC5_V_SYNC(height) (((height) - 1) & 0x3ff) |
| 154 | 154 | ||
| 155 | #define SUN4I_TCON1_IO_POL_REG 0xf0 | 155 | #define SUN4I_TCON1_IO_POL_REG 0xf0 |
| 156 | /* there is no documentation about this bit */ | ||
| 157 | #define SUN4I_TCON1_IO_POL_UNKNOWN BIT(26) | ||
| 158 | #define SUN4I_TCON1_IO_POL_HSYNC_POSITIVE BIT(25) | ||
| 159 | #define SUN4I_TCON1_IO_POL_VSYNC_POSITIVE BIT(24) | ||
| 160 | |||
| 156 | #define SUN4I_TCON1_IO_TRI_REG 0xf4 | 161 | #define SUN4I_TCON1_IO_TRI_REG 0xf4 |
| 157 | 162 | ||
| 158 | #define SUN4I_TCON_ECC_FIFO_REG 0xf8 | 163 | #define SUN4I_TCON_ECC_FIFO_REG 0xf8 |
| @@ -235,6 +240,7 @@ struct sun4i_tcon_quirks { · 76 unmodified lines | |||
| 235 | bool needs_de_be_mux; /* sun6i needs mux to select backend */ | 240 | bool needs_de_be_mux; /* sun6i needs mux to select backend */ |
| 236 | bool needs_edp_reset; /* a80 edp reset needed for tcon0 access */ | 241 | bool needs_edp_reset; /* a80 edp reset needed for tcon0 access */ |
| 237 | bool supports_lvds; /* Does the TCON support an LVDS output? */ | 242 | bool supports_lvds; /* Does the TCON support an LVDS output? */ |
| 243 | bool polarity_in_ch0; /* some tcon1 channels have polarity bits in tcon0 pol register */ | ||
| 238 | u8 dclk_min_div; /* minimum divider for TCON0 DCLK */ | 244 | u8 dclk_min_div; /* minimum divider for TCON0 DCLK */ |
| 239 | 245 | ||
| 240 | /* callback to handle tcon muxing options */ | 246 | /* callback to handle tcon muxing options */ |
| @@ -21,8 +21,7 @@ static void sun8i_dw_hdmi_encoder_mode_set(struct drm_encoder *encoder, · 20 unmodified lines | |||
| 21 | { | 21 | { |
| 22 | struct sun8i_dw_hdmi *hdmi = encoder_to_sun8i_dw_hdmi(encoder); | 22 | struct sun8i_dw_hdmi *hdmi = encoder_to_sun8i_dw_hdmi(encoder); |
| 23 | 23 | ||
| 24 | if (hdmi->quirks->set_rate) | 24 | clk_set_rate(hdmi->clk_tmds, mode->crtc_clock * 1000); |
| 25 | clk_set_rate(hdmi->clk_tmds, mode->crtc_clock * 1000); | ||
| 26 | } | 25 | } |
| 27 | 26 | ||
| 28 | static const struct drm_encoder_helper_funcs | 27 | static const struct drm_encoder_helper_funcs |
| @@ -48,11 +47,9 @@ sun8i_dw_hdmi_mode_valid_h6(struct dw_hdmi *hdmi, void *data, · 19 unmodified lines | |||
| 48 | { | 47 | { |
| 49 | /* | 48 | /* |
| 50 | * Controller support maximum of 594 MHz, which correlates to | 49 | * Controller support maximum of 594 MHz, which correlates to |
| 51 | * 4K@60Hz 4:4:4 or RGB. However, for frequencies greater than | 50 | * 4K@60Hz 4:4:4 or RGB. |
| 52 | * 340 MHz scrambling has to be enabled. Because scrambling is | ||
| 53 | * not yet implemented, just limit to 340 MHz for now. | ||
| 54 | */ | 51 | */ |
| 55 | if (mode->clock > 340000) | 52 | if (mode->clock > 594000) |
| 56 | return MODE_CLOCK_HIGH; | 53 | return MODE_CLOCK_HIGH; |
| 57 | 54 | ||
| 58 | return MODE_OK; | 55 | return MODE_OK; |
| @@ -295,7 +292,6 @@ static int sun8i_dw_hdmi_remove(struct platform_device *pdev) · 236 unmodified lines | |||
| 295 | 292 | ||
| 296 | static const struct sun8i_dw_hdmi_quirks sun8i_a83t_quirks = { | 293 | static const struct sun8i_dw_hdmi_quirks sun8i_a83t_quirks = { |
| 297 | .mode_valid = sun8i_dw_hdmi_mode_valid_a83t, | 294 | .mode_valid = sun8i_dw_hdmi_mode_valid_a83t, |
| 298 | .set_rate = true, | ||
| 299 | }; | 295 | }; |
| 300 | 296 | ||
| 301 | static const struct sun8i_dw_hdmi_quirks sun50i_h6_quirks = { | 297 | static const struct sun8i_dw_hdmi_quirks sun50i_h6_quirks = { |
| @@ -179,7 +179,6 @@ struct sun8i_dw_hdmi_quirks { · 178 unmodified lines | |||
| 179 | enum drm_mode_status (*mode_valid)(struct dw_hdmi *hdmi, void *data, | 179 | enum drm_mode_status (*mode_valid)(struct dw_hdmi *hdmi, void *data, |
| 180 | const struct drm_display_info *info, | 180 | const struct drm_display_info *info, |
| 181 | const struct drm_display_mode *mode); | 181 | const struct drm_display_mode *mode); |
| 182 | unsigned int set_rate : 1; | ||
| 183 | unsigned int use_drm_infoframe : 1; | 182 | unsigned int use_drm_infoframe : 1; |
| 184 | }; | 183 | }; |
| 185 | 184 | ||
| @@ -104,29 +104,21 @@ static const struct dw_hdmi_mpll_config sun50i_h6_mpll_cfg[] = { · 103 unmodified lines | |||
| 104 | 104 | ||
| 105 | static const struct dw_hdmi_curr_ctrl sun50i_h6_cur_ctr[] = { | 105 | static const struct dw_hdmi_curr_ctrl sun50i_h6_cur_ctr[] = { |
| 106 | /* pixelclk bpp8 bpp10 bpp12 */ | 106 | /* pixelclk bpp8 bpp10 bpp12 */ |
| 107 | { 25175000, { 0x0000, 0x0000, 0x0000 }, }, | ||
| 108 | { 27000000, { 0x0012, 0x0000, 0x0000 }, }, | 107 | { 27000000, { 0x0012, 0x0000, 0x0000 }, }, |
| 109 | { 59400000, { 0x0008, 0x0008, 0x0008 }, }, | 108 | { 74250000, { 0x0013, 0x001a, 0x001b }, }, |
| 110 | { 72000000, { 0x0008, 0x0008, 0x001b }, }, | 109 | { 148500000, { 0x0019, 0x0033, 0x0034 }, }, |
| 111 | { 74250000, { 0x0013, 0x0013, 0x0013 }, }, | 110 | { 297000000, { 0x0019, 0x001b, 0x001b }, }, |
| 112 | { 90000000, { 0x0008, 0x001a, 0x001b }, }, | 111 | { 594000000, { 0x0010, 0x001b, 0x001b }, }, |
| 113 | { 118800000, { 0x001b, 0x001a, 0x001b }, }, | ||
| 114 | { 144000000, { 0x001b, 0x001a, 0x0034 }, }, | ||
| 115 | { 180000000, { 0x001b, 0x0033, 0x0034 }, }, | ||
| 116 | { 216000000, { 0x0036, 0x0033, 0x0034 }, }, | ||
| 117 | { 237600000, { 0x0036, 0x0033, 0x001b }, }, | ||
| 118 | { 288000000, { 0x0036, 0x001b, 0x001b }, }, | ||
| 119 | { 297000000, { 0x0019, 0x001b, 0x0019 }, }, | ||
| 120 | { 330000000, { 0x0036, 0x001b, 0x001b }, }, | ||
| 121 | { 594000000, { 0x003f, 0x001b, 0x001b }, }, | ||
| 122 | { ~0UL, { 0x0000, 0x0000, 0x0000 }, } | 112 | { ~0UL, { 0x0000, 0x0000, 0x0000 }, } |
| 123 | }; | 113 | }; |
| 124 | 114 | ||
| 125 | static const struct dw_hdmi_phy_config sun50i_h6_phy_config[] = { | 115 | static const struct dw_hdmi_phy_config sun50i_h6_phy_config[] = { |
| 126 | /*pixelclk symbol term vlev*/ | 116 | /*pixelclk symbol term vlev*/ |
| 127 | { 74250000, 0x8009, 0x0004, 0x0232}, | 117 | { 27000000, 0x8009, 0x0007, 0x02b0 }, |
| 128 | { 148500000, 0x8029, 0x0004, 0x0273}, | 118 | { 74250000, 0x8009, 0x0006, 0x022d }, |
| 129 | { 594000000, 0x8039, 0x0004, 0x014a}, | 119 | { 148500000, 0x8029, 0x0006, 0x0270 }, |
| 120 | { 297000000, 0x8039, 0x0005, 0x01ab }, | ||
| 121 | { 594000000, 0x8029, 0x0000, 0x008a }, | ||
| 130 | { ~0UL, 0x0000, 0x0000, 0x0000} | 122 | { ~0UL, 0x0000, 0x0000, 0x0000} |
| 131 | }; | 123 | }; |
| 132 | 124 | ||
| @@ -33,6 +33,7 @@ · 32 unmodified lines | |||
| 33 | 33 | ||
| 34 | #include <linux/module.h> | 34 | #include <linux/module.h> |
| 35 | #include <linux/dma-mapping.h> | 35 | #include <linux/dma-mapping.h> |
| 36 | #include <linux/highmem.h> | ||
| 36 | 37 | ||
| 37 | #ifdef CONFIG_X86 | 38 | #ifdef CONFIG_X86 |
| 38 | #include <asm/set_memory.h> | 39 | #include <asm/set_memory.h> |
| @@ -66,7 +67,7 @@ static struct ttm_pool_type global_uncached[MAX_ORDER]; · 27 unmodified lines | |||
| 66 | static struct ttm_pool_type global_dma32_write_combined[MAX_ORDER]; | 67 | static struct ttm_pool_type global_dma32_write_combined[MAX_ORDER]; |
| 67 | static struct ttm_pool_type global_dma32_uncached[MAX_ORDER]; | 68 | static struct ttm_pool_type global_dma32_uncached[MAX_ORDER]; |
| 68 | 69 | ||
| 69 | static spinlock_t shrinker_lock; | 70 | static struct mutex shrinker_lock; |
| 70 | static struct list_head shrinker_list; | 71 | static struct list_head shrinker_list; |
| 71 | static struct shrinker mm_shrinker; | 72 | static struct shrinker mm_shrinker; |
| 72 | 73 | ||
| @@ -79,12 +80,13 @@ static struct page *ttm_pool_alloc_page(struct ttm_pool *pool, gfp_t gfp_flags, · 6 unmodified lines | |||
| 79 | struct page *p; | 80 | struct page *p; |
| 80 | void *vaddr; | 81 | void *vaddr; |
| 81 | 82 | ||
| 82 | if (order) { | 83 | /* Don't set the __GFP_COMP flag for higher order allocations. |
| 83 | gfp_flags |= GFP_TRANSHUGE_LIGHT | __GFP_NORETRY | | 84 | * Mapping pages directly into an userspace process and calling |
| 85 | * put_page() on a TTM allocated page is illegal. | ||
| 86 | */ | ||
| 87 | if (order) | ||
| 88 | gfp_flags |= __GFP_NOMEMALLOC | __GFP_NORETRY | __GFP_NOWARN | | ||
| 84 | __GFP_KSWAPD_RECLAIM; | 89 | __GFP_KSWAPD_RECLAIM; |
| 85 | gfp_flags &= ~__GFP_MOVABLE; | ||
| 86 | gfp_flags &= ~__GFP_COMP; | ||
| 87 | } | ||
| 88 | 90 | ||
| 89 | if (!pool->use_dma_alloc) { | 91 | if (!pool->use_dma_alloc) { |
| 90 | p = alloc_pages(gfp_flags, order); | 92 | p = alloc_pages(gfp_flags, order); |
| @@ -190,7 +192,7 @@ static int ttm_pool_map(struct ttm_pool *pool, unsigned int order, · 99 unmodified lines | |||
| 190 | size_t size = (1ULL << order) * PAGE_SIZE; | 192 | size_t size = (1ULL << order) * PAGE_SIZE; |
| 191 | 193 | ||
| 192 | addr = dma_map_page(pool->dev, p, 0, size, DMA_BIDIRECTIONAL); | 194 | addr = dma_map_page(pool->dev, p, 0, size, DMA_BIDIRECTIONAL); |
| 193 | if (dma_mapping_error(pool->dev, **dma_addr)) | 195 | if (dma_mapping_error(pool->dev, addr)) |
| 194 | return -EFAULT; | 196 | return -EFAULT; |
| 195 | } | 197 | } |
| 196 | 198 | ||
| @@ -217,6 +219,15 @@ static void ttm_pool_unmap(struct ttm_pool *pool, dma_addr_t dma_addr, · 20 unmodified lines | |||
| 217 | /* Give pages into a specific pool_type */ | 219 | /* Give pages into a specific pool_type */ |
| 218 | static void ttm_pool_type_give(struct ttm_pool_type *pt, struct page *p) | 220 | static void ttm_pool_type_give(struct ttm_pool_type *pt, struct page *p) |
| 219 | { | 221 | { |
| 222 | unsigned int i, num_pages = 1 << pt->order; | ||
| 223 | |||
| 224 | for (i = 0; i < num_pages; ++i) { | ||
| 225 | if (PageHighMem(p)) | ||
| 226 | clear_highpage(p + i); | ||
| 227 | else | ||
| 228 | clear_page(page_address(p + i)); | ||
| 229 | } | ||
| 230 | |||
| 220 | spin_lock(&pt->lock); | 231 | spin_lock(&pt->lock); |
| 221 | list_add(&p->lru, &pt->pages); | 232 | list_add(&p->lru, &pt->pages); |
| 222 | spin_unlock(&pt->lock); | 233 | spin_unlock(&pt->lock); |
| @@ -249,9 +260,9 @@ static void ttm_pool_type_init(struct ttm_pool_type *pt, struct ttm_pool *pool, · 26 unmodified lines | |||
| 249 | spin_lock_init(&pt->lock); | 260 | spin_lock_init(&pt->lock); |
| 250 | INIT_LIST_HEAD(&pt->pages); | 261 | INIT_LIST_HEAD(&pt->pages); |
| 251 | 262 | ||
| 252 | spin_lock(&shrinker_lock); | 263 | mutex_lock(&shrinker_lock); |
| 253 | list_add_tail(&pt->shrinker_list, &shrinker_list); | 264 | list_add_tail(&pt->shrinker_list, &shrinker_list); |
| 254 | spin_unlock(&shrinker_lock); | 265 | mutex_unlock(&shrinker_lock); |
| 255 | } | 266 | } |
| 256 | 267 | ||
| 257 | /* Remove a pool_type from the global shrinker list and free all pages */ | 268 | /* Remove a pool_type from the global shrinker list and free all pages */ |
| @@ -259,9 +270,9 @@ static void ttm_pool_type_fini(struct ttm_pool_type *pt) · 1 unmodified line | |||
| 259 | { | 270 | { |
| 260 | struct page *p, *tmp; | 271 | struct page *p, *tmp; |
| 261 | 272 | ||
| 262 | spin_lock(&shrinker_lock); | 273 | mutex_lock(&shrinker_lock); |
| 263 | list_del(&pt->shrinker_list); | 274 | list_del(&pt->shrinker_list); |
| 264 | spin_unlock(&shrinker_lock); | 275 | mutex_unlock(&shrinker_lock); |
| 265 | 276 | ||
| 266 | list_for_each_entry_safe(p, tmp, &pt->pages, lru) | 277 | list_for_each_entry_safe(p, tmp, &pt->pages, lru) |
| 267 | ttm_pool_free_page(pt->pool, pt->caching, pt->order, p); | 278 | ttm_pool_free_page(pt->pool, pt->caching, pt->order, p); |
| @@ -302,7 +313,7 @@ static unsigned int ttm_pool_shrink(void) · 34 unmodified lines | |||
| 302 | unsigned int num_freed; | 313 | unsigned int num_freed; |
| 303 | struct page *p; | 314 | struct page *p; |
| 304 | 315 | ||
| 305 | spin_lock(&shrinker_lock); | 316 | mutex_lock(&shrinker_lock); |
| 306 | pt = list_first_entry(&shrinker_list, typeof(*pt), shrinker_list); | 317 | pt = list_first_entry(&shrinker_list, typeof(*pt), shrinker_list); |
| 307 | 318 | ||
| 308 | p = ttm_pool_type_take(pt); | 319 | p = ttm_pool_type_take(pt); |
| @@ -314,7 +325,7 @@ static unsigned int ttm_pool_shrink(void) · 5 unmodified lines | |||
| 314 | } | 325 | } |
| 315 | 326 | ||
| 316 | list_move_tail(&pt->shrinker_list, &shrinker_list); | 327 | list_move_tail(&pt->shrinker_list, &shrinker_list); |
| 317 | spin_unlock(&shrinker_lock); | 328 | mutex_unlock(&shrinker_lock); |
| 318 | 329 | ||
| 319 | return num_freed; | 330 | return num_freed; |
| 320 | } | 331 | } |
| @@ -507,7 +518,6 @@ void ttm_pool_init(struct ttm_pool *pool, struct device *dev, · 186 unmodified lines | |||
| 507 | ttm_pool_type_init(&pool->caching[i].orders[j], | 518 | ttm_pool_type_init(&pool->caching[i].orders[j], |
| 508 | pool, i, j); | 519 | pool, i, j); |
| 509 | } | 520 | } |
| 510 | EXPORT_SYMBOL(ttm_pool_init); | ||
| 511 | 521 | ||
| 512 | /** | 522 | /** |
| 513 | * ttm_pool_fini - Cleanup a pool | 523 | * ttm_pool_fini - Cleanup a pool |
| @@ -525,7 +535,6 @@ void ttm_pool_fini(struct ttm_pool *pool) · 11 unmodified lines | |||
| 525 | for (j = 0; j < MAX_ORDER; ++j) | 535 | for (j = 0; j < MAX_ORDER; ++j) |
| 526 | ttm_pool_type_fini(&pool->caching[i].orders[j]); | 536 | ttm_pool_type_fini(&pool->caching[i].orders[j]); |
| 527 | } | 537 | } |
| 528 | EXPORT_SYMBOL(ttm_pool_fini); | ||
| 529 | 538 | ||
| 530 | #ifdef CONFIG_DEBUG_FS | 539 | #ifdef CONFIG_DEBUG_FS |
| 531 | /* Count the number of pages available in a pool_type */ | 540 | /* Count the number of pages available in a pool_type */ |
| @@ -566,7 +575,7 @@ int ttm_pool_debugfs(struct ttm_pool *pool, struct seq_file *m) · 34 unmodified lines | |||
| 566 | { | 575 | { |
| 567 | unsigned int i; | 576 | unsigned int i; |
| 568 | 577 | ||
| 569 | spin_lock(&shrinker_lock); | 578 | mutex_lock(&shrinker_lock); |
| 570 | 579 | ||
| 571 | seq_puts(m, "\t "); | 580 | seq_puts(m, "\t "); |
| 572 | for (i = 0; i < MAX_ORDER; ++i) | 581 | for (i = 0; i < MAX_ORDER; ++i) |
| @@ -602,7 +611,7 @@ int ttm_pool_debugfs(struct ttm_pool *pool, struct seq_file *m) · 29 unmodified lines | |||
| 602 | seq_printf(m, "\ntotal\t: %8lu of %8lu\n", | 611 | seq_printf(m, "\ntotal\t: %8lu of %8lu\n", |
| 603 | atomic_long_read(&allocated_pages), page_pool_size); | 612 | atomic_long_read(&allocated_pages), page_pool_size); |
| 604 | 613 | ||
| 605 | spin_unlock(&shrinker_lock); | 614 | mutex_unlock(&shrinker_lock); |
| 606 | 615 | ||
| 607 | return 0; | 616 | return 0; |
| 608 | } | 617 | } |
| @@ -646,7 +655,7 @@ int ttm_pool_mgr_init(unsigned long num_pages) · 37 unmodified lines | |||
| 646 | if (!page_pool_size) | 655 | if (!page_pool_size) |
| 647 | page_pool_size = num_pages; | 656 | page_pool_size = num_pages; |
| 648 | 657 | ||
| 649 | spin_lock_init(&shrinker_lock); | 658 | mutex_init(&shrinker_lock); |
| 650 | INIT_LIST_HEAD(&shrinker_list); | 659 | INIT_LIST_HEAD(&shrinker_list); |
| 651 | 660 | ||
| 652 | for (i = 0; i < MAX_ORDER; ++i) { | 661 | for (i = 0; i < MAX_ORDER; ++i) { |
| @@ -1267,6 +1267,7 @@ static int vc4_hdmi_audio_init(struct vc4_hdmi *vc4_hdmi) · 1266 unmodified lines | |||
| 1267 | card->dai_link = dai_link; | 1267 | card->dai_link = dai_link; |
| 1268 | card->num_links = 1; | 1268 | card->num_links = 1; |
| 1269 | card->name = vc4_hdmi->variant->card_name; | 1269 | card->name = vc4_hdmi->variant->card_name; |
| 1270 | card->driver_name = "vc4-hdmi"; | ||
| 1270 | card->dev = dev; | 1271 | card->dev = dev; |
| 1271 | card->owner = THIS_MODULE; | 1272 | card->owner = THIS_MODULE; |
| 1272 | 1273 | ||
| @@ -620,11 +620,11 @@ static int vc4_hvs_bind(struct device *dev, struct device *master, void *data) · 619 unmodified lines | |||
| 620 | * for now we just allocate globally. | 620 | * for now we just allocate globally. |
| 621 | */ | 621 | */ |
| 622 | if (!hvs->hvs5) | 622 | if (!hvs->hvs5) |
| 623 | /* 96kB */ | 623 | /* 48k words of 2x12-bit pixels */ |
| 624 | drm_mm_init(&hvs->lbm_mm, 0, 96 * 1024); | 624 | drm_mm_init(&hvs->lbm_mm, 0, 48 * 1024); |
| 625 | else | 625 | else |
| 626 | /* 70k words */ | 626 | /* 60k words of 4x12-bit pixels */ |
| 627 | drm_mm_init(&hvs->lbm_mm, 0, 70 * 2 * 1024); | 627 | drm_mm_init(&hvs->lbm_mm, 0, 60 * 1024); |
| 628 | 628 | ||
| 629 | /* Upload filter kernels. We only have the one for now, so we | 629 | /* Upload filter kernels. We only have the one for now, so we |
| 630 | * keep it around for the lifetime of the driver. | 630 | * keep it around for the lifetime of the driver. |
| @@ -220,7 +220,7 @@ static void vc4_plane_reset(struct drm_plane *plane) · 219 unmodified lines | |||
| 220 | __drm_atomic_helper_plane_reset(plane, &vc4_state->base); | 220 | __drm_atomic_helper_plane_reset(plane, &vc4_state->base); |
| 221 | } | 221 | } |
| 222 | 222 | ||
| 223 | static void vc4_dlist_write(struct vc4_plane_state *vc4_state, u32 val) | 223 | static void vc4_dlist_counter_increment(struct vc4_plane_state *vc4_state) |
| 224 | { | 224 | { |
| 225 | if (vc4_state->dlist_count == vc4_state->dlist_size) { | 225 | if (vc4_state->dlist_count == vc4_state->dlist_size) { |
| 226 | u32 new_size = max(4u, vc4_state->dlist_count * 2); | 226 | u32 new_size = max(4u, vc4_state->dlist_count * 2); |
| @@ -235,7 +235,15 @@ static void vc4_dlist_write(struct vc4_plane_state *vc4_state, u32 val) · 8 unmodified lines | |||
| 235 | vc4_state->dlist_size = new_size; | 235 | vc4_state->dlist_size = new_size; |
| 236 | } | 236 | } |
| 237 | 237 | ||
| 238 | vc4_state->dlist[vc4_state->dlist_count++] = val; | 238 | vc4_state->dlist_count++; |
| 239 | } | ||
| 240 | |||
| 241 | static void vc4_dlist_write(struct vc4_plane_state *vc4_state, u32 val) | ||
| 242 | { | ||
| 243 | unsigned int idx = vc4_state->dlist_count; | ||
| 244 | |||
| 245 | vc4_dlist_counter_increment(vc4_state); | ||
| 246 | vc4_state->dlist[idx] = val; | ||
| 239 | } | 247 | } |
| 240 | 248 | ||
| 241 | /* Returns the scl0/scl1 field based on whether the dimensions need to | 249 | /* Returns the scl0/scl1 field based on whether the dimensions need to |
| @@ -437,6 +445,7 @@ static void vc4_write_ppf(struct vc4_plane_state *vc4_state, u32 src, u32 dst) · 195 unmodified lines | |||
| 437 | static u32 vc4_lbm_size(struct drm_plane_state *state) | 445 | static u32 vc4_lbm_size(struct drm_plane_state *state) |
| 438 | { | 446 | { |
| 439 | struct vc4_plane_state *vc4_state = to_vc4_plane_state(state); | 447 | struct vc4_plane_state *vc4_state = to_vc4_plane_state(state); |
| 448 | struct vc4_dev *vc4 = to_vc4_dev(state->plane->dev); | ||
| 440 | u32 pix_per_line; | 449 | u32 pix_per_line; |
| 441 | u32 lbm; | 450 | u32 lbm; |
| 442 | 451 | ||
| @@ -472,7 +481,11 @@ static u32 vc4_lbm_size(struct drm_plane_state *state) · 29 unmodified lines | |||
| 472 | lbm = pix_per_line * 16; | 481 | lbm = pix_per_line * 16; |
| 473 | } | 482 | } |
| 474 | 483 | ||
| 475 | lbm = roundup(lbm, 32); | 484 | /* Align it to 64 or 128 (hvs5) bytes */ |
| 485 | lbm = roundup(lbm, vc4->hvs->hvs5 ? 128 : 64); | ||
| 486 | |||
| 487 | /* Each "word" of the LBM memory contains 2 or 4 (hvs5) pixels */ | ||
| 488 | lbm /= vc4->hvs->hvs5 ? 4 : 2; | ||
| 476 | 489 | ||
| 477 | return lbm; | 490 | return lbm; |
| 478 | } | 491 | } |
| @@ -912,9 +925,9 @@ static int vc4_plane_mode_set(struct drm_plane *plane, · 433 unmodified lines | |||
| 912 | if (!vc4_state->is_unity) { | 925 | if (!vc4_state->is_unity) { |
| 913 | vc4_dlist_write(vc4_state, | 926 | vc4_dlist_write(vc4_state, |
| 914 | VC4_SET_FIELD(vc4_state->crtc_w, | 927 | VC4_SET_FIELD(vc4_state->crtc_w, |
| 915 | SCALER_POS1_SCL_WIDTH) | | 928 | SCALER5_POS1_SCL_WIDTH) | |
| 916 | VC4_SET_FIELD(vc4_state->crtc_h, | 929 | VC4_SET_FIELD(vc4_state->crtc_h, |
| 917 | SCALER_POS1_SCL_HEIGHT)); | 930 | SCALER5_POS1_SCL_HEIGHT)); |
| 918 | } | 931 | } |
| 919 | 932 | ||
| 920 | /* Position Word 2: Source Image Size */ | 933 | /* Position Word 2: Source Image Size */ |
| @@ -973,8 +986,10 @@ static int vc4_plane_mode_set(struct drm_plane *plane, · 52 unmodified lines | |||
| 973 | * be set when calling vc4_plane_allocate_lbm(). | 986 | * be set when calling vc4_plane_allocate_lbm(). |
| 974 | */ | 987 | */ |
| 975 | if (vc4_state->y_scaling[0] != VC4_SCALING_NONE || | 988 | if (vc4_state->y_scaling[0] != VC4_SCALING_NONE || |
| 976 | vc4_state->y_scaling[1] != VC4_SCALING_NONE) | 989 | vc4_state->y_scaling[1] != VC4_SCALING_NONE) { |
| 977 | vc4_state->lbm_offset = vc4_state->dlist_count++; | 990 | vc4_state->lbm_offset = vc4_state->dlist_count; |
| 991 | vc4_dlist_counter_increment(vc4_state); | ||
| 992 | } | ||
| 978 | 993 | ||
| 979 | if (num_planes > 1) { | 994 | if (num_planes > 1) { |
| 980 | /* Emit Cb/Cr as channel 0 and Y as channel | 995 | /* Emit Cb/Cr as channel 0 and Y as channel |
| @@ -1396,19 +1396,11 @@ static void zynqmp_disp_enable(struct zynqmp_disp *disp) · 1395 unmodified lines | |||
| 1396 | */ | 1396 | */ |
| 1397 | static void zynqmp_disp_disable(struct zynqmp_disp *disp) | 1397 | static void zynqmp_disp_disable(struct zynqmp_disp *disp) |
| 1398 | { | 1398 | { |
| 1399 | struct drm_crtc *crtc = &disp->crtc; | ||
| 1400 | |||
| 1401 | zynqmp_disp_audio_disable(&disp->audio); | 1399 | zynqmp_disp_audio_disable(&disp->audio); |
| 1402 | 1400 | ||
| 1403 | zynqmp_disp_avbuf_disable_audio(&disp->avbuf); | 1401 | zynqmp_disp_avbuf_disable_audio(&disp->avbuf); |
| 1404 | zynqmp_disp_avbuf_disable_channels(&disp->avbuf); | 1402 | zynqmp_disp_avbuf_disable_channels(&disp->avbuf); |
| 1405 | zynqmp_disp_avbuf_disable(&disp->avbuf); | 1403 | zynqmp_disp_avbuf_disable(&disp->avbuf); |
| 1406 | |||
| 1407 | /* Mark the flip is done as crtc is disabled anyway */ | ||
| 1408 | if (crtc->state->event) { | ||
| 1409 | complete_all(crtc->state->event->base.completion); | ||
| 1410 | crtc->state->event = NULL; | ||
| 1411 | } | ||
| 1412 | } | 1404 | } |
| 1413 | 1405 | ||
| 1414 | static inline struct zynqmp_disp *crtc_to_disp(struct drm_crtc *crtc) | 1406 | static inline struct zynqmp_disp *crtc_to_disp(struct drm_crtc *crtc) |
| @@ -1499,6 +1491,13 @@ zynqmp_disp_crtc_atomic_disable(struct drm_crtc *crtc, · 84 unmodified lines | |||
| 1499 | 1491 | ||
| 1500 | drm_crtc_vblank_off(&disp->crtc); | 1492 | drm_crtc_vblank_off(&disp->crtc); |
| 1501 | 1493 | ||
| 1494 | spin_lock_irq(&crtc->dev->event_lock); | ||
| 1495 | if (crtc->state->event) { | ||
| 1496 | drm_crtc_send_vblank_event(crtc, crtc->state->event); | ||
| 1497 | crtc->state->event = NULL; | ||
| 1498 | } | ||
| 1499 | spin_unlock_irq(&crtc->dev->event_lock); | ||
| 1500 | |||
| 1502 | clk_disable_unprepare(disp->pclk); | 1501 | clk_disable_unprepare(disp->pclk); |
| 1503 | pm_runtime_put_sync(disp->dev); | 1502 | pm_runtime_put_sync(disp->dev); |
| 1504 | } | 1503 | } |
| @@ -899,6 +899,7 @@ config HID_SONY · 898 unmodified lines | |||
| 899 | depends on NEW_LEDS | 899 | depends on NEW_LEDS |
| 900 | depends on LEDS_CLASS | 900 | depends on LEDS_CLASS |
| 901 | select POWER_SUPPLY | 901 | select POWER_SUPPLY |
| 902 | select CRC32 | ||
| 902 | help | 903 | help |
| 903 | Support for | 904 | Support for |
| 904 | 905 | ||
| @@ -154,7 +154,7 @@ int amd_sfh_hid_client_init(struct amd_mp2_dev *privdata) · 153 unmodified lines | |||
| 154 | 154 | ||
| 155 | for (i = 0; i < cl_data->num_hid_devices; i++) { | 155 | for (i = 0; i < cl_data->num_hid_devices; i++) { |
| 156 | cl_data->sensor_virt_addr[i] = dma_alloc_coherent(dev, sizeof(int) * 8, | 156 | cl_data->sensor_virt_addr[i] = dma_alloc_coherent(dev, sizeof(int) * 8, |
| 157 | &cl_data->sensor_phys_addr[i], | 157 | &cl_data->sensor_dma_addr[i], |
| 158 | GFP_KERNEL); | 158 | GFP_KERNEL); |
| 159 | cl_data->sensor_sts[i] = 0; | 159 | cl_data->sensor_sts[i] = 0; |
| 160 | cl_data->sensor_requested_cnt[i] = 0; | 160 | cl_data->sensor_requested_cnt[i] = 0; |
| @@ -187,7 +187,7 @@ int amd_sfh_hid_client_init(struct amd_mp2_dev *privdata) · 26 unmodified lines | |||
| 187 | } | 187 | } |
| 188 | info.period = msecs_to_jiffies(AMD_SFH_IDLE_LOOP); | 188 | info.period = msecs_to_jiffies(AMD_SFH_IDLE_LOOP); |
| 189 | info.sensor_idx = cl_idx; | 189 | info.sensor_idx = cl_idx; |
| 190 | info.phys_address = cl_data->sensor_phys_addr[i]; | ||
22 more lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 69 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 41 lines aren’t shown here.
This diff is large: its 101 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 32 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 52 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 70 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 273 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 38 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 42 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 99 lines aren’t shown here.
This diff is large: its 102 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 56 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 122 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 311 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 145 lines aren’t shown here.
This diff is large: its 30 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 4 lines aren’t shown here.
This diff is large: its 398 lines aren’t shown here.
This diff is large: its 41 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 72 lines aren’t shown here.
This diff is large: its 96 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 276 lines aren’t shown here.
This diff is large: its 206 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 59 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 67 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 268 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 127 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 338 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 116 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 48 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 51 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 119 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 61 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 56 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 71 lines aren’t shown here.
This diff is large: its 55 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 81 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 245 lines aren’t shown here.
This diff is large: its 55 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 73 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 80 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 39 lines aren’t shown here.
This diff is large: its 5 lines aren’t shown here.
This diff is large: its 5 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 50 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 54 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 88 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 81 lines aren’t shown here.
This diff is large: its 38 lines aren’t shown here.
This diff is large: its 98 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 91 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 38 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 48 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 70 lines aren’t shown here.
This diff is large: its 81 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 204 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 38 lines aren’t shown here.
This diff is large: its 59 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 114 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 48 lines aren’t shown here.
This diff is large: its 76 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 229 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 94 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 133 lines aren’t shown here.
This diff is large: its 53 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 335 lines aren’t shown here.
This diff is large: its 73 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 48 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 325 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 51 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 100 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 70 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 46 lines aren’t shown here.
This diff is large: its 93 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 72 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 61 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 88 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 93 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 39 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 115 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 268 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 95 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 47 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 32 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 51 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 4 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 49 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 180 lines aren’t shown here.
This diff is large: its 216 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 38 lines aren’t shown here.
This diff is large: its 45 lines aren’t shown here.
This diff is large: its 50 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 32 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 253 lines aren’t shown here.
This diff is large: its 107 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 276 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 146 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 30 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 134 lines aren’t shown here.
This diff is large: its 30 lines aren’t shown here.
This diff is large: its 41 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 88 lines aren’t shown here.
This diff is large: its 60 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 190 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 49 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 145 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 55 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 71 lines aren’t shown here.
This diff is large: its 163 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 178 lines aren’t shown here.
This diff is large: its 32 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 54 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 51 lines aren’t shown here.
This diff is large: its 78 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 49 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 122 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 42 lines aren’t shown here.
This diff is large: its 78 lines aren’t shown here.
This diff is large: its 123 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 203 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 50 lines aren’t shown here.
This diff is large: its 56 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 41 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 54 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 81 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 52 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 58 lines aren’t shown here.
This diff is large: its 81 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 124 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 52 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 139 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 84 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 53 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 38 lines aren’t shown here.
This diff is large: its 70 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 143 lines aren’t shown here.
This diff is large: its 74 lines aren’t shown here.
This diff is large: its 133 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 127 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 92 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 204 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 79 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 98 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 122 lines aren’t shown here.
This diff is large: its 46 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 169 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 146 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 83 lines aren’t shown here.
This diff is large: its 76 lines aren’t shown here.
This diff is large: its 375 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 1002 lines aren’t shown here.
This diff is large: its 164 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 30 lines aren’t shown here.
This diff is large: its 53 lines aren’t shown here.
This diff is large: its 71 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 272 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 55 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 153 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 34 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 74 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 94 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 75 lines aren’t shown here.
This diff is large: its 72 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 96 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 54 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 51 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 43 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 173 lines aren’t shown here.
This diff is large: its 60 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 88 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 91 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 145 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 43 lines aren’t shown here.
This diff is large: its 42 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 111 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 30 lines aren’t shown here.
This diff is large: its 30 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 383 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 5 lines aren’t shown here.
This diff is large: its 81 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 47 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 91 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 67 lines aren’t shown here.
This diff is large: its 204 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 32 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 59 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 41 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 73 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 67 lines aren’t shown here.
This diff is large: its 135 lines aren’t shown here.
This diff is large: its 140 lines aren’t shown here.
This diff is large: its 71 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 80 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 53 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 74 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 81 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 85 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 122 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 106 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 105 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 26 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 148 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 134 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 79 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 63 lines aren’t shown here.
This diff is large: its 78 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 96 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 101 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 57 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 207 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 104 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 98 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 60 lines aren’t shown here.
This diff is large: its 137 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 77 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 203 lines aren’t shown here.
This diff is large: its 117 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 33 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 27 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 55 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 21 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 64 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 46 lines aren’t shown here.
This diff is large: its 45 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 101 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 45 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 135 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 75 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 56 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 6 lines aren’t shown here.
This diff is large: its 14 lines aren’t shown here.
This diff is large: its 6 lines aren’t shown here.
This diff is large: its 6 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 6 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 6 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 111 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 72 lines aren’t shown here.
This diff is large: its 53 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 100 lines aren’t shown here.
This diff is large: its 47 lines aren’t shown here.
This diff is large: its 50 lines aren’t shown here.
This diff is large: its 41 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 59 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 48 lines aren’t shown here.
This diff is large: its 48 lines aren’t shown here.
This diff is large: its 55 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 30 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 70 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 73 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 133 lines aren’t shown here.
This diff is large: its 39 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 36 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 47 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 91 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 17 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 24 lines aren’t shown here.
This diff is large: its 49 lines aren’t shown here.
This diff is large: its 185 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 166 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 268 lines aren’t shown here.
This diff is large: its 48 lines aren’t shown here.
This diff is large: its 150 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 49 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 12 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 39 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 28 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 79 lines aren’t shown here.
This diff is large: its 15 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 56 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 840 lines aren’t shown here.
This diff is large: its 67 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 95 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 158 lines aren’t shown here.
This diff is large: its 221 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 11 lines aren’t shown here.
This diff is large: its 1130 lines aren’t shown here.
This diff is large: its 110 lines aren’t shown here.
This diff is large: its 13 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 151 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 103 lines aren’t shown here.
This diff is large: its 65 lines aren’t shown here.
This diff is large: its 40 lines aren’t shown here.
This diff is large: its 37 lines aren’t shown here.
This diff is large: its 18 lines aren’t shown here.
This diff is large: its 25 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 226 lines aren’t shown here.
This diff is large: its 295 lines aren’t shown here.
This diff is large: its 219 lines aren’t shown here.
This diff is large: its 22 lines aren’t shown here.
This diff is large: its 23 lines aren’t shown here.
This diff is large: its 193 lines aren’t shown here.
This diff is large: its 71 lines aren’t shown here.
This diff is large: its 16 lines aren’t shown here.
This diff is large: its 135 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 8 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 92 lines aren’t shown here.
This diff is large: its 44 lines aren’t shown here.
This diff is large: its 31 lines aren’t shown here.
This diff is large: its 107 lines aren’t shown here.
This diff is large: its 66 lines aren’t shown here.
This diff is large: its 10 lines aren’t shown here.
This diff is large: its 207 lines aren’t shown here.
This diff is large: its 35 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 20 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 7 lines aren’t shown here.
This diff is large: its 29 lines aren’t shown here.
This diff is large: its 56 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
This diff is large: its 9 lines aren’t shown here.
File renamed without changes.
This diff is large: its 6 lines aren’t shown here.
This diff is large: its 19 lines aren’t shown here.